X-Git-Url: http://drtracing.org/?a=blobdiff_plain;f=org.eclipse.linuxtools.lttng2.kernel.ui%2Fsrc%2Forg%2Feclipse%2Flinuxtools%2Finternal%2Flttng2%2Fkernel%2Fui%2Fviews%2Fcontrolflow%2FControlFlowView.java;h=03d2c4f94dfd5f9ac7b8c7f1dbcb542e5fc2cc05;hb=ea21cd6567c642dc081ee122d6dcc1125dd9ae70;hp=362fd5d83b720e2ab671e6dd50cd430bb33b7949;hpb=f7ddf9b3a76b987f41d95a88404e199dec4d8ddf;p=deliverable%2Ftracecompass.git diff --git a/org.eclipse.linuxtools.lttng2.kernel.ui/src/org/eclipse/linuxtools/internal/lttng2/kernel/ui/views/controlflow/ControlFlowView.java b/org.eclipse.linuxtools.lttng2.kernel.ui/src/org/eclipse/linuxtools/internal/lttng2/kernel/ui/views/controlflow/ControlFlowView.java index 362fd5d83b..03d2c4f94d 100644 --- a/org.eclipse.linuxtools.lttng2.kernel.ui/src/org/eclipse/linuxtools/internal/lttng2/kernel/ui/views/controlflow/ControlFlowView.java +++ b/org.eclipse.linuxtools.lttng2.kernel.ui/src/org/eclipse/linuxtools/internal/lttng2/kernel/ui/views/controlflow/ControlFlowView.java @@ -1,11 +1,11 @@ /******************************************************************************* * Copyright (c) 2012 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: * Patrick Tasse - Initial API and implementation *******************************************************************************/ @@ -14,6 +14,7 @@ package org.eclipse.linuxtools.internal.lttng2.kernel.ui.views.controlflow; import java.util.ArrayList; import java.util.Arrays; +import java.util.Collections; import java.util.Comparator; import java.util.List; @@ -43,6 +44,7 @@ import org.eclipse.linuxtools.tmf.core.signal.TmfSignalHandler; import org.eclipse.linuxtools.tmf.core.signal.TmfStateSystemBuildCompleted; import org.eclipse.linuxtools.tmf.core.signal.TmfTimeSynchSignal; import org.eclipse.linuxtools.tmf.core.statesystem.IStateSystemQuerier; +import org.eclipse.linuxtools.tmf.core.statesystem.IStateSystemQuerier2; import org.eclipse.linuxtools.tmf.core.trace.ITmfTrace; import org.eclipse.linuxtools.tmf.core.trace.TmfExperiment; import org.eclipse.linuxtools.tmf.ui.views.TmfView; @@ -66,6 +68,10 @@ import org.eclipse.swt.widgets.Display; import org.eclipse.swt.widgets.TreeColumn; import org.eclipse.ui.IActionBars; +/** + * The Control Flow view main object + * + */ public class ControlFlowView extends TmfView { // ------------------------------------------------------------------------ @@ -96,6 +102,11 @@ public class ControlFlowView extends TmfView { TRACE_COLUMN }; + /** + * Redraw state enum + */ + private enum State { IDLE, BUSY, PENDING } + // ------------------------------------------------------------------------ // Fields // ------------------------------------------------------------------------ @@ -109,6 +120,9 @@ public class ControlFlowView extends TmfView { // The timegraph entry list private ArrayList fEntryList; + // The time graph entry list synchronization object + final private Object fEntryListSyncObj = new Object(); + // The start time private long fStartTime; @@ -116,7 +130,7 @@ public class ControlFlowView extends TmfView { private long fEndTime; // The display width - private int fDisplayWidth; + private final int fDisplayWidth; // The zoom thread private ZoomThread fZoomThread; @@ -126,9 +140,15 @@ public class ControlFlowView extends TmfView { // The previous resource action private Action fPreviousResourceAction; - + // A comparator class - private ControlFlowEntryComparator fControlFlowEntryComparator = new ControlFlowEntryComparator(); + private final ControlFlowEntryComparator fControlFlowEntryComparator = new ControlFlowEntryComparator(); + + // The redraw state used to prevent unnecessary queuing of display runnables + private State fRedrawState = State.IDLE; + + // The redraw synchronization object + final private Object fSyncObj = new Object(); // ------------------------------------------------------------------------ // Classes @@ -224,6 +244,9 @@ public class ControlFlowView extends TmfView { ControlFlowEntry entry1 = (ControlFlowEntry) o1; ControlFlowEntry entry2 = (ControlFlowEntry) o2; result = entry1.getTrace().getStartTime().compareTo(entry2.getTrace().getStartTime()); + if (result == 0) { + result = entry1.getTrace().getName().compareTo(entry2.getTrace().getName()); + } if (result == 0) { result = entry1.getThreadId() < entry2.getThreadId() ? -1 : entry1.getThreadId() > entry2.getThreadId() ? 1 : 0; } @@ -237,12 +260,12 @@ public class ControlFlowView extends TmfView { } } - + private class ZoomThread extends Thread { - private long fZoomStartTime; - private long fZoomEndTime; - private long fResolution; - private IProgressMonitor fMonitor; + private final long fZoomStartTime; + private final long fZoomEndTime; + private final long fResolution; + private final IProgressMonitor fMonitor; public ZoomThread(long startTime, long endTime) { super("ControlFlowView zoom"); //$NON-NLS-1$ @@ -254,29 +277,31 @@ public class ControlFlowView extends TmfView { @Override public void run() { - ArrayList entryList = fEntryList; + ArrayList entryList = null; + synchronized (fEntryListSyncObj) { + entryList = fEntryList; + } if (entryList == null) { return; } for (ControlFlowEntry entry : entryList) { if (fMonitor.isCanceled()) { - return; + break; } zoom(entry, fMonitor); } - redraw(); } private void zoom(ControlFlowEntry entry, IProgressMonitor monitor) { if (fZoomStartTime <= fStartTime && fZoomEndTime >= fEndTime) { entry.setZoomedEventList(null); - return; - } - List zoomedEventList = getEventList(entry, fZoomStartTime, fZoomEndTime, fResolution, monitor); - if (fMonitor.isCanceled()) { - return; + } else { + List zoomedEventList = getEventList(entry, fZoomStartTime, fZoomEndTime, fResolution, monitor); + if (zoomedEventList != null) { + entry.setZoomedEventList(zoomedEventList); + } } - entry.setZoomedEventList(zoomedEventList); + redraw(); for (ControlFlowEntry child : entry.getChildren()) { if (fMonitor.isCanceled()) { return; @@ -294,6 +319,9 @@ public class ControlFlowView extends TmfView { // Constructors // ------------------------------------------------------------------------ + /** + * Constructor + */ public ControlFlowView() { super(ID); fDisplayWidth = Display.getDefault().getBounds().width; @@ -377,6 +405,12 @@ public class ControlFlowView extends TmfView { // Signal handlers // ------------------------------------------------------------------------ + /** + * Handler for the experiment selected signal + * + * @param signal + * The signal that's received + */ @TmfSignalHandler public void experimentSelected(final TmfExperimentSelectedSignal signal) { if (signal.getExperiment().equals(fSelectedExperiment)) { @@ -392,9 +426,15 @@ public class ControlFlowView extends TmfView { thread.start(); } + /** + * Handler for the synch signal + * + * @param signal + * The signal that's received + */ @TmfSignalHandler public void synchToTime(final TmfTimeSynchSignal signal) { - if (signal.getSource() == this) { + if (signal.getSource() == this || fSelectedExperiment == null || fSelectedExperiment.getTraces() == null) { return; } final long time = signal.getCurrentTime().normalize(0, -9).getValue(); @@ -433,7 +473,7 @@ public class ControlFlowView extends TmfView { } } final int selectedThread = thread; - + Display.getDefault().asyncExec(new Runnable() { @Override public void run() { @@ -458,9 +498,15 @@ public class ControlFlowView extends TmfView { }); } + /** + * Handler for the range sync signal + * + * @param signal + * The signal that's received + */ @TmfSignalHandler public void synchToRange(final TmfRangeSynchSignal signal) { - if (signal.getSource() == this) { + if (signal.getSource() == this || fSelectedExperiment == null) { return; } final long startTime = signal.getCurrentRange().getStartTime().normalize(0, -9).getValue(); @@ -479,10 +525,16 @@ public class ControlFlowView extends TmfView { }); } + /** + * Handler for the state system build completed signal + * + * @param signal + * The signal that's received + */ @TmfSignalHandler public void stateSystemBuildCompleted (final TmfStateSystemBuildCompleted signal) { final TmfExperiment selectedExperiment = fSelectedExperiment; - if (selectedExperiment == null) { + if (selectedExperiment == null || selectedExperiment.getTraces() == null) { return; } for (ITmfTrace trace : selectedExperiment.getTraces()) { @@ -508,9 +560,10 @@ public class ControlFlowView extends TmfView { fStartTime = Long.MAX_VALUE; fEndTime = Long.MIN_VALUE; fSelectedExperiment = (TmfExperiment) experiment; - ArrayList entryList = new ArrayList(); + ArrayList rootList = new ArrayList(); for (ITmfTrace trace : experiment.getTraces()) { if (trace instanceof CtfKernelTrace) { + ArrayList entryList = new ArrayList(); CtfKernelTrace ctfKernelTrace = (CtfKernelTrace) trace; IStateSystemQuerier ssq = ctfKernelTrace.getStateSystem(); long start = ssq.getStartTime(); @@ -567,19 +620,21 @@ public class ControlFlowView extends TmfView { e.printStackTrace(); } } + buildTree(entryList, rootList); } - buildTree(entryList); - refresh(INITIAL_WINDOW_OFFSET); - ControlFlowEntry[] entries = fEntryList.toArray(new ControlFlowEntry[0]); - Arrays.sort(entries, fControlFlowEntryComparator); - for (ControlFlowEntry entry : entries) { - buildStatusEvents(entry); + Collections.sort(rootList, fControlFlowEntryComparator); + synchronized (fEntryListSyncObj) { + fEntryList = (ArrayList) rootList.clone(); } + refresh(INITIAL_WINDOW_OFFSET); + } + for (ControlFlowEntry entry : rootList) { + buildStatusEvents(entry); } } - private void buildTree(ArrayList entryList) { - ArrayList rootList = new ArrayList(); + private static void buildTree(ArrayList entryList, + ArrayList rootList) { for (ControlFlowEntry entry : entryList) { boolean root = true; if (entry.getParentThreadId() > 0) { @@ -597,7 +652,6 @@ public class ControlFlowView extends TmfView { rootList.add(entry); } } - fEntryList = rootList; } private void buildStatusEvents(ControlFlowEntry entry) { @@ -613,17 +667,19 @@ public class ControlFlowView extends TmfView { } } - private List getEventList(ControlFlowEntry entry, long startTime, long endTime, long resolution, IProgressMonitor monitor) { + private static List getEventList(ControlFlowEntry entry, + long startTime, long endTime, long resolution, + IProgressMonitor monitor) { startTime = Math.max(startTime, entry.getStartTime()); endTime = Math.min(endTime, entry.getEndTime()); if (endTime <= startTime) { return null; } - IStateSystemQuerier ssq = entry.getTrace().getStateSystem(); + IStateSystemQuerier2 ssq = (IStateSystemQuerier2) entry.getTrace().getStateSystem(); List eventList = null; try { int statusQuark = ssq.getQuarkRelative(entry.getThreadQuark(), Attributes.STATUS); - List statusIntervals = ssq.queryHistoryRange(statusQuark, startTime, endTime - 1, resolution); + List statusIntervals = ssq.queryHistoryRange(statusQuark, startTime, endTime - 1, resolution, monitor); eventList = new ArrayList(statusIntervals.size()); long lastEndTime = -1; for (ITmfStateInterval statusInterval : statusIntervals) { @@ -659,7 +715,10 @@ public class ControlFlowView extends TmfView { if (fTimeGraphCombo.isDisposed()) { return; } - ITimeGraphEntry[] entries = fEntryList.toArray(new ITimeGraphEntry[0]); + ITimeGraphEntry[] entries = null; + synchronized (fEntryListSyncObj) { + entries = fEntryList.toArray(new ITimeGraphEntry[0]); + } Arrays.sort(entries, fControlFlowEntryComparator); fTimeGraphCombo.setInput(entries); fTimeGraphCombo.getTimeGraphViewer().setTimeBounds(fStartTime, fEndTime); @@ -680,6 +739,14 @@ public class ControlFlowView extends TmfView { } private void redraw() { + synchronized (fSyncObj) { + if (fRedrawState == State.IDLE) { + fRedrawState = State.BUSY; + } else { + fRedrawState = State.PENDING; + return; + } + } Display.getDefault().asyncExec(new Runnable() { @Override public void run() { @@ -688,6 +755,14 @@ public class ControlFlowView extends TmfView { } fTimeGraphCombo.redraw(); fTimeGraphCombo.update(); + synchronized (fSyncObj) { + if (fRedrawState == State.PENDING) { + fRedrawState = State.IDLE; + redraw(); + } else { + fRedrawState = State.IDLE; + } + } } }); }