aboutsummaryrefslogtreecommitdiff
path: root/lpcode.c
diff options
context:
space:
mode:
authorSergio Queiroz <sqmedeiros@gmail.com>2017-07-06 16:01:44 -0300
committerSergio Queiroz <sqmedeiros@gmail.com>2017-07-06 16:01:44 -0300
commite2a8e1c789a7a769c83a66d6fd2f191b0e465cba (patch)
treee2aecc3d439e44db98439c26cf23625da1bedb3f /lpcode.c
parenta36fe71ac0271d9013f76d9342f9a2fca40f64fc (diff)
downloadlpeglabel-e2a8e1c789a7a769c83a66d6fd2f191b0e465cba.tar.gz
lpeglabel-e2a8e1c789a7a769c83a66d6fd2f191b0e465cba.tar.bz2
lpeglabel-e2a8e1c789a7a769c83a66d6fd2f191b0e465cba.zip
Reintroducing the labeled ordered choice (tests without it passed)
Diffstat (limited to 'lpcode.c')
-rw-r--r--lpcode.c35
1 files changed, 27 insertions, 8 deletions
diff --git a/lpcode.c b/lpcode.c
index a5cf2e2..f335dcb 100644
--- a/lpcode.c
+++ b/lpcode.c
@@ -220,7 +220,7 @@ int checkaux (TTree *tree, int pred) {
220 if (checkaux(sib2(tree), pred)) return 1; 220 if (checkaux(sib2(tree), pred)) return 1;
221 /* else return checkaux(sib1(tree), pred); */ 221 /* else return checkaux(sib1(tree), pred); */
222 tree = sib1(tree); goto tailcall; 222 tree = sib1(tree); goto tailcall;
223 case TRecov: /* labeled failure */ 223 case TRecov: case TLabChoice: /* labeled failure */
224 /* we do not know whether sib2 will be evaluated */ 224 /* we do not know whether sib2 will be evaluated */
225 tree = sib1(tree); goto tailcall; 225 tree = sib1(tree); goto tailcall;
226 case TCapture: case TGrammar: case TRule: 226 case TCapture: case TGrammar: case TRule:
@@ -264,7 +264,7 @@ int fixedlen (TTree *tree) {
264 /* else return fixedlen(sib2(tree)) + len; */ 264 /* else return fixedlen(sib2(tree)) + len; */
265 len += n1; tree = sib2(tree); goto tailcall; 265 len += n1; tree = sib2(tree); goto tailcall;
266 } 266 }
267 case TChoice: { 267 case TChoice: case TLabChoice: { /* labeled failure */
268 int n1 = fixedlen(sib1(tree)); 268 int n1 = fixedlen(sib1(tree));
269 int n2 = fixedlen(sib2(tree)); 269 int n2 = fixedlen(sib2(tree));
270 if (n1 != n2 || n1 < 0) 270 if (n1 != n2 || n1 < 0)
@@ -314,7 +314,7 @@ static int getfirst (TTree *tree, const Charset *follow, Charset *firstset) {
314 loopset(i, firstset->cs[i] = follow->cs[i]); /* follow = fullset(?) */ 314 loopset(i, firstset->cs[i] = follow->cs[i]); /* follow = fullset(?) */
315 return 1; 315 return 1;
316 } 316 }
317 case TChoice: { 317 case TChoice: case TLabChoice: { /*(?) labeled failure */
318 Charset csaux; 318 Charset csaux;
319 int e1 = getfirst(sib1(tree), follow, firstset); 319 int e1 = getfirst(sib1(tree), follow, firstset);
320 int e2 = getfirst(sib2(tree), follow, &csaux); 320 int e2 = getfirst(sib2(tree), follow, &csaux);
@@ -405,7 +405,7 @@ static int headfail (TTree *tree) {
405 if (!nofail(sib2(tree))) return 0; 405 if (!nofail(sib2(tree))) return 0;
406 /* else return headfail(sib1(tree)); */ 406 /* else return headfail(sib1(tree)); */
407 tree = sib1(tree); goto tailcall; 407 tree = sib1(tree); goto tailcall;
408 case TChoice: case TRecov: /* labeled failure */ 408 case TChoice: case TRecov: case TLabChoice: /* labeled failure */
409 if (!headfail(sib1(tree))) return 0; 409 if (!headfail(sib1(tree))) return 0;
410 /* else return headfail(sib2(tree)); */ 410 /* else return headfail(sib2(tree)); */
411 tree = sib2(tree); goto tailcall; 411 tree = sib2(tree); goto tailcall;
@@ -425,7 +425,7 @@ static int needfollow (TTree *tree) {
425 case TChar: case TSet: case TAny: 425 case TChar: case TSet: case TAny:
426 case TFalse: case TTrue: case TAnd: case TNot: 426 case TFalse: case TTrue: case TAnd: case TNot:
427 case TRunTime: case TGrammar: case TCall: case TBehind: 427 case TRunTime: case TGrammar: case TCall: case TBehind:
428 case TThrow: case TRecov: /* (?)labeled failure */ 428 case TThrow: case TRecov: case TLabChoice: /* (?)labeled failure */
429 return 0; 429 return 0;
430 case TChoice: case TRep: 430 case TChoice: case TRep:
431 return 1; 431 return 1;
@@ -460,7 +460,7 @@ int sizei (const Instruction *i) {
460 return 2; 460 return 2;
461 case IThrow: /* labeled failure */ 461 case IThrow: /* labeled failure */
462 return 1; 462 return 1;
463 case IRecov: 463 case IRecov: case ILabChoice:
464 return (CHARSETINSTSIZE - 1) + 2; /* labeled failure */ 464 return (CHARSETINSTSIZE - 1) + 2; /* labeled failure */
465 465
466 default: return 1; 466 default: return 1;
@@ -527,7 +527,7 @@ static int addoffsetinst (CompileState *compst, Opcode op) {
527 int i = addinstruction(compst, op, 0); /* instruction */ 527 int i = addinstruction(compst, op, 0); /* instruction */
528 addinstruction(compst, (Opcode)0, 0); /* open space for offset */ 528 addinstruction(compst, (Opcode)0, 0); /* open space for offset */
529 assert(op == ITestSet || sizei(&getinstr(compst, i)) == 2 || 529 assert(op == ITestSet || sizei(&getinstr(compst, i)) == 2 ||
530 op == IRecov); /* labeled failure */ 530 op == IRecov || op == ILabChoice); /* labeled failure */
531 return i; 531 return i;
532} 532}
533 533
@@ -750,6 +750,21 @@ static void coderecovery (CompileState *compst, TTree *p1, TTree *p2, int opt,
750 addinstruction(compst, IRet, 0); 750 addinstruction(compst, IRet, 0);
751 jumptohere(compst, pcommit); 751 jumptohere(compst, pcommit);
752} 752}
753
754static void codelabchoice (CompileState *compst, TTree *p1, TTree *p2, int opt,
755 const Charset *fl, const byte *cs) {
756 int emptyp2 = (p2->tag == TTrue);
757 int pcommit;
758 int test = NOINST;
759 int pchoice = addoffsetinst(compst, ILabChoice);
760 addcharset(compst, cs);
761 codegen(compst, p1, emptyp2, test, fullset);
762 pcommit = addoffsetinst(compst, ICommit);
763 jumptohere(compst, pchoice);
764 jumptohere(compst, test);
765 codegen(compst, p2, opt, NOINST, fl);
766 jumptohere(compst, pcommit);
767}
753/* labeled failure end */ 768/* labeled failure end */
754 769
755 770
@@ -988,6 +1003,10 @@ static void codegen (CompileState *compst, TTree *tree, int opt, int tt,
988 coderecovery(compst, sib1(tree), sib2(tree), opt, fl, treelabelset(tree)); 1003 coderecovery(compst, sib1(tree), sib2(tree), opt, fl, treelabelset(tree));
989 break; 1004 break;
990 } 1005 }
1006 case TLabChoice: { /* labeled failure */
1007 codelabchoice(compst, sib1(tree), sib2(tree), opt, fl, treelabelset(tree));
1008 break;
1009 }
991 default: assert(0); 1010 default: assert(0);
992 } 1011 }
993} 1012}
@@ -1010,7 +1029,7 @@ static void peephole (CompileState *compst) {
1010 switch (code[i].i.code) { 1029 switch (code[i].i.code) {
1011 case IChoice: case ICall: case ICommit: case IPartialCommit: 1030 case IChoice: case ICall: case ICommit: case IPartialCommit:
1012 case IBackCommit: case ITestChar: case ITestSet: 1031 case IBackCommit: case ITestChar: case ITestSet:
1013 case IRecov: /* labeled failure */ 1032 case IRecov: case ILabChoice: /* labeled failure */
1014 case ITestAny: { /* instructions with labels */ 1033 case ITestAny: { /* instructions with labels */
1015 jumptothere(compst, i, finallabel(code, i)); /* optimize label */ 1034 jumptothere(compst, i, finallabel(code, i)); /* optimize label */
1016 break; 1035 break;