[rtems-central commit] validation: Add ability to skip action transitions
Sebastian Huber
sebh at rtems.org
Mon Jul 27 13:46:55 UTC 2020
Module: rtems-central
Branch: master
Commit: 55e17d23c133681cf4a6a24e5190216f5378f1e8
Changeset: http://git.rtems.org/rtems-central/commit/?id=55e17d23c133681cf4a6a24e5190216f5378f1e8
Author: Sebastian Huber <sebastian.huber at embedded-brains.de>
Date: Mon Jul 27 14:54:13 2020 +0200
validation: Add ability to skip action transitions
---
rtemsspec/tests/spec-validation/action2.yml | 24 +++++
rtemsspec/tests/spec-validation/directive.yml | 1 +
rtemsspec/tests/test_validation.py | 115 ++++++++++++++---------
rtemsspec/validation.py | 24 ++++-
spec/req/rtems/ident-local.yml | 1 +
spec/req/rtems/ident.yml | 1 +
spec/req/rtems/tasks/ident.yml | 1 +
spec/spec/requirement-action-skip-reasons.yml | 27 ++++++
spec/spec/requirement-action-transition-post.yml | 10 ++
spec/spec/requirement-action.yml | 4 +
10 files changed, 160 insertions(+), 48 deletions(-)
diff --git a/rtemsspec/tests/spec-validation/action2.yml b/rtemsspec/tests/spec-validation/action2.yml
index a2a2334..a2b852e 100644
--- a/rtemsspec/tests/spec-validation/action2.yml
+++ b/rtemsspec/tests/spec-validation/action2.yml
@@ -66,11 +66,19 @@ pre-conditions:
/* Pre B Y */
text: |
Pre B Y.
+ - name: Z
+ test-code: |
+ /* Pre B Z */
+ text: |
+ Pre B Z.
test-epilogue: |
/* Pre B epilogue. */
test-prologue: |
/* Pre B prologue. */
requirement-type: functional
+skip-reasons:
+ SkipReason: |
+ Skip it due to some reason.
test-action: |
/* Action */
test-brief: |
@@ -148,6 +156,22 @@ transition-map:
A: N/A
B:
- Y
+- enabled-by: true
+ post-conditions:
+ A: X
+ B: X
+ pre-conditions:
+ A:
+ - X
+ B:
+ - Z
+- enabled-by: true
+ post-conditions: SkipReason
+ pre-conditions:
+ A:
+ - Y
+ B:
+ - Z
rationale: null
references: []
text: |
diff --git a/rtemsspec/tests/spec-validation/directive.yml b/rtemsspec/tests/spec-validation/directive.yml
index e8842fe..2c8c20f 100644
--- a/rtemsspec/tests/spec-validation/directive.yml
+++ b/rtemsspec/tests/spec-validation/directive.yml
@@ -152,6 +152,7 @@ pre-conditions:
test-epilogue: null
test-prologue: null
requirement-type: functional
+skip-reasons: {}
test-action: |
ctx->status = rtems_task_ident( ctx->name, ctx->node, ctx->id );
test-brief: Test rtems_task_ident() brief description.
diff --git a/rtemsspec/tests/test_validation.py b/rtemsspec/tests/test_validation.py
index c9c4a9d..459f7cc 100644
--- a/rtemsspec/tests/test_validation.py
+++ b/rtemsspec/tests/test_validation.py
@@ -635,90 +635,91 @@ static const uint8_t ClassicTaskIdentification_TransitionMap[][ 2 ] = {
};
static const struct {
+ uint8_t Skip : 1;
uint8_t Pre_Name_NA : 1;
uint8_t Pre_Node_NA : 1;
uint8_t Pre_Id_NA : 1;
} ClassicTaskIdentification_TransitionInfo[] = {
{
- 0, 0, 0
+ 0, 0, 0, 0
}, {
- 0, 0, 0
+ 0, 0, 0, 0
}, {
- 0, 0, 0
+ 0, 0, 0, 0
}, {
- 0, 0, 0
+ 0, 0, 0, 0
}, {
- 0, 0, 0
+ 0, 0, 0, 0
}, {
- 0, 0, 0
+ 0, 0, 0, 0
}, {
- 0, 0, 0
+ 0, 0, 0, 0
}, {
- 0, 0, 0
+ 0, 0, 0, 0
}, {
- 0, 0, 0
+ 0, 0, 0, 0
}, {
- 0, 0, 0
+ 0, 0, 0, 0
}, {
- 0, 0, 0
+ 0, 0, 0, 0
}, {
- 0, 0, 0
+ 0, 0, 0, 0
}, {
- 0, 0, 0
+ 0, 0, 0, 0
}, {
- 0, 0, 0
+ 0, 0, 0, 0
}, {
- 0, 0, 0
+ 0, 0, 0, 0
}, {
- 0, 0, 0
+ 0, 0, 0, 0
}, {
- 0, 0, 0
+ 0, 0, 0, 0
}, {
- 0, 0, 0
+ 0, 0, 0, 0
}, {
- 0, 0, 0
+ 0, 0, 0, 0
}, {
- 0, 0, 0
+ 0, 0, 0, 0
}, {
- 0, 0, 0
+ 0, 0, 0, 0
}, {
- 0, 0, 0
+ 0, 0, 0, 0
}, {
- 0, 0, 0
+ 0, 0, 0, 0
}, {
- 0, 0, 0
+ 0, 0, 0, 0
}, {
- 0, 0, 0
+ 0, 0, 0, 0
}, {
- 0, 0, 0
+ 0, 0, 0, 0
}, {
- 0, 0, 0
+ 0, 0, 0, 0
}, {
#if defined(RTEMS_MULTIPROCESSING)
- 0, 0, 0
+ 0, 0, 0, 0
#else
- 0, 0, 0
+ 0, 0, 0, 0
#endif
}, {
- 0, 0, 0
+ 0, 0, 0, 0
}, {
- 0, 0, 0
+ 0, 0, 0, 0
}, {
- 0, 0, 0
+ 0, 0, 0, 0
}, {
- 0, 0, 0
+ 0, 0, 0, 0
}, {
- 0, 0, 0
+ 0, 0, 0, 0
}, {
#if defined(RTEMS_MULTIPROCESSING)
- 0, 0, 0
+ 0, 0, 0, 0
#else
- 0, 0, 0
+ 0, 0, 0, 0
#endif
}, {
- 0, 0, 0
+ 0, 0, 0, 0
}, {
- 0, 0, 0
+ 0, 0, 0, 0
}
};
@@ -774,6 +775,11 @@ T_TEST_CASE_FIXTURE(
index += ( ClassicTaskIdentification_Pre_Id_NA - 1 );
}
+ if ( ClassicTaskIdentification_TransitionInfo[ index ].Skip ) {
+ ++index;
+ continue;
+ }
+
ClassicTaskIdentification_Pre_Name_Prepare( ctx, ctx->pcs[ 0 ] );
ClassicTaskIdentification_Pre_Node_Prepare( ctx, ctx->pcs[ 1 ] );
ClassicTaskIdentification_Pre_Id_Prepare( ctx, ctx->pcs[ 2 ] );
@@ -1049,6 +1055,7 @@ typedef enum {
typedef enum {
Action2_Pre_B_X,
Action2_Pre_B_Y,
+ Action2_Pre_B_Z,
Action2_Pre_B_NA
} Action2_Pre_B;
@@ -1193,7 +1200,8 @@ static const char * const Action2_PreDesc_A[] = {
static const char * const Action2_PreDesc_B[] = {
"X",
- "Y"
+ "Y",
+ "Z"
};
static const char * const * const Action2_PreDesc[] = {
@@ -1241,6 +1249,11 @@ static void Action2_Pre_B_Prepare( Action2_Context *ctx, Action2_Pre_B state )
break;
}
+ case Action2_Pre_B_Z: {
+ /* Pre B Z */
+ break;
+ }
+
case Action2_Pre_B_NA:
break;
}
@@ -1358,25 +1371,36 @@ static const uint8_t Action2_TransitionMap[][ 2 ] = {
Action2_Post_B_X
}, {
Action2_Post_A_X,
+ Action2_Post_B_X
+ }, {
+ Action2_Post_A_X,
Action2_Post_B_Y
}, {
Action2_Post_A_Y,
Action2_Post_B_X
+ }, {
+ Action2_Post_A_Y,
+ Action2_Post_B_Y
}
};
static const struct {
+ uint8_t Skip : 1;
uint8_t Pre_A_NA : 1;
uint8_t Pre_B_NA : 1;
} Action2_TransitionInfo[] = {
{
- 0, 0
+ 0, 0, 0
}, {
- 1, 0
+ 0, 1, 0
}, {
- 0, 0
+ 0, 0, 0
+ }, {
+ 0, 0, 0
+ }, {
+ 0, 1, 0
}, {
- 1, 0
+ 1, 0, 0
}
};
@@ -1416,6 +1440,11 @@ void Action2_Run( int *a, int b, int *c )
index += ( Action2_Pre_B_NA - 1 );
}
+ if ( Action2_TransitionInfo[ index ].Skip ) {
+ ++index;
+ continue;
+ }
+
Action2_Pre_A_Prepare( ctx, ctx->pcs[ 0 ] );
Action2_Pre_B_Prepare( ctx, ctx->pcs[ 1 ] );
/* Action */
diff --git a/rtemsspec/validation.py b/rtemsspec/validation.py
index f914143..8dddec9 100644
--- a/rtemsspec/validation.py
+++ b/rtemsspec/validation.py
@@ -398,10 +398,20 @@ class _TestDirectiveItem(_TestItem):
transition_map = [list() for _ in range(transition_count)
] # type: _TransitionMap
for transition in self["transition-map"]:
- post = tuple(self._post_state_to_index[index][
- transition["post-conditions"][self._post_index_to_name[index]]]
- for index in range(self._post_condition_count))
- self._add_transitions(0, 0, transition, transition_map, [], post)
+ if isinstance(transition["post-conditions"], dict):
+ info = ["0"]
+ post_cond = tuple(
+ self._post_state_to_index[index][
+ transition["post-conditions"][
+ self._post_index_to_name[index]]]
+ for index in range(self._post_condition_count))
+ else:
+ info = ["1"]
+ post_cond = tuple(
+ len(self._post_state_to_index[index]) - 1
+ for index in range(self._post_condition_count))
+ self._add_transitions(0, 0, transition, transition_map, info,
+ post_cond)
return transition_map
def _post_condition_enumerators(self, conditions: Any) -> str:
@@ -448,9 +458,11 @@ class _TestDirectiveItem(_TestItem):
map_elements.append("\n".join(map_enumerators))
info_elements.append("\n".join(info_enumerators))
content.append(["\n }, {\n".join(map_elements), " }", "};"])
- pre_bits = 2**max(math.ceil(math.log2(self._pre_condition_count)), 3)
+ pre_bits = 2**max(math.ceil(math.log2(self._pre_condition_count + 1)),
+ 3)
content.add("static const struct {")
with content.indent():
+ content.append(f"uint{pre_bits}_t Skip : 1;")
for condition in self["pre-conditions"]:
content.append(
f"uint{pre_bits}_t Pre_{condition['name']}_NA : 1;")
@@ -458,6 +470,8 @@ class _TestDirectiveItem(_TestItem):
content.append(["\n }, {\n".join(info_elements), " }", "};"])
def _add_action(self, content: CContent) -> None:
+ with content.condition(f"{self.ident}_TransitionInfo[ index ].Skip"):
+ content.append(["++index;", "continue;"])
content.add_blank_line()
for index, enum in enumerate(self._pre_index_to_enum):
content.append(f"{enum[0]}_Prepare( ctx, ctx->pcs[ {index} ] );")
diff --git a/spec/req/rtems/ident-local.yml b/spec/req/rtems/ident-local.yml
index 38bf9cd..9bb542f 100644
--- a/spec/req/rtems/ident-local.yml
+++ b/spec/req/rtems/ident-local.yml
@@ -83,6 +83,7 @@ pre-conditions:
test-epilogue: null
test-prologue: null
requirement-type: functional
+skip-reasons: {}
test-action: |
ctx->status = ( *ctx->action )( ctx->name, ctx->id );
test-brief: null
diff --git a/spec/req/rtems/ident.yml b/spec/req/rtems/ident.yml
index b56603b..1a9bbfb 100644
--- a/spec/req/rtems/ident.yml
+++ b/spec/req/rtems/ident.yml
@@ -136,6 +136,7 @@ pre-conditions:
test-epilogue: null
test-prologue: null
requirement-type: functional
+skip-reasons: {}
test-action: |
ctx->status = ( *ctx->action )( ctx->name, ctx->node, ctx->id );
test-brief: null
diff --git a/spec/req/rtems/tasks/ident.yml b/spec/req/rtems/tasks/ident.yml
index 0a8171d..3d2d687 100644
--- a/spec/req/rtems/tasks/ident.yml
+++ b/spec/req/rtems/tasks/ident.yml
@@ -43,6 +43,7 @@ pre-conditions:
test-epilogue: null
test-prologue: null
requirement-type: functional
+skip-reasons: {}
test-action: |
if ( ctx->id != NULL ) {
ctx->status = rtems_task_ident( RTEMS_SELF, 0xdeadbeef, ctx->id );
diff --git a/spec/spec/requirement-action-skip-reasons.yml b/spec/spec/requirement-action-skip-reasons.yml
new file mode 100644
index 0000000..75be7ed
--- /dev/null
+++ b/spec/spec/requirement-action-skip-reasons.yml
@@ -0,0 +1,27 @@
+SPDX-License-Identifier: CC-BY-SA-4.0 OR BSD-2-Clause
+copyrights:
+- Copyright (C) 2020 embedded brains GmbH (http://www.embedded-brains.de)
+enabled-by: true
+links:
+- role: spec-member
+ uid: root
+spec-description: null
+spec-example: null
+spec-info:
+ dict:
+ attributes: {}
+ description: |
+ This set of attributes specifies skip reasons used to justify why
+ transitions in the transition map are skipped.
+ generic-attributes:
+ description: |
+ The key defines the name of a skip reason. The name can be used in
+ :ref:`SpecTypeActionRequirementTransitionPostConditions` to skip the
+ corresponding transitions. The value shall give a reason why the
+ transitions are skipped.
+ key-spec-type: requirement-action-name
+ value-spec-type: str
+ mandatory-attributes: all
+spec-name: Action Requirement Skip Reasons
+spec-type: requirement-action-skip-reasons
+type: spec
diff --git a/spec/spec/requirement-action-transition-post.yml b/spec/spec/requirement-action-transition-post.yml
index 7fca2f1..935484e 100644
--- a/spec/spec/requirement-action-transition-post.yml
+++ b/spec/spec/requirement-action-transition-post.yml
@@ -22,6 +22,16 @@ spec-info:
key-spec-type: requirement-action-name
value-spec-type: requirement-action-name
mandatory-attributes: all
+ str:
+ assert:
+ and:
+ - re: ^[A-Z][a-zA-Z0-9]+$
+ - not:
+ eq: NA
+ description: |
+ It shall be the name of a skip reason. If a skip reason is given instead
+ of a listing of post-condition states, then this transition is skipped
+ and no test code runs for this transition.
spec-name: Action Requirement Transition Post-Conditions
spec-type: requirement-action-transition-post
type: spec
diff --git a/spec/spec/requirement-action.yml b/spec/spec/requirement-action.yml
index 8eb7b7b..6afa787 100644
--- a/spec/spec/requirement-action.yml
+++ b/spec/spec/requirement-action.yml
@@ -81,6 +81,7 @@ spec-example: |
test-epilogue: null
test-prologue: null
requirement-type: functional
+ skip-reasons: {}
test-action: |
/* Call the function of the action */
test-brief: null
@@ -137,6 +138,9 @@ spec-info:
pre-conditions:
description: null
spec-type: requirement-action-condition-list
+ skip-reasons:
+ description: null
+ spec-type: requirement-action-skip-reasons
test-action:
description: |
It shall be the test action code.
More information about the vc
mailing list