/*- * Copyright (c) 2007 * Thorsten Glaser * * Provided that these terms and disclaimer and all copyright notices * are retained or reproduced in an accompanying document, permission * is granted to deal in this work without restriction, including un- * limited rights to use, publicly perform, distribute, sell, modify, * merge, give away, or sublicence. * * This work is provided "AS IS" and WITHOUT WARRANTY of any kind, to * the utmost extent permitted by applicable law, neither express nor * implied; without malicious intent or gross negligence. In no event * may a licensor, author or contributor be held liable for indirect, * direct, other damage, loss, or other issues arising in any way out * of dealing in the work, even if advised of the possibility of such * damage or existence of a defect, except proven that it results out * of said person's immediate fault when using the work as intended. */ #include #include __RCSID("$MirOS: src/lib/libc/string/bcopy.c,v 1.8 2007/08/08 20:57:41 tg Exp $"); /* this is the basic copy data type, should be fastest */ typedef unsigned long mword; #define mbytes sizeof (mword) #define mmask (mbytes - 1) #ifdef MEMCOPY #define MEMMOVE #define memmove memcpy #endif #ifdef MEMMOVE void * memmove(void *dst, const void *src, size_t len) #else void bcopy(const void *src, void *dst, size_t len) #endif { const uint8_t *s = src; uint8_t *d = dst; size_t n; intptr_t cp; if (len == 0 || dst == src) goto done; if ((intptr_t)dst < (intptr_t)src) { /* copy forward */ if ((((cp = (intptr_t)s) | (intptr_t)d) & mmask) && (((cp ^ (intptr_t)d) & mmask) == 0) && len >= mbytes) { /* low bits match: first align then copy entire words */ n = mbytes - (cp & mmask); len -= n; while (n--) *d++ = *s++; n = len / mbytes; len &= mmask; while (n--) { *(mword *)d = *(const mword *)s; s += mbytes; d += mbytes; } } while (len--) *d++ = *s++; } else { /* copy backward */ s += len; d += len; if ((((cp = (intptr_t)s) | (intptr_t)d) & mmask) && (((cp ^ (intptr_t)d) & mmask) == 0) && len >= mbytes) { /* low bits match: first align then copy entire words */ n = cp & mmask; len -= n; while (n--) *--d = *--s; n = len / mbytes; len &= mmask; while (n--) { s -= mbytes; d -= mbytes; *(mword *)d = *(const mword *)s; } } while (len--) *--d = *--s; } done: #ifdef MEMMOVE return (dst); #else return; #endif }