From: Ian Jackson Date: Wed, 4 Oct 2017 13:38:56 +0000 (+0100) Subject: fishdescriptor: Copy fd passing C sender code from libxl X-Git-Tag: archive/debian/6.0.0~1^2~45 X-Git-Url: http://www.chiark.greenend.org.uk/ucgi/~ian/git?p=chiark-utils.git;a=commitdiff_plain;h=77ccd21a8f405e46719f8ee02b57a4d067ecc7a4;hp=6cc6688a64eb5cea66b114e94c387a57190ff24a;ds=inline fishdescriptor: Copy fd passing C sender code from libxl Copy int libxl__sendmsg_fds from libxl so we can clone and hack it. Source was: xen.git#38ab259f559be5457f6866ba24185e013f27defb tools/libxl/libxl_utils.c libxl is LGPL2.1-only. We will upgrade this licence to be compatible with the rest of chiark utils (GPL3+) in a moment. This is permitted by LGPL-2.1 section 3. Signed-off-by: Ian Jackson --- diff --git a/fishdescriptor/donate.c b/fishdescriptor/donate.c new file mode 100644 index 0000000..b7ef5f8 --- /dev/null +++ b/fishdescriptor/donate.c @@ -0,0 +1,46 @@ +/* + * Copyright (C) 2009 Citrix Ltd. + * Copyright (C) 2017 Citrix Ltd. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU Lesser General Public License as published + * by the Free Software Foundation; version 2.1 only. with the special + * exception on linking described in file LICENSE. + */ + +int libxl__sendmsg_fds(libxl__gc *gc, int carrier, + const void *data, size_t datalen, + int nfds, const int fds[], const char *what) { + struct msghdr msg = { 0 }; + struct cmsghdr *cmsg; + size_t spaceneeded = nfds * sizeof(fds[0]); + char control[CMSG_SPACE(spaceneeded)]; + struct iovec iov; + int r; + + iov.iov_base = (void*)data; + iov.iov_len = datalen; + + /* compose the message */ + msg.msg_iov = &iov; + msg.msg_iovlen = 1; + msg.msg_control = control; + msg.msg_controllen = sizeof(control); + + /* attach open fd */ + cmsg = CMSG_FIRSTHDR(&msg); + cmsg->cmsg_level = SOL_SOCKET; + cmsg->cmsg_type = SCM_RIGHTS; + cmsg->cmsg_len = CMSG_LEN(spaceneeded); + memcpy(CMSG_DATA(cmsg), fds, spaceneeded); + + msg.msg_controllen = cmsg->cmsg_len; + + r = sendmsg(carrier, &msg, 0); + if (r < 0) { + LOGE(ERROR, "failed to send fd-carrying message (%s)", what); + return ERROR_FAIL; + } + + return 0; +}