]> git.ipfire.org Git - thirdparty/glibc.git/commitdiff
Fix i386 memmove issue (bug 22644).
authorAndrew Senkevich <andrew.n.senkevich@gmail.com>
Fri, 23 Mar 2018 15:19:45 +0000 (16:19 +0100)
committerAndrew Senkevich <andrew.n.senkevich@gmail.com>
Fri, 23 Mar 2018 15:19:45 +0000 (16:19 +0100)
[BZ #22644]
* sysdeps/i386/i686/multiarch/memcpy-sse2-unaligned.S: Fixed
branch conditions.
* string/test-memmove.c (do_test2): New testcase.

ChangeLog
string/test-memmove.c
sysdeps/i386/i686/multiarch/memcpy-sse2-unaligned.S

index 18ed09e5cb31f049e3b75c106c17f5cad09a0cdd..afdb7663dd6ae7e9d30671ba188860a47795bd77 100644 (file)
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,11 @@
+2018-03-23  Andrew Senkevich  <andrew.senkevich@intel.com>
+           Max Horn  <max@quendi.de>
+
+       [BZ #22644]
+       * sysdeps/i386/i686/multiarch/memcpy-sse2-unaligned.S: Fixed
+       branch conditions.
+       * string/test-memmove.c (do_test2): New testcase.
+
 2018-03-22  Joseph Myers  <joseph@codesourcery.com>
 
        * sysdeps/generic/frame.h: Remove file.
index edc7a4c3bf65d9628cb5f0a0d7aac6a05c5039c0..64e3651ba40604e47ddf6d633f4d0aea4644f60a 100644 (file)
@@ -24,6 +24,7 @@
 # define TEST_NAME "memmove"
 #endif
 #include "test-string.h"
+#include <support/test-driver.h>
 
 char *simple_memmove (char *, const char *, size_t);
 
@@ -245,6 +246,60 @@ do_random_tests (void)
     }
 }
 
+static void
+do_test2 (void)
+{
+  size_t size = 0x20000000;
+  uint32_t * large_buf;
+
+  large_buf = mmap ((void*) 0x70000000, size, PROT_READ | PROT_WRITE,
+                   MAP_PRIVATE | MAP_ANON, -1, 0);
+
+  if (large_buf == MAP_FAILED)
+    error (EXIT_UNSUPPORTED, errno, "Large mmap failed");
+
+  if ((uintptr_t) large_buf > 0x80000000 - 128
+      || 0x80000000 - (uintptr_t) large_buf > 0x20000000)
+    {
+      error (0, 0, "Large mmap allocated improperly");
+      ret = EXIT_UNSUPPORTED;
+      munmap ((void *) large_buf, size);
+      return;
+    }
+
+  size_t bytes_move = 0x80000000 - (uintptr_t) large_buf;
+  size_t arr_size = bytes_move / sizeof (uint32_t);
+  size_t i;
+
+  FOR_EACH_IMPL (impl, 0)
+    {
+      for (i = 0; i < arr_size; i++)
+        large_buf[i] = (uint32_t) i;
+
+      uint32_t * dst = &large_buf[33];
+
+#ifdef TEST_BCOPY
+      CALL (impl, (char *) large_buf, (char *) dst, bytes_move);
+#else
+      CALL (impl, (char *) dst, (char *) large_buf, bytes_move);
+#endif
+
+      for (i = 0; i < arr_size; i++)
+       {
+         if (dst[i] != (uint32_t) i)
+           {
+             error (0, 0,
+                    "Wrong result in function %s dst \"%p\" src \"%p\" offset \"%zd\"",
+                    impl->name, dst, large_buf, i);
+             ret = 1;
+             break;
+           }
+       }
+    }
+
+  munmap ((void *) large_buf, size);
+}
+
 int
 test_main (void)
 {
@@ -284,6 +339,9 @@ test_main (void)
     }
 
   do_random_tests ();
+
+  do_test2 ();
+
   return ret;
 }
 
index 9c3bbe7e176c820891d694b3d8fea9d72d5ad303..9aa17de99c9c3415a9b5ac28fd9f1eb4457f916d 100644 (file)
@@ -72,7 +72,7 @@ ENTRY (MEMCPY)
        cmp     %edx, %eax
 
 # ifdef USE_AS_MEMMOVE
-       jg      L(check_forward)
+       ja      L(check_forward)
 
 L(mm_len_0_or_more_backward):
 /* Now do checks for lengths. We do [0..16], [16..32], [32..64], [64..128]
@@ -81,7 +81,7 @@ L(mm_len_0_or_more_backward):
        jbe     L(mm_len_0_16_bytes_backward)
 
        cmpl    $32, %ecx
-       jg      L(mm_len_32_or_more_backward)
+       ja      L(mm_len_32_or_more_backward)
 
 /* Copy [0..32] and return.  */
        movdqu  (%eax), %xmm0
@@ -92,7 +92,7 @@ L(mm_len_0_or_more_backward):
 
 L(mm_len_32_or_more_backward):
        cmpl    $64, %ecx
-       jg      L(mm_len_64_or_more_backward)
+       ja      L(mm_len_64_or_more_backward)
 
 /* Copy [0..64] and return.  */
        movdqu  (%eax), %xmm0
@@ -107,7 +107,7 @@ L(mm_len_32_or_more_backward):
 
 L(mm_len_64_or_more_backward):
        cmpl    $128, %ecx
-       jg      L(mm_len_128_or_more_backward)
+       ja      L(mm_len_128_or_more_backward)
 
 /* Copy [0..128] and return.  */
        movdqu  (%eax), %xmm0
@@ -132,7 +132,7 @@ L(mm_len_128_or_more_backward):
        add     %ecx, %eax
        cmp     %edx, %eax
        movl    SRC(%esp), %eax
-       jle     L(forward)
+       jbe     L(forward)
        PUSH (%esi)
        PUSH (%edi)
        PUSH (%ebx)
@@ -269,7 +269,7 @@ L(check_forward):
        add     %edx, %ecx
        cmp     %eax, %ecx
        movl    LEN(%esp), %ecx
-       jle     L(forward)
+       jbe     L(forward)
 
 /* Now do checks for lengths. We do [0..16], [0..32], [0..64], [0..128]
        separately.  */