The "syscall entry" and "syscall exit" events were renamed in LTTng 2.6.
This patch adds a new trace layout, which extends the base LTTng definitions,
but updates the system call event names.
"syscall exit" also had to be changed to a prefix, because LTTng 2.6 now lists
the syscall name in exits too. We don't make use of it though, so it shouldn't
affect other tracers who don't.
Also required updating the CFV/RV to only display the non-prefix part of the
syscall name, no matter what layout is used underneat.
Change-Id: I9061b0dff92daa11894d951c09ed3dffe80e4d1b
Signed-off-by: Alexandre Montplaisir <alexmonthy@voxpopuli.im>
Reviewed-on: https://git.eclipse.org/r/36199
Reviewed-by: Matthew Khouzam <matthew.khouzam@ericsson.com>
Tested-by: Hudson CI
org.eclipse.tracecompass.tmf.ctf.core,
org.eclipse.tracecompass.lttng2.control.core
Export-Package: org.eclipse.tracecompass.internal.lttng2.kernel.core;x-friends:="org.eclipse.tracecompass.lttng2.kernel.ui,org.eclipse.tracecompass.lttng2.kernel.core.tests",
- org.eclipse.tracecompass.internal.lttng2.kernel.core.trace.layout;x-friends:="org.eclipse.tracecompass.lttng2.kernel.core.tests",
+ org.eclipse.tracecompass.internal.lttng2.kernel.core.trace.layout;x-friends:="org.eclipse.tracecompass.lttng2.kernel.core.tests,org.eclipse.tracecompass.lttng2.kernel.ui",
org.eclipse.tracecompass.lttng2.kernel.core.analysis.cpuusage,
org.eclipse.tracecompass.lttng2.kernel.core.analysis.kernel,
org.eclipse.tracecompass.lttng2.kernel.core.event.matching,
String eventStatedumpProcessState();
String eventSyscallEntryPrefix();
String eventCompatSyscallEntryPrefix();
- String eventSyscallExit();
+ String eventSyscallExitPrefix();
// ------------------------------------------------------------------------
// Event field names
--- /dev/null
+/*******************************************************************************
+ * Copyright (c) 2014 Ericsson
+ *
+ * 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:
+ * Alexandre Montplaisir - Initial API and implementation
+ ******************************************************************************/
+
+package org.eclipse.tracecompass.internal.lttng2.kernel.core.trace.layout;
+
+/**
+ * This file defines all the known event and field names for LTTng kernel
+ * traces, for versions of lttng-modules 2.6 and above.
+ *
+ * @author Alexandre Montplaisir
+ */
+public class Lttng26EventLayout extends LttngEventLayout {
+
+ private Lttng26EventLayout() {}
+
+ private static final Lttng26EventLayout INSTANCE = new Lttng26EventLayout();
+
+ public static Lttng26EventLayout getInstance() {
+ return INSTANCE;
+ }
+
+ // ------------------------------------------------------------------------
+ // New event names in these versions
+ // ------------------------------------------------------------------------
+
+ @Override
+ public String eventSyscallEntryPrefix() {
+ return "syscall_entry_"; //$NON-NLS-1$
+ }
+
+ @Override
+ public String eventCompatSyscallEntryPrefix() {
+ return "compat_syscall_entry_"; //$NON-NLS-1$
+ }
+
+ @Override
+ public String eventSyscallExitPrefix() {
+ return "syscall_exit_"; //$NON-NLS-1$
+ }
+}
import com.google.common.collect.ImmutableList;
/**
- * This file defines all the known event and field names for LTTng 2.0 kernel
- * traces.
+ * This file defines all the known event and field names for LTTng kernel
+ * traces, for versions of lttng-modules up to 2.5.
*
* These should not be externalized, since they need to match exactly what the
* tracer outputs. If you want to localize them in a view, you should do a
public class LttngEventLayout implements IKernelAnalysisEventLayout {
/* Event names */
- private static final String EXIT_SYSCALL = "exit_syscall";
private static final String IRQ_HANDLER_ENTRY = "irq_handler_entry";
private static final String IRQ_HANDLER_EXIT = "irq_handler_exit";
private static final String SOFTIRQ_ENTRY = "softirq_entry";
private static final String SCHED_PROCESS_FREE = "sched_process_free";
private static final String STATEDUMP_PROCESS_STATE = "lttng_statedump_process_state";
- private static final String SYSCALL_PREFIX = "sys_";
- private static final String COMPAT_SYSCALL_PREFIX = "compat_sys_";
+ private static final String SYSCALL_ENTRY_PREFIX = "sys_";
+ private static final String COMPAT_SYSCALL_ENTRY_PREFIX = "compat_sys_";
+ private static final String SYSCALL_EXIT_PREFIX = "exit_syscall";
/* Field names */
private static final String IRQ = "irq";
private static final String CHILD_TID = "child_tid";
/** All instances are the same. Only provide a static instance getter */
- private LttngEventLayout() {
+ protected LttngEventLayout() {
}
private static final IKernelAnalysisEventLayout INSTANCE = new LttngEventLayout();
public String eventStatedumpProcessState() {
return STATEDUMP_PROCESS_STATE;
}
- @Override
- public String eventSyscallExit() {
- return EXIT_SYSCALL;
- }
@Override
public String eventSyscallEntryPrefix() {
- return SYSCALL_PREFIX;
+ return SYSCALL_ENTRY_PREFIX;
}
@Override
public String eventCompatSyscallEntryPrefix() {
- return COMPAT_SYSCALL_PREFIX;
+ return COMPAT_SYSCALL_ENTRY_PREFIX;
+ }
+
+ @Override
+ public String eventSyscallExitPrefix() {
+ return SYSCALL_EXIT_PREFIX;
}
// ------------------------------------------------------------------------
* Version number of this state provider. Please bump this if you modify the
* contents of the generated state history in some way.
*/
- private static final int VERSION = 4;
+ private static final int VERSION = 5;
- private static final int SYSCALL_EXIT_INDEX = 0;
private static final int IRQ_HANDLER_ENTRY_INDEX = 1;
private static final int IRQ_HANDLER_EXIT_INDEX = 2;
private static final int SOFT_IRQ_ENTRY_INDEX = 3;
private static Map<String, Integer> buildEventNames(IKernelAnalysisEventLayout layout) {
ImmutableMap.Builder<String, Integer> builder = ImmutableMap.builder();
- builder.put(layout.eventSyscallExit(), SYSCALL_EXIT_INDEX);
builder.put(layout.eventIrqHandlerEntry(), IRQ_HANDLER_ENTRY_INDEX);
builder.put(layout.eventIrqHandlerExit(), IRQ_HANDLER_EXIT_INDEX);
builder.put(layout.eventSoftIrqEntry(), SOFT_IRQ_ENTRY_INDEX);
int intval = (idx == null ? -1 : idx.intValue());
switch (intval) {
- case SYSCALL_EXIT_INDEX:
- {
- /* Clear the current system call on the process */
- quark = ss.getQuarkRelativeAndAdd(currentThreadNode, Attributes.SYSTEM_CALL);
- value = TmfStateValue.nullValue();
- ss.modifyAttribute(ts, value, quark);
-
- /* Put the process' status back to user mode */
- quark = ss.getQuarkRelativeAndAdd(currentThreadNode, Attributes.STATUS);
- value = StateValues.PROCESS_STATUS_RUN_USERMODE_VALUE;
- ss.modifyAttribute(ts, value, quark);
-
- /* Put the CPU's status back to user mode */
- quark = ss.getQuarkRelativeAndAdd(currentCPUNode, Attributes.STATUS);
- value = StateValues.CPU_STATUS_RUN_USERMODE_VALUE;
- ss.modifyAttribute(ts, value, quark);
- }
- break;
-
case IRQ_HANDLER_ENTRY_INDEX:
{
Integer irqId = ((Long) event.getContent().getField(fLayout.fieldIrq()).getValue()).intValue();
{
if (eventName.startsWith(fLayout.eventSyscallEntryPrefix())
|| eventName.startsWith(fLayout.eventCompatSyscallEntryPrefix())) {
- /*
- * This is a replacement for the old sys_enter event. Now
- * syscall names are listed into the event type
- */
/* Assign the new system call to the process */
quark = ss.getQuarkRelativeAndAdd(currentThreadNode, Attributes.SYSTEM_CALL);
quark = ss.getQuarkRelativeAndAdd(currentCPUNode, Attributes.STATUS);
value = StateValues.CPU_STATUS_RUN_SYSCALL_VALUE;
ss.modifyAttribute(ts, value, quark);
+
+ } else if (eventName.startsWith(fLayout.eventSyscallExitPrefix())) {
+
+ /* Clear the current system call on the process */
+ quark = ss.getQuarkRelativeAndAdd(currentThreadNode, Attributes.SYSTEM_CALL);
+ value = TmfStateValue.nullValue();
+ ss.modifyAttribute(ts, value, quark);
+
+ /* Put the process' status back to user mode */
+ quark = ss.getQuarkRelativeAndAdd(currentThreadNode, Attributes.STATUS);
+ value = StateValues.PROCESS_STATUS_RUN_USERMODE_VALUE;
+ ss.modifyAttribute(ts, value, quark);
+
+ /* Put the CPU's status back to user mode */
+ quark = ss.getQuarkRelativeAndAdd(currentCPUNode, Attributes.STATUS);
+ value = StateValues.CPU_STATUS_RUN_USERMODE_VALUE;
+ ss.modifyAttribute(ts, value, quark);
}
+
}
break;
} // End of big switch
package org.eclipse.tracecompass.lttng2.kernel.core.trace;
import java.nio.BufferOverflowException;
+import java.util.Map;
import org.eclipse.core.resources.IProject;
import org.eclipse.core.resources.IResource;
import org.eclipse.tracecompass.internal.lttng2.kernel.core.trace.layout.LttngEventLayout;
import org.eclipse.tracecompass.tmf.core.event.ITmfEvent;
import org.eclipse.tracecompass.tmf.core.exceptions.TmfTraceException;
+import org.eclipse.tracecompass.internal.lttng2.kernel.core.trace.layout.Lttng26EventLayout;
import org.eclipse.tracecompass.tmf.core.trace.TraceValidationStatus;
import org.eclipse.tracecompass.tmf.ctf.core.trace.CtfTmfTrace;
* Supported Linux kernel tracers
*/
private enum OriginTracer {
- LTTNG(LttngEventLayout.getInstance());
+ LTTNG(LttngEventLayout.getInstance()),
+ LTTNG26(Lttng26EventLayout.getInstance());
private final @NonNull IKernelAnalysisEventLayout fLayout;
@Override
public void initTrace(IResource resource, String path,
Class<? extends ITmfEvent> eventType) throws TmfTraceException {
+ super.initTrace(resource, path, eventType);
+
/*
* Set the 'fOriginTracer' in accordance to what is found in the
* metadata
*/
- fOriginTracer = OriginTracer.LTTNG;
-
- super.initTrace(resource, path, eventType);
+ Map<String, String> traceEnv = this.getCTFTrace().getEnvironment();
+ String tracerName = traceEnv.get("tracer_name"); //$NON-NLS-1$
+ String tracerMajor = traceEnv.get("tracer_major"); //$NON-NLS-1$
+ String tracerMinor = traceEnv.get("tracer_minor"); //$NON-NLS-1$
+
+ if ("\"lttng-modules\"".equals(tracerName) && //$NON-NLS-1$
+ tracerMajor != null && (Integer.valueOf(tracerMajor) >= 2) &&
+ tracerMinor != null && (Integer.valueOf(tracerMinor) >= 6)) {
+ fOriginTracer = OriginTracer.LTTNG26;
+ } else {
+ fOriginTracer = OriginTracer.LTTNG;
+ }
}
/**
org.eclipse.core.runtime,
org.eclipse.tracecompass.tmf.core;bundle-version="0.1.0",
org.eclipse.tracecompass.tmf.ui;bundle-version="0.1.0",
+ org.eclipse.tracecompass.tmf.ctf.core;bundle-version="0.1.0",
org.eclipse.tracecompass.lttng2.control.core;bundle-version="0.1.0",
org.eclipse.tracecompass.lttng2.control.ui;bundle-version="0.1.0",
org.eclipse.tracecompass.lttng2.kernel.core;bundle-version="0.1.0"
import org.eclipse.swt.graphics.Rectangle;
import org.eclipse.tracecompass.internal.lttng2.kernel.core.Attributes;
import org.eclipse.tracecompass.internal.lttng2.kernel.core.StateValues;
+import org.eclipse.tracecompass.internal.lttng2.kernel.core.trace.layout.IKernelAnalysisEventLayout;
import org.eclipse.tracecompass.internal.lttng2.kernel.ui.Activator;
import org.eclipse.tracecompass.internal.lttng2.kernel.ui.Messages;
import org.eclipse.tracecompass.lttng2.kernel.core.analysis.kernel.LttngKernelAnalysis;
+import org.eclipse.tracecompass.lttng2.kernel.core.trace.LttngKernelTrace;
import org.eclipse.tracecompass.statesystem.core.ITmfStateSystem;
import org.eclipse.tracecompass.statesystem.core.exceptions.AttributeNotFoundException;
import org.eclipse.tracecompass.statesystem.core.exceptions.StateSystemDisposedException;
import org.eclipse.tracecompass.statesystem.core.interval.ITmfStateInterval;
import org.eclipse.tracecompass.statesystem.core.statevalue.ITmfStateValue;
import org.eclipse.tracecompass.tmf.core.statesystem.TmfStateSystemAnalysisModule;
+import org.eclipse.tracecompass.tmf.core.trace.ITmfTrace;
import org.eclipse.tracecompass.tmf.ui.widgets.timegraph.StateItem;
import org.eclipse.tracecompass.tmf.ui.widgets.timegraph.TimeGraphPresentationProvider;
import org.eclipse.tracecompass.tmf.ui.widgets.timegraph.model.ITimeEvent;
if (!value.getStateValue().isNull()) {
ITmfStateValue state = value.getStateValue();
gc.setForeground(gc.getDevice().getSystemColor(SWT.COLOR_WHITE));
- Utils.drawText(gc, state.toString().substring(4), bounds.x, bounds.y - 2, bounds.width, true, true);
+
+ /*
+ * Remove the "sys_" or "syscall_entry_" or similar from what we
+ * draw in the rectangle. This depends on the trace's event layout.
+ */
+ int beginIndex = 0;
+ ITmfTrace trace = entry.getTrace();
+ if (trace instanceof LttngKernelTrace) {
+ IKernelAnalysisEventLayout layout = ((LttngKernelTrace) trace).getEventLayout();
+ beginIndex = layout.eventSyscallEntryPrefix().length();
+ }
+
+ Utils.drawText(gc, state.toString().substring(beginIndex), bounds.x, bounds.y - 2, bounds.width, true, true);
}
} catch (AttributeNotFoundException | TimeRangeException e) {
Activator.getDefault().logError("Error in ControlFlowPresentationProvider", e); //$NON-NLS-1$
import org.eclipse.swt.graphics.Rectangle;
import org.eclipse.tracecompass.internal.lttng2.kernel.core.Attributes;
import org.eclipse.tracecompass.internal.lttng2.kernel.core.StateValues;
+import org.eclipse.tracecompass.internal.lttng2.kernel.core.trace.layout.IKernelAnalysisEventLayout;
import org.eclipse.tracecompass.internal.lttng2.kernel.ui.Activator;
import org.eclipse.tracecompass.internal.lttng2.kernel.ui.Messages;
import org.eclipse.tracecompass.internal.lttng2.kernel.ui.views.resources.ResourcesEntry.Type;
import org.eclipse.tracecompass.lttng2.kernel.core.analysis.kernel.LttngKernelAnalysis;
+import org.eclipse.tracecompass.lttng2.kernel.core.trace.LttngKernelTrace;
import org.eclipse.tracecompass.statesystem.core.ITmfStateSystem;
import org.eclipse.tracecompass.statesystem.core.exceptions.AttributeNotFoundException;
import org.eclipse.tracecompass.statesystem.core.exceptions.StateSystemDisposedException;
import org.eclipse.tracecompass.statesystem.core.interval.ITmfStateInterval;
import org.eclipse.tracecompass.statesystem.core.statevalue.ITmfStateValue;
import org.eclipse.tracecompass.tmf.core.statesystem.TmfStateSystemAnalysisModule;
+import org.eclipse.tracecompass.tmf.core.trace.ITmfTrace;
import org.eclipse.tracecompass.tmf.ui.widgets.timegraph.StateItem;
import org.eclipse.tracecompass.tmf.ui.widgets.timegraph.TimeGraphPresentationProvider;
import org.eclipse.tracecompass.tmf.ui.widgets.timegraph.model.ITimeEvent;
attribute = Attributes.EXEC_NAME;
} else if (status == StateValues.CPU_STATUS_RUN_SYSCALL) {
attribute = Attributes.SYSTEM_CALL;
- beginIndex = 4; // skip the 'sys_'
+ /*
+ * Remove the "sys_" or "syscall_entry_" or similar from what we
+ * draw in the rectangle. This depends on the trace's event layout.
+ */
+ ITmfTrace trace = entry.getTrace();
+ if (trace instanceof LttngKernelTrace) {
+ IKernelAnalysisEventLayout layout = ((LttngKernelTrace) trace).getEventLayout();
+ beginIndex = layout.eventSyscallEntryPrefix().length();
+ }
}
if (attribute != null) {
int quark = ss.getQuarkAbsolute(Attributes.THREADS, Integer.toString(currentThreadId), attribute);