This issue tracker has been migrated to GitHub, and is currently read-only.
For more information, see the GitHub FAQs in the Python's Developer Guide.

Author haubi
Recipients Michael.Felt, aixtools@gmail.com, haubi, martin.panter
Date 2017-01-31.19:22:57
SpamBayes Score -1.0
Marked as misclassified Yes
Message-id <1485890577.64.0.440553958792.issue27435@psf.upfronthosting.co.za>
In-reply-to
Content
Feels like it is up to me to shed some light on various topics here:

AIX defines (static) "Object" files and "Shared Object" files. Both can (but do not need to) be members of an "Archive Library".

When talking about (dynamically loading) a "shared library" on non-AIX systems, the correct wording for AIX is (dynamically loading) a "Shared Object" - independent of whether it is a standalone file or an archive member.

As you already agreed on, ctypes.util.find_library() indeed should return the location of the Shared Object - as either "/path/to/file" or "/path/to/file(member)". And ctypes.CDLL() should add the RTLD_MEMBER flag to _ctypes.dlopen() if there is the "(member)" part.

However, that does not necessarily mean the RTLD_MEMBER value needs to be available through the ctypes API. Instead, RTLD_MEMBER feels more appropriate for the _ctypes API - and on AIX only.

Anyway:
Unfortunately, there is no concept of embedding something like ELF's DT_SONAME tag into the Shared Object. The very (PATH,BASE,MEMBER) value as (specified to and) discovered by the linker is recorded into the just-linked executable (or Shared Object). This implies that the runtime loader does search for the very same filename (and member eventually) as the linker (at linktime).

However, to still get some kind of shared library versioning, multiple versions of one Shared Object are put into one single Archive Library, where the "old" versions get the LOADONLY flag set (via 'strip -e') - so executables linked against an old version still can load their "old" Shared Object, while the linker discovers the "current" version only.

But this "single-filename" based shared library versioning is a huge burden for packages managers - either human or software, even when they maintain their packages in a private prefix (like /opt/freeware, /usr/local and similar). Neither can they put their "current" Shared Object's version into the single (system's) Archive Library, nor can they mark existing Shared Objects as LOADONLY.
On the other hand, they also do not want to pull all the system versions into their own Archive Library.

So for package managers it is crucial to have "multi-filename" based shared library versioning instead.

But there is help:
AIX also provides (plain text) "Import Files": They contain a list of symbols for the linker, and a (PATH,BASE,MEMBER) tuple naming the Shared Object that provides these symbols at runtime.

So yes, Import Files can be used for "multi-filename" based shared library versioning.

Thus, libtool now offers the "--with-aix-soname=svr4" configure flag, where "libNAME.so.X" really is created as an Archive Library, containing the Shared Object "shr.o" with the LOADONLY flag set, and the Import File "shr.imp" referring to "libNAME.so.X(shr.o)" for runtime. Combined with the symlink "libNAME.so", for the "-lNAME" argument the linker discovers the Import File "libNAME.so(shr.imp)" now, while recording "libNAME.so.X(shr.o)" into the executable for the runtime loader.
Note that for 64bit the Shared Object and Import File is named "shr_64.o" and "shr_64.imp", respectively.

While libtool's "--with-aix-soname=svr4" variant creates "libNAME.a" from static Objects only, both libtool's "--with-aix-soname=aix" and "--with-aix-soname=both" - for backwards compatibility - create "libNAME.a" for traditional "single-filename" based versioning: Without any static Object - as even Shared Objects can be linked statically(!). But to statically link the Shared Object (as an archive member), neither the LOADONLY flag must be set, nor an Import File must be found (as Import Files cannot serve for static linking).

And "--with-aix-soname=aix", libtool still creates standalone "libNAME.so.X.Y.Z" along the (versioning-wise useless) symlinks.

So it is up to the package manager which "aix-soname" variant to choose within its prefix: For example, in Gentoo Prefix I'm using "--with-aix-soname=svr4" only.

But still, how to get ctypes.find_library() working - ideally for each variant, is another story. Right now it does not work for any variant, but I guess that search algorithm should follow how the linker discovers the (PATH,BASE,MEMBER) values to write into just-linked executables, combined with how the runtime loader finds the Shared Object to actually load.
History
Date User Action Args
2017-01-31 19:22:57haubisetrecipients: + haubi, martin.panter, Michael.Felt, aixtools@gmail.com
2017-01-31 19:22:57haubisetmessageid: <1485890577.64.0.440553958792.issue27435@psf.upfronthosting.co.za>
2017-01-31 19:22:57haubilinkissue27435 messages
2017-01-31 19:22:57haubicreate