lttng: Add the dependency graph model and handlers for an LTTng kernel
[deliverable/tracecompass.git] / lttng / org.eclipse.tracecompass.lttng2.kernel.core / src / org / eclipse / tracecompass / internal / lttng2 / kernel / core / analysis / graph / handlers / TraceEventHandlerSched.java
CommitLineData
af7f72ce
FG
1/*******************************************************************************
2 * Copyright (c) 2015 École Polytechnique de Montréal
3 *
4 * All rights reserved. This program and the accompanying materials are
5 * made available under the terms of the Eclipse Public License v1.0 which
6 * accompanies this distribution, and is available at
7 * http://www.eclipse.org/legal/epl-v10.html
8 *******************************************************************************/
9
10package org.eclipse.tracecompass.internal.lttng2.kernel.core.analysis.graph.handlers;
11
12import org.eclipse.tracecompass.analysis.os.linux.core.kernelanalysis.LinuxValues;
13import org.eclipse.tracecompass.analysis.os.linux.core.model.HostThread;
14import org.eclipse.tracecompass.common.core.NonNullUtils;
15import org.eclipse.tracecompass.internal.lttng2.kernel.core.analysis.graph.building.LttngKernelExecGraphProvider;
16import org.eclipse.tracecompass.internal.lttng2.kernel.core.analysis.graph.building.LttngKernelExecGraphProvider.ProcessStatus;
17import org.eclipse.tracecompass.internal.lttng2.kernel.core.analysis.graph.model.EventField;
18import org.eclipse.tracecompass.internal.lttng2.kernel.core.analysis.graph.model.LttngSystemModel;
19import org.eclipse.tracecompass.internal.lttng2.kernel.core.analysis.graph.model.LttngWorker;
20import org.eclipse.tracecompass.internal.lttng2.kernel.core.trace.layout.LttngEventLayout;
21import org.eclipse.tracecompass.tmf.core.event.ITmfEvent;
22import org.eclipse.tracecompass.tmf.core.event.aspect.TmfCpuAspect;
23import org.eclipse.tracecompass.tmf.core.trace.TmfTraceUtils;
24
25/**
26 * Provides the current task running on a CPU according to scheduling events
27 *
28 * @author Francis Giraldeau
29 * @author Geneviève Bastien
30 */
31public class TraceEventHandlerSched extends BaseHandler {
32
33 /**
34 * Constructor
35 *
36 * @param provider
37 * The parent graph provider
38 */
39 public TraceEventHandlerSched(LttngKernelExecGraphProvider provider) {
40 super(provider);
41 }
42
43 @Override
44 public void handleEvent(ITmfEvent ev) {
45 String eventName = ev.getName();
46 LttngEventLayout eventLayout = getProvider().getEventLayout();
47
48 if (eventName.equals(eventLayout.eventSchedSwitch())) {
49 handleSchedSwitch(ev);
50 } else if (eventName.equals(eventLayout.eventSchedProcessTTWU())) {
51 if (traceHasEventSchedTTWU(ev.getTrace())) {
52 handleSchedWakeup(ev);
53 }
54 } else if (eventName.equals(eventLayout.eventSchedProcessWakeup())) {
55 if (!traceHasEventSchedTTWU(ev.getTrace())) {
56 handleSchedWakeup(ev);
57 }
58 } else if (eventName.equals(eventLayout.eventSchedProcessWakeupNew())) {
59 if (!traceHasEventSchedTTWU(ev.getTrace())) {
60 handleSchedWakeup(ev);
61 }
62 } else if (eventName.equals(eventLayout.eventSchedProcessFork())) {
63 handleSchedProcessFork(ev);
64 } else if (eventName.equals(eventLayout.eventSchedProcessExit())) {
65 handleSchedProcessExit(ev);
66 } else if (eventName.equals(eventLayout.eventSchedProcessExec())) {
67 handleSchedProcessExec(ev);
68 }
69 }
70
71 private void handleSchedSwitch(ITmfEvent event) {
72 Object cpuObj = TmfTraceUtils.resolveEventAspectOfClassForEvent(event.getTrace(), TmfCpuAspect.class, event);
73 if (cpuObj == null) {
74 throw new NullPointerException();
75 }
76 Integer cpu = (Integer) cpuObj;
77 LttngEventLayout eventLayout = getProvider().getEventLayout();
78 LttngSystemModel system = getProvider().getSystem();
79
80 Integer next = EventField.getInt(event, eventLayout.fieldNextTid());
81 Integer prev = EventField.getInt(event, eventLayout.fieldPrevTid());
82 long ts = event.getTimestamp().getValue();
83 long prev_state = EventField.getLong(event, eventLayout.fieldPrevState());
84 prev_state = (long) ((int) prev_state) & (LinuxValues.TASK_STATE_RUNNING | LinuxValues.TASK_INTERRUPTIBLE | LinuxValues.TASK_UNINTERRUPTIBLE);
85 String host = event.getTrace().getHostId();
86
87 system.cacheTidOnCpu(cpu, new HostThread(event.getTrace().getHostId(), next));
88
89 HostThread nextHt = new HostThread(host, next);
90 LttngWorker nextTask = system.findWorker(nextHt);
91 if (nextTask == null) {
92 String name = EventField.getOrDefault(event, eventLayout.fieldNextComm(), NonNullUtils.checkNotNull(Messages.TraceEventHandlerSched_UnknownThreadName));
93 nextTask = new LttngWorker(nextHt, name, ts);
94 system.addWorker(nextTask);
95 }
96 nextTask.setStatus(ProcessStatus.RUN);
97
98 HostThread prevHt = new HostThread(host, prev);
99 LttngWorker prevTask = system.findWorker(prevHt);
100 if (prevTask == null) {
101 String name = EventField.getOrDefault(event, eventLayout.fieldPrevComm(), NonNullUtils.checkNotNull(Messages.TraceEventHandlerSched_UnknownThreadName));
102 prevTask = new LttngWorker(prevHt, name, ts);
103 system.addWorker(prevTask);
104 }
105 /* prev_state == 0 means runnable, thus waits for cpu */
106 if (prev_state == 0) {
107 prevTask.setStatus(ProcessStatus.WAIT_CPU);
108 } else {
109 prevTask.setStatus(ProcessStatus.WAIT_BLOCKED);
110 }
111 }
112
113 private void handleSchedProcessFork(ITmfEvent event) {
114 String host = event.getTrace().getHostId();
115 LttngEventLayout eventLayout = getProvider().getEventLayout();
116 LttngSystemModel system = getProvider().getSystem();
117
118 Integer childTid = EventField.getInt(event, eventLayout.fieldChildTid());
119 String name = EventField.getString(event, eventLayout.fieldChildComm());
120 long ts = event.getTimestamp().getValue();
121
122 HostThread childHt = new HostThread(host, childTid);
123
124 LttngWorker childTask = system.findWorker(childHt);
125 if (childTask == null) {
126 childTask = new LttngWorker(childHt, name, ts);
127 system.addWorker(childTask);
128 }
129
130 childTask.setStatus(ProcessStatus.WAIT_FORK);
131 }
132
133 private void handleSchedWakeup(ITmfEvent event) {
134 String host = event.getTrace().getHostId();
135 Object cpuObj = TmfTraceUtils.resolveEventAspectOfClassForEvent(event.getTrace(), TmfCpuAspect.class, event);
136 if (cpuObj == null) {
137 throw new NullPointerException();
138 }
139 Integer cpu = (Integer) cpuObj;
140 LttngEventLayout eventLayout = getProvider().getEventLayout();
141 LttngSystemModel system = getProvider().getSystem();
142
143 Integer tid = EventField.getInt(event, eventLayout.fieldTid());
144 HostThread targetHt = new HostThread(host, tid);
145
146 LttngWorker target = system.findWorker(targetHt);
147 LttngWorker current = system.getWorkerOnCpu(host, cpu);
148 if (target == null) {
149 String name = EventField.getOrDefault(event, eventLayout.fieldComm(), NonNullUtils.checkNotNull(Messages.TraceEventHandlerSched_UnknownThreadName));
150 target = new LttngWorker(targetHt, name, event.getTimestamp().getValue());
151 system.addWorker(target);
152 target.setStatus(ProcessStatus.WAIT_BLOCKED);
153 }
154 // spurious wakeup
155 ProcessStatus status = target.getStatus();
156 if ((current != null && target.getHostThread().equals(current.getHostThread())) ||
157 status == ProcessStatus.WAIT_CPU) {
158 return;
159 }
160 if (status == ProcessStatus.WAIT_BLOCKED ||
161 status == ProcessStatus.WAIT_FORK ||
162 status == ProcessStatus.UNKNOWN) {
163 target.setStatus(ProcessStatus.WAIT_CPU);
164 return;
165 }
166 }
167
168 private void handleSchedProcessExit(ITmfEvent event) {
169 String host = event.getTrace().getHostId();
170 LttngEventLayout eventLayout = getProvider().getEventLayout();
171 LttngSystemModel system = getProvider().getSystem();
172
173 Integer tid = EventField.getInt(event, eventLayout.fieldTid());
174 LttngWorker task = system.findWorker(new HostThread(host, tid));
175 if (task == null) {
176 return;
177 }
178 task.setStatus(ProcessStatus.EXIT);
179 }
180
181 private void handleSchedProcessExec(ITmfEvent event) {
182 String host = event.getTrace().getHostId();
183 Object cpuObj = TmfTraceUtils.resolveEventAspectOfClassForEvent(event.getTrace(), TmfCpuAspect.class, event);
184 if (cpuObj == null) {
185 throw new NullPointerException();
186 }
187 Integer cpu = (Integer) cpuObj;
188 LttngEventLayout eventLayout = getProvider().getEventLayout();
189 LttngSystemModel system = getProvider().getSystem();
190
191 String filename = EventField.getString(event, eventLayout.fieldFilename());
192 LttngWorker task = system.getWorkerOnCpu(host, cpu);
193 if (task == null) {
194 return;
195 }
196 task.setName(filename);
197 }
198
199}
This page took 0.035443 seconds and 5 git commands to generate.