Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

ARC: handle DSP presence in HW

When DSP extensions are present, some of the regular integer instructions
such as DIV, MACD etc are executed in the DSP unit with semantics alterable
by flags in DSP_CTRL aux register. This register is writable by userspace
and thus can potentially affect corresponding instructions in kernel code,
intentionally or otherwise. So safegaurd kernel by effectively disabling
DSP_CTRL upon bootup and every entry to kernel.

Do note that for this config we simply zero out the DSP_CTRL reg assuming
userspace doesn't really care about DSP. The next patch caters to the DSP
aware userspace where this reg is saved/restored upon kernel entry/exit.

Reviewed-by: Vineet Gupta <vgupta@synopsys.com>
Signed-off-by: Eugeniy Paltsev <Eugeniy.Paltsev@synopsys.com>
Signed-off-by: Vineet Gupta <vgupta@synopsys.com>

authored by

Eugeniy Paltsev and committed by
Vineet Gupta
4827d0cf 240c84b1

+104 -1
+28 -1
arch/arc/Kconfig
··· 401 401 default y 402 402 403 403 config ARC_HAS_ACCL_REGS 404 - bool "Reg Pair ACCL:ACCH (FPU and/or MPY > 6)" 404 + bool "Reg Pair ACCL:ACCH (FPU and/or MPY > 6 and/or DSP)" 405 405 default y 406 406 help 407 407 Depending on the configuration, CPU can contain accumulator reg-pair 408 408 (also referred to as r58:r59). These can also be used by gcc as GPR so 409 409 kernel needs to save/restore per process 410 + 411 + config ARC_DSP_HANDLED 412 + def_bool n 413 + 414 + choice 415 + prompt "DSP support" 416 + default ARC_DSP_NONE 417 + help 418 + Depending on the configuration, CPU can contain DSP registers 419 + (ACC0_GLO, ACC0_GHI, DSP_BFLY0, DSP_CTRL, DSP_FFT_CTRL). 420 + Bellow is options describing how to handle these registers in 421 + interrupt entry / exit and in context switch. 422 + 423 + config ARC_DSP_NONE 424 + bool "No DSP extension presence in HW" 425 + help 426 + No DSP extension presence in HW 427 + 428 + config ARC_DSP_KERNEL 429 + bool "DSP extension in HW, no support for userspace" 430 + select ARC_HAS_ACCL_REGS 431 + select ARC_DSP_HANDLED 432 + help 433 + DSP extension presence in HW, no support for DSP-enabled userspace 434 + applications. We don't save / restore DSP registers and only do 435 + some minimal preparations so userspace won't be able to break kernel 436 + endchoice 410 437 411 438 config ARC_IRQ_NO_AUTOSAVE 412 439 bool "Disable hardware autosave regfile on interrupts"
+12
arch/arc/include/asm/arcregs.h
··· 118 118 #define ARC_AUX_DPFP_2H 0x304 119 119 #define ARC_AUX_DPFP_STAT 0x305 120 120 121 + /* 122 + * DSP-related registers 123 + */ 124 + #define ARC_AUX_DSP_BUILD 0x7A 125 + #define ARC_AUX_ACC0_LO 0x580 126 + #define ARC_AUX_ACC0_GLO 0x581 127 + #define ARC_AUX_ACC0_HI 0x582 128 + #define ARC_AUX_ACC0_GHI 0x583 129 + #define ARC_AUX_DSP_BFLY0 0x598 130 + #define ARC_AUX_DSP_CTRL 0x59F 131 + #define ARC_AUX_DSP_FFT_CTRL 0x59E 132 + 121 133 #ifndef __ASSEMBLY__ 122 134 123 135 #include <soc/arc/aux.h>
+54
arch/arc/include/asm/dsp-impl.h
··· 1 + /* SPDX-License-Identifier: GPL-2.0-only */ 2 + /* 3 + * Copyright (C) 2020 Synopsys, Inc. (www.synopsys.com) 4 + * 5 + * Author: Eugeniy Paltsev <Eugeniy.Paltsev@synopsys.com> 6 + */ 7 + #ifndef __ASM_ARC_DSP_IMPL_H 8 + #define __ASM_ARC_DSP_IMPL_H 9 + 10 + #define DSP_CTRL_DISABLED_ALL 0 11 + 12 + #ifdef __ASSEMBLY__ 13 + 14 + /* clobbers r5 register */ 15 + .macro DSP_EARLY_INIT 16 + lr r5, [ARC_AUX_DSP_BUILD] 17 + bmsk r5, r5, 7 18 + breq r5, 0, 1f 19 + mov r5, DSP_CTRL_DISABLED_ALL 20 + sr r5, [ARC_AUX_DSP_CTRL] 21 + 1: 22 + .endm 23 + 24 + /* clobbers r10, r11 registers pair */ 25 + .macro DSP_SAVE_REGFILE_IRQ 26 + #if defined(CONFIG_ARC_DSP_KERNEL) 27 + /* 28 + * Drop any changes to DSP_CTRL made by userspace so userspace won't be 29 + * able to break kernel - reset it to DSP_CTRL_DISABLED_ALL value 30 + */ 31 + mov r10, DSP_CTRL_DISABLED_ALL 32 + sr r10, [ARC_AUX_DSP_CTRL] 33 + #endif /* ARC_DSP_KERNEL */ 34 + .endm 35 + 36 + #else /* __ASEMBLY__ */ 37 + 38 + #include <asm/asserts.h> 39 + 40 + static inline bool dsp_exist(void) 41 + { 42 + struct bcr_generic bcr; 43 + 44 + READ_BCR(ARC_AUX_DSP_BUILD, bcr); 45 + return !!bcr.ver; 46 + } 47 + 48 + static inline void dsp_config_check(void) 49 + { 50 + CHK_OPT_STRICT(CONFIG_ARC_DSP_HANDLED, dsp_exist()); 51 + } 52 + 53 + #endif /* __ASEMBLY__ */ 54 + #endif /* __ASM_ARC_DSP_IMPL_H */
+3
arch/arc/include/asm/entry-arcv2.h
··· 4 4 #define __ASM_ARC_ENTRY_ARCV2_H 5 5 6 6 #include <asm/asm-offsets.h> 7 + #include <asm/dsp-impl.h> 7 8 #include <asm/irqflags-arcv2.h> 8 9 #include <asm/thread_info.h> /* For THREAD_SIZE */ 9 10 ··· 166 165 ST2 r58, r59, PT_r58 167 166 #endif 168 167 168 + /* clobbers r10, r11 registers pair */ 169 + DSP_SAVE_REGFILE_IRQ 169 170 .endm 170 171 171 172 /*------------------------------------------------------------------------*/
+4
arch/arc/kernel/head.S
··· 14 14 #include <asm/entry.h> 15 15 #include <asm/arcregs.h> 16 16 #include <asm/cache.h> 17 + #include <asm/dsp-impl.h> 17 18 #include <asm/irqflags.h> 18 19 19 20 .macro CPU_EARLY_SETUP ··· 60 59 #endif 61 60 kflag r5 62 61 #endif 62 + ; Config DSP_CTRL properly, so kernel may use integer multiply, 63 + ; multiply-accumulate, and divide operations 64 + DSP_EARLY_INIT 63 65 .endm 64 66 65 67 .section .init.text, "ax",@progbits
+3
arch/arc/kernel/setup.c
··· 27 27 #include <asm/unwind.h> 28 28 #include <asm/mach_desc.h> 29 29 #include <asm/smp.h> 30 + #include <asm/dsp-impl.h> 30 31 31 32 #define FIX_PTR(x) __asm__ __volatile__(";" : "+r"(x)) 32 33 ··· 441 440 /* Accumulator Low:High pair (r58:59) present if DSP MPY or FPU */ 442 441 present = cpu->extn_mpy.dsp | cpu->extn.fpu_sp | cpu->extn.fpu_dp; 443 442 CHK_OPT_STRICT(CONFIG_ARC_HAS_ACCL_REGS, present); 443 + 444 + dsp_config_check(); 444 445 } 445 446 } 446 447