diff options
author | Peter Mikkelsen <peter@pmikkelsen.com> | 2021-06-29 17:51:20 +0000 |
---|---|---|
committer | Peter Mikkelsen <peter@pmikkelsen.com> | 2021-06-29 17:51:20 +0000 |
commit | 6ae2e2bb7bebdc3f4d450f1ddc6c69a02c3f4998 (patch) | |
tree | 303dec4cb3ead70d4e108d0138c561d65d660268 /parser.c | |
parent | 2d7f3ffa770b6eb698566b6566d7e37f10193744 (diff) |
Parse lists and {a,b,c} syntax (What is this even called?)
Diffstat (limited to 'parser.c')
-rw-r--r-- | parser.c | 47 |
1 files changed, 45 insertions, 2 deletions
@@ -59,7 +59,8 @@ enum { CurlyBracketLeftTok = 1<<10, /* 1024 */ CurlyBracketRightTok = 1<<11, /* 2048 */ CommaTok = 1<<12, /* 4096 */ - EofTok = 1<<13, /* 8192 */ + PipeTok = 1<<13, /* 8192 */ + EofTok = 1<<14, /* 16384 */ }; static Biobuf *parsein; @@ -72,6 +73,8 @@ Operator *getoperator(Rune *); void nexttoken(void); Term *fullterm(int, Rune *, Term *); Term *term(void); +Term *listterm(int); +Term *curlybracketterm(void); Term *compound(void); Term *parseoperators(Term *); void match(int); @@ -162,6 +165,12 @@ term(void) result = mkatom(L","); match(CommaTok); break; + case SquareBracketLeftTok: + result = listterm(1); + break; + case CurlyBracketLeftTok: + result = curlybracketterm(); + break; default: print("Cant parse term of token type %d\n", lookahead.tag); syntaxerror("term"); @@ -172,6 +181,38 @@ term(void) } Term * +listterm(int start) +{ + if(start) + match(SquareBracketLeftTok); + + if(lookahead.tag == SquareBracketRightTok){ + match(SquareBracketRightTok); + return mkatom(L"[]"); + }else if(lookahead.tag == PipeTok){ + match(PipeTok); + Term *t = fullterm(SquareBracketRightTok, nil, nil); + match(SquareBracketRightTok); + return t; + }else{ + Term *t = fullterm(CommaTok|PipeTok|SquareBracketRightTok, nil, nil); + if(lookahead.tag == CommaTok) + match(CommaTok); + t->next = listterm(0); + return mkcompound(L".", 2, t); + } +} + +Term * +curlybracketterm(void) +{ + match(CurlyBracketLeftTok); + Term *result = fullterm(CurlyBracketRightTok, nil, nil); + match(CurlyBracketRightTok); + return mkcompound(L"{}", 1, result); +} + +Term * compound(void) { Rune *name = lookahead.text; @@ -368,6 +409,7 @@ nexttoken(void) if(peek == L'%'){ while(peek != L'\n') peek = Bgetrune(parsein); + Bgetrune(parsein); peek = Bgetrune(parsein); } @@ -520,13 +562,14 @@ Integer: } /* Other */ - if(runestrchr(L",.()]}", peek)){ + if(runestrchr(L",.()]}|", peek)){ switch(peek){ case L',': lookahead.tag = CommaTok; break; case L'(': lookahead.tag = ParenLeftTok; break; case L')': lookahead.tag = ParenRightTok; break; case L']': lookahead.tag = SquareBracketRightTok; break; case L'}': lookahead.tag = CurlyBracketRightTok; break; + case L'|': lookahead.tag = PipeTok; break; } return; } |