Bug#495007: libc6: getaddrinfo_a causes SetFault in amd64 version

2008-08-13 Thread Matthew Von-Maszewski

Package: libc6
Version: 2.7-13
Severity: important
Tags: patch


getaddrinfo_a creates a segfault in its worker thread due to the stack  
size being too small.  Segfault happens here:


  Program received signal SIGSEGV, Segmentation fault.
  [Switching to Thread 0x40003950 (LWP 25753)]
  __res_vinit (statp=0x40003dc8, preinit=0) at res_init.c:179
  179 statp->id = res_randomid();

Upon entering __res_vinit, the stack pointer goes into the 0x1000 byte  
guard region at the bottom of the thread's segment.
The call into res_randomid causes the segment violation.  The code in  
res_randomid is never reached.


Here is a sample program to tickle the bug:

#include 
#include 
#include 

int
main(void)
{
int ret_val;
struct sigevent sig;
struct gaicb gaistruct;

memset(&gaistruct, 0, sizeof(gaistruct));
struct gaicb *gptr[1];
gptr[0] = &gaistruct;
memset(&sig, 0, sizeof(sig));
gptr[0]->ar_name = "a";
sig.sigev_notify = SIGEV_NONE;
ret_val = getaddrinfo_a(GAI_WAIT, gptr, 1, &sig);

return 0;
}


Root cause of the bug is in debian/linuxthreads/sysdeps/pthread/ 
gai_misc.h.  The code sets the stack size for

the worker thread to the pthreads minimum.  This is just not enough.


 System Information:
Debian Release: lenny/sid
  APT prefers testing
  APT policy: (500, 'testing')
Architecture: amd64 (x86_64)

Kernel: Linux 2.6.22.6091807 (SMP w/4 CPU cores)
Locale: LANG=en_US.UTF-8, LC_CTYPE=en_US.UTF-8 (charmap=UTF-8)
Shell: /bin/sh linked to /bin/bash

Versions of packages libc6 depends on:
ii  libgcc1   1:4.3.1-2  GCC support library

libc6 recommends no packages.

Versions of packages libc6 suggests:
pn  glibc-doc  (no description available)
ii  locales   2.7-13 GNU C Library: National  
Language (


-- debconf information excluded


--- glibc-2.7/resolv/gai_misc.c.orig2008-08-13 14:44:03.0 -0400
+++ glibc-2.7/resolv/gai_misc.c 2008-08-13 14:44:28.0 -0400
@@ -39,7 +39,6 @@
   /* Make sure the thread is created detached.  */
   pthread_attr_init (&attr);
   pthread_attr_setdetachstate (&attr, PTHREAD_CREATE_DETACHED);
-  pthread_attr_setstacksize(&attr, 32768);

   int ret = pthread_create (threadp, &attr, tf, arg);

--- ./glibc-2.7/nptl/sysdeps/pthread/gai_misc.h.orig	2008-08-13  
14:46:57.0 -0400
+++ ./glibc-2.7/nptl/sysdeps/pthread/gai_misc.h	2008-08-13  
14:47:24.0 -0400

@@ -96,8 +96,8 @@
   pthread_attr_init (&attr);
   pthread_attr_setdetachstate (&attr, PTHREAD_CREATE_DETACHED);

-  /* The helper thread needs only very little resources.  */
-  (void) pthread_attr_setstacksize (&attr, PTHREAD_STACK_MIN);
+  /* The helper thread needs only very little resources - but more  
than PTHREAD_STACK_MIN.  */

+  (void) pthread_attr_setstacksize (&attr, 32768);

   /* Block all signals in the helper thread.  To do this thoroughly we
  temporarily have to block all signals here.  */





--
To UNSUBSCRIBE, email to [EMAIL PROTECTED]
with a subject of "unsubscribe". Trouble? Contact [EMAIL PROTECTED]



Bug#495007: libc6: getaddrinfo_a causes SetFault in amd64 version

2008-08-13 Thread Matthew Von-Maszewski

Aurelien,

I doubt "linuxthreads" is anything but an old directory being reused.   
The file gai_misc.h appears in two places.  The one I mention below in  
the debian and another in the ./resolve directory.  The debian tree  
version appears to be someone's attempt at optimizing memory usage on  
the secondary thread.  The debian version overrides the libc/resolve  
version. The secondary thread is created by a conventional pthreads  
call (again unrelated to "linuxthreads").


The reduced stack size is now being pounded by what appears to be a  
ton of relatively new getaddrinfo code.  __res_vinit() has a large  
buffer it takes out of the stack.  It makes sense that the stack is  
now to small.


I ask that you give the bug serious consideration as written.  I  
followed this through from several angles:  register analysis, note of  
mmap/mprotect commands in strace, gdb si stepping, and finally code  
changes with unit tests.


Thanks,
Matthew


On Aug 13, 2008, at 7:38 PM, Aurelien Jarno wrote:


On Wed, Aug 13, 2008 at 02:53:44PM -0400, Matthew Von-Maszewski wrote:

Package: libc6
Version: 2.7-13
Severity: important
Tags: patch


getaddrinfo_a creates a segfault in its worker thread due to the  
stack

size being too small.  Segfault happens here:

 Program received signal SIGSEGV, Segmentation fault.
 [Switching to Thread 0x40003950 (LWP 25753)]
 __res_vinit (statp=0x40003dc8, preinit=0) at res_init.c:179
 179 statp->id = res_randomid();

Upon entering __res_vinit, the stack pointer goes into the 0x1000  
byte

guard region at the bottom of the thread's segment.
The call into res_randomid causes the segment violation.  The code in
res_randomid is never reached.

Here is a sample program to tickle the bug:

#include 
#include 
#include 

int
main(void)
{
int ret_val;
struct sigevent sig;
struct gaicb gaistruct;

memset(&gaistruct, 0, sizeof(gaistruct));
struct gaicb *gptr[1];
gptr[0] = &gaistruct;
memset(&sig, 0, sizeof(sig));
gptr[0]->ar_name = "a";
sig.sigev_notify = SIGEV_NONE;
ret_val = getaddrinfo_a(GAI_WAIT, gptr, 1, &sig);

return 0;
}


Root cause of the bug is in debian/linuxthreads/sysdeps/pthread/
gai_misc.h.  The code sets the stack size for


Are you kidding? linuxthreads is not used on amd64 for a long time.  
Given

this code is not even compiled on amd64, it can't be the root of the
problem.

--
 .''`.  Aurelien Jarno  | GPG: 1024D/F1BCDB73
: :' :  Debian developer   | Electrical Engineer
`. `'   [EMAIL PROTECTED] | [EMAIL PROTECTED]
  `-people.debian.org/~aurel32 | www.aurel32.net






--
To UNSUBSCRIBE, email to [EMAIL PROTECTED]
with a subject of "unsubscribe". Trouble? Contact [EMAIL PROTECTED]



Bug#495007: libc6: getaddrinfo_a causes SetFault in amd64 version

2008-08-13 Thread Matthew Von-Maszewski

Aurelien,

I can truly appreciate your hesitation with this bug report.  I can  
see how stupid this must look from your view point.


May I suggest this:

- verify whether or not debian/linuxthreads/sysdeps/pthread/gai_misc.h  
really contributes to a build.  Simply put garbage characters in the  
file and run a build.  If our analysis is correct, your build will  
fail.  We saw the file being used.


- try the test program contributed by Jon.  Try it even if you have a  
32 bit box.  The size of stack overflow is large enough that I suspect  
the amd64 is not really a key issue.


- we have a highly reproducible case.  Ask for any and all supporting  
data.  I can provide it:  register snap shots by frame, disassembly  
step through/to the crash point, etc.  I can be a resource.


Matthew



On Aug 13, 2008, at 9:10 PM, Aurelien Jarno wrote:


On Wed, Aug 13, 2008 at 08:23:31PM -0400, Matthew Von-Maszewski wrote:

Aurelien,

I doubt "linuxthreads" is anything but an old directory being reused.
The file gai_misc.h appears in two places.  The one I mention below  
in

the debian and another in the ./resolve directory.  The debian tree
version appears to be someone's attempt at optimizing memory usage on
the secondary thread.  The debian version overrides the libc/resolve
version. The secondary thread is created by a conventional pthreads
call (again unrelated to "linuxthreads").


I don't understand why you are speaking about a debian version, debian
does not patch this file, so there is nothing about optimizing memory
usage.


The reduced stack size is now being pounded by what appears to be a
ton of relatively new getaddrinfo code.  __res_vinit() has a large
buffer it takes out of the stack.  It makes sense that the stack is
now to small.

I ask that you give the bug serious consideration as written.  I


I haven't found yet a time to get a closer look, but your analysis  
seems

to be wrong given that:
- we are not using the linuxthreads anymore
- we do not change gai_misc.h

I'll have a closer look tomorrow.

--
 .''`.  Aurelien Jarno  | GPG: 1024D/F1BCDB73
: :' :  Debian developer   | Electrical Engineer
`. `'   [EMAIL PROTECTED] | [EMAIL PROTECTED]
  `-people.debian.org/~aurel32 | www.aurel32.net






--
To UNSUBSCRIBE, email to [EMAIL PROTECTED]
with a subject of "unsubscribe". Trouble? Contact [EMAIL PROTECTED]