summaryrefslogtreecommitdiff
path: root/libs/binder/RpcSession.cpp
diff options
context:
space:
mode:
author David Brazdil <dbrazdil@google.com> 2022-09-23 12:25:18 +0100
committer David Brazdil <dbrazdil@google.com> 2022-10-07 11:24:45 +0100
commit21c887c5a09040bf41d272a9e729119956e48a3f (patch)
tree3eb1e98a6aacd9b8134172f5decc9520d456d2b9 /libs/binder/RpcSession.cpp
parentcd8e35be036417c14c270a2ebc94e968d930c478 (diff)
RpcBinder: Add AF_UNIX socketpair transport
Add support for running RpcBinder over unnamed Unix domain sockets created by socketpair(). This is useful e.g. between parent/child processes. The implementation uses the initial socket pair only to create more socket pairs for individual connections. This creates a natural mapping to syscalls used on sockets bound to an address: socket() socketpair() bind() n/a (preconnected) connect() sendmsg() listen() recvmsg() Bug: 250685929 Test: atest binderRpcTest Change-Id: Id4ff3946ddcfefe3592eb1149c61582f7369aa29
Diffstat (limited to 'libs/binder/RpcSession.cpp')
-rw-r--r--libs/binder/RpcSession.cpp29
1 files changed, 29 insertions, 0 deletions
diff --git a/libs/binder/RpcSession.cpp b/libs/binder/RpcSession.cpp
index 49843e5953..ff50c16102 100644
--- a/libs/binder/RpcSession.cpp
+++ b/libs/binder/RpcSession.cpp
@@ -41,6 +41,7 @@
#include "OS.h"
#include "RpcSocketAddress.h"
#include "RpcState.h"
+#include "RpcTransportUtils.h"
#include "RpcWireFormat.h"
#include "Utils.h"
@@ -147,6 +148,34 @@ status_t RpcSession::setupUnixDomainClient(const char* path) {
return setupSocketClient(UnixSocketAddress(path));
}
+status_t RpcSession::setupUnixDomainSocketBootstrapClient(unique_fd bootstrapFd) {
+ mBootstrapTransport =
+ mCtx->newTransport(RpcTransportFd(std::move(bootstrapFd)), mShutdownTrigger.get());
+ return setupClient([&](const std::vector<uint8_t>& sessionId, bool incoming) {
+ int socks[2];
+ if (socketpair(AF_UNIX, SOCK_STREAM | SOCK_CLOEXEC | SOCK_NONBLOCK, 0, socks) < 0) {
+ int savedErrno = errno;
+ ALOGE("Failed socketpair: %s", strerror(savedErrno));
+ return -savedErrno;
+ }
+ unique_fd clientFd(socks[0]), serverFd(socks[1]);
+
+ int zero = 0;
+ iovec iov{&zero, sizeof(zero)};
+ std::vector<std::variant<base::unique_fd, base::borrowed_fd>> fds;
+ fds.push_back(std::move(serverFd));
+
+ status_t status = mBootstrapTransport->interruptableWriteFully(mShutdownTrigger.get(), &iov,
+ 1, std::nullopt, &fds);
+ if (status != OK) {
+ ALOGE("Failed to send fd over bootstrap transport: %s", strerror(-status));
+ return status;
+ }
+
+ return initAndAddConnection(RpcTransportFd(std::move(clientFd)), sessionId, incoming);
+ });
+}
+
status_t RpcSession::setupVsockClient(unsigned int cid, unsigned int port) {
return setupSocketClient(VsockSocketAddress(cid, port));
}