Add Changelog ...
[glibc.git] / sysdeps / powerpc / powerpc32 / 405 / memcpy.S
blob61025cf818093f37cde5385b0c342aa9c7717dc7
1 /* Optimized memcpy implementation for PowerPC476.
2    Copyright (C) 2010 Free Software Foundation, Inc.
3    This file is part of the GNU C Library.
5    The GNU C Library is free software; you can redistribute it and/or
6    modify it under the terms of the GNU Lesser General Public
7    License as published by the Free Software Foundation; either
8    version 2.1 of the License, or (at your option) any later version.
10    The GNU C Library is distributed in the hope that it will be useful,
11    but WITHOUT ANY WARRANTY; without even the implied warranty of
12    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
13    Lesser General Public License for more details.
15    You should have received a copy of the GNU Lesser General Public
16    License along with the GNU C Library.  If not, see
17    <http://www.gnu.org/licenses/>.  */
19 #include <sysdep.h>
20 #include <bp-sym.h>
21 #include <bp-asm.h>
23 /* memcpy
25        r0:return address
26        r3:destination address
27        r4:source address
28        r5:byte count
30        Save return address in r0.
31        If destinationn and source are unaligned and copy count is greater than 256
32        then copy 0-3 bytes to make destination aligned.
33        If 32 or more bytes to copy we use 32 byte copy loop.
34        Finaly we copy 0-31 extra bytes. */
36 EALIGN (BP_SYM (memcpy), 5, 0)
37 /* Check if bytes to copy are greater than 256 and if
38        source and destination are unaligned */
39        cmpwi   r5,0x0100
40        addi    r0,r3,0
41        ble     L(string_count_loop)
42        neg     r6,r3
43        clrlwi. r6,r6,30
44        beq     L(string_count_loop)
45        neg     r6,r4
46        clrlwi. r6,r6,30
47        beq     L(string_count_loop)
48        mtctr   r6
49        subf    r5,r6,r5
51 L(unaligned_bytecopy_loop): /* Align destination by coping 0-3 bytes */
52        lbz     r8,0x0(r4)
53        addi    r4,r4,1
54        stb     r8,0x0(r3)
55        addi    r3,r3,1
56        bdnz    L(unaligned_bytecopy_loop)
57        srwi.   r7,r5,5
58        beq     L(preword2_count_loop)
59        mtctr   r7
61 L(word8_count_loop_no_dcbt): /* Copy 32 bytes at a time */
62        lwz     r6,0(r4)
63        lwz     r7,4(r4)
64        lwz     r8,8(r4)
65        lwz     r9,12(r4)
66        subi    r5,r5,0x20
67        stw     r6,0(r3)
68        stw     r7,4(r3)
69        stw     r8,8(r3)
70        stw     r9,12(r3)
71        lwz     r6,16(r4)
72        lwz     r7,20(r4)
73        lwz     r8,24(r4)
74        lwz     r9,28(r4)
75        addi    r4,r4,0x20
76        stw     r6,16(r3)
77        stw     r7,20(r3)
78        stw     r8,24(r3)
79        stw     r9,28(r3)
80        addi    r3,r3,0x20
81        bdnz    L(word8_count_loop_no_dcbt)
83 L(preword2_count_loop): /* Copy remaining 0-31 bytes */
84        clrlwi. r12,r5,27
85        beq     L(end_memcpy)
86        mtxer   r12
87        lswx    r5,0,r4
88        stswx   r5,0,r3
89        mr       r3,r0
90        blr
92 L(string_count_loop): /* Copy odd 0-31 bytes */
93        clrlwi. r12,r5,28
94        add     r3,r3,r5
95        add     r4,r4,r5
96        beq     L(pre_string_copy)
97        mtxer   r12
98        subf    r4,r12,r4
99        subf    r3,r12,r3
100        lswx    r6,0,r4
101        stswx   r6,0,r3
103 L(pre_string_copy): /* Check how many 32 byte chunck to copy */
104        srwi.   r7,r5,4
105        beq     L(end_memcpy)
106        mtctr   r7
108 L(word4_count_loop_no_dcbt): /* Copy 32 bytes at a time */
109        lwz     r6,-4(r4)
110        lwz     r7,-8(r4)
111        lwz     r8,-12(r4)
112        lwzu    r9,-16(r4)
113        stw     r6,-4(r3)
114        stw     r7,-8(r3)
115        stw     r8,-12(r3)
116        stwu    r9,-16(r3)
117        bdz     L(end_memcpy)
118        lwz     r6,-4(r4)
119        lwz     r7,-8(r4)
120        lwz     r8,-12(r4)
121        lwzu    r9,-16(r4)
122        stw     r6,-4(r3)
123        stw     r7,-8(r3)
124        stw     r8,-12(r3)
125        stwu    r9,-16(r3)
126        bdnz    L(word4_count_loop_no_dcbt)
128 L(end_memcpy):
129        mr       r3,r0
130        blr
131 END (BP_SYM (memcpy))
132 libc_hidden_builtin_def (memcpy)