libraries

Chris Torek chris at mimsy.UUCP
Wed Dec 21 13:54:04 AEST 1988


[subject changed back to follow the other parallel thread]

In article <43200058 at uicsrd.csrd.uiuc.edu> kai at uicsrd.csrd.uiuc.edu writes:
[re replacing archive libraries with directories full of .o files]
>Large numbers of object files?  You've apparently never worked on a program
>so huge that */*.o expands to overflow the shell's command line buffer, so
>there is absolutely no way to link without storing them all in a library
>first.

You are not thinking clearly.  Indeed, a large number of .o files is
one of the very reasons I was considering giving up or modifying the
current library archive scheme.  When you have that many .o files,
`ar c lib.a *.o' also runs out of argv space, and you must build the
library in pieces, because you must name all the .o files for ar.
Getting the library sorted becomes a major hassle.

But if you were to run `ld -X /lib/crt0.o -o foo foo.o -lc', how is
that different from when you now run `ld -X /lib/crt0.o -o foo foo.o -lc'?
So *what* if `-lc' tells ld `go look at /lib/libc/*.o' rather than
`go look at /lib/libc.a'?  Indeed, library directories and library
archive-files are not at all incompatible; one could (as I did)
imagine ld containing code rather like the following:

	struct libops {
		int	(*lib_getsyms)();
		int	(*lib_readobj)();
		...
	};
	int sprintf();

	...
		if (!arlib_open(&lib, libname) && !dirlib_open(&lib, libname))
			stop("cannot find library `%s'", libname);
	...

	int arlib_getsyms(), arlib_readobj();
	struct libops arlib_ops = { arlib_getsyms, arlib_readobj, ... };

	/* try for an archive .a file */
	int
	arlib_open(lib, libname)
		struct libdata *lib;
		char *libname;
	{
		struct arlib_data *p;
		int fd;
		char fn[MAXPATHLEN];

		(void) sprintf(fn, "%s.a", libname);
		if ((fd = open(fn, O_RDONLY)) < 0)
			return (0);	/* no ar file */

		/* got an ar file. set up private data, etc */
		p = (struct arlib_data *)xalloc(sizeof(*p));
		lib->lib_data = (caddr_t)p;
		lib->lib_ops = &arlib_ops;
		p->ar_fd = fd;
		p->ar_israndom = arlib_hasfile("__.SYMDEF");
		...
		return (1);
	}

	...

	int dirlib_getsyms(), dirlib_readobj();
	struct libops dirlib_ops = { dirlib_getsyms, dirlib_readobj, ... };

	/* try for a directory .a file */
	int
	dirlib_open(lib, libname)
		struct libdata *lib;
		char *libname;
	{
		struct dirlib_data *p;
		struct stat st;

		if (stat(libname, &st) || (st.st_mode & S_IFMT) != S_IFDIR)
			return (0);	/* not a directory library */

		/* like, similar, y'know? */
		p = (struct dirlib_data *)xalloc(sizeof(*p));
		lib->lib_data = (caddr_t)p;
		lib->lib_ops = &dirlib_ops;
		p->d_file = p->d_path + sprintf(p->d_path, "%s/", libname);
		...
		return (1);
	}

plus any other arbitrary library scheme one cared to come up with (such
as multiple .a files for `sub-groups' of the library, in which loops in
the call topology do not cause so much ordering trouble as they do in
separate libraries now, because all the sub-groups are treated as a
single library by the grouplib() routines).

(Some will recognise the above approach as the way one writes `object
oriented' code in C.)
-- 
In-Real-Life: Chris Torek, Univ of MD Comp Sci Dept (+1 301 454 7163)
Domain:	chris at mimsy.umd.edu	Path:	uunet!mimsy!chris



More information about the Comp.unix.wizards mailing list