summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorCyril Plisko <[email protected]>2012-09-05 19:44:53 +0300
committerBrian Behlendorf <[email protected]>2012-09-11 10:21:49 -0700
commit27ccd4147bd29e9334c57a08d99481447a19c82f (patch)
treed7018d2a975fd6ee73b93e2cae7f384cfae3c616
parentaf909a1089b35ae527a90c222453c977c4beff62 (diff)
Avoid running exportfs on each zfs/zpool command invocation
Delay executing exportfs command until its results are actually required. Signed-off-by: Cyril Plisko <[email protected]> Signed-off-by: Gunnar Beutner <[email protected]> Signed-off-by: Brian Behlendorf <[email protected]>
-rw-r--r--lib/libshare/nfs.c39
1 files changed, 30 insertions, 9 deletions
diff --git a/lib/libshare/nfs.c b/lib/libshare/nfs.c
index 56725d27c..53691ebe5 100644
--- a/lib/libshare/nfs.c
+++ b/lib/libshare/nfs.c
@@ -22,6 +22,7 @@
/*
* Copyright (c) 2002, 2010, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2011 Gunnar Beutner
+ * Copyright (c) 2012 Cyril Plisko. All rights reserved.
*/
#include <stdio.h>
@@ -33,8 +34,9 @@
#include <libshare.h>
#include "libshare_impl.h"
+static boolean_t nfs_available(void);
+
static sa_fstype_t *nfs_fstype;
-static boolean_t nfs_available;
/*
* nfs_exportfs_temp_fd refers to a temporary copy of the output
@@ -407,7 +409,7 @@ nfs_enable_share(sa_share_impl_t impl_share)
char *shareopts, *linux_opts;
int rc;
- if (!nfs_available) {
+ if (!nfs_available()) {
return SA_SYSTEM_ERR;
}
@@ -480,7 +482,7 @@ nfs_disable_share_one(const char *sharepath, const char *host,
static int
nfs_disable_share(sa_share_impl_t impl_share)
{
- if (!nfs_available) {
+ if (!nfs_available()) {
/*
* The share can't possibly be active, so nothing
* needs to be done to disable it.
@@ -520,7 +522,7 @@ is_share_active(sa_share_impl_t impl_share)
char *tab, *cur;
FILE *nfs_exportfs_temp_fp;
- if (nfs_exportfs_temp_fd < 0)
+ if (!nfs_available())
return B_FALSE;
nfs_exportfs_temp_fp = fdopen(dup(nfs_exportfs_temp_fd), "r");
@@ -671,18 +673,27 @@ nfs_check_exportfs(void)
pid = fork();
- if (pid < 0)
+ if (pid < 0) {
+ (void) close(nfs_exportfs_temp_fd);
+ nfs_exportfs_temp_fd = -1;
return SA_SYSTEM_ERR;
+ }
if (pid > 0) {
while ((rc = waitpid(pid, &status, 0)) <= 0 && errno == EINTR)
; /* empty loop body */
- if (rc <= 0)
+ if (rc <= 0) {
+ (void) close(nfs_exportfs_temp_fd);
+ nfs_exportfs_temp_fd = -1;
return SA_SYSTEM_ERR;
+ }
- if (!WIFEXITED(status) || WEXITSTATUS(status) != 0)
+ if (!WIFEXITED(status) || WEXITSTATUS(status) != 0) {
+ (void) close(nfs_exportfs_temp_fd);
+ nfs_exportfs_temp_fd = -1;
return SA_CONFIG_ERR;
+ }
return SA_OK;
}
@@ -703,13 +714,23 @@ nfs_check_exportfs(void)
exit(0);
}
+/*
+ * Provides a convenient wrapper for determing nfs availability
+ */
+static boolean_t
+nfs_available(void)
+{
+ if (nfs_exportfs_temp_fd == -1)
+ (void) nfs_check_exportfs();
+
+ return (nfs_exportfs_temp_fd != -1) ? B_TRUE : B_FALSE;
+}
+
/**
* Initializes the NFS functionality of libshare.
*/
void
libshare_nfs_init(void)
{
- nfs_available = (nfs_check_exportfs() == SA_OK);
-
nfs_fstype = register_fstype("nfs", &nfs_shareops);
}