From: H.J. Lu Date: Fri, 19 Jan 2007 15:13:29 +0000 (+0000) Subject: ld/ X-Git-Url: https://git.libre-soc.org/?a=commitdiff_plain;h=d8cf8b513333c644cc5305eff9d5c0dfcac69de5;p=binutils-gdb.git ld/ 2007-01-19 H.J. Lu * ld.h (args_type): Add new symbolic and dynamic_list fields. * ld.texinfo: Update -Bsymbolic-functions. * ldmain.c (main): Initialize command_line.symbolic to symbolic_unset and command_line.dynamic_list to dynamic_list_unset. Check -Bsymbolic, -Bsymbolic-functions and --dynamic-list* before setting link_info.symbolic, link_info.dynamic and link_info.dynamic_data. * lexsup.c (option_values): Add OPTION_SYMBOLIC_FUNCTIONS. (ld_options): Use OPTION_SYMBOLIC_FUNCTIONS with -Bsymbolic-functions. (parse_args): Handle -Bsymbolic-functions. Don't set link_info.dynamic, link_info.dynamic_data and link_info.symbolic here. Set command_line.symbolic for -Bsymbolic. Set command_line.dynamic_list and command_line.symbolic for --dynamic-list-data, --dynamic-list-cpp-new, --dynamic-list-cpp-typeinfo and --dynamic-list. ld/testsuite/ 2007-01-19 H.J. Lu * ld-elf/dl6.c: New file. * ld-elf/dl6a.out: Likewise. * ld-elf/dl6amain.c: Likewise. * ld-elf/dl6b.out: Likewise. * ld-elf/dl6bmain.c: Likewise. * ld-elf/dl6cmain.c: Likewise. * ld-elf/dl6dmain.c: Likewise. * ld-elf/shared.exp: Add new tests for -Bsymbolic, -Bsymbolic-functions, --dynamic-list-data and --dynamic-list-cpp-new. --- diff --git a/ld/ChangeLog b/ld/ChangeLog index 4fb8e5545c0..48a9b3e7550 100644 --- a/ld/ChangeLog +++ b/ld/ChangeLog @@ -1,3 +1,25 @@ +2007-01-19 H.J. Lu + + * ld.h (args_type): Add new symbolic and dynamic_list fields. + + * ld.texinfo: Update -Bsymbolic-functions. + + * ldmain.c (main): Initialize command_line.symbolic to + symbolic_unset and command_line.dynamic_list to + dynamic_list_unset. Check -Bsymbolic, -Bsymbolic-functions and + --dynamic-list* before setting link_info.symbolic, + link_info.dynamic and link_info.dynamic_data. + + * lexsup.c (option_values): Add OPTION_SYMBOLIC_FUNCTIONS. + (ld_options): Use OPTION_SYMBOLIC_FUNCTIONS with + -Bsymbolic-functions. + (parse_args): Handle -Bsymbolic-functions. Don't set + link_info.dynamic, link_info.dynamic_data and link_info.symbolic + here. Set command_line.symbolic for -Bsymbolic. Set + command_line.dynamic_list and command_line.symbolic for + --dynamic-list-data, --dynamic-list-cpp-new, + --dynamic-list-cpp-typeinfo and --dynamic-list. + 2007-01-19 Jakub Jelinek H.J. Lu diff --git a/ld/ld.h b/ld/ld.h index e73ffe1d5e0..683b414ba7c 100644 --- a/ld/ld.h +++ b/ld/ld.h @@ -203,6 +203,23 @@ typedef struct { behaviour of the linker. The new default behaviour is to reject such input files. */ bfd_boolean accept_unknown_input_arch; + + /* -Bsymbolic and -Bsymbolic-functions, as set on command line. */ + enum + { + symbolic_unset = 0, + symbolic, + symbolic_functions, + } symbolic; + + /* --dynamic-list, --dynamic-list-cpp-new, --dynamic-list-cpp-typeinfo + and --dynamic-list FILE, as set on command line. */ + enum + { + dynamic_list_unset = 0, + dynamic_list_data, + dynamic_list + } dynamic_list; } args_type; extern args_type command_line; diff --git a/ld/ld.texinfo b/ld/ld.texinfo index 3c7b08f19dc..47e3e9ae200 100644 --- a/ld/ld.texinfo +++ b/ld/ld.texinfo @@ -1150,7 +1150,6 @@ platforms which support shared libraries. @item -Bsymbolic-functions When creating a shared library, bind references to global function symbols to the definition within the shared library, if any. -@option{-Bsymbolic-functions} is an alias for @option{--dynamic-list-data}. This option is only meaningful on ELF platforms which support shared libraries. diff --git a/ld/ldmain.c b/ld/ldmain.c index 8bd4bf4786a..9e6a0c393d8 100644 --- a/ld/ldmain.c +++ b/ld/ldmain.c @@ -256,6 +256,8 @@ main (int argc, char **argv) command_line.warn_mismatch = TRUE; command_line.check_section_addresses = TRUE; command_line.accept_unknown_input_arch = FALSE; + command_line.symbolic = symbolic_unset; + command_line.dynamic_list = dynamic_list_unset; sort_section = none; @@ -356,6 +358,43 @@ main (int argc, char **argv) einfo (_("%P%F: -r and -shared may not be used together\n")); } + /* We may have -Bsymbolic, -Bsymbolic-functions, --dynamic-list-data, + --dynamic-list-cpp-new, --dynamic-list-cpp-typeinfo and + --dynamic-list FILE. -Bsymbolic and -Bsymbolic-functions are + for shared libraries. -Bsymbolic overrides all others and vice + versa. */ + switch (command_line.symbolic) + { + case symbolic_unset: + break; + case symbolic: + /* -Bsymbolic is for shared library only. */ + if (link_info.shared) + { + link_info.symbolic = TRUE; + /* Should we free the unused memory? */ + link_info.dynamic_list = NULL; + command_line.dynamic_list = dynamic_list_unset; + } + break; + case symbolic_functions: + /* -Bsymbolic-functions is for shared library only. */ + if (link_info.shared) + command_line.dynamic_list = dynamic_list_data; + break; + } + + switch (command_line.dynamic_list) + { + case dynamic_list_unset: + break; + case dynamic_list_data: + link_info.dynamic_data = TRUE; + case dynamic_list: + link_info.dynamic = TRUE; + break; + } + if (! link_info.shared) { if (command_line.filter_shlib) diff --git a/ld/lexsup.c b/ld/lexsup.c index 125a987faad..a95b117abae 100644 --- a/ld/lexsup.c +++ b/ld/lexsup.c @@ -97,6 +97,7 @@ enum option_values OPTION_SORT_SECTION, OPTION_STATS, OPTION_SYMBOLIC, + OPTION_SYMBOLIC_FUNCTIONS, OPTION_TASK_LINK, OPTION_TBSS, OPTION_TDATA, @@ -353,7 +354,7 @@ static const struct ld_option ld_options[] = '\0', NULL, NULL, ONE_DASH }, { {"Bsymbolic", no_argument, NULL, OPTION_SYMBOLIC}, '\0', NULL, N_("Bind global references locally"), ONE_DASH }, - { {"Bsymbolic-functions", no_argument, NULL, OPTION_DYNAMIC_LIST_DATA}, + { {"Bsymbolic-functions", no_argument, NULL, OPTION_SYMBOLIC_FUNCTIONS}, '\0', NULL, N_("Bind global function references locally"), ONE_DASH }, { {"check-sections", no_argument, NULL, OPTION_CHECK_SECTIONS}, '\0', NULL, N_("Check section addresses for overlaps (default)"), @@ -1144,7 +1145,10 @@ parse_args (unsigned argc, char **argv) config.stats = TRUE; break; case OPTION_SYMBOLIC: - link_info.symbolic = TRUE; + command_line.symbolic = symbolic; + break; + case OPTION_SYMBOLIC_FUNCTIONS: + command_line.symbolic = symbolic_functions; break; case 't': trace_files = TRUE; @@ -1261,16 +1265,23 @@ parse_args (unsigned argc, char **argv) command_line.version_exports_section = optarg; break; case OPTION_DYNAMIC_LIST_DATA: - link_info.dynamic_data = TRUE; - link_info.dynamic = TRUE; + command_line.dynamic_list = dynamic_list_data; + if (command_line.symbolic == symbolic) + command_line.symbolic = symbolic_unset; break; case OPTION_DYNAMIC_LIST_CPP_TYPEINFO: lang_append_dynamic_list_cpp_typeinfo (); - link_info.dynamic = TRUE; + if (command_line.dynamic_list != dynamic_list_data) + command_line.dynamic_list = dynamic_list; + if (command_line.symbolic == symbolic) + command_line.symbolic = symbolic_unset; break; case OPTION_DYNAMIC_LIST_CPP_NEW: lang_append_dynamic_list_cpp_new (); - link_info.dynamic = TRUE; + if (command_line.dynamic_list != dynamic_list_data) + command_line.dynamic_list = dynamic_list; + if (command_line.symbolic == symbolic) + command_line.symbolic = symbolic_unset; break; case OPTION_DYNAMIC_LIST: /* This option indicates a small script that only specifies @@ -1285,7 +1296,10 @@ parse_args (unsigned argc, char **argv) parser_input = input_dynamic_list; yyparse (); } - link_info.dynamic = TRUE; + if (command_line.dynamic_list != dynamic_list_data) + command_line.dynamic_list = dynamic_list; + if (command_line.symbolic == symbolic) + command_line.symbolic = symbolic_unset; break; case OPTION_WARN_COMMON: config.warn_common = TRUE; diff --git a/ld/testsuite/ChangeLog b/ld/testsuite/ChangeLog index db2440e2a71..2aa43d907f9 100644 --- a/ld/testsuite/ChangeLog +++ b/ld/testsuite/ChangeLog @@ -1,3 +1,17 @@ +2007-01-19 H.J. Lu + + * ld-elf/dl6.c: New file. + * ld-elf/dl6a.out: Likewise. + * ld-elf/dl6amain.c: Likewise. + * ld-elf/dl6b.out: Likewise. + * ld-elf/dl6bmain.c: Likewise. + * ld-elf/dl6cmain.c: Likewise. + * ld-elf/dl6dmain.c: Likewise. + + * ld-elf/shared.exp: Add new tests for -Bsymbolic, + -Bsymbolic-functions, --dynamic-list-data and + --dynamic-list-cpp-new. + 2007-01-19 H.J. Lu * ld-elf/maxpage3.t: New file. diff --git a/ld/testsuite/ld-elf/dl6.c b/ld/testsuite/ld-elf/dl6.c new file mode 100644 index 00000000000..f655ca6ef33 --- /dev/null +++ b/ld/testsuite/ld-elf/dl6.c @@ -0,0 +1,14 @@ +#include + +int bar = 10; + +void +foo (void) +{ + if (bar == 10) + printf ("bar is in DSO.\n"); + else if (bar == -20) + printf ("bar is in main.\n"); + else + printf ("FAIL\n"); +} diff --git a/ld/testsuite/ld-elf/dl6a.out b/ld/testsuite/ld-elf/dl6a.out new file mode 100644 index 00000000000..186e8488e29 --- /dev/null +++ b/ld/testsuite/ld-elf/dl6a.out @@ -0,0 +1 @@ +bar is in main. diff --git a/ld/testsuite/ld-elf/dl6amain.c b/ld/testsuite/ld-elf/dl6amain.c new file mode 100644 index 00000000000..9824224661a --- /dev/null +++ b/ld/testsuite/ld-elf/dl6amain.c @@ -0,0 +1,33 @@ +#include +#include + +int bar = -20; + +int +main (void) +{ + int ret = 0; + void *handle; + void (*fcn) (void); + + handle = dlopen("./tmpdir/libdl6a.so", RTLD_GLOBAL|RTLD_LAZY); + if (!handle) + { + printf("dlopen ./tmpdir/libdl6a.so: %s\n", dlerror ()); + return 1; + } + + fcn = (void (*)(void)) dlsym(handle, "foo"); + if (!fcn) + { + printf("dlsym foo: %s\n", dlerror ()); + ret += 1; + } + else + { + (*fcn) (); + } + + dlclose (handle); + return ret; +} diff --git a/ld/testsuite/ld-elf/dl6b.out b/ld/testsuite/ld-elf/dl6b.out new file mode 100644 index 00000000000..8cc87f50d13 --- /dev/null +++ b/ld/testsuite/ld-elf/dl6b.out @@ -0,0 +1 @@ +bar is in DSO. diff --git a/ld/testsuite/ld-elf/dl6bmain.c b/ld/testsuite/ld-elf/dl6bmain.c new file mode 100644 index 00000000000..df9dbcc3fee --- /dev/null +++ b/ld/testsuite/ld-elf/dl6bmain.c @@ -0,0 +1,33 @@ +#include +#include + +int bar = -20; + +int +main (void) +{ + int ret = 0; + void *handle; + void (*fcn) (void); + + handle = dlopen("./tmpdir/libdl6b.so", RTLD_GLOBAL|RTLD_LAZY); + if (!handle) + { + printf("dlopen ./tmpdir/libdl6b.so: %s\n", dlerror ()); + return 1; + } + + fcn = (void (*)(void)) dlsym(handle, "foo"); + if (!fcn) + { + printf("dlsym foo: %s\n", dlerror ()); + ret += 1; + } + else + { + (*fcn) (); + } + + dlclose (handle); + return ret; +} diff --git a/ld/testsuite/ld-elf/dl6cmain.c b/ld/testsuite/ld-elf/dl6cmain.c new file mode 100644 index 00000000000..f6c285cdf62 --- /dev/null +++ b/ld/testsuite/ld-elf/dl6cmain.c @@ -0,0 +1,33 @@ +#include +#include + +int bar = -20; + +int +main (void) +{ + int ret = 0; + void *handle; + void (*fcn) (void); + + handle = dlopen("./tmpdir/libdl6c.so", RTLD_GLOBAL|RTLD_LAZY); + if (!handle) + { + printf("dlopen ./tmpdir/libdl6c.so: %s\n", dlerror ()); + return 1; + } + + fcn = (void (*)(void)) dlsym(handle, "foo"); + if (!fcn) + { + printf("dlsym foo: %s\n", dlerror ()); + ret += 1; + } + else + { + (*fcn) (); + } + + dlclose (handle); + return ret; +} diff --git a/ld/testsuite/ld-elf/dl6dmain.c b/ld/testsuite/ld-elf/dl6dmain.c new file mode 100644 index 00000000000..2e57eb751e9 --- /dev/null +++ b/ld/testsuite/ld-elf/dl6dmain.c @@ -0,0 +1,33 @@ +#include +#include + +int bar = -20; + +int +main (void) +{ + int ret = 0; + void *handle; + void (*fcn) (void); + + handle = dlopen("./tmpdir/libdl6d.so", RTLD_GLOBAL|RTLD_LAZY); + if (!handle) + { + printf("dlopen ./tmpdir/libdl6d.so: %s\n", dlerror ()); + return 1; + } + + fcn = (void (*)(void)) dlsym(handle, "foo"); + if (!fcn) + { + printf("dlsym foo: %s\n", dlerror ()); + ret += 1; + } + else + { + (*fcn) (); + } + + dlclose (handle); + return ret; +} diff --git a/ld/testsuite/ld-elf/shared.exp b/ld/testsuite/ld-elf/shared.exp index a6f97092a46..19c22a90ea9 100644 --- a/ld/testsuite/ld-elf/shared.exp +++ b/ld/testsuite/ld-elf/shared.exp @@ -78,21 +78,39 @@ set build_tests { {"Build libdl2b.so with --dynamic-list=dl2.list and dl2xxx.list" "-shared -Wl,--dynamic-list=dl2.list,--dynamic-list=dl2xxx.list" "-fPIC" {dl2.c dl2xxx.c} {} "libdl2b.so"} - {"Build libdl2b.so with --dynamic-list-data and dl2xxx.list" + {"Build libdl2c.so with --dynamic-list-data and dl2xxx.list" "-shared -Wl,--dynamic-list-data,--dynamic-list=dl2xxx.list" "-fPIC" - {dl2.c dl2xxx.c} {} "libdl2b.so"} + {dl2.c dl2xxx.c} {} "libdl2c.so"} {"Build libdl4a.so with --dynamic-list=dl4.list" "-shared -Wl,--dynamic-list=dl4.list" "-fPIC" {dl4.c dl4xxx.c} {} "libdl4a.so"} - {"Build libdl4a.so with --dynamic-list-data" + {"Build libdl4b.so with --dynamic-list-data" "-shared -Wl,--dynamic-list-data" "-fPIC" - {dl4.c dl4xxx.c} {} "libdl4a.so"} - {"Build libdl4b.so with --dynamic-list=dl4.list and dl4xxx.list" - "-shared -Wl,--dynamic-list=dl4.list,--dynamic-list=dl4xxx.list" "-fPIC" {dl4.c dl4xxx.c} {} "libdl4b.so"} - {"Build libdl4b.so with --dynamic-list-data and dl4xxx.list" + {"Build libdl4c.so with --dynamic-list=dl4.list and dl4xxx.list" + "-shared -Wl,--dynamic-list=dl4.list,--dynamic-list=dl4xxx.list" "-fPIC" + {dl4.c dl4xxx.c} {} "libdl4c.so"} + {"Build libdl4d.so with --dynamic-list-data and dl4xxx.list" "-shared -Wl,--dynamic-list-data,--dynamic-list=dl4xxx.list" "-fPIC" - {dl4.c dl4xxx.c} {} "libdl4b.so"} + {dl4.c dl4xxx.c} {} "libdl4d.so"} + {"Build libdl4e.so with -Bsymbolic-functions --dynamic-list-cpp-new" + "-shared -Wl,-Bsymbolic-functions,--dynamic-list-cpp-new" "-fPIC" + {dl4.c dl4xxx.c} {} "libdl4e.so"} + {"Build libdl4f.so with --dynamic-list-cpp-new -Bsymbolic-functions" + "-shared -Wl,--dynamic-list-cpp-new,-Bsymbolic-functions" "-fPIC" + {dl4.c dl4xxx.c} {} "libdl4f.so"} + {"Build libdl6a.so" + "-shared" "-fPIC" + {dl6.c} {} "libdl6a.so"} + {"Build libdl6b.so with -Bsymbolic --dynamic-list-data" + "-shared -Wl,-Bsymbolic,--dynamic-list-data" "-fPIC" + {dl6.c} {} "libdl6b.so"} + {"Build libdl6c.so with -Bsymbolic" + "-shared -Wl,-Bsymbolic" "-fPIC" + {dl6.c} {} "libdl6c.so"} + {"Build libdl6d.so with --dynamic-list-data -Bsymbolic" + "-shared -Wl,--dynamic-list-data,-Bsymbolic" "-fPIC" + {dl6.c} {} "libdl6d.so"} } set run_tests { @@ -132,24 +150,72 @@ set run_tests { {"Run hidden libbar.so with versioned libfoo.so" "tmpdir/libbarhfoov.so tmpdir/libfoov.so" "" {main.c} "hidden" "hidden.out"} - {"Run dl1 with --dynamic-list=dl1.list and dlopen on libdl1.so" + {"Run dl1a with --dynamic-list=dl1.list and dlopen on libdl1.so" "--dynamic-list=dl1.list -ldl" "" - {dl1main.c} "dl1" "dl1.out"} - {"Run dl1 with --dynamic-list-data and dlopen on libdl1.so" + {dl1main.c} "dl1a" "dl1.out"} + {"Run dl1b with --dynamic-list-data and dlopen on libdl1.so" "--dynamic-list-data -ldl" "" - {dl1main.c} "dl1" "dl1.out"} + {dl1main.c} "dl1b" "dl1.out"} {"Run with libdl2a.so" "tmpdir/libdl2a.so" "" {dl2main.c} "dl2a" "dl2a.out"} {"Run with libdl2b.so" "tmpdir/libdl2b.so" "" {dl2main.c} "dl2b" "dl2b.out"} + {"Run with libdl2c.so" + "tmpdir/libdl2c.so" "" + {dl2main.c} "dl2c" "dl2b.out"} {"Run with libdl4a.so" "tmpdir/libdl4a.so" "" {dl4main.c} "dl4a" "dl4a.out"} {"Run with libdl4b.so" "tmpdir/libdl4b.so" "" - {dl4main.c} "dl4b" "dl4b.out"} + {dl4main.c} "dl4b" "dl4a.out"} + {"Run with libdl4c.so" + "tmpdir/libdl4c.so" "" + {dl4main.c} "dl4c" "dl4b.out"} + {"Run with libdl4d.so" + "tmpdir/libdl4d.so" "" + {dl4main.c} "dl4d" "dl4b.out"} + {"Run with libdl4e.so" + "tmpdir/libdl4e.so" "" + {dl4main.c} "dl4e" "dl4a.out"} + {"Run with libdl4f.so" + "tmpdir/libdl4f.so" "" + {dl4main.c} "dl4f" "dl4a.out"} + {"Run dl6a1 with --dynamic-list-data and dlopen on libdl6a.so" + "--dynamic-list-data -ldl" "" + {dl6amain.c} "dl6a1" "dl6a.out"} + {"Run dl6a2 with -Bsymbolic-functions and dlopen on libdl6a.so" + "-Bsymbolic-functions -ldl" "" + {dl6amain.c} "dl6a2" "dl6b.out"} + {"Run dl6a3 with -Bsymbolic and dlopen on libdl6a.so" + "-Bsymbolic -ldl" "" + {dl6amain.c} "dl6a3" "dl6b.out"} + {"Run dl6a4 with -Bsymbolic --dynamic-list-data and dlopen on libdl6a.so" + "-Bsymbolic --dynamic-list-data -ldl" "" + {dl6amain.c} "dl6a4" "dl6a.out"} + {"Run dl6a5 with -Bsymbolic-functions --dynamic-list-cpp-new and dlopen on libdl6a.so" + "-Bsymbolic-functions --dynamic-list-cpp-new -ldl" "" + {dl6amain.c} "dl6a5" "dl6b.out"} + {"Run dl6a6 with --dynamic-list-cpp-new -Bsymbolic-functions and dlopen on libdl6a.so" + "--dynamic-list-cpp-new -Bsymbolic-functions -ldl" "" + {dl6amain.c} "dl6a6" "dl6b.out"} + {"Run dl6a7 with --dynamic-list-data -Bsymbolic and dlopen on libdl6a.so" + "--dynamic-list-data -Bsymbolic -ldl" "" + {dl6amain.c} "dl6a7" "dl6a.out"} + {"Run dl6b1 with --dynamic-list-data and dlopen on libdl6b.so" + "--dynamic-list-data -ldl" "" + {dl6bmain.c} "dl6b1" "dl6a.out"} + {"Run dl6b2 with dlopen on libdl6b.so" + "-ldl" "" + {dl6bmain.c} "dl6b2" "dl6b.out"} + {"Run dl6c1 with --dynamic-list-data and dlopen on libdl6c.so" + "--dynamic-list-data -ldl" "" + {dl6cmain.c} "dl6c1" "dl6b.out"} + {"Run dl6d1 with --dynamic-list-data and dlopen on libdl6d.so" + "--dynamic-list-data -ldl" "" + {dl6dmain.c} "dl6d1" "dl6b.out"} } run_cc_link_tests $build_tests @@ -171,9 +237,12 @@ set build_cxx_tests { {"Build libdl3a.so with --dynamic-list-cpp-typeinfo" "-shared -Wl,--dynamic-list-cpp-typeinfo" "-fPIC" {dl3.cc} {} "libdl3c.so" "c++"} - {"Build libdnew.so with -Bsymbolic-functions -dynamic-list-cpp-new" + {"Build libdnew1a.so with --Bsymbolic-functions --dynamic-list-cpp-new" "-shared -Wl,-Bsymbolic-functions,--dynamic-list-cpp-new" "-fPIC" - {del.cc new.cc} {} "libnew.so" "c++"} + {del.cc new.cc} {} "libnew1a.so" "c++"} + {"Build libdnew1b.so with --dynamic-list-data --dynamic-list-cpp-new" + "-shared -Wl,--dynamic-list-data,--dynamic-list-cpp-new" "-fPIC" + {del.cc new.cc} {} "libnew1b.so" "c++"} } set run_cxx_tests { @@ -186,9 +255,12 @@ set run_cxx_tests { {"Run with libdl3c.so" "tmpdir/libdl3c.so" "" {dl3main.cc} "dl3c" "dl3a.out" "" "c++"} - {"Run with libnew.so" - "tmpdir/libnew.so" "" - {dl5.cc} "dl5" "dl5.out" "" "c++"} + {"Run with libnew1a.so" + "tmpdir/libnew1a.so" "" + {dl5.cc} "dl5a" "dl5.out" "" "c++"} + {"Run with libnew1b.so" + "tmpdir/libnew1b.so" "" + {dl5.cc} "dl5b" "dl5.out" "" "c++"} } run_cc_link_tests $build_cxx_tests