diff options
Diffstat (limited to 'init')
-rw-r--r-- | init/init_first_stage.cpp | 57 |
1 files changed, 41 insertions, 16 deletions
diff --git a/init/init_first_stage.cpp b/init/init_first_stage.cpp index db60ce11e..2bc9f3ae0 100644 --- a/init/init_first_stage.cpp +++ b/init/init_first_stage.cpp | |||
@@ -29,6 +29,7 @@ | |||
29 | #include <android-base/file.h> | 29 | #include <android-base/file.h> |
30 | #include <android-base/logging.h> | 30 | #include <android-base/logging.h> |
31 | #include <android-base/strings.h> | 31 | #include <android-base/strings.h> |
32 | #include <liblp/metadata_format.h> | ||
32 | 33 | ||
33 | #include "devices.h" | 34 | #include "devices.h" |
34 | #include "fs_mgr.h" | 35 | #include "fs_mgr.h" |
@@ -75,6 +76,7 @@ class FirstStageMount { | |||
75 | 76 | ||
76 | std::unique_ptr<fstab, decltype(&fs_mgr_free_fstab)> device_tree_fstab_; | 77 | std::unique_ptr<fstab, decltype(&fs_mgr_free_fstab)> device_tree_fstab_; |
77 | std::unique_ptr<LogicalPartitionTable> dm_linear_table_; | 78 | std::unique_ptr<LogicalPartitionTable> dm_linear_table_; |
79 | std::string lp_metadata_partition_; | ||
78 | std::vector<fstab_rec*> mount_fstab_recs_; | 80 | std::vector<fstab_rec*> mount_fstab_recs_; |
79 | std::set<std::string> required_devices_partition_names_; | 81 | std::set<std::string> required_devices_partition_names_; |
80 | std::unique_ptr<DeviceHandler> device_handler_; | 82 | std::unique_ptr<DeviceHandler> device_handler_; |
@@ -120,13 +122,17 @@ static bool inline IsRecoveryMode() { | |||
120 | } | 122 | } |
121 | 123 | ||
122 | static inline bool IsDmLinearEnabled() { | 124 | static inline bool IsDmLinearEnabled() { |
123 | bool enabled = false; | 125 | static bool checked = false; |
124 | import_kernel_cmdline( | 126 | static bool enabled = false; |
125 | false, [&enabled](const std::string& key, const std::string& value, bool in_qemu) { | 127 | if (checked) { |
126 | if (key == "androidboot.logical_partitions" && value == "1") { | 128 | return enabled; |
127 | enabled = true; | 129 | } |
128 | } | 130 | import_kernel_cmdline(false, [](const std::string& key, const std::string& value, bool in_qemu) { |
129 | }); | 131 | if (key == "androidboot.logical_partitions" && value == "1") { |
132 | enabled = true; | ||
133 | } | ||
134 | }); | ||
135 | checked = true; | ||
130 | return enabled; | 136 | return enabled; |
131 | } | 137 | } |
132 | 138 | ||
@@ -163,7 +169,7 @@ std::unique_ptr<FirstStageMount> FirstStageMount::Create() { | |||
163 | } | 169 | } |
164 | 170 | ||
165 | bool FirstStageMount::DoFirstStageMount() { | 171 | bool FirstStageMount::DoFirstStageMount() { |
166 | if (!dm_linear_table_ && mount_fstab_recs_.empty()) { | 172 | if (!IsDmLinearEnabled() && mount_fstab_recs_.empty()) { |
167 | // Nothing to mount. | 173 | // Nothing to mount. |
168 | LOG(INFO) << "First stage mount skipped (missing/incompatible/empty fstab in device tree)"; | 174 | LOG(INFO) << "First stage mount skipped (missing/incompatible/empty fstab in device tree)"; |
169 | return true; | 175 | return true; |
@@ -184,14 +190,18 @@ bool FirstStageMount::InitDevices() { | |||
184 | 190 | ||
185 | bool FirstStageMount::GetBackingDmLinearDevices() { | 191 | bool FirstStageMount::GetBackingDmLinearDevices() { |
186 | // Add any additional devices required for dm-linear mappings. | 192 | // Add any additional devices required for dm-linear mappings. |
187 | if (!dm_linear_table_) { | 193 | if (!IsDmLinearEnabled()) { |
188 | return true; | 194 | return true; |
189 | } | 195 | } |
190 | 196 | ||
191 | for (const auto& partition : dm_linear_table_->partitions) { | 197 | required_devices_partition_names_.emplace(LP_METADATA_PARTITION_NAME); |
192 | for (const auto& extent : partition.extents) { | 198 | |
193 | const std::string& partition_name = android::base::Basename(extent.block_device()); | 199 | if (dm_linear_table_) { |
194 | required_devices_partition_names_.emplace(partition_name); | 200 | for (const auto& partition : dm_linear_table_->partitions) { |
201 | for (const auto& extent : partition.extents) { | ||
202 | const std::string& partition_name = android::base::Basename(extent.block_device()); | ||
203 | required_devices_partition_names_.emplace(partition_name); | ||
204 | } | ||
195 | } | 205 | } |
196 | } | 206 | } |
197 | return true; | 207 | return true; |
@@ -205,7 +215,7 @@ bool FirstStageMount::InitRequiredDevices() { | |||
205 | return true; | 215 | return true; |
206 | } | 216 | } |
207 | 217 | ||
208 | if (dm_linear_table_ || need_dm_verity_) { | 218 | if (IsDmLinearEnabled() || need_dm_verity_) { |
209 | const std::string dm_path = "/devices/virtual/misc/device-mapper"; | 219 | const std::string dm_path = "/devices/virtual/misc/device-mapper"; |
210 | bool found = false; | 220 | bool found = false; |
211 | auto dm_callback = [this, &dm_path, &found](const Uevent& uevent) { | 221 | auto dm_callback = [this, &dm_path, &found](const Uevent& uevent) { |
@@ -253,10 +263,21 @@ bool FirstStageMount::InitRequiredDevices() { | |||
253 | } | 263 | } |
254 | 264 | ||
255 | bool FirstStageMount::CreateLogicalPartitions() { | 265 | bool FirstStageMount::CreateLogicalPartitions() { |
256 | if (!dm_linear_table_) { | 266 | if (!IsDmLinearEnabled()) { |
257 | return true; | 267 | return true; |
258 | } | 268 | } |
259 | return android::fs_mgr::CreateLogicalPartitions(*dm_linear_table_.get()); | 269 | |
270 | if (lp_metadata_partition_.empty()) { | ||
271 | LOG(ERROR) << "Could not locate logical partition tables in partition " | ||
272 | << LP_METADATA_PARTITION_NAME; | ||
273 | return false; | ||
274 | } | ||
275 | if (dm_linear_table_) { | ||
276 | if (!android::fs_mgr::CreateLogicalPartitions(*dm_linear_table_.get())) { | ||
277 | return false; | ||
278 | } | ||
279 | } | ||
280 | return android::fs_mgr::CreateLogicalPartitions(lp_metadata_partition_); | ||
260 | } | 281 | } |
261 | 282 | ||
262 | ListenerAction FirstStageMount::HandleBlockDevice(const std::string& name, const Uevent& uevent) { | 283 | ListenerAction FirstStageMount::HandleBlockDevice(const std::string& name, const Uevent& uevent) { |
@@ -266,6 +287,10 @@ ListenerAction FirstStageMount::HandleBlockDevice(const std::string& name, const | |||
266 | auto iter = required_devices_partition_names_.find(name); | 287 | auto iter = required_devices_partition_names_.find(name); |
267 | if (iter != required_devices_partition_names_.end()) { | 288 | if (iter != required_devices_partition_names_.end()) { |
268 | LOG(VERBOSE) << __PRETTY_FUNCTION__ << ": found partition: " << *iter; | 289 | LOG(VERBOSE) << __PRETTY_FUNCTION__ << ": found partition: " << *iter; |
290 | if (IsDmLinearEnabled() && name == LP_METADATA_PARTITION_NAME) { | ||
291 | std::vector<std::string> links = device_handler_->GetBlockDeviceSymlinks(uevent); | ||
292 | lp_metadata_partition_ = links[0]; | ||
293 | } | ||
269 | required_devices_partition_names_.erase(iter); | 294 | required_devices_partition_names_.erase(iter); |
270 | device_handler_->HandleDeviceEvent(uevent); | 295 | device_handler_->HandleDeviceEvent(uevent); |
271 | if (required_devices_partition_names_.empty()) { | 296 | if (required_devices_partition_names_.empty()) { |