소스 검색

Add Throw mechanism and hierarchy in verbose mode

master
mtardy 4 년 전
부모
커밋
d9364885fe
1개의 변경된 파일98개의 추가작업 그리고 39개의 파일을 삭제
  1. +98
    -39
      parse.leg

+ 98
- 39
parse.leg 파일 보기

@ -18,7 +18,7 @@
_DO(PreDecVariable) _DO(PreDecMember) _DO(PreDecIndex) \
_DO(PostDecVariable) _DO(PostDecMember) _DO(PostDecIndex) \
_DO(GetVariable) _DO(GetMember) _DO(SetMember) _DO(GetIndex) _DO(SetIndex) \
_DO(Return) _DO(Break) _DO(Continue) \
_DO(Return) _DO(Break) _DO(Continue) _DO(Throw) \
_DO(Quasiquote) _DO(Unquote)
typedef enum {
@ -38,6 +38,7 @@ enum jb_t {
j_return = 1,
j_break,
j_continue,
j_throw,
};
typedef struct jb_record
@ -49,14 +50,6 @@ typedef struct jb_record
jb_record *jbs= NULL;
void jbsCheck(char *msg)
{
if (NULL == jbs) {
fprintf(stderr, "\n%s\n", msg);
exit(1);
}
}
jb_record *jbRecPush() {
jb_record *newJbRec = memcheck(malloc(sizeof(jb_record)));
newJbRec->result = null;
@ -607,10 +600,11 @@ exp = VAR l:ident ASSIGN e:exp { $$ = newDeclarati
| DO s:stmt WHILE LPAREN c:exp RPAREN { $$ = newDo(s, c) }
| FOR LPAREN i:stmt c:stmt u:exp RPAREN s:stmt { $$ = newFor(i, c, u, s) }
| s:switch { $$ = s }
| RETURN e:exp { $$ = newReturn(e) }
| RETURN e:exp { $$ = newReturn(e) }
| RETURN { $$ = newReturn(null) }
| BREAK { $$ = newBreak() }
| CONTINUE { $$ = newContinue() }
| THROW e:exp { $$ = newUnary(Throw_proto, e) }
| l:IDENT o:assignOp e:exp { $$ = newAssign(Assign_proto, l, o, e) }
| l:postfix DOT i:IDENT o:assignOp e:exp { $$ = newSetMap(SetMember_proto, l, i, o, e) }
| l:postfix LBRAC i:exp RBRAC o:assignOp e:exp { $$ = newSetMap(SetIndex_proto, l, i, o, e) }
@ -772,7 +766,7 @@ eol = ( "\n""\r"*
comment = "//" ( ![\n\r] . )*
| "/*" ( !"*/" . )* "*/"
keyword = FUN | SYNTAX | VAR | SWITCH | CASE | DEFAULT | DO | FOR | WHILE | IF | ELSE | NULL | RETURN | BREAK | CONTINUE
keyword = FUN | SYNTAX | VAR | SWITCH | CASE | DEFAULT | DO | FOR | WHILE | IF | ELSE | NULL | RETURN | BREAK | CONTINUE | THROW
IDENT = !keyword < [a-zA-Z_][a-zA-Z0-9_]* > - { $$ = intern(yytext) }
@ -797,6 +791,7 @@ NULL = 'null' ![a-zA-Z0-9_] -
RETURN = 'return' ![a-zA-Z0-9_] -
BREAK = 'break' ![a-zA-Z0-9_] -
CONTINUE = 'continue' ![a-zA-Z0-9_] -
THROW = 'throw' ![a-zA-Z0-9_] -
IMPORT = 'import' ![a-zA-Z0-9_] -
HASH = '#' -
LOGOR = '||' -
@ -1029,7 +1024,7 @@ oop evalArgs(oop scope, oop args);
oop eval(oop scope, oop ast)
{
if (opt_v) {
if (opt_v > 3) {
printf("EVAL: ");
println(ast);
}
@ -1094,12 +1089,13 @@ oop eval(oop scope, oop ast)
jbRecPush();
int jbt = sigsetjmp(jbs->jb, 0);
switch (jbt) {
case j_return: {
case j_return:
case j_throw: {
oop result = jbs->result;
jbRecPop();
jbsCheck("return outside a function");
assert(jbs);
jbs->result = result;
siglongjmp(jbs->jb, j_return);
siglongjmp(jbs->jb, jbt);
assert(0);
}
case j_break: {
@ -1123,12 +1119,13 @@ oop eval(oop scope, oop ast)
jbRecPush();
int jbt = sigsetjmp(jbs->jb, 0);
switch (jbt) {
case j_return: {
case j_return:
case j_throw: {
oop result = jbs->result;
jbRecPop();
jbsCheck("return outside a function");
assert(jbs);
jbs->result = result;
siglongjmp(jbs->jb, j_return);
siglongjmp(jbs->jb, jbt);
assert(0);
}
case j_break: {
@ -1158,12 +1155,13 @@ oop eval(oop scope, oop ast)
jbRecPush();
int jbt = sigsetjmp(jbs->jb, 0);
switch (jbt) {
case j_return: {
case j_return:
case j_throw: {
oop result = jbs->result;
jbRecPop();
jbsCheck("return outside a function");
assert(jbs);
jbs->result = result;
siglongjmp(jbs->jb, j_return);
siglongjmp(jbs->jb, jbt);
assert(0);
}
case j_break: {
@ -1179,6 +1177,7 @@ oop eval(oop scope, oop ast)
result= eval(localScope, body);
restart_for:;
}
jbRecPop();
return result;
}
case t_Switch: {
@ -1195,12 +1194,13 @@ oop eval(oop scope, oop ast)
jbRecPush();
int jbt = sigsetjmp(jbs->jb, 0);
switch (jbt) {
case j_return: {
case j_return:
case j_throw: {
oop result = jbs->result;
jbRecPop();
jbsCheck("return outside a function");
assert(jbs);
jbs->result = result;
siglongjmp(jbs->jb, j_return);
siglongjmp(jbs->jb, jbt);
assert(0);
}
case j_break: {
@ -1209,7 +1209,7 @@ oop eval(oop scope, oop ast)
}
case j_continue: {
jbRecPop();
jbsCheck("continue outside a loop");
assert(jbs);
siglongjmp(jbs->jb, j_continue);
assert(0);
}
@ -1219,6 +1219,7 @@ oop eval(oop scope, oop ast)
assert(map_hasIntegerKey(statements, i));
result= eval(scope, get(statements, Map, elements)[i].value);
}
jbRecPop();
return result;
}
case t_Assign: {
@ -1238,7 +1239,7 @@ oop eval(oop scope, oop ast)
oop body = map_get(ast, body_symbol);
oop fixed = map_get(ast, fixed_symbol);
oop func = makeFunction(NULL, name, param, body, scope, fixed);
if (opt_v) {
if (opt_v > 4) {
printf("funcscope: ");
println(scope);
printf("globalScope: ");
@ -1264,7 +1265,7 @@ oop eval(oop scope, oop ast)
oop localScope = map_zip(param, args);
map_set(localScope, __arguments___symbol, args);
map_set(localScope, __proto___symbol, get(func, Function, parentScope));
if (opt_v) {
if (opt_v > 4) {
printf("parentScope: ");
println(get(func, Function, parentScope));
printf("localScope: ");
@ -1287,6 +1288,12 @@ oop eval(oop scope, oop ast)
fprintf(stderr, "\ncontinue outside of a loop\n");
exit(1);
}
case j_throw: {
oop res= jbs->result;
jbRecPop();
jbs->result= res;
siglongjmp(jbs->jb, j_throw);
}
}
oop result = eval(localScope, get(func, Function, body));
@ -1315,7 +1322,7 @@ oop eval(oop scope, oop ast)
map_set(localScope, this_symbol, this);
map_set(localScope, __arguments___symbol, args);
map_set(localScope, __proto___symbol, get(func, Function, parentScope));
if (opt_v) {
if (opt_v > 4) {
printf("parentScope: ");
println(get(func, Function, parentScope));
printf("localScope: ");
@ -1338,6 +1345,12 @@ oop eval(oop scope, oop ast)
fprintf(stderr, "\ncontinue outside of a loop\n");
exit(1);
}
case j_throw: {
oop res= jbs->result;
jbRecPop();
jbs->result= res;
siglongjmp(jbs->jb, j_throw);
}
}
oop result = eval(localScope, get(func, Function, body));
@ -1346,18 +1359,23 @@ oop eval(oop scope, oop ast)
}
case t_Return: {
jbsCheck("return outside a function");
assert(jbs);
jbs->result = eval(scope, map_get(ast, value_symbol));
siglongjmp(jbs->jb, j_return);
}
case t_Break: {
jbsCheck("break outside a loop");
assert(jbs);
siglongjmp(jbs->jb, j_break);
}
case t_Continue: {
jbsCheck("continue outside a loop");
assert(jbs);
siglongjmp(jbs->jb, j_continue);
}
case t_Throw: {
assert(jbs);
jbs->result = eval(scope, map_get(ast, rhs_symbol));
siglongjmp(jbs->jb, j_throw);
}
case t_Block: {
oop statements = map_get(ast, statements_symbol);
int i = 0;
@ -1664,6 +1682,12 @@ oop prim_invoke(oop params)
fprintf(stderr, "\ncontinue outside of a loop\n");
exit(1);
}
case j_throw: {
oop res= jbs->result;
jbRecPop();
jbs->result= res;
siglongjmp(jbs->jb, j_throw);
}
}
oop result= eval(localScope, get(func, Function, body));
jbRecPop();
@ -1700,6 +1724,12 @@ oop apply(oop func, oop args)
fprintf(stderr, "\ncontinue outside of a loop\n");
exit(1);
}
case j_throw: {
oop res= jbs->result;
jbRecPop();
jbs->result= res;
siglongjmp(jbs->jb, j_throw);
}
}
oop result= eval(localScope, get(func, Function, body));
jbRecPop();
@ -1743,15 +1773,44 @@ oop AST= NULL;
void readEvalPrint(char *fileName) {
inputStackPush(fileName);
jbRecPush();
jb_record *jtop= jbs;
int jbt= sigsetjmp(jbs->jb, 0);
if (0 == jbt) {
while (inputStack && yyparse()) {
if (opt_v > 1) printf("%s:%i: ", inputStack->name, inputStack->lineNumber);
if (!yylval) {
fclose(inputStack->file);
inputStackPop();
continue;
} // EOF
if (opt_v > 1) println(yylval);
oop res = eval(globals, yylval);
if (opt_v > 0) println(res);
assert(jbs == jtop);
}
jbRecPop();
return;
}
while (inputStack && yyparse()) {
if (!yylval) {
fclose(inputStack->file);
inputStackPop();
continue;
} // EOF
if (opt_v) println(yylval);
println(eval(globals, yylval));
assert(jbs == jtop);
oop res = jbs->result;
jbRecPop();
switch (jbt) {
case j_return:
fprintf(stderr, "\nreturn outside of a function\n");
exit(1);
case j_break:
fprintf(stderr, "\nbreak outside of a loop or switch\n");
exit(1);
case j_continue:
fprintf(stderr, "\ncontinue outside of a loop\n");
exit(1);
case j_throw:
printf("\nunhandled exception: ");
println(res);
exit(1);
}
}

불러오는 중...
취소
저장