diff options
-rw-r--r-- | Lib/test/test_imp.py | 13 | ||||
-rw-r--r-- | Python/import.c | 90 |
2 files changed, 65 insertions, 38 deletions
diff --git a/Lib/test/test_imp.py b/Lib/test/test_imp.py index 6dd1e21..233d3da 100644 --- a/Lib/test/test_imp.py +++ b/Lib/test/test_imp.py @@ -306,11 +306,24 @@ class PEP3147Tests(unittest.TestCase): os.sep.join(('.', 'pep3147', '__init__.py'))) +class NullImporterTests(unittest.TestCase): + @unittest.skipIf(support.TESTFN_UNENCODEABLE is None, + "Need an undecodeable filename") + def test_unencodeable(self): + name = support.TESTFN_UNENCODEABLE + os.mkdir(name) + try: + self.assertRaises(ImportError, imp.NullImporter, name) + finally: + os.rmdir(name) + + def test_main(): tests = [ ImportTests, PEP3147Tests, ReloadTests, + NullImporterTests, ] try: import _thread diff --git a/Python/import.c b/Python/import.c index c06aa1c..4cdce74 100644 --- a/Python/import.c +++ b/Python/import.c @@ -3623,56 +3623,70 @@ typedef struct { static int NullImporter_init(NullImporter *self, PyObject *args, PyObject *kwds) { - char *path; - Py_ssize_t pathlen; +#ifndef MS_WINDOWS + PyObject *path; + struct stat statbuf; + int rv; if (!_PyArg_NoKeywords("NullImporter()", kwds)) return -1; - if (!PyArg_ParseTuple(args, "es:NullImporter", - Py_FileSystemDefaultEncoding, &path)) + if (!PyArg_ParseTuple(args, "O&:NullImporter", + PyUnicode_FSConverter, &path)) return -1; - pathlen = strlen(path); - if (pathlen == 0) { - PyMem_Free(path); + if (PyBytes_GET_SIZE(path) == 0) { + Py_DECREF(path); PyErr_SetString(PyExc_ImportError, "empty pathname"); return -1; - } else { -#ifndef MS_WINDOWS - struct stat statbuf; - int rv; - - rv = stat(path, &statbuf); - PyMem_Free(path); - if (rv == 0) { - /* it exists */ - if (S_ISDIR(statbuf.st_mode)) { - /* it's a directory */ - PyErr_SetString(PyExc_ImportError, - "existing directory"); - return -1; - } + } + + rv = stat(PyBytes_AS_STRING(path), &statbuf); + Py_DECREF(path); + if (rv == 0) { + /* it exists */ + if (S_ISDIR(statbuf.st_mode)) { + /* it's a directory */ + PyErr_SetString(PyExc_ImportError, "existing directory"); + return -1; } + } #else /* MS_WINDOWS */ - DWORD rv; - /* see issue1293 and issue3677: - * stat() on Windows doesn't recognise paths like - * "e:\\shared\\" and "\\\\whiterab-c2znlh\\shared" as dirs. - */ - rv = GetFileAttributesA(path); - PyMem_Free(path); - if (rv != INVALID_FILE_ATTRIBUTES) { - /* it exists */ - if (rv & FILE_ATTRIBUTE_DIRECTORY) { - /* it's a directory */ - PyErr_SetString(PyExc_ImportError, - "existing directory"); - return -1; - } + PyObject *pathobj; + DWORD rv; + wchar_t path[MAXPATHLEN+1]; + Py_ssize_t len; + + if (!_PyArg_NoKeywords("NullImporter()", kwds)) + return -1; + + if (!PyArg_ParseTuple(args, "U:NullImporter", + &pathobj)) + return -1; + + if (PyUnicode_GET_SIZE(pathobj) == 0) { + PyErr_SetString(PyExc_ImportError, "empty pathname"); + return -1; + } + + len = PyUnicode_AsWideChar((PyUnicodeObject*)pathobj, + path, sizeof(path) / sizeof(path[0])); + if (len == -1) + return -1; + /* see issue1293 and issue3677: + * stat() on Windows doesn't recognise paths like + * "e:\\shared\\" and "\\\\whiterab-c2znlh\\shared" as dirs. + */ + rv = GetFileAttributesW(path); + if (rv != INVALID_FILE_ATTRIBUTES) { + /* it exists */ + if (rv & FILE_ATTRIBUTE_DIRECTORY) { + /* it's a directory */ + PyErr_SetString(PyExc_ImportError, "existing directory"); + return -1; } -#endif } +#endif return 0; } |