FWIW, my thoughts:
You want to be able to load code selectively (on demand, not on startup, if I understand correctly), but then you don't want to do it because of loading speed concerns--that's sort of contradicting itself, isn't it? :)
With my chjmodule stuff, I'm going the .o1 file route; the programs I've been writing up to now are loading maybe 20 or 30 such object files only, not thousands. (It actually *is* a slow process with chjmodule, but not because of the loading of the object files themselves but because of the aliasing (copying) of the identifyers to the other namespaces; I'm using eval (like (eval `(define ,id1 ,id2))) for this and that's slow (I'm sure that can be improved, I just haven't bothered).)
If loading speed or the number of modules is an issue, maybe you could group together modules which are usually loaded together (by using, say, |include|), maybe reducing the 1000 items to a few hundred or less? (Gambit can also do a better job optimizing when you group together code (block compilation with inlining).) Dunno about zipping, one of the good things of shared object files is that they are mmap'ed into the process so they are shared by multiple independent processes; this is lost if each process extracts the objects to private memory.
What's the reason why you can't live with the code being already loaded at launch time?
Christian.