From patchwork Tue May 21 12:46:55 2019 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Trond Myklebust X-Patchwork-Id: 10953591 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id EC4B776 for ; Tue, 21 May 2019 12:49:17 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id DDB82288DD for ; Tue, 21 May 2019 12:49:17 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id D26D828961; Tue, 21 May 2019 12:49:17 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-8.0 required=2.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID,DKIM_VALID_AU,FREEMAIL_FROM,MAILING_LIST_MULTI,RCVD_IN_DNSWL_HI autolearn=ham version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id B7040288B6 for ; Tue, 21 May 2019 12:49:14 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1726344AbfEUMtO (ORCPT ); Tue, 21 May 2019 08:49:14 -0400 Received: from mail-it1-f195.google.com ([209.85.166.195]:52574 "EHLO mail-it1-f195.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1727251AbfEUMtN (ORCPT ); Tue, 21 May 2019 08:49:13 -0400 Received: by mail-it1-f195.google.com with SMTP id t184so4724034itf.2 for ; Tue, 21 May 2019 05:49:13 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:cc:subject:date:message-id:in-reply-to:references :mime-version:content-transfer-encoding; bh=0106F+OIYuqVEg46cY8S9oFV/iyDhlYutv2OgfNUAlo=; b=Qiz7dc11EDTEqdsK5oApuPDxvOXOKwXD/jxZ+aigDpohi7I8p5j86ZUyBTusTi6bjx /0+RtPm+ZCfSqrKriBAILDDAM35BGuNzwMn5YkW/9uOOAMFju0OCzo5MlTuk1QrMRu+e +KMPoTfY1T4ZJ2ZdwHe4SEOVh+EyQ5svDseQU9apdO2zPYzLkU4SS2UqKP0tRzWfDt3y Sb9nQ5aKXSnqtHwCRpPHmHaKH1dI9PleROWhECRE20jSgUiM0EFUoKyvYHj9wS+3gYlQ dZ3v5ZmgnOfmtbIyrOUpEDiGGCX6yXvOI6F0DL+YtvkxvL0YzA2qfXh1XVe3XvQAV2gv T4CA== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=0106F+OIYuqVEg46cY8S9oFV/iyDhlYutv2OgfNUAlo=; b=N+E5EJ7/TEhfvB/mEpmk8oRP+k3mo0heUdYm7OJMtCnbnwiipM3mXSVBBZ1lKqJ+sl taNjR9s3y8N3aZ7Qa6brRRI/SO4f4pDrkpKmxOkx8EBV99wZCyNtavXuPzJW6iZchs9B 4PQWEAyJLs0NA/HtOpB8GLOFVX257pODDfcWDRVaDDAss1uyIujSClXg9UsO8H0GmX+Q yB4sWnO0dyRj1ywEM40Htt8kHj1vosQoBrxdTc25/7eWjCC2BRYVGU898MLIS1Gtqjoa FBczh/d/gYG6NbGcvlqqV4DKKUtqs3q9iFerqMQzR1TEtTzyJfFSyeEn1WZbXfTSrwIF z3BA== X-Gm-Message-State: APjAAAWWifz4LGi+rbS4hFZdpKM1vdCq9byhmTNqsVOQE83hNhVGPuu+ F0FW/wcsyOWu/3hKilTABw== X-Google-Smtp-Source: APXvYqwAUPLJa1Bm1ipJhelXn+OmKiEgUte0IAiTWVGMY2BiM80Ro7TdUld55hhJXjbVL7KhHDrPrA== X-Received: by 2002:a02:b38e:: with SMTP id p14mr6114963jan.43.1558442952699; Tue, 21 May 2019 05:49:12 -0700 (PDT) Received: from localhost.localdomain (c-68-40-189-247.hsd1.mi.comcast.net. [68.40.189.247]) by smtp.gmail.com with ESMTPSA id v139sm1693180itb.25.2019.05.21.05.49.11 (version=TLS1_2 cipher=ECDHE-RSA-CHACHA20-POLY1305 bits=256/256); Tue, 21 May 2019 05:49:11 -0700 (PDT) From: Trond Myklebust X-Google-Original-From: Trond Myklebust To: SteveD@redhat.com Cc: linux-nfs@vger.kernel.org Subject: [RFC PATCH v2 1/7] mountd: Ensure we don't share cache file descriptors among processes. Date: Tue, 21 May 2019 08:46:55 -0400 Message-Id: <20190521124701.61849-2-trond.myklebust@hammerspace.com> X-Mailer: git-send-email 2.21.0 In-Reply-To: <20190521124701.61849-1-trond.myklebust@hammerspace.com> References: <20190521124701.61849-1-trond.myklebust@hammerspace.com> MIME-Version: 1.0 Sender: linux-nfs-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-nfs@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP Sharing cache descriptors without using locking can be very bad. Signed-off-by: Trond Myklebust --- utils/mountd/mountd.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/utils/mountd/mountd.c b/utils/mountd/mountd.c index fb7bba4cd390..88a207b3a85a 100644 --- a/utils/mountd/mountd.c +++ b/utils/mountd/mountd.c @@ -836,8 +836,6 @@ main(int argc, char **argv) if (!foreground) closeall(3); - cache_open(); - unregister_services(); if (version2()) { listeners += nfs_svc_create("mountd", MOUNTPROG, @@ -888,6 +886,9 @@ main(int argc, char **argv) if (num_threads > 1) fork_workers(); + /* Open files now to avoid sharing descriptors among forked processes */ + cache_open(); + xlog(L_NOTICE, "Version " VERSION " starting"); my_svc_run(); From patchwork Tue May 21 12:46:56 2019 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Trond Myklebust X-Patchwork-Id: 10953597 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 2C79076 for ; Tue, 21 May 2019 12:49:19 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 1BEE22880A for ; Tue, 21 May 2019 12:49:19 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 0FFE7288D0; Tue, 21 May 2019 12:49:19 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-8.0 required=2.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID,DKIM_VALID_AU,FREEMAIL_FROM,MAILING_LIST_MULTI,RCVD_IN_DNSWL_HI autolearn=ham version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 2A26928849 for ; Tue, 21 May 2019 12:49:16 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1727819AbfEUMtP (ORCPT ); Tue, 21 May 2019 08:49:15 -0400 Received: from mail-io1-f66.google.com ([209.85.166.66]:35551 "EHLO mail-io1-f66.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1727251AbfEUMtP (ORCPT ); Tue, 21 May 2019 08:49:15 -0400 Received: by mail-io1-f66.google.com with SMTP id p2so13831020iol.2 for ; Tue, 21 May 2019 05:49:14 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:cc:subject:date:message-id:in-reply-to:references :mime-version:content-transfer-encoding; bh=WTJIEF64GQ5WaLkZVqyDs/M6F2K2o7LdsId5gPgoX24=; b=vTuWr3fRsYPqMPJemTJnJAa97fd0TYf9EJbq1F4apLVyF3MjRPjOxoFpHgVQnm17Qg no7bKM3OuNpjBBleUYHYAkdx+ZNGhxTIVKBAicsm2arxSNMgrsTeMjBf21+uxlP0PpB3 RKyYtmB4xP3s7WUJ8AFuMCmFFc80dnaMAk6+pQjvBLT5AYeMfXc8PFrlFYflbqPzlcCE 9BP85XLrpFZM8tSozOl2V/HD3VkPMxCoo5T8NBJfOUkCfa0qNDQIRGfuzG09jNf7c+p7 siF+3nhG5zyiAPpm1YA92WGDGLIY9El1Svtn+wnMzIkg+EBUPTNR6+p6N2hQ32ucjTRT Ytxw== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=WTJIEF64GQ5WaLkZVqyDs/M6F2K2o7LdsId5gPgoX24=; b=IVgmiHqbm2iZKW/sIOLJrf6jGsMqx2VMwhOF6uB+c9sH3C0gNss8tZ2PaJ5FcZabsE C/wGanJVbvHGnJAFSs6uu91Ch/v6rOOHvYwmUbNj0eD/oW5IhEtJ1LmxzWaS3KlQLkp9 O2YepX++vBCijLkiqnUrxtJSmn2fUI4J9hgItO8pQ4M2kA3GugfCiQnySDHFKcK8GVa5 0bdM4oWMroMNIlDLM9RAvxX4B7638E08mwqWLM4oOrvHZuhc07paG075vlucD+I6sGWO RHEznO+sETbIzagsNNnQeOBrDxdO0ATyTiPo+1b0gbDDlc1JQYnPbGEPuxx8YW/6qeDB 2jlw== X-Gm-Message-State: APjAAAXy42UkZnotv7tZj3eat9AEUgWwKuTwRDFH29raRYfEKLPvYQcq Z9ZEbHuTUNFXgTyfi0haJg== X-Google-Smtp-Source: APXvYqx8cdJn+RYKoE60GRy6VxOV5b6V64mBhiz4TMHIP2bI5TQ4HJE9oVszKkIaK2akEL7ZUzSEQg== X-Received: by 2002:a6b:f719:: with SMTP id k25mr4837004iog.129.1558442953786; Tue, 21 May 2019 05:49:13 -0700 (PDT) Received: from localhost.localdomain (c-68-40-189-247.hsd1.mi.comcast.net. [68.40.189.247]) by smtp.gmail.com with ESMTPSA id v139sm1693180itb.25.2019.05.21.05.49.12 (version=TLS1_2 cipher=ECDHE-RSA-CHACHA20-POLY1305 bits=256/256); Tue, 21 May 2019 05:49:12 -0700 (PDT) From: Trond Myklebust X-Google-Original-From: Trond Myklebust To: SteveD@redhat.com Cc: linux-nfs@vger.kernel.org Subject: [RFC PATCH v2 2/7] Add a simple workqueue mechanism Date: Tue, 21 May 2019 08:46:56 -0400 Message-Id: <20190521124701.61849-3-trond.myklebust@hammerspace.com> X-Mailer: git-send-email 2.21.0 In-Reply-To: <20190521124701.61849-2-trond.myklebust@hammerspace.com> References: <20190521124701.61849-1-trond.myklebust@hammerspace.com> <20190521124701.61849-2-trond.myklebust@hammerspace.com> MIME-Version: 1.0 Sender: linux-nfs-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-nfs@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP Add a simple workqueue mechanism to allow us to run threads that are subject to chroot(), and have them operate on the knfsd kernel daemon. Signed-off-by: Trond Myklebust --- aclocal/libpthread.m4 | 13 +- configure.ac | 6 +- support/include/Makefile.am | 1 + support/include/workqueue.h | 18 +++ support/misc/Makefile.am | 2 +- support/misc/workqueue.c | 228 ++++++++++++++++++++++++++++++++++++ utils/mountd/Makefile.am | 3 +- 7 files changed, 262 insertions(+), 9 deletions(-) create mode 100644 support/include/workqueue.h create mode 100644 support/misc/workqueue.c diff --git a/aclocal/libpthread.m4 b/aclocal/libpthread.m4 index e87d2a0c2dc5..55e046e38cd1 100644 --- a/aclocal/libpthread.m4 +++ b/aclocal/libpthread.m4 @@ -3,11 +3,12 @@ dnl AC_DEFUN([AC_LIBPTHREAD], [ dnl Check for library, but do not add -lpthreads to LIBS - AC_CHECK_LIB([pthread], [pthread_create], [LIBPTHREAD=-lpthread], - [AC_MSG_ERROR([libpthread not found.])]) - AC_SUBST(LIBPTHREAD) - - AC_CHECK_HEADERS([pthread.h], , - [AC_MSG_ERROR([libpthread headers not found.])]) + AC_CHECK_LIB([pthread], [pthread_create], + [AC_DEFINE([HAVE_LIBPTHREAD], [1], + [Define to 1 if you have libpthread.]) + AC_CHECK_HEADERS([pthread.h], [], + [AC_MSG_ERROR([libpthread headers not found.])]) + AC_SUBST([LIBPTHREAD],[-lpthread])], + [$1]) ])dnl diff --git a/configure.ac b/configure.ac index 4d7096193d0b..c6c2d73b06dd 100644 --- a/configure.ac +++ b/configure.ac @@ -320,6 +320,10 @@ AC_CHECK_FUNC([getservbyname], , AC_CHECK_LIB([crypt], [crypt], [LIBCRYPT="-lcrypt"]) +AC_CHECK_HEADERS([sched.h], [], []) +AC_CHECK_FUNCS([unshare], [] , []) +AC_LIBPTHREAD([]) + if test "$enable_nfsv4" = yes; then dnl check for libevent libraries and headers AC_LIBEVENT @@ -417,7 +421,7 @@ if test "$enable_gss" = yes; then AC_KERBEROS_V5 dnl Check for pthreads - AC_LIBPTHREAD + AC_LIBPTHREAD([AC_MSG_ERROR([libpthread not found.])]) dnl librpcsecgss already has a dependency on libgssapi, dnl but we need to make sure we get the right version diff --git a/support/include/Makefile.am b/support/include/Makefile.am index 599f500e2b40..df5e47836d29 100644 --- a/support/include/Makefile.am +++ b/support/include/Makefile.am @@ -19,6 +19,7 @@ noinst_HEADERS = \ sockaddr.h \ tcpwrapper.h \ v4root.h \ + workqueue.h \ xio.h \ xlog.h \ xmalloc.h \ diff --git a/support/include/workqueue.h b/support/include/workqueue.h new file mode 100644 index 000000000000..518be82f1b34 --- /dev/null +++ b/support/include/workqueue.h @@ -0,0 +1,18 @@ +/* + * Copyright (C) 2019 Trond Myklebust + */ +#ifndef WORKQUEUE_H +#define WORKQUEUE_H + +struct xthread_workqueue; + +struct xthread_workqueue *xthread_workqueue_alloc(void); +void xthread_workqueue_shutdown(struct xthread_workqueue *wq); + +void xthread_work_run_sync(struct xthread_workqueue *wq, + void (*fn)(void *), void *data); + +void xthread_workqueue_chroot(struct xthread_workqueue *wq, + const char *path); + +#endif diff --git a/support/misc/Makefile.am b/support/misc/Makefile.am index 8936b0d64e45..d0bff8feb6ae 100644 --- a/support/misc/Makefile.am +++ b/support/misc/Makefile.am @@ -1,6 +1,6 @@ ## Process this file with automake to produce Makefile.in noinst_LIBRARIES = libmisc.a -libmisc_a_SOURCES = tcpwrapper.c from_local.c mountpoint.c file.c +libmisc_a_SOURCES = tcpwrapper.c from_local.c mountpoint.c file.c workqueue.c MAINTAINERCLEANFILES = Makefile.in diff --git a/support/misc/workqueue.c b/support/misc/workqueue.c new file mode 100644 index 000000000000..b8d03446f2c7 --- /dev/null +++ b/support/misc/workqueue.c @@ -0,0 +1,228 @@ +#include +#include + +#include "config.h" +#include "workqueue.h" +#include "xlog.h" + +#if defined(HAVE_SCHED_H) && defined(HAVE_LIBPTHREAD) && defined(HAVE_UNSHARE) +#include +#include + +struct xwork_struct { + struct xwork_struct *next; + void (*fn)(void *); + void *data; +}; + +struct xwork_queue { + struct xwork_struct *head; + struct xwork_struct **tail; + + unsigned char shutdown : 1; +}; + +static void xwork_queue_init(struct xwork_queue *queue) +{ + queue->head = NULL; + queue->tail = &queue->head; + queue->shutdown = 0; +} + +static void xwork_enqueue(struct xwork_queue *queue, + struct xwork_struct *entry) +{ + entry->next = NULL; + *queue->tail = entry; + queue->tail = &entry->next; +} + +static struct xwork_struct *xwork_dequeue(struct xwork_queue *queue) +{ + struct xwork_struct *entry = NULL; + if (queue->head) { + entry = queue->head; + queue->head = entry->next; + if (!queue->head) + queue->tail = &queue->head; + } + return entry; +} + +struct xthread_work { + struct xwork_struct work; + + pthread_cond_t cond; +}; + +struct xthread_workqueue { + struct xwork_queue queue; + + pthread_mutex_t mutex; + pthread_cond_t cond; +}; + +static void xthread_workqueue_init(struct xthread_workqueue *wq) +{ + xwork_queue_init(&wq->queue); + pthread_mutex_init(&wq->mutex, NULL); + pthread_cond_init(&wq->cond, NULL); +} + +static void xthread_workqueue_fini(struct xthread_workqueue *wq) +{ + pthread_cond_destroy(&wq->cond); + pthread_mutex_destroy(&wq->mutex); +} + +static int xthread_work_enqueue(struct xthread_workqueue *wq, + struct xthread_work *work) +{ + xwork_enqueue(&wq->queue, &work->work); + pthread_cond_signal(&wq->cond); + return 0; +} + +static struct xthread_work *xthread_work_dequeue(struct xthread_workqueue *wq) +{ + return (struct xthread_work *)xwork_dequeue(&wq->queue); +} + +static void xthread_workqueue_do_work(struct xthread_workqueue *wq) +{ + struct xthread_work *work; + + pthread_mutex_lock(&wq->mutex); + /* Signal the caller that we're up and running */ + pthread_cond_signal(&wq->cond); + for (;;) { + work = xthread_work_dequeue(wq); + if (work) { + work->work.fn(work->work.data); + pthread_cond_signal(&work->cond); + continue; + } + if (wq->queue.shutdown) + break; + pthread_cond_wait(&wq->cond, &wq->mutex); + } + pthread_mutex_unlock(&wq->mutex); +} + +void xthread_workqueue_shutdown(struct xthread_workqueue *wq) +{ + pthread_mutex_lock(&wq->mutex); + wq->queue.shutdown = 1; + pthread_cond_signal(&wq->cond); + pthread_mutex_unlock(&wq->mutex); +} + +static void xthread_workqueue_free(struct xthread_workqueue *wq) +{ + xthread_workqueue_fini(wq); + free(wq); +} + +static void xthread_workqueue_cleanup(void *data) +{ + xthread_workqueue_free(data); +} + +static void *xthread_workqueue_worker(void *data) +{ + pthread_cleanup_push(xthread_workqueue_cleanup, data); + xthread_workqueue_do_work(data); + pthread_cleanup_pop(1); + return NULL; +} + +struct xthread_workqueue *xthread_workqueue_alloc(void) +{ + struct xthread_workqueue *ret; + pthread_t thread; + + ret = malloc(sizeof(*ret)); + if (ret) { + xthread_workqueue_init(ret); + + pthread_mutex_lock(&ret->mutex); + if (pthread_create(&thread, NULL, + xthread_workqueue_worker, + ret) == 0) { + /* Wait for thread to start */ + pthread_cond_wait(&ret->cond, &ret->mutex); + pthread_mutex_unlock(&ret->mutex); + return ret; + } + pthread_mutex_unlock(&ret->mutex); + xthread_workqueue_free(ret); + ret = NULL; + } + return NULL; +} + +void xthread_work_run_sync(struct xthread_workqueue *wq, + void (*fn)(void *), void *data) +{ + struct xthread_work work = { + { + NULL, + fn, + data + }, + PTHREAD_COND_INITIALIZER, + }; + pthread_mutex_lock(&wq->mutex); + xthread_work_enqueue(wq, &work); + pthread_cond_wait(&work.cond, &wq->mutex); + pthread_mutex_unlock(&wq->mutex); + pthread_cond_destroy(&work.cond); +} + +static void xthread_workqueue_do_chroot(void *data) +{ + const char *path = data; + + if (unshare(CLONE_FS) != 0) { + xlog_err("unshare() failed: %m"); + return; + } + if (chroot(path) != 0) + xlog_err("chroot() failed: %m"); +} + +void xthread_workqueue_chroot(struct xthread_workqueue *wq, + const char *path) +{ + xthread_work_run_sync(wq, xthread_workqueue_do_chroot, (void *)path); +} + +#else + +struct xthread_workqueue { +}; + +static struct xthread_workqueue ret; + +struct xthread_workqueue *xthread_workqueue_alloc(void) +{ + return &ret; +} + +void xthread_workqueue_shutdown(struct xthread_workqueue *wq) +{ +} + +void xthread_work_run_sync(struct xthread_workqueue *wq, + void (*fn)(void *), void *data) +{ + fn(data); +} + +void xthread_workqueue_chroot(struct xthread_workqueue *wq, + const char *path) +{ + xlog_err("Unable to run as chroot"); +} + +#endif /* defined(HAVE_SCHED_H) && defined(HAVE_LIBPTHREAD) && defined(HAVE_UNSHARE) */ diff --git a/utils/mountd/Makefile.am b/utils/mountd/Makefile.am index 73eeb3f35070..18610f18238c 100644 --- a/utils/mountd/Makefile.am +++ b/utils/mountd/Makefile.am @@ -19,7 +19,8 @@ mountd_LDADD = ../../support/export/libexport.a \ ../../support/nfs/libnfs.la \ ../../support/misc/libmisc.a \ $(OPTLIBS) \ - $(LIBBSD) $(LIBWRAP) $(LIBNSL) $(LIBBLKID) $(LIBTIRPC) + $(LIBBSD) $(LIBWRAP) $(LIBNSL) $(LIBBLKID) $(LIBTIRPC) \ + $(LIBPTHREAD) mountd_CPPFLAGS = $(AM_CPPFLAGS) $(CPPFLAGS) \ -I$(top_builddir)/support/include \ -I$(top_srcdir)/support/export From patchwork Tue May 21 12:46:57 2019 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Trond Myklebust X-Patchwork-Id: 10953595 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 888AA17E0 for ; Tue, 21 May 2019 12:49:18 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 78A2C2880A for ; Tue, 21 May 2019 12:49:18 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 6CDEF288DD; Tue, 21 May 2019 12:49:18 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-8.0 required=2.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID,DKIM_VALID_AU,FREEMAIL_FROM,MAILING_LIST_MULTI,RCVD_IN_DNSWL_HI autolearn=ham version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id B5E1C288D0 for ; Tue, 21 May 2019 12:49:16 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1727941AbfEUMtQ (ORCPT ); Tue, 21 May 2019 08:49:16 -0400 Received: from mail-it1-f194.google.com ([209.85.166.194]:54574 "EHLO mail-it1-f194.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1727812AbfEUMtP (ORCPT ); Tue, 21 May 2019 08:49:15 -0400 Received: by mail-it1-f194.google.com with SMTP id h20so2156673itk.4 for ; Tue, 21 May 2019 05:49:15 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:cc:subject:date:message-id:in-reply-to:references :mime-version:content-transfer-encoding; bh=4SlCwu18mEUGkbPDNHJL0EYP1qCKU4LYpKACHLEmVyE=; b=Cm9lkIj5p62oDQkGXMU3ZoUqr7YirTcegw+QLRsFhTDmJvIkqXPC/LbdcxI73FgtQO QVpSZ9dF6SlA2fyeWW/UyAGGgzJIBfAVh5gP2x9HNqGnEIbLwvSLTHs9LPe+d4WqCQl7 EgTP07iZa9ly3UOSWG1JTmW/VuGcm9yrRoZh8952zUrFmV82PE2avGTdaRarD6RCfCGJ sfH2Puii3rynR9vC3yP37hTHwgCW1AtXbEo5+f4HtEWbZg7LODl+jmKUiT3lVbR/m8Rq 1iJIfa+fd4R6e6f2K/BoX+O7TwPgG0B4OuBMyk6cItb+PXqO9wm9tI0YfTxczW9kb0Pv 5cZw== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=4SlCwu18mEUGkbPDNHJL0EYP1qCKU4LYpKACHLEmVyE=; b=mMuIvanw07qyLorh2IsQt8i5r5AVW+Dclo+KK/cPsJ/AwRBK3YnRQd7W5wnPg7orWM jUlbJ+GTuGh991gotOgsQ/g3oBipaL4ga7flOvbAyLDERxxp2n/zZXyzW9pstqztHJgI brKEuWQLxIKWDbhUICCm7w3RH4cAgTXhiiOAq8cevMDm5G6UJRNOpV9NFp8LHvKZTyoa 6FXRbDi/Tfk3Lnj/W8SAnFX3QKjwDP6F/MxXJ63fU74u2Xf2m6EsVI1oxIf7rjlcioFg +Z4JPIvM3k7Yq/QNIKB1NOrVJtXVDsP9487clhRTLbHD9ugiAwwyZH8qK4GA0CHgIvaT t5PA== X-Gm-Message-State: APjAAAXfqJ5pJn4Ts1zsoaMVr4LECsxu99LNwqmeJnJVgyrJkoa/E0Wy 41Uu3iGoCx16lpW52v4PLQzs2Yc= X-Google-Smtp-Source: APXvYqwVPCQh1aaM7HAJa01QSXY4Wgo5iHHC6INg4k5O5I4l2QH5taWqxmE7iUFoIxd35RtD+kboXQ== X-Received: by 2002:a24:d613:: with SMTP id o19mr3476490itg.8.1558442954695; Tue, 21 May 2019 05:49:14 -0700 (PDT) Received: from localhost.localdomain (c-68-40-189-247.hsd1.mi.comcast.net. [68.40.189.247]) by smtp.gmail.com with ESMTPSA id v139sm1693180itb.25.2019.05.21.05.49.13 (version=TLS1_2 cipher=ECDHE-RSA-CHACHA20-POLY1305 bits=256/256); Tue, 21 May 2019 05:49:14 -0700 (PDT) From: Trond Myklebust X-Google-Original-From: Trond Myklebust To: SteveD@redhat.com Cc: linux-nfs@vger.kernel.org Subject: [RFC PATCH v2 3/7] Add utilities for resolving nfsd paths and stat()ing them Date: Tue, 21 May 2019 08:46:57 -0400 Message-Id: <20190521124701.61849-4-trond.myklebust@hammerspace.com> X-Mailer: git-send-email 2.21.0 In-Reply-To: <20190521124701.61849-3-trond.myklebust@hammerspace.com> References: <20190521124701.61849-1-trond.myklebust@hammerspace.com> <20190521124701.61849-2-trond.myklebust@hammerspace.com> <20190521124701.61849-3-trond.myklebust@hammerspace.com> MIME-Version: 1.0 Sender: linux-nfs-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-nfs@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP Add helper functions that can resolve nfsd paths by prepending the necessary prefix if the admin has specified a root path in the nfs.conf file. Signed-off-by: Trond Myklebust --- configure.ac | 2 +- support/include/Makefile.am | 1 + support/include/nfsd_path.h | 17 ++++ support/misc/Makefile.am | 3 +- support/misc/nfsd_path.c | 173 ++++++++++++++++++++++++++++++++++++ 5 files changed, 194 insertions(+), 2 deletions(-) create mode 100644 support/include/nfsd_path.h create mode 100644 support/misc/nfsd_path.c diff --git a/configure.ac b/configure.ac index c6c2d73b06dd..4793daeb2716 100644 --- a/configure.ac +++ b/configure.ac @@ -321,7 +321,7 @@ AC_CHECK_FUNC([getservbyname], , AC_CHECK_LIB([crypt], [crypt], [LIBCRYPT="-lcrypt"]) AC_CHECK_HEADERS([sched.h], [], []) -AC_CHECK_FUNCS([unshare], [] , []) +AC_CHECK_FUNCS([unshare openat fstatat], [] , []) AC_LIBPTHREAD([]) if test "$enable_nfsv4" = yes; then diff --git a/support/include/Makefile.am b/support/include/Makefile.am index df5e47836d29..fbf487eee0e2 100644 --- a/support/include/Makefile.am +++ b/support/include/Makefile.am @@ -10,6 +10,7 @@ noinst_HEADERS = \ misc.h \ nfs_mntent.h \ nfs_paths.h \ + nfsd_path.h \ nfslib.h \ nfsrpc.h \ nls.h \ diff --git a/support/include/nfsd_path.h b/support/include/nfsd_path.h new file mode 100644 index 000000000000..5936cd5ed666 --- /dev/null +++ b/support/include/nfsd_path.h @@ -0,0 +1,17 @@ +/* + * Copyright (C) 2019 Trond Myklebust + */ +#ifndef XPATH_H +#define XPATH_H + +void nfsd_path_init(void); +void nfsd_path_nfsd_rootfs_close(void); + +const char * nfsd_path_nfsd_rootdir(void); +char * nfsd_path_strip_root(char *pathname); +char * nfsd_path_prepend_dir(const char *dir, const char *pathname); + +int nfsd_path_stat(const char *pathname, struct stat *statbuf); +int nfsd_path_lstat(const char *pathname, struct stat *statbuf); + +#endif diff --git a/support/misc/Makefile.am b/support/misc/Makefile.am index d0bff8feb6ae..ff1e8ab79ae3 100644 --- a/support/misc/Makefile.am +++ b/support/misc/Makefile.am @@ -1,6 +1,7 @@ ## Process this file with automake to produce Makefile.in noinst_LIBRARIES = libmisc.a -libmisc_a_SOURCES = tcpwrapper.c from_local.c mountpoint.c file.c workqueue.c +libmisc_a_SOURCES = tcpwrapper.c from_local.c mountpoint.c file.c \ + nfsd_path.c workqueue.c MAINTAINERCLEANFILES = Makefile.in diff --git a/support/misc/nfsd_path.c b/support/misc/nfsd_path.c new file mode 100644 index 000000000000..481ba49a38fd --- /dev/null +++ b/support/misc/nfsd_path.c @@ -0,0 +1,173 @@ +#include +#include +#include +#include + +#include "config.h" +#include "conffile.h" +#include "xmalloc.h" +#include "xlog.h" +#include "nfsd_path.h" + +static int +nfsd_path_isslash(const char *path) +{ + return path[0] == '/' && path[1] == '/'; +} + +static int +nfsd_path_isdot(const char *path) +{ + return path[0] == '.' && path[1] == '/'; +} + +static const char * +nfsd_path_strip(const char *path) +{ + if (!path || *path == '\0') + goto out; + for (;;) { + if (nfsd_path_isslash(path)) { + path++; + continue; + } + if (nfsd_path_isdot(path)) { + path += 2; + continue; + } + break; + } +out: + return path; +} + +const char * +nfsd_path_nfsd_rootdir(void) +{ + const char *rootdir; + + rootdir = nfsd_path_strip(conf_get_str("nfsd", "root_dir")); + if (!rootdir || rootdir[0] == '\0') + return NULL; + if (rootdir[0] == '/' && rootdir[1] == '\0') + return NULL; + return rootdir; +} + +char * +nfsd_path_strip_root(char *pathname) +{ + const char *dir = nfsd_path_nfsd_rootdir(); + char *ret; + + ret = strstr(pathname, dir); + if (!ret || ret != pathname) + return pathname; + return pathname + strlen(dir); +} + +char * +nfsd_path_prepend_dir(const char *dir, const char *pathname) +{ + size_t len, dirlen; + char *ret; + + dirlen = strlen(dir); + while (dirlen > 0 && dir[dirlen - 1] == '/') + dirlen--; + if (!dirlen) + return NULL; + len = dirlen + strlen(pathname) + 1; + ret = xmalloc(len + 1); + snprintf(ret, len, "%.*s/%s", (int)dirlen, dir, pathname); + return ret; +} + +#if defined(HAVE_FSTATAT) && defined(HAVE_OPENAT) +static int nfsd_rootfs = AT_FDCWD; + +void nfsd_path_nfsd_rootfs_close(void) +{ + if (nfsd_rootfs != AT_FDCWD) { + close(nfsd_rootfs); + nfsd_rootfs = AT_FDCWD; + } +} + +void nfsd_path_init(void) +{ + const char *rootdir = nfsd_path_nfsd_rootdir(); + + nfsd_path_nfsd_rootfs_close(); + if (rootdir) { + nfsd_rootfs = openat(AT_FDCWD, rootdir, O_PATH); + if (nfsd_rootfs == -1) + xlog_err("Could not open directory %s: %m", rootdir); + } +} + +int nfsd_path_stat(const char *pathname, struct stat *statbuf) +{ + if (nfsd_rootfs != AT_FDCWD) { + while (pathname[0] == '/') + pathname++; + } + return fstatat(nfsd_rootfs, pathname, statbuf, AT_EMPTY_PATH | + AT_NO_AUTOMOUNT); +} + +int nfsd_path_lstat(const char *pathname, struct stat *statbuf) +{ + if (nfsd_rootfs != AT_FDCWD) { + while (pathname[0] == '/') + pathname++; + } + return fstatat(nfsd_rootfs, pathname, statbuf, AT_EMPTY_PATH | + AT_NO_AUTOMOUNT | AT_SYMLINK_NOFOLLOW); +} + +#else /* defined(HAVE_FSTATAT) && defined(HAVE_OPENAT) */ +void nfsd_path_init(void) +{ +} + +void nfsd_path_nfsd_rootfs_close(void) +{ +} + +int nfsd_path_stat(const char *pathname, struct stat *statbuf) +{ + const char *rootdir = nfsd_path_nfsd_rootdir(); + char *str; + int ret; + + if (!rootdir) + goto out_stat; + str = nfsd_path_prepend_dir(rootdir, nfsd_path_strip(pathname)); + if (!str) + goto out_stat; + ret = stat(str, statbuf); + xfree(str); + return ret; +out_stat: + return stat(pathname, statbuf); +} + +int nfsd_path_lstat(const char *pathname, struct stat *statbuf) +{ + const char *rootdir = nfsd_path_nfsd_rootdir(); + char *str; + int ret; + + if (!rootdir) + goto out_lstat; + str = nfsd_path_prepend_dir(rootdir, nfsd_path_strip(pathname)); + if (!str) + goto out_lstat; + ret = lstat(str, statbuf); + xfree(str); + return ret; +out_lstat: + return lstat(pathname, statbuf); +} +#endif From patchwork Tue May 21 12:46:58 2019 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Trond Myklebust X-Patchwork-Id: 10953593 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 5D3AD1708 for ; Tue, 21 May 2019 12:49:18 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 4CF562880A for ; Tue, 21 May 2019 12:49:18 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 41522289B4; Tue, 21 May 2019 12:49:18 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-8.0 required=2.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID,DKIM_VALID_AU,FREEMAIL_FROM,MAILING_LIST_MULTI,RCVD_IN_DNSWL_HI autolearn=ham version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id B5B932880A for ; Tue, 21 May 2019 12:49:17 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1727969AbfEUMtR (ORCPT ); Tue, 21 May 2019 08:49:17 -0400 Received: from mail-it1-f195.google.com ([209.85.166.195]:33173 "EHLO mail-it1-f195.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1727251AbfEUMtQ (ORCPT ); Tue, 21 May 2019 08:49:16 -0400 Received: by mail-it1-f195.google.com with SMTP id j17so2675175itk.0 for ; Tue, 21 May 2019 05:49:16 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:cc:subject:date:message-id:in-reply-to:references :mime-version:content-transfer-encoding; bh=oFdtiwK4kHqOG8CPwc58PSZjv/X3NKqeTWbmyNkVOvg=; b=E8bEfT/VlZVu4ergefhWlPxKpDpusHPsR3jOKPbubB1uUQuQNQ8/tVHueRrn+sBkke P2mAvJbIeAunE7mQm8Eb3VgDv1giro0qd4w/IzPdokcLKnAPAES1xUzPUYoF0/Nr0DWo 3duFdZYJpOnF0rzy0NkNQ7VmJEVAT+KLhQbsvdPhqeoBduCkfbd7FDge43gFDn5ikdOS 8FE4wXhyHFm2CY/VttRfC6dciUrtqtJMr7oIwQSTq8oyXedt+9mUMGglf+0yZemwWap0 bjaLiAIQ4J/OsiKSVt/hdctlg5X9P/Im2ykzKzxdELX7CpG0yRzk/rwNmSPTT7xgSWl1 qILg== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=oFdtiwK4kHqOG8CPwc58PSZjv/X3NKqeTWbmyNkVOvg=; b=tuIsAwVhTx+TcuvTmzotNE3gWXOHN+fGtO65+ZDw4uRMuU6zRLAKsYNFkiG7Btsd0v SCZ7dPUHEopFO01/XvKAF+sieT2dLtX9A1amPiOhgkPH39KXRDX3MYAoLNwjfM/+/pCt BEBpAwfYjiMmPcD+bnlv0uDt49ssCQsMBOPlqNpzmmO7a2zm7PczD+1GEXFMpDpVxpuf KZPiuy3Ahpeap1x9flImftLg+r7MO6cVnE/NOMKlHb0wYuJgKEmp/AWr092AOPNuwxli YiThzN0Iz3IJazuz4cVojPaNHv94KrvaTDs20UIhyL+HjjEQtlHmFXVZQixFzmO6qOzH 4+CA== X-Gm-Message-State: APjAAAW6v+mBCs98e9CyZl9q1sGtvivWh+tG4UqMxwKGEMWztHVSay3x lK4RHYslIdpafzuy2VPgDA== X-Google-Smtp-Source: APXvYqyqYlrhO27EW+o64Cw058gPdJT5wz2Wzr7HvqO9NGsD1TAV2g/z9JjAzUUigR5EXPuxoXgWNg== X-Received: by 2002:a24:5c90:: with SMTP id q138mr3216925itb.96.1558442955425; Tue, 21 May 2019 05:49:15 -0700 (PDT) Received: from localhost.localdomain (c-68-40-189-247.hsd1.mi.comcast.net. [68.40.189.247]) by smtp.gmail.com with ESMTPSA id v139sm1693180itb.25.2019.05.21.05.49.14 (version=TLS1_2 cipher=ECDHE-RSA-CHACHA20-POLY1305 bits=256/256); Tue, 21 May 2019 05:49:14 -0700 (PDT) From: Trond Myklebust X-Google-Original-From: Trond Myklebust To: SteveD@redhat.com Cc: linux-nfs@vger.kernel.org Subject: [RFC PATCH v2 4/7] Add a helper to return the real path given an export entry Date: Tue, 21 May 2019 08:46:58 -0400 Message-Id: <20190521124701.61849-5-trond.myklebust@hammerspace.com> X-Mailer: git-send-email 2.21.0 In-Reply-To: <20190521124701.61849-4-trond.myklebust@hammerspace.com> References: <20190521124701.61849-1-trond.myklebust@hammerspace.com> <20190521124701.61849-2-trond.myklebust@hammerspace.com> <20190521124701.61849-3-trond.myklebust@hammerspace.com> <20190521124701.61849-4-trond.myklebust@hammerspace.com> MIME-Version: 1.0 Sender: linux-nfs-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-nfs@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP Add a helper that can prepend the nfsd root directory path in order to allow mountd to perform its comparisons with mtab etc. Signed-off-by: Trond Myklebust --- support/export/export.c | 24 ++++++++++++++++++++++++ support/include/exportfs.h | 1 + support/include/nfslib.h | 1 + support/misc/nfsd_path.c | 4 +++- support/nfs/exports.c | 4 ++++ 5 files changed, 33 insertions(+), 1 deletion(-) diff --git a/support/export/export.c b/support/export/export.c index fbe68e84e5b3..229b02eb2dd4 100644 --- a/support/export/export.c +++ b/support/export/export.c @@ -20,6 +20,7 @@ #include "xmalloc.h" #include "nfslib.h" #include "exportfs.h" +#include "nfsd_path.h" exp_hash_table exportlist[MCL_MAXTYPES] = {{NULL, {{NULL,NULL}, }}, }; static int export_hash(char *); @@ -30,6 +31,28 @@ static void export_add(nfs_export *exp); static int export_check(const nfs_export *exp, const struct addrinfo *ai, const char *path); +/* Return a real path for the export. */ +static void +exportent_mkrealpath(struct exportent *eep) +{ + char *chroot = nfsd_path_nfsd_rootdir(); + char *ret = NULL; + + if (chroot) + ret = nfsd_path_prepend_dir(chroot, eep->e_path); + if (!ret) + ret = xstrdup(eep->e_path); + eep->e_realpath = ret; +} + +char * +exportent_realpath(struct exportent *eep) +{ + if (!eep->e_realpath) + exportent_mkrealpath(eep); + return eep->e_realpath; +} + void exportent_release(struct exportent *eep) { @@ -39,6 +62,7 @@ exportent_release(struct exportent *eep) free(eep->e_fslocdata); free(eep->e_uuid); xfree(eep->e_hostname); + xfree(eep->e_realpath); } static void diff --git a/support/include/exportfs.h b/support/include/exportfs.h index 4e0d9d132b4c..daa7e2a06d82 100644 --- a/support/include/exportfs.h +++ b/support/include/exportfs.h @@ -171,5 +171,6 @@ struct export_features { struct export_features *get_export_features(void); void fix_pseudoflavor_flags(struct exportent *ep); +char *exportent_realpath(struct exportent *eep); #endif /* EXPORTFS_H */ diff --git a/support/include/nfslib.h b/support/include/nfslib.h index b09fce42e677..84d8270b330f 100644 --- a/support/include/nfslib.h +++ b/support/include/nfslib.h @@ -84,6 +84,7 @@ struct exportent { char * e_uuid; struct sec_entry e_secinfo[SECFLAVOR_COUNT+1]; unsigned int e_ttl; + char * e_realpath; }; struct rmtabent { diff --git a/support/misc/nfsd_path.c b/support/misc/nfsd_path.c index 481ba49a38fd..386b171f26df 100644 --- a/support/misc/nfsd_path.c +++ b/support/misc/nfsd_path.c @@ -77,9 +77,11 @@ nfsd_path_prepend_dir(const char *dir, const char *pathname) dirlen--; if (!dirlen) return NULL; + while (pathname[0] == '/') + pathname++; len = dirlen + strlen(pathname) + 1; ret = xmalloc(len + 1); - snprintf(ret, len, "%.*s/%s", (int)dirlen, dir, pathname); + snprintf(ret, len+1, "%.*s/%s", (int)dirlen, dir, pathname); return ret; } diff --git a/support/nfs/exports.c b/support/nfs/exports.c index 5f4cb9568814..3ecfde797e3b 100644 --- a/support/nfs/exports.c +++ b/support/nfs/exports.c @@ -155,6 +155,7 @@ getexportent(int fromkernel, int fromexports) } xfree(ee.e_hostname); + xfree(ee.e_realpath); ee = def_ee; /* Check for default client */ @@ -358,6 +359,7 @@ dupexportent(struct exportent *dst, struct exportent *src) if (src->e_uuid) dst->e_uuid = strdup(src->e_uuid); dst->e_hostname = NULL; + dst->e_realpath = NULL; } struct exportent * @@ -369,6 +371,8 @@ mkexportent(char *hname, char *path, char *options) xfree(ee.e_hostname); ee.e_hostname = xstrdup(hname); + xfree(ee.e_realpath); + ee.e_realpath = NULL; if (strlen(path) >= sizeof(ee.e_path)) { xlog(L_ERROR, "path name %s too long", path); From patchwork Tue May 21 12:46:59 2019 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Trond Myklebust X-Patchwork-Id: 10953599 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 5FB781708 for ; Tue, 21 May 2019 12:49:19 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 4E2B92880A for ; Tue, 21 May 2019 12:49:19 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 42CA328849; Tue, 21 May 2019 12:49:19 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-8.0 required=2.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID,DKIM_VALID_AU,FREEMAIL_FROM,MAILING_LIST_MULTI,RCVD_IN_DNSWL_HI autolearn=ham version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id D5C5B288B6 for ; Tue, 21 May 2019 12:49:17 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1727251AbfEUMtR (ORCPT ); Tue, 21 May 2019 08:49:17 -0400 Received: from mail-io1-f66.google.com ([209.85.166.66]:40470 "EHLO mail-io1-f66.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1727812AbfEUMtR (ORCPT ); Tue, 21 May 2019 08:49:17 -0400 Received: by mail-io1-f66.google.com with SMTP id s20so13805603ioj.7 for ; Tue, 21 May 2019 05:49:16 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:cc:subject:date:message-id:in-reply-to:references :mime-version:content-transfer-encoding; bh=Yvd08hZwHj0WOPQBOc8y50kIfDMDBLgAaLTQJ0rzgHI=; b=GXaPovFIJim8v98IAUpOcLr0FYjbv6i8loTCe6jrTYL2Olw0ZWhqboVf/5Os2eBfEW cCTvIqe+8/7CITaPLn/5SyuftFHNtWKru47AzcIHIIJmAc3TeSBAFge59sHEL5eMdDzf /m0e/+Z7HAfV3k+RnISUi1wTVMO/pq3V1TsRRKkixaz89ZJSaQqSByKb5yZWx+gjYHqZ eTU7rkMZlhdsrrSvEtAnl9o6/6feqI/7ygPVr6k/5LqP6TC9LdEpRpvEhpdos/lY/6fd CVvLLJmhiIYXMuGuURoPQobWh6qIiqvgUTyvDYWgXgGweVklRIhtSXBYSh8NkRlDxVzI twtg== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=Yvd08hZwHj0WOPQBOc8y50kIfDMDBLgAaLTQJ0rzgHI=; b=LpBh03RKniWSLcR89J8epV+TSUo72HqMGvnAIV1r6LmQlrEoybrGZUNKSl5p6VCs9t b5vtagEEn6uNp3a3Ev0B8GTg2KLApsUr4Fca4xExu0y8vOMEKLQrPJzQ51VKx5e6DNPm yE2IvPgQ4TfYw48BzK89523MP74wCYuG2xwc0G7LIhVcP80UiYoQVriEflxkDZ2SDBwD Yuw4atYMso3Mi4egDp51RCGqS/YGME0QIf817wib5d65I/NIZm8rzTyREAgYDu4niYL+ bFErXLyBj7SoFrTFleqGLe/BIKx4rXUtPXuJp4inl/Xkc+xWJRork6o/sh65T2CeXeD6 HBFQ== X-Gm-Message-State: APjAAAVkcciUBM3tdqrrrFIVGvr53Tgnz4jkr3SKlx1rzNv7/ajSKIWn B+N64QRc2pjeDCPqw3koZg== X-Google-Smtp-Source: APXvYqw0e0iKuYjH4hlRYJQpg9Gfd2hS/ZddNLAu19uON94c59fr/UxK+eZ4iaEyGxYWvK3hB8s1Iw== X-Received: by 2002:a6b:e90e:: with SMTP id u14mr12705470iof.121.1558442956123; Tue, 21 May 2019 05:49:16 -0700 (PDT) Received: from localhost.localdomain (c-68-40-189-247.hsd1.mi.comcast.net. [68.40.189.247]) by smtp.gmail.com with ESMTPSA id v139sm1693180itb.25.2019.05.21.05.49.15 (version=TLS1_2 cipher=ECDHE-RSA-CHACHA20-POLY1305 bits=256/256); Tue, 21 May 2019 05:49:15 -0700 (PDT) From: Trond Myklebust X-Google-Original-From: Trond Myklebust To: SteveD@redhat.com Cc: linux-nfs@vger.kernel.org Subject: [RFC PATCH v2 5/7] Add helpers to read/write to a file through the chrooted thread Date: Tue, 21 May 2019 08:46:59 -0400 Message-Id: <20190521124701.61849-6-trond.myklebust@hammerspace.com> X-Mailer: git-send-email 2.21.0 In-Reply-To: <20190521124701.61849-5-trond.myklebust@hammerspace.com> References: <20190521124701.61849-1-trond.myklebust@hammerspace.com> <20190521124701.61849-2-trond.myklebust@hammerspace.com> <20190521124701.61849-3-trond.myklebust@hammerspace.com> <20190521124701.61849-4-trond.myklebust@hammerspace.com> <20190521124701.61849-5-trond.myklebust@hammerspace.com> MIME-Version: 1.0 Sender: linux-nfs-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-nfs@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP Add helper functions to do synchronous I/O to a file from inside the chrooted environment. This ensures that calls to kern_path() in the kernel resolves to paths that are relative to the nfsd root directory. Signed-off-by: Trond Myklebust --- support/include/workqueue.h | 4 ++ support/misc/workqueue.c | 78 +++++++++++++++++++++++++++++++++++++ 2 files changed, 82 insertions(+) diff --git a/support/include/workqueue.h b/support/include/workqueue.h index 518be82f1b34..21b1ee6bc873 100644 --- a/support/include/workqueue.h +++ b/support/include/workqueue.h @@ -15,4 +15,8 @@ void xthread_work_run_sync(struct xthread_workqueue *wq, void xthread_workqueue_chroot(struct xthread_workqueue *wq, const char *path); +ssize_t xthread_read(struct xthread_workqueue *wq, + int fd, char *buf, size_t len); +ssize_t xthread_write(struct xthread_workqueue *wq, + int fd, const char *buf, size_t len); #endif diff --git a/support/misc/workqueue.c b/support/misc/workqueue.c index b8d03446f2c7..9d967cef6547 100644 --- a/support/misc/workqueue.c +++ b/support/misc/workqueue.c @@ -1,3 +1,4 @@ +#include #include #include @@ -197,6 +198,72 @@ void xthread_workqueue_chroot(struct xthread_workqueue *wq, xthread_work_run_sync(wq, xthread_workqueue_do_chroot, (void *)path); } +struct xthread_read_data { + int fd; + char *buf; + size_t len; + ssize_t ret; + int err; +}; + +static void xthread_readfunc(void *data) +{ + struct xthread_read_data *d = data; + + d->ret = read(d->fd, d->buf, d->len); + if (d->ret < 0) + d->err = errno; +} + +ssize_t xthread_read(struct xthread_workqueue *wq, + int fd, char *buf, size_t len) +{ + struct xthread_read_data data = { + fd, + buf, + len, + 0, + 0 + }; + xthread_work_run_sync(wq, xthread_readfunc, &data); + if (data.ret < 0) + errno = data.err; + return data.ret; +} + +struct xthread_write_data { + int fd; + const char *buf; + size_t len; + ssize_t ret; + int err; +}; + +static void xthread_writefunc(void *data) +{ + struct xthread_write_data *d = data; + + d->ret = write(d->fd, d->buf, d->len); + if (d->ret < 0) + d->err = errno; +} + +ssize_t xthread_write(struct xthread_workqueue *wq, + int fd, const char *buf, size_t len) +{ + struct xthread_write_data data = { + fd, + buf, + len, + 0, + 0 + }; + xthread_work_run_sync(wq, xthread_writefunc, &data); + if (data.ret < 0) + errno = data.err; + return data.ret; +} + #else struct xthread_workqueue { @@ -225,4 +292,15 @@ void xthread_workqueue_chroot(struct xthread_workqueue *wq, xlog_err("Unable to run as chroot"); } +ssize_t xthread_read(struct xthread_workqueue *wq, + int fd, char *buf, size_t len) +{ + return read(fd, buf, len); +} + +ssize_t xthread_write(struct xthread_workqueue *wq, + int fd, const char *buf, size_t len) +{ + return write(fd, buf, len); +} #endif /* defined(HAVE_SCHED_H) && defined(HAVE_LIBPTHREAD) && defined(HAVE_UNSHARE) */ From patchwork Tue May 21 12:47:00 2019 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Trond Myklebust X-Patchwork-Id: 10953601 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 8BC7213AD for ; Tue, 21 May 2019 12:49:20 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 7B3AF2880A for ; Tue, 21 May 2019 12:49:20 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 70089288D0; Tue, 21 May 2019 12:49:20 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-8.0 required=2.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID,DKIM_VALID_AU,FREEMAIL_FROM,MAILING_LIST_MULTI,RCVD_IN_DNSWL_HI autolearn=ham version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 999892880A for ; Tue, 21 May 2019 12:49:19 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1727976AbfEUMtT (ORCPT ); Tue, 21 May 2019 08:49:19 -0400 Received: from mail-io1-f67.google.com ([209.85.166.67]:36744 "EHLO mail-io1-f67.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1727812AbfEUMtS (ORCPT ); Tue, 21 May 2019 08:49:18 -0400 Received: by mail-io1-f67.google.com with SMTP id e19so13833559iob.3 for ; Tue, 21 May 2019 05:49:17 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:cc:subject:date:message-id:in-reply-to:references :mime-version:content-transfer-encoding; bh=GLr9Jev1vzFH2WxtXzDL6iC0Z9XJSGhBflc8iGqtz0M=; b=mbbuhIXgMro0QiEdIcNthIsiAgUwKUBuf2Zw+JLwUXUv0sNL9T8iuKWQ9iYDIkcfAt TJ9kKymKSNA3aDP316rKyshzA9Lce+5fXTpPdSUvmCnJkGd5XZkl+HTdPZvfQvDZ9KCu pKQVor/+Q1vLuPuYYBsjtCNd0LuAwH2JKvpZlt/m2lYVjfZ/4lPksF0jvJeEisxAe9sP 6NRsngRGaljQa6fp1KSwuHYdWsSpSdOK6mGnHO49QOrELFKj5wj7yk3yEovYqGzK4Md1 LfR3kMxuQTqmbylfwLSkkJvhDtwlXQ01cPmeDa3jWLPFzeR7xRZwIBqG+VNW0tFe72rw zp+A== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=GLr9Jev1vzFH2WxtXzDL6iC0Z9XJSGhBflc8iGqtz0M=; b=WSIU3lKMXfj2Z9t6zlN0dXV6X24covVznbuKLGksas98s48tYEc7+xM+eRGggv0Zic gGuvS2jM8HFoTjgVJTK5W+d5OojMoSTv0P7e3TiJUkQnEL7RudWTs/Pwu+OmPCqF+IYE E8M06orWCZ56Knrb/66gkOak1oJEld91WAHcQojOySqjtIB7+zMOXwRLgcLCT4LftKWl L5RePRVlpFyyVn3cCoZoU6mUawqei0Iaby4UxJ3wErRiAfB6+GAidYbhU8CqIxuakuVe UM5tUPxNkhT/9e07Oq3LCetHZUvpCa++kTkL5LMC/gM5CcFLl1t7EVLubkVvnHx3N5T2 N2xw== X-Gm-Message-State: APjAAAXqja3kwo4fs3/WpLJIMZIHXe3/kTKjvyA8YbqID6jHrB9YSlp+ JfU5Mu+gzi2Atqrc2xLmo3ZTda4= X-Google-Smtp-Source: APXvYqyDwurOJsnLd5Jq8g2sjUxAnz1sR7lENjUfEPMG/DoP77TusXDwVIZVFXz/HeD4zwQZsvzqag== X-Received: by 2002:a5e:d50e:: with SMTP id e14mr10541868iom.224.1558442956868; Tue, 21 May 2019 05:49:16 -0700 (PDT) Received: from localhost.localdomain (c-68-40-189-247.hsd1.mi.comcast.net. [68.40.189.247]) by smtp.gmail.com with ESMTPSA id v139sm1693180itb.25.2019.05.21.05.49.16 (version=TLS1_2 cipher=ECDHE-RSA-CHACHA20-POLY1305 bits=256/256); Tue, 21 May 2019 05:49:16 -0700 (PDT) From: Trond Myklebust X-Google-Original-From: Trond Myklebust To: SteveD@redhat.com Cc: linux-nfs@vger.kernel.org Subject: [RFC PATCH v2 6/7] Add support for the nfsd rootdir configuration option to rpc.mountd Date: Tue, 21 May 2019 08:47:00 -0400 Message-Id: <20190521124701.61849-7-trond.myklebust@hammerspace.com> X-Mailer: git-send-email 2.21.0 In-Reply-To: <20190521124701.61849-6-trond.myklebust@hammerspace.com> References: <20190521124701.61849-1-trond.myklebust@hammerspace.com> <20190521124701.61849-2-trond.myklebust@hammerspace.com> <20190521124701.61849-3-trond.myklebust@hammerspace.com> <20190521124701.61849-4-trond.myklebust@hammerspace.com> <20190521124701.61849-5-trond.myklebust@hammerspace.com> <20190521124701.61849-6-trond.myklebust@hammerspace.com> MIME-Version: 1.0 Sender: linux-nfs-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-nfs@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP Ensure that I/O to those pseudo files that resolve filehandles and exports go through the chrooted threads, so that we can use paths that are relative to the nfsd root directory. Ensure that any stat() or lstat() calls go through their nfsd_path_* equivalent so that they too can be resolved correctly. Signed-off-by: Trond Myklebust --- nfs.conf | 1 + support/misc/mountpoint.c | 5 ++- systemd/nfs.conf.man | 3 +- utils/mountd/cache.c | 79 ++++++++++++++++++++++++++++----------- utils/mountd/mountd.c | 8 ++-- utils/nfsd/nfsd.man | 6 +++ 6 files changed, 74 insertions(+), 28 deletions(-) diff --git a/nfs.conf b/nfs.conf index 27e962c8a2a9..4d3bc512c4be 100644 --- a/nfs.conf +++ b/nfs.conf @@ -60,6 +60,7 @@ # vers4.1=y # vers4.2=y # rdma=n +# root_dir=/export # [statd] # debug=0 diff --git a/support/misc/mountpoint.c b/support/misc/mountpoint.c index 9f9ce44ec1e3..9723dcede79d 100644 --- a/support/misc/mountpoint.c +++ b/support/misc/mountpoint.c @@ -7,6 +7,7 @@ #include "xcommon.h" #include #include "misc.h" +#include "nfsd_path.h" int is_mountpoint(char *path) @@ -26,8 +27,8 @@ is_mountpoint(char *path) dotdot = xmalloc(strlen(path)+4); strcat(strcpy(dotdot, path), "/.."); - if (lstat(path, &stb) != 0 || - lstat(dotdot, &pstb) != 0) + if (nfsd_path_lstat(path, &stb) != 0 || + nfsd_path_lstat(dotdot, &pstb) != 0) rv = 0; else if (stb.st_dev != pstb.st_dev || diff --git a/systemd/nfs.conf.man b/systemd/nfs.conf.man index e3654a3c2c2b..a88799769365 100644 --- a/systemd/nfs.conf.man +++ b/systemd/nfs.conf.man @@ -136,7 +136,8 @@ Recognized values: .BR vers4.0 , .BR vers4.1 , .BR vers4.2 , -.BR rdma . +.BR rdma , +.BR root_dir . Version and protocol values are Boolean values as described above, and are also used by diff --git a/utils/mountd/cache.c b/utils/mountd/cache.c index bdbd1904eb76..6e15ecd986aa 100644 --- a/utils/mountd/cache.c +++ b/utils/mountd/cache.c @@ -27,17 +27,21 @@ #include #include #include "misc.h" +#include "nfsd_path.h" #include "nfslib.h" #include "exportfs.h" #include "mountd.h" #include "fsloc.h" #include "pseudoflavors.h" +#include "workqueue.h" #include "xcommon.h" #ifdef USE_BLKID #include "blkid/blkid.h" #endif +static struct xthread_workqueue *cache_workqueue; + /* * Invoked by RPC service loop */ @@ -55,6 +59,34 @@ enum nfsd_fsid { FSID_UUID16_INUM, }; +static ssize_t cache_read(int fd, char *buf, size_t len) +{ + if (cache_workqueue) + return xthread_read(cache_workqueue, fd, buf, len); + return read(fd, buf, len); +} + +static ssize_t cache_write(int fd, const char *buf, size_t len) +{ + if (cache_workqueue) + return xthread_write(cache_workqueue, fd, buf, len); + return write(fd, buf, len); +} + +static void +cache_setup_workqueue(void) +{ + const char *chroot; + + chroot = nfsd_path_nfsd_rootdir(); + if (!chroot) + return; + cache_workqueue = xthread_workqueue_alloc(); + if (!cache_workqueue) + return; + xthread_workqueue_chroot(cache_workqueue, chroot); +} + /* * Support routines for text-based upcalls. * Fields are separated by spaces. @@ -221,7 +253,7 @@ static const char *get_uuid_blkdev(char *path) if (cache == NULL) blkid_get_cache(&cache, NULL); - if (stat(path, &stb) != 0) + if (nfsd_path_stat(path, &stb) != 0) return NULL; devname = blkid_devno_to_devname(stb.st_dev); if (!devname) @@ -373,21 +405,22 @@ static char *next_mnt(void **v, char *p) FILE *f; struct mntent *me; size_t l = strlen(p); + char *mnt_dir = NULL; + if (*v == NULL) { f = setmntent("/etc/mtab", "r"); *v = f; } else f = *v; - while ((me = getmntent(f)) != NULL && l > 1 && - (strncmp(me->mnt_dir, p, l) != 0 || - me->mnt_dir[l] != '/')) - ; - if (me == NULL) { - endmntent(f); - *v = NULL; - return NULL; + while ((me = getmntent(f)) != NULL && l > 1) { + mnt_dir = nfsd_path_strip_root(me->mnt_dir); + + if (strncmp(mnt_dir, p, l) == 0 && mnt_dir[l] != '/') + return mnt_dir; } - return me->mnt_dir; + endmntent(f); + *v = NULL; + return NULL; } /* same_path() check is two paths refer to the same directory. @@ -458,9 +491,9 @@ fallback: * bind-mounted in two places and both are exported, it * could give a false positive */ - if (lstat(p, &sc) != 0) + if (nfsd_path_lstat(p, &sc) != 0) return 0; - if (lstat(parent, &sp) != 0) + if (nfsd_path_lstat(parent, &sp) != 0) return 0; if (sc.st_dev != sp.st_dev) return 0; @@ -610,7 +643,7 @@ static bool match_fsid(struct parsed_fsid *parsed, nfs_export *exp, char *path) int type; char u[16]; - if (stat(path, &stb) != 0) + if (nfsd_path_stat(path, &stb) != 0) return false; if (!S_ISDIR(stb.st_mode) && !S_ISREG(stb.st_mode)) return false; @@ -692,7 +725,7 @@ static void nfsd_fh(int f) char buf[RPC_CHAN_BUF_SIZE], *bp; int blen; - blen = read(f, buf, sizeof(buf)); + blen = cache_read(f, buf, sizeof(buf)); if (blen <= 0 || buf[blen-1] != '\n') return; buf[blen-1] = 0; @@ -829,7 +862,7 @@ static void nfsd_fh(int f) if (found) qword_add(&bp, &blen, found_path); qword_addeol(&bp, &blen); - if (blen <= 0 || write(f, buf, bp - buf) != bp - buf) + if (blen <= 0 || cache_write(f, buf, bp - buf) != bp - buf) xlog(L_ERROR, "nfsd_fh: error writing reply"); out: if (found_path) @@ -921,7 +954,7 @@ static int dump_to_cache(int f, char *buf, int buflen, char *domain, qword_adduint(&bp, &blen, now + ttl); qword_addeol(&bp, &blen); if (blen <= 0) return -1; - if (write(f, buf, bp - buf) != bp - buf) return -1; + if (cache_write(f, buf, bp - buf) != bp - buf) return -1; return 0; } @@ -1298,7 +1331,7 @@ static void nfsd_export(int f) char buf[RPC_CHAN_BUF_SIZE], *bp; int blen; - blen = read(f, buf, sizeof(buf)); + blen = cache_read(f, buf, sizeof(buf)); if (blen <= 0 || buf[blen-1] != '\n') return; buf[blen-1] = 0; @@ -1381,6 +1414,8 @@ extern int manage_gids; void cache_open(void) { int i; + + cache_setup_workqueue(); for (i=0; cachelist[i].cache_name; i++ ) { char path[100]; if (!manage_gids && cachelist[i].cache_handle == auth_unix_gid) @@ -1456,7 +1491,7 @@ static int cache_export_ent(char *buf, int buflen, char *domain, struct exporten if (strlen(path) <= l || path[l] != '/' || strncmp(exp->e_path, path, l) != 0) break; - if (stat(exp->e_path, &stb) != 0) + if (nfsd_path_stat(exp->e_path, &stb) != 0) break; dev = stb.st_dev; while(path[l] == '/') { @@ -1469,7 +1504,7 @@ static int cache_export_ent(char *buf, int buflen, char *domain, struct exporten l++; c = path[l]; path[l] = 0; - err2 = lstat(path, &stb); + err2 = nfsd_path_lstat(path, &stb); path[l] = c; if (err2 < 0) break; @@ -1508,7 +1543,7 @@ int cache_export(nfs_export *exp, char *path) qword_adduint(&bp, &blen, time(0) + exp->m_export.e_ttl); qword_add(&bp, &blen, exp->m_client->m_hostname); qword_addeol(&bp, &blen); - if (blen <= 0 || write(f, buf, bp - buf) != bp - buf) blen = -1; + if (blen <= 0 || cache_write(f, buf, bp - buf) != bp - buf) blen = -1; close(f); if (blen < 0) return -1; @@ -1546,12 +1581,12 @@ cache_get_filehandle(nfs_export *exp, int len, char *p) qword_add(&bp, &blen, p); qword_addint(&bp, &blen, len); qword_addeol(&bp, &blen); - if (blen <= 0 || write(f, buf, bp - buf) != bp - buf) { + if (blen <= 0 || cache_write(f, buf, bp - buf) != bp - buf) { close(f); return NULL; } bp = buf; - blen = read(f, buf, sizeof(buf)); + blen = cache_read(f, buf, sizeof(buf)); close(f); if (blen <= 0 || buf[blen-1] != '\n') diff --git a/utils/mountd/mountd.c b/utils/mountd/mountd.c index 88a207b3a85a..db9891269051 100644 --- a/utils/mountd/mountd.c +++ b/utils/mountd/mountd.c @@ -29,6 +29,7 @@ #include "mountd.h" #include "rpcmisc.h" #include "pseudoflavors.h" +#include "nfsd_path.h" #include "nfslib.h" extern void my_svc_run(void); @@ -374,7 +375,7 @@ mount_pathconf_2_svc(struct svc_req *rqstp, dirpath *path, ppathcnf *res) exp = auth_authenticate("pathconf", sap, p); if (exp == NULL) return 1; - else if (stat(p, &stb) < 0) { + else if (nfsd_path_stat(p, &stb) < 0) { xlog(L_WARNING, "can't stat exported dir %s: %s", p, strerror(errno)); return 1; @@ -483,7 +484,7 @@ get_rootfh(struct svc_req *rqstp, dirpath *path, nfs_export **expret, *error = MNT3ERR_ACCES; return NULL; } - if (stat(p, &stb) < 0) { + if (nfsd_path_stat(p, &stb) < 0) { xlog(L_WARNING, "can't stat exported dir %s: %s", p, strerror(errno)); if (errno == ENOENT) @@ -497,7 +498,7 @@ get_rootfh(struct svc_req *rqstp, dirpath *path, nfs_export **expret, *error = MNT3ERR_NOTDIR; return NULL; } - if (stat(exp->m_export.e_path, &estb) < 0) { + if (nfsd_path_stat(exp->m_export.e_path, &estb) < 0) { xlog(L_WARNING, "can't stat export point %s: %s", p, strerror(errno)); *error = MNT3ERR_NOENT; @@ -886,6 +887,7 @@ main(int argc, char **argv) if (num_threads > 1) fork_workers(); + nfsd_path_init(); /* Open files now to avoid sharing descriptors among forked processes */ cache_open(); diff --git a/utils/nfsd/nfsd.man b/utils/nfsd/nfsd.man index d83ef869d26e..1f3bdf75a2b4 100644 --- a/utils/nfsd/nfsd.man +++ b/utils/nfsd/nfsd.man @@ -167,6 +167,12 @@ Setting these to "off" or similar will disable the selected minor versions. Setting to "on" will enable them. The default values are determined by the kernel, and usually minor versions default to being enabled once the implementation is sufficiently complete. +.B root_dir +Setting this to a valid path causes the nfs server to act as if the +supplied path is being prefixed to all the exported entries. For +instance, if "root_dir=/my/root", and there is an entry in /etc/exports +for '/filesystem', then the client can mount '/filesystem', but the +actual path on the server will resolve to '/my/root/filesystem'. .SH NOTES If the program is built with TI-RPC support, it will enable any protocol and From patchwork Tue May 21 12:47:01 2019 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Trond Myklebust X-Patchwork-Id: 10953603 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id B1AA61708 for ; Tue, 21 May 2019 12:49:20 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id A220B2880A for ; Tue, 21 May 2019 12:49:20 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 96B2D288B6; Tue, 21 May 2019 12:49:20 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-8.0 required=2.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID,DKIM_VALID_AU,FREEMAIL_FROM,MAILING_LIST_MULTI,RCVD_IN_DNSWL_HI autolearn=ham version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 2FC9F28849 for ; Tue, 21 May 2019 12:49:20 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1727812AbfEUMtT (ORCPT ); Tue, 21 May 2019 08:49:19 -0400 Received: from mail-it1-f195.google.com ([209.85.166.195]:52019 "EHLO mail-it1-f195.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1727624AbfEUMtS (ORCPT ); Tue, 21 May 2019 08:49:18 -0400 Received: by mail-it1-f195.google.com with SMTP id m3so4723758itl.1 for ; Tue, 21 May 2019 05:49:18 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:cc:subject:date:message-id:in-reply-to:references :mime-version:content-transfer-encoding; bh=y0J7r1j+ktNhdVDgcbWhWVBMoXoEOq9RiXDpoM7+ALM=; b=bHcOW+Eh2FxwiVt7kYYa/RNhwl9ArM0nb7cKvLLzLWBHF2OIoqMu798PYR4UcBptMH KTGexYjrOQqml+P7fYvqLklPS92d+JtmIgeu6Q+vvtXOo4iT03aM43cFKLQxcW/wBZGG Imf0bwNFyvg0Np52lXqdNqys6zKB0OZpzL4gNijiohyCuL69tyOZfkM9P4MskS6m/YU6 TAVbv4Vxd0XkU0kncgtakC4GVhDA4YpoeH1xaFUyR60C+QmjPkldXiHJVxXcTQz/1vnw fWAv/SJTPsFxHJpnLCVS//IAKcEhfkXS2nCnOaFbSy8G2EhXV/moMgYPDJvep/kHCYX9 YT4Q== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=y0J7r1j+ktNhdVDgcbWhWVBMoXoEOq9RiXDpoM7+ALM=; b=CLum99fjfZIDqH75kVfPruyiML4j8pu5gUfM3UumCk5X0d9inOXw64fHd3pdhbzHCv JHCfA2Gx5woTTcx2z8iVGEs0OzysnnQENCTfeeCcPCWlCbW30hGyFIDdG8gtHXXzPSPn olKl+eiOilYZwj65b4m90wSmS8HsnOBZ12bUj/ssXl6VP+sIqPp9VRYkVuG6yJgwjOMp 33zO3/9p2sjEWZJYalukNQVJqu78yxlEmWlqnAx8sYY7S0umbvBzE0j+81JKqk7/hMXX rPhFfSXwqwbjPvtwmFkkaXp12cdpaiwUAYFBRoL5ChsXU4GD/Q82dqJ+9DL1ba7bXtgk W1eA== X-Gm-Message-State: APjAAAXDi+VWmT1TkSmPT5J5QifBTG5zNm9ld9FTzuIB8w02xoV+LKu1 WogHtWOoBbuWYS1bOOoe1Q== X-Google-Smtp-Source: APXvYqzr6yxkBn3ctXMdIM3Noi4U4r3/L452G6E4X4ufIgvpLgEuHuioqW7yDKEz4/WnfXfOmdXHdA== X-Received: by 2002:a24:9187:: with SMTP id i129mr3583451ite.137.1558442957752; Tue, 21 May 2019 05:49:17 -0700 (PDT) Received: from localhost.localdomain (c-68-40-189-247.hsd1.mi.comcast.net. [68.40.189.247]) by smtp.gmail.com with ESMTPSA id v139sm1693180itb.25.2019.05.21.05.49.16 (version=TLS1_2 cipher=ECDHE-RSA-CHACHA20-POLY1305 bits=256/256); Tue, 21 May 2019 05:49:17 -0700 (PDT) From: Trond Myklebust X-Google-Original-From: Trond Myklebust To: SteveD@redhat.com Cc: linux-nfs@vger.kernel.org Subject: [RFC PATCH v2 7/7] Add support for the nfsd root directory to exportfs Date: Tue, 21 May 2019 08:47:01 -0400 Message-Id: <20190521124701.61849-8-trond.myklebust@hammerspace.com> X-Mailer: git-send-email 2.21.0 In-Reply-To: <20190521124701.61849-7-trond.myklebust@hammerspace.com> References: <20190521124701.61849-1-trond.myklebust@hammerspace.com> <20190521124701.61849-2-trond.myklebust@hammerspace.com> <20190521124701.61849-3-trond.myklebust@hammerspace.com> <20190521124701.61849-4-trond.myklebust@hammerspace.com> <20190521124701.61849-5-trond.myklebust@hammerspace.com> <20190521124701.61849-6-trond.myklebust@hammerspace.com> <20190521124701.61849-7-trond.myklebust@hammerspace.com> MIME-Version: 1.0 Sender: linux-nfs-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-nfs@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP Ensure that exportfs also resolves paths relative to the nfsd root directory Signed-off-by: Trond Myklebust --- utils/exportfs/Makefile.am | 2 +- utils/exportfs/exportfs.c | 32 ++++++++++++++++++++++++++++++-- 2 files changed, 31 insertions(+), 3 deletions(-) diff --git a/utils/exportfs/Makefile.am b/utils/exportfs/Makefile.am index 4b291610d19b..96524c729359 100644 --- a/utils/exportfs/Makefile.am +++ b/utils/exportfs/Makefile.am @@ -10,6 +10,6 @@ exportfs_SOURCES = exportfs.c exportfs_LDADD = ../../support/export/libexport.a \ ../../support/nfs/libnfs.la \ ../../support/misc/libmisc.a \ - $(LIBWRAP) $(LIBNSL) + $(LIBWRAP) $(LIBNSL) $(LIBPTHREAD) MAINTAINERCLEANFILES = Makefile.in diff --git a/utils/exportfs/exportfs.c b/utils/exportfs/exportfs.c index 333eadcd0228..05481ad3f896 100644 --- a/utils/exportfs/exportfs.c +++ b/utils/exportfs/exportfs.c @@ -33,8 +33,10 @@ #include "sockaddr.h" #include "misc.h" +#include "nfsd_path.h" #include "nfslib.h" #include "exportfs.h" +#include "workqueue.h" #include "xlog.h" #include "conffile.h" @@ -52,6 +54,29 @@ static const char *lockfile = EXP_LOCKFILE; static int _lockfd = -1; struct state_paths etab; +static struct xthread_workqueue *exportfs_wq; + +static ssize_t exportfs_write(int fd, const char *buf, size_t len) +{ + if (exportfs_wq) + return xthread_write(exportfs_wq, fd, buf, len); + return write(fd, buf, len); +} + +static void +exportfs_setup_workqueue(void) +{ + const char *chroot = nfsd_path_nfsd_rootdir(); + + if (!chroot || chroot[0] == '\0') + return; + if (chroot[0] == '/' && chroot[1] == '\0') + return; + exportfs_wq = xthread_workqueue_alloc(); + if (!exportfs_wq) + return; + xthread_workqueue_chroot(exportfs_wq, chroot); +} /* * If we aren't careful, changes made by exportfs can be lost @@ -109,6 +134,7 @@ main(int argc, char **argv) conf_init_file(NFS_CONFFILE); xlog_from_conffile("exportfs"); + nfsd_path_init(); /* NOTE: following uses "mountd" section of nfs.conf !!!! */ s = conf_get_str("mountd", "state-directory-path"); @@ -181,6 +207,8 @@ main(int argc, char **argv) } } + exportfs_setup_workqueue(); + /* * Serialize things as best we can */ @@ -505,7 +533,7 @@ static int test_export(nfs_export *exp, int with_fsid) fd = open("/proc/net/rpc/nfsd.export/channel", O_WRONLY); if (fd < 0) return 0; - n = write(fd, buf, strlen(buf)); + n = exportfs_write(fd, buf, strlen(buf)); close(fd); if (n < 0) return 0; @@ -521,7 +549,7 @@ validate_export(nfs_export *exp) * otherwise trial-export to '-test-client-' and check for failure. */ struct stat stb; - char *path = exp->m_export.e_path; + char *path = exportent_realpath(&exp->m_export); struct statfs64 stf; int fs_has_fsid = 0;