Cleanup: add `#include <stdbool.h>` whenever `bool` type is used
[babeltrace.git] / src / plugins / ctf / common / metadata / ctf-meta-update-in-ir.c
CommitLineData
7b33a0e0
PP
1/*
2 * Copyright 2018 - Philippe Proulx <pproulx@efficios.com>
3 *
4 * Permission is hereby granted, free of charge, to any person obtaining a copy
5 * of this software and associated documentation files (the "Software"), to deal
6 * in the Software without restriction, including without limitation the rights
7 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
8 * copies of the Software, and to permit persons to whom the Software is
9 * furnished to do so, subject to the following conditions:
10 *
11 * The above copyright notice and this permission notice shall be included in
12 * all copies or substantial portions of the Software.
13 */
14
71c5da58 15#include <babeltrace2/babeltrace.h>
85e7137b 16#include "common/macros.h"
57952005
MJ
17#include "common/assert.h"
18#include "compat/glib.h"
7b33a0e0 19#include <glib.h>
969c1d8a 20#include <stdbool.h>
7b33a0e0
PP
21#include <stdint.h>
22#include <string.h>
23#include <inttypes.h>
57952005 24#include "common/assert.h"
7b33a0e0
PP
25
26#include "ctf-meta-visitors.h"
27
0476f6f7
PP
28static
29void force_update_field_class_in_ir(struct ctf_field_class *fc, bool in_ir)
30{
31 uint64_t i;
32
33 if (!fc) {
34 goto end;
35 }
36
37 fc->in_ir = in_ir;
38
39 switch (fc->type) {
40 case CTF_FIELD_CLASS_TYPE_STRUCT:
41 {
42 struct ctf_field_class_struct *struct_fc = (void *) fc;
43
44 for (i = 0; i < struct_fc->members->len; i++) {
45 struct ctf_named_field_class *named_fc =
46 ctf_field_class_struct_borrow_member_by_index(
47 struct_fc, i);
48
49 force_update_field_class_in_ir(named_fc->fc, in_ir);
50 }
51
52 break;
53 }
54 case CTF_FIELD_CLASS_TYPE_VARIANT:
55 {
56 struct ctf_named_field_class *named_fc;
57 struct ctf_field_class_variant *var_fc = (void *) fc;
58
59 for (i = 0; i < var_fc->options->len; i++) {
60 named_fc =
61 ctf_field_class_variant_borrow_option_by_index(
62 var_fc, i);
63
64 force_update_field_class_in_ir(named_fc->fc, in_ir);
65 }
66
67 break;
68 }
69 case CTF_FIELD_CLASS_TYPE_ARRAY:
70 case CTF_FIELD_CLASS_TYPE_SEQUENCE:
71 {
72 struct ctf_field_class_array_base *array_fc = (void *) fc;
73
74 force_update_field_class_in_ir(array_fc->elem_fc, in_ir);
75 break;
76 }
77 default:
78 break;
79 }
80
81end:
82 return;
83}
84
7b33a0e0 85static
939190b3 86void update_field_class_in_ir(struct ctf_field_class *fc,
7b33a0e0
PP
87 GHashTable *ft_dependents)
88{
89 int64_t i;
90
939190b3 91 if (!fc) {
7b33a0e0
PP
92 goto end;
93 }
94
af0c18e3
PP
95 switch (fc->type) {
96 case CTF_FIELD_CLASS_TYPE_INT:
97 case CTF_FIELD_CLASS_TYPE_ENUM:
7b33a0e0 98 {
939190b3 99 struct ctf_field_class_int *int_fc = (void *) fc;
7b33a0e0 100
e4853767
PP
101 /*
102 * Conditions to be in trace IR; one of:
103 *
104 * 1. Does NOT have a mapped clock class AND does not
105 * have a special meaning.
106 * 2. Another field class depends on it.
107 */
108 if ((!int_fc->mapped_clock_class &&
109 int_fc->meaning == CTF_FIELD_CLASS_MEANING_NONE) ||
939190b3 110 bt_g_hash_table_contains(ft_dependents, fc)) {
939190b3 111 fc->in_ir = true;
7b33a0e0
PP
112 }
113
114 break;
115 }
af0c18e3 116 case CTF_FIELD_CLASS_TYPE_STRUCT:
7b33a0e0 117 {
939190b3 118 struct ctf_field_class_struct *struct_fc = (void *) fc;
7b33a0e0 119
496fac93
PP
120 /*
121 * Make it part of IR if it's empty because it was
122 * originally empty.
123 */
124 if (struct_fc->members->len == 0) {
125 fc->in_ir = true;
126 }
127
7b33a0e0 128 /* Reverse order */
939190b3
PP
129 for (i = (int64_t) struct_fc->members->len - 1; i >= 0; i--) {
130 struct ctf_named_field_class *named_fc =
131 ctf_field_class_struct_borrow_member_by_index(
132 struct_fc, i);
7b33a0e0 133
939190b3 134 update_field_class_in_ir(named_fc->fc, ft_dependents);
7b33a0e0 135
939190b3 136 if (named_fc->fc->in_ir) {
7b33a0e0 137 /* At least one member is part of IR */
939190b3 138 fc->in_ir = true;
7b33a0e0
PP
139 }
140 }
141
142 break;
143 }
af0c18e3 144 case CTF_FIELD_CLASS_TYPE_VARIANT:
7b33a0e0 145 {
939190b3
PP
146 struct ctf_named_field_class *named_fc;
147 struct ctf_field_class_variant *var_fc = (void *) fc;
7b33a0e0
PP
148
149 /*
150 * Reverse order, although it is not important for this
939190b3
PP
151 * loop because a field class within a variant field
152 * type's option cannot depend on a field class in
153 * another option of the same variant field class.
7b33a0e0 154 */
939190b3
PP
155 for (i = (int64_t) var_fc->options->len - 1; i >= 0; i--) {
156 named_fc =
157 ctf_field_class_variant_borrow_option_by_index(
158 var_fc, i);
7b33a0e0 159
939190b3 160 update_field_class_in_ir(named_fc->fc, ft_dependents);
7b33a0e0 161
939190b3 162 if (named_fc->fc->in_ir) {
7b33a0e0 163 /* At least one option is part of IR */
939190b3 164 fc->in_ir = true;
7b33a0e0
PP
165 }
166 }
167
939190b3 168 if (fc->in_ir) {
7b33a0e0
PP
169 /*
170 * At least one option will make it to IR. In
171 * this case, make all options part of IR
172 * because the variant's tag could still select
173 * (dynamically) a removed option. This can mean
174 * having an empty structure as an option, for
175 * example, but at least all the options are
176 * selectable.
177 */
939190b3
PP
178 for (i = 0; i < var_fc->options->len; i++) {
179 ctf_field_class_variant_borrow_option_by_index(
180 var_fc, i)->fc->in_ir = true;
7b33a0e0
PP
181 }
182
183 /*
939190b3
PP
184 * This variant field class is part of IR and
185 * depends on a tag field class (which must also
7b33a0e0
PP
186 * be part of IR).
187 */
939190b3
PP
188 g_hash_table_insert(ft_dependents, var_fc->tag_fc,
189 var_fc->tag_fc);
7b33a0e0
PP
190 }
191
192 break;
193 }
af0c18e3
PP
194 case CTF_FIELD_CLASS_TYPE_ARRAY:
195 case CTF_FIELD_CLASS_TYPE_SEQUENCE:
7b33a0e0 196 {
939190b3 197 struct ctf_field_class_array_base *array_fc = (void *) fc;
7b33a0e0 198
939190b3
PP
199 update_field_class_in_ir(array_fc->elem_fc, ft_dependents);
200 fc->in_ir = array_fc->elem_fc->in_ir;
7b33a0e0 201
af0c18e3 202 if (fc->type == CTF_FIELD_CLASS_TYPE_ARRAY) {
939190b3 203 struct ctf_field_class_array *arr_fc = (void *) fc;
7b33a0e0 204
939190b3
PP
205 assert(arr_fc->meaning == CTF_FIELD_CLASS_MEANING_NONE ||
206 arr_fc->meaning == CTF_FIELD_CLASS_MEANING_UUID);
7b33a0e0
PP
207
208 /*
939190b3 209 * UUID field class: nothing depends on this, so
7b33a0e0
PP
210 * it's not part of IR.
211 */
939190b3
PP
212 if (arr_fc->meaning == CTF_FIELD_CLASS_MEANING_UUID) {
213 fc->in_ir = false;
214 array_fc->elem_fc->in_ir = false;
7b33a0e0 215 }
af0c18e3 216 } else if (fc->type == CTF_FIELD_CLASS_TYPE_SEQUENCE) {
939190b3
PP
217 if (fc->in_ir) {
218 struct ctf_field_class_sequence *seq_fc = (void *) fc;
7b33a0e0
PP
219
220 /*
939190b3
PP
221 * This sequence field class is part of
222 * IR and depends on a length field class
7b33a0e0
PP
223 * (which must also be part of IR).
224 */
225 g_hash_table_insert(ft_dependents,
939190b3 226 seq_fc->length_fc, seq_fc->length_fc);
7b33a0e0
PP
227 }
228 }
229
230 break;
231 }
232 default:
939190b3 233 fc->in_ir = true;
7b33a0e0
PP
234 break;
235 }
236
237end:
238 return;
239}
240
241/*
939190b3
PP
242 * Scopes and field classes are processed in reverse order because we need
243 * to know if a given integer field class has dependents (sequence or
244 * variant field classes) when we reach it. Dependents can only be located
245 * after the length/tag field class in the metadata tree.
7b33a0e0
PP
246 */
247BT_HIDDEN
248int ctf_trace_class_update_in_ir(struct ctf_trace_class *ctf_tc)
249{
250 int ret = 0;
251 uint64_t i;
252
253 GHashTable *ft_dependents = g_hash_table_new(g_direct_hash,
254 g_direct_equal);
255
256 BT_ASSERT(ft_dependents);
257
258 for (i = 0; i < ctf_tc->stream_classes->len; i++) {
259 struct ctf_stream_class *sc = ctf_tc->stream_classes->pdata[i];
260 uint64_t j;
261
262 for (j = 0; j < sc->event_classes->len; j++) {
263 struct ctf_event_class *ec = sc->event_classes->pdata[j];
264
265 if (ec->is_translated) {
266 continue;
267 }
268
939190b3
PP
269 update_field_class_in_ir(ec->payload_fc, ft_dependents);
270 update_field_class_in_ir(ec->spec_context_fc,
7b33a0e0
PP
271 ft_dependents);
272 }
273
274 if (!sc->is_translated) {
939190b3 275 update_field_class_in_ir(sc->event_common_context_fc,
7b33a0e0 276 ft_dependents);
0476f6f7
PP
277 force_update_field_class_in_ir(sc->event_header_fc,
278 false);
939190b3 279 update_field_class_in_ir(sc->packet_context_fc,
7b33a0e0
PP
280 ft_dependents);
281 }
282 }
283
284 if (!ctf_tc->is_translated) {
0476f6f7
PP
285 force_update_field_class_in_ir(ctf_tc->packet_header_fc,
286 false);
7b33a0e0
PP
287 }
288
289 g_hash_table_destroy(ft_dependents);
290 return ret;
291}
This page took 0.067724 seconds and 4 git commands to generate.