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