From: "Srivatsa S. Bhat" <srivatsa.bhat@linux.vnet.ibm.com>
To: Sam Ravnborg <sam@ravnborg.org>
Cc: David Miller <davem@davemloft.net>,
tglx@linutronix.de, peterz@infradead.org,
paulmck@linux.vnet.ibm.com, rusty@rustcorp.com.au,
mingo@kernel.org, yong.zhang0@gmail.com,
akpm@linux-foundation.org, vatsa@linux.vnet.ibm.com, rjw@sisk.pl,
linux-arch@vger.kernel.org, linux-kernel@vger.kernel.org,
nikunj@linux.vnet.ibm.com, vapier@gentoo.org, konrad@gaisler.com,
tkhai@yandex.ru, sparclinux@vger.kernel.org
Subject: Re: [UPDATED PATCH 21/27] sparc32, smpboot: Use generic SMP booting infrastructure
Date: Sat, 02 Jun 2012 21:28:35 +0530 [thread overview]
Message-ID: <4FCA382B.6050601@linux.vnet.ibm.com> (raw)
In-Reply-To: <20120602151348.GA17409@merkur.ravnborg.org>
On 06/02/2012 08:43 PM, Sam Ravnborg wrote:
>>
>>> I will try to dive into this and see if I on the sparc32 side
>>> can make leon behave like the other platforms, and then
>>> unify some of the smp cpu boot stuff such that we then
>>> can introduce the generalization from your patch.
>
> This is what I came up with.
> I modelled this over your patch-set to make it
> simpler to convert to the generic scheme.
>
Thanks a lot for doing this :-)
> I realised a bit more how CPU's are started up on sparc32.
> So I think all of leon, sun4m and sun4d should work with this.
>
> But my SUN box is defunct atm. so I have not tested it.
> Comments appreciated!
>
> PS. I used the ugly __names for now.
> As soon as you have found a better set of names this should
> be fixed here too.
>
As I mentioned in my other mail, I am thinking of changing them to
arch_cpu_pre_starting(), arch_cpu_pre_online() and arch_cpu_post_online().
Let me know what you think of those names.
Would you kindly add a changelog and your sign-off to this patch?
>
> diff --git a/arch/sparc/kernel/kernel.h b/arch/sparc/kernel/kernel.h
> index 291bb5d..2bc1c6d 100644
> --- a/arch/sparc/kernel/kernel.h
> +++ b/arch/sparc/kernel/kernel.h
> @@ -48,6 +48,10 @@ extern void sun4m_init_IRQ(void);
> extern void sun4m_unmask_profile_irq(void);
> extern void sun4m_clear_profile_irq(int cpu);
>
> +/* sun4m_smp.c */
> +void sun4m_cpu_pre_starting(void);
> +void sun4m_cpu_pre_online(void);
> +
> /* sun4d_irq.c */
> extern spinlock_t sun4d_imsk_lock;
>
> @@ -60,6 +64,14 @@ extern int show_sun4d_interrupts(struct seq_file *, void *);
> extern void sun4d_distribute_irqs(void);
> extern void sun4d_free_irq(unsigned int irq, void *dev_id);
>
> +/* sun4d_smp.c */
> +void sun4d_cpu_pre_starting(void);
> +void sun4d_cpu_pre_online(void);
> +
> +/* leon_smp.c */
> +void leon_cpu_pre_starting(void);
> +void leon_cpu_pre_online(void);
> +
> /* head_32.S */
> extern unsigned int t_nmi[];
> extern unsigned int linux_trap_ipi15_sun4d[];
> diff --git a/arch/sparc/kernel/leon_smp.c b/arch/sparc/kernel/leon_smp.c
> index 0f3fb6d..0b028b3 100644
> --- a/arch/sparc/kernel/leon_smp.c
> +++ b/arch/sparc/kernel/leon_smp.c
> @@ -69,31 +69,20 @@ static inline unsigned long do_swap(volatile unsigned long *ptr,
> return val;
> }
>
> -void __cpuinit leon_callin(void)
> +void __cpuinit leon_cpu_pre_starting(void)
> {
> - int cpuid = hard_smp_processor_id();
> -
> - local_ops->cache_all();
> - local_ops->tlb_all();
> leon_configure_cache_smp();
> +}
>
> - notify_cpu_starting(cpuid);
> -
> - /* Get our local ticker going. */
> - register_percpu_ce(cpuid);
> -
> - calibrate_delay();
> - smp_store_cpu_info(cpuid);
>
> - local_ops->cache_all();
> - local_ops->tlb_all();
> +void __cpuinit cpu_cpu_pre_starting(void *unused)
Shouldn't this be leon_cpu_pre_online()? And the parameters
should be consistent too (here it expects a void*, but it is
called with no arguments...)
> +{
> + int cpuid = hard_smp_processor_id();
>
> - /*
> - * Unblock the master CPU _only_ when the scheduler state
> - * of all secondary CPUs will be up-to-date, so after
> - * the SMP initialization the master will be just allowed
> - * to call the scheduler code.
> - * Allow master to continue.
> + /* Allow master to continue. The master will then give us the
> + * go-ahead by setting the smp_commenced_mask and will wait without
> + * timeouts until our setup is completed fully (signified by
> + * our bit being set in the cpu_online_mask).
> */
> do_swap(&cpu_callin_map[cpuid], 1);
>
> @@ -110,9 +99,6 @@ void __cpuinit leon_callin(void)
>
> while (!cpumask_test_cpu(cpuid, &smp_commenced_mask))
> mb();
> -
> - local_irq_enable();
> - set_cpu_online(cpuid, true);
> }
>
> /*
> diff --git a/arch/sparc/kernel/smp_32.c b/arch/sparc/kernel/smp_32.c
> index 79db45e..2e2990f 100644
> --- a/arch/sparc/kernel/smp_32.c
> +++ b/arch/sparc/kernel/smp_32.c
> @@ -20,6 +20,7 @@
> #include <linux/seq_file.h>
> #include <linux/cache.h>
> #include <linux/delay.h>
> +#include <linux/cpu.h>
>
> #include <asm/ptrace.h>
> #include <linux/atomic.h>
> @@ -32,8 +33,10 @@
> #include <asm/cacheflush.h>
> #include <asm/tlbflush.h>
> #include <asm/cpudata.h>
> +#include <asm/timer.h>
> #include <asm/leon.h>
>
> +#include "kernel.h"
> #include "irq.h"
>
> volatile unsigned long cpu_callin_map[NR_CPUS] __cpuinitdata = {0,};
> @@ -294,6 +297,89 @@ int __cpuinit __cpu_up(unsigned int cpu, struct task_struct *tidle)
> return ret;
> }
>
> +void __cpuinit __cpu_pre_starting(void *unused)
> +{
> + local_ops->cache_all();
> + local_ops->tlb_all();
> +
> + switch(sparc_cpu_model) {
> + case sun4m:
> + sun4m_cpu_pre_starting();
Wouldn't it be better to have a provision to pass the
pointer down to these functions as well?
> + break;
> + case sun4d:
> + sun4d_cpu_pre_starting();
> + break;
> + case sparc_leon:
> + leon_cpu_pre_starting();
> + break;
> + default:
> + BUG();
> + }
> +}
> +
> +void __cpuinit __cpu_pre_online(void *unused)
> +{
> + unsigned int cpuid = hard_smp_processor_id();
> +
> + register_percpu_ce(cpuid);
> +
> + calibrate_delay();
> + smp_store_cpu_info(cpuid);
> +
> + local_ops->cache_all();
> + local_ops->tlb_all();
> +
> + switch(sparc_cpu_model) {
> + case sun4m:
> + sun4m_cpu_pre_online();
> + break;
> + case sun4d:
> + sun4d_cpu_pre_online();
> + break;
> + case sparc_leon:
> + leon_cpu_pre_starting();
Shouldn't this be leon_cpu_pre_online()?
> + break;
> + default:
> + BUG();
> + }
> +}
> +
> +void __cpuinit sparc_start_secondary(void *unused)
> +{
> + unsigned int cpu;
> +
> + /*
> + * SMP booting is extremely fragile in some architectures. So run
> + * the cpu initialization code first before anything else.
> + */
> + __cpu_pre_starting(NULL);
> +
Why not pass the pointer to __cpu_pre_starting() as well as the rest of
the functions?
> + preempt_disable();
> + cpu = smp_processor_id();
> +
> + /* Invoke the CPU_STARTING notifier callbacks */
> + notify_cpu_starting(cpu);
> +
> + __cpu_pre_online(NULL);
> +
> + /* Set the CPU in the cpu_online_mask */
> + set_cpu_online(cpu, true);
> +
> + /* Enable local interrupts now */
> + local_irq_enable();
> +
> + wmb();
> + cpu_idle();
> +
> + /* We should never reach here! */
> + BUG();
> +}
> +
> +void __cpuinit smp_callin(void)
> +{
> + sparc_start_secondary(NULL);
> +}
> +
> void smp_bogo(struct seq_file *m)
> {
> int i;
> diff --git a/arch/sparc/kernel/sun4d_smp.c b/arch/sparc/kernel/sun4d_smp.c
> index ddaea31..bfbbc46 100644
> --- a/arch/sparc/kernel/sun4d_smp.c
> +++ b/arch/sparc/kernel/sun4d_smp.c
> @@ -50,10 +50,9 @@ static inline void show_leds(int cpuid)
> "i" (ASI_M_CTL));
> }
>
> -void __cpuinit smp4d_callin(void)
> +void __cpuinit sun4d_cpu_pre_starting(void)
> {
> int cpuid = hard_smp_processor_id();
> - unsigned long flags;
>
> /* Show we are alive */
> cpu_leds[cpuid] = 0x6;
> @@ -61,24 +60,14 @@ void __cpuinit smp4d_callin(void)
>
> /* Enable level15 interrupt, disable level14 interrupt for now */
> cc_set_imsk((cc_get_imsk() & ~0x8000) | 0x4000);
> +}
>
> - local_ops->cache_all();
> - local_ops->tlb_all();
> -
> - notify_cpu_starting(cpuid);
> - /*
> - * Unblock the master CPU _only_ when the scheduler state
> - * of all secondary CPUs will be up-to-date, so after
> - * the SMP initialization the master will be just allowed
> - * to call the scheduler code.
> - */
> - /* Get our local ticker going. */
> - register_percpu_ce(cpuid);
> +void __cpuinit sun4d_cpu_pre_online(void)
> +{
> + unsigned long flags;
> + int cpuid;
>
> - calibrate_delay();
> - smp_store_cpu_info(cpuid);
> - local_ops->cache_all();
> - local_ops->tlb_all();
> + cpuid = hard_smp_processor_id();
>
> /* Allow master to continue. */
> sun4d_swap((unsigned long *)&cpu_callin_map[cpuid], 1);
> @@ -106,16 +95,12 @@ void __cpuinit smp4d_callin(void)
> local_ops->cache_all();
> local_ops->tlb_all();
>
> - local_irq_enable(); /* We don't allow PIL 14 yet */
> -
> while (!cpumask_test_cpu(cpuid, &smp_commenced_mask))
> barrier();
>
> spin_lock_irqsave(&sun4d_imsk_lock, flags);
> cc_set_imsk(cc_get_imsk() & ~0x4000); /* Allow PIL 14 as well */
> spin_unlock_irqrestore(&sun4d_imsk_lock, flags);
> - set_cpu_online(cpuid, true);
> -
> }
>
> /*
> diff --git a/arch/sparc/kernel/sun4m_smp.c b/arch/sparc/kernel/sun4m_smp.c
> index 128af73..0cf6b4f 100644
> --- a/arch/sparc/kernel/sun4m_smp.c
> +++ b/arch/sparc/kernel/sun4m_smp.c
> @@ -34,30 +34,19 @@ swap_ulong(volatile unsigned long *ptr, unsigned long val)
> return val;
> }
>
> -void __cpuinit smp4m_callin(void)
> +void __cpuinit sun4m_cpu_pre_starting(void)
> {
> - int cpuid = hard_smp_processor_id();
> -
> - local_ops->cache_all();
> - local_ops->tlb_all();
> -
> - notify_cpu_starting(cpuid);
> -
> - register_percpu_ce(cpuid);
> -
> - calibrate_delay();
> - smp_store_cpu_info(cpuid);
> +}
>
> - local_ops->cache_all();
> - local_ops->tlb_all();
> +void __cpuinit sun4m_cpu_pre_online(void)
> +{
> + int cpuid = hard_smp_processor_id();
>
> - /*
> - * Unblock the master CPU _only_ when the scheduler state
> - * of all secondary CPUs will be up-to-date, so after
> - * the SMP initialization the master will be just allowed
> - * to call the scheduler code.
> + /* Allow master to continue. The master will then give us the
> + * go-ahead by setting the smp_commenced_mask and will wait without
> + * timeouts until our setup is completed fully (signified by
> + * our bit being set in the cpu_online_mask).
> */
> - /* Allow master to continue. */
> swap_ulong(&cpu_callin_map[cpuid], 1);
>
> /* XXX: What's up with all the flushes? */
> @@ -75,10 +64,6 @@ void __cpuinit smp4m_callin(void)
>
> while (!cpumask_test_cpu(cpuid, &smp_commenced_mask))
> mb();
> -
> - local_irq_enable();
> -
> - set_cpu_online(cpuid, true);
> }
>
> /*
> diff --git a/arch/sparc/kernel/trampoline_32.S b/arch/sparc/kernel/trampoline_32.S
> index af27aca..6cdb08c 100644
> --- a/arch/sparc/kernel/trampoline_32.S
> +++ b/arch/sparc/kernel/trampoline_32.S
> @@ -79,18 +79,15 @@ cpu3_startup:
> nop
>
> /* Start this processor. */
> - call smp4m_callin
> + call smp_callin
> nop
>
> - b,a smp_do_cpu_idle
> + b,a smp_panic
>
> .text
> .align 4
>
> -smp_do_cpu_idle:
> - call cpu_idle
> - mov 0, %o0
> -
> +smp_panic:
> call cpu_panic
> nop
>
> @@ -144,10 +141,10 @@ sun4d_cpu_startup:
> nop
>
> /* Start this processor. */
> - call smp4d_callin
> + call smp_callin
> nop
>
> - b,a smp_do_cpu_idle
> + b,a smp_panic
>
> __CPUINIT
> .align 4
> @@ -201,7 +198,7 @@ leon_smp_cpu_startup:
> nop
>
> /* Start this processor. */
> - call leon_callin
> + call smp_callin
I still didn't get how this solves the original problem of
not having sparc_cpu_model set to sparc_leon. You mentioned
that by the time we reach leon_smp_cpu_startup, that variable
is not set. Even inside leon_smp_cpu_startup, I don't immediately
see where it is set. Am I missing something?
> nop
>
> - b,a smp_do_cpu_idle
> + b,a smp_panic
>
Regards,
Srivatsa S. Bhat
next prev parent reply other threads:[~2012-06-02 15:59 UTC|newest]
Thread overview: 91+ messages / expand[flat|nested] mbox.gz Atom feed top
2012-06-01 9:10 [PATCH 00/27] Generic framework for SMP booting/CPU hotplug related code Srivatsa S. Bhat
2012-06-01 9:10 ` [PATCH 01/27] smpboot: Provide a generic method to boot secondary processors Srivatsa S. Bhat
2012-06-01 12:09 ` Srivatsa S. Bhat
2012-06-03 8:51 ` Yong Zhang
2012-06-03 11:22 ` Srivatsa S. Bhat
2012-06-04 2:18 ` Yong Zhang
2012-06-03 8:53 ` Yong Zhang
2012-06-03 11:33 ` Srivatsa S. Bhat
2012-06-03 11:39 ` Russell King - ARM Linux
2012-06-03 12:05 ` Srivatsa S. Bhat
2012-06-01 16:51 ` Sam Ravnborg
2012-06-01 22:29 ` Srivatsa S. Bhat
2012-06-04 10:32 ` Thomas Gleixner
2012-06-04 13:07 ` Srivatsa S. Bhat
2012-06-04 13:18 ` Thomas Gleixner
2012-06-04 16:53 ` Srivatsa S. Bhat
2012-06-05 5:11 ` Yong Zhang
2012-06-05 6:07 ` Srivatsa S. Bhat
2012-06-01 16:53 ` Sam Ravnborg
2012-06-01 22:41 ` Srivatsa S. Bhat
2012-06-02 15:16 ` Sam Ravnborg
2012-06-02 15:34 ` Srivatsa S. Bhat
2012-06-01 9:10 ` [PATCH 02/27] smpboot: Add provisions for arch-specific locking around cpu_online_mask Srivatsa S. Bhat
2012-06-01 12:12 ` Srivatsa S. Bhat
2012-06-01 9:11 ` [PATCH 04/27] smpboot, x86, xen: Determine smp booting implementations at run-time Srivatsa S. Bhat
2012-06-01 9:11 ` [PATCH 05/27] xen, cpu hotplug: Don't call cpu_bringup() in xen_play_dead() Srivatsa S. Bhat
2012-06-01 12:59 ` [Xen-devel] " Jan Beulich
2012-06-01 15:13 ` Srivatsa S. Bhat
2012-06-01 15:36 ` Jan Beulich
2012-06-02 18:06 ` Srivatsa S. Bhat
2012-06-05 16:49 ` Konrad Rzeszutek Wilk
2012-06-05 17:36 ` Srivatsa S. Bhat
2012-06-05 17:40 ` Thomas Gleixner
2012-06-05 17:48 ` Srivatsa S. Bhat
2012-06-01 9:11 ` [PATCH 06/27] xen, smpboot: Use generic SMP booting infrastructure Srivatsa S. Bhat
2012-06-01 9:11 ` [PATCH 07/27] x86, " Srivatsa S. Bhat
2012-06-04 14:29 ` Thomas Gleixner
2012-06-04 17:00 ` Srivatsa S. Bhat
2012-06-01 9:12 ` [PATCH 08/27] m32r: Fix horrible logic in smp_prepare_cpus() Srivatsa S. Bhat
2012-06-01 9:12 ` [PATCH 09/27] m32r, smpboot: Use generic SMP booting infrastructure Srivatsa S. Bhat
2012-06-01 9:12 ` [PATCH 10/27] mips, " Srivatsa S. Bhat
2012-06-03 8:25 ` Yong Zhang
2012-06-03 11:48 ` Srivatsa S. Bhat
2012-06-04 2:17 ` Yong Zhang
2012-06-01 9:12 ` [PATCH 11/27] sh, " Srivatsa S. Bhat
2012-06-01 9:12 ` [PATCH 12/27] tile, " Srivatsa S. Bhat
2012-06-01 18:07 ` Chris Metcalf
2012-06-01 9:13 ` [PATCH 13/27] hexagon, " Srivatsa S. Bhat
2012-06-01 9:13 ` [PATCH 14/27] ia64: Move holding of vector_lock to __setup_vector_irq() Srivatsa S. Bhat
2012-06-01 9:13 ` [PATCH 15/27] ia64, smpboot: Use generic SMP booting infrastructure Srivatsa S. Bhat
2012-06-01 9:13 ` [PATCH 16/27] mn10300: Fix horrible logic in smp_prepare_cpus() Srivatsa S. Bhat
2012-06-01 9:14 ` [PATCH 17/27] mn10300, smpboot: Use generic SMP booting infrastructure Srivatsa S. Bhat
2012-06-03 8:33 ` Yong Zhang
2012-06-03 11:50 ` Srivatsa S. Bhat
2012-06-01 9:14 ` [PATCH 18/27] powerpc, " Srivatsa S. Bhat
2012-06-02 6:14 ` Paul Mackerras
2012-06-01 9:14 ` [PATCH 19/27] blackfin, " Srivatsa S. Bhat
2012-06-01 9:14 ` [PATCH 20/27] sparc64, " Srivatsa S. Bhat
2012-06-01 17:55 ` David Miller
2012-06-01 22:44 ` [UPDATED PATCH " Srivatsa S. Bhat
2012-06-01 22:52 ` David Miller
2012-06-01 9:15 ` [PATCH 21/27] sparc32, " Srivatsa S. Bhat
2012-06-01 17:56 ` David Miller
2012-06-01 18:54 ` Sam Ravnborg
2012-06-01 22:47 ` [UPDATED PATCH " Srivatsa S. Bhat
2012-06-01 22:53 ` David Miller
2012-06-01 23:17 ` Srivatsa S. Bhat
2012-06-02 6:52 ` Sam Ravnborg
2012-06-02 7:44 ` Sam Ravnborg
2012-06-02 8:01 ` Srivatsa S. Bhat
2012-06-02 8:14 ` Srivatsa S. Bhat
2012-06-02 15:13 ` Sam Ravnborg
2012-06-02 15:58 ` Srivatsa S. Bhat [this message]
2012-06-02 16:23 ` Sam Ravnborg
2012-06-02 16:34 ` Srivatsa S. Bhat
2012-06-03 21:17 ` [PATCH] sparc32: refactor smp boot Sam Ravnborg
2012-06-04 1:04 ` David Miller
2012-06-04 6:48 ` Srivatsa S. Bhat
2012-06-01 9:15 ` [PATCH 22/27] um, smpboot: Use generic SMP booting infrastructure Srivatsa S. Bhat
2012-06-01 9:15 ` [PATCH 23/27] cris, " Srivatsa S. Bhat
2012-06-03 8:41 ` Yong Zhang
2012-06-03 11:52 ` Srivatsa S. Bhat
2012-06-01 9:15 ` [PATCH 24/27] parisc, " Srivatsa S. Bhat
2012-06-01 9:16 ` [PATCH 25/27] s390, " Srivatsa S. Bhat
2012-06-01 10:45 ` Heiko Carstens
2012-06-01 9:16 ` [PATCH 26/27] arm, " Srivatsa S. Bhat
2012-06-01 11:04 ` Russell King - ARM Linux
2012-06-01 9:16 ` [PATCH 27/27] alpha, " Srivatsa S. Bhat
[not found] ` <20120601091038.31979.67878.stgit@srivatsabhat.in.ibm.com>
2012-06-01 12:19 ` [PATCH 03/27] smpboot: Define and use cpu_state per-cpu variable in generic code Srivatsa S. Bhat
2012-06-01 12:25 ` Russell King - ARM Linux
2012-06-01 12:55 ` Srivatsa S. Bhat
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=4FCA382B.6050601@linux.vnet.ibm.com \
--to=srivatsa.bhat@linux.vnet.ibm.com \
--cc=akpm@linux-foundation.org \
--cc=davem@davemloft.net \
--cc=konrad@gaisler.com \
--cc=linux-arch@vger.kernel.org \
--cc=linux-kernel@vger.kernel.org \
--cc=mingo@kernel.org \
--cc=nikunj@linux.vnet.ibm.com \
--cc=paulmck@linux.vnet.ibm.com \
--cc=peterz@infradead.org \
--cc=rjw@sisk.pl \
--cc=rusty@rustcorp.com.au \
--cc=sam@ravnborg.org \
--cc=sparclinux@vger.kernel.org \
--cc=tglx@linutronix.de \
--cc=tkhai@yandex.ru \
--cc=vapier@gentoo.org \
--cc=vatsa@linux.vnet.ibm.com \
--cc=yong.zhang0@gmail.com \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).