Returning scope as type without a constructor generates wrong code
The following NaBL2 constraint rule:
[[ _ ^ (_) : s ]] := new s.
generates the following Stratego code:
nabl2--generate-constraint-default-rule(|nabl2_source, nabl2_args): nabl2_term@_ -> nabl2_constraint with(ParamsAndType(nabl2_params@(_), nabl2_type@s) := nabl2_args <+ fatal-err( | <concat-strings> [ "Cannot match expected " , "^ (_) : s" , " with actual " , <nabl2--pp-flat-args> nabl2_args , " when matching " , "_" , " with " , <pp-NaBL2-Term> nabl2_term , "." ] )) with(if nabl2-debug-constraint-generation-hook then <(concat-strings ; debug)> [ "default" , " [[ " , <pp-NaBL2-Term> nabl2_term , " ^ " , <pp-NaBL2-CTerm> nabl2_params , " : " , <pp-NaBL2-Type> nabl2_type , " ]]" ] end) with(id) with(s := <nabl2--new-scope(|nabl2_source)> "s" ; id) with(nabl2_index := <nabl2--get-ast-index> nabl2_term ; nabl2_metadata := [ CAstProperty(nabl2_index, Params(), nabl2_params) , CAstProperty(nabl2_index, Type(), nabl2_type) ]) with(nabl2_constraint := <conc ; nabl2--flatten-list> (nabl2_metadata, ))
but this will always cause a failure, because the variable
sis being bound twice:
- In line 3 from the top:
- In line 6 from the bottom:
with(s := <nabl2--new-scope(|nabl2_source)> "s" ; id)
A workaround is to wrap the scope in a constructor:
[[ _ ^ (_) : ScopeType(s) ]] := new s.
which then changes line 3 to:
with(ParamsAndType(nabl2_params@(_), nabl2_type@nabl2_type) := nabl2_args
preventing the double bind (althoughSubmitted by Gabriël Konat on 23 January 2017 at 10:16
nabl2_type@nabl2_typeis also a weird binding!)
Problem is that using
sin the type causes it to match against the passed arguments. Using
newresults in imperatively creating a new scope. Using both in the same rule causes a clash during traversal. This could be resolved by adding an equality constraint, instead of doing the match against the variable directly.
this is fixed in recent builds.
Log in to post comments