Pass the CPU index as a parameter to startup.

This addition is in support of future multicore support in
coreboot. It also will allow us to remove some asssembly code.

The CPU "index" -- i.e., its order in the sequence in which
cores are brought up, NOT its APIC id -- is passed into the
secondary start. We modify the function to specify regparm(0).
We also take this opportunity to do some cleanup:
indexes become unsigned ints, not unsigned longs, for example.

Build and boot on a multicore system, with pcserial enabled.

Capture the output. Observe that the messages
Initializing CPU #0
Initializing CPU #1
Initializing CPU #2
Initializing CPU #3
appear exactly as they do prior to this change.

Change-Id: I5854d8d957c414f75fdd63fb017d2249330f955d
Signed-off-by: Ronald G. Minnich <rminnich@chromium.org>
Reviewed-on: http://review.coreboot.org/1820
Reviewed-by: Stefan Reinauer <stefan.reinauer@coreboot.org>
Tested-by: build bot (Jenkins)
This commit is contained in:
Ronald G. Minnich 2012-06-05 14:41:27 -07:00 committed by Stefan Reinauer
parent 455f4b4328
commit 8b93059ecc
5 changed files with 18 additions and 14 deletions

View File

@ -160,7 +160,7 @@ struct cpu_driver *find_cpu_driver(struct device *cpu);
struct cpu_info { struct cpu_info {
device_t cpu; device_t cpu;
unsigned long index; unsigned int index;
}; };
static inline struct cpu_info *cpu_info(void) static inline struct cpu_info *cpu_info(void)

View File

@ -234,7 +234,7 @@ static void set_cpu_ops(struct device *cpu)
cpu->ops = driver ? driver->ops : NULL; cpu->ops = driver ? driver->ops : NULL;
} }
void cpu_initialize(void) void cpu_initialize(unsigned int index)
{ {
/* Because we busy wait at the printk spinlock. /* Because we busy wait at the printk spinlock.
* It is important to keep the number of printed messages * It is important to keep the number of printed messages
@ -247,7 +247,7 @@ void cpu_initialize(void)
info = cpu_info(); info = cpu_info();
printk(BIOS_INFO, "Initializing CPU #%ld\n", info->index); printk(BIOS_INFO, "Initializing CPU #%d\n", index);
cpu = info->cpu; cpu = info->cpu;
if (!cpu) { if (!cpu) {
@ -284,7 +284,7 @@ void cpu_initialize(void)
cpu->ops->init(cpu); cpu->ops->init(cpu);
} }
printk(BIOS_INFO, "CPU #%ld initialized\n", info->index); printk(BIOS_INFO, "CPU #%d initialized\n", index);
return; return;
} }

View File

@ -209,13 +209,14 @@ static atomic_t active_cpus = ATOMIC_INIT(1);
* for select the stack from assembly language. * for select the stack from assembly language.
* *
* In addition communicating by variables to the cpu I * In addition communicating by variables to the cpu I
* am starting allows me to veryify it has started before * am starting allows me to verify it has started before
* start_cpu returns. * start_cpu returns.
*/ */
static spinlock_t start_cpu_lock = SPIN_LOCK_UNLOCKED; static spinlock_t start_cpu_lock = SPIN_LOCK_UNLOCKED;
static unsigned last_cpu_index = 0; static unsigned int last_cpu_index = 0;
volatile unsigned long secondary_stack; volatile unsigned long secondary_stack;
volatile unsigned int secondary_cpu_index;
void *stacks[CONFIG_MAX_CPUS]; void *stacks[CONFIG_MAX_CPUS];
int start_cpu(device_t cpu) int start_cpu(device_t cpu)
@ -226,7 +227,7 @@ int start_cpu(device_t cpu)
unsigned long stack_base; unsigned long stack_base;
unsigned long *stack; unsigned long *stack;
unsigned long apicid; unsigned long apicid;
unsigned long index; unsigned int index;
unsigned long count; unsigned long count;
int i; int i;
int result; int result;
@ -243,7 +244,7 @@ int start_cpu(device_t cpu)
stack_end = ((unsigned long)_estack) - (CONFIG_STACK_SIZE*index) - sizeof(struct cpu_info); stack_end = ((unsigned long)_estack) - (CONFIG_STACK_SIZE*index) - sizeof(struct cpu_info);
stack_base = ((unsigned long)_estack) - (CONFIG_STACK_SIZE*(index+1)); stack_base = ((unsigned long)_estack) - (CONFIG_STACK_SIZE*(index+1));
printk(BIOS_SPEW, "CPU%ld: stack_base %p, stack_end %p\n", index, printk(BIOS_SPEW, "CPU%d: stack_base %p, stack_end %p\n", index,
(void *)stack_base, (void *)stack_end); (void *)stack_base, (void *)stack_end);
/* poison the stack */ /* poison the stack */
for(stack = (void *)stack_base, i = 0; i < CONFIG_STACK_SIZE; i++) for(stack = (void *)stack_base, i = 0; i < CONFIG_STACK_SIZE; i++)
@ -254,8 +255,9 @@ int start_cpu(device_t cpu)
info->index = index; info->index = index;
info->cpu = cpu; info->cpu = cpu;
/* Advertise the new stack to start_cpu */ /* Advertise the new stack and index to start_cpu */
secondary_stack = stack_end; secondary_stack = stack_end;
secondary_cpu_index = index;
/* Until the cpu starts up report the cpu is not enabled */ /* Until the cpu starts up report the cpu is not enabled */
cpu->enabled = 0; cpu->enabled = 0;
@ -384,7 +386,7 @@ static __inline__ __attribute__((always_inline)) void writecr4(unsigned long Dat
#endif #endif
/* C entry point of secondary cpus */ /* C entry point of secondary cpus */
void __attribute__((regparm(0))) secondary_cpu_init(void) void __attribute__((regparm(0))) secondary_cpu_init(unsigned int index)
{ {
atomic_inc(&active_cpus); atomic_inc(&active_cpus);
#if CONFIG_SERIAL_CPU_INIT #if CONFIG_SERIAL_CPU_INIT
@ -401,7 +403,7 @@ void __attribute__((regparm(0))) secondary_cpu_init(void)
cr4_val |= (1 << 9 | 1 << 10); cr4_val |= (1 << 9 | 1 << 10);
writecr4(cr4_val); writecr4(cr4_val);
#endif #endif
cpu_initialize(); cpu_initialize(index);
#if CONFIG_SERIAL_CPU_INIT #if CONFIG_SERIAL_CPU_INIT
spin_unlock(&start_cpu_lock); spin_unlock(&start_cpu_lock);
#endif #endif
@ -537,7 +539,7 @@ void initialize_cpus(struct bus *cpu_bus)
#endif #endif
/* Initialize the bootstrap processor */ /* Initialize the bootstrap processor */
cpu_initialize(); cpu_initialize(0);
#if CONFIG_SMP && CONFIG_MAX_CPUS > 1 #if CONFIG_SMP && CONFIG_MAX_CPUS > 1
#if CONFIG_SERIAL_CPU_INIT #if CONFIG_SERIAL_CPU_INIT

View File

@ -53,6 +53,8 @@ __ap_protected_start:
/* Set the stack pointer, and flag that we are done */ /* Set the stack pointer, and flag that we are done */
xorl %eax, %eax xorl %eax, %eax
movl secondary_stack, %esp movl secondary_stack, %esp
movl secondary_cpu_index, %edi
pushl %edi
movl %eax, secondary_stack movl %eax, secondary_stack
call secondary_cpu_init call secondary_cpu_init

View File

@ -4,10 +4,10 @@
#include <arch/cpu.h> #include <arch/cpu.h>
#if !defined(__ROMCC__) #if !defined(__ROMCC__)
void cpu_initialize(void); void cpu_initialize(unsigned int cpu_index);
struct bus; struct bus;
void initialize_cpus(struct bus *cpu_bus); void initialize_cpus(struct bus *cpu_bus);
void __attribute__((regparm(0))) secondary_cpu_init(void); void __attribute__((regparm(0))) secondary_cpu_init(unsigned int cpu_index);
#if CONFIG_HAVE_SMI_HANDLER #if CONFIG_HAVE_SMI_HANDLER
void smm_init(void); void smm_init(void);