2 * SPDX-License-Identifier: MIT
4 * Copyright 2018 Philippe Proulx <pproulx@efficios.com>
7 #include <babeltrace2/babeltrace.h>
9 #include "cpp-common/bt2c/logging.hpp"
11 #include "ctf-meta-visitors.hpp"
13 static int validate_stream_class(struct ctf_stream_class
*sc
, const bt2c::Logger
& logger
)
16 struct ctf_field_class_int
*int_fc
;
17 struct ctf_field_class
*fc
;
19 if (sc
->is_translated
) {
23 fc
= ctf_field_class_struct_borrow_member_field_class_by_name(
24 ctf_field_class_as_struct(sc
->packet_context_fc
), "timestamp_begin");
26 if (fc
->type
!= CTF_FIELD_CLASS_TYPE_INT
&& fc
->type
!= CTF_FIELD_CLASS_TYPE_ENUM
) {
27 BT_CPPLOGE_APPEND_CAUSE_SPEC(logger
,
28 "Invalid packet context field class: "
29 "`timestamp_begin` member is not an integer field class.");
33 int_fc
= ctf_field_class_as_int(fc
);
35 if (int_fc
->is_signed
) {
36 BT_CPPLOGE_APPEND_CAUSE_SPEC(logger
, "Invalid packet context field class: "
37 "`timestamp_begin` member is signed.");
42 fc
= ctf_field_class_struct_borrow_member_field_class_by_name(
43 ctf_field_class_as_struct(sc
->packet_context_fc
), "timestamp_end");
45 if (fc
->type
!= CTF_FIELD_CLASS_TYPE_INT
&& fc
->type
!= CTF_FIELD_CLASS_TYPE_ENUM
) {
46 BT_CPPLOGE_APPEND_CAUSE_SPEC(logger
,
47 "Invalid packet context field class: "
48 "`timestamp_end` member is not an integer field class.");
52 int_fc
= ctf_field_class_as_int(fc
);
54 if (int_fc
->is_signed
) {
55 BT_CPPLOGE_APPEND_CAUSE_SPEC(logger
, "Invalid packet context field class: "
56 "`timestamp_end` member is signed.");
61 fc
= ctf_field_class_struct_borrow_member_field_class_by_name(
62 ctf_field_class_as_struct(sc
->packet_context_fc
), "events_discarded");
64 if (fc
->type
!= CTF_FIELD_CLASS_TYPE_INT
&& fc
->type
!= CTF_FIELD_CLASS_TYPE_ENUM
) {
65 BT_CPPLOGE_APPEND_CAUSE_SPEC(
66 logger
, "Invalid packet context field class: "
67 "`events_discarded` member is not an integer field class.");
71 int_fc
= ctf_field_class_as_int(fc
);
73 if (int_fc
->is_signed
) {
74 BT_CPPLOGE_APPEND_CAUSE_SPEC(logger
, "Invalid packet context field class: "
75 "`events_discarded` member is signed.");
80 fc
= ctf_field_class_struct_borrow_member_field_class_by_name(
81 ctf_field_class_as_struct(sc
->packet_context_fc
), "packet_seq_num");
83 if (fc
->type
!= CTF_FIELD_CLASS_TYPE_INT
&& fc
->type
!= CTF_FIELD_CLASS_TYPE_ENUM
) {
84 BT_CPPLOGE_APPEND_CAUSE_SPEC(logger
,
85 "Invalid packet context field class: "
86 "`packet_seq_num` member is not an integer field class.");
90 int_fc
= ctf_field_class_as_int(fc
);
92 if (int_fc
->is_signed
) {
93 BT_CPPLOGE_APPEND_CAUSE_SPEC(logger
, "Invalid packet context field class: "
94 "`packet_seq_num` member is signed.");
99 fc
= ctf_field_class_struct_borrow_member_field_class_by_name(
100 ctf_field_class_as_struct(sc
->packet_context_fc
), "packet_size");
102 if (fc
->type
!= CTF_FIELD_CLASS_TYPE_INT
&& fc
->type
!= CTF_FIELD_CLASS_TYPE_ENUM
) {
103 BT_CPPLOGE_APPEND_CAUSE_SPEC(logger
,
104 "Invalid packet context field class: "
105 "`packet_size` member is not an integer field class.");
109 int_fc
= ctf_field_class_as_int(fc
);
111 if (int_fc
->is_signed
) {
112 BT_CPPLOGE_APPEND_CAUSE_SPEC(logger
, "Invalid packet context field class: "
113 "`packet_size` member is signed.");
118 fc
= ctf_field_class_struct_borrow_member_field_class_by_name(
119 ctf_field_class_as_struct(sc
->packet_context_fc
), "content_size");
121 if (fc
->type
!= CTF_FIELD_CLASS_TYPE_INT
&& fc
->type
!= CTF_FIELD_CLASS_TYPE_ENUM
) {
122 BT_CPPLOGE_APPEND_CAUSE_SPEC(logger
,
123 "Invalid packet context field class: "
124 "`content_size` member is not an integer field class.");
128 int_fc
= ctf_field_class_as_int(fc
);
130 if (int_fc
->is_signed
) {
131 BT_CPPLOGE_APPEND_CAUSE_SPEC(logger
, "Invalid packet context field class: "
132 "`content_size` member is signed.");
137 fc
= ctf_field_class_struct_borrow_member_field_class_by_name(
138 ctf_field_class_as_struct(sc
->event_header_fc
), "id");
140 if (fc
->type
!= CTF_FIELD_CLASS_TYPE_INT
&& fc
->type
!= CTF_FIELD_CLASS_TYPE_ENUM
) {
141 BT_CPPLOGE_APPEND_CAUSE_SPEC(logger
, "Invalid event header field class: "
142 "`id` member is not an integer field class.");
146 int_fc
= ctf_field_class_as_int(fc
);
148 if (int_fc
->is_signed
) {
149 BT_CPPLOGE_APPEND_CAUSE_SPEC(logger
, "Invalid event header field class: "
150 "`id` member is signed.");
154 if (sc
->event_classes
->len
> 1) {
155 BT_CPPLOGE_APPEND_CAUSE_SPEC(logger
, "Invalid event header field class: "
156 "missing `id` member as there's "
157 "more than one event class.");
171 int ctf_trace_class_validate(struct ctf_trace_class
*ctf_tc
, const bt2c::Logger
& parentLogger
)
174 struct ctf_field_class_int
*int_fc
;
177 bt2c::Logger logger
{parentLogger
, "PLUGIN/CTF/META/VALIDATE"};
179 if (!ctf_tc
->is_translated
) {
180 struct ctf_field_class
*fc
;
182 fc
= ctf_field_class_struct_borrow_member_field_class_by_name(
183 ctf_field_class_as_struct(ctf_tc
->packet_header_fc
), "magic");
185 struct ctf_named_field_class
*named_fc
= ctf_field_class_struct_borrow_member_by_index(
186 ctf_field_class_as_struct(ctf_tc
->packet_header_fc
), 0);
188 if (named_fc
->fc
!= fc
) {
189 BT_CPPLOGE_APPEND_CAUSE_SPEC(logger
, "Invalid packet header field class: "
190 "`magic` member is not the first member.");
194 if (fc
->type
!= CTF_FIELD_CLASS_TYPE_INT
&& fc
->type
!= CTF_FIELD_CLASS_TYPE_ENUM
) {
195 BT_CPPLOGE_APPEND_CAUSE_SPEC(logger
,
196 "Invalid packet header field class: "
197 "`magic` member is not an integer field class.");
201 int_fc
= ctf_field_class_as_int(fc
);
203 if (int_fc
->is_signed
) {
204 BT_CPPLOGE_APPEND_CAUSE_SPEC(logger
, "Invalid packet header field class: "
205 "`magic` member is signed.");
209 if (int_fc
->base
.size
!= 32) {
210 BT_CPPLOGE_APPEND_CAUSE_SPEC(logger
, "Invalid packet header field class: "
211 "`magic` member is not 32-bit.");
216 fc
= ctf_field_class_struct_borrow_member_field_class_by_name(
217 ctf_field_class_as_struct(ctf_tc
->packet_header_fc
), "stream_id");
219 if (fc
->type
!= CTF_FIELD_CLASS_TYPE_INT
&& fc
->type
!= CTF_FIELD_CLASS_TYPE_ENUM
) {
220 BT_CPPLOGE_APPEND_CAUSE_SPEC(logger
,
221 "Invalid packet header field class: "
222 "`stream_id` member is not an integer field class.");
226 int_fc
= ctf_field_class_as_int(fc
);
228 if (int_fc
->is_signed
) {
229 BT_CPPLOGE_APPEND_CAUSE_SPEC(logger
, "Invalid packet header field class: "
230 "`stream_id` member is signed.");
234 if (ctf_tc
->stream_classes
->len
> 1) {
235 BT_CPPLOGE_APPEND_CAUSE_SPEC(logger
, "Invalid packet header field class: "
236 "missing `stream_id` member as there's "
237 "more than one stream class.");
242 fc
= ctf_field_class_struct_borrow_member_field_class_by_name(
243 ctf_field_class_as_struct(ctf_tc
->packet_header_fc
), "stream_instance_id");
245 if (fc
->type
!= CTF_FIELD_CLASS_TYPE_INT
&& fc
->type
!= CTF_FIELD_CLASS_TYPE_ENUM
) {
246 BT_CPPLOGE_APPEND_CAUSE_SPEC(
247 logger
, "Invalid packet header field class: "
248 "`stream_instance_id` member is not an integer field class.");
252 int_fc
= ctf_field_class_as_int(fc
);
254 if (int_fc
->is_signed
) {
255 BT_CPPLOGE_APPEND_CAUSE_SPEC(logger
, "Invalid packet header field class: "
256 "`stream_instance_id` member is signed.");
261 fc
= ctf_field_class_struct_borrow_member_field_class_by_name(
262 ctf_field_class_as_struct(ctf_tc
->packet_header_fc
), "uuid");
264 if (fc
->type
!= CTF_FIELD_CLASS_TYPE_ARRAY
) {
265 BT_CPPLOGE_APPEND_CAUSE_SPEC(logger
, "Invalid packet header field class: "
266 "`uuid` member is not an array field class.");
270 ctf_field_class_array
*array_fc
= ctf_field_class_as_array(fc
);
272 if (array_fc
->length
!= 16) {
273 BT_CPPLOGE_APPEND_CAUSE_SPEC(
274 logger
, "Invalid packet header field class: "
275 "`uuid` member is not a 16-element array field class.");
279 if (array_fc
->base
.elem_fc
->type
!= CTF_FIELD_CLASS_TYPE_INT
) {
280 BT_CPPLOGE_APPEND_CAUSE_SPEC(logger
, "Invalid packet header field class: "
281 "`uuid` member's element field class is not "
282 "an integer field class.");
286 int_fc
= ctf_field_class_as_int(array_fc
->base
.elem_fc
);
288 if (int_fc
->is_signed
) {
289 BT_CPPLOGE_APPEND_CAUSE_SPEC(logger
, "Invalid packet header field class: "
290 "`uuid` member's element field class "
291 "is a signed integer field class.");
295 if (int_fc
->base
.size
!= 8) {
296 BT_CPPLOGE_APPEND_CAUSE_SPEC(logger
, "Invalid packet header field class: "
297 "`uuid` member's element field class "
298 "is not an 8-bit integer field class.");
302 if (int_fc
->base
.base
.alignment
!= 8) {
303 BT_CPPLOGE_APPEND_CAUSE_SPEC(logger
, "Invalid packet header field class: "
304 "`uuid` member's element field class's "
305 "alignment is not 8.");
311 for (i
= 0; i
< ctf_tc
->stream_classes
->len
; i
++) {
312 struct ctf_stream_class
*sc
= (ctf_stream_class
*) ctf_tc
->stream_classes
->pdata
[i
];
314 ret
= validate_stream_class(sc
, logger
);
316 BT_CPPLOGE_APPEND_CAUSE_SPEC(logger
, "Invalid stream class: sc-id={}", sc
->id
);