Linux-libre 5.4.48-gnu
[librecmc/linux-libre.git] / arch / sparc / lib / bzero.S
1 /* SPDX-License-Identifier: GPL-2.0 */
2 /* bzero.S: Simple prefetching memset, bzero, and clear_user
3  *          implementations.
4  *
5  * Copyright (C) 2005 David S. Miller <davem@davemloft.net>
6  */
7
8 #include <linux/linkage.h>
9 #include <asm/export.h>
10
11         .text
12
13 ENTRY(memset) /* %o0=buf, %o1=pat, %o2=len */
14         and             %o1, 0xff, %o3
15         mov             %o2, %o1
16         sllx            %o3, 8, %g1
17         or              %g1, %o3, %o2
18         sllx            %o2, 16, %g1
19         or              %g1, %o2, %o2
20         sllx            %o2, 32, %g1
21         ba,pt           %xcc, 1f
22          or             %g1, %o2, %o2
23
24 ENTRY(__bzero) /* %o0=buf, %o1=len */
25         clr             %o2
26 1:      mov             %o0, %o3
27         brz,pn          %o1, __bzero_done
28          cmp            %o1, 16
29         bl,pn           %icc, __bzero_tiny
30          prefetch       [%o0 + 0x000], #n_writes
31         andcc           %o0, 0x3, %g0
32         be,pt           %icc, 2f
33 1:       stb            %o2, [%o0 + 0x00]
34         add             %o0, 1, %o0
35         andcc           %o0, 0x3, %g0
36         bne,pn          %icc, 1b
37          sub            %o1, 1, %o1
38 2:      andcc           %o0, 0x7, %g0
39         be,pt           %icc, 3f
40          stw            %o2, [%o0 + 0x00]
41         sub             %o1, 4, %o1
42         add             %o0, 4, %o0
43 3:      and             %o1, 0x38, %g1
44         cmp             %o1, 0x40
45         andn            %o1, 0x3f, %o4
46         bl,pn           %icc, 5f
47          and            %o1, 0x7, %o1
48         prefetch        [%o0 + 0x040], #n_writes
49         prefetch        [%o0 + 0x080], #n_writes
50         prefetch        [%o0 + 0x0c0], #n_writes
51         prefetch        [%o0 + 0x100], #n_writes
52         prefetch        [%o0 + 0x140], #n_writes
53 4:      prefetch        [%o0 + 0x180], #n_writes
54         stx             %o2, [%o0 + 0x00]
55         stx             %o2, [%o0 + 0x08]
56         stx             %o2, [%o0 + 0x10]
57         stx             %o2, [%o0 + 0x18]
58         stx             %o2, [%o0 + 0x20]
59         stx             %o2, [%o0 + 0x28]
60         stx             %o2, [%o0 + 0x30]
61         stx             %o2, [%o0 + 0x38]
62         subcc           %o4, 0x40, %o4
63         bne,pt          %icc, 4b
64          add            %o0, 0x40, %o0
65         brz,pn          %g1, 6f
66          nop
67 5:      stx             %o2, [%o0 + 0x00]
68         subcc           %g1, 8, %g1
69         bne,pt          %icc, 5b
70          add            %o0, 0x8, %o0
71 6:      brz,pt          %o1, __bzero_done
72          nop
73 __bzero_tiny:
74 1:      stb             %o2, [%o0 + 0x00]
75         subcc           %o1, 1, %o1
76         bne,pt          %icc, 1b
77          add            %o0, 1, %o0
78 __bzero_done:
79         retl
80          mov            %o3, %o0
81 ENDPROC(__bzero)
82 ENDPROC(memset)
83 EXPORT_SYMBOL(__bzero)
84 EXPORT_SYMBOL(memset)
85
86 #define EX_ST(x,y)              \
87 98:     x,y;                    \
88         .section __ex_table,"a";\
89         .align 4;               \
90         .word 98b, __retl_o1;   \
91         .text;                  \
92         .align 4;
93
94 ENTRY(__clear_user) /* %o0=buf, %o1=len */
95         brz,pn          %o1, __clear_user_done
96          cmp            %o1, 16
97         bl,pn           %icc, __clear_user_tiny
98          EX_ST(prefetcha [%o0 + 0x00] %asi, #n_writes)
99         andcc           %o0, 0x3, %g0
100         be,pt           %icc, 2f
101 1:       EX_ST(stba     %g0, [%o0 + 0x00] %asi)
102         add             %o0, 1, %o0
103         andcc           %o0, 0x3, %g0
104         bne,pn          %icc, 1b
105          sub            %o1, 1, %o1
106 2:      andcc           %o0, 0x7, %g0
107         be,pt           %icc, 3f
108          EX_ST(stwa     %g0, [%o0 + 0x00] %asi)
109         sub             %o1, 4, %o1
110         add             %o0, 4, %o0
111 3:      and             %o1, 0x38, %g1
112         cmp             %o1, 0x40
113         andn            %o1, 0x3f, %o4
114         bl,pn           %icc, 5f
115          and            %o1, 0x7, %o1
116         EX_ST(prefetcha [%o0 + 0x040] %asi, #n_writes)
117         EX_ST(prefetcha [%o0 + 0x080] %asi, #n_writes)
118         EX_ST(prefetcha [%o0 + 0x0c0] %asi, #n_writes)
119         EX_ST(prefetcha [%o0 + 0x100] %asi, #n_writes)
120         EX_ST(prefetcha [%o0 + 0x140] %asi, #n_writes)
121 4:      EX_ST(prefetcha [%o0 + 0x180] %asi, #n_writes)
122         EX_ST(stxa      %g0, [%o0 + 0x00] %asi)
123         EX_ST(stxa      %g0, [%o0 + 0x08] %asi)
124         EX_ST(stxa      %g0, [%o0 + 0x10] %asi)
125         EX_ST(stxa      %g0, [%o0 + 0x18] %asi)
126         EX_ST(stxa      %g0, [%o0 + 0x20] %asi)
127         EX_ST(stxa      %g0, [%o0 + 0x28] %asi)
128         EX_ST(stxa      %g0, [%o0 + 0x30] %asi)
129         EX_ST(stxa      %g0, [%o0 + 0x38] %asi)
130         subcc           %o4, 0x40, %o4
131         bne,pt          %icc, 4b
132          add            %o0, 0x40, %o0
133         brz,pn          %g1, 6f
134          nop
135 5:      EX_ST(stxa      %g0, [%o0 + 0x00] %asi)
136         subcc           %g1, 8, %g1
137         bne,pt          %icc, 5b
138          add            %o0, 0x8, %o0
139 6:      brz,pt          %o1, __clear_user_done
140          nop
141 __clear_user_tiny:
142 1:      EX_ST(stba      %g0, [%o0 + 0x00] %asi)
143         subcc           %o1, 1, %o1
144         bne,pt          %icc, 1b
145          add            %o0, 1, %o0
146 __clear_user_done:
147         retl
148          clr            %o0
149 ENDPROC(__clear_user)
150 EXPORT_SYMBOL(__clear_user)