我一直在尝试测试不同.cpp
文件中朋友类的多个定义是否有效。为此,我在main_class.hpp
文件中定义了一个主类:
class main_class
{
private:
int a;
int b;
int gimme_a()
{
return a;
}
public:
main_class(int a, int b) : a(a), b(b) {}
int gimme_b()
{
return b;
}
friend class main_class_friend;
};
然后我定义main_class_friend
了两次,首先是在main_friend_class1.cpp
文件中:
class main_class_friend
{
main_class c;
public:
main_class_friend() : c(10, 10) {}
int gimme_a()
{
return c.gimme_a();
}
int gimme_b()
{
return c.gimme_b();
}
};
和相应的公共测试功能:
void test1()
{
main_class_friend ff;
std::cout << "Gimme a: " << ff.gimme_a() << " and gimme b: " <<
ff.gimme_b() << std::endl;
}
然后我定义了第二个main_class_friend
内部main_friend_class2.cpp
和一个相应的公共测试函数:
class main_class_friend
{
private:
main_class ca;
int c;
public:
main_class_friend() : ca(9 ,9), c(11) {}
int gimme_a()
{
return ca.gimme_a();
}
int gimme_b()
{
return ca.gimme_b();
}
int gimme_c()
{
return c;
}
};
void test2()
{
main_class_friend ff;
std::cout << "Gimme a: " << ff.gimme_a() << " and gimme b: " << ff.gimme_b()
<< " and gimme c: " << ff.gimme_c() << std::endl;
}
最后我在 main 中调用test1
并运行:test2
int main()
{
test1();
test2();
return 0;
}
编译程序(没有错误g++
),然后运行它。输出是:
Gimme a: 9 and gimme b: 9
*** stack smashing detected ***: ./a.out terminated
Aborted (core dumped)
对我来说真正奇怪的是,它a
是b
由内部的构造函数初始化的,main_friend_class2.cpp
而不是定义函数的main_friend_class1.cpp
地方test1
。
然后我发现当一个程序用-fstack-protector
flag编译时,可以很容易地调试堆栈粉碎。所以我再次编译它,然后程序的输出是:
Gimme a: 9 and gimme b: 9
Gimme a: 9 and gimme b: 9 and gimme c: 11
所以没有更多的堆栈粉碎问题,但是test1
和test2
函数都使用main_friend_class2.cpp
文件中的构造函数。
这附近发生了什么?我不明白。如果没有缓冲区溢出,为什么会出现堆栈粉碎错误,因为没有使用任何缓冲区?
我的第二个问题是:有没有办法定义多次main_class_friend
,但是在不同的文件中使用它们以使它们对于使用类的文件“私有”?