Update copyright notices with scripts/update-copyrights.
[glibc.git] / sysdeps / i386 / i586 / strcpy.S
blobaf23bf5a26958a78db3ec77edcfb60b7631fef9b
1 /* strcpy/stpcpy implementation for i586.
2    Copyright (C) 1997-2013 Free Software Foundation, Inc.
3    This file is part of the GNU C Library.
4    Contributed by Ulrich Drepper <drepper@cygnus.com>, 1997.
6    The GNU C Library is free software; you can redistribute it and/or
7    modify it under the terms of the GNU Lesser General Public
8    License as published by the Free Software Foundation; either
9    version 2.1 of the License, or (at your option) any later version.
11    The GNU C Library is distributed in the hope that it will be useful,
12    but WITHOUT ANY WARRANTY; without even the implied warranty of
13    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14    Lesser General Public License for more details.
16    You should have received a copy of the GNU Lesser General Public
17    License along with the GNU C Library; if not, see
18    <http://www.gnu.org/licenses/>.  */
20 #include <sysdep.h>
21 #include "asm-syntax.h"
22 #include "bp-sym.h"
23 #include "bp-asm.h"
25 #define PARMS   LINKAGE+12      /* space for 3 saved regs */
26 #define RTN     PARMS
27 #define DEST    RTN+RTN_SIZE
28 #define SRC     DEST+PTR_SIZE
30 #ifndef USE_AS_STPCPY
31 # define STRCPY strcpy
32 #endif
34 #define magic 0xfefefeff
36         .text
37 ENTRY (BP_SYM (STRCPY))
38         ENTER
40         pushl   %edi
41         cfi_adjust_cfa_offset (4)
42         pushl   %esi
43         cfi_adjust_cfa_offset (4)
44         pushl   %ebx
45         cfi_adjust_cfa_offset (4)
47         movl    DEST(%esp), %edi
48         cfi_rel_offset (edi, 8)
49         movl    SRC(%esp), %esi
50         cfi_rel_offset (esi, 4)
51         CHECK_BOUNDS_LOW (%edi, DEST(%esp))
52         CHECK_BOUNDS_LOW (%esi, SRC(%esp))
54         xorl    %eax, %eax
55         leal    -1(%esi), %ecx
57         movl    $magic, %ebx
58         cfi_rel_offset (ebx, 0)
59         andl    $3, %ecx
61 #ifdef PIC
62         call    2f
63         cfi_adjust_cfa_offset (4)
64 2:      popl    %edx
65         cfi_adjust_cfa_offset (-4)
66         /* 0xb is the distance between 2: and 1: but we avoid writing
67            1f-2b because the assembler generates worse code.  */
68         leal    0xb(%edx,%ecx,8), %ecx
69 #else
70         leal    1f(,%ecx,8), %ecx
71 #endif
73         jmp     *%ecx
75         .align 8
77         orb     (%esi), %al
78         jz      L(end)
79         stosb
80         xorl    %eax, %eax
81         incl    %esi
83         orb     (%esi), %al
84         jz      L(end)
85         stosb
86         xorl    %eax, %eax
87         incl    %esi
89         orb     (%esi), %al
90         jz      L(end)
91         stosb
92         xorl    %eax, %eax
93         incl    %esi
95 L(1):   movl    (%esi), %ecx
96         leal    4(%esi),%esi
98         subl    %ecx, %eax
99         addl    %ebx, %ecx
101         decl    %eax
102         jnc     L(3)
104         movl    %ecx, %edx
105         xorl    %ecx, %eax
107         subl    %ebx, %edx
108         andl    $~magic, %eax
110         jne     L(4)
112         movl    %edx, (%edi)
113         leal    4(%edi),%edi
115         jmp     L(1)
117 L(3):   movl    %ecx, %edx
119         subl    %ebx, %edx
121 L(4):   movb    %dl, (%edi)
122         testb   %dl, %dl
124         movl    %edx, %eax
125         jz      L(end2)
127         shrl    $16, %eax
128         movb    %dh, 1(%edi)
129 #ifdef USE_AS_STPCPY
130         addl    $1, %edi
131 #endif
133         cmpb    $0, %dh
134         jz      L(end2)
136 #ifdef USE_AS_STPCPY
137         movb    %al, 1(%edi)
138         addl    $1, %edi
140         cmpb    $0, %al
141         jz      L(end2)
143         addl    $1, %edi
144 #else
145         movb    %al, 2(%edi)
146         testb   %al, %al
148         leal    3(%edi), %edi
149         jz      L(end2)
150 #endif
152 L(end): movb    %ah, (%edi)
154 L(end2):
155         /* GKM FIXME: check high bounds  */
156 #ifdef USE_AS_STPCPY
157         movl    %edi, %eax
158 #else
159         movl    DEST(%esp), %eax
160 #endif
161         RETURN_BOUNDED_POINTER (DEST(%esp))
162         popl    %ebx
163         cfi_adjust_cfa_offset (-4)
164         cfi_restore (ebx)
165         popl    %esi
166         cfi_adjust_cfa_offset (-4)
167         cfi_restore (esi)
168         popl    %edi
169         cfi_adjust_cfa_offset (-4)
170         cfi_restore (edi)
172         LEAVE
173         RET_PTR
174 END (BP_SYM (STRCPY))
175 #ifndef USE_AS_STPCPY
176 libc_hidden_builtin_def (strcpy)
177 #endif