summaryrefslogtreecommitdiffstats
path: root/Lib
diff options
context:
space:
mode:
authorAntoine Pitrou <solipsis@pitrou.net>2015-02-15 17:03:59 (GMT)
committerAntoine Pitrou <solipsis@pitrou.net>2015-02-15 17:03:59 (GMT)
commit57fffd6f99d55ccd623b381622b989410a695b99 (patch)
treee7496d2dd553e3843195302918b6cb874eb25704 /Lib
parent0aa74e10bb7697db00514d62269ff9cae7bd7af9 (diff)
downloadcpython-57fffd6f99d55ccd623b381622b989410a695b99.zip
cpython-57fffd6f99d55ccd623b381622b989410a695b99.tar.gz
cpython-57fffd6f99d55ccd623b381622b989410a695b99.tar.bz2
Issue #23146: Fix mishandling of absolute Windows paths with forward slashes in pathlib.
Detected and fixed by Serhiy.
Diffstat (limited to 'Lib')
-rw-r--r--Lib/pathlib.py4
-rw-r--r--Lib/test/test_pathlib.py36
2 files changed, 24 insertions, 16 deletions
diff --git a/Lib/pathlib.py b/Lib/pathlib.py
index 73fd432..918ac8d 100644
--- a/Lib/pathlib.py
+++ b/Lib/pathlib.py
@@ -73,6 +73,10 @@ class _Flavour(object):
# parts. This makes the result of parsing e.g.
# ("C:", "/", "a") reasonably intuitive.
for part in it:
+ if not part:
+ continue
+ if altsep:
+ part = part.replace(altsep, sep)
drv = self.splitroot(part)[0]
if drv:
break
diff --git a/Lib/test/test_pathlib.py b/Lib/test/test_pathlib.py
index ab88c34..11420e2 100644
--- a/Lib/test/test_pathlib.py
+++ b/Lib/test/test_pathlib.py
@@ -105,31 +105,35 @@ class NTFlavourTest(_BaseFlavourTest, unittest.TestCase):
check = self._check_parse_parts
# First part is anchored
check(['c:'], ('c:', '', ['c:']))
- check(['c:\\'], ('c:', '\\', ['c:\\']))
- check(['\\'], ('', '\\', ['\\']))
+ check(['c:/'], ('c:', '\\', ['c:\\']))
+ check(['/'], ('', '\\', ['\\']))
check(['c:a'], ('c:', '', ['c:', 'a']))
- check(['c:\\a'], ('c:', '\\', ['c:\\', 'a']))
- check(['\\a'], ('', '\\', ['\\', 'a']))
+ check(['c:/a'], ('c:', '\\', ['c:\\', 'a']))
+ check(['/a'], ('', '\\', ['\\', 'a']))
# UNC paths
- check(['\\\\a\\b'], ('\\\\a\\b', '\\', ['\\\\a\\b\\']))
- check(['\\\\a\\b\\'], ('\\\\a\\b', '\\', ['\\\\a\\b\\']))
- check(['\\\\a\\b\\c'], ('\\\\a\\b', '\\', ['\\\\a\\b\\', 'c']))
+ check(['//a/b'], ('\\\\a\\b', '\\', ['\\\\a\\b\\']))
+ check(['//a/b/'], ('\\\\a\\b', '\\', ['\\\\a\\b\\']))
+ check(['//a/b/c'], ('\\\\a\\b', '\\', ['\\\\a\\b\\', 'c']))
# Second part is anchored, so that the first part is ignored
check(['a', 'Z:b', 'c'], ('Z:', '', ['Z:', 'b', 'c']))
- check(['a', 'Z:\\b', 'c'], ('Z:', '\\', ['Z:\\', 'b', 'c']))
- check(['a', '\\b', 'c'], ('', '\\', ['\\', 'b', 'c']))
+ check(['a', 'Z:/b', 'c'], ('Z:', '\\', ['Z:\\', 'b', 'c']))
# UNC paths
- check(['a', '\\\\b\\c', 'd'], ('\\\\b\\c', '\\', ['\\\\b\\c\\', 'd']))
+ check(['a', '//b/c', 'd'], ('\\\\b\\c', '\\', ['\\\\b\\c\\', 'd']))
# Collapsing and stripping excess slashes
- check(['a', 'Z:\\\\b\\\\c\\', 'd\\'], ('Z:', '\\', ['Z:\\', 'b', 'c', 'd']))
+ check(['a', 'Z://b//c/', 'd/'], ('Z:', '\\', ['Z:\\', 'b', 'c', 'd']))
# UNC paths
- check(['a', '\\\\b\\c\\\\', 'd'], ('\\\\b\\c', '\\', ['\\\\b\\c\\', 'd']))
+ check(['a', '//b/c//', 'd'], ('\\\\b\\c', '\\', ['\\\\b\\c\\', 'd']))
# Extended paths
- check(['\\\\?\\c:\\'], ('\\\\?\\c:', '\\', ['\\\\?\\c:\\']))
- check(['\\\\?\\c:\\a'], ('\\\\?\\c:', '\\', ['\\\\?\\c:\\', 'a']))
+ check(['//?/c:/'], ('\\\\?\\c:', '\\', ['\\\\?\\c:\\']))
+ check(['//?/c:/a'], ('\\\\?\\c:', '\\', ['\\\\?\\c:\\', 'a']))
+ check(['//?/c:/a', '/b'], ('\\\\?\\c:', '\\', ['\\\\?\\c:\\', 'b']))
# Extended UNC paths (format is "\\?\UNC\server\share")
- check(['\\\\?\\UNC\\b\\c'], ('\\\\?\\UNC\\b\\c', '\\', ['\\\\?\\UNC\\b\\c\\']))
- check(['\\\\?\\UNC\\b\\c\\d'], ('\\\\?\\UNC\\b\\c', '\\', ['\\\\?\\UNC\\b\\c\\', 'd']))
+ check(['//?/UNC/b/c'], ('\\\\?\\UNC\\b\\c', '\\', ['\\\\?\\UNC\\b\\c\\']))
+ check(['//?/UNC/b/c/d'], ('\\\\?\\UNC\\b\\c', '\\', ['\\\\?\\UNC\\b\\c\\', 'd']))
+ # Second part has a root but not drive
+ check(['a', '/b', 'c'], ('', '\\', ['\\', 'b', 'c']))
+ check(['Z:/a', '/b', 'c'], ('Z:', '\\', ['Z:\\', 'b', 'c']))
+ check(['//?/Z:/a', '/b', 'c'], ('\\\\?\\Z:', '\\', ['\\\\?\\Z:\\', 'b', 'c']))
def test_splitroot(self):
f = self.flavour.splitroot