1 /* 2 * This file is subject to the terms and conditions of the GNU General Public 3 * License. See the file COPYING in the main directory of this archive 4 * for more details. 5 */ 6 7 #include <linux/module.h> 8 #include <linux/string.h> 9 10 void *memcpy(void *to, const void *from, size_t n) 11 { 12 void *xto = to; 13 size_t temp, temp1; 14 15 if (!n) 16 return xto; 17 if ((long)to & 1) { 18 char *cto = to; 19 const char *cfrom = from; 20 *cto++ = *cfrom++; 21 to = cto; 22 from = cfrom; 23 n--; 24 } 25 #if defined(CONFIG_M68000) 26 if ((long)from & 1) { 27 char *cto = to; 28 const char *cfrom = from; 29 for (; n; n--) 30 *cto++ = *cfrom++; 31 return xto; 32 } 33 #endif 34 if (n > 2 && (long)to & 2) { 35 short *sto = to; 36 const short *sfrom = from; 37 *sto++ = *sfrom++; 38 to = sto; 39 from = sfrom; 40 n -= 2; 41 } 42 temp = n >> 2; 43 if (temp) { 44 long *lto = to; 45 const long *lfrom = from; 46 #if defined(CONFIG_M68000) || defined(CONFIG_COLDFIRE) 47 for (; temp; temp--) 48 *lto++ = *lfrom++; 49 #else 50 asm volatile ( 51 " movel %2,%3\n" 52 " andw #7,%3\n" 53 " lsrl #3,%2\n" 54 " negw %3\n" 55 " jmp %%pc@(1f,%3:w:2)\n" 56 "4: movel %0@+,%1@+\n" 57 " movel %0@+,%1@+\n" 58 " movel %0@+,%1@+\n" 59 " movel %0@+,%1@+\n" 60 " movel %0@+,%1@+\n" 61 " movel %0@+,%1@+\n" 62 " movel %0@+,%1@+\n" 63 " movel %0@+,%1@+\n" 64 "1: dbra %2,4b\n" 65 " clrw %2\n" 66 " subql #1,%2\n" 67 " jpl 4b" 68 : "=a" (lfrom), "=a" (lto), "=d" (temp), "=&d" (temp1) 69 : "0" (lfrom), "1" (lto), "2" (temp)); 70 #endif 71 to = lto; 72 from = lfrom; 73 } 74 if (n & 2) { 75 short *sto = to; 76 const short *sfrom = from; 77 *sto++ = *sfrom++; 78 to = sto; 79 from = sfrom; 80 } 81 if (n & 1) { 82 char *cto = to; 83 const char *cfrom = from; 84 *cto = *cfrom; 85 } 86 return xto; 87 } 88 EXPORT_SYMBOL(memcpy); 89