From owner-freebsd-arch Sat Feb 23 15:22: 0 2002 Delivered-To: freebsd-arch@freebsd.org Received: from flood.ping.uio.no (flood.ping.uio.no [129.240.78.31]) by hub.freebsd.org (Postfix) with ESMTP id C750E37B404; Sat, 23 Feb 2002 15:21:52 -0800 (PST) Received: by flood.ping.uio.no (Postfix, from userid 2602) id 19C545341; Sun, 24 Feb 2002 00:21:50 +0100 (CET) X-URL: http://www.ofug.org/~des/ X-Disclaimer: The views expressed in this message do not necessarily coincide with those of any organisation or company with which I am or have been affiliated. To: arch@freebsd.org Subject: bin/25059 (rtld bug) From: Dag-Erling Smorgrav Date: 24 Feb 2002 00:21:49 +0100 Message-ID: Lines: 24 User-Agent: Gnus/5.0808 (Gnus v5.8.8) Emacs/21.1 MIME-Version: 1.0 Content-Type: multipart/mixed; boundary="=-=-=" Sender: owner-freebsd-arch@FreeBSD.ORG Precedence: bulk List-ID: List-Archive: (Web Archive) List-Help: (List Instructions) List-Subscribe: List-Unsubscribe: X-Loop: FreeBSD.ORG --=-=-= Our dlopen(3) man page states: RTLD_GLOBAL Symbols from this shared object and its directed acyclic graph (DAG) of needed objects will be available for resolv ing undefined references from all other shared objects. but this is a lie - only the object itself is searched, not its DAG. The attached patch fixes this by adding a flag to the Obj_Entry structure that marks an object as global, and changing symlook_list() to search each global object's DAG if the object itself doesn't have the requested symbol. With this patch applied, the test program referenced in the PR works. (some might argue that symlook_obj() should be changed instead - but changing symlook_list() was simpler, and the only difference it makes is, in the worst case, a slightly longer search) DES -- Dag-Erling Smorgrav - des@ofug.org --=-=-= Content-Type: text/x-patch Content-Disposition: attachment; filename=rtld.diff Index: rtld.c =================================================================== RCS file: /home/ncvs/src/libexec/rtld-elf/rtld.c,v retrieving revision 1.60 diff -u -r1.60 rtld.c --- rtld.c 17 Feb 2002 07:00:25 -0000 1.60 +++ rtld.c 23 Feb 2002 23:21:28 -0000 @@ -1329,6 +1329,7 @@ elm = NEW(Objlist_Entry); elm->obj = obj; STAILQ_INSERT_TAIL(list, elm, link); + obj->global = true; } static void @@ -1581,7 +1582,7 @@ if (obj) { obj->dl_refcount++; - if (mode & RTLD_GLOBAL && objlist_find(&list_global, obj) == NULL) + if (mode & RTLD_GLOBAL && !obj->global) objlist_push_tail(&list_global, obj); mode &= RTLD_MODEMASK; if (*old_obj_tail != NULL) { /* We loaded something new. */ @@ -1915,7 +1916,7 @@ } } - /* Search all RTLD_GLOBAL objects. */ + /* Search all RTLD_GLOBAL objects and their DAGs. */ if (def == NULL || ELF_ST_BIND(def->st_info) == STB_WEAK) { symp = symlook_list(name, hash, &list_global, &obj, in_plt, &donelist); if (symp != NULL && @@ -1965,6 +1966,12 @@ if (ELF_ST_BIND(def->st_info) != STB_WEAK) break; } + } else if (elm->obj->global) { + /* search the DAGs of global objects */ + symp = symlook_list(name, hash, &elm->obj->dagmembers, + defobj_out, in_plt, dlp); + if (symp != NULL) + return symp; } } if (def != NULL) Index: rtld.h =================================================================== RCS file: /home/ncvs/src/libexec/rtld-elf/rtld.h,v retrieving revision 1.24 diff -u -r1.24 rtld.h --- rtld.h 29 Oct 2001 10:10:02 -0000 1.24 +++ rtld.h 23 Feb 2002 23:02:18 -0000 @@ -155,6 +155,7 @@ bool traced; /* Already printed in ldd trace output */ bool jmpslots_done; /* Already have relocated the jump slots */ bool init_done; /* Already have added object to init list */ + bool global; /* This object is on the global list */ struct link_map linkmap; /* for GDB */ Objlist dldags; /* Object belongs to these dlopened DAGs (%) */ --=-=-=-- To Unsubscribe: send mail to majordomo@FreeBSD.org with "unsubscribe freebsd-arch" in the body of the message