internalize some CTF API
authorMatthew Khouzam <matthew.khouzam@ericsson.com>
Wed, 11 Apr 2012 19:04:58 +0000 (15:04 -0400)
committerFrancois Chouinard <fchouinard@gmail.com>
Mon, 16 Apr 2012 18:20:31 +0000 (14:20 -0400)
38 files changed:
org.eclipse.linuxtools.ctf.core.tests/src/org/eclipse/linuxtools/ctf/core/tests/event/CTFEventFieldTest.java
org.eclipse.linuxtools.ctf.core.tests/src/org/eclipse/linuxtools/ctf/core/tests/io/BitBufferIntTest.java
org.eclipse.linuxtools.ctf.core.tests/src/org/eclipse/linuxtools/ctf/core/tests/io/BitBufferTest.java
org.eclipse.linuxtools.ctf.core.tests/src/org/eclipse/linuxtools/ctf/core/tests/trace/StreamInputPacketIndexEntryTest.java
org.eclipse.linuxtools.ctf.core.tests/src/org/eclipse/linuxtools/ctf/core/tests/trace/StreamInputPacketIndexTest.java
org.eclipse.linuxtools.ctf.core.tests/src/org/eclipse/linuxtools/ctf/core/tests/trace/StreamInputPacketReaderTest.java
org.eclipse.linuxtools.ctf.core.tests/src/org/eclipse/linuxtools/ctf/core/tests/trace/StreamInputReaderComparatorTest.java
org.eclipse.linuxtools.ctf.core.tests/src/org/eclipse/linuxtools/ctf/core/tests/types/ArrayDefinitionTest.java
org.eclipse.linuxtools.ctf.core.tests/src/org/eclipse/linuxtools/ctf/core/tests/types/DefinitionTest.java
org.eclipse.linuxtools.ctf.core.tests/src/org/eclipse/linuxtools/ctf/core/tests/types/EnumDefinitionTest.java
org.eclipse.linuxtools.ctf.core.tests/src/org/eclipse/linuxtools/ctf/core/tests/types/IntegerDefinitionTest.java
org.eclipse.linuxtools.ctf.core.tests/src/org/eclipse/linuxtools/ctf/core/tests/types/SequenceDefinitionTest.java
org.eclipse.linuxtools.ctf.core.tests/src/org/eclipse/linuxtools/ctf/core/tests/types/StringDefinitionTest.java
org.eclipse.linuxtools.ctf.core.tests/src/org/eclipse/linuxtools/ctf/core/tests/types/StructDefinitionTest.java
org.eclipse.linuxtools.ctf.core/META-INF/MANIFEST.MF
org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/ctf/core/event/io/BitBuffer.java [deleted file]
org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/ctf/core/event/metadata/IOStructGen.java [deleted file]
org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/ctf/core/event/types/ArrayDefinition.java
org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/ctf/core/event/types/Definition.java
org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/ctf/core/event/types/EnumDefinition.java
org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/ctf/core/event/types/IntegerDefinition.java
org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/ctf/core/event/types/SequenceDefinition.java
org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/ctf/core/event/types/StringDefinition.java
org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/ctf/core/event/types/StructDefinition.java
org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/ctf/core/event/types/VariantDefinition.java
org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/ctf/core/trace/CTFTrace.java
org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/ctf/core/trace/CTFTraceReader.java
org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/ctf/core/trace/Metadata.java
org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/ctf/core/trace/StreamInput.java
org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/ctf/core/trace/StreamInputPacketIndex.java
org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/ctf/core/trace/StreamInputPacketIndexEntry.java [deleted file]
org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/ctf/core/trace/StreamInputPacketReader.java
org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/ctf/core/trace/StreamInputReader.java
org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/ctf/core/trace/StreamInputReaderComparator.java [deleted file]
org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/internal/ctf/core/event/io/BitBuffer.java [new file with mode: 0644]
org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/internal/ctf/core/event/metadata/IOStructGen.java [new file with mode: 0644]
org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/internal/ctf/core/trace/StreamInputPacketIndexEntry.java [new file with mode: 0644]
org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/internal/ctf/core/trace/StreamInputReaderComparator.java [new file with mode: 0644]

index 47a4d8609c1f5cb04d192ac383739620346724a2..7b5e2da1c13c58bbb4db6bae90b380c5a56c965c 100644 (file)
@@ -6,7 +6,6 @@ import static org.junit.Assert.assertNotNull;
 import java.nio.ByteBuffer;
 import java.nio.ByteOrder;
 
-import org.eclipse.linuxtools.ctf.core.event.io.BitBuffer;
 import org.eclipse.linuxtools.ctf.core.event.types.ArrayDeclaration;
 import org.eclipse.linuxtools.ctf.core.event.types.ArrayDefinition;
 import org.eclipse.linuxtools.ctf.core.event.types.Definition;
@@ -20,6 +19,7 @@ import org.eclipse.linuxtools.ctf.core.event.types.StringDefinition;
 import org.eclipse.linuxtools.ctf.core.event.types.StructDeclaration;
 import org.eclipse.linuxtools.ctf.core.event.types.StructDefinition;
 import org.eclipse.linuxtools.ctf.core.trace.CTFReaderException;
+import org.eclipse.linuxtools.internal.ctf.core.event.io.BitBuffer;
 import org.junit.After;
 import org.junit.Before;
 import org.junit.Test;
index aedef1995968f650d49ff3fba63334f70731b923..79b4bc2fc7eb3c5df86c80c66ec2d985ba2eac3d 100644 (file)
@@ -5,7 +5,7 @@ import static org.junit.Assert.assertEquals;
 import java.nio.ByteBuffer;
 import java.nio.ByteOrder;
 
-import org.eclipse.linuxtools.ctf.core.event.io.BitBuffer;
+import org.eclipse.linuxtools.internal.ctf.core.event.io.BitBuffer;
 import org.junit.After;
 import org.junit.Before;
 import org.junit.Test;
index 84d01067ab29d877e6157ec8219a78d5fb252efd..a8edb89e7b5b3608f91fde958fd2cf46bb986c68 100644 (file)
@@ -6,7 +6,7 @@ import static org.junit.Assert.assertNotNull;
 import java.nio.ByteBuffer;
 import java.nio.ByteOrder;
 
-import org.eclipse.linuxtools.ctf.core.event.io.BitBuffer;
+import org.eclipse.linuxtools.internal.ctf.core.event.io.BitBuffer;
 import org.junit.After;
 import org.junit.Before;
 import org.junit.Test;
index e76e7f11565402302c70c9fe609428b1d678ddb0..0b558ae3a093b21f720c28d6e883822abaa231e7 100644 (file)
@@ -3,7 +3,7 @@ package org.eclipse.linuxtools.ctf.core.tests.trace;
 import static org.junit.Assert.assertEquals;
 import static org.junit.Assert.assertNotNull;
 
-import org.eclipse.linuxtools.ctf.core.trace.StreamInputPacketIndexEntry;
+import org.eclipse.linuxtools.internal.ctf.core.trace.StreamInputPacketIndexEntry;
 import org.junit.After;
 import org.junit.Before;
 import org.junit.Test;
index c83ae86b18e5c559f173a861464b4b9c7f80e49b..99fca9d9d8794e6d1d37e3e410fe7706f4bb5e92 100644 (file)
@@ -8,7 +8,7 @@ import java.util.ListIterator;
 
 import org.eclipse.linuxtools.ctf.core.trace.CTFReaderException;
 import org.eclipse.linuxtools.ctf.core.trace.StreamInputPacketIndex;
-import org.eclipse.linuxtools.ctf.core.trace.StreamInputPacketIndexEntry;
+import org.eclipse.linuxtools.internal.ctf.core.trace.StreamInputPacketIndexEntry;
 import org.junit.After;
 import org.junit.Before;
 import org.junit.Test;
index c075684b3aeeeadfb4141903513222e4c3147b91..49aac9d4b26f3d80eec954f5f65a9ffd37955d2f 100644 (file)
@@ -13,9 +13,9 @@ import org.eclipse.linuxtools.ctf.core.tests.TestParams;
 import org.eclipse.linuxtools.ctf.core.trace.CTFReaderException;
 import org.eclipse.linuxtools.ctf.core.trace.Stream;
 import org.eclipse.linuxtools.ctf.core.trace.StreamInput;
-import org.eclipse.linuxtools.ctf.core.trace.StreamInputPacketIndexEntry;
 import org.eclipse.linuxtools.ctf.core.trace.StreamInputPacketReader;
 import org.eclipse.linuxtools.ctf.core.trace.StreamInputReader;
+import org.eclipse.linuxtools.internal.ctf.core.trace.StreamInputPacketIndexEntry;
 import org.junit.After;
 import org.junit.Before;
 import org.junit.Test;
index 5c4e27892035b164d38500ee6cc0503a315b6280..280194de105746f762c7125c4b2541ed58c11dcf 100644 (file)
@@ -11,7 +11,7 @@ import org.eclipse.linuxtools.ctf.core.trace.CTFReaderException;
 import org.eclipse.linuxtools.ctf.core.trace.Stream;
 import org.eclipse.linuxtools.ctf.core.trace.StreamInput;
 import org.eclipse.linuxtools.ctf.core.trace.StreamInputReader;
-import org.eclipse.linuxtools.ctf.core.trace.StreamInputReaderComparator;
+import org.eclipse.linuxtools.internal.ctf.core.trace.StreamInputReaderComparator;
 import org.junit.*;
 
 /**
index adb35a2d416bf7c4fb1157c66edc4ac234f57b0f..d995e26992da2572778758481f872342ca1097bd 100644 (file)
@@ -8,7 +8,6 @@ import java.nio.ByteBuffer;
 import java.nio.ByteOrder;
 
 import org.eclipse.linuxtools.ctf.core.event.EventDefinition;
-import org.eclipse.linuxtools.ctf.core.event.io.BitBuffer;
 import org.eclipse.linuxtools.ctf.core.event.types.ArrayDeclaration;
 import org.eclipse.linuxtools.ctf.core.event.types.ArrayDefinition;
 import org.eclipse.linuxtools.ctf.core.event.types.Definition;
@@ -23,6 +22,7 @@ import org.eclipse.linuxtools.ctf.core.tests.TestParams;
 import org.eclipse.linuxtools.ctf.core.trace.CTFReaderException;
 import org.eclipse.linuxtools.ctf.core.trace.CTFTrace;
 import org.eclipse.linuxtools.ctf.core.trace.CTFTraceReader;
+import org.eclipse.linuxtools.internal.ctf.core.event.io.BitBuffer;
 import org.junit.After;
 import org.junit.Before;
 import org.junit.Test;
index 56af49da16ccd9a03d3feed7d2e68327faae095c..7e172082f988b5a9b30e95bd9e01a79593498f49 100644 (file)
@@ -2,9 +2,9 @@ package org.eclipse.linuxtools.ctf.core.tests.types;
 
 import static org.junit.Assert.assertNotNull;
 
-import org.eclipse.linuxtools.ctf.core.event.io.BitBuffer;
 import org.eclipse.linuxtools.ctf.core.event.types.Definition;
 import org.eclipse.linuxtools.ctf.core.event.types.IDefinitionScope;
+import org.eclipse.linuxtools.internal.ctf.core.event.io.BitBuffer;
 import org.junit.After;
 import org.junit.Before;
 import org.junit.Test;
index 9fdb60e0570721bcbf231cac88e8d4176eb7aa39..15c827c1dbb29f3b7fe1218a14e307aeaa4538c2 100644 (file)
@@ -7,11 +7,11 @@ import static org.junit.Assert.assertTrue;
 import java.nio.ByteBuffer;
 import java.nio.ByteOrder;
 
-import org.eclipse.linuxtools.ctf.core.event.io.BitBuffer;
 import org.eclipse.linuxtools.ctf.core.event.types.Encoding;
 import org.eclipse.linuxtools.ctf.core.event.types.EnumDeclaration;
 import org.eclipse.linuxtools.ctf.core.event.types.EnumDefinition;
 import org.eclipse.linuxtools.ctf.core.event.types.IntegerDeclaration;
+import org.eclipse.linuxtools.internal.ctf.core.event.io.BitBuffer;
 import org.junit.After;
 import org.junit.Before;
 import org.junit.Test;
index a06be0ca6377cc56a55ebb31bfba2af202b5943b..1d6a8eb83f292ea104b16f8be3085d6f67d7bce0 100644 (file)
@@ -6,7 +6,6 @@ import static org.junit.Assert.assertNotNull;
 import java.nio.ByteOrder;
 
 import org.eclipse.linuxtools.ctf.core.event.EventDefinition;
-import org.eclipse.linuxtools.ctf.core.event.io.BitBuffer;
 import org.eclipse.linuxtools.ctf.core.event.types.Definition;
 import org.eclipse.linuxtools.ctf.core.event.types.Encoding;
 import org.eclipse.linuxtools.ctf.core.event.types.IDefinitionScope;
@@ -17,6 +16,7 @@ import org.eclipse.linuxtools.ctf.core.tests.TestParams;
 import org.eclipse.linuxtools.ctf.core.trace.CTFReaderException;
 import org.eclipse.linuxtools.ctf.core.trace.CTFTrace;
 import org.eclipse.linuxtools.ctf.core.trace.CTFTraceReader;
+import org.eclipse.linuxtools.internal.ctf.core.event.io.BitBuffer;
 import org.junit.After;
 import org.junit.Before;
 import org.junit.Test;
index 0ca0e137038879e92923a867f4939128d1249f5b..11745a81f1ec0403824928fe0bd7852b05c18ec4 100644 (file)
@@ -6,7 +6,6 @@ import static org.junit.Assert.assertTrue;
 
 import java.nio.ByteOrder;
 
-import org.eclipse.linuxtools.ctf.core.event.io.BitBuffer;
 import org.eclipse.linuxtools.ctf.core.event.types.Definition;
 import org.eclipse.linuxtools.ctf.core.event.types.Encoding;
 import org.eclipse.linuxtools.ctf.core.event.types.IntegerDeclaration;
@@ -15,6 +14,7 @@ import org.eclipse.linuxtools.ctf.core.event.types.SequenceDefinition;
 import org.eclipse.linuxtools.ctf.core.event.types.StructDeclaration;
 import org.eclipse.linuxtools.ctf.core.event.types.StructDefinition;
 import org.eclipse.linuxtools.ctf.core.trace.CTFReaderException;
+import org.eclipse.linuxtools.internal.ctf.core.event.io.BitBuffer;
 import org.junit.After;
 import org.junit.Before;
 import org.junit.Test;
index a80df32b7244703efd08e7163fc295b5be1f7e15..fbfd03b3e15f598c84f6eb7b788f9ce3b67db310 100644 (file)
@@ -3,7 +3,6 @@ package org.eclipse.linuxtools.ctf.core.tests.types;
 import static org.junit.Assert.assertNotNull;
 
 import org.eclipse.linuxtools.ctf.core.event.EventDefinition;
-import org.eclipse.linuxtools.ctf.core.event.io.BitBuffer;
 import org.eclipse.linuxtools.ctf.core.event.types.Definition;
 import org.eclipse.linuxtools.ctf.core.event.types.IDefinitionScope;
 import org.eclipse.linuxtools.ctf.core.event.types.StringDeclaration;
@@ -13,6 +12,7 @@ import org.eclipse.linuxtools.ctf.core.tests.TestParams;
 import org.eclipse.linuxtools.ctf.core.trace.CTFReaderException;
 import org.eclipse.linuxtools.ctf.core.trace.CTFTrace;
 import org.eclipse.linuxtools.ctf.core.trace.CTFTraceReader;
+import org.eclipse.linuxtools.internal.ctf.core.event.io.BitBuffer;
 
 import org.junit.After;
 import org.junit.Before;
index 0d4bce83f3660d7a26dc4fb12554bfa17e71395a..136581c120718ad60e8bc4129818dbf9e4a8efdc 100644 (file)
@@ -7,7 +7,6 @@ import java.nio.ByteBuffer;
 import java.util.HashMap;
 
 import org.eclipse.linuxtools.ctf.core.event.EventDefinition;
-import org.eclipse.linuxtools.ctf.core.event.io.BitBuffer;
 import org.eclipse.linuxtools.ctf.core.event.types.ArrayDefinition;
 import org.eclipse.linuxtools.ctf.core.event.types.Definition;
 import org.eclipse.linuxtools.ctf.core.event.types.EnumDefinition;
@@ -21,6 +20,7 @@ import org.eclipse.linuxtools.ctf.core.tests.TestParams;
 import org.eclipse.linuxtools.ctf.core.trace.CTFReaderException;
 import org.eclipse.linuxtools.ctf.core.trace.CTFTrace;
 import org.eclipse.linuxtools.ctf.core.trace.CTFTraceReader;
+import org.eclipse.linuxtools.internal.ctf.core.event.io.BitBuffer;
 
 import org.junit.After;
 import org.junit.Before;
index 1bd574c12a980f78115ad8720950e1cd4eafeab1..bc67bb984e6099d31e3a9ea4cffffb1b51ddef51 100644 (file)
@@ -12,7 +12,6 @@ Require-Bundle: org.eclipse.core.runtime;bundle-version="3.7.0",
  org.antlr.runtime;bundle-version="3.2.0",
  org.eclipse.linuxtools.ctf.parser;bundle-version="0.1.0"
 Export-Package: org.eclipse.linuxtools.ctf.core.event,
- org.eclipse.linuxtools.ctf.core.event.io,
  org.eclipse.linuxtools.ctf.core.event.metadata,
  org.eclipse.linuxtools.ctf.core.event.metadata.exceptions,
  org.eclipse.linuxtools.ctf.core.event.types,
diff --git a/org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/ctf/core/event/io/BitBuffer.java b/org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/ctf/core/event/io/BitBuffer.java
deleted file mode 100644 (file)
index 64dc466..0000000
+++ /dev/null
@@ -1,510 +0,0 @@
-/*******************************************************************************.
- * Copyright (c) 2011-2012 Ericsson, Ecole Polytechnique de Montreal and others
- *
- * All rights reserved. This program and the accompanying materials are made
- * available under the terms of the Eclipse Public License v1.0 which
- * accompanies this distribution, and is available at
- * http://www.eclipse.org/legal/epl-v10.html
- *
- * Contributors: Matthew Khouzam - Initial Design and implementation
- * Contributors: Francis Giraldeau - Initial API and implementation
- *******************************************************************************/
-
-package org.eclipse.linuxtools.ctf.core.event.io;
-
-import java.nio.BufferOverflowException;
-import java.nio.ByteBuffer;
-import java.nio.ByteOrder;
-
-/**
- * <b><u>BitBuffer</u></b>
- * <p>
- * TODO Implement me. Please.
- */
-public class BitBuffer {
-
-    // ------------------------------------------------------------------------
-    // Constants
-    // ------------------------------------------------------------------------
-
-    /* default bit width */
-    public static final int BIT_CHAR = 8;
-    public static final int BIT_SHORT = 16;
-    public static final int BIT_INT = 32;
-    public static final int BIT_FLOAT = 32;
-    public static final int BIT_LONG = 64;
-
-    // ------------------------------------------------------------------------
-    // Attributes
-    // ------------------------------------------------------------------------
-
-    private ByteBuffer buf;
-    private int pos;
-    private ByteOrder byteOrder;
-
-    // ------------------------------------------------------------------------
-    // Constructors
-    // ------------------------------------------------------------------------
-
-    public BitBuffer() {
-        this(null, ByteOrder.BIG_ENDIAN);
-    }
-
-    public BitBuffer(ByteBuffer buf) {
-        this(buf, ByteOrder.BIG_ENDIAN);
-    }
-
-    public BitBuffer(ByteBuffer buf, ByteOrder order) {
-        setByteBuffer(buf);
-        order(order);
-        position(0);
-    }
-
-    // ------------------------------------------------------------------------
-    // 'Get' operations on buffer
-    // ------------------------------------------------------------------------
-
-    /**
-     * Relative <i>get</i> method for reading 32-bit integer.
-     *
-     * Reads next four bytes from the current bit position according to current
-     * byte order.
-     *
-     * @return The int value read from the buffer
-     */
-    public int getInt() {
-        int val = getInt(BIT_INT, true);
-        pos += BIT_INT;
-        return val;
-    }
-
-    /**
-     * Relative <i>get</i> method for reading integer of <i>length</i> bits.
-     *
-     * Reads <i>length</i> bits starting at the current position. The result is
-     * signed extended if <i>signed</i> is true. The current position is
-     * increased of <i>length</i> bits.
-     *
-     * @param length
-     *            The length in bits of this integer
-     * @param signed
-     *            The sign extended flag
-     * @return The int value read from the buffer
-     */
-    public int getInt(int length, boolean signed) {
-        int val;
-        if (!canRead(pos, length)) {
-            throw new BufferOverflowException();
-        }
-        if (length == 0) {
-            val = 0;
-        }
-        if (byteOrder == ByteOrder.LITTLE_ENDIAN) {
-            val = getIntLE(pos, length, signed);
-        } else {
-            val = getIntBE(pos, length, signed);
-        }
-        pos += length;
-        return val;
-    }
-
-    /**
-     * Absolute <i>get</i> method for reading integer of <i>length</i> bits.
-     *
-     * Reads <i>length</i> bits starting from position <i>index</i>. The result
-     * is signed extended if <i>signed</i> is true. The current position is
-     * increased of <i>length</i> bits.
-     *
-     * @param index
-     *            The start index in bits
-     * @param length
-     *            The length in bits to read
-     * @param signed
-     *            The sign extended flag
-     * @return The int value read from the buffer
-     */
-    public int getInt(int index, int length, boolean signed) {
-        if (!canRead(index, length)) {
-            throw new BufferOverflowException();
-        }
-        if (length == 0) {
-            return 0;
-        }
-        if (byteOrder == ByteOrder.LITTLE_ENDIAN) {
-            return getIntLE(index, length, signed);
-        }
-        return getIntBE(index, length, signed);
-    }
-
-    private int getIntBE(int index, int length, boolean signed) {
-        assert ((length > 0) && (length <= BIT_INT));
-        int end = index + length;
-        int startByte = index / BIT_CHAR;
-        int endByte = (end + (BIT_CHAR - 1)) / BIT_CHAR;
-        int currByte, lshift, cshift, mask, cmask, cache;
-        int value = 0;
-
-        currByte = startByte;
-        cache = buf.get(currByte) & 0xFF;
-        boolean isNeg = (cache & (1 << (BIT_CHAR - (index % BIT_CHAR) - 1))) != 0;
-        if (signed && isNeg) {
-            value = ~0;
-        }
-        if (startByte == (endByte - 1)) {
-            cmask = cache >>> ((BIT_CHAR - (end % BIT_CHAR)) % BIT_CHAR);
-            if (((length) % BIT_CHAR) > 0) {
-                mask = ~((~0) << length);
-                cmask &= mask;
-            }
-            value <<= length;
-            value |= cmask;
-            return value;
-        }
-        cshift = index % BIT_CHAR;
-        if (cshift > 0) {
-            mask = ~((~0) << (BIT_CHAR - cshift));
-            cmask = cache & mask;
-            lshift = BIT_CHAR - cshift;
-            value <<= lshift;
-            value |= cmask;
-            // index += lshift;
-            currByte++;
-        }
-        for (; currByte < (endByte - 1); currByte++) {
-            value <<= BIT_CHAR;
-            value |= buf.get(currByte) & 0xFF;
-        }
-        lshift = end % BIT_CHAR;
-        if (lshift > 0) {
-            mask = ~((~0) << lshift);
-            cmask = buf.get(currByte) & 0xFF;
-            cmask >>>= BIT_CHAR - lshift;
-            cmask &= mask;
-            value <<= lshift;
-            value |= cmask;
-        } else {
-            value <<= BIT_CHAR;
-            value |= buf.get(currByte) & 0xFF;
-        }
-        return value;
-    }
-
-    private int getIntLE(int index, int length, boolean signed) {
-        assert ((length > 0) && (length <= BIT_INT));
-        int end = index + length;
-        int startByte = index / BIT_CHAR;
-        int endByte = (end + (BIT_CHAR - 1)) / BIT_CHAR;
-        int currByte, lshift, cshift, mask, cmask, cache, mod;
-        int value = 0;
-
-        currByte = endByte - 1;
-        cache = buf.get(currByte) & 0xFF;
-        mod = end % BIT_CHAR;
-        lshift = (mod > 0) ? mod : BIT_CHAR;
-        boolean isNeg = (cache & (1 << (lshift - 1))) != 0;
-        if (signed && isNeg) {
-            value = ~0;
-        }
-        if (startByte == (endByte - 1)) {
-            cmask = cache >>> (index % BIT_CHAR);
-            if (((length) % BIT_CHAR) > 0) {
-                mask = ~((~0) << length);
-                cmask &= mask;
-            }
-            value <<= length;
-            value |= cmask;
-            return value;
-        }
-        cshift = end % BIT_CHAR;
-        if (cshift > 0) {
-            mask = ~((~0) << cshift);
-            cmask = cache & mask;
-            value <<= cshift;
-            value |= cmask;
-            // end -= cshift;
-            currByte--;
-        }
-        for (; currByte >= (startByte + 1); currByte--) {
-            value <<= BIT_CHAR;
-            value |= buf.get(currByte) & 0xFF;
-        }
-        lshift = index % BIT_CHAR;
-        if (lshift > 0) {
-            mask = ~((~0) << (BIT_CHAR - lshift));
-            cmask = buf.get(currByte) & 0xFF;
-            cmask >>>= lshift;
-            cmask &= mask;
-            value <<= (BIT_CHAR - lshift);
-            value |= cmask;
-        } else {
-            value <<= BIT_CHAR;
-            value |= buf.get(currByte) & 0xFF;
-        }
-        return value;
-    }
-
-    // ------------------------------------------------------------------------
-    // 'Put' operations on buffer
-    // ------------------------------------------------------------------------
-
-    /**
-     * Relative <i>put</i> method to write signed 32-bit integer.
-     *
-     * Write four bytes starting from current bit position in the buffer
-     * according to the current byte order. The current position is increased of
-     * <i>length</i> bits.
-     *
-     * @param value
-     *            The int value to write
-     */
-    public void putInt(int value) {
-        putInt(BIT_INT, value);
-    }
-
-    /**
-     * Relative <i>put</i> method to write <i>length</i> bits integer.
-     *
-     * Writes <i>length</i> lower-order bits from the provided <i>value</i>,
-     * starting from current bit position in the buffer. Sequential bytes are
-     * written according to the current byte order. The sign bit is carried to
-     * the MSB if signed is true. The sign bit is included in <i>length</i>. The
-     * current position is increased of <i>length</i>.
-     *
-     * @param length
-     *            The number of bits to write
-     * @param value
-     *            The value to write
-     */
-    public void putInt(int length, int value) {
-        putInt(this.pos, length, value);
-    }
-
-    /**
-     * Absolute <i>put</i> method to write <i>length</i> bits integer.
-     *
-     * Writes <i>length</i> lower-order bits from the provided <i>value</i>,
-     * starting from <i>index</i> position in the buffer. Sequential bytes are
-     * written according to the current byte order. The sign bit is carried to
-     * the MSB if signed is true. The sign bit is included in <i>length</i>. The
-     * current position is increased of <i>length</i>.
-     *
-     * @param index
-     *            The start position to write the value
-     * @param value
-     *            The value to write
-     * @param length
-     *            The number of bits to write
-     */
-    public void putInt(int index, int length, int value) {
-        if (!canRead(index, length)) {
-            throw new BufferOverflowException();
-        }
-        if (length == 0) {
-            return;
-        }
-        if (byteOrder == ByteOrder.LITTLE_ENDIAN) {
-            putIntLE(index, length, value);
-        } else {
-            putIntBE(index, length, value);
-        }
-    }
-
-    private void putIntBE(int index, int length, int value) {
-        assert ((length > 0) && (length <= BIT_INT));
-        int end = index + length;
-        int startByte = index / BIT_CHAR;
-        int endByte = (end + (BIT_CHAR - 1)) / BIT_CHAR;
-        int currByte, lshift, cshift, mask, cmask;
-        int correctedValue = value;
-
-        /*
-         * mask v high bits. Works for unsigned and two complement signed
-         * numbers which value do not overflow on length bits.
-         */
-
-        if (length < BIT_INT) {
-            correctedValue &= ~(~0 << length);
-        }
-
-        /* sub byte */
-        if (startByte == (endByte - 1)) {
-            lshift = (BIT_CHAR - (end % BIT_CHAR)) % BIT_CHAR;
-            mask = ~((~0) << lshift);
-            if ((index % BIT_CHAR) > 0) {
-                mask |= (~(0)) << (BIT_CHAR - (index % BIT_CHAR));
-            }
-            cmask = correctedValue << lshift;
-            /*
-             * low bits are cleared because of lshift and high bits are already
-             * cleared
-             */
-            cmask &= ~mask;
-            int b = buf.get(startByte) & 0xFF;
-            buf.put(startByte, (byte) ((b & mask) | cmask));
-            return;
-        }
-
-        /* head byte contains MSB */
-        currByte = endByte - 1;
-        cshift = end % BIT_CHAR;
-        if (cshift > 0) {
-            lshift = BIT_CHAR - cshift;
-            mask = ~((~0) << lshift);
-            cmask = correctedValue << lshift;
-            cmask &= ~mask;
-            int b = buf.get(currByte) & 0xFF;
-            buf.put(currByte, (byte) ((b & mask) | cmask));
-            correctedValue >>>= cshift;
-            // end -= cshift;
-            currByte--;
-        }
-
-        /* middle byte(s) */
-        for (; currByte >= (startByte + 1); currByte--) {
-            buf.put(currByte, (byte) correctedValue);
-            correctedValue >>>= BIT_CHAR;
-        }
-        /* end byte contains LSB */
-        if ((index % BIT_CHAR) > 0) {
-            mask = (~0) << (BIT_CHAR - (index % BIT_CHAR));
-            cmask = correctedValue & ~mask;
-            int b = buf.get(currByte) & 0xFF;
-            buf.put(currByte, (byte) ((b & mask) | cmask));
-        } else {
-            buf.put(currByte, (byte) correctedValue);
-        }
-    }
-
-    private void putIntLE(int index, int length, int value) {
-        assert ((length > 0) && (length <= BIT_INT));
-        int end = index + length;
-        int startByte = index / BIT_CHAR;
-        int endByte = (end + (BIT_CHAR - 1)) / BIT_CHAR;
-        int currByte, lshift, cshift, mask, cmask;
-        int correctedValue = value;
-
-        /*
-         * mask v high bits. Works for unsigned and two complement signed
-         * numbers which value do not overflow on length bits.
-         */
-
-        if (length < BIT_INT) {
-            correctedValue &= ~(~0 << length);
-        }
-
-        /* sub byte */
-        if (startByte == (endByte - 1)) {
-            lshift = index % BIT_CHAR;
-            mask = ~((~0) << lshift);
-            if ((end % BIT_CHAR) > 0) {
-                mask |= (~(0)) << (end % BIT_CHAR);
-            }
-            cmask = correctedValue << lshift;
-            /*
-             * low bits are cleared because of lshift and high bits are already
-             * cleared
-             */
-            cmask &= ~mask;
-            int b = buf.get(startByte) & 0xFF;
-            buf.put(startByte, (byte) ((b & mask) | cmask));
-            return;
-        }
-
-        /* head byte */
-        currByte = startByte;
-        cshift = index % BIT_CHAR;
-        if (cshift > 0) {
-            mask = ~((~0) << cshift);
-            cmask = correctedValue << cshift;
-            cmask &= ~mask;
-            int b = buf.get(currByte) & 0xFF;
-            buf.put(currByte, (byte) ((b & mask) | cmask));
-            correctedValue >>>= BIT_CHAR - cshift;
-            // index += BIT_CHAR - cshift;
-            currByte++;
-        }
-
-        /* middle byte(s) */
-        for (; currByte < (endByte - 1); currByte++) {
-            buf.put(currByte, (byte) correctedValue);
-            correctedValue >>>= BIT_CHAR;
-        }
-        /* end byte */
-        if ((end % BIT_CHAR) > 0) {
-            mask = (~0) << (end % BIT_CHAR);
-            cmask = correctedValue & ~mask;
-            int b = buf.get(currByte) & 0xFF;
-            buf.put(currByte, (byte) ((b & mask) | cmask));
-        } else {
-            buf.put(currByte, (byte) correctedValue);
-        }
-    }
-
-    // ------------------------------------------------------------------------
-    // Buffer attributes handling
-    // ------------------------------------------------------------------------
-
-    public boolean canRead(int length) {
-        return canRead(pos, length);
-    }
-
-    public boolean canRead(int index, int length) {
-        if (buf == null) {
-            return false;
-        }
-
-        if ((index + length) > (buf.capacity() * BIT_CHAR)) {
-            return false;
-        }
-        return true;
-    }
-
-    public void order(ByteOrder order) {
-        this.byteOrder = order;
-        if (buf != null) {
-            buf.order(order);
-        }
-    }
-
-    public ByteOrder order() {
-        return byteOrder;
-    }
-
-    public void position(int newPosition) {
-        this.pos = newPosition;
-    }
-
-    public int position() {
-        return pos;
-    }
-
-    public void setByteBuffer(ByteBuffer buf) {
-        this.buf = buf;
-        if (buf != null) {
-            this.buf.order(byteOrder);
-        }
-        clear();
-    }
-
-    public ByteBuffer getByteBuffer() {
-        return buf;
-    }
-
-    public void setByteOrder(ByteOrder byteOrder) {
-        this.byteOrder = byteOrder;
-    }
-
-    public ByteOrder getByteOrder() {
-        return byteOrder;
-    }
-
-    public void clear() {
-        position(0);
-
-        if (buf == null) {
-            return;
-        }
-        buf.clear();
-    }
-
-}
diff --git a/org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/ctf/core/event/metadata/IOStructGen.java b/org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/ctf/core/event/metadata/IOStructGen.java
deleted file mode 100644 (file)
index 519f44d..0000000
+++ /dev/null
@@ -1,2723 +0,0 @@
-/*******************************************************************************
- * Copyright (c) 2011-2012 Ericsson, Ecole Polytechnique de Montreal and others
- *
- * All rights reserved. This program and the accompanying materials are made
- * available under the terms of the Eclipse Public License v1.0 which
- * accompanies this distribution, and is available at
- * http://www.eclipse.org/legal/epl-v10.html
- *
- * Contributors: Matthew Khouzam - Initial Design and Grammar
- * Contributors: Francis Giraldeau - Initial API and implementation
- *******************************************************************************/
-
-package org.eclipse.linuxtools.ctf.core.event.metadata;
-
-import java.io.FileNotFoundException;
-import java.io.IOException;
-import java.io.UnsupportedEncodingException;
-import java.nio.ByteOrder;
-import java.util.ArrayList;
-import java.util.Collections;
-import java.util.LinkedList;
-import java.util.List;
-import java.util.UUID;
-
-import org.antlr.runtime.tree.CommonTree;
-import org.eclipse.linuxtools.ctf.core.event.CTFClock;
-import org.eclipse.linuxtools.ctf.core.event.EventDeclaration;
-import org.eclipse.linuxtools.ctf.core.event.metadata.exceptions.ParseException;
-import org.eclipse.linuxtools.ctf.core.event.types.ArrayDeclaration;
-import org.eclipse.linuxtools.ctf.core.event.types.Encoding;
-import org.eclipse.linuxtools.ctf.core.event.types.EnumDeclaration;
-import org.eclipse.linuxtools.ctf.core.event.types.IDeclaration;
-import org.eclipse.linuxtools.ctf.core.event.types.IntegerDeclaration;
-import org.eclipse.linuxtools.ctf.core.event.types.SequenceDeclaration;
-import org.eclipse.linuxtools.ctf.core.event.types.StringDeclaration;
-import org.eclipse.linuxtools.ctf.core.event.types.StructDeclaration;
-import org.eclipse.linuxtools.ctf.core.event.types.VariantDeclaration;
-import org.eclipse.linuxtools.ctf.core.trace.CTFTrace;
-import org.eclipse.linuxtools.ctf.core.trace.Stream;
-import org.eclipse.linuxtools.ctf.parser.CTFParser;
-import org.eclipse.linuxtools.internal.ctf.core.Activator;
-
-/*
- * Asserts throughout this class denote the assumptions we can make because of
- * the way the grammar generates the AST.
- *
- * There is also an assert at the beginning of each function that receives a
- * tree node to make sure that the node is indeed of the type the function is
- * expecting.
- */
-/*
- * Suppress unchecked warnings for things like List<CommonTree> children =
- * root.getChildren(), because ANTLR doesn't know what generics are.
- */
-/**
- * <b><u>IOStructGen</u></b>
- */
-@SuppressWarnings("unchecked")
-public class IOStructGen {
-
-    // ------------------------------------------------------------------------
-    // Attributes
-    // ------------------------------------------------------------------------
-
-    static private final boolean DEBUG_ = false;
-
-    /**
-     * The trace
-     */
-    private final CTFTrace trace;
-    private final CommonTree tree;
-
-    /**
-     * The current declaration scope.
-     */
-    private DeclarationScope scope = null;
-
-    // ------------------------------------------------------------------------
-    // Constructor
-    // ------------------------------------------------------------------------
-
-    public IOStructGen(CommonTree tree, CTFTrace trace) {
-        this.trace = trace;
-        this.tree = tree;
-    }
-
-    public void generate() throws ParseException {
-        parseRoot(tree);
-    }
-
-    // ------------------------------------------------------------------------
-    // Operations
-    // ------------------------------------------------------------------------
-
-    /**
-     * Parse the root node.
-     *
-     * @param root
-     *            A ROOT node.
-     * @throws ParseException
-     */
-    private void parseRoot(CommonTree root) throws ParseException {
-        assert (root.getType() == CTFParser.ROOT);
-
-        List<CommonTree> children = root.getChildren();
-        assert (children != null);
-        java.io.FileOutputStream fos = null;
-        java.io.OutputStreamWriter out = null;
-        if (DEBUG_) {
-            try {
-                fos = new java.io.FileOutputStream("/tmp/astInfo.txt"); //$NON-NLS-1$
-                out = new java.io.OutputStreamWriter(fos, "UTF-8"); //$NON-NLS-1$
-            } catch (FileNotFoundException e) {
-                e.printStackTrace();
-                return;
-            } catch (UnsupportedEncodingException e) {
-                e.printStackTrace();
-                return;
-            }
-        }
-
-        CommonTree traceNode = null;
-        List<CommonTree> streams = new ArrayList<CommonTree>();
-        List<CommonTree> events = new ArrayList<CommonTree>();
-        List<CommonTree> declarations = new ArrayList<CommonTree>();
-        List<CommonTree> environments = new ArrayList<CommonTree>();
-        List<CommonTree> clocks = new ArrayList<CommonTree>();
-        /* Create a new declaration scope with no parent. */
-        pushScope();
-
-        try {
-            for (CommonTree child : children) {
-                if (DEBUG_) {
-                    out.write(child.toString()
-                            + " -> " + child.getType() + '\n'); //$NON-NLS-1$
-                }
-                switch (child.getType()) {
-                case CTFParser.DECLARATION:
-                    declarations.add(child);
-                    break;
-                case CTFParser.TRACE:
-                    if (traceNode != null) {
-                        throw new ParseException(
-                                "Only one trace block is allowed"); //$NON-NLS-1$
-                    }
-                    traceNode = child;
-                    break;
-                case CTFParser.STREAM:
-                    streams.add(child);
-                    break;
-                case CTFParser.EVENT:
-                    events.add(child);
-                    break;
-                case CTFParser.CLOCK:
-                    clocks.add(child);
-                    break;
-                case CTFParser.ENV:
-                    environments.add(child);
-                    break;
-                default:
-                    childTypeError(child);
-                }
-            }
-
-            if (DEBUG_) {
-                out.write("Environments\n"); //$NON-NLS-1$
-            }
-            for (CommonTree environment : environments) {
-                parseEnvironment(environment);
-            }
-            if (DEBUG_) {
-                out.write("Clocks\n"); //$NON-NLS-1$
-            }
-            for (CommonTree clock : clocks) {
-                parseClock(clock);
-            }
-            if (DEBUG_) {
-                out.write("Declarations\n"); //$NON-NLS-1$
-            }
-            for (CommonTree decl : declarations) {
-                if (DEBUG_) {
-                    out.write(decl.toString() + '\n');
-                }
-                parseRootDeclaration(decl);
-            }
-
-            if (traceNode == null) {
-                throw new ParseException("Missing trace block"); //$NON-NLS-1$
-            }
-
-            parseTrace(traceNode);
-
-            if (DEBUG_) {
-                out.write("Streams\n"); //$NON-NLS-1$
-            }
-            if (streams.size() > 0) {
-                for (CommonTree stream : streams) {
-                    if (DEBUG_) {
-                        try {
-                            out.write(stream.toString() + '\n');
-                        } catch (IOException e) {
-                            e.printStackTrace();
-                        }
-                    }
-                    parseStream(stream);
-                }
-            } else {
-                /* Add an empty stream that will have a null id */
-                trace.addStream(new Stream(trace));
-            }
-
-            if (DEBUG_) {
-                out.write("Events\n"); //$NON-NLS-1$
-            }
-            for (CommonTree event : events) {
-                parseEvent(event);
-                CommonTree name = (CommonTree) event.getChild(0).getChild(1)
-                        .getChild(0).getChild(0);
-                if (DEBUG_) {
-                    out.write("Name = " + name); //$NON-NLS-1$
-                }
-                CommonTree id = (CommonTree) event.getChild(1).getChild(1)
-                        .getChild(0).getChild(0);
-                if (DEBUG_) {
-                    out.write("Name = " + name + " Id = " + id + '\n'); //$NON-NLS-1$ //$NON-NLS-2$
-                }
-            }
-
-            if (DEBUG_) {
-                out.close();
-                fos.close();
-            }
-        } catch (IOException e) {
-            e.printStackTrace();
-        }
-        popScope();
-    }
-
-    private void parseEnvironment(CommonTree environment) {
-        List<CommonTree> children = environment.getChildren();
-        for (CommonTree child : children) {
-            String left;
-            String right;
-            left = child.getChild(0).getChild(0).getChild(0).getText();
-            right = child.getChild(1).getChild(0).getChild(0).getText();
-            trace.addEnvironmentVar(left, right);
-        }
-    }
-
-    private void parseClock(CommonTree clock) {
-        List<CommonTree> children = clock.getChildren();
-        CTFClock ctfClock = new CTFClock();
-        for (CommonTree child : children) {
-            final String key = child.getChild(0).getChild(0).getChild(0)
-                    .getText();
-            final CommonTree value = (CommonTree) child.getChild(1).getChild(0).getChild(0);
-            final int type = value.getType();
-            switch (type) {
-            case CTFParser.INTEGER:
-            case CTFParser.DECIMAL_LITERAL:
-                /*
-                 * Not a pretty hack, this is to make sure that there is no number
-                 * overflow due to 63 bit integers. The offset should only really
-                 * be an issue in the year 2262. the tracer in C/ASM can write an offset in
-                 * an unsigned 64 bit long. In java, the last bit, being set to 1 will
-                 * be read as a negative number, but since it is too big a positive it will
-                 * throw an exception. this will happen in 2^63 ns from 1970.
-                 * Therefore 293 years from 1970
-                 */
-                Long numValue;
-                try{
-                    numValue = Long.parseLong(value.getText());
-                }
-                catch( Exception e)
-                {
-                    numValue = 1330938566783103277L;
-                }
-                ctfClock.addAttribute(key, numValue);
-                break;
-            default:
-                ctfClock.addAttribute(key, value.getText());
-            }
-
-        }
-        String NameValue = ctfClock.getName();
-        trace.addClock(NameValue, ctfClock);
-    }
-
-    private void parseTrace(CommonTree traceNode) throws ParseException {
-        assert (traceNode.getType() == CTFParser.TRACE);
-
-        List<CommonTree> children = traceNode.getChildren();
-        if (children == null) {
-            throw new ParseException("Trace block is empty"); //$NON-NLS-1$
-        }
-
-        pushScope();
-
-        for (CommonTree child : children) {
-            switch (child.getType()) {
-            case CTFParser.TYPEALIAS:
-                parseTypealias(child);
-                break;
-            case CTFParser.TYPEDEF:
-                parseTypedef(child);
-                break;
-            case CTFParser.CTF_EXPRESSION_TYPE:
-            case CTFParser.CTF_EXPRESSION_VAL:
-                parseTraceDeclaration(child);
-                break;
-            default:
-                childTypeError(child);
-                break;
-            }
-        }
-
-        /*
-         * If trace byte order was not specified and not using packet based
-         * metadata
-         */
-        if (trace.getByteOrder() == null) {
-            throw new ParseException("Trace byte order not set"); //$NON-NLS-1$
-        }
-
-        popScope();
-    }
-
-    private void parseTraceDeclaration(CommonTree traceDecl)
-            throws ParseException {
-        assert ((traceDecl.getType() == CTFParser.CTF_EXPRESSION_TYPE) || (traceDecl
-                .getType() == CTFParser.CTF_EXPRESSION_VAL));
-
-        /* There should be a left and right */
-        assert (traceDecl.getChildCount() == 2);
-
-        CommonTree leftNode = (CommonTree) traceDecl.getChild(0);
-        assert (leftNode.getType() == CTFParser.CTF_LEFT);
-        CommonTree rightNode = (CommonTree) traceDecl.getChild(1);
-        assert (rightNode.getType() == CTFParser.CTF_RIGHT);
-
-        List<CommonTree> leftStrings = leftNode.getChildren();
-        assert (leftStrings != null);
-
-        if (!isUnaryString(leftStrings.get(0))) {
-            throw new ParseException(
-                    "Left side of CTF assignment must be a string"); //$NON-NLS-1$
-        }
-
-        String left = concatenateUnaryStrings(leftStrings);
-
-        if (left.equals("major")) { //$NON-NLS-1$
-            if (trace.majortIsSet()) {
-                throw new ParseException("major is already set"); //$NON-NLS-1$
-            }
-
-            trace.setMajor(getMajorOrMinor(rightNode));
-        } else if (left.equals("minor")) { //$NON-NLS-1$
-            if (trace.minorIsSet()) {
-                throw new ParseException("minor is already set"); //$NON-NLS-1$
-            }
-
-            trace.setMinor(getMajorOrMinor(rightNode));
-        } else if (left.equals("uuid")) { //$NON-NLS-1$
-            UUID uuid = getUUID(rightNode);
-
-            /*
-             * If uuid was already set by a metadata packet, compare it to see
-             * if it matches
-             */
-            if (trace.UUIDIsSet()) {
-                if (trace.getUUID().compareTo(uuid) != 0) {
-                    throw new ParseException("UUID mismatch. Packet says " //$NON-NLS-1$
-                            + trace.getUUID() + " but metadata says " + uuid); //$NON-NLS-1$
-                }
-            } else {
-                trace.setUUID(uuid);
-            }
-
-        } else if (left.equals("byte_order")) { //$NON-NLS-1$
-            ByteOrder byteOrder = getByteOrder(rightNode);
-
-            /*
-             * If byte order was already set by a metadata packet, compare it to
-             * see if it matches
-             */
-            if (trace.getByteOrder() != null) {
-                if (trace.getByteOrder() != byteOrder) {
-                    throw new ParseException(
-                            "Endianness mismatch. Magic number says " //$NON-NLS-1$
-                                    + trace.getByteOrder()
-                                    + " but metadata says " + byteOrder); //$NON-NLS-1$
-                }
-            } else {
-                trace.setByteOrder(byteOrder);
-            }
-        } else if (left.equals("packet.header")) { //$NON-NLS-1$
-            if (trace.packetHeaderIsSet()) {
-                throw new ParseException("packet.header already defined"); //$NON-NLS-1$
-            }
-
-            CommonTree typeSpecifier = (CommonTree) rightNode.getChild(0);
-
-            if (typeSpecifier.getType() != CTFParser.TYPE_SPECIFIER_LIST) {
-                throw new ParseException(
-                        "packet.header expects a type specifier"); //$NON-NLS-1$
-            }
-
-            IDeclaration packetHeaderDecl = parseTypeSpecifierList(
-                    typeSpecifier, null);
-
-            if (!(packetHeaderDecl instanceof StructDeclaration)) {
-                throw new ParseException("packet.header expects a struct"); //$NON-NLS-1$
-            }
-
-            trace.setPacketHeader((StructDeclaration) packetHeaderDecl);
-        } else {
-            throw new ParseException("Unknown trace attribute : " + left); //$NON-NLS-1$
-        }
-    }
-
-    private void parseStream(CommonTree streamNode) throws ParseException {
-        assert (streamNode.getType() == CTFParser.STREAM);
-
-        Stream stream = new Stream(trace);
-
-        List<CommonTree> children = streamNode.getChildren();
-        if (children == null) {
-            throw new ParseException("Empty stream block"); //$NON-NLS-1$
-        }
-
-        pushScope();
-
-        for (CommonTree child : children) {
-            switch (child.getType()) {
-            case CTFParser.TYPEALIAS:
-                parseTypealias(child);
-                break;
-            case CTFParser.TYPEDEF:
-                parseTypedef(child);
-                break;
-            case CTFParser.CTF_EXPRESSION_TYPE:
-            case CTFParser.CTF_EXPRESSION_VAL:
-                parseStreamDeclaration(child, stream);
-                break;
-            default:
-                childTypeError(child);
-                break;
-            }
-        }
-
-        if (stream.idIsSet()) {
-            if (!trace.packetHeaderIsSet()
-                    || !trace.getPacketHeader().hasField("stream_id")) { //$NON-NLS-1$
-                throw new ParseException(
-                        "Stream has an ID, but there is no stream_id field in packet header."); //$NON-NLS-1$
-            }
-        }
-
-        trace.addStream(stream);
-
-        popScope();
-    }
-
-    private void parseStreamDeclaration(CommonTree streamDecl, Stream stream)
-            throws ParseException {
-        assert ((streamDecl.getType() == CTFParser.CTF_EXPRESSION_TYPE) || (streamDecl
-                .getType() == CTFParser.CTF_EXPRESSION_VAL));
-
-        /* There should be a left and right */
-        assert (streamDecl.getChildCount() == 2);
-
-        CommonTree leftNode = (CommonTree) streamDecl.getChild(0);
-        assert (leftNode.getType() == CTFParser.CTF_LEFT);
-        CommonTree rightNode = (CommonTree) streamDecl.getChild(1);
-        assert (rightNode.getType() == CTFParser.CTF_RIGHT);
-
-        List<CommonTree> leftStrings = leftNode.getChildren();
-        assert (leftStrings != null);
-
-        if (!isUnaryString(leftStrings.get(0))) {
-            throw new ParseException(
-                    "Left side of CTF assignment must be a string"); //$NON-NLS-1$
-        }
-
-        String left = concatenateUnaryStrings(leftStrings);
-
-        if (left.equals("id")) { //$NON-NLS-1$
-            if (stream.idIsSet()) {
-                throw new ParseException("stream id already defined"); //$NON-NLS-1$
-            }
-
-            long streamID = getStreamID(rightNode);
-
-            stream.setId(streamID);
-        } else if (left.equals("event.header")) { //$NON-NLS-1$
-            if (stream.eventHeaderIsSet()) {
-                throw new ParseException("event.header already defined"); //$NON-NLS-1$
-            }
-
-            CommonTree typeSpecifier = (CommonTree) rightNode.getChild(0);
-
-            if (typeSpecifier.getType() != CTFParser.TYPE_SPECIFIER_LIST) {
-                throw new ParseException(
-                        "event.header expects a type specifier"); //$NON-NLS-1$
-            }
-
-            IDeclaration eventHeaderDecl = parseTypeSpecifierList(
-                    typeSpecifier, null);
-
-            if (!(eventHeaderDecl instanceof StructDeclaration)) {
-                throw new ParseException("event.header expects a struct"); //$NON-NLS-1$
-            }
-
-            stream.setEventHeader((StructDeclaration) eventHeaderDecl);
-        } else if (left.equals("event.context")) { //$NON-NLS-1$
-            if (stream.eventContextIsSet()) {
-                throw new ParseException("event.context already defined"); //$NON-NLS-1$
-            }
-
-            CommonTree typeSpecifier = (CommonTree) rightNode.getChild(0);
-
-            if (typeSpecifier.getType() != CTFParser.TYPE_SPECIFIER_LIST) {
-                throw new ParseException(
-                        "event.context expects a type specifier"); //$NON-NLS-1$
-            }
-
-            IDeclaration eventContextDecl = parseTypeSpecifierList(
-                    typeSpecifier, null);
-
-            if (!(eventContextDecl instanceof StructDeclaration)) {
-                throw new ParseException("event.context expects a struct"); //$NON-NLS-1$
-            }
-
-            stream.setEventContext((StructDeclaration) eventContextDecl);
-        } else if (left.equals("packet.context")) { //$NON-NLS-1$
-            if (stream.packetContextIsSet()) {
-                throw new ParseException("packet.context already defined"); //$NON-NLS-1$
-            }
-
-            CommonTree typeSpecifier = (CommonTree) rightNode.getChild(0);
-
-            if (typeSpecifier.getType() != CTFParser.TYPE_SPECIFIER_LIST) {
-                throw new ParseException(
-                        "packet.context expects a type specifier"); //$NON-NLS-1$
-            }
-
-            IDeclaration packetContextDecl = parseTypeSpecifierList(
-                    typeSpecifier, null);
-
-            if (!(packetContextDecl instanceof StructDeclaration)) {
-                throw new ParseException("packet.context expects a struct"); //$NON-NLS-1$
-            }
-
-            stream.setPacketContext((StructDeclaration) packetContextDecl);
-        } else {
-            throw new ParseException("Unknown stream attribute : " + left); //$NON-NLS-1$
-        }
-    }
-
-    private void parseEvent(CommonTree eventNode) throws ParseException {
-        assert (eventNode.getType() == CTFParser.EVENT);
-
-        List<CommonTree> children = eventNode.getChildren();
-        if (children == null) {
-            throw new ParseException("Empty event block"); //$NON-NLS-1$
-        }
-
-        EventDeclaration event = new EventDeclaration();
-
-        pushScope();
-
-        for (CommonTree child : children) {
-            switch (child.getType()) {
-            case CTFParser.TYPEALIAS:
-                parseTypealias(child);
-                break;
-            case CTFParser.TYPEDEF:
-                parseTypedef(child);
-                break;
-            case CTFParser.CTF_EXPRESSION_TYPE:
-            case CTFParser.CTF_EXPRESSION_VAL:
-                parseEventDeclaration(child, event);
-                break;
-            default:
-                childTypeError(child);
-                break;
-            }
-        }
-
-        if (!event.nameIsSet()) {
-            throw new ParseException("Event name not set"); //$NON-NLS-1$
-        }
-
-        /*
-         * If the event did not specify a stream, then the trace must be single
-         * stream
-         */
-        if (!event.streamIsSet()) {
-            if (trace.nbStreams() > 1) {
-                throw new ParseException(
-                        "Event without stream_id with more than one stream"); //$NON-NLS-1$
-            }
-
-            /*
-             * If the event did not specify a stream, the only existing stream
-             * must not have an id. Note: That behavior could be changed, it
-             * could be possible to just get the only existing stream, whatever
-             * is its id.
-             */
-            Stream stream = trace.getStream(null);
-
-            if (stream != null) {
-                event.setStream(stream);
-            } else {
-                throw new ParseException(
-                        "Event without stream_id, but there is no stream without id"); //$NON-NLS-1$
-            }
-        }
-
-        /*
-         * Add the event to the stream.
-         */
-        event.getStream().addEvent(event);
-
-        popScope();
-    }
-
-    private void parseEventDeclaration(CommonTree eventDecl,
-            EventDeclaration event) throws ParseException {
-        assert ((eventDecl.getType() == CTFParser.CTF_EXPRESSION_TYPE) || (eventDecl
-                .getType() == CTFParser.CTF_EXPRESSION_VAL));
-
-        /* There should be a left and right */
-        assert (eventDecl.getChildCount() == 2);
-
-        CommonTree leftNode = (CommonTree) eventDecl.getChild(0);
-        assert (leftNode.getType() == CTFParser.CTF_LEFT);
-        CommonTree rightNode = (CommonTree) eventDecl.getChild(1);
-        assert (rightNode.getType() == CTFParser.CTF_RIGHT);
-
-        List<CommonTree> leftStrings = leftNode.getChildren();
-        assert (leftStrings != null);
-
-        if (!isUnaryString(leftStrings.get(0))) {
-            throw new ParseException(
-                    "Left side of CTF assignment must be a string"); //$NON-NLS-1$
-        }
-
-        String left = concatenateUnaryStrings(leftStrings);
-
-        if (left.equals("name")) { //$NON-NLS-1$
-            if (event.nameIsSet()) {
-                throw new ParseException("name already defined"); //$NON-NLS-1$
-            }
-
-            String name = getEventName(rightNode);
-
-            event.setName(name);
-        } else if (left.equals("id")) { //$NON-NLS-1$
-            if (event.idIsSet()) {
-                throw new ParseException("id already defined"); //$NON-NLS-1$
-            }
-
-            long id = getEventID(rightNode);
-
-            event.setId(id);
-        } else if (left.equals("stream_id")) { //$NON-NLS-1$
-            if (event.streamIsSet()) {
-                throw new ParseException("stream id already defined"); //$NON-NLS-1$
-            }
-
-            long streamId = getStreamID(rightNode);
-
-            Stream stream = trace.getStream(streamId);
-
-            if (stream == null) {
-                throw new ParseException("Stream " + streamId + " not found"); //$NON-NLS-1$ //$NON-NLS-2$
-            }
-
-            event.setStream(stream);
-        } else if (left.equals("context")) { //$NON-NLS-1$
-            if (event.contextIsSet()) {
-                throw new ParseException("context already defined"); //$NON-NLS-1$
-            }
-
-            CommonTree typeSpecifier = (CommonTree) rightNode.getChild(0);
-
-            if (typeSpecifier.getType() != CTFParser.TYPE_SPECIFIER_LIST) {
-                throw new ParseException("context expects a type specifier"); //$NON-NLS-1$
-            }
-
-            IDeclaration contextDecl = parseTypeSpecifierList(typeSpecifier,
-                    null);
-
-            if (!(contextDecl instanceof StructDeclaration)) {
-                throw new ParseException("context expects a struct"); //$NON-NLS-1$
-            }
-
-            event.setContext((StructDeclaration) contextDecl);
-        } else if (left.equals("fields")) { //$NON-NLS-1$
-            if (event.fieldsIsSet()) {
-                throw new ParseException("fields already defined"); //$NON-NLS-1$
-            }
-
-            CommonTree typeSpecifier = (CommonTree) rightNode.getChild(0);
-
-            if (typeSpecifier.getType() != CTFParser.TYPE_SPECIFIER_LIST) {
-                throw new ParseException("fields expects a type specifier"); //$NON-NLS-1$
-            }
-
-            IDeclaration fieldsDecl;
-            fieldsDecl = parseTypeSpecifierList(typeSpecifier, null);
-
-            if (!(fieldsDecl instanceof StructDeclaration)) {
-                throw new ParseException("fields expects a struct"); //$NON-NLS-1$
-            }
-            /*
-             * The underscores in the event names.
-             * These underscores were added by the LTTng tracer.
-             */
-            final StructDeclaration fields = (StructDeclaration) fieldsDecl;
-            event.setFields(fields);
-
-        } else {
-            throw new ParseException("Unknown event attribute : " + left); //$NON-NLS-1$
-        }
-    }
-
-    /**
-     * Parses a declaration at the root level.
-     *
-     * @param declaration
-     *            The declaration subtree.
-     * @throws ParseException
-     */
-    private void parseRootDeclaration(CommonTree declaration)
-            throws ParseException {
-        assert (declaration.getType() == CTFParser.DECLARATION);
-
-        List<CommonTree> children = declaration.getChildren();
-        assert (children != null);
-
-        for (CommonTree child : children) {
-            switch (child.getType()) {
-            case CTFParser.TYPEDEF:
-                parseTypedef(child);
-                break;
-            case CTFParser.TYPEALIAS:
-                parseTypealias(child);
-                break;
-            case CTFParser.TYPE_SPECIFIER_LIST:
-                parseTypeSpecifierList(child, null);
-                break;
-            default:
-                childTypeError(child);
-            }
-        }
-    }
-
-    /**
-     * Parses a typealias node. It parses the target, the alias, and registers
-     * the type in the current scope.
-     *
-     * @param typealias
-     *            A TYPEALIAS node.
-     * @throws ParseException
-     */
-    private void parseTypealias(CommonTree typealias) throws ParseException {
-        assert (typealias.getType() == CTFParser.TYPEALIAS);
-
-        List<CommonTree> children = typealias.getChildren();
-        assert (children != null);
-
-        CommonTree target = null;
-        CommonTree alias = null;
-
-        for (CommonTree child : children) {
-            switch (child.getType()) {
-            case CTFParser.TYPEALIAS_TARGET:
-                assert (target == null);
-                target = child;
-                break;
-            case CTFParser.TYPEALIAS_ALIAS:
-                assert (alias == null);
-                alias = child;
-                break;
-            default:
-                childTypeError(child);
-                break;
-            }
-        }
-
-        assert (target != null);
-        assert (alias != null);
-
-        IDeclaration targetDeclaration = parseTypealiasTarget(target);
-
-        if (targetDeclaration instanceof VariantDeclaration) {
-            if (((VariantDeclaration) targetDeclaration).isTagged()) {
-                throw new ParseException(
-                        "Typealias of untagged variant is not permitted"); //$NON-NLS-1$
-            }
-        }
-
-        String aliasString = parseTypealiasAlias(alias);
-
-        getCurrentScope().registerType(aliasString, targetDeclaration);
-    }
-
-    /**
-     * Parses the target part of a typealias and gets the corresponding
-     * declaration.
-     *
-     * @param target
-     *            A TYPEALIAS_TARGET node.
-     * @return The corresponding declaration.
-     * @throws ParseException
-     */
-    private IDeclaration parseTypealiasTarget(CommonTree target)
-            throws ParseException {
-        assert (target.getType() == CTFParser.TYPEALIAS_TARGET);
-
-        List<CommonTree> children = target.getChildren();
-        assert (children != null);
-
-        CommonTree typeSpecifierList = null;
-        CommonTree typeDeclaratorList = null;
-        CommonTree typeDeclarator = null;
-        StringBuilder identifierSB = new StringBuilder();
-
-        for (CommonTree child : children) {
-            switch (child.getType()) {
-            case CTFParser.TYPE_SPECIFIER_LIST:
-                assert (typeSpecifierList == null);
-                typeSpecifierList = child;
-                break;
-            case CTFParser.TYPE_DECLARATOR_LIST:
-                assert (typeDeclaratorList == null);
-                typeDeclaratorList = child;
-                break;
-            default:
-                childTypeError(child);
-                break;
-            }
-        }
-
-        assert (typeSpecifierList != null);
-
-        if (typeDeclaratorList != null) {
-            /*
-             * Only allow one declarator
-             *
-             * eg: "typealias uint8_t *, ** := puint8_t;" is not permitted,
-             * otherwise the new type puint8_t would maps to two different
-             * types.
-             */
-            if (typeDeclaratorList.getChildCount() != 1) {
-                throw new ParseException(
-                        "Only one type declarator is allowed in the typealias target"); //$NON-NLS-1$
-            }
-
-            typeDeclarator = (CommonTree) typeDeclaratorList.getChild(0);
-        }
-
-        /* Parse the target type and get the declaration */
-        IDeclaration targetDeclaration = parseTypeDeclarator(typeDeclarator,
-                typeSpecifierList, identifierSB);
-
-        /*
-         * We don't allow identifier in the target
-         *
-         * eg: "typealias uint8_t* hello := puint8_t;", the "hello" is not
-         * permitted
-         */
-        if (identifierSB.length() > 0) {
-            throw new ParseException("Identifier (" + identifierSB.toString() //$NON-NLS-1$
-                    + ") not expected in the typealias target"); //$NON-NLS-1$
-        }
-
-        return targetDeclaration;
-    }
-
-    /**
-     * Parses the alias part of a typealias. It parses the underlying specifier
-     * list and declarator and creates the string representation that will be
-     * used to register the type.
-     *
-     * @param alias
-     *            A TYPEALIAS_ALIAS node.
-     * @return The string representation of the alias.
-     * @throws ParseException
-     */
-    private static String parseTypealiasAlias(CommonTree alias)
-            throws ParseException {
-        assert (alias.getType() == CTFParser.TYPEALIAS_ALIAS);
-
-        List<CommonTree> children = alias.getChildren();
-        assert (children != null);
-
-        CommonTree typeSpecifierList = null;
-        CommonTree typeDeclaratorList = null;
-        CommonTree typeDeclarator = null;
-        List<CommonTree> pointers = new LinkedList<CommonTree>();
-
-        for (CommonTree child : children) {
-            switch (child.getType()) {
-            case CTFParser.TYPE_SPECIFIER_LIST:
-                assert (typeSpecifierList == null);
-                typeSpecifierList = child;
-                break;
-            case CTFParser.TYPE_DECLARATOR_LIST:
-                assert (typeDeclaratorList == null);
-                typeDeclaratorList = child;
-                break;
-            default:
-                childTypeError(child);
-                break;
-            }
-        }
-
-        /* If there is a type declarator list, extract the pointers */
-        if (typeDeclaratorList != null) {
-            /*
-             * Only allow one declarator
-             *
-             * eg: "typealias uint8_t := puint8_t *, **;" is not permitted.
-             */
-            if (typeDeclaratorList.getChildCount() != 1) {
-                throw new ParseException(
-                        "Only one type declarator is allowed in the typealias alias"); //$NON-NLS-1$
-            }
-
-            typeDeclarator = (CommonTree) typeDeclaratorList.getChild(0);
-
-            List<CommonTree> typeDeclaratorChildren = typeDeclarator
-                    .getChildren();
-            assert (typeDeclaratorChildren != null);
-
-            for (CommonTree child : typeDeclaratorChildren) {
-                switch (child.getType()) {
-                case CTFParser.POINTER:
-                    pointers.add(child);
-                    break;
-                case CTFParser.IDENTIFIER:
-                    throw new ParseException("Identifier (" + child.getText() //$NON-NLS-1$
-                            + ") not expected in the typealias target"); //$NON-NLS-1$
-                    /* break; */
-                default:
-                    childTypeError(child);
-                    break;
-                }
-            }
-        }
-
-        return createTypeDeclarationString(typeSpecifierList, pointers);
-    }
-
-    /**
-     * Parses a typedef node. This creates and registers a new declaration for
-     * each declarator found in the typedef.
-     *
-     * @param typedef
-     *            A TYPEDEF node.
-     * @throws ParseException
-     *             If there is an error creating the declaration.
-     */
-    private void parseTypedef(CommonTree typedef) throws ParseException {
-        assert (typedef.getType() == CTFParser.TYPEDEF);
-
-        CommonTree typeDeclaratorListNode = (CommonTree) typedef
-                .getFirstChildWithType(CTFParser.TYPE_DECLARATOR_LIST);
-        assert (typeDeclaratorListNode != null);
-
-        CommonTree typeSpecifierListNode = (CommonTree) typedef
-                .getFirstChildWithType(CTFParser.TYPE_SPECIFIER_LIST);
-        assert (typeSpecifierListNode != null);
-
-        List<CommonTree> typeDeclaratorList = typeDeclaratorListNode
-                .getChildren();
-        assert (typeDeclaratorList != null);
-
-        for (CommonTree typeDeclaratorNode : typeDeclaratorList) {
-            StringBuilder identifierSB = new StringBuilder();
-
-            IDeclaration type_declaration = parseTypeDeclarator(
-                    typeDeclaratorNode, typeSpecifierListNode, identifierSB);
-
-            if (type_declaration instanceof VariantDeclaration) {
-                if (((VariantDeclaration) type_declaration).isTagged()) {
-                    throw new ParseException(
-                            "Typealias of untagged variant is not permitted"); //$NON-NLS-1$
-                }
-            }
-
-            getCurrentScope().registerType(identifierSB.toString(),
-                    type_declaration);
-        }
-    }
-
-    /**
-     * Parses a pair type declarator / type specifier list and returns the
-     * corresponding declaration. If it is present, it also writes the
-     * identifier of the declarator in the given {@link StringBuilder}.
-     *
-     * @param typeDeclarator
-     *            A TYPE_DECLARATOR node.
-     * @param typeSpecifierList
-     *            A TYPE_SPECIFIER_LIST node.
-     * @param identifierSB
-     *            A StringBuilder that will receive the identifier found in the
-     *            declarator.
-     * @return The corresponding declaration.
-     * @throws ParseException
-     *             If there is an error finding or creating the declaration.
-     */
-    private IDeclaration parseTypeDeclarator(CommonTree typeDeclarator,
-            CommonTree typeSpecifierList, StringBuilder identifierSB)
-            throws ParseException {
-        if (typeDeclarator != null) {
-            assert (typeDeclarator.getType() == CTFParser.TYPE_DECLARATOR);
-        }
-        assert (typeSpecifierList.getType() == CTFParser.TYPE_SPECIFIER_LIST);
-
-        IDeclaration declaration = null;
-        List<CommonTree> children = null;
-        List<CommonTree> pointers = new LinkedList<CommonTree>();
-        List<CommonTree> lengths = new LinkedList<CommonTree>();
-        CommonTree identifier = null;
-
-        /* Separate the tokens by type */
-        if (typeDeclarator != null) {
-            children = typeDeclarator.getChildren();
-            assert (children != null);
-            for (CommonTree child : children) {
-
-                switch (child.getType()) {
-                case CTFParser.POINTER:
-                    pointers.add(child);
-                    break;
-                case CTFParser.IDENTIFIER:
-                    assert (identifier == null);
-                    identifier = child;
-                    break;
-                case CTFParser.LENGTH:
-                    lengths.add(child);
-                    break;
-                default:
-                    childTypeError(child);
-                    break;
-                }
-            }
-
-        }
-
-        /*
-         * Parse the type specifier list, which is the "base" type. For example,
-         * it would be int in int a[3][len].
-         */
-        declaration = parseTypeSpecifierList(typeSpecifierList, pointers);
-
-        /*
-         * Each length subscript means that we must create a nested array or
-         * sequence. For example, int a[3][len] means that we have an array of 3
-         * (sequences of length 'len' of (int)).
-         */
-        if (lengths.size() > 0 ) {
-            /* We begin at the end */
-            Collections.reverse(lengths);
-
-            for (CommonTree length : lengths) {
-                /*
-                 * By looking at the first expression, we can determine whether
-                 * it is an array or a sequence.
-                 */
-                List<CommonTree> lengthChildren = length.getChildren();
-                assert (lengthChildren != null);
-
-                CommonTree first = lengthChildren.get(0);
-                if (isUnaryInteger(first)) {
-                    /* Array */
-                    int arrayLength = (int) parseUnaryInteger(first);
-
-                    if (arrayLength < 1) {
-                        throw new ParseException("Array length is negative"); //$NON-NLS-1$
-                    }
-
-                    /* Create the array declaration. */
-                    declaration = new ArrayDeclaration(arrayLength, declaration);
-                } else if (isUnaryString(first)) {
-                    /* Sequence */
-                    String lengthName = concatenateUnaryStrings(lengthChildren);
-
-                    /* Create the sequence declaration. */
-                    declaration = new SequenceDeclaration(lengthName,
-                            declaration);
-                } else {
-                    childTypeError(first);
-                }
-            }
-        }
-
-        if (identifier != null) {
-            identifierSB.append(identifier.getText());
-        }
-
-        return declaration;
-    }
-
-    /**
-     * Parses a type specifier list and returns the corresponding declaration.
-     *
-     * @param typeSpecifierList
-     *            A TYPE_SPECIFIER_LIST node.
-     * @param pointerList
-     *            A list of POINTER nodes that apply to the specified type.
-     * @return The corresponding declaration.
-     * @throws ParseException
-     *             If the type has not been defined or if there is an error
-     *             creating the declaration.
-     */
-    private IDeclaration parseTypeSpecifierList(CommonTree typeSpecifierList,
-            List<CommonTree> pointerList) throws ParseException {
-        assert (typeSpecifierList.getType() == CTFParser.TYPE_SPECIFIER_LIST);
-        IDeclaration declaration = null;
-
-        /*
-         * By looking at the first element of the type specifier list, we can
-         * determine which type it belongs to.
-         */
-        CommonTree firstChild = (CommonTree) typeSpecifierList.getChild(0);
-        assert (firstChild != null); /* grammar */
-
-        switch (firstChild.getType()) {
-        case CTFParser.FLOATING_POINT:
-            Activator
-                    .getDefault()
-                    .log("parseTypeSpecifierList: floating_point not implemented yet"); //$NON-NLS-1$
-            break;
-        case CTFParser.INTEGER:
-            declaration = parseInteger(firstChild);
-            break;
-        case CTFParser.STRING:
-            declaration = parseString(firstChild);
-            break;
-        case CTFParser.STRUCT:
-            declaration = parseStruct(firstChild);
-            break;
-        case CTFParser.VARIANT:
-            declaration = parseVariant(firstChild);
-            break;
-        case CTFParser.ENUM:
-            declaration = parseEnum(firstChild);
-            break;
-        case CTFParser.IDENTIFIER:
-        case CTFParser.FLOATTOK:
-        case CTFParser.INTTOK:
-        case CTFParser.LONGTOK:
-        case CTFParser.SHORTTOK:
-        case CTFParser.SIGNEDTOK:
-        case CTFParser.UNSIGNEDTOK:
-        case CTFParser.CHARTOK:
-        case CTFParser.DOUBLETOK:
-        case CTFParser.VOIDTOK:
-        case CTFParser.BOOLTOK:
-        case CTFParser.COMPLEXTOK:
-        case CTFParser.IMAGINARYTOK:
-            declaration = parseTypeDeclaration(typeSpecifierList, pointerList);
-            break;
-        default:
-            childTypeError(firstChild);
-        }
-
-        assert (declaration != null);
-        return declaration;
-    }
-
-    /**
-     * Parses a type specifier list as a user-declared type.
-     *
-     * @param typeSpecifierList
-     *            A TYPE_SPECIFIER_LIST node containing a user-declared type.
-     * @param pointerList
-     *            A list of POINTER nodes that apply to the type specified in
-     *            typeSpecifierList.
-     * @return The corresponding declaration.
-     * @throws ParseException
-     *             If the type does not exist (has not been found).
-     */
-    private IDeclaration parseTypeDeclaration(CommonTree typeSpecifierList,
-            List<CommonTree> pointerList) throws ParseException {
-        /* Create the string representation of the type declaration */
-        String typeStringRepresentation = createTypeDeclarationString(
-                typeSpecifierList, pointerList);
-
-        /* Use the string representation to search the type in the current scope */
-        IDeclaration decl = getCurrentScope().rlookupType(
-                typeStringRepresentation);
-
-        if (decl == null) {
-            throw new ParseException("Type " + typeStringRepresentation //$NON-NLS-1$
-                    + " has not been defined."); //$NON-NLS-1$
-        }
-
-        return decl;
-    }
-
-    /**
-     * Parses an integer declaration node.
-     *
-     * @param integer
-     *            An INTEGER node.
-     * @return The corresponding integer declaration.
-     * @throws ParseException
-     */
-    private IntegerDeclaration parseInteger(CommonTree integer)
-            throws ParseException {
-        assert (integer.getType() == CTFParser.INTEGER);
-
-        List<CommonTree> children = integer.getChildren();
-
-        /*
-         * If the integer has no attributes, then it is missing the size
-         * attribute which is required
-         */
-        if (children == null) {
-            throw new ParseException("integer: missing size attribute"); //$NON-NLS-1$
-        }
-
-        /* The return value */
-        IntegerDeclaration integerDeclaration = null;
-        boolean signed = false;
-        ByteOrder byteOrder = trace.getByteOrder();
-        long size = 0;
-        long alignment = 0;
-        int base = 10;
-        String clock = null;
-
-        Encoding encoding = Encoding.NONE;
-
-        /* Iterate on all integer children */
-        for (CommonTree child : children) {
-            switch (child.getType()) {
-            case CTFParser.CTF_EXPRESSION_VAL:
-                /*
-                 * An assignment expression must have 2 children, left and right
-                 */
-                assert (child.getChildCount() == 2);
-
-                CommonTree leftNode = (CommonTree) child.getChild(0);
-                assert (leftNode.getType() == CTFParser.CTF_LEFT);
-                CommonTree rightNode = (CommonTree) child.getChild(1);
-                assert (rightNode.getType() == CTFParser.CTF_RIGHT);
-
-                List<CommonTree> leftStrings = leftNode.getChildren();
-                assert (leftStrings != null);
-
-                if (!isUnaryString(leftStrings.get(0))) {
-                    throw new ParseException(
-                            "Left side of ctf expression must be a string"); //$NON-NLS-1$
-                }
-                String left = concatenateUnaryStrings(leftStrings);
-
-                if (left.equals("signed")) { //$NON-NLS-1$
-                    signed = getSigned(rightNode);
-                } else if (left.equals("byte_order")) { //$NON-NLS-1$
-                    byteOrder = getByteOrder(rightNode);
-                } else if (left.equals("size")) { //$NON-NLS-1$
-                    size = getSize(rightNode);
-                } else if (left.equals("align")) { //$NON-NLS-1$
-                    alignment = getAlignment(rightNode);
-                } else if (left.equals("base")) { //$NON-NLS-1$
-                    base = getBase(rightNode);
-                } else if (left.equals("encoding")) { //$NON-NLS-1$
-                    encoding = getEncoding(rightNode);
-                } else if (left.equals("map")) { //$NON-NLS-1$
-                    clock = getClock(rightNode);
-                } else {
-                    throw new ParseException("Integer: unknown attribute " + left); //$NON-NLS-1$
-                }
-
-                break;
-            default:
-                childTypeError(child);
-                break;
-            }
-        }
-
-        if (size == 0) {
-            throw new ParseException("Integer missing size attribute"); //$NON-NLS-1$
-        }
-
-        if (alignment == 0) {
-            if ((size % 8) == 0) {
-                alignment = 1;
-            } else {
-                alignment = 8;
-            }
-        }
-
-        integerDeclaration = new IntegerDeclaration((int) size, signed, base,
-                byteOrder, encoding, clock);
-
-        assert (integerDeclaration != null);
-        return integerDeclaration;
-    }
-
-    private static String getClock(CommonTree rightNode) {
-        return rightNode.getChild(1).getChild(0).getChild(0).getText();
-    }
-
-    private static StringDeclaration parseString(CommonTree string)
-            throws ParseException {
-        assert (string.getType() == CTFParser.STRING);
-
-        List<CommonTree> children = string.getChildren();
-        StringDeclaration stringDeclaration = null;
-
-        if (children == null) {
-            stringDeclaration = new StringDeclaration();
-        } else {
-            Encoding encoding = Encoding.UTF8;
-            for (CommonTree child : children) {
-                switch (child.getType()) {
-                case CTFParser.CTF_EXPRESSION_VAL:
-                    /*
-                     * An assignment expression must have 2 children, left and
-                     * right
-                     */
-                    assert (child.getChildCount() == 2);
-
-                    CommonTree leftNode = (CommonTree) child.getChild(0);
-                    assert (leftNode.getType() == CTFParser.CTF_LEFT);
-                    CommonTree rightNode = (CommonTree) child.getChild(1);
-                    assert (rightNode.getType() == CTFParser.CTF_RIGHT);
-
-                    List<CommonTree> leftStrings = leftNode.getChildren();
-                    assert (leftStrings != null);
-
-                    if (!isUnaryString(leftStrings.get(0))) {
-                        throw new ParseException(
-                                "Left side of ctf expression must be a string"); //$NON-NLS-1$
-                    }
-                    String left = concatenateUnaryStrings(leftStrings);
-
-                    if (left.equals("encoding")) { //$NON-NLS-1$
-                        encoding = getEncoding(rightNode);
-                    } else {
-                        throw new ParseException("String: unknown attribute " //$NON-NLS-1$
-                                + left);
-                    }
-
-                    break;
-                default:
-                    childTypeError(child);
-                    break;
-                }
-            }
-
-            stringDeclaration = new StringDeclaration(encoding);
-        }
-
-        return stringDeclaration;
-    }
-
-    /**
-     * Parses a struct declaration and returns the corresponding declaration.
-     *
-     * @param struct
-     *            An STRUCT node.
-     * @return The corresponding struct declaration.
-     * @throws ParseException
-     */
-    private StructDeclaration parseStruct(CommonTree struct)
-            throws ParseException {
-        assert (struct.getType() == CTFParser.STRUCT);
-
-        List<CommonTree> children = struct.getChildren();
-        assert (children != null);
-
-        /* The return value */
-        StructDeclaration structDeclaration = null;
-
-        /* Name */
-        String structName = null;
-        boolean hasName = false;
-
-        /* Body */
-        CommonTree structBody = null;
-        boolean hasBody = false;
-
-        /* Align */
-        long structAlign = 0;
-
-        /* Loop on all children and identify what we have to work with. */
-        for (CommonTree child : children) {
-            switch (child.getType()) {
-            case CTFParser.STRUCT_NAME: {
-                hasName = true;
-
-                assert (child.getChildCount() == 1);
-                CommonTree structNameIdentifier = (CommonTree) child
-                        .getChild(0);
-
-                assert (structNameIdentifier.getType() == CTFParser.IDENTIFIER);
-                structName = structNameIdentifier.getText();
-
-                break;
-            }
-            case CTFParser.STRUCT_BODY: {
-                hasBody = true;
-
-                structBody = child;
-
-                break;
-            }
-            case CTFParser.ALIGN: {
-                assert (child.getChildCount() == 1);
-                CommonTree structAlignExpression = (CommonTree) child
-                        .getChild(0);
-
-                structAlign = getAlignment(structAlignExpression);
-
-                break;
-            }
-            default:
-                childTypeError(child);
-
-                break;
-            }
-        }
-
-        /*
-         * If a struct has just a body and no name (just like the song,
-         * "A Struct With No Name" by America (sorry for that...)), it's a
-         * definition of a new type, so we create the type declaration and
-         * return it. We can't add it to the declaration scope since there is no
-         * name, but that's what we want because it won't be possible to use it
-         * again to declare another field.
-         *
-         * If it has just a name, we look it up in the declaration scope and
-         * return the associated declaration. If it is not found in the
-         * declaration scope, it means that a struct with that name has not been
-         * declared, which is an error.
-         *
-         * If it has both, then we create the type declaration and register it
-         * to the current scope.
-         *
-         * If it has none, then what are we doing here ?
-         */
-        if (hasBody) {
-            /*
-             * If struct has a name, check if already defined in the current
-             * scope.
-             */
-            if (hasName && (getCurrentScope().lookupStruct(structName) != null)) {
-                throw new ParseException("struct " + structName //$NON-NLS-1$
-                        + " already defined."); //$NON-NLS-1$
-            }
-
-            /* Create the declaration */
-            structDeclaration = new StructDeclaration(structAlign);
-
-            /* Parse the body */
-            parseStructBody(structBody, structDeclaration);
-
-            /* If struct has name, add it to the current scope. */
-            if (hasName) {
-                getCurrentScope().registerStruct(structName, structDeclaration);
-            }
-        } else /* !hasBody */{
-            if (hasName) {
-                /* Name and !body */
-
-                /* Lookup the name in the current scope. */
-                structDeclaration = getCurrentScope().rlookupStruct(structName);
-
-                /*
-                 * If not found, it means that a struct with such name has not
-                 * been defined
-                 */
-                if (structDeclaration == null) {
-                    throw new ParseException("struct " + structName //$NON-NLS-1$
-                            + " is not defined"); //$NON-NLS-1$
-                }
-            } else {
-                /* !Name and !body */
-
-                /* We can't do anything with that. */
-                throw new ParseException("struct with no name and no body"); //$NON-NLS-1$
-            }
-        }
-
-        assert (structDeclaration != null);
-        return structDeclaration;
-    }
-
-    /**
-     * Parses a struct body, adding the fields to specified structure
-     * declaration.
-     *
-     * @param structBody
-     *            A STRUCT_BODY node.
-     * @param structDeclaration
-     *            The struct declaration.
-     * @throws ParseException
-     */
-    private void parseStructBody(CommonTree structBody,
-            StructDeclaration structDeclaration) throws ParseException {
-        assert (structBody.getType() == CTFParser.STRUCT_BODY);
-
-        List<CommonTree> structDeclarations = structBody.getChildren();
-
-        /*
-         * If structDeclaration is null, structBody has no children and the
-         * struct body is empty.
-         */
-        if (structDeclarations != null) {
-            pushScope();
-
-            for (CommonTree declarationNode : structDeclarations) {
-                switch (declarationNode.getType()) {
-                case CTFParser.TYPEALIAS:
-                    parseTypealias(declarationNode);
-                    break;
-                case CTFParser.TYPEDEF:
-                    parseTypedef(declarationNode);
-                    break;
-                case CTFParser.SV_DECLARATION:
-                    parseStructDeclaration(declarationNode, structDeclaration);
-                    break;
-                default:
-                    childTypeError(declarationNode);
-                    break;
-                }
-            }
-            popScope();
-        }
-    }
-
-    /**
-     * Parses a declaration found in a struct.
-     *
-     * @param declaration
-     *            A SV_DECLARATION node.
-     * @param struct
-     *            A struct declaration. (I know, little name clash here...)
-     * @throws ParseException
-     */
-    private void parseStructDeclaration(CommonTree declaration,
-            StructDeclaration struct) throws ParseException {
-        assert (declaration.getType() == CTFParser.SV_DECLARATION);
-
-        List<CommonTree> children = declaration.getChildren();
-        assert (children != null);
-
-        /* Get the type specifier list node */
-        CommonTree typeSpecifierListNode = (CommonTree) declaration
-                .getFirstChildWithType(CTFParser.TYPE_SPECIFIER_LIST);
-        assert (typeSpecifierListNode != null);
-
-        /* Get the type declarator list node */
-        CommonTree typeDeclaratorListNode = (CommonTree) declaration
-                .getFirstChildWithType(CTFParser.TYPE_DECLARATOR_LIST);
-        assert (typeDeclaratorListNode != null);
-
-        /* Get the type declarator list */
-        List<CommonTree> typeDeclaratorList = typeDeclaratorListNode
-                .getChildren();
-        assert (typeDeclaratorList != null);
-
-        /*
-         * For each type declarator, parse the declaration and add a field to
-         * the struct
-         */
-        for (CommonTree typeDeclaratorNode : typeDeclaratorList) {
-            assert (typeDeclaratorNode.getType() == CTFParser.TYPE_DECLARATOR);
-
-            StringBuilder identifierSB = new StringBuilder();
-
-            IDeclaration decl = parseTypeDeclarator(typeDeclaratorNode,
-                    typeSpecifierListNode, identifierSB);
-            String fieldName = identifierSB.toString();
-
-            if (struct.hasField(fieldName)) {
-                throw new ParseException("struct: duplicate field " //$NON-NLS-1$
-                        + fieldName);
-            }
-
-            struct.addField(fieldName, decl);
-
-        }
-    }
-
-    /**
-     * Parses an enum declaration and returns the corresponding declaration.
-     *
-     * @param _enum
-     *            An ENUM node.
-     * @return The corresponding enum declaration.
-     * @throws ParseException
-     */
-    private EnumDeclaration parseEnum(CommonTree _enum) throws ParseException {
-        assert (_enum.getType() == CTFParser.ENUM);
-
-        List<CommonTree> children = _enum.getChildren();
-        assert (children != null);
-
-        /* The return value */
-        EnumDeclaration enumDeclaration = null;
-
-        /* Name */
-        String enumName = null;
-
-        /* Body */
-        CommonTree enumBody = null;
-
-        /* Container type */
-        IntegerDeclaration containerTypeDeclaration = null;
-
-        /* Loop on all children and identify what we have to work with. */
-        for (CommonTree child : children) {
-            switch (child.getType()) {
-            case CTFParser.ENUM_NAME: {
-                assert (enumName == null);
-
-                assert (child.getChildCount() == 1);
-                CommonTree enumNameIdentifier = (CommonTree) child.getChild(0);
-
-                assert (enumNameIdentifier.getType() == CTFParser.IDENTIFIER);
-                enumName = enumNameIdentifier.getText();
-
-                break;
-            }
-            case CTFParser.ENUM_BODY: {
-                assert (enumBody == null);
-
-                enumBody = child;
-
-                break;
-            }
-            case CTFParser.ENUM_CONTAINER_TYPE: {
-                assert (containerTypeDeclaration == null);
-
-                containerTypeDeclaration = parseEnumContainerType(child);
-
-                break;
-            }
-            default:
-                childTypeError(child);
-                break;
-            }
-        }
-
-        /*
-         * If the container type has not been defined explicitly, we assume it
-         * is "int".
-         */
-        if (containerTypeDeclaration == null) {
-            IDeclaration decl = getCurrentScope().rlookupType("int"); //$NON-NLS-1$
-
-            if (decl == null) {
-                throw new ParseException(
-                        "enum container type implicit and type int not defined"); //$NON-NLS-1$
-            } else if (!(decl instanceof IntegerDeclaration)) {
-                throw new ParseException(
-                        "enum container type implicit and type int not an integer"); //$NON-NLS-1$
-            }
-
-            containerTypeDeclaration = (IntegerDeclaration) decl;
-        }
-
-        /*
-         * If it has a body, it's a new declaration, otherwise it's a reference
-         * to an existing declaration. Same logic as struct.
-         */
-        if (enumBody != null) {
-            /*
-             * If enum has a name, check if already defined in the current
-             * scope.
-             */
-            if ((enumName != null)
-                    && (getCurrentScope().lookupEnum(enumName) != null)) {
-                throw new ParseException("enum " + enumName //$NON-NLS-1$
-                        + " already defined"); //$NON-NLS-1$
-            }
-
-            /* Create the declaration */
-            enumDeclaration = new EnumDeclaration(containerTypeDeclaration);
-
-            /* Parse the body */
-            parseEnumBody(enumBody, enumDeclaration);
-
-            /* If the enum has name, add it to the current scope. */
-            if (enumName != null) {
-                getCurrentScope().registerEnum(enumName, enumDeclaration);
-            }
-        } else {
-            if (enumName != null) {
-                /* Name and !body */
-
-                /* Lookup the name in the current scope. */
-                enumDeclaration = getCurrentScope().rlookupEnum(enumName);
-
-                /*
-                 * If not found, it means that an enum with such name has not
-                 * been defined
-                 */
-                if (enumDeclaration == null) {
-                    throw new ParseException("enum " + enumName //$NON-NLS-1$
-                            + " is not defined"); //$NON-NLS-1$
-                }
-            } else {
-                /* !Name and !body */
-                throw new ParseException("enum with no name and no body"); //$NON-NLS-1$
-            }
-        }
-
-        return enumDeclaration;
-
-    }
-
-    /**
-     * Parses an enum body, adding the enumerators to the specified enum
-     * declaration.
-     *
-     * @param enumBody
-     *            An ENUM_BODY node.
-     * @param enumDeclaration
-     *            The enum declaration.
-     * @throws ParseException
-     */
-    private void parseEnumBody(CommonTree enumBody,
-            EnumDeclaration enumDeclaration) throws ParseException {
-        assert (enumBody.getType() == CTFParser.ENUM_BODY);
-
-        List<CommonTree> enumerators = enumBody.getChildren();
-        /* enum body can't be empty (unlike struct). */
-        assert (enumerators != null);
-
-        pushScope();
-
-        /*
-         * Start at -1, so that if the first enumrator has no explicit value, it
-         * will choose 0
-         */
-        long lastHigh = -1;
-
-        for (CommonTree enumerator : enumerators) {
-            lastHigh = parseEnumEnumerator(enumerator, enumDeclaration,
-                    lastHigh);
-        }
-
-        popScope();
-
-    }
-
-    /**
-     * Parses an enumerator node and adds an enumerator declaration to an
-     * enumeration declaration.
-     *
-     * The high value of the range of the last enumerator is needed in case the
-     * current enumerator does not specify its value.
-     *
-     * @param enumerator
-     *            An ENUM_ENUMERATOR node.
-     * @param enumDeclaration
-     *            en enumeration declaration to which will be added the
-     *            enumerator.
-     * @param lastHigh
-     *            The high value of the range of the last enumerator
-     * @return The high value of the value range of the current enumerator.
-     * @throws ParseException
-     */
-    private static long parseEnumEnumerator(CommonTree enumerator,
-            EnumDeclaration enumDeclaration, long lastHigh)
-            throws ParseException {
-        assert (enumerator.getType() == CTFParser.ENUM_ENUMERATOR);
-
-        List<CommonTree> children = enumerator.getChildren();
-        assert (children != null);
-
-        long low = 0, high = 0;
-        boolean valueSpecified = false;
-        String label = null;
-
-        for (CommonTree child : children) {
-            if (isUnaryString(child)) {
-                label = parseUnaryString(child);
-            } else if (child.getType() == CTFParser.ENUM_VALUE) {
-                assert (child.getChildCount() == 1);
-                assert (isUnaryInteger((CommonTree) child.getChild(0)));
-
-                valueSpecified = true;
-
-                low = parseUnaryInteger((CommonTree) child.getChild(0));
-                high = low;
-            } else if (child.getType() == CTFParser.ENUM_VALUE_RANGE) {
-                assert (child.getChildCount() == 2);
-                assert (isUnaryInteger((CommonTree) child.getChild(0)));
-                assert (isUnaryInteger((CommonTree) child.getChild(1)));
-
-                valueSpecified = true;
-
-                low = parseUnaryInteger((CommonTree) child.getChild(0));
-                high = parseUnaryInteger((CommonTree) child.getChild(1));
-            } else {
-                childTypeError(child);
-            }
-        }
-
-        assert (label != null);
-
-        if (!valueSpecified) {
-            low = lastHigh + 1;
-            high = low;
-        }
-
-        if (low > high) {
-            throw new ParseException("enum low value greater than high value"); //$NON-NLS-1$
-        }
-
-        if (!enumDeclaration.add(low, high, label)) {
-            throw new ParseException("enum declarator values overlap."); //$NON-NLS-1$
-        }
-
-        return high;
-    }
-
-    /**
-     * Parses an enum container type node and returns the corresponding integer
-     * type.
-     *
-     * @param enumContainerType
-     *            An ENUM_CONTAINER_TYPE node.
-     * @return An integer declaration corresponding to the container type.
-     * @throws ParseException
-     *             If the type does not parse correctly or if it is not an
-     *             integer type.
-     */
-    private IntegerDeclaration parseEnumContainerType(
-            CommonTree enumContainerType) throws ParseException {
-        assert (enumContainerType.getType() == CTFParser.ENUM_CONTAINER_TYPE);
-
-        /* Get the child, which should be a type specifier list */
-        assert (enumContainerType.getChildCount() == 1);
-        CommonTree typeSpecifierList = (CommonTree) enumContainerType
-                .getChild(0);
-
-        /* Parse it and get the corresponding declaration */
-        IDeclaration decl = parseTypeSpecifierList(typeSpecifierList, null);
-
-        /* If is is an integer, return it, else throw an error */
-        if (decl instanceof IntegerDeclaration) {
-            return (IntegerDeclaration) decl;
-        }
-        throw new ParseException("enum container type must be an integer"); //$NON-NLS-1$
-    }
-
-    private VariantDeclaration parseVariant(CommonTree variant)
-            throws ParseException {
-        assert (variant.getType() == CTFParser.VARIANT);
-
-        List<CommonTree> children = variant.getChildren();
-        VariantDeclaration variantDeclaration = null;
-
-        boolean hasName = false;
-        String variantName = null;
-
-        boolean hasBody = false;
-        CommonTree variantBody = null;
-
-        boolean hasTag = false;
-        String variantTag = null;
-
-        for (CommonTree child : children) {
-            switch (child.getType()) {
-            case CTFParser.VARIANT_NAME:
-                assert (variantName == null);
-
-                hasName = true;
-
-                assert (child.getChildCount() == 1);
-                CommonTree variantNameIdentifier = (CommonTree) child
-                        .getChild(0);
-
-                assert (variantNameIdentifier.getType() == CTFParser.IDENTIFIER);
-                variantName = variantNameIdentifier.getText();
-
-                break;
-            case CTFParser.VARIANT_TAG:
-                assert (variantTag == null);
-
-                hasTag = true;
-
-                assert (child.getChildCount() == 1);
-                CommonTree variantTagIdentifier = (CommonTree) child
-                        .getChild(0);
-
-                assert (variantTagIdentifier.getType() == CTFParser.IDENTIFIER);
-                variantTag = variantTagIdentifier.getText();
-
-                break;
-            case CTFParser.VARIANT_BODY:
-                assert (variantBody == null);
-
-                hasBody = true;
-
-                variantBody = child;
-
-                break;
-            default:
-                childTypeError(child);
-                break;
-            }
-        }
-
-        if (hasBody) {
-            /*
-             * If variant has a name, check if already defined in the current
-             * scope.
-             */
-            if (hasName
-                    && (getCurrentScope().lookupVariant(variantName) != null)) {
-                throw new ParseException("variant " + variantName //$NON-NLS-1$
-                        + " already defined."); //$NON-NLS-1$
-            }
-
-            /* Create the declaration */
-            variantDeclaration = new VariantDeclaration();
-
-            /* Parse the body */
-            parseVariantBody(variantBody, variantDeclaration);
-
-            /* If variant has name, add it to the current scope. */
-            if (hasName) {
-                getCurrentScope().registerVariant(variantName,
-                        variantDeclaration);
-            }
-        } else /* !hasBody */{
-            if (hasName) {
-                /* Name and !body */
-
-                /* Lookup the name in the current scope. */
-                variantDeclaration = getCurrentScope().rlookupVariant(
-                        variantName);
-
-                /*
-                 * If not found, it means that a struct with such name has not
-                 * been defined
-                 */
-                if (variantDeclaration == null) {
-                    throw new ParseException("variant " + variantName //$NON-NLS-1$
-                            + " is not defined"); //$NON-NLS-1$
-                }
-            } else {
-                /* !Name and !body */
-
-                /* We can't do anything with that. */
-                throw new ParseException("variant with no name and no body"); //$NON-NLS-1$
-            }
-        }
-
-        if (hasTag) {
-            variantDeclaration.setTag(variantTag);
-        }
-
-        assert (variantDeclaration != null);
-        return variantDeclaration;
-    }
-
-    private void parseVariantBody(CommonTree variantBody,
-            VariantDeclaration variantDeclaration) throws ParseException {
-        assert (variantBody.getType() == CTFParser.VARIANT_BODY);
-
-        List<CommonTree> variantDeclarations = variantBody.getChildren();
-        assert (variantDeclarations != null);
-
-        pushScope();
-
-        for (CommonTree declarationNode : variantDeclarations) {
-            switch (declarationNode.getType()) {
-            case CTFParser.TYPEALIAS:
-                parseTypealias(declarationNode);
-                break;
-            case CTFParser.TYPEDEF:
-                parseTypedef(declarationNode);
-                break;
-            case CTFParser.SV_DECLARATION:
-                parseVariantDeclaration(declarationNode, variantDeclaration);
-                break;
-            default:
-                childTypeError(declarationNode);
-                break;
-            }
-        }
-
-        popScope();
-    }
-
-    private void parseVariantDeclaration(CommonTree declaration,
-            VariantDeclaration variant) throws ParseException {
-        assert (declaration.getType() == CTFParser.SV_DECLARATION);
-
-        List<CommonTree> children = declaration.getChildren();
-        assert (children != null);
-
-        /* Get the type specifier list node */
-        CommonTree typeSpecifierListNode = (CommonTree) declaration
-                .getFirstChildWithType(CTFParser.TYPE_SPECIFIER_LIST);
-        assert (typeSpecifierListNode != null);
-
-        /* Get the type declarator list node */
-        CommonTree typeDeclaratorListNode = (CommonTree) declaration
-                .getFirstChildWithType(CTFParser.TYPE_DECLARATOR_LIST);
-        assert (typeDeclaratorListNode != null);
-
-        /* Get the type declarator list */
-        List<CommonTree> typeDeclaratorList = typeDeclaratorListNode
-                .getChildren();
-        assert (typeDeclaratorList != null);
-
-        /*
-         * For each type declarator, parse the declaration and add a field to
-         * the variant
-         */
-        for (CommonTree typeDeclaratorNode : typeDeclaratorList) {
-            assert (typeDeclaratorNode.getType() == CTFParser.TYPE_DECLARATOR);
-
-            StringBuilder identifierSB = new StringBuilder();
-
-            IDeclaration decl = parseTypeDeclarator(typeDeclaratorNode,
-                    typeSpecifierListNode, identifierSB);
-
-            if (variant.hasField(identifierSB.toString())) {
-                throw new ParseException("variant: duplicate field " //$NON-NLS-1$
-                        + identifierSB.toString());
-            }
-
-            variant.addField(identifierSB.toString(), decl);
-        }
-    }
-
-    /**
-     * Creates the string representation of a type declaration (type specifier
-     * list + pointers).
-     *
-     * @param typeSpecifierList
-     *            A TYPE_SPECIFIER_LIST node.
-     * @param pointers
-     *            A list of POINTER nodes.
-     * @return The string representation.
-     * @throws ParseException
-     */
-    private static String createTypeDeclarationString(
-            CommonTree typeSpecifierList, List<CommonTree> pointers)
-            throws ParseException {
-        StringBuilder sb = new StringBuilder();
-
-        createTypeSpecifierListString(typeSpecifierList, sb);
-        createPointerListString(pointers, sb);
-
-        return sb.toString();
-    }
-
-    /**
-     * Creates the string representation of a list of type specifiers.
-     *
-     * @param typeSpecifierList
-     *            A TYPE_SPECIFIER_LIST node.
-     * @param sb
-     *            A StringBuilder to which will be appended the string.
-     * @throws ParseException
-     */
-    private static void createTypeSpecifierListString(
-            CommonTree typeSpecifierList, StringBuilder sb)
-            throws ParseException {
-        assert (typeSpecifierList.getType() == CTFParser.TYPE_SPECIFIER_LIST);
-
-        List<CommonTree> children = typeSpecifierList.getChildren();
-        assert (children != null);
-
-        boolean firstItem = true;
-
-        for (CommonTree child : children) {
-            if (!firstItem) {
-                sb.append(' ');
-
-            }
-
-            firstItem = false;
-
-            /* Append the string that represents this type specifier. */
-            createTypeSpecifierString(child, sb);
-        }
-    }
-
-    /**
-     * Creates the string representation of a type specifier.
-     *
-     * @param typeSpecifier
-     *            A TYPE_SPECIFIER node.
-     * @param sb
-     *            A StringBuilder to which will be appended the string.
-     * @throws ParseException
-     */
-    private static void createTypeSpecifierString(CommonTree typeSpecifier,
-            StringBuilder sb) throws ParseException {
-        switch (typeSpecifier.getType()) {
-        case CTFParser.FLOATTOK:
-        case CTFParser.INTTOK:
-        case CTFParser.LONGTOK:
-        case CTFParser.SHORTTOK:
-        case CTFParser.SIGNEDTOK:
-        case CTFParser.UNSIGNEDTOK:
-        case CTFParser.CHARTOK:
-        case CTFParser.DOUBLETOK:
-        case CTFParser.VOIDTOK:
-        case CTFParser.BOOLTOK:
-        case CTFParser.COMPLEXTOK:
-        case CTFParser.IMAGINARYTOK:
-        case CTFParser.CONSTTOK:
-        case CTFParser.IDENTIFIER:
-            sb.append(typeSpecifier.getText());
-            break;
-        case CTFParser.STRUCT: {
-            CommonTree structName = (CommonTree) typeSpecifier
-                    .getFirstChildWithType(CTFParser.STRUCT_NAME);
-            if (structName == null) {
-                throw new ParseException(
-                        "nameless struct found in createTypeSpecifierString"); //$NON-NLS-1$
-            }
-            assert (structName.getChildCount() == 1);
-
-            CommonTree structNameIdentifier = (CommonTree) structName
-                    .getChild(0);
-            assert (structNameIdentifier.getType() == CTFParser.IDENTIFIER);
-
-            sb.append(structNameIdentifier.getText());
-            break;
-        }
-        case CTFParser.VARIANT: {
-            CommonTree variantName = (CommonTree) typeSpecifier
-                    .getFirstChildWithType(CTFParser.VARIANT_NAME);
-            if (variantName == null) {
-                throw new ParseException(
-                        "nameless variant found in createTypeSpecifierString"); //$NON-NLS-1$
-            }
-            assert (variantName.getChildCount() == 1);
-
-            CommonTree variantNameIdentifier = (CommonTree) variantName
-                    .getChild(0);
-            assert (variantNameIdentifier.getType() == CTFParser.IDENTIFIER);
-
-            sb.append(variantNameIdentifier.getText());
-            break;
-        }
-        case CTFParser.ENUM: {
-            CommonTree enumName = (CommonTree) typeSpecifier
-                    .getFirstChildWithType(CTFParser.ENUM_NAME);
-            if (enumName == null) {
-                throw new ParseException(
-                        "nameless enum found in createTypeSpecifierString"); //$NON-NLS-1$
-            }
-            assert (enumName.getChildCount() == 1);
-
-            CommonTree enumNameIdentifier = (CommonTree) enumName.getChild(0);
-            assert (enumNameIdentifier.getType() == CTFParser.IDENTIFIER);
-
-            sb.append(enumNameIdentifier.getText());
-            break;
-        }
-        case CTFParser.FLOATING_POINT:
-        case CTFParser.INTEGER:
-        case CTFParser.STRING:
-            throw new ParseException(
-                    "CTF type found in createTypeSpecifierString"); //$NON-NLS-1$
-            /* break; */
-        default:
-            childTypeError(typeSpecifier);
-            break;
-        }
-    }
-
-    /**
-     * Creates the string representation of a list of pointers.
-     *
-     * @param pointerList
-     *            A list of pointer nodes. If pointerList is null, this function
-     *            does nothing.
-     * @param sb
-     *            A stringbuilder to which will be appended the string.
-     */
-    private static void createPointerListString(List<CommonTree> pointerList,
-            StringBuilder sb) {
-        if (pointerList == null) {
-            return;
-        }
-
-        for (CommonTree pointer : pointerList) {
-            assert (pointer.getType() == CTFParser.POINTER);
-
-            sb.append(" *"); //$NON-NLS-1$
-            if (pointer.getChildCount() > 0) {
-                assert (pointer.getChildCount() == 1);
-                CommonTree constQualifier = (CommonTree) pointer.getChild(0);
-                assert (constQualifier.getType() == CTFParser.CONSTTOK);
-
-                sb.append(" const"); //$NON-NLS-1$
-            }
-        }
-    }
-
-    /**
-     * @param node
-     *            The node to check.
-     * @return True if the given node is an unary string or unary integer.
-     */
-    private static boolean isUnaryExpression(CommonTree node) {
-        return isUnaryInteger(node) || isUnaryString(node);
-    }
-
-    /**
-     * @param node
-     *            The node to check.
-     * @return True if the given node is an unary string.
-     */
-    private static boolean isUnaryString(CommonTree node) {
-        return ((node.getType() == CTFParser.UNARY_EXPRESSION_STRING) || (node
-                .getType() == CTFParser.UNARY_EXPRESSION_STRING_QUOTES));
-    }
-
-    /**
-     * @param node
-     *            The node to check.
-     * @return True if the given node is an unary integer.
-     */
-    private static boolean isUnaryInteger(CommonTree node) {
-        return ((node.getType() == CTFParser.UNARY_EXPRESSION_DEC)
-                || (node.getType() == CTFParser.UNARY_EXPRESSION_HEX) || (node
-                    .getType() == CTFParser.UNARY_EXPRESSION_OCT));
-    }
-
-    /**
-     * Parses a unary string node and return the string value.
-     *
-     * @param unaryString
-     *            The unary string node to parse (type UNARY_EXPRESSION_STRING
-     *            or UNARY_EXPRESSION_STRING_QUOTES).
-     * @return The string value.
-     */
-    /*
-     * It would be really nice to remove the quotes earlier, such as in the
-     * parser.
-     */
-    private static String parseUnaryString(CommonTree unaryString) {
-        assert (isUnaryString(unaryString));
-
-        assert (unaryString.getChildCount() == 1);
-        CommonTree value = (CommonTree) unaryString.getChild(0);
-        assert (value != null);
-        String strval = value.getText();
-
-        /* Remove quotes */
-        if (unaryString.getType() == CTFParser.UNARY_EXPRESSION_STRING_QUOTES) {
-            strval = strval.substring(1, strval.length() - 1);
-        }
-
-        return strval;
-    }
-
-    /**
-     * Parses an unary integer (dec, hex or oct).
-     *
-     * @param unaryInteger
-     *            An unary integer node.
-     * @return The integer value.
-     */
-    private static long parseUnaryInteger(CommonTree unaryInteger) {
-        assert (isUnaryInteger(unaryInteger));
-
-        assert (unaryInteger.getChildCount() >= 1);
-
-        List<CommonTree> children = unaryInteger.getChildren();
-        CommonTree value = children.get(0);
-        String strval = value.getText();
-
-        long intval;
-
-        if (unaryInteger.getType() == CTFParser.UNARY_EXPRESSION_DEC) {
-            intval = Long.parseLong(strval, 10);
-        } else if (unaryInteger.getType() == CTFParser.UNARY_EXPRESSION_HEX) {
-            intval = Long.parseLong(strval, 0x10);
-        } else { /* unaryInteger.getType() == CTFParser.UNARY_EXPRESSION_OCT */
-            intval = Long.parseLong(strval, 010); // 010 == 0x08 == 8
-        }
-
-        /* The rest of children are sign */
-        if ((children.size() % 2) == 0) {
-            return -intval;
-        }
-        return intval;
-    }
-
-    private static long getMajorOrMinor(CommonTree rightNode)
-            throws ParseException {
-        assert (rightNode.getType() == CTFParser.CTF_RIGHT);
-        assert (rightNode.getChildCount() > 0);
-
-        CommonTree firstChild = (CommonTree) rightNode.getChild(0);
-
-        if (isUnaryInteger(firstChild)) {
-            if (rightNode.getChildCount() > 1) {
-                throw new ParseException("Invalid value for major/minor"); //$NON-NLS-1$
-            }
-
-            long m = parseUnaryInteger(firstChild);
-
-            if (m < 0) {
-                throw new ParseException("Invalid value for major/minor"); //$NON-NLS-1$
-            }
-
-            return m;
-        }
-        throw new ParseException("Invalid value for major/minor"); //$NON-NLS-1$
-    }
-
-    private static UUID getUUID(CommonTree rightNode) throws ParseException {
-        assert (rightNode.getType() == CTFParser.CTF_RIGHT);
-        assert (rightNode.getChildCount() > 0);
-
-        CommonTree firstChild = (CommonTree) rightNode.getChild(0);
-
-        if (isUnaryString(firstChild)) {
-            if (rightNode.getChildCount() > 1) {
-                throw new ParseException("Invalid value for UUID"); //$NON-NLS-1$
-            }
-
-            String uuidstr = parseUnaryString(firstChild);
-
-            try {
-                UUID uuid = UUID.fromString(uuidstr);
-                return uuid;
-            } catch (IllegalArgumentException e) {
-                throw new ParseException("Invalid format for UUID"); //$NON-NLS-1$
-            }
-        }
-        throw new ParseException("Invalid value for UUID"); //$NON-NLS-1$
-    }
-
-    /**
-     * Gets the value of a "signed" integer attribute.
-     *
-     * @param rightNode
-     *            A CTF_RIGHT node.
-     * @return The "signed" value as a boolean.
-     * @throws ParseException
-     */
-    private static boolean getSigned(CommonTree rightNode)
-            throws ParseException {
-        assert (rightNode.getType() == CTFParser.CTF_RIGHT);
-        assert (rightNode.getChildCount() > 0);
-
-        boolean ret = false;
-        CommonTree firstChild = (CommonTree) rightNode.getChild(0);
-
-        if (isUnaryString(firstChild)) {
-            String strval = concatenateUnaryStrings(rightNode.getChildren());
-
-            if (strval.equals("true") || strval.equals("TRUE")) { //$NON-NLS-1$ //$NON-NLS-2$
-                ret = true;
-            } else if (strval.equals("false") || strval.equals("FALSE")) { //$NON-NLS-1$ //$NON-NLS-2$
-                ret = false;
-            } else {
-                throw new ParseException("Invalid boolean value " //$NON-NLS-1$
-                        + firstChild.getChild(0).getText());
-            }
-        } else if (isUnaryInteger(firstChild)) {
-            /* Happens if the value is something like "1234.hello" */
-            if (rightNode.getChildCount() > 1) {
-                throw new ParseException("Invalid boolean value"); //$NON-NLS-1$
-            }
-
-            long intval = parseUnaryInteger(firstChild);
-
-            if (intval == 1) {
-                ret = true;
-            } else if (intval == 0) {
-                ret = false;
-            } else {
-                throw new ParseException("Invalid boolean value " //$NON-NLS-1$
-                        + firstChild.getChild(0).getText());
-            }
-        } else {
-            throw new ParseException();
-        }
-
-        return ret;
-    }
-
-    /**
-     * Gets the value of a "byte_order" integer attribute.
-     *
-     * @param rightNode
-     *            A CTF_RIGHT node.
-     * @return The "byte_order" value.
-     * @throws ParseException
-     */
-    private ByteOrder getByteOrder(CommonTree rightNode) throws ParseException {
-        assert (rightNode.getType() == CTFParser.CTF_RIGHT);
-        assert (rightNode.getChildCount() > 0);
-
-        CommonTree firstChild = (CommonTree) rightNode.getChild(0);
-
-        if (isUnaryString(firstChild)) {
-            String strval = concatenateUnaryStrings(rightNode.getChildren());
-
-            if (strval.equals("le")) { //$NON-NLS-1$
-                return ByteOrder.LITTLE_ENDIAN;
-            } else if (strval.equals("be") || strval.equals("network")) { //$NON-NLS-1$ //$NON-NLS-2$
-                return ByteOrder.BIG_ENDIAN;
-            } else if (strval.equals("native")) { //$NON-NLS-1$
-                return trace.getByteOrder();
-            } else {
-                throw new ParseException("Invalid value for byte order"); //$NON-NLS-1$
-            }
-        }
-        throw new ParseException("Invalid value for byte order"); //$NON-NLS-1$
-    }
-
-    /**
-     * Determines if the given value is a valid alignment value.
-     *
-     * @param alignment
-     *            The value to check.
-     * @return True if it is valid.
-     */
-    private static boolean isValidAlignment(long alignment) {
-        return !((alignment <= 0) || ((alignment & (alignment - 1)) != 0));
-    }
-
-    /**
-     * Gets the value of a "size" integer attribute.
-     *
-     * @param rightNode
-     *            A CTF_RIGHT node.
-     * @return The "size" value.
-     * @throws ParseException
-     */
-    private static long getSize(CommonTree rightNode) throws ParseException {
-        assert (rightNode.getType() == CTFParser.CTF_RIGHT);
-        assert (rightNode.getChildCount() > 0);
-
-        CommonTree firstChild = (CommonTree) rightNode.getChild(0);
-
-        if (isUnaryInteger(firstChild)) {
-            if (rightNode.getChildCount() > 1) {
-                throw new ParseException("Invalid value for size"); //$NON-NLS-1$
-            }
-
-            long size = parseUnaryInteger(firstChild);
-
-            if (size < 1) {
-                throw new ParseException("Invalid value for size"); //$NON-NLS-1$
-            }
-
-            return size;
-        }
-        throw new ParseException("Invalid value for size"); //$NON-NLS-1$
-    }
-
-    /**
-     * Gets the value of a "align" integer or struct attribute.
-     *
-     * @param node
-     *            A CTF_RIGHT node or directly an unary integer.
-     * @return The align value.
-     * @throws ParseException
-     */
-    private static long getAlignment(CommonTree node) throws ParseException {
-        assert (isUnaryExpression(node) || (node.getType() == CTFParser.CTF_RIGHT));
-
-        /*
-         * If a CTF_RIGHT node was passed, call getAlignment with the first
-         * child
-         */
-        if (node.getType() == CTFParser.CTF_RIGHT) {
-            if (node.getChildCount() > 1) {
-                throw new ParseException("Invalid alignment value"); //$NON-NLS-1$
-            }
-
-            return getAlignment((CommonTree) node.getChild(0));
-        } else if (isUnaryInteger(node)) {
-            long alignment = parseUnaryInteger(node);
-
-            if (!isValidAlignment(alignment)) {
-                throw new ParseException("Invalid value for alignment : " //$NON-NLS-1$
-                        + alignment);
-            }
-
-            return alignment;
-        }
-        throw new ParseException("Invalid value for alignment"); //$NON-NLS-1$
-    }
-
-    /**
-     * Gets the value of a "base" integer attribute.
-     *
-     * @param rightNode
-     *            An CTF_RIGHT node.
-     * @return The "base" value.
-     * @throws ParseException
-     */
-    private static int getBase(CommonTree rightNode) throws ParseException {
-        assert (rightNode.getType() == CTFParser.CTF_RIGHT);
-        assert (rightNode.getChildCount() > 0);
-
-        CommonTree firstChild = (CommonTree) rightNode.getChild(0);
-
-        if (isUnaryInteger(firstChild)) {
-            if (rightNode.getChildCount() > 1) {
-                throw new ParseException("invalid base value"); //$NON-NLS-1$
-            }
-
-            long intval = parseUnaryInteger(firstChild);
-            if ((intval == 2) || (intval == 8) || (intval == 10)
-                    || (intval == 16)) {
-                return (int) intval;
-            }
-            throw new ParseException("Invalid value for base"); //$NON-NLS-1$
-        } else if (isUnaryString(firstChild)) {
-            String strval = concatenateUnaryStrings(rightNode.getChildren());
-
-            if (strval.equals("decimal") || strval.equals("dec") //$NON-NLS-1$ //$NON-NLS-2$
-                    || strval.equals("d") || strval.equals("i") //$NON-NLS-1$ //$NON-NLS-2$
-                    || strval.equals("u")) { //$NON-NLS-1$
-                return 10;
-            } else if (strval.equals("hexadecimal") || strval.equals("hex") //$NON-NLS-1$ //$NON-NLS-2$
-                    || strval.equals("x") || strval.equals("X") //$NON-NLS-1$ //$NON-NLS-2$
-                    || strval.equals("p")) { //$NON-NLS-1$
-                return 16;
-            } else if (strval.equals("octal") || strval.equals("oct") //$NON-NLS-1$ //$NON-NLS-2$
-                    || strval.equals("o")) { //$NON-NLS-1$
-                return 8;
-            } else if (strval.equals("binary") || strval.equals("b")) { //$NON-NLS-1$ //$NON-NLS-2$
-                return 2;
-            } else {
-                throw new ParseException("Invalid value for base"); //$NON-NLS-1$
-            }
-        } else {
-            throw new ParseException("invalid value for base"); //$NON-NLS-1$
-        }
-    }
-
-    /**
-     * Gets the value of an "encoding" integer attribute.
-     *
-     * @param rightNode
-     *            A CTF_RIGHT node.
-     * @return The "encoding" value.
-     * @throws ParseException
-     */
-    private static Encoding getEncoding(CommonTree rightNode)
-            throws ParseException {
-        assert (rightNode.getType() == CTFParser.CTF_RIGHT);
-
-        CommonTree firstChild = (CommonTree) rightNode.getChild(0);
-
-        if (isUnaryString(firstChild)) {
-            String strval = concatenateUnaryStrings(rightNode.getChildren());
-
-            if (strval.equals("UTF8")) { //$NON-NLS-1$
-                return Encoding.UTF8;
-            } else if (strval.equals("ASCII")) { //$NON-NLS-1$
-                return Encoding.ASCII;
-            } else if (strval.equals("none")) { //$NON-NLS-1$
-                return Encoding.NONE;
-            } else {
-                throw new ParseException("Invalid value for encoding"); //$NON-NLS-1$
-            }
-        }
-        throw new ParseException("Invalid value for encoding"); //$NON-NLS-1$
-    }
-
-    private static long getStreamID(CommonTree rightNode) throws ParseException {
-        assert (rightNode.getType() == CTFParser.CTF_RIGHT);
-        assert (rightNode.getChildCount() > 0);
-
-        CommonTree firstChild = (CommonTree) rightNode.getChild(0);
-
-        if (isUnaryInteger(firstChild)) {
-            if (rightNode.getChildCount() > 1) {
-                throw new ParseException("invalid value for stream id"); //$NON-NLS-1$
-            }
-
-            long intval = parseUnaryInteger(firstChild);
-
-            return intval;
-        }
-        throw new ParseException("invalid value for stream id"); //$NON-NLS-1$
-    }
-
-    private static String getEventName(CommonTree rightNode)
-            throws ParseException {
-        assert (rightNode.getType() == CTFParser.CTF_RIGHT);
-        assert (rightNode.getChildCount() > 0);
-
-        CommonTree firstChild = (CommonTree) rightNode.getChild(0);
-
-        if (isUnaryString(firstChild)) {
-            String str = concatenateUnaryStrings(rightNode.getChildren());
-
-            return str;
-        }
-        throw new ParseException("invalid value for event name"); //$NON-NLS-1$
-    }
-
-    private static long getEventID(CommonTree rightNode) throws ParseException {
-        assert (rightNode.getType() == CTFParser.CTF_RIGHT);
-        assert (rightNode.getChildCount() > 0);
-
-        CommonTree firstChild = (CommonTree) rightNode.getChild(0);
-
-        if (isUnaryInteger(firstChild)) {
-            if (rightNode.getChildCount() > 1) {
-                throw new ParseException("invalid value for event id"); //$NON-NLS-1$
-            }
-
-            long intval = parseUnaryInteger(firstChild);
-
-            return intval;
-        }
-        throw new ParseException("invalid value for event id"); //$NON-NLS-1$
-    }
-
-    /**
-     * Concatenates a list of unary strings separated by arrows (->) or dots.
-     *
-     * @param strings
-     *            A list, first element being an unary string, subsequent
-     *            elements being ARROW or DOT nodes with unary strings as child.
-     * @return The string representation of the unary string chain.
-     */
-    private static String concatenateUnaryStrings(List<CommonTree> strings) {
-        assert ((strings != null) && (strings.size() > 0));
-
-        StringBuilder sb = new StringBuilder();
-
-        CommonTree first = strings.get(0);
-        sb.append(parseUnaryString(first));
-
-        boolean isFirst = true;
-
-        for (CommonTree ref : strings) {
-            if (isFirst) {
-                isFirst = false;
-                continue;
-            }
-
-            assert ((ref.getType() == CTFParser.ARROW) || (ref.getType() == CTFParser.DOT));
-            assert (ref.getChildCount() == 1);
-
-            CommonTree id = (CommonTree) ref.getChild(0);
-
-            if (ref.getType() == CTFParser.ARROW) {
-                sb.append("->"); //$NON-NLS-1$
-            } else { /* DOT */
-                sb.append('.');
-            }
-
-            sb.append(parseUnaryString(id));
-        }
-
-        return sb.toString();
-    }
-
-    /**
-     * Throws a ParseException stating that the parent-child relation between
-     * the given node and its parent is not valid. It means that the shape of
-     * the AST is unexpected.
-     *
-     * @param child
-     *            The invalid child node.
-     * @throws ParseException
-     */
-    private static void childTypeError(CommonTree child) throws ParseException {
-        CommonTree parent = (CommonTree) child.getParent();
-        String error = "Parent " + CTFParser.tokenNames[parent.getType()] //$NON-NLS-1$
-                + " can't have a child of type " //$NON-NLS-1$
-                + CTFParser.tokenNames[child.getType()] + "."; //$NON-NLS-1$
-
-        throw new ParseException(error);
-    }
-
-    // ------------------------------------------------------------------------
-    // Scope management
-    // ------------------------------------------------------------------------
-
-    /**
-     * Adds a new declaration scope on the top of the scope stack.
-     */
-    private void pushScope() {
-        scope = new DeclarationScope(scope);
-    }
-
-    /**
-     * Removes the top declaration scope from the scope stack.
-     */
-    private void popScope() {
-        assert (scope != null);
-        scope = scope.getParentScope();
-    }
-
-    /**
-     * Returns the current declaration scope.
-     *
-     * @return The current declaration scope.
-     */
-    private DeclarationScope getCurrentScope() {
-        assert (scope != null);
-        return scope;
-    }
-
-}
index 8c7e67a0f81405e40aa7c33e474edb23c7e2fea5..da5cef3475fd16779949783e19b851fcb38961c2 100644 (file)
@@ -12,7 +12,7 @@
 
 package org.eclipse.linuxtools.ctf.core.event.types;
 
-import org.eclipse.linuxtools.ctf.core.event.io.BitBuffer;
+import org.eclipse.linuxtools.internal.ctf.core.event.io.BitBuffer;
 
 /**
  * <b><u>ArrayDefinition</u></b>
index 4d4d28ba3da096ede0805dd6ee9c544b0c64cc1b..52ea6ef36643245a2e6c5bd34a26dfc9a2b587c9 100644 (file)
@@ -12,7 +12,7 @@
 
 package org.eclipse.linuxtools.ctf.core.event.types;
 
-import org.eclipse.linuxtools.ctf.core.event.io.BitBuffer;
+import org.eclipse.linuxtools.internal.ctf.core.event.io.BitBuffer;
 
 /**
  * <b><u>Definition</u></b>
index aef0446728f7866d34802ea33f04b53c457b12fb..e7824197d74280f763865df9cc96c5518f3bc0fc 100644 (file)
@@ -12,7 +12,7 @@
 
 package org.eclipse.linuxtools.ctf.core.event.types;
 
-import org.eclipse.linuxtools.ctf.core.event.io.BitBuffer;
+import org.eclipse.linuxtools.internal.ctf.core.event.io.BitBuffer;
 
 /**
  * <b><u>EnumDefinition</u></b>
index 9c594ebc15dda59c739b359acbf10594bf346b4e..6ac0d93d9f9b96d9d0fd6bc37c81578af86930ae 100644 (file)
@@ -12,7 +12,7 @@
 
 package org.eclipse.linuxtools.ctf.core.event.types;
 
-import org.eclipse.linuxtools.ctf.core.event.io.BitBuffer;
+import org.eclipse.linuxtools.internal.ctf.core.event.io.BitBuffer;
 
 /**
  * <b><u>IntegerDefinition</u></b>
index 9a7a1bd02970b717cebee18b3b59ced6923c5609..29d946e83e6b912a80adc5ae373fc3757b8e08db 100644 (file)
@@ -12,8 +12,8 @@
 
 package org.eclipse.linuxtools.ctf.core.event.types;
 
-import org.eclipse.linuxtools.ctf.core.event.io.BitBuffer;
 import org.eclipse.linuxtools.ctf.core.trace.CTFReaderException;
+import org.eclipse.linuxtools.internal.ctf.core.event.io.BitBuffer;
 
 /**
  * <b><u>SequenceDefinition</u></b>
index 17506a9ec6699d70d95890c2af6f4e762d4b9ecf..8a4eb8733a706a9009b50f4cf722a1eda3186571 100644 (file)
@@ -12,7 +12,7 @@
 
 package org.eclipse.linuxtools.ctf.core.event.types;
 
-import org.eclipse.linuxtools.ctf.core.event.io.BitBuffer;
+import org.eclipse.linuxtools.internal.ctf.core.event.io.BitBuffer;
 
 /**
  * <b><u>StringDefinition</u></b>
index 5ca77b2c207f3ac40b9838767b1e03c4ccb9ae59..e29a6d0d680211f7b548509b9d17c5330a7c640f 100644 (file)
@@ -15,7 +15,7 @@ package org.eclipse.linuxtools.ctf.core.event.types;
 import java.util.HashMap;
 import java.util.ListIterator;
 
-import org.eclipse.linuxtools.ctf.core.event.io.BitBuffer;
+import org.eclipse.linuxtools.internal.ctf.core.event.io.BitBuffer;
 
 /**
  * <b><u>StructDefinition</u></b>
index 135ff682d021a75981f813302c84e7a174681289..55011eae9f1706c37388ecb74027504a18b1c869 100644 (file)
@@ -15,7 +15,7 @@ package org.eclipse.linuxtools.ctf.core.event.types;
 import java.util.HashMap;
 import java.util.Map;
 
-import org.eclipse.linuxtools.ctf.core.event.io.BitBuffer;
+import org.eclipse.linuxtools.internal.ctf.core.event.io.BitBuffer;
 
 /**
  * <b><u>VariantDefinition</u></b>
index f22c45426bcd96d3fd24c831e4b3b2788e83bc59..599f3521ce827eeda5b39640e083858d9b9e781f 100644 (file)
@@ -28,7 +28,6 @@ import java.util.Set;
 import java.util.UUID;
 
 import org.eclipse.linuxtools.ctf.core.event.CTFClock;
-import org.eclipse.linuxtools.ctf.core.event.io.BitBuffer;
 import org.eclipse.linuxtools.ctf.core.event.metadata.exceptions.ParseException;
 import org.eclipse.linuxtools.ctf.core.event.types.ArrayDefinition;
 import org.eclipse.linuxtools.ctf.core.event.types.Definition;
@@ -37,6 +36,7 @@ import org.eclipse.linuxtools.ctf.core.event.types.IntegerDefinition;
 import org.eclipse.linuxtools.ctf.core.event.types.StructDeclaration;
 import org.eclipse.linuxtools.ctf.core.event.types.StructDefinition;
 import org.eclipse.linuxtools.internal.ctf.core.Activator;
+import org.eclipse.linuxtools.internal.ctf.core.event.io.BitBuffer;
 
 /**
  * <b><u>CTFTrace</u></b>
index 791cc3fdc527e1d807f86a1ff88a551979a0bff3..0de9104e6c92713235edf4046d6ae6a3e8f5544d 100644 (file)
@@ -19,6 +19,7 @@ import java.util.Vector;
 
 import org.eclipse.linuxtools.ctf.core.event.EventDefinition;
 import org.eclipse.linuxtools.internal.ctf.core.Activator;
+import org.eclipse.linuxtools.internal.ctf.core.trace.StreamInputPacketIndexEntry;
 
 /**
  * Reads the events of a trace.
index 749bf393ba6f6b6bb04d764a77fa2e8b307f019a..f1931a927ddfe83b7d61717c0540ff226b360975 100644 (file)
@@ -29,11 +29,11 @@ import org.antlr.runtime.ANTLRReaderStream;
 import org.antlr.runtime.CommonTokenStream;
 import org.antlr.runtime.RecognitionException;
 import org.antlr.runtime.tree.CommonTree;
-import org.eclipse.linuxtools.ctf.core.event.metadata.IOStructGen;
 import org.eclipse.linuxtools.ctf.core.event.metadata.exceptions.ParseException;
 import org.eclipse.linuxtools.ctf.parser.CTFLexer;
 import org.eclipse.linuxtools.ctf.parser.CTFParser;
 import org.eclipse.linuxtools.ctf.parser.CTFParser.parse_return;
+import org.eclipse.linuxtools.internal.ctf.core.event.metadata.IOStructGen;
 
 /**
  * <b><u>Metadata</u></b>
index 23ad52dc43a1df93ae51664f807d7f2d18461bc6..ca42c1e0b8fbe9fd0491a692e20d1b19e8584ffa 100644 (file)
@@ -19,12 +19,13 @@ import java.nio.channels.FileChannel;
 import java.nio.channels.FileChannel.MapMode;
 import java.util.UUID;
 
-import org.eclipse.linuxtools.ctf.core.event.io.BitBuffer;
 import org.eclipse.linuxtools.ctf.core.event.types.ArrayDefinition;
 import org.eclipse.linuxtools.ctf.core.event.types.Definition;
 import org.eclipse.linuxtools.ctf.core.event.types.IDefinitionScope;
 import org.eclipse.linuxtools.ctf.core.event.types.IntegerDefinition;
 import org.eclipse.linuxtools.ctf.core.event.types.StructDefinition;
+import org.eclipse.linuxtools.internal.ctf.core.event.io.BitBuffer;
+import org.eclipse.linuxtools.internal.ctf.core.trace.StreamInputPacketIndexEntry;
 
 /**
  * <b><u>StreamInput</u></b>
index 84c4bcc3397b3fe648de5f8fa81ae595a70e8227..cf2252c1a76bf275cb1efaf7e8ddb1825d6393b3 100644 (file)
@@ -15,6 +15,8 @@ package org.eclipse.linuxtools.ctf.core.trace;
 import java.util.ListIterator;
 import java.util.Vector;
 
+import org.eclipse.linuxtools.internal.ctf.core.trace.StreamInputPacketIndexEntry;
+
 /**
  * <b><u>StreamInputPacketIndex</u></b>
  * <p>
diff --git a/org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/ctf/core/trace/StreamInputPacketIndexEntry.java b/org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/ctf/core/trace/StreamInputPacketIndexEntry.java
deleted file mode 100644 (file)
index 10cfdc2..0000000
+++ /dev/null
@@ -1,216 +0,0 @@
-/*******************************************************************************
- * Copyright (c) 2011-2012 Ericsson, Ecole Polytechnique de Montreal and others
- *
- * All rights reserved. This program and the accompanying materials are made
- * available under the terms of the Eclipse Public License v1.0 which
- * accompanies this distribution, and is available at
- * http://www.eclipse.org/legal/epl-v10.html
- *
- * Contributors: Matthew Khouzam - Initial API and implementation
- * Contributors: Simon Marchi - Initial API and implementation
- *******************************************************************************/
-
-package org.eclipse.linuxtools.ctf.core.trace;
-
-/**
- * <b><u>StreamInputPacketIndexEntry</u></b>
- * <p>
- * Represents an entry in the index of event packets.
- */
-public class StreamInputPacketIndexEntry {
-
-    // ------------------------------------------------------------------------
-    // Attributes
-    // ------------------------------------------------------------------------
-
-
-
-    /**
-     * Offset of the packet in the file, in bytes
-     */
-    final private long offsetBytes;
-
-    /**
-     * Offset of the data in the packet, in bits
-     */
-    private int dataOffsetBits = 0;
-
-    /**
-     * Packet size, in bits
-     */
-    private int packetSizeBits = 0;
-
-    /**
-     * Content size, in bits
-     */
-    private int contentSizeBits = 0;
-
-    /**
-     * Begin timestamp
-     */
-    private long timestampBegin = 0;
-
-    /**
-     * End timestamp
-     */
-    private long timestampEnd = 0;
-
-
-    private long indexBegin = Long.MAX_VALUE;
-
-    private long indexEnd = Long.MAX_VALUE;
-
-    // ------------------------------------------------------------------------
-    // Constructors
-    // ------------------------------------------------------------------------
-
-    /**
-     * Constructs an index entry.
-     *
-     * @param offset
-     *            The offset of the packet in the file, in bytes.
-     */
-
-    public StreamInputPacketIndexEntry(long offset) {
-        this.offsetBytes = offset;
-    }
-
-    // ------------------------------------------------------------------------
-    // Operations
-    // ------------------------------------------------------------------------
-
-    /**
-     * Returns whether the packet includes (inclusively) the given timestamp in
-     * the begin-end timestamp range.
-     *
-     * @param ts
-     *            The timestamp to check.
-     * @return True if the packet includes the timestamp.
-     */
-    boolean includes(long ts) {
-        return (ts >= timestampBegin) && (ts <= timestampEnd);
-    }
-
-    boolean includesIndex(long index){
-        return (index >= indexBegin) && (index <= indexEnd);
-    }
-    /* (non-Javadoc)
-     * @see java.lang.Object#toString()
-     */
-    @Override
-    public String toString() {
-        return "StreamInputPacketIndexEntry [offsetBytes=" + offsetBytes //$NON-NLS-1$
-                + ", timestampBegin=" + timestampBegin + ", timestampEnd=" //$NON-NLS-1$ //$NON-NLS-2$
-                + timestampEnd + ", indexBegin=" + indexBegin + ", indexEnd=" //$NON-NLS-1$ //$NON-NLS-2$
-                + indexEnd + "]"; //$NON-NLS-1$
-    }
-
-    // ------------------------------------------------------------------------
-    // Getters and Setters
-    // ------------------------------------------------------------------------
-
-    /**
-     * @return the offsetBytes
-     */
-    public long getOffsetBytes() {
-        return offsetBytes;
-    }
-
-    /**
-     * @return the dataOffsetBits
-     */
-    public int getDataOffsetBits() {
-        return dataOffsetBits;
-    }
-
-    /**
-     * @param dataOffsetBits the dataOffsetBits to set
-     */
-    public void setDataOffsetBits(int dataOffsetBits) {
-        this.dataOffsetBits = dataOffsetBits;
-    }
-
-    /**
-     * @return the packetSizeBits
-     */
-    public int getPacketSizeBits() {
-        return packetSizeBits;
-    }
-
-    /**
-     * @param packetSizeBits the packetSizeBits to set
-     */
-    public void setPacketSizeBits(int packetSizeBits) {
-        this.packetSizeBits = packetSizeBits;
-    }
-
-    /**
-     * @return the contentSizeBits
-     */
-    public int getContentSizeBits() {
-        return contentSizeBits;
-    }
-
-    /**
-     * @param contentSizeBits the contentSizeBits to set
-     */
-    public void setContentSizeBits(int contentSizeBits) {
-        this.contentSizeBits = contentSizeBits;
-    }
-
-    /**
-     * @return the timestampBegin
-     */
-    public long getTimestampBegin() {
-        return timestampBegin;
-    }
-
-    /**
-     * @param timestampBegin the timestampBegin to set
-     */
-    public void setTimestampBegin(long timestampBegin) {
-        this.timestampBegin = timestampBegin;
-    }
-
-    /**
-     * @return the timestampEnd
-     */
-    public long getTimestampEnd() {
-        return timestampEnd;
-    }
-
-    /**
-     * @param timestampEnd the timestampEnd to set
-     */
-    public void setTimestampEnd(long timestampEnd) {
-        this.timestampEnd = timestampEnd;
-    }
-
-    /**
-     * @return the indexBegin
-     */
-    public long getIndexBegin() {
-        return indexBegin;
-    }
-
-    /**
-     * @param indexBegin the indexBegin to set
-     */
-    public void setIndexBegin(long indexBegin) {
-        this.indexBegin = indexBegin;
-    }
-
-    /**
-     * @return the indexEnd
-     */
-    public long getIndexEnd() {
-        return indexEnd;
-    }
-
-    /**
-     * @param indexEnd the indexEnd to set
-     */
-    public void setIndexEnd(long indexEnd) {
-        this.indexEnd = indexEnd;
-    }
-}
index cc9f556b51f525b4e332aab9b00a19005217c049..bd6684d1915f0061f47377a7deed301eaddf0a6c 100644 (file)
@@ -19,7 +19,6 @@ import java.util.HashMap;
 
 import org.eclipse.linuxtools.ctf.core.event.EventDeclaration;
 import org.eclipse.linuxtools.ctf.core.event.EventDefinition;
-import org.eclipse.linuxtools.ctf.core.event.io.BitBuffer;
 import org.eclipse.linuxtools.ctf.core.event.types.Definition;
 import org.eclipse.linuxtools.ctf.core.event.types.EnumDefinition;
 import org.eclipse.linuxtools.ctf.core.event.types.IDefinitionScope;
@@ -27,6 +26,8 @@ import org.eclipse.linuxtools.ctf.core.event.types.IntegerDefinition;
 import org.eclipse.linuxtools.ctf.core.event.types.StructDeclaration;
 import org.eclipse.linuxtools.ctf.core.event.types.StructDefinition;
 import org.eclipse.linuxtools.ctf.core.event.types.VariantDefinition;
+import org.eclipse.linuxtools.internal.ctf.core.event.io.BitBuffer;
+import org.eclipse.linuxtools.internal.ctf.core.trace.StreamInputPacketIndexEntry;
 
 /**
  * <b><u>StreamInputPacketReader</u></b>
index 4150c8475f76e2b7df14f826fb37f6135cd5024c..8c421baec19b88a4d64874df5eead8fabdc6bc49 100644 (file)
@@ -16,6 +16,7 @@ import java.util.ListIterator;
 
 import org.eclipse.linuxtools.ctf.core.event.EventDefinition;
 import org.eclipse.linuxtools.ctf.core.event.types.StructDefinition;
+import org.eclipse.linuxtools.internal.ctf.core.trace.StreamInputPacketIndexEntry;
 
 /**
  * <b><u>StreamInputReader</u></b>
diff --git a/org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/ctf/core/trace/StreamInputReaderComparator.java b/org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/ctf/core/trace/StreamInputReaderComparator.java
deleted file mode 100644 (file)
index 1b81e0d..0000000
+++ /dev/null
@@ -1,51 +0,0 @@
-/*******************************************************************************
- * Copyright (c) 2011-2012 Ericsson, Ecole Polytechnique de Montreal and others
- *
- * All rights reserved. This program and the accompanying materials are made
- * available under the terms of the Eclipse Public License v1.0 which
- * accompanies this distribution, and is available at
- * http://www.eclipse.org/legal/epl-v10.html
- *
- * Contributors: Matthew Khouzam - Initial API and implementation
- * Contributors: Simon Marchi - Initial API and implementation
- *******************************************************************************/
-
-package org.eclipse.linuxtools.ctf.core.trace;
-
-import java.io.Serializable;
-import java.util.Comparator;
-
-/**
- * <b><u>StreamInputReaderComparator</u></b>
- * <p>
- * TODO Implement me. Please.
- */
-public class StreamInputReaderComparator implements
-        Comparator<StreamInputReader>, Serializable {
-
-    // ------------------------------------------------------------------------
-    // Constants
-    // ------------------------------------------------------------------------
-
-    private static final long serialVersionUID = 7477206132343139753L;
-
-    // ------------------------------------------------------------------------
-    // Operations
-    // ------------------------------------------------------------------------
-
-    @Override
-    public int compare(StreamInputReader a, StreamInputReader b) {
-        // TODO: use unsigned comparison to avoid sign errors if needed
-        long ta = a.getCurrentEvent().timestamp;
-        long tb = b.getCurrentEvent().timestamp;
-
-        if (ta < tb) {
-            return -1;
-        } else if (ta > tb) {
-            return 1;
-        } else {
-            return 0;
-        }
-    }
-
-}
diff --git a/org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/internal/ctf/core/event/io/BitBuffer.java b/org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/internal/ctf/core/event/io/BitBuffer.java
new file mode 100644 (file)
index 0000000..04e5490
--- /dev/null
@@ -0,0 +1,510 @@
+/*******************************************************************************.
+ * Copyright (c) 2011-2012 Ericsson, Ecole Polytechnique de Montreal and others
+ *
+ * All rights reserved. This program and the accompanying materials are made
+ * available under the terms of the Eclipse Public License v1.0 which
+ * accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors: Matthew Khouzam - Initial Design and implementation
+ * Contributors: Francis Giraldeau - Initial API and implementation
+ *******************************************************************************/
+
+package org.eclipse.linuxtools.internal.ctf.core.event.io;
+
+import java.nio.BufferOverflowException;
+import java.nio.ByteBuffer;
+import java.nio.ByteOrder;
+
+/**
+ * <b><u>BitBuffer</u></b>
+ * <p>
+ * TODO Implement me. Please.
+ */
+public class BitBuffer {
+
+    // ------------------------------------------------------------------------
+    // Constants
+    // ------------------------------------------------------------------------
+
+    /* default bit width */
+    public static final int BIT_CHAR = 8;
+    public static final int BIT_SHORT = 16;
+    public static final int BIT_INT = 32;
+    public static final int BIT_FLOAT = 32;
+    public static final int BIT_LONG = 64;
+
+    // ------------------------------------------------------------------------
+    // Attributes
+    // ------------------------------------------------------------------------
+
+    private ByteBuffer buf;
+    private int pos;
+    private ByteOrder byteOrder;
+
+    // ------------------------------------------------------------------------
+    // Constructors
+    // ------------------------------------------------------------------------
+
+    public BitBuffer() {
+        this(null, ByteOrder.BIG_ENDIAN);
+    }
+
+    public BitBuffer(ByteBuffer buf) {
+        this(buf, ByteOrder.BIG_ENDIAN);
+    }
+
+    public BitBuffer(ByteBuffer buf, ByteOrder order) {
+        setByteBuffer(buf);
+        order(order);
+        position(0);
+    }
+
+    // ------------------------------------------------------------------------
+    // 'Get' operations on buffer
+    // ------------------------------------------------------------------------
+
+    /**
+     * Relative <i>get</i> method for reading 32-bit integer.
+     *
+     * Reads next four bytes from the current bit position according to current
+     * byte order.
+     *
+     * @return The int value read from the buffer
+     */
+    public int getInt() {
+        int val = getInt(BIT_INT, true);
+        pos += BIT_INT;
+        return val;
+    }
+
+    /**
+     * Relative <i>get</i> method for reading integer of <i>length</i> bits.
+     *
+     * Reads <i>length</i> bits starting at the current position. The result is
+     * signed extended if <i>signed</i> is true. The current position is
+     * increased of <i>length</i> bits.
+     *
+     * @param length
+     *            The length in bits of this integer
+     * @param signed
+     *            The sign extended flag
+     * @return The int value read from the buffer
+     */
+    public int getInt(int length, boolean signed) {
+        int val;
+        if (!canRead(pos, length)) {
+            throw new BufferOverflowException();
+        }
+        if (length == 0) {
+            val = 0;
+        }
+        if (byteOrder == ByteOrder.LITTLE_ENDIAN) {
+            val = getIntLE(pos, length, signed);
+        } else {
+            val = getIntBE(pos, length, signed);
+        }
+        pos += length;
+        return val;
+    }
+
+    /**
+     * Absolute <i>get</i> method for reading integer of <i>length</i> bits.
+     *
+     * Reads <i>length</i> bits starting from position <i>index</i>. The result
+     * is signed extended if <i>signed</i> is true. The current position is
+     * increased of <i>length</i> bits.
+     *
+     * @param index
+     *            The start index in bits
+     * @param length
+     *            The length in bits to read
+     * @param signed
+     *            The sign extended flag
+     * @return The int value read from the buffer
+     */
+    public int getInt(int index, int length, boolean signed) {
+        if (!canRead(index, length)) {
+            throw new BufferOverflowException();
+        }
+        if (length == 0) {
+            return 0;
+        }
+        if (byteOrder == ByteOrder.LITTLE_ENDIAN) {
+            return getIntLE(index, length, signed);
+        }
+        return getIntBE(index, length, signed);
+    }
+
+    private int getIntBE(int index, int length, boolean signed) {
+        assert ((length > 0) && (length <= BIT_INT));
+        int end = index + length;
+        int startByte = index / BIT_CHAR;
+        int endByte = (end + (BIT_CHAR - 1)) / BIT_CHAR;
+        int currByte, lshift, cshift, mask, cmask, cache;
+        int value = 0;
+
+        currByte = startByte;
+        cache = buf.get(currByte) & 0xFF;
+        boolean isNeg = (cache & (1 << (BIT_CHAR - (index % BIT_CHAR) - 1))) != 0;
+        if (signed && isNeg) {
+            value = ~0;
+        }
+        if (startByte == (endByte - 1)) {
+            cmask = cache >>> ((BIT_CHAR - (end % BIT_CHAR)) % BIT_CHAR);
+            if (((length) % BIT_CHAR) > 0) {
+                mask = ~((~0) << length);
+                cmask &= mask;
+            }
+            value <<= length;
+            value |= cmask;
+            return value;
+        }
+        cshift = index % BIT_CHAR;
+        if (cshift > 0) {
+            mask = ~((~0) << (BIT_CHAR - cshift));
+            cmask = cache & mask;
+            lshift = BIT_CHAR - cshift;
+            value <<= lshift;
+            value |= cmask;
+            // index += lshift;
+            currByte++;
+        }
+        for (; currByte < (endByte - 1); currByte++) {
+            value <<= BIT_CHAR;
+            value |= buf.get(currByte) & 0xFF;
+        }
+        lshift = end % BIT_CHAR;
+        if (lshift > 0) {
+            mask = ~((~0) << lshift);
+            cmask = buf.get(currByte) & 0xFF;
+            cmask >>>= BIT_CHAR - lshift;
+            cmask &= mask;
+            value <<= lshift;
+            value |= cmask;
+        } else {
+            value <<= BIT_CHAR;
+            value |= buf.get(currByte) & 0xFF;
+        }
+        return value;
+    }
+
+    private int getIntLE(int index, int length, boolean signed) {
+        assert ((length > 0) && (length <= BIT_INT));
+        int end = index + length;
+        int startByte = index / BIT_CHAR;
+        int endByte = (end + (BIT_CHAR - 1)) / BIT_CHAR;
+        int currByte, lshift, cshift, mask, cmask, cache, mod;
+        int value = 0;
+
+        currByte = endByte - 1;
+        cache = buf.get(currByte) & 0xFF;
+        mod = end % BIT_CHAR;
+        lshift = (mod > 0) ? mod : BIT_CHAR;
+        boolean isNeg = (cache & (1 << (lshift - 1))) != 0;
+        if (signed && isNeg) {
+            value = ~0;
+        }
+        if (startByte == (endByte - 1)) {
+            cmask = cache >>> (index % BIT_CHAR);
+            if (((length) % BIT_CHAR) > 0) {
+                mask = ~((~0) << length);
+                cmask &= mask;
+            }
+            value <<= length;
+            value |= cmask;
+            return value;
+        }
+        cshift = end % BIT_CHAR;
+        if (cshift > 0) {
+            mask = ~((~0) << cshift);
+            cmask = cache & mask;
+            value <<= cshift;
+            value |= cmask;
+            // end -= cshift;
+            currByte--;
+        }
+        for (; currByte >= (startByte + 1); currByte--) {
+            value <<= BIT_CHAR;
+            value |= buf.get(currByte) & 0xFF;
+        }
+        lshift = index % BIT_CHAR;
+        if (lshift > 0) {
+            mask = ~((~0) << (BIT_CHAR - lshift));
+            cmask = buf.get(currByte) & 0xFF;
+            cmask >>>= lshift;
+            cmask &= mask;
+            value <<= (BIT_CHAR - lshift);
+            value |= cmask;
+        } else {
+            value <<= BIT_CHAR;
+            value |= buf.get(currByte) & 0xFF;
+        }
+        return value;
+    }
+
+    // ------------------------------------------------------------------------
+    // 'Put' operations on buffer
+    // ------------------------------------------------------------------------
+
+    /**
+     * Relative <i>put</i> method to write signed 32-bit integer.
+     *
+     * Write four bytes starting from current bit position in the buffer
+     * according to the current byte order. The current position is increased of
+     * <i>length</i> bits.
+     *
+     * @param value
+     *            The int value to write
+     */
+    public void putInt(int value) {
+        putInt(BIT_INT, value);
+    }
+
+    /**
+     * Relative <i>put</i> method to write <i>length</i> bits integer.
+     *
+     * Writes <i>length</i> lower-order bits from the provided <i>value</i>,
+     * starting from current bit position in the buffer. Sequential bytes are
+     * written according to the current byte order. The sign bit is carried to
+     * the MSB if signed is true. The sign bit is included in <i>length</i>. The
+     * current position is increased of <i>length</i>.
+     *
+     * @param length
+     *            The number of bits to write
+     * @param value
+     *            The value to write
+     */
+    public void putInt(int length, int value) {
+        putInt(this.pos, length, value);
+    }
+
+    /**
+     * Absolute <i>put</i> method to write <i>length</i> bits integer.
+     *
+     * Writes <i>length</i> lower-order bits from the provided <i>value</i>,
+     * starting from <i>index</i> position in the buffer. Sequential bytes are
+     * written according to the current byte order. The sign bit is carried to
+     * the MSB if signed is true. The sign bit is included in <i>length</i>. The
+     * current position is increased of <i>length</i>.
+     *
+     * @param index
+     *            The start position to write the value
+     * @param value
+     *            The value to write
+     * @param length
+     *            The number of bits to write
+     */
+    public void putInt(int index, int length, int value) {
+        if (!canRead(index, length)) {
+            throw new BufferOverflowException();
+        }
+        if (length == 0) {
+            return;
+        }
+        if (byteOrder == ByteOrder.LITTLE_ENDIAN) {
+            putIntLE(index, length, value);
+        } else {
+            putIntBE(index, length, value);
+        }
+    }
+
+    private void putIntBE(int index, int length, int value) {
+        assert ((length > 0) && (length <= BIT_INT));
+        int end = index + length;
+        int startByte = index / BIT_CHAR;
+        int endByte = (end + (BIT_CHAR - 1)) / BIT_CHAR;
+        int currByte, lshift, cshift, mask, cmask;
+        int correctedValue = value;
+
+        /*
+         * mask v high bits. Works for unsigned and two complement signed
+         * numbers which value do not overflow on length bits.
+         */
+
+        if (length < BIT_INT) {
+            correctedValue &= ~(~0 << length);
+        }
+
+        /* sub byte */
+        if (startByte == (endByte - 1)) {
+            lshift = (BIT_CHAR - (end % BIT_CHAR)) % BIT_CHAR;
+            mask = ~((~0) << lshift);
+            if ((index % BIT_CHAR) > 0) {
+                mask |= (~(0)) << (BIT_CHAR - (index % BIT_CHAR));
+            }
+            cmask = correctedValue << lshift;
+            /*
+             * low bits are cleared because of lshift and high bits are already
+             * cleared
+             */
+            cmask &= ~mask;
+            int b = buf.get(startByte) & 0xFF;
+            buf.put(startByte, (byte) ((b & mask) | cmask));
+            return;
+        }
+
+        /* head byte contains MSB */
+        currByte = endByte - 1;
+        cshift = end % BIT_CHAR;
+        if (cshift > 0) {
+            lshift = BIT_CHAR - cshift;
+            mask = ~((~0) << lshift);
+            cmask = correctedValue << lshift;
+            cmask &= ~mask;
+            int b = buf.get(currByte) & 0xFF;
+            buf.put(currByte, (byte) ((b & mask) | cmask));
+            correctedValue >>>= cshift;
+            // end -= cshift;
+            currByte--;
+        }
+
+        /* middle byte(s) */
+        for (; currByte >= (startByte + 1); currByte--) {
+            buf.put(currByte, (byte) correctedValue);
+            correctedValue >>>= BIT_CHAR;
+        }
+        /* end byte contains LSB */
+        if ((index % BIT_CHAR) > 0) {
+            mask = (~0) << (BIT_CHAR - (index % BIT_CHAR));
+            cmask = correctedValue & ~mask;
+            int b = buf.get(currByte) & 0xFF;
+            buf.put(currByte, (byte) ((b & mask) | cmask));
+        } else {
+            buf.put(currByte, (byte) correctedValue);
+        }
+    }
+
+    private void putIntLE(int index, int length, int value) {
+        assert ((length > 0) && (length <= BIT_INT));
+        int end = index + length;
+        int startByte = index / BIT_CHAR;
+        int endByte = (end + (BIT_CHAR - 1)) / BIT_CHAR;
+        int currByte, lshift, cshift, mask, cmask;
+        int correctedValue = value;
+
+        /*
+         * mask v high bits. Works for unsigned and two complement signed
+         * numbers which value do not overflow on length bits.
+         */
+
+        if (length < BIT_INT) {
+            correctedValue &= ~(~0 << length);
+        }
+
+        /* sub byte */
+        if (startByte == (endByte - 1)) {
+            lshift = index % BIT_CHAR;
+            mask = ~((~0) << lshift);
+            if ((end % BIT_CHAR) > 0) {
+                mask |= (~(0)) << (end % BIT_CHAR);
+            }
+            cmask = correctedValue << lshift;
+            /*
+             * low bits are cleared because of lshift and high bits are already
+             * cleared
+             */
+            cmask &= ~mask;
+            int b = buf.get(startByte) & 0xFF;
+            buf.put(startByte, (byte) ((b & mask) | cmask));
+            return;
+        }
+
+        /* head byte */
+        currByte = startByte;
+        cshift = index % BIT_CHAR;
+        if (cshift > 0) {
+            mask = ~((~0) << cshift);
+            cmask = correctedValue << cshift;
+            cmask &= ~mask;
+            int b = buf.get(currByte) & 0xFF;
+            buf.put(currByte, (byte) ((b & mask) | cmask));
+            correctedValue >>>= BIT_CHAR - cshift;
+            // index += BIT_CHAR - cshift;
+            currByte++;
+        }
+
+        /* middle byte(s) */
+        for (; currByte < (endByte - 1); currByte++) {
+            buf.put(currByte, (byte) correctedValue);
+            correctedValue >>>= BIT_CHAR;
+        }
+        /* end byte */
+        if ((end % BIT_CHAR) > 0) {
+            mask = (~0) << (end % BIT_CHAR);
+            cmask = correctedValue & ~mask;
+            int b = buf.get(currByte) & 0xFF;
+            buf.put(currByte, (byte) ((b & mask) | cmask));
+        } else {
+            buf.put(currByte, (byte) correctedValue);
+        }
+    }
+
+    // ------------------------------------------------------------------------
+    // Buffer attributes handling
+    // ------------------------------------------------------------------------
+
+    public boolean canRead(int length) {
+        return canRead(pos, length);
+    }
+
+    public boolean canRead(int index, int length) {
+        if (buf == null) {
+            return false;
+        }
+
+        if ((index + length) > (buf.capacity() * BIT_CHAR)) {
+            return false;
+        }
+        return true;
+    }
+
+    public void order(ByteOrder order) {
+        this.byteOrder = order;
+        if (buf != null) {
+            buf.order(order);
+        }
+    }
+
+    public ByteOrder order() {
+        return byteOrder;
+    }
+
+    public void position(int newPosition) {
+        this.pos = newPosition;
+    }
+
+    public int position() {
+        return pos;
+    }
+
+    public void setByteBuffer(ByteBuffer buf) {
+        this.buf = buf;
+        if (buf != null) {
+            this.buf.order(byteOrder);
+        }
+        clear();
+    }
+
+    public ByteBuffer getByteBuffer() {
+        return buf;
+    }
+
+    public void setByteOrder(ByteOrder byteOrder) {
+        this.byteOrder = byteOrder;
+    }
+
+    public ByteOrder getByteOrder() {
+        return byteOrder;
+    }
+
+    public void clear() {
+        position(0);
+
+        if (buf == null) {
+            return;
+        }
+        buf.clear();
+    }
+
+}
diff --git a/org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/internal/ctf/core/event/metadata/IOStructGen.java b/org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/internal/ctf/core/event/metadata/IOStructGen.java
new file mode 100644 (file)
index 0000000..e6e9e47
--- /dev/null
@@ -0,0 +1,2724 @@
+/*******************************************************************************
+ * Copyright (c) 2011-2012 Ericsson, Ecole Polytechnique de Montreal and others
+ *
+ * All rights reserved. This program and the accompanying materials are made
+ * available under the terms of the Eclipse Public License v1.0 which
+ * accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors: Matthew Khouzam - Initial Design and Grammar
+ * Contributors: Francis Giraldeau - Initial API and implementation
+ *******************************************************************************/
+
+package org.eclipse.linuxtools.internal.ctf.core.event.metadata;
+
+import java.io.FileNotFoundException;
+import java.io.IOException;
+import java.io.UnsupportedEncodingException;
+import java.nio.ByteOrder;
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.LinkedList;
+import java.util.List;
+import java.util.UUID;
+
+import org.antlr.runtime.tree.CommonTree;
+import org.eclipse.linuxtools.ctf.core.event.CTFClock;
+import org.eclipse.linuxtools.ctf.core.event.EventDeclaration;
+import org.eclipse.linuxtools.ctf.core.event.metadata.DeclarationScope;
+import org.eclipse.linuxtools.ctf.core.event.metadata.exceptions.ParseException;
+import org.eclipse.linuxtools.ctf.core.event.types.ArrayDeclaration;
+import org.eclipse.linuxtools.ctf.core.event.types.Encoding;
+import org.eclipse.linuxtools.ctf.core.event.types.EnumDeclaration;
+import org.eclipse.linuxtools.ctf.core.event.types.IDeclaration;
+import org.eclipse.linuxtools.ctf.core.event.types.IntegerDeclaration;
+import org.eclipse.linuxtools.ctf.core.event.types.SequenceDeclaration;
+import org.eclipse.linuxtools.ctf.core.event.types.StringDeclaration;
+import org.eclipse.linuxtools.ctf.core.event.types.StructDeclaration;
+import org.eclipse.linuxtools.ctf.core.event.types.VariantDeclaration;
+import org.eclipse.linuxtools.ctf.core.trace.CTFTrace;
+import org.eclipse.linuxtools.ctf.core.trace.Stream;
+import org.eclipse.linuxtools.ctf.parser.CTFParser;
+import org.eclipse.linuxtools.internal.ctf.core.Activator;
+
+/*
+ * Asserts throughout this class denote the assumptions we can make because of
+ * the way the grammar generates the AST.
+ *
+ * There is also an assert at the beginning of each function that receives a
+ * tree node to make sure that the node is indeed of the type the function is
+ * expecting.
+ */
+/*
+ * Suppress unchecked warnings for things like List<CommonTree> children =
+ * root.getChildren(), because ANTLR doesn't know what generics are.
+ */
+/**
+ * <b><u>IOStructGen</u></b>
+ */
+@SuppressWarnings("unchecked")
+public class IOStructGen {
+
+    // ------------------------------------------------------------------------
+    // Attributes
+    // ------------------------------------------------------------------------
+
+    static private final boolean DEBUG_ = false;
+
+    /**
+     * The trace
+     */
+    private final CTFTrace trace;
+    private final CommonTree tree;
+
+    /**
+     * The current declaration scope.
+     */
+    private DeclarationScope scope = null;
+
+    // ------------------------------------------------------------------------
+    // Constructor
+    // ------------------------------------------------------------------------
+
+    public IOStructGen(CommonTree tree, CTFTrace trace) {
+        this.trace = trace;
+        this.tree = tree;
+    }
+
+    public void generate() throws ParseException {
+        parseRoot(tree);
+    }
+
+    // ------------------------------------------------------------------------
+    // Operations
+    // ------------------------------------------------------------------------
+
+    /**
+     * Parse the root node.
+     *
+     * @param root
+     *            A ROOT node.
+     * @throws ParseException
+     */
+    private void parseRoot(CommonTree root) throws ParseException {
+        assert (root.getType() == CTFParser.ROOT);
+
+        List<CommonTree> children = root.getChildren();
+        assert (children != null);
+        java.io.FileOutputStream fos = null;
+        java.io.OutputStreamWriter out = null;
+        if (DEBUG_) {
+            try {
+                fos = new java.io.FileOutputStream("/tmp/astInfo.txt"); //$NON-NLS-1$
+                out = new java.io.OutputStreamWriter(fos, "UTF-8"); //$NON-NLS-1$
+            } catch (FileNotFoundException e) {
+                e.printStackTrace();
+                return;
+            } catch (UnsupportedEncodingException e) {
+                e.printStackTrace();
+                return;
+            }
+        }
+
+        CommonTree traceNode = null;
+        List<CommonTree> streams = new ArrayList<CommonTree>();
+        List<CommonTree> events = new ArrayList<CommonTree>();
+        List<CommonTree> declarations = new ArrayList<CommonTree>();
+        List<CommonTree> environments = new ArrayList<CommonTree>();
+        List<CommonTree> clocks = new ArrayList<CommonTree>();
+        /* Create a new declaration scope with no parent. */
+        pushScope();
+
+        try {
+            for (CommonTree child : children) {
+                if (DEBUG_) {
+                    out.write(child.toString()
+                            + " -> " + child.getType() + '\n'); //$NON-NLS-1$
+                }
+                switch (child.getType()) {
+                case CTFParser.DECLARATION:
+                    declarations.add(child);
+                    break;
+                case CTFParser.TRACE:
+                    if (traceNode != null) {
+                        throw new ParseException(
+                                "Only one trace block is allowed"); //$NON-NLS-1$
+                    }
+                    traceNode = child;
+                    break;
+                case CTFParser.STREAM:
+                    streams.add(child);
+                    break;
+                case CTFParser.EVENT:
+                    events.add(child);
+                    break;
+                case CTFParser.CLOCK:
+                    clocks.add(child);
+                    break;
+                case CTFParser.ENV:
+                    environments.add(child);
+                    break;
+                default:
+                    childTypeError(child);
+                }
+            }
+
+            if (DEBUG_) {
+                out.write("Environments\n"); //$NON-NLS-1$
+            }
+            for (CommonTree environment : environments) {
+                parseEnvironment(environment);
+            }
+            if (DEBUG_) {
+                out.write("Clocks\n"); //$NON-NLS-1$
+            }
+            for (CommonTree clock : clocks) {
+                parseClock(clock);
+            }
+            if (DEBUG_) {
+                out.write("Declarations\n"); //$NON-NLS-1$
+            }
+            for (CommonTree decl : declarations) {
+                if (DEBUG_) {
+                    out.write(decl.toString() + '\n');
+                }
+                parseRootDeclaration(decl);
+            }
+
+            if (traceNode == null) {
+                throw new ParseException("Missing trace block"); //$NON-NLS-1$
+            }
+
+            parseTrace(traceNode);
+
+            if (DEBUG_) {
+                out.write("Streams\n"); //$NON-NLS-1$
+            }
+            if (streams.size() > 0) {
+                for (CommonTree stream : streams) {
+                    if (DEBUG_) {
+                        try {
+                            out.write(stream.toString() + '\n');
+                        } catch (IOException e) {
+                            e.printStackTrace();
+                        }
+                    }
+                    parseStream(stream);
+                }
+            } else {
+                /* Add an empty stream that will have a null id */
+                trace.addStream(new Stream(trace));
+            }
+
+            if (DEBUG_) {
+                out.write("Events\n"); //$NON-NLS-1$
+            }
+            for (CommonTree event : events) {
+                parseEvent(event);
+                CommonTree name = (CommonTree) event.getChild(0).getChild(1)
+                        .getChild(0).getChild(0);
+                if (DEBUG_) {
+                    out.write("Name = " + name); //$NON-NLS-1$
+                }
+                CommonTree id = (CommonTree) event.getChild(1).getChild(1)
+                        .getChild(0).getChild(0);
+                if (DEBUG_) {
+                    out.write("Name = " + name + " Id = " + id + '\n'); //$NON-NLS-1$ //$NON-NLS-2$
+                }
+            }
+
+            if (DEBUG_) {
+                out.close();
+                fos.close();
+            }
+        } catch (IOException e) {
+            e.printStackTrace();
+        }
+        popScope();
+    }
+
+    private void parseEnvironment(CommonTree environment) {
+        List<CommonTree> children = environment.getChildren();
+        for (CommonTree child : children) {
+            String left;
+            String right;
+            left = child.getChild(0).getChild(0).getChild(0).getText();
+            right = child.getChild(1).getChild(0).getChild(0).getText();
+            trace.addEnvironmentVar(left, right);
+        }
+    }
+
+    private void parseClock(CommonTree clock) {
+        List<CommonTree> children = clock.getChildren();
+        CTFClock ctfClock = new CTFClock();
+        for (CommonTree child : children) {
+            final String key = child.getChild(0).getChild(0).getChild(0)
+                    .getText();
+            final CommonTree value = (CommonTree) child.getChild(1).getChild(0).getChild(0);
+            final int type = value.getType();
+            switch (type) {
+            case CTFParser.INTEGER:
+            case CTFParser.DECIMAL_LITERAL:
+                /*
+                 * Not a pretty hack, this is to make sure that there is no number
+                 * overflow due to 63 bit integers. The offset should only really
+                 * be an issue in the year 2262. the tracer in C/ASM can write an offset in
+                 * an unsigned 64 bit long. In java, the last bit, being set to 1 will
+                 * be read as a negative number, but since it is too big a positive it will
+                 * throw an exception. this will happen in 2^63 ns from 1970.
+                 * Therefore 293 years from 1970
+                 */
+                Long numValue;
+                try{
+                    numValue = Long.parseLong(value.getText());
+                }
+                catch( Exception e)
+                {
+                    numValue = 1330938566783103277L;
+                }
+                ctfClock.addAttribute(key, numValue);
+                break;
+            default:
+                ctfClock.addAttribute(key, value.getText());
+            }
+
+        }
+        String NameValue = ctfClock.getName();
+        trace.addClock(NameValue, ctfClock);
+    }
+
+    private void parseTrace(CommonTree traceNode) throws ParseException {
+        assert (traceNode.getType() == CTFParser.TRACE);
+
+        List<CommonTree> children = traceNode.getChildren();
+        if (children == null) {
+            throw new ParseException("Trace block is empty"); //$NON-NLS-1$
+        }
+
+        pushScope();
+
+        for (CommonTree child : children) {
+            switch (child.getType()) {
+            case CTFParser.TYPEALIAS:
+                parseTypealias(child);
+                break;
+            case CTFParser.TYPEDEF:
+                parseTypedef(child);
+                break;
+            case CTFParser.CTF_EXPRESSION_TYPE:
+            case CTFParser.CTF_EXPRESSION_VAL:
+                parseTraceDeclaration(child);
+                break;
+            default:
+                childTypeError(child);
+                break;
+            }
+        }
+
+        /*
+         * If trace byte order was not specified and not using packet based
+         * metadata
+         */
+        if (trace.getByteOrder() == null) {
+            throw new ParseException("Trace byte order not set"); //$NON-NLS-1$
+        }
+
+        popScope();
+    }
+
+    private void parseTraceDeclaration(CommonTree traceDecl)
+            throws ParseException {
+        assert ((traceDecl.getType() == CTFParser.CTF_EXPRESSION_TYPE) || (traceDecl
+                .getType() == CTFParser.CTF_EXPRESSION_VAL));
+
+        /* There should be a left and right */
+        assert (traceDecl.getChildCount() == 2);
+
+        CommonTree leftNode = (CommonTree) traceDecl.getChild(0);
+        assert (leftNode.getType() == CTFParser.CTF_LEFT);
+        CommonTree rightNode = (CommonTree) traceDecl.getChild(1);
+        assert (rightNode.getType() == CTFParser.CTF_RIGHT);
+
+        List<CommonTree> leftStrings = leftNode.getChildren();
+        assert (leftStrings != null);
+
+        if (!isUnaryString(leftStrings.get(0))) {
+            throw new ParseException(
+                    "Left side of CTF assignment must be a string"); //$NON-NLS-1$
+        }
+
+        String left = concatenateUnaryStrings(leftStrings);
+
+        if (left.equals("major")) { //$NON-NLS-1$
+            if (trace.majortIsSet()) {
+                throw new ParseException("major is already set"); //$NON-NLS-1$
+            }
+
+            trace.setMajor(getMajorOrMinor(rightNode));
+        } else if (left.equals("minor")) { //$NON-NLS-1$
+            if (trace.minorIsSet()) {
+                throw new ParseException("minor is already set"); //$NON-NLS-1$
+            }
+
+            trace.setMinor(getMajorOrMinor(rightNode));
+        } else if (left.equals("uuid")) { //$NON-NLS-1$
+            UUID uuid = getUUID(rightNode);
+
+            /*
+             * If uuid was already set by a metadata packet, compare it to see
+             * if it matches
+             */
+            if (trace.UUIDIsSet()) {
+                if (trace.getUUID().compareTo(uuid) != 0) {
+                    throw new ParseException("UUID mismatch. Packet says " //$NON-NLS-1$
+                            + trace.getUUID() + " but metadata says " + uuid); //$NON-NLS-1$
+                }
+            } else {
+                trace.setUUID(uuid);
+            }
+
+        } else if (left.equals("byte_order")) { //$NON-NLS-1$
+            ByteOrder byteOrder = getByteOrder(rightNode);
+
+            /*
+             * If byte order was already set by a metadata packet, compare it to
+             * see if it matches
+             */
+            if (trace.getByteOrder() != null) {
+                if (trace.getByteOrder() != byteOrder) {
+                    throw new ParseException(
+                            "Endianness mismatch. Magic number says " //$NON-NLS-1$
+                                    + trace.getByteOrder()
+                                    + " but metadata says " + byteOrder); //$NON-NLS-1$
+                }
+            } else {
+                trace.setByteOrder(byteOrder);
+            }
+        } else if (left.equals("packet.header")) { //$NON-NLS-1$
+            if (trace.packetHeaderIsSet()) {
+                throw new ParseException("packet.header already defined"); //$NON-NLS-1$
+            }
+
+            CommonTree typeSpecifier = (CommonTree) rightNode.getChild(0);
+
+            if (typeSpecifier.getType() != CTFParser.TYPE_SPECIFIER_LIST) {
+                throw new ParseException(
+                        "packet.header expects a type specifier"); //$NON-NLS-1$
+            }
+
+            IDeclaration packetHeaderDecl = parseTypeSpecifierList(
+                    typeSpecifier, null);
+
+            if (!(packetHeaderDecl instanceof StructDeclaration)) {
+                throw new ParseException("packet.header expects a struct"); //$NON-NLS-1$
+            }
+
+            trace.setPacketHeader((StructDeclaration) packetHeaderDecl);
+        } else {
+            throw new ParseException("Unknown trace attribute : " + left); //$NON-NLS-1$
+        }
+    }
+
+    private void parseStream(CommonTree streamNode) throws ParseException {
+        assert (streamNode.getType() == CTFParser.STREAM);
+
+        Stream stream = new Stream(trace);
+
+        List<CommonTree> children = streamNode.getChildren();
+        if (children == null) {
+            throw new ParseException("Empty stream block"); //$NON-NLS-1$
+        }
+
+        pushScope();
+
+        for (CommonTree child : children) {
+            switch (child.getType()) {
+            case CTFParser.TYPEALIAS:
+                parseTypealias(child);
+                break;
+            case CTFParser.TYPEDEF:
+                parseTypedef(child);
+                break;
+            case CTFParser.CTF_EXPRESSION_TYPE:
+            case CTFParser.CTF_EXPRESSION_VAL:
+                parseStreamDeclaration(child, stream);
+                break;
+            default:
+                childTypeError(child);
+                break;
+            }
+        }
+
+        if (stream.idIsSet()) {
+            if (!trace.packetHeaderIsSet()
+                    || !trace.getPacketHeader().hasField("stream_id")) { //$NON-NLS-1$
+                throw new ParseException(
+                        "Stream has an ID, but there is no stream_id field in packet header."); //$NON-NLS-1$
+            }
+        }
+
+        trace.addStream(stream);
+
+        popScope();
+    }
+
+    private void parseStreamDeclaration(CommonTree streamDecl, Stream stream)
+            throws ParseException {
+        assert ((streamDecl.getType() == CTFParser.CTF_EXPRESSION_TYPE) || (streamDecl
+                .getType() == CTFParser.CTF_EXPRESSION_VAL));
+
+        /* There should be a left and right */
+        assert (streamDecl.getChildCount() == 2);
+
+        CommonTree leftNode = (CommonTree) streamDecl.getChild(0);
+        assert (leftNode.getType() == CTFParser.CTF_LEFT);
+        CommonTree rightNode = (CommonTree) streamDecl.getChild(1);
+        assert (rightNode.getType() == CTFParser.CTF_RIGHT);
+
+        List<CommonTree> leftStrings = leftNode.getChildren();
+        assert (leftStrings != null);
+
+        if (!isUnaryString(leftStrings.get(0))) {
+            throw new ParseException(
+                    "Left side of CTF assignment must be a string"); //$NON-NLS-1$
+        }
+
+        String left = concatenateUnaryStrings(leftStrings);
+
+        if (left.equals("id")) { //$NON-NLS-1$
+            if (stream.idIsSet()) {
+                throw new ParseException("stream id already defined"); //$NON-NLS-1$
+            }
+
+            long streamID = getStreamID(rightNode);
+
+            stream.setId(streamID);
+        } else if (left.equals("event.header")) { //$NON-NLS-1$
+            if (stream.eventHeaderIsSet()) {
+                throw new ParseException("event.header already defined"); //$NON-NLS-1$
+            }
+
+            CommonTree typeSpecifier = (CommonTree) rightNode.getChild(0);
+
+            if (typeSpecifier.getType() != CTFParser.TYPE_SPECIFIER_LIST) {
+                throw new ParseException(
+                        "event.header expects a type specifier"); //$NON-NLS-1$
+            }
+
+            IDeclaration eventHeaderDecl = parseTypeSpecifierList(
+                    typeSpecifier, null);
+
+            if (!(eventHeaderDecl instanceof StructDeclaration)) {
+                throw new ParseException("event.header expects a struct"); //$NON-NLS-1$
+            }
+
+            stream.setEventHeader((StructDeclaration) eventHeaderDecl);
+        } else if (left.equals("event.context")) { //$NON-NLS-1$
+            if (stream.eventContextIsSet()) {
+                throw new ParseException("event.context already defined"); //$NON-NLS-1$
+            }
+
+            CommonTree typeSpecifier = (CommonTree) rightNode.getChild(0);
+
+            if (typeSpecifier.getType() != CTFParser.TYPE_SPECIFIER_LIST) {
+                throw new ParseException(
+                        "event.context expects a type specifier"); //$NON-NLS-1$
+            }
+
+            IDeclaration eventContextDecl = parseTypeSpecifierList(
+                    typeSpecifier, null);
+
+            if (!(eventContextDecl instanceof StructDeclaration)) {
+                throw new ParseException("event.context expects a struct"); //$NON-NLS-1$
+            }
+
+            stream.setEventContext((StructDeclaration) eventContextDecl);
+        } else if (left.equals("packet.context")) { //$NON-NLS-1$
+            if (stream.packetContextIsSet()) {
+                throw new ParseException("packet.context already defined"); //$NON-NLS-1$
+            }
+
+            CommonTree typeSpecifier = (CommonTree) rightNode.getChild(0);
+
+            if (typeSpecifier.getType() != CTFParser.TYPE_SPECIFIER_LIST) {
+                throw new ParseException(
+                        "packet.context expects a type specifier"); //$NON-NLS-1$
+            }
+
+            IDeclaration packetContextDecl = parseTypeSpecifierList(
+                    typeSpecifier, null);
+
+            if (!(packetContextDecl instanceof StructDeclaration)) {
+                throw new ParseException("packet.context expects a struct"); //$NON-NLS-1$
+            }
+
+            stream.setPacketContext((StructDeclaration) packetContextDecl);
+        } else {
+            throw new ParseException("Unknown stream attribute : " + left); //$NON-NLS-1$
+        }
+    }
+
+    private void parseEvent(CommonTree eventNode) throws ParseException {
+        assert (eventNode.getType() == CTFParser.EVENT);
+
+        List<CommonTree> children = eventNode.getChildren();
+        if (children == null) {
+            throw new ParseException("Empty event block"); //$NON-NLS-1$
+        }
+
+        EventDeclaration event = new EventDeclaration();
+
+        pushScope();
+
+        for (CommonTree child : children) {
+            switch (child.getType()) {
+            case CTFParser.TYPEALIAS:
+                parseTypealias(child);
+                break;
+            case CTFParser.TYPEDEF:
+                parseTypedef(child);
+                break;
+            case CTFParser.CTF_EXPRESSION_TYPE:
+            case CTFParser.CTF_EXPRESSION_VAL:
+                parseEventDeclaration(child, event);
+                break;
+            default:
+                childTypeError(child);
+                break;
+            }
+        }
+
+        if (!event.nameIsSet()) {
+            throw new ParseException("Event name not set"); //$NON-NLS-1$
+        }
+
+        /*
+         * If the event did not specify a stream, then the trace must be single
+         * stream
+         */
+        if (!event.streamIsSet()) {
+            if (trace.nbStreams() > 1) {
+                throw new ParseException(
+                        "Event without stream_id with more than one stream"); //$NON-NLS-1$
+            }
+
+            /*
+             * If the event did not specify a stream, the only existing stream
+             * must not have an id. Note: That behavior could be changed, it
+             * could be possible to just get the only existing stream, whatever
+             * is its id.
+             */
+            Stream stream = trace.getStream(null);
+
+            if (stream != null) {
+                event.setStream(stream);
+            } else {
+                throw new ParseException(
+                        "Event without stream_id, but there is no stream without id"); //$NON-NLS-1$
+            }
+        }
+
+        /*
+         * Add the event to the stream.
+         */
+        event.getStream().addEvent(event);
+
+        popScope();
+    }
+
+    private void parseEventDeclaration(CommonTree eventDecl,
+            EventDeclaration event) throws ParseException {
+        assert ((eventDecl.getType() == CTFParser.CTF_EXPRESSION_TYPE) || (eventDecl
+                .getType() == CTFParser.CTF_EXPRESSION_VAL));
+
+        /* There should be a left and right */
+        assert (eventDecl.getChildCount() == 2);
+
+        CommonTree leftNode = (CommonTree) eventDecl.getChild(0);
+        assert (leftNode.getType() == CTFParser.CTF_LEFT);
+        CommonTree rightNode = (CommonTree) eventDecl.getChild(1);
+        assert (rightNode.getType() == CTFParser.CTF_RIGHT);
+
+        List<CommonTree> leftStrings = leftNode.getChildren();
+        assert (leftStrings != null);
+
+        if (!isUnaryString(leftStrings.get(0))) {
+            throw new ParseException(
+                    "Left side of CTF assignment must be a string"); //$NON-NLS-1$
+        }
+
+        String left = concatenateUnaryStrings(leftStrings);
+
+        if (left.equals("name")) { //$NON-NLS-1$
+            if (event.nameIsSet()) {
+                throw new ParseException("name already defined"); //$NON-NLS-1$
+            }
+
+            String name = getEventName(rightNode);
+
+            event.setName(name);
+        } else if (left.equals("id")) { //$NON-NLS-1$
+            if (event.idIsSet()) {
+                throw new ParseException("id already defined"); //$NON-NLS-1$
+            }
+
+            long id = getEventID(rightNode);
+
+            event.setId(id);
+        } else if (left.equals("stream_id")) { //$NON-NLS-1$
+            if (event.streamIsSet()) {
+                throw new ParseException("stream id already defined"); //$NON-NLS-1$
+            }
+
+            long streamId = getStreamID(rightNode);
+
+            Stream stream = trace.getStream(streamId);
+
+            if (stream == null) {
+                throw new ParseException("Stream " + streamId + " not found"); //$NON-NLS-1$ //$NON-NLS-2$
+            }
+
+            event.setStream(stream);
+        } else if (left.equals("context")) { //$NON-NLS-1$
+            if (event.contextIsSet()) {
+                throw new ParseException("context already defined"); //$NON-NLS-1$
+            }
+
+            CommonTree typeSpecifier = (CommonTree) rightNode.getChild(0);
+
+            if (typeSpecifier.getType() != CTFParser.TYPE_SPECIFIER_LIST) {
+                throw new ParseException("context expects a type specifier"); //$NON-NLS-1$
+            }
+
+            IDeclaration contextDecl = parseTypeSpecifierList(typeSpecifier,
+                    null);
+
+            if (!(contextDecl instanceof StructDeclaration)) {
+                throw new ParseException("context expects a struct"); //$NON-NLS-1$
+            }
+
+            event.setContext((StructDeclaration) contextDecl);
+        } else if (left.equals("fields")) { //$NON-NLS-1$
+            if (event.fieldsIsSet()) {
+                throw new ParseException("fields already defined"); //$NON-NLS-1$
+            }
+
+            CommonTree typeSpecifier = (CommonTree) rightNode.getChild(0);
+
+            if (typeSpecifier.getType() != CTFParser.TYPE_SPECIFIER_LIST) {
+                throw new ParseException("fields expects a type specifier"); //$NON-NLS-1$
+            }
+
+            IDeclaration fieldsDecl;
+            fieldsDecl = parseTypeSpecifierList(typeSpecifier, null);
+
+            if (!(fieldsDecl instanceof StructDeclaration)) {
+                throw new ParseException("fields expects a struct"); //$NON-NLS-1$
+            }
+            /*
+             * The underscores in the event names.
+             * These underscores were added by the LTTng tracer.
+             */
+            final StructDeclaration fields = (StructDeclaration) fieldsDecl;
+            event.setFields(fields);
+
+        } else {
+            throw new ParseException("Unknown event attribute : " + left); //$NON-NLS-1$
+        }
+    }
+
+    /**
+     * Parses a declaration at the root level.
+     *
+     * @param declaration
+     *            The declaration subtree.
+     * @throws ParseException
+     */
+    private void parseRootDeclaration(CommonTree declaration)
+            throws ParseException {
+        assert (declaration.getType() == CTFParser.DECLARATION);
+
+        List<CommonTree> children = declaration.getChildren();
+        assert (children != null);
+
+        for (CommonTree child : children) {
+            switch (child.getType()) {
+            case CTFParser.TYPEDEF:
+                parseTypedef(child);
+                break;
+            case CTFParser.TYPEALIAS:
+                parseTypealias(child);
+                break;
+            case CTFParser.TYPE_SPECIFIER_LIST:
+                parseTypeSpecifierList(child, null);
+                break;
+            default:
+                childTypeError(child);
+            }
+        }
+    }
+
+    /**
+     * Parses a typealias node. It parses the target, the alias, and registers
+     * the type in the current scope.
+     *
+     * @param typealias
+     *            A TYPEALIAS node.
+     * @throws ParseException
+     */
+    private void parseTypealias(CommonTree typealias) throws ParseException {
+        assert (typealias.getType() == CTFParser.TYPEALIAS);
+
+        List<CommonTree> children = typealias.getChildren();
+        assert (children != null);
+
+        CommonTree target = null;
+        CommonTree alias = null;
+
+        for (CommonTree child : children) {
+            switch (child.getType()) {
+            case CTFParser.TYPEALIAS_TARGET:
+                assert (target == null);
+                target = child;
+                break;
+            case CTFParser.TYPEALIAS_ALIAS:
+                assert (alias == null);
+                alias = child;
+                break;
+            default:
+                childTypeError(child);
+                break;
+            }
+        }
+
+        assert (target != null);
+        assert (alias != null);
+
+        IDeclaration targetDeclaration = parseTypealiasTarget(target);
+
+        if (targetDeclaration instanceof VariantDeclaration) {
+            if (((VariantDeclaration) targetDeclaration).isTagged()) {
+                throw new ParseException(
+                        "Typealias of untagged variant is not permitted"); //$NON-NLS-1$
+            }
+        }
+
+        String aliasString = parseTypealiasAlias(alias);
+
+        getCurrentScope().registerType(aliasString, targetDeclaration);
+    }
+
+    /**
+     * Parses the target part of a typealias and gets the corresponding
+     * declaration.
+     *
+     * @param target
+     *            A TYPEALIAS_TARGET node.
+     * @return The corresponding declaration.
+     * @throws ParseException
+     */
+    private IDeclaration parseTypealiasTarget(CommonTree target)
+            throws ParseException {
+        assert (target.getType() == CTFParser.TYPEALIAS_TARGET);
+
+        List<CommonTree> children = target.getChildren();
+        assert (children != null);
+
+        CommonTree typeSpecifierList = null;
+        CommonTree typeDeclaratorList = null;
+        CommonTree typeDeclarator = null;
+        StringBuilder identifierSB = new StringBuilder();
+
+        for (CommonTree child : children) {
+            switch (child.getType()) {
+            case CTFParser.TYPE_SPECIFIER_LIST:
+                assert (typeSpecifierList == null);
+                typeSpecifierList = child;
+                break;
+            case CTFParser.TYPE_DECLARATOR_LIST:
+                assert (typeDeclaratorList == null);
+                typeDeclaratorList = child;
+                break;
+            default:
+                childTypeError(child);
+                break;
+            }
+        }
+
+        assert (typeSpecifierList != null);
+
+        if (typeDeclaratorList != null) {
+            /*
+             * Only allow one declarator
+             *
+             * eg: "typealias uint8_t *, ** := puint8_t;" is not permitted,
+             * otherwise the new type puint8_t would maps to two different
+             * types.
+             */
+            if (typeDeclaratorList.getChildCount() != 1) {
+                throw new ParseException(
+                        "Only one type declarator is allowed in the typealias target"); //$NON-NLS-1$
+            }
+
+            typeDeclarator = (CommonTree) typeDeclaratorList.getChild(0);
+        }
+
+        /* Parse the target type and get the declaration */
+        IDeclaration targetDeclaration = parseTypeDeclarator(typeDeclarator,
+                typeSpecifierList, identifierSB);
+
+        /*
+         * We don't allow identifier in the target
+         *
+         * eg: "typealias uint8_t* hello := puint8_t;", the "hello" is not
+         * permitted
+         */
+        if (identifierSB.length() > 0) {
+            throw new ParseException("Identifier (" + identifierSB.toString() //$NON-NLS-1$
+                    + ") not expected in the typealias target"); //$NON-NLS-1$
+        }
+
+        return targetDeclaration;
+    }
+
+    /**
+     * Parses the alias part of a typealias. It parses the underlying specifier
+     * list and declarator and creates the string representation that will be
+     * used to register the type.
+     *
+     * @param alias
+     *            A TYPEALIAS_ALIAS node.
+     * @return The string representation of the alias.
+     * @throws ParseException
+     */
+    private static String parseTypealiasAlias(CommonTree alias)
+            throws ParseException {
+        assert (alias.getType() == CTFParser.TYPEALIAS_ALIAS);
+
+        List<CommonTree> children = alias.getChildren();
+        assert (children != null);
+
+        CommonTree typeSpecifierList = null;
+        CommonTree typeDeclaratorList = null;
+        CommonTree typeDeclarator = null;
+        List<CommonTree> pointers = new LinkedList<CommonTree>();
+
+        for (CommonTree child : children) {
+            switch (child.getType()) {
+            case CTFParser.TYPE_SPECIFIER_LIST:
+                assert (typeSpecifierList == null);
+                typeSpecifierList = child;
+                break;
+            case CTFParser.TYPE_DECLARATOR_LIST:
+                assert (typeDeclaratorList == null);
+                typeDeclaratorList = child;
+                break;
+            default:
+                childTypeError(child);
+                break;
+            }
+        }
+
+        /* If there is a type declarator list, extract the pointers */
+        if (typeDeclaratorList != null) {
+            /*
+             * Only allow one declarator
+             *
+             * eg: "typealias uint8_t := puint8_t *, **;" is not permitted.
+             */
+            if (typeDeclaratorList.getChildCount() != 1) {
+                throw new ParseException(
+                        "Only one type declarator is allowed in the typealias alias"); //$NON-NLS-1$
+            }
+
+            typeDeclarator = (CommonTree) typeDeclaratorList.getChild(0);
+
+            List<CommonTree> typeDeclaratorChildren = typeDeclarator
+                    .getChildren();
+            assert (typeDeclaratorChildren != null);
+
+            for (CommonTree child : typeDeclaratorChildren) {
+                switch (child.getType()) {
+                case CTFParser.POINTER:
+                    pointers.add(child);
+                    break;
+                case CTFParser.IDENTIFIER:
+                    throw new ParseException("Identifier (" + child.getText() //$NON-NLS-1$
+                            + ") not expected in the typealias target"); //$NON-NLS-1$
+                    /* break; */
+                default:
+                    childTypeError(child);
+                    break;
+                }
+            }
+        }
+
+        return createTypeDeclarationString(typeSpecifierList, pointers);
+    }
+
+    /**
+     * Parses a typedef node. This creates and registers a new declaration for
+     * each declarator found in the typedef.
+     *
+     * @param typedef
+     *            A TYPEDEF node.
+     * @throws ParseException
+     *             If there is an error creating the declaration.
+     */
+    private void parseTypedef(CommonTree typedef) throws ParseException {
+        assert (typedef.getType() == CTFParser.TYPEDEF);
+
+        CommonTree typeDeclaratorListNode = (CommonTree) typedef
+                .getFirstChildWithType(CTFParser.TYPE_DECLARATOR_LIST);
+        assert (typeDeclaratorListNode != null);
+
+        CommonTree typeSpecifierListNode = (CommonTree) typedef
+                .getFirstChildWithType(CTFParser.TYPE_SPECIFIER_LIST);
+        assert (typeSpecifierListNode != null);
+
+        List<CommonTree> typeDeclaratorList = typeDeclaratorListNode
+                .getChildren();
+        assert (typeDeclaratorList != null);
+
+        for (CommonTree typeDeclaratorNode : typeDeclaratorList) {
+            StringBuilder identifierSB = new StringBuilder();
+
+            IDeclaration type_declaration = parseTypeDeclarator(
+                    typeDeclaratorNode, typeSpecifierListNode, identifierSB);
+
+            if (type_declaration instanceof VariantDeclaration) {
+                if (((VariantDeclaration) type_declaration).isTagged()) {
+                    throw new ParseException(
+                            "Typealias of untagged variant is not permitted"); //$NON-NLS-1$
+                }
+            }
+
+            getCurrentScope().registerType(identifierSB.toString(),
+                    type_declaration);
+        }
+    }
+
+    /**
+     * Parses a pair type declarator / type specifier list and returns the
+     * corresponding declaration. If it is present, it also writes the
+     * identifier of the declarator in the given {@link StringBuilder}.
+     *
+     * @param typeDeclarator
+     *            A TYPE_DECLARATOR node.
+     * @param typeSpecifierList
+     *            A TYPE_SPECIFIER_LIST node.
+     * @param identifierSB
+     *            A StringBuilder that will receive the identifier found in the
+     *            declarator.
+     * @return The corresponding declaration.
+     * @throws ParseException
+     *             If there is an error finding or creating the declaration.
+     */
+    private IDeclaration parseTypeDeclarator(CommonTree typeDeclarator,
+            CommonTree typeSpecifierList, StringBuilder identifierSB)
+            throws ParseException {
+        if (typeDeclarator != null) {
+            assert (typeDeclarator.getType() == CTFParser.TYPE_DECLARATOR);
+        }
+        assert (typeSpecifierList.getType() == CTFParser.TYPE_SPECIFIER_LIST);
+
+        IDeclaration declaration = null;
+        List<CommonTree> children = null;
+        List<CommonTree> pointers = new LinkedList<CommonTree>();
+        List<CommonTree> lengths = new LinkedList<CommonTree>();
+        CommonTree identifier = null;
+
+        /* Separate the tokens by type */
+        if (typeDeclarator != null) {
+            children = typeDeclarator.getChildren();
+            assert (children != null);
+            for (CommonTree child : children) {
+
+                switch (child.getType()) {
+                case CTFParser.POINTER:
+                    pointers.add(child);
+                    break;
+                case CTFParser.IDENTIFIER:
+                    assert (identifier == null);
+                    identifier = child;
+                    break;
+                case CTFParser.LENGTH:
+                    lengths.add(child);
+                    break;
+                default:
+                    childTypeError(child);
+                    break;
+                }
+            }
+
+        }
+
+        /*
+         * Parse the type specifier list, which is the "base" type. For example,
+         * it would be int in int a[3][len].
+         */
+        declaration = parseTypeSpecifierList(typeSpecifierList, pointers);
+
+        /*
+         * Each length subscript means that we must create a nested array or
+         * sequence. For example, int a[3][len] means that we have an array of 3
+         * (sequences of length 'len' of (int)).
+         */
+        if (lengths.size() > 0 ) {
+            /* We begin at the end */
+            Collections.reverse(lengths);
+
+            for (CommonTree length : lengths) {
+                /*
+                 * By looking at the first expression, we can determine whether
+                 * it is an array or a sequence.
+                 */
+                List<CommonTree> lengthChildren = length.getChildren();
+                assert (lengthChildren != null);
+
+                CommonTree first = lengthChildren.get(0);
+                if (isUnaryInteger(first)) {
+                    /* Array */
+                    int arrayLength = (int) parseUnaryInteger(first);
+
+                    if (arrayLength < 1) {
+                        throw new ParseException("Array length is negative"); //$NON-NLS-1$
+                    }
+
+                    /* Create the array declaration. */
+                    declaration = new ArrayDeclaration(arrayLength, declaration);
+                } else if (isUnaryString(first)) {
+                    /* Sequence */
+                    String lengthName = concatenateUnaryStrings(lengthChildren);
+
+                    /* Create the sequence declaration. */
+                    declaration = new SequenceDeclaration(lengthName,
+                            declaration);
+                } else {
+                    childTypeError(first);
+                }
+            }
+        }
+
+        if (identifier != null) {
+            identifierSB.append(identifier.getText());
+        }
+
+        return declaration;
+    }
+
+    /**
+     * Parses a type specifier list and returns the corresponding declaration.
+     *
+     * @param typeSpecifierList
+     *            A TYPE_SPECIFIER_LIST node.
+     * @param pointerList
+     *            A list of POINTER nodes that apply to the specified type.
+     * @return The corresponding declaration.
+     * @throws ParseException
+     *             If the type has not been defined or if there is an error
+     *             creating the declaration.
+     */
+    private IDeclaration parseTypeSpecifierList(CommonTree typeSpecifierList,
+            List<CommonTree> pointerList) throws ParseException {
+        assert (typeSpecifierList.getType() == CTFParser.TYPE_SPECIFIER_LIST);
+        IDeclaration declaration = null;
+
+        /*
+         * By looking at the first element of the type specifier list, we can
+         * determine which type it belongs to.
+         */
+        CommonTree firstChild = (CommonTree) typeSpecifierList.getChild(0);
+        assert (firstChild != null); /* grammar */
+
+        switch (firstChild.getType()) {
+        case CTFParser.FLOATING_POINT:
+            Activator
+                    .getDefault()
+                    .log("parseTypeSpecifierList: floating_point not implemented yet"); //$NON-NLS-1$
+            break;
+        case CTFParser.INTEGER:
+            declaration = parseInteger(firstChild);
+            break;
+        case CTFParser.STRING:
+            declaration = parseString(firstChild);
+            break;
+        case CTFParser.STRUCT:
+            declaration = parseStruct(firstChild);
+            break;
+        case CTFParser.VARIANT:
+            declaration = parseVariant(firstChild);
+            break;
+        case CTFParser.ENUM:
+            declaration = parseEnum(firstChild);
+            break;
+        case CTFParser.IDENTIFIER:
+        case CTFParser.FLOATTOK:
+        case CTFParser.INTTOK:
+        case CTFParser.LONGTOK:
+        case CTFParser.SHORTTOK:
+        case CTFParser.SIGNEDTOK:
+        case CTFParser.UNSIGNEDTOK:
+        case CTFParser.CHARTOK:
+        case CTFParser.DOUBLETOK:
+        case CTFParser.VOIDTOK:
+        case CTFParser.BOOLTOK:
+        case CTFParser.COMPLEXTOK:
+        case CTFParser.IMAGINARYTOK:
+            declaration = parseTypeDeclaration(typeSpecifierList, pointerList);
+            break;
+        default:
+            childTypeError(firstChild);
+        }
+
+        assert (declaration != null);
+        return declaration;
+    }
+
+    /**
+     * Parses a type specifier list as a user-declared type.
+     *
+     * @param typeSpecifierList
+     *            A TYPE_SPECIFIER_LIST node containing a user-declared type.
+     * @param pointerList
+     *            A list of POINTER nodes that apply to the type specified in
+     *            typeSpecifierList.
+     * @return The corresponding declaration.
+     * @throws ParseException
+     *             If the type does not exist (has not been found).
+     */
+    private IDeclaration parseTypeDeclaration(CommonTree typeSpecifierList,
+            List<CommonTree> pointerList) throws ParseException {
+        /* Create the string representation of the type declaration */
+        String typeStringRepresentation = createTypeDeclarationString(
+                typeSpecifierList, pointerList);
+
+        /* Use the string representation to search the type in the current scope */
+        IDeclaration decl = getCurrentScope().rlookupType(
+                typeStringRepresentation);
+
+        if (decl == null) {
+            throw new ParseException("Type " + typeStringRepresentation //$NON-NLS-1$
+                    + " has not been defined."); //$NON-NLS-1$
+        }
+
+        return decl;
+    }
+
+    /**
+     * Parses an integer declaration node.
+     *
+     * @param integer
+     *            An INTEGER node.
+     * @return The corresponding integer declaration.
+     * @throws ParseException
+     */
+    private IntegerDeclaration parseInteger(CommonTree integer)
+            throws ParseException {
+        assert (integer.getType() == CTFParser.INTEGER);
+
+        List<CommonTree> children = integer.getChildren();
+
+        /*
+         * If the integer has no attributes, then it is missing the size
+         * attribute which is required
+         */
+        if (children == null) {
+            throw new ParseException("integer: missing size attribute"); //$NON-NLS-1$
+        }
+
+        /* The return value */
+        IntegerDeclaration integerDeclaration = null;
+        boolean signed = false;
+        ByteOrder byteOrder = trace.getByteOrder();
+        long size = 0;
+        long alignment = 0;
+        int base = 10;
+        String clock = null;
+
+        Encoding encoding = Encoding.NONE;
+
+        /* Iterate on all integer children */
+        for (CommonTree child : children) {
+            switch (child.getType()) {
+            case CTFParser.CTF_EXPRESSION_VAL:
+                /*
+                 * An assignment expression must have 2 children, left and right
+                 */
+                assert (child.getChildCount() == 2);
+
+                CommonTree leftNode = (CommonTree) child.getChild(0);
+                assert (leftNode.getType() == CTFParser.CTF_LEFT);
+                CommonTree rightNode = (CommonTree) child.getChild(1);
+                assert (rightNode.getType() == CTFParser.CTF_RIGHT);
+
+                List<CommonTree> leftStrings = leftNode.getChildren();
+                assert (leftStrings != null);
+
+                if (!isUnaryString(leftStrings.get(0))) {
+                    throw new ParseException(
+                            "Left side of ctf expression must be a string"); //$NON-NLS-1$
+                }
+                String left = concatenateUnaryStrings(leftStrings);
+
+                if (left.equals("signed")) { //$NON-NLS-1$
+                    signed = getSigned(rightNode);
+                } else if (left.equals("byte_order")) { //$NON-NLS-1$
+                    byteOrder = getByteOrder(rightNode);
+                } else if (left.equals("size")) { //$NON-NLS-1$
+                    size = getSize(rightNode);
+                } else if (left.equals("align")) { //$NON-NLS-1$
+                    alignment = getAlignment(rightNode);
+                } else if (left.equals("base")) { //$NON-NLS-1$
+                    base = getBase(rightNode);
+                } else if (left.equals("encoding")) { //$NON-NLS-1$
+                    encoding = getEncoding(rightNode);
+                } else if (left.equals("map")) { //$NON-NLS-1$
+                    clock = getClock(rightNode);
+                } else {
+                    throw new ParseException("Integer: unknown attribute " + left); //$NON-NLS-1$
+                }
+
+                break;
+            default:
+                childTypeError(child);
+                break;
+            }
+        }
+
+        if (size == 0) {
+            throw new ParseException("Integer missing size attribute"); //$NON-NLS-1$
+        }
+
+        if (alignment == 0) {
+            if ((size % 8) == 0) {
+                alignment = 1;
+            } else {
+                alignment = 8;
+            }
+        }
+
+        integerDeclaration = new IntegerDeclaration((int) size, signed, base,
+                byteOrder, encoding, clock);
+
+        assert (integerDeclaration != null);
+        return integerDeclaration;
+    }
+
+    private static String getClock(CommonTree rightNode) {
+        return rightNode.getChild(1).getChild(0).getChild(0).getText();
+    }
+
+    private static StringDeclaration parseString(CommonTree string)
+            throws ParseException {
+        assert (string.getType() == CTFParser.STRING);
+
+        List<CommonTree> children = string.getChildren();
+        StringDeclaration stringDeclaration = null;
+
+        if (children == null) {
+            stringDeclaration = new StringDeclaration();
+        } else {
+            Encoding encoding = Encoding.UTF8;
+            for (CommonTree child : children) {
+                switch (child.getType()) {
+                case CTFParser.CTF_EXPRESSION_VAL:
+                    /*
+                     * An assignment expression must have 2 children, left and
+                     * right
+                     */
+                    assert (child.getChildCount() == 2);
+
+                    CommonTree leftNode = (CommonTree) child.getChild(0);
+                    assert (leftNode.getType() == CTFParser.CTF_LEFT);
+                    CommonTree rightNode = (CommonTree) child.getChild(1);
+                    assert (rightNode.getType() == CTFParser.CTF_RIGHT);
+
+                    List<CommonTree> leftStrings = leftNode.getChildren();
+                    assert (leftStrings != null);
+
+                    if (!isUnaryString(leftStrings.get(0))) {
+                        throw new ParseException(
+                                "Left side of ctf expression must be a string"); //$NON-NLS-1$
+                    }
+                    String left = concatenateUnaryStrings(leftStrings);
+
+                    if (left.equals("encoding")) { //$NON-NLS-1$
+                        encoding = getEncoding(rightNode);
+                    } else {
+                        throw new ParseException("String: unknown attribute " //$NON-NLS-1$
+                                + left);
+                    }
+
+                    break;
+                default:
+                    childTypeError(child);
+                    break;
+                }
+            }
+
+            stringDeclaration = new StringDeclaration(encoding);
+        }
+
+        return stringDeclaration;
+    }
+
+    /**
+     * Parses a struct declaration and returns the corresponding declaration.
+     *
+     * @param struct
+     *            An STRUCT node.
+     * @return The corresponding struct declaration.
+     * @throws ParseException
+     */
+    private StructDeclaration parseStruct(CommonTree struct)
+            throws ParseException {
+        assert (struct.getType() == CTFParser.STRUCT);
+
+        List<CommonTree> children = struct.getChildren();
+        assert (children != null);
+
+        /* The return value */
+        StructDeclaration structDeclaration = null;
+
+        /* Name */
+        String structName = null;
+        boolean hasName = false;
+
+        /* Body */
+        CommonTree structBody = null;
+        boolean hasBody = false;
+
+        /* Align */
+        long structAlign = 0;
+
+        /* Loop on all children and identify what we have to work with. */
+        for (CommonTree child : children) {
+            switch (child.getType()) {
+            case CTFParser.STRUCT_NAME: {
+                hasName = true;
+
+                assert (child.getChildCount() == 1);
+                CommonTree structNameIdentifier = (CommonTree) child
+                        .getChild(0);
+
+                assert (structNameIdentifier.getType() == CTFParser.IDENTIFIER);
+                structName = structNameIdentifier.getText();
+
+                break;
+            }
+            case CTFParser.STRUCT_BODY: {
+                hasBody = true;
+
+                structBody = child;
+
+                break;
+            }
+            case CTFParser.ALIGN: {
+                assert (child.getChildCount() == 1);
+                CommonTree structAlignExpression = (CommonTree) child
+                        .getChild(0);
+
+                structAlign = getAlignment(structAlignExpression);
+
+                break;
+            }
+            default:
+                childTypeError(child);
+
+                break;
+            }
+        }
+
+        /*
+         * If a struct has just a body and no name (just like the song,
+         * "A Struct With No Name" by America (sorry for that...)), it's a
+         * definition of a new type, so we create the type declaration and
+         * return it. We can't add it to the declaration scope since there is no
+         * name, but that's what we want because it won't be possible to use it
+         * again to declare another field.
+         *
+         * If it has just a name, we look it up in the declaration scope and
+         * return the associated declaration. If it is not found in the
+         * declaration scope, it means that a struct with that name has not been
+         * declared, which is an error.
+         *
+         * If it has both, then we create the type declaration and register it
+         * to the current scope.
+         *
+         * If it has none, then what are we doing here ?
+         */
+        if (hasBody) {
+            /*
+             * If struct has a name, check if already defined in the current
+             * scope.
+             */
+            if (hasName && (getCurrentScope().lookupStruct(structName) != null)) {
+                throw new ParseException("struct " + structName //$NON-NLS-1$
+                        + " already defined."); //$NON-NLS-1$
+            }
+
+            /* Create the declaration */
+            structDeclaration = new StructDeclaration(structAlign);
+
+            /* Parse the body */
+            parseStructBody(structBody, structDeclaration);
+
+            /* If struct has name, add it to the current scope. */
+            if (hasName) {
+                getCurrentScope().registerStruct(structName, structDeclaration);
+            }
+        } else /* !hasBody */{
+            if (hasName) {
+                /* Name and !body */
+
+                /* Lookup the name in the current scope. */
+                structDeclaration = getCurrentScope().rlookupStruct(structName);
+
+                /*
+                 * If not found, it means that a struct with such name has not
+                 * been defined
+                 */
+                if (structDeclaration == null) {
+                    throw new ParseException("struct " + structName //$NON-NLS-1$
+                            + " is not defined"); //$NON-NLS-1$
+                }
+            } else {
+                /* !Name and !body */
+
+                /* We can't do anything with that. */
+                throw new ParseException("struct with no name and no body"); //$NON-NLS-1$
+            }
+        }
+
+        assert (structDeclaration != null);
+        return structDeclaration;
+    }
+
+    /**
+     * Parses a struct body, adding the fields to specified structure
+     * declaration.
+     *
+     * @param structBody
+     *            A STRUCT_BODY node.
+     * @param structDeclaration
+     *            The struct declaration.
+     * @throws ParseException
+     */
+    private void parseStructBody(CommonTree structBody,
+            StructDeclaration structDeclaration) throws ParseException {
+        assert (structBody.getType() == CTFParser.STRUCT_BODY);
+
+        List<CommonTree> structDeclarations = structBody.getChildren();
+
+        /*
+         * If structDeclaration is null, structBody has no children and the
+         * struct body is empty.
+         */
+        if (structDeclarations != null) {
+            pushScope();
+
+            for (CommonTree declarationNode : structDeclarations) {
+                switch (declarationNode.getType()) {
+                case CTFParser.TYPEALIAS:
+                    parseTypealias(declarationNode);
+                    break;
+                case CTFParser.TYPEDEF:
+                    parseTypedef(declarationNode);
+                    break;
+                case CTFParser.SV_DECLARATION:
+                    parseStructDeclaration(declarationNode, structDeclaration);
+                    break;
+                default:
+                    childTypeError(declarationNode);
+                    break;
+                }
+            }
+            popScope();
+        }
+    }
+
+    /**
+     * Parses a declaration found in a struct.
+     *
+     * @param declaration
+     *            A SV_DECLARATION node.
+     * @param struct
+     *            A struct declaration. (I know, little name clash here...)
+     * @throws ParseException
+     */
+    private void parseStructDeclaration(CommonTree declaration,
+            StructDeclaration struct) throws ParseException {
+        assert (declaration.getType() == CTFParser.SV_DECLARATION);
+
+        List<CommonTree> children = declaration.getChildren();
+        assert (children != null);
+
+        /* Get the type specifier list node */
+        CommonTree typeSpecifierListNode = (CommonTree) declaration
+                .getFirstChildWithType(CTFParser.TYPE_SPECIFIER_LIST);
+        assert (typeSpecifierListNode != null);
+
+        /* Get the type declarator list node */
+        CommonTree typeDeclaratorListNode = (CommonTree) declaration
+                .getFirstChildWithType(CTFParser.TYPE_DECLARATOR_LIST);
+        assert (typeDeclaratorListNode != null);
+
+        /* Get the type declarator list */
+        List<CommonTree> typeDeclaratorList = typeDeclaratorListNode
+                .getChildren();
+        assert (typeDeclaratorList != null);
+
+        /*
+         * For each type declarator, parse the declaration and add a field to
+         * the struct
+         */
+        for (CommonTree typeDeclaratorNode : typeDeclaratorList) {
+            assert (typeDeclaratorNode.getType() == CTFParser.TYPE_DECLARATOR);
+
+            StringBuilder identifierSB = new StringBuilder();
+
+            IDeclaration decl = parseTypeDeclarator(typeDeclaratorNode,
+                    typeSpecifierListNode, identifierSB);
+            String fieldName = identifierSB.toString();
+
+            if (struct.hasField(fieldName)) {
+                throw new ParseException("struct: duplicate field " //$NON-NLS-1$
+                        + fieldName);
+            }
+
+            struct.addField(fieldName, decl);
+
+        }
+    }
+
+    /**
+     * Parses an enum declaration and returns the corresponding declaration.
+     *
+     * @param _enum
+     *            An ENUM node.
+     * @return The corresponding enum declaration.
+     * @throws ParseException
+     */
+    private EnumDeclaration parseEnum(CommonTree _enum) throws ParseException {
+        assert (_enum.getType() == CTFParser.ENUM);
+
+        List<CommonTree> children = _enum.getChildren();
+        assert (children != null);
+
+        /* The return value */
+        EnumDeclaration enumDeclaration = null;
+
+        /* Name */
+        String enumName = null;
+
+        /* Body */
+        CommonTree enumBody = null;
+
+        /* Container type */
+        IntegerDeclaration containerTypeDeclaration = null;
+
+        /* Loop on all children and identify what we have to work with. */
+        for (CommonTree child : children) {
+            switch (child.getType()) {
+            case CTFParser.ENUM_NAME: {
+                assert (enumName == null);
+
+                assert (child.getChildCount() == 1);
+                CommonTree enumNameIdentifier = (CommonTree) child.getChild(0);
+
+                assert (enumNameIdentifier.getType() == CTFParser.IDENTIFIER);
+                enumName = enumNameIdentifier.getText();
+
+                break;
+            }
+            case CTFParser.ENUM_BODY: {
+                assert (enumBody == null);
+
+                enumBody = child;
+
+                break;
+            }
+            case CTFParser.ENUM_CONTAINER_TYPE: {
+                assert (containerTypeDeclaration == null);
+
+                containerTypeDeclaration = parseEnumContainerType(child);
+
+                break;
+            }
+            default:
+                childTypeError(child);
+                break;
+            }
+        }
+
+        /*
+         * If the container type has not been defined explicitly, we assume it
+         * is "int".
+         */
+        if (containerTypeDeclaration == null) {
+            IDeclaration decl = getCurrentScope().rlookupType("int"); //$NON-NLS-1$
+
+            if (decl == null) {
+                throw new ParseException(
+                        "enum container type implicit and type int not defined"); //$NON-NLS-1$
+            } else if (!(decl instanceof IntegerDeclaration)) {
+                throw new ParseException(
+                        "enum container type implicit and type int not an integer"); //$NON-NLS-1$
+            }
+
+            containerTypeDeclaration = (IntegerDeclaration) decl;
+        }
+
+        /*
+         * If it has a body, it's a new declaration, otherwise it's a reference
+         * to an existing declaration. Same logic as struct.
+         */
+        if (enumBody != null) {
+            /*
+             * If enum has a name, check if already defined in the current
+             * scope.
+             */
+            if ((enumName != null)
+                    && (getCurrentScope().lookupEnum(enumName) != null)) {
+                throw new ParseException("enum " + enumName //$NON-NLS-1$
+                        + " already defined"); //$NON-NLS-1$
+            }
+
+            /* Create the declaration */
+            enumDeclaration = new EnumDeclaration(containerTypeDeclaration);
+
+            /* Parse the body */
+            parseEnumBody(enumBody, enumDeclaration);
+
+            /* If the enum has name, add it to the current scope. */
+            if (enumName != null) {
+                getCurrentScope().registerEnum(enumName, enumDeclaration);
+            }
+        } else {
+            if (enumName != null) {
+                /* Name and !body */
+
+                /* Lookup the name in the current scope. */
+                enumDeclaration = getCurrentScope().rlookupEnum(enumName);
+
+                /*
+                 * If not found, it means that an enum with such name has not
+                 * been defined
+                 */
+                if (enumDeclaration == null) {
+                    throw new ParseException("enum " + enumName //$NON-NLS-1$
+                            + " is not defined"); //$NON-NLS-1$
+                }
+            } else {
+                /* !Name and !body */
+                throw new ParseException("enum with no name and no body"); //$NON-NLS-1$
+            }
+        }
+
+        return enumDeclaration;
+
+    }
+
+    /**
+     * Parses an enum body, adding the enumerators to the specified enum
+     * declaration.
+     *
+     * @param enumBody
+     *            An ENUM_BODY node.
+     * @param enumDeclaration
+     *            The enum declaration.
+     * @throws ParseException
+     */
+    private void parseEnumBody(CommonTree enumBody,
+            EnumDeclaration enumDeclaration) throws ParseException {
+        assert (enumBody.getType() == CTFParser.ENUM_BODY);
+
+        List<CommonTree> enumerators = enumBody.getChildren();
+        /* enum body can't be empty (unlike struct). */
+        assert (enumerators != null);
+
+        pushScope();
+
+        /*
+         * Start at -1, so that if the first enumrator has no explicit value, it
+         * will choose 0
+         */
+        long lastHigh = -1;
+
+        for (CommonTree enumerator : enumerators) {
+            lastHigh = parseEnumEnumerator(enumerator, enumDeclaration,
+                    lastHigh);
+        }
+
+        popScope();
+
+    }
+
+    /**
+     * Parses an enumerator node and adds an enumerator declaration to an
+     * enumeration declaration.
+     *
+     * The high value of the range of the last enumerator is needed in case the
+     * current enumerator does not specify its value.
+     *
+     * @param enumerator
+     *            An ENUM_ENUMERATOR node.
+     * @param enumDeclaration
+     *            en enumeration declaration to which will be added the
+     *            enumerator.
+     * @param lastHigh
+     *            The high value of the range of the last enumerator
+     * @return The high value of the value range of the current enumerator.
+     * @throws ParseException
+     */
+    private static long parseEnumEnumerator(CommonTree enumerator,
+            EnumDeclaration enumDeclaration, long lastHigh)
+            throws ParseException {
+        assert (enumerator.getType() == CTFParser.ENUM_ENUMERATOR);
+
+        List<CommonTree> children = enumerator.getChildren();
+        assert (children != null);
+
+        long low = 0, high = 0;
+        boolean valueSpecified = false;
+        String label = null;
+
+        for (CommonTree child : children) {
+            if (isUnaryString(child)) {
+                label = parseUnaryString(child);
+            } else if (child.getType() == CTFParser.ENUM_VALUE) {
+                assert (child.getChildCount() == 1);
+                assert (isUnaryInteger((CommonTree) child.getChild(0)));
+
+                valueSpecified = true;
+
+                low = parseUnaryInteger((CommonTree) child.getChild(0));
+                high = low;
+            } else if (child.getType() == CTFParser.ENUM_VALUE_RANGE) {
+                assert (child.getChildCount() == 2);
+                assert (isUnaryInteger((CommonTree) child.getChild(0)));
+                assert (isUnaryInteger((CommonTree) child.getChild(1)));
+
+                valueSpecified = true;
+
+                low = parseUnaryInteger((CommonTree) child.getChild(0));
+                high = parseUnaryInteger((CommonTree) child.getChild(1));
+            } else {
+                childTypeError(child);
+            }
+        }
+
+        assert (label != null);
+
+        if (!valueSpecified) {
+            low = lastHigh + 1;
+            high = low;
+        }
+
+        if (low > high) {
+            throw new ParseException("enum low value greater than high value"); //$NON-NLS-1$
+        }
+
+        if (!enumDeclaration.add(low, high, label)) {
+            throw new ParseException("enum declarator values overlap."); //$NON-NLS-1$
+        }
+
+        return high;
+    }
+
+    /**
+     * Parses an enum container type node and returns the corresponding integer
+     * type.
+     *
+     * @param enumContainerType
+     *            An ENUM_CONTAINER_TYPE node.
+     * @return An integer declaration corresponding to the container type.
+     * @throws ParseException
+     *             If the type does not parse correctly or if it is not an
+     *             integer type.
+     */
+    private IntegerDeclaration parseEnumContainerType(
+            CommonTree enumContainerType) throws ParseException {
+        assert (enumContainerType.getType() == CTFParser.ENUM_CONTAINER_TYPE);
+
+        /* Get the child, which should be a type specifier list */
+        assert (enumContainerType.getChildCount() == 1);
+        CommonTree typeSpecifierList = (CommonTree) enumContainerType
+                .getChild(0);
+
+        /* Parse it and get the corresponding declaration */
+        IDeclaration decl = parseTypeSpecifierList(typeSpecifierList, null);
+
+        /* If is is an integer, return it, else throw an error */
+        if (decl instanceof IntegerDeclaration) {
+            return (IntegerDeclaration) decl;
+        }
+        throw new ParseException("enum container type must be an integer"); //$NON-NLS-1$
+    }
+
+    private VariantDeclaration parseVariant(CommonTree variant)
+            throws ParseException {
+        assert (variant.getType() == CTFParser.VARIANT);
+
+        List<CommonTree> children = variant.getChildren();
+        VariantDeclaration variantDeclaration = null;
+
+        boolean hasName = false;
+        String variantName = null;
+
+        boolean hasBody = false;
+        CommonTree variantBody = null;
+
+        boolean hasTag = false;
+        String variantTag = null;
+
+        for (CommonTree child : children) {
+            switch (child.getType()) {
+            case CTFParser.VARIANT_NAME:
+                assert (variantName == null);
+
+                hasName = true;
+
+                assert (child.getChildCount() == 1);
+                CommonTree variantNameIdentifier = (CommonTree) child
+                        .getChild(0);
+
+                assert (variantNameIdentifier.getType() == CTFParser.IDENTIFIER);
+                variantName = variantNameIdentifier.getText();
+
+                break;
+            case CTFParser.VARIANT_TAG:
+                assert (variantTag == null);
+
+                hasTag = true;
+
+                assert (child.getChildCount() == 1);
+                CommonTree variantTagIdentifier = (CommonTree) child
+                        .getChild(0);
+
+                assert (variantTagIdentifier.getType() == CTFParser.IDENTIFIER);
+                variantTag = variantTagIdentifier.getText();
+
+                break;
+            case CTFParser.VARIANT_BODY:
+                assert (variantBody == null);
+
+                hasBody = true;
+
+                variantBody = child;
+
+                break;
+            default:
+                childTypeError(child);
+                break;
+            }
+        }
+
+        if (hasBody) {
+            /*
+             * If variant has a name, check if already defined in the current
+             * scope.
+             */
+            if (hasName
+                    && (getCurrentScope().lookupVariant(variantName) != null)) {
+                throw new ParseException("variant " + variantName //$NON-NLS-1$
+                        + " already defined."); //$NON-NLS-1$
+            }
+
+            /* Create the declaration */
+            variantDeclaration = new VariantDeclaration();
+
+            /* Parse the body */
+            parseVariantBody(variantBody, variantDeclaration);
+
+            /* If variant has name, add it to the current scope. */
+            if (hasName) {
+                getCurrentScope().registerVariant(variantName,
+                        variantDeclaration);
+            }
+        } else /* !hasBody */{
+            if (hasName) {
+                /* Name and !body */
+
+                /* Lookup the name in the current scope. */
+                variantDeclaration = getCurrentScope().rlookupVariant(
+                        variantName);
+
+                /*
+                 * If not found, it means that a struct with such name has not
+                 * been defined
+                 */
+                if (variantDeclaration == null) {
+                    throw new ParseException("variant " + variantName //$NON-NLS-1$
+                            + " is not defined"); //$NON-NLS-1$
+                }
+            } else {
+                /* !Name and !body */
+
+                /* We can't do anything with that. */
+                throw new ParseException("variant with no name and no body"); //$NON-NLS-1$
+            }
+        }
+
+        if (hasTag) {
+            variantDeclaration.setTag(variantTag);
+        }
+
+        assert (variantDeclaration != null);
+        return variantDeclaration;
+    }
+
+    private void parseVariantBody(CommonTree variantBody,
+            VariantDeclaration variantDeclaration) throws ParseException {
+        assert (variantBody.getType() == CTFParser.VARIANT_BODY);
+
+        List<CommonTree> variantDeclarations = variantBody.getChildren();
+        assert (variantDeclarations != null);
+
+        pushScope();
+
+        for (CommonTree declarationNode : variantDeclarations) {
+            switch (declarationNode.getType()) {
+            case CTFParser.TYPEALIAS:
+                parseTypealias(declarationNode);
+                break;
+            case CTFParser.TYPEDEF:
+                parseTypedef(declarationNode);
+                break;
+            case CTFParser.SV_DECLARATION:
+                parseVariantDeclaration(declarationNode, variantDeclaration);
+                break;
+            default:
+                childTypeError(declarationNode);
+                break;
+            }
+        }
+
+        popScope();
+    }
+
+    private void parseVariantDeclaration(CommonTree declaration,
+            VariantDeclaration variant) throws ParseException {
+        assert (declaration.getType() == CTFParser.SV_DECLARATION);
+
+        List<CommonTree> children = declaration.getChildren();
+        assert (children != null);
+
+        /* Get the type specifier list node */
+        CommonTree typeSpecifierListNode = (CommonTree) declaration
+                .getFirstChildWithType(CTFParser.TYPE_SPECIFIER_LIST);
+        assert (typeSpecifierListNode != null);
+
+        /* Get the type declarator list node */
+        CommonTree typeDeclaratorListNode = (CommonTree) declaration
+                .getFirstChildWithType(CTFParser.TYPE_DECLARATOR_LIST);
+        assert (typeDeclaratorListNode != null);
+
+        /* Get the type declarator list */
+        List<CommonTree> typeDeclaratorList = typeDeclaratorListNode
+                .getChildren();
+        assert (typeDeclaratorList != null);
+
+        /*
+         * For each type declarator, parse the declaration and add a field to
+         * the variant
+         */
+        for (CommonTree typeDeclaratorNode : typeDeclaratorList) {
+            assert (typeDeclaratorNode.getType() == CTFParser.TYPE_DECLARATOR);
+
+            StringBuilder identifierSB = new StringBuilder();
+
+            IDeclaration decl = parseTypeDeclarator(typeDeclaratorNode,
+                    typeSpecifierListNode, identifierSB);
+
+            if (variant.hasField(identifierSB.toString())) {
+                throw new ParseException("variant: duplicate field " //$NON-NLS-1$
+                        + identifierSB.toString());
+            }
+
+            variant.addField(identifierSB.toString(), decl);
+        }
+    }
+
+    /**
+     * Creates the string representation of a type declaration (type specifier
+     * list + pointers).
+     *
+     * @param typeSpecifierList
+     *            A TYPE_SPECIFIER_LIST node.
+     * @param pointers
+     *            A list of POINTER nodes.
+     * @return The string representation.
+     * @throws ParseException
+     */
+    private static String createTypeDeclarationString(
+            CommonTree typeSpecifierList, List<CommonTree> pointers)
+            throws ParseException {
+        StringBuilder sb = new StringBuilder();
+
+        createTypeSpecifierListString(typeSpecifierList, sb);
+        createPointerListString(pointers, sb);
+
+        return sb.toString();
+    }
+
+    /**
+     * Creates the string representation of a list of type specifiers.
+     *
+     * @param typeSpecifierList
+     *            A TYPE_SPECIFIER_LIST node.
+     * @param sb
+     *            A StringBuilder to which will be appended the string.
+     * @throws ParseException
+     */
+    private static void createTypeSpecifierListString(
+            CommonTree typeSpecifierList, StringBuilder sb)
+            throws ParseException {
+        assert (typeSpecifierList.getType() == CTFParser.TYPE_SPECIFIER_LIST);
+
+        List<CommonTree> children = typeSpecifierList.getChildren();
+        assert (children != null);
+
+        boolean firstItem = true;
+
+        for (CommonTree child : children) {
+            if (!firstItem) {
+                sb.append(' ');
+
+            }
+
+            firstItem = false;
+
+            /* Append the string that represents this type specifier. */
+            createTypeSpecifierString(child, sb);
+        }
+    }
+
+    /**
+     * Creates the string representation of a type specifier.
+     *
+     * @param typeSpecifier
+     *            A TYPE_SPECIFIER node.
+     * @param sb
+     *            A StringBuilder to which will be appended the string.
+     * @throws ParseException
+     */
+    private static void createTypeSpecifierString(CommonTree typeSpecifier,
+            StringBuilder sb) throws ParseException {
+        switch (typeSpecifier.getType()) {
+        case CTFParser.FLOATTOK:
+        case CTFParser.INTTOK:
+        case CTFParser.LONGTOK:
+        case CTFParser.SHORTTOK:
+        case CTFParser.SIGNEDTOK:
+        case CTFParser.UNSIGNEDTOK:
+        case CTFParser.CHARTOK:
+        case CTFParser.DOUBLETOK:
+        case CTFParser.VOIDTOK:
+        case CTFParser.BOOLTOK:
+        case CTFParser.COMPLEXTOK:
+        case CTFParser.IMAGINARYTOK:
+        case CTFParser.CONSTTOK:
+        case CTFParser.IDENTIFIER:
+            sb.append(typeSpecifier.getText());
+            break;
+        case CTFParser.STRUCT: {
+            CommonTree structName = (CommonTree) typeSpecifier
+                    .getFirstChildWithType(CTFParser.STRUCT_NAME);
+            if (structName == null) {
+                throw new ParseException(
+                        "nameless struct found in createTypeSpecifierString"); //$NON-NLS-1$
+            }
+            assert (structName.getChildCount() == 1);
+
+            CommonTree structNameIdentifier = (CommonTree) structName
+                    .getChild(0);
+            assert (structNameIdentifier.getType() == CTFParser.IDENTIFIER);
+
+            sb.append(structNameIdentifier.getText());
+            break;
+        }
+        case CTFParser.VARIANT: {
+            CommonTree variantName = (CommonTree) typeSpecifier
+                    .getFirstChildWithType(CTFParser.VARIANT_NAME);
+            if (variantName == null) {
+                throw new ParseException(
+                        "nameless variant found in createTypeSpecifierString"); //$NON-NLS-1$
+            }
+            assert (variantName.getChildCount() == 1);
+
+            CommonTree variantNameIdentifier = (CommonTree) variantName
+                    .getChild(0);
+            assert (variantNameIdentifier.getType() == CTFParser.IDENTIFIER);
+
+            sb.append(variantNameIdentifier.getText());
+            break;
+        }
+        case CTFParser.ENUM: {
+            CommonTree enumName = (CommonTree) typeSpecifier
+                    .getFirstChildWithType(CTFParser.ENUM_NAME);
+            if (enumName == null) {
+                throw new ParseException(
+                        "nameless enum found in createTypeSpecifierString"); //$NON-NLS-1$
+            }
+            assert (enumName.getChildCount() == 1);
+
+            CommonTree enumNameIdentifier = (CommonTree) enumName.getChild(0);
+            assert (enumNameIdentifier.getType() == CTFParser.IDENTIFIER);
+
+            sb.append(enumNameIdentifier.getText());
+            break;
+        }
+        case CTFParser.FLOATING_POINT:
+        case CTFParser.INTEGER:
+        case CTFParser.STRING:
+            throw new ParseException(
+                    "CTF type found in createTypeSpecifierString"); //$NON-NLS-1$
+            /* break; */
+        default:
+            childTypeError(typeSpecifier);
+            break;
+        }
+    }
+
+    /**
+     * Creates the string representation of a list of pointers.
+     *
+     * @param pointerList
+     *            A list of pointer nodes. If pointerList is null, this function
+     *            does nothing.
+     * @param sb
+     *            A stringbuilder to which will be appended the string.
+     */
+    private static void createPointerListString(List<CommonTree> pointerList,
+            StringBuilder sb) {
+        if (pointerList == null) {
+            return;
+        }
+
+        for (CommonTree pointer : pointerList) {
+            assert (pointer.getType() == CTFParser.POINTER);
+
+            sb.append(" *"); //$NON-NLS-1$
+            if (pointer.getChildCount() > 0) {
+                assert (pointer.getChildCount() == 1);
+                CommonTree constQualifier = (CommonTree) pointer.getChild(0);
+                assert (constQualifier.getType() == CTFParser.CONSTTOK);
+
+                sb.append(" const"); //$NON-NLS-1$
+            }
+        }
+    }
+
+    /**
+     * @param node
+     *            The node to check.
+     * @return True if the given node is an unary string or unary integer.
+     */
+    private static boolean isUnaryExpression(CommonTree node) {
+        return isUnaryInteger(node) || isUnaryString(node);
+    }
+
+    /**
+     * @param node
+     *            The node to check.
+     * @return True if the given node is an unary string.
+     */
+    private static boolean isUnaryString(CommonTree node) {
+        return ((node.getType() == CTFParser.UNARY_EXPRESSION_STRING) || (node
+                .getType() == CTFParser.UNARY_EXPRESSION_STRING_QUOTES));
+    }
+
+    /**
+     * @param node
+     *            The node to check.
+     * @return True if the given node is an unary integer.
+     */
+    private static boolean isUnaryInteger(CommonTree node) {
+        return ((node.getType() == CTFParser.UNARY_EXPRESSION_DEC)
+                || (node.getType() == CTFParser.UNARY_EXPRESSION_HEX) || (node
+                    .getType() == CTFParser.UNARY_EXPRESSION_OCT));
+    }
+
+    /**
+     * Parses a unary string node and return the string value.
+     *
+     * @param unaryString
+     *            The unary string node to parse (type UNARY_EXPRESSION_STRING
+     *            or UNARY_EXPRESSION_STRING_QUOTES).
+     * @return The string value.
+     */
+    /*
+     * It would be really nice to remove the quotes earlier, such as in the
+     * parser.
+     */
+    private static String parseUnaryString(CommonTree unaryString) {
+        assert (isUnaryString(unaryString));
+
+        assert (unaryString.getChildCount() == 1);
+        CommonTree value = (CommonTree) unaryString.getChild(0);
+        assert (value != null);
+        String strval = value.getText();
+
+        /* Remove quotes */
+        if (unaryString.getType() == CTFParser.UNARY_EXPRESSION_STRING_QUOTES) {
+            strval = strval.substring(1, strval.length() - 1);
+        }
+
+        return strval;
+    }
+
+    /**
+     * Parses an unary integer (dec, hex or oct).
+     *
+     * @param unaryInteger
+     *            An unary integer node.
+     * @return The integer value.
+     */
+    private static long parseUnaryInteger(CommonTree unaryInteger) {
+        assert (isUnaryInteger(unaryInteger));
+
+        assert (unaryInteger.getChildCount() >= 1);
+
+        List<CommonTree> children = unaryInteger.getChildren();
+        CommonTree value = children.get(0);
+        String strval = value.getText();
+
+        long intval;
+
+        if (unaryInteger.getType() == CTFParser.UNARY_EXPRESSION_DEC) {
+            intval = Long.parseLong(strval, 10);
+        } else if (unaryInteger.getType() == CTFParser.UNARY_EXPRESSION_HEX) {
+            intval = Long.parseLong(strval, 0x10);
+        } else { /* unaryInteger.getType() == CTFParser.UNARY_EXPRESSION_OCT */
+            intval = Long.parseLong(strval, 010); // 010 == 0x08 == 8
+        }
+
+        /* The rest of children are sign */
+        if ((children.size() % 2) == 0) {
+            return -intval;
+        }
+        return intval;
+    }
+
+    private static long getMajorOrMinor(CommonTree rightNode)
+            throws ParseException {
+        assert (rightNode.getType() == CTFParser.CTF_RIGHT);
+        assert (rightNode.getChildCount() > 0);
+
+        CommonTree firstChild = (CommonTree) rightNode.getChild(0);
+
+        if (isUnaryInteger(firstChild)) {
+            if (rightNode.getChildCount() > 1) {
+                throw new ParseException("Invalid value for major/minor"); //$NON-NLS-1$
+            }
+
+            long m = parseUnaryInteger(firstChild);
+
+            if (m < 0) {
+                throw new ParseException("Invalid value for major/minor"); //$NON-NLS-1$
+            }
+
+            return m;
+        }
+        throw new ParseException("Invalid value for major/minor"); //$NON-NLS-1$
+    }
+
+    private static UUID getUUID(CommonTree rightNode) throws ParseException {
+        assert (rightNode.getType() == CTFParser.CTF_RIGHT);
+        assert (rightNode.getChildCount() > 0);
+
+        CommonTree firstChild = (CommonTree) rightNode.getChild(0);
+
+        if (isUnaryString(firstChild)) {
+            if (rightNode.getChildCount() > 1) {
+                throw new ParseException("Invalid value for UUID"); //$NON-NLS-1$
+            }
+
+            String uuidstr = parseUnaryString(firstChild);
+
+            try {
+                UUID uuid = UUID.fromString(uuidstr);
+                return uuid;
+            } catch (IllegalArgumentException e) {
+                throw new ParseException("Invalid format for UUID"); //$NON-NLS-1$
+            }
+        }
+        throw new ParseException("Invalid value for UUID"); //$NON-NLS-1$
+    }
+
+    /**
+     * Gets the value of a "signed" integer attribute.
+     *
+     * @param rightNode
+     *            A CTF_RIGHT node.
+     * @return The "signed" value as a boolean.
+     * @throws ParseException
+     */
+    private static boolean getSigned(CommonTree rightNode)
+            throws ParseException {
+        assert (rightNode.getType() == CTFParser.CTF_RIGHT);
+        assert (rightNode.getChildCount() > 0);
+
+        boolean ret = false;
+        CommonTree firstChild = (CommonTree) rightNode.getChild(0);
+
+        if (isUnaryString(firstChild)) {
+            String strval = concatenateUnaryStrings(rightNode.getChildren());
+
+            if (strval.equals("true") || strval.equals("TRUE")) { //$NON-NLS-1$ //$NON-NLS-2$
+                ret = true;
+            } else if (strval.equals("false") || strval.equals("FALSE")) { //$NON-NLS-1$ //$NON-NLS-2$
+                ret = false;
+            } else {
+                throw new ParseException("Invalid boolean value " //$NON-NLS-1$
+                        + firstChild.getChild(0).getText());
+            }
+        } else if (isUnaryInteger(firstChild)) {
+            /* Happens if the value is something like "1234.hello" */
+            if (rightNode.getChildCount() > 1) {
+                throw new ParseException("Invalid boolean value"); //$NON-NLS-1$
+            }
+
+            long intval = parseUnaryInteger(firstChild);
+
+            if (intval == 1) {
+                ret = true;
+            } else if (intval == 0) {
+                ret = false;
+            } else {
+                throw new ParseException("Invalid boolean value " //$NON-NLS-1$
+                        + firstChild.getChild(0).getText());
+            }
+        } else {
+            throw new ParseException();
+        }
+
+        return ret;
+    }
+
+    /**
+     * Gets the value of a "byte_order" integer attribute.
+     *
+     * @param rightNode
+     *            A CTF_RIGHT node.
+     * @return The "byte_order" value.
+     * @throws ParseException
+     */
+    private ByteOrder getByteOrder(CommonTree rightNode) throws ParseException {
+        assert (rightNode.getType() == CTFParser.CTF_RIGHT);
+        assert (rightNode.getChildCount() > 0);
+
+        CommonTree firstChild = (CommonTree) rightNode.getChild(0);
+
+        if (isUnaryString(firstChild)) {
+            String strval = concatenateUnaryStrings(rightNode.getChildren());
+
+            if (strval.equals("le")) { //$NON-NLS-1$
+                return ByteOrder.LITTLE_ENDIAN;
+            } else if (strval.equals("be") || strval.equals("network")) { //$NON-NLS-1$ //$NON-NLS-2$
+                return ByteOrder.BIG_ENDIAN;
+            } else if (strval.equals("native")) { //$NON-NLS-1$
+                return trace.getByteOrder();
+            } else {
+                throw new ParseException("Invalid value for byte order"); //$NON-NLS-1$
+            }
+        }
+        throw new ParseException("Invalid value for byte order"); //$NON-NLS-1$
+    }
+
+    /**
+     * Determines if the given value is a valid alignment value.
+     *
+     * @param alignment
+     *            The value to check.
+     * @return True if it is valid.
+     */
+    private static boolean isValidAlignment(long alignment) {
+        return !((alignment <= 0) || ((alignment & (alignment - 1)) != 0));
+    }
+
+    /**
+     * Gets the value of a "size" integer attribute.
+     *
+     * @param rightNode
+     *            A CTF_RIGHT node.
+     * @return The "size" value.
+     * @throws ParseException
+     */
+    private static long getSize(CommonTree rightNode) throws ParseException {
+        assert (rightNode.getType() == CTFParser.CTF_RIGHT);
+        assert (rightNode.getChildCount() > 0);
+
+        CommonTree firstChild = (CommonTree) rightNode.getChild(0);
+
+        if (isUnaryInteger(firstChild)) {
+            if (rightNode.getChildCount() > 1) {
+                throw new ParseException("Invalid value for size"); //$NON-NLS-1$
+            }
+
+            long size = parseUnaryInteger(firstChild);
+
+            if (size < 1) {
+                throw new ParseException("Invalid value for size"); //$NON-NLS-1$
+            }
+
+            return size;
+        }
+        throw new ParseException("Invalid value for size"); //$NON-NLS-1$
+    }
+
+    /**
+     * Gets the value of a "align" integer or struct attribute.
+     *
+     * @param node
+     *            A CTF_RIGHT node or directly an unary integer.
+     * @return The align value.
+     * @throws ParseException
+     */
+    private static long getAlignment(CommonTree node) throws ParseException {
+        assert (isUnaryExpression(node) || (node.getType() == CTFParser.CTF_RIGHT));
+
+        /*
+         * If a CTF_RIGHT node was passed, call getAlignment with the first
+         * child
+         */
+        if (node.getType() == CTFParser.CTF_RIGHT) {
+            if (node.getChildCount() > 1) {
+                throw new ParseException("Invalid alignment value"); //$NON-NLS-1$
+            }
+
+            return getAlignment((CommonTree) node.getChild(0));
+        } else if (isUnaryInteger(node)) {
+            long alignment = parseUnaryInteger(node);
+
+            if (!isValidAlignment(alignment)) {
+                throw new ParseException("Invalid value for alignment : " //$NON-NLS-1$
+                        + alignment);
+            }
+
+            return alignment;
+        }
+        throw new ParseException("Invalid value for alignment"); //$NON-NLS-1$
+    }
+
+    /**
+     * Gets the value of a "base" integer attribute.
+     *
+     * @param rightNode
+     *            An CTF_RIGHT node.
+     * @return The "base" value.
+     * @throws ParseException
+     */
+    private static int getBase(CommonTree rightNode) throws ParseException {
+        assert (rightNode.getType() == CTFParser.CTF_RIGHT);
+        assert (rightNode.getChildCount() > 0);
+
+        CommonTree firstChild = (CommonTree) rightNode.getChild(0);
+
+        if (isUnaryInteger(firstChild)) {
+            if (rightNode.getChildCount() > 1) {
+                throw new ParseException("invalid base value"); //$NON-NLS-1$
+            }
+
+            long intval = parseUnaryInteger(firstChild);
+            if ((intval == 2) || (intval == 8) || (intval == 10)
+                    || (intval == 16)) {
+                return (int) intval;
+            }
+            throw new ParseException("Invalid value for base"); //$NON-NLS-1$
+        } else if (isUnaryString(firstChild)) {
+            String strval = concatenateUnaryStrings(rightNode.getChildren());
+
+            if (strval.equals("decimal") || strval.equals("dec") //$NON-NLS-1$ //$NON-NLS-2$
+                    || strval.equals("d") || strval.equals("i") //$NON-NLS-1$ //$NON-NLS-2$
+                    || strval.equals("u")) { //$NON-NLS-1$
+                return 10;
+            } else if (strval.equals("hexadecimal") || strval.equals("hex") //$NON-NLS-1$ //$NON-NLS-2$
+                    || strval.equals("x") || strval.equals("X") //$NON-NLS-1$ //$NON-NLS-2$
+                    || strval.equals("p")) { //$NON-NLS-1$
+                return 16;
+            } else if (strval.equals("octal") || strval.equals("oct") //$NON-NLS-1$ //$NON-NLS-2$
+                    || strval.equals("o")) { //$NON-NLS-1$
+                return 8;
+            } else if (strval.equals("binary") || strval.equals("b")) { //$NON-NLS-1$ //$NON-NLS-2$
+                return 2;
+            } else {
+                throw new ParseException("Invalid value for base"); //$NON-NLS-1$
+            }
+        } else {
+            throw new ParseException("invalid value for base"); //$NON-NLS-1$
+        }
+    }
+
+    /**
+     * Gets the value of an "encoding" integer attribute.
+     *
+     * @param rightNode
+     *            A CTF_RIGHT node.
+     * @return The "encoding" value.
+     * @throws ParseException
+     */
+    private static Encoding getEncoding(CommonTree rightNode)
+            throws ParseException {
+        assert (rightNode.getType() == CTFParser.CTF_RIGHT);
+
+        CommonTree firstChild = (CommonTree) rightNode.getChild(0);
+
+        if (isUnaryString(firstChild)) {
+            String strval = concatenateUnaryStrings(rightNode.getChildren());
+
+            if (strval.equals("UTF8")) { //$NON-NLS-1$
+                return Encoding.UTF8;
+            } else if (strval.equals("ASCII")) { //$NON-NLS-1$
+                return Encoding.ASCII;
+            } else if (strval.equals("none")) { //$NON-NLS-1$
+                return Encoding.NONE;
+            } else {
+                throw new ParseException("Invalid value for encoding"); //$NON-NLS-1$
+            }
+        }
+        throw new ParseException("Invalid value for encoding"); //$NON-NLS-1$
+    }
+
+    private static long getStreamID(CommonTree rightNode) throws ParseException {
+        assert (rightNode.getType() == CTFParser.CTF_RIGHT);
+        assert (rightNode.getChildCount() > 0);
+
+        CommonTree firstChild = (CommonTree) rightNode.getChild(0);
+
+        if (isUnaryInteger(firstChild)) {
+            if (rightNode.getChildCount() > 1) {
+                throw new ParseException("invalid value for stream id"); //$NON-NLS-1$
+            }
+
+            long intval = parseUnaryInteger(firstChild);
+
+            return intval;
+        }
+        throw new ParseException("invalid value for stream id"); //$NON-NLS-1$
+    }
+
+    private static String getEventName(CommonTree rightNode)
+            throws ParseException {
+        assert (rightNode.getType() == CTFParser.CTF_RIGHT);
+        assert (rightNode.getChildCount() > 0);
+
+        CommonTree firstChild = (CommonTree) rightNode.getChild(0);
+
+        if (isUnaryString(firstChild)) {
+            String str = concatenateUnaryStrings(rightNode.getChildren());
+
+            return str;
+        }
+        throw new ParseException("invalid value for event name"); //$NON-NLS-1$
+    }
+
+    private static long getEventID(CommonTree rightNode) throws ParseException {
+        assert (rightNode.getType() == CTFParser.CTF_RIGHT);
+        assert (rightNode.getChildCount() > 0);
+
+        CommonTree firstChild = (CommonTree) rightNode.getChild(0);
+
+        if (isUnaryInteger(firstChild)) {
+            if (rightNode.getChildCount() > 1) {
+                throw new ParseException("invalid value for event id"); //$NON-NLS-1$
+            }
+
+            long intval = parseUnaryInteger(firstChild);
+
+            return intval;
+        }
+        throw new ParseException("invalid value for event id"); //$NON-NLS-1$
+    }
+
+    /**
+     * Concatenates a list of unary strings separated by arrows (->) or dots.
+     *
+     * @param strings
+     *            A list, first element being an unary string, subsequent
+     *            elements being ARROW or DOT nodes with unary strings as child.
+     * @return The string representation of the unary string chain.
+     */
+    private static String concatenateUnaryStrings(List<CommonTree> strings) {
+        assert ((strings != null) && (strings.size() > 0));
+
+        StringBuilder sb = new StringBuilder();
+
+        CommonTree first = strings.get(0);
+        sb.append(parseUnaryString(first));
+
+        boolean isFirst = true;
+
+        for (CommonTree ref : strings) {
+            if (isFirst) {
+                isFirst = false;
+                continue;
+            }
+
+            assert ((ref.getType() == CTFParser.ARROW) || (ref.getType() == CTFParser.DOT));
+            assert (ref.getChildCount() == 1);
+
+            CommonTree id = (CommonTree) ref.getChild(0);
+
+            if (ref.getType() == CTFParser.ARROW) {
+                sb.append("->"); //$NON-NLS-1$
+            } else { /* DOT */
+                sb.append('.');
+            }
+
+            sb.append(parseUnaryString(id));
+        }
+
+        return sb.toString();
+    }
+
+    /**
+     * Throws a ParseException stating that the parent-child relation between
+     * the given node and its parent is not valid. It means that the shape of
+     * the AST is unexpected.
+     *
+     * @param child
+     *            The invalid child node.
+     * @throws ParseException
+     */
+    private static void childTypeError(CommonTree child) throws ParseException {
+        CommonTree parent = (CommonTree) child.getParent();
+        String error = "Parent " + CTFParser.tokenNames[parent.getType()] //$NON-NLS-1$
+                + " can't have a child of type " //$NON-NLS-1$
+                + CTFParser.tokenNames[child.getType()] + "."; //$NON-NLS-1$
+
+        throw new ParseException(error);
+    }
+
+    // ------------------------------------------------------------------------
+    // Scope management
+    // ------------------------------------------------------------------------
+
+    /**
+     * Adds a new declaration scope on the top of the scope stack.
+     */
+    private void pushScope() {
+        scope = new DeclarationScope(scope);
+    }
+
+    /**
+     * Removes the top declaration scope from the scope stack.
+     */
+    private void popScope() {
+        assert (scope != null);
+        scope = scope.getParentScope();
+    }
+
+    /**
+     * Returns the current declaration scope.
+     *
+     * @return The current declaration scope.
+     */
+    private DeclarationScope getCurrentScope() {
+        assert (scope != null);
+        return scope;
+    }
+
+}
diff --git a/org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/internal/ctf/core/trace/StreamInputPacketIndexEntry.java b/org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/internal/ctf/core/trace/StreamInputPacketIndexEntry.java
new file mode 100644 (file)
index 0000000..f996845
--- /dev/null
@@ -0,0 +1,216 @@
+/*******************************************************************************
+ * Copyright (c) 2011-2012 Ericsson, Ecole Polytechnique de Montreal and others
+ *
+ * All rights reserved. This program and the accompanying materials are made
+ * available under the terms of the Eclipse Public License v1.0 which
+ * accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors: Matthew Khouzam - Initial API and implementation
+ * Contributors: Simon Marchi - Initial API and implementation
+ *******************************************************************************/
+
+package org.eclipse.linuxtools.internal.ctf.core.trace;
+
+/**
+ * <b><u>StreamInputPacketIndexEntry</u></b>
+ * <p>
+ * Represents an entry in the index of event packets.
+ */
+public class StreamInputPacketIndexEntry {
+
+    // ------------------------------------------------------------------------
+    // Attributes
+    // ------------------------------------------------------------------------
+
+
+
+    /**
+     * Offset of the packet in the file, in bytes
+     */
+    final private long offsetBytes;
+
+    /**
+     * Offset of the data in the packet, in bits
+     */
+    private int dataOffsetBits = 0;
+
+    /**
+     * Packet size, in bits
+     */
+    private int packetSizeBits = 0;
+
+    /**
+     * Content size, in bits
+     */
+    private int contentSizeBits = 0;
+
+    /**
+     * Begin timestamp
+     */
+    private long timestampBegin = 0;
+
+    /**
+     * End timestamp
+     */
+    private long timestampEnd = 0;
+
+
+    private long indexBegin = Long.MAX_VALUE;
+
+    private long indexEnd = Long.MAX_VALUE;
+
+    // ------------------------------------------------------------------------
+    // Constructors
+    // ------------------------------------------------------------------------
+
+    /**
+     * Constructs an index entry.
+     *
+     * @param offset
+     *            The offset of the packet in the file, in bytes.
+     */
+
+    public StreamInputPacketIndexEntry(long offset) {
+        this.offsetBytes = offset;
+    }
+
+    // ------------------------------------------------------------------------
+    // Operations
+    // ------------------------------------------------------------------------
+
+    /**
+     * Returns whether the packet includes (inclusively) the given timestamp in
+     * the begin-end timestamp range.
+     *
+     * @param ts
+     *            The timestamp to check.
+     * @return True if the packet includes the timestamp.
+     */
+    boolean includes(long ts) {
+        return (ts >= timestampBegin) && (ts <= timestampEnd);
+    }
+
+    boolean includesIndex(long index){
+        return (index >= indexBegin) && (index <= indexEnd);
+    }
+    /* (non-Javadoc)
+     * @see java.lang.Object#toString()
+     */
+    @Override
+    public String toString() {
+        return "StreamInputPacketIndexEntry [offsetBytes=" + offsetBytes //$NON-NLS-1$
+                + ", timestampBegin=" + timestampBegin + ", timestampEnd=" //$NON-NLS-1$ //$NON-NLS-2$
+                + timestampEnd + ", indexBegin=" + indexBegin + ", indexEnd=" //$NON-NLS-1$ //$NON-NLS-2$
+                + indexEnd + "]"; //$NON-NLS-1$
+    }
+
+    // ------------------------------------------------------------------------
+    // Getters and Setters
+    // ------------------------------------------------------------------------
+
+    /**
+     * @return the offsetBytes
+     */
+    public long getOffsetBytes() {
+        return offsetBytes;
+    }
+
+    /**
+     * @return the dataOffsetBits
+     */
+    public int getDataOffsetBits() {
+        return dataOffsetBits;
+    }
+
+    /**
+     * @param dataOffsetBits the dataOffsetBits to set
+     */
+    public void setDataOffsetBits(int dataOffsetBits) {
+        this.dataOffsetBits = dataOffsetBits;
+    }
+
+    /**
+     * @return the packetSizeBits
+     */
+    public int getPacketSizeBits() {
+        return packetSizeBits;
+    }
+
+    /**
+     * @param packetSizeBits the packetSizeBits to set
+     */
+    public void setPacketSizeBits(int packetSizeBits) {
+        this.packetSizeBits = packetSizeBits;
+    }
+
+    /**
+     * @return the contentSizeBits
+     */
+    public int getContentSizeBits() {
+        return contentSizeBits;
+    }
+
+    /**
+     * @param contentSizeBits the contentSizeBits to set
+     */
+    public void setContentSizeBits(int contentSizeBits) {
+        this.contentSizeBits = contentSizeBits;
+    }
+
+    /**
+     * @return the timestampBegin
+     */
+    public long getTimestampBegin() {
+        return timestampBegin;
+    }
+
+    /**
+     * @param timestampBegin the timestampBegin to set
+     */
+    public void setTimestampBegin(long timestampBegin) {
+        this.timestampBegin = timestampBegin;
+    }
+
+    /**
+     * @return the timestampEnd
+     */
+    public long getTimestampEnd() {
+        return timestampEnd;
+    }
+
+    /**
+     * @param timestampEnd the timestampEnd to set
+     */
+    public void setTimestampEnd(long timestampEnd) {
+        this.timestampEnd = timestampEnd;
+    }
+
+    /**
+     * @return the indexBegin
+     */
+    public long getIndexBegin() {
+        return indexBegin;
+    }
+
+    /**
+     * @param indexBegin the indexBegin to set
+     */
+    public void setIndexBegin(long indexBegin) {
+        this.indexBegin = indexBegin;
+    }
+
+    /**
+     * @return the indexEnd
+     */
+    public long getIndexEnd() {
+        return indexEnd;
+    }
+
+    /**
+     * @param indexEnd the indexEnd to set
+     */
+    public void setIndexEnd(long indexEnd) {
+        this.indexEnd = indexEnd;
+    }
+}
diff --git a/org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/internal/ctf/core/trace/StreamInputReaderComparator.java b/org.eclipse.linuxtools.ctf.core/src/org/eclipse/linuxtools/internal/ctf/core/trace/StreamInputReaderComparator.java
new file mode 100644 (file)
index 0000000..43d5962
--- /dev/null
@@ -0,0 +1,53 @@
+/*******************************************************************************
+ * Copyright (c) 2011-2012 Ericsson, Ecole Polytechnique de Montreal and others
+ *
+ * All rights reserved. This program and the accompanying materials are made
+ * available under the terms of the Eclipse Public License v1.0 which
+ * accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors: Matthew Khouzam - Initial API and implementation
+ * Contributors: Simon Marchi - Initial API and implementation
+ *******************************************************************************/
+
+package org.eclipse.linuxtools.internal.ctf.core.trace;
+
+import java.io.Serializable;
+import java.util.Comparator;
+
+import org.eclipse.linuxtools.ctf.core.trace.StreamInputReader;
+
+/**
+ * <b><u>StreamInputReaderComparator</u></b>
+ * <p>
+ * TODO Implement me. Please.
+ */
+public class StreamInputReaderComparator implements
+        Comparator<StreamInputReader>, Serializable {
+
+    // ------------------------------------------------------------------------
+    // Constants
+    // ------------------------------------------------------------------------
+
+    private static final long serialVersionUID = 7477206132343139753L;
+
+    // ------------------------------------------------------------------------
+    // Operations
+    // ------------------------------------------------------------------------
+
+    @Override
+    public int compare(StreamInputReader a, StreamInputReader b) {
+        // TODO: use unsigned comparison to avoid sign errors if needed
+        long ta = a.getCurrentEvent().timestamp;
+        long tb = b.getCurrentEvent().timestamp;
+
+        if (ta < tb) {
+            return -1;
+        } else if (ta > tb) {
+            return 1;
+        } else {
+            return 0;
+        }
+    }
+
+}
This page took 0.104036 seconds and 5 git commands to generate.