0ee1b0928ed3e20f34c190585d8d79ccee3bb2fb
[lttv.git] / lttv / lttv / iattribute.c
1 /* This file is part of the Linux Trace Toolkit viewer
2 * Copyright (C) 2003-2004 Michel Dagenais
3 *
4 * This program is free software; you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License Version 2 as
6 * published by the Free Software Foundation;
7 *
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
12 *
13 * You should have received a copy of the GNU General Public License
14 * along with this program; if not, write to the Free Software
15 * Foundation, Inc., 59 Temple Place - Suite 330, Boston,
16 * MA 02111-1307, USA.
17 */
18
19 #ifdef HAVE_CONFIG_H
20 #include <config.h>
21 #endif
22
23 #include <lttv/iattribute.h>
24
25 static void lttv_iattribute_base_init (gpointer klass)
26 {
27 static gboolean initialized = FALSE;
28
29 if (!initialized) {
30 initialized = TRUE;
31 }
32 }
33
34
35 GType lttv_iattribute_get_type (void)
36 {
37 static GType type = 0;
38 if (type == 0) {
39 static const GTypeInfo info = {
40 sizeof (LttvIAttributeClass),
41 lttv_iattribute_base_init, /* base_init */
42 NULL, /* base_finalize */
43 NULL, /* class_init */
44 NULL, /* class_finalize */
45 NULL, /* class_data */
46 0,
47 0, /* n_preallocs */
48 NULL /* instance_init */
49 };
50 type = g_type_register_static (G_TYPE_INTERFACE, "LttvIAttribute",
51 &info, 0);
52 }
53 return type;
54 }
55
56
57 unsigned int lttv_iattribute_get_number(LttvIAttribute *self)
58 {
59 return LTTV_IATTRIBUTE_GET_CLASS (self)->get_number (self);
60 }
61
62
63 gboolean lttv_iattribute_named(LttvIAttribute *self, gboolean *homogeneous)
64 {
65 return LTTV_IATTRIBUTE_GET_CLASS (self)->named (self, homogeneous);
66 }
67
68
69 LttvAttributeType lttv_iattribute_get(LttvIAttribute *self, unsigned i,
70 LttvAttributeName *name, LttvAttributeValue *v, gboolean *is_named)
71 {
72 return LTTV_IATTRIBUTE_GET_CLASS (self)->get (self, i, name, v, is_named);
73 }
74
75
76 LttvAttributeType lttv_iattribute_get_by_name(LttvIAttribute *self,
77 LttvAttributeName name, LttvAttributeValue *v)
78 {
79 return LTTV_IATTRIBUTE_GET_CLASS (self)->get_by_name (self, name, v);
80 }
81
82
83 LttvAttributeValue lttv_iattribute_add(LttvIAttribute *self,
84 LttvAttributeName name, LttvAttributeType t)
85 {
86 return LTTV_IATTRIBUTE_GET_CLASS (self)->add (self, name, t);
87 }
88
89 LttvAttributeValue lttv_iattribute_add_unnamed(LttvIAttribute *self,
90 LttvAttributeName name, LttvAttributeType t)
91 {
92 return LTTV_IATTRIBUTE_GET_CLASS (self)->add_unnamed (self, name, t);
93 }
94
95 void lttv_iattribute_remove(LttvIAttribute *self, unsigned i)
96 {
97 return LTTV_IATTRIBUTE_GET_CLASS (self)->remove (self, i);
98 }
99
100
101 void lttv_iattribute_remove_by_name(LttvIAttribute *self,
102 LttvAttributeName name)
103 {
104 return LTTV_IATTRIBUTE_GET_CLASS (self)->remove_by_name (self, name);
105 }
106
107 LttvIAttribute* lttv_iattribute_find_subdir(LttvIAttribute *self,
108 LttvAttributeName name)
109 {
110 return LTTV_IATTRIBUTE_GET_CLASS (self)->find_subdir (self, name);
111 }
112
113 LttvIAttribute* lttv_iattribute_find_subdir_unnamed(LttvIAttribute *self,
114 LttvAttributeName name)
115 {
116 return LTTV_IATTRIBUTE_GET_CLASS (self)->find_subdir_unnamed (self, name);
117 }
118
119
120
121 /* Find the named attribute in the table, which must be of the specified type.
122 If it does not exist, it is created with a default value of 0 (NULL for
123 pointer types). Since the address of the value is obtained, it may be
124 changed easily afterwards. The function returns false when the attribute
125 exists but is of incorrect type. */
126
127 gboolean lttv_iattribute_find(LttvIAttribute *self, LttvAttributeName name,
128 LttvAttributeType t, LttvAttributeValue *v)
129 {
130 LttvAttributeType found_type;
131
132 found_type = lttv_iattribute_get_by_name(self, name, v);
133 if(found_type == t) return TRUE;
134
135 if(found_type == LTTV_NONE) {
136 *v = lttv_iattribute_add(self, name, t);
137 return TRUE;
138 }
139
140 return FALSE;
141 }
142
143
144 /* Trees of attribute tables may be accessed using a hierarchical path with
145 components separated by /, like in filesystems */
146
147 gboolean lttv_iattribute_find_by_path(LttvIAttribute *self, const char *path,
148 LttvAttributeType t, LttvAttributeValue *v)
149 {
150 LttvIAttribute *node = self;
151
152 LttvAttributeType found_type;
153
154 LttvAttributeName name;
155
156 gchar **components, **cursor;
157
158 components = g_strsplit(path, "\"", G_MAXINT);
159
160 if(components == NULL || *components == NULL) {
161 g_strfreev(components);
162 return FALSE;
163 }
164
165 for(cursor = components;;) {
166 name = g_quark_from_string(*cursor);
167 cursor++;
168
169 if(*cursor == NULL) {
170 g_strfreev(components);
171 return lttv_iattribute_find(node, name, t, v);
172 } else {
173 found_type = lttv_iattribute_get_by_name(node, name, v);
174 if(found_type == LTTV_NONE) {
175 node = lttv_iattribute_find_subdir(node, name);
176 }
177 else if(found_type == LTTV_GOBJECT &&
178 LTTV_IS_IATTRIBUTE(*(v->v_gobject))) {
179 node = LTTV_IATTRIBUTE(*(v->v_gobject));
180 } else {
181 g_strfreev(components);
182 return FALSE;
183 }
184 }
185 }
186 }
187
188
189 /* Shallow and deep copies */
190
191 LttvIAttribute *lttv_iattribute_shallow_copy(LttvIAttribute *self)
192 {
193 LttvIAttribute *copy;
194
195 LttvAttributeType t;
196
197 LttvAttributeValue v, v_copy;
198
199 LttvAttributeName name;
200
201 gboolean is_named;
202
203 int i;
204
205 int nb_attributes = lttv_iattribute_get_number(self);
206
207 copy = LTTV_IATTRIBUTE_GET_CLASS(self)->new_attribute(NULL);
208
209 for(i = 0 ; i < nb_attributes ; i++) {
210 t = lttv_iattribute_get(self, i, &name, &v, &is_named);
211 if(is_named)
212 v_copy = lttv_iattribute_add(copy, name, t);
213 else
214 v_copy = lttv_iattribute_add_unnamed(copy, name, t);
215 lttv_iattribute_copy_value(t, v_copy, v);
216 }
217 return copy;
218 }
219
220 LttvIAttribute *lttv_iattribute_deep_copy(LttvIAttribute *self)
221 {
222 LttvIAttribute *copy, *child;
223
224 LttvAttributeType t;
225
226 LttvAttributeValue v, v_copy;
227
228 LttvAttributeName name;
229
230 gboolean is_named;
231
232 int i;
233
234 int nb_attributes = lttv_iattribute_get_number(self);
235
236 copy = LTTV_IATTRIBUTE_GET_CLASS(self)->new_attribute(NULL);
237
238 for(i = 0 ; i < nb_attributes ; i++) {
239 t = lttv_iattribute_get(self, i, &name, &v, &is_named);
240 if(is_named)
241 v_copy = lttv_iattribute_add(copy, name, t);
242 else
243 v_copy = lttv_iattribute_add_unnamed(copy, name, t);
244 if(t == LTTV_GOBJECT && LTTV_IS_IATTRIBUTE(*(v.v_gobject))) {
245 child = LTTV_IATTRIBUTE(*(v.v_gobject));
246 *(v_copy.v_gobject) = G_OBJECT(lttv_iattribute_deep_copy(child));
247 }
248 else lttv_iattribute_copy_value(t, v_copy, v);
249 }
250 return copy;
251 }
252
253 void lttv_iattribute_copy_value(LttvAttributeType t, LttvAttributeValue dest,
254 LttvAttributeValue src)
255 {
256 switch(t) {
257 case LTTV_INT:
258 *(dest.v_int) = *(src.v_int);
259 break;
260
261 case LTTV_UINT:
262 *(dest.v_uint) = *(src.v_uint);
263 break;
264
265 case LTTV_LONG:
266 *(dest.v_long) = *(src.v_long);
267 break;
268
269 case LTTV_ULONG:
270 *(dest.v_ulong) = *(src.v_ulong);
271 break;
272
273 case LTTV_FLOAT:
274 *(dest.v_float) = *(src.v_float);
275 break;
276
277 case LTTV_DOUBLE:
278 *(dest.v_double) = *(src.v_double);
279 break;
280
281 case LTTV_TIME:
282 *(dest.v_time) = *(src.v_time);
283 break;
284
285 case LTTV_POINTER:
286 *(dest.v_pointer) = *(src.v_pointer);
287 break;
288
289 case LTTV_STRING:
290 *(dest.v_string) = *(src.v_string);
291 break;
292
293 case LTTV_GOBJECT:
294 *(dest.v_gobject) = *(src.v_gobject);
295 if(*(dest.v_gobject) != NULL) g_object_ref(*(dest.v_gobject));
296 break;
297
298 case LTTV_NONE:
299 break;
300 }
301 }
302
303
This page took 0.034356 seconds and 3 git commands to generate.