This is the mail archive of the glibc-bugs@sourceware.org mailing list for the glibc project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

[Bug string/19390] New: Integer overflow in strncat


https://sourceware.org/bugzilla/show_bug.cgi?id=19390

            Bug ID: 19390
           Summary: Integer overflow in strncat
           Product: glibc
           Version: 2.22
            Status: NEW
          Severity: normal
          Priority: P2
         Component: string
          Assignee: unassigned at sourceware dot org
          Reporter: cherepan at mccme dot ru
  Target Milestone: ---
             Flags: security+

Apparently, on x86_64 (and other archs?) the asm version of strncat has an
integer overflow similar to bug 19387.

sysdeps/x86_64/multiarch/strcat-sse2-unaligned.S is used on my machine. I
didn't look into the details but it looks like strncat(s1, s2, n) misbehave
when n is near SIZE_MAX, strlen(s2) >= 34 and s2 has specific offset.

For example, the program:

----------------------------------------------------------------------

#include <stdint.h>
#include <stdalign.h>
#include <string.h>
#include <stdio.h>

int main()
{
  alignas(64) char s[144];
  memset(s, 1, sizeof s);

  /* the first string... */
  char *s1 = s;             /* ...is at the start of the buffer */
  s1[0] = 0;                /* ...and is empty */

  /* the second string...  */
  char *s2 = s + 95;            /* ...starts as pos 95,  */
  memset(s2, 2, s + sizeof s - s2); /* ...filled with 2s for contrast */
  s2[33] = 0;                   /* ...and has the length 33 */

  printf("before:\n");
  for (int i = 0; i < 50; i++)
    printf("%x", (unsigned char)s[i]);
  printf("...\n");

  strncat(s1, s2, SIZE_MAX);

  printf("after:\n");
  for (int i = 0; i < 50; i++)
    printf("%x", (unsigned char)s[i]);
  printf("...\n");
  printf("%-33s^\n", "the string should end here");
}

----------------------------------------------------------------------

outputs this:

----------------------------------------------------------------------

before:
01111111111111111111111111111111111111111111111111...
after:
22222222222222222222222222222222202222211111111111...
the string should end here       ^

----------------------------------------------------------------------

Here, strncat put '\0' exactly where it should be but also copied 5 extra chars
from s2 into s1 after '\0'. In other cases it copies less chars than required.

Checked on x86_64:
- git master (glibc-2.22-616-g5537f46) -- failed;
- Debian jessie (glibc 2.19-18+deb8u1) -- failed;
- Debian wheezy (eglibc 2.13-38+deb7u8) -- ok.

Checked on x86_64 with gcc -m32:
- Debian jessie (glibc 2.19-18+deb8u1) -- failed;
- Debian wheezy (eglibc 2.13-38+deb7u8) -- ok.

I didn't look into the details of 32-bit version.

The bug can have evident security implications but using strncat with
n=SIZE_MAX seems rare hence filing it publicly.

-- 
You are receiving this mail because:
You are on the CC list for the bug.

Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]