Commit | Line | Data |
---|---|---|
66d83ab3 GU |
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 | */ | |
1da177e4 | 6 | |
66d83ab3 GU |
7 | #include <linux/module.h> |
8 | #include <linux/string.h> | |
1da177e4 | 9 | |
66d83ab3 | 10 | void *memcpy(void *to, const void *from, size_t n) |
1da177e4 | 11 | { |
66d83ab3 | 12 | void *xto = to; |
423c01ea | 13 | size_t temp; |
1da177e4 | 14 | |
66d83ab3 GU |
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 | } | |
f230e80b GU |
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 | |
66d83ab3 GU |
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; | |
734c3ce3 GU |
46 | #if defined(CONFIG_M68000) || defined(CONFIG_COLDFIRE) |
47 | for (; temp; temp--) | |
48 | *lto++ = *lfrom++; | |
49 | #else | |
423c01ea | 50 | size_t temp1; |
66d83ab3 GU |
51 | asm volatile ( |
52 | " movel %2,%3\n" | |
53 | " andw #7,%3\n" | |
54 | " lsrl #3,%2\n" | |
55 | " negw %3\n" | |
56 | " jmp %%pc@(1f,%3:w:2)\n" | |
57 | "4: 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 | " movel %0@+,%1@+\n" | |
65 | "1: dbra %2,4b\n" | |
66 | " clrw %2\n" | |
67 | " subql #1,%2\n" | |
68 | " jpl 4b" | |
69 | : "=a" (lfrom), "=a" (lto), "=d" (temp), "=&d" (temp1) | |
70 | : "0" (lfrom), "1" (lto), "2" (temp)); | |
1da177e4 | 71 | #endif |
66d83ab3 GU |
72 | to = lto; |
73 | from = lfrom; | |
74 | } | |
75 | if (n & 2) { | |
76 | short *sto = to; | |
77 | const short *sfrom = from; | |
78 | *sto++ = *sfrom++; | |
79 | to = sto; | |
80 | from = sfrom; | |
81 | } | |
82 | if (n & 1) { | |
83 | char *cto = to; | |
84 | const char *cfrom = from; | |
85 | *cto = *cfrom; | |
86 | } | |
87 | return xto; | |
1da177e4 | 88 | } |
66d83ab3 | 89 | EXPORT_SYMBOL(memcpy); |