Jörg Walter wrote: > Hi! > > I have found a bug where qemu would sit in an endless loop whenever "-smb" > was > enabled and accessed. It is probably the same problem some people in the user > forums talk about, and here's my analysis and fix: > > On glibc systems with NPTL, fork() is not atomic with regard to signals, > while > on non-NPTL-systems, it is. This behaviour is considered to be correct by the > libc developers, as no relevant spec forbids this behaviour. > > See this thread for details: > http://sourceware.org/ml/libc-hacker/2007-02/msg00009.html > > In qemu, accessing the SMB ip-address causes the slirp code to issue a fork > in > slirp/misc.c, which hangs, as we are in mid-emulation and SIGALARM signals > come in at a high rate, probably triggering the above mentioned behaviour. > > This patch solves the problem by temporarily blocking all signals until the > fork is over. It doesn't unblock signals in the child, as I assume that > executing the server program will care for that anyways. It works for me, > finally I can access "-smb"-folders again. > > -- > CU > Jörg
> --- slirp/misc.c 2007-08-27 10:30:20.000000000 +0200 > +++ slirp/misc.c.new 2007-08-27 10:29:50.000000000 +0200 > @@ -313,6 +313,7 @@ > int opt; > int master; > char *argv[256]; > + int mask; > #if 0 > char buff[256]; > #endif > @@ -346,8 +347,10 @@ > } > } > > + mask = sigsetmask(~0); > switch(fork()) { > case -1: > + sigsetmask(mask); > lprint("Error: fork failed: %s\n", strerror(errno)); > close(s); > if (do_pty == 2) > @@ -426,6 +429,7 @@ > exit(1); > > default: > + sigsetmask(mask); > if (do_pty == 2) { > close(s); > so->s = master; Could you rewrite this using pthread_sigmask, to make it thread safe? Thiemo