diff options
author | Andy Fiddaman <omnios@citrus-it.co.uk> | 2020-12-04 11:41:39 +0000 |
---|---|---|
committer | Andy Fiddaman <omnios@citrus-it.co.uk> | 2020-12-17 21:18:56 +0000 |
commit | 88a08813800ed7ba7c927986421cee437f7f2233 (patch) | |
tree | 5ee2cc36e4a8aa6c6f35f47268f4912f1ab44b08 /usr/src/lib | |
parent | 3dd4cd56e7843e01a8ab147a0d102cd4f6d732c1 (diff) | |
download | illumos-joyent-88a08813800ed7ba7c927986421cee437f7f2233.tar.gz |
13363 ctfconvert could support more granular ignore for missing debug data
Reviewed by: Robert Mustacchi <rm@fingolfin.org>
Approved by: Rich Lowe <richlowe@richlowe.net>
Diffstat (limited to 'usr/src/lib')
-rw-r--r-- | usr/src/lib/libctf/common/ctf_convert.c | 49 | ||||
-rw-r--r-- | usr/src/lib/libctf/common/ctf_dwarf.c | 93 | ||||
-rw-r--r-- | usr/src/lib/libctf/common/ctf_merge.c | 23 | ||||
-rw-r--r-- | usr/src/lib/libctf/common/libctf.h | 1 | ||||
-rw-r--r-- | usr/src/lib/libctf/common/libctf_impl.h | 7 | ||||
-rw-r--r-- | usr/src/lib/libctf/common/mapfile-vers | 1 |
6 files changed, 102 insertions, 72 deletions
diff --git a/usr/src/lib/libctf/common/ctf_convert.c b/usr/src/lib/libctf/common/ctf_convert.c index dcf84e57c9..6dff7994f8 100644 --- a/usr/src/lib/libctf/common/ctf_convert.c +++ b/usr/src/lib/libctf/common/ctf_convert.c @@ -24,6 +24,7 @@ #include <libctf_impl.h> #include <assert.h> #include <gelf.h> +#include <sys/list.h> static ctf_convert_f ctf_converters[] = { ctf_dwarf_convert @@ -209,17 +210,29 @@ ctf_convert_init(int *errp) cch->cch_batchsize = CTF_CONVERT_DEFAULT_BATCHSIZE; cch->cch_warncb = NULL; cch->cch_warncb_arg = NULL; + list_create(&cch->cch_nodebug, sizeof (ctf_convert_filelist_t), + offsetof(ctf_convert_filelist_t, ccf_node)); return (cch); } +static void +ctf_convert_fini_filelist(ctf_convert_filelist_t *ccf) +{ + ctf_strfree(ccf->ccf_basename); + ctf_free(ccf, sizeof (ctf_convert_filelist_t)); +} + void ctf_convert_fini(ctf_convert_t *cch) { - if (cch->cch_label != NULL) { - size_t len = strlen(cch->cch_label) + 1; - ctf_free(cch->cch_label, len); - } + ctf_convert_filelist_t *ccf; + + ctf_strfree(cch->cch_label); + while ((ccf = list_remove_head(&cch->cch_nodebug)) != NULL) + ctf_convert_fini_filelist(ccf); + list_destroy(&cch->cch_nodebug); + ctf_free(cch, sizeof (struct ctf_convert_handle)); } @@ -262,11 +275,7 @@ ctf_convert_set_label(ctf_convert_t *cch, const char *label) if (dup == NULL) return (ENOMEM); - if (cch->cch_label != NULL) { - size_t len = strlen(cch->cch_label) + 1; - ctf_free(cch->cch_label, len); - } - + ctf_strfree(cch->cch_label); cch->cch_label = dup; return (0); } @@ -279,6 +288,28 @@ ctf_convert_set_warncb(ctf_convert_t *cch, ctf_convert_warn_f cb, void *arg) return (0); } +int +ctf_convert_add_ignore(ctf_convert_t *cch, const char *basename) +{ + ctf_convert_filelist_t *ccf; + + if (strchr(basename, '/') != NULL) + return (EINVAL); + + ccf = ctf_alloc(sizeof (ctf_convert_filelist_t)); + if (ccf == NULL) + return (ENOMEM); + + ccf->ccf_basename = ctf_strdup(basename); + if (ccf->ccf_basename == NULL) { + ctf_free(ccf, sizeof (ctf_convert_filelist_t)); + return (ENOMEM); + } + list_insert_tail(&cch->cch_nodebug, ccf); + + return (0); +} + ctf_file_t * ctf_fdconvert(ctf_convert_t *cch, int fd, int *errp, char *errbuf, size_t errlen) diff --git a/usr/src/lib/libctf/common/ctf_dwarf.c b/usr/src/lib/libctf/common/ctf_dwarf.c index 58a0f5f4a7..b0b221f96e 100644 --- a/usr/src/lib/libctf/common/ctf_dwarf.c +++ b/usr/src/lib/libctf/common/ctf_dwarf.c @@ -202,6 +202,7 @@ #include <libctf_impl.h> #include <sys/avl.h> #include <sys/debug.h> +#include <sys/list.h> #include <gelf.h> #include <libdwarf.h> #include <dwarf.h> @@ -1152,7 +1153,7 @@ ctf_dwarf_create_base(ctf_cu_t *cup, Dwarf_Die die, ctf_id_t *idp, int isroot, bzero(&enc, sizeof (ctf_encoding_t)); enc.cte_bits = sz * 8; if ((ret = ctf_dwarf_parse_int(name, &kind, &enc, &nname)) == 0) { - ctf_free(name, strlen(name) + 1); + ctf_strfree(name); name = nname; } else { if (ret != EINVAL) { @@ -1167,7 +1168,7 @@ ctf_dwarf_create_base(ctf_cu_t *cup, Dwarf_Die die, ctf_id_t *idp, int isroot, &enc, &nname)) != 0) { goto out; } else if (nname != NULL) { - ctf_free(name, strlen(name) + 1); + ctf_strfree(name); name = nname; } } @@ -1180,7 +1181,7 @@ ctf_dwarf_create_base(ctf_cu_t *cup, Dwarf_Die die, ctf_id_t *idp, int isroot, ret = ctf_dwmap_add(cup, id, die, B_FALSE); } out: - ctf_free(name, strlen(name) + 1); + ctf_strfree(name); return (ret); } @@ -1440,7 +1441,7 @@ ctf_dwarf_fixup_sou(ctf_cu_t *cup, Dwarf_Die die, ctf_id_t base, boolean_t add) } else if ((ret = ctf_dwarf_member_offset(cup, memb, mid, &memboff)) != 0) { if (mname != NULL) - ctf_free(mname, strlen(mname) + 1); + ctf_strfree(mname); return (ret); } @@ -1453,12 +1454,12 @@ ctf_dwarf_fixup_sou(ctf_cu_t *cup, Dwarf_Die die, ctf_id_t base, boolean_t add) "failed to add member %s: %s\n", mname, ctf_errmsg(ctf_errno(cup->cu_ctfp))); if (mname != NULL) - ctf_free(mname, strlen(mname) + 1); + ctf_strfree(mname); return (ECTF_CONVBKERR); } if (mname != NULL) - ctf_free(mname, strlen(mname) + 1); + ctf_strfree(mname); next: if ((ret = ctf_dwarf_sib(cup, memb, &sib)) != 0) @@ -1530,7 +1531,7 @@ ctf_dwarf_create_sou(ctf_cu_t *cup, Dwarf_Die die, ctf_id_t *idp, ctf_dprintf("added sou %s (%d) (%ld) forward=%d\n", name, kind, base, decl == B_TRUE); if (name != NULL) - ctf_free(name, strlen(name) + 1); + ctf_strfree(name); if (base == CTF_ERR) return (ctf_errno(cup->cu_ctfp)); *idp = base; @@ -1845,33 +1846,28 @@ ctf_dwarf_create_reference(ctf_cu_t *cup, Dwarf_Die die, ctf_id_t *idp, ctf_id_t id; Dwarf_Die tdie; char *name; - size_t namelen; if ((ret = ctf_dwarf_string(cup, die, DW_AT_name, &name)) != 0 && ret != ENOENT) return (ret); - if (ret == ENOENT) { + if (ret == ENOENT) name = NULL; - namelen = 0; - } else { - namelen = strlen(name); - } ctf_dprintf("reference kind %d %s\n", kind, name != NULL ? name : "<>"); if ((ret = ctf_dwarf_refdie(cup, die, DW_AT_type, &tdie)) != 0) { if (ret != ENOENT) { - ctf_free(name, namelen); + ctf_strfree(name); return (ret); } if ((id = ctf_dwarf_void(cup)) == CTF_ERR) { - ctf_free(name, namelen); + ctf_strfree(name); return (ctf_errno(cup->cu_ctfp)); } } else { if ((ret = ctf_dwarf_convert_type(cup, tdie, &id, CTF_ADD_NONROOT)) != 0) { - ctf_free(name, namelen); + ctf_strfree(name); return (ret); } } @@ -1883,17 +1879,17 @@ ctf_dwarf_create_reference(ctf_cu_t *cup, Dwarf_Die die, ctf_id_t *idp, *idp = id; } - ctf_free(name, namelen); + ctf_strfree(name); return (ret); } if ((*idp = ctf_add_reftype(cup->cu_ctfp, isroot, name, id, kind)) == CTF_ERR) { - ctf_free(name, namelen); + ctf_strfree(name); return (ctf_errno(cup->cu_ctfp)); } - ctf_free(name, namelen); + ctf_strfree(name); return (ctf_dwmap_add(cup, *idp, die, B_FALSE)); } @@ -1997,7 +1993,7 @@ ctf_dwarf_create_enum(ctf_cu_t *cup, Dwarf_Die die, ctf_id_t *idp, int isroot) "value\n"); ret = ECTF_CONVBKERR; } - ctf_free(name, strlen(name) + 1); + ctf_strfree(name); break; } @@ -2021,16 +2017,16 @@ ctf_dwarf_create_enum(ctf_cu_t *cup, Dwarf_Die die, ctf_id_t *idp, int isroot) "to %s (%d)\n", name, eval, enumname == NULL ? "<anon>" : enumname, id); } - ctf_free(name, strlen(name) + 1); + ctf_strfree(name); break; } - ctf_free(name, strlen(name) + 1); + ctf_strfree(name); } out: if (enumname != NULL) - ctf_free(enumname, strlen(enumname) + 1); + ctf_strfree(enumname); return (ret); } @@ -2251,7 +2247,7 @@ ctf_dwarf_function_count(ctf_cu_t *cup, Dwarf_Die die, ctf_funcinfo_t *fip, fip->ctc_flags |= CTF_FUNC_VARARG; else fip->ctc_argc++; - ctf_free(name, strlen(name) + 1); + ctf_strfree(name); } else if (tag == DW_TAG_formal_parameter) { fip->ctc_argc++; } else if (tag == DW_TAG_unspecified_parameters && @@ -2338,7 +2334,7 @@ ctf_dwarf_convert_function(ctf_cu_t *cup, Dwarf_Die die) if ((ret = ctf_dwarf_boolean(cup, die, DW_AT_declaration, &b)) != 0) { if (ret != ENOENT) { - ctf_free(name, strlen(name) + 1); + ctf_strfree(name); return (ret); } } else if (b != 0) { @@ -2351,12 +2347,12 @@ ctf_dwarf_convert_function(ctf_cu_t *cup, Dwarf_Die die) */ ctf_dprintf("ignoring declaration of function %s (die %llx)\n", name, ctf_die_offset(cup, die)); - ctf_free(name, strlen(name) + 1); + ctf_strfree(name); return (0); } if ((cdf = ctf_alloc(sizeof (ctf_dwfunc_t))) == NULL) { - ctf_free(name, strlen(name) + 1); + ctf_strfree(name); return (ENOMEM); } bzero(cdf, sizeof (ctf_dwfunc_t)); @@ -2365,18 +2361,18 @@ ctf_dwarf_convert_function(ctf_cu_t *cup, Dwarf_Die die) if ((ret = ctf_dwarf_refdie(cup, die, DW_AT_type, &tdie)) == 0) { if ((ret = ctf_dwarf_convert_type(cup, tdie, &(cdf->cdf_fip.ctc_return), CTF_ADD_ROOT)) != 0) { - ctf_free(name, strlen(name) + 1); + ctf_strfree(name); ctf_free(cdf, sizeof (ctf_dwfunc_t)); return (ret); } } else if (ret != ENOENT) { - ctf_free(name, strlen(name) + 1); + ctf_strfree(name); ctf_free(cdf, sizeof (ctf_dwfunc_t)); return (ret); } else { if ((cdf->cdf_fip.ctc_return = ctf_dwarf_void(cup)) == CTF_ERR) { - ctf_free(name, strlen(name) + 1); + ctf_strfree(name); ctf_free(cdf, sizeof (ctf_dwfunc_t)); return (ctf_errno(cup->cu_ctfp)); } @@ -2394,7 +2390,7 @@ ctf_dwarf_convert_function(ctf_cu_t *cup, Dwarf_Die die) */ if ((ret = ctf_dwarf_function_count(cup, die, &cdf->cdf_fip, B_FALSE)) != 0) { - ctf_free(name, strlen(name) + 1); + ctf_strfree(name); ctf_free(cdf, sizeof (ctf_dwfunc_t)); return (ret); } @@ -2404,14 +2400,14 @@ ctf_dwarf_convert_function(ctf_cu_t *cup, Dwarf_Die die) uint_t argc = cdf->cdf_fip.ctc_argc; cdf->cdf_argv = ctf_alloc(sizeof (ctf_id_t) * argc); if (cdf->cdf_argv == NULL) { - ctf_free(name, strlen(name) + 1); + ctf_strfree(name); ctf_free(cdf, sizeof (ctf_dwfunc_t)); return (ENOMEM); } if ((ret = ctf_dwarf_convert_fargs(cup, die, &cdf->cdf_fip, cdf->cdf_argv)) != 0) { ctf_free(cdf->cdf_argv, sizeof (ctf_id_t) * argc); - ctf_free(name, strlen(name) + 1); + ctf_strfree(name); ctf_free(cdf, sizeof (ctf_dwfunc_t)); return (ret); } @@ -2422,7 +2418,7 @@ ctf_dwarf_convert_function(ctf_cu_t *cup, Dwarf_Die die) if ((ret = ctf_dwarf_isglobal(cup, die, &cdf->cdf_global)) != 0) { ctf_free(cdf->cdf_argv, sizeof (ctf_id_t) * cdf->cdf_fip.ctc_argc); - ctf_free(name, strlen(name) + 1); + ctf_strfree(name); ctf_free(cdf, sizeof (ctf_dwfunc_t)); return (ret); } @@ -2478,7 +2474,7 @@ ctf_dwarf_convert_variable(ctf_cu_t *cup, Dwarf_Die die) return (0); if ((ret = ctf_dwarf_refdie(cup, die, DW_AT_type, &tdie)) != 0) { - ctf_free(name, strlen(name) + 1); + ctf_strfree(name); return (ret); } @@ -2487,7 +2483,7 @@ ctf_dwarf_convert_variable(ctf_cu_t *cup, Dwarf_Die die) return (ret); if ((cdv = ctf_alloc(sizeof (ctf_dwvar_t))) == NULL) { - ctf_free(name, strlen(name) + 1); + ctf_strfree(name); return (ENOMEM); } @@ -2496,7 +2492,7 @@ ctf_dwarf_convert_variable(ctf_cu_t *cup, Dwarf_Die die) if ((ret = ctf_dwarf_isglobal(cup, die, &cdv->cdv_global)) != 0) { ctf_free(cdv, sizeof (ctf_dwvar_t)); - ctf_free(name, strlen(name) + 1); + ctf_strfree(name); return (ret); } @@ -3082,7 +3078,7 @@ ctf_dwarf_free_die(ctf_cu_t *cup) ctf_dprintf("Trying to free name: %p\n", cup->cu_name); if (cup->cu_name != NULL) { - ctf_free(cup->cu_name, strlen(cup->cu_name) + 1); + ctf_strfree(cup->cu_name); cup->cu_name = NULL; } @@ -3095,7 +3091,7 @@ ctf_dwarf_free_die(ctf_cu_t *cup) ctf_dprintf("Trying to free functions\n"); for (cdf = ctf_list_next(&cup->cu_funcs); cdf != NULL; cdf = ndf) { ndf = ctf_list_next(cdf); - ctf_free(cdf->cdf_name, strlen(cdf->cdf_name) + 1); + ctf_strfree(cdf->cdf_name); if (cdf->cdf_fip.ctc_argc != 0) { ctf_free(cdf->cdf_argv, sizeof (ctf_id_t) * cdf->cdf_fip.ctc_argc); @@ -3106,7 +3102,7 @@ ctf_dwarf_free_die(ctf_cu_t *cup) ctf_dprintf("Trying to free variables\n"); for (cdv = ctf_list_next(&cup->cu_vars); cdv != NULL; cdv = ndv) { ndv = ctf_list_next(cdv); - ctf_free(cdv->cdv_name, strlen(cdv->cdv_name) + 1); + ctf_strfree(cdv->cdv_name); ctf_free(cdv, sizeof (ctf_dwvar_t)); } @@ -3228,11 +3224,10 @@ ctf_dwarf_preinit_dies(ctf_convert_t *cch, int fd, Elf *elf, Dwarf_Debug dw, } if (ctf_dwarf_string(cup, cu, DW_AT_name, &name) == 0) { - size_t len = strlen(name) + 1; char *b = basename(name); cup->cu_name = strdup(b); - ctf_free(name, len); + ctf_strfree(name); if (cup->cu_name == NULL) return (ENOMEM); } @@ -3329,9 +3324,11 @@ ctf_dwarf_init_die(ctf_cu_t *cup) * the -m option. */ static boolean_t -c_source_has_debug(const char *file, ctf_cu_t *cus, size_t nr_cus) +c_source_has_debug(ctf_convert_t *cch, const char *file, + ctf_cu_t *cus, size_t nr_cus) { const char *basename = strrchr(file, '/'); + ctf_convert_filelist_t *ccf; if (basename == NULL) basename = file; @@ -3347,6 +3344,14 @@ c_source_has_debug(const char *file, ctf_cu_t *cus, size_t nr_cus) strncmp(basename, "values-", strlen("values-")) == 0) return (B_TRUE); + for (ccf = list_head(&cch->cch_nodebug); ccf != NULL; + ccf = list_next(&cch->cch_nodebug, ccf)) { + if (ccf->ccf_basename != NULL && + strcmp(basename, ccf->ccf_basename) == 0) { + return (B_TRUE); + } + } + for (size_t i = 0; i < nr_cus; i++) { if (cus[i].cu_name != NULL && strcmp(basename, cus[i].cu_name) == 0) { @@ -3423,7 +3428,7 @@ ctf_dwarf_check_missing(ctf_convert_t *cch, ctf_cu_t *cus, size_t nr_cus, if (len < 2 || strncmp(".c", &file[len - 2], 2) != 0) continue; - if (!c_source_has_debug(file, cus, nr_cus)) { + if (!c_source_has_debug(cch, file, cus, nr_cus)) { if (cch->cch_warncb != NULL) { cch->cch_warncb( cch->cch_warncb_arg, diff --git a/usr/src/lib/libctf/common/ctf_merge.c b/usr/src/lib/libctf/common/ctf_merge.c index a5888de8c0..6b0d89784c 100644 --- a/usr/src/lib/libctf/common/ctf_merge.c +++ b/usr/src/lib/libctf/common/ctf_merge.c @@ -1003,18 +1003,10 @@ ctf_merge_fini_input(ctf_merge_input_t *cmi) void ctf_merge_fini(ctf_merge_t *cmh) { - size_t len; ctf_merge_input_t *cmi; - if (cmh->cmh_label != NULL) { - len = strlen(cmh->cmh_label) + 1; - ctf_free(cmh->cmh_label, len); - } - - if (cmh->cmh_pname != NULL) { - len = strlen(cmh->cmh_pname) + 1; - ctf_free(cmh->cmh_pname, len); - } + ctf_strfree(cmh->cmh_label); + ctf_strfree(cmh->cmh_pname); while ((cmi = list_remove_head(&cmh->cmh_inputs)) != NULL) ctf_merge_fini_input(cmi); @@ -1074,11 +1066,7 @@ ctf_merge_label(ctf_merge_t *cmh, const char *label) if (dup == NULL) return (EAGAIN); - if (cmh->cmh_label != NULL) { - size_t len = strlen(cmh->cmh_label) + 1; - ctf_free(cmh->cmh_label, len); - } - + ctf_strfree(cmh->cmh_label); cmh->cmh_label = dup; return (0); } @@ -1272,10 +1260,7 @@ ctf_merge_uniquify(ctf_merge_t *cmh, ctf_file_t *u, const char *pname) dup = ctf_strdup(pname); if (dup == NULL) return (EINVAL); - if (cmh->cmh_pname != NULL) { - size_t len = strlen(cmh->cmh_pname) + 1; - ctf_free(cmh->cmh_pname, len); - } + ctf_strfree(cmh->cmh_pname); cmh->cmh_pname = dup; cmh->cmh_unique = u; return (0); diff --git a/usr/src/lib/libctf/common/libctf.h b/usr/src/lib/libctf/common/libctf.h index 8f6a232057..9412143a91 100644 --- a/usr/src/lib/libctf/common/libctf.h +++ b/usr/src/lib/libctf/common/libctf.h @@ -118,6 +118,7 @@ extern int ctf_convert_set_batchsize(ctf_convert_t *, uint_t); extern int ctf_convert_set_flags(ctf_convert_t *, ctf_convert_flag_t); extern int ctf_convert_set_label(ctf_convert_t *, const char *); extern int ctf_convert_set_nthreads(ctf_convert_t *, uint_t); +extern int ctf_convert_add_ignore(ctf_convert_t *, const char *); extern ctf_file_t *ctf_fdconvert(ctf_convert_t *, int, int *, char *, size_t); diff --git a/usr/src/lib/libctf/common/libctf_impl.h b/usr/src/lib/libctf/common/libctf_impl.h index 6ed2665d11..8028dc0f8f 100644 --- a/usr/src/lib/libctf/common/libctf_impl.h +++ b/usr/src/lib/libctf/common/libctf_impl.h @@ -25,17 +25,24 @@ #include <libelf.h> #include <libctf.h> #include <ctf_impl.h> +#include <sys/list.h> #ifdef __cplusplus extern "C" { #endif +typedef struct ctf_convert_filelist { + list_node_t ccf_node; + char *ccf_basename; +} ctf_convert_filelist_t; + struct ctf_convert_handle { char *cch_label; uint_t cch_flags; uint_t cch_nthreads; uint_t cch_batchsize; ctf_convert_warn_f cch_warncb; + list_t cch_nodebug; void *cch_warncb_arg; }; diff --git a/usr/src/lib/libctf/common/mapfile-vers b/usr/src/lib/libctf/common/mapfile-vers index 9f5c408406..1337fbba45 100644 --- a/usr/src/lib/libctf/common/mapfile-vers +++ b/usr/src/lib/libctf/common/mapfile-vers @@ -67,6 +67,7 @@ SYMBOL_VERSION SUNWprivate_1.2 { ctf_add_typedef; ctf_add_union; ctf_add_volatile; + ctf_convert_add_ignore; ctf_convert_fini; ctf_convert_init; ctf_convert_set_batchsize; |