recovery: Support writing to Virtual A/B partitions

Change-Id: Ice74e460242a58140fe31240b9fc464848b3aeea
diff --git a/install/install.cpp b/install/install.cpp
index c332968..f207db5 100644
--- a/install/install.cpp
+++ b/install/install.cpp
@@ -46,6 +46,7 @@
 #include <android-base/strings.h>
 #include <android-base/unique_fd.h>
 
+#include "install/snapshot_utils.h"
 #include "install/spl_check.h"
 #include "install/wipe_data.h"
 #include "otautil/error_code.h"
@@ -384,6 +385,7 @@
   bool device_supports_ab = android::base::GetBoolProperty("ro.build.ab_update", false);
   bool ab_device_supports_nonab = true;
   bool device_only_supports_ab = device_supports_ab && !ab_device_supports_nonab;
+  bool device_supports_virtual_ab = android::base::GetBoolProperty("ro.virtual_ab.enabled", false);
 
   const auto current_spl = android::base::GetProperty("ro.build.version.security_patch", "");
   if (ViolatesSPLDowngrade(zip, current_spl)) {
@@ -406,6 +408,15 @@
     }
   }
 
+  if (!package_is_ab && !logical_partitions_mapped()) {
+    CreateSnapshotPartitions();
+    map_logical_partitions();
+  } else if (package_is_ab && device_supports_virtual_ab && logical_partitions_mapped()) {
+    LOG(ERROR) << "Logical partitions are mapped. "
+               << "Please reboot recovery before installing an OTA update.";
+    return INSTALL_ERROR;
+  }
+
   ReadSourceTargetBuild(metadata, log_buffer);
 
   // The updater in child process writes to the pipe to communicate with recovery.