[Python-checkins] r81062 - in python/branches/py3k-jit: Doc/library/_dummy_thread.rst Doc/library/_thread.rst Doc/library/datetime.rst Doc/library/html.parser.rst Doc/library/http.client.rst Doc/library/http.cookiejar.rst Doc/library/http.cookies.rst Doc/library/http.server.rst Doc/library/os.path.rst Doc/library/os.rst Doc/library/posix.rst Doc/library/tkinter.scrolledtext.rst Doc/library/tkinter.tix.rst Doc/library/tkinter.ttk.rst Doc/library/turtle.rst Doc/library/unittest.rst Doc/library/weakref.rst Doc/library/winreg.rst Doc/library/xmlrpc.client.rst Doc/library/xmlrpc.server.rst Include/unicodeobject.h Lib/_dummy_thread.py Lib/compileall.py Lib/dbm/dumb.py Lib/email/test/test_email_codecs.py Lib/http/client.py Lib/http/cookiejar.py Lib/http/cookies.py Lib/http/server.py Lib/lib2to3/fixes/fix_import.py Lib/lib2to3/fixes/fix_operator.py Lib/lib2to3/fixes/fix_reduce.py Lib/lib2to3/fixes/fix_tuple_params.py Lib/lib2to3/fixes/fix_xrange.py Lib/lib2to3/main.py Lib/lib2to3/pgen2/tokenize.py Lib/lib2to3/pytree.py Lib/lib2to3/refactor.py Lib/lib2to3/tests/test_fixers.py Lib/lib2to3/tests/test_parser.py Lib/lib2to3/tests/test_pytree.py Lib/lib2to3/tests/test_refactor.py Lib/os.py Lib/py_compile.py Lib/site.py Lib/subprocess.py Lib/sysconfig.py Lib/test/regrtest.py Lib/test/test_datetime.py Lib/test/test_dbm.py Lib/test/test_dbm_dumb.py Lib/test/test_dbm_gnu.py Lib/test/test_dbm_ndbm.py Lib/test/test_enumerate.py Lib/test/test_http_cookiejar.py Lib/test/test_http_cookies.py Lib/test/test_os.py Lib/test/test_posix.py Lib/test/test_signal.py Lib/test/test_subprocess.py Lib/test/test_sysconfig.py Lib/test/test_ttk_guionly.py Lib/test/test_ttk_textonly.py Lib/test/test_urllib2.py Lib/test/test_urlparse.py Lib/test/test_zlib.py Lib/tkinter/__init__.py Lib/tkinter/_fix.py Lib/tkinter/colorchooser.py Lib/tkinter/commondialog.py Lib/tkinter/constants.py Lib/tkinter/dialog.py Lib/tkinter/dnd.py Lib/tkinter/filedialog.py Lib/tkinter/font.py Lib/tkinter/messagebox.py Lib/tkinter/scrolledtext.py Lib/tkinter/simpledialog.py Lib/tkinter/test/support.py Lib/tkinter/tix.py Lib/turtle.py Lib/unittest/case.py Lib/unittest/loader.py Lib/unittest/main.py Lib/unittest/suite.py Lib/unittest/test/test_discovery.py Lib/unittest/test/test_program.py Lib/unittest/test/test_runner.py Lib/unittest/test/test_suite.py Lib/urllib/request.py Lib/xmlrpc/client.py Lib/xmlrpc/server.py Misc/NEWS Modules/_dbmmodule.c Modules/_gdbmmodule.c Modules/_io/_iomodule.c Modules/_io/_iomodule.h Modules/_io/bufferedio.c Modules/_io/bytesio.c Modules/_io/fileio.c Modules/_io/iobase.c Modules/_io/stringio.c Modules/_io/textio.c Modules/_threadmodule.c Modules/datetimemodule.c Modules/grpmodule.c Modules/posixmodule.c Modules/pwdmodule.c Modules/signalmodule.c Modules/spwdmodule.c Modules/zlibmodule.c Objects/codeobject.c Objects/longobject.c Objects/moduleobject.c PC/os2emx/python27.def PC/winreg.c Python/errors.c Python/pythonrun.c
jeffrey.yasskin
python-checkins at python.org
Mon May 10 23:19:58 CEST 2010
Author: jeffrey.yasskin
Date: Mon May 10 23:19:57 2010
New Revision: 81062
Log:
Merged revisions 80885,80887-80893,80897,80900,80902,80904-80905,80910,80919,80921,80923,80925,80928,80933,80936,80938,80940,80947-80950,80955,80959,80962,80968,80971,80973,80975,80979,80981,80983,80989,80992-80993,80999,81001,81003,81005-81006,81009-81010,81014,81016-81017,81019,81021,81023-81024,81028 via svnmerge from
svn+ssh://pythondev@svn.python.org/python/branches/py3k
................
r80885 | victor.stinner | 2010-05-06 15:05:07 -0700 (Thu, 06 May 2010) | 7 lines
Issue #8603: Create a bytes version of os.environ for Unix
Create os.environb mapping and os.getenvb() function, os.unsetenv() encodes str
argument to the file system encoding with the surrogateescape error handler
(instead of utf8/strict) and accepts bytes, and posix.environ keys and values
are bytes.
................
r80887 | benjamin.peterson | 2010-05-06 15:09:03 -0700 (Thu, 06 May 2010) | 1 line
versionadded for environb
................
r80888 | benjamin.peterson | 2010-05-06 15:13:11 -0700 (Thu, 06 May 2010) | 1 line
spacing and another versionadded
................
r80889 | victor.stinner | 2010-05-06 15:19:30 -0700 (Thu, 06 May 2010) | 2 lines
Fix test_posix (regression introduced by r80885)
................
r80890 | benjamin.peterson | 2010-05-06 15:23:58 -0700 (Thu, 06 May 2010) | 1 line
use concise skipping
................
r80891 | benjamin.peterson | 2010-05-06 15:25:42 -0700 (Thu, 06 May 2010) | 1 line
wrap long lines
................
r80892 | benjamin.peterson | 2010-05-06 15:26:31 -0700 (Thu, 06 May 2010) | 1 line
self.skip -> self.skipTest
................
r80893 | benjamin.peterson | 2010-05-06 15:29:53 -0700 (Thu, 06 May 2010) | 1 line
rephrase
................
r80897 | benjamin.peterson | 2010-05-06 16:03:05 -0700 (Thu, 06 May 2010) | 13 lines
Merged revisions 80894,80896 via svnmerge from
svn+ssh://pythondev@svn.python.org/python/trunk
........
r80894 | benjamin.peterson | 2010-05-06 17:33:46 -0500 (Thu, 06 May 2010) | 1 line
Availability gets its own line
........
r80896 | benjamin.peterson | 2010-05-06 17:49:28 -0500 (Thu, 06 May 2010) | 1 line
ensure that availability information is on its own line at the end of the function docs
........
................
r80900 | victor.stinner | 2010-05-06 17:41:18 -0700 (Thu, 06 May 2010) | 4 lines
code_repr(): use %U to format the filename
Avoid useless unicode decoding/recoding of the filename.
................
r80902 | victor.stinner | 2010-05-06 17:50:12 -0700 (Thu, 06 May 2010) | 4 lines
module_repr(): use %U to format the file name
Avoid useless encode/decode of the filename
................
r80904 | victor.stinner | 2010-05-06 17:54:14 -0700 (Thu, 06 May 2010) | 2 lines
Fix test_os: os.environb doesn't exist on Windows
................
r80905 | victor.stinner | 2010-05-06 17:57:12 -0700 (Thu, 06 May 2010) | 4 lines
regrtest.py: disable replace_stdout() on Windows until it is fixed
See issue #8533 (problem with newlines on Windows).
................
r80910 | senthil.kumaran | 2010-05-06 21:19:23 -0700 (Thu, 06 May 2010) | 9 lines
Merged revisions 80908 via svnmerge from
svn+ssh://pythondev@svn.python.org/python/trunk
........
r80908 | senthil.kumaran | 2010-05-07 09:37:29 +0530 (Fri, 07 May 2010) | 3 lines
Testsuite for RFC3986 based parsing scenario. Related Issue1462525.
........
................
r80919 | michael.foord | 2010-05-07 08:35:24 -0700 (Fri, 07 May 2010) | 9 lines
Merged revisions 80918 via svnmerge from
svn+ssh://pythondev@svn.python.org/python/trunk
........
r80918 | michael.foord | 2010-05-07 17:34:08 +0200 (Fri, 07 May 2010) | 1 line
Adding a test for unittest test discovery with dotted path name.
........
................
r80921 | michael.foord | 2010-05-07 09:00:30 -0700 (Fri, 07 May 2010) | 9 lines
Merged revisions 80920 via svnmerge from
svn+ssh://pythondev@svn.python.org/python/trunk
........
r80920 | michael.foord | 2010-05-07 17:52:05 +0200 (Fri, 07 May 2010) | 1 line
Adding tests for unittest command line handling of buffer, catchbreak and failfast.
........
................
r80923 | victor.stinner | 2010-05-07 09:34:53 -0700 (Fri, 07 May 2010) | 3 lines
Replace PyUnicode_Decode(buf, strlen(buf), Py_FileSystemDefaultEncoding,
"surrogateescape") by PyUnicode_DecodeFSDefault(val).
................
r80925 | benjamin.peterson | 2010-05-07 09:42:51 -0700 (Fri, 07 May 2010) | 1 line
correct call
................
r80928 | antoine.pitrou | 2010-05-07 10:04:02 -0700 (Fri, 07 May 2010) | 11 lines
Merged revisions 80926 via svnmerge from
svn+ssh://pythondev@svn.python.org/python/trunk
........
r80926 | antoine.pitrou | 2010-05-07 18:50:34 +0200 (ven., 07 mai 2010) | 5 lines
Issue #8571: Fix an internal error when compressing or decompressing a
chunk larger than 1GB with the zlib module's compressor and decompressor
objects.
........
................
r80933 | michael.foord | 2010-05-07 11:18:14 -0700 (Fri, 07 May 2010) | 9 lines
Merged revisions 80932 via svnmerge from
svn+ssh://pythondev@svn.python.org/python/trunk
........
r80932 | michael.foord | 2010-05-07 20:16:19 +0200 (Fri, 07 May 2010) | 1 line
Issue 8547 - detecting and reporting that modules have been imported from the wrong location under test discovery.
........
................
r80936 | benjamin.peterson | 2010-05-07 12:10:11 -0700 (Fri, 07 May 2010) | 76 lines
Merged revisions 80934 via svnmerge from
svn+ssh://pythondev@svn.python.org/python/trunk
................
r80934 | benjamin.peterson | 2010-05-07 13:58:23 -0500 (Fri, 07 May 2010) | 69 lines
Merged revisions 79911,79916-79917,80018,80418,80572-80573,80635-80639,80668,80922 via svnmerge from
svn+ssh://pythondev@svn.python.org/sandbox/trunk/2to3/lib2to3
........
r79911 | benjamin.peterson | 2010-04-09 15:38:53 -0500 (Fri, 09 Apr 2010) | 1 line
use absolute import
........
r79916 | benjamin.peterson | 2010-04-09 16:05:21 -0500 (Fri, 09 Apr 2010) | 1 line
generalize detection of __future__ imports and attach them to the tree
........
r79917 | benjamin.peterson | 2010-04-09 16:11:44 -0500 (Fri, 09 Apr 2010) | 1 line
don't try to 'fix' relative imports when absolute_import is enabled #8858
........
r80018 | benjamin.peterson | 2010-04-12 16:12:12 -0500 (Mon, 12 Apr 2010) | 4 lines
prevent diffs from being mangled is multiprocess mode #6409
Patch by George Boutsioukis.
........
r80418 | benjamin.peterson | 2010-04-23 16:00:03 -0500 (Fri, 23 Apr 2010) | 1 line
remove unhelpful description
........
r80572 | benjamin.peterson | 2010-04-27 20:33:54 -0500 (Tue, 27 Apr 2010) | 1 line
use unicode literals
........
r80573 | jeffrey.yasskin | 2010-04-27 23:08:27 -0500 (Tue, 27 Apr 2010) | 6 lines
Don't transform imports that are already relative. 2to3 turned
from . import refactor
into
from .. import refactor
which broke the transformation of 2to3 itself.
........
r80635 | benjamin.peterson | 2010-04-29 16:02:23 -0500 (Thu, 29 Apr 2010) | 1 line
remove imports
........
r80636 | benjamin.peterson | 2010-04-29 16:02:41 -0500 (Thu, 29 Apr 2010) | 1 line
unicode literal
........
r80637 | benjamin.peterson | 2010-04-29 16:03:42 -0500 (Thu, 29 Apr 2010) | 1 line
must pass a string to Number
........
r80638 | benjamin.peterson | 2010-04-29 16:05:34 -0500 (Thu, 29 Apr 2010) | 1 line
unicode literals
........
r80639 | benjamin.peterson | 2010-04-29 16:06:09 -0500 (Thu, 29 Apr 2010) | 1 line
pass string to Number
........
r80668 | jeffrey.yasskin | 2010-04-30 18:02:47 -0500 (Fri, 30 Apr 2010) | 4 lines
Make 2to3 run under Python 2.5 so that the benchmark suite at
http://hg.python.org/benchmarks/ can use it and still run on implementations
that haven't gotten to 2.6 yet. Fixes issue 8566.
........
r80922 | benjamin.peterson | 2010-05-07 11:06:25 -0500 (Fri, 07 May 2010) | 1 line
prevent xrange transformation from wrapping range calls it produces in list
........
................
................
r80938 | benjamin.peterson | 2010-05-07 13:21:26 -0700 (Fri, 07 May 2010) | 1 line
alias PyUnicode_CompareWithASCII
................
r80940 | benjamin.peterson | 2010-05-07 13:47:43 -0700 (Fri, 07 May 2010) | 9 lines
Merged revisions 80939 via svnmerge from
svn+ssh://pythondev@svn.python.org/python/trunk
........
r80939 | benjamin.peterson | 2010-05-07 15:45:07 -0500 (Fri, 07 May 2010) | 1 line
revert r80932; it breaks windows
........
................
r80947 | michael.foord | 2010-05-07 16:42:40 -0700 (Fri, 07 May 2010) | 9 lines
Merged revisions 80946 via svnmerge from
svn+ssh://pythondev@svn.python.org/python/trunk
........
r80946 | michael.foord | 2010-05-08 01:39:38 +0200 (Sat, 08 May 2010) | 1 line
Issue 8547 - detecting and reporting that modules have been imported from the wrong location under test discovery.
........
................
r80948 | victor.stinner | 2010-05-07 17:07:07 -0700 (Fri, 07 May 2010) | 2 lines
err_input(): don't encode/decode the unicode message
................
r80949 | victor.stinner | 2010-05-07 17:35:33 -0700 (Fri, 07 May 2010) | 3 lines
PyErr_SetFromErrnoWithFilename() decodes the filename using
PyUnicode_DecodeFSDefault() instead of PyUnicode_FromString()
................
r80950 | victor.stinner | 2010-05-07 17:36:42 -0700 (Fri, 07 May 2010) | 5 lines
posix_error_with_allocated_filename() decodes the filename with
PyUnicode_DecodeFSDefaultAndSize() and call
PyErr_SetFromErrnoWithFilenameObject() instead of
PyErr_SetFromErrnoWithFilename()
................
r80955 | senthil.kumaran | 2010-05-07 20:29:09 -0700 (Fri, 07 May 2010) | 9 lines
Merged revisions 80953 via svnmerge from
svn+ssh://pythondev@svn.python.org/python/trunk
........
r80953 | senthil.kumaran | 2010-05-08 08:41:50 +0530 (Sat, 08 May 2010) | 3 lines
Fix Issue8656 - urllib2 mangles file://-scheme URLs
........
................
r80959 | senthil.kumaran | 2010-05-07 22:12:05 -0700 (Fri, 07 May 2010) | 9 lines
Merged revisions 80957 via svnmerge from
svn+ssh://pythondev@svn.python.org/python/trunk
........
r80957 | senthil.kumaran | 2010-05-08 10:30:11 +0530 (Sat, 08 May 2010) | 2 lines
Fixing the errors trigerred in test_urllib2net. Related to issue8656.
........
................
r80962 | mark.dickinson | 2010-05-08 01:03:09 -0700 (Sat, 08 May 2010) | 9 lines
Merged revisions 80961 via svnmerge from
svn+ssh://pythondev@svn.python.org/python/trunk
........
r80961 | mark.dickinson | 2010-05-08 09:01:19 +0100 (Sat, 08 May 2010) | 2 lines
Issue #8659: Remove redundant ABS calls. Thanks Daniel Stutzbach.
........
................
r80968 | ronald.oussoren | 2010-05-08 03:49:43 -0700 (Sat, 08 May 2010) | 11 lines
Merged revisions 80967 via svnmerge from
svn+ssh://pythondev@svn.python.org/python/trunk
........
r80967 | ronald.oussoren | 2010-05-08 12:29:06 +0200 (Sat, 08 May 2010) | 4 lines
Issue #8084: ensure that the --user directory
conforms to platforms standars on OSX when
using a python framework.
........
................
r80971 | victor.stinner | 2010-05-08 04:10:09 -0700 (Sat, 08 May 2010) | 3 lines
Issue #8514: Add os.fsencode() function (Unix only): encode a string to bytes
for use in the file system, environment variables or the command line.
................
r80973 | matthias.klose | 2010-05-08 04:12:56 -0700 (Sat, 08 May 2010) | 27 lines
Blocked revisions 80964-80966,80969-80970 via svnmerge
........
r80964 | matthias.klose | 2010-05-08 12:00:28 +0200 (Sa, 08 Mai 2010) | 2 lines
- Issue #8510: Update to autoconf2.65.
........
r80965 | matthias.klose | 2010-05-08 12:14:46 +0200 (Sa, 08 Mai 2010) | 2 lines
- configure.in: Replace AC_HELP_STRING with AS_HELP_STRING
........
r80966 | matthias.klose | 2010-05-08 12:17:27 +0200 (Sa, 08 Mai 2010) | 2 lines
configure.in: s/AC_AIX/AC_USE_SYSTEM_EXTENSIONS/
........
r80969 | matthias.klose | 2010-05-08 13:01:39 +0200 (Sa, 08 Mai 2010) | 3 lines
configure.in: convert all obsolete AC_TRY_* macros to AC_*_IFELSE,
only whitespace changes in generated configure (diff -uEwB).
........
r80970 | matthias.klose | 2010-05-08 13:04:18 +0200 (Sa, 08 Mai 2010) | 4 lines
configure.in: Avoid autoconf warning: Assume C89 semantics that
RETSIGTYPE is always void (issue #8510).
pyconfig.h: Regenerate
........
................
r80975 | michael.foord | 2010-05-08 06:23:31 -0700 (Sat, 08 May 2010) | 9 lines
Merged revisions 80974 via svnmerge from
svn+ssh://pythondev@svn.python.org/python/trunk
........
r80974 | michael.foord | 2010-05-08 15:20:07 +0200 (Sat, 08 May 2010) | 1 line
Issue 7780. Adding a test for unittest test discovery from a dotted path.
........
................
r80979 | mark.dickinson | 2010-05-08 07:35:02 -0700 (Sat, 08 May 2010) | 6 lines
Issue #8644: Improve accuracy of timedelta.total_seconds, by doing intermediate
computations with integer arithmetic instead of floating point.
td.total_seconds() now agrees with td / timedelta(seconds = 1).
Thanks Alexander Belopolsky for the patch.
................
r80981 | michael.foord | 2010-05-08 08:13:42 -0700 (Sat, 08 May 2010) | 9 lines
Merged revisions 80980 via svnmerge from
svn+ssh://pythondev@svn.python.org/python/trunk
........
r80980 | michael.foord | 2010-05-08 17:09:37 +0200 (Sat, 08 May 2010) | 1 line
Documenting test discovery from package name and potential problems with test discovery importing tests from the wrong location. Issue 7780 and issue 8547.
........
................
r80983 | benjamin.peterson | 2010-05-08 08:26:30 -0700 (Sat, 08 May 2010) | 1 line
replace long with int
................
r80989 | benjamin.peterson | 2010-05-08 08:51:23 -0700 (Sat, 08 May 2010) | 13 lines
Merged revisions 80986-80987 via svnmerge from
svn+ssh://pythondev@svn.python.org/python/trunk
........
r80986 | benjamin.peterson | 2010-05-08 10:41:44 -0500 (Sat, 08 May 2010) | 1 line
r80967 introduced a new scheme
........
r80987 | benjamin.peterson | 2010-05-08 10:42:29 -0500 (Sat, 08 May 2010) | 1 line
add underscore
........
................
r80992 | michael.foord | 2010-05-08 09:46:14 -0700 (Sat, 08 May 2010) | 9 lines
Merged revisions 80990 via svnmerge from
svn+ssh://pythondev@svn.python.org/python/trunk
........
r80990 | michael.foord | 2010-05-08 18:40:52 +0200 (Sat, 08 May 2010) | 1 line
Updating documentation and adding docstrings to unittest.TestCase.assertRegexpMatches and assertNotRegexpMatches. Issue 8038.
........
................
r80993 | benjamin.peterson | 2010-05-08 09:51:16 -0700 (Sat, 08 May 2010) | 9 lines
Merged revisions 80991 via svnmerge from
svn+ssh://pythondev@svn.python.org/python/trunk
........
r80991 | benjamin.peterson | 2010-05-08 11:44:52 -0500 (Sat, 08 May 2010) | 1 line
run and fix enumerate start test cases #8636
........
................
r80999 | michael.foord | 2010-05-08 10:10:05 -0700 (Sat, 08 May 2010) | 9 lines
Merged revisions 80997 via svnmerge from
svn+ssh://pythondev@svn.python.org/python/trunk
........
r80997 | michael.foord | 2010-05-08 19:06:25 +0200 (Sat, 08 May 2010) | 1 line
unittest: issue 8301. Adding functions to test suites no longer crashes.
........
................
r81001 | gregory.p.smith | 2010-05-08 11:05:46 -0700 (Sat, 08 May 2010) | 2 lines
Adds a unittest for the internal os._execvpe function.
................
r81003 | benjamin.peterson | 2010-05-08 11:57:34 -0700 (Sat, 08 May 2010) | 16 lines
Blocked revisions 80996,80998,81002 via svnmerge
........
r80996 | benjamin.peterson | 2010-05-08 12:05:19 -0500 (Sat, 08 May 2010) | 1 line
update pydoc-topics
........
r80998 | benjamin.peterson | 2010-05-08 12:08:17 -0500 (Sat, 08 May 2010) | 1 line
bump version to 2.7 beta 2
........
r81002 | benjamin.peterson | 2010-05-08 13:53:42 -0500 (Sat, 08 May 2010) | 1 line
towards 2.7 release candidate 1
........
................
r81005 | benjamin.peterson | 2010-05-08 12:52:21 -0700 (Sat, 08 May 2010) | 4 lines
Create __pycache__ dir when the pyc path is explicitly given
Patch from Arfrever Frehtes Taifersar Arahesis.
................
r81006 | benjamin.peterson | 2010-05-08 12:52:49 -0700 (Sat, 08 May 2010) | 1 line
add news for r81005
................
r81009 | benjamin.peterson | 2010-05-08 14:03:44 -0700 (Sat, 08 May 2010) | 8 lines
Blocked revisions 81008 via svnmerge
........
r81008 | benjamin.peterson | 2010-05-08 15:59:42 -0500 (Sat, 08 May 2010) | 1 line
remove svn:mergeinfo property
........
................
r81010 | benjamin.peterson | 2010-05-08 14:05:35 -0700 (Sat, 08 May 2010) | 1 line
remove svn:mergeinfo
................
r81014 | victor.stinner | 2010-05-08 20:15:33 -0700 (Sat, 08 May 2010) | 2 lines
Write tests for the new function os.fsencode()
................
r81016 | jean-paul.calderone | 2010-05-08 20:18:57 -0700 (Sat, 08 May 2010) | 9 lines
Merged revisions 81007 via svnmerge from
svn+ssh://pythondev@svn.python.org/python/trunk
........
r81007 | jean-paul.calderone | 2010-05-08 16:06:02 -0400 (Sat, 08 May 2010) | 1 line
Skip signal handler re-installation if it is not necessary. Issue 8354.
........
................
r81017 | benjamin.peterson | 2010-05-08 20:22:58 -0700 (Sat, 08 May 2010) | 1 line
make condition more specific
................
r81019 | gregory.p.smith | 2010-05-08 20:36:42 -0700 (Sat, 08 May 2010) | 3 lines
Replace /s with os.sep in the new internal_execvpe test. Hopefully fixes
this test on windows.
................
r81021 | mark.dickinson | 2010-05-09 02:30:53 -0700 (Sun, 09 May 2010) | 9 lines
Blocked revisions 81020 via svnmerge
........
r81020 | mark.dickinson | 2010-05-09 10:30:06 +0100 (Sun, 09 May 2010) | 3 lines
Issue #8644: Improve accuracy of timedelta.total_seconds method.
(Backport of r80979 to py3k.) Thanks Alexander Belopolsky.
........
................
r81023 | michael.foord | 2010-05-09 02:59:35 -0700 (Sun, 09 May 2010) | 9 lines
Merged revisions 81022 via svnmerge from
svn+ssh://pythondev@svn.python.org/python/trunk
........
r81022 | michael.foord | 2010-05-09 11:58:25 +0200 (Sun, 09 May 2010) | 1 line
Adding a test for unittest.BaseTestSuite.
........
................
r81024 | mark.dickinson | 2010-05-09 05:16:29 -0700 (Sun, 09 May 2010) | 1 line
Fix test_urllib2 failure on OS X.
................
r81028 | eric.smith | 2010-05-09 07:09:25 -0700 (Sun, 09 May 2010) | 8 lines
Blocked revisions 81026 via svnmerge
........
r81026 | eric.smith | 2010-05-09 10:04:59 -0400 (Sun, 09 May 2010) | 1 line
Issue 8671: Whitespace fix.
........
................
Modified:
python/branches/py3k-jit/ (props changed)
python/branches/py3k-jit/Doc/library/_dummy_thread.rst (props changed)
python/branches/py3k-jit/Doc/library/_thread.rst (props changed)
python/branches/py3k-jit/Doc/library/datetime.rst
python/branches/py3k-jit/Doc/library/html.parser.rst (props changed)
python/branches/py3k-jit/Doc/library/http.client.rst (props changed)
python/branches/py3k-jit/Doc/library/http.cookiejar.rst (props changed)
python/branches/py3k-jit/Doc/library/http.cookies.rst (props changed)
python/branches/py3k-jit/Doc/library/http.server.rst (props changed)
python/branches/py3k-jit/Doc/library/os.path.rst
python/branches/py3k-jit/Doc/library/os.rst
python/branches/py3k-jit/Doc/library/posix.rst
python/branches/py3k-jit/Doc/library/tkinter.scrolledtext.rst (props changed)
python/branches/py3k-jit/Doc/library/tkinter.tix.rst (props changed)
python/branches/py3k-jit/Doc/library/tkinter.ttk.rst (props changed)
python/branches/py3k-jit/Doc/library/turtle.rst (props changed)
python/branches/py3k-jit/Doc/library/unittest.rst
python/branches/py3k-jit/Doc/library/weakref.rst
python/branches/py3k-jit/Doc/library/winreg.rst (props changed)
python/branches/py3k-jit/Doc/library/xmlrpc.client.rst (props changed)
python/branches/py3k-jit/Doc/library/xmlrpc.server.rst (props changed)
python/branches/py3k-jit/Include/unicodeobject.h
python/branches/py3k-jit/Lib/_dummy_thread.py (props changed)
python/branches/py3k-jit/Lib/compileall.py
python/branches/py3k-jit/Lib/dbm/dumb.py (props changed)
python/branches/py3k-jit/Lib/email/test/test_email_codecs.py (props changed)
python/branches/py3k-jit/Lib/http/client.py (props changed)
python/branches/py3k-jit/Lib/http/cookiejar.py (props changed)
python/branches/py3k-jit/Lib/http/cookies.py (props changed)
python/branches/py3k-jit/Lib/http/server.py (props changed)
python/branches/py3k-jit/Lib/lib2to3/fixes/fix_import.py
python/branches/py3k-jit/Lib/lib2to3/fixes/fix_operator.py
python/branches/py3k-jit/Lib/lib2to3/fixes/fix_reduce.py
python/branches/py3k-jit/Lib/lib2to3/fixes/fix_tuple_params.py
python/branches/py3k-jit/Lib/lib2to3/fixes/fix_xrange.py
python/branches/py3k-jit/Lib/lib2to3/main.py
python/branches/py3k-jit/Lib/lib2to3/pgen2/tokenize.py
python/branches/py3k-jit/Lib/lib2to3/pytree.py
python/branches/py3k-jit/Lib/lib2to3/refactor.py
python/branches/py3k-jit/Lib/lib2to3/tests/test_fixers.py
python/branches/py3k-jit/Lib/lib2to3/tests/test_parser.py
python/branches/py3k-jit/Lib/lib2to3/tests/test_pytree.py
python/branches/py3k-jit/Lib/lib2to3/tests/test_refactor.py
python/branches/py3k-jit/Lib/os.py
python/branches/py3k-jit/Lib/py_compile.py
python/branches/py3k-jit/Lib/site.py
python/branches/py3k-jit/Lib/subprocess.py
python/branches/py3k-jit/Lib/sysconfig.py
python/branches/py3k-jit/Lib/test/regrtest.py
python/branches/py3k-jit/Lib/test/test_datetime.py
python/branches/py3k-jit/Lib/test/test_dbm.py (props changed)
python/branches/py3k-jit/Lib/test/test_dbm_dumb.py (props changed)
python/branches/py3k-jit/Lib/test/test_dbm_gnu.py (props changed)
python/branches/py3k-jit/Lib/test/test_dbm_ndbm.py (props changed)
python/branches/py3k-jit/Lib/test/test_enumerate.py
python/branches/py3k-jit/Lib/test/test_http_cookiejar.py (props changed)
python/branches/py3k-jit/Lib/test/test_http_cookies.py (props changed)
python/branches/py3k-jit/Lib/test/test_os.py
python/branches/py3k-jit/Lib/test/test_posix.py
python/branches/py3k-jit/Lib/test/test_signal.py
python/branches/py3k-jit/Lib/test/test_subprocess.py
python/branches/py3k-jit/Lib/test/test_sysconfig.py
python/branches/py3k-jit/Lib/test/test_ttk_guionly.py (props changed)
python/branches/py3k-jit/Lib/test/test_ttk_textonly.py (props changed)
python/branches/py3k-jit/Lib/test/test_urllib2.py
python/branches/py3k-jit/Lib/test/test_urlparse.py
python/branches/py3k-jit/Lib/test/test_zlib.py
python/branches/py3k-jit/Lib/tkinter/__init__.py (props changed)
python/branches/py3k-jit/Lib/tkinter/_fix.py (props changed)
python/branches/py3k-jit/Lib/tkinter/colorchooser.py (props changed)
python/branches/py3k-jit/Lib/tkinter/commondialog.py (props changed)
python/branches/py3k-jit/Lib/tkinter/constants.py (props changed)
python/branches/py3k-jit/Lib/tkinter/dialog.py (props changed)
python/branches/py3k-jit/Lib/tkinter/dnd.py (props changed)
python/branches/py3k-jit/Lib/tkinter/filedialog.py (props changed)
python/branches/py3k-jit/Lib/tkinter/font.py (props changed)
python/branches/py3k-jit/Lib/tkinter/messagebox.py (props changed)
python/branches/py3k-jit/Lib/tkinter/scrolledtext.py (props changed)
python/branches/py3k-jit/Lib/tkinter/simpledialog.py (props changed)
python/branches/py3k-jit/Lib/tkinter/test/support.py (props changed)
python/branches/py3k-jit/Lib/tkinter/tix.py (props changed)
python/branches/py3k-jit/Lib/turtle.py (props changed)
python/branches/py3k-jit/Lib/unittest/case.py
python/branches/py3k-jit/Lib/unittest/loader.py
python/branches/py3k-jit/Lib/unittest/main.py
python/branches/py3k-jit/Lib/unittest/suite.py
python/branches/py3k-jit/Lib/unittest/test/test_discovery.py
python/branches/py3k-jit/Lib/unittest/test/test_program.py
python/branches/py3k-jit/Lib/unittest/test/test_runner.py
python/branches/py3k-jit/Lib/unittest/test/test_suite.py
python/branches/py3k-jit/Lib/urllib/request.py
python/branches/py3k-jit/Lib/xmlrpc/client.py (props changed)
python/branches/py3k-jit/Lib/xmlrpc/server.py (props changed)
python/branches/py3k-jit/Misc/NEWS
python/branches/py3k-jit/Modules/_dbmmodule.c (props changed)
python/branches/py3k-jit/Modules/_gdbmmodule.c (props changed)
python/branches/py3k-jit/Modules/_io/_iomodule.c (props changed)
python/branches/py3k-jit/Modules/_io/_iomodule.h (props changed)
python/branches/py3k-jit/Modules/_io/bufferedio.c (props changed)
python/branches/py3k-jit/Modules/_io/bytesio.c (props changed)
python/branches/py3k-jit/Modules/_io/fileio.c (props changed)
python/branches/py3k-jit/Modules/_io/iobase.c (props changed)
python/branches/py3k-jit/Modules/_io/stringio.c (props changed)
python/branches/py3k-jit/Modules/_io/textio.c (props changed)
python/branches/py3k-jit/Modules/_threadmodule.c (props changed)
python/branches/py3k-jit/Modules/datetimemodule.c
python/branches/py3k-jit/Modules/grpmodule.c
python/branches/py3k-jit/Modules/posixmodule.c
python/branches/py3k-jit/Modules/pwdmodule.c
python/branches/py3k-jit/Modules/signalmodule.c
python/branches/py3k-jit/Modules/spwdmodule.c
python/branches/py3k-jit/Modules/zlibmodule.c
python/branches/py3k-jit/Objects/codeobject.c
python/branches/py3k-jit/Objects/longobject.c
python/branches/py3k-jit/Objects/moduleobject.c
python/branches/py3k-jit/PC/os2emx/python27.def (props changed)
python/branches/py3k-jit/PC/winreg.c (props changed)
python/branches/py3k-jit/Python/errors.c
python/branches/py3k-jit/Python/pythonrun.c
Modified: python/branches/py3k-jit/Doc/library/datetime.rst
==============================================================================
--- python/branches/py3k-jit/Doc/library/datetime.rst (original)
+++ python/branches/py3k-jit/Doc/library/datetime.rst Mon May 10 23:19:57 2010
@@ -287,7 +287,10 @@
.. method:: timedelta.total_seconds()
Return the total number of seconds contained in the duration. Equivalent to
- ``td.microseconds / 1000000 + td.seconds + td.days * 24 * 3600``.
+ ``td / timedelta(seconds=1)``.
+
+ Note that for very large time intervals (greater than 270 years on
+ most platforms) this method will lose microsecond accuracy.
.. versionadded:: 3.2
Modified: python/branches/py3k-jit/Doc/library/os.path.rst
==============================================================================
--- python/branches/py3k-jit/Doc/library/os.path.rst (original)
+++ python/branches/py3k-jit/Doc/library/os.path.rst Mon May 10 23:19:57 2010
@@ -223,19 +223,24 @@
Return a relative filepath to *path* either from the current directory or from
an optional *start* point.
- *start* defaults to :attr:`os.curdir`. Availability: Windows, Unix.
+ *start* defaults to :attr:`os.curdir`.
+
+ Availability: Windows, Unix.
.. function:: samefile(path1, path2)
Return ``True`` if both pathname arguments refer to the same file or directory
(as indicated by device number and i-node number). Raise an exception if a
- :func:`os.stat` call on either pathname fails. Availability: Unix.
+ :func:`os.stat` call on either pathname fails.
+
+ Availability: Unix.
.. function:: sameopenfile(fp1, fp2)
Return ``True`` if the file descriptors *fp1* and *fp2* refer to the same file.
+
Availability: Unix.
@@ -244,7 +249,9 @@
Return ``True`` if the stat tuples *stat1* and *stat2* refer to the same file.
These structures may have been returned by :func:`fstat`, :func:`lstat`, or
:func:`stat`. This function implements the underlying comparison used by
- :func:`samefile` and :func:`sameopenfile`. Availability: Unix.
+ :func:`samefile` and :func:`sameopenfile`.
+
+ Availability: Unix.
.. function:: split(path)
@@ -293,7 +300,9 @@
Split the pathname *path* into a pair ``(unc, rest)`` so that *unc* is the UNC
mount point (such as ``r'\\host\mount'``), if present, and *rest* the rest of
the path (such as ``r'\path\file.ext'``). For paths containing drive letters,
- *unc* will always be the empty string. Availability: Windows.
+ *unc* will always be the empty string.
+
+ Availability: Windows.
.. data:: supports_unicode_filenames
Modified: python/branches/py3k-jit/Doc/library/os.rst
==============================================================================
--- python/branches/py3k-jit/Doc/library/os.rst (original)
+++ python/branches/py3k-jit/Doc/library/os.rst Mon May 10 23:19:57 2010
@@ -41,6 +41,9 @@
* If not separately noted, all functions that claim "Availability: Unix" are
supported on Mac OS X, which builds on a Unix core.
+.. Availability notes get their own line and occur at the end of the function
+.. documentation.
+
.. note::
All functions in this module raise :exc:`OSError` in the case of invalid or
@@ -107,6 +110,10 @@
to modify the environment as well as query the environment. :func:`putenv` will
be called automatically when the mapping is modified.
+ On Unix, keys and values use :func:`sys.getfilesystemencoding` and
+ ``'surrogateescape'`` error handler. Use :data:`environb` if you would like
+ to use a different encoding.
+
.. note::
Calling :func:`putenv` directly does not change ``os.environ``, so it's better
@@ -128,6 +135,18 @@
one of the :meth:`pop` or :meth:`clear` methods is called.
+.. data:: environb
+
+ Bytes version of :data:`environ`: a mapping object representing the
+ environment as byte strings. :data:`environ` and :data:`environb` are
+ synchronized (modify :data:`environb` updates :data:`environ`, and vice
+ versa).
+
+ Availability: Unix.
+
+ .. versionadded:: 3.2
+
+
.. function:: chdir(path)
fchdir(fd)
getcwd()
@@ -136,6 +155,17 @@
These functions are described in :ref:`os-file-dir`.
+.. function:: fsencode(value)
+
+ Encode *value* to bytes for use in the file system, environment variables or
+ the command line. Uses :func:`sys.getfilesystemencoding` and
+ ``'surrogateescape'`` error handler for strings and returns bytes unchanged.
+
+ Availability: Unix.
+
+ .. versionadded:: 3.2
+
+
.. function:: get_exec_path(env=None)
Returns the list of directories that will be searched for a named
@@ -150,33 +180,40 @@
.. function:: ctermid()
Return the filename corresponding to the controlling terminal of the process.
+
Availability: Unix.
.. function:: getegid()
Return the effective group id of the current process. This corresponds to the
- "set id" bit on the file being executed in the current process. Availability:
- Unix.
+ "set id" bit on the file being executed in the current process.
+
+ Availability: Unix.
.. function:: geteuid()
.. index:: single: user; effective id
- Return the current process's effective user id. Availability: Unix.
+ Return the current process's effective user id.
+
+ Availability: Unix.
.. function:: getgid()
.. index:: single: process; group
- Return the real group id of the current process. Availability: Unix.
+ Return the real group id of the current process.
+
+ Availability: Unix.
.. function:: getgroups()
Return list of supplemental group ids associated with the current process.
+
Availability: Unix.
@@ -184,7 +221,9 @@
Call the system initgroups() to initialize the group access list with all of
the groups of which the specified username is a member, plus the specified
- group id. Availability: Unix.
+ group id.
+
+ Availability: Unix.
.. versionadded:: 3.2
@@ -195,40 +234,51 @@
process. For most purposes, it is more useful to use the environment variable
:envvar:`LOGNAME` to find out who the user is, or
``pwd.getpwuid(os.getuid())[0]`` to get the login name of the currently
- effective user id. Availability: Unix.
+ effective user id.
+
+ Availability: Unix.
.. function:: getpgid(pid)
Return the process group id of the process with process id *pid*. If *pid* is 0,
- the process group id of the current process is returned. Availability: Unix.
+ the process group id of the current process is returned.
+ Availability: Unix.
.. function:: getpgrp()
.. index:: single: process; group
- Return the id of the current process group. Availability: Unix.
+ Return the id of the current process group.
+
+ Availability: Unix.
.. function:: getpid()
.. index:: single: process; id
- Return the current process id. Availability: Unix, Windows.
+ Return the current process id.
+
+ Availability: Unix, Windows.
.. function:: getppid()
.. index:: single: process; id of parent
- Return the parent's process id. Availability: Unix.
+ Return the parent's process id.
+
+ Availability: Unix.
.. function:: getresuid()
Return a tuple (ruid, euid, suid) denoting the current process's
- real, effective, and saved user ids. Availability: Unix.
+ real, effective, and saved user ids.
+
+ Availability: Unix.
.. versionadded:: 3.2
@@ -236,7 +286,9 @@
.. function:: getresgid()
Return a tuple (rgid, egid, sgid) denoting the current process's
- real, effective, and saved user ids. Availability: Unix.
+ real, effective, and saved user ids.
+
+ Availability: Unix.
.. versionadded:: 3.2
@@ -245,13 +297,31 @@
.. index:: single: user; id
- Return the current process's user id. Availability: Unix.
+ Return the current process's user id.
+
+ Availability: Unix.
.. function:: getenv(key, default=None)
Return the value of the environment variable *key* if it exists, or
- *default* if it doesn't. Availability: most flavors of Unix, Windows.
+ *default* if it doesn't. *key*, *default* and the result are str.
+
+ On Unix, keys and values are decoded with :func:`sys.getfilesystemencoding`
+ and ``'surrogateescape'`` error handler. Use :func:`os.getenvb` if you
+ would like to use a different encoding.
+
+ Availability: most flavors of Unix, Windows.
+
+
+.. function:: getenvb(key, default=None)
+
+ Return the value of the environment variable *key* if it exists, or
+ *default* if it doesn't. *key*, *default* and the result are bytes.
+
+ Availability: most flavors of Unix.
+
+ .. versionadded:: 3.2
.. function:: putenv(key, value)
@@ -260,8 +330,9 @@
Set the environment variable named *key* to the string *value*. Such
changes to the environment affect subprocesses started with :func:`os.system`,
- :func:`popen` or :func:`fork` and :func:`execv`. Availability: most flavors of
- Unix, Windows.
+ :func:`popen` or :func:`fork` and :func:`execv`.
+
+ Availability: most flavors of Unix, Windows.
.. note::
@@ -276,17 +347,23 @@
.. function:: setegid(egid)
- Set the current process's effective group id. Availability: Unix.
+ Set the current process's effective group id.
+
+ Availability: Unix.
.. function:: seteuid(euid)
- Set the current process's effective user id. Availability: Unix.
+ Set the current process's effective user id.
+
+ Availability: Unix.
.. function:: setgid(gid)
- Set the current process' group id. Availability: Unix.
+ Set the current process' group id.
+
+ Availability: Unix.
.. function:: setgroups(groups)
@@ -294,6 +371,7 @@
Set the list of supplemental group ids associated with the current process to
*groups*. *groups* must be a sequence, and each element must be an integer
identifying a group. This operation is typically available only to the superuser.
+
Availability: Unix.
@@ -301,6 +379,7 @@
Call the system call :cfunc:`setpgrp` or :cfunc:`setpgrp(0, 0)` depending on
which version is implemented (if any). See the Unix manual for the semantics.
+
Availability: Unix.
@@ -308,17 +387,22 @@
Call the system call :cfunc:`setpgid` to set the process group id of the
process with id *pid* to the process group with id *pgrp*. See the Unix manual
- for the semantics. Availability: Unix.
+ for the semantics.
+
+ Availability: Unix.
.. function:: setregid(rgid, egid)
- Set the current process's real and effective group ids. Availability: Unix.
+ Set the current process's real and effective group ids.
+
+ Availability: Unix.
.. function:: setresgid(rgid, egid, sgid)
Set the current process's real, effective, and saved group ids.
+
Availability: Unix.
.. versionadded:: 3.2
@@ -327,6 +411,7 @@
.. function:: setresuid(ruid, euid, suid)
Set the current process's real, effective, and saved user ids.
+
Availibility: Unix.
.. versionadded:: 3.2
@@ -334,18 +419,22 @@
.. function:: setreuid(ruid, euid)
- Set the current process's real and effective user ids. Availability: Unix.
+ Set the current process's real and effective user ids.
+
+ Availability: Unix.
.. function:: getsid(pid)
Call the system call :cfunc:`getsid`. See the Unix manual for the semantics.
+
Availability: Unix.
.. function:: setsid()
Call the system call :cfunc:`setsid`. See the Unix manual for the semantics.
+
Availability: Unix.
@@ -353,7 +442,9 @@
.. index:: single: user; id, setting
- Set the current process's user id. Availability: Unix.
+ Set the current process's user id.
+
+ Availability: Unix.
.. placed in this section since it relates to errno.... a little weak
@@ -361,13 +452,16 @@
Return the error message corresponding to the error code in *code*.
On platforms where :cfunc:`strerror` returns ``NULL`` when given an unknown
- error number, :exc:`ValueError` is raised. Availability: Unix, Windows.
+ error number, :exc:`ValueError` is raised.
+
+ Availability: Unix, Windows.
.. function:: umask(mask)
- Set the current numeric umask and return the previous umask. Availability:
- Unix, Windows.
+ Set the current numeric umask and return the previous umask.
+
+ Availability: Unix, Windows.
.. function:: uname()
@@ -381,8 +475,9 @@
machine)``. Some systems truncate the nodename to 8 characters or to the
leading component; a better way to get the hostname is
:func:`socket.gethostname` or even
- ``socket.gethostbyaddr(socket.gethostname())``. Availability: recent flavors of
- Unix.
+ ``socket.gethostbyaddr(socket.gethostname())``.
+
+ Availability: recent flavors of Unix.
.. function:: unsetenv(key)
@@ -391,13 +486,15 @@
Unset (delete) the environment variable named *key*. Such changes to the
environment affect subprocesses started with :func:`os.system`, :func:`popen` or
- :func:`fork` and :func:`execv`. Availability: most flavors of Unix, Windows.
+ :func:`fork` and :func:`execv`.
When :func:`unsetenv` is supported, deletion of items in ``os.environ`` is
automatically translated into a corresponding call to :func:`unsetenv`; however,
calls to :func:`unsetenv` don't update ``os.environ``, so it is actually
preferable to delete items of ``os.environ``.
+ Availability: most flavors of Unix, Windows.
+
.. _os-newstreams:
@@ -413,7 +510,7 @@
Return an open file object connected to the file descriptor *fd*. The *mode*
and *bufsize* arguments have the same meaning as the corresponding arguments to
- the built-in :func:`open` function. Availability: Unix, Windows.
+ the built-in :func:`open` function.
When specified, the *mode* argument must start with one of the letters
``'r'``, ``'w'``, or ``'a'``, otherwise a :exc:`ValueError` is raised.
@@ -422,6 +519,8 @@
set on the file descriptor (which the :cfunc:`fdopen` implementation already
does on most platforms).
+ Availability: Unix, Windows.
+
.. _os-fd-ops:
@@ -444,7 +543,9 @@
.. function:: close(fd)
- Close file descriptor *fd*. Availability: Unix, Windows.
+ Close file descriptor *fd*.
+
+ Availability: Unix, Windows.
.. note::
@@ -457,7 +558,7 @@
.. function:: closerange(fd_low, fd_high)
Close all file descriptors from *fd_low* (inclusive) to *fd_high* (exclusive),
- ignoring errors. Availability: Unix, Windows. Equivalent to::
+ ignoring errors. Equivalent to::
for fd in range(fd_low, fd_high):
try:
@@ -465,6 +566,8 @@
except OSError:
pass
+ Availability: Unix, Windows.
+
.. function:: device_encoding(fd)
@@ -474,33 +577,40 @@
.. function:: dup(fd)
- Return a duplicate of file descriptor *fd*. Availability: Unix,
- Windows.
+ Return a duplicate of file descriptor *fd*.
+
+ Availability: Unix, Windows.
.. function:: dup2(fd, fd2)
Duplicate file descriptor *fd* to *fd2*, closing the latter first if necessary.
+
Availability: Unix, Windows.
.. function:: fchmod(fd, mode)
Change the mode of the file given by *fd* to the numeric *mode*. See the docs
- for :func:`chmod` for possible values of *mode*. Availability: Unix.
+ for :func:`chmod` for possible values of *mode*.
+
+ Availability: Unix.
.. function:: fchown(fd, uid, gid)
Change the owner and group id of the file given by *fd* to the numeric *uid*
and *gid*. To leave one of the ids unchanged, set it to -1.
+
Availability: Unix.
.. function:: fdatasync(fd)
Force write of file with filedescriptor *fd* to disk. Does not force update of
- metadata. Availability: Unix.
+ metadata.
+
+ Availability: Unix.
.. note::
This function is not available on MacOS.
@@ -515,24 +625,28 @@
additional names as well. The names known to the host operating system are
given in the ``pathconf_names`` dictionary. For configuration variables not
included in that mapping, passing an integer for *name* is also accepted.
- Availability: Unix.
If *name* is a string and is not known, :exc:`ValueError` is raised. If a
specific value for *name* is not supported by the host system, even if it is
included in ``pathconf_names``, an :exc:`OSError` is raised with
:const:`errno.EINVAL` for the error number.
+ Availability: Unix.
+
.. function:: fstat(fd)
- Return status for file descriptor *fd*, like :func:`stat`. Availability:
- Unix, Windows.
+ Return status for file descriptor *fd*, like :func:`stat`.
+
+ Availability: Unix, Windows.
.. function:: fstatvfs(fd)
Return information about the filesystem containing the file associated with file
- descriptor *fd*, like :func:`statvfs`. Availability: Unix.
+ descriptor *fd*, like :func:`statvfs`.
+
+ Availability: Unix.
.. function:: fsync(fd)
@@ -542,19 +656,25 @@
If you're starting with a Python file object *f*, first do ``f.flush()``, and
then do ``os.fsync(f.fileno())``, to ensure that all internal buffers associated
- with *f* are written to disk. Availability: Unix, Windows.
+ with *f* are written to disk.
+
+ Availability: Unix, and Windows.
.. function:: ftruncate(fd, length)
Truncate the file corresponding to file descriptor *fd*, so that it is at most
- *length* bytes in size. Availability: Unix.
+ *length* bytes in size.
+
+ Availability: Unix.
.. function:: isatty(fd)
Return ``True`` if the file descriptor *fd* is open and connected to a
- tty(-like) device, else ``False``. Availability: Unix.
+ tty(-like) device, else ``False``.
+
+ Availability: Unix.
.. function:: lseek(fd, pos, how)
@@ -563,7 +683,9 @@
by *how*: :const:`SEEK_SET` or ``0`` to set the position relative to the
beginning of the file; :const:`SEEK_CUR` or ``1`` to set it relative to the
current position; :const:`os.SEEK_END` or ``2`` to set it relative to the end of
- the file. Availability: Unix, Windows.
+ the file.
+
+ Availability: Unix, Windows.
.. function:: open(file, flags[, mode])
@@ -571,17 +693,19 @@
Open the file *file* and set various flags according to *flags* and possibly
its mode according to *mode*. The default *mode* is ``0o777`` (octal), and
the current umask value is first masked out. Return the file descriptor for
- the newly opened file. Availability: Unix, Windows.
+ the newly opened file.
For a description of the flag and mode values, see the C run-time documentation;
flag constants (like :const:`O_RDONLY` and :const:`O_WRONLY`) are defined in
this module too (see below).
+ Availability: Unix, Windows.
+
.. note::
This function is intended for low-level I/O. For normal usage, use the
built-in function :func:`open`, which returns a "file object" with
- :meth:`~file.read` and :meth:`~file.write` methods (and many more). To
+ :meth:`~file.read` and :meth:`~file.wprite` methods (and many more). To
wrap a file descriptor in a "file object", use :func:`fdopen`.
@@ -591,21 +715,26 @@
Open a new pseudo-terminal pair. Return a pair of file descriptors ``(master,
slave)`` for the pty and the tty, respectively. For a (slightly) more portable
- approach, use the :mod:`pty` module. Availability: some flavors of
- Unix.
+ approach, use the :mod:`pty` module.
+
+ Availability: some flavors of Unix.
.. function:: pipe()
Create a pipe. Return a pair of file descriptors ``(r, w)`` usable for reading
- and writing, respectively. Availability: Unix, Windows.
+ and writing, respectively.
+
+ Availability: Unix, Windows.
.. function:: read(fd, n)
Read at most *n* bytes from file descriptor *fd*. Return a bytestring containing the
bytes read. If the end of the file referred to by *fd* has been reached, an
- empty bytes object is returned. Availability: Unix, Windows.
+ empty bytes object is returned.
+
+ Availability: Unix, Windows.
.. note::
@@ -619,26 +748,34 @@
.. function:: tcgetpgrp(fd)
Return the process group associated with the terminal given by *fd* (an open
- file descriptor as returned by :func:`os.open`). Availability: Unix.
+ file descriptor as returned by :func:`os.open`).
+
+ Availability: Unix.
.. function:: tcsetpgrp(fd, pg)
Set the process group associated with the terminal given by *fd* (an open file
- descriptor as returned by :func:`os.open`) to *pg*. Availability: Unix.
+ descriptor as returned by :func:`os.open`) to *pg*.
+
+ Availability: Unix.
.. function:: ttyname(fd)
Return a string which specifies the terminal device associated with
file descriptor *fd*. If *fd* is not associated with a terminal device, an
- exception is raised. Availability: Unix.
+ exception is raised.
+
+ Availability: Unix.
.. function:: write(fd, str)
Write the bytestring in *str* to file descriptor *fd*. Return the number of
- bytes actually written. Availability: Unix, Windows.
+ bytes actually written.
+
+ Availability: Unix, Windows.
.. note::
@@ -721,7 +858,9 @@
can be the inclusive OR of one or more of :const:`R_OK`, :const:`W_OK`, and
:const:`X_OK` to test permissions. Return :const:`True` if access is allowed,
:const:`False` if not. See the Unix man page :manpage:`access(2)` for more
- information. Availability: Unix, Windows.
+ information.
+
+ Availability: Unix, Windows.
.. note::
@@ -765,25 +904,31 @@
.. index:: single: directory; changing
- Change the current working directory to *path*. Availability: Unix,
- Windows.
+ Change the current working directory to *path*.
+
+ Availability: Unix, Windows.
.. function:: fchdir(fd)
Change the current working directory to the directory represented by the file
descriptor *fd*. The descriptor must refer to an opened directory, not an open
- file. Availability: Unix.
+ file.
+
+ Availability: Unix.
.. function:: getcwd()
Return a string representing the current working directory.
+
Availability: Unix, Windows.
+
.. function:: getcwdb()
Return a bytestring representing the current working directory.
+
Availability: Unix, Windows.
@@ -851,32 +996,41 @@
.. function:: chown(path, uid, gid)
Change the owner and group id of *path* to the numeric *uid* and *gid*. To leave
- one of the ids unchanged, set it to -1. Availability: Unix.
+ one of the ids unchanged, set it to -1.
+
+ Availability: Unix.
.. function:: lchflags(path, flags)
Set the flags of *path* to the numeric *flags*, like :func:`chflags`, but do not
- follow symbolic links. Availability: Unix.
+ follow symbolic links.
+
+ Availability: Unix.
.. function:: lchmod(path, mode)
Change the mode of *path* to the numeric *mode*. If path is a symlink, this
affects the symlink rather than the target. See the docs for :func:`chmod`
- for possible values of *mode*. Availability: Unix.
+ for possible values of *mode*.
+
+ Availability: Unix.
.. function:: lchown(path, uid, gid)
Change the owner and group id of *path* to the numeric *uid* and *gid*. This
- function will not follow symbolic links. Availability: Unix.
+ function will not follow symbolic links.
+
+ Availability: Unix.
.. function:: link(source, link_name)
- Create a hard link pointing to *source* named *link_name*. Availability:
- Unix.
+ Create a hard link pointing to *source* named *link_name*.
+
+ Availability: Unix.
.. function:: listdir(path)
@@ -884,11 +1038,12 @@
Return a list containing the names of the entries in the directory given by
*path*. The list is in arbitrary order. It does not include the special
entries ``'.'`` and ``'..'`` even if they are present in the directory.
- Availability: Unix, Windows.
This function can be called with a bytes or string argument, and returns
filenames of the same datatype.
+ Availability: Unix, Windows.
+
.. function:: lstat(path)
@@ -901,7 +1056,7 @@
Create a FIFO (a named pipe) named *path* with numeric mode *mode*. The
default *mode* is ``0o666`` (octal). The current umask value is first masked
- out from the mode. Availability: Unix.
+ out from the mode.
FIFOs are pipes that can be accessed like regular files. FIFOs exist until they
are deleted (for example with :func:`os.unlink`). Generally, FIFOs are used as
@@ -909,6 +1064,8 @@
FIFO for reading, and the client opens it for writing. Note that :func:`mkfifo`
doesn't open the FIFO --- it just creates the rendezvous point.
+ Availability: Unix.
+
.. function:: mknod(filename[, mode=0o600[, device]])
@@ -942,11 +1099,13 @@
Create a directory named *path* with numeric mode *mode*. The default *mode*
is ``0o777`` (octal). On some systems, *mode* is ignored. Where it is used,
- the current umask value is first masked out. Availability: Unix, Windows.
+ the current umask value is first masked out.
It is also possible to create temporary directories; see the
:mod:`tempfile` module's :func:`tempfile.mkdtemp` function.
+ Availability: Unix, Windows.
+
.. function:: makedirs(path[, mode])
@@ -977,13 +1136,14 @@
additional names as well. The names known to the host operating system are
given in the ``pathconf_names`` dictionary. For configuration variables not
included in that mapping, passing an integer for *name* is also accepted.
- Availability: Unix.
If *name* is a string and is not known, :exc:`ValueError` is raised. If a
specific value for *name* is not supported by the host system, even if it is
included in ``pathconf_names``, an :exc:`OSError` is raised with
:const:`errno.EINVAL` for the error number.
+ Availability: Unix.
+
.. data:: pathconf_names
@@ -1014,8 +1174,9 @@
the :func:`unlink` function documented below. On Windows, attempting to
remove a file that is in use causes an exception to be raised; on Unix, the
directory entry is removed but the storage allocated to the file is not made
- available until the original file is no longer in use. Availability: Unix,
- Windows.
+ available until the original file is no longer in use.
+
+ Availability: Unix, Windows.
.. function:: removedirs(path)
@@ -1041,7 +1202,9 @@
the renaming will be an atomic operation (this is a POSIX requirement). On
Windows, if *dst* already exists, :exc:`OSError` will be raised even if it is a
file; there may be no way to implement an atomic rename when *dst* names an
- existing file. Availability: Unix, Windows.
+ existing file.
+
+ Availability: Unix, Windows.
.. function:: renames(old, new)
@@ -1061,8 +1224,9 @@
Remove (delete) the directory *path*. Only works when the directory is
empty, otherwise, :exc:`OSError` is raised. In order to remove whole
- directory trees, :func:`shutil.rmtree` can be used. Availability: Unix,
- Windows.
+ directory trees, :func:`shutil.rmtree` can be used.
+
+ Availability: Unix, Windows.
.. function:: stat(path)
@@ -1153,20 +1317,25 @@
correspond to the members of the :ctype:`statvfs` structure, namely:
:attr:`f_bsize`, :attr:`f_frsize`, :attr:`f_blocks`, :attr:`f_bfree`,
:attr:`f_bavail`, :attr:`f_files`, :attr:`f_ffree`, :attr:`f_favail`,
- :attr:`f_flag`, :attr:`f_namemax`. Availability: Unix.
+ :attr:`f_flag`, :attr:`f_namemax`.
+
+ Availability: Unix.
.. function:: symlink(source, link_name)
- Create a symbolic link pointing to *source* named *link_name*. Availability:
- Unix.
+ Create a symbolic link pointing to *source* named *link_name*.
+
+ Availability: Unix.
.. function:: unlink(path)
Remove (delete) the file *path*. This is the same function as
:func:`remove`; the :func:`unlink` name is its traditional Unix
- name. Availability: Unix, Windows.
+ name.
+
+ Availability: Unix, Windows.
.. function:: utime(path, times)
@@ -1290,6 +1459,7 @@
behavior is to produce a core dump; on Windows, the process immediately returns
an exit code of ``3``. Be aware that programs which use :func:`signal.signal`
to register a handler for :const:`SIGABRT` will behave differently.
+
Availability: Unix, Windows.
@@ -1345,7 +1515,9 @@
.. function:: _exit(n)
Exit to the system with status *n*, without calling cleanup handlers, flushing
- stdio buffers, etc. Availability: Unix, Windows.
+ stdio buffers, etc.
+
+ Availability: Unix, Windows.
.. note::
@@ -1365,69 +1537,88 @@
.. data:: EX_OK
- Exit code that means no error occurred. Availability: Unix.
+ Exit code that means no error occurred.
+
+ Availability: Unix.
.. data:: EX_USAGE
Exit code that means the command was used incorrectly, such as when the wrong
- number of arguments are given. Availability: Unix.
+ number of arguments are given.
+
+ Availability: Unix.
.. data:: EX_DATAERR
- Exit code that means the input data was incorrect. Availability: Unix.
+ Exit code that means the input data was incorrect.
+
+ Availability: Unix.
.. data:: EX_NOINPUT
Exit code that means an input file did not exist or was not readable.
+
Availability: Unix.
.. data:: EX_NOUSER
- Exit code that means a specified user did not exist. Availability: Unix.
+ Exit code that means a specified user did not exist.
+
+ Availability: Unix.
.. data:: EX_NOHOST
- Exit code that means a specified host did not exist. Availability: Unix.
+ Exit code that means a specified host did not exist.
+
+ Availability: Unix.
.. data:: EX_UNAVAILABLE
- Exit code that means that a required service is unavailable. Availability:
- Unix.
+ Exit code that means that a required service is unavailable.
+
+ Availability: Unix.
.. data:: EX_SOFTWARE
- Exit code that means an internal software error was detected. Availability:
- Unix.
+ Exit code that means an internal software error was detected.
+
+ Availability: Unix.
.. data:: EX_OSERR
Exit code that means an operating system error was detected, such as the
- inability to fork or create a pipe. Availability: Unix.
+ inability to fork or create a pipe.
+
+ Availability: Unix.
.. data:: EX_OSFILE
Exit code that means some system file did not exist, could not be opened, or had
- some other kind of error. Availability: Unix.
+ some other kind of error.
+
+ Availability: Unix.
.. data:: EX_CANTCREAT
Exit code that means a user specified output file could not be created.
+
Availability: Unix.
.. data:: EX_IOERR
Exit code that means that an error occurred while doing I/O on some file.
+
Availability: Unix.
@@ -1435,31 +1626,39 @@
Exit code that means a temporary failure occurred. This indicates something
that may not really be an error, such as a network connection that couldn't be
- made during a retryable operation. Availability: Unix.
+ made during a retryable operation.
+
+ Availability: Unix.
.. data:: EX_PROTOCOL
Exit code that means that a protocol exchange was illegal, invalid, or not
- understood. Availability: Unix.
+ understood.
+
+ Availability: Unix.
.. data:: EX_NOPERM
Exit code that means that there were insufficient permissions to perform the
- operation (but not intended for file system problems). Availability: Unix.
+ operation (but not intended for file system problems).
+
+ Availability: Unix.
.. data:: EX_CONFIG
Exit code that means that some kind of configuration error occurred.
+
Availability: Unix.
.. data:: EX_NOTFOUND
- Exit code that means something like "an entry was not found". Availability:
- Unix.
+ Exit code that means something like "an entry was not found".
+
+ Availability: Unix.
.. function:: fork()
@@ -1480,6 +1679,7 @@
new child's process id in the parent, and *fd* is the file descriptor of the
master end of the pseudo-terminal. For a more portable approach, use the
:mod:`pty` module. If an error occurs :exc:`OSError` is raised.
+
Availability: some flavors of Unix.
@@ -1509,19 +1709,24 @@
single: process; killing
single: process; signalling
- Send the signal *sig* to the process group *pgid*. Availability: Unix.
+ Send the signal *sig* to the process group *pgid*.
+
+ Availability: Unix.
.. function:: nice(increment)
Add *increment* to the process's "niceness". Return the new niceness.
+
Availability: Unix.
.. function:: plock(op)
Lock program segments into memory. The value of *op* (defined in
- ``<sys/lock.h>``) determines which segments are locked. Availability: Unix.
+ ``<sys/lock.h>``) determines which segments are locked.
+
+ Availability: Unix.
.. function:: popen(...)
@@ -1600,7 +1805,9 @@
Possible values for the *mode* parameter to the :func:`spawn\*` family of
functions. If either of these values is given, the :func:`spawn\*` functions
will return as soon as the new process has been created, with the process id as
- the return value. Availability: Unix, Windows.
+ the return value.
+
+ Availability: Unix, Windows.
.. data:: P_WAIT
@@ -1609,7 +1816,9 @@
functions. If this is given as *mode*, the :func:`spawn\*` functions will not
return until the new process has run to completion and will return the exit code
of the process the run is successful, or ``-signal`` if a signal kills the
- process. Availability: Unix, Windows.
+ process.
+
+ Availability: Unix, Windows.
.. data:: P_DETACH
@@ -1620,6 +1829,7 @@
is similar to :const:`P_NOWAIT`, but the new process is detached from the
console of the calling process. If :const:`P_OVERLAY` is used, the current
process will be replaced; the :func:`spawn\*` function will not return.
+
Availability: Windows.
@@ -1643,7 +1853,9 @@
directory. If you want to use an absolute path, make sure the first character
is not a slash (``'/'``); the underlying Win32 :cfunc:`ShellExecute` function
doesn't work if it is. Use the :func:`os.path.normpath` function to ensure that
- the path is properly encoded for Win32. Availability: Windows.
+ the path is properly encoded for Win32.
+
+ Availability: Windows.
.. function:: system(command)
@@ -1665,22 +1877,24 @@
the command run; on systems using a non-native shell, consult your shell
documentation.
- Availability: Unix, Windows.
-
The :mod:`subprocess` module provides more powerful facilities for spawning new
processes and retrieving their results; using that module is preferable to using
this function. Use the :mod:`subprocess` module. Check especially the
:ref:`subprocess-replacements` section.
+ Availability: Unix, Windows.
+
.. function:: times()
- Return a 5-tuple of floating point numbers indicating accumulated (processor or
- other) times, in seconds. The items are: user time, system time, children's
- user time, children's system time, and elapsed real time since a fixed point in
- the past, in that order. See the Unix manual page :manpage:`times(2)` or the
- corresponding Windows Platform API documentation. Availability: Unix,
- Windows. On Windows, only the first two items are filled, the others are zero.
+ Return a 5-tuple of floating point numbers indicating accumulated (processor
+ or other) times, in seconds. The items are: user time, system time,
+ children's user time, children's system time, and elapsed real time since a
+ fixed point in the past, in that order. See the Unix manual page
+ :manpage:`times(2)` or the corresponding Windows Platform API documentation.
+ On Windows, only the first two items are filled, the others are zero.
+
+ Availability: Unix, Windows
.. function:: wait()
@@ -1689,7 +1903,9 @@
and exit status indication: a 16-bit number, whose low byte is the signal number
that killed the process, and whose high byte is the exit status (if the signal
number is zero); the high bit of the low byte is set if a core file was
- produced. Availability: Unix.
+ produced.
+
+ Availability: Unix.
.. function:: waitpid(pid, options)
@@ -1727,6 +1943,7 @@
resource usage information is returned. Refer to :mod:`resource`.\
:func:`getrusage` for details on resource usage information. The option
argument is the same as that provided to :func:`waitpid` and :func:`wait4`.
+
Availability: Unix.
@@ -1736,28 +1953,33 @@
process id, exit status indication, and resource usage information is returned.
Refer to :mod:`resource`.\ :func:`getrusage` for details on resource usage
information. The arguments to :func:`wait4` are the same as those provided to
- :func:`waitpid`. Availability: Unix.
+ :func:`waitpid`.
+
+ Availability: Unix.
.. data:: WNOHANG
The option for :func:`waitpid` to return immediately if no child process status
is available immediately. The function returns ``(0, 0)`` in this case.
+
Availability: Unix.
.. data:: WCONTINUED
This option causes child processes to be reported if they have been continued
- from a job control stop since their status was last reported. Availability: Some
- Unix systems.
+ from a job control stop since their status was last reported.
+
+ Availability: Some Unix systems.
.. data:: WUNTRACED
This option causes child processes to be reported if they have been stopped but
- their current state has not been reported since they were stopped. Availability:
- Unix.
+ their current state has not been reported since they were stopped.
+
+ Availability: Unix.
The following functions take a process status code as returned by
@@ -1767,48 +1989,63 @@
.. function:: WCOREDUMP(status)
Return ``True`` if a core dump was generated for the process, otherwise
- return ``False``. Availability: Unix.
+ return ``False``.
+
+ Availability: Unix.
.. function:: WIFCONTINUED(status)
Return ``True`` if the process has been continued from a job control stop,
- otherwise return ``False``. Availability: Unix.
+ otherwise return ``False``.
+
+ Availability: Unix.
.. function:: WIFSTOPPED(status)
Return ``True`` if the process has been stopped, otherwise return
- ``False``. Availability: Unix.
+ ``False``.
+
+ Availability: Unix.
.. function:: WIFSIGNALED(status)
Return ``True`` if the process exited due to a signal, otherwise return
- ``False``. Availability: Unix.
+ ``False``.
+
+ Availability: Unix.
.. function:: WIFEXITED(status)
Return ``True`` if the process exited using the :manpage:`exit(2)` system call,
- otherwise return ``False``. Availability: Unix.
+ otherwise return ``False``.
+
+ Availability: Unix.
.. function:: WEXITSTATUS(status)
If ``WIFEXITED(status)`` is true, return the integer parameter to the
:manpage:`exit(2)` system call. Otherwise, the return value is meaningless.
+
Availability: Unix.
.. function:: WSTOPSIG(status)
- Return the signal which caused the process to stop. Availability: Unix.
+ Return the signal which caused the process to stop.
+
+ Availability: Unix.
.. function:: WTERMSIG(status)
- Return the signal which caused the process to exit. Availability: Unix.
+ Return the signal which caused the process to exit.
+
+ Availability: Unix.
.. _os-path:
@@ -1825,8 +2062,7 @@
Unix 95, Unix 98, and others). Some platforms define additional names as well.
The names known to the host operating system are given as the keys of the
``confstr_names`` dictionary. For configuration variables not included in that
- mapping, passing an integer for *name* is also accepted. Availability:
- Unix.
+ mapping, passing an integer for *name* is also accepted.
If the configuration value specified by *name* isn't defined, ``None`` is
returned.
@@ -1836,19 +2072,25 @@
included in ``confstr_names``, an :exc:`OSError` is raised with
:const:`errno.EINVAL` for the error number.
+ Availability: Unix
+
.. data:: confstr_names
Dictionary mapping names accepted by :func:`confstr` to the integer values
defined for those names by the host operating system. This can be used to
- determine the set of names known to the system. Availability: Unix.
+ determine the set of names known to the system.
+
+ Availability: Unix.
.. function:: getloadavg()
Return the number of processes in the system run queue averaged over the last
1, 5, and 15 minutes or raises :exc:`OSError` if the load average was
- unobtainable. Availability: Unix.
+ unobtainable.
+
+ Availability: Unix.
.. function:: sysconf(name)
@@ -1857,6 +2099,7 @@
specified by *name* isn't defined, ``-1`` is returned. The comments regarding
the *name* parameter for :func:`confstr` apply here as well; the dictionary that
provides information on the known names is given by ``sysconf_names``.
+
Availability: Unix.
@@ -1864,7 +2107,9 @@
Dictionary mapping names accepted by :func:`sysconf` to the integer values
defined for those names by the host operating system. This can be used to
- determine the set of names known to the system. Availability: Unix.
+ determine the set of names known to the system.
+
+ Availability: Unix.
The following data values are used to support path manipulation operations. These
are defined for all platforms.
Modified: python/branches/py3k-jit/Doc/library/posix.rst
==============================================================================
--- python/branches/py3k-jit/Doc/library/posix.rst (original)
+++ python/branches/py3k-jit/Doc/library/posix.rst Mon May 10 23:19:57 2010
@@ -69,17 +69,22 @@
.. data:: environ
A dictionary representing the string environment at the time the interpreter
- was started. For example, ``environ['HOME']`` is the pathname of your home
- directory, equivalent to ``getenv("HOME")`` in C.
+ was started. Keys and values are bytes on Unix and str on Windows. For
+ example, ``environ[b'HOME']`` (``environ['HOME']`` on Windows) is the
+ pathname of your home directory, equivalent to ``getenv("HOME")`` in C.
Modifying this dictionary does not affect the string environment passed on by
:func:`execv`, :func:`popen` or :func:`system`; if you need to change the
environment, pass ``environ`` to :func:`execve` or add variable assignments and
export statements to the command string for :func:`system` or :func:`popen`.
+ .. versionchanged:: 3.2
+ On Unix, keys and values are bytes.
+
.. note::
- The :mod:`os` module provides an alternate implementation of ``environ`` which
- updates the environment on modification. Note also that updating ``os.environ``
- will render this dictionary obsolete. Use of the :mod:`os` module version of
- this is recommended over direct access to the :mod:`posix` module.
+ The :mod:`os` module provides an alternate implementation of ``environ``
+ which updates the environment on modification. Note also that updating
+ :data:`os.environ` will render this dictionary obsolete. Use of the
+ :mod:`os` module version of this is recommended over direct access to the
+ :mod:`posix` module.
Modified: python/branches/py3k-jit/Doc/library/unittest.rst
==============================================================================
--- python/branches/py3k-jit/Doc/library/unittest.rst (original)
+++ python/branches/py3k-jit/Doc/library/unittest.rst Mon May 10 23:19:57 2010
@@ -276,6 +276,27 @@
python -m unittest discover -s project_directory -p '*_test.py'
python -m unittest discover project_directory '*_test.py'
+As well as being a path it is possible to pass a package name, for example
+``myproject.subpackage.test``, as the start directory. The package name you
+supply will then be imported and its location on the filesystem will be used
+as the start directory.
+
+.. caution::
+
+ Test discovery loads tests by importing them. Once test discovery has
+ found all the test files from the start directory you specify it turns the
+ paths into package names to import. For example `foo/bar/baz.py` will be
+ imported as ``foo.bar.baz``.
+
+ If you have a package installed globally and attempt test discovery on
+ a different copy of the package then the import *could* happen from the
+ wrong place. If this happens test discovery will warn you and exit.
+
+ If you supply the start directory as a package name rather than a
+ path to a directory then discover assumes that whichever location it
+ imports from is the location you intended, so you will not get the
+ warning.
+
Test modules and packages can customize test loading and discovery by through
the `load_tests protocol`_.
@@ -882,9 +903,9 @@
.. method:: assertNotRegexpMatches(text, regexp, msg=None)
Verifies that a *regexp* search does not match *text*. Fails with an error
- message including the pattern and the *text*. *regexp* may be
- a regular expression object or a string containing a regular expression
- suitable for use by :func:`re.search`.
+ message including the pattern and the part of *text* that matches. *regexp*
+ may be a regular expression object or a string containing a regular
+ expression suitable for use by :func:`re.search`.
.. versionadded:: 3.2
Modified: python/branches/py3k-jit/Doc/library/weakref.rst
==============================================================================
--- python/branches/py3k-jit/Doc/library/weakref.rst (original)
+++ python/branches/py3k-jit/Doc/library/weakref.rst Mon May 10 23:19:57 2010
@@ -72,9 +72,9 @@
obj = Dict(red=1, green=2, blue=3) # this object is weak referenceable
-Other built-in types such as :class:`tuple` and :class:`long` do not support
-weak references even when subclassed (This is an implementation detail and may
-be different across various Python implementations.).
+Other built-in types such as :class:`tuple` and :class:`int` do not support weak
+references even when subclassed (This is an implementation detail and may be
+different across various Python implementations.).
Extension types can easily be made to support weak references; see
:ref:`weakref-support`.
Modified: python/branches/py3k-jit/Include/unicodeobject.h
==============================================================================
--- python/branches/py3k-jit/Include/unicodeobject.h (original)
+++ python/branches/py3k-jit/Include/unicodeobject.h Mon May 10 23:19:57 2010
@@ -158,6 +158,7 @@
# define PyUnicode_AsWideChar PyUnicodeUCS2_AsWideChar
# define PyUnicode_ClearFreeList PyUnicodeUCS2_ClearFreelist
# define PyUnicode_Compare PyUnicodeUCS2_Compare
+# define PyUnicode_CompareWithASCII PyUnicodeUCS2_CompareASCII
# define PyUnicode_Concat PyUnicodeUCS2_Concat
# define PyUnicode_Append PyUnicodeUCS2_Append
# define PyUnicode_AppendAndDel PyUnicodeUCS2_AppendAndDel
@@ -257,6 +258,7 @@
# define PyUnicode_AsWideChar PyUnicodeUCS4_AsWideChar
# define PyUnicode_ClearFreeList PyUnicodeUCS4_ClearFreelist
# define PyUnicode_Compare PyUnicodeUCS4_Compare
+# define PyUnicode_CompareWithASCII PyUnicodeUCS4_CompareWithASCII
# define PyUnicode_Concat PyUnicodeUCS4_Concat
# define PyUnicode_Append PyUnicodeUCS4_Append
# define PyUnicode_AppendAndDel PyUnicodeUCS4_AppendAndDel
Modified: python/branches/py3k-jit/Lib/compileall.py
==============================================================================
--- python/branches/py3k-jit/Lib/compileall.py (original)
+++ python/branches/py3k-jit/Lib/compileall.py Mon May 10 23:19:57 2010
@@ -93,12 +93,6 @@
cache_dir = os.path.dirname(cfile)
head, tail = name[:-3], name[-3:]
if tail == '.py':
- if not legacy:
- try:
- os.mkdir(cache_dir)
- except OSError as error:
- if error.errno != errno.EEXIST:
- raise
if not force:
try:
mtime = int(os.stat(fullname).st_mtime)
Modified: python/branches/py3k-jit/Lib/lib2to3/fixes/fix_import.py
==============================================================================
--- python/branches/py3k-jit/Lib/lib2to3/fixes/fix_import.py (original)
+++ python/branches/py3k-jit/Lib/lib2to3/fixes/fix_import.py Mon May 10 23:19:57 2010
@@ -43,7 +43,13 @@
import_name< 'import' imp=any >
"""
+ def start_tree(self, tree, name):
+ super(FixImport, self).start_tree(tree, name)
+ self.skip = "absolute_import" in tree.future_features
+
def transform(self, node, results):
+ if self.skip:
+ return
imp = results['imp']
if node.type == syms.import_from:
@@ -71,19 +77,22 @@
self.warning(node, "absolute and local imports together")
return
- new = FromImport('.', [imp])
+ new = FromImport(".", [imp])
new.prefix = node.prefix
return new
def probably_a_local_import(self, imp_name):
- imp_name = imp_name.split('.', 1)[0]
+ if imp_name.startswith("."):
+ # Relative imports are certainly not local imports.
+ return False
+ imp_name = imp_name.split(".", 1)[0]
base_path = dirname(self.filename)
base_path = join(base_path, imp_name)
# If there is no __init__.py next to the file its not in a package
# so can't be a relative import.
- if not exists(join(dirname(base_path), '__init__.py')):
+ if not exists(join(dirname(base_path), "__init__.py")):
return False
- for ext in ['.py', sep, '.pyc', '.so', '.sl', '.pyd']:
+ for ext in [".py", sep, ".pyc", ".so", ".sl", ".pyd"]:
if exists(base_path + ext):
return True
return False
Modified: python/branches/py3k-jit/Lib/lib2to3/fixes/fix_operator.py
==============================================================================
--- python/branches/py3k-jit/Lib/lib2to3/fixes/fix_operator.py (original)
+++ python/branches/py3k-jit/Lib/lib2to3/fixes/fix_operator.py Mon May 10 23:19:57 2010
@@ -14,10 +14,10 @@
func = "'(' func=any ')'"
PATTERN = """
power< module='operator'
- trailer< '.' {methods} > trailer< {func} > >
+ trailer< '.' %(methods)s > trailer< %(func)s > >
|
- power< {methods} trailer< {func} > >
- """.format(methods=methods, func=func)
+ power< %(methods)s trailer< %(func)s > >
+ """ % dict(methods=methods, func=func)
def transform(self, node, results):
method = results["method"][0]
Modified: python/branches/py3k-jit/Lib/lib2to3/fixes/fix_reduce.py
==============================================================================
--- python/branches/py3k-jit/Lib/lib2to3/fixes/fix_reduce.py (original)
+++ python/branches/py3k-jit/Lib/lib2to3/fixes/fix_reduce.py Mon May 10 23:19:57 2010
@@ -7,9 +7,8 @@
used in that module.
"""
-from .. import pytree
-from .. import fixer_base
-from ..fixer_util import Name, Attr, touch_import
+from lib2to3 import fixer_base
+from lib2to3.fixer_util import touch_import
Modified: python/branches/py3k-jit/Lib/lib2to3/fixes/fix_tuple_params.py
==============================================================================
--- python/branches/py3k-jit/Lib/lib2to3/fixes/fix_tuple_params.py (original)
+++ python/branches/py3k-jit/Lib/lib2to3/fixes/fix_tuple_params.py Mon May 10 23:19:57 2010
@@ -154,7 +154,7 @@
if d is None:
d = {}
for i, obj in enumerate(param_list):
- trailer = [Subscript(Number(i))]
+ trailer = [Subscript(Number(str(i)))]
if isinstance(obj, list):
map_to_index(obj, trailer, d=d)
else:
Modified: python/branches/py3k-jit/Lib/lib2to3/fixes/fix_xrange.py
==============================================================================
--- python/branches/py3k-jit/Lib/lib2to3/fixes/fix_xrange.py (original)
+++ python/branches/py3k-jit/Lib/lib2to3/fixes/fix_xrange.py Mon May 10 23:19:57 2010
@@ -17,6 +17,13 @@
rest=any* >
"""
+ def start_tree(self, tree, filename):
+ super(FixXrange, self).start_tree(tree, filename)
+ self.transformed_xranges = set()
+
+ def finish_tree(self, tree, filename):
+ self.transformed_xranges = None
+
def transform(self, node, results):
name = results["name"]
if name.value == "xrange":
@@ -29,9 +36,12 @@
def transform_xrange(self, node, results):
name = results["name"]
name.replace(Name("range", prefix=name.prefix))
+ # This prevents the new range call from being wrapped in a list later.
+ self.transformed_xranges.add(id(node))
def transform_range(self, node, results):
- if not self.in_special_context(node):
+ if (id(node) not in self.transformed_xranges and
+ not self.in_special_context(node)):
range_call = Call(Name("range"), [results["args"].clone()])
# Encase the range call in list().
list_call = Call(Name("list"), [range_call],
Modified: python/branches/py3k-jit/Lib/lib2to3/main.py
==============================================================================
--- python/branches/py3k-jit/Lib/lib2to3/main.py (original)
+++ python/branches/py3k-jit/Lib/lib2to3/main.py Mon May 10 23:19:57 2010
@@ -2,6 +2,8 @@
Main program for 2to3.
"""
+from __future__ import with_statement
+
import sys
import os
import difflib
@@ -62,8 +64,14 @@
if self.show_diffs:
diff_lines = diff_texts(old, new, filename)
try:
- for line in diff_lines:
- print(line)
+ if self.output_lock is not None:
+ with self.output_lock:
+ for line in diff_lines:
+ print(line)
+ sys.stdout.flush()
+ else:
+ for line in diff_lines:
+ print(line)
except UnicodeEncodeError:
warn("couldn't encode %s's diff for your terminal" %
(filename,))
@@ -94,7 +102,7 @@
parser.add_option("-x", "--nofix", action="append", default=[],
help="Prevent a fixer from being run.")
parser.add_option("-l", "--list-fixes", action="store_true",
- help="List available transformations (fixes/fix_*.py)")
+ help="List available transformations")
parser.add_option("-p", "--print-function", action="store_true",
help="Modify the grammar so that print() is a function")
parser.add_option("-v", "--verbose", action="store_true",
Modified: python/branches/py3k-jit/Lib/lib2to3/pgen2/tokenize.py
==============================================================================
--- python/branches/py3k-jit/Lib/lib2to3/pgen2/tokenize.py (original)
+++ python/branches/py3k-jit/Lib/lib2to3/pgen2/tokenize.py Mon May 10 23:19:57 2010
@@ -38,6 +38,13 @@
"generate_tokens", "untokenize"]
del token
+try:
+ bytes
+except NameError:
+ # Support bytes type in Python <= 2.5, so 2to3 turns itself into
+ # valid Python 3 code.
+ bytes = str
+
def group(*choices): return '(' + '|'.join(choices) + ')'
def any(*choices): return group(*choices) + '*'
def maybe(*choices): return group(*choices) + '?'
@@ -267,7 +274,7 @@
try:
return readline()
except StopIteration:
- return b''
+ return bytes()
def find_cookie(line):
try:
Modified: python/branches/py3k-jit/Lib/lib2to3/pytree.py
==============================================================================
--- python/branches/py3k-jit/Lib/lib2to3/pytree.py (original)
+++ python/branches/py3k-jit/Lib/lib2to3/pytree.py Mon May 10 23:19:57 2010
@@ -289,8 +289,7 @@
for node in child.post_order():
yield node
- @property
- def prefix(self):
+ def _prefix_getter(self):
"""
The whitespace and comments preceding this node in the input.
"""
@@ -298,11 +297,12 @@
return ""
return self.children[0].prefix
- @prefix.setter
- def prefix(self, prefix):
+ def _prefix_setter(self, prefix):
if self.children:
self.children[0].prefix = prefix
+ prefix = property(_prefix_getter, _prefix_setter)
+
def set_child(self, i, child):
"""
Equivalent to 'node.children[i] = child'. This method also sets the
@@ -390,18 +390,17 @@
"""Return a pre-order iterator for the tree."""
yield self
- @property
- def prefix(self):
+ def _prefix_getter(self):
"""
The whitespace and comments preceding this token in the input.
"""
return self._prefix
- @prefix.setter
- def prefix(self, prefix):
+ def _prefix_setter(self, prefix):
self.changed()
self._prefix = prefix
+ prefix = property(_prefix_getter, _prefix_setter)
def convert(gr, raw_node):
"""
Modified: python/branches/py3k-jit/Lib/lib2to3/refactor.py
==============================================================================
--- python/branches/py3k-jit/Lib/lib2to3/refactor.py (original)
+++ python/branches/py3k-jit/Lib/lib2to3/refactor.py Mon May 10 23:19:57 2010
@@ -8,6 +8,8 @@
provides infrastructure to write your own refactoring tool.
"""
+from __future__ import with_statement
+
__author__ = "Guido van Rossum <guido at python.org>"
@@ -122,13 +124,14 @@
_to_system_newlines = _identity
-def _detect_future_print(source):
+def _detect_future_features(source):
have_docstring = False
gen = tokenize.generate_tokens(io.StringIO(source).readline)
def advance():
tok = next(gen)
return tok[0], tok[1]
ignore = frozenset((token.NEWLINE, tokenize.NL, token.COMMENT))
+ features = set()
try:
while True:
tp, value = advance()
@@ -140,26 +143,25 @@
have_docstring = True
elif tp == token.NAME and value == "from":
tp, value = advance()
- if tp != token.NAME and value != "__future__":
+ if tp != token.NAME or value != "__future__":
break
tp, value = advance()
- if tp != token.NAME and value != "import":
+ if tp != token.NAME or value != "import":
break
tp, value = advance()
if tp == token.OP and value == "(":
tp, value = advance()
while tp == token.NAME:
- if value == "print_function":
- return True
+ features.add(value)
tp, value = advance()
- if tp != token.OP and value != ",":
+ if tp != token.OP or value != ",":
break
tp, value = advance()
else:
break
except StopIteration:
pass
- return False
+ return frozenset(features)
class FixerError(Exception):
@@ -341,7 +343,8 @@
An AST corresponding to the refactored input stream; None if
there were errors during the parse.
"""
- if _detect_future_print(data):
+ features = _detect_future_features(data)
+ if "print_function" in features:
self.driver.grammar = pygram.python_grammar_no_print_statement
try:
tree = self.driver.parse_string(data)
@@ -351,6 +354,7 @@
return
finally:
self.driver.grammar = self.grammar
+ tree.future_features = features
self.log_debug("Refactoring %s", name)
self.refactor_tree(tree, name)
return tree
@@ -605,6 +609,7 @@
def __init__(self, *args, **kwargs):
super(MultiprocessRefactoringTool, self).__init__(*args, **kwargs)
self.queue = None
+ self.output_lock = None
def refactor(self, items, write=False, doctests_only=False,
num_processes=1):
@@ -618,6 +623,7 @@
if self.queue is not None:
raise RuntimeError("already doing multiple processes")
self.queue = multiprocessing.JoinableQueue()
+ self.output_lock = multiprocessing.Lock()
processes = [multiprocessing.Process(target=self._child)
for i in range(num_processes)]
try:
Modified: python/branches/py3k-jit/Lib/lib2to3/tests/test_fixers.py
==============================================================================
--- python/branches/py3k-jit/Lib/lib2to3/tests/test_fixers.py (original)
+++ python/branches/py3k-jit/Lib/lib2to3/tests/test_fixers.py Mon May 10 23:19:57 2010
@@ -1497,6 +1497,17 @@
for call in fixer_util.consuming_calls:
self.unchanged("a = %s(range(10))" % call)
+class Test_xrange_with_reduce(FixerTestCase):
+
+ def setUp(self):
+ super(Test_xrange_with_reduce, self).setUp(["xrange", "reduce"])
+
+ def test_double_transform(self):
+ b = """reduce(x, xrange(5))"""
+ a = """from functools import reduce
+reduce(x, range(5))"""
+ self.check(b, a)
+
class Test_raw_input(FixerTestCase):
fixer = "raw_input"
@@ -3679,7 +3690,7 @@
self.files_checked.append(name)
return self.always_exists or (name in self.present_files)
- from ..fixes import fix_import
+ from lib2to3.fixes import fix_import
fix_import.exists = fake_exists
def tearDown(self):
@@ -3722,6 +3733,12 @@
self.present_files = set(["bar.py"])
self.unchanged(s)
+ def test_with_absolute_import_enabled(self):
+ s = "from __future__ import absolute_import\nimport bar"
+ self.always_exists = False
+ self.present_files = set(["__init__.py", "bar.py"])
+ self.unchanged(s)
+
def test_in_package(self):
b = "import bar"
a = "from . import bar"
@@ -3736,6 +3753,10 @@
self.present_files = set(["__init__.py", "bar" + os.path.sep])
self.check(b, a)
+ def test_already_relative_import(self):
+ s = "from . import bar"
+ self.unchanged(s)
+
def test_comments_and_indent(self):
b = "import bar # Foo"
a = "from . import bar # Foo"
Modified: python/branches/py3k-jit/Lib/lib2to3/tests/test_parser.py
==============================================================================
--- python/branches/py3k-jit/Lib/lib2to3/tests/test_parser.py (original)
+++ python/branches/py3k-jit/Lib/lib2to3/tests/test_parser.py Mon May 10 23:19:57 2010
@@ -6,6 +6,8 @@
test_grammar.py files from both Python 2 and Python 3.
"""
+from __future__ import with_statement
+
# Testing imports
from . import support
from .support import driver, test_dir
@@ -149,10 +151,11 @@
for filepath in support.all_project_files():
with open(filepath, "rb") as fp:
encoding = tokenize.detect_encoding(fp.readline)[0]
- fp.seek(0)
+ self.assertTrue(encoding is not None,
+ "can't detect encoding for %s" % filepath)
+ with open(filepath, "r") as fp:
source = fp.read()
- if encoding:
- source = source.decode(encoding)
+ source = source.decode(encoding)
tree = driver.parse_string(source)
new = str(tree)
if encoding:
@@ -199,10 +202,10 @@
self.validate(s)
-def diff(fn, result):
- f = open("@", "wb")
+def diff(fn, result, encoding):
+ f = open("@", "w")
try:
- f.write(result)
+ f.write(result.encode(encoding))
finally:
f.close()
try:
Modified: python/branches/py3k-jit/Lib/lib2to3/tests/test_pytree.py
==============================================================================
--- python/branches/py3k-jit/Lib/lib2to3/tests/test_pytree.py (original)
+++ python/branches/py3k-jit/Lib/lib2to3/tests/test_pytree.py Mon May 10 23:19:57 2010
@@ -9,6 +9,9 @@
especially when debugging a test.
"""
+from __future__ import with_statement
+
+import sys
import warnings
# Testing imports
@@ -28,20 +31,22 @@
"""Unit tests for nodes (Base, Leaf, Node)."""
- def test_deprecated_prefix_methods(self):
- l = pytree.Leaf(100, "foo")
- with warnings.catch_warnings(record=True) as w:
- warnings.simplefilter("always", DeprecationWarning)
- self.assertEqual(l.get_prefix(), "")
- l.set_prefix("hi")
- self.assertEqual(l.prefix, "hi")
- self.assertEqual(len(w), 2)
- for warning in w:
- self.assertTrue(warning.category is DeprecationWarning)
- self.assertEqual(str(w[0].message), "get_prefix() is deprecated; " \
- "use the prefix property")
- self.assertEqual(str(w[1].message), "set_prefix() is deprecated; " \
- "use the prefix property")
+ if sys.version_info >= (2,6):
+ # warnings.catch_warnings is new in 2.6.
+ def test_deprecated_prefix_methods(self):
+ l = pytree.Leaf(100, "foo")
+ with warnings.catch_warnings(record=True) as w:
+ warnings.simplefilter("always", DeprecationWarning)
+ self.assertEqual(l.get_prefix(), "")
+ l.set_prefix("hi")
+ self.assertEqual(l.prefix, "hi")
+ self.assertEqual(len(w), 2)
+ for warning in w:
+ self.assertTrue(warning.category is DeprecationWarning)
+ self.assertEqual(str(w[0].message), "get_prefix() is deprecated; " \
+ "use the prefix property")
+ self.assertEqual(str(w[1].message), "set_prefix() is deprecated; " \
+ "use the prefix property")
def test_instantiate_base(self):
if __debug__:
Modified: python/branches/py3k-jit/Lib/lib2to3/tests/test_refactor.py
==============================================================================
--- python/branches/py3k-jit/Lib/lib2to3/tests/test_refactor.py (original)
+++ python/branches/py3k-jit/Lib/lib2to3/tests/test_refactor.py Mon May 10 23:19:57 2010
@@ -2,6 +2,8 @@
Unit tests for refactor.py.
"""
+from __future__ import with_statement
+
import sys
import os
import codecs
@@ -61,42 +63,50 @@
self.assertEqual(full_names,
["myfixes.fix_" + name for name in contents])
- def test_detect_future_print(self):
- run = refactor._detect_future_print
- self.assertFalse(run(""))
- self.assertTrue(run("from __future__ import print_function"))
- self.assertFalse(run("from __future__ import generators"))
- self.assertFalse(run("from __future__ import generators, feature"))
- input = "from __future__ import generators, print_function"
- self.assertTrue(run(input))
- input ="from __future__ import print_function, generators"
- self.assertTrue(run(input))
- input = "from __future__ import (print_function,)"
- self.assertTrue(run(input))
- input = "from __future__ import (generators, print_function)"
- self.assertTrue(run(input))
- input = "from __future__ import (generators, nested_scopes)"
- self.assertFalse(run(input))
- input = """from __future__ import generators
+ def test_detect_future_features(self):
+ run = refactor._detect_future_features
+ fs = frozenset
+ empty = fs()
+ self.assertEqual(run(""), empty)
+ self.assertEqual(run("from __future__ import print_function"),
+ fs(("print_function",)))
+ self.assertEqual(run("from __future__ import generators"),
+ fs(("generators",)))
+ self.assertEqual(run("from __future__ import generators, feature"),
+ fs(("generators", "feature")))
+ inp = "from __future__ import generators, print_function"
+ self.assertEqual(run(inp), fs(("generators", "print_function")))
+ inp ="from __future__ import print_function, generators"
+ self.assertEqual(run(inp), fs(("print_function", "generators")))
+ inp = "from __future__ import (print_function,)"
+ self.assertEqual(run(inp), fs(("print_function",)))
+ inp = "from __future__ import (generators, print_function)"
+ self.assertEqual(run(inp), fs(("generators", "print_function")))
+ inp = "from __future__ import (generators, nested_scopes)"
+ self.assertEqual(run(inp), fs(("generators", "nested_scopes")))
+ inp = """from __future__ import generators
from __future__ import print_function"""
- self.assertTrue(run(input))
- self.assertFalse(run("from"))
- self.assertFalse(run("from 4"))
- self.assertFalse(run("from x"))
- self.assertFalse(run("from x 5"))
- self.assertFalse(run("from x im"))
- self.assertFalse(run("from x import"))
- self.assertFalse(run("from x import 4"))
- input = "'docstring'\nfrom __future__ import print_function"
- self.assertTrue(run(input))
- input = "'docstring'\n'somng'\nfrom __future__ import print_function"
- self.assertFalse(run(input))
- input = "# comment\nfrom __future__ import print_function"
- self.assertTrue(run(input))
- input = "# comment\n'doc'\nfrom __future__ import print_function"
- self.assertTrue(run(input))
- input = "class x: pass\nfrom __future__ import print_function"
- self.assertFalse(run(input))
+ self.assertEqual(run(inp), fs(("generators", "print_function")))
+ invalid = ("from",
+ "from 4",
+ "from x",
+ "from x 5",
+ "from x im",
+ "from x import",
+ "from x import 4",
+ )
+ for inp in invalid:
+ self.assertEqual(run(inp), empty)
+ inp = "'docstring'\nfrom __future__ import print_function"
+ self.assertEqual(run(inp), fs(("print_function",)))
+ inp = "'docstring'\n'somng'\nfrom __future__ import print_function"
+ self.assertEqual(run(inp), empty)
+ inp = "# comment\nfrom __future__ import print_function"
+ self.assertEqual(run(inp), fs(("print_function",)))
+ inp = "# comment\n'doc'\nfrom __future__ import print_function"
+ self.assertEqual(run(inp), fs(("print_function",)))
+ inp = "class x: pass\nfrom __future__ import print_function"
+ self.assertEqual(run(inp), empty)
def test_get_headnode_dict(self):
class NoneFix(fixer_base.BaseFix):
Modified: python/branches/py3k-jit/Lib/os.py
==============================================================================
--- python/branches/py3k-jit/Lib/os.py (original)
+++ python/branches/py3k-jit/Lib/os.py Mon May 10 23:19:57 2010
@@ -387,29 +387,33 @@
from _abcoll import MutableMapping # Can't use collections (bootstrap)
class _Environ(MutableMapping):
- def __init__(self, environ, keymap, putenv, unsetenv):
- self.keymap = keymap
+ def __init__(self, data, encodekey, decodekey, encodevalue, decodevalue, putenv, unsetenv):
+ self.encodekey = encodekey
+ self.decodekey = decodekey
+ self.encodevalue = encodevalue
+ self.decodevalue = decodevalue
self.putenv = putenv
self.unsetenv = unsetenv
- self.data = data = {}
- for key, value in environ.items():
- data[keymap(key)] = str(value)
+ self.data = data
def __getitem__(self, key):
- return self.data[self.keymap(key)]
+ value = self.data[self.encodekey(key)]
+ return self.decodevalue(value)
def __setitem__(self, key, value):
- value = str(value)
+ key = self.encodekey(key)
+ value = self.encodevalue(value)
self.putenv(key, value)
- self.data[self.keymap(key)] = value
+ self.data[key] = value
def __delitem__(self, key):
+ key = self.encodekey(key)
self.unsetenv(key)
- del self.data[self.keymap(key)]
+ del self.data[key]
def __iter__(self):
for key in self.data:
- yield key
+ yield self.decodekey(key)
def __len__(self):
return len(self.data)
@@ -439,22 +443,78 @@
else:
__all__.append("unsetenv")
-if name in ('os2', 'nt'): # Where Env Var Names Must Be UPPERCASE
- _keymap = lambda key: str(key.upper())
-else: # Where Env Var Names Can Be Mixed Case
- _keymap = lambda key: str(key)
-
-environ = _Environ(environ, _keymap, _putenv, _unsetenv)
+def _createenviron():
+ if name in ('os2', 'nt'):
+ # Where Env Var Names Must Be UPPERCASE
+ def check_str(value):
+ if not isinstance(value, str):
+ raise TypeError("str expected, not %s" % type(value).__name__)
+ return value
+ encode = check_str
+ decode = str
+ def encodekey(key):
+ return encode(key).upper()
+ data = {}
+ for key, value in environ.items():
+ data[encodekey(key)] = value
+ else:
+ # Where Env Var Names Can Be Mixed Case
+ def encode(value):
+ if not isinstance(value, str):
+ raise TypeError("str expected, not %s" % type(value).__name__)
+ return value.encode(sys.getfilesystemencoding(), 'surrogateescape')
+ def decode(value):
+ return value.decode(sys.getfilesystemencoding(), 'surrogateescape')
+ encodekey = encode
+ data = environ
+ return _Environ(data,
+ encodekey, decode,
+ encode, decode,
+ _putenv, _unsetenv)
+
+# unicode environ
+environ = _createenviron()
+del _createenviron
def getenv(key, default=None):
"""Get an environment variable, return None if it doesn't exist.
- The optional second argument can specify an alternate default."""
- if isinstance(key, bytes):
- key = key.decode(sys.getfilesystemencoding(), "surrogateescape")
+ The optional second argument can specify an alternate default.
+ key, default and the result are str."""
return environ.get(key, default)
__all__.append("getenv")
+if name not in ('os2', 'nt'):
+ def _check_bytes(value):
+ if not isinstance(value, bytes):
+ raise TypeError("bytes expected, not %s" % type(value).__name__)
+ return value
+
+ # bytes environ
+ environb = _Environ(environ.data,
+ _check_bytes, bytes,
+ _check_bytes, bytes,
+ _putenv, _unsetenv)
+ del _check_bytes
+
+ def getenvb(key, default=None):
+ """Get an environment variable, return None if it doesn't exist.
+ The optional second argument can specify an alternate default.
+ key, default and the result are bytes."""
+ return environb.get(key, default)
+ __all__.append("getenvb")
+
+if name != 'nt':
+ def fsencode(value):
+ """Encode value for use in the file system, environment variables
+ or the command line."""
+ if isinstance(value, bytes):
+ return value
+ elif isinstance(value, str):
+ return value.encode(sys.getfilesystemencoding(), 'surrogateescape')
+ else:
+ raise TypeError("expect bytes or str, not %s" % type(value).__name__)
+
def _exists(name):
return name in globals()
Modified: python/branches/py3k-jit/Lib/py_compile.py
==============================================================================
--- python/branches/py3k-jit/Lib/py_compile.py (original)
+++ python/branches/py3k-jit/Lib/py_compile.py Mon May 10 23:19:57 2010
@@ -123,11 +123,11 @@
return
if cfile is None:
cfile = imp.cache_from_source(file)
- try:
- os.mkdir(os.path.dirname(cfile))
- except OSError as error:
- if error.errno != errno.EEXIST:
- raise
+ try:
+ os.makedirs(os.path.dirname(cfile))
+ except OSError as error:
+ if error.errno != errno.EEXIST:
+ raise
with open(cfile, 'wb') as fc:
fc.write(b'\0\0\0\0')
wr_long(fc, timestamp)
Modified: python/branches/py3k-jit/Lib/site.py
==============================================================================
--- python/branches/py3k-jit/Lib/site.py (original)
+++ python/branches/py3k-jit/Lib/site.py Mon May 10 23:19:57 2010
@@ -240,6 +240,13 @@
from sysconfig import get_path
import os
+
+ if sys.platform == 'darwin':
+ from sysconfig import get_config_var
+ if get_config_var('PYTHONFRAMEWORK'):
+ USER_SITE = get_path('purelib', 'osx_framework_user')
+ return USER_SITE
+
USER_SITE = get_path('purelib', '%s_user' % os.name)
return USER_SITE
@@ -286,13 +293,11 @@
if sys.platform == "darwin":
# for framework builds *only* we add the standard Apple
# locations.
- if 'Python.framework' in prefix:
- sitepackages.append(
- os.path.expanduser(
- os.path.join("~", "Library", "Python",
- sys.version[:3], "site-packages")))
+ from sysconfig import get_config_var
+ framework = get_config_var("PYTHONFRAMEWORK")
+ if framework and "/%s.framework/"%(framework,) in prefix:
sitepackages.append(
- os.path.join("/Library", "Python",
+ os.path.join("/Library", framework,
sys.version[:3], "site-packages"))
return sitepackages
Modified: python/branches/py3k-jit/Lib/subprocess.py
==============================================================================
--- python/branches/py3k-jit/Lib/subprocess.py (original)
+++ python/branches/py3k-jit/Lib/subprocess.py Mon May 10 23:19:57 2010
@@ -1079,32 +1079,24 @@
self._set_cloexec_flag(errpipe_write)
if _posixsubprocess:
- fs_encoding = sys.getfilesystemencoding()
- def fs_encode(s):
- """Encode s for use in the env, fs or cmdline."""
- if isinstance(s, bytes):
- return s
- else:
- return s.encode(fs_encoding, 'surrogateescape')
-
# We must avoid complex work that could involve
# malloc or free in the child process to avoid
# potential deadlocks, thus we do all this here.
# and pass it to fork_exec()
if env:
- env_list = [fs_encode(k) + b'=' + fs_encode(v)
+ env_list = [os.fsencode(k) + b'=' + os.fsencode(v)
for k, v in env.items()]
else:
env_list = None # Use execv instead of execve.
if os.path.dirname(executable):
- executable_list = (fs_encode(executable),)
+ executable_list = (os.fsencode(executable),)
else:
# This matches the behavior of os._execvpe().
path_list = os.get_exec_path(env)
executable_list = (os.path.join(dir, executable)
for dir in path_list)
- executable_list = tuple(fs_encode(exe)
+ executable_list = tuple(os.fsencode(exe)
for exe in executable_list)
self.pid = _posixsubprocess.fork_exec(
args, executable_list,
Modified: python/branches/py3k-jit/Lib/sysconfig.py
==============================================================================
--- python/branches/py3k-jit/Lib/sysconfig.py (original)
+++ python/branches/py3k-jit/Lib/sysconfig.py Mon May 10 23:19:57 2010
@@ -73,6 +73,15 @@
'scripts': '{userbase}/bin',
'data' : '{userbase}',
},
+ 'osx_framework_user': {
+ 'stdlib': '{userbase}/lib/python',
+ 'platstdlib': '{userbase}/lib/python',
+ 'purelib': '{userbase}/lib/python/site-packages',
+ 'platlib': '{userbase}/lib/python/site-packages',
+ 'include': '{userbase}/include',
+ 'scripts': '{userbase}/bin',
+ 'data' : '{userbase}',
+ },
}
_SCHEME_KEYS = ('stdlib', 'platstdlib', 'purelib', 'platlib', 'include',
@@ -157,6 +166,12 @@
base = os.environ.get("APPDATA") or "~"
return env_base if env_base else joinuser(base, "Python")
+ if sys.platform == "darwin":
+ framework = get_config_var("PYTHONFRAMEWORK")
+ if framework:
+ return joinuser("~", "Library", framework, "%d.%d"%(
+ sys.version_info[:2]))
+
return env_base if env_base else joinuser("~", ".local")
@@ -400,13 +415,17 @@
_CONFIG_VARS['py_version_nodot'] = _PY_VERSION[0] + _PY_VERSION[2]
_CONFIG_VARS['base'] = _PREFIX
_CONFIG_VARS['platbase'] = _EXEC_PREFIX
- _CONFIG_VARS['userbase'] = _getuserbase()
_CONFIG_VARS['projectbase'] = _PROJECT_BASE
if os.name in ('nt', 'os2'):
_init_non_posix(_CONFIG_VARS)
if os.name == 'posix':
_init_posix(_CONFIG_VARS)
+ # Setting 'userbase' is done below the call to the
+ # init function to enable using 'get_config_var' in
+ # the init-function.
+ _CONFIG_VARS['userbase'] = _getuserbase()
+
if 'srcdir' not in _CONFIG_VARS:
_CONFIG_VARS['srcdir'] = _PROJECT_BASE
Modified: python/branches/py3k-jit/Lib/test/regrtest.py
==============================================================================
--- python/branches/py3k-jit/Lib/test/regrtest.py (original)
+++ python/branches/py3k-jit/Lib/test/regrtest.py Mon May 10 23:19:57 2010
@@ -733,6 +733,9 @@
def replace_stdout():
"""Set stdout encoder error handler to backslashreplace (as stderr error
handler) to avoid UnicodeEncodeError when printing a traceback"""
+ if os.name == "nt":
+ # Replace sys.stdout breaks the stdout newlines on Windows: issue #8533
+ return
stdout = sys.stdout
sys.stdout = open(stdout.fileno(), 'w',
encoding=stdout.encoding,
Modified: python/branches/py3k-jit/Lib/test/test_datetime.py
==============================================================================
--- python/branches/py3k-jit/Lib/test/test_datetime.py (original)
+++ python/branches/py3k-jit/Lib/test/test_datetime.py Mon May 10 23:19:57 2010
@@ -264,6 +264,11 @@
for total_seconds in [123456.789012, -123456.789012, 0.123456, 0, 1e6]:
td = timedelta(seconds=total_seconds)
self.assertEqual(td.total_seconds(), total_seconds)
+ # Issue8644: Test that td.total_seconds() has the same
+ # accuracy as td / timedelta(seconds=1).
+ for ms in [-1, -2, -123]:
+ td = timedelta(microseconds=ms)
+ self.assertEqual(td.total_seconds(), td / timedelta(seconds=1))
def test_carries(self):
t1 = timedelta(days=100,
Modified: python/branches/py3k-jit/Lib/test/test_enumerate.py
==============================================================================
--- python/branches/py3k-jit/Lib/test/test_enumerate.py (original)
+++ python/branches/py3k-jit/Lib/test/test_enumerate.py Mon May 10 23:19:57 2010
@@ -199,26 +199,31 @@
self.assertEqual(rc, sys.getrefcount(r))
-class TestStart(EnumerateTestCase):
+class EnumerateStartTestCase(EnumerateTestCase):
- enum = lambda i: enumerate(i, start=11)
- seq, res = 'abc', [(1, 'a'), (2, 'b'), (3, 'c')]
+ def test_basicfunction(self):
+ e = self.enum(self.seq)
+ self.assertEqual(iter(e), e)
+ self.assertEqual(list(self.enum(self.seq)), self.res)
-class TestLongStart(EnumerateTestCase):
+class TestStart(EnumerateStartTestCase):
- enum = lambda i: enumerate(i, start=sys.maxsize+1)
+ enum = lambda self, i: enumerate(i, start=11)
+ seq, res = 'abc', [(11, 'a'), (12, 'b'), (13, 'c')]
+
+
+class TestLongStart(EnumerateStartTestCase):
+
+ enum = lambda self, i: enumerate(i, start=sys.maxsize+1)
seq, res = 'abc', [(sys.maxsize+1,'a'), (sys.maxsize+2,'b'),
(sys.maxsize+3,'c')]
def test_main(verbose=None):
- testclasses = (EnumerateTestCase, SubclassTestCase, TestEmpty, TestBig,
- TestReversed)
- support.run_unittest(*testclasses)
+ support.run_unittest(__name__)
# verify reference counting
- import sys
if verbose and hasattr(sys, "gettotalrefcount"):
counts = [None] * 5
for i in range(len(counts)):
Modified: python/branches/py3k-jit/Lib/test/test_os.py
==============================================================================
--- python/branches/py3k-jit/Lib/test/test_os.py (original)
+++ python/branches/py3k-jit/Lib/test/test_os.py Mon May 10 23:19:57 2010
@@ -369,12 +369,17 @@
def setUp(self):
self.__save = dict(os.environ)
+ if os.name not in ('os2', 'nt'):
+ self.__saveb = dict(os.environb)
for key, value in self._reference().items():
os.environ[key] = value
def tearDown(self):
os.environ.clear()
os.environ.update(self.__save)
+ if os.name not in ('os2', 'nt'):
+ os.environb.clear()
+ os.environb.update(self.__saveb)
def _reference(self):
return {"KEY1":"VALUE1", "KEY2":"VALUE2", "KEY3":"VALUE3"}
@@ -439,6 +444,27 @@
# Supplied PATH environment variable
self.assertSequenceEqual(test_path, os.get_exec_path(test_env))
+ @unittest.skipIf(sys.platform == "win32", "POSIX specific test")
+ def test_environb(self):
+ # os.environ -> os.environb
+ value = 'euro\u20ac'
+ try:
+ value_bytes = value.encode(sys.getfilesystemencoding(),
+ 'surrogateescape')
+ except UnicodeEncodeError:
+ msg = "U+20AC character is not encodable to %s" % (
+ sys.getfilesystemencoding(),)
+ self.skipTest(msg)
+ os.environ['unicode'] = value
+ self.assertEquals(os.environ['unicode'], value)
+ self.assertEquals(os.environb[b'unicode'], value_bytes)
+
+ # os.environb -> os.environ
+ value = b'\xff'
+ os.environb[b'bytes'] = value
+ self.assertEquals(os.environb[b'bytes'], value)
+ value_str = value.decode(sys.getfilesystemencoding(), 'surrogateescape')
+ self.assertEquals(os.environ['bytes'], value_str)
class WalkTests(unittest.TestCase):
"""Tests for os.walk()."""
@@ -607,6 +633,58 @@
def test_execvpe_with_bad_arglist(self):
self.assertRaises(ValueError, os.execvpe, 'notepad', [], None)
+ class _stub_out_for_execvpe_test(object):
+ """
+ Stubs out execv, execve and get_exec_path functions when
+ used as context manager. Records exec calls. The mock execv
+ and execve functions always raise an exception as they would
+ normally never return.
+ """
+ def __init__(self):
+ # A list of tuples containing (function name, first arg, args)
+ # of calls to execv or execve that have been made.
+ self.calls = []
+ def _mock_execv(self, name, *args):
+ self.calls.append(('execv', name, args))
+ raise RuntimeError("execv called")
+
+ def _mock_execve(self, name, *args):
+ self.calls.append(('execve', name, args))
+ raise OSError(errno.ENOTDIR, "execve called")
+
+ def _mock_get_exec_path(self, env=None):
+ return [os.sep+'p', os.sep+'pp']
+
+ def __enter__(self):
+ self.orig_execv = os.execv
+ self.orig_execve = os.execve
+ self.orig_get_exec_path = os.get_exec_path
+ os.execv = self._mock_execv
+ os.execve = self._mock_execve
+ os.get_exec_path = self._mock_get_exec_path
+
+ def __exit__(self, type, value, tb):
+ os.execv = self.orig_execv
+ os.execve = self.orig_execve
+ os.get_exec_path = self.orig_get_exec_path
+
+ @unittest.skipUnless(hasattr(os, '_execvpe'),
+ "No internal os._execvpe function to test.")
+ def test_internal_execvpe(self):
+ exec_stubbed = self._stub_out_for_execvpe_test()
+ with exec_stubbed:
+ self.assertRaises(RuntimeError, os._execvpe, os.sep+'f', ['-a'])
+ self.assertEqual([('execv', os.sep+'f', (['-a'],))],
+ exec_stubbed.calls)
+ exec_stubbed.calls = []
+ self.assertRaises(OSError, os._execvpe, 'f', ['-a'],
+ env={'spam': 'beans'})
+ self.assertEqual([('execve', os.sep+'p'+os.sep+'f',
+ (['-a'], {'spam': 'beans'})),
+ ('execve', os.sep+'pp'+os.sep+'f',
+ (['-a'], {'spam': 'beans'}))],
+ exec_stubbed.calls)
+
class Win32ErrorTests(unittest.TestCase):
def test_rename(self):
self.assertRaises(WindowsError, os.rename, support.TESTFN, support.TESTFN+".bak")
@@ -862,6 +940,14 @@
self._kill_with_event(signal.CTRL_BREAK_EVENT, "CTRL_BREAK_EVENT")
+class MiscTests(unittest.TestCase):
+
+ @unittest.skipIf(os.name == "nt", "POSIX specific test")
+ def test_fsencode(self):
+ self.assertEquals(os.fsencode(b'ab\xff'), b'ab\xff')
+ self.assertEquals(os.fsencode('ab\uDCFF'), b'ab\xff')
+
+
def test_main():
support.run_unittest(
FileTests,
@@ -876,7 +962,8 @@
TestInvalidFD,
PosixUidGidTests,
Pep383Tests,
- Win32KillTests
+ Win32KillTests,
+ MiscTests,
)
if __name__ == "__main__":
Modified: python/branches/py3k-jit/Lib/test/test_posix.py
==============================================================================
--- python/branches/py3k-jit/Lib/test/test_posix.py (original)
+++ python/branches/py3k-jit/Lib/test/test_posix.py Mon May 10 23:19:57 2010
@@ -299,9 +299,13 @@
posix.lchflags(support.TESTFN, st.st_flags)
def test_environ(self):
+ if os.name == "nt":
+ item_type = str
+ else:
+ item_type = bytes
for k, v in posix.environ.items():
- self.assertEqual(type(k), str)
- self.assertEqual(type(v), str)
+ self.assertEqual(type(k), item_type)
+ self.assertEqual(type(v), item_type)
def test_getcwd_long_pathnames(self):
if hasattr(posix, 'getcwd'):
Modified: python/branches/py3k-jit/Lib/test/test_signal.py
==============================================================================
--- python/branches/py3k-jit/Lib/test/test_signal.py (original)
+++ python/branches/py3k-jit/Lib/test/test_signal.py Mon May 10 23:19:57 2010
@@ -255,48 +255,105 @@
class SiginterruptTest(unittest.TestCase):
signum = signal.SIGUSR1
- def readpipe_interrupted(self, cb):
+
+ def setUp(self):
+ """Install a no-op signal handler that can be set to allow
+ interrupts or not, and arrange for the original signal handler to be
+ re-installed when the test is finished.
+ """
+ oldhandler = signal.signal(self.signum, lambda x,y: None)
+ self.addCleanup(signal.signal, self.signum, oldhandler)
+
+ def readpipe_interrupted(self):
+ """Perform a read during which a signal will arrive. Return True if the
+ read is interrupted by the signal and raises an exception. Return False
+ if it returns normally.
+ """
+ # Create a pipe that can be used for the read. Also clean it up
+ # when the test is over, since nothing else will (but see below for
+ # the write end).
r, w = os.pipe()
+ self.addCleanup(os.close, r)
+
+ # Create another process which can send a signal to this one to try
+ # to interrupt the read.
ppid = os.getpid()
pid = os.fork()
- oldhandler = signal.signal(self.signum, lambda x,y: None)
- cb()
- if pid==0:
- # child code: sleep, kill, sleep. and then exit,
- # which closes the pipe from which the parent process reads
+ if pid == 0:
+ # Child code: sleep to give the parent enough time to enter the
+ # read() call (there's a race here, but it's really tricky to
+ # eliminate it); then signal the parent process. Also, sleep
+ # again to make it likely that the signal is delivered to the
+ # parent process before the child exits. If the child exits
+ # first, the write end of the pipe will be closed and the test
+ # is invalid.
try:
time.sleep(0.2)
os.kill(ppid, self.signum)
time.sleep(0.2)
finally:
+ # No matter what, just exit as fast as possible now.
exit_subprocess()
-
- try:
+ else:
+ # Parent code.
+ # Make sure the child is eventually reaped, else it'll be a
+ # zombie for the rest of the test suite run.
+ self.addCleanup(os.waitpid, pid, 0)
+
+ # Close the write end of the pipe. The child has a copy, so
+ # it's not really closed until the child exits. We need it to
+ # close when the child exits so that in the non-interrupt case
+ # the read eventually completes, otherwise we could just close
+ # it *after* the test.
os.close(w)
+ # Try the read and report whether it is interrupted or not to
+ # the caller.
try:
- d=os.read(r, 1)
+ d = os.read(r, 1)
return False
except OSError as err:
if err.errno != errno.EINTR:
raise
return True
- finally:
- signal.signal(self.signum, oldhandler)
- os.waitpid(pid, 0)
def test_without_siginterrupt(self):
- i=self.readpipe_interrupted(lambda: None)
- self.assertEquals(i, True)
+ """If a signal handler is installed and siginterrupt is not called
+ at all, when that signal arrives, it interrupts a syscall that's in
+ progress.
+ """
+ i = self.readpipe_interrupted()
+ self.assertTrue(i)
+ # Arrival of the signal shouldn't have changed anything.
+ i = self.readpipe_interrupted()
+ self.assertTrue(i)
def test_siginterrupt_on(self):
- i=self.readpipe_interrupted(lambda: signal.siginterrupt(self.signum, 1))
- self.assertEquals(i, True)
+ """If a signal handler is installed and siginterrupt is called with
+ a true value for the second argument, when that signal arrives, it
+ interrupts a syscall that's in progress.
+ """
+ signal.siginterrupt(self.signum, 1)
+ i = self.readpipe_interrupted()
+ self.assertTrue(i)
+ # Arrival of the signal shouldn't have changed anything.
+ i = self.readpipe_interrupted()
+ self.assertTrue(i)
def test_siginterrupt_off(self):
- i=self.readpipe_interrupted(lambda: signal.siginterrupt(self.signum, 0))
- self.assertEquals(i, False)
+ """If a signal handler is installed and siginterrupt is called with
+ a false value for the second argument, when that signal arrives, it
+ does not interrupt a syscall that's in progress.
+ """
+ signal.siginterrupt(self.signum, 0)
+ i = self.readpipe_interrupted()
+ self.assertFalse(i)
+ # Arrival of the signal shouldn't have changed anything.
+ i = self.readpipe_interrupted()
+ self.assertFalse(i)
+
+
class ItimerTest(unittest.TestCase):
def setUp(self):
Modified: python/branches/py3k-jit/Lib/test/test_subprocess.py
==============================================================================
--- python/branches/py3k-jit/Lib/test/test_subprocess.py (original)
+++ python/branches/py3k-jit/Lib/test/test_subprocess.py Mon May 10 23:19:57 2010
@@ -803,8 +803,6 @@
def test_undecodable_env(self):
for key, value in (('test', 'abc\uDCFF'), ('test\uDCFF', '42')):
- value_repr = repr(value).encode("ascii")
-
# test str with surrogates
script = "import os; print(repr(os.getenv(%s)))" % repr(key)
env = os.environ.copy()
@@ -813,19 +811,19 @@
[sys.executable, "-c", script],
env=env)
stdout = stdout.rstrip(b'\n\r')
- self.assertEquals(stdout, value_repr)
+ self.assertEquals(stdout.decode('ascii'), repr(value))
# test bytes
key = key.encode("ascii", "surrogateescape")
value = value.encode("ascii", "surrogateescape")
- script = "import os; print(repr(os.getenv(%s)))" % repr(key)
+ script = "import os; print(repr(os.getenvb(%s)))" % repr(key)
env = os.environ.copy()
env[key] = value
stdout = subprocess.check_output(
[sys.executable, "-c", script],
env=env)
stdout = stdout.rstrip(b'\n\r')
- self.assertEquals(stdout, value_repr)
+ self.assertEquals(stdout.decode('ascii'), repr(value))
@unittest.skipUnless(mswindows, "Windows specific tests")
Modified: python/branches/py3k-jit/Lib/test/test_sysconfig.py
==============================================================================
--- python/branches/py3k-jit/Lib/test/test_sysconfig.py (original)
+++ python/branches/py3k-jit/Lib/test/test_sysconfig.py Mon May 10 23:19:57 2010
@@ -234,8 +234,8 @@
self.assertTrue(os.path.isfile(config_h), config_h)
def test_get_scheme_names(self):
- wanted = ('nt', 'nt_user', 'os2', 'os2_home', 'posix_home',
- 'posix_prefix', 'posix_user')
+ wanted = ('nt', 'nt_user', 'os2', 'os2_home', 'osx_framework_user',
+ 'posix_home', 'posix_prefix', 'posix_user')
self.assertEquals(get_scheme_names(), wanted)
def test_symlink(self):
Modified: python/branches/py3k-jit/Lib/test/test_urllib2.py
==============================================================================
--- python/branches/py3k-jit/Lib/test/test_urllib2.py (original)
+++ python/branches/py3k-jit/Lib/test/test_urllib2.py Mon May 10 23:19:57 2010
@@ -684,7 +684,7 @@
try:
data = r.read()
headers = r.info()
- newurl = r.geturl()
+ respurl = r.geturl()
finally:
r.close()
stats = os.stat(TESTFN)
@@ -695,6 +695,7 @@
self.assertEqual(headers["Content-type"], "text/plain")
self.assertEqual(headers["Content-length"], "13")
self.assertEqual(headers["Last-modified"], modified)
+ self.assertEqual(respurl, url)
for url in [
"file://localhost:80%s" % urlpath,
Modified: python/branches/py3k-jit/Lib/test/test_urlparse.py
==============================================================================
--- python/branches/py3k-jit/Lib/test/test_urlparse.py (original)
+++ python/branches/py3k-jit/Lib/test/test_urlparse.py Mon May 10 23:19:57 2010
@@ -6,7 +6,7 @@
RFC1808_BASE = "http://a/b/c/d;p?q#f"
RFC2396_BASE = "http://a/b/c/d;p?q"
-RFC3986_BASE = "http://a/b/c/d;p?q"
+RFC3986_BASE = 'http://a/b/c/d;p?q'
# A list of test cases. Each test case is a a two-tuple that contains
# a string with the query and a dictionary with the expected result.
@@ -235,14 +235,60 @@
self.checkJoin(RFC2396_BASE, 'g#s/./x', 'http://a/b/c/g#s/./x')
self.checkJoin(RFC2396_BASE, 'g#s/../x', 'http://a/b/c/g#s/../x')
- #The following scenarios have been updated in RFC3986
- #self.checkJoin(RFC2396_BASE, '?y', 'http://a/b/c/?y')
- #self.checkJoin(RFC2396_BASE, ';x', 'http://a/b/c/;x')
-
-
def test_RFC3986(self):
+ # Test cases from RFC3986
self.checkJoin(RFC3986_BASE, '?y','http://a/b/c/d;p?y')
self.checkJoin(RFC2396_BASE, ';x', 'http://a/b/c/;x')
+ self.checkJoin(RFC3986_BASE, 'g:h','g:h')
+ self.checkJoin(RFC3986_BASE, 'g','http://a/b/c/g')
+ self.checkJoin(RFC3986_BASE, './g','http://a/b/c/g')
+ self.checkJoin(RFC3986_BASE, 'g/','http://a/b/c/g/')
+ self.checkJoin(RFC3986_BASE, '/g','http://a/g')
+ self.checkJoin(RFC3986_BASE, '//g','http://g')
+ self.checkJoin(RFC3986_BASE, '?y','http://a/b/c/d;p?y')
+ self.checkJoin(RFC3986_BASE, 'g?y','http://a/b/c/g?y')
+ self.checkJoin(RFC3986_BASE, '#s','http://a/b/c/d;p?q#s')
+ self.checkJoin(RFC3986_BASE, 'g#s','http://a/b/c/g#s')
+ self.checkJoin(RFC3986_BASE, 'g?y#s','http://a/b/c/g?y#s')
+ self.checkJoin(RFC3986_BASE, ';x','http://a/b/c/;x')
+ self.checkJoin(RFC3986_BASE, 'g;x','http://a/b/c/g;x')
+ self.checkJoin(RFC3986_BASE, 'g;x?y#s','http://a/b/c/g;x?y#s')
+ self.checkJoin(RFC3986_BASE, '','http://a/b/c/d;p?q')
+ self.checkJoin(RFC3986_BASE, '.','http://a/b/c/')
+ self.checkJoin(RFC3986_BASE, './','http://a/b/c/')
+ self.checkJoin(RFC3986_BASE, '..','http://a/b/')
+ self.checkJoin(RFC3986_BASE, '../','http://a/b/')
+ self.checkJoin(RFC3986_BASE, '../g','http://a/b/g')
+ self.checkJoin(RFC3986_BASE, '../..','http://a/')
+ self.checkJoin(RFC3986_BASE, '../../','http://a/')
+ self.checkJoin(RFC3986_BASE, '../../g','http://a/g')
+
+ #Abnormal Examples
+
+ # The 'abnormal scenarios' are incompatible with RFC2986 parsing
+ # Tests are here for reference.
+
+ #self.checkJoin(RFC3986_BASE, '../../../g','http://a/g')
+ #self.checkJoin(RFC3986_BASE, '../../../../g','http://a/g')
+ #self.checkJoin(RFC3986_BASE, '/./g','http://a/g')
+ #self.checkJoin(RFC3986_BASE, '/../g','http://a/g')
+
+ self.checkJoin(RFC3986_BASE, 'g.','http://a/b/c/g.')
+ self.checkJoin(RFC3986_BASE, '.g','http://a/b/c/.g')
+ self.checkJoin(RFC3986_BASE, 'g..','http://a/b/c/g..')
+ self.checkJoin(RFC3986_BASE, '..g','http://a/b/c/..g')
+ self.checkJoin(RFC3986_BASE, './../g','http://a/b/g')
+ self.checkJoin(RFC3986_BASE, './g/.','http://a/b/c/g/')
+ self.checkJoin(RFC3986_BASE, 'g/./h','http://a/b/c/g/h')
+ self.checkJoin(RFC3986_BASE, 'g/../h','http://a/b/c/h')
+ self.checkJoin(RFC3986_BASE, 'g;x=1/./y','http://a/b/c/g;x=1/y')
+ self.checkJoin(RFC3986_BASE, 'g;x=1/../y','http://a/b/c/y')
+ self.checkJoin(RFC3986_BASE, 'g?y/./x','http://a/b/c/g?y/./x')
+ self.checkJoin(RFC3986_BASE, 'g?y/../x','http://a/b/c/g?y/../x')
+ self.checkJoin(RFC3986_BASE, 'g#s/./x','http://a/b/c/g#s/./x')
+ self.checkJoin(RFC3986_BASE, 'g#s/../x','http://a/b/c/g#s/../x')
+ #self.checkJoin(RFC3986_BASE, 'http:g','http:g') # strict parser
+ self.checkJoin(RFC3986_BASE, 'http:g','http://a/b/c/g') #relaxed parser
def test_RFC2732(self):
for url, hostname, port in [
Modified: python/branches/py3k-jit/Lib/test/test_zlib.py
==============================================================================
--- python/branches/py3k-jit/Lib/test/test_zlib.py (original)
+++ python/branches/py3k-jit/Lib/test/test_zlib.py Mon May 10 23:19:57 2010
@@ -2,6 +2,7 @@
from test import support
import binascii
import random
+from test.support import precisionbigmemtest, _1G
zlib = support.import_module('zlib')
@@ -93,8 +94,39 @@
self.assertRaises(ValueError, zlib.decompressobj().flush, -1)
+class BaseCompressTestCase(object):
+ def check_big_compress_buffer(self, size, compress_func):
+ _1M = 1024 * 1024
+ fmt = "%%0%dx" % (2 * _1M)
+ # Generate 10MB worth of random, and expand it by repeating it.
+ # The assumption is that zlib's memory is not big enough to exploit
+ # such spread out redundancy.
+ data = b''.join([random.getrandbits(8 * _1M).to_bytes(_1M, 'little')
+ for i in range(10)])
+ data = data * (size // len(data) + 1)
+ try:
+ compress_func(data)
+ finally:
+ # Release memory
+ data = None
+
+ def check_big_decompress_buffer(self, size, decompress_func):
+ data = b'x' * size
+ try:
+ compressed = zlib.compress(data, 1)
+ finally:
+ # Release memory
+ data = None
+ data = decompress_func(compressed)
+ # Sanity check
+ try:
+ self.assertEqual(len(data), size)
+ self.assertEqual(len(data.strip(b'x')), 0)
+ finally:
+ data = None
-class CompressTestCase(unittest.TestCase):
+
+class CompressTestCase(BaseCompressTestCase, unittest.TestCase):
# Test compression in one go (whole message compression)
def test_speech(self):
x = zlib.compress(HAMLET_SCENE)
@@ -108,9 +140,19 @@
for ob in x, bytearray(x):
self.assertEqual(zlib.decompress(ob), data)
+ # Memory use of the following functions takes into account overallocation
+
+ @precisionbigmemtest(size=_1G + 1024 * 1024, memuse=3)
+ def test_big_compress_buffer(self, size):
+ compress = lambda s: zlib.compress(s, 1)
+ self.check_big_compress_buffer(size, compress)
+
+ @precisionbigmemtest(size=_1G + 1024 * 1024, memuse=2)
+ def test_big_decompress_buffer(self, size):
+ self.check_big_decompress_buffer(size, zlib.decompress)
-class CompressObjectTestCase(unittest.TestCase):
+class CompressObjectTestCase(BaseCompressTestCase, unittest.TestCase):
# Test compression object
def test_pair(self):
# straightforward compress/decompress objects
@@ -399,6 +441,21 @@
d.flush()
self.assertRaises(ValueError, d.copy)
+ # Memory use of the following functions takes into account overallocation
+
+ @precisionbigmemtest(size=_1G + 1024 * 1024, memuse=3)
+ def test_big_compress_buffer(self, size):
+ c = zlib.compressobj(1)
+ compress = lambda s: c.compress(s) + c.flush()
+ self.check_big_compress_buffer(size, compress)
+
+ @precisionbigmemtest(size=_1G + 1024 * 1024, memuse=2)
+ def test_big_decompress_buffer(self, size):
+ d = zlib.decompressobj()
+ decompress = lambda s: d.decompress(s) + d.flush()
+ self.check_big_decompress_buffer(size, decompress)
+
+
def genblock(seed, length, step=1024, generator=random):
"""length-byte stream of random data from a seed (in step-byte blocks)."""
if seed is not None:
Modified: python/branches/py3k-jit/Lib/unittest/case.py
==============================================================================
--- python/branches/py3k-jit/Lib/unittest/case.py (original)
+++ python/branches/py3k-jit/Lib/unittest/case.py Mon May 10 23:19:57 2010
@@ -993,6 +993,7 @@
callable_obj(*args, **kwargs)
def assertRegexpMatches(self, text, expected_regexp, msg=None):
+ """Fail the test unless the text matches the regular expression."""
if isinstance(expected_regexp, (str, bytes)):
expected_regexp = re.compile(expected_regexp)
if not expected_regexp.search(text):
@@ -1001,6 +1002,7 @@
raise self.failureException(msg)
def assertNotRegexpMatches(self, text, unexpected_regexp, msg=None):
+ """Fail the test if the text matches the regular expression."""
if isinstance(unexpected_regexp, (str, bytes)):
unexpected_regexp = re.compile(unexpected_regexp)
match = unexpected_regexp.search(text)
Modified: python/branches/py3k-jit/Lib/unittest/loader.py
==============================================================================
--- python/branches/py3k-jit/Lib/unittest/loader.py (original)
+++ python/branches/py3k-jit/Lib/unittest/loader.py Mon May 10 23:19:57 2010
@@ -178,7 +178,10 @@
if not top_level_dir in sys.path:
# all test modules must be importable from the top level directory
- sys.path.append(top_level_dir)
+ # should we *unconditionally* put the start directory in first
+ # in sys.path to minimise likelihood of conflicts between installed
+ # modules and development versions?
+ sys.path.insert(0, top_level_dir)
self._top_level_dir = top_level_dir
is_not_importable = False
@@ -251,6 +254,16 @@
except:
yield _make_failed_import_test(name, self.suiteClass)
else:
+ mod_file = os.path.abspath(getattr(module, '__file__', full_path))
+ realpath = os.path.splitext(mod_file)[0]
+ fullpath_noext = os.path.splitext(full_path)[0]
+ if realpath.lower() != fullpath_noext.lower():
+ module_dir = os.path.dirname(realpath)
+ mod_name = os.path.splitext(os.path.basename(full_path))[0]
+ expected_dir = os.path.dirname(full_path)
+ msg = ("%r module incorrectly imported from %r. Expected %r. "
+ "Is this module globally installed?")
+ raise ImportError(msg % (mod_name, module_dir, expected_dir))
yield self.loadTestsFromModule(module)
elif os.path.isdir(full_path):
if not os.path.isfile(os.path.join(full_path, '__init__.py')):
Modified: python/branches/py3k-jit/Lib/unittest/main.py
==============================================================================
--- python/branches/py3k-jit/Lib/unittest/main.py (original)
+++ python/branches/py3k-jit/Lib/unittest/main.py Mon May 10 23:19:57 2010
@@ -70,10 +70,10 @@
# defaults for testing
failfast = catchbreak = buffer = None
- def __init__(self, module='__main__', defaultTest=None,
- argv=None, testRunner=None,
- testLoader=loader.defaultTestLoader, exit=True,
- verbosity=1, failfast=None, catchbreak=None, buffer=None):
+ def __init__(self, module='__main__', defaultTest=None, argv=None,
+ testRunner=None, testLoader=loader.defaultTestLoader,
+ exit=True, verbosity=1, failfast=None, catchbreak=None,
+ buffer=None):
if isinstance(module, str):
self.module = __import__(module)
for part in module.split('.')[1:]:
Modified: python/branches/py3k-jit/Lib/unittest/suite.py
==============================================================================
--- python/branches/py3k-jit/Lib/unittest/suite.py (original)
+++ python/branches/py3k-jit/Lib/unittest/suite.py Mon May 10 23:19:57 2010
@@ -116,7 +116,12 @@
if getattr(currentClass, "__unittest_skip__", False):
return
- currentClass._classSetupFailed = False
+ try:
+ currentClass._classSetupFailed = False
+ except TypeError:
+ # test may actually be a function
+ # so its class will be a builtin-type
+ pass
setUpClass = getattr(currentClass, 'setUpClass', None)
if setUpClass is not None:
Modified: python/branches/py3k-jit/Lib/unittest/test/test_discovery.py
==============================================================================
--- python/branches/py3k-jit/Lib/unittest/test/test_discovery.py (original)
+++ python/branches/py3k-jit/Lib/unittest/test/test_discovery.py Mon May 10 23:19:57 2010
@@ -1,4 +1,5 @@
import os
+import re
import sys
import unittest
@@ -53,8 +54,9 @@
loader._get_module_from_name = lambda path: path + ' module'
loader.loadTestsFromModule = lambda module: module + ' tests'
- loader._top_level_dir = '/foo'
- suite = list(loader._find_tests('/foo', 'test*.py'))
+ top_level = os.path.abspath('/foo')
+ loader._top_level_dir = top_level
+ suite = list(loader._find_tests(top_level, 'test*.py'))
expected = [name + ' module tests' for name in
('test1', 'test2')]
@@ -294,6 +296,63 @@
self.assertTrue(program.failfast)
self.assertTrue(program.catchbreak)
+ def test_detect_module_clash(self):
+ class Module(object):
+ __file__ = 'bar/foo.py'
+ sys.modules['foo'] = Module
+ full_path = os.path.abspath('foo')
+ original_listdir = os.listdir
+ original_isfile = os.path.isfile
+ original_isdir = os.path.isdir
+
+ def cleanup():
+ os.listdir = original_listdir
+ os.path.isfile = original_isfile
+ os.path.isdir = original_isdir
+ del sys.modules['foo']
+ if full_path in sys.path:
+ sys.path.remove(full_path)
+ self.addCleanup(cleanup)
+
+ def listdir(_):
+ return ['foo.py']
+ def isfile(_):
+ return True
+ def isdir(_):
+ return True
+ os.listdir = listdir
+ os.path.isfile = isfile
+ os.path.isdir = isdir
+
+ loader = unittest.TestLoader()
+
+ mod_dir = os.path.abspath('bar')
+ expected_dir = os.path.abspath('foo')
+ msg = re.escape(r"'foo' module incorrectly imported from %r. Expected %r. "
+ "Is this module globally installed?" % (mod_dir, expected_dir))
+ self.assertRaisesRegexp(
+ ImportError, '^%s$' % msg, loader.discover,
+ start_dir='foo', pattern='foo.py'
+ )
+ self.assertEqual(sys.path[0], full_path)
+
+
+ def test_discovery_from_dotted_path(self):
+ loader = unittest.TestLoader()
+
+ tests = [self]
+ expectedPath = os.path.abspath(os.path.dirname(unittest.test.__file__))
+
+ self.wasRun = False
+ def _find_tests(start_dir, pattern):
+ self.wasRun = True
+ self.assertEqual(start_dir, expectedPath)
+ return tests
+ loader._find_tests = _find_tests
+ suite = loader.discover('unittest.test')
+ self.assertTrue(self.wasRun)
+ self.assertEqual(suite._tests, tests)
+
if __name__ == '__main__':
unittest.main()
Modified: python/branches/py3k-jit/Lib/unittest/test/test_program.py
==============================================================================
--- python/branches/py3k-jit/Lib/unittest/test/test_program.py (original)
+++ python/branches/py3k-jit/Lib/unittest/test/test_program.py Mon May 10 23:19:57 2010
@@ -1,10 +1,28 @@
import io
+import os
+import sys
import unittest
class Test_TestProgram(unittest.TestCase):
+ def test_discovery_from_dotted_path(self):
+ loader = unittest.TestLoader()
+
+ tests = [self]
+ expectedPath = os.path.abspath(os.path.dirname(unittest.test.__file__))
+
+ self.wasRun = False
+ def _find_tests(start_dir, pattern):
+ self.wasRun = True
+ self.assertEqual(start_dir, expectedPath)
+ return tests
+ loader._find_tests = _find_tests
+ suite = loader.discover('unittest.test')
+ self.assertTrue(self.wasRun)
+ self.assertEqual(suite._tests, tests)
+
# Horrible white box test
def testNoExit(self):
result = object()
@@ -72,3 +90,166 @@
argv=["foobar"],
testRunner=unittest.TextTestRunner(stream=io.StringIO()),
testLoader=self.FooBarLoader())
+
+
+class InitialisableProgram(unittest.TestProgram):
+ exit = False
+ result = None
+ verbosity = 1
+ defaultTest = None
+ testRunner = None
+ testLoader = unittest.defaultTestLoader
+ progName = 'test'
+ test = 'test'
+ def __init__(self, *args):
+ pass
+
+RESULT = object()
+
+class FakeRunner(object):
+ initArgs = None
+ test = None
+ raiseError = False
+
+ def __init__(self, **kwargs):
+ FakeRunner.initArgs = kwargs
+ if FakeRunner.raiseError:
+ FakeRunner.raiseError = False
+ raise TypeError
+
+ def run(self, test):
+ FakeRunner.test = test
+ return RESULT
+
+class TestCommandLineArgs(unittest.TestCase):
+
+ def setUp(self):
+ self.program = InitialisableProgram()
+ self.program.createTests = lambda: None
+ FakeRunner.initArgs = None
+ FakeRunner.test = None
+ FakeRunner.raiseError = False
+
+ def testHelpAndUnknown(self):
+ program = self.program
+ def usageExit(msg=None):
+ program.msg = msg
+ program.exit = True
+ program.usageExit = usageExit
+
+ for opt in '-h', '-H', '--help':
+ program.exit = False
+ program.parseArgs([None, opt])
+ self.assertTrue(program.exit)
+ self.assertIsNone(program.msg)
+
+ program.parseArgs([None, '-$'])
+ self.assertTrue(program.exit)
+ self.assertIsNotNone(program.msg)
+
+ def testVerbosity(self):
+ program = self.program
+
+ for opt in '-q', '--quiet':
+ program.verbosity = 1
+ program.parseArgs([None, opt])
+ self.assertEqual(program.verbosity, 0)
+
+ for opt in '-v', '--verbose':
+ program.verbosity = 1
+ program.parseArgs([None, opt])
+ self.assertEqual(program.verbosity, 2)
+
+ def testBufferCatchFailfast(self):
+ program = self.program
+ for arg, attr in (('buffer', 'buffer'), ('failfast', 'failfast'),
+ ('catch', 'catchbreak')):
+ if attr == 'catch' and not hasInstallHandler:
+ continue
+
+ short_opt = '-%s' % arg[0]
+ long_opt = '--%s' % arg
+ for opt in short_opt, long_opt:
+ setattr(program, attr, None)
+
+ program.parseArgs([None, opt])
+ self.assertTrue(getattr(program, attr))
+
+ for opt in short_opt, long_opt:
+ not_none = object()
+ setattr(program, attr, not_none)
+
+ program.parseArgs([None, opt])
+ self.assertEqual(getattr(program, attr), not_none)
+
+ def testRunTestsRunnerClass(self):
+ program = self.program
+
+ program.testRunner = FakeRunner
+ program.verbosity = 'verbosity'
+ program.failfast = 'failfast'
+ program.buffer = 'buffer'
+
+ program.runTests()
+
+ self.assertEqual(FakeRunner.initArgs, {'verbosity': 'verbosity',
+ 'failfast': 'failfast',
+ 'buffer': 'buffer'})
+ self.assertEqual(FakeRunner.test, 'test')
+ self.assertIs(program.result, RESULT)
+
+ def testRunTestsRunnerInstance(self):
+ program = self.program
+
+ program.testRunner = FakeRunner()
+ FakeRunner.initArgs = None
+
+ program.runTests()
+
+ # A new FakeRunner should not have been instantiated
+ self.assertIsNone(FakeRunner.initArgs)
+
+ self.assertEqual(FakeRunner.test, 'test')
+ self.assertIs(program.result, RESULT)
+
+ def testRunTestsOldRunnerClass(self):
+ program = self.program
+
+ FakeRunner.raiseError = True
+ program.testRunner = FakeRunner
+ program.verbosity = 'verbosity'
+ program.failfast = 'failfast'
+ program.buffer = 'buffer'
+ program.test = 'test'
+
+ program.runTests()
+
+ # If initialising raises a type error it should be retried
+ # without the new keyword arguments
+ self.assertEqual(FakeRunner.initArgs, {})
+ self.assertEqual(FakeRunner.test, 'test')
+ self.assertIs(program.result, RESULT)
+
+ def testCatchBreakInstallsHandler(self):
+ module = sys.modules['unittest.main']
+ original = module.installHandler
+ def restore():
+ module.installHandler = original
+ self.addCleanup(restore)
+
+ self.installed = False
+ def fakeInstallHandler():
+ self.installed = True
+ module.installHandler = fakeInstallHandler
+
+ program = self.program
+ program.catchbreak = True
+
+ program.testRunner = FakeRunner
+
+ program.runTests()
+ self.assertTrue(self.installed)
+
+
+if __name__ == '__main__':
+ unittest.main()
Modified: python/branches/py3k-jit/Lib/unittest/test/test_runner.py
==============================================================================
--- python/branches/py3k-jit/Lib/unittest/test/test_runner.py (original)
+++ python/branches/py3k-jit/Lib/unittest/test/test_runner.py Mon May 10 23:19:57 2010
@@ -114,6 +114,52 @@
class Test_TextTestRunner(unittest.TestCase):
"""Tests for TextTestRunner."""
+ def test_init(self):
+ runner = unittest.TextTestRunner()
+ self.assertFalse(runner.failfast)
+ self.assertFalse(runner.buffer)
+ self.assertEqual(runner.verbosity, 1)
+ self.assertTrue(runner.descriptions)
+ self.assertEqual(runner.resultclass, unittest.TextTestResult)
+
+
+ def testBufferAndFailfast(self):
+ class Test(unittest.TestCase):
+ def testFoo(self):
+ pass
+ result = unittest.TestResult()
+ runner = unittest.TextTestRunner(stream=io.StringIO(), failfast=True,
+ buffer=True)
+ # Use our result object
+ runner._makeResult = lambda: result
+ runner.run(Test('testFoo'))
+
+ self.assertTrue(result.failfast)
+ self.assertTrue(result.buffer)
+
+ def testRunnerRegistersResult(self):
+ class Test(unittest.TestCase):
+ def testFoo(self):
+ pass
+ originalRegisterResult = unittest.runner.registerResult
+ def cleanup():
+ unittest.runner.registerResult = originalRegisterResult
+ self.addCleanup(cleanup)
+
+ result = unittest.TestResult()
+ runner = unittest.TextTestRunner(stream=io.StringIO())
+ # Use our result object
+ runner._makeResult = lambda: result
+
+ self.wasRegistered = 0
+ def fakeRegisterResult(thisResult):
+ self.wasRegistered += 1
+ self.assertEqual(thisResult, result)
+ unittest.runner.registerResult = fakeRegisterResult
+
+ runner.run(unittest.TestSuite())
+ self.assertEqual(self.wasRegistered, 1)
+
def test_works_with_result_without_startTestRun_stopTestRun(self):
class OldTextResult(ResultWithNoStartTestRunStopTestRun):
separator2 = ''
Modified: python/branches/py3k-jit/Lib/unittest/test/test_suite.py
==============================================================================
--- python/branches/py3k-jit/Lib/unittest/test/test_suite.py (original)
+++ python/branches/py3k-jit/Lib/unittest/test/test_suite.py Mon May 10 23:19:57 2010
@@ -1,5 +1,6 @@
import unittest
+import sys
from .support import LoggingResult, TestEquality
@@ -289,3 +290,60 @@
def test_addTests__string(self):
suite = unittest.TestSuite()
self.assertRaises(TypeError, suite.addTests, "foo")
+
+ def test_function_in_suite(self):
+ def f(_):
+ pass
+ suite = unittest.TestSuite()
+ suite.addTest(f)
+
+ # when the bug is fixed this line will not crash
+ suite.run(unittest.TestResult())
+
+
+
+ def test_basetestsuite(self):
+ class Test(unittest.TestCase):
+ wasSetUp = False
+ wasTornDown = False
+ @classmethod
+ def setUpClass(cls):
+ cls.wasSetUp = True
+ @classmethod
+ def tearDownClass(cls):
+ cls.wasTornDown = True
+ def testPass(self):
+ pass
+ def testFail(self):
+ fail
+ class Module(object):
+ wasSetUp = False
+ wasTornDown = False
+ @staticmethod
+ def setUpModule():
+ Module.wasSetUp = True
+ @staticmethod
+ def tearDownModule():
+ Module.wasTornDown = True
+
+ Test.__module__ = 'Module'
+ sys.modules['Module'] = Module
+ self.addCleanup(sys.modules.pop, 'Module')
+
+ suite = unittest.BaseTestSuite()
+ suite.addTests([Test('testPass'), Test('testFail')])
+ self.assertEqual(suite.countTestCases(), 2)
+
+ result = unittest.TestResult()
+ suite.run(result)
+ self.assertFalse(Module.wasSetUp)
+ self.assertFalse(Module.wasTornDown)
+ self.assertFalse(Test.wasSetUp)
+ self.assertFalse(Test.wasTornDown)
+ self.assertEqual(len(result.errors), 1)
+ self.assertEqual(len(result.failures), 0)
+ self.assertEqual(result.testsRun, 2)
+
+
+if __name__ == '__main__':
+ unittest.main()
Modified: python/branches/py3k-jit/Lib/urllib/request.py
==============================================================================
--- python/branches/py3k-jit/Lib/urllib/request.py (original)
+++ python/branches/py3k-jit/Lib/urllib/request.py Mon May 10 23:19:57 2010
@@ -1202,13 +1202,13 @@
import email.utils
import mimetypes
host = req.host
- file = req.selector
- localfile = url2pathname(file)
+ filename = req.selector
+ localfile = url2pathname(filename)
try:
stats = os.stat(localfile)
size = stats.st_size
modified = email.utils.formatdate(stats.st_mtime, usegmt=True)
- mtype = mimetypes.guess_type(file)[0]
+ mtype = mimetypes.guess_type(filename)[0]
headers = email.message_from_string(
'Content-type: %s\nContent-length: %d\nLast-modified: %s\n' %
(mtype or 'text/plain', size, modified))
@@ -1216,7 +1216,11 @@
host, port = splitport(host)
if not host or \
(not port and _safe_gethostbyname(host) in self.get_names()):
- return addinfourl(open(localfile, 'rb'), headers, 'file:'+file)
+ if host:
+ origurl = 'file://' + host + filename
+ else:
+ origurl = 'file://' + filename
+ return addinfourl(open(localfile, 'rb'), headers, origurl)
except OSError as msg:
# users shouldn't expect OSErrors coming from urlopen()
raise URLError(msg)
@@ -2155,7 +2159,7 @@
def ip2num(ipAddr):
parts = ipAddr.split('.')
- parts = map(int, parts)
+ parts = list(map(int, parts))
if len(parts) != 4:
parts = (parts + [0, 0, 0, 0])[:4]
return (parts[0] << 24) | (parts[1] << 16) | (parts[2] << 8) | parts[3]
Modified: python/branches/py3k-jit/Misc/NEWS
==============================================================================
--- python/branches/py3k-jit/Misc/NEWS (original)
+++ python/branches/py3k-jit/Misc/NEWS Mon May 10 23:19:57 2010
@@ -290,6 +290,9 @@
- Issue #7072: isspace(0xa0) is true on Mac OS X
+- Issue #8084: PEP 370 now conforms to system conventions for framework
+ builds on MacOS X. That is, "python setup.py install --user" will install
+ into "~/Library/Python/2.7" instead of "~/.local".
C-API
-----
@@ -348,6 +351,21 @@
Library
-------
+- Issue #8664: In py_compile, create __pycache__ when the compiled path is
+ given.
+
+- Issue #8514: Add os.fsencode() function (Unix only): encode a string to bytes
+ for use in the file system, environment variables or the command line.
+
+- Issue #8571: Fix an internal error when compressing or decompressing a
+ chunk larger than 1GB with the zlib module's compressor and decompressor
+ objects.
+
+- Issue #8603: Support bytes environmental variables on Unix: Add os.environb
+ mapping and os.getenvb() function. os.unsetenv() encodes str argument to the
+ file system encoding with the surrogateescape error handler (instead of
+ utf8/strict) and accepts bytes. posix.environ keys and values are now bytes.
+
- Issue #8573: asyncore _strerror() function might throw ValueError.
- Issue #8483: asyncore.dispatcher's __getattr__ method produced confusing
@@ -379,6 +397,9 @@
- Issue #4687: Fix accuracy of garbage collection runtimes displayed with
gc.DEBUG_STATS.
+- Issue #8354: The siginterrupt setting is now preserved for all signals,
+ not just SIGCHLD.
+
- Issue #7192: webbrowser.get("firefox") now wors on Mac OS X, as does
webbrowser.get("safari").
@@ -1090,6 +1111,11 @@
Extension Modules
-----------------
+- Issue #8644: The accuracy of td.total_seconds() has been improved (by
+ calculating with integer arithmetic instead of float arithmetic internally):
+ the result is now always correctly rounded, and is equivalent to td /
+ timedelta(seconds=1).
+
- Issue #2706: Allow division of a timedelta by another timedelta:
timedelta / timedelta, timedelta % timedelta, timedelta // timedelta
and divmod(timedelta, timedelta) are all supported.
Modified: python/branches/py3k-jit/Modules/datetimemodule.c
==============================================================================
--- python/branches/py3k-jit/Modules/datetimemodule.c (original)
+++ python/branches/py3k-jit/Modules/datetimemodule.c Mon May 10 23:19:57 2010
@@ -2211,9 +2211,25 @@
static PyObject *
delta_total_seconds(PyObject *self)
{
- return PyFloat_FromDouble(GET_TD_MICROSECONDS(self) / 1000000.0 +
- GET_TD_SECONDS(self) +
- GET_TD_DAYS(self) * 24.0 * 3600.0);
+ PyObject *total_seconds;
+ PyObject *total_microseconds;
+ PyObject *one_million;
+
+ total_microseconds = delta_to_microseconds((PyDateTime_Delta *)self);
+ if (total_microseconds == NULL)
+ return NULL;
+
+ one_million = PyLong_FromLong(1000000L);
+ if (one_million == NULL) {
+ Py_DECREF(total_microseconds);
+ return NULL;
+ }
+
+ total_seconds = PyNumber_TrueDivide(total_microseconds, one_million);
+
+ Py_DECREF(total_microseconds);
+ Py_DECREF(one_million);
+ return total_seconds;
}
static PyObject *
Modified: python/branches/py3k-jit/Modules/grpmodule.c
==============================================================================
--- python/branches/py3k-jit/Modules/grpmodule.c (original)
+++ python/branches/py3k-jit/Modules/grpmodule.c Mon May 10 23:19:57 2010
@@ -46,11 +46,8 @@
Py_DECREF(v);
return NULL;
}
-#define FSDECODE(val) PyUnicode_Decode(val, strlen(val),\
- Py_FileSystemDefaultEncoding,\
- "surrogateescape")
for (member = p->gr_mem; *member != NULL; member++) {
- PyObject *x = FSDECODE(*member);
+ PyObject *x = PyUnicode_DecodeFSDefault(*member);
if (x == NULL || PyList_Append(w, x) != 0) {
Py_XDECREF(x);
Py_DECREF(w);
@@ -61,13 +58,13 @@
}
#define SET(i,val) PyStructSequence_SET_ITEM(v, i, val)
- SET(setIndex++, FSDECODE(p->gr_name));
+ SET(setIndex++, PyUnicode_DecodeFSDefault(p->gr_name));
#ifdef __VMS
SET(setIndex++, Py_None);
Py_INCREF(Py_None);
#else
if (p->gr_passwd)
- SET(setIndex++, FSDECODE(p->gr_passwd));
+ SET(setIndex++, PyUnicode_DecodeFSDefault(p->gr_passwd));
else {
SET(setIndex++, Py_None);
Py_INCREF(Py_None);
Modified: python/branches/py3k-jit/Modules/posixmodule.c
==============================================================================
--- python/branches/py3k-jit/Modules/posixmodule.c (original)
+++ python/branches/py3k-jit/Modules/posixmodule.c Mon May 10 23:19:57 2010
@@ -498,14 +498,12 @@
char *p = strchr(*e, '=');
if (p == NULL)
continue;
- k = PyUnicode_Decode(*e, (int)(p-*e),
- Py_FileSystemDefaultEncoding, "surrogateescape");
+ k = PyBytes_FromStringAndSize(*e, (int)(p-*e));
if (k == NULL) {
PyErr_Clear();
continue;
}
- v = PyUnicode_Decode(p+1, strlen(p+1),
- Py_FileSystemDefaultEncoding, "surrogateescape");
+ v = PyBytes_FromStringAndSize(p+1, strlen(p+1));
if (v == NULL) {
PyErr_Clear();
Py_DECREF(k);
@@ -561,9 +559,13 @@
static PyObject *
posix_error_with_allocated_filename(PyObject* name)
{
- PyObject *rc = PyErr_SetFromErrnoWithFilename(PyExc_OSError,
- PyBytes_AsString(name));
+ PyObject *name_str, *rc;
+ name_str = PyUnicode_DecodeFSDefaultAndSize(PyBytes_AsString(name),
+ PyBytes_GET_SIZE(name));
Py_DECREF(name);
+ rc = PyErr_SetFromErrnoWithFilenameObject(PyExc_OSError,
+ name_str);
+ Py_XDECREF(name_str);
return rc;
}
@@ -2033,7 +2035,7 @@
return posix_error();
if (use_bytes)
return PyBytes_FromStringAndSize(buf, strlen(buf));
- return PyUnicode_Decode(buf, strlen(buf), Py_FileSystemDefaultEncoding,"surrogateescape");
+ return PyUnicode_DecodeFSDefault(buf);
}
PyDoc_STRVAR(posix_getcwd__doc__,
@@ -5301,7 +5303,7 @@
char *s1, *s2;
char *newenv;
#endif
- PyObject *newstr;
+ PyObject *newstr = NULL;
size_t len;
#ifdef MS_WINDOWS
@@ -5324,15 +5326,19 @@
APIRET rc;
rc = DosSetExtLIBPATH(s2, BEGIN_LIBPATH);
- if (rc != NO_ERROR)
- return os2_error(rc);
+ if (rc != NO_ERROR) {
+ os2_error(rc);
+ goto error;
+ }
} else if (stricmp(s1, "ENDLIBPATH") == 0) {
APIRET rc;
rc = DosSetExtLIBPATH(s2, END_LIBPATH);
- if (rc != NO_ERROR)
- return os2_error(rc);
+ if (rc != NO_ERROR) {
+ os2_error(rc);
+ goto error;
+ }
} else {
#endif
/* XXX This can leak memory -- not easy to fix :-( */
@@ -5342,36 +5348,40 @@
len = wcslen(s1) + wcslen(s2) + 2;
newstr = PyUnicode_FromUnicode(NULL, (int)len - 1);
#else
- len = strlen(s1) + strlen(s2) + 2;
+ len = PyBytes_GET_SIZE(os1) + PyBytes_GET_SIZE(os2) + 2;
newstr = PyBytes_FromStringAndSize(NULL, (int)len - 1);
#endif
- if (newstr == NULL)
- return PyErr_NoMemory();
+ if (newstr == NULL) {
+ PyErr_NoMemory();
+ goto error;
+ }
#ifdef MS_WINDOWS
newenv = PyUnicode_AsUnicode(newstr);
_snwprintf(newenv, len, L"%s=%s", s1, s2);
if (_wputenv(newenv)) {
- Py_DECREF(newstr);
posix_error();
- return NULL;
+ goto error;
}
#else
newenv = PyBytes_AS_STRING(newstr);
PyOS_snprintf(newenv, len, "%s=%s", s1, s2);
if (putenv(newenv)) {
- Py_DECREF(newstr);
- Py_DECREF(os1);
- Py_DECREF(os2);
posix_error();
- return NULL;
+ goto error;
}
#endif
+
/* Install the first arg and newstr in posix_putenv_garbage;
* this will cause previous value to be collected. This has to
* happen after the real putenv() call because the old value
* was still accessible until then. */
if (PyDict_SetItem(posix_putenv_garbage,
- PyTuple_GET_ITEM(args, 0), newstr)) {
+#ifdef MS_WINDOWS
+ PyTuple_GET_ITEM(args, 0),
+#else
+ os1,
+#endif
+ newstr)) {
/* really not much we can do; just leak */
PyErr_Clear();
}
@@ -5382,12 +5392,20 @@
#if defined(PYOS_OS2)
}
#endif
+
#ifndef MS_WINDOWS
Py_DECREF(os1);
Py_DECREF(os2);
#endif
- Py_INCREF(Py_None);
- return Py_None;
+ Py_RETURN_NONE;
+
+error:
+#ifndef MS_WINDOWS
+ Py_DECREF(os1);
+ Py_DECREF(os2);
+#endif
+ Py_XDECREF(newstr);
+ return NULL;
}
#endif /* putenv */
@@ -5399,10 +5417,20 @@
static PyObject *
posix_unsetenv(PyObject *self, PyObject *args)
{
+#ifdef MS_WINDOWS
char *s1;
if (!PyArg_ParseTuple(args, "s:unsetenv", &s1))
return NULL;
+#else
+ PyObject *os1;
+ char *s1;
+
+ if (!PyArg_ParseTuple(args, "O&:unsetenv",
+ PyUnicode_FSConverter, &os1))
+ return NULL;
+ s1 = PyBytes_AsString(os1);
+#endif
unsetenv(s1);
@@ -5412,13 +5440,20 @@
* old value was still accessible until then.
*/
if (PyDict_DelItem(posix_putenv_garbage,
- PyTuple_GET_ITEM(args, 0))) {
+#ifdef MS_WINDOWS
+ PyTuple_GET_ITEM(args, 0)
+#else
+ os1
+#endif
+ )) {
/* really not much we can do; just leak */
PyErr_Clear();
}
- Py_INCREF(Py_None);
- return Py_None;
+#ifndef MS_WINDOWS
+ Py_DECREF(os1);
+#endif
+ Py_RETURN_NONE;
}
#endif /* unsetenv */
Modified: python/branches/py3k-jit/Modules/pwdmodule.c
==============================================================================
--- python/branches/py3k-jit/Modules/pwdmodule.c (original)
+++ python/branches/py3k-jit/Modules/pwdmodule.c Mon May 10 23:19:57 2010
@@ -49,9 +49,7 @@
sets(PyObject *v, int i, const char* val)
{
if (val) {
- PyObject *o = PyUnicode_Decode(val, strlen(val),
- Py_FileSystemDefaultEncoding,
- "surrogateescape");
+ PyObject *o = PyUnicode_DecodeFSDefault(val);
PyStructSequence_SET_ITEM(v, i, o);
}
else {
Modified: python/branches/py3k-jit/Modules/signalmodule.c
==============================================================================
--- python/branches/py3k-jit/Modules/signalmodule.c (original)
+++ python/branches/py3k-jit/Modules/signalmodule.c Mon May 10 23:19:57 2010
@@ -198,7 +198,12 @@
return;
}
#endif
+#ifndef HAVE_SIGACTION
+ /* If the handler was not set up with sigaction, reinstall it. See
+ * Python/pythonrun.c for the implementation of PyOS_setsig which
+ * makes this true. See also issue8354. */
PyOS_setsig(sig_num, signal_handler);
+#endif
}
Modified: python/branches/py3k-jit/Modules/spwdmodule.c
==============================================================================
--- python/branches/py3k-jit/Modules/spwdmodule.c (original)
+++ python/branches/py3k-jit/Modules/spwdmodule.c Mon May 10 23:19:57 2010
@@ -60,9 +60,7 @@
sets(PyObject *v, int i, const char* val)
{
if (val) {
- PyObject *o = PyUnicode_Decode(val, strlen(val),
- Py_FileSystemDefaultEncoding,
- "surrogateescape");
+ PyObject *o = PyUnicode_DecodeFSDefault(val);
PyStructSequence_SET_ITEM(v, i, o);
} else {
PyStructSequence_SET_ITEM(v, i, Py_None);
Modified: python/branches/py3k-jit/Modules/zlibmodule.c
==============================================================================
--- python/branches/py3k-jit/Modules/zlibmodule.c (original)
+++ python/branches/py3k-jit/Modules/zlibmodule.c Mon May 10 23:19:57 2010
@@ -396,7 +396,8 @@
static PyObject *
PyZlib_objcompress(compobject *self, PyObject *args)
{
- int err, inplen, length = DEFAULTALLOC;
+ int err, inplen;
+ Py_ssize_t length = DEFAULTALLOC;
PyObject *RetVal;
Py_buffer pinput;
Byte *input;
@@ -477,8 +478,8 @@
static PyObject *
PyZlib_objdecompress(compobject *self, PyObject *args)
{
- int err, inplen, old_length, length = DEFAULTALLOC;
- int max_length = 0;
+ int err, inplen, max_length = 0;
+ Py_ssize_t old_length, length = DEFAULTALLOC;
PyObject *RetVal;
Py_buffer pinput;
Byte *input;
Modified: python/branches/py3k-jit/Objects/codeobject.c
==============================================================================
--- python/branches/py3k-jit/Objects/codeobject.c (original)
+++ python/branches/py3k-jit/Objects/codeobject.c Mon May 10 23:19:57 2010
@@ -340,16 +340,20 @@
static PyObject *
code_repr(PyCodeObject *co)
{
- int lineno = -1;
- char *filename = "???";
-
+ int lineno;
if (co->co_firstlineno != 0)
lineno = co->co_firstlineno;
- if (co->co_filename && PyUnicode_Check(co->co_filename))
- filename = _PyUnicode_AsString(co->co_filename);
- return PyUnicode_FromFormat(
- "<code object %.100U at %p, file \"%.300s\", line %d>",
- co->co_name, co, filename, lineno);
+ else
+ lineno = -1;
+ if (co->co_filename && PyUnicode_Check(co->co_filename)) {
+ return PyUnicode_FromFormat(
+ "<code object %.100U at %p, file \"%.300U\", line %d>",
+ co->co_name, co, co->co_filename, lineno);
+ } else {
+ return PyUnicode_FromFormat(
+ "<code object %.100U at %p, file ???, line %d>",
+ co->co_name, co, lineno);
+ }
}
static PyObject *
Modified: python/branches/py3k-jit/Objects/longobject.c
==============================================================================
--- python/branches/py3k-jit/Objects/longobject.c (original)
+++ python/branches/py3k-jit/Objects/longobject.c Mon May 10 23:19:57 2010
@@ -2492,10 +2492,7 @@
Py_ssize_t sign;
if (Py_SIZE(a) != Py_SIZE(b)) {
- if (ABS(Py_SIZE(a)) == 0 && ABS(Py_SIZE(b)) == 0)
- sign = 0;
- else
- sign = Py_SIZE(a) - Py_SIZE(b);
+ sign = Py_SIZE(a) - Py_SIZE(b);
}
else {
Py_ssize_t i = ABS(Py_SIZE(a));
@@ -3772,7 +3769,7 @@
static int
long_bool(PyLongObject *v)
{
- return ABS(Py_SIZE(v)) != 0;
+ return Py_SIZE(v) != 0;
}
static PyObject *
Modified: python/branches/py3k-jit/Objects/moduleobject.c
==============================================================================
--- python/branches/py3k-jit/Objects/moduleobject.c (original)
+++ python/branches/py3k-jit/Objects/moduleobject.c Mon May 10 23:19:57 2010
@@ -191,8 +191,8 @@
return _PyUnicode_AsString(nameobj);
}
-const char *
-PyModule_GetFilename(PyObject *m)
+static PyObject*
+module_getfilename(PyObject *m)
{
PyObject *d;
PyObject *fileobj;
@@ -208,6 +208,16 @@
PyErr_SetString(PyExc_SystemError, "module filename missing");
return NULL;
}
+ return fileobj;
+}
+
+const char *
+PyModule_GetFilename(PyObject *m)
+{
+ PyObject *fileobj;
+ fileobj = module_getfilename(m);
+ if (fileobj == NULL)
+ return NULL;
return _PyUnicode_AsString(fileobj);
}
@@ -327,19 +337,19 @@
module_repr(PyModuleObject *m)
{
const char *name;
- const char *filename;
+ PyObject *filename;
name = PyModule_GetName((PyObject *)m);
if (name == NULL) {
PyErr_Clear();
name = "?";
}
- filename = PyModule_GetFilename((PyObject *)m);
+ filename = module_getfilename((PyObject *)m);
if (filename == NULL) {
PyErr_Clear();
return PyUnicode_FromFormat("<module '%s' (built-in)>", name);
}
- return PyUnicode_FromFormat("<module '%s' from '%s'>", name, filename);
+ return PyUnicode_FromFormat("<module '%s' from '%U'>", name, filename);
}
static int
Modified: python/branches/py3k-jit/Python/errors.c
==============================================================================
--- python/branches/py3k-jit/Python/errors.c (original)
+++ python/branches/py3k-jit/Python/errors.c Mon May 10 23:19:57 2010
@@ -446,7 +446,7 @@
PyObject *
PyErr_SetFromErrnoWithFilename(PyObject *exc, const char *filename)
{
- PyObject *name = filename ? PyUnicode_FromString(filename) : NULL;
+ PyObject *name = filename ? PyUnicode_DecodeFSDefault(filename) : NULL;
PyObject *result = PyErr_SetFromErrnoWithFilenameObject(exc, name);
Py_XDECREF(name);
return result;
Modified: python/branches/py3k-jit/Python/pythonrun.c
==============================================================================
--- python/branches/py3k-jit/Python/pythonrun.c (original)
+++ python/branches/py3k-jit/Python/pythonrun.c Mon May 10 23:19:57 2010
@@ -1896,7 +1896,7 @@
err_input(perrdetail *err)
{
PyObject *v, *w, *errtype, *errtext;
- PyObject* u = NULL;
+ PyObject *msg_obj = NULL;
char *msg = NULL;
errtype = PyExc_SyntaxError;
switch (err->error) {
@@ -1952,14 +1952,9 @@
case E_DECODE: {
PyObject *type, *value, *tb;
PyErr_Fetch(&type, &value, &tb);
- if (value != NULL) {
- u = PyObject_Str(value);
- if (u != NULL) {
- msg = _PyUnicode_AsString(u);
- }
- }
- if (msg == NULL)
- msg = "unknown decode error";
+ msg = "unknown decode error";
+ if (value != NULL)
+ msg_obj = PyObject_Str(value);
Py_XDECREF(type);
Py_XDECREF(value);
Py_XDECREF(tb);
@@ -1988,14 +1983,18 @@
}
v = Py_BuildValue("(ziiN)", err->filename,
err->lineno, err->offset, errtext);
- w = NULL;
- if (v != NULL)
- w = Py_BuildValue("(sO)", msg, v);
- Py_XDECREF(u);
+ if (v != NULL) {
+ if (msg_obj)
+ w = Py_BuildValue("(OO)", msg_obj, v);
+ else
+ w = Py_BuildValue("(sO)", msg, v);
+ } else
+ w = NULL;
Py_XDECREF(v);
PyErr_SetObject(errtype, w);
Py_XDECREF(w);
cleanup:
+ Py_XDECREF(msg_obj);
if (err->text != NULL) {
PyObject_FREE(err->text);
err->text = NULL;
@@ -2255,6 +2254,10 @@
PyOS_setsig(int sig, PyOS_sighandler_t handler)
{
#ifdef HAVE_SIGACTION
+ /* Some code in Modules/signalmodule.c depends on sigaction() being
+ * used here if HAVE_SIGACTION is defined. Fix that if this code
+ * changes to invalidate that assumption.
+ */
struct sigaction context, ocontext;
context.sa_handler = handler;
sigemptyset(&context.sa_mask);
More information about the Python-checkins
mailing list