On Tuesday 21 May 2002 01:57 pm, David Korn wrote:
> There could be a command to turn a script into an executable
> which would insert the 8-bit characters
> #! <pathname>
> into the file.
> For example,
> mkexec file [interp [arg]]
> would modify file so that it would be an executable that is
> processed by interp (or the standard shell) optionally invoked
> with [arg].
My problem with mkexec is that it would reduce shebang portability to the
level of compiled code. Given that we're talking about interpreters instead
of compilers, an implicit goal should be runtime portability across
implementations. Mkexec would explicitly remove any chance of runtime
portability, which would give heartburn to many sysadmins (including me) who
manage multi-vendor sites -- we currently take pains to write scripts that
defacto work on any given vendor's UNIX system (typically using /bin/ksh or
/usr/bin/perl). We either share these scripts via NFS or rsync them. With
mkexec's level of portability, we sysadmins might have to completely abandon
NFS/DFS/AFS sharing of scripts among systems, and rsync sharing would require
extra processing.
If we look at this from a broader perspective, associating an interpreter
with a script is a subset of the larger problem of associating a program with
a file. Apple solved this with resource forks, which is really just
metadata. Ideally we should be using filesystem level metadata, but that
won't happen anytime soon, so we still needed the shebang line. The Internet
folks have already solved the problem of associating programs with files by
using MIME. In the MIME scheme there is a mime.types extension-map that maps
simple file extensions, such as "sh", to MIME types, e.g.
application/x-shell. Such an entry in mime.types looks like
application/x-shell sh
Then a second file called 'mailcap' is used to map MIME types to commands,
e.g. /bin/sh. (See rfc1524.txt) Such an entry in mailcap looks like
application/x-shell; /bin/sh %s
Thus, we could define shebang processing rules as follows:
(1) #! /absolute/path args
Starts with a slash, so bypass mime.types and mailcap. Provides
backward
compatibility.
Example: #! /bin/sh
(2) #! type/subtype args
Embedded slash means a MIME type, so lookup directly in mailcap.
Example: #! application/x-shell
(3) #! extension args
No embedded slash means an extension, so lookup the extension in
mime.types
to get the MIME type, then lookup the MIME type in mailcap.
Example: #! sh
Default mime.types and mailcap files would be provided by each UNIX vendor
that map to the correct absolute path for each interpreter. Each site can
augment or change those host-wide mappings as needed. Moreover, end-users
can augment/override mappings using their own ~/.mime.types and ~/.mailcap
files.
Note that the filename of the shell script need not end in .sh -- the "#! sh"
line provides that association. But an interesting aside is that the exec()
loader could also use the mime.types & mailcap file, so that a file whose
name ends in .sh would not need the shebang line.
-david
P.S. An aside on file-level metadata: I'd like to see the metadata associated
with a file implemented as a simple XML string accessed via simple APIs like
setenv/getenv. Mode, owner/group, and ACLs would just be sets/gets of
specific XML tags. Then tar/pax would just copy the whole XML string of
metadata when creating and restoring archives. If a system where an archived
file is restored doesn't support a particular XML tag, those tags are just
ignored at runtime. That's true portability.
--
David Nessl
1664 Fox Chase Dr
Blacklick, OH 43004
614-860-0888
yyy@xxxxxxxxx
www.nessl.org/drn
|