diff options
author | Kim Phillips <kim.phillips@freescale.com> | 2006-12-08 03:43:30 -0500 |
---|---|---|
committer | Kumar Gala <galak@kernel.crashing.org> | 2006-12-08 03:43:30 -0500 |
commit | aa42c69c67f82e88f0726258efe7306708e1cf14 (patch) | |
tree | d5305de3285d504e1bd1e955155e5e06b5b9ef76 /arch | |
parent | c99767974ebd2a719d849fdeaaa1674456f5283f (diff) |
[POWERPC] Add support for FP emulation for the e300c2 core
The e300c2 has no FPU. Its MSR[FP] is grounded to zero. If an attempt
is made to execute a floating point instruction (including floating-point
load, store, or move instructions), the e300c2 takes a floating-point
unavailable interrupt.
This patch adds support for FP emulation on the e300c2 by declaring a
new CPU_FTR_FP_TAKES_FPUNAVAIL, where FP unavail interrupts are
intercepted and redirected to the ProgramCheck exception path for
correct emulation handling.
(If we run out of CPU_FTR bits we could look to reclaim this bit by adding
support to test the cpu_user_features for PPC_FEATURE_HAS_FPU instead)
It adds a nop to the exception path for 32-bit processors with a FPU.
Signed-off-by: Kim Phillips <kim.phillips@freescale.com>
Signed-off-by: Kumar Gala <galak@kernel.crashing.org>
Diffstat (limited to 'arch')
-rw-r--r-- | arch/powerpc/Kconfig | 2 | ||||
-rw-r--r-- | arch/powerpc/kernel/cputable.c | 2 | ||||
-rw-r--r-- | arch/powerpc/kernel/head_32.S | 7 | ||||
-rw-r--r-- | arch/powerpc/kernel/traps.c | 2 |
4 files changed, 11 insertions, 2 deletions
diff --git a/arch/powerpc/Kconfig b/arch/powerpc/Kconfig index 291c95ac4b31..0b2d05da89d7 100644 --- a/arch/powerpc/Kconfig +++ b/arch/powerpc/Kconfig | |||
@@ -706,7 +706,7 @@ config FORCE_MAX_ZONEORDER | |||
706 | 706 | ||
707 | config MATH_EMULATION | 707 | config MATH_EMULATION |
708 | bool "Math emulation" | 708 | bool "Math emulation" |
709 | depends on 4xx || 8xx || E200 || E500 | 709 | depends on 4xx || 8xx || E200 || PPC_83xx || E500 |
710 | ---help--- | 710 | ---help--- |
711 | Some PowerPC chips designed for embedded applications do not have | 711 | Some PowerPC chips designed for embedded applications do not have |
712 | a floating-point unit and therefore do not implement the | 712 | a floating-point unit and therefore do not implement the |
diff --git a/arch/powerpc/kernel/cputable.c b/arch/powerpc/kernel/cputable.c index 9d1614c3ce67..11bfbaf655b5 100644 --- a/arch/powerpc/kernel/cputable.c +++ b/arch/powerpc/kernel/cputable.c | |||
@@ -833,7 +833,7 @@ static struct cpu_spec cpu_specs[] = { | |||
833 | .pvr_mask = 0x7fff0000, | 833 | .pvr_mask = 0x7fff0000, |
834 | .pvr_value = 0x00840000, | 834 | .pvr_value = 0x00840000, |
835 | .cpu_name = "e300c2", | 835 | .cpu_name = "e300c2", |
836 | .cpu_features = CPU_FTRS_E300, | 836 | .cpu_features = CPU_FTRS_E300C2, |
837 | .cpu_user_features = PPC_FEATURE_32 | PPC_FEATURE_HAS_MMU, | 837 | .cpu_user_features = PPC_FEATURE_32 | PPC_FEATURE_HAS_MMU, |
838 | .icache_bsize = 32, | 838 | .icache_bsize = 32, |
839 | .dcache_bsize = 32, | 839 | .dcache_bsize = 32, |
diff --git a/arch/powerpc/kernel/head_32.S b/arch/powerpc/kernel/head_32.S index d88e182e40b3..9417cf5b4b7e 100644 --- a/arch/powerpc/kernel/head_32.S +++ b/arch/powerpc/kernel/head_32.S | |||
@@ -437,6 +437,13 @@ Alignment: | |||
437 | /* Floating-point unavailable */ | 437 | /* Floating-point unavailable */ |
438 | . = 0x800 | 438 | . = 0x800 |
439 | FPUnavailable: | 439 | FPUnavailable: |
440 | BEGIN_FTR_SECTION | ||
441 | /* | ||
442 | * Certain Freescale cores don't have a FPU and treat fp instructions | ||
443 | * as a FP Unavailable exception. Redirect to illegal/emulation handling. | ||
444 | */ | ||
445 | b ProgramCheck | ||
446 | END_FTR_SECTION_IFSET(CPU_FTR_FPU_UNAVAILABLE) | ||
440 | EXCEPTION_PROLOG | 447 | EXCEPTION_PROLOG |
441 | bne load_up_fpu /* if from user, just load it up */ | 448 | bne load_up_fpu /* if from user, just load it up */ |
442 | addi r3,r1,STACK_FRAME_OVERHEAD | 449 | addi r3,r1,STACK_FRAME_OVERHEAD |
diff --git a/arch/powerpc/kernel/traps.c b/arch/powerpc/kernel/traps.c index 0d4e203fa7a0..fde820e52d03 100644 --- a/arch/powerpc/kernel/traps.c +++ b/arch/powerpc/kernel/traps.c | |||
@@ -782,6 +782,8 @@ void __kprobes program_check_exception(struct pt_regs *regs) | |||
782 | unsigned int reason = get_reason(regs); | 782 | unsigned int reason = get_reason(regs); |
783 | extern int do_mathemu(struct pt_regs *regs); | 783 | extern int do_mathemu(struct pt_regs *regs); |
784 | 784 | ||
785 | /* We can now get here via a FP Unavailable exception if the core | ||
786 | * has no FPU, in that case no reason flags will be set */ | ||
785 | #ifdef CONFIG_MATH_EMULATION | 787 | #ifdef CONFIG_MATH_EMULATION |
786 | /* (reason & REASON_ILLEGAL) would be the obvious thing here, | 788 | /* (reason & REASON_ILLEGAL) would be the obvious thing here, |
787 | * but there seems to be a hardware bug on the 405GP (RevD) | 789 | * but there seems to be a hardware bug on the 405GP (RevD) |