Hi,
Initially, this problem was discover with www/vimb. But I have isolated
it, and it seems related to glib+gio with/or librthread. The mail is
cross-posted to ports@ (if glib+gio is the problem) and bugs@ (if the
problem is with librthread).
I run openbsd -current (GENERIC.MP) under amd64.
For vimb, calling:
$ vimb -C "sh xterm"
will generate a "vimb.core" in cwd.
The segfault occurs at fork() (in librthead) in the child process (the
window of vimb stay here: it is the child that segfault).
Here a minimal c-file that reproduce the problem:
---- BEGIN test.c ----
/*
* cc test.c -o test `pkg-config -cflags -libs glib-2.0 gio-2.0`
*/
#include <stdio.h>
#include <stdlib.h>
#include <glib.h>
#include <gio/gio.h>
int main(int argc, char *argv) {
char *stdOut = NULL, *stdErr = NULL;
int status;
GError *error = NULL;
g_tls_file_database_new("/etc/ssl/cert.pem", &error);
if (error) {
printf("could not load ssl database: %s\n", error->message);
g_error_free(error);
return(EXIT_FAILURE);
}
if (FALSE == g_spawn_command_line_sync("xterm", &stdOut, &stdErr,
&status, &error)) {
printf("can't run cmd: %s\n", error ? error->message :
"(null)");
g_clear_error(&error);
return(EXIT_FAILURE);
}
return(EXIT_SUCCESS);
}
---- END test.c ----
Here a commented gdb session (and an explaination below):
$ gdb ./test
## the segfault occurs in child, so follow the child
(gdb) set follow-fork-mode child
## track when the "bad data" is setted
(gdb) br pthread_atfork
Function "pthread_atfork" not defined.
Make breakpoint pending on future shared library load? (y or [n]) y
Breakpoint 1 (pthread_atfork) pending.
## run the program
(gdb) r
Starting program: /home/semarie/tmp/src/test-gio/test
Breakpoint 2 at 0x10e3aaf73840: file /usr/src/lib/librthread/rthread_fork.c,
line 179.
Pending breakpoint "pthread_atfork" resolved
## the "bad data" will be 0x10e356d3ae40 (child argument)
## the backtrace don't saw useful information... be we are somewhere in
## g_tls_file_database_new() call (when loading giomodule for tls).
Breakpoint 2, pthread_atfork (prepare=0, parent=0, child=0x10e356d3ae40) at
/usr/src/lib/librthread/rthread_fork.c:179
179 {
(gdb) bt
#0 pthread_atfork (prepare=0, parent=0, child=0x10e356d3ae40) at
/usr/src/lib/librthread/rthread_fork.c:179
#1 0x000010e3aaf7128e in pthread_once (once_control=0x10e356f55f40,
init_routine=0x10e356d3aef0)
at /usr/src/lib/librthread/rthread_once.c:26
#2 0x000010e356d08eae in ?? ()
#3 0x0000000000000000 in ?? ()
## the "bad data" is not bad here: we could access it.
(gdb) print *0x10e356d3ae40
$1 = 1761971016
## there is some others call to pthread_atfork, skip them
(gdb) disable
(gdb) continue
Continuing.
[New process 21972]
Program received signal SIGSEGV, Segmentation fault.
[Switching to thread 1028857]
0x000010e356d3ae40 in ?? ()
## ok, we try to access the "bad data"
## we are *after* the fork occurs (see New process)
(gdb) bt
#0 0x000010e356d3ae40 in ?? ()
#1 0x000010e3aaf73afb in fork () at /usr/src/lib/librthread/rthread_fork.c:160
#2 0x000010e368f2b72c in fork_exec_with_pipes () from
/usr/local/lib/libglib-2.0.so.4200.0
#3 0x000010e368f2c55c in g_spawn_sync () from
/usr/local/lib/libglib-2.0.so.4200.0
#4 0x000010e368f2ca6a in g_spawn_command_line_sync () from
/usr/local/lib/libglib-2.0.so.4200.0
#5 0x000010e0b9200fbb in main () from /home/semarie/tmp/src/test-gio/test
## the "bad data" is not accessible
(gdb) print *0x000010e356d3ae40
Cannot access memory at address 0x000010e356d3ae40
Somewhere in loading some giomodule in g_tls_file_database_new call,
pthread_atfork is called with child=0x10e356d3ae40. At this time, the
memory address is accessible (gdb print command works).
When g_spawn_command_line_sync is called, after the fork (we are in the
child process), the memory address 0x10e356d3ae40 is not accessible
anymore.
I don't known where to search now... the problem could be related to
librthread, or the use of glib+gio. Any help is welcome.
Thanks.
--
Sébastien Marie