Linux v2.6.13-rc3
[pohmelfs.git] / arch / x86_64 / lib / putuser.S
blob5828b8191667da13f3295034a685f474746ce3b2
1 /*
2  * __put_user functions.
3  *
4  * (C) Copyright 1998 Linus Torvalds
5  * (C) Copyright 2005 Andi Kleen
6  *
7  * These functions have a non-standard call interface
8  * to make them more efficient, especially as they
9  * return an error value in addition to the "real"
10  * return value.
11  */
14  * __put_user_X
15  *
16  * Inputs:      %rcx contains the address
17  *              %rdx contains new value
18  *
19  * Outputs:     %rax is error code (0 or -EFAULT)
20  *
21  * %r8 is destroyed.
22  *
23  * These functions should not modify any other registers,
24  * as they get called from within inline assembly.
25  */
27 #include <linux/linkage.h>
28 #include <asm/page.h>
29 #include <asm/errno.h>
30 #include <asm/offset.h>
31 #include <asm/thread_info.h>
33         .text
34         .p2align 4
35 .globl __put_user_1
36 __put_user_1:
37         GET_THREAD_INFO(%r8)
38         cmpq threadinfo_addr_limit(%r8),%rcx
39         jae bad_put_user
40 1:      movb %dl,(%rcx)
41         xorl %eax,%eax
42         ret
44         .p2align 4
45 .globl __put_user_2
46 __put_user_2:
47         GET_THREAD_INFO(%r8)
48         addq $1,%rcx
49         jc 20f
50         cmpq threadinfo_addr_limit(%r8),%rcx
51         jae 20f
52         decq %rcx
53 2:      movw %dx,(%rcx)
54         xorl %eax,%eax
55         ret
56 20:     decq %rcx
57         jmp bad_put_user
59         .p2align 4
60 .globl __put_user_4
61 __put_user_4:
62         GET_THREAD_INFO(%r8)
63         addq $3,%rcx
64         jc 30f
65         cmpq threadinfo_addr_limit(%r8),%rcx
66         jae 30f
67         subq $3,%rcx
68 3:      movl %edx,(%rcx)
69         xorl %eax,%eax
70         ret
71 30:     subq $3,%rcx
72         jmp bad_put_user
74         .p2align 4
75 .globl __put_user_8
76 __put_user_8:
77         GET_THREAD_INFO(%r8)
78         addq $7,%rcx
79         jc 40f
80         cmpq threadinfo_addr_limit(%r8),%rcx
81         jae 40f
82         subq $7,%rcx
83 4:      movq %rdx,(%rcx)
84         xorl %eax,%eax
85         ret
86 40:     subq $7,%rcx
87         jmp bad_put_user
89 bad_put_user:
90         movq $(-EFAULT),%rax
91         ret
93 .section __ex_table,"a"
94         .quad 1b,bad_put_user
95         .quad 2b,bad_put_user
96         .quad 3b,bad_put_user
97         .quad 4b,bad_put_user
98 .previous