summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorVenky Shankar <vshankar@redhat.com>2015-04-06 18:14:53 +0530
committerVijay Bellur <vbellur@redhat.com>2015-04-08 06:47:51 +0000
commit7fb55dbdabf73f9169b0f3021a42fa120d64b373 (patch)
tree9acde6f2303f402f18c469c33e0638bae3241c3d
parent2dfc36811337666c26e42c13f19eb59a7cef674f (diff)
tests/bitrot-stub: Object versioning test(s)
This patch introduces basic object versioning test(s) which is required for bitrot detection to work correctly. Basic test(s) such as opening a file in read-only mode, single open, multiple open()s are covered on FUSE mount _only_ as stub does not support anonymous fds yet. For this reason, the test case disables open-behind. Actual verification is implemented as a C source which makes use of the same on-disk data structures as used by the stub code. The data structures are moved to separate header file which is included by the test script. Such modularization helps in future enhancements to keep the version "data type" opaque and provide handful of APIs version checking (equal/greater/etc..). [ This is just a start and should grow over time as stub is enhanced and codebase matures. ] Change-Id: Ibee20e65a15b56bbdd59fd2703f9305b115aec7a BUG: 1201724 Signed-off-by: Venky Shankar <vshankar@redhat.com> Reviewed-on: http://review.gluster.org/10140 Reviewed-by: Raghavendra Bhat <raghavendra@redhat.com> Tested-by: Gluster Build System <jenkins@build.gluster.com> Reviewed-by: Vijay Bellur <vbellur@redhat.com>
-rw-r--r--tests/bitrot/br-stub.c147
-rw-r--r--tests/bitrot/br-stub.t44
-rw-r--r--xlators/features/bit-rot/src/stub/bit-rot-common.h17
-rw-r--r--xlators/features/bit-rot/src/stub/bit-rot-object-version.h30
4 files changed, 222 insertions, 16 deletions
diff --git a/tests/bitrot/br-stub.c b/tests/bitrot/br-stub.c
new file mode 100644
index 00000000000..81481f86905
--- /dev/null
+++ b/tests/bitrot/br-stub.c
@@ -0,0 +1,147 @@
+#define _GNU_SOURCE
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <limits.h>
+#include <unistd.h>
+#include <fcntl.h>
+#include <stdint.h>
+#include <sys/types.h>
+#include <sys/xattr.h>
+
+#include "bit-rot-object-version.h"
+
+/* NOTE: no size discovery */
+int
+brstub_validate_version (char *bpath, unsigned long version)
+{
+ int ret = 0;
+ int match = 0;
+ size_t xsize = 0;
+ br_version_t *xv = NULL;
+
+ xsize = sizeof (br_version_t);
+
+ xv = calloc (1, xsize);
+ if (!xv)
+ goto err;
+
+ ret = getxattr (bpath, "trusted.glusterfs.bit-rot.version", xv, xsize);
+ if (ret < 0)
+ goto err;
+
+ if (xv->ongoingversion != version)
+ match = -1;
+ free (xv);
+
+ return match;
+
+ err:
+ return -1;
+}
+
+int
+brstub_open_validation (char *filp, char *bpath, unsigned long startversion)
+{
+ int fd1 = 0;
+ int fd2 = 0;
+ int ret = 0;
+
+ /* read only check */
+ fd1 = open (filp, O_RDONLY);
+ if (fd1 < 0)
+ goto err;
+ close (fd1);
+
+ ret = brstub_validate_version (bpath, startversion);
+ if (ret < 0)
+ goto err;
+
+ /* single open (write/) check */
+ fd1 = open (filp, O_RDWR);
+ if (fd1 < 0)
+ goto err;
+ close (fd1);
+
+ startversion++;
+ ret = brstub_validate_version (bpath, startversion);
+
+ /* multi open (write/) check */
+ fd1 = open (filp, O_RDWR);
+ if (fd1 < 0)
+ goto err;
+ fd2 = open (filp, O_WRONLY);
+ if (fd1 < 0)
+ goto err;
+ close (fd1);
+ close (fd2);
+
+ /**
+ * incremented once per open()/open().../close()/close() sequence
+ */
+ startversion++;
+ ret = brstub_validate_version (bpath, startversion);
+ if (ret < 0)
+ goto err;
+
+ return 0;
+
+ err:
+ return -1;
+}
+
+int
+brstub_new_object_validate (char *filp, char *brick)
+{
+ int ret = 0;
+ char *fname = NULL;
+ char bpath[PATH_MAX] = {0,};
+
+ fname = basename (filp);
+ if (!fname)
+ goto err;
+
+ (void) snprintf (bpath, PATH_MAX, "%s/%s", brick, fname);
+
+ printf ("Validating initial version..\n");
+ ret = brstub_validate_version (bpath, 1);
+ if (ret < 0)
+ goto err;
+
+ printf ("Validating version on modifications..\n");
+ ret = brstub_open_validation (filp, bpath, 1);
+ if (ret < 0)
+ goto err;
+
+ return 0;
+
+ err:
+ return -1;
+}
+
+int
+main (int argc, char **argv)
+{
+ int ret = 0;
+ char *filp = NULL;
+ char *brick = NULL;
+
+ if (argc != 3) {
+ printf ("Usage: %s <path> <brick>\n", argv[0]);
+ goto err;
+ }
+
+ filp = argv[1];
+ brick = argv[2];
+
+ printf ("Validating object version [%s]\n", filp);
+ ret = brstub_new_object_validate (filp, brick);
+ if (ret < 0)
+ goto err;
+
+ return 0;
+
+ err:
+ return -1;
+}
diff --git a/tests/bitrot/br-stub.t b/tests/bitrot/br-stub.t
new file mode 100644
index 00000000000..11d02418785
--- /dev/null
+++ b/tests/bitrot/br-stub.t
@@ -0,0 +1,44 @@
+#!/bin/bash
+
+. $(dirname $0)/../include.rc
+. $(dirname $0)/../volume.rc
+
+STUB_SOURCE=$(dirname $0)/br-stub.c
+STUB_EXEC=$(dirname $0)/br-stub
+
+cleanup;
+
+TEST glusterd
+TEST pidof glusterd
+
+## Create a distribute volume (B=2)
+TEST $CLI volume create $V0 $H0:$B0/${V0}1 $H0:$B0/${V0}2;
+EXPECT "$V0" volinfo_field $V0 'Volume Name';
+EXPECT 'Created' volinfo_field $V0 'Status';
+EXPECT '2' brick_count $V0
+
+## Turn off open-behind (stub does not work with anonfd yet..)
+TEST $CLI volume set $V0 performance.open-behind off
+EXPECT 'off' volinfo_field $V0 'performance.open-behind'
+
+## Start the volume
+TEST $CLI volume start $V0;
+EXPECT 'Started' volinfo_field $V0 'Status';
+
+## Mount the volume
+TEST $GFS --volfile-server=$H0 --volfile-id=$V0 $M0;
+
+## Build stub C source
+build_tester $STUB_SOURCE -o $STUB_EXEC -I$(dirname $0)/../../xlators/features/bit-rot/src/stub
+TEST [ -e $STUB_EXEC ]
+
+## create & check version
+fname="$M0/filezero"
+touch $fname
+backpath=$(get_backend_paths $fname)
+TEST $STUB_EXEC $fname $(dirname $backpath)
+
+## cleanups..
+rm -f $STUB_EXEC
+
+cleanup;
diff --git a/xlators/features/bit-rot/src/stub/bit-rot-common.h b/xlators/features/bit-rot/src/stub/bit-rot-common.h
index ae1f45f6d1d..fdf23142768 100644
--- a/xlators/features/bit-rot/src/stub/bit-rot-common.h
+++ b/xlators/features/bit-rot/src/stub/bit-rot-common.h
@@ -17,22 +17,7 @@
#endif
#include "glusterfs.h"
-
-/**
- * on-disk formats for ongoing version and object signature.
- */
-typedef struct br_version {
- unsigned long ongoingversion;
- uint32_t timebuf[2];
-} br_version_t;
-
-typedef struct br_signature {
- int8_t signaturetype;
-
- unsigned long signedversion;
-
- char signature[0];
-} br_signature_t;
+#include "bit-rot-object-version.h"
#define BR_VXATTR_VERSION (1 << 0)
#define BR_VXATTR_SIGNATURE (1 << 1)
diff --git a/xlators/features/bit-rot/src/stub/bit-rot-object-version.h b/xlators/features/bit-rot/src/stub/bit-rot-object-version.h
new file mode 100644
index 00000000000..a158adf8153
--- /dev/null
+++ b/xlators/features/bit-rot/src/stub/bit-rot-object-version.h
@@ -0,0 +1,30 @@
+/*
+ Copyright (c) 2015 Red Hat, Inc. <http://www.redhat.com>
+ This file is part of GlusterFS.
+
+ This file is licensed to you under your choice of the GNU Lesser
+ General Public License, version 3 or any later version (LGPLv3 or
+ later), or the GNU General Public License, version 2 (GPLv2), in all
+ cases as published by the Free Software Foundation.
+*/
+
+#ifndef __BIT_ROT_OBJECT_VERSION_H
+#define __BIT_ROT_OBJECT_VERSION_H
+
+/**
+ * on-disk formats for ongoing version and object signature.
+ */
+typedef struct br_version {
+ unsigned long ongoingversion;
+ uint32_t timebuf[2];
+} br_version_t;
+
+typedef struct br_signature {
+ int8_t signaturetype;
+
+ unsigned long signedversion;
+
+ char signature[0];
+} br_signature_t;
+
+#endif