tmf: Replace state value types with an enum
[deliverable/tracecompass.git] / org.eclipse.linuxtools.lttng2.kernel.ui / src / org / eclipse / linuxtools / internal / lttng2 / kernel / ui / views / controlflow / ControlFlowView.java
CommitLineData
6151d86c 1/*******************************************************************************
af10fe06 2 * Copyright (c) 2012, 2013 Ericsson
6151d86c
PT
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 * Contributors:
10 * Patrick Tasse - Initial API and implementation
11 *******************************************************************************/
12
13package org.eclipse.linuxtools.internal.lttng2.kernel.ui.views.controlflow;
14
15import java.util.ArrayList;
16import java.util.Arrays;
17import java.util.Collections;
18import java.util.Comparator;
faa38350 19import java.util.HashMap;
6151d86c
PT
20import java.util.List;
21
22import org.eclipse.core.runtime.IProgressMonitor;
23import org.eclipse.core.runtime.NullProgressMonitor;
24import org.eclipse.jface.action.Action;
25import org.eclipse.jface.action.IToolBarManager;
26import org.eclipse.jface.action.Separator;
27import org.eclipse.jface.viewers.ILabelProviderListener;
28import org.eclipse.jface.viewers.ITableLabelProvider;
29import org.eclipse.jface.viewers.ITreeContentProvider;
30import org.eclipse.jface.viewers.Viewer;
31import org.eclipse.linuxtools.internal.lttng2.kernel.core.Attributes;
32import org.eclipse.linuxtools.internal.lttng2.kernel.ui.Messages;
33import org.eclipse.linuxtools.lttng2.kernel.core.trace.CtfKernelTrace;
34import org.eclipse.linuxtools.tmf.core.ctfadaptor.CtfTmfTimestamp;
6151d86c 35import org.eclipse.linuxtools.tmf.core.exceptions.AttributeNotFoundException;
96345c5a 36import org.eclipse.linuxtools.tmf.core.exceptions.StateSystemDisposedException;
6151d86c
PT
37import org.eclipse.linuxtools.tmf.core.exceptions.StateValueTypeException;
38import org.eclipse.linuxtools.tmf.core.exceptions.TimeRangeException;
39import org.eclipse.linuxtools.tmf.core.interval.ITmfStateInterval;
6151d86c
PT
40import org.eclipse.linuxtools.tmf.core.signal.TmfRangeSynchSignal;
41import org.eclipse.linuxtools.tmf.core.signal.TmfSignalHandler;
6151d86c 42import org.eclipse.linuxtools.tmf.core.signal.TmfTimeSynchSignal;
faa38350
PT
43import org.eclipse.linuxtools.tmf.core.signal.TmfTraceClosedSignal;
44import org.eclipse.linuxtools.tmf.core.signal.TmfTraceSelectedSignal;
f1f86dfb 45import org.eclipse.linuxtools.tmf.core.statesystem.ITmfStateSystem;
b67a2540 46import org.eclipse.linuxtools.tmf.core.statevalue.ITmfStateValue;
3bd46eef
AM
47import org.eclipse.linuxtools.tmf.core.timestamp.ITmfTimestamp;
48import org.eclipse.linuxtools.tmf.core.timestamp.TmfTimeRange;
49import org.eclipse.linuxtools.tmf.core.timestamp.TmfTimestamp;
6151d86c
PT
50import org.eclipse.linuxtools.tmf.core.trace.ITmfTrace;
51import org.eclipse.linuxtools.tmf.core.trace.TmfExperiment;
faa38350 52import org.eclipse.linuxtools.tmf.ui.editors.ITmfTraceEditor;
6151d86c
PT
53import org.eclipse.linuxtools.tmf.ui.views.TmfView;
54import org.eclipse.linuxtools.tmf.ui.widgets.timegraph.ITimeGraphRangeListener;
55import org.eclipse.linuxtools.tmf.ui.widgets.timegraph.ITimeGraphSelectionListener;
56import org.eclipse.linuxtools.tmf.ui.widgets.timegraph.ITimeGraphTimeListener;
57import org.eclipse.linuxtools.tmf.ui.widgets.timegraph.TimeGraphCombo;
58import org.eclipse.linuxtools.tmf.ui.widgets.timegraph.TimeGraphRangeUpdateEvent;
59import org.eclipse.linuxtools.tmf.ui.widgets.timegraph.TimeGraphSelectionEvent;
60import org.eclipse.linuxtools.tmf.ui.widgets.timegraph.TimeGraphTimeEvent;
61import org.eclipse.linuxtools.tmf.ui.widgets.timegraph.model.ITimeEvent;
62import org.eclipse.linuxtools.tmf.ui.widgets.timegraph.model.ITimeGraphEntry;
63import org.eclipse.linuxtools.tmf.ui.widgets.timegraph.model.TimeEvent;
64import org.eclipse.linuxtools.tmf.ui.widgets.timegraph.widgets.Utils;
65import org.eclipse.linuxtools.tmf.ui.widgets.timegraph.widgets.Utils.Resolution;
66import org.eclipse.linuxtools.tmf.ui.widgets.timegraph.widgets.Utils.TimeFormat;
67import org.eclipse.swt.SWT;
68import org.eclipse.swt.graphics.Image;
69import org.eclipse.swt.widgets.Composite;
70import org.eclipse.swt.widgets.Display;
71import org.eclipse.swt.widgets.TreeColumn;
72import org.eclipse.ui.IActionBars;
faa38350 73import org.eclipse.ui.IEditorPart;
6151d86c
PT
74
75/**
76 * The Control Flow view main object
77 *
78 */
79public class ControlFlowView extends TmfView {
80
81 // ------------------------------------------------------------------------
82 // Constants
83 // ------------------------------------------------------------------------
84
85 /**
86 * View ID.
87 */
88 public static final String ID = "org.eclipse.linuxtools.lttng2.kernel.ui.views.controlflow"; //$NON-NLS-1$
89
6151d86c
PT
90 private static final String PROCESS_COLUMN = Messages.ControlFlowView_processColumn;
91 private static final String TID_COLUMN = Messages.ControlFlowView_tidColumn;
92 private static final String PTID_COLUMN = Messages.ControlFlowView_ptidColumn;
93 private static final String BIRTH_TIME_COLUMN = Messages.ControlFlowView_birthTimeColumn;
94 private static final String TRACE_COLUMN = Messages.ControlFlowView_traceColumn;
95
96 private final String[] COLUMN_NAMES = new String[] {
97 PROCESS_COLUMN,
98 TID_COLUMN,
99 PTID_COLUMN,
100 BIRTH_TIME_COLUMN,
101 TRACE_COLUMN
102 };
103
6ac5a950
AM
104 private final String[] FILTER_COLUMN_NAMES = new String[] {
105 PROCESS_COLUMN,
106 TID_COLUMN
107 };
108
6151d86c
PT
109 /**
110 * Redraw state enum
111 */
112 private enum State { IDLE, BUSY, PENDING }
113
114 // ------------------------------------------------------------------------
115 // Fields
116 // ------------------------------------------------------------------------
117
118 // The timegraph combo
119 private TimeGraphCombo fTimeGraphCombo;
120
faa38350
PT
121 // The selected trace
122 private ITmfTrace fTrace;
6151d86c
PT
123
124 // The timegraph entry list
125 private ArrayList<ControlFlowEntry> fEntryList;
126
faa38350
PT
127 // The trace to entry list hash map
128 final private HashMap<ITmfTrace, ArrayList<ControlFlowEntry>> fEntryListMap = new HashMap<ITmfTrace, ArrayList<ControlFlowEntry>>();
129
130 // The trace to build thread hash map
131 final private HashMap<ITmfTrace, BuildThread> fBuildThreadMap = new HashMap<ITmfTrace, BuildThread>();
6151d86c
PT
132
133 // The start time
134 private long fStartTime;
135
136 // The end time
137 private long fEndTime;
138
139 // The display width
140 private final int fDisplayWidth;
141
142 // The zoom thread
143 private ZoomThread fZoomThread;
144
145 // The next resource action
146 private Action fNextResourceAction;
147
148 // The previous resource action
149 private Action fPreviousResourceAction;
150
151 // A comparator class
152 private final ControlFlowEntryComparator fControlFlowEntryComparator = new ControlFlowEntryComparator();
153
154 // The redraw state used to prevent unnecessary queuing of display runnables
155 private State fRedrawState = State.IDLE;
156
157 // The redraw synchronization object
158 final private Object fSyncObj = new Object();
159
160 // ------------------------------------------------------------------------
161 // Classes
162 // ------------------------------------------------------------------------
163
164 private class TreeContentProvider implements ITreeContentProvider {
165
166 @Override
167 public void dispose() {
168 }
169
170 @Override
171 public void inputChanged(Viewer viewer, Object oldInput, Object newInput) {
172 }
173
174 @Override
175 public Object[] getElements(Object inputElement) {
176 return (ITimeGraphEntry[]) inputElement;
177 }
178
179 @Override
180 public Object[] getChildren(Object parentElement) {
181 ITimeGraphEntry entry = (ITimeGraphEntry) parentElement;
30652cc3
AM
182 List<? extends ITimeGraphEntry> children = entry.getChildren();
183 return children.toArray(new ITimeGraphEntry[children.size()]);
6151d86c
PT
184 }
185
186 @Override
187 public Object getParent(Object element) {
188 ITimeGraphEntry entry = (ITimeGraphEntry) element;
189 return entry.getParent();
190 }
191
192 @Override
193 public boolean hasChildren(Object element) {
194 ITimeGraphEntry entry = (ITimeGraphEntry) element;
195 return entry.hasChildren();
196 }
197
198 }
199
200 private class TreeLabelProvider implements ITableLabelProvider {
201
202 @Override
203 public void addListener(ILabelProviderListener listener) {
204 }
205
206 @Override
207 public void dispose() {
208 }
209
210 @Override
211 public boolean isLabelProperty(Object element, String property) {
212 return false;
213 }
214
215 @Override
216 public void removeListener(ILabelProviderListener listener) {
217 }
218
219 @Override
220 public Image getColumnImage(Object element, int columnIndex) {
221 return null;
222 }
223
224 @Override
225 public String getColumnText(Object element, int columnIndex) {
226 ControlFlowEntry entry = (ControlFlowEntry) element;
227 if (columnIndex == 0) {
228 return entry.getName();
229 } else if (columnIndex == 1) {
230 return Integer.toString(entry.getThreadId());
231 } else if (columnIndex == 2) {
232 if (entry.getParentThreadId() > 0) {
233 return Integer.toString(entry.getParentThreadId());
234 }
235 } else if (columnIndex == 3) {
826deb93 236 return Utils.formatTime(entry.getStartTime(), TimeFormat.CALENDAR, Resolution.NANOSEC);
6151d86c
PT
237 } else if (columnIndex == 4) {
238 return entry.getTrace().getName();
239 }
240 return ""; //$NON-NLS-1$
241 }
242
243 }
244
245 private static class ControlFlowEntryComparator implements Comparator<ITimeGraphEntry> {
246
247 @Override
248 public int compare(ITimeGraphEntry o1, ITimeGraphEntry o2) {
249 int result = 0;
250
251 if ((o1 instanceof ControlFlowEntry) && (o2 instanceof ControlFlowEntry)) {
252 ControlFlowEntry entry1 = (ControlFlowEntry) o1;
253 ControlFlowEntry entry2 = (ControlFlowEntry) o2;
254 result = entry1.getTrace().getStartTime().compareTo(entry2.getTrace().getStartTime());
255 if (result == 0) {
256 result = entry1.getTrace().getName().compareTo(entry2.getTrace().getName());
257 }
258 if (result == 0) {
259 result = entry1.getThreadId() < entry2.getThreadId() ? -1 : entry1.getThreadId() > entry2.getThreadId() ? 1 : 0;
260 }
261 }
262
263 if (result == 0) {
264 result = o1.getStartTime() < o2.getStartTime() ? -1 : o1.getStartTime() > o2.getStartTime() ? 1 : 0;
265 }
266
267 return result;
268 }
269 }
270
faa38350
PT
271 private class BuildThread extends Thread {
272 private final ITmfTrace fBuildTrace;
273 private final IProgressMonitor fMonitor;
274
275 public BuildThread(ITmfTrace trace) {
276 super("ControlFlowView build"); //$NON-NLS-1$
277 fBuildTrace = trace;
278 fMonitor = new NullProgressMonitor();
279 }
280
281 @Override
282 public void run() {
283 buildEventList(fBuildTrace, fMonitor);
284 synchronized (fBuildThreadMap) {
285 fBuildThreadMap.remove(this);
286 }
287 }
288
289 public void cancel() {
290 fMonitor.setCanceled(true);
291 }
292 }
6151d86c
PT
293
294 private class ZoomThread extends Thread {
faa38350 295 private final ArrayList<ControlFlowEntry> fZoomEntryList;
6151d86c
PT
296 private final long fZoomStartTime;
297 private final long fZoomEndTime;
298 private final long fResolution;
299 private final IProgressMonitor fMonitor;
300
faa38350 301 public ZoomThread(ArrayList<ControlFlowEntry> entryList, long startTime, long endTime) {
6151d86c 302 super("ControlFlowView zoom"); //$NON-NLS-1$
faa38350 303 fZoomEntryList = entryList;
6151d86c
PT
304 fZoomStartTime = startTime;
305 fZoomEndTime = endTime;
306 fResolution = Math.max(1, (fZoomEndTime - fZoomStartTime) / fDisplayWidth);
307 fMonitor = new NullProgressMonitor();
308 }
309
310 @Override
311 public void run() {
faa38350 312 if (fZoomEntryList == null) {
6151d86c
PT
313 return;
314 }
faa38350 315 for (ControlFlowEntry entry : fZoomEntryList) {
6151d86c
PT
316 if (fMonitor.isCanceled()) {
317 break;
318 }
319 zoom(entry, fMonitor);
320 }
321 }
322
323 private void zoom(ControlFlowEntry entry, IProgressMonitor monitor) {
324 if (fZoomStartTime <= fStartTime && fZoomEndTime >= fEndTime) {
325 entry.setZoomedEventList(null);
326 } else {
327 List<ITimeEvent> zoomedEventList = getEventList(entry, fZoomStartTime, fZoomEndTime, fResolution, monitor);
328 if (zoomedEventList != null) {
329 entry.setZoomedEventList(zoomedEventList);
330 }
331 }
332 redraw();
333 for (ControlFlowEntry child : entry.getChildren()) {
334 if (fMonitor.isCanceled()) {
335 return;
336 }
337 zoom(child, monitor);
338 }
339 }
340
341 public void cancel() {
342 fMonitor.setCanceled(true);
343 }
344 }
345
346 // ------------------------------------------------------------------------
347 // Constructors
348 // ------------------------------------------------------------------------
349
350 /**
351 * Constructor
352 */
353 public ControlFlowView() {
354 super(ID);
355 fDisplayWidth = Display.getDefault().getBounds().width;
356 }
357
358 // ------------------------------------------------------------------------
359 // ViewPart
360 // ------------------------------------------------------------------------
361
362 /* (non-Javadoc)
363 * @see org.eclipse.linuxtools.tmf.ui.views.TmfView#createPartControl(org.eclipse.swt.widgets.Composite)
364 */
365 @Override
366 public void createPartControl(Composite parent) {
367 fTimeGraphCombo = new TimeGraphCombo(parent, SWT.NONE);
368
369 fTimeGraphCombo.setTreeContentProvider(new TreeContentProvider());
370
371 fTimeGraphCombo.setTreeLabelProvider(new TreeLabelProvider());
372
373 fTimeGraphCombo.setTimeGraphProvider(new ControlFlowPresentationProvider());
374
375 fTimeGraphCombo.setTreeColumns(COLUMN_NAMES);
376
6ac5a950
AM
377 fTimeGraphCombo.setFilterContentProvider(new TreeContentProvider());
378
379 fTimeGraphCombo.setFilterLabelProvider(new TreeLabelProvider());
380
381 fTimeGraphCombo.setFilterColumns(FILTER_COLUMN_NAMES);
382
6151d86c
PT
383 fTimeGraphCombo.getTimeGraphViewer().addRangeListener(new ITimeGraphRangeListener() {
384 @Override
385 public void timeRangeUpdated(TimeGraphRangeUpdateEvent event) {
386 final long startTime = event.getStartTime();
387 final long endTime = event.getEndTime();
388 TmfTimeRange range = new TmfTimeRange(new CtfTmfTimestamp(startTime), new CtfTmfTimestamp(endTime));
389 TmfTimestamp time = new CtfTmfTimestamp(fTimeGraphCombo.getTimeGraphViewer().getSelectedTime());
390 broadcast(new TmfRangeSynchSignal(ControlFlowView.this, range, time));
391 if (fZoomThread != null) {
392 fZoomThread.cancel();
393 }
394 startZoomThread(startTime, endTime);
395 }
396 });
397
398 fTimeGraphCombo.getTimeGraphViewer().addTimeListener(new ITimeGraphTimeListener() {
399 @Override
400 public void timeSelected(TimeGraphTimeEvent event) {
401 long time = event.getTime();
402 broadcast(new TmfTimeSynchSignal(ControlFlowView.this, new CtfTmfTimestamp(time)));
403 }
404 });
405
406 fTimeGraphCombo.addSelectionListener(new ITimeGraphSelectionListener() {
407 @Override
408 public void selectionChanged(TimeGraphSelectionEvent event) {
409 //ITimeGraphEntry selection = event.getSelection();
410 }
411 });
412
026664b7 413 fTimeGraphCombo.getTimeGraphViewer().setTimeFormat(TimeFormat.CALENDAR);
6151d86c 414
6151d86c
PT
415 // View Action Handling
416 makeActions();
417 contributeToActionBars();
faa38350 418
f28d404e 419 IEditorPart editor = getSite().getPage().getActiveEditor();
faa38350
PT
420 if (editor instanceof ITmfTraceEditor) {
421 ITmfTrace trace = ((ITmfTraceEditor) editor).getTrace();
422 if (trace != null) {
423 traceSelected(new TmfTraceSelectedSignal(this, trace));
424 }
425 }
7e7a91ae
FG
426
427 // make selection available to other views
428 getSite().setSelectionProvider(fTimeGraphCombo.getTreeViewer());
6151d86c
PT
429 }
430
431 /* (non-Javadoc)
432 * @see org.eclipse.ui.part.WorkbenchPart#setFocus()
433 */
434 @Override
435 public void setFocus() {
436 fTimeGraphCombo.setFocus();
437 }
438
439 // ------------------------------------------------------------------------
440 // Signal handlers
441 // ------------------------------------------------------------------------
442
443 /**
faa38350 444 * Handler for the trace selected signal
6151d86c
PT
445 *
446 * @param signal
447 * The signal that's received
448 */
449 @TmfSignalHandler
faa38350
PT
450 public void traceSelected(final TmfTraceSelectedSignal signal) {
451 if (signal.getTrace() == fTrace) {
6151d86c
PT
452 return;
453 }
faa38350 454 fTrace = signal.getTrace();
6151d86c 455
faa38350
PT
456 synchronized (fEntryListMap) {
457 fEntryList = fEntryListMap.get(fTrace);
458 if (fEntryList == null) {
459 synchronized (fBuildThreadMap) {
460 BuildThread buildThread = new BuildThread(fTrace);
461 fBuildThreadMap.put(fTrace, buildThread);
462 buildThread.start();
463 }
464 } else {
465 fStartTime = fTrace.getStartTime().normalize(0, ITmfTimestamp.NANOSECOND_SCALE).getValue();
466 fEndTime = fTrace.getEndTime().normalize(0, ITmfTimestamp.NANOSECOND_SCALE).getValue();
d7ee91bb 467 refresh();
6151d86c 468 }
faa38350 469 }
6151d86c
PT
470 }
471
472 /**
faa38350 473 * Trace is closed: clear the data structures and the view
6151d86c
PT
474 *
475 * @param signal the signal received
476 */
477 @TmfSignalHandler
faa38350
PT
478 public void traceClosed(final TmfTraceClosedSignal signal) {
479 synchronized (fBuildThreadMap) {
480 BuildThread buildThread = fBuildThreadMap.remove(signal.getTrace());
481 if (buildThread != null) {
482 buildThread.cancel();
483 }
484 }
485 synchronized (fEntryListMap) {
486 fEntryListMap.remove(signal.getTrace());
487 }
488 if (signal.getTrace() == fTrace) {
489 fTrace = null;
6151d86c
PT
490 fStartTime = 0;
491 fEndTime = 0;
faa38350
PT
492 if (fZoomThread != null) {
493 fZoomThread.cancel();
6151d86c 494 }
d7ee91bb 495 refresh();
6151d86c
PT
496 }
497 }
498
499 /**
500 * Handler for the synch signal
501 *
502 * @param signal
503 * The signal that's received
504 */
505 @TmfSignalHandler
506 public void synchToTime(final TmfTimeSynchSignal signal) {
faa38350 507 if (signal.getSource() == this || fTrace == null) {
6151d86c
PT
508 return;
509 }
faa38350 510 final long time = signal.getCurrentTime().normalize(0, ITmfTimestamp.NANOSECOND_SCALE).getValue();
6151d86c
PT
511
512 int thread = -1;
faa38350
PT
513 ITmfTrace[] traces;
514 if (fTrace instanceof TmfExperiment) {
515 TmfExperiment experiment = (TmfExperiment) fTrace;
516 traces = experiment.getTraces();
517 } else {
518 traces = new ITmfTrace[] { fTrace };
519 }
520 for (ITmfTrace trace : traces) {
6151d86c
PT
521 if (thread > 0) {
522 break;
523 }
524 if (trace instanceof CtfKernelTrace) {
525 CtfKernelTrace ctfKernelTrace = (CtfKernelTrace) trace;
a51b2b9f 526 ITmfStateSystem ssq = ctfKernelTrace.getStateSystem(CtfKernelTrace.STATE_ID);
6151d86c
PT
527 if (time >= ssq.getStartTime() && time <= ssq.getCurrentEndTime()) {
528 List<Integer> currentThreadQuarks = ssq.getQuarks(Attributes.CPUS, "*", Attributes.CURRENT_THREAD); //$NON-NLS-1$
529 for (int currentThreadQuark : currentThreadQuarks) {
530 try {
531 ITmfStateInterval currentThreadInterval = ssq.querySingleState(time, currentThreadQuark);
532 int currentThread = currentThreadInterval.getStateValue().unboxInt();
533 if (currentThread > 0) {
534 int statusQuark = ssq.getQuarkAbsolute(Attributes.THREADS, Integer.toString(currentThread), Attributes.STATUS);
535 ITmfStateInterval statusInterval = ssq.querySingleState(time, statusQuark);
536 if (statusInterval.getStartTime() == time) {
537 thread = currentThread;
538 break;
539 }
540 }
541 } catch (AttributeNotFoundException e) {
542 e.printStackTrace();
543 } catch (TimeRangeException e) {
544 e.printStackTrace();
545 } catch (StateValueTypeException e) {
546 e.printStackTrace();
96345c5a
AM
547 } catch (StateSystemDisposedException e) {
548 /* Ignored */
6151d86c
PT
549 }
550 }
551 }
552 }
553 }
554 final int selectedThread = thread;
555
556 Display.getDefault().asyncExec(new Runnable() {
557 @Override
558 public void run() {
559 if (fTimeGraphCombo.isDisposed()) {
560 return;
561 }
562 fTimeGraphCombo.getTimeGraphViewer().setSelectedTime(time, true);
563 startZoomThread(fTimeGraphCombo.getTimeGraphViewer().getTime0(), fTimeGraphCombo.getTimeGraphViewer().getTime1());
564
565 if (selectedThread > 0) {
566 for (Object element : fTimeGraphCombo.getTimeGraphViewer().getExpandedElements()) {
567 if (element instanceof ControlFlowEntry) {
568 ControlFlowEntry entry = (ControlFlowEntry) element;
569 if (entry.getThreadId() == selectedThread) {
570 fTimeGraphCombo.setSelection(entry);
571 break;
572 }
573 }
574 }
575 }
576 }
577 });
578 }
579
580 /**
581 * Handler for the range sync signal
582 *
583 * @param signal
584 * The signal that's received
585 */
586 @TmfSignalHandler
587 public void synchToRange(final TmfRangeSynchSignal signal) {
faa38350 588 if (signal.getSource() == this || fTrace == null) {
6151d86c
PT
589 return;
590 }
1c6a842a
PT
591 if (signal.getCurrentRange().getIntersection(fTrace.getTimeRange()) == null) {
592 return;
593 }
faa38350
PT
594 final long startTime = signal.getCurrentRange().getStartTime().normalize(0, ITmfTimestamp.NANOSECOND_SCALE).getValue();
595 final long endTime = signal.getCurrentRange().getEndTime().normalize(0, ITmfTimestamp.NANOSECOND_SCALE).getValue();
596 final long time = signal.getCurrentTime().normalize(0, ITmfTimestamp.NANOSECOND_SCALE).getValue();
6151d86c
PT
597 Display.getDefault().asyncExec(new Runnable() {
598 @Override
599 public void run() {
600 if (fTimeGraphCombo.isDisposed()) {
601 return;
602 }
603 fTimeGraphCombo.getTimeGraphViewer().setStartFinishTime(startTime, endTime);
604 fTimeGraphCombo.getTimeGraphViewer().setSelectedTime(time, false);
605 startZoomThread(startTime, endTime);
606 }
607 });
608 }
609
6151d86c
PT
610 // ------------------------------------------------------------------------
611 // Internal
612 // ------------------------------------------------------------------------
613
faa38350 614 private void buildEventList(final ITmfTrace trace, IProgressMonitor monitor) {
6151d86c
PT
615 fStartTime = Long.MAX_VALUE;
616 fEndTime = Long.MIN_VALUE;
faa38350
PT
617 ITmfTrace[] traces;
618 if (trace instanceof TmfExperiment) {
619 TmfExperiment experiment = (TmfExperiment) trace;
620 traces = experiment.getTraces();
621 } else {
622 traces = new ITmfTrace[] { trace };
623 }
6151d86c 624 ArrayList<ControlFlowEntry> rootList = new ArrayList<ControlFlowEntry>();
faa38350
PT
625 for (ITmfTrace aTrace : traces) {
626 if (monitor.isCanceled()) {
627 return;
628 }
629 if (aTrace instanceof CtfKernelTrace) {
6151d86c 630 ArrayList<ControlFlowEntry> entryList = new ArrayList<ControlFlowEntry>();
faa38350 631 CtfKernelTrace ctfKernelTrace = (CtfKernelTrace) aTrace;
a51b2b9f 632 ITmfStateSystem ssq = ctfKernelTrace.getStateSystem(CtfKernelTrace.STATE_ID);
faa38350
PT
633 if (!ssq.waitUntilBuilt()) {
634 return;
635 }
6151d86c
PT
636 long start = ssq.getStartTime();
637 long end = ssq.getCurrentEndTime() + 1;
638 fStartTime = Math.min(fStartTime, start);
639 fEndTime = Math.max(fEndTime, end);
640 List<Integer> threadQuarks = ssq.getQuarks(Attributes.THREADS, "*"); //$NON-NLS-1$
641 for (int threadQuark : threadQuarks) {
faa38350
PT
642 if (monitor.isCanceled()) {
643 return;
644 }
6151d86c
PT
645 String threadName = ssq.getAttributeName(threadQuark);
646 int threadId = -1;
647 try {
648 threadId = Integer.parseInt(threadName);
649 } catch (NumberFormatException e1) {
650 continue;
651 }
652 if (threadId == 0) { // ignore the swapper thread
653 continue;
654 }
655 int execNameQuark = -1;
656 try {
657 try {
658 execNameQuark = ssq.getQuarkRelative(threadQuark, Attributes.EXEC_NAME);
659 } catch (AttributeNotFoundException e) {
660 continue;
661 }
662 int ppidQuark = ssq.getQuarkRelative(threadQuark, Attributes.PPID);
faa38350
PT
663 List<ITmfStateInterval> execNameIntervals = ssq.queryHistoryRange(execNameQuark, start, end - 1); // use monitor when available in api
664 if (monitor.isCanceled()) {
665 return;
666 }
826deb93 667 ControlFlowEntry entry = null;
6151d86c 668 for (ITmfStateInterval execNameInterval : execNameIntervals) {
faa38350
PT
669 if (monitor.isCanceled()) {
670 return;
671 }
b67a2540
AM
672 if (!execNameInterval.getStateValue().isNull() &&
673 execNameInterval.getStateValue().getType() == ITmfStateValue.Type.STRING) {
6151d86c
PT
674 String execName = execNameInterval.getStateValue().unboxStr();
675 long startTime = execNameInterval.getStartTime();
676 long endTime = execNameInterval.getEndTime() + 1;
6151d86c
PT
677 int ppid = -1;
678 if (ppidQuark != -1) {
679 ITmfStateInterval ppidInterval = ssq.querySingleState(startTime, ppidQuark);
680 ppid = ppidInterval.getStateValue().unboxInt();
681 }
826deb93
PT
682 if (entry == null) {
683 entry = new ControlFlowEntry(threadQuark, ctfKernelTrace, execName, threadId, ppid, startTime, endTime);
684 entryList.add(entry);
685 } else {
686 // update the name of the entry to the latest execName
687 entry.setName(execName);
688 }
6151d86c
PT
689 entry.addEvent(new TimeEvent(entry, startTime, endTime - startTime));
690 } else {
826deb93 691 entry = null;
6151d86c
PT
692 }
693 }
694 } catch (AttributeNotFoundException e) {
695 e.printStackTrace();
696 } catch (TimeRangeException e) {
697 e.printStackTrace();
698 } catch (StateValueTypeException e) {
699 e.printStackTrace();
96345c5a
AM
700 } catch (StateSystemDisposedException e) {
701 /* Ignored */
6151d86c
PT
702 }
703 }
704 buildTree(entryList, rootList);
705 }
706 Collections.sort(rootList, fControlFlowEntryComparator);
faa38350
PT
707 synchronized (fEntryListMap) {
708 fEntryListMap.put(trace, (ArrayList<ControlFlowEntry>) rootList.clone());
709 }
710 if (trace == fTrace) {
d7ee91bb 711 refresh();
6151d86c 712 }
6151d86c
PT
713 }
714 for (ControlFlowEntry entry : rootList) {
faa38350
PT
715 if (monitor.isCanceled()) {
716 return;
717 }
718 buildStatusEvents(trace, entry, monitor);
6151d86c
PT
719 }
720 }
721
722 private static void buildTree(ArrayList<ControlFlowEntry> entryList,
723 ArrayList<ControlFlowEntry> rootList) {
724 for (ControlFlowEntry entry : entryList) {
725 boolean root = true;
726 if (entry.getParentThreadId() > 0) {
727 for (ControlFlowEntry parent : entryList) {
728 if (parent.getThreadId() == entry.getParentThreadId() &&
729 entry.getStartTime() >= parent.getStartTime() &&
730 entry.getStartTime() <= parent.getEndTime()) {
731 parent.addChild(entry);
732 root = false;
733 break;
734 }
735 }
736 }
737 if (root) {
738 rootList.add(entry);
739 }
740 }
741 }
742
faa38350 743 private void buildStatusEvents(ITmfTrace trace, ControlFlowEntry entry, IProgressMonitor monitor) {
a51b2b9f 744 ITmfStateSystem ssq = entry.getTrace().getStateSystem(CtfKernelTrace.STATE_ID);
6151d86c
PT
745 long start = ssq.getStartTime();
746 long end = ssq.getCurrentEndTime() + 1;
747 long resolution = Math.max(1, (end - start) / fDisplayWidth);
faa38350
PT
748 List<ITimeEvent> eventList = getEventList(entry, entry.getStartTime(), entry.getEndTime(), resolution, monitor);
749 if (monitor.isCanceled()) {
750 return;
751 }
6151d86c 752 entry.setEventList(eventList);
faa38350
PT
753 if (trace == fTrace) {
754 redraw();
755 }
6151d86c 756 for (ITimeGraphEntry child : entry.getChildren()) {
faa38350
PT
757 if (monitor.isCanceled()) {
758 return;
759 }
760 buildStatusEvents(trace, (ControlFlowEntry) child, monitor);
6151d86c
PT
761 }
762 }
763
764 private static List<ITimeEvent> getEventList(ControlFlowEntry entry,
765 long startTime, long endTime, long resolution,
766 IProgressMonitor monitor) {
41b5c37f
AM
767 final long realStart = Math.max(startTime, entry.getStartTime());
768 final long realEnd = Math.min(endTime, entry.getEndTime());
769 if (realEnd <= realStart) {
6151d86c
PT
770 return null;
771 }
a51b2b9f 772 ITmfStateSystem ssq = entry.getTrace().getStateSystem(CtfKernelTrace.STATE_ID);
6151d86c
PT
773 List<ITimeEvent> eventList = null;
774 try {
775 int statusQuark = ssq.getQuarkRelative(entry.getThreadQuark(), Attributes.STATUS);
41b5c37f 776 List<ITmfStateInterval> statusIntervals = ssq.queryHistoryRange(statusQuark, realStart, realEnd - 1, resolution, monitor);
6151d86c
PT
777 eventList = new ArrayList<ITimeEvent>(statusIntervals.size());
778 long lastEndTime = -1;
779 for (ITmfStateInterval statusInterval : statusIntervals) {
780 if (monitor.isCanceled()) {
781 return null;
782 }
783 long time = statusInterval.getStartTime();
784 long duration = statusInterval.getEndTime() - time + 1;
785 int status = -1;
786 try {
787 status = statusInterval.getStateValue().unboxInt();
788 } catch (StateValueTypeException e) {
789 e.printStackTrace();
790 }
791 if (lastEndTime != time && lastEndTime != -1) {
af10fe06 792 eventList.add(new TimeEvent(entry, lastEndTime, time - lastEndTime));
6151d86c
PT
793 }
794 eventList.add(new ControlFlowEvent(entry, time, duration, status));
795 lastEndTime = time + duration;
796 }
797 } catch (AttributeNotFoundException e) {
798 e.printStackTrace();
799 } catch (TimeRangeException e) {
800 e.printStackTrace();
96345c5a
AM
801 } catch (StateSystemDisposedException e) {
802 /* Ignored */
6151d86c
PT
803 }
804 return eventList;
805 }
806
d7ee91bb 807 private void refresh() {
6151d86c
PT
808 Display.getDefault().asyncExec(new Runnable() {
809 @Override
810 public void run() {
811 if (fTimeGraphCombo.isDisposed()) {
812 return;
813 }
814 ITimeGraphEntry[] entries = null;
faa38350
PT
815 synchronized (fEntryListMap) {
816 fEntryList = fEntryListMap.get(fTrace);
817 if (fEntryList == null) {
818 fEntryList = new ArrayList<ControlFlowEntry>();
819 }
6151d86c
PT
820 entries = fEntryList.toArray(new ITimeGraphEntry[0]);
821 }
822 Arrays.sort(entries, fControlFlowEntryComparator);
823 fTimeGraphCombo.setInput(entries);
824 fTimeGraphCombo.getTimeGraphViewer().setTimeBounds(fStartTime, fEndTime);
825
d7ee91bb
PT
826 long timestamp = fTrace == null ? 0 : fTrace.getCurrentTime().normalize(0, ITmfTimestamp.NANOSECOND_SCALE).getValue();
827 long startTime = fTrace == null ? 0 : fTrace.getCurrentRange().getStartTime().normalize(0, ITmfTimestamp.NANOSECOND_SCALE).getValue();
828 long endTime = fTrace == null ? 0 : fTrace.getCurrentRange().getEndTime().normalize(0, ITmfTimestamp.NANOSECOND_SCALE).getValue();
829 startTime = Math.max(startTime, fStartTime);
830 endTime = Math.min(endTime, fEndTime);
831 fTimeGraphCombo.getTimeGraphViewer().setSelectedTime(timestamp, false);
832 fTimeGraphCombo.getTimeGraphViewer().setStartFinishTime(startTime, endTime);
6151d86c 833
6151d86c
PT
834 for (TreeColumn column : fTimeGraphCombo.getTreeViewer().getTree().getColumns()) {
835 column.pack();
836 }
837
d7ee91bb 838 startZoomThread(startTime, endTime);
6151d86c
PT
839 }
840 });
841 }
842
843 private void redraw() {
844 synchronized (fSyncObj) {
845 if (fRedrawState == State.IDLE) {
846 fRedrawState = State.BUSY;
847 } else {
848 fRedrawState = State.PENDING;
849 return;
850 }
851 }
852 Display.getDefault().asyncExec(new Runnable() {
853 @Override
854 public void run() {
855 if (fTimeGraphCombo.isDisposed()) {
856 return;
857 }
858 fTimeGraphCombo.redraw();
859 fTimeGraphCombo.update();
860 synchronized (fSyncObj) {
861 if (fRedrawState == State.PENDING) {
862 fRedrawState = State.IDLE;
863 redraw();
864 } else {
865 fRedrawState = State.IDLE;
866 }
867 }
868 }
869 });
870 }
871
872 private void startZoomThread(long startTime, long endTime) {
873 if (fZoomThread != null) {
874 fZoomThread.cancel();
875 }
faa38350 876 fZoomThread = new ZoomThread(fEntryList, startTime, endTime);
6151d86c
PT
877 fZoomThread.start();
878 }
879
880 private void makeActions() {
881 fPreviousResourceAction = fTimeGraphCombo.getTimeGraphViewer().getPreviousItemAction();
882 fPreviousResourceAction.setText(Messages.ControlFlowView_previousProcessActionNameText);
883 fPreviousResourceAction.setToolTipText(Messages.ControlFlowView_previousProcessActionToolTipText);
884 fNextResourceAction = fTimeGraphCombo.getTimeGraphViewer().getNextItemAction();
885 fNextResourceAction.setText(Messages.ControlFlowView_nextProcessActionNameText);
886 fNextResourceAction.setToolTipText(Messages.ControlFlowView_nextProcessActionToolTipText);
887 }
888
889 private void contributeToActionBars() {
890 IActionBars bars = getViewSite().getActionBars();
891 fillLocalToolBar(bars.getToolBarManager());
892 }
893
894 private void fillLocalToolBar(IToolBarManager manager) {
6ac5a950 895 manager.add(fTimeGraphCombo.getShowFilterAction());
6151d86c
PT
896 manager.add(fTimeGraphCombo.getTimeGraphViewer().getShowLegendAction());
897 manager.add(new Separator());
898 manager.add(fTimeGraphCombo.getTimeGraphViewer().getResetScaleAction());
899 manager.add(fTimeGraphCombo.getTimeGraphViewer().getPreviousEventAction());
900 manager.add(fTimeGraphCombo.getTimeGraphViewer().getNextEventAction());
901 manager.add(fPreviousResourceAction);
902 manager.add(fNextResourceAction);
903 manager.add(fTimeGraphCombo.getTimeGraphViewer().getZoomInAction());
904 manager.add(fTimeGraphCombo.getTimeGraphViewer().getZoomOutAction());
905 manager.add(new Separator());
906 }
907}
This page took 0.071415 seconds and 5 git commands to generate.