Subject: lib/32609: seekdir blocks if pthread is linked
To: None <lib-bug-people@netbsd.org, gnats-admin@netbsd.org,>
From: None <akr@m17n.org>
List: netbsd-bugs
Date: 01/24/2006 05:00:00
>Number:         32609
>Category:       lib
>Synopsis:       seekdir blocks if pthread is linked
>Confidential:   no
>Severity:       non-critical
>Priority:       medium
>Responsible:    lib-bug-people
>State:          open
>Class:          sw-bug
>Submitter-Id:   net
>Arrival-Date:   Tue Jan 24 05:00:00 +0000 2006
>Originator:     Tanaka Akira
>Release:        NetBSD 3.0
>Organization:
AIST
>Environment:
NetBSD netbsd30.vmw 3.0 NetBSD 3.0 (GENERIC) #0: Mon Dec 19 01:04:02 UTC 2005  builds@works.netbsd.org:/home/builds/ab/netbsd-3-0-RELEASE/i386/200512182024Z-obj/home/builds/ab/netbsd-3-0-RELEASE/src/sys/arch/i386/compile/GENERIC i386

>Description:
seekdir blocks if pthread library is linked.

Since the backtrace contains pthread_mutex_lock, it seems some pthread related problem.

>How-To-Repeat:
It is reproducible as follows.

  % cat t.c
  #include <stdlib.h>
  #include <stdio.h>
  #include <dirent.h>

  int main()
  {
    DIR *dirp;
    struct dirent *ent;
    long pos;

    dirp = opendir(".");
    if (dirp == NULL) { perror("opendir"); exit(1); }

    ent = readdir(dirp);
    if (ent == NULL) { fprintf(stderr, "readdir returns NULL."); exit(1); }

    pos = telldir(dirp);

    fprintf(stderr, "pos: %ld\n", pos);

    ent = readdir(dirp);
    if (ent == NULL) { fprintf(stderr, "readdir returns NULL."); exit(1); }

    fprintf(stderr, "seekdir start\n");
    seekdir(dirp, pos);
    fprintf(stderr, "seekdir end\n");

    return 0;
  }
  % gcc -Wall t.c -lpthread
  % ./a.out 
  pos: 1
  seekdir start
  ^C

The backtrace is follows.

  % gdb a.out 
  GNU gdb 5.3nb1
  Copyright 2002 Free Software Foundation, Inc.
  GDB is free software, covered by the GNU General Public License, and you are
  welcome to change it and/or distribute copies of it under certain conditions.
  Type "show copying" to see the conditions.
  There is absolutely no warranty for GDB.  Type "show warranty" for details.
  This GDB was configured as "i386--netbsdelf"...(no debugging symbols found)...
  (gdb) run
  Starting program: /home/akr/chkbuild/tmp/build/ruby-trunk-pth/20060124T065508/a.out 
  (no debugging symbols found)...(no debugging symbols found)...
  pos: 1
  seekdir start
  ^C(no debugging symbols found)...
  Program received signal SIGINT, Interrupt.
  [Switching to LWP 1]
  0xbdb33ee7 in _sys___sigsuspend14 () from /usr/lib/libc.so.12
  (gdb) bt
  #0  0xbdb33ee7 in _sys___sigsuspend14 () from /usr/lib/libc.so.12
  #1  0xbdbdf004 in __sigsuspend14 () from /usr/lib/libpthread.so.0
  #2  0xbdbe3054 in pthread_mutex_lock () from /usr/lib/libpthread.so.0
  #3  0xbdbe2ee7 in pthread_mutex_lock () from /usr/lib/libpthread.so.0
  #4  0xbdba1137 in readdir () from /usr/lib/libc.so.12
  #5  0xbdba1018 in __seekdir () from /usr/lib/libc.so.12
  #6  0xbdb55358 in seekdir () from /usr/lib/libc.so.12
  #7  0x08048943 in main ()
  #8  0x08048686 in ___start ()
  (gdb) info threads 
    2 Thread 1 ()  0xbdb33ee7 in _sys___sigsuspend14 () from /usr/lib/libc.so.12
  * 1 LWP 1  0xbdb33ee7 in _sys___sigsuspend14 () from /usr/lib/libc.so.12
  (gdb) 

If pthread is not linked, it works fine.

  % gcc -Wall t.c          
  % ./a.out 
  pos: 1
  seekdir start
  seekdir end

>Fix: