commit 817252c2a475371f9764883c7d0f0cde63b3cfe8 Author: Patrick McHardy Date: Mon Nov 26 16:00:50 2007 +0100 [XFRM]: Fix leak of expired xfrm_states The xfrm_timer calls __xfrm_state_delete, which drops the final reference manually without triggering destruction of the state. Signed-off-by: Patrick McHardy diff --git a/net/xfrm/xfrm_state.c b/net/xfrm/xfrm_state.c index 224b44e..11e9a48 100644 --- a/net/xfrm/xfrm_state.c +++ b/net/xfrm/xfrm_state.c @@ -416,7 +416,7 @@ static inline unsigned long make_jiffies(long secs) static void xfrm_timer_handler(unsigned long data) { - struct xfrm_state *x = (struct xfrm_state*)data; + struct xfrm_state *x = (struct xfrm_state*)data, *del = NULL; unsigned long now = get_seconds(); long next = LONG_MAX; int warn = 0; @@ -479,6 +479,8 @@ expired: goto resched; } + del = x; + xfrm_state_hold(del); err = __xfrm_state_delete(x); if (!err && x->id.spi) km_state_expired(x, 1, 0); @@ -488,6 +490,8 @@ expired: out: spin_unlock(&x->lock); + if (del) + xfrm_state_put(del); } static void xfrm_replay_timer_handler(unsigned long data);