From aa6f54aa24c3b1cfb4f8864dafd0e1a135fdb7f4 Mon Sep 17 00:00:00 2001 From: Ingo Weinhold Date: Fri, 9 Oct 2009 03:07:11 +0000 Subject: [PATCH] Amended the {user,debug}_strlcpy() fix: Due to the strlcpy() semantics to always return the source string length, we can't really prevent an overflow of the source address. git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@33489 a95241bf-73f2-0310-859d-f6bbb57e9c96 --- src/system/kernel/debug/debug.cpp | 4 +++- src/system/kernel/vm/vm.cpp | 5 +++-- 2 files changed, 6 insertions(+), 3 deletions(-) diff --git a/src/system/kernel/debug/debug.cpp b/src/system/kernel/debug/debug.cpp index 5cbb748421..d1f98fd5f8 100644 --- a/src/system/kernel/debug/debug.cpp +++ b/src/system/kernel/debug/debug.cpp @@ -1559,6 +1559,8 @@ debug_strlcpy(char* to, const char* from, size_t size) // limit size to avoid address overflows size_t maxSize = std::min(size, ~(addr_t)0 - std::max((addr_t)from, (addr_t)to) + 1); + // NOTE: Since strlcpy() determines the length of \a from, the source + // address might still overflow. debug_strlcpy_parameters parameters = {to, from, maxSize}; @@ -1568,7 +1570,7 @@ debug_strlcpy(char* to, const char* from, size_t size) } // If we hit the address overflow boundary, fail. - if (parameters.result == maxSize && maxSize < size) + if (parameters.result >= maxSize && maxSize < size) return B_BAD_ADDRESS; return parameters.result; diff --git a/src/system/kernel/vm/vm.cpp b/src/system/kernel/vm/vm.cpp index d45c0671b4..7323e6d72e 100644 --- a/src/system/kernel/vm/vm.cpp +++ b/src/system/kernel/vm/vm.cpp @@ -5491,13 +5491,14 @@ user_strlcpy(char* to, const char* from, size_t size) // limit size to avoid address overflows size_t maxSize = std::min(size, ~(addr_t)0 - std::max((addr_t)from, (addr_t)to) + 1); - + // NOTE: Since arch_cpu_user_strlcpy() determines the length of \a from, + // the source address might still overflow. ssize_t result = arch_cpu_user_strlcpy(to, from, maxSize, &thread_get_current_thread()->fault_handler); // If we hit the address overflow boundary, fail. - if (result >= 0 && (size_t)result == maxSize && maxSize < size) + if (result >= 0 && (size_t)result >= maxSize && maxSize < size) return B_BAD_ADDRESS; return result;