Rename and move CreateDirRecursive

PiperOrigin-RevId: 510186053
Change-Id: I0e68cc8fff44780ab98f1d57f829ff900790eed5
This commit is contained in:
Wiktor Garbacz 2023-02-16 10:43:25 -08:00 committed by Copybara-Service
parent 6db17e7ab3
commit e1246332d1
9 changed files with 42 additions and 59 deletions

View File

@ -629,7 +629,6 @@ cc_library(
deps = [
":mount_tree_cc_proto",
":mounts",
":util",
":violation_cc_proto",
"//sandboxed_api/util:file_base",
"//sandboxed_api/util:fileops",
@ -928,7 +927,6 @@ cc_test(
copts = sapi_platform_copts(),
deps = [
":util",
"//sandboxed_api:testing",
"@com_google_googletest//:gtest_main",
],
)

View File

@ -586,7 +586,6 @@ target_link_libraries(sandbox2_namespace PRIVATE
sandbox2::mounts
sandbox2::mount_tree_proto
sapi::strerror
sandbox2::util
sandbox2::violation_proto
sapi::base
sapi::raw_logging
@ -1035,7 +1034,6 @@ if(BUILD_TESTING AND SAPI_BUILD_TESTING)
OUTPUT_NAME util_test
)
target_link_libraries(sandbox2_util_test PRIVATE
sapi::testing
sandbox2::util
sapi::test_main
)

View File

@ -35,7 +35,6 @@
#include "absl/strings/str_cat.h"
#include "absl/strings/str_format.h"
#include "absl/strings/string_view.h"
#include "sandboxed_api/sandbox2/util.h"
#include "sandboxed_api/util/fileops.h"
#include "sandboxed_api/util/path.h"
#include "sandboxed_api/util/raw_logging.h"
@ -67,7 +66,8 @@ int MountFallbackToReadOnly(const char* source, const char* target,
void PrepareChroot(const Mounts& mounts) {
// Create a tmpfs mount for the new rootfs.
SAPI_RAW_CHECK(util::CreateDirRecursive(kSandbox2ChrootPath, 0700),
SAPI_RAW_CHECK(
file_util::fileops::CreateDirectoryRecursively(kSandbox2ChrootPath, 0700),
"could not create directory for rootfs");
SAPI_RAW_PCHECK(mount("none", kSandbox2ChrootPath, "tmpfs", 0, nullptr) == 0,
"mounting rootfs failed");
@ -340,12 +340,14 @@ void Namespace::InitializeNamespaces(uid_t uid, gid_t gid, int32_t clone_flags,
void Namespace::InitializeInitialNamespaces(uid_t uid, gid_t gid) {
SetupIDMaps(uid, gid);
SAPI_RAW_CHECK(util::CreateDirRecursive(kSandbox2ChrootPath, 0700),
SAPI_RAW_CHECK(
file_util::fileops::CreateDirectoryRecursively(kSandbox2ChrootPath, 0700),
"could not create directory for rootfs");
SAPI_RAW_PCHECK(mount("none", kSandbox2ChrootPath, "tmpfs", 0, nullptr) == 0,
"mounting rootfs failed");
auto realroot_path = file::JoinPath(kSandbox2ChrootPath, "/realroot");
SAPI_RAW_CHECK(util::CreateDirRecursive(realroot_path, 0700),
SAPI_RAW_CHECK(
file_util::fileops::CreateDirectoryRecursively(realroot_path, 0700),
"could not create directory for real root");
SAPI_RAW_PCHECK(syscall(__NR_pivot_root, kSandbox2ChrootPath,
realroot_path.c_str()) != -1,

View File

@ -19,7 +19,6 @@
#include <spawn.h>
#include <sys/ptrace.h>
#include <sys/resource.h>
#include <sys/stat.h>
#include <sys/uio.h>
#include <sys/wait.h>
#include <unistd.h>
@ -169,34 +168,6 @@ long Syscall(long sys_no, // NOLINT
return syscall(sys_no, a1, a2, a3, a4, a5, a6);
}
bool CreateDirRecursive(const std::string& path, mode_t mode) {
int error = mkdir(path.c_str(), mode);
if (error == 0 || errno == EEXIST) {
return true;
}
// We couldn't create the dir for reasons we can't handle.
if (errno != ENOENT) {
return false;
}
// The EEXIST case, the parent directory doesn't exist yet.
// Let's create it.
const std::string dir = file_util::fileops::StripBasename(path);
if (dir == "/" || dir.empty()) {
return false;
}
if (!CreateDirRecursive(dir, mode)) {
return false;
}
// Now the parent dir exists, retry creating the directory.
error = mkdir(path.c_str(), mode);
return error == 0;
}
namespace {
int ChildFunc(void* arg) {

View File

@ -78,9 +78,6 @@ long Syscall(long sys_no, // NOLINT
uintptr_t a1 = 0, uintptr_t a2 = 0, uintptr_t a3 = 0,
uintptr_t a4 = 0, uintptr_t a5 = 0, uintptr_t a6 = 0);
// Recursively creates a directory, skipping segments that already exist.
bool CreateDirRecursive(const std::string& path, mode_t mode);
// Fork based on clone() which updates glibc's PID/TID caches - Based on:
// https://chromium.googlesource.com/chromium/src/+/9eb564175dbd452196f782da2b28e3e8e79c49a5%5E!/
//

View File

@ -16,31 +16,15 @@
#include <unistd.h>
#include <string>
#include "gmock/gmock.h"
#include "gtest/gtest.h"
#include "sandboxed_api/testing.h"
namespace sandbox2::util {
namespace {
using ::sapi::GetTestTempPath;
using ::testing::Gt;
using ::testing::IsTrue;
constexpr char kTestDir[] = "a/b/c";
TEST(UtilTest, TestCreateDirSuccess) {
EXPECT_THAT(CreateDirRecursive(GetTestTempPath(kTestDir), 0700), IsTrue());
}
TEST(UtilTest, TestCreateDirExistSuccess) {
const std::string test_dir = GetTestTempPath(kTestDir);
EXPECT_THAT(CreateDirRecursive(test_dir, 0700), IsTrue());
EXPECT_THAT(CreateDirRecursive(test_dir, 0700), IsTrue());
}
TEST(UtilTest, TestCreateMemFd) {
int fd = 0;
ASSERT_THAT(CreateMemFd(&fd), IsTrue());

View File

@ -220,6 +220,30 @@ bool ListDirectoryEntries(const std::string& directory,
return true;
}
bool CreateDirectoryRecursively(const std::string& path, int mode) {
if (mkdir(path.c_str(), mode) == 0 || errno == EEXIST) {
return true;
}
// We couldn't create the dir for reasons we can't handle.
if (errno != ENOENT) {
return false;
}
// The ENOENT case, the parent directory doesn't exist yet.
// Let's create it.
const std::string dir = StripBasename(path);
if (dir == "/" || dir.empty()) {
return false;
}
if (!CreateDirectoryRecursively(dir, mode)) {
return false;
}
// Now the parent dir exists, retry creating the directory.
return mkdir(path.c_str(), mode) == 0;
}
bool DeleteRecursively(const std::string& filename) {
std::vector<std::string> to_delete;
to_delete.push_back(filename);

View File

@ -89,6 +89,9 @@ bool ListDirectoryEntries(const std::string& directory,
std::vector<std::string>* entries,
std::string* error);
// Recursively creates a directory, skipping segments that already exist.
bool CreateDirectoryRecursively(const std::string& path, int mode);
// Deletes the specified file or directory, including any sub-directories.
bool DeleteRecursively(const std::string& filename);

View File

@ -332,6 +332,12 @@ void SetupDirectory() {
ASSERT_THAT(chmod("foo/bar/baz/foo", 0644), Eq(0));
}
TEST_F(FileOpsTest, CreateDirectoryRecursivelyTest) {
constexpr char kTestDir[] = "a/b/c";
EXPECT_THAT(fileops::CreateDirectoryRecursively(kTestDir, 0700), IsTrue());
EXPECT_THAT(fileops::CreateDirectoryRecursively(kTestDir, 0700), IsTrue());
}
TEST_F(FileOpsTest, DeleteRecursivelyTest) {
EXPECT_THAT(fileops::DeleteRecursively("foo"), IsTrue());
EXPECT_THAT(fileops::DeleteRecursively("/not_there"), IsTrue());