1 /* SPDX-License-Identifier: GPL-2.0-only */
3 * This file is derived from memcpy_32.c in the Linux kernel.
10 void *memmove(void *dest
, const void *src
, size_t n
)
12 int d0
, d1
, d2
, d3
, d4
, d5
;
15 #if (ENV_ROMSTAGE && CONFIG(ASAN_IN_ROMSTAGE)) || \
16 (ENV_RAMSTAGE && CONFIG(ASAN_IN_RAMSTAGE))
17 check_memory_region((unsigned long)src
, n
, false, _RET_IP_
);
18 check_memory_region((unsigned long)dest
, n
, true, _RET_IP_
);
22 /* Handle more 16bytes in loop */
26 /* Decide forward/backward copy mode */
31 * movs instruction have many startup latency
32 * so we handle small size by general register.
37 * movs instruction is only good for aligned case.
47 * We gobble 16byts forward in each loop.
59 "lea 0x10(%1), %1\n\t"
60 "lea 0x10(%2), %2\n\t"
66 * Handle data forward by movs.
70 "mov -4(%1, %0), %3\n\t"
71 "lea -4(%2, %0), %4\n\t"
77 * Handle data backward by movs.
83 "lea -4(%1, %0), %1\n\t"
84 "lea -4(%2, %0), %2\n\t"
93 * Start to prepare for backward copy.
105 * Calculate copy position to tail.
113 * We gobble 16byts backward in each loop.
118 "mov -1*4(%1), %3\n\t"
119 "mov -2*4(%1), %4\n\t"
120 "mov %3, -1*4(%2)\n\t"
121 "mov %4, -2*4(%2)\n\t"
122 "mov -3*4(%1), %3\n\t"
123 "mov -4*4(%1), %4\n\t"
124 "mov %3, -3*4(%2)\n\t"
125 "mov %4, -4*4(%2)\n\t"
126 "lea -0x10(%1), %1\n\t"
127 "lea -0x10(%2), %2\n\t"
130 * Calculate copy position to head.
137 * Move data from 8 bytes to 15 bytes.
143 "mov 0*4(%1), %3\n\t"
144 "mov 1*4(%1), %4\n\t"
145 "mov -2*4(%1, %0), %5\n\t"
146 "mov -1*4(%1, %0), %1\n\t"
148 "mov %3, 0*4(%2)\n\t"
149 "mov %4, 1*4(%2)\n\t"
150 "mov %5, -2*4(%2, %0)\n\t"
151 "mov %1, -1*4(%2, %0)\n\t"
155 * Move data from 4 bytes to 7 bytes.
161 "mov 0*4(%1), %3\n\t"
162 "mov -1*4(%1, %0), %4\n\t"
163 "mov %3, 0*4(%2)\n\t"
164 "mov %4, -1*4(%2, %0)\n\t"
168 * Move data from 2 bytes to 3 bytes.
174 "movw 0*2(%1), %%dx\n\t"
175 "movw -1*2(%1, %0), %%bx\n\t"
176 "movw %%dx, 0*2(%2)\n\t"
177 "movw %%bx, -1*2(%2, %0)\n\t"
181 * Move data for 1 byte.
187 "movb (%1), %%cl\n\t"
188 "movb %%cl, (%2)\n\t"
191 : "=&c" (d0
), "=&S" (d1
), "=&D" (d2
),
192 "=r" (d3
), "=r" (d4
), "=r"(d5
)