On Sat, 24 May 2025 15:19:10 +0200, Christian Franke wrote:
If /proc/PID/maps is opened in parallel threads, the process PID may segfault.

Testcase:

$ uname -r
3.7.0-0.98.gb39b510c1ce6.x86_64

$ cat thrdopen.c
#include <fcntl.h>
#include <pthread.h>
#include <stdio.h>
#include <unistd.h>

static const char * name;

static void *worker(void *arg)
{
  for (int i = 0; i < 10000; i++) {
    putchar((int)(intptr_t)arg); fflush(stdout);
    int fd = open(name, O_RDONLY);
    if (fd < 0) {
      perror(name); break;
    }
    close(fd);
  }
  return NULL;
}

int main(int argc, char **argv)
{
  if (argc != 2)
    return 1;
  name = argv[1];
  pthread_t t;
  if (pthread_create(&t, NULL, worker, (void*)'-'))
    return 2;
  worker((void*)'+');
  pthread_join(t, NULL);
  return 0;
}

$ gcc -o thrdopen thrdopen.c

$ cygstart mintty - # start 2nd terminal

$ pstree -p
?(1)─┬─mintty(1146)───bash(1147)
     └─mintty(992)───bash(993)───pstree(1152)

$ ./thrdopen /proc/1147/maps # 2nd terminal closes
+-+-+-+-+--+-++--+-+-+-+-+-++-+-+-+-+-+-+-+/proc/1147/maps: No such file or directory
-/proc/1147/maps: No such file or directory

$ pstree -p
?(1)───mintty(992)───bash(993)───pstree(1154)


If the bash is run in strace, output is like this:
...
  155  536982 [main] bash 1179 select_stuff::wait: m 3, us 18446744073709551615, wmfo_timeout -1
[testcase run here]
--- Process 14992 (pid: 1179) thread 15200 exited with status 0xc0000005
--- Process 14992 thread 15024 exited with status 0xc0000005
--- Process 14992 thread 9340 exited with status 0xc0000005
--- Process 14992 thread 2504 exited with status 0xc0000005
--- Process 14992 thread 2136 exited with status 0xc0000005
--- Process 14992 thread 880 exited with status 0xc0000005
--- Process 14992 thread 6484 exited with status 0xc0000005
--- Process 14992 thread 16516 exited with status 0xc0000005
--- Process 14992 exited with status 0xc0000005

The last line may not appear and strace hangs then.

Problem is not reproducible with any of the other /proc/PID/* files.


A closer look shows that the problem is unrelated to thread safety. The segfault also occurs when the following command is run simultaneously in two terminals:

$ while cat /proc/1234/maps > /dev/null; do printf .; done
.............cat: /proc/1234/maps: No such file or directory

--
Regards,
Christian


--
Problem reports:      https://cygwin.com/problems.html
FAQ:                  https://cygwin.com/faq/
Documentation:        https://cygwin.com/docs.html
Unsubscribe info:     https://cygwin.com/ml/#unsubscribe-simple

Reply via email to