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