aboutsummaryrefslogtreecommitdiffstats
path: root/arch/x86/include/asm/xsave.h
diff options
context:
space:
mode:
authorJonathan Herman <hermanjl@cs.unc.edu>2013-01-17 16:15:55 -0500
committerJonathan Herman <hermanjl@cs.unc.edu>2013-01-17 16:15:55 -0500
commit8dea78da5cee153b8af9c07a2745f6c55057fe12 (patch)
treea8f4d49d63b1ecc92f2fddceba0655b2472c5bd9 /arch/x86/include/asm/xsave.h
parent406089d01562f1e2bf9f089fd7637009ebaad589 (diff)
Patched in Tegra support.
Diffstat (limited to 'arch/x86/include/asm/xsave.h')
-rw-r--r--arch/x86/include/asm/xsave.h33
1 files changed, 22 insertions, 11 deletions
diff --git a/arch/x86/include/asm/xsave.h b/arch/x86/include/asm/xsave.h
index 0415cdabb5a..c6ce2452f10 100644
--- a/arch/x86/include/asm/xsave.h
+++ b/arch/x86/include/asm/xsave.h
@@ -34,14 +34,17 @@
34extern unsigned int xstate_size; 34extern unsigned int xstate_size;
35extern u64 pcntxt_mask; 35extern u64 pcntxt_mask;
36extern u64 xstate_fx_sw_bytes[USER_XSTATE_FX_SW_WORDS]; 36extern u64 xstate_fx_sw_bytes[USER_XSTATE_FX_SW_WORDS];
37extern struct xsave_struct *init_xstate_buf;
38 37
39extern void xsave_init(void); 38extern void xsave_init(void);
40extern void update_regset_xstate_info(unsigned int size, u64 xstate_mask); 39extern void update_regset_xstate_info(unsigned int size, u64 xstate_mask);
41extern int init_fpu(struct task_struct *child); 40extern int init_fpu(struct task_struct *child);
41extern int check_for_xstate(struct i387_fxsave_struct __user *buf,
42 void __user *fpstate,
43 struct _fpx_sw_bytes *sw);
42 44
43static inline int fpu_xrstor_checking(struct xsave_struct *fx) 45static inline int fpu_xrstor_checking(struct fpu *fpu)
44{ 46{
47 struct xsave_struct *fx = &fpu->state->xsave;
45 int err; 48 int err;
46 49
47 asm volatile("1: .byte " REX_PREFIX "0x0f,0xae,0x2f\n\t" 50 asm volatile("1: .byte " REX_PREFIX "0x0f,0xae,0x2f\n\t"
@@ -66,21 +69,27 @@ static inline int xsave_user(struct xsave_struct __user *buf)
66 * Clear the xsave header first, so that reserved fields are 69 * Clear the xsave header first, so that reserved fields are
67 * initialized to zero. 70 * initialized to zero.
68 */ 71 */
69 err = __clear_user(&buf->xsave_hdr, sizeof(buf->xsave_hdr)); 72 err = __clear_user(&buf->xsave_hdr,
73 sizeof(struct xsave_hdr_struct));
70 if (unlikely(err)) 74 if (unlikely(err))
71 return -EFAULT; 75 return -EFAULT;
72 76
73 __asm__ __volatile__(ASM_STAC "\n" 77 __asm__ __volatile__("1: .byte " REX_PREFIX "0x0f,0xae,0x27\n"
74 "1: .byte " REX_PREFIX "0x0f,0xae,0x27\n" 78 "2:\n"
75 "2: " ASM_CLAC "\n"
76 ".section .fixup,\"ax\"\n" 79 ".section .fixup,\"ax\"\n"
77 "3: movl $-1,%[err]\n" 80 "3: movl $-1,%[err]\n"
78 " jmp 2b\n" 81 " jmp 2b\n"
79 ".previous\n" 82 ".previous\n"
80 _ASM_EXTABLE(1b,3b) 83 ".section __ex_table,\"a\"\n"
84 _ASM_ALIGN "\n"
85 _ASM_PTR "1b,3b\n"
86 ".previous"
81 : [err] "=r" (err) 87 : [err] "=r" (err)
82 : "D" (buf), "a" (-1), "d" (-1), "0" (0) 88 : "D" (buf), "a" (-1), "d" (-1), "0" (0)
83 : "memory"); 89 : "memory");
90 if (unlikely(err) && __clear_user(buf, xstate_size))
91 err = -EFAULT;
92 /* No need to clear here because the caller clears USED_MATH */
84 return err; 93 return err;
85} 94}
86 95
@@ -91,14 +100,16 @@ static inline int xrestore_user(struct xsave_struct __user *buf, u64 mask)
91 u32 lmask = mask; 100 u32 lmask = mask;
92 u32 hmask = mask >> 32; 101 u32 hmask = mask >> 32;
93 102
94 __asm__ __volatile__(ASM_STAC "\n" 103 __asm__ __volatile__("1: .byte " REX_PREFIX "0x0f,0xae,0x2f\n"
95 "1: .byte " REX_PREFIX "0x0f,0xae,0x2f\n" 104 "2:\n"
96 "2: " ASM_CLAC "\n"
97 ".section .fixup,\"ax\"\n" 105 ".section .fixup,\"ax\"\n"
98 "3: movl $-1,%[err]\n" 106 "3: movl $-1,%[err]\n"
99 " jmp 2b\n" 107 " jmp 2b\n"
100 ".previous\n" 108 ".previous\n"
101 _ASM_EXTABLE(1b,3b) 109 ".section __ex_table,\"a\"\n"
110 _ASM_ALIGN "\n"
111 _ASM_PTR "1b,3b\n"
112 ".previous"
102 : [err] "=r" (err) 113 : [err] "=r" (err)
103 : "D" (xstate), "a" (lmask), "d" (hmask), "0" (0) 114 : "D" (xstate), "a" (lmask), "d" (hmask), "0" (0)
104 : "memory"); /* memory required? */ 115 : "memory"); /* memory required? */