From 4d07e5521ea811278f00f434fe2b8345ea1d8832 Mon Sep 17 00:00:00 2001 From: Rich Felker Date: Wed, 23 Jan 2013 22:07:45 -0500 Subject: [PATCH] add support for RTLD_NOLOAD to dlopen based on patch by Pierre Carrier that just added the flag constant, but with minimal additional code so that it actually works as documented. this is a nonstandard option but some major software (reportedly, Firefox) uses it and it was easy to add anyway. --- include/dlfcn.h | 1 + src/ldso/dynlink.c | 10 +++++++--- 2 files changed, 8 insertions(+), 3 deletions(-) diff --git a/include/dlfcn.h b/include/dlfcn.h index 46c4e185..5b57e8ac 100644 --- a/include/dlfcn.h +++ b/include/dlfcn.h @@ -9,6 +9,7 @@ extern "C" { #define RTLD_LAZY 1 #define RTLD_NOW 2 +#define RTLD_NOLOAD 4 #define RTLD_GLOBAL 256 #define RTLD_LOCAL 0 diff --git a/src/ldso/dynlink.c b/src/ldso/dynlink.c index e73806cd..b1a4409d 100644 --- a/src/ldso/dynlink.c +++ b/src/ldso/dynlink.c @@ -99,6 +99,7 @@ static int ssp_used; static int runtime; static int ldd_mode; static int ldso_fail; +static int noload; static jmp_buf rtld_fail; static pthread_rwlock_t lock; static struct debug debug; @@ -508,7 +509,7 @@ static struct dso *load_library(const char *name) return p; } } - map = map_library(fd, &temp_dso); + map = noload ? 0 : map_library(fd, &temp_dso); close(fd); if (!map) return 0; @@ -1027,6 +1028,7 @@ void *dlopen(const char *file, int mode) orig_tls_offset = tls_offset; orig_tls_align = tls_align; orig_tail = tail; + noload = mode & RTLD_NOLOAD; if (setjmp(rtld_fail)) { /* Clean up anything new that was (partially) loaded */ @@ -1050,8 +1052,10 @@ void *dlopen(const char *file, int mode) } else p = load_library(file); if (!p) { - snprintf(errbuf, sizeof errbuf, - "Error loading shared library %s: %m", file); + snprintf(errbuf, sizeof errbuf, noload ? + "Library %s is not already loaded" : + "Error loading shared library %s: %m", + file); errflag = 1; goto end; } -- 2.25.1