1 /* Generated by re2c */
2 #line 1 "push_f.re"
3 // re2c $INPUT -o $OUTPUT -f
4 /*
5  *  A push-model scanner example for re2c -f
6  *  Written Mon Apr 11 2005 by mgix@mgix.com
7  *  This file is in the public domain.
8  *
9  */
10 
11 // ----------------------------------------------------------------------
12 
13 #include <fcntl.h>
14 #include <stdio.h>
15 #include <stddef.h>
16 #include <stdlib.h>
17 #include <string.h>
18 
19 #if defined(WIN32)
20 
21     typedef signed char     int8_t;
22     typedef signed short    int16_t;
23     typedef signed int      int32_t;
24 
25     typedef unsigned char   uint8_t;
26     typedef unsigned short  uint16_t;
27     typedef unsigned int    uint32_t;
28 
29 #else
30 
31     #include <stdint.h>
32     #include <unistd.h>
33 
34     #ifndef O_BINARY
35         #define O_BINARY 0
36     #endif
37 
38 #endif
39 
40 // ----------------------------------------------------------------------
41 #define TOKENS              \
42                             \
43     TOK(kEOF)               \
44     TOK(kEOL)               \
45     TOK(kUnknown)           \
46     TOK(kIdentifier)        \
47     TOK(kDecimalConstant)   \
48                             \
49     TOK(kEqual)             \
50     TOK(kLeftParen)         \
51     TOK(kRightParen)        \
52     TOK(kMinus)             \
53     TOK(kPlus)              \
54     TOK(kStar)              \
55     TOK(kSlash)             \
56                             \
57     TOK(kIf)                \
58     TOK(kFor)               \
59     TOK(kElse)              \
60     TOK(kGoto)              \
61     TOK(kBreak)             \
62     TOK(kWhile)             \
63     TOK(kReturn)            \
64 
65 
66 // ----------------------------------------------------------------------
67 static const char *tokenNames[] =
68 {
69     #define TOK(x) #x,
70         TOKENS
71     #undef TOK
72 };
73 
74 // ----------------------------------------------------------------------
75 class PushScanner
76 {
77 public:
78 
79     enum Token
80     {
81         #define TOK(x) x,
82             TOKENS
83         #undef TOK
84     };
85 
86 private:
87 
88     bool        eof;
89     int32_t     state;
90 
91     uint8_t     *limit;
92     uint8_t     *start;
93     uint8_t     *cursor;
94     uint8_t     *marker;
95 
96     uint8_t     *buffer;
97     uint8_t     *bufferEnd;
98 
99     uint8_t     yych;
100     uint32_t    yyaccept;
101 
102 public:
103 
104     // ----------------------------------------------------------------------
PushScanner()105     PushScanner()
106     {
107         limit = 0;
108         start = 0;
109         state = -1;
110         cursor = 0;
111         marker = 0;
112         buffer = 0;
113         eof = false;
114         bufferEnd = 0;
115     }
116 
117     // ----------------------------------------------------------------------
~PushScanner()118     ~PushScanner()
119     {
120     }
121 
122     // ----------------------------------------------------------------------
send(Token token)123     void send(
124         Token token
125     )
126     {
127         size_t tokenSize = cursor-start;
128         const char *tokenName = tokenNames[token];
129         printf(
130             "scanner is pushing out a token of type %d (%s)",
131             token,
132             tokenName
133         );
134 
135         if(token==kEOF) putchar('\n');
136         else
137         {
138             size_t tokenNameSize = strlen(tokenNames[token]);
139             size_t padSize = 20-(20<tokenNameSize ? 20 : tokenNameSize);
140             for(size_t i=0; i<padSize; ++i) putchar(' ');
141             printf(" : ---->");
142 
143             fwrite(
144                 start,
145                 tokenSize,
146                 1,
147                 stdout
148             );
149 
150             printf("<----\n");
151         }
152     }
153 
154     // ----------------------------------------------------------------------
push(const void * input,ssize_t inputSize)155     uint32_t push(
156         const void  *input,
157         ssize_t     inputSize
158     )
159     {
160         printf(
161             "scanner is receiving a new data batch of length %d\n"
162             "scanner continues with saved state = %d\n",
163             inputSize,
164             state
165         );
166 
167         /*
168          * Data source is signaling end of file when batch size
169          * is less than maxFill. This is slightly annoying because
170          * maxFill is a value that can only be known after re2c does
171          * its thing. Practically though, maxFill is never bigger than
172          * the longest keyword, so given our grammar, 32 is a safe bet.
173          */
174         uint8_t null[64];
175         const ssize_t maxFill = 32;
176         if(inputSize<maxFill)
177         {
178             eof = true;
179             input = null;
180             inputSize = sizeof(null);
181             memset(null, 0, sizeof(null));
182         }
183 
184         /*
185          * When we get here, we have a partially
186          * consumed buffer which is in the following state:
187          *                                                                last valid char        last valid buffer spot
188          *                                                                v                      v
189          * +-------------------+-------------+---------------+-------------+----------------------+
190          * ^                   ^             ^               ^             ^                      ^
191          * buffer              start         marker          cursor        limit                  bufferEnd
192          *
193          * We need to stretch the buffer and concatenate the new chunk of input to it
194          *
195          */
196         size_t used = limit-buffer;
197         size_t needed = used+inputSize;
198         size_t allocated = bufferEnd-buffer;
199         if(allocated<needed)
200         {
201             size_t limitOffset = limit-buffer;
202             size_t startOffset = start-buffer;
203             size_t markerOffset = marker-buffer;
204             size_t cursorOffset = cursor-buffer;
205 
206                 buffer = (uint8_t*)realloc(buffer, needed);
207                 bufferEnd = needed+buffer;
208 
209             marker = markerOffset + buffer;
210             cursor = cursorOffset + buffer;
211             start = buffer + startOffset;
212             limit = limitOffset + buffer;
213         }
214         memcpy(limit, input, inputSize);
215         limit += inputSize;
216 
217         // The scanner starts here
218         #define YYLIMIT         limit
219         #define YYCURSOR        cursor
220         #define YYMARKER        marker
221         #define YYCTYPE         uint8_t
222 
223         #define SKIP(x)         { start = cursor; goto yy0; }
224         #define SEND(x)         { send(x); SKIP();          }
225         #define YYFILL(n)       { goto fill;                }
226 
227         #define YYGETSTATE()    state
228         #define YYSETSTATE(x)   { state = (x);  }
229 
230     start:
231 
232 
233 #line 234 "push_f.c"
234 
235 	switch (YYGETSTATE()) {
236 	default:
237 		goto yy0;
238 	case 0:
239 		goto yyFillLabel0;
240 	case 1:
241 		goto yyFillLabel1;
242 	case 2:
243 		goto yyFillLabel2;
244 	}
245 yy0:
246 	YYSETSTATE(0);
247 	if ((YYLIMIT - YYCURSOR) < 7) YYFILL(7);
248 yyFillLabel0:
249 	yych = *YYCURSOR;
250 	switch (yych) {
251 	case 0x00:	goto yy3;
252 	case '\t':
253 	case '\v':
254 	case '\f':
255 	case '\r':
256 	case ' ':	goto yy7;
257 	case '\n':	goto yy9;
258 	case '(':	goto yy11;
259 	case ')':	goto yy13;
260 	case '*':	goto yy15;
261 	case '+':	goto yy17;
262 	case '-':	goto yy19;
263 	case '/':	goto yy21;
264 	case '0':
265 	case '1':
266 	case '2':
267 	case '3':
268 	case '4':
269 	case '5':
270 	case '6':
271 	case '7':
272 	case '8':
273 	case '9':	goto yy23;
274 	case '=':	goto yy26;
275 	case 'A':
276 	case 'B':
277 	case 'C':
278 	case 'D':
279 	case 'E':
280 	case 'F':
281 	case 'G':
282 	case 'H':
283 	case 'I':
284 	case 'J':
285 	case 'K':
286 	case 'L':
287 	case 'M':
288 	case 'N':
289 	case 'O':
290 	case 'P':
291 	case 'Q':
292 	case 'R':
293 	case 'S':
294 	case 'T':
295 	case 'U':
296 	case 'V':
297 	case 'W':
298 	case 'X':
299 	case 'Y':
300 	case 'Z':
301 	case '_':
302 	case 'a':
303 	case 'c':
304 	case 'd':
305 	case 'h':
306 	case 'j':
307 	case 'k':
308 	case 'l':
309 	case 'm':
310 	case 'n':
311 	case 'o':
312 	case 'p':
313 	case 'q':
314 	case 's':
315 	case 't':
316 	case 'u':
317 	case 'v':
318 	case 'x':
319 	case 'y':
320 	case 'z':	goto yy28;
321 	case 'b':	goto yy31;
322 	case 'e':	goto yy32;
323 	case 'f':	goto yy33;
324 	case 'g':	goto yy34;
325 	case 'i':	goto yy35;
326 	case 'r':	goto yy36;
327 	case 'w':	goto yy37;
328 	default:	goto yy5;
329 	}
330 yy3:
331 	++YYCURSOR;
332 #line 260 "push_f.re"
333 	{ send(kEOF); return 1;  }
334 #line 335 "push_f.c"
335 yy5:
336 	++YYCURSOR;
337 #line 261 "push_f.re"
338 	{ SEND(kUnknown);        }
339 #line 340 "push_f.c"
340 yy7:
341 	++YYCURSOR;
342 #line 259 "push_f.re"
343 	{ SKIP();                }
344 #line 345 "push_f.c"
345 yy9:
346 	++YYCURSOR;
347 #line 258 "push_f.re"
348 	{ SKIP();                }
349 #line 350 "push_f.c"
350 yy11:
351 	++YYCURSOR;
352 #line 251 "push_f.re"
353 	{ SEND(kLeftParen);      }
354 #line 355 "push_f.c"
355 yy13:
356 	++YYCURSOR;
357 #line 252 "push_f.re"
358 	{ SEND(kRightParen);     }
359 #line 360 "push_f.c"
360 yy15:
361 	++YYCURSOR;
362 #line 255 "push_f.re"
363 	{ SEND(kStar);           }
364 #line 365 "push_f.c"
365 yy17:
366 	++YYCURSOR;
367 #line 254 "push_f.re"
368 	{ SEND(kPlus);           }
369 #line 370 "push_f.c"
370 yy19:
371 	++YYCURSOR;
372 #line 253 "push_f.re"
373 	{ SEND(kMinus);          }
374 #line 375 "push_f.c"
375 yy21:
376 	++YYCURSOR;
377 #line 256 "push_f.re"
378 	{ SEND(kSlash);          }
379 #line 380 "push_f.c"
380 yy23:
381 	++YYCURSOR;
382 	YYSETSTATE(1);
383 	if (YYLIMIT <= YYCURSOR) YYFILL(1);
384 yyFillLabel1:
385 	yych = *YYCURSOR;
386 	switch (yych) {
387 	case '0':
388 	case '1':
389 	case '2':
390 	case '3':
391 	case '4':
392 	case '5':
393 	case '6':
394 	case '7':
395 	case '8':
396 	case '9':	goto yy23;
397 	default:	goto yy25;
398 	}
399 yy25:
400 #line 248 "push_f.re"
401 	{ SEND(kDecimalConstant);}
402 #line 403 "push_f.c"
403 yy26:
404 	++YYCURSOR;
405 #line 250 "push_f.re"
406 	{ SEND(kEqual);          }
407 #line 408 "push_f.c"
408 yy28:
409 	++YYCURSOR;
410 	YYSETSTATE(2);
411 	if (YYLIMIT <= YYCURSOR) YYFILL(1);
412 yyFillLabel2:
413 	yych = *YYCURSOR;
414 yy29:
415 	switch (yych) {
416 	case '0':
417 	case '1':
418 	case '2':
419 	case '3':
420 	case '4':
421 	case '5':
422 	case '6':
423 	case '7':
424 	case '8':
425 	case '9':
426 	case 'A':
427 	case 'B':
428 	case 'C':
429 	case 'D':
430 	case 'E':
431 	case 'F':
432 	case 'G':
433 	case 'H':
434 	case 'I':
435 	case 'J':
436 	case 'K':
437 	case 'L':
438 	case 'M':
439 	case 'N':
440 	case 'O':
441 	case 'P':
442 	case 'Q':
443 	case 'R':
444 	case 'S':
445 	case 'T':
446 	case 'U':
447 	case 'V':
448 	case 'W':
449 	case 'X':
450 	case 'Y':
451 	case 'Z':
452 	case '_':
453 	case 'a':
454 	case 'b':
455 	case 'c':
456 	case 'd':
457 	case 'e':
458 	case 'f':
459 	case 'g':
460 	case 'h':
461 	case 'i':
462 	case 'j':
463 	case 'k':
464 	case 'l':
465 	case 'm':
466 	case 'n':
467 	case 'o':
468 	case 'p':
469 	case 'q':
470 	case 'r':
471 	case 's':
472 	case 't':
473 	case 'u':
474 	case 'v':
475 	case 'w':
476 	case 'x':
477 	case 'y':
478 	case 'z':	goto yy28;
479 	default:	goto yy30;
480 	}
481 yy30:
482 #line 247 "push_f.re"
483 	{ SEND(kIdentifier);     }
484 #line 485 "push_f.c"
485 yy31:
486 	yych = *++YYCURSOR;
487 	switch (yych) {
488 	case 'r':	goto yy38;
489 	default:	goto yy29;
490 	}
491 yy32:
492 	yych = *++YYCURSOR;
493 	switch (yych) {
494 	case 'l':	goto yy39;
495 	default:	goto yy29;
496 	}
497 yy33:
498 	yych = *++YYCURSOR;
499 	switch (yych) {
500 	case 'o':	goto yy40;
501 	default:	goto yy29;
502 	}
503 yy34:
504 	yych = *++YYCURSOR;
505 	switch (yych) {
506 	case 'o':	goto yy41;
507 	default:	goto yy29;
508 	}
509 yy35:
510 	yych = *++YYCURSOR;
511 	switch (yych) {
512 	case 'f':	goto yy42;
513 	default:	goto yy29;
514 	}
515 yy36:
516 	yych = *++YYCURSOR;
517 	switch (yych) {
518 	case 'e':	goto yy44;
519 	default:	goto yy29;
520 	}
521 yy37:
522 	yych = *++YYCURSOR;
523 	switch (yych) {
524 	case 'h':	goto yy45;
525 	default:	goto yy29;
526 	}
527 yy38:
528 	yych = *++YYCURSOR;
529 	switch (yych) {
530 	case 'e':	goto yy46;
531 	default:	goto yy29;
532 	}
533 yy39:
534 	yych = *++YYCURSOR;
535 	switch (yych) {
536 	case 's':	goto yy47;
537 	default:	goto yy29;
538 	}
539 yy40:
540 	yych = *++YYCURSOR;
541 	switch (yych) {
542 	case 'r':	goto yy48;
543 	default:	goto yy29;
544 	}
545 yy41:
546 	yych = *++YYCURSOR;
547 	switch (yych) {
548 	case 't':	goto yy50;
549 	default:	goto yy29;
550 	}
551 yy42:
552 	yych = *++YYCURSOR;
553 	switch (yych) {
554 	case '0':
555 	case '1':
556 	case '2':
557 	case '3':
558 	case '4':
559 	case '5':
560 	case '6':
561 	case '7':
562 	case '8':
563 	case '9':
564 	case 'A':
565 	case 'B':
566 	case 'C':
567 	case 'D':
568 	case 'E':
569 	case 'F':
570 	case 'G':
571 	case 'H':
572 	case 'I':
573 	case 'J':
574 	case 'K':
575 	case 'L':
576 	case 'M':
577 	case 'N':
578 	case 'O':
579 	case 'P':
580 	case 'Q':
581 	case 'R':
582 	case 'S':
583 	case 'T':
584 	case 'U':
585 	case 'V':
586 	case 'W':
587 	case 'X':
588 	case 'Y':
589 	case 'Z':
590 	case '_':
591 	case 'a':
592 	case 'b':
593 	case 'c':
594 	case 'd':
595 	case 'e':
596 	case 'f':
597 	case 'g':
598 	case 'h':
599 	case 'i':
600 	case 'j':
601 	case 'k':
602 	case 'l':
603 	case 'm':
604 	case 'n':
605 	case 'o':
606 	case 'p':
607 	case 'q':
608 	case 'r':
609 	case 's':
610 	case 't':
611 	case 'u':
612 	case 'v':
613 	case 'w':
614 	case 'x':
615 	case 'y':
616 	case 'z':	goto yy28;
617 	default:	goto yy43;
618 	}
619 yy43:
620 #line 240 "push_f.re"
621 	{ SEND(kIf);             }
622 #line 623 "push_f.c"
623 yy44:
624 	yych = *++YYCURSOR;
625 	switch (yych) {
626 	case 't':	goto yy51;
627 	default:	goto yy29;
628 	}
629 yy45:
630 	yych = *++YYCURSOR;
631 	switch (yych) {
632 	case 'i':	goto yy52;
633 	default:	goto yy29;
634 	}
635 yy46:
636 	yych = *++YYCURSOR;
637 	switch (yych) {
638 	case 'a':	goto yy53;
639 	default:	goto yy29;
640 	}
641 yy47:
642 	yych = *++YYCURSOR;
643 	switch (yych) {
644 	case 'e':	goto yy54;
645 	default:	goto yy29;
646 	}
647 yy48:
648 	yych = *++YYCURSOR;
649 	switch (yych) {
650 	case '0':
651 	case '1':
652 	case '2':
653 	case '3':
654 	case '4':
655 	case '5':
656 	case '6':
657 	case '7':
658 	case '8':
659 	case '9':
660 	case 'A':
661 	case 'B':
662 	case 'C':
663 	case 'D':
664 	case 'E':
665 	case 'F':
666 	case 'G':
667 	case 'H':
668 	case 'I':
669 	case 'J':
670 	case 'K':
671 	case 'L':
672 	case 'M':
673 	case 'N':
674 	case 'O':
675 	case 'P':
676 	case 'Q':
677 	case 'R':
678 	case 'S':
679 	case 'T':
680 	case 'U':
681 	case 'V':
682 	case 'W':
683 	case 'X':
684 	case 'Y':
685 	case 'Z':
686 	case '_':
687 	case 'a':
688 	case 'b':
689 	case 'c':
690 	case 'd':
691 	case 'e':
692 	case 'f':
693 	case 'g':
694 	case 'h':
695 	case 'i':
696 	case 'j':
697 	case 'k':
698 	case 'l':
699 	case 'm':
700 	case 'n':
701 	case 'o':
702 	case 'p':
703 	case 'q':
704 	case 'r':
705 	case 's':
706 	case 't':
707 	case 'u':
708 	case 'v':
709 	case 'w':
710 	case 'x':
711 	case 'y':
712 	case 'z':	goto yy28;
713 	default:	goto yy49;
714 	}
715 yy49:
716 #line 241 "push_f.re"
717 	{ SEND(kFor);            }
718 #line 719 "push_f.c"
719 yy50:
720 	yych = *++YYCURSOR;
721 	switch (yych) {
722 	case 'o':	goto yy56;
723 	default:	goto yy29;
724 	}
725 yy51:
726 	yych = *++YYCURSOR;
727 	switch (yych) {
728 	case 'u':	goto yy58;
729 	default:	goto yy29;
730 	}
731 yy52:
732 	yych = *++YYCURSOR;
733 	switch (yych) {
734 	case 'l':	goto yy59;
735 	default:	goto yy29;
736 	}
737 yy53:
738 	yych = *++YYCURSOR;
739 	switch (yych) {
740 	case 'k':	goto yy60;
741 	default:	goto yy29;
742 	}
743 yy54:
744 	yych = *++YYCURSOR;
745 	switch (yych) {
746 	case '0':
747 	case '1':
748 	case '2':
749 	case '3':
750 	case '4':
751 	case '5':
752 	case '6':
753 	case '7':
754 	case '8':
755 	case '9':
756 	case 'A':
757 	case 'B':
758 	case 'C':
759 	case 'D':
760 	case 'E':
761 	case 'F':
762 	case 'G':
763 	case 'H':
764 	case 'I':
765 	case 'J':
766 	case 'K':
767 	case 'L':
768 	case 'M':
769 	case 'N':
770 	case 'O':
771 	case 'P':
772 	case 'Q':
773 	case 'R':
774 	case 'S':
775 	case 'T':
776 	case 'U':
777 	case 'V':
778 	case 'W':
779 	case 'X':
780 	case 'Y':
781 	case 'Z':
782 	case '_':
783 	case 'a':
784 	case 'b':
785 	case 'c':
786 	case 'd':
787 	case 'e':
788 	case 'f':
789 	case 'g':
790 	case 'h':
791 	case 'i':
792 	case 'j':
793 	case 'k':
794 	case 'l':
795 	case 'm':
796 	case 'n':
797 	case 'o':
798 	case 'p':
799 	case 'q':
800 	case 'r':
801 	case 's':
802 	case 't':
803 	case 'u':
804 	case 'v':
805 	case 'w':
806 	case 'x':
807 	case 'y':
808 	case 'z':	goto yy28;
809 	default:	goto yy55;
810 	}
811 yy55:
812 #line 242 "push_f.re"
813 	{ SEND(kElse);           }
814 #line 815 "push_f.c"
815 yy56:
816 	yych = *++YYCURSOR;
817 	switch (yych) {
818 	case '0':
819 	case '1':
820 	case '2':
821 	case '3':
822 	case '4':
823 	case '5':
824 	case '6':
825 	case '7':
826 	case '8':
827 	case '9':
828 	case 'A':
829 	case 'B':
830 	case 'C':
831 	case 'D':
832 	case 'E':
833 	case 'F':
834 	case 'G':
835 	case 'H':
836 	case 'I':
837 	case 'J':
838 	case 'K':
839 	case 'L':
840 	case 'M':
841 	case 'N':
842 	case 'O':
843 	case 'P':
844 	case 'Q':
845 	case 'R':
846 	case 'S':
847 	case 'T':
848 	case 'U':
849 	case 'V':
850 	case 'W':
851 	case 'X':
852 	case 'Y':
853 	case 'Z':
854 	case '_':
855 	case 'a':
856 	case 'b':
857 	case 'c':
858 	case 'd':
859 	case 'e':
860 	case 'f':
861 	case 'g':
862 	case 'h':
863 	case 'i':
864 	case 'j':
865 	case 'k':
866 	case 'l':
867 	case 'm':
868 	case 'n':
869 	case 'o':
870 	case 'p':
871 	case 'q':
872 	case 'r':
873 	case 's':
874 	case 't':
875 	case 'u':
876 	case 'v':
877 	case 'w':
878 	case 'x':
879 	case 'y':
880 	case 'z':	goto yy28;
881 	default:	goto yy57;
882 	}
883 yy57:
884 #line 243 "push_f.re"
885 	{ SEND(kGoto);           }
886 #line 887 "push_f.c"
887 yy58:
888 	yych = *++YYCURSOR;
889 	switch (yych) {
890 	case 'r':	goto yy62;
891 	default:	goto yy29;
892 	}
893 yy59:
894 	yych = *++YYCURSOR;
895 	switch (yych) {
896 	case 'e':	goto yy63;
897 	default:	goto yy29;
898 	}
899 yy60:
900 	yych = *++YYCURSOR;
901 	switch (yych) {
902 	case '0':
903 	case '1':
904 	case '2':
905 	case '3':
906 	case '4':
907 	case '5':
908 	case '6':
909 	case '7':
910 	case '8':
911 	case '9':
912 	case 'A':
913 	case 'B':
914 	case 'C':
915 	case 'D':
916 	case 'E':
917 	case 'F':
918 	case 'G':
919 	case 'H':
920 	case 'I':
921 	case 'J':
922 	case 'K':
923 	case 'L':
924 	case 'M':
925 	case 'N':
926 	case 'O':
927 	case 'P':
928 	case 'Q':
929 	case 'R':
930 	case 'S':
931 	case 'T':
932 	case 'U':
933 	case 'V':
934 	case 'W':
935 	case 'X':
936 	case 'Y':
937 	case 'Z':
938 	case '_':
939 	case 'a':
940 	case 'b':
941 	case 'c':
942 	case 'd':
943 	case 'e':
944 	case 'f':
945 	case 'g':
946 	case 'h':
947 	case 'i':
948 	case 'j':
949 	case 'k':
950 	case 'l':
951 	case 'm':
952 	case 'n':
953 	case 'o':
954 	case 'p':
955 	case 'q':
956 	case 'r':
957 	case 's':
958 	case 't':
959 	case 'u':
960 	case 'v':
961 	case 'w':
962 	case 'x':
963 	case 'y':
964 	case 'z':	goto yy28;
965 	default:	goto yy61;
966 	}
967 yy61:
968 #line 244 "push_f.re"
969 	{ SEND(kBreak);          }
970 #line 971 "push_f.c"
971 yy62:
972 	yych = *++YYCURSOR;
973 	switch (yych) {
974 	case 'n':	goto yy65;
975 	default:	goto yy29;
976 	}
977 yy63:
978 	yych = *++YYCURSOR;
979 	switch (yych) {
980 	case '0':
981 	case '1':
982 	case '2':
983 	case '3':
984 	case '4':
985 	case '5':
986 	case '6':
987 	case '7':
988 	case '8':
989 	case '9':
990 	case 'A':
991 	case 'B':
992 	case 'C':
993 	case 'D':
994 	case 'E':
995 	case 'F':
996 	case 'G':
997 	case 'H':
998 	case 'I':
999 	case 'J':
1000 	case 'K':
1001 	case 'L':
1002 	case 'M':
1003 	case 'N':
1004 	case 'O':
1005 	case 'P':
1006 	case 'Q':
1007 	case 'R':
1008 	case 'S':
1009 	case 'T':
1010 	case 'U':
1011 	case 'V':
1012 	case 'W':
1013 	case 'X':
1014 	case 'Y':
1015 	case 'Z':
1016 	case '_':
1017 	case 'a':
1018 	case 'b':
1019 	case 'c':
1020 	case 'd':
1021 	case 'e':
1022 	case 'f':
1023 	case 'g':
1024 	case 'h':
1025 	case 'i':
1026 	case 'j':
1027 	case 'k':
1028 	case 'l':
1029 	case 'm':
1030 	case 'n':
1031 	case 'o':
1032 	case 'p':
1033 	case 'q':
1034 	case 'r':
1035 	case 's':
1036 	case 't':
1037 	case 'u':
1038 	case 'v':
1039 	case 'w':
1040 	case 'x':
1041 	case 'y':
1042 	case 'z':	goto yy28;
1043 	default:	goto yy64;
1044 	}
1045 yy64:
1046 #line 245 "push_f.re"
1047 	{ SEND(kWhile);          }
1048 #line 1049 "push_f.c"
1049 yy65:
1050 	yych = *++YYCURSOR;
1051 	switch (yych) {
1052 	case '0':
1053 	case '1':
1054 	case '2':
1055 	case '3':
1056 	case '4':
1057 	case '5':
1058 	case '6':
1059 	case '7':
1060 	case '8':
1061 	case '9':
1062 	case 'A':
1063 	case 'B':
1064 	case 'C':
1065 	case 'D':
1066 	case 'E':
1067 	case 'F':
1068 	case 'G':
1069 	case 'H':
1070 	case 'I':
1071 	case 'J':
1072 	case 'K':
1073 	case 'L':
1074 	case 'M':
1075 	case 'N':
1076 	case 'O':
1077 	case 'P':
1078 	case 'Q':
1079 	case 'R':
1080 	case 'S':
1081 	case 'T':
1082 	case 'U':
1083 	case 'V':
1084 	case 'W':
1085 	case 'X':
1086 	case 'Y':
1087 	case 'Z':
1088 	case '_':
1089 	case 'a':
1090 	case 'b':
1091 	case 'c':
1092 	case 'd':
1093 	case 'e':
1094 	case 'f':
1095 	case 'g':
1096 	case 'h':
1097 	case 'i':
1098 	case 'j':
1099 	case 'k':
1100 	case 'l':
1101 	case 'm':
1102 	case 'n':
1103 	case 'o':
1104 	case 'p':
1105 	case 'q':
1106 	case 'r':
1107 	case 's':
1108 	case 't':
1109 	case 'u':
1110 	case 'v':
1111 	case 'w':
1112 	case 'x':
1113 	case 'y':
1114 	case 'z':	goto yy28;
1115 	default:	goto yy66;
1116 	}
1117 yy66:
1118 #line 246 "push_f.re"
1119 	{ SEND(kReturn);         }
1120 #line 1121 "push_f.c"
1121 #line 262 "push_f.re"
1122 
1123 
1124     fill:
1125         ssize_t unfinishedSize = cursor-start;
1126         printf(
1127             "scanner needs a refill. Exiting for now with:\n"
1128             "    saved fill state = %d\n"
1129             "    unfinished token size = %d\n",
1130             state,
1131             unfinishedSize
1132         );
1133 
1134         if(0<unfinishedSize && start<limit)
1135         {
1136             printf("    unfinished token is :");
1137             fwrite(start, 1, cursor-start, stdout);
1138             putchar('\n');
1139         }
1140         putchar('\n');
1141 
1142         /*
1143          * Once we get here, we can get rid of
1144          * everything before start and after limit.
1145          */
1146         if(eof==true) goto start;
1147         if(buffer<start)
1148         {
1149             size_t startOffset = start-buffer;
1150             memmove(buffer, start, limit-start);
1151             marker -= startOffset;
1152             cursor -= startOffset;
1153             limit -= startOffset;
1154             start -= startOffset;
1155         }
1156         return 0;
1157     }
1158 };
1159 
1160 // ----------------------------------------------------------------------
main(int argc,char ** argv)1161 int main(
1162     int     argc,
1163     char    **argv
1164 )
1165 {
1166     // Parse cmd line
1167     int input = 0;
1168     if(1<argc)
1169     {
1170         input = open(argv[1], O_RDONLY | O_BINARY);
1171         if(input<0)
1172         {
1173             fprintf(
1174                 stderr,
1175                 "could not open file %s\n",
1176                 argv[1]
1177             );
1178             exit(1);
1179         }
1180     }
1181 
1182     /*
1183      * Tokenize input file by pushing batches
1184      * of data one by one into the scanner.
1185      */
1186     const size_t batchSize = 256;
1187     uint8_t buffer[batchSize];
1188     PushScanner scanner;
1189     while(1)
1190     {
1191         ssize_t n = read(input, buffer, batchSize);
1192         scanner.push(buffer, n);
1193         if(n<batchSize) break;
1194     }
1195     scanner.push(0, -1);
1196     close(input);
1197 
1198     // Done
1199     return 0;
1200 }
1201 
1202 push_f.re:238:22: warning: escape has no effect: '\h' [-Wuseless-escape]
1203