动态生成Protobuf消息并将指针返回到它
Dynamically generate protobuf Message and return a pointer to it
首先,我对C 的经验不太经验,所以也许我在这里监督一些东西。我正在尝试通过以下代码从.proto文件中动态生成Protobuf消息:
int init_msg(const std::string & filename, protobuf::Arena* arena, protobuf::Message** new_msg){
using namespace google::protobuf;
using namespace google::protobuf::compiler;
DiskSourceTree source_tree;
source_tree.MapPath("file", filename);
MuFiErCo error_mist;
Importer imp(&source_tree, &error_mist);
printf("Lade Datei:%s n", filename.c_str());
const FileDescriptor* f_desc = imp.Import("file");
const Descriptor* desc = f_desc->FindMessageTypeByName("TestNachricht");
const Message* new_msg_proto = dmf.GetPrototype(desc);
*new_msg = new_msg_proto->New(arena);
//Debug
cout << (*new_msg)->GetTypeName() << endl;
return 0;
}
int main(int argc, char* argv[]){
protobuf::Arena arena;
protobuf::Message *adr2, *adr1;
init_msg("schema-1.proto", &arena, &adr1);
init_msg("schema-1.proto", &arena, &adr2);
printf("MSG_Pointer: %p, %pn", adr1, adr2);
cout << adr1->GetTypeName() << endl;
arena.Reset();
return 0;
}
我以为如果我使用竞技场,新消息也可以在功能范围之外提供。但是,如果我尝试访问消息,总会有一个segfault。我想这是一个简单的错误,但我不知道,如何解决这个问题。
这是OUPUT:
Lade Datei:schema-1.proto
packet.TestNachricht
Lade Datei:schema-1.proto
packet.TestNachricht
MSG_Pointer: 0x1b293b0, 0x1b287f0
Speicherzugriffsfehler (Speicherabzug geschrieben)
我认为,问题是,当提交的文字者等人被摧毁时 init_msg返回,留下新创建的消息,无法 询问其.proto定义。您需要移动进口商 实例向主机保持生命。这与 竞技场。 - Igor Tandetnik
那是解决方案。
这是一些有效的示例代码
#include <string>
#include <stdio.h>
#include <stdlib.h>
#include <iostream>
#include <memory>
#include <google/protobuf/descriptor.h>
#include <google/protobuf/message.h>
#include <google/protobuf/compiler/importer.h>
#include <google/protobuf/dynamic_message.h>
#include <google/protobuf/arena.h>
using namespace std;
using namespace google::protobuf;
class MuFiErCo : public compiler::MultiFileErrorCollector
{
public:
void AddError(const string & filename, int line, int column, const string & message){
printf("Err: %sn", message.c_str());
}
void AddWarning(const string & filename, int line, int column, const string & message){
printf("Warn: %sn", message.c_str());
}
};
compiler::Importer* init_proto_dir(Arena* arena, const std::string &root_dir){
using namespace compiler;
static DiskSourceTree source_tree;
source_tree.MapPath("", root_dir);
static MuFiErCo error_mist;
static Importer* imp = Arena::Create<Importer>(arena, &source_tree, &error_mist);
return imp;
}
void init_proto_def(compiler::Importer* imp, const std::string &proto_file){
using namespace compiler;
imp->Import(proto_file);
return;
}
Message* init_msg(compiler::Importer* imp, Arena* arena, const std::string &msg_name){
const DescriptorPool* pool = imp->pool();
static DynamicMessageFactory dmf;
const Descriptor* desc = pool->FindMessageTypeByName(msg_name);
const Message* msg_proto = dmf.GetPrototype(desc);
return msg_proto->New(arena);
}
int set_value(Message* msg, const char* value_name, unsigned long int value){
const Message::Reflection* reflec = msg->GetReflection();
const Descriptor* desc = msg->GetDescriptor();
const FieldDescriptor* fdesc = desc->FindFieldByName(value_name);
reflec->SetUInt64(msg, fdesc, value);
return 0;
}
int main(int argc, char* argv[]){
Arena arena;
compiler::Importer* imp = init_proto_dir(&arena, "");
init_proto_def(imp, "schema-1.proto");
Message* msg = init_msg(imp, &arena, "packet.TestNachricht");
set_value(msg, "zahl", 23434);
cout << msg->DebugString() << endl;
return 0;
}
相关文章:
- 在 const 函数中通过引用和指针返回之间的区别
- 指向 std::unrodered_map 中元素的指针返回'Read access violation'
- 为什么要为指针返回类型返回一系列字符?
- Visual C 运行时:Malloc将指针返回到已经使用的内存(包含实际字符串)
- 将原始指针返回到智能指针
- 从函数中的指针返回对象,例如链接列表
- 将指针返回使用New创建的数组数组
- 查找并将指针返回向量中的对象
- 函数可以将指针返回其自己的类型
- 指针返回值的地址
- 为什么静态指针返回函数中有一个"静态"键?
- 从弱指针返回类型返回共享指针
- 如何将C++引用和指针返回转换为 C++/CLR
- 从指针返回对象时出现意外的析构函数调用
- 阵列指针返回垃圾
- (C )当在同一类中调用时,污点指针返回正确的值,而从MAIN调用时为0
- C 从指针返回到成员功能
- 在构造函数以外的任何其他位置访问相机时,我的相机指针返回 null
- 从取消引用的指针返回原始指针
- 指针返回