use of org.eclipse.tracecompass.internal.provisional.analysis.lami.core.types.LamiTimeRange in project tracecompass by tracecompass.
the class LamiTimeRangeDurationAspect method resolveString.
@Override
@Nullable
public String resolveString(LamiTableEntry entry) {
LamiData data = entry.getValue(fColIndex);
if (data instanceof LamiTimeRange) {
LamiTimeRange range = (LamiTimeRange) data;
// TODO: Consider low and high limits here.
Number duration = range.getDuration();
if (duration != null) {
return String.valueOf(duration.longValue());
}
}
return data.toString();
}
use of org.eclipse.tracecompass.internal.provisional.analysis.lami.core.types.LamiTimeRange in project tracecompass by tracecompass.
the class LamiTimeRangeEndAspect method resolveNumber.
@Override
@Nullable
public Number resolveNumber(@NonNull LamiTableEntry entry) {
LamiData data = entry.getValue(getColIndex());
if (data instanceof LamiTimeRange) {
LamiTimeRange range = (LamiTimeRange) data;
LamiTimestamp ts = range.getEnd();
// TODO: Consider low and high limits here.
return ts.getValue();
}
return null;
}
use of org.eclipse.tracecompass.internal.provisional.analysis.lami.core.types.LamiTimeRange in project tracecompass by tracecompass.
the class LamiAnalysis method execute.
@Override
public List<LamiResultTable> execute(ITmfTrace trace, @Nullable TmfTimeRange timeRange, String extraParamsString, IProgressMonitor monitor) throws CoreException {
/* Should have been called already, but in case it was not */
initialize();
@NonNull final String tracePath = checkNotNull(trace.getPath());
@NonNull final String trimmedExtraParamsString = checkNotNull(extraParamsString.trim());
final List<String> extraParams = ShellUtils.commandStringToArgs(trimmedExtraParamsString);
ImmutableList.Builder<String> builder = getBaseCommand(timeRange);
builder.addAll(extraParams);
builder.add(tracePath);
List<String> command = builder.build();
TraceCompassLogUtils.traceInstant(LOGGER, Level.INFO, RUNNING_EXECUTE_COMMAND, COMMAND, command);
String output = getResultsFromCommand(command, monitor);
if (output.isEmpty()) {
IStatus status = new Status(IStatus.INFO, Activator.instance().getPluginId(), Messages.LamiAnalysis_NoResults);
throw new CoreException(status);
}
/*
* {
* "results": [
* {
* "time-range": {
* "type": "time-range",
* "begin": 1444334398154194201,
* "end": 1444334425194487548
* },
* "class": "syscall-latency",
* "data": [
* [
* {"type": "syscall", "name": "open"},
* 45,
* {"type": "duration", "value": 5562},
* {"type": "duration", "value": 13835},
* {"type": "duration", "value": 77683},
* {"type": "duration", "value": 15263}
* ],
* [
* {"type": "syscall", "name": "read"},
* 109,
* {"type": "duration", "value": 316},
* {"type": "duration", "value": 5774},
* {"type": "duration", "value": 62569},
* {"type": "duration", "value": 9277}
* ]
* ]
* },
* {
* "time-range": {
* "type": "time-range",
* "begin": 1444334425194487549,
* "end": 1444334425254887190
* },
* "class": "syscall-latency",
* "data": [
* [
* {"type": "syscall", "name": "open"},
* 45,
* {"type": "duration", "value": 1578},
* {"type": "duration", "value": 16648},
* {"type": "duration", "value": 15444},
* {"type": "duration", "value": 68540}
* ],
* [
* {"type": "syscall", "name": "read"},
* 109,
* {"type": "duration", "value": 78},
* {"type": "duration", "value": 1948},
* {"type": "duration", "value": 11184},
* {"type": "duration", "value": 94670}
* ]
* ]
* }
* ]
* }
*
*/
ImmutableList.Builder<LamiResultTable> resultsBuilder = new ImmutableList.Builder<>();
try {
JSONObject obj = new JSONObject(output);
JSONArray results = obj.getJSONArray(LamiStrings.RESULTS);
if (results.length() == 0) {
/*
* No results were reported. This may be normal, but warn the
* user why a report won't be created.
*/
IStatus status = new Status(IStatus.INFO, Activator.instance().getPluginId(), Messages.LamiAnalysis_NoResults);
throw new CoreException(status);
}
for (int i = 0; i < results.length(); i++) {
JSONObject result = results.getJSONObject(i);
/* Parse the time-range */
JSONObject trObject = checkNotNull(result.getJSONObject(LamiStrings.TIME_RANGE));
LamiData trData = LamiData.createFromObject(trObject);
if (!(trData instanceof LamiTimeRange)) {
// $NON-NLS-1$
throw new JSONException("Time range did not have expected class type.");
}
LamiTimeRange tr = (LamiTimeRange) trData;
/* Parse the table's class */
LamiTableClass tableClass;
JSONObject tableClassObject = result.optJSONObject(LamiStrings.CLASS);
if (tableClassObject == null) {
/*
* "class" is just a standard string, indicating we use a
* metadata-defined table class as-is
*/
@NonNull String tableClassName = checkNotNull(result.getString(LamiStrings.CLASS));
tableClass = getTableClassFromName(tableClassName);
// FIXME Rest will become more generic eventually in the LAMI format.
} else if (tableClassObject.has(LamiStrings.INHERIT)) {
/*
* Dynamic title: We reuse an existing table class but
* override the title.
*/
String baseTableName = checkNotNull(tableClassObject.getString(LamiStrings.INHERIT));
LamiTableClass baseTableClass = getTableClassFromName(baseTableName);
String newTitle = checkNotNull(tableClassObject.getString(LamiStrings.TITLE));
tableClass = new LamiTableClass(baseTableClass, newTitle);
} else {
/*
* Dynamic column descriptions: we implement a new table
* class entirely.
*/
String title = checkNotNull(tableClassObject.getString(LamiStrings.TITLE));
JSONArray columnDescriptions = checkNotNull(tableClassObject.getJSONArray(LamiStrings.COLUMN_DESCRIPTIONS));
List<LamiTableEntryAspect> aspects = getAspectsFromColumnDescriptions(columnDescriptions);
tableClass = new LamiTableClass(nullToEmptyString(Messages.LamiAnalysis_DefaultDynamicTableName), title, aspects, Collections.emptySet());
}
/* Parse the "data", which is the array of rows */
JSONArray data = result.getJSONArray(LamiStrings.DATA);
ImmutableList.Builder<LamiTableEntry> dataBuilder = new ImmutableList.Builder<>();
for (int j = 0; j < data.length(); j++) {
/* A row is an array of cells */
JSONArray row = data.getJSONArray(j);
ImmutableList.Builder<LamiData> rowBuilder = ImmutableList.builder();
for (int k = 0; k < row.length(); k++) {
Object cellObject = checkNotNull(row.get(k));
LamiData cellValue = LamiData.createFromObject(cellObject);
rowBuilder.add(cellValue);
}
dataBuilder.add(new LamiTableEntry(rowBuilder.build()));
}
resultsBuilder.add(new LamiResultTable(tr, tableClass, dataBuilder.build()));
}
} catch (JSONException e) {
TraceCompassLogUtils.traceInstant(LOGGER, Level.WARNING, ERROR_PARSING_EXECUTION_OUTPUT, e.getMessage());
IStatus status = new Status(IStatus.ERROR, Activator.instance().getPluginId(), e.getMessage(), e);
throw new CoreException(status);
}
return resultsBuilder.build();
}
use of org.eclipse.tracecompass.internal.provisional.analysis.lami.core.types.LamiTimeRange in project tracecompass by tracecompass.
the class LamiTableEntry method getCorrespondingTimeRange.
/**
* Get the time range represented by this row.
*
* If more than one exists, one of them (usually the first) is returned.
*
* If there are no time ranges in this row, null is returned.
*
* @return The time range of this row
*/
@Nullable
public LamiTimeRange getCorrespondingTimeRange() {
/*
* If there is one or more time range(s) in the values, return the first
* one we find directly.
*/
Optional<LamiTimeRange> oTimerange = fValues.stream().filter(LamiTimeRange.class::isInstance).map(LamiTimeRange.class::cast).findFirst();
if (oTimerange.isPresent()) {
return oTimerange.get();
}
/* Look for individual timestamps instead */
List<LamiTimestamp> timestamps = fValues.stream().filter(LamiTimestamp.class::isInstance).map(LamiTimestamp.class::cast).collect(Collectors.toList());
if (timestamps.size() > 1) {
/* We can try using the first two timestamps to create a range (making sure it's valid) */
LamiTimestamp firstTs = timestamps.get(0);
LamiTimestamp secondTs = timestamps.get(1);
Number firstTsValue = firstTs.getValue();
Number secondTsValue = secondTs.getValue();
// TODO: Consider low and high limits in comparisons.
if (firstTsValue != null && secondTsValue != null && Long.compare(firstTsValue.longValue(), secondTsValue.longValue()) <= 0) {
return new LamiTimeRange(firstTs, secondTs);
}
}
if (!timestamps.isEmpty()) {
/* If there is only one timestamp, use it to create a punctual range */
LamiTimestamp ts = timestamps.get(0);
return new LamiTimeRange(ts, ts);
}
/* Didn't find any timestamp we can't use */
return null;
}
use of org.eclipse.tracecompass.internal.provisional.analysis.lami.core.types.LamiTimeRange in project tracecompass by tracecompass.
the class LamiReportViewTabPage method getEntriesIntersectingTimerange.
// ------------------------------------------------------------------------
// Util methods
// ------------------------------------------------------------------------
/**
* Util method that returns {@link LamiTableEntry} that intersects a
* {@link TmfTimeRange}.
*
* @param table
* The result table to search for entries
* @param range
* The time range itself
* @return The set of entries that intersect with the time range
*/
private static Set<Object> getEntriesIntersectingTimerange(LamiResultTable table, TmfTimeRange range) {
Set<Object> entries = new HashSet<>();
for (LamiTableEntry entry : table.getEntries()) {
LamiTimeRange lamiTimeRange = entry.getCorrespondingTimeRange();
/* Make sure the table has time ranges */
if (lamiTimeRange == null) {
return entries;
}
/* Get the timestamps from the time range */
/**
* TODO: Consider low and high limits of timestamps here.
*/
Number tsBeginValueNumber = lamiTimeRange.getBegin().getValue();
Number tsEndValueNumber = lamiTimeRange.getEnd().getValue();
if (tsBeginValueNumber == null || tsEndValueNumber == null) {
return entries;
}
/* Convert the timestamps into TMF timestamps */
ITmfTimestamp start = TmfTimestamp.fromNanos(tsBeginValueNumber.longValue());
ITmfTimestamp end = TmfTimestamp.fromNanos(tsEndValueNumber.longValue());
/* Add iff the time range intersects the the signal */
TmfTimeRange tempTimeRange = new TmfTimeRange(start, end);
if (tempTimeRange.getIntersection(range) != null) {
entries.add(entry);
}
}
return entries;
}
Aggregations