我在静态初始化期间实例化的 protobuf 消息遇到问题。 DebugPrint() 等一些函数会导致崩溃,并且序列化失败并出现大小不匹配的错误。
考虑https://developers.google.com/protocol-buffers/docs/reference/cpp/google.protobuf.common#ShutdownProtobufLibrary.details并查看生成的 mymessage.pb.cc 文件,我认为问题在于尚未调用消息的静态初始值设定项。
有谁知道我是否可以以某种“合法”的方式强制预先调用消息的静态初始值设定项(或者我调用它们)?通过查看生成的代码,我可以调用一些神奇出现的函数,但这似乎很可能会中断。或者这只是我必须忍受并懒惰地初始化消息的东西?
最佳答案
在尝试使用 MyType
之前,至少尝试调用一次 MyType::default_instance()
。这会触发一系列可能满足您需求的初始化。
如果这不起作用,那么您将需要找到一些方法使 .pb.o 的动态初始化程序在您自己的代码之前运行。这可能取决于对象在链接器命令行中列出的顺序,您可以通过更改该顺序来“解决”问题,尽管这显然是一个糟糕的 hack。
如果这也不起作用,那你就不走运了。不要依赖动态初始化,而是考虑使用 pthread_once
或 Win32 的 InitOnce
在首次使用时初始化您的数据。
FWIW,Cap'n Proto ,来自同一作者(我)的 Protobufs 的更新替代品,具有严格的无动态初始化程序策略,因此不存在此类问题。
(术语吹毛求疵:“静态初始化”指的是在编译时知道结果内存内容的初始化程序,因此不需要在启动时执行代码。这包括例如基本类型的全局变量或constexpr
s.“动态初始化”指的是在启动时运行的构造函数,这就是您在这里所说的。不可否认,几乎每个人都犯了这个错误,历史上包括我自己。)
关于c++ - 全局 protobuf 消息,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/27088810/