在Linux内核中生成和优化文件中的FP/SIMD代码,其中包含KERNEL_FPU_BEGIN()? [英] Generate and optimize FP / SIMD code in the Linux Kernel on files which contains kernel_fpu_begin()?
本文介绍了在Linux内核中生成和优化文件中的FP/SIMD代码,其中包含KERNEL_FPU_BEGIN()?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!
问题描述
我知道禁止在内核中使用任何形式的浮点代码,我们永远不应该使用任何可能生成FP/SIMD指令的GCC标志,但一些使用kernel_fpu_begin()
和kernel_fpu_end()
的源代码(特别是arch/x86/crypto/*
)怎么办?
我有一个老式英特尔酷睿2双核CPU,用于我的64位Linux内核,并且在主要Makefile
中我使用以下C标志:
# Target specific Flags
KBUILD_CFLAGS +=
-m64
-march=core2
-mtune=core2
-mfpmath=sse
-msoft-float
-mno-fp-ret-in-387
-mno-mmx
-mno-sse
-mno-sse2
-mno-sse3
-mno-ssse3
# FPU Flags
FPU_CFLAGS := $(KBUILD_CFLAGS)
-mhard-float
-mfp-ret-in-387
-mmmx
-msse
-msse2
-msse3
-mssse3
-ftree-vectorize
在存在kernel_fpu_begin()
的文件中,我将FPU_CFLAGS
传递给它们的Makefiles
,如下所示:
CFLAGS_sha512_ssse3_glue.o := $(FPU_CFLAGS)
这是正确的吗?它会优化FP/SIMD代码吗?或者它是不需要的,并且这种实现甚至可能破坏FPU/SIMD的状态?
推荐答案
这样做正确吗
不,绝对不要这样做。这些选项告诉GCC,它可以在此编译单元中的任何位置使用SIMD/FP指令,包括之前kernel_fpu_begin()
或kernel_fpu_end()
之后,或者在从不调用kernel_fpu_begin()
的函数中。
例如,它可以发出movdqu
加载或存储来复制16字节的结构,并在kernel_fpu_begin
保存它之前corrupt user-space XMM register state。
不是,使用并将优化FP/SIMD代码?
kernel_fpu_begin()
的内核代码也使用内联ASM来运行SIMD指令。这将发出SIMD指令,而不需要编译器的任何帮助。
或者在理论上,一些内核代码可以使用类似__attribute__((target("sse2")))
的函数属性,或者类似于从kernel_fpu_begin()
/end
块内部调用的助手函数的属性。但我认为Linux更喜欢内联ASM,而不是内联ASM加上内部函数或自动向量化。
如果内核没有从中获得任何好处,则它不会费心包括kernel_fpu_begin()
/end
调用。顺便说一句,您可以反汇编相关的.ko
内核模块,并看到它们实际上包含使用XMM寄存器的SIMD指令。使用objdump -drwC -Mintel foo.ko
这篇关于在Linux内核中生成和优化文件中的FP/SIMD代码,其中包含KERNEL_FPU_BEGIN()?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!
查看全文