summaryrefslogtreecommitdiffstats
path: root/Lib/shutil.py
diff options
context:
space:
mode:
authorBruno P. Kinoshita <kinow@users.noreply.github.com>2019-11-27 01:10:37 (GMT)
committerGiampaolo Rodola <g.rodola@gmail.com>2019-11-27 01:10:37 (GMT)
commit9bbcbc9f6dfe1368fe7330b117707f828e6a2c18 (patch)
tree8a4c4de3fd1e0f90885006c6b26c51bb3ad0df3c /Lib/shutil.py
parentc7c01ab1e5415b772c68e15f1aba51e520010830 (diff)
downloadcpython-9bbcbc9f6dfe1368fe7330b117707f828e6a2c18.zip
cpython-9bbcbc9f6dfe1368fe7330b117707f828e6a2c18.tar.gz
cpython-9bbcbc9f6dfe1368fe7330b117707f828e6a2c18.tar.bz2
bpo-38688, shutil.copytree: consume iterator and create list of entries to prevent infinite recursion (GH-17098)
Diffstat (limited to 'Lib/shutil.py')
-rw-r--r--Lib/shutil.py13
1 files changed, 7 insertions, 6 deletions
diff --git a/Lib/shutil.py b/Lib/shutil.py
index f97de78..8f609b3 100644
--- a/Lib/shutil.py
+++ b/Lib/shutil.py
@@ -442,7 +442,7 @@ def ignore_patterns(*patterns):
def _copytree(entries, src, dst, symlinks, ignore, copy_function,
ignore_dangling_symlinks, dirs_exist_ok=False):
if ignore is not None:
- ignored_names = ignore(src, set(os.listdir(src)))
+ ignored_names = ignore(src, {x.name for x in entries})
else:
ignored_names = set()
@@ -543,11 +543,12 @@ def copytree(src, dst, symlinks=False, ignore=None, copy_function=copy2,
"""
sys.audit("shutil.copytree", src, dst)
- with os.scandir(src) as entries:
- return _copytree(entries=entries, src=src, dst=dst, symlinks=symlinks,
- ignore=ignore, copy_function=copy_function,
- ignore_dangling_symlinks=ignore_dangling_symlinks,
- dirs_exist_ok=dirs_exist_ok)
+ with os.scandir(src) as itr:
+ entries = list(itr)
+ return _copytree(entries=entries, src=src, dst=dst, symlinks=symlinks,
+ ignore=ignore, copy_function=copy_function,
+ ignore_dangling_symlinks=ignore_dangling_symlinks,
+ dirs_exist_ok=dirs_exist_ok)
if hasattr(os.stat_result, 'st_file_attributes'):
# Special handling for directory junctions to make them behave like