]> source.dussan.org Git - rspamd.git/commitdiff
* Add monitoring for cdb
authorVsevolod Stakhov <vsevolod@rambler-co.ru>
Wed, 9 Mar 2011 14:09:25 +0000 (17:09 +0300)
committerVsevolod Stakhov <vsevolod@rambler-co.ru>
Wed, 9 Mar 2011 14:09:25 +0000 (17:09 +0300)
src/cdb/cdb.h
src/cdb/cdb_init.c
src/lua/lua_cdb.c

index 5802da4d52a1008e3a76f12f516cec307e3e4f62..f61d5133452e06112027f739caf4cc9b46200b2b 100644 (file)
@@ -21,15 +21,19 @@ unsigned cdb_hash(const void *buf, unsigned len);
 unsigned cdb_unpack(const unsigned char buf[4]);
 void cdb_pack(unsigned num, unsigned char buf[4]);
 
-struct cdb {
-  int cdb_fd;                  /* file descriptor */
-  char *filename;       /* file name */
-  /* private members */
-  unsigned cdb_fsize;          /* datafile size */
-  unsigned cdb_dend;           /* end of data ptr */
-  const unsigned char *cdb_mem; /* mmap'ed file memory */
-  unsigned cdb_vpos, cdb_vlen; /* found data */
-  unsigned cdb_kpos, cdb_klen; /* found key */
+struct cdb
+{
+       int cdb_fd; /* file descriptor */
+       char *filename; /* file name */
+       time_t mtime; /* mtime of cdb file */
+       struct event *check_timer_ev; /* event structure for checking cdb for modifications */
+       struct timeval *check_timer_tv;
+       /* private members */
+       unsigned cdb_fsize; /* datafile size */
+       unsigned cdb_dend; /* end of data ptr */
+       const unsigned char *cdb_mem; /* mmap'ed file memory */
+       unsigned cdb_vpos, cdb_vlen; /* found data */
+       unsigned cdb_kpos, cdb_klen; /* found key */
 };
 
 #define CDB_STATIC_INIT {0,0,0,0,0,0,0,0}
@@ -41,10 +45,10 @@ struct cdb {
 #define cdb_fileno(c) ((c)->cdb_fd)
 
 int cdb_init(struct cdb *cdbp, int fd);
+void cdb_add_timer(struct cdb *cdbp, unsigned seconds);
 void cdb_free(struct cdb *cdbp);
 
-int cdb_read(const struct cdb *cdbp,
-             void *buf, unsigned len, unsigned pos);
+int cdb_read(const struct cdb *cdbp, void *buf, unsigned len, unsigned pos);
 #define cdb_readdata(cdbp, buf) \
         cdb_read((cdbp), (buf), cdb_datalen(cdbp), cdb_datapos(cdbp))
 #define cdb_readkey(cdbp, buf) \
@@ -58,17 +62,18 @@ const void *cdb_get(const struct cdb *cdbp, unsigned len, unsigned pos);
 
 int cdb_find(struct cdb *cdbp, const void *key, unsigned klen);
 
-struct cdb_find {
-  struct cdb *cdb_cdbp;
-  unsigned cdb_hval;
-  const unsigned char *cdb_htp, *cdb_htab, *cdb_htend;
-  unsigned cdb_httodo;
-  const void *cdb_key;
-  unsigned cdb_klen;
+struct cdb_find
+{
+       struct cdb *cdb_cdbp;
+       unsigned cdb_hval;
+       const unsigned char *cdb_htp, *cdb_htab, *cdb_htend;
+       unsigned cdb_httodo;
+       const void *cdb_key;
+       unsigned cdb_klen;
 };
 
-int cdb_findinit(struct cdb_find *cdbfp, struct cdb *cdbp,
-                 const void *key, unsigned klen);
+int cdb_findinit(struct cdb_find *cdbfp, struct cdb *cdbp, const void *key,
+               unsigned klen);
 int cdb_findnext(struct cdb_find *cdbfp);
 
 #define cdb_seqinit(cptr, cdbp) ((*(cptr))=2048)
@@ -81,66 +86,63 @@ int cdb_bread(int fd, void *buf, int len);
 
 /* cdb_make */
 
-struct cdb_make {
-  int cdb_fd;                  /* file descriptor */
-  /* private */
-  unsigned cdb_dpos;           /* data position so far */
-  unsigned cdb_rcnt;           /* record count so far */
-  unsigned char cdb_buf[4096]; /* write buffer */
-  unsigned char *cdb_bpos;     /* current buf position */
-  struct cdb_rl *cdb_rec[256]; /* list of arrays of record infos */
+struct cdb_make
+{
+       int cdb_fd; /* file descriptor */
+
+       /* private */
+       unsigned cdb_dpos; /* data position so far */
+       unsigned cdb_rcnt; /* record count so far */
+       unsigned char cdb_buf[4096]; /* write buffer */
+       unsigned char *cdb_bpos; /* current buf position */
+       struct cdb_rl *cdb_rec[256]; /* list of arrays of record infos */
 };
 
-enum cdb_put_mode {
-  CDB_PUT_ADD = 0,     /* add unconditionnaly, like cdb_make_add() */
+enum cdb_put_mode
+{
+       CDB_PUT_ADD = 0, /* add unconditionnaly, like cdb_make_add() */
 #define CDB_PUT_ADD    CDB_PUT_ADD
-  CDB_FIND = CDB_PUT_ADD,
-  CDB_PUT_REPLACE,     /* replace: do not place to index OLD record */
+       CDB_FIND = CDB_PUT_ADD, CDB_PUT_REPLACE, /* replace: do not place to index OLD record */
 #define CDB_PUT_REPLACE        CDB_PUT_REPLACE
-  CDB_FIND_REMOVE = CDB_PUT_REPLACE,
-  CDB_PUT_INSERT,      /* add only if not already exists */
+       CDB_FIND_REMOVE = CDB_PUT_REPLACE, CDB_PUT_INSERT, /* add only if not already exists */
 #define CDB_PUT_INSERT CDB_PUT_INSERT
-  CDB_PUT_WARN,                /* add unconditionally but ret. 1 if exists */
+       CDB_PUT_WARN, /* add unconditionally but ret. 1 if exists */
 #define CDB_PUT_WARN   CDB_PUT_WARN
-  CDB_PUT_REPLACE0,    /* if a record exists, fill old one with zeros */
+       CDB_PUT_REPLACE0, /* if a record exists, fill old one with zeros */
 #define CDB_PUT_REPLACE0 CDB_PUT_REPLACE0
-  CDB_FIND_FILL0 = CDB_PUT_REPLACE0
+       CDB_FIND_FILL0 = CDB_PUT_REPLACE0
 };
 
 int cdb_make_start(struct cdb_make *cdbmp, int fd);
-int cdb_make_add(struct cdb_make *cdbmp,
-                 const void *key, unsigned klen,
-                 const void *val, unsigned vlen);
-int cdb_make_exists(struct cdb_make *cdbmp,
-                    const void *key, unsigned klen);
-int cdb_make_find(struct cdb_make *cdbmp,
-                  const void *key, unsigned klen,
-                  enum cdb_put_mode mode);
-int cdb_make_put(struct cdb_make *cdbmp,
-                 const void *key, unsigned klen,
-                 const void *val, unsigned vlen,
-                 enum cdb_put_mode mode);
+int cdb_make_add(struct cdb_make *cdbmp, const void *key, unsigned klen,
+               const void *val, unsigned vlen);
+int cdb_make_exists(struct cdb_make *cdbmp, const void *key, unsigned klen);
+int cdb_make_find(struct cdb_make *cdbmp, const void *key, unsigned klen,
+               enum cdb_put_mode mode);
+int cdb_make_put(struct cdb_make *cdbmp, const void *key, unsigned klen,
+               const void *val, unsigned vlen, enum cdb_put_mode mode);
 int cdb_make_finish(struct cdb_make *cdbmp);
 
 /** Private API **/
-struct cdb_rec {
-  unsigned hval;
-  unsigned rpos;
+struct cdb_rec
+{
+       unsigned hval;
+       unsigned rpos;
 };
 
-struct cdb_rl {
-  struct cdb_rl *next;
-  unsigned cnt;
-  struct cdb_rec rec[254];
+struct cdb_rl
+{
+       struct cdb_rl *next;
+       unsigned cnt;
+       struct cdb_rec rec[254];
 };
 
-int _cdb_make_write(struct cdb_make *cdbmp,
-                   const unsigned char *ptr, unsigned len);
+int _cdb_make_write(struct cdb_make *cdbmp, const unsigned char *ptr,
+               unsigned len);
 int _cdb_make_fullwrite(int fd, const unsigned char *buf, unsigned len);
 int _cdb_make_flush(struct cdb_make *cdbmp);
-int _cdb_make_add(struct cdb_make *cdbmp, unsigned hval,
-                  const void *key, unsigned klen,
-                  const void *val, unsigned vlen);
+int _cdb_make_add(struct cdb_make *cdbmp, unsigned hval, const void *key,
+               unsigned klen, const void *val, unsigned vlen);
 
 #ifdef __cplusplus
 } /* extern "C" */
index d3ae8c01b7e9dcbe6309a58935dc16d678a253ff..af7b252560a06a623464120b2163797ba73efd74 100644 (file)
@@ -56,7 +56,9 @@ cdb_init(struct cdb *cdbp, int fd)
        cdbp->cdb_fd = fd;
        cdbp->cdb_fsize = fsize;
        cdbp->cdb_mem = mem;
-
+       cdbp->mtime = st.st_mtime;
+       cdbp->check_timer_ev = NULL;
+       cdbp->check_timer_tv = NULL;
 
        cdbp->cdb_vpos = cdbp->cdb_vlen = 0;
        cdbp->cdb_kpos = cdbp->cdb_klen = 0;
@@ -82,6 +84,12 @@ cdb_free(struct cdb *cdbp)
                cdbp->cdb_mem = NULL;
        }
        cdbp->cdb_fsize = 0;
+
+       if (cdbp->check_timer_ev) {
+               evtimer_del (cdbp->check_timer_ev);
+               g_free (cdbp->check_timer_ev);
+               g_free (cdbp->check_timer_tv);
+       }
 }
 
 const void *
@@ -103,3 +111,45 @@ cdb_read(const struct cdb *cdbp, void *buf, unsigned len, unsigned pos)
        memcpy (buf, data, len);
        return 0;
 }
+
+static void
+cdb_timer_callback (int fd, short what, gpointer ud)
+{
+       struct cdb *cdbp = ud;
+       gint nfd;
+       struct stat st;
+
+       /* Check cdb file for modifications */
+       if (stat (cdbp->filename, &st) != -1) {
+               if (st.st_mtime > cdbp->mtime) {
+                       if ((nfd = open (cdbp->filename, O_RDONLY)) != -1) {
+                               if (cdbp->cdb_mem) {
+#ifdef _WIN32
+                                       UnmapViewOfFile((void*) cdbp->cdb_mem);
+#else
+                                       munmap ((void*) cdbp->cdb_mem, cdbp->cdb_fsize);
+#endif /* _WIN32 */
+                                       cdbp->cdb_mem = NULL;
+                               }
+                               (void)close (cdbp->cdb_fd);
+                               cdbp->cdb_fsize = 0;
+                               (void)cdb_init (cdbp, fd);
+                       }
+               }
+       }
+
+       evtimer_add (cdbp->check_timer_ev, cdbp->check_timer_tv);
+}
+
+void
+cdb_add_timer(struct cdb *cdbp, unsigned seconds)
+{
+       cdbp->check_timer_ev = g_malloc (sizeof (struct event));
+       cdbp->check_timer_tv = g_malloc (sizeof (struct timeval));
+
+       cdbp->check_timer_tv->tv_sec = seconds;
+       cdbp->check_timer_tv->tv_usec = 0;
+
+       evtimer_set (cdbp->check_timer_ev, cdb_timer_callback, cdbp);
+       evtimer_add (cdbp->check_timer_ev, cdbp->check_timer_tv);
+}
index ef6041d7c1c3420ea47a3d206d670764ddc1d37b..61bcf1df44821a9351c358e0e048552a9adc51a7 100644 (file)
@@ -24,6 +24,8 @@
 #include "lua_common.h"
 #include "../cdb/cdb.h"
 
+#define CDB_REFRESH_TIME 60
+
 LUA_FUNCTION_DEF (cdb, create);
 LUA_FUNCTION_DEF (cdb, lookup);
 LUA_FUNCTION_DEF (cdb, get_name);
@@ -102,6 +104,14 @@ lua_cdb_lookup (lua_State *L)
        gsize                           vlen;
        goffset                         vpos;
 
+       /*
+        * XXX: this code is placed here because event_loop is called inside workers, so start
+        * monitoring on first check, not on creation
+        */
+       if (cdb->check_timer_ev == NULL) {
+               cdb_add_timer (cdb, CDB_REFRESH_TIME);
+       }
+
        what = luaL_checkstring (L, 2);
        if (cdb_find (cdb, what, strlen (what)) > 0) {
                /* Extract and push value to lua as string */
@@ -126,6 +136,7 @@ lua_cdb_destroy (lua_State *L)
 
        if (cdb) {
                cdb_free (cdb);
+               (void)close (cdb->cdb_fd);
                g_free (cdb->filename);
                g_free (cdb);
        }
@@ -146,7 +157,7 @@ luaopen_cdb (lua_State * L)
        lua_rawset (L, -3);
 
        luaL_openlib (L, NULL, cdblib_m, 0);
-       luaL_openlib(L, "cdb", cdblib_f, 0);
+       luaL_openlib (L, "cdb", cdblib_f, 0);
 
        return 1;
 }