xref: /illumos-gate/usr/src/lib/libdwarf/common/dwarf_global.c (revision 4d9fdb46b215739778ebc12079842c9905586999)
1bc1f688bSRobert Mustacchi /*
2bc1f688bSRobert Mustacchi 
3bc1f688bSRobert Mustacchi   Copyright (C) 2000-2005 Silicon Graphics, Inc.  All Rights Reserved.
4*4d9fdb46SRobert Mustacchi   Portions Copyright (C) 2007-2011 David Anderson. All Rights Reserved.
5bc1f688bSRobert 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.
10bc1f688bSRobert 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.
15bc1f688bSRobert 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.
23bc1f688bSRobert 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.
28bc1f688bSRobert Mustacchi 
29bc1f688bSRobert Mustacchi */
30bc1f688bSRobert Mustacchi 
31bc1f688bSRobert Mustacchi #include "config.h"
32bc1f688bSRobert 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"
38bc1f688bSRobert Mustacchi #include "dwarf_global.h"
39bc1f688bSRobert Mustacchi 
40bc1f688bSRobert Mustacchi 
41bc1f688bSRobert Mustacchi #ifdef __sgi  /* __sgi should only be defined for IRIX/MIPS. */
42bc1f688bSRobert Mustacchi /* The 'fixup' here intended for IRIX targets only.
43bc1f688bSRobert Mustacchi    With a  2+GB Elf64 IRIX executable (under 4GB in size),
44bc1f688bSRobert Mustacchi    some DIE offsets wrongly
45bc1f688bSRobert Mustacchi    got the 32bit upper bit sign extended.  For the cu-header
46bc1f688bSRobert Mustacchi    offset in the .debug_pubnames section  and in the
47bc1f688bSRobert Mustacchi    .debug_aranges section.
48bc1f688bSRobert Mustacchi    the 'varp' here is a pointer to an offset into .debug_info.
49bc1f688bSRobert Mustacchi    We fix up the offset here if it seems advisable..
50bc1f688bSRobert Mustacchi 
51bc1f688bSRobert Mustacchi    As of June 2005 we have identified a series of mistakes
52bc1f688bSRobert Mustacchi    in ldx64 that can cause this (64 bit values getting passed
53bc1f688bSRobert Mustacchi    thru 32-bit signed knothole).
54bc1f688bSRobert Mustacchi */
55bc1f688bSRobert Mustacchi void
_dwarf_fix_up_offset_irix(Dwarf_Debug dbg,Dwarf_Unsigned * varp,char * caller_site_name)56bc1f688bSRobert Mustacchi _dwarf_fix_up_offset_irix(Dwarf_Debug dbg,
57bc1f688bSRobert Mustacchi     Dwarf_Unsigned * varp, char *caller_site_name)
58bc1f688bSRobert Mustacchi {
59bc1f688bSRobert Mustacchi 
60bc1f688bSRobert Mustacchi     Dwarf_Unsigned var = *varp;
61bc1f688bSRobert Mustacchi 
62bc1f688bSRobert Mustacchi #define UPPER33 0xffffffff80000000LL
63bc1f688bSRobert Mustacchi #define LOWER32         0xffffffffLL
64bc1f688bSRobert Mustacchi     /*  Restrict the hack to the known case. Upper 32 bits erroneously
65bc1f688bSRobert Mustacchi         sign extended from lower 32 upper bit. */
66bc1f688bSRobert Mustacchi     if ((var & UPPER33) == UPPER33) {
67bc1f688bSRobert Mustacchi         var &= LOWER32;
68bc1f688bSRobert Mustacchi         /* Apply the fix. Dreadful hack. */
69bc1f688bSRobert Mustacchi         *varp = var;
70bc1f688bSRobert Mustacchi     }
71bc1f688bSRobert Mustacchi #undef UPPER33
72bc1f688bSRobert Mustacchi #undef LOWER32
73bc1f688bSRobert Mustacchi     return;
74bc1f688bSRobert Mustacchi }
75*4d9fdb46SRobert Mustacchi #endif  /* __sgi */
76bc1f688bSRobert Mustacchi 
77*4d9fdb46SRobert Mustacchi static void
dealloc_globals_chain(Dwarf_Debug dbg,Dwarf_Chain head_chain)78*4d9fdb46SRobert Mustacchi dealloc_globals_chain(Dwarf_Debug dbg,
79*4d9fdb46SRobert Mustacchi     Dwarf_Chain head_chain)
80*4d9fdb46SRobert Mustacchi {
81*4d9fdb46SRobert Mustacchi     Dwarf_Chain curr_chain = 0;
82*4d9fdb46SRobert Mustacchi     Dwarf_Chain prev_chain = 0;
83*4d9fdb46SRobert Mustacchi     int chaintype = DW_DLA_CHAIN;
84*4d9fdb46SRobert Mustacchi 
85*4d9fdb46SRobert Mustacchi     curr_chain = head_chain;
86*4d9fdb46SRobert Mustacchi     for (; curr_chain; ) {
87*4d9fdb46SRobert Mustacchi         void *item = curr_chain->ch_item;
88*4d9fdb46SRobert Mustacchi         int itemtype = curr_chain->ch_itemtype;
89*4d9fdb46SRobert Mustacchi 
90*4d9fdb46SRobert Mustacchi         prev_chain = curr_chain;
91*4d9fdb46SRobert Mustacchi         dwarf_dealloc(dbg, item,itemtype);
92*4d9fdb46SRobert Mustacchi         prev_chain->ch_item = 0;
93*4d9fdb46SRobert Mustacchi         curr_chain = curr_chain->ch_next;
94*4d9fdb46SRobert Mustacchi         dwarf_dealloc(dbg, prev_chain, chaintype);
95*4d9fdb46SRobert Mustacchi     }
96*4d9fdb46SRobert Mustacchi }
97bc1f688bSRobert Mustacchi 
98bc1f688bSRobert Mustacchi int
dwarf_get_globals(Dwarf_Debug dbg,Dwarf_Global ** globals,Dwarf_Signed * return_count,Dwarf_Error * error)99bc1f688bSRobert Mustacchi dwarf_get_globals(Dwarf_Debug dbg,
100bc1f688bSRobert Mustacchi     Dwarf_Global ** globals,
101bc1f688bSRobert Mustacchi     Dwarf_Signed * return_count, Dwarf_Error * error)
102bc1f688bSRobert Mustacchi {
103bc1f688bSRobert Mustacchi     int res = _dwarf_load_section(dbg, &dbg->de_debug_pubnames,error);
104bc1f688bSRobert Mustacchi     if (res != DW_DLV_OK) {
105bc1f688bSRobert Mustacchi         return res;
106bc1f688bSRobert Mustacchi     }
107*4d9fdb46SRobert Mustacchi     if (!dbg->de_debug_pubnames.dss_size) {
108*4d9fdb46SRobert Mustacchi         return DW_DLV_NO_ENTRY;
109*4d9fdb46SRobert Mustacchi     }
110bc1f688bSRobert Mustacchi 
111*4d9fdb46SRobert Mustacchi     res = _dwarf_internal_get_pubnames_like_data(dbg,
112bc1f688bSRobert Mustacchi         dbg->de_debug_pubnames.dss_data,
113bc1f688bSRobert Mustacchi         dbg->de_debug_pubnames.dss_size,
114bc1f688bSRobert Mustacchi         globals,
115bc1f688bSRobert Mustacchi         return_count,
116bc1f688bSRobert Mustacchi         error,
117bc1f688bSRobert Mustacchi         DW_DLA_GLOBAL_CONTEXT,
118bc1f688bSRobert Mustacchi         DW_DLA_GLOBAL,
119bc1f688bSRobert Mustacchi         DW_DLE_PUBNAMES_LENGTH_BAD,
120bc1f688bSRobert Mustacchi         DW_DLE_PUBNAMES_VERSION_ERROR);
121*4d9fdb46SRobert Mustacchi     return res;
122bc1f688bSRobert Mustacchi 
123bc1f688bSRobert Mustacchi }
124bc1f688bSRobert Mustacchi 
125bc1f688bSRobert Mustacchi /* Deallocating fully requires deallocating the list
126bc1f688bSRobert Mustacchi    and all entries.  But some internal data is
127bc1f688bSRobert Mustacchi    not exposed, so we need a function with internal knowledge.
128bc1f688bSRobert Mustacchi */
129bc1f688bSRobert Mustacchi 
130bc1f688bSRobert Mustacchi void
dwarf_globals_dealloc(Dwarf_Debug dbg,Dwarf_Global * dwgl,Dwarf_Signed count)131bc1f688bSRobert Mustacchi dwarf_globals_dealloc(Dwarf_Debug dbg, Dwarf_Global * dwgl,
132bc1f688bSRobert Mustacchi     Dwarf_Signed count)
133bc1f688bSRobert Mustacchi {
134bc1f688bSRobert Mustacchi     _dwarf_internal_globals_dealloc(dbg, dwgl,
135bc1f688bSRobert Mustacchi         count,
136bc1f688bSRobert Mustacchi         DW_DLA_GLOBAL_CONTEXT,
137bc1f688bSRobert Mustacchi         DW_DLA_GLOBAL, DW_DLA_LIST);
138bc1f688bSRobert Mustacchi     return;
139bc1f688bSRobert Mustacchi }
140bc1f688bSRobert Mustacchi 
141bc1f688bSRobert Mustacchi void
_dwarf_internal_globals_dealloc(Dwarf_Debug dbg,Dwarf_Global * dwgl,Dwarf_Signed count,int context_DLA_code,int global_DLA_code,int list_DLA_code)142bc1f688bSRobert Mustacchi _dwarf_internal_globals_dealloc(Dwarf_Debug dbg, Dwarf_Global * dwgl,
143bc1f688bSRobert Mustacchi     Dwarf_Signed count,
144*4d9fdb46SRobert Mustacchi     int context_DLA_code,
145*4d9fdb46SRobert Mustacchi     int global_DLA_code, int list_DLA_code)
146bc1f688bSRobert Mustacchi {
147bc1f688bSRobert Mustacchi     Dwarf_Signed i;
148*4d9fdb46SRobert Mustacchi     struct Dwarf_Global_Context_s *glcp = 0;
149*4d9fdb46SRobert Mustacchi     struct Dwarf_Global_Context_s *lastglcp = 0;
150bc1f688bSRobert Mustacchi 
151*4d9fdb46SRobert Mustacchi     if(!dwgl) {
152*4d9fdb46SRobert Mustacchi         return;
153*4d9fdb46SRobert Mustacchi     }
154bc1f688bSRobert Mustacchi     for (i = 0; i < count; i++) {
155bc1f688bSRobert Mustacchi         Dwarf_Global dgb = dwgl[i];
156bc1f688bSRobert Mustacchi 
157*4d9fdb46SRobert Mustacchi         if (!dgb) {
158*4d9fdb46SRobert Mustacchi             continue;
159bc1f688bSRobert Mustacchi         }
160*4d9fdb46SRobert Mustacchi         /*  Avoids duplicate frees of repeated
161*4d9fdb46SRobert Mustacchi             use of contexts (while assuming that
162*4d9fdb46SRobert Mustacchi             all uses of a particular gl_context
163*4d9fdb46SRobert Mustacchi             will appear next to each other. */
164*4d9fdb46SRobert Mustacchi         glcp = dgb->gl_context;
165*4d9fdb46SRobert Mustacchi         if (lastglcp != glcp) {
166*4d9fdb46SRobert Mustacchi             lastglcp = glcp;
167*4d9fdb46SRobert Mustacchi             dwarf_dealloc(dbg, glcp, context_DLA_code);
168bc1f688bSRobert Mustacchi         }
169*4d9fdb46SRobert Mustacchi         dwarf_dealloc(dbg, dgb, global_DLA_code);
170*4d9fdb46SRobert Mustacchi     }
171*4d9fdb46SRobert Mustacchi     dwarf_dealloc(dbg, dwgl, list_DLA_code);
172bc1f688bSRobert Mustacchi     return;
173bc1f688bSRobert Mustacchi }
174bc1f688bSRobert Mustacchi 
175*4d9fdb46SRobert Mustacchi /* Sweeps the complete  section.  */
176bc1f688bSRobert Mustacchi int
_dwarf_internal_get_pubnames_like_data(Dwarf_Debug dbg,Dwarf_Small * section_data_ptr,Dwarf_Unsigned section_length,Dwarf_Global ** globals,Dwarf_Signed * return_count,Dwarf_Error * error,int context_DLA_code,int global_DLA_code,int length_err_num,int version_err_num)177bc1f688bSRobert Mustacchi _dwarf_internal_get_pubnames_like_data(Dwarf_Debug dbg,
178bc1f688bSRobert Mustacchi     Dwarf_Small * section_data_ptr,
179bc1f688bSRobert Mustacchi     Dwarf_Unsigned section_length,
180bc1f688bSRobert Mustacchi     Dwarf_Global ** globals,
181bc1f688bSRobert Mustacchi     Dwarf_Signed * return_count,
182bc1f688bSRobert Mustacchi     Dwarf_Error * error,
183*4d9fdb46SRobert Mustacchi     int context_DLA_code,
184*4d9fdb46SRobert Mustacchi     int global_DLA_code,
185bc1f688bSRobert Mustacchi     int length_err_num,
186bc1f688bSRobert Mustacchi     int version_err_num)
187bc1f688bSRobert Mustacchi {
188bc1f688bSRobert Mustacchi     Dwarf_Small *pubnames_like_ptr = 0;
189*4d9fdb46SRobert Mustacchi     Dwarf_Off pubnames_section_offset = 0;
190*4d9fdb46SRobert Mustacchi     Dwarf_Small *section_end_ptr = section_data_ptr +section_length;
191bc1f688bSRobert Mustacchi 
192bc1f688bSRobert Mustacchi     /*  Points to the context for the current set of global names, and
193bc1f688bSRobert Mustacchi         contains information to identify the compilation-unit that the
194bc1f688bSRobert Mustacchi         set refers to. */
195bc1f688bSRobert Mustacchi     Dwarf_Global_Context pubnames_context = 0;
196bc1f688bSRobert Mustacchi 
197*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned version = 0;
198bc1f688bSRobert Mustacchi 
199*4d9fdb46SRobert Mustacchi     /*  Offset from the start of compilation-unit for the current
200bc1f688bSRobert Mustacchi         global. */
201bc1f688bSRobert Mustacchi     Dwarf_Off die_offset_in_cu = 0;
202bc1f688bSRobert Mustacchi 
203bc1f688bSRobert Mustacchi     Dwarf_Unsigned global_count = 0;
204bc1f688bSRobert Mustacchi 
205bc1f688bSRobert Mustacchi     /* Points to the current global read. */
206bc1f688bSRobert Mustacchi     Dwarf_Global global = 0;
207bc1f688bSRobert Mustacchi 
208bc1f688bSRobert Mustacchi     /*  Used to chain the Dwarf_Global_s structs for creating contiguous
209bc1f688bSRobert Mustacchi         list of pointers to the structs. */
210bc1f688bSRobert Mustacchi     Dwarf_Chain curr_chain = 0;
211bc1f688bSRobert Mustacchi     Dwarf_Chain prev_chain = 0;
212bc1f688bSRobert Mustacchi     Dwarf_Chain head_chain = 0;
213bc1f688bSRobert Mustacchi 
214bc1f688bSRobert Mustacchi     /* Points to contiguous block of Dwarf_Global's to be returned. */
215bc1f688bSRobert Mustacchi     Dwarf_Global *ret_globals = 0;
216*4d9fdb46SRobert Mustacchi     int mres = 0;
217bc1f688bSRobert Mustacchi 
218bc1f688bSRobert Mustacchi     /* Temporary counter. */
219bc1f688bSRobert Mustacchi     Dwarf_Unsigned i = 0;
220bc1f688bSRobert Mustacchi 
221bc1f688bSRobert Mustacchi     if (dbg == NULL) {
222bc1f688bSRobert Mustacchi         _dwarf_error(NULL, error, DW_DLE_DBG_NULL);
223bc1f688bSRobert Mustacchi         return (DW_DLV_ERROR);
224bc1f688bSRobert Mustacchi     }
225bc1f688bSRobert Mustacchi     /* We will eventually need the .debug_info data. Load it now. */
226bc1f688bSRobert Mustacchi     if (!dbg->de_debug_info.dss_data) {
227bc1f688bSRobert Mustacchi         int res = _dwarf_load_debug_info(dbg, error);
228bc1f688bSRobert Mustacchi 
229bc1f688bSRobert Mustacchi         if (res != DW_DLV_OK) {
230bc1f688bSRobert Mustacchi             return res;
231bc1f688bSRobert Mustacchi         }
232bc1f688bSRobert Mustacchi     }
233bc1f688bSRobert Mustacchi     if (section_data_ptr == NULL) {
234bc1f688bSRobert Mustacchi         return (DW_DLV_NO_ENTRY);
235bc1f688bSRobert Mustacchi     }
236bc1f688bSRobert Mustacchi     pubnames_like_ptr = section_data_ptr;
237bc1f688bSRobert Mustacchi     do {
238bc1f688bSRobert Mustacchi         Dwarf_Unsigned length = 0;
239bc1f688bSRobert Mustacchi         int local_extension_size = 0;
240bc1f688bSRobert Mustacchi         int local_length_size = 0;
241bc1f688bSRobert Mustacchi 
242bc1f688bSRobert Mustacchi         /*  Some compilers emit padding at the end of each cu's area.
243*4d9fdb46SRobert Mustacchi             pubnames_ptr_past_end_cu records the true area end for the
244*4d9fdb46SRobert Mustacchi             pubnames(like) content of a cu.
245*4d9fdb46SRobert Mustacchi             Essentially the length in the header and the 0
246bc1f688bSRobert Mustacchi             terminator of the data are redundant information. The
247bc1f688bSRobert Mustacchi             dwarf2/3 spec does not mention what to do if the length is
248bc1f688bSRobert Mustacchi             past the 0 terminator. So we take any bytes left after the 0
249bc1f688bSRobert Mustacchi             as padding and ignore them. */
250bc1f688bSRobert Mustacchi         Dwarf_Small *pubnames_ptr_past_end_cu = 0;
251bc1f688bSRobert Mustacchi 
252bc1f688bSRobert Mustacchi 
253bc1f688bSRobert Mustacchi         pubnames_context = (Dwarf_Global_Context)
254*4d9fdb46SRobert Mustacchi             _dwarf_get_alloc(dbg, context_DLA_code, 1);
255bc1f688bSRobert Mustacchi         if (pubnames_context == NULL) {
256*4d9fdb46SRobert Mustacchi             dealloc_globals_chain(dbg,head_chain);
257bc1f688bSRobert Mustacchi             _dwarf_error(dbg, error, DW_DLE_ALLOC_FAIL);
258*4d9fdb46SRobert Mustacchi             return DW_DLV_ERROR;
259bc1f688bSRobert Mustacchi         }
260bc1f688bSRobert Mustacchi         /*  READ_AREA_LENGTH updates pubnames_like_ptr for consumed
261bc1f688bSRobert Mustacchi             bytes. */
262*4d9fdb46SRobert Mustacchi         mres = _dwarf_read_area_length_ck_wrapper(dbg,
263*4d9fdb46SRobert Mustacchi             &length,&pubnames_like_ptr,&local_length_size,
264*4d9fdb46SRobert Mustacchi             &local_extension_size,section_length,section_end_ptr,
265*4d9fdb46SRobert Mustacchi             error);
266*4d9fdb46SRobert Mustacchi         if (mres != DW_DLV_OK) {
267*4d9fdb46SRobert Mustacchi             dealloc_globals_chain(dbg,head_chain);
268*4d9fdb46SRobert Mustacchi             dwarf_dealloc(dbg,pubnames_context,context_DLA_code);
269*4d9fdb46SRobert Mustacchi             return mres;
270*4d9fdb46SRobert Mustacchi         }
271bc1f688bSRobert Mustacchi         pubnames_context->pu_length_size = local_length_size;
272*4d9fdb46SRobert Mustacchi         pubnames_context->pu_length = length;
273bc1f688bSRobert Mustacchi         pubnames_context->pu_extension_size = local_extension_size;
274bc1f688bSRobert Mustacchi         pubnames_context->pu_dbg = dbg;
275*4d9fdb46SRobert Mustacchi         pubnames_context->pu_pub_offset = pubnames_section_offset;
276bc1f688bSRobert Mustacchi         pubnames_ptr_past_end_cu = pubnames_like_ptr + length;
277bc1f688bSRobert Mustacchi 
278*4d9fdb46SRobert Mustacchi         mres = _dwarf_read_unaligned_ck_wrapper(dbg,
279*4d9fdb46SRobert Mustacchi             &version,pubnames_like_ptr,DWARF_HALF_SIZE,
280*4d9fdb46SRobert Mustacchi             section_end_ptr,error);
281*4d9fdb46SRobert Mustacchi         if (mres != DW_DLV_OK) {
282*4d9fdb46SRobert Mustacchi             dealloc_globals_chain(dbg,head_chain);
283*4d9fdb46SRobert Mustacchi             dwarf_dealloc(dbg,pubnames_context,context_DLA_code);
284*4d9fdb46SRobert Mustacchi             return mres;
285*4d9fdb46SRobert Mustacchi         }
286*4d9fdb46SRobert Mustacchi         pubnames_context->pu_version = version;
287*4d9fdb46SRobert Mustacchi         pubnames_like_ptr += DWARF_HALF_SIZE;
288*4d9fdb46SRobert Mustacchi         /* ASSERT: DW_PUBNAMES_VERSION2 == DW_PUBTYPES_VERSION2 */
289*4d9fdb46SRobert Mustacchi         if (version != DW_PUBNAMES_VERSION2) {
290*4d9fdb46SRobert Mustacchi             dealloc_globals_chain(dbg,head_chain);
291*4d9fdb46SRobert Mustacchi             dwarf_dealloc(dbg,pubnames_context,context_DLA_code);
292bc1f688bSRobert Mustacchi             _dwarf_error(dbg, error, version_err_num);
293*4d9fdb46SRobert Mustacchi             return DW_DLV_ERROR;
294bc1f688bSRobert Mustacchi         }
295bc1f688bSRobert Mustacchi 
296bc1f688bSRobert Mustacchi         /* Offset of CU header in debug section. */
297*4d9fdb46SRobert Mustacchi         mres = _dwarf_read_unaligned_ck_wrapper(dbg,
298*4d9fdb46SRobert Mustacchi             &pubnames_context->pu_offset_of_cu_header,
299*4d9fdb46SRobert Mustacchi             pubnames_like_ptr,
300*4d9fdb46SRobert Mustacchi             pubnames_context->pu_length_size,
301*4d9fdb46SRobert Mustacchi             section_end_ptr,error);
302*4d9fdb46SRobert Mustacchi         if (mres != DW_DLV_OK) {
303*4d9fdb46SRobert Mustacchi             dealloc_globals_chain(dbg,head_chain);
304*4d9fdb46SRobert Mustacchi             dwarf_dealloc(dbg,pubnames_context,context_DLA_code);
305*4d9fdb46SRobert Mustacchi             return mres;
306*4d9fdb46SRobert Mustacchi         }
307*4d9fdb46SRobert Mustacchi 
308bc1f688bSRobert Mustacchi         pubnames_like_ptr += pubnames_context->pu_length_size;
309bc1f688bSRobert Mustacchi 
310bc1f688bSRobert Mustacchi         FIX_UP_OFFSET_IRIX_BUG(dbg,
311bc1f688bSRobert Mustacchi             pubnames_context->pu_offset_of_cu_header,
312bc1f688bSRobert Mustacchi             "pubnames cu header offset");
313*4d9fdb46SRobert Mustacchi         mres = _dwarf_read_unaligned_ck_wrapper(dbg,
314*4d9fdb46SRobert Mustacchi             &pubnames_context->pu_info_length,
315*4d9fdb46SRobert Mustacchi             pubnames_like_ptr,
316*4d9fdb46SRobert Mustacchi             pubnames_context->pu_length_size,
317*4d9fdb46SRobert Mustacchi             section_end_ptr,error);
318*4d9fdb46SRobert Mustacchi         if (mres != DW_DLV_OK) {
319*4d9fdb46SRobert Mustacchi             dealloc_globals_chain(dbg,head_chain);
320*4d9fdb46SRobert Mustacchi             dwarf_dealloc(dbg,pubnames_context,context_DLA_code);
321*4d9fdb46SRobert Mustacchi             return mres;
322*4d9fdb46SRobert Mustacchi         }
323bc1f688bSRobert Mustacchi         pubnames_like_ptr += pubnames_context->pu_length_size;
324bc1f688bSRobert Mustacchi 
325bc1f688bSRobert Mustacchi         if (pubnames_like_ptr > (section_data_ptr + section_length)) {
326*4d9fdb46SRobert Mustacchi             dealloc_globals_chain(dbg,head_chain);
327*4d9fdb46SRobert Mustacchi             dwarf_dealloc(dbg,pubnames_context,context_DLA_code);
328bc1f688bSRobert Mustacchi             _dwarf_error(dbg, error, length_err_num);
329bc1f688bSRobert Mustacchi             return (DW_DLV_ERROR);
330bc1f688bSRobert Mustacchi         }
331bc1f688bSRobert Mustacchi 
332bc1f688bSRobert Mustacchi         /*  Read initial offset (of DIE within CU) of a pubname, final
333bc1f688bSRobert Mustacchi             entry is not a pair, just a zero offset. */
334*4d9fdb46SRobert Mustacchi         mres = _dwarf_read_unaligned_ck_wrapper(dbg,
335*4d9fdb46SRobert Mustacchi             &die_offset_in_cu,
336bc1f688bSRobert Mustacchi             pubnames_like_ptr,
337*4d9fdb46SRobert Mustacchi             pubnames_context->pu_length_size,
338*4d9fdb46SRobert Mustacchi             section_end_ptr,error);
339*4d9fdb46SRobert Mustacchi         if (mres != DW_DLV_OK) {
340*4d9fdb46SRobert Mustacchi             dealloc_globals_chain(dbg,head_chain);
341*4d9fdb46SRobert Mustacchi             dwarf_dealloc(dbg,pubnames_context,context_DLA_code);
342*4d9fdb46SRobert Mustacchi             return mres;
343*4d9fdb46SRobert Mustacchi         }
344bc1f688bSRobert Mustacchi         pubnames_like_ptr += pubnames_context->pu_length_size;
345bc1f688bSRobert Mustacchi         FIX_UP_OFFSET_IRIX_BUG(dbg,
346bc1f688bSRobert Mustacchi             die_offset_in_cu, "offset of die in cu");
347*4d9fdb46SRobert Mustacchi         if (pubnames_like_ptr > (section_data_ptr + section_length)) {
348*4d9fdb46SRobert Mustacchi             dealloc_globals_chain(dbg,head_chain);
349*4d9fdb46SRobert Mustacchi             dwarf_dealloc(dbg,pubnames_context,context_DLA_code);
350*4d9fdb46SRobert Mustacchi             _dwarf_error(dbg, error, length_err_num);
351*4d9fdb46SRobert Mustacchi             return DW_DLV_ERROR;
352*4d9fdb46SRobert Mustacchi         }
353bc1f688bSRobert Mustacchi 
354bc1f688bSRobert Mustacchi         /* Loop thru pairs. DIE off with CU followed by string. */
355*4d9fdb46SRobert Mustacchi         if (dbg->de_return_empty_pubnames && die_offset_in_cu == 0) {
356*4d9fdb46SRobert Mustacchi             /*  Here we have a pubnames CU with no actual
357*4d9fdb46SRobert Mustacchi                 entries so we fake up an entry to hold the
358*4d9fdb46SRobert Mustacchi                 header data.  There are no 'pairs' here,
359*4d9fdb46SRobert Mustacchi                 just the end of list zero value.  We do this
360*4d9fdb46SRobert Mustacchi                 only if de_return_empty_pubnames is set
361*4d9fdb46SRobert Mustacchi                 so that we by default return exactly the same
362*4d9fdb46SRobert Mustacchi                 data this always returned, yet dwarfdump can
363*4d9fdb46SRobert Mustacchi                 request the empty-cu records get created
364*4d9fdb46SRobert Mustacchi                 to test that feature.
365*4d9fdb46SRobert Mustacchi                 see dwarf_get_globals_header()  */
366bc1f688bSRobert Mustacchi             global =
367*4d9fdb46SRobert Mustacchi                 (Dwarf_Global) _dwarf_get_alloc(dbg, global_DLA_code, 1);
368bc1f688bSRobert Mustacchi             if (global == NULL) {
369*4d9fdb46SRobert Mustacchi                 dealloc_globals_chain(dbg,head_chain);
370*4d9fdb46SRobert Mustacchi                 dwarf_dealloc(dbg,pubnames_context,context_DLA_code);
371bc1f688bSRobert Mustacchi                 _dwarf_error(dbg, error, DW_DLE_ALLOC_FAIL);
372bc1f688bSRobert Mustacchi                 return (DW_DLV_ERROR);
373bc1f688bSRobert Mustacchi             }
374bc1f688bSRobert Mustacchi             global_count++;
375bc1f688bSRobert Mustacchi             global->gl_context = pubnames_context;
376*4d9fdb46SRobert Mustacchi             global->gl_named_die_offset_within_cu = 0;
377*4d9fdb46SRobert Mustacchi             global->gl_name = (Dwarf_Small *)"";
378*4d9fdb46SRobert Mustacchi             /* Finish off current entry chain */
379bc1f688bSRobert Mustacchi             curr_chain =
380bc1f688bSRobert Mustacchi                 (Dwarf_Chain) _dwarf_get_alloc(dbg, DW_DLA_CHAIN, 1);
381bc1f688bSRobert Mustacchi             if (curr_chain == NULL) {
382*4d9fdb46SRobert Mustacchi                 dealloc_globals_chain(dbg,head_chain);
383*4d9fdb46SRobert Mustacchi                 dwarf_dealloc(dbg,pubnames_context,context_DLA_code);
384*4d9fdb46SRobert Mustacchi                 _dwarf_error(dbg, error, DW_DLE_ALLOC_FAIL);
385*4d9fdb46SRobert Mustacchi                 return DW_DLV_ERROR;
386*4d9fdb46SRobert Mustacchi             }
387*4d9fdb46SRobert Mustacchi             /* Put current global on singly_linked list. */
388*4d9fdb46SRobert Mustacchi             curr_chain->ch_itemtype = global_DLA_code;
389*4d9fdb46SRobert Mustacchi             curr_chain->ch_item = (Dwarf_Global) global;
390*4d9fdb46SRobert Mustacchi             if (head_chain == NULL)
391*4d9fdb46SRobert Mustacchi                 head_chain = prev_chain = curr_chain;
392*4d9fdb46SRobert Mustacchi             else {
393*4d9fdb46SRobert Mustacchi                 prev_chain->ch_next = curr_chain;
394*4d9fdb46SRobert Mustacchi                 prev_chain = curr_chain;
395*4d9fdb46SRobert Mustacchi             }
396*4d9fdb46SRobert Mustacchi             /* There is no next entry, we are at it already */
397*4d9fdb46SRobert Mustacchi         } else if (!die_offset_in_cu) {
398*4d9fdb46SRobert Mustacchi             /*  The section is empty.
399*4d9fdb46SRobert Mustacchi                 Nowhere to record pubnames_context); */
400*4d9fdb46SRobert Mustacchi             dwarf_dealloc(dbg,pubnames_context,context_DLA_code);
401*4d9fdb46SRobert Mustacchi             pubnames_context = 0;
402*4d9fdb46SRobert Mustacchi             continue;
403*4d9fdb46SRobert Mustacchi         }
404*4d9fdb46SRobert Mustacchi         while (die_offset_in_cu) {
405*4d9fdb46SRobert Mustacchi             int res = 0;
406*4d9fdb46SRobert Mustacchi 
407*4d9fdb46SRobert Mustacchi             /*  Already read offset, pubnames_like_ptr
408*4d9fdb46SRobert Mustacchi                 now points to the string. */
409*4d9fdb46SRobert Mustacchi             global =
410*4d9fdb46SRobert Mustacchi                 (Dwarf_Global) _dwarf_get_alloc(dbg, global_DLA_code, 1);
411*4d9fdb46SRobert Mustacchi             if (global == NULL) {
412*4d9fdb46SRobert Mustacchi                 dealloc_globals_chain(dbg,head_chain);
413*4d9fdb46SRobert Mustacchi                 dwarf_dealloc(dbg,pubnames_context,context_DLA_code);
414bc1f688bSRobert Mustacchi                 _dwarf_error(dbg, error, DW_DLE_ALLOC_FAIL);
415bc1f688bSRobert Mustacchi                 return (DW_DLV_ERROR);
416bc1f688bSRobert Mustacchi             }
417*4d9fdb46SRobert Mustacchi             global_count++;
418*4d9fdb46SRobert Mustacchi             global->gl_context = pubnames_context;
419*4d9fdb46SRobert Mustacchi             global->gl_named_die_offset_within_cu = die_offset_in_cu;
420*4d9fdb46SRobert Mustacchi             global->gl_name = pubnames_like_ptr;
421*4d9fdb46SRobert Mustacchi             res = _dwarf_check_string_valid(dbg,section_data_ptr,
422*4d9fdb46SRobert Mustacchi                 pubnames_like_ptr,section_end_ptr,
423*4d9fdb46SRobert Mustacchi                 DW_DLE_STRING_OFF_END_PUBNAMES_LIKE,error);
424*4d9fdb46SRobert Mustacchi             if (res != DW_DLV_OK) {
425*4d9fdb46SRobert Mustacchi                 dealloc_globals_chain(dbg,head_chain);
426*4d9fdb46SRobert Mustacchi                 dwarf_dealloc(dbg,pubnames_context,context_DLA_code);
427*4d9fdb46SRobert Mustacchi                 return res;
428*4d9fdb46SRobert Mustacchi             }
429*4d9fdb46SRobert Mustacchi             pubnames_like_ptr = pubnames_like_ptr +
430*4d9fdb46SRobert Mustacchi                 strlen((char *) pubnames_like_ptr) + 1;
431bc1f688bSRobert Mustacchi 
432*4d9fdb46SRobert Mustacchi             /* Finish off current entry chain */
433*4d9fdb46SRobert Mustacchi             curr_chain =
434*4d9fdb46SRobert Mustacchi                 (Dwarf_Chain) _dwarf_get_alloc(dbg, DW_DLA_CHAIN, 1);
435*4d9fdb46SRobert Mustacchi             if (curr_chain == NULL) {
436*4d9fdb46SRobert Mustacchi                 dealloc_globals_chain(dbg,head_chain);
437*4d9fdb46SRobert Mustacchi                 dwarf_dealloc(dbg,pubnames_context,context_DLA_code);
438*4d9fdb46SRobert Mustacchi                 _dwarf_error(dbg, error, DW_DLE_ALLOC_FAIL);
439*4d9fdb46SRobert Mustacchi                 return (DW_DLV_ERROR);
440*4d9fdb46SRobert Mustacchi             }
441bc1f688bSRobert Mustacchi             /* Put current global on singly_linked list. */
442bc1f688bSRobert Mustacchi             curr_chain->ch_item = (Dwarf_Global) global;
443*4d9fdb46SRobert Mustacchi             curr_chain->ch_itemtype = global_DLA_code;
444bc1f688bSRobert Mustacchi             if (head_chain == NULL)
445bc1f688bSRobert Mustacchi                 head_chain = prev_chain = curr_chain;
446bc1f688bSRobert Mustacchi             else {
447bc1f688bSRobert Mustacchi                 prev_chain->ch_next = curr_chain;
448bc1f688bSRobert Mustacchi                 prev_chain = curr_chain;
449bc1f688bSRobert Mustacchi             }
450bc1f688bSRobert Mustacchi 
451*4d9fdb46SRobert Mustacchi             /* Read offset for the *next* entry */
452*4d9fdb46SRobert Mustacchi             mres = _dwarf_read_unaligned_ck_wrapper(dbg,
453*4d9fdb46SRobert Mustacchi                 &die_offset_in_cu,
454bc1f688bSRobert Mustacchi                 pubnames_like_ptr,
455*4d9fdb46SRobert Mustacchi                 pubnames_context->pu_length_size,
456*4d9fdb46SRobert Mustacchi                 section_end_ptr,error);
457*4d9fdb46SRobert Mustacchi             if (mres != DW_DLV_OK) {
458*4d9fdb46SRobert Mustacchi                 dealloc_globals_chain(dbg,head_chain);
459*4d9fdb46SRobert Mustacchi                 dwarf_dealloc(dbg,pubnames_context,context_DLA_code);
460*4d9fdb46SRobert Mustacchi                 return mres;
461*4d9fdb46SRobert Mustacchi             }
462bc1f688bSRobert Mustacchi             pubnames_like_ptr += pubnames_context->pu_length_size;
463bc1f688bSRobert Mustacchi             FIX_UP_OFFSET_IRIX_BUG(dbg,
464*4d9fdb46SRobert Mustacchi                 die_offset_in_cu, "offset of next die in cu");
465bc1f688bSRobert Mustacchi             if (pubnames_like_ptr > (section_data_ptr + section_length)) {
466*4d9fdb46SRobert Mustacchi                 dealloc_globals_chain(dbg,head_chain);
467*4d9fdb46SRobert Mustacchi                 dwarf_dealloc(dbg,pubnames_context,context_DLA_code);
468bc1f688bSRobert Mustacchi                 _dwarf_error(dbg, error, length_err_num);
469*4d9fdb46SRobert Mustacchi                 return DW_DLV_ERROR;
470bc1f688bSRobert Mustacchi             }
471bc1f688bSRobert Mustacchi         }
472bc1f688bSRobert Mustacchi         /* ASSERT: die_offset_in_cu == 0 */
473bc1f688bSRobert Mustacchi         if (pubnames_like_ptr > pubnames_ptr_past_end_cu) {
474bc1f688bSRobert Mustacchi             /* This is some kind of error. This simply cannot happen.
475bc1f688bSRobert Mustacchi             The encoding is wrong or the length in the header for
476bc1f688bSRobert Mustacchi             this cu's contribution is wrong. */
477bc1f688bSRobert Mustacchi             _dwarf_error(dbg, error, length_err_num);
478*4d9fdb46SRobert Mustacchi             dealloc_globals_chain(dbg,head_chain);
479*4d9fdb46SRobert Mustacchi             dwarf_dealloc(dbg,pubnames_context,context_DLA_code);
480*4d9fdb46SRobert Mustacchi             return DW_DLV_ERROR;
481bc1f688bSRobert Mustacchi         }
482bc1f688bSRobert Mustacchi         /*  If there is some kind of padding at the end of the section,
483bc1f688bSRobert Mustacchi             as emitted by some compilers, skip over that padding and
484bc1f688bSRobert Mustacchi             simply ignore the bytes thus passed-over.  With most
485bc1f688bSRobert Mustacchi             compilers, pubnames_like_ptr == pubnames_ptr_past_end_cu at
486bc1f688bSRobert Mustacchi             this point */
487*4d9fdb46SRobert Mustacchi         {
488*4d9fdb46SRobert Mustacchi             Dwarf_Unsigned increment =
489*4d9fdb46SRobert Mustacchi                 pubnames_context->pu_length_size +
490*4d9fdb46SRobert Mustacchi                 pubnames_context->pu_length +
491*4d9fdb46SRobert Mustacchi                 pubnames_context->pu_extension_size;
492*4d9fdb46SRobert Mustacchi             pubnames_section_offset += increment;
493*4d9fdb46SRobert Mustacchi         }
494bc1f688bSRobert Mustacchi         pubnames_like_ptr = pubnames_ptr_past_end_cu;
495*4d9fdb46SRobert Mustacchi     } while (pubnames_like_ptr < section_end_ptr);
496bc1f688bSRobert Mustacchi 
497bc1f688bSRobert Mustacchi     /* Points to contiguous block of Dwarf_Global's. */
498bc1f688bSRobert Mustacchi     ret_globals = (Dwarf_Global *)
499bc1f688bSRobert Mustacchi         _dwarf_get_alloc(dbg, DW_DLA_LIST, global_count);
500bc1f688bSRobert Mustacchi     if (ret_globals == NULL) {
501*4d9fdb46SRobert Mustacchi         dealloc_globals_chain(dbg,head_chain);
502*4d9fdb46SRobert Mustacchi         dwarf_dealloc(dbg,pubnames_context,context_DLA_code);
503bc1f688bSRobert Mustacchi         _dwarf_error(dbg, error, DW_DLE_ALLOC_FAIL);
504*4d9fdb46SRobert Mustacchi         return DW_DLV_ERROR;
505bc1f688bSRobert Mustacchi     }
506bc1f688bSRobert Mustacchi 
507*4d9fdb46SRobert Mustacchi     /*  Store pointers to Dwarf_Global_s structs in contiguous block,
508*4d9fdb46SRobert Mustacchi         and deallocate the chain.  This ignores the various
509*4d9fdb46SRobert Mustacchi         headers */
510bc1f688bSRobert Mustacchi     curr_chain = head_chain;
511bc1f688bSRobert Mustacchi     for (i = 0; i < global_count; i++) {
512bc1f688bSRobert Mustacchi         *(ret_globals + i) = curr_chain->ch_item;
513bc1f688bSRobert Mustacchi         prev_chain = curr_chain;
514bc1f688bSRobert Mustacchi         curr_chain = curr_chain->ch_next;
515*4d9fdb46SRobert Mustacchi         prev_chain->ch_item = 0; /* Not actually necessary. */
516bc1f688bSRobert Mustacchi         dwarf_dealloc(dbg, prev_chain, DW_DLA_CHAIN);
517bc1f688bSRobert Mustacchi     }
518bc1f688bSRobert Mustacchi     *globals = ret_globals;
519bc1f688bSRobert Mustacchi     *return_count = (Dwarf_Signed) global_count;
520bc1f688bSRobert Mustacchi     return DW_DLV_OK;
521bc1f688bSRobert Mustacchi }
522bc1f688bSRobert Mustacchi 
523bc1f688bSRobert Mustacchi 
524*4d9fdb46SRobert Mustacchi /*  Given a pubnames entry (or other like section entry)
525bc1f688bSRobert Mustacchi     return thru the ret_name pointer
526*4d9fdb46SRobert Mustacchi     a pointer to the string which is the entry name.  */
527bc1f688bSRobert Mustacchi int
dwarf_globname(Dwarf_Global glob,char ** ret_name,Dwarf_Error * error)528bc1f688bSRobert Mustacchi dwarf_globname(Dwarf_Global glob, char **ret_name, Dwarf_Error * error)
529bc1f688bSRobert Mustacchi {
530bc1f688bSRobert Mustacchi     if (glob == NULL) {
531bc1f688bSRobert Mustacchi         _dwarf_error(NULL, error, DW_DLE_GLOBAL_NULL);
532bc1f688bSRobert Mustacchi         return (DW_DLV_ERROR);
533bc1f688bSRobert Mustacchi     }
534bc1f688bSRobert Mustacchi 
535bc1f688bSRobert Mustacchi     *ret_name = (char *) (glob->gl_name);
536bc1f688bSRobert Mustacchi     return DW_DLV_OK;
537bc1f688bSRobert Mustacchi }
538bc1f688bSRobert Mustacchi 
539bc1f688bSRobert Mustacchi 
540*4d9fdb46SRobert Mustacchi /*  Given a pubnames entry (or other like section entry)
541bc1f688bSRobert Mustacchi     return thru the ret_off pointer the
542bc1f688bSRobert Mustacchi     global offset of the DIE for this entry.
543bc1f688bSRobert Mustacchi     The global offset is the offset within the .debug_info
544*4d9fdb46SRobert Mustacchi     section as a whole.  */
545bc1f688bSRobert Mustacchi int
dwarf_global_die_offset(Dwarf_Global global,Dwarf_Off * ret_off,Dwarf_Error * error)546bc1f688bSRobert Mustacchi dwarf_global_die_offset(Dwarf_Global global,
547bc1f688bSRobert Mustacchi     Dwarf_Off * ret_off, Dwarf_Error * error)
548bc1f688bSRobert Mustacchi {
549bc1f688bSRobert Mustacchi     if (global == NULL) {
550bc1f688bSRobert Mustacchi         _dwarf_error(NULL, error, DW_DLE_GLOBAL_NULL);
551bc1f688bSRobert Mustacchi         return (DW_DLV_ERROR);
552bc1f688bSRobert Mustacchi     }
553bc1f688bSRobert Mustacchi 
554bc1f688bSRobert Mustacchi     if (global->gl_context == NULL) {
555bc1f688bSRobert Mustacchi         _dwarf_error(NULL, error, DW_DLE_GLOBAL_CONTEXT_NULL);
556bc1f688bSRobert Mustacchi         return (DW_DLV_ERROR);
557bc1f688bSRobert Mustacchi     }
558bc1f688bSRobert Mustacchi 
559bc1f688bSRobert Mustacchi     *ret_off = (global->gl_named_die_offset_within_cu +
560bc1f688bSRobert Mustacchi         global->gl_context->pu_offset_of_cu_header);
561bc1f688bSRobert Mustacchi     return DW_DLV_OK;
562bc1f688bSRobert Mustacchi }
563bc1f688bSRobert Mustacchi 
564*4d9fdb46SRobert Mustacchi /*  Given a pubnames entry (or other like section entry)
565bc1f688bSRobert Mustacchi     return thru the ret_off pointer the
566bc1f688bSRobert Mustacchi     offset of the compilation unit header of the
567bc1f688bSRobert Mustacchi     compilation unit the global is part of.
568bc1f688bSRobert Mustacchi 
569bc1f688bSRobert Mustacchi     In early versions of this, the value returned was
570bc1f688bSRobert Mustacchi     the offset of the compilation unit die, and
571bc1f688bSRobert Mustacchi     other cu-local die offsets were faked so adding this to
572bc1f688bSRobert Mustacchi     such a cu-local offset got a true section offset.
573bc1f688bSRobert Mustacchi     Now things do as they say (adding *cu_header_offset to
574*4d9fdb46SRobert Mustacchi     a cu-local offset gets the section offset).  */
575bc1f688bSRobert Mustacchi int
dwarf_global_cu_offset(Dwarf_Global global,Dwarf_Off * cu_header_offset,Dwarf_Error * error)576bc1f688bSRobert Mustacchi dwarf_global_cu_offset(Dwarf_Global global,
577bc1f688bSRobert Mustacchi     Dwarf_Off * cu_header_offset,
578bc1f688bSRobert Mustacchi     Dwarf_Error * error)
579bc1f688bSRobert Mustacchi {
580bc1f688bSRobert Mustacchi     Dwarf_Global_Context con = 0;
581bc1f688bSRobert Mustacchi 
582bc1f688bSRobert Mustacchi     if (global == NULL) {
583bc1f688bSRobert Mustacchi         _dwarf_error(NULL, error, DW_DLE_GLOBAL_NULL);
584bc1f688bSRobert Mustacchi         return (DW_DLV_ERROR);
585bc1f688bSRobert Mustacchi     }
586bc1f688bSRobert Mustacchi 
587bc1f688bSRobert Mustacchi     con = global->gl_context;
588bc1f688bSRobert Mustacchi 
589bc1f688bSRobert Mustacchi     if (con == NULL) {
590bc1f688bSRobert Mustacchi         _dwarf_error(NULL, error, DW_DLE_GLOBAL_CONTEXT_NULL);
591bc1f688bSRobert Mustacchi         return (DW_DLV_ERROR);
592bc1f688bSRobert Mustacchi     }
593bc1f688bSRobert Mustacchi 
594bc1f688bSRobert Mustacchi     /*  In early libdwarf, this incorrectly returned the offset of the
595bc1f688bSRobert Mustacchi         CU DIE. Now correctly returns the header offset. */
596bc1f688bSRobert Mustacchi     *cu_header_offset = con->pu_offset_of_cu_header;
597bc1f688bSRobert Mustacchi 
598bc1f688bSRobert Mustacchi     return DW_DLV_OK;
599bc1f688bSRobert Mustacchi }
600bc1f688bSRobert Mustacchi 
601*4d9fdb46SRobert Mustacchi static void
build_off_end_msg(Dwarf_Unsigned offval,Dwarf_Unsigned withincr,Dwarf_Unsigned secsize,dwarfstring * m)602*4d9fdb46SRobert Mustacchi build_off_end_msg(Dwarf_Unsigned offval,
603*4d9fdb46SRobert Mustacchi    Dwarf_Unsigned withincr,
604*4d9fdb46SRobert Mustacchi    Dwarf_Unsigned secsize,
605*4d9fdb46SRobert Mustacchi    dwarfstring *m)
606*4d9fdb46SRobert Mustacchi {
607*4d9fdb46SRobert Mustacchi     const char *msg = "past";
608*4d9fdb46SRobert Mustacchi     if (offval < secsize){
609*4d9fdb46SRobert Mustacchi         msg = "too near";
610*4d9fdb46SRobert Mustacchi     }
611*4d9fdb46SRobert Mustacchi     dwarfstring_append_printf_u(m,"DW_DLE_OFFSET_BAD: "
612*4d9fdb46SRobert Mustacchi         "The CU header offset of %u in a pubnames-like entry ",
613*4d9fdb46SRobert Mustacchi         withincr);
614*4d9fdb46SRobert Mustacchi     dwarfstring_append_printf_s(m,
615*4d9fdb46SRobert Mustacchi         "would put us %s the end of .debug_info. "
616*4d9fdb46SRobert Mustacchi         "No room for a DIE there... "
617*4d9fdb46SRobert Mustacchi         "Corrupt Dwarf.",(char *)msg);
618*4d9fdb46SRobert Mustacchi     return;
619*4d9fdb46SRobert Mustacchi }
620*4d9fdb46SRobert Mustacchi 
621*4d9fdb46SRobert Mustacchi 
622bc1f688bSRobert Mustacchi /*
623bc1f688bSRobert Mustacchi   Give back the pubnames entry (or any other like section)
624bc1f688bSRobert Mustacchi   name, symbol DIE offset, and the cu-DIE offset.
625bc1f688bSRobert Mustacchi 
626bc1f688bSRobert Mustacchi   Various errors are possible.
627bc1f688bSRobert Mustacchi 
628bc1f688bSRobert Mustacchi   The string pointer returned thru ret_name is not
629bc1f688bSRobert Mustacchi   dwarf_get_alloc()ed, so no dwarf_dealloc()
630bc1f688bSRobert Mustacchi   DW_DLA_STRING should be applied to it.
631bc1f688bSRobert Mustacchi 
632bc1f688bSRobert Mustacchi */
633bc1f688bSRobert Mustacchi int
dwarf_global_name_offsets(Dwarf_Global global,char ** ret_name,Dwarf_Off * die_offset,Dwarf_Off * cu_die_offset,Dwarf_Error * error)634bc1f688bSRobert Mustacchi dwarf_global_name_offsets(Dwarf_Global global,
635bc1f688bSRobert Mustacchi     char **ret_name,
636bc1f688bSRobert Mustacchi     Dwarf_Off * die_offset,
637bc1f688bSRobert Mustacchi     Dwarf_Off * cu_die_offset,
638bc1f688bSRobert Mustacchi     Dwarf_Error * error)
639bc1f688bSRobert Mustacchi {
640bc1f688bSRobert Mustacchi     Dwarf_Global_Context con = 0;
641bc1f688bSRobert Mustacchi     Dwarf_Debug dbg = 0;
642*4d9fdb46SRobert Mustacchi     Dwarf_Off cuhdr_off = 0;
643bc1f688bSRobert Mustacchi 
644bc1f688bSRobert Mustacchi     if (global == NULL) {
645bc1f688bSRobert Mustacchi         _dwarf_error(NULL, error, DW_DLE_GLOBAL_NULL);
646bc1f688bSRobert Mustacchi         return (DW_DLV_ERROR);
647bc1f688bSRobert Mustacchi     }
648bc1f688bSRobert Mustacchi 
649bc1f688bSRobert Mustacchi     con = global->gl_context;
650bc1f688bSRobert Mustacchi 
651bc1f688bSRobert Mustacchi     if (con == NULL) {
652bc1f688bSRobert Mustacchi         _dwarf_error(NULL, error, DW_DLE_GLOBAL_CONTEXT_NULL);
653bc1f688bSRobert Mustacchi         return (DW_DLV_ERROR);
654bc1f688bSRobert Mustacchi     }
655bc1f688bSRobert Mustacchi 
656*4d9fdb46SRobert Mustacchi     cuhdr_off = con->pu_offset_of_cu_header;
657bc1f688bSRobert Mustacchi     /*  The offset had better not be too close to the end. If it is,
658bc1f688bSRobert Mustacchi         _dwarf_length_of_cu_header() will step off the end and therefore
659bc1f688bSRobert Mustacchi         must not be used. 10 is a meaningless heuristic, but no CU
660bc1f688bSRobert Mustacchi         header is that small so it is safe. An erroneous offset is due
661bc1f688bSRobert Mustacchi         to a bug in the tool chain. A bug like this has been seen on
662bc1f688bSRobert Mustacchi         IRIX with MIPSpro 7.3.1.3 and an executable > 2GB in size and
663bc1f688bSRobert Mustacchi         with 2 million pubnames entries. */
664bc1f688bSRobert Mustacchi #define MIN_CU_HDR_SIZE 10
665bc1f688bSRobert Mustacchi     dbg = con->pu_dbg;
666bc1f688bSRobert Mustacchi     if (dbg == NULL) {
667bc1f688bSRobert Mustacchi         _dwarf_error(NULL, error, DW_DLE_DBG_NULL);
668bc1f688bSRobert Mustacchi         return (DW_DLV_ERROR);
669bc1f688bSRobert Mustacchi     }
670*4d9fdb46SRobert Mustacchi     /* Cannot refer to debug_types */
671bc1f688bSRobert Mustacchi     if (dbg->de_debug_info.dss_size &&
672*4d9fdb46SRobert Mustacchi         ((cuhdr_off + MIN_CU_HDR_SIZE) >= dbg->de_debug_info.dss_size)) {
673*4d9fdb46SRobert Mustacchi         dwarfstring m;
674*4d9fdb46SRobert Mustacchi         dwarfstring_constructor(&m);
675*4d9fdb46SRobert Mustacchi         build_off_end_msg(cuhdr_off,cuhdr_off+MIN_CU_HDR_SIZE,
676*4d9fdb46SRobert Mustacchi             dbg->de_debug_info.dss_size,&m);
677*4d9fdb46SRobert Mustacchi         _dwarf_error_string(dbg, error, DW_DLE_OFFSET_BAD,
678*4d9fdb46SRobert Mustacchi             dwarfstring_string(&m));
679*4d9fdb46SRobert Mustacchi         dwarfstring_destructor(&m);
680bc1f688bSRobert Mustacchi         return (DW_DLV_ERROR);
681bc1f688bSRobert Mustacchi     }
682bc1f688bSRobert Mustacchi #undef MIN_CU_HDR_SIZE
683*4d9fdb46SRobert Mustacchi     /*  If global->gl_named_die_offset_within_cu
684*4d9fdb46SRobert Mustacchi         is zero then this is a fake global for
685*4d9fdb46SRobert Mustacchi         a pubnames CU with no pubnames. The offset is from the
686*4d9fdb46SRobert Mustacchi         start of the CU header, so no die can have a zero
687*4d9fdb46SRobert Mustacchi         offset, all valid offsets are positive numbers */
688*4d9fdb46SRobert Mustacchi     if (die_offset) {
689*4d9fdb46SRobert Mustacchi         if(global->gl_named_die_offset_within_cu) {
690*4d9fdb46SRobert Mustacchi             *die_offset = global->gl_named_die_offset_within_cu + cuhdr_off;
691*4d9fdb46SRobert Mustacchi         } else {
692*4d9fdb46SRobert Mustacchi             *die_offset = 0;
693bc1f688bSRobert Mustacchi         }
694*4d9fdb46SRobert Mustacchi     }
695bc1f688bSRobert Mustacchi     *ret_name = (char *) global->gl_name;
696*4d9fdb46SRobert Mustacchi     if (cu_die_offset) {
697*4d9fdb46SRobert Mustacchi         /* Globals cannot refer to debug_types */
698*4d9fdb46SRobert Mustacchi         int cres = 0;
699*4d9fdb46SRobert Mustacchi         Dwarf_Unsigned headerlen = 0;
700bc1f688bSRobert Mustacchi         int res = _dwarf_load_debug_info(dbg, error);
701bc1f688bSRobert Mustacchi 
702bc1f688bSRobert Mustacchi         if (res != DW_DLV_OK) {
703bc1f688bSRobert Mustacchi             return res;
704bc1f688bSRobert Mustacchi         }
705*4d9fdb46SRobert Mustacchi         /*  The offset had better not be too close to the end.
706*4d9fdb46SRobert Mustacchi             If it is,
707bc1f688bSRobert Mustacchi             _dwarf_length_of_cu_header() will step off the end and
708bc1f688bSRobert Mustacchi             therefore must not be used. 10 is a meaningless heuristic,
709bc1f688bSRobert Mustacchi             but no CU header is that small so it is safe. */
710*4d9fdb46SRobert Mustacchi         /* Globals cannot refer to debug_types */
711*4d9fdb46SRobert Mustacchi         if ((cuhdr_off + 10) >= dbg->de_debug_info.dss_size) {
712*4d9fdb46SRobert Mustacchi             dwarfstring m;
713*4d9fdb46SRobert Mustacchi 
714*4d9fdb46SRobert Mustacchi             dwarfstring_constructor(&m);
715*4d9fdb46SRobert Mustacchi             build_off_end_msg(cuhdr_off,cuhdr_off+10,
716*4d9fdb46SRobert Mustacchi                 dbg->de_debug_info.dss_size,&m);
717*4d9fdb46SRobert Mustacchi             _dwarf_error_string(dbg, error, DW_DLE_OFFSET_BAD,
718*4d9fdb46SRobert Mustacchi                 dwarfstring_string(&m));
719*4d9fdb46SRobert Mustacchi             dwarfstring_destructor(&m);
720bc1f688bSRobert Mustacchi             return (DW_DLV_ERROR);
721bc1f688bSRobert Mustacchi         }
722*4d9fdb46SRobert Mustacchi         cres = _dwarf_length_of_cu_header(dbg, cuhdr_off,true,
723*4d9fdb46SRobert Mustacchi             &headerlen,error);
724*4d9fdb46SRobert Mustacchi         if(cres != DW_DLV_OK) {
725*4d9fdb46SRobert Mustacchi             return cres;
726bc1f688bSRobert Mustacchi         }
727*4d9fdb46SRobert Mustacchi         *cu_die_offset = cuhdr_off + headerlen;
728*4d9fdb46SRobert Mustacchi     }
729bc1f688bSRobert Mustacchi     return DW_DLV_OK;
730bc1f688bSRobert Mustacchi }
731bc1f688bSRobert Mustacchi 
732*4d9fdb46SRobert Mustacchi 
733*4d9fdb46SRobert Mustacchi /*  New February 2019 from better dwarfdump printing
734*4d9fdb46SRobert Mustacchi     of debug_pubnames and pubtypes.
735*4d9fdb46SRobert Mustacchi     For ao the Dwarf_Global records in one pubnames
736*4d9fdb46SRobert Mustacchi     CU group exactly the same data will be returned.
737*4d9fdb46SRobert Mustacchi 
738*4d9fdb46SRobert Mustacchi */
739*4d9fdb46SRobert Mustacchi int
dwarf_get_globals_header(Dwarf_Global global,Dwarf_Off * pub_section_hdr_offset,Dwarf_Unsigned * pub_offset_size,Dwarf_Unsigned * pub_cu_length,Dwarf_Unsigned * version,Dwarf_Off * info_header_offset,Dwarf_Unsigned * info_length,Dwarf_Error * error)740*4d9fdb46SRobert Mustacchi dwarf_get_globals_header(Dwarf_Global global,
741*4d9fdb46SRobert Mustacchi     Dwarf_Off      *pub_section_hdr_offset,
742*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned *pub_offset_size,
743*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned *pub_cu_length,
744*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned *version,
745*4d9fdb46SRobert Mustacchi     Dwarf_Off      *info_header_offset,
746*4d9fdb46SRobert Mustacchi     Dwarf_Unsigned *info_length,
747*4d9fdb46SRobert Mustacchi     Dwarf_Error*   error)
748*4d9fdb46SRobert Mustacchi {
749*4d9fdb46SRobert Mustacchi     Dwarf_Global_Context con = 0;
750*4d9fdb46SRobert Mustacchi     Dwarf_Debug dbg = 0;
751*4d9fdb46SRobert Mustacchi 
752*4d9fdb46SRobert Mustacchi     if (global == NULL) {
753*4d9fdb46SRobert Mustacchi         _dwarf_error(NULL, error, DW_DLE_GLOBAL_NULL);
754*4d9fdb46SRobert Mustacchi         return DW_DLV_ERROR;
755*4d9fdb46SRobert Mustacchi     }
756*4d9fdb46SRobert Mustacchi     con = global->gl_context;
757*4d9fdb46SRobert Mustacchi     if (con == NULL) {
758*4d9fdb46SRobert Mustacchi         _dwarf_error(NULL, error, DW_DLE_GLOBAL_CONTEXT_NULL);
759*4d9fdb46SRobert Mustacchi         return DW_DLV_ERROR;
760*4d9fdb46SRobert Mustacchi     }
761*4d9fdb46SRobert Mustacchi     dbg = con->pu_dbg;
762*4d9fdb46SRobert Mustacchi     if (dbg == NULL) {
763*4d9fdb46SRobert Mustacchi         _dwarf_error(NULL, error, DW_DLE_DBG_NULL);
764*4d9fdb46SRobert Mustacchi         return DW_DLV_ERROR;
765*4d9fdb46SRobert Mustacchi     }
766*4d9fdb46SRobert Mustacchi     if(pub_section_hdr_offset) {
767*4d9fdb46SRobert Mustacchi         *pub_section_hdr_offset = con->pu_pub_offset;
768*4d9fdb46SRobert Mustacchi     }
769*4d9fdb46SRobert Mustacchi     if (pub_offset_size) {
770*4d9fdb46SRobert Mustacchi         *pub_offset_size = con->pu_length_size;
771*4d9fdb46SRobert Mustacchi     }
772*4d9fdb46SRobert Mustacchi     if (pub_cu_length) {
773*4d9fdb46SRobert Mustacchi         *pub_cu_length = con->pu_length;
774*4d9fdb46SRobert Mustacchi     }
775*4d9fdb46SRobert Mustacchi     if (version) {
776*4d9fdb46SRobert Mustacchi         *version = con->pu_version;
777*4d9fdb46SRobert Mustacchi     }
778*4d9fdb46SRobert Mustacchi     if(info_header_offset) {
779*4d9fdb46SRobert Mustacchi         *info_header_offset = con->pu_offset_of_cu_header;
780*4d9fdb46SRobert Mustacchi     }
781*4d9fdb46SRobert Mustacchi     if (info_length) {
782*4d9fdb46SRobert Mustacchi         *info_length = con->pu_info_length;
783*4d9fdb46SRobert Mustacchi     }
784*4d9fdb46SRobert Mustacchi     return DW_DLV_OK;
785*4d9fdb46SRobert Mustacchi }
786*4d9fdb46SRobert Mustacchi 
787*4d9fdb46SRobert Mustacchi 
788*4d9fdb46SRobert Mustacchi /*  We have the offset to a CU header.
789bc1f688bSRobert Mustacchi     Return thru outFileOffset the offset of the CU DIE.
790bc1f688bSRobert Mustacchi 
791bc1f688bSRobert Mustacchi     New June, 2001.
792*4d9fdb46SRobert Mustacchi     Used by SGI IRIX debuggers.
793*4d9fdb46SRobert Mustacchi     No error used to be possible.
794*4d9fdb46SRobert Mustacchi     As of May 2016 an error is possible if the DWARF is
795*4d9fdb46SRobert Mustacchi     corrupted! (IRIX debuggers are no longer built ...)
796bc1f688bSRobert Mustacchi 
797bc1f688bSRobert Mustacchi     See also dwarf_CU_dieoffset_given_die().
798*4d9fdb46SRobert Mustacchi 
799*4d9fdb46SRobert Mustacchi     This is assumed to never apply to data in .debug_types, it
800*4d9fdb46SRobert Mustacchi     only refers to .debug_info.
801*4d9fdb46SRobert Mustacchi 
802bc1f688bSRobert Mustacchi */
803bc1f688bSRobert Mustacchi 
804bc1f688bSRobert Mustacchi /* ARGSUSED */
805bc1f688bSRobert Mustacchi int
dwarf_get_cu_die_offset_given_cu_header_offset(Dwarf_Debug dbg,Dwarf_Off in_cu_header_offset,Dwarf_Off * out_cu_die_offset,UNUSEDARG Dwarf_Error * err)806bc1f688bSRobert Mustacchi dwarf_get_cu_die_offset_given_cu_header_offset(Dwarf_Debug dbg,
807bc1f688bSRobert Mustacchi     Dwarf_Off in_cu_header_offset,
808bc1f688bSRobert Mustacchi     Dwarf_Off * out_cu_die_offset,
809*4d9fdb46SRobert Mustacchi     UNUSEDARG Dwarf_Error * err)
810bc1f688bSRobert Mustacchi {
811*4d9fdb46SRobert Mustacchi     Dwarf_Off headerlen = 0;
812*4d9fdb46SRobert Mustacchi     int cres = 0;
813bc1f688bSRobert Mustacchi 
814*4d9fdb46SRobert Mustacchi     cres = _dwarf_length_of_cu_header(dbg, in_cu_header_offset,true,
815*4d9fdb46SRobert Mustacchi         &headerlen,err);
816*4d9fdb46SRobert Mustacchi     if (cres != DW_DLV_OK) {
817*4d9fdb46SRobert Mustacchi         return cres;
818*4d9fdb46SRobert Mustacchi     }
819*4d9fdb46SRobert Mustacchi     *out_cu_die_offset = in_cu_header_offset + headerlen;
820*4d9fdb46SRobert Mustacchi     return DW_DLV_OK;
821*4d9fdb46SRobert Mustacchi }
822bc1f688bSRobert Mustacchi 
823*4d9fdb46SRobert Mustacchi /*  The following version new in October 2011, does allow finding
824*4d9fdb46SRobert Mustacchi     the offset if one knows whether debug_info or debug_types.
825*4d9fdb46SRobert Mustacchi 
826*4d9fdb46SRobert Mustacchi     However, it is not accurate in DWARF5 because
827*4d9fdb46SRobert Mustacchi     there are two different header lengths (CU and TU)
828*4d9fdb46SRobert Mustacchi     in DWARF5 .debug_info.  In that case, pretend
829*4d9fdb46SRobert Mustacchi     that it's .debug_types (here) and pass is_info zero for
830*4d9fdb46SRobert Mustacchi     a TU (as if it was in .debug_types).
831*4d9fdb46SRobert Mustacchi     */
832*4d9fdb46SRobert Mustacchi int
dwarf_get_cu_die_offset_given_cu_header_offset_b(Dwarf_Debug dbg,Dwarf_Off in_cu_header_offset,Dwarf_Bool is_info,Dwarf_Off * out_cu_die_offset,UNUSEDARG Dwarf_Error * err)833*4d9fdb46SRobert Mustacchi dwarf_get_cu_die_offset_given_cu_header_offset_b(Dwarf_Debug dbg,
834*4d9fdb46SRobert Mustacchi     Dwarf_Off in_cu_header_offset,
835*4d9fdb46SRobert Mustacchi     Dwarf_Bool is_info,
836*4d9fdb46SRobert Mustacchi     Dwarf_Off * out_cu_die_offset,
837*4d9fdb46SRobert Mustacchi     UNUSEDARG Dwarf_Error * err)
838*4d9fdb46SRobert Mustacchi {
839*4d9fdb46SRobert Mustacchi     Dwarf_Off headerlen = 0;
840*4d9fdb46SRobert Mustacchi     int cres = 0;
841*4d9fdb46SRobert Mustacchi 
842*4d9fdb46SRobert Mustacchi     cres = _dwarf_length_of_cu_header(dbg, in_cu_header_offset,is_info,
843*4d9fdb46SRobert Mustacchi         &headerlen,err);
844*4d9fdb46SRobert Mustacchi     if (cres != DW_DLV_OK) {
845*4d9fdb46SRobert Mustacchi         return cres;
846*4d9fdb46SRobert Mustacchi     }
847*4d9fdb46SRobert Mustacchi     *out_cu_die_offset = in_cu_header_offset + headerlen;
848bc1f688bSRobert Mustacchi     return DW_DLV_OK;
849bc1f688bSRobert Mustacchi }
850bc1f688bSRobert Mustacchi /*  dwarf_CU_dieoffset_given_die returns
851bc1f688bSRobert Mustacchi     the global debug_info section offset of the CU die
852bc1f688bSRobert Mustacchi     that is the CU containing the given (passed-in) die.
853bc1f688bSRobert Mustacchi     This information makes it possible for a consumer to
854bc1f688bSRobert Mustacchi     find and print context information for any die.
855bc1f688bSRobert Mustacchi 
856bc1f688bSRobert Mustacchi     Use dwarf_offdie() passing in the offset this returns
857*4d9fdb46SRobert Mustacchi     to get a die pointer to the CU die.  */
858bc1f688bSRobert Mustacchi int
dwarf_CU_dieoffset_given_die(Dwarf_Die die,Dwarf_Off * return_offset,Dwarf_Error * error)859bc1f688bSRobert Mustacchi dwarf_CU_dieoffset_given_die(Dwarf_Die die,
860bc1f688bSRobert Mustacchi     Dwarf_Off*       return_offset,
861bc1f688bSRobert Mustacchi     Dwarf_Error*     error)
862bc1f688bSRobert Mustacchi {
863bc1f688bSRobert Mustacchi     Dwarf_Off  dieoff = 0;
864bc1f688bSRobert Mustacchi     Dwarf_CU_Context cucontext = 0;
865bc1f688bSRobert Mustacchi 
866bc1f688bSRobert Mustacchi     CHECK_DIE(die, DW_DLV_ERROR);
867bc1f688bSRobert Mustacchi     cucontext = die->di_cu_context;
868*4d9fdb46SRobert Mustacchi     dieoff =  cucontext->cc_debug_offset;
869bc1f688bSRobert Mustacchi     /*  The following call cannot fail, so no error check. */
870*4d9fdb46SRobert Mustacchi     dwarf_get_cu_die_offset_given_cu_header_offset_b(
871*4d9fdb46SRobert Mustacchi         cucontext->cc_dbg, dieoff,
872*4d9fdb46SRobert Mustacchi         die->di_is_info, return_offset,error);
873*4d9fdb46SRobert Mustacchi     return DW_DLV_OK;
874*4d9fdb46SRobert Mustacchi }
875*4d9fdb46SRobert Mustacchi 
876*4d9fdb46SRobert Mustacchi /*  We do not want to screw up error in case
877*4d9fdb46SRobert Mustacchi     it has something important.  So not touching it now. */
dwarf_return_empty_pubnames(Dwarf_Debug dbg,int flag,UNUSEDARG Dwarf_Error * err)878*4d9fdb46SRobert Mustacchi int dwarf_return_empty_pubnames(Dwarf_Debug dbg,
879*4d9fdb46SRobert Mustacchi     int flag, UNUSEDARG Dwarf_Error *err )
880*4d9fdb46SRobert Mustacchi {
881*4d9fdb46SRobert Mustacchi     if (dbg == NULL) {
882*4d9fdb46SRobert Mustacchi         return DW_DLV_OK;
883*4d9fdb46SRobert Mustacchi     }
884*4d9fdb46SRobert Mustacchi     if (flag && flag != 1) {
885*4d9fdb46SRobert Mustacchi         return DW_DLV_OK;
886*4d9fdb46SRobert Mustacchi     }
887*4d9fdb46SRobert Mustacchi     dbg->de_return_empty_pubnames = (unsigned char)flag;
888bc1f688bSRobert Mustacchi     return DW_DLV_OK;
889bc1f688bSRobert Mustacchi }
890