This patch modifies __nf_ct_refresh_acct() and other timeout updating functions to use mod_timer_noact() which will save one spin_lock_irqsave / spin_lock_irqrestore pair per conntrack timer update. It also removes a general race-condition during deletion of conntracks which relies on del_timer() in order to initiate the slaughter of a conntrack entry. Signed-off-by: Martin Josefsson --- net/netfilter/nf_conntrack_core.c | 9 +++------ net/netfilter/nf_conntrack_expect.c | 4 +--- net/netfilter/nf_conntrack_netlink.c | 5 +---- 3 files changed, 5 insertions(+), 13 deletions(-) Index: linux-2.6.19-rc3-git4.quilt/net/netfilter/nf_conntrack_core.c =================================================================== --- linux-2.6.19-rc3-git4.quilt.orig/net/netfilter/nf_conntrack_core.c 2006-11-02 19:16:02.000000000 +0100 +++ linux-2.6.19-rc3-git4.quilt/net/netfilter/nf_conntrack_core.c 2006-11-02 19:16:05.000000000 +0100 @@ -929,14 +929,11 @@ void __nf_ct_refresh_acct(struct nf_conn unsigned long newtime = jiffies + extra_jiffies; /* Only update the timeout if the new timeout is at least - HZ jiffies from the old timeout. Need del_timer for race - avoidance (may already be dying). */ + HZ jiffies from the old timeout. Need mod_timer_noact for + race avoidance (may already be dying). */ if (newtime - ct->timeout.expires >= HZ - && del_timer(&ct->timeout)) { - ct->timeout.expires = newtime; - add_timer(&ct->timeout); + && mod_timer_noact(&ct->timeout, newtime)) event = IPCT_REFRESH; - } } #ifdef CONFIG_NF_CT_ACCT Index: linux-2.6.19-rc3-git4.quilt/net/netfilter/nf_conntrack_expect.c =================================================================== --- linux-2.6.19-rc3-git4.quilt.orig/net/netfilter/nf_conntrack_expect.c 2006-11-02 19:15:47.000000000 +0100 +++ linux-2.6.19-rc3-git4.quilt/net/netfilter/nf_conntrack_expect.c 2006-11-02 19:16:05.000000000 +0100 @@ -242,11 +242,9 @@ static inline int refresh_timer(struct n { struct nf_conn_help *master_help = nfct_help(i->master); - if (!del_timer(&i->timeout)) + if (!mod_timer_noact(&i->timeout, master_help->helper->timeout*HZ)) return 0; - i->timeout.expires = jiffies + master_help->helper->timeout*HZ; - add_timer(&i->timeout); return 1; } Index: linux-2.6.19-rc3-git4.quilt/net/netfilter/nf_conntrack_netlink.c =================================================================== --- linux-2.6.19-rc3-git4.quilt.orig/net/netfilter/nf_conntrack_netlink.c 2006-11-02 19:15:54.000000000 +0100 +++ linux-2.6.19-rc3-git4.quilt/net/netfilter/nf_conntrack_netlink.c 2006-11-02 19:16:05.000000000 +0100 @@ -911,12 +911,9 @@ ctnetlink_change_timeout(struct nf_conn { u_int32_t timeout = ntohl(*(u_int32_t *)NFA_DATA(cda[CTA_TIMEOUT-1])); - if (!del_timer(&ct->timeout)) + if (!mod_timer_noact(&ct->timeout, jiffies + timeout * HZ)) return -ETIME; - ct->timeout.expires = jiffies + timeout * HZ; - add_timer(&ct->timeout); - return 0; }