@@ -21,6 +21,9 @@ $fileHeader(ctx=ctx, file=[ctx.filename, "PubSubTypes.cpp"], description=["This
2121
2222#include "$ctx.filename$PubSubTypes.hpp"
2323
24+ #include <algorithm>
25+ #include <mutex>
26+
2427#include <fastdds/dds/log/Log.hpp>
2528#include <fastdds/rtps/common/CdrSerialization.hpp>
2629
@@ -34,7 +37,6 @@ using InstanceHandle_t = eprosima::fastdds::rtps::InstanceHandle_t;
3437using DataRepresentationId_t = eprosima::fastdds::dds::DataRepresentationId_t;
3538
3639$definitions; separator="\n"$
37-
3840$if(ctx.thereIsStructOrUnion || ctx.thereIsInterface)$
3941// Include auxiliary functions like for serializing/deserializing.
4042#include "$ctx.filename$CdrAux.ipp"
@@ -44,7 +46,7 @@ $endif$
4446
4547module(ctx, parent, module, definition_list) ::= <<
4648namespace $module.name$ {
47- $definition_list$
49+ $definition_list$
4850} // namespace $module.name$
4951
5052>>
@@ -58,26 +60,32 @@ $struct.name$PubSubType::$struct.name$PubSubType()
5860 uint32_t type_size = $struct.cScopedname$_max_cdr_typesize;
5961 type_size += static_cast<uint32_t>(eprosima::fastcdr::Cdr::alignment(type_size, 4)); /* possible submessage alignment */
6062 max_serialized_type_size = type_size + 4; /*encapsulation*/
61- is_compute_key_provided = $if(struct.hasKey)$true$else$false$endif$;
62- uint32_t key_length = $struct.cScopedname$_max_key_cdr_typesize > 16 ? $struct.cScopedname$_max_key_cdr_typesize : 16;
63- key_buffer_ = reinterpret_cast<unsigned char*>(malloc(key_length));
64- memset(key_buffer_, 0, key_length);
63+ $if(struct.hasKey)$
64+ is_compute_key_provided = true;
65+ key_buffer_ = nullptr;
66+ get_key_buffer_nts();
67+ $else$
68+ is_compute_key_provided = false;
69+ $endif$
6570}
6671
6772$struct.name$PubSubType::~$struct.name$PubSubType()
6873{
74+ $if(struct.hasKey)$
6975 if (key_buffer_ != nullptr)
7076 {
7177 free(key_buffer_);
7278 }
79+ $endif$
7380}
7481
7582bool $struct.name$PubSubType::serialize(
7683 const void* const data,
7784 SerializedPayload_t& payload,
7885 DataRepresentationId_t data_representation)
7986{
80- const ::$struct.scopedname$* p_type = static_cast<const ::$struct.scopedname$*>(data);
87+ const ::$struct.scopedname$* p_type =
88+ static_cast<const ::$struct.scopedname$*>(data);
8189
8290 // Object that manages the raw buffer.
8391 eprosima::fastcdr::FastBuffer fastbuffer(reinterpret_cast<char*>(payload.data), payload.max_size);
@@ -97,7 +105,7 @@ bool $struct.name$PubSubType::serialize(
97105 ser.serialize_encapsulation();
98106 // Serialize the object.
99107 ser << *p_type;
100- ser.set_dds_cdr_options({0,0});
108+ ser.set_dds_cdr_options({0, 0});
101109 }
102110 catch (eprosima::fastcdr::exception::Exception& /*exception*/)
103111 {
@@ -116,7 +124,8 @@ bool $struct.name$PubSubType::deserialize(
116124 try
117125 {
118126 // Convert DATA to pointer of your type
119- ::$struct.scopedname$* p_type = static_cast<::$struct.scopedname$*>(data);
127+ ::$struct.scopedname$* p_type =
128+ static_cast<::$struct.scopedname$*>(data);
120129
121130 // Object that manages the raw buffer.
122131 eprosima::fastcdr::FastBuffer fastbuffer(reinterpret_cast<char*>(payload.data), payload.length);
@@ -149,9 +158,10 @@ uint32_t $struct.name$PubSubType::calculate_serialized_size(
149158 data_representation == DataRepresentationId_t::XCDR_DATA_REPRESENTATION ?
150159 eprosima::fastcdr::CdrVersion::XCDRv1 :eprosima::fastcdr::CdrVersion::XCDRv2);
151160 size_t current_alignment {0};
152- return static_cast<uint32_t>(calculator.calculate_serialized_size(
153- *static_cast<const ::$struct.scopedname$*>(data), current_alignment)) +
154- 4u /*encapsulation*/;
161+ const ::$struct.scopedname$* p_type =
162+ static_cast<const ::$struct.scopedname$*>(data);
163+ auto calc_size = calculator.calculate_serialized_size(*p_type, current_alignment);
164+ return static_cast<uint32_t>(calc_size) + 4u /*encapsulation*/;
155165 }
156166 catch (eprosima::fastcdr::exception::Exception& /*exception*/)
157167 {
@@ -175,16 +185,17 @@ bool $struct.name$PubSubType::compute_key(
175185 InstanceHandle_t& handle,
176186 bool force_md5)
177187{
178- if (!is_compute_key_provided)
179- {
180- return false;
181- }
182-
188+ $if(struct.hasKey)$
183189 ::$struct.scopedname$ data;
184190 if (deserialize(payload, static_cast<void*>(&data)))
185191 {
186192 return compute_key(static_cast<void*>(&data), handle, force_md5);
187193 }
194+ $else$
195+ static_cast<void>(payload);
196+ static_cast<void>(handle);
197+ static_cast<void>(force_md5);
198+ $endif$
188199
189200 return false;
190201}
@@ -194,48 +205,80 @@ bool $struct.name$PubSubType::compute_key(
194205 InstanceHandle_t& handle,
195206 bool force_md5)
196207{
197- if (!is_compute_key_provided)
208+ $if(struct.hasKey)$
209+ std::lock_guard<std::mutex> guard(compute_key_mtx_);
210+ const ::$struct.scopedname$* p_type =
211+ static_cast<const ::$struct.scopedname$*>(data);
212+
213+ // Ensure the key buffer is reserved
214+ unsigned char* key_buffer = get_key_buffer_nts();
215+ if (key_buffer == nullptr)
198216 {
199217 return false;
200218 }
201219
202- const ::$struct.scopedname$* p_type = static_cast<const ::$struct.scopedname$*>(data);
203-
204220 // Object that manages the raw buffer.
205- eprosima::fastcdr::FastBuffer fastbuffer(reinterpret_cast<char*>(key_buffer_ ),
221+ eprosima::fastcdr::FastBuffer fastbuffer(reinterpret_cast<char*>(key_buffer ),
206222 $struct.cScopedname$_max_key_cdr_typesize);
207223
208224 // Object that serializes the data.
209- eprosima::fastcdr::Cdr ser(fastbuffer, eprosima::fastcdr::Cdr::BIG_ENDIANNESS, eprosima::fastcdr::CdrVersion::XCDRv2);
225+ eprosima::fastcdr::Cdr ser(
226+ fastbuffer,
227+ eprosima::fastcdr::Cdr::BIG_ENDIANNESS,
228+ eprosima::fastcdr::CdrVersion::XCDRv2);
210229 ser.set_encoding_flag(eprosima::fastcdr::EncodingAlgorithmFlag::PLAIN_CDR2);
211230 eprosima::fastcdr::serialize_key(ser, *p_type);
212231 if (force_md5 || $struct.cScopedname$_max_key_cdr_typesize > 16)
213232 {
214- md5_.init();
215- md5_.update(key_buffer_, static_cast<unsigned int>(ser.get_serialized_data_length()));
216- md5_.finalize();
233+ eprosima::fastdds::MD5 md5;
234+ md5.init();
235+ md5.update(key_buffer, static_cast<unsigned int>(ser.get_serialized_data_length()));
236+ md5.finalize();
217237 for (uint8_t i = 0; i < 16; ++i)
218238 {
219- handle.value[i] = md5_ .digest[i];
239+ handle.value[i] = md5 .digest[i];
220240 }
221241 }
222242 else
223243 {
224244 for (uint8_t i = 0; i < 16; ++i)
225245 {
226- handle.value[i] = key_buffer_ [i];
246+ handle.value[i] = key_buffer [i];
227247 }
228248 }
229249 return true;
250+ $else$
251+ static_cast<void>(data);
252+ static_cast<void>(handle);
253+ static_cast<void>(force_md5);
254+
255+ return false;
256+ $endif$
230257}
231258
259+ $if(struct.hasKey)$
260+ unsigned char* $struct.name$PubSubType::get_key_buffer_nts()
261+ {
262+ // If already reserved, return
263+ if (key_buffer_ != nullptr)
264+ {
265+ return key_buffer_;
266+ }
267+
268+ // Allocate the key buffer
269+ uint32_t key_length = (std::max)($struct.cScopedname$_max_key_cdr_typesize, 16u);
270+ key_buffer_ = reinterpret_cast<unsigned char*>(calloc(key_length, 1u));
271+ return key_buffer_;
272+ }
273+ $endif$
274+
232275void $struct.name$PubSubType::register_type_object_representation()
233276{
234277 $if (ctx.generateTypeObjectSupport)$
235278 register_$struct.name$_type_identifier(type_identifiers_);
236279 $else$
237280 EPROSIMA_LOG_WARNING(XTYPES_TYPE_REPRESENTATION,
238- "TypeObject type representation support disabled in generated code");
281+ "TypeObject type representation support disabled in generated code");
239282 $endif$
240283}
241284$endif$
@@ -310,7 +353,7 @@ public:
310353 ser.serialize_encapsulation();
311354 // Serialize the object.
312355 ser << *p_type;
313- ser.set_dds_cdr_options({0,0});
356+ ser.set_dds_cdr_options({0, 0});
314357 }
315358 catch (eprosima::fastcdr::exception::Exception& /*exception*/)
316359 {
@@ -362,9 +405,9 @@ public:
362405 data_representation == DataRepresentationId_t::XCDR_DATA_REPRESENTATION ?
363406 eprosima::fastcdr::CdrVersion::XCDRv1 : eprosima::fastcdr::CdrVersion::XCDRv2);
364407 size_t current_alignment {0};
365- return static_cast<uint32_t>(calculator.calculate_serialized_size(
366- *static_cast<const type*>(data) , current_alignment)) +
367- 4u /*encapsulation*/;
408+ const type* p_type = static_cast<const type*>(data);
409+ auto calc_size = calculator.calculate_serialized_size(*p_type , current_alignment);
410+ return static_cast<uint32_t>(calc_size) + 4u /*encapsulation*/;
368411 }
369412 catch (eprosima::fastcdr::exception::Exception& /*exception*/)
370413 {
@@ -412,7 +455,7 @@ $if (ctx.generateTypeObjectSupport)$
412455 register_$interface.name$_$suffix$_type_identifier(type_identifiers_);
413456$else$
414457 EPROSIMA_LOG_WARNING(XTYPES_TYPE_REPRESENTATION,
415- "TypeObject type representation support disabled in generated code");
458+ "TypeObject type representation support disabled in generated code");
416459$endif$
417460 }
418461
0 commit comments