diff --git a/net/sched/act_api.c b/net/sched/act_api.c index 0eb545bcb2476fc282b5cc456a2486c4f48f7bb8..a306974e2fb4bfe866628d84b8c4aa7ae4fddb8c 100644 --- a/net/sched/act_api.c +++ b/net/sched/act_api.c @@ -296,10 +296,12 @@ int tcf_idr_create(struct tc_action_net *tn, u32 index, struct nlattr *est, spin_lock_init(&p->tcfa_lock); /* user doesn't specify an index */ if (!index) { + idr_preload(GFP_KERNEL); spin_lock_bh(&idrinfo->lock); err = idr_alloc_ext(idr, NULL, &idr_index, 1, 0, - GFP_KERNEL); + GFP_ATOMIC); spin_unlock_bh(&idrinfo->lock); + idr_preload_end(); if (err) { err3: free_percpu(p->cpu_qstats); @@ -307,10 +309,12 @@ int tcf_idr_create(struct tc_action_net *tn, u32 index, struct nlattr *est, } p->tcfa_index = idr_index; } else { + idr_preload(GFP_KERNEL); spin_lock_bh(&idrinfo->lock); err = idr_alloc_ext(idr, NULL, NULL, index, index + 1, - GFP_KERNEL); + GFP_ATOMIC); spin_unlock_bh(&idrinfo->lock); + idr_preload_end(); if (err) goto err3; p->tcfa_index = index;