132115b10SPawel Jakub Dawidek /*- 2*4d846d26SWarner Losh * SPDX-License-Identifier: BSD-2-Clause 31de7b4b8SPedro F. Giffuni * 432115b10SPawel Jakub Dawidek * Copyright (c) 2009-2010 The FreeBSD Foundation 532115b10SPawel Jakub Dawidek * 632115b10SPawel Jakub Dawidek * This software was developed by Pawel Jakub Dawidek under sponsorship from 732115b10SPawel Jakub Dawidek * the FreeBSD Foundation. 832115b10SPawel Jakub Dawidek * 932115b10SPawel Jakub Dawidek * Redistribution and use in source and binary forms, with or without 1032115b10SPawel Jakub Dawidek * modification, are permitted provided that the following conditions 1132115b10SPawel Jakub Dawidek * are met: 1232115b10SPawel Jakub Dawidek * 1. Redistributions of source code must retain the above copyright 1332115b10SPawel Jakub Dawidek * notice, this list of conditions and the following disclaimer. 1432115b10SPawel Jakub Dawidek * 2. Redistributions in binary form must reproduce the above copyright 1532115b10SPawel Jakub Dawidek * notice, this list of conditions and the following disclaimer in the 1632115b10SPawel Jakub Dawidek * documentation and/or other materials provided with the distribution. 1732115b10SPawel Jakub Dawidek * 1832115b10SPawel Jakub Dawidek * THIS SOFTWARE IS PROVIDED BY THE AUTHORS AND CONTRIBUTORS ``AS IS'' AND 1932115b10SPawel Jakub Dawidek * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 2032115b10SPawel Jakub Dawidek * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 2132115b10SPawel Jakub Dawidek * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHORS OR CONTRIBUTORS BE LIABLE 2232115b10SPawel Jakub Dawidek * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 2332115b10SPawel Jakub Dawidek * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 2432115b10SPawel Jakub Dawidek * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 2532115b10SPawel Jakub Dawidek * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 2632115b10SPawel Jakub Dawidek * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 2732115b10SPawel Jakub Dawidek * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 2832115b10SPawel Jakub Dawidek * SUCH DAMAGE. 2932115b10SPawel Jakub Dawidek */ 3032115b10SPawel Jakub Dawidek 3132115b10SPawel Jakub Dawidek #include <sys/cdefs.h> 3232115b10SPawel Jakub Dawidek /* UDS - UNIX Domain Socket */ 3332115b10SPawel Jakub Dawidek 340d8d3721SPawel Jakub Dawidek #include <sys/types.h> 35e2eabb44SPawel Jakub Dawidek #include <sys/socket.h> 3632115b10SPawel Jakub Dawidek #include <sys/un.h> 3732115b10SPawel Jakub Dawidek 3832115b10SPawel Jakub Dawidek #include <errno.h> 3932115b10SPawel Jakub Dawidek #include <stdbool.h> 4032115b10SPawel Jakub Dawidek #include <stdint.h> 4132115b10SPawel Jakub Dawidek #include <stdio.h> 4232115b10SPawel Jakub Dawidek #include <string.h> 4332115b10SPawel Jakub Dawidek #include <unistd.h> 4432115b10SPawel Jakub Dawidek 452c5dadc9SPawel Jakub Dawidek #include "pjdlog.h" 4632115b10SPawel Jakub Dawidek #include "proto_impl.h" 4732115b10SPawel Jakub Dawidek 4832115b10SPawel Jakub Dawidek #define UDS_CTX_MAGIC 0xd541c 4932115b10SPawel Jakub Dawidek struct uds_ctx { 5032115b10SPawel Jakub Dawidek int uc_magic; 5132115b10SPawel Jakub Dawidek struct sockaddr_un uc_sun; 5232115b10SPawel Jakub Dawidek int uc_fd; 5332115b10SPawel Jakub Dawidek int uc_side; 5432115b10SPawel Jakub Dawidek #define UDS_SIDE_CLIENT 0 5532115b10SPawel Jakub Dawidek #define UDS_SIDE_SERVER_LISTEN 1 5632115b10SPawel Jakub Dawidek #define UDS_SIDE_SERVER_WORK 2 57f431ab18SPawel Jakub Dawidek pid_t uc_owner; 5832115b10SPawel Jakub Dawidek }; 5932115b10SPawel Jakub Dawidek 6032115b10SPawel Jakub Dawidek static void uds_close(void *ctx); 6132115b10SPawel Jakub Dawidek 6232115b10SPawel Jakub Dawidek static int 6332115b10SPawel Jakub Dawidek uds_addr(const char *addr, struct sockaddr_un *sunp) 6432115b10SPawel Jakub Dawidek { 6532115b10SPawel Jakub Dawidek 6632115b10SPawel Jakub Dawidek if (addr == NULL) 6732115b10SPawel Jakub Dawidek return (-1); 6832115b10SPawel Jakub Dawidek 6932115b10SPawel Jakub Dawidek if (strncasecmp(addr, "uds://", 6) == 0) 7032115b10SPawel Jakub Dawidek addr += 6; 7132115b10SPawel Jakub Dawidek else if (strncasecmp(addr, "unix://", 7) == 0) 7232115b10SPawel Jakub Dawidek addr += 7; 7332115b10SPawel Jakub Dawidek else if (addr[0] == '/' && /* If it starts from /... */ 7432115b10SPawel Jakub Dawidek strstr(addr, "://") == NULL)/* ...and there is no prefix... */ 7532115b10SPawel Jakub Dawidek ; /* ...we assume its us. */ 7632115b10SPawel Jakub Dawidek else 7732115b10SPawel Jakub Dawidek return (-1); 7832115b10SPawel Jakub Dawidek 7932115b10SPawel Jakub Dawidek sunp->sun_family = AF_UNIX; 8032115b10SPawel Jakub Dawidek if (strlcpy(sunp->sun_path, addr, sizeof(sunp->sun_path)) >= 8132115b10SPawel Jakub Dawidek sizeof(sunp->sun_path)) { 8232115b10SPawel Jakub Dawidek return (ENAMETOOLONG); 8332115b10SPawel Jakub Dawidek } 8432115b10SPawel Jakub Dawidek sunp->sun_len = SUN_LEN(sunp); 8532115b10SPawel Jakub Dawidek 8632115b10SPawel Jakub Dawidek return (0); 8732115b10SPawel Jakub Dawidek } 8832115b10SPawel Jakub Dawidek 8932115b10SPawel Jakub Dawidek static int 9032115b10SPawel Jakub Dawidek uds_common_setup(const char *addr, void **ctxp, int side) 9132115b10SPawel Jakub Dawidek { 9232115b10SPawel Jakub Dawidek struct uds_ctx *uctx; 9332115b10SPawel Jakub Dawidek int ret; 9432115b10SPawel Jakub Dawidek 9532115b10SPawel Jakub Dawidek uctx = malloc(sizeof(*uctx)); 9632115b10SPawel Jakub Dawidek if (uctx == NULL) 9732115b10SPawel Jakub Dawidek return (errno); 9832115b10SPawel Jakub Dawidek 9932115b10SPawel Jakub Dawidek /* Parse given address. */ 10032115b10SPawel Jakub Dawidek if ((ret = uds_addr(addr, &uctx->uc_sun)) != 0) { 10132115b10SPawel Jakub Dawidek free(uctx); 10232115b10SPawel Jakub Dawidek return (ret); 10332115b10SPawel Jakub Dawidek } 10432115b10SPawel Jakub Dawidek 10532115b10SPawel Jakub Dawidek uctx->uc_fd = socket(AF_UNIX, SOCK_STREAM, 0); 10632115b10SPawel Jakub Dawidek if (uctx->uc_fd == -1) { 10732115b10SPawel Jakub Dawidek ret = errno; 10832115b10SPawel Jakub Dawidek free(uctx); 10932115b10SPawel Jakub Dawidek return (ret); 11032115b10SPawel Jakub Dawidek } 11132115b10SPawel Jakub Dawidek 11232115b10SPawel Jakub Dawidek uctx->uc_side = side; 113f431ab18SPawel Jakub Dawidek uctx->uc_owner = 0; 11432115b10SPawel Jakub Dawidek uctx->uc_magic = UDS_CTX_MAGIC; 11532115b10SPawel Jakub Dawidek *ctxp = uctx; 11632115b10SPawel Jakub Dawidek 11732115b10SPawel Jakub Dawidek return (0); 11832115b10SPawel Jakub Dawidek } 11932115b10SPawel Jakub Dawidek 12032115b10SPawel Jakub Dawidek static int 1210b626a28SPawel Jakub Dawidek uds_client(const char *srcaddr, const char *dstaddr, void **ctxp) 12232115b10SPawel Jakub Dawidek { 1230b626a28SPawel Jakub Dawidek int ret; 12432115b10SPawel Jakub Dawidek 1250b626a28SPawel Jakub Dawidek ret = uds_common_setup(dstaddr, ctxp, UDS_SIDE_CLIENT); 1260b626a28SPawel Jakub Dawidek if (ret != 0) 1270b626a28SPawel Jakub Dawidek return (ret); 1280b626a28SPawel Jakub Dawidek 1290b626a28SPawel Jakub Dawidek PJDLOG_ASSERT(srcaddr == NULL); 1300b626a28SPawel Jakub Dawidek 1310b626a28SPawel Jakub Dawidek return (0); 13232115b10SPawel Jakub Dawidek } 13332115b10SPawel Jakub Dawidek 13432115b10SPawel Jakub Dawidek static int 1359d70b24bSPawel Jakub Dawidek uds_connect(void *ctx, int timeout) 13632115b10SPawel Jakub Dawidek { 13732115b10SPawel Jakub Dawidek struct uds_ctx *uctx = ctx; 13832115b10SPawel Jakub Dawidek 1392ec483c5SPawel Jakub Dawidek PJDLOG_ASSERT(uctx != NULL); 1402ec483c5SPawel Jakub Dawidek PJDLOG_ASSERT(uctx->uc_magic == UDS_CTX_MAGIC); 1412ec483c5SPawel Jakub Dawidek PJDLOG_ASSERT(uctx->uc_side == UDS_SIDE_CLIENT); 1422ec483c5SPawel Jakub Dawidek PJDLOG_ASSERT(uctx->uc_fd >= 0); 1431c193322SPawel Jakub Dawidek PJDLOG_ASSERT(timeout >= -1); 14432115b10SPawel Jakub Dawidek 14532115b10SPawel Jakub Dawidek if (connect(uctx->uc_fd, (struct sockaddr *)&uctx->uc_sun, 1462b1b224dSPawel Jakub Dawidek sizeof(uctx->uc_sun)) == -1) { 14732115b10SPawel Jakub Dawidek return (errno); 14832115b10SPawel Jakub Dawidek } 14932115b10SPawel Jakub Dawidek 15032115b10SPawel Jakub Dawidek return (0); 15132115b10SPawel Jakub Dawidek } 15232115b10SPawel Jakub Dawidek 15332115b10SPawel Jakub Dawidek static int 1541c193322SPawel Jakub Dawidek uds_connect_wait(void *ctx, int timeout) 1551c193322SPawel Jakub Dawidek { 1561c193322SPawel Jakub Dawidek struct uds_ctx *uctx = ctx; 1571c193322SPawel Jakub Dawidek 1581c193322SPawel Jakub Dawidek PJDLOG_ASSERT(uctx != NULL); 1591c193322SPawel Jakub Dawidek PJDLOG_ASSERT(uctx->uc_magic == UDS_CTX_MAGIC); 1601c193322SPawel Jakub Dawidek PJDLOG_ASSERT(uctx->uc_side == UDS_SIDE_CLIENT); 1611c193322SPawel Jakub Dawidek PJDLOG_ASSERT(uctx->uc_fd >= 0); 1621c193322SPawel Jakub Dawidek PJDLOG_ASSERT(timeout >= 0); 1631c193322SPawel Jakub Dawidek 1641c193322SPawel Jakub Dawidek return (0); 1651c193322SPawel Jakub Dawidek } 1661c193322SPawel Jakub Dawidek 1671c193322SPawel Jakub Dawidek static int 16832115b10SPawel Jakub Dawidek uds_server(const char *addr, void **ctxp) 16932115b10SPawel Jakub Dawidek { 17032115b10SPawel Jakub Dawidek struct uds_ctx *uctx; 17132115b10SPawel Jakub Dawidek int ret; 17232115b10SPawel Jakub Dawidek 17332115b10SPawel Jakub Dawidek ret = uds_common_setup(addr, ctxp, UDS_SIDE_SERVER_LISTEN); 17432115b10SPawel Jakub Dawidek if (ret != 0) 17532115b10SPawel Jakub Dawidek return (ret); 17632115b10SPawel Jakub Dawidek 17732115b10SPawel Jakub Dawidek uctx = *ctxp; 17832115b10SPawel Jakub Dawidek 179f431ab18SPawel Jakub Dawidek (void)unlink(uctx->uc_sun.sun_path); 18032115b10SPawel Jakub Dawidek if (bind(uctx->uc_fd, (struct sockaddr *)&uctx->uc_sun, 1812b1b224dSPawel Jakub Dawidek sizeof(uctx->uc_sun)) == -1) { 18232115b10SPawel Jakub Dawidek ret = errno; 18332115b10SPawel Jakub Dawidek uds_close(uctx); 18432115b10SPawel Jakub Dawidek return (ret); 18532115b10SPawel Jakub Dawidek } 186f431ab18SPawel Jakub Dawidek uctx->uc_owner = getpid(); 1872b1b224dSPawel Jakub Dawidek if (listen(uctx->uc_fd, 8) == -1) { 18832115b10SPawel Jakub Dawidek ret = errno; 18932115b10SPawel Jakub Dawidek uds_close(uctx); 19032115b10SPawel Jakub Dawidek return (ret); 19132115b10SPawel Jakub Dawidek } 19232115b10SPawel Jakub Dawidek 19332115b10SPawel Jakub Dawidek return (0); 19432115b10SPawel Jakub Dawidek } 19532115b10SPawel Jakub Dawidek 19632115b10SPawel Jakub Dawidek static int 19732115b10SPawel Jakub Dawidek uds_accept(void *ctx, void **newctxp) 19832115b10SPawel Jakub Dawidek { 19932115b10SPawel Jakub Dawidek struct uds_ctx *uctx = ctx; 20032115b10SPawel Jakub Dawidek struct uds_ctx *newuctx; 20132115b10SPawel Jakub Dawidek socklen_t fromlen; 20232115b10SPawel Jakub Dawidek int ret; 20332115b10SPawel Jakub Dawidek 2042ec483c5SPawel Jakub Dawidek PJDLOG_ASSERT(uctx != NULL); 2052ec483c5SPawel Jakub Dawidek PJDLOG_ASSERT(uctx->uc_magic == UDS_CTX_MAGIC); 2062ec483c5SPawel Jakub Dawidek PJDLOG_ASSERT(uctx->uc_side == UDS_SIDE_SERVER_LISTEN); 2072ec483c5SPawel Jakub Dawidek PJDLOG_ASSERT(uctx->uc_fd >= 0); 20832115b10SPawel Jakub Dawidek 20932115b10SPawel Jakub Dawidek newuctx = malloc(sizeof(*newuctx)); 21032115b10SPawel Jakub Dawidek if (newuctx == NULL) 21132115b10SPawel Jakub Dawidek return (errno); 21232115b10SPawel Jakub Dawidek 213f431ab18SPawel Jakub Dawidek fromlen = sizeof(newuctx->uc_sun); 214f431ab18SPawel Jakub Dawidek newuctx->uc_fd = accept(uctx->uc_fd, 215f431ab18SPawel Jakub Dawidek (struct sockaddr *)&newuctx->uc_sun, &fromlen); 2162b1b224dSPawel Jakub Dawidek if (newuctx->uc_fd == -1) { 21732115b10SPawel Jakub Dawidek ret = errno; 21832115b10SPawel Jakub Dawidek free(newuctx); 21932115b10SPawel Jakub Dawidek return (ret); 22032115b10SPawel Jakub Dawidek } 22132115b10SPawel Jakub Dawidek 22232115b10SPawel Jakub Dawidek newuctx->uc_side = UDS_SIDE_SERVER_WORK; 22332115b10SPawel Jakub Dawidek newuctx->uc_magic = UDS_CTX_MAGIC; 22432115b10SPawel Jakub Dawidek *newctxp = newuctx; 22532115b10SPawel Jakub Dawidek 22632115b10SPawel Jakub Dawidek return (0); 22732115b10SPawel Jakub Dawidek } 22832115b10SPawel Jakub Dawidek 22932115b10SPawel Jakub Dawidek static int 23001ab52c0SPawel Jakub Dawidek uds_send(void *ctx, const unsigned char *data, size_t size, int fd) 23132115b10SPawel Jakub Dawidek { 23232115b10SPawel Jakub Dawidek struct uds_ctx *uctx = ctx; 23332115b10SPawel Jakub Dawidek 2342ec483c5SPawel Jakub Dawidek PJDLOG_ASSERT(uctx != NULL); 2352ec483c5SPawel Jakub Dawidek PJDLOG_ASSERT(uctx->uc_magic == UDS_CTX_MAGIC); 2362ec483c5SPawel Jakub Dawidek PJDLOG_ASSERT(uctx->uc_fd >= 0); 23732115b10SPawel Jakub Dawidek 23801ab52c0SPawel Jakub Dawidek return (proto_common_send(uctx->uc_fd, data, size, fd)); 23932115b10SPawel Jakub Dawidek } 24032115b10SPawel Jakub Dawidek 24132115b10SPawel Jakub Dawidek static int 24201ab52c0SPawel Jakub Dawidek uds_recv(void *ctx, unsigned char *data, size_t size, int *fdp) 24332115b10SPawel Jakub Dawidek { 24432115b10SPawel Jakub Dawidek struct uds_ctx *uctx = ctx; 24532115b10SPawel Jakub Dawidek 2462ec483c5SPawel Jakub Dawidek PJDLOG_ASSERT(uctx != NULL); 2472ec483c5SPawel Jakub Dawidek PJDLOG_ASSERT(uctx->uc_magic == UDS_CTX_MAGIC); 2482ec483c5SPawel Jakub Dawidek PJDLOG_ASSERT(uctx->uc_fd >= 0); 24932115b10SPawel Jakub Dawidek 25001ab52c0SPawel Jakub Dawidek return (proto_common_recv(uctx->uc_fd, data, size, fdp)); 2518046c499SPawel Jakub Dawidek } 2528046c499SPawel Jakub Dawidek 2538046c499SPawel Jakub Dawidek static int 25432115b10SPawel Jakub Dawidek uds_descriptor(const void *ctx) 25532115b10SPawel Jakub Dawidek { 25632115b10SPawel Jakub Dawidek const struct uds_ctx *uctx = ctx; 25732115b10SPawel Jakub Dawidek 2582ec483c5SPawel Jakub Dawidek PJDLOG_ASSERT(uctx != NULL); 2592ec483c5SPawel Jakub Dawidek PJDLOG_ASSERT(uctx->uc_magic == UDS_CTX_MAGIC); 26032115b10SPawel Jakub Dawidek 26132115b10SPawel Jakub Dawidek return (uctx->uc_fd); 26232115b10SPawel Jakub Dawidek } 26332115b10SPawel Jakub Dawidek 26432115b10SPawel Jakub Dawidek static void 26532115b10SPawel Jakub Dawidek uds_local_address(const void *ctx, char *addr, size_t size) 26632115b10SPawel Jakub Dawidek { 26732115b10SPawel Jakub Dawidek const struct uds_ctx *uctx = ctx; 26832115b10SPawel Jakub Dawidek struct sockaddr_un sun; 26932115b10SPawel Jakub Dawidek socklen_t sunlen; 27032115b10SPawel Jakub Dawidek 2712ec483c5SPawel Jakub Dawidek PJDLOG_ASSERT(uctx != NULL); 2722ec483c5SPawel Jakub Dawidek PJDLOG_ASSERT(uctx->uc_magic == UDS_CTX_MAGIC); 2732ec483c5SPawel Jakub Dawidek PJDLOG_ASSERT(addr != NULL); 27432115b10SPawel Jakub Dawidek 27532115b10SPawel Jakub Dawidek sunlen = sizeof(sun); 2762b1b224dSPawel Jakub Dawidek if (getsockname(uctx->uc_fd, (struct sockaddr *)&sun, &sunlen) == -1) { 2772c5dadc9SPawel Jakub Dawidek PJDLOG_VERIFY(strlcpy(addr, "N/A", size) < size); 27832115b10SPawel Jakub Dawidek return; 27932115b10SPawel Jakub Dawidek } 2802ec483c5SPawel Jakub Dawidek PJDLOG_ASSERT(sun.sun_family == AF_UNIX); 28132115b10SPawel Jakub Dawidek if (sun.sun_path[0] == '\0') { 2822c5dadc9SPawel Jakub Dawidek PJDLOG_VERIFY(strlcpy(addr, "N/A", size) < size); 28332115b10SPawel Jakub Dawidek return; 28432115b10SPawel Jakub Dawidek } 2852c5dadc9SPawel Jakub Dawidek PJDLOG_VERIFY(snprintf(addr, size, "uds://%s", sun.sun_path) < (ssize_t)size); 28632115b10SPawel Jakub Dawidek } 28732115b10SPawel Jakub Dawidek 28832115b10SPawel Jakub Dawidek static void 28932115b10SPawel Jakub Dawidek uds_remote_address(const void *ctx, char *addr, size_t size) 29032115b10SPawel Jakub Dawidek { 29132115b10SPawel Jakub Dawidek const struct uds_ctx *uctx = ctx; 29232115b10SPawel Jakub Dawidek struct sockaddr_un sun; 29332115b10SPawel Jakub Dawidek socklen_t sunlen; 29432115b10SPawel Jakub Dawidek 2952ec483c5SPawel Jakub Dawidek PJDLOG_ASSERT(uctx != NULL); 2962ec483c5SPawel Jakub Dawidek PJDLOG_ASSERT(uctx->uc_magic == UDS_CTX_MAGIC); 2972ec483c5SPawel Jakub Dawidek PJDLOG_ASSERT(addr != NULL); 29832115b10SPawel Jakub Dawidek 29932115b10SPawel Jakub Dawidek sunlen = sizeof(sun); 3002b1b224dSPawel Jakub Dawidek if (getpeername(uctx->uc_fd, (struct sockaddr *)&sun, &sunlen) == -1) { 3012c5dadc9SPawel Jakub Dawidek PJDLOG_VERIFY(strlcpy(addr, "N/A", size) < size); 30232115b10SPawel Jakub Dawidek return; 30332115b10SPawel Jakub Dawidek } 3042ec483c5SPawel Jakub Dawidek PJDLOG_ASSERT(sun.sun_family == AF_UNIX); 30532115b10SPawel Jakub Dawidek if (sun.sun_path[0] == '\0') { 3062c5dadc9SPawel Jakub Dawidek PJDLOG_VERIFY(strlcpy(addr, "N/A", size) < size); 30732115b10SPawel Jakub Dawidek return; 30832115b10SPawel Jakub Dawidek } 30932115b10SPawel Jakub Dawidek snprintf(addr, size, "uds://%s", sun.sun_path); 31032115b10SPawel Jakub Dawidek } 31132115b10SPawel Jakub Dawidek 31232115b10SPawel Jakub Dawidek static void 31332115b10SPawel Jakub Dawidek uds_close(void *ctx) 31432115b10SPawel Jakub Dawidek { 31532115b10SPawel Jakub Dawidek struct uds_ctx *uctx = ctx; 31632115b10SPawel Jakub Dawidek 3172ec483c5SPawel Jakub Dawidek PJDLOG_ASSERT(uctx != NULL); 3182ec483c5SPawel Jakub Dawidek PJDLOG_ASSERT(uctx->uc_magic == UDS_CTX_MAGIC); 31932115b10SPawel Jakub Dawidek 32032115b10SPawel Jakub Dawidek if (uctx->uc_fd >= 0) 32132115b10SPawel Jakub Dawidek close(uctx->uc_fd); 322f431ab18SPawel Jakub Dawidek /* 323f431ab18SPawel Jakub Dawidek * Unlink the socket only if we are the owner and this is descriptor 324f431ab18SPawel Jakub Dawidek * we listen on. 325f431ab18SPawel Jakub Dawidek */ 326f431ab18SPawel Jakub Dawidek if (uctx->uc_side == UDS_SIDE_SERVER_LISTEN && 327f431ab18SPawel Jakub Dawidek uctx->uc_owner == getpid()) { 328493812eeSPawel Jakub Dawidek PJDLOG_ASSERT(uctx->uc_sun.sun_path[0] != '\0'); 329493812eeSPawel Jakub Dawidek if (unlink(uctx->uc_sun.sun_path) == -1) { 330493812eeSPawel Jakub Dawidek pjdlog_errno(LOG_WARNING, 331493812eeSPawel Jakub Dawidek "Unable to unlink socket file %s", 332493812eeSPawel Jakub Dawidek uctx->uc_sun.sun_path); 333493812eeSPawel Jakub Dawidek } 334f431ab18SPawel Jakub Dawidek } 335f431ab18SPawel Jakub Dawidek uctx->uc_owner = 0; 33632115b10SPawel Jakub Dawidek uctx->uc_magic = 0; 33732115b10SPawel Jakub Dawidek free(uctx); 33832115b10SPawel Jakub Dawidek } 33932115b10SPawel Jakub Dawidek 340e2eabb44SPawel Jakub Dawidek static struct proto uds_proto = { 341e2eabb44SPawel Jakub Dawidek .prt_name = "uds", 342e2eabb44SPawel Jakub Dawidek .prt_client = uds_client, 343e2eabb44SPawel Jakub Dawidek .prt_connect = uds_connect, 344e2eabb44SPawel Jakub Dawidek .prt_connect_wait = uds_connect_wait, 345e2eabb44SPawel Jakub Dawidek .prt_server = uds_server, 346e2eabb44SPawel Jakub Dawidek .prt_accept = uds_accept, 347e2eabb44SPawel Jakub Dawidek .prt_send = uds_send, 348e2eabb44SPawel Jakub Dawidek .prt_recv = uds_recv, 349e2eabb44SPawel Jakub Dawidek .prt_descriptor = uds_descriptor, 350e2eabb44SPawel Jakub Dawidek .prt_local_address = uds_local_address, 351e2eabb44SPawel Jakub Dawidek .prt_remote_address = uds_remote_address, 352e2eabb44SPawel Jakub Dawidek .prt_close = uds_close 35332115b10SPawel Jakub Dawidek }; 35432115b10SPawel Jakub Dawidek 35532115b10SPawel Jakub Dawidek static __constructor void 35632115b10SPawel Jakub Dawidek uds_ctor(void) 35732115b10SPawel Jakub Dawidek { 35832115b10SPawel Jakub Dawidek 35950692f84SPawel Jakub Dawidek proto_register(&uds_proto, false); 36032115b10SPawel Jakub Dawidek } 361