]>
Commit | Line | Data |
---|---|---|
bf98ec6c PB |
1 | /* Miscellaneous BPABI functions. ARMv6M implementation |
2 | ||
748086b7 | 3 | Copyright (C) 2006, 2008, 2009 Free Software Foundation, Inc. |
bf98ec6c PB |
4 | Contributed by CodeSourcery. |
5 | ||
6 | This file is free software; you can redistribute it and/or modify it | |
7 | under the terms of the GNU General Public License as published by the | |
748086b7 | 8 | Free Software Foundation; either version 3, or (at your option) any |
bf98ec6c PB |
9 | later version. |
10 | ||
bf98ec6c PB |
11 | This file is distributed in the hope that it will be useful, but |
12 | WITHOUT ANY WARRANTY; without even the implied warranty of | |
13 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | |
14 | General Public License for more details. | |
15 | ||
748086b7 JJ |
16 | Under Section 7 of GPL version 3, you are granted additional |
17 | permissions described in the GCC Runtime Library Exception, version | |
18 | 3.1, as published by the Free Software Foundation. | |
19 | ||
20 | You should have received a copy of the GNU General Public License and | |
21 | a copy of the GCC Runtime Library Exception along with this program; | |
22 | see the files COPYING3 and COPYING.RUNTIME respectively. If not, see | |
23 | <http://www.gnu.org/licenses/>. */ | |
bf98ec6c | 24 | |
bf98ec6c PB |
25 | #ifdef L_aeabi_lcmp |
26 | ||
27 | FUNC_START aeabi_lcmp | |
28 | cmp xxh, yyh | |
29 | beq 1f | |
30 | bgt 2f | |
31 | mov r0, #1 | |
32 | neg r0, r0 | |
33 | RET | |
34 | 2: | |
35 | mov r0, #1 | |
36 | RET | |
37 | 1: | |
38 | sub r0, xxl, yyl | |
39 | beq 1f | |
40 | bhi 2f | |
41 | mov r0, #1 | |
42 | neg r0, r0 | |
43 | RET | |
44 | 2: | |
45 | mov r0, #1 | |
46 | 1: | |
47 | RET | |
48 | FUNC_END aeabi_lcmp | |
49 | ||
50 | #endif /* L_aeabi_lcmp */ | |
51 | ||
52 | #ifdef L_aeabi_ulcmp | |
53 | ||
54 | FUNC_START aeabi_ulcmp | |
55 | cmp xxh, yyh | |
56 | bne 1f | |
57 | sub r0, xxl, yyl | |
58 | beq 2f | |
59 | 1: | |
60 | bcs 1f | |
61 | mov r0, #1 | |
62 | neg r0, r0 | |
63 | RET | |
64 | 1: | |
65 | mov r0, #1 | |
66 | 2: | |
67 | RET | |
68 | FUNC_END aeabi_ulcmp | |
69 | ||
70 | #endif /* L_aeabi_ulcmp */ | |
71 | ||
72 | #ifdef L_aeabi_ldivmod | |
73 | ||
74 | FUNC_START aeabi_ldivmod | |
75 | push {r0, r1} | |
76 | mov r0, sp | |
77 | push {r0, lr} | |
78 | ldr r0, [sp, #8] | |
79 | bl SYM(__gnu_ldivmod_helper) | |
80 | ldr r3, [sp, #4] | |
81 | mov lr, r3 | |
82 | add sp, sp, #8 | |
83 | pop {r2, r3} | |
84 | RET | |
85 | FUNC_END aeabi_ldivmod | |
86 | ||
87 | #endif /* L_aeabi_ldivmod */ | |
88 | ||
89 | #ifdef L_aeabi_uldivmod | |
90 | ||
91 | FUNC_START aeabi_uldivmod | |
92 | push {r0, r1} | |
93 | mov r0, sp | |
94 | push {r0, lr} | |
95 | ldr r0, [sp, #8] | |
96 | bl SYM(__gnu_uldivmod_helper) | |
97 | ldr r3, [sp, #4] | |
98 | mov lr, r3 | |
99 | add sp, sp, #8 | |
100 | pop {r2, r3} | |
101 | RET | |
102 | FUNC_END aeabi_uldivmod | |
103 | ||
104 | #endif /* L_aeabi_uldivmod */ | |
105 | ||
106 | #ifdef L_arm_addsubsf3 | |
107 | ||
108 | FUNC_START aeabi_frsub | |
109 | ||
110 | push {r4, lr} | |
111 | mov r4, #1 | |
112 | lsl r4, #31 | |
113 | eor r0, r0, r4 | |
114 | bl __aeabi_fadd | |
115 | pop {r4, pc} | |
116 | ||
117 | FUNC_END aeabi_frsub | |
118 | ||
119 | #endif /* L_arm_addsubsf3 */ | |
120 | ||
121 | #ifdef L_arm_cmpsf2 | |
122 | ||
123 | FUNC_START aeabi_cfrcmple | |
124 | ||
125 | mov ip, r0 | |
126 | mov r0, r1 | |
127 | mov r1, ip | |
128 | b 6f | |
129 | ||
130 | FUNC_START aeabi_cfcmpeq | |
131 | FUNC_ALIAS aeabi_cfcmple aeabi_cfcmpeq | |
132 | ||
133 | @ The status-returning routines are required to preserve all | |
134 | @ registers except ip, lr, and cpsr. | |
135 | 6: push {r0, r1, r2, r3, r4, lr} | |
136 | bl __lesf2 | |
137 | @ Set the Z flag correctly, and the C flag unconditionally. | |
138 | cmp r0, #0 | |
139 | @ Clear the C flag if the return value was -1, indicating | |
140 | @ that the first operand was smaller than the second. | |
141 | bmi 1f | |
142 | mov r1, #0 | |
143 | cmn r0, r1 | |
144 | 1: | |
145 | pop {r0, r1, r2, r3, r4, pc} | |
146 | ||
147 | FUNC_END aeabi_cfcmple | |
148 | FUNC_END aeabi_cfcmpeq | |
149 | FUNC_END aeabi_cfrcmple | |
150 | ||
151 | FUNC_START aeabi_fcmpeq | |
152 | ||
153 | push {r4, lr} | |
154 | bl __eqsf2 | |
155 | neg r0, r0 | |
156 | add r0, r0, #1 | |
157 | pop {r4, pc} | |
158 | ||
159 | FUNC_END aeabi_fcmpeq | |
160 | ||
161 | .macro COMPARISON cond, helper, mode=sf2 | |
162 | FUNC_START aeabi_fcmp\cond | |
163 | ||
164 | push {r4, lr} | |
165 | bl __\helper\mode | |
166 | cmp r0, #0 | |
167 | b\cond 1f | |
168 | mov r0, #0 | |
169 | pop {r4, pc} | |
170 | 1: | |
171 | mov r0, #1 | |
172 | pop {r4, pc} | |
173 | ||
174 | FUNC_END aeabi_fcmp\cond | |
175 | .endm | |
176 | ||
177 | COMPARISON lt, le | |
178 | COMPARISON le, le | |
179 | COMPARISON gt, ge | |
180 | COMPARISON ge, ge | |
181 | ||
182 | #endif /* L_arm_cmpsf2 */ | |
183 | ||
184 | #ifdef L_arm_addsubdf3 | |
185 | ||
186 | FUNC_START aeabi_drsub | |
187 | ||
188 | push {r4, lr} | |
189 | mov r4, #1 | |
190 | lsl r4, #31 | |
191 | eor xxh, xxh, r4 | |
192 | bl __aeabi_dadd | |
193 | pop {r4, pc} | |
194 | ||
195 | FUNC_END aeabi_drsub | |
196 | ||
197 | #endif /* L_arm_addsubdf3 */ | |
198 | ||
199 | #ifdef L_arm_cmpdf2 | |
200 | ||
201 | FUNC_START aeabi_cdrcmple | |
202 | ||
203 | mov ip, r0 | |
204 | mov r0, r2 | |
205 | mov r2, ip | |
206 | mov ip, r1 | |
207 | mov r1, r3 | |
208 | mov r3, ip | |
209 | b 6f | |
210 | ||
211 | FUNC_START aeabi_cdcmpeq | |
212 | FUNC_ALIAS aeabi_cdcmple aeabi_cdcmpeq | |
213 | ||
214 | @ The status-returning routines are required to preserve all | |
215 | @ registers except ip, lr, and cpsr. | |
216 | 6: push {r0, r1, r2, r3, r4, lr} | |
217 | bl __ledf2 | |
218 | @ Set the Z flag correctly, and the C flag unconditionally. | |
219 | cmp r0, #0 | |
220 | @ Clear the C flag if the return value was -1, indicating | |
221 | @ that the first operand was smaller than the second. | |
222 | bmi 1f | |
223 | mov r1, #0 | |
224 | cmn r0, r1 | |
225 | 1: | |
226 | pop {r0, r1, r2, r3, r4, pc} | |
227 | ||
228 | FUNC_END aeabi_cdcmple | |
229 | FUNC_END aeabi_cdcmpeq | |
230 | FUNC_END aeabi_cdrcmple | |
231 | ||
232 | FUNC_START aeabi_dcmpeq | |
233 | ||
234 | push {r4, lr} | |
235 | bl __eqdf2 | |
236 | neg r0, r0 | |
237 | add r0, r0, #1 | |
238 | pop {r4, pc} | |
239 | ||
240 | FUNC_END aeabi_dcmpeq | |
241 | ||
242 | .macro COMPARISON cond, helper, mode=df2 | |
243 | FUNC_START aeabi_dcmp\cond | |
244 | ||
245 | push {r4, lr} | |
246 | bl __\helper\mode | |
247 | cmp r0, #0 | |
248 | b\cond 1f | |
249 | mov r0, #0 | |
250 | pop {r4, pc} | |
251 | 1: | |
252 | mov r0, #1 | |
253 | pop {r4, pc} | |
254 | ||
255 | FUNC_END aeabi_dcmp\cond | |
256 | .endm | |
257 | ||
258 | COMPARISON lt, le | |
259 | COMPARISON le, le | |
260 | COMPARISON gt, ge | |
261 | COMPARISON ge, ge | |
262 | ||
263 | #endif /* L_arm_cmpdf2 */ |