Windows specific directory handling

On windows os.open does not work for directories.
If borg tries to open an directory on windows, None is returned
as file descriptor. The archive and archiver where adjusted to
handle the case if a file descriptor is None.
This commit is contained in:
Jürg Rast 2019-08-08 23:48:23 +02:00
parent 6b426d08d7
commit bff97a99e1
3 changed files with 11 additions and 3 deletions

View file

@ -239,7 +239,9 @@ def OsOpen(*, flags, path=None, parent_fd=None, name=None, noatime=False, op='op
try:
yield fd
finally:
os.close(fd)
# On windows fd is None for directories.
if fd is not None:
os.close(fd)
class DownloadPipeline:

View file

@ -625,8 +625,10 @@ class Archiver:
elif stat.S_ISDIR(st.st_mode):
with OsOpen(path=path, parent_fd=parent_fd, name=name, flags=flags_dir,
noatime=True, op='dir_open') as child_fd:
with backup_io('fstat'):
st = stat_update_check(st, os.fstat(child_fd))
# child_fd is None for directories on windows, in that case a race condition check is not possible.
if child_fd is not None:
with backup_io('fstat'):
st = stat_update_check(st, os.fstat(child_fd))
if recurse:
tag_names = dir_is_tagged(path, exclude_caches, exclude_if_present)
if tag_names:

View file

@ -8,6 +8,7 @@ import sys
import textwrap
from .process import prepare_subprocess_env
from ..platformflags import is_win32
from ..constants import * # NOQA
@ -230,6 +231,9 @@ def os_open(*, flags, path=None, parent_fd=None, name=None, noatime=False):
fname = name # use name relative to parent_fd
else:
fname, parent_fd = path, None # just use the path
if is_win32 and os.path.isdir(fname):
# Directories can not be opened on Windows.
return None
_flags_normal = flags
if noatime:
_flags_noatime = _flags_normal | O_('NOATIME')