support for wildcard as reward state property

Signed-off-by: Stefano Puri <stefano.puri@intecs.it>
diff --git a/plugins/mobius/org.polarsys.chess.mobius/transformations/CHESS2SAN.qvto b/plugins/mobius/org.polarsys.chess.mobius/transformations/CHESS2SAN.qvto
index 7cc8e0a..5a67b38 100644
--- a/plugins/mobius/org.polarsys.chess.mobius/transformations/CHESS2SAN.qvto
+++ b/plugins/mobius/org.polarsys.chess.mobius/transformations/CHESS2SAN.qvto
@@ -49,6 +49,8 @@
 property rootComponentInstance : InstanceSpecification;

 property umlInstancesConnectors : Set(UML::InstanceSpecification) = Set{};		--Instances of connectors

 property umlAtomicInstances : Set(UML::InstanceSpecification) = Set{};		--Instances of terminal instances

+property instancePackage : Package;

+

 

 property sbaTransitions : Sequence(OclAny) = Sequence{CHESS::ThreatsPropagation::Failure, CHESS::ThreatsPropagation::InternalPropagation, CHESS::ThreatsPropagation::InternalFault};

 

@@ -65,7 +67,7 @@
 

 main() {

 	this.model := source.rootObjects()![Model];

-	var selectedInstSpec : Package = model.findElementByQualifiedName(selectedPlatformQName).oclAsType(Package);

+	instancePackage := model.findElementByQualifiedName(selectedPlatformQName).oclAsType(Package);

 	

 	log ("analysis context: " + analysisContextQName);

 	analysisContext := model.findElementByQualifiedName(analysisContextQName).oclAsType(Class);

@@ -74,10 +76,10 @@
 	analysisContext.initAttackScenario();

 	analysisContext.initRewards();

 	

-	this.rootComponentInstance := selectedInstSpec.ownedElement[InstanceSpecification]->

-		selectOne(name = selectedInstSpec.name.substringBefore("_instSpec"));

-	this.rootComponent := selectedInstSpec.ownedElement[InstanceSpecification]->

-		selectOne(name = selectedInstSpec.name.substringBefore("_instSpec")).classifier![Class];

+	this.rootComponentInstance := instancePackage.ownedElement[InstanceSpecification]->

+		selectOne(name = instancePackage.name.substringBefore("_instSpec"));

+	this.rootComponent := instancePackage.ownedElement[InstanceSpecification]->

+		selectOne(name = instancePackage.name.substringBefore("_instSpec")).classifier![Class];

 	//this.rootComponent.ownedComment += object Comment {body := "hello CHESS"; annotatedElement += rootComponent;};

 	//this.rootComponent.UmlComponent2SANnode();

 	var sanModel := this.rootComponentInstance.map UMLInstance2SANModel();

@@ -87,7 +89,7 @@
 	//failure propagation

 	

 	//retrieve the set of connector instances

-	var instances : Set(UML::Element) = selectedInstSpec.ownedElement->select(i | i.oclIsKindOf(InstanceSpecification));

+	var instances : Set(UML::Element) = instancePackage.ownedElement->select(i | i.oclIsKindOf(InstanceSpecification));

 				

 	--log ("found instances"+ instances->size().toString());

 	

@@ -1485,18 +1487,45 @@
 

 }

 

-//TODO use AnalysisContext.??? property

+

 query UML::Class::initRewards(){

 	var analysis : CHESS::StateBasedAnalysis::CyberSecurityAnalysis := self.getStereotypeApplication(CYBERSECURITYANALYSIS_STEREOTYPE).oclAsType(CHESS::StateBasedAnalysis::CyberSecurityAnalysis);

-	this.rewardStates := analysis.context;

 	

-	//TODO here I just copy the name of the state from the analysis context...for each state, I should check that it exist actually in the model

+	analysis.context-> forEach (reward){

+		if (reward.toString().startsWith('*.')){  //support for wildcard, e.g. *.ErrorState ->all instances having ErorState are interested by the reward

+			var stateName := reward.toString().substring(3, reward.toString().size());

+			//check all errorModel instances

+			var children := getAllErrorModelBehaviourInstance();

+			var errorModel : UML::StateMachine;

+			children -> forEach(child){

+				log ("CHECKING instance " + child.name);

+				errorModel := child.getErrorModel();

+				//if (errorModel != null and not errorModel->oclIsInvalid()){ //this is actually guaranteed

+					var vertexes := errorModel.region->asSequence()->first().oclAsType(UML::Region).subvertex;

+					vertexes ->forEach(vertex){

+						if (vertex.name = stateName){

+							this.rewardStates  += child.name+"."+vertex.oclAsType(UML::State).name;

+						}

+					}

+				//}

+			}

+		}else{

+			//TODO here I just copy the name of the state from the analysis context...for each state, I should check that it exist actually in the model

+			//Assumption: reward = <instance name>.<error model state name>

+			this.rewardStates+=reward;

+		}

+	};

 	this.rewardStates -> forEach(state){

-		log("rewards state: " + state);

+		log("reward states of interest: " + state);

 	};

 	

 }

 

+query getAllErrorModelBehaviourInstance() : Set(UML::InstanceSpecification){

+	var set := instancePackage.ownedElement->selectByKind(InstanceSpecification)->select(i:InstanceSpecification | not (i->oclAsType(UML::InstanceSpecification).getErrorModel()=null));

+	return set;

+}

+

 //returns the UML Messages associated (through vulnerability) to transition

 query UML::Transition::getAttackMessages() : Set(UML::Message){