From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1757524Ab1E3QrI (ORCPT ); Mon, 30 May 2011 12:47:08 -0400 Received: from casper.infradead.org ([85.118.1.10]:40417 "EHLO casper.infradead.org" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1757418Ab1E3QrH convert rfc822-to-8bit (ORCPT ); Mon, 30 May 2011 12:47:07 -0400 Subject: Re: Very high CPU load when idle with 3.0-rc1 From: Peter Zijlstra To: paulmck@linux.vnet.ibm.com Cc: Damien Wyart , Ingo Molnar , Mike Galbraith , linux-kernel@vger.kernel.org In-Reply-To: <20110530162354.GQ2668@linux.vnet.ibm.com> References: <20110530055924.GA9169@brouette> <1306755291.1200.2872.camel@twins> <20110530162354.GQ2668@linux.vnet.ibm.com> Content-Type: text/plain; charset="UTF-8" Content-Transfer-Encoding: 8BIT Date: Mon, 30 May 2011 18:46:21 +0200 Message-ID: <1306773981.23844.2.camel@twins> Mime-Version: 1.0 X-Mailer: Evolution 2.30.3 Sender: linux-kernel-owner@vger.kernel.org List-ID: X-Mailing-List: linux-kernel@vger.kernel.org On Mon, 2011-05-30 at 09:23 -0700, Paul E. McKenney wrote: > > @@ -1772,18 +1772,30 @@ static int __init rcu_spawn_kthreads(void) > > { > > int cpu; > > struct rcu_node *rnp; > > + struct task_struct *t; > > > > rcu_kthreads_spawnable = 1; > > for_each_possible_cpu(cpu) { > > per_cpu(rcu_cpu_has_work, cpu) = 0; > > - if (cpu_online(cpu)) > > + if (cpu_online(cpu)) { > > (void)rcu_spawn_one_cpu_kthread(cpu); > > + t = per_cpu(rcu_cpu_kthread_task, cpu); > > + if (t) > > + wake_up_process(t); > > + } > > Would it be OK to simplify the code a bit by doing this initial wakeup > in rcu_spawn_one_cpu_kthread() itself? My thought would be to rearrange > rcu_spawn_one_cpu_kthread() as follows: > well, no that would get us back to waking a task affine to an offline cpu :-) > > @@ -2209,6 +2221,31 @@ static void __cpuinit rcu_online_kthreads(int cpu) > > } > > > > /* > > + * kthread_create() creates threads in TASK_UNINTERRUPTIBLE state, > > + * but the RCU threads are woken on demand, and if demand is low this > > + * could be a while triggering the hung task watchdog. > > + * > > + * In order to avoid this, poke all tasks once the CPU is fully > > + * up and running. > > + */ > > +static void __cpuinit rcu_online_kthreads(int cpu) > > +{ > > + struct rcu_data *rdp = per_cpu_ptr(rcu_state->rda, cpu); > > + struct rcu_node *rnp = rdp->mynode; > > + struct task_struct *t; > > + > > + t = per_cpu(rcu_cpu_kthread_task, cpu); > > + if (t) > > + wake_up_process(t); > > + > > + t = rnp->node_kthread_task; > > + if (t) > > + wake_up_process(t); > > + > > + rcu_wake_one_boost_kthread(rnp); > > Interesting... So we are really awakening them twice, once at creation > time to get them to sleep interruptibly, and a second time when the CPU > comes online. > > What does this second set of wake_up_process() calls do? Ah, not so, see the initial one is conditional on cpu_online() and will fail for the CPU_UP_PREPARE case, this new function will be ran from CPU_ONLINE to then issue the first wakeup. The distinction comes from the initialize while cpus are already running vs hotplug.