I have some changes to libstore that I've been noodling with off and on for a while. Since this stuff definitely needs more polishing, and has had no testing whatsoever (I presume it doesn't work), and because I haven't consulted anybody else about the changes beforehand, I've checked this stuff in on a branch for now. To get this code, go into your hurd checkout in the libstore subdirectory and do "cvs up -r roland_libstore_modules_branch". The branch exists only in the libstore subdir, so don't try the -r elsewhere.
I have gotten rid of the `store_std_classes' variable and replaced it with a somewhat complex scheme that is much more dynamic. What that means is that the standard set of classes is assembled at link time via magic using a special section, and there is also a dlopen-based dynamic loading feature. For static linking, you have to make specific reference at link time to each store class you want to have available by name at run time. Any module that you get linked in from libstore.a will automagically go into the standard list (because each one has a `store_std_classes' section pointing to the `struct store_class' it defines). So e.g. if you call `store_gunzip_open' or `store_gunzip_create' in your program, then the "gunzip" store type will be available to store_open et al as well. But if you don't refer to a given type, it won't be linked in. (In practice you wind up always getting the "file" type and the pseudo-types like "typed" and "query" just by virtue of calling store_open or store_parsed_open.) To get a desired set of types into a static link, you can use `-lstore_TYPE' (i.e. `-lstore_gunzip' for the "gunzip" type module). That works because there is a libstore_TYPE.a installed for each standard TYPE, which is actually a linker script with the same effect as the linker switch `-u store_TYPE_class'. When using the shared library (which is almost always the case), the same link-reference plan applies. However, this is extended to the sections named `store_std_classes' not just of the executable but of each shared object that's loaded. Since libstore.so still contains all the standard types, this is in the usual case just like the current fixed array. However, the functions that look for a store type by name at run time will also try to load an external module using dlopen if there is no existing type of that name. It dlopen's `libstore_foo.so.0.2' for the type "foo", and uses dlsym to look up `store_foo_class'. Note that once loaded for a successful open, the module is never unloaded. Thereafter, that module (and any other modules you might have dlopen'd independent of libstore) get searched for `store_std_classes' sections. Because of this (and dlopen's own redundancy detection), you could have a single libstore_foo.so.0.2 module that defined several classes and symlink together the different names by which it might be first loaded. It had been my original thinking to take all of the standard modules out and make them individually loaded on demand. But all the modules we have are in fact so tiny that the extra overhead and memory wasted for page alignment and redundant relocs would be just silly. So I left all the existing modules in the main library. For static linking, this means that if you call e.g. store_gunzip_open directly then you don't need -lstore_gunzip -lstore, just -lstore. In the shared library, it means that existing types are in practice found in basically the same way as before. Obviously, the important thing that the new dynamic features make possible is to have new store type implementation modules that are not part of the hurd package itself and can be developed and maintained separately. For example, nbd could be moved out into a standalone nbd_client package for parity with the Debian package for Linux (along with a simple `nbd-client' shell script to give a work-alike interface). In the case of nbd, that doesn't really buy anything because libstore/nbd.c is simple and self-contained (but it would make sense if e.g. the nbd protocol might change to get the client and server from related interdependent packages instead of the client being part of the basic hurd package). I would definitely like to move out the "part" store type code (libstore/part.c), which uses the Parted libraries that are already a separately maintained package. Rather than the hurd build using a configure check and conditionally relying on parts of libparted, the "part" module (both static and shared) can be installed by the libparted packages instead. Note that for the statically linked bootstrap filesystems to support the "part" store type, the libstore_part.a library will have to be installed already when linking the hurd binaries. This is something of a chicken and egg problem, but I don't think that will be much of a hassle. As I said, this code has had zero testing. So please try it out if this interests you. It's probably easiest to test the plain shared library cases and work out the kinks there before worrying about static linking or using this in your bootstrap filesystem. As I also said, I haven't floated any of these ideas before doing them. So comments are very welcome and I am open to reorganizing the code if I am convinced of some benefit to doing things differently from what I have come up with. Enjoy, Roland _______________________________________________ Bug-hurd mailing list [EMAIL PROTECTED] http://mail.gnu.org/mailman/listinfo/bug-hurd
