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 #define __IN_STRING_C
8 
9 #include <linux/module.h>
10 #include <linux/string.h>
11 
memmove(void * dest,const void * src,size_t n)12 void *memmove(void *dest, const void *src, size_t n)
13 {
14 	void *xdest = dest;
15 	size_t temp;
16 
17 	if (!n)
18 		return xdest;
19 
20 	if (dest < src) {
21 		if ((long)dest & 1) {
22 			char *cdest = dest;
23 			const char *csrc = src;
24 			*cdest++ = *csrc++;
25 			dest = cdest;
26 			src = csrc;
27 			n--;
28 		}
29 		if (n > 2 && (long)dest & 2) {
30 			short *sdest = dest;
31 			const short *ssrc = src;
32 			*sdest++ = *ssrc++;
33 			dest = sdest;
34 			src = ssrc;
35 			n -= 2;
36 		}
37 		temp = n >> 2;
38 		if (temp) {
39 			long *ldest = dest;
40 			const long *lsrc = src;
41 			temp--;
42 			do
43 				*ldest++ = *lsrc++;
44 			while (temp--);
45 			dest = ldest;
46 			src = lsrc;
47 		}
48 		if (n & 2) {
49 			short *sdest = dest;
50 			const short *ssrc = src;
51 			*sdest++ = *ssrc++;
52 			dest = sdest;
53 			src = ssrc;
54 		}
55 		if (n & 1) {
56 			char *cdest = dest;
57 			const char *csrc = src;
58 			*cdest = *csrc;
59 		}
60 	} else {
61 		dest = (char *)dest + n;
62 		src = (const char *)src + n;
63 		if ((long)dest & 1) {
64 			char *cdest = dest;
65 			const char *csrc = src;
66 			*--cdest = *--csrc;
67 			dest = cdest;
68 			src = csrc;
69 			n--;
70 		}
71 		if (n > 2 && (long)dest & 2) {
72 			short *sdest = dest;
73 			const short *ssrc = src;
74 			*--sdest = *--ssrc;
75 			dest = sdest;
76 			src = ssrc;
77 			n -= 2;
78 		}
79 		temp = n >> 2;
80 		if (temp) {
81 			long *ldest = dest;
82 			const long *lsrc = src;
83 			temp--;
84 			do
85 				*--ldest = *--lsrc;
86 			while (temp--);
87 			dest = ldest;
88 			src = lsrc;
89 		}
90 		if (n & 2) {
91 			short *sdest = dest;
92 			const short *ssrc = src;
93 			*--sdest = *--ssrc;
94 			dest = sdest;
95 			src = ssrc;
96 		}
97 		if (n & 1) {
98 			char *cdest = dest;
99 			const char *csrc = src;
100 			*--cdest = *--csrc;
101 		}
102 	}
103 	return xdest;
104 }
105 EXPORT_SYMBOL(memmove);
106