linux-l: fork() problem mit omniorb

Stefan Bund sbund at artec-berlin.com
Fr Nov 24 17:40:29 CET 2000


Hallo liste,

Ich hoffe, ihr seid jetzt von so einer langen, technischen Mail nicht
erschlagen ...

ich hatte schon mal so 'ne ähnliche Frage gestellt. Hier nochmal mit
mehr info. Ich verwende omniorb in C++ um einen CORBA basierten Server
zu implementieren.

Ich habe jetzt schon länger versucht meinen Server so zu schreiben,
das er selbst in den hintergrund geht, aber irgendwie klappt das
nicht: sobald ich fork()-e bleibt das Programm kurz nach dem fork()
hängen.

Ich habe hier mal den strace-output drangehängt, vielleicht hilft das
ja jemandem (der daemon hat jetzt eine --no-fork option, die einfach
die fork() anweisung überbrückt --- so testet sichs leichter):

Ablauf mit --no-fork:

  [...]
    stat("tmp/share/textures", {st_mode=S_IFDIR|0775, st_size=35, ...}) = 0
    stat("tmp/share/objects", {st_mode=S_IFDIR|0775, st_size=35, ...}) = 0
    stat("tmp/var/modells", {st_mode=S_IFDIR|0775, st_size=35, ...}) = 0
    open("tmp/run/dagserv", O_WRONLY|O_CREAT|O_TRUNC|0x8000, 0664) = 3
    close(3)                                = 0
    access("/dev/random", R_OK)             = 0
    umask(0167)                             = 02
    open("tmp/run/dagserv", O_WRONLY|O_CREAT|O_TRUNC|0x8000, 0664) = 3
    open("/dev/random", O_RDONLY|0x8000)    = 4
  [... vgl klammer (1) unten mit fork() ...]
 /  fstat(4, {st_mode=S_IFCHR|0444, st_rdev=makedev(1, 8), ...}) = 0
(1) old_mmap(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x40014000
 \  ioctl(4, TCGETS, 0xbffff2a8)            = -1 EINVAL (Invalid argument)
  []
    read(4, "\0\10\307\22\336\276\25\351\265\370\233\340^\'\21150\343"..., 4096) = 412
    fstat(3, {st_mode=S_IFREG|0664, st_size=0, ...}) = 0
  [marker für unten]
 /  old_mmap(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x40015000
 |  getpid()                                = 15757
 |  write(3, "12c70800 e915bede e09bf8b5 35892"..., 72) = 72
 |  write(3, "15757\n", 6)                  = 6
 |  close(3)                                = 0
 |  munmap(0x40015000, 4096)                = 0
 |  close(4)                                = 0
(2) munmap(0x40014000, 4096)                = 0
 |  umask(02)                               = 0167
 |  rt_sigaction(SIGPIPE, {SIG_IGN}, NULL, 8) = 0
 |  brk(0x807e000)                          = 0x807e000
 |  pipe([3, 4])                            = 0
 |  fn=0xf00, child_stack=0x807d5f0, flags=0, args=0x8clone()                                 = 15758
 |  write(4, "L\3265@\5\0\0\0\270/C@@\0\0\0X<C@\270+C@\0\20C@\f\0\0\0"..., 148) = 148
 \  rt_sigprocmask(SIG_SETMASK, NULL, [RT_0], 8) = 0
  [marker für unten]
    write(4, "\240\30D@\0\0\0\0X\364\377\277\254\210-@\250\265\7\10\0"..., 148) = 148
    rt_sigprocmask(SIG_SETMASK, NULL, [RT_0], 8) = 0
    rt_sigsuspend([] <unfinished ...>
    --- SIGRT_0 (Real-time signal 0) ---
    <... rt_sigsuspend resumed> )           = -1 EINTR (Interrupted system call)
    sigreturn()                             = ? (mask now [])
    rt_sigprocmask(SIG_SETMASK, NULL, [RT_0], 8) = 0
    write(4, "\240\30D@\0\0\0\0h\364\377\277\254\210-@\210\326\7\10\0"..., 148) = 148
    rt_sigprocmask(SIG_SETMASK, NULL, [RT_0], 8) = 0
    rt_sigsuspend([] <unfinished ...>
    --- SIGRT_0 (Real-time signal 0) ---
  [...]

Ablauf ohne --no-fork ist identisch bis auf die Tatsache, das kein
SIGRT_0-Signal auftritt und somit der Prozess unbegrenzt blockiert:

  [...]
    stat("tmp/share/textures", {st_mode=S_IFDIR|0775, st_size=35, ...}) = 0
    stat("tmp/share/objects", {st_mode=S_IFDIR|0775, st_size=35, ...}) = 0
    stat("tmp/var/modells", {st_mode=S_IFDIR|0775, st_size=35, ...}) = 0
    open("tmp/run/dagserv", O_WRONLY|O_CREAT|O_TRUNC|0x8000, 0664) = 3
    close(3)                                = 0
    access("/dev/random", R_OK)             = 0
  [... vgl. klammer (1) oben ohne fork() ...]
 /  fork()                                  = 15770
 |  [pid 15770] umask(0167)                 = 02
 |  [pid 15770] open("tmp/run/dagserv", O_WRONLY|O_CREAT|O_TRUNC|0x8000, 0664) = 3
(1) [pid 15770] open("/dev/random", O_RDONLY|0x8000) = 4
 |  [pid 15770] fstat(4, {st_mode=S_IFCHR|0444, st_rdev=makedev(1, 8), ...}) = 0
 |  [pid 15770] old_mmap(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1,[pid 15770] ioctl(4, TCGETS <unfinished ...>
 |  [pid 15769] _exit(0)                    = ?
 \  [pid 15770] <... ioctl resumed> , 0xbffff2a8) = -1 EINVAL (Invalid argument)
  []
    read(4, "C\221>P\5\22\223\325\30\313E\367\263\0373\227\347;\226"..., 4096) = 152
    fstat(3, {st_mode=S_IFREG|0664, st_size=0, ...}) = 0
  [... siehe klammer (2) oben...]
    write(4, "\240\30D@\0\0\0\0X\364\377\277\254\210-@\250\265\7\10\0"..., 148) = 148
    rt_sigprocmask(SIG_SETMASK, NULL, [RT_0], 8) = 0
    rt_sigsuspend([] <unfinished ...>

an dieser Stelle blockiert der Prozess dann dauerhaft. Kein SIGRT_0 :-(

Ich bin etwas irritiert, das hier ein real-time signal auftritt (so
würde ich SIGRT übersetzen). Was hat omniorb mit real-time zu tun????

Versteht jemand, was hier abgeht? Zur zeit helfe ich mir, indem ich
den Prozess einfach von der shell aus in den Hintergrund schicke. Das
ist aber eigentlich keine Lösung, da ist dann die Fehlerbehandlung im
daemon-Prozess etwas schlecht (der daemon soll eigentlich erst in den
Hintergrund gehen, wenn alle vorhersehbaren Fehler überprüft wurden).

Also falls jemand eine Idee hat, was ich machen soll ...

etwas ratlos,

Stefan.



Mehr Informationen über die Mailingliste linux-l