initial libretro port
[picodrive.git] / pico / misc_arm.s
CommitLineData
cff531af 1/*
2 * Generic memory routines.
3 * (C) notaz, 2007-2008
4 *
5 * This work is licensed under the terms of MAME license.
6 * See COPYING file in the top-level directory.
7 */
fa1e5e29 8
9.global memcpy16 @ unsigned short *dest, unsigned short *src, int count
10
11memcpy16:
12 eor r3, r0, r1
13 tst r3, #2
14 bne mcp16_cant_align
15
16 tst r0, #2
17 ldrneh r3, [r1], #2
18 subne r2, r2, #1
19 strneh r3, [r0], #2
20
21 subs r2, r2, #4
22 bmi mcp16_fin
23
24mcp16_loop:
25 ldmia r1!, {r3,r12}
26 subs r2, r2, #4
27 stmia r0!, {r3,r12}
28 bpl mcp16_loop
29
30mcp16_fin:
31 tst r2, #2
32 ldrne r3, [r1], #4
33 strne r3, [r0], #4
34 ands r2, r2, #1
35 bxeq lr
36
37mcp16_cant_align:
38 ldrh r3, [r1], #2
39 subs r2, r2, #1
40 strh r3, [r0], #2
41 bne mcp16_cant_align
42
43 bx lr
44
45
46
0a051f55 47@ 0x12345678 -> 0x34127856
48@ r4=temp, lr=0x00ff00ff
49.macro bswap reg
50 and r4, \reg, lr
51 and \reg, lr, \reg, lsr #8
52 orr \reg, \reg, r4, lsl #8
53.endm
54
55
56@ dest must be halfword aligned, src can be unaligned
57.global memcpy16bswap @ unsigned short *dest, void *src, int count
58
59memcpy16bswap:
60 tst r1, #1
61 bne mcp16bs_cant_align2
62
63 eor r3, r0, r1
64 tst r3, #2
65 bne mcp16bs_cant_align
66
67 tst r0, #2
68 beq mcp16bs_aligned
69 ldrh r3, [r1], #2
70 sub r2, r2, #1
71 orr r3, r3, r3, lsl #16
72 mov r3, r3, lsr #8
73 strh r3, [r0], #2
74
75mcp16bs_aligned:
76 stmfd sp!, {r4,lr}
77 mov lr, #0xff
78 orr lr, lr, lr, lsl #16
79
80 subs r2, r2, #4
81 bmi mcp16bs_fin4
82
83mcp16bs_loop:
84 ldmia r1!, {r3,r12}
85 subs r2, r2, #4
86 bswap r3
87 bswap r12
88 stmia r0!, {r3,r12}
89 bpl mcp16bs_loop
90
91mcp16bs_fin4:
92 tst r2, #2
93 beq mcp16bs_fin2
94 ldr r3, [r1], #4
95 bswap r3
96 str r3, [r0], #4
97
98mcp16bs_fin2:
99 ldmfd sp!, {r4,lr}
100 ands r2, r2, #1
101 bxeq lr
102
103mcp16bs_cant_align:
104 ldrh r3, [r1], #2
105 subs r2, r2, #1
106 orr r3, r3, r3, lsl #16
107 mov r3, r3, lsr #8
108 strh r3, [r0], #2
109 bne mcp16bs_cant_align
110 bx lr
111
112 @ worst case
113mcp16bs_cant_align2:
114 ldrb r3, [r1], #1
115 ldrb r12,[r1], #1
116 subs r2, r2, #1
117 mov r3, r3, lsl #8
118 orr r3, r3, r12
119 strh r3, [r0], #2
120 bne mcp16bs_cant_align2
121 bx lr
122
123
124
fa1e5e29 125.global memcpy32 @ int *dest, int *src, int count
126
127memcpy32:
128 stmfd sp!, {r4,lr}
129
130 subs r2, r2, #4
131 bmi mcp32_fin
132
133mcp32_loop:
134 ldmia r1!, {r3,r4,r12,lr}
135 subs r2, r2, #4
136 stmia r0!, {r3,r4,r12,lr}
137 bpl mcp32_loop
138
139mcp32_fin:
140 tst r2, #3
141 ldmeqfd sp!, {r4,pc}
142 tst r2, #1
143 ldrne r3, [r1], #4
144 strne r3, [r0], #4
145
146mcp32_no_unal1:
147 tst r2, #2
148 ldmneia r1!, {r3,r12}
149 ldmfd sp!, {r4,lr}
150 stmneia r0!, {r3,r12}
151 bx lr
152
153
154
155.global memset32 @ int *dest, int c, int count
156
157memset32:
158 stmfd sp!, {lr}
159
160 mov r3, r1
161 subs r2, r2, #4
162 bmi mst32_fin
163
164 mov r12,r1
165 mov lr, r1
166
167mst32_loop:
168 subs r2, r2, #4
169 stmia r0!, {r1,r3,r12,lr}
170 bpl mst32_loop
171
172mst32_fin:
173 tst r2, #1
174 strne r1, [r0], #4
175
176 tst r2, #2
177 stmneia r0!, {r1,r3}
178
179 ldmfd sp!, {lr}
180 bx lr
181
cff531af 182@ vim:filetype=armasm