* [PATCH] Allow __libc_dlopen from libraries __libc_dlopen'ed by statically linked executables
@ 2003-06-11 20:32 Jakub Jelinek
2003-06-25 8:44 ` Ulrich Drepper
0 siblings, 1 reply; 2+ messages in thread
From: Jakub Jelinek @ 2003-06-11 20:32 UTC (permalink / raw)
To: Ulrich Drepper, Roland McGrath; +Cc: Glibc hackers
Hi!
This patch should make Thorsten's new nss_compat module working even from
statically linked binaries.
It will work only if the binaries are relinked, but I think we should be
clear that there is no guarantee that statically linked binaries using
NSS or iconv will work after glibc upgrade unless they have been
recompiled/relinked with the new glibc.
Tested with a statically linked binary __libc_dlopen'ing shared library
doing getpwnam.
The impact on libc.so.6 shouldn't be big, basically one more exported
symbol, __WORDSIZE bytes in .bss section and in 3 different functions
memory load + compare + jump to short unlikely code.
2003-06-11 Jakub Jelinek <jakub@redhat.com>
* elf/Versions (libc): Add _dl_open_hook@GLIBC_PRIVATE.
* elf/dl-libc.c (struct dl_open_hook): New.
(_dl_open_hook): New variable.
(do_dlsym_private): New function.
(__libc_dlopen_mode) [!SHARED]: Lookup _dl_open_hook@GLIBC_PRIVATE
and initialize it if found.
(__libc_dlopen_mode) [SHARED]: If _dl_open_hook is non-NULL,
call dlopen_mode hook.
(__libc_dlsym) [SHARED]: If _dl_open_hook is non-NULL,
call dlsym hook.
(__libc_dlclose) [SHARED]: If _dl_open_hook is non-NULL,
call dlclose hook.
--- libc/elf/Versions.jj 2003-03-20 05:58:48.000000000 -0500
+++ libc/elf/Versions 2003-06-11 10:57:15.000000000 -0400
@@ -21,6 +21,7 @@ libc {
# functions used in other libraries
_dl_open; _dl_close; _dl_addr;
_dl_sym; _dl_vsym;
+ _dl_open_hook;
}
}
--- libc/elf/dl-libc.c.jj 2002-11-24 19:57:43.000000000 -0500
+++ libc/elf/dl-libc.c 2003-06-11 11:53:10.000000000 -0400
@@ -96,6 +96,50 @@ do_dlclose (void *ptr)
_dl_close ((struct link_map *) ptr);
}
+/* This code is to support __libc_dlopen from __libc_dlopen'ed shared
+ libraries. We need to ensure the statically linked __libc_dlopen
+ etc. functions are used instead of the dynamically loaded. */
+struct dl_open_hook
+{
+ void *(*dlopen_mode) (const char *name, int mode);
+ void *(*dlsym) (void *map, const char *name);
+ int (*dlclose) (void *map);
+};
+
+#ifdef SHARED
+extern struct dl_open_hook *_dl_open_hook;
+libc_hidden_proto (_dl_open_hook);
+struct dl_open_hook *_dl_open_hook __attribute__((nocommon));
+libc_hidden_data_def (_dl_open_hook);
+#else
+static void
+do_dlsym_private (void *ptr)
+{
+ lookup_t l;
+ struct r_found_version vers;
+ vers.name = "GLIBC_PRIVATE";
+ vers.hidden = 1;
+ /* vers.hash = _dl_elf_hash (version); */
+ vers.hash = 0x0963cf85;
+ /* FIXME: Shouldn't we use libc.so.6* here? */
+ vers.filename = NULL;
+
+ struct do_dlsym_args *args = (struct do_dlsym_args *) ptr;
+ args->ref = NULL;
+ l = _dl_lookup_versioned_symbol (args->name, args->map,
+ &args->ref, args->map->l_scope,
+ &vers, 0, 0);
+ args->loadbase = l;
+}
+
+static struct dl_open_hook _dl_open_hook =
+ {
+ .dlopen_mode = __libc_dlopen_mode,
+ .dlsym = __libc_dlsym,
+ .dlclose = __libc_dlclose
+ };
+#endif
+
/* ... and these functions call dlerror_run. */
void *
@@ -105,7 +149,29 @@ __libc_dlopen_mode (const char *name, in
args.name = name;
args.mode = mode;
+#ifdef SHARED
+ if (__builtin_expect (_dl_open_hook != NULL, 0))
+ return _dl_open_hook->dlopen_mode (name, mode);
return (dlerror_run (do_dlopen, &args) ? NULL : (void *) args.map);
+#else
+ if (dlerror_run (do_dlopen, &args))
+ return NULL;
+
+ struct do_dlsym_args sargs;
+ sargs.map = args.map;
+ sargs.name = "_dl_open_hook";
+
+ if (! dlerror_run (do_dlsym_private, &sargs))
+ {
+ struct dl_open_hook **hook
+ = (struct dl_open_hook **)
+ (DL_SYMBOL_ADDRESS (sargs.loadbase, sargs.ref));
+ if (hook != NULL)
+ *hook = &_dl_open_hook;
+ }
+
+ return (void *) args.map;
+#endif
}
void *
@@ -115,6 +181,10 @@ __libc_dlsym (void *map, const char *nam
args.map = map;
args.name = name;
+#ifdef SHARED
+ if (__builtin_expect (_dl_open_hook != NULL, 0))
+ return _dl_open_hook->dlsym (map, name);
+#endif
return (dlerror_run (do_dlsym, &args) ? NULL
: (void *) (DL_SYMBOL_ADDRESS (args.loadbase, args.ref)));
}
@@ -122,6 +192,10 @@ __libc_dlsym (void *map, const char *nam
int
__libc_dlclose (void *map)
{
+#ifdef SHARED
+ if (__builtin_expect (_dl_open_hook != NULL, 0))
+ return _dl_open_hook->dlclose (map);
+#endif
return dlerror_run (do_dlclose, map);
}
Jakub
^ permalink raw reply [flat|nested] 2+ messages in thread
* Re: [PATCH] Allow __libc_dlopen from libraries __libc_dlopen'ed by statically linked executables
2003-06-11 20:32 [PATCH] Allow __libc_dlopen from libraries __libc_dlopen'ed by statically linked executables Jakub Jelinek
@ 2003-06-25 8:44 ` Ulrich Drepper
0 siblings, 0 replies; 2+ messages in thread
From: Ulrich Drepper @ 2003-06-25 8:44 UTC (permalink / raw)
To: Jakub Jelinek; +Cc: Glibc hackers
-----BEGIN PGP SIGNED MESSAGE-----
Hash: SHA1
Jakub Jelinek wrote:
> 2003-06-11 Jakub Jelinek <jakub@redhat.com>
>
> * elf/Versions (libc): Add _dl_open_hook@GLIBC_PRIVATE.
> * elf/dl-libc.c (struct dl_open_hook): New.
> (_dl_open_hook): New variable.
> (do_dlsym_private): New function.
> (__libc_dlopen_mode) [!SHARED]: Lookup _dl_open_hook@GLIBC_PRIVATE
> and initialize it if found.
> (__libc_dlopen_mode) [SHARED]: If _dl_open_hook is non-NULL,
> call dlopen_mode hook.
> (__libc_dlsym) [SHARED]: If _dl_open_hook is non-NULL,
> call dlsym hook.
> (__libc_dlclose) [SHARED]: If _dl_open_hook is non-NULL,
> call dlclose hook.
I've added the patch now. I would appreciate if this code can be given
some testing. If it works out I'll look at the LDAP changes. Without
this working it's not worth it.
- --
- --------------. ,-. 444 Castro Street
Ulrich Drepper \ ,-----------------' \ Mountain View, CA 94041 USA
Red Hat `--' drepper at redhat.com `---------------------------
-----BEGIN PGP SIGNATURE-----
Version: GnuPG v1.2.1 (GNU/Linux)
iD8DBQE++V4V2ijCOnn/RHQRAoUvAKCcSRL9jlPMn884Qw5Ixe6PlsxX9wCgswSV
KthTFdneJYdb283TCVYQuRA=
=A/O9
-----END PGP SIGNATURE-----
^ permalink raw reply [flat|nested] 2+ messages in thread
end of thread, other threads:[~2003-06-25 8:44 UTC | newest]
Thread overview: 2+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2003-06-11 20:32 [PATCH] Allow __libc_dlopen from libraries __libc_dlopen'ed by statically linked executables Jakub Jelinek
2003-06-25 8:44 ` Ulrich Drepper
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).