tmf.xml: Add support for consuming event in the fsm
authorJean-Christian Kouame <jean-christian.kouame@ericsson.com>
Fri, 29 Jul 2016 17:58:03 +0000 (13:58 -0400)
committerJean-Christian Kouame <jean-christian.kouame@ericsson.com>
Wed, 24 Aug 2016 15:41:01 +0000 (11:41 -0400)
This patch adds the possibility for an fsm to be consuming. A consuming
fsm can use an ongoing event for only one of its scenario.

Change-Id: Iaa2a883ef212019c1ef87811722ee863c36567f7
Signed-off-by: Jean-Christian Kouame <jean-christian.kouame@ericsson.com>
Reviewed-on: https://git.eclipse.org/r/78189
Reviewed-by: Hudson CI
Reviewed-by: Bernd Hufmann <bernd.hufmann@ericsson.com>
Tested-by: Bernd Hufmann <bernd.hufmann@ericsson.com>
tmf/org.eclipse.tracecompass.tmf.analysis.xml.core.tests/common/org/eclipse/tracecompass/tmf/analysis/xml/core/tests/common/TmfXmlTestFiles.java
tmf/org.eclipse.tracecompass.tmf.analysis.xml.core.tests/src/org/eclipse/tracecompass/tmf/analysis/xml/core/tests/module/XmlUtilsTest.java
tmf/org.eclipse.tracecompass.tmf.analysis.xml.core.tests/src/org/eclipse/tracecompass/tmf/analysis/xml/core/tests/stateprovider/ConsumingFsmTest.java [new file with mode: 0644]
tmf/org.eclipse.tracecompass.tmf.analysis.xml.core.tests/test_traces/testTrace5.xml [new file with mode: 0644]
tmf/org.eclipse.tracecompass.tmf.analysis.xml.core.tests/test_xml_files/test_valid/test_consuming_fsm.xml [new file with mode: 0644]
tmf/org.eclipse.tracecompass.tmf.analysis.xml.core/src/org/eclipse/tracecompass/internal/tmf/analysis/xml/core/model/TmfXmlFsm.java
tmf/org.eclipse.tracecompass.tmf.analysis.xml.core/src/org/eclipse/tracecompass/internal/tmf/analysis/xml/core/model/TmfXmlScenario.java
tmf/org.eclipse.tracecompass.tmf.analysis.xml.core/src/org/eclipse/tracecompass/internal/tmf/analysis/xml/core/module/xmlPatternStateProvider.xsd
tmf/org.eclipse.tracecompass.tmf.analysis.xml.core/src/org/eclipse/tracecompass/internal/tmf/analysis/xml/core/stateprovider/TmfXmlStrings.java

index ef4b538a877323d1e5920ec4644475b6e66ad76c..e2c7ca6fdf3114d9d86bcfe1702b4e8361616483 100644 (file)
@@ -47,7 +47,9 @@ public enum TmfXmlTestFiles {
     /** A valid file for pattern tests */
     VALID_PATTERN_FILE("test_xml_files/test_valid/test_valid_pattern.xml"),
     /** A valid pattern file to test the pattern segment **/
-    VALID_PATTERN_SEGMENT("test_xml_files/test_valid/test_pattern_segment.xml");
+    VALID_PATTERN_SEGMENT("test_xml_files/test_valid/test_pattern_segment.xml"),
+    /** A valid file for consuming fsm test */
+    CONSUMING_FSM_TEST("test_xml_files/test_valid/test_consuming_fsm.xml");
 
     private final String fPath;
 
index e57794c3fbf952cef223fa9bd4e90cf04ca62df5..ab163ae6f44380fe3b9f2a1e7821683e0a29f367 100644 (file)
@@ -31,6 +31,7 @@ import org.eclipse.core.runtime.Path;
 import org.eclipse.jdt.annotation.NonNull;
 import org.eclipse.jdt.annotation.Nullable;
 import org.eclipse.tracecompass.internal.tmf.analysis.xml.core.module.XmlUtils;
+import org.eclipse.tracecompass.internal.tmf.analysis.xml.core.pattern.stateprovider.XmlPatternAnalysis;
 import org.eclipse.tracecompass.internal.tmf.analysis.xml.core.segment.TmfXmlPatternSegment;
 import org.eclipse.tracecompass.internal.tmf.analysis.xml.core.stateprovider.TmfXmlStrings;
 import org.eclipse.tracecompass.internal.tmf.analysis.xml.core.stateprovider.XmlStateSystemModule;
@@ -261,6 +262,34 @@ public class XmlUtilsTest {
         return module;
     }
 
+    /**
+     * Initialize a new pattern analysis using the xml file
+     *
+     * @param xmlAnalysisFile
+     *            The xml file used to initialize the pattern analysis
+     * @return The pattern analysis
+     */
+    public static @NonNull XmlPatternAnalysis initializePatternModule(TmfXmlTestFiles xmlAnalysisFile) {
+
+        /* Initialize the state provider module */
+        Document doc = xmlAnalysisFile.getXmlDocument();
+        assertNotNull(doc);
+
+        /* get State Providers modules */
+        NodeList patternNodes = doc.getElementsByTagName(TmfXmlStrings.PATTERN);
+        assertFalse(patternNodes.getLength() == 0);
+
+        Element node = (Element) patternNodes.item(0);
+        XmlPatternAnalysis analysis = new XmlPatternAnalysis();
+        String moduleId = node.getAttribute(TmfXmlStrings.ID);
+        assertNotNull(moduleId);
+        analysis.setId(moduleId);
+
+        analysis.setXmlFile(xmlAnalysisFile.getPath());
+
+        return analysis;
+    }
+
     /**
      * This function test the data provided by the state intervals queried
      *
diff --git a/tmf/org.eclipse.tracecompass.tmf.analysis.xml.core.tests/src/org/eclipse/tracecompass/tmf/analysis/xml/core/tests/stateprovider/ConsumingFsmTest.java b/tmf/org.eclipse.tracecompass.tmf.analysis.xml.core.tests/src/org/eclipse/tracecompass/tmf/analysis/xml/core/tests/stateprovider/ConsumingFsmTest.java
new file mode 100644 (file)
index 0000000..a340c95
--- /dev/null
@@ -0,0 +1,120 @@
+/*******************************************************************************
+ * Copyright (c) 2016 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
+ *******************************************************************************/
+
+package org.eclipse.tracecompass.tmf.analysis.xml.core.tests.stateprovider;
+
+import static org.junit.Assert.assertNotNull;
+
+import org.eclipse.jdt.annotation.NonNull;
+import org.eclipse.tracecompass.internal.tmf.analysis.xml.core.pattern.stateprovider.XmlPatternAnalysis;
+import org.eclipse.tracecompass.statesystem.core.ITmfStateSystem;
+import org.eclipse.tracecompass.statesystem.core.exceptions.AttributeNotFoundException;
+import org.eclipse.tracecompass.statesystem.core.exceptions.StateSystemDisposedException;
+import org.eclipse.tracecompass.statesystem.core.statevalue.ITmfStateValue;
+import org.eclipse.tracecompass.statesystem.core.statevalue.TmfStateValue;
+import org.eclipse.tracecompass.tmf.analysis.xml.core.tests.common.TmfXmlTestFiles;
+import org.eclipse.tracecompass.tmf.analysis.xml.core.tests.module.XmlUtilsTest;
+import org.eclipse.tracecompass.tmf.core.exceptions.TmfAnalysisException;
+import org.eclipse.tracecompass.tmf.core.trace.ITmfTrace;
+import org.junit.After;
+import org.junit.Before;
+import org.junit.Test;
+
+/**
+ * Test the consuming state of an fsm. This test creates a pattern with two fsm.
+ * One is consuming, the other is not. Each fsm will create three scenarios. We
+ * use a counter to verify if an event was consumed or not.
+ *
+ * @author Jean-Christian Kouame
+ */
+public class ConsumingFsmTest {
+
+    private static final @NonNull String TEST_TRACE = "test_traces/testTrace5.xml";
+
+    ITmfTrace fTrace;
+    XmlPatternAnalysis fModule;
+
+    /**
+     * Initializes the trace and the module for the tests
+     *
+     * @throws TmfAnalysisException
+     *             Any exception thrown during module initialization
+     */
+    @Before
+    public void setUp() throws TmfAnalysisException {
+        ITmfTrace trace = XmlUtilsTest.initializeTrace(TEST_TRACE);
+        @NonNull XmlPatternAnalysis module = XmlUtilsTest.initializePatternModule(TmfXmlTestFiles.CONSUMING_FSM_TEST);
+
+        module.setTrace(trace);
+
+        module.schedule();
+        module.waitForCompletion();
+
+        fTrace = trace;
+        fModule = module;
+    }
+
+    /**
+     * Dispose the module and the trace
+     */
+    @After
+    public void cleanUp() {
+        fTrace.dispose();
+        fModule.dispose();
+    }
+
+    /**
+     * Test the consuming fsm counter
+     *
+     * @throws StateSystemDisposedException
+     *             Exceptions thrown during state system verification
+     * @throws AttributeNotFoundException
+     *             Exceptions thrown during state system verification
+     */
+    @Test
+    public void testConsumingFsm() throws AttributeNotFoundException, StateSystemDisposedException {
+        XmlPatternAnalysis module = fModule;
+        assertNotNull(module);
+
+        ITmfStateSystem ss = module.getStateSystem(module.getId());
+        assertNotNull(ss);
+
+        int quark = ss.getQuarkAbsolute("consuming");
+
+        final int[] expectedStarts = { 1, 7, 7 };
+        ITmfStateValue[] expectedValues = { TmfStateValue.nullValue(), TmfStateValue.newValueLong(1l)};
+        XmlUtilsTest.verifyStateIntervals("testConsuming", ss, quark, expectedStarts, expectedValues);
+
+    }
+
+    /**
+     * Test the non consuming fsm counter
+     *
+     * @throws StateSystemDisposedException
+     *             Exceptions thrown during state system verification
+     * @throws AttributeNotFoundException
+     *             Exceptions thrown during state system verification
+     */
+    @Test
+    public void testNonConsumingFsm() throws AttributeNotFoundException, StateSystemDisposedException {
+        XmlPatternAnalysis module = fModule;
+        assertNotNull(module);
+
+        ITmfStateSystem ss = module.getStateSystem(module.getId());
+        assertNotNull(ss);
+
+        int quark = ss.getQuarkAbsolute("non_consuming");
+
+        final int[] expectedStarts = { 1, 7, 7 };
+        ITmfStateValue[] expectedValues = { TmfStateValue.nullValue(), TmfStateValue.newValueLong(3l)};
+        XmlUtilsTest.verifyStateIntervals("testNonConsuming", ss, quark, expectedStarts, expectedValues);
+
+    }
+}
+
diff --git a/tmf/org.eclipse.tracecompass.tmf.analysis.xml.core.tests/test_traces/testTrace5.xml b/tmf/org.eclipse.tracecompass.tmf.analysis.xml.core.tests/test_traces/testTrace5.xml
new file mode 100644 (file)
index 0000000..066e492
--- /dev/null
@@ -0,0 +1,22 @@
+<!-- ***************************************************************************
+* Copyright (c) 2014 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
+*************************************************************************** -->
+<trace>
+<event timestamp="1" name="entry" source="0">
+<field name="cpu" type="int" value="0" />
+</event>
+<event timestamp="3" name="entry" source="0">
+<field name="cpu" type="int" value="0" />
+</event>
+<event timestamp="5" name="entry" source="0">
+<field name="cpu" type="int" value="0" />
+</event>
+<event timestamp="7" name="exit" source="0">
+<field name="cpu" type="int" value="0" />
+</event>
+</trace>
\ No newline at end of file
diff --git a/tmf/org.eclipse.tracecompass.tmf.analysis.xml.core.tests/test_xml_files/test_valid/test_consuming_fsm.xml b/tmf/org.eclipse.tracecompass.tmf.analysis.xml.core.tests/test_xml_files/test_valid/test_consuming_fsm.xml
new file mode 100644 (file)
index 0000000..498875a
--- /dev/null
@@ -0,0 +1,49 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<tmfxml xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+       xsi:noNamespaceSchemaLocation="xmlDefinition.xsd">
+<!-- ***************************************************************************
+* Copyright (c) 2016 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
+*************************************************************************** -->
+<pattern version="0" id="syscall.analysis">
+       <patternHandler>
+               <action id="increment_counter_consuming">
+                       <stateChange>
+                               <stateAttribute type="constant" value="consuming" />
+                               <stateValue increment="true" type="long" value="1"/>
+                       </stateChange>
+               </action>
+
+               <fsm id="consuming">
+                       <state id="start">
+                               <transition event="entry" target="exit_state"/>
+                       </state>
+                       <state id="exit_state" >
+                               <transition event="exit" target="end" action="increment_counter_consuming"/>
+                       </state>
+                       <final id="end"/>
+               </fsm>
+
+               <action id="increment_counter_non_consuming">
+                       <stateChange>
+                               <stateAttribute type="constant" value="non_consuming" />
+                               <stateValue increment="true" type="long" value="1"/>
+                       </stateChange>
+               </action>
+
+               <fsm id="non_consuming" consuming="false">
+                       <state id="start">
+                               <transition event="entry" target="exit_state"/>
+                       </state>
+                       <state id="exit_state" >
+                               <transition event="exit" target="end" action="increment_counter_non_consuming"/>
+                       </state>
+                       <final id="end"/>
+               </fsm>
+       </patternHandler>
+</pattern>
+</tmfxml>
\ No newline at end of file
index 4d8bd302a27a7ea432078e75392cde615c6e161e..a6ecb57a8338fec59ddefe7e30e942393f267687 100644 (file)
@@ -48,6 +48,8 @@ public class TmfXmlFsm {
     private final String fAbandonStateId;
     private final boolean fInstanceMultipleEnabled;
     private final String fInitialStateId;
+    private final boolean fConsuming;
+    private boolean fEventConsumed;
     private int fTotalScenarios;
 
     /**
@@ -63,6 +65,7 @@ public class TmfXmlFsm {
      */
     public static TmfXmlFsm create(ITmfXmlModelFactory modelFactory, Element node, IXmlStateSystemContainer container) {
         String id = node.getAttribute(TmfXmlStrings.ID);
+        boolean consuming = node.getAttribute(TmfXmlStrings.CONSUMING).isEmpty() ? true : Boolean.parseBoolean(node.getAttribute(TmfXmlStrings.CONSUMING));
         boolean instanceMultipleEnabled = node.getAttribute(TmfXmlStrings.MULTIPLE).isEmpty() ? true : Boolean.parseBoolean(node.getAttribute(TmfXmlStrings.MULTIPLE));
         final List<@NonNull TmfXmlBasicTransition> preconditions = new ArrayList<>();
 
@@ -127,16 +130,17 @@ public class TmfXmlFsm {
                 statesMap.put(abandonState.getId(), abandonState);
             }
         }
-        return new TmfXmlFsm(modelFactory, container, id, instanceMultipleEnabled, initialState, finalStateId, abandonStateId, preconditions, statesMap);
+        return new TmfXmlFsm(modelFactory, container, id, consuming, instanceMultipleEnabled, initialState, finalStateId, abandonStateId, preconditions, statesMap);
     }
 
-    private TmfXmlFsm(ITmfXmlModelFactory modelFactory, IXmlStateSystemContainer container, String id, boolean multiple,
-            String initialState, String finalState, String abandonState, List<TmfXmlBasicTransition> preconditions,
+    private TmfXmlFsm(ITmfXmlModelFactory modelFactory, IXmlStateSystemContainer container, String id, boolean consuming,
+            boolean multiple, String initialState, String finalState, String abandonState, List<TmfXmlBasicTransition> preconditions,
             Map<String, TmfXmlState> states) {
         fModelFactory = modelFactory;
         fTotalScenarios = 0;
         fContainer = container;
         fId = id;
+        fConsuming = consuming;
         fInstanceMultipleEnabled = multiple;
         fInitialStateId = initialState;
         fFinalStateId = finalState;
@@ -191,6 +195,20 @@ public class TmfXmlFsm {
         return Collections.unmodifiableMap(fStatesMap);
     }
 
+    /**
+     * Set whether the ongoing was consumed by a scenario or not
+     *
+     * @param eventConsumed
+     *            The consumed state
+     */
+    public void setEventConsumed(boolean eventConsumed) {
+        fEventConsumed = eventConsumed;
+    }
+
+    private boolean isEventConsumed() {
+        return fEventConsumed;
+    }
+
     /**
      * Process the active event and determine the next step of this fsm
      *
@@ -252,6 +270,7 @@ public class TmfXmlFsm {
      *            The transitions of the pattern
      */
     public void handleEvent(ITmfEvent event, Map<String, TmfXmlTransitionValidator> transitionMap) {
+        setEventConsumed(false);
         if (!validatePreconditions(event, transitionMap)) {
             return;
         }
@@ -262,6 +281,9 @@ public class TmfXmlFsm {
                 currentItr.remove();
             } else {
                 handleScenario(scenario, event);
+                if (fConsuming && isEventConsumed()) {
+                    return;
+                }
             }
         }
     }
index c4b551f20a9d7c8125e9a44fa213009838f54eb3..eeea5781b608e38c15247e554e60b68cfba3bfff 100644 (file)
@@ -99,6 +99,7 @@ public class TmfXmlScenario {
             return;
         }
 
+        fFsm.setEventConsumed(true);
         // Processing the actions in the transition
         final List<String> actions = out.getAction();
         for (String actionId : actions) {
index 042fa1925db991aa3c84300abac492cee6b88aff..6b26b446c1de986bf293dbee4bac5f9e4654403f 100644 (file)
                <xs:attribute name="multiple" type="xs:boolean" use="optional" default="true">
                        <xs:annotation>
                                <xs:documentation>ONLY USE for fsm. Specifies if this FSM allows multiple instance or only one instance. If not specified, this attribute will be set to 'true' by default.</xs:documentation></xs:annotation></xs:attribute>
+               <xs:attribute name="consuming" type="xs:boolean" use="optional" default="true">
+                       <xs:annotation>
+                               <xs:documentation>ONLY USE for fsm. Specifies if this FSM is consuming or not. If the FSM is consuming the ongoing event can be used by only one scenario of the FSM, if not, the ongoing scenario can be used in one or several scenario of the FSM. If not specified, this attribute will be set to 'true' by default.</xs:documentation></xs:annotation></xs:attribute>
        </xs:complexType>
 
        <xs:complexType name="transition">
This page took 0.032471 seconds and 5 git commands to generate.