1 /* FLEX lexer for Ada expressions, for GDB. 2 Copyright (C) 1994, 1997, 1998, 2000, 2001, 2002, 2003 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 2 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, write to the Free Software 19 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ 20 21 /*----------------------------------------------------------------------*/ 22 23 /* The converted version of this file is to be included in ada-exp.y, */ 24 /* the Ada parser for gdb. The function yylex obtains characters from */ 25 /* the global pointer lexptr. It returns a syntactic category for */ 26 /* each successive token and places a semantic value into yylval */ 27 /* (ada-lval), defined by the parser. */ 28 29 DIG [0-9] 30 NUM10 ({DIG}({DIG}|_)*) 31 HEXDIG [0-9a-f] 32 NUM16 ({HEXDIG}({HEXDIG}|_)*) 33 OCTDIG [0-7] 34 LETTER [a-z_] 35 ID ({LETTER}({LETTER}|{DIG})*|"<"{LETTER}({LETTER}|{DIG})*">") 36 WHITE [ \t\n] 37 TICK ("'"{WHITE}*) 38 GRAPHIC [a-z0-9 #&'()*+,-./:;<>=_|!$%?@\[\]\\^`{}~] 39 OPER ([-+*/=<>&]|"<="|">="|"**"|"/="|"and"|"or"|"xor"|"not"|"mod"|"rem"|"abs") 40 41 EXP (e[+-]{NUM10}) 42 POSEXP (e"+"?{NUM10}) 43 44 %{ 45 46 #define NUMERAL_WIDTH 256 47 #define LONGEST_SIGN ((ULONGEST) 1 << (sizeof(LONGEST) * HOST_CHAR_BIT - 1)) 48 49 /* Temporary staging for numeric literals. */ 50 static char numbuf[NUMERAL_WIDTH]; 51 static void canonicalizeNumeral (char *s1, const char *); 52 static int processInt (const char *, const char *, const char *); 53 static int processReal (const char *); 54 static int 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 char *tempbuf = NULL; 73 static int tempbufsize = 0; 74 static int tempbuf_len; 75 static struct block *left_block_context; 76 77 static void resize_tempbuf (unsigned int); 78 79 static void block_lookup (char *, char *); 80 81 static int name_lookup (char *, char *, int *, int); 82 83 static int find_dot_all (const char *); 84 85 %} 86 87 %option case-insensitive interactive nodefault 88 89 %s IN_STRING BEFORE_QUAL_QUOTE 90 91 %% 92 93 {WHITE} { } 94 95 "--".* { yyterminate(); } 96 97 {NUM10}{POSEXP} { 98 canonicalizeNumeral (numbuf, yytext); 99 return processInt (NULL, numbuf, strrchr(numbuf, 'e')+1); 100 } 101 102 {NUM10} { 103 canonicalizeNumeral (numbuf, yytext); 104 return processInt (NULL, numbuf, NULL); 105 } 106 107 {NUM10}"#"{HEXDIG}({HEXDIG}|_)*"#"{POSEXP} { 108 canonicalizeNumeral (numbuf, yytext); 109 return processInt (numbuf, 110 strchr (numbuf, '#') + 1, 111 strrchr(numbuf, '#') + 1); 112 } 113 114 {NUM10}"#"{HEXDIG}({HEXDIG}|_)*"#" { 115 canonicalizeNumeral (numbuf, yytext); 116 return processInt (numbuf, strchr (numbuf, '#') + 1, NULL); 117 } 118 119 "0x"{HEXDIG}+ { 120 canonicalizeNumeral (numbuf, yytext+2); 121 return processInt ("16#", numbuf, NULL); 122 } 123 124 125 {NUM10}"."{NUM10}{EXP} { 126 canonicalizeNumeral (numbuf, yytext); 127 return processReal (numbuf); 128 } 129 130 {NUM10}"."{NUM10} { 131 canonicalizeNumeral (numbuf, yytext); 132 return processReal (numbuf); 133 } 134 135 {NUM10}"#"{NUM16}"."{NUM16}"#"{EXP} { 136 error ("Based real literals not implemented yet."); 137 } 138 139 {NUM10}"#"{NUM16}"."{NUM16}"#" { 140 error ("Based real literals not implemented yet."); 141 } 142 143 <INITIAL>"'"({GRAPHIC}|\")"'" { 144 yylval.typed_val.type = type_char (); 145 yylval.typed_val.val = yytext[1]; 146 return CHARLIT; 147 } 148 149 <INITIAL>"'[\""{HEXDIG}{2}"\"]'" { 150 int v; 151 yylval.typed_val.type = type_char (); 152 sscanf (yytext+3, "%2x", &v); 153 yylval.typed_val.val = v; 154 return CHARLIT; 155 } 156 157 <INITIAL>\" { 158 tempbuf_len = 0; 159 BEGIN IN_STRING; 160 } 161 162 <IN_STRING>{GRAPHIC}*\" { 163 resize_tempbuf (yyleng+tempbuf_len); 164 strncpy (tempbuf+tempbuf_len, yytext, yyleng-1); 165 tempbuf_len += yyleng-1; 166 yylval.sval.ptr = tempbuf; 167 yylval.sval.length = tempbuf_len; 168 BEGIN INITIAL; 169 return STRING; 170 } 171 172 <IN_STRING>{GRAPHIC}*"[\""{HEXDIG}{2}"\"]" { 173 int n; 174 resize_tempbuf (yyleng-5+tempbuf_len+1); 175 strncpy (tempbuf+tempbuf_len, yytext, yyleng-6); 176 sscanf(yytext+yyleng-4, "%2x", &n); 177 tempbuf[yyleng-6+tempbuf_len] = (char) n; 178 tempbuf_len += yyleng-5; 179 } 180 181 <IN_STRING>{GRAPHIC}*"[\"\"\"]" { 182 int n; 183 resize_tempbuf (yyleng-4+tempbuf_len+1); 184 strncpy (tempbuf+tempbuf_len, yytext, yyleng-6); 185 tempbuf[yyleng-5+tempbuf_len] = '"'; 186 tempbuf_len += yyleng-4; 187 } 188 189 if { 190 while (*lexptr != 'i' && *lexptr != 'I') 191 lexptr -= 1; 192 yyrestart(NULL); 193 return 0; 194 } 195 196 /* ADA KEYWORDS */ 197 198 abs { return ABS; } 199 and { return _AND_; } 200 else { return ELSE; } 201 in { return IN; } 202 mod { return MOD; } 203 new { return NEW; } 204 not { return NOT; } 205 null { return NULL_PTR; } 206 or { return OR; } 207 rem { return REM; } 208 then { return THEN; } 209 xor { return XOR; } 210 211 /* ATTRIBUTES */ 212 213 {TICK}[a-zA-Z][a-zA-Z]+ { return processAttribute (yytext+1); } 214 215 /* PUNCTUATION */ 216 217 "=>" { return ARROW; } 218 ".." { return DOTDOT; } 219 "**" { return STARSTAR; } 220 ":=" { return ASSIGN; } 221 "/=" { return NOTEQUAL; } 222 "<=" { return LEQ; } 223 ">=" { return GEQ; } 224 225 <BEFORE_QUAL_QUOTE>"'" { BEGIN INITIAL; return '\''; } 226 227 [-&*+./:<>=|;\[\]] { return yytext[0]; } 228 229 "," { if (paren_depth == 0 && comma_terminates) 230 { 231 lexptr -= 1; 232 yyrestart(NULL); 233 return 0; 234 } 235 else 236 return ','; 237 } 238 239 "(" { paren_depth += 1; return '('; } 240 ")" { if (paren_depth == 0) 241 { 242 lexptr -= 1; 243 yyrestart(NULL); 244 return 0; 245 } 246 else 247 { 248 paren_depth -= 1; 249 return ')'; 250 } 251 } 252 253 "."{WHITE}*all { return DOT_ALL; } 254 255 "."{WHITE}*{ID} { 256 processId (yytext+1, yyleng-1); 257 return DOT_ID; 258 } 259 260 {ID}({WHITE}*"."{WHITE}*({ID}|\"{OPER}\"))*(" "*"'")? { 261 int all_posn = find_dot_all (yytext); 262 int token_type, segments, k; 263 int quote_follows; 264 265 if (all_posn == -1 && yytext[yyleng-1] == '\'') 266 { 267 quote_follows = 1; 268 do { 269 yyless (yyleng-1); 270 } while (yytext[yyleng-1] == ' '); 271 } 272 else 273 quote_follows = 0; 274 275 if (all_posn >= 0) 276 yyless (all_posn); 277 processId(yytext, yyleng); 278 segments = name_lookup (ada_encode (yylval.ssym.stoken.ptr), 279 yylval.ssym.stoken.ptr, 280 &token_type, 281 MAX_RENAMING_CHAIN_LENGTH); 282 left_block_context = NULL; 283 for (k = yyleng; segments > 0 && k > 0; k -= 1) 284 { 285 if (yytext[k-1] == '.') 286 segments -= 1; 287 quote_follows = 0; 288 } 289 if (k <= 0) 290 error ("confused by name %s", yytext); 291 yyless (k); 292 if (quote_follows) 293 BEGIN BEFORE_QUAL_QUOTE; 294 return token_type; 295 } 296 297 /* GDB EXPRESSION CONSTRUCTS */ 298 299 300 "'"[^']+"'"{WHITE}*:: { 301 processId(yytext, yyleng-2); 302 block_lookup (yylval.ssym.stoken.ptr, yylval.ssym.stoken.ptr); 303 return BLOCKNAME; 304 } 305 306 {ID}({WHITE}*"."{WHITE}*({ID}|\"{OPER}\"))*{WHITE}*:: { 307 processId(yytext, yyleng-2); 308 block_lookup (ada_encode (yylval.ssym.stoken.ptr), 309 yylval.ssym.stoken.ptr); 310 return BLOCKNAME; 311 } 312 313 [{}@] { return yytext[0]; } 314 315 /* REGISTERS AND GDB CONVENIENCE VARIABLES */ 316 317 "$"({LETTER}|{DIG}|"$")* { 318 yylval.sval.ptr = yytext; 319 yylval.sval.length = yyleng; 320 return SPECIAL_VARIABLE; 321 } 322 323 /* CATCH-ALL ERROR CASE */ 324 325 . { error ("Invalid character '%s' in expression.", yytext); } 326 %% 327 328 #include <ctype.h> 329 #include "gdb_string.h" 330 331 /* Initialize the lexer for processing new expression */ 332 void 333 lexer_init (FILE *inp) 334 { 335 BEGIN INITIAL; 336 yyrestart (inp); 337 } 338 339 340 /* Make sure that tempbuf points at an array at least N characters long. */ 341 342 static void 343 resize_tempbuf (unsigned int n) 344 { 345 if (tempbufsize < n) 346 { 347 tempbufsize = (n+63) & ~63; 348 tempbuf = xrealloc (tempbuf, tempbufsize); 349 } 350 } 351 352 /* Copy S2 to S1, removing all underscores, and downcasing all letters. */ 353 354 static void 355 canonicalizeNumeral (char *s1, const char *s2) 356 { 357 for (; *s2 != '\000'; s2 += 1) 358 { 359 if (*s2 != '_') 360 { 361 *s1 = tolower(*s2); 362 s1 += 1; 363 } 364 } 365 s1[0] = '\000'; 366 } 367 368 #define HIGH_BYTE_POSN ((sizeof (ULONGEST) - 1) * HOST_CHAR_BIT) 369 370 /* True (non-zero) iff DIGIT is a valid digit in radix BASE, 371 where 2 <= BASE <= 16. */ 372 373 static int 374 is_digit_in_base (unsigned char digit, int base) 375 { 376 if (!isxdigit (digit)) 377 return 0; 378 if (base <= 10) 379 return (isdigit (digit) && digit < base + '0'); 380 else 381 return (isdigit (digit) || tolower (digit) < base - 10 + 'a'); 382 } 383 384 static int 385 digit_to_int (unsigned char c) 386 { 387 if (isdigit (c)) 388 return c - '0'; 389 else 390 return tolower (c) - 'a' + 10; 391 } 392 393 /* As for strtoul, but for ULONGEST results. */ 394 ULONGEST 395 strtoulst (const char *num, const char **trailer, int base) 396 { 397 unsigned int high_part; 398 ULONGEST result; 399 int i; 400 unsigned char lim; 401 402 if (base < 2 || base > 16) 403 { 404 errno = EINVAL; 405 return 0; 406 } 407 lim = base - 1 + '0'; 408 409 result = high_part = 0; 410 for (i = 0; is_digit_in_base (num[i], base); i += 1) 411 { 412 result = result*base + digit_to_int (num[i]); 413 high_part = high_part*base + (unsigned int) (result >> HIGH_BYTE_POSN); 414 result &= ((ULONGEST) 1 << HIGH_BYTE_POSN) - 1; 415 if (high_part > 0xff) 416 { 417 errno = ERANGE; 418 result = high_part = 0; 419 break; 420 } 421 } 422 423 if (trailer != NULL) 424 *trailer = &num[i]; 425 426 return result + ((ULONGEST) high_part << HIGH_BYTE_POSN); 427 } 428 429 430 431 /* Interprets the prefix of NUM that consists of digits of the given BASE 432 as an integer of that BASE, with the string EXP as an exponent. 433 Puts value in yylval, and returns INT, if the string is valid. Causes 434 an error if the number is improperly formated. BASE, if NULL, defaults 435 to "10", and EXP to "1". The EXP does not contain a leading 'e' or 'E'. */ 436 437 static int 438 processInt (const char *base0, const char *num0, const char *exp0) 439 { 440 ULONGEST result; 441 long exp; 442 int base; 443 444 char *trailer; 445 446 if (base0 == NULL) 447 base = 10; 448 else 449 { 450 base = strtol (base0, (char **) NULL, 10); 451 if (base < 2 || base > 16) 452 error ("Invalid base: %d.", base); 453 } 454 455 if (exp0 == NULL) 456 exp = 0; 457 else 458 exp = strtol(exp0, (char **) NULL, 10); 459 460 errno = 0; 461 result = strtoulst (num0, (const char **) &trailer, base); 462 if (errno == ERANGE) 463 error ("Integer literal out of range"); 464 if (isxdigit(*trailer)) 465 error ("Invalid digit `%c' in based literal", *trailer); 466 467 while (exp > 0) 468 { 469 if (result > (ULONG_MAX / base)) 470 error ("Integer literal out of range"); 471 result *= base; 472 exp -= 1; 473 } 474 475 if ((result >> (TARGET_INT_BIT-1)) == 0) 476 yylval.typed_val.type = type_int (); 477 else if ((result >> (TARGET_LONG_BIT-1)) == 0) 478 yylval.typed_val.type = type_long (); 479 else if (((result >> (TARGET_LONG_BIT-1)) >> 1) == 0) 480 { 481 /* We have a number representable as an unsigned integer quantity. 482 For consistency with the C treatment, we will treat it as an 483 anonymous modular (unsigned) quantity. Alas, the types are such 484 that we need to store .val as a signed quantity. Sorry 485 for the mess, but C doesn't officially guarantee that a simple 486 assignment does the trick (no, it doesn't; read the reference manual). 487 */ 488 yylval.typed_val.type = builtin_type_unsigned_long; 489 if (result & LONGEST_SIGN) 490 yylval.typed_val.val = 491 (LONGEST) (result & ~LONGEST_SIGN) 492 - (LONGEST_SIGN>>1) - (LONGEST_SIGN>>1); 493 else 494 yylval.typed_val.val = (LONGEST) result; 495 return INT; 496 } 497 else 498 yylval.typed_val.type = type_long_long (); 499 500 yylval.typed_val.val = (LONGEST) result; 501 return INT; 502 } 503 504 #if defined (PRINTF_HAS_LONG_DOUBLE) 505 # undef PRINTF_HAS_LONG_DOUBLE 506 # define PRINTF_HAS_LONG_DOUBLE 1 507 #else 508 # define PRINTF_HAS_LONG_DOUBLE 0 509 #endif 510 511 static int 512 processReal (const char *num0) 513 { 514 #if defined (PRINTF_HAS_LONG_DOUBLE) 515 if (sizeof (DOUBLEST) > sizeof (double)) 516 sscanf (num0, "%Lg", &yylval.typed_val_float.dval); 517 else 518 #endif 519 { 520 double temp; 521 sscanf (num0, "%lg", &temp); 522 yylval.typed_val_float.dval = temp; 523 } 524 525 yylval.typed_val_float.type = type_float (); 526 if (sizeof(DOUBLEST) >= TARGET_DOUBLE_BIT / TARGET_CHAR_BIT) 527 yylval.typed_val_float.type = type_double (); 528 if (sizeof(DOUBLEST) >= TARGET_LONG_DOUBLE_BIT / TARGET_CHAR_BIT) 529 yylval.typed_val_float.type = type_long_double (); 530 531 return FLOAT; 532 } 533 534 static int 535 processId (const char *name0, int len) 536 { 537 char *name = obstack_alloc (&temp_parse_space, len + 11); 538 int i0, i; 539 540 while (len > 0 && isspace (name0[len-1])) 541 len -= 1; 542 i = i0 = 0; 543 while (i0 < len) 544 { 545 if (isalnum (name0[i0])) 546 { 547 name[i] = tolower (name0[i0]); 548 i += 1; i0 += 1; 549 } 550 else switch (name0[i0]) 551 { 552 default: 553 name[i] = name0[i0]; 554 i += 1; i0 += 1; 555 break; 556 case ' ': case '\t': 557 i0 += 1; 558 break; 559 case '\'': 560 i0 += 1; 561 while (i0 < len && name0[i0] != '\'') 562 { 563 name[i] = name0[i0]; 564 i += 1; i0 += 1; 565 } 566 i0 += 1; 567 break; 568 case '<': 569 i0 += 1; 570 while (i0 < len && name0[i0] != '>') 571 { 572 name[i] = name0[i0]; 573 i += 1; i0 += 1; 574 } 575 i0 += 1; 576 break; 577 } 578 } 579 name[i] = '\000'; 580 581 yylval.ssym.sym = NULL; 582 yylval.ssym.stoken.ptr = name; 583 yylval.ssym.stoken.length = i; 584 return NAME; 585 } 586 587 static void 588 block_lookup (char *name, char *err_name) 589 { 590 struct ada_symbol_info *syms; 591 int nsyms; 592 struct symtab *symtab; 593 nsyms = ada_lookup_symbol_list (name, left_block_context, 594 VAR_DOMAIN, &syms); 595 if (left_block_context == NULL && 596 (nsyms == 0 || SYMBOL_CLASS (syms[0].sym) != LOC_BLOCK)) 597 symtab = lookup_symtab (name); 598 else 599 symtab = NULL; 600 601 if (symtab != NULL) 602 left_block_context = yylval.bval = 603 BLOCKVECTOR_BLOCK (BLOCKVECTOR (symtab), STATIC_BLOCK); 604 else if (nsyms == 0 || SYMBOL_CLASS (syms[0].sym) != LOC_BLOCK) 605 { 606 if (left_block_context == NULL) 607 error ("No file or function \"%s\".", err_name); 608 else 609 error ("No function \"%s\" in specified context.", err_name); 610 } 611 else 612 { 613 left_block_context = yylval.bval = SYMBOL_BLOCK_VALUE (syms[0].sym); 614 if (nsyms > 1) 615 warning ("Function name \"%s\" ambiguous here", err_name); 616 } 617 } 618 619 /* Look up NAME0 (assumed to be encoded) as a name in VAR_DOMAIN, 620 setting *TOKEN_TYPE to NAME or TYPENAME, depending on what is 621 found. Try first the entire name, then the name without the last 622 segment (i.e., after the last .id), etc., and return the number of 623 segments that had to be removed to get a match. Try only the full 624 name if it starts with "standard__". Calls error if no 625 matches are found, using ERR_NAME in any error message. When 626 exactly one symbol match is found, it is placed in yylval. When 627 the symbol is a renaming, follow at most DEPTH steps to find the 628 ultimate definition; cause error if depth exceeded. */ 629 630 static int 631 name_lookup (char *name0, char *err_name, int *token_type, int depth) 632 { 633 struct ada_symbol_info *syms; 634 struct type *type; 635 int len0 = strlen (name0); 636 char *name = obsavestring (name0, len0, &temp_parse_space); 637 int nsyms; 638 int segments; 639 640 if (depth <= 0) 641 error ("Could not find renamed symbol \"%s\"", err_name); 642 643 yylval.ssym.stoken.ptr = name; 644 yylval.ssym.stoken.length = strlen (name); 645 for (segments = 0; ; segments += 1) 646 { 647 struct type *preferred_type; 648 int i, preferred_index; 649 650 if (left_block_context == NULL) 651 nsyms = ada_lookup_symbol_list (name, expression_context_block, 652 VAR_DOMAIN, &syms); 653 else 654 nsyms = ada_lookup_symbol_list (name, left_block_context, 655 VAR_DOMAIN, &syms); 656 657 658 /* Check for a type renaming. */ 659 660 if (nsyms == 1 && !ada_is_object_renaming (syms[0].sym)) 661 { 662 struct symbol *renaming_sym = 663 ada_find_renaming_symbol (SYMBOL_LINKAGE_NAME (syms[0].sym), 664 syms[0].block); 665 666 if (renaming_sym != NULL) 667 syms[0].sym = renaming_sym; 668 } 669 670 /* Check for a type definition. */ 671 672 /* Look for a symbol that doesn't denote void. This is (I think) a */ 673 /* temporary kludge to get around problems in GNAT output. */ 674 preferred_index = -1; preferred_type = NULL; 675 for (i = 0; i < nsyms; i += 1) 676 switch (SYMBOL_CLASS (syms[i].sym)) 677 { 678 case LOC_TYPEDEF: 679 if (ada_prefer_type (SYMBOL_TYPE (syms[i].sym), preferred_type)) 680 { 681 preferred_index = i; 682 preferred_type = SYMBOL_TYPE (syms[i].sym); 683 } 684 break; 685 case LOC_REGISTER: 686 case LOC_ARG: 687 case LOC_REF_ARG: 688 case LOC_REGPARM: 689 case LOC_REGPARM_ADDR: 690 case LOC_LOCAL: 691 case LOC_LOCAL_ARG: 692 case LOC_BASEREG: 693 case LOC_BASEREG_ARG: 694 case LOC_COMPUTED: 695 case LOC_COMPUTED_ARG: 696 goto NotType; 697 default: 698 break; 699 } 700 if (preferred_type != NULL) 701 { 702 if (TYPE_CODE (preferred_type) == TYPE_CODE_VOID) 703 error ("`%s' matches only void type name(s)", 704 ada_decode (name)); 705 else if (ada_is_object_renaming (syms[preferred_index].sym)) 706 { 707 yylval.ssym.sym = syms[preferred_index].sym; 708 *token_type = OBJECT_RENAMING; 709 return segments; 710 } 711 else if (ada_renaming_type (SYMBOL_TYPE (syms[preferred_index].sym)) 712 != NULL) 713 { 714 int result; 715 char *renaming 716 = ada_simple_renamed_entity (syms[preferred_index].sym); 717 char *new_name 718 = (char *) obstack_alloc (&temp_parse_space, 719 strlen (renaming) + len0 720 - yylval.ssym.stoken.length + 1); 721 strcpy (new_name, renaming); 722 xfree (renaming); 723 strcat (new_name, name0 + yylval.ssym.stoken.length); 724 result = name_lookup (new_name, err_name, token_type, depth - 1); 725 if (result > segments) 726 error ("Confused by renamed symbol."); 727 return result; 728 } 729 else if (segments == 0) 730 { 731 yylval.tval = preferred_type; 732 *token_type = TYPENAME; 733 return 0; 734 } 735 } 736 737 if (segments == 0) 738 { 739 type = language_lookup_primitive_type_by_name (current_language, 740 current_gdbarch, 741 name); 742 if (type == NULL && strcmp ("system__address", name) == 0) 743 type = type_system_address (); 744 if (type != NULL) 745 { 746 /* First check to see if we have a regular definition of this 747 type that just didn't happen to have been read yet. */ 748 int ntypes; 749 struct symbol *sym; 750 char *expanded_name = 751 (char *) alloca (strlen (name) + sizeof ("standard__")); 752 strcpy (expanded_name, "standard__"); 753 strcat (expanded_name, name); 754 sym = ada_lookup_symbol (expanded_name, NULL, 755 VAR_DOMAIN, NULL, NULL); 756 if (sym != NULL && SYMBOL_CLASS (sym) == LOC_TYPEDEF) 757 type = SYMBOL_TYPE (sym); 758 759 yylval.tval = type; 760 *token_type = TYPENAME; 761 return 0; 762 } 763 } 764 765 NotType: 766 if (nsyms == 1) 767 { 768 *token_type = NAME; 769 yylval.ssym.sym = syms[0].sym; 770 yylval.ssym.msym = NULL; 771 yylval.ssym.block = syms[0].block; 772 return segments; 773 } 774 else if (nsyms == 0) { 775 int i; 776 yylval.ssym.msym = ada_lookup_simple_minsym (name); 777 if (yylval.ssym.msym != NULL) 778 { 779 yylval.ssym.sym = NULL; 780 yylval.ssym.block = NULL; 781 *token_type = NAME; 782 return segments; 783 } 784 785 if (segments == 0 786 && strncmp (name, "standard__", sizeof ("standard__") - 1) == 0) 787 error ("No definition of \"%s\" found.", err_name); 788 789 for (i = yylval.ssym.stoken.length - 1; i > 0; i -= 1) 790 { 791 if (name[i] == '.') 792 { 793 name[i] = '\0'; 794 yylval.ssym.stoken.length = i; 795 break; 796 } 797 else if (name[i] == '_' && name[i-1] == '_') 798 { 799 i -= 1; 800 name[i] = '\0'; 801 yylval.ssym.stoken.length = i; 802 break; 803 } 804 } 805 if (i <= 0) 806 { 807 if (!have_full_symbols () && !have_partial_symbols () 808 && left_block_context == NULL) 809 error ("No symbol table is loaded. Use the \"file\" command."); 810 if (left_block_context == NULL) 811 error ("No definition of \"%s\" in current context.", 812 err_name); 813 else 814 error ("No definition of \"%s\" in specified context.", 815 err_name); 816 } 817 } 818 else 819 { 820 *token_type = NAME; 821 yylval.ssym.sym = NULL; 822 yylval.ssym.msym = NULL; 823 if (left_block_context == NULL) 824 yylval.ssym.block = expression_context_block; 825 else 826 yylval.ssym.block = left_block_context; 827 return segments; 828 } 829 } 830 } 831 832 /* Returns the position within STR of the '.' in a 833 '.{WHITE}*all' component of a dotted name, or -1 if there is none. */ 834 static int 835 find_dot_all (const char *str) 836 { 837 int i; 838 for (i = 0; str[i] != '\000'; i += 1) 839 { 840 if (str[i] == '.') 841 { 842 int i0 = i; 843 do 844 i += 1; 845 while (isspace (str[i])); 846 if (strcmp (str+i, "all") == 0 847 && ! isalnum (str[i+3]) && str[i+3] != '_') 848 return i0; 849 } 850 } 851 return -1; 852 } 853 854 /* Returns non-zero iff string SUBSEQ matches a subsequence of STR, ignoring 855 case. */ 856 857 static int 858 subseqMatch (const char *subseq, const char *str) 859 { 860 if (subseq[0] == '\0') 861 return 1; 862 else if (str[0] == '\0') 863 return 0; 864 else if (tolower (subseq[0]) == tolower (str[0])) 865 return subseqMatch (subseq+1, str+1) || subseqMatch (subseq, str+1); 866 else 867 return subseqMatch (subseq, str+1); 868 } 869 870 871 static struct { const char *name; int code; } 872 attributes[] = { 873 { "address", TICK_ADDRESS }, 874 { "unchecked_access", TICK_ACCESS }, 875 { "unrestricted_access", TICK_ACCESS }, 876 { "access", TICK_ACCESS }, 877 { "first", TICK_FIRST }, 878 { "last", TICK_LAST }, 879 { "length", TICK_LENGTH }, 880 { "max", TICK_MAX }, 881 { "min", TICK_MIN }, 882 { "modulus", TICK_MODULUS }, 883 { "pos", TICK_POS }, 884 { "range", TICK_RANGE }, 885 { "size", TICK_SIZE }, 886 { "tag", TICK_TAG }, 887 { "val", TICK_VAL }, 888 { NULL, -1 } 889 }; 890 891 /* Return the syntactic code corresponding to the attribute name or 892 abbreviation STR. */ 893 894 static int 895 processAttribute (const char *str) 896 { 897 int i, k; 898 899 for (i = 0; attributes[i].code != -1; i += 1) 900 if (strcasecmp (str, attributes[i].name) == 0) 901 return attributes[i].code; 902 903 for (i = 0, k = -1; attributes[i].code != -1; i += 1) 904 if (subseqMatch (str, attributes[i].name)) 905 { 906 if (k == -1) 907 k = i; 908 else 909 error ("ambiguous attribute name: `%s'", str); 910 } 911 if (k == -1) 912 error ("unrecognized attribute: `%s'", str); 913 914 return attributes[k].code; 915 } 916 917 int 918 yywrap(void) 919 { 920 return 1; 921 } 922 923 /* Dummy definition to suppress warnings about unused static definitions. */ 924 typedef void (*dummy_function) (); 925 dummy_function ada_flex_use[] = 926 { 927 (dummy_function) yyunput 928 }; 929