1 /*
   2  * CDDL HEADER START
   3  *
   4  * The contents of this file are subject to the terms of the
   5  * Common Development and Distribution License (the "License").
   6  * You may not use this file except in compliance with the License.
   7  *
   8  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
   9  * or http://www.opensolaris.org/os/licensing.
  10  * See the License for the specific language governing permissions
  11  * and limitations under the License.
  12  *
  13  * When distributing Covered Code, include this CDDL HEADER in each
  14  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
  15  * If applicable, add the following below this CDDL HEADER, with the
  16  * fields enclosed by brackets "[]" replaced with your own identifying
  17  * information: Portions Copyright [yyyy] [name of copyright owner]
  18  *
  19  * CDDL HEADER END
  20  */
  21 /*
  22  * Copyright (c) 2001, 2010, Oracle and/or its affiliates. All rights reserved.
  23  */
  24 
  25 /*
  26  * This file is a sewer.
  27  */
  28 
  29 #include <limits.h>
  30 #include <stdarg.h>
  31 #include <stdio.h>
  32 #include <assert.h>
  33 #include <strings.h>
  34 #include <setjmp.h>
  35 #include <ctype.h>
  36 #include <uts/common/sys/ctf.h>
  37 
  38 #include "ctftools.h"
  39 #include "memory.h"
  40 #include "list.h"
  41 
  42 #define HASH(NUM)       ((int)(NUM & (BUCKETS - 1)))
  43 #define BUCKETS         128
  44 
  45 #define TYPEPAIRMULT    10000
  46 #define MAKETYPEID(file, num)   ((file) * TYPEPAIRMULT + num)
  47 #define TYPEFILE(tid)           ((tid) / TYPEPAIRMULT)
  48 #define TYPENUM(tid)            ((tid) % TYPEPAIRMULT)
  49 
  50 #define expected(a, b, c) _expected(a, b, c, __LINE__)
  51 
  52 static int faketypenumber = 100000000;
  53 
  54 static tdesc_t *hash_table[BUCKETS];
  55 static tdesc_t *name_table[BUCKETS];
  56 
  57 list_t *typedbitfldmems;
  58 
  59 static void reset(void);
  60 static jmp_buf  resetbuf;
  61 
  62 static char *soudef(char *cp, stabtype_t type, tdesc_t **rtdp);
  63 static void enumdef(char *cp, tdesc_t **rtdp);
  64 static int compute_sum(const char *w);
  65 
  66 static char *number(char *cp, int *n);
  67 static char *name(char *cp, char **w);
  68 static char *id(char *cp, int *h);
  69 static char *whitesp(char *cp);
  70 static void addhash(tdesc_t *tdp, int num);
  71 static int tagadd(char *w, int h, tdesc_t *tdp);
  72 static char *tdefdecl(char *cp, int h, tdesc_t **rtdp);
  73 static char *intrinsic(char *cp, tdesc_t **rtdp);
  74 static char *arraydef(char *cp, tdesc_t **rtdp);
  75 
  76 extern int debug_level;
  77 int debug_parse = DEBUG_PARSE;
  78 
  79 /*PRINTFLIKE3*/
  80 static void
  81 parse_debug(int level, char *cp, char *fmt, ...)
  82 {
  83         va_list ap;
  84         char buf[1024];
  85         char tmp[32];
  86         int i;
  87 
  88         if (level > debug_level || !debug_parse)
  89                 return;
  90 
  91         if (cp != NULL) {
  92                 for (i = 0; i < 30; i++) {
  93                         if (cp[i] == '\0')
  94                                 break;
  95                         if (!iscntrl(cp[i]))
  96                                 tmp[i] = cp[i];
  97                 }
  98                 tmp[i] = '\0';
  99                 (void) snprintf(buf, sizeof (buf), "%s [cp='%s']\n", fmt, tmp);
 100         } else {
 101                 strcpy(buf, fmt);
 102                 strcat(buf, "\n");
 103         }
 104 
 105         va_start(ap, fmt);
 106         vadebug(level, buf, ap);
 107         va_end(ap);
 108 }
 109 
 110 /* Report unexpected syntax in stabs. */
 111 static void
 112 _expected(
 113         char *who,      /* what function, or part thereof, is reporting */
 114         char *what,     /* what was expected */
 115         char *where,    /* where we were in the line of input */
 116         int line)
 117 {
 118         fprintf(stderr, "%s, expecting \"%s\" at \"%s\"\n", who, what, where);
 119         fprintf(stderr, "code line: %d, file %s\n", line,
 120             (curhdr ? curhdr : "NO FILE"));
 121         reset();
 122 }
 123 
 124 /*ARGSUSED*/
 125 void
 126 parse_init(tdata_t *td)
 127 {
 128         int i;
 129 
 130         for (i = 0; i < BUCKETS; i++) {
 131                 hash_table[i] = NULL;
 132                 name_table[i] = NULL;
 133         }
 134 
 135         if (typedbitfldmems != NULL) {
 136                 list_free(typedbitfldmems, NULL, NULL);
 137                 typedbitfldmems = NULL;
 138         }
 139 }
 140 
 141 void
 142 parse_finish(tdata_t *td)
 143 {
 144         td->td_nextid = ++faketypenumber;
 145 }
 146 
 147 static tdesc_t *
 148 unres_new(int tid)
 149 {
 150         tdesc_t *tdp;
 151 
 152         tdp = xcalloc(sizeof (*tdp));
 153         tdp->t_type = TYPEDEF_UNRES;
 154         tdp->t_id = tid;
 155 
 156         return (tdp);
 157 }
 158 
 159 char *
 160 read_tid(char *cp, tdesc_t **tdpp)
 161 {
 162         tdesc_t *tdp;
 163         int tid;
 164 
 165         cp = id(cp, &tid);
 166 
 167         assert(tid != 0);
 168 
 169         if (*cp == '=') {
 170                 if (!(cp = tdefdecl(cp + 1, tid, &tdp)))
 171                         return (NULL);
 172                 if (tdp->t_id && tdp->t_id != tid) {
 173                         tdesc_t *ntdp = xcalloc(sizeof (*ntdp));
 174 
 175                         ntdp->t_type = TYPEDEF;
 176                         ntdp->t_tdesc = tdp;
 177                         tdp = ntdp;
 178                 }
 179                 addhash(tdp, tid);
 180         } else if ((tdp = lookup(tid)) == NULL)
 181                 tdp = unres_new(tid);
 182 
 183         *tdpp = tdp;
 184         return (cp);
 185 }
 186 
 187 static iitype_t
 188 parse_fun(char *cp, iidesc_t *ii)
 189 {
 190         iitype_t iitype;
 191         tdesc_t *tdp;
 192         tdesc_t **args = NULL;
 193         int nargs = 0;
 194         int va = 0;
 195 
 196         /*
 197          * name:P               prototype
 198          * name:F               global function
 199          * name:f               static function
 200          */
 201         switch (*cp++) {
 202         case 'P':
 203                 iitype = II_NOT; /* not interesting */
 204                 break;
 205 
 206         case 'F':
 207                 iitype = II_GFUN;
 208                 break;
 209 
 210         case 'f':
 211                 iitype = II_SFUN;
 212                 break;
 213 
 214         default:
 215                 expected("parse_nfun", "[PfF]", cp - 1);
 216         }
 217 
 218         if (!(cp = read_tid(cp, &tdp)))
 219                 return (-1);
 220 
 221         if (*cp)
 222                 args = xmalloc(sizeof (tdesc_t *) * FUNCARG_DEF);
 223 
 224         while (*cp && *++cp) {
 225                 if (*cp == '0') {
 226                         va = 1;
 227                         continue;
 228                 }
 229 
 230                 nargs++;
 231                 if (nargs > FUNCARG_DEF)
 232                         args = xrealloc(args, sizeof (tdesc_t *) * nargs);
 233                 if (!(cp = read_tid(cp, &args[nargs - 1])))
 234                         return (-1);
 235         }
 236 
 237         ii->ii_type = iitype;
 238         ii->ii_dtype = tdp;
 239         ii->ii_nargs = nargs;
 240         ii->ii_args = args;
 241         ii->ii_vargs = va;
 242 
 243         return (iitype);
 244 }
 245 
 246 static iitype_t
 247 parse_sym(char *cp, iidesc_t *ii)
 248 {
 249         tdesc_t *tdp;
 250         iitype_t iitype;
 251 
 252         /*
 253          * name:G               global variable
 254          * name:S               static variable
 255          */
 256         switch (*cp++) {
 257         case 'G':
 258                 iitype = II_GVAR;
 259                 break;
 260         case 'S':
 261                 iitype = II_SVAR;
 262                 break;
 263         case 'p':
 264                 iitype = II_PSYM;
 265                 break;
 266         case '(':
 267                 cp--;
 268                 /*FALLTHROUGH*/
 269         case 'r':
 270         case 'V':
 271                 iitype = II_NOT; /* not interesting */
 272                 break;
 273         default:
 274                 expected("parse_sym", "[GprSV(]", cp - 1);
 275         }
 276 
 277         if (!(cp = read_tid(cp, &tdp)))
 278                 return (-1);
 279 
 280         ii->ii_type = iitype;
 281         ii->ii_dtype = tdp;
 282 
 283         return (iitype);
 284 }
 285 
 286 static iitype_t
 287 parse_type(char *cp, iidesc_t *ii)
 288 {
 289         tdesc_t *tdp, *ntdp;
 290         int tid;
 291 
 292         if (*cp++ != 't')
 293                 expected("parse_type", "t (type)", cp - 1);
 294 
 295         cp = id(cp, &tid);
 296         if ((tdp = lookup(tid)) == NULL) {
 297                 if (*cp++ != '=')
 298                         expected("parse_type", "= (definition)", cp - 1);
 299 
 300                 (void) tdefdecl(cp, tid, &tdp);
 301 
 302                 if (tdp->t_id == tid) {
 303                         assert(tdp->t_type != TYPEDEF);
 304                         assert(!lookup(tdp->t_id));
 305 
 306                         if (!streq(tdp->t_name, ii->ii_name)) {
 307                                 ntdp = xcalloc(sizeof (*ntdp));
 308                                 ntdp->t_name = xstrdup(ii->ii_name);
 309                                 ntdp->t_type = TYPEDEF;
 310                                 ntdp->t_tdesc = tdp;
 311                                 tdp->t_id = faketypenumber++;
 312                                 tdp = ntdp;
 313                         }
 314                 } else if (tdp->t_id == 0) {
 315                         assert(tdp->t_type == FORWARD ||
 316                             tdp->t_type == INTRINSIC);
 317 
 318                         if (tdp->t_name && !streq(tdp->t_name, ii->ii_name)) {
 319                                 ntdp = xcalloc(sizeof (*ntdp));
 320                                 ntdp->t_name = xstrdup(ii->ii_name);
 321                                 ntdp->t_type = TYPEDEF;
 322                                 ntdp->t_tdesc = tdp;
 323                                 tdp->t_id = faketypenumber++;
 324                                 tdp = ntdp;
 325                         }
 326                 } else if (tdp->t_id != tid) {
 327                         ntdp = xcalloc(sizeof (*ntdp));
 328                         ntdp->t_name = xstrdup(ii->ii_name);
 329                         ntdp->t_type = TYPEDEF;
 330                         ntdp->t_tdesc = tdp;
 331                         tdp = ntdp;
 332                 }
 333 
 334                 if (tagadd(ii->ii_name, tid, tdp) < 0)
 335                         return (-1);
 336         }
 337 
 338         ii->ii_type = II_TYPE;
 339         ii->ii_dtype = tdp;
 340         return (II_TYPE);
 341 }
 342 
 343 static iitype_t
 344 parse_sou(char *cp, iidesc_t *idp)
 345 {
 346         tdesc_t *rtdp;
 347         int tid;
 348 
 349         if (*cp++ != 'T')
 350                 expected("parse_sou", "T (sou)", cp - 1);
 351 
 352         cp = id(cp, &tid);
 353         if (*cp++ != '=')
 354                 expected("parse_sou", "= (definition)", cp - 1);
 355 
 356         parse_debug(1, NULL, "parse_sou: declaring '%s'", idp->ii_name ?
 357             idp->ii_name : "(anon)");
 358         if ((rtdp = lookup(tid)) != NULL) {
 359                 if (idp->ii_name != NULL) {
 360                         if (rtdp->t_name != NULL &&
 361                             strcmp(rtdp->t_name, idp->ii_name) != 0) {
 362                                 tdesc_t *tdp;
 363 
 364                                 tdp = xcalloc(sizeof (*tdp));
 365                                 tdp->t_name = xstrdup(idp->ii_name);
 366                                 tdp->t_type = TYPEDEF;
 367                                 tdp->t_tdesc = rtdp;
 368                                 addhash(tdp, tid); /* for *(x,y) types */
 369                                 parse_debug(3, NULL, "    %s defined as %s(%d)",
 370                                     idp->ii_name, tdesc_name(rtdp), tid);
 371                         } else if (rtdp->t_name == NULL) {
 372                                 rtdp->t_name = xstrdup(idp->ii_name);
 373                                 addhash(rtdp, tid);
 374                         }
 375                 }
 376         } else {
 377                 rtdp = xcalloc(sizeof (*rtdp));
 378                 rtdp->t_name = idp->ii_name ? xstrdup(idp->ii_name) : NULL;
 379                 addhash(rtdp, tid);
 380         }
 381 
 382         switch (*cp++) {
 383         case 's':
 384                 (void) soudef(cp, STRUCT, &rtdp);
 385                 break;
 386         case 'u':
 387                 (void) soudef(cp, UNION, &rtdp);
 388                 break;
 389         case 'e':
 390                 enumdef(cp, &rtdp);
 391                 break;
 392         default:
 393                 expected("parse_sou", "<tag type s/u/e>", cp - 1);
 394                 break;
 395         }
 396 
 397         idp->ii_type = II_SOU;
 398         idp->ii_dtype = rtdp;
 399         return (II_SOU);
 400 }
 401 
 402 int
 403 parse_stab(stab_t *stab, char *cp, iidesc_t **iidescp)
 404 {
 405         iidesc_t *ii = NULL;
 406         iitype_t (*parse)(char *, iidesc_t *);
 407         int rc;
 408 
 409         /*
 410          * set up for reset()
 411          */
 412         if (setjmp(resetbuf))
 413                 return (-1);
 414 
 415         cp = whitesp(cp);
 416         ii = iidesc_new(NULL);
 417         cp = name(cp, &ii->ii_name);
 418 
 419         switch (stab->n_type) {
 420         case N_FUN:
 421                 parse = parse_fun;
 422                 break;
 423 
 424         case N_LSYM:
 425                 if (*cp == 't')
 426                         parse = parse_type;
 427                 else if (*cp == 'T')
 428                         parse = parse_sou;
 429                 else
 430                         parse = parse_sym;
 431                 break;
 432 
 433         case N_GSYM:
 434         case N_LCSYM:
 435         case N_PSYM:
 436         case N_ROSYM:
 437         case N_RSYM:
 438         case N_STSYM:
 439                 parse = parse_sym;
 440                 break;
 441         default:
 442                 parse_debug(1, cp, "Unknown stab type %#x", stab->n_type);
 443                 bzero(&resetbuf, sizeof (resetbuf));
 444                 return (-1);
 445         }
 446 
 447         rc = parse(cp, ii);
 448         bzero(&resetbuf, sizeof (resetbuf));
 449 
 450         if (rc < 0 || ii->ii_type == II_NOT) {
 451                 iidesc_free(ii);
 452                 return (rc);
 453         }
 454 
 455         *iidescp = ii;
 456 
 457         return (1);
 458 }
 459 
 460 /*
 461  * Check if we have this node in the hash table already
 462  */
 463 tdesc_t *
 464 lookup(int h)
 465 {
 466         int bucket = HASH(h);
 467         tdesc_t *tdp = hash_table[bucket];
 468 
 469         while (tdp != NULL) {
 470                 if (tdp->t_id == h)
 471                         return (tdp);
 472                 tdp = tdp->t_hash;
 473         }
 474         return (NULL);
 475 }
 476 
 477 static char *
 478 whitesp(char *cp)
 479 {
 480         char c;
 481 
 482         for (c = *cp++; isspace(c); c = *cp++)
 483                 ;
 484         --cp;
 485         return (cp);
 486 }
 487 
 488 static char *
 489 name(char *cp, char **w)
 490 {
 491         char *new, *orig, c;
 492         int len;
 493 
 494         orig = cp;
 495         c = *cp++;
 496         if (c == ':')
 497                 *w = NULL;
 498         else if (isalpha(c) || strchr("_.$#", c)) {
 499                 for (c = *cp++; isalnum(c) || strchr(" _.$#", c); c = *cp++)
 500                         ;
 501                 if (c != ':')
 502                         reset();
 503                 len = cp - orig;
 504                 new = xmalloc(len);
 505                 while (orig < cp - 1)
 506                         *new++ = *orig++;
 507                 *new = '\0';
 508                 *w = new - (len - 1);
 509         } else
 510                 reset();
 511 
 512         return (cp);
 513 }
 514 
 515 static char *
 516 number(char *cp, int *n)
 517 {
 518         char *next;
 519 
 520         *n = (int)strtol(cp, &next, 10);
 521         if (next == cp)
 522                 expected("number", "<number>", cp);
 523         return (next);
 524 }
 525 
 526 static char *
 527 id(char *cp, int *h)
 528 {
 529         int n1, n2;
 530 
 531         if (*cp == '(') {       /* SunPro style */
 532                 cp++;
 533                 cp = number(cp, &n1);
 534                 if (*cp++ != ',')
 535                         expected("id", ",", cp - 1);
 536                 cp = number(cp, &n2);
 537                 if (*cp++ != ')')
 538                         expected("id", ")", cp - 1);
 539                 *h = MAKETYPEID(n1, n2);
 540         } else if (isdigit(*cp)) { /* gcc style */
 541                 cp = number(cp, &n1);
 542                 *h = n1;
 543         } else {
 544                 expected("id", "(/0-9", cp);
 545         }
 546         return (cp);
 547 }
 548 
 549 static int
 550 tagadd(char *w, int h, tdesc_t *tdp)
 551 {
 552         tdesc_t *otdp;
 553 
 554         tdp->t_name = w;
 555         if (!(otdp = lookup(h)))
 556                 addhash(tdp, h);
 557         else if (otdp != tdp) {
 558                 warning("duplicate entry\n");
 559                 warning("  old: %s %d (%d,%d)\n", tdesc_name(otdp),
 560                     otdp->t_type, TYPEFILE(otdp->t_id), TYPENUM(otdp->t_id));
 561                 warning("  new: %s %d (%d,%d)\n", tdesc_name(tdp),
 562                     tdp->t_type, TYPEFILE(tdp->t_id), TYPENUM(tdp->t_id));
 563                 return (-1);
 564         }
 565 
 566         return (0);
 567 }
 568 
 569 static char *
 570 tdefdecl(char *cp, int h, tdesc_t **rtdp)
 571 {
 572         tdesc_t *ntdp;
 573         char *w;
 574         int c, h2;
 575         char type;
 576 
 577         parse_debug(3, cp, "tdefdecl h=%d", h);
 578 
 579         /* Type codes */
 580         switch (type = *cp) {
 581         case 'b': /* integer */
 582         case 'R': /* fp */
 583                 cp = intrinsic(cp, rtdp);
 584                 break;
 585         case '(': /* equiv to another type */
 586                 cp = id(cp, &h2);
 587                 ntdp = lookup(h2);
 588 
 589                 if (ntdp != NULL && *cp == '=') {
 590                         if (ntdp->t_type == FORWARD && *(cp + 1) == 'x') {
 591                                 /*
 592                                  * The 6.2 compiler, and possibly others, will
 593                                  * sometimes emit the same stab for a forward
 594                                  * declaration twice.  That is, "(1,2)=xsfoo:"
 595                                  * will sometimes show up in two different
 596                                  * places.  This is, of course, quite fun.  We
 597                                  * want CTF to work in spite of the compiler,
 598                                  * so we'll let this one through.
 599                                  */
 600                                 char *c2 = cp + 2;
 601                                 char *nm;
 602 
 603                                 if (!strchr("sue", *c2++)) {
 604                                         expected("tdefdecl/x-redefine", "[sue]",
 605                                             c2 - 1);
 606                                 }
 607 
 608                                 c2 = name(c2, &nm);
 609                                 if (strcmp(nm, ntdp->t_name) != 0) {
 610                                         terminate("Stabs error: Attempt to "
 611                                             "redefine type (%d,%d) as "
 612                                             "something else: %s\n",
 613                                             TYPEFILE(h2), TYPENUM(h2),
 614                                             c2 - 1);
 615                                 }
 616                                 free(nm);
 617 
 618                                 h2 = faketypenumber++;
 619                                 ntdp = NULL;
 620                         } else {
 621                                 terminate("Stabs error: Attempting to "
 622                                     "redefine type (%d,%d)\n", TYPEFILE(h2),
 623                                     TYPENUM(h2));
 624                         }
 625                 }
 626 
 627                 if (ntdp == NULL) {  /* if that type isn't defined yet */
 628                         if (*cp != '=') {
 629                                 /* record it as unresolved */
 630                                 parse_debug(3, NULL, "tdefdecl unres type %d",
 631                                     h2);
 632                                 *rtdp = calloc(sizeof (**rtdp), 1);
 633                                 (*rtdp)->t_type = TYPEDEF_UNRES;
 634                                 (*rtdp)->t_id = h2;
 635                                 break;
 636                         } else
 637                                 cp++;
 638 
 639                         /* define a new type */
 640                         cp = tdefdecl(cp, h2, rtdp);
 641                         if ((*rtdp)->t_id && (*rtdp)->t_id != h2) {
 642                                 ntdp = calloc(sizeof (*ntdp), 1);
 643                                 ntdp->t_type = TYPEDEF;
 644                                 ntdp->t_tdesc = *rtdp;
 645                                 *rtdp = ntdp;
 646                         }
 647 
 648                         addhash(*rtdp, h2);
 649 
 650                 } else { /* that type is already defined */
 651                         if (ntdp->t_type != TYPEDEF || ntdp->t_name != NULL) {
 652                                 *rtdp = ntdp;
 653                         } else {
 654                                 parse_debug(3, NULL,
 655                                     "No duplicate typedef anon for ref");
 656                                 *rtdp = ntdp;
 657                         }
 658                 }
 659                 break;
 660         case '*':
 661                 ntdp = NULL;
 662                 cp = tdefdecl(cp + 1, h, &ntdp);
 663                 if (ntdp == NULL)
 664                         expected("tdefdecl/*", "id", cp);
 665 
 666                 if (!ntdp->t_id)
 667                         ntdp->t_id = faketypenumber++;
 668 
 669                 *rtdp = xcalloc(sizeof (**rtdp));
 670                 (*rtdp)->t_type = POINTER;
 671                 (*rtdp)->t_size = 0;
 672                 (*rtdp)->t_id = h;
 673                 (*rtdp)->t_tdesc = ntdp;
 674                 break;
 675         case 'f':
 676                 cp = tdefdecl(cp + 1, h, &ntdp);
 677                 *rtdp = xcalloc(sizeof (**rtdp));
 678                 (*rtdp)->t_type = FUNCTION;
 679                 (*rtdp)->t_size = 0;
 680                 (*rtdp)->t_id = h;
 681                 (*rtdp)->t_fndef = xcalloc(sizeof (fndef_t));
 682                 /*
 683                  * The 6.1 compiler will sometimes generate incorrect stabs for
 684                  * function pointers (it'll get the return type wrong).  This
 685                  * causes merges to fail.  We therefore treat function pointers
 686                  * as if they all point to functions that return int.  When
 687                  * 4432549 is fixed, the lookupname() call below should be
 688                  * replaced with `ntdp'.
 689                  */
 690                 (*rtdp)->t_fndef->fn_ret = lookupname("int");
 691                 break;
 692         case 'a':
 693         case 'z':
 694                 cp++;
 695                 if (*cp++ != 'r')
 696                         expected("tdefdecl/[az]", "r", cp - 1);
 697                 *rtdp = xcalloc(sizeof (**rtdp));
 698                 (*rtdp)->t_type = ARRAY;
 699                 (*rtdp)->t_id = h;
 700                 cp = arraydef(cp, rtdp);
 701                 break;
 702         case 'x':
 703                 c = *++cp;
 704                 if (c != 's' && c != 'u' && c != 'e')
 705                         expected("tdefdecl/x", "[sue]", cp - 1);
 706                 cp = name(cp + 1, &w);
 707 
 708                 ntdp = xcalloc(sizeof (*ntdp));
 709                 ntdp->t_type = FORWARD;
 710                 ntdp->t_name = w;
 711                 /*
 712                  * We explicitly don't set t_id here - the caller will do it.
 713                  * The caller may want to use a real type ID, or they may
 714                  * choose to make one up.
 715                  */
 716 
 717                 *rtdp = ntdp;
 718                 break;
 719 
 720         case 'B': /* volatile */
 721                 cp = tdefdecl(cp + 1, h, &ntdp);
 722 
 723                 if (!ntdp->t_id)
 724                         ntdp->t_id = faketypenumber++;
 725 
 726                 *rtdp = xcalloc(sizeof (**rtdp));
 727                 (*rtdp)->t_type = VOLATILE;
 728                 (*rtdp)->t_size = 0;
 729                 (*rtdp)->t_tdesc = ntdp;
 730                 (*rtdp)->t_id = h;
 731                 break;
 732 
 733         case 'k': /* const */
 734                 cp = tdefdecl(cp + 1, h, &ntdp);
 735 
 736                 if (!ntdp->t_id)
 737                         ntdp->t_id = faketypenumber++;
 738 
 739                 *rtdp = xcalloc(sizeof (**rtdp));
 740                 (*rtdp)->t_type = CONST;
 741                 (*rtdp)->t_size = 0;
 742                 (*rtdp)->t_tdesc = ntdp;
 743                 (*rtdp)->t_id = h;
 744                 break;
 745 
 746         case 'K': /* restricted */
 747                 cp = tdefdecl(cp + 1, h, &ntdp);
 748 
 749                 if (!ntdp->t_id)
 750                         ntdp->t_id = faketypenumber++;
 751 
 752                 *rtdp = xcalloc(sizeof (**rtdp));
 753                 (*rtdp)->t_type = RESTRICT;
 754                 (*rtdp)->t_size = 0;
 755                 (*rtdp)->t_tdesc = ntdp;
 756                 (*rtdp)->t_id = h;
 757                 break;
 758 
 759         case 'u':
 760         case 's':
 761                 cp++;
 762 
 763                 *rtdp = xcalloc(sizeof (**rtdp));
 764                 (*rtdp)->t_name = NULL;
 765                 cp = soudef(cp, (type == 'u') ? UNION : STRUCT, rtdp);
 766                 break;
 767         default:
 768                 expected("tdefdecl", "<type code>", cp);
 769         }
 770         return (cp);
 771 }
 772 
 773 static char *
 774 intrinsic(char *cp, tdesc_t **rtdp)
 775 {
 776         intr_t *intr = xcalloc(sizeof (intr_t));
 777         tdesc_t *tdp;
 778         int width, fmt, i;
 779 
 780         switch (*cp++) {
 781         case 'b':
 782                 intr->intr_type = INTR_INT;
 783                 if (*cp == 's')
 784                         intr->intr_signed = 1;
 785                 else if (*cp != 'u')
 786                         expected("intrinsic/b", "[su]", cp);
 787                 cp++;
 788 
 789                 if (strchr("cbv", *cp))
 790                         intr->intr_iformat = *cp++;
 791 
 792                 cp = number(cp, &width);
 793                 if (*cp++ != ';')
 794                         expected("intrinsic/b", "; (post-width)", cp - 1);
 795 
 796                 cp = number(cp, &intr->intr_offset);
 797                 if (*cp++ != ';')
 798                         expected("intrinsic/b", "; (post-offset)", cp - 1);
 799 
 800                 cp = number(cp, &intr->intr_nbits);
 801                 break;
 802 
 803         case 'R':
 804                 intr->intr_type = INTR_REAL;
 805                 for (fmt = 0, i = 0; isdigit(*(cp + i)); i++)
 806                         fmt = fmt * 10 + (*(cp + i) - '0');
 807 
 808                 if (fmt < 1 || fmt > CTF_FP_MAX)
 809                         expected("intrinsic/R", "number <= CTF_FP_MAX", cp);
 810 
 811                 intr->intr_fformat = fmt;
 812                 cp += i;
 813 
 814                 if (*cp++ != ';')
 815                         expected("intrinsic/R", ";", cp - 1);
 816                 cp = number(cp, &width);
 817 
 818                 intr->intr_nbits = width * 8;
 819                 break;
 820         }
 821 
 822         tdp = xcalloc(sizeof (*tdp));
 823         tdp->t_type = INTRINSIC;
 824         tdp->t_size = width;
 825         tdp->t_name = NULL;
 826         tdp->t_intr = intr;
 827         parse_debug(3, NULL, "intrinsic: size=%d", width);
 828         *rtdp = tdp;
 829 
 830         return (cp);
 831 }
 832 
 833 static tdesc_t *
 834 bitintrinsic(tdesc_t *template, int nbits)
 835 {
 836         tdesc_t *newtdp = xcalloc(sizeof (tdesc_t));
 837 
 838         newtdp->t_name = xstrdup(template->t_name);
 839         newtdp->t_id = faketypenumber++;
 840         newtdp->t_type = INTRINSIC;
 841         newtdp->t_size = template->t_size;
 842         newtdp->t_intr = xmalloc(sizeof (intr_t));
 843         bcopy(template->t_intr, newtdp->t_intr, sizeof (intr_t));
 844         newtdp->t_intr->intr_nbits = nbits;
 845 
 846         return (newtdp);
 847 }
 848 
 849 static char *
 850 offsize(char *cp, mlist_t *mlp)
 851 {
 852         int offset, size;
 853 
 854         if (*cp == ',')
 855                 cp++;
 856         cp = number(cp, &offset);
 857         if (*cp++ != ',')
 858                 expected("offsize/2", ",", cp - 1);
 859         cp = number(cp, &size);
 860         if (*cp++ != ';')
 861                 expected("offsize/3", ";", cp - 1);
 862         mlp->ml_offset = offset;
 863         mlp->ml_size = size;
 864         return (cp);
 865 }
 866 
 867 static tdesc_t *
 868 find_intrinsic(tdesc_t *tdp)
 869 {
 870         for (;;) {
 871                 switch (tdp->t_type) {
 872                 case TYPEDEF:
 873                 case VOLATILE:
 874                 case CONST:
 875                 case RESTRICT:
 876                         tdp = tdp->t_tdesc;
 877                         break;
 878 
 879                 default:
 880                         return (tdp);
 881                 }
 882         }
 883 }
 884 
 885 static char *
 886 soudef(char *cp, stabtype_t type, tdesc_t **rtdp)
 887 {
 888         mlist_t *mlp, **prev;
 889         char *w;
 890         int h;
 891         int size;
 892         tdesc_t *tdp, *itdp;
 893 
 894         cp = number(cp, &size);
 895         (*rtdp)->t_size = size;
 896         (*rtdp)->t_type = type; /* s or u */
 897 
 898         /*
 899          * An '@' here indicates a bitmask follows.   This is so the
 900          * compiler can pass information to debuggers about how structures
 901          * are passed in the v9 world.  We don't need this information
 902          * so we skip over it.
 903          */
 904         if (cp[0] == '@') {
 905                 cp += 3;
 906         }
 907 
 908         parse_debug(3, cp, "soudef: %s size=%d", tdesc_name(*rtdp),
 909             (*rtdp)->t_size);
 910 
 911         prev = &((*rtdp)->t_members);
 912         /* now fill up the fields */
 913         while ((*cp != '\0') && (*cp != ';')) { /* signifies end of fields */
 914                 mlp = xcalloc(sizeof (*mlp));
 915                 *prev = mlp;
 916                 cp = name(cp, &w);
 917                 mlp->ml_name = w;
 918                 cp = id(cp, &h);
 919                 /*
 920                  * find the tdesc struct in the hash table for this type
 921                  * and stick a ptr in here
 922                  */
 923                 tdp = lookup(h);
 924                 if (tdp == NULL) { /* not in hash list */
 925                         parse_debug(3, NULL, "      defines %s (%d)", w, h);
 926                         if (*cp++ != '=') {
 927                                 tdp = unres_new(h);
 928                                 parse_debug(3, NULL,
 929                                     "      refers to %s (unresolved %d)",
 930                                     (w ? w : "anon"), h);
 931                         } else {
 932                                 cp = tdefdecl(cp, h, &tdp);
 933 
 934                                 if (tdp->t_id && tdp->t_id != h) {
 935                                         tdesc_t *ntdp = xcalloc(sizeof (*ntdp));
 936 
 937                                         ntdp->t_type = TYPEDEF;
 938                                         ntdp->t_tdesc = tdp;
 939                                         tdp = ntdp;
 940                                 }
 941 
 942                                 addhash(tdp, h);
 943                                 parse_debug(4, cp,
 944                                     "     soudef now looking at    ");
 945                                 cp++;
 946                         }
 947                 } else {
 948                         parse_debug(3, NULL, "      refers to %s (%d, %s)",
 949                             w ? w : "anon", h, tdesc_name(tdp));
 950                 }
 951 
 952                 cp = offsize(cp, mlp);
 953 
 954                 itdp = find_intrinsic(tdp);
 955                 if (itdp->t_type == INTRINSIC) {
 956                         if (mlp->ml_size != itdp->t_intr->intr_nbits) {
 957                                 parse_debug(4, cp, "making %d bit intrinsic "
 958                                     "from %s", mlp->ml_size, tdesc_name(itdp));
 959                                 mlp->ml_type = bitintrinsic(itdp, mlp->ml_size);
 960                         } else
 961                                 mlp->ml_type = tdp;
 962                 } else if (itdp->t_type == TYPEDEF_UNRES) {
 963                         list_add(&typedbitfldmems, mlp);
 964                         mlp->ml_type = tdp;
 965                 } else {
 966                         mlp->ml_type = tdp;
 967                 }
 968 
 969                 /* cp is now pointing to next field */
 970                 prev = &mlp->ml_next;
 971         }
 972         return (cp);
 973 }
 974 
 975 static char *
 976 arraydef(char *cp, tdesc_t **rtdp)
 977 {
 978         int start, end, h;
 979 
 980         cp = id(cp, &h);
 981         if (*cp++ != ';')
 982                 expected("arraydef/1", ";", cp - 1);
 983 
 984         (*rtdp)->t_ardef = xcalloc(sizeof (ardef_t));
 985         (*rtdp)->t_ardef->ad_idxtype = lookup(h);
 986 
 987         cp = number(cp, &start); /* lower */
 988         if (*cp++ != ';')
 989                 expected("arraydef/2", ";", cp - 1);
 990 
 991         if (*cp == 'S') {
 992                 /*
 993                  * variable length array - treat as null dimensioned
 994                  *
 995                  * For VLA variables on sparc, SS12 generated stab entry
 996                  * looks as follows:
 997                  * .stabs "buf:(0,28)=zr(0,4);0;S-12;(0,1)", 0x80, 0, 0, -16
 998                  * Whereas SS12u1 generated stab entry looks like this:
 999                  * .stabs "buf:(0,28)=zr(0,4);0;S0;(0,1)", 0x80, 0, 0, 0
1000                  * On x86, both versions generate the first type of entry.
1001                  * We should be able to parse both.
1002                  */
1003                 cp++;
1004                 if (*cp == '-')
1005                         cp++;
1006                 cp = number(cp, &end);
1007                 end = start;
1008         } else {
1009                 /*
1010                  * normal fixed-dimension array
1011                  * Stab entry for this looks as follows :
1012                  * .stabs "x:(0,28)=ar(0,4);0;9;(0,3)", 0x80, 0, 40, 0
1013                  */
1014                 cp = number(cp, &end);  /* upper */
1015         }
1016 
1017         if (*cp++ != ';')
1018                 expected("arraydef/3", ";", cp - 1);
1019         (*rtdp)->t_ardef->ad_nelems = end - start + 1;
1020         cp = tdefdecl(cp, h, &((*rtdp)->t_ardef->ad_contents));
1021 
1022         parse_debug(3, cp, "defined array idx type %d %d-%d next ",
1023             h, start, end);
1024 
1025         return (cp);
1026 }
1027 
1028 static void
1029 enumdef(char *cp, tdesc_t **rtdp)
1030 {
1031         elist_t *elp, **prev;
1032         char *w;
1033 
1034         (*rtdp)->t_type = ENUM;
1035         (*rtdp)->t_emem = NULL;
1036 
1037         prev = &((*rtdp)->t_emem);
1038         while (*cp != ';') {
1039                 elp = xcalloc(sizeof (*elp));
1040                 elp->el_next = NULL;
1041                 *prev = elp;
1042                 cp = name(cp, &w);
1043                 elp->el_name = w;
1044                 cp = number(cp, &elp->el_number);
1045                 parse_debug(3, NULL, "enum %s: %s=%d", tdesc_name(*rtdp),
1046                     elp->el_name, elp->el_number);
1047                 prev = &elp->el_next;
1048                 if (*cp++ != ',')
1049                         expected("enumdef", ",", cp - 1);
1050         }
1051 }
1052 
1053 tdesc_t *
1054 lookup_name(tdesc_t **hash, const char *name)
1055 {
1056         int bucket = compute_sum(name);
1057         tdesc_t *tdp, *ttdp = NULL;
1058 
1059         for (tdp = hash[bucket]; tdp != NULL; tdp = tdp->t_next) {
1060                 if (tdp->t_name != NULL && strcmp(tdp->t_name, name) == 0) {
1061                         if (tdp->t_type == STRUCT || tdp->t_type == UNION ||
1062                             tdp->t_type == ENUM || tdp->t_type == INTRINSIC)
1063                                 return (tdp);
1064                         if (tdp->t_type == TYPEDEF)
1065                                 ttdp = tdp;
1066                 }
1067         }
1068         return (ttdp);
1069 }
1070 
1071 tdesc_t *
1072 lookupname(const char *name)
1073 {
1074         return (lookup_name(name_table, name));
1075 }
1076 
1077 /*
1078  * Add a node to the hash queues.
1079  */
1080 static void
1081 addhash(tdesc_t *tdp, int num)
1082 {
1083         int hash = HASH(num);
1084         tdesc_t *ttdp;
1085         char added_num = 0, added_name = 0;
1086 
1087         /*
1088          * If it already exists in the hash table don't add it again
1089          * (but still check to see if the name should be hashed).
1090          */
1091         ttdp = lookup(num);
1092 
1093         if (ttdp == NULL) {
1094                 tdp->t_id = num;
1095                 tdp->t_hash = hash_table[hash];
1096                 hash_table[hash] = tdp;
1097                 added_num = 1;
1098         }
1099 
1100         if (tdp->t_name != NULL) {
1101                 ttdp = lookupname(tdp->t_name);
1102                 if (ttdp == NULL) {
1103                         hash = compute_sum(tdp->t_name);
1104                         tdp->t_next = name_table[hash];
1105                         name_table[hash] = tdp;
1106                         added_name = 1;
1107                 }
1108         }
1109         if (!added_num && !added_name) {
1110                 terminate("stabs: broken hash\n");
1111         }
1112 }
1113 
1114 static int
1115 compute_sum(const char *w)
1116 {
1117         char c;
1118         int sum;
1119 
1120         for (sum = 0; (c = *w) != '\0'; sum += c, w++)
1121                 ;
1122         return (HASH(sum));
1123 }
1124 
1125 static void
1126 reset(void)
1127 {
1128         longjmp(resetbuf, 1);
1129 }
1130 
1131 void
1132 check_hash(void)
1133 {
1134         tdesc_t *tdp;
1135         int i;
1136 
1137         printf("checking hash\n");
1138         for (i = 0; i < BUCKETS; i++) {
1139                 if (hash_table[i]) {
1140                         for (tdp = hash_table[i]->t_hash;
1141                             tdp && tdp != hash_table[i];
1142                             tdp = tdp->t_hash)
1143                                 continue;
1144                         if (tdp) {
1145                                 terminate("cycle in hash bucket %d\n", i);
1146                                 return;
1147                         }
1148                 }
1149 
1150                 if (name_table[i]) {
1151                         for (tdp = name_table[i]->t_next;
1152                             tdp && tdp != name_table[i];
1153                             tdp = tdp->t_next)
1154                                 continue;
1155                         if (tdp) {
1156                                 terminate("cycle in name bucket %d\n", i);
1157                                 return;
1158                         }
1159                 }
1160         }
1161         printf("done\n");
1162 }
1163 
1164 /*ARGSUSED1*/
1165 static int
1166 resolve_typed_bitfields_cb(mlist_t *ml, void *private)
1167 {
1168         tdesc_t *tdp = ml->ml_type;
1169 
1170         debug(3, "Resolving typed bitfields (member %s)\n",
1171             (ml->ml_name ? ml->ml_name : "(anon)"));
1172 
1173         while (tdp) {
1174                 switch (tdp->t_type) {
1175                 case INTRINSIC:
1176                         if (ml->ml_size != tdp->t_intr->intr_nbits) {
1177                                 debug(3, "making %d bit intrinsic from %s",
1178                                     ml->ml_size, tdesc_name(tdp));
1179                                 ml->ml_type = bitintrinsic(tdp, ml->ml_size);
1180                         } else {
1181                                 debug(3, "using existing %d bit %s intrinsic",
1182                                     ml->ml_size, tdesc_name(tdp));
1183                                 ml->ml_type = tdp;
1184                         }
1185                         return (1);
1186 
1187                 case POINTER:
1188                 case TYPEDEF:
1189                 case VOLATILE:
1190                 case CONST:
1191                 case RESTRICT:
1192                         tdp = tdp->t_tdesc;
1193                         break;
1194 
1195                 default:
1196                         return (1);
1197                 }
1198         }
1199 
1200         terminate("type chain for bitfield member %s has a NULL", ml->ml_name);
1201         /*NOTREACHED*/
1202         return (0);
1203 }
1204 
1205 void
1206 resolve_typed_bitfields(void)
1207 {
1208         (void) list_iter(typedbitfldmems,
1209             (int (*)())resolve_typed_bitfields_cb, NULL);
1210 }