/*
 *  arch/s390/kernel/smp.c
 *
 *    Copyright (C) IBM Corp. 1999,2006
 *    Author(s): Denis Joseph Barrow (djbarrow@de.ibm.com,barrow_dj@yahoo.com),
 *               Martin Schwidefsky (schwidefsky@de.ibm.com)
 *               Heiko Carstens (heiko.carstens@de.ibm.com)
 *
 *  based on other smp stuff by 
 *    (c) 1995 Alan Cox, CymruNET Ltd  <alan@cymru.net>
 *    (c) 1998 Ingo Molnar
 *
 * We work with logical cpu numbering everywhere we can. The only
 * functions using the real cpu address (got from STAP) are the sigp
 * functions. For all other functions we use the identity mapping.
 * That means that cpu_number_map[i] == i for every cpu. cpu_number_map is
 * used e.g. to find the idle task belonging to a logical cpu. Every array
 * in the kernel is sorted by the logical cpu number and not by the physical
 * one which is causing all the confusion with __cpu_logical_map and
 * cpu_number_map in other architectures.
 */

#include <linux/module.h>
#include <linux/init.h>

#include <linux/mm.h>
#include <linux/spinlock.h>
#include <linux/kernel_stat.h>
#include <linux/smp_lock.h>

#include <linux/delay.h>
#include <linux/cache.h>
#include <linux/interrupt.h>
#include <linux/cpu.h>

#include <asm/sigp.h>
#include <asm/pgalloc.h>
#include <asm/irq.h>
#include <asm/s390_ext.h>
#include <asm/cpcmd.h>
#include <asm/tlbflush.h>

extern volatile int __cpu_logical_map[];

/*
 * An array with a pointer the lowcore of every CPU.
 */

struct _lowcore *lowcore_ptr[NR_CPUS];

cpumask_t cpu_online_map = CPU_MASK_NONE;
cpumask_t cpu_possible_map = CPU_MASK_NONE;

static struct task_struct *current_set[NR_CPUS];

/*
 * Reboot, halt and power_off routines for SMP.
 */
extern char vmhalt_cmd[];
extern char vmpoff_cmd[];

static void smp_ext_bitcall(int, ec_bit_sig);
static void smp_ext_bitcall_others(ec_bit_sig);

/*
5B * Structure and data for smp_call_function(). This is designed to minimise
 * static memory requirements. It also looks cleaner.
 */
static DEFINE_SPINLOCK(call_lock);

struct call_data_struct {
	void (*func) (void *info);
	void *info;
	atomic_t started;
	atomic_t finished;
	int wait;
};

static struct call_data_struct * call_data;

/*
 * 'Call function' interrupt callback
 */
static void do_call_function(void)
{
	void (*func) (void *info) = call_data->func;
	void *info = call_data->info;
	int wait = call_data->wait;

	atomic_inc(&call_data->started);
	(*func)(info);
	if (wait)
		atomic_inc(&call_data->finished);
}

/*
 * this function sends a 'generic call function' IPI to all other CPUs
 * in the system.
 */

int smp_call_function (void (*func) (void *info), void *info, int nonatomic,
			int wait)
/*
 * [SUMMARY] Run a function on all other CPUs.
 * <func> The function to run. This must be fast and non-blocking.
 * <info> An arbitrary pointer to pass to the function.
 * <nonatomic> currently unused.
 * <wait> If true, wait (atomically) until function has completed on other CPUs.
 * [RETURNS] 0 on success, else a negative status code. Does not return until
 * remote CPUs are nearly ready to execute <<func>> or are or have executed.
 *
 * You must not call this function with disabled interrupts or from a
 * hardware interrupt handler or from a bottom half handler.
 */
{
	struct call_data_struct data;
	int cpus = num_online_cpus()-1;

	if (cpus <= 0)
		return 0;

	/* Can deadlock when called with interrupts disabled */
	WARN_ON(irqs_disabled());

	data.func = func;
	data.info = info;
	atomic_set(&data.started, 0);
	data.wait = wait;
	if (wait)
		atomic_set(&data.finished, 0);

	spin_lock(&call_lock);
	call_data = &data;
	/* Send a message to all other CPUs and wait for them to respond */
        smp_ext_bitcall_others(ec_call_function);

	/* Wait for response */
	while (atomic_read(&data.started) != cpus)
		cpu_relax();

	if (wait)
		while (atomic_read(&data.finished) != cpus)
			cpu_relax();
	spin_unlock(&call_lock);

	return 0;
}

/*
 * Call a function on one CPU
 * cpu : the CPU the function should be executed on
 *
 * You must not call this function with disabled interrupts or from a
 * hardware interrupt handler. You may call it from a bottom half.
 *
 * It is guaranteed that the called function runs on the specified CPU,
 * preemption is disabled.
 */
int smp_call_function_on(void (*func) (void *info), void *info,
			 int nonatomic, int wait, int cpu)
{
	struct call_data_struct data;
	int curr_cpu;

	if (!cpu_online(cpu))
		return -EINVAL;

	/* disable preemption for local function call */
	curr_cpu = get_cpu();

	if (curr_cpu == cpu) {
		/* direct call to function */
		func(info);
		put_cpu();
		return 0;
	}

	data.func = func;
	data.info = info;
	atomic_set(&data.started, 0);
	data.wait = wait;
	if (wait)
		atomic_set(&data.finished, 0);

	spin_lock_bh(&call_lock);
	call_data = &data;
	smp_ext_bitcall(cpu, ec_call_function);

	/* Wait for response */
	while (atomic_read(&data.started) != 1)
		cpu_relax();

	if (wait)
		while (atomic_read(&data.finished) != 1)
			cpu_relax();

	spin_unlock_bh(&call_lock);
	put_cpu();
	return 0;
}
EXPORT_SYMBOL(smp_call_function_on);

static inline void do_send_stop(void)
{
        int cpu, rc;

        /* stop all processors */
	for_each_online_cpu(cpu) {
		if (cpu == smp_processor_id())
			continue;
		do {
			rc = signal_processor(cpu, sigp_stop);
		} while (rc == sigp_busy);
	}
}

static inline void do_store_status(void)
{
        int cpu, rc;

        /* store status of all processors in their lowcores (real 0) */
	for_each_online_cpu(cpu) {
		if (cpu == smp_processor_id())
			continue;
		do {
			rc = signal_processor_p(
				(__u32)(unsigned long) lowcore_ptr[cpu], cpu,
				sigp_store_status_at_address);
		} while(rc == sigp_busy);
        }
}

/*
 * this function sends a 'stop' sigp to all other CPUs in the system.
 * it goes straight through.
 */
void smp_send_stop(void)
{
        /* write magic number to zero page (absolute 0) */
	lowcore_ptr[smp_processor_id()]->panic_magic = __PANIC_MAGIC;

	/* stop other processors. */
	do_send_stop();

	/* store status of other processors. */
	do_store_status();
}

/*
 * Reboot, halt and power_off routines for SMP.
 */

static void do_machine_restart(void * __unused)
{
	int cpu;
	static atomic_t cpuid = ATOMIC_INIT(-1);

	if (atomic_cmpxchg(&cpuid, -1, smp_processor_id()) != -1)
		signal_processor(smp_processor_id(), sigp_stop);

	/* Wait for all other cpus to enter stopped state */
	for_each_online_cpu(cpu) {
		if (cpu == smp_processor_id())
			continue;
		while(!smp_cpu_not_running(cpu))
			cpu_relax();
	}

	/* Store status of other cpus. */
	do_store_status();

	/*
	 * Finally call reipl. Because we waited for all other
	 * cpus to enter this function we know that they do
	 * not hold any s390irq-locks (the cpus have been
	 * interrupted by an external interrupt and s390irq
	 * locks are always held disabled).
	 */
	do_reipl();
}

void machine_restart_smp(char * __unused) 
{
        on_each_cpu(do_machine_restart, NULL, 0, 0);
}

static void do_wait_for_stop(void)
{
	unsigned long cr[16];

	__ctl_store(cr, 0, 15);
	cr[0] &= ~0xffff;
	cr[6] = 0;
	__ctl_load(cr, 0, 15);
	for (;;)
		enabled_wait();
}

static void do_machine_halt(void * __unused)
{
	static atomic_t cpuid = ATOMIC_INIT(-1);

	if (atomic_cmpxchg(&cpuid, -1, smp_processor_id()) == -1) {
		smp_send_stop();
		if (MACHINE_IS_VM && strlen(vmhalt_cmd) > 0)
			cpcmd(vmhalt_cmd, NULL, 0, NULL);
		signal_processor(smp_processor_id(),
				 sigp_stop_and_store_status);
	}
	do_wait_for_stop();
}

void machine_halt_smp(void)
{
        on_each_cpu(do_machine_halt, NULL, 0, 0);
}

static void do_machine_power_off(void * __unused)
{
	static atomic_t cpuid = ATOMIC_INIT(-1);

	if (atomic_cmpxchg(&cpuid, -1, smp_processor_id()) == -1) {
		smp_send_stop();
		if (MACHINE_IS_VM && strlen(vmpoff_cmd) > 0)
			cpcmd(vmpoff_cmd, NULL, 0, NULL);
		signal_processor(smp_processor_id(),
				 sigp_stop_and_store_status);
	}
	do_wait_for_stop();
}

void machine_power_off_smp(void)
{
        on_each_cpu(do_machine_power_off, NULL, 0, 0);
}

/*
 * This is the main routine where commands issued by other
 * cpus are handled.
 */

void do_ext_call_interrupt(struct pt_regs *regs, __u16 code)
{
        unsigned long bits;

        /*
         * handle bit signal external calls
         *
         * For the ec_schedule signal we have to do nothing. All the work
         * is done automatically when we return from the interrupt.
         */
	bits = xchg(&S390_lowcore.ext_call_fast, 0);

	if (test_bit(ec_call_function, &bits)) 
		do_call_function();
}

/*
 * Send an external call sigp to another cpu and return without waiting
 * for its completion.
 */
static void smp_ext_bitcall(int cpu, ec_bit_sig sig)
{
        /*
         * Set signaling bit in lowcore of target cpu and kick it
         */
	set_bit(sig, (unsigned long *) &lowcore_ptr[cpu]->ext_call_fast);
	while(signal_processor(cpu, sigp_emergency_signal) == sigp_busy)
		udelay(10);
}

/*
 * Send an external call sigp to every other cpu in the system and
 * return without waiting for its completion.
 */
static void smp_ext_bitcall_others(ec_bit_sig sig)
{
        int cpu;

	for_each_online_cpu(cpu) {
		if (cpu == smp_processor_id())
                        continue;
                /*
                 * Set signaling bit in lowcore of target cpu and kick it
                 */
		set_bit(sig, (unsigned long *) &lowcore_ptr[cpu]->ext_call_fast);
		while (signal_processor(cpu, sigp_emergency_signal) == sigp_busy)
			udelay(10);
        }
}

#ifndef CONFIG_64BIT
/*
 * this function sends a 'purge tlb' signal to another CPU.
 */
void smp_ptlb_callback(void *info)
{
	local_flush_tlb();
}

void smp_ptlb_all(void)
{
        on_each_cpu(smp_ptlb_callback, NULL, 0, 1);
}
EXPORT_SYMBOL(smp_ptlb_all);
#endif /* ! CONFIG_64BIT */

/*
 * this function sends a 'reschedule' IPI to another CPU.
 * it goes straight through and wastes no time serializing
 * anything. Worst case is that we lose a reschedule ...
 */
void smp_send_reschedule(int cpu)
{
        smp_ext_bitcall(cpu, ec_schedule);
}

/*
 * parameter area for the set/clear control bit callbacks
 */
struct ec_creg_mask_parms {
	unsigned long orvals[16];
	unsigned long andvals[16];
};

/*
 * callback for setting/clearing control bits
 */
void smp_ctl_bit_callback(void *info) {
	struct ec_creg_mask_parms *pp = info;
	unsigned long cregs[16];
	int i;
	
	__ctl_store(cregs, 0, 15);
	for (i = 0; i <= 15; i++)
		cregs[i] = (cregs[i] & pp->andvals[i]) | pp->orvals[i];
	__ctl_load(cregs, 0, 15);
}

/*
 * Set a bit in a control register of all cpus
 */
void smp_ctl_set_bit(int cr, int bit)
{
	struct ec_creg_mask_parms parms;

	memset(&parms.orvals, 0, sizeof(parms.orvals));
	memset(&parms.andvals, 0xff, sizeof(parms.andvals));
	parms.orvals[cr] = 1 << bit;
	on_each_cpu(smp_ctl_bit_callback, &parms, 0, 1);
}

/*
 * Clear a bit in a control register of all cpus
 */
void smp_ctl_clear_bit(int cr, int bit)
{
	struct ec_creg_mask_parms parms;

	memset(&parms.orvals, 0, sizeof(parms.orvals));
	memset(&parms.andvals, 0xff, sizeof(parms.andvals));
	parms.andvals[cr] = ~(1L << bit);
	on_each_cpu(smp_ctl_bit_callback, &parms, 0, 1);
}

/*
 * Lets check how many CPUs we have.
 */

static unsigned int
__init smp_count_cpus(void)
{
	unsigned int cpu, num_cpus;
	__u16 boot_cpu_addr;

	/*
	 * cpu 0 is the boot cpu. See smp_prepare_boot_cpu.
	 */

	boot_cpu_addr = S390_lowcore.cpu_data.cpu_addr;
	current_thread_info()->cpu = 0;
	num_cpus = 1;
	for (cpu = 0; cpu <= 65535; cpu++) {
		if ((__u16) cpu == boot_cpu_addr)
			continue;
		__cpu_logical_map[1] = (__u16) cpu;
		if (signal_processor(1, sigp_sense) ==
		    sigp_not_operational)
			continue;
		num_cpus++;
	}

	printk("Detected %d CPU's\n",(int) num_cpus);
	printk("Boot cpu address %2X\n", boot_cpu_addr);

	return num_cpus;
}

/*
 *      Activate a secondary processor.
 */
extern void init_cpu_timer(void);
extern void init_cpu_vtimer(void);
extern int pfault_init(void);
extern void pfault_fini(void);

int __devinit start_secondary(void *cpuvoid)
{
        /* Setup the cpu */
        cpu_init();
	preempt_disable();
        /* init per CPU timer */
        init_cpu_timer();
#ifdef CONFIG_VIRT_TIMER
        init_cpu_vtimer();
#endif
#ifdef CONFIG_PFAULT
	/* Enable pfault pseudo page faults on this cpu. */
	if (MACHINE_IS_VM)
		pfault_init();
#endif
	/* Mark this cpu as online */
	cpu_set(smp_processor_id(), cpu_online_map);
	/* Switch on interrupts */
	local_irq_enable();
        /* Print info about this processor */
        print_cpu_info(&S390_lowcore.cpu_data);
        /* cpu_idle will call schedule for us */
        cpu_idle();
        return 0;
}

static void __init smp_create_idle(unsigned int cpu)
{
	struct task_struct *p;

	/*
	 *  don't care about the psw and regs settings since we'll never
	 *  reschedule the forked task.
	 */
	p = fork_idle(cpu);
	if (IS_ERR(p))
		panic("failed fork for CPU %u: %li", cpu, PTR_ERR(p));
	current_set[cpu] = p;
}

/* Reserving and releasing of CPUs */

static DEFINE_SPINLOCK(smp_reserve_lock);
static int smp_cpu_reserved[NR_CPUS];

int
smp_get_cpu(cpumask_t cpu_mask)
{
	unsigned long flags;
	int cpu;

	spin_lock_irqsave(&smp_reserve_lock, flags);
	/* Try to find an already reserved cpu. */
	for_each_cpu_mask(cpu, cpu_mask) {
		if (smp_cpu_reserved[cpu] != 0) {
			smp_cpu_reserved[cpu]++;
			/* Found one. */
			goto out;
		}
	}
	/* Reserve a new cpu from cpu_mask. */
	for_each_cpu_mask(cpu, cpu_mask) {
		if (cpu_online(cpu)) {
			smp_cpu_reserved[cpu]++;
			goto out;
		}
	}
	cpu = -ENODEV;
out:
	spin_unlock_irqrestore(&smp_reserve_lock, flags);
	return cpu;
}

void
smp_put_cpu(int cpu)
{
	unsigned long flags;

	spin_lock_irqsave(&smp_reserve_lock, flags);
	smp_cpu_reserved[cpu]--;
	spin_unlock_irqrestore(&smp_reserve_lock, flags);
}

static inline int
cpu_stopped(int cpu)
{
	__u32 status;

	/* Check for stopped state */
	if (signal_processor_ps(&status, 0, cpu, sigp_sense) == sigp_status_stored) {
		if (status & 0x40)
			return 1;
	}
	return 0;
}

/* Upping and downing of CPUs */

int
__cpu_up(unsigned int cpu)
{
	struct task_struct *idle;
        struct _lowcore    *cpu_lowcore;
	struct stack_frame *sf;
        sigp_ccode          ccode;
	int                 curr_cpu;

	for (curr_cpu = 0; curr_cpu <= 65535; curr_cpu++) {
		__cpu_logical_map[cpu] = (__u16) curr_cpu;
		if (cpu_stopped(cpu))
			break;
	}

	if (!cpu_stopped(cpu))
		return -ENODEV;

	ccode = signal_processor_p((__u32)(unsigned long)(lowcore_ptr[cpu]),
				   cpu, sigp_set_prefix);
	if (ccode){
		printk("sigp_set_prefix failed for cpu %d "
		       "with condition code %d\n",
		       (int) cpu, (int) ccode);
		return -EIO;
	}

	idle = current_set[cpu];
        cpu_lowcore = lowcore_ptr[cpu];
	cpu_lowcore->kernel_stack = (unsigned long)
		task_stack_page(idle) + (THREAD_SIZE);
	sf = (struct stack_frame *) (cpu_lowcore->kernel_stack
				     - sizeof(struct pt_regs)
				     - sizeof(struct stack_frame));
	memset(sf, 0, sizeof(struct stack_frame));
	sf->gprs[9] = (unsigned long) sf;
	cpu_lowcore->save_area[15] = (unsigned long) sf;
	__ctl_store(cpu_lowcore->cregs_save_area[0], 0, 15);
	asm volatile(
		"	stam	0,15,0(%0)"
		: : "a" (&cpu_lowcore->access_regs_save_area) : "memory");
	cpu_lowcore->percpu_offset = __per_cpu_offset[cpu];
        cpu_lowcore->current_task = (unsigned long) idle;
        cpu_lowcore->cpu_data.cpu_nr = cpu;
	eieio();

	while (signal_processor(cpu,sigp_restart) == sigp_busy)
		udelay(10);

	while (!cpu_online(cpu))
		cpu_relax();
	return 0;
}

static unsigned int __initdata additional_cpus;
static unsigned int __initdata possible_cpus;

void __init smp_setup_cpu_possible_map(void)
{
	unsigned int phy_cpus, pos_cpus, cpu;

	phy_cpus = smp_count_cpus();
	pos_cpus = min(phy_cpus + additional_cpus, (unsigned int) NR_CPUS);

	if (possible_cpus)
		pos_cpus = min(possible_cpus, (unsigned int) NR_CPUS);

	for (cpu = 0; cpu < pos_cpus; cpu++)
		cpu_set(cpu, cpu_possible_map);

	phy_cpus = min(phy_cpus, pos_cpus);

	for (cpu = 0; cpu < phy_cpus; cpu++)
		cpu_set(cpu, cpu_present_map);
}

#ifdef CONFIG_HOTPLUG_CPU

static int __init setup_additional_cpus(char *s)
{
	additional_cpus = simple_strtoul(s, NULL, 0);
	return 0;
}
early_param("additional_cpus", setup_additional_cpus);

static int __init setup_possible_cpus(char *s)
{
	possible_cpus = simple_strtoul(s, NULL, 0);
	return 0;
}
early_param("possible_cpus", setup_possible_cpus);

int
__cpu_disable(void)
{
	unsigned long flags;
	struct ec_creg_mask_parms cr_parms;
	int cpu = smp_processor_id();

	spin_lock_irqsave(&smp_reserve_lock, flags);
	if (smp_cpu_reserved[cpu] != 0) {
		spin_unlock_irqrestore(&smp_reserve_lock, flags);
		return -EBUSY;
	}
	cpu_clear(cpu, cpu_online_map);

#ifdef CONFIG_PFAULT
	/* Disable pfault pseudo page faults on this cpu. */
	if (MACHINE_IS_VM)
		pfault_fini();
#endif

	memset(&cr_parms.orvals, 0, sizeof(cr_parms.orvals));
	memset(&cr_parms.andvals, 0xff, sizeof(cr_parms.andvals));

	/* disable all external interrupts */
	cr_parms.orvals[0] = 0;
	cr_parms.andvals[0] = ~(1<<15 | 1<<14 | 1<<13 | 1<<12 |
				1<<11 | 1<<10 | 1<< 6 | 1<< 4);
	/* disable all I/O interrupts */
	cr_parms.orvals[6] = 0;
	cr_parms.andvals[6] = ~(1<<31 | 1<<30 | 1<<29 | 1<<28 |
				1<<27 | 1<<26 | 1<<25 | 1<<24);
	/* disable most machine checks */
	cr_parms.orvals[14] = 0;
	cr_parms.andvals[14] = ~(1<<28 | 1<<27 | 1<<26 | 1<<25 | 1<<24);

	smp_ctl_bit_callback(&cr_parms);

	spin_unlock_irqrestore(&smp_reserve_lock, flags);
	return 0;
}

void
__cpu_die(unsigned int cpu)
{
	/* Wait until target cpu is down */
	while (!smp_cpu_not_running(cpu))
		cpu_relax();
	printk("Processor %d spun down\n", cpu);
}

void
cpu_die(void)
{
	idle_task_exit();
	signal_processor(smp_processor_id(), sigp_stop);
	BUG();
	for(;;);
}

#endif /* CONFIG_HOTPLUG_CPU */

/*
 *	Cycle through the processors and setup structures.
 */

void __init smp_prepare_cpus(unsigned int max_cpus)
{
	unsigned long stack;
	unsigned int cpu;
        int i;

        /* request the 0x1201 emergency signal external interrupt */
        if (register_external_interrupt(0x1201, do_ext_call_interrupt) != 0)
                panic("Couldn't request external interrupt 0x1201");
        memset(lowcore_ptr,0,sizeof(lowcore_ptr));  
        /*
         *  Initialize prefix pages and stacks for all possible cpus
         */
	print_cpu_info(&S390_lowcore.cpu_data);

        for_each_possible_cpu(i) {
		lowcore_ptr[i] = (struct _lowcore *)
			__get_free_pages(GFP_KERNEL|GFP_DMA, 
					sizeof(void*) == 8 ? 1 : 0);
		stack = __get_free_pages(GFP_KERNEL,ASYNC_ORDER);
		if (lowcore_ptr[i] == NULL || stack == 0ULL)
			panic("smp_boot_cpus failed to allocate memory\n");

		*(lowcore_ptr[i]) = S390_lowcore;
		lowcore_ptr[i]->async_stack = stack + (ASYNC_SIZE);
		stack = __get_free_pages(GFP_KERNEL,0);
		if (stack == 0ULL)
			panic("smp_boot_cpus failed to allocate memory\n");
		lowcore_ptr[i]->panic_stack = stack + (PAGE_SIZE);
#ifndef CONFIG_64BIT
		if (MACHINE_HAS_IEEE) {
			lowcore_ptr[i]->extended_save_area_addr =
				(__u32) __get_free_pages(GFP_KERNEL,0);
			if (lowcore_ptr[i]->extended_save_area_addr == 0)
				panic("smp_boot_cpus failed to "
				      "allocate memory\n");
		}
#endif
	}
#ifndef CONFIG_64BIT
	if (MACHINE_HAS_IEEE)
		ctl_set_bit(14, 29); /* enable extended save area */
#endif
	set_prefix((u32)(unsigned long) lowcore_ptr[smp_processor_id()]);

	for_each_possible_cpu(cpu)
		if (cpu != smp_processor_id())
			smp_create_idle(cpu);
}

void __devinit smp_prepare_boot_cpu(void)
{
	BUG_ON(smp_processor_id() != 0);

	cpu_set(0, cpu_online_map);
	S390_lowcore.percpu_offset = __per_cpu_offset[0];
	current_set[0] = current;
}

void smp_cpus_done(unsigned int max_cpus)
{
	cpu_present_map = cpu_possible_map;
}

/*
 * the frequency of the profiling timer can be changed
 * by writing a multiplier value into /proc/profile.
 *
 * usually you want to run this on all CPUs ;)
 */
int setup_profiling_timer(unsigned int multiplier)
{
        return 0;
}

static DEFINE_PER_CPU(struct cpu, cpu_devices);

static int __init topology_init(void)
{
	int cpu;
	int ret;

	for_each_possible_cpu(cpu) {
		ret = register_cpu(&per_cpu(cpu_devices, cpu), cpu);
		if (ret)
			printk(KERN_WARNING "topology_init: register_cpu %d "
			       "failed (%d)\n", cpu, ret);
	}
	return 0;
}

subsys_initcall(topology_init);

EXPORT_SYMBOL(cpu_online_map);
EXPORT_SYMBOL(cpu_possible_map);
EXPORT_SYMBOL(lowcore_ptr);
EXPORT_SYMBOL(smp_ctl_set_bit);
EXPORT_SYMBOL(smp_ctl_clear_bit);
EXPORT_SYMBOL(smp_call_function);
EXPORT_SYMBOL(smp_get_cpu);
EXPORT_SYMBOL(smp_put_cpu);

