[Python-checkins] python/dist/src/Lib os.py,1.50.8.2,1.50.8.3

gvanrossum@users.sourceforge.net gvanrossum@users.sourceforge.net
Thu, 08 Aug 2002 12:35:56 -0700


Update of /cvsroot/python/python/dist/src/Lib
In directory usw-pr-cvs1:/tmp/cvs-serv24650

Modified Files:
      Tag: release22-maint
	os.py 
Log Message:
Backport of SF patch 590294: os._execvpe security fix (Zack Weinberg).

1) Do not attempt to exec a file which does not exist
just to find out what error the operating system
returns. This is an exploitable race on all platforms
that support symbolic links.

2) Immediately re-raise the exception if we get an
error other than errno.ENOENT or errno.ENOTDIR. This
may need to be adapted for other platforms.


Index: os.py
===================================================================
RCS file: /cvsroot/python/python/dist/src/Lib/os.py,v
retrieving revision 1.50.8.2
retrieving revision 1.50.8.3
diff -C2 -d -r1.50.8.2 -r1.50.8.3
*** os.py	16 Mar 2002 18:02:20 -0000	1.50.8.2
--- os.py	8 Aug 2002 19:35:53 -0000	1.50.8.3
***************
*** 309,314 ****
  __all__.extend(["execl","execle","execlp","execlpe","execvp","execvpe"])
  
- _notfound = None
  def _execvpe(file, args, env=None):
      if env is not None:
          func = execve
--- 309,315 ----
  __all__.extend(["execl","execle","execlp","execlpe","execvp","execvpe"])
  
  def _execvpe(file, args, env=None):
+     from errno import ENOENT, ENOTDIR
+ 
      if env is not None:
          func = execve
***************
*** 318,322 ****
          argrest = (args,)
          env = environ
!     global _notfound
      head, tail = path.split(file)
      if head:
--- 319,323 ----
          argrest = (args,)
          env = environ
! 
      head, tail = path.split(file)
      if head:
***************
*** 328,346 ****
          envpath = defpath
      PATH = envpath.split(pathsep)
-     if not _notfound:
-         if sys.platform[:4] == 'beos':
-             #  Process handling (fork, wait) under BeOS (up to 5.0)
-             #  doesn't interoperate reliably with the thread interlocking
-             #  that happens during an import.  The actual error we need
-             #  is the same on BeOS for posix.open() et al., ENOENT.
-             try: unlink('/_#.# ## #.#')
-             except error, _notfound: pass
-         else:
-             import tempfile
-             t = tempfile.mktemp()
-             # Exec a file that is guaranteed not to exist
-             try: execv(t, ('blah',))
-             except error, _notfound: pass
-     exc, arg = error, _notfound
      for dir in PATH:
          fullname = path.join(dir, file)
--- 329,332 ----
***************
*** 348,355 ****
              apply(func, (fullname,) + argrest)
          except error, (errno, msg):
!             if errno != arg[0]:
!                 exc, arg = error, (errno, msg)
!     raise exc, arg
! 
  
  # Change environ to automatically call putenv() if it exists
--- 334,340 ----
              apply(func, (fullname,) + argrest)
          except error, (errno, msg):
!             if errno != ENOENT and errno != ENOTDIR:
!                 raise
!     raise error, (errno, msg)
  
  # Change environ to automatically call putenv() if it exists