static void desugar_sequence(HAllocator *mm__, HCFStack *stk__, void *env) { HSequence *s = (HSequence*)env; HCFS_BEGIN_CHOICE() { HCFS_BEGIN_SEQ() { for (size_t i = 0; i < s->len; i++) HCFS_DESUGAR(s->p_array[i]); } HCFS_END_SEQ(); HCFS_THIS_CHOICE->reshape = reshape_sequence; } HCFS_END_CHOICE(); }
static void desugar_whitespace(HAllocator *mm__, HCFStack *stk__, void *env) { HCharset ws_cs = new_charset(mm__); for(size_t i=0; i<sizeof(SPACE_CHRS); i++) charset_set(ws_cs, SPACE_CHRS[i], 1); HCFS_BEGIN_CHOICE() { HCFS_BEGIN_SEQ() { HCFS_BEGIN_CHOICE() { HCFS_BEGIN_SEQ() { HCFS_ADD_CHARSET(ws_cs); HCFS_APPEND(HCFS_THIS_CHOICE); // yay circular pointer! } HCFS_END_SEQ(); HCFS_BEGIN_SEQ() { } HCFS_END_SEQ(); } HCFS_END_CHOICE(); HCFS_DESUGAR( (HParser*)env ); } HCFS_END_SEQ(); HCFS_THIS_CHOICE->reshape = h_act_last; } HCFS_END_CHOICE(); }
static void desugar_action(HAllocator *mm__, HCFStack *stk__, void *env) { HParseAction *a = (HParseAction*)env; HCFS_BEGIN_CHOICE() { HCFS_BEGIN_SEQ() { HCFS_DESUGAR(a->p); } HCFS_END_SEQ(); HCFS_THIS_CHOICE->user_data = a->user_data; HCFS_THIS_CHOICE->action = a->action; HCFS_THIS_CHOICE->reshape = h_act_first; } HCFS_END_CHOICE(); }
// desugar parser with a fresh start symbol // this guarantees that the start symbol will not occur in any productions HCFChoice *h_desugar_augmented(HAllocator *mm__, HParser *parser) { HCFChoice *augmented = h_new(HCFChoice, 1); HCFStack *stk__ = h_cfstack_new(mm__); stk__->prealloc = augmented; HCFS_BEGIN_CHOICE() { HCFS_BEGIN_SEQ() { HCFS_DESUGAR(parser); } HCFS_END_SEQ(); HCFS_THIS_CHOICE->reshape = h_act_first; } HCFS_END_CHOICE(); h_cfstack_free(mm__, stk__); return augmented; }
static void desugar_optional(HAllocator *mm__, HCFStack *stk__, void *env) { HParser *p = (HParser*) env; /* optional(A) => S -> A -> \epsilon */ HCFS_BEGIN_CHOICE() { HCFS_BEGIN_SEQ() { HCFS_DESUGAR(p); } HCFS_END_SEQ(); HCFS_BEGIN_SEQ() { } HCFS_END_SEQ(); HCFS_THIS_CHOICE->reshape = reshape_optional; HCFS_THIS_CHOICE->user_data = NULL; } HCFS_END_CHOICE(); }
static void desugar_ignoreseq(HAllocator *mm__, HCFStack *stk__, void *env) { HIgnoreSeq *seq = (HIgnoreSeq*)env; HCFS_BEGIN_CHOICE() { HCFS_BEGIN_SEQ() { for (size_t i=0; i<seq->len; ++i) HCFS_DESUGAR(seq->parsers[i]); } HCFS_END_SEQ(); if(seq->which == 0) HCFS_THIS_CHOICE->reshape = h_act_first; else if(seq->which == 1) HCFS_THIS_CHOICE->reshape = h_act_second; // for h_middle else if(seq->which == seq->len-1) HCFS_THIS_CHOICE->reshape = h_act_last; else assert(!"Ignoreseq must select item 0, 1, or n-1"); } HCFS_END_CHOICE(); }