Ada: Reserved word "all" should not need to be spelled in lowercase.
[external/binutils.git] / gdb / ada-lex.l
1 /* FLEX lexer for Ada expressions, for GDB.
2    Copyright (C) 1994-2013 Free Software Foundation, Inc.
3
4    This file is part of GDB.
5
6    This program is free software; you can redistribute it and/or modify
7    it under the terms of the GNU General Public License as published by
8    the Free Software Foundation; either version 3 of the License, or
9    (at your option) any later version.
10
11    This program is distributed in the hope that it will be useful,
12    but WITHOUT ANY WARRANTY; without even the implied warranty of
13    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14    GNU General Public License for more details.
15
16    You should have received a copy of the GNU General Public License
17    along with this program.  If not, see <http://www.gnu.org/licenses/>.  */
18
19 /*----------------------------------------------------------------------*/
20
21 /* The converted version of this file is to be included in ada-exp.y, */
22 /* the Ada parser for gdb.  The function yylex obtains characters from */
23 /* the global pointer lexptr.  It returns a syntactic category for */
24 /* each successive token and places a semantic value into yylval */
25 /* (ada-lval), defined by the parser.   */
26
27 DIG     [0-9]
28 NUM10   ({DIG}({DIG}|_)*)
29 HEXDIG  [0-9a-f]
30 NUM16   ({HEXDIG}({HEXDIG}|_)*)
31 OCTDIG  [0-7]
32 LETTER  [a-z_]
33 ID      ({LETTER}({LETTER}|{DIG})*|"<"{LETTER}({LETTER}|{DIG})*">")
34 WHITE   [ \t\n]
35 TICK    ("'"{WHITE}*)
36 GRAPHIC [a-z0-9 #&'()*+,-./:;<>=_|!$%?@\[\]\\^`{}~]
37 OPER    ([-+*/=<>&]|"<="|">="|"**"|"/="|"and"|"or"|"xor"|"not"|"mod"|"rem"|"abs")
38
39 EXP     (e[+-]{NUM10})
40 POSEXP  (e"+"?{NUM10})
41
42 %{
43
44 #define NUMERAL_WIDTH 256
45 #define LONGEST_SIGN ((ULONGEST) 1 << (sizeof(LONGEST) * HOST_CHAR_BIT - 1))
46
47 /* Temporary staging for numeric literals.  */
48 static char numbuf[NUMERAL_WIDTH];
49  static void canonicalizeNumeral (char *s1, const char *);
50 static struct stoken processString (const char*, int);
51 static int processInt (const char *, const char *, const char *);
52 static int processReal (const char *);
53 static struct stoken processId (const char *, int);
54 static int processAttribute (const char *);
55 static int find_dot_all (const char *);
56 static void rewind_to_char (int);
57
58 #undef YY_DECL
59 #define YY_DECL static int yylex ( void )
60
61 /* Flex generates a static function "input" which is not used.
62    Defining YY_NO_INPUT comments it out.  */
63 #define YY_NO_INPUT
64
65 #undef YY_INPUT
66 #define YY_INPUT(BUF, RESULT, MAX_SIZE) \
67     if ( *lexptr == '\000' ) \
68       (RESULT) = YY_NULL; \
69     else \
70       { \
71         *(BUF) = *lexptr; \
72         (RESULT) = 1; \
73         lexptr += 1; \
74       }
75
76 static int find_dot_all (const char *);
77
78 %}
79
80 %option case-insensitive interactive nodefault
81
82 %s BEFORE_QUAL_QUOTE
83
84 %%
85
86 {WHITE}          { }
87
88 "--".*           { yyterminate(); }
89
90 {NUM10}{POSEXP}  {
91                    canonicalizeNumeral (numbuf, yytext);
92                    return processInt (NULL, numbuf, strrchr(numbuf, 'e')+1);
93                  }
94
95 {NUM10}          {
96                    canonicalizeNumeral (numbuf, yytext);
97                    return processInt (NULL, numbuf, NULL);
98                  }
99
100 {NUM10}"#"{HEXDIG}({HEXDIG}|_)*"#"{POSEXP} {
101                    canonicalizeNumeral (numbuf, yytext);
102                    return processInt (numbuf,
103                                       strchr (numbuf, '#') + 1,
104                                       strrchr(numbuf, '#') + 1);
105                  }
106
107 {NUM10}"#"{HEXDIG}({HEXDIG}|_)*"#" {
108                    canonicalizeNumeral (numbuf, yytext);
109                    return processInt (numbuf, strchr (numbuf, '#') + 1, NULL);
110                  }
111
112 "0x"{HEXDIG}+   {
113                   canonicalizeNumeral (numbuf, yytext+2);
114                   return processInt ("16#", numbuf, NULL);
115                 }
116
117
118 {NUM10}"."{NUM10}{EXP} {
119                    canonicalizeNumeral (numbuf, yytext);
120                    return processReal (numbuf);
121                 }
122
123 {NUM10}"."{NUM10} {
124                    canonicalizeNumeral (numbuf, yytext);
125                    return processReal (numbuf);
126                 }
127
128 {NUM10}"#"{NUM16}"."{NUM16}"#"{EXP} {
129                    error (_("Based real literals not implemented yet."));
130                 }
131
132 {NUM10}"#"{NUM16}"."{NUM16}"#" {
133                    error (_("Based real literals not implemented yet."));
134                 }
135
136 <INITIAL>"'"({GRAPHIC}|\")"'" {
137                    yylval.typed_val.type = type_char ();
138                    yylval.typed_val.val = yytext[1];
139                    return CHARLIT;
140                 }
141
142 <INITIAL>"'[\""{HEXDIG}{2}"\"]'"   {
143                    int v;
144                    yylval.typed_val.type = type_char ();
145                    sscanf (yytext+3, "%2x", &v);
146                    yylval.typed_val.val = v;
147                    return CHARLIT;
148                 }
149
150 \"({GRAPHIC}|"[\""({HEXDIG}{2}|\")"\"]")*\"   {
151                    yylval.sval = processString (yytext+1, yyleng-2);
152                    return STRING;
153                 }
154
155 \"              {
156                    error (_("ill-formed or non-terminated string literal"));
157                 }
158
159
160 if              {
161                   rewind_to_char ('i');
162                   return 0;
163                 }
164
165 task            {
166                   rewind_to_char ('t');
167                   return 0;
168                 }
169
170 thread{WHITE}+{DIG} {
171                   /* This keyword signals the end of the expression and
172                      will be processed separately.  */
173                   rewind_to_char ('t');
174                   return 0;
175                 }
176
177         /* ADA KEYWORDS */
178
179 abs             { return ABS; }
180 and             { return _AND_; }
181 else            { return ELSE; }
182 in              { return IN; }
183 mod             { return MOD; }
184 new             { return NEW; }
185 not             { return NOT; }
186 null            { return NULL_PTR; }
187 or              { return OR; }
188 others          { return OTHERS; }
189 rem             { return REM; }
190 then            { return THEN; }
191 xor             { return XOR; }
192
193         /* BOOLEAN "KEYWORDS" */
194
195  /* True and False are not keywords in Ada, but rather enumeration constants.
196     However, the boolean type is no longer represented as an enum, so True
197     and False are no longer defined in symbol tables.  We compromise by
198     making them keywords (when bare). */
199
200 true            { return TRUEKEYWORD; }
201 false           { return FALSEKEYWORD; }
202
203         /* ATTRIBUTES */
204
205 {TICK}[a-zA-Z][a-zA-Z]+ { return processAttribute (yytext+1); }
206
207         /* PUNCTUATION */
208
209 "=>"            { return ARROW; }
210 ".."            { return DOTDOT; }
211 "**"            { return STARSTAR; }
212 ":="            { return ASSIGN; }
213 "/="            { return NOTEQUAL; }
214 "<="            { return LEQ; }
215 ">="            { return GEQ; }
216
217 <BEFORE_QUAL_QUOTE>"'" { BEGIN INITIAL; return '\''; }
218
219 [-&*+./:<>=|;\[\]] { return yytext[0]; }
220
221 ","             { if (paren_depth == 0 && comma_terminates)
222                     {
223                       rewind_to_char (',');
224                       return 0;
225                     }
226                   else
227                     return ',';
228                 }
229
230 "("             { paren_depth += 1; return '('; }
231 ")"             { if (paren_depth == 0)
232                     {
233                       rewind_to_char (')');
234                       return 0;
235                     }
236                   else
237                     {
238                       paren_depth -= 1;
239                       return ')';
240                     }
241                 }
242
243 "."{WHITE}*all  { return DOT_ALL; }
244
245 "."{WHITE}*{ID} {
246                   yylval.sval = processId (yytext+1, yyleng-1);
247                   return DOT_ID;
248                 }
249
250 {ID}({WHITE}*"."{WHITE}*({ID}|\"{OPER}\"))*(" "*"'")?  {
251                   int all_posn = find_dot_all (yytext);
252
253                   if (all_posn == -1 && yytext[yyleng-1] == '\'')
254                     {
255                       BEGIN BEFORE_QUAL_QUOTE;
256                       yyless (yyleng-1);
257                     }
258                   else if (all_posn >= 0)
259                     yyless (all_posn);
260                   yylval.sval = processId (yytext, yyleng);
261                   return NAME;
262                }
263
264
265         /* GDB EXPRESSION CONSTRUCTS  */
266
267 "'"[^']+"'"{WHITE}*:: {
268                   yyless (yyleng - 2);
269                   yylval.sval = processId (yytext, yyleng);
270                   return NAME;
271                 }
272
273 "::"            { return COLONCOLON; }
274
275 [{}@]           { return yytext[0]; }
276
277         /* REGISTERS AND GDB CONVENIENCE VARIABLES */
278
279 "$"({LETTER}|{DIG}|"$")*  {
280                   yylval.sval.ptr = yytext;
281                   yylval.sval.length = yyleng;
282                   return SPECIAL_VARIABLE;
283                 }
284
285         /* CATCH-ALL ERROR CASE */
286
287 .               { error (_("Invalid character '%s' in expression."), yytext); }
288 %%
289
290 #include <ctype.h>
291 #include <string.h>
292
293 /* Initialize the lexer for processing new expression. */
294
295 static void
296 lexer_init (FILE *inp)
297 {
298   BEGIN INITIAL;
299   yyrestart (inp);
300 }
301
302
303 /* Copy S2 to S1, removing all underscores, and downcasing all letters.  */
304
305 static void
306 canonicalizeNumeral (char *s1, const char *s2)
307 {
308   for (; *s2 != '\000'; s2 += 1)
309     {
310       if (*s2 != '_')
311         {
312           *s1 = tolower(*s2);
313           s1 += 1;
314         }
315     }
316   s1[0] = '\000';
317 }
318
319 /* Interprets the prefix of NUM that consists of digits of the given BASE
320    as an integer of that BASE, with the string EXP as an exponent.
321    Puts value in yylval, and returns INT, if the string is valid.  Causes
322    an error if the number is improperly formated.   BASE, if NULL, defaults
323    to "10", and EXP to "1".  The EXP does not contain a leading 'e' or 'E'.
324  */
325
326 static int
327 processInt (const char *base0, const char *num0, const char *exp0)
328 {
329   ULONGEST result;
330   long exp;
331   int base;
332   const char *trailer;
333
334   if (base0 == NULL)
335     base = 10;
336   else
337     {
338       base = strtol (base0, (char **) NULL, 10);
339       if (base < 2 || base > 16)
340         error (_("Invalid base: %d."), base);
341     }
342
343   if (exp0 == NULL)
344     exp = 0;
345   else
346     exp = strtol(exp0, (char **) NULL, 10);
347
348   errno = 0;
349   result = strtoulst (num0, &trailer, base);
350   if (errno == ERANGE)
351     error (_("Integer literal out of range"));
352   if (isxdigit(*trailer))
353     error (_("Invalid digit `%c' in based literal"), *trailer);
354
355   while (exp > 0)
356     {
357       if (result > (ULONG_MAX / base))
358         error (_("Integer literal out of range"));
359       result *= base;
360       exp -= 1;
361     }
362
363   if ((result >> (gdbarch_int_bit (parse_gdbarch)-1)) == 0)
364     yylval.typed_val.type = type_int ();
365   else if ((result >> (gdbarch_long_bit (parse_gdbarch)-1)) == 0)
366     yylval.typed_val.type = type_long ();
367   else if (((result >> (gdbarch_long_bit (parse_gdbarch)-1)) >> 1) == 0)
368     {
369       /* We have a number representable as an unsigned integer quantity.
370          For consistency with the C treatment, we will treat it as an
371          anonymous modular (unsigned) quantity.  Alas, the types are such
372          that we need to store .val as a signed quantity.  Sorry
373          for the mess, but C doesn't officially guarantee that a simple
374          assignment does the trick (no, it doesn't; read the reference manual).
375        */
376       yylval.typed_val.type
377         = builtin_type (parse_gdbarch)->builtin_unsigned_long;
378       if (result & LONGEST_SIGN)
379         yylval.typed_val.val =
380           (LONGEST) (result & ~LONGEST_SIGN)
381           - (LONGEST_SIGN>>1) - (LONGEST_SIGN>>1);
382       else
383         yylval.typed_val.val = (LONGEST) result;
384       return INT;
385     }
386   else
387     yylval.typed_val.type = type_long_long ();
388
389   yylval.typed_val.val = (LONGEST) result;
390   return INT;
391 }
392
393 static int
394 processReal (const char *num0)
395 {
396   sscanf (num0, "%" DOUBLEST_SCAN_FORMAT, &yylval.typed_val_float.dval);
397
398   yylval.typed_val_float.type = type_float ();
399   if (sizeof(DOUBLEST) >= gdbarch_double_bit (parse_gdbarch)
400                             / TARGET_CHAR_BIT)
401     yylval.typed_val_float.type = type_double ();
402   if (sizeof(DOUBLEST) >= gdbarch_long_double_bit (parse_gdbarch)
403                             / TARGET_CHAR_BIT)
404     yylval.typed_val_float.type = type_long_double ();
405
406   return FLOAT;
407 }
408
409
410 /* Store a canonicalized version of NAME0[0..LEN-1] in yylval.ssym.  The
411    resulting string is valid until the next call to ada_parse.  If
412    NAME0 contains the substring "___", it is assumed to be already
413    encoded and the resulting name is equal to it.  Otherwise, it differs
414    from NAME0 in that:
415     + Characters between '...' or <...> are transfered verbatim to 
416       yylval.ssym.
417     + <, >, and trailing "'" characters in quoted sequences are removed
418       (a leading quote is preserved to indicate that the name is not to be
419       GNAT-encoded).
420     + Unquoted whitespace is removed.
421     + Unquoted alphabetic characters are mapped to lower case.
422    Result is returned as a struct stoken, but for convenience, the string
423    is also null-terminated.  Result string valid until the next call of
424    ada_parse.
425  */
426 static struct stoken
427 processId (const char *name0, int len)
428 {
429   char *name = obstack_alloc (&temp_parse_space, len + 11);
430   int i0, i;
431   struct stoken result;
432
433   result.ptr = name;
434   while (len > 0 && isspace (name0[len-1]))
435     len -= 1;
436
437   if (strstr (name0, "___") != NULL)
438     {
439       strncpy (name, name0, len);
440       name[len] = '\000';
441       result.length = len;
442       return result;
443     }
444
445   i = i0 = 0;
446   while (i0 < len)
447     {
448       if (isalnum (name0[i0]))
449         {
450           name[i] = tolower (name0[i0]);
451           i += 1; i0 += 1;
452         }
453       else switch (name0[i0])
454         {
455         default:
456           name[i] = name0[i0];
457           i += 1; i0 += 1;
458           break;
459         case ' ': case '\t':
460           i0 += 1;
461           break;
462         case '\'':
463           do
464             {
465               name[i] = name0[i0];
466               i += 1; i0 += 1;
467             }
468           while (i0 < len && name0[i0] != '\'');
469           i0 += 1;
470           break;
471         case '<':
472           i0 += 1;
473           while (i0 < len && name0[i0] != '>')
474             {
475               name[i] = name0[i0];
476               i += 1; i0 += 1;
477             }
478           i0 += 1;
479           break;
480         }
481     }
482   name[i] = '\000';
483
484   result.length = i;
485   return result;
486 }
487
488 /* Return TEXT[0..LEN-1], a string literal without surrounding quotes,
489    with special hex character notations replaced with characters. 
490    Result valid until the next call to ada_parse.  */
491
492 static struct stoken
493 processString (const char *text, int len)
494 {
495   const char *p;
496   char *q;
497   const char *lim = text + len;
498   struct stoken result;
499
500   q = obstack_alloc (&temp_parse_space, len);
501   result.ptr = q;
502   p = text;
503   while (p < lim)
504     {
505       if (p[0] == '[' && p[1] == '"' && p+2 < lim)
506          {
507            if (p[2] == '"')  /* "...["""]... */
508              {
509                *q = '"';
510                p += 4;
511              }
512            else
513              {
514                int chr;
515                sscanf (p+2, "%2x", &chr);
516                *q = (char) chr;
517                p += 5;
518              }
519          }
520        else
521          *q = *p;
522        q += 1;
523        p += 1;
524      }
525   result.length = q - result.ptr;
526   return result;
527 }
528
529 /* Returns the position within STR of the '.' in a
530    '.{WHITE}*all' component of a dotted name, or -1 if there is none.
531    Note: we actually don't need this routine, since 'all' can never be an
532    Ada identifier.  Thus, looking up foo.all or foo.all.x as a name
533    must fail, and will eventually be interpreted as (foo).all or
534    (foo).all.x.  However, this does avoid an extraneous lookup. */
535
536 static int
537 find_dot_all (const char *str)
538 {
539   int i;
540   for (i = 0; str[i] != '\000'; i += 1)
541     {
542       if (str[i] == '.')
543         {
544           int i0 = i;
545           do
546             i += 1;
547           while (isspace (str[i]));
548           if (strncasecmp (str+i, "all", 3) == 0
549               && ! isalnum (str[i+3]) && str[i+3] != '_')
550             return i0;
551         }
552     }
553   return -1;
554 }
555
556 /* Returns non-zero iff string SUBSEQ matches a subsequence of STR, ignoring
557    case.  */
558
559 static int
560 subseqMatch (const char *subseq, const char *str)
561 {
562   if (subseq[0] == '\0')
563     return 1;
564   else if (str[0] == '\0')
565     return 0;
566   else if (tolower (subseq[0]) == tolower (str[0]))
567     return subseqMatch (subseq+1, str+1) || subseqMatch (subseq, str+1);
568   else
569     return subseqMatch (subseq, str+1);
570 }
571
572
573 static struct { const char *name; int code; }
574 attributes[] = {
575   { "address", TICK_ADDRESS },
576   { "unchecked_access", TICK_ACCESS },
577   { "unrestricted_access", TICK_ACCESS },
578   { "access", TICK_ACCESS },
579   { "first", TICK_FIRST },
580   { "last", TICK_LAST },
581   { "length", TICK_LENGTH },
582   { "max", TICK_MAX },
583   { "min", TICK_MIN },
584   { "modulus", TICK_MODULUS },
585   { "pos", TICK_POS },
586   { "range", TICK_RANGE },
587   { "size", TICK_SIZE },
588   { "tag", TICK_TAG },
589   { "val", TICK_VAL },
590   { NULL, -1 }
591 };
592
593 /* Return the syntactic code corresponding to the attribute name or
594    abbreviation STR.  */
595
596 static int
597 processAttribute (const char *str)
598 {
599   int i, k;
600
601   for (i = 0; attributes[i].code != -1; i += 1)
602     if (strcasecmp (str, attributes[i].name) == 0)
603       return attributes[i].code;
604
605   for (i = 0, k = -1; attributes[i].code != -1; i += 1)
606     if (subseqMatch (str, attributes[i].name))
607       {
608         if (k == -1)
609           k = i;
610         else
611           error (_("ambiguous attribute name: `%s'"), str);
612       }
613   if (k == -1)
614     error (_("unrecognized attribute: `%s'"), str);
615
616   return attributes[k].code;
617 }
618
619 /* Back up lexptr by yyleng and then to the rightmost occurrence of
620    character CH, case-folded (there must be one).  WARNING: since
621    lexptr points to the next input character that Flex has not yet
622    transferred to its internal buffer, the use of this function
623    depends on the assumption that Flex calls YY_INPUT only when it is
624    logically necessary to do so (thus, there is no reading ahead
625    farther than needed to identify the next token.)  */
626
627 static void
628 rewind_to_char (int ch)
629 {
630   lexptr -= yyleng;
631   while (toupper (*lexptr) != toupper (ch))
632     lexptr -= 1;
633   yyrestart (NULL);
634 }
635
636 int
637 yywrap(void)
638 {
639   return 1;
640 }
641
642 /* Dummy definition to suppress warnings about unused static definitions. */
643 typedef void (*dummy_function) ();
644 dummy_function ada_flex_use[] = 
645
646   (dummy_function) yyunput
647 };