aboutsummaryrefslogtreecommitdiffhomepage
path: root/src/core
diff options
context:
space:
mode:
authorGravatar Craig Tiller <craig.tiller@gmail.com>2015-02-13 23:16:32 -0800
committerGravatar Craig Tiller <craig.tiller@gmail.com>2015-02-13 23:16:32 -0800
commitae7fe92389d51e7eb22d6a167a2f16ad61acd50a (patch)
treeb799a5a56f78afe556d21773b1e898b424b863a7 /src/core
parentbb62706f8428357d3f96d6de9e65c8fc6b439b9c (diff)
Unix domain socket support
Diffstat (limited to 'src/core')
-rw-r--r--src/core/iomgr/resolve_address.c13
-rw-r--r--src/core/iomgr/sockaddr_utils.c2
-rw-r--r--src/core/iomgr/tcp_client_posix.c6
-rw-r--r--src/core/iomgr/tcp_server_posix.c13
4 files changed, 29 insertions, 5 deletions
diff --git a/src/core/iomgr/resolve_address.c b/src/core/iomgr/resolve_address.c
index 575f884d91..58daade03c 100644
--- a/src/core/iomgr/resolve_address.c
+++ b/src/core/iomgr/resolve_address.c
@@ -39,6 +39,7 @@
#include "src/core/iomgr/resolve_address.h"
#include <sys/types.h>
+#include <sys/un.h>
#include <string.h>
#include "src/core/iomgr/iomgr_internal.h"
@@ -123,6 +124,18 @@ grpc_resolved_addresses *grpc_blocking_resolve_address(
size_t i;
grpc_resolved_addresses *addrs = NULL;
const gpr_timespec start_time = gpr_now();
+ struct sockaddr_un *un;
+
+ if (name[0] == 'u' && name[1] == 'n' && name[2] == 'i' && name[3] == 'x' && name[4] == ':' && name[5] != 0) {
+ addrs = gpr_malloc(sizeof(grpc_resolved_addresses));
+ addrs->naddrs = 1;
+ addrs->addrs = gpr_malloc(sizeof(grpc_resolved_address));
+ un = (struct sockaddr_un *)addrs->addrs->addr;
+ un->sun_family = AF_UNIX;
+ strcpy(un->sun_path, name + 5);
+ addrs->addrs->len = strlen(un->sun_path) + sizeof(un->sun_family);
+ return addrs;
+ }
/* parse name, splitting it into host and port parts */
split_host_port(name, &host, &port);
diff --git a/src/core/iomgr/sockaddr_utils.c b/src/core/iomgr/sockaddr_utils.c
index 8dcfca74c6..f794241776 100644
--- a/src/core/iomgr/sockaddr_utils.c
+++ b/src/core/iomgr/sockaddr_utils.c
@@ -166,6 +166,8 @@ int grpc_sockaddr_get_port(const struct sockaddr *addr) {
return ntohs(((struct sockaddr_in *)addr)->sin_port);
case AF_INET6:
return ntohs(((struct sockaddr_in6 *)addr)->sin6_port);
+ case AF_UNIX:
+ return 1;
default:
gpr_log(GPR_ERROR, "Unknown socket family %d in %s", addr->sa_family,
__FUNCTION__);
diff --git a/src/core/iomgr/tcp_client_posix.c b/src/core/iomgr/tcp_client_posix.c
index 851530ce68..397dff5a5d 100644
--- a/src/core/iomgr/tcp_client_posix.c
+++ b/src/core/iomgr/tcp_client_posix.c
@@ -62,13 +62,13 @@ typedef struct {
int refs;
} async_connect;
-static int prepare_socket(int fd) {
+static int prepare_socket(const struct sockaddr* addr, int fd) {
if (fd < 0) {
goto error;
}
if (!grpc_set_socket_nonblocking(fd, 1) || !grpc_set_socket_cloexec(fd, 1) ||
- !grpc_set_socket_low_latency(fd, 1)) {
+ (addr->sa_family != AF_UNIX && !grpc_set_socket_low_latency(fd, 1))) {
gpr_log(GPR_ERROR, "Unable to configure socket %d: %s", fd,
strerror(errno));
goto error;
@@ -200,7 +200,7 @@ void grpc_tcp_client_connect(void (*cb)(void *arg, grpc_endpoint *ep),
addr = (struct sockaddr *)&addr4_copy;
addr_len = sizeof(addr4_copy);
}
- if (!prepare_socket(fd)) {
+ if (!prepare_socket(addr, fd)) {
cb(arg, NULL);
return;
}
diff --git a/src/core/iomgr/tcp_server_posix.c b/src/core/iomgr/tcp_server_posix.c
index 091f0aab1a..b69dbd923b 100644
--- a/src/core/iomgr/tcp_server_posix.c
+++ b/src/core/iomgr/tcp_server_posix.c
@@ -48,12 +48,14 @@
#include <netinet/tcp.h>
#include <stdio.h>
#include <sys/types.h>
+#include <sys/un.h>
#include <sys/socket.h>
#include <unistd.h>
#include <string.h>
#include <errno.h>
#include "src/core/iomgr/pollset_posix.h"
+#include "src/core/iomgr/resolve_address.h"
#include "src/core/iomgr/sockaddr_utils.h"
#include "src/core/iomgr/socket_utils_posix.h"
#include "src/core/iomgr/tcp_posix.h"
@@ -73,6 +75,8 @@ typedef struct {
int fd;
grpc_fd *emfd;
grpc_tcp_server *server;
+ gpr_uint8 addr[GRPC_MAX_SOCKADDR_SIZE];
+ int addr_len;
} server_port;
/* the overall server */
@@ -121,6 +125,10 @@ void grpc_tcp_server_destroy(grpc_tcp_server *s) {
/* delete ALL the things */
for (i = 0; i < s->nports; i++) {
server_port *sp = &s->ports[i];
+ if (((struct sockaddr *)sp->addr)->sa_family == AF_UNIX) {
+ struct sockaddr_un *un = (struct sockaddr_un *)sp->addr;
+ unlink(un->sun_path);
+ }
grpc_fd_orphan(sp->emfd, NULL, NULL);
}
gpr_free(s->ports);
@@ -170,8 +178,7 @@ static int prepare_socket(int fd, const struct sockaddr *addr, int addr_len) {
}
if (!grpc_set_socket_nonblocking(fd, 1) || !grpc_set_socket_cloexec(fd, 1) ||
- !grpc_set_socket_low_latency(fd, 1) ||
- !grpc_set_socket_reuse_addr(fd, 1)) {
+ (addr->sa_family != AF_UNIX && (!grpc_set_socket_low_latency(fd, 1) || !grpc_set_socket_reuse_addr(fd, 1)))) {
gpr_log(GPR_ERROR, "Unable to configure socket %d: %s", fd,
strerror(errno));
goto error;
@@ -265,6 +272,8 @@ static int add_socket_to_server(grpc_tcp_server *s, int fd,
sp->server = s;
sp->fd = fd;
sp->emfd = grpc_fd_create(fd);
+ memcpy(sp->addr, addr, addr_len);
+ sp->addr_len = addr_len;
GPR_ASSERT(sp->emfd);
gpr_mu_unlock(&s->mu);
}