From: teigland@sourceware.org <teigland@sourceware.org>
To: cluster-devel.redhat.com
Subject: [Cluster-devel] cluster/dlm/tests/usertest dlmtest2.c
Date: 27 Mar 2007 19:04:31 -0000 [thread overview]
Message-ID: <20070327190431.3159.qmail@sourceware.org> (raw)
CVSROOT: /cvs/cluster
Module name: cluster
Changes by: teigland at sourceware.org 2007-03-27 20:04:31
Modified files:
dlm/tests/usertest: dlmtest2.c
Log message:
latest version, "stress" test running correctly
Patches:
http://sourceware.org/cgi-bin/cvsweb.cgi/cluster/dlm/tests/usertest/dlmtest2.c.diff?cvsroot=cluster&r1=1.5&r2=1.6
--- cluster/dlm/tests/usertest/dlmtest2.c 2007/02/27 18:55:52 1.5
+++ cluster/dlm/tests/usertest/dlmtest2.c 2007/03/27 19:04:30 1.6
@@ -1,7 +1,7 @@
/******************************************************************************
*******************************************************************************
**
-** Copyright (C) 2006 Red Hat, Inc. All rights reserved.
+** Copyright (C) 2007 Red Hat, Inc. All rights reserved.
**
** This copyrighted material is made available to anyone wishing to use,
** modify, copy, or redistribute it subject to the terms and conditions
@@ -32,14 +32,19 @@
#define MAX_CLIENTS 4
#define MAX_LOCKS 16
+#define MAX_RESOURCES 16
static dlm_lshandle_t *dh;
static int libdlm_fd;
static int noqueue = 1;
+static int persistent = 0;
static int quiet = 1;
static int verbose = 0;
static int bast_cb;
static int maxn = MAX_LOCKS;
+static int maxr = MAX_RESOURCES;
+static int iterations;
+static int stress_stop = 0;
#define log_print(fmt, args...) \
do { \
@@ -158,7 +163,7 @@
for (i = 0; i < maxn; i++) {
lk = get_lock(i);
- printf("x %2d lkid %06x gr %2d rq %2d wait_ast %d last op %s\t%s\n",
+ printf("x %2d lkid %08x gr %2d rq %2d wait_ast %d last op %s \t%s\n",
i,
lk->lksb.sb_lkid,
lk->grmode,
@@ -272,6 +277,11 @@
lk->rqmode = -1;
}
+/* EBUSY from dlm_ls_lock() is expected sometimes, e.g. lock, cancel, lock;
+ the first lock is successful and the app gets the status back,
+ and issues the second lock before the reply for the overlapping
+ cancel (which did nothing) has been received in the dlm. */
+
void lock(int i, int mode)
{
char name[DLM_RESNAME_MAXLEN];
@@ -285,12 +295,14 @@
if (noqueue)
flags |= LKF_NOQUEUE;
+ if (persistent)
+ flags |= LKF_PERSISTENT;
if (lk->lksb.sb_lkid)
flags |= LKF_CONVERT;
memset(name, 0, sizeof(name));
- snprintf(name, sizeof(name), "test%d", i);
+ snprintf(name, sizeof(name), "test%d", (i % maxr));
log_verbose("lock: %d grmode %d rqmode %d flags %x lkid %x %s\n",
i, lk->grmode, mode, flags, lk->lksb.sb_lkid, name);
@@ -304,8 +316,9 @@
printf(" : lock %3d\t%x: EBUSY gr %d rq %d wait_ast %d\n",
i, lk->lksb.sb_lkid, lk->grmode, lk->rqmode, lk->wait_ast);
} else {
- printf(" : lock %3d\t%x: errno %d gr %d rq %d wait_ast %d\n",
- i, lk->lksb.sb_lkid, errno, lk->grmode, lk->rqmode, lk->wait_ast);
+ printf(" : lock %3d\t%x: errno %d rv %d gr %d rq %d wait_ast %d\n",
+ i, lk->lksb.sb_lkid, errno, rv, lk->grmode, lk->rqmode, lk->wait_ast);
+ stress_stop = 1;
}
log_verbose("lock: %d rv %d sb_lkid %x sb_status %x\n",
@@ -327,12 +340,14 @@
if (noqueue)
flags |= LKF_NOQUEUE;
+ if (persistent)
+ flags |= LKF_PERSISTENT;
if (lk->lksb.sb_lkid)
flags |= LKF_CONVERT;
memset(name, 0, sizeof(name));
- snprintf(name, sizeof(name), "test%d", i);
+ snprintf(name, sizeof(name), "test%d", (i % maxr));
log_verbose("lock_sync: %d rqmode %d flags %x lkid %x %s\n",
i, mode, flags, lk->lksb.sb_lkid, name);
@@ -364,6 +379,19 @@
lock(i, mode);
}
+char *uflags(uint32_t flags)
+{
+ if (flags == LKF_FORCEUNLOCK)
+ return "FORCEUNLOCK";
+ if (flags == LKF_CANCEL)
+ return "CANCEL";
+ return "0";
+}
+
+/* ENOENT is expected from dlm_ls_unlock() sometimes because we'll
+ try to do an unlockf during an outstanding op that will free
+ the lock itself */
+
void _unlock(int i, uint32_t flags)
{
struct lk *lk;
@@ -384,21 +412,14 @@
if (!rv) {
lk->wait_ast = 1;
} else if (rv == -1 && errno == EBUSY) {
- printf("unlock: EBUSY %d %x flags %x gr %d rq %d wait_ast %d\n",
- i, lk->lksb.sb_lkid, flags, lk->grmode, lk->rqmode, lk->wait_ast);
+ printf(" : unlock %3d\t%x: EBUSY flags %s gr %d rq %d wait_ast %d\n",
+ i, lk->lksb.sb_lkid, uflags(flags), lk->grmode, lk->rqmode, lk->wait_ast);
+ } else if (rv == -1 && errno == ENOENT) {
+ printf(" : unlock %3d\t%x: ENOENT flags %s gr %d rq %d wait_ast %d\n",
+ i, lk->lksb.sb_lkid, uflags(flags), lk->grmode, lk->rqmode, lk->wait_ast);
} else {
- printf("unlock: error %d %x flags %x rv %d errno %d gr %d rq %d wait_ast %d\n",
- i, lk->lksb.sb_lkid, flags, rv, errno, lk->grmode, lk->rqmode,
- lk->wait_ast);
-#if 0
- char input[32];
- printf("press X to exit, D to dispatch, other to continue\n");
- fgets(input, 32, stdin);
- if (input[0] == 'X')
- exit(-1);
- else if (input[0] == 'D')
- dlm_dispatch(libdlm_fd);
-#endif
+ printf(" : unlock %3d\t%x: errno %d flags %s rv %d gr %d rq %d wait_ast %d\n",
+ i, lk->lksb.sb_lkid, errno, uflags(flags), rv, lk->grmode, lk->rqmode, lk->wait_ast);
}
}
@@ -473,7 +494,7 @@
n = skips = lock_ops = unlock_ops = unlockf_ops = cancel_ops = 0;
- while (1) {
+ while (!stress_stop) {
process_libdlm();
if (++n == num)
@@ -515,7 +536,7 @@
lock(i, rand_int(0, 5));
lock_ops++;
- printf("%8u: lock %3d\t%x\n", n, i, lk->lksb.sb_lkid);
+ printf("%8x: lock %3d\t%x\n", n, i, lk->lksb.sb_lkid);
break;
case Op_unlock:
@@ -534,7 +555,7 @@
unlock(i);
unlock_ops++;
- printf("%8u: unlock %3d\t%x\n", n, i, lk->lksb.sb_lkid);
+ printf("%8x: unlock %3d\t%x\n", n, i, lk->lksb.sb_lkid);
break;
case Op_unlockf:
@@ -549,7 +570,7 @@
unlockf(i);
unlockf_ops++;
- printf("%8u: unlockf %3d\t%x\n", n, i, lk->lksb.sb_lkid);
+ printf("%8x: unlockf %3d\t%x\n", n, i, lk->lksb.sb_lkid);
break;
case Op_cancel:
@@ -564,7 +585,7 @@
cancel(i);
cancel_ops++;
- printf("%8u: cancel %3d\t%x\n", n, i, lk->lksb.sb_lkid);
+ printf("%8x: cancel %3d\t%x\n", n, i, lk->lksb.sb_lkid);
break;
}
@@ -611,6 +632,40 @@
client[i].fd = -1;
}
+void print_commands(void)
+{
+ printf("Usage:\n");
+ printf("max locks (maxn) is %d (x of 0 to %d)\n", maxn, maxn-1);
+ printf("max resources (maxr) is %d, lock x used on resource (x % maxr)\n", maxr);
+ printf("EXIT - exit program after unlocking any held locks\n");
+ printf("kill - exit program without unlocking any locks\n");
+ printf("lock x mode - request/convert lock x\n");
+ printf("unlock x - unlock lock x\n");
+ printf("unlockf x - force unlock lock x\n");
+ printf("cancel x - cancel lock x\n");
+ printf("lock_sync x mode - synchronous version of lock\n");
+ printf("unlock_sync x - synchronous version of unlock\n");
+ printf("ex x - equivalent to: lock x 5\n");
+ printf("pr x - equivalent to: lock x 3\n");
+ printf("hold - for x in 0 to max, lock x 3\n");
+ printf("release - for x in 0 to max, unlock x\n");
+ printf("stress n - loop doing random lock/unlock/unlockf/cancel on all locks, n times\n");
+ printf("dump - show info for all locks\n");
+ printf("noqueue - toggle NOQUEUE flag for all requests\n");
+ printf("persistent - toggle PERSISTENT flag for all requests\n");
+ printf("quiet - toggle quiet flag\n");
+ printf("verbose - toggle verbose flag\n");
+
+ printf("\ncombined operations\n");
+ printf("hold-kill - hold; kill\n");
+ printf("release-kill - release; kill\n");
+ printf("lock-kill x mode - lock; kill\n");
+ printf("unlock-kill x - unlock; kill\n");
+ printf("lock-cancel x mode msec - lock; sleep; cancel\n");
+ printf("lock-unlockf x mode msec - lock; sleep; unlockf\n");
+ printf("lock-cancel-kill x mode msec - lock; sleep; cancel; kill\n");
+ printf("lock-unlockf-kill x mode msec - lock; sleep; unlockf; kill\n");
+}
void process_command(int *quit)
{
@@ -735,6 +790,12 @@
return;
}
+ if (!strncmp(cmd, "persistent", 10)) {
+ persistent = !persistent;
+ printf("persistent is %s\n", persistent ? "on" : "off");
+ return;
+ }
+
if (!strncmp(cmd, "quiet", 5)) {
quiet = !quiet;
printf("quiet is %d\n", quiet);
@@ -748,49 +809,91 @@
}
if (!strncmp(cmd, "help", 4)) {
- printf("Usage:\n");
- printf("max locks is %d (x of 0 to %d)\n", maxn, maxn-1);
- printf("EXIT - exit program after unlocking any held locks\n");
- printf("kill - exit program without unlocking any locks\n");
- printf("lock x mode - request/convert lock on resource x\n");
- printf("unlock x - unlock lock on resource x\n");
- printf("unlockf x - force unlock lock on resource x\n");
- printf("cancel x - cancel lock on resource x\n");
- printf("lock_sync x mode - synchronous version of lock\n");
- printf("unlock_sync x - synchronous version of unlock\n");
- printf("ex x - equivalent to: lock x 5\n");
- printf("pr x - equivalent to: lock x 3\n");
- printf("hold - for x in 0 to max, lock x 3\n");
- printf("release - for x in 0 to max, unlock x\n");
- printf("stress n - loop doing random lock/unlock/unlockf/cancel on all locks, n times\n");
- printf("dump - show info for all resources\n");
- printf("noqueue - toggle NOQUEUE flag for all requests\n");
- printf("quiet - toggle quiet flag\n");
- printf("verbose - toggle verbose flag\n");
-
- printf("\ncombined operations\n");
- printf("hold-kill - hold; kill\n");
- printf("release-kill - release; kill\n");
- printf("lock-kill x mode - lock; kill\n");
- printf("unlock-kill x - unlock; kill\n");
- printf("lock-cancel x mode msec - lock; sleep; cancel\n");
- printf("lock-unlockf x mode msec - lock; sleep; unlockf\n");
- printf("lock-cancel-kill x mode msec - lock; sleep; cancel; kill\n");
- printf("lock-unlockf-kill x mode msec - lock; sleep; unlockf; kill\n");
+ print_commands();
return;
}
printf("unknown command %s\n", cmd);
}
+void print_usage(void)
+{
+ printf("Options:\n");
+ printf("\n");
+ printf(" -n The number of resources to work with, default %d\n", MAX_LOCKS);
+ printf(" -i Iterations in looping stress test, default 0 is no limit\n");
+}
+
+static void decode_arguments(int argc, char **argv)
+{
+ int cont = 1;
+ int optchar;
+
+ while (cont) {
+ optchar = getopt(argc, argv, "n:r:i:hV");
+
+ switch (optchar) {
+
+ case 'n':
+ maxn = atoi(optarg);
+ break;
+
+ case 'r':
+ maxr = atoi(optarg);
+ break;
+
+ case 'i':
+ iterations = atoi(optarg);
+ break;
+
+ case 'h':
+ print_usage();
+ exit(EXIT_SUCCESS);
+ break;
+
+ case 'V':
+ printf("%s (built %s %s)\n", argv[0], __DATE__, __TIME__);
+ /* printf("%s\n", REDHAT_COPYRIGHT); */
+ exit(EXIT_SUCCESS);
+ break;
+
+ case ':':
+ case '?':
+ fprintf(stderr, "Please use '-h' for usage.\n");
+ exit(EXIT_FAILURE);
+ break;
+
+ case EOF:
+ cont = 0;
+ break;
+
+ default:
+ fprintf(stderr, "unknown option: %c\n", optchar);
+ exit(EXIT_FAILURE);
+ break;
+ };
+ }
+}
+
int main(int argc, char *argv[])
{
struct lk *lk;
int i, rv, maxi = 0, quit = 0;
- if (argc > 1)
- maxn = atoi(argv[1]);
+ decode_arguments(argc, argv);
+
+ if (maxn < maxr) {
+ printf("number of resources must be >= number of locks\n");
+ return -1;
+ }
+ if (maxn % maxr) {
+ printf("number of locks must be multiple of number of resources\n");
+ return -1;
+ }
+
printf("maxn = %d\n", maxn);
+ printf("maxr = %d\n", maxr);
+ printf("locks per resource = %d\n", maxn / maxr);
client_init();
@@ -828,10 +931,15 @@
client_add(libdlm_fd, &maxi);
client_add(STDIN_FILENO, &maxi);
+ if (strstr(argv[0], "dlmstress"))
+ stress(iterations);
+
printf("Type EXIT to finish, help for usage\n");
while (1) {
rv = poll(pollfd, maxi + 1, -1);
+ if (rv < 0 && errno == EINTR)
+ continue;
if (rv < 0)
printf("poll error %d errno %d\n", rv, errno);
next reply other threads:[~2007-03-27 19:04 UTC|newest]
Thread overview: 11+ messages / expand[flat|nested] mbox.gz Atom feed top
2007-03-27 19:04 teigland [this message]
-- strict thread matches above, loose matches on Subject: below --
2008-02-21 17:49 [Cluster-devel] cluster/dlm/tests/usertest dlmtest2.c teigland
2008-01-17 21:49 teigland
2007-08-23 19:13 teigland
2007-08-22 14:01 teigland
2007-05-30 19:31 teigland
2007-04-27 19:09 teigland
2007-02-27 18:55 teigland
2007-01-04 20:34 teigland
2006-12-12 21:17 teigland
2006-12-08 19:25 teigland
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20070327190431.3159.qmail@sourceware.org \
--to=teigland@sourceware.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).