beam: fix path_sandbox root="/" containment (was requiring "//" prefix)
This commit is contained in:
1 parent
ec60dedf74
commit
2b080cfca9
1 file changed
+16
-5
@@ -59,13 +59,22 @@ def safe_join(root, *parts):
|
||||
candidate = os.path.join(rr, *parts) if parts else rr
|
||||
# normalize (collapses . and redundant slashes) but does not resolve symlinks
|
||||
candidate = os.path.normpath(candidate)
|
||||
# containment check on the normalized (pre-symlink) form
|
||||
if candidate != rr and not candidate.startswith(rr + os.sep):
|
||||
raise PathEscapeError("joined path escapes root: %r" % candidate)
|
||||
# containment check on the normalized (pre-symlink) form.
|
||||
# Special-case root == "/" so we don't require a "//" prefix.
|
||||
if rr == os.sep:
|
||||
if not (candidate == rr or candidate.startswith(rr)):
|
||||
raise PathEscapeError("joined path escapes root: %r" % candidate)
|
||||
else:
|
||||
if candidate != rr and not candidate.startswith(rr + os.sep):
|
||||
raise PathEscapeError("joined path escapes root: %r" % candidate)
|
||||
# now resolve symlinks and re-check containment
|
||||
resolved = os.path.realpath(candidate)
|
||||
if resolved != rr and not resolved.startswith(rr + os.sep):
|
||||
raise PathEscapeError("symlink escape: %r -> %r" % (candidate, resolved))
|
||||
if rr == os.sep:
|
||||
if not (resolved == rr or resolved.startswith(rr)):
|
||||
raise PathEscapeError("symlink escape: %r -> %r" % (candidate, resolved))
|
||||
else:
|
||||
if resolved != rr and not resolved.startswith(rr + os.sep):
|
||||
raise PathEscapeError("symlink escape: %r -> %r" % (candidate, resolved))
|
||||
return resolved
|
||||
|
||||
|
||||
@@ -86,4 +95,6 @@ def is_within(root, target):
|
||||
rt = os.path.realpath(target)
|
||||
except (OSError, ValueError):
|
||||
return False
|
||||
if rr == os.sep:
|
||||
return rt == rr or rt.startswith(rr)
|
||||
return rt == rr or rt.startswith(rr + os.sep)
|
||||
Reference in new issue
Block a user