Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Exception handling in Protocol Buffers C++

I don't find anything in Protocol Buffers documentation for exception handling in C++. In Javadoc it has clearly defined ones like InvalidProtocolBufferException, but not in C++.

Sometimes I ran my program and it crashes when it finds missing fields in what it thinks a valid message, then it simply stops and throws errors like this:

[libprotobuf FATAL google/protobuf/message_lite.cc:273] CHECK failed: 
IsInitialized(): Can't serialize message of type "XXX" because it is 
missing required fields: YY, ZZ
unknown file: Failure
C++ exception with description "CHECK failed: IsInitialized(): Can't 
serialize message of type "XXX" because it is missing required fields: 
YY, ZZ" thrown in the test body.

The source code of message_lite.cc all wrapped around with "GOOGLE_DCHECK" or "InitializationErrorMessage"...

My application does not allow exceptions like this to halt the program (not sure what the term is in C++ but basically no UncheckedExceptions), so I really need a way to catch these, log errors, and return gracefully, in case some messages got severely corrupted. Is there anyway doing that? Why do I see this post indicating some sort of google::protobuf::FatalException but I couldn't find documentations around it (only FatalException probably not enough also).

Thanks!

like image 488
Superziyi Avatar asked Dec 19 '22 05:12

Superziyi


1 Answers

The failure you are seeing indicates that there is a bug in your program -- the program has requested to serialize a message without having filled in all the required fields first. Think of this like a segmentation fault. You shouldn't try to catch this exception -- you should instead fix your app so that the exception never happens in the first place.

Note that the check is a DCHECK, meaning it is only checked in debug builds. In your release builds (when NDEBUG is defined), this check will be skipped and the message will be written even though it is not valid. So, you don't have to worry about this crashing your application in production, only while debugging.

(Technically you could catch google::protobuf::FatalException, but the Protobuf code was not originally designed to be exception-safe. Originally, check failures would simply abort the program. It looks like FatalException was added recently, but since the code is not exception-safe, it's likely that you'll have memory leaks any time a FatalException is thrown. So, you probably should treat it like an abort().)

like image 179
Kenton Varda Avatar answered Jan 01 '23 16:01

Kenton Varda