Snap for 6272866 from 423129bb53e9c238342b14ffac2651a1a0142dc0 to rvc-release

Change-Id: I9abeb707d34232b54be6374a566b4796ec12af58
diff --git a/Android.bp b/Android.bp
index 1667ffb..f96ec25 100644
--- a/Android.bp
+++ b/Android.bp
@@ -127,6 +127,7 @@
         "aidl/android/gsi/GsiProgress.aidl",
         "aidl/android/gsi/IGsid.aidl",
         "aidl/android/gsi/IGsiService.aidl",
+        "aidl/android/gsi/IGsiServiceCallback.aidl",
         "aidl/android/gsi/IImageService.aidl",
         "aidl/android/gsi/IProgressCallback.aidl",
         "aidl/android/gsi/MappedImage.aidl",
diff --git a/aidl/android/gsi/IGsiService.aidl b/aidl/android/gsi/IGsiService.aidl
index 65050fe..5503493 100644
--- a/aidl/android/gsi/IGsiService.aidl
+++ b/aidl/android/gsi/IGsiService.aidl
@@ -18,6 +18,7 @@
 
 import android.gsi.AvbPublicKey;
 import android.gsi.GsiProgress;
+import android.gsi.IGsiServiceCallback;
 import android.gsi.IImageService;
 import android.os.ParcelFileDescriptor;
 
@@ -86,6 +87,12 @@
     int enableGsi(boolean oneShot, @utf8InCpp String dsuSlot);
 
     /**
+     * Asynchronous enableGsi
+     * @param result        callback for result
+     */
+    oneway void enableGsiAsync(boolean oneShot, @utf8InCpp String dsuSlot, IGsiServiceCallback result);
+
+    /**
      * @return              True if Gsi is enabled
      */
     boolean isGsiEnabled();
@@ -110,6 +117,12 @@
     boolean removeGsi();
 
     /**
+     * Asynchronous removeGsi
+     * @param result        callback for result
+     */
+    oneway void removeGsiAsync(IGsiServiceCallback result);
+
+    /**
      * Disables a GSI install. The image and userdata will be retained, but can
      * be re-enabled at any time with setGsiBootable.
      */
diff --git a/aidl/android/gsi/IGsiServiceCallback.aidl b/aidl/android/gsi/IGsiServiceCallback.aidl
new file mode 100644
index 0000000..a764ecd
--- /dev/null
+++ b/aidl/android/gsi/IGsiServiceCallback.aidl
@@ -0,0 +1,22 @@
+/*
+ * Copyright (C) 2020 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package android.gsi;
+
+/** {@hide} */
+oneway interface IGsiServiceCallback {
+    void onResult(int result);
+}
diff --git a/gsi_service.cpp b/gsi_service.cpp
index 3705c5b..77db54b 100644
--- a/gsi_service.cpp
+++ b/gsi_service.cpp
@@ -33,6 +33,7 @@
 #include <android-base/errors.h>
 #include <android-base/file.h>
 #include <android-base/logging.h>
+#include <android-base/properties.h>
 #include <android-base/stringprintf.h>
 #include <android-base/strings.h>
 #include <android/gsi/BnImageService.h>
@@ -57,6 +58,7 @@
 using android::base::ReadFileToString;
 using android::base::ReadFullyAtOffset;
 using android::base::RemoveFileIfExists;
+using android::base::SetProperty;
 using android::base::StringPrintf;
 using android::base::unique_fd;
 using android::base::WriteStringToFd;
@@ -278,6 +280,18 @@
     return binder::Status::ok();
 }
 
+binder::Status GsiService::enableGsiAsync(bool one_shot, const std::string& dsuSlot,
+                                          const sp<IGsiServiceCallback>& resultCallback) {
+    int result;
+    auto status = enableGsi(one_shot, dsuSlot, &result);
+    if (!status.isOk()) {
+        LOG(ERROR) << "Could not enableGsi: " << status.exceptionMessage().string();
+        result = IGsiService::INSTALL_ERROR_GENERIC;
+    }
+    resultCallback->onResult(result);
+    return binder::Status::ok();
+}
+
 binder::Status GsiService::enableGsi(bool one_shot, const std::string& dsuSlot, int* _aidl_return) {
     std::lock_guard<std::mutex> guard(parent_->lock());
 
@@ -317,6 +331,17 @@
     return binder::Status::ok();
 }
 
+binder::Status GsiService::removeGsiAsync(const sp<IGsiServiceCallback>& resultCallback) {
+    bool result;
+    auto status = removeGsi(&result);
+    if (!status.isOk()) {
+        LOG(ERROR) << "Could not removeGsi: " << status.exceptionMessage().string();
+        result = IGsiService::INSTALL_ERROR_GENERIC;
+    }
+    resultCallback->onResult(result);
+    return binder::Status::ok();
+}
+
 binder::Status GsiService::removeGsi(bool* _aidl_return) {
     ENFORCE_SYSTEM_OR_SHELL;
     std::lock_guard<std::mutex> guard(parent_->lock());
@@ -474,6 +499,7 @@
         PLOG(ERROR) << "write " << kDsuInstallStatusFile;
         return false;
     }
+    SetProperty(kGsiInstalledProp, "1");
     return true;
 }
 
@@ -904,6 +930,9 @@
             ok = false;
         }
     }
+    if (ok) {
+        SetProperty(kGsiInstalledProp, "0");
+    }
     return ok;
 }
 
diff --git a/gsi_service.h b/gsi_service.h
index a853e2b..0f9880c 100644
--- a/gsi_service.h
+++ b/gsi_service.h
@@ -69,8 +69,11 @@
     binder::Status commitGsiChunkFromAshmem(int64_t bytes, bool* _aidl_return) override;
     binder::Status cancelGsiInstall(bool* _aidl_return) override;
     binder::Status enableGsi(bool oneShot, const std::string& dsuSlot, int* _aidl_return) override;
+    binder::Status enableGsiAsync(bool oneShot, const ::std::string& dsuSlot,
+                                  const sp<IGsiServiceCallback>& resultCallback) override;
     binder::Status isGsiEnabled(bool* _aidl_return) override;
     binder::Status removeGsi(bool* _aidl_return) override;
+    binder::Status removeGsiAsync(const sp<IGsiServiceCallback>& resultCallback) override;
     binder::Status disableGsi(bool* _aidl_return) override;
     binder::Status isGsiInstalled(bool* _aidl_return) override;
     binder::Status isGsiRunning(bool* _aidl_return) override;
diff --git a/gsi_tool.cpp b/gsi_tool.cpp
index a38bf20..b059947 100644
--- a/gsi_tool.cpp
+++ b/gsi_tool.cpp
@@ -374,7 +374,7 @@
     }
 
     int error;
-    status = gsid->zeroPartition("userdata", &error);
+    status = gsid->zeroPartition("userdata" + std::string(kDsuPostfix), &error);
     if (!status.isOk() || error) {
         std::cerr << "Could not wipe GSI userdata: " << ErrorMessage(status, error) << "\n";
         return EX_SOFTWARE;
diff --git a/include/libgsi/libgsi.h b/include/libgsi/libgsi.h
index c824c57..fbe2f17 100644
--- a/include/libgsi/libgsi.h
+++ b/include/libgsi/libgsi.h
@@ -47,6 +47,8 @@
 
 static constexpr char kGsiBootedProp[] = "ro.gsid.image_running";
 
+static constexpr char kGsiInstalledProp[] = "gsid.image_installed";
+
 static constexpr char kDsuPostfix[] = "_gsi";
 
 static constexpr int kMaxBootAttempts = 1;
diff --git a/partition_installer.cpp b/partition_installer.cpp
index 2ac313f..357df50 100644
--- a/partition_installer.cpp
+++ b/partition_installer.cpp
@@ -348,7 +348,7 @@
     uint64_t erase_size = std::min(kEraseSize, get_block_device_size(device->fd()));
     for (uint64_t i = 0; i < erase_size; i += zeroes.size()) {
         if (!android::base::WriteFully(device->fd(), zeroes.data(), zeroes.size())) {
-            PLOG(ERROR) << "write userdata_gsi";
+            PLOG(ERROR) << "write " << name;
             return IGsiService::INSTALL_ERROR_GENERIC;
         }
     }