blob: 7f0c4deb6c6185fd88deee8f4da57d4403d2093b [file] [log] [blame]
From 6d2019885330a84196ebd6d020e77f4e19b60836 Mon Sep 17 00:00:00 2001
From: Jaeyoon Choi <j_yoon.choi@samsung.com>
Date: Thu, 29 Jul 2021 20:25:41 +0900
Subject: [PATCH 5/5] [f2fs] Add filesystem specific mkfs option
Change-Id: I95efc450142b50808f4ba642eebc7083ee002e22
---
.../cpp/include/fs-management/admin.h | 3 ++
src/lib/storage/fs_management/cpp/mkfs.cc | 53 ++++++++++++++++++-
src/storage/bin/mkfs/main.cc | 10 +++-
3 files changed, 63 insertions(+), 3 deletions(-)
diff --git a/src/lib/storage/fs_management/cpp/include/fs-management/admin.h b/src/lib/storage/fs_management/cpp/include/fs-management/admin.h
index 7fc1b358f12..611c01155e0 100644
--- a/src/lib/storage/fs_management/cpp/include/fs-management/admin.h
+++ b/src/lib/storage/fs_management/cpp/include/fs-management/admin.h
@@ -65,6 +65,9 @@ struct MkfsOptions {
// The initial number of inodes to allocate space for. If 0, a default is used. Only supported
// for blobfs.
uint64_t num_inodes = 0;
+
+ // Filesystem-specific options (currently for f2fs)
+ char* private_options = nullptr;
};
struct FsckOptions {
diff --git a/src/lib/storage/fs_management/cpp/mkfs.cc b/src/lib/storage/fs_management/cpp/mkfs.cc
index 93566c917be..ee6d3b1d28c 100644
--- a/src/lib/storage/fs_management/cpp/mkfs.cc
+++ b/src/lib/storage/fs_management/cpp/mkfs.cc
@@ -18,6 +18,7 @@
#include <iterator>
#include <new>
+#include <sstream>
#include <vector>
#include <fbl/algorithm.h>
@@ -96,6 +97,55 @@ zx_status_t MkfsFat(const char* device_path, LaunchCallback cb, const MkfsOption
return cb(argv.size() - 1, argv.data(), NULL, NULL, 0);
}
+zx_status_t MkfsF2fs(const char* device_path, LaunchCallback cb, const MkfsOptions& options) {
+ fbl::unique_fd device_fd;
+ device_fd.reset(open(device_path, O_RDWR));
+ if (!device_fd) {
+ fprintf(stderr, "Failed to open device\n");
+ return ZX_ERR_BAD_STATE;
+ }
+ zx::channel block_device;
+ zx_status_t status =
+ fdio_get_service_handle(device_fd.release(), block_device.reset_and_get_address());
+ if (status != ZX_OK) {
+ return status;
+ }
+
+ const std::string tool_path = fs_management::GetBinaryPath("f2fs");
+ std::vector<const char*> argv = {tool_path.c_str()};
+ argv.push_back("mkfs");
+
+ std::vector<std::string> private_options_buf(10, "");
+
+ if (options.private_options != nullptr) {
+ std::istringstream iss(options.private_options);
+ std::string token;
+ uint32_t idx = 0;
+
+ while (std::getline(iss, token, ' ')) {
+ if (token == "")
+ continue;
+
+ if (idx >= private_options_buf.size()) {
+ private_options_buf.resize(private_options_buf.size() * 2, "");
+ }
+ private_options_buf[idx++] = token;
+ }
+
+ for (uint32_t i = 0; i < idx; i++) {
+ argv.push_back(private_options_buf[i].c_str());
+ }
+ }
+
+ argv.push_back(nullptr);
+
+ zx_handle_t hnd = block_device.release();
+ uint32_t id = FS_HANDLE_BLOCK_DEVICE_ID;
+ status =
+ static_cast<zx_status_t>(cb(static_cast<int>(argv.size() - 1), argv.data(), &hnd, &id, 1));
+ return status;
+}
+
} // namespace
__EXPORT
@@ -117,8 +167,7 @@ zx_status_t mkfs(const char* device_path, disk_format_t df, LaunchCallback cb,
return MkfsNativeFs(fs_management::GetBinaryPath("blobfs").c_str(), device_path, cb, options,
true);
case DISK_FORMAT_F2FS:
- return MkfsNativeFs(fs_management::GetBinaryPath("f2fs").c_str(), device_path, cb, options,
- true);
+ return MkfsF2fs(device_path, cb, options);
default:
auto* format = fs_management::CustomDiskFormat::Get(df);
if (format == nullptr) {
diff --git a/src/storage/bin/mkfs/main.cc b/src/storage/bin/mkfs/main.cc
index 1d82a1ebf11..22e2d860648 100644
--- a/src/storage/bin/mkfs/main.cc
+++ b/src/storage/bin/mkfs/main.cc
@@ -40,6 +40,10 @@ int usage(void) {
" -s|--fvm_data_slices SLICES If block device is on top of a FVM,\n"
" the filesystem will have at least SLICES slices\n"
" allocated for data.\n");
+ fprintf(stderr, " -p|--private_options OPTIONS Filesystem-specific options, wrapped in \"\".\n");
+ fprintf(stderr,
+ " It is delivered to filesystem without parsing,\n");
+ fprintf(stderr, " and the filesystem will parse it.\n");
fprintf(stderr, " values for 'filesystem' include:\n");
for (size_t i = 0; i < countof(FILESYSTEMS); i++) {
fprintf(stderr, " '%s'\n", FILESYSTEMS[i].name);
@@ -52,13 +56,14 @@ int parse_args(int argc, char** argv, MkfsOptions* options, disk_format_t* df, c
{"help", no_argument, NULL, 'h'},
{"verbose", no_argument, NULL, 'v'},
{"fvm_data_slices", required_argument, NULL, 's'},
+ {"private_options", required_argument, NULL, 'p'},
{0, 0, 0, 0},
};
int opt_index = -1;
int c = -1;
- while ((c = getopt_long(argc, argv, "hvs:", cmds, &opt_index)) >= 0) {
+ while ((c = getopt_long(argc, argv, "hvs:p:", cmds, &opt_index)) >= 0) {
switch (c) {
case 'v':
options->verbose = true;
@@ -72,6 +77,9 @@ int parse_args(int argc, char** argv, MkfsOptions* options, disk_format_t* df, c
break;
case 'h':
return usage();
+ case 'p':
+ options->private_options = optarg;
+ break;
default:
break;
};
--
2.25.1