/src/binutils-gdb/libctf/ctf-open.c
Line | Count | Source (jump to first uncovered line) |
1 | | /* Opening CTF files. |
2 | | Copyright (C) 2019-2025 Free Software Foundation, Inc. |
3 | | |
4 | | This file is part of libctf. |
5 | | |
6 | | libctf is free software; you can redistribute it and/or modify it under |
7 | | the terms of the GNU General Public License as published by the Free |
8 | | Software Foundation; either version 3, or (at your option) any later |
9 | | version. |
10 | | |
11 | | This program is distributed in the hope that it will be useful, but |
12 | | WITHOUT ANY WARRANTY; without even the implied warranty of |
13 | | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. |
14 | | See the GNU General Public License for more details. |
15 | | |
16 | | You should have received a copy of the GNU General Public License |
17 | | along with this program; see the file COPYING. If not see |
18 | | <http://www.gnu.org/licenses/>. */ |
19 | | |
20 | | #include <ctf-impl.h> |
21 | | #include <stddef.h> |
22 | | #include <string.h> |
23 | | #include <sys/types.h> |
24 | | #include <elf.h> |
25 | | #include "swap.h" |
26 | | #include <bfd.h> |
27 | | #include <zlib.h> |
28 | | |
29 | | static const ctf_dmodel_t _libctf_models[] = { |
30 | | {"ILP32", CTF_MODEL_ILP32, 4, 1, 2, 4, 4}, |
31 | | {"LP64", CTF_MODEL_LP64, 8, 1, 2, 4, 8}, |
32 | | {NULL, 0, 0, 0, 0, 0, 0} |
33 | | }; |
34 | | |
35 | | const char _CTF_SECTION[] = ".ctf"; |
36 | | const char _CTF_NULLSTR[] = ""; |
37 | | |
38 | | /* Version-sensitive accessors. */ |
39 | | |
40 | | static uint32_t |
41 | | get_kind_v1 (uint32_t info) |
42 | 0 | { |
43 | 0 | return (CTF_V1_INFO_KIND (info)); |
44 | 0 | } |
45 | | |
46 | | static uint32_t |
47 | | get_root_v1 (uint32_t info) |
48 | 0 | { |
49 | 0 | return (CTF_V1_INFO_ISROOT (info)); |
50 | 0 | } |
51 | | |
52 | | static uint32_t |
53 | | get_vlen_v1 (uint32_t info) |
54 | 0 | { |
55 | 0 | return (CTF_V1_INFO_VLEN (info)); |
56 | 0 | } |
57 | | |
58 | | static uint32_t |
59 | | get_kind_v2 (uint32_t info) |
60 | 0 | { |
61 | 0 | return (CTF_V2_INFO_KIND (info)); |
62 | 0 | } |
63 | | |
64 | | static uint32_t |
65 | | get_root_v2 (uint32_t info) |
66 | 0 | { |
67 | 0 | return (CTF_V2_INFO_ISROOT (info)); |
68 | 0 | } |
69 | | |
70 | | static uint32_t |
71 | | get_vlen_v2 (uint32_t info) |
72 | 0 | { |
73 | 0 | return (CTF_V2_INFO_VLEN (info)); |
74 | 0 | } |
75 | | |
76 | | static inline ssize_t |
77 | | get_ctt_size_common (const ctf_dict_t *fp _libctf_unused_, |
78 | | const ctf_type_t *tp _libctf_unused_, |
79 | | ssize_t *sizep, ssize_t *incrementp, size_t lsize, |
80 | | size_t csize, size_t ctf_type_size, |
81 | | size_t ctf_stype_size, size_t ctf_lsize_sent) |
82 | 0 | { |
83 | 0 | ssize_t size, increment; |
84 | |
|
85 | 0 | if (csize == ctf_lsize_sent) |
86 | 0 | { |
87 | 0 | size = lsize; |
88 | 0 | increment = ctf_type_size; |
89 | 0 | } |
90 | 0 | else |
91 | 0 | { |
92 | 0 | size = csize; |
93 | 0 | increment = ctf_stype_size; |
94 | 0 | } |
95 | |
|
96 | 0 | if (sizep) |
97 | 0 | *sizep = size; |
98 | 0 | if (incrementp) |
99 | 0 | *incrementp = increment; |
100 | |
|
101 | 0 | return size; |
102 | 0 | } |
103 | | |
104 | | static ssize_t |
105 | | get_ctt_size_v1 (const ctf_dict_t *fp, const ctf_type_t *tp, |
106 | | ssize_t *sizep, ssize_t *incrementp) |
107 | 0 | { |
108 | 0 | ctf_type_v1_t *t1p = (ctf_type_v1_t *) tp; |
109 | |
|
110 | 0 | return (get_ctt_size_common (fp, tp, sizep, incrementp, |
111 | 0 | CTF_TYPE_LSIZE (t1p), t1p->ctt_size, |
112 | 0 | sizeof (ctf_type_v1_t), sizeof (ctf_stype_v1_t), |
113 | 0 | CTF_LSIZE_SENT_V1)); |
114 | 0 | } |
115 | | |
116 | | /* Return the size that a v1 will be once it is converted to v2. */ |
117 | | |
118 | | static ssize_t |
119 | | get_ctt_size_v2_unconverted (const ctf_dict_t *fp, const ctf_type_t *tp, |
120 | | ssize_t *sizep, ssize_t *incrementp) |
121 | 0 | { |
122 | 0 | ctf_type_v1_t *t1p = (ctf_type_v1_t *) tp; |
123 | |
|
124 | 0 | return (get_ctt_size_common (fp, tp, sizep, incrementp, |
125 | 0 | CTF_TYPE_LSIZE (t1p), t1p->ctt_size, |
126 | 0 | sizeof (ctf_type_t), sizeof (ctf_stype_t), |
127 | 0 | CTF_LSIZE_SENT)); |
128 | 0 | } |
129 | | |
130 | | static ssize_t |
131 | | get_ctt_size_v2 (const ctf_dict_t *fp, const ctf_type_t *tp, |
132 | | ssize_t *sizep, ssize_t *incrementp) |
133 | 0 | { |
134 | 0 | return (get_ctt_size_common (fp, tp, sizep, incrementp, |
135 | 0 | CTF_TYPE_LSIZE (tp), tp->ctt_size, |
136 | 0 | sizeof (ctf_type_t), sizeof (ctf_stype_t), |
137 | 0 | CTF_LSIZE_SENT)); |
138 | 0 | } |
139 | | |
140 | | static ssize_t |
141 | | get_vbytes_common (ctf_dict_t *fp, unsigned short kind, |
142 | | ssize_t size _libctf_unused_, size_t vlen) |
143 | 0 | { |
144 | 0 | switch (kind) |
145 | 0 | { |
146 | 0 | case CTF_K_INTEGER: |
147 | 0 | case CTF_K_FLOAT: |
148 | 0 | return (sizeof (uint32_t)); |
149 | 0 | case CTF_K_SLICE: |
150 | 0 | return (sizeof (ctf_slice_t)); |
151 | 0 | case CTF_K_ENUM: |
152 | 0 | return (sizeof (ctf_enum_t) * vlen); |
153 | 0 | case CTF_K_FORWARD: |
154 | 0 | case CTF_K_UNKNOWN: |
155 | 0 | case CTF_K_POINTER: |
156 | 0 | case CTF_K_TYPEDEF: |
157 | 0 | case CTF_K_VOLATILE: |
158 | 0 | case CTF_K_CONST: |
159 | 0 | case CTF_K_RESTRICT: |
160 | 0 | return 0; |
161 | 0 | default: |
162 | 0 | ctf_set_errno (fp, ECTF_CORRUPT); |
163 | 0 | ctf_err_warn (fp, 0, 0, _("detected invalid CTF kind: %x"), kind); |
164 | 0 | return -1; |
165 | 0 | } |
166 | 0 | } |
167 | | |
168 | | static ssize_t |
169 | | get_vbytes_v1 (ctf_dict_t *fp, unsigned short kind, ssize_t size, size_t vlen) |
170 | 0 | { |
171 | 0 | switch (kind) |
172 | 0 | { |
173 | 0 | case CTF_K_ARRAY: |
174 | 0 | return (sizeof (ctf_array_v1_t)); |
175 | 0 | case CTF_K_FUNCTION: |
176 | 0 | return (sizeof (unsigned short) * (vlen + (vlen & 1))); |
177 | 0 | case CTF_K_STRUCT: |
178 | 0 | case CTF_K_UNION: |
179 | 0 | if (size < CTF_LSTRUCT_THRESH_V1) |
180 | 0 | return (sizeof (ctf_member_v1_t) * vlen); |
181 | 0 | else |
182 | 0 | return (sizeof (ctf_lmember_v1_t) * vlen); |
183 | 0 | } |
184 | | |
185 | 0 | return (get_vbytes_common (fp, kind, size, vlen)); |
186 | 0 | } |
187 | | |
188 | | static ssize_t |
189 | | get_vbytes_v2 (ctf_dict_t *fp, unsigned short kind, ssize_t size, size_t vlen) |
190 | 0 | { |
191 | 0 | switch (kind) |
192 | 0 | { |
193 | 0 | case CTF_K_ARRAY: |
194 | 0 | return (sizeof (ctf_array_t)); |
195 | 0 | case CTF_K_FUNCTION: |
196 | 0 | return (sizeof (uint32_t) * (vlen + (vlen & 1))); |
197 | 0 | case CTF_K_STRUCT: |
198 | 0 | case CTF_K_UNION: |
199 | 0 | if (size < CTF_LSTRUCT_THRESH) |
200 | 0 | return (sizeof (ctf_member_t) * vlen); |
201 | 0 | else |
202 | 0 | return (sizeof (ctf_lmember_t) * vlen); |
203 | 0 | } |
204 | | |
205 | 0 | return (get_vbytes_common (fp, kind, size, vlen)); |
206 | 0 | } |
207 | | |
208 | | static const ctf_dictops_t ctf_dictops[] = { |
209 | | {NULL, NULL, NULL, NULL, NULL}, |
210 | | /* CTF_VERSION_1 */ |
211 | | {get_kind_v1, get_root_v1, get_vlen_v1, get_ctt_size_v1, get_vbytes_v1}, |
212 | | /* CTF_VERSION_1_UPGRADED_3 */ |
213 | | {get_kind_v2, get_root_v2, get_vlen_v2, get_ctt_size_v2, get_vbytes_v2}, |
214 | | /* CTF_VERSION_2 */ |
215 | | {get_kind_v2, get_root_v2, get_vlen_v2, get_ctt_size_v2, get_vbytes_v2}, |
216 | | /* CTF_VERSION_3, identical to 2: only new type kinds */ |
217 | | {get_kind_v2, get_root_v2, get_vlen_v2, get_ctt_size_v2, get_vbytes_v2}, |
218 | | }; |
219 | | |
220 | | /* Initialize the symtab translation table as appropriate for its indexing |
221 | | state. For unindexed symtypetabs, fill each entry with the offset of the CTF |
222 | | type or function data corresponding to each STT_FUNC or STT_OBJECT entry in |
223 | | the symbol table. For indexed symtypetabs, do nothing: the needed |
224 | | initialization for indexed lookups may be quite expensive, so it is done only |
225 | | as needed, when lookups happen. (In particular, the majority of indexed |
226 | | symtypetabs come from the compiler, and all the linker does is iteration over |
227 | | all entries, which doesn't need this initialization.) |
228 | | |
229 | | The SP symbol table section may be NULL if there is no symtab. |
230 | | |
231 | | If init_symtab works on one call, it cannot fail on future calls to the same |
232 | | fp: ctf_symsect_endianness relies on this. */ |
233 | | |
234 | | static int |
235 | | init_symtab (ctf_dict_t *fp, const ctf_header_t *hp, const ctf_sect_t *sp) |
236 | 0 | { |
237 | 0 | const unsigned char *symp; |
238 | 0 | int skip_func_info = 0; |
239 | 0 | int i; |
240 | 0 | uint32_t *xp = fp->ctf_sxlate; |
241 | 0 | uint32_t *xend = PTR_ADD (xp, fp->ctf_nsyms); |
242 | |
|
243 | 0 | uint32_t objtoff = hp->cth_objtoff; |
244 | 0 | uint32_t funcoff = hp->cth_funcoff; |
245 | | |
246 | | /* If the CTF_F_NEWFUNCINFO flag is not set, pretend the func info section |
247 | | is empty: this compiler is too old to emit a function info section we |
248 | | understand. */ |
249 | |
|
250 | 0 | if (!(hp->cth_flags & CTF_F_NEWFUNCINFO)) |
251 | 0 | skip_func_info = 1; |
252 | |
|
253 | 0 | if (hp->cth_objtidxoff < hp->cth_funcidxoff) |
254 | 0 | fp->ctf_objtidx_names = (uint32_t *) (fp->ctf_buf + hp->cth_objtidxoff); |
255 | 0 | if (hp->cth_funcidxoff < hp->cth_varoff && !skip_func_info) |
256 | 0 | fp->ctf_funcidx_names = (uint32_t *) (fp->ctf_buf + hp->cth_funcidxoff); |
257 | | |
258 | | /* Don't bother doing the rest if everything is indexed, or if we don't have a |
259 | | symbol table: we will never use it. */ |
260 | 0 | if ((fp->ctf_objtidx_names && fp->ctf_funcidx_names) || !sp || !sp->cts_data) |
261 | 0 | return 0; |
262 | | |
263 | | /* The CTF data object and function type sections are ordered to match the |
264 | | relative order of the respective symbol types in the symtab, unless there |
265 | | is an index section, in which case the order is arbitrary and the index |
266 | | gives the mapping. If no type information is available for a symbol table |
267 | | entry, a pad is inserted in the CTF section. As a further optimization, |
268 | | anonymous or undefined symbols are omitted from the CTF data. If an |
269 | | index is available for function symbols but not object symbols, or vice |
270 | | versa, we populate the xslate table for the unindexed symbols only. */ |
271 | | |
272 | 0 | for (i = 0, symp = sp->cts_data; xp < xend; xp++, symp += sp->cts_entsize, |
273 | 0 | i++) |
274 | 0 | { |
275 | 0 | ctf_link_sym_t sym; |
276 | |
|
277 | 0 | switch (sp->cts_entsize) |
278 | 0 | { |
279 | 0 | case sizeof (Elf64_Sym): |
280 | 0 | { |
281 | 0 | const Elf64_Sym *symp64 = (Elf64_Sym *) (uintptr_t) symp; |
282 | 0 | ctf_elf64_to_link_sym (fp, &sym, symp64, i); |
283 | 0 | } |
284 | 0 | break; |
285 | 0 | case sizeof (Elf32_Sym): |
286 | 0 | { |
287 | 0 | const Elf32_Sym *symp32 = (Elf32_Sym *) (uintptr_t) symp; |
288 | 0 | ctf_elf32_to_link_sym (fp, &sym, symp32, i); |
289 | 0 | } |
290 | 0 | break; |
291 | 0 | default: |
292 | 0 | return ECTF_SYMTAB; |
293 | 0 | } |
294 | | |
295 | | /* This call may be led astray if our idea of the symtab's endianness is |
296 | | wrong, but when this is fixed by a call to ctf_symsect_endianness, |
297 | | init_symtab will be called again with the right endianness in |
298 | | force. */ |
299 | 0 | if (ctf_symtab_skippable (&sym)) |
300 | 0 | { |
301 | 0 | *xp = -1u; |
302 | 0 | continue; |
303 | 0 | } |
304 | | |
305 | 0 | switch (sym.st_type) |
306 | 0 | { |
307 | 0 | case STT_OBJECT: |
308 | 0 | if (fp->ctf_objtidx_names || objtoff >= hp->cth_funcoff) |
309 | 0 | { |
310 | 0 | *xp = -1u; |
311 | 0 | break; |
312 | 0 | } |
313 | | |
314 | 0 | *xp = objtoff; |
315 | 0 | objtoff += sizeof (uint32_t); |
316 | 0 | break; |
317 | | |
318 | 0 | case STT_FUNC: |
319 | 0 | if (fp->ctf_funcidx_names || funcoff >= hp->cth_objtidxoff |
320 | 0 | || skip_func_info) |
321 | 0 | { |
322 | 0 | *xp = -1u; |
323 | 0 | break; |
324 | 0 | } |
325 | | |
326 | 0 | *xp = funcoff; |
327 | 0 | funcoff += sizeof (uint32_t); |
328 | 0 | break; |
329 | | |
330 | 0 | default: |
331 | 0 | *xp = -1u; |
332 | 0 | break; |
333 | 0 | } |
334 | 0 | } |
335 | | |
336 | 0 | ctf_dprintf ("loaded %lu symtab entries\n", fp->ctf_nsyms); |
337 | 0 | return 0; |
338 | 0 | } |
339 | | |
340 | | /* Reset the CTF base pointer and derive the buf pointer from it, initializing |
341 | | everything in the ctf_dict that depends on the base or buf pointers. |
342 | | |
343 | | The original gap between the buf and base pointers, if any -- the original, |
344 | | unconverted CTF header -- is kept, but its contents are not specified and are |
345 | | never used. */ |
346 | | |
347 | | static void |
348 | | ctf_set_base (ctf_dict_t *fp, const ctf_header_t *hp, unsigned char *base) |
349 | 0 | { |
350 | 0 | fp->ctf_buf = base + (fp->ctf_buf - fp->ctf_base); |
351 | 0 | fp->ctf_base = base; |
352 | 0 | fp->ctf_vars = (ctf_varent_t *) ((const char *) fp->ctf_buf + |
353 | 0 | hp->cth_varoff); |
354 | 0 | fp->ctf_nvars = (hp->cth_typeoff - hp->cth_varoff) / sizeof (ctf_varent_t); |
355 | |
|
356 | 0 | fp->ctf_str[CTF_STRTAB_0].cts_strs = (const char *) fp->ctf_buf |
357 | 0 | + hp->cth_stroff; |
358 | 0 | fp->ctf_str[CTF_STRTAB_0].cts_len = hp->cth_strlen; |
359 | | |
360 | | /* If we have a parent dict name and label, store the relocated string |
361 | | pointers in the CTF dict for easy access later. */ |
362 | | |
363 | | /* Note: before conversion, these will be set to values that will be |
364 | | immediately invalidated by the conversion process, but the conversion |
365 | | process will call ctf_set_base() again to fix things up. */ |
366 | |
|
367 | 0 | if (hp->cth_parlabel != 0) |
368 | 0 | fp->ctf_parlabel = ctf_strptr (fp, hp->cth_parlabel); |
369 | 0 | if (hp->cth_parname != 0) |
370 | 0 | fp->ctf_parname = ctf_strptr (fp, hp->cth_parname); |
371 | 0 | if (hp->cth_cuname != 0) |
372 | 0 | fp->ctf_cuname = ctf_strptr (fp, hp->cth_cuname); |
373 | |
|
374 | 0 | if (fp->ctf_cuname) |
375 | 0 | ctf_dprintf ("ctf_set_base: CU name %s\n", fp->ctf_cuname); |
376 | 0 | if (fp->ctf_parname) |
377 | 0 | ctf_dprintf ("ctf_set_base: parent name %s (label %s)\n", |
378 | 0 | fp->ctf_parname, |
379 | 0 | fp->ctf_parlabel ? fp->ctf_parlabel : "<NULL>"); |
380 | 0 | } |
381 | | |
382 | | /* Set the version of the CTF file. */ |
383 | | |
384 | | /* When this is reset, LCTF_* changes behaviour, but there is no guarantee that |
385 | | the variable data list associated with each type has been upgraded: the |
386 | | caller must ensure this has been done in advance. */ |
387 | | |
388 | | static void |
389 | | ctf_set_version (ctf_dict_t *fp, ctf_header_t *cth, int ctf_version) |
390 | 0 | { |
391 | 0 | fp->ctf_version = ctf_version; |
392 | 0 | cth->cth_version = ctf_version; |
393 | 0 | fp->ctf_dictops = &ctf_dictops[ctf_version]; |
394 | 0 | } |
395 | | |
396 | | |
397 | | /* Upgrade the header to CTF_VERSION_3. The upgrade is done in-place. */ |
398 | | static void |
399 | | upgrade_header (ctf_header_t *hp) |
400 | 0 | { |
401 | 0 | ctf_header_v2_t *oldhp = (ctf_header_v2_t *) hp; |
402 | |
|
403 | 0 | hp->cth_strlen = oldhp->cth_strlen; |
404 | 0 | hp->cth_stroff = oldhp->cth_stroff; |
405 | 0 | hp->cth_typeoff = oldhp->cth_typeoff; |
406 | 0 | hp->cth_varoff = oldhp->cth_varoff; |
407 | 0 | hp->cth_funcidxoff = hp->cth_varoff; /* No index sections. */ |
408 | 0 | hp->cth_objtidxoff = hp->cth_funcidxoff; |
409 | 0 | hp->cth_funcoff = oldhp->cth_funcoff; |
410 | 0 | hp->cth_objtoff = oldhp->cth_objtoff; |
411 | 0 | hp->cth_lbloff = oldhp->cth_lbloff; |
412 | 0 | hp->cth_cuname = 0; /* No CU name. */ |
413 | 0 | } |
414 | | |
415 | | /* Upgrade the type table to CTF_VERSION_3 (really CTF_VERSION_1_UPGRADED_3) |
416 | | from CTF_VERSION_1. |
417 | | |
418 | | The upgrade is not done in-place: the ctf_base is moved. ctf_strptr() must |
419 | | not be called before reallocation is complete. |
420 | | |
421 | | Sections not checked here due to nonexistence or nonpopulated state in older |
422 | | formats: objtidx, funcidx. |
423 | | |
424 | | Type kinds not checked here due to nonexistence in older formats: |
425 | | CTF_K_SLICE. */ |
426 | | static int |
427 | | upgrade_types_v1 (ctf_dict_t *fp, ctf_header_t *cth) |
428 | 0 | { |
429 | 0 | const ctf_type_v1_t *tbuf; |
430 | 0 | const ctf_type_v1_t *tend; |
431 | 0 | unsigned char *ctf_base, *old_ctf_base = (unsigned char *) fp->ctf_dynbase; |
432 | 0 | ctf_type_t *t2buf; |
433 | |
|
434 | 0 | ssize_t increase = 0, size, increment, v2increment, vbytes, v2bytes; |
435 | 0 | const ctf_type_v1_t *tp; |
436 | 0 | ctf_type_t *t2p; |
437 | |
|
438 | 0 | tbuf = (ctf_type_v1_t *) (fp->ctf_buf + cth->cth_typeoff); |
439 | 0 | tend = (ctf_type_v1_t *) (fp->ctf_buf + cth->cth_stroff); |
440 | | |
441 | | /* Much like init_static_types(), this is a two-pass process. |
442 | | |
443 | | First, figure out the new type-section size needed. (It is possible, |
444 | | in theory, for it to be less than the old size, but this is very |
445 | | unlikely. It cannot be so small that cth_typeoff ends up of negative |
446 | | size. We validate this with an assertion below.) |
447 | | |
448 | | We must cater not only for changes in vlen and types sizes but also |
449 | | for changes in 'increment', which happen because v2 places some types |
450 | | into ctf_stype_t where v1 would be forced to use the larger non-stype. */ |
451 | |
|
452 | 0 | for (tp = tbuf; tp < tend; |
453 | 0 | tp = (ctf_type_v1_t *) ((uintptr_t) tp + increment + vbytes)) |
454 | 0 | { |
455 | 0 | unsigned short kind = CTF_V1_INFO_KIND (tp->ctt_info); |
456 | 0 | unsigned long vlen = CTF_V1_INFO_VLEN (tp->ctt_info); |
457 | |
|
458 | 0 | size = get_ctt_size_v1 (fp, (const ctf_type_t *) tp, NULL, &increment); |
459 | 0 | vbytes = get_vbytes_v1 (fp, kind, size, vlen); |
460 | |
|
461 | 0 | get_ctt_size_v2_unconverted (fp, (const ctf_type_t *) tp, NULL, |
462 | 0 | &v2increment); |
463 | 0 | v2bytes = get_vbytes_v2 (fp, kind, size, vlen); |
464 | |
|
465 | 0 | if ((vbytes < 0) || (size < 0)) |
466 | 0 | return ECTF_CORRUPT; |
467 | | |
468 | 0 | increase += v2increment - increment; /* May be negative. */ |
469 | 0 | increase += v2bytes - vbytes; |
470 | 0 | } |
471 | | |
472 | | /* Allocate enough room for the new buffer, then copy everything but the type |
473 | | section into place, and reset the base accordingly. Leave the version |
474 | | number unchanged, so that LCTF_INFO_* still works on the |
475 | | as-yet-untranslated type info. */ |
476 | | |
477 | 0 | if ((ctf_base = malloc (fp->ctf_size + increase)) == NULL) |
478 | 0 | return ECTF_ZALLOC; |
479 | | |
480 | | /* Start at ctf_buf, not ctf_base, to squeeze out the original header: we |
481 | | never use it and it is unconverted. */ |
482 | | |
483 | 0 | memcpy (ctf_base, fp->ctf_buf, cth->cth_typeoff); |
484 | 0 | memcpy (ctf_base + cth->cth_stroff + increase, |
485 | 0 | fp->ctf_buf + cth->cth_stroff, cth->cth_strlen); |
486 | |
|
487 | 0 | memset (ctf_base + cth->cth_typeoff, 0, cth->cth_stroff - cth->cth_typeoff |
488 | 0 | + increase); |
489 | |
|
490 | 0 | cth->cth_stroff += increase; |
491 | 0 | fp->ctf_size += increase; |
492 | 0 | assert (cth->cth_stroff >= cth->cth_typeoff); |
493 | 0 | fp->ctf_base = ctf_base; |
494 | 0 | fp->ctf_buf = ctf_base; |
495 | 0 | fp->ctf_dynbase = ctf_base; |
496 | 0 | ctf_set_base (fp, cth, ctf_base); |
497 | |
|
498 | 0 | t2buf = (ctf_type_t *) (fp->ctf_buf + cth->cth_typeoff); |
499 | | |
500 | | /* Iterate through all the types again, upgrading them. |
501 | | |
502 | | Everything that hasn't changed can just be outright memcpy()ed. |
503 | | Things that have changed need field-by-field consideration. */ |
504 | |
|
505 | 0 | for (tp = tbuf, t2p = t2buf; tp < tend; |
506 | 0 | tp = (ctf_type_v1_t *) ((uintptr_t) tp + increment + vbytes), |
507 | 0 | t2p = (ctf_type_t *) ((uintptr_t) t2p + v2increment + v2bytes)) |
508 | 0 | { |
509 | 0 | unsigned short kind = CTF_V1_INFO_KIND (tp->ctt_info); |
510 | 0 | int isroot = CTF_V1_INFO_ISROOT (tp->ctt_info); |
511 | 0 | unsigned long vlen = CTF_V1_INFO_VLEN (tp->ctt_info); |
512 | 0 | ssize_t v2size; |
513 | 0 | void *vdata, *v2data; |
514 | |
|
515 | 0 | size = get_ctt_size_v1 (fp, (const ctf_type_t *) tp, NULL, &increment); |
516 | 0 | vbytes = get_vbytes_v1 (fp, kind, size, vlen); |
517 | |
|
518 | 0 | t2p->ctt_name = tp->ctt_name; |
519 | 0 | t2p->ctt_info = CTF_TYPE_INFO (kind, isroot, vlen); |
520 | |
|
521 | 0 | switch (kind) |
522 | 0 | { |
523 | 0 | case CTF_K_FUNCTION: |
524 | 0 | case CTF_K_FORWARD: |
525 | 0 | case CTF_K_TYPEDEF: |
526 | 0 | case CTF_K_POINTER: |
527 | 0 | case CTF_K_VOLATILE: |
528 | 0 | case CTF_K_CONST: |
529 | 0 | case CTF_K_RESTRICT: |
530 | 0 | t2p->ctt_type = tp->ctt_type; |
531 | 0 | break; |
532 | 0 | case CTF_K_INTEGER: |
533 | 0 | case CTF_K_FLOAT: |
534 | 0 | case CTF_K_ARRAY: |
535 | 0 | case CTF_K_STRUCT: |
536 | 0 | case CTF_K_UNION: |
537 | 0 | case CTF_K_ENUM: |
538 | 0 | case CTF_K_UNKNOWN: |
539 | 0 | if ((size_t) size <= CTF_MAX_SIZE) |
540 | 0 | t2p->ctt_size = size; |
541 | 0 | else |
542 | 0 | { |
543 | 0 | t2p->ctt_lsizehi = CTF_SIZE_TO_LSIZE_HI (size); |
544 | 0 | t2p->ctt_lsizelo = CTF_SIZE_TO_LSIZE_LO (size); |
545 | 0 | } |
546 | 0 | break; |
547 | 0 | } |
548 | | |
549 | 0 | v2size = get_ctt_size_v2 (fp, t2p, NULL, &v2increment); |
550 | 0 | v2bytes = get_vbytes_v2 (fp, kind, v2size, vlen); |
551 | | |
552 | | /* Catch out-of-sync get_ctt_size_*(). The count goes wrong if |
553 | | these are not identical (and having them different makes no |
554 | | sense semantically). */ |
555 | |
|
556 | 0 | assert (size == v2size); |
557 | | |
558 | | /* Now the varlen info. */ |
559 | | |
560 | 0 | vdata = (void *) ((uintptr_t) tp + increment); |
561 | 0 | v2data = (void *) ((uintptr_t) t2p + v2increment); |
562 | |
|
563 | 0 | switch (kind) |
564 | 0 | { |
565 | 0 | case CTF_K_ARRAY: |
566 | 0 | { |
567 | 0 | const ctf_array_v1_t *ap = (const ctf_array_v1_t *) vdata; |
568 | 0 | ctf_array_t *a2p = (ctf_array_t *) v2data; |
569 | |
|
570 | 0 | a2p->cta_contents = ap->cta_contents; |
571 | 0 | a2p->cta_index = ap->cta_index; |
572 | 0 | a2p->cta_nelems = ap->cta_nelems; |
573 | 0 | break; |
574 | 0 | } |
575 | 0 | case CTF_K_STRUCT: |
576 | 0 | case CTF_K_UNION: |
577 | 0 | { |
578 | 0 | ctf_member_t tmp; |
579 | 0 | const ctf_member_v1_t *m1 = (const ctf_member_v1_t *) vdata; |
580 | 0 | const ctf_lmember_v1_t *lm1 = (const ctf_lmember_v1_t *) m1; |
581 | 0 | ctf_member_t *m2 = (ctf_member_t *) v2data; |
582 | 0 | ctf_lmember_t *lm2 = (ctf_lmember_t *) m2; |
583 | 0 | unsigned long i; |
584 | | |
585 | | /* We walk all four pointers forward, but only reference the two |
586 | | that are valid for the given size, to avoid quadruplicating all |
587 | | the code. */ |
588 | |
|
589 | 0 | for (i = vlen; i != 0; i--, m1++, lm1++, m2++, lm2++) |
590 | 0 | { |
591 | 0 | size_t offset; |
592 | 0 | if (size < CTF_LSTRUCT_THRESH_V1) |
593 | 0 | { |
594 | 0 | offset = m1->ctm_offset; |
595 | 0 | tmp.ctm_name = m1->ctm_name; |
596 | 0 | tmp.ctm_type = m1->ctm_type; |
597 | 0 | } |
598 | 0 | else |
599 | 0 | { |
600 | 0 | offset = CTF_LMEM_OFFSET (lm1); |
601 | 0 | tmp.ctm_name = lm1->ctlm_name; |
602 | 0 | tmp.ctm_type = lm1->ctlm_type; |
603 | 0 | } |
604 | 0 | if (size < CTF_LSTRUCT_THRESH) |
605 | 0 | { |
606 | 0 | m2->ctm_name = tmp.ctm_name; |
607 | 0 | m2->ctm_type = tmp.ctm_type; |
608 | 0 | m2->ctm_offset = offset; |
609 | 0 | } |
610 | 0 | else |
611 | 0 | { |
612 | 0 | lm2->ctlm_name = tmp.ctm_name; |
613 | 0 | lm2->ctlm_type = tmp.ctm_type; |
614 | 0 | lm2->ctlm_offsethi = CTF_OFFSET_TO_LMEMHI (offset); |
615 | 0 | lm2->ctlm_offsetlo = CTF_OFFSET_TO_LMEMLO (offset); |
616 | 0 | } |
617 | 0 | } |
618 | 0 | break; |
619 | 0 | } |
620 | 0 | case CTF_K_FUNCTION: |
621 | 0 | { |
622 | 0 | unsigned long i; |
623 | 0 | unsigned short *a1 = (unsigned short *) vdata; |
624 | 0 | uint32_t *a2 = (uint32_t *) v2data; |
625 | |
|
626 | 0 | for (i = vlen; i != 0; i--, a1++, a2++) |
627 | 0 | *a2 = *a1; |
628 | 0 | } |
629 | | /* FALLTHRU */ |
630 | 0 | default: |
631 | | /* Catch out-of-sync get_vbytes_*(). */ |
632 | 0 | assert (vbytes == v2bytes); |
633 | 0 | memcpy (v2data, vdata, vbytes); |
634 | 0 | } |
635 | 0 | } |
636 | | |
637 | | /* Verify that the entire region was converted. If not, we are either |
638 | | converting too much, or too little (leading to a buffer overrun either here |
639 | | or at read time, in init_static_types().) */ |
640 | | |
641 | 0 | assert ((size_t) t2p - (size_t) fp->ctf_buf == cth->cth_stroff); |
642 | | |
643 | 0 | ctf_set_version (fp, cth, CTF_VERSION_1_UPGRADED_3); |
644 | 0 | free (old_ctf_base); |
645 | |
|
646 | 0 | return 0; |
647 | 0 | } |
648 | | |
649 | | /* Upgrade from any earlier version. */ |
650 | | static int |
651 | | upgrade_types (ctf_dict_t *fp, ctf_header_t *cth) |
652 | 0 | { |
653 | 0 | switch (cth->cth_version) |
654 | 0 | { |
655 | | /* v1 requires a full pass and reformatting. */ |
656 | 0 | case CTF_VERSION_1: |
657 | 0 | upgrade_types_v1 (fp, cth); |
658 | | /* FALLTHRU */ |
659 | | /* Already-converted v1 is just like later versions except that its |
660 | | parent/child boundary is unchanged (and much lower). */ |
661 | |
|
662 | 0 | case CTF_VERSION_1_UPGRADED_3: |
663 | 0 | fp->ctf_parmax = CTF_MAX_PTYPE_V1; |
664 | | |
665 | | /* v2 is just the same as v3 except for new types and sections: |
666 | | no upgrading required. */ |
667 | 0 | case CTF_VERSION_2: ; |
668 | | /* FALLTHRU */ |
669 | 0 | } |
670 | 0 | return 0; |
671 | 0 | } |
672 | | |
673 | | static int |
674 | | init_static_types_internal (ctf_dict_t *fp, ctf_header_t *cth, |
675 | | ctf_dynset_t *all_enums); |
676 | | |
677 | | /* Populate statically-defined types (those loaded from a saved buffer). |
678 | | |
679 | | Initialize the type ID translation table with the byte offset of each type, |
680 | | and initialize the hash tables of each named type. Upgrade the type table to |
681 | | the latest supported representation in the process, if needed, and if this |
682 | | recension of libctf supports upgrading. |
683 | | |
684 | | Returns zero on success and a *positive* ECTF_* or errno value on error. |
685 | | |
686 | | This is a wrapper to simplify memory allocation on error in the _internal |
687 | | function that does all the actual work. */ |
688 | | |
689 | | static int |
690 | | init_static_types (ctf_dict_t *fp, ctf_header_t *cth) |
691 | 0 | { |
692 | 0 | ctf_dynset_t *all_enums; |
693 | 0 | int err; |
694 | |
|
695 | 0 | if ((all_enums = ctf_dynset_create (htab_hash_pointer, htab_eq_pointer, |
696 | 0 | NULL)) == NULL) |
697 | 0 | return ENOMEM; |
698 | | |
699 | 0 | err = init_static_types_internal (fp, cth, all_enums); |
700 | 0 | ctf_dynset_destroy (all_enums); |
701 | 0 | return err; |
702 | 0 | } |
703 | | |
704 | | static int |
705 | | init_static_types_internal (ctf_dict_t *fp, ctf_header_t *cth, |
706 | | ctf_dynset_t *all_enums) |
707 | 0 | { |
708 | 0 | const ctf_type_t *tbuf; |
709 | 0 | const ctf_type_t *tend; |
710 | |
|
711 | 0 | unsigned long pop[CTF_K_MAX + 1] = { 0 }; |
712 | 0 | int pop_enumerators = 0; |
713 | 0 | const ctf_type_t *tp; |
714 | 0 | uint32_t id; |
715 | 0 | uint32_t *xp; |
716 | 0 | unsigned long typemax = 0; |
717 | 0 | ctf_next_t *i = NULL; |
718 | 0 | void *k; |
719 | | |
720 | | /* We determine whether the dict is a child or a parent based on the value of |
721 | | cth_parname. */ |
722 | |
|
723 | 0 | int child = cth->cth_parname != 0; |
724 | 0 | int nlstructs = 0, nlunions = 0; |
725 | 0 | int err; |
726 | |
|
727 | 0 | if (_libctf_unlikely_ (fp->ctf_version == CTF_VERSION_1)) |
728 | 0 | { |
729 | 0 | int err; |
730 | 0 | if ((err = upgrade_types (fp, cth)) != 0) |
731 | 0 | return err; /* Upgrade failed. */ |
732 | 0 | } |
733 | | |
734 | 0 | tbuf = (ctf_type_t *) (fp->ctf_buf + cth->cth_typeoff); |
735 | 0 | tend = (ctf_type_t *) (fp->ctf_buf + cth->cth_stroff); |
736 | | |
737 | | /* We make two passes through the entire type section, and one third pass |
738 | | through part of it. In this first pass, we count the number of each type |
739 | | and type-like identifier (like enumerators) and the total number of |
740 | | types. */ |
741 | |
|
742 | 0 | for (tp = tbuf; tp < tend; typemax++) |
743 | 0 | { |
744 | 0 | unsigned short kind = LCTF_INFO_KIND (fp, tp->ctt_info); |
745 | 0 | unsigned long vlen = LCTF_INFO_VLEN (fp, tp->ctt_info); |
746 | 0 | ssize_t size, increment, vbytes; |
747 | |
|
748 | 0 | (void) ctf_get_ctt_size (fp, tp, &size, &increment); |
749 | 0 | vbytes = LCTF_VBYTES (fp, kind, size, vlen); |
750 | |
|
751 | 0 | if (vbytes < 0) |
752 | 0 | return ECTF_CORRUPT; |
753 | | |
754 | | /* For forward declarations, ctt_type is the CTF_K_* kind for the tag, |
755 | | so bump that population count too. */ |
756 | 0 | if (kind == CTF_K_FORWARD) |
757 | 0 | pop[tp->ctt_type]++; |
758 | |
|
759 | 0 | tp = (ctf_type_t *) ((uintptr_t) tp + increment + vbytes); |
760 | 0 | pop[kind]++; |
761 | |
|
762 | 0 | if (kind == CTF_K_ENUM) |
763 | 0 | pop_enumerators += vlen; |
764 | 0 | } |
765 | | |
766 | 0 | if (child) |
767 | 0 | { |
768 | 0 | ctf_dprintf ("CTF dict %p is a child\n", (void *) fp); |
769 | 0 | fp->ctf_flags |= LCTF_CHILD; |
770 | 0 | } |
771 | 0 | else |
772 | 0 | ctf_dprintf ("CTF dict %p is a parent\n", (void *) fp); |
773 | | |
774 | | /* Now that we've counted up the number of each type, we can allocate |
775 | | the hash tables, type translation table, and pointer table. */ |
776 | |
|
777 | 0 | if ((fp->ctf_structs |
778 | 0 | = ctf_dynhash_create_sized (pop[CTF_K_STRUCT], ctf_hash_string, |
779 | 0 | ctf_hash_eq_string, NULL, NULL)) == NULL) |
780 | 0 | return ENOMEM; |
781 | | |
782 | 0 | if ((fp->ctf_unions |
783 | 0 | = ctf_dynhash_create_sized (pop[CTF_K_UNION], ctf_hash_string, |
784 | 0 | ctf_hash_eq_string, NULL, NULL)) == NULL) |
785 | 0 | return ENOMEM; |
786 | | |
787 | 0 | if ((fp->ctf_enums |
788 | 0 | = ctf_dynhash_create_sized (pop[CTF_K_ENUM], ctf_hash_string, |
789 | 0 | ctf_hash_eq_string, NULL, NULL)) == NULL) |
790 | 0 | return ENOMEM; |
791 | | |
792 | 0 | if ((fp->ctf_names |
793 | 0 | = ctf_dynhash_create_sized (pop[CTF_K_UNKNOWN] + |
794 | 0 | pop[CTF_K_INTEGER] + |
795 | 0 | pop[CTF_K_FLOAT] + |
796 | 0 | pop[CTF_K_FUNCTION] + |
797 | 0 | pop[CTF_K_TYPEDEF] + |
798 | 0 | pop[CTF_K_POINTER] + |
799 | 0 | pop[CTF_K_VOLATILE] + |
800 | 0 | pop[CTF_K_CONST] + |
801 | 0 | pop[CTF_K_RESTRICT] + |
802 | 0 | pop_enumerators, |
803 | 0 | ctf_hash_string, |
804 | 0 | ctf_hash_eq_string, NULL, NULL)) == NULL) |
805 | 0 | return ENOMEM; |
806 | | |
807 | 0 | if ((fp->ctf_conflicting_enums |
808 | 0 | = ctf_dynset_create (htab_hash_string, htab_eq_string, NULL)) == NULL) |
809 | 0 | return ENOMEM; |
810 | | |
811 | | /* The ptrtab and txlate can be appropriately sized for precisely this set |
812 | | of types: the txlate because it is only used to look up static types, |
813 | | so dynamic types added later will never go through it, and the ptrtab |
814 | | because later-added types will call grow_ptrtab() automatically, as |
815 | | needed. */ |
816 | | |
817 | 0 | fp->ctf_txlate = malloc (sizeof (uint32_t) * (typemax + 1)); |
818 | 0 | fp->ctf_ptrtab_len = typemax + 1; |
819 | 0 | fp->ctf_ptrtab = malloc (sizeof (uint32_t) * fp->ctf_ptrtab_len); |
820 | 0 | fp->ctf_stypes = typemax; |
821 | |
|
822 | 0 | if (fp->ctf_txlate == NULL || fp->ctf_ptrtab == NULL) |
823 | 0 | return ENOMEM; /* Memory allocation failed. */ |
824 | | |
825 | 0 | xp = fp->ctf_txlate; |
826 | 0 | *xp++ = 0; /* Type id 0 is used as a sentinel value. */ |
827 | |
|
828 | 0 | memset (fp->ctf_txlate, 0, sizeof (uint32_t) * (typemax + 1)); |
829 | 0 | memset (fp->ctf_ptrtab, 0, sizeof (uint32_t) * (typemax + 1)); |
830 | | |
831 | | /* In the second pass through the types, we fill in each entry of the |
832 | | type and pointer tables and add names to the appropriate hashes. |
833 | | |
834 | | (Not all names are added in this pass, only type names. See below.) |
835 | | |
836 | | Bump ctf_typemax as we go, but keep it one higher than normal, so that |
837 | | the type being read in is considered a valid type and it is at least |
838 | | barely possible to run simple lookups on it. */ |
839 | |
|
840 | 0 | for (id = 1, fp->ctf_typemax = 1, tp = tbuf; tp < tend; xp++, id++, fp->ctf_typemax++) |
841 | 0 | { |
842 | 0 | unsigned short kind = LCTF_INFO_KIND (fp, tp->ctt_info); |
843 | 0 | unsigned short isroot = LCTF_INFO_ISROOT (fp, tp->ctt_info); |
844 | 0 | unsigned long vlen = LCTF_INFO_VLEN (fp, tp->ctt_info); |
845 | 0 | ssize_t size, increment, vbytes; |
846 | |
|
847 | 0 | const char *name; |
848 | |
|
849 | 0 | (void) ctf_get_ctt_size (fp, tp, &size, &increment); |
850 | 0 | name = ctf_strptr (fp, tp->ctt_name); |
851 | | /* Cannot fail: shielded by call in loop above. */ |
852 | 0 | vbytes = LCTF_VBYTES (fp, kind, size, vlen); |
853 | |
|
854 | 0 | *xp = (uint32_t) ((uintptr_t) tp - (uintptr_t) fp->ctf_buf); |
855 | |
|
856 | 0 | switch (kind) |
857 | 0 | { |
858 | 0 | case CTF_K_UNKNOWN: |
859 | 0 | case CTF_K_INTEGER: |
860 | 0 | case CTF_K_FLOAT: |
861 | 0 | { |
862 | 0 | ctf_id_t existing; |
863 | 0 | ctf_encoding_t existing_en; |
864 | 0 | ctf_encoding_t this_en; |
865 | |
|
866 | 0 | if (!isroot) |
867 | 0 | break; |
868 | | |
869 | | /* Names are reused by bitfields, which are differentiated by |
870 | | their encodings. So check for the type already existing, and |
871 | | iff the new type is a root-visible non-bitfield, replace the |
872 | | old one. It's a little hard to figure out whether a type is |
873 | | a non-bitfield without already knowing that type's native |
874 | | width, but we can converge on it by replacing an existing |
875 | | type as long as the new type is zero-offset and has a |
876 | | bit-width wider than the existing one, since the native type |
877 | | must necessarily have a bit-width at least as wide as any |
878 | | bitfield based on it. */ |
879 | | |
880 | 0 | if (((existing = ctf_dynhash_lookup_type (fp->ctf_names, name)) == 0) |
881 | 0 | || ctf_type_encoding (fp, existing, &existing_en) != 0 |
882 | 0 | || (ctf_type_encoding (fp, LCTF_INDEX_TO_TYPE (fp, id, child), &this_en) == 0 |
883 | 0 | && this_en.cte_offset == 0 |
884 | 0 | && (existing_en.cte_offset != 0 |
885 | 0 | || existing_en.cte_bits < this_en.cte_bits))) |
886 | 0 | { |
887 | 0 | err = ctf_dynhash_insert_type (fp, fp->ctf_names, |
888 | 0 | LCTF_INDEX_TO_TYPE (fp, id, child), |
889 | 0 | tp->ctt_name); |
890 | 0 | if (err != 0) |
891 | 0 | return err * -1; |
892 | 0 | } |
893 | 0 | break; |
894 | 0 | } |
895 | | |
896 | | /* These kinds have no name, so do not need interning into any |
897 | | hashtables. */ |
898 | 0 | case CTF_K_ARRAY: |
899 | 0 | case CTF_K_SLICE: |
900 | 0 | break; |
901 | | |
902 | 0 | case CTF_K_FUNCTION: |
903 | 0 | if (!isroot) |
904 | 0 | break; |
905 | | |
906 | 0 | err = ctf_dynhash_insert_type (fp, fp->ctf_names, |
907 | 0 | LCTF_INDEX_TO_TYPE (fp, id, child), |
908 | 0 | tp->ctt_name); |
909 | 0 | if (err != 0) |
910 | 0 | return err * -1; |
911 | 0 | break; |
912 | | |
913 | 0 | case CTF_K_STRUCT: |
914 | 0 | if (size >= CTF_LSTRUCT_THRESH) |
915 | 0 | nlstructs++; |
916 | |
|
917 | 0 | if (!isroot) |
918 | 0 | break; |
919 | | |
920 | 0 | err = ctf_dynhash_insert_type (fp, fp->ctf_structs, |
921 | 0 | LCTF_INDEX_TO_TYPE (fp, id, child), |
922 | 0 | tp->ctt_name); |
923 | |
|
924 | 0 | if (err != 0) |
925 | 0 | return err * -1; |
926 | | |
927 | 0 | break; |
928 | | |
929 | 0 | case CTF_K_UNION: |
930 | 0 | if (size >= CTF_LSTRUCT_THRESH) |
931 | 0 | nlunions++; |
932 | |
|
933 | 0 | if (!isroot) |
934 | 0 | break; |
935 | | |
936 | 0 | err = ctf_dynhash_insert_type (fp, fp->ctf_unions, |
937 | 0 | LCTF_INDEX_TO_TYPE (fp, id, child), |
938 | 0 | tp->ctt_name); |
939 | |
|
940 | 0 | if (err != 0) |
941 | 0 | return err * -1; |
942 | 0 | break; |
943 | | |
944 | 0 | case CTF_K_ENUM: |
945 | 0 | { |
946 | 0 | if (!isroot) |
947 | 0 | break; |
948 | | |
949 | 0 | err = ctf_dynhash_insert_type (fp, fp->ctf_enums, |
950 | 0 | LCTF_INDEX_TO_TYPE (fp, id, child), |
951 | 0 | tp->ctt_name); |
952 | |
|
953 | 0 | if (err != 0) |
954 | 0 | return err * -1; |
955 | | |
956 | | /* Remember all enums for later rescanning. */ |
957 | | |
958 | 0 | err = ctf_dynset_insert (all_enums, (void *) (ptrdiff_t) |
959 | 0 | LCTF_INDEX_TO_TYPE (fp, id, child)); |
960 | 0 | if (err != 0) |
961 | 0 | return err * -1; |
962 | 0 | break; |
963 | 0 | } |
964 | | |
965 | 0 | case CTF_K_TYPEDEF: |
966 | 0 | if (!isroot) |
967 | 0 | break; |
968 | | |
969 | 0 | err = ctf_dynhash_insert_type (fp, fp->ctf_names, |
970 | 0 | LCTF_INDEX_TO_TYPE (fp, id, child), |
971 | 0 | tp->ctt_name); |
972 | 0 | if (err != 0) |
973 | 0 | return err * -1; |
974 | 0 | break; |
975 | | |
976 | 0 | case CTF_K_FORWARD: |
977 | 0 | { |
978 | 0 | ctf_dynhash_t *h = ctf_name_table (fp, tp->ctt_type); |
979 | |
|
980 | 0 | if (!isroot) |
981 | 0 | break; |
982 | | |
983 | | /* Only insert forward tags into the given hash if the type or tag |
984 | | name is not already present. */ |
985 | 0 | if (ctf_dynhash_lookup_type (h, name) == 0) |
986 | 0 | { |
987 | 0 | err = ctf_dynhash_insert_type (fp, h, LCTF_INDEX_TO_TYPE (fp, id, child), |
988 | 0 | tp->ctt_name); |
989 | 0 | if (err != 0) |
990 | 0 | return err * -1; |
991 | 0 | } |
992 | 0 | break; |
993 | 0 | } |
994 | | |
995 | 0 | case CTF_K_POINTER: |
996 | | /* If the type referenced by the pointer is in this CTF dict, then |
997 | | store the index of the pointer type in fp->ctf_ptrtab[ index of |
998 | | referenced type ]. */ |
999 | |
|
1000 | 0 | if (LCTF_TYPE_ISCHILD (fp, tp->ctt_type) == child |
1001 | 0 | && LCTF_TYPE_TO_INDEX (fp, tp->ctt_type) <= fp->ctf_typemax) |
1002 | 0 | fp->ctf_ptrtab[LCTF_TYPE_TO_INDEX (fp, tp->ctt_type)] = id; |
1003 | | /*FALLTHRU*/ |
1004 | |
|
1005 | 0 | case CTF_K_VOLATILE: |
1006 | 0 | case CTF_K_CONST: |
1007 | 0 | case CTF_K_RESTRICT: |
1008 | 0 | if (!isroot) |
1009 | 0 | break; |
1010 | | |
1011 | 0 | err = ctf_dynhash_insert_type (fp, fp->ctf_names, |
1012 | 0 | LCTF_INDEX_TO_TYPE (fp, id, child), |
1013 | 0 | tp->ctt_name); |
1014 | 0 | if (err != 0) |
1015 | 0 | return err * -1; |
1016 | 0 | break; |
1017 | 0 | default: |
1018 | 0 | ctf_err_warn (fp, 0, ECTF_CORRUPT, |
1019 | 0 | _("init_static_types(): unhandled CTF kind: %x"), kind); |
1020 | 0 | return ECTF_CORRUPT; |
1021 | 0 | } |
1022 | 0 | tp = (ctf_type_t *) ((uintptr_t) tp + increment + vbytes); |
1023 | 0 | } |
1024 | 0 | fp->ctf_typemax--; |
1025 | 0 | assert (fp->ctf_typemax == typemax); |
1026 | | |
1027 | 0 | ctf_dprintf ("%lu total types processed\n", fp->ctf_typemax); |
1028 | | |
1029 | | /* In the third pass, we traverse the enums we spotted earlier and track all |
1030 | | the enumeration constants to aid in future detection of duplicates. |
1031 | | |
1032 | | Doing this in a third pass is necessary to avoid the case where an |
1033 | | enum appears with a constant FOO, then later a type named FOO appears, |
1034 | | too late to spot the conflict by checking the enum's constants. */ |
1035 | |
|
1036 | 0 | while ((err = ctf_dynset_next (all_enums, &i, &k)) == 0) |
1037 | 0 | { |
1038 | 0 | ctf_id_t enum_id = (uintptr_t) k; |
1039 | 0 | ctf_next_t *i_constants = NULL; |
1040 | 0 | const char *cte_name; |
1041 | |
|
1042 | 0 | while ((cte_name = ctf_enum_next (fp, enum_id, &i_constants, NULL)) != NULL) |
1043 | 0 | { |
1044 | 0 | if (ctf_track_enumerator (fp, enum_id, cte_name) < 0) |
1045 | 0 | { |
1046 | 0 | ctf_next_destroy (i_constants); |
1047 | 0 | ctf_next_destroy (i); |
1048 | 0 | return ctf_errno (fp); |
1049 | 0 | } |
1050 | 0 | } |
1051 | 0 | if (ctf_errno (fp) != ECTF_NEXT_END) |
1052 | 0 | { |
1053 | 0 | ctf_next_destroy (i); |
1054 | 0 | return ctf_errno (fp); |
1055 | 0 | } |
1056 | 0 | } |
1057 | 0 | if (err != ECTF_NEXT_END) |
1058 | 0 | return err; |
1059 | | |
1060 | 0 | ctf_dprintf ("%zu enum names hashed\n", |
1061 | 0 | ctf_dynhash_elements (fp->ctf_enums)); |
1062 | 0 | ctf_dprintf ("%zu conflicting enumerators identified\n", |
1063 | 0 | ctf_dynset_elements (fp->ctf_conflicting_enums)); |
1064 | 0 | ctf_dprintf ("%zu struct names hashed (%d long)\n", |
1065 | 0 | ctf_dynhash_elements (fp->ctf_structs), nlstructs); |
1066 | 0 | ctf_dprintf ("%zu union names hashed (%d long)\n", |
1067 | 0 | ctf_dynhash_elements (fp->ctf_unions), nlunions); |
1068 | 0 | ctf_dprintf ("%zu base type names and identifiers hashed\n", |
1069 | 0 | ctf_dynhash_elements (fp->ctf_names)); |
1070 | |
|
1071 | 0 | return 0; |
1072 | 0 | } |
1073 | | |
1074 | | /* Endianness-flipping routines. |
1075 | | |
1076 | | We flip everything, mindlessly, even 1-byte entities, so that future |
1077 | | expansions do not require changes to this code. */ |
1078 | | |
1079 | | /* Flip the endianness of the CTF header. */ |
1080 | | |
1081 | | void |
1082 | | ctf_flip_header (ctf_header_t *cth) |
1083 | 0 | { |
1084 | 0 | swap_thing (cth->cth_preamble.ctp_magic); |
1085 | 0 | swap_thing (cth->cth_preamble.ctp_version); |
1086 | 0 | swap_thing (cth->cth_preamble.ctp_flags); |
1087 | 0 | swap_thing (cth->cth_parlabel); |
1088 | 0 | swap_thing (cth->cth_parname); |
1089 | 0 | swap_thing (cth->cth_cuname); |
1090 | 0 | swap_thing (cth->cth_objtoff); |
1091 | 0 | swap_thing (cth->cth_funcoff); |
1092 | 0 | swap_thing (cth->cth_objtidxoff); |
1093 | 0 | swap_thing (cth->cth_funcidxoff); |
1094 | 0 | swap_thing (cth->cth_varoff); |
1095 | 0 | swap_thing (cth->cth_typeoff); |
1096 | 0 | swap_thing (cth->cth_stroff); |
1097 | 0 | swap_thing (cth->cth_strlen); |
1098 | 0 | } |
1099 | | |
1100 | | /* Flip the endianness of the label section, an array of ctf_lblent_t. */ |
1101 | | |
1102 | | static void |
1103 | | flip_lbls (void *start, size_t len) |
1104 | 0 | { |
1105 | 0 | ctf_lblent_t *lbl = start; |
1106 | 0 | ssize_t i; |
1107 | |
|
1108 | 0 | for (i = len / sizeof (struct ctf_lblent); i > 0; lbl++, i--) |
1109 | 0 | { |
1110 | 0 | swap_thing (lbl->ctl_label); |
1111 | 0 | swap_thing (lbl->ctl_type); |
1112 | 0 | } |
1113 | 0 | } |
1114 | | |
1115 | | /* Flip the endianness of the data-object or function sections or their indexes, |
1116 | | all arrays of uint32_t. */ |
1117 | | |
1118 | | static void |
1119 | | flip_objts (void *start, size_t len) |
1120 | 0 | { |
1121 | 0 | uint32_t *obj = start; |
1122 | 0 | ssize_t i; |
1123 | |
|
1124 | 0 | for (i = len / sizeof (uint32_t); i > 0; obj++, i--) |
1125 | 0 | swap_thing (*obj); |
1126 | 0 | } |
1127 | | |
1128 | | /* Flip the endianness of the variable section, an array of ctf_varent_t. */ |
1129 | | |
1130 | | static void |
1131 | | flip_vars (void *start, size_t len) |
1132 | 0 | { |
1133 | 0 | ctf_varent_t *var = start; |
1134 | 0 | ssize_t i; |
1135 | |
|
1136 | 0 | for (i = len / sizeof (struct ctf_varent); i > 0; var++, i--) |
1137 | 0 | { |
1138 | 0 | swap_thing (var->ctv_name); |
1139 | 0 | swap_thing (var->ctv_type); |
1140 | 0 | } |
1141 | 0 | } |
1142 | | |
1143 | | /* Flip the endianness of the type section, a tagged array of ctf_type or |
1144 | | ctf_stype followed by variable data. */ |
1145 | | |
1146 | | static int |
1147 | | flip_types (ctf_dict_t *fp, void *start, size_t len, int to_foreign) |
1148 | 0 | { |
1149 | 0 | ctf_type_t *t = start; |
1150 | |
|
1151 | 0 | while ((uintptr_t) t < ((uintptr_t) start) + len) |
1152 | 0 | { |
1153 | 0 | uint32_t kind; |
1154 | 0 | size_t size; |
1155 | 0 | uint32_t vlen; |
1156 | 0 | size_t vbytes; |
1157 | |
|
1158 | 0 | if (to_foreign) |
1159 | 0 | { |
1160 | 0 | kind = CTF_V2_INFO_KIND (t->ctt_info); |
1161 | 0 | size = t->ctt_size; |
1162 | 0 | vlen = CTF_V2_INFO_VLEN (t->ctt_info); |
1163 | 0 | vbytes = get_vbytes_v2 (fp, kind, size, vlen); |
1164 | 0 | } |
1165 | |
|
1166 | 0 | swap_thing (t->ctt_name); |
1167 | 0 | swap_thing (t->ctt_info); |
1168 | 0 | swap_thing (t->ctt_size); |
1169 | |
|
1170 | 0 | if (!to_foreign) |
1171 | 0 | { |
1172 | 0 | kind = CTF_V2_INFO_KIND (t->ctt_info); |
1173 | 0 | size = t->ctt_size; |
1174 | 0 | vlen = CTF_V2_INFO_VLEN (t->ctt_info); |
1175 | 0 | vbytes = get_vbytes_v2 (fp, kind, size, vlen); |
1176 | 0 | } |
1177 | |
|
1178 | 0 | if (_libctf_unlikely_ (size == CTF_LSIZE_SENT)) |
1179 | 0 | { |
1180 | 0 | if (to_foreign) |
1181 | 0 | size = CTF_TYPE_LSIZE (t); |
1182 | |
|
1183 | 0 | swap_thing (t->ctt_lsizehi); |
1184 | 0 | swap_thing (t->ctt_lsizelo); |
1185 | |
|
1186 | 0 | if (!to_foreign) |
1187 | 0 | size = CTF_TYPE_LSIZE (t); |
1188 | |
|
1189 | 0 | t = (ctf_type_t *) ((uintptr_t) t + sizeof (ctf_type_t)); |
1190 | 0 | } |
1191 | 0 | else |
1192 | 0 | t = (ctf_type_t *) ((uintptr_t) t + sizeof (ctf_stype_t)); |
1193 | | |
1194 | 0 | switch (kind) |
1195 | 0 | { |
1196 | 0 | case CTF_K_FORWARD: |
1197 | 0 | case CTF_K_UNKNOWN: |
1198 | 0 | case CTF_K_POINTER: |
1199 | 0 | case CTF_K_TYPEDEF: |
1200 | 0 | case CTF_K_VOLATILE: |
1201 | 0 | case CTF_K_CONST: |
1202 | 0 | case CTF_K_RESTRICT: |
1203 | | /* These types have no vlen data to swap. */ |
1204 | 0 | assert (vbytes == 0); |
1205 | 0 | break; |
1206 | | |
1207 | 0 | case CTF_K_INTEGER: |
1208 | 0 | case CTF_K_FLOAT: |
1209 | 0 | { |
1210 | | /* These types have a single uint32_t. */ |
1211 | |
|
1212 | 0 | uint32_t *item = (uint32_t *) t; |
1213 | |
|
1214 | 0 | swap_thing (*item); |
1215 | 0 | break; |
1216 | 0 | } |
1217 | | |
1218 | 0 | case CTF_K_FUNCTION: |
1219 | 0 | { |
1220 | | /* This type has a bunch of uint32_ts. */ |
1221 | |
|
1222 | 0 | uint32_t *item = (uint32_t *) t; |
1223 | 0 | ssize_t i; |
1224 | |
|
1225 | 0 | for (i = vlen; i > 0; item++, i--) |
1226 | 0 | swap_thing (*item); |
1227 | 0 | break; |
1228 | 0 | } |
1229 | | |
1230 | 0 | case CTF_K_ARRAY: |
1231 | 0 | { |
1232 | | /* This has a single ctf_array_t. */ |
1233 | |
|
1234 | 0 | ctf_array_t *a = (ctf_array_t *) t; |
1235 | |
|
1236 | 0 | assert (vbytes == sizeof (ctf_array_t)); |
1237 | 0 | swap_thing (a->cta_contents); |
1238 | 0 | swap_thing (a->cta_index); |
1239 | 0 | swap_thing (a->cta_nelems); |
1240 | |
|
1241 | 0 | break; |
1242 | 0 | } |
1243 | | |
1244 | 0 | case CTF_K_SLICE: |
1245 | 0 | { |
1246 | | /* This has a single ctf_slice_t. */ |
1247 | |
|
1248 | 0 | ctf_slice_t *s = (ctf_slice_t *) t; |
1249 | |
|
1250 | 0 | assert (vbytes == sizeof (ctf_slice_t)); |
1251 | 0 | swap_thing (s->cts_type); |
1252 | 0 | swap_thing (s->cts_offset); |
1253 | 0 | swap_thing (s->cts_bits); |
1254 | |
|
1255 | 0 | break; |
1256 | 0 | } |
1257 | | |
1258 | 0 | case CTF_K_STRUCT: |
1259 | 0 | case CTF_K_UNION: |
1260 | 0 | { |
1261 | | /* This has an array of ctf_member or ctf_lmember, depending on |
1262 | | size. We could consider it to be a simple array of uint32_t, |
1263 | | but for safety's sake in case these structures ever acquire |
1264 | | non-uint32_t members, do it member by member. */ |
1265 | |
|
1266 | 0 | if (_libctf_unlikely_ (size >= CTF_LSTRUCT_THRESH)) |
1267 | 0 | { |
1268 | 0 | ctf_lmember_t *lm = (ctf_lmember_t *) t; |
1269 | 0 | ssize_t i; |
1270 | 0 | for (i = vlen; i > 0; i--, lm++) |
1271 | 0 | { |
1272 | 0 | swap_thing (lm->ctlm_name); |
1273 | 0 | swap_thing (lm->ctlm_offsethi); |
1274 | 0 | swap_thing (lm->ctlm_type); |
1275 | 0 | swap_thing (lm->ctlm_offsetlo); |
1276 | 0 | } |
1277 | 0 | } |
1278 | 0 | else |
1279 | 0 | { |
1280 | 0 | ctf_member_t *m = (ctf_member_t *) t; |
1281 | 0 | ssize_t i; |
1282 | 0 | for (i = vlen; i > 0; i--, m++) |
1283 | 0 | { |
1284 | 0 | swap_thing (m->ctm_name); |
1285 | 0 | swap_thing (m->ctm_offset); |
1286 | 0 | swap_thing (m->ctm_type); |
1287 | 0 | } |
1288 | 0 | } |
1289 | 0 | break; |
1290 | 0 | } |
1291 | | |
1292 | 0 | case CTF_K_ENUM: |
1293 | 0 | { |
1294 | | /* This has an array of ctf_enum_t. */ |
1295 | |
|
1296 | 0 | ctf_enum_t *item = (ctf_enum_t *) t; |
1297 | 0 | ssize_t i; |
1298 | |
|
1299 | 0 | for (i = vlen; i > 0; item++, i--) |
1300 | 0 | { |
1301 | 0 | swap_thing (item->cte_name); |
1302 | 0 | swap_thing (item->cte_value); |
1303 | 0 | } |
1304 | 0 | break; |
1305 | 0 | } |
1306 | 0 | default: |
1307 | 0 | ctf_err_warn (fp, 0, ECTF_CORRUPT, |
1308 | 0 | _("unhandled CTF kind in endianness conversion: %x"), |
1309 | 0 | kind); |
1310 | 0 | return ECTF_CORRUPT; |
1311 | 0 | } |
1312 | | |
1313 | 0 | t = (ctf_type_t *) ((uintptr_t) t + vbytes); |
1314 | 0 | } |
1315 | | |
1316 | 0 | return 0; |
1317 | 0 | } |
1318 | | |
1319 | | /* Flip the endianness of BUF, given the offsets in the (native-endianness) CTH. |
1320 | | If TO_FOREIGN is set, flip to foreign-endianness; if not, flip away. |
1321 | | |
1322 | | All of this stuff happens before the header is fully initialized, so the |
1323 | | LCTF_*() macros cannot be used yet. Since we do not try to endian-convert v1 |
1324 | | data, this is no real loss. */ |
1325 | | |
1326 | | int |
1327 | | ctf_flip (ctf_dict_t *fp, ctf_header_t *cth, unsigned char *buf, |
1328 | | int to_foreign) |
1329 | 0 | { |
1330 | 0 | ctf_dprintf("flipping endianness\n"); |
1331 | |
|
1332 | 0 | flip_lbls (buf + cth->cth_lbloff, cth->cth_objtoff - cth->cth_lbloff); |
1333 | 0 | flip_objts (buf + cth->cth_objtoff, cth->cth_funcoff - cth->cth_objtoff); |
1334 | 0 | flip_objts (buf + cth->cth_funcoff, cth->cth_objtidxoff - cth->cth_funcoff); |
1335 | 0 | flip_objts (buf + cth->cth_objtidxoff, cth->cth_funcidxoff - cth->cth_objtidxoff); |
1336 | 0 | flip_objts (buf + cth->cth_funcidxoff, cth->cth_varoff - cth->cth_funcidxoff); |
1337 | 0 | flip_vars (buf + cth->cth_varoff, cth->cth_typeoff - cth->cth_varoff); |
1338 | 0 | return flip_types (fp, buf + cth->cth_typeoff, |
1339 | 0 | cth->cth_stroff - cth->cth_typeoff, to_foreign); |
1340 | 0 | } |
1341 | | |
1342 | | /* Set up the ctl hashes in a ctf_dict_t. Called by both writable and |
1343 | | non-writable dictionary initialization. */ |
1344 | | void ctf_set_ctl_hashes (ctf_dict_t *fp) |
1345 | 0 | { |
1346 | | /* Initialize the ctf_lookup_by_name top-level dictionary. We keep an |
1347 | | array of type name prefixes and the corresponding ctf_hash to use. */ |
1348 | 0 | fp->ctf_lookups[0].ctl_prefix = "struct"; |
1349 | 0 | fp->ctf_lookups[0].ctl_len = strlen (fp->ctf_lookups[0].ctl_prefix); |
1350 | 0 | fp->ctf_lookups[0].ctl_hash = fp->ctf_structs; |
1351 | 0 | fp->ctf_lookups[1].ctl_prefix = "union"; |
1352 | 0 | fp->ctf_lookups[1].ctl_len = strlen (fp->ctf_lookups[1].ctl_prefix); |
1353 | 0 | fp->ctf_lookups[1].ctl_hash = fp->ctf_unions; |
1354 | 0 | fp->ctf_lookups[2].ctl_prefix = "enum"; |
1355 | 0 | fp->ctf_lookups[2].ctl_len = strlen (fp->ctf_lookups[2].ctl_prefix); |
1356 | 0 | fp->ctf_lookups[2].ctl_hash = fp->ctf_enums; |
1357 | 0 | fp->ctf_lookups[3].ctl_prefix = _CTF_NULLSTR; |
1358 | 0 | fp->ctf_lookups[3].ctl_len = strlen (fp->ctf_lookups[3].ctl_prefix); |
1359 | 0 | fp->ctf_lookups[3].ctl_hash = fp->ctf_names; |
1360 | 0 | fp->ctf_lookups[4].ctl_prefix = NULL; |
1361 | 0 | fp->ctf_lookups[4].ctl_len = 0; |
1362 | 0 | fp->ctf_lookups[4].ctl_hash = NULL; |
1363 | 0 | } |
1364 | | |
1365 | | /* Open a CTF file, mocking up a suitable ctf_sect. */ |
1366 | | |
1367 | | ctf_dict_t *ctf_simple_open (const char *ctfsect, size_t ctfsect_size, |
1368 | | const char *symsect, size_t symsect_size, |
1369 | | size_t symsect_entsize, |
1370 | | const char *strsect, size_t strsect_size, |
1371 | | int *errp) |
1372 | 0 | { |
1373 | 0 | ctf_sect_t skeleton; |
1374 | |
|
1375 | 0 | ctf_sect_t ctf_sect, sym_sect, str_sect; |
1376 | 0 | ctf_sect_t *ctfsectp = NULL; |
1377 | 0 | ctf_sect_t *symsectp = NULL; |
1378 | 0 | ctf_sect_t *strsectp = NULL; |
1379 | |
|
1380 | 0 | skeleton.cts_name = _CTF_SECTION; |
1381 | 0 | skeleton.cts_entsize = 1; |
1382 | |
|
1383 | 0 | if (ctfsect) |
1384 | 0 | { |
1385 | 0 | memcpy (&ctf_sect, &skeleton, sizeof (struct ctf_sect)); |
1386 | 0 | ctf_sect.cts_data = ctfsect; |
1387 | 0 | ctf_sect.cts_size = ctfsect_size; |
1388 | 0 | ctfsectp = &ctf_sect; |
1389 | 0 | } |
1390 | |
|
1391 | 0 | if (symsect) |
1392 | 0 | { |
1393 | 0 | memcpy (&sym_sect, &skeleton, sizeof (struct ctf_sect)); |
1394 | 0 | sym_sect.cts_data = symsect; |
1395 | 0 | sym_sect.cts_size = symsect_size; |
1396 | 0 | sym_sect.cts_entsize = symsect_entsize; |
1397 | 0 | symsectp = &sym_sect; |
1398 | 0 | } |
1399 | |
|
1400 | 0 | if (strsect) |
1401 | 0 | { |
1402 | 0 | memcpy (&str_sect, &skeleton, sizeof (struct ctf_sect)); |
1403 | 0 | str_sect.cts_data = strsect; |
1404 | 0 | str_sect.cts_size = strsect_size; |
1405 | 0 | strsectp = &str_sect; |
1406 | 0 | } |
1407 | |
|
1408 | 0 | return ctf_bufopen (ctfsectp, symsectp, strsectp, errp); |
1409 | 0 | } |
1410 | | |
1411 | | /* Decode the specified CTF buffer and optional symbol table, and create a new |
1412 | | CTF dict representing the symbolic debugging information. This code can |
1413 | | be used directly by the debugger, or it can be used as the engine for |
1414 | | ctf_fdopen() or ctf_open(), below. */ |
1415 | | |
1416 | | ctf_dict_t * |
1417 | | ctf_bufopen (const ctf_sect_t *ctfsect, const ctf_sect_t *symsect, |
1418 | | const ctf_sect_t *strsect, int *errp) |
1419 | 0 | { |
1420 | 0 | const ctf_preamble_t *pp; |
1421 | 0 | size_t hdrsz = sizeof (ctf_header_t); |
1422 | 0 | ctf_header_t *hp; |
1423 | 0 | ctf_dict_t *fp; |
1424 | 0 | int foreign_endian = 0; |
1425 | 0 | int err; |
1426 | |
|
1427 | 0 | libctf_init_debug(); |
1428 | |
|
1429 | 0 | ctf_set_open_errno (errp, 0); |
1430 | |
|
1431 | 0 | if ((ctfsect == NULL) || ((symsect != NULL) && (strsect == NULL))) |
1432 | 0 | return (ctf_set_open_errno (errp, EINVAL)); |
1433 | | |
1434 | 0 | if (symsect != NULL && symsect->cts_entsize != sizeof (Elf32_Sym) && |
1435 | 0 | symsect->cts_entsize != sizeof (Elf64_Sym)) |
1436 | 0 | return (ctf_set_open_errno (errp, ECTF_SYMTAB)); |
1437 | | |
1438 | 0 | if (symsect != NULL && symsect->cts_data == NULL) |
1439 | 0 | return (ctf_set_open_errno (errp, ECTF_SYMBAD)); |
1440 | | |
1441 | 0 | if (strsect != NULL && strsect->cts_data == NULL) |
1442 | 0 | return (ctf_set_open_errno (errp, ECTF_STRBAD)); |
1443 | | |
1444 | 0 | if (ctfsect->cts_data == NULL |
1445 | 0 | || ctfsect->cts_size < sizeof (ctf_preamble_t)) |
1446 | 0 | return (ctf_set_open_errno (errp, ECTF_NOCTFBUF)); |
1447 | | |
1448 | 0 | pp = (const ctf_preamble_t *) ctfsect->cts_data; |
1449 | |
|
1450 | 0 | ctf_dprintf ("ctf_bufopen: magic=0x%x version=%u\n", |
1451 | 0 | pp->ctp_magic, pp->ctp_version); |
1452 | | |
1453 | | /* Validate each part of the CTF header. |
1454 | | |
1455 | | First, we validate the preamble (common to all versions). At that point, |
1456 | | we know the endianness and specific header version, and can validate the |
1457 | | version-specific parts including section offsets and alignments. */ |
1458 | |
|
1459 | 0 | if (_libctf_unlikely_ (pp->ctp_magic != CTF_MAGIC)) |
1460 | 0 | { |
1461 | 0 | if (pp->ctp_magic == bswap_16 (CTF_MAGIC)) |
1462 | 0 | foreign_endian = 1; |
1463 | 0 | else |
1464 | 0 | return (ctf_set_open_errno (errp, ECTF_NOCTFBUF)); |
1465 | 0 | } |
1466 | | |
1467 | 0 | if (_libctf_unlikely_ ((pp->ctp_version < CTF_VERSION_1) |
1468 | 0 | || (pp->ctp_version > CTF_VERSION_3))) |
1469 | 0 | return (ctf_set_open_errno (errp, ECTF_CTFVERS)); |
1470 | | |
1471 | 0 | if ((symsect != NULL) && (pp->ctp_version < CTF_VERSION_2)) |
1472 | 0 | { |
1473 | | /* The symtab can contain function entries which contain embedded ctf |
1474 | | info. We do not support dynamically upgrading such entries (none |
1475 | | should exist in any case, since dwarf2ctf does not create them). */ |
1476 | |
|
1477 | 0 | ctf_err_warn (NULL, 0, ECTF_NOTSUP, _("ctf_bufopen: CTF version %d " |
1478 | 0 | "symsect not supported"), |
1479 | 0 | pp->ctp_version); |
1480 | 0 | return (ctf_set_open_errno (errp, ECTF_NOTSUP)); |
1481 | 0 | } |
1482 | | |
1483 | 0 | if (pp->ctp_version < CTF_VERSION_3) |
1484 | 0 | hdrsz = sizeof (ctf_header_v2_t); |
1485 | |
|
1486 | 0 | if (_libctf_unlikely_ (pp->ctp_flags > CTF_F_MAX)) |
1487 | 0 | { |
1488 | 0 | ctf_err_warn (NULL, 0, ECTF_FLAGS, _("ctf_bufopen: invalid header " |
1489 | 0 | "flags: %x"), |
1490 | 0 | (unsigned int) pp->ctp_flags); |
1491 | 0 | return (ctf_set_open_errno (errp, ECTF_FLAGS)); |
1492 | 0 | } |
1493 | | |
1494 | 0 | if (ctfsect->cts_size < hdrsz) |
1495 | 0 | return (ctf_set_open_errno (errp, ECTF_NOCTFBUF)); |
1496 | | |
1497 | 0 | if ((fp = malloc (sizeof (ctf_dict_t))) == NULL) |
1498 | 0 | return (ctf_set_open_errno (errp, ENOMEM)); |
1499 | | |
1500 | 0 | memset (fp, 0, sizeof (ctf_dict_t)); |
1501 | |
|
1502 | 0 | if ((fp->ctf_header = malloc (sizeof (struct ctf_header))) == NULL) |
1503 | 0 | { |
1504 | 0 | free (fp); |
1505 | 0 | return (ctf_set_open_errno (errp, ENOMEM)); |
1506 | 0 | } |
1507 | 0 | hp = fp->ctf_header; |
1508 | 0 | memcpy (hp, ctfsect->cts_data, hdrsz); |
1509 | 0 | if (pp->ctp_version < CTF_VERSION_3) |
1510 | 0 | upgrade_header (hp); |
1511 | |
|
1512 | 0 | if (foreign_endian) |
1513 | 0 | ctf_flip_header (hp); |
1514 | 0 | fp->ctf_openflags = hp->cth_flags; |
1515 | 0 | fp->ctf_size = hp->cth_stroff + hp->cth_strlen; |
1516 | |
|
1517 | 0 | ctf_dprintf ("ctf_bufopen: uncompressed size=%lu\n", |
1518 | 0 | (unsigned long) fp->ctf_size); |
1519 | |
|
1520 | 0 | if (hp->cth_lbloff > fp->ctf_size || hp->cth_objtoff > fp->ctf_size |
1521 | 0 | || hp->cth_funcoff > fp->ctf_size || hp->cth_objtidxoff > fp->ctf_size |
1522 | 0 | || hp->cth_funcidxoff > fp->ctf_size || hp->cth_typeoff > fp->ctf_size |
1523 | 0 | || hp->cth_stroff > fp->ctf_size) |
1524 | 0 | { |
1525 | 0 | ctf_err_warn (NULL, 0, ECTF_CORRUPT, _("header offset exceeds CTF size")); |
1526 | 0 | return (ctf_set_open_errno (errp, ECTF_CORRUPT)); |
1527 | 0 | } |
1528 | | |
1529 | 0 | if (hp->cth_lbloff > hp->cth_objtoff |
1530 | 0 | || hp->cth_objtoff > hp->cth_funcoff |
1531 | 0 | || hp->cth_funcoff > hp->cth_typeoff |
1532 | 0 | || hp->cth_funcoff > hp->cth_objtidxoff |
1533 | 0 | || hp->cth_objtidxoff > hp->cth_funcidxoff |
1534 | 0 | || hp->cth_funcidxoff > hp->cth_varoff |
1535 | 0 | || hp->cth_varoff > hp->cth_typeoff || hp->cth_typeoff > hp->cth_stroff) |
1536 | 0 | { |
1537 | 0 | ctf_err_warn (NULL, 0, ECTF_CORRUPT, _("overlapping CTF sections")); |
1538 | 0 | return (ctf_set_open_errno (errp, ECTF_CORRUPT)); |
1539 | 0 | } |
1540 | | |
1541 | 0 | if ((hp->cth_lbloff & 3) || (hp->cth_objtoff & 2) |
1542 | 0 | || (hp->cth_funcoff & 2) || (hp->cth_objtidxoff & 2) |
1543 | 0 | || (hp->cth_funcidxoff & 2) || (hp->cth_varoff & 3) |
1544 | 0 | || (hp->cth_typeoff & 3)) |
1545 | 0 | { |
1546 | 0 | ctf_err_warn (NULL, 0, ECTF_CORRUPT, |
1547 | 0 | _("CTF sections not properly aligned")); |
1548 | 0 | return (ctf_set_open_errno (errp, ECTF_CORRUPT)); |
1549 | 0 | } |
1550 | | |
1551 | | /* This invariant will be lifted in v4, but for now it is true. */ |
1552 | | |
1553 | 0 | if ((hp->cth_funcidxoff - hp->cth_objtidxoff != 0) && |
1554 | 0 | (hp->cth_funcidxoff - hp->cth_objtidxoff |
1555 | 0 | != hp->cth_funcoff - hp->cth_objtoff)) |
1556 | 0 | { |
1557 | 0 | ctf_err_warn (NULL, 0, ECTF_CORRUPT, |
1558 | 0 | _("Object index section is neither empty nor the " |
1559 | 0 | "same length as the object section: %u versus %u " |
1560 | 0 | "bytes"), hp->cth_funcoff - hp->cth_objtoff, |
1561 | 0 | hp->cth_funcidxoff - hp->cth_objtidxoff); |
1562 | 0 | return (ctf_set_open_errno (errp, ECTF_CORRUPT)); |
1563 | 0 | } |
1564 | | |
1565 | 0 | if ((hp->cth_varoff - hp->cth_funcidxoff != 0) && |
1566 | 0 | (hp->cth_varoff - hp->cth_funcidxoff |
1567 | 0 | != hp->cth_objtidxoff - hp->cth_funcoff) && |
1568 | 0 | (hp->cth_flags & CTF_F_NEWFUNCINFO)) |
1569 | 0 | { |
1570 | 0 | ctf_err_warn (NULL, 0, ECTF_CORRUPT, |
1571 | 0 | _("Function index section is neither empty nor the " |
1572 | 0 | "same length as the function section: %u versus %u " |
1573 | 0 | "bytes"), hp->cth_objtidxoff - hp->cth_funcoff, |
1574 | 0 | hp->cth_varoff - hp->cth_funcidxoff); |
1575 | 0 | return (ctf_set_open_errno (errp, ECTF_CORRUPT)); |
1576 | 0 | } |
1577 | | |
1578 | | /* Once everything is determined to be valid, attempt to decompress the CTF |
1579 | | data buffer if it is compressed, or copy it into new storage if it is not |
1580 | | compressed but needs endian-flipping. Otherwise we just put the data |
1581 | | section's buffer pointer into ctf_buf, below. */ |
1582 | | |
1583 | | /* Note: if this is a v1 buffer, it will be reallocated and expanded by |
1584 | | init_static_types(). */ |
1585 | | |
1586 | 0 | if (hp->cth_flags & CTF_F_COMPRESS) |
1587 | 0 | { |
1588 | 0 | size_t srclen; |
1589 | 0 | uLongf dstlen; |
1590 | 0 | const void *src; |
1591 | 0 | int rc = Z_OK; |
1592 | | |
1593 | | /* We are allocating this ourselves, so we can drop the ctf header |
1594 | | copy in favour of ctf->ctf_header. */ |
1595 | |
|
1596 | 0 | if ((fp->ctf_base = malloc (fp->ctf_size)) == NULL) |
1597 | 0 | { |
1598 | 0 | err = ECTF_ZALLOC; |
1599 | 0 | goto bad; |
1600 | 0 | } |
1601 | 0 | fp->ctf_dynbase = fp->ctf_base; |
1602 | 0 | hp->cth_flags &= ~CTF_F_COMPRESS; |
1603 | |
|
1604 | 0 | src = (unsigned char *) ctfsect->cts_data + hdrsz; |
1605 | 0 | srclen = ctfsect->cts_size - hdrsz; |
1606 | 0 | dstlen = fp->ctf_size; |
1607 | 0 | fp->ctf_buf = fp->ctf_base; |
1608 | |
|
1609 | 0 | if ((rc = uncompress (fp->ctf_base, &dstlen, src, srclen)) != Z_OK) |
1610 | 0 | { |
1611 | 0 | ctf_err_warn (NULL, 0, ECTF_DECOMPRESS, _("zlib inflate err: %s"), |
1612 | 0 | zError (rc)); |
1613 | 0 | err = ECTF_DECOMPRESS; |
1614 | 0 | goto bad; |
1615 | 0 | } |
1616 | | |
1617 | 0 | if ((size_t) dstlen != fp->ctf_size) |
1618 | 0 | { |
1619 | 0 | ctf_err_warn (NULL, 0, ECTF_CORRUPT, |
1620 | 0 | _("zlib inflate short: got %lu of %lu bytes"), |
1621 | 0 | (unsigned long) dstlen, (unsigned long) fp->ctf_size); |
1622 | 0 | err = ECTF_CORRUPT; |
1623 | 0 | goto bad; |
1624 | 0 | } |
1625 | 0 | } |
1626 | 0 | else |
1627 | 0 | { |
1628 | 0 | if (_libctf_unlikely_ (ctfsect->cts_size < hdrsz + fp->ctf_size)) |
1629 | 0 | { |
1630 | 0 | ctf_err_warn (NULL, 0, ECTF_CORRUPT, |
1631 | 0 | _("%lu byte long CTF dictionary overruns %lu byte long CTF section"), |
1632 | 0 | (unsigned long) ctfsect->cts_size, |
1633 | 0 | (unsigned long) (hdrsz + fp->ctf_size)); |
1634 | 0 | err = ECTF_CORRUPT; |
1635 | 0 | goto bad; |
1636 | 0 | } |
1637 | | |
1638 | 0 | if (foreign_endian) |
1639 | 0 | { |
1640 | 0 | if ((fp->ctf_base = malloc (fp->ctf_size)) == NULL) |
1641 | 0 | { |
1642 | 0 | err = ECTF_ZALLOC; |
1643 | 0 | goto bad; |
1644 | 0 | } |
1645 | 0 | fp->ctf_dynbase = fp->ctf_base; |
1646 | 0 | memcpy (fp->ctf_base, ((unsigned char *) ctfsect->cts_data) + hdrsz, |
1647 | 0 | fp->ctf_size); |
1648 | 0 | fp->ctf_buf = fp->ctf_base; |
1649 | 0 | } |
1650 | 0 | else |
1651 | 0 | { |
1652 | | /* We are just using the section passed in -- but its header may |
1653 | | be an old version. Point ctf_buf past the old header, and |
1654 | | never touch it again. */ |
1655 | 0 | fp->ctf_base = (unsigned char *) ctfsect->cts_data; |
1656 | 0 | fp->ctf_dynbase = NULL; |
1657 | 0 | fp->ctf_buf = fp->ctf_base + hdrsz; |
1658 | 0 | } |
1659 | 0 | } |
1660 | | |
1661 | | /* Once we have uncompressed and validated the CTF data buffer, we can |
1662 | | proceed with initializing the ctf_dict_t we allocated above. |
1663 | | |
1664 | | Nothing that depends on buf or base should be set directly in this function |
1665 | | before the init_static_types() call, because it may be reallocated during |
1666 | | transparent upgrade if this recension of libctf is so configured: see |
1667 | | ctf_set_base(). */ |
1668 | | |
1669 | 0 | ctf_set_version (fp, hp, hp->cth_version); |
1670 | | |
1671 | | /* Temporary assignment, just enough to be able to initialize |
1672 | | the atoms table. */ |
1673 | |
|
1674 | 0 | fp->ctf_str[CTF_STRTAB_0].cts_strs = (const char *) fp->ctf_buf |
1675 | 0 | + hp->cth_stroff; |
1676 | 0 | fp->ctf_str[CTF_STRTAB_0].cts_len = hp->cth_strlen; |
1677 | 0 | if (ctf_str_create_atoms (fp) < 0) |
1678 | 0 | { |
1679 | 0 | err = ENOMEM; |
1680 | 0 | goto bad; |
1681 | 0 | } |
1682 | | |
1683 | 0 | fp->ctf_parmax = CTF_MAX_PTYPE; |
1684 | 0 | memcpy (&fp->ctf_data, ctfsect, sizeof (ctf_sect_t)); |
1685 | |
|
1686 | 0 | if (symsect != NULL) |
1687 | 0 | { |
1688 | 0 | memcpy (&fp->ctf_ext_symtab, symsect, sizeof (ctf_sect_t)); |
1689 | 0 | memcpy (&fp->ctf_ext_strtab, strsect, sizeof (ctf_sect_t)); |
1690 | 0 | } |
1691 | |
|
1692 | 0 | if (fp->ctf_data.cts_name != NULL) |
1693 | 0 | if ((fp->ctf_data.cts_name = strdup (fp->ctf_data.cts_name)) == NULL) |
1694 | 0 | { |
1695 | 0 | err = ENOMEM; |
1696 | 0 | goto bad; |
1697 | 0 | } |
1698 | 0 | if (fp->ctf_ext_symtab.cts_name != NULL) |
1699 | 0 | if ((fp->ctf_ext_symtab.cts_name = strdup (fp->ctf_ext_symtab.cts_name)) == NULL) |
1700 | 0 | { |
1701 | 0 | err = ENOMEM; |
1702 | 0 | goto bad; |
1703 | 0 | } |
1704 | 0 | if (fp->ctf_ext_strtab.cts_name != NULL) |
1705 | 0 | if ((fp->ctf_ext_strtab.cts_name = strdup (fp->ctf_ext_strtab.cts_name)) == NULL) |
1706 | 0 | { |
1707 | 0 | err = ENOMEM; |
1708 | 0 | goto bad; |
1709 | 0 | } |
1710 | | |
1711 | 0 | if (fp->ctf_data.cts_name == NULL) |
1712 | 0 | fp->ctf_data.cts_name = _CTF_NULLSTR; |
1713 | 0 | if (fp->ctf_ext_symtab.cts_name == NULL) |
1714 | 0 | fp->ctf_ext_symtab.cts_name = _CTF_NULLSTR; |
1715 | 0 | if (fp->ctf_ext_strtab.cts_name == NULL) |
1716 | 0 | fp->ctf_ext_strtab.cts_name = _CTF_NULLSTR; |
1717 | |
|
1718 | 0 | if (strsect != NULL) |
1719 | 0 | { |
1720 | 0 | fp->ctf_str[CTF_STRTAB_1].cts_strs = strsect->cts_data; |
1721 | 0 | fp->ctf_str[CTF_STRTAB_1].cts_len = strsect->cts_size; |
1722 | 0 | } |
1723 | | |
1724 | | /* Dynamic state, for dynamic addition to this dict after loading. */ |
1725 | |
|
1726 | 0 | fp->ctf_dthash = ctf_dynhash_create (ctf_hash_integer, ctf_hash_eq_integer, |
1727 | 0 | NULL, NULL); |
1728 | 0 | fp->ctf_dvhash = ctf_dynhash_create (ctf_hash_string, ctf_hash_eq_string, |
1729 | 0 | NULL, NULL); |
1730 | 0 | fp->ctf_snapshots = 1; |
1731 | |
|
1732 | 0 | fp->ctf_objthash = ctf_dynhash_create (ctf_hash_string, ctf_hash_eq_string, |
1733 | 0 | free, NULL); |
1734 | 0 | fp->ctf_funchash = ctf_dynhash_create (ctf_hash_string, ctf_hash_eq_string, |
1735 | 0 | free, NULL); |
1736 | |
|
1737 | 0 | if (!fp->ctf_dthash || !fp->ctf_dvhash || !fp->ctf_snapshots || |
1738 | 0 | !fp->ctf_objthash || !fp->ctf_funchash) |
1739 | 0 | { |
1740 | 0 | err = ENOMEM; |
1741 | 0 | goto bad; |
1742 | 0 | } |
1743 | | |
1744 | 0 | if (foreign_endian && |
1745 | 0 | (err = ctf_flip (fp, hp, fp->ctf_buf, 0)) != 0) |
1746 | 0 | { |
1747 | | /* We can be certain that ctf_flip() will have endian-flipped everything |
1748 | | other than the types table when we return. In particular the header |
1749 | | is fine, so set it, to allow freeing to use the usual code path. */ |
1750 | |
|
1751 | 0 | ctf_set_base (fp, hp, fp->ctf_base); |
1752 | 0 | goto bad; |
1753 | 0 | } |
1754 | | |
1755 | 0 | ctf_set_base (fp, hp, fp->ctf_base); |
1756 | |
|
1757 | 0 | if ((err = init_static_types (fp, hp)) != 0) |
1758 | 0 | goto bad; |
1759 | | |
1760 | | /* Allocate and initialize the symtab translation table, pointed to by |
1761 | | ctf_sxlate, and the corresponding index sections. This table may be too |
1762 | | large for the actual size of the object and function info sections: if so, |
1763 | | ctf_nsyms will be adjusted and the excess will never be used. It's |
1764 | | possible to do indexed symbol lookups even without a symbol table, so check |
1765 | | even in that case. Initially, we assume the symtab is native-endian: if it |
1766 | | isn't, the caller will inform us later by calling ctf_symsect_endianness. */ |
1767 | | #ifdef WORDS_BIGENDIAN |
1768 | | fp->ctf_symsect_little_endian = 0; |
1769 | | #else |
1770 | 0 | fp->ctf_symsect_little_endian = 1; |
1771 | 0 | #endif |
1772 | |
|
1773 | 0 | if (symsect != NULL) |
1774 | 0 | { |
1775 | 0 | fp->ctf_nsyms = symsect->cts_size / symsect->cts_entsize; |
1776 | 0 | fp->ctf_sxlate = malloc (fp->ctf_nsyms * sizeof (uint32_t)); |
1777 | |
|
1778 | 0 | if (fp->ctf_sxlate == NULL) |
1779 | 0 | { |
1780 | 0 | err = ENOMEM; |
1781 | 0 | goto bad; |
1782 | 0 | } |
1783 | 0 | } |
1784 | | |
1785 | 0 | if ((err = init_symtab (fp, hp, symsect)) != 0) |
1786 | 0 | goto bad; |
1787 | | |
1788 | 0 | ctf_set_ctl_hashes (fp); |
1789 | |
|
1790 | 0 | if (symsect != NULL) |
1791 | 0 | { |
1792 | 0 | if (symsect->cts_entsize == sizeof (Elf64_Sym)) |
1793 | 0 | (void) ctf_setmodel (fp, CTF_MODEL_LP64); |
1794 | 0 | else |
1795 | 0 | (void) ctf_setmodel (fp, CTF_MODEL_ILP32); |
1796 | 0 | } |
1797 | 0 | else |
1798 | 0 | (void) ctf_setmodel (fp, CTF_MODEL_NATIVE); |
1799 | |
|
1800 | 0 | fp->ctf_refcnt = 1; |
1801 | 0 | return fp; |
1802 | | |
1803 | 0 | bad: |
1804 | 0 | ctf_set_open_errno (errp, err); |
1805 | 0 | ctf_err_warn_to_open (fp); |
1806 | | /* Without this, the refcnt is zero on entry and ctf_dict_close() won't |
1807 | | actually do anything on the grounds that this is a recursive call via |
1808 | | another dict being closed. */ |
1809 | 0 | fp->ctf_refcnt = 1; |
1810 | 0 | ctf_dict_close (fp); |
1811 | 0 | return NULL; |
1812 | 0 | } |
1813 | | |
1814 | | /* Bump the refcount on the specified CTF dict, to allow export of ctf_dict_t's |
1815 | | from iterators that open and close the ctf_dict_t around the loop. (This |
1816 | | does not extend their lifetime beyond that of the ctf_archive_t in which they |
1817 | | are contained.) */ |
1818 | | |
1819 | | void |
1820 | | ctf_ref (ctf_dict_t *fp) |
1821 | 0 | { |
1822 | 0 | fp->ctf_refcnt++; |
1823 | 0 | } |
1824 | | |
1825 | | /* Close the specified CTF dict and free associated data structures. Note that |
1826 | | ctf_dict_close() is a reference counted operation: if the specified file is |
1827 | | the parent of other active dict, its reference count will be greater than one |
1828 | | and it will be freed later when no active children exist. */ |
1829 | | |
1830 | | void |
1831 | | ctf_dict_close (ctf_dict_t *fp) |
1832 | 0 | { |
1833 | 0 | ctf_dtdef_t *dtd, *ntd; |
1834 | 0 | ctf_dvdef_t *dvd, *nvd; |
1835 | 0 | ctf_in_flight_dynsym_t *did, *nid; |
1836 | 0 | ctf_err_warning_t *err, *nerr; |
1837 | |
|
1838 | 0 | if (fp == NULL) |
1839 | 0 | return; /* Allow ctf_dict_close(NULL) to simplify caller code. */ |
1840 | | |
1841 | 0 | ctf_dprintf ("ctf_dict_close(%p) refcnt=%u\n", (void *) fp, fp->ctf_refcnt); |
1842 | |
|
1843 | 0 | if (fp->ctf_refcnt > 1) |
1844 | 0 | { |
1845 | 0 | fp->ctf_refcnt--; |
1846 | 0 | return; |
1847 | 0 | } |
1848 | | |
1849 | | /* It is possible to recurse back in here, notably if dicts in the |
1850 | | ctf_link_inputs or ctf_link_outputs cite this dict as a parent without |
1851 | | using ctf_import_unref. Do nothing in that case. */ |
1852 | 0 | if (fp->ctf_refcnt == 0) |
1853 | 0 | return; |
1854 | | |
1855 | 0 | fp->ctf_refcnt--; |
1856 | 0 | free (fp->ctf_dyncuname); |
1857 | 0 | free (fp->ctf_dynparname); |
1858 | 0 | if (fp->ctf_parent && !fp->ctf_parent_unreffed) |
1859 | 0 | ctf_dict_close (fp->ctf_parent); |
1860 | |
|
1861 | 0 | for (dtd = ctf_list_next (&fp->ctf_dtdefs); dtd != NULL; dtd = ntd) |
1862 | 0 | { |
1863 | 0 | ntd = ctf_list_next (dtd); |
1864 | 0 | ctf_dtd_delete (fp, dtd); |
1865 | 0 | } |
1866 | 0 | ctf_dynhash_destroy (fp->ctf_dthash); |
1867 | |
|
1868 | 0 | ctf_dynset_destroy (fp->ctf_conflicting_enums); |
1869 | 0 | ctf_dynhash_destroy (fp->ctf_structs); |
1870 | 0 | ctf_dynhash_destroy (fp->ctf_unions); |
1871 | 0 | ctf_dynhash_destroy (fp->ctf_enums); |
1872 | 0 | ctf_dynhash_destroy (fp->ctf_names); |
1873 | |
|
1874 | 0 | for (dvd = ctf_list_next (&fp->ctf_dvdefs); dvd != NULL; dvd = nvd) |
1875 | 0 | { |
1876 | 0 | nvd = ctf_list_next (dvd); |
1877 | 0 | ctf_dvd_delete (fp, dvd); |
1878 | 0 | } |
1879 | 0 | ctf_dynhash_destroy (fp->ctf_dvhash); |
1880 | |
|
1881 | 0 | ctf_dynhash_destroy (fp->ctf_symhash_func); |
1882 | 0 | ctf_dynhash_destroy (fp->ctf_symhash_objt); |
1883 | 0 | free (fp->ctf_funcidx_sxlate); |
1884 | 0 | free (fp->ctf_objtidx_sxlate); |
1885 | 0 | ctf_dynhash_destroy (fp->ctf_objthash); |
1886 | 0 | ctf_dynhash_destroy (fp->ctf_funchash); |
1887 | 0 | free (fp->ctf_dynsymidx); |
1888 | 0 | ctf_dynhash_destroy (fp->ctf_dynsyms); |
1889 | 0 | for (did = ctf_list_next (&fp->ctf_in_flight_dynsyms); did != NULL; did = nid) |
1890 | 0 | { |
1891 | 0 | nid = ctf_list_next (did); |
1892 | 0 | ctf_list_delete (&fp->ctf_in_flight_dynsyms, did); |
1893 | 0 | free (did); |
1894 | 0 | } |
1895 | |
|
1896 | 0 | ctf_str_free_atoms (fp); |
1897 | 0 | free (fp->ctf_tmp_typeslice); |
1898 | |
|
1899 | 0 | if (fp->ctf_data.cts_name != _CTF_NULLSTR) |
1900 | 0 | free ((char *) fp->ctf_data.cts_name); |
1901 | |
|
1902 | 0 | if (fp->ctf_ext_symtab.cts_name != _CTF_NULLSTR) |
1903 | 0 | free ((char *) fp->ctf_ext_symtab.cts_name); |
1904 | |
|
1905 | 0 | if (fp->ctf_ext_strtab.cts_name != _CTF_NULLSTR) |
1906 | 0 | free ((char *) fp->ctf_ext_strtab.cts_name); |
1907 | 0 | else if (fp->ctf_data_mmapped) |
1908 | 0 | ctf_munmap (fp->ctf_data_mmapped, fp->ctf_data_mmapped_len); |
1909 | |
|
1910 | 0 | free (fp->ctf_dynbase); |
1911 | |
|
1912 | 0 | ctf_dynhash_destroy (fp->ctf_syn_ext_strtab); |
1913 | 0 | ctf_dynhash_destroy (fp->ctf_link_inputs); |
1914 | 0 | ctf_dynhash_destroy (fp->ctf_link_outputs); |
1915 | 0 | ctf_dynhash_destroy (fp->ctf_link_type_mapping); |
1916 | 0 | ctf_dynhash_destroy (fp->ctf_link_in_cu_mapping); |
1917 | 0 | ctf_dynhash_destroy (fp->ctf_link_out_cu_mapping); |
1918 | 0 | ctf_dynhash_destroy (fp->ctf_add_processing); |
1919 | 0 | ctf_dedup_fini (fp, NULL, 0); |
1920 | 0 | ctf_dynset_destroy (fp->ctf_dedup_atoms_alloc); |
1921 | |
|
1922 | 0 | for (err = ctf_list_next (&fp->ctf_errs_warnings); err != NULL; err = nerr) |
1923 | 0 | { |
1924 | 0 | nerr = ctf_list_next (err); |
1925 | 0 | ctf_list_delete (&fp->ctf_errs_warnings, err); |
1926 | 0 | free (err->cew_text); |
1927 | 0 | free (err); |
1928 | 0 | } |
1929 | |
|
1930 | 0 | free (fp->ctf_sxlate); |
1931 | 0 | free (fp->ctf_txlate); |
1932 | 0 | free (fp->ctf_ptrtab); |
1933 | 0 | free (fp->ctf_pptrtab); |
1934 | |
|
1935 | 0 | free (fp->ctf_header); |
1936 | 0 | free (fp); |
1937 | 0 | } |
1938 | | |
1939 | | /* Backward compatibility. */ |
1940 | | void |
1941 | | ctf_file_close (ctf_file_t *fp) |
1942 | 0 | { |
1943 | 0 | ctf_dict_close (fp); |
1944 | 0 | } |
1945 | | |
1946 | | /* The converse of ctf_open(). ctf_open() disguises whatever it opens as an |
1947 | | archive, so closing one is just like closing an archive. */ |
1948 | | void |
1949 | | ctf_close (ctf_archive_t *arc) |
1950 | 0 | { |
1951 | 0 | ctf_arc_close (arc); |
1952 | 0 | } |
1953 | | |
1954 | | /* Get the CTF archive from which this ctf_dict_t is derived. */ |
1955 | | ctf_archive_t * |
1956 | | ctf_get_arc (const ctf_dict_t *fp) |
1957 | 0 | { |
1958 | 0 | return fp->ctf_archive; |
1959 | 0 | } |
1960 | | |
1961 | | /* Return the ctfsect out of the core ctf_impl. Useful for freeing the |
1962 | | ctfsect's data * after ctf_dict_close(), which is why we return the actual |
1963 | | structure, not a pointer to it, since that is likely to become a pointer to |
1964 | | freed data before the return value is used under the expected use case of |
1965 | | ctf_getsect()/ ctf_dict_close()/free(). */ |
1966 | | ctf_sect_t |
1967 | | ctf_getdatasect (const ctf_dict_t *fp) |
1968 | 0 | { |
1969 | 0 | return fp->ctf_data; |
1970 | 0 | } |
1971 | | |
1972 | | ctf_sect_t |
1973 | | ctf_getsymsect (const ctf_dict_t *fp) |
1974 | 0 | { |
1975 | 0 | return fp->ctf_ext_symtab; |
1976 | 0 | } |
1977 | | |
1978 | | ctf_sect_t |
1979 | | ctf_getstrsect (const ctf_dict_t *fp) |
1980 | 0 | { |
1981 | 0 | return fp->ctf_ext_strtab; |
1982 | 0 | } |
1983 | | |
1984 | | /* Set the endianness of the symbol table attached to FP. */ |
1985 | | void |
1986 | | ctf_symsect_endianness (ctf_dict_t *fp, int little_endian) |
1987 | 0 | { |
1988 | 0 | int old_endianness = fp->ctf_symsect_little_endian; |
1989 | |
|
1990 | 0 | fp->ctf_symsect_little_endian = !!little_endian; |
1991 | | |
1992 | | /* If we already have a symtab translation table, we need to repopulate it if |
1993 | | our idea of the endianness has changed. */ |
1994 | |
|
1995 | 0 | if (old_endianness != fp->ctf_symsect_little_endian |
1996 | 0 | && fp->ctf_sxlate != NULL && fp->ctf_ext_symtab.cts_data != NULL) |
1997 | 0 | assert (init_symtab (fp, fp->ctf_header, &fp->ctf_ext_symtab) == 0); |
1998 | 0 | } |
1999 | | |
2000 | | /* Return the CTF handle for the parent CTF dict, if one exists. Otherwise |
2001 | | return NULL to indicate this dict has no imported parent. */ |
2002 | | ctf_dict_t * |
2003 | | ctf_parent_dict (ctf_dict_t *fp) |
2004 | 0 | { |
2005 | 0 | return fp->ctf_parent; |
2006 | 0 | } |
2007 | | |
2008 | | /* Backward compatibility. */ |
2009 | | ctf_dict_t * |
2010 | | ctf_parent_file (ctf_dict_t *fp) |
2011 | 0 | { |
2012 | 0 | return ctf_parent_dict (fp); |
2013 | 0 | } |
2014 | | |
2015 | | /* Return the name of the parent CTF dict, if one exists, or NULL otherwise. */ |
2016 | | const char * |
2017 | | ctf_parent_name (ctf_dict_t *fp) |
2018 | 0 | { |
2019 | 0 | return fp->ctf_parname; |
2020 | 0 | } |
2021 | | |
2022 | | /* Set the parent name. It is an error to call this routine without calling |
2023 | | ctf_import() at some point. */ |
2024 | | int |
2025 | | ctf_parent_name_set (ctf_dict_t *fp, const char *name) |
2026 | 0 | { |
2027 | 0 | if (fp->ctf_dynparname != NULL) |
2028 | 0 | free (fp->ctf_dynparname); |
2029 | |
|
2030 | 0 | if ((fp->ctf_dynparname = strdup (name)) == NULL) |
2031 | 0 | return (ctf_set_errno (fp, ENOMEM)); |
2032 | 0 | fp->ctf_parname = fp->ctf_dynparname; |
2033 | 0 | return 0; |
2034 | 0 | } |
2035 | | |
2036 | | /* Return the name of the compilation unit this CTF file applies to. Usually |
2037 | | non-NULL only for non-parent dicts. */ |
2038 | | const char * |
2039 | | ctf_cuname (ctf_dict_t *fp) |
2040 | 0 | { |
2041 | 0 | return fp->ctf_cuname; |
2042 | 0 | } |
2043 | | |
2044 | | /* Set the compilation unit name. */ |
2045 | | int |
2046 | | ctf_cuname_set (ctf_dict_t *fp, const char *name) |
2047 | 0 | { |
2048 | 0 | if (fp->ctf_dyncuname != NULL) |
2049 | 0 | free (fp->ctf_dyncuname); |
2050 | |
|
2051 | 0 | if ((fp->ctf_dyncuname = strdup (name)) == NULL) |
2052 | 0 | return (ctf_set_errno (fp, ENOMEM)); |
2053 | 0 | fp->ctf_cuname = fp->ctf_dyncuname; |
2054 | 0 | return 0; |
2055 | 0 | } |
2056 | | |
2057 | | /* Import the types from the specified parent dict by storing a pointer to it in |
2058 | | ctf_parent and incrementing its reference count. Only one parent is allowed: |
2059 | | if a parent already exists, it is replaced by the new parent. The pptrtab |
2060 | | is wiped, and will be refreshed by the next ctf_lookup_by_name call. */ |
2061 | | int |
2062 | | ctf_import (ctf_dict_t *fp, ctf_dict_t *pfp) |
2063 | 0 | { |
2064 | 0 | if (fp == NULL || fp == pfp || (pfp != NULL && pfp->ctf_refcnt == 0)) |
2065 | 0 | return (ctf_set_errno (fp, EINVAL)); |
2066 | | |
2067 | 0 | if (pfp != NULL && pfp->ctf_dmodel != fp->ctf_dmodel) |
2068 | 0 | return (ctf_set_errno (fp, ECTF_DMODEL)); |
2069 | | |
2070 | 0 | if (fp->ctf_parent && !fp->ctf_parent_unreffed) |
2071 | 0 | ctf_dict_close (fp->ctf_parent); |
2072 | 0 | fp->ctf_parent = NULL; |
2073 | |
|
2074 | 0 | free (fp->ctf_pptrtab); |
2075 | 0 | fp->ctf_pptrtab = NULL; |
2076 | 0 | fp->ctf_pptrtab_len = 0; |
2077 | 0 | fp->ctf_pptrtab_typemax = 0; |
2078 | |
|
2079 | 0 | if (pfp != NULL) |
2080 | 0 | { |
2081 | 0 | int err; |
2082 | |
|
2083 | 0 | if (fp->ctf_parname == NULL) |
2084 | 0 | if ((err = ctf_parent_name_set (fp, "PARENT")) < 0) |
2085 | 0 | return err; |
2086 | | |
2087 | 0 | fp->ctf_flags |= LCTF_CHILD; |
2088 | 0 | pfp->ctf_refcnt++; |
2089 | 0 | fp->ctf_parent_unreffed = 0; |
2090 | 0 | } |
2091 | | |
2092 | 0 | fp->ctf_parent = pfp; |
2093 | 0 | return 0; |
2094 | 0 | } |
2095 | | |
2096 | | /* Like ctf_import, but does not increment the refcount on the imported parent |
2097 | | or close it at any point: as a result it can go away at any time and the |
2098 | | caller must do all freeing itself. Used internally to avoid refcount |
2099 | | loops. */ |
2100 | | int |
2101 | | ctf_import_unref (ctf_dict_t *fp, ctf_dict_t *pfp) |
2102 | 0 | { |
2103 | 0 | if (fp == NULL || fp == pfp || (pfp != NULL && pfp->ctf_refcnt == 0)) |
2104 | 0 | return (ctf_set_errno (fp, EINVAL)); |
2105 | | |
2106 | 0 | if (pfp != NULL && pfp->ctf_dmodel != fp->ctf_dmodel) |
2107 | 0 | return (ctf_set_errno (fp, ECTF_DMODEL)); |
2108 | | |
2109 | 0 | if (fp->ctf_parent && !fp->ctf_parent_unreffed) |
2110 | 0 | ctf_dict_close (fp->ctf_parent); |
2111 | 0 | fp->ctf_parent = NULL; |
2112 | |
|
2113 | 0 | free (fp->ctf_pptrtab); |
2114 | 0 | fp->ctf_pptrtab = NULL; |
2115 | 0 | fp->ctf_pptrtab_len = 0; |
2116 | 0 | fp->ctf_pptrtab_typemax = 0; |
2117 | 0 | if (pfp != NULL) |
2118 | 0 | { |
2119 | 0 | int err; |
2120 | |
|
2121 | 0 | if (fp->ctf_parname == NULL) |
2122 | 0 | if ((err = ctf_parent_name_set (fp, "PARENT")) < 0) |
2123 | 0 | return err; |
2124 | | |
2125 | 0 | fp->ctf_flags |= LCTF_CHILD; |
2126 | 0 | fp->ctf_parent_unreffed = 1; |
2127 | 0 | } |
2128 | | |
2129 | 0 | fp->ctf_parent = pfp; |
2130 | 0 | return 0; |
2131 | 0 | } |
2132 | | |
2133 | | /* Set the data model constant for the CTF dict. */ |
2134 | | int |
2135 | | ctf_setmodel (ctf_dict_t *fp, int model) |
2136 | 0 | { |
2137 | 0 | const ctf_dmodel_t *dp; |
2138 | |
|
2139 | 0 | for (dp = _libctf_models; dp->ctd_name != NULL; dp++) |
2140 | 0 | { |
2141 | 0 | if (dp->ctd_code == model) |
2142 | 0 | { |
2143 | 0 | fp->ctf_dmodel = dp; |
2144 | 0 | return 0; |
2145 | 0 | } |
2146 | 0 | } |
2147 | | |
2148 | 0 | return (ctf_set_errno (fp, EINVAL)); |
2149 | 0 | } |
2150 | | |
2151 | | /* Return the data model constant for the CTF dict. */ |
2152 | | int |
2153 | | ctf_getmodel (ctf_dict_t *fp) |
2154 | 0 | { |
2155 | 0 | return fp->ctf_dmodel->ctd_code; |
2156 | 0 | } |
2157 | | |
2158 | | /* The caller can hang an arbitrary pointer off each ctf_dict_t using this |
2159 | | function. */ |
2160 | | void |
2161 | | ctf_setspecific (ctf_dict_t *fp, void *data) |
2162 | 0 | { |
2163 | 0 | fp->ctf_specific = data; |
2164 | 0 | } |
2165 | | |
2166 | | /* Retrieve the arbitrary pointer again. */ |
2167 | | void * |
2168 | | ctf_getspecific (ctf_dict_t *fp) |
2169 | 0 | { |
2170 | 0 | return fp->ctf_specific; |
2171 | 0 | } |