SF bug #1473760 TempFile can hang on Windows.

Python 2.4 changed ntpath.abspath to do an import
inside the function.  As a result, due to Python's
import lock, anything calling abspath on Windows
(directly, or indirectly like tempfile.TemporaryFile)
hung when it was called from a thread spawned as a
side effect of importing a module.

This is a depressingly frequent problem, and
deserves a more general fix.  I'm settling for
a micro-fix here because this specific one accounts
for a report of Zope Corp's ZEO hanging on Windows,
and it was an odd way to change abspath to begin
with (ntpath needs a different implementation
depending on whether we're actually running on
Windows, and the _obvious_ way to arrange for that
is not to bury a possibly-failing import _inside_
the function).

Note that if/when other micro-fixes of this kind
get made, the new Lib/test/threaded_import_hangers.py
is a convenient place to add tests for them.
This commit is contained in:
Tim Peters 2006-04-21 21:18:10 +00:00
parent 9f7e58afa7
commit 21fbd57d66
4 changed files with 86 additions and 21 deletions

View file

@ -481,27 +481,28 @@ def normpath(path):
# Return an absolute path.
def abspath(path):
"""Return the absolute version of a path"""
try:
from nt import _getfullpathname
except ImportError: # Not running on Windows - mock up something sensible.
global abspath
def _abspath(path):
if not isabs(path):
path = join(os.getcwd(), path)
return normpath(path)
abspath = _abspath
return _abspath(path)
try:
from nt import _getfullpathname
if path: # Empty path must return current working directory.
try:
path = _getfullpathname(path)
except WindowsError:
pass # Bad path - return unchanged.
else:
path = os.getcwd()
return normpath(path)
except ImportError: # not running on Windows - mock up something sensible
def abspath(path):
"""Return the absolute version of a path."""
if not isabs(path):
path = join(os.getcwd(), path)
return normpath(path)
else: # use native Windows method on Windows
def abspath(path):
"""Return the absolute version of a path."""
if path: # Empty path must return current working directory.
try:
path = _getfullpathname(path)
except WindowsError:
pass # Bad path - return unchanged.
else:
path = os.getcwd()
return normpath(path)
# realpath is a no-op on systems without islink support
realpath = abspath