简体   繁体   English

C ++静态初始化vs __attribute __((构造函数))

[英]C++ static initialization vs __attribute__((constructor))

Example: 例:

struct Foo { Foo() { printf("foo\n"); } };
static Foo foo;

__attribute__((constructor)) static void _bar() { printf("bar\n"); }

Is it deterministic wether foo or bar is printed first? 它是确定性的,首先打印foobar

(I hope and would expect that constructors of static objects are always executed first but not sure and GCCs doc about the constructor attribute doesn't say anything about it.) (我希望并且期望静态对象的构造函数总是先执行但不确定,并且关于构造函数属性的GCC文档没有说明任何内容。)

foo will be printed first, as the objects are initialized in the order of their declarations. 首先打印foo ,因为对象按其声明的顺序初始化。 Run and see: 跑步看看:

By the way, __attribute__((constructor)) is not Standard C++. 顺便说一句, __attribute__((constructor))不是标准C ++。 It is GCC's extension. 这是GCC的延伸。 So the behavior of your program depends on how GCC has defined it. 因此,程序的行为取决于GCC如何定义它。 In short, it is implementation-defined, according to it foo is printed first. 简而言之,它是实现定义的,根据它首先打印foo

The doc says, 医生说,

The constructor attribute causes the function to be called automatically before execution enters main (). 构造函数属性导致在执行main()之前自动调用该函数。 Similarly, the destructor attribute causes the function to be called automatically after main () has completed or exit () has been called. 类似地,析构函数属性导致在main()完成或调用exit()之后自动调用该函数。 Functions with these attributes are useful for initializing data that will be used implicitly during the execution of the program. 具有这些属性的函数对于初始化将在程序执行期间隐式使用的数据非常有用。

You may provide an optional integer priority to control the order in which constructor and destructor functions are run. 您可以提供可选的整数优先级来控制构造函数和析构函数的运行顺序。 A constructor with a smaller priority number runs before a constructor with a larger priority number; 具有较小优先级编号的构造函数在具有较大优先级编号的构造函数之前运行; the opposite relationship holds for destructors. 析构函数的相反关系成立。 So, if you have a constructor that allocates a resource and a destructor that deallocates the same resource, both functions typically have the same priority. 因此,如果您有一个分配资源的构造函数和一个释放相同资源的析构函数,那么这两个函数通常具有相同的优先级。 The priorities for constructor and destructor functions are the same as those specified for namespace-scope C++ objects (see C++ Attributes). 构造函数和析构函数的优先级与为命名空间范围的C ++对象指定的优先级相同 (请参阅C ++属性)。

I think the text in bold implies, the objects are initialized in the order of their declarations, as I said before, which is pretty much confirmed by online demo also. 我认为粗体文本意味着,对象按其声明的顺序进行初始化,正如我之前所说的那样,这也得到了在线演示的证实。

I guess you would also like to read this: 我猜你也想读这个:

If you want to control/alter the initialization order, you can use init_priority attribute, providing priority . 如果要控制/更改初始化顺序,可以使用init_priority属性,提供优先级 Taken from the page : 摘自页面

Some_Class  A  __attribute__ ((init_priority (2000)));
Some_Class  B  __attribute__ ((init_priority (543)));

Here, B is initialized before A . 这里, BA之前初始化。

It seems non-deterministic. 这似乎是不确定的。 I also had foo\\nbar\\n as the output of the example in my question when compiled with GCC. 在使用GCC编译时,我的foo\\nbar\\n作为我的问题中示例的输出。 However, when compiled with LLVM/Clang, I get bar\\nfoo\\n . 但是,当使用LLVM / Clang编译时,我得到了bar\\nfoo\\n

But, as I'm not sure if this might be a bug in Clang, I filled a bug report here . 但是,由于我不确定这可能是Clang中的错误,我在这里填写了错误报告。 Edit: I got an answer there and it seems to be really a bug in Clang which is not yet fixed. 编辑:我在那里得到了一个答案,它似乎真的是一个尚未修复的Clang中的错误。 Not sure what to conclude from that. 不知道从中得出什么结论。 The expected and should-be behavior really is deterministic here, however, you can't depend on it as there is at least one major compiler (Clang) which does it wrong (or different than GCC, if we take that as the spec for __attribute__((constructor)) ). 预期和应该行为在这里确实是确定性的,但是,你不能依赖它,因为至少有一个主要编译器(Clang)做错了(或者与GCC不同,如果我们把它作为规范__attribute__((constructor)) )。

Note that this can be really relevant and important in real world code. 请注意,这在现实世界的代码中可能非常重要和重要。 Eg here is an example which seeds a random generator which fails with Clang. 例如, 这里是一个种子随着Clang失败的随机发生器的例子。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM