[conntrack-tools] fix broken normal deletion in caches

Pablo Neira netfilter-cvslog-bounces at lists.netfilter.org
Fri Aug 1 14:35:54 CEST 2008


Gitweb:		http://git.netfilter.org/cgi-bin/gitweb.cgi?p=conntrack-tools.git;a=commit;h=6356d191a6d97483ad904fa1c8279a30564220cf
commit 6356d191a6d97483ad904fa1c8279a30564220cf
Author:     Pablo Neira Ayuso <pablo at netfilter.org>
AuthorDate: Fri Aug 1 14:35:47 2008 +0200
Commit:     Pablo Neira Ayuso <pablo at netfilter.org>
CommitDate: Fri Aug 1 14:35:47 2008 +0200

    fix broken normal deletion in caches
    
    This patch fixes the non-timer-based cache deletion. This bug affects
    the alarm-based approach since the backup replicas did not get the
    deletion event, thus, delaying the deletion.
    
    This patch introduces cache_find() to look up for a conntrack object
    and __cache_del_timer() to perform direct deletions by means of the
    pointer obtained with cache_find().
    
    Signed-off-by: Pablo Neira Ayuso <pablo at netfilter.org>
       via  6356d191a6d97483ad904fa1c8279a30564220cf (commit)
      from  ff402549052eb4b98ac9404a2f273d78ce323c94 (commit)

Those revisions listed above that are new to this repository have
not appeared on any other notification email; so we list those
revisions in full, below.

- Log -----------------------------------------------------------------
commit 6356d191a6d97483ad904fa1c8279a30564220cf
Author: Pablo Neira Ayuso <pablo at netfilter.org>
Date:   Fri Aug 1 14:35:47 2008 +0200

    fix broken normal deletion in caches
    
    This patch fixes the non-timer-based cache deletion. This bug affects
    the alarm-based approach since the backup replicas did not get the
    deletion event, thus, delaying the deletion.
    
    This patch introduces cache_find() to look up for a conntrack object
    and __cache_del_timer() to perform direct deletions by means of the
    pointer obtained with cache_find().
    
    Signed-off-by: Pablo Neira Ayuso <pablo at netfilter.org>

-----------------------------------------------------------------------

 include/cache.h |    3 +-
 src/cache.c     |   62 +++++++++++++++++++++++++++---------------------------
 src/sync-mode.c |   19 ++++++++--------
 3 files changed, 42 insertions(+), 42 deletions(-)
This patch fixes the non-timer-based cache deletion. This bug affects
the alarm-based approach since the backup replicas did not get the
deletion event, thus, delaying the deletion.

This patch introduces cache_find() to look up for a conntrack object
and __cache_del_timer() to perform direct deletions by means of the
pointer obtained with cache_find().

Signed-off-by: Pablo Neira Ayuso <pablo at netfilter.org>

diff --git a/include/cache.h b/include/cache.h
index 442a563..e2e2e34 100644
--- a/include/cache.h
+++ b/include/cache.h
@@ -82,7 +82,8 @@ struct us_conntrack *cache_add(struct cache *c, struct nf_conntrack *ct);
 struct us_conntrack *cache_update(struct cache *c, struct nf_conntrack *ct);
 struct us_conntrack *cache_update_force(struct cache *c, struct nf_conntrack *ct);
 int cache_del(struct cache *c, struct nf_conntrack *ct);
-struct us_conntrack *cache_del_timeout(struct cache *c, struct nf_conntrack *ct, int timeout);
+int __cache_del_timer(struct cache *c, struct us_conntrack *u, int timeout);
+struct us_conntrack *cache_find(struct cache *c, struct nf_conntrack *ct);
 int cache_test(struct cache *c, struct nf_conntrack *ct);
 void cache_stats(const struct cache *c, int fd);
 struct us_conntrack *cache_get_conntrack(struct cache *, void *);
diff --git a/src/cache.c b/src/cache.c
index a73854f..7cd5ac7 100644
--- a/src/cache.c
+++ b/src/cache.c
@@ -321,7 +321,13 @@ static void __del2(struct cache *c, struct us_conntrack *u)
 	free(p);
 }
 
-static int __del(struct cache *c, struct nf_conntrack *ct)
+static void __cache_del(struct cache *c, struct us_conntrack *u)
+{
+	del_alarm(&u->alarm);
+	__del2(c, u);
+}
+
+int cache_del(struct cache *c, struct nf_conntrack *ct)
 {
 	size_t size = c->h->datasize;
 	char buf[size];
@@ -331,16 +337,7 @@ static int __del(struct cache *c, struct nf_conntrack *ct)
 
 	u = (struct us_conntrack *) hashtable_test(c->h, u);
 	if (u) {
-		del_alarm(&u->alarm);
-		__del2(c, u);
-		return 1;
-	}
-	return 0;
-}
-
-int cache_del(struct cache *c, struct nf_conntrack *ct)
-{
-	if (__del(c, ct)) {
+		__cache_del(c, u);
 		c->del_ok++;
 		return 1;
 	}
@@ -356,33 +353,36 @@ static void __del_timeout(struct alarm_block *a, void *data)
 	__del2(u->cache, u);
 }
 
-struct us_conntrack *
-cache_del_timeout(struct cache *c, struct nf_conntrack *ct, int timeout)
+int
+__cache_del_timer(struct cache *c, struct us_conntrack *u, int timeout)
+{
+	if (timeout <= 0) {
+		__cache_del(c, u);
+		return 1;
+	}
+	if (!alarm_pending(&u->alarm)) {
+		add_alarm(&u->alarm, timeout, 0);
+		/*
+		 * increase stats even if this entry was not really
+		 * removed yet. We do not want to make people think
+		 * that the replication protocol does not work 
+		 * properly.
+		 */
+		c->del_ok++;
+		return 1;
+	}
+	return 0;
+}
+
+struct us_conntrack *cache_find(struct cache *c, struct nf_conntrack *ct)
 {
 	size_t size = c->h->datasize;
 	char buf[size];
 	struct us_conntrack *u = (struct us_conntrack *) buf;
 
-	if (timeout <= 0)
-		cache_del(c, ct);
-
 	u->ct = ct;
 
-	u = (struct us_conntrack *) hashtable_test(c->h, u);
-	if (u) {
-		if (!alarm_pending(&u->alarm)) {
-			add_alarm(&u->alarm, timeout, 0);
-			/*
-			 * increase stats even if this entry was not really
-			 * removed yet. We do not want to make people think
-			 * that the replication protocol does not work 
-			 * properly.
-			 */
-			c->del_ok++;
-			return u;
-		}
-	}
-	return NULL;
+	return ((struct us_conntrack *) hashtable_test(c->h, u));
 }
 
 struct us_conntrack *cache_get_conntrack(struct cache *c, void *data)
diff --git a/src/sync-mode.c b/src/sync-mode.c
index 0f3760e..56c30af 100644
--- a/src/sync-mode.c
+++ b/src/sync-mode.c
@@ -407,10 +407,8 @@ static int purge_step(void *data1, void *data2)
 	ret = nfct_query(h, NFCT_Q_GET, u->ct);
 	if (ret == -1 && errno == ENOENT) {
 		debug_ct(u->ct, "overrun purge resync");
-		if (cache_del_timeout(STATE_SYNC(internal),
-				      u->ct, 
-				      CONFIG(del_timeout)))
-			mcast_send_sync(u, NFCT_Q_DESTROY);
+		mcast_send_sync(u, NFCT_Q_DESTROY);
+		__cache_del_timer(STATE_SYNC(internal), u, CONFIG(del_timeout));
 	}
 
 	return 0;
@@ -502,15 +500,16 @@ static int event_destroy_sync(struct nf_conntrack *ct)
 	if (!CONFIG(cache_write_through))
 		nfct_attr_unset(ct, ATTR_TIMEOUT);
 
-	u = cache_del_timeout(STATE_SYNC(internal), ct, CONFIG(del_timeout));
-	if (u != NULL) {
-		mcast_send_sync(u, NFCT_Q_DESTROY);
-		debug_ct(ct, "internal destroy");
-		return 1;
-	} else {
+	u = cache_find(STATE_SYNC(internal), ct);
+	if (u == NULL) {
 		debug_ct(ct, "can't destroy");
 		return 0;
 	}
+
+	mcast_send_sync(u, NFCT_Q_DESTROY);
+	__cache_del_timer(STATE_SYNC(internal), u, CONFIG(del_timeout));
+	debug_ct(ct, "internal destroy");
+	return 1;
 }
 
 struct ct_mode sync_mode = {



More information about the netfilter-cvslog mailing list