1*a9fa9459Szrj /* wrstabs.c -- Output stabs debugging information 2*a9fa9459Szrj Copyright (C) 1996-2016 Free Software Foundation, Inc. 3*a9fa9459Szrj Written by Ian Lance Taylor <ian@cygnus.com>. 4*a9fa9459Szrj 5*a9fa9459Szrj This file is part of GNU Binutils. 6*a9fa9459Szrj 7*a9fa9459Szrj This program is free software; you can redistribute it and/or modify 8*a9fa9459Szrj it under the terms of the GNU General Public License as published by 9*a9fa9459Szrj the Free Software Foundation; either version 3 of the License, or 10*a9fa9459Szrj (at your option) any later version. 11*a9fa9459Szrj 12*a9fa9459Szrj This program is distributed in the hope that it will be useful, 13*a9fa9459Szrj but WITHOUT ANY WARRANTY; without even the implied warranty of 14*a9fa9459Szrj MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 15*a9fa9459Szrj GNU General Public License for more details. 16*a9fa9459Szrj 17*a9fa9459Szrj You should have received a copy of the GNU General Public License 18*a9fa9459Szrj along with this program; if not, write to the Free Software 19*a9fa9459Szrj Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, MA 20*a9fa9459Szrj 02110-1301, USA. */ 21*a9fa9459Szrj 22*a9fa9459Szrj /* This file contains code which writes out stabs debugging 23*a9fa9459Szrj information. */ 24*a9fa9459Szrj 25*a9fa9459Szrj #include "sysdep.h" 26*a9fa9459Szrj #include <assert.h> 27*a9fa9459Szrj #include "bfd.h" 28*a9fa9459Szrj #include "libiberty.h" 29*a9fa9459Szrj #include "filenames.h" 30*a9fa9459Szrj #include "safe-ctype.h" 31*a9fa9459Szrj #include "bucomm.h" 32*a9fa9459Szrj #include "debug.h" 33*a9fa9459Szrj #include "budbg.h" 34*a9fa9459Szrj #include "aout/aout64.h" 35*a9fa9459Szrj #include "aout/stab_gnu.h" 36*a9fa9459Szrj 37*a9fa9459Szrj /* The size of a stabs symbol. This presumes 32 bit values. */ 38*a9fa9459Szrj 39*a9fa9459Szrj #define STAB_SYMBOL_SIZE (12) 40*a9fa9459Szrj 41*a9fa9459Szrj /* An entry in a string hash table. */ 42*a9fa9459Szrj 43*a9fa9459Szrj struct string_hash_entry 44*a9fa9459Szrj { 45*a9fa9459Szrj struct bfd_hash_entry root; 46*a9fa9459Szrj /* Next string in this table. */ 47*a9fa9459Szrj struct string_hash_entry *next; 48*a9fa9459Szrj /* Index in string table. */ 49*a9fa9459Szrj long index; 50*a9fa9459Szrj /* Size of type if this is a typedef. */ 51*a9fa9459Szrj unsigned int size; 52*a9fa9459Szrj }; 53*a9fa9459Szrj 54*a9fa9459Szrj /* A string hash table. */ 55*a9fa9459Szrj 56*a9fa9459Szrj struct string_hash_table 57*a9fa9459Szrj { 58*a9fa9459Szrj struct bfd_hash_table table; 59*a9fa9459Szrj }; 60*a9fa9459Szrj 61*a9fa9459Szrj /* The type stack. Each element on the stack is a string. */ 62*a9fa9459Szrj 63*a9fa9459Szrj struct stab_type_stack 64*a9fa9459Szrj { 65*a9fa9459Szrj /* The next element on the stack. */ 66*a9fa9459Szrj struct stab_type_stack *next; 67*a9fa9459Szrj /* This element as a string. */ 68*a9fa9459Szrj char *string; 69*a9fa9459Szrj /* The type index of this element. */ 70*a9fa9459Szrj long index; 71*a9fa9459Szrj /* The size of the type. */ 72*a9fa9459Szrj unsigned int size; 73*a9fa9459Szrj /* Whether type string defines a new type. */ 74*a9fa9459Szrj bfd_boolean definition; 75*a9fa9459Szrj /* String defining struct fields. */ 76*a9fa9459Szrj char *fields; 77*a9fa9459Szrj /* NULL terminated array of strings defining base classes for a 78*a9fa9459Szrj class. */ 79*a9fa9459Szrj char **baseclasses; 80*a9fa9459Szrj /* String defining class methods. */ 81*a9fa9459Szrj char *methods; 82*a9fa9459Szrj /* String defining vtable pointer for a class. */ 83*a9fa9459Szrj char *vtable; 84*a9fa9459Szrj }; 85*a9fa9459Szrj 86*a9fa9459Szrj /* This structure is used to keep track of type indices for tagged 87*a9fa9459Szrj types. */ 88*a9fa9459Szrj 89*a9fa9459Szrj struct stab_tag 90*a9fa9459Szrj { 91*a9fa9459Szrj /* The type index. */ 92*a9fa9459Szrj long index; 93*a9fa9459Szrj /* The tag name. */ 94*a9fa9459Szrj const char *tag; 95*a9fa9459Szrj /* The kind of type. This is set to DEBUG_KIND_ILLEGAL when the 96*a9fa9459Szrj type is defined. */ 97*a9fa9459Szrj enum debug_type_kind kind; 98*a9fa9459Szrj /* The size of the struct. */ 99*a9fa9459Szrj unsigned int size; 100*a9fa9459Szrj }; 101*a9fa9459Szrj 102*a9fa9459Szrj /* We remember various sorts of type indices. They are not related, 103*a9fa9459Szrj but, for convenience, we keep all the information in this 104*a9fa9459Szrj structure. */ 105*a9fa9459Szrj 106*a9fa9459Szrj struct stab_type_cache 107*a9fa9459Szrj { 108*a9fa9459Szrj /* The void type index. */ 109*a9fa9459Szrj long void_type; 110*a9fa9459Szrj /* Signed integer type indices, indexed by size - 1. */ 111*a9fa9459Szrj long signed_integer_types[8]; 112*a9fa9459Szrj /* Unsigned integer type indices, indexed by size - 1. */ 113*a9fa9459Szrj long unsigned_integer_types[8]; 114*a9fa9459Szrj /* Floating point types, indexed by size - 1. */ 115*a9fa9459Szrj long float_types[16]; 116*a9fa9459Szrj /* Pointers to types, indexed by the type index. */ 117*a9fa9459Szrj long *pointer_types; 118*a9fa9459Szrj size_t pointer_types_alloc; 119*a9fa9459Szrj /* Functions returning types, indexed by the type index. */ 120*a9fa9459Szrj long *function_types; 121*a9fa9459Szrj size_t function_types_alloc; 122*a9fa9459Szrj /* References to types, indexed by the type index. */ 123*a9fa9459Szrj long *reference_types; 124*a9fa9459Szrj size_t reference_types_alloc; 125*a9fa9459Szrj /* Struct/union/class type indices, indexed by the struct id. */ 126*a9fa9459Szrj struct stab_tag *struct_types; 127*a9fa9459Szrj size_t struct_types_alloc; 128*a9fa9459Szrj }; 129*a9fa9459Szrj 130*a9fa9459Szrj /* This is the handle passed through debug_write. */ 131*a9fa9459Szrj 132*a9fa9459Szrj struct stab_write_handle 133*a9fa9459Szrj { 134*a9fa9459Szrj /* The BFD. */ 135*a9fa9459Szrj bfd *abfd; 136*a9fa9459Szrj /* This buffer holds the symbols. */ 137*a9fa9459Szrj bfd_byte *symbols; 138*a9fa9459Szrj size_t symbols_size; 139*a9fa9459Szrj size_t symbols_alloc; 140*a9fa9459Szrj /* This is a list of hash table entries for the strings. */ 141*a9fa9459Szrj struct string_hash_entry *strings; 142*a9fa9459Szrj /* The last string hash table entry. */ 143*a9fa9459Szrj struct string_hash_entry *last_string; 144*a9fa9459Szrj /* The size of the strings. */ 145*a9fa9459Szrj size_t strings_size; 146*a9fa9459Szrj /* This hash table eliminates duplicate strings. */ 147*a9fa9459Szrj struct string_hash_table strhash; 148*a9fa9459Szrj /* The type stack. */ 149*a9fa9459Szrj struct stab_type_stack *type_stack; 150*a9fa9459Szrj /* The next type index. */ 151*a9fa9459Szrj long type_index; 152*a9fa9459Szrj /* The type cache. */ 153*a9fa9459Szrj struct stab_type_cache type_cache; 154*a9fa9459Szrj /* A mapping from typedef names to type indices. */ 155*a9fa9459Szrj struct string_hash_table typedef_hash; 156*a9fa9459Szrj /* If this is not -1, it is the offset to the most recent N_SO 157*a9fa9459Szrj symbol, and the value of that symbol needs to be set. */ 158*a9fa9459Szrj long so_offset; 159*a9fa9459Szrj /* If this is not -1, it is the offset to the most recent N_FUN 160*a9fa9459Szrj symbol, and the value of that symbol needs to be set. */ 161*a9fa9459Szrj long fun_offset; 162*a9fa9459Szrj /* The last text section address seen. */ 163*a9fa9459Szrj bfd_vma last_text_address; 164*a9fa9459Szrj /* The block nesting depth. */ 165*a9fa9459Szrj unsigned int nesting; 166*a9fa9459Szrj /* The function address. */ 167*a9fa9459Szrj bfd_vma fnaddr; 168*a9fa9459Szrj /* A pending LBRAC symbol. */ 169*a9fa9459Szrj bfd_vma pending_lbrac; 170*a9fa9459Szrj /* The current line number file name. */ 171*a9fa9459Szrj const char *lineno_filename; 172*a9fa9459Szrj }; 173*a9fa9459Szrj 174*a9fa9459Szrj static struct bfd_hash_entry *string_hash_newfunc 175*a9fa9459Szrj (struct bfd_hash_entry *, struct bfd_hash_table *, const char *); 176*a9fa9459Szrj static bfd_boolean stab_write_symbol 177*a9fa9459Szrj (struct stab_write_handle *, int, int, bfd_vma, const char *); 178*a9fa9459Szrj static bfd_boolean stab_push_string 179*a9fa9459Szrj (struct stab_write_handle *, const char *, long, bfd_boolean, unsigned int); 180*a9fa9459Szrj static bfd_boolean stab_push_defined_type 181*a9fa9459Szrj (struct stab_write_handle *, long, unsigned int); 182*a9fa9459Szrj static char *stab_pop_type (struct stab_write_handle *); 183*a9fa9459Szrj static bfd_boolean stab_modify_type 184*a9fa9459Szrj (struct stab_write_handle *, int, unsigned int, long **, size_t *); 185*a9fa9459Szrj static long stab_get_struct_index 186*a9fa9459Szrj (struct stab_write_handle *, const char *, unsigned int, 187*a9fa9459Szrj enum debug_type_kind, unsigned int *); 188*a9fa9459Szrj static bfd_boolean stab_class_method_var 189*a9fa9459Szrj (struct stab_write_handle *, const char *, enum debug_visibility, 190*a9fa9459Szrj bfd_boolean, bfd_boolean, bfd_boolean, bfd_vma, bfd_boolean); 191*a9fa9459Szrj static bfd_boolean stab_start_compilation_unit (void *, const char *); 192*a9fa9459Szrj static bfd_boolean stab_start_source (void *, const char *); 193*a9fa9459Szrj static bfd_boolean stab_empty_type (void *); 194*a9fa9459Szrj static bfd_boolean stab_void_type (void *); 195*a9fa9459Szrj static bfd_boolean stab_int_type (void *, unsigned int, bfd_boolean); 196*a9fa9459Szrj static bfd_boolean stab_float_type (void *, unsigned int); 197*a9fa9459Szrj static bfd_boolean stab_complex_type (void *, unsigned int); 198*a9fa9459Szrj static bfd_boolean stab_bool_type (void *, unsigned int); 199*a9fa9459Szrj static bfd_boolean stab_enum_type 200*a9fa9459Szrj (void *, const char *, const char **, bfd_signed_vma *); 201*a9fa9459Szrj static bfd_boolean stab_pointer_type (void *); 202*a9fa9459Szrj static bfd_boolean stab_function_type (void *, int, bfd_boolean); 203*a9fa9459Szrj static bfd_boolean stab_reference_type (void *); 204*a9fa9459Szrj static bfd_boolean stab_range_type (void *, bfd_signed_vma, bfd_signed_vma); 205*a9fa9459Szrj static bfd_boolean stab_array_type 206*a9fa9459Szrj (void *, bfd_signed_vma, bfd_signed_vma, bfd_boolean); 207*a9fa9459Szrj static bfd_boolean stab_set_type (void *, bfd_boolean); 208*a9fa9459Szrj static bfd_boolean stab_offset_type (void *); 209*a9fa9459Szrj static bfd_boolean stab_method_type (void *, bfd_boolean, int, bfd_boolean); 210*a9fa9459Szrj static bfd_boolean stab_const_type (void *); 211*a9fa9459Szrj static bfd_boolean stab_volatile_type (void *); 212*a9fa9459Szrj static bfd_boolean stab_start_struct_type 213*a9fa9459Szrj (void *, const char *, unsigned int, bfd_boolean, unsigned int); 214*a9fa9459Szrj static bfd_boolean stab_struct_field 215*a9fa9459Szrj (void *, const char *, bfd_vma, bfd_vma, enum debug_visibility); 216*a9fa9459Szrj static bfd_boolean stab_end_struct_type (void *); 217*a9fa9459Szrj static bfd_boolean stab_start_class_type 218*a9fa9459Szrj (void *, const char *, unsigned int, bfd_boolean, unsigned int, 219*a9fa9459Szrj bfd_boolean, bfd_boolean); 220*a9fa9459Szrj static bfd_boolean stab_class_static_member 221*a9fa9459Szrj (void *, const char *, const char *, enum debug_visibility); 222*a9fa9459Szrj static bfd_boolean stab_class_baseclass 223*a9fa9459Szrj (void *, bfd_vma, bfd_boolean, enum debug_visibility); 224*a9fa9459Szrj static bfd_boolean stab_class_start_method (void *, const char *); 225*a9fa9459Szrj static bfd_boolean stab_class_method_variant 226*a9fa9459Szrj (void *, const char *, enum debug_visibility, bfd_boolean, bfd_boolean, 227*a9fa9459Szrj bfd_vma, bfd_boolean); 228*a9fa9459Szrj static bfd_boolean stab_class_static_method_variant 229*a9fa9459Szrj (void *, const char *, enum debug_visibility, bfd_boolean, bfd_boolean); 230*a9fa9459Szrj static bfd_boolean stab_class_end_method (void *); 231*a9fa9459Szrj static bfd_boolean stab_end_class_type (void *); 232*a9fa9459Szrj static bfd_boolean stab_typedef_type (void *, const char *); 233*a9fa9459Szrj static bfd_boolean stab_tag_type 234*a9fa9459Szrj (void *, const char *, unsigned int, enum debug_type_kind); 235*a9fa9459Szrj static bfd_boolean stab_typdef (void *, const char *); 236*a9fa9459Szrj static bfd_boolean stab_tag (void *, const char *); 237*a9fa9459Szrj static bfd_boolean stab_int_constant (void *, const char *, bfd_vma); 238*a9fa9459Szrj static bfd_boolean stab_float_constant (void *, const char *, double); 239*a9fa9459Szrj static bfd_boolean stab_typed_constant (void *, const char *, bfd_vma); 240*a9fa9459Szrj static bfd_boolean stab_variable 241*a9fa9459Szrj (void *, const char *, enum debug_var_kind, bfd_vma); 242*a9fa9459Szrj static bfd_boolean stab_start_function (void *, const char *, bfd_boolean); 243*a9fa9459Szrj static bfd_boolean stab_function_parameter 244*a9fa9459Szrj (void *, const char *, enum debug_parm_kind, bfd_vma); 245*a9fa9459Szrj static bfd_boolean stab_start_block (void *, bfd_vma); 246*a9fa9459Szrj static bfd_boolean stab_end_block (void *, bfd_vma); 247*a9fa9459Szrj static bfd_boolean stab_end_function (void *); 248*a9fa9459Szrj static bfd_boolean stab_lineno (void *, const char *, unsigned long, bfd_vma); 249*a9fa9459Szrj 250*a9fa9459Szrj static const struct debug_write_fns stab_fns = 251*a9fa9459Szrj { 252*a9fa9459Szrj stab_start_compilation_unit, 253*a9fa9459Szrj stab_start_source, 254*a9fa9459Szrj stab_empty_type, 255*a9fa9459Szrj stab_void_type, 256*a9fa9459Szrj stab_int_type, 257*a9fa9459Szrj stab_float_type, 258*a9fa9459Szrj stab_complex_type, 259*a9fa9459Szrj stab_bool_type, 260*a9fa9459Szrj stab_enum_type, 261*a9fa9459Szrj stab_pointer_type, 262*a9fa9459Szrj stab_function_type, 263*a9fa9459Szrj stab_reference_type, 264*a9fa9459Szrj stab_range_type, 265*a9fa9459Szrj stab_array_type, 266*a9fa9459Szrj stab_set_type, 267*a9fa9459Szrj stab_offset_type, 268*a9fa9459Szrj stab_method_type, 269*a9fa9459Szrj stab_const_type, 270*a9fa9459Szrj stab_volatile_type, 271*a9fa9459Szrj stab_start_struct_type, 272*a9fa9459Szrj stab_struct_field, 273*a9fa9459Szrj stab_end_struct_type, 274*a9fa9459Szrj stab_start_class_type, 275*a9fa9459Szrj stab_class_static_member, 276*a9fa9459Szrj stab_class_baseclass, 277*a9fa9459Szrj stab_class_start_method, 278*a9fa9459Szrj stab_class_method_variant, 279*a9fa9459Szrj stab_class_static_method_variant, 280*a9fa9459Szrj stab_class_end_method, 281*a9fa9459Szrj stab_end_class_type, 282*a9fa9459Szrj stab_typedef_type, 283*a9fa9459Szrj stab_tag_type, 284*a9fa9459Szrj stab_typdef, 285*a9fa9459Szrj stab_tag, 286*a9fa9459Szrj stab_int_constant, 287*a9fa9459Szrj stab_float_constant, 288*a9fa9459Szrj stab_typed_constant, 289*a9fa9459Szrj stab_variable, 290*a9fa9459Szrj stab_start_function, 291*a9fa9459Szrj stab_function_parameter, 292*a9fa9459Szrj stab_start_block, 293*a9fa9459Szrj stab_end_block, 294*a9fa9459Szrj stab_end_function, 295*a9fa9459Szrj stab_lineno 296*a9fa9459Szrj }; 297*a9fa9459Szrj 298*a9fa9459Szrj /* Routine to create an entry in a string hash table. */ 299*a9fa9459Szrj 300*a9fa9459Szrj static struct bfd_hash_entry * 301*a9fa9459Szrj string_hash_newfunc (struct bfd_hash_entry *entry, 302*a9fa9459Szrj struct bfd_hash_table *table, const char *string) 303*a9fa9459Szrj { 304*a9fa9459Szrj struct string_hash_entry *ret = (struct string_hash_entry *) entry; 305*a9fa9459Szrj 306*a9fa9459Szrj /* Allocate the structure if it has not already been allocated by a 307*a9fa9459Szrj subclass. */ 308*a9fa9459Szrj if (ret == (struct string_hash_entry *) NULL) 309*a9fa9459Szrj ret = ((struct string_hash_entry *) 310*a9fa9459Szrj bfd_hash_allocate (table, sizeof (struct string_hash_entry))); 311*a9fa9459Szrj if (ret == (struct string_hash_entry *) NULL) 312*a9fa9459Szrj return NULL; 313*a9fa9459Szrj 314*a9fa9459Szrj /* Call the allocation method of the superclass. */ 315*a9fa9459Szrj ret = ((struct string_hash_entry *) 316*a9fa9459Szrj bfd_hash_newfunc ((struct bfd_hash_entry *) ret, table, string)); 317*a9fa9459Szrj 318*a9fa9459Szrj if (ret) 319*a9fa9459Szrj { 320*a9fa9459Szrj /* Initialize the local fields. */ 321*a9fa9459Szrj ret->next = NULL; 322*a9fa9459Szrj ret->index = -1; 323*a9fa9459Szrj ret->size = 0; 324*a9fa9459Szrj } 325*a9fa9459Szrj 326*a9fa9459Szrj return (struct bfd_hash_entry *) ret; 327*a9fa9459Szrj } 328*a9fa9459Szrj 329*a9fa9459Szrj /* Look up an entry in a string hash table. */ 330*a9fa9459Szrj 331*a9fa9459Szrj #define string_hash_lookup(t, string, create, copy) \ 332*a9fa9459Szrj ((struct string_hash_entry *) \ 333*a9fa9459Szrj bfd_hash_lookup (&(t)->table, (string), (create), (copy))) 334*a9fa9459Szrj 335*a9fa9459Szrj /* Add a symbol to the stabs debugging information we are building. */ 336*a9fa9459Szrj 337*a9fa9459Szrj static bfd_boolean 338*a9fa9459Szrj stab_write_symbol (struct stab_write_handle *info, int type, int desc, 339*a9fa9459Szrj bfd_vma value, const char *string) 340*a9fa9459Szrj { 341*a9fa9459Szrj bfd_size_type strx; 342*a9fa9459Szrj bfd_byte sym[STAB_SYMBOL_SIZE]; 343*a9fa9459Szrj 344*a9fa9459Szrj if (string == NULL) 345*a9fa9459Szrj strx = 0; 346*a9fa9459Szrj else 347*a9fa9459Szrj { 348*a9fa9459Szrj struct string_hash_entry *h; 349*a9fa9459Szrj 350*a9fa9459Szrj h = string_hash_lookup (&info->strhash, string, TRUE, TRUE); 351*a9fa9459Szrj if (h == NULL) 352*a9fa9459Szrj { 353*a9fa9459Szrj non_fatal (_("string_hash_lookup failed: %s"), 354*a9fa9459Szrj bfd_errmsg (bfd_get_error ())); 355*a9fa9459Szrj return FALSE; 356*a9fa9459Szrj } 357*a9fa9459Szrj if (h->index != -1) 358*a9fa9459Szrj strx = h->index; 359*a9fa9459Szrj else 360*a9fa9459Szrj { 361*a9fa9459Szrj strx = info->strings_size; 362*a9fa9459Szrj h->index = strx; 363*a9fa9459Szrj if (info->last_string == NULL) 364*a9fa9459Szrj info->strings = h; 365*a9fa9459Szrj else 366*a9fa9459Szrj info->last_string->next = h; 367*a9fa9459Szrj info->last_string = h; 368*a9fa9459Szrj info->strings_size += strlen (string) + 1; 369*a9fa9459Szrj } 370*a9fa9459Szrj } 371*a9fa9459Szrj 372*a9fa9459Szrj /* This presumes 32 bit values. */ 373*a9fa9459Szrj bfd_put_32 (info->abfd, strx, sym); 374*a9fa9459Szrj bfd_put_8 (info->abfd, type, sym + 4); 375*a9fa9459Szrj bfd_put_8 (info->abfd, 0, sym + 5); 376*a9fa9459Szrj bfd_put_16 (info->abfd, desc, sym + 6); 377*a9fa9459Szrj bfd_put_32 (info->abfd, value, sym + 8); 378*a9fa9459Szrj 379*a9fa9459Szrj if (info->symbols_size + STAB_SYMBOL_SIZE > info->symbols_alloc) 380*a9fa9459Szrj { 381*a9fa9459Szrj info->symbols_alloc *= 2; 382*a9fa9459Szrj info->symbols = (bfd_byte *) xrealloc (info->symbols, 383*a9fa9459Szrj info->symbols_alloc); 384*a9fa9459Szrj } 385*a9fa9459Szrj 386*a9fa9459Szrj memcpy (info->symbols + info->symbols_size, sym, STAB_SYMBOL_SIZE); 387*a9fa9459Szrj 388*a9fa9459Szrj info->symbols_size += STAB_SYMBOL_SIZE; 389*a9fa9459Szrj 390*a9fa9459Szrj return TRUE; 391*a9fa9459Szrj } 392*a9fa9459Szrj 393*a9fa9459Szrj /* Push a string on to the type stack. */ 394*a9fa9459Szrj 395*a9fa9459Szrj static bfd_boolean 396*a9fa9459Szrj stab_push_string (struct stab_write_handle *info, const char *string, 397*a9fa9459Szrj long tindex, bfd_boolean definition, unsigned int size) 398*a9fa9459Szrj { 399*a9fa9459Szrj struct stab_type_stack *s; 400*a9fa9459Szrj 401*a9fa9459Szrj s = (struct stab_type_stack *) xmalloc (sizeof *s); 402*a9fa9459Szrj s->string = xstrdup (string); 403*a9fa9459Szrj s->index = tindex; 404*a9fa9459Szrj s->definition = definition; 405*a9fa9459Szrj s->size = size; 406*a9fa9459Szrj 407*a9fa9459Szrj s->fields = NULL; 408*a9fa9459Szrj s->baseclasses = NULL; 409*a9fa9459Szrj s->methods = NULL; 410*a9fa9459Szrj s->vtable = NULL; 411*a9fa9459Szrj 412*a9fa9459Szrj s->next = info->type_stack; 413*a9fa9459Szrj info->type_stack = s; 414*a9fa9459Szrj 415*a9fa9459Szrj return TRUE; 416*a9fa9459Szrj } 417*a9fa9459Szrj 418*a9fa9459Szrj /* Push a type index which has already been defined. */ 419*a9fa9459Szrj 420*a9fa9459Szrj static bfd_boolean 421*a9fa9459Szrj stab_push_defined_type (struct stab_write_handle *info, long tindex, 422*a9fa9459Szrj unsigned int size) 423*a9fa9459Szrj { 424*a9fa9459Szrj char buf[20]; 425*a9fa9459Szrj 426*a9fa9459Szrj sprintf (buf, "%ld", tindex); 427*a9fa9459Szrj return stab_push_string (info, buf, tindex, FALSE, size); 428*a9fa9459Szrj } 429*a9fa9459Szrj 430*a9fa9459Szrj /* Pop a type off the type stack. The caller is responsible for 431*a9fa9459Szrj freeing the string. */ 432*a9fa9459Szrj 433*a9fa9459Szrj static char * 434*a9fa9459Szrj stab_pop_type (struct stab_write_handle *info) 435*a9fa9459Szrj { 436*a9fa9459Szrj struct stab_type_stack *s; 437*a9fa9459Szrj char *ret; 438*a9fa9459Szrj 439*a9fa9459Szrj s = info->type_stack; 440*a9fa9459Szrj assert (s != NULL); 441*a9fa9459Szrj 442*a9fa9459Szrj info->type_stack = s->next; 443*a9fa9459Szrj 444*a9fa9459Szrj ret = s->string; 445*a9fa9459Szrj 446*a9fa9459Szrj free (s); 447*a9fa9459Szrj 448*a9fa9459Szrj return ret; 449*a9fa9459Szrj } 450*a9fa9459Szrj 451*a9fa9459Szrj /* The general routine to write out stabs in sections debugging 452*a9fa9459Szrj information. This accumulates the stabs symbols and the strings in 453*a9fa9459Szrj two obstacks. We can't easily write out the information as we go 454*a9fa9459Szrj along, because we need to know the section sizes before we can 455*a9fa9459Szrj write out the section contents. ABFD is the BFD and DHANDLE is the 456*a9fa9459Szrj handle for the debugging information. This sets *PSYMS to point to 457*a9fa9459Szrj the symbols, *PSYMSIZE the size of the symbols, *PSTRINGS to the 458*a9fa9459Szrj strings, and *PSTRINGSIZE to the size of the strings. */ 459*a9fa9459Szrj 460*a9fa9459Szrj bfd_boolean 461*a9fa9459Szrj write_stabs_in_sections_debugging_info (bfd *abfd, void *dhandle, 462*a9fa9459Szrj bfd_byte **psyms, 463*a9fa9459Szrj bfd_size_type *psymsize, 464*a9fa9459Szrj bfd_byte **pstrings, 465*a9fa9459Szrj bfd_size_type *pstringsize) 466*a9fa9459Szrj { 467*a9fa9459Szrj struct stab_write_handle info; 468*a9fa9459Szrj struct string_hash_entry *h; 469*a9fa9459Szrj bfd_byte *p; 470*a9fa9459Szrj 471*a9fa9459Szrj info.abfd = abfd; 472*a9fa9459Szrj 473*a9fa9459Szrj info.symbols_size = 0; 474*a9fa9459Szrj info.symbols_alloc = 500; 475*a9fa9459Szrj info.symbols = (bfd_byte *) xmalloc (info.symbols_alloc); 476*a9fa9459Szrj 477*a9fa9459Szrj info.strings = NULL; 478*a9fa9459Szrj info.last_string = NULL; 479*a9fa9459Szrj /* Reserve 1 byte for a null byte. */ 480*a9fa9459Szrj info.strings_size = 1; 481*a9fa9459Szrj 482*a9fa9459Szrj if (!bfd_hash_table_init (&info.strhash.table, string_hash_newfunc, 483*a9fa9459Szrj sizeof (struct string_hash_entry)) 484*a9fa9459Szrj || !bfd_hash_table_init (&info.typedef_hash.table, string_hash_newfunc, 485*a9fa9459Szrj sizeof (struct string_hash_entry))) 486*a9fa9459Szrj { 487*a9fa9459Szrj non_fatal ("bfd_hash_table_init_failed: %s", 488*a9fa9459Szrj bfd_errmsg (bfd_get_error ())); 489*a9fa9459Szrj return FALSE; 490*a9fa9459Szrj } 491*a9fa9459Szrj 492*a9fa9459Szrj info.type_stack = NULL; 493*a9fa9459Szrj info.type_index = 1; 494*a9fa9459Szrj memset (&info.type_cache, 0, sizeof info.type_cache); 495*a9fa9459Szrj info.so_offset = -1; 496*a9fa9459Szrj info.fun_offset = -1; 497*a9fa9459Szrj info.last_text_address = 0; 498*a9fa9459Szrj info.nesting = 0; 499*a9fa9459Szrj info.fnaddr = 0; 500*a9fa9459Szrj info.pending_lbrac = (bfd_vma) -1; 501*a9fa9459Szrj 502*a9fa9459Szrj /* The initial symbol holds the string size. */ 503*a9fa9459Szrj if (! stab_write_symbol (&info, 0, 0, 0, (const char *) NULL)) 504*a9fa9459Szrj return FALSE; 505*a9fa9459Szrj 506*a9fa9459Szrj /* Output an initial N_SO symbol. */ 507*a9fa9459Szrj info.so_offset = info.symbols_size; 508*a9fa9459Szrj if (! stab_write_symbol (&info, N_SO, 0, 0, bfd_get_filename (abfd))) 509*a9fa9459Szrj return FALSE; 510*a9fa9459Szrj 511*a9fa9459Szrj if (! debug_write (dhandle, &stab_fns, (void *) &info)) 512*a9fa9459Szrj return FALSE; 513*a9fa9459Szrj 514*a9fa9459Szrj assert (info.pending_lbrac == (bfd_vma) -1); 515*a9fa9459Szrj 516*a9fa9459Szrj /* Output a trailing N_SO. */ 517*a9fa9459Szrj if (! stab_write_symbol (&info, N_SO, 0, info.last_text_address, 518*a9fa9459Szrj (const char *) NULL)) 519*a9fa9459Szrj return FALSE; 520*a9fa9459Szrj 521*a9fa9459Szrj /* Put the string size in the initial symbol. */ 522*a9fa9459Szrj bfd_put_32 (abfd, info.strings_size, info.symbols + 8); 523*a9fa9459Szrj 524*a9fa9459Szrj *psyms = info.symbols; 525*a9fa9459Szrj *psymsize = info.symbols_size; 526*a9fa9459Szrj 527*a9fa9459Szrj *pstringsize = info.strings_size; 528*a9fa9459Szrj *pstrings = (bfd_byte *) xmalloc (info.strings_size); 529*a9fa9459Szrj 530*a9fa9459Szrj p = *pstrings; 531*a9fa9459Szrj *p++ = '\0'; 532*a9fa9459Szrj for (h = info.strings; h != NULL; h = h->next) 533*a9fa9459Szrj { 534*a9fa9459Szrj strcpy ((char *) p, h->root.string); 535*a9fa9459Szrj p += strlen ((char *) p) + 1; 536*a9fa9459Szrj } 537*a9fa9459Szrj 538*a9fa9459Szrj return TRUE; 539*a9fa9459Szrj } 540*a9fa9459Szrj 541*a9fa9459Szrj /* Start writing out information for a compilation unit. */ 542*a9fa9459Szrj 543*a9fa9459Szrj static bfd_boolean 544*a9fa9459Szrj stab_start_compilation_unit (void *p, const char *filename) 545*a9fa9459Szrj { 546*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 547*a9fa9459Szrj 548*a9fa9459Szrj /* We would normally output an N_SO symbol here. However, that 549*a9fa9459Szrj would force us to reset all of our type information. I think we 550*a9fa9459Szrj will be better off just outputting an N_SOL symbol, and not 551*a9fa9459Szrj worrying about splitting information between files. */ 552*a9fa9459Szrj 553*a9fa9459Szrj info->lineno_filename = filename; 554*a9fa9459Szrj 555*a9fa9459Szrj return stab_write_symbol (info, N_SOL, 0, 0, filename); 556*a9fa9459Szrj } 557*a9fa9459Szrj 558*a9fa9459Szrj /* Start writing out information for a particular source file. */ 559*a9fa9459Szrj 560*a9fa9459Szrj static bfd_boolean 561*a9fa9459Szrj stab_start_source (void *p, const char *filename) 562*a9fa9459Szrj { 563*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 564*a9fa9459Szrj 565*a9fa9459Szrj /* FIXME: The symbol's value is supposed to be the text section 566*a9fa9459Szrj address. However, we would have to fill it in later, and gdb 567*a9fa9459Szrj doesn't care, so we don't bother with it. */ 568*a9fa9459Szrj 569*a9fa9459Szrj info->lineno_filename = filename; 570*a9fa9459Szrj 571*a9fa9459Szrj return stab_write_symbol (info, N_SOL, 0, 0, filename); 572*a9fa9459Szrj } 573*a9fa9459Szrj 574*a9fa9459Szrj /* Push an empty type. This shouldn't normally happen. We just use a 575*a9fa9459Szrj void type. */ 576*a9fa9459Szrj 577*a9fa9459Szrj static bfd_boolean 578*a9fa9459Szrj stab_empty_type (void *p) 579*a9fa9459Szrj { 580*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 581*a9fa9459Szrj 582*a9fa9459Szrj /* We don't call stab_void_type if the type is not yet defined, 583*a9fa9459Szrj because that might screw up the typedef. */ 584*a9fa9459Szrj 585*a9fa9459Szrj if (info->type_cache.void_type != 0) 586*a9fa9459Szrj return stab_push_defined_type (info, info->type_cache.void_type, 0); 587*a9fa9459Szrj else 588*a9fa9459Szrj { 589*a9fa9459Szrj long tindex; 590*a9fa9459Szrj char buf[40]; 591*a9fa9459Szrj 592*a9fa9459Szrj tindex = info->type_index; 593*a9fa9459Szrj ++info->type_index; 594*a9fa9459Szrj 595*a9fa9459Szrj sprintf (buf, "%ld=%ld", tindex, tindex); 596*a9fa9459Szrj 597*a9fa9459Szrj return stab_push_string (info, buf, tindex, FALSE, 0); 598*a9fa9459Szrj } 599*a9fa9459Szrj } 600*a9fa9459Szrj 601*a9fa9459Szrj /* Push a void type. */ 602*a9fa9459Szrj 603*a9fa9459Szrj static bfd_boolean 604*a9fa9459Szrj stab_void_type (void *p) 605*a9fa9459Szrj { 606*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 607*a9fa9459Szrj 608*a9fa9459Szrj if (info->type_cache.void_type != 0) 609*a9fa9459Szrj return stab_push_defined_type (info, info->type_cache.void_type, 0); 610*a9fa9459Szrj else 611*a9fa9459Szrj { 612*a9fa9459Szrj long tindex; 613*a9fa9459Szrj char buf[40]; 614*a9fa9459Szrj 615*a9fa9459Szrj tindex = info->type_index; 616*a9fa9459Szrj ++info->type_index; 617*a9fa9459Szrj 618*a9fa9459Szrj info->type_cache.void_type = tindex; 619*a9fa9459Szrj 620*a9fa9459Szrj sprintf (buf, "%ld=%ld", tindex, tindex); 621*a9fa9459Szrj 622*a9fa9459Szrj return stab_push_string (info, buf, tindex, TRUE, 0); 623*a9fa9459Szrj } 624*a9fa9459Szrj } 625*a9fa9459Szrj 626*a9fa9459Szrj /* Push an integer type. */ 627*a9fa9459Szrj 628*a9fa9459Szrj static bfd_boolean 629*a9fa9459Szrj stab_int_type (void *p, unsigned int size, bfd_boolean unsignedp) 630*a9fa9459Szrj { 631*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 632*a9fa9459Szrj long *cache; 633*a9fa9459Szrj 634*a9fa9459Szrj if (size <= 0 || (size > sizeof (long) && size != 8)) 635*a9fa9459Szrj { 636*a9fa9459Szrj non_fatal (_("stab_int_type: bad size %u"), size); 637*a9fa9459Szrj return FALSE; 638*a9fa9459Szrj } 639*a9fa9459Szrj 640*a9fa9459Szrj if (unsignedp) 641*a9fa9459Szrj cache = info->type_cache.signed_integer_types; 642*a9fa9459Szrj else 643*a9fa9459Szrj cache = info->type_cache.unsigned_integer_types; 644*a9fa9459Szrj 645*a9fa9459Szrj if (cache[size - 1] != 0) 646*a9fa9459Szrj return stab_push_defined_type (info, cache[size - 1], size); 647*a9fa9459Szrj else 648*a9fa9459Szrj { 649*a9fa9459Szrj long tindex; 650*a9fa9459Szrj char buf[100]; 651*a9fa9459Szrj 652*a9fa9459Szrj tindex = info->type_index; 653*a9fa9459Szrj ++info->type_index; 654*a9fa9459Szrj 655*a9fa9459Szrj cache[size - 1] = tindex; 656*a9fa9459Szrj 657*a9fa9459Szrj sprintf (buf, "%ld=r%ld;", tindex, tindex); 658*a9fa9459Szrj if (unsignedp) 659*a9fa9459Szrj { 660*a9fa9459Szrj strcat (buf, "0;"); 661*a9fa9459Szrj if (size < sizeof (long)) 662*a9fa9459Szrj sprintf (buf + strlen (buf), "%ld;", ((long) 1 << (size * 8)) - 1); 663*a9fa9459Szrj else if (size == sizeof (long)) 664*a9fa9459Szrj strcat (buf, "-1;"); 665*a9fa9459Szrj else if (size == 8) 666*a9fa9459Szrj strcat (buf, "01777777777777777777777;"); 667*a9fa9459Szrj else 668*a9fa9459Szrj abort (); 669*a9fa9459Szrj } 670*a9fa9459Szrj else 671*a9fa9459Szrj { 672*a9fa9459Szrj if (size <= sizeof (long)) 673*a9fa9459Szrj sprintf (buf + strlen (buf), "%ld;%ld;", 674*a9fa9459Szrj (long) - ((unsigned long) 1 << (size * 8 - 1)), 675*a9fa9459Szrj (long) (((unsigned long) 1 << (size * 8 - 1)) - 1)); 676*a9fa9459Szrj else if (size == 8) 677*a9fa9459Szrj strcat (buf, "01000000000000000000000;0777777777777777777777;"); 678*a9fa9459Szrj else 679*a9fa9459Szrj abort (); 680*a9fa9459Szrj } 681*a9fa9459Szrj 682*a9fa9459Szrj return stab_push_string (info, buf, tindex, TRUE, size); 683*a9fa9459Szrj } 684*a9fa9459Szrj } 685*a9fa9459Szrj 686*a9fa9459Szrj /* Push a floating point type. */ 687*a9fa9459Szrj 688*a9fa9459Szrj static bfd_boolean 689*a9fa9459Szrj stab_float_type (void *p, unsigned int size) 690*a9fa9459Szrj { 691*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 692*a9fa9459Szrj 693*a9fa9459Szrj if (size > 0 694*a9fa9459Szrj && size - 1 < (sizeof info->type_cache.float_types 695*a9fa9459Szrj / sizeof info->type_cache.float_types[0]) 696*a9fa9459Szrj && info->type_cache.float_types[size - 1] != 0) 697*a9fa9459Szrj return stab_push_defined_type (info, 698*a9fa9459Szrj info->type_cache.float_types[size - 1], 699*a9fa9459Szrj size); 700*a9fa9459Szrj else 701*a9fa9459Szrj { 702*a9fa9459Szrj long tindex; 703*a9fa9459Szrj char *int_type; 704*a9fa9459Szrj char buf[50]; 705*a9fa9459Szrj 706*a9fa9459Szrj /* Floats are defined as a subrange of int. */ 707*a9fa9459Szrj if (! stab_int_type (info, 4, FALSE)) 708*a9fa9459Szrj return FALSE; 709*a9fa9459Szrj int_type = stab_pop_type (info); 710*a9fa9459Szrj 711*a9fa9459Szrj tindex = info->type_index; 712*a9fa9459Szrj ++info->type_index; 713*a9fa9459Szrj 714*a9fa9459Szrj if (size > 0 715*a9fa9459Szrj && size - 1 < (sizeof info->type_cache.float_types 716*a9fa9459Szrj / sizeof info->type_cache.float_types[0])) 717*a9fa9459Szrj info->type_cache.float_types[size - 1] = tindex; 718*a9fa9459Szrj 719*a9fa9459Szrj sprintf (buf, "%ld=r%s;%u;0;", tindex, int_type, size); 720*a9fa9459Szrj 721*a9fa9459Szrj free (int_type); 722*a9fa9459Szrj 723*a9fa9459Szrj return stab_push_string (info, buf, tindex, TRUE, size); 724*a9fa9459Szrj } 725*a9fa9459Szrj } 726*a9fa9459Szrj 727*a9fa9459Szrj /* Push a complex type. */ 728*a9fa9459Szrj 729*a9fa9459Szrj static bfd_boolean 730*a9fa9459Szrj stab_complex_type (void *p, unsigned int size) 731*a9fa9459Szrj { 732*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 733*a9fa9459Szrj char buf[50]; 734*a9fa9459Szrj long tindex; 735*a9fa9459Szrj 736*a9fa9459Szrj tindex = info->type_index; 737*a9fa9459Szrj ++info->type_index; 738*a9fa9459Szrj 739*a9fa9459Szrj sprintf (buf, "%ld=r%ld;%u;0;", tindex, tindex, size); 740*a9fa9459Szrj 741*a9fa9459Szrj return stab_push_string (info, buf, tindex, TRUE, size * 2); 742*a9fa9459Szrj } 743*a9fa9459Szrj 744*a9fa9459Szrj /* Push a bfd_boolean type. We use an XCOFF predefined type, since gdb 745*a9fa9459Szrj always recognizes them. */ 746*a9fa9459Szrj 747*a9fa9459Szrj static bfd_boolean 748*a9fa9459Szrj stab_bool_type (void *p, unsigned int size) 749*a9fa9459Szrj { 750*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 751*a9fa9459Szrj long tindex; 752*a9fa9459Szrj 753*a9fa9459Szrj switch (size) 754*a9fa9459Szrj { 755*a9fa9459Szrj case 1: 756*a9fa9459Szrj tindex = -21; 757*a9fa9459Szrj break; 758*a9fa9459Szrj 759*a9fa9459Szrj case 2: 760*a9fa9459Szrj tindex = -22; 761*a9fa9459Szrj break; 762*a9fa9459Szrj 763*a9fa9459Szrj default: 764*a9fa9459Szrj case 4: 765*a9fa9459Szrj tindex = -16; 766*a9fa9459Szrj break; 767*a9fa9459Szrj 768*a9fa9459Szrj case 8: 769*a9fa9459Szrj tindex = -33; 770*a9fa9459Szrj break; 771*a9fa9459Szrj } 772*a9fa9459Szrj 773*a9fa9459Szrj return stab_push_defined_type (info, tindex, size); 774*a9fa9459Szrj } 775*a9fa9459Szrj 776*a9fa9459Szrj /* Push an enum type. */ 777*a9fa9459Szrj 778*a9fa9459Szrj static bfd_boolean 779*a9fa9459Szrj stab_enum_type (void *p, const char *tag, const char **names, 780*a9fa9459Szrj bfd_signed_vma *vals) 781*a9fa9459Szrj { 782*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 783*a9fa9459Szrj size_t len; 784*a9fa9459Szrj const char **pn; 785*a9fa9459Szrj char *buf; 786*a9fa9459Szrj long tindex = 0; 787*a9fa9459Szrj bfd_signed_vma *pv; 788*a9fa9459Szrj 789*a9fa9459Szrj if (names == NULL) 790*a9fa9459Szrj { 791*a9fa9459Szrj assert (tag != NULL); 792*a9fa9459Szrj 793*a9fa9459Szrj buf = (char *) xmalloc (10 + strlen (tag)); 794*a9fa9459Szrj sprintf (buf, "xe%s:", tag); 795*a9fa9459Szrj /* FIXME: The size is just a guess. */ 796*a9fa9459Szrj if (! stab_push_string (info, buf, 0, FALSE, 4)) 797*a9fa9459Szrj return FALSE; 798*a9fa9459Szrj free (buf); 799*a9fa9459Szrj return TRUE; 800*a9fa9459Szrj } 801*a9fa9459Szrj 802*a9fa9459Szrj len = 10; 803*a9fa9459Szrj if (tag != NULL) 804*a9fa9459Szrj len += strlen (tag); 805*a9fa9459Szrj for (pn = names; *pn != NULL; pn++) 806*a9fa9459Szrj len += strlen (*pn) + 20; 807*a9fa9459Szrj 808*a9fa9459Szrj buf = (char *) xmalloc (len); 809*a9fa9459Szrj 810*a9fa9459Szrj if (tag == NULL) 811*a9fa9459Szrj strcpy (buf, "e"); 812*a9fa9459Szrj else 813*a9fa9459Szrj { 814*a9fa9459Szrj tindex = info->type_index; 815*a9fa9459Szrj ++info->type_index; 816*a9fa9459Szrj sprintf (buf, "%s:T%ld=e", tag, tindex); 817*a9fa9459Szrj } 818*a9fa9459Szrj 819*a9fa9459Szrj for (pn = names, pv = vals; *pn != NULL; pn++, pv++) 820*a9fa9459Szrj sprintf (buf + strlen (buf), "%s:%ld,", *pn, (long) *pv); 821*a9fa9459Szrj strcat (buf, ";"); 822*a9fa9459Szrj 823*a9fa9459Szrj if (tag == NULL) 824*a9fa9459Szrj { 825*a9fa9459Szrj /* FIXME: The size is just a guess. */ 826*a9fa9459Szrj if (! stab_push_string (info, buf, 0, FALSE, 4)) 827*a9fa9459Szrj return FALSE; 828*a9fa9459Szrj } 829*a9fa9459Szrj else 830*a9fa9459Szrj { 831*a9fa9459Szrj /* FIXME: The size is just a guess. */ 832*a9fa9459Szrj if (! stab_write_symbol (info, N_LSYM, 0, 0, buf) 833*a9fa9459Szrj || ! stab_push_defined_type (info, tindex, 4)) 834*a9fa9459Szrj return FALSE; 835*a9fa9459Szrj } 836*a9fa9459Szrj 837*a9fa9459Szrj free (buf); 838*a9fa9459Szrj 839*a9fa9459Szrj return TRUE; 840*a9fa9459Szrj } 841*a9fa9459Szrj 842*a9fa9459Szrj /* Push a modification of the top type on the stack. Cache the 843*a9fa9459Szrj results in CACHE and CACHE_ALLOC. */ 844*a9fa9459Szrj 845*a9fa9459Szrj static bfd_boolean 846*a9fa9459Szrj stab_modify_type (struct stab_write_handle *info, int mod, 847*a9fa9459Szrj unsigned int size, long **cache, size_t *cache_alloc) 848*a9fa9459Szrj { 849*a9fa9459Szrj long targindex; 850*a9fa9459Szrj long tindex; 851*a9fa9459Szrj char *s, *buf; 852*a9fa9459Szrj 853*a9fa9459Szrj assert (info->type_stack != NULL); 854*a9fa9459Szrj targindex = info->type_stack->index; 855*a9fa9459Szrj 856*a9fa9459Szrj if (targindex <= 0 857*a9fa9459Szrj || cache == NULL) 858*a9fa9459Szrj { 859*a9fa9459Szrj bfd_boolean definition; 860*a9fa9459Szrj 861*a9fa9459Szrj /* Either the target type has no index, or we aren't caching 862*a9fa9459Szrj this modifier. Either way we have no way of recording the 863*a9fa9459Szrj new type, so we don't bother to define one. */ 864*a9fa9459Szrj definition = info->type_stack->definition; 865*a9fa9459Szrj s = stab_pop_type (info); 866*a9fa9459Szrj buf = (char *) xmalloc (strlen (s) + 2); 867*a9fa9459Szrj sprintf (buf, "%c%s", mod, s); 868*a9fa9459Szrj free (s); 869*a9fa9459Szrj if (! stab_push_string (info, buf, 0, definition, size)) 870*a9fa9459Szrj return FALSE; 871*a9fa9459Szrj free (buf); 872*a9fa9459Szrj } 873*a9fa9459Szrj else 874*a9fa9459Szrj { 875*a9fa9459Szrj if ((size_t) targindex >= *cache_alloc) 876*a9fa9459Szrj { 877*a9fa9459Szrj size_t alloc; 878*a9fa9459Szrj 879*a9fa9459Szrj alloc = *cache_alloc; 880*a9fa9459Szrj if (alloc == 0) 881*a9fa9459Szrj alloc = 10; 882*a9fa9459Szrj while ((size_t) targindex >= alloc) 883*a9fa9459Szrj alloc *= 2; 884*a9fa9459Szrj *cache = (long *) xrealloc (*cache, alloc * sizeof (long)); 885*a9fa9459Szrj memset (*cache + *cache_alloc, 0, 886*a9fa9459Szrj (alloc - *cache_alloc) * sizeof (long)); 887*a9fa9459Szrj *cache_alloc = alloc; 888*a9fa9459Szrj } 889*a9fa9459Szrj 890*a9fa9459Szrj tindex = (*cache)[targindex]; 891*a9fa9459Szrj if (tindex != 0 && ! info->type_stack->definition) 892*a9fa9459Szrj { 893*a9fa9459Szrj /* We have already defined a modification of this type, and 894*a9fa9459Szrj the entry on the type stack is not a definition, so we 895*a9fa9459Szrj can safely discard it (we may have a definition on the 896*a9fa9459Szrj stack, even if we already defined a modification, if it 897*a9fa9459Szrj is a struct which we did not define at the time it was 898*a9fa9459Szrj referenced). */ 899*a9fa9459Szrj free (stab_pop_type (info)); 900*a9fa9459Szrj if (! stab_push_defined_type (info, tindex, size)) 901*a9fa9459Szrj return FALSE; 902*a9fa9459Szrj } 903*a9fa9459Szrj else 904*a9fa9459Szrj { 905*a9fa9459Szrj tindex = info->type_index; 906*a9fa9459Szrj ++info->type_index; 907*a9fa9459Szrj 908*a9fa9459Szrj s = stab_pop_type (info); 909*a9fa9459Szrj buf = (char *) xmalloc (strlen (s) + 20); 910*a9fa9459Szrj sprintf (buf, "%ld=%c%s", tindex, mod, s); 911*a9fa9459Szrj free (s); 912*a9fa9459Szrj 913*a9fa9459Szrj (*cache)[targindex] = tindex; 914*a9fa9459Szrj 915*a9fa9459Szrj if (! stab_push_string (info, buf, tindex, TRUE, size)) 916*a9fa9459Szrj return FALSE; 917*a9fa9459Szrj 918*a9fa9459Szrj free (buf); 919*a9fa9459Szrj } 920*a9fa9459Szrj } 921*a9fa9459Szrj 922*a9fa9459Szrj return TRUE; 923*a9fa9459Szrj } 924*a9fa9459Szrj 925*a9fa9459Szrj /* Push a pointer type. */ 926*a9fa9459Szrj 927*a9fa9459Szrj static bfd_boolean 928*a9fa9459Szrj stab_pointer_type (void *p) 929*a9fa9459Szrj { 930*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 931*a9fa9459Szrj 932*a9fa9459Szrj /* FIXME: The size should depend upon the architecture. */ 933*a9fa9459Szrj return stab_modify_type (info, '*', 4, &info->type_cache.pointer_types, 934*a9fa9459Szrj &info->type_cache.pointer_types_alloc); 935*a9fa9459Szrj } 936*a9fa9459Szrj 937*a9fa9459Szrj /* Push a function type. */ 938*a9fa9459Szrj 939*a9fa9459Szrj static bfd_boolean 940*a9fa9459Szrj stab_function_type (void *p, int argcount, 941*a9fa9459Szrj bfd_boolean varargs ATTRIBUTE_UNUSED) 942*a9fa9459Szrj { 943*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 944*a9fa9459Szrj int i; 945*a9fa9459Szrj 946*a9fa9459Szrj /* We have no way to represent the argument types, so we just 947*a9fa9459Szrj discard them. However, if they define new types, we must output 948*a9fa9459Szrj them. We do this by producing empty typedefs. */ 949*a9fa9459Szrj for (i = 0; i < argcount; i++) 950*a9fa9459Szrj { 951*a9fa9459Szrj if (! info->type_stack->definition) 952*a9fa9459Szrj free (stab_pop_type (info)); 953*a9fa9459Szrj else 954*a9fa9459Szrj { 955*a9fa9459Szrj char *s, *buf; 956*a9fa9459Szrj 957*a9fa9459Szrj s = stab_pop_type (info); 958*a9fa9459Szrj 959*a9fa9459Szrj buf = (char *) xmalloc (strlen (s) + 3); 960*a9fa9459Szrj sprintf (buf, ":t%s", s); 961*a9fa9459Szrj free (s); 962*a9fa9459Szrj 963*a9fa9459Szrj if (! stab_write_symbol (info, N_LSYM, 0, 0, buf)) 964*a9fa9459Szrj return FALSE; 965*a9fa9459Szrj 966*a9fa9459Szrj free (buf); 967*a9fa9459Szrj } 968*a9fa9459Szrj } 969*a9fa9459Szrj 970*a9fa9459Szrj return stab_modify_type (info, 'f', 0, &info->type_cache.function_types, 971*a9fa9459Szrj &info->type_cache.function_types_alloc); 972*a9fa9459Szrj } 973*a9fa9459Szrj 974*a9fa9459Szrj /* Push a reference type. */ 975*a9fa9459Szrj 976*a9fa9459Szrj static bfd_boolean 977*a9fa9459Szrj stab_reference_type (void *p) 978*a9fa9459Szrj { 979*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 980*a9fa9459Szrj 981*a9fa9459Szrj /* FIXME: The size should depend upon the architecture. */ 982*a9fa9459Szrj return stab_modify_type (info, '&', 4, &info->type_cache.reference_types, 983*a9fa9459Szrj &info->type_cache.reference_types_alloc); 984*a9fa9459Szrj } 985*a9fa9459Szrj 986*a9fa9459Szrj /* Push a range type. */ 987*a9fa9459Szrj 988*a9fa9459Szrj static bfd_boolean 989*a9fa9459Szrj stab_range_type (void *p, bfd_signed_vma low, bfd_signed_vma high) 990*a9fa9459Szrj { 991*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 992*a9fa9459Szrj bfd_boolean definition; 993*a9fa9459Szrj unsigned int size; 994*a9fa9459Szrj char *s, *buf; 995*a9fa9459Szrj 996*a9fa9459Szrj definition = info->type_stack->definition; 997*a9fa9459Szrj size = info->type_stack->size; 998*a9fa9459Szrj 999*a9fa9459Szrj s = stab_pop_type (info); 1000*a9fa9459Szrj buf = (char *) xmalloc (strlen (s) + 100); 1001*a9fa9459Szrj sprintf (buf, "r%s;%ld;%ld;", s, (long) low, (long) high); 1002*a9fa9459Szrj free (s); 1003*a9fa9459Szrj 1004*a9fa9459Szrj if (! stab_push_string (info, buf, 0, definition, size)) 1005*a9fa9459Szrj return FALSE; 1006*a9fa9459Szrj 1007*a9fa9459Szrj free (buf); 1008*a9fa9459Szrj 1009*a9fa9459Szrj return TRUE; 1010*a9fa9459Szrj } 1011*a9fa9459Szrj 1012*a9fa9459Szrj /* Push an array type. */ 1013*a9fa9459Szrj 1014*a9fa9459Szrj static bfd_boolean 1015*a9fa9459Szrj stab_array_type (void *p, bfd_signed_vma low, bfd_signed_vma high, 1016*a9fa9459Szrj bfd_boolean stringp) 1017*a9fa9459Szrj { 1018*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 1019*a9fa9459Szrj bfd_boolean definition; 1020*a9fa9459Szrj unsigned int element_size; 1021*a9fa9459Szrj char *range, *element, *buf; 1022*a9fa9459Szrj long tindex; 1023*a9fa9459Szrj unsigned int size; 1024*a9fa9459Szrj 1025*a9fa9459Szrj definition = info->type_stack->definition; 1026*a9fa9459Szrj range = stab_pop_type (info); 1027*a9fa9459Szrj 1028*a9fa9459Szrj definition = definition || info->type_stack->definition; 1029*a9fa9459Szrj element_size = info->type_stack->size; 1030*a9fa9459Szrj element = stab_pop_type (info); 1031*a9fa9459Szrj 1032*a9fa9459Szrj buf = (char *) xmalloc (strlen (range) + strlen (element) + 100); 1033*a9fa9459Szrj 1034*a9fa9459Szrj if (! stringp) 1035*a9fa9459Szrj { 1036*a9fa9459Szrj tindex = 0; 1037*a9fa9459Szrj *buf = '\0'; 1038*a9fa9459Szrj } 1039*a9fa9459Szrj else 1040*a9fa9459Szrj { 1041*a9fa9459Szrj /* We need to define a type in order to include the string 1042*a9fa9459Szrj attribute. */ 1043*a9fa9459Szrj tindex = info->type_index; 1044*a9fa9459Szrj ++info->type_index; 1045*a9fa9459Szrj definition = TRUE; 1046*a9fa9459Szrj sprintf (buf, "%ld=@S;", tindex); 1047*a9fa9459Szrj } 1048*a9fa9459Szrj 1049*a9fa9459Szrj sprintf (buf + strlen (buf), "ar%s;%ld;%ld;%s", 1050*a9fa9459Szrj range, (long) low, (long) high, element); 1051*a9fa9459Szrj free (range); 1052*a9fa9459Szrj free (element); 1053*a9fa9459Szrj 1054*a9fa9459Szrj if (high < low) 1055*a9fa9459Szrj size = 0; 1056*a9fa9459Szrj else 1057*a9fa9459Szrj size = element_size * ((high - low) + 1); 1058*a9fa9459Szrj if (! stab_push_string (info, buf, tindex, definition, size)) 1059*a9fa9459Szrj return FALSE; 1060*a9fa9459Szrj 1061*a9fa9459Szrj free (buf); 1062*a9fa9459Szrj 1063*a9fa9459Szrj return TRUE; 1064*a9fa9459Szrj } 1065*a9fa9459Szrj 1066*a9fa9459Szrj /* Push a set type. */ 1067*a9fa9459Szrj 1068*a9fa9459Szrj static bfd_boolean 1069*a9fa9459Szrj stab_set_type (void *p, bfd_boolean bitstringp) 1070*a9fa9459Szrj { 1071*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 1072*a9fa9459Szrj bfd_boolean definition; 1073*a9fa9459Szrj char *s, *buf; 1074*a9fa9459Szrj long tindex; 1075*a9fa9459Szrj 1076*a9fa9459Szrj definition = info->type_stack->definition; 1077*a9fa9459Szrj 1078*a9fa9459Szrj s = stab_pop_type (info); 1079*a9fa9459Szrj buf = (char *) xmalloc (strlen (s) + 30); 1080*a9fa9459Szrj 1081*a9fa9459Szrj if (! bitstringp) 1082*a9fa9459Szrj { 1083*a9fa9459Szrj *buf = '\0'; 1084*a9fa9459Szrj tindex = 0; 1085*a9fa9459Szrj } 1086*a9fa9459Szrj else 1087*a9fa9459Szrj { 1088*a9fa9459Szrj /* We need to define a type in order to include the string 1089*a9fa9459Szrj attribute. */ 1090*a9fa9459Szrj tindex = info->type_index; 1091*a9fa9459Szrj ++info->type_index; 1092*a9fa9459Szrj definition = TRUE; 1093*a9fa9459Szrj sprintf (buf, "%ld=@S;", tindex); 1094*a9fa9459Szrj } 1095*a9fa9459Szrj 1096*a9fa9459Szrj sprintf (buf + strlen (buf), "S%s", s); 1097*a9fa9459Szrj free (s); 1098*a9fa9459Szrj 1099*a9fa9459Szrj if (! stab_push_string (info, buf, tindex, definition, 0)) 1100*a9fa9459Szrj return FALSE; 1101*a9fa9459Szrj 1102*a9fa9459Szrj free (buf); 1103*a9fa9459Szrj 1104*a9fa9459Szrj return TRUE; 1105*a9fa9459Szrj } 1106*a9fa9459Szrj 1107*a9fa9459Szrj /* Push an offset type. */ 1108*a9fa9459Szrj 1109*a9fa9459Szrj static bfd_boolean 1110*a9fa9459Szrj stab_offset_type (void *p) 1111*a9fa9459Szrj { 1112*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 1113*a9fa9459Szrj bfd_boolean definition; 1114*a9fa9459Szrj char *target, *base, *buf; 1115*a9fa9459Szrj 1116*a9fa9459Szrj definition = info->type_stack->definition; 1117*a9fa9459Szrj target = stab_pop_type (info); 1118*a9fa9459Szrj 1119*a9fa9459Szrj definition = definition || info->type_stack->definition; 1120*a9fa9459Szrj base = stab_pop_type (info); 1121*a9fa9459Szrj 1122*a9fa9459Szrj buf = (char *) xmalloc (strlen (target) + strlen (base) + 3); 1123*a9fa9459Szrj sprintf (buf, "@%s,%s", base, target); 1124*a9fa9459Szrj free (base); 1125*a9fa9459Szrj free (target); 1126*a9fa9459Szrj 1127*a9fa9459Szrj if (! stab_push_string (info, buf, 0, definition, 0)) 1128*a9fa9459Szrj return FALSE; 1129*a9fa9459Szrj 1130*a9fa9459Szrj free (buf); 1131*a9fa9459Szrj 1132*a9fa9459Szrj return TRUE; 1133*a9fa9459Szrj } 1134*a9fa9459Szrj 1135*a9fa9459Szrj /* Push a method type. */ 1136*a9fa9459Szrj 1137*a9fa9459Szrj static bfd_boolean 1138*a9fa9459Szrj stab_method_type (void *p, bfd_boolean domainp, int argcount, 1139*a9fa9459Szrj bfd_boolean varargs) 1140*a9fa9459Szrj { 1141*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 1142*a9fa9459Szrj bfd_boolean definition; 1143*a9fa9459Szrj char *domain, *return_type, *buf; 1144*a9fa9459Szrj char **args; 1145*a9fa9459Szrj int i; 1146*a9fa9459Szrj size_t len; 1147*a9fa9459Szrj 1148*a9fa9459Szrj /* We don't bother with stub method types, because that would 1149*a9fa9459Szrj require a mangler for C++ argument types. This will waste space 1150*a9fa9459Szrj in the debugging output. */ 1151*a9fa9459Szrj 1152*a9fa9459Szrj /* We need a domain. I'm not sure DOMAINP can ever be false, 1153*a9fa9459Szrj anyhow. */ 1154*a9fa9459Szrj if (! domainp) 1155*a9fa9459Szrj { 1156*a9fa9459Szrj if (! stab_empty_type (p)) 1157*a9fa9459Szrj return FALSE; 1158*a9fa9459Szrj } 1159*a9fa9459Szrj 1160*a9fa9459Szrj definition = info->type_stack->definition; 1161*a9fa9459Szrj domain = stab_pop_type (info); 1162*a9fa9459Szrj 1163*a9fa9459Szrj /* A non-varargs function is indicated by making the last parameter 1164*a9fa9459Szrj type be void. */ 1165*a9fa9459Szrj 1166*a9fa9459Szrj if (argcount < 0) 1167*a9fa9459Szrj { 1168*a9fa9459Szrj args = NULL; 1169*a9fa9459Szrj argcount = 0; 1170*a9fa9459Szrj } 1171*a9fa9459Szrj else if (argcount == 0) 1172*a9fa9459Szrj { 1173*a9fa9459Szrj if (varargs) 1174*a9fa9459Szrj args = NULL; 1175*a9fa9459Szrj else 1176*a9fa9459Szrj { 1177*a9fa9459Szrj args = (char **) xmalloc (1 * sizeof (*args)); 1178*a9fa9459Szrj if (! stab_empty_type (p)) 1179*a9fa9459Szrj return FALSE; 1180*a9fa9459Szrj definition = definition || info->type_stack->definition; 1181*a9fa9459Szrj args[0] = stab_pop_type (info); 1182*a9fa9459Szrj argcount = 1; 1183*a9fa9459Szrj } 1184*a9fa9459Szrj } 1185*a9fa9459Szrj else 1186*a9fa9459Szrj { 1187*a9fa9459Szrj args = (char **) xmalloc ((argcount + 1) * sizeof (*args)); 1188*a9fa9459Szrj for (i = argcount - 1; i >= 0; i--) 1189*a9fa9459Szrj { 1190*a9fa9459Szrj definition = definition || info->type_stack->definition; 1191*a9fa9459Szrj args[i] = stab_pop_type (info); 1192*a9fa9459Szrj } 1193*a9fa9459Szrj if (! varargs) 1194*a9fa9459Szrj { 1195*a9fa9459Szrj if (! stab_empty_type (p)) 1196*a9fa9459Szrj return FALSE; 1197*a9fa9459Szrj definition = definition || info->type_stack->definition; 1198*a9fa9459Szrj args[argcount] = stab_pop_type (info); 1199*a9fa9459Szrj ++argcount; 1200*a9fa9459Szrj } 1201*a9fa9459Szrj } 1202*a9fa9459Szrj 1203*a9fa9459Szrj definition = definition || info->type_stack->definition; 1204*a9fa9459Szrj return_type = stab_pop_type (info); 1205*a9fa9459Szrj 1206*a9fa9459Szrj len = strlen (domain) + strlen (return_type) + 10; 1207*a9fa9459Szrj for (i = 0; i < argcount; i++) 1208*a9fa9459Szrj len += strlen (args[i]); 1209*a9fa9459Szrj 1210*a9fa9459Szrj buf = (char *) xmalloc (len); 1211*a9fa9459Szrj 1212*a9fa9459Szrj sprintf (buf, "#%s,%s", domain, return_type); 1213*a9fa9459Szrj free (domain); 1214*a9fa9459Szrj free (return_type); 1215*a9fa9459Szrj for (i = 0; i < argcount; i++) 1216*a9fa9459Szrj { 1217*a9fa9459Szrj strcat (buf, ","); 1218*a9fa9459Szrj strcat (buf, args[i]); 1219*a9fa9459Szrj free (args[i]); 1220*a9fa9459Szrj } 1221*a9fa9459Szrj strcat (buf, ";"); 1222*a9fa9459Szrj 1223*a9fa9459Szrj if (args != NULL) 1224*a9fa9459Szrj free (args); 1225*a9fa9459Szrj 1226*a9fa9459Szrj if (! stab_push_string (info, buf, 0, definition, 0)) 1227*a9fa9459Szrj return FALSE; 1228*a9fa9459Szrj 1229*a9fa9459Szrj free (buf); 1230*a9fa9459Szrj 1231*a9fa9459Szrj return TRUE; 1232*a9fa9459Szrj } 1233*a9fa9459Szrj 1234*a9fa9459Szrj /* Push a const version of a type. */ 1235*a9fa9459Szrj 1236*a9fa9459Szrj static bfd_boolean 1237*a9fa9459Szrj stab_const_type (void *p) 1238*a9fa9459Szrj { 1239*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 1240*a9fa9459Szrj 1241*a9fa9459Szrj return stab_modify_type (info, 'k', info->type_stack->size, 1242*a9fa9459Szrj (long **) NULL, (size_t *) NULL); 1243*a9fa9459Szrj } 1244*a9fa9459Szrj 1245*a9fa9459Szrj /* Push a volatile version of a type. */ 1246*a9fa9459Szrj 1247*a9fa9459Szrj static bfd_boolean 1248*a9fa9459Szrj stab_volatile_type (void *p) 1249*a9fa9459Szrj { 1250*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 1251*a9fa9459Szrj 1252*a9fa9459Szrj return stab_modify_type (info, 'B', info->type_stack->size, 1253*a9fa9459Szrj (long **) NULL, (size_t *) NULL); 1254*a9fa9459Szrj } 1255*a9fa9459Szrj 1256*a9fa9459Szrj /* Get the type index to use for a struct/union/class ID. This should 1257*a9fa9459Szrj return -1 if it fails. */ 1258*a9fa9459Szrj 1259*a9fa9459Szrj static long 1260*a9fa9459Szrj stab_get_struct_index (struct stab_write_handle *info, const char *tag, 1261*a9fa9459Szrj unsigned int id, enum debug_type_kind kind, 1262*a9fa9459Szrj unsigned int *psize) 1263*a9fa9459Szrj { 1264*a9fa9459Szrj if (id >= info->type_cache.struct_types_alloc) 1265*a9fa9459Szrj { 1266*a9fa9459Szrj size_t alloc; 1267*a9fa9459Szrj 1268*a9fa9459Szrj alloc = info->type_cache.struct_types_alloc; 1269*a9fa9459Szrj if (alloc == 0) 1270*a9fa9459Szrj alloc = 10; 1271*a9fa9459Szrj while (id >= alloc) 1272*a9fa9459Szrj alloc *= 2; 1273*a9fa9459Szrj info->type_cache.struct_types = 1274*a9fa9459Szrj (struct stab_tag *) xrealloc (info->type_cache.struct_types, 1275*a9fa9459Szrj alloc * sizeof (struct stab_tag)); 1276*a9fa9459Szrj memset ((info->type_cache.struct_types 1277*a9fa9459Szrj + info->type_cache.struct_types_alloc), 1278*a9fa9459Szrj 0, 1279*a9fa9459Szrj ((alloc - info->type_cache.struct_types_alloc) 1280*a9fa9459Szrj * sizeof (struct stab_tag))); 1281*a9fa9459Szrj info->type_cache.struct_types_alloc = alloc; 1282*a9fa9459Szrj } 1283*a9fa9459Szrj 1284*a9fa9459Szrj if (info->type_cache.struct_types[id].index == 0) 1285*a9fa9459Szrj { 1286*a9fa9459Szrj info->type_cache.struct_types[id].index = info->type_index; 1287*a9fa9459Szrj ++info->type_index; 1288*a9fa9459Szrj info->type_cache.struct_types[id].tag = tag; 1289*a9fa9459Szrj info->type_cache.struct_types[id].kind = kind; 1290*a9fa9459Szrj } 1291*a9fa9459Szrj 1292*a9fa9459Szrj if (kind == DEBUG_KIND_ILLEGAL) 1293*a9fa9459Szrj { 1294*a9fa9459Szrj /* This is a definition of the struct. */ 1295*a9fa9459Szrj info->type_cache.struct_types[id].kind = kind; 1296*a9fa9459Szrj info->type_cache.struct_types[id].size = *psize; 1297*a9fa9459Szrj } 1298*a9fa9459Szrj else 1299*a9fa9459Szrj *psize = info->type_cache.struct_types[id].size; 1300*a9fa9459Szrj 1301*a9fa9459Szrj return info->type_cache.struct_types[id].index; 1302*a9fa9459Szrj } 1303*a9fa9459Szrj 1304*a9fa9459Szrj /* Start outputting a struct. We ignore the tag, and handle it in 1305*a9fa9459Szrj stab_tag. */ 1306*a9fa9459Szrj 1307*a9fa9459Szrj static bfd_boolean 1308*a9fa9459Szrj stab_start_struct_type (void *p, const char *tag, unsigned int id, 1309*a9fa9459Szrj bfd_boolean structp, unsigned int size) 1310*a9fa9459Szrj { 1311*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 1312*a9fa9459Szrj long tindex; 1313*a9fa9459Szrj bfd_boolean definition; 1314*a9fa9459Szrj char buf[40]; 1315*a9fa9459Szrj 1316*a9fa9459Szrj if (id == 0) 1317*a9fa9459Szrj { 1318*a9fa9459Szrj tindex = 0; 1319*a9fa9459Szrj *buf = '\0'; 1320*a9fa9459Szrj definition = FALSE; 1321*a9fa9459Szrj } 1322*a9fa9459Szrj else 1323*a9fa9459Szrj { 1324*a9fa9459Szrj tindex = stab_get_struct_index (info, tag, id, DEBUG_KIND_ILLEGAL, 1325*a9fa9459Szrj &size); 1326*a9fa9459Szrj if (tindex < 0) 1327*a9fa9459Szrj return FALSE; 1328*a9fa9459Szrj sprintf (buf, "%ld=", tindex); 1329*a9fa9459Szrj definition = TRUE; 1330*a9fa9459Szrj } 1331*a9fa9459Szrj 1332*a9fa9459Szrj sprintf (buf + strlen (buf), "%c%u", 1333*a9fa9459Szrj structp ? 's' : 'u', 1334*a9fa9459Szrj size); 1335*a9fa9459Szrj 1336*a9fa9459Szrj if (! stab_push_string (info, buf, tindex, definition, size)) 1337*a9fa9459Szrj return FALSE; 1338*a9fa9459Szrj 1339*a9fa9459Szrj info->type_stack->fields = (char *) xmalloc (1); 1340*a9fa9459Szrj info->type_stack->fields[0] = '\0'; 1341*a9fa9459Szrj 1342*a9fa9459Szrj return TRUE; 1343*a9fa9459Szrj } 1344*a9fa9459Szrj 1345*a9fa9459Szrj /* Add a field to a struct. */ 1346*a9fa9459Szrj 1347*a9fa9459Szrj static bfd_boolean 1348*a9fa9459Szrj stab_struct_field (void *p, const char *name, bfd_vma bitpos, 1349*a9fa9459Szrj bfd_vma bitsize, enum debug_visibility visibility) 1350*a9fa9459Szrj { 1351*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 1352*a9fa9459Szrj bfd_boolean definition; 1353*a9fa9459Szrj unsigned int size; 1354*a9fa9459Szrj char *s, *n; 1355*a9fa9459Szrj const char *vis; 1356*a9fa9459Szrj 1357*a9fa9459Szrj definition = info->type_stack->definition; 1358*a9fa9459Szrj size = info->type_stack->size; 1359*a9fa9459Szrj s = stab_pop_type (info); 1360*a9fa9459Szrj 1361*a9fa9459Szrj /* Add this field to the end of the current struct fields, which is 1362*a9fa9459Szrj currently on the top of the stack. */ 1363*a9fa9459Szrj 1364*a9fa9459Szrj assert (info->type_stack->fields != NULL); 1365*a9fa9459Szrj n = (char *) xmalloc (strlen (info->type_stack->fields) 1366*a9fa9459Szrj + strlen (name) 1367*a9fa9459Szrj + strlen (s) 1368*a9fa9459Szrj + 50); 1369*a9fa9459Szrj 1370*a9fa9459Szrj switch (visibility) 1371*a9fa9459Szrj { 1372*a9fa9459Szrj default: 1373*a9fa9459Szrj abort (); 1374*a9fa9459Szrj 1375*a9fa9459Szrj case DEBUG_VISIBILITY_PUBLIC: 1376*a9fa9459Szrj vis = ""; 1377*a9fa9459Szrj break; 1378*a9fa9459Szrj 1379*a9fa9459Szrj case DEBUG_VISIBILITY_PRIVATE: 1380*a9fa9459Szrj vis = "/0"; 1381*a9fa9459Szrj break; 1382*a9fa9459Szrj 1383*a9fa9459Szrj case DEBUG_VISIBILITY_PROTECTED: 1384*a9fa9459Szrj vis = "/1"; 1385*a9fa9459Szrj break; 1386*a9fa9459Szrj } 1387*a9fa9459Szrj 1388*a9fa9459Szrj if (bitsize == 0) 1389*a9fa9459Szrj { 1390*a9fa9459Szrj bitsize = size * 8; 1391*a9fa9459Szrj if (bitsize == 0) 1392*a9fa9459Szrj non_fatal (_("%s: warning: unknown size for field `%s' in struct"), 1393*a9fa9459Szrj bfd_get_filename (info->abfd), name); 1394*a9fa9459Szrj } 1395*a9fa9459Szrj 1396*a9fa9459Szrj sprintf (n, "%s%s:%s%s,%ld,%ld;", info->type_stack->fields, name, vis, s, 1397*a9fa9459Szrj (long) bitpos, (long) bitsize); 1398*a9fa9459Szrj 1399*a9fa9459Szrj free (info->type_stack->fields); 1400*a9fa9459Szrj info->type_stack->fields = n; 1401*a9fa9459Szrj 1402*a9fa9459Szrj if (definition) 1403*a9fa9459Szrj info->type_stack->definition = TRUE; 1404*a9fa9459Szrj 1405*a9fa9459Szrj return TRUE; 1406*a9fa9459Szrj } 1407*a9fa9459Szrj 1408*a9fa9459Szrj /* Finish up a struct. */ 1409*a9fa9459Szrj 1410*a9fa9459Szrj static bfd_boolean 1411*a9fa9459Szrj stab_end_struct_type (void *p) 1412*a9fa9459Szrj { 1413*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 1414*a9fa9459Szrj bfd_boolean definition; 1415*a9fa9459Szrj long tindex; 1416*a9fa9459Szrj unsigned int size; 1417*a9fa9459Szrj char *fields, *first, *buf; 1418*a9fa9459Szrj 1419*a9fa9459Szrj assert (info->type_stack != NULL && info->type_stack->fields != NULL); 1420*a9fa9459Szrj 1421*a9fa9459Szrj definition = info->type_stack->definition; 1422*a9fa9459Szrj tindex = info->type_stack->index; 1423*a9fa9459Szrj size = info->type_stack->size; 1424*a9fa9459Szrj fields = info->type_stack->fields; 1425*a9fa9459Szrj first = stab_pop_type (info); 1426*a9fa9459Szrj 1427*a9fa9459Szrj buf = (char *) xmalloc (strlen (first) + strlen (fields) + 2); 1428*a9fa9459Szrj sprintf (buf, "%s%s;", first, fields); 1429*a9fa9459Szrj free (first); 1430*a9fa9459Szrj free (fields); 1431*a9fa9459Szrj 1432*a9fa9459Szrj if (! stab_push_string (info, buf, tindex, definition, size)) 1433*a9fa9459Szrj return FALSE; 1434*a9fa9459Szrj 1435*a9fa9459Szrj free (buf); 1436*a9fa9459Szrj 1437*a9fa9459Szrj return TRUE; 1438*a9fa9459Szrj } 1439*a9fa9459Szrj 1440*a9fa9459Szrj /* Start outputting a class. */ 1441*a9fa9459Szrj 1442*a9fa9459Szrj static bfd_boolean 1443*a9fa9459Szrj stab_start_class_type (void *p, const char *tag, unsigned int id, bfd_boolean structp, unsigned int size, bfd_boolean vptr, bfd_boolean ownvptr) 1444*a9fa9459Szrj { 1445*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 1446*a9fa9459Szrj bfd_boolean definition; 1447*a9fa9459Szrj char *vstring; 1448*a9fa9459Szrj 1449*a9fa9459Szrj if (! vptr || ownvptr) 1450*a9fa9459Szrj { 1451*a9fa9459Szrj definition = FALSE; 1452*a9fa9459Szrj vstring = NULL; 1453*a9fa9459Szrj } 1454*a9fa9459Szrj else 1455*a9fa9459Szrj { 1456*a9fa9459Szrj definition = info->type_stack->definition; 1457*a9fa9459Szrj vstring = stab_pop_type (info); 1458*a9fa9459Szrj } 1459*a9fa9459Szrj 1460*a9fa9459Szrj if (! stab_start_struct_type (p, tag, id, structp, size)) 1461*a9fa9459Szrj return FALSE; 1462*a9fa9459Szrj 1463*a9fa9459Szrj if (vptr) 1464*a9fa9459Szrj { 1465*a9fa9459Szrj char *vtable; 1466*a9fa9459Szrj 1467*a9fa9459Szrj if (ownvptr) 1468*a9fa9459Szrj { 1469*a9fa9459Szrj assert (info->type_stack->index > 0); 1470*a9fa9459Szrj vtable = (char *) xmalloc (20); 1471*a9fa9459Szrj sprintf (vtable, "~%%%ld", info->type_stack->index); 1472*a9fa9459Szrj } 1473*a9fa9459Szrj else 1474*a9fa9459Szrj { 1475*a9fa9459Szrj vtable = (char *) xmalloc (strlen (vstring) + 3); 1476*a9fa9459Szrj sprintf (vtable, "~%%%s", vstring); 1477*a9fa9459Szrj free (vstring); 1478*a9fa9459Szrj } 1479*a9fa9459Szrj 1480*a9fa9459Szrj info->type_stack->vtable = vtable; 1481*a9fa9459Szrj } 1482*a9fa9459Szrj 1483*a9fa9459Szrj if (definition) 1484*a9fa9459Szrj info->type_stack->definition = TRUE; 1485*a9fa9459Szrj 1486*a9fa9459Szrj return TRUE; 1487*a9fa9459Szrj } 1488*a9fa9459Szrj 1489*a9fa9459Szrj /* Add a static member to the class on the type stack. */ 1490*a9fa9459Szrj 1491*a9fa9459Szrj static bfd_boolean 1492*a9fa9459Szrj stab_class_static_member (void *p, const char *name, const char *physname, 1493*a9fa9459Szrj enum debug_visibility visibility) 1494*a9fa9459Szrj { 1495*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 1496*a9fa9459Szrj bfd_boolean definition; 1497*a9fa9459Szrj char *s, *n; 1498*a9fa9459Szrj const char *vis; 1499*a9fa9459Szrj 1500*a9fa9459Szrj definition = info->type_stack->definition; 1501*a9fa9459Szrj s = stab_pop_type (info); 1502*a9fa9459Szrj 1503*a9fa9459Szrj /* Add this field to the end of the current struct fields, which is 1504*a9fa9459Szrj currently on the top of the stack. */ 1505*a9fa9459Szrj 1506*a9fa9459Szrj assert (info->type_stack->fields != NULL); 1507*a9fa9459Szrj n = (char *) xmalloc (strlen (info->type_stack->fields) 1508*a9fa9459Szrj + strlen (name) 1509*a9fa9459Szrj + strlen (s) 1510*a9fa9459Szrj + strlen (physname) 1511*a9fa9459Szrj + 10); 1512*a9fa9459Szrj 1513*a9fa9459Szrj switch (visibility) 1514*a9fa9459Szrj { 1515*a9fa9459Szrj default: 1516*a9fa9459Szrj abort (); 1517*a9fa9459Szrj 1518*a9fa9459Szrj case DEBUG_VISIBILITY_PUBLIC: 1519*a9fa9459Szrj vis = ""; 1520*a9fa9459Szrj break; 1521*a9fa9459Szrj 1522*a9fa9459Szrj case DEBUG_VISIBILITY_PRIVATE: 1523*a9fa9459Szrj vis = "/0"; 1524*a9fa9459Szrj break; 1525*a9fa9459Szrj 1526*a9fa9459Szrj case DEBUG_VISIBILITY_PROTECTED: 1527*a9fa9459Szrj vis = "/1"; 1528*a9fa9459Szrj break; 1529*a9fa9459Szrj } 1530*a9fa9459Szrj 1531*a9fa9459Szrj sprintf (n, "%s%s:%s%s:%s;", info->type_stack->fields, name, vis, s, 1532*a9fa9459Szrj physname); 1533*a9fa9459Szrj 1534*a9fa9459Szrj free (info->type_stack->fields); 1535*a9fa9459Szrj info->type_stack->fields = n; 1536*a9fa9459Szrj 1537*a9fa9459Szrj if (definition) 1538*a9fa9459Szrj info->type_stack->definition = TRUE; 1539*a9fa9459Szrj 1540*a9fa9459Szrj return TRUE; 1541*a9fa9459Szrj } 1542*a9fa9459Szrj 1543*a9fa9459Szrj /* Add a base class to the class on the type stack. */ 1544*a9fa9459Szrj 1545*a9fa9459Szrj static bfd_boolean 1546*a9fa9459Szrj stab_class_baseclass (void *p, bfd_vma bitpos, bfd_boolean is_virtual, 1547*a9fa9459Szrj enum debug_visibility visibility) 1548*a9fa9459Szrj { 1549*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 1550*a9fa9459Szrj bfd_boolean definition; 1551*a9fa9459Szrj char *s; 1552*a9fa9459Szrj char *buf; 1553*a9fa9459Szrj unsigned int c; 1554*a9fa9459Szrj char **baseclasses; 1555*a9fa9459Szrj 1556*a9fa9459Szrj definition = info->type_stack->definition; 1557*a9fa9459Szrj s = stab_pop_type (info); 1558*a9fa9459Szrj 1559*a9fa9459Szrj /* Build the base class specifier. */ 1560*a9fa9459Szrj 1561*a9fa9459Szrj buf = (char *) xmalloc (strlen (s) + 25); 1562*a9fa9459Szrj buf[0] = is_virtual ? '1' : '0'; 1563*a9fa9459Szrj switch (visibility) 1564*a9fa9459Szrj { 1565*a9fa9459Szrj default: 1566*a9fa9459Szrj abort (); 1567*a9fa9459Szrj 1568*a9fa9459Szrj case DEBUG_VISIBILITY_PRIVATE: 1569*a9fa9459Szrj buf[1] = '0'; 1570*a9fa9459Szrj break; 1571*a9fa9459Szrj 1572*a9fa9459Szrj case DEBUG_VISIBILITY_PROTECTED: 1573*a9fa9459Szrj buf[1] = '1'; 1574*a9fa9459Szrj break; 1575*a9fa9459Szrj 1576*a9fa9459Szrj case DEBUG_VISIBILITY_PUBLIC: 1577*a9fa9459Szrj buf[1] = '2'; 1578*a9fa9459Szrj break; 1579*a9fa9459Szrj } 1580*a9fa9459Szrj 1581*a9fa9459Szrj sprintf (buf + 2, "%ld,%s;", (long) bitpos, s); 1582*a9fa9459Szrj free (s); 1583*a9fa9459Szrj 1584*a9fa9459Szrj /* Add the new baseclass to the existing ones. */ 1585*a9fa9459Szrj 1586*a9fa9459Szrj assert (info->type_stack != NULL && info->type_stack->fields != NULL); 1587*a9fa9459Szrj 1588*a9fa9459Szrj if (info->type_stack->baseclasses == NULL) 1589*a9fa9459Szrj c = 0; 1590*a9fa9459Szrj else 1591*a9fa9459Szrj { 1592*a9fa9459Szrj c = 0; 1593*a9fa9459Szrj while (info->type_stack->baseclasses[c] != NULL) 1594*a9fa9459Szrj ++c; 1595*a9fa9459Szrj } 1596*a9fa9459Szrj 1597*a9fa9459Szrj baseclasses = (char **) xrealloc (info->type_stack->baseclasses, 1598*a9fa9459Szrj (c + 2) * sizeof (*baseclasses)); 1599*a9fa9459Szrj baseclasses[c] = buf; 1600*a9fa9459Szrj baseclasses[c + 1] = NULL; 1601*a9fa9459Szrj 1602*a9fa9459Szrj info->type_stack->baseclasses = baseclasses; 1603*a9fa9459Szrj 1604*a9fa9459Szrj if (definition) 1605*a9fa9459Szrj info->type_stack->definition = TRUE; 1606*a9fa9459Szrj 1607*a9fa9459Szrj return TRUE; 1608*a9fa9459Szrj } 1609*a9fa9459Szrj 1610*a9fa9459Szrj /* Start adding a method to the class on the type stack. */ 1611*a9fa9459Szrj 1612*a9fa9459Szrj static bfd_boolean 1613*a9fa9459Szrj stab_class_start_method (void *p, const char *name) 1614*a9fa9459Szrj { 1615*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 1616*a9fa9459Szrj char *m; 1617*a9fa9459Szrj 1618*a9fa9459Szrj assert (info->type_stack != NULL && info->type_stack->fields != NULL); 1619*a9fa9459Szrj 1620*a9fa9459Szrj if (info->type_stack->methods == NULL) 1621*a9fa9459Szrj { 1622*a9fa9459Szrj m = (char *) xmalloc (strlen (name) + 3); 1623*a9fa9459Szrj *m = '\0'; 1624*a9fa9459Szrj } 1625*a9fa9459Szrj else 1626*a9fa9459Szrj { 1627*a9fa9459Szrj m = (char *) xrealloc (info->type_stack->methods, 1628*a9fa9459Szrj (strlen (info->type_stack->methods) 1629*a9fa9459Szrj + strlen (name) 1630*a9fa9459Szrj + 4)); 1631*a9fa9459Szrj } 1632*a9fa9459Szrj 1633*a9fa9459Szrj sprintf (m + strlen (m), "%s::", name); 1634*a9fa9459Szrj 1635*a9fa9459Szrj info->type_stack->methods = m; 1636*a9fa9459Szrj 1637*a9fa9459Szrj return TRUE; 1638*a9fa9459Szrj } 1639*a9fa9459Szrj 1640*a9fa9459Szrj /* Add a variant, either static or not, to the current method. */ 1641*a9fa9459Szrj 1642*a9fa9459Szrj static bfd_boolean 1643*a9fa9459Szrj stab_class_method_var (struct stab_write_handle *info, const char *physname, 1644*a9fa9459Szrj enum debug_visibility visibility, 1645*a9fa9459Szrj bfd_boolean staticp, bfd_boolean constp, 1646*a9fa9459Szrj bfd_boolean volatilep, bfd_vma voffset, 1647*a9fa9459Szrj bfd_boolean contextp) 1648*a9fa9459Szrj { 1649*a9fa9459Szrj bfd_boolean definition; 1650*a9fa9459Szrj char *type; 1651*a9fa9459Szrj char *context = NULL; 1652*a9fa9459Szrj char visc, qualc, typec; 1653*a9fa9459Szrj 1654*a9fa9459Szrj definition = info->type_stack->definition; 1655*a9fa9459Szrj type = stab_pop_type (info); 1656*a9fa9459Szrj 1657*a9fa9459Szrj if (contextp) 1658*a9fa9459Szrj { 1659*a9fa9459Szrj definition = definition || info->type_stack->definition; 1660*a9fa9459Szrj context = stab_pop_type (info); 1661*a9fa9459Szrj } 1662*a9fa9459Szrj 1663*a9fa9459Szrj assert (info->type_stack != NULL && info->type_stack->methods != NULL); 1664*a9fa9459Szrj 1665*a9fa9459Szrj switch (visibility) 1666*a9fa9459Szrj { 1667*a9fa9459Szrj default: 1668*a9fa9459Szrj abort (); 1669*a9fa9459Szrj 1670*a9fa9459Szrj case DEBUG_VISIBILITY_PRIVATE: 1671*a9fa9459Szrj visc = '0'; 1672*a9fa9459Szrj break; 1673*a9fa9459Szrj 1674*a9fa9459Szrj case DEBUG_VISIBILITY_PROTECTED: 1675*a9fa9459Szrj visc = '1'; 1676*a9fa9459Szrj break; 1677*a9fa9459Szrj 1678*a9fa9459Szrj case DEBUG_VISIBILITY_PUBLIC: 1679*a9fa9459Szrj visc = '2'; 1680*a9fa9459Szrj break; 1681*a9fa9459Szrj } 1682*a9fa9459Szrj 1683*a9fa9459Szrj if (constp) 1684*a9fa9459Szrj { 1685*a9fa9459Szrj if (volatilep) 1686*a9fa9459Szrj qualc = 'D'; 1687*a9fa9459Szrj else 1688*a9fa9459Szrj qualc = 'B'; 1689*a9fa9459Szrj } 1690*a9fa9459Szrj else 1691*a9fa9459Szrj { 1692*a9fa9459Szrj if (volatilep) 1693*a9fa9459Szrj qualc = 'C'; 1694*a9fa9459Szrj else 1695*a9fa9459Szrj qualc = 'A'; 1696*a9fa9459Szrj } 1697*a9fa9459Szrj 1698*a9fa9459Szrj if (staticp) 1699*a9fa9459Szrj typec = '?'; 1700*a9fa9459Szrj else if (! contextp) 1701*a9fa9459Szrj typec = '.'; 1702*a9fa9459Szrj else 1703*a9fa9459Szrj typec = '*'; 1704*a9fa9459Szrj 1705*a9fa9459Szrj info->type_stack->methods = 1706*a9fa9459Szrj (char *) xrealloc (info->type_stack->methods, 1707*a9fa9459Szrj (strlen (info->type_stack->methods) 1708*a9fa9459Szrj + strlen (type) 1709*a9fa9459Szrj + strlen (physname) 1710*a9fa9459Szrj + (contextp ? strlen (context) : 0) 1711*a9fa9459Szrj + 40)); 1712*a9fa9459Szrj 1713*a9fa9459Szrj sprintf (info->type_stack->methods + strlen (info->type_stack->methods), 1714*a9fa9459Szrj "%s:%s;%c%c%c", type, physname, visc, qualc, typec); 1715*a9fa9459Szrj free (type); 1716*a9fa9459Szrj 1717*a9fa9459Szrj if (contextp) 1718*a9fa9459Szrj { 1719*a9fa9459Szrj sprintf (info->type_stack->methods + strlen (info->type_stack->methods), 1720*a9fa9459Szrj "%ld;%s;", (long) voffset, context); 1721*a9fa9459Szrj free (context); 1722*a9fa9459Szrj } 1723*a9fa9459Szrj 1724*a9fa9459Szrj if (definition) 1725*a9fa9459Szrj info->type_stack->definition = TRUE; 1726*a9fa9459Szrj 1727*a9fa9459Szrj return TRUE; 1728*a9fa9459Szrj } 1729*a9fa9459Szrj 1730*a9fa9459Szrj /* Add a variant to the current method. */ 1731*a9fa9459Szrj 1732*a9fa9459Szrj static bfd_boolean 1733*a9fa9459Szrj stab_class_method_variant (void *p, const char *physname, 1734*a9fa9459Szrj enum debug_visibility visibility, 1735*a9fa9459Szrj bfd_boolean constp, bfd_boolean volatilep, 1736*a9fa9459Szrj bfd_vma voffset, bfd_boolean contextp) 1737*a9fa9459Szrj { 1738*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 1739*a9fa9459Szrj 1740*a9fa9459Szrj return stab_class_method_var (info, physname, visibility, FALSE, constp, 1741*a9fa9459Szrj volatilep, voffset, contextp); 1742*a9fa9459Szrj } 1743*a9fa9459Szrj 1744*a9fa9459Szrj /* Add a static variant to the current method. */ 1745*a9fa9459Szrj 1746*a9fa9459Szrj static bfd_boolean 1747*a9fa9459Szrj stab_class_static_method_variant (void *p, const char *physname, 1748*a9fa9459Szrj enum debug_visibility visibility, 1749*a9fa9459Szrj bfd_boolean constp, bfd_boolean volatilep) 1750*a9fa9459Szrj { 1751*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 1752*a9fa9459Szrj 1753*a9fa9459Szrj return stab_class_method_var (info, physname, visibility, TRUE, constp, 1754*a9fa9459Szrj volatilep, 0, FALSE); 1755*a9fa9459Szrj } 1756*a9fa9459Szrj 1757*a9fa9459Szrj /* Finish up a method. */ 1758*a9fa9459Szrj 1759*a9fa9459Szrj static bfd_boolean 1760*a9fa9459Szrj stab_class_end_method (void *p) 1761*a9fa9459Szrj { 1762*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 1763*a9fa9459Szrj 1764*a9fa9459Szrj assert (info->type_stack != NULL && info->type_stack->methods != NULL); 1765*a9fa9459Szrj 1766*a9fa9459Szrj /* We allocated enough room on info->type_stack->methods to add the 1767*a9fa9459Szrj trailing semicolon. */ 1768*a9fa9459Szrj strcat (info->type_stack->methods, ";"); 1769*a9fa9459Szrj 1770*a9fa9459Szrj return TRUE; 1771*a9fa9459Szrj } 1772*a9fa9459Szrj 1773*a9fa9459Szrj /* Finish up a class. */ 1774*a9fa9459Szrj 1775*a9fa9459Szrj static bfd_boolean 1776*a9fa9459Szrj stab_end_class_type (void *p) 1777*a9fa9459Szrj { 1778*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 1779*a9fa9459Szrj size_t len; 1780*a9fa9459Szrj unsigned int i = 0; 1781*a9fa9459Szrj char *buf; 1782*a9fa9459Szrj 1783*a9fa9459Szrj assert (info->type_stack != NULL && info->type_stack->fields != NULL); 1784*a9fa9459Szrj 1785*a9fa9459Szrj /* Work out the size we need to allocate for the class definition. */ 1786*a9fa9459Szrj 1787*a9fa9459Szrj len = (strlen (info->type_stack->string) 1788*a9fa9459Szrj + strlen (info->type_stack->fields) 1789*a9fa9459Szrj + 10); 1790*a9fa9459Szrj if (info->type_stack->baseclasses != NULL) 1791*a9fa9459Szrj { 1792*a9fa9459Szrj len += 20; 1793*a9fa9459Szrj for (i = 0; info->type_stack->baseclasses[i] != NULL; i++) 1794*a9fa9459Szrj len += strlen (info->type_stack->baseclasses[i]); 1795*a9fa9459Szrj } 1796*a9fa9459Szrj if (info->type_stack->methods != NULL) 1797*a9fa9459Szrj len += strlen (info->type_stack->methods); 1798*a9fa9459Szrj if (info->type_stack->vtable != NULL) 1799*a9fa9459Szrj len += strlen (info->type_stack->vtable); 1800*a9fa9459Szrj 1801*a9fa9459Szrj /* Build the class definition. */ 1802*a9fa9459Szrj 1803*a9fa9459Szrj buf = (char *) xmalloc (len); 1804*a9fa9459Szrj 1805*a9fa9459Szrj strcpy (buf, info->type_stack->string); 1806*a9fa9459Szrj 1807*a9fa9459Szrj if (info->type_stack->baseclasses != NULL) 1808*a9fa9459Szrj { 1809*a9fa9459Szrj sprintf (buf + strlen (buf), "!%u,", i); 1810*a9fa9459Szrj for (i = 0; info->type_stack->baseclasses[i] != NULL; i++) 1811*a9fa9459Szrj { 1812*a9fa9459Szrj strcat (buf, info->type_stack->baseclasses[i]); 1813*a9fa9459Szrj free (info->type_stack->baseclasses[i]); 1814*a9fa9459Szrj } 1815*a9fa9459Szrj free (info->type_stack->baseclasses); 1816*a9fa9459Szrj info->type_stack->baseclasses = NULL; 1817*a9fa9459Szrj } 1818*a9fa9459Szrj 1819*a9fa9459Szrj strcat (buf, info->type_stack->fields); 1820*a9fa9459Szrj free (info->type_stack->fields); 1821*a9fa9459Szrj info->type_stack->fields = NULL; 1822*a9fa9459Szrj 1823*a9fa9459Szrj if (info->type_stack->methods != NULL) 1824*a9fa9459Szrj { 1825*a9fa9459Szrj strcat (buf, info->type_stack->methods); 1826*a9fa9459Szrj free (info->type_stack->methods); 1827*a9fa9459Szrj info->type_stack->methods = NULL; 1828*a9fa9459Szrj } 1829*a9fa9459Szrj 1830*a9fa9459Szrj strcat (buf, ";"); 1831*a9fa9459Szrj 1832*a9fa9459Szrj if (info->type_stack->vtable != NULL) 1833*a9fa9459Szrj { 1834*a9fa9459Szrj strcat (buf, info->type_stack->vtable); 1835*a9fa9459Szrj free (info->type_stack->vtable); 1836*a9fa9459Szrj info->type_stack->vtable = NULL; 1837*a9fa9459Szrj } 1838*a9fa9459Szrj 1839*a9fa9459Szrj /* Replace the string on the top of the stack with the complete 1840*a9fa9459Szrj class definition. */ 1841*a9fa9459Szrj free (info->type_stack->string); 1842*a9fa9459Szrj info->type_stack->string = buf; 1843*a9fa9459Szrj 1844*a9fa9459Szrj return TRUE; 1845*a9fa9459Szrj } 1846*a9fa9459Szrj 1847*a9fa9459Szrj /* Push a typedef which was previously defined. */ 1848*a9fa9459Szrj 1849*a9fa9459Szrj static bfd_boolean 1850*a9fa9459Szrj stab_typedef_type (void *p, const char *name) 1851*a9fa9459Szrj { 1852*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 1853*a9fa9459Szrj struct string_hash_entry *h; 1854*a9fa9459Szrj 1855*a9fa9459Szrj h = string_hash_lookup (&info->typedef_hash, name, FALSE, FALSE); 1856*a9fa9459Szrj assert (h != NULL && h->index > 0); 1857*a9fa9459Szrj 1858*a9fa9459Szrj return stab_push_defined_type (info, h->index, h->size); 1859*a9fa9459Szrj } 1860*a9fa9459Szrj 1861*a9fa9459Szrj /* Push a struct, union or class tag. */ 1862*a9fa9459Szrj 1863*a9fa9459Szrj static bfd_boolean 1864*a9fa9459Szrj stab_tag_type (void *p, const char *name, unsigned int id, 1865*a9fa9459Szrj enum debug_type_kind kind) 1866*a9fa9459Szrj { 1867*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 1868*a9fa9459Szrj long tindex; 1869*a9fa9459Szrj unsigned int size = 0; 1870*a9fa9459Szrj 1871*a9fa9459Szrj tindex = stab_get_struct_index (info, name, id, kind, &size); 1872*a9fa9459Szrj if (tindex < 0) 1873*a9fa9459Szrj return FALSE; 1874*a9fa9459Szrj 1875*a9fa9459Szrj return stab_push_defined_type (info, tindex, size); 1876*a9fa9459Szrj } 1877*a9fa9459Szrj 1878*a9fa9459Szrj /* Define a typedef. */ 1879*a9fa9459Szrj 1880*a9fa9459Szrj static bfd_boolean 1881*a9fa9459Szrj stab_typdef (void *p, const char *name) 1882*a9fa9459Szrj { 1883*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 1884*a9fa9459Szrj long tindex; 1885*a9fa9459Szrj unsigned int size; 1886*a9fa9459Szrj char *s, *buf; 1887*a9fa9459Szrj struct string_hash_entry *h; 1888*a9fa9459Szrj 1889*a9fa9459Szrj tindex = info->type_stack->index; 1890*a9fa9459Szrj size = info->type_stack->size; 1891*a9fa9459Szrj s = stab_pop_type (info); 1892*a9fa9459Szrj 1893*a9fa9459Szrj buf = (char *) xmalloc (strlen (name) + strlen (s) + 20); 1894*a9fa9459Szrj 1895*a9fa9459Szrj if (tindex > 0) 1896*a9fa9459Szrj sprintf (buf, "%s:t%s", name, s); 1897*a9fa9459Szrj else 1898*a9fa9459Szrj { 1899*a9fa9459Szrj tindex = info->type_index; 1900*a9fa9459Szrj ++info->type_index; 1901*a9fa9459Szrj sprintf (buf, "%s:t%ld=%s", name, tindex, s); 1902*a9fa9459Szrj } 1903*a9fa9459Szrj 1904*a9fa9459Szrj free (s); 1905*a9fa9459Szrj 1906*a9fa9459Szrj if (! stab_write_symbol (info, N_LSYM, 0, 0, buf)) 1907*a9fa9459Szrj return FALSE; 1908*a9fa9459Szrj 1909*a9fa9459Szrj free (buf); 1910*a9fa9459Szrj 1911*a9fa9459Szrj h = string_hash_lookup (&info->typedef_hash, name, TRUE, FALSE); 1912*a9fa9459Szrj if (h == NULL) 1913*a9fa9459Szrj { 1914*a9fa9459Szrj non_fatal (_("string_hash_lookup failed: %s"), 1915*a9fa9459Szrj bfd_errmsg (bfd_get_error ())); 1916*a9fa9459Szrj return FALSE; 1917*a9fa9459Szrj } 1918*a9fa9459Szrj 1919*a9fa9459Szrj /* I don't think we care about redefinitions. */ 1920*a9fa9459Szrj 1921*a9fa9459Szrj h->index = tindex; 1922*a9fa9459Szrj h->size = size; 1923*a9fa9459Szrj 1924*a9fa9459Szrj return TRUE; 1925*a9fa9459Szrj } 1926*a9fa9459Szrj 1927*a9fa9459Szrj /* Define a tag. */ 1928*a9fa9459Szrj 1929*a9fa9459Szrj static bfd_boolean 1930*a9fa9459Szrj stab_tag (void *p, const char *tag) 1931*a9fa9459Szrj { 1932*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 1933*a9fa9459Szrj char *s, *buf; 1934*a9fa9459Szrj 1935*a9fa9459Szrj s = stab_pop_type (info); 1936*a9fa9459Szrj 1937*a9fa9459Szrj buf = (char *) xmalloc (strlen (tag) + strlen (s) + 3); 1938*a9fa9459Szrj 1939*a9fa9459Szrj sprintf (buf, "%s:T%s", tag, s); 1940*a9fa9459Szrj free (s); 1941*a9fa9459Szrj 1942*a9fa9459Szrj if (! stab_write_symbol (info, N_LSYM, 0, 0, buf)) 1943*a9fa9459Szrj return FALSE; 1944*a9fa9459Szrj 1945*a9fa9459Szrj free (buf); 1946*a9fa9459Szrj 1947*a9fa9459Szrj return TRUE; 1948*a9fa9459Szrj } 1949*a9fa9459Szrj 1950*a9fa9459Szrj /* Define an integer constant. */ 1951*a9fa9459Szrj 1952*a9fa9459Szrj static bfd_boolean 1953*a9fa9459Szrj stab_int_constant (void *p, const char *name, bfd_vma val) 1954*a9fa9459Szrj { 1955*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 1956*a9fa9459Szrj char *buf; 1957*a9fa9459Szrj 1958*a9fa9459Szrj buf = (char *) xmalloc (strlen (name) + 20); 1959*a9fa9459Szrj sprintf (buf, "%s:c=i%ld", name, (long) val); 1960*a9fa9459Szrj 1961*a9fa9459Szrj if (! stab_write_symbol (info, N_LSYM, 0, 0, buf)) 1962*a9fa9459Szrj return FALSE; 1963*a9fa9459Szrj 1964*a9fa9459Szrj free (buf); 1965*a9fa9459Szrj 1966*a9fa9459Szrj return TRUE; 1967*a9fa9459Szrj } 1968*a9fa9459Szrj 1969*a9fa9459Szrj /* Define a floating point constant. */ 1970*a9fa9459Szrj 1971*a9fa9459Szrj static bfd_boolean 1972*a9fa9459Szrj stab_float_constant (void *p, const char *name, double val) 1973*a9fa9459Szrj { 1974*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 1975*a9fa9459Szrj char *buf; 1976*a9fa9459Szrj 1977*a9fa9459Szrj buf = (char *) xmalloc (strlen (name) + 20); 1978*a9fa9459Szrj sprintf (buf, "%s:c=f%g", name, val); 1979*a9fa9459Szrj 1980*a9fa9459Szrj if (! stab_write_symbol (info, N_LSYM, 0, 0, buf)) 1981*a9fa9459Szrj return FALSE; 1982*a9fa9459Szrj 1983*a9fa9459Szrj free (buf); 1984*a9fa9459Szrj 1985*a9fa9459Szrj return TRUE; 1986*a9fa9459Szrj } 1987*a9fa9459Szrj 1988*a9fa9459Szrj /* Define a typed constant. */ 1989*a9fa9459Szrj 1990*a9fa9459Szrj static bfd_boolean 1991*a9fa9459Szrj stab_typed_constant (void *p, const char *name, bfd_vma val) 1992*a9fa9459Szrj { 1993*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 1994*a9fa9459Szrj char *s, *buf; 1995*a9fa9459Szrj 1996*a9fa9459Szrj s = stab_pop_type (info); 1997*a9fa9459Szrj 1998*a9fa9459Szrj buf = (char *) xmalloc (strlen (name) + strlen (s) + 20); 1999*a9fa9459Szrj sprintf (buf, "%s:c=e%s,%ld", name, s, (long) val); 2000*a9fa9459Szrj free (s); 2001*a9fa9459Szrj 2002*a9fa9459Szrj if (! stab_write_symbol (info, N_LSYM, 0, 0, buf)) 2003*a9fa9459Szrj return FALSE; 2004*a9fa9459Szrj 2005*a9fa9459Szrj free (buf); 2006*a9fa9459Szrj 2007*a9fa9459Szrj return TRUE; 2008*a9fa9459Szrj } 2009*a9fa9459Szrj 2010*a9fa9459Szrj /* Record a variable. */ 2011*a9fa9459Szrj 2012*a9fa9459Szrj static bfd_boolean 2013*a9fa9459Szrj stab_variable (void *p, const char *name, enum debug_var_kind kind, 2014*a9fa9459Szrj bfd_vma val) 2015*a9fa9459Szrj { 2016*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 2017*a9fa9459Szrj char *s, *buf; 2018*a9fa9459Szrj int stab_type; 2019*a9fa9459Szrj const char *kindstr; 2020*a9fa9459Szrj 2021*a9fa9459Szrj s = stab_pop_type (info); 2022*a9fa9459Szrj 2023*a9fa9459Szrj switch (kind) 2024*a9fa9459Szrj { 2025*a9fa9459Szrj default: 2026*a9fa9459Szrj abort (); 2027*a9fa9459Szrj 2028*a9fa9459Szrj case DEBUG_GLOBAL: 2029*a9fa9459Szrj stab_type = N_GSYM; 2030*a9fa9459Szrj kindstr = "G"; 2031*a9fa9459Szrj break; 2032*a9fa9459Szrj 2033*a9fa9459Szrj case DEBUG_STATIC: 2034*a9fa9459Szrj stab_type = N_STSYM; 2035*a9fa9459Szrj kindstr = "S"; 2036*a9fa9459Szrj break; 2037*a9fa9459Szrj 2038*a9fa9459Szrj case DEBUG_LOCAL_STATIC: 2039*a9fa9459Szrj stab_type = N_STSYM; 2040*a9fa9459Szrj kindstr = "V"; 2041*a9fa9459Szrj break; 2042*a9fa9459Szrj 2043*a9fa9459Szrj case DEBUG_LOCAL: 2044*a9fa9459Szrj stab_type = N_LSYM; 2045*a9fa9459Szrj kindstr = ""; 2046*a9fa9459Szrj 2047*a9fa9459Szrj /* Make sure that this is a type reference or definition. */ 2048*a9fa9459Szrj if (! ISDIGIT (*s)) 2049*a9fa9459Szrj { 2050*a9fa9459Szrj char *n; 2051*a9fa9459Szrj long tindex; 2052*a9fa9459Szrj 2053*a9fa9459Szrj tindex = info->type_index; 2054*a9fa9459Szrj ++info->type_index; 2055*a9fa9459Szrj n = (char *) xmalloc (strlen (s) + 20); 2056*a9fa9459Szrj sprintf (n, "%ld=%s", tindex, s); 2057*a9fa9459Szrj free (s); 2058*a9fa9459Szrj s = n; 2059*a9fa9459Szrj } 2060*a9fa9459Szrj break; 2061*a9fa9459Szrj 2062*a9fa9459Szrj case DEBUG_REGISTER: 2063*a9fa9459Szrj stab_type = N_RSYM; 2064*a9fa9459Szrj kindstr = "r"; 2065*a9fa9459Szrj break; 2066*a9fa9459Szrj } 2067*a9fa9459Szrj 2068*a9fa9459Szrj buf = (char *) xmalloc (strlen (name) + strlen (s) + 3); 2069*a9fa9459Szrj sprintf (buf, "%s:%s%s", name, kindstr, s); 2070*a9fa9459Szrj free (s); 2071*a9fa9459Szrj 2072*a9fa9459Szrj if (! stab_write_symbol (info, stab_type, 0, val, buf)) 2073*a9fa9459Szrj return FALSE; 2074*a9fa9459Szrj 2075*a9fa9459Szrj free (buf); 2076*a9fa9459Szrj 2077*a9fa9459Szrj return TRUE; 2078*a9fa9459Szrj } 2079*a9fa9459Szrj 2080*a9fa9459Szrj /* Start outputting a function. */ 2081*a9fa9459Szrj 2082*a9fa9459Szrj static bfd_boolean 2083*a9fa9459Szrj stab_start_function (void *p, const char *name, bfd_boolean globalp) 2084*a9fa9459Szrj { 2085*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 2086*a9fa9459Szrj char *rettype, *buf; 2087*a9fa9459Szrj 2088*a9fa9459Szrj assert (info->nesting == 0 && info->fun_offset == -1); 2089*a9fa9459Szrj 2090*a9fa9459Szrj rettype = stab_pop_type (info); 2091*a9fa9459Szrj 2092*a9fa9459Szrj buf = (char *) xmalloc (strlen (name) + strlen (rettype) + 3); 2093*a9fa9459Szrj sprintf (buf, "%s:%c%s", name, 2094*a9fa9459Szrj globalp ? 'F' : 'f', 2095*a9fa9459Szrj rettype); 2096*a9fa9459Szrj 2097*a9fa9459Szrj /* We don't know the value now, so we set it in start_block. */ 2098*a9fa9459Szrj info->fun_offset = info->symbols_size; 2099*a9fa9459Szrj 2100*a9fa9459Szrj if (! stab_write_symbol (info, N_FUN, 0, 0, buf)) 2101*a9fa9459Szrj return FALSE; 2102*a9fa9459Szrj 2103*a9fa9459Szrj free (buf); 2104*a9fa9459Szrj 2105*a9fa9459Szrj return TRUE; 2106*a9fa9459Szrj } 2107*a9fa9459Szrj 2108*a9fa9459Szrj /* Output a function parameter. */ 2109*a9fa9459Szrj 2110*a9fa9459Szrj static bfd_boolean 2111*a9fa9459Szrj stab_function_parameter (void *p, const char *name, enum debug_parm_kind kind, bfd_vma val) 2112*a9fa9459Szrj { 2113*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 2114*a9fa9459Szrj char *s, *buf; 2115*a9fa9459Szrj int stab_type; 2116*a9fa9459Szrj char kindc; 2117*a9fa9459Szrj 2118*a9fa9459Szrj s = stab_pop_type (info); 2119*a9fa9459Szrj 2120*a9fa9459Szrj switch (kind) 2121*a9fa9459Szrj { 2122*a9fa9459Szrj default: 2123*a9fa9459Szrj abort (); 2124*a9fa9459Szrj 2125*a9fa9459Szrj case DEBUG_PARM_STACK: 2126*a9fa9459Szrj stab_type = N_PSYM; 2127*a9fa9459Szrj kindc = 'p'; 2128*a9fa9459Szrj break; 2129*a9fa9459Szrj 2130*a9fa9459Szrj case DEBUG_PARM_REG: 2131*a9fa9459Szrj stab_type = N_RSYM; 2132*a9fa9459Szrj kindc = 'P'; 2133*a9fa9459Szrj break; 2134*a9fa9459Szrj 2135*a9fa9459Szrj case DEBUG_PARM_REFERENCE: 2136*a9fa9459Szrj stab_type = N_PSYM; 2137*a9fa9459Szrj kindc = 'v'; 2138*a9fa9459Szrj break; 2139*a9fa9459Szrj 2140*a9fa9459Szrj case DEBUG_PARM_REF_REG: 2141*a9fa9459Szrj stab_type = N_RSYM; 2142*a9fa9459Szrj kindc = 'a'; 2143*a9fa9459Szrj break; 2144*a9fa9459Szrj } 2145*a9fa9459Szrj 2146*a9fa9459Szrj buf = (char *) xmalloc (strlen (name) + strlen (s) + 3); 2147*a9fa9459Szrj sprintf (buf, "%s:%c%s", name, kindc, s); 2148*a9fa9459Szrj free (s); 2149*a9fa9459Szrj 2150*a9fa9459Szrj if (! stab_write_symbol (info, stab_type, 0, val, buf)) 2151*a9fa9459Szrj return FALSE; 2152*a9fa9459Szrj 2153*a9fa9459Szrj free (buf); 2154*a9fa9459Szrj 2155*a9fa9459Szrj return TRUE; 2156*a9fa9459Szrj } 2157*a9fa9459Szrj 2158*a9fa9459Szrj /* Start a block. */ 2159*a9fa9459Szrj 2160*a9fa9459Szrj static bfd_boolean 2161*a9fa9459Szrj stab_start_block (void *p, bfd_vma addr) 2162*a9fa9459Szrj { 2163*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 2164*a9fa9459Szrj 2165*a9fa9459Szrj /* Fill in any slots which have been waiting for the first known 2166*a9fa9459Szrj text address. */ 2167*a9fa9459Szrj 2168*a9fa9459Szrj if (info->so_offset != -1) 2169*a9fa9459Szrj { 2170*a9fa9459Szrj bfd_put_32 (info->abfd, addr, info->symbols + info->so_offset + 8); 2171*a9fa9459Szrj info->so_offset = -1; 2172*a9fa9459Szrj } 2173*a9fa9459Szrj 2174*a9fa9459Szrj if (info->fun_offset != -1) 2175*a9fa9459Szrj { 2176*a9fa9459Szrj bfd_put_32 (info->abfd, addr, info->symbols + info->fun_offset + 8); 2177*a9fa9459Szrj info->fun_offset = -1; 2178*a9fa9459Szrj } 2179*a9fa9459Szrj 2180*a9fa9459Szrj ++info->nesting; 2181*a9fa9459Szrj 2182*a9fa9459Szrj /* We will be called with a top level block surrounding the 2183*a9fa9459Szrj function, but stabs information does not output that block, so we 2184*a9fa9459Szrj ignore it. */ 2185*a9fa9459Szrj 2186*a9fa9459Szrj if (info->nesting == 1) 2187*a9fa9459Szrj { 2188*a9fa9459Szrj info->fnaddr = addr; 2189*a9fa9459Szrj return TRUE; 2190*a9fa9459Szrj } 2191*a9fa9459Szrj 2192*a9fa9459Szrj /* We have to output the LBRAC symbol after any variables which are 2193*a9fa9459Szrj declared inside the block. We postpone the LBRAC until the next 2194*a9fa9459Szrj start_block or end_block. */ 2195*a9fa9459Szrj 2196*a9fa9459Szrj /* If we have postponed an LBRAC, output it now. */ 2197*a9fa9459Szrj if (info->pending_lbrac != (bfd_vma) -1) 2198*a9fa9459Szrj { 2199*a9fa9459Szrj if (! stab_write_symbol (info, N_LBRAC, 0, info->pending_lbrac, 2200*a9fa9459Szrj (const char *) NULL)) 2201*a9fa9459Szrj return FALSE; 2202*a9fa9459Szrj } 2203*a9fa9459Szrj 2204*a9fa9459Szrj /* Remember the address and output it later. */ 2205*a9fa9459Szrj 2206*a9fa9459Szrj info->pending_lbrac = addr - info->fnaddr; 2207*a9fa9459Szrj 2208*a9fa9459Szrj return TRUE; 2209*a9fa9459Szrj } 2210*a9fa9459Szrj 2211*a9fa9459Szrj /* End a block. */ 2212*a9fa9459Szrj 2213*a9fa9459Szrj static bfd_boolean 2214*a9fa9459Szrj stab_end_block (void *p, bfd_vma addr) 2215*a9fa9459Szrj { 2216*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 2217*a9fa9459Szrj 2218*a9fa9459Szrj if (addr > info->last_text_address) 2219*a9fa9459Szrj info->last_text_address = addr; 2220*a9fa9459Szrj 2221*a9fa9459Szrj /* If we have postponed an LBRAC, output it now. */ 2222*a9fa9459Szrj if (info->pending_lbrac != (bfd_vma) -1) 2223*a9fa9459Szrj { 2224*a9fa9459Szrj if (! stab_write_symbol (info, N_LBRAC, 0, info->pending_lbrac, 2225*a9fa9459Szrj (const char *) NULL)) 2226*a9fa9459Szrj return FALSE; 2227*a9fa9459Szrj info->pending_lbrac = (bfd_vma) -1; 2228*a9fa9459Szrj } 2229*a9fa9459Szrj 2230*a9fa9459Szrj assert (info->nesting > 0); 2231*a9fa9459Szrj 2232*a9fa9459Szrj --info->nesting; 2233*a9fa9459Szrj 2234*a9fa9459Szrj /* We ignore the outermost block. */ 2235*a9fa9459Szrj if (info->nesting == 0) 2236*a9fa9459Szrj return TRUE; 2237*a9fa9459Szrj 2238*a9fa9459Szrj return stab_write_symbol (info, N_RBRAC, 0, addr - info->fnaddr, 2239*a9fa9459Szrj (const char *) NULL); 2240*a9fa9459Szrj } 2241*a9fa9459Szrj 2242*a9fa9459Szrj /* End a function. */ 2243*a9fa9459Szrj 2244*a9fa9459Szrj static bfd_boolean 2245*a9fa9459Szrj stab_end_function (void *p ATTRIBUTE_UNUSED) 2246*a9fa9459Szrj { 2247*a9fa9459Szrj return TRUE; 2248*a9fa9459Szrj } 2249*a9fa9459Szrj 2250*a9fa9459Szrj /* Output a line number. */ 2251*a9fa9459Szrj 2252*a9fa9459Szrj static bfd_boolean 2253*a9fa9459Szrj stab_lineno (void *p, const char *file, unsigned long lineno, bfd_vma addr) 2254*a9fa9459Szrj { 2255*a9fa9459Szrj struct stab_write_handle *info = (struct stab_write_handle *) p; 2256*a9fa9459Szrj 2257*a9fa9459Szrj assert (info->lineno_filename != NULL); 2258*a9fa9459Szrj 2259*a9fa9459Szrj if (addr > info->last_text_address) 2260*a9fa9459Szrj info->last_text_address = addr; 2261*a9fa9459Szrj 2262*a9fa9459Szrj if (filename_cmp (file, info->lineno_filename) != 0) 2263*a9fa9459Szrj { 2264*a9fa9459Szrj if (! stab_write_symbol (info, N_SOL, 0, addr, file)) 2265*a9fa9459Szrj return FALSE; 2266*a9fa9459Szrj info->lineno_filename = file; 2267*a9fa9459Szrj } 2268*a9fa9459Szrj 2269*a9fa9459Szrj return stab_write_symbol (info, N_SLINE, lineno, addr - info->fnaddr, 2270*a9fa9459Szrj (const char *) NULL); 2271*a9fa9459Szrj } 2272