percpu_init_areas();
set_processor_id(0); /* needed early, for smp_processor_id() */
- __set_current((struct vcpu *)0xfffff000); /* debug sanity */
+ set_current((struct vcpu *)0xfffff000); /* debug sanity */
idle_vcpu[0] = current;
smp_prepare_cpus(cpus);
/* Number of non-boot CPUs ready to enter C */
unsigned long __initdata ready_cpus = 0;
+/* ID of the PCPU we're running on */
+DEFINE_PER_CPU(unsigned int, cpu_id);
+
void __init
smp_prepare_cpus (unsigned int max_cpus)
{
/* Setup Hyp vector base */
WRITE_CP32((uint32_t) hyp_traps_vector, HVBAR);
- dprintk(XENLOG_DEBUG, "CPU %li awake.\n", cpuid);
-
mmu_init_secondary_cpu();
gic_init_secondary_cpu();
local_irq_enable();
- dprintk(XENLOG_DEBUG, "CPU %li booted.\n", cpuid);
+ dprintk(XENLOG_DEBUG, "CPU %u booted.\n", smp_processor_id());
startup_cpu_idle_loop();
}
/* CP15 CR13: */
#define FCSEIDR p15,0,c13,c0,0 /* FCSE Process ID Register */
#define CONTEXTIDR p15,0,c13,c0,1 /* Context ID Register */
+#define HTPIDR p15,4,c13,c0,2 /* Hyp. Software Thread ID Register */
/* CP15 CR14: */
#define CNTPCT p15,0,c14 /* Time counter value */
struct vcpu;
-/*
- * Which VCPU is "current" on this PCPU.
- */
+/* Which VCPU is "current" on this PCPU. */
DECLARE_PER_CPU(struct vcpu *, curr_vcpu);
+#define current (this_cpu(curr_vcpu))
+#define set_current(vcpu) do { current = (vcpu); } while (0)
+
+/* Per-VCPU state that lives at the top of the stack */
struct cpu_info {
struct cpu_user_regs guest_cpu_user_regs;
unsigned long elr;
- /* The following are valid iff this VCPU is current */
- unsigned int processor_id;
- unsigned long per_cpu_offset;
unsigned int pad;
};
return (struct cpu_info *)((sp & ~(STACK_SIZE - 1)) + STACK_SIZE - sizeof(struct cpu_info));
}
-#define get_processor_id() (get_cpu_info()->processor_id)
-#define set_processor_id(id) do { \
- struct cpu_info *ci__ = get_cpu_info(); \
- ci__->per_cpu_offset = __per_cpu_offset[ci__->processor_id = (id)]; \
-} while (0)
-
-#define get_current() (this_cpu(curr_vcpu))
-#define __set_current(vcpu) (this_cpu(curr_vcpu) = (vcpu))
-#define set_current(vcpu) do { \
- int cpu = get_processor_id(); \
- vcpu->arch.cpu_info->processor_id = cpu; \
- vcpu->arch.cpu_info->per_cpu_offset = __per_cpu_offset[cpu]; \
- __set_current(vcpu); \
-} while (0)
-#define current (get_current())
-
#define guest_cpu_user_regs() (&get_cpu_info()->guest_cpu_user_regs)
#define switch_stack_and_jump(stack, fn) \
extern char __per_cpu_start[], __per_cpu_data_end[];
extern unsigned long __per_cpu_offset[NR_CPUS];
void percpu_init_areas(void);
-#endif
/* Separate out the type, so (int[3], foo) works. */
#define __DEFINE_PER_CPU(type, name, suffix) \
#define per_cpu(var, cpu) \
(*RELOC_HIDE(&per_cpu__##var, __per_cpu_offset[cpu]))
#define __get_cpu_var(var) \
- (*RELOC_HIDE(&per_cpu__##var, get_cpu_info()->per_cpu_offset))
+ (*RELOC_HIDE(&per_cpu__##var, READ_CP32(HTPIDR)))
#define DECLARE_PER_CPU(type, name) extern __typeof__(type) per_cpu__##name
+DECLARE_PER_CPU(unsigned int, cpu_id);
+#define get_processor_id() (this_cpu(cpu_id))
+#define set_processor_id(id) do { \
+ WRITE_CP32(__per_cpu_offset[id], HTPIDR); \
+ this_cpu(cpu_id) = (id); \
+} while(0)
+#endif
+
#endif /* __ARM_PERCPU_H__ */
/*
* Local variables: