diff options
author | 2013-06-15 18:51:44 +0000 | |
---|---|---|
committer | 2013-06-15 18:51:44 +0000 | |
commit | cda765abcdd837f8d89352d7d29ad5881ca71284 (patch) | |
tree | d7135599700df27c30cdb0a7cdbb8ff5d33084e6 /sys/lib/libkern/arch | |
parent | Don't return garbage in memcpy() but the original destination pointer. (diff) | |
download | wireguard-openbsd-cda765abcdd837f8d89352d7d29ad5881ca71284.tar.xz wireguard-openbsd-cda765abcdd837f8d89352d7d29ad5881ca71284.zip |
Correctly handle a length of zero in memcpy().
Return the original destination pointer in memcpy() and memmove().
Diffstat (limited to 'sys/lib/libkern/arch')
-rw-r--r-- | sys/lib/libkern/arch/alpha/memmove.S | 21 |
1 files changed, 14 insertions, 7 deletions
diff --git a/sys/lib/libkern/arch/alpha/memmove.S b/sys/lib/libkern/arch/alpha/memmove.S index 2a994c8ab1a..63ff77ca272 100644 --- a/sys/lib/libkern/arch/alpha/memmove.S +++ b/sys/lib/libkern/arch/alpha/memmove.S @@ -31,20 +31,27 @@ * Copy a bytes within the kernel's address space. The bcopy and memmove * variants handle overlapping regions, the memcpy variant does not. * - * void memcpy(char *to, char *from, size_t len); - * void memmove(char *to, char *from, size_t len); - * void bcopy(char *from, char *to, size_t len); + * void* memcpy(void *to, void *from, size_t len); + * void* memmove(void *to, void *from, size_t len); + * void bcopy(void *from, void *to, size_t len); */ LEAF(memcpy,3) - cmoveq zero,a0,t5 + /* Swap arguments, also saving the original `from' in v0 */ + cmoveq zero,a0,v0 cmoveq zero,a1,a0 - cmoveq zero,t5,a1 + cmoveq zero,v0,a1 + + /* Check for zero length */ + beq a2,bcopy_done + br bcopy_forward XLEAF(memmove,3) - cmoveq zero,a0,t5 + /* Swap arguments, also saving the original `from' in v0 */ + cmoveq zero,a0,v0 cmoveq zero,a1,a0 - cmoveq zero,t5,a1 + cmoveq zero,v0,a1 + XLEAF(bcopy,3) /* Check for zero length */ beq a2,bcopy_done |