From 23c386f2b4511acfdb389adc7f48f15d284c639c Mon Sep 17 00:00:00 2001 From: Adam Dickmeiss Date: Thu, 23 Mar 2006 09:15:24 +0000 Subject: [PATCH] Moved file locking utilities from index/lockutil.c to util/flock.c and definitions in include/idzebra/flock.h. --- include/idzebra/Makefile.am | 4 +- include/idzebra/flock.h | 42 ++++++++++ index/Makefile.am | 4 +- index/index.h | 19 +---- index/lockutil.c | 186 ------------------------------------------- index/zebraapi.c | 15 +++- util/Makefile.am | 8 +- util/flock.c | 146 +++++++++++++++++++++++++++++++++ util/tstflock.c | 68 ++++++++++++++++ 9 files changed, 281 insertions(+), 211 deletions(-) create mode 100644 include/idzebra/flock.h delete mode 100644 index/lockutil.c create mode 100644 util/flock.c create mode 100644 util/tstflock.c diff --git a/include/idzebra/Makefile.am b/include/idzebra/Makefile.am index 4a998e0..add082c 100644 --- a/include/idzebra/Makefile.am +++ b/include/idzebra/Makefile.am @@ -1,6 +1,6 @@ -# $Id: Makefile.am,v 1.8 2005-09-15 10:34:22 adam Exp $ +# $Id: Makefile.am,v 1.9 2006-03-23 09:15:24 adam Exp $ pkginclude_HEADERS=api.h version.h res.h recctrl.h data1.h recgrs.h \ zebramap.h bfile.h dict.h isam-codec.h isams.h isamc.h isamb.h util.h \ - snippet.h api_swig.h + snippet.h api_swig.h flock.h diff --git a/include/idzebra/flock.h b/include/idzebra/flock.h new file mode 100644 index 0000000..3cd5de6 --- /dev/null +++ b/include/idzebra/flock.h @@ -0,0 +1,42 @@ +/* $Id: flock.h,v 1.1 2006-03-23 09:15:24 adam Exp $ + Copyright (C) 1995-2005 + Index Data ApS + +This file is part of the Zebra server. + +Zebra is free software; you can redistribute it and/or modify it under +the terms of the GNU General Public License as published by the Free +Software Foundation; either version 2, or (at your option) any later +version. + +Zebra 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 General Public License +for more details. + +You should have received a copy of the GNU General Public License +along with Zebra; see the file LICENSE.zebra. If not, write to the +Free Software Foundation, 59 Temple Place - Suite 330, Boston, MA +02111-1307, USA. +*/ + +#include + +#ifndef FLOCK_H +#define FLOCK_H + +YAZ_BEGIN_CDECL + +typedef struct zebra_lock_info *ZebraLockHandle; + +ZebraLockHandle zebra_lock_create(const char *dir, const char *file); +void zebra_lock_destroy (ZebraLockHandle h); +int zebra_unlock (ZebraLockHandle h); +char *zebra_mk_fname (const char *dir, const char *name); + +int zebra_lock_w (ZebraLockHandle h); +int zebra_lock_r (ZebraLockHandle h); + +YAZ_END_CDECL + +#endif diff --git a/index/Makefile.am b/index/Makefile.am index 5b8e891..a183c1c 100644 --- a/index/Makefile.am +++ b/index/Makefile.am @@ -1,11 +1,11 @@ -## $Id: Makefile.am,v 1.35 2006-01-19 13:31:08 adam Exp $ +## $Id: Makefile.am,v 1.36 2006-03-23 09:15:25 adam Exp $ noinst_PROGRAMS = apitest kdump lib_LTLIBRARIES = libidzebra-api.la libidzebra_api_la_SOURCES = dir.c dirs.c trav.c kinput.c kcompare.c \ - attribute.c symtab.c recindex.c recstat.c lockutil.c \ + attribute.c symtab.c recindex.c recstat.c \ zebraapi.c api_swig.c \ zinfo.c invstat.c sortidx.c compact.c zsets.c zrpn.c \ rank1.c trunc.c retrieve.c extract.c rankstatic.c \ diff --git a/index/index.h b/index/index.h index f544d8b..164d195 100644 --- a/index/index.h +++ b/index/index.h @@ -1,4 +1,4 @@ -/* $Id: index.h,v 1.155 2006-02-20 18:39:43 adam Exp $ +/* $Id: index.h,v 1.156 2006-03-23 09:15:25 adam Exp $ Copyright (C) 1995-2005 Index Data ApS @@ -27,6 +27,7 @@ Free Software Foundation, 59 Temple Place - Suite 330, Boston, MA #include #include #include +#include #include #if HAVE_SYS_TIMES_H @@ -141,25 +142,13 @@ void zebraIndexUnlock (ZebraHandle zh); int zebraIndexLock (BFiles bfs, ZebraHandle zh, int commitNow, const char *rval); int zebraIndexWait (ZebraHandle zh, int commitPhase); +void zebra_lock_prefix (Res res, char *dst); + #define FNAME_MAIN_LOCK "zebraidx.LCK" #define FNAME_COMMIT_LOCK "zebracmt.LCK" #define FNAME_ORG_LOCK "zebraorg.LCK" #define FNAME_TOUCH_TIME "zebraidx.time" -typedef struct zebra_lock_info *ZebraLockHandle; -ZebraLockHandle zebra_lock_create(const char *dir, - const char *file, int excl_flag); -void zebra_lock_destroy (ZebraLockHandle h); -int zebra_lock (ZebraLockHandle h); -int zebra_lock_nb (ZebraLockHandle h); -int zebra_unlock (ZebraLockHandle h); -int zebra_lock_fd (ZebraLockHandle h); -void zebra_lock_prefix (Res res, char *dst); -char *zebra_mk_fname (const char *dir, const char *name); - -int zebra_lock_w (ZebraLockHandle h); -int zebra_lock_r (ZebraLockHandle h); - void zebra_load_atts (data1_handle dh, Res res); int key_SU_decode (int *ch, const unsigned char *out); diff --git a/index/lockutil.c b/index/lockutil.c deleted file mode 100644 index 4c7cbf7..0000000 --- a/index/lockutil.c +++ /dev/null @@ -1,186 +0,0 @@ -/* $Id: lockutil.c,v 1.21 2005-06-14 20:28:54 adam Exp $ - Copyright (C) 1995-2005 - Index Data ApS - -This file is part of the Zebra server. - -Zebra is free software; you can redistribute it and/or modify it under -the terms of the GNU General Public License as published by the Free -Software Foundation; either version 2, or (at your option) any later -version. - -Zebra 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 General Public License -for more details. - -You should have received a copy of the GNU General Public License -along with Zebra; see the file LICENSE.zebra. If not, write to the -Free Software Foundation, 59 Temple Place - Suite 330, Boston, MA -02111-1307, USA. -*/ - - -#include -#include -#include -#include -#include -#include -#ifdef WIN32 -#include -#include -#endif -#if HAVE_UNISTD_H -#include -#endif - -#include "index.h" - -struct zebra_lock_info { - int fd; - int excl_flag; -}; - -char *zebra_mk_fname (const char *dir, const char *name) -{ - int dlen = dir ? strlen(dir) : 0; - char *fname = xmalloc (dlen + strlen(name) + 3); - -#ifdef WIN32 - if (dlen) - { - int last_one = dir[dlen-1]; - - if (!strchr ("/\\:", last_one)) - sprintf (fname, "%s\\%s", dir, name); - else - sprintf (fname, "%s%s", dir, name); - } - else - sprintf (fname, "%s", name); -#else - if (dlen) - { - int last_one = dir[dlen-1]; - - if (!strchr ("/", last_one)) - sprintf (fname, "%s/%s", dir, name); - else - sprintf (fname, "%s%s", dir, name); - } - else - sprintf (fname, "%s", name); -#endif - return fname; -} - -ZebraLockHandle zebra_lock_create (const char *dir, - const char *name, int excl_flag) -{ - char *fname = zebra_mk_fname(dir, name); - ZebraLockHandle h = (ZebraLockHandle) xmalloc (sizeof(*h)); - - h->excl_flag = excl_flag; - h->fd = -1; - - -#ifdef WIN32 - if (!h->excl_flag) - h->fd = open (name, O_BINARY|O_RDONLY); - if (h->fd == -1) - h->fd = open (fname, ((h->excl_flag > 1) ? O_EXCL : 0)| - (O_BINARY|O_CREAT|O_RDWR), 0666); -#else - h->fd= open (fname, ((h->excl_flag > 1) ? O_EXCL : 0)| - (O_BINARY|O_CREAT|O_RDWR), 0666); -#endif - if (h->fd == -1) - { - if (h->excl_flag <= 1) - yaz_log (YLOG_WARN|YLOG_ERRNO, "open %s", fname); - xfree (h); - h = 0; - } - xfree (fname); - return h; -} - -void zebra_lock_destroy (ZebraLockHandle h) -{ - if (!h) - return; - if (h->fd != -1) - close (h->fd); - xfree (h); -} - -void zebra_lock_prefix (Res res, char *path) -{ - const char *lock_dir = res_get_def (res, "lockDir", ""); - - strcpy (path, lock_dir); - if (*path && path[strlen(path)-1] != '/') - strcat (path, "/"); -} - -#ifndef WIN32 -static int unixLock (int fd, int type, int cmd) -{ - struct flock area; - area.l_type = type; - area.l_whence = SEEK_SET; - area.l_len = area.l_start = 0L; - return fcntl (fd, cmd, &area); -} -#endif - -int zebra_lock_w (ZebraLockHandle h) -{ -#ifdef WIN32 - return _locking (h->fd, _LK_LOCK, 1); -#else - return unixLock (h->fd, F_WRLCK, F_SETLKW); -#endif -} - -int zebra_lock_r (ZebraLockHandle h) -{ -#ifdef WIN32 - return _locking (h->fd, _LK_LOCK, 1); -#else - return unixLock (h->fd, F_RDLCK, F_SETLKW); -#endif -} - -int zebra_lock (ZebraLockHandle h) -{ -#ifdef WIN32 - return _locking (h->fd, _LK_LOCK, 1); -#else - return unixLock (h->fd, h->excl_flag ? F_WRLCK : F_RDLCK, F_SETLKW); -#endif -} - -int zebra_lock_nb (ZebraLockHandle h) -{ -#ifdef WIN32 - return _locking (h->fd, _LK_NBLCK, 1); -#else - return unixLock (h->fd, h->excl_flag ? F_WRLCK : F_RDLCK, F_SETLK); -#endif -} - -int zebra_unlock (ZebraLockHandle h) -{ -#ifdef WIN32 - return _locking (h->fd, _LK_UNLCK, 1); -#else - return unixLock (h->fd, F_UNLCK, F_SETLKW); -#endif -} - -int zebra_lock_fd (ZebraLockHandle h) -{ - return h->fd; -} diff --git a/index/zebraapi.c b/index/zebraapi.c index cb05bb6..d89c263 100644 --- a/index/zebraapi.c +++ b/index/zebraapi.c @@ -1,4 +1,4 @@ -/* $Id: zebraapi.c,v 1.203 2006-03-13 17:42:09 mike Exp $ +/* $Id: zebraapi.c,v 1.204 2006-03-23 09:15:25 adam Exp $ Copyright (C) 1995-2005 Index Data ApS @@ -701,11 +701,11 @@ static void zebra_select_register (ZebraHandle zh, const char *new_reg) res_set (zh->res, "lockDir", zh->path_reg); sprintf (fname, "norm.%s.LCK", zh->reg_name); zh->lock_normal = - zebra_lock_create (res_get(zh->res, "lockDir"), fname, 0); + zebra_lock_create (res_get(zh->res, "lockDir"), fname); sprintf (fname, "shadow.%s.LCK", zh->reg_name); zh->lock_shadow = - zebra_lock_create (res_get(zh->res, "lockDir"), fname, 0); + zebra_lock_create (res_get(zh->res, "lockDir"), fname); if (!zh->lock_normal || !zh->lock_shadow) { @@ -2358,3 +2358,12 @@ void zebra_setError_zint(ZebraHandle zh, int code, zint i) zh->errString = nmem_strdup(zh->nmem_error, vstr); } +void zebra_lock_prefix (Res res, char *path) +{ + const char *lock_dir = res_get_def (res, "lockDir", ""); + + strcpy (path, lock_dir); + if (*path && path[strlen(path)-1] != '/') + strcat (path, "/"); +} + diff --git a/util/Makefile.am b/util/Makefile.am index 008071e..57e2750 100644 --- a/util/Makefile.am +++ b/util/Makefile.am @@ -1,10 +1,10 @@ -## $Id: Makefile.am,v 1.15 2005-06-15 21:31:45 adam Exp $ +## $Id: Makefile.am,v 1.16 2006-03-23 09:15:25 adam Exp $ lib_LTLIBRARIES = libidzebra-util.la noinst_PROGRAMS = passtest -check_PROGRAMS = tstcharmap +check_PROGRAMS = tstcharmap tstflock TESTS = $(check_PROGRAMS) @@ -18,8 +18,10 @@ AM_CPPFLAGS = -I$(srcdir)/../include $(YAZINC) -DDEFAULT_PROFILE_PATH=\"$(pkgdat LDADD = libidzebra-util.la $(YAZLALIB) libidzebra_util_la_SOURCES = zint.c res.c charmap.c zebramap.c passwddb.c \ - zebra-lock.c dirent.c xpath.c atoi_zn.c snippet.c + zebra-lock.c dirent.c xpath.c atoi_zn.c snippet.c flock.c passtest_SOURCES = passtest.c tstcharmap_SOURCES = tstcharmap.c + +tstflock_SOURCES = tstflock.c diff --git a/util/flock.c b/util/flock.c new file mode 100644 index 0000000..62fd4ac --- /dev/null +++ b/util/flock.c @@ -0,0 +1,146 @@ +/* $Id: flock.c,v 1.1 2006-03-23 09:15:25 adam Exp $ + Copyright (C) 1995-2005 + Index Data ApS + +This file is part of the Zebra server. + +Zebra is free software; you can redistribute it and/or modify it under +the terms of the GNU General Public License as published by the Free +Software Foundation; either version 2, or (at your option) any later +version. + +Zebra 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 General Public License +for more details. + +You should have received a copy of the GNU General Public License +along with Zebra; see the file LICENSE.zebra. If not, write to the +Free Software Foundation, 59 Temple Place - Suite 330, Boston, MA +02111-1307, USA. +*/ + + +#include +#include +#include +#include +#include +#include +#ifdef WIN32 +#include +#include +#endif +#if HAVE_UNISTD_H +#include +#endif + +#include +#include + +struct zebra_lock_info { + int fd; +}; + +char *zebra_mk_fname (const char *dir, const char *name) +{ + int dlen = dir ? strlen(dir) : 0; + char *fname = xmalloc (dlen + strlen(name) + 3); + +#ifdef WIN32 + if (dlen) + { + int last_one = dir[dlen-1]; + + if (!strchr ("/\\:", last_one)) + sprintf (fname, "%s\\%s", dir, name); + else + sprintf (fname, "%s%s", dir, name); + } + else + sprintf (fname, "%s", name); +#else + if (dlen) + { + int last_one = dir[dlen-1]; + + if (!strchr ("/", last_one)) + sprintf (fname, "%s/%s", dir, name); + else + sprintf (fname, "%s%s", dir, name); + } + else + sprintf (fname, "%s", name); +#endif + return fname; +} + +ZebraLockHandle zebra_lock_create (const char *dir, const char *name) +{ + char *fname = zebra_mk_fname(dir, name); + ZebraLockHandle h = (ZebraLockHandle) xmalloc (sizeof(*h)); + + h->fd = -1; +#ifdef WIN32 + h->fd = open (name, O_BINARY|O_RDONLY); + if (h->fd == -1) + h->fd = open (fname, (O_BINARY|O_CREAT|O_RDWR), 0666); +#else + h->fd= open (fname, (O_BINARY|O_CREAT|O_RDWR), 0666); +#endif + if (h->fd == -1) + { + xfree (h); + h = 0; + } + xfree (fname); + return h; +} + +void zebra_lock_destroy (ZebraLockHandle h) +{ + if (!h) + return; + if (h->fd != -1) + close (h->fd); + xfree (h); +} + +#ifndef WIN32 +static int unixLock (int fd, int type, int cmd) +{ + struct flock area; + area.l_type = type; + area.l_whence = SEEK_SET; + area.l_len = area.l_start = 0L; + return fcntl (fd, cmd, &area); +} +#endif + +int zebra_lock_w (ZebraLockHandle h) +{ +#ifdef WIN32 + return _locking (h->fd, _LK_LOCK, 1); +#else + return unixLock (h->fd, F_WRLCK, F_SETLKW); +#endif +} + +int zebra_lock_r (ZebraLockHandle h) +{ +#ifdef WIN32 + return _locking (h->fd, _LK_LOCK, 1); +#else + return unixLock (h->fd, F_RDLCK, F_SETLKW); +#endif +} + +int zebra_unlock (ZebraLockHandle h) +{ +#ifdef WIN32 + return _locking (h->fd, _LK_UNLCK, 1); +#else + return unixLock (h->fd, F_UNLCK, F_SETLKW); +#endif +} + diff --git a/util/tstflock.c b/util/tstflock.c new file mode 100644 index 0000000..0d0be35 --- /dev/null +++ b/util/tstflock.c @@ -0,0 +1,68 @@ +/* + * Copyright (C) 1995-2005, Index Data ApS + * See the file LICENSE for details. + * + * $Id: tstflock.c,v 1.1 2006-03-23 09:15:25 adam Exp $ + */ + +#include +#if YAZ_POSIX_THREADS +#include +#endif + +#include +#include +#include + +static char seq[20]; +static char *seqp = seq; + +void *run_func(void *arg) +{ + int i; + ZebraLockHandle lh = zebra_lock_create(0, "my.LCK"); + for (i = 0; i<2; i++) + { + zebra_lock_w(lh); + + *seqp++ = 'L'; + sleep(1); + *seqp++ = 'U'; + + zebra_unlock(lh); + } + zebra_lock_destroy(lh); + return 0; +} + +static void tst1() +{ + pthread_t child_thread[2]; + int id1 = 1; + int id2 = 2; + pthread_create(&child_thread[0], 0 /* attr */, run_func, &id1); + pthread_create(&child_thread[1], 0 /* attr */, run_func, &id2); + pthread_join(child_thread[0], 0); + pthread_join(child_thread[1], 0); + *seqp++ = '\0'; +} + +int main(int argc, char **argv) +{ + YAZ_CHECK_INIT(argc, argv); + tst1(); + +#if 0 + /* does not pass.. for bug 529 */ + YAZ_CHECK(strcmp(seq, "LULULULU") == 0); +#endif + YAZ_CHECK_TERM; +} +/* + * Local variables: + * c-basic-offset: 4 + * indent-tabs-mode: nil + * End: + * vim: shiftwidth=4 tabstop=8 expandtab + */ + -- 1.7.10.4