1
2
3
4
5
6
7
8
9
10
11
12
13 #include <linux/linkage.h>
14 #include <asm/assembler.h>
15
16
17
18
19
20
21
22
23
24
25
26
27
28 #define REP8_01 0x0101010101010101
29 #define REP8_7f 0x7f7f7f7f7f7f7f7f
30 #define REP8_80 0x8080808080808080
31
32
33 src1 .req x0
34 src2 .req x1
35 result .req x0
36
37
38 data1 .req x2
39 data1w .req w2
40 data2 .req x3
41 data2w .req w3
42 has_nul .req x4
43 diff .req x5
44 syndrome .req x6
45 tmp1 .req x7
46 tmp2 .req x8
47 tmp3 .req x9
48 zeroones .req x10
49 pos .req x11
50
51 WEAK(strcmp)
52 eor tmp1, src1, src2
53 mov zeroones, #REP8_01
54 tst tmp1, #7
55 b.ne .Lmisaligned8
56 ands tmp1, src1, #7
57 b.ne .Lmutual_align
58
59
60
61
62
63
64 .Lloop_aligned:
65 ldr data1, [src1], #8
66 ldr data2, [src2], #8
67 .Lstart_realigned:
68 sub tmp1, data1, zeroones
69 orr tmp2, data1, #REP8_7f
70 eor diff, data1, data2
71 bic has_nul, tmp1, tmp2
72 orr syndrome, diff, has_nul
73 cbz syndrome, .Lloop_aligned
74 b .Lcal_cmpresult
75
76 .Lmutual_align:
77
78
79
80
81
82 bic src1, src1, #7
83 bic src2, src2, #7
84 lsl tmp1, tmp1, #3
85 ldr data1, [src1], #8
86 neg tmp1, tmp1
87 ldr data2, [src2], #8
88 mov tmp2, #~0
89
90 CPU_BE( lsl tmp2, tmp2, tmp1 )
91
92 CPU_LE( lsr tmp2, tmp2, tmp1 )
93
94 orr data1, data1, tmp2
95 orr data2, data2, tmp2
96 b .Lstart_realigned
97
98 .Lmisaligned8:
99
100
101
102
103 and tmp1, src1, #7
104 neg tmp1, tmp1
105 add tmp1, tmp1, #8
106 and tmp2, src2, #7
107 neg tmp2, tmp2
108 add tmp2, tmp2, #8
109 subs tmp3, tmp1, tmp2
110 csel pos, tmp1, tmp2, hi
111 .Ltinycmp:
112 ldrb data1w, [src1], #1
113 ldrb data2w, [src2], #1
114 subs pos, pos, #1
115 ccmp data1w, #1, #0, ne
116 ccmp data1w, data2w, #0, cs
117 b.eq .Ltinycmp
118 cbnz pos, 1f
119 cmp data1w, #1
120 ccmp data1w, data2w, #0, cs
121 b.eq .Lstart_align
122 1:
123 sub result, data1, data2
124 ret
125
126 .Lstart_align:
127 ands xzr, src1, #7
128 b.eq .Lrecal_offset
129
130 add src1, src1, tmp3
131 add src2, src2, tmp3
132
133 ldr data1, [src1], #8
134 ldr data2, [src2], #8
135
136 sub tmp1, data1, zeroones
137 orr tmp2, data1, #REP8_7f
138 bic has_nul, tmp1, tmp2
139 eor diff, data1, data2
140 orr syndrome, diff, has_nul
141 cbnz syndrome, .Lcal_cmpresult
142
143 and tmp3, tmp3, #7
144 .Lrecal_offset:
145 neg pos, tmp3
146 .Lloopcmp_proc:
147
148
149
150
151
152
153
154
155
156 ldr data1, [src1,pos]
157 ldr data2, [src2,pos]
158 sub tmp1, data1, zeroones
159 orr tmp2, data1, #REP8_7f
160 bic has_nul, tmp1, tmp2
161 eor diff, data1, data2
162 orr syndrome, diff, has_nul
163 cbnz syndrome, .Lcal_cmpresult
164
165
166 ldr data1, [src1], #8
167 ldr data2, [src2], #8
168 sub tmp1, data1, zeroones
169 orr tmp2, data1, #REP8_7f
170 bic has_nul, tmp1, tmp2
171 eor diff, data1, data2
172 orr syndrome, diff, has_nul
173 cbz syndrome, .Lloopcmp_proc
174
175 .Lcal_cmpresult:
176
177
178
179
180 CPU_LE( rev syndrome, syndrome )
181 CPU_LE( rev data1, data1 )
182 CPU_LE( rev data2, data2 )
183
184
185
186
187
188
189
190
191
192 CPU_BE( cbnz has_nul, 1f )
193 CPU_BE( cmp data1, data2 )
194 CPU_BE( cset result, ne )
195 CPU_BE( cneg result, result, lo )
196 CPU_BE( ret )
197 CPU_BE( 1: )
198
199 CPU_BE( rev tmp3, data1 )
200 CPU_BE( sub tmp1, tmp3, zeroones )
201 CPU_BE( orr tmp2, tmp3, #REP8_7f )
202 CPU_BE( bic has_nul, tmp1, tmp2 )
203 CPU_BE( rev has_nul, has_nul )
204 CPU_BE( orr syndrome, diff, has_nul )
205
206 clz pos, syndrome
207
208
209
210
211
212
213 lsl data1, data1, pos
214 lsl data2, data2, pos
215
216
217
218
219 lsr data1, data1, #56
220 sub result, data1, data2, lsr #56
221 ret
222 ENDPIPROC(strcmp)
223 EXPORT_SYMBOL_NOKASAN(strcmp)