[Python-checkins] bpo-38030: Fix os.stat failures on block devices on Windows (GH-15681)
Miss Islington (bot)
webhook-mailer at python.org
Wed Sep 4 18:18:08 EDT 2019
https://github.com/python/cpython/commit/cad7abf8abe657b696b9c8deb4b727e0cefaf36d
commit: cad7abf8abe657b696b9c8deb4b727e0cefaf36d
branch: 3.8
author: Miss Islington (bot) <31488909+miss-islington at users.noreply.github.com>
committer: GitHub <noreply at github.com>
date: 2019-09-04T15:18:05-07:00
summary:
bpo-38030: Fix os.stat failures on block devices on Windows (GH-15681)
(cherry picked from commit 772ec0fad57412daa53d16d7019b6b2fe6e94942)
Co-authored-by: Steve Dower <steve.dower at python.org>
files:
A Misc/NEWS.d/next/Windows/2019-09-04-14-01-08.bpo-38030._USdtk.rst
M Lib/test/test_os.py
M Modules/posixmodule.c
diff --git a/Lib/test/test_os.py b/Lib/test/test_os.py
index 440cd6c1cf73..8ff0296fad0b 100644
--- a/Lib/test/test_os.py
+++ b/Lib/test/test_os.py
@@ -591,6 +591,14 @@ def test_access_denied(self):
result = os.stat(fname)
self.assertNotEqual(result.st_size, 0)
+ @unittest.skipUnless(sys.platform == "win32", "Win32 specific tests")
+ def test_stat_block_device(self):
+ # bpo-38030: os.stat fails for block devices
+ # Test a filename like "//./C:"
+ fname = "//./" + os.path.splitdrive(os.getcwd())[0]
+ result = os.stat(fname)
+ self.assertEqual(result.st_mode, stat.S_IFBLK)
+
class UtimeTests(unittest.TestCase):
def setUp(self):
diff --git a/Misc/NEWS.d/next/Windows/2019-09-04-14-01-08.bpo-38030._USdtk.rst b/Misc/NEWS.d/next/Windows/2019-09-04-14-01-08.bpo-38030._USdtk.rst
new file mode 100644
index 000000000000..f1be8a1e1c86
--- /dev/null
+++ b/Misc/NEWS.d/next/Windows/2019-09-04-14-01-08.bpo-38030._USdtk.rst
@@ -0,0 +1 @@
+Fixes :func:`os.stat` failing for block devices on Windows
diff --git a/Modules/posixmodule.c b/Modules/posixmodule.c
index b9e8c0d94c20..771c5616152c 100644
--- a/Modules/posixmodule.c
+++ b/Modules/posixmodule.c
@@ -1793,13 +1793,13 @@ win32_xstat_impl(const wchar_t *path, struct _Py_stat_struct *result,
case ERROR_INVALID_PARAMETER:
case ERROR_INVALID_FUNCTION:
case ERROR_NOT_SUPPORTED:
- retval = -1;
+ /* Volumes and physical disks are block devices, e.g.
+ \\.\C: and \\.\PhysicalDrive0. */
+ memset(result, 0, sizeof(*result));
+ result->st_mode = 0x6000; /* S_IFBLK */
goto cleanup;
}
- /* Volumes and physical disks are block devices, e.g.
- \\.\C: and \\.\PhysicalDrive0. */
- memset(result, 0, sizeof(*result));
- result->st_mode = 0x6000; /* S_IFBLK */
+ retval = -1;
goto cleanup;
}
}
@@ -1826,7 +1826,14 @@ win32_xstat_impl(const wchar_t *path, struct _Py_stat_struct *result,
cleanup:
if (hFile != INVALID_HANDLE_VALUE) {
- CloseHandle(hFile);
+ /* Preserve last error if we are failing */
+ error = retval ? GetLastError() : 0;
+ if (!CloseHandle(hFile)) {
+ retval = -1;
+ } else if (retval) {
+ /* Restore last error */
+ SetLastError(error);
+ }
}
return retval;
More information about the Python-checkins
mailing list