Date: Wed, 3 Nov 2010 15:20:06 GMT From: Kostik Belousov <kostikbel@gmail.com> To: freebsd-bugs@FreeBSD.org Subject: Re: misc/151861: dlclose() of library causes separately opened libraries to unload as well Message-ID: <201011031520.oA3FK6wP036589@freefall.freebsd.org>
next in thread | raw e-mail | index | archive | help
The following reply was made to PR misc/151861; it has been noted by GNATS. From: Kostik Belousov <kostikbel@gmail.com> To: Jaakko Heinonen <jh@freebsd.org> Cc: Arjan van Leeuwen <freebsd-maintainer@opera.com>, bug-followup@freebsd.org, kan@freebsd.org Subject: Re: misc/151861: dlclose() of library causes separately opened libraries to unload as well Date: Wed, 3 Nov 2010 17:14:08 +0200 --MqBZZc8f0rLWAE1Q Content-Type: text/plain; charset=us-ascii Content-Disposition: inline Content-Transfer-Encoding: quoted-printable On Wed, Nov 03, 2010 at 05:02:24PM +0200, Jaakko Heinonen wrote: > On 2010-11-03, Kostik Belousov wrote: > > > Why init_dag() should be allowed to be called multiple times for an > > > object? > >=20 > > If already loaded object is dlopened, dlclosed, and then again dlopened, > > init_dag() will be called twice, one time for each dlopen. >=20 > If the object gets unloaded after dlclose(), this will not happen? I am > not sure if I like that it can be called multiple times. Yes, for the case when dlclose() removes the last reference, the object is unloaded. But, if the object was loaded as dependency that is still valid, it will not. Assume that main executable is linked against b.so, and then dlopen("b.so"); dlclose("b.so"); dlopen("b.so"); is called. >=20 > > --- a/libexec/rtld-elf/rtld.c > > +++ b/libexec/rtld-elf/rtld.c > > @@ -1275,11 +1275,12 @@ init_dag(Obj_Entry *root) > > { > > DoneList donelist; > > =20 > > - if (root->dag_inited) > > - return; > > - donelist_init(&donelist); > > - init_dag1(root, root, &donelist); > > - root->dag_inited =3D true; > > + if (!root->dag_inited) { > > + donelist_init(&donelist); > > + init_dag1(root, root, &donelist); > > + root->dag_inited =3D true; > > + } > > + ref_dag(root); > > } >=20 > If you are going to take this approach, why not remove init_dag() altoget= her > and make ref_dag() to initialize the dag when necessary? I like the explicit notion that ref_dag() does not initialize the DAG. We may add some assertion about state of the DAG there. I tried reverse change, always using init_dag(), there is only one place after the patch where ref_dag() is called, but init_dag() is not. The reason why I decided to call both is the same. --MqBZZc8f0rLWAE1Q Content-Type: application/pgp-signature Content-Disposition: inline -----BEGIN PGP SIGNATURE----- Version: GnuPG v1.4.11 (FreeBSD) iEYEARECAAYFAkzRfD8ACgkQC3+MBN1Mb4gbBgCdEp5jauPSC6s1bxijJABcTqdw Z/gAoI0cA6Xe5pL2K6NCXW82mMzAzSSI =xwJx -----END PGP SIGNATURE----- --MqBZZc8f0rLWAE1Q--
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201011031520.oA3FK6wP036589>