tmf: Statistics provider based on event requests
authorAlexandre Montplaisir <alexmonthy@voxpopuli.im>
Mon, 22 Oct 2012 18:37:45 +0000 (14:37 -0400)
committerAlexandre Montplaisir <alexmonthy@voxpopuli.im>
Wed, 31 Oct 2012 18:10:35 +0000 (14:10 -0400)
This patch adds a TmfEventsStatistics, which uses trace event
requests and counts the instances of each event types to
provide statistics information. This is useful for trace types
that cannot use the default implementation using the state
system (traces where events are not chronologically ordered,
for example).

The previous TmfStatistics has been renamed TmfStateStatistics,
to better differentiate between the two alternatives that are
now available.

To keep the request coalescing, the separate threading is now
done is a new ITmfStatistics.updateStats(). This allows the signal
handler code to send the queries, but return immediately and
spawn a thread that will wait for the requests to be done.

When the results are ready, they will be sent back to the view
using the new TmfStatsUpdatedSignal. This makes the handler for
the StateSystemBuildCompleted signal obsolete.

Change-Id: I5b6237aef7f5c7cb373c68e4624376146a6e5086
Signed-off-by: Alexandre Montplaisir <alexmonthy@voxpopuli.im>
Reviewed-on: https://git.eclipse.org/r/8376
Tested-by: Hudson CI
Reviewed-by: Francois Chouinard <fchouinard@gmail.com>
IP-Clean: Francois Chouinard <fchouinard@gmail.com>
Tested-by: Francois Chouinard <fchouinard@gmail.com>
org.eclipse.linuxtools.tmf.core/src/org/eclipse/linuxtools/tmf/core/signal/TmfStatsUpdatedSignal.java [new file with mode: 0644]
org.eclipse.linuxtools.tmf.core/src/org/eclipse/linuxtools/tmf/core/statistics/ITmfStatistics.java
org.eclipse.linuxtools.tmf.core/src/org/eclipse/linuxtools/tmf/core/statistics/StatsStateProvider.java
org.eclipse.linuxtools.tmf.core/src/org/eclipse/linuxtools/tmf/core/statistics/TmfEventsStatistics.java [new file with mode: 0644]
org.eclipse.linuxtools.tmf.core/src/org/eclipse/linuxtools/tmf/core/statistics/TmfStateStatistics.java [new file with mode: 0644]
org.eclipse.linuxtools.tmf.core/src/org/eclipse/linuxtools/tmf/core/statistics/TmfStatistics.java [deleted file]
org.eclipse.linuxtools.tmf.core/src/org/eclipse/linuxtools/tmf/core/trace/TmfTrace.java
org.eclipse.linuxtools.tmf.ui/src/org/eclipse/linuxtools/tmf/ui/viewers/statistics/TmfStatisticsViewer.java

diff --git a/org.eclipse.linuxtools.tmf.core/src/org/eclipse/linuxtools/tmf/core/signal/TmfStatsUpdatedSignal.java b/org.eclipse.linuxtools.tmf.core/src/org/eclipse/linuxtools/tmf/core/signal/TmfStatsUpdatedSignal.java
new file mode 100644 (file)
index 0000000..da339ec
--- /dev/null
@@ -0,0 +1,95 @@
+/*******************************************************************************
+ * 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:
+ *   Alexandre Montplaisir - Initial API and implementation
+ *******************************************************************************/
+
+package org.eclipse.linuxtools.tmf.core.signal;
+
+import java.util.Map;
+
+import org.eclipse.linuxtools.tmf.core.statistics.ITmfStatistics;
+import org.eclipse.linuxtools.tmf.core.trace.ITmfTrace;
+
+/**
+ * Signal sent when a call to {@link ITmfStatistics#updateStats} has completed.
+ *
+ * @author Alexandre Montplaisir
+ * @version 1.0
+ * @since 2.0
+ */
+public class TmfStatsUpdatedSignal extends TmfSignal {
+
+    private final ITmfTrace trace;
+    private final boolean isGlobal;
+    private final long eventTotal;
+    private final Map<String, Long> eventsPerType;
+
+    /**
+     * Constructor
+     *
+     * @param source
+     *            Object sending this signal
+     * @param trace
+     *            The trace for which we track the statistics
+     * @param isGlobal
+     *            Is this a global query (whole range of the trace), or not
+     * @param eventTotal
+     *            The total number of events. This should be equal to the sum of
+     *            the values in eventsPerType.
+     * @param eventsPerType
+     *            The map representing the number of events of each type
+     *
+     * @since 2.0
+     */
+    public TmfStatsUpdatedSignal(Object source, ITmfTrace trace, boolean isGlobal,
+            long eventTotal, Map<String, Long> eventsPerType) {
+        super(source);
+        this.trace = trace;
+        this.isGlobal = isGlobal;
+        this.eventTotal = eventTotal;
+        this.eventsPerType = eventsPerType;
+    }
+
+    /**
+     * @return The trace referred to by this signal
+     */
+    public ITmfTrace getTrace() {
+        return trace;
+    }
+
+    /**
+     * @return True if it's a global query, false if it's for the current time
+     *         range
+     */
+    public boolean isGlobal() {
+        return isGlobal;
+    }
+
+    /**
+     * @return The total number of events for this query
+     */
+    public long getEventTotal() {
+        return eventTotal;
+    }
+
+    /**
+     * @return The map representing the number of events per type for this query
+     */
+    public Map<String, Long> getEventsPerType() {
+        return eventsPerType;
+    }
+
+    @Override
+    public String toString() {
+        return "[TmfStatsUpdatedSignal (trace = " + trace.toString() + //$NON-NLS-1$
+                ", total = " + eventTotal + ")]"; //$NON-NLS-1$ //$NON-NLS-2$
+    }
+
+}
index d02b7674bb4bf3da5d70846bb93ca61e19a31b2f..7c1c078957f45553b3ef09ab63f968d3ba8278af 100644 (file)
@@ -15,6 +15,7 @@ package org.eclipse.linuxtools.tmf.core.statistics;
 import java.util.Map;
 
 import org.eclipse.linuxtools.tmf.core.event.ITmfTimestamp;
+import org.eclipse.linuxtools.tmf.core.signal.TmfStatsUpdatedSignal;
 
 /**
  * Provider for statistics, which is assigned to a trace. This can be used to
@@ -25,6 +26,29 @@ import org.eclipse.linuxtools.tmf.core.event.ITmfTimestamp;
  */
 public interface ITmfStatistics {
 
+    /**
+     * This method provides a centralized and asynchronous way of querying
+     * statistics information. It is an alternative to the other get* methods,
+     * and should not block the caller for too long.
+     *
+     * Implementors can usually call their own getEventTotal(),
+     * getEventsInRange(), etc. but should do so in a separate thread, and
+     * should send a {@link TmfStatsUpdatedSignal} whenever they are done (that
+     * signal will carry the results).
+     *
+     * @param isGlobal
+     *            Is this for a global query (whole time range of a trace), or
+     *            just for a specific time range.
+     * @param start
+     *            The start time of the query range. Has no effect if isGlobal
+     *            is true.
+     * @param end
+     *            The end time of the query range. Has no effect if isGlobal is
+     *            true.
+     */
+    public void updateStats(final boolean isGlobal, ITmfTimestamp start,
+            ITmfTimestamp end);
+
     /**
      * Return the total number of events in the trace.
      *
index 362c4aca5f2d9a9cacedd724473312fb0532e960..37582d7b10133417eff583ee2418e0ab999b53ec 100644 (file)
@@ -18,12 +18,12 @@ import org.eclipse.linuxtools.tmf.core.exceptions.StateValueTypeException;
 import org.eclipse.linuxtools.tmf.core.exceptions.TimeRangeException;
 import org.eclipse.linuxtools.tmf.core.statesystem.AbstractStateChangeInput;
 import org.eclipse.linuxtools.tmf.core.statesystem.ITmfStateSystemBuilder;
-import org.eclipse.linuxtools.tmf.core.statistics.TmfStatistics.Attributes;
+import org.eclipse.linuxtools.tmf.core.statistics.TmfStateStatistics.Attributes;
 import org.eclipse.linuxtools.tmf.core.trace.ITmfTrace;
 
 /**
- * The state provider for traces statistics. It should work with any type of
- * trace TMF can handle.
+ * The state provider for traces statistics that use TmfStateStatistics. It
+ * should work with any trace type for which we can use the state system.
  *
  * The resulting attribute tree will look like this:
  *
diff --git a/org.eclipse.linuxtools.tmf.core/src/org/eclipse/linuxtools/tmf/core/statistics/TmfEventsStatistics.java b/org.eclipse.linuxtools.tmf.core/src/org/eclipse/linuxtools/tmf/core/statistics/TmfEventsStatistics.java
new file mode 100644 (file)
index 0000000..39abdd3
--- /dev/null
@@ -0,0 +1,248 @@
+/*******************************************************************************
+ * 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:
+ *   Alexandre Montplaisir - Initial API and implementation
+ ******************************************************************************/
+
+package org.eclipse.linuxtools.tmf.core.statistics;
+
+import java.util.HashMap;
+import java.util.Map;
+
+import org.eclipse.linuxtools.tmf.core.event.ITmfEvent;
+import org.eclipse.linuxtools.tmf.core.event.ITmfTimestamp;
+import org.eclipse.linuxtools.tmf.core.event.TmfTimeRange;
+import org.eclipse.linuxtools.tmf.core.request.ITmfDataRequest;
+import org.eclipse.linuxtools.tmf.core.request.TmfDataRequest;
+import org.eclipse.linuxtools.tmf.core.request.TmfEventRequest;
+import org.eclipse.linuxtools.tmf.core.signal.TmfSignal;
+import org.eclipse.linuxtools.tmf.core.signal.TmfSignalManager;
+import org.eclipse.linuxtools.tmf.core.signal.TmfStatsUpdatedSignal;
+import org.eclipse.linuxtools.tmf.core.trace.ITmfTrace;
+
+/**
+ * Implementation of ITmfStatistics which uses event requests to the trace to
+ * retrieve its information.
+ *
+ * There is almost no setup time, but queries themselves are longer than with a
+ * TmfStateStatistics. Queries are O(n * m), where n is the size of the trace,
+ * and m is the portion of the trace covered by the selected interval.
+ *
+ * @author Alexandre Montplaisir
+ * @since 2.0
+ */
+public class TmfEventsStatistics implements ITmfStatistics {
+
+    private final ITmfTrace trace;
+
+    /* Event request objects for the time-range request. */
+    private StatsTotalRequest totalRequest = null;
+    private StatsPerTypeRequest perTypeRequest = null;
+
+    /**
+     * Constructor
+     *
+     * @param trace
+     *            The trace for which we are building the statistics
+     */
+    public TmfEventsStatistics(ITmfTrace trace) {
+        this.trace = trace;
+    }
+
+    @Override
+    public void updateStats(final boolean isGlobal, ITmfTimestamp start,
+            ITmfTimestamp end) {
+        cancelOngoingRequests();
+
+        /*
+         * Prepare and send the event requests. This needs to be done in the
+         * same thread, since it will be run by TmfStatisticsViewer's signal
+         * handlers, to ensure they get correctly coalesced.
+         */
+        TmfTimeRange range = isGlobal ? TmfTimeRange.ETERNITY : new TmfTimeRange(start, end);
+        final StatsTotalRequest totalReq = new StatsTotalRequest(trace, range);
+        final StatsPerTypeRequest perTypeReq = new StatsPerTypeRequest(trace, range);
+
+        /*
+         * Only allow one time-range request at a time (there should be only one
+         * global request at the beginning anyway, no need to track those).
+         */
+        if (!isGlobal) {
+            this.totalRequest = totalReq;
+            this.perTypeRequest = perTypeReq;
+        }
+
+        trace.sendRequest(totalReq);
+        trace.sendRequest(perTypeReq);
+
+        /*
+         * This thread can now return. Start a new thread that will wait until
+         * the request are done and will then send the results.
+         */
+        Thread statsThread = new Thread("Statistics update") { //$NON-NLS-1$
+            @Override
+            public void run() {
+                /* Wait for both requests to complete */
+                try {
+                    totalReq.waitForCompletion();
+                    perTypeReq.waitForCompletion();
+                } catch (InterruptedException e) {
+                    e.printStackTrace();
+                }
+
+                /*
+                 * If the request was cancelled, this means a newer one was
+                 * sent, discard the current one and return without sending
+                 * the signal.
+                 */
+                if (totalReq.isCancelled() || perTypeReq.isCancelled()) {
+                    return;
+                }
+
+                /* If it completed successfully, retrieve the results. */
+                long total = totalReq.getResult();
+                Map<String, Long> map = perTypeReq.getResults();
+
+                /* Send the signal to notify the stats viewer to update its display. */
+                TmfSignal sig = new TmfStatsUpdatedSignal(this, trace, isGlobal, total, map);
+                TmfSignalManager.dispatchSignal(sig);
+            }
+        };
+        statsThread.start();
+        return;
+    }
+
+    private synchronized void cancelOngoingRequests() {
+        if (totalRequest != null && totalRequest.isRunning()) {
+            totalRequest.cancel();
+        }
+        if (perTypeRequest != null && perTypeRequest.isRunning()) {
+            perTypeRequest.cancel();
+        }
+    }
+
+    @Override
+    public long getEventsTotal() {
+        StatsTotalRequest request = new StatsTotalRequest(trace, TmfTimeRange.ETERNITY);
+        sendAndWait(request);
+
+        long total = request.getResult();
+        return total;
+    }
+
+    @Override
+    public Map<String, Long> getEventTypesTotal() {
+        StatsPerTypeRequest request = new StatsPerTypeRequest(trace, TmfTimeRange.ETERNITY);
+        sendAndWait(request);
+
+        Map<String, Long> stats =  request.getResults();
+        return stats;
+    }
+
+    @Override
+    public long getEventsInRange(ITmfTimestamp start, ITmfTimestamp end) {
+        TmfTimeRange range = new TmfTimeRange(start, end);
+        StatsTotalRequest request = new StatsTotalRequest(trace, range);
+        sendAndWait(request);
+
+        long total =  request.getResult();
+        return total;
+    }
+
+    @Override
+    public Map<String, Long> getEventTypesInRange(ITmfTimestamp start,
+            ITmfTimestamp end) {
+        TmfTimeRange range = new TmfTimeRange(start, end);
+        StatsPerTypeRequest request = new StatsPerTypeRequest(trace, range);
+        sendAndWait(request);
+
+        Map<String, Long> stats =  request.getResults();
+        return stats;
+    }
+
+    private void sendAndWait(TmfEventRequest request) {
+        trace.sendRequest(request);
+        try {
+            request.waitForCompletion();
+        } catch (InterruptedException e) {
+            e.printStackTrace();
+        }
+    }
+
+
+    /**
+     * Event request to get the total number of events
+     */
+    private class StatsTotalRequest extends TmfEventRequest {
+
+        /* Total number of events the request has found */
+        private long total;
+
+        public StatsTotalRequest(ITmfTrace trace, TmfTimeRange range) {
+            super(trace.getEventType(), range, TmfDataRequest.ALL_DATA,
+                    trace.getCacheSize(), ITmfDataRequest.ExecutionType.BACKGROUND);
+            total = 0;
+        }
+
+        public long getResult() {
+            return total;
+        }
+
+        @Override
+        public void handleData(final ITmfEvent event) {
+            super.handleData(event);
+            if (event != null) {
+                if (event.getTrace() == trace) {
+                    total += 1;
+                }
+            }
+        }
+    }
+
+
+    /**
+     * Event request to get the counts per event type
+     */
+    private class StatsPerTypeRequest extends TmfEventRequest {
+
+        /* Map in which the results are saved */
+        private final Map<String, Long> stats;
+
+        public StatsPerTypeRequest(ITmfTrace trace, TmfTimeRange range) {
+            super(trace.getEventType(), range, TmfDataRequest.ALL_DATA,
+                    trace.getCacheSize(), ITmfDataRequest.ExecutionType.BACKGROUND);
+            this.stats = new HashMap<String, Long>();
+        }
+
+        public Map<String, Long> getResults() {
+            return stats;
+        }
+
+        @Override
+        public void handleData(final ITmfEvent event) {
+            super.handleData(event);
+            if (event != null) {
+                if (event.getTrace() == trace) {
+                    processEvent(event);
+                }
+            }
+        }
+
+        private void processEvent(ITmfEvent event) {
+            String eventType = event.getType().getName();
+            if (stats.containsKey(eventType)) {
+                long curValue = stats.get(eventType);
+                stats.put(eventType, curValue + 1L);
+            } else {
+                stats.put(eventType, 1L);
+            }
+        }
+    }
+
+}
diff --git a/org.eclipse.linuxtools.tmf.core/src/org/eclipse/linuxtools/tmf/core/statistics/TmfStateStatistics.java b/org.eclipse.linuxtools.tmf.core/src/org/eclipse/linuxtools/tmf/core/statistics/TmfStateStatistics.java
new file mode 100644 (file)
index 0000000..6146c20
--- /dev/null
@@ -0,0 +1,319 @@
+/*******************************************************************************
+ * 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:
+ *   Alexandre Montplaisir - Initial API and implementation
+ ******************************************************************************/
+
+package org.eclipse.linuxtools.tmf.core.statistics;
+
+import java.io.File;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+import org.eclipse.core.resources.IResource;
+import org.eclipse.core.runtime.CoreException;
+import org.eclipse.linuxtools.tmf.core.TmfCommonConstants;
+import org.eclipse.linuxtools.tmf.core.event.ITmfTimestamp;
+import org.eclipse.linuxtools.tmf.core.exceptions.AttributeNotFoundException;
+import org.eclipse.linuxtools.tmf.core.exceptions.StateValueTypeException;
+import org.eclipse.linuxtools.tmf.core.exceptions.TimeRangeException;
+import org.eclipse.linuxtools.tmf.core.exceptions.TmfTraceException;
+import org.eclipse.linuxtools.tmf.core.interval.ITmfStateInterval;
+import org.eclipse.linuxtools.tmf.core.signal.TmfSignal;
+import org.eclipse.linuxtools.tmf.core.signal.TmfSignalManager;
+import org.eclipse.linuxtools.tmf.core.signal.TmfStatsUpdatedSignal;
+import org.eclipse.linuxtools.tmf.core.statesystem.IStateChangeInput;
+import org.eclipse.linuxtools.tmf.core.statesystem.ITmfStateSystem;
+import org.eclipse.linuxtools.tmf.core.statesystem.StateSystemManager;
+import org.eclipse.linuxtools.tmf.core.trace.ITmfTrace;
+
+/**
+ * Implementation of ITmfStatistics which uses a state history for storing its
+ * information.
+ *
+ * It requires building the history first, but gives very fast response times
+ * when built : Queries are O(log n) wrt the size of the trace, and O(1) wrt to
+ * the size of the time interval selected.
+ *
+ * @author Alexandre Montplaisir
+ * @since 2.0
+ */
+
+public class TmfStateStatistics implements ITmfStatistics {
+
+    /** ID for the statistics state system */
+    public static final String STATE_ID = "org.eclipse.linuxtools.tmf.statistics"; //$NON-NLS-1$
+
+    /** Filename the "statistics state history" file will have */
+    private static final String STATS_STATE_FILENAME = "statistics.ht"; //$NON-NLS-1$
+
+    private final ITmfTrace trace;
+
+    /**
+     * The state system that's used to stored the statistics. It's hidden from
+     * the trace, so that it doesn't conflict with ITmfTrace.getStateSystem()
+     * (which is something else!)
+     */
+    private final ITmfStateSystem stats;
+
+    /**
+     * Empty constructor. The resulting TmfStatistics object will not be usable,
+     * but it might be needed for sub-classes.
+     */
+    public TmfStateStatistics() {
+        stats = null;
+        trace = null;
+    }
+
+    /**
+     * Constructor
+     *
+     * @param trace
+     *            The trace for which we build these statistics
+     * @throws TmfTraceException
+     *             If something went wrong trying to initialize the statistics
+     */
+    public TmfStateStatistics(ITmfTrace trace) throws TmfTraceException {
+        /* Set up the path to the history tree file we'll use */
+        this.trace = trace;
+        IResource resource = trace.getResource();
+        String supplDirectory = null;
+
+        try {
+            // get the directory where the history file will be stored.
+            supplDirectory = resource.getPersistentProperty(TmfCommonConstants.TRACE_SUPPLEMENTARY_FOLDER);
+        } catch (CoreException e) {
+            throw new TmfTraceException(e.toString(), e);
+        }
+
+        final File htFile = new File(supplDirectory + File.separator + STATS_STATE_FILENAME);
+        final IStateChangeInput htInput = new StatsStateProvider(trace);
+
+        this.stats = StateSystemManager.loadStateHistory(htFile, htInput, STATE_ID, false);
+    }
+
+    // ------------------------------------------------------------------------
+    // ITmfStatistics
+    // ------------------------------------------------------------------------
+
+    @Override
+    public void updateStats(final boolean isGlobal, final ITmfTimestamp start,
+            final ITmfTimestamp end) {
+        /*
+         * Since we are currently in a signal handler (ie, in the UI thread),
+         * and since state system queries can be arbitrarily long (O(log n) wrt
+         * the size of the trace), we will run those queries in a separate
+         * thread and update the statistics view out-of-band.
+         */
+        Thread statsThread = new Thread("Statistics update") { //$NON-NLS-1$
+            @Override
+            public void run() {
+                long total;
+                Map<String, Long> map;
+
+                /* Wait until the history building completed */
+                stats.waitUntilBuilt();
+
+                /* Range should be valid for both global and time range queries */
+                total = getEventsInRange(start, end);
+                map = getEventTypesInRange(start, end);
+
+                /* Send the signal to notify the stats viewer to update its display */
+                TmfSignal sig = new TmfStatsUpdatedSignal(this, trace, isGlobal, total, map);
+                TmfSignalManager.dispatchSignal(sig);
+            }
+        };
+        statsThread.start();
+        return;
+
+    }
+
+    @Override
+    public long getEventsTotal() {
+        long startTime = stats.getStartTime();
+        long endTime = stats.getCurrentEndTime();
+        int countAtStart = 0, countAtEnd = 0;
+
+        try {
+            final int quark = stats.getQuarkAbsolute(Attributes.TOTAL);
+            countAtStart = stats.querySingleState(startTime, quark).getStateValue().unboxInt();
+            countAtEnd = stats.querySingleState(endTime, quark).getStateValue().unboxInt();
+
+        } catch (TimeRangeException e) {
+            /* Assume there is no events for that range */
+            return 0;
+        } catch (AttributeNotFoundException e) {
+            e.printStackTrace();
+        } catch (StateValueTypeException e) {
+            e.printStackTrace();
+        }
+
+        long total = countAtEnd - countAtStart;
+        return total;
+    }
+
+    @Override
+    public Map<String, Long> getEventTypesTotal() {
+        Map<String, Long> map = new HashMap<String, Long>();
+        long endTime = stats.getCurrentEndTime(); //shouldn't need to check it...
+
+        try {
+            /* Get the list of quarks, one for each even type in the database */
+            int quark = stats.getQuarkAbsolute(Attributes.EVENT_TYPES);
+            List<Integer> quarks = stats.getSubAttributes(quark, false);
+
+            /* Since we want the total we can look only at the end */
+            List<ITmfStateInterval> endState = stats.queryFullState(endTime);
+
+            String curEventName;
+            long eventCount;
+            for (int typeQuark : quarks) {
+                curEventName = stats.getAttributeName(typeQuark);
+                eventCount = endState.get(typeQuark).getStateValue().unboxInt();
+                map.put(curEventName, eventCount);
+            }
+
+        } catch (TimeRangeException e) {
+            /* Assume there is no events, nothing will be put in the map. */
+        } catch (AttributeNotFoundException e) {
+            e.printStackTrace();
+        } catch (StateValueTypeException e) {
+            e.printStackTrace();
+        }
+        return map;
+    }
+
+    @Override
+    public long getEventsInRange(ITmfTimestamp start, ITmfTimestamp end) {
+        int countAtStart = 0, countAtEnd = 0;
+        long startTime = checkStartTime(start);
+        long endTime = checkEndTime(end);
+
+        try {
+            final int quark = stats.getQuarkAbsolute(Attributes.TOTAL);
+            countAtStart = stats.querySingleState(startTime, quark).getStateValue().unboxInt();
+            countAtEnd = stats.querySingleState(endTime, quark).getStateValue().unboxInt();
+
+        } catch (TimeRangeException e) {
+            /* Assume there is no events for that range */
+            return 0;
+        } catch (AttributeNotFoundException e) {
+            e.printStackTrace();
+        } catch (StateValueTypeException e) {
+            e.printStackTrace();
+        }
+
+        long total = countAtEnd - countAtStart;
+        return total;
+    }
+
+    @Override
+    public Map<String, Long> getEventTypesInRange(ITmfTimestamp start, ITmfTimestamp end) {
+        Map<String, Long> map = new HashMap<String, Long>();
+
+        /* Make sure the start/end times are within the state history, so we
+         * don't get TimeRange exceptions.
+         */
+        long startTime = checkStartTime(start);
+        long endTime = checkEndTime(end);
+
+        try {
+            /* Get the list of quarks, one for each even type in the database */
+            int quark = stats.getQuarkAbsolute(Attributes.EVENT_TYPES);
+            List<Integer> quarks = stats.getSubAttributes(quark, false);
+
+            /*
+             * Get the complete states (in our case, event counts) at the start
+             * time and end time of the requested time range.
+             */
+            List<ITmfStateInterval> startState = stats.queryFullState(startTime);
+            List<ITmfStateInterval> endState = stats.queryFullState(endTime);
+
+            /* Save the relevant information in the map we will be returning */
+            String curEventName;
+            long countAtStart, countAtEnd, eventCount;
+            for (int typeQuark : quarks) {
+                curEventName = stats.getAttributeName(typeQuark);
+                countAtStart = startState.get(typeQuark).getStateValue().unboxInt();
+                countAtEnd = endState.get(typeQuark).getStateValue().unboxInt();
+
+                /*
+                 * The default value for the statistics is 0, rather than the
+                 * value -1 used by the state system for non-initialized state.
+                 */
+                if (startTime == stats.getStartTime() || countAtStart == -1) {
+                    countAtStart = 0;
+                }
+
+                /*
+                 * Workaround a bug in the state system where requests for the
+                 * very last state change will give -1. Send the request 1ns
+                 * before the end of the trace and add the last event to the
+                 * count.
+                 */
+                if (countAtEnd < 0) {
+                    ITmfStateInterval realInterval = stats.querySingleState(endTime - 1, typeQuark);
+                    countAtEnd = realInterval.getStateValue().unboxInt() + 1;
+                }
+
+                /*
+                 * If after this it is still at -1, it's because no event of
+                 * this type happened during the requested time range.
+                 */
+                if (countAtEnd < 0) {
+                    countAtEnd = 0;
+                }
+
+                eventCount = countAtEnd - countAtStart;
+                map.put(curEventName, eventCount);
+            }
+        } catch (TimeRangeException e) {
+            /* Assume there is no events, nothing will be put in the map. */
+        } catch (AttributeNotFoundException e) {
+            /*
+             * These other exception types would show a logic problem however,
+             * so they should not happen.
+             */
+            e.printStackTrace();
+        } catch (StateValueTypeException e) {
+            e.printStackTrace();
+        }
+        return map;
+    }
+
+    protected long checkStartTime(ITmfTimestamp startTs) {
+        long start = startTs.normalize(0, ITmfTimestamp.NANOSECOND_SCALE).getValue();
+        if (start < stats.getStartTime()) {
+            return stats.getStartTime();
+        }
+        return start;
+    }
+
+    protected long checkEndTime(ITmfTimestamp endTs) {
+        long end = endTs.normalize(0, ITmfTimestamp.NANOSECOND_SCALE).getValue();
+        if (end > stats.getCurrentEndTime()) {
+            return stats.getCurrentEndTime();
+        }
+        return end;
+    }
+
+
+    /**
+     * The attribute names that are used in the state provider
+     */
+    public static class Attributes {
+
+        /** Total nb of events */
+        public static final String TOTAL = "total"; //$NON-NLS-1$
+
+        /** event_types */
+        public static final String EVENT_TYPES = "event_types"; //$NON-NLS-1$<
+    }
+}
diff --git a/org.eclipse.linuxtools.tmf.core/src/org/eclipse/linuxtools/tmf/core/statistics/TmfStatistics.java b/org.eclipse.linuxtools.tmf.core/src/org/eclipse/linuxtools/tmf/core/statistics/TmfStatistics.java
deleted file mode 100644 (file)
index dcfd93b..0000000
+++ /dev/null
@@ -1,275 +0,0 @@
-/*******************************************************************************
- * 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:
- *   Alexandre Montplaisir - Initial API and implementation
- ******************************************************************************/
-
-package org.eclipse.linuxtools.tmf.core.statistics;
-
-import java.io.File;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-
-import org.eclipse.core.resources.IResource;
-import org.eclipse.core.runtime.CoreException;
-import org.eclipse.linuxtools.tmf.core.TmfCommonConstants;
-import org.eclipse.linuxtools.tmf.core.event.ITmfTimestamp;
-import org.eclipse.linuxtools.tmf.core.exceptions.AttributeNotFoundException;
-import org.eclipse.linuxtools.tmf.core.exceptions.StateValueTypeException;
-import org.eclipse.linuxtools.tmf.core.exceptions.TimeRangeException;
-import org.eclipse.linuxtools.tmf.core.exceptions.TmfTraceException;
-import org.eclipse.linuxtools.tmf.core.interval.ITmfStateInterval;
-import org.eclipse.linuxtools.tmf.core.statesystem.IStateChangeInput;
-import org.eclipse.linuxtools.tmf.core.statesystem.ITmfStateSystem;
-import org.eclipse.linuxtools.tmf.core.statesystem.StateSystemManager;
-import org.eclipse.linuxtools.tmf.core.trace.ITmfTrace;
-
-/**
- * Default implementation of an ITmfStatisticsProvider. It uses a state system
- * underneath to store its information.
- *
- * @author Alexandre Montplaisir
- * @since 2.0
- */
-
-public class TmfStatistics  implements ITmfStatistics {
-
-    /** ID for the statistics state system */
-    public static final String STATE_ID = "org.eclipse.linuxtools.tmf.statistics"; //$NON-NLS-1$
-
-    /* Filename the "statistics state history" file will have */
-    private static final String STATS_STATE_FILENAME = "statistics.ht"; //$NON-NLS-1$
-
-    /*
-     * The state system that's used to stored the statistics. It's hidden from
-     * the trace, so that it doesn't conflict with ITmfTrace.getStateSystem()
-     * (which is something else!)
-     */
-    private final ITmfStateSystem stats;
-
-    /**
-     * Empty constructor. The resulting TmfStatistics object will not be usable,
-     * but it might be needed for sub-classes.
-     */
-    public TmfStatistics() {
-        stats = null;
-    }
-
-    /**
-     * Constructor
-     *
-     * @param trace
-     *            The trace for which we build these statistics
-     * @throws TmfTraceException
-     *             If something went wrong trying to initialize the statistics
-     */
-    public TmfStatistics(ITmfTrace trace) throws TmfTraceException {
-        /* Set up the path to the history tree file we'll use */
-        IResource resource = trace.getResource();
-        String supplDirectory = null;
-
-        try {
-            // get the directory where the history file will be stored.
-            supplDirectory = resource.getPersistentProperty(TmfCommonConstants.TRACE_SUPPLEMENTARY_FOLDER);
-        } catch (CoreException e) {
-            throw new TmfTraceException(e.toString(), e);
-        }
-
-        final File htFile = new File(supplDirectory + File.separator + STATS_STATE_FILENAME);
-        final IStateChangeInput htInput = new StatsStateProvider(trace);
-
-        this.stats = StateSystemManager.loadStateHistory(htFile, htInput, STATE_ID, false);
-    }
-
-    // ------------------------------------------------------------------------
-    // ITmfStatisticsProvider
-    // ------------------------------------------------------------------------
-
-    @Override
-    public long getEventsTotal() {
-        long start = stats.getStartTime();
-        long end = stats.getCurrentEndTime();
-        int countAtStart = 0, countAtEnd = 0;
-
-        try {
-            final int quark = stats.getQuarkAbsolute(Attributes.TOTAL);
-            countAtStart = stats.querySingleState(start, quark).getStateValue().unboxInt();
-            countAtEnd = stats.querySingleState(end, quark).getStateValue().unboxInt();
-        } catch (AttributeNotFoundException e) {
-            e.printStackTrace();
-        } catch (StateValueTypeException e) {
-            e.printStackTrace();
-        } catch (TimeRangeException e) {
-            /* Should not happen, we're clamped to the start and end times */
-            e.printStackTrace();
-        }
-
-        long total = countAtEnd - countAtStart;
-        return total;
-    }
-
-    @Override
-    public Map<String, Long> getEventTypesTotal() {
-        Map<String, Long> map = new HashMap<String, Long>();
-        long endTime = stats.getCurrentEndTime(); //shouldn't need to check it...
-
-        try {
-            /* Get the list of quarks, one for each even type in the database */
-            int quark = stats.getQuarkAbsolute(Attributes.EVENT_TYPES);
-            List<Integer> quarks = stats.getSubAttributes(quark, false);
-
-            /* Since we want the total we can look only at the end */
-            List<ITmfStateInterval> endState = stats.queryFullState(endTime);
-
-            String curEventName;
-            long eventCount;
-            for (int typeQuark : quarks) {
-                curEventName = stats.getAttributeName(typeQuark);
-                eventCount = endState.get(typeQuark).getStateValue().unboxInt();
-                map.put(curEventName, eventCount);
-            }
-
-        } catch (TimeRangeException e) {
-            /* Ignore silently */
-        } catch (AttributeNotFoundException e) {
-            e.printStackTrace();
-        } catch (StateValueTypeException e) {
-            e.printStackTrace();
-        }
-        return map;
-    }
-
-    @Override
-    public long getEventsInRange(ITmfTimestamp start, ITmfTimestamp end) {
-        int countAtStart = 0, countAtEnd = 0;
-        long startTimestamp = checkStartTime(start.getValue());
-        long endTimestamp = checkEndTime(end.getValue());
-
-        try {
-            final int quark = stats.getQuarkAbsolute(Attributes.TOTAL);
-            countAtStart = stats.querySingleState(startTimestamp, quark).getStateValue().unboxInt();
-            countAtEnd = stats.querySingleState(endTimestamp, quark).getStateValue().unboxInt();
-        } catch (AttributeNotFoundException e) {
-            e.printStackTrace();
-        } catch (StateValueTypeException e) {
-            e.printStackTrace();
-        } catch (TimeRangeException e) {
-            /* Should not happen, we're clamped to the start and end times */
-            e.printStackTrace();
-        }
-
-        long total = countAtEnd - countAtStart;
-        return total;
-    }
-
-    @Override
-    public Map<String, Long> getEventTypesInRange(ITmfTimestamp start, ITmfTimestamp end) {
-        Map<String, Long> map = new HashMap<String, Long>();
-
-        /* Make sure the start/end times are within the state history, so we
-         * don't get TimeRange exceptions.
-         */
-        long startTimestamp = checkStartTime(start.getValue());
-        long endTimestamp = checkEndTime(end.getValue());
-
-        try {
-            /* Get the list of quarks, one for each even type in the database */
-            int quark = stats.getQuarkAbsolute(Attributes.EVENT_TYPES);
-            List<Integer> quarks = stats.getSubAttributes(quark, false);
-
-            /*
-             * Get the complete states (in our case, event counts) at the start
-             * time and end time of the requested time range.
-             */
-            List<ITmfStateInterval> startState = stats.queryFullState(startTimestamp);
-            List<ITmfStateInterval> endState = stats.queryFullState(endTimestamp);
-
-            /* Save the relevant information in the map we will be returning */
-            String curEventName;
-            long countAtStart, countAtEnd, eventCount;
-            for (int typeQuark : quarks) {
-                curEventName = stats.getAttributeName(typeQuark);
-                countAtStart = startState.get(typeQuark).getStateValue().unboxInt();
-                countAtEnd = endState.get(typeQuark).getStateValue().unboxInt();
-
-                /*
-                 * The default value for the statistics is 0, rather than the
-                 * value -1 used by the state system for non-initialized state.
-                 */
-                if (startTimestamp == stats.getStartTime() || countAtStart == -1) {
-                    countAtStart = 0;
-                }
-
-                /*
-                 * Workaround a bug in the state system where requests for the
-                 * very last state change will give -1. Send the request 1ns
-                 * before the end of the trace and add the last event to the
-                 * count.
-                 */
-                if (countAtEnd < 0) {
-                    ITmfStateInterval realInterval = stats.querySingleState(endTimestamp - 1, typeQuark);
-                    countAtEnd = realInterval.getStateValue().unboxInt() + 1;
-                }
-
-                /*
-                 * If after this it is still at -1, it's because no event of
-                 * this type happened during the requested time range.
-                 */
-                if (countAtEnd < 0) {
-                    countAtEnd = 0;
-                }
-
-                eventCount = countAtEnd - countAtStart;
-                map.put(curEventName, eventCount);
-            }
-        } catch (TimeRangeException e) {
-            /*
-             * If a request is made for an invalid time range, we will ignore it
-             * silently and not add any information to the map.
-             */
-        } catch (AttributeNotFoundException e) {
-            /*
-             * These other exceptions would show a logic problem however, so
-             * they should not happen.
-             */
-            e.printStackTrace();
-        } catch (StateValueTypeException e) {
-            e.printStackTrace();
-        }
-        return map;
-    }
-
-    protected long checkStartTime(long start) {
-        if (start < stats.getStartTime()) {
-            return stats.getStartTime();
-        }
-        return start;
-    }
-
-    protected long checkEndTime(long end) {
-        if (end > stats.getCurrentEndTime()) {
-            return stats.getCurrentEndTime();
-        }
-        return end;
-    }
-
-
-    /**
-     * The attribute names that are used in the state provider
-     */
-    public static class Attributes {
-
-        /** Total nb of events */
-        public static final String TOTAL = "total"; //$NON-NLS-1$
-
-        /** event_types */
-        public static final String EVENT_TYPES = "event_types"; //$NON-NLS-1$<
-    }
-}
index 1c29a40d63d026e87bcc0a8412b39dcd66ac09c6..803590e6a0f49659963b112a68690ec09c8dfd1d 100644 (file)
@@ -27,7 +27,7 @@ import org.eclipse.linuxtools.tmf.core.request.ITmfDataRequest;
 import org.eclipse.linuxtools.tmf.core.request.ITmfEventRequest;
 import org.eclipse.linuxtools.tmf.core.statesystem.ITmfStateSystem;
 import org.eclipse.linuxtools.tmf.core.statistics.ITmfStatistics;
-import org.eclipse.linuxtools.tmf.core.statistics.TmfStatistics;
+import org.eclipse.linuxtools.tmf.core.statistics.TmfStateStatistics;
 
 /**
  * Abstract implementation of ITmfTrace.
@@ -262,7 +262,7 @@ public abstract class TmfTrace extends TmfEventProvider implements ITmfTrace {
          * Initialize the statistics provider, but only if a Resource has been
          * set (so we don't build it for experiments, for unit tests, etc.)
          */
-        fStatistics = (fResource == null ? null : new TmfStatistics(this) );
+        fStatistics = (fResource == null ? null : new TmfStateStatistics(this) );
     }
 
     /**
index 031850df744d378d99787b95f360966dcb040279..c966c00d9d23ee8acd5b8d8986f0d85d6082023e 100644 (file)
@@ -29,8 +29,9 @@ import org.eclipse.linuxtools.tmf.core.signal.TmfExperimentRangeUpdatedSignal;
 import org.eclipse.linuxtools.tmf.core.signal.TmfRangeSynchSignal;
 import org.eclipse.linuxtools.tmf.core.signal.TmfSignalHandler;
 import org.eclipse.linuxtools.tmf.core.signal.TmfStateSystemBuildCompleted;
+import org.eclipse.linuxtools.tmf.core.signal.TmfStatsUpdatedSignal;
 import org.eclipse.linuxtools.tmf.core.statistics.ITmfStatistics;
-import org.eclipse.linuxtools.tmf.core.statistics.TmfStatistics;
+import org.eclipse.linuxtools.tmf.core.statistics.TmfStateStatistics;
 import org.eclipse.linuxtools.tmf.core.trace.ITmfTrace;
 import org.eclipse.linuxtools.tmf.core.trace.TmfExperiment;
 import org.eclipse.linuxtools.tmf.ui.viewers.TmfViewer;
@@ -227,20 +228,9 @@ public class TmfStatisticsViewer extends TmfViewer {
         TmfStatisticsTreeManager.removeStatTreeRoot(getTreeID());
     }
 
-    /**
-     * Handler for the state system build completed signal
-     *
-     * @param signal
-     *            The signal that's received
-     */
-    @TmfSignalHandler
-    public void stateSystemBuildCompleted(final TmfStateSystemBuildCompleted signal) {
-        if (isListeningTo(signal.getTrace().getName()) && signal.getID().equals(TmfStatistics.STATE_ID)) {
-            TmfExperiment experiment = TmfExperiment.getCurrentExperiment();
-            requestData(experiment, experiment.getTimeRange());
-            requestTimeRangeData(experiment, fRequestedTimerange);
-        }
-    }
+    // ------------------------------------------------------------------------
+    // Signal handlers
+    // ------------------------------------------------------------------------
 
     /**
      * Handles the signal about new experiment range.
@@ -284,6 +274,69 @@ public class TmfStatisticsViewer extends TmfViewer {
         requestTimeRangeData(TmfExperiment.getCurrentExperiment(), signal.getCurrentRange());
     }
 
+    /**
+     * Whenever a trace's statistics back-end finishes computing the statistics
+     * for a given interval, it will send the StatsUpdated signal. This method
+     * will receive this signal and update the statistics view accordingly.
+     *
+     * @param sig
+     *            The signal that is received
+     */
+    @TmfSignalHandler
+    public void statsUpdated(TmfStatsUpdatedSignal sig) {
+        /* Only handle this signal if it's about the trace we represent. */
+        if (!isListeningTo(sig.getTrace())) {
+            return;
+        }
+
+        final TmfStatisticsTree statsData = TmfStatisticsTreeManager.getStatTree(getTreeID());
+        Map<String, Long> map = sig.getEventsPerType();
+        String name = sig.getTrace().getName();
+        boolean isGlobal = sig.isGlobal();
+
+        /*
+         * "Global", "partial", "total", etc., it's all very confusing...
+         *
+         * The base view shows the total count for the trace and for
+         * each even types, organized in columns like this:
+         *
+         *                   |  Global  |  Time range |
+         * trace name        |    A     |      B      |
+         *    Event Type     |          |             |
+         *       <event 1>   |    C     |      D      |
+         *       <event 2>   |   ...    |     ...     |
+         *         ...       |          |             |
+         *
+         * Here, we called the cells like this:
+         *  A : GlobalTotal
+         *  B : TimeRangeTotal
+         *  C : GlobalTypeCount(s)
+         *  D : TimeRangeTypeCount(s)
+         */
+
+        /* Fill in an the event counts (either cells C or D) */
+        for (Map.Entry<String, Long> entry : map.entrySet()) {
+            statsData.setTypeCount(name, entry.getKey(), isGlobal, entry.getValue());
+        }
+
+        /*
+         * Calculate the totals (cell A or B, depending if isGlobal). We will
+         * use the results of the previous request instead of sending another
+         * one.
+         */
+        long globalTotal = 0;
+        for (long val : map.values()) {
+            globalTotal += val;
+        }
+        statsData.setTotal(name, isGlobal, globalTotal);
+
+        modelComplete(isGlobal);
+    }
+
+    // ------------------------------------------------------------------------
+    // Class methods
+    // ------------------------------------------------------------------------
+
     /*
      * Returns the primary control associated with this viewer.
      *
@@ -569,12 +622,12 @@ public class TmfStatisticsViewer extends TmfViewer {
     /**
      * Tells if the viewer is listening to a trace from the selected experiment.
      *
-     * @param traceName
+     * @param trace
      *            The trace that the viewer may be listening
      * @return true if the viewer is listening to the trace, false otherwise
      */
-    protected boolean isListeningTo(String traceName) {
-        if (fProcessAll || traceName.equals(fTrace.getName())) {
+    protected boolean isListeningTo(ITmfTrace trace) {
+        if (fProcessAll || trace == fTrace) {
             return true;
         }
         return false;
@@ -626,13 +679,7 @@ public class TmfStatisticsViewer extends TmfViewer {
      *            The range to request to the experiment
      */
     protected void requestData(final TmfExperiment experiment, final TmfTimeRange timeRange) {
-        final Thread thread = new Thread("Statistics view build") { //$NON-NLS-1$
-            @Override
-            public void run() {
-                buildStatisticsTree(experiment, timeRange, true);
-            }
-        };
-        thread.start();
+        buildStatisticsTree(experiment, timeRange, true);
     }
 
     /**
@@ -645,14 +692,7 @@ public class TmfStatisticsViewer extends TmfViewer {
      */
     protected void requestTimeRangeData(final TmfExperiment experiment, final TmfTimeRange timeRange) {
         fRequestedTimerange = timeRange;
-
-        final Thread thread = new Thread("Statistics view build") { //$NON-NLS-1$
-            @Override
-            public void run() {
-                buildStatisticsTree(experiment, timeRange, false);
-            }
-        };
-        thread.start();
+        buildStatisticsTree(experiment, timeRange, false);
     }
 
     /**
@@ -690,7 +730,7 @@ public class TmfStatisticsViewer extends TmfViewer {
              * listening to multiple traces.
              */
             for (final ITmfTrace trace : experiment.getTraces()) {
-                if (!isListeningTo(trace.getName())) {
+                if (!isListeningTo(trace)) {
                     continue;
                 }
 
@@ -698,82 +738,27 @@ public class TmfStatisticsViewer extends TmfViewer {
                 final ITmfStatistics stats = trace.getStatistics();
                 if (stats == null) {
                     /*
-                     * The state system is not accessible yet for this trace.
-                     * Try the next one.
+                     * The statistics provider for this trace is not accessible
+                     * (yet?). Try the next one.
                      */
                     continue;
                 }
 
-                updateValues(statsData, trace, timeRange, isGlobal);
+                /* The generic statistics are stored in nanoseconds, so we must make
+                 * sure the time range is scaled correctly. */
+                ITmfTimestamp start = timeRange.getStartTime().normalize(0, TIME_SCALE);
+                ITmfTimestamp end = timeRange.getEndTime().normalize(0, TIME_SCALE);
 
-                modelComplete(isGlobal);
+                /*
+                 * Send a request to update the statistics view. The result will
+                 * be sent through a {@link TmfStatsUpdatedSignal}, and will be
+                 * processed by the signal handler.
+                 */
+                trace.getStatistics().updateStats(isGlobal, start, end);
             }
         }
     }
 
-    /**
-     * Update the statistics values. It can be extended by subclasses if they
-     * want to show something other than the base information in their viewer.
-     * They can decide to show the base information too, by calling
-     * super.updateValues() or not.
-     *
-     * @param statsData
-     *            The statistics tree we are updating
-     * @param trace
-     *            The trace related to these statistics
-     * @param timeRange
-     *            The time range for which we are updating. For updates to the
-     *            global data this should be the whole (available) time range of
-     *            the trace.
-     * @param isGlobal
-     *            Are we updating the Global data (for the complete time range
-     *            of the trace), or the selected time range data?
-     */
-    protected void updateValues(TmfStatisticsTree statsData, ITmfTrace trace,
-            TmfTimeRange timeRange, boolean isGlobal) {
-        ITmfStatistics stats = trace.getStatistics();
-
-        /*
-         * "Global", "partial", "total", etc., it's all very confusing...
-         *
-         * The base view shows the total count for the trace and for
-         * each even types, organized in columns like this:
-         *
-         *                   |  Global  |  Time range |
-         * trace name        |    A     |      B      |
-         *    Event Type     |          |             |
-         *       <event 1>   |    C     |      D      |
-         *       <event 2>   |   ...    |     ...     |
-         *         ...       |          |             |
-         *
-         * Here, we called the cells like this:
-         *  A : GlobalTotal
-         *  B : TimeRangeTotal
-         *  C : GlobalTypeCount(s)
-         *  D : TimeRangeTypeCount(s)
-         */
-
-        /* The generic statistics are stored in nanoseconds, so we must make
-         * sure the time range is scaled correctly. */
-        ITmfTimestamp start = timeRange.getStartTime().normalize(0, TIME_SCALE);
-        ITmfTimestamp end = timeRange.getEndTime().normalize(0, TIME_SCALE);
-        String name = trace.getName();
-
-        /*
-         * Fill in the Total row (cell A or B, depending if isGlobal)
-         * (we can still use .getEventsInRange(), even if it's global,
-         * start and end will cover the whole trace)
-         */
-        long globalTotal = stats.getEventsInRange(start, end);
-        statsData.setTotal(name, isGlobal, globalTotal);
-
-        /* Fill in an the event counts (either cells C or D) */
-        Map<String, Long> map = stats.getEventTypesInRange(start, end);
-        for (Map.Entry<String, Long> entry : map.entrySet()) {
-            statsData.setTypeCount(name, entry.getKey(), isGlobal, entry.getValue());
-        }
-    }
-
     /**
      * Resets the number of events within the time range
      */
This page took 0.038399 seconds and 5 git commands to generate.