aboutsummaryrefslogtreecommitdiffstats
path: root/arch
diff options
context:
space:
mode:
Diffstat (limited to 'arch')
-rw-r--r--arch/x86/include/asm/pda.h2
-rw-r--r--arch/x86/kernel/asm-offsets_64.c1
-rw-r--r--arch/x86/kernel/entry_64.S10
-rw-r--r--arch/x86/kernel/process_64.c8
-rw-r--r--arch/x86/xen/xen-asm_64.S8
5 files changed, 15 insertions, 14 deletions
diff --git a/arch/x86/include/asm/pda.h b/arch/x86/include/asm/pda.h
index 4d28ffba6e1b..ae23deb99559 100644
--- a/arch/x86/include/asm/pda.h
+++ b/arch/x86/include/asm/pda.h
@@ -14,7 +14,7 @@ struct x8664_pda {
14 unsigned long unused1; 14 unsigned long unused1;
15 unsigned long unused2; 15 unsigned long unused2;
16 unsigned long unused3; 16 unsigned long unused3;
17 unsigned long oldrsp; /* 24 user rsp for system call */ 17 unsigned long unused4;
18 int irqcount; /* 32 Irq nesting counter. Starts -1 */ 18 int irqcount; /* 32 Irq nesting counter. Starts -1 */
19 unsigned int unused6; /* 36 was cpunumber */ 19 unsigned int unused6; /* 36 was cpunumber */
20#ifdef CONFIG_CC_STACKPROTECTOR 20#ifdef CONFIG_CC_STACKPROTECTOR
diff --git a/arch/x86/kernel/asm-offsets_64.c b/arch/x86/kernel/asm-offsets_64.c
index cafff5f4a031..afda6deb8515 100644
--- a/arch/x86/kernel/asm-offsets_64.c
+++ b/arch/x86/kernel/asm-offsets_64.c
@@ -49,7 +49,6 @@ int main(void)
49 BLANK(); 49 BLANK();
50#undef ENTRY 50#undef ENTRY
51#define ENTRY(entry) DEFINE(pda_ ## entry, offsetof(struct x8664_pda, entry)) 51#define ENTRY(entry) DEFINE(pda_ ## entry, offsetof(struct x8664_pda, entry))
52 ENTRY(oldrsp);
53 ENTRY(irqcount); 52 ENTRY(irqcount);
54 DEFINE(pda_size, sizeof(struct x8664_pda)); 53 DEFINE(pda_size, sizeof(struct x8664_pda));
55 BLANK(); 54 BLANK();
diff --git a/arch/x86/kernel/entry_64.S b/arch/x86/kernel/entry_64.S
index 0dd45859a7a8..7c27da407da7 100644
--- a/arch/x86/kernel/entry_64.S
+++ b/arch/x86/kernel/entry_64.S
@@ -210,7 +210,7 @@ ENTRY(native_usergs_sysret64)
210 210
211 /* %rsp:at FRAMEEND */ 211 /* %rsp:at FRAMEEND */
212 .macro FIXUP_TOP_OF_STACK tmp offset=0 212 .macro FIXUP_TOP_OF_STACK tmp offset=0
213 movq %gs:pda_oldrsp,\tmp 213 movq PER_CPU_VAR(old_rsp),\tmp
214 movq \tmp,RSP+\offset(%rsp) 214 movq \tmp,RSP+\offset(%rsp)
215 movq $__USER_DS,SS+\offset(%rsp) 215 movq $__USER_DS,SS+\offset(%rsp)
216 movq $__USER_CS,CS+\offset(%rsp) 216 movq $__USER_CS,CS+\offset(%rsp)
@@ -221,7 +221,7 @@ ENTRY(native_usergs_sysret64)
221 221
222 .macro RESTORE_TOP_OF_STACK tmp offset=0 222 .macro RESTORE_TOP_OF_STACK tmp offset=0
223 movq RSP+\offset(%rsp),\tmp 223 movq RSP+\offset(%rsp),\tmp
224 movq \tmp,%gs:pda_oldrsp 224 movq \tmp,PER_CPU_VAR(old_rsp)
225 movq EFLAGS+\offset(%rsp),\tmp 225 movq EFLAGS+\offset(%rsp),\tmp
226 movq \tmp,R11+\offset(%rsp) 226 movq \tmp,R11+\offset(%rsp)
227 .endm 227 .endm
@@ -479,7 +479,7 @@ ENTRY(system_call)
479 */ 479 */
480ENTRY(system_call_after_swapgs) 480ENTRY(system_call_after_swapgs)
481 481
482 movq %rsp,%gs:pda_oldrsp 482 movq %rsp,PER_CPU_VAR(old_rsp)
483 movq PER_CPU_VAR(kernel_stack),%rsp 483 movq PER_CPU_VAR(kernel_stack),%rsp
484 /* 484 /*
485 * No need to follow this irqs off/on section - it's straight 485 * No need to follow this irqs off/on section - it's straight
@@ -523,7 +523,7 @@ sysret_check:
523 CFI_REGISTER rip,rcx 523 CFI_REGISTER rip,rcx
524 RESTORE_ARGS 0,-ARG_SKIP,1 524 RESTORE_ARGS 0,-ARG_SKIP,1
525 /*CFI_REGISTER rflags,r11*/ 525 /*CFI_REGISTER rflags,r11*/
526 movq %gs:pda_oldrsp, %rsp 526 movq PER_CPU_VAR(old_rsp), %rsp
527 USERGS_SYSRET64 527 USERGS_SYSRET64
528 528
529 CFI_RESTORE_STATE 529 CFI_RESTORE_STATE
@@ -833,7 +833,7 @@ common_interrupt:
833 XCPT_FRAME 833 XCPT_FRAME
834 addq $-0x80,(%rsp) /* Adjust vector to [-256,-1] range */ 834 addq $-0x80,(%rsp) /* Adjust vector to [-256,-1] range */
835 interrupt do_IRQ 835 interrupt do_IRQ
836 /* 0(%rsp): oldrsp-ARGOFFSET */ 836 /* 0(%rsp): old_rsp-ARGOFFSET */
837ret_from_intr: 837ret_from_intr:
838 DISABLE_INTERRUPTS(CLBR_NONE) 838 DISABLE_INTERRUPTS(CLBR_NONE)
839 TRACE_IRQS_OFF 839 TRACE_IRQS_OFF
diff --git a/arch/x86/kernel/process_64.c b/arch/x86/kernel/process_64.c
index 6c5f57602108..480128918926 100644
--- a/arch/x86/kernel/process_64.c
+++ b/arch/x86/kernel/process_64.c
@@ -60,6 +60,8 @@ asmlinkage extern void ret_from_fork(void);
60DEFINE_PER_CPU(struct task_struct *, current_task) = &init_task; 60DEFINE_PER_CPU(struct task_struct *, current_task) = &init_task;
61EXPORT_PER_CPU_SYMBOL(current_task); 61EXPORT_PER_CPU_SYMBOL(current_task);
62 62
63DEFINE_PER_CPU(unsigned long, old_rsp);
64
63unsigned long kernel_thread_flags = CLONE_VM | CLONE_UNTRACED; 65unsigned long kernel_thread_flags = CLONE_VM | CLONE_UNTRACED;
64 66
65static ATOMIC_NOTIFIER_HEAD(idle_notifier); 67static ATOMIC_NOTIFIER_HEAD(idle_notifier);
@@ -395,7 +397,7 @@ start_thread(struct pt_regs *regs, unsigned long new_ip, unsigned long new_sp)
395 load_gs_index(0); 397 load_gs_index(0);
396 regs->ip = new_ip; 398 regs->ip = new_ip;
397 regs->sp = new_sp; 399 regs->sp = new_sp;
398 write_pda(oldrsp, new_sp); 400 percpu_write(old_rsp, new_sp);
399 regs->cs = __USER_CS; 401 regs->cs = __USER_CS;
400 regs->ss = __USER_DS; 402 regs->ss = __USER_DS;
401 regs->flags = 0x200; 403 regs->flags = 0x200;
@@ -616,8 +618,8 @@ __switch_to(struct task_struct *prev_p, struct task_struct *next_p)
616 /* 618 /*
617 * Switch the PDA and FPU contexts. 619 * Switch the PDA and FPU contexts.
618 */ 620 */
619 prev->usersp = read_pda(oldrsp); 621 prev->usersp = percpu_read(old_rsp);
620 write_pda(oldrsp, next->usersp); 622 percpu_write(old_rsp, next->usersp);
621 percpu_write(current_task, next_p); 623 percpu_write(current_task, next_p);
622 624
623 percpu_write(kernel_stack, 625 percpu_write(kernel_stack,
diff --git a/arch/x86/xen/xen-asm_64.S b/arch/x86/xen/xen-asm_64.S
index 5a23e8993678..d6fc51f4ce85 100644
--- a/arch/x86/xen/xen-asm_64.S
+++ b/arch/x86/xen/xen-asm_64.S
@@ -194,11 +194,11 @@ RELOC(xen_sysexit, 1b+1)
194ENTRY(xen_sysret64) 194ENTRY(xen_sysret64)
195 /* We're already on the usermode stack at this point, but still 195 /* We're already on the usermode stack at this point, but still
196 with the kernel gs, so we can easily switch back */ 196 with the kernel gs, so we can easily switch back */
197 movq %rsp, %gs:pda_oldrsp 197 movq %rsp, PER_CPU_VAR(old_rsp)
198 movq PER_CPU_VAR(kernel_stack),%rsp 198 movq PER_CPU_VAR(kernel_stack),%rsp
199 199
200 pushq $__USER_DS 200 pushq $__USER_DS
201 pushq %gs:pda_oldrsp 201 pushq PER_CPU_VAR(old_rsp)
202 pushq %r11 202 pushq %r11
203 pushq $__USER_CS 203 pushq $__USER_CS
204 pushq %rcx 204 pushq %rcx
@@ -211,11 +211,11 @@ RELOC(xen_sysret64, 1b+1)
211ENTRY(xen_sysret32) 211ENTRY(xen_sysret32)
212 /* We're already on the usermode stack at this point, but still 212 /* We're already on the usermode stack at this point, but still
213 with the kernel gs, so we can easily switch back */ 213 with the kernel gs, so we can easily switch back */
214 movq %rsp, %gs:pda_oldrsp 214 movq %rsp, PER_CPU_VAR(old_rsp)
215 movq PER_CPU_VAR(kernel_stack), %rsp 215 movq PER_CPU_VAR(kernel_stack), %rsp
216 216
217 pushq $__USER32_DS 217 pushq $__USER32_DS
218 pushq %gs:pda_oldrsp 218 pushq PER_CPU_VAR(old_rsp)
219 pushq %r11 219 pushq %r11
220 pushq $__USER32_CS 220 pushq $__USER32_CS
221 pushq %rcx 221 pushq %rcx