XRM 53: Add meta-if at Expression level.

8 Jun
2006
8 Jun
'06
2:07 p.m.
https://svn.lrde.epita.fr/svn/xrm/trunk Index: ChangeLog from SIGOURE Benoit <sigoure.benoit@lrde.epita.fr> Add meta-if at Expression level. So basically, it is now possible to have a meta-if statement everywhere we can find an Expression. /!\ NOTE: meta-if statements at Expression level are restricted to one single expressions in the then-part and else-part. eg: if some-condition then exp1 exp2 end is *invalid* at Expression level because neither the base language nor the extended language provide real statements/sequences of expressions. Other improvements: PRISM-If statements (cond ? then-part : else-part) are now evaluated by prism-desugar when possible. It is also possible to reduce the condition of a meta-if statement down to a simple Int(_) or Double(_). If that Int(_) or Double(_) is zero, the condition will evaluate as False() otherwise True() [like in C]. NOTE: for Double(_) all tests are performed with a precision of 10^-7 in other words if 0.000000001 then ... else /*executed*/ end will be false. * src/str/prism-desugar.str: Add EvalIf and LitToBool. * src/str/eval-meta-code.str: Allow if statements to evaluate as integer/real. In this case the behavior is the same as in C: 0 means false and all the other values mean true. * src/str/xrm-front.str: Change a debug message to be a notice. * src/syn/xrm/XRM-Arrays.sdf: Use XRMRange for array subscripts. * src/syn/xrm/XRM-MetaIf.sdf: Add meta-if at the Expression level. Correct EBNF grammar. * src/syn/xrm/XRM-MetaFor.sdf: Remove trailing whitespaces. * src/syn/xrm/XRM-Expression.sdf: Add XRMRange. This basically just a simple range but it has a different priority in the grammar than the original Range from the base grammar. It is used for array subscripts. Actually XRMRange might not be a wise name for this sorts. * tests/xrm/desugar-if.xpm: New. * tests/xrm/if-exp.xpm: New. * tests/xrm/cond-array-access.xpm: New. * tests/xrm/priorities-exp-array-subscript.xpm: New. src/str/eval-meta-code.str | 4 +- src/str/prism-desugar.str | 46 +++++++++++++++++++++++++++ src/str/xrm-front.str | 3 - src/syn/xrm/XRM-Arrays.sdf | 16 ++++----- src/syn/xrm/XRM-Expression.sdf | 27 +++++++++++++++ src/syn/xrm/XRM-MetaIf.sdf | 44 ++++++++++++++++++++++--- tests/xrm/cond-array-access.xpm | 4 ++ tests/xrm/desugar-if.xpm | 15 ++++++++ tests/xrm/if-exp.xpm | 7 ++++ tests/xrm/priorities-exp-array-subscript.xpm | 9 +++++ 10 files changed, 158 insertions(+), 17 deletions(-) Index: src/str/prism-desugar.str --- src/str/prism-desugar.str (revision 52) +++ src/str/prism-desugar.str (working copy) @@ -27,6 +27,7 @@ <+ EvalAnd <+ EvalOr <+ EvalMin <+ EvalMax <+ EvalFloor <+ EvalCeil <+ EvalPow <+ EvalMod <+ (EvalStaticRand; IntToDouble) + <+ EvalIf ) ; topdown(try(SimplifyDoubles <+ TruncateDouble)) @@ -305,6 +306,28 @@ /* ** ## ============= ## +** ## If statements ## +** ## ============= ## +*/ + +rules + + EvalIf: + |[ true ? e1 : e2 ]| -> |[ e1 ]| + + EvalIf: + |[ false ? e1 : e2 ]| -> |[ e2 ]| + + EvalIf: + |[ d ? e1 : e2 ]| -> |[ e1 ]| + where <not(compare(real-eq))>(d, 0) + + EvalIf: + |[ d ? e1 : e2 ]| -> |[ e2 ]| + where <compare(real-eq)>(d, 0) + +/* +** ## ============= ## ** ## Eval Builtins ## ** ## ============= ## ** @@ -348,3 +371,26 @@ else <modS> (i, j) => r end + +/* +** ## =========== ## +** ## Misc. stuff ## +** ## =========== ## +*/ + +rules + + LitToBool: + |[ 0 ]| -> |[ false ]| + + LitToBool: + |[ i ]| -> |[ true ]| + where <not(eq)>(i, "0") + + LitToBool: + |[ d ]| -> |[ false ]| + where <compare(real-eq)>(d, 0) + + LitToBool: + |[ d ]| -> |[ true ]| + where <not(compare(real-eq))>(d, 0) Index: src/str/eval-meta-code.str --- src/str/eval-meta-code.str (revision 52) +++ src/str/eval-meta-code.str (working copy) @@ -23,6 +23,7 @@ imports ice signatures + prism-desugar strategies @@ -38,7 +39,8 @@ ?MetaIf(condition, then-part, else-part) ///*DEBUG*/; say(!" @@@ eval-meta-if: starting:") ///*DEBUG*/; printf(|" condition = ", condition) - ; where(<prism-desugar> condition => condition-value) + ; where(<prism-desugar> condition + ; try(LitToBool) => condition-value) ///*DEBUG*/; printf(|" condition-value = ", condition-value) ; if !condition-value => True() then <eval-meta-code> then-part Index: src/str/xrm-front.str --- src/str/xrm-front.str (revision 52) +++ src/str/xrm-front.str (working copy) @@ -42,10 +42,9 @@ notice-msg(|"transformation pipeline starting") ; where(<set-random-seed> (<time>)) ; xrm-to-prism - ; dbg(|"xrm-to-prism finished") ; if must-desugar then prism-desugar - ; dbg(|"prism-desugar finished") + ; notice-msg(|"prism-desugar finished") end /** list of available options for xrm-front */ Index: src/syn/xrm/XRM-Arrays.sdf --- src/syn/xrm/XRM-Arrays.sdf (revision 52) +++ src/syn/xrm/XRM-Arrays.sdf (working copy) @@ -6,21 +6,21 @@ %% EBNF Grammar: Arrays %% ArrayAccess ::= - %% Identifier "[" Range {"," Range} "]" - %% | ArrayAccess "[" Range {"," Range} "]" + %% Identifier "[" XRMRange {"," XRMRange} "]" + %% | ArrayAccess "[" XRMRange {"," XRMRange} "]" %% %% ArrayAccessPrime ::= - %% Identifier "[" Range {"," Range} "]" "'" - %% | ArrayAccess "[" Range {"," Range} "]" "'" + %% Identifier "[" XRMRange {"," XRMRange} "]" "'" + %% | ArrayAccess "[" XRMRange {"," XRMRange} "]" "'" sorts ArrayAccess context-free syntax - Identifier "[" {Range ","}+ "]" -> ArrayAccess {cons("ArrayAccess")} - ArrayAccess "[" {Range ","}+ "]" -> ArrayAccess {cons("ArrayAccess")} + Identifier "[" {XRMRange ","}+ "]" -> ArrayAccess {cons("ArrayAccess")} + ArrayAccess "[" {XRMRange ","}+ "]" -> ArrayAccess {cons("ArrayAccess")} sorts ArrayAccessPrime context-free syntax - ArrayAccess "[" {Range ","}+ "]" "'" + ArrayAccess "[" {XRMRange ","}+ "]" "'" -> ArrayAccessPrime {cons("ArrayAccessPrime")} - Identifier "[" {Range ","}+ "]" "'" + Identifier "[" {XRMRange ","}+ "]" "'" -> ArrayAccessPrime {cons("ArrayAccessPrime")} Index: src/syn/xrm/XRM-MetaIf.sdf --- src/syn/xrm/XRM-MetaIf.sdf (revision 52) +++ src/syn/xrm/XRM-MetaIf.sdf (working copy) @@ -7,23 +7,37 @@ %% EBNF Grammar: Meta if-then-else %% (* if-then-else at top-level *) %% ModulesFileSection ::= - %% "if" Expression "then" ModulesFileSection {ModulesFileSection} "end" + %% "if" Expression "then" {ModulesFileSection} "end" %% | "if" Expression "then" - %% ModulesFileSection {ModulesFileSection} + %% {ModulesFileSection} %% "else" - %% ModulesFileSection {ModulesFileSection} + %% {ModulesFileSection} %% "end" %% %% (* if-then-else inside modules *) %% DeclarationOrCommand ::= - %% "if" Expression "then" DeclarationOrCommand {DeclarationOrCommand} "end" + %% "if" Expression "then" {DeclarationOrCommand} "end" %% | "if" Expression "then" - %% DeclarationOrCommand {DeclarationOrCommand} + %% {DeclarationOrCommand} %% "else" - %% DeclarationOrCommand {DeclarationOrCommand} + %% {DeclarationOrCommand} + %% "end" + %% + %% (* if-then-else inside expressions *) + %% (* NOTE: it's not possible to have more than 1 exp in the then-part + %% * and else-part of the meta-if statements for expression. This is + %% * because the current base and extended language don't have real + %% * statements nor sequences of expressions. *) + %% Expression ::= + %% "if" Expression "then" Expression "end" + %% | "if" Expression "then" + %% Expression + %% "else" + %% Expression %% "end" context-free syntax + %% if-then at top-level "if" Expression "then" ModulesFileSection* "end" -> ModulesFileSection {cons("MetaIf")} @@ -36,6 +50,7 @@ "end" -> ModulesFileSection {cons("MetaIf")} context-free syntax + %% if-then within modules "if" Expression "then" DeclarationOrCommand* "end" -> DeclarationOrCommand {cons("MetaIf")} @@ -46,3 +61,20 @@ "else" DeclarationOrCommand* "end" -> DeclarationOrCommand {cons("MetaIf")} + + %% NOTE: it's not possible to have more than 1 exp in the then-part + %% and else-part of the meta-if statements for expression. This is + %% because the current base and extended language don't have real + %% statements nor sequences of expressions. + context-free syntax + + %% if-then within expressions + "if" Expression "then" Expression "end" + -> Expression {cons("MetaIf")} + + %% if-then-else within expressions + "if" Expression "then" + Expression + "else" + Expression + "end" -> Expression {cons("MetaIf")} Index: src/syn/xrm/XRM-MetaFor.sdf Index: src/syn/xrm/XRM-Expression.sdf --- src/syn/xrm/XRM-Expression.sdf (revision 52) +++ src/syn/xrm/XRM-Expression.sdf (working copy) @@ -18,6 +18,9 @@ %% (* builtin functions calls using the "func" notation *) %% | "func" "(" "rand" "," Expression {"," Expression} ")" %% | "func" "(" "static_rand" "," Expression {"," Expression} ")" + %% + %% (* Ranges in XRM with different priority (for array accesses) *) + %% XRMRange ::= Expression | Expression ".." Expression context-free syntax ArrayAccess -> Expression @@ -39,6 +42,12 @@ "func" "(" "static_rand" "," {Expression ","}+ ")" -> Expression {cons("StaticRand")} + %% Ranges in XRM with different priority (for array accesses) + sorts XRMRange + context-free syntax + Expression -> XRMRange + Expression ".." Expression -> XRMRange {cons("Range")} + %% NOTE: remember: priorities are transitive in SDF. %% The following priorities are marked either with "inherited" or "new". %% The former means that these priorities are inherited from the base @@ -71,3 +80,21 @@ > { %% inherited Expression -> Range } + > { %% inherited + "!" Expression -> Expression + } + > {left: %% inherited + Expression "&" Expression -> Expression + } + > {left: %% inherited + Expression "|" Expression -> Expression + } + > { %% inherited + Expression "?" Expression ":" Expression -> Expression + } + > {non-assoc: %% new + Expression ".." Expression -> XRMRange + } + > { %% new + Expression -> XRMRange + } Index: tests/xrm/desugar-if.xpm --- tests/xrm/desugar-if.xpm (revision 0) +++ tests/xrm/desugar-if.xpm (revision 0) @@ -0,0 +1,15 @@ +if 0=1?0:2 then + const int success1 = 1; + if 0=1?0:2 then + const int success2 = 1; + if false?0:0 then + const int fail1 = 1; + else + const int success3 = 1; + end + else + const int fail2 = 1; + end +else + const int fail3 = 1; +end Index: tests/xrm/if-exp.xpm --- tests/xrm/if-exp.xpm (revision 0) +++ tests/xrm/if-exp.xpm (revision 0) @@ -0,0 +1,7 @@ +const int N = 3; +const int success = 1; + +module test + x : [if true then 0 end..if false then 0 else 42 end]; + [] x=0 -> x'=if 42 then success else -1 end; +endmodule Index: tests/xrm/cond-array-access.xpm --- tests/xrm/cond-array-access.xpm (revision 0) +++ tests/xrm/cond-array-access.xpm (revision 0) @@ -0,0 +1,4 @@ +module test + x[4] : [0..42] init 0; + [] x[-1<0?0:-1]=0 -> true; +endmodule Index: tests/xrm/priorities-exp-array-subscript.xpm --- tests/xrm/priorities-exp-array-subscript.xpm (revision 0) +++ tests/xrm/priorities-exp-array-subscript.xpm (revision 0) @@ -0,0 +1,9 @@ +module test + x[3] : bool init false; + y : bool init true; + x[4] : [0..42] init 0; + + //[] true -> x[1|1]'=true; + [] x[true?2:3]=0 -> true; + [] true -> x[0..1&1]'=true; +endmodule
7017
Age (days ago)
7017
Last active (days ago)
0 comments
1 participants
participants (1)
-
SIGOURE Benoit