aboutsummaryrefslogtreecommitdiffstats
path: root/arch/x86_64/kernel
diff options
context:
space:
mode:
Diffstat (limited to 'arch/x86_64/kernel')
-rw-r--r--arch/x86_64/kernel/apic.c3
-rw-r--r--arch/x86_64/kernel/entry.S1
-rw-r--r--arch/x86_64/kernel/head.S7
-rw-r--r--arch/x86_64/kernel/io_apic.c16
-rw-r--r--arch/x86_64/kernel/mpparse.c4
-rw-r--r--arch/x86_64/kernel/nmi.c19
-rw-r--r--arch/x86_64/kernel/pci-gart.c6
-rw-r--r--arch/x86_64/kernel/time.c15
-rw-r--r--arch/x86_64/kernel/traps.c18
9 files changed, 68 insertions, 21 deletions
diff --git a/arch/x86_64/kernel/apic.c b/arch/x86_64/kernel/apic.c
index 6147770b4347..e5b14c57eaa0 100644
--- a/arch/x86_64/kernel/apic.c
+++ b/arch/x86_64/kernel/apic.c
@@ -708,7 +708,7 @@ static void setup_APIC_timer(unsigned int clocks)
708 local_irq_save(flags); 708 local_irq_save(flags);
709 709
710 /* wait for irq slice */ 710 /* wait for irq slice */
711 if (vxtime.hpet_address) { 711 if (vxtime.hpet_address && hpet_use_timer) {
712 int trigger = hpet_readl(HPET_T0_CMP); 712 int trigger = hpet_readl(HPET_T0_CMP);
713 while (hpet_readl(HPET_COUNTER) >= trigger) 713 while (hpet_readl(HPET_COUNTER) >= trigger)
714 /* do nothing */ ; 714 /* do nothing */ ;
@@ -1152,6 +1152,7 @@ __setup("noapicmaintimer", setup_noapicmaintimer);
1152static __init int setup_apicpmtimer(char *s) 1152static __init int setup_apicpmtimer(char *s)
1153{ 1153{
1154 apic_calibrate_pmtmr = 1; 1154 apic_calibrate_pmtmr = 1;
1155 notsc_setup(NULL);
1155 return setup_apicmaintimer(NULL); 1156 return setup_apicmaintimer(NULL);
1156} 1157}
1157__setup("apicpmtimer", setup_apicpmtimer); 1158__setup("apicpmtimer", setup_apicpmtimer);
diff --git a/arch/x86_64/kernel/entry.S b/arch/x86_64/kernel/entry.S
index b150c87a08c6..7c10e9009d61 100644
--- a/arch/x86_64/kernel/entry.S
+++ b/arch/x86_64/kernel/entry.S
@@ -554,6 +554,7 @@ iret_label:
554 /* running with kernel gs */ 554 /* running with kernel gs */
555bad_iret: 555bad_iret:
556 movq $-9999,%rdi /* better code? */ 556 movq $-9999,%rdi /* better code? */
557 sti
557 jmp do_exit 558 jmp do_exit
558 .previous 559 .previous
559 560
diff --git a/arch/x86_64/kernel/head.S b/arch/x86_64/kernel/head.S
index 692c737feddb..02fc7fa0ea28 100644
--- a/arch/x86_64/kernel/head.S
+++ b/arch/x86_64/kernel/head.S
@@ -213,6 +213,11 @@ ENTRY(early_idt_handler)
213 cmpl $2,early_recursion_flag(%rip) 213 cmpl $2,early_recursion_flag(%rip)
214 jz 1f 214 jz 1f
215 call dump_stack 215 call dump_stack
216#ifdef CONFIG_KALLSYMS
217 leaq early_idt_ripmsg(%rip),%rdi
218 movq 8(%rsp),%rsi # get rip again
219 call __print_symbol
220#endif
2161: hlt 2211: hlt
217 jmp 1b 222 jmp 1b
218early_recursion_flag: 223early_recursion_flag:
@@ -220,6 +225,8 @@ early_recursion_flag:
220 225
221early_idt_msg: 226early_idt_msg:
222 .asciz "PANIC: early exception rip %lx error %lx cr2 %lx\n" 227 .asciz "PANIC: early exception rip %lx error %lx cr2 %lx\n"
228early_idt_ripmsg:
229 .asciz "RIP %s\n"
223 230
224.code32 231.code32
225ENTRY(no_long_mode) 232ENTRY(no_long_mode)
diff --git a/arch/x86_64/kernel/io_apic.c b/arch/x86_64/kernel/io_apic.c
index 4282d72b2a26..2585c1d92b26 100644
--- a/arch/x86_64/kernel/io_apic.c
+++ b/arch/x86_64/kernel/io_apic.c
@@ -30,6 +30,9 @@
30#include <linux/mc146818rtc.h> 30#include <linux/mc146818rtc.h>
31#include <linux/acpi.h> 31#include <linux/acpi.h>
32#include <linux/sysdev.h> 32#include <linux/sysdev.h>
33#ifdef CONFIG_ACPI
34#include <acpi/acpi_bus.h>
35#endif
33 36
34#include <asm/io.h> 37#include <asm/io.h>
35#include <asm/smp.h> 38#include <asm/smp.h>
@@ -260,6 +263,8 @@ __setup("apic", enable_ioapic_setup);
260 263
261 And another hack to disable the IOMMU on VIA chipsets. 264 And another hack to disable the IOMMU on VIA chipsets.
262 265
266 ... and others. Really should move this somewhere else.
267
263 Kludge-O-Rama. */ 268 Kludge-O-Rama. */
264void __init check_ioapic(void) 269void __init check_ioapic(void)
265{ 270{
@@ -307,6 +312,17 @@ void __init check_ioapic(void)
307 case PCI_VENDOR_ID_ATI: 312 case PCI_VENDOR_ID_ATI:
308 if (apic_runs_main_timer != 0) 313 if (apic_runs_main_timer != 0)
309 break; 314 break;
315#ifdef CONFIG_ACPI
316 /* Don't do this for laptops right
317 right now because their timer
318 doesn't necessarily tick in C2/3 */
319 if (acpi_fadt.revision >= 3 &&
320 (acpi_fadt.plvl2_lat + acpi_fadt.plvl3_lat) < 1100) {
321 printk(KERN_INFO
322"ATI board detected, but seems to be a laptop. Timer might be shakey, sorry\n");
323 break;
324 }
325#endif
310 printk(KERN_INFO 326 printk(KERN_INFO
311 "ATI board detected. Using APIC/PM timer.\n"); 327 "ATI board detected. Using APIC/PM timer.\n");
312 apic_runs_main_timer = 1; 328 apic_runs_main_timer = 1;
diff --git a/arch/x86_64/kernel/mpparse.c b/arch/x86_64/kernel/mpparse.c
index dc49bfb6db0a..9013a90b5c2e 100644
--- a/arch/x86_64/kernel/mpparse.c
+++ b/arch/x86_64/kernel/mpparse.c
@@ -288,9 +288,9 @@ static int __init smp_read_mpc(struct mp_config_table *mpc)
288 288
289 memcpy(str,mpc->mpc_productid,12); 289 memcpy(str,mpc->mpc_productid,12);
290 str[12]=0; 290 str[12]=0;
291 printk(KERN_INFO "Product ID: %s ",str); 291 printk("Product ID: %s ",str);
292 292
293 printk(KERN_INFO "APIC at: 0x%X\n",mpc->mpc_lapic); 293 printk("APIC at: 0x%X\n",mpc->mpc_lapic);
294 294
295 /* save the local APIC address, it might be non-default */ 295 /* save the local APIC address, it might be non-default */
296 if (!acpi_lapic) 296 if (!acpi_lapic)
diff --git a/arch/x86_64/kernel/nmi.c b/arch/x86_64/kernel/nmi.c
index 8be407a1f62d..5bf17e41cd2d 100644
--- a/arch/x86_64/kernel/nmi.c
+++ b/arch/x86_64/kernel/nmi.c
@@ -236,6 +236,7 @@ static void enable_lapic_nmi_watchdog(void)
236{ 236{
237 if (nmi_active < 0) { 237 if (nmi_active < 0) {
238 nmi_watchdog = NMI_LOCAL_APIC; 238 nmi_watchdog = NMI_LOCAL_APIC;
239 touch_nmi_watchdog();
239 setup_apic_nmi_watchdog(); 240 setup_apic_nmi_watchdog();
240 } 241 }
241} 242}
@@ -456,15 +457,17 @@ static DEFINE_PER_CPU(int, nmi_touch);
456 457
457void touch_nmi_watchdog (void) 458void touch_nmi_watchdog (void)
458{ 459{
459 int i; 460 if (nmi_watchdog > 0) {
461 unsigned cpu;
460 462
461 /* 463 /*
462 * Tell other CPUs to reset their alert counters. We cannot 464 * Tell other CPUs to reset their alert counters. We cannot
463 * do it ourselves because the alert count increase is not 465 * do it ourselves because the alert count increase is not
464 * atomic. 466 * atomic.
465 */ 467 */
466 for (i = 0; i < NR_CPUS; i++) 468 for_each_present_cpu (cpu)
467 per_cpu(nmi_touch, i) = 1; 469 per_cpu(nmi_touch, cpu) = 1;
470 }
468 471
469 touch_softlockup_watchdog(); 472 touch_softlockup_watchdog();
470} 473}
diff --git a/arch/x86_64/kernel/pci-gart.c b/arch/x86_64/kernel/pci-gart.c
index 2fe23a6c361b..dd0718dc178b 100644
--- a/arch/x86_64/kernel/pci-gart.c
+++ b/arch/x86_64/kernel/pci-gart.c
@@ -310,7 +310,7 @@ void gart_unmap_sg(struct device *dev, struct scatterlist *sg, int nents, int di
310 310
311 for (i = 0; i < nents; i++) { 311 for (i = 0; i < nents; i++) {
312 struct scatterlist *s = &sg[i]; 312 struct scatterlist *s = &sg[i];
313 if (!s->dma_length || !s->length) 313 if (!s->dma_length)
314 break; 314 break;
315 dma_unmap_single(dev, s->dma_address, s->dma_length, dir); 315 dma_unmap_single(dev, s->dma_address, s->dma_length, dir);
316 } 316 }
@@ -364,7 +364,6 @@ static int __dma_map_cont(struct scatterlist *sg, int start, int stopat,
364 364
365 BUG_ON(i > start && s->offset); 365 BUG_ON(i > start && s->offset);
366 if (i == start) { 366 if (i == start) {
367 *sout = *s;
368 sout->dma_address = iommu_bus_base; 367 sout->dma_address = iommu_bus_base;
369 sout->dma_address += iommu_page*PAGE_SIZE + s->offset; 368 sout->dma_address += iommu_page*PAGE_SIZE + s->offset;
370 sout->dma_length = s->length; 369 sout->dma_length = s->length;
@@ -379,7 +378,7 @@ static int __dma_map_cont(struct scatterlist *sg, int start, int stopat,
379 SET_LEAK(iommu_page); 378 SET_LEAK(iommu_page);
380 addr += PAGE_SIZE; 379 addr += PAGE_SIZE;
381 iommu_page++; 380 iommu_page++;
382 } 381 }
383 } 382 }
384 BUG_ON(iommu_page - iommu_start != pages); 383 BUG_ON(iommu_page - iommu_start != pages);
385 return 0; 384 return 0;
@@ -391,7 +390,6 @@ static inline int dma_map_cont(struct scatterlist *sg, int start, int stopat,
391{ 390{
392 if (!need) { 391 if (!need) {
393 BUG_ON(stopat - start != 1); 392 BUG_ON(stopat - start != 1);
394 *sout = sg[start];
395 sout->dma_length = sg[start].length; 393 sout->dma_length = sg[start].length;
396 return 0; 394 return 0;
397 } 395 }
diff --git a/arch/x86_64/kernel/time.c b/arch/x86_64/kernel/time.c
index dba7237be5c1..67841d11ed1f 100644
--- a/arch/x86_64/kernel/time.c
+++ b/arch/x86_64/kernel/time.c
@@ -59,7 +59,7 @@ static int notsc __initdata = 0;
59unsigned int cpu_khz; /* TSC clocks / usec, not used here */ 59unsigned int cpu_khz; /* TSC clocks / usec, not used here */
60static unsigned long hpet_period; /* fsecs / HPET clock */ 60static unsigned long hpet_period; /* fsecs / HPET clock */
61unsigned long hpet_tick; /* HPET clocks / interrupt */ 61unsigned long hpet_tick; /* HPET clocks / interrupt */
62static int hpet_use_timer; /* Use counter of hpet for time keeping, otherwise PIT */ 62int hpet_use_timer; /* Use counter of hpet for time keeping, otherwise PIT */
63unsigned long vxtime_hz = PIT_TICK_RATE; 63unsigned long vxtime_hz = PIT_TICK_RATE;
64int report_lost_ticks; /* command line option */ 64int report_lost_ticks; /* command line option */
65unsigned long long monotonic_base; 65unsigned long long monotonic_base;
@@ -326,7 +326,10 @@ static noinline void handle_lost_ticks(int lost, struct pt_regs *regs)
326 print_symbol("rip %s\n", regs->rip); 326 print_symbol("rip %s\n", regs->rip);
327 if (vxtime.mode == VXTIME_TSC && vxtime.hpet_address) { 327 if (vxtime.mode == VXTIME_TSC && vxtime.hpet_address) {
328 printk(KERN_WARNING "Falling back to HPET\n"); 328 printk(KERN_WARNING "Falling back to HPET\n");
329 vxtime.last = hpet_readl(HPET_T0_CMP) - hpet_tick; 329 if (hpet_use_timer)
330 vxtime.last = hpet_readl(HPET_T0_CMP) - hpet_tick;
331 else
332 vxtime.last = hpet_readl(HPET_COUNTER);
330 vxtime.mode = VXTIME_HPET; 333 vxtime.mode = VXTIME_HPET;
331 do_gettimeoffset = do_gettimeoffset_hpet; 334 do_gettimeoffset = do_gettimeoffset_hpet;
332 } 335 }
@@ -988,7 +991,10 @@ void __init time_init_gtod(void)
988 notsc = 1; 991 notsc = 1;
989 if (vxtime.hpet_address && notsc) { 992 if (vxtime.hpet_address && notsc) {
990 timetype = hpet_use_timer ? "HPET" : "PIT/HPET"; 993 timetype = hpet_use_timer ? "HPET" : "PIT/HPET";
991 vxtime.last = hpet_readl(HPET_T0_CMP) - hpet_tick; 994 if (hpet_use_timer)
995 vxtime.last = hpet_readl(HPET_T0_CMP) - hpet_tick;
996 else
997 vxtime.last = hpet_readl(HPET_COUNTER);
992 vxtime.mode = VXTIME_HPET; 998 vxtime.mode = VXTIME_HPET;
993 do_gettimeoffset = do_gettimeoffset_hpet; 999 do_gettimeoffset = do_gettimeoffset_hpet;
994#ifdef CONFIG_X86_PM_TIMER 1000#ifdef CONFIG_X86_PM_TIMER
@@ -1321,8 +1327,7 @@ static int __init nohpet_setup(char *s)
1321 1327
1322__setup("nohpet", nohpet_setup); 1328__setup("nohpet", nohpet_setup);
1323 1329
1324 1330int __init notsc_setup(char *s)
1325static int __init notsc_setup(char *s)
1326{ 1331{
1327 notsc = 1; 1332 notsc = 1;
1328 return 0; 1333 return 0;
diff --git a/arch/x86_64/kernel/traps.c b/arch/x86_64/kernel/traps.c
index ee1b2da9e5e7..28d50dc540e8 100644
--- a/arch/x86_64/kernel/traps.c
+++ b/arch/x86_64/kernel/traps.c
@@ -90,6 +90,20 @@ static inline void conditional_sti(struct pt_regs *regs)
90 local_irq_enable(); 90 local_irq_enable();
91} 91}
92 92
93static inline void preempt_conditional_sti(struct pt_regs *regs)
94{
95 preempt_disable();
96 if (regs->eflags & X86_EFLAGS_IF)
97 local_irq_enable();
98}
99
100static inline void preempt_conditional_cli(struct pt_regs *regs)
101{
102 if (regs->eflags & X86_EFLAGS_IF)
103 local_irq_disable();
104 preempt_enable_no_resched();
105}
106
93static int kstack_depth_to_print = 10; 107static int kstack_depth_to_print = 10;
94 108
95#ifdef CONFIG_KALLSYMS 109#ifdef CONFIG_KALLSYMS
@@ -693,7 +707,7 @@ asmlinkage void __kprobes do_debug(struct pt_regs * regs,
693 SIGTRAP) == NOTIFY_STOP) 707 SIGTRAP) == NOTIFY_STOP)
694 return; 708 return;
695 709
696 conditional_sti(regs); 710 preempt_conditional_sti(regs);
697 711
698 /* Mask out spurious debug traps due to lazy DR7 setting */ 712 /* Mask out spurious debug traps due to lazy DR7 setting */
699 if (condition & (DR_TRAP0|DR_TRAP1|DR_TRAP2|DR_TRAP3)) { 713 if (condition & (DR_TRAP0|DR_TRAP1|DR_TRAP2|DR_TRAP3)) {
@@ -738,11 +752,13 @@ asmlinkage void __kprobes do_debug(struct pt_regs * regs,
738 752
739clear_dr7: 753clear_dr7:
740 set_debugreg(0UL, 7); 754 set_debugreg(0UL, 7);
755 preempt_conditional_cli(regs);
741 return; 756 return;
742 757
743clear_TF_reenable: 758clear_TF_reenable:
744 set_tsk_thread_flag(tsk, TIF_SINGLESTEP); 759 set_tsk_thread_flag(tsk, TIF_SINGLESTEP);
745 regs->eflags &= ~TF_MASK; 760 regs->eflags &= ~TF_MASK;
761 preempt_conditional_cli(regs);
746} 762}
747 763
748static int kernel_math_error(struct pt_regs *regs, const char *str, int trapnr) 764static int kernel_math_error(struct pt_regs *regs, const char *str, int trapnr)