misc/151861: dlclose() of library causes separately opened libraries to unload as well

Kostik Belousov kostikbel at gmail.com
Wed Nov 3 15:20:07 UTC 2010


The following reply was made to PR misc/151861; it has been noted by GNATS.

From: Kostik Belousov <kostikbel at gmail.com>
To: Jaakko Heinonen <jh at freebsd.org>
Cc: Arjan van Leeuwen <freebsd-maintainer at opera.com>, bug-followup at freebsd.org,
        kan at 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--


More information about the freebsd-bugs mailing list