diff options
-rw-r--r-- | cmd/dtrace/test/tst/common/funcs/tst.substr.d | 74 | ||||
-rw-r--r-- | cmd/dtrace/test/tst/common/funcs/tst.substr.d.out | 92 | ||||
-rw-r--r-- | cmd/sgs/include/debug.h | 11 | ||||
-rw-r--r-- | cmd/sgs/include/sgs.h | 12 | ||||
-rw-r--r-- | lib/libdtrace/common/dt_cc.c | 6 | ||||
-rw-r--r-- | lib/libdtrace/common/dt_impl.h | 2 | ||||
-rw-r--r-- | lib/libdtrace/common/dt_link.c | 38 | ||||
-rw-r--r-- | lib/libdtrace/common/dt_open.c | 12 | ||||
-rw-r--r-- | lib/libdtrace/common/dt_pid.c | 8 | ||||
-rw-r--r-- | lib/libdtrace/common/dt_pragma.c | 48 |
10 files changed, 218 insertions, 85 deletions
diff --git a/cmd/dtrace/test/tst/common/funcs/tst.substr.d b/cmd/dtrace/test/tst/common/funcs/tst.substr.d index 6001d6b..edee644 100644 --- a/cmd/dtrace/test/tst/common/funcs/tst.substr.d +++ b/cmd/dtrace/test/tst/common/funcs/tst.substr.d @@ -20,18 +20,20 @@ */ /* - * Copyright 2006 Sun Microsystems, Inc. All rights reserved. + * Copyright 2008 Sun Microsystems, Inc. All rights reserved. * Use is subject to license terms. */ #pragma ident "%Z%%M% %I% %E% SMI" #pragma D option quiet +#pragma D option strsize=32 struct { int index; int length; int nolen; + int alt; } command[int]; int i; @@ -39,6 +41,9 @@ int i; BEGIN { str = "foobarbazbop"; + str2 = ""; + altstr = "CRAIG: Positioned them, I don't "; + altstr2 = "know... I'm fairly wide guy."; command[i].index = 3; command[i].nolen = 1; @@ -108,6 +113,18 @@ BEGIN command[i].length = -1; i++; + command[i].index = 3; + command[i].length = -4; + i++; + + command[i].index = 3; + command[i].length = -20; + i++; + + command[i].index = -10; + command[i].length = -5; + i++; + command[i].index = 0; command[i].length = 400; i++; @@ -144,6 +161,16 @@ BEGIN command[i].length = strlen(str) - 1; i++; + command[i].index = 100; + command[i].length = 10; + command[i].alt = 1; + i++; + + command[i].index = 100; + command[i].nolen = 1; + command[i].alt = 1; + i++; + end = i; i = 0; printf("#!/usr/perl5/bin/perl\n\nBEGIN {\n"); @@ -153,17 +180,21 @@ BEGIN tick-1ms /i < end && command[i].nolen/ { - this->result = substr(str, command[i].index); + this->str = command[i].alt ? altstr : str; + this->str2 = command[i].alt ? altstr2 : str2; + this->result = substr(command[i].alt ? + "CRAIG: Positioned them, I don't know... I'm fairly wide guy." : + str, command[i].index); - printf("\tif (substr(\"%s\", %d) != \"%s\") {\n", - str, command[i].index, this->result); + printf("\tif (substr(\"%s%s\", %d) ne \"%s\") {\n", + this->str, this->str2, command[i].index, this->result); - printf("\t\tprintf(\"perl => substr(\\\"%s\\\", %d) = ", - str, command[i].index); - printf("\\\"%%s\\\"\\n\",\n\t\t substr(\"%s\", %d));\n", - str, command[i].index); - printf("\t\tprintf(\" D => substr(\\\"%s\\\", %d) = ", - str, command[i].index); + printf("\t\tprintf(\"perl => substr(\\\"%s%s\\\", %d) = ", + this->str, this->str2, command[i].index); + printf("\\\"%%s\\\"\\n\",\n\t\t substr(\"%s%s\", %d));\n", + this->str, this->str2, command[i].index); + printf("\t\tprintf(\" D => substr(\\\"%s%s\\\", %d) = ", + this->str, this->str2, command[i].index); printf("\\\"%%s\\\"\\n\",\n\t\t \"%s\");\n", this->result); printf("\t\t$failed++;\n"); printf("\t}\n\n"); @@ -172,16 +203,21 @@ tick-1ms tick-1ms /i < end && !command[i].nolen/ { - this->result = substr(str, command[i].index, command[i].length); - - printf("\tif (substr(\"%s\", %d, %d) != \"%s\") {\n", - str, command[i].index, command[i].length, this->result); - printf("\t\tprintf(\"perl => substr(\\\"%s\\\", %d, %d) = ", - str, command[i].index, command[i].length); - printf("\\\"%%s\\\"\\n\",\n\t\t substr(\"%s\", %d, %d));\n", - str, command[i].index, command[i].length); - printf("\t\tprintf(\" D => substr(\\\"%s\\\", %d, %d) = ", + this->str = command[i].alt ? altstr : str; + this->str2 = command[i].alt ? altstr2 : str2; + this->result = substr(command[i].alt ? + "CRAIG: Positioned them, I don't know... I'm fairly wide guy." : str, command[i].index, command[i].length); + + printf("\tif (substr(\"%s%s\", %d, %d) ne \"%s\") {\n", + this->str, this->str2, command[i].index, command[i].length, + this->result); + printf("\t\tprintf(\"perl => substr(\\\"%s%s\\\", %d, %d) = ", + this->str, this->str2, command[i].index, command[i].length); + printf("\\\"%%s\\\"\\n\",\n\t\t substr(\"%s%s\", %d, %d));\n", + this->str, this->str2, command[i].index, command[i].length); + printf("\t\tprintf(\" D => substr(\\\"%s%s\\\", %d, %d) = ", + this->str, this->str2, command[i].index, command[i].length); printf("\\\"%%s\\\"\\n\",\n\t\t \"%s\");\n", this->result); printf("\t\t$failed++;\n"); printf("\t}\n\n"); diff --git a/cmd/dtrace/test/tst/common/funcs/tst.substr.d.out b/cmd/dtrace/test/tst/common/funcs/tst.substr.d.out index d4087a2..5b498ef 100644 --- a/cmd/dtrace/test/tst/common/funcs/tst.substr.d.out +++ b/cmd/dtrace/test/tst/common/funcs/tst.substr.d.out @@ -1,7 +1,7 @@ #!/usr/perl5/bin/perl BEGIN { - if (substr("foobarbazbop", 3) != "barbazbop") { + if (substr("foobarbazbop", 3) ne "barbazbop") { printf("perl => substr(\"foobarbazbop\", 3) = \"%s\"\n", substr("foobarbazbop", 3)); printf(" D => substr(\"foobarbazbop\", 3) = \"%s\"\n", @@ -9,7 +9,7 @@ BEGIN { $failed++; } - if (substr("foobarbazbop", 300) != "") { + if (substr("foobarbazbop", 300) ne "") { printf("perl => substr(\"foobarbazbop\", 300) = \"%s\"\n", substr("foobarbazbop", 300)); printf(" D => substr(\"foobarbazbop\", 300) = \"%s\"\n", @@ -17,7 +17,7 @@ BEGIN { $failed++; } - if (substr("foobarbazbop", -10) != "obarbazbop") { + if (substr("foobarbazbop", -10) ne "obarbazbop") { printf("perl => substr(\"foobarbazbop\", -10) = \"%s\"\n", substr("foobarbazbop", -10)); printf(" D => substr(\"foobarbazbop\", -10) = \"%s\"\n", @@ -25,7 +25,7 @@ BEGIN { $failed++; } - if (substr("foobarbazbop", 0) != "foobarbazbop") { + if (substr("foobarbazbop", 0) ne "foobarbazbop") { printf("perl => substr(\"foobarbazbop\", 0) = \"%s\"\n", substr("foobarbazbop", 0)); printf(" D => substr(\"foobarbazbop\", 0) = \"%s\"\n", @@ -33,7 +33,7 @@ BEGIN { $failed++; } - if (substr("foobarbazbop", 1) != "oobarbazbop") { + if (substr("foobarbazbop", 1) ne "oobarbazbop") { printf("perl => substr(\"foobarbazbop\", 1) = \"%s\"\n", substr("foobarbazbop", 1)); printf(" D => substr(\"foobarbazbop\", 1) = \"%s\"\n", @@ -41,7 +41,7 @@ BEGIN { $failed++; } - if (substr("foobarbazbop", 11) != "p") { + if (substr("foobarbazbop", 11) ne "p") { printf("perl => substr(\"foobarbazbop\", 11) = \"%s\"\n", substr("foobarbazbop", 11)); printf(" D => substr(\"foobarbazbop\", 11) = \"%s\"\n", @@ -49,7 +49,7 @@ BEGIN { $failed++; } - if (substr("foobarbazbop", 12) != "") { + if (substr("foobarbazbop", 12) ne "") { printf("perl => substr(\"foobarbazbop\", 12) = \"%s\"\n", substr("foobarbazbop", 12)); printf(" D => substr(\"foobarbazbop\", 12) = \"%s\"\n", @@ -57,7 +57,7 @@ BEGIN { $failed++; } - if (substr("foobarbazbop", 13) != "") { + if (substr("foobarbazbop", 13) ne "") { printf("perl => substr(\"foobarbazbop\", 13) = \"%s\"\n", substr("foobarbazbop", 13)); printf(" D => substr(\"foobarbazbop\", 13) = \"%s\"\n", @@ -65,7 +65,7 @@ BEGIN { $failed++; } - if (substr("foobarbazbop", 8, 20) != "zbop") { + if (substr("foobarbazbop", 8, 20) ne "zbop") { printf("perl => substr(\"foobarbazbop\", 8, 20) = \"%s\"\n", substr("foobarbazbop", 8, 20)); printf(" D => substr(\"foobarbazbop\", 8, 20) = \"%s\"\n", @@ -73,7 +73,7 @@ BEGIN { $failed++; } - if (substr("foobarbazbop", 4, 4) != "arba") { + if (substr("foobarbazbop", 4, 4) ne "arba") { printf("perl => substr(\"foobarbazbop\", 4, 4) = \"%s\"\n", substr("foobarbazbop", 4, 4)); printf(" D => substr(\"foobarbazbop\", 4, 4) = \"%s\"\n", @@ -81,7 +81,7 @@ BEGIN { $failed++; } - if (substr("foobarbazbop", 5, 8) != "rbazbop") { + if (substr("foobarbazbop", 5, 8) ne "rbazbop") { printf("perl => substr(\"foobarbazbop\", 5, 8) = \"%s\"\n", substr("foobarbazbop", 5, 8)); printf(" D => substr(\"foobarbazbop\", 5, 8) = \"%s\"\n", @@ -89,7 +89,7 @@ BEGIN { $failed++; } - if (substr("foobarbazbop", 5, 9) != "rbazbop") { + if (substr("foobarbazbop", 5, 9) ne "rbazbop") { printf("perl => substr(\"foobarbazbop\", 5, 9) = \"%s\"\n", substr("foobarbazbop", 5, 9)); printf(" D => substr(\"foobarbazbop\", 5, 9) = \"%s\"\n", @@ -97,7 +97,7 @@ BEGIN { $failed++; } - if (substr("foobarbazbop", 400, 20) != "") { + if (substr("foobarbazbop", 400, 20) ne "") { printf("perl => substr(\"foobarbazbop\", 400, 20) = \"%s\"\n", substr("foobarbazbop", 400, 20)); printf(" D => substr(\"foobarbazbop\", 400, 20) = \"%s\"\n", @@ -105,7 +105,7 @@ BEGIN { $failed++; } - if (substr("foobarbazbop", 400, 0) != "") { + if (substr("foobarbazbop", 400, 0) ne "") { printf("perl => substr(\"foobarbazbop\", 400, 0) = \"%s\"\n", substr("foobarbazbop", 400, 0)); printf(" D => substr(\"foobarbazbop\", 400, 0) = \"%s\"\n", @@ -113,7 +113,7 @@ BEGIN { $failed++; } - if (substr("foobarbazbop", 400, -1) != "") { + if (substr("foobarbazbop", 400, -1) ne "") { printf("perl => substr(\"foobarbazbop\", 400, -1) = \"%s\"\n", substr("foobarbazbop", 400, -1)); printf(" D => substr(\"foobarbazbop\", 400, -1) = \"%s\"\n", @@ -121,7 +121,7 @@ BEGIN { $failed++; } - if (substr("foobarbazbop", 3, 0) != "") { + if (substr("foobarbazbop", 3, 0) ne "") { printf("perl => substr(\"foobarbazbop\", 3, 0) = \"%s\"\n", substr("foobarbazbop", 3, 0)); printf(" D => substr(\"foobarbazbop\", 3, 0) = \"%s\"\n", @@ -129,15 +129,39 @@ BEGIN { $failed++; } - if (substr("foobarbazbop", 3, -1) != "") { + if (substr("foobarbazbop", 3, -1) ne "barbazbo") { printf("perl => substr(\"foobarbazbop\", 3, -1) = \"%s\"\n", substr("foobarbazbop", 3, -1)); printf(" D => substr(\"foobarbazbop\", 3, -1) = \"%s\"\n", + "barbazbo"); + $failed++; + } + + if (substr("foobarbazbop", 3, -4) ne "barba") { + printf("perl => substr(\"foobarbazbop\", 3, -4) = \"%s\"\n", + substr("foobarbazbop", 3, -4)); + printf(" D => substr(\"foobarbazbop\", 3, -4) = \"%s\"\n", + "barba"); + $failed++; + } + + if (substr("foobarbazbop", 3, -20) ne "") { + printf("perl => substr(\"foobarbazbop\", 3, -20) = \"%s\"\n", + substr("foobarbazbop", 3, -20)); + printf(" D => substr(\"foobarbazbop\", 3, -20) = \"%s\"\n", ""); $failed++; } - if (substr("foobarbazbop", 0, 400) != "foobarbazbop") { + if (substr("foobarbazbop", -10, -5) ne "obarb") { + printf("perl => substr(\"foobarbazbop\", -10, -5) = \"%s\"\n", + substr("foobarbazbop", -10, -5)); + printf(" D => substr(\"foobarbazbop\", -10, -5) = \"%s\"\n", + "obarb"); + $failed++; + } + + if (substr("foobarbazbop", 0, 400) ne "foobarbazbop") { printf("perl => substr(\"foobarbazbop\", 0, 400) = \"%s\"\n", substr("foobarbazbop", 0, 400)); printf(" D => substr(\"foobarbazbop\", 0, 400) = \"%s\"\n", @@ -145,7 +169,7 @@ BEGIN { $failed++; } - if (substr("foobarbazbop", -1, 400) != "p") { + if (substr("foobarbazbop", -1, 400) ne "p") { printf("perl => substr(\"foobarbazbop\", -1, 400) = \"%s\"\n", substr("foobarbazbop", -1, 400)); printf(" D => substr(\"foobarbazbop\", -1, 400) = \"%s\"\n", @@ -153,7 +177,7 @@ BEGIN { $failed++; } - if (substr("foobarbazbop", -1, 0) != "") { + if (substr("foobarbazbop", -1, 0) ne "") { printf("perl => substr(\"foobarbazbop\", -1, 0) = \"%s\"\n", substr("foobarbazbop", -1, 0)); printf(" D => substr(\"foobarbazbop\", -1, 0) = \"%s\"\n", @@ -161,7 +185,7 @@ BEGIN { $failed++; } - if (substr("foobarbazbop", -1, -1) != "") { + if (substr("foobarbazbop", -1, -1) ne "") { printf("perl => substr(\"foobarbazbop\", -1, -1) = \"%s\"\n", substr("foobarbazbop", -1, -1)); printf(" D => substr(\"foobarbazbop\", -1, -1) = \"%s\"\n", @@ -169,7 +193,7 @@ BEGIN { $failed++; } - if (substr("foobarbazbop", -24, 24) != "foobarbazbop") { + if (substr("foobarbazbop", -24, 24) ne "foobarbazbop") { printf("perl => substr(\"foobarbazbop\", -24, 24) = \"%s\"\n", substr("foobarbazbop", -24, 24)); printf(" D => substr(\"foobarbazbop\", -24, 24) = \"%s\"\n", @@ -177,7 +201,7 @@ BEGIN { $failed++; } - if (substr("foobarbazbop", -24, 12) != "") { + if (substr("foobarbazbop", -24, 12) ne "") { printf("perl => substr(\"foobarbazbop\", -24, 12) = \"%s\"\n", substr("foobarbazbop", -24, 12)); printf(" D => substr(\"foobarbazbop\", -24, 12) = \"%s\"\n", @@ -185,7 +209,7 @@ BEGIN { $failed++; } - if (substr("foobarbazbop", -24, 13) != "f") { + if (substr("foobarbazbop", -24, 13) ne "f") { printf("perl => substr(\"foobarbazbop\", -24, 13) = \"%s\"\n", substr("foobarbazbop", -24, 13)); printf(" D => substr(\"foobarbazbop\", -24, 13) = \"%s\"\n", @@ -193,7 +217,7 @@ BEGIN { $failed++; } - if (substr("foobarbazbop", -12, 12) != "foobarbazbop") { + if (substr("foobarbazbop", -12, 12) ne "foobarbazbop") { printf("perl => substr(\"foobarbazbop\", -12, 12) = \"%s\"\n", substr("foobarbazbop", -12, 12)); printf(" D => substr(\"foobarbazbop\", -12, 12) = \"%s\"\n", @@ -201,7 +225,7 @@ BEGIN { $failed++; } - if (substr("foobarbazbop", -12, 11) != "foobarbazbo") { + if (substr("foobarbazbop", -12, 11) ne "foobarbazbo") { printf("perl => substr(\"foobarbazbop\", -12, 11) = \"%s\"\n", substr("foobarbazbop", -12, 11)); printf(" D => substr(\"foobarbazbop\", -12, 11) = \"%s\"\n", @@ -209,6 +233,22 @@ BEGIN { $failed++; } + if (substr("CRAIG: Positioned them, I don't know... I'm fairly wide guy.", 100, 10) ne "") { + printf("perl => substr(\"CRAIG: Positioned them, I don't know... I'm fairly wide guy.\", 100, 10) = \"%s\"\n", + substr("CRAIG: Positioned them, I don't know... I'm fairly wide guy.", 100, 10)); + printf(" D => substr(\"CRAIG: Positioned them, I don't know... I'm fairly wide guy.\", 100, 10) = \"%s\"\n", + ""); + $failed++; + } + + if (substr("CRAIG: Positioned them, I don't know... I'm fairly wide guy.", 100) ne "") { + printf("perl => substr(\"CRAIG: Positioned them, I don't know... I'm fairly wide guy.\", 100) = \"%s\"\n", + substr("CRAIG: Positioned them, I don't know... I'm fairly wide guy.", 100)); + printf(" D => substr(\"CRAIG: Positioned them, I don't know... I'm fairly wide guy.\", 100) = \"%s\"\n", + ""); + $failed++; + } + exit($failed); } diff --git a/cmd/sgs/include/debug.h b/cmd/sgs/include/debug.h index 1b733bb..0a42f8d 100644 --- a/cmd/sgs/include/debug.h +++ b/cmd/sgs/include/debug.h @@ -405,6 +405,7 @@ extern uintptr_t Dbg_setup(const char *, Dbg_desc *); #define Dbg_unused_file Dbg64_unused_file #define Dbg_unused_lcinterface Dbg64_unused_lcinterface +#define Dbg_unused_path Dbg64_unused_path #define Dbg_unused_sec Dbg64_unused_sec #define Dbg_unused_unref Dbg64_unused_unref @@ -607,6 +608,7 @@ extern uintptr_t Dbg_setup(const char *, Dbg_desc *); #define Dbg_unused_file Dbg32_unused_file #define Dbg_unused_lcinterface Dbg32_unused_lcinterface +#define Dbg_unused_path Dbg32_unused_path #define Dbg_unused_sec Dbg32_unused_sec #define Dbg_unused_unref Dbg32_unused_unref @@ -676,7 +678,7 @@ extern void Dbg_file_del_rescan(Lm_list *); extern void Dbg_file_delete(Rt_map *); extern void Dbg_file_dlclose(Lm_list *, const char *, int); extern void Dbg_file_dldump(Rt_map *, const char *, int); -extern void Dbg_file_dlopen(Rt_map *, const char *, int); +extern void Dbg_file_dlopen(Rt_map *, const char *, int *, int); extern void Dbg_file_elf(Lm_list *, const char *, ulong_t, ulong_t, ulong_t, ulong_t, const char *, Aliste); extern void Dbg_file_filtee(Lm_list *, const char *, const char *, int); @@ -708,7 +710,7 @@ extern void Dbg_libs_found(Lm_list *, const char *, int); extern void Dbg_libs_ignore(Lm_list *, const char *); extern void Dbg_libs_init(Lm_list *, List *, List *); extern void Dbg_libs_l(Lm_list *, const char *, const char *); -extern void Dbg_libs_path(Lm_list *, const char *, Half, const char *); +extern void Dbg_libs_path(Lm_list *, const char *, uint_t, const char *); extern void Dbg_libs_req(Lm_list *, const char *, const char *, const char *); extern void Dbg_libs_update(Lm_list *, List *, List *); @@ -805,7 +807,8 @@ extern void Dbg_syms_ar_resolve(Lm_list *, Xword, Elf_Arsym *, extern void Dbg_syms_ar_title(Lm_list *, const char *, int); extern void Dbg_syms_created(Lm_list *, const char *); extern void Dbg_syms_discarded(Lm_list *, Sym_desc *); -extern void Dbg_syms_dlsym(Rt_map *, const char *, const char *, int); +extern void Dbg_syms_dlsym(Rt_map *, const char *, int *, const char *, + int); extern void Dbg_syms_dup_sort_addr(Lm_list *, const char *, const char *, const char *, Addr); extern void Dbg_syms_entered(Ofl_desc *, Sym *, Sym_desc *); @@ -858,6 +861,8 @@ extern void Dbg_util_wait(Rt_map *, Rt_map *, int); extern void Dbg_unused_file(Lm_list *, const char *, int, uint_t); extern void Dbg_unused_lcinterface(Rt_map *, Rt_map *, int); +extern void Dbg_unused_path(Lm_list *, const char *, uint_t, uint_t, + const char *); extern void Dbg_unused_sec(Lm_list *, Is_desc *); extern void Dbg_unused_unref(Rt_map *, const char *); diff --git a/cmd/sgs/include/sgs.h b/cmd/sgs/include/sgs.h index a1ec44b..388ec97 100644 --- a/cmd/sgs/include/sgs.h +++ b/cmd/sgs/include/sgs.h @@ -24,7 +24,7 @@ * All Rights Reserved * * - * Copyright 2006 Sun Microsystems, Inc. All rights reserved. + * Copyright 2008 Sun Microsystems, Inc. All rights reserved. * Use is subject to license terms. * * Global include file for all sgs. @@ -66,8 +66,14 @@ extern "C" { #ifndef _ASM -extern const char link_ver_string[]; /* Linker version id */ - /* see libconv/{plat}/vernote.s */ +/* + * link_ver_string[] contains a version string for use by the link-editor + * and all other linker components. It is found in libconv, and is + * generated by sgs/libconv/common/bld_vernote.ksh. That script produces + * libconv/{plat}/vernote.s, which is in turn assembled/linked into + * libconv. + */ +extern const char link_ver_string[]; /* * Macro to round to next double word boundary. */ diff --git a/lib/libdtrace/common/dt_cc.c b/lib/libdtrace/common/dt_cc.c index 64b2922..575fb9c 100644 --- a/lib/libdtrace/common/dt_cc.c +++ b/lib/libdtrace/common/dt_cc.c @@ -20,7 +20,7 @@ */ /* - * Copyright 2007 Sun Microsystems, Inc. All rights reserved. + * Copyright 2008 Sun Microsystems, Inc. All rights reserved. * Use is subject to license terms. */ @@ -2010,8 +2010,10 @@ dt_load_libs_dir(dtrace_hdl_t *dtp, const char *path) dt_dprintf("skipping library %s: %s\n", dld->dtld_library, dtrace_errmsg(dtp, dtrace_errno(dtp))); - } else + } else { + dld->dtld_loaded = B_TRUE; dt_program_destroy(dtp, pgp); + } } dt_lib_depend_free(dtp); diff --git a/lib/libdtrace/common/dt_impl.h b/lib/libdtrace/common/dt_impl.h index 2454e3b..9b22dfb 100644 --- a/lib/libdtrace/common/dt_impl.h +++ b/lib/libdtrace/common/dt_impl.h @@ -18,6 +18,7 @@ * * CDDL HEADER END */ + /* * Copyright 2008 Sun Microsystems, Inc. All rights reserved. * Use is subject to license terms. @@ -183,6 +184,7 @@ typedef struct dt_lib_depend { char *dtld_libpath; /* library pathname */ uint_t dtld_finish; /* completion time in tsort for lib */ uint_t dtld_start; /* starting time in tsort for lib */ + uint_t dtld_loaded; /* boolean: is this library loaded */ dt_list_t dtld_dependencies; /* linked-list of lib dependencies */ dt_list_t dtld_dependents; /* linked-list of lib dependents */ } dt_lib_depend_t; diff --git a/lib/libdtrace/common/dt_link.c b/lib/libdtrace/common/dt_link.c index 957d8f8..e317fe7 100644 --- a/lib/libdtrace/common/dt_link.c +++ b/lib/libdtrace/common/dt_link.c @@ -20,7 +20,7 @@ */ /* - * Copyright 2007 Sun Microsystems, Inc. All rights reserved. + * Copyright 2008 Sun Microsystems, Inc. All rights reserved. * Use is subject to license terms. */ @@ -850,7 +850,9 @@ dt_modtext(dtrace_hdl_t *dtp, char *p, int isenabled, GElf_Rela *rela, #elif defined(__i386) || defined(__amd64) #define DT_OP_NOP 0x90 +#define DT_OP_RET 0xc3 #define DT_OP_CALL 0xe8 +#define DT_OP_JMP32 0xe9 #define DT_OP_REX_RAX 0x48 #define DT_OP_XOR_EAX_0 0x33 #define DT_OP_XOR_EAX_1 0xc0 @@ -860,6 +862,7 @@ dt_modtext(dtrace_hdl_t *dtp, char *p, int isenabled, GElf_Rela *rela, uint32_t *off) { uint8_t *ip = (uint8_t *)(p + rela->r_offset - 1); + uint8_t ret; /* * On x86, the first byte of the instruction is the call opcode and @@ -883,38 +886,43 @@ dt_modtext(dtrace_hdl_t *dtp, char *p, int isenabled, GElf_Rela *rela, * We may have already processed this object file in an earlier linker * invocation. Check to see if the present instruction sequence matches * the one we would install. For is-enabled probes, we advance the - * offset to the first nop instruction in the sequence. + * offset to the first nop instruction in the sequence to match the + * text modification code below. */ if (!isenabled) { - if (ip[0] == DT_OP_NOP && ip[1] == DT_OP_NOP && - ip[2] == DT_OP_NOP && ip[3] == DT_OP_NOP && - ip[4] == DT_OP_NOP) + if ((ip[0] == DT_OP_NOP || ip[0] == DT_OP_RET) && + ip[1] == DT_OP_NOP && ip[2] == DT_OP_NOP && + ip[3] == DT_OP_NOP && ip[4] == DT_OP_NOP) return (0); } else if (dtp->dt_oflags & DTRACE_O_LP64) { if (ip[0] == DT_OP_REX_RAX && ip[1] == DT_OP_XOR_EAX_0 && ip[2] == DT_OP_XOR_EAX_1 && - ip[3] == DT_OP_NOP && ip[4] == DT_OP_NOP) { + (ip[3] == DT_OP_NOP || ip[3] == DT_OP_RET) && + ip[4] == DT_OP_NOP) { (*off) += 3; return (0); } } else { if (ip[0] == DT_OP_XOR_EAX_0 && ip[1] == DT_OP_XOR_EAX_1 && - ip[2] == DT_OP_NOP && ip[3] == DT_OP_NOP && - ip[4] == DT_OP_NOP) { + (ip[2] == DT_OP_NOP || ip[2] == DT_OP_RET) && + ip[3] == DT_OP_NOP && ip[4] == DT_OP_NOP) { (*off) += 2; return (0); } } /* - * We only expect a call instrution with a 32-bit displacement. + * We expect either a call instrution with a 32-bit displacement or a + * jmp instruction with a 32-bit displacement acting as a tail-call. */ - if (ip[0] != DT_OP_CALL) { - dt_dprintf("found %x instead of a call instruction at %llx\n", - ip[0], (u_longlong_t)rela->r_offset); + if (ip[0] != DT_OP_CALL && ip[0] != DT_OP_JMP32) { + dt_dprintf("found %x instead of a call or jmp instruction at " + "%llx\n", ip[0], (u_longlong_t)rela->r_offset); return (-1); } + ret = (ip[0] == DT_OP_JMP32) ? DT_OP_RET : DT_OP_NOP; + /* * Establish the instruction sequence -- all nops for probes, and an * instruction to clear the return value register (%eax/%rax) followed @@ -923,7 +931,7 @@ dt_modtext(dtrace_hdl_t *dtp, char *p, int isenabled, GElf_Rela *rela, * for more readable disassembly when the probe is enabled. */ if (!isenabled) { - ip[0] = DT_OP_NOP; + ip[0] = ret; ip[1] = DT_OP_NOP; ip[2] = DT_OP_NOP; ip[3] = DT_OP_NOP; @@ -932,13 +940,13 @@ dt_modtext(dtrace_hdl_t *dtp, char *p, int isenabled, GElf_Rela *rela, ip[0] = DT_OP_REX_RAX; ip[1] = DT_OP_XOR_EAX_0; ip[2] = DT_OP_XOR_EAX_1; - ip[3] = DT_OP_NOP; + ip[3] = ret; ip[4] = DT_OP_NOP; (*off) += 3; } else { ip[0] = DT_OP_XOR_EAX_0; ip[1] = DT_OP_XOR_EAX_1; - ip[2] = DT_OP_NOP; + ip[2] = ret; ip[3] = DT_OP_NOP; ip[4] = DT_OP_NOP; (*off) += 2; diff --git a/lib/libdtrace/common/dt_open.c b/lib/libdtrace/common/dt_open.c index 5c04bee..86f1864 100644 --- a/lib/libdtrace/common/dt_open.c +++ b/lib/libdtrace/common/dt_open.c @@ -103,8 +103,9 @@ #define DT_VERS_1_4_1 DT_VERSION_NUMBER(1, 4, 1) #define DT_VERS_1_5 DT_VERSION_NUMBER(1, 5, 0) #define DT_VERS_1_6 DT_VERSION_NUMBER(1, 6, 0) -#define DT_VERS_LATEST DT_VERS_1_6 -#define DT_VERS_STRING "Sun D 1.6" +#define DT_VERS_1_6_1 DT_VERSION_NUMBER(1, 6, 1) +#define DT_VERS_LATEST DT_VERS_1_6_1 +#define DT_VERS_STRING "Sun D 1.6.1" const dt_version_t _dtrace_versions[] = { DT_VERS_1_0, /* D API 1.0.0 (PSARC 2001/466) Solaris 10 FCS */ @@ -117,6 +118,7 @@ const dt_version_t _dtrace_versions[] = { DT_VERS_1_4_1, /* D API 1.4.1 Solaris Express 4/07 */ DT_VERS_1_5, /* D API 1.5 Solaris Express 7/07 */ DT_VERS_1_6, /* D API 1.6 */ + DT_VERS_1_6_1, /* D API 1.6.1 */ 0 }; @@ -1291,6 +1293,9 @@ dtrace_close(dtrace_hdl_t *dtp) dt_dirpath_t *dirp; int i; + if (dtp->dt_procs != NULL) + dt_proc_hash_destroy(dtp); + while ((pgp = dt_list_next(&dtp->dt_programs)) != NULL) dt_program_destroy(dtp, pgp); @@ -1319,9 +1324,6 @@ dtrace_close(dtrace_hdl_t *dtp) while ((pvp = dt_list_next(&dtp->dt_provlist)) != NULL) dt_provider_destroy(dtp, pvp); - if (dtp->dt_procs != NULL) - dt_proc_hash_destroy(dtp); - if (dtp->dt_fd != -1) (void) close(dtp->dt_fd); if (dtp->dt_ftfd != -1) diff --git a/lib/libdtrace/common/dt_pid.c b/lib/libdtrace/common/dt_pid.c index 6346329..cf9498b 100644 --- a/lib/libdtrace/common/dt_pid.c +++ b/lib/libdtrace/common/dt_pid.c @@ -667,7 +667,13 @@ dt_pid_create_probes(dtrace_probedesc_t *pdp, dtrace_hdl_t *dtp, dt_pcb_t *pcb) assert(dpr != NULL); (void) pthread_mutex_lock(&dpr->dpr_lock); - err = dt_pid_create_pid_probes(pdp, dtp, pcb, dpr); + if ((err = dt_pid_create_pid_probes(pdp, dtp, pcb, dpr)) == 0) { + /* + * Alert other retained enablings which may match + * against the newly created probes. + */ + (void) dt_ioctl(dtp, DTRACEIOC_ENABLE, NULL); + } (void) pthread_mutex_unlock(&dpr->dpr_lock); dt_proc_release(dtp, P); diff --git a/lib/libdtrace/common/dt_pragma.c b/lib/libdtrace/common/dt_pragma.c index 00b8269..a8bab85 100644 --- a/lib/libdtrace/common/dt_pragma.c +++ b/lib/libdtrace/common/dt_pragma.c @@ -18,8 +18,9 @@ * * CDDL HEADER END */ + /* - * Copyright 2007 Sun Microsystems, Inc. All rights reserved. + * Copyright 2008 Sun Microsystems, Inc. All rights reserved. * Use is subject to license terms. */ @@ -210,6 +211,7 @@ dt_pragma_depends(const char *prname, dt_node_t *cnp) dt_node_t *nnp = cnp ? cnp->dn_list : NULL; int found; dt_lib_depend_t *dld; + char lib[MAXPATHLEN]; if (cnp == NULL || nnp == NULL || cnp->dn_kind != DT_NODE_IDENT || nnp->dn_kind != DT_NODE_IDENT) { @@ -223,29 +225,53 @@ dt_pragma_depends(const char *prname, dt_node_t *cnp) dt_module_t *mp = dt_module_lookup_by_name(dtp, nnp->dn_string); found = mp != NULL && dt_module_getctf(dtp, mp) != NULL; } else if (strcmp(cnp->dn_string, "library") == 0) { - - /* - * We have the file we are working on in dtp->dt_filetag - * so find that node and add the dependency in. - */ if (yypcb->pcb_cflags & DTRACE_C_CTL) { - char lib[MAXPATHLEN]; + assert(dtp->dt_filetag != NULL); + /* + * We have the file we are working on in dtp->dt_filetag + * so find that node and add the dependency in. + */ dld = dt_lib_depend_lookup(&dtp->dt_lib_dep, dtp->dt_filetag); assert(dld != NULL); - (void) snprintf(lib, MAXPATHLEN, "%s%s", + (void) snprintf(lib, sizeof (lib), "%s%s", dld->dtld_libpath, nnp->dn_string); if ((dt_lib_depend_add(dtp, &dld->dtld_dependencies, lib)) != 0) { xyerror(D_PRAGMA_DEPEND, - "failed to add dependency %s:%s\n", - lib, + "failed to add dependency %s:%s\n", lib, dtrace_errmsg(dtp, dtrace_errno(dtp))); } + } else { + /* + * By this point we have already performed a topological + * sort of the dependencies; we process this directive + * as satisfied as long as the dependency was properly + * loaded. + */ + if (dtp->dt_filetag == NULL) + xyerror(D_PRAGMA_DEPEND, "main program may " + "not explicitly depend on a library"); + + dld = dt_lib_depend_lookup(&dtp->dt_lib_dep, + dtp->dt_filetag); + assert(dld != NULL); + + (void) snprintf(lib, sizeof (lib), "%s%s", + dld->dtld_libpath, nnp->dn_string); + dld = dt_lib_depend_lookup(&dtp->dt_lib_dep_sorted, + lib); + assert(dld != NULL); + + if (!dld->dtld_loaded) + xyerror(D_PRAGMA_DEPEND, "program requires " + "library \"%s\" which failed to load", + lib); } - found = 1; + + found = B_TRUE; } else { xyerror(D_PRAGMA_INVAL, "invalid class %s " "specified by #pragma %s\n", cnp->dn_string, prname); |