diff options
Diffstat (limited to 'arch/x86/include/asm/uaccess.h')
-rw-r--r-- | arch/x86/include/asm/uaccess.h | 33 |
1 files changed, 26 insertions, 7 deletions
diff --git a/arch/x86/include/asm/uaccess.h b/arch/x86/include/asm/uaccess.h index 0ec6de4bcb0b..b685ece89d5c 100644 --- a/arch/x86/include/asm/uaccess.h +++ b/arch/x86/include/asm/uaccess.h | |||
@@ -186,7 +186,7 @@ extern int __get_user_bad(void); | |||
186 | 186 | ||
187 | 187 | ||
188 | #ifdef CONFIG_X86_32 | 188 | #ifdef CONFIG_X86_32 |
189 | #define __put_user_asm_u64(x, addr, err) \ | 189 | #define __put_user_asm_u64(x, addr, err, errret) \ |
190 | asm volatile("1: movl %%eax,0(%2)\n" \ | 190 | asm volatile("1: movl %%eax,0(%2)\n" \ |
191 | "2: movl %%edx,4(%2)\n" \ | 191 | "2: movl %%edx,4(%2)\n" \ |
192 | "3:\n" \ | 192 | "3:\n" \ |
@@ -197,7 +197,7 @@ extern int __get_user_bad(void); | |||
197 | _ASM_EXTABLE(1b, 4b) \ | 197 | _ASM_EXTABLE(1b, 4b) \ |
198 | _ASM_EXTABLE(2b, 4b) \ | 198 | _ASM_EXTABLE(2b, 4b) \ |
199 | : "=r" (err) \ | 199 | : "=r" (err) \ |
200 | : "A" (x), "r" (addr), "i" (-EFAULT), "0" (err)) | 200 | : "A" (x), "r" (addr), "i" (errret), "0" (err)) |
201 | 201 | ||
202 | #define __put_user_asm_ex_u64(x, addr) \ | 202 | #define __put_user_asm_ex_u64(x, addr) \ |
203 | asm volatile("1: movl %%eax,0(%1)\n" \ | 203 | asm volatile("1: movl %%eax,0(%1)\n" \ |
@@ -211,8 +211,8 @@ extern int __get_user_bad(void); | |||
211 | asm volatile("call __put_user_8" : "=a" (__ret_pu) \ | 211 | asm volatile("call __put_user_8" : "=a" (__ret_pu) \ |
212 | : "A" ((typeof(*(ptr)))(x)), "c" (ptr) : "ebx") | 212 | : "A" ((typeof(*(ptr)))(x)), "c" (ptr) : "ebx") |
213 | #else | 213 | #else |
214 | #define __put_user_asm_u64(x, ptr, retval) \ | 214 | #define __put_user_asm_u64(x, ptr, retval, errret) \ |
215 | __put_user_asm(x, ptr, retval, "q", "", "Zr", -EFAULT) | 215 | __put_user_asm(x, ptr, retval, "q", "", "Zr", errret) |
216 | #define __put_user_asm_ex_u64(x, addr) \ | 216 | #define __put_user_asm_ex_u64(x, addr) \ |
217 | __put_user_asm_ex(x, addr, "q", "", "Zr") | 217 | __put_user_asm_ex(x, addr, "q", "", "Zr") |
218 | #define __put_user_x8(x, ptr, __ret_pu) __put_user_x(8, x, ptr, __ret_pu) | 218 | #define __put_user_x8(x, ptr, __ret_pu) __put_user_x(8, x, ptr, __ret_pu) |
@@ -289,7 +289,8 @@ do { \ | |||
289 | __put_user_asm(x, ptr, retval, "l", "k", "ir", errret); \ | 289 | __put_user_asm(x, ptr, retval, "l", "k", "ir", errret); \ |
290 | break; \ | 290 | break; \ |
291 | case 8: \ | 291 | case 8: \ |
292 | __put_user_asm_u64((__typeof__(*ptr))(x), ptr, retval); \ | 292 | __put_user_asm_u64((__typeof__(*ptr))(x), ptr, retval, \ |
293 | errret); \ | ||
293 | break; \ | 294 | break; \ |
294 | default: \ | 295 | default: \ |
295 | __put_user_bad(); \ | 296 | __put_user_bad(); \ |
@@ -525,8 +526,6 @@ struct __large_struct { unsigned long buf[100]; }; | |||
525 | */ | 526 | */ |
526 | #define get_user_try uaccess_try | 527 | #define get_user_try uaccess_try |
527 | #define get_user_catch(err) uaccess_catch(err) | 528 | #define get_user_catch(err) uaccess_catch(err) |
528 | #define put_user_try uaccess_try | ||
529 | #define put_user_catch(err) uaccess_catch(err) | ||
530 | 529 | ||
531 | #define get_user_ex(x, ptr) do { \ | 530 | #define get_user_ex(x, ptr) do { \ |
532 | unsigned long __gue_val; \ | 531 | unsigned long __gue_val; \ |
@@ -534,9 +533,29 @@ struct __large_struct { unsigned long buf[100]; }; | |||
534 | (x) = (__force __typeof__(*(ptr)))__gue_val; \ | 533 | (x) = (__force __typeof__(*(ptr)))__gue_val; \ |
535 | } while (0) | 534 | } while (0) |
536 | 535 | ||
536 | #ifdef CONFIG_X86_WP_WORKS_OK | ||
537 | |||
538 | #define put_user_try uaccess_try | ||
539 | #define put_user_catch(err) uaccess_catch(err) | ||
540 | |||
537 | #define put_user_ex(x, ptr) \ | 541 | #define put_user_ex(x, ptr) \ |
538 | __put_user_size_ex((__typeof__(*(ptr)))(x), (ptr), sizeof(*(ptr))) | 542 | __put_user_size_ex((__typeof__(*(ptr)))(x), (ptr), sizeof(*(ptr))) |
539 | 543 | ||
544 | #else /* !CONFIG_X86_WP_WORKS_OK */ | ||
545 | |||
546 | #define put_user_try do { \ | ||
547 | int __uaccess_err = 0; | ||
548 | |||
549 | #define put_user_catch(err) \ | ||
550 | (err) |= __uaccess_err; \ | ||
551 | } while (0) | ||
552 | |||
553 | #define put_user_ex(x, ptr) do { \ | ||
554 | __uaccess_err |= __put_user(x, ptr); \ | ||
555 | } while (0) | ||
556 | |||
557 | #endif /* CONFIG_X86_WP_WORKS_OK */ | ||
558 | |||
540 | /* | 559 | /* |
541 | * movsl can be slow when source and dest are not both 8-byte aligned | 560 | * movsl can be slow when source and dest are not both 8-byte aligned |
542 | */ | 561 | */ |