|go text: || - index - problems - systems - libraries - [ converting ] - programming - old library - new library - links -
||topics: || - old non-off_t code - going largefile - longlong default - face dualmode - [ make twinlibs ] - and defend - converting to twinlibs

Step 5: converting to two libs being twins

Often is not needed to create a dualmode library that can serve both third party usage as providing both a largefile API and a non-largefile API as cousin entries in a single binary. That is just making it easier for third party libs since they can just deploy AC_SYS_LARGEFILE and that's it, the rest is pure magic of a 64on32 unix98-compatible system.

Instead one can create two libraries which each provide a single API but one time it is compiled as largefile and the other time it is compiled as non-largefile. Both export the same symbol names but they expect to be called one time with a 64bit off_t and the other time with a 32bit off_t. Well, the difference hits only those call entries that actually use off_t on the source level.

In other words, you retain binary compatibility under the old name of the library but you offer a second variant that is resistant to largefile usage. The interesting point: after having completed Step-1 with providing your library sources as off_t-clean this is just easy, simply detect the case of a target system being LARGEFILE_SENSITIVE and compile the portable sources twice, linking them to two twinlibs where the largefile one gets a slightly different name - by tradition a *64 gets appended to the basename.

Now it is the task of the third party application / library to decide which library to link with, i.e. to LDADD=-lz or to use LDADD=-lz64 instead. It is quite advisable to help him with instructions and possibly an autoconf macro or gnumake macro that does the selection automatically. But actually, that's not your piece of cake, for an opensource developer there is another incentive: if you develop on linux/solaris most of the time then compiling twinlibs will ensure your sources are off_t-clean and readily portable and largefile resistant.

Actually, if you grep through the autoconf and libtool mailinglists you will find numerous instances where people wanted to `configure once` and compile both sharedlibs (lib and lib64) just easily (with AIX making a good candidate AFAICS). Sadly that is not achivable that easily. Personally, I've done the trick to add code after AC_OUTPUT that (conditionally on 64on32) copies the src/* subtree (which already configured!) to a new src64/*, implant the necessary largefile -D_defs, add the install-modifier, and add it to the toplevel SUBDIRS. There are other ways however, an easy way would be to just don't do it, and instead use an rpm .spec file that does the subtree copy and that also calls `make` a secod time on the src64* with the necessary -D_defs, so you don't need to "implant" anything.

One can't say anything else than: this is easy. But It just also means that you do not only have two compiled functions per each off_t-sensitive function but you do now have two compiled libraries with all functions existing twice even that they have the exact same binary code. With large disks today it is not much a problem, it's more interesting if some third party round goes to mix library and application parts where some parts link with the largefile variant and the other with the non-largefile variant of your library. In some cases there might be subtle problems with this but I've not heard of anything of a real problem - and even if it would then it just makes a good push to move some other parts to use the largefile variant as well.