4 * BabelTrace - Converter
8 * Copyright 2010, 2011 - Mathieu Desnoyers <mathieu.desnoyers@efficios.com>
10 * Permission is hereby granted, free of charge, to any person obtaining a copy
11 * of this software and associated documentation files (the "Software"), to deal
12 * in the Software without restriction, including without limitation the rights
13 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
14 * copies of the Software, and to permit persons to whom the Software is
15 * furnished to do so, subject to the following conditions:
17 * The above copyright notice and this permission notice shall be included in
18 * all copies or substantial portions of the Software.
21 #include <babeltrace/format.h>
27 lookup_typedef_declaration_scope(GQuark declaration_name
,
28 struct declaration_scope
*scope
)
30 return g_hash_table_lookup(scope
->typedef_declarations
,
31 (gconstpointer
) (unsigned long) declaration_name
);
34 struct definition
*lookup_typedef_declaration(GQuark declaration_name
,
35 struct declaration_scope
*scope
)
37 struct definition
*definition
;
40 definition
= lookup_typedef_declaration_scope(declaration_name
,
44 scope
= scope
->parent_scope
;
49 int register_typedef_declaration(GQuark name
, struct declaration
*declaration
,
50 struct declaration_scope
*scope
)
55 /* Only lookup in local scope */
56 if (lookup_typedef_declaration_scope(name
, scope
))
59 g_hash_table_insert(scope
->typedef_declarations
,
60 (gpointer
) (unsigned long) name
,
62 declaration_ref(declaration
);
68 lookup_field_definition_scope(GQuark field_name
,
69 struct definition_scope
*scope
)
71 return g_hash_table_lookup(scope
->definitions
,
72 (gconstpointer
) (unsigned long) field_name
);
76 * Returns the index at which the paths differ.
77 * If the value returned equals len, it means the paths are identical
78 * from index 0 to len-1.
80 static int compare_paths(GArray
*a
, GArray
*b
, int len
)
84 assert(len
<= a
->len
);
85 assert(len
<= b
->len
);
87 for (i
= 0; i
< len
; i
++) {
90 qa
= g_array_index(a
, GQuark
, i
);
91 qb
= g_array_index(b
, GQuark
, i
);
98 static int is_path_child_of(GArray
*path
, GArray
*maybe_parent
)
100 if (path
->len
<= maybe_parent
->len
)
102 if (compare_paths(path
, maybe_parent
, maybe_parent
->len
)
103 == maybe_parent
->len
)
109 static struct definition_scope
*
110 get_definition_scope(struct definition
*definition
)
112 switch (definition
->declaration
->id
) {
113 case CTF_TYPE_STRUCT
:
115 struct definition_struct
*def
=
116 container_of(definition
, struct definition_struct
, p
);
119 case CTF_TYPE_VARIANT
:
121 struct definition_variant
*def
=
122 container_of(definition
, struct definition_variant
, p
);
127 struct definition_array
*def
=
128 container_of(definition
, struct definition_array
, p
);
131 case CTF_TYPE_SEQUENCE
:
133 struct definition_sequence
*def
=
134 container_of(definition
, struct definition_sequence
, p
);
138 case CTF_TYPE_INTEGER
:
141 case CTF_TYPE_STRING
:
142 case CTF_TYPE_UNKNOWN
:
149 * OK, here is the fun. We want to lookup a field that is:
150 * - either in the current scope, but prior to the current field.
151 * - or in a parent scope (or parent of parent ...) still in a field
152 * prior to the current field position within the parents.
153 * A reaching through a dynamic scoping (e.g. from payload structure to
154 * event header structure), the parent fields are always entirely prior
156 * If we cannot find such a field that is prior to our current path, we
159 * cur_path: the path leading to the variant definition.
160 * lookup_path: the path leading to the enum we want to look for.
161 * scope: the definition scope containing the variant definition.
164 lookup_definition(GArray
*cur_path
,
166 struct definition_scope
*scope
)
168 struct definition
*definition
, *lookup_definition
;
173 /* going up in the hierarchy. Check where we come from. */
174 assert(is_path_child_of(cur_path
, scope
->scope_path
));
175 assert(cur_path
->len
- scope
->scope_path
->len
== 1);
176 last
= g_array_index(cur_path
, GQuark
, cur_path
->len
- 1);
177 definition
= lookup_field_definition_scope(last
, scope
);
179 index
= definition
->index
;
181 if (is_path_child_of(lookup_path
, scope
->scope_path
)) {
182 /* Means we can lookup the field in this scope */
183 last
= g_array_index(lookup_path
, GQuark
,
184 scope
->scope_path
->len
);
185 lookup_definition
= lookup_field_definition_scope(last
, scope
);
186 if (!lookup_definition
|| ((index
!= -1) && lookup_definition
->index
>= index
))
188 /* Found it! And it is prior to the current field. */
189 if (lookup_path
->len
- scope
->scope_path
->len
== 1) {
191 return lookup_definition
;
193 scope
= get_definition_scope(lookup_definition
);
194 /* Check if the definition has a sub-scope */
198 * Don't compare index anymore, because we are
199 * going within a scope that has been validated
200 * to be entirely prior to the current scope.
208 /* lookup_path is within an upper scope */
209 cur_path
= scope
->scope_path
;
210 scope
= scope
->parent_scope
;
216 int register_field_definition(GQuark field_name
, struct definition
*definition
,
217 struct definition_scope
*scope
)
222 /* Only lookup in local scope */
223 if (lookup_field_definition_scope(field_name
, scope
))
226 g_hash_table_insert(scope
->definitions
,
227 (gpointer
) (unsigned long) field_name
,
229 definition_ref(definition
);
233 void declaration_ref(struct declaration
*declaration
)
238 void declaration_unref(struct declaration
*declaration
)
240 if (!--declaration
->ref
)
241 declaration
->declaration_free(declaration
);
244 void definition_ref(struct definition
*definition
)
249 void definition_unref(struct definition
*definition
)
251 if (!--definition
->ref
)
252 definition
->declaration
->definition_free(definition
);
255 struct declaration_scope
*
256 new_declaration_scope(struct declaration_scope
*parent_scope
)
258 struct declaration_scope
*scope
= g_new(struct declaration_scope
, 1);
260 scope
->typedef_declarations
= g_hash_table_new_full(g_direct_hash
,
261 g_direct_equal
, NULL
,
262 (GDestroyNotify
) definition_unref
);
263 scope
->struct_declarations
= g_hash_table_new_full(g_direct_hash
,
264 g_direct_equal
, NULL
,
265 (GDestroyNotify
) declaration_unref
);
266 scope
->variant_declarations
= g_hash_table_new_full(g_direct_hash
,
267 g_direct_equal
, NULL
,
268 (GDestroyNotify
) declaration_unref
);
269 scope
->enum_declarations
= g_hash_table_new_full(g_direct_hash
,
270 g_direct_equal
, NULL
,
271 (GDestroyNotify
) declaration_unref
);
272 scope
->parent_scope
= parent_scope
;
276 void free_declaration_scope(struct declaration_scope
*scope
)
278 g_hash_table_destroy(scope
->enum_declarations
);
279 g_hash_table_destroy(scope
->variant_declarations
);
280 g_hash_table_destroy(scope
->struct_declarations
);
281 g_hash_table_destroy(scope
->typedef_declarations
);
286 struct declaration_struct
*lookup_struct_declaration_scope(GQuark struct_name
,
287 struct declaration_scope
*scope
)
289 return g_hash_table_lookup(scope
->struct_declarations
,
290 (gconstpointer
) (unsigned long) struct_name
);
293 struct declaration_struct
*lookup_struct_declaration(GQuark struct_name
,
294 struct declaration_scope
*scope
)
296 struct declaration_struct
*declaration
;
299 declaration
= lookup_struct_declaration_scope(struct_name
, scope
);
302 scope
= scope
->parent_scope
;
307 int register_struct_declaration(GQuark struct_name
,
308 struct declaration_struct
*struct_declaration
,
309 struct declaration_scope
*scope
)
314 /* Only lookup in local scope */
315 if (lookup_struct_declaration_scope(struct_name
, scope
))
318 g_hash_table_insert(scope
->struct_declarations
,
319 (gpointer
) (unsigned long) struct_name
,
321 declaration_ref(&struct_declaration
->p
);
326 struct declaration_variant
*
327 lookup_variant_declaration_scope(GQuark variant_name
,
328 struct declaration_scope
*scope
)
330 return g_hash_table_lookup(scope
->variant_declarations
,
331 (gconstpointer
) (unsigned long) variant_name
);
334 struct declaration_variant
*
335 lookup_variant_declaration(GQuark variant_name
,
336 struct declaration_scope
*scope
)
338 struct declaration_variant
*declaration
;
341 declaration
= lookup_variant_declaration_scope(variant_name
, scope
);
344 scope
= scope
->parent_scope
;
349 int register_variant_declaration(GQuark variant_name
,
350 struct declaration_variant
*variant_declaration
,
351 struct declaration_scope
*scope
)
356 /* Only lookup in local scope */
357 if (lookup_variant_declaration_scope(variant_name
, scope
))
360 g_hash_table_insert(scope
->variant_declarations
,
361 (gpointer
) (unsigned long) variant_name
,
362 variant_declaration
);
363 declaration_ref(&variant_declaration
->p
);
368 struct declaration_enum
*
369 lookup_enum_declaration_scope(GQuark enum_name
,
370 struct declaration_scope
*scope
)
372 return g_hash_table_lookup(scope
->enum_declarations
,
373 (gconstpointer
) (unsigned long) enum_name
);
376 struct declaration_enum
*
377 lookup_enum_declaration(GQuark enum_name
,
378 struct declaration_scope
*scope
)
380 struct declaration_enum
*declaration
;
383 declaration
= lookup_enum_declaration_scope(enum_name
, scope
);
386 scope
= scope
->parent_scope
;
391 int register_enum_declaration(GQuark enum_name
,
392 struct declaration_enum
*enum_declaration
,
393 struct declaration_scope
*scope
)
398 /* Only lookup in local scope */
399 if (lookup_enum_declaration_scope(enum_name
, scope
))
402 g_hash_table_insert(scope
->enum_declarations
,
403 (gpointer
) (unsigned long) enum_name
,
405 declaration_ref(&enum_declaration
->p
);
409 struct definition_scope
*
410 new_definition_scope(struct definition_scope
*parent_scope
,
413 struct definition_scope
*scope
= g_new(struct definition_scope
, 1);
414 int scope_path_len
= 1;
416 scope
->definitions
= g_hash_table_new_full(g_direct_hash
,
417 g_direct_equal
, NULL
,
418 (GDestroyNotify
) definition_unref
);
419 scope
->parent_scope
= parent_scope
;
420 if (scope
->parent_scope
)
421 scope_path_len
+= scope
->parent_scope
->scope_path
->len
;
422 scope
->scope_path
= g_array_sized_new(FALSE
, TRUE
, sizeof(GQuark
),
424 g_array_set_size(scope
->scope_path
, scope_path_len
);
425 if (scope
->parent_scope
)
426 memcpy(scope
->scope_path
, scope
->parent_scope
->scope_path
,
427 sizeof(GQuark
) * (scope_path_len
- 1));
428 g_array_index(scope
->scope_path
, GQuark
, scope_path_len
- 1) =
433 void free_definition_scope(struct definition_scope
*scope
)
435 g_array_free(scope
->scope_path
, TRUE
);
436 g_hash_table_destroy(scope
->definitions
);
This page took 0.037107 seconds and 4 git commands to generate.