fs_mgr: Allow to set defaults for CreateLogicalPartitionParams
Test: boots
Change-Id: I6a969a19b9d29e682f50872bd3e9027eaca41512
diff --git a/fs_mgr/fs_mgr_dm_linear.cpp b/fs_mgr/fs_mgr_dm_linear.cpp
index fa756a0..aa514bb 100644
--- a/fs_mgr/fs_mgr_dm_linear.cpp
+++ b/fs_mgr/fs_mgr_dm_linear.cpp
@@ -154,61 +154,77 @@
return true;
}
-bool CreateLogicalPartition(const CreateLogicalPartitionParams& params, std::string* path) {
- const LpMetadata* metadata = params.metadata;
+bool CreateLogicalPartitionParams::InitDefaults(CreateLogicalPartitionParams::OwnedData* owned) {
+ if (block_device.empty()) {
+ LOG(ERROR) << "block_device is required for CreateLogicalPartition";
+ return false;
+ }
// Read metadata if needed.
- std::unique_ptr<LpMetadata> local_metadata;
if (!metadata) {
- if (!params.metadata_slot) {
+ if (!metadata_slot) {
LOG(ERROR) << "Either metadata or a metadata slot must be specified.";
return false;
}
- auto slot = *params.metadata_slot;
- if (local_metadata = ReadMetadata(params.block_device, slot); !local_metadata) {
- LOG(ERROR) << "Could not read partition table for: " << params.block_device;
+ auto slot = *metadata_slot;
+ if (owned->metadata = ReadMetadata(block_device, slot); !owned->metadata) {
+ LOG(ERROR) << "Could not read partition table for: " << block_device;
return false;
}
- metadata = local_metadata.get();
+ metadata = owned->metadata.get();
}
// Find the partition by name if needed.
- const LpMetadataPartition* partition = params.partition;
if (!partition) {
- for (const auto& iter : metadata->partitions) {
- if (GetPartitionName(iter) == params.partition_name) {
- partition = &iter;
+ for (const auto& metadata_partition : metadata->partitions) {
+ if (android::fs_mgr::GetPartitionName(metadata_partition) == partition_name) {
+ partition = &metadata_partition;
break;
}
}
- if (!partition) {
- LERROR << "Could not find any partition with name: " << params.partition_name;
- return false;
- }
+ }
+ if (!partition) {
+ LERROR << "Could not find any partition with name: " << partition_name;
+ return false;
+ }
+ if (partition_name.empty()) {
+ partition_name = android::fs_mgr::GetPartitionName(*partition);
+ } else if (partition_name != android::fs_mgr::GetPartitionName(*partition)) {
+ LERROR << "Inconsistent partition_name " << partition_name << " with partition "
+ << android::fs_mgr::GetPartitionName(*partition);
+ return false;
}
- PartitionOpener default_opener;
- const IPartitionOpener* opener =
- params.partition_opener ? params.partition_opener : &default_opener;
+ if (!partition_opener) {
+ owned->partition_opener = std::make_unique<PartitionOpener>();
+ partition_opener = owned->partition_opener.get();
+ }
+
+ if (device_name.empty()) {
+ device_name = partition_name;
+ }
+
+ return true;
+}
+
+bool CreateLogicalPartition(CreateLogicalPartitionParams params, std::string* path) {
+ CreateLogicalPartitionParams::OwnedData owned_data;
+ if (!params.InitDefaults(&owned_data)) return false;
DmTable table;
- if (!CreateDmTable(*opener, *metadata, *partition, params.block_device, &table)) {
+ if (!CreateDmTable(*params.partition_opener, *params.metadata, *params.partition,
+ params.block_device, &table)) {
return false;
}
if (params.force_writable) {
table.set_readonly(false);
}
- std::string device_name = params.device_name;
- if (device_name.empty()) {
- device_name = GetPartitionName(*partition);
- }
-
DeviceMapper& dm = DeviceMapper::Instance();
- if (!dm.CreateDevice(device_name, table, path, params.timeout_ms)) {
+ if (!dm.CreateDevice(params.device_name, table, path, params.timeout_ms)) {
return false;
}
- LINFO << "Created logical partition " << device_name << " on device " << *path;
+ LINFO << "Created logical partition " << params.device_name << " on device " << *path;
return true;
}
diff --git a/fs_mgr/include/fs_mgr_dm_linear.h b/fs_mgr/include/fs_mgr_dm_linear.h
index 2054fa1..ebeae32 100644
--- a/fs_mgr/include/fs_mgr_dm_linear.h
+++ b/fs_mgr/include/fs_mgr_dm_linear.h
@@ -81,9 +81,24 @@
// Helpers for determining the effective partition and device name.
std::string GetPartitionName() const;
std::string GetDeviceName() const;
+
+ // Specify ownership of fields. The ownership of these fields are managed
+ // by the caller of InitDefaults().
+ // These are not declared in CreateLogicalPartitionParams so that the
+ // copy constructor is not deleted.
+ struct OwnedData {
+ std::unique_ptr<LpMetadata> metadata;
+ std::unique_ptr<IPartitionOpener> partition_opener;
+ };
+
+ // Fill in default values for |params| that CreateLogicalPartition assumes. Caller does
+ // not need to call this before calling CreateLogicalPartition; CreateLogicalPartition sets
+ // values when they are missing.
+ // Caller is responsible for destroying owned_data when |this| is not used.
+ bool InitDefaults(OwnedData* owned);
};
-bool CreateLogicalPartition(const CreateLogicalPartitionParams& params, std::string* path);
+bool CreateLogicalPartition(CreateLogicalPartitionParams params, std::string* path);
// Destroy the block device for a logical partition, by name. If |timeout_ms|
// is non-zero, then this will block until the device path has been unlinked.