diff options
author | David Teigland <teigland@redhat.com> | 2010-04-13 10:16:56 -0500 |
---|---|---|
committer | David Teigland <teigland@redhat.com> | 2010-04-13 10:16:56 -0500 |
commit | ecb30a00e3683f50076fd27a3058a46c833de3bf (patch) | |
tree | 32eeb06cb6a81ff62cb79c7a5ffbb3e5c00b20b8 | |
parent | aa83b1c3b1bc430af1f2e682a18181488465f87b (diff) | |
download | dct-stuff-ecb30a00e3683f50076fd27a3058a46c833de3bf.tar.gz dct-stuff-ecb30a00e3683f50076fd27a3058a46c833de3bf.tar.xz dct-stuff-ecb30a00e3683f50076fd27a3058a46c833de3bf.zip |
alternate-lvb: copy over
from cluster git tree
Signed-off-by: David Teigland <teigland@redhat.com>
-rw-r--r-- | dlm/alternate-lvb.c | 179 |
1 files changed, 179 insertions, 0 deletions
diff --git a/dlm/alternate-lvb.c b/dlm/alternate-lvb.c new file mode 100644 index 0000000..4797fb5 --- /dev/null +++ b/dlm/alternate-lvb.c @@ -0,0 +1,179 @@ +/* + * Copyright (c) 2007 David Teigland + * All Rights Reserved. + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License V2 + * as published by the Free Software Foundation. + * + * This program is distributed in the hope that it would be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + +#include <unistd.h> +#include <stdio.h> +#include <stdlib.h> +#include <stdint.h> +#include <stddef.h> +#include <string.h> +#include <fcntl.h> +#include <errno.h> +#include <time.h> +#include <sys/time.h> +#include <syslog.h> +#include <asm/types.h> +#include <sys/socket.h> +#include <sys/poll.h> +#include <sys/un.h> +#include <sys/types.h> +#include <sys/stat.h> +#include <sys/errno.h> + +#include "libdlm.h" + +#define die(fmt, args...) \ +do \ +{ \ + fprintf(stderr, "%s: ", prog_name); \ + fprintf(stderr, fmt, ##args); \ + exit(EXIT_FAILURE); \ +} \ +while (0) + +static char *prog_name; +static dlm_lshandle_t *dh; +static int verbose; + +static struct dlm_lksb lksb; +static char lvb[32]; + +int main(int argc, char *argv[]) +{ + unsigned long long offset; + unsigned long long num, last_num = 0; + unsigned int id, clients, sleeptime = 0; + unsigned long long skip = 0; + char *name; + int rv; + + prog_name = argv[0]; + verbose = 0; + + if (argc < 5) + die("name offset id clients [sleep]\n"); + + name = argv[1]; + offset = atoll(argv[2]); + id = atoi(argv[3]); + clients = atoi(argv[4]); + + if (argc > 5) + sleeptime = atoi(argv[5]); + + printf("Joining \"alternate\" lockspace...\n"); + + dh = dlm_create_lockspace("alternate", 0600); + if (!dh) { + printf("dlm_create_lockspace error %p %d\n",dh, errno); + return -ENOTCONN; + } + + rv = dlm_ls_pthread_init(dh); + if (rv < 0) { + printf("dlm_ls_pthread_init error %d %d\n", rv, errno); + dlm_release_lockspace("alternate", dh, 1); + return rv; + } + + memset(&lksb, 0, sizeof(lksb)); + memset(&lvb, 0, sizeof(lvb)); + lksb.sb_lvbptr = lvb; + + if (verbose) + printf("request NL\n"); + + rv = dlm_ls_lock_wait(dh, LKM_NLMODE, &lksb, LKF_VALBLK, + name, strlen(name), 0, NULL, NULL, NULL); + + while (1) { + if (verbose) + printf("convert NL->PR\n"); + + rv = dlm_ls_lock_wait(dh, LKM_PRMODE, &lksb, + LKF_VALBLK | LKF_CONVERT, + name, strlen(name), + 0, NULL, NULL, NULL); + if (rv) + printf("lock1 error: %d %d\n", rv, lksb.sb_status); + + memcpy(&num, &lvb, sizeof(num)); + + if (verbose) + printf("read lvb %llu\n", num); + + /* it's our turn */ + if (num % clients == id) { + if (last_num && last_num + clients != num + 1) + die("bad: num %llu last_num %llu\n", + num, last_num); + + if (verbose) + printf("convert PR->EX\n"); + + rv = dlm_ls_lock_wait(dh, LKM_EXMODE, &lksb, + LKF_VALBLK | LKF_CONVERT, + name, strlen(name), + 0, NULL, NULL, NULL); + if (rv) + printf("lock2 error: %d %d\n", rv, + lksb.sb_status); + + memcpy(&num, &lvb, sizeof(num)); + if (num % clients != id) + die("bad2: num %llu\n", num); + + num++; + + memcpy(&lvb, &num, sizeof(num)); + printf("%llu %llu\n", num, skip); + + if (verbose) + printf("convert EX->NL\n"); + + rv = dlm_ls_lock_wait(dh, LKM_NLMODE, &lksb, + LKF_VALBLK | LKF_CONVERT, + name, strlen(name), + 0, NULL, NULL, NULL); + if (rv) + printf("lock3 error: %d %d\n", rv, + lksb.sb_status); + + last_num = num; + skip = 0; + } else { + skip++; + + if (verbose) + printf("convert PR->NL, skip %llu\n", skip); + + rv = dlm_ls_lock_wait(dh, LKM_NLMODE, &lksb, + LKF_VALBLK | LKF_CONVERT, + name, strlen(name), + 0, NULL, NULL, NULL); + if (rv) + printf("lock4 error: %d %d\n", rv, + lksb.sb_status); + } + + if (sleeptime) + usleep(sleeptime); + } + + dlm_ls_unlock_wait(dh, lksb.sb_lkid, 0, &lksb); + dlm_release_lockspace("alternate", dh, 1); + + exit(EXIT_SUCCESS); +} + |