Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

Lisp as replacement for python

48 views
Skip to first unread message

Joakim Hove

unread,
Dec 7, 2001, 9:36:25 AM12/7/01
to

Dear lisp experts,

I use emacs for all my file-editing, and have come to like (simple)
e-lisp programming quite a lot. For various "administrative" tasks I
use Python. I wondered if there was a possibility to change
Python -> lisp, spesifically I want:

1. Something like #!/usr/bin/lisp-interpreter which I can put in the
top of lisp-(scripts|programs).

2. Simple access to system-libraries

and as a bonus:

3. Libraries for networking/xml/....

e-lisp fullfills point 2/3 well enough, but I still tend to consider
emacs as en *editor*, not an operating system, so I would like to be
able to excute lisp programs without going through emacs.

What, if any, solutions could fullfill these requirements? I am on a
Linux platform and portability (at least outside *ix) is not
important.

Best regards,


Joakim Hove


--
==== Joakim Hove www.phys.ntnu.no/~hove/ =======================
|| Institutt for fysikk (735) 93637 / E3-166 | Skøyensgate 10D ||
|| N - 7491 Trondheim ho...@phys.ntnu.no | N - 7030 Trondheim ||
================================================= 73 93 31 68 =========

Michael J. Ferrador

unread,
Dec 7, 2001, 10:45:55 AM12/7/01
to

Joakim Hove <ho...@phys.ntnu.no> wrote in message
news:k0npu5r...@metropolis.phys.ntnu.no...

>
> Dear lisp experts,
>
> I use emacs for all my file-editing, and have come to like (simple)
> e-lisp programming quite a lot. For various "administrative" tasks I
> use Python. I wondered if there was a possibility to change
> Python -> lisp, spesifically I want:
>
> 1. Something like #!/usr/bin/lisp-interpreter which I can put in the
> top of lisp-(scripts|programs).

That's an OS feature, should work with any /usr/bin/MyFavLang
some (most ?) interps "know" to ignore a #! line like this
if # is not their native comment.

and Linux also has "foreign" (java, etc.) binaries ?
CMUCL - first trick&tip on http://www.cons.org/cmucl/doc/index.html
But I have not tried it yet...


> e-lisp fullfills point 2/3 well enough, but I still tend to consider
> emacs as en *editor*, not an operating system, so I would like to be
> able to excute lisp programs without going through emacs.

emacs -batch MyApp.el(c)

Although I'm sure some will say elisp is just different enough
to be annoying if your goal is CL

Dr. Edmund Weitz

unread,
Dec 7, 2001, 11:04:21 AM12/7/01
to
Joakim Hove <ho...@phys.ntnu.no> writes:

> Dear lisp experts,
>
> I use emacs for all my file-editing, and have come to like (simple)
> e-lisp programming quite a lot. For various "administrative" tasks I
> use Python. I wondered if there was a possibility to change Python
> -> lisp, spesifically I want:
>
> 1. Something like #!/usr/bin/lisp-interpreter which I can put in
> the top of lisp-(scripts|programs).
>
> 2. Simple access to system-libraries
>
> and as a bonus:
>
> 3. Libraries for networking/xml/....
>
> e-lisp fullfills point 2/3 well enough, but I still tend to consider
> emacs as en *editor*, not an operating system, so I would like to be
> able to excute lisp programs without going through emacs.
>
> What, if any, solutions could fullfill these requirements? I am on a
> Linux platform and portability (at least outside *ix) is not
> important.

See <http://www.actrix.gen.nz/users/mycroft/runlisp.html> (CMUCL) or
<http://clisp.sourceforge.net/impnotes.html#quickstart> (CLISP) for
examples. But note that these are implementations of Common
Lisp. Common Lisp is a lot better than Emacs Lisp in everybody's
humble opinion, but it's of course _different_, so you'll have to
learn it first.

Good luck,
Edi.

Joakim Hove

unread,
Dec 7, 2001, 11:29:05 AM12/7/01
to

Thank you very much to both Michael and Edmund - I think I have the
answer to my question - then I just have to try it out, and see how it
compares with mu existing Python (Guido van R...) approach.

Best Regards,

Edward O'Connor

unread,
Dec 7, 2001, 12:11:44 PM12/7/01
to
> Thank you very much to both Michael and Edmund - I think I have the
> answer to my question - then I just have to try it out, and see how
> it compares with mu existing Python (Guido van R...) approach.

Another option you might consider is scsh, the Scheme shell. From the
scsh web page <URL:http://scsh.sourceforge.net/>:

Scsh is a broad-spectrum systems-programming environment for
Unix embedded in R4RS Scheme. It is brought to you by the
Scheme underground. We currently run on most major Unix
platforms and Win32.

Now it's Scheme, not CL, so it be that it's not what you want, but
from your original post I gather that that isn't an issue.


HTH,
Ted

--
Edward O'Connor
t...@oconnor.cx

bc1...@attbi.com

unread,
Dec 7, 2001, 12:43:52 PM12/7/01
to
Joakim Hove <ho...@phys.ntnu.no> writes:

> I use emacs for all my file-editing, and have come to like (simple)
> e-lisp programming quite a lot. For various "administrative" tasks I
> use Python. I wondered if there was a possibility to change
> Python -> lisp, spesifically I want:
>
> 1. Something like #!/usr/bin/lisp-interpreter which I can put in the
> top of lisp-(scripts|programs).

Thomas Burdick answered this question a while ago for another poster:

Reply by Thomas Burdick on c.l.l:
=================================

> I have an application I want to bundle up as somethign I can call from
> scripts or makefiles, with arguments. I'm on Solaris not Linux, and I
> very much need to have it compiled, so I don't think any of the clever
> fasl-files as executables or source-files-as-scripts are available to
> me.

Sure you can, read the implementation notes. fasl-files-as-scripts
works just fine (if you have an actual executable `clisp', not a
script) -- I do this all the time on Solaris:

$ cat shebang.txt
#!/path/to/clisp

$ cat shebang.txt hello.fas > example.fas
$ chmod u+x example.fas
$ ./example.fas
Hello, World!
$


Duane Rettig

unread,
Dec 7, 2001, 1:45:21 PM12/7/01
to
Joakim Hove <ho...@phys.ntnu.no> writes:

> I use emacs for all my file-editing, and have come to like (simple)
> e-lisp programming quite a lot. For various "administrative" tasks I
> use Python. I wondered if there was a possibility to change
> Python -> lisp, spesifically I want:
>
> 1. Something like #!/usr/bin/lisp-interpreter which I can put in the
> top of lisp-(scripts|programs).

For Allegro CL's part, documentation is at
http://www.franz.com/support/documentation/6.1/doc/startup.htm#starting-unix-script-3

There are some caveats, one of which has already been mentioned
in another reply. I will be requesting an enhancement to the
above documentation to include these caveats (or to make them
clearer):

1. The interpreter must be an executable, and not a shell-script.
If your execution of your installed lisp involves a shell script to
invoke the real executable, you must point to the real executable.

2. Except on Solaris and on Linux kernels which have version > 2.4,
the Allegro CL executable which you are using as an interpreter
must be in your $PATH. If it is not, you will get an error message
mentioning that it can't find the executable location.

The reason for #2 is apparently due to a bug in many of the #!
implementations in the way that argv[0] is passed. Allegro CL
uses a combination of argv[0] and the PATH variable to figure out
where the executable resides, in order to have several pieces of
information (the SYS host translation is based on this result,
and the executable's C symbol table is retrieved for debugging
purposes, among other things). If a lisp resides in some hidden
directory like /usr/my-allegro/bin/alisp where /usr/my-allegro/bin/
is not on the PATH variable, then whether a script that starts with
#! /usr/my-allegro/bin/alisp ...
works or not depends on whether the operating system (correctly)
passes "/usr/my-allegro/bin/alisp" as argv[0], or (incorrectly)
passes "alisp".

We submitted a patch for Linux, but it wasn't incorporated until
kernel 2.4, so older kernels ar buggy in this respect. Solaris
has always done it right, and all others seem to do it wrong (we
had thought that FreeBSD did it right, but apparently it does not).

--
Duane Rettig Franz Inc. http://www.franz.com/ (www)
1995 University Ave Suite 275 Berkeley, CA 94704
Phone: (510) 548-3600; FAX: (510) 548-8253 du...@Franz.COM (internet)

Kaz Kylheku

unread,
Dec 7, 2001, 3:40:28 PM12/7/01
to
In article <4adwuk...@beta.franz.com>, Duane Rettig wrote:
>purposes, among other things). If a lisp resides in some hidden
>directory like /usr/my-allegro/bin/alisp where /usr/my-allegro/bin/
>is not on the PATH variable, then whether a script that starts with
>#! /usr/my-allegro/bin/alisp ...
>works or not depends on whether the operating system (correctly)
>passes "/usr/my-allegro/bin/alisp" as argv[0], or (incorrectly)
>passes "alisp".

What is incorrect are programs which assume assume that argv[0] is the
full path name to the executable. There is no such requirement in
ANSI C, POSIX or The Single UNIX Specification.

Thus application developers must find some other way for their program to
locate itself or related files.

#! is not the only mechanism by which your program may be invoked.
In other contexts, what you get as argv[0] depends entirely on the
whims of the command interpreter shell, or other software which
launches programs. The execv() function allows a parent process to pass
anything it wants as the child's argv[0].

>We submitted a patch for Linux, but it wasn't incorporated until
>kernel 2.4, so older kernels ar buggy in this respect. Solaris
>has always done it right, and all others seem to do it wrong (we
>had thought that FreeBSD did it right, but apparently it does not).

The treatment of #! is not specified by the Single UNIX Specification
in any great detail.

The semantic description of the exec*() functions includes
this text:

If the process image file is not a valid executable object,
execlp() and execvp() use the contents of that file as standard
input to a command interpreter conforming to system(). In this
case, the command interpreter becomes the new process image.

Nothing is said about there being different kinds of executables,
or executables which name their interpreters using #! If it's not an
executable, it s shunted to the same command interpreter that the
system() function invokes. That interpreter can optionally process #!,
as provided by this text in the shell command language description:``[I]f
the first line of a file of shell commands starts with the characters #!,
the results are unspecified.''

Thus, the only provision for #! is that exec*() falls back on the
command interpreter, and that the command shell interpreter's behavior is
unspecified if the input file's first line starts with the #! digraph.

Pierre R. Mai

unread,
Dec 7, 2001, 4:00:14 PM12/7/01
to
Duane Rettig <du...@franz.com> writes:

[ Passing the full path to #! script-interpreter in argv[0] ]

> We submitted a patch for Linux, but it wasn't incorporated until
> kernel 2.4, so older kernels ar buggy in this respect. Solaris
> has always done it right, and all others seem to do it wrong (we
> had thought that FreeBSD did it right, but apparently it does not).

FWIW, cursory tests seem to indicate that at least FreeBSD 4.3 (as
well as OpenBSD 2.9) do the right thing, whereas Linux 2.2.19 doesn't.

Regs, Pierre.

--
Pierre R. Mai <pm...@acm.org> http://www.pmsf.de/pmai/
The most likely way for the world to be destroyed, most experts agree,
is by accident. That's where we come in; we're computer professionals.
We cause accidents. -- Nathaniel Borenstein

Kevin Layer

unread,
Dec 7, 2001, 4:38:24 PM12/7/01
to
"Pierre R. Mai" <pm...@acm.org> writes:

> Duane Rettig <du...@franz.com> writes:
>
> [ Passing the full path to #! script-interpreter in argv[0] ]
>
> > We submitted a patch for Linux, but it wasn't incorporated until
> > kernel 2.4, so older kernels ar buggy in this respect. Solaris
> > has always done it right, and all others seem to do it wrong (we
> > had thought that FreeBSD did it right, but apparently it does not).
>
> FWIW, cursory tests seem to indicate that at least FreeBSD 4.3 (as
> well as OpenBSD 2.9) do the right thing, whereas Linux 2.2.19 doesn't.

With the following patch, the original one that I sent to the linux kernel
mailing list, it will work.

diff -c ./fs/binfmt_script.c,0 ./fs/binfmt_script.c
*** ./fs/binfmt_script.c,0 Thu Aug 20 14:32:48 1998
--- ./fs/binfmt_script.c Wed Feb 16 10:57:33 2000
***************
*** 47,54 ****
--- 47,57 ----
i_name_start = i_name = cp;
i_arg = 0;
for ( ; *cp && (*cp != ' ') && (*cp != '\t'); cp++) {
+ /* DKL: DON'T REMOVE THE PATH */
+ #if 0
if (*cp == '/')
i_name = cp+1;
+ #endif
}
while ((*cp == ' ') || (*cp == '\t'))
*cp++ = '\0';

Kevin Layer

unread,
Dec 7, 2001, 4:50:09 PM12/7/01
to
k...@ashi.footprints.net (Kaz Kylheku) writes:

I've never heard of the Single UNIX Specification, but when I brought
this up on the linux kernel mailing list (back before 2.4 was
released), my argument was that this feature was first added to UNIX
in the early 80's in BSD. If you think of that original
implementation as the reference implementation, what it did to cause
argv[0] to be the full path to the "interpreter". Solaris and FreeBSD
(and probably the other BSD variants) maintain compatibility with that
original implementation. Many other variants of UNIX do not (HP-UX,
for one).

The most compelling reason not to strip off the path, for me, is that
the target program can strip it off, but the target program can't add
it back if it is stripped off before the program is called.

> The semantic description of the exec*() functions includes
> this text:

To me, it's not about exec. It's about the code that calls exec in
the kernel. That is where the decision to pass in the value for
argv[0] is made. Perhaps I misunderstood what you were getting at
here, though.

Erik Naggum

unread,
Dec 7, 2001, 10:20:43 PM12/7/01
to
* Kaz Kylheku

| If it's not an executable, it s shunted to the same command interpreter
| that the system() function invokes. That interpreter can optionally
| process #!, as provided by this text in the shell command language
| description:``[I]f the first line of a file of shell commands starts with
| the characters #!, the results are unspecified.''

This is incorrect for many systems, probably all reasonably modern
systems. #! is processed by the kernel as just another magic number for
executabies, not by the shell, anymore. Processing #! in the shell was
an old hack until it could get into the kernel, the smart way for new
functionality to be added.

Another way to find one's "home directory" is to require an environment
variable to hold the home directory of the system.

A better way than all this would be a system call to request the full
path name of one's executable. That, of course, does not exist.
Sometimes, Unix really sucks.

///
--
The past is not more important than the future, despite what your culture
has taught you. Your future observations, conclusions, and beliefs are
more important to you than those in your past ever will be. The world is
changing so fast the balance between the past and the future has shifted.

Kaz Kylheku

unread,
Dec 8, 2001, 12:20:04 AM12/8/01
to
In article <32167704...@naggum.net>, Erik Naggum wrote:
>* Kaz Kylheku
>| If it's not an executable, it s shunted to the same command interpreter
>| that the system() function invokes. That interpreter can optionally
>| process #!, as provided by this text in the shell command language
>| description:``[I]f the first line of a file of shell commands starts with
>| the characters #!, the results are unspecified.''
>
> This is incorrect for many systems, probably all reasonably modern
> systems. #! is processed by the kernel as just another magic number for

It's not incorrect, it's only too weak to express what is provided by
actual useful implementations. Those modern systems do conform the
weak spec as written. Treating the #! as a comment is an exemplary
provision of ``unspecified behavior''. Plus there is plenty of
room to interpret what is considered an executable file by the exec*()
functions, which opens the door to magic numbers.

> executabies, not by the shell, anymore. Processing #! in the shell was
> an old hack until it could get into the kernel, the smart way for new
> functionality to be added.

True; and there are obvious security concerns as well. There is no way
for a user space interpreter to lock out troublesome races.

> Another way to find one's "home directory" is to require an environment
> variable to hold the home directory of the system.
>
> A better way than all this would be a system call to request the full
> path name of one's executable. That, of course, does not exist.
> Sometimes, Unix really sucks.

It doesn't exist in any *portable* way.

On Linux, for instance, we have a special /proc filesystem section where
you can look up the paths of your memory mappings.

cat /proc/self/maps # Meow!
cat /proc/$$/maps # Ah, the shell's maps.

This is arguably a step better than relying on argv[0]; for one thing,
it sees through symbolic links, so that if the program was run
using #!/somewhere/some_symlink, here you find the
/somewhere_else/real_executable expansion. Whereas argv[0] will
unfortunately give you /somewhere/some_symlink, even with the #! fix in
Linux 2.4.

Hard links are the remaining culprit, but of course they are fundamentally
incompatible with the notion of a path name being an attribute of
a filesystem object, so we just sweep them under the rug and make-believe. ;)

Erik Naggum

unread,
Dec 8, 2001, 4:57:22 AM12/8/01
to
* Kaz Kylheku
| If it's not an executable, it s shunted to the same command interpreter
| that the system() function invokes. That interpreter can optionally
| process #!, as provided by this text in the shell command language
| description:``[I]f the first line of a file of shell commands starts with
| the characters #!, the results are unspecified.''

* Erik Naggum


> This is incorrect for many systems, probably all reasonably modern
> systems. #! is processed by the kernel as just another magic number for

> executabies, not by the shell, anymore.

* Kaz Kylheku


| It's not incorrect, it's only too weak to express what is provided by
| actual useful implementations. Those modern systems do conform the
| weak spec as written. Treating the #! as a comment is an exemplary
| provision of ``unspecified behavior''. Plus there is plenty of
| room to interpret what is considered an executable file by the exec*()
| functions, which opens the door to magic numbers.

I thought the premise for your elaboration was the first sentence. The
first sentence is incorrect, since the file has to be executable, but
maybe there is a difference between an executable file and an executable.
In any case, the followup would be arbitrary.

> A better way than all this would be a system call to request the full
> path name of one's executable. That, of course, does not exist.
> Sometimes, Unix really sucks.

| It doesn't exist in any *portable* way.

Well, those of us who still have a working memory of better times past
remember TOPS-10 and TOPS-20 and their excellent operating system support
for this kind of information.

| On Linux, for instance, we have a special /proc filesystem section where
| you can look up the paths of your memory mappings.

Now that you made me look for it (thanks :), I vastly prefer
(unix:readlink "/proc/self/exe").

Pierre R. Mai

unread,
Dec 8, 2001, 11:29:29 AM12/8/01
to
k...@ashi.footprints.net (Kaz Kylheku) writes:

> cat /proc/self/maps # Meow!
> cat /proc/$$/maps # Ah, the shell's maps.
>
> This is arguably a step better than relying on argv[0]; for one thing,
> it sees through symbolic links, so that if the program was run
> using #!/somewhere/some_symlink, here you find the
> /somewhere_else/real_executable expansion. Whereas argv[0] will
> unfortunately give you /somewhere/some_symlink, even with the #! fix in
> Linux 2.4.

It is unclear to me that returning the "truename" is actually
desirable. If the program really wanted to get at the truename, it
could always just resolve the symbolic links itself. If it only gets
the resolved "truename", it can't get back to the invocation name.
This disables a lot of useful uses of symbolic links, e.g. using
symbolic links to share executables (across file systems), libraries,
etc., but not configuration files:

/opt/blubber/bin/blub

looks in invocation-dir+"../lib/" for its libraries, and in
invocation-dir+"../etc/" for its config files.

We want to use the 3GB application, but want to subsititue our own
config files, so we do

mkdir ~/my-blubber/
cd ~/my-blubber/
mkdir etc
[edit our own config files]
ln -s /opt/blubber/{bin,lib}/ .

we can now call blub with ~/my-blubber/bin/blub, and everything will
work as wanted. With canonicalized paths, we will just get the old
behaviour.

From a security standpoint, this is a wash, since any security
conscious application will have to check permissions and truenames for
files and directories itself anyway.

Alexander Kjeldaas

unread,
Dec 9, 2001, 7:31:11 AM12/9/01
to
Duane Rettig wrote:

> Joakim Hove <ho...@phys.ntnu.no> writes:
>
>> I use emacs for all my file-editing, and have come to like (simple)
>> e-lisp programming quite a lot. For various "administrative" tasks I
>> use Python. I wondered if there was a possibility to change
>> Python -> lisp, spesifically I want:
>>
>> 1. Something like #!/usr/bin/lisp-interpreter which I can put in the
>> top of lisp-(scripts|programs).
>
> For Allegro CL's part, documentation is at
>
http://www.franz.com/support/documentation/6.1/doc/startup.htm#starting-unix-script-3
>
> There are some caveats, one of which has already been mentioned
> in another reply. I will be requesting an enhancement to the
> above documentation to include these caveats (or to make them
> clearer):
>
> 1. The interpreter must be an executable, and not a shell-script.
> If your execution of your installed lisp involves a shell script to
> invoke the real executable, you must point to the real executable.
>
> 2. Except on Solaris and on Linux kernels which have version > 2.4,
> the Allegro CL executable which you are using as an interpreter
> must be in your $PATH. If it is not, you will get an error message
> mentioning that it can't find the executable location.
>

I think looking for the Allegro CL executable in your PATH or by using an
environment variable is what you want. Looking at argv[0] can only be a
hach. It is not a script's responsibility to know where the executable
lies - what's why the normal way to invoke a python interpreter is:

#! /usr/bin/env python

In my experience, python and bourne shell scripts are the only ones that
work "out of the box" and finds their interpreter. The perl community uses
/usr/bin/perl and /usr/local/bin/perl interchangeable, and bash scripts use
/bin/bash and /usr/local/bin/bash. I nearly always have to edit scripts to
make them use the /usr/bin/env convention because authors do not take into
account where an executable may be on the system.

The python documentation _only_ mentions the /usr/bin/env method and I
think they avoid a world of problems for their users because of this:

http://www.python.org/doc/current/tut/node4.html#SECTION004220000000000000000

I see that this method isn't mentioned in the Allegro CL documentation.

astor

Raymond Wiker

unread,
Dec 9, 2001, 3:13:31 PM12/9/01
to
Alexander Kjeldaas <astor...@fast.no> writes:

> I think looking for the Allegro CL executable in your PATH or by using an
> environment variable is what you want. Looking at argv[0] can only be a
> hach. It is not a script's responsibility to know where the executable
> lies - what's why the normal way to invoke a python interpreter is:
>
> #! /usr/bin/env python

If I understand this correctly, this has the disadvantage of
using the first "python" in the user's path. This is not necessarily a
good thing :-)

Further, some platforms may actually put "env" under /bin
instead of /usr/bin, which means that you haven't really solved
anything...

Finally, "env" is a dynamic executable under some
platforms, which means that you may not be able to use it in
single-user mode.

All in all, I have a feeling that using env in this way is not
really a good solution.

--
Raymond Wiker Mail: Raymon...@fast.no
Senior Software Engineer Web: http://www.fast.no/
Fast Search & Transfer ASA Phone: +47 23 01 11 60
P.O. Box 1677 Vika Fax: +47 35 54 87 99
NO-0120 Oslo, NORWAY Mob: +47 48 01 11 60

Try FAST Search: http://alltheweb.com/

Alexander Kjeldaas

unread,
Dec 9, 2001, 9:12:23 PM12/9/01
to
Raymond Wiker wrote:

> Alexander Kjeldaas <astor...@fast.no> writes:
>
>> I think looking for the Allegro CL executable in your PATH or by using an
>> environment variable is what you want. Looking at argv[0] can only be a
>> hach. It is not a script's responsibility to know where the executable
>> lies - what's why the normal way to invoke a python interpreter is:
>>
>> #! /usr/bin/env python
>
> If I understand this correctly, this has the disadvantage of
> using the first "python" in the user's path. This is not necessarily a
> good thing :-)
>

It _is_ a good thing if you are trying to write a portable script. You
then leave it up to the user to decide where to find the executable, and
there is a well known technique for that - the PATH environment variable.

If your mission is to help some interpreter find itself, or if you are a
developer with N versions of the interpreter installed, you might be
interested in selecting a specific interpreter, but that is an _exception_
to the rule. The general rule is to let the user decide unless you have
special reasons not to.


> Further, some platforms may actually put "env" under /bin
> instead of /usr/bin, which means that you haven't really solved
> anything...
>

Please give me an example of a UNIX flavor which is _in general use_ and
which lacks /usr/bin/env. Inventing the possibility of a platform where
/usr/bin/env might be missing isn't a strong argument. I have checked
Linux, FreeBSD, NetBSD, Solaris, SunOS, IRIX, AIX, HP-UX, Digital UNIX, and
ULTRIX so you can skip those. Right now I can't remember any other major
UNIX flavors to check.

Furthermore, "env" is mandatory in the UNIX 98, UNIX 95, POSIX.2, and SVID3
standards. I am quite sure that UNIX 98, UNIX 95, and POSIX.2 specifies
/usr/bin/env, I'm not sure what SVID3 specifies.

Hell, even the Scheme SRFI 22 "Running Scheme Scripts on Unix" recommends
/usr/bin/env!

But you are right - I actually know of _one_ UNIX flavor which does not
have /usr/bin/env (but has /bin/env). It's claim to fame as I know it is
its lack of standards compliance which makes porting software painful. It
is also a flavor I would leave out of the "in general use" category.

Tip: It is a UNIX flavor made by a big software company known for another
popular desktop operating system.

> Finally, "env" is a dynamic executable under some
> platforms, which means that you may not be able to use it in
> single-user mode.
>

Please explain why a dynamic executable stops working because your system
is in single-user mode.

Also note that you are getting into seriously system-specific territory.
If getting your system up and running in a multi-user state requires an
interpreter then it is a very integrated part of the system, and yes - in
that case you would want to use the explicit path for the executable. The
reason you would want to do that is not because you have to, but because in
that case you _do not_ want the user to easily install a different version
of the interpreter.

> All in all, I have a feeling that using env in this way is not
> really a good solution.
>

I feel that you need to find better arguments against /usr/bin/env :-)

astor

Bruce Hoult

unread,
Dec 9, 2001, 9:38:51 PM12/9/01
to
In article <9v15mc$kjb$1...@news.ost.eltele.no>, Alexander Kjeldaas
<astor...@fast.no> wrote:

> Please give me an example of a UNIX flavor which is _in general use_ and
> which lacks /usr/bin/env. Inventing the possibility of a platform where
> /usr/bin/env might be missing isn't a strong argument. I have checked
> Linux, FreeBSD, NetBSD, Solaris, SunOS, IRIX, AIX, HP-UX, Digital UNIX,
> and
> ULTRIX so you can skip those. Right now I can't remember any other major
> UNIX flavors to check.

You can add MacOS X to the list.

-- Bruce

Raymond Wiker

unread,
Dec 9, 2001, 10:38:42 PM12/9/01
to
Alexander Kjeldaas <astor...@fast.no> writes:

> Raymond Wiker wrote:
>
> > Alexander Kjeldaas <astor...@fast.no> writes:
> >
> >> I think looking for the Allegro CL executable in your PATH or by using an
> >> environment variable is what you want. Looking at argv[0] can only be a
> >> hach. It is not a script's responsibility to know where the executable
> >> lies - what's why the normal way to invoke a python interpreter is:
> >>
> >> #! /usr/bin/env python
> >
> > If I understand this correctly, this has the disadvantage of
> > using the first "python" in the user's path. This is not necessarily a
> > good thing :-)
> >
>
> It _is_ a good thing if you are trying to write a portable script. You
> then leave it up to the user to decide where to find the executable, and
> there is a well known technique for that - the PATH environment variable.
>
> If your mission is to help some interpreter find itself, or if you are a
> developer with N versions of the interpreter installed, you might be
> interested in selecting a specific interpreter, but that is an _exception_
> to the rule. The general rule is to let the user decide unless you have
> special reasons not to.

Security-wise, I consider this case to be similar to having "."
in $PATH. It is also problematic support-wise.

Because /usr isn't even _mounted_, and the dynamic linking
machinery has not been initialised?

> Also note that you are getting into seriously system-specific territory.
> If getting your system up and running in a multi-user state requires an
> interpreter then it is a very integrated part of the system, and yes - in
> that case you would want to use the explicit path for the executable. The
> reason you would want to do that is not because you have to, but because in
> that case you _do not_ want the user to easily install a different version
> of the interpreter.
>
> > All in all, I have a feeling that using env in this way is not
> > really a good solution.
> >
>
> I feel that you need to find better arguments against /usr/bin/env :-)

Not really, no. For _me_ it is sufficient that using
/usr/bin/env introduces a dependency on the user's PATH. Having
dependencies on the user's runtime environment is seldom necessary,
and complicates things for the user and whoever supports him/her.

The install procedure for scripted applications should take
care of editing the script headers at installation time.

Thomas F. Burdick

unread,
Dec 10, 2001, 12:24:14 AM12/10/01
to
Raymond Wiker <Raymon...@fast.no> writes:

> Alexander Kjeldaas <astor...@fast.no> writes:
>
> > It _is_ a good thing if you are trying to write a portable script. You
> > then leave it up to the user to decide where to find the executable, and
> > there is a well known technique for that - the PATH environment variable.
> >
> > If your mission is to help some interpreter find itself, or if you are a
> > developer with N versions of the interpreter installed, you might be
> > interested in selecting a specific interpreter, but that is an _exception_
> > to the rule. The general rule is to let the user decide unless you have
> > special reasons not to.
>
> Security-wise, I consider this case to be similar to having "."
> in $PATH.

You're going to have to do more than just assert that. I don't see
the similarity at all. Having "." in the path will execute arbitrary
programs depending on where the user is. By using "env", you're using
whatever interpreter the user/admin has decided to put in the user's
path, which, unless they have "." in the path, won't be some arbitrary
program that depends on the currend wd, but will be the system's
installation of the interpreter.

> It is also problematic support-wise.

How is this problematic? If you find the exact path at install time,
you might be installing on a system like Debian, where, eg, if I type
'which emacs', I get /usr/bin/emacs -> /etc/alternatives/emacs ->
/usr/bin/emacs20 -> /usr/bin/emacs-20.7. I don't think this is any
less likely to change under you than what "env" gets you -- in both
cases, they'll change when the sysadmin changes the interpreter's
installation.

> > I feel that you need to find better arguments against /usr/bin/env :-)
>
> Not really, no. For _me_ it is sufficient that using
> /usr/bin/env introduces a dependency on the user's PATH. Having
> dependencies on the user's runtime environment is seldom necessary,
> and complicates things for the user and whoever supports him/her.
>
> The install procedure for scripted applications should take
> care of editing the script headers at installation time.

As I said above, I don't think this'll make much of a difference. A
well-configured Debian or Unix system will have symlinks for the major
interpreters, pointing to the specific installation. Neither
technique is going to save you from the sysadmin doing a minor upgrade
to the interpreter. If you want to protect against that, just check
the version of the interpreter in the actual code.

--
/|_ .-----------------------.
,' .\ / | No to Imperialist war |
,--' _,' | Wage class war! |
/ / `-----------------------'
( -. |
| ) |
(`-. '--.)
`. )----'

Duane Rettig

unread,
Dec 10, 2001, 4:45:37 AM12/10/01
to
Alexander Kjeldaas <astor...@fast.no> writes:

> Duane Rettig wrote:
>
> > 2. Except on Solaris and on Linux kernels which have version > 2.4,
> > the Allegro CL executable which you are using as an interpreter
> > must be in your $PATH. If it is not, you will get an error message
> > mentioning that it can't find the executable location.
> >
>
> I think looking for the Allegro CL executable in your PATH

[...]
> is what you want.

That is precisely what I said in the above paragraph.

> Looking at argv[0] can only be a hach.

Of course it's a hack. It's the same Unix hack that allows e.g.
gzip and gunzip to perform opposite functionalities, even though
they are precisely the same executable file when they are both
installed with hard links. And it is this hack which some unix
systems use similarly to distinguish similar-functioning programs,
including C compilers, in some cases, and also including shells,
in some cases.

In Allegro CL's case, if the name in argv[0] is not a full pathname,
then the last component of that name is looked for in the $PATH.
If the executable is not in the user's PATH, then it won't be able
to find itself.

Alexander Kjeldaas

unread,
Dec 10, 2001, 5:48:44 AM12/10/01
to
Bruce Hoult wrote:

They got it right! The UNIX flavor I mentioned that didn't support
/usr/bin/env was A/UX :-)

astor

Duane Rettig

unread,
Dec 10, 2001, 5:00:50 AM12/10/01
to
Alexander Kjeldaas <astor...@fast.no> writes:

> Raymond Wiker wrote:
>
> > Alexander Kjeldaas <astor...@fast.no> writes:
> >
> >> I think looking for the Allegro CL executable in your PATH or by using an
> >> environment variable is what you want. Looking at argv[0] can only be a
> >> hach. It is not a script's responsibility to know where the executable
> >> lies - what's why the normal way to invoke a python interpreter is:
> >>
> >> #! /usr/bin/env python
> >
> > If I understand this correctly, this has the disadvantage of
> > using the first "python" in the user's path. This is not necessarily a
> > good thing :-)
> >
>
> It _is_ a good thing if you are trying to write a portable script. You
> then leave it up to the user to decide where to find the executable, and
> there is a well known technique for that - the PATH environment variable.

In this particular paragraph, you are confusing the finding of the
executable by the user with the finding of the executable by the
program being executed. We are only talking about the latter, by
virtue of the fact that we are discussing argv[0]. A user isn't
concerned with argv[0], only the program already being run (and thus
having already been found by the user) can be concerned with argv[0].

> If your mission is to help some interpreter find itself, or if you are a
> developer with N versions of the interpreter installed, you might be
> interested in selecting a specific interpreter, but that is an _exception_
> to the rule. The general rule is to let the user decide unless you have
> special reasons not to.

Again, there is user/program confusion here. The user has already found
the program he or she wants. The question is whether or not the
already-running program can find itself. If two different versions of
the same program are installed on the same system, and the one that is
running finds the other one, then that is _not_ a good thing.

Michael Hudson

unread,
Dec 10, 2001, 7:49:25 AM12/10/01
to
Alexander Kjeldaas <astor...@fast.no> writes:

> The python documentation _only_ mentions the /usr/bin/env method and
> I think they avoid a world of problems for their users because of
> this:

Well, if you're distributing your scripts, you should use distutils
which will fiddle the shebang line to point to the Python interpreter
on installation; the point being that the Python developer's have
found problems with /usr/bin/env too.

Cheers,
M.

--
About the use of language: it is impossible to sharpen a
pencil with a blunt axe. It is equally vain to try to do
it with ten blunt axes instead.
-- E.W.Dijkstra, 18th June 1975. Perl did not exist at the time.

Raymond Wiker

unread,
Dec 10, 2001, 1:27:31 PM12/10/01
to
t...@conquest.OCF.Berkeley.EDU (Thomas F. Burdick) writes:

> Raymond Wiker <Raymon...@fast.no> writes:
>
> > Alexander Kjeldaas <astor...@fast.no> writes:
> >
> > > It _is_ a good thing if you are trying to write a portable script. You
> > > then leave it up to the user to decide where to find the executable, and
> > > there is a well known technique for that - the PATH environment variable.
> > >
> > > If your mission is to help some interpreter find itself, or if you are a
> > > developer with N versions of the interpreter installed, you might be
> > > interested in selecting a specific interpreter, but that is an _exception_
> > > to the rule. The general rule is to let the user decide unless you have
> > > special reasons not to.
> >
> > Security-wise, I consider this case to be similar to having "."
> > in $PATH.
>
> You're going to have to do more than just assert that. I don't see
> the similarity at all. Having "." in the path will execute arbitrary
> programs depending on where the user is. By using "env", you're using
> whatever interpreter the user/admin has decided to put in the user's
> path, which, unless they have "." in the path, won't be some arbitrary
> program that depends on the currend wd, but will be the system's
> installation of the interpreter.

What about setuid scripts? (yeah, I know; bad idea).

Anyway, it's not just a question of "the user using whatever
interpreter the admin has placed in the user's path". A script may be
written for a particular version of an interpreter, and may not work
with a different version. By having the path hardcoded in the script
header you make that dependency explicit.

> > It is also problematic support-wise.
>
> How is this problematic? If you find the exact path at install time,
> you might be installing on a system like Debian, where, eg, if I type
> 'which emacs', I get /usr/bin/emacs -> /etc/alternatives/emacs ->
> /usr/bin/emacs20 -> /usr/bin/emacs-20.7. I don't think this is any
> less likely to change under you than what "env" gets you -- in both
> cases, they'll change when the sysadmin changes the interpreter's
> installation.

It'll also change whenever the PATH is changed, which could be
because of a change to system defaults, or a change in the user's
startup files. On a FreeBSD machine, it could be that the user wants
to use /usr/local/bin/make instead of /usr/bin/make, so he places
/usr/local/bin/make in front of the path. There may also be an
installation of perl under /usr/local, which would then be used for
perl scripts using the "env" trick. Given that the version of perl
installed under /usr/local is likely to be less stable than the one
delivered with the system, there is a definite potential for
problems. This is a support problem because:

- different users may observe different behaviour

- an implicit version dependency is broken

Feel free to consider other examples than make and perl :-)

> > > I feel that you need to find better arguments against /usr/bin/env :-)
> >
> > Not really, no. For _me_ it is sufficient that using
> > /usr/bin/env introduces a dependency on the user's PATH. Having
> > dependencies on the user's runtime environment is seldom necessary,
> > and complicates things for the user and whoever supports him/her.
> >
> > The install procedure for scripted applications should take
> > care of editing the script headers at installation time.
>
> As I said above, I don't think this'll make much of a difference. A
> well-configured Debian or Unix system will have symlinks for the major
> interpreters, pointing to the specific installation. Neither
> technique is going to save you from the sysadmin doing a minor upgrade
> to the interpreter. If you want to protect against that, just check
> the version of the interpreter in the actual code.

A check in the actual code is not going to help - it will just
get you an error message earlier.

Daniel Barlow

unread,
Dec 10, 2001, 9:24:40 AM12/10/01
to
Alexander Kjeldaas <astor...@fast.no> writes:

> They got it right! The UNIX flavor I mentioned that didn't support
> /usr/bin/env was A/UX :-)

I guessed it was the NT POSIX subsystem :-(

Oh well.


-dan

--

http://ww.telent.net/cliki/ - Link farm for free CL-on-Unix resources

Brian Palmer

unread,
Dec 10, 2001, 4:32:18 PM12/10/01
to
Daniel Barlow <d...@telent.net> writes:

> Alexander Kjeldaas <astor...@fast.no> writes:
>
> > They got it right! The UNIX flavor I mentioned that didn't support
> > /usr/bin/env was A/UX :-)
>
> I guessed it was the NT POSIX subsystem :-(

And here I was thinking it was Xenix.

--
Brian Palmer
"Whoever fights monsters should see to it that in the process he does
not become a monster. And when you look long into an abyss, the abyss
also looks into you" - Nietzsche

Sam Steingold

unread,
Dec 11, 2001, 1:09:13 PM12/11/01
to
> * In message <k0npu5r...@metropolis.phys.ntnu.no>
> * On the subject of "Lisp as replacement for python"
> * Sent on 07 Dec 2001 15:36:25 +0100

> * Honorable Joakim Hove <ho...@phys.ntnu.no> writes:
>
> 1. Something like #!/usr/bin/lisp-interpreter which I can put in the
> top of lisp-(scripts|programs).

<http://clisp.cons.org/impnotes.html#quickstart>

> 2. Simple access to system-libraries

<http://clisp.cons.org/impnotes.html#d39e32138>

clisp -K full offers access to all glibc system calls.

> 3. Libraries for networking/xml/....

CLOCC/CLLIB/xml.lisp
CLOCC/CLLIB/url.lisp
<http://www.podval.org/~sds/data/cllib.html>


--
Sam Steingold (http://www.podval.org/~sds)
Keep Jerusalem united! <http://www.onejerusalem.org/Petition.asp>
Read, think and remember! <http://www.iris.org.il> <http://www.memri.org/>
Whom computers would destroy, they must first drive mad.

Rune Skårsmoen

unread,
Dec 13, 2001, 7:35:55 AM12/13/01
to
Alexander Kjeldaas <astor...@fast.no> writes:

So you weren't thinking of SCO UNIX, then? ;)


--

0 new messages