From 7acefbbcbeab725420ea07397ae35992f505f702 Mon Sep 17 00:00:00 2001 From: Damien Miller Date: Fri, 18 Jul 2014 14:11:24 +1000 Subject: - millert@cvs.openbsd.org 2014/07/15 15:54:14 [PROTOCOL auth-options.c auth-passwd.c auth-rh-rsa.c auth-rhosts.c] [auth-rsa.c auth.c auth1.c auth2-hostbased.c auth2-kbdint.c auth2-none.c] [auth2-passwd.c auth2-pubkey.c auth2.c canohost.c channels.c channels.h] [clientloop.c misc.c misc.h monitor.c mux.c packet.c readconf.c] [readconf.h servconf.c servconf.h serverloop.c session.c ssh-agent.c] [ssh.c ssh_config.5 sshconnect.c sshconnect1.c sshconnect2.c sshd.c] [sshd_config.5 sshlogin.c] Add support for Unix domain socket forwarding. A remote TCP port may be forwarded to a local Unix domain socket and vice versa or both ends may be a Unix domain socket. This is a reimplementation of the streamlocal patches by William Ahern from: http://www.25thandclement.com/~william/projects/streamlocal.html OK djm@ markus@ --- misc.c | 49 ++++++++++++++++++++++++++++++++++++++++++++++++- 1 file changed, 48 insertions(+), 1 deletion(-) (limited to 'misc.c') diff --git a/misc.c b/misc.c index 099c4ef80..739916ba4 100644 --- a/misc.c +++ b/misc.c @@ -1,4 +1,4 @@ -/* $OpenBSD: misc.c,v 1.93 2014/04/20 02:30:25 djm Exp $ */ +/* $OpenBSD: misc.c,v 1.94 2014/07/15 15:54:14 millert Exp $ */ /* * Copyright (c) 2000 Markus Friedl. All rights reserved. * Copyright (c) 2005,2006 Damien Miller. All rights reserved. @@ -29,6 +29,7 @@ #include #include #include +#include #include #include @@ -1056,6 +1057,52 @@ lowercase(char *s) for (; *s; s++) *s = tolower((u_char)*s); } + +int +unix_listener(const char *path, int backlog, int unlink_first) +{ + struct sockaddr_un sunaddr; + int saved_errno, sock; + + memset(&sunaddr, 0, sizeof(sunaddr)); + sunaddr.sun_family = AF_UNIX; + if (strlcpy(sunaddr.sun_path, path, sizeof(sunaddr.sun_path)) >= sizeof(sunaddr.sun_path)) { + error("%s: \"%s\" too long for Unix domain socket", __func__, + path); + errno = ENAMETOOLONG; + return -1; + } + + sock = socket(PF_UNIX, SOCK_STREAM, 0); + if (sock < 0) { + saved_errno = errno; + error("socket: %.100s", strerror(errno)); + errno = saved_errno; + return -1; + } + if (unlink_first == 1) { + if (unlink(path) != 0 && errno != ENOENT) + error("unlink(%s): %.100s", path, strerror(errno)); + } + if (bind(sock, (struct sockaddr *)&sunaddr, sizeof(sunaddr)) < 0) { + saved_errno = errno; + error("bind: %.100s", strerror(errno)); + close(sock); + error("%s: cannot bind to path: %s", __func__, path); + errno = saved_errno; + return -1; + } + if (listen(sock, backlog) < 0) { + saved_errno = errno; + error("listen: %.100s", strerror(errno)); + close(sock); + unlink(path); + error("%s: cannot listen on path: %s", __func__, path); + errno = saved_errno; + return -1; + } + return sock; +} void sock_set_v6only(int s) { -- cgit v1.2.3