Author: Armin Rigo <ar...@tunes.org> Branch: py3.5 Changeset: r86578:2eee1909c4d1 Date: 2016-08-26 19:11 +0200 http://bitbucket.org/pypy/pypy/changeset/2eee1909c4d1/
Log: hg merge py3k diff --git a/pypy/module/_file/readinto.py b/pypy/module/_file/readinto.py deleted file mode 100644 --- a/pypy/module/_file/readinto.py +++ /dev/null @@ -1,82 +0,0 @@ -import sys, errno -from rpython.rlib import rposix -from rpython.rlib.objectmodel import keepalive_until_here -from rpython.rtyper.lltypesystem import lltype, rffi -from pypy.module._file.interp_file import is_wouldblock_error, signal_checker - -_WIN32 = sys.platform.startswith('win') -UNDERSCORE_ON_WIN32 = '_' if _WIN32 else '' - -os_read = rffi.llexternal(UNDERSCORE_ON_WIN32 + 'read', - [rffi.INT, rffi.CCHARP, rffi.SIZE_T], - rffi.SSIZE_T, save_err=rffi.RFFI_SAVE_ERRNO) - - -def direct_readinto(self, w_rwbuffer): - rwbuffer = self.space.writebuf_w(w_rwbuffer) - stream = self.getstream() - size = rwbuffer.getlength() - target_address = lltype.nullptr(rffi.CCHARP.TO) - fd = -1 - target_pos = 0 - - if size > 64: - try: - target_address = rwbuffer.get_raw_address() - except ValueError: - pass - else: - fd = stream.try_to_find_file_descriptor() - - if fd < 0 or not target_address: - # fall-back - MAX_PART = 1024 * 1024 # 1 MB - while size > MAX_PART: - data = self.direct_read(MAX_PART) - rwbuffer.setslice(target_pos, data) - target_pos += len(data) - size -= len(data) - if len(data) != MAX_PART: - break - else: - data = self.direct_read(size) - rwbuffer.setslice(target_pos, data) - target_pos += len(data) - - else: - # optimized case: reading more than 64 bytes into a rwbuffer - # with a valid raw address - self.check_readable() - - # first "read" the part that is already sitting in buffers, if any - initial_size = min(size, stream.count_buffered_bytes()) - if initial_size > 0: - data = stream.read(initial_size) - rwbuffer.setslice(target_pos, data) - target_pos += len(data) - size -= len(data) - - # then call os_read() to get the rest - if size > 0: - stream.flush() - while True: - got = os_read(fd, rffi.ptradd(target_address, target_pos), size) - got = rffi.cast(lltype.Signed, got) - if got > 0: - target_pos += got - size -= got - if size <= 0: - break - elif got == 0: - break - else: - err = rposix.get_saved_errno() - if err == errno.EINTR: - signal_checker(self.space)() - continue - if is_wouldblock_error(err) and target_pos > 0: - break - raise OSError(err, "read error") - keepalive_until_here(rwbuffer) - - return self.space.wrap(target_pos) diff --git a/pypy/module/_socket/interp_func.py b/pypy/module/_socket/interp_func.py --- a/pypy/module/_socket/interp_func.py +++ b/pypy/module/_socket/interp_func.py @@ -142,7 +142,10 @@ @unwrap_spec(fd=int) def dup(space, fd): - newfd = rsocket.dup(fd) + try: + newfd = rsocket.dup(fd) + except SocketError as e: + raise converted_error(space, e) return space.wrap(newfd) @unwrap_spec(fd=int, family=int, type=int, proto=int) diff --git a/pypy/module/_socket/test/test_sock_app.py b/pypy/module/_socket/test/test_sock_app.py --- a/pypy/module/_socket/test/test_sock_app.py +++ b/pypy/module/_socket/test/test_sock_app.py @@ -552,6 +552,10 @@ fd = socket.dup(s.fileno()) assert s.fileno() != fd + def test_dup_error(self): + import _socket + raises(_socket.error, _socket.dup, 123456) + def test_buffer(self): # Test that send/sendall/sendto accept a buffer as arg import _socket, os diff --git a/pypy/module/posix/__init__.py b/pypy/module/posix/__init__.py --- a/pypy/module/posix/__init__.py +++ b/pypy/module/posix/__init__.py @@ -19,6 +19,7 @@ 'statvfs_result': 'app_posix.statvfs_result', 'uname_result': 'app_posix.uname_result', 'urandom': 'app_posix.urandom', + 'terminal_size': 'app_posix.terminal_size' } if os.name == 'nt': del appleveldefs['urandom'] # at interp on win32 @@ -74,6 +75,7 @@ 'abort': 'interp_posix.abort', 'urandom': 'interp_posix.urandom', 'device_encoding': 'interp_posix.device_encoding', + 'get_terminal_size': 'interp_posix.get_terminal_size' 'scandir': 'interp_scandir.scandir', } diff --git a/pypy/module/posix/app_posix.py b/pypy/module/posix/app_posix.py --- a/pypy/module/posix/app_posix.py +++ b/pypy/module/posix/app_posix.py @@ -92,6 +92,12 @@ version = structseqfield(3, "operating system version") machine = structseqfield(4, "hardware identifier") +class terminal_size(metaclass=structseqtype): + + name = "os.terminal_size" + + columns = structseqfield(0, "width of the terminal window in characters") + lines = structseqfield(1, "height of the terminal window in characters") if osname == 'posix': # POSIX: we want to check the file descriptor when fdopen() is called, diff --git a/pypy/module/posix/interp_posix.py b/pypy/module/posix/interp_posix.py --- a/pypy/module/posix/interp_posix.py +++ b/pypy/module/posix/interp_posix.py @@ -8,16 +8,18 @@ # some Pythons don't have errno.ENOTSUP ENOTSUP = 0 -from rpython.rlib import rposix, rposix_stat +from rpython.rlib import rposix, rposix_stat, rfile from rpython.rlib import objectmodel, rurandom from rpython.rlib.objectmodel import specialize -from rpython.rlib.rarithmetic import r_longlong, intmask, r_uint +from rpython.rlib.rarithmetic import r_longlong, intmask, r_uint, r_int from rpython.rlib.unroll import unrolling_iterable +from rpython.rtyper.lltypesystem import lltype from rpython.tool.sourcetools import func_with_new_name from pypy.interpreter.gateway import unwrap_spec, WrappedDefault, Unwrapper from pypy.interpreter.error import ( - OperationError, oefmt, wrap_oserror, wrap_oserror2, strerror as _strerror) + OperationError, oefmt, wrap_oserror, wrap_oserror2, strerror as _strerror, + exception_from_saved_errno) from pypy.interpreter.executioncontext import ExecutionContext @@ -2142,3 +2144,50 @@ have_functions.append("HAVE_%s" % name) if _WIN32: have_functions.append("HAVE_MS_WINDOWS") + +def get_terminal_size(space, w_fd=None): + if w_fd is None: + fd = rfile.RFile(rfile.c_stdout(), close2=(None, None)).fileno() + else: + if not space.isinstance_w(w_fd, space.w_int): + raise oefmt(space.w_TypeError, + "an integer is required, got %T", w_fd) + else: + fd = space.c_int_w(w_fd) + + if _WIN32: + if fd == 0: + handle_id = rwin32.STD_INPUT_HANDLE + elif fd == 1: + handle_id = rwin32.STD_OUTPUT_HANDLE + elif fd == 2: + handle_id = rwin32.STD_ERROR_HANDLE + else: + raise oefmt(space.w_ValueError, "bad file descriptor") + + handle = rwin32.GetStdHandle(handle_id) + + if handle == rwin32.NULL_HANDLE: + raise oefmt(space.w_OSError, "handle cannot be retrieved") + elif handle == rwin32.INVALID_HANDLE_VALUE: + raise rwin32.lastSavedWindowsError() + with lltype.scoped_alloc(rwin32.CONSOLE_SCREEN_BUFFER_INFO) as buffer_info: + success = rwin32.GetConsoleScreenBufferInfo(handle, buffer_info) + if not success: + raise rwin32.lastSavedWindowsError() + w_columns = space.wrap(r_int(buffer_info.c_srWindow.c_Right) - r_int(buffer_info.c_srWindow.c_Left) + 1) + w_lines = space.wrap(r_int(buffer_info.c_srWindow.c_Bottom) - r_int(buffer_info.c_srWindow.c_Top) + 1) + else: + with lltype.scoped_alloc(rposix.WINSIZE) as winsize: + failed = rposix.c_ioctl_voidp(fd, rposix.TIOCGWINSZ, winsize) + if failed: + raise exception_from_saved_errno(space, space.w_OSError) + + w_columns = space.wrap(r_uint(winsize.c_ws_col)) + w_lines = space.wrap(r_uint(winsize.c_ws_row)) + + w_tuple = space.newtuple([w_columns, w_lines]) + w_terminal_size = space.getattr(space.getbuiltinmodule(os.name), + space.wrap('terminal_size')) + + return space.call_function(w_terminal_size, w_tuple) diff --git a/pypy/module/sys/__init__.py b/pypy/module/sys/__init__.py --- a/pypy/module/sys/__init__.py +++ b/pypy/module/sys/__init__.py @@ -139,12 +139,10 @@ space = self.space if not space.config.translating: - ##from pypy.module.sys.interp_encoding import _getfilesystemencoding - ##self.filesystemencoding = _getfilesystemencoding(space) + from pypy.module.sys.interp_encoding import _getfilesystemencoding + self.filesystemencoding = _getfilesystemencoding(space) # XXX the two lines above take a few seconds to run whenever - # we initialize the space; for tests, use a simpler version - from pypy.module.sys.interp_encoding import base_encoding - self.filesystemencoding = base_encoding + # we initialize the space def flush_std_files(self, space): w_stdout = space.sys.getdictvalue(space, 'stdout') diff --git a/rpython/rlib/rposix.py b/rpython/rlib/rposix.py --- a/rpython/rlib/rposix.py +++ b/rpython/rlib/rposix.py @@ -258,6 +258,7 @@ if not _WIN32: UID_T = rffi_platform.SimpleType('uid_t', rffi.UINT) GID_T = rffi_platform.SimpleType('gid_t', rffi.UINT) + TIOCGWINSZ = rffi_platform.DefinedConstantInteger('TIOCGWINSZ') TMS = rffi_platform.Struct( 'struct tms', [('tms_utime', rffi.INT), @@ -265,6 +266,12 @@ ('tms_cutime', rffi.INT), ('tms_cstime', rffi.INT)]) + WINSIZE = rffi_platform.Struct( + 'struct winsize', [('ws_row', rffi.USHORT), + ('ws_col', rffi.USHORT), + ('ws_xpixel', rffi.USHORT), + ('ws_ypixel', rffi.USHORT)]) + GETPGRP_HAVE_ARG = rffi_platform.Has("getpgrp(0)") SETPGRP_HAVE_ARG = rffi_platform.Has("setpgrp(0, 0)") @@ -628,6 +635,8 @@ macro=True, save_err=rffi.RFFI_FULL_ERRNO_ZERO) c_closedir = external('closedir', [DIRP], rffi.INT, releasegil=False) c_dirfd = external('dirfd', [DIRP], rffi.INT, releasegil=False) + c_ioctl_voidp = external('ioctl', [rffi.INT, rffi.UINT, rffi.VOIDP], rffi.INT, + save_err=rffi.RFFI_SAVE_ERRNO) else: dirent_config = {} diff --git a/rpython/rlib/rsocket.py b/rpython/rlib/rsocket.py --- a/rpython/rlib/rsocket.py +++ b/rpython/rlib/rsocket.py @@ -1121,14 +1121,14 @@ return result else: def dup(fd): - return _c.dup(fd) - - def fromfd(fd, family, type, proto=0, SocketClass=RSocket): - # Dup the fd so it and the socket can be closed independently fd = _c.dup(fd) if fd < 0: raise last_error() - return make_socket(fd, family, type, proto, SocketClass) + return fd + +def fromfd(fd, family, type, proto=0, SocketClass=RSocket): + # Dup the fd so it and the socket can be closed independently + return make_socket(dup(fd), family, type, proto, SocketClass) def getdefaulttimeout(): return defaults.timeout diff --git a/rpython/rlib/rwin32.py b/rpython/rlib/rwin32.py --- a/rpython/rlib/rwin32.py +++ b/rpython/rlib/rwin32.py @@ -59,6 +59,24 @@ SYSTEMTIME = rffi_platform.Struct('SYSTEMTIME', []) + Struct = rffi_platform.Struct + COORD = Struct("COORD", + [("X", rffi.SHORT), + ("Y", rffi.SHORT)]) + + SMALL_RECT = Struct("SMALL_RECT", + [("Left", rffi.SHORT), + ("Top", rffi.SHORT), + ("Right", rffi.SHORT), + ("Bottom", rffi.SHORT)]) + + CONSOLE_SCREEN_BUFFER_INFO = Struct("CONSOLE_SCREEN_BUFFER_INFO", + [("dwSize", COORD), + ("dwCursorPosition", COORD), + ("wAttributes", WORD.ctype_hint), + ("srWindow", SMALL_RECT), + ("dwMaximumWindowSize", COORD)]) + OSVERSIONINFOEX = rffi_platform.Struct( 'OSVERSIONINFOEX', [('dwOSVersionInfoSize', rffi.UINT), @@ -93,7 +111,8 @@ PROCESS_VM_WRITE CTRL_C_EVENT CTRL_BREAK_EVENT MB_ERR_INVALID_CHARS ERROR_NO_UNICODE_TRANSLATION - WC_NO_BEST_FIT_CHARS + WC_NO_BEST_FIT_CHARS STD_INPUT_HANDLE STD_OUTPUT_HANDLE + STD_ERROR_HANDLE """ from rpython.translator.platform import host_factory static_platform = host_factory() @@ -444,3 +463,13 @@ return rffi.cast(lltype.Signed, _GetConsoleOutputCP()) _wenviron_items, _wgetenv, _wputenv = make_env_impls(win32=True) + + + _GetStdHandle = winexternal( + 'GetStdHandle', [DWORD], HANDLE) + + def GetStdHandle(handle_id): + return _GetStdHandle(handle_id) + CONSOLE_SCREEN_BUFFER_INFO_P = lltype.Ptr(CONSOLE_SCREEN_BUFFER_INFO) + GetConsoleScreenBufferInfo = winexternal( + "GetConsoleScreenBufferInfo", [HANDLE, CONSOLE_SCREEN_BUFFER_INFO_P], BOOL) _______________________________________________ pypy-commit mailing list pypy-commit@python.org https://mail.python.org/mailman/listinfo/pypy-commit