|
|
@@ -124,6 +124,54 @@ Integer function are_connected(model: Element, el1:Element, el2:Element):
|
|
|
return 0 //edge is not connected
|
|
|
return 0 // if the function doesn't support it, assume disconnected
|
|
|
|
|
|
+Element function read_outgoing_assoc(model:Element, el1:Element, allowed:Element):
|
|
|
+ Element result
|
|
|
+ result = create_node()
|
|
|
+ if(is_edge(el1)):
|
|
|
+ set_add(result, read_edge_dst(el1))
|
|
|
+ return result
|
|
|
+ else:
|
|
|
+ Integer length
|
|
|
+ length = read_nr_out(el1)
|
|
|
+ log(cast_i2s(length))
|
|
|
+ Integer counter
|
|
|
+ counter = 0
|
|
|
+ Element edge
|
|
|
+ while (counter < length):
|
|
|
+ edge = read_out(el1, counter)
|
|
|
+ //check if edge is part of the model
|
|
|
+ if (set_in_node(allowed, edge)):
|
|
|
+ //check if it is not attribute related
|
|
|
+ if(bool_not(isAttributeRelated(model, edge))):
|
|
|
+ set_add(result, edge)
|
|
|
+ counter = counter + 1
|
|
|
+ return result
|
|
|
+ return create_node()
|
|
|
+
|
|
|
+Element function read_incoming_assoc(model:Element, el1:Element, allowed:Element):
|
|
|
+ Element result
|
|
|
+ result = create_node()
|
|
|
+ if(is_edge(el1)):
|
|
|
+ set_add(result, read_edge_src(el1))
|
|
|
+ return result
|
|
|
+ else:
|
|
|
+ //get possible types of associations
|
|
|
+ Integer length
|
|
|
+ length = read_nr_in(model["typemapping"][el1])
|
|
|
+ Integer counter
|
|
|
+ counter = 0
|
|
|
+
|
|
|
+ Element edge
|
|
|
+ while (counter < length):
|
|
|
+ edge = read_in(el1, counter)
|
|
|
+ //check if edge is part of the model
|
|
|
+ if (set_in_node(allowed, edge)):
|
|
|
+ //check if it is not attribute related
|
|
|
+ if(bool_not(isAttributeRelated(model, edge))):
|
|
|
+ set_add(result, edge)
|
|
|
+ counter = counter + 1
|
|
|
+ return result
|
|
|
+ return create_node()
|
|
|
|
|
|
Element function new_SearchState(OldSearchState : Element, TransfModel : Element, NewTransfElem: Element, HostModel : Element, NewHostElem : Element):
|
|
|
//some variables
|
|
|
@@ -131,6 +179,12 @@ Element function new_SearchState(OldSearchState : Element, TransfModel : Element
|
|
|
nss = create_node()
|
|
|
Integer index // used for list looping
|
|
|
Element elem // reusable loop variable
|
|
|
+ Element ol //old list = old pattern out
|
|
|
+ Element nl //new list = new N pattern out
|
|
|
+ Element allowedP
|
|
|
+ allowedP = OldSearchState["V_pattern"]
|
|
|
+ Element allowedH
|
|
|
+ allowedH = OldSearchState["V_host"]
|
|
|
|
|
|
//new MATCHES
|
|
|
dict_add(nss, "matches", OldSearchState["matches"]) //hopefully works as a reference
|
|
|
@@ -140,21 +194,31 @@ Element function new_SearchState(OldSearchState : Element, TransfModel : Element
|
|
|
OldCurMatchKeys = dict_keys(OldSearchState["curmatch"])
|
|
|
Element new_curmatch //the new curmatch
|
|
|
new_curmatch = create_node()
|
|
|
+ Element new_curmatch_pattern //keep a set of all matches pattern nodes
|
|
|
+ new_curmatch_pattern = create_node()
|
|
|
+ Element new_curmatch_host //keep a set of all matched host nodes
|
|
|
+ new_curmatch_host = create_node()
|
|
|
while (integer_lt(0, list_len(OldCurMatchKeys))): //copying the old curmatch
|
|
|
index = set_pop(OldCurMatchKeys)
|
|
|
dict_add(new_curmatch, index, OldSearchState["curmatch"][index])
|
|
|
+ set_add(new_curmatch_pattern, OldSearchState["curmatch"][index]["pn"] )
|
|
|
+ set_add(new_curmatch_host, OldSearchState["curmatch"][index]["hn"] )
|
|
|
Element newPair // the new pair to be added
|
|
|
newPair = create_node()
|
|
|
dict_add(newPair, "pn", NewTransfElem) //PatternNode
|
|
|
+ set_add(new_curmatch_pattern, NewTransfElem)
|
|
|
dict_add(newPair, "hn", NewHostElem) // HostNode
|
|
|
+ set_add(new_curmatch_host, NewHostElem)
|
|
|
Integer plabel
|
|
|
plabel = read_attribute(TransfModel, getName(TransfModel, NewTransfElem), "plabel")
|
|
|
dict_add(new_curmatch, plabel, newPair) //add pair to new curmatch
|
|
|
dict_add(nss, "curmatch", new_curmatch) //add curmatch to state
|
|
|
|
|
|
+ //new CURMATCH_pattern and host (constructed during the previous loop)
|
|
|
+ dict_add(nss, "curmatch_pattern", new_curmatch_pattern)
|
|
|
+ dict_add(nss, "curmatch_host", new_curmatch_pattern)
|
|
|
+
|
|
|
//new N_PATTERN_OUT (copy everything but the new match elements)
|
|
|
- Element ol //old list = old pattern out
|
|
|
- Element nl //new list = new N pattern out
|
|
|
ol = OldSearchState["N_pattern_out"]
|
|
|
nl = create_node()
|
|
|
index = 0
|
|
|
@@ -162,7 +226,12 @@ Element function new_SearchState(OldSearchState : Element, TransfModel : Element
|
|
|
elem = list_read(ol, index)
|
|
|
index = index + 1
|
|
|
if(bool_not(element_eq(elem, NewTransfElem))):
|
|
|
- list_append(nl, elem)
|
|
|
+ set_add(nl, elem)
|
|
|
+ ol = read_outgoing_assoc(TransfModel, NewTransfElem, allowedP)
|
|
|
+ while (read_nr_out(ol)>0):
|
|
|
+ elem = set_pop(ol)
|
|
|
+ if (bool_not(set_in_node(new_curmatch_pattern, elem))):
|
|
|
+ list_append(nl,elem)
|
|
|
dict_add(nss, "N_pattern_out", nl)
|
|
|
|
|
|
//new N_HOST_OUT (copy everything but the new match elements)
|
|
|
@@ -174,6 +243,11 @@ Element function new_SearchState(OldSearchState : Element, TransfModel : Element
|
|
|
index = index + 1
|
|
|
if(bool_not(element_eq(elem, NewHostElem))):
|
|
|
list_append(nl, elem)
|
|
|
+ ol = read_outgoing_assoc(HostModel, NewHostElem, allowedH)
|
|
|
+ while (read_nr_out(ol)>0):
|
|
|
+ elem = set_pop(ol)
|
|
|
+ if (bool_not(set_in_node(new_curmatch_host, elem))):
|
|
|
+ list_append(nl,elem)
|
|
|
dict_add(nss, "N_host_out", nl)
|
|
|
|
|
|
//new N_PATTERN_IN (copy everything but the new match elements)
|
|
|
@@ -185,6 +259,11 @@ Element function new_SearchState(OldSearchState : Element, TransfModel : Element
|
|
|
index = index + 1
|
|
|
if(bool_not(element_eq(elem, NewTransfElem))):
|
|
|
list_append(nl, elem)
|
|
|
+ ol = read_incoming_assoc(TransfModel, NewTransfElem, allowedP)
|
|
|
+ while (read_nr_out(ol)>0):
|
|
|
+ elem = set_pop(ol)
|
|
|
+ if (bool_not(set_in_node(new_curmatch_pattern, elem))):
|
|
|
+ list_append(nl,elem)
|
|
|
dict_add(nss, "N_pattern_in", nl)
|
|
|
|
|
|
//new N_HOST_IN (copy everything but the new match elements
|
|
|
@@ -196,56 +275,48 @@ Element function new_SearchState(OldSearchState : Element, TransfModel : Element
|
|
|
index = index + 1
|
|
|
if(bool_not(element_eq(elem, NewHostElem))):
|
|
|
list_append(nl, elem)
|
|
|
+ ol = read_incoming_assoc(HostModel, NewHostElem, allowedH)
|
|
|
+ while (read_nr_out(ol) > 0):
|
|
|
+ elem = set_pop(ol)
|
|
|
+ if (bool_not(set_in_node(new_curmatch_host, elem))):
|
|
|
+ list_append(nl,elem)
|
|
|
dict_add(nss, "N_host_in", nl)
|
|
|
|
|
|
//new V_PATTERN
|
|
|
- ol = OldSearchState["V_pattern"]
|
|
|
- nl = create_node()
|
|
|
- index = 0
|
|
|
- Integer connectedness
|
|
|
- while (index < list_len(ol)): //loop trough old list
|
|
|
- elem = list_read(ol, index)
|
|
|
- index = index + 1
|
|
|
- if(bool_not(element_eq(elem, NewTransfElem))):
|
|
|
- connectedness = are_connected(TransfModel, NewTransfElem, elem)
|
|
|
- if (connectedness == 0): // if not connected, keep in V
|
|
|
- list_append(nl, elem)
|
|
|
- elif (connectedness == 1): //if connected in outwards manner, don't keep in v and add to outlist
|
|
|
- list_append(nss["N_pattern_out"], elem)
|
|
|
- elif (connectedness == 2): //if connected in inwards manner, don't keep in v and add to inlist
|
|
|
- list_append(nss["N_pattern_in"], elem)
|
|
|
- else:
|
|
|
- log("new_SearchState: unsupported connectedness value")
|
|
|
- log(cast_i2s(connectedness))
|
|
|
- dict_add(nss, "V_pattern", nl)
|
|
|
+ dict_add(nss, "V_pattern", allowedP)
|
|
|
|
|
|
//new V_HOST
|
|
|
- ol = OldSearchState["V_host"]
|
|
|
- nl = create_node()
|
|
|
- index = 0
|
|
|
- while (index < list_len(ol)): //loop trough old list
|
|
|
- elem = list_read(ol, index)
|
|
|
- index = index + 1
|
|
|
- if(bool_not(element_eq(elem, NewHostElem))):
|
|
|
- connectedness = are_connected(HostModel, NewHostElem, elem)
|
|
|
- if (connectedness == 0): // if not connected, keep in V
|
|
|
- list_append(nl, elem)
|
|
|
- elif (connectedness == 1): //if connected in outwards manner, don't keep in v and add to outlist
|
|
|
- list_append(nss["N_host_out"], elem)
|
|
|
- elif (connectedness == 2): //if connected in inwards manner, don't keep in v and add to inlist
|
|
|
- list_append(nss["N_host_in"], elem)
|
|
|
- else:
|
|
|
- log("new_SearchState: unsupported connectedness value")
|
|
|
- log(cast_i2s(connectedness))
|
|
|
- dict_add(nss, "V_host", nl)
|
|
|
+ dict_add(nss, "V_host", allowedH)
|
|
|
|
|
|
// copy pattern_size
|
|
|
dict_add(nss, "pattern_size", OldSearchState["pattern_size"])
|
|
|
|
|
|
return nss
|
|
|
|
|
|
-Element function transf_vf2(SearchState: Element, transf_m : Element, host_m : Element):
|
|
|
+Element function destruct(nss:Element):
|
|
|
+ log("destructing")
|
|
|
+ //destruct current_match
|
|
|
+ Element todelete
|
|
|
+ while (read_nr_out(nss["curmatch"])>0):
|
|
|
+ todelete = set_pop(nss["curmatch"])
|
|
|
+ delete_element(todelete)
|
|
|
+
|
|
|
+ delete_element(nss["curmatch_pattern"])
|
|
|
+ delete_element(nss["curmatch_host"])
|
|
|
+ delete_element(nss["N_pattern_out"])
|
|
|
+ delete_element(nss["N_pattern_in"])
|
|
|
+ delete_element(nss["N_host_in"])
|
|
|
+ delete_element(nss["N_host_out"])
|
|
|
|
|
|
+
|
|
|
+
|
|
|
+ delete_element(nss)
|
|
|
+ log("end destructing")
|
|
|
+
|
|
|
+ return 0
|
|
|
+
|
|
|
+Element function transf_vf2(SearchState: Element, transf_m : Element, host_m : Element):
|
|
|
+ log("transf_vf2")
|
|
|
// get the current match from the search-state
|
|
|
Element current_match
|
|
|
current_match = dict_read(SearchState,"curmatch")
|
|
|
@@ -254,7 +325,20 @@ Element function transf_vf2(SearchState: Element, transf_m : Element, host_m : E
|
|
|
Integer pattern_size
|
|
|
pattern_size = SearchState["pattern_size"]
|
|
|
if pattern_size == list_len(current_match):
|
|
|
- list_append(SearchState["matches"], SearchState["curmatch"])
|
|
|
+ Element OldCurMatchKeys // for looping trough old curmatch (for copying)
|
|
|
+ OldCurMatchKeys = dict_keys(SearchState["curmatch"])
|
|
|
+ Element new_curmatch //the new curmatch
|
|
|
+ new_curmatch = create_node()
|
|
|
+ Element deepcopy
|
|
|
+ Integer index
|
|
|
+
|
|
|
+ while (integer_lt(0, list_len(OldCurMatchKeys))): //copying the old curmatch
|
|
|
+ index = set_pop(OldCurMatchKeys)
|
|
|
+ deepcopy = create_node()
|
|
|
+ dict_add(deepcopy, "pn", SearchState["curmatch"][index]["pn"])
|
|
|
+ dict_add(deepcopy, "hn", SearchState["curmatch"][index]["hn"])
|
|
|
+ dict_add(new_curmatch, index, deepcopy)
|
|
|
+ list_append(SearchState["matches"], new_curmatch)
|
|
|
//log("MATCHED")
|
|
|
return SearchState
|
|
|
|
|
|
@@ -263,8 +347,6 @@ Element function transf_vf2(SearchState: Element, transf_m : Element, host_m : E
|
|
|
return SearchState
|
|
|
if (list_len(SearchState["N_pattern_in"]) > list_len(SearchState["N_host_in"])):
|
|
|
return SearchState
|
|
|
- if (list_len(SearchState["V_pattern"]) > list_len(SearchState["V_host"])):
|
|
|
- return SearchState
|
|
|
|
|
|
//initialise some variables
|
|
|
Integer index2 //an index used for looping trough host_list
|
|
|
@@ -287,6 +369,7 @@ Element function transf_vf2(SearchState: Element, transf_m : Element, host_m : E
|
|
|
nss = transf_vf2(nss, transf_m, host_m)
|
|
|
dict_delete(SearchState, "matches")
|
|
|
dict_add(SearchState, "matches", nss["matches"])
|
|
|
+ destruct(nss)
|
|
|
elif ( list_len(SearchState["N_pattern_in"]) > 0 ):
|
|
|
//check for candidates in (N_pattern_in, N_host_in)
|
|
|
host_list = SearchState["N_host_in"]
|
|
|
@@ -300,10 +383,12 @@ Element function transf_vf2(SearchState: Element, transf_m : Element, host_m : E
|
|
|
nss = transf_vf2(nss, transf_m, host_m)
|
|
|
dict_delete(SearchState, "matches")
|
|
|
dict_add(SearchState, "matches", nss["matches"])
|
|
|
+ destruct(nss)
|
|
|
elif ( list_len(SearchState["V_pattern"]) > 0 ):
|
|
|
//check for candidates in (V_pattern, V_host))
|
|
|
host_list = SearchState["V_host"]
|
|
|
- pattern_node = list_read(SearchState["V_pattern"], 0)
|
|
|
+ pattern_node = set_pop(SearchState["V_pattern"])
|
|
|
+ //list_read(SearchState["V_pattern"], 0)
|
|
|
index2 = 0
|
|
|
while (index2 < list_len(host_list)):
|
|
|
host_node = list_read(host_list, index2)
|
|
|
@@ -313,8 +398,10 @@ Element function transf_vf2(SearchState: Element, transf_m : Element, host_m : E
|
|
|
nss = transf_vf2(nss, transf_m, host_m)
|
|
|
dict_delete(SearchState, "matches")
|
|
|
dict_add(SearchState, "matches", nss["matches"])
|
|
|
+ destruct(nss)
|
|
|
else:
|
|
|
log("no candidate found")
|
|
|
+ log(" end transf_vf2")
|
|
|
return SearchState
|
|
|
|
|
|
|
|
|
@@ -356,6 +443,8 @@ Element function tf_matchAll(tf_ma_transformation: Element, tf_ma_pattern : Elem
|
|
|
SearchState = create_node()
|
|
|
dict_add(SearchState, "matches", create_node())
|
|
|
dict_add(SearchState, "curmatch", create_node())
|
|
|
+ dict_add(SearchState, "curmatch_pattern", create_node())
|
|
|
+ dict_add(SearchState, "curmatch_host", create_node())
|
|
|
dict_add(SearchState, "N_pattern_out", create_node())
|
|
|
dict_add(SearchState, "N_host_out", create_node())
|
|
|
dict_add(SearchState, "N_pattern_in", create_node())
|
|
|
@@ -370,8 +459,14 @@ Element function tf_matchAll(tf_ma_transformation: Element, tf_ma_pattern : Elem
|
|
|
|
|
|
//timing info
|
|
|
log(string_join("matching took ", cast_i2s( current_time() - starttime)))
|
|
|
-
|
|
|
- return SearchState["matches"]
|
|
|
+
|
|
|
+ delete_element(tf_ma_ramified_nodes)
|
|
|
+ delete_element(host_nodes)
|
|
|
+
|
|
|
+ Element matches
|
|
|
+ matches = SearchState["matches"]
|
|
|
+ destruct(SearchState)
|
|
|
+ return matches
|
|
|
|
|
|
Element function mergeLHSNAC(tf_er_lhs : Element, tf_er_nac: Element):
|
|
|
|
|
|
@@ -583,6 +678,21 @@ Element function tf_executeFRule(tf_er_transformation: Element,tf_er_rule: Eleme
|
|
|
dict_add(plabel_to_rhsnode,rhs_plabel, rhs_node)
|
|
|
|
|
|
rhs_rewrite(final_matches ,plabel_to_rhsnode, tf_er_transformation, tf_er_model )
|
|
|
+
|
|
|
+ //clean up matches
|
|
|
+ Element todelete
|
|
|
+ Element todelete2
|
|
|
+ while (read_nr_out(tf_er_nac) >0):
|
|
|
+ todelete2 = set_pop(tf_er_nac)
|
|
|
+ while (read_nr_out(todelete2)>0):
|
|
|
+ todelete = set_pop(todelete2)
|
|
|
+ delete_element(todelete)
|
|
|
+
|
|
|
+ while (read_nr_out(tf_er_lhs) >0):
|
|
|
+ todelete2 = set_pop(tf_er_nac)
|
|
|
+ while (read_nr_out(todelete2)>0):
|
|
|
+ todelete = set_pop(todelete2)
|
|
|
+ delete_element(todelete)
|
|
|
|
|
|
return True
|
|
|
|
|
|
@@ -1018,11 +1128,11 @@ Element function petrinet_transformation(root: Element):
|
|
|
instantiate_link(my_model, "getrule","", "frule3", "produce_tokens")
|
|
|
|
|
|
//create circularity link
|
|
|
- instantiate_link(my_model, "next_onSucces", "", "frule3", "arule1")
|
|
|
+ //instantiate_link(my_model, "next_onSucces", "", "frule3", "arule1")
|
|
|
//if you cannot consume, still try to produce (for source transitions)
|
|
|
- instantiate_link(my_model, "next_onFailure", "", "frule2", "frule3")
|
|
|
+ //instantiate_link(my_model, "next_onFailure", "", "frule2", "frule3")
|
|
|
//if you cannot produce, still check for other transitions (it might have consumed already)
|
|
|
- instantiate_link(my_model, "next_onFailure", "", "frule3", "arule1")
|
|
|
+ //instantiate_link(my_model, "next_onFailure", "", "frule3", "arule1")
|
|
|
|
|
|
|
|
|
|