tools/elf4rom/libs/dwarf-20071209/libdwarf/pro_forms.c
changeset 34 92d87f2e53c2
equal deleted inserted replaced
33:1af5c1be89f8 34:92d87f2e53c2
       
     1 /*
       
     2 
       
     3   Copyright (C) 2000,2004 Silicon Graphics, Inc.  All Rights Reserved.
       
     4   Portions Copyright 2002 Sun Microsystems, Inc. All rights reserved.
       
     5   Portions Copyright 2007 David Anderson. All rights reserved.
       
     6 
       
     7   This program is free software; you can redistribute it and/or modify it
       
     8   under the terms of version 2.1 of the GNU Lesser General Public License 
       
     9   as published by the Free Software Foundation.
       
    10 
       
    11   This program is distributed in the hope that it would be useful, but
       
    12   WITHOUT ANY WARRANTY; without even the implied warranty of
       
    13   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  
       
    14 
       
    15   Further, this software is distributed without any warranty that it is
       
    16   free of the rightful claim of any third person regarding infringement 
       
    17   or the like.  Any license provided herein, whether implied or 
       
    18   otherwise, applies only to this software file.  Patent licenses, if
       
    19   any, provided herein do not apply to combinations of this program with 
       
    20   other software, or any other product whatsoever.  
       
    21 
       
    22   You should have received a copy of the GNU Lesser General Public 
       
    23   License along with this program; if not, write the Free Software 
       
    24   Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston MA 02110-1301,
       
    25   USA.
       
    26 
       
    27   Contact information:  Silicon Graphics, Inc., 1500 Crittenden Lane,
       
    28   Mountain View, CA 94043, or:
       
    29 
       
    30   http://www.sgi.com
       
    31 
       
    32   For further information regarding this notice, see:
       
    33 
       
    34   http://oss.sgi.com/projects/GenInfo/NoticeExplan
       
    35 
       
    36 */
       
    37 
       
    38 
       
    39 
       
    40 #include "config.h"
       
    41 #include "libdwarfdefs.h"
       
    42 #include <stdio.h>
       
    43 #include <string.h>
       
    44 #include <limits.h>
       
    45 #include "pro_incl.h"
       
    46 #include "pro_expr.h"
       
    47 
       
    48 #ifndef R_MIPS_NONE
       
    49 #define R_MIPS_NONE 0
       
    50 #endif
       
    51 
       
    52 
       
    53     /* Indicates no relocation needed. */
       
    54 #define NO_ELF_SYM_INDEX	0
       
    55 
       
    56 
       
    57 /* adds an attribute to a die */
       
    58 extern void _dwarf_pro_add_at_to_die(Dwarf_P_Die die,
       
    59 				     Dwarf_P_Attribute attr);
       
    60 
       
    61 /*
       
    62     This function adds an attribute whose value is
       
    63     a target address to the given die.  The attribute
       
    64     is given the name provided by attr.  The address
       
    65     is given in pc_value.
       
    66 */
       
    67 
       
    68 static Dwarf_P_Attribute
       
    69 local_add_AT_address(Dwarf_P_Debug dbg,
       
    70 		     Dwarf_P_Die ownerdie,
       
    71 		     Dwarf_Half attr,
       
    72 		     Dwarf_Signed form,
       
    73 		     Dwarf_Unsigned pc_value,
       
    74 		     Dwarf_Unsigned sym_index,
       
    75 		     Dwarf_Error * error);
       
    76      
       
    77 /* old interface */
       
    78 Dwarf_P_Attribute
       
    79 dwarf_add_AT_targ_address(Dwarf_P_Debug dbg,
       
    80 			  Dwarf_P_Die ownerdie,
       
    81 			  Dwarf_Half attr,
       
    82 			  Dwarf_Unsigned pc_value,
       
    83 			  Dwarf_Signed sym_index, Dwarf_Error * error)
       
    84 {
       
    85     return 
       
    86 	dwarf_add_AT_targ_address_b(dbg,
       
    87 				    ownerdie, 
       
    88 				    attr,
       
    89 				    pc_value, 
       
    90 				    (Dwarf_Unsigned) sym_index, error);
       
    91 }
       
    92 
       
    93 /* New interface, replacing dwarf_add_AT_targ_address. 
       
    94    Essentially just makes sym_index a Dwarf_Unsigned
       
    95    so for symbolic relocations it can be a full address.
       
    96 */
       
    97 Dwarf_P_Attribute
       
    98 dwarf_add_AT_targ_address_b(Dwarf_P_Debug dbg,
       
    99 			    Dwarf_P_Die ownerdie,
       
   100 			    Dwarf_Half attr,
       
   101 			    Dwarf_Unsigned pc_value,
       
   102 			    Dwarf_Unsigned sym_index,
       
   103 			    Dwarf_Error * error)
       
   104 {
       
   105     switch (attr) {
       
   106     case DW_AT_low_pc:
       
   107     case DW_AT_high_pc:
       
   108 
       
   109     /* added to support location lists */
       
   110     /* no way to check that this is a loclist-style address though */
       
   111     case DW_AT_location:
       
   112     case DW_AT_string_length:
       
   113     case DW_AT_return_addr:
       
   114     case DW_AT_frame_base:
       
   115     case DW_AT_segment:
       
   116     case DW_AT_static_link:
       
   117     case DW_AT_use_location:
       
   118     case DW_AT_vtable_elem_location:
       
   119 	
       
   120 	break;
       
   121 
       
   122     default: 
       
   123 	if ( attr < DW_AT_lo_user || attr > DW_AT_hi_user ) {
       
   124 	    _dwarf_p_error(dbg, error, DW_DLE_INPUT_ATTR_BAD);
       
   125 	    return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   126 	}
       
   127 	break;
       
   128     }
       
   129     
       
   130     return local_add_AT_address(dbg, ownerdie, attr, DW_FORM_addr,
       
   131 				pc_value, sym_index, error);
       
   132 }
       
   133 
       
   134 Dwarf_P_Attribute
       
   135 dwarf_add_AT_ref_address(Dwarf_P_Debug dbg,
       
   136 			 Dwarf_P_Die ownerdie,
       
   137 			 Dwarf_Half attr,
       
   138 			 Dwarf_Unsigned pc_value,
       
   139 			 Dwarf_Unsigned sym_index,
       
   140 			 Dwarf_Error * error)
       
   141 {
       
   142     switch (attr) {
       
   143     case DW_AT_type:
       
   144     case DW_AT_import:
       
   145 	break;
       
   146 
       
   147     default: 
       
   148 	if ( attr < DW_AT_lo_user || attr > DW_AT_hi_user ) {
       
   149 	    _dwarf_p_error(dbg, error, DW_DLE_INPUT_ATTR_BAD);
       
   150 	    return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   151 	}
       
   152 	break;
       
   153     }
       
   154     
       
   155     return local_add_AT_address(dbg, ownerdie, attr, DW_FORM_ref_addr,
       
   156 				pc_value, sym_index, error);    
       
   157 }
       
   158 
       
   159 
       
   160 /* Make sure attribute types are checked before entering here. */
       
   161 static Dwarf_P_Attribute
       
   162 local_add_AT_address(Dwarf_P_Debug dbg,
       
   163 		     Dwarf_P_Die ownerdie,
       
   164 		     Dwarf_Half attr,
       
   165 		     Dwarf_Signed form,
       
   166 		     Dwarf_Unsigned pc_value,
       
   167 		     Dwarf_Unsigned sym_index,
       
   168 		     Dwarf_Error * error)
       
   169 {
       
   170     Dwarf_P_Attribute new_attr;
       
   171     int upointer_size = dbg->de_pointer_size;
       
   172 
       
   173     if (dbg == NULL) {
       
   174 	_dwarf_p_error(NULL, error, DW_DLE_DBG_NULL);
       
   175 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   176     }
       
   177 
       
   178     if (ownerdie == NULL) {
       
   179 	_dwarf_p_error(dbg, error, DW_DLE_DIE_NULL);
       
   180 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   181     }
       
   182 
       
   183     /* attribute types have already been checked */
       
   184     /* switch (attr) { ... } */
       
   185 
       
   186     new_attr = (Dwarf_P_Attribute)
       
   187 	_dwarf_p_get_alloc(dbg, sizeof(struct Dwarf_P_Attribute_s));
       
   188     if (new_attr == NULL) {
       
   189 	_dwarf_p_error(dbg, error, DW_DLE_ALLOC_FAIL);
       
   190 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   191     }
       
   192 
       
   193     new_attr->ar_attribute = attr;
       
   194     new_attr->ar_attribute_form = form;
       
   195     new_attr->ar_nbytes = upointer_size;
       
   196     new_attr->ar_rel_symidx = sym_index;
       
   197     new_attr->ar_reloc_len = upointer_size;
       
   198     new_attr->ar_next = 0;
       
   199     if (sym_index != NO_ELF_SYM_INDEX)
       
   200 	new_attr->ar_rel_type = dbg->de_ptr_reloc;
       
   201     else
       
   202 	new_attr->ar_rel_type = R_MIPS_NONE;
       
   203 
       
   204     new_attr->ar_data = (char *)
       
   205 	_dwarf_p_get_alloc(dbg, upointer_size);
       
   206     if (new_attr->ar_data == NULL) {
       
   207 	_dwarf_p_error(dbg, error, DW_DLE_ALLOC_FAIL);
       
   208 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   209     }
       
   210     WRITE_UNALIGNED(dbg, new_attr->ar_data,
       
   211 		    (const void *) &pc_value,
       
   212 		    sizeof(pc_value), upointer_size);
       
   213 
       
   214     /* add attribute to the die */
       
   215     _dwarf_pro_add_at_to_die(ownerdie, new_attr);
       
   216     return new_attr;
       
   217 }
       
   218 
       
   219 /*
       
   220  * Functions to compress and uncompress data from normal
       
   221  * arrays of integral types into arrays of LEB128 numbers.
       
   222  * Extend these functions as needed to handle wider input
       
   223  * variety.  Return values should be freed with _dwarf_p_dealloc
       
   224  * after they aren't needed any more.
       
   225  */
       
   226 
       
   227 /* return value points to an array of LEB number */
       
   228 
       
   229 void *
       
   230 dwarf_compress_integer_block(
       
   231     Dwarf_P_Debug    dbg,
       
   232     Dwarf_Bool       unit_is_signed,
       
   233     Dwarf_Small      unit_length_in_bits,
       
   234     void*            input_block,
       
   235     Dwarf_Unsigned   input_length_in_units,
       
   236     Dwarf_Unsigned*  output_length_in_bytes_ptr,
       
   237     Dwarf_Error*     error
       
   238 )
       
   239 {
       
   240     Dwarf_Unsigned output_length_in_bytes;
       
   241     char * output_block;
       
   242     char encode_buffer[ENCODE_SPACE_NEEDED];
       
   243     int unit_length;
       
   244     int i;
       
   245     char * ptr;
       
   246     int remain;
       
   247     int result;
       
   248 
       
   249     if (dbg == NULL) {
       
   250         _dwarf_p_error(NULL, error, DW_DLE_DBG_NULL);
       
   251         return((void *)DW_DLV_BADADDR);
       
   252     }
       
   253     
       
   254     if (unit_is_signed == false ||
       
   255 	unit_length_in_bits != 32 ||
       
   256 	input_block == NULL ||
       
   257 	input_length_in_units == 0 ||
       
   258 	output_length_in_bytes_ptr == NULL) {
       
   259 	
       
   260 	_dwarf_p_error(NULL, error, DW_DLE_BADBITC);
       
   261 	return ((void *) DW_DLV_BADADDR);
       
   262     }
       
   263 
       
   264     /* At this point we assume the format is: signed 32 bit */
       
   265 
       
   266     /* first compress everything to find the total size. */
       
   267 
       
   268     output_length_in_bytes = 0;
       
   269     for (i=0; i<input_length_in_units; i++) {
       
   270 	int unit_encoded_size;
       
   271 	Dwarf_sfixed unit; /* this is fixed at signed-32-bits */
       
   272 	
       
   273 	unit = ((Dwarf_sfixed*)input_block)[i];
       
   274 	
       
   275 	result = _dwarf_pro_encode_signed_leb128_nm(unit, &unit_encoded_size,
       
   276 					     encode_buffer,sizeof(encode_buffer));
       
   277 	if (result !=  DW_DLV_OK) {
       
   278 	    _dwarf_p_error(dbg, error, DW_DLE_ALLOC_FAIL);
       
   279 	    return((Dwarf_P_Attribute)DW_DLV_BADADDR);
       
   280 	}
       
   281 	output_length_in_bytes += unit_encoded_size;
       
   282     }
       
   283 
       
   284     
       
   285     /* then alloc */
       
   286 
       
   287     output_block = (void *)
       
   288         _dwarf_p_get_alloc(dbg, output_length_in_bytes);
       
   289     if (output_block == NULL) {
       
   290         _dwarf_p_error(dbg, error, DW_DLE_ALLOC_FAIL);
       
   291         return((void*)DW_DLV_BADADDR);
       
   292     }
       
   293     
       
   294     /* then compress again and copy into new buffer */
       
   295 
       
   296     ptr = output_block;
       
   297     remain = output_length_in_bytes;
       
   298     for (i=0; i<input_length_in_units; i++) {
       
   299 	int unit_encoded_size;
       
   300 	Dwarf_sfixed unit; /* this is fixed at signed-32-bits */
       
   301 	
       
   302 	unit = ((Dwarf_sfixed*)input_block)[i];
       
   303 	
       
   304 	result = _dwarf_pro_encode_signed_leb128_nm(unit, &unit_encoded_size,
       
   305 					     ptr, remain);
       
   306 	if (result !=  DW_DLV_OK) {
       
   307 	    _dwarf_p_error(dbg, error, DW_DLE_ALLOC_FAIL);
       
   308 	    return((Dwarf_P_Attribute)DW_DLV_BADADDR);
       
   309 	}
       
   310 	remain -= unit_encoded_size;
       
   311 	ptr += unit_encoded_size;
       
   312     }
       
   313 
       
   314     if (remain != 0) {
       
   315 	_dwarf_p_dealloc(dbg, (unsigned char *)output_block);
       
   316 	_dwarf_p_error(dbg, error, DW_DLE_ALLOC_FAIL);
       
   317 	return((Dwarf_P_Attribute)DW_DLV_BADADDR);
       
   318     }
       
   319 
       
   320     *output_length_in_bytes_ptr = output_length_in_bytes;
       
   321     return (void*) output_block;
       
   322 
       
   323 }
       
   324 
       
   325 void
       
   326 dwarf_dealloc_compressed_block(Dwarf_P_Debug dbg, void * space)
       
   327 {
       
   328     _dwarf_p_dealloc(dbg, space);
       
   329 }
       
   330 
       
   331 /* This is very similar to targ_address but results in a different FORM */
       
   332 /* dbg->de_ar_data_attribute_form is data4 or data8
       
   333    and dwarf4 changes the definition for such on DW_AT_high_pc.
       
   334    DWARF 3: the FORM here has no defined meaning for dwarf3.
       
   335    DWARF 4: the FORM here means that for DW_AT_high_pc the value
       
   336             is not a high address but is instead an offset
       
   337             from a (separate) DW_AT_low_pc. 
       
   338    The intent for DWARF4 is that this is not a relocated
       
   339    address at all.  Instead a simple offset.
       
   340    But this should NOT be called for a simple non-relocated offset.
       
   341    So do not call this with an attr of DW_AT_high_pc.
       
   342    Use dwarf_add_AT_unsigned_const() (for example) instead of
       
   343    dwarf_add_AT_dataref when the value is a simple offset .
       
   344 */
       
   345 Dwarf_P_Attribute
       
   346 dwarf_add_AT_dataref(
       
   347     Dwarf_P_Debug dbg,
       
   348     Dwarf_P_Die ownerdie,
       
   349     Dwarf_Half attr,
       
   350     Dwarf_Unsigned pc_value,
       
   351     Dwarf_Unsigned sym_index,
       
   352     Dwarf_Error * error)
       
   353 {
       
   354     /* TODO: Add checking here */
       
   355     return local_add_AT_address(dbg, ownerdie, attr,
       
   356 				dbg->de_ar_data_attribute_form,
       
   357 				pc_value,
       
   358 				sym_index,
       
   359 				error);
       
   360 }
       
   361 
       
   362 
       
   363 
       
   364 Dwarf_P_Attribute 
       
   365 dwarf_add_AT_block(
       
   366     Dwarf_P_Debug	dbg,
       
   367     Dwarf_P_Die 	ownerdie,
       
   368     Dwarf_Half		attr,
       
   369     Dwarf_Small         *block_data,
       
   370     Dwarf_Unsigned      block_size,
       
   371     Dwarf_Error 	*error
       
   372 )
       
   373 {
       
   374     Dwarf_P_Attribute 	new_attr;
       
   375     int result;
       
   376     char encode_buffer[ENCODE_SPACE_NEEDED];
       
   377     int len_size;
       
   378     char * attrdata;
       
   379 
       
   380     if (dbg == NULL) {
       
   381         _dwarf_p_error(NULL, error, DW_DLE_DBG_NULL);
       
   382         return((Dwarf_P_Attribute)DW_DLV_BADADDR);
       
   383     }
       
   384 
       
   385     if (ownerdie == NULL) {
       
   386         _dwarf_p_error(dbg, error, DW_DLE_DIE_NULL);
       
   387         return((Dwarf_P_Attribute)DW_DLV_BADADDR);
       
   388     }
       
   389 
       
   390     /* I don't mess with block1, block2, block4, not worth the effort */
       
   391 
       
   392     /* So, encode the length into LEB128 */
       
   393     result = _dwarf_pro_encode_leb128_nm(block_size, &len_size,
       
   394 					 encode_buffer,sizeof(encode_buffer));
       
   395     if (result !=  DW_DLV_OK) {
       
   396 	_dwarf_p_error(dbg, error, DW_DLE_ALLOC_FAIL);
       
   397 	return((Dwarf_P_Attribute)DW_DLV_BADADDR);
       
   398     }
       
   399 
       
   400     /* Allocate the new attribute */
       
   401     new_attr = (Dwarf_P_Attribute)
       
   402         _dwarf_p_get_alloc(dbg, sizeof(struct Dwarf_P_Attribute_s));
       
   403     if (new_attr == NULL) {
       
   404         _dwarf_p_error(dbg, error, DW_DLE_ALLOC_FAIL);
       
   405         return((Dwarf_P_Attribute)DW_DLV_BADADDR);
       
   406     }
       
   407 
       
   408     /* Fill in the attribute */
       
   409     new_attr->ar_attribute = attr;
       
   410     new_attr->ar_attribute_form = DW_FORM_block;
       
   411     new_attr->ar_nbytes = len_size + block_size;
       
   412     new_attr->ar_next = 0;
       
   413 
       
   414     new_attr->ar_data = attrdata = (char *)
       
   415         _dwarf_p_get_alloc(dbg, len_size + block_size);
       
   416     if (new_attr->ar_data == NULL) {
       
   417 	/* free the block we got earlier */
       
   418 	_dwarf_p_dealloc(dbg, (unsigned char *) new_attr);
       
   419         _dwarf_p_error(dbg, error, DW_DLE_ALLOC_FAIL);
       
   420         return((Dwarf_P_Attribute)DW_DLV_BADADDR);
       
   421     }
       
   422 
       
   423     /* write length and data to attribute data buffer */
       
   424     memcpy(attrdata, encode_buffer, len_size);
       
   425     attrdata += len_size;
       
   426     memcpy(attrdata, block_data, block_size);
       
   427     
       
   428     /* add attribute to the die */
       
   429     _dwarf_pro_add_at_to_die(ownerdie, new_attr);
       
   430 
       
   431     return new_attr;
       
   432 }
       
   433 
       
   434 
       
   435 /*
       
   436     This function adds attributes whose value
       
   437     is an unsigned constant.  It determines the 
       
   438     size of the value field from the value of 
       
   439     the constant.
       
   440 */
       
   441 Dwarf_P_Attribute
       
   442 dwarf_add_AT_unsigned_const(Dwarf_P_Debug dbg,
       
   443 			    Dwarf_P_Die ownerdie,
       
   444 			    Dwarf_Half attr,
       
   445 			    Dwarf_Unsigned value, Dwarf_Error * error)
       
   446 {
       
   447     Dwarf_P_Attribute new_attr;
       
   448     Dwarf_Half attr_form;
       
   449     Dwarf_Small size;
       
   450 
       
   451     if (dbg == NULL) {
       
   452 	_dwarf_p_error(NULL, error, DW_DLE_DBG_NULL);
       
   453 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   454     }
       
   455 
       
   456     if (ownerdie == NULL) {
       
   457 	_dwarf_p_error(dbg, error, DW_DLE_DIE_NULL);
       
   458 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   459     }
       
   460 
       
   461     switch (attr) {
       
   462     case DW_AT_ordering:
       
   463     case DW_AT_byte_size:
       
   464     case DW_AT_bit_offset:
       
   465     case DW_AT_bit_size:
       
   466     case DW_AT_inline:
       
   467     case DW_AT_language:
       
   468     case DW_AT_visibility:
       
   469     case DW_AT_virtuality:
       
   470     case DW_AT_accessibility:
       
   471     case DW_AT_address_class:
       
   472     case DW_AT_calling_convention:
       
   473     case DW_AT_encoding:
       
   474     case DW_AT_identifier_case:
       
   475     case DW_AT_MIPS_loop_unroll_factor:
       
   476     case DW_AT_MIPS_software_pipeline_depth:
       
   477 	break;
       
   478 
       
   479     case DW_AT_decl_column:
       
   480     case DW_AT_decl_file:
       
   481     case DW_AT_decl_line:
       
   482     case DW_AT_const_value:
       
   483     case DW_AT_start_scope:
       
   484     case DW_AT_stride_size:
       
   485     case DW_AT_count:
       
   486     case DW_AT_associated:
       
   487     case DW_AT_allocated:
       
   488     case DW_AT_upper_bound:
       
   489     case DW_AT_lower_bound:
       
   490 	break;
       
   491 
       
   492         default: {
       
   493 	         if ( attr < DW_AT_lo_user || attr > DW_AT_hi_user ) {
       
   494 	             _dwarf_p_error(dbg, error, DW_DLE_INPUT_ATTR_BAD);
       
   495 	             return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   496 	       }
       
   497 	       break;
       
   498 	    }
       
   499         }
       
   500 
       
   501     /* 
       
   502        Compute the number of bytes needed to hold constant. */
       
   503     if (value <= UCHAR_MAX) {
       
   504 	attr_form = DW_FORM_data1;
       
   505 	size = 1;
       
   506     } else if (value <= USHRT_MAX) {
       
   507 	attr_form = DW_FORM_data2;
       
   508 	size = 2;
       
   509     } else if (value <= UINT_MAX) {
       
   510 	attr_form = DW_FORM_data4;
       
   511 	size = 4;
       
   512     } else {
       
   513 	attr_form = DW_FORM_data8;
       
   514 	size = 8;
       
   515     }
       
   516 
       
   517     new_attr = (Dwarf_P_Attribute)
       
   518 	_dwarf_p_get_alloc(dbg, sizeof(struct Dwarf_P_Attribute_s));
       
   519     if (new_attr == NULL) {
       
   520 	_dwarf_p_error(dbg, error, DW_DLE_ALLOC_FAIL);
       
   521 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   522     }
       
   523 
       
   524     new_attr->ar_attribute = attr;
       
   525     new_attr->ar_attribute_form = attr_form;
       
   526     new_attr->ar_rel_type = R_MIPS_NONE;
       
   527     new_attr->ar_reloc_len = 0;	/* irrelevant: unused with R_MIPS_NONE */
       
   528     new_attr->ar_nbytes = size;
       
   529     new_attr->ar_next = 0;
       
   530 
       
   531     new_attr->ar_data = (char *)
       
   532 	_dwarf_p_get_alloc(dbg, size);
       
   533     if (new_attr->ar_data == NULL) {
       
   534 	_dwarf_p_error(dbg, error, DW_DLE_ALLOC_FAIL);
       
   535 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   536     }
       
   537     WRITE_UNALIGNED(dbg, new_attr->ar_data,
       
   538 		    (const void *) &value, sizeof(value), size);
       
   539 
       
   540     /* add attribute to the die */
       
   541     _dwarf_pro_add_at_to_die(ownerdie, new_attr);
       
   542     return new_attr;
       
   543 }
       
   544 
       
   545 
       
   546 /*
       
   547     This function adds attributes whose value
       
   548     is an signed constant.  It determines the 
       
   549     size of the value field from the value of 
       
   550     the constant.
       
   551 */
       
   552 Dwarf_P_Attribute
       
   553 dwarf_add_AT_signed_const(Dwarf_P_Debug dbg,
       
   554 			  Dwarf_P_Die ownerdie,
       
   555 			  Dwarf_Half attr,
       
   556 			  Dwarf_Signed value, Dwarf_Error * error)
       
   557 {
       
   558     Dwarf_P_Attribute new_attr;
       
   559     Dwarf_Half attr_form;
       
   560     Dwarf_Small size;
       
   561 
       
   562     if (dbg == NULL) {
       
   563 	_dwarf_p_error(NULL, error, DW_DLE_DBG_NULL);
       
   564 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   565     }
       
   566 
       
   567     if (ownerdie == NULL) {
       
   568 	_dwarf_p_error(dbg, error, DW_DLE_DIE_NULL);
       
   569 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   570     }
       
   571 
       
   572     switch (attr) {
       
   573     case DW_AT_upper_bound:
       
   574     case DW_AT_lower_bound:
       
   575     case DW_AT_const_value:
       
   576         break;
       
   577 
       
   578     default:{ 
       
   579 	        if ( attr < DW_AT_lo_user || attr > DW_AT_hi_user ) {
       
   580 	             _dwarf_p_error(dbg, error, DW_DLE_INPUT_ATTR_BAD);
       
   581 	             return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   582 	        }
       
   583 	}
       
   584 	break;
       
   585     }
       
   586 
       
   587     /* 
       
   588        Compute the number of bytes needed to hold constant. */
       
   589     if (value >= SCHAR_MIN && value <= SCHAR_MAX) {
       
   590 	attr_form = DW_FORM_data1;
       
   591 	size = 1;
       
   592     } else if (value >= SHRT_MIN && value <= SHRT_MAX) {
       
   593 	attr_form = DW_FORM_data2;
       
   594 	size = 2;
       
   595     } else if (value >= INT_MIN && value <= INT_MAX) {
       
   596 	attr_form = DW_FORM_data4;
       
   597 	size = 4;
       
   598     } else {
       
   599 	attr_form = DW_FORM_data8;
       
   600 	size = 8;
       
   601     }
       
   602 
       
   603     new_attr = (Dwarf_P_Attribute)
       
   604 	_dwarf_p_get_alloc(dbg, sizeof(struct Dwarf_P_Attribute_s));
       
   605     if (new_attr == NULL) {
       
   606 	_dwarf_p_error(dbg, error, DW_DLE_ALLOC_FAIL);
       
   607 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   608     }
       
   609 
       
   610     new_attr->ar_attribute = attr;
       
   611     new_attr->ar_attribute_form = attr_form;
       
   612     new_attr->ar_rel_type = R_MIPS_NONE;
       
   613     new_attr->ar_reloc_len = 0;	/* irrelevant: unused with R_MIPS_NONE */
       
   614     new_attr->ar_nbytes = size;
       
   615     new_attr->ar_next = 0;
       
   616 
       
   617     new_attr->ar_data = (char *)
       
   618 	_dwarf_p_get_alloc(dbg, size);
       
   619     if (new_attr->ar_data == NULL) {
       
   620 	_dwarf_p_error(dbg, error, DW_DLE_ALLOC_FAIL);
       
   621 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   622     }
       
   623     WRITE_UNALIGNED(dbg, new_attr->ar_data,
       
   624 		    (const void *) &value, sizeof(value), size);
       
   625 
       
   626     /* add attribute to the die */
       
   627     _dwarf_pro_add_at_to_die(ownerdie, new_attr);
       
   628     return new_attr;
       
   629 }
       
   630 
       
   631 
       
   632 /*
       
   633     This function adds attributes whose value
       
   634     is a location expression.
       
   635 */
       
   636 Dwarf_P_Attribute
       
   637 dwarf_add_AT_location_expr(Dwarf_P_Debug dbg,
       
   638 			   Dwarf_P_Die ownerdie,
       
   639 			   Dwarf_Half attr,
       
   640 			   Dwarf_P_Expr loc_expr, Dwarf_Error * error)
       
   641 {
       
   642     char encode_buffer[ENCODE_SPACE_NEEDED];
       
   643     int res;
       
   644     Dwarf_P_Attribute new_attr;
       
   645     Dwarf_Half attr_form;
       
   646     char *len_str = 0;
       
   647     int len_size;
       
   648     int block_size;
       
   649     char *block_dest_ptr;
       
   650     int do_len_as_int = 0;
       
   651 
       
   652     if (dbg == NULL) {
       
   653 	_dwarf_p_error(NULL, error, DW_DLE_DBG_NULL);
       
   654 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   655     }
       
   656 
       
   657     if (ownerdie == NULL) {
       
   658 	_dwarf_p_error(dbg, error, DW_DLE_DIE_NULL);
       
   659 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   660     }
       
   661 
       
   662     if (loc_expr == NULL) {
       
   663 	_dwarf_p_error(dbg, error, DW_DLE_EXPR_NULL);
       
   664 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   665     }
       
   666 
       
   667     if (loc_expr->ex_dbg != dbg) {
       
   668 	_dwarf_p_error(dbg, error, DW_DLE_LOC_EXPR_BAD);
       
   669 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   670     }
       
   671     block_size = loc_expr->ex_next_byte_offset;
       
   672 
       
   673     switch (attr) {
       
   674     case DW_AT_location:
       
   675     case DW_AT_string_length:
       
   676     case DW_AT_const_value:
       
   677     case DW_AT_use_location:
       
   678     case DW_AT_return_addr:
       
   679     case DW_AT_data_member_location:
       
   680     case DW_AT_frame_base:
       
   681     case DW_AT_static_link:
       
   682     case DW_AT_vtable_elem_location:
       
   683 	case DW_AT_lower_bound:
       
   684 	case DW_AT_upper_bound:
       
   685 	case DW_AT_count:
       
   686 	case DW_AT_associated:
       
   687 	case DW_AT_allocated:
       
   688 	break;
       
   689 
       
   690         default:
       
   691 	    if ( attr < DW_AT_lo_user || attr > DW_AT_hi_user ) {
       
   692 	    _dwarf_p_error(dbg, error, DW_DLE_INPUT_ATTR_BAD);
       
   693 	    return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   694 	}
       
   695 	    break;
       
   696     }
       
   697 
       
   698     /* 
       
   699        Compute the number of bytes needed to hold constant. */
       
   700     if (block_size <= UCHAR_MAX) {
       
   701 	attr_form = DW_FORM_block1;
       
   702 	len_size = 1;
       
   703 	do_len_as_int = 1;
       
   704     } else if (block_size <= USHRT_MAX) {
       
   705 	attr_form = DW_FORM_block2;
       
   706 	len_size = 2;
       
   707 	do_len_as_int = 1;
       
   708     } else if (block_size <= UINT_MAX) {
       
   709 	attr_form = DW_FORM_block4;
       
   710 	len_size = 4;
       
   711 	do_len_as_int = 1;
       
   712     } else {
       
   713 	attr_form = DW_FORM_block;
       
   714 	res = _dwarf_pro_encode_leb128_nm(block_size, &len_size,
       
   715 					  encode_buffer,
       
   716 					  sizeof(encode_buffer));
       
   717 	if (res != DW_DLV_OK) {
       
   718 	    _dwarf_p_error(dbg, error, DW_DLE_ALLOC_FAIL);
       
   719 	    return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   720 	}
       
   721 	len_str = (char *) encode_buffer;
       
   722     }
       
   723 
       
   724     new_attr = (Dwarf_P_Attribute)
       
   725 	_dwarf_p_get_alloc(dbg, sizeof(struct Dwarf_P_Attribute_s));
       
   726     if (new_attr == NULL) {
       
   727 	_dwarf_p_error(dbg, error, DW_DLE_ALLOC_FAIL);
       
   728 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   729     }
       
   730 
       
   731     new_attr->ar_attribute = attr;
       
   732     new_attr->ar_attribute_form = attr_form;
       
   733     new_attr->ar_reloc_len = dbg->de_pointer_size;
       
   734     if (loc_expr->ex_reloc_sym_index != NO_ELF_SYM_INDEX) {
       
   735 	new_attr->ar_rel_type = dbg->de_ptr_reloc;
       
   736     } else {
       
   737 	new_attr->ar_rel_type = R_MIPS_NONE;
       
   738     }
       
   739     new_attr->ar_rel_symidx = loc_expr->ex_reloc_sym_index;
       
   740     new_attr->ar_rel_offset =
       
   741 	(Dwarf_Word) loc_expr->ex_reloc_offset + len_size;
       
   742 
       
   743     new_attr->ar_nbytes = block_size + len_size;
       
   744 
       
   745     new_attr->ar_next = 0;
       
   746     new_attr->ar_data = block_dest_ptr =
       
   747 	(char *) _dwarf_p_get_alloc(dbg, block_size + len_size);
       
   748     if (new_attr->ar_data == NULL) {
       
   749 	_dwarf_p_error(dbg, error, DW_DLE_ALLOC_FAIL);
       
   750 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   751     }
       
   752 
       
   753     if (do_len_as_int) {
       
   754 	WRITE_UNALIGNED(dbg, block_dest_ptr, (const void *) &block_size,
       
   755 			sizeof(block_size), len_size);
       
   756     } else {
       
   757 	/* Is uleb number form, DW_FORM_block. See above. */
       
   758 	memcpy(block_dest_ptr, len_str, len_size);
       
   759     }
       
   760     block_dest_ptr += len_size;
       
   761     memcpy(block_dest_ptr, &(loc_expr->ex_byte_stream[0]), block_size);
       
   762 
       
   763     /* add attribute to the die */
       
   764     _dwarf_pro_add_at_to_die(ownerdie, new_attr);
       
   765     return new_attr;
       
   766 }
       
   767 
       
   768 
       
   769 /*
       
   770     This function adds attributes of reference class.
       
   771     The references here are local CU references, 
       
   772     not DW_FORM_ref_addr.
       
   773     The offset field is 4 bytes for 32-bit objects,
       
   774     and 8-bytes for 64-bit objects.  Otherdie is the
       
   775     that is referenced by ownerdie.
       
   776 
       
   777     For reference attributes, the ar_data and ar_nbytes
       
   778     are not needed.  Instead, the ar_ref_die points to
       
   779     the other die, and its di_offset value is used as
       
   780     the reference value.
       
   781 */
       
   782 Dwarf_P_Attribute
       
   783 dwarf_add_AT_reference(Dwarf_P_Debug dbg,
       
   784 		       Dwarf_P_Die ownerdie,
       
   785 		       Dwarf_Half attr,
       
   786 		       Dwarf_P_Die otherdie, Dwarf_Error * error)
       
   787 {
       
   788     Dwarf_P_Attribute new_attr;
       
   789 
       
   790     if (dbg == NULL) {
       
   791 	_dwarf_p_error(NULL, error, DW_DLE_DBG_NULL);
       
   792 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   793     }
       
   794 
       
   795     if (ownerdie == NULL) {
       
   796 	_dwarf_p_error(dbg, error, DW_DLE_DIE_NULL);
       
   797 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   798     }
       
   799 
       
   800     if (otherdie == NULL) {
       
   801 	_dwarf_p_error(dbg, error, DW_DLE_DIE_NULL);
       
   802 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   803     }
       
   804 
       
   805     switch (attr) {
       
   806     case DW_AT_specification:
       
   807     case DW_AT_discr:
       
   808     case DW_AT_common_reference:
       
   809     case DW_AT_import:
       
   810     case DW_AT_containing_type:
       
   811     case DW_AT_default_value:
       
   812     case DW_AT_abstract_origin:
       
   813     case DW_AT_friend:
       
   814     case DW_AT_priority:
       
   815     case DW_AT_type:
       
   816     case DW_AT_lower_bound:
       
   817     case DW_AT_upper_bound:
       
   818     case DW_AT_count:
       
   819     case DW_AT_associated:
       
   820     case DW_AT_allocated:
       
   821     case DW_AT_sibling:
       
   822     case DW_AT_namelist_item:
       
   823 	break;
       
   824 
       
   825     default:
       
   826 	if ( attr < DW_AT_lo_user || attr > DW_AT_hi_user ) {
       
   827 	    _dwarf_p_error(dbg, error, DW_DLE_INPUT_ATTR_BAD);
       
   828 	    return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   829 	}
       
   830 	break;
       
   831     }
       
   832 
       
   833     new_attr = (Dwarf_P_Attribute)
       
   834 	_dwarf_p_get_alloc(dbg, sizeof(struct Dwarf_P_Attribute_s));
       
   835     if (new_attr == NULL) {
       
   836 	_dwarf_p_error(dbg, error, DW_DLE_ALLOC_FAIL);
       
   837 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   838     }
       
   839 
       
   840     new_attr->ar_attribute = attr;
       
   841     new_attr->ar_attribute_form = dbg->de_ar_ref_attr_form;
       
   842     new_attr->ar_nbytes = dbg->de_offset_size;
       
   843     new_attr->ar_reloc_len = dbg->de_offset_size;
       
   844     new_attr->ar_ref_die = otherdie;
       
   845     new_attr->ar_rel_type = R_MIPS_NONE;
       
   846     new_attr->ar_next = 0;
       
   847 
       
   848     /* add attribute to the die */
       
   849     _dwarf_pro_add_at_to_die(ownerdie, new_attr);
       
   850     return new_attr;
       
   851 }
       
   852 
       
   853 
       
   854 /*
       
   855     This function adds attributes of the flag class.
       
   856 */
       
   857 Dwarf_P_Attribute
       
   858 dwarf_add_AT_flag(Dwarf_P_Debug dbg,
       
   859 		  Dwarf_P_Die ownerdie,
       
   860 		  Dwarf_Half attr,
       
   861 		  Dwarf_Small flag, Dwarf_Error * error)
       
   862 {
       
   863     Dwarf_P_Attribute new_attr;
       
   864 
       
   865     if (dbg == NULL) {
       
   866 	_dwarf_p_error(NULL, error, DW_DLE_DBG_NULL);
       
   867 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   868     }
       
   869 
       
   870     if (ownerdie == NULL) {
       
   871 	_dwarf_p_error(dbg, error, DW_DLE_DIE_NULL);
       
   872 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   873     }
       
   874 
       
   875 #if 0    
       
   876     switch (attr) {
       
   877     case DW_AT_is_optional:
       
   878     case DW_AT_artificial:
       
   879     case DW_AT_declaration:
       
   880     case DW_AT_external:
       
   881     case DW_AT_prototyped:
       
   882     case DW_AT_variable_parameter:
       
   883 	break;
       
   884 
       
   885         default:
       
   886 	    if ( attr < DW_AT_lo_user || attr > DW_AT_hi_user ) {
       
   887 	    _dwarf_p_error(dbg, error, DW_DLE_INPUT_ATTR_BAD);
       
   888 	    return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   889 	}
       
   890     	    break;
       
   891     }
       
   892 #endif    
       
   893 
       
   894     new_attr = (Dwarf_P_Attribute)
       
   895 	_dwarf_p_get_alloc(dbg, sizeof(struct Dwarf_P_Attribute_s));
       
   896     if (new_attr == NULL) {
       
   897 	_dwarf_p_error(dbg, error, DW_DLE_ALLOC_FAIL);
       
   898 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   899     }
       
   900 
       
   901     new_attr->ar_attribute = attr;
       
   902     new_attr->ar_attribute_form = DW_FORM_flag;
       
   903     new_attr->ar_nbytes = 1;
       
   904     new_attr->ar_reloc_len = 0;	/* not used */
       
   905     new_attr->ar_rel_type = R_MIPS_NONE;
       
   906     new_attr->ar_next = 0;
       
   907 
       
   908     new_attr->ar_data = (char *)
       
   909 	_dwarf_p_get_alloc(dbg, 1);
       
   910     if (new_attr->ar_data == NULL) {
       
   911 	_dwarf_p_error(dbg, error, DW_DLE_ALLOC_FAIL);
       
   912 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   913     }
       
   914     memcpy(new_attr->ar_data, &flag, 1);
       
   915 
       
   916     /* add attribute to the die */
       
   917     _dwarf_pro_add_at_to_die(ownerdie, new_attr);
       
   918     return new_attr;
       
   919 }
       
   920 
       
   921 
       
   922 /*
       
   923     This function adds values of attributes
       
   924     belonging to the string class.
       
   925 */
       
   926 Dwarf_P_Attribute
       
   927 dwarf_add_AT_string(Dwarf_P_Debug dbg,
       
   928 		    Dwarf_P_Die ownerdie,
       
   929 		    Dwarf_Half attr, char *string, Dwarf_Error * error)
       
   930 {
       
   931     Dwarf_P_Attribute new_attr;
       
   932 
       
   933     if (dbg == NULL) {
       
   934 	_dwarf_p_error(NULL, error, DW_DLE_DBG_NULL);
       
   935 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   936     }
       
   937 
       
   938     if (ownerdie == NULL) {
       
   939 	_dwarf_p_error(dbg, error, DW_DLE_DIE_NULL);
       
   940 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   941     }
       
   942 
       
   943     new_attr = (Dwarf_P_Attribute)
       
   944 	_dwarf_p_get_alloc(dbg, sizeof(struct Dwarf_P_Attribute_s));
       
   945     if (new_attr == NULL) {
       
   946 	_dwarf_p_error(dbg, error, DW_DLE_ALLOC_FAIL);
       
   947 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   948     }
       
   949 
       
   950     switch (attr) {
       
   951     case DW_AT_name:
       
   952     case DW_AT_comp_dir:
       
   953     case DW_AT_const_value:
       
   954     case DW_AT_producer:
       
   955 	break;
       
   956 
       
   957 	default:
       
   958 	    if ( attr < DW_AT_lo_user || attr > DW_AT_hi_user ) {
       
   959 	    _dwarf_p_error(dbg, error, DW_DLE_INPUT_ATTR_BAD);
       
   960 	    return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   961 	}
       
   962 	    break;
       
   963     }
       
   964 
       
   965     new_attr->ar_attribute = attr;
       
   966     new_attr->ar_attribute_form = DW_FORM_string;
       
   967     new_attr->ar_nbytes = strlen(string) + 1;
       
   968     new_attr->ar_next = 0;
       
   969 
       
   970     new_attr->ar_data =
       
   971 	(char *) _dwarf_p_get_alloc(dbg, strlen(string)+1);
       
   972     if (new_attr->ar_data == NULL) {
       
   973 	_dwarf_p_error(dbg, error, DW_DLE_ALLOC_FAIL);
       
   974 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   975     }
       
   976 
       
   977     strcpy(new_attr->ar_data, string);
       
   978     new_attr->ar_rel_type = R_MIPS_NONE;
       
   979     new_attr->ar_reloc_len = 0;	/* unused for R_MIPS_NONE */
       
   980 
       
   981     /* add attribute to the die */
       
   982     _dwarf_pro_add_at_to_die(ownerdie, new_attr);
       
   983     return new_attr;
       
   984 }
       
   985 
       
   986 
       
   987 Dwarf_P_Attribute
       
   988 dwarf_add_AT_const_value_string(Dwarf_P_Die ownerdie,
       
   989 				char *string_value, Dwarf_Error * error)
       
   990 {
       
   991     Dwarf_P_Attribute new_attr;
       
   992 
       
   993     if (ownerdie == NULL) {
       
   994 	_dwarf_p_error(NULL, error, DW_DLE_DIE_NULL);
       
   995 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
   996     }
       
   997 
       
   998     new_attr = (Dwarf_P_Attribute)
       
   999         _dwarf_p_get_alloc(ownerdie->di_dbg, sizeof(struct Dwarf_P_Attribute_s));
       
  1000     if (new_attr == NULL) {
       
  1001 	_dwarf_p_error(NULL, error, DW_DLE_ALLOC_FAIL);
       
  1002 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
  1003     }
       
  1004 
       
  1005     new_attr->ar_attribute = DW_AT_const_value;
       
  1006     new_attr->ar_attribute_form = DW_FORM_string;
       
  1007     new_attr->ar_nbytes = strlen(string_value) + 1;
       
  1008     new_attr->ar_next = 0;
       
  1009 
       
  1010     new_attr->ar_data =
       
  1011 	(char *) _dwarf_p_get_alloc(ownerdie->di_dbg, strlen(string_value)+1);
       
  1012     if (new_attr->ar_data == NULL) {
       
  1013 	_dwarf_p_error(NULL, error, DW_DLE_ALLOC_FAIL);
       
  1014 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
  1015     }
       
  1016 
       
  1017     strcpy(new_attr->ar_data, string_value);
       
  1018     new_attr->ar_rel_type = R_MIPS_NONE;
       
  1019     new_attr->ar_reloc_len = 0;	/* unused for R_MIPS_NONE */
       
  1020 
       
  1021     /* add attribute to the die */
       
  1022     _dwarf_pro_add_at_to_die(ownerdie, new_attr);
       
  1023     return new_attr;
       
  1024 }
       
  1025 
       
  1026 
       
  1027 Dwarf_P_Attribute
       
  1028 dwarf_add_AT_producer(Dwarf_P_Die ownerdie,
       
  1029 		      char *producer_string, Dwarf_Error * error)
       
  1030 {
       
  1031     Dwarf_P_Attribute new_attr;
       
  1032 
       
  1033     if (ownerdie == NULL) {
       
  1034 	_dwarf_p_error(NULL, error, DW_DLE_DIE_NULL);
       
  1035 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
  1036     }
       
  1037 
       
  1038     new_attr = (Dwarf_P_Attribute)
       
  1039         _dwarf_p_get_alloc(ownerdie->di_dbg, sizeof(struct Dwarf_P_Attribute_s));
       
  1040     if (new_attr == NULL) {
       
  1041 	_dwarf_p_error(NULL, error, DW_DLE_ALLOC_FAIL);
       
  1042 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
  1043     }
       
  1044 
       
  1045     new_attr->ar_attribute = DW_AT_producer;
       
  1046     new_attr->ar_attribute_form = DW_FORM_string;
       
  1047     new_attr->ar_nbytes = strlen(producer_string) + 1;
       
  1048     new_attr->ar_next = 0;
       
  1049 
       
  1050     new_attr->ar_data =
       
  1051 	(char *) _dwarf_p_get_alloc(ownerdie->di_dbg, strlen(producer_string)+1);
       
  1052     if (new_attr->ar_data == NULL) {
       
  1053 	_dwarf_p_error(NULL, error, DW_DLE_ALLOC_FAIL);
       
  1054 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
  1055     }
       
  1056 
       
  1057     strcpy(new_attr->ar_data, producer_string);
       
  1058     new_attr->ar_rel_type = R_MIPS_NONE;
       
  1059     new_attr->ar_reloc_len = 0;	/* unused for R_MIPS_NONE */
       
  1060 
       
  1061     /* add attribute to the die */
       
  1062     _dwarf_pro_add_at_to_die(ownerdie, new_attr);
       
  1063     return new_attr;
       
  1064 }
       
  1065 
       
  1066 
       
  1067 Dwarf_P_Attribute
       
  1068 dwarf_add_AT_const_value_signedint(Dwarf_P_Die ownerdie,
       
  1069 				   Dwarf_Signed signed_value,
       
  1070 				   Dwarf_Error * error)
       
  1071 {
       
  1072     Dwarf_P_Attribute new_attr;
       
  1073     int leb_size;
       
  1074     char encode_buffer[ENCODE_SPACE_NEEDED];
       
  1075     int res;
       
  1076 
       
  1077     if (ownerdie == NULL) {
       
  1078 	_dwarf_p_error(NULL, error, DW_DLE_DIE_NULL);
       
  1079 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
  1080     }
       
  1081 
       
  1082     new_attr = (Dwarf_P_Attribute)
       
  1083         _dwarf_p_get_alloc(ownerdie->di_dbg, sizeof(struct Dwarf_P_Attribute_s));
       
  1084     if (new_attr == NULL) {
       
  1085 	_dwarf_p_error(NULL, error, DW_DLE_ALLOC_FAIL);
       
  1086 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
  1087     }
       
  1088 
       
  1089     new_attr->ar_attribute = DW_AT_const_value;
       
  1090     new_attr->ar_attribute_form = DW_FORM_sdata;
       
  1091     new_attr->ar_rel_type = R_MIPS_NONE;
       
  1092     new_attr->ar_reloc_len = 0;	/* unused for R_MIPS_NONE */
       
  1093     new_attr->ar_next = 0;
       
  1094 
       
  1095     res = _dwarf_pro_encode_signed_leb128_nm(signed_value, &leb_size,
       
  1096 					     encode_buffer,
       
  1097 					     sizeof(encode_buffer));
       
  1098     if (res != DW_DLV_OK) {
       
  1099 	_dwarf_p_error(NULL, error, DW_DLE_ALLOC_FAIL);
       
  1100 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
  1101     }
       
  1102     new_attr->ar_data = (char *)
       
  1103         _dwarf_p_get_alloc(ownerdie->di_dbg, leb_size);
       
  1104     if (new_attr->ar_data == NULL) {
       
  1105 	_dwarf_p_error(NULL, error, DW_DLE_ALLOC_FAIL);
       
  1106 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
  1107     }
       
  1108     memcpy(new_attr->ar_data, encode_buffer, leb_size);
       
  1109     new_attr->ar_nbytes = leb_size;
       
  1110 
       
  1111     /* add attribute to the die */
       
  1112     _dwarf_pro_add_at_to_die(ownerdie, new_attr);
       
  1113     return new_attr;
       
  1114 }
       
  1115 
       
  1116 
       
  1117 Dwarf_P_Attribute
       
  1118 dwarf_add_AT_const_value_unsignedint(Dwarf_P_Die ownerdie,
       
  1119 				     Dwarf_Unsigned unsigned_value,
       
  1120 				     Dwarf_Error * error)
       
  1121 {
       
  1122     Dwarf_P_Attribute new_attr;
       
  1123     int leb_size;
       
  1124     char encode_buffer[ENCODE_SPACE_NEEDED];
       
  1125     int res;
       
  1126 
       
  1127     if (ownerdie == NULL) {
       
  1128 	_dwarf_p_error(NULL, error, DW_DLE_DIE_NULL);
       
  1129 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
  1130     }
       
  1131 
       
  1132     new_attr = (Dwarf_P_Attribute)
       
  1133         _dwarf_p_get_alloc(ownerdie->di_dbg, sizeof(struct Dwarf_P_Attribute_s));
       
  1134     if (new_attr == NULL) {
       
  1135 	_dwarf_p_error(NULL, error, DW_DLE_ALLOC_FAIL);
       
  1136 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
  1137     }
       
  1138 
       
  1139     new_attr->ar_attribute = DW_AT_const_value;
       
  1140     new_attr->ar_attribute_form = DW_FORM_udata;
       
  1141     new_attr->ar_rel_type = R_MIPS_NONE;
       
  1142     new_attr->ar_reloc_len = 0;	/* unused for R_MIPS_NONE */
       
  1143     new_attr->ar_next = 0;
       
  1144 
       
  1145     res = _dwarf_pro_encode_leb128_nm(unsigned_value, &leb_size,
       
  1146 				      encode_buffer,
       
  1147 				      sizeof(encode_buffer));
       
  1148     if (res != DW_DLV_OK) {
       
  1149 	_dwarf_p_error(NULL, error, DW_DLE_ALLOC_FAIL);
       
  1150 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
  1151     }
       
  1152     new_attr->ar_data = (char *)
       
  1153 	_dwarf_p_get_alloc(ownerdie->di_dbg, leb_size);
       
  1154     if (new_attr->ar_data == NULL) {
       
  1155 	_dwarf_p_error(NULL, error, DW_DLE_ALLOC_FAIL);
       
  1156 	return ((Dwarf_P_Attribute) DW_DLV_BADADDR);
       
  1157     }
       
  1158     memcpy(new_attr->ar_data, encode_buffer, leb_size);
       
  1159     new_attr->ar_nbytes = leb_size;
       
  1160 
       
  1161     /* add attribute to the die */
       
  1162     _dwarf_pro_add_at_to_die(ownerdie, new_attr);
       
  1163     return new_attr;
       
  1164 }