summaryrefslogtreecommitdiff
path: root/Lib/tarfile.py
diff options
context:
space:
mode:
authorLars Gustäbel <lars@gustaebel.de>2016-04-19 08:53:14 +0200
committerLars Gustäbel <lars@gustaebel.de>2016-04-19 08:53:14 +0200
commit7c3e6848f200360ce4a7de514801d0d3b7a9da3f (patch)
tree4a82c0c7eab802bfef26941e9eb98122fbcabf50 /Lib/tarfile.py
parent1d0489269e714a9aa81a1defac96df0ab4444d91 (diff)
parent0f450abec432763b92d6a9b1a778e8c0e5232338 (diff)
downloadcpython-git-7c3e6848f200360ce4a7de514801d0d3b7a9da3f.tar.gz
Issue #24838: Merge tarfile fix from 3.5.
Diffstat (limited to 'Lib/tarfile.py')
-rwxr-xr-xLib/tarfile.py29
1 files changed, 15 insertions, 14 deletions
diff --git a/Lib/tarfile.py b/Lib/tarfile.py
index ad0f5c3946..8ed87c2f43 100755
--- a/Lib/tarfile.py
+++ b/Lib/tarfile.py
@@ -815,11 +815,11 @@ class TarInfo(object):
"""
info["magic"] = POSIX_MAGIC
- if len(info["linkname"]) > LENGTH_LINK:
+ if len(info["linkname"].encode(encoding, errors)) > LENGTH_LINK:
raise ValueError("linkname is too long")
- if len(info["name"]) > LENGTH_NAME:
- info["prefix"], info["name"] = self._posix_split_name(info["name"])
+ if len(info["name"].encode(encoding, errors)) > LENGTH_NAME:
+ info["prefix"], info["name"] = self._posix_split_name(info["name"], encoding, errors)
return self._create_header(info, USTAR_FORMAT, encoding, errors)
@@ -829,10 +829,10 @@ class TarInfo(object):
info["magic"] = GNU_MAGIC
buf = b""
- if len(info["linkname"]) > LENGTH_LINK:
+ if len(info["linkname"].encode(encoding, errors)) > LENGTH_LINK:
buf += self._create_gnu_long_header(info["linkname"], GNUTYPE_LONGLINK, encoding, errors)
- if len(info["name"]) > LENGTH_NAME:
+ if len(info["name"].encode(encoding, errors)) > LENGTH_NAME:
buf += self._create_gnu_long_header(info["name"], GNUTYPE_LONGNAME, encoding, errors)
return buf + self._create_header(info, GNU_FORMAT, encoding, errors)
@@ -892,19 +892,20 @@ class TarInfo(object):
"""
return cls._create_pax_generic_header(pax_headers, XGLTYPE, "utf-8")
- def _posix_split_name(self, name):
+ def _posix_split_name(self, name, encoding, errors):
"""Split a name longer than 100 chars into a prefix
and a name part.
"""
- prefix = name[:LENGTH_PREFIX + 1]
- while prefix and prefix[-1] != "/":
- prefix = prefix[:-1]
-
- name = name[len(prefix):]
- prefix = prefix[:-1]
-
- if not prefix or len(name) > LENGTH_NAME:
+ components = name.split("/")
+ for i in range(1, len(components)):
+ prefix = "/".join(components[:i])
+ name = "/".join(components[i:])
+ if len(prefix.encode(encoding, errors)) <= LENGTH_PREFIX and \
+ len(name.encode(encoding, errors)) <= LENGTH_NAME:
+ break
+ else:
raise ValueError("name is too long")
+
return prefix, name
@staticmethod