aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorYinghai Lu <yhlu.kernel@gmail.com>2008-09-03 19:58:31 -0400
committerIngo Molnar <mingo@elte.hu>2008-10-16 10:53:04 -0400
commita11b5abef50722e42a7d13f6b799c4f606fcb797 (patch)
treeeed224f07b6c8fc20cc4a454578e34721999b763
parentc59d85a7b7822b83fc9783314543eea0ca860480 (diff)
x2apic: fix reserved APIC register accesses in print_local_APIC()
APIC_ARBPRI is a reserved register for XAPIC and beyond. APIC_RRR is a reserved register except for 82489DX, APIC for Pentium processors. APIC_EOI is a write only register. APIC_DFR is reserved in x2apic mode. Access to these registers in x2apic will result in #GP fault. Fix these apic register accesses. Signed-off-by: Yinghai Lu <yhlu.kernel@gmail.com> Signed-off-by: Suresh Siddha <suresh.b.siddha@intel.com> Cc: Maciej W. Rozycki <macro@linux-mips.org> Signed-off-by: Ingo Molnar <mingo@elte.hu>
-rw-r--r--arch/x86/kernel/io_apic.c27
-rw-r--r--include/asm-x86/apic.h14
2 files changed, 32 insertions, 9 deletions
diff --git a/arch/x86/kernel/io_apic.c b/arch/x86/kernel/io_apic.c
index d28128e0392c..93ceb19d1e90 100644
--- a/arch/x86/kernel/io_apic.c
+++ b/arch/x86/kernel/io_apic.c
@@ -1751,21 +1751,30 @@ __apicdebuginit(void) print_local_APIC(void *dummy)
1751 printk(KERN_DEBUG "... APIC TASKPRI: %08x (%02x)\n", v, v & APIC_TPRI_MASK); 1751 printk(KERN_DEBUG "... APIC TASKPRI: %08x (%02x)\n", v, v & APIC_TPRI_MASK);
1752 1752
1753 if (APIC_INTEGRATED(ver)) { /* !82489DX */ 1753 if (APIC_INTEGRATED(ver)) { /* !82489DX */
1754 v = apic_read(APIC_ARBPRI); 1754 if (!APIC_XAPIC(ver)) {
1755 printk(KERN_DEBUG "... APIC ARBPRI: %08x (%02x)\n", v, 1755 v = apic_read(APIC_ARBPRI);
1756 v & APIC_ARBPRI_MASK); 1756 printk(KERN_DEBUG "... APIC ARBPRI: %08x (%02x)\n", v,
1757 v & APIC_ARBPRI_MASK);
1758 }
1757 v = apic_read(APIC_PROCPRI); 1759 v = apic_read(APIC_PROCPRI);
1758 printk(KERN_DEBUG "... APIC PROCPRI: %08x\n", v); 1760 printk(KERN_DEBUG "... APIC PROCPRI: %08x\n", v);
1759 } 1761 }
1760 1762
1761 v = apic_read(APIC_EOI); 1763 /*
1762 printk(KERN_DEBUG "... APIC EOI: %08x\n", v); 1764 * Remote read supported only in the 82489DX and local APIC for
1763 v = apic_read(APIC_RRR); 1765 * Pentium processors.
1764 printk(KERN_DEBUG "... APIC RRR: %08x\n", v); 1766 */
1767 if (!APIC_INTEGRATED(ver) || maxlvt == 3) {
1768 v = apic_read(APIC_RRR);
1769 printk(KERN_DEBUG "... APIC RRR: %08x\n", v);
1770 }
1771
1765 v = apic_read(APIC_LDR); 1772 v = apic_read(APIC_LDR);
1766 printk(KERN_DEBUG "... APIC LDR: %08x\n", v); 1773 printk(KERN_DEBUG "... APIC LDR: %08x\n", v);
1767 v = apic_read(APIC_DFR); 1774 if (!x2apic_enabled()) {
1768 printk(KERN_DEBUG "... APIC DFR: %08x\n", v); 1775 v = apic_read(APIC_DFR);
1776 printk(KERN_DEBUG "... APIC DFR: %08x\n", v);
1777 }
1769 v = apic_read(APIC_SPIV); 1778 v = apic_read(APIC_SPIV);
1770 printk(KERN_DEBUG "... APIC SPIV: %08x\n", v); 1779 printk(KERN_DEBUG "... APIC SPIV: %08x\n", v);
1771 1780
diff --git a/include/asm-x86/apic.h b/include/asm-x86/apic.h
index 2d970f6bc2a1..ef1d72dbdfe0 100644
--- a/include/asm-x86/apic.h
+++ b/include/asm-x86/apic.h
@@ -98,6 +98,20 @@ extern void check_x2apic(void);
98extern void enable_x2apic(void); 98extern void enable_x2apic(void);
99extern void enable_IR_x2apic(void); 99extern void enable_IR_x2apic(void);
100extern void x2apic_icr_write(u32 low, u32 id); 100extern void x2apic_icr_write(u32 low, u32 id);
101static inline int x2apic_enabled(void)
102{
103 int msr, msr2;
104
105 if (!cpu_has_x2apic)
106 return 0;
107
108 rdmsr(MSR_IA32_APICBASE, msr, msr2);
109 if (msr & X2APIC_ENABLE)
110 return 1;
111 return 0;
112}
113#else
114#define x2apic_enabled() 0
101#endif 115#endif
102 116
103struct apic_ops { 117struct apic_ops {