2 Copyright (C) 2019-2020 Free Software Foundation, Inc.
4 This file is part of libctf.
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
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.
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/>. */
21 #include <sys/types.h>
24 #include "ctf-endian.h"
35 static off_t
arc_write_one_ctf (ctf_dict_t
* f
, int fd
, size_t threshold
);
36 static ctf_dict_t
*ctf_dict_open_by_offset (const struct ctf_archive
*arc
,
37 const ctf_sect_t
*symsect
,
38 const ctf_sect_t
*strsect
,
39 size_t offset
, int *errp
);
40 static int sort_modent_by_name (const void *one
, const void *two
, void *n
);
41 static void *arc_mmap_header (int fd
, size_t headersz
);
42 static void *arc_mmap_file (int fd
, size_t size
);
43 static int arc_mmap_writeout (int fd
, void *header
, size_t headersz
,
45 static int arc_mmap_unmap (void *header
, size_t headersz
, const char **errmsg
);
46 static void ctf_arc_import_parent (const ctf_archive_t
*arc
, ctf_dict_t
*fp
);
48 /* Flag to indicate "symbol not present" in
49 ctf_archive_internal.ctfi_symdicts. Never initialized. */
50 static ctf_dict_t enosym
;
52 /* Write out a CTF archive to the start of the file referenced by the passed-in
53 fd. The entries in CTF_DICTS are referenced by name: the names are passed in
54 the names array, which must have CTF_DICTS entries.
56 Returns 0 on success, or an errno, or an ECTF_* value. */
58 ctf_arc_write_fd (int fd
, ctf_dict_t
**ctf_dicts
, size_t ctf_dict_cnt
,
59 const char **names
, size_t threshold
)
62 struct ctf_archive
*archdr
;
67 size_t ctf_startoffs
; /* Start of the section we are working over. */
68 char *nametbl
= NULL
; /* The name table. */
71 struct ctf_archive_modent
*modent
;
73 ctf_dprintf ("Writing CTF archive with %lu files\n",
74 (unsigned long) ctf_dict_cnt
);
76 /* Figure out the size of the mmap()ed header, including the
77 ctf_archive_modent array. We assume that all of this needs no
78 padding: a likely assumption, given that it's all made up of
80 headersz
= sizeof (struct ctf_archive
)
81 + (ctf_dict_cnt
* sizeof (uint64_t) * 2);
82 ctf_dprintf ("headersz is %lu\n", (unsigned long) headersz
);
84 /* From now on we work in two pieces: an mmap()ed region from zero up to the
85 headersz, and a region updated via write() starting after that, containing
86 all the tables. Platforms that do not support mmap() just use write(). */
87 ctf_startoffs
= headersz
;
88 if (lseek (fd
, ctf_startoffs
- 1, SEEK_SET
) < 0)
90 errmsg
= N_("ctf_arc_write(): cannot extend file while writing");
94 if (write (fd
, &dummy
, 1) < 0)
96 errmsg
= N_("ctf_arc_write(): cannot extend file while writing");
100 if ((archdr
= arc_mmap_header (fd
, headersz
)) == NULL
)
102 errmsg
= N_("ctf_arc_write(): cannot mmap");
106 /* Fill in everything we can, which is everything other than the name
108 archdr
->ctfa_magic
= htole64 (CTFA_MAGIC
);
109 archdr
->ctfa_ndicts
= htole64 (ctf_dict_cnt
);
110 archdr
->ctfa_ctfs
= htole64 (ctf_startoffs
);
112 /* We could validate that all CTF files have the same data model, but
113 since any reasonable construction process will be building things of
114 only one bitness anyway, this is pretty pointless, so just use the
115 model of the first CTF file for all of them. (It *is* valid to
116 create an empty archive: the value of ctfa_model is irrelevant in
117 this case, but we must be sure not to dereference uninitialized
120 if (ctf_dict_cnt
> 0)
121 archdr
->ctfa_model
= htole64 (ctf_getmodel (ctf_dicts
[0]));
123 /* Now write out the CTFs: ctf_archive_modent array via the mapping,
124 ctfs via write(). The names themselves have not been written yet: we
125 track them in a local strtab until the time is right, and sort the
126 modents array after construction.
128 The name table is not sorted. */
130 for (i
= 0, namesz
= 0; i
< le64toh (archdr
->ctfa_ndicts
); i
++)
131 namesz
+= strlen (names
[i
]) + 1;
133 nametbl
= malloc (namesz
);
136 errmsg
= N_("ctf_arc_write(): error writing named CTF to archive");
140 for (i
= 0, namesz
= 0,
141 modent
= (ctf_archive_modent_t
*) ((char *) archdr
142 + sizeof (struct ctf_archive
));
143 i
< le64toh (archdr
->ctfa_ndicts
); i
++)
147 strcpy (&nametbl
[namesz
], names
[i
]);
149 off
= arc_write_one_ctf (ctf_dicts
[i
], fd
, threshold
);
150 if ((off
< 0) && (off
> -ECTF_BASE
))
152 errmsg
= N_("ctf_arc_write(): cannot determine file "
153 "position while writing to archive");
158 errmsg
= N_("ctf_arc_write(): cannot write CTF file to archive");
163 modent
->name_offset
= htole64 (namesz
);
164 modent
->ctf_offset
= htole64 (off
- ctf_startoffs
);
165 namesz
+= strlen (names
[i
]) + 1;
169 ctf_qsort_r ((ctf_archive_modent_t
*) ((char *) archdr
170 + sizeof (struct ctf_archive
)),
171 le64toh (archdr
->ctfa_ndicts
),
172 sizeof (struct ctf_archive_modent
), sort_modent_by_name
,
175 /* Now the name table. */
177 if ((nameoffs
= lseek (fd
, 0, SEEK_CUR
)) < 0)
179 errmsg
= N_("ctf_arc_write(): cannot get current file position "
183 archdr
->ctfa_names
= htole64 (nameoffs
);
188 if ((len
= write (fd
, np
, namesz
)) < 0)
190 errmsg
= N_("ctf_arc_write(): cannot write name table to archive");
198 if (arc_mmap_writeout (fd
, archdr
, headersz
, &errmsg
) < 0)
200 if (arc_mmap_unmap (archdr
, headersz
, &errmsg
) < 0)
207 arc_mmap_unmap (archdr
, headersz
, NULL
);
209 /* We report errors into the first file in the archive, if any: if this is a
210 zero-file archive, put it in the open-errors stream for lack of anywhere
211 else for it to go. */
212 ctf_err_warn (ctf_dict_cnt
> 0 ? ctf_dicts
[0] : NULL
, 0, errno
, "%s",
217 /* Write out a CTF archive. The entries in CTF_DICTS are referenced by name:
218 the names are passed in the names array, which must have CTF_DICTS entries.
220 If the filename is NULL, create a temporary file and return a pointer to it.
222 Returns 0 on success, or an errno, or an ECTF_* value. */
224 ctf_arc_write (const char *file
, ctf_dict_t
**ctf_dicts
, size_t ctf_dict_cnt
,
225 const char **names
, size_t threshold
)
230 if ((fd
= open (file
, O_RDWR
| O_CREAT
| O_TRUNC
| O_CLOEXEC
, 0666)) < 0)
232 ctf_err_warn (ctf_dict_cnt
> 0 ? ctf_dicts
[0] : NULL
, 0, errno
,
233 _("ctf_arc_write(): cannot create %s"), file
);
237 err
= ctf_arc_write_fd (fd
, ctf_dicts
, ctf_dict_cnt
, names
, threshold
);
241 if ((err
= close (fd
)) < 0)
242 ctf_err_warn (ctf_dict_cnt
> 0 ? ctf_dicts
[0] : NULL
, 0, errno
,
243 _("ctf_arc_write(): cannot close after writing to archive"));
255 /* Write one CTF file out. Return the file position of the written file (or
256 rather, of the file-size uint64_t that precedes it): negative return is a
257 negative errno or ctf_errno value. On error, the file position may no longer
258 be at the end of the file. */
260 arc_write_one_ctf (ctf_dict_t
* f
, int fd
, size_t threshold
)
266 int (*writefn
) (ctf_dict_t
* fp
, int fd
);
268 if (ctf_serialize (f
) < 0)
269 return f
->ctf_errno
* -1;
271 if ((off
= lseek (fd
, 0, SEEK_CUR
)) < 0)
274 if (f
->ctf_size
> threshold
)
275 writefn
= ctf_compress_write
;
279 /* This zero-write turns into the size in a moment. */
280 ctfsz_len
= sizeof (ctfsz
);
281 ctfszp
= (char *) &ctfsz
;
282 while (ctfsz_len
> 0)
284 ssize_t writelen
= write (fd
, ctfszp
, ctfsz_len
);
287 ctfsz_len
-= writelen
;
291 if (writefn (f
, fd
) != 0)
292 return f
->ctf_errno
* -1;
294 if ((end_off
= lseek (fd
, 0, SEEK_CUR
)) < 0)
296 ctfsz
= htole64 (end_off
- off
);
298 if ((lseek (fd
, off
, SEEK_SET
)) < 0)
302 ctfsz_len
= sizeof (ctfsz
);
303 ctfszp
= (char *) &ctfsz
;
304 while (ctfsz_len
> 0)
306 ssize_t writelen
= write (fd
, ctfszp
, ctfsz_len
);
309 ctfsz_len
-= writelen
;
313 end_off
= LCTF_ALIGN_OFFS (end_off
, 8);
314 if ((lseek (fd
, end_off
, SEEK_SET
)) < 0)
320 /* qsort() function to sort the array of struct ctf_archive_modents into
321 ascending name order. */
323 sort_modent_by_name (const void *one
, const void *two
, void *n
)
325 const struct ctf_archive_modent
*a
= one
;
326 const struct ctf_archive_modent
*b
= two
;
329 return strcmp (&nametbl
[le64toh (a
->name_offset
)],
330 &nametbl
[le64toh (b
->name_offset
)]);
333 /* bsearch_r() function to search for a given name in the sorted array of struct
334 ctf_archive_modents. */
336 search_modent_by_name (const void *key
, const void *ent
, void *arg
)
339 const struct ctf_archive_modent
*v
= ent
;
340 const char *search_nametbl
= arg
;
342 return strcmp (k
, &search_nametbl
[le64toh (v
->name_offset
)]);
345 /* Make a new struct ctf_archive_internal wrapper for a ctf_archive or a
346 ctf_dict. Closes ARC and/or FP on error. Arrange to free the SYMSECT or
347 STRSECT, as needed, on close. Possibly do not unmap on close. */
349 struct ctf_archive_internal
*
350 ctf_new_archive_internal (int is_archive
, int unmap_on_close
,
351 struct ctf_archive
*arc
,
352 ctf_dict_t
*fp
, const ctf_sect_t
*symsect
,
353 const ctf_sect_t
*strsect
,
356 struct ctf_archive_internal
*arci
;
358 if ((arci
= calloc (1, sizeof (struct ctf_archive_internal
))) == NULL
)
363 ctf_arc_close_internal (arc
);
367 return (ctf_set_open_errno (errp
, errno
));
369 arci
->ctfi_is_archive
= is_archive
;
371 arci
->ctfi_archive
= arc
;
373 arci
->ctfi_dict
= fp
;
375 memcpy (&arci
->ctfi_symsect
, symsect
, sizeof (struct ctf_sect
));
377 memcpy (&arci
->ctfi_strsect
, strsect
, sizeof (struct ctf_sect
));
378 arci
->ctfi_free_symsect
= 0;
379 arci
->ctfi_free_strsect
= 0;
380 arci
->ctfi_unmap_on_close
= unmap_on_close
;
385 /* Get the CTF preamble from data in a buffer, which may be either an archive or
386 a CTF dict. If multiple dicts are present in an archive, the preamble comes
387 from an arbitrary dict. The preamble is a pointer into the ctfsect passed
390 const ctf_preamble_t
*
391 ctf_arc_bufpreamble (const ctf_sect_t
*ctfsect
)
393 if (ctfsect
->cts_size
> sizeof (uint64_t) &&
394 (le64toh ((*(uint64_t *) ctfsect
->cts_data
)) == CTFA_MAGIC
))
396 struct ctf_archive
*arc
= (struct ctf_archive
*) ctfsect
->cts_data
;
397 return (const ctf_preamble_t
*) ((char *) arc
+ le64toh (arc
->ctfa_ctfs
)
398 + sizeof (uint64_t));
401 return (const ctf_preamble_t
*) ctfsect
->cts_data
;
404 /* Open a CTF archive or dictionary from data in a buffer (which the caller must
405 preserve until ctf_arc_close() time). Returns the archive, or NULL and an
406 error in *err (if not NULL). */
408 ctf_arc_bufopen (const ctf_sect_t
*ctfsect
, const ctf_sect_t
*symsect
,
409 const ctf_sect_t
*strsect
, int *errp
)
411 struct ctf_archive
*arc
= NULL
;
413 ctf_dict_t
*fp
= NULL
;
415 if (ctfsect
->cts_size
> sizeof (uint64_t) &&
416 (le64toh ((*(uint64_t *) ctfsect
->cts_data
)) == CTFA_MAGIC
))
418 /* The archive is mmappable, so this operation is trivial.
420 This buffer is nonmodifiable, so the trick involving mmapping only part
421 of it and storing the length in the magic number is not applicable: so
422 record this fact in the archive-wrapper header. (We cannot record it
423 in the archive, because the archive may very well be a read-only
427 arc
= (struct ctf_archive
*) ctfsect
->cts_data
;
432 if ((fp
= ctf_bufopen (ctfsect
, symsect
, strsect
, errp
)) == NULL
)
434 ctf_err_warn (NULL
, 0, *errp
, _("ctf_arc_bufopen(): cannot open CTF"));
438 return ctf_new_archive_internal (is_archive
, 0, arc
, fp
, symsect
, strsect
,
442 /* Open a CTF archive. Returns the archive, or NULL and an error in *err (if
445 ctf_arc_open_internal (const char *filename
, int *errp
)
450 struct ctf_archive
*arc
; /* (Actually the whole file.) */
453 if ((fd
= open (filename
, O_RDONLY
)) < 0)
455 errmsg
= N_("ctf_arc_open(): cannot open %s");
458 if (fstat (fd
, &s
) < 0)
460 errmsg
= N_("ctf_arc_open(): cannot stat %s");
464 if ((arc
= arc_mmap_file (fd
, s
.st_size
)) == NULL
)
466 errmsg
= N_("ctf_arc_open(): cannot read in %s");
470 if (le64toh (arc
->ctfa_magic
) != CTFA_MAGIC
)
472 errmsg
= N_("ctf_arc_open(): %s: invalid magic number");
477 /* This horrible hack lets us know how much to unmap when the file is
478 closed. (We no longer need the magic number, and the mapping
480 arc
->ctfa_magic
= s
.st_size
;
485 arc_mmap_unmap (arc
, s
.st_size
, NULL
);
491 ctf_err_warn (NULL
, 0, errno
, gettext (errmsg
), filename
);
495 /* Close an archive. */
497 ctf_arc_close_internal (struct ctf_archive
*arc
)
502 /* See the comment in ctf_arc_open(). */
503 arc_mmap_unmap (arc
, arc
->ctfa_magic
, NULL
);
506 /* Public entry point: close an archive, or CTF file. */
508 ctf_arc_close (ctf_archive_t
*arc
)
513 if (arc
->ctfi_is_archive
)
515 if (arc
->ctfi_unmap_on_close
)
516 ctf_arc_close_internal (arc
->ctfi_archive
);
519 ctf_dict_close (arc
->ctfi_dict
);
520 free (arc
->ctfi_syms
);
521 free (arc
->ctfi_symdicts
);
522 ctf_dynhash_destroy (arc
->ctfi_dicts
);
523 if (arc
->ctfi_free_symsect
)
524 free ((void *) arc
->ctfi_symsect
.cts_data
);
525 if (arc
->ctfi_free_strsect
)
526 free ((void *) arc
->ctfi_strsect
.cts_data
);
527 free (arc
->ctfi_data
);
528 if (arc
->ctfi_bfd_close
)
529 arc
->ctfi_bfd_close (arc
);
533 /* Return the ctf_dict_t with the given name, or NULL if none, setting 'err' if
534 non-NULL. A name of NULL means to open the default file. */
536 ctf_dict_open_internal (const struct ctf_archive
*arc
,
537 const ctf_sect_t
*symsect
,
538 const ctf_sect_t
*strsect
,
539 const char *name
, int *errp
)
541 struct ctf_archive_modent
*modent
;
542 const char *search_nametbl
;
545 name
= _CTF_SECTION
; /* The default name. */
547 ctf_dprintf ("ctf_dict_open_internal(%s): opening\n", name
);
549 modent
= (ctf_archive_modent_t
*) ((char *) arc
550 + sizeof (struct ctf_archive
));
552 search_nametbl
= (const char *) arc
+ le64toh (arc
->ctfa_names
);
553 modent
= bsearch_r (name
, modent
, le64toh (arc
->ctfa_ndicts
),
554 sizeof (struct ctf_archive_modent
),
555 search_modent_by_name
, (void *) search_nametbl
);
557 /* This is actually a common case and normal operation: no error
562 *errp
= ECTF_ARNNAME
;
566 return ctf_dict_open_by_offset (arc
, symsect
, strsect
,
567 le64toh (modent
->ctf_offset
), errp
);
570 /* Return the ctf_dict_t with the given name, or NULL if none, setting 'err' if
571 non-NULL. A name of NULL means to open the default file.
573 Use the specified string and symbol table sections.
575 Public entry point. */
577 ctf_dict_open_sections (const ctf_archive_t
*arc
,
578 const ctf_sect_t
*symsect
,
579 const ctf_sect_t
*strsect
,
583 if (arc
->ctfi_is_archive
)
586 ret
= ctf_dict_open_internal (arc
->ctfi_archive
, symsect
, strsect
,
590 ret
->ctf_archive
= (ctf_archive_t
*) arc
;
591 ctf_arc_import_parent (arc
, ret
);
596 if ((name
!= NULL
) && (strcmp (name
, _CTF_SECTION
) != 0))
599 *errp
= ECTF_ARNNAME
;
602 arc
->ctfi_dict
->ctf_archive
= (ctf_archive_t
*) arc
;
604 /* Bump the refcount so that the user can ctf_dict_close() it. */
605 arc
->ctfi_dict
->ctf_refcnt
++;
606 return arc
->ctfi_dict
;
609 /* Return the ctf_dict_t with the given name, or NULL if none, setting 'err' if
610 non-NULL. A name of NULL means to open the default file.
612 Public entry point. */
614 ctf_dict_open (const ctf_archive_t
*arc
, const char *name
, int *errp
)
616 const ctf_sect_t
*symsect
= &arc
->ctfi_symsect
;
617 const ctf_sect_t
*strsect
= &arc
->ctfi_strsect
;
619 if (symsect
->cts_name
== NULL
)
621 if (strsect
->cts_name
== NULL
)
624 return ctf_dict_open_sections (arc
, symsect
, strsect
, name
, errp
);
628 ctf_cached_dict_close (void *fp
)
630 ctf_dict_close ((ctf_dict_t
*) fp
);
633 /* Return the ctf_dict_t with the given name and cache it in the
634 archive's ctfi_dicts. */
636 ctf_dict_open_cached (ctf_archive_t
*arc
, const char *name
, int *errp
)
641 /* Just return from the cache if possible. */
643 && ((fp
= ctf_dynhash_lookup (arc
->ctfi_dicts
, name
)) != NULL
))
649 /* Not yet cached: open it. */
650 fp
= ctf_dict_open (arc
, name
, errp
);
651 dupname
= strdup (name
);
656 if (arc
->ctfi_dicts
== NULL
)
658 = ctf_dynhash_create (ctf_hash_string
, ctf_hash_eq_string
,
659 free
, ctf_cached_dict_close
)) == NULL
)
662 if (ctf_dynhash_insert (arc
->ctfi_dicts
, dupname
, fp
) < 0)
676 /* Flush any caches the CTF archive may have open. */
678 ctf_arc_flush_caches (ctf_archive_t
*wrapper
)
680 free (wrapper
->ctfi_symdicts
);
681 free (wrapper
->ctfi_syms
);
682 ctf_dynhash_destroy (wrapper
->ctfi_dicts
);
683 wrapper
->ctfi_symdicts
= NULL
;
684 wrapper
->ctfi_syms
= NULL
;
685 wrapper
->ctfi_dicts
= NULL
;
688 /* Return the ctf_dict_t at the given ctfa_ctfs-relative offset, or NULL if
689 none, setting 'err' if non-NULL. */
691 ctf_dict_open_by_offset (const struct ctf_archive
*arc
,
692 const ctf_sect_t
*symsect
,
693 const ctf_sect_t
*strsect
, size_t offset
,
699 ctf_dprintf ("ctf_dict_open_by_offset(%lu): opening\n", (unsigned long) offset
);
701 memset (&ctfsect
, 0, sizeof (ctf_sect_t
));
703 offset
+= le64toh (arc
->ctfa_ctfs
);
705 ctfsect
.cts_name
= _CTF_SECTION
;
706 ctfsect
.cts_size
= le64toh (*((uint64_t *) ((char *) arc
+ offset
)));
707 ctfsect
.cts_entsize
= 1;
708 ctfsect
.cts_data
= (void *) ((char *) arc
+ offset
+ sizeof (uint64_t));
709 fp
= ctf_bufopen (&ctfsect
, symsect
, strsect
, errp
);
711 ctf_setmodel (fp
, le64toh (arc
->ctfa_model
));
715 /* Backward compatibility. */
717 ctf_arc_open_by_name (const ctf_archive_t
*arc
, const char *name
,
720 return ctf_dict_open (arc
, name
, errp
);
724 ctf_arc_open_by_name_sections (const ctf_archive_t
*arc
,
725 const ctf_sect_t
*symsect
,
726 const ctf_sect_t
*strsect
,
730 return ctf_dict_open_sections (arc
, symsect
, strsect
, name
, errp
);
733 /* Import the parent into a ctf archive, if this is a child, the parent is not
734 already set, and a suitable archive member exists. No error is raised if
735 this is not possible: this is just a best-effort helper operation to give
736 people useful dicts to start with. */
738 ctf_arc_import_parent (const ctf_archive_t
*arc
, ctf_dict_t
*fp
)
740 if ((fp
->ctf_flags
& LCTF_CHILD
) && fp
->ctf_parname
&& !fp
->ctf_parent
)
742 ctf_dict_t
*parent
= ctf_dict_open_cached ((ctf_archive_t
*) arc
,
743 fp
->ctf_parname
, NULL
);
746 ctf_import (fp
, parent
);
747 ctf_dict_close (parent
);
752 /* Return the number of members in an archive. */
754 ctf_archive_count (const ctf_archive_t
*wrapper
)
756 if (!wrapper
->ctfi_is_archive
)
759 return wrapper
->ctfi_archive
->ctfa_ndicts
;
762 /* Look up a symbol in an archive. Return the dict in the archive that the
763 symbol is found in, and (optionally) the ctf_id_t of the symbol in that dict
764 (so you don't have to look it up yourself). The dict and mapping are both
765 cached, so repeated lookups are nearly free.
767 As usual, you should ctf_dict_close() the returned dict once you are done
770 Returns NULL on error, and an error in errp (if set). */
773 ctf_arc_lookup_symbol (ctf_archive_t
*wrapper
, unsigned long symidx
,
774 ctf_id_t
*typep
, int *errp
)
779 /* The usual non-archive-transparent-wrapper special case. */
780 if (!wrapper
->ctfi_is_archive
)
782 if ((type
= ctf_lookup_by_symbol (wrapper
->ctfi_dict
, symidx
)) == CTF_ERR
)
785 *errp
= ctf_errno (wrapper
->ctfi_dict
);
790 wrapper
->ctfi_dict
->ctf_refcnt
++;
791 return wrapper
->ctfi_dict
;
794 if (wrapper
->ctfi_symsect
.cts_name
== NULL
795 || wrapper
->ctfi_symsect
.cts_data
== NULL
796 || wrapper
->ctfi_symsect
.cts_size
== 0
797 || wrapper
->ctfi_symsect
.cts_entsize
== 0)
800 *errp
= ECTF_NOSYMTAB
;
804 /* Make enough space for all possible symbols, if not already done.
805 We cache both the ctf_id_t and the originating dictionary of all symbols.
806 The dict links are weak, to the dictionaries cached in ctfi_dicts: their
807 refcnts are *not* bumped. */
809 if (!wrapper
->ctfi_syms
)
811 if ((wrapper
->ctfi_syms
= calloc (wrapper
->ctfi_symsect
.cts_size
812 / wrapper
->ctfi_symsect
.cts_entsize
,
813 sizeof (ctf_id_t
))) == NULL
)
820 if (!wrapper
->ctfi_symdicts
)
822 if ((wrapper
->ctfi_symdicts
= calloc (wrapper
->ctfi_symsect
.cts_size
823 / wrapper
->ctfi_symsect
.cts_entsize
,
824 sizeof (ctf_dict_t
*))) == NULL
)
832 /* Perhaps it's cached. */
833 if (wrapper
->ctfi_symdicts
[symidx
] != NULL
)
835 if (wrapper
->ctfi_symdicts
[symidx
] == &enosym
)
838 *errp
= ECTF_NOTYPEDAT
;
845 *typep
= wrapper
->ctfi_syms
[symidx
];
846 wrapper
->ctfi_symdicts
[symidx
]->ctf_refcnt
++;
847 return wrapper
->ctfi_symdicts
[symidx
];
850 /* Not cached: find it and cache it. We must track open errors ourselves even
851 if our caller doesn't, to be able to distinguish no-error end-of-iteration
856 ctf_next_t
*i
= NULL
;
862 local_errp
= &local_err
;
864 while ((fp
= ctf_archive_next (wrapper
, &i
, &name
, 0, local_errp
)) != NULL
)
866 if ((type
= ctf_lookup_by_symbol (fp
, symidx
)) != CTF_ERR
)
868 wrapper
->ctfi_syms
[symidx
] = type
;
869 wrapper
->ctfi_symdicts
[symidx
] = fp
;
870 ctf_next_destroy (i
);
878 if (*local_errp
!= ECTF_NEXT_END
)
880 ctf_next_destroy (i
);
883 /* Don't leak end-of-iteration to the caller. */
886 wrapper
->ctfi_symdicts
[symidx
] = &enosym
;
889 *errp
= ECTF_NOTYPEDAT
;
895 /* Raw iteration over all CTF files in an archive. We pass the raw data for all
896 CTF files in turn to the specified callback function. */
898 ctf_archive_raw_iter_internal (const struct ctf_archive
*arc
,
899 ctf_archive_raw_member_f
*func
, void *data
)
903 struct ctf_archive_modent
*modent
;
906 modent
= (ctf_archive_modent_t
*) ((char *) arc
907 + sizeof (struct ctf_archive
));
908 nametbl
= (((const char *) arc
) + le64toh (arc
->ctfa_names
));
910 for (i
= 0; i
< le64toh (arc
->ctfa_ndicts
); i
++)
915 name
= &nametbl
[le64toh (modent
[i
].name_offset
)];
916 fp
= ((char *) arc
+ le64toh (arc
->ctfa_ctfs
)
917 + le64toh (modent
[i
].ctf_offset
));
919 if ((rc
= func (name
, (void *) (fp
+ sizeof (uint64_t)),
920 le64toh (*((uint64_t *) fp
)), data
)) != 0)
926 /* Raw iteration over all CTF files in an archive: public entry point.
928 Returns -EINVAL if not supported for this sort of archive. */
930 ctf_archive_raw_iter (const ctf_archive_t
*arc
,
931 ctf_archive_raw_member_f
* func
, void *data
)
933 if (arc
->ctfi_is_archive
)
934 return ctf_archive_raw_iter_internal (arc
->ctfi_archive
, func
, data
);
936 return -EINVAL
; /* Not supported. */
939 /* Iterate over all CTF files in an archive. We pass all CTF files in turn to
940 the specified callback function. */
942 ctf_archive_iter_internal (const ctf_archive_t
*wrapper
,
943 const struct ctf_archive
*arc
,
944 const ctf_sect_t
*symsect
,
945 const ctf_sect_t
*strsect
,
946 ctf_archive_member_f
*func
, void *data
)
951 struct ctf_archive_modent
*modent
;
954 modent
= (ctf_archive_modent_t
*) ((char *) arc
955 + sizeof (struct ctf_archive
));
956 nametbl
= (((const char *) arc
) + le64toh (arc
->ctfa_names
));
958 for (i
= 0; i
< le64toh (arc
->ctfa_ndicts
); i
++)
962 name
= &nametbl
[le64toh (modent
[i
].name_offset
)];
963 if ((f
= ctf_dict_open_internal (arc
, symsect
, strsect
,
967 f
->ctf_archive
= (ctf_archive_t
*) wrapper
;
968 ctf_arc_import_parent (wrapper
, f
);
969 if ((rc
= func (f
, name
, data
)) != 0)
980 /* Iterate over all CTF files in an archive: public entry point. We pass all
981 CTF files in turn to the specified callback function. */
983 ctf_archive_iter (const ctf_archive_t
*arc
, ctf_archive_member_f
*func
,
986 const ctf_sect_t
*symsect
= &arc
->ctfi_symsect
;
987 const ctf_sect_t
*strsect
= &arc
->ctfi_strsect
;
989 if (symsect
->cts_name
== NULL
)
991 if (strsect
->cts_name
== NULL
)
994 if (arc
->ctfi_is_archive
)
995 return ctf_archive_iter_internal (arc
, arc
->ctfi_archive
, symsect
, strsect
,
998 return func (arc
->ctfi_dict
, _CTF_SECTION
, data
);
1001 /* Iterate over all CTF files in an archive, returning each dict in turn as a
1002 ctf_dict_t, and NULL on error or end of iteration. It is the caller's
1003 responsibility to close it. Parent dicts may be skipped. Regardless of
1004 whether they are skipped or not, the caller must ctf_import the parent if
1007 The archive member is cached for rapid return on future calls.
1009 We identify parents by name rather than by flag value: for now, with the
1010 linker only emitting parents named _CTF_SECTION, this works well enough. */
1013 ctf_archive_next (const ctf_archive_t
*wrapper
, ctf_next_t
**it
, const char **name
,
1014 int skip_parent
, int *errp
)
1017 ctf_next_t
*i
= *it
;
1018 struct ctf_archive
*arc
;
1019 struct ctf_archive_modent
*modent
;
1020 const char *nametbl
;
1025 if ((i
= ctf_next_create()) == NULL
)
1031 i
->cu
.ctn_arc
= wrapper
;
1032 i
->ctn_iter_fun
= (void (*) (void)) ctf_archive_next
;
1036 if ((void (*) (void)) ctf_archive_next
!= i
->ctn_iter_fun
)
1039 *errp
= ECTF_NEXT_WRONGFUN
;
1043 if (wrapper
!= i
->cu
.ctn_arc
)
1046 *errp
= ECTF_NEXT_WRONGFP
;
1050 /* Iteration is made a bit more complex by the need to handle ctf_dict_t's
1051 transparently wrapped in a single-member archive. These are parents: if
1052 skip_parent is on, they are skipped and the iterator terminates
1055 if (!wrapper
->ctfi_is_archive
&& i
->ctn_n
== 0)
1060 wrapper
->ctfi_dict
->ctf_refcnt
++;
1061 return wrapper
->ctfi_dict
;
1065 arc
= wrapper
->ctfi_archive
;
1067 /* The loop keeps going when skip_parent is on as long as the member we find
1068 is the parent (i.e. at most two iterations, but possibly an early return if
1069 *all* we have is a parent). */
1073 if ((!wrapper
->ctfi_is_archive
) || (i
->ctn_n
>= le64toh (arc
->ctfa_ndicts
)))
1075 ctf_next_destroy (i
);
1078 *errp
= ECTF_NEXT_END
;
1082 modent
= (ctf_archive_modent_t
*) ((char *) arc
1083 + sizeof (struct ctf_archive
));
1084 nametbl
= (((const char *) arc
) + le64toh (arc
->ctfa_names
));
1086 name_
= &nametbl
[le64toh (modent
[i
->ctn_n
].name_offset
)];
1088 } while (skip_parent
&& strcmp (name_
, _CTF_SECTION
) == 0);
1093 f
= ctf_dict_open_cached ((ctf_archive_t
*) wrapper
, name_
, errp
);
1098 /* Map the header in. Only used on new, empty files. */
1099 static void *arc_mmap_header (int fd
, size_t headersz
)
1102 if ((hdr
= mmap (NULL
, headersz
, PROT_READ
| PROT_WRITE
, MAP_SHARED
, fd
,
1108 /* mmap() the whole file, for reading only. (Map it writably, but privately: we
1109 need to modify the region, but don't need anyone else to see the
1111 static void *arc_mmap_file (int fd
, size_t size
)
1114 if ((arc
= mmap (NULL
, size
, PROT_READ
| PROT_WRITE
, MAP_PRIVATE
,
1115 fd
, 0)) == MAP_FAILED
)
1120 /* Persist the header to disk. */
1121 static int arc_mmap_writeout (int fd _libctf_unused_
, void *header
,
1122 size_t headersz
, const char **errmsg
)
1124 if (msync (header
, headersz
, MS_ASYNC
) < 0)
1127 *errmsg
= N_("arc_mmap_writeout(): cannot sync after writing "
1134 /* Unmap the region. */
1135 static int arc_mmap_unmap (void *header
, size_t headersz
, const char **errmsg
)
1137 if (munmap (header
, headersz
) < 0)
1140 *errmsg
= N_("arc_mmap_munmap(): cannot unmap after writing "
1147 /* Map the header in. Only used on new, empty files. */
1148 static void *arc_mmap_header (int fd _libctf_unused_
, size_t headersz
)
1151 if ((hdr
= malloc (headersz
)) == NULL
)
1156 /* Pull in the whole file, for reading only. We assume the current file
1157 position is at the start of the file. */
1158 static void *arc_mmap_file (int fd
, size_t size
)
1162 if ((data
= malloc (size
)) == NULL
)
1165 if (ctf_pread (fd
, data
, size
, 0) < 0)
1173 /* Persist the header to disk. */
1174 static int arc_mmap_writeout (int fd
, void *header
, size_t headersz
,
1175 const char **errmsg
)
1179 char *data
= (char *) header
;
1180 ssize_t count
= headersz
;
1182 if ((lseek (fd
, 0, SEEK_SET
)) < 0)
1185 *errmsg
= N_("arc_mmap_writeout(): cannot seek while writing header to "
1190 while (headersz
> 0)
1192 if ((len
= write (fd
, data
, count
)) < 0)
1195 *errmsg
= N_("arc_mmap_writeout(): cannot write header to %s: %s");
1202 if (len
== 0) /* EOF. */
1211 /* Unmap the region. */
1212 static int arc_mmap_unmap (void *header
, size_t headersz _libctf_unused_
,
1213 const char **errmsg _libctf_unused_
)