home *** CD-ROM | disk | FTP | other *** search
/ Total Destruction / Total_Destruction.iso / addons / Lccwin32.exe / Lccwin32 / lccpub / src / lex.c < prev    next >
Encoding:
C/C++ Source or Header  |  1997-11-11  |  32.0 KB  |  1,307 lines

  1. #include "c.h"
  2. #include <errno.h>
  3. //int DefaultAlignment = 16;
  4. #define MAXTOKEN 32
  5. int StatementCount=0;
  6. static int statementLevel;
  7. enum { BLANK=01,  NEWLINE=02, LETTER=04,
  8.        DIGIT=010, HEX=020,    OTHER=040 };
  9.  
  10. static unsigned char map[256] = { /* 000 nul */    0,
  11.                    /* 001 soh */    0,
  12.                    /* 002 stx */    0,
  13.                    /* 003 etx */    0,
  14.                    /* 004 eot */    0,
  15.                    /* 005 enq */    0,
  16.                    /* 006 ack */    0,
  17.                    /* 007 bel */    0,
  18.                    /* 010 bs  */    0,
  19.                    /* 011 ht  */    BLANK,
  20.                    /* 012 nl  */    NEWLINE,
  21.                    /* 013 vt  */    BLANK,
  22.                    /* 014 ff  */    BLANK,
  23.                    /* 015 cr  */    0,
  24.                    /* 016 so  */    0,
  25.                    /* 017 si  */    0,
  26.                    /* 020 dle */    0,
  27.                    /* 021 dc1 */    0,
  28.                    /* 022 dc2 */    0,
  29.                    /* 023 dc3 */    0,
  30.                    /* 024 dc4 */    0,
  31.                    /* 025 nak */    0,
  32.                    /* 026 syn */    0,
  33.                    /* 027 etb */    0,
  34.                    /* 030 can */    0,
  35.                    /* 031 em  */    0,
  36.                    /* 032 sub */    0,
  37.                    /* 033 esc */    0,
  38.                    /* 034 fs  */    0,
  39.                    /* 035 gs  */    0,
  40.                    /* 036 rs  */    0,
  41.                    /* 037 us  */    0,
  42.                    /* 040 sp  */    BLANK,
  43.                    /* 041 !   */    OTHER,
  44.                    /* 042 "   */    OTHER,
  45.                    /* 043 #   */    OTHER,
  46.                    /* 044 $   */    0,
  47.                    /* 045 %   */    OTHER,
  48.                    /* 046 &   */    OTHER,
  49.                    /* 047 '   */    OTHER,
  50.                    /* 050 (   */    OTHER,
  51.                    /* 051 )   */    OTHER,
  52.                    /* 052 *   */    OTHER,
  53.                    /* 053 +   */    OTHER,
  54.                    /* 054 ,   */    OTHER,
  55.                    /* 055 -   */    OTHER,
  56.                    /* 056 .   */    OTHER,
  57.                    /* 057 /   */    OTHER,
  58.                    /* 060 0   */    DIGIT,
  59.                    /* 061 1   */    DIGIT,
  60.                    /* 062 2   */    DIGIT,
  61.                    /* 063 3   */    DIGIT,
  62.                    /* 064 4   */    DIGIT,
  63.                    /* 065 5   */    DIGIT,
  64.                    /* 066 6   */    DIGIT,
  65.                    /* 067 7   */    DIGIT,
  66.                    /* 070 8   */    DIGIT,
  67.                    /* 071 9   */    DIGIT,
  68.                    /* 072 :   */    OTHER,
  69.                    /* 073 ;   */    OTHER,
  70.                    /* 074 <   */    OTHER,
  71.                    /* 075 =   */    OTHER,
  72.                    /* 076 >   */    OTHER,
  73.                    /* 077 ?   */    OTHER,
  74.                    /* 100 @   */    0,
  75.                    /* 101 A   */    LETTER|HEX,
  76.                    /* 102 B   */    LETTER|HEX,
  77.                    /* 103 C   */    LETTER|HEX,
  78.                    /* 104 D   */    LETTER|HEX,
  79.                    /* 105 E   */    LETTER|HEX,
  80.                    /* 106 F   */    LETTER|HEX,
  81.                    /* 107 G   */    LETTER,
  82.                    /* 110 H   */    LETTER,
  83.                    /* 111 I   */    LETTER,
  84.                    /* 112 J   */    LETTER,
  85.                    /* 113 K   */    LETTER,
  86.                    /* 114 L   */    LETTER,
  87.                    /* 115 M   */    LETTER,
  88.                    /* 116 N   */    LETTER,
  89.                    /* 117 O   */    LETTER,
  90.                    /* 120 P   */    LETTER,
  91.                    /* 121 Q   */    LETTER,
  92.                    /* 122 R   */    LETTER,
  93.                    /* 123 S   */    LETTER,
  94.                    /* 124 T   */    LETTER,
  95.                    /* 125 U   */    LETTER,
  96.                    /* 126 V   */    LETTER,
  97.                    /* 127 W   */    LETTER,
  98.                    /* 130 X   */    LETTER,
  99.                    /* 131 Y   */    LETTER,
  100.                    /* 132 Z   */    LETTER,
  101.                    /* 133 [   */    OTHER,
  102.                    /* 134 \   */    OTHER,
  103.                    /* 135 ]   */    OTHER,
  104.                    /* 136 ^   */    OTHER,
  105.                    /* 137 _   */    LETTER,
  106.                    /* 140 `   */    0,
  107.                    /* 141 a   */    LETTER|HEX,
  108.                    /* 142 b   */    LETTER|HEX,
  109.                    /* 143 c   */    LETTER|HEX,
  110.                    /* 144 d   */    LETTER|HEX,
  111.                    /* 145 e   */    LETTER|HEX,
  112.                    /* 146 f   */    LETTER|HEX,
  113.                    /* 147 g   */    LETTER,
  114.                    /* 150 h   */    LETTER,
  115.                    /* 151 i   */    LETTER,
  116.                    /* 152 j   */    LETTER,
  117.                    /* 153 k   */    LETTER,
  118.                    /* 154 l   */    LETTER,
  119.                    /* 155 m   */    LETTER,
  120.                    /* 156 n   */    LETTER,
  121.                    /* 157 o   */    LETTER,
  122.                    /* 160 p   */    LETTER,
  123.                    /* 161 q   */    LETTER,
  124.                    /* 162 r   */    LETTER,
  125.                    /* 163 s   */    LETTER,
  126.                    /* 164 t   */    LETTER,
  127.                    /* 165 u   */    LETTER,
  128.                    /* 166 v   */    LETTER,
  129.                    /* 167 w   */    LETTER,
  130.                    /* 170 x   */    LETTER,
  131.                    /* 171 y   */    LETTER,
  132.                    /* 172 z   */    LETTER,
  133.                    /* 173 {   */    OTHER,
  134.                    /* 174 |   */    OTHER,
  135.                    /* 175 }   */    OTHER,
  136.                    /* 176 ~   */    OTHER, 
  137.                    /* 177 del */    OTHER,
  138.                    /* 200     */    LETTER,
  139.                     /* 130     */    LETTER,
  140.                     /* 200     */    LETTER,
  141.                     /* 200     */    LETTER,
  142.                     /* 200     */    LETTER,
  143.                     /* 200     */    LETTER,
  144.                    /* 135     */    LETTER,
  145.                    /* 200     */    LETTER,
  146.                    /* 200     */    LETTER,
  147.                    /* 200     */    LETTER,
  148.                    /* 200     */    LETTER,
  149.                    /* 140     */    LETTER,
  150.                    /* 200     */    LETTER,
  151.                    /* 200     */    LETTER,
  152.                    /* 200     */    LETTER,
  153.                    /* 200     */    LETTER,
  154.                    /* 145     */    LETTER,
  155.                    /* 200     */    LETTER,
  156.                    /* 200     */    LETTER,
  157.                    /* 200     */    LETTER,
  158.                    /* 200     */    LETTER,
  159.                    /* 150     */    LETTER,
  160.                    /* 200     */    LETTER,
  161.                    /* 200     */    LETTER,
  162.                    /* 200     */    LETTER,
  163.                    /* 200     */    LETTER,
  164.                    /* 155     */    LETTER,
  165.                    /* 200     */    LETTER,
  166.                    /* 200     */    LETTER,
  167.                    /* 200     */    LETTER,
  168.                    /* 200     */    LETTER,
  169.                    /* 160     */    LETTER,
  170.                    /* 200     */    LETTER,
  171.                    /* 200     */    LETTER,
  172.                    /* 200     */    LETTER,
  173.                    /* 200     */    LETTER,
  174.                    /* 165     */    LETTER,
  175.                    /* 200     */    LETTER,
  176.                    /* 200     */    LETTER,
  177.                    /* 200     */    LETTER,
  178.                    /* 200     */    LETTER,
  179.                    /* 170     */    LETTER,
  180.                    /* 200     */    LETTER,
  181.                    /* 200     */    LETTER,
  182.                    /* 200     */    LETTER,
  183.                    /* 200     */    LETTER,
  184.                    /* 175     */    LETTER,
  185.                    /* 200     */    LETTER,
  186.                    /* 200     */    LETTER,
  187.                    /* 200     */    LETTER,
  188.                    /* 200     */    LETTER,
  189.                    /* 180     */    LETTER,
  190.                    /* 200     */    LETTER,
  191.                    /* 200     */    LETTER,
  192.                    /* 200     */    LETTER,
  193.                    /* 200     */    LETTER,
  194.                    /* 185     */    LETTER,
  195.                    /* 200     */    LETTER,
  196.                    /* 200     */    LETTER,
  197.                    /* 200     */    LETTER,
  198.                    /* 200     */    LETTER,
  199.                    /* 190     */    LETTER,
  200.                    /* 200     */    LETTER,
  201.                    /* 200     */    LETTER,
  202.                    /* 200     */    LETTER,
  203.                    /* 200     */    LETTER,
  204.                    /* 195     */    LETTER,
  205.                    /* 200     */    LETTER,
  206.                    /* 200     */    LETTER,
  207.                    /* 200     */    LETTER,
  208.                    /* 200     */    LETTER,
  209.                    /* 200     */    LETTER,
  210.                    /* 200     */    LETTER,
  211.                    /* 200     */    LETTER,
  212.                    /* 200     */    LETTER,
  213.                    /* 200     */    LETTER,
  214.                    /* 205     */    LETTER,
  215.                    /* 200     */    LETTER,
  216.                    /* 200     */    LETTER,
  217.                    /* 200     */    LETTER,
  218.                    /* 200     */    LETTER,
  219.                    /* 210     */    LETTER,
  220.                    /* 200     */    LETTER,
  221.                    /* 200     */    LETTER,
  222.                    /* 200     */    LETTER,
  223.                    /* 200     */    LETTER,
  224.                    /* 215     */    LETTER,
  225.                    /* 200     */    LETTER,
  226.                    /* 200     */    LETTER,
  227.                    /* 200     */    LETTER,
  228.                    /* 200     */    LETTER,
  229.                    /* 220     */    LETTER,
  230.                    /* 200     */    LETTER,
  231.                    /* 200     */    LETTER,
  232.                    /* 200     */    LETTER,
  233.                    /* 200     */    LETTER,
  234.                    /* 225     */    LETTER,
  235.                    /* 200     */    LETTER,
  236.                    /* 200     */    LETTER,
  237.                    /* 200     */    LETTER,
  238.                    /* 200     */    LETTER,
  239.                    /* 230     */    LETTER,
  240.                    /* 200     */    LETTER,
  241.                    /* 200     */    LETTER,
  242.                    /* 200     */    LETTER,
  243.                    /* 200     */    LETTER,
  244.                    /* 235     */    LETTER,
  245.                    /* 200     */    LETTER,
  246.                    /* 200     */    LETTER,
  247.                    /* 200     */    LETTER,
  248.                    /* 200     */    LETTER,
  249.                    /* 240     */    LETTER,
  250.                    /* 200     */    LETTER,
  251.                    /* 200     */    LETTER,
  252.                    /* 200     */    LETTER,
  253.                    /* 200     */    LETTER,
  254.                    /* 245     */    LETTER,
  255.                    /* 200     */    LETTER,
  256.                    /* 200     */    LETTER,
  257.                    /* 200     */    LETTER,
  258.                    /* 200     */    LETTER,
  259.                    /* 250     */    LETTER,
  260.                    /* 200     */    LETTER,
  261.                    /* 200     */    LETTER,
  262.                    /* 200     */    LETTER,
  263.                    /* 200     */    LETTER,
  264.  
  265. };
  266. static struct symbol tval;
  267. static int backslash ARGS((int q));
  268. static Symbol fcon ARGS((void));
  269. static Symbol icon ARGS((unsigned int, int, int));
  270. static void ppnumber ARGS((char *));
  271. Coordinate src;        /* current source coordinate */
  272. int t;
  273. char *token;        /* current token */
  274. Symbol tsym;        /* symbol table entry for current token */
  275.  
  276. #ifdef BUILTIN_ASM
  277. /* asmargs - break out %name in string p, fill in argv, returned edited string */
  278. static char *asmargs(Symbol p,Symbol argv[],int size)
  279. {
  280.         int n = 0;
  281.         char *s1, *s2, str[MAXLINE];
  282.  
  283.         if (p->type->size >= MAXLINE) {
  284.                 error("asm string too long\n");
  285.                 return "";
  286.         }
  287.         for (s2 = str, s1 = p->u.c.v.p; *s1; )
  288.                 if ((*s2++ = *s1++) == '%' && *s1 && map[*s1]&LETTER) {
  289.                         char *t = s1;
  290.                         while (*t && map[*t]&(LETTER|DIGIT))
  291.                                 t++;
  292.                         if ((argv[n] = lookup(stringn(s1, t - s1), identifiers))
  293.                         && argv[n]->sclass != TYPEDEF && argv[n]->sclass != ENUM) {
  294.                                 argv[n]->ref += refinc;
  295.                                 argv[n]->references++;
  296.                                 argv[n]->lastuse = StatementCount;
  297. //                                argv[n]->initialized = 1;       /* in case ref overflows */
  298.                                 if (++n == size) {
  299.                                         error("too many variable references in asm string\n");
  300.                                         n = size - 1;
  301.                                 } else {
  302.                                         *s2++ = n - 1;
  303.                                         s1 = t;
  304.                                 }
  305.                         }
  306.                 }
  307.         *s2 = 0;
  308.         argv[n] = 0;
  309.         return stringn(str, s2 - str);
  310. }
  311.  
  312. static void assem(void) {
  313.         if (Aflag >= 2)
  314.                 warning("non-ANSI asm\n");
  315.         t = gettok();
  316.         if (t == '{') {
  317.             do {
  318.                 t = gettok();
  319.             } while (t != '}');
  320.             return;
  321.         }
  322.         expect('(');
  323.         if (t == SCON) {
  324.                 char *s;
  325.                 Symbol *argv = (Symbol *)allocate(11*sizeof(Symbol *),FUNC);
  326.                 s = asmargs(tsym, argv, 11);
  327.                 if (fname) {
  328.                         walk(0, 0, 0);
  329.                         code(Start);    /* prevent unreachable code message */
  330.                         code(Asm);
  331.                         codelist->u.acode.code = s;
  332.                         codelist->u.acode.argv = argv;
  333.                 } else
  334.                         asmcode(s, argv);
  335.                 t = gettok();
  336.         } else
  337.                 error("missing string constant in asm\n");
  338.         if (t != ')')
  339.                 expect(')');
  340. }
  341. #endif                                                                               
  342.  
  343.  
  344.  
  345.  
  346. int gettok(void) {
  347.     for (;;) {
  348.         register unsigned char *rcp = cp;
  349.         while (map[*rcp]&BLANK)
  350.             rcp++;
  351.         if (limit - rcp < MAXTOKEN) {
  352.             cp = rcp;
  353.             fillbuf();
  354.             rcp = cp;
  355.         }
  356.         src.file = file;
  357.         src.x = (char *)rcp - line;
  358.         src.y = lineno;
  359.         cp = rcp + 1;
  360.         switch (*rcp++) {
  361.         case '/': if (*rcp == '*') {
  362.                   int c = 0;
  363.                   for (rcp++; *rcp != '/' || c != '*'; )
  364.                       if (map[*rcp]&NEWLINE) {
  365.                           if (rcp < limit)
  366.                               c = *rcp;
  367.                           cp = rcp + 1;
  368.                           nextline();
  369.                           rcp = cp;
  370.                           if (rcp == limit)
  371.                               break;
  372.                       } else
  373.                           c = *rcp++;
  374.                   if (rcp < limit)
  375.                       rcp++;
  376.                   else
  377.                       error("unclosed comment\n");
  378.                   cp = rcp;
  379.                   continue;
  380.               }
  381.               return '/';
  382.         case 'L': if (*rcp == '\'') {
  383.                   int t = gettok();
  384.                   assert(t == ICON);
  385.                   src.x--;
  386.                   tval.type = unsignedchar;
  387.                   tval.u.c.v.uc = (unsigned char)tval.u.c.v.i;
  388.                   return t;
  389.               }
  390.               if (*rcp != '"')
  391.                   goto id;
  392.               cp = rcp + 1;
  393.               goto scon;
  394. case '<':
  395.     if (*rcp == '=') return cp++, LEQ;
  396.     if (*rcp == '<') return cp++, LSHIFT;
  397.     return '<';
  398. case '>':
  399.     if (*rcp == '=') return cp++, GEQ;
  400.     if (*rcp == '>') return cp++, RSHIFT;
  401.     return '>';
  402. case '-':
  403.     if (*rcp == '>') return cp++, DEREF;
  404.     if (*rcp == '-') return cp++, DECR;
  405.     return '-';
  406. case '=': return *rcp == '=' ? cp++, EQL    : '=';
  407. case '!': return *rcp == '=' ? cp++, NEQ    : '!';
  408. case '|': return *rcp == '|' ? cp++, OROR   : '|';
  409. case '&': return *rcp == '&' ? cp++, ANDAND : '&';
  410. case '+': return *rcp == '+' ? cp++, INCR   : '+';
  411. case ',': case ':':
  412. case '*': case '~': case '%': case '^': case '?':
  413. case '[': case ']': case '(': case ')': 
  414.     return rcp[-1];
  415.         case ';':
  416.             return rcp[-1];
  417.         case '{':
  418.             statementLevel++;
  419.             return rcp[-1];
  420.         case '}':
  421.             if (statementLevel) statementLevel--;
  422.             return rcp[-1];
  423.         case '\n': case '\v': case '\r': case '\f':
  424.             nextline();
  425.             if (cp == limit) {
  426.                 tsym = NULL;
  427.                 return EOI;
  428.             }
  429.             continue;
  430.  
  431.         case 'i':
  432.             if (rcp[0] == 'f'
  433.             && !(map[rcp[1]]&(DIGIT|LETTER))) {
  434.                 cp = rcp + 1;
  435.                 return IF;
  436.             }
  437.             if (rcp[0] == 'n'
  438.             &&  rcp[1] == 't'
  439.             && !(map[rcp[2]]&(DIGIT|LETTER))) {
  440.                 cp = rcp + 2;
  441.                 tsym = inttype->u.sym;
  442.                 return INT;
  443.             }
  444.             goto id;
  445.         case '_':
  446.             if (rcp[0] != 'p' && rcp[0] != 's' && rcp[0] != 'a' && rcp[0] != '_') goto id;
  447.             if (rcp[0] == 'p' &&
  448.                 rcp[1] == 'a' &&
  449.                 rcp[2] == 's' &&
  450.                 rcp[3] == 'c' &&
  451.                 rcp[4] == 'a' &&
  452.                 rcp[5] == 'l' &&
  453.                 !(map[rcp[6]]&(DIGIT|LETTER))) {
  454.                 cp = rcp + 6;
  455.                 return PASCALKEYW;
  456.             }
  457.             if (rcp[0] == 's' &&
  458.                 rcp[1] == 't' &&
  459.                 rcp[2] == 'd' &&
  460.                 rcp[3] == 'c' &&
  461.                 rcp[4] == 'a' &&
  462.                 rcp[5] == 'l' &&
  463.                 rcp[6] == 'l' &&
  464.                 !(map[rcp[7]]&(DIGIT|LETTER))) {
  465.                 cp = rcp + 7;
  466.                 return STDCALL;
  467.             }
  468.             if (rcp[0] == 'a' && 
  469.                 rcp[1] == 's' &&
  470.                 rcp[2] == 'm' &&
  471.                 !(map[rcp[3]]&(DIGIT|LETTER))) {
  472.                 cp = rcp+3;
  473.                 assem();
  474.                 return(gettok());
  475.             }
  476.             if (rcp[0] == '_' &&
  477.                 rcp[1] == 't' &&
  478.                 rcp[2] == 'r' &&
  479.                 rcp[3] == 'y' &&
  480.                 !(map[rcp[4]]&(DIGIT|LETTER))) {
  481.                     cp = rcp+4;
  482.                     doTry();
  483.                     return(gettok());
  484.                 }
  485.             if (rcp[0] == '_' &&
  486.                 rcp[1] == 'e' &&
  487.                 rcp[2] == 'x' &&
  488.                 rcp[3] == 'c' &&
  489.                 rcp[4] == 'e' &&
  490.                 rcp[5] == 'p' &&
  491.                 rcp[6] == 't' &&
  492.                 !(map[rcp[7]]&(DIGIT|LETTER))) {
  493.                     cp = rcp+7;
  494.                     doExcept();
  495.                     return(t);
  496.                 }
  497.  
  498.             goto id;
  499.  
  500.         case 'h': case 'j': case 'k': case 'm': case 'n': case 'o':
  501.         case 'p': case 'q': case 'x': case 'y': case 'z':
  502.         case 'A': case 'B': case 'C': case 'D': case 'E': case 'F':
  503.         case 'G': case 'H': case 'I': case 'J': case 'K':
  504.         case 'M': case 'N': case 'O': case 'P': case 'Q': case 'R':
  505.         case 'S': case 'T': case 'U': case 'V': case 'W': case 'X':
  506.         case 'Y': case 'Z': 
  507.         id:
  508.             if (limit - rcp < MAXLINE) {
  509.                 cp = rcp - 1;
  510.                 fillbuf();
  511.                 rcp = ++cp;
  512.             }
  513.             assert(cp == rcp);
  514.             token = (char *)rcp - 1;
  515.             while (map[*rcp]&(DIGIT|LETTER))
  516.                 rcp++;
  517.             token = stringn(token, (char *)rcp - token);
  518.             tsym = lookup(token, identifiers);
  519.             cp = rcp;
  520.             return ID;
  521.         case '0': case '1': case '2': case '3': case '4':
  522.         case '5': case '6': case '7': case '8': case '9': {
  523.             unsigned int n = 0;
  524.             if (limit - rcp < MAXLINE) {
  525.                 cp = rcp - 1;
  526.                 fillbuf();
  527.                 rcp = ++cp;
  528.             }
  529.             assert(cp == rcp);
  530.             token = (char *)rcp - 1;
  531.             if (*token == '0' && (*rcp == 'x' || *rcp == 'X')) {
  532.                 int d, overflow = 0;
  533.                 while (*++rcp) {
  534.                     if (map[*rcp]&DIGIT)
  535.                         d = *rcp - '0';
  536.                     else if (*rcp >= 'a' && *rcp <= 'f')
  537.                         d = *rcp - 'a' + 10;
  538.                     else if (*rcp >= 'A' && *rcp <= 'F')
  539.                         d = *rcp - 'A' + 10;
  540.                     else
  541.                         break;
  542.                     if (n&~((unsigned)-1 >> 4))
  543.                         overflow = 1;
  544.                     else
  545.                         n = (n<<4) + d;
  546.                 }
  547.                 if ((char *)rcp - token <= 2)
  548.                     error("invalid hexadecimal constant `%S'\n", token, (char *)rcp-token);
  549.                 cp = rcp;
  550.                 tsym = icon(n, overflow, 16);
  551.             } else if (*token == '0') {
  552.                 int err = 0, overflow = 0;
  553.                 for ( ; map[*rcp]&DIGIT; rcp++) {
  554.                     if (*rcp == '8' || *rcp == '9')
  555.                         err = 1;
  556.                     if (n&~((unsigned)-1 >> 3))
  557.                         overflow = 1;
  558.                     else
  559.                         n = (n<<3) + (unsigned)(*rcp - '0');
  560.                 }
  561. if (*rcp == '.' || *rcp == 'e' || *rcp == 'E') {
  562.     cp = rcp;
  563.     tsym = fcon();
  564.     return FCON;
  565. }
  566.                 cp = rcp;
  567.                 tsym = icon(n, overflow, 8);
  568.                 if (err)
  569.                     error("invalid octal constant `%S'\n", token, (char*)cp-token);
  570.             } else {
  571.                 int overflow = 0;
  572.                 for (n = *token - '0'; map[*rcp]&DIGIT; ) {
  573.                     int d = *rcp++ - '0';
  574.                     if (n > ((unsigned)UINT_MAX - d)/10)
  575.                         overflow = 1;
  576.                     else
  577.                         n = 10*n + d;
  578.                 }
  579. if (*rcp == '.' || *rcp == 'e' || *rcp == 'E') {
  580.     cp = rcp;
  581.     tsym = fcon();
  582.     return FCON;
  583. }
  584.                 cp = rcp;
  585.                 tsym = icon(n, overflow, 10);
  586.             }
  587.             return ICON;
  588.         }
  589.         case '.':
  590.             if (rcp[0] == '.' && rcp[1] == '.') {
  591.                 cp += 2;
  592.                 return ELLIPSIS;
  593.             }
  594.             if ((map[*rcp]&DIGIT) == 0)
  595.                 return '.';
  596.             if (limit - rcp < MAXLINE) {
  597.                 cp = rcp - 1;
  598.                 fillbuf();
  599.                 rcp = ++cp;
  600.             }
  601.             assert(cp == rcp);
  602.             cp = rcp - 1;
  603.             token = (char *)cp;
  604.             tsym = fcon();
  605.             return FCON;
  606.         scon:
  607.         case '\'': case '"': {
  608.             static char cbuf[BUFSIZE+1];
  609.             char *s = cbuf;
  610.             int nbad = 0;
  611.             *s++ = *--cp;
  612.             do {
  613.                 cp++;
  614.                 while (*cp != cbuf[0]) {
  615.                     int c;
  616.                     if (map[*cp]&NEWLINE) {
  617.                         if (cp < limit)
  618.                             break;
  619.                         cp++;
  620.                         nextline();
  621.                         if (cp == limit)
  622.                             break;
  623.                         continue;
  624.                     }
  625.                     c = *cp++;
  626. #ifdef JAPAN                            // DBCS (Shift-KIS) trap
  627.                                         if (((0x80 < c) && (c <= 0x9f)) ||
  628.                                                 ((0xe0 <= c) && (c <= 0xff))) {
  629.                                                 if (s < &cbuf[sizeof cbuf] - 3) {
  630.                                                         *s++ = (char)c;
  631.                                                         c = *cp++;
  632.                                                         *s++ = (char)c;
  633.                                                         continue;
  634.                                                 }
  635.                                         }
  636. #endif
  637.                     if (c == '\\') {
  638.                         if (map[*cp]&NEWLINE) {
  639.                             if (cp < limit)
  640.                                 break;
  641.                             cp++;
  642.                             nextline();
  643.                         }
  644.                         if (limit - cp < MAXTOKEN)
  645.                             fillbuf();
  646.                         c = backslash(cbuf[0]);
  647.                     } else if (map[c] == 0)
  648.                         nbad++;
  649.                     if (s < &cbuf[sizeof cbuf] - 2)
  650.                         *s++ = (char)c;
  651.                 }
  652.                 if (*cp == cbuf[0])
  653.                     cp++;
  654.                 else
  655.                     error("missing %c\n", cbuf[0]);
  656.             } while (cbuf[0] == '"' && getchr() == '"');
  657.             *s++ = 0;
  658.             if (s >= &cbuf[sizeof cbuf])
  659.                 error("%s literal too long\n",
  660.                     cbuf[0] == '"' ? "string" : "character");
  661.             if (Aflag >= 2 && cbuf[0] == '"' && s - cbuf - 1 > 509)
  662.                 warning("more than 509 characters in a string literal\n");
  663.             if (Aflag >= 2 && nbad)
  664.                 warning("%s literal contains non-portable characters\n",
  665.                     cbuf[0] == '"' ? "string" : "character");
  666.             token = cbuf;
  667.             tsym = &tval;
  668.             if (cbuf[0] == '"') {
  669.                 tval.type = array(chartype, s - cbuf - 1, 0);
  670.                 tval.u.c.v.p = cbuf + 1;
  671.                 return SCON;
  672.             } else {
  673.                 if (s - cbuf > 3)
  674.                     warning("excess characters in multibyte character literal `%S' ignored\n", token, (char*)cp-token);
  675.  
  676.                 else if (s - cbuf <= 2)
  677.                     error("missing '\n");
  678.                 tval.type = inttype;
  679.                 tval.u.c.v.i = cbuf[1];
  680.                 return ICON;
  681.             }
  682.         }
  683.         case 'a':
  684.             if (rcp[0] == 'u'
  685.             &&  rcp[1] == 't'
  686.             &&  rcp[2] == 'o'
  687.             && !(map[rcp[3]]&(DIGIT|LETTER))) {
  688.                 cp = rcp + 3;
  689.                 return AUTO;
  690.             }
  691.             goto id;
  692.         case 'b':
  693.             if (rcp[0] == 'r'
  694.             &&  rcp[1] == 'e'
  695.             &&  rcp[2] == 'a'
  696.             &&  rcp[3] == 'k'
  697.             && !(map[rcp[4]]&(DIGIT|LETTER))) {
  698.                 cp = rcp + 4;
  699.                 return BREAK;
  700.             }
  701.             goto id;
  702.         case 'c':
  703.             if (rcp[0] == 'a'
  704.             &&  rcp[1] == 's'
  705.             &&  rcp[2] == 'e'
  706.             && !(map[rcp[3]]&(DIGIT|LETTER))) {
  707.                 cp = rcp + 3;
  708.                 return CASE;
  709.             }
  710.             if (rcp[0] == 'h'
  711.             &&  rcp[1] == 'a'
  712.             &&  rcp[2] == 'r'
  713.             && !(map[rcp[3]]&(DIGIT|LETTER))) {
  714.                 cp = rcp + 3;
  715.                 tsym = chartype->u.sym;
  716.                 return CHAR;
  717.             }
  718.             if (rcp[0] == 'o'
  719.             &&  rcp[1] == 'n'
  720.             &&  rcp[2] == 's'
  721.             &&  rcp[3] == 't'
  722.             && !(map[rcp[4]]&(DIGIT|LETTER))) {
  723.                 cp = rcp + 4;
  724.                 return CONST;
  725.             }
  726.             if (rcp[0] == 'o'
  727.             &&  rcp[1] == 'n'
  728.             &&  rcp[2] == 't'
  729.             &&  rcp[3] == 'i'
  730.             &&  rcp[4] == 'n'
  731.             &&  rcp[5] == 'u'
  732.             &&  rcp[6] == 'e'
  733.             && !(map[rcp[7]]&(DIGIT|LETTER))) {
  734.                 cp = rcp + 7;
  735.                 return CONTINUE;
  736.             }
  737.             goto id;
  738.         case 'd':
  739.             if (rcp[0] == 'e'
  740.             &&  rcp[1] == 'f'
  741.             &&  rcp[2] == 'a'
  742.             &&  rcp[3] == 'u'
  743.             &&  rcp[4] == 'l'
  744.             &&  rcp[5] == 't'
  745.             && !(map[rcp[6]]&(DIGIT|LETTER))) {
  746.                 cp = rcp + 6;
  747.                 return DEFAULT;
  748.             }
  749.             if (rcp[0] == 'o'
  750.             &&  rcp[1] == 'u'
  751.             &&  rcp[2] == 'b'
  752.             &&  rcp[3] == 'l'
  753.             &&  rcp[4] == 'e'
  754.             && !(map[rcp[5]]&(DIGIT|LETTER))) {
  755.                 cp = rcp + 5;
  756.                 tsym = doubletype->u.sym;
  757.                 return DOUBLE;
  758.             }
  759.             if (rcp[0] == 'o'
  760.             && !(map[rcp[1]]&(DIGIT|LETTER))) {
  761.                 cp = rcp + 1;
  762.                 return DO;
  763.             }
  764.             goto id;
  765.         case 'e':
  766.             if (rcp[0] == 'l'
  767.             &&  rcp[1] == 's'
  768.             &&  rcp[2] == 'e'
  769.             && !(map[rcp[3]]&(DIGIT|LETTER))) {
  770.                 cp = rcp + 3;
  771.                 return ELSE;
  772.             }
  773.             if (rcp[0] == 'n'
  774.             &&  rcp[1] == 'u'
  775.             &&  rcp[2] == 'm'
  776.             && !(map[rcp[3]]&(DIGIT|LETTER))) {
  777.                 cp = rcp + 3;
  778.                 return ENUM;
  779.             }
  780.             if (rcp[0] == 'x'
  781.             &&  rcp[1] == 't'
  782.             &&  rcp[2] == 'e'
  783.             &&  rcp[3] == 'r'
  784.             &&  rcp[4] == 'n'
  785.             && !(map[rcp[5]]&(DIGIT|LETTER))) {
  786.                 cp = rcp + 5;
  787.                 return EXTERN;
  788.             }
  789.             goto id;
  790.         case 'f':
  791.             if (rcp[0] == 'l'
  792.             &&  rcp[1] == 'o'
  793.             &&  rcp[2] == 'a'
  794.             &&  rcp[3] == 't'
  795.             && !(map[rcp[4]]&(DIGIT|LETTER))) {
  796.                 cp = rcp + 4;
  797.                 tsym = floattype->u.sym;
  798.                 return FLOAT;
  799.             }
  800.             if (rcp[0] == 'o'
  801.             &&  rcp[1] == 'r'
  802.             && !(map[rcp[2]]&(DIGIT|LETTER))) {
  803.                 cp = rcp + 2;
  804.                 return FOR;
  805.             }
  806.             goto id;
  807.         case 'g':
  808.             if (rcp[0] == 'o'
  809.             &&  rcp[1] == 't'
  810.             &&  rcp[2] == 'o'
  811.             && !(map[rcp[3]]&(DIGIT|LETTER))) {
  812.                 cp = rcp + 3;
  813.                 return GOTO;
  814.             }
  815.             goto id;
  816.         case 'l':
  817.             if (rcp[0] == 'o'
  818.             &&  rcp[1] == 'n'
  819.             &&  rcp[2] == 'g'
  820.             && !(map[rcp[3]]&(DIGIT|LETTER))) {
  821.                 cp = rcp + 3;
  822.                 while (*cp && (map[*cp]&BLANK))
  823.                     cp++;
  824.                 if (*cp == 'l' && cp[1] == 'o' && cp[2] == 'n' &&
  825.                     cp[3] == 'g' && !(map[cp[4]] & (DIGIT|LETTER))) {
  826.                     cp += 4;
  827.                     tsym = longlongtype->u.sym;
  828.                     return LONGLONG;
  829.                 }
  830.                 cp = rcp+3;
  831.                 tsym = longtype->u.sym;
  832.                 return LONG;
  833.             }
  834.             goto id;
  835.         case 'r':
  836.             if (rcp[0] == 'e'
  837.             &&  rcp[1] == 'g'
  838.             &&  rcp[2] == 'i'
  839.             &&  rcp[3] == 's'
  840.             &&  rcp[4] == 't'
  841.             &&  rcp[5] == 'e'
  842.             &&  rcp[6] == 'r'
  843.             && !(map[rcp[7]]&(DIGIT|LETTER))) {
  844.                 cp = rcp + 7;
  845.                 return REGISTER;
  846.             }
  847.             if (rcp[0] == 'e'
  848.             &&  rcp[1] == 't'
  849.             &&  rcp[2] == 'u'
  850.             &&  rcp[3] == 'r'
  851.             &&  rcp[4] == 'n'
  852.             && !(map[rcp[5]]&(DIGIT|LETTER))) {
  853.                 cp = rcp + 5;
  854.                 return RETURN;
  855.             }
  856.             goto id;
  857.         case 's':
  858.             if (rcp[0] == 'h'
  859.             &&  rcp[1] == 'o'
  860.             &&  rcp[2] == 'r'
  861.             &&  rcp[3] == 't'
  862.             && !(map[rcp[4]]&(DIGIT|LETTER))) {
  863.                 cp = rcp + 4;
  864.                 tsym = shorttype->u.sym;
  865.                 return SHORT;
  866.             }
  867.             if (rcp[0] == 'i'
  868.             &&  rcp[1] == 'g'
  869.             &&  rcp[2] == 'n'
  870.             &&  rcp[3] == 'e'
  871.             &&  rcp[4] == 'd'
  872.             && !(map[rcp[5]]&(DIGIT|LETTER))) {
  873.                 cp = rcp + 5;
  874.                 return SIGNED;
  875.             }
  876.             if (rcp[0] == 'i'
  877.             &&  rcp[1] == 'z'
  878.             &&  rcp[2] == 'e'
  879.             &&  rcp[3] == 'o'
  880.             &&  rcp[4] == 'f'
  881.             && !(map[rcp[5]]&(DIGIT|LETTER))) {
  882.                 cp = rcp + 5;
  883.                 return SIZEOF;
  884.             }
  885.             if (rcp[0] == 't'
  886.             &&  rcp[1] == 'a'
  887.             &&  rcp[2] == 't'
  888.             &&  rcp[3] == 'i'
  889.             &&  rcp[4] == 'c'
  890.             && !(map[rcp[5]]&(DIGIT|LETTER))) {
  891.                 cp = rcp + 5;
  892.                 return STATIC;
  893.             }
  894.             if (rcp[0] == 't'
  895.             &&  rcp[1] == 'r'
  896.             &&  rcp[2] == 'u'
  897.             &&  rcp[3] == 'c'
  898.             &&  rcp[4] == 't'
  899.             && !(map[rcp[5]]&(DIGIT|LETTER))) {
  900.                 cp = rcp + 5;
  901.                 return STRUCT;
  902.             }
  903.             if (rcp[0] == 'w'
  904.             &&  rcp[1] == 'i'
  905.             &&  rcp[2] == 't'
  906.             &&  rcp[3] == 'c'
  907.             &&  rcp[4] == 'h'
  908.             && !(map[rcp[5]]&(DIGIT|LETTER))) {
  909.                 cp = rcp + 5;
  910.                 return SWITCH;
  911.             }
  912.             goto id;
  913.         case 't':
  914.             if (rcp[0] == 'y'
  915.             &&  rcp[1] == 'p'
  916.             &&  rcp[2] == 'e'
  917.             &&  rcp[3] == 'd'
  918.             &&  rcp[4] == 'e'
  919.             &&  rcp[5] == 'f'
  920.             && !(map[rcp[6]]&(DIGIT|LETTER))) {
  921.                 cp = rcp + 6;
  922.                 return TYPEDEF;
  923.             }
  924.             goto id;
  925.         case 'u':
  926.             if (rcp[0] == 'n'
  927.             &&  rcp[1] == 'i'
  928.             &&  rcp[2] == 'o'
  929.             &&  rcp[3] == 'n'
  930.             && !(map[rcp[4]]&(DIGIT|LETTER))) {
  931.                 cp = rcp + 4;
  932.                 return UNION;
  933.             }
  934.             if (rcp[0] == 'n'
  935.             &&  rcp[1] == 's'
  936.             &&  rcp[2] == 'i'
  937.             &&  rcp[3] == 'g'
  938.             &&  rcp[4] == 'n'
  939.             &&  rcp[5] == 'e'
  940.             &&  rcp[6] == 'd'
  941.             && !(map[rcp[7]]&(DIGIT|LETTER))) {
  942.                 cp = rcp + 7;
  943.                 return UNSIGNED;
  944.             }
  945.             goto id;
  946.         case 'v':
  947.             if (rcp[0] == 'o'
  948.             &&  rcp[1] == 'i'
  949.             &&  rcp[2] == 'd'
  950.             && !(map[rcp[3]]&(DIGIT|LETTER))) {
  951.                 cp = rcp + 3;
  952.                 tsym = voidtype->u.sym;
  953.                 return VOID;
  954.             }
  955.             if (rcp[0] == 'o'
  956.             &&  rcp[1] == 'l'
  957.             &&  rcp[2] == 'a'
  958.             &&  rcp[3] == 't'
  959.             &&  rcp[4] == 'i'
  960.             &&  rcp[5] == 'l'
  961.             &&  rcp[6] == 'e'
  962.             && !(map[rcp[7]]&(DIGIT|LETTER))) {
  963.                 cp = rcp + 7;
  964.                 return VOLATILE;
  965.             }
  966.             goto id;
  967.         case 'w':
  968.             if (rcp[0] == 'h'
  969.             &&  rcp[1] == 'i'
  970.             &&  rcp[2] == 'l'
  971.             &&  rcp[3] == 'e'
  972.             && !(map[rcp[4]]&(DIGIT|LETTER))) {
  973.                 cp = rcp + 4;
  974.                 return WHILE;
  975.             }
  976.             goto id;
  977.         default:
  978.             if ((map[cp[-1]]&BLANK) == 0)
  979.                 if (cp[-1] < ' ' || cp[-1] >= 0177)
  980.                     error("illegal character `\\0%o'\n", cp[-1]);
  981.                 else
  982.                     error("illegal character `%c'\n", cp[-1]);
  983.         }
  984.     }
  985. }
  986. static Symbol icon(unsigned n,int overflow,int base)
  987. {
  988.     if ((*cp=='u'||*cp=='U') && (cp[1]=='l'||cp[1]=='L')
  989.     ||  (*cp=='l'||*cp=='L') && (cp[1]=='u'||cp[1]=='U')) {
  990.         tval.type = unsignedlong;
  991.         cp += 2;
  992.     } else if (*cp == 'u' || *cp == 'U') {
  993.         tval.type = unsignedtype;
  994.         cp += 1;
  995.     } else if (*cp == 'l' || *cp == 'L') {
  996.         if (n > (unsigned)LONG_MAX)
  997.             tval.type = unsignedlong;
  998.         else
  999.             tval.type = longtype;
  1000.         cp += 1;
  1001.     } else if (base == 10 && n > (unsigned)LONG_MAX)
  1002.         tval.type = unsignedlong;
  1003.     else if (n > (unsigned)INT_MAX)
  1004.         tval.type = unsignedtype;
  1005.     else
  1006.         tval.type = inttype;
  1007.     if (overflow) {
  1008.         warning("overflow in constant `%S'\n", token,
  1009.             (char*)cp - token);
  1010.         n = LONG_MAX;
  1011.     }
  1012.     if (isunsigned(tval.type))
  1013.         tval.u.c.v.u = n;
  1014.     else
  1015.         tval.u.c.v.i = n;        
  1016.     ppnumber("integer");
  1017.     return &tval;
  1018. }
  1019. static void ppnumber(char *which)
  1020. {
  1021.     unsigned char *rcp = cp--;
  1022.  
  1023.     for ( ; (map[*cp]&(DIGIT|LETTER)) || *cp == '.'; cp++)
  1024.         if ((cp[0] == 'E' || cp[0] == 'e')
  1025.         &&  (cp[1] == '-' || cp[1] == '+'))
  1026.             cp++;
  1027.     if (cp > rcp)
  1028.         error("`%S' is a preprocessing number but an invalid %s constant\n", token,
  1029.  
  1030.             (char*)cp-token, which);
  1031. }
  1032. static Symbol fcon(void)
  1033. {
  1034.     if (*cp == '.')
  1035.         do
  1036.             cp++;
  1037.         while (map[*cp]&DIGIT);
  1038.     if (*cp == 'e' || *cp == 'E') {
  1039.         if (*++cp == '-' || *cp == '+')
  1040.             cp++;
  1041.         if (map[*cp]&DIGIT)
  1042.             do
  1043.                 cp++;
  1044.             while (map[*cp]&DIGIT);
  1045.         else
  1046.             error("invalid floating constant `%S'\n", token,
  1047.                 (char*)cp - token);
  1048.     }
  1049.  
  1050.     errno = 0;
  1051.     tval.u.c.v.d = strtod(token, NULL);
  1052.     if (errno == ERANGE)
  1053.         warning("overflow in floating constant `%S'\n", token,
  1054.             (char*)cp - token);
  1055.     if (*cp == 'f' || *cp == 'F') {
  1056.         ++cp;
  1057.         if (tval.u.c.v.d > FLT_MAX)
  1058.             warning("overflow in floating constant `%S'\n", token,
  1059.                 (char*)cp - token);
  1060.         tval.type = floattype;
  1061.         tval.u.c.v.f = (float)tval.u.c.v.d;
  1062.     } else if (*cp == 'l' || *cp == 'L') {
  1063.         cp++;
  1064.         tval.type = longdouble;
  1065.     } else
  1066.         tval.type = doubletype;
  1067.     ppnumber("floating");
  1068.     return &tval;
  1069. }
  1070.  
  1071. int getchr(void)
  1072. {
  1073.     register int c;
  1074.  
  1075.     for (;;) {
  1076.         c = *cp;
  1077.         while (map[c]&BLANK)
  1078.             c = *++cp;
  1079.         if (!(map[c]&NEWLINE)) {
  1080.             if (c == '_' && cp[1] == '_' && cp[2] == 't' &&
  1081.                 cp[3] == 'r' && cp[4] == 'y') {
  1082.                 unsigned char *oldcp = cp;
  1083.                 cp += 5;
  1084.                 c = getchr();
  1085.                 cp = oldcp;
  1086.                 return(c);
  1087.             }
  1088.             return c;
  1089.         }
  1090.         cp++;
  1091.         nextline();
  1092.         if (cp == limit)
  1093.             return EOI;
  1094.     }
  1095. }
  1096. static int backslash(int q)
  1097. {
  1098.     int c;
  1099.  
  1100.     switch (*cp++) {
  1101.     case 'a': return 7;
  1102.     case 'b': return '\b';
  1103.     case 'f': return '\f';
  1104.     case 'n': return '\n';
  1105.     case 'r': return '\r';
  1106.     case 't': return '\t';
  1107.     case 'v': return '\v';
  1108.     case '\'': case '"': case '\\': case '\?': break;
  1109.     case 'x': {
  1110.         int overflow = 0;
  1111.         if ((map[*cp]&(DIGIT|HEX)) == 0) {
  1112.             if (*cp < ' ' || *cp == 0177)
  1113.                 error("ill-formed hexadecimal escape sequence\n");
  1114.             else
  1115.                 error("ill-formed hexadecimal escape sequence `\\x%c'\n", *cp);
  1116.             if (*cp != q)
  1117.                 cp++;
  1118.             return 0;
  1119.         }
  1120.         for (c = 0; map[*cp]&(DIGIT|HEX); cp++) {
  1121.             if (c&~((unsigned)-1 >> 4))
  1122.                 overflow++;
  1123.             if (map[*cp]&DIGIT)
  1124.                 c = (c<<4) + *cp - '0';
  1125.             else
  1126.                 c = (c<<4) + (*cp&~040) - 'A' + 10;
  1127.         }
  1128.         if (c&~0377 || overflow)
  1129.             warning("overflow in hexadecimal escape sequence\n");
  1130.         return c&0377;
  1131.         }
  1132.     case '0': case '1': case '2': case '3':
  1133.     case '4': case '5': case '6': case '7':
  1134.         c = *(cp-1) - '0';
  1135.         if (*cp >= '0' && *cp <= '7') {
  1136.             c = (c<<3) + *cp++ - '0';
  1137.             if (*cp >= '0' && *cp <= '7')
  1138.                 c = (c<<3) + *cp++ - '0';
  1139.         }
  1140.         if (c&~0377)
  1141.             warning("overflow in octal escape sequence\n");
  1142.         return c&0377;
  1143.     default:
  1144.         if (cp[-1] < ' ' || cp[-1] >= 0177)
  1145.             warning("unrecognized character escape sequence\n");
  1146.         else
  1147.             warning("unrecognized character escape sequence `\\%c'\n", cp[-1]);
  1148.     }
  1149.     return cp[-1];
  1150. }
  1151.  
  1152. static char packstack[32];
  1153. static char packstackptr=0;
  1154. void ProcessPragmaPack(void)
  1155. {
  1156.     int newAlignment;
  1157.  
  1158.     t = gettok();
  1159.     if (t == '(') {
  1160.         t = gettok();
  1161.         if (t != ICON) {
  1162.             if (t != ')') {
  1163.                 if (t == ID) {
  1164.                    if (token[0] == 'p' && token[1] == 'u' &&
  1165.                        token[2] == 's' && token[3] == 'h') {
  1166.                        if (packstackptr > 31) {
  1167.                            error("Overflow in #pragma(push)\n");
  1168.                            return;
  1169.                        }
  1170.                        packstack[packstackptr++] = DefaultAlignment;
  1171.                        t = gettok();
  1172.                        if (t == ',') {
  1173.                            t = gettok();
  1174.                            if (t == ICON) 
  1175.                                goto suite;
  1176.                        }
  1177.                        else if (t == ')')
  1178.                            return;
  1179.                        else
  1180.                            error("Syntax error in pragma <pack>\n");
  1181.                        return;
  1182.                    }
  1183.                    else if (token[0] == 'p' && token[1] == 'o' &&
  1184.                        token[2] == 'p') {
  1185.                         t = gettok();
  1186.                         if (packstackptr < 1) {
  1187.                            error("pragma pack(pop) stack underflow\n");
  1188.                            return;
  1189.                         }
  1190.                         if (t != ')')
  1191.                            error("pragma pack(pop) syntax error\n");
  1192.                         packstackptr--;
  1193.                         DefaultAlignment = packstack[packstackptr];
  1194.                         return;
  1195.                    }
  1196.                 }
  1197.                 warning("Integer constant expected in 'pack' pragma. Ignored.");
  1198.                 return;
  1199.             }
  1200.             newAlignment = 16;
  1201.         }
  1202.         else {
  1203. suite:
  1204.             newAlignment = tval.u.c.v.i;
  1205.             t = gettok();
  1206.             if (t != ')') {
  1207.                 warning("Incorrect 'pragma pack' syntax");
  1208.                 return;
  1209.             }
  1210.         }
  1211.         switch (newAlignment) {
  1212.             case 1:
  1213.                 break;
  1214.             case 2:
  1215.                 break;
  1216.             case 4:
  1217.                 break;
  1218.             case 8:
  1219.                 break;
  1220.             case 16:
  1221.                 break;
  1222.             default:
  1223.                 warning("Illegal pragma pack(%d) ignored",newAlignment);
  1224.                 return;
  1225.         }
  1226.     }
  1227.     else {
  1228.         warning("Incorrect syntax in pragma statement");
  1229.         return;
  1230.     }
  1231.     DefaultAlignment = newAlignment;
  1232. }
  1233. void ProcessOptimize(void)
  1234. {
  1235.     int val;
  1236.  
  1237.     t = gettok();
  1238.     if (t == '(') {
  1239.         t = gettok();
  1240.         if (t != ICON) {
  1241.             if (t != ')') {
  1242.                 warning("Integer constant expected in 'optimize' pragma. Ignored.");
  1243.                 return;
  1244.             }
  1245.             val = 0;
  1246.         }
  1247.         else {
  1248.             val = tval.u.c.v.i;
  1249.             t = gettok();
  1250.             if (t != ')') {
  1251.                 warning("Incorrect 'optimize' syntax");
  1252.                 return;
  1253.             }
  1254.         }
  1255.         OptimizeFlag = val;
  1256.     }
  1257.     else {
  1258.         warning("Incorrect syntax in pragma statement");
  1259.         return;
  1260.     }
  1261. }
  1262.  
  1263. void ProcessSection(void)
  1264. {
  1265.     char tmpbuf[40];
  1266.  
  1267.     t = gettok();
  1268.     if (t == '(') {
  1269.         t = gettok();
  1270.         if (t != SCON) {
  1271.             if (t != ')') {
  1272.                 warning("String constant expected in 'pack' pragma. Ignored.");
  1273.                 return;
  1274.             }
  1275.             print("\tsection .text\n");
  1276.         }
  1277.         else {
  1278.             assert(tval.type);
  1279.             if (tval.type->size > 9) {
  1280.                 warning("Section name too long. Max. 8 chars. Ignored.");
  1281.                 return;
  1282.             }
  1283.             sprintf(tmpbuf,"\t.section %s\n",tval.u.c.v.p);
  1284.             t = gettok();
  1285.             if (t != ')') {
  1286.                 warning("Incorrect 'pragma section' syntax");
  1287.                 return;
  1288.             }
  1289.             print(tmpbuf);
  1290.         }
  1291.     }
  1292.     else {
  1293.         warning("Incorrect syntax in pragma statement");
  1294.         return;
  1295.     }
  1296. }
  1297.  
  1298. int getTvalValue(void)
  1299. {
  1300.     return(tval.u.c.v.i);
  1301. }
  1302.  
  1303. int getLevel(void)
  1304. {
  1305.     return(statementLevel);
  1306. }
  1307.