From patchwork Thu Dec 20 23:38:17 2012 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Eric Dumazet X-Patchwork-Id: 207743 X-Patchwork-Delegate: davem@davemloft.net Return-Path: X-Original-To: patchwork-incoming@ozlabs.org Delivered-To: patchwork-incoming@ozlabs.org Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by ozlabs.org (Postfix) with ESMTP id 07FFB2C0092 for ; Fri, 21 Dec 2012 10:43:57 +1100 (EST) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1751952Ab2LTXnz (ORCPT ); Thu, 20 Dec 2012 18:43:55 -0500 Received: from mail-pb0-f46.google.com ([209.85.160.46]:54309 "EHLO mail-pb0-f46.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1751805Ab2LTXnx (ORCPT ); Thu, 20 Dec 2012 18:43:53 -0500 Received: by mail-pb0-f46.google.com with SMTP id wy7so2306187pbc.5 for ; Thu, 20 Dec 2012 15:43:53 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=x-received:subject:from:to:cc:in-reply-to:references:content-type :date:message-id:mime-version:x-mailer:content-transfer-encoding; bh=csaf1LKZGnbJMxShlBqIp36BdV2iE7s3w+p626DKmJQ=; b=bv1jl4/Vhi2jcuYytNgOOT0zAhIfs0KlY/l8e84z9nWRAWqE7h3vAKaM5VLHtnCael fmIxNbk28+Mw1P4lsanU6xs8si2bYFkgEYvNv+KUU4Ermbqh3De38jZ0dQM6o83rXZPu CFOp657thqZpvZOaDAt66dRERGmMyipE1OOBhJeZ1r6bqTNpOPVg6rr/JJuDbwkD1D6H bGWuFqmTEtO2upqtQ6M4zCoRezwXyxBUY9VYRxgM1C/e+jdepDKgjyYM788cHK0o9apX 0T8e+FfZvNEvvM2XeLUDLqqNhmAq3JAC9T+oBDk2QziF4SCaXlSc3a8ncYT0vF6HZsSY ifAA== X-Received: by 10.68.209.136 with SMTP id mm8mr33914323pbc.146.1356046700632; Thu, 20 Dec 2012 15:38:20 -0800 (PST) Received: from ?IPv6:2620:0:1000:3304:224:d7ff:fee3:2a94? ([2620:0:1000:3304:224:d7ff:fee3:2a94]) by mx.google.com with ESMTPS id qt3sm5804918pbb.32.2012.12.20.15.38.18 (version=SSLv3 cipher=OTHER); Thu, 20 Dec 2012 15:38:19 -0800 (PST) Subject: Re: TUN problems (regression?) From: Eric Dumazet To: Paul Moore Cc: Jason Wang , netdev@vger.kernel.org In-Reply-To: <4151394.nMo40zlg68@sifl> References: <4151394.nMo40zlg68@sifl> Date: Thu, 20 Dec 2012 15:38:17 -0800 Message-ID: <1356046697.21834.3606.camel@edumazet-glaptop> Mime-Version: 1.0 X-Mailer: Evolution 2.28.3 Sender: netdev-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: netdev@vger.kernel.org On Thu, 2012-12-20 at 18:16 -0500, Paul Moore wrote: > [CC'ing netdev in case this is a known problem I just missed ...] > > Hi Jason, > > I started doing some more testing with the multiqueue TUN changes and I ran > into a problem when running tunctl: running it once w/o arguments works as > expected, but running it a second time results in failure and a > kmem_cache_sanity_check() failure. The problem appears to be very repeatable > on my test VM and happens independent of the LSM/SELinux fixup patches. > > Have you seen this before? > Obviously code in tun_flow_init() is wrong... static int tun_flow_init(struct tun_struct *tun) { int i; tun->flow_cache = kmem_cache_create("tun_flow_cache", sizeof(struct tun_flow_entry), 0, 0, NULL); if (!tun->flow_cache) return -ENOMEM; ... } I have no idea why we would need a kmem_cache per tun_struct, and why we even need a kmem_cache. I would try following patch : drivers/net/tun.c | 24 +++--------------------- 1 file changed, 3 insertions(+), 21 deletions(-) Acked-by: Stephen Hemminger Acked-by: Jason Wang --- To unsubscribe from this list: send the line "unsubscribe netdev" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html diff --git a/drivers/net/tun.c b/drivers/net/tun.c index 504f7f1..fbd106e 100644 --- a/drivers/net/tun.c +++ b/drivers/net/tun.c @@ -180,7 +180,6 @@ struct tun_struct { int debug; #endif spinlock_t lock; - struct kmem_cache *flow_cache; struct hlist_head flows[TUN_NUM_FLOW_ENTRIES]; struct timer_list flow_gc_timer; unsigned long ageing_time; @@ -209,8 +208,8 @@ static struct tun_flow_entry *tun_flow_create(struct tun_struct *tun, struct hlist_head *head, u32 rxhash, u16 queue_index) { - struct tun_flow_entry *e = kmem_cache_alloc(tun->flow_cache, - GFP_ATOMIC); + struct tun_flow_entry *e = kmalloc(sizeof(*e), GFP_ATOMIC); + if (e) { tun_debug(KERN_INFO, tun, "create flow: hash %u index %u\n", rxhash, queue_index); @@ -223,19 +222,12 @@ static struct tun_flow_entry *tun_flow_create(struct tun_struct *tun, return e; } -static void tun_flow_free(struct rcu_head *head) -{ - struct tun_flow_entry *e - = container_of(head, struct tun_flow_entry, rcu); - kmem_cache_free(e->tun->flow_cache, e); -} - static void tun_flow_delete(struct tun_struct *tun, struct tun_flow_entry *e) { tun_debug(KERN_INFO, tun, "delete flow: hash %u index %u\n", e->rxhash, e->queue_index); hlist_del_rcu(&e->hash_link); - call_rcu(&e->rcu, tun_flow_free); + kfree_rcu(e, rcu); } static void tun_flow_flush(struct tun_struct *tun) @@ -833,12 +825,6 @@ static int tun_flow_init(struct tun_struct *tun) { int i; - tun->flow_cache = kmem_cache_create("tun_flow_cache", - sizeof(struct tun_flow_entry), 0, 0, - NULL); - if (!tun->flow_cache) - return -ENOMEM; - for (i = 0; i < TUN_NUM_FLOW_ENTRIES; i++) INIT_HLIST_HEAD(&tun->flows[i]); @@ -854,10 +840,6 @@ static void tun_flow_uninit(struct tun_struct *tun) { del_timer_sync(&tun->flow_gc_timer); tun_flow_flush(tun); - - /* Wait for completion of call_rcu()'s */ - rcu_barrier(); - kmem_cache_destroy(tun->flow_cache); } /* Initialize net device. */