Annotation of gdb/valprint.c, revision 1.1.1.3

1.1       root        1: /* Print values for GNU debugger gdb.
                      2:    Copyright (C) 1986 Free Software Foundation, Inc.
                      3: 
                      4: GDB is distributed in the hope that it will be useful, but WITHOUT ANY
                      5: WARRANTY.  No author or distributor accepts responsibility to anyone
                      6: for the consequences of using it or for whether it serves any
                      7: particular purpose or works at all, unless he says so in writing.
                      8: Refer to the GDB General Public License for full details.
                      9: 
                     10: Everyone is granted permission to copy, modify and redistribute GDB,
                     11: but only under the conditions described in the GDB General Public
                     12: License.  A copy of this license is supposed to have been given to you
                     13: along with GDB so you can know your rights and responsibilities.  It
                     14: should be in a file named COPYING.  Among other things, the copyright
                     15: notice and this notice must be preserved on all copies.
                     16: 
                     17: In other words, go ahead and share GDB, but don't try to stop
                     18: anyone else from sharing it farther.  Help stamp out software hoarding!
                     19: */
                     20: 
                     21: #include <stdio.h>
                     22: #include "defs.h"
                     23: #include "initialize.h"
                     24: #include "symtab.h"
                     25: #include "value.h"
                     26: 
                     27: /* Maximum number of chars to print for a string pointer value
                     28:    or vector contents.  */
                     29: 
                     30: static int print_max;
                     31: 
                     32: static void type_print_varspec_suffix ();
                     33: static void type_print_varspec_prefix ();
                     34: static void type_print_base ();
1.1.1.3 ! root       35: static void type_print_method_args ();
1.1       root       36: 
                     37: START_FILE
                     38: 
                     39: char **unsigned_type_table;
                     40: char **signed_type_table;
                     41: char **float_type_table;
                     42: 
                     43: /* Print the value VAL in C-ish syntax on stream STREAM.
                     44:    If the object printed is a string pointer, returns
                     45:    the number of string bytes printed.  */
                     46: 
                     47: value_print (val, stream)
                     48:      value val;
                     49:      FILE *stream;
                     50: {
                     51:   register int i, n, typelen;
                     52: 
                     53:   /* A "repeated" value really contains several values in a row.
                     54:      They are made by the @ operator.
                     55:      Print such values as if they were arrays.  */
                     56: 
                     57:   if (VALUE_REPEATED (val))
                     58:     {
                     59:       n = VALUE_REPETITIONS (val);
                     60:       typelen = TYPE_LENGTH (VALUE_TYPE (val));
                     61:       fputc ('{', stream);
                     62:       /* Print arrays of characters using string syntax.  */
                     63:       if (VALUE_TYPE (val) == builtin_type_char
                     64:          || VALUE_TYPE (val) == builtin_type_unsigned_char)
                     65:        {
                     66:          fputc ('"', stream);
                     67:          for (i = 0; i < n && i < print_max; i++)
                     68:            {
                     69:              QUIT;
                     70:              printchar (VALUE_CONTENTS (val)[i], stream);
                     71:            }
                     72:          if (i < n)
                     73:            fprintf (stream, "...");
                     74:          fputc ('"', stream);
                     75:        }
                     76:       else
                     77:        {
                     78:          for (i = 0; i < n && i < print_max; i++)
                     79:            {
                     80:              if (i)
                     81:                fprintf (stream, ", ");
                     82:              val_print (VALUE_TYPE (val), VALUE_CONTENTS (val) + typelen * i,
                     83:                         VALUE_ADDRESS (val) + typelen * i, stream);
                     84:            }
                     85:          if (i < n)
                     86:            fprintf (stream, "...");
                     87:        }
                     88:       fputc ('}', stream);
                     89:     }
                     90:   else
                     91:     {
1.1.1.3 ! root       92:       /* If it is a pointer, indicate what it points to.
        !            93: 
        !            94:          C++: if it is a member pointer, we will take care
        !            95:         of that when we print it.  */
1.1       root       96:       if (TYPE_CODE (VALUE_TYPE (val)) == TYPE_CODE_PTR)
                     97:        {
                     98:          fprintf (stream, "(");
                     99:          type_print (VALUE_TYPE (val), "", stream, -1);
                    100:          fprintf (stream, ") ");
                    101:        }
                    102:       return val_print (VALUE_TYPE (val), VALUE_CONTENTS (val),
                    103:                        VALUE_ADDRESS (val), stream);
                    104:     }
                    105: }
                    106: 
                    107: /* Print on STREAM data stored in debugger at address VALADDR
                    108:    according to the format of type TYPE.
                    109:    ADDRESS is the location in the inferior that the data
                    110:    is supposed to have come from.
                    111: 
                    112:    If the data are a string pointer, returns the number of
                    113:    sting characters printed.  */
                    114: 
                    115: int
                    116: val_print (type, valaddr, address, stream)
                    117:      struct type *type;
                    118:      char *valaddr;
                    119:      CORE_ADDR address;
                    120:      FILE *stream;
                    121: {
                    122:   register int i;
                    123:   int len;
                    124:   struct type *elttype;
                    125:   int eltlen;
                    126:   int val;
                    127:   unsigned char c;
                    128: 
                    129:   QUIT;
                    130: 
                    131:   switch (TYPE_CODE (type))
                    132:     {
                    133:     case TYPE_CODE_ARRAY:
                    134:       if (TYPE_LENGTH (type) >= 0)
                    135:        {
                    136:          elttype = TYPE_TARGET_TYPE (type);
                    137:          eltlen = TYPE_LENGTH (elttype);
                    138:          len = TYPE_LENGTH (type) / eltlen;
                    139:          fprintf (stream, "{");
                    140:          /* For an array of chars, print with string syntax.  */
                    141:          if (elttype == builtin_type_char
                    142:              || elttype == builtin_type_unsigned_char)
                    143:            {
                    144:              fputc ('"', stream);
                    145:              for (i = 0; i < len && i < print_max; i++)
                    146:                {
                    147:                  QUIT;
                    148:                  printchar (valaddr[i], stream);
                    149:                }
                    150:              if (i < len)
                    151:                fprintf (stream, "...");
                    152:              fputc ('"', stream);
                    153:            }
                    154:          else
                    155:            {
                    156:              for (i = 0; i < len && i < print_max; i++)
                    157:                {
                    158:                  if (i) fprintf (stream, ", ");
                    159:                  val_print (elttype, valaddr + i * eltlen,
                    160:                             0, stream);
                    161:                }
                    162:              if (i < len)
                    163:                fprintf (stream, "...");
                    164:            }
                    165:          fprintf (stream, "}");
                    166:          break;
                    167:        }
                    168:       /* Array of unspecified length: treat like pointer.  */
                    169: 
                    170:     case TYPE_CODE_PTR:
                    171:       fprintf (stream, "0x%x", * (int *) valaddr);
                    172:       /* For a pointer to char or unsigned char,
                    173:         also print the string pointed to, unless pointer is null.  */
                    174:       if ((TYPE_TARGET_TYPE (type) == builtin_type_char
                    175:           || TYPE_TARGET_TYPE (type) == builtin_type_unsigned_char)
                    176:          && unpack_long (type, valaddr) != 0)
                    177:        {
                    178:          fputc (' ', stream);
                    179:          fputc ('"', stream);
                    180:          for (i = 0; i < print_max; i++)
                    181:            {
                    182:              QUIT;
                    183:              read_memory (unpack_long (type, valaddr) + i, &c, 1);
                    184:              if (c == 0)
                    185:                break;
                    186:              printchar (c, stream);
                    187:            }
                    188:          fputc ('"', stream);
                    189:          if (i == print_max)
                    190:            fprintf (stream, "...");
                    191:          fflush (stream);
                    192:          /* Return number of characters printed, plus one for the
                    193:             terminating null if we have "reached the end".  */
                    194:          return i + (i != print_max);
                    195:        }
                    196:       break;
                    197: 
1.1.1.3 ! root      198:     case TYPE_CODE_MPTR:
        !           199:       {
        !           200:        struct type *domain = TYPE_DOMAIN_TYPE (type);
        !           201:        struct type *target = TYPE_TARGET_TYPE (type);
        !           202:        struct fn_field *f;
        !           203:        int j, len2;
        !           204:        char *kind = "";
        !           205: 
        !           206:        val = unpack_long (builtin_type_int, valaddr);
        !           207:        if (TYPE_CODE (target) == TYPE_CODE_FUNC)
        !           208:          {
        !           209:            if (val < 128)
        !           210:              {
        !           211:                len = TYPE_NFN_FIELDS (domain);
        !           212:                for (i = 0; i < len; i++)
        !           213:                  {
        !           214:                    f = TYPE_FN_FIELDLIST1 (domain, i);
        !           215:                    len2 = TYPE_FN_FIELDLIST_LENGTH (domain, i);
        !           216: 
        !           217:                    for (j = 0; j < len2; j++)
        !           218:                      {
        !           219:                        QUIT;
        !           220:                        if (TYPE_FN_FIELD_VOFFSET (f, j) == val)
        !           221:                          {
        !           222:                            kind = " virtual";
        !           223:                            goto common;
        !           224:                          }
        !           225:                      }
        !           226:                  }
        !           227:              }
        !           228:            else
        !           229:              {
        !           230:                struct symbol *sym = find_pc_function (val);
        !           231:                if (sym == 0)
        !           232:                  error ("invalid pointer to member function");
        !           233:                len = TYPE_NFN_FIELDS (domain);
        !           234:                for (i = 0; i < len; i++)
        !           235:                  {
        !           236:                    f = TYPE_FN_FIELDLIST1 (domain, i);
        !           237:                    len2 = TYPE_FN_FIELDLIST_LENGTH (domain, i);
        !           238: 
        !           239:                    for (j = 0; j < len2; j++)
        !           240:                      {
        !           241:                        QUIT;
        !           242:                        if (!strcmp (SYMBOL_NAME (sym), TYPE_FN_FIELD_PHYSNAME (f, j)))
        !           243:                          goto common;
        !           244:                      }
        !           245:                  }
        !           246:              }
        !           247:          common:
        !           248:            if (i < len)
        !           249:              {
        !           250:                fprintf (stream, "& ");
        !           251:                type_print_base (domain, stream, 0, 0);
        !           252:                fprintf (stream, "::%s", kind);
        !           253:                type_print_varspec_prefix (TYPE_FN_FIELD_TYPE (f, j), stream, 0, 0);
        !           254:                if (TYPE_FN_FIELD_PHYSNAME (f, j)[0] == '_'
        !           255:                    && TYPE_FN_FIELD_PHYSNAME (f, j)[1] == '$')
        !           256:                  type_print_method_args
        !           257:                    (TYPE_FN_FIELD_ARGS (f, j) + 1, "~",
        !           258:                     TYPE_FN_FIELDLIST_NAME (domain, i), stream);
        !           259:                else
        !           260:                  type_print_method_args
        !           261:                    (TYPE_FN_FIELD_ARGS (f, j), "",
        !           262:                     TYPE_FN_FIELDLIST_NAME (domain, i), stream);
        !           263:                break;
        !           264:              }
        !           265:          }
        !           266:        else
        !           267:          {
        !           268:            /* VAL is a byte offset into the structure type DOMAIN.
        !           269:               Find the name of the field for that offset and
        !           270:               print it.  */
        !           271:            int extra = 0;
        !           272:            int bits = 0;
        !           273:            len = TYPE_NFIELDS (domain);
        !           274:            val <<= 3;          /* @@ Make VAL into bit offset */
        !           275:            for (i = 0; i < len; i++)
        !           276:              {
        !           277:                int bitpos = TYPE_FIELD_BITPOS (domain, i);
        !           278:                QUIT;
        !           279:                if (val == bitpos)
        !           280:                  break;
        !           281:                if (val < bitpos && i > 0)
        !           282:                  {
        !           283:                    int ptrsize = (TYPE_LENGTH (builtin_type_char) * TYPE_LENGTH (target));
        !           284:                    /* Somehow pointing into a field.  */
        !           285:                    i -= 1;
        !           286:                    extra = (val - TYPE_FIELD_BITPOS (domain, i));
        !           287:                    if (extra & 0x3)
        !           288:                      bits = 1;
        !           289:                    else
        !           290:                      extra >>= 3;
        !           291:                    break;
        !           292:                  }
        !           293:              }
        !           294:            if (i < len)
        !           295:              {
        !           296:                fprintf (stream, "& ");
        !           297:                type_print_base (domain, stream, 0, 0);
        !           298:                fprintf (stream, "::");
        !           299:                fprintf (stream, "%s", TYPE_FIELD_NAME (domain, i));
        !           300:                if (extra)
        !           301:                  fprintf (stream, " + %d bytes", extra);
        !           302:                if (bits)
        !           303:                  fprintf (stream, " (offset in bits)");
        !           304:                break;
        !           305:              }
        !           306:          }
        !           307:        fputc ('(', stream);
        !           308:        type_print (type, "", stream, -1);
        !           309:        fprintf (stream, ") %d", val >> 3);
        !           310:        break;
        !           311:       }
        !           312: 
        !           313:     case TYPE_CODE_REF:
        !           314:       fprintf (stream, "(0x%x &) = ", * (int *) valaddr);
        !           315:       /* De-reference the reference.  */
        !           316:       if (TYPE_CODE (TYPE_TARGET_TYPE (type)) != TYPE_CODE_UNDEF)
        !           317:        {
        !           318:          value val = value_at (TYPE_TARGET_TYPE (type), * (int *)valaddr);
        !           319:          val_print (VALUE_TYPE (val), VALUE_CONTENTS (val),
        !           320:                     VALUE_ADDRESS (val), stream);
        !           321:        }
        !           322:       else
        !           323:        fprintf (stream, "???");
        !           324:       break;
        !           325: 
1.1       root      326:     case TYPE_CODE_STRUCT:
                    327:     case TYPE_CODE_UNION:
                    328:       fprintf (stream, "{");
                    329:       len = TYPE_NFIELDS (type);
1.1.1.3 ! root      330:       if (TYPE_BASECLASS (type))
        !           331:        {
        !           332:          i = 1;
        !           333:          fprintf (stream, "<%s> = ", TYPE_NAME (TYPE_BASECLASS (type)));
        !           334:          val_print (TYPE_FIELD_TYPE (type, 0),
        !           335:                     valaddr + TYPE_FIELD_BITPOS (type, 0) / 8,
        !           336:                     0, stream);
        !           337: 
        !           338:        }
        !           339:       else i = 0;
        !           340:       for (; i < len; i++)
1.1       root      341:        {
                    342:          if (i) fprintf (stream, ", ");
                    343:          fprintf (stream, "%s = ", TYPE_FIELD_NAME (type, i));
1.1.1.3 ! root      344:          /* check if static field */
        !           345:          if (TYPE_FIELD_STATIC (type, i))
        !           346:            {
        !           347:              value v;
        !           348: 
        !           349:              v = value_static_field (type, TYPE_FIELD_NAME (type, i), i);
        !           350:              val_print (TYPE_FIELD_TYPE (type, i),
        !           351:                         VALUE_CONTENTS (v), 0, stream);
        !           352:            }
        !           353:          else if (TYPE_FIELD_PACKED (type, i))
1.1       root      354:            {
                    355:              val = unpack_field_as_long (type, valaddr, i);
                    356:              val_print (TYPE_FIELD_TYPE (type, i), &val, 0, stream);
                    357:            }
                    358:          else
1.1.1.3 ! root      359:            {
        !           360:              val_print (TYPE_FIELD_TYPE (type, i), 
        !           361:                         valaddr + TYPE_FIELD_BITPOS (type, i) / 8,
        !           362:                         0, stream);
        !           363:            }
1.1       root      364:        }
                    365:       fprintf (stream, "}");
                    366:       break;
                    367: 
                    368:     case TYPE_CODE_ENUM:
                    369:       len = TYPE_NFIELDS (type);
                    370:       val = unpack_long (builtin_type_int, valaddr);
                    371:       for (i = 0; i < len; i++)
                    372:        {
                    373:          QUIT;
                    374:          if (val == TYPE_FIELD_VALUE (type, i))
                    375:            break;
                    376:        }
                    377:       if (i < len)
                    378:        fprintf (stream, "%s", TYPE_FIELD_NAME (type, i));
                    379:       else
                    380:        fprintf (stream, "%d", val);
                    381:       break;
                    382: 
                    383:     case TYPE_CODE_FUNC:
                    384:       fprintf (stream, "{");
                    385:       type_print (type, "", stream, -1);
                    386:       fprintf (stream, "} ");
                    387:       fprintf (stream, "0x%x", address);
                    388:       break;
                    389: 
                    390:     case TYPE_CODE_INT:
                    391:       fprintf (stream,
                    392:               TYPE_UNSIGNED (type) ? "%u" : "%d",
                    393:               unpack_long (type, valaddr));
                    394:       if (type == builtin_type_char
                    395:          || type == builtin_type_unsigned_char)
                    396:        {
                    397:          fprintf (stream, " '");
                    398:          printchar (unpack_long (type, valaddr), stream);
                    399:          fputc ('\'', stream);
                    400:        }
                    401:       break;
                    402: 
                    403:     case TYPE_CODE_FLT:
1.1.1.2   root      404: #ifdef IEEE_FLOAT
                    405:       if (is_nan (unpack_double (type, valaddr)))
                    406:        {
                    407:          fprintf (stream, "Nan");
                    408:          break;
                    409:        }
                    410: #endif
1.1       root      411:       fprintf (stream, "%g", unpack_double (type, valaddr));
                    412:       break;
                    413: 
                    414:     case TYPE_CODE_VOID:
                    415:       fprintf (stream, "void");
                    416:       break;
                    417: 
                    418:     default:
                    419:       error ("Invalid type code in symbol table.");
                    420:     }
                    421:   fflush (stream);
                    422: }
                    423: 
1.1.1.2   root      424: #ifdef IEEE_FLOAT
                    425: 
                    426: union ieee {
                    427:   int i[2];
                    428:   double d;
                    429: };
                    430: 
                    431: /* Nonzero if ARG (a double) is a NAN.  */
                    432: 
                    433: int
                    434: is_nan (arg)
                    435:      union ieee arg;
                    436: {
                    437:   int lowhalf, highhalf;
                    438:   union { int i; char c; } test;
                    439: 
                    440:   /* Separate the high and low words of the double.
                    441:      Distinguish big and little-endian machines.  */
                    442:   test.i = 1;
                    443:   if (test.c != 1)
                    444:     /* Big-endian machine */
                    445:     lowhalf = arg.i[1], highhalf = arg.i[0];
                    446:   else
                    447:     lowhalf = arg.i[0], highhalf = arg.i[1];
                    448: 
                    449:   /* Nan: exponent is the maximum possible, and fraction is nonzero.  */
                    450:   return (((highhalf>>20) & 0x7ff) == 0x7ff
                    451:          &&
                    452:          ! ((highhalf & 0xfffff == 0) && (lowhalf == 0)));
                    453: }
                    454: #endif
                    455: 
1.1       root      456: /* Print a description of a type TYPE
                    457:    in the form of a declaration of a variable named VARSTRING.
                    458:    Output goes to STREAM (via stdio).
                    459:    If SHOW is positive, we show the contents of the outermost level
                    460:    of structure even if there is a type name that could be used instead.
                    461:    If SHOW is negative, we never show the details of elements' types.  */
                    462: 
                    463: type_print (type, varstring, stream, show)
                    464:      struct type *type;
                    465:      char *varstring;
                    466:      FILE *stream;
                    467:      int show;
                    468: {
                    469:   type_print_1 (type, varstring, stream, show, 0);
                    470: }
                    471: 
                    472: /* LEVEL is the depth to indent lines by.  */
                    473: 
                    474: type_print_1 (type, varstring, stream, show, level)
                    475:      struct type *type;
                    476:      char *varstring;
                    477:      FILE *stream;
                    478:      int show;
                    479:      int level;
                    480: {
                    481:   register enum type_code code;
                    482:   type_print_base (type, stream, show, level);
                    483:   code = TYPE_CODE (type);
                    484:   if ((varstring && *varstring)
                    485:       ||
                    486:       /* Need a space if going to print stars or brackets;
                    487:         but not if we will print just a type name.  */
                    488:       ((show > 0 || TYPE_NAME (type) == 0)
                    489:        &&
                    490:        (code == TYPE_CODE_PTR || code == TYPE_CODE_FUNC
1.1.1.3 ! root      491:        || code == TYPE_CODE_ARRAY
        !           492:        || code == TYPE_CODE_MPTR
        !           493:        || code == TYPE_CODE_REF)))
1.1       root      494:     fprintf (stream, " ");
                    495:   type_print_varspec_prefix (type, stream, show, 0);
                    496:   fprintf (stream, "%s", varstring);
                    497:   type_print_varspec_suffix (type, stream, show, 0);
                    498: }
                    499: 
1.1.1.3 ! root      500: /* Print the method arguments ARGS to the file STREAM.  */
        !           501: static void
        !           502: type_print_method_args (args, prefix, varstring, stream)
        !           503:      struct type **args;
        !           504:      char *prefix, *varstring;
        !           505:      FILE *stream;
        !           506: {
        !           507:   int i;
        !           508: 
        !           509:   fprintf (stream, " %s%s (", prefix, varstring);
        !           510:   if (args[1] && args[1]->code != TYPE_CODE_VOID)
        !           511:     {
        !           512:       i = 1;                   /* skip the class variable */
        !           513:       while (1)
        !           514:        {
        !           515:          type_print (args[i++], "", stream, 0);
        !           516:          if (args[i]->code != TYPE_CODE_VOID)
        !           517:            {
        !           518:              fprintf (stream, ", ");
        !           519:            }
        !           520:          else break;
        !           521:        }
        !           522:     }
        !           523:   fprintf (stream, ")");
        !           524: }
        !           525:   
1.1       root      526: /* Print any asterisks or open-parentheses needed before the
                    527:    variable name (to describe its type).
                    528: 
                    529:    On outermost call, pass 0 for PASSED_A_PTR.
                    530:    On outermost call, SHOW > 0 means should ignore
                    531:    any typename for TYPE and show its details.
                    532:    SHOW is always zero on recursive calls.  */
                    533: 
                    534: static void
                    535: type_print_varspec_prefix (type, stream, show, passed_a_ptr)
                    536:      struct type *type;
                    537:      FILE *stream;
                    538:      int show;
                    539:      int passed_a_ptr;
                    540: {
                    541:   if (TYPE_NAME (type) && show <= 0)
                    542:     return;
                    543: 
                    544:   QUIT;
                    545: 
                    546:   switch (TYPE_CODE (type))
                    547:     {
                    548:     case TYPE_CODE_PTR:
                    549:       type_print_varspec_prefix (TYPE_TARGET_TYPE (type), stream, 0, 1);
                    550:       fputc ('*', stream);
                    551:       break;
                    552: 
1.1.1.3 ! root      553:     case TYPE_CODE_MPTR:
        !           554:       type_print_varspec_prefix (TYPE_TARGET_TYPE (type), stream, 0, 1);
        !           555:       if (passed_a_ptr)
        !           556:        fputc ('(', stream);
        !           557:       type_print_base (TYPE_DOMAIN_TYPE (type), stream, 0, 1);
        !           558:       fprintf (stream, "::*");
        !           559:       break;
        !           560: 
        !           561:     case TYPE_CODE_REF:
        !           562:       type_print_varspec_prefix (TYPE_TARGET_TYPE (type), stream, 0, 1);
        !           563:       fputc ('&', stream);
        !           564:       break;
        !           565: 
1.1       root      566:     case TYPE_CODE_FUNC:
1.1.1.3 ! root      567:       type_print_varspec_prefix (TYPE_TARGET_TYPE (type), stream, 0,
        !           568:                                 passed_a_ptr);
1.1       root      569:       if (passed_a_ptr)
                    570:        fputc ('(', stream);
                    571:       break;
1.1.1.3 ! root      572: 
        !           573:     case TYPE_CODE_ARRAY:
        !           574:       type_print_varspec_prefix (TYPE_TARGET_TYPE (type), stream, 0,
        !           575:                                 passed_a_ptr);
1.1       root      576:     }
                    577: }
                    578: 
                    579: /* Print any array sizes, function arguments or close parentheses
                    580:    needed after the variable name (to describe its type).
                    581:    Args work like type_print_varspec_prefix.  */
                    582: 
                    583: static void
                    584: type_print_varspec_suffix (type, stream, show, passed_a_ptr)
                    585:      struct type *type;
                    586:      FILE *stream;
                    587:      int show;
                    588:      int passed_a_ptr;
                    589: {
                    590:   if (TYPE_NAME (type) && show <= 0)
                    591:     return;
                    592: 
                    593:   QUIT;
                    594: 
                    595:   switch (TYPE_CODE (type))
                    596:     {
                    597:     case TYPE_CODE_ARRAY:
1.1.1.3 ! root      598:       type_print_varspec_suffix (TYPE_TARGET_TYPE (type), stream, 0,
        !           599:                                 passed_a_ptr);
1.1       root      600:       fprintf (stream, "[");
                    601:       if (TYPE_LENGTH (type) >= 0)
                    602:        fprintf (stream, "%d",
                    603:                 TYPE_LENGTH (type) / TYPE_LENGTH (TYPE_TARGET_TYPE (type)));
                    604:       fprintf (stream, "]");
                    605:       break;
                    606: 
1.1.1.3 ! root      607:     case TYPE_CODE_MPTR:
        !           608:       if (passed_a_ptr)
        !           609:        fputc (')', stream);
        !           610:       /* Fall through.  */
1.1       root      611:     case TYPE_CODE_PTR:
1.1.1.3 ! root      612:     case TYPE_CODE_REF:
1.1       root      613:       type_print_varspec_suffix (TYPE_TARGET_TYPE (type), stream, 0, 1);
                    614:       break;
                    615: 
                    616:     case TYPE_CODE_FUNC:
1.1.1.3 ! root      617:       type_print_varspec_suffix (TYPE_TARGET_TYPE (type), stream, 0,
        !           618:                                 passed_a_ptr);
1.1       root      619:       if (passed_a_ptr)
                    620:        fprintf (stream, ")");
                    621:       fprintf (stream, "()");
                    622:       break;
                    623:     }
                    624: }
                    625: 
                    626: /* Print the name of the type (or the ultimate pointer target,
                    627:    function value or array element), or the description of a
                    628:    structure or union.
                    629: 
                    630:    SHOW nonzero means don't print this type as just its name;
                    631:    show its real definition even if it has a name.
                    632:    SHOW zero means print just typename or struct tag if there is one
                    633:    SHOW negative means abbreviate structure elements.
                    634:    SHOW is decremented for printing of structure elements.
                    635: 
                    636:    LEVEL is the depth to indent by.
                    637:    We increase it for some recursive calls.  */
                    638: 
                    639: static void
                    640: type_print_base (type, stream, show, level)
                    641:      struct type *type;
                    642:      FILE *stream;
                    643:      int show;
                    644:      int level;
                    645: {
                    646:   char *name;
                    647:   register int i;
                    648:   register int len;
                    649:   register int lastval;
                    650: 
                    651:   QUIT;
                    652: 
                    653:   if (TYPE_NAME (type) && show <= 0)
                    654:     {
                    655:       fprintf (stream, TYPE_NAME (type));
                    656:       return;
                    657:     }
                    658: 
                    659:   switch (TYPE_CODE (type))
                    660:     {
                    661:     case TYPE_CODE_ARRAY:
                    662:     case TYPE_CODE_PTR:
1.1.1.3 ! root      663:     case TYPE_CODE_MPTR:
        !           664:     case TYPE_CODE_REF:
1.1       root      665:     case TYPE_CODE_FUNC:
                    666:       type_print_base (TYPE_TARGET_TYPE (type), stream, show, level);
                    667:       break;
                    668: 
                    669:     case TYPE_CODE_STRUCT:
                    670:       fprintf (stream, "struct ");
                    671:       goto struct_union;
                    672: 
                    673:     case TYPE_CODE_UNION:
                    674:       fprintf (stream, "union ");
                    675:     struct_union:
                    676:       if (TYPE_NAME (type) && (name = TYPE_NAME (type)))
                    677:        {
                    678:          while (*name != ' ') name++;
                    679:          fprintf (stream, "%s ", name + 1);
                    680:        }
                    681:       if (show < 0)
                    682:        fprintf (stream, "{...}");
                    683:       else
                    684:        {
1.1.1.3 ! root      685:          struct type *basetype, *dtype;
        !           686: 
        !           687:          dtype = type;
        !           688:          basetype = TYPE_BASECLASS (type);
        !           689:          while (basetype)
        !           690:            {
        !           691:              if (TYPE_NAME (basetype) && (name = TYPE_NAME (basetype)))
        !           692:                {
        !           693:                  while (*name != ' ') name++;
        !           694:                  fprintf (stream, ": %s %s ",
        !           695:                           TYPE_VIA_PUBLIC (dtype) ? "public" : "private",
        !           696:                           name + 1);
        !           697:                }
        !           698:              dtype = basetype;
        !           699:              basetype = TYPE_BASECLASS (basetype);
        !           700:            }
1.1       root      701:          fprintf (stream, "{");
                    702:          len = TYPE_NFIELDS (type);
1.1.1.3 ! root      703:          if (len) fprintf (stream, "\n");
        !           704:          else fprintf (stream, "<no data fields>\n");
        !           705: 
        !           706:          /* If there is a base class for this type,
        !           707:             do not print the field that it occupies.  */
        !           708:          for (i = !! TYPE_BASECLASS (type); i < len; i++)
1.1       root      709:            {
                    710:              QUIT;
1.1.1.3 ! root      711:              /* Don't print out virtual function table.  */
        !           712:              if (! strncmp (TYPE_FIELD_NAME (type, i),
        !           713:                           "_vptr$", 6))
        !           714:                continue;
1.1.1.2   root      715: 
1.1.1.3 ! root      716:              print_spaces (level + 4, stream);
        !           717:              if (TYPE_FIELD_STATIC (type, i))
1.1.1.2   root      718:                {
1.1.1.3 ! root      719:                  fprintf (stream, "static ");
1.1.1.2   root      720:                }
1.1       root      721:              type_print_1 (TYPE_FIELD_TYPE (type, i),
                    722:                            TYPE_FIELD_NAME (type, i),
                    723:                            stream, show - 1, level + 4);
1.1.1.3 ! root      724:              if (!TYPE_FIELD_STATIC (type, i)
        !           725:                  && TYPE_FIELD_PACKED (type, i))
        !           726:                {
        !           727:                  /* ??? don't know what to put here ??? */;
        !           728:                }
        !           729:              fprintf (stream, ";\n");
        !           730:            }
1.1.1.2   root      731: 
1.1.1.3 ! root      732:          /* C++: print out the methods */
        !           733:          len = TYPE_NFN_FIELDS (type);
        !           734:          if (len) fprintf (stream, "\n");
        !           735:          for (i = 0; i < len; i++)
        !           736:            {
        !           737:              struct fn_field *f = TYPE_FN_FIELDLIST1 (type, i);
        !           738:              int j, len2 = TYPE_FN_FIELDLIST_LENGTH (type, i);
1.1.1.2   root      739: 
1.1.1.3 ! root      740:              for (j = 0; j < len2; j++)
        !           741:                {
        !           742:                  QUIT;
        !           743:                  print_spaces (level + 4, stream);
        !           744:                  if (TYPE_FN_FIELD_VIRTUAL_P (f, j))
        !           745:                    fprintf (stream, "virtual ");
        !           746:                  type_print_base (TYPE_FN_FIELD_TYPE (f, j), stream, 0, level);
        !           747:                  type_print_varspec_prefix (TYPE_FN_FIELD_TYPE (f, j), stream, 0, 0);
        !           748:                  if (TYPE_FN_FIELD_PHYSNAME (f, j)[0] == '_'
        !           749:                      && TYPE_FN_FIELD_PHYSNAME (f, j)[1] == '$')
        !           750:                    type_print_method_args
        !           751:                      (TYPE_FN_FIELD_ARGS (f, j) + 1, "~",
        !           752:                       TYPE_FN_FIELDLIST_NAME (type, i), stream);
        !           753:                  else
        !           754:                    type_print_method_args
        !           755:                      (TYPE_FN_FIELD_ARGS (f, j), "",
        !           756:                       TYPE_FN_FIELDLIST_NAME (type, i), stream);
1.1.1.2   root      757: 
1.1.1.3 ! root      758:                  fprintf (stream, ";\n");
        !           759:                }
        !           760:              if (len2) fprintf (stream, "\n");
1.1       root      761:            }
1.1.1.3 ! root      762: 
1.1       root      763:          print_spaces (level, stream);
                    764:          fputc ('}', stream);
                    765:        }
                    766:       break;
                    767: 
                    768:     case TYPE_CODE_ENUM:
                    769:       fprintf (stream, "enum ");
                    770:       if (TYPE_NAME (type))
                    771:        {
                    772:          name = TYPE_NAME (type);
                    773:          while (*name != ' ') name++;
                    774:          fprintf (stream, "%s ", name + 1);
                    775:        }
                    776:       if (show < 0)
                    777:        fprintf (stream, "{...}");
                    778:       else
                    779:        {
                    780:          fprintf (stream, "{");
                    781:          len = TYPE_NFIELDS (type);
                    782:          lastval = 0;
                    783:          for (i = 0; i < len; i++)
                    784:            {
                    785:              QUIT;
                    786:              if (i) fprintf (stream, ", ");
                    787:              fprintf (stream, "%s", TYPE_FIELD_NAME (type, i));
                    788:              if (lastval != TYPE_FIELD_VALUE (type, i))
                    789:                {
                    790:                  fprintf (stream, " : %d", TYPE_FIELD_VALUE (type, i));
                    791:                  lastval = TYPE_FIELD_VALUE (type, i);
                    792:                }
                    793:              lastval++;
                    794:            }
                    795:          fprintf (stream, "}");
                    796:        }
                    797:       break;
                    798: 
                    799:     case TYPE_CODE_INT:
                    800:       if (TYPE_UNSIGNED (type))
                    801:        name = unsigned_type_table[TYPE_LENGTH (type)];
                    802:       else
                    803:        name = signed_type_table[TYPE_LENGTH (type)];
                    804:       fprintf (stream, "%s", name);
                    805:       break;
                    806: 
                    807:     case TYPE_CODE_FLT:
                    808:       name = float_type_table[TYPE_LENGTH (type)];
                    809:       fprintf (stream, "%s", name);
                    810:       break;
                    811: 
                    812:     case TYPE_CODE_VOID:
                    813:       fprintf (stream, "void");
                    814:       break;
                    815: 
                    816:     case 0:
                    817:       fprintf (stream, "struct unknown");
                    818:       break;
                    819: 
                    820:     default:
                    821:       error ("Invalid type code in symbol table.");
                    822:     }
                    823: }
                    824: 
                    825: static void
                    826: set_maximum_command (arg)
                    827:      char *arg;
                    828: {
                    829:   if (!arg) error_no_arg ("value for maximum elements to print");
                    830:   print_max = atoi (arg);
                    831: }
                    832: 
                    833: static
                    834: initialize ()
                    835: {
                    836:   add_com ("set-maximum", class_vars, set_maximum_command,
                    837:           "Set NUMBER as limit on string chars or array elements to print.");
                    838: 
                    839:   print_max = 200;
                    840: 
                    841:   unsigned_type_table
                    842:     = (char **) xmalloc ((1 + sizeof (unsigned long)) * sizeof (char *));
                    843:   bzero (unsigned_type_table, (1 + sizeof (unsigned long)));
                    844:   unsigned_type_table[sizeof (unsigned char)] = "unsigned char";
                    845:   unsigned_type_table[sizeof (unsigned short)] = "unsigned short";
                    846:   unsigned_type_table[sizeof (unsigned long)] = "unsigned long";
                    847:   unsigned_type_table[sizeof (unsigned int)] = "unsigned int";
                    848: 
                    849:   signed_type_table
                    850:     = (char **) xmalloc ((1 + sizeof (long)) * sizeof (char *));
                    851:   bzero (signed_type_table, (1 + sizeof (long)));
                    852:   signed_type_table[sizeof (char)] = "char";
                    853:   signed_type_table[sizeof (short)] = "short";
                    854:   signed_type_table[sizeof (long)] = "long";
                    855:   signed_type_table[sizeof (int)] = "int";
                    856: 
                    857:   float_type_table
                    858:     = (char **) xmalloc ((1 + sizeof (double)) * sizeof (char *));
                    859:   bzero (float_type_table, (1 + sizeof (double)));
                    860:   float_type_table[sizeof (float)] = "float";
                    861:   float_type_table[sizeof (double)] = "double";
                    862: }
                    863: 
                    864: END_FILE

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.