23 #ifndef DCCLCOMPAT20131116H 24 #define DCCLCOMPAT20131116H 26 #include "goby/acomms/acomms_helpers.h" 27 #include "goby/acomms/protobuf/dccl.pb.h" 28 #include "goby/common/logger.h" 29 #include "goby/util/binary.h" 31 #include "dccl/codec.h" 32 #include "dccl/codecs2/field_codec_default.h" 33 #include "dccl/field_codec_id.h" 34 #include "dccl/internal/field_codec_message_stack.h" 47 typedef dccl::Exception DCCLException;
48 typedef dccl::NullValueException DCCLNullValueException;
50 typedef dccl::DefaultIdentifierCodec DCCLDefaultIdentifierCodec;
51 template <
typename WireType,
typename FieldType = WireType>
56 typedef dccl::v2::DefaultBoolCodec DCCLDefaultBoolCodec;
57 typedef dccl::v2::DefaultStringCodec DCCLDefaultStringCodec;
58 typedef dccl::v2::DefaultBytesCodec DCCLDefaultBytesCodec;
59 typedef dccl::v2::DefaultEnumCodec DCCLDefaultEnumCodec;
65 typedef dccl::MessagePart MessagePart;
66 static const MessagePart HEAD = dccl::HEAD, BODY = dccl::BODY, UNKNOWN = dccl::UNKNOWN;
71 BOOST_STATIC_ASSERT(
sizeof(
TimeCodec) == 0);
88 typedef dccl::v2::DefaultMessageCodec DCCLDefaultMessageCodec;
90 typedef dccl::FieldCodecBase DCCLFieldCodecBase;
92 template <
typename WireType,
typename FieldType = WireType>
95 typedef dccl::FieldCodecBase DCCLFieldCodecBase;
98 template <
typename WireType,
typename FieldType = WireType>
101 typedef dccl::FieldCodecBase DCCLFieldCodecBase;
104 template <
typename WireType,
typename FieldType = WireType>
107 typedef dccl::FieldCodecBase DCCLFieldCodecBase;
110 typedef dccl::FieldCodecManager DCCLFieldCodecManager;
112 typedef dccl::FieldCodecManager DCCLFieldCodecManager;
113 typedef dccl::internal::FromProtoCppTypeBase FromProtoCppTypeBase;
117 typedef dccl::Bitset Bitset;
118 typedef dccl::internal::TypeHelper DCCLTypeHelper;
134 boost::shared_ptr<dccl::Codec>
codec() {
return codec_; }
144 bool new_id_codec = (cfg_.id_codec() != cfg.id_codec());
146 process_cfg(new_id_codec);
149 void load_shared_library_codecs(
void* dl_handle)
151 codec_->load_library(dl_handle);
152 loaded_libs_.insert(dl_handle);
155 template <
typename ProtobufMessage>
void validate() { validate(ProtobufMessage::descriptor()); }
157 template <
typename ProtobufMessage>
void info(std::ostream* os)
const 159 info(ProtobufMessage::descriptor(), os);
162 void info_all(std::ostream* os)
const { codec_->info_all(os); }
164 template <
typename ProtobufMessage>
unsigned id()
const 166 return id(ProtobufMessage::descriptor());
171 static const std::string& glog_encode_group() {
return glog_encode_group_; }
172 static const std::string& glog_decode_group() {
return glog_decode_group_; }
177 codec_->encode(bytes, msg, header_only);
182 codec_->decode(bytes, msg, header_only);
185 unsigned id_from_encoded(
const std::string& bytes) {
return codec_->id(bytes); }
187 void validate(
const google::protobuf::Descriptor* desc)
190 loaded_msgs_.insert(desc);
193 void validate_repeated(
const std::list<const google::protobuf::Descriptor*>& descs)
195 BOOST_FOREACH (
const google::protobuf::Descriptor* p, descs)
199 void info(
const google::protobuf::Descriptor* desc, std::ostream* os)
const 201 codec_->info(desc, os);
204 void info_repeated(
const std::list<const google::protobuf::Descriptor*>& desc,
205 std::ostream* os)
const 207 BOOST_FOREACH (
const google::protobuf::Descriptor* p, desc)
211 unsigned id(
const google::protobuf::Descriptor* desc)
const 213 return desc->options().GetExtension(dccl::msg).id();
216 template <
typename GoogleProtobufMessagePo
inter>
217 unsigned size_repeated(
const std::list<GoogleProtobufMessagePointer>& msgs)
220 BOOST_FOREACH (
const GoogleProtobufMessagePointer& msg, msgs)
225 template <
typename GoogleProtobufMessagePo
inter>
226 GoogleProtobufMessagePointer decode(
const std::string& bytes,
bool header_only =
false)
228 return codec_->decode<GoogleProtobufMessagePointer>(bytes, header_only);
231 template <
typename GoogleProtobufMessagePo
inter>
232 std::string encode_repeated(
const std::list<GoogleProtobufMessagePointer>& msgs)
235 BOOST_FOREACH (
const GoogleProtobufMessagePointer& msg, msgs)
238 encode(&piece, *msg);
245 template <
typename GoogleProtobufMessagePo
inter>
246 std::list<GoogleProtobufMessagePointer> decode_repeated(
const std::string& orig_bytes)
248 std::string bytes = orig_bytes;
249 std::list<GoogleProtobufMessagePointer> out;
250 while (!bytes.empty())
254 out.push_back(decode<GoogleProtobufMessagePointer>(bytes));
255 unsigned last_size = size(*out.back());
256 glog.is(common::logger::DEBUG1) &&
glog <<
"last message size was: " << last_size
258 bytes.erase(0, last_size);
260 catch (dccl::Exception& e)
266 glog.is(common::logger::WARN) &&
267 glog <<
"failed to decode " << goby::util::hex_encode(bytes)
268 <<
" but returning parts already decoded" << std::endl;
276 template <
typename DCCLTypedFieldCodecU
int32>
void add_id_codec(
const std::string& identifier)
278 dccl::FieldCodecManager::add<DCCLTypedFieldCodecUint32>(identifier);
281 void set_id_codec(
const std::string& identifier)
283 codec_.reset(
new dccl::Codec(identifier));
285 for (std::set<void*>::const_iterator it = loaded_libs_.begin(), end = loaded_libs_.end();
287 load_shared_library_codecs(*it);
289 for (std::set<const google::protobuf::Descriptor*>::const_iterator
290 it = loaded_msgs_.begin(),
291 end = loaded_msgs_.end();
298 catch (dccl::Exception& e)
300 glog.is(common::logger::WARN) &&
glog <<
"Failed to reload " << (*it)->full_name()
301 <<
" after ID codec change: " << e.what()
307 void reset_id_codec() { set_id_codec(dccl::Codec::default_id_codec_name()); }
313 template <
typename T>
friend void boost::checked_delete(T*);
321 void process_cfg(
bool new_id_codec)
323 if (cfg_.has_crypto_passphrase())
325 std::set<unsigned> skip_crypto_ids;
326 for (
int i = 0, n = cfg_.skip_crypto_for_id_size(); i < n; ++i)
327 skip_crypto_ids.insert(cfg_.skip_crypto_for_id(i));
328 codec_->set_crypto_passphrase(cfg_.crypto_passphrase(), skip_crypto_ids);
331 if (new_id_codec && cfg_.has_id_codec())
333 set_id_codec(cfg_.id_codec());
337 void dlog_message(
const std::string& msg, dccl::logger::Verbosity vrb, dccl::logger::Group grp)
339 if (grp == dccl::logger::DECODE)
340 goby::glog << group(glog_decode_group_) << msg << std::endl;
341 else if (grp == dccl::logger::ENCODE)
342 goby::glog << group(glog_encode_group_) << msg << std::endl;
343 else if (grp == dccl::logger::SIZE)
344 goby::glog << group(glog_encode_group_) <<
" {size} " << msg << std::endl;
346 goby::glog << group(glog_encode_group_) << msg << std::endl;
350 static boost::shared_ptr<DCCLCodec> inst_;
352 static std::string glog_encode_group_;
353 static std::string glog_decode_group_;
357 boost::shared_ptr<dccl::Codec> codec_;
359 std::set<void*> loaded_libs_;
360 std::set<const google::protobuf::Descriptor*> loaded_msgs_;
363 inline std::ostream& operator<<(std::ostream& os,
const DCCLCodec& codec)
static DCCLCodec * get()
DCCLCodec is a singleton class; use this to get a pointer to the class.
boost::shared_ptr< dccl::Codec > codec()
Return the underlying dccl::Codec that is used by this wrapper.
google::protobuf::int64 int64
a signed 64 bit integer
common::FlexOstream glog
Access the Goby logger through this object.
The global namespace for the Goby project.
google::protobuf::uint64 uint64
an unsigned 64 bit integer