Skip to content

Commit f7786ce

Browse files
ctf: add static string type
Change-Id: Iaf2558ab50b1f47604da28f4529bd094135a4ce5 Signed-off-by: Matthew Khouzam <[email protected]>
1 parent a0ce0f7 commit f7786ce

File tree

4 files changed

+216
-3
lines changed

4 files changed

+216
-3
lines changed

ctf/org.eclipse.tracecompass.ctf.core/src/org/eclipse/tracecompass/internal/ctf/core/event/metadata/tsdl/TypeAliasParser.java

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,7 @@
2727
import org.eclipse.tracecompass.internal.ctf.core.event.metadata.tsdl.dynamicstring.DynamicLengthStringParser;
2828
import org.eclipse.tracecompass.internal.ctf.core.event.metadata.tsdl.enumeration.EnumParser;
2929
import org.eclipse.tracecompass.internal.ctf.core.event.metadata.tsdl.integer.IntegerDeclarationParser;
30+
import org.eclipse.tracecompass.internal.ctf.core.event.metadata.tsdl.staticstring.StaticLengthStringParser;
3031
import org.eclipse.tracecompass.internal.ctf.core.event.metadata.tsdl.string.StringDeclarationParser;
3132
import org.eclipse.tracecompass.internal.ctf.core.event.metadata.tsdl.variant.VariantParser;
3233
import org.eclipse.tracecompass.internal.ctf.core.event.types.ICTFMetadataNode;
@@ -161,7 +162,9 @@ public IDeclaration parse(ICTFMetadataNode typealias, ICommonTreeParserParameter
161162
} else if (JsonMetadataStrings.FIXED_UNSIGNED_ENUMERATION.equals(type)) {
162163
targetDeclaration = EnumParser.INSTANCE.parse(typealias, new EnumParser.Param(trace, scope));
163164
} else if (JsonMetadataStrings.DYNAMIC_LENGTH_STRING.equals(type)) {
164-
targetDeclaration = DynamicLengthStringParser.INSTANCE.parse(typealias, new DynamicLengthStringParser.Param(trace));
165+
targetDeclaration = DynamicLengthStringParser.INSTANCE.parse(typealias, new DynamicLengthStringParser.Param(trace));
166+
} else if (JsonMetadataStrings.STATIC_LENGTH_STRING.equals(type)) {
167+
targetDeclaration = StaticLengthStringParser.INSTANCE.parse(typealias, new StaticLengthStringParser.Param(trace));
165168
} else {
166169
throw new ParseException("Invalid field class: " + type); //$NON-NLS-1$
167170
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,102 @@
1+
/*******************************************************************************
2+
* Copyright (c) 2025 Ericsson
3+
*
4+
* All rights reserved. This program and the accompanying materials
5+
* are made available under the terms of the Eclipse Public License 2.0
6+
* which accompanies this distribution, and is available at
7+
* https://www.eclipse.org/legal/epl-2.0/
8+
*
9+
* SPDX-License-Identifier: EPL-2.0
10+
*******************************************************************************/
11+
package org.eclipse.tracecompass.internal.ctf.core.event.metadata.tsdl.staticstring;
12+
13+
import java.nio.charset.Charset;
14+
import java.nio.charset.StandardCharsets;
15+
16+
import org.eclipse.jdt.annotation.NonNullByDefault;
17+
import org.eclipse.tracecompass.ctf.core.event.types.IDeclaration;
18+
import org.eclipse.tracecompass.ctf.core.trace.CTFTrace;
19+
import org.eclipse.tracecompass.internal.ctf.core.event.metadata.AbstractScopedCommonTreeParser;
20+
import org.eclipse.tracecompass.internal.ctf.core.event.metadata.JsonStructureFieldMemberMetadataNode;
21+
import org.eclipse.tracecompass.internal.ctf.core.event.metadata.ParseException;
22+
import org.eclipse.tracecompass.internal.ctf.core.event.types.ICTFMetadataNode;
23+
import org.eclipse.tracecompass.internal.ctf.core.event.types.StaticLengthStringDeclaration;
24+
import org.eclipse.tracecompass.internal.ctf.core.utils.JsonMetadataStrings;
25+
26+
import com.google.gson.JsonElement;
27+
import com.google.gson.JsonObject;
28+
29+
/**
30+
* A dynamic-length string field class is an abstract string field class which
31+
* describes dynamic-length string fields.
32+
*
33+
* A dynamic-length string field is a sequence of zero or more contiguous
34+
* encoded Unicode codepoints. All the encoded codepoints of a dynamic-length
35+
* string field before the first "NULL" (U+0000) codepoint, if any, form the
36+
* resulting string value. The first U+0000 codepoint, if any, and all the
37+
* following bytes are considered padding (garbage data).
38+
*
39+
* The length, or number of bytes, of a dynamic-length string field is the
40+
* value of another, anterior (already encoded/decoded) length field. A
41+
* consumer can locate this length field thanks to the length-field-location
42+
* property of the dynamic-length string field class.
43+
*
44+
* @author Matthew Khouzam
45+
*/
46+
public final class StaticLengthStringParser extends AbstractScopedCommonTreeParser {
47+
48+
/**
49+
* Instance
50+
*/
51+
public static final StaticLengthStringParser INSTANCE = new StaticLengthStringParser();
52+
53+
private StaticLengthStringParser() {
54+
}
55+
56+
@Override
57+
public IDeclaration parse(ICTFMetadataNode node, ICommonTreeParserParameter param) throws ParseException {
58+
if (!(node instanceof JsonStructureFieldMemberMetadataNode)) {
59+
throw new ParseException("Dynamic-length string only supported in JSON metadata"); //$NON-NLS-1$
60+
}
61+
62+
JsonStructureFieldMemberMetadataNode member = (JsonStructureFieldMemberMetadataNode) node;
63+
JsonObject fieldClass = member.getFieldClass().getAsJsonObject();
64+
65+
JsonElement lengthField = fieldClass.get(JsonMetadataStrings.LENGTH);
66+
if (lengthField == null) {
67+
throw new ParseException("Dynamic-length string requires length-field-location property"); //$NON-NLS-1$
68+
}
69+
JsonElement encodingField = fieldClass.get(JsonMetadataStrings.ENCODING);
70+
int length = lengthField.getAsInt();
71+
Charset encoding = encodingField != null ?
72+
JsonMetadataStrings.ENCODINGS.getOrDefault(encodingField.getAsString(), StandardCharsets.UTF_8) :
73+
StandardCharsets.UTF_8;
74+
return new StaticLengthStringDeclaration(length, encoding);
75+
}
76+
77+
/**
78+
* Parameters for the dynamic-length string parser
79+
*/
80+
@NonNullByDefault
81+
public static final class Param implements ICommonTreeParserParameter {
82+
private final CTFTrace fTrace;
83+
84+
/**
85+
* Parameter constructor
86+
*
87+
* @param trace the trace
88+
*/
89+
public Param(CTFTrace trace) {
90+
fTrace = trace;
91+
}
92+
93+
/**
94+
* Get the trace
95+
*
96+
* @return the trace
97+
*/
98+
public CTFTrace getTrace() {
99+
return fTrace;
100+
}
101+
}
102+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,106 @@
1+
/*******************************************************************************
2+
* Copyright (c) 2025 Ericsson
3+
*
4+
* All rights reserved. This program and the accompanying materials
5+
* are made available under the terms of the Eclipse Public License 2.0
6+
* which accompanies this distribution, and is available at
7+
* https://www.eclipse.org/legal/epl-2.0/
8+
*
9+
* SPDX-License-Identifier: EPL-2.0
10+
*******************************************************************************/
11+
package org.eclipse.tracecompass.internal.ctf.core.event.types;
12+
13+
import java.nio.charset.Charset;
14+
15+
import org.eclipse.jdt.annotation.Nullable;
16+
import org.eclipse.tracecompass.ctf.core.CTFException;
17+
import org.eclipse.tracecompass.ctf.core.event.io.BitBuffer;
18+
import org.eclipse.tracecompass.ctf.core.event.scope.IDefinitionScope;
19+
import org.eclipse.tracecompass.ctf.core.event.types.Declaration;
20+
import org.eclipse.tracecompass.ctf.core.event.types.IDeclaration;
21+
import org.eclipse.tracecompass.ctf.core.event.types.StringDefinition2;
22+
23+
/**
24+
* Dynamic-length string declaration with encoding support
25+
*
26+
* @author Matthew Khouzam
27+
*/
28+
public class StaticLengthStringDeclaration extends Declaration {
29+
30+
private final Charset fEncoding;
31+
private final int fLength;
32+
33+
/**
34+
* Constructor
35+
*
36+
* @param lengthName
37+
* the name of the length field
38+
* @param encoding
39+
* the character encoding
40+
*/
41+
public StaticLengthStringDeclaration(int length, Charset encoding) {
42+
fLength = length;
43+
fEncoding = encoding;
44+
}
45+
46+
/**
47+
* Get the encoding
48+
*
49+
* @return the character encoding
50+
*/
51+
public Charset getEncoding() {
52+
return fEncoding;
53+
}
54+
55+
/**
56+
* Get the length
57+
*
58+
* @return the length
59+
*/
60+
public int getLength() {
61+
return fLength;
62+
}
63+
64+
@Override
65+
public StringDefinition2 createDefinition(@Nullable IDefinitionScope definitionScope, String fieldName, BitBuffer input) throws CTFException {
66+
long rawLength = fLength;
67+
if (rawLength < 0) {
68+
throw new CTFException("Cannot have a length < 0, declared = " + rawLength); //$NON-NLS-1$
69+
}
70+
if (rawLength > 1e6) {
71+
throw new CTFException("Cannot have a length > 1000000, declared = " + rawLength); //$NON-NLS-1$
72+
}
73+
int length = (int) rawLength;
74+
byte[] bytes = new byte[length];
75+
for (int i = 0; i < length; i++) {
76+
bytes[i] = (byte) input.get(Byte.SIZE, false);
77+
}
78+
String value = new String(bytes, fEncoding);
79+
int nullIndex = value.indexOf('\0');
80+
if (nullIndex >= 0) {
81+
value = value.substring(0, nullIndex);
82+
}
83+
return new StringDefinition2(this, definitionScope, fieldName, value);
84+
}
85+
86+
@Override
87+
public long getAlignment() {
88+
return Byte.SIZE;
89+
}
90+
91+
@Override
92+
public int getMaximumSize() {
93+
return Integer.MAX_VALUE;
94+
}
95+
96+
@Override
97+
public String toString() {
98+
return "dynamic_string[" + fLength + "]<" + fEncoding.name() + ">"; //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$
99+
}
100+
101+
@Override
102+
public boolean isBinaryEquivalent(IDeclaration other) {
103+
// TODO Auto-generated method stub
104+
return false;
105+
}
106+
}

ctf/org.eclipse.tracecompass.ctf.core/src/org/eclipse/tracecompass/internal/ctf/core/utils/JsonMetadataStrings.java

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -210,6 +210,8 @@ private JsonMetadataStrings() {
210210
*/
211211
public static final String ENCODING = "encoding"; //$NON-NLS-1$
212212

213-
214-
213+
/**
214+
* Static length string
215+
*/
216+
public static final String STATIC_LENGTH_STRING = "static-length-string"; //$NON-NLS-1$
215217
}

0 commit comments

Comments
 (0)