Skip to content

Commit 6a564c7

Browse files
happyCoder92copybara-github
authored andcommitted
PolicyBuilder: add convenience APIs for adding files/dirs that might not exist
Follow-up changes will make the regular APIs error out early for non-existing files/dirs. PiperOrigin-RevId: 819218320 Change-Id: Ice147bf5ca20f86c24b9d9dc95955f39c6ae7472
1 parent 183f3a8 commit 6a564c7

File tree

3 files changed

+63
-1
lines changed

3 files changed

+63
-1
lines changed

sandboxed_api/sandbox2/policybuilder.cc

Lines changed: 35 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -104,6 +104,22 @@ namespace {
104104
namespace file = ::sapi::file;
105105
namespace fileops = ::sapi::file_util::fileops;
106106

107+
bool IsDirectory(const std::string& path) {
108+
struct stat sb;
109+
if (stat(path.c_str(), &sb) == -1) {
110+
return false;
111+
}
112+
return S_ISDIR(sb.st_mode);
113+
}
114+
115+
bool IsFile(const std::string& path) {
116+
struct stat sb;
117+
if (stat(path.c_str(), &sb) == -1) {
118+
return false;
119+
}
120+
return !S_ISDIR(sb.st_mode);
121+
}
122+
107123
// Validates that the path is absolute and canonical.
108124
absl::StatusOr<std::string> ValidatePath(absl::string_view path,
109125
bool allow_relative_path = false) {
@@ -521,7 +537,9 @@ PolicyBuilder& PolicyBuilder::AllowLlvmCoverage() {
521537
AllowMkdir();
522538
AllowSafeFcntl();
523539
AllowSyscalls({
524-
__NR_munmap, __NR_close, __NR_lseek,
540+
__NR_munmap,
541+
__NR_close,
542+
__NR_lseek,
525543
#ifdef __NR__llseek
526544
__NR__llseek, // Newer glibc on PPC
527545
#endif
@@ -1538,6 +1556,14 @@ PolicyBuilder& PolicyBuilder::AddFile(absl::string_view path, bool is_ro) {
15381556
return AddFileAt(path, path, is_ro);
15391557
}
15401558

1559+
PolicyBuilder& PolicyBuilder::AddFileIfExists(absl::string_view path,
1560+
bool is_ro) {
1561+
if (IsFile(std::string(path))) {
1562+
AddFile(path, is_ro);
1563+
}
1564+
return *this;
1565+
}
1566+
15411567
PolicyBuilder& PolicyBuilder::AddFileAt(absl::string_view outside,
15421568
absl::string_view inside, bool is_ro) {
15431569
EnableNamespaces(); // NOLINT(clang-diagnostic-deprecated-declarations)
@@ -1611,6 +1637,14 @@ PolicyBuilder& PolicyBuilder::AddDirectory(absl::string_view path, bool is_ro) {
16111637
return AddDirectoryAt(path, path, is_ro);
16121638
}
16131639

1640+
PolicyBuilder& PolicyBuilder::AddDirectoryIfExists(absl::string_view path,
1641+
bool is_ro) {
1642+
if (IsDirectory(std::string(path))) {
1643+
AddDirectory(path, is_ro);
1644+
}
1645+
return *this;
1646+
}
1647+
16141648
PolicyBuilder& PolicyBuilder::AddDirectoryAt(absl::string_view outside,
16151649
absl::string_view inside,
16161650
bool is_ro) {

sandboxed_api/sandbox2/policybuilder.h

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -795,6 +795,8 @@ class PolicyBuilder final {
795795
PolicyBuilder& AddFile(absl::string_view path, bool is_ro = true);
796796
PolicyBuilder& AddFileAt(absl::string_view outside, absl::string_view inside,
797797
bool is_ro = true);
798+
// Same as `AddFile`, but no error is raised if the file does not exist.
799+
PolicyBuilder& AddFileIfExists(absl::string_view path, bool is_ro = true);
798800

799801
// Adds the libraries and linker required by a binary.
800802
//
@@ -829,6 +831,10 @@ class PolicyBuilder final {
829831
PolicyBuilder& AddDirectory(absl::string_view path, bool is_ro = true);
830832
PolicyBuilder& AddDirectoryAt(absl::string_view outside,
831833
absl::string_view inside, bool is_ro = true);
834+
// Same as `AddDirectory`, but no error is raised if the directory does not
835+
// exist.
836+
PolicyBuilder& AddDirectoryIfExists(absl::string_view path,
837+
bool is_ro = true);
832838

833839
// Adds a tmpfs inside the namespace.
834840
//

sandboxed_api/sandbox2/policybuilder_test.cc

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -115,6 +115,28 @@ TEST(PolicyBuilderTest, Testpolicy_size) {
115115
// clang-format on
116116
}
117117

118+
TEST(PolicyBuilderTest, NonExistingIgnored) {
119+
PolicyBuilder pb;
120+
pb.AddFileIfExists("/non_existing_file");
121+
ASSERT_THAT(pb.mounts().ResolvePath("/non_existing_file"),
122+
StatusIs(absl::StatusCode::kNotFound));
123+
pb.AddDirectoryIfExists("/non_existing_dir");
124+
ASSERT_THAT(pb.mounts().ResolvePath("/non_existing_dir"),
125+
StatusIs(absl::StatusCode::kNotFound));
126+
EXPECT_THAT(pb.TryBuild(), IsOk());
127+
}
128+
129+
TEST(PolicyBuilderTest, WrongTypeIgnored) {
130+
PolicyBuilder pb;
131+
pb.AddFileIfExists("/usr"); // This is a directory, not a file.
132+
ASSERT_THAT(pb.mounts().ResolvePath("/usr"),
133+
StatusIs(absl::StatusCode::kNotFound));
134+
pb.AddDirectoryIfExists("/etc/passwd"); // This is a file, not a directory.
135+
ASSERT_THAT(pb.mounts().ResolvePath("/etc/passwd"),
136+
StatusIs(absl::StatusCode::kNotFound));
137+
EXPECT_THAT(pb.TryBuild(), IsOk());
138+
}
139+
118140
TEST(PolicyBuilderTest, ApisWithPathValidation) {
119141
const std::initializer_list<std::pair<absl::string_view, absl::StatusCode>>
120142
kTestCases = {

0 commit comments

Comments
 (0)