tmf: Add support for versioning state input plugins
[deliverable/tracecompass.git] / org.eclipse.linuxtools.lttng2.kernel.core / src / org / eclipse / linuxtools / internal / lttng2 / kernel / core / stateprovider / CtfKernelStateInput.java
1 /*******************************************************************************
2 * Copyright (c) 2012 Ericsson
3 * Copyright (c) 2010, 2011 École Polytechnique de Montréal
4 * Copyright (c) 2010, 2011 Alexandre Montplaisir <alexandre.montplaisir@gmail.com>
5 *
6 * All rights reserved. This program and the accompanying materials are
7 * made available under the terms of the Eclipse Public License v1.0 which
8 * accompanies this distribution, and is available at
9 * http://www.eclipse.org/legal/epl-v10.html
10 *
11 *******************************************************************************/
12
13 package org.eclipse.linuxtools.internal.lttng2.kernel.core.stateprovider;
14
15 import java.util.HashMap;
16
17 import org.eclipse.linuxtools.internal.lttng2.kernel.core.Attributes;
18 import org.eclipse.linuxtools.internal.lttng2.kernel.core.LttngStrings;
19 import org.eclipse.linuxtools.internal.lttng2.kernel.core.StateValues;
20 import org.eclipse.linuxtools.tmf.core.ctfadaptor.CtfTmfEvent;
21 import org.eclipse.linuxtools.tmf.core.ctfadaptor.CtfTmfTrace;
22 import org.eclipse.linuxtools.tmf.core.event.ITmfEvent;
23 import org.eclipse.linuxtools.tmf.core.event.ITmfEventField;
24 import org.eclipse.linuxtools.tmf.core.exceptions.AttributeNotFoundException;
25 import org.eclipse.linuxtools.tmf.core.exceptions.StateValueTypeException;
26 import org.eclipse.linuxtools.tmf.core.exceptions.TimeRangeException;
27 import org.eclipse.linuxtools.tmf.core.statesystem.AbstractStateChangeInput;
28 import org.eclipse.linuxtools.tmf.core.statesystem.ITmfStateSystemBuilder;
29 import org.eclipse.linuxtools.tmf.core.statevalue.ITmfStateValue;
30 import org.eclipse.linuxtools.tmf.core.statevalue.TmfStateValue;
31
32 /**
33 * This is the state change input plugin for TMF's state system which handles
34 * the LTTng 2.0 kernel traces in CTF format.
35 *
36 * It uses the reference handler defined in CTFKernelHandler.java.
37 *
38 * @author alexmont
39 *
40 */
41 public class CtfKernelStateInput extends AbstractStateChangeInput {
42
43 /**
44 * Version number of this state provider. Please bump this if you modify the
45 * contents of the generated state history in some way.
46 */
47 private static final int VERSION = 0;
48
49 /* Event names HashMap. TODO: This can be discarded once we move to Java 7 */
50 private final HashMap<String, Integer> knownEventNames;
51
52 /* Common locations in the attribute tree */
53 private int cpusNode = -1;
54 private int threadsNode = -1;
55 private int irqsNode = -1;
56 private int softIrqsNode = -1;
57
58
59 /**
60 * Instantiate a new state provider plugin.
61 *
62 * @param trace
63 * The LTTng 2.0 kernel trace directory
64 */
65 public CtfKernelStateInput(CtfTmfTrace trace) {
66 super(trace, CtfTmfEvent.class, "LTTng Kernel"); //$NON-NLS-1$
67 knownEventNames = fillEventNames();
68 }
69
70 @Override
71 public int getVersion() {
72 return VERSION;
73 }
74
75 @Override
76 public void assignTargetStateSystem(ITmfStateSystemBuilder ssb) {
77 /* We can only set up the locations once the state system is assigned */
78 super.assignTargetStateSystem(ssb);
79 setupCommonLocations();
80 }
81
82 @Override
83 protected void eventHandle(ITmfEvent ev) {
84 /*
85 * AbstractStateChangeInput should have already checked for the correct
86 * class type
87 */
88 CtfTmfEvent event = (CtfTmfEvent) ev;
89
90 int quark;
91 ITmfStateValue value;
92
93 final ITmfEventField content = event.getContent();
94 final String eventName = event.getEventName();
95 final long ts = event.getTimestamp().getValue();
96
97 try {
98 /* Shortcut for the "current CPU" attribute node */
99 final Integer currentCPUNode = ss.getQuarkRelativeAndAdd(cpusNode, String.valueOf(event.getCPU()));
100
101 /*
102 * Shortcut for the "current thread" attribute node. It requires
103 * querying the current CPU's current thread.
104 */
105 quark = ss.getQuarkRelativeAndAdd(currentCPUNode, Attributes.CURRENT_THREAD);
106 value = ss.queryOngoingState(quark);
107 int thread = value.unboxInt();
108 final Integer currentThreadNode = ss.getQuarkRelativeAndAdd(threadsNode, String.valueOf(thread));
109
110 /*
111 * Feed event to the history system if it's known to cause a state
112 * transition.
113 */
114 switch (getEventIndex(eventName)) {
115
116 case 1: // "exit_syscall":
117 /* Fields: int64 ret */
118 {
119 /* Clear the current system call on the process */
120 quark = ss.getQuarkRelativeAndAdd(currentThreadNode, Attributes.SYSTEM_CALL);
121 value = TmfStateValue.nullValue();
122 ss.modifyAttribute(ts, value, quark);
123
124 /* Put the process' status back to user mode */
125 quark = ss.getQuarkRelativeAndAdd(currentThreadNode, Attributes.STATUS);
126 value = TmfStateValue.newValueInt(StateValues.PROCESS_STATUS_RUN_USERMODE);
127 ss.modifyAttribute(ts, value, quark);
128
129 /* Put the CPU's status back to user mode */
130 quark = ss.getQuarkRelativeAndAdd(currentCPUNode, Attributes.STATUS);
131 value = TmfStateValue.newValueInt(StateValues.CPU_STATUS_RUN_USERMODE);
132 ss.modifyAttribute(ts, value, quark);
133 }
134 break;
135
136 case 2: // "irq_handler_entry":
137 /* Fields: int32 irq, string name */
138 {
139 Integer irqId = ((Long) content.getField(LttngStrings.IRQ).getValue()).intValue();
140
141 /* Mark this IRQ as active in the resource tree.
142 * The state value = the CPU on which this IRQ is sitting */
143 quark = ss.getQuarkRelativeAndAdd(irqsNode, irqId.toString());
144 value = TmfStateValue.newValueInt(event.getCPU());
145 ss.modifyAttribute(ts, value, quark);
146
147 /* Change the status of the running process to interrupted */
148 quark = ss.getQuarkRelativeAndAdd(currentThreadNode, Attributes.STATUS);
149 value = TmfStateValue.newValueInt(StateValues.PROCESS_STATUS_INTERRUPTED);
150 ss.modifyAttribute(ts, value, quark);
151
152 /* Change the status of the CPU to interrupted */
153 quark = ss.getQuarkRelativeAndAdd(currentCPUNode, Attributes.STATUS);
154 value = TmfStateValue.newValueInt(StateValues.CPU_STATUS_IRQ);
155 ss.modifyAttribute(ts, value, quark);
156 }
157 break;
158
159 case 3: // "irq_handler_exit":
160 /* Fields: int32 irq, int32 ret */
161 {
162 Integer irqId = ((Long) content.getField(LttngStrings.IRQ).getValue()).intValue();
163
164 /* Put this IRQ back to inactive in the resource tree */
165 quark = ss.getQuarkRelativeAndAdd(irqsNode, irqId.toString());
166 value = TmfStateValue.nullValue();
167 ss.modifyAttribute(ts, value, quark);
168
169 /* Set the previous process back to running */
170 setProcessToRunning(ts, currentThreadNode);
171
172 /* Set the CPU status back to running or "idle" */
173 cpuExitInterrupt(ts, currentCPUNode, currentThreadNode);
174 }
175 break;
176
177 case 4: // "softirq_entry":
178 /* Fields: int32 vec */
179 {
180 Integer softIrqId = ((Long) content.getField(LttngStrings.VEC).getValue()).intValue();
181
182 /* Mark this SoftIRQ as active in the resource tree.
183 * The state value = the CPU on which this SoftIRQ is processed */
184 quark = ss.getQuarkRelativeAndAdd(softIrqsNode, softIrqId.toString());
185 value = TmfStateValue.newValueInt(event.getCPU());
186 ss.modifyAttribute(ts, value, quark);
187
188 /* Change the status of the running process to interrupted */
189 quark = ss.getQuarkRelativeAndAdd(currentThreadNode, Attributes.STATUS);
190 value = TmfStateValue.newValueInt(StateValues.PROCESS_STATUS_INTERRUPTED);
191 ss.modifyAttribute(ts, value, quark);
192
193 /* Change the status of the CPU to interrupted */
194 quark = ss.getQuarkRelativeAndAdd(currentCPUNode, Attributes.STATUS);
195 value = TmfStateValue.newValueInt(StateValues.CPU_STATUS_SOFTIRQ);
196 ss.modifyAttribute(ts, value, quark);
197 }
198 break;
199
200 case 5: // "softirq_exit":
201 /* Fields: int32 vec */
202 {
203 Integer softIrqId = ((Long) content.getField(LttngStrings.VEC).getValue()).intValue();
204
205 /* Put this SoftIRQ back to inactive (= -1) in the resource tree */
206 quark = ss.getQuarkRelativeAndAdd(softIrqsNode, softIrqId.toString());
207 value = TmfStateValue.nullValue();
208 ss.modifyAttribute(ts, value, quark);
209
210 /* Set the previous process back to running */
211 setProcessToRunning(ts, currentThreadNode);
212
213 /* Set the CPU status back to "busy" or "idle" */
214 cpuExitInterrupt(ts, currentCPUNode, currentThreadNode);
215 }
216 break;
217
218 case 6: // "softirq_raise":
219 /* Fields: int32 vec */
220 {
221 Integer softIrqId = ((Long) content.getField(LttngStrings.VEC).getValue()).intValue();
222
223 /* Mark this SoftIRQ as *raised* in the resource tree.
224 * State value = -2 */
225 quark = ss.getQuarkRelativeAndAdd(softIrqsNode, softIrqId.toString());
226 value = TmfStateValue.newValueInt(StateValues.SOFT_IRQ_RAISED);
227 ss.modifyAttribute(ts, value, quark);
228 }
229 break;
230
231 case 7: // "sched_switch":
232 /*
233 * Fields: string prev_comm, int32 prev_tid, int32 prev_prio, int64 prev_state,
234 * string next_comm, int32 next_tid, int32 next_prio
235 */
236 {
237 Integer prevTid = ((Long) content.getField(LttngStrings.PREV_TID).getValue()).intValue();
238 Long prevState = (Long) content.getField(LttngStrings.PREV_STATE).getValue();
239 String nextProcessName = (String) content.getField(LttngStrings.NEXT_COMM).getValue();
240 Integer nextTid = ((Long) content.getField(LttngStrings.NEXT_TID).getValue()).intValue();
241
242 Integer formerThreadNode = ss.getQuarkRelativeAndAdd(threadsNode, prevTid.toString());
243 Integer newCurrentThreadNode = ss.getQuarkRelativeAndAdd(threadsNode, nextTid.toString());
244
245 /* Set the status of the process that got scheduled out. */
246 quark = ss.getQuarkRelativeAndAdd(formerThreadNode, Attributes.STATUS);
247 if (prevState != 0) {
248 value = TmfStateValue.newValueInt(StateValues.PROCESS_STATUS_WAIT_BLOCKED);
249 } else {
250 value = TmfStateValue.newValueInt(StateValues.PROCESS_STATUS_WAIT_FOR_CPU);
251 }
252 ss.modifyAttribute(ts, value, quark);
253
254 /* Set the status of the new scheduled process */
255 setProcessToRunning(ts, newCurrentThreadNode);
256
257 /* Set the exec name of the new process */
258 quark = ss.getQuarkRelativeAndAdd(newCurrentThreadNode, Attributes.EXEC_NAME);
259 value = TmfStateValue.newValueString(nextProcessName);
260 ss.modifyAttribute(ts, value, quark);
261
262 /*
263 * Check if we need to set the syscall state and the PPID of
264 * the new process (in case we haven't seen this process before)
265 */
266 quark = ss.getQuarkRelativeAndAdd(newCurrentThreadNode, Attributes.SYSTEM_CALL);
267 if (ss.isLastAttribute(quark)) { /* Did we just add this attribute? */
268 value = TmfStateValue.nullValue();
269 ss.modifyAttribute(ts, value, quark);
270 }
271 quark = ss.getQuarkRelativeAndAdd(newCurrentThreadNode, Attributes.PPID);
272 if (ss.isLastAttribute(quark)) {
273 value = TmfStateValue.nullValue();
274 ss.modifyAttribute(ts, value, quark);
275 }
276
277 /* Set the current scheduled process on the relevant CPU */
278 quark = ss.getQuarkRelativeAndAdd(currentCPUNode, Attributes.CURRENT_THREAD);
279 value = TmfStateValue.newValueInt(nextTid);
280 ss.modifyAttribute(ts, value, quark);
281
282 /* Set the status of the CPU itself */
283 if (nextTid > 0) {
284 /* Check if the entering process is in kernel or user mode */
285 quark = ss.getQuarkRelativeAndAdd(newCurrentThreadNode, Attributes.SYSTEM_CALL);
286 if (ss.queryOngoingState(quark).isNull()) {
287 value = TmfStateValue.newValueInt(StateValues.CPU_STATUS_RUN_USERMODE);
288 } else {
289 value = TmfStateValue.newValueInt(StateValues.CPU_STATUS_RUN_SYSCALL);
290 }
291 } else {
292 value = TmfStateValue.newValueInt(StateValues.CPU_STATUS_IDLE);
293 }
294 quark = ss.getQuarkRelativeAndAdd(currentCPUNode, Attributes.STATUS);
295 ss.modifyAttribute(ts, value, quark);
296 }
297 break;
298
299 case 8: // "sched_process_fork":
300 /* Fields: string parent_comm, int32 parent_tid,
301 * string child_comm, int32 child_tid */
302 {
303 // String parentProcessName = (String) event.getFieldValue("parent_comm");
304 String childProcessName = (String) content.getField(LttngStrings.CHILD_COMM).getValue();
305 // assert ( parentProcessName.equals(childProcessName) );
306
307 Integer parentTid = ((Long) content.getField(LttngStrings.PARENT_TID).getValue()).intValue();
308 Integer childTid = ((Long) content.getField(LttngStrings.CHILD_TID).getValue()).intValue();
309
310 Integer parentTidNode = ss.getQuarkRelativeAndAdd(threadsNode, parentTid.toString());
311 Integer childTidNode = ss.getQuarkRelativeAndAdd(threadsNode, childTid.toString());
312
313 /* Assign the PPID to the new process */
314 quark = ss.getQuarkRelativeAndAdd(childTidNode, Attributes.PPID);
315 value = TmfStateValue.newValueInt(parentTid);
316 ss.modifyAttribute(ts, value, quark);
317
318 /* Set the new process' exec_name */
319 quark = ss.getQuarkRelativeAndAdd(childTidNode, Attributes.EXEC_NAME);
320 value = TmfStateValue.newValueString(childProcessName);
321 ss.modifyAttribute(ts, value, quark);
322
323 /* Set the new process' status */
324 quark = ss.getQuarkRelativeAndAdd(childTidNode, Attributes.STATUS);
325 value = TmfStateValue.newValueInt(StateValues.PROCESS_STATUS_WAIT_FOR_CPU);
326 ss.modifyAttribute(ts, value, quark);
327
328 /* Set the process' syscall name, to be the same as the parent's */
329 quark = ss.getQuarkRelativeAndAdd(parentTidNode, Attributes.SYSTEM_CALL);
330 value = ss.queryOngoingState(quark);
331 quark = ss.getQuarkRelativeAndAdd(childTidNode, Attributes.SYSTEM_CALL);
332 ss.modifyAttribute(ts, value, quark);
333 }
334 break;
335
336 case 9: // "sched_process_exit":
337 /* Fields: string comm, int32 tid, int32 prio */
338 break;
339
340 case 10: // "sched_process_free":
341 /* Fields: string comm, int32 tid, int32 prio */
342 /*
343 * A sched_process_free will always happen after the sched_switch
344 * that will remove the process from the cpu for the last time. So
345 * this is when we should delete everything wrt to the process.
346 */
347 {
348 Integer tid = ((Long) content.getField(LttngStrings.TID).getValue()).intValue();
349 /*
350 * Remove the process and all its sub-attributes from the
351 * current state
352 */
353 quark = ss.getQuarkRelativeAndAdd(threadsNode, tid.toString());
354 ss.removeAttribute(ts, quark);
355 }
356 break;
357
358 case 11: // "lttng_statedump_process_state":
359 /* Fields:
360 * int32 type, int32 mode, int32 pid, int32 submode, int32 vpid,
361 * int32 ppid, int32 tid, string name, int32 status, int32 vtid */
362 {
363 Integer tid = ((Long) content.getField(LttngStrings.TID).getValue()).intValue();
364 int ppid = ((Long) content.getField(LttngStrings.PPID).getValue()).intValue();
365 int status = ((Long) content.getField(LttngStrings.STATUS).getValue()).intValue();
366 String name = (String) content.getField(LttngStrings.NAME).getValue();
367 /*
368 * "mode" could be interesting too, but it doesn't seem to be
369 * populated with anything relevant for now.
370 */
371
372 int curThreadNode = ss.getQuarkRelativeAndAdd(threadsNode, tid.toString());
373
374 /* Set the process' name */
375 quark = ss.getQuarkRelativeAndAdd(curThreadNode, Attributes.EXEC_NAME);
376 if (ss.queryOngoingState(quark).isNull()) {
377 /* If the value didn't exist previously, set it */
378 value = TmfStateValue.newValueString(name);
379 ss.modifyAttribute(ts, value, quark);
380 }
381
382 /* Set the process' PPID */
383 quark = ss.getQuarkRelativeAndAdd(curThreadNode, Attributes.PPID);
384 if (ss.queryOngoingState(quark).isNull()) {
385 value = TmfStateValue.newValueInt(ppid);
386 ss.modifyAttribute(ts, value, quark);
387 }
388
389 /* Set the process' status */
390 quark = ss.getQuarkRelativeAndAdd(curThreadNode, Attributes.STATUS);
391 if (ss.queryOngoingState(quark).isNull()) {
392 /* "2" here means "WAIT_FOR_CPU", and "5" "WAIT_BLOCKED" in the LTTng kernel. */
393 if (status == 2) {
394 value = TmfStateValue.newValueInt(StateValues.PROCESS_STATUS_WAIT_FOR_CPU);
395 } else if (status == 5) {
396 value = TmfStateValue.newValueInt(StateValues.PROCESS_STATUS_WAIT_BLOCKED);
397 } else {
398 value = TmfStateValue.newValueInt(StateValues.PROCESS_STATUS_UNKNOWN);
399 }
400 ss.modifyAttribute(ts, value, quark);
401 }
402 }
403 break;
404
405 default:
406 /* Other event types not covered by the main switch */
407 {
408 if (eventName.startsWith(LttngStrings.SYSCALL_PREFIX)
409 || eventName.startsWith(LttngStrings.COMPAT_SYSCALL_PREFIX)) {
410 /*
411 * This is a replacement for the old sys_enter event. Now
412 * syscall names are listed into the event type
413 */
414
415 /* Assign the new system call to the process */
416 quark = ss.getQuarkRelativeAndAdd(currentThreadNode, Attributes.SYSTEM_CALL);
417 value = TmfStateValue.newValueString(eventName);
418 ss.modifyAttribute(ts, value, quark);
419
420 /* Put the process in system call mode */
421 quark = ss.getQuarkRelativeAndAdd(currentThreadNode, Attributes.STATUS);
422 value = TmfStateValue.newValueInt(StateValues.PROCESS_STATUS_RUN_SYSCALL);
423 ss.modifyAttribute(ts, value, quark);
424
425 /* Put the CPU in system call (kernel) mode */
426 quark = ss.getQuarkRelativeAndAdd(currentCPUNode, Attributes.STATUS);
427 value = TmfStateValue.newValueInt(StateValues.CPU_STATUS_RUN_SYSCALL);
428 ss.modifyAttribute(ts, value, quark);
429 }
430 }
431 break;
432 } // End of big switch
433
434 /*
435 * Statistics
436 */
437
438 /* Number of events of each type, globally */
439 // quark = ss.getQuarkAbsoluteAndAdd(Attributes.STATISTICS,
440 // Attributes.EVENT_TYPES, eventName);
441 // ss.incrementAttribute(ts, quark);
442
443 /* Number of events per CPU */
444 // quark = ss.getQuarkRelativeAndAdd(currentCPUNode,
445 // Attributes.STATISTICS, Attributes.EVENT_TYPES, eventName);
446 // ss.incrementAttribute(ts, quark);
447
448 /* Number of events per process */
449 // quark = ss.getQuarkRelativeAndAdd(currentThreadNode,
450 // Attributes.STATISTICS, Attributes.EVENT_TYPES, eventName);
451 // ss.incrementAttribute(ts, quark);
452
453 } catch (AttributeNotFoundException ae) {
454 /*
455 * This would indicate a problem with the logic of the manager here,
456 * so it shouldn't happen.
457 */
458 ae.printStackTrace();
459
460 } catch (TimeRangeException tre) {
461 /*
462 * This would happen if the events in the trace aren't ordered
463 * chronologically, which should never be the case ...
464 */
465 System.err.println("TimeRangeExcpetion caught in the state system's event manager."); //$NON-NLS-1$
466 System.err.println("Are the events in the trace correctly ordered?"); //$NON-NLS-1$
467 tre.printStackTrace();
468
469 } catch (StateValueTypeException sve) {
470 /*
471 * This would happen if we were trying to push/pop attributes not of
472 * type integer. Which, once again, should never happen.
473 */
474 sve.printStackTrace();
475 }
476 }
477
478 private void setupCommonLocations() {
479 cpusNode = ss.getQuarkAbsoluteAndAdd(Attributes.CPUS);
480 threadsNode = ss.getQuarkAbsoluteAndAdd(Attributes.THREADS);
481 irqsNode = ss.getQuarkAbsoluteAndAdd(Attributes.RESOURCES, Attributes.IRQS);
482 softIrqsNode = ss.getQuarkAbsoluteAndAdd(Attributes.RESOURCES, Attributes.SOFT_IRQS);
483 }
484
485 private static HashMap<String, Integer> fillEventNames() {
486 /*
487 * TODO Replace with straight strings in the switch/case once we move to
488 * Java 7
489 */
490 HashMap<String, Integer> map = new HashMap<String, Integer>();
491
492 map.put(LttngStrings.EXIT_SYSCALL, 1);
493 map.put(LttngStrings.IRQ_HANDLER_ENTRY, 2);
494 map.put(LttngStrings.IRQ_HANDLER_EXIT, 3);
495 map.put(LttngStrings.SOFTIRQ_ENTRY, 4);
496 map.put(LttngStrings.SOFTIRQ_EXIT, 5);
497 map.put(LttngStrings.SOFTIRQ_RAISE, 6);
498 map.put(LttngStrings.SCHED_SWITCH, 7);
499 map.put(LttngStrings.SCHED_PROCESS_FORK, 8);
500 map.put(LttngStrings.SCHED_PROCESS_EXIT, 9);
501 map.put(LttngStrings.SCHED_PROCESS_FREE, 10);
502 map.put(LttngStrings.STATEDUMP_PROCESS_STATE, 11);
503
504 return map;
505 }
506
507 private int getEventIndex(String eventName) {
508 Integer ret = knownEventNames.get(eventName);
509 return (ret != null) ? ret : -1;
510 }
511
512 /**
513 * When we want to set a process back to a "running" state, first check
514 * its current System_call attribute. If there is a system call active, we
515 * put the process back in the syscall state. If not, we put it back in
516 * user mode state.
517 */
518 private void setProcessToRunning(long ts, int currentThreadNode)
519 throws AttributeNotFoundException, TimeRangeException,
520 StateValueTypeException {
521 int quark;
522 ITmfStateValue value;
523
524 quark = ss.getQuarkRelativeAndAdd(currentThreadNode, Attributes.SYSTEM_CALL);
525 if (ss.queryOngoingState(quark).isNull()) {
526 /* We were in user mode before the interruption */
527 value = TmfStateValue.newValueInt(StateValues.PROCESS_STATUS_RUN_USERMODE);
528 } else {
529 /* We were previously in kernel mode */
530 value = TmfStateValue.newValueInt(StateValues.PROCESS_STATUS_RUN_SYSCALL);
531 }
532 quark = ss.getQuarkRelativeAndAdd(currentThreadNode, Attributes.STATUS);
533 ss.modifyAttribute(ts, value, quark);
534 }
535
536 /**
537 * Similar logic as above, but to set the CPU's status when it's coming out
538 * of an interruption.
539 */
540 private void cpuExitInterrupt(long ts, int currentCpuNode, int currentThreadNode)
541 throws StateValueTypeException, AttributeNotFoundException,
542 TimeRangeException {
543 int quark;
544 ITmfStateValue value;
545
546 quark = ss.getQuarkRelativeAndAdd(currentCpuNode, Attributes.CURRENT_THREAD);
547 if (ss.queryOngoingState(quark).unboxInt() > 0) {
548 /* There was a process on the CPU */
549 quark = ss.getQuarkRelative(currentThreadNode, Attributes.SYSTEM_CALL);
550 if (ss.queryOngoingState(quark).isNull()) {
551 /* That process was in user mode */
552 value = TmfStateValue.newValueInt(StateValues.CPU_STATUS_RUN_USERMODE);
553 } else {
554 /* That process was in a system call */
555 value = TmfStateValue.newValueInt(StateValues.CPU_STATUS_RUN_SYSCALL);
556 }
557 } else {
558 /* There was no real process scheduled, CPU was idle */
559 value = TmfStateValue.newValueInt(StateValues.CPU_STATUS_IDLE);
560 }
561 quark = ss.getQuarkRelativeAndAdd(currentCpuNode, Attributes.STATUS);
562 ss.modifyAttribute(ts, value, quark);
563 }
564 }
This page took 0.06838 seconds and 5 git commands to generate.