aboutsummaryrefslogtreecommitdiffstats
path: root/arch
diff options
context:
space:
mode:
authorNicolas Pitre <nico@org.rmk.(none)>2005-05-05 18:24:45 -0400
committerRussell King <rmk+kernel@arm.linux.org.uk>2005-05-05 18:24:45 -0400
commit4b0e07a5566a4e3f141e52c1f17e683e4a5bba91 (patch)
tree4a2f67e6cb6ea665c6d45529a5b7c61ac255663d /arch
parentf7e68bbf405a45d6e7c5b8fc384ff1ba20dd7aa4 (diff)
[PATCH] ARM: 2663/1: straightify TLS register emulation a bit more
Patch from Nicolas Pitre This better express things, and should cover RMK's weird SMP toys. Signed-off-by: Nicolas Pitre Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
Diffstat (limited to 'arch')
-rw-r--r--arch/arm/kernel/entry-armv.S10
-rw-r--r--arch/arm/kernel/traps.c11
-rw-r--r--arch/arm/mm/Kconfig24
3 files changed, 25 insertions, 20 deletions
diff --git a/arch/arm/kernel/entry-armv.S b/arch/arm/kernel/entry-armv.S
index 080df907f242..c6af1a03e081 100644
--- a/arch/arm/kernel/entry-armv.S
+++ b/arch/arm/kernel/entry-armv.S
@@ -505,9 +505,9 @@ ENTRY(__switch_to)
505 mra r4, r5, acc0 505 mra r4, r5, acc0
506 stmia ip, {r4, r5} 506 stmia ip, {r4, r5}
507#endif 507#endif
508#ifdef CONFIG_HAS_TLS_REG 508#if defined(CONFIG_HAS_TLS_REG)
509 mcr p15, 0, r3, c13, c0, 3 @ set TLS register 509 mcr p15, 0, r3, c13, c0, 3 @ set TLS register
510#else 510#elif !defined(CONFIG_TLS_REG_EMUL)
511 mov r4, #0xffff0fff 511 mov r4, #0xffff0fff
512 str r3, [r4, #-15] @ TLS val at 0xffff0ff0 512 str r3, [r4, #-15] @ TLS val at 0xffff0ff0
513#endif 513#endif
@@ -690,11 +690,7 @@ __kuser_cmpxchg: @ 0xffff0fc0
690 690
691__kuser_get_tls: @ 0xffff0fe0 691__kuser_get_tls: @ 0xffff0fe0
692 692
693#ifndef CONFIG_HAS_TLS_REG 693#if !defined(CONFIG_HAS_TLS_REG) && !defined(CONFIG_TLS_REG_EMUL)
694
695#ifdef CONFIG_SMP /* sanity check */
696#error "CONFIG_SMP without CONFIG_HAS_TLS_REG is wrong"
697#endif
698 694
699 ldr r0, [pc, #(16 - 8)] @ TLS stored at 0xffff0ff0 695 ldr r0, [pc, #(16 - 8)] @ TLS stored at 0xffff0ff0
700 mov pc, lr 696 mov pc, lr
diff --git a/arch/arm/kernel/traps.c b/arch/arm/kernel/traps.c
index 8988c02119fd..14df16b983f4 100644
--- a/arch/arm/kernel/traps.c
+++ b/arch/arm/kernel/traps.c
@@ -451,9 +451,9 @@ asmlinkage int arm_syscall(int no, struct pt_regs *regs)
451 451
452 case NR(set_tls): 452 case NR(set_tls):
453 thread->tp_value = regs->ARM_r0; 453 thread->tp_value = regs->ARM_r0;
454#ifdef CONFIG_HAS_TLS_REG 454#if defined(CONFIG_HAS_TLS_REG)
455 asm ("mcr p15, 0, %0, c13, c0, 3" : : "r" (regs->ARM_r0) ); 455 asm ("mcr p15, 0, %0, c13, c0, 3" : : "r" (regs->ARM_r0) );
456#else 456#elif !defined(CONFIG_TLS_REG_EMUL)
457 /* 457 /*
458 * User space must never try to access this directly. 458 * User space must never try to access this directly.
459 * Expect your app to break eventually if you do so. 459 * Expect your app to break eventually if you do so.
@@ -498,11 +498,14 @@ asmlinkage int arm_syscall(int no, struct pt_regs *regs)
498 return 0; 498 return 0;
499} 499}
500 500
501#if defined(CONFIG_CPU_32v6) && !defined(CONFIG_HAS_TLS_REG) 501#ifdef CONFIG_TLS_REG_EMUL
502 502
503/* 503/*
504 * We might be running on an ARMv6+ processor which should have the TLS 504 * We might be running on an ARMv6+ processor which should have the TLS
505 * register, but for some reason we can't use it and have to emulate it. 505 * register but for some reason we can't use it, or maybe an SMP system
506 * using a pre-ARMv6 processor (there are apparently a few prototypes like
507 * that in existence) and therefore access to that register must be
508 * emulated.
506 */ 509 */
507 510
508static int get_tp_trap(struct pt_regs *regs, unsigned int instr) 511static int get_tp_trap(struct pt_regs *regs, unsigned int instr)
diff --git a/arch/arm/mm/Kconfig b/arch/arm/mm/Kconfig
index 27892e34b060..c4fc6be629de 100644
--- a/arch/arm/mm/Kconfig
+++ b/arch/arm/mm/Kconfig
@@ -410,17 +410,23 @@ config CPU_BPREDICT_DISABLE
410 help 410 help
411 Say Y here to disable branch prediction. If unsure, say N. 411 Say Y here to disable branch prediction. If unsure, say N.
412 412
413config TLS_REG_EMUL
414 bool
415 default y if (SMP || CPU_32v6) && (CPU_32v5 || CPU_32v4 || CPU_32v3)
416 help
417 We might be running on an ARMv6+ processor which should have the TLS
418 register but for some reason we can't use it, or maybe an SMP system
419 using a pre-ARMv6 processor (there are apparently a few prototypes
420 like that in existence) and therefore access to that register must
421 be emulated.
422
413config HAS_TLS_REG 423config HAS_TLS_REG
414 bool 424 bool
415 depends on CPU_32v6 && !CPU_32v5 && !CPU_32v4 && !CPU_32v3 425 depends on CPU_32v6
416 default y 426 default y if !TLS_REG_EMUL
417 help 427 help
418 This selects support for the CP15 thread register. 428 This selects support for the CP15 thread register.
419 It is defined to be available on ARMv6 or later. However 429 It is defined to be available on ARMv6 or later. If a particular
420 if the kernel is configured to support multiple CPUs including 430 ARMv6 or later CPU doesn't support it then it must omc;ide "select
421 a pre-ARMv6 processors, or if a given ARMv6 processor doesn't 431 TLS_REG_EMUL" along with its other caracteristics.
422 implement the thread register for some reason, then access to
423 this register from user space must be trapped and emulated.
424 If user space is relying on the __kuser_get_tls code then
425 there should not be any impact.
426 432