home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Usenet 1994 October
/
usenetsourcesnewsgroupsinfomagicoctober1994disk2.iso
/
misc
/
volume21
/
libiexec
/
part01
/
README
< prev
Wrap
Text File
|
1991-07-25
|
3KB
|
67 lines
libiexec
BSD-derived Unixes have a very useful kernel hack that most System V
(R<4) Unixes don't, which makes it easy to run scripts for various
interpreters such as perl, ksh, csh, and awk.
If an exec-family function finds that a file it has been told to run
does not have a valid magic number for a binary, it tries to run the
file as a script. To do this, it checks to see whether the file
starts with the characters "#!". If it does, the kernel takes the
word following the "#!" to be the pathname of the program to run
instead, with the path of the script file given as an argument, and if
there is another word in the "#!" line following the program pathname,
that is also passed to the program as an argument, before the script
name. As a special case, if the file is neither a binary nor a script
starting with "#!", execlp and execvp try to run it as a /bin/sh script.
In comp.unix.wizards, john@sco.COM (John R. MacMillan) argued recently
that there is no good reason why the "#!" interpretation must be done
in the kernel; it can easily be done in the exec library functions
instead.
So here is an attempt to retrofit "#!" support onto systems that don't
have it. It is a library of replacement functions for execl, execvp,
et al. that have an "i" (for "interpreter support") prepended to the
names. This means that you don't have to change your system libraries
in order to use them. To compile programs using them, add these to
the flags you pass cc:
-Dexecl=iexecl -Dexecle=iexecle -Dexeclp=iexeclp -Dexecv=iexecv
-Dexecve=iexecve -Dexecvp=iexecvp
Or, just pass the ones redefining the functions the program you are
compiling actually uses.
Then add libiexec.a to the list of files passed to the linking phase.
A limitation of this implementation is that you can't add "#!" support
to programs you don't have the source code to, probably including sh
and csh (unless you have some kind of shared libraries, perhaps). A
solution for the shells is to get free shells such as bash and tcsh
(version 6.00 or later) and install them as /bin/sh or /bin/csh
instead. bash itself supports "#!" on systems where the exec
functions don't, except that versions 1.08 and previous don't do it
for programs you run with the "exec" command. Because bash uses
execve, "exec scriptname" will fail if the script does not start with
"#!interpreter-path" even if you link it with this library (and even
if you run bash on a BSD system). If you want to fix that problem, at
the loss of some BSD compatibility in the functions, change the ", 0"
to ", 1" in iexecve in iexec.c. bash doesn't have the getopts builtin
or some of ksh's esoteric features, but as of release 1.08 it's in
reasonably good shape otherwise.
If you want to make linking with these functions transparent, the
following procedure will probably work, though I have not tried it.
Using some program that can edit binary files, such as GNU emacs,
change every "execv" or "execl" in your libc.a to "oxecv" or "oxecl"
("o" for "old"). Change iexec.c so that script_execve, iexecve and
iexecvp call oxecve instead of execve; then rename the functions
defined in iexec.c so that they do not have the initial "i" in their
names. Compile iexec.c and use ar to add iexec.o to libc.a.
ietest.c is a test program that is linked with libiexec.a and runs
cshscript to make sure the library works.
David MacKenzie <djm@eng.umd.edu>