/* SMP support routines.
 *
 * Copyright (C) 2006-2008 Panasonic Corporation
 * All Rights Reserved.
 *
 * This program is free software; you can redistribute it and/or
 * modify it under the terms of the GNU General Public License
 * version 2 as published by the Free Software Foundation.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
 * GNU General Public License for more details.
 */

#include <linux/interrupt.h>
#include <linux/spinlock.h>
#include <linux/init.h>
#include <linux/jiffies.h>
#include <linux/cpumask.h>
#include <linux/err.h>
#include <linux/kernel.h>
#include <linux/delay.h>
#include <linux/sched.h>
#include <linux/profile.h>
#include <linux/smp.h>
#include <linux/cpu.h>
#include <asm/tlbflush.h>
#include <asm/bitops.h>
#include <asm/processor.h>
#include <asm/bug.h>
#include <asm/exceptions.h>
#include <asm/hardirq.h>
#include <asm/fpu.h>
#include <asm/mmu_context.h>
#include <asm/thread_info.h>
#include <asm/cpu-regs.h>
#include <asm/intctl-regs.h>
#include "internal.h"

#ifdef CONFIG_HOTPLUG_CPU
#include <asm/cacheflush.h>

static unsigned long sleep_mode[NR_CPUS];

static void run_sleep_cpu(unsigned int cpu);
static void run_wakeup_cpu(unsigned int cpu);
#endif /* CONFIG_HOTPLUG_CPU */

/*
 * Debug Message function
 */

#undef DEBUG_SMP
#ifdef DEBUG_SMP
#define Dprintk(fmt, ...) printk(KERN_DEBUG fmt, ##__VA_ARGS__)
#else
#define Dprintk(fmt, ...) no_printk(KERN_DEBUG fmt, ##__VA_ARGS__)
#endif

/* timeout value in msec for smp_nmi_call_function. zero is no timeout. */
#define	CALL_FUNCTION_NMI_IPI_TIMEOUT	0

/*
 * Structure and data for smp_nmi_call_function().
 */
struct nmi_call_data_struct {
	smp_call_func_t	func;
	void		*info;
	cpumask_t	started;
	cpumask_t	finished;
	int		wait;
	char		size_alignment[0]
	__attribute__ ((__aligned__(SMP_CACHE_BYTES)));
} __attribute__ ((__aligned__(SMP_CACHE_BYTES)));

static DEFINE_SPINLOCK(smp_nmi_call_lock);
static struct nmi_call_data_struct *nmi_call_data;

/*
 * Data structures and variables
 */
static cpumask_t cpu_callin_map;	/* Bitmask of callin CPUs */
static cpumask_t cpu_callout_map;	/* Bitmask of callout CPUs */
cpumask_t cpu_boot_map;			/* Bitmask of boot APs */
unsigned long start_stack[NR_CPUS - 1];

/*
 * Per CPU parameters
 */
struct mn10300_cpuinfo cpu_data[NR_CPUS] __cacheline_aligned;

static int cpucount;			/* The count of boot CPUs */
static cpumask_t smp_commenced_mask;
cpumask_t cpu_initialized __initdata = CPU_MASK_NONE;

/*
 * Function Prototypes
 */
static int do_boot_cpu(int);
static void smp_show_cpu_info(int cpu_id);
static void smp_callin(void);
static void smp_online(void);
static void smp_store_cpu_info(int);
static void smp_cpu_init(void);
static void smp_tune_scheduling(void);
static void send_IPI_mask(const cpumask_t *cpumask, int irq);
static void init_ipi(void);

/*
 * IPI Initialization interrupt definitions
 */
static void mn10300_ipi_disable(unsigned int irq);
static void mn10300_ipi_enable(unsigned int irq);
static void mn10300_ipi_chip_disable(struct irq_data *d);
static void mn10300_ipi_chip_enable(struct irq_data *d);
static void mn10300_ipi_ack(struct irq_data *d);
static void mn10300_ipi_nop(struct irq_data *d);

static struct irq_chip mn10300_ipi_type = {
	.name		= "cpu_ipi",
	.irq_disable	= mn10300_ipi_chip_disable,
	.irq_enable	= mn10300_ipi_chip_enable,
	.irq_ack	= mn10300_ipi_ack,
	.irq_eoi	= mn10300_ipi_nop
};

static irqreturn_t smp_reschedule_interrupt(int irq, void *dev_id);
static irqreturn_t smp_call_function_interrupt(int irq, void *dev_id);

static struct irqaction reschedule_ipi = {
	.handler	= smp_reschedule_interrupt,
	.flags		= IRQF_NOBALANCING,
	.name		= "smp reschedule IPI"
};
static struct irqaction call_function_ipi = {
	.handler	= smp_call_function_interrupt,
	.flags		= IRQF_NOBALANCING,
	.name		= "smp call function IPI"
};

#if !defined(CONFIG_GENERIC_CLOCKEVENTS) || defined(CONFIG_GENERIC_CLOCKEVENTS_BROADCAST)
static irqreturn_t smp_ipi_timer_interrupt(int irq, void *dev_id);
static struct irqaction local_timer_ipi = {
	.handler	= smp_ipi_timer_interrupt,
	.flags		= IRQF_NOBALANCING,
	.name		= "smp local timer IPI"
};
#endif

/**
 * init_ipi - Initialise the IPI mechanism
 */
static void init_ipi(void)
{
	unsigned long flags;
	u16 tmp16;

	/* set up the reschedule IPI */
	irq_set_chip_and_handler(RESCHEDULE_IPI, &mn10300_ipi_type,
				 handle_percpu_irq);
	setup_irq(RESCHEDULE_IPI, &reschedule_ipi);
	set_intr_level(RESCHEDULE_IPI, RESCHEDULE_GxICR_LV);
	mn10300_ipi_enable(RESCHEDULE_IPI);

	/* set up the call function IPI */
	irq_set_chip_and_handler(CALL_FUNC_SINGLE_IPI, &mn10300_ipi_type,
				 handle_percpu_irq);
	setup_irq(CALL_FUNC_SINGLE_IPI, &call_function_ipi);
	set_intr_level(CALL_FUNC_SINGLE_IPI, CALL_FUNCTION_GxICR_LV);
	mn10300_ipi_enable(CALL_FUNC_SINGLE_IPI);

	/* set up the local timer IPI */
#if !defined(CONFIG_GENERIC_CLOCKEVENTS) || \
    defined(CONFIG_GENERIC_CLOCKEVENTS_BROADCAST)
	irq_set_chip_and_handler(LOCAL_TIMER_IPI, &mn10300_ipi_type,
				 handle_percpu_irq);
	setup_irq(LOCAL_TIMER_IPI, &local_timer_ipi);
	set_intr_level(LOCAL_TIMER_IPI, LOCAL_TIMER_GxICR_LV);
	mn10300_ipi_enable(LOCAL_TIMER_IPI);
#endif

#ifdef CONFIG_MN10300_CACHE_ENABLED
	/* set up the cache flush IPI */
	irq_set_chip(FLUSH_CACHE_IPI, &mn10300_ipi_type);
	flags = arch_local_cli_save();
	__set_intr_stub(NUM2EXCEP_IRQ_LEVEL(FLUSH_CACHE_GxICR_LV),
			mn10300_low_ipi_handler);
	GxICR(FLUSH_CACHE_IPI) = FLUSH_CACHE_GxICR_LV | GxICR_DETECT;
	mn10300_ipi_enable(FLUSH_CACHE_IPI);
	arch_local_irq_restore(flags);
#endif

	/* set up the NMI call function IPI */
	irq_set_chip(CALL_FUNCTION_NMI_IPI, &mn10300_ipi_type);
	flags = arch_local_cli_save();
	GxICR(CALL_FUNCTION_NMI_IPI) = GxICR_NMI | GxICR_ENABLE | GxICR_DETECT;
	tmp16 = GxICR(CALL_FUNCTION_NMI_IPI);
	arch_local_irq_restore(flags);

	/* set up the SMP boot IPI */
	flags = arch_local_cli_save();
	__set_intr_stub(NUM2EXCEP_IRQ_LEVEL(SMP_BOOT_GxICR_LV),
			mn10300_low_ipi_handler);
	arch_local_irq_restore(flags);

#ifdef CONFIG_KERNEL_DEBUGGER
	irq_set_chip(DEBUGGER_NMI_IPI, &mn10300_ipi_type);
#endif
}

/**
 * mn10300_ipi_shutdown - Shut down handling of an IPI
 * @irq: The IPI to be shut down.
 */
static void mn10300_ipi_shutdown(unsigned int irq)
{
	unsigned long flags;
	u16 tmp;

	flags = arch_local_cli_save();

	tmp = GxICR(irq);
	GxICR(irq) = (tmp & GxICR_LEVEL) | GxICR_DETECT;
	tmp = GxICR(irq);

	arch_local_irq_restore(flags);
}

/**
 * mn10300_ipi_enable - Enable an IPI
 * @irq: The IPI to be enabled.
 */
static void mn10300_ipi_enable(unsigned int irq)
{
	unsigned long flags;
	u16 tmp;

	flags = arch_local_cli_save();

	tmp = GxICR(irq);
	GxICR(irq) = (tmp & GxICR_LEVEL) | GxICR_ENABLE;
	tmp = GxICR(irq);

	arch_local_irq_restore(flags);
}

static void mn10300_ipi_chip_enable(struct irq_data *d)
{
	mn10300_ipi_enable(d->irq);
}

/**
 * mn10300_ipi_disable - Disable an IPI
 * @irq: The IPI to be disabled.
 */
static void mn10300_ipi_disable(unsigned int irq)
{
	unsigned long flags;
	u16 tmp;

	flags = arch_local_cli_save();

	tmp = GxICR(irq);
	GxICR(irq) = tmp & GxICR_LEVEL;
	tmp = GxICR(irq);

	arch_local_irq_restore(flags);
}

static void mn10300_ipi_chip_disable(struct irq_data *d)
{
	mn10300_ipi_disable(d->irq);
}


/**
 * mn10300_ipi_ack - Acknowledge an IPI interrupt in the PIC
 * @irq: The IPI to be acknowledged.
 *
 * Clear the interrupt detection flag for the IPI on the appropriate interrupt
 * channel in the PIC.
 */
static void mn10300_ipi_ack(struct irq_data *d)
{
	unsigned int irq = d->irq;
	unsigned long flags;
	u16 tmp;

	flags = arch_local_cli_save();
	GxICR_u8(irq) = GxICR_DETECT;
	tmp = GxICR(irq);
	arch_local_irq_restore(flags);
}

/**
 * mn10300_ipi_nop - Dummy IPI action
 * @irq: The IPI to be acted upon.
 */
static void mn10300_ipi_nop(struct irq_data *d)
{
}

/**
 * send_IPI_mask - Send IPIs to all CPUs in list
 * @cpumask: The list of CPUs to target.
 * @irq: The IPI request to be sent.
 *
 * Send the specified IPI to all the CPUs in the list, not waiting for them to
 * finish before returning.  The caller is responsible for synchronisation if
 * that is needed.
 */
static void send_IPI_mask(const cpumask_t *cpumask, int irq)
{
	int i;
	u16 tmp;

	for (i = 0; i < NR_CPUS; i++) {
		if (cpumask_test_cpu(i, cpumask)) {
			/* send IPI */
			tmp = CROSS_GxICR(irq, i);
			CROSS_GxICR(irq, i) =
				tmp | GxICR_REQUEST | GxICR_DETECT;
			tmp = CROSS_GxICR(irq, i); /* flush write buffer */
		}
	}
}

/**
 * send_IPI_self - Send an IPI to this CPU.
 * @irq: The IPI request to be sent.
 *
 * Send the specified IPI to the current CPU.
 */
void send_IPI_self(int irq)
{
	send_IPI_mask(cpumask_of(smp_processor_id()), irq);
}

/**
 * send_IPI_allbutself - Send IPIs to all the other CPUs.
 * @irq: The IPI request to be sent.
 *
 * Send the specified IPI to all CPUs in the system barring the current one,
 * not waiting for them to finish before returning.  The caller is responsible
 * for synchronisation if that is needed.
 */
void send_IPI_allbutself(int irq)
{
	cpumask_t cpumask;

	cpumask_copy(&cpumask, cpu_online_mask);
	cpumask_clear_cpu(smp_processor_id(), &cpumask);
	send_IPI_mask(&cpumask, irq);
}

void arch_send_call_function_ipi_mask(const struct cpumask *mask)
{
	BUG();
	/*send_IPI_mask(mask, CALL_FUNCTION_IPI);*/
}

void arch_send_call_function_single_ipi(int cpu)
{
	send_IPI_mask(cpumask_of(cpu), CALL_FUNC_SINGLE_IPI);
}

/**
 * smp_send_reschedule - Send reschedule IPI to a CPU
 * @cpu: The CPU to target.
 */
void smp_send_reschedule(int cpu)
{
	send_IPI_mask(cpumask_of(cpu), RESCHEDULE_IPI);
}

/**
 * smp_nmi_call_function - Send a call function NMI IPI to all CPUs
 * @func: The function to ask to be run.
 * @info: The context data to pass to that function.
 * @wait: If true, wait (atomically) until function is run on all CPUs.
 *
 * Send a non-maskable request to all CPUs in the system, requesting them to
 * run the specified function with the given context data, and, potentially, to
 * wait for completion of that function on all CPUs.
 *
 * Returns 0 if successful, -ETIMEDOUT if we were asked to wait, but hit the
 * timeout.
 */
int smp_nmi_call_function(smp_call_func_t func, void *info, int wait)
{
	struct nmi_call_data_struct data;
	unsigned long flags;
	unsigned int cnt;
	int cpus, ret = 0;

	cpus = num_online_cpus() - 1;
	if (cpus < 1)
		return 0;

	data.func = func;
	data.info = info;
	cpumask_copy(&data.started, cpu_online_mask);
	cpumask_clear_cpu(smp_processor_id(), &data.started);
	data.wait = wait;
	if (wait)
		data.finished = data.started;

	spin_lock_irqsave(&smp_nmi_call_lock, flags);
	nmi_call_data = &data;
	smp_mb();

	/* Send a message to all other CPUs and wait for them to respond */
	send_IPI_allbutself(CALL_FUNCTION_NMI_IPI);

	/* Wait for response */
	if (CALL_FUNCTION_NMI_IPI_TIMEOUT > 0) {
		for (cnt = 0;
		     cnt < CALL_FUNCTION_NMI_IPI_TIMEOUT &&
			     !cpumask_empty(&data.started);
		     cnt++)
			mdelay(1);

		if (wait && cnt < CALL_FUNCTION_NMI_IPI_TIMEOUT) {
			for (cnt = 0;
			     cnt < CALL_FUNCTION_NMI_IPI_TIMEOUT &&
				     !cpumask_empty(&data.finished);
			     cnt++)
				mdelay(1);
		}

		if (cnt >= CALL_FUNCTION_NMI_IPI_TIMEOUT)
			ret = -ETIMEDOUT;

	} else {
		/* If timeout value is zero, wait until cpumask has been
		 * cleared */
		while (!cpumask_empty(&data.started))
			barrier();
		if (wait)
			while (!cpumask_empty(&data.finished))
				barrier();
	}

	spin_unlock_irqrestore(&smp_nmi_call_lock, flags);
	return ret;
}

/**
 * smp_jump_to_debugger - Make other CPUs enter the debugger by sending an IPI
 *
 * Send a non-maskable request to all other CPUs in the system, instructing
 * them to jump into the debugger.  The caller is responsible for checking that
 * the other CPUs responded to the instruction.
 *
 * The caller should make sure that this CPU's debugger IPI is disabled.
 */
void smp_jump_to_debugger(void)
{
	if (num_online_cpus() > 1)
		/* Send a message to all other CPUs */
		send_IPI_allbutself(DEBUGGER_NMI_IPI);
}

/**
 * stop_this_cpu - Callback to stop a CPU.
 * @unused: Callback context (ignored).
 */
void stop_this_cpu(void *unused)
{
	static volatile int stopflag;
	unsigned long flags;

#ifdef CONFIG_GDBSTUB
	/* In case of single stepping smp_send_stop by other CPU,
	 * clear procindebug to avoid deadlock.
	 */
	atomic_set(&procindebug[smp_processor_id()], 0);
#endif	/* CONFIG_GDBSTUB */

	flags = arch_local_cli_save();
	set_cpu_online(smp_processor_id(), false);

	while (!stopflag)
		cpu_relax();

	set_cpu_online(smp_processor_id(), true);
	arch_local_irq_restore(flags);
}

/**
 * smp_send_stop - Send a stop request to all CPUs.
 */
void smp_send_stop(void)
{
	smp_nmi_call_function(stop_this_cpu, NULL, 0);
}

/**
 * smp_reschedule_interrupt - Reschedule IPI handler
 * @irq: The interrupt number.
 * @dev_id: The device ID.
 *
 * Returns IRQ_HANDLED to indicate we handled the interrupt successfully.
 */
static irqreturn_t smp_reschedule_interrupt(int irq, void *dev_id)
{
	scheduler_ipi();
	return IRQ_HANDLED;
}

/**
 * smp_call_function_interrupt - Call function IPI handler
 * @irq: The interrupt number.
 * @dev_id: The device ID.
 *
 * Returns IRQ_HANDLED to indicate we handled the interrupt successfully.
 */
static irqreturn_t smp_call_function_interrupt(int irq, void *dev_id)
{
	/* generic_smp_call_function_interrupt(); */
	generic_smp_call_function_single_interrupt();
	return IRQ_HANDLED;
}

/**
 * smp_nmi_call_function_interrupt - Non-maskable call function IPI handler
 */
void smp_nmi_call_function_interrupt(void)
{
	smp_call_func_t func = nmi_call_data->func;
	void *info = nmi_call_data->info;
	int wait = nmi_call_data->wait;

	/* Notify the initiating CPU that I've grabbed the data and am about to
	 * execute the function
	 */
	smp_mb();
	cpumask_clear_cpu(smp_processor_id(), &nmi_call_data->started);
	(*func)(info);

	if (wait) {
		smp_mb();
		cpumask_clear_cpu(smp_processor_id(),
				  &nmi_call_data->finished);
	}
}

#if !defined(CONFIG_GENERIC_CLOCKEVENTS) || \
    defined(CONFIG_GENERIC_CLOCKEVENTS_BROADCAST)
/**
 * smp_ipi_timer_interrupt - Local timer IPI handler
 * @irq: The interrupt number.
 * @dev_id: The device ID.
 *
 * Returns IRQ_HANDLED to indicate we handled the interrupt successfully.
 */
static irqreturn_t smp_ipi_timer_interrupt(int irq, void *dev_id)
{
	return local_timer_interrupt();
}
#endif

void __init smp_init_cpus(void)
{
	int i;
	for (i = 0; i < NR_CPUS; i++) {
		set_cpu_possible(i, true);
		set_cpu_present(i, true);
	}
}

/**
 * smp_cpu_init - Initialise AP in start_secondary.
 *
 * For this Application Processor, set up init_mm, initialise FPU and set
 * interrupt level 0-6 setting.
 */
static void __init smp_cpu_init(void)
{
	unsigned long flags;
	int cpu_id = smp_processor_id();
	u16 tmp16;

	if (test_and_set_bit(cpu_id, &cpu_initialized)) {
		printk(KERN_WARNING "CPU#%d already initialized!\n", cpu_id);
		for (;;)
			local_irq_enable();
	}
	printk(KERN_INFO "Initializing CPU#%d\n", cpu_id);

	atomic_inc(&init_mm.mm_count);
	current->active_mm = &init_mm;
	BUG_ON(current->mm);

	enter_lazy_tlb(&init_mm, current);

	/* Force FPU initialization */
	clear_using_fpu(current);

	GxICR(CALL_FUNC_SINGLE_IPI) = CALL_FUNCTION_GxICR_LV | GxICR_DETECT;
	mn10300_ipi_enable(CALL_FUNC_SINGLE_IPI);

	GxICR(LOCAL_TIMER_IPI) = LOCAL_TIMER_GxICR_LV | GxICR_DETECT;
	mn10300_ipi_enable(LOCAL_TIMER_IPI);

	GxICR(RESCHEDULE_IPI) = RESCHEDULE_GxICR_LV | GxICR_DETECT;
	mn10300_ipi_enable(RESCHEDULE_IPI);

#ifdef CONFIG_MN10300_CACHE_ENABLED
	GxICR(FLUSH_CACHE_IPI) = FLUSH_CACHE_GxICR_LV | GxICR_DETECT;
	mn10300_ipi_enable(FLUSH_CACHE_IPI);
#endif

	mn10300_ipi_shutdown(SMP_BOOT_IRQ);

	/* Set up the non-maskable call function IPI */
	flags = arch_local_cli_save();
	GxICR(CALL_FUNCTION_NMI_IPI) = GxICR_NMI | GxICR_ENABLE | GxICR_DETECT;
	tmp16 = GxICR(CALL_FUNCTION_NMI_IPI);
	arch_local_irq_restore(flags);
}

/**
 * smp_prepare_cpu_init - Initialise CPU in startup_secondary
 *
 * Set interrupt level 0-6 setting and init ICR of the kernel debugger.
 */
void smp_prepare_cpu_init(void)
{
	int loop;

	/* Set the interrupt vector registers */
	IVAR0 = EXCEP_IRQ_LEVEL0;
	IVAR1 = EXCEP_IRQ_LEVEL1;
	IVAR2 = EXCEP_IRQ_LEVEL2;
	IVAR3 = EXCEP_IRQ_LEVEL3;
	IVAR4 = EXCEP_IRQ_LEVEL4;
	IVAR5 = EXCEP_IRQ_LEVEL5;
	IVAR6 = EXCEP_IRQ_LEVEL6;

	/* Disable all interrupts and set to priority 6 (lowest) */
	for (loop = 0; loop < GxICR_NUM_IRQS; loop++)
		GxICR(loop) = GxICR_LEVEL_6 | GxICR_DETECT;

#ifdef CONFIG_KERNEL_DEBUGGER
	/* initialise the kernel debugger interrupt */
	do {
		unsigned long flags;
		u16 tmp16;

		flags = arch_local_cli_save();
		GxICR(DEBUGGER_NMI_IPI) = GxICR_NMI | GxICR_ENABLE | GxICR_DETECT;
		tmp16 = GxICR(DEBUGGER_NMI_IPI);
		arch_local_irq_restore(flags);
	} while (0);
#endif
}

/**
 * start_secondary - Activate a secondary CPU (AP)
 * @unused: Thread parameter (ignored).
 */
int __init start_secondary(void *unused)
{
	smp_cpu_init();
	smp_callin();
	while (!cpumask_test_cpu(smp_processor_id(), &smp_commenced_mask))
		cpu_relax();

	local_flush_tlb();
	preempt_disable();
	smp_online();

#ifdef CONFIG_GENERIC_CLOCKEVENTS
	init_clockevents();
#endif
	cpu_startup_entry(CPUHP_ONLINE);
	return 0;
}

/**
 * smp_prepare_cpus - Boot up secondary CPUs (APs)
 * @max_cpus: Maximum number of CPUs to boot.
 *
 * Call do_boot_cpu, and boot up APs.
 */
void __init smp_prepare_cpus(unsigned int max_cpus)
{
	int phy_id;

	/* Setup boot CPU information */
	smp_store_cpu_info(0);
	smp_tune_scheduling();

	init_ipi();

	/* If SMP should be disabled, then finish */
	if (max_cpus == 0) {
		printk(KERN_INFO "SMP mode deactivated.\n");
		goto smp_done;
	}

	/* Boot secondary CPUs (for which phy_id > 0) */
	for (phy_id = 0; phy_id < NR_CPUS; phy_id++) {
		/* Don't boot primary CPU */
		if (max_cpus <= cpucount + 1)
			continue;
		if (phy_id != 0)
			do_boot_cpu(phy_id);
		set_cpu_possible(phy_id, true);
		smp_show_cpu_info(phy_id);
	}

smp_done:
	Dprintk("Boot done.\n");
}

/**
 * smp_store_cpu_info - Save a CPU's information
 * @cpu: The CPU to save for.
 *
 * Save boot_cpu_data and jiffy for the specified CPU.
 */
static void __init smp_store_cpu_info(int cpu)
{
	struct mn10300_cpuinfo *ci = &cpu_data[cpu];

	*ci = boot_cpu_data;
	ci->loops_per_jiffy = loops_per_jiffy;
	ci->type = CPUREV;
}

/**
 * smp_tune_scheduling - Set time slice value
 *
 * Nothing to do here.
 */
static void __init smp_tune_scheduling(void)
{
}

/**
 * do_boot_cpu: Boot up one CPU
 * @phy_id: Physical ID of CPU to boot.
 *
 * Send an IPI to a secondary CPU to boot it.  Returns 0 on success, 1
 * otherwise.
 */
static int __init do_boot_cpu(int phy_id)
{
	struct task_struct *idle;
	unsigned long send_status, callin_status;
	int timeout, cpu_id;

	send_status = GxICR_REQUEST;
	callin_status = 0;
	timeout = 0;
	cpu_id = phy_id;

	cpucount++;

	/* Create idle thread for this CPU */
	idle = fork_idle(cpu_id);
	if (IS_ERR(idle))
		panic("Failed fork for CPU#%d.", cpu_id);

	idle->thread.pc = (unsigned long)start_secondary;

	printk(KERN_NOTICE "Booting CPU#%d\n", cpu_id);
	start_stack[cpu_id - 1] = idle->thread.sp;

	task_thread_info(idle)->cpu = cpu_id;

	/* Send boot IPI to AP */
	send_IPI_mask(cpumask_of(phy_id), SMP_BOOT_IRQ);

	Dprintk("Waiting for send to finish...\n");

	/* Wait for AP's IPI receive in 100[ms] */
	do {
		udelay(1000);
		send_status =
			CROSS_GxICR(SMP_BOOT_IRQ, phy_id) & GxICR_REQUEST;
	} while (send_status == GxICR_REQUEST && timeout++ < 100);

	Dprintk("Waiting for cpu_callin_map.\n");

	if (send_status == 0) {
		/* Allow AP to start initializing */
		cpumask_set_cpu(cpu_id, &cpu_callout_map);

		/* Wait for setting cpu_callin_map */
		timeout = 0;
		do {
			udelay(1000);
			callin_status = cpumask_test_cpu(cpu_id,
							 &cpu_callin_map);
		} while (callin_status == 0 && timeout++ < 5000);

		if (callin_status == 0)
			Dprintk("Not responding.\n");
	} else {
		printk(KERN_WARNING "IPI not delivered.\n");
	}

	if (send_status == GxICR_REQUEST || callin_status == 0) {
		cpumask_clear_cpu(cpu_id, &cpu_callout_map);
		cpumask_clear_cpu(cpu_id, &cpu_callin_map);
		cpumask_clear_cpu(cpu_id, &cpu_initialized);
		cpucount--;
		return 1;
	}
	return 0;
}

/**
 * smp_show_cpu_info - Show SMP CPU information
 * @cpu: The CPU of interest.
 */
static void __init smp_show_cpu_info(int cpu)
{
	struct mn10300_cpuinfo *ci = &cpu_data[cpu];

	printk(KERN_INFO
	       "CPU#%d : ioclk speed: %lu.%02luMHz : bogomips : %lu.%02lu\n",
	       cpu,
	       MN10300_IOCLK / 1000000,
	       (MN10300_IOCLK / 10000) % 100,
	       ci->loops_per_jiffy / (500000 / HZ),
	       (ci->loops_per_jiffy / (5000 / HZ)) % 100);
}

/**
 * smp_callin - Set cpu_callin_map of the current CPU ID
 */
static void __init smp_callin(void)
{
	unsigned long timeout;
	int cpu;

	cpu = smp_processor_id();
	timeout = jiffies + (2 * HZ);

	if (cpumask_test_cpu(cpu, &cpu_callin_map)) {
		printk(KERN_ERR "CPU#%d already present.\n", cpu);
		BUG();
	}
	Dprintk("CPU#%d waiting for CALLOUT\n", cpu);

	/* Wait for AP startup 2s total */
	while (time_before(jiffies, timeout)) {
		if (cpumask_test_cpu(cpu, &cpu_callout_map))
			break;
		cpu_relax();
	}

	if (!time_before(jiffies, timeout)) {
		printk(KERN_ERR
		       "BUG: CPU#%d started up but did not get a callout!\n",
		       cpu);
		BUG();
	}

#ifdef CONFIG_CALIBRATE_DELAY
	calibrate_delay();		/* Get our bogomips */
#endif

	/* Save our processor parameters */
	smp_store_cpu_info(cpu);

	/* Allow the boot processor to continue */
	cpumask_set_cpu(cpu, &cpu_callin_map);
}

/**
 * smp_online - Set cpu_online_mask
 */
static void __init smp_online(void)
{
	int cpu;

	cpu = smp_processor_id();

	notify_cpu_starting(cpu);

	set_cpu_online(cpu, true);

	local_irq_enable();
}

/**
 * smp_cpus_done -
 * @max_cpus: Maximum CPU count.
 *
 * Do nothing.
 */
void __init smp_cpus_done(unsigned int max_cpus)
{
}

/*
 * smp_prepare_boot_cpu - Set up stuff for the boot processor.
 *
 * Set up the cpu_online_mask, cpu_callout_map and cpu_callin_map of the boot
 * processor (CPU 0).
 */
void smp_prepare_boot_cpu(void)
{
	cpumask_set_cpu(0, &cpu_callout_map);
	cpumask_set_cpu(0, &cpu_callin_map);
	current_thread_info()->cpu = 0;
}

/*
 * initialize_secondary - Initialise a secondary CPU (Application Processor).
 *
 * Set SP register and jump to thread's PC address.
 */
void initialize_secondary(void)
{
	asm volatile (
		"mov	%0,sp	\n"
		"jmp	(%1)	\n"
		:
		: "a"(current->thread.sp), "a"(current->thread.pc));
}

/**
 * __cpu_up - Set smp_commenced_mask for the nominated CPU
 * @cpu: The target CPU.
 */
int __cpu_up(unsigned int cpu, struct task_struct *tidle)
{
	int timeout;

#ifdef CONFIG_HOTPLUG_CPU
	if (sleep_mode[cpu])
		run_wakeup_cpu(cpu);
#endif /* CONFIG_HOTPLUG_CPU */

	cpumask_set_cpu(cpu, &smp_commenced_mask);

	/* Wait 5s total for a response */
	for (timeout = 0 ; timeout < 5000 ; timeout++) {
		if (cpu_online(cpu))
			break;
		udelay(1000);
	}

	BUG_ON(!cpu_online(cpu));
	return 0;
}

/**
 * setup_profiling_timer - Set up the profiling timer
 * @multiplier - The frequency multiplier to use
 *
 * The frequency of the profiling timer can be changed by writing a multiplier
 * value into /proc/profile.
 */
int setup_profiling_timer(unsigned int multiplier)
{
	return -EINVAL;
}

/*
 * CPU hotplug routines
 */
#ifdef CONFIG_HOTPLUG_CPU

static DEFINE_PER_CPU(struct cpu, cpu_devices);

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

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

subsys_initcall(topology_init);

int __cpu_disable(void)
{
	int cpu = smp_processor_id();
	if (cpu == 0)
		return -EBUSY;

	migrate_irqs();
	cpumask_clear_cpu(cpu, &mm_cpumask(current->active_mm));
	return 0;
}

void __cpu_die(unsigned int cpu)
{
	run_sleep_cpu(cpu);
}

#ifdef CONFIG_MN10300_CACHE_ENABLED
static inline void hotplug_cpu_disable_cache(void)
{
	int tmp;
	asm volatile(
		"	movhu	(%1),%0	\n"
		"	and	%2,%0	\n"
		"	movhu	%0,(%1)	\n"
		"1:	movhu	(%1),%0	\n"
		"	btst	%3,%0	\n"
		"	bne	1b	\n"
		: "=&r"(tmp)
		: "a"(&CHCTR),
		  "i"(~(CHCTR_ICEN | CHCTR_DCEN)),
		  "i"(CHCTR_ICBUSY | CHCTR_DCBUSY)
		: "memory", "cc");
}

static inline void hotplug_cpu_enable_cache(void)
{
	int tmp;
	asm volatile(
		"movhu	(%1),%0	\n"
		"or	%2,%0	\n"
		"movhu	%0,(%1)	\n"
		: "=&r"(tmp)
		: "a"(&CHCTR),
		  "i"(CHCTR_ICEN | CHCTR_DCEN)
		: "memory", "cc");
}

static inline void hotplug_cpu_invalidate_cache(void)
{
	int tmp;
	asm volatile (
		"movhu	(%1),%0	\n"
		"or	%2,%0	\n"
		"movhu	%0,(%1)	\n"
		: "=&r"(tmp)
		: "a"(&CHCTR),
		  "i"(CHCTR_ICINV | CHCTR_DCINV)
		: "cc");
}

#else /* CONFIG_MN10300_CACHE_ENABLED */
#define hotplug_cpu_disable_cache()	do {} while (0)
#define hotplug_cpu_enable_cache()	do {} while (0)
#define hotplug_cpu_invalidate_cache()	do {} while (0)
#endif /* CONFIG_MN10300_CACHE_ENABLED */

/**
 * hotplug_cpu_nmi_call_function - Call a function on other CPUs for hotplug
 * @cpumask: List of target CPUs.
 * @func: The function to call on those CPUs.
 * @info: The context data for the function to be called.
 * @wait: Whether to wait for the calls to complete.
 *
 * Non-maskably call a function on another CPU for hotplug purposes.
 *
 * This function must be called with maskable interrupts disabled.
 */
static int hotplug_cpu_nmi_call_function(cpumask_t cpumask,
					 smp_call_func_t func, void *info,
					 int wait)
{
	/*
	 * The address and the size of nmi_call_func_mask_data
	 * need to be aligned on L1_CACHE_BYTES.
	 */
	static struct nmi_call_data_struct nmi_call_func_mask_data
		__cacheline_aligned;
	unsigned long start, end;

	start = (unsigned long)&nmi_call_func_mask_data;
	end = start + sizeof(struct nmi_call_data_struct);

	nmi_call_func_mask_data.func = func;
	nmi_call_func_mask_data.info = info;
	nmi_call_func_mask_data.started = cpumask;
	nmi_call_func_mask_data.wait = wait;
	if (wait)
		nmi_call_func_mask_data.finished = cpumask;

	spin_lock(&smp_nmi_call_lock);
	nmi_call_data = &nmi_call_func_mask_data;
	mn10300_local_dcache_flush_range(start, end);
	smp_wmb();

	send_IPI_mask(cpumask, CALL_FUNCTION_NMI_IPI);

	do {
		mn10300_local_dcache_inv_range(start, end);
		barrier();
	} while (!cpumask_empty(&nmi_call_func_mask_data.started));

	if (wait) {
		do {
			mn10300_local_dcache_inv_range(start, end);
			barrier();
		} while (!cpumask_empty(&nmi_call_func_mask_data.finished));
	}

	spin_unlock(&smp_nmi_call_lock);
	return 0;
}

static void restart_wakeup_cpu(void)
{
	unsigned int cpu = smp_processor_id();

	cpumask_set_cpu(cpu, &cpu_callin_map);
	local_flush_tlb();
	set_cpu_online(cpu, true);
	smp_wmb();
}

static void prepare_sleep_cpu(void *unused)
{
	sleep_mode[smp_processor_id()] = 1;
	smp_mb();
	mn10300_local_dcache_flush_inv();
	hotplug_cpu_disable_cache();
	hotplug_cpu_invalidate_cache();
}

/* when this function called, IE=0, NMID=0. */
static void sleep_cpu(void *unused)
{
	unsigned int cpu_id = smp_processor_id();
	/*
	 * CALL_FUNCTION_NMI_IPI for wakeup_cpu() shall not be requested,
	 * before this cpu goes in SLEEP mode.
	 */
	do {
		smp_mb();
		__sleep_cpu();
	} while (sleep_mode[cpu_id]);
	restart_wakeup_cpu();
}

static void run_sleep_cpu(unsigned int cpu)
{
	unsigned long flags;
	cpumask_t cpumask;

	cpumask_copy(&cpumask, &cpumask_of(cpu));
	flags = arch_local_cli_save();
	hotplug_cpu_nmi_call_function(cpumask, prepare_sleep_cpu, NULL, 1);
	hotplug_cpu_nmi_call_function(cpumask, sleep_cpu, NULL, 0);
	udelay(1);		/* delay for the cpu to sleep. */
	arch_local_irq_restore(flags);
}

static void wakeup_cpu(void)
{
	hotplug_cpu_invalidate_cache();
	hotplug_cpu_enable_cache();
	smp_mb();
	sleep_mode[smp_processor_id()] = 0;
}

static void run_wakeup_cpu(unsigned int cpu)
{
	unsigned long flags;

	flags = arch_local_cli_save();
#if NR_CPUS == 2
	mn10300_local_dcache_flush_inv();
#else
	/*
	 * Before waking up the cpu,
	 * all online cpus should stop and flush D-Cache for global data.
	 */
#error not support NR_CPUS > 2, when CONFIG_HOTPLUG_CPU=y.
#endif
	hotplug_cpu_nmi_call_function(cpumask_of(cpu), wakeup_cpu, NULL, 1);
	arch_local_irq_restore(flags);
}

#endif /* CONFIG_HOTPLUG_CPU */
