| /* |
| * Machine specific setup for generic |
| */ |
| |
| #include <linux/smp.h> |
| #include <linux/init.h> |
| #include <linux/interrupt.h> |
| #include <asm/acpi.h> |
| #include <asm/arch_hooks.h> |
| #include <asm/e820.h> |
| #include <asm/setup.h> |
| |
| /* |
| * Any quirks to be performed to initialize timers/irqs/etc? |
| */ |
| int (*arch_time_init_quirk)(void); |
| int (*arch_pre_intr_init_quirk)(void); |
| int (*arch_intr_init_quirk)(void); |
| int (*arch_trap_init_quirk)(void); |
| |
| #ifdef CONFIG_HOTPLUG_CPU |
| #define DEFAULT_SEND_IPI (1) |
| #else |
| #define DEFAULT_SEND_IPI (0) |
| #endif |
| |
| int no_broadcast=DEFAULT_SEND_IPI; |
| |
| /** |
| * pre_intr_init_hook - initialisation prior to setting up interrupt vectors |
| * |
| * Description: |
| * Perform any necessary interrupt initialisation prior to setting up |
| * the "ordinary" interrupt call gates. For legacy reasons, the ISA |
| * interrupts should be initialised here if the machine emulates a PC |
| * in any way. |
| **/ |
| void __init pre_intr_init_hook(void) |
| { |
| if (arch_pre_intr_init_quirk) { |
| if (arch_pre_intr_init_quirk()) |
| return; |
| } |
| init_ISA_irqs(); |
| } |
| |
| /* |
| * IRQ2 is cascade interrupt to second interrupt controller |
| */ |
| static struct irqaction irq2 = { |
| .handler = no_action, |
| .mask = CPU_MASK_NONE, |
| .name = "cascade", |
| }; |
| |
| /** |
| * intr_init_hook - post gate setup interrupt initialisation |
| * |
| * Description: |
| * Fill in any interrupts that may have been left out by the general |
| * init_IRQ() routine. interrupts having to do with the machine rather |
| * than the devices on the I/O bus (like APIC interrupts in intel MP |
| * systems) are started here. |
| **/ |
| void __init intr_init_hook(void) |
| { |
| if (arch_intr_init_quirk) { |
| if (arch_intr_init_quirk()) |
| return; |
| } |
| #ifdef CONFIG_X86_LOCAL_APIC |
| apic_intr_init(); |
| #endif |
| |
| if (!acpi_ioapic) |
| setup_irq(2, &irq2); |
| } |
| |
| /** |
| * pre_setup_arch_hook - hook called prior to any setup_arch() execution |
| * |
| * Description: |
| * generally used to activate any machine specific identification |
| * routines that may be needed before setup_arch() runs. On Voyager |
| * this is used to get the board revision and type. |
| **/ |
| void __init pre_setup_arch_hook(void) |
| { |
| } |
| |
| /** |
| * trap_init_hook - initialise system specific traps |
| * |
| * Description: |
| * Called as the final act of trap_init(). Used in VISWS to initialise |
| * the various board specific APIC traps. |
| **/ |
| void __init trap_init_hook(void) |
| { |
| if (arch_trap_init_quirk) { |
| if (arch_trap_init_quirk()) |
| return; |
| } |
| } |
| |
| static struct irqaction irq0 = { |
| .handler = timer_interrupt, |
| .flags = IRQF_DISABLED | IRQF_NOBALANCING | IRQF_IRQPOLL, |
| .mask = CPU_MASK_NONE, |
| .name = "timer" |
| }; |
| |
| /** |
| * time_init_hook - do any specific initialisations for the system timer. |
| * |
| * Description: |
| * Must plug the system timer interrupt source at HZ into the IRQ listed |
| * in irq_vectors.h:TIMER_IRQ |
| **/ |
| void __init time_init_hook(void) |
| { |
| if (arch_time_init_quirk) { |
| /* |
| * A nonzero return code does not mean failure, it means |
| * that the architecture quirk does not want any |
| * generic (timer) setup to be performed after this: |
| */ |
| if (arch_time_init_quirk()) |
| return; |
| } |
| |
| irq0.mask = cpumask_of_cpu(0); |
| setup_irq(0, &irq0); |
| } |
| |
| #ifdef CONFIG_MCA |
| /** |
| * mca_nmi_hook - hook into MCA specific NMI chain |
| * |
| * Description: |
| * The MCA (Microchannel Architecture) has an NMI chain for NMI sources |
| * along the MCA bus. Use this to hook into that chain if you will need |
| * it. |
| **/ |
| void mca_nmi_hook(void) |
| { |
| /* If I recall correctly, there's a whole bunch of other things that |
| * we can do to check for NMI problems, but that's all I know about |
| * at the moment. |
| */ |
| |
| printk("NMI generated from unknown source!\n"); |
| } |
| #endif |
| |
| static __init int no_ipi_broadcast(char *str) |
| { |
| get_option(&str, &no_broadcast); |
| printk ("Using %s mode\n", no_broadcast ? "No IPI Broadcast" : |
| "IPI Broadcast"); |
| return 1; |
| } |
| |
| __setup("no_ipi_broadcast=", no_ipi_broadcast); |
| |
| static int __init print_ipi_mode(void) |
| { |
| printk ("Using IPI %s mode\n", no_broadcast ? "No-Shortcut" : |
| "Shortcut"); |
| return 0; |
| } |
| |
| late_initcall(print_ipi_mode); |
| |