4 * Copyright (c) 2007 John Birrell (jb@freebsd.org)
7 * Redistribution and use in source and binary forms, with or without
8 * modification, are permitted provided that the following conditions
10 * 1. Redistributions of source code must retain the above copyright
11 * notice, this list of conditions and the following disclaimer.
12 * 2. Redistributions in binary form must reproduce the above copyright
13 * notice, this list of conditions and the following disclaimer in the
14 * documentation and/or other materials provided with the distribution.
16 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
17 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
18 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
19 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
20 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
21 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
22 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
23 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
24 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
25 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
28 * $FreeBSD: src/lib/libdwarf/dwarf_attrval.c,v 1.1.4.1 2009/08/03 08:13:06 kensmith Exp $
34 #include "_libdwarf.h"
37 dwarf_attrval_find(Dwarf_Die die
, Dwarf_Half attr
)
41 STAILQ_FOREACH(av
, &die
->die_attrval
, av_next
) {
42 if (av
->av_attrib
== attr
)
50 dwarf_attrval_add(Dwarf_Die die
, Dwarf_AttrValue avref
, Dwarf_AttrValue
*avp
, Dwarf_Error
*error
)
53 int ret
= DWARF_E_NONE
;
55 if ((av
= malloc(sizeof(struct _Dwarf_AttrValue
))) == NULL
) {
56 DWARF_SET_ERROR(error
, DWARF_E_MEMORY
);
57 return DWARF_E_MEMORY
;
60 memcpy(av
, avref
, sizeof(struct _Dwarf_AttrValue
));
62 /* Add the attribute value to the list in the die. */
63 STAILQ_INSERT_TAIL(&die
->die_attrval
, av
, av_next
);
65 /* Save a pointer to the attribute name if this is one. */
66 if (av
->av_attrib
== DW_AT_name
)
67 switch (av
->av_form
) {
69 die
->die_name
= av
->u
[1].s
;
72 die
->die_name
= av
->u
[0].s
;
85 dwarf_attrval_flag(Dwarf_Die die
, uint64_t attr
, Dwarf_Bool
*valp
, Dwarf_Error
*err
)
88 int ret
= DWARF_E_NONE
;
93 if (die
== NULL
|| valp
== NULL
) {
94 DWARF_SET_ERROR(err
, DWARF_E_ARGUMENT
);
95 return DWARF_E_ARGUMENT
;
100 if ((av
= dwarf_attrval_find(die
, attr
)) == NULL
) {
101 DWARF_SET_ERROR(err
, DWARF_E_NO_ENTRY
);
102 ret
= DWARF_E_NO_ENTRY
;
104 switch (av
->av_form
) {
106 *valp
= (Dwarf_Bool
) av
->u
[0].u64
;
109 printf("%s(%d): av->av_form '%s' (0x%lx) not handled\n",
110 __func__
,__LINE__
,get_form_desc(av
->av_form
),
111 (u_long
) av
->av_form
);
112 DWARF_SET_ERROR(err
, DWARF_E_BAD_FORM
);
113 ret
= DWARF_E_BAD_FORM
;
121 dwarf_attrval_string(Dwarf_Die die
, uint64_t attr
, const char **strp
, Dwarf_Error
*err
)
124 int ret
= DWARF_E_NONE
;
127 return DWARF_E_ERROR
;
129 if (die
== NULL
|| strp
== NULL
) {
130 DWARF_SET_ERROR(err
, DWARF_E_ARGUMENT
);
131 return DWARF_E_ARGUMENT
;
136 if (attr
== DW_AT_name
)
137 *strp
= die
->die_name
;
138 else if ((av
= dwarf_attrval_find(die
, attr
)) == NULL
) {
139 DWARF_SET_ERROR(err
, DWARF_E_NO_ENTRY
);
140 ret
= DWARF_E_NO_ENTRY
;
142 switch (av
->av_form
) {
150 printf("%s(%d): av->av_form '%s' (0x%lx) not handled\n",
151 __func__
,__LINE__
,get_form_desc(av
->av_form
),
152 (u_long
) av
->av_form
);
153 DWARF_SET_ERROR(err
, DWARF_E_BAD_FORM
);
154 ret
= DWARF_E_BAD_FORM
;
162 dwarf_attrval_signed(Dwarf_Die die
, uint64_t attr
, Dwarf_Signed
*valp
, Dwarf_Error
*err
)
165 int ret
= DWARF_E_NONE
;
168 return DWARF_E_ERROR
;
170 if (die
== NULL
|| valp
== NULL
) {
171 DWARF_SET_ERROR(err
, DWARF_E_ARGUMENT
);
172 return DWARF_E_ARGUMENT
;
177 if ((av
= dwarf_attrval_find(die
, attr
)) == NULL
) {
178 DWARF_SET_ERROR(err
, DWARF_E_NO_ENTRY
);
179 ret
= DWARF_E_NO_ENTRY
;
181 switch (av
->av_form
) {
184 *valp
= av
->u
[0].s64
;
187 printf("%s(%d): av->av_form '%s' (0x%lx) not handled\n",
188 __func__
,__LINE__
,get_form_desc(av
->av_form
),
189 (u_long
) av
->av_form
);
190 DWARF_SET_ERROR(err
, DWARF_E_BAD_FORM
);
191 ret
= DWARF_E_BAD_FORM
;
199 dwarf_attrval_unsigned(Dwarf_Die die
, uint64_t attr
, Dwarf_Unsigned
*valp
, Dwarf_Error
*err
)
202 int ret
= DWARF_E_NONE
;
205 return DWARF_E_ERROR
;
207 if (die
== NULL
|| valp
== NULL
) {
208 DWARF_SET_ERROR(err
, DWARF_E_ARGUMENT
);
209 return DWARF_E_ARGUMENT
;
214 if ((av
= dwarf_attrval_find(die
, attr
)) == NULL
&& attr
!= DW_AT_type
) {
215 DWARF_SET_ERROR(err
, DWARF_E_NO_ENTRY
);
216 ret
= DWARF_E_NO_ENTRY
;
217 } else if (av
== NULL
&& (av
= dwarf_attrval_find(die
,
218 DW_AT_abstract_origin
)) != NULL
) {
222 switch (av
->av_form
) {
231 case DW_FORM_ref_udata
:
234 if ((die1
= dwarf_die_find(die
, val
)) == NULL
||
235 (av
= dwarf_attrval_find(die1
, attr
)) == NULL
) {
236 DWARF_SET_ERROR(err
, DWARF_E_NO_ENTRY
);
237 ret
= DWARF_E_NO_ENTRY
;
241 printf("%s(%d): av->av_form '%s' (0x%lx) not handled\n",
242 __func__
,__LINE__
,get_form_desc(av
->av_form
),
243 (u_long
) av
->av_form
);
244 DWARF_SET_ERROR(err
, DWARF_E_BAD_FORM
);
245 ret
= DWARF_E_BAD_FORM
;
249 if (ret
== DWARF_E_NONE
) {
250 switch (av
->av_form
) {
259 case DW_FORM_ref_udata
:
260 *valp
= av
->u
[0].u64
;
263 printf("%s(%d): av->av_form '%s' (0x%lx) not handled\n",
264 __func__
,__LINE__
,get_form_desc(av
->av_form
),
265 (u_long
) av
->av_form
);
266 DWARF_SET_ERROR(err
, DWARF_E_BAD_FORM
);
267 ret
= DWARF_E_BAD_FORM
;