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

Why Perl do But Python can't?

3 views
Skip to first unread message

Kelly Lynn Martin

unread,
Jan 30, 2000, 3:00:00 AM1/30/00
to pytho...@python.org
On Mon, 31 Jan 2000 08:48:09 +0800, "周公" <jfz...@188.net> said:

>Someone know the difference of Perl and Python in the CGI running
>mode?

Scripts (of any sort) are inherently unsafe when run setuid or setgid.
See the perlsec manpage for why.

Kelly


周公

unread,
Jan 31, 2000, 3:00:00 AM1/31/00
to
I write a CGI useing Perl to modify passwd,set the CGI mod to 4755,and it
really do.
But When I change it into Python with the same function,set mod to 4755,but
it not use the Setuid bit.

Someone know the difference of Perl and Python in the CGI running mode?

Luc...@soim.net
2000.1.30


周公

unread,
Jan 31, 2000, 3:00:00 AM1/31/00
to
Thank you help.
But How I do it to solve the follow quertion:

1:through the WWW to manage user,the CGI need root uid.
2:how to read or write files that need some privilege ie. root ,admin etc...

some one tell me
1:use another programme to communite with CGI useing socket,but it is
complex.
2:use expect mod ,but python dosn't have.

is there better solution?


Kelly Lynn Martin wrote in message
<2000013101...@poverty.bloomington.in.us>...


>On Mon, 31 Jan 2000 08:48:09 +0800, "周公" <jfz...@188.net> said:
>

>>Someone know the difference of Perl and Python in the CGI running
>>mode?
>

Jørn Helge B. Dahl

unread,
Jan 31, 2000, 3:00:00 AM1/31/00
to
* "周公" <jfz...@188.net>

> But How I do it to solve the follow quertion:

It is written qwertyon (sorry, could't help it. No offense :-))

> 1:through the WWW to manage user,the CGI need root uid.
> 2:how to read or write files that need some privilege ie. root ,admin etc...

Write a C wrapper program (or another compiled language) that has the
right privileges (setuid, setgid, or whatever) and call the script
(which has no privs) from there.

> some one tell me
> 1:use another programme to communite with CGI useing socket,but it is
> complex.
> 2:use expect mod ,but python dosn't have.

I don't know.
--
This goes to eleven

Clarence Gardner

unread,
Jan 31, 2000, 3:00:00 AM1/31/00
to
Kelly Lynn Martin <ke...@poverty.bloomington.in.us> wrote:
: Scripts (of any sort) are inherently unsafe when run setuid or setgid.

: See the perlsec manpage for why.

This is not true, and is a myth people need to get over. The danger
Kelly referred to exists on some Unix-like systems and not on others.
On a system where they are safe, there is no reason whatsoever to use
a setuid wrapper.

--
Clarence Gardner
Software Engineer
NetLojix Communications NASDAQ:NETX
clar...@netlojix.com

Adrian Eyre

unread,
Jan 31, 2000, 3:00:00 AM1/31/00
to Clarence Gardner, pytho...@python.org
> : Scripts (of any sort) are inherently unsafe when run setuid or setgid.
> : See the perlsec manpage for why.
>
> This is not true, and is a myth people need to get over. The danger
> Kelly referred to exists on some Unix-like systems and not on others.
> On a system where they are safe, there is no reason whatsoever to use
> a setuid wrapper.

Just out of interest, what is the reason why this in unsafe. I couldn't
see the difference between a script and a binary.

--------------------------------------------
Adrian Eyre <a.e...@optichrome.com>
http://www.optichrome.com

Cameron Laird

unread,
Jan 31, 2000, 3:00:00 AM1/31/00
to
In article <8737c1$76d$1...@news.cz.js.cn>, 周公 <jfz...@188.net> wrote:
>Thank you help.

>But How I do it to solve the follow quertion:
>
>1:through the WWW to manage user,the CGI need root uid.
>2:how to read or write files that need some privilege ie. root ,admin etc...
>
>some one tell me
>1:use another programme to communite with CGI useing socket,but it is
>complex.
>2:use expect mod ,but python dosn't have.
>
>is there better solution?
.
.
.
As best I can understand,

use expect mod ,but python dosn't have.
refers to Expect.pm, and has no particular relation to
WWW, suid, sgid, or other elements of this post.

In fact Python does have analogues to Expect.pm. The
little research I've done indicates that they're not
well-researched. I've been considering writing up a
tutorial on their use and status ... In the meantime,
I recommend those whom this topic interests visit
ftp://ftp.python.org/pub/python/contrib-09-Dec-1999/System/expy-0.4a.README
ftp://ftp.python.org/pub/python/contrib-09-Dec-1999/System/pipe-1.0.README
ftp://ftp.python.org/pub/python/contrib-09-Dec-1999/All/pyexpect.README

Thanks to Barry Warsaw for his help with these data.
--

Cameron Laird <cla...@NeoSoft.com>
Business: http://www.Phaseit.net
Personal: http://starbase.neosoft.com/~claird/home.html

Clarence Gardner

unread,
Jan 31, 2000, 3:00:00 AM1/31/00
to Adrian Eyre
> > This is not true, and is a myth people need to get over. The danger
> > Kelly referred to exists on some Unix-like systems and not on others.
> > On a system where they are safe, there is no reason whatsoever to use
> > a setuid wrapper.
>
> Just out of interest, what is the reason why this in unsafe. I couldn't
> see the difference between a script and a binary.

It has to do with how the text of the script is provided to the
interpreter (Perl, Python, etc). The danger comes in if the operating
system, having started the interpreter and changed the processes
credentials according to the setxid bits, then passes it the name of the
script file to run -- that file may have been changed to a different one
by the time the interpreter opens it.

Safe systems (generally SystemV descendants, like Solaris and Irix, but
not Linux), do not pass the name of the actual script file to the
interpreter. The operating system opens the script file in the context
of the process, then passes it a filename from the file descriptor
filesystem that refers to it (e.g., /dev/fd/6), which cannot have been
tampered with.


Thomas Wouters

unread,
Jan 31, 2000, 3:00:00 AM1/31/00
to pytho...@python.org
On Mon, Jan 31, 2000 at 06:13:11PM -0000, Adrian Eyre wrote:

> > : Scripts (of any sort) are inherently unsafe when run setuid or setgid.
> > : See the perlsec manpage for why.
> >

> > This is not true, and is a myth people need to get over. The danger
> > Kelly referred to exists on some Unix-like systems and not on others.
> > On a system where they are safe, there is no reason whatsoever to use
> > a setuid wrapper.
>
> Just out of interest, what is the reason why this in unsafe. I couldn't
> see the difference between a script and a binary.

When you try to execute a script (using any of the exec*() family C calls)
the UNIX (or perhaps C library on some systems) opens the program in
question and tries to determine what kind of binary format it is. If it's a
pure binary, it gets handled as pure code, executed right away. If it has
shared libraries of any kind the runtime link/loader is called in to do the
setup. But if it's a script, it has to do something different :P

It has to read the first line of the file, strip the #!, check if the
interpreter exists, and exec()'s that, with a modified argv: basically the
shebang line, minus the #!, with the script name and the original arguments
to the script attached. Thus,

spam.py:
-
#!/usr/bin/python -X
-

centurion: ~> ./spam.py -i10 foobar


becomes (pseudocode)

execv("/usr/bin/python -X spam.py -i10 foobar")

If setuid bits on scripts where allowed, it would have to do the exec()
running as the owner of the file already, so that '/usr/bin/python' is
called as the right user. But this means there is a possible race condition,
using symlinks (or hard links, if you are on the same disk.)

Say a system I work on has a setuid-root script somewhere, like
/sbin/fixperms. It has its own security-checking inside the script, so it's
setuid-root and executable by everyone, or perhaps by a limited group.

Mr. M. Alicious wants to hack me, and he can execute the above script, but
is stopped by the internal security checks. What he does is this:

--- hack.py --
#!/usr/bin/python

import os

os.execv("/bin/sh",("/bin/sh",))
--- hack.py --

hack.py is owned by alicious, just executable, not setuid. Now Mr. A.
creates a symlink to /sbin/fixperms, say, 'runme', and then starts to create
a heavy load on the machine (not necessary, but makes the next step a lot
easier.) preferably by generating lots of swap-activity, or lots of I/O on
the same disk the python executable is located on.

Then Mr. Alicious starts /sbin/fixperms _via the symlink_, and at the same
time sets the symlink to hack.py. He has to take care to replace the symlink
at exactly the right moment, though, between the setuid-bit checks in the
kernel/libc and the opening of the script by python. On a heavily loaded
machine this isn't that big a feat. Python gets started as root, opens
'runme', and gets the contents of hack.py. and exec()'s /bin/sh, giving Mr.
M a nice root-owned shell.

There are a couple of solutions possible, unfortunately, most of these are
incompatible in some minor way with how it is currently done. The most
common one is not to pass the script to be run by the interpreter as a
command line, but instead as an open filedescriptor, fd 3. The interpreter
would have to be altered to accept that, however(*), and since UNIX in
general has a lot of different interpreters.. icky.

Another option would be for the python interpreter itself to check for
setuid bits... I only thought that up just now, so I'm not sure if there's a
problem with that, but now that I look at the perlsec manpage, I believe
this is what suidperl does; Python could check for setuid or setgid bits on
the scripts it is about to execute, and invoke a special setuid-root part of
the interpreter (seperate binary, of course) to re-invoke python with the
proper userid/groupid (in a race-free manner, such as passing an open fd.)
Perhaps for backward compatibility it would be best only to invoke the
setuid part of python if python is started with, say, the -s option.

Any takers on that idea ? It wouldn't be hard to write, I bet ;) But then,
it's probably already been suggested and rejected before ;)

*) on Linux systems, passing an open fd is actually fairly easy and fairly
compatible; old (or perhaps just all) interpreters could be started with
'/proc/fd/3' as the script. There was talk about this on the linux kernel
list a year or so ago (and probably more often before and after that) but
the problem was, and probably still is, that it would break interpreters
that rely on opening a filedescriptor right after starting and assuming it
will be fd 3.

Paranoid-android-ly y'rs,
--
Thomas Wouters <tho...@xs4all.net>

Hi! I'm a .signature virus! copy me into your .signature file to help me spread!


Gene Chiaramonte

unread,
Jan 31, 2000, 3:00:00 AM1/31/00
to pytho...@python.org
Does anyone know of a Python Module for Codebase from Sequiter?

Thanks,

Gene


Ivan Van Laningham

unread,
Jan 31, 2000, 3:00:00 AM1/31/00
to Python Mailing List
Hi All--

Clarence Gardner wrote:
>
> Thomas Wouters <tho...@xs4all.net> wrote:
> : *) on Linux systems, passing an open fd is actually fairly easy and fairly


> : compatible; old (or perhaps just all) interpreters could be started with
> : '/proc/fd/3' as the script. There was talk about this on the linux kernel
> : list a year or so ago (and probably more often before and after that) but
> : the problem was, and probably still is, that it would break interpreters
> : that rely on opening a filedescriptor right after starting and assuming it
> : will be fd 3.
>

> What interpreter is so braindead as to assume that particular file
> descriptors are available when it is invoked? And even if there are
> any, catering to them is worse than all of the Microsoft backward-
> compatibility-to-1985 hacks put together, IMNSHO.
>

stdin = fd 0
stdout = fd 1
stderr = fd2
next fd you ask for = fd3

Not braindead at all. Just a nice tradition, which is observed on
unices & their descendents, but not on M$.

<oh-poop-where-did-fd-1-go?>-ly y'rs,
Ivan
----------------------------------------------
Ivan Van Laningham
Callware Technologies, Inc.
iva...@callware.com
iva...@home.com
http://www.pauahtun.org
See also:
http://www.foretec.com/python/workshops/1998-11/proceedings.html
Army Signal Corps: Cu Chi, Class of '70
Author: Teach Yourself Python in 24 Hours
----------------------------------------------


Clarence Gardner

unread,
Feb 1, 2000, 3:00:00 AM2/1/00
to
Thomas Wouters <tho...@xs4all.net> wrote:
: *) on Linux systems, passing an open fd is actually fairly easy and fairly
: compatible; old (or perhaps just all) interpreters could be started with
: '/proc/fd/3' as the script. There was talk about this on the linux kernel
: list a year or so ago (and probably more often before and after that) but
: the problem was, and probably still is, that it would break interpreters
: that rely on opening a filedescriptor right after starting and assuming it
: will be fd 3.

What interpreter is so braindead as to assume that particular file
descriptors are available when it is invoked? And even if there are
any, catering to them is worse than all of the Microsoft backward-
compatibility-to-1985 hacks put together, IMNSHO.

--

Kelly Lynn Martin

unread,
Feb 1, 2000, 3:00:00 AM2/1/00
to Clarence Gardner
On Mon, 31 Jan 2000 18:04:15 GMT, Clarence Gardner <clar...@beach.silcom.com> said:

>This is not true, and is a myth people need to get over. The danger
>Kelly referred to exists on some Unix-like systems and not on others.
>On a system where they are safe, there is no reason whatsoever to use
>a setuid wrapper.

Of course, not every system is safe. Unless you know your system is
secure, don't assume it is.

Kelly


Fredrik Lundh

unread,
Feb 1, 2000, 3:00:00 AM2/1/00
to Clarence Gardner
Clarence Gardner <clar...@beach.silcom.com> wrote:
> What interpreter is so braindead as to assume that particular file
> descriptors are available when it is invoked? And even if there are
> any, catering to them is worse than all of the Microsoft backward-
> compatibility-to-1985 hacks put together, IMNSHO.

umm. how about catering to the Single UNIX
Specification? the following is required to be
true for any program running under Unix:

...

At program startup, three streams are predefined and need
not be opened explicitly: standard input (for reading conventional
input), standard output (for writing conventional output), and
standard error (for writing diagnostic output).

...

The following symbolic constants are defined for file streams:

STDIN_FILENO
File number of stdin. It is 0.

STDOUT_FILENO
File number of stdout. It is 1.

STDERR_FILENO
File number of stderr. It is 2.

...

(the last version of that spec is from 1997, and I doubt
Microsoft was involved in writing it ;-)

</F>

Gordon McMillan

unread,
Feb 1, 2000, 3:00:00 AM2/1/00
to Ivan Van Laningham, Python Mailing List
Ivan Van Laningham wrote:

>
> stdin = fd 0
> stdout = fd 1
> stderr = fd2
> next fd you ask for = fd3
>
> Not braindead at all. Just a nice tradition, which is observed on
> unices & their descendents, but not on M$.

Python 1.5.2 (#0, Apr 13 1999, 10:51:12) [MSC 32 bit (Intel)] on win32
Copyright 1991-1995 Stichting Mathematisch Centrum, Amsterdam
>>> import sys
>>> sys.stdin.fileno()
0
>>> sys.stdout.fileno()
1
>>> sys.stderr.fileno()
2
>>>

It's only a GUI on MS that has no concept of std*. A "feature"
they stole from a Mac, I guess.

- Gordon


Clarence Gardner

unread,
Feb 1, 2000, 3:00:00 AM2/1/00
to
Clarence Gardner <clar...@beach.silcom.com> wrote:
: What interpreter is so braindead as to assume that particular file
: descriptors are available when it is invoked? And even if there are
: any, catering to them is worse than all of the Microsoft backward-
: compatibility-to-1985 hacks put together, IMNSHO.

To which Ivan Van Laningham <iv...@callware.com> replied:


>stdin = fd 0
>stdout = fd 1
>stderr = fd2
>next fd you ask for = fd3
>Not braindead at all. Just a nice tradition, which is observed on
>unices & their descendents, but not on M$.

and Fredrik Lundh mentioned the Single Unix Specification


> At program startup, three streams are predefined and need
> not be opened explicitly: standard input (for reading conventional
> input), standard output (for writing conventional output), and
> standard error (for writing diagnostic output).

> The following symbolic constants are defined for file streams:
> STDIN_FILENO
> File number of stdin. It is 0.
> STDOUT_FILENO
> File number of stdout. It is 1.
> STDERR_FILENO
> File number of stderr. It is 2.

What I said was braindead was the assumption of the file descriptor
state. Sure, if fds 0,1,2 are open, *and no others are*, then the next
file you open will be on fd 3. That is more than a Unix tradition, it
is an absolute requirement for any Unix kernel. That is, after all, why
most often the file descriptor that the script text is open on would be 3.
But there is no reason in the world to require that fd 3 was not already
open to something else. (My use of /dev/fd/6 as an example in my
original message was not to say that the fd will be arbitrary, but it
can be unknowable in advance.)

The part of the SUS that /F quotes (I haven't read it) sounds like it is
talking about C (certainly the symbolic constants are), and to be picky,
which one must when referring to specifications, that neither says that
no other fds (not streams, which is a C issue) will be open, but it
doesn't even require that fds 0, 1, or 2 be open. If, for whatever
reason, fd 1 was not open when your program started, stdout would still
be properly defined and initialized in your program -- you would just
get an error if you tried to write to it. This is, of course, unusual.
But the spec can hardly guarantee the state that your program starts in.
It cannot guarantee that it was not started by this program:
#include <unistd.h>
#include <fcntl.h>
int main(void)
{ int three = open("/", "rb");
fcntl(three, F_SETFD, 0);
close(1);
execl("/yourprogram", 0);
}

And similarly, to get back to the issue (and to the reasonable world:) ),
there is nothing at all wrong with running a setuid script like this:
$ setuidscript 3</etc/passwd
which, even in a perfectly normal environment with a perfectly normal shell,
will (on the safe systems under discussion) deliver the script text to the
interpreter on file descriptor 4.

Cameron Laird

unread,
Feb 1, 2000, 3:00:00 AM2/1/00
to
In article <058AFBA1CD7F1621.791F88D0...@lp.airnews.net>,
I remarked:

>In article <8737c1$76d$1...@news.cz.js.cn>, 周公 <jfz...@188.net> wrote:
.
.

.
>>2:use expect mod ,but python dosn't have.
>>
>>is there better solution?
> .
> .
> .
>As best I can understand,
> use expect mod ,but python dosn't have.
>refers to Expect.pm, and has no particular relation to
>WWW, suid, sgid, or other elements of this post.
>
>In fact Python does have analogues to Expect.pm. The
>little research I've done indicates that they're not
>well-researched. I've been considering writing up a
.
.
.
I made two errors in what I sent before. The sentence immedi-
ately above should have read
... they're not well-maintained.
Moreover, I hiccoughed, and left out a paragraph on the module
that addresses this domain and *is* well-maintained: telnetlib
<URL:http://www.python.org/doc/current/lib/module-telnetlib.html>
I apologize for the confusion.

Anders M Eriksson

unread,
Feb 2, 2000, 3:00:00 AM2/2/00
to
On Mon, 31 Jan 2000 16:24:30 -0400, "Gene Chiaramonte"
<gchiar...@ibl.bm> wrote:

>Does anyone know of a Python Module for Codebase from Sequiter?
>

Nope!

But since Codebase comes for C/C++ or Java it shouldn't be hard (.now
I'm guessing cause I haven't tried.) to create one.

An another way could be to use the Codebase ODBC drivers and mxODBC

If you find any module or create one, I would be interested!!

// Anders
--
English isn't my first or second language,
so errors or anything that you find offending is not there on
purpose it's just due to the translation.

Michael P. Reilly

unread,
Feb 3, 2000, 3:00:00 AM2/3/00
to
Cameron Laird <cla...@starbase.neosoft.com> wrote:
: In article <058AFBA1CD7F1621.791F88D0...@lp.airnews.net>,
: I remarked:
:>In article <8737c1$76d$1...@news.cz.js.cn>, XXXX <jfz...@188.net> wrote:
: ^I^I^I.
: ^I^I^I.
: ^I^I^I.
:>>2:use expect mod ,but python dosn't have.
:>>
:>>is there better solution?
:>^I^I^I.
:>^I^I^I.
:>^I^I^I.
:>As best I can understand,

:> use expect mod ,but python dosn't have.
:>refers to Expect.pm, and has no particular relation to
:>WWW, suid, sgid, or other elements of this post.
:>
:>In fact Python does have analogues to Expect.pm. The
:>little research I've done indicates that they're not
:>well-researched. I've been considering writing up a
: ^I^I^I.
: ^I^I^I.
: ^I^I^I.
: I made two errors in what I sent before. The sentence immedi-

: ately above should have read
: ... they're not well-maintained.
: Moreover, I hiccoughed, and left out a paragraph on the module
: that addresses this domain and *is* well-maintained: telnetlib
: <URL:http://www.python.org/doc/current/lib/module-telnetlib.html>
: I apologize for the confusion.

If we are talking about Expect-like functionality, then you are missing
the "pty" standard module and ExpectPy.

ExpectPy is maintained; it is available at
<URL:http://starship.python.net/crew/arcege/ExpectPy/>

The expy module is more than five years old.

-Arcege


0 new messages