149d3bc91SRichard Lowe /*
207dc1947SRichard Lowe   Copyright (C) 2000-2006 Silicon Graphics, Inc.  All Rights Reserved.
3*4d9fdb46SRobert Mustacchi   Portions Copyright (C) 2007-2019 David Anderson. All Rights Reserved.
4*4d9fdb46SRobert Mustacchi   Portions Copyright 2012 SN Systems Ltd. All rights reserved.
5*4d9fdb46SRobert Mustacchi 
6*4d9fdb46SRobert Mustacchi   This program is free software; you can redistribute it
7*4d9fdb46SRobert Mustacchi   and/or modify it under the terms of version 2.1 of the
8*4d9fdb46SRobert Mustacchi   GNU Lesser General Public License as published by the Free
9*4d9fdb46SRobert Mustacchi   Software Foundation.
10*4d9fdb46SRobert Mustacchi 
11*4d9fdb46SRobert Mustacchi   This program is distributed in the hope that it would be
12*4d9fdb46SRobert Mustacchi   useful, but WITHOUT ANY WARRANTY; without even the implied
13*4d9fdb46SRobert Mustacchi   warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
14*4d9fdb46SRobert Mustacchi   PURPOSE.
15*4d9fdb46SRobert Mustacchi 
16*4d9fdb46SRobert Mustacchi   Further, this software is distributed without any warranty
17*4d9fdb46SRobert Mustacchi   that it is free of the rightful claim of any third person
18*4d9fdb46SRobert Mustacchi   regarding infringement or the like.  Any license provided
19*4d9fdb46SRobert Mustacchi   herein, whether implied or otherwise, applies only to this
20*4d9fdb46SRobert Mustacchi   software file.  Patent licenses, if any, provided herein
21*4d9fdb46SRobert Mustacchi   do not apply to combinations of this program with other
22*4d9fdb46SRobert Mustacchi   software, or any other product whatsoever.
23*4d9fdb46SRobert Mustacchi 
24*4d9fdb46SRobert Mustacchi   You should have received a copy of the GNU Lesser General
25*4d9fdb46SRobert Mustacchi   Public License along with this program; if not, write the
26*4d9fdb46SRobert Mustacchi   Free Software Foundation, Inc., 51 Franklin Street - Fifth
27*4d9fdb46SRobert Mustacchi   Floor, Boston MA 02110-1301, USA.
2849d3bc91SRichard Lowe 
29*4d9fdb46SRobert Mustacchi */
3049d3bc91SRichard Lowe 
31*4d9fdb46SRobert Mustacchi #include "config.h"
32*4d9fdb46SRobert Mustacchi #include <stdio.h>
33*4d9fdb46SRobert Mustacchi #include "dwarf_incl.h"
34*4d9fdb46SRobert Mustacchi #include "dwarf_alloc.h"
35*4d9fdb46SRobert Mustacchi #include "dwarf_error.h"
36*4d9fdb46SRobert Mustacchi #include "dwarf_util.h"
37*4d9fdb46SRobert Mustacchi #include "dwarfstring.h"
38*4d9fdb46SRobert Mustacchi #include "dwarf_die_deliv.h"
3949d3bc91SRichard Lowe 
40*4d9fdb46SRobert Mustacchi #define FALSE 0
41*4d9fdb46SRobert Mustacchi #define TRUE 1
42*4d9fdb46SRobert Mustacchi 
43*4d9fdb46SRobert Mustacchi /* These are sanity checks, not 'rules'. */
44*4d9fdb46SRobert Mustacchi #define MINIMUM_ADDRESS_SIZE 2
45*4d9fdb46SRobert Mustacchi #define MAXIMUM_ADDRESS_SIZE 8
46*4d9fdb46SRobert Mustacchi 
47*4d9fdb46SRobert Mustacchi static void assign_correct_unit_type(Dwarf_CU_Context cu_context);
48*4d9fdb46SRobert Mustacchi static int find_cu_die_base_fields(Dwarf_Debug dbg,
49*4d9fdb46SRobert Mustacchi     Dwarf_CU_Context cucon,
50*4d9fdb46SRobert Mustacchi     Dwarf_Die cudie,
51*4d9fdb46SRobert Mustacchi     Dwarf_Error*    error);
52*4d9fdb46SRobert Mustacchi 
53*4d9fdb46SRobert Mustacchi static int _dwarf_siblingof_internal(Dwarf_Debug dbg,
54*4d9fdb46SRobert Mustacchi     Dwarf_Die die,
55*4d9fdb46SRobert Mustacchi     Dwarf_CU_Context context,
56*4d9fdb46SRobert Mustacchi     Dwarf_Bool is_info,
57*4d9fdb46SRobert Mustacchi     Dwarf_Die * caller_ret_die, Dwarf_Error * error);
58*4d9fdb46SRobert Mustacchi 
59*4d9fdb46SRobert Mustacchi /*  see cuandunit.txt for an overview of the
60*4d9fdb46SRobert Mustacchi     DWARF5 split dwarf sections and values
61*4d9fdb46SRobert Mustacchi     and the DWARF4 GNU cc version of a draft
62*4d9fdb46SRobert Mustacchi     version of DWARF5 (quite different from
63*4d9fdb46SRobert Mustacchi     the final DWARF5).
6407dc1947SRichard Lowe */
6507dc1947SRichard Lowe 
66*4d9fdb46SRobert Mustacchi /*  New October 2011.  Enables client code to know if
67*4d9fdb46SRobert Mustacchi     it is a debug_info or debug_types context. */
68*4d9fdb46SRobert Mustacchi Dwarf_Bool
dwarf_get_die_infotypes_flag(Dwarf_Die die)69*4d9fdb46SRobert Mustacchi dwarf_get_die_infotypes_flag(Dwarf_Die die)
70*4d9fdb46SRobert Mustacchi {
71*4d9fdb46SRobert Mustacchi     return die->di_is_info;
72*4d9fdb46SRobert Mustacchi }
7349d3bc91SRichard Lowe 
74*4d9fdb46SRobert Mustacchi #if 0
75*4d9fdb46SRobert Mustacchi static void
76*4d9fdb46SRobert Mustacchi dump_bytes(char * msg,Dwarf_Small * start, long len)
77*4d9fdb46SRobert Mustacchi {
78*4d9fdb46SRobert Mustacchi     Dwarf_Small *end = start + len;
79*4d9fdb46SRobert Mustacchi     Dwarf_Small *cur = start;
8049d3bc91SRichard Lowe 
81*4d9fdb46SRobert Mustacchi     printf("%s ",msg);
82*4d9fdb46SRobert Mustacchi     for (; cur < end; cur++) {
83*4d9fdb46SRobert Mustacchi         printf("%02x ", *cur);
84*4d9fdb46SRobert Mustacchi     }
85*4d9fdb46SRobert Mustacchi     printf("\n");
86*4d9fdb46SRobert Mustacchi }
8749d3bc91SRichard Lowe #endif
8849d3bc91SRichard Lowe 
8949d3bc91SRichard Lowe /*
90*4d9fdb46SRobert Mustacchi     For a given Dwarf_Debug dbg, this function checks
91*4d9fdb46SRobert Mustacchi     if a CU that includes the given offset has been read
92*4d9fdb46SRobert Mustacchi     or not.  If yes, it returns the Dwarf_CU_Context
93*4d9fdb46SRobert Mustacchi     for the CU.  Otherwise it returns NULL.  Being an
94*4d9fdb46SRobert Mustacchi     internal routine, it is assumed that a valid dbg
9549d3bc91SRichard Lowe     is passed.
9649d3bc91SRichard Lowe 
9749d3bc91SRichard Lowe     **This is a sequential search.  May be too slow.
9849d3bc91SRichard Lowe 
9949d3bc91SRichard Lowe     If debug_info and debug_abbrev not loaded, this will
10049d3bc91SRichard Lowe     wind up returning NULL. So no need to load before calling
10149d3bc91SRichard Lowe     this.
10249d3bc91SRichard Lowe */
10349d3bc91SRichard Lowe static Dwarf_CU_Context
_dwarf_find_CU_Context(Dwarf_Debug dbg,Dwarf_Off offset,Dwarf_Bool is_info)104*4d9fdb46SRobert Mustacchi _dwarf_find_CU_Context(Dwarf_Debug dbg, Dwarf_Off offset,Dwarf_Bool is_info)
10549d3bc91SRichard Lowe {
10607dc1947SRichard Lowe     Dwarf_CU_Context cu_context = 0;
107*4d9fdb46SRobert Mustacchi     Dwarf_Debug_InfoTypes dis = is_info? &dbg->de_info_reading:
108*4d9fdb46SRobert Mustacchi         &dbg->de_types_reading;
10949d3bc91SRichard Lowe 
110*4d9fdb46SRobert Mustacchi     if (offset >= dis->de_last_offset)
11107dc1947SRichard Lowe         return (NULL);
11249d3bc91SRichard Lowe 
113*4d9fdb46SRobert Mustacchi     if (dis->de_cu_context != NULL &&
114*4d9fdb46SRobert Mustacchi         dis->de_cu_context->cc_next != NULL &&
115*4d9fdb46SRobert Mustacchi         dis->de_cu_context->cc_next->cc_debug_offset == offset) {
11649d3bc91SRichard Lowe 
117*4d9fdb46SRobert Mustacchi         return (dis->de_cu_context->cc_next);
11849d3bc91SRichard Lowe     }
11949d3bc91SRichard Lowe 
120*4d9fdb46SRobert Mustacchi     if (dis->de_cu_context != NULL &&
121*4d9fdb46SRobert Mustacchi         dis->de_cu_context->cc_debug_offset <= offset) {
12249d3bc91SRichard Lowe 
123*4d9fdb46SRobert Mustacchi         for (cu_context = dis->de_cu_context;
124*4d9fdb46SRobert Mustacchi             cu_context != NULL;
125*4d9fdb46SRobert Mustacchi             cu_context = cu_context->cc_next) {
12649d3bc91SRichard Lowe 
127*4d9fdb46SRobert Mustacchi             if (offset >= cu_context->cc_debug_offset &&
128*4d9fdb46SRobert Mustacchi                 offset < cu_context->cc_debug_offset +
12907dc1947SRichard Lowe                 cu_context->cc_length + cu_context->cc_length_size
13007dc1947SRichard Lowe                 + cu_context->cc_extension_size) {
13149d3bc91SRichard Lowe 
13207dc1947SRichard Lowe                 return (cu_context);
13307dc1947SRichard Lowe             }
13407dc1947SRichard Lowe         }
13549d3bc91SRichard Lowe     }
13649d3bc91SRichard Lowe 
137*4d9fdb46SRobert Mustacchi     for (cu_context = dis->de_cu_context_list;
138*4d9fdb46SRobert Mustacchi         cu_context != NULL;
139*4d9fdb46SRobert Mustacchi         cu_context = cu_context->cc_next) {
14049d3bc91SRichard Lowe 
141*4d9fdb46SRobert Mustacchi         if (offset >= cu_context->cc_debug_offset &&
142*4d9fdb46SRobert Mustacchi             offset < cu_context->cc_debug_offset +
14307dc1947SRichard Lowe             cu_context->cc_length + cu_context->cc_length_size
14407dc1947SRichard Lowe             + cu_context->cc_extension_size) {
14549d3bc91SRichard Lowe 
14607dc1947SRichard Lowe             return (cu_context);
14707dc1947SRichard Lowe         }
14849d3bc91SRichard Lowe     }
14949d3bc91SRichard Lowe 
15049d3bc91SRichard Lowe     return (NULL);
15149d3bc91SRichard Lowe }
15249d3bc91SRichard Lowe 
153*4d9fdb46SRobert Mustacchi int
dwarf_get_debugfission_for_die(Dwarf_Die die,struct Dwarf_Debug_Fission_Per_CU_s * fission_out,Dwarf_Error * error)154*4d9fdb46SRobert Mustacchi dwarf_get_debugfission_for_die(Dwarf_Die die,
155*4d9fdb46SRobert Mustacchi     struct Dwarf_Debug_Fission_Per_CU_s *fission_out,
156*4d9fdb46SRobert Mustacchi     Dwarf_Error *error)
157*4d9fdb46SRobert Mustacchi {
158*4d9fdb46SRobert Mustacchi     Dwarf_CU_Context context = 0;
159*4d9fdb46SRobert Mustacchi     Dwarf_Debug dbg = 0;
160*4d9fdb46SRobert Mustacchi     struct Dwarf_Debug_Fission_Per_CU_s * percu = 0;
16149d3bc91SRichard Lowe 
162*4d9fdb46SRobert Mustacchi     CHECK_DIE(die, DW_DLV_ERROR);
163*4d9fdb46SRobert Mustacchi     context = die->di_cu_context;
164*4d9fdb46SRobert Mustacchi     dbg = context->cc_dbg;
165*4d9fdb46SRobert Mustacchi     if (!_dwarf_file_has_debug_fission_index(dbg)) {
166*4d9fdb46SRobert Mustacchi         return DW_DLV_NO_ENTRY;
167*4d9fdb46SRobert Mustacchi     }
168*4d9fdb46SRobert Mustacchi 
169*4d9fdb46SRobert Mustacchi     /*  Logic should work for DW4 and DW5. */
170*4d9fdb46SRobert Mustacchi     if (context->cc_unit_type == DW_UT_type||
171*4d9fdb46SRobert Mustacchi         context->cc_unit_type == DW_UT_split_type ) {
172*4d9fdb46SRobert Mustacchi         if (!_dwarf_file_has_debug_fission_tu_index(dbg)) {
173*4d9fdb46SRobert Mustacchi             return DW_DLV_NO_ENTRY;
174*4d9fdb46SRobert Mustacchi         }
175*4d9fdb46SRobert Mustacchi     } else if (context->cc_unit_type == DW_UT_split_compile) {
176*4d9fdb46SRobert Mustacchi         if (!_dwarf_file_has_debug_fission_cu_index(dbg)) {
177*4d9fdb46SRobert Mustacchi             return DW_DLV_NO_ENTRY;
178*4d9fdb46SRobert Mustacchi         }
179*4d9fdb46SRobert Mustacchi     }
180*4d9fdb46SRobert Mustacchi     percu = &context->cc_dwp_offsets;
181*4d9fdb46SRobert Mustacchi     if (!percu->pcu_type) {
182*4d9fdb46SRobert Mustacchi         return DW_DLV_NO_ENTRY;
183*4d9fdb46SRobert Mustacchi     }
184*4d9fdb46SRobert Mustacchi     *fission_out = *percu;
185*4d9fdb46SRobert Mustacchi     return DW_DLV_OK;
186*4d9fdb46SRobert Mustacchi }
187*4d9fdb46SRobert Mustacchi 
188*4d9fdb46SRobert Mustacchi static Dwarf_Bool
is_unknown_UT_value(int ut)189*4d9fdb46SRobert Mustacchi is_unknown_UT_value(int ut)
190*4d9fdb46SRobert Mustacchi {
191*4d9fdb46SRobert Mustacchi     switch(ut) {
192*4d9fdb46SRobert Mustacchi     case DW_UT_compile:
193*4d9fdb46SRobert Mustacchi     case DW_UT_type:
194*4d9fdb46SRobert Mustacchi     case DW_UT_partial:
195*4d9fdb46SRobert Mustacchi         return FALSE;
196*4d9fdb46SRobert Mustacchi     case DW_UT_skeleton:
197*4d9fdb46SRobert Mustacchi     case DW_UT_split_compile:
198*4d9fdb46SRobert Mustacchi     case DW_UT_split_type:
199*4d9fdb46SRobert Mustacchi         return FALSE;
200*4d9fdb46SRobert Mustacchi     }
201*4d9fdb46SRobert Mustacchi     return TRUE;
202*4d9fdb46SRobert Mustacchi }
203*4d9fdb46SRobert Mustacchi 
204*4d9fdb46SRobert Mustacchi 
205*4d9fdb46SRobert Mustacchi /*  ASSERT: whichone is a DW_SECT* macro value. */
206*4d9fdb46SRobert Mustacchi Dwarf_Unsigned
_dwarf_get_dwp_extra_offset(struct Dwarf_Debug_Fission_Per_CU_s * dwp,unsigned whichone,Dwarf_Unsigned * size)207*4d9fdb46SRobert Mustacchi _dwarf_get_dwp_extra_offset(struct Dwarf_Debug_Fission_Per_CU_s* dwp,
208*4d9fdb46SRobert Mustacchi     unsigned whichone, Dwarf_Unsigned * size)
209*4d9fdb46SRobert Mustacchi {
210*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned sectoff = 0;
211*4d9fdb46SRobert Mustacchi     if (!dwp->pcu_type) {
212*4d9fdb46SRobert Mustacchi         return 0;
213*4d9fdb46SRobert Mustacchi     }
214*4d9fdb46SRobert Mustacchi     sectoff = dwp->pcu_offset[whichone];
215*4d9fdb46SRobert Mustacchi     *size = dwp->pcu_size[whichone];
216*4d9fdb46SRobert Mustacchi     return sectoff;
217*4d9fdb46SRobert Mustacchi }
218*4d9fdb46SRobert Mustacchi 
219*4d9fdb46SRobert Mustacchi 
220*4d9fdb46SRobert Mustacchi /*  _dwarf_get_fission_addition_die returns DW_DLV_OK etc.
22149d3bc91SRichard Lowe */
222*4d9fdb46SRobert Mustacchi int
_dwarf_get_fission_addition_die(Dwarf_Die die,int dw_sect_index,Dwarf_Unsigned * offset,Dwarf_Unsigned * size,Dwarf_Error * error)223*4d9fdb46SRobert Mustacchi _dwarf_get_fission_addition_die(Dwarf_Die die, int dw_sect_index,
224*4d9fdb46SRobert Mustacchi    Dwarf_Unsigned *offset,
225*4d9fdb46SRobert Mustacchi    Dwarf_Unsigned *size,
226*4d9fdb46SRobert Mustacchi    Dwarf_Error *error)
22749d3bc91SRichard Lowe {
228*4d9fdb46SRobert Mustacchi     /* We do not yet know the DIE hash, so we cannot use it
229*4d9fdb46SRobert Mustacchi         to identify the offset. */
230*4d9fdb46SRobert Mustacchi     Dwarf_CU_Context context = 0;
231*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned dwpadd = 0;
232*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned dwpsize = 0;
23349d3bc91SRichard Lowe 
234*4d9fdb46SRobert Mustacchi     CHECK_DIE(die, DW_DLV_ERROR);
235*4d9fdb46SRobert Mustacchi     context = die->di_cu_context;
236*4d9fdb46SRobert Mustacchi     dwpadd =  _dwarf_get_dwp_extra_offset(
237*4d9fdb46SRobert Mustacchi         &context->cc_dwp_offsets,
238*4d9fdb46SRobert Mustacchi         dw_sect_index,&dwpsize);
239*4d9fdb46SRobert Mustacchi     *offset = dwpadd;
240*4d9fdb46SRobert Mustacchi     *size = dwpsize;
241*4d9fdb46SRobert Mustacchi     return DW_DLV_OK;
242*4d9fdb46SRobert Mustacchi }
24349d3bc91SRichard Lowe 
244*4d9fdb46SRobert Mustacchi /*  Not sure if this is the only way to be sure early on in
245*4d9fdb46SRobert Mustacchi     reading a compile unit.  */
246*4d9fdb46SRobert Mustacchi static int
section_name_ends_with_dwo(const char * name)247*4d9fdb46SRobert Mustacchi section_name_ends_with_dwo(const char *name)
248*4d9fdb46SRobert Mustacchi {
249*4d9fdb46SRobert Mustacchi     int lenstr = 0;
250*4d9fdb46SRobert Mustacchi     int dotpos = 0;
251*4d9fdb46SRobert Mustacchi     if (!name) {
252*4d9fdb46SRobert Mustacchi         return FALSE;
253*4d9fdb46SRobert Mustacchi     }
254*4d9fdb46SRobert Mustacchi     lenstr = strlen(name);
255*4d9fdb46SRobert Mustacchi     if (lenstr < 5) {
256*4d9fdb46SRobert Mustacchi         return FALSE;
257*4d9fdb46SRobert Mustacchi     }
258*4d9fdb46SRobert Mustacchi     dotpos = lenstr - 4;
259*4d9fdb46SRobert Mustacchi     if(strcmp(name+dotpos,".dwo")) {
260*4d9fdb46SRobert Mustacchi         return FALSE;
261*4d9fdb46SRobert Mustacchi     }
262*4d9fdb46SRobert Mustacchi     return TRUE;
263*4d9fdb46SRobert Mustacchi }
26449d3bc91SRichard Lowe 
265*4d9fdb46SRobert Mustacchi void
_dwarf_create_address_size_dwarf_error(Dwarf_Debug dbg,Dwarf_Error * error,Dwarf_Unsigned addrsize,int errcode,const char * errname)266*4d9fdb46SRobert Mustacchi _dwarf_create_address_size_dwarf_error(Dwarf_Debug dbg,
267*4d9fdb46SRobert Mustacchi     Dwarf_Error *error,
268*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned addrsize,
269*4d9fdb46SRobert Mustacchi     int errcode,const char *errname)
270*4d9fdb46SRobert Mustacchi {
271*4d9fdb46SRobert Mustacchi     dwarfstring m;
272*4d9fdb46SRobert Mustacchi     const char *bites = "bytes";
273*4d9fdb46SRobert Mustacchi     if (addrsize == 1) {
274*4d9fdb46SRobert Mustacchi         bites = "byte";
275*4d9fdb46SRobert Mustacchi     }
27649d3bc91SRichard Lowe 
277*4d9fdb46SRobert Mustacchi     dwarfstring_constructor(&m);
278*4d9fdb46SRobert Mustacchi     dwarfstring_append(&m,(char *)errname);
279*4d9fdb46SRobert Mustacchi     dwarfstring_append_printf_u(&m,
280*4d9fdb46SRobert Mustacchi         ": Address size of %u ",
281*4d9fdb46SRobert Mustacchi         addrsize);
282*4d9fdb46SRobert Mustacchi     dwarfstring_append_printf_s(&m,
283*4d9fdb46SRobert Mustacchi         "%s is not supported. Corrupt DWARF.",
284*4d9fdb46SRobert Mustacchi         (char *)bites);
285*4d9fdb46SRobert Mustacchi     _dwarf_error_string(dbg,error,errcode,
286*4d9fdb46SRobert Mustacchi         dwarfstring_string(&m));
287*4d9fdb46SRobert Mustacchi     dwarfstring_destructor(&m);
28849d3bc91SRichard Lowe }
28949d3bc91SRichard Lowe 
290*4d9fdb46SRobert Mustacchi /*  New January 2017 */
291*4d9fdb46SRobert Mustacchi static int
_dwarf_read_cu_version_and_abbrev_offset(Dwarf_Debug dbg,Dwarf_Small * data,Dwarf_Bool is_info,UNUSEDARG unsigned group_number,unsigned offset_size,Dwarf_CU_Context cu_context,Dwarf_Small * end_data,Dwarf_Unsigned * bytes_read_out,Dwarf_Error * error)292*4d9fdb46SRobert Mustacchi _dwarf_read_cu_version_and_abbrev_offset(Dwarf_Debug dbg,
293*4d9fdb46SRobert Mustacchi     Dwarf_Small *data,
294*4d9fdb46SRobert Mustacchi     Dwarf_Bool is_info,
295*4d9fdb46SRobert Mustacchi     UNUSEDARG unsigned group_number,
296*4d9fdb46SRobert Mustacchi     unsigned offset_size, /* 4 or 8 */
297*4d9fdb46SRobert Mustacchi     Dwarf_CU_Context cu_context,
298*4d9fdb46SRobert Mustacchi     /* end_data used for sanity checking */
299*4d9fdb46SRobert Mustacchi     Dwarf_Small *    end_data,
300*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned * bytes_read_out,
301*4d9fdb46SRobert Mustacchi     Dwarf_Error *    error)
302*4d9fdb46SRobert Mustacchi {
303*4d9fdb46SRobert Mustacchi     Dwarf_Small *  data_start = data;
304*4d9fdb46SRobert Mustacchi     Dwarf_Small *  dataptr = data;
305*4d9fdb46SRobert Mustacchi     int            unit_type = 0;
306*4d9fdb46SRobert Mustacchi     Dwarf_Ubyte    addrsize =  0;
307*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned abbrev_offset = 0;
308*4d9fdb46SRobert Mustacchi     Dwarf_Half version = 0;
309*4d9fdb46SRobert Mustacchi 
310*4d9fdb46SRobert Mustacchi     READ_UNALIGNED_CK(dbg, version, Dwarf_Half,
311*4d9fdb46SRobert Mustacchi         dataptr,DWARF_HALF_SIZE,error,end_data);
312*4d9fdb46SRobert Mustacchi     dataptr += DWARF_HALF_SIZE;
313*4d9fdb46SRobert Mustacchi     if (version == DW_CU_VERSION5) {
314*4d9fdb46SRobert Mustacchi         Dwarf_Ubyte unit_typeb = 0;
315*4d9fdb46SRobert Mustacchi 
316*4d9fdb46SRobert Mustacchi         READ_UNALIGNED_CK(dbg, unit_typeb, Dwarf_Ubyte,
317*4d9fdb46SRobert Mustacchi             dataptr, sizeof(unit_typeb),error,end_data);
318*4d9fdb46SRobert Mustacchi         dataptr += sizeof(unit_typeb);
319*4d9fdb46SRobert Mustacchi 
320*4d9fdb46SRobert Mustacchi         unit_type = unit_typeb;
321*4d9fdb46SRobert Mustacchi         /* We do not need is_info flag in DWARF5 */
322*4d9fdb46SRobert Mustacchi         if (is_unknown_UT_value(unit_type)) {
323*4d9fdb46SRobert Mustacchi             /*  DWARF5 object file is corrupt. Invalid value */
324*4d9fdb46SRobert Mustacchi             dwarfstring m;
325*4d9fdb46SRobert Mustacchi             dwarfstring_constructor(&m);
326*4d9fdb46SRobert Mustacchi             dwarfstring_append_printf_u(&m,
327*4d9fdb46SRobert Mustacchi                 "DW_DLE_CU_UT_TYPE_ERROR: we do not know "
328*4d9fdb46SRobert Mustacchi                 " the CU header unit_type 0x%x",unit_type);
329*4d9fdb46SRobert Mustacchi             dwarfstring_append_printf_u(&m," (%u) so cannot"
330*4d9fdb46SRobert Mustacchi                 "process this compilation_unit. A valid type ",
331*4d9fdb46SRobert Mustacchi                 unit_type);
332*4d9fdb46SRobert Mustacchi             dwarfstring_append(&m,"would be DW_UT_compile"
333*4d9fdb46SRobert Mustacchi                 ", for example");
334*4d9fdb46SRobert Mustacchi             _dwarf_error_string(dbg, error,
335*4d9fdb46SRobert Mustacchi                 DW_DLE_CU_UT_TYPE_ERROR,
336*4d9fdb46SRobert Mustacchi                 dwarfstring_string(&m));
337*4d9fdb46SRobert Mustacchi             dwarfstring_destructor(&m);
338*4d9fdb46SRobert Mustacchi             return DW_DLV_ERROR;
339*4d9fdb46SRobert Mustacchi         }
340*4d9fdb46SRobert Mustacchi         READ_UNALIGNED_CK(dbg, addrsize, unsigned char,
341*4d9fdb46SRobert Mustacchi             dataptr, sizeof(addrsize),error,end_data);
342*4d9fdb46SRobert Mustacchi         dataptr += sizeof(char);
343*4d9fdb46SRobert Mustacchi 
344*4d9fdb46SRobert Mustacchi         READ_UNALIGNED_CK(dbg, abbrev_offset, Dwarf_Unsigned,
345*4d9fdb46SRobert Mustacchi             dataptr, offset_size,error,end_data);
346*4d9fdb46SRobert Mustacchi         dataptr += offset_size;
347*4d9fdb46SRobert Mustacchi 
348*4d9fdb46SRobert Mustacchi     } else if (version == DW_CU_VERSION2 ||
349*4d9fdb46SRobert Mustacchi         version == DW_CU_VERSION3 ||
350*4d9fdb46SRobert Mustacchi         version == DW_CU_VERSION4) {
351*4d9fdb46SRobert Mustacchi         /*  DWARF2,3,4  */
352*4d9fdb46SRobert Mustacchi         READ_UNALIGNED_CK(dbg, abbrev_offset, Dwarf_Unsigned,
353*4d9fdb46SRobert Mustacchi             dataptr, offset_size,error,end_data);
354*4d9fdb46SRobert Mustacchi         dataptr += offset_size;
355*4d9fdb46SRobert Mustacchi 
356*4d9fdb46SRobert Mustacchi         READ_UNALIGNED_CK(dbg, addrsize, Dwarf_Ubyte,
357*4d9fdb46SRobert Mustacchi             dataptr, sizeof(addrsize),error,end_data);
358*4d9fdb46SRobert Mustacchi         dataptr += sizeof(addrsize);
359*4d9fdb46SRobert Mustacchi 
360*4d9fdb46SRobert Mustacchi         /*  This is an initial approximation of unit_type.
361*4d9fdb46SRobert Mustacchi             For DW4 we will refine this after we
362*4d9fdb46SRobert Mustacchi             have built the CU header (by reading
363*4d9fdb46SRobert Mustacchi             CU_die)
364*4d9fdb46SRobert Mustacchi         */
365*4d9fdb46SRobert Mustacchi         unit_type = is_info?DW_UT_compile:DW_UT_type;
366*4d9fdb46SRobert Mustacchi     } else {
367*4d9fdb46SRobert Mustacchi         _dwarf_error(dbg, error, DW_DLE_VERSION_STAMP_ERROR);
368*4d9fdb46SRobert Mustacchi         return DW_DLV_ERROR;
369*4d9fdb46SRobert Mustacchi     }
370*4d9fdb46SRobert Mustacchi     cu_context->cc_version_stamp = version;
371*4d9fdb46SRobert Mustacchi     cu_context->cc_unit_type = unit_type;
372*4d9fdb46SRobert Mustacchi     cu_context->cc_address_size = addrsize;
373*4d9fdb46SRobert Mustacchi     cu_context->cc_abbrev_offset = abbrev_offset;
374*4d9fdb46SRobert Mustacchi     if (!addrsize) {
375*4d9fdb46SRobert Mustacchi         _dwarf_error(dbg,error,DW_DLE_ADDRESS_SIZE_ZERO);
376*4d9fdb46SRobert Mustacchi         return DW_DLV_ERROR;
377*4d9fdb46SRobert Mustacchi     }
378*4d9fdb46SRobert Mustacchi     if (addrsize < MINIMUM_ADDRESS_SIZE ||
379*4d9fdb46SRobert Mustacchi         addrsize > MAXIMUM_ADDRESS_SIZE ) {
380*4d9fdb46SRobert Mustacchi         _dwarf_create_address_size_dwarf_error(dbg,error,addrsize,
381*4d9fdb46SRobert Mustacchi             DW_DLE_ADDRESS_SIZE_ERROR,
382*4d9fdb46SRobert Mustacchi             "DW_DLE_ADDRESS_SIZE_ERROR::");
383*4d9fdb46SRobert Mustacchi         return DW_DLV_ERROR;
384*4d9fdb46SRobert Mustacchi     }
385*4d9fdb46SRobert Mustacchi     if (addrsize  > sizeof(Dwarf_Addr)) {
386*4d9fdb46SRobert Mustacchi         _dwarf_create_address_size_dwarf_error(dbg,error,addrsize,
387*4d9fdb46SRobert Mustacchi             DW_DLE_ADDRESS_SIZE_ERROR,
388*4d9fdb46SRobert Mustacchi             "DW_DLE_ADDRESS_SIZE_ERROR: not representable"
389*4d9fdb46SRobert Mustacchi             " in Dwarf_Addr field.");
390*4d9fdb46SRobert Mustacchi         return DW_DLV_ERROR;
391*4d9fdb46SRobert Mustacchi     }
39249d3bc91SRichard Lowe 
393*4d9fdb46SRobert Mustacchi 
394*4d9fdb46SRobert Mustacchi 
395*4d9fdb46SRobert Mustacchi     /* We are ignoring this. Can get it from DWARF5. */
396*4d9fdb46SRobert Mustacchi     cu_context->cc_segment_selector_size = 0;
397*4d9fdb46SRobert Mustacchi     *bytes_read_out = (dataptr - data_start);
398*4d9fdb46SRobert Mustacchi     return DW_DLV_OK;
399*4d9fdb46SRobert Mustacchi }
400*4d9fdb46SRobert Mustacchi 
401*4d9fdb46SRobert Mustacchi /*  .debug_info[.dwo]   .debug_types[.dwo]
402*4d9fdb46SRobert Mustacchi     the latter only DWARF4. */
403*4d9fdb46SRobert Mustacchi static int
read_info_area_length_and_check(Dwarf_Debug dbg,Dwarf_CU_Context cu_context,Dwarf_Unsigned offset,Dwarf_Byte_Ptr * cu_ptr_io,Dwarf_Unsigned section_size,Dwarf_Byte_Ptr section_end_ptr,Dwarf_Unsigned * max_cu_global_offset_out,Dwarf_Error * error)404*4d9fdb46SRobert Mustacchi read_info_area_length_and_check(Dwarf_Debug dbg,
405*4d9fdb46SRobert Mustacchi     Dwarf_CU_Context cu_context,
406*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned offset,
407*4d9fdb46SRobert Mustacchi     Dwarf_Byte_Ptr *cu_ptr_io,
408*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned section_size,
409*4d9fdb46SRobert Mustacchi     Dwarf_Byte_Ptr section_end_ptr,
410*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned *max_cu_global_offset_out,
411*4d9fdb46SRobert Mustacchi     Dwarf_Error *error)
412*4d9fdb46SRobert Mustacchi {
413*4d9fdb46SRobert Mustacchi     Dwarf_Byte_Ptr  cu_ptr = 0;
414*4d9fdb46SRobert Mustacchi     int local_length_size = 0;
415*4d9fdb46SRobert Mustacchi     int local_extension_size = 0;
416*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned max_cu_global_offset = 0;
417*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned length = 0;
418*4d9fdb46SRobert Mustacchi 
419*4d9fdb46SRobert Mustacchi     cu_ptr = *cu_ptr_io;
420*4d9fdb46SRobert Mustacchi     /* READ_AREA_LENGTH updates cu_ptr for consumed bytes */
421*4d9fdb46SRobert Mustacchi     READ_AREA_LENGTH_CK(dbg, length, Dwarf_Unsigned,
422*4d9fdb46SRobert Mustacchi         cu_ptr, local_length_size, local_extension_size,
423*4d9fdb46SRobert Mustacchi         error,section_size,section_end_ptr);
424*4d9fdb46SRobert Mustacchi     if (!length) {
425*4d9fdb46SRobert Mustacchi         return DW_DLV_NO_ENTRY;
426*4d9fdb46SRobert Mustacchi     }
427*4d9fdb46SRobert Mustacchi 
428*4d9fdb46SRobert Mustacchi     cu_context->cc_length_size = local_length_size;
429*4d9fdb46SRobert Mustacchi     cu_context->cc_extension_size = local_extension_size;
430*4d9fdb46SRobert Mustacchi     cu_context->cc_length = length;
431*4d9fdb46SRobert Mustacchi 
432*4d9fdb46SRobert Mustacchi     /*  This is a bare minimum, not the real max offset.
433*4d9fdb46SRobert Mustacchi         A preliminary sanity check. */
434*4d9fdb46SRobert Mustacchi     max_cu_global_offset =  offset + length +
435*4d9fdb46SRobert Mustacchi         local_extension_size + local_length_size;
436*4d9fdb46SRobert Mustacchi     if(length > section_size) {
437*4d9fdb46SRobert Mustacchi         _dwarf_error(dbg, error, DW_DLE_CU_LENGTH_ERROR);
438*4d9fdb46SRobert Mustacchi         return DW_DLV_ERROR;
439*4d9fdb46SRobert Mustacchi     }
440*4d9fdb46SRobert Mustacchi     if(max_cu_global_offset > section_size) {
441*4d9fdb46SRobert Mustacchi         _dwarf_error(dbg, error, DW_DLE_CU_LENGTH_ERROR);
442*4d9fdb46SRobert Mustacchi         return DW_DLV_ERROR;
443*4d9fdb46SRobert Mustacchi     }
444*4d9fdb46SRobert Mustacchi     *cu_ptr_io = cu_ptr;
445*4d9fdb46SRobert Mustacchi     *max_cu_global_offset_out = max_cu_global_offset;
446*4d9fdb46SRobert Mustacchi     return DW_DLV_OK;
447*4d9fdb46SRobert Mustacchi }
448*4d9fdb46SRobert Mustacchi 
449*4d9fdb46SRobert Mustacchi 
450*4d9fdb46SRobert Mustacchi /*  In DWARF4  GNU dwp there is a problem.
451*4d9fdb46SRobert Mustacchi     We cannot read the CU die  and it's
452*4d9fdb46SRobert Mustacchi     DW_AT_GNU_dwo_id until we know the
453*4d9fdb46SRobert Mustacchi     section offsets from the index files.
454*4d9fdb46SRobert Mustacchi     Hence we do not know how to search the
455*4d9fdb46SRobert Mustacchi     index files by key. So search by offset.
456*4d9fdb46SRobert Mustacchi 
457*4d9fdb46SRobert Mustacchi     There is no such problem in DWARF5.
458*4d9fdb46SRobert Mustacchi 
459*4d9fdb46SRobert Mustacchi     We have not yet corrected the unit_type so, for DWARF4,
460*4d9fdb46SRobert Mustacchi     we check for simpler unit types.
461*4d9fdb46SRobert Mustacchi */
462*4d9fdb46SRobert Mustacchi 
463*4d9fdb46SRobert Mustacchi static int
fill_in_dwp_offsets_if_present(Dwarf_Debug dbg,Dwarf_CU_Context cu_context,Dwarf_Sig8 * signaturedata,Dwarf_Off offset,Dwarf_Error * error)464*4d9fdb46SRobert Mustacchi fill_in_dwp_offsets_if_present(Dwarf_Debug dbg,
465*4d9fdb46SRobert Mustacchi     Dwarf_CU_Context cu_context,
466*4d9fdb46SRobert Mustacchi     Dwarf_Sig8 * signaturedata,
467*4d9fdb46SRobert Mustacchi     Dwarf_Off    offset,
468*4d9fdb46SRobert Mustacchi     Dwarf_Error *error)
469*4d9fdb46SRobert Mustacchi {
470*4d9fdb46SRobert Mustacchi     Dwarf_Half unit_type = cu_context->cc_unit_type;
471*4d9fdb46SRobert Mustacchi     const char * typename = 0;
472*4d9fdb46SRobert Mustacchi     Dwarf_Half ver = cu_context->cc_version_stamp;
473*4d9fdb46SRobert Mustacchi 
474*4d9fdb46SRobert Mustacchi     if (unit_type == DW_UT_split_type ||
475*4d9fdb46SRobert Mustacchi         (ver == DW_CU_VERSION4 && unit_type == DW_UT_type)){
476*4d9fdb46SRobert Mustacchi         typename = "tu";
477*4d9fdb46SRobert Mustacchi         if (!_dwarf_file_has_debug_fission_tu_index(dbg) ){
478*4d9fdb46SRobert Mustacchi             /* nothing to do. */
479*4d9fdb46SRobert Mustacchi             return DW_DLV_OK;
480*4d9fdb46SRobert Mustacchi         }
481*4d9fdb46SRobert Mustacchi     } else if (unit_type == DW_UT_split_compile ||
482*4d9fdb46SRobert Mustacchi         (ver == DW_CU_VERSION4 &&
483*4d9fdb46SRobert Mustacchi         unit_type == DW_UT_compile)){
484*4d9fdb46SRobert Mustacchi         typename = "cu";
485*4d9fdb46SRobert Mustacchi         if (!_dwarf_file_has_debug_fission_cu_index(dbg) ){
486*4d9fdb46SRobert Mustacchi             /* nothing to do. */
487*4d9fdb46SRobert Mustacchi             return DW_DLV_OK;
488*4d9fdb46SRobert Mustacchi         }
489*4d9fdb46SRobert Mustacchi     } else {
490*4d9fdb46SRobert Mustacchi         /* nothing to do. */
491*4d9fdb46SRobert Mustacchi         return DW_DLV_OK;
492*4d9fdb46SRobert Mustacchi     }
493*4d9fdb46SRobert Mustacchi 
494*4d9fdb46SRobert Mustacchi     if (cu_context->cc_signature_present) {
495*4d9fdb46SRobert Mustacchi         int resdf = 0;
496*4d9fdb46SRobert Mustacchi 
497*4d9fdb46SRobert Mustacchi         resdf = dwarf_get_debugfission_for_key(dbg,
498*4d9fdb46SRobert Mustacchi             signaturedata,
499*4d9fdb46SRobert Mustacchi             typename,
500*4d9fdb46SRobert Mustacchi             &cu_context->cc_dwp_offsets,
501*4d9fdb46SRobert Mustacchi             error);
502*4d9fdb46SRobert Mustacchi         if (resdf == DW_DLV_ERROR) {
503*4d9fdb46SRobert Mustacchi             return resdf;
504*4d9fdb46SRobert Mustacchi         } else if (resdf == DW_DLV_NO_ENTRY) {
505*4d9fdb46SRobert Mustacchi             _dwarf_error_string(dbg, error,
506*4d9fdb46SRobert Mustacchi                 DW_DLE_MISSING_REQUIRED_CU_OFFSET_HASH,
507*4d9fdb46SRobert Mustacchi                 "DW_DLE_MISSING_REQUIRED_CU_OFFSET_HASH: "
508*4d9fdb46SRobert Mustacchi                 " dwarf_get_debugfission_for_key returned"
509*4d9fdb46SRobert Mustacchi                 " DW_DLV_NO_ENTRY, something is wrong");
510*4d9fdb46SRobert Mustacchi             return DW_DLV_ERROR;
511*4d9fdb46SRobert Mustacchi         }
512*4d9fdb46SRobert Mustacchi     } else {
513*4d9fdb46SRobert Mustacchi         int resdf = 0;
514*4d9fdb46SRobert Mustacchi 
515*4d9fdb46SRobert Mustacchi         resdf = _dwarf_get_debugfission_for_offset(dbg,
516*4d9fdb46SRobert Mustacchi             offset,
517*4d9fdb46SRobert Mustacchi             typename,
518*4d9fdb46SRobert Mustacchi             &cu_context->cc_dwp_offsets,
519*4d9fdb46SRobert Mustacchi             error);
520*4d9fdb46SRobert Mustacchi         if (resdf == DW_DLV_ERROR) {
521*4d9fdb46SRobert Mustacchi             return resdf;
522*4d9fdb46SRobert Mustacchi         } else if (resdf == DW_DLV_NO_ENTRY) {
523*4d9fdb46SRobert Mustacchi             _dwarf_error_string(dbg, error,
524*4d9fdb46SRobert Mustacchi                 DW_DLE_MISSING_REQUIRED_CU_OFFSET_HASH,
525*4d9fdb46SRobert Mustacchi                 "DW_DLE_MISSING_REQUIRED_CU_OFFSET_HASH: "
526*4d9fdb46SRobert Mustacchi                 " dwarf_get_debugfission_for_offset returned"
527*4d9fdb46SRobert Mustacchi                 " DW_DLV_NO_ENTRY, something is wrong");
528*4d9fdb46SRobert Mustacchi             return DW_DLV_ERROR;
529*4d9fdb46SRobert Mustacchi         }
530*4d9fdb46SRobert Mustacchi         cu_context->cc_signature =
531*4d9fdb46SRobert Mustacchi             cu_context->cc_dwp_offsets.pcu_hash;
532*4d9fdb46SRobert Mustacchi         cu_context->cc_signature_present = TRUE;
533*4d9fdb46SRobert Mustacchi     }
534*4d9fdb46SRobert Mustacchi     return DW_DLV_OK;
535*4d9fdb46SRobert Mustacchi }
536*4d9fdb46SRobert Mustacchi 
537*4d9fdb46SRobert Mustacchi static Dwarf_Bool
_dwarf_may_have_base_fields(Dwarf_CU_Context cu_context)538*4d9fdb46SRobert Mustacchi _dwarf_may_have_base_fields(Dwarf_CU_Context cu_context)
539*4d9fdb46SRobert Mustacchi {
540*4d9fdb46SRobert Mustacchi     if (cu_context->cc_version_stamp < DW_CU_VERSION4) {
541*4d9fdb46SRobert Mustacchi         return FALSE;
542*4d9fdb46SRobert Mustacchi     }
543*4d9fdb46SRobert Mustacchi     return TRUE;
544*4d9fdb46SRobert Mustacchi }
545*4d9fdb46SRobert Mustacchi 
546*4d9fdb46SRobert Mustacchi static int
finish_cu_context_via_cudie_inner(Dwarf_Debug dbg,Dwarf_CU_Context cu_context,Dwarf_Error * error)547*4d9fdb46SRobert Mustacchi finish_cu_context_via_cudie_inner(
548*4d9fdb46SRobert Mustacchi     Dwarf_Debug dbg,
549*4d9fdb46SRobert Mustacchi     Dwarf_CU_Context cu_context,
550*4d9fdb46SRobert Mustacchi     Dwarf_Error *error)
551*4d9fdb46SRobert Mustacchi {
552*4d9fdb46SRobert Mustacchi     if (_dwarf_may_have_base_fields(cu_context)) {
553*4d9fdb46SRobert Mustacchi         /*  DW4: Look for DW_AT_dwo_id and
554*4d9fdb46SRobert Mustacchi             if there is one pick up the hash
555*4d9fdb46SRobert Mustacchi             DW5: hash in skeleton CU die
556*4d9fdb46SRobert Mustacchi             Also pick up cc_str_offset_base and
557*4d9fdb46SRobert Mustacchi             any other base values. */
558*4d9fdb46SRobert Mustacchi 
559*4d9fdb46SRobert Mustacchi         Dwarf_Die cudie = 0;
560*4d9fdb46SRobert Mustacchi         int resdwo = 0;
561*4d9fdb46SRobert Mustacchi 
562*4d9fdb46SRobert Mustacchi         /*  Must call the internal siblingof so
563*4d9fdb46SRobert Mustacchi             we do not depend on the dbg...de_cu_context
564*4d9fdb46SRobert Mustacchi             used by and for dwarf_cu_header_* calls. */
565*4d9fdb46SRobert Mustacchi         resdwo = _dwarf_siblingof_internal(dbg,NULL,
566*4d9fdb46SRobert Mustacchi             cu_context,
567*4d9fdb46SRobert Mustacchi             cu_context->cc_is_info,
568*4d9fdb46SRobert Mustacchi             &cudie, error);
569*4d9fdb46SRobert Mustacchi         if (resdwo == DW_DLV_OK) {
570*4d9fdb46SRobert Mustacchi             Dwarf_Half cutag = 0;
571*4d9fdb46SRobert Mustacchi             int resdwob = 0;
572*4d9fdb46SRobert Mustacchi             resdwob = find_cu_die_base_fields(dbg,
573*4d9fdb46SRobert Mustacchi                 cu_context,
574*4d9fdb46SRobert Mustacchi                 cudie,
575*4d9fdb46SRobert Mustacchi                 error);
576*4d9fdb46SRobert Mustacchi             if (resdwob == DW_DLV_NO_ENTRY) {
577*4d9fdb46SRobert Mustacchi                 /* The CU die has no children */
578*4d9fdb46SRobert Mustacchi                 dwarf_dealloc(dbg,cudie,DW_DLA_DIE);
579*4d9fdb46SRobert Mustacchi                 cudie = 0;
580*4d9fdb46SRobert Mustacchi                 cu_context->cc_cu_die_has_children = FALSE;
581*4d9fdb46SRobert Mustacchi                 return DW_DLV_OK;
582*4d9fdb46SRobert Mustacchi             } else if (resdwob == DW_DLV_ERROR) {
583*4d9fdb46SRobert Mustacchi                 /*  Not applicable or an error */
584*4d9fdb46SRobert Mustacchi                 dwarf_dealloc(dbg,cudie,DW_DLA_DIE);
585*4d9fdb46SRobert Mustacchi                 cudie = 0;
586*4d9fdb46SRobert Mustacchi                 return resdwob;
587*4d9fdb46SRobert Mustacchi             }
588*4d9fdb46SRobert Mustacchi             resdwob = dwarf_tag(cudie,&cutag,error);
589*4d9fdb46SRobert Mustacchi             if (resdwob == DW_DLV_OK) {
590*4d9fdb46SRobert Mustacchi                 cu_context->cc_cu_die_tag = cutag;
591*4d9fdb46SRobert Mustacchi             }
592*4d9fdb46SRobert Mustacchi             dwarf_dealloc(dbg,cudie,DW_DLA_DIE);
593*4d9fdb46SRobert Mustacchi             return resdwob;
594*4d9fdb46SRobert Mustacchi         } else  if (resdwo == DW_DLV_NO_ENTRY) {
595*4d9fdb46SRobert Mustacchi             /* no cudie. Empty CU. */
596*4d9fdb46SRobert Mustacchi             return DW_DLV_OK;
597*4d9fdb46SRobert Mustacchi         } else {
598*4d9fdb46SRobert Mustacchi             /* no cudie. Error.*/
599*4d9fdb46SRobert Mustacchi             return resdwo;
600*4d9fdb46SRobert Mustacchi         }
601*4d9fdb46SRobert Mustacchi     }
602*4d9fdb46SRobert Mustacchi     return DW_DLV_OK;
603*4d9fdb46SRobert Mustacchi }
604*4d9fdb46SRobert Mustacchi 
605*4d9fdb46SRobert Mustacchi static void
local_dealloc_cu_context(Dwarf_Debug dbg,Dwarf_CU_Context context)606*4d9fdb46SRobert Mustacchi local_dealloc_cu_context(Dwarf_Debug dbg,
607*4d9fdb46SRobert Mustacchi     Dwarf_CU_Context context)
608*4d9fdb46SRobert Mustacchi {
609*4d9fdb46SRobert Mustacchi     Dwarf_Hash_Table hash_table = 0;
610*4d9fdb46SRobert Mustacchi 
611*4d9fdb46SRobert Mustacchi     if (!context) {
612*4d9fdb46SRobert Mustacchi         return;
613*4d9fdb46SRobert Mustacchi     }
614*4d9fdb46SRobert Mustacchi     hash_table = context->cc_abbrev_hash_table;
615*4d9fdb46SRobert Mustacchi     if (hash_table) {
616*4d9fdb46SRobert Mustacchi         _dwarf_free_abbrev_hash_table_contents(dbg,hash_table);
617*4d9fdb46SRobert Mustacchi         hash_table->tb_entries = 0;
618*4d9fdb46SRobert Mustacchi         dwarf_dealloc(dbg,hash_table, DW_DLA_HASH_TABLE);
619*4d9fdb46SRobert Mustacchi         context->cc_abbrev_hash_table = 0;
620*4d9fdb46SRobert Mustacchi     }
621*4d9fdb46SRobert Mustacchi     dwarf_dealloc(dbg, context, DW_DLA_CU_CONTEXT);
622*4d9fdb46SRobert Mustacchi }
623*4d9fdb46SRobert Mustacchi 
624*4d9fdb46SRobert Mustacchi static void
report_local_unit_type_error(Dwarf_Debug dbg,int unit_type,const char * msg,Dwarf_Error * err)625*4d9fdb46SRobert Mustacchi report_local_unit_type_error(Dwarf_Debug dbg,
626*4d9fdb46SRobert Mustacchi     int unit_type,
627*4d9fdb46SRobert Mustacchi     const char *msg,
628*4d9fdb46SRobert Mustacchi     Dwarf_Error *err)
629*4d9fdb46SRobert Mustacchi {
630*4d9fdb46SRobert Mustacchi     dwarfstring m;
631*4d9fdb46SRobert Mustacchi 
632*4d9fdb46SRobert Mustacchi     dwarfstring_constructor(&m);
633*4d9fdb46SRobert Mustacchi     dwarfstring_append_printf_s(&m,
634*4d9fdb46SRobert Mustacchi         "DW_DLE_CU_UT_TYPE_VALUE: %s ",(char *)msg);
635*4d9fdb46SRobert Mustacchi     dwarfstring_append_printf_u(&m,
636*4d9fdb46SRobert Mustacchi         "the compilation unit unit_type is 0x%x,"
637*4d9fdb46SRobert Mustacchi         " which is unknown to libdwarf. Corrupt DWARF.",
638*4d9fdb46SRobert Mustacchi         unit_type);
639*4d9fdb46SRobert Mustacchi     _dwarf_error_string(dbg,err,DW_DLE_CU_UT_TYPE_VALUE,
640*4d9fdb46SRobert Mustacchi         dwarfstring_string(&m));
641*4d9fdb46SRobert Mustacchi     dwarfstring_destructor(&m);
642*4d9fdb46SRobert Mustacchi }
643*4d9fdb46SRobert Mustacchi 
644*4d9fdb46SRobert Mustacchi /*  This function is used to create a CU Context for
645*4d9fdb46SRobert Mustacchi     a compilation-unit that begins at offset in
64649d3bc91SRichard Lowe     .debug_info.  The CU Context is attached to the
64749d3bc91SRichard Lowe     list of CU Contexts for this dbg.  It is assumed
64849d3bc91SRichard Lowe     that the CU at offset has not been read before,
64949d3bc91SRichard Lowe     and so do not call this routine before making
65049d3bc91SRichard Lowe     sure of this with _dwarf_find_CU_Context().
65149d3bc91SRichard Lowe     Returns NULL on error.  As always, being an
65249d3bc91SRichard Lowe     internal routine, assumes a good dbg.
65349d3bc91SRichard Lowe 
654*4d9fdb46SRobert Mustacchi     The offset argument is global offset, the offset
655*4d9fdb46SRobert Mustacchi     in the section, irrespective of CUs.
656*4d9fdb46SRobert Mustacchi     The offset has the DWP Package File offset built in
657*4d9fdb46SRobert Mustacchi     as it comes from the actual section.
658*4d9fdb46SRobert Mustacchi 
659*4d9fdb46SRobert Mustacchi     max_cu_local_offset is a local offset in this CU.
660*4d9fdb46SRobert Mustacchi     So zero of this field is immediately following the length
661*4d9fdb46SRobert Mustacchi     field of the CU header. so max_cu_local_offset is
662*4d9fdb46SRobert Mustacchi     identical to the CU length field.
663*4d9fdb46SRobert Mustacchi     max_cu_global_offset is the offset one-past the end
664*4d9fdb46SRobert Mustacchi     of this entire CU.  */
665*4d9fdb46SRobert Mustacchi static int
_dwarf_make_CU_Context(Dwarf_Debug dbg,Dwarf_Off offset,Dwarf_Bool is_info,Dwarf_CU_Context * context_out,Dwarf_Error * error)66649d3bc91SRichard Lowe _dwarf_make_CU_Context(Dwarf_Debug dbg,
667*4d9fdb46SRobert Mustacchi     Dwarf_Off offset,Dwarf_Bool is_info,
668*4d9fdb46SRobert Mustacchi     Dwarf_CU_Context * context_out,Dwarf_Error * error)
66949d3bc91SRichard Lowe {
67007dc1947SRichard Lowe     Dwarf_CU_Context cu_context = 0;
671*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned   length = 0;
672*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned   typeoffset = 0;
673*4d9fdb46SRobert Mustacchi     Dwarf_Sig8       signaturedata;
674*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned   types_extra_len = 0;
675*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned   max_cu_local_offset =  0;
676*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned   max_cu_global_offset =  0;
677*4d9fdb46SRobert Mustacchi     Dwarf_Byte_Ptr   cu_ptr = 0;
678*4d9fdb46SRobert Mustacchi     Dwarf_Byte_Ptr   section_end_ptr = 0;
679*4d9fdb46SRobert Mustacchi     int              local_length_size = 0;
680*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned   bytes_read = 0;
681*4d9fdb46SRobert Mustacchi     const char *     secname = is_info?dbg->de_debug_info.dss_name:
682*4d9fdb46SRobert Mustacchi         dbg->de_debug_types.dss_name;
683*4d9fdb46SRobert Mustacchi     Dwarf_Debug_InfoTypes dis = is_info? &dbg->de_info_reading:
684*4d9fdb46SRobert Mustacchi         &dbg->de_types_reading;
685*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned   section_size = is_info? dbg->de_debug_info.dss_size:
686*4d9fdb46SRobert Mustacchi         dbg->de_debug_types.dss_size;
687*4d9fdb46SRobert Mustacchi     int              unit_type = 0;
688*4d9fdb46SRobert Mustacchi     int              version = 0;
689*4d9fdb46SRobert Mustacchi     Dwarf_Small *    dataptr = 0;
690*4d9fdb46SRobert Mustacchi     int              res = 0;
691*4d9fdb46SRobert Mustacchi 
692*4d9fdb46SRobert Mustacchi     memset(&signaturedata,0,sizeof(signaturedata));
69349d3bc91SRichard Lowe     cu_context =
694*4d9fdb46SRobert Mustacchi         (Dwarf_CU_Context)_dwarf_get_alloc(dbg, DW_DLA_CU_CONTEXT, 1);
695*4d9fdb46SRobert Mustacchi     if (!cu_context) {
69607dc1947SRichard Lowe         _dwarf_error(dbg, error, DW_DLE_ALLOC_FAIL);
697*4d9fdb46SRobert Mustacchi         return DW_DLV_ERROR;
69849d3bc91SRichard Lowe     }
69949d3bc91SRichard Lowe     cu_context->cc_dbg = dbg;
700*4d9fdb46SRobert Mustacchi     cu_context->cc_is_info = is_info;
701*4d9fdb46SRobert Mustacchi 
702*4d9fdb46SRobert Mustacchi     dataptr = is_info? dbg->de_debug_info.dss_data:
703*4d9fdb46SRobert Mustacchi         dbg->de_debug_types.dss_data;
704*4d9fdb46SRobert Mustacchi     /*  Preliminary sanity checking. */
705*4d9fdb46SRobert Mustacchi     if (!dataptr) {
706*4d9fdb46SRobert Mustacchi         local_dealloc_cu_context(dbg,cu_context);
707*4d9fdb46SRobert Mustacchi         _dwarf_error(dbg, error, DW_DLE_INFO_HEADER_ERROR);
708*4d9fdb46SRobert Mustacchi         return DW_DLV_ERROR;
709*4d9fdb46SRobert Mustacchi     }
710*4d9fdb46SRobert Mustacchi     if (offset >= section_size) {
711*4d9fdb46SRobert Mustacchi         local_dealloc_cu_context(dbg,cu_context);
712*4d9fdb46SRobert Mustacchi         return DW_DLV_ERROR;
713*4d9fdb46SRobert Mustacchi     }
714*4d9fdb46SRobert Mustacchi     if ((offset+4) > section_size) {
715*4d9fdb46SRobert Mustacchi         local_dealloc_cu_context(dbg,cu_context);
716*4d9fdb46SRobert Mustacchi         return DW_DLV_ERROR;
717*4d9fdb46SRobert Mustacchi     }
718*4d9fdb46SRobert Mustacchi     section_end_ptr = dataptr+section_size;
719*4d9fdb46SRobert Mustacchi     cu_ptr = (Dwarf_Byte_Ptr) (dataptr+offset);
72049d3bc91SRichard Lowe 
721*4d9fdb46SRobert Mustacchi     if (section_name_ends_with_dwo(secname)) {
722*4d9fdb46SRobert Mustacchi         cu_context->cc_is_dwo = TRUE;
723*4d9fdb46SRobert Mustacchi     }
724*4d9fdb46SRobert Mustacchi     res = read_info_area_length_and_check(dbg,
725*4d9fdb46SRobert Mustacchi         cu_context,
726*4d9fdb46SRobert Mustacchi         offset,
727*4d9fdb46SRobert Mustacchi         &cu_ptr,
728*4d9fdb46SRobert Mustacchi         section_size,
729*4d9fdb46SRobert Mustacchi         section_end_ptr,
730*4d9fdb46SRobert Mustacchi         &max_cu_global_offset,
731*4d9fdb46SRobert Mustacchi         error);
732*4d9fdb46SRobert Mustacchi     if (res != DW_DLV_OK) {
733*4d9fdb46SRobert Mustacchi         local_dealloc_cu_context(dbg,cu_context);
734*4d9fdb46SRobert Mustacchi         return res;
735*4d9fdb46SRobert Mustacchi     }
736*4d9fdb46SRobert Mustacchi     local_length_size = cu_context->cc_length_size;
737*4d9fdb46SRobert Mustacchi     length = cu_context->cc_length;
738*4d9fdb46SRobert Mustacchi     max_cu_local_offset =  length;
739*4d9fdb46SRobert Mustacchi     res  = _dwarf_read_cu_version_and_abbrev_offset(dbg,
740*4d9fdb46SRobert Mustacchi         cu_ptr,
741*4d9fdb46SRobert Mustacchi         is_info,
742*4d9fdb46SRobert Mustacchi         dbg->de_groupnumber,
743*4d9fdb46SRobert Mustacchi         local_length_size,
744*4d9fdb46SRobert Mustacchi         cu_context,
745*4d9fdb46SRobert Mustacchi         section_end_ptr,
746*4d9fdb46SRobert Mustacchi         &bytes_read,error);
747*4d9fdb46SRobert Mustacchi     if (res != DW_DLV_OK) {
748*4d9fdb46SRobert Mustacchi         local_dealloc_cu_context(dbg,cu_context);
749*4d9fdb46SRobert Mustacchi         return res;
750*4d9fdb46SRobert Mustacchi     }
751*4d9fdb46SRobert Mustacchi     version = cu_context->cc_version_stamp;
752*4d9fdb46SRobert Mustacchi     cu_ptr += bytes_read;
753*4d9fdb46SRobert Mustacchi     unit_type = cu_context->cc_unit_type;
754*4d9fdb46SRobert Mustacchi     if (cu_ptr > section_end_ptr) {
755*4d9fdb46SRobert Mustacchi         local_dealloc_cu_context(dbg,cu_context);
756*4d9fdb46SRobert Mustacchi         _dwarf_error(dbg, error, DW_DLE_INFO_HEADER_ERROR);
757*4d9fdb46SRobert Mustacchi         return DW_DLV_ERROR;
758*4d9fdb46SRobert Mustacchi     }
75949d3bc91SRichard Lowe 
760*4d9fdb46SRobert Mustacchi     /*  In a dwp context, the abbrev_offset is
761*4d9fdb46SRobert Mustacchi         still  incomplete.
762*4d9fdb46SRobert Mustacchi         We need to add in the base from the .debug_cu_index
763*4d9fdb46SRobert Mustacchi         or .debug_tu_index . Done below */
764*4d9fdb46SRobert Mustacchi 
765*4d9fdb46SRobert Mustacchi     /*  At this point, for DW4, the unit_type is not fully
766*4d9fdb46SRobert Mustacchi         correct as we don't know if it is a skeleton or
767*4d9fdb46SRobert Mustacchi         a split_compile or split_type */
768*4d9fdb46SRobert Mustacchi     if (version ==  DW_CU_VERSION5 ||
769*4d9fdb46SRobert Mustacchi         version == DW_CU_VERSION4) {
770*4d9fdb46SRobert Mustacchi         /*  DW4/DW5  header fields, depending on UT type.
771*4d9fdb46SRobert Mustacchi             See DW5  section 7.5.1.x, DW4
772*4d9fdb46SRobert Mustacchi             data is a GNU extension of DW4. */
773*4d9fdb46SRobert Mustacchi         switch(unit_type) {
774*4d9fdb46SRobert Mustacchi         case DW_UT_split_type:
775*4d9fdb46SRobert Mustacchi         case DW_UT_type: {
776*4d9fdb46SRobert Mustacchi             types_extra_len = sizeof(Dwarf_Sig8) /* 8 */ +
777*4d9fdb46SRobert Mustacchi                 local_length_size /*type_offset size*/;
778*4d9fdb46SRobert Mustacchi             break;
779*4d9fdb46SRobert Mustacchi         }
780*4d9fdb46SRobert Mustacchi         case DW_UT_skeleton:
781*4d9fdb46SRobert Mustacchi         case DW_UT_split_compile: {
782*4d9fdb46SRobert Mustacchi             types_extra_len = sizeof(Dwarf_Sig8) /* 8 */;
783*4d9fdb46SRobert Mustacchi             break;
784*4d9fdb46SRobert Mustacchi         }
785*4d9fdb46SRobert Mustacchi         case DW_UT_compile: /*  No additional fields */
786*4d9fdb46SRobert Mustacchi         case DW_UT_partial: /*  No additional fields */
787*4d9fdb46SRobert Mustacchi             break;
788*4d9fdb46SRobert Mustacchi         default:
789*4d9fdb46SRobert Mustacchi             /*  Data corruption in libdwarf? */
790*4d9fdb46SRobert Mustacchi             report_local_unit_type_error(dbg, unit_type,
791*4d9fdb46SRobert Mustacchi                 "(DW4 or DW5)",error);
792*4d9fdb46SRobert Mustacchi             local_dealloc_cu_context(dbg,cu_context);
793*4d9fdb46SRobert Mustacchi             return DW_DLV_ERROR;
794*4d9fdb46SRobert Mustacchi         }
795*4d9fdb46SRobert Mustacchi     }
79649d3bc91SRichard Lowe 
797*4d9fdb46SRobert Mustacchi     /*  Compare the space following the length field
798*4d9fdb46SRobert Mustacchi         to the bytes in the CU header. */
799*4d9fdb46SRobert Mustacchi     if (length <
800*4d9fdb46SRobert Mustacchi         (CU_VERSION_STAMP_SIZE /* is 2 */ +
801*4d9fdb46SRobert Mustacchi         local_length_size /*for debug_abbrev offset */ +
802*4d9fdb46SRobert Mustacchi         CU_ADDRESS_SIZE_SIZE /* is 1 */ +
803*4d9fdb46SRobert Mustacchi         /* and finally size of the rest of the header: */
804*4d9fdb46SRobert Mustacchi         types_extra_len)) {
80549d3bc91SRichard Lowe 
806*4d9fdb46SRobert Mustacchi         local_dealloc_cu_context(dbg,cu_context);
807*4d9fdb46SRobert Mustacchi         _dwarf_error(dbg, error, DW_DLE_CU_LENGTH_ERROR);
808*4d9fdb46SRobert Mustacchi         return DW_DLV_ERROR;
809*4d9fdb46SRobert Mustacchi     }
810*4d9fdb46SRobert Mustacchi     /*  Now we can read the fields with some confidence,
811*4d9fdb46SRobert Mustacchi         we know the fields of the header are inside
812*4d9fdb46SRobert Mustacchi         the section. */
813*4d9fdb46SRobert Mustacchi 
814*4d9fdb46SRobert Mustacchi     cu_context->cc_unit_type = unit_type;
815*4d9fdb46SRobert Mustacchi     switch(unit_type) {
816*4d9fdb46SRobert Mustacchi     case DW_UT_split_type:
817*4d9fdb46SRobert Mustacchi     case DW_UT_type: {
818*4d9fdb46SRobert Mustacchi         int tres = 0;
819*4d9fdb46SRobert Mustacchi         /*  ASSERT: DW_CU_VERSION4 or DW_CU_VERSION5,
820*4d9fdb46SRobert Mustacchi             determined by logic above.
821*4d9fdb46SRobert Mustacchi             Now read the debug_types extra header fields of
822*4d9fdb46SRobert Mustacchi             the signature (8 bytes) and the typeoffset.
823*4d9fdb46SRobert Mustacchi             This can be in executable, ordinary object
824*4d9fdb46SRobert Mustacchi             (as in Type Unit),
825*4d9fdb46SRobert Mustacchi             there was no dwo in DWARF4
826*4d9fdb46SRobert Mustacchi         */
827*4d9fdb46SRobert Mustacchi         memcpy(&signaturedata,cu_ptr,sizeof(signaturedata));
828*4d9fdb46SRobert Mustacchi         cu_ptr += sizeof(signaturedata);
829*4d9fdb46SRobert Mustacchi #if 0
830*4d9fdb46SRobert Mustacchi         READ_UNALIGNED_CK(dbg, typeoffset, Dwarf_Unsigned,
831*4d9fdb46SRobert Mustacchi             cu_ptr, local_length_size,error,section_end_ptr);
832*4d9fdb46SRobert Mustacchi #endif
833*4d9fdb46SRobert Mustacchi         tres = _dwarf_read_unaligned_ck_wrapper(dbg,
834*4d9fdb46SRobert Mustacchi             &typeoffset,cu_ptr,local_length_size,
835*4d9fdb46SRobert Mustacchi             section_end_ptr,error);
836*4d9fdb46SRobert Mustacchi         if (tres != DW_DLV_OK ) {
837*4d9fdb46SRobert Mustacchi             local_dealloc_cu_context(dbg,cu_context);
838*4d9fdb46SRobert Mustacchi             return tres;
839*4d9fdb46SRobert Mustacchi         }
840*4d9fdb46SRobert Mustacchi         cu_context->cc_signature = signaturedata;
841*4d9fdb46SRobert Mustacchi         cu_context->cc_signature_present = TRUE;
842*4d9fdb46SRobert Mustacchi         cu_context->cc_signature_offset = typeoffset;
843*4d9fdb46SRobert Mustacchi         if (typeoffset >= max_cu_local_offset) {
844*4d9fdb46SRobert Mustacchi             local_dealloc_cu_context(dbg,cu_context);
845*4d9fdb46SRobert Mustacchi             _dwarf_error(dbg, error,
846*4d9fdb46SRobert Mustacchi                 DW_DLE_DEBUG_TYPEOFFSET_BAD);
847*4d9fdb46SRobert Mustacchi             return DW_DLV_ERROR;
848*4d9fdb46SRobert Mustacchi         }
849*4d9fdb46SRobert Mustacchi         }
850*4d9fdb46SRobert Mustacchi         break;
851*4d9fdb46SRobert Mustacchi     case DW_UT_skeleton:
852*4d9fdb46SRobert Mustacchi     case DW_UT_split_compile: {
853*4d9fdb46SRobert Mustacchi         /*  These unit types make a pair and
854*4d9fdb46SRobert Mustacchi             paired units have identical signature.*/
855*4d9fdb46SRobert Mustacchi         memcpy(&signaturedata,cu_ptr,sizeof(signaturedata));
856*4d9fdb46SRobert Mustacchi         cu_context->cc_signature = signaturedata;
857*4d9fdb46SRobert Mustacchi         cu_context->cc_signature_present = TRUE;
858*4d9fdb46SRobert Mustacchi 
859*4d9fdb46SRobert Mustacchi         break;
860*4d9fdb46SRobert Mustacchi         }
861*4d9fdb46SRobert Mustacchi     /* The following with no additional fields */
862*4d9fdb46SRobert Mustacchi     case DW_UT_compile:
863*4d9fdb46SRobert Mustacchi     case DW_UT_partial:
864*4d9fdb46SRobert Mustacchi         break;
865*4d9fdb46SRobert Mustacchi     default: {
866*4d9fdb46SRobert Mustacchi         /*  Data corruption in libdwarf? */
867*4d9fdb46SRobert Mustacchi         report_local_unit_type_error(dbg, unit_type,
868*4d9fdb46SRobert Mustacchi             "",error);
869*4d9fdb46SRobert Mustacchi         local_dealloc_cu_context(dbg,cu_context);
870*4d9fdb46SRobert Mustacchi         return DW_DLV_ERROR;
871*4d9fdb46SRobert Mustacchi         }
872*4d9fdb46SRobert Mustacchi     }
873*4d9fdb46SRobert Mustacchi     cu_context->cc_abbrev_hash_table =
874*4d9fdb46SRobert Mustacchi         (Dwarf_Hash_Table) _dwarf_get_alloc(dbg, DW_DLA_HASH_TABLE, 1);
875*4d9fdb46SRobert Mustacchi     if (cu_context->cc_abbrev_hash_table == NULL) {
876*4d9fdb46SRobert Mustacchi         local_dealloc_cu_context(dbg,cu_context);
877*4d9fdb46SRobert Mustacchi         _dwarf_error(dbg, error, DW_DLE_ALLOC_FAIL);
878*4d9fdb46SRobert Mustacchi         return DW_DLV_ERROR;
879*4d9fdb46SRobert Mustacchi     }
88049d3bc91SRichard Lowe 
881*4d9fdb46SRobert Mustacchi     cu_context->cc_debug_offset = offset;
88249d3bc91SRichard Lowe 
883*4d9fdb46SRobert Mustacchi     /*  This is recording an overall section value for later
884*4d9fdb46SRobert Mustacchi         sanity checking. */
885*4d9fdb46SRobert Mustacchi     dis->de_last_offset = max_cu_global_offset;
886*4d9fdb46SRobert Mustacchi     *context_out  = cu_context;
887*4d9fdb46SRobert Mustacchi     return DW_DLV_OK;
888*4d9fdb46SRobert Mustacchi }
88949d3bc91SRichard Lowe 
890*4d9fdb46SRobert Mustacchi static int
reloc_incomplete(int res,Dwarf_Error err)891*4d9fdb46SRobert Mustacchi reloc_incomplete(int res,Dwarf_Error err)
892*4d9fdb46SRobert Mustacchi {
893*4d9fdb46SRobert Mustacchi     int e = 0;
89449d3bc91SRichard Lowe 
895*4d9fdb46SRobert Mustacchi     if (res == DW_DLV_OK) {
896*4d9fdb46SRobert Mustacchi         return FALSE;
897*4d9fdb46SRobert Mustacchi     }
898*4d9fdb46SRobert Mustacchi     if (res == DW_DLV_NO_ENTRY) {
899*4d9fdb46SRobert Mustacchi         return FALSE;
900*4d9fdb46SRobert Mustacchi     }
901*4d9fdb46SRobert Mustacchi     e = dwarf_errno(err);
902*4d9fdb46SRobert Mustacchi     if (e == DW_DLE_RELOC_MISMATCH_INDEX        ||
903*4d9fdb46SRobert Mustacchi         e == DW_DLE_RELOC_MISMATCH_RELOC_INDEX  ||
904*4d9fdb46SRobert Mustacchi         e == DW_DLE_RELOC_MISMATCH_STRTAB_INDEX ||
905*4d9fdb46SRobert Mustacchi         e == DW_DLE_RELOC_SECTION_MISMATCH      ||
906*4d9fdb46SRobert Mustacchi         e == DW_DLE_RELOC_SECTION_MISSING_INDEX ||
907*4d9fdb46SRobert Mustacchi         e == DW_DLE_RELOC_SECTION_LENGTH_ODD    ||
908*4d9fdb46SRobert Mustacchi         e == DW_DLE_RELOC_SECTION_PTR_NULL      ||
909*4d9fdb46SRobert Mustacchi         e == DW_DLE_RELOC_SECTION_MALLOC_FAIL   ||
910*4d9fdb46SRobert Mustacchi         e == DW_DLE_SEEK_OFF_END                ||
911*4d9fdb46SRobert Mustacchi         e == DW_DLE_RELOC_INVALID               ||
912*4d9fdb46SRobert Mustacchi         e == DW_DLE_RELOC_SECTION_SYMBOL_INDEX_BAD ) {
913*4d9fdb46SRobert Mustacchi         return TRUE;
914*4d9fdb46SRobert Mustacchi     }
915*4d9fdb46SRobert Mustacchi     return FALSE;
916*4d9fdb46SRobert Mustacchi }
91749d3bc91SRichard Lowe 
918*4d9fdb46SRobert Mustacchi 
919*4d9fdb46SRobert Mustacchi 
920*4d9fdb46SRobert Mustacchi /*  Returns offset of next compilation-unit thru next_cu_offset
921*4d9fdb46SRobert Mustacchi     pointer.
922*4d9fdb46SRobert Mustacchi     It sequentially moves from one
923*4d9fdb46SRobert Mustacchi     cu to the next.  The current cu is recorded
924*4d9fdb46SRobert Mustacchi     internally by libdwarf.
925*4d9fdb46SRobert Mustacchi 
926*4d9fdb46SRobert Mustacchi     The _b form is new for DWARF4 adding new returned fields.  */
927*4d9fdb46SRobert Mustacchi int
dwarf_next_cu_header(Dwarf_Debug dbg,Dwarf_Unsigned * cu_header_length,Dwarf_Half * version_stamp,Dwarf_Unsigned * abbrev_offset,Dwarf_Half * address_size,Dwarf_Unsigned * next_cu_offset,Dwarf_Error * error)928*4d9fdb46SRobert Mustacchi dwarf_next_cu_header(Dwarf_Debug dbg,
929*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned * cu_header_length,
930*4d9fdb46SRobert Mustacchi     Dwarf_Half * version_stamp,
931*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned * abbrev_offset,
932*4d9fdb46SRobert Mustacchi     Dwarf_Half * address_size,
933*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned * next_cu_offset,
934*4d9fdb46SRobert Mustacchi     Dwarf_Error * error)
935*4d9fdb46SRobert Mustacchi {
936*4d9fdb46SRobert Mustacchi     Dwarf_Bool is_info = true;
937*4d9fdb46SRobert Mustacchi     Dwarf_Half header_type = 0;
938*4d9fdb46SRobert Mustacchi     return _dwarf_next_cu_header_internal(dbg,
939*4d9fdb46SRobert Mustacchi         is_info,
940*4d9fdb46SRobert Mustacchi         cu_header_length,
941*4d9fdb46SRobert Mustacchi         version_stamp,
942*4d9fdb46SRobert Mustacchi         abbrev_offset,
943*4d9fdb46SRobert Mustacchi         address_size,
944*4d9fdb46SRobert Mustacchi         0,0,0,0,0,
945*4d9fdb46SRobert Mustacchi         next_cu_offset,
946*4d9fdb46SRobert Mustacchi         &header_type,
947*4d9fdb46SRobert Mustacchi         error);
948*4d9fdb46SRobert Mustacchi }
949*4d9fdb46SRobert Mustacchi int
dwarf_next_cu_header_b(Dwarf_Debug dbg,Dwarf_Unsigned * cu_header_length,Dwarf_Half * version_stamp,Dwarf_Unsigned * abbrev_offset,Dwarf_Half * address_size,Dwarf_Half * offset_size,Dwarf_Half * extension_size,Dwarf_Unsigned * next_cu_offset,Dwarf_Error * error)950*4d9fdb46SRobert Mustacchi dwarf_next_cu_header_b(Dwarf_Debug dbg,
951*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned * cu_header_length,
952*4d9fdb46SRobert Mustacchi     Dwarf_Half * version_stamp,
953*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned * abbrev_offset,
954*4d9fdb46SRobert Mustacchi     Dwarf_Half * address_size,
955*4d9fdb46SRobert Mustacchi     Dwarf_Half * offset_size,
956*4d9fdb46SRobert Mustacchi     Dwarf_Half * extension_size,
957*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned * next_cu_offset,
958*4d9fdb46SRobert Mustacchi     Dwarf_Error * error)
959*4d9fdb46SRobert Mustacchi {
960*4d9fdb46SRobert Mustacchi     Dwarf_Bool is_info = true;
961*4d9fdb46SRobert Mustacchi     Dwarf_Half header_type = 0;
962*4d9fdb46SRobert Mustacchi     return _dwarf_next_cu_header_internal(dbg,
963*4d9fdb46SRobert Mustacchi         is_info,
964*4d9fdb46SRobert Mustacchi         cu_header_length,
965*4d9fdb46SRobert Mustacchi         version_stamp,
966*4d9fdb46SRobert Mustacchi         abbrev_offset,
967*4d9fdb46SRobert Mustacchi         address_size,
968*4d9fdb46SRobert Mustacchi         offset_size,extension_size,
969*4d9fdb46SRobert Mustacchi         0,0,0,
970*4d9fdb46SRobert Mustacchi         next_cu_offset,
971*4d9fdb46SRobert Mustacchi         &header_type,
972*4d9fdb46SRobert Mustacchi         error);
973*4d9fdb46SRobert Mustacchi }
974*4d9fdb46SRobert Mustacchi 
975*4d9fdb46SRobert Mustacchi int
dwarf_next_cu_header_c(Dwarf_Debug dbg,Dwarf_Bool is_info,Dwarf_Unsigned * cu_header_length,Dwarf_Half * version_stamp,Dwarf_Unsigned * abbrev_offset,Dwarf_Half * address_size,Dwarf_Half * offset_size,Dwarf_Half * extension_size,Dwarf_Sig8 * signature,Dwarf_Unsigned * typeoffset,Dwarf_Unsigned * next_cu_offset,Dwarf_Error * error)976*4d9fdb46SRobert Mustacchi dwarf_next_cu_header_c(Dwarf_Debug dbg,
977*4d9fdb46SRobert Mustacchi     Dwarf_Bool is_info,
978*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned * cu_header_length,
979*4d9fdb46SRobert Mustacchi     Dwarf_Half * version_stamp,
980*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned * abbrev_offset,
981*4d9fdb46SRobert Mustacchi     Dwarf_Half * address_size,
982*4d9fdb46SRobert Mustacchi     Dwarf_Half * offset_size,
983*4d9fdb46SRobert Mustacchi     Dwarf_Half * extension_size,
984*4d9fdb46SRobert Mustacchi     Dwarf_Sig8 * signature,
985*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned * typeoffset,
986*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned * next_cu_offset,
987*4d9fdb46SRobert Mustacchi     Dwarf_Error * error)
988*4d9fdb46SRobert Mustacchi {
989*4d9fdb46SRobert Mustacchi     Dwarf_Half header_type = 0;
990*4d9fdb46SRobert Mustacchi     int res =_dwarf_next_cu_header_internal(dbg,
991*4d9fdb46SRobert Mustacchi         is_info,
992*4d9fdb46SRobert Mustacchi         cu_header_length,
993*4d9fdb46SRobert Mustacchi         version_stamp,
994*4d9fdb46SRobert Mustacchi         abbrev_offset,
995*4d9fdb46SRobert Mustacchi         address_size,
996*4d9fdb46SRobert Mustacchi         offset_size,
997*4d9fdb46SRobert Mustacchi         extension_size,
998*4d9fdb46SRobert Mustacchi         signature,
999*4d9fdb46SRobert Mustacchi         0,
1000*4d9fdb46SRobert Mustacchi         typeoffset,
1001*4d9fdb46SRobert Mustacchi         next_cu_offset,
1002*4d9fdb46SRobert Mustacchi         &header_type,
1003*4d9fdb46SRobert Mustacchi         error);
1004*4d9fdb46SRobert Mustacchi     return res;
1005*4d9fdb46SRobert Mustacchi }
1006*4d9fdb46SRobert Mustacchi int
dwarf_next_cu_header_d(Dwarf_Debug dbg,Dwarf_Bool is_info,Dwarf_Unsigned * cu_header_length,Dwarf_Half * version_stamp,Dwarf_Unsigned * abbrev_offset,Dwarf_Half * address_size,Dwarf_Half * offset_size,Dwarf_Half * extension_size,Dwarf_Sig8 * signature,Dwarf_Unsigned * typeoffset,Dwarf_Unsigned * next_cu_offset,Dwarf_Half * header_cu_type,Dwarf_Error * error)1007*4d9fdb46SRobert Mustacchi dwarf_next_cu_header_d(Dwarf_Debug dbg,
1008*4d9fdb46SRobert Mustacchi     Dwarf_Bool is_info,
1009*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned * cu_header_length,
1010*4d9fdb46SRobert Mustacchi     Dwarf_Half * version_stamp,
1011*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned * abbrev_offset,
1012*4d9fdb46SRobert Mustacchi     Dwarf_Half * address_size,
1013*4d9fdb46SRobert Mustacchi     Dwarf_Half * offset_size,
1014*4d9fdb46SRobert Mustacchi     Dwarf_Half * extension_size,
1015*4d9fdb46SRobert Mustacchi     Dwarf_Sig8 * signature,
1016*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned * typeoffset,
1017*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned * next_cu_offset,
1018*4d9fdb46SRobert Mustacchi     Dwarf_Half * header_cu_type,
1019*4d9fdb46SRobert Mustacchi     Dwarf_Error * error)
1020*4d9fdb46SRobert Mustacchi {
1021*4d9fdb46SRobert Mustacchi     /* Faking has_signature to do nothing. */
1022*4d9fdb46SRobert Mustacchi     Dwarf_Bool* has_signature = 0;
1023*4d9fdb46SRobert Mustacchi     int res = 0;
1024*4d9fdb46SRobert Mustacchi 
1025*4d9fdb46SRobert Mustacchi     res = _dwarf_next_cu_header_internal(dbg,
1026*4d9fdb46SRobert Mustacchi         is_info,
1027*4d9fdb46SRobert Mustacchi         cu_header_length,
1028*4d9fdb46SRobert Mustacchi         version_stamp,
1029*4d9fdb46SRobert Mustacchi         abbrev_offset,
1030*4d9fdb46SRobert Mustacchi         address_size,
1031*4d9fdb46SRobert Mustacchi         offset_size,
1032*4d9fdb46SRobert Mustacchi         extension_size,
1033*4d9fdb46SRobert Mustacchi         signature,
1034*4d9fdb46SRobert Mustacchi         has_signature,
1035*4d9fdb46SRobert Mustacchi         typeoffset,
1036*4d9fdb46SRobert Mustacchi         next_cu_offset,
1037*4d9fdb46SRobert Mustacchi         header_cu_type,
1038*4d9fdb46SRobert Mustacchi         error);
1039*4d9fdb46SRobert Mustacchi     return res;
1040*4d9fdb46SRobert Mustacchi }
1041*4d9fdb46SRobert Mustacchi 
1042*4d9fdb46SRobert Mustacchi 
1043*4d9fdb46SRobert Mustacchi static void
local_attrlist_dealloc(Dwarf_Debug dbg,Dwarf_Signed atcount,Dwarf_Attribute * alist)1044*4d9fdb46SRobert Mustacchi local_attrlist_dealloc(Dwarf_Debug dbg,
1045*4d9fdb46SRobert Mustacchi     Dwarf_Signed atcount,
1046*4d9fdb46SRobert Mustacchi     Dwarf_Attribute *alist)
1047*4d9fdb46SRobert Mustacchi {
1048*4d9fdb46SRobert Mustacchi     Dwarf_Signed i = 0;
1049*4d9fdb46SRobert Mustacchi 
1050*4d9fdb46SRobert Mustacchi     for ( ; i < atcount; ++i) {
1051*4d9fdb46SRobert Mustacchi         dwarf_dealloc(dbg,alist[i],DW_DLA_ATTR);
105249d3bc91SRichard Lowe     }
1053*4d9fdb46SRobert Mustacchi     dwarf_dealloc(dbg,alist,DW_DLA_LIST);
1054*4d9fdb46SRobert Mustacchi }
105549d3bc91SRichard Lowe 
1056*4d9fdb46SRobert Mustacchi 
1057*4d9fdb46SRobert Mustacchi 
1058*4d9fdb46SRobert Mustacchi /*
1059*4d9fdb46SRobert Mustacchi     A DWO/DWP CU has different base fields than
1060*4d9fdb46SRobert Mustacchi     a normal object/executable, but this finds
1061*4d9fdb46SRobert Mustacchi     the base fields for both types.
1062*4d9fdb46SRobert Mustacchi */
1063*4d9fdb46SRobert Mustacchi static int
find_cu_die_base_fields(Dwarf_Debug dbg,Dwarf_CU_Context cucon,Dwarf_Die cudie,Dwarf_Error * error)1064*4d9fdb46SRobert Mustacchi find_cu_die_base_fields(Dwarf_Debug dbg,
1065*4d9fdb46SRobert Mustacchi     Dwarf_CU_Context cucon,
1066*4d9fdb46SRobert Mustacchi     Dwarf_Die cudie,
1067*4d9fdb46SRobert Mustacchi     Dwarf_Error*    error)
1068*4d9fdb46SRobert Mustacchi {
1069*4d9fdb46SRobert Mustacchi     Dwarf_CU_Context  cu_context = 0;
1070*4d9fdb46SRobert Mustacchi     Dwarf_Attribute * alist = 0;
1071*4d9fdb46SRobert Mustacchi     Dwarf_Signed      atcount = 0;
1072*4d9fdb46SRobert Mustacchi     unsigned          version_stamp = 2;
1073*4d9fdb46SRobert Mustacchi     int               alres = 0;
1074*4d9fdb46SRobert Mustacchi     Dwarf_Signed      i = 0;
1075*4d9fdb46SRobert Mustacchi     Dwarf_Signed low_pc_attrnum = -1;
1076*4d9fdb46SRobert Mustacchi     Dwarf_Signed at_addr_base_attrnum = -1;
1077*4d9fdb46SRobert Mustacchi 
1078*4d9fdb46SRobert Mustacchi     cu_context = cudie->di_cu_context;
1079*4d9fdb46SRobert Mustacchi     version_stamp = cu_context->cc_version_stamp;
1080*4d9fdb46SRobert Mustacchi 
1081*4d9fdb46SRobert Mustacchi     alres = dwarf_attrlist(cudie, &alist,
1082*4d9fdb46SRobert Mustacchi         &atcount,error);
1083*4d9fdb46SRobert Mustacchi     if(alres != DW_DLV_OK) {
1084*4d9fdb46SRobert Mustacchi         /* Something is badly wrong. No attrlist! */
1085*4d9fdb46SRobert Mustacchi         return alres;
108649d3bc91SRichard Lowe     }
1087*4d9fdb46SRobert Mustacchi     /*  DW_AT_dwo_id and/or DW_AT_GNU_dwo_id
1088*4d9fdb46SRobert Mustacchi         are only found  in some
1089*4d9fdb46SRobert Mustacchi         experimental DWARF4.
1090*4d9fdb46SRobert Mustacchi         DWARF5 changed CU header contents
1091*4d9fdb46SRobert Mustacchi         to make this attribute unnecessary.
1092*4d9fdb46SRobert Mustacchi         DW_AT_GNU_odr_signature is the same format,
1093*4d9fdb46SRobert Mustacchi         but is in a different namespace so not
1094*4d9fdb46SRobert Mustacchi         appropriate here..
1095*4d9fdb46SRobert Mustacchi     */
1096*4d9fdb46SRobert Mustacchi     for(i = 0;  i < atcount; ++i) {
1097*4d9fdb46SRobert Mustacchi         Dwarf_Half attrnum;
1098*4d9fdb46SRobert Mustacchi         int ares = 0;
1099*4d9fdb46SRobert Mustacchi         Dwarf_Attribute attr = alist[i];
1100*4d9fdb46SRobert Mustacchi         ares = dwarf_whatattr(attr,&attrnum,error);
1101*4d9fdb46SRobert Mustacchi         if (ares == DW_DLV_OK) {
1102*4d9fdb46SRobert Mustacchi             switch(attrnum) {
1103*4d9fdb46SRobert Mustacchi             case DW_AT_dwo_id:
1104*4d9fdb46SRobert Mustacchi             case DW_AT_GNU_dwo_id: {
1105*4d9fdb46SRobert Mustacchi                 Dwarf_Sig8 signature;
1106*4d9fdb46SRobert Mustacchi                 /*  This is for DWARF4 with an early
1107*4d9fdb46SRobert Mustacchi                     non-standard version
1108*4d9fdb46SRobert Mustacchi                     of split dwarf. Not DWARF5. */
1109*4d9fdb46SRobert Mustacchi                 int sres = 0;
1110*4d9fdb46SRobert Mustacchi                 if (version_stamp != DW_CU_VERSION4 ) {
1111*4d9fdb46SRobert Mustacchi                     /* Not supposed to happen. */
1112*4d9fdb46SRobert Mustacchi                     local_attrlist_dealloc(dbg,atcount,alist);
1113*4d9fdb46SRobert Mustacchi                     _dwarf_error(dbg,error,
1114*4d9fdb46SRobert Mustacchi                         DW_DLE_IMPROPER_DWO_ID);
1115*4d9fdb46SRobert Mustacchi                     return DW_DLV_ERROR;
1116*4d9fdb46SRobert Mustacchi                 }
1117*4d9fdb46SRobert Mustacchi                 memset(&signature, 0, sizeof(signature));
1118*4d9fdb46SRobert Mustacchi                 sres = dwarf_formsig8_const(attr,
1119*4d9fdb46SRobert Mustacchi                     &signature,error);
1120*4d9fdb46SRobert Mustacchi                 if(sres == DW_DLV_OK) {
1121*4d9fdb46SRobert Mustacchi                     if (!cucon->cc_signature_present) {
1122*4d9fdb46SRobert Mustacchi                         cucon->cc_signature = signature;
1123*4d9fdb46SRobert Mustacchi                         cucon->cc_signature_present = TRUE;
1124*4d9fdb46SRobert Mustacchi                     } else {
1125*4d9fdb46SRobert Mustacchi                         /*  Something wrong. Two styles ?
1126*4d9fdb46SRobert Mustacchi                             Do what? verify the same sig?
1127*4d9fdb46SRobert Mustacchi                             FIXME */
1128*4d9fdb46SRobert Mustacchi                     }
1129*4d9fdb46SRobert Mustacchi                 } else {
1130*4d9fdb46SRobert Mustacchi                     /* Something is badly wrong. */
1131*4d9fdb46SRobert Mustacchi                     local_attrlist_dealloc(dbg,atcount,alist);
1132*4d9fdb46SRobert Mustacchi                     return sres;
1133*4d9fdb46SRobert Mustacchi                 }
1134*4d9fdb46SRobert Mustacchi                 break;
1135*4d9fdb46SRobert Mustacchi             }
1136*4d9fdb46SRobert Mustacchi             /*  If, in .debug_rnglists for a CU the
1137*4d9fdb46SRobert Mustacchi                 applicable range has no base address
1138*4d9fdb46SRobert Mustacchi                 this attribute provides a base address.
1139*4d9fdb46SRobert Mustacchi                 If this is indexed doing this now would
1140*4d9fdb46SRobert Mustacchi                 lead to an infinite recursion.
1141*4d9fdb46SRobert Mustacchi                 So wait till all the other fields seen.
1142*4d9fdb46SRobert Mustacchi             */
1143*4d9fdb46SRobert Mustacchi             case DW_AT_low_pc: {
1144*4d9fdb46SRobert Mustacchi                 low_pc_attrnum = i;
1145*4d9fdb46SRobert Mustacchi                 break;
1146*4d9fdb46SRobert Mustacchi             }
114749d3bc91SRichard Lowe 
1148*4d9fdb46SRobert Mustacchi             /*  The offset is of the first offset in
1149*4d9fdb46SRobert Mustacchi                 .debug_str_offsets that is the string table
1150*4d9fdb46SRobert Mustacchi                 for this CU. */
1151*4d9fdb46SRobert Mustacchi             case DW_AT_str_offsets_base:{
1152*4d9fdb46SRobert Mustacchi                 int udres = 0;
1153*4d9fdb46SRobert Mustacchi                 udres = dwarf_global_formref(attr,
1154*4d9fdb46SRobert Mustacchi                     &cucon->cc_str_offsets_base,
1155*4d9fdb46SRobert Mustacchi                     error);
1156*4d9fdb46SRobert Mustacchi                 if(udres == DW_DLV_OK) {
1157*4d9fdb46SRobert Mustacchi                     cucon->cc_str_offsets_base_present = TRUE;
1158*4d9fdb46SRobert Mustacchi                 } else {
1159*4d9fdb46SRobert Mustacchi                     local_attrlist_dealloc(dbg,atcount,alist);
1160*4d9fdb46SRobert Mustacchi                     /* Something is badly wrong. */
1161*4d9fdb46SRobert Mustacchi                     return udres;
1162*4d9fdb46SRobert Mustacchi                 }
1163*4d9fdb46SRobert Mustacchi                 break;
1164*4d9fdb46SRobert Mustacchi             }
1165*4d9fdb46SRobert Mustacchi             /*  offset in .debug_loclists  of the offsets table
1166*4d9fdb46SRobert Mustacchi                 applicable to this CU. */
1167*4d9fdb46SRobert Mustacchi             case DW_AT_loclists_base: {
1168*4d9fdb46SRobert Mustacchi                 int udres = 0;
1169*4d9fdb46SRobert Mustacchi                 udres = dwarf_global_formref(attr,
1170*4d9fdb46SRobert Mustacchi                     &cucon->cc_loclists_base,
1171*4d9fdb46SRobert Mustacchi                     error);
1172*4d9fdb46SRobert Mustacchi                 if(udres == DW_DLV_OK) {
1173*4d9fdb46SRobert Mustacchi                     cucon->cc_loclists_base_present = TRUE;
1174*4d9fdb46SRobert Mustacchi                 } else {
1175*4d9fdb46SRobert Mustacchi                     local_attrlist_dealloc(dbg,atcount,alist);
1176*4d9fdb46SRobert Mustacchi                     /* Something is badly wrong. */
1177*4d9fdb46SRobert Mustacchi                     return udres;
1178*4d9fdb46SRobert Mustacchi                 }
1179*4d9fdb46SRobert Mustacchi                 break;
1180*4d9fdb46SRobert Mustacchi                 }
1181*4d9fdb46SRobert Mustacchi             /*  Base offset  in .debug_addr of the addr table
1182*4d9fdb46SRobert Mustacchi                 for this CU. DWARF5 (and possibly GNU DWARF4) */
1183*4d9fdb46SRobert Mustacchi             case DW_AT_addr_base:
1184*4d9fdb46SRobert Mustacchi             case DW_AT_GNU_addr_base: {
1185*4d9fdb46SRobert Mustacchi                 int udres = 0;
1186*4d9fdb46SRobert Mustacchi                 at_addr_base_attrnum = i;
1187*4d9fdb46SRobert Mustacchi                 udres = dwarf_global_formref(attr,
1188*4d9fdb46SRobert Mustacchi                     &cucon->cc_addr_base,
1189*4d9fdb46SRobert Mustacchi                     error);
1190*4d9fdb46SRobert Mustacchi                 if(udres == DW_DLV_OK) {
1191*4d9fdb46SRobert Mustacchi                     cucon->cc_addr_base_present = TRUE;
1192*4d9fdb46SRobert Mustacchi                 } else {
1193*4d9fdb46SRobert Mustacchi                     local_attrlist_dealloc(dbg,atcount,alist);
1194*4d9fdb46SRobert Mustacchi                     /* Something is badly wrong. */
1195*4d9fdb46SRobert Mustacchi                     return udres;
1196*4d9fdb46SRobert Mustacchi                 }
1197*4d9fdb46SRobert Mustacchi                 break;
1198*4d9fdb46SRobert Mustacchi             }
1199*4d9fdb46SRobert Mustacchi             case DW_AT_GNU_ranges_base:
1200*4d9fdb46SRobert Mustacchi             /*  The DW4 ranges base was never used in GNU
1201*4d9fdb46SRobert Mustacchi                 but did get emitted in skeletons.
1202*4d9fdb46SRobert Mustacchi                 http://llvm.1065342.n5.nabble.com/
1203*4d9fdb46SRobert Mustacchi                 DebugInfo-DW-AT-GNU-ranges-base-in-
1204*4d9fdb46SRobert Mustacchi                 non-fission-td64194.html
1205*4d9fdb46SRobert Mustacchi                 We therefore ignore it.  */
1206*4d9fdb46SRobert Mustacchi                 break;
1207*4d9fdb46SRobert Mustacchi             /*  offset in .debug_rnglists  of the offsets table
1208*4d9fdb46SRobert Mustacchi                 applicable to this CU. */
1209*4d9fdb46SRobert Mustacchi             case  DW_AT_rnglists_base: {
1210*4d9fdb46SRobert Mustacchi                 int udres = 0;
1211*4d9fdb46SRobert Mustacchi                 udres = dwarf_global_formref(attr,
1212*4d9fdb46SRobert Mustacchi                     &cucon->cc_rnglists_base,
1213*4d9fdb46SRobert Mustacchi                     error);
1214*4d9fdb46SRobert Mustacchi                 if(udres == DW_DLV_OK) {
1215*4d9fdb46SRobert Mustacchi                     cucon->cc_rnglists_base_present = TRUE;
1216*4d9fdb46SRobert Mustacchi                 } else {
1217*4d9fdb46SRobert Mustacchi                     local_attrlist_dealloc(dbg,atcount,alist);
1218*4d9fdb46SRobert Mustacchi                     /* Something is badly wrong. */
1219*4d9fdb46SRobert Mustacchi                     return udres;
1220*4d9fdb46SRobert Mustacchi                 }
1221*4d9fdb46SRobert Mustacchi                 break;
1222*4d9fdb46SRobert Mustacchi                 }
1223*4d9fdb46SRobert Mustacchi             /*  A signature, found in a DWARF5 skeleton
1224*4d9fdb46SRobert Mustacchi                 compilation unit. */
1225*4d9fdb46SRobert Mustacchi             case DW_AT_GNU_dwo_name:
1226*4d9fdb46SRobert Mustacchi             case DW_AT_dwo_name: {
1227*4d9fdb46SRobert Mustacchi                 int dnres = 0;
1228*4d9fdb46SRobert Mustacchi 
1229*4d9fdb46SRobert Mustacchi                 dnres = dwarf_formstring(attr,
1230*4d9fdb46SRobert Mustacchi                     &cucon->cc_dwo_name,error);
1231*4d9fdb46SRobert Mustacchi                 if (dnres != DW_DLV_OK) {
1232*4d9fdb46SRobert Mustacchi                     local_attrlist_dealloc(dbg,atcount,alist);
1233*4d9fdb46SRobert Mustacchi                     return dnres;
1234*4d9fdb46SRobert Mustacchi                 }
1235*4d9fdb46SRobert Mustacchi                 cucon->cc_dwo_name_present = TRUE;
1236*4d9fdb46SRobert Mustacchi                 break;
1237*4d9fdb46SRobert Mustacchi                 }
1238*4d9fdb46SRobert Mustacchi             default: /* do nothing, not an attribute
1239*4d9fdb46SRobert Mustacchi                 we need to deal with here. */
1240*4d9fdb46SRobert Mustacchi                 break;
1241*4d9fdb46SRobert Mustacchi             }
1242*4d9fdb46SRobert Mustacchi         }
124349d3bc91SRichard Lowe     }
1244*4d9fdb46SRobert Mustacchi     if (low_pc_attrnum >= 0 ){
1245*4d9fdb46SRobert Mustacchi         int lres = 0;
1246*4d9fdb46SRobert Mustacchi         Dwarf_Attribute attr = alist[low_pc_attrnum];
1247*4d9fdb46SRobert Mustacchi         Dwarf_Half form = 0;
1248*4d9fdb46SRobert Mustacchi 
1249*4d9fdb46SRobert Mustacchi         /* If the form is indexed, we better have
1250*4d9fdb46SRobert Mustacchi             seen DW_AT_addr_base.! */
1251*4d9fdb46SRobert Mustacchi         lres = dwarf_whatform(attr,&form,error);
1252*4d9fdb46SRobert Mustacchi         if (lres != DW_DLV_OK) {
1253*4d9fdb46SRobert Mustacchi             local_attrlist_dealloc(dbg,atcount,alist);
1254*4d9fdb46SRobert Mustacchi             return lres;
1255*4d9fdb46SRobert Mustacchi         }
1256*4d9fdb46SRobert Mustacchi         if (dwarf_addr_form_is_indexed(form)) {
1257*4d9fdb46SRobert Mustacchi             if (at_addr_base_attrnum < 0) {
1258*4d9fdb46SRobert Mustacchi                 dwarfstring m;
1259*4d9fdb46SRobert Mustacchi 
1260*4d9fdb46SRobert Mustacchi                 dwarfstring_constructor(&m);
1261*4d9fdb46SRobert Mustacchi                 dwarfstring_append(&m,
1262*4d9fdb46SRobert Mustacchi                     "DW_DLE_ATTR_NO_CU_CONTEXT: "
1263*4d9fdb46SRobert Mustacchi                     "The DW_AT_low_pc  CU_DIE uses "
1264*4d9fdb46SRobert Mustacchi                     "an indexed attribute yet "
1265*4d9fdb46SRobert Mustacchi                     "DW_AT_addr_base is not in the CU DIE.");
1266*4d9fdb46SRobert Mustacchi                 _dwarf_error_string(dbg,error,
1267*4d9fdb46SRobert Mustacchi                     DW_DLE_ATTR_NO_CU_CONTEXT,
1268*4d9fdb46SRobert Mustacchi                     dwarfstring_string(&m));
1269*4d9fdb46SRobert Mustacchi                 dwarfstring_destructor(&m);
1270*4d9fdb46SRobert Mustacchi                 local_attrlist_dealloc(dbg,atcount,alist);
1271*4d9fdb46SRobert Mustacchi                 return DW_DLV_ERROR;
1272*4d9fdb46SRobert Mustacchi             }
1273*4d9fdb46SRobert Mustacchi         }
1274*4d9fdb46SRobert Mustacchi         lres = dwarf_formaddr(attr,
1275*4d9fdb46SRobert Mustacchi             &cucon->cc_low_pc,error);
1276*4d9fdb46SRobert Mustacchi         if(lres == DW_DLV_OK) {
1277*4d9fdb46SRobert Mustacchi             cucon->cc_low_pc_present = TRUE;
1278*4d9fdb46SRobert Mustacchi         } else {
1279*4d9fdb46SRobert Mustacchi             /* Something is badly wrong. */
1280*4d9fdb46SRobert Mustacchi             local_attrlist_dealloc(dbg,atcount,alist);
1281*4d9fdb46SRobert Mustacchi             return lres;
1282*4d9fdb46SRobert Mustacchi         }
1283*4d9fdb46SRobert Mustacchi     }
1284*4d9fdb46SRobert Mustacchi     local_attrlist_dealloc(dbg,atcount,alist);
1285*4d9fdb46SRobert Mustacchi     alist = 0;
1286*4d9fdb46SRobert Mustacchi     atcount = 0;
1287*4d9fdb46SRobert Mustacchi     {
1288*4d9fdb46SRobert Mustacchi         int chres = 0;
1289*4d9fdb46SRobert Mustacchi         Dwarf_Half flag = 0;
1290*4d9fdb46SRobert Mustacchi 
1291*4d9fdb46SRobert Mustacchi         /*  always winds up with cc_cu_die_has_children
1292*4d9fdb46SRobert Mustacchi             set intentionally...to something. */
1293*4d9fdb46SRobert Mustacchi         cucon->cc_cu_die_has_children = TRUE;
1294*4d9fdb46SRobert Mustacchi         chres = dwarf_die_abbrev_children_flag(cudie,&flag);
1295*4d9fdb46SRobert Mustacchi         /*  If chres is not DW_DLV_OK the assumption
1296*4d9fdb46SRobert Mustacchi             of children remains true. */
1297*4d9fdb46SRobert Mustacchi         if (chres == DW_DLV_OK) {
1298*4d9fdb46SRobert Mustacchi             cucon->cc_cu_die_has_children = flag;
1299*4d9fdb46SRobert Mustacchi         }
1300*4d9fdb46SRobert Mustacchi     }
1301*4d9fdb46SRobert Mustacchi     return DW_DLV_OK;
1302*4d9fdb46SRobert Mustacchi }
130349d3bc91SRichard Lowe 
1304*4d9fdb46SRobert Mustacchi /*  Called only for DWARF4 */
1305*4d9fdb46SRobert Mustacchi static void
assign_correct_unit_type(Dwarf_CU_Context cu_context)1306*4d9fdb46SRobert Mustacchi assign_correct_unit_type(Dwarf_CU_Context cu_context)
1307*4d9fdb46SRobert Mustacchi {
1308*4d9fdb46SRobert Mustacchi     Dwarf_Half tag = cu_context->cc_cu_die_tag;
1309*4d9fdb46SRobert Mustacchi     if(!cu_context->cc_cu_die_has_children) {
1310*4d9fdb46SRobert Mustacchi         if(cu_context->cc_signature_present) {
1311*4d9fdb46SRobert Mustacchi             if (tag == DW_TAG_compile_unit ||
1312*4d9fdb46SRobert Mustacchi                 tag == DW_TAG_type_unit ) {
1313*4d9fdb46SRobert Mustacchi                 cu_context->cc_unit_type = DW_UT_skeleton;
1314*4d9fdb46SRobert Mustacchi             }
1315*4d9fdb46SRobert Mustacchi         }
1316*4d9fdb46SRobert Mustacchi     } else {
1317*4d9fdb46SRobert Mustacchi         if(cu_context->cc_signature_present) {
1318*4d9fdb46SRobert Mustacchi             if (tag == DW_TAG_compile_unit) {
1319*4d9fdb46SRobert Mustacchi                 cu_context->cc_unit_type = DW_UT_split_compile;
1320*4d9fdb46SRobert Mustacchi             } else if (tag == DW_TAG_type_unit) {
1321*4d9fdb46SRobert Mustacchi                 cu_context->cc_unit_type = DW_UT_split_type;
1322*4d9fdb46SRobert Mustacchi             }
1323*4d9fdb46SRobert Mustacchi         }
1324*4d9fdb46SRobert Mustacchi     }
1325*4d9fdb46SRobert Mustacchi }
1326*4d9fdb46SRobert Mustacchi 
1327*4d9fdb46SRobert Mustacchi static int
finish_up_cu_context_from_cudie(Dwarf_Debug dbg,Dwarf_Unsigned offset,Dwarf_CU_Context cu_context,Dwarf_Error * error)1328*4d9fdb46SRobert Mustacchi finish_up_cu_context_from_cudie(Dwarf_Debug dbg,
1329*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned offset,
1330*4d9fdb46SRobert Mustacchi     Dwarf_CU_Context cu_context,
1331*4d9fdb46SRobert Mustacchi     Dwarf_Error *error)
1332*4d9fdb46SRobert Mustacchi {
1333*4d9fdb46SRobert Mustacchi     int version = cu_context->cc_version_stamp;
1334*4d9fdb46SRobert Mustacchi     Dwarf_Sig8 signaturedata;
1335*4d9fdb46SRobert Mustacchi     int res = 0;
1336*4d9fdb46SRobert Mustacchi 
1337*4d9fdb46SRobert Mustacchi 
1338*4d9fdb46SRobert Mustacchi     memset(&signaturedata,0,sizeof(signaturedata));
1339*4d9fdb46SRobert Mustacchi     signaturedata = cu_context->cc_signature;
1340*4d9fdb46SRobert Mustacchi 
1341*4d9fdb46SRobert Mustacchi     /*  Loads and initializes the dwarf .debug_cu_index
1342*4d9fdb46SRobert Mustacchi         and .debug_tu_index split dwarf package
1343*4d9fdb46SRobert Mustacchi         file sections */
1344*4d9fdb46SRobert Mustacchi     res = fill_in_dwp_offsets_if_present(dbg,
1345*4d9fdb46SRobert Mustacchi         cu_context,
1346*4d9fdb46SRobert Mustacchi         &signaturedata,
1347*4d9fdb46SRobert Mustacchi         offset,
1348*4d9fdb46SRobert Mustacchi         error);
1349*4d9fdb46SRobert Mustacchi     if (res == DW_DLV_ERROR) {
1350*4d9fdb46SRobert Mustacchi         return res;
1351*4d9fdb46SRobert Mustacchi     }
1352*4d9fdb46SRobert Mustacchi     if (res != DW_DLV_OK) {
1353*4d9fdb46SRobert Mustacchi         return res;
135449d3bc91SRichard Lowe     }
135549d3bc91SRichard Lowe 
1356*4d9fdb46SRobert Mustacchi     if (cu_context->cc_dwp_offsets.pcu_type) {
1357*4d9fdb46SRobert Mustacchi         Dwarf_Unsigned absize = 0;
1358*4d9fdb46SRobert Mustacchi         Dwarf_Unsigned aboff = 0;
135949d3bc91SRichard Lowe 
1360*4d9fdb46SRobert Mustacchi         aboff = _dwarf_get_dwp_extra_offset(
1361*4d9fdb46SRobert Mustacchi             &cu_context->cc_dwp_offsets,
1362*4d9fdb46SRobert Mustacchi             DW_SECT_ABBREV, &absize);
1363*4d9fdb46SRobert Mustacchi         cu_context->cc_abbrev_offset +=  aboff;
1364*4d9fdb46SRobert Mustacchi     }
1365*4d9fdb46SRobert Mustacchi 
1366*4d9fdb46SRobert Mustacchi     if (cu_context->cc_abbrev_offset >=
1367*4d9fdb46SRobert Mustacchi         dbg->de_debug_abbrev.dss_size) {
1368*4d9fdb46SRobert Mustacchi         _dwarf_error(dbg, error, DW_DLE_ABBREV_OFFSET_ERROR);
1369*4d9fdb46SRobert Mustacchi         return DW_DLV_ERROR;
1370*4d9fdb46SRobert Mustacchi     }
1371*4d9fdb46SRobert Mustacchi     /*  Now we can read the CU die and determine
1372*4d9fdb46SRobert Mustacchi         the correct DW_UT_ type for DWARF4 and some
1373*4d9fdb46SRobert Mustacchi         offset base fields for DW4-fission and DW5 */
1374*4d9fdb46SRobert Mustacchi     if (version == DW_CU_VERSION4 || version == DW_CU_VERSION5) {
1375*4d9fdb46SRobert Mustacchi         res = finish_cu_context_via_cudie_inner(dbg,
1376*4d9fdb46SRobert Mustacchi             cu_context,
1377*4d9fdb46SRobert Mustacchi             error);
1378*4d9fdb46SRobert Mustacchi         if(res == DW_DLV_ERROR) {
1379*4d9fdb46SRobert Mustacchi             return res;
1380*4d9fdb46SRobert Mustacchi         }
1381*4d9fdb46SRobert Mustacchi         if(res != DW_DLV_OK) {
1382*4d9fdb46SRobert Mustacchi             return res;
1383*4d9fdb46SRobert Mustacchi         }
1384*4d9fdb46SRobert Mustacchi         if (version == DW_CU_VERSION4) {
1385*4d9fdb46SRobert Mustacchi             assign_correct_unit_type(cu_context);
1386*4d9fdb46SRobert Mustacchi         }
138749d3bc91SRichard Lowe     }
1388*4d9fdb46SRobert Mustacchi     return DW_DLV_OK;
138949d3bc91SRichard Lowe }
139049d3bc91SRichard Lowe /*
1391*4d9fdb46SRobert Mustacchi     CU_Contexts do not overlap.
1392*4d9fdb46SRobert Mustacchi     cu_context we see here is not in the list we
1393*4d9fdb46SRobert Mustacchi     are updating. See _dwarf_find_CU_Context()
139407dc1947SRichard Lowe 
1395*4d9fdb46SRobert Mustacchi     Invariant: cc_debug_offset in strictly
1396*4d9fdb46SRobert Mustacchi         ascending order in the list.
139749d3bc91SRichard Lowe */
1398*4d9fdb46SRobert Mustacchi static void
insert_into_cu_context_list(Dwarf_Debug_InfoTypes dis,Dwarf_CU_Context icu_context)1399*4d9fdb46SRobert Mustacchi insert_into_cu_context_list(Dwarf_Debug_InfoTypes dis,
1400*4d9fdb46SRobert Mustacchi     Dwarf_CU_Context icu_context)
1401*4d9fdb46SRobert Mustacchi {
1402*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned ioffset = icu_context->cc_debug_offset;
1403*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned eoffset = 0;
1404*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned hoffset = 0;
1405*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned coffset = 0;
1406*4d9fdb46SRobert Mustacchi     Dwarf_CU_Context next = 0;
1407*4d9fdb46SRobert Mustacchi     Dwarf_CU_Context past = 0;
1408*4d9fdb46SRobert Mustacchi     Dwarf_CU_Context cur = 0;
1409*4d9fdb46SRobert Mustacchi 
1410*4d9fdb46SRobert Mustacchi     /*  Add the context into the section context list.
1411*4d9fdb46SRobert Mustacchi         This is the one and only place where it is
1412*4d9fdb46SRobert Mustacchi         saved for re-use and eventual dealloc. */
1413*4d9fdb46SRobert Mustacchi     if (!dis->de_cu_context_list) {
1414*4d9fdb46SRobert Mustacchi         /*  First cu encountered. */
1415*4d9fdb46SRobert Mustacchi         dis->de_cu_context_list = icu_context;
1416*4d9fdb46SRobert Mustacchi         dis->de_cu_context_list_end = icu_context;
1417*4d9fdb46SRobert Mustacchi         return;
1418*4d9fdb46SRobert Mustacchi     }
1419*4d9fdb46SRobert Mustacchi     eoffset = dis->de_cu_context_list_end->cc_debug_offset;
1420*4d9fdb46SRobert Mustacchi     if (eoffset < ioffset) {
1421*4d9fdb46SRobert Mustacchi         /* Normal case, add at end. */
1422*4d9fdb46SRobert Mustacchi         dis->de_cu_context_list_end->cc_next = icu_context;
1423*4d9fdb46SRobert Mustacchi         dis->de_cu_context_list_end = icu_context;
1424*4d9fdb46SRobert Mustacchi         return;
1425*4d9fdb46SRobert Mustacchi     }
1426*4d9fdb46SRobert Mustacchi     hoffset = dis->de_cu_context_list->cc_debug_offset;
1427*4d9fdb46SRobert Mustacchi     if (hoffset > ioffset) {
1428*4d9fdb46SRobert Mustacchi         /* insert as new head. Unusual. */
1429*4d9fdb46SRobert Mustacchi         next =  dis->de_cu_context_list;
1430*4d9fdb46SRobert Mustacchi         dis->de_cu_context_list = icu_context;
1431*4d9fdb46SRobert Mustacchi         dis->de_cu_context_list->cc_next = next;
1432*4d9fdb46SRobert Mustacchi         /*  No need to touch de_cu_context_list_end */
1433*4d9fdb46SRobert Mustacchi         return;
1434*4d9fdb46SRobert Mustacchi     }
1435*4d9fdb46SRobert Mustacchi     cur = dis->de_cu_context_list;
1436*4d9fdb46SRobert Mustacchi     past = 0;
1437*4d9fdb46SRobert Mustacchi     /*  Insert in middle somewhere. Neither at
1438*4d9fdb46SRobert Mustacchi         start nor end.
1439*4d9fdb46SRobert Mustacchi         ASSERT: cur non-null
1440*4d9fdb46SRobert Mustacchi         ASSERT: past non-null */
1441*4d9fdb46SRobert Mustacchi     past = cur;
1442*4d9fdb46SRobert Mustacchi     cur = cur->cc_next;
1443*4d9fdb46SRobert Mustacchi     for ( ; cur ; cur = next) {
1444*4d9fdb46SRobert Mustacchi         next = cur->cc_next;
1445*4d9fdb46SRobert Mustacchi         coffset = cur->cc_debug_offset;
1446*4d9fdb46SRobert Mustacchi         if (coffset  >  ioffset) {
1447*4d9fdb46SRobert Mustacchi             /*  Insert before cur, using past.
1448*4d9fdb46SRobert Mustacchi                 ASSERT: past non-null  */
1449*4d9fdb46SRobert Mustacchi             past->cc_next = icu_context;
1450*4d9fdb46SRobert Mustacchi             icu_context->cc_next = cur;
1451*4d9fdb46SRobert Mustacchi             return;
1452*4d9fdb46SRobert Mustacchi         }
1453*4d9fdb46SRobert Mustacchi         past = cur;
1454*4d9fdb46SRobert Mustacchi     }
1455*4d9fdb46SRobert Mustacchi     /*  Impossible, for end, coffset (ie, eoffset) > ioffset  */
1456*4d9fdb46SRobert Mustacchi     /* NOTREACHED */
1457*4d9fdb46SRobert Mustacchi     return;
145807dc1947SRichard Lowe }
1459*4d9fdb46SRobert Mustacchi 
146007dc1947SRichard Lowe int
_dwarf_next_cu_header_internal(Dwarf_Debug dbg,Dwarf_Bool is_info,Dwarf_Unsigned * cu_header_length,Dwarf_Half * version_stamp,Dwarf_Unsigned * abbrev_offset,Dwarf_Half * address_size,Dwarf_Half * offset_size,Dwarf_Half * extension_size,Dwarf_Sig8 * signature_out,Dwarf_Bool * has_signature,Dwarf_Unsigned * typeoffset,Dwarf_Unsigned * next_cu_offset,Dwarf_Half * header_type,Dwarf_Error * error)1461*4d9fdb46SRobert Mustacchi _dwarf_next_cu_header_internal(Dwarf_Debug dbg,
1462*4d9fdb46SRobert Mustacchi     Dwarf_Bool is_info,
1463*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned * cu_header_length,
1464*4d9fdb46SRobert Mustacchi     Dwarf_Half * version_stamp,
1465*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned * abbrev_offset,
1466*4d9fdb46SRobert Mustacchi     Dwarf_Half * address_size,
1467*4d9fdb46SRobert Mustacchi     Dwarf_Half * offset_size,
1468*4d9fdb46SRobert Mustacchi     Dwarf_Half * extension_size,
1469*4d9fdb46SRobert Mustacchi     Dwarf_Sig8 * signature_out,
1470*4d9fdb46SRobert Mustacchi     Dwarf_Bool * has_signature,
1471*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned *typeoffset,
1472*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned * next_cu_offset,
1473*4d9fdb46SRobert Mustacchi 
1474*4d9fdb46SRobert Mustacchi     /*  header_type: DW_UT_compile, DW_UT_partial,
1475*4d9fdb46SRobert Mustacchi         DW_UT_type, returned through the pointer.
1476*4d9fdb46SRobert Mustacchi         A new item in DWARF5, synthesized for earlier DWARF
1477*4d9fdb46SRobert Mustacchi         CUs (& TUs). */
1478*4d9fdb46SRobert Mustacchi     Dwarf_Half * header_type,
1479*4d9fdb46SRobert Mustacchi     Dwarf_Error * error)
148049d3bc91SRichard Lowe {
148149d3bc91SRichard Lowe     /* Offset for current and new CU. */
148207dc1947SRichard Lowe     Dwarf_Unsigned new_offset = 0;
148349d3bc91SRichard Lowe 
148449d3bc91SRichard Lowe     /* CU Context for current CU. */
148507dc1947SRichard Lowe     Dwarf_CU_Context cu_context = 0;
1486*4d9fdb46SRobert Mustacchi     Dwarf_Debug_InfoTypes dis = 0;
1487*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned section_size =  0;
1488*4d9fdb46SRobert Mustacchi     int res = 0;
148949d3bc91SRichard Lowe 
149049d3bc91SRichard Lowe     /* ***** BEGIN CODE ***** */
149149d3bc91SRichard Lowe 
149249d3bc91SRichard Lowe     if (dbg == NULL) {
149307dc1947SRichard Lowe         _dwarf_error(NULL, error, DW_DLE_DBG_NULL);
149407dc1947SRichard Lowe         return (DW_DLV_ERROR);
149549d3bc91SRichard Lowe     }
1496*4d9fdb46SRobert Mustacchi     dis = is_info? &dbg->de_info_reading: &dbg->de_types_reading;
1497*4d9fdb46SRobert Mustacchi     /*  Get offset into .debug_info of next CU.
1498*4d9fdb46SRobert Mustacchi         If dbg has no context,
1499*4d9fdb46SRobert Mustacchi         this has to be the first one.  */
1500*4d9fdb46SRobert Mustacchi     if (!dis->de_cu_context) {
1501*4d9fdb46SRobert Mustacchi         Dwarf_Small *dataptr = is_info? dbg->de_debug_info.dss_data:
1502*4d9fdb46SRobert Mustacchi             dbg->de_debug_types.dss_data;
150307dc1947SRichard Lowe         new_offset = 0;
1504*4d9fdb46SRobert Mustacchi         if (!dataptr) {
1505*4d9fdb46SRobert Mustacchi             Dwarf_Error err2= 0;
1506*4d9fdb46SRobert Mustacchi             int resd = is_info?_dwarf_load_debug_info(dbg, &err2):
1507*4d9fdb46SRobert Mustacchi                 _dwarf_load_debug_types(dbg,&err2);
1508*4d9fdb46SRobert Mustacchi 
1509*4d9fdb46SRobert Mustacchi             if (resd != DW_DLV_OK) {
1510*4d9fdb46SRobert Mustacchi                 if (reloc_incomplete(resd,err2)) {
1511*4d9fdb46SRobert Mustacchi                     /*  We will assume all is ok, though it is not.
1512*4d9fdb46SRobert Mustacchi                         Relocation errors need not be fatal. */
1513*4d9fdb46SRobert Mustacchi                     char msg_buf[300];
1514*4d9fdb46SRobert Mustacchi                     char *dwerrmsg = 0;
1515*4d9fdb46SRobert Mustacchi                     char *msgprefix =
1516*4d9fdb46SRobert Mustacchi                         "Relocations did not complete successfully, "
1517*4d9fdb46SRobert Mustacchi                         "but we are " " ignoring error: ";
1518*4d9fdb46SRobert Mustacchi                     size_t totallen = 0;
1519*4d9fdb46SRobert Mustacchi                     size_t prefixlen = 0;
1520*4d9fdb46SRobert Mustacchi 
1521*4d9fdb46SRobert Mustacchi                     dwerrmsg = dwarf_errmsg(err2);
1522*4d9fdb46SRobert Mustacchi                     prefixlen = strlen(msgprefix);
1523*4d9fdb46SRobert Mustacchi                     totallen = prefixlen + strlen(dwerrmsg);
1524*4d9fdb46SRobert Mustacchi                     if( totallen >= sizeof(msg_buf)) {
1525*4d9fdb46SRobert Mustacchi                         /*  Impossible unless something corrupted.
1526*4d9fdb46SRobert Mustacchi                             Provide a shorter dwerrmsg*/
1527*4d9fdb46SRobert Mustacchi                         strcpy(msg_buf,"Error:corrupted dwarf message table!");
1528*4d9fdb46SRobert Mustacchi                     } else {
1529*4d9fdb46SRobert Mustacchi                         strcpy(msg_buf,msgprefix);
1530*4d9fdb46SRobert Mustacchi                         strcpy(msg_buf+prefixlen,dwerrmsg);
1531*4d9fdb46SRobert Mustacchi                     }
1532*4d9fdb46SRobert Mustacchi                     dwarf_insert_harmless_error(dbg,msg_buf);
1533*4d9fdb46SRobert Mustacchi                     /*  Fall thru to use the newly loaded section.
1534*4d9fdb46SRobert Mustacchi                         even though it might not be adequately
1535*4d9fdb46SRobert Mustacchi                         relocated. */
1536*4d9fdb46SRobert Mustacchi                     if (resd == DW_DLV_ERROR) {
1537*4d9fdb46SRobert Mustacchi                         dwarf_dealloc(dbg,err2,DW_DLA_ERROR);
1538*4d9fdb46SRobert Mustacchi                         err2 = 0;
1539*4d9fdb46SRobert Mustacchi                     }
1540*4d9fdb46SRobert Mustacchi                 } else {
1541*4d9fdb46SRobert Mustacchi                     if (error) {
1542*4d9fdb46SRobert Mustacchi                         *error = err2;
1543*4d9fdb46SRobert Mustacchi                         err2 = 0;
1544*4d9fdb46SRobert Mustacchi                     }
1545*4d9fdb46SRobert Mustacchi                     /*  There is nothing here, or
1546*4d9fdb46SRobert Mustacchi                         what is here is damaged. */
1547*4d9fdb46SRobert Mustacchi                     return resd;
1548*4d9fdb46SRobert Mustacchi                 }
154949d3bc91SRichard Lowe 
155007dc1947SRichard Lowe             }
155107dc1947SRichard Lowe         }
1552*4d9fdb46SRobert Mustacchi         /*  We are leaving new_offset zero. We are at the
1553*4d9fdb46SRobert Mustacchi             start of a section. */
155449d3bc91SRichard Lowe     } else {
1555*4d9fdb46SRobert Mustacchi         /* We already have is_info  cu_context. */
1556*4d9fdb46SRobert Mustacchi 
1557*4d9fdb46SRobert Mustacchi         new_offset = dis->de_cu_context->cc_debug_offset +
1558*4d9fdb46SRobert Mustacchi             dis->de_cu_context->cc_length +
1559*4d9fdb46SRobert Mustacchi             dis->de_cu_context->cc_length_size +
1560*4d9fdb46SRobert Mustacchi             dis->de_cu_context->cc_extension_size;
1561*4d9fdb46SRobert Mustacchi     }
1562*4d9fdb46SRobert Mustacchi 
1563*4d9fdb46SRobert Mustacchi     /*  Check that there is room in .debug_info beyond
1564*4d9fdb46SRobert Mustacchi         the new offset for at least a new cu header.
1565*4d9fdb46SRobert Mustacchi         If not, return -1 (DW_DLV_NO_ENTRY) to indicate end
1566*4d9fdb46SRobert Mustacchi         of debug_info section, and reset
1567*4d9fdb46SRobert Mustacchi         de_cu_debug_info_offset to
1568*4d9fdb46SRobert Mustacchi         enable looping back through the cu's. */
1569*4d9fdb46SRobert Mustacchi     section_size = is_info? dbg->de_debug_info.dss_size:
1570*4d9fdb46SRobert Mustacchi         dbg->de_debug_types.dss_size;
1571*4d9fdb46SRobert Mustacchi     if ((new_offset + _dwarf_length_of_cu_header_simple(dbg,is_info)) >=
1572*4d9fdb46SRobert Mustacchi         section_size) {
1573*4d9fdb46SRobert Mustacchi         dis->de_cu_context = NULL;
1574*4d9fdb46SRobert Mustacchi         return DW_DLV_NO_ENTRY;
157549d3bc91SRichard Lowe     }
157649d3bc91SRichard Lowe 
157749d3bc91SRichard Lowe     /* Check if this CU has been read before. */
1578*4d9fdb46SRobert Mustacchi     cu_context = _dwarf_find_CU_Context(dbg, new_offset,is_info);
157949d3bc91SRichard Lowe 
158049d3bc91SRichard Lowe     /* If not, make CU Context for it. */
1581*4d9fdb46SRobert Mustacchi     if (!cu_context) {
1582*4d9fdb46SRobert Mustacchi         res = _dwarf_make_CU_Context(dbg, new_offset,is_info,
1583*4d9fdb46SRobert Mustacchi             &cu_context,error);
1584*4d9fdb46SRobert Mustacchi         if (res == DW_DLV_ERROR) {
1585*4d9fdb46SRobert Mustacchi             return res;
1586*4d9fdb46SRobert Mustacchi         }
1587*4d9fdb46SRobert Mustacchi         if (res == DW_DLV_NO_ENTRY) {
1588*4d9fdb46SRobert Mustacchi             return res;
1589*4d9fdb46SRobert Mustacchi         }
1590*4d9fdb46SRobert Mustacchi         res = finish_up_cu_context_from_cudie(dbg,new_offset,
1591*4d9fdb46SRobert Mustacchi             cu_context,error);
1592*4d9fdb46SRobert Mustacchi         if (res == DW_DLV_ERROR) {
1593*4d9fdb46SRobert Mustacchi             local_dealloc_cu_context(dbg,cu_context);
1594*4d9fdb46SRobert Mustacchi             return res;
1595*4d9fdb46SRobert Mustacchi         }
1596*4d9fdb46SRobert Mustacchi         if (res == DW_DLV_NO_ENTRY) {
1597*4d9fdb46SRobert Mustacchi             local_dealloc_cu_context(dbg,cu_context);
1598*4d9fdb46SRobert Mustacchi             return res;
159907dc1947SRichard Lowe         }
160049d3bc91SRichard Lowe 
1601*4d9fdb46SRobert Mustacchi         dis->de_cu_context = cu_context;
1602*4d9fdb46SRobert Mustacchi         insert_into_cu_context_list(dis,cu_context);
1603*4d9fdb46SRobert Mustacchi     } else {
1604*4d9fdb46SRobert Mustacchi         dis->de_cu_context = cu_context;
1605*4d9fdb46SRobert Mustacchi     }
160649d3bc91SRichard Lowe 
1607*4d9fdb46SRobert Mustacchi     if (cu_header_length) {
160807dc1947SRichard Lowe         *cu_header_length = cu_context->cc_length;
1609*4d9fdb46SRobert Mustacchi     }
161049d3bc91SRichard Lowe 
1611*4d9fdb46SRobert Mustacchi     if (version_stamp) {
161207dc1947SRichard Lowe         *version_stamp = cu_context->cc_version_stamp;
1613*4d9fdb46SRobert Mustacchi     }
1614*4d9fdb46SRobert Mustacchi     if (abbrev_offset) {
161507dc1947SRichard Lowe         *abbrev_offset = cu_context->cc_abbrev_offset;
1616*4d9fdb46SRobert Mustacchi     }
1617*4d9fdb46SRobert Mustacchi     if (address_size) {
161807dc1947SRichard Lowe         *address_size = cu_context->cc_address_size;
1619*4d9fdb46SRobert Mustacchi     }
1620*4d9fdb46SRobert Mustacchi     if (offset_size) {
162107dc1947SRichard Lowe         *offset_size = cu_context->cc_length_size;
1622*4d9fdb46SRobert Mustacchi     }
1623*4d9fdb46SRobert Mustacchi     if (extension_size) {
162407dc1947SRichard Lowe         *extension_size = cu_context->cc_extension_size;
1625*4d9fdb46SRobert Mustacchi     }
1626*4d9fdb46SRobert Mustacchi     if (header_type) {
1627*4d9fdb46SRobert Mustacchi         *header_type = cu_context->cc_unit_type;
1628*4d9fdb46SRobert Mustacchi     }
1629*4d9fdb46SRobert Mustacchi     if (typeoffset) {
1630*4d9fdb46SRobert Mustacchi         *typeoffset = cu_context->cc_signature_offset;
1631*4d9fdb46SRobert Mustacchi     }
1632*4d9fdb46SRobert Mustacchi     if (signature_out) {
1633*4d9fdb46SRobert Mustacchi         *signature_out = cu_context->cc_signature;
1634*4d9fdb46SRobert Mustacchi     }
1635*4d9fdb46SRobert Mustacchi     if (has_signature) {
1636*4d9fdb46SRobert Mustacchi         *has_signature = cu_context->cc_signature_present;
1637*4d9fdb46SRobert Mustacchi     }
1638*4d9fdb46SRobert Mustacchi     /*  Determine the offset of the next CU. */
163949d3bc91SRichard Lowe     new_offset = new_offset + cu_context->cc_length +
164007dc1947SRichard Lowe         cu_context->cc_length_size + cu_context->cc_extension_size;
1641*4d9fdb46SRobert Mustacchi     /*  Allowing null argument starting 22 April 2019. */
1642*4d9fdb46SRobert Mustacchi     if (next_cu_offset) {
1643*4d9fdb46SRobert Mustacchi         *next_cu_offset = new_offset;
1644*4d9fdb46SRobert Mustacchi     }
1645*4d9fdb46SRobert Mustacchi     return DW_DLV_OK;
1646*4d9fdb46SRobert Mustacchi }
1647*4d9fdb46SRobert Mustacchi 
1648*4d9fdb46SRobert Mustacchi /*  This involves data in a split dwarf or package file.
1649*4d9fdb46SRobert Mustacchi 
1650*4d9fdb46SRobert Mustacchi     Given hash signature, return the CU_die of the applicable CU.
1651*4d9fdb46SRobert Mustacchi     The hash is assumed to be from 'somewhere'.
1652*4d9fdb46SRobert Mustacchi     For DWARF 4:
1653*4d9fdb46SRobert Mustacchi         From a skeleton DIE DW_AT_GNU_dwo_id  ("cu" case) or
1654*4d9fdb46SRobert Mustacchi         From a DW_FORM_ref_sig8 ("tu" case).
1655*4d9fdb46SRobert Mustacchi     For DWARF5:
1656*4d9fdb46SRobert Mustacchi         From  dwo_id in a skeleton CU header (DW_UT_skeleton).
1657*4d9fdb46SRobert Mustacchi         From a DW_FORM_ref_sig8 ("tu" case).
1658*4d9fdb46SRobert Mustacchi 
1659*4d9fdb46SRobert Mustacchi 
1660*4d9fdb46SRobert Mustacchi     If "tu" request,  the CU_die
1661*4d9fdb46SRobert Mustacchi     of of the type unit.
1662*4d9fdb46SRobert Mustacchi     Works on either a dwp package file or a dwo object.
1663*4d9fdb46SRobert Mustacchi 
1664*4d9fdb46SRobert Mustacchi     If "cu" request,  the CU_die
1665*4d9fdb46SRobert Mustacchi     of the compilation unit.
1666*4d9fdb46SRobert Mustacchi     Works on either a dwp package file or a dwo object.
1667*4d9fdb46SRobert Mustacchi 
1668*4d9fdb46SRobert Mustacchi     If the hash passed is not present, returns DW_DLV_NO_ENTRY
1669*4d9fdb46SRobert Mustacchi     (but read the next two paragraphs for more detail).
1670*4d9fdb46SRobert Mustacchi 
1671*4d9fdb46SRobert Mustacchi     If a dwp package file with the hash signature
1672*4d9fdb46SRobert Mustacchi     is present in the applicable index but no matching
1673*4d9fdb46SRobert Mustacchi     compilation unit can be found, it returns DW_DLV_ERROR.
1674*4d9fdb46SRobert Mustacchi 
1675*4d9fdb46SRobert Mustacchi     If a .dwo object there is no index and we look at the
1676*4d9fdb46SRobert Mustacchi     compilation units (possibly all of them). If not present
1677*4d9fdb46SRobert Mustacchi     then we return DW_DLV_NO_ENTRY.
1678*4d9fdb46SRobert Mustacchi 
1679*4d9fdb46SRobert Mustacchi     The returned_die is a CU DIE if the sig_type is "cu".
1680*4d9fdb46SRobert Mustacchi     The returned_die is a type DIE if the sig_type is "tu".
1681*4d9fdb46SRobert Mustacchi     Perhaps both should return CU die.
1682*4d9fdb46SRobert Mustacchi 
1683*4d9fdb46SRobert Mustacchi     New 27 April, 2015
1684*4d9fdb46SRobert Mustacchi */
1685*4d9fdb46SRobert Mustacchi int
dwarf_die_from_hash_signature(Dwarf_Debug dbg,Dwarf_Sig8 * hash_sig,const char * sig_type,Dwarf_Die * returned_die,Dwarf_Error * error)1686*4d9fdb46SRobert Mustacchi dwarf_die_from_hash_signature(Dwarf_Debug dbg,
1687*4d9fdb46SRobert Mustacchi     Dwarf_Sig8 *     hash_sig,
1688*4d9fdb46SRobert Mustacchi     const char *     sig_type  /* "tu" or "cu"*/,
1689*4d9fdb46SRobert Mustacchi     Dwarf_Die  *     returned_die,
1690*4d9fdb46SRobert Mustacchi     Dwarf_Error*     error)
1691*4d9fdb46SRobert Mustacchi {
1692*4d9fdb46SRobert Mustacchi     Dwarf_Bool is_type_unit = FALSE;
1693*4d9fdb46SRobert Mustacchi     int sres = 0;
1694*4d9fdb46SRobert Mustacchi 
1695*4d9fdb46SRobert Mustacchi     sres = _dwarf_load_debug_info(dbg,error);
1696*4d9fdb46SRobert Mustacchi     if (sres == DW_DLV_ERROR) {
1697*4d9fdb46SRobert Mustacchi         return sres;
1698*4d9fdb46SRobert Mustacchi     }
1699*4d9fdb46SRobert Mustacchi     sres = _dwarf_load_debug_types(dbg,error);
1700*4d9fdb46SRobert Mustacchi     if (sres == DW_DLV_ERROR) {
1701*4d9fdb46SRobert Mustacchi         return sres;
1702*4d9fdb46SRobert Mustacchi     }
1703*4d9fdb46SRobert Mustacchi 
1704*4d9fdb46SRobert Mustacchi     if (!strcmp(sig_type,"tu")) {
1705*4d9fdb46SRobert Mustacchi         is_type_unit = TRUE;
1706*4d9fdb46SRobert Mustacchi     } else if (!strcmp(sig_type,"cu")) {
1707*4d9fdb46SRobert Mustacchi         is_type_unit = FALSE;
1708*4d9fdb46SRobert Mustacchi     } else {
1709*4d9fdb46SRobert Mustacchi         _dwarf_error(dbg,error,DW_DLE_SIG_TYPE_WRONG_STRING);
1710*4d9fdb46SRobert Mustacchi         return DW_DLV_ERROR;
1711*4d9fdb46SRobert Mustacchi     }
1712*4d9fdb46SRobert Mustacchi 
1713*4d9fdb46SRobert Mustacchi     if (_dwarf_file_has_debug_fission_index(dbg)) {
1714*4d9fdb46SRobert Mustacchi         /* This is a dwp package file. */
1715*4d9fdb46SRobert Mustacchi         int fisres = 0;
1716*4d9fdb46SRobert Mustacchi         Dwarf_Bool is_info2 = 0;
1717*4d9fdb46SRobert Mustacchi         Dwarf_Off cu_header_off = 0;
1718*4d9fdb46SRobert Mustacchi         Dwarf_Off cu_size = 0;
1719*4d9fdb46SRobert Mustacchi         Dwarf_Off cu_die_off = 0;
1720*4d9fdb46SRobert Mustacchi         Dwarf_Off typeoffset = 0;
1721*4d9fdb46SRobert Mustacchi         Dwarf_Die cudie = 0;
1722*4d9fdb46SRobert Mustacchi         Dwarf_Die typedie = 0;
1723*4d9fdb46SRobert Mustacchi         Dwarf_CU_Context context = 0;
1724*4d9fdb46SRobert Mustacchi         Dwarf_Debug_Fission_Per_CU fiss;
1725*4d9fdb46SRobert Mustacchi 
1726*4d9fdb46SRobert Mustacchi         memset(&fiss,0,sizeof(fiss));
1727*4d9fdb46SRobert Mustacchi         fisres = dwarf_get_debugfission_for_key(dbg,hash_sig,
1728*4d9fdb46SRobert Mustacchi             sig_type,&fiss,error);
1729*4d9fdb46SRobert Mustacchi         if (fisres != DW_DLV_OK) {
1730*4d9fdb46SRobert Mustacchi             return fisres;
1731*4d9fdb46SRobert Mustacchi         }
1732*4d9fdb46SRobert Mustacchi         /* Found it */
1733*4d9fdb46SRobert Mustacchi         if(is_type_unit) {
1734*4d9fdb46SRobert Mustacchi             /*  DW4 has debug_types, so look in .debug_types
1735*4d9fdb46SRobert Mustacchi                 Else look in .debug_info.  */
1736*4d9fdb46SRobert Mustacchi             is_info2 = dbg->de_debug_types.dss_size?FALSE:TRUE;
1737*4d9fdb46SRobert Mustacchi         } else {
1738*4d9fdb46SRobert Mustacchi             is_info2 = TRUE;
1739*4d9fdb46SRobert Mustacchi         }
1740*4d9fdb46SRobert Mustacchi 
1741*4d9fdb46SRobert Mustacchi         cu_header_off = _dwarf_get_dwp_extra_offset(&fiss,
1742*4d9fdb46SRobert Mustacchi             is_info2?DW_SECT_INFO:DW_SECT_TYPES,
1743*4d9fdb46SRobert Mustacchi             &cu_size);
1744*4d9fdb46SRobert Mustacchi 
1745*4d9fdb46SRobert Mustacchi         fisres = dwarf_get_cu_die_offset_given_cu_header_offset_b(
1746*4d9fdb46SRobert Mustacchi             dbg,cu_header_off,
1747*4d9fdb46SRobert Mustacchi             is_info2,
1748*4d9fdb46SRobert Mustacchi             &cu_die_off,error);
1749*4d9fdb46SRobert Mustacchi         if (fisres != DW_DLV_OK) {
1750*4d9fdb46SRobert Mustacchi             return fisres;
1751*4d9fdb46SRobert Mustacchi         }
1752*4d9fdb46SRobert Mustacchi         fisres = dwarf_offdie_b(dbg,cu_die_off,is_info2,
1753*4d9fdb46SRobert Mustacchi             &cudie,error);
1754*4d9fdb46SRobert Mustacchi         if (fisres != DW_DLV_OK) {
1755*4d9fdb46SRobert Mustacchi             return fisres;
1756*4d9fdb46SRobert Mustacchi         }
1757*4d9fdb46SRobert Mustacchi         if (!is_type_unit) {
1758*4d9fdb46SRobert Mustacchi             *returned_die = cudie;
1759*4d9fdb46SRobert Mustacchi             return DW_DLV_OK;
1760*4d9fdb46SRobert Mustacchi         }
1761*4d9fdb46SRobert Mustacchi         context = cudie->di_cu_context;
1762*4d9fdb46SRobert Mustacchi         typeoffset = context->cc_signature_offset;
1763*4d9fdb46SRobert Mustacchi         typeoffset += cu_header_off;
1764*4d9fdb46SRobert Mustacchi         fisres = dwarf_offdie_b(dbg,typeoffset,is_info2,
1765*4d9fdb46SRobert Mustacchi             &typedie,error);
1766*4d9fdb46SRobert Mustacchi         if (fisres != DW_DLV_OK) {
1767*4d9fdb46SRobert Mustacchi             dwarf_dealloc(dbg,cudie,DW_DLA_DIE);
1768*4d9fdb46SRobert Mustacchi             return fisres;
1769*4d9fdb46SRobert Mustacchi         }
1770*4d9fdb46SRobert Mustacchi         *returned_die = typedie;
1771*4d9fdb46SRobert Mustacchi         dwarf_dealloc(dbg,cudie,DW_DLA_DIE);
1772*4d9fdb46SRobert Mustacchi         return DW_DLV_OK;
1773*4d9fdb46SRobert Mustacchi     }
1774*4d9fdb46SRobert Mustacchi     /*  Look thru all the CUs, there is no DWP tu/cu index.
1775*4d9fdb46SRobert Mustacchi         There will be COMDAT sections for  the type TUs
1776*4d9fdb46SRobert Mustacchi             (DW_UT_type).
1777*4d9fdb46SRobert Mustacchi         A single non-comdat for the DW_UT_compile. */
1778*4d9fdb46SRobert Mustacchi     /*  FIXME: DW_DLE_DEBUG_FISSION_INCOMPLETE  */
1779*4d9fdb46SRobert Mustacchi     _dwarf_error(dbg,error,DW_DLE_DEBUG_FISSION_INCOMPLETE);
1780*4d9fdb46SRobert Mustacchi     return DW_DLV_ERROR;
1781*4d9fdb46SRobert Mustacchi }
1782*4d9fdb46SRobert Mustacchi 
1783*4d9fdb46SRobert Mustacchi static int
dwarf_ptr_CU_offset(Dwarf_CU_Context cu_context,Dwarf_Byte_Ptr di_ptr,Dwarf_Bool is_info,Dwarf_Off * cu_off)1784*4d9fdb46SRobert Mustacchi dwarf_ptr_CU_offset(Dwarf_CU_Context cu_context,
1785*4d9fdb46SRobert Mustacchi     Dwarf_Byte_Ptr di_ptr,
1786*4d9fdb46SRobert Mustacchi     Dwarf_Bool is_info,
1787*4d9fdb46SRobert Mustacchi     Dwarf_Off * cu_off)
1788*4d9fdb46SRobert Mustacchi {
1789*4d9fdb46SRobert Mustacchi     Dwarf_Debug dbg = cu_context->cc_dbg;
1790*4d9fdb46SRobert Mustacchi     Dwarf_Small *dataptr = is_info? dbg->de_debug_info.dss_data:
1791*4d9fdb46SRobert Mustacchi         dbg->de_debug_types.dss_data;
1792*4d9fdb46SRobert Mustacchi     *cu_off = (di_ptr - dataptr);
1793*4d9fdb46SRobert Mustacchi     return DW_DLV_OK;
1794*4d9fdb46SRobert Mustacchi }
1795*4d9fdb46SRobert Mustacchi #if 0 /* FOR DEBUGGING */
1796*4d9fdb46SRobert Mustacchi /* Just for debug purposes */
1797*4d9fdb46SRobert Mustacchi void print_sib_offset(Dwarf_Die sibling)
1798*4d9fdb46SRobert Mustacchi {
1799*4d9fdb46SRobert Mustacchi     Dwarf_Off sib_off;
1800*4d9fdb46SRobert Mustacchi     Dwarf_Error error;
1801*4d9fdb46SRobert Mustacchi     dwarf_dieoffset(sibling,&sib_off,&error);
1802*4d9fdb46SRobert Mustacchi     fprintf(stderr," SIB OFF = 0x%" DW_PR_XZEROS DW_PR_DUx,sib_off);
1803*4d9fdb46SRobert Mustacchi }
1804*4d9fdb46SRobert Mustacchi void print_ptr_offset(Dwarf_CU_Context cu_context,Dwarf_Byte_Ptr di_ptr)
1805*4d9fdb46SRobert Mustacchi {
1806*4d9fdb46SRobert Mustacchi     Dwarf_Off ptr_off;
1807*4d9fdb46SRobert Mustacchi     dwarf_ptr_CU_offset(cu_context,di_ptr,&ptr_off);
1808*4d9fdb46SRobert Mustacchi     fprintf(stderr," PTR OFF = 0x%" DW_PR_XZEROS DW_PR_DUx,ptr_off);
180949d3bc91SRichard Lowe }
1810*4d9fdb46SRobert Mustacchi #endif
1811*4d9fdb46SRobert Mustacchi 
1812*4d9fdb46SRobert Mustacchi 
1813*4d9fdb46SRobert Mustacchi /*  Validate the sibling DIE. This only makes sense to call
1814*4d9fdb46SRobert Mustacchi     if the sibling's DIEs have been travsersed and
1815*4d9fdb46SRobert Mustacchi     dwarf_child() called on each,
1816*4d9fdb46SRobert Mustacchi     so that the last DIE dwarf_child saw was the last.
1817*4d9fdb46SRobert Mustacchi     Essentially ensuring that (after such traversal) that we
1818*4d9fdb46SRobert Mustacchi     are in the same place a sibling attribute would identify.
1819*4d9fdb46SRobert Mustacchi     In case we return DW_DLV_ERROR, the global offset of the last
1820*4d9fdb46SRobert Mustacchi     DIE traversed by dwarf_child is returned through *offset
1821*4d9fdb46SRobert Mustacchi 
1822*4d9fdb46SRobert Mustacchi     It is essentially guaranteed that  dbg->de_last_die
1823*4d9fdb46SRobert Mustacchi     is a stale DIE pointer of a deallocated DIE when we get here.
1824*4d9fdb46SRobert Mustacchi     It must not be used as a DIE pointer here,
1825*4d9fdb46SRobert Mustacchi     just as a sort of anonymous pointer that we just check against
1826*4d9fdb46SRobert Mustacchi     NULL.
1827*4d9fdb46SRobert Mustacchi 
1828*4d9fdb46SRobert Mustacchi     There is a (subtle?) dependence on the fact that when we call this
1829*4d9fdb46SRobert Mustacchi     the last dwarf_child() call would have been for this sibling.
1830*4d9fdb46SRobert Mustacchi     Meaning that this works in a depth-first traversal even though there
1831*4d9fdb46SRobert Mustacchi     is no stack of 'de_last_die' values.
1832*4d9fdb46SRobert Mustacchi 
1833*4d9fdb46SRobert Mustacchi     The check for dbg->de_last_die just ensures sanity.
1834*4d9fdb46SRobert Mustacchi 
1835*4d9fdb46SRobert Mustacchi     If one is switching between normal debug_frame and eh_frame
1836*4d9fdb46SRobert Mustacchi     (traversing them in tandem, let us say) in a single
1837*4d9fdb46SRobert Mustacchi     Dwarf_Debug this validator makes no sense.
1838*4d9fdb46SRobert Mustacchi     It works if one processes a .debug_frame (entirely) and
1839*4d9fdb46SRobert Mustacchi     then an eh_frame (or vice versa) though.
1840*4d9fdb46SRobert Mustacchi     Use caution.
1841*4d9fdb46SRobert Mustacchi */
1842*4d9fdb46SRobert Mustacchi int
dwarf_validate_die_sibling(Dwarf_Die sibling,Dwarf_Off * offset)1843*4d9fdb46SRobert Mustacchi dwarf_validate_die_sibling(Dwarf_Die sibling,Dwarf_Off *offset)
1844*4d9fdb46SRobert Mustacchi {
1845*4d9fdb46SRobert Mustacchi     Dwarf_Debug dbg = 0;
1846*4d9fdb46SRobert Mustacchi     Dwarf_Error *error = 0;
1847*4d9fdb46SRobert Mustacchi     Dwarf_Debug_InfoTypes dis = 0;
1848*4d9fdb46SRobert Mustacchi     CHECK_DIE(sibling, DW_DLV_ERROR);
1849*4d9fdb46SRobert Mustacchi     dbg = sibling->di_cu_context->cc_dbg;
1850*4d9fdb46SRobert Mustacchi 
1851*4d9fdb46SRobert Mustacchi     dis = sibling->di_is_info? &dbg->de_info_reading: &dbg->de_types_reading;
185249d3bc91SRichard Lowe 
1853*4d9fdb46SRobert Mustacchi     *offset = 0;
1854*4d9fdb46SRobert Mustacchi     if (dis->de_last_die && dis->de_last_di_ptr) {
1855*4d9fdb46SRobert Mustacchi         if (sibling->di_debug_ptr == dis->de_last_di_ptr) {
1856*4d9fdb46SRobert Mustacchi             return (DW_DLV_OK);
1857*4d9fdb46SRobert Mustacchi         }
1858*4d9fdb46SRobert Mustacchi     }
1859*4d9fdb46SRobert Mustacchi     /* Calculate global offset used for error reporting */
1860*4d9fdb46SRobert Mustacchi     dwarf_ptr_CU_offset(sibling->di_cu_context,
1861*4d9fdb46SRobert Mustacchi         dis->de_last_di_ptr,sibling->di_is_info,offset);
1862*4d9fdb46SRobert Mustacchi     return (DW_DLV_ERROR);
1863*4d9fdb46SRobert Mustacchi }
186449d3bc91SRichard Lowe 
1865*4d9fdb46SRobert Mustacchi /*  This function does two slightly different things
186649d3bc91SRichard Lowe     depending on the input flag want_AT_sibling.  If
186749d3bc91SRichard Lowe     this flag is true, it checks if the input die has
186849d3bc91SRichard Lowe     a DW_AT_sibling attribute.  If it does it returns
186949d3bc91SRichard Lowe     a pointer to the start of the sibling die in the
1870*4d9fdb46SRobert Mustacchi     .debug_info section.  Otherwise it behaves the
187149d3bc91SRichard Lowe     same as the want_AT_sibling false case.
187249d3bc91SRichard Lowe 
187349d3bc91SRichard Lowe     If the want_AT_sibling flag is false, it returns
1874*4d9fdb46SRobert Mustacchi     a pointer to the immediately adjacent die in the
187549d3bc91SRichard Lowe     .debug_info section.
187649d3bc91SRichard Lowe 
1877*4d9fdb46SRobert Mustacchi     Die_info_end points to the end of the .debug_info
1878*4d9fdb46SRobert Mustacchi     portion for the cu the die belongs to.  It is used
1879*4d9fdb46SRobert Mustacchi     to check that the search for the next die does not
1880*4d9fdb46SRobert Mustacchi     cross the end of the current cu.  Cu_info_start points
1881*4d9fdb46SRobert Mustacchi     to the start of the .debug_info portion for the
1882*4d9fdb46SRobert Mustacchi     current cu, and is used to add to the offset for
1883*4d9fdb46SRobert Mustacchi     DW_AT_sibling attributes.  Finally, has_die_child
1884*4d9fdb46SRobert Mustacchi     is a pointer to a Dwarf_Bool that is set true if
1885*4d9fdb46SRobert Mustacchi     the present die has children, false otherwise.
1886*4d9fdb46SRobert Mustacchi     However, in case want_AT_child is true and the die
1887*4d9fdb46SRobert Mustacchi     has a DW_AT_sibling attribute *has_die_child is set
188849d3bc91SRichard Lowe     false to indicate that the children are being skipped.
188907dc1947SRichard Lowe 
1890*4d9fdb46SRobert Mustacchi     die_info_end  points to the last byte+1 of the cu.  */
1891*4d9fdb46SRobert Mustacchi static int
_dwarf_next_die_info_ptr(Dwarf_Byte_Ptr die_info_ptr,Dwarf_CU_Context cu_context,Dwarf_Byte_Ptr die_info_end,Dwarf_Byte_Ptr cu_info_start,Dwarf_Bool want_AT_sibling,Dwarf_Bool * has_die_child,Dwarf_Byte_Ptr * next_die_ptr_out,Dwarf_Error * error)189249d3bc91SRichard Lowe _dwarf_next_die_info_ptr(Dwarf_Byte_Ptr die_info_ptr,
1893*4d9fdb46SRobert Mustacchi     Dwarf_CU_Context cu_context,
1894*4d9fdb46SRobert Mustacchi     Dwarf_Byte_Ptr die_info_end,
1895*4d9fdb46SRobert Mustacchi     Dwarf_Byte_Ptr cu_info_start,
1896*4d9fdb46SRobert Mustacchi     Dwarf_Bool want_AT_sibling,
1897*4d9fdb46SRobert Mustacchi     Dwarf_Bool * has_die_child,
1898*4d9fdb46SRobert Mustacchi     Dwarf_Byte_Ptr *next_die_ptr_out,
1899*4d9fdb46SRobert Mustacchi     Dwarf_Error *error)
190049d3bc91SRichard Lowe {
190107dc1947SRichard Lowe     Dwarf_Byte_Ptr info_ptr = 0;
190207dc1947SRichard Lowe     Dwarf_Byte_Ptr abbrev_ptr = 0;
1903*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned abbrev_code = 0;
1904*4d9fdb46SRobert Mustacchi     Dwarf_Abbrev_List abbrev_list = 0;
190507dc1947SRichard Lowe     Dwarf_Half attr = 0;
190607dc1947SRichard Lowe     Dwarf_Half attr_form = 0;
190707dc1947SRichard Lowe     Dwarf_Unsigned offset = 0;
190807dc1947SRichard Lowe     Dwarf_Unsigned utmp = 0;
190907dc1947SRichard Lowe     Dwarf_Debug dbg = 0;
1910*4d9fdb46SRobert Mustacchi     Dwarf_Byte_Ptr abbrev_end = 0;
1911*4d9fdb46SRobert Mustacchi     int lres = 0;
191249d3bc91SRichard Lowe 
191349d3bc91SRichard Lowe     info_ptr = die_info_ptr;
1914*4d9fdb46SRobert Mustacchi     DECODE_LEB128_UWORD_CK(info_ptr, utmp,dbg,error,die_info_end);
1915*4d9fdb46SRobert Mustacchi     abbrev_code = (Dwarf_Unsigned) utmp;
191649d3bc91SRichard Lowe     if (abbrev_code == 0) {
1917*4d9fdb46SRobert Mustacchi         /*  Should never happen. Tested before we got here. */
1918*4d9fdb46SRobert Mustacchi         _dwarf_error(dbg, error, DW_DLE_NEXT_DIE_PTR_NULL);
1919*4d9fdb46SRobert Mustacchi         return DW_DLV_ERROR;
192049d3bc91SRichard Lowe     }
192149d3bc91SRichard Lowe 
192207dc1947SRichard Lowe 
1923*4d9fdb46SRobert Mustacchi     lres = _dwarf_get_abbrev_for_code(cu_context, abbrev_code,
1924*4d9fdb46SRobert Mustacchi         &abbrev_list,error);
1925*4d9fdb46SRobert Mustacchi     if (lres == DW_DLV_ERROR) {
1926*4d9fdb46SRobert Mustacchi         return lres;
1927*4d9fdb46SRobert Mustacchi     }
1928*4d9fdb46SRobert Mustacchi     if (lres == DW_DLV_NO_ENTRY) {
1929*4d9fdb46SRobert Mustacchi         _dwarf_error(dbg, error, DW_DLE_NEXT_DIE_NO_ABBREV_LIST);
1930*4d9fdb46SRobert Mustacchi         return DW_DLV_ERROR;
193149d3bc91SRichard Lowe     }
193249d3bc91SRichard Lowe     dbg = cu_context->cc_dbg;
193349d3bc91SRichard Lowe 
1934*4d9fdb46SRobert Mustacchi     *has_die_child = abbrev_list->abl_has_child;
1935*4d9fdb46SRobert Mustacchi 
1936*4d9fdb46SRobert Mustacchi     abbrev_ptr = abbrev_list->abl_abbrev_ptr;
1937*4d9fdb46SRobert Mustacchi     abbrev_end = _dwarf_calculate_abbrev_section_end_ptr(cu_context);
193849d3bc91SRichard Lowe 
193949d3bc91SRichard Lowe     do {
194007dc1947SRichard Lowe         Dwarf_Unsigned utmp2;
194107dc1947SRichard Lowe 
1942*4d9fdb46SRobert Mustacchi         DECODE_LEB128_UWORD_CK(abbrev_ptr, utmp2,dbg,error,
1943*4d9fdb46SRobert Mustacchi             abbrev_end);
1944*4d9fdb46SRobert Mustacchi         if (utmp2 > DW_AT_hi_user) {
1945*4d9fdb46SRobert Mustacchi             _dwarf_error(dbg, error, DW_DLE_ATTR_CORRUPT);
1946*4d9fdb46SRobert Mustacchi             return DW_DLV_ERROR;
1947*4d9fdb46SRobert Mustacchi         }
194807dc1947SRichard Lowe         attr = (Dwarf_Half) utmp2;
1949*4d9fdb46SRobert Mustacchi         DECODE_LEB128_UWORD_CK(abbrev_ptr, utmp2,dbg,error,
1950*4d9fdb46SRobert Mustacchi             abbrev_end);
1951*4d9fdb46SRobert Mustacchi         if (!_dwarf_valid_form_we_know(utmp2,attr)) {
1952*4d9fdb46SRobert Mustacchi             _dwarf_error(dbg, error, DW_DLE_UNKNOWN_FORM);
1953*4d9fdb46SRobert Mustacchi             return DW_DLV_ERROR;
1954*4d9fdb46SRobert Mustacchi         }
195507dc1947SRichard Lowe         attr_form = (Dwarf_Half) utmp2;
195607dc1947SRichard Lowe         if (attr_form == DW_FORM_indirect) {
195707dc1947SRichard Lowe             Dwarf_Unsigned utmp6;
195807dc1947SRichard Lowe 
195907dc1947SRichard Lowe             /* DECODE_LEB128_UWORD updates info_ptr */
1960*4d9fdb46SRobert Mustacchi             DECODE_LEB128_UWORD_CK(info_ptr, utmp6,dbg,error,
1961*4d9fdb46SRobert Mustacchi                 die_info_end);
196207dc1947SRichard Lowe             attr_form = (Dwarf_Half) utmp6;
1963*4d9fdb46SRobert Mustacchi         }
1964*4d9fdb46SRobert Mustacchi         if (attr_form == DW_FORM_implicit_const) {
1965*4d9fdb46SRobert Mustacchi             UNUSEDARG Dwarf_Signed cval = 0;
196607dc1947SRichard Lowe 
1967*4d9fdb46SRobert Mustacchi             DECODE_LEB128_SWORD_CK(abbrev_ptr, cval,dbg,error,
1968*4d9fdb46SRobert Mustacchi                 abbrev_end);
196907dc1947SRichard Lowe         }
197007dc1947SRichard Lowe 
197107dc1947SRichard Lowe         if (want_AT_sibling && attr == DW_AT_sibling) {
197207dc1947SRichard Lowe             switch (attr_form) {
197307dc1947SRichard Lowe             case DW_FORM_ref1:
1974*4d9fdb46SRobert Mustacchi                 READ_UNALIGNED_CK(dbg, offset, Dwarf_Unsigned,
1975*4d9fdb46SRobert Mustacchi                     info_ptr, sizeof(Dwarf_Small),
1976*4d9fdb46SRobert Mustacchi                     error,die_info_end);
197707dc1947SRichard Lowe                 break;
197807dc1947SRichard Lowe             case DW_FORM_ref2:
197907dc1947SRichard Lowe                 /* READ_UNALIGNED does not update info_ptr */
1980*4d9fdb46SRobert Mustacchi                 READ_UNALIGNED_CK(dbg, offset, Dwarf_Unsigned,
1981*4d9fdb46SRobert Mustacchi                     info_ptr,DWARF_HALF_SIZE,
1982*4d9fdb46SRobert Mustacchi                     error,die_info_end);
198307dc1947SRichard Lowe                 break;
198407dc1947SRichard Lowe             case DW_FORM_ref4:
1985*4d9fdb46SRobert Mustacchi                 READ_UNALIGNED_CK(dbg, offset, Dwarf_Unsigned,
1986*4d9fdb46SRobert Mustacchi                     info_ptr, DWARF_32BIT_SIZE,
1987*4d9fdb46SRobert Mustacchi                     error,die_info_end);
198807dc1947SRichard Lowe                 break;
198907dc1947SRichard Lowe             case DW_FORM_ref8:
1990*4d9fdb46SRobert Mustacchi                 READ_UNALIGNED_CK(dbg, offset, Dwarf_Unsigned,
1991*4d9fdb46SRobert Mustacchi                     info_ptr, DWARF_64BIT_SIZE,
1992*4d9fdb46SRobert Mustacchi                     error,die_info_end);
199307dc1947SRichard Lowe                 break;
199407dc1947SRichard Lowe             case DW_FORM_ref_udata:
1995*4d9fdb46SRobert Mustacchi                 DECODE_LEB128_UWORD_CK(info_ptr, offset,
1996*4d9fdb46SRobert Mustacchi                     dbg,error,die_info_end);
199707dc1947SRichard Lowe                 break;
199807dc1947SRichard Lowe             case DW_FORM_ref_addr:
1999*4d9fdb46SRobert Mustacchi                 /*  Very unusual.  The FORM is intended to refer to
2000*4d9fdb46SRobert Mustacchi                     a different CU, but a different CU cannot
2001*4d9fdb46SRobert Mustacchi                     be a sibling, can it?
2002*4d9fdb46SRobert Mustacchi                     We could ignore this and treat as if no
2003*4d9fdb46SRobert Mustacchi                     DW_AT_sibling
2004*4d9fdb46SRobert Mustacchi                     present.   Or derive the offset from it and if
2005*4d9fdb46SRobert Mustacchi                     it is in the same CU use it directly.
2006*4d9fdb46SRobert Mustacchi                     The offset here is *supposed* to be a
2007*4d9fdb46SRobert Mustacchi                     global offset,
2008*4d9fdb46SRobert Mustacchi                     so adding cu_info_start is wrong  to any offset
2009*4d9fdb46SRobert Mustacchi                     we find here unless cu_info_start
2010*4d9fdb46SRobert Mustacchi                     is zero! Lets pretend there is no DW_AT_sibling
2011*4d9fdb46SRobert Mustacchi                     attribute.  */
201207dc1947SRichard Lowe                 goto no_sibling_attr;
201307dc1947SRichard Lowe             default:
2014*4d9fdb46SRobert Mustacchi                 _dwarf_error(dbg, error, DW_DLE_NEXT_DIE_WRONG_FORM);
2015*4d9fdb46SRobert Mustacchi                 return DW_DLV_ERROR;
201607dc1947SRichard Lowe             }
201707dc1947SRichard Lowe 
2018*4d9fdb46SRobert Mustacchi             /*  Reset *has_die_child to indicate children skipped.  */
201907dc1947SRichard Lowe             *has_die_child = false;
202007dc1947SRichard Lowe 
2021*4d9fdb46SRobert Mustacchi             /*  A value beyond die_info_end indicates an error. Exactly
2022*4d9fdb46SRobert Mustacchi                 at die_info_end means 1-past-cu-end and simply means we
2023*4d9fdb46SRobert Mustacchi                 are at the end, do not return error. Higher level
2024*4d9fdb46SRobert Mustacchi                 will detect that we are at the end. */
2025*4d9fdb46SRobert Mustacchi             {   /*  Care required here. Offset can be garbage. */
2026*4d9fdb46SRobert Mustacchi                 ptrdiff_t plen = die_info_end - cu_info_start;
2027*4d9fdb46SRobert Mustacchi                 ptrdiff_t signdoffset = (ptrdiff_t)offset;
2028*4d9fdb46SRobert Mustacchi                 if (signdoffset > plen || signdoffset < 0) {
2029*4d9fdb46SRobert Mustacchi                     /* Error case, bad DWARF. */
2030*4d9fdb46SRobert Mustacchi                     _dwarf_error(dbg, error,DW_DLE_SIBLING_OFFSET_WRONG);
2031*4d9fdb46SRobert Mustacchi                     return DW_DLV_ERROR;
2032*4d9fdb46SRobert Mustacchi                 }
203307dc1947SRichard Lowe             }
203407dc1947SRichard Lowe             /* At or before end-of-cu */
2035*4d9fdb46SRobert Mustacchi             *next_die_ptr_out = cu_info_start + offset;
2036*4d9fdb46SRobert Mustacchi             return DW_DLV_OK;
203707dc1947SRichard Lowe         }
203807dc1947SRichard Lowe 
203907dc1947SRichard Lowe         no_sibling_attr:
2040*4d9fdb46SRobert Mustacchi         if (attr_form != 0 && attr_form != DW_FORM_implicit_const) {
2041*4d9fdb46SRobert Mustacchi             int res = 0;
2042*4d9fdb46SRobert Mustacchi             Dwarf_Unsigned sizeofval = 0;
2043*4d9fdb46SRobert Mustacchi             ptrdiff_t  sizeb = 0;
2044*4d9fdb46SRobert Mustacchi 
2045*4d9fdb46SRobert Mustacchi             res = _dwarf_get_size_of_val(cu_context->cc_dbg,
2046*4d9fdb46SRobert Mustacchi                 attr_form,
2047*4d9fdb46SRobert Mustacchi                 cu_context->cc_version_stamp,
2048*4d9fdb46SRobert Mustacchi                 cu_context->cc_address_size,
2049*4d9fdb46SRobert Mustacchi                 info_ptr,
2050*4d9fdb46SRobert Mustacchi                 cu_context->cc_length_size,
2051*4d9fdb46SRobert Mustacchi                 &sizeofval,
2052*4d9fdb46SRobert Mustacchi                 die_info_end,
2053*4d9fdb46SRobert Mustacchi                 error);
2054*4d9fdb46SRobert Mustacchi             if(res != DW_DLV_OK) {
2055*4d9fdb46SRobert Mustacchi                 return res;
2056*4d9fdb46SRobert Mustacchi             }
2057*4d9fdb46SRobert Mustacchi             /*  It is ok for info_ptr == die_info_end, as we will test
2058*4d9fdb46SRobert Mustacchi                 later before using a too-large info_ptr */
2059*4d9fdb46SRobert Mustacchi             sizeb = (ptrdiff_t)sizeofval;
2060*4d9fdb46SRobert Mustacchi             if (sizeb > (die_info_end - info_ptr) ||
2061*4d9fdb46SRobert Mustacchi                 sizeb < 0) {
2062*4d9fdb46SRobert Mustacchi                 _dwarf_error(dbg, error, DW_DLE_NEXT_DIE_PAST_END);
2063*4d9fdb46SRobert Mustacchi                 return DW_DLV_ERROR;
2064*4d9fdb46SRobert Mustacchi             }
2065*4d9fdb46SRobert Mustacchi             info_ptr += sizeofval;
206607dc1947SRichard Lowe             if (info_ptr > die_info_end) {
2067*4d9fdb46SRobert Mustacchi                 /*  More than one-past-end indicates a bug somewhere,
2068*4d9fdb46SRobert Mustacchi                     likely bad dwarf generation. */
2069*4d9fdb46SRobert Mustacchi                 _dwarf_error(dbg, error, DW_DLE_NEXT_DIE_PAST_END);
2070*4d9fdb46SRobert Mustacchi                 return DW_DLV_ERROR;
207107dc1947SRichard Lowe             }
207207dc1947SRichard Lowe         }
207349d3bc91SRichard Lowe     } while (attr != 0 || attr_form != 0);
2074*4d9fdb46SRobert Mustacchi     *next_die_ptr_out = info_ptr;
2075*4d9fdb46SRobert Mustacchi     return DW_DLV_OK;
207649d3bc91SRichard Lowe }
207749d3bc91SRichard Lowe 
2078*4d9fdb46SRobert Mustacchi /*  Multiple TAGs are in fact compile units.
2079*4d9fdb46SRobert Mustacchi     Allow them all.
2080*4d9fdb46SRobert Mustacchi     Return non-zero if a CU tag.
2081*4d9fdb46SRobert Mustacchi     Else return 0.
2082*4d9fdb46SRobert Mustacchi */
2083*4d9fdb46SRobert Mustacchi static int
is_cu_tag(int t)2084*4d9fdb46SRobert Mustacchi is_cu_tag(int t)
2085*4d9fdb46SRobert Mustacchi {
2086*4d9fdb46SRobert Mustacchi     if (t == DW_TAG_compile_unit  ||
2087*4d9fdb46SRobert Mustacchi         t == DW_TAG_partial_unit  ||
2088*4d9fdb46SRobert Mustacchi         t == DW_TAG_skeleton_unit ||
2089*4d9fdb46SRobert Mustacchi         t == DW_TAG_type_unit) {
2090*4d9fdb46SRobert Mustacchi         return 1;
2091*4d9fdb46SRobert Mustacchi     }
2092*4d9fdb46SRobert Mustacchi     return 0;
2093*4d9fdb46SRobert Mustacchi }
209449d3bc91SRichard Lowe 
2095*4d9fdb46SRobert Mustacchi /*  Given a Dwarf_Debug dbg, and a Dwarf_Die die, it returns
2096*4d9fdb46SRobert Mustacchi     a Dwarf_Die for the sibling of die.  In case die is NULL,
2097*4d9fdb46SRobert Mustacchi     it returns (thru ptr) a Dwarf_Die for the first die in the current
209849d3bc91SRichard Lowe     cu in dbg.  Returns DW_DLV_ERROR on error.
209949d3bc91SRichard Lowe 
2100*4d9fdb46SRobert Mustacchi     It is assumed that every sibling chain including those with
2101*4d9fdb46SRobert Mustacchi     only one element is terminated with a NULL die, except a
210249d3bc91SRichard Lowe     chain with only a NULL die.
210349d3bc91SRichard Lowe 
2104*4d9fdb46SRobert Mustacchi     The algorithm moves from one die to the adjacent one.  It
2105*4d9fdb46SRobert Mustacchi     returns when the depth of children it sees equals the number
2106*4d9fdb46SRobert Mustacchi     of sibling chain terminations.  A single count, child_depth
2107*4d9fdb46SRobert Mustacchi     is used to track the depth of children and sibling terminations
2108*4d9fdb46SRobert Mustacchi     encountered.  Child_depth is incremented when a die has the
2109*4d9fdb46SRobert Mustacchi     Has-Child flag set unless the child happens to be a NULL die.
2110*4d9fdb46SRobert Mustacchi     Child_depth is decremented when a die has Has-Child false,
2111*4d9fdb46SRobert Mustacchi     and the adjacent die is NULL.  Algorithm returns when
211249d3bc91SRichard Lowe     child_depth is 0.
211349d3bc91SRichard Lowe 
2114*4d9fdb46SRobert Mustacchi     **NOTE: Do not modify input die, since it is used at the end.  */
211549d3bc91SRichard Lowe int
dwarf_siblingof(Dwarf_Debug dbg,Dwarf_Die die,Dwarf_Die * caller_ret_die,Dwarf_Error * error)211649d3bc91SRichard Lowe dwarf_siblingof(Dwarf_Debug dbg,
2117*4d9fdb46SRobert Mustacchi     Dwarf_Die die,
2118*4d9fdb46SRobert Mustacchi     Dwarf_Die * caller_ret_die, Dwarf_Error * error)
2119*4d9fdb46SRobert Mustacchi {
2120*4d9fdb46SRobert Mustacchi     int res = 0;
2121*4d9fdb46SRobert Mustacchi     Dwarf_Bool is_info = TRUE;
2122*4d9fdb46SRobert Mustacchi     Dwarf_Debug_InfoTypes dis = 0;
2123*4d9fdb46SRobert Mustacchi 
2124*4d9fdb46SRobert Mustacchi     dis = &dbg->de_info_reading;
2125*4d9fdb46SRobert Mustacchi     res = _dwarf_siblingof_internal(dbg,die,
2126*4d9fdb46SRobert Mustacchi         die?die->di_cu_context:dis->de_cu_context,
2127*4d9fdb46SRobert Mustacchi         is_info,caller_ret_die,error);
2128*4d9fdb46SRobert Mustacchi     return res;
2129*4d9fdb46SRobert Mustacchi }
2130*4d9fdb46SRobert Mustacchi /*  This is the new form, October 2011.  On calling with 'die' NULL,
2131*4d9fdb46SRobert Mustacchi     we cannot tell if this is debug_info or debug_types, so
2132*4d9fdb46SRobert Mustacchi     we must be informed!. */
2133*4d9fdb46SRobert Mustacchi int
dwarf_siblingof_b(Dwarf_Debug dbg,Dwarf_Die die,Dwarf_Bool is_info,Dwarf_Die * caller_ret_die,Dwarf_Error * error)2134*4d9fdb46SRobert Mustacchi dwarf_siblingof_b(Dwarf_Debug dbg,
2135*4d9fdb46SRobert Mustacchi     Dwarf_Die die,
2136*4d9fdb46SRobert Mustacchi     Dwarf_Bool is_info,
2137*4d9fdb46SRobert Mustacchi     Dwarf_Die * caller_ret_die, Dwarf_Error * error)
2138*4d9fdb46SRobert Mustacchi {
2139*4d9fdb46SRobert Mustacchi     int res;
2140*4d9fdb46SRobert Mustacchi     Dwarf_Debug_InfoTypes dis = 0;
2141*4d9fdb46SRobert Mustacchi 
2142*4d9fdb46SRobert Mustacchi     dis = is_info? &dbg->de_info_reading:
2143*4d9fdb46SRobert Mustacchi         &dbg->de_types_reading;
2144*4d9fdb46SRobert Mustacchi 
2145*4d9fdb46SRobert Mustacchi     res = _dwarf_siblingof_internal(dbg,die,
2146*4d9fdb46SRobert Mustacchi         die?die->di_cu_context:dis->de_cu_context,
2147*4d9fdb46SRobert Mustacchi         is_info,caller_ret_die,error);
2148*4d9fdb46SRobert Mustacchi     return res;
2149*4d9fdb46SRobert Mustacchi }
2150*4d9fdb46SRobert Mustacchi 
2151*4d9fdb46SRobert Mustacchi static int
_dwarf_siblingof_internal(Dwarf_Debug dbg,Dwarf_Die die,Dwarf_CU_Context context,Dwarf_Bool is_info,Dwarf_Die * caller_ret_die,Dwarf_Error * error)2152*4d9fdb46SRobert Mustacchi _dwarf_siblingof_internal(Dwarf_Debug dbg,
2153*4d9fdb46SRobert Mustacchi     Dwarf_Die die,
2154*4d9fdb46SRobert Mustacchi     Dwarf_CU_Context context,
2155*4d9fdb46SRobert Mustacchi     Dwarf_Bool is_info,
2156*4d9fdb46SRobert Mustacchi     Dwarf_Die * caller_ret_die, Dwarf_Error * error)
215749d3bc91SRichard Lowe {
215807dc1947SRichard Lowe     Dwarf_Die ret_die = 0;
215907dc1947SRichard Lowe     Dwarf_Byte_Ptr die_info_ptr = 0;
216049d3bc91SRichard Lowe     Dwarf_Byte_Ptr cu_info_start = 0;
216107dc1947SRichard Lowe 
216207dc1947SRichard Lowe     /* die_info_end points 1-past end of die (once set) */
216349d3bc91SRichard Lowe     Dwarf_Byte_Ptr die_info_end = 0;
2164*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned abbrev_code = 0;
216507dc1947SRichard Lowe     Dwarf_Unsigned utmp = 0;
2166*4d9fdb46SRobert Mustacchi     int lres = 0;
2167*4d9fdb46SRobert Mustacchi     int dieres = 0;
2168*4d9fdb46SRobert Mustacchi     /* Since die may be NULL, we rely on the input argument. */
2169*4d9fdb46SRobert Mustacchi     Dwarf_Small *dataptr =  0;
217049d3bc91SRichard Lowe 
217149d3bc91SRichard Lowe     if (dbg == NULL) {
217207dc1947SRichard Lowe         _dwarf_error(NULL, error, DW_DLE_DBG_NULL);
217307dc1947SRichard Lowe         return (DW_DLV_ERROR);
217449d3bc91SRichard Lowe     }
2175*4d9fdb46SRobert Mustacchi     dataptr = is_info? dbg->de_debug_info.dss_data:
2176*4d9fdb46SRobert Mustacchi         dbg->de_debug_types.dss_data;
217749d3bc91SRichard Lowe     if (die == NULL) {
2178*4d9fdb46SRobert Mustacchi         /*  Find root die of cu */
2179*4d9fdb46SRobert Mustacchi         /*  die_info_end is untouched here, need not be set in this
2180*4d9fdb46SRobert Mustacchi             branch. */
2181*4d9fdb46SRobert Mustacchi         Dwarf_Off off2 = 0;
2182*4d9fdb46SRobert Mustacchi         Dwarf_Unsigned headerlen = 0;
2183*4d9fdb46SRobert Mustacchi         int cres = 0;
2184*4d9fdb46SRobert Mustacchi 
2185*4d9fdb46SRobert Mustacchi         /*  If we've not loaded debug_info
2186*4d9fdb46SRobert Mustacchi             context will be NULL. */
2187*4d9fdb46SRobert Mustacchi         if (!context) {
2188*4d9fdb46SRobert Mustacchi             local_dealloc_cu_context(dbg,context);
218907dc1947SRichard Lowe             return (DW_DLV_ERROR);
219007dc1947SRichard Lowe         }
2191*4d9fdb46SRobert Mustacchi         off2 = context->cc_debug_offset;
2192*4d9fdb46SRobert Mustacchi         cu_info_start = dataptr + off2;
2193*4d9fdb46SRobert Mustacchi         cres = _dwarf_length_of_cu_header(dbg, off2,is_info,
2194*4d9fdb46SRobert Mustacchi             &headerlen,error);
2195*4d9fdb46SRobert Mustacchi         if (cres != DW_DLV_OK) {
2196*4d9fdb46SRobert Mustacchi             return cres;
2197*4d9fdb46SRobert Mustacchi         }
2198*4d9fdb46SRobert Mustacchi         die_info_ptr = cu_info_start + headerlen;
2199*4d9fdb46SRobert Mustacchi         die_info_end = _dwarf_calculate_info_section_end_ptr(context);
2200*4d9fdb46SRobert Mustacchi 
2201*4d9fdb46SRobert Mustacchi         /*  Recording the CU die pointer so we can later access
2202*4d9fdb46SRobert Mustacchi             for special FORMs relating to .debug_str_offsets
2203*4d9fdb46SRobert Mustacchi             and .debug_addr  */
2204*4d9fdb46SRobert Mustacchi         context->cc_cu_die_offset_present = TRUE;
2205*4d9fdb46SRobert Mustacchi         context->cc_cu_die_global_sec_offset = off2 + headerlen;
220649d3bc91SRichard Lowe     } else {
220707dc1947SRichard Lowe         /* Find sibling die. */
220807dc1947SRichard Lowe         Dwarf_Bool has_child = false;
2209*4d9fdb46SRobert Mustacchi         Dwarf_Signed child_depth = 0;
221007dc1947SRichard Lowe 
2211*4d9fdb46SRobert Mustacchi         /*  We cannot have a legal die unless debug_info
2212*4d9fdb46SRobert Mustacchi             was loaded, so
2213*4d9fdb46SRobert Mustacchi             no need to load debug_info here. */
221407dc1947SRichard Lowe         CHECK_DIE(die, DW_DLV_ERROR);
221507dc1947SRichard Lowe 
2216*4d9fdb46SRobert Mustacchi         die_info_ptr = die->di_debug_ptr;
221707dc1947SRichard Lowe         if (*die_info_ptr == 0) {
221807dc1947SRichard Lowe             return (DW_DLV_NO_ENTRY);
221907dc1947SRichard Lowe         }
2220*4d9fdb46SRobert Mustacchi         context = die->di_cu_context;
2221*4d9fdb46SRobert Mustacchi         cu_info_start = dataptr+ context->cc_debug_offset;
2222*4d9fdb46SRobert Mustacchi         die_info_end = _dwarf_calculate_info_section_end_ptr(context);
222307dc1947SRichard Lowe 
222407dc1947SRichard Lowe         if ((*die_info_ptr) == 0) {
222507dc1947SRichard Lowe             return (DW_DLV_NO_ENTRY);
222607dc1947SRichard Lowe         }
222707dc1947SRichard Lowe         child_depth = 0;
222807dc1947SRichard Lowe         do {
2229*4d9fdb46SRobert Mustacchi             int res2 = 0;
2230*4d9fdb46SRobert Mustacchi             Dwarf_Byte_Ptr die_info_ptr2 = 0;
2231*4d9fdb46SRobert Mustacchi 
2232*4d9fdb46SRobert Mustacchi             res2 = _dwarf_next_die_info_ptr(die_info_ptr,
2233*4d9fdb46SRobert Mustacchi                 context, die_info_end,
2234*4d9fdb46SRobert Mustacchi                 cu_info_start, true, &has_child,
2235*4d9fdb46SRobert Mustacchi                 &die_info_ptr2,
2236*4d9fdb46SRobert Mustacchi                 error);
2237*4d9fdb46SRobert Mustacchi             if(res2 != DW_DLV_OK) {
2238*4d9fdb46SRobert Mustacchi                 return res2;
2239*4d9fdb46SRobert Mustacchi             }
2240*4d9fdb46SRobert Mustacchi             if (die_info_ptr2 < die_info_ptr) {
2241*4d9fdb46SRobert Mustacchi                 /*  There is something very wrong, our die value
2242*4d9fdb46SRobert Mustacchi                     decreased.  Bad DWARF. */
2243*4d9fdb46SRobert Mustacchi                 _dwarf_error(dbg, error, DW_DLE_NEXT_DIE_LOW_ERROR);
2244*4d9fdb46SRobert Mustacchi                 return (DW_DLV_ERROR);
2245*4d9fdb46SRobert Mustacchi             }
2246*4d9fdb46SRobert Mustacchi             if (die_info_ptr2 > die_info_end) {
2247*4d9fdb46SRobert Mustacchi                 _dwarf_error(dbg, error, DW_DLE_NEXT_DIE_PAST_END);
224807dc1947SRichard Lowe                 return (DW_DLV_ERROR);
224907dc1947SRichard Lowe             }
2250*4d9fdb46SRobert Mustacchi             die_info_ptr = die_info_ptr2;
225107dc1947SRichard Lowe 
2252*4d9fdb46SRobert Mustacchi             /*  die_info_end is one past end. Do not read it!
2253*4d9fdb46SRobert Mustacchi                 A test for '!= die_info_end'  would work as well,
2254*4d9fdb46SRobert Mustacchi                 but perhaps < reads more like the meaning. */
2255*4d9fdb46SRobert Mustacchi             if (die_info_ptr < die_info_end) {
225607dc1947SRichard Lowe                 if ((*die_info_ptr) == 0 && has_child) {
225707dc1947SRichard Lowe                     die_info_ptr++;
225807dc1947SRichard Lowe                     has_child = false;
225907dc1947SRichard Lowe                 }
226007dc1947SRichard Lowe             }
226107dc1947SRichard Lowe 
2262*4d9fdb46SRobert Mustacchi             /*  die_info_ptr can be one-past-end.  */
226307dc1947SRichard Lowe             if ((die_info_ptr == die_info_end) ||
226407dc1947SRichard Lowe                 ((*die_info_ptr) == 0)) {
2265*4d9fdb46SRobert Mustacchi                 /* We are at the end of a sibling list.
2266*4d9fdb46SRobert Mustacchi                     get back to the next containing
2267*4d9fdb46SRobert Mustacchi                     sibling list (looking for a libling
2268*4d9fdb46SRobert Mustacchi                     list with more on it).
2269*4d9fdb46SRobert Mustacchi                     */
2270*4d9fdb46SRobert Mustacchi                 for (;;) {
2271*4d9fdb46SRobert Mustacchi                     if (child_depth == 0) {
2272*4d9fdb46SRobert Mustacchi                         /*  Meaning there is no outer list,
2273*4d9fdb46SRobert Mustacchi                             so stop. */
2274*4d9fdb46SRobert Mustacchi                         break;
2275*4d9fdb46SRobert Mustacchi                     }
2276*4d9fdb46SRobert Mustacchi                     if (die_info_ptr == die_info_end) {
2277*4d9fdb46SRobert Mustacchi                         /*  September 2016: do not deref
2278*4d9fdb46SRobert Mustacchi                             if we are past end.
2279*4d9fdb46SRobert Mustacchi                             If we are at end at this point
2280*4d9fdb46SRobert Mustacchi                             it means the sibling list
2281*4d9fdb46SRobert Mustacchi                             inside this CU is not properly
2282*4d9fdb46SRobert Mustacchi                             terminated.
2283*4d9fdb46SRobert Mustacchi                             August 2019:
2284*4d9fdb46SRobert Mustacchi                             We used to declare an error,
2285*4d9fdb46SRobert Mustacchi                             DW_DLE_SIBLING_LIST_IMPROPER but
2286*4d9fdb46SRobert Mustacchi                             now we just silently
2287*4d9fdb46SRobert Mustacchi                             declare this is the end of the list.
2288*4d9fdb46SRobert Mustacchi                             Each level of a sibling nest should
2289*4d9fdb46SRobert Mustacchi                             have a single NUL byte, but here
2290*4d9fdb46SRobert Mustacchi                             things are wrong, the DWARF
2291*4d9fdb46SRobert Mustacchi                             is corrupt.  */
2292*4d9fdb46SRobert Mustacchi                         return DW_DLV_NO_ENTRY;
2293*4d9fdb46SRobert Mustacchi                     }
2294*4d9fdb46SRobert Mustacchi                     if (*die_info_ptr) {
2295*4d9fdb46SRobert Mustacchi                         /* We have a real sibling. */
2296*4d9fdb46SRobert Mustacchi                         break;
2297*4d9fdb46SRobert Mustacchi                     }
2298*4d9fdb46SRobert Mustacchi                     /*  Move out one DIE level.
2299*4d9fdb46SRobert Mustacchi                         Move past NUL byte marking end of
2300*4d9fdb46SRobert Mustacchi                         this sibling list. */
2301*4d9fdb46SRobert Mustacchi                     child_depth--;
2302*4d9fdb46SRobert Mustacchi                     die_info_ptr++;
2303*4d9fdb46SRobert Mustacchi                 }
230407dc1947SRichard Lowe             } else {
230507dc1947SRichard Lowe                 child_depth = has_child ? child_depth + 1 : child_depth;
230607dc1947SRichard Lowe             }
230707dc1947SRichard Lowe         } while (child_depth != 0);
230807dc1947SRichard Lowe     }
230907dc1947SRichard Lowe 
2310*4d9fdb46SRobert Mustacchi     /*  die_info_ptr > die_info_end is really a bug (possibly in dwarf
2311*4d9fdb46SRobert Mustacchi         generation)(but we are past end, no more DIEs here), whereas
2312*4d9fdb46SRobert Mustacchi         die_info_ptr == die_info_end means 'one past end, no more DIEs
2313*4d9fdb46SRobert Mustacchi         here'. */
2314*4d9fdb46SRobert Mustacchi     if (die_info_ptr >= die_info_end) {
231507dc1947SRichard Lowe         return (DW_DLV_NO_ENTRY);
231649d3bc91SRichard Lowe     }
231749d3bc91SRichard Lowe     if ((*die_info_ptr) == 0) {
231807dc1947SRichard Lowe         return (DW_DLV_NO_ENTRY);
231949d3bc91SRichard Lowe     }
232049d3bc91SRichard Lowe 
232149d3bc91SRichard Lowe     ret_die = (Dwarf_Die) _dwarf_get_alloc(dbg, DW_DLA_DIE, 1);
232249d3bc91SRichard Lowe     if (ret_die == NULL) {
232307dc1947SRichard Lowe         _dwarf_error(dbg, error, DW_DLE_ALLOC_FAIL);
232407dc1947SRichard Lowe         return (DW_DLV_ERROR);
232549d3bc91SRichard Lowe     }
232649d3bc91SRichard Lowe 
2327*4d9fdb46SRobert Mustacchi     ret_die->di_is_info = is_info;
2328*4d9fdb46SRobert Mustacchi     ret_die->di_debug_ptr = die_info_ptr;
232949d3bc91SRichard Lowe     ret_die->di_cu_context =
2330*4d9fdb46SRobert Mustacchi         die == NULL ? context : die->di_cu_context;
233149d3bc91SRichard Lowe 
2332*4d9fdb46SRobert Mustacchi #if 0
2333*4d9fdb46SRobert Mustacchi     DECODE_LEB128_UWORD_CK(die_info_ptr, utmp,dbg,error,die_info_end);
2334*4d9fdb46SRobert Mustacchi #endif
2335*4d9fdb46SRobert Mustacchi     dieres = _dwarf_leb128_uword_wrapper(dbg,
2336*4d9fdb46SRobert Mustacchi         &die_info_ptr,die_info_end,&utmp,error);
2337*4d9fdb46SRobert Mustacchi     if (dieres == DW_DLV_ERROR) {
2338*4d9fdb46SRobert Mustacchi         dwarf_dealloc(dbg, ret_die, DW_DLA_DIE);
2339*4d9fdb46SRobert Mustacchi         return dieres;
2340*4d9fdb46SRobert Mustacchi     }
2341*4d9fdb46SRobert Mustacchi     if (die_info_ptr > die_info_end) {
2342*4d9fdb46SRobert Mustacchi         /*  We managed to go past the end of the CU!.
2343*4d9fdb46SRobert Mustacchi             Something is badly wrong. */
2344*4d9fdb46SRobert Mustacchi         dwarf_dealloc(dbg, ret_die, DW_DLA_DIE);
2345*4d9fdb46SRobert Mustacchi         _dwarf_error(dbg, error, DW_DLE_ABBREV_DECODE_ERROR);
2346*4d9fdb46SRobert Mustacchi         return (DW_DLV_ERROR);
2347*4d9fdb46SRobert Mustacchi     }
2348*4d9fdb46SRobert Mustacchi     abbrev_code = (Dwarf_Unsigned) utmp;
234949d3bc91SRichard Lowe     if (abbrev_code == 0) {
235007dc1947SRichard Lowe         /* Zero means a null DIE */
235107dc1947SRichard Lowe         dwarf_dealloc(dbg, ret_die, DW_DLA_DIE);
235207dc1947SRichard Lowe         return (DW_DLV_NO_ENTRY);
235349d3bc91SRichard Lowe     }
235407dc1947SRichard Lowe     ret_die->di_abbrev_code = abbrev_code;
2355*4d9fdb46SRobert Mustacchi     lres = _dwarf_get_abbrev_for_code(ret_die->di_cu_context,
2356*4d9fdb46SRobert Mustacchi         abbrev_code,
2357*4d9fdb46SRobert Mustacchi         &ret_die->di_abbrev_list,error);
2358*4d9fdb46SRobert Mustacchi     if (lres == DW_DLV_ERROR) {
2359*4d9fdb46SRobert Mustacchi         dwarf_dealloc(dbg, ret_die, DW_DLA_DIE);
2360*4d9fdb46SRobert Mustacchi         return lres;
2361*4d9fdb46SRobert Mustacchi     }
2362*4d9fdb46SRobert Mustacchi     if (lres == DW_DLV_NO_ENTRY) {
2363*4d9fdb46SRobert Mustacchi         dwarfstring m;
2364*4d9fdb46SRobert Mustacchi         dwarf_dealloc(dbg, ret_die, DW_DLA_DIE);
2365*4d9fdb46SRobert Mustacchi         dwarfstring_constructor(&m);
2366*4d9fdb46SRobert Mustacchi         dwarfstring_append_printf_u(&m,
2367*4d9fdb46SRobert Mustacchi             "There is no abbrev present for code 0x%x .",
2368*4d9fdb46SRobert Mustacchi             abbrev_code);
2369*4d9fdb46SRobert Mustacchi         _dwarf_error_string(dbg, error,
2370*4d9fdb46SRobert Mustacchi             DW_DLE_DIE_ABBREV_LIST_NULL,dwarfstring_string(&m));
2371*4d9fdb46SRobert Mustacchi         dwarfstring_destructor(&m);
2372*4d9fdb46SRobert Mustacchi         return DW_DLV_ERROR;
2373*4d9fdb46SRobert Mustacchi     }
2374*4d9fdb46SRobert Mustacchi     if (die == NULL && !is_cu_tag(ret_die->di_abbrev_list->abl_tag)) {
237507dc1947SRichard Lowe         dwarf_dealloc(dbg, ret_die, DW_DLA_DIE);
237607dc1947SRichard Lowe         _dwarf_error(dbg, error, DW_DLE_FIRST_DIE_NOT_CU);
2377*4d9fdb46SRobert Mustacchi         return DW_DLV_ERROR;
237849d3bc91SRichard Lowe     }
237949d3bc91SRichard Lowe 
238049d3bc91SRichard Lowe     *caller_ret_die = ret_die;
238149d3bc91SRichard Lowe     return (DW_DLV_OK);
238249d3bc91SRichard Lowe }
238349d3bc91SRichard Lowe 
238449d3bc91SRichard Lowe 
238549d3bc91SRichard Lowe int
dwarf_child(Dwarf_Die die,Dwarf_Die * caller_ret_die,Dwarf_Error * error)238649d3bc91SRichard Lowe dwarf_child(Dwarf_Die die,
2387*4d9fdb46SRobert Mustacchi     Dwarf_Die * caller_ret_die,
2388*4d9fdb46SRobert Mustacchi     Dwarf_Error * error)
238949d3bc91SRichard Lowe {
239007dc1947SRichard Lowe     Dwarf_Byte_Ptr die_info_ptr = 0;
2391*4d9fdb46SRobert Mustacchi     Dwarf_Byte_Ptr die_info_ptr2 = 0;
239207dc1947SRichard Lowe 
239307dc1947SRichard Lowe     /* die_info_end points one-past-end of die area. */
239407dc1947SRichard Lowe     Dwarf_Byte_Ptr die_info_end = 0;
239507dc1947SRichard Lowe     Dwarf_Die ret_die = 0;
239607dc1947SRichard Lowe     Dwarf_Bool has_die_child = 0;
239749d3bc91SRichard Lowe     Dwarf_Debug dbg;
2398*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned abbrev_code = 0;
239907dc1947SRichard Lowe     Dwarf_Unsigned utmp = 0;
2400*4d9fdb46SRobert Mustacchi     Dwarf_Debug_InfoTypes dis = 0;
2401*4d9fdb46SRobert Mustacchi     int res = 0;
2402*4d9fdb46SRobert Mustacchi     Dwarf_CU_Context context = 0;
2403*4d9fdb46SRobert Mustacchi     int lres = 0;
240449d3bc91SRichard Lowe 
240507dc1947SRichard Lowe     CHECK_DIE(die, DW_DLV_ERROR);
240607dc1947SRichard Lowe     dbg = die->di_cu_context->cc_dbg;
2407*4d9fdb46SRobert Mustacchi     dis = die->di_is_info? &dbg->de_info_reading:
2408*4d9fdb46SRobert Mustacchi         &dbg->de_types_reading;
2409*4d9fdb46SRobert Mustacchi     die_info_ptr = die->di_debug_ptr;
241049d3bc91SRichard Lowe 
2411*4d9fdb46SRobert Mustacchi     /*  We are saving a DIE pointer here, but the pointer
2412*4d9fdb46SRobert Mustacchi         will not be presumed live later, when it is tested. */
2413*4d9fdb46SRobert Mustacchi     dis->de_last_die = die;
2414*4d9fdb46SRobert Mustacchi     dis->de_last_di_ptr = die_info_ptr;
241549d3bc91SRichard Lowe 
2416*4d9fdb46SRobert Mustacchi     /* NULL die has no child. */
2417*4d9fdb46SRobert Mustacchi     if ((*die_info_ptr) == 0) {
2418*4d9fdb46SRobert Mustacchi         return DW_DLV_NO_ENTRY;
2419*4d9fdb46SRobert Mustacchi     }
2420*4d9fdb46SRobert Mustacchi     context = die->di_cu_context;
2421*4d9fdb46SRobert Mustacchi     die_info_end = _dwarf_calculate_info_section_end_ptr(context);
2422*4d9fdb46SRobert Mustacchi 
2423*4d9fdb46SRobert Mustacchi     res = _dwarf_next_die_info_ptr(die_info_ptr,
2424*4d9fdb46SRobert Mustacchi         die->di_cu_context,
2425*4d9fdb46SRobert Mustacchi         die_info_end,
2426*4d9fdb46SRobert Mustacchi         NULL, false,
2427*4d9fdb46SRobert Mustacchi         &has_die_child,
2428*4d9fdb46SRobert Mustacchi         &die_info_ptr2,
2429*4d9fdb46SRobert Mustacchi         error);
2430*4d9fdb46SRobert Mustacchi     if(res != DW_DLV_OK) {
2431*4d9fdb46SRobert Mustacchi         return res;
2432*4d9fdb46SRobert Mustacchi     }
2433*4d9fdb46SRobert Mustacchi     if (die_info_ptr == die_info_end) {
2434*4d9fdb46SRobert Mustacchi         return DW_DLV_NO_ENTRY;
243549d3bc91SRichard Lowe     }
2436*4d9fdb46SRobert Mustacchi     die_info_ptr = die_info_ptr2;
243749d3bc91SRichard Lowe 
2438*4d9fdb46SRobert Mustacchi     dis->de_last_di_ptr = die_info_ptr;
2439*4d9fdb46SRobert Mustacchi 
2440*4d9fdb46SRobert Mustacchi     if (!has_die_child) {
2441*4d9fdb46SRobert Mustacchi         /* Look for end of sibling chain. */
2442*4d9fdb46SRobert Mustacchi         while (dis->de_last_di_ptr < die_info_end) {
2443*4d9fdb46SRobert Mustacchi             if (*dis->de_last_di_ptr) {
2444*4d9fdb46SRobert Mustacchi                 break;
2445*4d9fdb46SRobert Mustacchi             }
2446*4d9fdb46SRobert Mustacchi             ++dis->de_last_di_ptr;
2447*4d9fdb46SRobert Mustacchi         }
2448*4d9fdb46SRobert Mustacchi         return DW_DLV_NO_ENTRY;
2449*4d9fdb46SRobert Mustacchi     }
245049d3bc91SRichard Lowe 
245149d3bc91SRichard Lowe     ret_die = (Dwarf_Die) _dwarf_get_alloc(dbg, DW_DLA_DIE, 1);
245249d3bc91SRichard Lowe     if (ret_die == NULL) {
245307dc1947SRichard Lowe         _dwarf_error(dbg, error, DW_DLE_ALLOC_FAIL);
2454*4d9fdb46SRobert Mustacchi         return DW_DLV_ERROR;
245549d3bc91SRichard Lowe     }
2456*4d9fdb46SRobert Mustacchi     ret_die->di_debug_ptr = die_info_ptr;
245749d3bc91SRichard Lowe     ret_die->di_cu_context = die->di_cu_context;
2458*4d9fdb46SRobert Mustacchi     ret_die->di_is_info = die->di_is_info;
2459*4d9fdb46SRobert Mustacchi 
2460*4d9fdb46SRobert Mustacchi     DECODE_LEB128_UWORD_CK(die_info_ptr, utmp,
2461*4d9fdb46SRobert Mustacchi         dbg,error,die_info_end);
2462*4d9fdb46SRobert Mustacchi     abbrev_code = (Dwarf_Unsigned) utmp;
2463*4d9fdb46SRobert Mustacchi 
2464*4d9fdb46SRobert Mustacchi     dis->de_last_di_ptr = die_info_ptr;
246549d3bc91SRichard Lowe 
246649d3bc91SRichard Lowe     if (abbrev_code == 0) {
2467*4d9fdb46SRobert Mustacchi         /* Look for end of sibling chain */
2468*4d9fdb46SRobert Mustacchi         while (dis->de_last_di_ptr < die_info_end) {
2469*4d9fdb46SRobert Mustacchi             if (*dis->de_last_di_ptr) {
2470*4d9fdb46SRobert Mustacchi                 break;
2471*4d9fdb46SRobert Mustacchi             }
2472*4d9fdb46SRobert Mustacchi             ++dis->de_last_di_ptr;
2473*4d9fdb46SRobert Mustacchi         }
2474*4d9fdb46SRobert Mustacchi 
2475*4d9fdb46SRobert Mustacchi         /*  We have arrived at a null DIE,
2476*4d9fdb46SRobert Mustacchi             at the end of a CU or the end
2477*4d9fdb46SRobert Mustacchi             of a list of siblings. */
247807dc1947SRichard Lowe         *caller_ret_die = 0;
247907dc1947SRichard Lowe         dwarf_dealloc(dbg, ret_die, DW_DLA_DIE);
2480*4d9fdb46SRobert Mustacchi         ret_die = 0;
248107dc1947SRichard Lowe         return DW_DLV_NO_ENTRY;
248249d3bc91SRichard Lowe     }
248307dc1947SRichard Lowe     ret_die->di_abbrev_code = abbrev_code;
2484*4d9fdb46SRobert Mustacchi     lres = _dwarf_get_abbrev_for_code(die->di_cu_context, abbrev_code,
2485*4d9fdb46SRobert Mustacchi         &ret_die->di_abbrev_list,error);
2486*4d9fdb46SRobert Mustacchi     if (lres == DW_DLV_ERROR) {
248707dc1947SRichard Lowe         dwarf_dealloc(dbg, ret_die, DW_DLA_DIE);
2488*4d9fdb46SRobert Mustacchi         ret_die = 0;
2489*4d9fdb46SRobert Mustacchi         return lres;
2490*4d9fdb46SRobert Mustacchi     }
2491*4d9fdb46SRobert Mustacchi     if (lres == DW_DLV_NO_ENTRY) {
2492*4d9fdb46SRobert Mustacchi         dwarf_dealloc(dbg, ret_die, DW_DLA_DIE);
2493*4d9fdb46SRobert Mustacchi         ret_die = 0;
2494*4d9fdb46SRobert Mustacchi         _dwarf_error(dbg, error, DW_DLE_ABBREV_MISSING);
2495*4d9fdb46SRobert Mustacchi         return DW_DLV_ERROR;
249649d3bc91SRichard Lowe     }
249749d3bc91SRichard Lowe     *caller_ret_die = ret_die;
249849d3bc91SRichard Lowe     return (DW_DLV_OK);
249949d3bc91SRichard Lowe }
250049d3bc91SRichard Lowe 
2501*4d9fdb46SRobert Mustacchi /*  Given a (global, not cu_relative) die offset, this returns
2502*4d9fdb46SRobert Mustacchi     a pointer to a DIE thru *new_die.
2503*4d9fdb46SRobert Mustacchi     It is up to the caller to do a
2504*4d9fdb46SRobert Mustacchi     dwarf_dealloc(dbg,*new_die,DW_DLE_DIE);
2505*4d9fdb46SRobert Mustacchi     The old form only works with debug_info.
2506*4d9fdb46SRobert Mustacchi     The new _b form works with debug_info or debug_types.
2507*4d9fdb46SRobert Mustacchi     */
250849d3bc91SRichard Lowe int
dwarf_offdie(Dwarf_Debug dbg,Dwarf_Off offset,Dwarf_Die * new_die,Dwarf_Error * error)250949d3bc91SRichard Lowe dwarf_offdie(Dwarf_Debug dbg,
2510*4d9fdb46SRobert Mustacchi     Dwarf_Off offset, Dwarf_Die * new_die, Dwarf_Error * error)
2511*4d9fdb46SRobert Mustacchi {
2512*4d9fdb46SRobert Mustacchi     Dwarf_Bool is_info = true;
2513*4d9fdb46SRobert Mustacchi     return dwarf_offdie_b(dbg,offset,is_info,new_die,error);
2514*4d9fdb46SRobert Mustacchi }
2515*4d9fdb46SRobert Mustacchi 
2516*4d9fdb46SRobert Mustacchi int
dwarf_offdie_b(Dwarf_Debug dbg,Dwarf_Off offset,Dwarf_Bool is_info,Dwarf_Die * new_die,Dwarf_Error * error)2517*4d9fdb46SRobert Mustacchi dwarf_offdie_b(Dwarf_Debug dbg,
2518*4d9fdb46SRobert Mustacchi     Dwarf_Off offset, Dwarf_Bool is_info,
2519*4d9fdb46SRobert Mustacchi     Dwarf_Die * new_die, Dwarf_Error * error)
252049d3bc91SRichard Lowe {
252107dc1947SRichard Lowe     Dwarf_CU_Context cu_context = 0;
252249d3bc91SRichard Lowe     Dwarf_Off new_cu_offset = 0;
252307dc1947SRichard Lowe     Dwarf_Die die = 0;
252407dc1947SRichard Lowe     Dwarf_Byte_Ptr info_ptr = 0;
252507dc1947SRichard Lowe     Dwarf_Unsigned abbrev_code = 0;
252607dc1947SRichard Lowe     Dwarf_Unsigned utmp = 0;
2527*4d9fdb46SRobert Mustacchi     int lres = 0;
2528*4d9fdb46SRobert Mustacchi     Dwarf_Debug_InfoTypes dis = 0;
2529*4d9fdb46SRobert Mustacchi     Dwarf_Byte_Ptr die_info_end = 0;
253049d3bc91SRichard Lowe 
253149d3bc91SRichard Lowe     if (dbg == NULL) {
253207dc1947SRichard Lowe         _dwarf_error(NULL, error, DW_DLE_DBG_NULL);
253307dc1947SRichard Lowe         return (DW_DLV_ERROR);
253449d3bc91SRichard Lowe     }
2535*4d9fdb46SRobert Mustacchi     dis = is_info? &dbg->de_info_reading:
2536*4d9fdb46SRobert Mustacchi         &dbg->de_types_reading;
253749d3bc91SRichard Lowe 
2538*4d9fdb46SRobert Mustacchi     cu_context = _dwarf_find_CU_Context(dbg, offset,is_info);
253949d3bc91SRichard Lowe     if (cu_context == NULL) {
2540*4d9fdb46SRobert Mustacchi         Dwarf_Unsigned section_size = is_info?
2541*4d9fdb46SRobert Mustacchi             dbg->de_debug_info.dss_size:
2542*4d9fdb46SRobert Mustacchi             dbg->de_debug_types.dss_size;
2543*4d9fdb46SRobert Mustacchi         int res = is_info?_dwarf_load_debug_info(dbg, error):
2544*4d9fdb46SRobert Mustacchi             _dwarf_load_debug_types(dbg,error);
254507dc1947SRichard Lowe 
254607dc1947SRichard Lowe         if (res != DW_DLV_OK) {
254707dc1947SRichard Lowe             return res;
254807dc1947SRichard Lowe         }
254907dc1947SRichard Lowe 
2550*4d9fdb46SRobert Mustacchi         if (dis->de_cu_context_list_end != NULL) {
255107dc1947SRichard Lowe             Dwarf_CU_Context lcu_context =
2552*4d9fdb46SRobert Mustacchi                 dis->de_cu_context_list_end;
255307dc1947SRichard Lowe             new_cu_offset =
2554*4d9fdb46SRobert Mustacchi                 lcu_context->cc_debug_offset +
255507dc1947SRichard Lowe                 lcu_context->cc_length +
255607dc1947SRichard Lowe                 lcu_context->cc_length_size +
255707dc1947SRichard Lowe                 lcu_context->cc_extension_size;
255807dc1947SRichard Lowe         }
255907dc1947SRichard Lowe 
256007dc1947SRichard Lowe         do {
256107dc1947SRichard Lowe             if ((new_cu_offset +
2562*4d9fdb46SRobert Mustacchi                 _dwarf_length_of_cu_header_simple(dbg,is_info)) >=
2563*4d9fdb46SRobert Mustacchi                 section_size) {
256407dc1947SRichard Lowe                 _dwarf_error(dbg, error, DW_DLE_OFFSET_BAD);
256507dc1947SRichard Lowe                 return (DW_DLV_ERROR);
256607dc1947SRichard Lowe             }
2567*4d9fdb46SRobert Mustacchi             res = _dwarf_make_CU_Context(dbg, new_cu_offset,is_info,
2568*4d9fdb46SRobert Mustacchi                 &cu_context,error);
2569*4d9fdb46SRobert Mustacchi             if (res != DW_DLV_OK) {
2570*4d9fdb46SRobert Mustacchi                 local_dealloc_cu_context(dbg,cu_context);
2571*4d9fdb46SRobert Mustacchi                 return res;
257207dc1947SRichard Lowe             }
257307dc1947SRichard Lowe 
2574*4d9fdb46SRobert Mustacchi             res = finish_up_cu_context_from_cudie(dbg,new_cu_offset,
2575*4d9fdb46SRobert Mustacchi                 cu_context,error);
2576*4d9fdb46SRobert Mustacchi             if (res == DW_DLV_ERROR) {
2577*4d9fdb46SRobert Mustacchi                 local_dealloc_cu_context(dbg,cu_context);
2578*4d9fdb46SRobert Mustacchi                 return res;
257907dc1947SRichard Lowe             }
2580*4d9fdb46SRobert Mustacchi             if (res == DW_DLV_NO_ENTRY) {
2581*4d9fdb46SRobert Mustacchi                 local_dealloc_cu_context(dbg,cu_context);
2582*4d9fdb46SRobert Mustacchi                 return res;
2583*4d9fdb46SRobert Mustacchi             }
2584*4d9fdb46SRobert Mustacchi             /*  Add the new cu_context to a list of contexts */
2585*4d9fdb46SRobert Mustacchi             insert_into_cu_context_list(dis,cu_context);
258607dc1947SRichard Lowe             new_cu_offset = new_cu_offset + cu_context->cc_length +
2587*4d9fdb46SRobert Mustacchi                 cu_context->cc_length_size +
2588*4d9fdb46SRobert Mustacchi                 cu_context->cc_extension_size;
258907dc1947SRichard Lowe         } while (offset >= new_cu_offset);
259049d3bc91SRichard Lowe     }
259149d3bc91SRichard Lowe 
2592*4d9fdb46SRobert Mustacchi     die_info_end = _dwarf_calculate_info_section_end_ptr(cu_context);
259349d3bc91SRichard Lowe     die = (Dwarf_Die) _dwarf_get_alloc(dbg, DW_DLA_DIE, 1);
2594*4d9fdb46SRobert Mustacchi     if (!die) {
259507dc1947SRichard Lowe         _dwarf_error(dbg, error, DW_DLE_ALLOC_FAIL);
259607dc1947SRichard Lowe         return (DW_DLV_ERROR);
259749d3bc91SRichard Lowe     }
259849d3bc91SRichard Lowe     die->di_cu_context = cu_context;
2599*4d9fdb46SRobert Mustacchi     die->di_is_info = is_info;
260049d3bc91SRichard Lowe 
2601*4d9fdb46SRobert Mustacchi     {
2602*4d9fdb46SRobert Mustacchi         Dwarf_Small *dataptr = is_info? dbg->de_debug_info.dss_data:
2603*4d9fdb46SRobert Mustacchi             dbg->de_debug_types.dss_data;
2604*4d9fdb46SRobert Mustacchi         info_ptr = dataptr + offset;
2605*4d9fdb46SRobert Mustacchi     }
2606*4d9fdb46SRobert Mustacchi     die->di_debug_ptr = info_ptr;
2607*4d9fdb46SRobert Mustacchi #if 0
2608*4d9fdb46SRobert Mustacchi     DECODE_LEB128_UWORD_CK(info_ptr, utmp,dbg,error,die_info_end);
2609*4d9fdb46SRobert Mustacchi #endif
2610*4d9fdb46SRobert Mustacchi     lres = _dwarf_leb128_uword_wrapper(dbg,&info_ptr,die_info_end,
2611*4d9fdb46SRobert Mustacchi         &utmp,error);
2612*4d9fdb46SRobert Mustacchi     if (lres != DW_DLV_OK) {
2613*4d9fdb46SRobert Mustacchi         dwarf_dealloc(dbg, die, DW_DLA_DIE);
2614*4d9fdb46SRobert Mustacchi         return lres;
2615*4d9fdb46SRobert Mustacchi     }
261607dc1947SRichard Lowe     abbrev_code = utmp;
261749d3bc91SRichard Lowe     if (abbrev_code == 0) {
261807dc1947SRichard Lowe         /* we are at a null DIE (or there is a bug). */
261907dc1947SRichard Lowe         *new_die = 0;
262007dc1947SRichard Lowe         dwarf_dealloc(dbg, die, DW_DLA_DIE);
262107dc1947SRichard Lowe         return DW_DLV_NO_ENTRY;
262249d3bc91SRichard Lowe     }
262307dc1947SRichard Lowe     die->di_abbrev_code = abbrev_code;
2624*4d9fdb46SRobert Mustacchi     lres = _dwarf_get_abbrev_for_code(cu_context, abbrev_code,
2625*4d9fdb46SRobert Mustacchi         &die->di_abbrev_list,error);
2626*4d9fdb46SRobert Mustacchi     if (lres == DW_DLV_ERROR) {
262707dc1947SRichard Lowe         dwarf_dealloc(dbg, die, DW_DLA_DIE);
2628*4d9fdb46SRobert Mustacchi         return lres;
2629*4d9fdb46SRobert Mustacchi     }
2630*4d9fdb46SRobert Mustacchi     if (lres == DW_DLV_NO_ENTRY) {
2631*4d9fdb46SRobert Mustacchi         dwarfstring m;
2632*4d9fdb46SRobert Mustacchi 
2633*4d9fdb46SRobert Mustacchi         dwarf_dealloc(dbg,die, DW_DLA_DIE);
2634*4d9fdb46SRobert Mustacchi         dwarfstring_constructor(&m);
2635*4d9fdb46SRobert Mustacchi         dwarfstring_append_printf_u(&m,
2636*4d9fdb46SRobert Mustacchi             "There is no abbrev present for code 0x%x .",
2637*4d9fdb46SRobert Mustacchi             abbrev_code);
2638*4d9fdb46SRobert Mustacchi         _dwarf_error_string(dbg, error,
2639*4d9fdb46SRobert Mustacchi             DW_DLE_DIE_ABBREV_LIST_NULL,dwarfstring_string(&m));
2640*4d9fdb46SRobert Mustacchi         dwarfstring_destructor(&m);
2641*4d9fdb46SRobert Mustacchi         return DW_DLV_ERROR;
2642*4d9fdb46SRobert Mustacchi     }
2643*4d9fdb46SRobert Mustacchi     *new_die = die;
2644*4d9fdb46SRobert Mustacchi     return DW_DLV_OK;
2645*4d9fdb46SRobert Mustacchi }
2646*4d9fdb46SRobert Mustacchi 
2647*4d9fdb46SRobert Mustacchi /*  New March 2016.
2648*4d9fdb46SRobert Mustacchi     Lets one cross check the abbreviations section and
2649*4d9fdb46SRobert Mustacchi     the DIE information presented  by dwarfdump -i -G -v. */
2650*4d9fdb46SRobert Mustacchi int
dwarf_die_abbrev_global_offset(Dwarf_Die die,Dwarf_Off * abbrev_goffset,Dwarf_Unsigned * abbrev_count,Dwarf_Error * error)2651*4d9fdb46SRobert Mustacchi dwarf_die_abbrev_global_offset(Dwarf_Die die,
2652*4d9fdb46SRobert Mustacchi     Dwarf_Off       * abbrev_goffset,
2653*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned  * abbrev_count,
2654*4d9fdb46SRobert Mustacchi     Dwarf_Error*      error)
2655*4d9fdb46SRobert Mustacchi {
2656*4d9fdb46SRobert Mustacchi     Dwarf_Abbrev_List dal = 0;
2657*4d9fdb46SRobert Mustacchi     Dwarf_Debug dbg = 0;
2658*4d9fdb46SRobert Mustacchi 
2659*4d9fdb46SRobert Mustacchi     CHECK_DIE(die, DW_DLV_ERROR);
2660*4d9fdb46SRobert Mustacchi     dbg = die->di_cu_context->cc_dbg;
2661*4d9fdb46SRobert Mustacchi     dal = die->di_abbrev_list;
2662*4d9fdb46SRobert Mustacchi     if(!dal) {
2663*4d9fdb46SRobert Mustacchi         _dwarf_error(dbg,error,DW_DLE_DWARF_ABBREV_NULL);
2664*4d9fdb46SRobert Mustacchi         return DW_DLV_ERROR;
2665*4d9fdb46SRobert Mustacchi     }
2666*4d9fdb46SRobert Mustacchi     *abbrev_goffset = dal->abl_goffset;
2667*4d9fdb46SRobert Mustacchi     *abbrev_count = dal->abl_count;
2668*4d9fdb46SRobert Mustacchi     return DW_DLV_OK;
2669*4d9fdb46SRobert Mustacchi }
2670*4d9fdb46SRobert Mustacchi 
2671*4d9fdb46SRobert Mustacchi 
2672*4d9fdb46SRobert Mustacchi /*  New August 2018.
2673*4d9fdb46SRobert Mustacchi     Because some real compressed sections
2674*4d9fdb46SRobert Mustacchi     have .zdebug instead
2675*4d9fdb46SRobert Mustacchi     of .debug as the leading characters.
2676*4d9fdb46SRobert Mustacchi     actual_sec_name_out points to a static
2677*4d9fdb46SRobert Mustacchi     string so so not free it. */
2678*4d9fdb46SRobert Mustacchi int
dwarf_get_real_section_name(Dwarf_Debug dbg,const char * std_section_name,const char ** actual_sec_name_out,Dwarf_Small * marked_zcompressed,Dwarf_Small * marked_zlib_compressed,Dwarf_Small * marked_shf_compressed,Dwarf_Unsigned * compressed_length,Dwarf_Unsigned * uncompressed_length,Dwarf_Error * error)2679*4d9fdb46SRobert Mustacchi dwarf_get_real_section_name(Dwarf_Debug dbg,
2680*4d9fdb46SRobert Mustacchi     const char  *std_section_name,
2681*4d9fdb46SRobert Mustacchi     const char **actual_sec_name_out,
2682*4d9fdb46SRobert Mustacchi     Dwarf_Small *marked_zcompressed, /* zdebug */
2683*4d9fdb46SRobert Mustacchi     Dwarf_Small *marked_zlib_compressed, /* ZLIB string */
2684*4d9fdb46SRobert Mustacchi     Dwarf_Small *marked_shf_compressed, /* SHF_COMPRESSED */
2685*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned *compressed_length,
2686*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned *uncompressed_length,
2687*4d9fdb46SRobert Mustacchi     Dwarf_Error *error)
2688*4d9fdb46SRobert Mustacchi {
2689*4d9fdb46SRobert Mustacchi     unsigned i = 0;
2690*4d9fdb46SRobert Mustacchi     char tbuf[50];
2691*4d9fdb46SRobert Mustacchi     unsigned std_sec_name_len = strlen(std_section_name);
2692*4d9fdb46SRobert Mustacchi 
2693*4d9fdb46SRobert Mustacchi     tbuf[0] = 0;
2694*4d9fdb46SRobert Mustacchi     /*  std_section_name never has the .dwo on the end,
2695*4d9fdb46SRobert Mustacchi         so allow for that and allow one (arbitrarily) more. */
2696*4d9fdb46SRobert Mustacchi     if ((std_sec_name_len + 5) < sizeof(tbuf)) {
2697*4d9fdb46SRobert Mustacchi         strcpy(tbuf,std_section_name);
2698*4d9fdb46SRobert Mustacchi         strcpy(tbuf+std_sec_name_len,".dwo");
2699*4d9fdb46SRobert Mustacchi     }
2700*4d9fdb46SRobert Mustacchi     if (dbg == NULL) {
2701*4d9fdb46SRobert Mustacchi         _dwarf_error(NULL, error, DW_DLE_DBG_NULL);
270207dc1947SRichard Lowe         return (DW_DLV_ERROR);
270349d3bc91SRichard Lowe     }
2704*4d9fdb46SRobert Mustacchi     for (i=0; i < dbg->de_debug_sections_total_entries; i++) {
2705*4d9fdb46SRobert Mustacchi         struct Dwarf_dbg_sect_s *sdata = &dbg->de_debug_sections[i];
2706*4d9fdb46SRobert Mustacchi         struct Dwarf_Section_s *section = sdata->ds_secdata;
2707*4d9fdb46SRobert Mustacchi         const char *std = section->dss_standard_name;
2708*4d9fdb46SRobert Mustacchi 
2709*4d9fdb46SRobert Mustacchi         if (!strcmp(std,std_section_name) ||
2710*4d9fdb46SRobert Mustacchi             !strcmp(std,tbuf)) {
2711*4d9fdb46SRobert Mustacchi             const char *used = section->dss_name;
2712*4d9fdb46SRobert Mustacchi             *actual_sec_name_out = used;
2713*4d9fdb46SRobert Mustacchi             if (sdata->ds_have_zdebug) {
2714*4d9fdb46SRobert Mustacchi                 *marked_zcompressed = TRUE;
2715*4d9fdb46SRobert Mustacchi             }
2716*4d9fdb46SRobert Mustacchi             if (section->dss_ZLIB_compressed) {
2717*4d9fdb46SRobert Mustacchi                 *marked_zlib_compressed = TRUE;
2718*4d9fdb46SRobert Mustacchi                 if (uncompressed_length) {
2719*4d9fdb46SRobert Mustacchi                     *uncompressed_length =
2720*4d9fdb46SRobert Mustacchi                         section->dss_uncompressed_length;
2721*4d9fdb46SRobert Mustacchi                 }
2722*4d9fdb46SRobert Mustacchi                 if (compressed_length) {
2723*4d9fdb46SRobert Mustacchi                     *compressed_length =
2724*4d9fdb46SRobert Mustacchi                         section->dss_compressed_length;
2725*4d9fdb46SRobert Mustacchi                 }
2726*4d9fdb46SRobert Mustacchi             }
2727*4d9fdb46SRobert Mustacchi             if (section->dss_shf_compressed) {
2728*4d9fdb46SRobert Mustacchi                 *marked_shf_compressed = TRUE;
2729*4d9fdb46SRobert Mustacchi                 if (uncompressed_length) {
2730*4d9fdb46SRobert Mustacchi                     *uncompressed_length =
2731*4d9fdb46SRobert Mustacchi                         section->dss_uncompressed_length;
2732*4d9fdb46SRobert Mustacchi                 }
2733*4d9fdb46SRobert Mustacchi                 if (compressed_length) {
2734*4d9fdb46SRobert Mustacchi                     *compressed_length =
2735*4d9fdb46SRobert Mustacchi                         section->dss_compressed_length;
2736*4d9fdb46SRobert Mustacchi                 }
2737*4d9fdb46SRobert Mustacchi             }
2738*4d9fdb46SRobert Mustacchi             return DW_DLV_OK;
2739*4d9fdb46SRobert Mustacchi         }
2740*4d9fdb46SRobert Mustacchi     }
2741*4d9fdb46SRobert Mustacchi     return DW_DLV_NO_ENTRY;
2742*4d9fdb46SRobert Mustacchi }
2743*4d9fdb46SRobert Mustacchi /*  This is useful when printing DIE data.
2744*4d9fdb46SRobert Mustacchi     The string pointer returned must not be freed.
2745*4d9fdb46SRobert Mustacchi     With non-elf objects it is possible the
2746*4d9fdb46SRobert Mustacchi     string returned might be empty or NULL,
2747*4d9fdb46SRobert Mustacchi     so callers should be prepared for that kind
2748*4d9fdb46SRobert Mustacchi     of return. */
2749*4d9fdb46SRobert Mustacchi int
dwarf_get_die_section_name(Dwarf_Debug dbg,Dwarf_Bool is_info,const char ** sec_name,Dwarf_Error * error)2750*4d9fdb46SRobert Mustacchi dwarf_get_die_section_name(Dwarf_Debug dbg,
2751*4d9fdb46SRobert Mustacchi     Dwarf_Bool    is_info,
2752*4d9fdb46SRobert Mustacchi     const char ** sec_name,
2753*4d9fdb46SRobert Mustacchi     Dwarf_Error * error)
2754*4d9fdb46SRobert Mustacchi {
2755*4d9fdb46SRobert Mustacchi     struct Dwarf_Section_s *sec = 0;
275649d3bc91SRichard Lowe 
2757*4d9fdb46SRobert Mustacchi     if (dbg == NULL) {
2758*4d9fdb46SRobert Mustacchi         _dwarf_error(NULL, error, DW_DLE_DBG_NULL);
2759*4d9fdb46SRobert Mustacchi         return (DW_DLV_ERROR);
2760*4d9fdb46SRobert Mustacchi     }
2761*4d9fdb46SRobert Mustacchi     if (is_info) {
2762*4d9fdb46SRobert Mustacchi         sec = &dbg->de_debug_info;
2763*4d9fdb46SRobert Mustacchi     } else {
2764*4d9fdb46SRobert Mustacchi         sec = &dbg->de_debug_types;
2765*4d9fdb46SRobert Mustacchi     }
2766*4d9fdb46SRobert Mustacchi     if (sec->dss_size == 0) {
2767*4d9fdb46SRobert Mustacchi         /* We don't have such a  section at all. */
2768*4d9fdb46SRobert Mustacchi         return DW_DLV_NO_ENTRY;
2769*4d9fdb46SRobert Mustacchi     }
2770*4d9fdb46SRobert Mustacchi     *sec_name = sec->dss_name;
2771*4d9fdb46SRobert Mustacchi     return DW_DLV_OK;
2772*4d9fdb46SRobert Mustacchi }
2773*4d9fdb46SRobert Mustacchi 
2774*4d9fdb46SRobert Mustacchi /* This one assumes is_info not known to caller but a DIE is known. */
2775*4d9fdb46SRobert Mustacchi int
dwarf_get_die_section_name_b(Dwarf_Die die,const char ** sec_name,Dwarf_Error * error)2776*4d9fdb46SRobert Mustacchi dwarf_get_die_section_name_b(Dwarf_Die die,
2777*4d9fdb46SRobert Mustacchi     const char ** sec_name,
2778*4d9fdb46SRobert Mustacchi     Dwarf_Error * error)
2779*4d9fdb46SRobert Mustacchi {
2780*4d9fdb46SRobert Mustacchi     Dwarf_CU_Context context = 0;
2781*4d9fdb46SRobert Mustacchi     Dwarf_Bool is_info = 0;
2782*4d9fdb46SRobert Mustacchi     Dwarf_Debug dbg = 0;
2783*4d9fdb46SRobert Mustacchi 
2784*4d9fdb46SRobert Mustacchi     CHECK_DIE(die, DW_DLV_ERROR);
2785*4d9fdb46SRobert Mustacchi     context = die->di_cu_context;
2786*4d9fdb46SRobert Mustacchi     dbg = context->cc_dbg;
2787*4d9fdb46SRobert Mustacchi     is_info = context->cc_is_info;
2788*4d9fdb46SRobert Mustacchi     return dwarf_get_die_section_name(dbg,is_info,sec_name,error);
278949d3bc91SRichard Lowe }
2790