GNU Linux-libre 4.9.296-gnu1
[releases.git] / arch / sparc / lib / memmove.S
1 /* memmove.S: Simple memmove implementation.
2  *
3  * Copyright (C) 1997, 2004 David S. Miller (davem@redhat.com)
4  * Copyright (C) 1996, 1997, 1998, 1999 Jakub Jelinek (jj@ultra.linux.cz)
5  */
6
7 #include <linux/linkage.h>
8 #include <asm/export.h>
9
10         .text
11 ENTRY(memmove) /* o0=dst o1=src o2=len */
12         brz,pn          %o2, 99f
13          mov            %o0, %g1
14
15         cmp             %o0, %o1
16         bleu,pt         %xcc, 2f
17          add            %o1, %o2, %g7
18         cmp             %g7, %o0
19         bleu,pt         %xcc, memcpy
20          add            %o0, %o2, %o5
21         sub             %g7, 1, %o1
22
23         sub             %o5, 1, %o0
24 1:      ldub            [%o1], %g7
25         subcc           %o2, 1, %o2
26         sub             %o1, 1, %o1
27         stb             %g7, [%o0]
28         bne,pt          %icc, 1b
29          sub            %o0, 1, %o0
30 99:
31         retl
32          mov            %g1, %o0
33
34         /* We can't just call memcpy for these memmove cases.  On some
35          * chips the memcpy uses cache initializing stores and when dst
36          * and src are close enough, those can clobber the source data
37          * before we've loaded it in.
38          */
39 2:      or              %o0, %o1, %g7
40         or              %o2, %g7, %g7
41         andcc           %g7, 0x7, %g0
42         bne,pn          %xcc, 4f
43          nop
44
45 3:      ldx             [%o1], %g7
46         add             %o1, 8, %o1
47         subcc           %o2, 8, %o2
48         add             %o0, 8, %o0
49         bne,pt          %icc, 3b
50          stx            %g7, [%o0 - 0x8]
51         ba,a,pt         %xcc, 99b
52
53 4:      ldub            [%o1], %g7
54         add             %o1, 1, %o1
55         subcc           %o2, 1, %o2
56         add             %o0, 1, %o0
57         bne,pt          %icc, 4b
58          stb            %g7, [%o0 - 0x1]
59         ba,a,pt         %xcc, 99b
60 ENDPROC(memmove)
61 EXPORT_SYMBOL(memmove)