From 6ffcae2eab6133c541d43399fa5f408a03c907a7 Mon Sep 17 00:00:00 2001 From: Ian Piumarta Date: Fri, 30 Sep 2022 16:23:58 +0900 Subject: [PATCH] remove is_C_keyword flag from Symbol payload; add is_C_keyword() function --- ccmeta.leg | 92 ++++++++++++++++++++++++++++++++++++------------------ 1 file changed, 61 insertions(+), 31 deletions(-) diff --git a/ccmeta.leg b/ccmeta.leg index 55b5466..647bf85 100644 --- a/ccmeta.leg +++ b/ccmeta.leg @@ -3,7 +3,7 @@ # Copyright (c) 2016-2021 Ian Piumarta and other contributors (see AUTHORS) # All rights reserved (see LICENSE) # -# Last edited: 2021-08-16 18:55:57 by piumarta on DESKTOP-GMTB276 +# Last edited: 2022-09-30 16:23:05 by piumarta on zora-10.local %{ /* compile: leg -o ccmeta.c ccmeta.leg @@ -54,22 +54,24 @@ DO_PROTOS() #undef _DO } proto_t; -#define SYMBOL_PAYLOAD proto_t prototype; int is_C_keyword; +#define SYMBOL_PAYLOAD proto_t prototype; #define DELTA 3 #include "scope.c" #include "object.c" -#define DO_C_KEYWORDS() \ - _DO(__alignof__) _DO(__alignof) _DO(asm) _DO(__asm) _DO(__asm__) _DO(__attribute__) _DO(auto) \ - _DO(_Bool) _DO(break) _DO(case) _DO(char) _DO(_Complex) _DO(const) _DO(__const) _DO(continue) \ - _DO(default) _DO(do) _DO(double) _DO(else) _DO(enum) _DO(extern) _DO(float) _DO(for) _DO(goto) \ - _DO(if) _DO(inline) _DO(int) _DO(long) _DO(register) _DO(restrict) _DO(return) _DO(short) \ - _DO(signed) _DO(sizeof) _DO(static) _DO(struct) _DO(switch) _DO(typedef) _DO(typeof) \ - _DO(__typeof__) _DO(union) _DO(unsigned) _DO(void) _DO(volatile) _DO(while) +// these MUST be in alphabetical order otherwise keywords will not be identified +#define DO_C_KEYWORDS() \ + _DO(_Bool) _DO(_Complex) _DO(__alignof) _DO(__alignof__) _DO(__asm) _DO(__asm__) _DO(__attribute__) _DO(__const) \ + _DO(__typeof__) _DO(asm) _DO(auto) _DO(break) _DO(case) _DO(char) _DO(const) _DO(continue) \ + _DO(default) _DO(do) _DO(double) _DO(else) _DO(enum) _DO(extern) _DO(float) _DO(for) \ + _DO(goto) _DO(if) _DO(inline) _DO(int) _DO(long) _DO(register) _DO(restrict) _DO(return) \ + _DO(short) _DO(signed) _DO(sizeof) _DO(static) _DO(struct) _DO(switch) _DO(typedef) _DO(typeof) \ + _DO(union) _DO(unsigned) _DO(void) _DO(volatile) _DO(while) -#define DO_C_KEYWORDS_GNU() \ - _DO(__complex__) _DO(__inline__) _DO(__imag__) _DO(__label__) _DO(__real__) +// these MUST be in alphabetical order otherwise keywords will not be identified +#define DO_GNU_KEYWORDS() \ + _DO(__complex__) _DO(__imag__) _DO(__inline__) _DO(__label__) _DO(__real__) #include @@ -668,10 +670,9 @@ void listWith(oop obj) { oop listEnd(void) { - if(isEmpty) return null; - assert(currentList); - oop list= currentList; + oop list= currentList; assert(list); currentList= OopStack_pop(&listOfLists); + if (isEmpty) return null; return list; } @@ -898,6 +899,42 @@ void error(char *source) exit(1); } +int isKeyword(char *word, char **keywords, ssize_t n) +{ + ssize_t lo = 0, hi = n - 1; + while (lo <= hi) { + ssize_t mi = (lo + hi) / 2; + char *key = keywords[mi]; + int cmp = strcmp(key, word); + if (cmp < 0) lo = mi + 1; + else if (cmp > 0) hi = mi - 1; + else return 1; + } + return 0; +} + +#define indexableSize(A) (sizeof(A) / sizeof(*(A))) + +int is_GNU_keyword(char *word) +{ + char *keywords[] = { +#define _DO(W) #W, + DO_GNU_KEYWORDS() +#undef _DO + }; + return isKeyword(word, keywords, indexableSize(keywords)); +} + +int is_C_keyword(char *word) +{ + char *keywords[] = { +#define _DO(W) #W, + DO_C_KEYWORDS() +#undef _DO + }; + return isKeyword(word, keywords, indexableSize(keywords)); +} + #define newBegin() newToken("{") #define newEnd() newToken("}") @@ -1283,7 +1320,7 @@ error = EOL* < (!EOL .)* EOL* (!EOL .)* > &{ error(yytext), 1 idOpt = id | {$$=newNullObject()} id = { $$= new_C_id(yytext) } - -ID = &{ !get(intern(yytext), Symbol, is_C_keyword) } +ID = &{ !is_C_keyword(yytext) } name = { $$= new_C_id(yytext) } - NAME = IDFIRST IDREST* @@ -2098,7 +2135,7 @@ __INLINE = '__inline' !IDREST &{gnu} { $$= newToken("__inlin _FLOAT128 = '_Float128' !IDREST &{gnu} { $$= newToken("_Float128" ) } - -#--------------------------------------------- Common rules ----------------------------------------------# +#--------------------------------------------- Common rules ----------------------------------------------# - = (blank | comment)* &{lang == META} | < Space* > &{lang == C} { if (yyleng && $$) setComment($$, newComment(yytext)) } @@ -2121,13 +2158,13 @@ Directive = "#" (!EOL .)* Any = . { ++icol } #| Meta rules -blank = space | eol -space = [ \t] -eol = ( "\n""\r"* - | "\r""\n"* - ) { inputStack->lineNumber++ } +blank = space | eol +space = [ \t] +eol = ( "\n""\r"* + | "\r""\n"* + ) { inputStack->lineNumber++ } -comment = "//" ( ![\n\r] . )* +comment = "//" ( ![\n\r] . )* | "/*" ( !"*/" (eol | .) )* "*/" #--------------------------------------------- Meta grammar ----------------------------------------------# @@ -4259,7 +4296,7 @@ void outputTree(oop node, int depth) break; #undef CASE - /** Meta nodes */ + /** Meta nodes */ #define CASE(NAME) case t_##NAME:printf("%s:\n", #NAME); CASE(Map) @@ -4334,7 +4371,7 @@ void outputTree(oop node, int depth) CASE(Logand) OUT(lhs); OUT(rhs); - break; + break; CASE(Continue) break; CASE(Bitand) @@ -4559,13 +4596,6 @@ int main(int argc, char **argv) /* File scope */ pushScope(); -#define _DO(NAME) set(intern(#NAME), Symbol, is_C_keyword, 1); - DO_C_KEYWORDS() - if(gnu) { - DO_C_KEYWORDS_GNU(); - } -#undef _DO - int repled = 0; /* Checking arguments */ while (argc-- > 1) {