1 /* 2 * Copyright 2004 Sun Microsystems, Inc. All rights reserved. 3 * Use is subject to license terms. 4 */ 5 6 #pragma ident "%Z%%M% %I% %E% SMI" 7 8 /*- 9 * Copyright (c) 1993 The Regents of the University of California. 10 * All rights reserved. 11 * 12 * Redistribution and use in source and binary forms, with or without 13 * modification, are permitted provided that the following conditions 14 * are met: 15 * 1. Redistributions of source code must retain the above copyright 16 * notice, this list of conditions and the following disclaimer. 17 * 2. Redistributions in binary form must reproduce the above copyright 18 * notice, this list of conditions and the following disclaimer in the 19 * documentation and/or other materials provided with the distribution. 20 * 3. All advertising materials mentioning features or use of this software 21 * must display the following acknowledgement: 22 * This product includes software developed by the University of 23 * California, Berkeley and its contributors. 24 * 4. Neither the name of the University nor the names of its contributors 25 * may be used to endorse or promote products derived from this software 26 * without specific prior written permission. 27 * 28 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 29 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 30 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 31 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 32 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 33 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 34 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 35 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 36 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 37 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 38 * SUCH DAMAGE. 39 * 40 * $FreeBSD: src/sys/amd64/amd64/support.S,v 1.102 2003/10/02 05:08:13 alc Exp $ 41 */ 42 43 #include <sys/asm_linkage.h> 44 45 #if defined(__lint) 46 47 /* 48 * Overlapping bcopy (source and target may overlap arbitrarily). 49 */ 50 /* ARGSUSED */ 51 void 52 ovbcopy(const void *from, void *to, size_t count) 53 {} 54 55 #else /* __lint */ 56 57 /* 58 * Adapted from fbsd bcopy(). 59 * 60 * bcopy(src, dst, cnt) 61 * rdi, rsi, rdx 62 * ws@tools.de (Wolfgang Solfrank, TooLs GmbH) +49-228-985800 63 */ 64 65 #if defined(__amd64) 66 67 ENTRY(ovbcopy) 68 xchgq %rsi,%rdi 69 movq %rdx,%rcx 70 71 movq %rdi,%rax 72 subq %rsi,%rax 73 cmpq %rcx,%rax /* overlapping && src < dst? */ 74 jb reverse 75 76 shrq $3,%rcx /* copy by 64-bit words */ 77 cld /* nope, copy forwards */ 78 rep 79 movsq 80 movq %rdx,%rcx 81 andq $7,%rcx /* any bytes left? */ 82 rep 83 movsb 84 ret 85 86 reverse: 87 addq %rcx,%rdi /* copy backwards */ 88 addq %rcx,%rsi 89 decq %rdi 90 decq %rsi 91 andq $7,%rcx /* any fractional bytes? */ 92 std 93 rep 94 movsb 95 movq %rdx,%rcx /* copy remainder by 32-bit words */ 96 shrq $3,%rcx 97 subq $7,%rsi 98 subq $7,%rdi 99 rep 100 movsq 101 cld 102 ret 103 SET_SIZE(ovbcopy) 104 105 #elif defined(__i386) 106 107 ENTRY(ovbcopy) 108 pushl %esi 109 pushl %edi 110 movl 12(%esp),%esi 111 movl 16(%esp),%edi 112 movl 20(%esp),%ecx 113 114 movl %edi,%eax 115 subl %esi,%eax 116 cmpl %ecx,%eax /* overlapping && src < dst? */ 117 jb reverse 118 119 shrl $2,%ecx /* copy by 32-bit words */ 120 cld /* nope, copy forwards */ 121 rep 122 movsl 123 movl 20(%esp),%ecx 124 andl $3,%ecx /* any bytes left? */ 125 rep 126 movsb 127 popl %edi 128 popl %esi 129 ret 130 131 reverse: 132 addl %ecx,%edi /* copy backwards */ 133 addl %ecx,%esi 134 decl %edi 135 decl %esi 136 andl $3,%ecx /* any fractional bytes? */ 137 std 138 rep 139 movsb 140 movl 20(%esp),%ecx /* copy remainder by 32-bit words */ 141 shrl $2,%ecx 142 subl $3,%esi 143 subl $3,%edi 144 rep 145 movsl 146 popl %edi 147 popl %esi 148 cld 149 ret 150 SET_SIZE(ovbcopy) 151 152 #endif /* __i386 */ 153 154 #endif /* __lint */