This is the mail archive of the libc-alpha@sourceware.org mailing list for the glibc project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

Re: [PATCH] ld.so: command argument "--preload"


On 6/11/18 11:14 pm, Florian Weimer wrote:
Don't forget to verify that the test works even if you configure glibc
with --enable-hardcoded-path-in-tests.  If not, we can disable the test
in this case.

I've done all that.

Here's a patch that adds --preload to rtld, and  includes a test that works with or without --enable-hardcoded-path-in-tests.

By the way, is this a list which permits MIME attachments?

----8<--------8<--------8<--------8<--------8<--------8<--------8<--------8<--
diff --git a/elf/Makefile b/elf/Makefile
index d72e7b6..901e188 100644
--- a/elf/Makefile
+++ b/elf/Makefile
@@ -353,7 +353,8 @@ endif
ifeq (yes,$(build-shared))
 ifeq ($(run-built-tests),yes)
-tests-special += $(objpfx)tst-pathopt.out $(objpfx)tst-rtld-load-self.out
+tests-special += $(objpfx)tst-pathopt.out $(objpfx)tst-rtld-load-self.out \
+		 $(objpfx)tst-rtld-preload.out
 endif
 tests-special += $(objpfx)check-textrel.out $(objpfx)check-execstack.out \
 		 $(objpfx)check-localplt.out $(objpfx)check-initfini.out
@@ -882,6 +883,13 @@ $(objpfx)tst-rtld-load-self.out: tst-rtld-load-self.sh $(objpfx)ld.so
 	$(SHELL) $^ '$(test-wrapper)' '$(test-wrapper-env)' > $@; \
 	$(evaluate-test)
+tst-rtld-preload-OBJS = $(subst $(empty) ,:,$(strip $(preloadtest-preloads:=.so)))
+$(objpfx)tst-rtld-preload.out: tst-rtld-preload.sh $(objpfx)ld.so \
+			       $(objpfx)preloadtest
+	$(SHELL) $^ '$(test-wrapper)' '$(test-wrapper-env)' '$(run_program_env)' \
+		    '$(rpath-link)' '$(tst-rtld-preload-OBJS)' > $@; \
+ 	$(evaluate-test)
+
 $(objpfx)initfirst: $(libdl)
 $(objpfx)initfirst.out: $(objpfx)firstobj.so
diff --git a/elf/rtld.c b/elf/rtld.c
index 1b0c747..f046f6e 100644
--- a/elf/rtld.c
+++ b/elf/rtld.c
@@ -826,6 +826,8 @@ static const char *library_path attribute_relro;
 static const char *preloadlist attribute_relro;
 /* Nonzero if information about versions has to be printed.  */
 static int version_info attribute_relro;
+/* The preload list passed as a command argument. */
+static const char *preloadarg attribute_relro;
/* The LD_PRELOAD environment variable gives list of libraries
    separated by white space or colons that are loaded before the
@@ -833,8 +835,9 @@ static int version_info attribute_relro;
    (If the binary is running setuid all elements containing a '/' are
    ignored since it is insecure.)  Return the number of preloads
    performed.  */
+/* Ditto for --preload command argument */
 unsigned int
-handle_ld_preload (const char *preloadlist, struct link_map *main_map)
+handle_preload_list (const char *preloadlist, struct link_map *main_map, const char *where)
 {
   unsigned int npreloads = 0;
   const char *p = preloadlist;
@@ -858,7 +861,7 @@ handle_ld_preload (const char *preloadlist, struct link_map *main_map)
 	++p;
if (dso_name_valid_for_suid (fname))
-	npreloads += do_preload (fname, main_map, "LD_PRELOAD");
+	npreloads += do_preload (fname, main_map, where);
     }
   return npreloads;
 }
@@ -978,6 +981,13 @@ dl_main (const ElfW(Phdr) *phdr,
 	    _dl_argc -= 2;
 	    _dl_argv += 2;
 	  }
+	else if (! strcmp(_dl_argv[1], "--preload") && _dl_argc > 2)
+	  {
+	    preloadarg = _dl_argv[2];
+	    _dl_skip_args += 2;
+	    _dl_argc -= 2;
+	    _dl_argv += 2;
+	  }
 	else
 	  break;
@@ -1006,7 +1016,8 @@ of this helper program; chances are you did not intend to run this program.\n\
 			variable LD_LIBRARY_PATH\n\
   --inhibit-rpath LIST  ignore RUNPATH and RPATH information in object names\n\
 			in LIST\n\
-  --audit LIST          use objects named in LIST as auditors\n");
+  --audit LIST          use objects named in LIST as auditors\n\
+  --preload LIST        preload objects named in LIST\n");
++_dl_skip_args;
       --_dl_argc;
@@ -1620,7 +1631,16 @@ ERROR: ld.so: object '%s' cannot be loaded as audit interface: %s; ignored.\n",
   if (__glibc_unlikely (preloadlist != NULL))
     {
       HP_TIMING_NOW (start);
-      npreloads += handle_ld_preload (preloadlist, main_map);
+      npreloads += handle_preload_list (preloadlist, main_map, "LD_PRELOAD");
+      HP_TIMING_NOW (stop);
+      HP_TIMING_DIFF (diff, start, stop);
+      HP_TIMING_ACCUM_NT (load_time, diff);
+    }
+
+  if (__glibc_unlikely (preloadarg != NULL))
+    {
+      HP_TIMING_NOW (start);
+      npreloads += handle_preload_list (preloadarg, main_map, "--preload");
       HP_TIMING_NOW (stop);
       HP_TIMING_DIFF (diff, start, stop);
       HP_TIMING_ACCUM_NT (load_time, diff);
diff --git a/elf/tst-rtld-preload.sh b/elf/tst-rtld-preload.sh
new file mode 100755
index 0000000..4a6a58d
--- /dev/null
+++ b/elf/tst-rtld-preload.sh
@@ -0,0 +1,37 @@
+#!/bin/sh
+# Test how rtld loads itself.
+# Copyright (C) 2012-2016 Free Software Foundation, Inc.
+# This file is part of the GNU C Library.
+#
+
+# The GNU C Library is free software; you can redistribute it and/or
+# modify it under the terms of the GNU Lesser General Public
+# License as published by the Free Software Foundation; either
+# version 2.1 of the License, or (at your option) any later version.
+
+# The GNU C Library is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+# Lesser General Public License for more details.
+
+# You should have received a copy of the GNU Lesser General Public
+# License along with the GNU C Library; if not, see
+#. + +set -e + +rtld=$1 +test_program=$2 +test_wrapper=$3 +test_wrapper_env=$4 +run_program_env=$5 +library_path=$6 +preload=$7 + +echo "# [${test_wrapper}] [$rtld] [--library-path] [$library_path] [--preload] [$preload] [$test_program]" +${test_wrapper_env} \ +${run_program_env} \ +${test_wrapper} $rtld --library-path $library_path --preload $preload $test_program 2>&1 && rc=0 || rc=$? +echo "# exit status $rc" + +exit $rc


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]