xref: /openbsd/gnu/usr.bin/binutils/gdb/ada-lex.l (revision 17df1aa7)
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