diff options
author | Heiko Carstens <hca@linux.ibm.com> | 2024-02-03 11:45:07 +0100 |
---|---|---|
committer | Heiko Carstens <hca@linux.ibm.com> | 2024-02-16 14:30:15 +0100 |
commit | 3a5866a001e83e1aa143fc0aeba0248247483962 (patch) | |
tree | 9439898f3b6e59c909d28315e5af297b4817bc13 /arch/s390/kernel/fpu.c | |
parent | f4e3de75d0c4ebe9bbbfef19d7845ee70cb017bd (diff) |
s390/fpu: provide and use vlm and vstm inline assemblies
Instead of open-coding vlm and vstm inline assemblies at several locations,
provide an fpu_* function for each instruction, and use them in the new
save_vx_regs() and load_vx_regs() helper functions.
Note that "O" and "R" inline assembly operand modifiers are used in order
to pass the displacement and base register of the memory operands to the
existing VLM and VSTM macros. The two operand modifiers are not available
for clang. Therefore provide two variants of each inline assembly.
The clang variant always uses and clobbers general purpose register 1, like
in the previous inline assemblies, so it can be used as base register with
a zero displacement. This generates slightly less efficient code, but can
be removed as soon as clang has support for the used operand modifiers.
Reviewed-by: Claudio Imbrenda <imbrenda@linux.ibm.com>
Signed-off-by: Heiko Carstens <hca@linux.ibm.com>
Diffstat (limited to 'arch/s390/kernel/fpu.c')
-rw-r--r-- | arch/s390/kernel/fpu.c | 24 |
1 files changed, 6 insertions, 18 deletions
diff --git a/arch/s390/kernel/fpu.c b/arch/s390/kernel/fpu.c index 6bfd4d0f33e1..092a4bdf88ed 100644 --- a/arch/s390/kernel/fpu.c +++ b/arch/s390/kernel/fpu.c @@ -137,16 +137,10 @@ void __load_fpu_regs(void) void *regs = current->thread.fpu.regs; fpu_lfpc_safe(&state->fpc); - if (likely(cpu_has_vx())) { - asm volatile("lgr 1,%0\n" - "VLM 0,15,0,1\n" - "VLM 16,31,256,1\n" - : - : "d" (regs) - : "1", "cc", "memory"); - } else { + if (likely(cpu_has_vx())) + load_vx_regs(regs); + else load_fp_regs(regs); - } clear_cpu_flag(CIF_FPU); } @@ -173,16 +167,10 @@ void save_fpu_regs(void) regs = current->thread.fpu.regs; fpu_stfpc(&state->fpc); - if (likely(cpu_has_vx())) { - asm volatile("lgr 1,%0\n" - "VSTM 0,15,0,1\n" - "VSTM 16,31,256,1\n" - : - : "d" (regs) - : "1", "cc", "memory"); - } else { + if (likely(cpu_has_vx())) + save_vx_regs(regs); + else save_fp_regs(regs); - } set_cpu_flag(CIF_FPU); out: local_irq_restore(flags); |