X-Git-Url: http://git.efficios.com/?a=blobdiff_plain;f=formats%2Fctf%2Fir%2Fevent-fields.c;h=809ffc33a95300d22f38bd1ed33b088c5d7378e0;hb=d2dc44b6775655cf77a13a3901898c3f1ca26baa;hp=ac77cfb7bf3648f9ca8282b67b96d4eeb52c448f;hpb=de9dd3975ba39e915d7e046877af9059990c595e;p=babeltrace.git diff --git a/formats/ctf/ir/event-fields.c b/formats/ctf/ir/event-fields.c index ac77cfb7..809ffc33 100644 --- a/formats/ctf/ir/event-fields.c +++ b/formats/ctf/ir/event-fields.c @@ -1,7 +1,7 @@ /* * event-fields.c * - * Babeltrace CTF Writer + * Babeltrace CTF IR - Event Fields * * Copyright 2013, 2014 Jérémie Galarneau * @@ -88,6 +88,21 @@ int bt_ctf_field_array_validate(struct bt_ctf_field *field); static int bt_ctf_field_sequence_validate(struct bt_ctf_field *field); +static +int bt_ctf_field_generic_reset(struct bt_ctf_field *field); +static +int bt_ctf_field_structure_reset(struct bt_ctf_field *field); +static +int bt_ctf_field_variant_reset(struct bt_ctf_field *field); +static +int bt_ctf_field_enumeration_reset(struct bt_ctf_field *field); +static +int bt_ctf_field_array_reset(struct bt_ctf_field *field); +static +int bt_ctf_field_sequence_reset(struct bt_ctf_field *field); +static +int bt_ctf_field_string_reset(struct bt_ctf_field *field); + static int bt_ctf_field_integer_serialize(struct bt_ctf_field *, struct ctf_stream_pos *); @@ -155,6 +170,18 @@ int (*field_validate_funcs[])(struct bt_ctf_field *) = { [CTF_TYPE_STRING] = bt_ctf_field_generic_validate, }; +static +int (*field_reset_funcs[])(struct bt_ctf_field *) = { + [CTF_TYPE_INTEGER] = bt_ctf_field_generic_reset, + [CTF_TYPE_ENUM] = bt_ctf_field_enumeration_reset, + [CTF_TYPE_FLOAT] = bt_ctf_field_generic_reset, + [CTF_TYPE_STRUCT] = bt_ctf_field_structure_reset, + [CTF_TYPE_VARIANT] = bt_ctf_field_variant_reset, + [CTF_TYPE_ARRAY] = bt_ctf_field_array_reset, + [CTF_TYPE_SEQUENCE] = bt_ctf_field_sequence_reset, + [CTF_TYPE_STRING] = bt_ctf_field_string_reset, +}; + static int (*field_serialize_funcs[])(struct bt_ctf_field *, struct ctf_stream_pos *) = { @@ -305,8 +332,7 @@ struct bt_ctf_field *bt_ctf_field_structure_get_field( struct bt_ctf_field *new_field = NULL; GQuark field_quark; struct bt_ctf_field_structure *structure; - struct bt_ctf_field_type_structure *structure_type; - struct bt_ctf_field_type *field_type; + struct bt_ctf_field_type *field_type = NULL; size_t index; if (!field || !name || @@ -317,9 +343,9 @@ struct bt_ctf_field *bt_ctf_field_structure_get_field( field_quark = g_quark_from_string(name); structure = container_of(field, struct bt_ctf_field_structure, parent); - structure_type = container_of(field->type, - struct bt_ctf_field_type_structure, parent); - field_type = bt_ctf_field_type_structure_get_type(structure_type, name); + field_type = + bt_ctf_field_type_structure_get_field_type_by_name(field->type, + name); if (!g_hash_table_lookup_extended(structure->field_name_to_index, GUINT_TO_POINTER(field_quark), NULL, (gpointer *)&index)) { goto error; @@ -339,6 +365,9 @@ struct bt_ctf_field *bt_ctf_field_structure_get_field( end: bt_ctf_field_get(new_field); error: + if (field_type) { + bt_ctf_field_type_put(field_type); + } return new_field; } @@ -402,8 +431,7 @@ int bt_ctf_field_structure_set_field(struct bt_ctf_field *field, int ret = 0; GQuark field_quark; struct bt_ctf_field_structure *structure; - struct bt_ctf_field_type_structure *structure_type; - struct bt_ctf_field_type *expected_field_type; + struct bt_ctf_field_type *expected_field_type = NULL; size_t index; if (!field || !name || !value || @@ -415,10 +443,9 @@ int bt_ctf_field_structure_set_field(struct bt_ctf_field *field, field_quark = g_quark_from_string(name); structure = container_of(field, struct bt_ctf_field_structure, parent); - structure_type = container_of(field->type, - struct bt_ctf_field_type_structure, parent); - expected_field_type = bt_ctf_field_type_structure_get_type( - structure_type, name); + expected_field_type = + bt_ctf_field_type_structure_get_field_type_by_name(field->type, + name); if (expected_field_type != value->type) { ret = -1; goto end; @@ -436,6 +463,9 @@ int bt_ctf_field_structure_set_field(struct bt_ctf_field *field, structure->fields->pdata[index] = value; bt_ctf_field_get(value); end: + if (expected_field_type) { + bt_ctf_field_type_put(expected_field_type); + } return ret; } @@ -443,9 +473,8 @@ struct bt_ctf_field *bt_ctf_field_array_get_field(struct bt_ctf_field *field, uint64_t index) { struct bt_ctf_field *new_field = NULL; + struct bt_ctf_field_type *field_type = NULL; struct bt_ctf_field_array *array; - struct bt_ctf_field_type_array *array_type; - struct bt_ctf_field_type *field_type; if (!field || bt_ctf_field_type_get_type_id(field->type) != CTF_TYPE_ARRAY) { @@ -457,9 +486,7 @@ struct bt_ctf_field *bt_ctf_field_array_get_field(struct bt_ctf_field *field, goto end; } - array_type = container_of(field->type, struct bt_ctf_field_type_array, - parent); - field_type = bt_ctf_field_type_array_get_element_type(array_type); + field_type = bt_ctf_field_type_array_get_element_type(field->type); if (array->elements->pdata[(size_t)index]) { new_field = array->elements->pdata[(size_t)index]; goto end; @@ -469,6 +496,9 @@ struct bt_ctf_field *bt_ctf_field_array_get_field(struct bt_ctf_field *field, bt_ctf_field_get(new_field); array->elements->pdata[(size_t)index] = new_field; end: + if (field_type) { + bt_ctf_field_type_put(field_type); + } return new_field; } @@ -476,9 +506,8 @@ struct bt_ctf_field *bt_ctf_field_sequence_get_field(struct bt_ctf_field *field, uint64_t index) { struct bt_ctf_field *new_field = NULL; + struct bt_ctf_field_type *field_type = NULL; struct bt_ctf_field_sequence *sequence; - struct bt_ctf_field_type_sequence *sequence_type; - struct bt_ctf_field_type *field_type; if (!field || bt_ctf_field_type_get_type_id(field->type) != CTF_TYPE_SEQUENCE) { @@ -490,9 +519,7 @@ struct bt_ctf_field *bt_ctf_field_sequence_get_field(struct bt_ctf_field *field, goto end; } - sequence_type = container_of(field->type, - struct bt_ctf_field_type_sequence, parent); - field_type = bt_ctf_field_type_sequence_get_element_type(sequence_type); + field_type = bt_ctf_field_type_sequence_get_element_type(field->type); if (sequence->elements->pdata[(size_t)index]) { new_field = sequence->elements->pdata[(size_t)index]; goto end; @@ -502,6 +529,9 @@ struct bt_ctf_field *bt_ctf_field_sequence_get_field(struct bt_ctf_field *field, bt_ctf_field_get(new_field); sequence->elements->pdata[(size_t)index] = new_field; end: + if (field_type) { + bt_ctf_field_type_put(field_type); + } return new_field; } @@ -540,8 +570,8 @@ struct bt_ctf_field *bt_ctf_field_variant_get_field(struct bt_ctf_field *field, } tag_enum_value = tag_enum_integer->definition.value._signed; - field_type = bt_ctf_field_type_variant_get_field_type(variant_type, - tag_enum_value); + field_type = bt_ctf_field_type_variant_get_field_type_signed( + variant_type, tag_enum_value); if (!field_type) { goto end; } @@ -568,7 +598,8 @@ struct bt_ctf_field *bt_ctf_field_enumeration_get_container( struct bt_ctf_field *container = NULL; struct bt_ctf_field_enumeration *enumeration; - if (!field) { + if (!field || bt_ctf_field_type_get_type_id(field->type) != + CTF_TYPE_ENUM) { goto end; } @@ -847,10 +878,11 @@ int bt_ctf_field_string_set_value(struct bt_ctf_field *field, string = container_of(field, struct bt_ctf_field_string, parent); if (string->payload) { - g_string_free(string->payload, TRUE); + g_string_assign(string->payload, value); + } else { + string->payload = g_string_new(value); } - string->payload = g_string_new(value); string->parent.payload_set = 1; end: return ret; @@ -878,6 +910,28 @@ end: return ret; } +BT_HIDDEN +int bt_ctf_field_reset(struct bt_ctf_field *field) +{ + int ret = 0; + enum ctf_type_id type_id; + + if (!field) { + ret = -1; + goto end; + } + + type_id = bt_ctf_field_type_get_type_id(field->type); + if (type_id <= CTF_TYPE_UNKNOWN || type_id >= NR_CTF_TYPES) { + ret = -1; + goto end; + } + + ret = field_reset_funcs[type_id](field); +end: + return ret; +} + BT_HIDDEN int bt_ctf_field_serialize(struct bt_ctf_field *field, struct ctf_stream_pos *pos) @@ -1292,6 +1346,185 @@ end: return ret; } +static +int bt_ctf_field_generic_reset(struct bt_ctf_field *field) +{ + int ret = 0; + + if (!field) { + ret = -1; + goto end; + } + + field->payload_set = 0; +end: + return ret; +} + +static +int bt_ctf_field_enumeration_reset(struct bt_ctf_field *field) +{ + int ret = 0; + struct bt_ctf_field_enumeration *enumeration; + + if (!field) { + ret = -1; + goto end; + } + + enumeration = container_of(field, struct bt_ctf_field_enumeration, + parent); + if (!enumeration->payload) { + goto end; + } + + ret = bt_ctf_field_reset(enumeration->payload); +end: + return ret; +} + +static +int bt_ctf_field_structure_reset(struct bt_ctf_field *field) +{ + size_t i; + int ret = 0; + struct bt_ctf_field_structure *structure; + + if (!field) { + ret = -1; + goto end; + } + + structure = container_of(field, struct bt_ctf_field_structure, parent); + for (i = 0; i < structure->fields->len; i++) { + struct bt_ctf_field *member = structure->fields->pdata[i]; + + if (!member) { + /* + * Structure members are lazily initialized; skip if + * this member has not been allocated yet. + */ + continue; + } + + ret = bt_ctf_field_reset(member); + if (ret) { + goto end; + } + } +end: + return ret; +} + +static +int bt_ctf_field_variant_reset(struct bt_ctf_field *field) +{ + int ret = 0; + struct bt_ctf_field_variant *variant; + + if (!field) { + ret = -1; + goto end; + } + + variant = container_of(field, struct bt_ctf_field_variant, parent); + if (variant->payload) { + ret = bt_ctf_field_reset(variant->payload); + } +end: + return ret; +} + +static +int bt_ctf_field_array_reset(struct bt_ctf_field *field) +{ + size_t i; + int ret = 0; + struct bt_ctf_field_array *array; + + if (!field) { + ret = -1; + goto end; + } + + array = container_of(field, struct bt_ctf_field_array, parent); + for (i = 0; i < array->elements->len; i++) { + struct bt_ctf_field *member = array->elements->pdata[i]; + + if (!member) { + /* + * Array elements are lazily initialized; skip if + * this member has not been allocated yet. + */ + continue; + } + + ret = bt_ctf_field_reset(member); + if (ret) { + goto end; + } + } +end: + return ret; +} + +static +int bt_ctf_field_sequence_reset(struct bt_ctf_field *field) +{ + size_t i; + int ret = 0; + struct bt_ctf_field_sequence *sequence; + + if (!field) { + ret = -1; + goto end; + } + + sequence = container_of(field, struct bt_ctf_field_sequence, parent); + for (i = 0; i < sequence->elements->len; i++) { + struct bt_ctf_field *member = sequence->elements->pdata[i]; + + if (!member) { + /* + * Sequence elements are lazily initialized; skip if + * this member has not been allocated yet. + */ + continue; + } + + ret = bt_ctf_field_reset(member); + if (ret) { + goto end; + } + } +end: + return ret; +} + +static +int bt_ctf_field_string_reset(struct bt_ctf_field *field) +{ + int ret = 0; + struct bt_ctf_field_string *string; + + if (!field) { + ret = -1; + goto end; + } + + ret = bt_ctf_field_generic_reset(field); + if (ret) { + goto end; + } + + string = container_of(field, struct bt_ctf_field_string, parent); + if (string->payload) { + g_string_truncate(string->payload, 0); + } +end: + return ret; +} + static int bt_ctf_field_integer_serialize(struct bt_ctf_field *field, struct ctf_stream_pos *pos)