[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

SRFI-22 -- What won't work



* Point one: Sharp-bang is not recursive
----------------------------------------
    From: Marc Feeley <feeley@xxxxxxxxxxxxxxxx> 
    Well it could be the executable for the interpreter, but it could also
    be a shell script that execs the appropriate underlying interpreter
    (Gambit, Scheme48, etc) after doing some administrative checks (that
    the user has permission to run the interpreter, logging the use of
    a Scheme script, or whatever).  For example, I can perfectly imagine
    Gambit's interpreter to reside in "gsi" and "scheme-script"
    is a shell script like this

       #! /bin/sh
       ... parse command line options BUT DON'T CHANGE THE ENVIRONMENT!
       exec gsi ...

Unfortunately, Marc, that won't work. It ought to, but it doesn't.

The Unix sharp-bang interpreter escape in the exec(2) system call is *not*
recursive. That is, if you try to exec(2) the file foo with command-line args
of ("foo", "-x") and foo's first few bytes are

      #!/usr/bin/bar -y
      ...

this will turn into an exec of /usr/bin/bar, with command-line args of

     ("/usr/bin/bar" "-y" "foo" "-x")

At this point, however, file /usr/bin/bar better be a "real" Unix binary. If
it, itself, is a file whose first 16 bits are "#!", the exec() call will lose,
usually with a rather misleading error msg.

What this means is that "scheme-script" *cannot* itself be a #! script,
e.g., a /bin/sh shell script. OK?

Scsh deals with this by having /usr/local/bin/scsh be a tiny little trampoline
program -- native-code executable -- that inserts a few items in front
of the argv[] values and execs the S48 vm. That allows you to do scripts
of the form
    #!/usr/local/bin/scsh -s
    !#
    ...
Had /usr/local/bin/scsh itself been a vm heap image as a script, i.e. a file
of the form
    #!/usr/local/lib/scsh/scheme48vm -i
    ...vm image bits here...
then you would lose.

-------------------------------------------------------------------------------
* Point two: 28 is a small number
---------------------------------
While I'm at it, let me remind y'all of another losing feature of Unix'
lame kernel support for #!.

You usually only get 32 chars on that first sharp-bang line, divvied up
between the sharp, the bang, the interpreter filename and the (optional,
single) argument. (Linux gives you 127, but 32 is *very* common on other
systems. I believe Posix only promises you 32, to boot, but i can't swear
to it, since my Posix spec has gone missing.)

Now, remember that you want to put an absolute path name for the
interpreter, since you get no path-search help from the true kernel exec().
Let's do the accounting: 2 chars for sharp & bang. 1 char for the space
separating the interpreter from the argument. N chars for the argument
itself. That leaves 29-N chars for the interpreter, so even if you make the
argument as short as possible -- 1 char -- you still max out at 28 chars for
the interpreter.

Let's see:
    /usr/local/bin/scm-ieee-1178-90
That's 31 characters. Oops.

Now you know why I made scsh's meta-switch a single char. Horrible, isn't it?

My advice: make these program names *short* and highly coded, because the
binaries may live in various directories, and you'd like to allow as much
winnage as possible.
    -Olin