From: Jeff Layton <jlayton(a)redhat.com>
Add a new command-line tool for manipulating and querying the rados_grace
database. It will dump out the state of the epochs and then a list of
omap keys and their flags.
Change-Id: If57591265ce736cdcebab749651d5ab6982341d8
Signed-off-by: Jeff Layton <jlayton(a)redhat.com>
---
src/nfs-ganesha.spec-in.cmake | 2 +
src/tools/CMakeLists.txt | 4 +
src/tools/rados_grace_tool.c | 178 ++++++++++++++++++++++++++++++++++
3 files changed, 184 insertions(+)
create mode 100644 src/tools/rados_grace_tool.c
diff --git a/src/nfs-ganesha.spec-in.cmake b/src/nfs-ganesha.spec-in.cmake
index e93973eda1f7..c55fad58c083 100644
--- a/src/nfs-ganesha.spec-in.cmake
+++ b/src/nfs-ganesha.spec-in.cmake
@@ -508,6 +508,7 @@ install -m 644 config_samples/xfs.conf
%{buildroot}%{_sysconfdir}/ganesha
%if %{with ceph}
install -m 644 config_samples/ceph.conf %{buildroot}%{_sysconfdir}/ganesha
+install -m 755 tools/rados_grace_tool %{buildroot}%{_sbindir}/rados_grace_tool
%endif
%if %{with rgw}
@@ -690,6 +691,7 @@ exit 0
%defattr(-,root,root,-)
%{_libdir}/ganesha/libfsalceph*
%config(noreplace) %{_sysconfdir}/ganesha/ceph.conf
+%{_sbindir}/rados_grace_tool
%if %{with man_page}
%{_mandir}/*/ganesha-ceph-config.8.gz
%endif
diff --git a/src/tools/CMakeLists.txt b/src/tools/CMakeLists.txt
index 7b536193568a..3856571f3ba1 100644
--- a/src/tools/CMakeLists.txt
+++ b/src/tools/CMakeLists.txt
@@ -1,3 +1,7 @@
+if (USE_RADOS_RECOV)
+ add_executable(rados_grace_tool rados_grace_tool.c)
+ target_link_libraries(rados_grace_tool rados_grace ${RADOS_LIBRARIES})
+endif(USE_RADOS_RECOV)
########### install files ###############
diff --git a/src/tools/rados_grace_tool.c b/src/tools/rados_grace_tool.c
new file mode 100644
index 000000000000..6cc15e8f3b38
--- /dev/null
+++ b/src/tools/rados_grace_tool.c
@@ -0,0 +1,178 @@
+/*
+ * vim:noexpandtab:shiftwidth=8:tabstop=8:
+ *
+ * Copyright 2017 Red Hat, Inc. and/or its affiliates.
+ * Author: Jeff Layton <jlayton(a)redhat.com>
+ *
+ * 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; either
+ * version 3 of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc.,
+ * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
+ *
+ * rados-grace: tool for managing coordinated grace period database
+ *
+ * This tool allows an administrator to make direct changes to the rados_grace
+ * database. See the rados_grace support library sources for more info about
+ * the internals.
+ */
+#include "config.h"
+#include <stdio.h>
+#include <stdint.h>
+#include <endian.h>
+#include <rados/librados.h>
+#include <errno.h>
+#include <getopt.h>
+#include <stdlib.h>
+#include <limits.h>
+#include <stdbool.h>
+#include <rados_grace.h>
+
+#define POOL_ID "nfs-ganesha"
+#define RADOS_GRACE_OID "grace"
+
+static int
+cluster_connect(rados_ioctx_t *io_ctx, const char *pool)
+{
+ int ret;
+ rados_t clnt;
+
+ ret = rados_create(&clnt, NULL);
+ if (ret < 0) {
+ fprintf(stderr, "rados_create: %d\n", ret);
+ return ret;
+ }
+
+ ret = rados_conf_read_file(clnt, NULL);
+ if (ret < 0) {
+ fprintf(stderr, "rados_conf_read_file: %d\n", ret);
+ return ret;
+ }
+
+ ret = rados_connect(clnt);
+ if (ret < 0) {
+ fprintf(stderr, "rados_connect: %d\n", ret);
+ return ret;
+ }
+
+ ret = rados_pool_create(clnt, pool);
+ if (ret < 0 && ret != -EEXIST) {
+ fprintf(stderr, "rados_pool_create: %d\n", ret);
+ return ret;
+ }
+
+ ret = rados_ioctx_create(clnt, pool, io_ctx);
+ if (ret < 0) {
+ fprintf(stderr, "rados_ioctx_create: %d\n", ret);
+ return ret;
+ }
+ return 0;
+}
+
+static void usage(const char **argv)
+{
+ fprintf(stderr,
+ "Usage:\n%s [dump|start|join|lift|remove|enforce|noenforce] [ nodeid ...
]\n",
+ argv[0]);
+}
+
+int main(int argc, const char **argv)
+{
+ int ret, nodes = 0;
+ rados_ioctx_t io_ctx;
+ const char *cmd = "dump";
+ uint64_t cur, rec;
+
+ if (argc > 1) {
+ cmd = argv[1];
+ nodes = argc - 2;
+ }
+
+ ret = cluster_connect(&io_ctx, POOL_ID);
+ if (ret) {
+ fprintf(stderr, "Can't connect to cluster: %d\n", ret);
+ return 1;
+ }
+
+ ret = rados_grace_create(io_ctx, RADOS_GRACE_OID);
+ if (ret < 0 && ret != -EEXIST) {
+ fprintf(stderr, "Can't create grace db: %d\n", ret);
+ return 1;
+ }
+
+ if (!strcmp(cmd, "dump")) {
+ ret = rados_grace_dump(io_ctx, RADOS_GRACE_OID);
+ } else if (!strcmp(cmd, "start")) {
+ if (!nodes) {
+ fprintf(stderr, "Need at least one nodeid.\n");
+ ret = -EINVAL;
+ } else {
+ ret = rados_grace_join_bulk(io_ctx, RADOS_GRACE_OID,
+ nodes, &argv[2], &cur, &rec,
+ true);
+ }
+ } else if (!strcmp(cmd, "join")) {
+ uint64_t cur, rec;
+
+ if (!nodes) {
+ fprintf(stderr, "Need at least one nodeid.\n");
+ ret = -EINVAL;
+ } else {
+ ret = rados_grace_join_bulk(io_ctx, RADOS_GRACE_OID,
+ nodes, &argv[2], &cur, &rec,
+ false);
+ }
+ } else if (!strcmp(cmd, "lift")) {
+ if (!nodes) {
+ fprintf(stderr, "Need at least one nodeid.\n");
+ ret = -EINVAL;
+ } else {
+ ret = rados_grace_lift_bulk(io_ctx, RADOS_GRACE_OID,
+ nodes, &argv[2], &cur, &rec,
+ false);
+ }
+ } else if (!strcmp(cmd, "remove")) {
+ if (!nodes) {
+ fprintf(stderr, "Need at least one nodeid.\n");
+ ret = -EINVAL;
+ } else {
+ ret = rados_grace_lift_bulk(io_ctx, RADOS_GRACE_OID,
+ nodes, &argv[2], &cur, &rec,
+ true);
+ }
+ } else if (!strcmp(cmd, "enforce")) {
+ if (!nodes) {
+ fprintf(stderr, "Need at least one nodeid.\n");
+ ret = -EINVAL;
+ } else {
+ ret = rados_grace_enforcing_toggle(io_ctx,
+ RADOS_GRACE_OID, nodes, &argv[2],
+ &cur, &rec, true);
+ }
+ } else if (!strcmp(cmd, "noenforce")) {
+ if (!nodes) {
+ fprintf(stderr, "Need at least one nodeid.\n");
+ ret = -EINVAL;
+ } else {
+ ret = rados_grace_enforcing_toggle(io_ctx,
+ RADOS_GRACE_OID, nodes, &argv[2],
+ &cur, &rec, false);
+ }
+ } else {
+ usage(argv);
+ ret = -EINVAL;
+ }
+
+ if (ret)
+ return 1;
+ return 0;
+}
--
2.17.0