OSDN Git Service

Bind mount install and android writable DATA and OBB dirs
authorRicky Wai <rickywai@google.com>
Tue, 7 Apr 2020 12:43:20 +0000 (13:43 +0100)
committerRicky Wai <rickywai@google.com>
Mon, 20 Apr 2020 14:06:58 +0000 (15:06 +0100)
To improvement performance, and also making them able to list
the dirs.

This should also be fine under b/151055432, as the whole obb
directory is mounted, renameTo() from installer to apps should be
a move not copy.

Bug: 153422990
Bug: 153540919
Test: atest AdoptableHostTest
Change-Id: Ia18fd4393db14a0f11d6e5b947dd716515bdeeef

VolumeManager.cpp
model/EmulatedVolume.cpp

index e4e5781..eac020f 100644 (file)
@@ -947,7 +947,7 @@ int VolumeManager::unmountAll() {
              !StartsWith(test, "/mnt/scratch") &&
 #endif
              !StartsWith(test, "/mnt/vendor") && !StartsWith(test, "/mnt/product") &&
-             !StartsWith(test, "/mnt/installer")) ||
+             !StartsWith(test, "/mnt/installer") && !StartsWith(test, "/mnt/androidwritable")) ||
             StartsWith(test, "/storage/")) {
             toUnmount.push_front(test);
         }
index e411b33..e7cd36e 100644 (file)
@@ -141,12 +141,49 @@ status_t EmulatedVolume::mountFuseBindMounts() {
     // a special bind mount, since app-private and OBB dirs share the same GID, but we
     // only want to give access to the latter.
     if (mUseSdcardFs) {
-        std::string installerSource(
-                StringPrintf("/mnt/runtime/write/%s/%d/Android/obb", label.c_str(), userId));
-        std::string installerTarget(
-                StringPrintf("/mnt/installer/%d/%s/%d/Android/obb", userId, label.c_str(), userId));
+        std::string obbSource(StringPrintf("/mnt/runtime/write/%s/%d/Android/obb",
+                label.c_str(), userId));
+        std::string obbInstallerTarget(StringPrintf("/mnt/installer/%d/%s/%d/Android/obb",
+                userId, label.c_str(), userId));
+
+        status = doFuseBindMount(obbSource, obbInstallerTarget, pathsToUnmount);
+        if (status != OK) {
+            return status;
+        }
+    } else if (mAppDataIsolationEnabled) {
+        std::string obbSource(StringPrintf("%s/obb", androidSource.c_str()));
+        std::string obbInstallerTarget(StringPrintf("/mnt/installer/%d/%s/%d/Android/obb",
+                userId, label.c_str(), userId));
 
-        status = doFuseBindMount(installerSource, installerTarget, pathsToUnmount);
+        status = doFuseBindMount(obbSource, obbInstallerTarget, pathsToUnmount);
+        if (status != OK) {
+            return status;
+        }
+    }
+
+    // /mnt/androidwriteable is similar to /mnt/installer, but it's for
+    // MOUNT_EXTERNAL_ANDROID_WRITABLE apps and it can also access DATA (Android/data) dirs.
+    if (mAppDataIsolationEnabled) {
+        std::string obbSource = mUseSdcardFs ?
+            StringPrintf("/mnt/runtime/write/%s/%d/Android/obb", label.c_str(), userId)
+            : StringPrintf("%s/obb", androidSource.c_str());
+
+        std::string obbAndroidWritableTarget(
+                StringPrintf("/mnt/androidwritable/%d/%s/%d/Android/obb",
+                userId, label.c_str(), userId));
+
+        status = doFuseBindMount(obbSource, obbAndroidWritableTarget, pathsToUnmount);
+        if (status != OK) {
+            return status;
+        }
+
+        std::string dataSource = mUseSdcardFs ?
+                StringPrintf("/mnt/runtime/write/%s/%d/Android/data", label.c_str(), userId)
+                : StringPrintf("%s/data", androidSource.c_str());
+        std::string dataTarget(StringPrintf("/mnt/androidwritable/%d/%s/%d/Android/data",
+                userId, label.c_str(), userId));
+
+        status = doFuseBindMount(dataSource, dataTarget, pathsToUnmount);
         if (status != OK) {
             return status;
         }
@@ -159,7 +196,7 @@ status_t EmulatedVolume::unmountFuseBindMounts() {
     std::string label = getLabel();
     int userId = getMountUserId();
 
-    if (mUseSdcardFs) {
+    if (mUseSdcardFs || mAppDataIsolationEnabled) {
         std::string installerTarget(
                 StringPrintf("/mnt/installer/%d/%s/%d/Android/obb", userId, label.c_str(), userId));
         LOG(INFO) << "Unmounting " << installerTarget;
@@ -169,6 +206,25 @@ status_t EmulatedVolume::unmountFuseBindMounts() {
             // Intentional continue to try to unmount the other bind mount
         }
     }
+    if (mAppDataIsolationEnabled) {
+        std::string obbTarget( StringPrintf("/mnt/androidwritable/%d/%s/%d/Android/obb",
+                userId, label.c_str(), userId));
+        LOG(INFO) << "Unmounting " << obbTarget;
+        auto status = UnmountTree(obbTarget);
+        if (status != OK) {
+            LOG(ERROR) << "Failed to unmount " << obbTarget;
+            // Intentional continue to try to unmount the other bind mount
+        }
+        std::string dataTarget(StringPrintf("/mnt/androidwritable/%d/%s/%d/Android/data",
+                userId, label.c_str(), userId));
+        LOG(INFO) << "Unmounting " << dataTarget;
+        status = UnmountTree(dataTarget);
+        if (status != OK) {
+            LOG(ERROR) << "Failed to unmount " << dataTarget;
+            // Intentional continue to try to unmount the other bind mount
+        }
+    }
+
     // When app data isolation is enabled, kill all apps that obb/ is mounted, otherwise we should
     // umount the whole Android/ dir.
     if (mAppDataIsolationEnabled) {