sheepy

build system (sheepy) and package manager (spm) for C
git clone https://spartatek.se/git/sheepy.git
Log | Files | Refs | README | LICENSE

parser.c (23216B)


      1 // TO READ THIS FILE:
      2 // see grammar.txt
      3 // see the stateFt STATEF[FINAL] array
      4 // and see the functions
      5 
      6 #include "parser.h"
      7 
      8 // TODO remove global variables to be able to run multithreaded
      9 int stateM = IDLE;
     10 
     11 smallArrayt *generatedC = NULL;
     12 smallArrayt *sheepyC    = NULL;
     13 smallArrayt *stateStack = NULL;
     14 smallArrayt *textStack  = NULL;
     15 
     16 char *STATESSTR[FINAL] = {
     17 	"IDLE",
     18 	"TYPE",
     19 	"TYPEID",
     20 	"POINTERTYPE",
     21 	"TYPEINIT",
     22 	"TYPEINITSTR",
     23 	"TYPEEND",
     24 	"CONST_",
     25 	"EXTERN_",
     26 	"VOLATILE_",
     27 	"STATIC_",
     28 	"UNSIGNED_",
     29 	"SIGNED_",
     30 	"ENUM_",
     31 	"ENUM_END",
     32 	"TYPEDEF_",
     33 	"TDSTRUCT",
     34 	"STRUCTBLOCK",
     35 	"STRUCTINBLOCK",
     36 	"UNIONINSTRUCT",
     37 	"STRUCTTYPE",
     38 	"STRUCTTYPEID",
     39 	"STRUCTTYPEEND",
     40 	"STRUCTID",
     41 	"STRUCTBLOCKEND",
     42 	"UNIONBLOCK",
     43 	"STRUCTINUNION",
     44 	"UNIONINBLOCK",
     45 	"UNIONTYPE",
     46 	"UNIONTYPEID",
     47 	"UNIONTYPEEND",
     48 	"UNIONID",
     49 	"UNIONBLOCKEND",
     50 	"FUNCOPEN",
     51 	"FUNCCLOSE",
     52 	"PROTOTYPE",
     53 	"CODEBLOCK",
     54 	"CONTINUE_",
     55 	"CODEBLOCKID",
     56 	"CALL",
     57 	"CALLSTR",
     58 	"CALLCLOSE",
     59 	"CALLEND",
     60 	"CALLENDNPOP",
     61 	"INCREMENT",
     62 	"GOTO_",
     63 	"GOTO_ID",
     64 	"GOTO_END",
     65 	"GOTO_ENDNPOP",
     66 	"COLON",
     67 	"COLONEND",
     68 	"ARRAYINDEX",
     69 	"ARRAYINDEXEND",
     70 	"ASSIGNMENT",
     71 	"NUMBER",
     72 	"ASSIGNID",
     73 	"QUOTED_CHAR",
     74 	"QUOTED_CHAR_SEMICOLON",
     75 	"SIZEOF_",
     76 	"IF_",
     77 	"ELSE_",
     78 	"FOR_",
     79 	"DO_",
     80 	"SWITCH_",
     81 	"SWITCH_BLOCK",
     82 	"CASE_",
     83 	"CASE_ID",
     84 	"CASE_BLOCK",
     85 	"BREAK_",
     86 	"SWITCH_BLOCKEND",
     87 	"RETURN_",
     88 	"RETURN_STR",
     89 	"RETURN_END",
     90 	"CODEBLOCKEND",
     91 	"DO_END",
     92 	"DO_FOR",
     93 	"DO_CLOSE",
     94 	"USE",
     95 	"USEID",
     96 	"USEDOT",
     97 	"USECOMMA",
     98 	"USEEND",
     99 };
    100 
    101 // extra -1 -1 to run a default function when a token is not found
    102 int STATES[FINAL][TRANSITIONS*2] = {
    103 /*IDLE*/ {QUEX_TKN_PP_USE, USE, QUEX_TKN_CONST, CONST_, QUEX_TKN_TYPE_INT, TYPE, QUEX_TKN_TYPE_VOID, TYPE, QUEX_TKN_EXTERN, EXTERN_, QUEX_TKN_ENUM, ENUM_, QUEX_TKN_TYPE, TYPEDEF_, -1, -1},
    104 /*TYPE*/ {QUEX_TKN_IDENTIFIER, TYPEID, QUEX_TKN_MULT, POINTERTYPE, -1, -1},
    105 /*TYPEID*/ {QUEX_TKN_BRACKET_O, FUNCOPEN, QUEX_TKN_NODENT, TYPEEND, QUEX_TKN_OP_ASSIGNMENT, TYPEINIT, -1, -1},
    106 /*POINTERTYPE*/ {QUEX_TKN_IDENTIFIER, TYPEID, -1, -1},
    107 /*TYPEINIT*/ {QUEX_TKN_STRING, TYPEINITSTR, QUEX_TKN_NODENT, TYPEEND, -1, -1},
    108 /*TYPEINITSTR*/ {-1, -1, -1, -1},
    109 /*TYPEEND*/ {-1, -1, -1, -1},
    110 /*CONST_*/ {QUEX_TKN_TYPE_CHAR, TYPE, -1, -1},
    111 /*EXTERN_*/ {QUEX_TKN_TYPE_INT, TYPE, -1, -1},
    112 /*VOLATILE_*/ {QUEX_TKN_TYPE_INT, TYPE, -1, -1},
    113 /*STATIC_*/ {QUEX_TKN_TYPE_INT, TYPE, QUEX_TKN_TYPE_UNSIGNED, UNSIGNED_, -1, -1},
    114 /*UNSIGNED_*/ {QUEX_TKN_TYPE_LONG, TYPE, -1, -1},
    115 /*SIGNED_*/ {QUEX_TKN_TYPE_SHORT, TYPE, -1, -1},
    116 /*ENUM_*/ {QUEX_TKN_NODENT, ENUM_END, -1, -1},
    117 /*ENUM_END*/ {-1, -1, -1, -1},
    118 /*TYPEDEF_*/ {QUEX_TKN_STRUCT, TDSTRUCT, -1, -1},
    119 /*TDSTRUCT*/ {QUEX_TKN_INDENT, STRUCTBLOCK, -1, -1},
    120 /*STRUCTBLOCK*/ {QUEX_TKN_TYPE_INT, STRUCTTYPE, QUEX_TKN_IDENTIFIER, STRUCTID, QUEX_TKN_STRUCT, STRUCTINBLOCK, QUEX_TKN_UNION, UNIONINSTRUCT, -1, -1},
    121 /*STRUCTINBLOCK*/ {QUEX_TKN_INDENT, STRUCTBLOCK, -1, -1},
    122 /*UNIONINSTRUCT*/ {QUEX_TKN_INDENT, UNIONBLOCK, -1, -1},
    123 /*STRUCTTYPE*/ {QUEX_TKN_IDENTIFIER, STRUCTTYPEID, -1, -1},
    124 /*STRUCTTYPEID*/ {QUEX_TKN_NODENT, STRUCTTYPEEND, -1, -1},
    125 /*STRUCTTYPEEND*/ {-1, -1, -1, -1},
    126 /*STRUCTID*/ {QUEX_TKN_DEDENT, STRUCTBLOCKEND, -1, -1},
    127 /*STRUCTBLOCKEND*/ {-1, -1, -1, -1},
    128 /*UNIONBLOCK*/ {QUEX_TKN_TYPE_CHAR, UNIONTYPE, QUEX_TKN_TYPE_INT, UNIONTYPE, QUEX_TKN_IDENTIFIER, UNIONID, QUEX_TKN_STRUCT, STRUCTINUNION, QUEX_TKN_UNION, UNIONINBLOCK, -1, -1},
    129 /*STRUCTINUNION*/ {QUEX_TKN_INDENT, STRUCTBLOCK, -1, -1},
    130 /*UNIONINBLOCK*/ {QUEX_TKN_INDENT, UNIONBLOCK, -1, -1},
    131 /*UNIONTYPE*/ {QUEX_TKN_IDENTIFIER, UNIONTYPEID, -1, -1},
    132 /*UNIONTYPEID*/ {QUEX_TKN_NODENT, UNIONTYPEEND, -1, -1},
    133 /*UNIONTYPEEND*/ {-1, -1, -1, -1},
    134 /*UNIONID*/ {QUEX_TKN_DEDENT, UNIONBLOCKEND, -1, -1},
    135 /*UNIONBLOCKEND*/ {-1, -1, -1, -1},
    136 /*FUNCOPEN*/ {QUEX_TKN_BRACKET_C, FUNCCLOSE, -1, -1},
    137 /*FUNCCLOSE*/ {QUEX_TKN_INDENT, CODEBLOCK, QUEX_TKN_NODENT, PROTOTYPE, -1, -1},
    138 /*PROTOTYPE*/ {-1, -1, -1, -1},
    139 /*CODEBLOCK*/ {QUEX_TKN_CONST, CONST_, QUEX_TKN_CONTINUE, CONTINUE_, QUEX_TKN_VOLATILE, VOLATILE_, QUEX_TKN_STATIC, STATIC_, QUEX_TKN_TYPE_SIGNED, SIGNED_, QUEX_TKN_TYPE_CHAR, TYPE, QUEX_TKN_TYPE_DOUBLE, TYPE, QUEX_TKN_TYPE_FLOAT, TYPE, QUEX_TKN_TYPE_INT, TYPE, QUEX_TKN_IDENTIFIER, CODEBLOCKID, QUEX_TKN_DO, DO_, QUEX_TKN_ELSE, ELSE_, QUEX_TKN_FOR, FOR_, QUEX_TKN_GOTO, GOTO_, QUEX_TKN_IF, IF_, QUEX_TKN_RETURN, RETURN_, QUEX_TKN_SWITCH, SWITCH_, QUEX_TKN_DEDENT, CODEBLOCKEND, -1, -1},
    140 /*CONTINUE_*/ {QUEX_TKN_DEDENT, CODEBLOCKEND, -1, -1},
    141 /*CODEBLOCKID*/ {QUEX_TKN_BRACKET_O, CALL, QUEX_TKN_COLON, COLON, QUEX_TKN_CORNER_BRACKET_O, ARRAYINDEX, QUEX_TKN_OP_ASSIGNMENT, ASSIGNMENT, QUEX_TKN_INCREMENT, INCREMENT, -1, -1},
    142 /*CALL*/ {QUEX_TKN_STRING, CALLSTR, QUEX_TKN_BRACKET_C, CALLCLOSE, -1, -1},
    143 /*CALLSTR*/ {-1, -1, -1, -1},
    144 /*CALLCLOSE*/ {QUEX_TKN_NODENT, CALLEND, QUEX_TKN_DEDENT, CALLENDNPOP, -1, -1},
    145 /*CALLEND*/ {-1, -1, -1, -1},
    146 /*CALLENDNPOP*/ {-1, -1, -1, -1},
    147 /*INCREMENT*/ {QUEX_TKN_NODENT, CALLEND, QUEX_TKN_DEDENT, CALLENDNPOP, -1, -1},
    148 /*GOTO_*/ {QUEX_TKN_IDENTIFIER, GOTO_ID, -1, -1},
    149 /*GOTO_ID*/ {QUEX_TKN_NODENT, GOTO_END, QUEX_TKN_DEDENT, GOTO_ENDNPOP, -1, -1},
    150 /*GOTO_END*/ {-1, -1, -1, -1},
    151 /*GOTO_ENDNPOP*/ {-1, -1, -1, -1},
    152 /*COLON*/ {QUEX_TKN_NODENT, COLONEND, -1, -1},
    153 /*COLONEND*/ {-1, -1, -1, -1},
    154 /*ARRAYINDEX*/ {QUEX_TKN_CORNER_BRACKET_C, ARRAYINDEXEND, -1, -1},
    155 /*ARRAYINDEXEND*/ {QUEX_TKN_OP_ASSIGNMENT, ASSIGNMENT, -1, -1},
    156 /*ASSIGNMENT*/ {QUEX_TKN_NUMBER, NUMBER, QUEX_TKN_QUOTED_CHAR, QUOTED_CHAR, QUEX_TKN_SIZEOF, SIZEOF_, QUEX_TKN_IDENTIFIER, ASSIGNID, -1, -1},
    157 /*NUMBER*/ {QUEX_TKN_NODENT, CALLEND, QUEX_TKN_DEDENT, CALLENDNPOP, -1, -1},
    158 /*ASSIGNID*/ {QUEX_TKN_BRACKET_O, CALL, -1, -1},
    159 /*QUOTED_CHAR*/ {QUEX_TKN_SEMICOLON, QUOTED_CHAR_SEMICOLON, QUEX_TKN_NODENT, CALLEND, -1, -1},
    160 /*QUOTED_CHAR_SEMICOLON*/ {QUEX_TKN_NODENT, CALLEND, -1, -1},
    161 /*SIZEOF_*/ {QUEX_TKN_BRACKET_O, CALL, -1, -1},
    162 /*IF_*/ {QUEX_TKN_INDENT, CODEBLOCK, -1, -1},
    163 /*ELSE_*/ {QUEX_TKN_INDENT, CODEBLOCK, -1, -1},
    164 /*FOR_*/ {QUEX_TKN_INDENT, CODEBLOCK, -1, -1},
    165 /*DO_*/ {QUEX_TKN_INDENT, CODEBLOCK, -1, -1},
    166 /*SWITCH_*/ {QUEX_TKN_INDENT, SWITCH_BLOCK, -1, -1},
    167 /*SWITCH_BLOCK*/ {QUEX_TKN_CASE, CASE_, QUEX_TKN_DEFAULT, CASE_ID, QUEX_TKN_DEDENT, SWITCH_BLOCKEND, -1, -1},
    168 /*CASE_*/ {QUEX_TKN_IDENTIFIER, CASE_ID, QUEX_TKN_NUMBER, CASE_ID, -1, -1},
    169 /*CASE_ID*/ {QUEX_TKN_INDENT, CASE_BLOCK, -1, -1},
    170 /*CASE_BLOCK*/ {QUEX_TKN_IDENTIFIER, CODEBLOCKID, QUEX_TKN_BREAK, BREAK_, QUEX_TKN_DO, DO_, QUEX_TKN_ELSE, ELSE_, QUEX_TKN_FOR, FOR_, QUEX_TKN_GOTO, GOTO_, QUEX_TKN_IF, IF_, QUEX_TKN_RETURN, RETURN_, QUEX_TKN_SWITCH, SWITCH_, QUEX_TKN_DEDENT, CODEBLOCKEND, -1, -1},
    171 /*BREAK_*/ {QUEX_TKN_DEDENT, CODEBLOCKEND, -1, -1},
    172 /*SWITCH_BLOCKEND*/ {-1, -1, -1, -1},
    173 /*RETURN_*/ {QUEX_TKN_STRING, RETURN_STR, QUEX_TKN_DEDENT, RETURN_END, -1, -1},
    174 /*RETURN_STR*/ {-1, -1, -1, -1},
    175 /*RETURN_END*/ {-1, -1, -1, -1},
    176 /*CODEBLOCKEND*/ {-1, -1, -1, -1},
    177 /*DO_END*/ {QUEX_TKN_FOR, DO_FOR, -1, -1},
    178 /*DO_FOR*/ {QUEX_TKN_NODENT, DO_CLOSE, -1, -1},
    179 /*DO_CLOSE*/ {-1, -1, -1, -1},
    180 /*USE*/ {QUEX_TKN_IDENTIFIER, USEID, -1, -1},
    181 /*USEID*/ {QUEX_TKN_DOT, USEDOT, QUEX_TKN_COMMA, USECOMMA, QUEX_TKN_NODENT, USEEND, -1, -1},
    182 /*USEDOT*/ {QUEX_TKN_IDENTIFIER, USEID, -1, -1},
    183 /*USECOMMA*/ {QUEX_TKN_IDENTIFIER, USEID, -1, -1},
    184 /*USEEND*/ {-1, -1, -1, -1},
    185 };
    186 
    187 void toCString(char *text) {
    188 	// convert to C string
    189 	char *tmp = dupS(text);
    190 	pErrorNULL(setS(tmp, 0, '\"'));
    191 	pErrorNULL(setS(tmp, -1, '\"'));
    192 	// TODO regular expression
    193 	pErrorNULL(iReplaceS_max(&tmp, "\'", "'"));
    194 	pErrorNULL(pushNFreeG(sheepyC, tmp));
    195 	return;
    196 }
    197 
    198 void generateCodeL() {
    199 	smallStringt *tmp = joinG(sheepyC, "");
    200 	pErrorNULL(pushNFreeG(generatedC, tmp));
    201 	freeG(sheepyC);
    202 	//initiateAllocateSmallString(&sheepyC);
    203 }
    204 
    205 void defaultInState(int ste, char *text) {
    206 	//printf("%s %s %s\n",__func__,STATESSTR[ste], text);
    207 }
    208 
    209 void defaultInStateCopy(int ste, char *text) {
    210 	pErrorNULL(pushG(sheepyC, " "));
    211 	pErrorNULL(pushG(sheepyC, text));
    212 }
    213 
    214 void idle(int ste, char *text) {
    215 }
    216 
    217 void type(int ste, char *text) {
    218 	pErrorNULL(pushG(sheepyC, " "));
    219 	pErrorNULL(pushG(sheepyC, text));
    220 	// set next state
    221 	pErrorNULL(pushG(stateStack, stateM));
    222 	stateM = ste;
    223 }
    224 
    225 void typeid(int ste, char *text) {
    226 	// set next state
    227 	stateM = ste;
    228 }
    229 
    230 void pointertype(int ste, char *text) {
    231 	// set next state
    232 	stateM = ste;
    233 }
    234 
    235 void typeinit(int ste, char *text) {
    236 	// set next state
    237 	stateM = ste;
    238 }
    239 
    240 void typeinitstr(int ste, char *text) {
    241 	toCString(text);
    242 	// set next state
    243 	stateM = TYPEINIT;
    244 }
    245 
    246 void typeend(int ste, char *text) {
    247 	pErrorNULL(pushG(sheepyC, ";"));
    248 	generateCodeL();
    249 	// set next state
    250 	stateM = popG(stateStack, rtInt32_t);
    251 	if ((stateM == IDLE)||(stateM == CODEBLOCK)||(stateM == CASE_BLOCK)) {
    252 		return;
    253 	}
    254 	if (stateM == EXTERN_) {
    255 		stateM = IDLE;
    256 		return;
    257 	}
    258 	// TODO pop until block is found
    259 	stateM = popG(stateStack, rtInt32_t);
    260 	if ((stateM == CODEBLOCK)||(stateM == CASE_BLOCK)) {
    261 		return;
    262 	}
    263 	stateM = popG(stateStack, rtInt32_t);
    264 }
    265 
    266 void extern_(int ste, char *text) {
    267 	// set next state
    268 	stateM = ste;
    269 }
    270 
    271 void volatile_(int ste, char *text) {
    272 	// set next state
    273 	stateM = ste;
    274 }
    275 
    276 void static_(int ste, char *text) {
    277 	// set next state
    278 	stateM = ste;
    279 }
    280 
    281 void unsigned_(int ste, char *text) {
    282 	// set next state
    283 	stateM = ste;
    284 }
    285 
    286 void signed_(int ste, char *text) {
    287 	// set next state
    288 	stateM = ste;
    289 }
    290 
    291 void enum_(int ste, char *text) {
    292 	pushG(sheepyC, "enum {");
    293 	// set next state
    294 	stateM = ste;
    295 }
    296 
    297 void enum_end(int ste, char *text) {
    298 	pErrorNULL(pushG(sheepyC, "};"));
    299 	generateCodeL();
    300 	// set next state
    301 	stateM = IDLE;
    302 }
    303 
    304 void typedef_(int ste, char *text) {
    305 	pErrorNULL(pushG(sheepyC, "typedef"));
    306 	// set next state
    307 	stateM = ste;
    308 }
    309 
    310 void tdstruct(int ste, char *text) {
    311 	// set next state
    312 	stateM = ste;
    313 }
    314 
    315 void structblock(int ste, char *text) {
    316 	pErrorNULL(pushG(sheepyC, " {"));
    317 	generateCodeL();
    318 	pErrorNULL(pushG(stateStack, stateM));
    319 	// set next state
    320 	stateM = ste;
    321 }
    322 
    323 void structinblock(int ste, char *text) {
    324 	// set next state
    325 	stateM = ste;
    326 }
    327 
    328 void unioninstruct(int ste, char *text) {
    329 	// set next state
    330 	stateM = ste;
    331 }
    332 
    333 void structtype(int ste, char *text) {
    334 	// set next state
    335 	stateM = ste;
    336 }
    337 
    338 void structtypeid(int ste, char *text) {
    339 	// set next state
    340 	stateM = ste;
    341 }
    342 
    343 void structtypeend(int ste, char *text) {
    344 	pErrorNULL(pushG(sheepyC, ";"));
    345 	generateCodeL();
    346 	// set next state
    347 	stateM = STRUCTBLOCK;
    348 }
    349 
    350 void structid(int ste, char *text) {
    351 	pErrorNULL(pushG(textStack, text));
    352 	// set next state
    353 	stateM = ste;
    354 }
    355 
    356 void structblockend(int ste, char *text) {
    357 	char *id = popG(textStack, rtChar);
    358 	pErrorNULL(pushG(sheepyC, "} "));
    359 	pErrorNULL(pushNFreeG(sheepyC, id));
    360 	pErrorNULL(pushG(sheepyC, ";"));
    361 	generateCodeL();
    362 	// set next state
    363 	stateM = popG(stateStack, rtInt32_t);
    364 	switch(stateM) {
    365 		case TDSTRUCT:
    366 			stateM = IDLE;
    367 			break;
    368 		case STRUCTINBLOCK:
    369 			stateM = STRUCTBLOCK;
    370 			break;
    371 		case STRUCTINUNION:
    372 			stateM = UNIONBLOCK;
    373 			break;
    374 	}
    375 }
    376 
    377 void unionblock(int ste, char *text) {
    378 	// set next state
    379 	stateM = ste;
    380 }
    381 
    382 void structinunion(int ste, char *text) {
    383 	// set next state
    384 	stateM = ste;
    385 }
    386 
    387 void unioninblock(int ste, char *text) {
    388 	// set next state
    389 	stateM = ste;
    390 }
    391 
    392 void uniontype(int ste, char *text) {
    393 	// set next state
    394 	stateM = ste;
    395 }
    396 
    397 void uniontypeid(int ste, char *text) {
    398 	// set next state
    399 	stateM = ste;
    400 }
    401 
    402 void uniontypeend(int ste, char *text) {
    403 	pErrorNULL(pushG(sheepyC, ";"));
    404 	generateCodeL();
    405 	// set next state
    406 	stateM = UNIONBLOCK;
    407 }
    408 
    409 void unionid(int ste, char *text) {
    410 	// set next state
    411 	stateM = ste;
    412 }
    413 
    414 void unionblockend(int ste, char *text) {
    415 	char *id = popG(textStack, rtChar);
    416 	pErrorNULL(pushG(sheepyC, "} "));
    417 	pErrorNULL(pushNFreeG(sheepyC, id));
    418 	pErrorNULL(pushG(sheepyC, ";"));
    419 	generateCodeL();
    420 	// set next state
    421 	stateM = popG(stateStack, rtInt32_t);
    422 	switch(stateM) {
    423 		/* case TDUNION: */
    424 		/* 	stateM = IDLE; */
    425 		/* 	break; */
    426 		case UNIONINBLOCK:
    427 			stateM = UNIONBLOCK;
    428 			break;
    429 		case UNIONINSTRUCT:
    430 			stateM = STRUCTBLOCK;
    431 			break;
    432 	}
    433 }
    434 
    435 void funcopen(int ste, char *text) {
    436 	// set next state
    437 	stateM = ste;
    438 }
    439 
    440 void funcclose(int ste, char *text) {
    441 	// do nothing the bracket ) and curly bracket are in the
    442 	// codeblock function
    443 	// set next state
    444 	stateM = ste;
    445 }
    446 
    447 void prototype(int ste, char *text) {
    448 	pushG(sheepyC, ");");
    449 	generateCodeL();
    450 	// set next state
    451 	stateM = IDLE;
    452 }
    453 
    454 void codeblock(int ste, char *text) {
    455 	if ((stateM == DO_)||(stateM == ELSE_)) {
    456 		pErrorNULL(pushG(sheepyC, " {"));
    457 	}
    458 	else {
    459 		// close condition statement
    460 		pErrorNULL(pushG(sheepyC, ") {"));
    461 	}
    462 	generateCodeL();
    463 	pErrorNULL(pushG(stateStack, stateM));
    464 	// set next state
    465 	stateM = ste;
    466 }
    467 
    468 void codeblockid(int ste, char *text) {
    469 	pErrorNULL(pushG(sheepyC, text));
    470 	// set next state
    471 	pushG(stateStack, stateM);
    472 	stateM = ste;
    473 }
    474 
    475 void call(int ste, char *text) {
    476 	pErrorNULL(pushG(sheepyC, "("));
    477 	// set next state
    478 	stateM = ste;
    479 }
    480 
    481 void callstr(int ste, char *text) {
    482 	toCString(text);
    483 	// set next state
    484 	stateM = CALL;
    485 }
    486 
    487 void callclose(int ste, char *text) {
    488 	pErrorNULL(pushG(sheepyC, ")"));
    489 	// set next state
    490 	stateM = ste;
    491 }
    492 
    493 void callend(int ste, char *text) {
    494 	pErrorNULL(pushG(sheepyC, ";"));
    495 	generateCodeL();
    496 	// set next state
    497 	// pop to return to CODEBLOCK or CASE_BLOCK
    498 	stateM = popG(stateStack, rtInt32_t);
    499 }
    500 
    501 void callendnpop(int ste, char *text) {
    502 	pErrorNULL(pushG(sheepyC, ";"));
    503 	generateCodeL();
    504 	// set next state
    505 	// pop to return to CODEBLOCK or CASE_BLOCK
    506 	stateM = popG(stateStack, rtInt32_t);
    507 	codeblockend(ste, text);
    508 }
    509 
    510 void increment(int ste, char *text) {
    511 	// set next state
    512 	stateM = ste;
    513 }
    514 
    515 void goto_(int ste, char *text) {
    516 	// set next state
    517 	stateM = ste;
    518 }
    519 
    520 void goto_id(int ste, char *text) {
    521 	// set next state
    522 	stateM = ste;
    523 }
    524 
    525 void goto_end(int ste, char *text) {
    526 	pErrorNULL(pushG(sheepyC, ";"));
    527 	generateCodeL();
    528 	// set next state
    529 	stateM = CODEBLOCK;
    530 }
    531 
    532 void goto_endnpop(int ste, char *text) {
    533 	pErrorNULL(pushG(sheepyC, ";"));
    534 	generateCodeL();
    535 	// set next state
    536 	codeblockend(ste, text);
    537 }
    538 
    539 void colon(int ste, char *text) {
    540 	pErrorNULL(pushG(sheepyC, ":"));
    541 	generateCodeL();
    542 	// set next state
    543 	// pop stateM pushed in codeblockid
    544 	// discard because goto labels are always in codeblocks
    545 	popG(stateStack, rtInt32_t);
    546 	stateM = ste;
    547 }
    548 
    549 void colonend(int ste, char *text) {
    550 	// set next state
    551 	stateM = CODEBLOCK;
    552 }
    553 
    554 void arrayindex(int ste, char *text) {
    555 	// set next state
    556 	stateM = ste;
    557 }
    558 
    559 void arrayindexend(int ste, char *text) {
    560 	// set next state
    561 	stateM = ste;
    562 }
    563 
    564 void assignment(int ste, char *text) {
    565 	// set next state
    566 	stateM = ste;
    567 }
    568 
    569 void quoted_char(int ste, char *text) {
    570 	// convert to C char
    571 	text = dupS(text);
    572 	pErrorNULL(iReplaceS(&text, "'", "\\'", 1));
    573 	pErrorNULL(setS(text, 0, '\''));
    574 	pErrorNULL(iAppendS(&text, "'"));
    575 	pErrorNULL(iReplaceS(&text, "\\@", "@", 1));
    576 	pErrorNULL(pushNFreeG(sheepyC, text));
    577 	// set next state
    578 	stateM = ste;
    579 }
    580 
    581 void quoted_char_semicolon(int ste, char *text) {
    582 	// change last string in sheepyC
    583 	// add space in char
    584 	// tabs should be \t
    585 	smallStringt *txt = getG(sheepyC, rtSmallStringt, -1);
    586 	pErrorNULL(setG(txt, 1, ' '));
    587 	pErrorNULL(pushG(txt, "'"));
    588 	// pointer in sheepyC should be updated with setPG sheepyC
    589 	// but this string is always short
    590 	// the pointer doesn't change
    591 	smashG(txt);
    592 	// set next state
    593 	stateM = ste;
    594 }
    595 
    596 void sizeof_(int ste, char *text) {
    597 	// set next state
    598 	stateM = ste;
    599 }
    600 
    601 void assignmentend(int ste, char *text) {
    602 	// set next state
    603 	stateM = ste;
    604 }
    605 
    606 void if_(int ste, char *text) {
    607 	pErrorNULL(pushG(sheepyC, text));
    608 	pErrorNULL(pushG(sheepyC, " ("));
    609 	// set next state
    610 	stateM = ste;
    611 }
    612 
    613 void else_(int ste, char *text) {
    614 	// set next state
    615 	stateM = ste;
    616 }
    617 
    618 void for_(int ste, char *text) {
    619 	// set next state
    620 	stateM = ste;
    621 }
    622 
    623 void do_(int ste, char *text) {
    624 	// set next state
    625 	stateM = ste;
    626 }
    627 
    628 void switch_(int ste, char *text) {
    629 	// set next state
    630 	stateM = ste;
    631 }
    632 
    633 void switch_block(int ste, char *text) {
    634 	pErrorNULL(pushG(sheepyC, ") {"));
    635 	generateCodeL();
    636 	// TODO push stateM >> use structblock function
    637 	// set next state
    638 	stateM = ste;
    639 }
    640 
    641 void case_(int ste, char *text) {
    642 	// set next state
    643 	stateM = ste;
    644 }
    645 
    646 void case_id(int ste, char *text) {
    647 	// set next state
    648 	stateM = ste;
    649 }
    650 
    651 void case_block(int ste, char *text) {
    652 	// add curly brackets around code for case labels
    653 	pErrorNULL(pushG(sheepyC, ": {"));
    654 	generateCodeL();
    655 	pErrorNULL(pushG(stateStack, stateM));
    656 	// set next state
    657 	stateM = ste;
    658 }
    659 
    660 void break_(int ste, char *text) {
    661 	pErrorNULL(pushG(sheepyC, text));
    662 	pErrorNULL(pushG(sheepyC, ";"));
    663 	// set next state
    664 	stateM = ste;
    665 }
    666 
    667 void switch_blockend(int ste, char *text) {
    668 	pErrorNULL(pushG(sheepyC, "}"));
    669 	// TODO pop stateM
    670 	// set next state
    671 	stateM = CODEBLOCK;
    672 }
    673 
    674 void return_(int ste, char *text) {
    675 	// set next state
    676 	stateM = ste;
    677 }
    678 
    679 void return_str(int ste, char *text) {
    680 	// convert to C string
    681 	toCString(text);
    682 	// set next state
    683 	stateM = RETURN_;
    684 }
    685 
    686 void return_end(int ste, char *text) {
    687 	// when return doesnt have parameters
    688 	// replace bracket with semicolon
    689 	char *tmp = getG(sheepyC, rtChar, -1);
    690 	if (getS(tmp, -1) == '(') {
    691 		pErrorNULL(setS(tmp, -1, ';'));
    692 	}
    693 	else {
    694 		pErrorNULL(pushG(sheepyC, ");"));
    695 	}
    696 	generateCodeL();
    697 	// set next state
    698 	stateM = CODEBLOCKEND;
    699 	codeblockend(ste, text);
    700 }
    701 
    702 void codeblockend(int ste, char *text) {
    703 	pErrorNULL(pushG(sheepyC, "}"));
    704 	// set next state
    705 	stateM = popG(stateStack, rtInt32_t);
    706 	switch(stateM) {
    707 		case FUNCCLOSE:
    708 			generateCodeL();
    709 			stateM = IDLE;
    710 			break;
    711 		case IF_:
    712 			generateCodeL();
    713 			stateM = CODEBLOCK;
    714 			break;
    715 		case ELSE_:
    716 			generateCodeL();
    717 			stateM = CODEBLOCK;
    718 			break;
    719 		case FOR_:
    720 			generateCodeL();
    721 			stateM = CODEBLOCK;
    722 			break;
    723 		case DO_:
    724 			// dont generate code because the conditional
    725 			// statement is after that
    726 			stateM = DO_END;
    727 			break;
    728 		case CASE_ID:
    729 			generateCodeL();
    730 			stateM = SWITCH_BLOCK;
    731 			break;
    732 	}
    733 }
    734 
    735 void do_end(int ste, char *text) {
    736 	// set next state
    737 	stateM = ste;
    738 }
    739 
    740 void do_for(int ste, char *text) {
    741 	pErrorNULL(pushG(sheepyC, " while ("));
    742 	// set next state
    743 	stateM = ste;
    744 }
    745 
    746 void do_close(int ste, char *text) {
    747 	pErrorNULL(pushG(sheepyC, ");"));
    748 	generateCodeL();
    749 	// set next state
    750 	stateM = CODEBLOCK;
    751 }
    752 
    753 void use(int ste, char *text) {
    754 	pErrorNULL(pushG(sheepyC, "#include \""));
    755 	// set next state
    756 	stateM = ste;
    757 }
    758 
    759 void addT(int ste, char *text) {
    760 	pErrorNULL(pushG(sheepyC, text));
    761 	// set next state
    762 	stateM = ste;
    763 }
    764 
    765 void usecomma(int ste, char *text) {
    766 	pErrorNULL(pushG(sheepyC, "\""));
    767 	generateCodeL();
    768 	// expecting more use
    769 	use(ste, text);
    770 }
    771 
    772 void useend(int ste, char *text) {
    773 	pErrorNULL(pushG(sheepyC, "\""));
    774 	generateCodeL();
    775 	stateM = IDLE;
    776 }
    777 
    778 void addSpaceNT(int ste, char *text) {
    779 	pErrorNULL(pushG(sheepyC, " "));
    780 	pErrorNULL(pushG(sheepyC, text));
    781 	// set next state
    782 	stateM = ste;
    783 }
    784 
    785 
    786 // ste is the state it is transitioning to
    787 // text is the token
    788 typedef void (*stateFt)(int ste, char *text);
    789 stateFt STATEF[FINAL] = {
    790 /*IDLE*/ idle,
    791 /*TYPE*/ type,
    792 /*TYPEID*/ addSpaceNT,
    793 /*POINTERTYPE*/ addSpaceNT,
    794 /*TYPEINIT*/ addT,
    795 /*TYPEINITSTR*/ typeinitstr,
    796 /*TYPEEND*/ typeend,
    797 /*CONST_*/ type,
    798 /*EXTERN_*/ addSpaceNT,
    799 /*VOLATILE_*/ type,
    800 /*STATIC_*/ type,
    801 /*UNSIGNED_*/ type,
    802 /*SIGNED_*/ type,
    803 /*ENUM_*/ enum_,
    804 /*ENUM_END*/ enum_end,
    805 /*TYPEDEF_*/ typedef_,
    806 /*TDSTRUCT*/ addSpaceNT,
    807 /*STRUCTBLOCK*/ structblock,
    808 /*STRUCTINBLOCK*/ addT,
    809 /*UNIONINSTRUCT*/ addT,
    810 /*STRUCTTYPE*/ addSpaceNT,
    811 /*STRUCTTYPEID*/ addSpaceNT,
    812 /*STRUCTTYPEEND*/ structtypeend,
    813 /*STRUCTID*/ structid,
    814 /*STRUCTBLOCKEND*/ structblockend,
    815 /*UNIONBLOCK*/ structblock,
    816 /*STRUCTINUNION*/ addT,
    817 /*UNIONINBLOCK*/ addT,
    818 /*UNIONTYPE*/ addSpaceNT,
    819 /*UNIONTYPEID*/ addSpaceNT,
    820 /*UNIONTYPEEND*/ uniontypeend,
    821 /*UNIONID*/ structid,
    822 /*UNIONBLOCKEND*/ unionblockend,
    823 /*FUNCOPEN*/ addSpaceNT,
    824 /*FUNCCLOSE*/ funcclose,
    825 /*PROTOTYPE*/ prototype,
    826 /*CODEBLOCK*/ codeblock,
    827 /*CONTINUE_*/ break_,
    828 /*CODEBLOCKID*/ codeblockid,
    829 /*CALL*/ call,
    830 /*CALLSTR*/ callstr,
    831 /*CALLCLOSE*/ callclose,
    832 /*CALLEND*/ callend,
    833 /*CALLENDNPOP*/ callendnpop,
    834 /*INCREMENT*/ addT,
    835 /*GOTO_*/ addT,
    836 /*GOTO_ID*/ addSpaceNT,
    837 /*GOTO_END*/ goto_end,
    838 /*GOTO_ENDNPOP*/ goto_endnpop,
    839 /*COLON*/ colon,
    840 /*COLONEND*/ colonend,
    841 /*ARRAYINDEX*/ addT,
    842 /*ARRAYINDEXEND*/ addT,
    843 /*ASSIGNMENT*/ addSpaceNT,
    844 /*NUMBER*/ addSpaceNT,
    845 /*ASSIGNID*/ addT,
    846 /*QUOTED_CHAR*/ quoted_char,
    847 /*QUOTED_CHAR_SEMICOLON*/ quoted_char_semicolon,
    848 /*SIZEOF_*/ addT,
    849 /*IF_*/ if_,
    850 /*ELSE_*/ addT,
    851 /*FOR_*/ if_,
    852 /*DO_*/ addT,
    853 /*SWITCH_*/ if_,
    854 /*SWITCH_BLOCK*/ switch_block,
    855 /*CASE_*/ addT,
    856 /*CASE_ID*/ addSpaceNT,
    857 /*CASE_BLOCK*/ case_block,
    858 /*BREAK_*/ break_,
    859 /*SWITCH_BLOCKEND*/ switch_blockend,
    860 /*RETURN_*/ if_,
    861 /*RETURN_STR*/ return_str,
    862 /*RETURN_END*/ return_end,
    863 /*CODEBLOCKEND*/ codeblockend,
    864 /*DO_END*/ do_end,
    865 /*DO_FOR*/ do_for,
    866 /*DO_CLOSE*/ do_close,
    867 /*USE*/ use,
    868 /*USEID*/ addT,
    869 /*USEDOT*/ addT,
    870 /*USECOMMA*/ usecomma,
    871 /*USEEND*/ useend,
    872 };
    873 
    874 stateFt STATEDEFAULTF[FINAL] = {
    875 /*IDLE*/ idle,
    876 /*TYPE*/ defaultInState,
    877 /*TYPEID*/ defaultInState,
    878 /*POINTERTYPE*/ defaultInState,
    879 /*TYPEINIT*/ defaultInStateCopy,
    880 /*TYPEINITSTR*/ defaultInState,
    881 /*TYPEEND*/ defaultInState,
    882 /*CONST_*/ defaultInState,
    883 /*EXTERN_*/ defaultInState,
    884 /*VOLATILE_*/ defaultInState,
    885 /*STATIC_*/ defaultInState,
    886 /*UNSIGNED_*/ defaultInState,
    887 /*SIGNED_*/ defaultInState,
    888 /*ENUM_*/ defaultInStateCopy,
    889 /*ENUM_END*/ defaultInState,
    890 /*TYPEDEF_*/ defaultInState,
    891 /*TDSTRUCT*/ defaultInState,
    892 /*STRUCTBLOCK*/ defaultInState,
    893 /*STRUCTINBLOCK*/ defaultInState,
    894 /*UNIONINSTRUCT*/ defaultInState,
    895 /*STRUCTTYPE*/ defaultInState,
    896 /*STRUCTTYPEID*/ defaultInState,
    897 /*STRUCTTYPEEND*/ defaultInState,
    898 /*STRUCTID*/ defaultInState,
    899 /*STRUCTBLOCKEND*/ defaultInState,
    900 /*UNIONBLOCK*/ defaultInState,
    901 /*STRUCTINUNION*/ defaultInState,
    902 /*UNIONINBLOCK*/ defaultInState,
    903 /*UNIONTYPE*/ defaultInState,
    904 /*UNIONTYPEID*/ defaultInState,
    905 /*UNIONTYPEEND*/ defaultInState,
    906 /*UNIONID*/ defaultInState,
    907 /*UNIONBLOCKEND*/ defaultInState,
    908 /*FUNCOPEN*/ defaultInStateCopy,
    909 /*FUNCCLOSE*/ defaultInState,
    910 /*PROTOTYPE*/ defaultInState,
    911 /*CODEBLOCK*/ defaultInState,
    912 /*CONTINUE_*/ defaultInState,
    913 /*CODEBLOCKID*/ defaultInState,
    914 /*CALL*/ defaultInStateCopy,
    915 /*CALLSTR*/ defaultInState,
    916 /*CALLCLOSE*/ defaultInState,
    917 /*CALLEND*/ defaultInState,
    918 /*CALLENDNPOP*/ defaultInState,
    919 /*INCREMENT*/ defaultInState,
    920 /*GOTO_*/ defaultInState,
    921 /*GOTO_ID*/ defaultInState,
    922 /*GOTO_END*/ defaultInState,
    923 /*GOTO_ENDNPOP*/ defaultInState,
    924 /*COLON*/ defaultInState,
    925 /*COLONEND*/ defaultInState,
    926 /*ARRAYINDEX*/ defaultInStateCopy,
    927 /*ARRAYINDEXEND*/ defaultInState,
    928 /*ASSIGNMENT*/ defaultInState,
    929 /*NUMBER*/ defaultInState,
    930 /*ASSIGNID*/ defaultInState,
    931 /*QUOTED_CHAR*/ defaultInState,
    932 /*QUOTED_CHAR_SEMICOLON*/ defaultInState,
    933 /*SIZEOF_*/ defaultInState,
    934 /*IF_*/ defaultInStateCopy,
    935 /*ELSE_*/ defaultInState,
    936 /*FOR_*/ defaultInStateCopy,
    937 /*DO_*/ defaultInState,
    938 /*SWITCH_*/ defaultInStateCopy,
    939 /*SWITCH_BLOCK*/ defaultInState,
    940 /*CASE_*/ defaultInState,
    941 /*CASE_ID*/ defaultInState,
    942 /*CASE_BLOCK*/ defaultInState,
    943 /*BREAK_*/ defaultInState,
    944 /*SWITCH_BLOCKEND*/ defaultInState,
    945 /*RETURN_*/ defaultInStateCopy,
    946 /*RETURN_STR*/ defaultInState,
    947 /*RETURN_END*/ defaultInState,
    948 /*CODEBLOCKEND*/ defaultInState,
    949 /*DO_END*/ defaultInState,
    950 /*DO_FOR*/ defaultInStateCopy,
    951 /*DO_CLOSE*/ defaultInState,
    952 /*USE*/ defaultInState,
    953 /*USEID*/ defaultInState,
    954 /*USEDOT*/ defaultInState,
    955 /*USECOMMA*/ defaultInState,
    956 /*USEEND*/ defaultInState,
    957 };
    958