1*4882a593Smuzhiyun /* 2*4882a593Smuzhiyun * This file is subject to the terms and conditions of the GNU General Public 3*4882a593Smuzhiyun * License. See the file COPYING in the main directory of this archive 4*4882a593Smuzhiyun * for more details. 5*4882a593Smuzhiyun */ 6*4882a593Smuzhiyun 7*4882a593Smuzhiyun #include <linux/module.h> 8*4882a593Smuzhiyun #include <linux/string.h> 9*4882a593Smuzhiyun memmove(void * dest,const void * src,size_t n)10*4882a593Smuzhiyunvoid *memmove(void *dest, const void *src, size_t n) 11*4882a593Smuzhiyun { 12*4882a593Smuzhiyun void *xdest = dest; 13*4882a593Smuzhiyun size_t temp; 14*4882a593Smuzhiyun 15*4882a593Smuzhiyun if (!n) 16*4882a593Smuzhiyun return xdest; 17*4882a593Smuzhiyun 18*4882a593Smuzhiyun if (dest < src) { 19*4882a593Smuzhiyun if ((long)dest & 1) { 20*4882a593Smuzhiyun char *cdest = dest; 21*4882a593Smuzhiyun const char *csrc = src; 22*4882a593Smuzhiyun *cdest++ = *csrc++; 23*4882a593Smuzhiyun dest = cdest; 24*4882a593Smuzhiyun src = csrc; 25*4882a593Smuzhiyun n--; 26*4882a593Smuzhiyun } 27*4882a593Smuzhiyun if (n > 2 && (long)dest & 2) { 28*4882a593Smuzhiyun short *sdest = dest; 29*4882a593Smuzhiyun const short *ssrc = src; 30*4882a593Smuzhiyun *sdest++ = *ssrc++; 31*4882a593Smuzhiyun dest = sdest; 32*4882a593Smuzhiyun src = ssrc; 33*4882a593Smuzhiyun n -= 2; 34*4882a593Smuzhiyun } 35*4882a593Smuzhiyun temp = n >> 2; 36*4882a593Smuzhiyun if (temp) { 37*4882a593Smuzhiyun long *ldest = dest; 38*4882a593Smuzhiyun const long *lsrc = src; 39*4882a593Smuzhiyun temp--; 40*4882a593Smuzhiyun do 41*4882a593Smuzhiyun *ldest++ = *lsrc++; 42*4882a593Smuzhiyun while (temp--); 43*4882a593Smuzhiyun dest = ldest; 44*4882a593Smuzhiyun src = lsrc; 45*4882a593Smuzhiyun } 46*4882a593Smuzhiyun if (n & 2) { 47*4882a593Smuzhiyun short *sdest = dest; 48*4882a593Smuzhiyun const short *ssrc = src; 49*4882a593Smuzhiyun *sdest++ = *ssrc++; 50*4882a593Smuzhiyun dest = sdest; 51*4882a593Smuzhiyun src = ssrc; 52*4882a593Smuzhiyun } 53*4882a593Smuzhiyun if (n & 1) { 54*4882a593Smuzhiyun char *cdest = dest; 55*4882a593Smuzhiyun const char *csrc = src; 56*4882a593Smuzhiyun *cdest = *csrc; 57*4882a593Smuzhiyun } 58*4882a593Smuzhiyun } else { 59*4882a593Smuzhiyun dest = (char *)dest + n; 60*4882a593Smuzhiyun src = (const char *)src + n; 61*4882a593Smuzhiyun if ((long)dest & 1) { 62*4882a593Smuzhiyun char *cdest = dest; 63*4882a593Smuzhiyun const char *csrc = src; 64*4882a593Smuzhiyun *--cdest = *--csrc; 65*4882a593Smuzhiyun dest = cdest; 66*4882a593Smuzhiyun src = csrc; 67*4882a593Smuzhiyun n--; 68*4882a593Smuzhiyun } 69*4882a593Smuzhiyun if (n > 2 && (long)dest & 2) { 70*4882a593Smuzhiyun short *sdest = dest; 71*4882a593Smuzhiyun const short *ssrc = src; 72*4882a593Smuzhiyun *--sdest = *--ssrc; 73*4882a593Smuzhiyun dest = sdest; 74*4882a593Smuzhiyun src = ssrc; 75*4882a593Smuzhiyun n -= 2; 76*4882a593Smuzhiyun } 77*4882a593Smuzhiyun temp = n >> 2; 78*4882a593Smuzhiyun if (temp) { 79*4882a593Smuzhiyun long *ldest = dest; 80*4882a593Smuzhiyun const long *lsrc = src; 81*4882a593Smuzhiyun temp--; 82*4882a593Smuzhiyun do 83*4882a593Smuzhiyun *--ldest = *--lsrc; 84*4882a593Smuzhiyun while (temp--); 85*4882a593Smuzhiyun dest = ldest; 86*4882a593Smuzhiyun src = lsrc; 87*4882a593Smuzhiyun } 88*4882a593Smuzhiyun if (n & 2) { 89*4882a593Smuzhiyun short *sdest = dest; 90*4882a593Smuzhiyun const short *ssrc = src; 91*4882a593Smuzhiyun *--sdest = *--ssrc; 92*4882a593Smuzhiyun dest = sdest; 93*4882a593Smuzhiyun src = ssrc; 94*4882a593Smuzhiyun } 95*4882a593Smuzhiyun if (n & 1) { 96*4882a593Smuzhiyun char *cdest = dest; 97*4882a593Smuzhiyun const char *csrc = src; 98*4882a593Smuzhiyun *--cdest = *--csrc; 99*4882a593Smuzhiyun } 100*4882a593Smuzhiyun } 101*4882a593Smuzhiyun return xdest; 102*4882a593Smuzhiyun } 103*4882a593Smuzhiyun EXPORT_SYMBOL(memmove); 104