1dnl #
2dnl # Handle differences in kernel FPU code.
3dnl #
4dnl # Kernel
5dnl # 5.16:	XCR code put into asm/fpu/xcr.h
6dnl # 		HAVE_KERNEL_FPU_XCR_HEADER
7dnl #
8dnl # 5.0:	Wrappers have been introduced to save/restore the FPU state.
9dnl #		This change was made to the 4.19.38 and 4.14.120 LTS kernels.
10dnl #		HAVE_KERNEL_FPU_INTERNAL
11dnl #
12dnl # 4.2:	Use __kernel_fpu_{begin,end}()
13dnl #		HAVE_UNDERSCORE_KERNEL_FPU & KERNEL_EXPORTS_X86_FPU
14dnl #
15dnl # Pre-4.2:	Use kernel_fpu_{begin,end}()
16dnl #		HAVE_KERNEL_FPU & KERNEL_EXPORTS_X86_FPU
17dnl #
18dnl # N.B. The header check is performed before all other checks since it
19dnl # depends on HAVE_KERNEL_FPU_API_HEADER being set in confdefs.h.
20dnl #
21AC_DEFUN([ZFS_AC_KERNEL_FPU_HEADER], [
22	AC_MSG_CHECKING([whether fpu headers are available])
23	ZFS_LINUX_TRY_COMPILE([
24		#include <linux/module.h>
25		#include <asm/fpu/api.h>
26	],[
27	],[
28		AC_DEFINE(HAVE_KERNEL_FPU_API_HEADER, 1,
29		    [kernel has asm/fpu/api.h])
30		AC_MSG_RESULT(asm/fpu/api.h)
31		AC_MSG_CHECKING([whether fpu/xcr header is available])
32		ZFS_LINUX_TRY_COMPILE([
33			#include <linux/module.h>
34			#include <asm/fpu/xcr.h>
35		],[
36		],[
37			AC_DEFINE(HAVE_KERNEL_FPU_XCR_HEADER, 1,
38				[kernel has asm/fpu/xcr.h])
39			AC_MSG_RESULT(asm/fpu/xcr.h)
40		],[
41			AC_MSG_RESULT(no asm/fpu/xcr.h)
42		])
43	],[
44		AC_MSG_RESULT(i387.h & xcr.h)
45	])
46])
47
48AC_DEFUN([ZFS_AC_KERNEL_SRC_FPU], [
49	ZFS_LINUX_TEST_SRC([kernel_fpu], [
50		#include <linux/types.h>
51		#ifdef HAVE_KERNEL_FPU_API_HEADER
52		#include <asm/fpu/api.h>
53		#else
54		#include <asm/i387.h>
55		#include <asm/xcr.h>
56		#endif
57	], [
58		kernel_fpu_begin();
59		kernel_fpu_end();
60	], [], [ZFS_META_LICENSE])
61
62	ZFS_LINUX_TEST_SRC([__kernel_fpu], [
63		#include <linux/types.h>
64		#ifdef HAVE_KERNEL_FPU_API_HEADER
65		#include <asm/fpu/api.h>
66		#else
67		#include <asm/i387.h>
68		#include <asm/xcr.h>
69		#endif
70	], [
71		__kernel_fpu_begin();
72		__kernel_fpu_end();
73	], [], [ZFS_META_LICENSE])
74
75	ZFS_LINUX_TEST_SRC([fpu_internal], [
76		#if defined(__x86_64) || defined(__x86_64__) || \
77		    defined(__i386) || defined(__i386__)
78		#if !defined(__x86)
79		#define __x86
80		#endif
81		#endif
82
83		#if !defined(__x86)
84		#error Unsupported architecture
85		#endif
86
87		#include <linux/types.h>
88		#ifdef HAVE_KERNEL_FPU_API_HEADER
89		#include <asm/fpu/api.h>
90		#include <asm/fpu/internal.h>
91		#else
92		#include <asm/i387.h>
93		#include <asm/xcr.h>
94		#endif
95
96		#if !defined(XSTATE_XSAVE)
97		#error XSTATE_XSAVE not defined
98		#endif
99
100		#if !defined(XSTATE_XRESTORE)
101		#error XSTATE_XRESTORE not defined
102		#endif
103	],[
104		struct fpu *fpu = &current->thread.fpu;
105		union fpregs_state *st = &fpu->state;
106		struct fregs_state *fr __attribute__ ((unused)) = &st->fsave;
107		struct fxregs_state *fxr __attribute__ ((unused)) = &st->fxsave;
108		struct xregs_state *xr __attribute__ ((unused)) = &st->xsave;
109	])
110])
111
112AC_DEFUN([ZFS_AC_KERNEL_FPU], [
113	dnl #
114	dnl # Legacy kernel
115	dnl #
116	AC_MSG_CHECKING([whether kernel fpu is available])
117	ZFS_LINUX_TEST_RESULT_SYMBOL([kernel_fpu_license],
118	    [kernel_fpu_begin], [arch/x86/kernel/fpu/core.c], [
119		AC_MSG_RESULT(kernel_fpu_*)
120		AC_DEFINE(HAVE_KERNEL_FPU, 1,
121		    [kernel has kernel_fpu_* functions])
122		AC_DEFINE(KERNEL_EXPORTS_X86_FPU, 1,
123		    [kernel exports FPU functions])
124	],[
125		dnl #
126		dnl # Linux 4.2 kernel
127		dnl #
128		ZFS_LINUX_TEST_RESULT_SYMBOL([__kernel_fpu_license],
129		    [__kernel_fpu_begin],
130		    [arch/x86/kernel/fpu/core.c arch/x86/kernel/i387.c], [
131			AC_MSG_RESULT(__kernel_fpu_*)
132			AC_DEFINE(HAVE_UNDERSCORE_KERNEL_FPU, 1,
133			    [kernel has __kernel_fpu_* functions])
134			AC_DEFINE(KERNEL_EXPORTS_X86_FPU, 1,
135			    [kernel exports FPU functions])
136		],[
137			ZFS_LINUX_TEST_RESULT([fpu_internal], [
138				AC_MSG_RESULT(internal)
139				AC_DEFINE(HAVE_KERNEL_FPU_INTERNAL, 1,
140				    [kernel fpu internal])
141			],[
142				AC_MSG_RESULT(unavailable)
143			])
144		])
145	])
146])
147