Loading libs/binder/RpcConnection.cpp +54 −104 Original line number Diff line number Diff line Loading @@ -20,7 +20,6 @@ #include <binder/Parcel.h> #include <binder/Stability.h> #include <utils/String8.h> #include "RpcState.h" #include "RpcWireFormat.h" Loading @@ -30,20 +29,14 @@ #include <sys/un.h> #include <unistd.h> #ifdef __GLIBC__ #if defined(__GLIBC__) extern "C" pid_t gettid(); #endif #ifdef __BIONIC__ #include <linux/vm_sockets.h> #endif namespace android { using base::unique_fd; RpcConnection::SocketAddress::~SocketAddress() {} RpcConnection::RpcConnection() { LOG_RPC_DETAIL("RpcConnection created %p", this); Loading @@ -57,67 +50,64 @@ sp<RpcConnection> RpcConnection::make() { return new RpcConnection; } class UnixSocketAddress : public RpcConnection::SocketAddress { public: explicit UnixSocketAddress(const char* path) : mAddr({.sun_family = AF_UNIX}) { unsigned int pathLen = strlen(path) + 1; LOG_ALWAYS_FATAL_IF(pathLen > sizeof(mAddr.sun_path), "%u %s", pathLen, path); memcpy(mAddr.sun_path, path, pathLen); } virtual ~UnixSocketAddress() {} std::string toString() const override { return String8::format("path '%.*s'", static_cast<int>(sizeof(mAddr.sun_path)), mAddr.sun_path) .c_str(); bool RpcConnection::setupUnixDomainServer(const char* path) { LOG_ALWAYS_FATAL_IF(mServer.get() != -1, "Only supports one server now"); unique_fd serverFd(TEMP_FAILURE_RETRY(socket(AF_UNIX, SOCK_STREAM | SOCK_CLOEXEC, 0))); if (serverFd == -1) { ALOGE("Could not create socket at %s: %s", path, strerror(errno)); return false; } const sockaddr* addr() const override { return reinterpret_cast<const sockaddr*>(&mAddr); } size_t addrSize() const override { return sizeof(mAddr); } private: sockaddr_un mAddr; struct sockaddr_un addr = { .sun_family = AF_UNIX, }; bool RpcConnection::setupUnixDomainServer(const char* path) { return addServer(UnixSocketAddress(path)); unsigned int pathLen = strlen(path) + 1; LOG_ALWAYS_FATAL_IF(pathLen > sizeof(addr.sun_path), "%u", pathLen); memcpy(addr.sun_path, path, pathLen); if (0 != TEMP_FAILURE_RETRY(bind(serverFd.get(), (struct sockaddr*)&addr, sizeof(addr)))) { ALOGE("Could not bind socket at %s: %s", path, strerror(errno)); return false; } bool RpcConnection::addUnixDomainClient(const char* path) { return addClient(UnixSocketAddress(path)); if (0 != TEMP_FAILURE_RETRY(listen(serverFd.get(), 1 /*backlog*/))) { ALOGE("Could not listen socket at %s: %s", path, strerror(errno)); return false; } #ifdef __BIONIC__ mServer = std::move(serverFd); return true; } bool RpcConnection::addUnixDomainClient(const char* path) { LOG_RPC_DETAIL("Connecting on path: %s", path); class VsockSocketAddress : public RpcConnection::SocketAddress { public: VsockSocketAddress(unsigned int cid, unsigned int port) : mAddr({ .svm_family = AF_VSOCK, .svm_port = port, .svm_cid = cid, }) {} virtual ~VsockSocketAddress() {} std::string toString() const override { return String8::format("cid %du port %du", mAddr.svm_cid, mAddr.svm_port).c_str(); unique_fd serverFd(TEMP_FAILURE_RETRY(socket(AF_UNIX, SOCK_STREAM | SOCK_CLOEXEC, 0))); if (serverFd == -1) { ALOGE("Could not create socket at %s: %s", path, strerror(errno)); return false; } const sockaddr* addr() const override { return reinterpret_cast<const sockaddr*>(&mAddr); } size_t addrSize() const override { return sizeof(mAddr); } private: sockaddr_vm mAddr; struct sockaddr_un addr = { .sun_family = AF_UNIX, }; bool RpcConnection::setupVsockServer(unsigned int port) { // realizing value w/ this type at compile time to avoid ubsan abort constexpr unsigned int kAnyCid = VMADDR_CID_ANY; unsigned int pathLen = strlen(path) + 1; LOG_ALWAYS_FATAL_IF(pathLen > sizeof(addr.sun_path), "%u", pathLen); memcpy(addr.sun_path, path, pathLen); return addServer(VsockSocketAddress(kAnyCid, port)); if (0 != TEMP_FAILURE_RETRY(connect(serverFd.get(), (struct sockaddr*)&addr, sizeof(addr)))) { ALOGE("Could not connect socket at %s: %s", path, strerror(errno)); return false; } bool RpcConnection::addVsockClient(unsigned int cid, unsigned int port) { return addClient(VsockSocketAddress(cid, port)); } LOG_RPC_DETAIL("Unix domain client with fd %d", serverFd.get()); #endif // __BIONIC__ addClient(std::move(serverFd)); return true; } sp<IBinder> RpcConnection::getRootObject() { ExclusiveSocket socket(this, SocketUse::CLIENT); Loading @@ -140,8 +130,11 @@ status_t RpcConnection::sendDecStrong(const RpcAddress& address) { void RpcConnection::join() { // establish a connection { unique_fd clientFd( TEMP_FAILURE_RETRY(accept4(mServer.get(), nullptr, 0 /*length*/, SOCK_CLOEXEC))); struct sockaddr_un clientSa; socklen_t clientSaLen = sizeof(clientSa); unique_fd clientFd(TEMP_FAILURE_RETRY( accept4(mServer.get(), (struct sockaddr*)&clientSa, &clientSaLen, SOCK_CLOEXEC))); if (clientFd < 0) { // If this log becomes confusing, should save more state from setupUnixDomainServer // in order to output here. Loading @@ -151,7 +144,7 @@ void RpcConnection::join() { LOG_RPC_DETAIL("accept4 on fd %d yields fd %d", mServer.get(), clientFd.get()); assignServerToThisThread(std::move(clientFd)); addServer(std::move(clientFd)); } // We may not use the connection we just established (two threads might Loading @@ -177,57 +170,14 @@ wp<RpcServer> RpcConnection::server() { return mForServer; } bool RpcConnection::addServer(const SocketAddress& addr) { LOG_ALWAYS_FATAL_IF(mServer.get() != -1, "Each RpcConnection can only have one server."); unique_fd serverFd( TEMP_FAILURE_RETRY(socket(addr.addr()->sa_family, SOCK_STREAM | SOCK_CLOEXEC, 0))); if (serverFd == -1) { ALOGE("Could not create socket: %s", strerror(errno)); return false; } if (0 != TEMP_FAILURE_RETRY(bind(serverFd.get(), addr.addr(), addr.addrSize()))) { int savedErrno = errno; ALOGE("Could not bind socket at %s: %s", addr.toString().c_str(), strerror(savedErrno)); return false; } if (0 != TEMP_FAILURE_RETRY(listen(serverFd.get(), 1 /*backlog*/))) { int savedErrno = errno; ALOGE("Could not listen socket at %s: %s", addr.toString().c_str(), strerror(savedErrno)); return false; } mServer = std::move(serverFd); return true; } bool RpcConnection::addClient(const SocketAddress& addr) { unique_fd serverFd( TEMP_FAILURE_RETRY(socket(addr.addr()->sa_family, SOCK_STREAM | SOCK_CLOEXEC, 0))); if (serverFd == -1) { int savedErrno = errno; ALOGE("Could not create socket at %s: %s", addr.toString().c_str(), strerror(savedErrno)); return false; } if (0 != TEMP_FAILURE_RETRY(connect(serverFd.get(), addr.addr(), addr.addrSize()))) { int savedErrno = errno; ALOGE("Could not connect socket at %s: %s", addr.toString().c_str(), strerror(savedErrno)); return false; } LOG_RPC_DETAIL("Socket at %s client with fd %d", addr.toString().c_str(), serverFd.get()); void RpcConnection::addClient(base::unique_fd&& fd) { std::lock_guard<std::mutex> _l(mSocketMutex); sp<ConnectionSocket> connection = new ConnectionSocket(); connection->fd = std::move(serverFd); connection->fd = std::move(fd); mClients.push_back(connection); return true; } void RpcConnection::assignServerToThisThread(base::unique_fd&& fd) { void RpcConnection::addServer(base::unique_fd&& fd) { std::lock_guard<std::mutex> _l(mSocketMutex); sp<ConnectionSocket> connection = new ConnectionSocket(); connection->fd = std::move(fd); Loading libs/binder/include/binder/RpcConnection.h +2 −23 Original line number Diff line number Diff line Loading @@ -61,18 +61,6 @@ public: */ [[nodiscard]] bool addUnixDomainClient(const char* path); #ifdef __BIONIC__ /** * Creates an RPC server at the current port. */ [[nodiscard]] bool setupVsockServer(unsigned int port); /** * Connects to an RPC server at the CVD & port. */ [[nodiscard]] bool addVsockClient(unsigned int cvd, unsigned int port); #endif // __BIONIC__ /** * Query the other side of the connection for the root object hosted by that * process's RpcServer (if one exists) Loading @@ -97,20 +85,11 @@ public: // internal only const std::unique_ptr<RpcState>& state() { return mState; } class SocketAddress { public: virtual ~SocketAddress(); virtual std::string toString() const = 0; virtual const sockaddr* addr() const = 0; virtual size_t addrSize() const = 0; }; private: RpcConnection(); bool addServer(const SocketAddress& address); bool addClient(const SocketAddress& address); void assignServerToThisThread(base::unique_fd&& fd); void addServer(base::unique_fd&& fd); void addClient(base::unique_fd&& fd); struct ConnectionSocket : public RefBase { base::unique_fd fd; Loading libs/binder/tests/Android.bp +0 −1 Original line number Diff line number Diff line Loading @@ -122,7 +122,6 @@ cc_test { ], test_suites: ["general-tests"], require_root: true, host_supported: true, } cc_test { Loading libs/binder/tests/binderRpcTest.cpp +109 −171 Original line number Diff line number Diff line Loading @@ -14,6 +14,14 @@ * limitations under the License. */ #include <sys/prctl.h> #include <unistd.h> #include <chrono> #include <cstdlib> #include <iostream> #include <thread> #include <BnBinderRpcSession.h> #include <BnBinderRpcTest.h> #include <android-base/logging.h> Loading @@ -25,18 +33,6 @@ #include <binder/RpcServer.h> #include <gtest/gtest.h> #include <chrono> #include <cstdlib> #include <iostream> #include <thread> #ifdef __BIONIC__ #include <linux/vm_sockets.h> #endif //__BIONIC__ #include <sys/prctl.h> #include <unistd.h> #include "../RpcState.h" // for debugging namespace android { Loading Loading @@ -189,13 +185,8 @@ private: static std::string allocateSocketAddress() { static size_t id = 0; static bool gUseTmp = access("/tmp/", F_OK) != -1; if (gUseTmp) { return "/tmp/binderRpcTest_" + std::to_string(id++); } else { return "/dev/binderRpcTest_" + std::to_string(id++); } }; struct ProcessConnection { Loading Loading @@ -223,51 +214,6 @@ struct ProcessConnection { } }; // Process connection where the process hosts IBinderRpcTest, the server used // for most testing here struct BinderRpcTestProcessConnection { ProcessConnection proc; // pre-fetched root object sp<IBinder> rootBinder; // pre-casted root object sp<IBinderRpcTest> rootIface; ~BinderRpcTestProcessConnection() { if (!proc.expectInvalid) { int32_t remoteBinders = 0; EXPECT_OK(rootIface->countBinders(&remoteBinders)); // should only be the root binder object, iface EXPECT_EQ(remoteBinders, 1); } rootIface = nullptr; rootBinder = nullptr; } }; enum class SocketType { UNIX, #ifdef __BIONIC__ VSOCK, #endif // __BIONIC__ }; static inline std::string PrintSocketType(const testing::TestParamInfo<SocketType>& info) { switch (info.param) { case SocketType::UNIX: return "unix_domain_socket"; #ifdef __BIONIC__ case SocketType::VSOCK: return "vm_socket"; #endif // __BIONIC__ default: LOG_ALWAYS_FATAL("Unknown socket type"); return ""; } } class BinderRpc : public ::testing::TestWithParam<SocketType> { public: // This creates a new process serving an interface on a certain number of // threads. ProcessConnection createRpcTestSocketServerProcess( Loading @@ -275,12 +221,8 @@ public: const std::function<void(const sp<RpcServer>&, const sp<RpcConnection>&)>& configure) { CHECK_GT(numThreads, 0); SocketType socketType = GetParam(); std::string addr = allocateSocketAddress(); unlink(addr.c_str()); static unsigned int port = 3456; port++; auto ret = ProcessConnection{ .host = Process([&] { Loading @@ -290,19 +232,7 @@ public: // server supporting one client on one socket sp<RpcConnection> connection = server->addClientConnection(); switch (socketType) { case SocketType::UNIX: CHECK(connection->setupUnixDomainServer(addr.c_str())) << addr; break; #ifdef __BIONIC__ case SocketType::VSOCK: CHECK(connection->setupVsockServer(port)); break; #endif // __BIONIC__ default: LOG_ALWAYS_FATAL("Unknown socket type"); } configure(server, connection); Loading @@ -317,31 +247,49 @@ public: .connection = RpcConnection::make(), }; // wait up to 1s for sockets to be created constexpr useconds_t kMaxWaitUs = 1000000; constexpr useconds_t kWaitDivision = 100; for (size_t i = 0; i < kWaitDivision && 0 != access(addr.c_str(), F_OK); i++) { usleep(kMaxWaitUs / kWaitDivision); } // create remainder of connections for (size_t i = 0; i < numThreads; i++) { for (size_t tries = 0; tries < 5; tries++) { usleep(10000); switch (socketType) { case SocketType::UNIX: if (ret.connection->addUnixDomainClient(addr.c_str())) goto success; break; #ifdef __BIONIC__ case SocketType::VSOCK: if (ret.connection->addVsockClient(VMADDR_CID_LOCAL, port)) goto success; break; #endif // __BIONIC__ default: LOG_ALWAYS_FATAL("Unknown socket type"); } } LOG_ALWAYS_FATAL("Could not connect"); success:; // Connection refused sometimes after file created but before listening. CHECK(ret.connection->addUnixDomainClient(addr.c_str()) || (usleep(10000), ret.connection->addUnixDomainClient(addr.c_str()))) << i; } ret.rootBinder = ret.connection->getRootObject(); return ret; } // Process connection where the process hosts IBinderRpcTest, the server used // for most testing here struct BinderRpcTestProcessConnection { ProcessConnection proc; // pre-fetched root object sp<IBinder> rootBinder; // pre-casted root object sp<IBinderRpcTest> rootIface; ~BinderRpcTestProcessConnection() { if (!proc.expectInvalid) { int32_t remoteBinders = 0; EXPECT_OK(rootIface->countBinders(&remoteBinders)); // should only be the root binder object, iface EXPECT_EQ(remoteBinders, 1); } rootIface = nullptr; rootBinder = nullptr; } }; BinderRpcTestProcessConnection createRpcTestSocketServerProcess(size_t numThreads) { BinderRpcTestProcessConnection ret{ .proc = createRpcTestSocketServerProcess(numThreads, Loading @@ -360,9 +308,8 @@ public: return ret; } }; TEST_P(BinderRpc, RootObjectIsNull) { TEST(BinderRpc, RootObjectIsNull) { auto proc = createRpcTestSocketServerProcess(1, [](const sp<RpcServer>& server, const sp<RpcConnection>&) { Loading @@ -377,20 +324,20 @@ TEST_P(BinderRpc, RootObjectIsNull) { EXPECT_EQ(nullptr, proc.connection->getRootObject()); } TEST_P(BinderRpc, Ping) { TEST(BinderRpc, Ping) { auto proc = createRpcTestSocketServerProcess(1); ASSERT_NE(proc.rootBinder, nullptr); EXPECT_EQ(OK, proc.rootBinder->pingBinder()); } TEST_P(BinderRpc, TransactionsMustBeMarkedRpc) { TEST(BinderRpc, TransactionsMustBeMarkedRpc) { auto proc = createRpcTestSocketServerProcess(1); Parcel data; Parcel reply; EXPECT_EQ(BAD_TYPE, proc.rootBinder->transact(IBinder::PING_TRANSACTION, data, &reply, 0)); } TEST_P(BinderRpc, UnknownTransaction) { TEST(BinderRpc, UnknownTransaction) { auto proc = createRpcTestSocketServerProcess(1); Parcel data; data.markForBinder(proc.rootBinder); Loading @@ -398,19 +345,19 @@ TEST_P(BinderRpc, UnknownTransaction) { EXPECT_EQ(UNKNOWN_TRANSACTION, proc.rootBinder->transact(1337, data, &reply, 0)); } TEST_P(BinderRpc, SendSomethingOneway) { TEST(BinderRpc, SendSomethingOneway) { auto proc = createRpcTestSocketServerProcess(1); EXPECT_OK(proc.rootIface->sendString("asdf")); } TEST_P(BinderRpc, SendAndGetResultBack) { TEST(BinderRpc, SendAndGetResultBack) { auto proc = createRpcTestSocketServerProcess(1); std::string doubled; EXPECT_OK(proc.rootIface->doubleString("cool ", &doubled)); EXPECT_EQ("cool cool ", doubled); } TEST_P(BinderRpc, SendAndGetResultBackBig) { TEST(BinderRpc, SendAndGetResultBackBig) { auto proc = createRpcTestSocketServerProcess(1); std::string single = std::string(1024, 'a'); std::string doubled; Loading @@ -418,7 +365,7 @@ TEST_P(BinderRpc, SendAndGetResultBackBig) { EXPECT_EQ(single + single, doubled); } TEST_P(BinderRpc, CallMeBack) { TEST(BinderRpc, CallMeBack) { auto proc = createRpcTestSocketServerProcess(1); int32_t pingResult; Loading @@ -428,7 +375,7 @@ TEST_P(BinderRpc, CallMeBack) { EXPECT_EQ(0, MyBinderRpcSession::gNum); } TEST_P(BinderRpc, RepeatBinder) { TEST(BinderRpc, RepeatBinder) { auto proc = createRpcTestSocketServerProcess(1); sp<IBinder> inBinder = new MyBinderRpcSession("foo"); Loading @@ -450,7 +397,7 @@ TEST_P(BinderRpc, RepeatBinder) { EXPECT_EQ(0, MyBinderRpcSession::gNum); } TEST_P(BinderRpc, RepeatTheirBinder) { TEST(BinderRpc, RepeatTheirBinder) { auto proc = createRpcTestSocketServerProcess(1); sp<IBinderRpcSession> session; Loading @@ -474,7 +421,7 @@ TEST_P(BinderRpc, RepeatTheirBinder) { EXPECT_EQ(nullptr, weak.promote()); } TEST_P(BinderRpc, RepeatBinderNull) { TEST(BinderRpc, RepeatBinderNull) { auto proc = createRpcTestSocketServerProcess(1); sp<IBinder> outBinder; Loading @@ -482,7 +429,7 @@ TEST_P(BinderRpc, RepeatBinderNull) { EXPECT_EQ(nullptr, outBinder); } TEST_P(BinderRpc, HoldBinder) { TEST(BinderRpc, HoldBinder) { auto proc = createRpcTestSocketServerProcess(1); IBinder* ptr = nullptr; Loading @@ -508,7 +455,7 @@ TEST_P(BinderRpc, HoldBinder) { // These are behavioral differences form regular binder, where certain usecases // aren't supported. TEST_P(BinderRpc, CannotMixBindersBetweenUnrelatedSocketConnections) { TEST(BinderRpc, CannotMixBindersBetweenUnrelatedSocketConnections) { auto proc1 = createRpcTestSocketServerProcess(1); auto proc2 = createRpcTestSocketServerProcess(1); Loading @@ -517,7 +464,7 @@ TEST_P(BinderRpc, CannotMixBindersBetweenUnrelatedSocketConnections) { proc1.rootIface->repeatBinder(proc2.rootBinder, &outBinder).transactionError()); } TEST_P(BinderRpc, CannotSendRegularBinderOverSocketBinder) { TEST(BinderRpc, CannotSendRegularBinderOverSocketBinder) { auto proc = createRpcTestSocketServerProcess(1); sp<IBinder> someRealBinder = IInterface::asBinder(defaultServiceManager()); Loading @@ -526,7 +473,7 @@ TEST_P(BinderRpc, CannotSendRegularBinderOverSocketBinder) { proc.rootIface->repeatBinder(someRealBinder, &outBinder).transactionError()); } TEST_P(BinderRpc, CannotSendSocketBinderOverRegularBinder) { TEST(BinderRpc, CannotSendSocketBinderOverRegularBinder) { auto proc = createRpcTestSocketServerProcess(1); // for historical reasons, IServiceManager interface only returns the Loading @@ -537,7 +484,7 @@ TEST_P(BinderRpc, CannotSendSocketBinderOverRegularBinder) { // END TESTS FOR LIMITATIONS OF SOCKET BINDER TEST_P(BinderRpc, RepeatRootObject) { TEST(BinderRpc, RepeatRootObject) { auto proc = createRpcTestSocketServerProcess(1); sp<IBinder> outBinder; Loading @@ -545,7 +492,7 @@ TEST_P(BinderRpc, RepeatRootObject) { EXPECT_EQ(proc.rootBinder, outBinder); } TEST_P(BinderRpc, NestedTransactions) { TEST(BinderRpc, NestedTransactions) { auto proc = createRpcTestSocketServerProcess(1); auto nastyNester = sp<MyBinderRpcTest>::make(); Loading @@ -556,7 +503,7 @@ TEST_P(BinderRpc, NestedTransactions) { EXPECT_EQ(nullptr, weak.promote()); } TEST_P(BinderRpc, SameBinderEquality) { TEST(BinderRpc, SameBinderEquality) { auto proc = createRpcTestSocketServerProcess(1); sp<IBinder> a; Loading @@ -568,7 +515,7 @@ TEST_P(BinderRpc, SameBinderEquality) { EXPECT_EQ(a, b); } TEST_P(BinderRpc, SameBinderEqualityWeak) { TEST(BinderRpc, SameBinderEqualityWeak) { auto proc = createRpcTestSocketServerProcess(1); sp<IBinder> a; Loading Loading @@ -600,7 +547,7 @@ TEST_P(BinderRpc, SameBinderEqualityWeak) { EXPECT_EQ(expected, session); \ } while (false) TEST_P(BinderRpc, SingleSession) { TEST(BinderRpc, SingleSession) { auto proc = createRpcTestSocketServerProcess(1); sp<IBinderRpcSession> session; Loading @@ -614,7 +561,7 @@ TEST_P(BinderRpc, SingleSession) { expectSessions(0, proc.rootIface); } TEST_P(BinderRpc, ManySessions) { TEST(BinderRpc, ManySessions) { auto proc = createRpcTestSocketServerProcess(1); std::vector<sp<IBinderRpcSession>> sessions; Loading Loading @@ -648,7 +595,7 @@ size_t epochMillis() { return duration_cast<milliseconds>(system_clock::now().time_since_epoch()).count(); } TEST_P(BinderRpc, ThreadPoolGreaterThanEqualRequested) { TEST(BinderRpc, ThreadPoolGreaterThanEqualRequested) { constexpr size_t kNumThreads = 10; auto proc = createRpcTestSocketServerProcess(kNumThreads); Loading Loading @@ -680,7 +627,7 @@ TEST_P(BinderRpc, ThreadPoolGreaterThanEqualRequested) { for (auto& t : ts) t.join(); } TEST_P(BinderRpc, ThreadPoolOverSaturated) { TEST(BinderRpc, ThreadPoolOverSaturated) { constexpr size_t kNumThreads = 10; constexpr size_t kNumCalls = kNumThreads + 3; constexpr size_t kSleepMs = 500; Loading @@ -704,7 +651,7 @@ TEST_P(BinderRpc, ThreadPoolOverSaturated) { EXPECT_LE(epochMsAfter, epochMsBefore + 3 * kSleepMs); } TEST_P(BinderRpc, ThreadingStressTest) { TEST(BinderRpc, ThreadingStressTest) { constexpr size_t kNumClientThreads = 10; constexpr size_t kNumServerThreads = 10; constexpr size_t kNumCalls = 100; Loading @@ -725,7 +672,7 @@ TEST_P(BinderRpc, ThreadingStressTest) { for (auto& t : threads) t.join(); } TEST_P(BinderRpc, OnewayCallDoesNotWait) { TEST(BinderRpc, OnewayCallDoesNotWait) { constexpr size_t kReallyLongTimeMs = 100; constexpr size_t kSleepMs = kReallyLongTimeMs * 5; Loading @@ -740,7 +687,7 @@ TEST_P(BinderRpc, OnewayCallDoesNotWait) { EXPECT_LT(epochMsAfter, epochMsBefore + kReallyLongTimeMs); } TEST_P(BinderRpc, OnewayCallQueueing) { TEST(BinderRpc, OnewayCallQueueing) { constexpr size_t kNumSleeps = 10; constexpr size_t kNumExtraServerThreads = 4; constexpr size_t kSleepMs = 50; Loading @@ -764,7 +711,7 @@ TEST_P(BinderRpc, OnewayCallQueueing) { EXPECT_GT(epochMsAfter, epochMsBefore + kSleepMs * kNumSleeps); } TEST_P(BinderRpc, Die) { TEST(BinderRpc, Die) { // TODO(b/183141167): handle this in library signal(SIGPIPE, SIG_IGN); Loading Loading @@ -796,7 +743,7 @@ ssize_t countFds() { return ret; } TEST_P(BinderRpc, Fds) { TEST(BinderRpc, Fds) { ssize_t beforeFds = countFds(); ASSERT_GE(beforeFds, 0); { Loading @@ -806,19 +753,10 @@ TEST_P(BinderRpc, Fds) { ASSERT_EQ(beforeFds, countFds()) << (system("ls -l /proc/self/fd/"), "fd leak?"); } INSTANTIATE_TEST_CASE_P(PerSocket, BinderRpc, ::testing::Values(SocketType::UNIX #ifdef __BIONIC__ , SocketType::VSOCK #endif // __BIONIC__ ), PrintSocketType); } // namespace android int main(int argc, char** argv) { extern "C" int main(int argc, char** argv) { ::testing::InitGoogleTest(&argc, argv); android::base::InitLogging(argv, android::base::StderrLogger, android::base::DefaultAborter); return RUN_ALL_TESTS(); } } // namespace android Loading
libs/binder/RpcConnection.cpp +54 −104 Original line number Diff line number Diff line Loading @@ -20,7 +20,6 @@ #include <binder/Parcel.h> #include <binder/Stability.h> #include <utils/String8.h> #include "RpcState.h" #include "RpcWireFormat.h" Loading @@ -30,20 +29,14 @@ #include <sys/un.h> #include <unistd.h> #ifdef __GLIBC__ #if defined(__GLIBC__) extern "C" pid_t gettid(); #endif #ifdef __BIONIC__ #include <linux/vm_sockets.h> #endif namespace android { using base::unique_fd; RpcConnection::SocketAddress::~SocketAddress() {} RpcConnection::RpcConnection() { LOG_RPC_DETAIL("RpcConnection created %p", this); Loading @@ -57,67 +50,64 @@ sp<RpcConnection> RpcConnection::make() { return new RpcConnection; } class UnixSocketAddress : public RpcConnection::SocketAddress { public: explicit UnixSocketAddress(const char* path) : mAddr({.sun_family = AF_UNIX}) { unsigned int pathLen = strlen(path) + 1; LOG_ALWAYS_FATAL_IF(pathLen > sizeof(mAddr.sun_path), "%u %s", pathLen, path); memcpy(mAddr.sun_path, path, pathLen); } virtual ~UnixSocketAddress() {} std::string toString() const override { return String8::format("path '%.*s'", static_cast<int>(sizeof(mAddr.sun_path)), mAddr.sun_path) .c_str(); bool RpcConnection::setupUnixDomainServer(const char* path) { LOG_ALWAYS_FATAL_IF(mServer.get() != -1, "Only supports one server now"); unique_fd serverFd(TEMP_FAILURE_RETRY(socket(AF_UNIX, SOCK_STREAM | SOCK_CLOEXEC, 0))); if (serverFd == -1) { ALOGE("Could not create socket at %s: %s", path, strerror(errno)); return false; } const sockaddr* addr() const override { return reinterpret_cast<const sockaddr*>(&mAddr); } size_t addrSize() const override { return sizeof(mAddr); } private: sockaddr_un mAddr; struct sockaddr_un addr = { .sun_family = AF_UNIX, }; bool RpcConnection::setupUnixDomainServer(const char* path) { return addServer(UnixSocketAddress(path)); unsigned int pathLen = strlen(path) + 1; LOG_ALWAYS_FATAL_IF(pathLen > sizeof(addr.sun_path), "%u", pathLen); memcpy(addr.sun_path, path, pathLen); if (0 != TEMP_FAILURE_RETRY(bind(serverFd.get(), (struct sockaddr*)&addr, sizeof(addr)))) { ALOGE("Could not bind socket at %s: %s", path, strerror(errno)); return false; } bool RpcConnection::addUnixDomainClient(const char* path) { return addClient(UnixSocketAddress(path)); if (0 != TEMP_FAILURE_RETRY(listen(serverFd.get(), 1 /*backlog*/))) { ALOGE("Could not listen socket at %s: %s", path, strerror(errno)); return false; } #ifdef __BIONIC__ mServer = std::move(serverFd); return true; } bool RpcConnection::addUnixDomainClient(const char* path) { LOG_RPC_DETAIL("Connecting on path: %s", path); class VsockSocketAddress : public RpcConnection::SocketAddress { public: VsockSocketAddress(unsigned int cid, unsigned int port) : mAddr({ .svm_family = AF_VSOCK, .svm_port = port, .svm_cid = cid, }) {} virtual ~VsockSocketAddress() {} std::string toString() const override { return String8::format("cid %du port %du", mAddr.svm_cid, mAddr.svm_port).c_str(); unique_fd serverFd(TEMP_FAILURE_RETRY(socket(AF_UNIX, SOCK_STREAM | SOCK_CLOEXEC, 0))); if (serverFd == -1) { ALOGE("Could not create socket at %s: %s", path, strerror(errno)); return false; } const sockaddr* addr() const override { return reinterpret_cast<const sockaddr*>(&mAddr); } size_t addrSize() const override { return sizeof(mAddr); } private: sockaddr_vm mAddr; struct sockaddr_un addr = { .sun_family = AF_UNIX, }; bool RpcConnection::setupVsockServer(unsigned int port) { // realizing value w/ this type at compile time to avoid ubsan abort constexpr unsigned int kAnyCid = VMADDR_CID_ANY; unsigned int pathLen = strlen(path) + 1; LOG_ALWAYS_FATAL_IF(pathLen > sizeof(addr.sun_path), "%u", pathLen); memcpy(addr.sun_path, path, pathLen); return addServer(VsockSocketAddress(kAnyCid, port)); if (0 != TEMP_FAILURE_RETRY(connect(serverFd.get(), (struct sockaddr*)&addr, sizeof(addr)))) { ALOGE("Could not connect socket at %s: %s", path, strerror(errno)); return false; } bool RpcConnection::addVsockClient(unsigned int cid, unsigned int port) { return addClient(VsockSocketAddress(cid, port)); } LOG_RPC_DETAIL("Unix domain client with fd %d", serverFd.get()); #endif // __BIONIC__ addClient(std::move(serverFd)); return true; } sp<IBinder> RpcConnection::getRootObject() { ExclusiveSocket socket(this, SocketUse::CLIENT); Loading @@ -140,8 +130,11 @@ status_t RpcConnection::sendDecStrong(const RpcAddress& address) { void RpcConnection::join() { // establish a connection { unique_fd clientFd( TEMP_FAILURE_RETRY(accept4(mServer.get(), nullptr, 0 /*length*/, SOCK_CLOEXEC))); struct sockaddr_un clientSa; socklen_t clientSaLen = sizeof(clientSa); unique_fd clientFd(TEMP_FAILURE_RETRY( accept4(mServer.get(), (struct sockaddr*)&clientSa, &clientSaLen, SOCK_CLOEXEC))); if (clientFd < 0) { // If this log becomes confusing, should save more state from setupUnixDomainServer // in order to output here. Loading @@ -151,7 +144,7 @@ void RpcConnection::join() { LOG_RPC_DETAIL("accept4 on fd %d yields fd %d", mServer.get(), clientFd.get()); assignServerToThisThread(std::move(clientFd)); addServer(std::move(clientFd)); } // We may not use the connection we just established (two threads might Loading @@ -177,57 +170,14 @@ wp<RpcServer> RpcConnection::server() { return mForServer; } bool RpcConnection::addServer(const SocketAddress& addr) { LOG_ALWAYS_FATAL_IF(mServer.get() != -1, "Each RpcConnection can only have one server."); unique_fd serverFd( TEMP_FAILURE_RETRY(socket(addr.addr()->sa_family, SOCK_STREAM | SOCK_CLOEXEC, 0))); if (serverFd == -1) { ALOGE("Could not create socket: %s", strerror(errno)); return false; } if (0 != TEMP_FAILURE_RETRY(bind(serverFd.get(), addr.addr(), addr.addrSize()))) { int savedErrno = errno; ALOGE("Could not bind socket at %s: %s", addr.toString().c_str(), strerror(savedErrno)); return false; } if (0 != TEMP_FAILURE_RETRY(listen(serverFd.get(), 1 /*backlog*/))) { int savedErrno = errno; ALOGE("Could not listen socket at %s: %s", addr.toString().c_str(), strerror(savedErrno)); return false; } mServer = std::move(serverFd); return true; } bool RpcConnection::addClient(const SocketAddress& addr) { unique_fd serverFd( TEMP_FAILURE_RETRY(socket(addr.addr()->sa_family, SOCK_STREAM | SOCK_CLOEXEC, 0))); if (serverFd == -1) { int savedErrno = errno; ALOGE("Could not create socket at %s: %s", addr.toString().c_str(), strerror(savedErrno)); return false; } if (0 != TEMP_FAILURE_RETRY(connect(serverFd.get(), addr.addr(), addr.addrSize()))) { int savedErrno = errno; ALOGE("Could not connect socket at %s: %s", addr.toString().c_str(), strerror(savedErrno)); return false; } LOG_RPC_DETAIL("Socket at %s client with fd %d", addr.toString().c_str(), serverFd.get()); void RpcConnection::addClient(base::unique_fd&& fd) { std::lock_guard<std::mutex> _l(mSocketMutex); sp<ConnectionSocket> connection = new ConnectionSocket(); connection->fd = std::move(serverFd); connection->fd = std::move(fd); mClients.push_back(connection); return true; } void RpcConnection::assignServerToThisThread(base::unique_fd&& fd) { void RpcConnection::addServer(base::unique_fd&& fd) { std::lock_guard<std::mutex> _l(mSocketMutex); sp<ConnectionSocket> connection = new ConnectionSocket(); connection->fd = std::move(fd); Loading
libs/binder/include/binder/RpcConnection.h +2 −23 Original line number Diff line number Diff line Loading @@ -61,18 +61,6 @@ public: */ [[nodiscard]] bool addUnixDomainClient(const char* path); #ifdef __BIONIC__ /** * Creates an RPC server at the current port. */ [[nodiscard]] bool setupVsockServer(unsigned int port); /** * Connects to an RPC server at the CVD & port. */ [[nodiscard]] bool addVsockClient(unsigned int cvd, unsigned int port); #endif // __BIONIC__ /** * Query the other side of the connection for the root object hosted by that * process's RpcServer (if one exists) Loading @@ -97,20 +85,11 @@ public: // internal only const std::unique_ptr<RpcState>& state() { return mState; } class SocketAddress { public: virtual ~SocketAddress(); virtual std::string toString() const = 0; virtual const sockaddr* addr() const = 0; virtual size_t addrSize() const = 0; }; private: RpcConnection(); bool addServer(const SocketAddress& address); bool addClient(const SocketAddress& address); void assignServerToThisThread(base::unique_fd&& fd); void addServer(base::unique_fd&& fd); void addClient(base::unique_fd&& fd); struct ConnectionSocket : public RefBase { base::unique_fd fd; Loading
libs/binder/tests/Android.bp +0 −1 Original line number Diff line number Diff line Loading @@ -122,7 +122,6 @@ cc_test { ], test_suites: ["general-tests"], require_root: true, host_supported: true, } cc_test { Loading
libs/binder/tests/binderRpcTest.cpp +109 −171 Original line number Diff line number Diff line Loading @@ -14,6 +14,14 @@ * limitations under the License. */ #include <sys/prctl.h> #include <unistd.h> #include <chrono> #include <cstdlib> #include <iostream> #include <thread> #include <BnBinderRpcSession.h> #include <BnBinderRpcTest.h> #include <android-base/logging.h> Loading @@ -25,18 +33,6 @@ #include <binder/RpcServer.h> #include <gtest/gtest.h> #include <chrono> #include <cstdlib> #include <iostream> #include <thread> #ifdef __BIONIC__ #include <linux/vm_sockets.h> #endif //__BIONIC__ #include <sys/prctl.h> #include <unistd.h> #include "../RpcState.h" // for debugging namespace android { Loading Loading @@ -189,13 +185,8 @@ private: static std::string allocateSocketAddress() { static size_t id = 0; static bool gUseTmp = access("/tmp/", F_OK) != -1; if (gUseTmp) { return "/tmp/binderRpcTest_" + std::to_string(id++); } else { return "/dev/binderRpcTest_" + std::to_string(id++); } }; struct ProcessConnection { Loading Loading @@ -223,51 +214,6 @@ struct ProcessConnection { } }; // Process connection where the process hosts IBinderRpcTest, the server used // for most testing here struct BinderRpcTestProcessConnection { ProcessConnection proc; // pre-fetched root object sp<IBinder> rootBinder; // pre-casted root object sp<IBinderRpcTest> rootIface; ~BinderRpcTestProcessConnection() { if (!proc.expectInvalid) { int32_t remoteBinders = 0; EXPECT_OK(rootIface->countBinders(&remoteBinders)); // should only be the root binder object, iface EXPECT_EQ(remoteBinders, 1); } rootIface = nullptr; rootBinder = nullptr; } }; enum class SocketType { UNIX, #ifdef __BIONIC__ VSOCK, #endif // __BIONIC__ }; static inline std::string PrintSocketType(const testing::TestParamInfo<SocketType>& info) { switch (info.param) { case SocketType::UNIX: return "unix_domain_socket"; #ifdef __BIONIC__ case SocketType::VSOCK: return "vm_socket"; #endif // __BIONIC__ default: LOG_ALWAYS_FATAL("Unknown socket type"); return ""; } } class BinderRpc : public ::testing::TestWithParam<SocketType> { public: // This creates a new process serving an interface on a certain number of // threads. ProcessConnection createRpcTestSocketServerProcess( Loading @@ -275,12 +221,8 @@ public: const std::function<void(const sp<RpcServer>&, const sp<RpcConnection>&)>& configure) { CHECK_GT(numThreads, 0); SocketType socketType = GetParam(); std::string addr = allocateSocketAddress(); unlink(addr.c_str()); static unsigned int port = 3456; port++; auto ret = ProcessConnection{ .host = Process([&] { Loading @@ -290,19 +232,7 @@ public: // server supporting one client on one socket sp<RpcConnection> connection = server->addClientConnection(); switch (socketType) { case SocketType::UNIX: CHECK(connection->setupUnixDomainServer(addr.c_str())) << addr; break; #ifdef __BIONIC__ case SocketType::VSOCK: CHECK(connection->setupVsockServer(port)); break; #endif // __BIONIC__ default: LOG_ALWAYS_FATAL("Unknown socket type"); } configure(server, connection); Loading @@ -317,31 +247,49 @@ public: .connection = RpcConnection::make(), }; // wait up to 1s for sockets to be created constexpr useconds_t kMaxWaitUs = 1000000; constexpr useconds_t kWaitDivision = 100; for (size_t i = 0; i < kWaitDivision && 0 != access(addr.c_str(), F_OK); i++) { usleep(kMaxWaitUs / kWaitDivision); } // create remainder of connections for (size_t i = 0; i < numThreads; i++) { for (size_t tries = 0; tries < 5; tries++) { usleep(10000); switch (socketType) { case SocketType::UNIX: if (ret.connection->addUnixDomainClient(addr.c_str())) goto success; break; #ifdef __BIONIC__ case SocketType::VSOCK: if (ret.connection->addVsockClient(VMADDR_CID_LOCAL, port)) goto success; break; #endif // __BIONIC__ default: LOG_ALWAYS_FATAL("Unknown socket type"); } } LOG_ALWAYS_FATAL("Could not connect"); success:; // Connection refused sometimes after file created but before listening. CHECK(ret.connection->addUnixDomainClient(addr.c_str()) || (usleep(10000), ret.connection->addUnixDomainClient(addr.c_str()))) << i; } ret.rootBinder = ret.connection->getRootObject(); return ret; } // Process connection where the process hosts IBinderRpcTest, the server used // for most testing here struct BinderRpcTestProcessConnection { ProcessConnection proc; // pre-fetched root object sp<IBinder> rootBinder; // pre-casted root object sp<IBinderRpcTest> rootIface; ~BinderRpcTestProcessConnection() { if (!proc.expectInvalid) { int32_t remoteBinders = 0; EXPECT_OK(rootIface->countBinders(&remoteBinders)); // should only be the root binder object, iface EXPECT_EQ(remoteBinders, 1); } rootIface = nullptr; rootBinder = nullptr; } }; BinderRpcTestProcessConnection createRpcTestSocketServerProcess(size_t numThreads) { BinderRpcTestProcessConnection ret{ .proc = createRpcTestSocketServerProcess(numThreads, Loading @@ -360,9 +308,8 @@ public: return ret; } }; TEST_P(BinderRpc, RootObjectIsNull) { TEST(BinderRpc, RootObjectIsNull) { auto proc = createRpcTestSocketServerProcess(1, [](const sp<RpcServer>& server, const sp<RpcConnection>&) { Loading @@ -377,20 +324,20 @@ TEST_P(BinderRpc, RootObjectIsNull) { EXPECT_EQ(nullptr, proc.connection->getRootObject()); } TEST_P(BinderRpc, Ping) { TEST(BinderRpc, Ping) { auto proc = createRpcTestSocketServerProcess(1); ASSERT_NE(proc.rootBinder, nullptr); EXPECT_EQ(OK, proc.rootBinder->pingBinder()); } TEST_P(BinderRpc, TransactionsMustBeMarkedRpc) { TEST(BinderRpc, TransactionsMustBeMarkedRpc) { auto proc = createRpcTestSocketServerProcess(1); Parcel data; Parcel reply; EXPECT_EQ(BAD_TYPE, proc.rootBinder->transact(IBinder::PING_TRANSACTION, data, &reply, 0)); } TEST_P(BinderRpc, UnknownTransaction) { TEST(BinderRpc, UnknownTransaction) { auto proc = createRpcTestSocketServerProcess(1); Parcel data; data.markForBinder(proc.rootBinder); Loading @@ -398,19 +345,19 @@ TEST_P(BinderRpc, UnknownTransaction) { EXPECT_EQ(UNKNOWN_TRANSACTION, proc.rootBinder->transact(1337, data, &reply, 0)); } TEST_P(BinderRpc, SendSomethingOneway) { TEST(BinderRpc, SendSomethingOneway) { auto proc = createRpcTestSocketServerProcess(1); EXPECT_OK(proc.rootIface->sendString("asdf")); } TEST_P(BinderRpc, SendAndGetResultBack) { TEST(BinderRpc, SendAndGetResultBack) { auto proc = createRpcTestSocketServerProcess(1); std::string doubled; EXPECT_OK(proc.rootIface->doubleString("cool ", &doubled)); EXPECT_EQ("cool cool ", doubled); } TEST_P(BinderRpc, SendAndGetResultBackBig) { TEST(BinderRpc, SendAndGetResultBackBig) { auto proc = createRpcTestSocketServerProcess(1); std::string single = std::string(1024, 'a'); std::string doubled; Loading @@ -418,7 +365,7 @@ TEST_P(BinderRpc, SendAndGetResultBackBig) { EXPECT_EQ(single + single, doubled); } TEST_P(BinderRpc, CallMeBack) { TEST(BinderRpc, CallMeBack) { auto proc = createRpcTestSocketServerProcess(1); int32_t pingResult; Loading @@ -428,7 +375,7 @@ TEST_P(BinderRpc, CallMeBack) { EXPECT_EQ(0, MyBinderRpcSession::gNum); } TEST_P(BinderRpc, RepeatBinder) { TEST(BinderRpc, RepeatBinder) { auto proc = createRpcTestSocketServerProcess(1); sp<IBinder> inBinder = new MyBinderRpcSession("foo"); Loading @@ -450,7 +397,7 @@ TEST_P(BinderRpc, RepeatBinder) { EXPECT_EQ(0, MyBinderRpcSession::gNum); } TEST_P(BinderRpc, RepeatTheirBinder) { TEST(BinderRpc, RepeatTheirBinder) { auto proc = createRpcTestSocketServerProcess(1); sp<IBinderRpcSession> session; Loading @@ -474,7 +421,7 @@ TEST_P(BinderRpc, RepeatTheirBinder) { EXPECT_EQ(nullptr, weak.promote()); } TEST_P(BinderRpc, RepeatBinderNull) { TEST(BinderRpc, RepeatBinderNull) { auto proc = createRpcTestSocketServerProcess(1); sp<IBinder> outBinder; Loading @@ -482,7 +429,7 @@ TEST_P(BinderRpc, RepeatBinderNull) { EXPECT_EQ(nullptr, outBinder); } TEST_P(BinderRpc, HoldBinder) { TEST(BinderRpc, HoldBinder) { auto proc = createRpcTestSocketServerProcess(1); IBinder* ptr = nullptr; Loading @@ -508,7 +455,7 @@ TEST_P(BinderRpc, HoldBinder) { // These are behavioral differences form regular binder, where certain usecases // aren't supported. TEST_P(BinderRpc, CannotMixBindersBetweenUnrelatedSocketConnections) { TEST(BinderRpc, CannotMixBindersBetweenUnrelatedSocketConnections) { auto proc1 = createRpcTestSocketServerProcess(1); auto proc2 = createRpcTestSocketServerProcess(1); Loading @@ -517,7 +464,7 @@ TEST_P(BinderRpc, CannotMixBindersBetweenUnrelatedSocketConnections) { proc1.rootIface->repeatBinder(proc2.rootBinder, &outBinder).transactionError()); } TEST_P(BinderRpc, CannotSendRegularBinderOverSocketBinder) { TEST(BinderRpc, CannotSendRegularBinderOverSocketBinder) { auto proc = createRpcTestSocketServerProcess(1); sp<IBinder> someRealBinder = IInterface::asBinder(defaultServiceManager()); Loading @@ -526,7 +473,7 @@ TEST_P(BinderRpc, CannotSendRegularBinderOverSocketBinder) { proc.rootIface->repeatBinder(someRealBinder, &outBinder).transactionError()); } TEST_P(BinderRpc, CannotSendSocketBinderOverRegularBinder) { TEST(BinderRpc, CannotSendSocketBinderOverRegularBinder) { auto proc = createRpcTestSocketServerProcess(1); // for historical reasons, IServiceManager interface only returns the Loading @@ -537,7 +484,7 @@ TEST_P(BinderRpc, CannotSendSocketBinderOverRegularBinder) { // END TESTS FOR LIMITATIONS OF SOCKET BINDER TEST_P(BinderRpc, RepeatRootObject) { TEST(BinderRpc, RepeatRootObject) { auto proc = createRpcTestSocketServerProcess(1); sp<IBinder> outBinder; Loading @@ -545,7 +492,7 @@ TEST_P(BinderRpc, RepeatRootObject) { EXPECT_EQ(proc.rootBinder, outBinder); } TEST_P(BinderRpc, NestedTransactions) { TEST(BinderRpc, NestedTransactions) { auto proc = createRpcTestSocketServerProcess(1); auto nastyNester = sp<MyBinderRpcTest>::make(); Loading @@ -556,7 +503,7 @@ TEST_P(BinderRpc, NestedTransactions) { EXPECT_EQ(nullptr, weak.promote()); } TEST_P(BinderRpc, SameBinderEquality) { TEST(BinderRpc, SameBinderEquality) { auto proc = createRpcTestSocketServerProcess(1); sp<IBinder> a; Loading @@ -568,7 +515,7 @@ TEST_P(BinderRpc, SameBinderEquality) { EXPECT_EQ(a, b); } TEST_P(BinderRpc, SameBinderEqualityWeak) { TEST(BinderRpc, SameBinderEqualityWeak) { auto proc = createRpcTestSocketServerProcess(1); sp<IBinder> a; Loading Loading @@ -600,7 +547,7 @@ TEST_P(BinderRpc, SameBinderEqualityWeak) { EXPECT_EQ(expected, session); \ } while (false) TEST_P(BinderRpc, SingleSession) { TEST(BinderRpc, SingleSession) { auto proc = createRpcTestSocketServerProcess(1); sp<IBinderRpcSession> session; Loading @@ -614,7 +561,7 @@ TEST_P(BinderRpc, SingleSession) { expectSessions(0, proc.rootIface); } TEST_P(BinderRpc, ManySessions) { TEST(BinderRpc, ManySessions) { auto proc = createRpcTestSocketServerProcess(1); std::vector<sp<IBinderRpcSession>> sessions; Loading Loading @@ -648,7 +595,7 @@ size_t epochMillis() { return duration_cast<milliseconds>(system_clock::now().time_since_epoch()).count(); } TEST_P(BinderRpc, ThreadPoolGreaterThanEqualRequested) { TEST(BinderRpc, ThreadPoolGreaterThanEqualRequested) { constexpr size_t kNumThreads = 10; auto proc = createRpcTestSocketServerProcess(kNumThreads); Loading Loading @@ -680,7 +627,7 @@ TEST_P(BinderRpc, ThreadPoolGreaterThanEqualRequested) { for (auto& t : ts) t.join(); } TEST_P(BinderRpc, ThreadPoolOverSaturated) { TEST(BinderRpc, ThreadPoolOverSaturated) { constexpr size_t kNumThreads = 10; constexpr size_t kNumCalls = kNumThreads + 3; constexpr size_t kSleepMs = 500; Loading @@ -704,7 +651,7 @@ TEST_P(BinderRpc, ThreadPoolOverSaturated) { EXPECT_LE(epochMsAfter, epochMsBefore + 3 * kSleepMs); } TEST_P(BinderRpc, ThreadingStressTest) { TEST(BinderRpc, ThreadingStressTest) { constexpr size_t kNumClientThreads = 10; constexpr size_t kNumServerThreads = 10; constexpr size_t kNumCalls = 100; Loading @@ -725,7 +672,7 @@ TEST_P(BinderRpc, ThreadingStressTest) { for (auto& t : threads) t.join(); } TEST_P(BinderRpc, OnewayCallDoesNotWait) { TEST(BinderRpc, OnewayCallDoesNotWait) { constexpr size_t kReallyLongTimeMs = 100; constexpr size_t kSleepMs = kReallyLongTimeMs * 5; Loading @@ -740,7 +687,7 @@ TEST_P(BinderRpc, OnewayCallDoesNotWait) { EXPECT_LT(epochMsAfter, epochMsBefore + kReallyLongTimeMs); } TEST_P(BinderRpc, OnewayCallQueueing) { TEST(BinderRpc, OnewayCallQueueing) { constexpr size_t kNumSleeps = 10; constexpr size_t kNumExtraServerThreads = 4; constexpr size_t kSleepMs = 50; Loading @@ -764,7 +711,7 @@ TEST_P(BinderRpc, OnewayCallQueueing) { EXPECT_GT(epochMsAfter, epochMsBefore + kSleepMs * kNumSleeps); } TEST_P(BinderRpc, Die) { TEST(BinderRpc, Die) { // TODO(b/183141167): handle this in library signal(SIGPIPE, SIG_IGN); Loading Loading @@ -796,7 +743,7 @@ ssize_t countFds() { return ret; } TEST_P(BinderRpc, Fds) { TEST(BinderRpc, Fds) { ssize_t beforeFds = countFds(); ASSERT_GE(beforeFds, 0); { Loading @@ -806,19 +753,10 @@ TEST_P(BinderRpc, Fds) { ASSERT_EQ(beforeFds, countFds()) << (system("ls -l /proc/self/fd/"), "fd leak?"); } INSTANTIATE_TEST_CASE_P(PerSocket, BinderRpc, ::testing::Values(SocketType::UNIX #ifdef __BIONIC__ , SocketType::VSOCK #endif // __BIONIC__ ), PrintSocketType); } // namespace android int main(int argc, char** argv) { extern "C" int main(int argc, char** argv) { ::testing::InitGoogleTest(&argc, argv); android::base::InitLogging(argv, android::base::StderrLogger, android::base::DefaultAborter); return RUN_ALL_TESTS(); } } // namespace android