xref: /plan9-contrib/sys/src/ape/lib/ap/mips/memmove.s (revision f53d914d322ac68515baf41fa58042ce9dfbf05b)
1219b2ee8SDavid du Colombier	TEXT	memmove(SB), $0
2219b2ee8SDavid du Colombier
3219b2ee8SDavid du Colombier	JMP	move
4219b2ee8SDavid du Colombier
5219b2ee8SDavid du Colombier	TEXT	memcpy(SB), $0
6219b2ee8SDavid du Colombiermove:
7219b2ee8SDavid du Colombier	MOVW	R1, s1+0(FP)
8219b2ee8SDavid du Colombier
9219b2ee8SDavid du Colombier	MOVW	n+8(FP), R3		/* R3 is count */
10219b2ee8SDavid du Colombier	MOVW	R1, R4			/* R4 is to-pointer */
11219b2ee8SDavid du Colombier	SGT	R0, R3, R5
12219b2ee8SDavid du Colombier	BEQ	R5, ok
13219b2ee8SDavid du Colombier	MOVW	(R0), R0		/* abort if negative count */
14219b2ee8SDavid du Colombierok:
15219b2ee8SDavid du Colombier	MOVW	s2+4(FP), R5		/* R5 is from-pointer */
16219b2ee8SDavid du Colombier	ADDU	R3,R5, R7		/* R7 is end from-pointer */
17219b2ee8SDavid du Colombier	ADDU	R3,R4, R6		/* R6 is end to-pointer */
18219b2ee8SDavid du Colombier
19219b2ee8SDavid du Colombier/*
20219b2ee8SDavid du Colombier * easiest test is copy backwards if
21219b2ee8SDavid du Colombier * destination string has higher mem address
22219b2ee8SDavid du Colombier */
23219b2ee8SDavid du Colombier	SGT	$4,R3, R2
24219b2ee8SDavid du Colombier	SGTU	R4,R5, R1
25219b2ee8SDavid du Colombier	BNE	R1, back
26219b2ee8SDavid du Colombier
27219b2ee8SDavid du Colombier/*
28219b2ee8SDavid du Colombier * if not at least 4 chars,
29*f53d914dSDavid du Colombier * don't even mess around.
30219b2ee8SDavid du Colombier * 3 chars to guarantee any
31219b2ee8SDavid du Colombier * rounding up to a word
32219b2ee8SDavid du Colombier * boundary and 4 characters
33219b2ee8SDavid du Colombier * to get at least maybe one
34219b2ee8SDavid du Colombier * full word store.
35219b2ee8SDavid du Colombier */
36219b2ee8SDavid du Colombier	BNE	R2, fout
37219b2ee8SDavid du Colombier
38219b2ee8SDavid du Colombier/*
39219b2ee8SDavid du Colombier * test if both pointers
40219b2ee8SDavid du Colombier * are similarly word aligned
41219b2ee8SDavid du Colombier */
42219b2ee8SDavid du Colombier	XOR	R4,R5, R1
43219b2ee8SDavid du Colombier	AND	$3, R1
44219b2ee8SDavid du Colombier	BNE	R1, fout
45219b2ee8SDavid du Colombier
46219b2ee8SDavid du Colombier/*
47219b2ee8SDavid du Colombier * byte at a time to word align
48219b2ee8SDavid du Colombier */
49219b2ee8SDavid du Colombierf1:
50219b2ee8SDavid du Colombier	AND	$3,R4, R1
51219b2ee8SDavid du Colombier	BEQ	R1, f2
52219b2ee8SDavid du Colombier	MOVB	0(R5), R8
53219b2ee8SDavid du Colombier	ADDU	$1, R5
54219b2ee8SDavid du Colombier	MOVB	R8, 0(R4)
55219b2ee8SDavid du Colombier	ADDU	$1, R4
56219b2ee8SDavid du Colombier	JMP	f1
57219b2ee8SDavid du Colombier
58219b2ee8SDavid du Colombier/*
59219b2ee8SDavid du Colombier * turn R3 into to-end pointer-15
60219b2ee8SDavid du Colombier * copy 16 at a time while theres room.
61219b2ee8SDavid du Colombier * R6 is smaller than R7 --
62219b2ee8SDavid du Colombier * there are problems if R7 is 0.
63219b2ee8SDavid du Colombier */
64219b2ee8SDavid du Colombierf2:
65219b2ee8SDavid du Colombier	ADDU	$-15,R6, R3
66219b2ee8SDavid du Colombierf3:
67219b2ee8SDavid du Colombier	SGTU	R3,R4, R1
68219b2ee8SDavid du Colombier	BEQ	R1, f4
69219b2ee8SDavid du Colombier	MOVW	0(R5), R8
70219b2ee8SDavid du Colombier	MOVW	4(R5), R9
71219b2ee8SDavid du Colombier	MOVW	R8, 0(R4)
72219b2ee8SDavid du Colombier	MOVW	8(R5), R8
73219b2ee8SDavid du Colombier	MOVW	R9, 4(R4)
74219b2ee8SDavid du Colombier	MOVW	12(R5), R9
75219b2ee8SDavid du Colombier	ADDU	$16, R5
76219b2ee8SDavid du Colombier	MOVW	R8, 8(R4)
77219b2ee8SDavid du Colombier	MOVW	R9, 12(R4)
78219b2ee8SDavid du Colombier	ADDU	$16, R4
79219b2ee8SDavid du Colombier	JMP	f3
80219b2ee8SDavid du Colombier
81219b2ee8SDavid du Colombier/*
82219b2ee8SDavid du Colombier * turn R3 into to-end pointer-3
83219b2ee8SDavid du Colombier * copy 4 at a time while theres room
84219b2ee8SDavid du Colombier */
85219b2ee8SDavid du Colombierf4:
86219b2ee8SDavid du Colombier	ADDU	$-3,R6, R3
87219b2ee8SDavid du Colombierf5:
88219b2ee8SDavid du Colombier	SGTU	R3,R4, R1
89219b2ee8SDavid du Colombier	BEQ	R1, fout
90219b2ee8SDavid du Colombier	MOVW	0(R5), R8
91219b2ee8SDavid du Colombier	ADDU	$4, R5
92219b2ee8SDavid du Colombier	MOVW	R8, 0(R4)
93219b2ee8SDavid du Colombier	ADDU	$4, R4
94219b2ee8SDavid du Colombier	JMP	f5
95219b2ee8SDavid du Colombier
96219b2ee8SDavid du Colombier/*
97219b2ee8SDavid du Colombier * last loop, copy byte at a time
98219b2ee8SDavid du Colombier */
99219b2ee8SDavid du Colombierfout:
100219b2ee8SDavid du Colombier	BEQ	R7,R5, ret
101219b2ee8SDavid du Colombier	MOVB	0(R5), R8
102219b2ee8SDavid du Colombier	ADDU	$1, R5
103219b2ee8SDavid du Colombier	MOVB	R8, 0(R4)
104219b2ee8SDavid du Colombier	ADDU	$1, R4
105219b2ee8SDavid du Colombier	JMP	fout
106219b2ee8SDavid du Colombier
107219b2ee8SDavid du Colombier/*
108219b2ee8SDavid du Colombier * whole thing repeated for backwards
109219b2ee8SDavid du Colombier */
110219b2ee8SDavid du Colombierback:
111219b2ee8SDavid du Colombier	BNE	R2, bout
112219b2ee8SDavid du Colombier	XOR	R6,R7, R1
113219b2ee8SDavid du Colombier	AND	$3, R1
114219b2ee8SDavid du Colombier	BNE	R1, bout
115219b2ee8SDavid du Colombierb1:
116219b2ee8SDavid du Colombier	AND	$3,R7, R1
117219b2ee8SDavid du Colombier	BEQ	R1, b2
118219b2ee8SDavid du Colombier	MOVB	-1(R7), R8
119219b2ee8SDavid du Colombier	ADDU	$-1, R7
120219b2ee8SDavid du Colombier	MOVB	R8, -1(R6)
121219b2ee8SDavid du Colombier	ADDU	$-1, R6
122219b2ee8SDavid du Colombier	JMP	b1
123219b2ee8SDavid du Colombierb2:
124219b2ee8SDavid du Colombier	ADDU	$15,R5, R3
125219b2ee8SDavid du Colombierb3:
126219b2ee8SDavid du Colombier	SGTU	R7,R3, R1
127219b2ee8SDavid du Colombier	BEQ	R1, b4
128219b2ee8SDavid du Colombier	MOVW	-4(R7), R8
129219b2ee8SDavid du Colombier	MOVW	-8(R7), R9
130219b2ee8SDavid du Colombier	MOVW	R8, -4(R6)
131219b2ee8SDavid du Colombier	MOVW	-12(R7), R8
132219b2ee8SDavid du Colombier	MOVW	R9, -8(R6)
133219b2ee8SDavid du Colombier	MOVW	-16(R7), R9
134219b2ee8SDavid du Colombier	ADDU	$-16, R7
135219b2ee8SDavid du Colombier	MOVW	R8, -12(R6)
136219b2ee8SDavid du Colombier	MOVW	R9, -16(R6)
137219b2ee8SDavid du Colombier	ADDU	$-16, R6
138219b2ee8SDavid du Colombier	JMP	b3
139219b2ee8SDavid du Colombierb4:
140219b2ee8SDavid du Colombier	ADDU	$3,R5, R3
141219b2ee8SDavid du Colombierb5:
142219b2ee8SDavid du Colombier	SGTU	R7,R3, R1
143219b2ee8SDavid du Colombier	BEQ	R1, bout
144219b2ee8SDavid du Colombier	MOVW	-4(R7), R8
145219b2ee8SDavid du Colombier	ADDU	$-4, R7
146219b2ee8SDavid du Colombier	MOVW	R8, -4(R6)
147219b2ee8SDavid du Colombier	ADDU	$-4, R6
148219b2ee8SDavid du Colombier	JMP	b5
149219b2ee8SDavid du Colombier
150219b2ee8SDavid du Colombierbout:
151219b2ee8SDavid du Colombier	BEQ	R7,R5, ret
152219b2ee8SDavid du Colombier	MOVB	-1(R7), R8
153219b2ee8SDavid du Colombier	ADDU	$-1, R7
154219b2ee8SDavid du Colombier	MOVB	R8, -1(R6)
155219b2ee8SDavid du Colombier	ADDU	$-1, R6
156219b2ee8SDavid du Colombier	JMP	bout
157219b2ee8SDavid du Colombier
158219b2ee8SDavid du Colombierret:
159219b2ee8SDavid du Colombier	MOVW	s1+0(FP), R1
160219b2ee8SDavid du Colombier	RET
161219b2ee8SDavid du Colombier	END
162