diff options
Diffstat (limited to 'Modules')
-rw-r--r-- | Modules/posixmodule.c | 123 |
1 files changed, 64 insertions, 59 deletions
diff --git a/Modules/posixmodule.c b/Modules/posixmodule.c index 10549d6f..5134ed7 100644 --- a/Modules/posixmodule.c +++ b/Modules/posixmodule.c @@ -506,17 +506,6 @@ void _Py_attribute_data_to_stat(BY_HANDLE_FILE_INFORMATION *, ULONG, struct _Py_stat_struct *); #endif -#ifdef MS_WINDOWS -static int -win32_warn_bytes_api() -{ - return PyErr_WarnEx(PyExc_DeprecationWarning, - "The Windows bytes API has been deprecated, " - "use Unicode filenames instead", - 1); -} -#endif - #ifndef MS_WINDOWS PyObject * @@ -3334,83 +3323,99 @@ os_lchown_impl(PyObject *module, path_t *path, uid_t uid, gid_t gid) static PyObject * posix_getcwd(int use_bytes) { - char *buf, *tmpbuf; - char *cwd; - const size_t chunk = 1024; - size_t buflen = 0; - PyObject *obj; - #ifdef MS_WINDOWS - if (!use_bytes) { - wchar_t wbuf[MAXPATHLEN]; - wchar_t *wbuf2 = wbuf; - PyObject *resobj; - DWORD len; - Py_BEGIN_ALLOW_THREADS - len = GetCurrentDirectoryW(Py_ARRAY_LENGTH(wbuf), wbuf); - /* If the buffer is large enough, len does not include the - terminating \0. If the buffer is too small, len includes - the space needed for the terminator. */ - if (len >= Py_ARRAY_LENGTH(wbuf)) { + wchar_t wbuf[MAXPATHLEN]; + wchar_t *wbuf2 = wbuf; + DWORD len; + + Py_BEGIN_ALLOW_THREADS + len = GetCurrentDirectoryW(Py_ARRAY_LENGTH(wbuf), wbuf); + /* If the buffer is large enough, len does not include the + terminating \0. If the buffer is too small, len includes + the space needed for the terminator. */ + if (len >= Py_ARRAY_LENGTH(wbuf)) { + if (len >= PY_SSIZE_T_MAX / sizeof(wchar_t)) { wbuf2 = PyMem_RawMalloc(len * sizeof(wchar_t)); - if (wbuf2) - len = GetCurrentDirectoryW(len, wbuf2); } - Py_END_ALLOW_THREADS - if (!wbuf2) { - PyErr_NoMemory(); - return NULL; + else { + wbuf2 = NULL; } - if (!len) { - if (wbuf2 != wbuf) - PyMem_RawFree(wbuf2); - return PyErr_SetFromWindowsErr(0); + if (wbuf2) { + len = GetCurrentDirectoryW(len, wbuf2); } - resobj = PyUnicode_FromWideChar(wbuf2, len); + } + Py_END_ALLOW_THREADS + + if (!wbuf2) { + PyErr_NoMemory(); + return NULL; + } + if (!len) { if (wbuf2 != wbuf) PyMem_RawFree(wbuf2); - return resobj; + return PyErr_SetFromWindowsErr(0); } - if (win32_warn_bytes_api()) - return NULL; -#endif + PyObject *resobj = PyUnicode_FromWideChar(wbuf2, len); + if (wbuf2 != wbuf) { + PyMem_RawFree(wbuf2); + } + + if (use_bytes) { + if (resobj == NULL) { + return NULL; + } + Py_SETREF(resobj, PyUnicode_EncodeFSDefault(resobj)); + } + + return resobj; +#else + const size_t chunk = 1024; + + char *buf = NULL; + char *cwd = NULL; + size_t buflen = 0; - buf = cwd = NULL; Py_BEGIN_ALLOW_THREADS do { - buflen += chunk; -#ifdef MS_WINDOWS - if (buflen > INT_MAX) { - PyErr_NoMemory(); - break; + char *newbuf; + if (buflen <= PY_SSIZE_T_MAX - chunk) { + buflen += chunk; + newbuf = PyMem_RawRealloc(buf, buflen); } -#endif - tmpbuf = PyMem_RawRealloc(buf, buflen); - if (tmpbuf == NULL) + else { + newbuf = NULL; + } + if (newbuf == NULL) { + PyMem_RawFree(buf); + buf = NULL; break; + } + buf = newbuf; - buf = tmpbuf; -#ifdef MS_WINDOWS - cwd = getcwd(buf, (int)buflen); -#else cwd = getcwd(buf, buflen); -#endif } while (cwd == NULL && errno == ERANGE); Py_END_ALLOW_THREADS + if (buf == NULL) { + return PyErr_NoMemory(); + } if (cwd == NULL) { PyMem_RawFree(buf); return posix_error(); } - if (use_bytes) + PyObject *obj; + if (use_bytes) { obj = PyBytes_FromStringAndSize(buf, strlen(buf)); - else + } + else { obj = PyUnicode_DecodeFSDefault(buf); + } PyMem_RawFree(buf); return obj; +#endif /* !MS_WINDOWS */ } |