Add a BackendUnifiedServiceManager wrapper

This can be directly used by java and rust ffi
Test: atest aidl_integration_test
Bug: 333854840
Flag: EXEMPT refactor

Change-Id: I12c3730a89422bf08ab723a82888431f291bd7b3
diff --git a/libs/binder/Android.bp b/libs/binder/Android.bp
index f31f8d3..1abde5c 100644
--- a/libs/binder/Android.bp
+++ b/libs/binder/Android.bp
@@ -442,8 +442,10 @@
     name: "libbinder_kernel_defaults",
     srcs: [
         "BufferedTextOutput.cpp",
+        "BackendUnifiedServiceManager.cpp",
         "IPCThreadState.cpp",
         "IServiceManager.cpp",
+        "IServiceManagerFFI.cpp",
         "ProcessState.cpp",
         "Static.cpp",
         ":libbinder_aidl",
@@ -519,7 +521,6 @@
         "ParcelableHolder.cpp",
         "PersistableBundle.cpp",
     ],
-
     target: {
         android: {
             // NOT static to keep the wire protocol unfrozen
diff --git a/libs/binder/BackendUnifiedServiceManager.cpp b/libs/binder/BackendUnifiedServiceManager.cpp
new file mode 100644
index 0000000..496c5ef
--- /dev/null
+++ b/libs/binder/BackendUnifiedServiceManager.cpp
@@ -0,0 +1,119 @@
+/*
+ * Copyright (C) 2024 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.
+ */
+#include "BackendUnifiedServiceManager.h"
+
+namespace android {
+
+using AidlServiceManager = android::os::IServiceManager;
+
+BackendUnifiedServiceManager::BackendUnifiedServiceManager(const sp<AidlServiceManager>& impl)
+      : mTheRealServiceManager(impl) {}
+
+sp<AidlServiceManager> BackendUnifiedServiceManager::getImpl() {
+    return mTheRealServiceManager;
+}
+binder::Status BackendUnifiedServiceManager::getService(const ::std::string& name,
+                                                        sp<IBinder>* _aidl_return) {
+    return mTheRealServiceManager->getService(name, _aidl_return);
+}
+binder::Status BackendUnifiedServiceManager::checkService(const ::std::string& name,
+                                                          sp<IBinder>* _aidl_return) {
+    return mTheRealServiceManager->checkService(name, _aidl_return);
+}
+binder::Status BackendUnifiedServiceManager::addService(const ::std::string& name,
+                                                        const sp<IBinder>& service,
+                                                        bool allowIsolated, int32_t dumpPriority) {
+    return mTheRealServiceManager->addService(name, service, allowIsolated, dumpPriority);
+}
+binder::Status BackendUnifiedServiceManager::listServices(
+        int32_t dumpPriority, ::std::vector<::std::string>* _aidl_return) {
+    return mTheRealServiceManager->listServices(dumpPriority, _aidl_return);
+}
+binder::Status BackendUnifiedServiceManager::registerForNotifications(
+        const ::std::string& name, const sp<os::IServiceCallback>& callback) {
+    return mTheRealServiceManager->registerForNotifications(name, callback);
+}
+binder::Status BackendUnifiedServiceManager::unregisterForNotifications(
+        const ::std::string& name, const sp<os::IServiceCallback>& callback) {
+    return mTheRealServiceManager->unregisterForNotifications(name, callback);
+}
+binder::Status BackendUnifiedServiceManager::isDeclared(const ::std::string& name,
+                                                        bool* _aidl_return) {
+    return mTheRealServiceManager->isDeclared(name, _aidl_return);
+}
+binder::Status BackendUnifiedServiceManager::getDeclaredInstances(
+        const ::std::string& iface, ::std::vector<::std::string>* _aidl_return) {
+    return mTheRealServiceManager->getDeclaredInstances(iface, _aidl_return);
+}
+binder::Status BackendUnifiedServiceManager::updatableViaApex(
+        const ::std::string& name, ::std::optional<::std::string>* _aidl_return) {
+    return mTheRealServiceManager->updatableViaApex(name, _aidl_return);
+}
+binder::Status BackendUnifiedServiceManager::getUpdatableNames(
+        const ::std::string& apexName, ::std::vector<::std::string>* _aidl_return) {
+    return mTheRealServiceManager->getUpdatableNames(apexName, _aidl_return);
+}
+binder::Status BackendUnifiedServiceManager::getConnectionInfo(
+        const ::std::string& name, ::std::optional<os::ConnectionInfo>* _aidl_return) {
+    return mTheRealServiceManager->getConnectionInfo(name, _aidl_return);
+}
+binder::Status BackendUnifiedServiceManager::registerClientCallback(
+        const ::std::string& name, const sp<IBinder>& service,
+        const sp<os::IClientCallback>& callback) {
+    return mTheRealServiceManager->registerClientCallback(name, service, callback);
+}
+binder::Status BackendUnifiedServiceManager::tryUnregisterService(const ::std::string& name,
+                                                                  const sp<IBinder>& service) {
+    return mTheRealServiceManager->tryUnregisterService(name, service);
+}
+binder::Status BackendUnifiedServiceManager::getServiceDebugInfo(
+        ::std::vector<os::ServiceDebugInfo>* _aidl_return) {
+    return mTheRealServiceManager->getServiceDebugInfo(_aidl_return);
+}
+
+[[clang::no_destroy]] static std::once_flag gUSmOnce;
+[[clang::no_destroy]] static sp<BackendUnifiedServiceManager> gUnifiedServiceManager;
+
+sp<BackendUnifiedServiceManager> getBackendUnifiedServiceManager() {
+    std::call_once(gUSmOnce, []() {
+#if defined(__BIONIC__) && !defined(__ANDROID_VNDK__)
+        /* wait for service manager */ {
+            using std::literals::chrono_literals::operator""s;
+            using android::base::WaitForProperty;
+            while (!WaitForProperty("servicemanager.ready", "true", 1s)) {
+                ALOGE("Waited for servicemanager.ready for a second, waiting another...");
+            }
+        }
+#endif
+
+        sp<AidlServiceManager> sm = nullptr;
+        while (sm == nullptr) {
+            sm = interface_cast<AidlServiceManager>(
+                    ProcessState::self()->getContextObject(nullptr));
+            if (sm == nullptr) {
+                ALOGE("Waiting 1s on context object on %s.",
+                      ProcessState::self()->getDriverName().c_str());
+                sleep(1);
+            }
+        }
+
+        gUnifiedServiceManager = sp<BackendUnifiedServiceManager>::make(sm);
+    });
+
+    return gUnifiedServiceManager;
+}
+
+} // namespace android
\ No newline at end of file
diff --git a/libs/binder/BackendUnifiedServiceManager.h b/libs/binder/BackendUnifiedServiceManager.h
new file mode 100644
index 0000000..a67d5ba
--- /dev/null
+++ b/libs/binder/BackendUnifiedServiceManager.h
@@ -0,0 +1,68 @@
+/*
+ * Copyright (C) 2024 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.
+ */
+#pragma once
+
+#include <android-base/properties.h>
+#include <android/os/BnServiceManager.h>
+#include <android/os/IServiceManager.h>
+#include <binder/IPCThreadState.h>
+
+namespace android {
+
+class BackendUnifiedServiceManager : public android::os::BnServiceManager {
+public:
+    explicit BackendUnifiedServiceManager(const sp<os::IServiceManager>& impl);
+
+    sp<os::IServiceManager> getImpl();
+    binder::Status getService(const ::std::string& name, sp<IBinder>* _aidl_return) override;
+    binder::Status checkService(const ::std::string& name, sp<IBinder>* _aidl_return) override;
+    binder::Status addService(const ::std::string& name, const sp<IBinder>& service,
+                              bool allowIsolated, int32_t dumpPriority) override;
+    binder::Status listServices(int32_t dumpPriority,
+                                ::std::vector<::std::string>* _aidl_return) override;
+    binder::Status registerForNotifications(const ::std::string& name,
+                                            const sp<os::IServiceCallback>& callback) override;
+    binder::Status unregisterForNotifications(const ::std::string& name,
+                                              const sp<os::IServiceCallback>& callback) override;
+    binder::Status isDeclared(const ::std::string& name, bool* _aidl_return) override;
+    binder::Status getDeclaredInstances(const ::std::string& iface,
+                                        ::std::vector<::std::string>* _aidl_return) override;
+    binder::Status updatableViaApex(const ::std::string& name,
+                                    ::std::optional<::std::string>* _aidl_return) override;
+    binder::Status getUpdatableNames(const ::std::string& apexName,
+                                     ::std::vector<::std::string>* _aidl_return) override;
+    binder::Status getConnectionInfo(const ::std::string& name,
+                                     ::std::optional<os::ConnectionInfo>* _aidl_return) override;
+    binder::Status registerClientCallback(const ::std::string& name, const sp<IBinder>& service,
+                                          const sp<os::IClientCallback>& callback) override;
+    binder::Status tryUnregisterService(const ::std::string& name,
+                                        const sp<IBinder>& service) override;
+    binder::Status getServiceDebugInfo(::std::vector<os::ServiceDebugInfo>* _aidl_return) override;
+
+    // for legacy ABI
+    const String16& getInterfaceDescriptor() const override {
+        return mTheRealServiceManager->getInterfaceDescriptor();
+    }
+
+    IBinder* onAsBinder() override { return IInterface::asBinder(mTheRealServiceManager).get(); }
+
+private:
+    sp<os::IServiceManager> mTheRealServiceManager;
+};
+
+sp<BackendUnifiedServiceManager> getBackendUnifiedServiceManager();
+
+} // namespace android
\ No newline at end of file
diff --git a/libs/binder/IServiceManager.cpp b/libs/binder/IServiceManager.cpp
index fbcf823..5844c85 100644
--- a/libs/binder/IServiceManager.cpp
+++ b/libs/binder/IServiceManager.cpp
@@ -16,6 +16,7 @@
 
 #define LOG_TAG "ServiceManagerCppClient"
 
+#include <BackendUnifiedServiceManager.h>
 #include <binder/IServiceManager.h>
 
 #include <inttypes.h>
@@ -111,14 +112,12 @@
     std::vector<IServiceManager::ServiceDebugInfo> getServiceDebugInfo() override;
     // for legacy ABI
     const String16& getInterfaceDescriptor() const override {
-        return mTheRealServiceManager->getInterfaceDescriptor();
+        return mUnifiedServiceManager->getInterfaceDescriptor();
     }
-    IBinder* onAsBinder() override {
-        return IInterface::asBinder(mTheRealServiceManager).get();
-    }
+    IBinder* onAsBinder() override { return IInterface::asBinder(mUnifiedServiceManager).get(); }
 
 protected:
-    sp<AidlServiceManager> mTheRealServiceManager;
+    sp<BackendUnifiedServiceManager> mUnifiedServiceManager;
     // AidlRegistrationCallback -> services that its been registered for
     // notifications.
     using LocalRegistrationAndWaiter =
@@ -136,9 +135,9 @@
     // will still have the 5s delay that is expected by a large amount of Android code.
     //
     // When implementing ServiceManagerShim, use realGetService instead of
-    // mTheRealServiceManager->getService so that it can be overridden in ServiceManagerHostShim.
+    // mUnifiedServiceManager->getService so that it can be overridden in ServiceManagerHostShim.
     virtual Status realGetService(const std::string& name, sp<IBinder>* _aidl_return) {
-        return mTheRealServiceManager->getService(name, _aidl_return);
+        return mUnifiedServiceManager->getService(name, _aidl_return);
     }
 };
 
@@ -148,26 +147,7 @@
 sp<IServiceManager> defaultServiceManager()
 {
     std::call_once(gSmOnce, []() {
-#if defined(__BIONIC__) && !defined(__ANDROID_VNDK__)
-        /* wait for service manager */ {
-            using std::literals::chrono_literals::operator""s;
-            using android::base::WaitForProperty;
-            while (!WaitForProperty("servicemanager.ready", "true", 1s)) {
-                ALOGE("Waited for servicemanager.ready for a second, waiting another...");
-            }
-        }
-#endif
-
-        sp<AidlServiceManager> sm = nullptr;
-        while (sm == nullptr) {
-            sm = interface_cast<AidlServiceManager>(ProcessState::self()->getContextObject(nullptr));
-            if (sm == nullptr) {
-                ALOGE("Waiting 1s on context object on %s.", ProcessState::self()->getDriverName().c_str());
-                sleep(1);
-            }
-        }
-
-        gDefaultServiceManager = sp<ServiceManagerShim>::make(sm);
+        gDefaultServiceManager = sp<ServiceManagerShim>::make(getBackendUnifiedServiceManager());
     });
 
     return gDefaultServiceManager;
@@ -290,9 +270,9 @@
 
 // ----------------------------------------------------------------------
 
-ServiceManagerShim::ServiceManagerShim(const sp<AidlServiceManager>& impl)
- : mTheRealServiceManager(impl)
-{}
+ServiceManagerShim::ServiceManagerShim(const sp<AidlServiceManager>& impl) {
+    mUnifiedServiceManager = sp<BackendUnifiedServiceManager>::make(impl);
+}
 
 // This implementation could be simplified and made more efficient by delegating
 // to waitForService. However, this changes the threading structure in some
@@ -345,7 +325,7 @@
 sp<IBinder> ServiceManagerShim::checkService(const String16& name) const
 {
     sp<IBinder> ret;
-    if (!mTheRealServiceManager->checkService(String8(name).c_str(), &ret).isOk()) {
+    if (!mUnifiedServiceManager->checkService(String8(name).c_str(), &ret).isOk()) {
         return nullptr;
     }
     return ret;
@@ -354,15 +334,15 @@
 status_t ServiceManagerShim::addService(const String16& name, const sp<IBinder>& service,
                                         bool allowIsolated, int dumpsysPriority)
 {
-    Status status = mTheRealServiceManager->addService(
-        String8(name).c_str(), service, allowIsolated, dumpsysPriority);
+    Status status = mUnifiedServiceManager->addService(String8(name).c_str(), service,
+                                                       allowIsolated, dumpsysPriority);
     return status.exceptionCode();
 }
 
 Vector<String16> ServiceManagerShim::listServices(int dumpsysPriority)
 {
     std::vector<std::string> ret;
-    if (!mTheRealServiceManager->listServices(dumpsysPriority, &ret).isOk()) {
+    if (!mUnifiedServiceManager->listServices(dumpsysPriority, &ret).isOk()) {
         return {};
     }
 
@@ -420,15 +400,13 @@
     if (out != nullptr) return out;
 
     sp<Waiter> waiter = sp<Waiter>::make();
-    if (Status status = mTheRealServiceManager->registerForNotifications(name, waiter);
+    if (Status status = mUnifiedServiceManager->registerForNotifications(name, waiter);
         !status.isOk()) {
         ALOGW("Failed to registerForNotifications in waitForService for %s: %s", name.c_str(),
               status.toString8().c_str());
         return nullptr;
     }
-    Defer unregister ([&] {
-        mTheRealServiceManager->unregisterForNotifications(name, waiter);
-    });
+    Defer unregister([&] { mUnifiedServiceManager->unregisterForNotifications(name, waiter); });
 
     while(true) {
         {
@@ -469,7 +447,7 @@
 
 bool ServiceManagerShim::isDeclared(const String16& name) {
     bool declared;
-    if (Status status = mTheRealServiceManager->isDeclared(String8(name).c_str(), &declared);
+    if (Status status = mUnifiedServiceManager->isDeclared(String8(name).c_str(), &declared);
         !status.isOk()) {
         ALOGW("Failed to get isDeclared for %s: %s", String8(name).c_str(),
               status.toString8().c_str());
@@ -481,7 +459,7 @@
 Vector<String16> ServiceManagerShim::getDeclaredInstances(const String16& interface) {
     std::vector<std::string> out;
     if (Status status =
-                mTheRealServiceManager->getDeclaredInstances(String8(interface).c_str(), &out);
+                mUnifiedServiceManager->getDeclaredInstances(String8(interface).c_str(), &out);
         !status.isOk()) {
         ALOGW("Failed to getDeclaredInstances for %s: %s", String8(interface).c_str(),
               status.toString8().c_str());
@@ -498,7 +476,7 @@
 
 std::optional<String16> ServiceManagerShim::updatableViaApex(const String16& name) {
     std::optional<std::string> declared;
-    if (Status status = mTheRealServiceManager->updatableViaApex(String8(name).c_str(), &declared);
+    if (Status status = mUnifiedServiceManager->updatableViaApex(String8(name).c_str(), &declared);
         !status.isOk()) {
         ALOGW("Failed to get updatableViaApex for %s: %s", String8(name).c_str(),
               status.toString8().c_str());
@@ -509,7 +487,7 @@
 
 Vector<String16> ServiceManagerShim::getUpdatableNames(const String16& apexName) {
     std::vector<std::string> out;
-    if (Status status = mTheRealServiceManager->getUpdatableNames(String8(apexName).c_str(), &out);
+    if (Status status = mUnifiedServiceManager->getUpdatableNames(String8(apexName).c_str(), &out);
         !status.isOk()) {
         ALOGW("Failed to getUpdatableNames for %s: %s", String8(apexName).c_str(),
               status.toString8().c_str());
@@ -528,7 +506,7 @@
         const String16& name) {
     std::optional<os::ConnectionInfo> connectionInfo;
     if (Status status =
-                mTheRealServiceManager->getConnectionInfo(String8(name).c_str(), &connectionInfo);
+                mUnifiedServiceManager->getConnectionInfo(String8(name).c_str(), &connectionInfo);
         !status.isOk()) {
         ALOGW("Failed to get ConnectionInfo for %s: %s", String8(name).c_str(),
               status.toString8().c_str());
@@ -549,7 +527,7 @@
     sp<RegistrationWaiter> registrationWaiter = sp<RegistrationWaiter>::make(cb);
     std::lock_guard<std::mutex> lock(mNameToRegistrationLock);
     if (Status status =
-                mTheRealServiceManager->registerForNotifications(nameStr, registrationWaiter);
+                mUnifiedServiceManager->registerForNotifications(nameStr, registrationWaiter);
         !status.isOk()) {
         ALOGW("Failed to registerForNotifications for %s: %s", nameStr.c_str(),
               status.toString8().c_str());
@@ -600,7 +578,7 @@
         ALOGE("%s Callback passed wasn't used to register for notifications", __FUNCTION__);
         return BAD_VALUE;
     }
-    if (Status status = mTheRealServiceManager->unregisterForNotifications(String8(name).c_str(),
+    if (Status status = mUnifiedServiceManager->unregisterForNotifications(String8(name).c_str(),
                                                                            registrationWaiter);
         !status.isOk()) {
         ALOGW("Failed to get service manager to unregisterForNotifications for %s: %s",
@@ -613,7 +591,7 @@
 std::vector<IServiceManager::ServiceDebugInfo> ServiceManagerShim::getServiceDebugInfo() {
     std::vector<os::ServiceDebugInfo> serviceDebugInfos;
     std::vector<IServiceManager::ServiceDebugInfo> ret;
-    if (Status status = mTheRealServiceManager->getServiceDebugInfo(&serviceDebugInfos);
+    if (Status status = mUnifiedServiceManager->getServiceDebugInfo(&serviceDebugInfos);
         !status.isOk()) {
         ALOGW("%s Failed to get ServiceDebugInfo", __FUNCTION__);
         return ret;
diff --git a/libs/binder/IServiceManagerFFI.cpp b/libs/binder/IServiceManagerFFI.cpp
new file mode 100644
index 0000000..7d4d7dc
--- /dev/null
+++ b/libs/binder/IServiceManagerFFI.cpp
@@ -0,0 +1,27 @@
+/*
+ * Copyright (C) 2024 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.
+ */
+#include <android/os/IServiceManager.h>
+
+#include <BackendUnifiedServiceManager.h>
+#include <binder/IServiceManagerFFI.h>
+
+namespace android::impl {
+sp<android::os::IServiceManager>
+getJavaServicemanagerImplPrivateDoNotUseExceptInTheOnePlaceItIsUsed() {
+    return getBackendUnifiedServiceManager();
+}
+
+} // namespace android::impl
diff --git a/libs/binder/include/binder/IServiceManagerFFI.h b/libs/binder/include/binder/IServiceManagerFFI.h
new file mode 100644
index 0000000..7537355
--- /dev/null
+++ b/libs/binder/include/binder/IServiceManagerFFI.h
@@ -0,0 +1,25 @@
+/*
+ * Copyright (C) 2024 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.
+ */
+#pragma once
+
+#include <android/os/IServiceManager.h>
+
+namespace android::impl {
+
+LIBBINDER_EXPORTED sp<android::os::IServiceManager>
+getJavaServicemanagerImplPrivateDoNotUseExceptInTheOnePlaceItIsUsed();
+
+} // namespace android::impl