ack/lang/m2/comp/statement.g

227 lines
4.4 KiB
Plaintext
Raw Normal View History

1986-03-26 15:11:02 +00:00
/* S T A T E M E N T S */
1986-03-20 14:52:03 +00:00
{
static char *RcsId = "$Header$";
1986-04-06 17:42:56 +00:00
#include <em_arith.h>
1986-04-17 09:28:09 +00:00
#include <em_label.h>
1986-04-22 22:36:16 +00:00
#include "idf.h"
1986-04-06 17:42:56 +00:00
#include "LLlex.h"
1986-04-22 22:36:16 +00:00
#include "scope.h"
#include "def.h"
1986-04-17 09:28:09 +00:00
#include "type.h"
1986-04-06 17:42:56 +00:00
#include "node.h"
1986-04-15 17:51:53 +00:00
static int loopcount = 0; /* Count nested loops */
1986-04-22 22:36:16 +00:00
extern struct def *currentdef;
1986-03-20 14:52:03 +00:00
}
1986-04-15 17:51:53 +00:00
statement(struct node **pnd;)
1986-04-06 17:42:56 +00:00
{
1986-04-17 09:28:09 +00:00
register struct node *nd;
1986-04-06 17:42:56 +00:00
} :
1986-04-15 17:51:53 +00:00
{ *pnd = 0; }
1986-03-20 14:52:03 +00:00
[
/*
* This part is not in the reference grammar. The reference grammar
* states : assignment | ProcedureCall | ...
* but this gives LL(1) conflicts
*/
1986-04-17 09:28:09 +00:00
designator(pnd)
[ { nd = MkNode(Call, *pnd, NULLNODE, &dot);
nd->nd_symb = '(';
1986-04-09 18:14:49 +00:00
}
1986-04-17 09:28:09 +00:00
ActualParameters(&(nd->nd_right))?
1986-03-20 14:52:03 +00:00
|
1986-04-17 09:28:09 +00:00
BECOMES { nd = MkNode(Stat, *pnd, NULLNODE, &dot); }
expression(&(nd->nd_right))
1986-03-20 14:52:03 +00:00
]
1986-04-17 09:28:09 +00:00
{ *pnd = nd; }
1986-03-20 14:52:03 +00:00
/*
* end of changed part
*/
|
1986-04-15 17:51:53 +00:00
IfStatement(pnd)
1986-03-20 14:52:03 +00:00
|
1986-04-15 17:51:53 +00:00
CaseStatement(pnd)
1986-03-20 14:52:03 +00:00
|
1986-04-15 17:51:53 +00:00
WhileStatement(pnd)
1986-03-20 14:52:03 +00:00
|
1986-04-15 17:51:53 +00:00
RepeatStatement(pnd)
1986-03-20 14:52:03 +00:00
|
1986-04-15 17:51:53 +00:00
{ loopcount++; }
LoopStatement(pnd)
{ loopcount--; }
1986-03-20 14:52:03 +00:00
|
1986-04-15 17:51:53 +00:00
ForStatement(pnd)
1986-03-20 14:52:03 +00:00
|
1986-04-15 17:51:53 +00:00
WithStatement(pnd)
1986-03-20 14:52:03 +00:00
|
EXIT
1986-04-15 17:51:53 +00:00
{ if (!loopcount) {
1986-04-22 22:36:16 +00:00
error("EXIT not in a LOOP");
1986-04-15 17:51:53 +00:00
}
*pnd = MkNode(Stat, NULLNODE, NULLNODE, &dot);
}
1986-03-20 14:52:03 +00:00
|
1986-04-17 09:28:09 +00:00
RETURN { *pnd = nd = MkNode(Stat, NULLNODE, NULLNODE, &dot); }
1986-04-06 17:42:56 +00:00
[
1986-04-17 09:28:09 +00:00
expression(&(nd->nd_right))
1986-04-22 22:36:16 +00:00
{ if (scopeclosed(CurrentScope)) {
error("a module body has no result value");
}
else if (! currentdef->df_type->next) {
error("procedure \"%s\" has no result value", currentdef->df_idf->id_text);
}
}
1986-04-23 22:12:22 +00:00
|
{ if (currentdef->df_type->next) {
error("procedure \"%s\" must return a value", currentdef->df_idf->id_text);
}
}
]
1986-03-20 14:52:03 +00:00
]?
;
/*
* The next two rules in-line in "Statement", because of an LL(1) conflict
assignment:
designator BECOMES expression
;
ProcedureCall:
designator ActualParameters?
;
*/
1986-04-15 17:51:53 +00:00
StatementSequence(struct node **pnd;):
statement(pnd)
[
';' { *pnd = MkNode(Link, *pnd, NULLNODE, &dot);
pnd = &((*pnd)->nd_right);
}
statement(pnd)
]*
1986-03-20 14:52:03 +00:00
;
1986-04-15 17:51:53 +00:00
IfStatement(struct node **pnd;)
1986-04-06 17:42:56 +00:00
{
1986-04-15 17:51:53 +00:00
register struct node *nd;
1986-04-06 17:42:56 +00:00
} :
1986-04-15 17:51:53 +00:00
IF { nd = MkNode(Stat, NULLNODE, NULLNODE, &dot);
*pnd = nd;
}
expression(&(nd->nd_left))
THEN { nd = MkNode(Link, NULLNODE, NULLNODE, &dot);
(*pnd)->nd_right = nd;
}
StatementSequence(&(nd->nd_left))
[
ELSIF { nd->nd_right = MkNode(Stat,NULLNODE,NULLNODE,&dot);
nd = nd->nd_right;
nd->nd_symb = IF;
}
expression(&(nd->nd_left))
THEN { nd->nd_right = MkNode(Link,NULLNODE,NULLNODE,&dot);
nd = nd->nd_right;
}
StatementSequence(&(nd->nd_left))
]*
[
ELSE
StatementSequence(&(nd->nd_right))
]?
1986-03-20 14:52:03 +00:00
END
;
1986-04-15 17:51:53 +00:00
CaseStatement(struct node **pnd;)
1986-04-06 17:42:56 +00:00
{
1986-04-15 17:51:53 +00:00
register struct node *nd;
struct type *tp = 0;
1986-04-06 17:42:56 +00:00
} :
1986-04-15 17:51:53 +00:00
CASE { *pnd = nd = MkNode(Stat, NULLNODE, NULLNODE, &dot); }
expression(&(nd->nd_left))
OF
case(&(nd->nd_right), &tp)
{ nd = nd->nd_right; }
[
'|'
case(&(nd->nd_right), &tp)
{ nd = nd->nd_right; }
]*
[ ELSE StatementSequence(&(nd->nd_right)) ]?
1986-03-20 14:52:03 +00:00
END
;
1986-04-15 17:51:53 +00:00
case(struct node **pnd; struct type **ptp;) :
{ *pnd = 0; }
1986-04-17 09:28:09 +00:00
[ CaseLabelList(ptp, pnd)
1986-04-15 17:51:53 +00:00
':' { *pnd = MkNode(Link, *pnd, NULLNODE, &dot); }
StatementSequence(&((*pnd)->nd_right))
]?
1986-03-20 14:52:03 +00:00
/* This rule is changed in new modula-2 */
1986-04-15 17:51:53 +00:00
{ *pnd = MkNode(Link, *pnd, NULLNODE, &dot);
(*pnd)->nd_symb = '|';
}
1986-03-20 14:52:03 +00:00
;
1986-04-15 17:51:53 +00:00
WhileStatement(struct node **pnd;)
1986-04-06 17:42:56 +00:00
{
1986-04-15 17:51:53 +00:00
register struct node *nd;
1986-04-06 17:42:56 +00:00
}:
1986-04-15 17:51:53 +00:00
WHILE { *pnd = nd = MkNode(Stat, NULLNODE, NULLNODE, &dot); }
expression(&(nd->nd_left))
DO
StatementSequence(&(nd->nd_right))
END
1986-03-20 14:52:03 +00:00
;
1986-04-15 17:51:53 +00:00
RepeatStatement(struct node **pnd;)
1986-04-06 17:42:56 +00:00
{
1986-04-15 17:51:53 +00:00
register struct node *nd;
1986-04-06 17:42:56 +00:00
}:
1986-04-15 17:51:53 +00:00
REPEAT { *pnd = nd = MkNode(Stat, NULLNODE, NULLNODE, &dot); }
StatementSequence(&(nd->nd_left))
UNTIL
expression(&(nd->nd_right))
1986-03-20 14:52:03 +00:00
;
1986-04-15 17:51:53 +00:00
ForStatement(struct node **pnd;)
1986-04-06 17:42:56 +00:00
{
1986-04-15 17:51:53 +00:00
register struct node *nd;
1986-04-06 17:42:56 +00:00
}:
1986-04-15 17:51:53 +00:00
FOR { *pnd = MkNode(Stat, NULLNODE, NULLNODE, &dot); }
IDENT { nd = MkNode(Name, NULLNODE, NULLNODE, &dot); }
BECOMES { nd = MkNode(BECOMES, nd, NULLNODE, &dot); }
expression(&(nd->nd_right))
TO { (*pnd)->nd_left=nd=MkNode(Link,nd,NULLNODE,&dot); }
expression(&(nd->nd_right))
[
BY { nd->nd_right=MkNode(Link,NULLNODE,nd->nd_right,&dot);
}
ConstExpression(&(nd->nd_right->nd_left))
|
]
DO
StatementSequence(&((*pnd)->nd_right))
END
1986-03-20 14:52:03 +00:00
;
1986-04-15 17:51:53 +00:00
LoopStatement(struct node **pnd;):
LOOP { *pnd = MkNode(Stat, NULLNODE, NULLNODE, &dot); }
StatementSequence(&((*pnd)->nd_right))
END
1986-03-20 14:52:03 +00:00
;
1986-04-15 17:51:53 +00:00
WithStatement(struct node **pnd;)
1986-04-06 17:42:56 +00:00
{
1986-04-15 17:51:53 +00:00
register struct node *nd;
1986-04-06 17:42:56 +00:00
}:
1986-04-15 17:51:53 +00:00
WITH { *pnd = nd = MkNode(Stat, NULLNODE, NULLNODE, &dot); }
designator(&(nd->nd_left))
DO
StatementSequence(&(nd->nd_right))
END
1986-03-20 14:52:03 +00:00
;