From 8695be5049294c32c45ef69f8a500dd759f46079 Mon Sep 17 00:00:00 2001 From: Rene Gollent Date: Mon, 2 Jul 2012 14:41:31 -0400 Subject: [PATCH] Fix regressions in arch_cpu_user_strlcpy(). - repnz movsb turns out to not actually be a legal instruction, resulting in various strings being copied incorrectly, leading to random crashes in various places. Rework to use loop instead. Thanks to Alex Smith for helping review changes and offering improvements. - Minor cleanups. - Fixes #8650 properly. --- src/system/kernel/arch/x86/arch_x86.S | 27 +++++++++++++++++++-------- 1 file changed, 19 insertions(+), 8 deletions(-) diff --git a/src/system/kernel/arch/x86/arch_x86.S b/src/system/kernel/arch/x86/arch_x86.S index 58e20fc8cc..f731299222 100644 --- a/src/system/kernel/arch/x86/arch_x86.S +++ b/src/system/kernel/arch/x86/arch_x86.S @@ -276,19 +276,32 @@ FUNCTION(arch_cpu_user_strlcpy): /* Copy at most count - 1 bytes */ dec %ecx - /* move data by bytes */ + /* If count is now 0, skip straight to null terminating + as our loop will otherwise overflow */ + cmp $0,%ecx + jne .L_user_strlcpy_copy_begin + movb $0,(%edi) + jmp .L_user_strlcpy_source_count + +.L_user_strlcpy_copy_begin: cld - repnz +.L_user_strlcpy_copy_loop: + /* move data by bytes */ movsb + cmpb $0,-1(%esi) + je .L_user_strlcpy_copy_loop_done + loop .L_user_strlcpy_copy_loop - /* null terminate string */ - movb $0,(%edi) - dec %esi - +.L_user_strlcpy_copy_loop_done: /* check if we copied the entire source string */ cmp $0,%ecx jne .L_user_strlcpy_source_done +.L_user_strlcpy_zero_terminate: + /* null terminate string */ + movb $0,(%edi) + dec %esi + /* count remaining bytes in src */ .L_user_strlcpy_source_count: not %ecx @@ -297,11 +310,9 @@ FUNCTION(arch_cpu_user_strlcpy): scasb .L_user_strlcpy_source_done: - movl %esi,%eax subl 20(%esp),%eax subl $1,%eax - /* restore the old fault handler */ movl %ebx,(%edx)