diff options
Diffstat (limited to 'elf/dl-open.c')
-rw-r--r-- | elf/dl-open.c | 32 |
1 files changed, 30 insertions, 2 deletions
diff --git a/elf/dl-open.c b/elf/dl-open.c index 8d699d3ff8..533fb96e8f 100644 --- a/elf/dl-open.c +++ b/elf/dl-open.c @@ -177,6 +177,23 @@ _dl_find_dso_for_object (const ElfW(Addr) addr) } rtld_hidden_def (_dl_find_dso_for_object); +/* struct dl_init_args and call_dl_init are used to call _dl_init with + exception handling disabled. */ +struct dl_init_args +{ + struct link_map *new; + int argc; + char **argv; + char **env; +}; + +static void +call_dl_init (void *closure) +{ + struct dl_init_args *args = closure; + _dl_init (args->new, args->argc, args->argv, args->env); +} + static void dl_open_worker (void *a) { @@ -509,8 +526,19 @@ TLS generation counter wrapped! Please report this.")); DL_STATIC_INIT (new); #endif - /* Run the initializer functions of new objects. */ - _dl_init (new, args->argc, args->argv, args->env); + /* Run the initializer functions of new objects. Temporarily + disable the exception handler, so that lazy binding failures are + fatal. */ + { + struct dl_init_args init_args = + { + .new = new, + .argc = args->argc, + .argv = args->argv, + .env = args->env + }; + _dl_catch_exception (NULL, call_dl_init, &init_args); + } /* Now we can make the new map available in the global scope. */ if (mode & RTLD_GLOBAL) |