Merge branch 'master' into lttng-luna
[deliverable/tracecompass.git] / org.eclipse.linuxtools.tmf.core / src / org / eclipse / linuxtools / tmf / core / ctfadaptor / CtfTmfEventField.java
CommitLineData
a3fc8213 1/*******************************************************************************
404b264a 2 * Copyright (c) 2011, 2013 Ericsson, École Polytechnique de Montréal
a3fc8213
AM
3 *
4 * All rights reserved. This program and the accompanying materials are made
5 * available under the terms of the Eclipse Public License v1.0 which
6 * accompanies this distribution, and is available at
7 * http://www.eclipse.org/legal/epl-v10.html
8 *
d4a8d935
BH
9 * Contributors:
10 * Matthew Khouzam - Initial API and implementation
404b264a 11 * Alexandre Montplaisir - Initial API and implementation, extend TmfEventField
d4a8d935 12 * Bernd Hufmann - Add Enum field handling
404b264a 13 * Geneviève Bastien - Add Struct and Variant field handling
459f705b 14 * Jean-Christian Kouame - Correct handling of unsigned integer fields
a3fc8213
AM
15 *******************************************************************************/
16
17package org.eclipse.linuxtools.tmf.core.ctfadaptor;
18
a6223d74 19import java.util.ArrayList;
7a6cee1a 20import java.util.Arrays;
a6223d74 21import java.util.List;
7a6cee1a 22import java.util.Map.Entry;
a6223d74 23
a3fc8213
AM
24import org.eclipse.linuxtools.ctf.core.event.types.ArrayDeclaration;
25import org.eclipse.linuxtools.ctf.core.event.types.ArrayDefinition;
26import org.eclipse.linuxtools.ctf.core.event.types.Definition;
21fb02fa 27import org.eclipse.linuxtools.ctf.core.event.types.EnumDefinition;
a04464b1 28import org.eclipse.linuxtools.ctf.core.event.types.FloatDefinition;
a3fc8213
AM
29import org.eclipse.linuxtools.ctf.core.event.types.IntegerDeclaration;
30import org.eclipse.linuxtools.ctf.core.event.types.IntegerDefinition;
31import org.eclipse.linuxtools.ctf.core.event.types.SequenceDeclaration;
32import org.eclipse.linuxtools.ctf.core.event.types.SequenceDefinition;
33import org.eclipse.linuxtools.ctf.core.event.types.StringDefinition;
7a6cee1a 34import org.eclipse.linuxtools.ctf.core.event.types.StructDefinition;
404b264a
GB
35import org.eclipse.linuxtools.ctf.core.event.types.VariantDefinition;
36import org.eclipse.linuxtools.internal.tmf.core.Messages;
7a6cee1a 37import org.eclipse.linuxtools.tmf.core.event.ITmfEventField;
68b18f2f 38import org.eclipse.linuxtools.tmf.core.event.TmfEventField;
a3fc8213
AM
39
40/**
7558a1e1
AM
41 * The CTF implementation of the TMF event field model
42 *
d4a8d935 43 * @version 2.0
7558a1e1 44 * @author Matthew Khouzam
d09f973b 45 * @author Alexandre Montplaisir
a3fc8213 46 */
68b18f2f 47public abstract class CtfTmfEventField extends TmfEventField {
a3fc8213 48
a3fc8213 49 // ------------------------------------------------------------------------
7558a1e1 50 // Constructor
a3fc8213
AM
51 // ------------------------------------------------------------------------
52
b1baa808 53 /**
7558a1e1
AM
54 * Standard constructor. Only to be used internally, call parseField() to
55 * generate a new field object.
56 *
57 * @param name
58 * The name of this field
68b18f2f
AM
59 * @param value
60 * The value of this field. Its type should match the field type.
81ed27a8
MK
61 * @param fields
62 * The children fields. Useful for composite fields
68b18f2f 63 * @since 2.0
b1baa808 64 */
81ed27a8 65 protected CtfTmfEventField(String name, Object value, ITmfEventField[] fields) {
68b18f2f
AM
66 super(/* Strip the underscore from the field name if there is one */
67 name.startsWith("_") ? name.substring(1) : name, //$NON-NLS-1$
68 value,
81ed27a8 69 fields);
a3fc8213
AM
70 }
71
72 // ------------------------------------------------------------------------
73 // Operations
74 // ------------------------------------------------------------------------
75
b1baa808 76 /**
7558a1e1
AM
77 * Factory method to instantiate CtfTmfEventField objects.
78 *
79 * @param fieldDef
80 * The CTF Definition of this event field
81 * @param fieldName
82 * String The name to assign to this field
83 * @return The resulting CtfTmfEventField object
b1baa808 84 */
a3fc8213
AM
85 public static CtfTmfEventField parseField(Definition fieldDef,
86 String fieldName) {
87 CtfTmfEventField field = null;
88
89 /* Determine the Definition type */
90 if (fieldDef instanceof IntegerDefinition) {
367bcd2b
AM
91 IntegerDefinition intDef = (IntegerDefinition) fieldDef;
92 int base = intDef.getDeclaration().getBase();
459f705b 93 field = new CTFIntegerField(fieldName, intDef.getValue(), base, intDef.getDeclaration().isSigned());
a3fc8213 94
21fb02fa
MK
95 } else if (fieldDef instanceof EnumDefinition) {
96 EnumDefinition enumDef = (EnumDefinition) fieldDef;
68b18f2f 97 field = new CTFEnumField(fieldName, new CtfEnumPair(enumDef.getValue(), enumDef.getIntegerValue()));
21fb02fa 98
a3fc8213 99 } else if (fieldDef instanceof StringDefinition) {
68b18f2f
AM
100 field = new CTFStringField(fieldName, ((StringDefinition) fieldDef).getValue());
101
102 } else if (fieldDef instanceof FloatDefinition) {
103 FloatDefinition floatDef = (FloatDefinition) fieldDef;
104 field = new CTFFloatField(fieldName, floatDef.getValue());
a3fc8213
AM
105
106 } else if (fieldDef instanceof ArrayDefinition) {
107 ArrayDefinition arrayDef = (ArrayDefinition) fieldDef;
108 ArrayDeclaration arrayDecl = arrayDef.getDeclaration();
109
110 if (arrayDef.isString()) {
111 /* This is an array of UTF-8 bytes, a.k.a. a String! */
68b18f2f 112 field = new CTFStringField(fieldName, fieldDef.toString());
a3fc8213
AM
113
114 } else if (arrayDecl.getElementType() instanceof IntegerDeclaration) {
115 /* This is a an array of CTF Integers */
68b18f2f 116 List<Long> values = new ArrayList<Long>(arrayDecl.getLength());
a3fc8213 117 for (int i = 0; i < arrayDecl.getLength(); i++) {
68b18f2f 118 values.add(((IntegerDefinition) arrayDef.getElem(i)).getValue());
a3fc8213 119 }
459f705b
JCK
120 field = new CTFIntegerArrayField(fieldName, values, ((IntegerDeclaration) arrayDecl.getElementType()).getBase(),
121 ((IntegerDeclaration) arrayDecl.getElementType()).isSigned());
a3fc8213
AM
122 }
123 /* Add other types of arrays here */
124
125 } else if (fieldDef instanceof SequenceDefinition) {
126 SequenceDefinition seqDef = (SequenceDefinition) fieldDef;
127 SequenceDeclaration seqDecl = seqDef.getDeclaration();
128
129 if (seqDef.getLength() == 0) {
130 /* Some sequences have length = 0. Simply use an empty string */
68b18f2f 131 field = new CTFStringField(fieldName, ""); //$NON-NLS-1$
a3fc8213
AM
132 } else if (seqDef.isString()) {
133 /* Interpret this sequence as a String */
68b18f2f 134 field = new CTFStringField(fieldName, seqDef.toString());
a3fc8213
AM
135 } else if (seqDecl.getElementType() instanceof IntegerDeclaration) {
136 /* Sequence of integers => CTFIntegerArrayField */
68b18f2f 137 List<Long> values = new ArrayList<Long>(seqDef.getLength());
a3fc8213 138 for (int i = 0; i < seqDef.getLength(); i++) {
68b18f2f 139 values.add(((IntegerDefinition) seqDef.getElem(i)).getValue());
a3fc8213 140 }
459f705b
JCK
141 field = new CTFIntegerArrayField(fieldName, values, ((IntegerDeclaration) seqDecl.getElementType()).getBase(),
142 ((IntegerDeclaration) seqDecl.getElementType()).isSigned());
a3fc8213
AM
143 }
144 /* Add other Sequence types here */
367bcd2b 145
7a6cee1a
GB
146 } else if (fieldDef instanceof StructDefinition) {
147 StructDefinition strDef = (StructDefinition) fieldDef;
148
149 String curFieldName = null;
150 Definition curFieldDef;
151 CtfTmfEventField curField;
152 List<ITmfEventField> list = new ArrayList<ITmfEventField>();
153 /* Recursively parse the fields */
154 for (Entry<String, Definition> entry : strDef.getDefinitions().entrySet()) {
155 curFieldName = entry.getKey();
156 curFieldDef = entry.getValue();
157 curField = CtfTmfEventField.parseField(curFieldDef, curFieldName);
158 list.add(curField);
159 }
160 field = new CTFStructField(fieldName, list.toArray(new CtfTmfEventField[list.size()]));
a0e9eac8 161
404b264a
GB
162 } else if (fieldDef instanceof VariantDefinition) {
163 VariantDefinition varDef = (VariantDefinition) fieldDef;
164
165 String curFieldName = varDef.getCurrentFieldName();
166 Definition curFieldDef = varDef.getDefinitions().get(curFieldName);
167 if (curFieldDef != null) {
51cc7ef4
GB
168 CtfTmfEventField subField = CtfTmfEventField.parseField(curFieldDef, curFieldName);
169 field = new CTFVariantField(fieldName, subField);
404b264a
GB
170 } else {
171 /* A safe-guard, but curFieldDef should never be null */
172 field = new CTFStringField(curFieldName, ""); //$NON-NLS-1$
173 }
174
175 } else {
459f705b
JCK
176 /*
177 * Safe-guard, to avoid null exceptions later, field is expected not
178 * to be null
179 */
404b264a 180 field = new CTFStringField(fieldName, Messages.TmfEventField_UnsupportedType + fieldDef.getClass().toString());
a3fc8213 181 }
a3fc8213
AM
182 return field;
183 }
184
a3fc8213 185 @Override
68b18f2f 186 public String toString() {
51cc7ef4 187 return getName() + '=' + getFormattedValue();
a3fc8213 188 }
a3fc8213
AM
189}
190
191/**
7558a1e1
AM
192 * The CTF field implementation for integer fields.
193 *
194 * @author alexmont
a3fc8213
AM
195 */
196final class CTFIntegerField extends CtfTmfEventField {
197
367bcd2b 198 private final int base;
459f705b 199 private final boolean signed;
a3fc8213
AM
200
201 /**
202 * A CTF "IntegerDefinition" can be an integer of any byte size, so in the
203 * Java parser this is interpreted as a long.
7558a1e1 204 *
7558a1e1
AM
205 * @param name
206 * The name of this field
459f705b
JCK
207 * @param longValue
208 * The integer value of this field
209 * @param signed
210 * Is the value signed or not
a3fc8213 211 */
459f705b 212 CTFIntegerField(String name, long longValue, int base, boolean signed) {
81ed27a8 213 super(name, longValue, null);
459f705b 214 this.signed = signed;
367bcd2b
AM
215 this.base = base;
216 }
217
a3fc8213
AM
218 @Override
219 public Long getValue() {
68b18f2f 220 return (Long) super.getValue();
a3fc8213
AM
221 }
222
8f86c552
GB
223 @Override
224 public String getFormattedValue() {
3b11ddc7 225 return IntegerDefinition.formatNumber(getValue(), base, signed);
8f86c552
GB
226 }
227
a3fc8213
AM
228}
229
230/**
7558a1e1
AM
231 * The CTF field implementation for string fields
232 *
233 * @author alexmont
a3fc8213
AM
234 */
235final class CTFStringField extends CtfTmfEventField {
236
b1baa808
MK
237 /**
238 * Constructor for CTFStringField.
7558a1e1
AM
239 *
240 * @param strValue
241 * The string value of this field
242 * @param name
243 * The name of this field
b1baa808 244 */
68b18f2f 245 CTFStringField(String name, String strValue) {
81ed27a8 246 super(name, strValue, null);
a3fc8213
AM
247 }
248
a3fc8213
AM
249 @Override
250 public String getValue() {
68b18f2f 251 return (String) super.getValue();
a3fc8213
AM
252 }
253}
254
255/**
7558a1e1
AM
256 * CTF field implementation for arrays of integers.
257 *
258 * @author alexmont
a3fc8213
AM
259 */
260final class CTFIntegerArrayField extends CtfTmfEventField {
261
404b264a 262 private final int base;
459f705b 263 private final boolean signed;
8f86c552 264 private String formattedValue = null;
404b264a 265
b1baa808
MK
266 /**
267 * Constructor for CTFIntegerArrayField.
7558a1e1 268 *
459f705b
JCK
269 * @param name
270 * The name of this field
7558a1e1
AM
271 * @param longValues
272 * The array of integers (as longs) that compose this field's
273 * value
459f705b
JCK
274 * @param signed
275 * Are the values in the array signed or not
b1baa808 276 */
459f705b 277 CTFIntegerArrayField(String name, List<Long> longValues, int base, boolean signed) {
81ed27a8 278 super(name, longValues, null);
404b264a 279 this.base = base;
459f705b 280 this.signed = signed;
a3fc8213
AM
281 }
282
a6223d74
MK
283 @Override
284 public List<Long> getValue() {
68b18f2f 285 return (List<Long>) super.getValue();
a3fc8213 286 }
404b264a 287
8f86c552
GB
288 @Override
289 public String getFormattedValue() {
290 if (formattedValue == null) {
291 List<String> strings = new ArrayList<String>();
292 for (Long value : getValue()) {
3b11ddc7 293 strings.add(IntegerDefinition.formatNumber(value, base, signed));
8f86c552
GB
294 }
295 formattedValue = strings.toString();
296 }
297 return formattedValue;
298 }
299
a3fc8213
AM
300}
301
b1baa808 302/**
7558a1e1
AM
303 * CTF field implementation for floats.
304 *
305 * @author emathko
b1baa808 306 */
a04464b1
MK
307final class CTFFloatField extends CtfTmfEventField {
308
b1baa808
MK
309 /**
310 * Constructor for CTFFloatField.
7558a1e1
AM
311 *
312 * @param value
313 * The float value (actually a double) of this field
314 * @param name
315 * The name of this field
b1baa808 316 */
68b18f2f 317 protected CTFFloatField(String name, double value) {
81ed27a8 318 super(name, value, null);
a04464b1
MK
319 }
320
a04464b1 321 @Override
81c8e6f7 322 public Double getValue() {
68b18f2f 323 return (Double) super.getValue();
a04464b1 324 }
a04464b1 325}
7558a1e1 326
d4a8d935
BH
327/**
328 * The CTF field implementation for Enum fields
329 *
330 * @author Bernd Hufmann
331 */
332final class CTFEnumField extends CtfTmfEventField {
333
d4a8d935
BH
334 /**
335 * Constructor for CTFEnumField.
336 *
337 * @param enumValue
459f705b
JCK
338 * The Enum value consisting of a pair of Enum value name and its
339 * long value
d4a8d935
BH
340 * @param name
341 * The name of this field
342 */
68b18f2f
AM
343 CTFEnumField(String name, CtfEnumPair enumValue) {
344 super(name, new CtfEnumPair(enumValue.getFirst(),
459f705b 345 enumValue.getSecond().longValue()), null);
d4a8d935
BH
346 }
347
d4a8d935 348 @Override
68b18f2f
AM
349 public CtfEnumPair getValue() {
350 return (CtfEnumPair) super.getValue();
d4a8d935
BH
351 }
352}
353
7a6cee1a 354/**
51cc7ef4 355 * The CTF field implementation for struct fields with sub-fields
7a6cee1a
GB
356 *
357 * @author gbastien
358 */
359final class CTFStructField extends CtfTmfEventField {
360
361 /**
51cc7ef4 362 * Constructor for CTFStructField.
7a6cee1a 363 *
51cc7ef4
GB
364 * @param fields
365 * The children of this field
7a6cee1a
GB
366 * @param name
367 * The name of this field
368 */
369 CTFStructField(String name, CtfTmfEventField[] fields) {
81ed27a8 370 super(name, fields, fields);
7a6cee1a
GB
371 }
372
7a6cee1a
GB
373 @Override
374 public CtfTmfEventField[] getValue() {
375 return (CtfTmfEventField[]) super.getValue();
376 }
377
378 @Override
51cc7ef4
GB
379 public String getFormattedValue() {
380 return Arrays.toString(getValue());
7a6cee1a 381 }
51cc7ef4
GB
382
383}
384
385/**
386 * The CTF field implementation for variant fields its child
387 *
388 * @author gbastien
389 */
390final class CTFVariantField extends CtfTmfEventField {
391
392 /**
393 * Constructor for CTFVariantField.
394 *
395 * @param field
396 * The field selected for this variant
397 * @param name
398 * The name of this field
399 */
400 CTFVariantField(String name, CtfTmfEventField field) {
459f705b 401 super(name, field, new CtfTmfEventField[] { field });
51cc7ef4
GB
402 }
403
404 @Override
405 public CtfTmfEventField getValue() {
406 return (CtfTmfEventField) super.getValue();
407 }
408
7a6cee1a
GB
409}
410
a3fc8213 411/* Implement other possible fields types here... */
This page took 0.057904 seconds and 5 git commands to generate.