Re: ospfd and ripd dump core on exit
Jan Klemkow <[email protected]> Tue, 5 May 2026 16:04:57 +0200
| Newsgroups | gmane.os.openbsd.bugs |
|---|---|
| Message-ID | <enf653xge7wrafdtgeyig2dq7x2a77upjgwj3b7nhkzk52fecq@3db3qdnx6op5> |
On Mon, Dec 08, 2025 at 10:04:21PM +0300, Alexander Mukhin wrote: > On Thu, Dec 04, 2025 at 04:51:55PM +0300, Alexander Mukhin wrote: > > >Synopsis: ospfd and ripd dump core on exit > > >Category: user > > >Environment: > > System : OpenBSD 7.8 > > Details : OpenBSD 7.8 (GENERIC) #54: Sun Oct 12 12:45:58 MDT 2025 > > [email protected]:/usr/src/sys/arch/amd64/compile/GENERIC > > > > Architecture: OpenBSD.amd64 > > Machine : amd64 > > >Description: > > ospfd and ripd dump core on exit when static redistribution is enabled > > >How-To-Repeat: > > # cat ospfd.conf > > redistribute static > > area 0.0.0.0 { > > interface vio1 > > } > > # route add ... > > # ospfd -d -v -f ospfd.conf > > ... > > ^C > > ... > > Segmentation fault (core dumped) > > > > # cat ripd.conf > > redistribute static > > interface vio1 > > # route add ... > > # ripd -d -v -f ripd.conf > > ... > > ^C > > ... > > Segmentation fault (core dumped) > > > > >Fix: > > The reason is the same in both cases - sending imsgs through > > closed pipes. Calling kr_shutdown() before closing pipes helps. > > The proper fix is probably something like Claudio Jeker did > > for ldpd. > > Patches: > > --- ospfd.c > +++ ospfd.c > @@ -313,6 +313,8 @@ > int status; > struct redistribute *r; > > + kr_shutdown(); > + > /* close pipes */ > imsgbuf_clear(&iev_ospfe->ibuf); > close(iev_ospfe->ibuf.fd); > @@ -324,7 +326,6 @@ > SIMPLEQ_REMOVE_HEAD(&ospfd_conf->redist_list, entry); > free(r); > } > - kr_shutdown(); > carp_demote_shutdown(); > > log_debug("waiting for children to terminate"); > > > --- ripd.c > +++ ripd.c > @@ -271,6 +271,8 @@ > pid_t pid; > int status; > > + kr_shutdown(); > + > /* close pipes */ > imsgbuf_clear(&iev_ripe->ibuf); > close(iev_ripe->ibuf.fd); > @@ -281,8 +283,6 @@ > LIST_REMOVE(i, entry); > if_del(i); > } > - > - kr_shutdown(); > > log_debug("waiting for children to terminate"); > do { > Thanks Alexander for your patch. I would suggest to the following diff. So, the code is more like the ospfe_shutdown() in ospfe.c. Closing the imsg buffer after disabling the timers, also prevents a race here, because the timer functions also dealing with imsg stuff. And the problem is also solved for ospf6d(8). ok? Index: usr.sbin/ospf6d/ospf6d.c =================================================================== RCS file: /cvs/src/usr.sbin/ospf6d/ospf6d.c,v diff -u -p -r1.61 ospf6d.c --- usr.sbin/ospf6d/ospf6d.c 21 Nov 2024 13:38:14 -0000 1.61 +++ usr.sbin/ospf6d/ospf6d.c 5 May 2026 12:21:52 -0000 @@ -301,12 +301,6 @@ ospfd_shutdown(void) pid_t pid; int status; - /* close pipes */ - imsgbuf_clear(&iev_ospfe->ibuf); - close(iev_ospfe->ibuf.fd); - imsgbuf_clear(&iev_rde->ibuf); - close(iev_rde->ibuf.fd); - control_cleanup(); kr_shutdown(); carp_demote_shutdown(); @@ -322,6 +316,12 @@ ospfd_shutdown(void) (pid == rde_pid) ? "route decision engine" : "ospf engine", WTERMSIG(status)); } while (pid != -1 || (pid == -1 && errno == EINTR)); + + /* close pipes */ + imsgbuf_clear(&iev_ospfe->ibuf); + close(iev_ospfe->ibuf.fd); + imsgbuf_clear(&iev_rde->ibuf); + close(iev_rde->ibuf.fd); free(iev_ospfe); free(iev_rde); Index: usr.sbin/ospfd/ospfd.c =================================================================== RCS file: /cvs/src/usr.sbin/ospfd/ospfd.c,v diff -u -p -r1.124 ospfd.c --- usr.sbin/ospfd/ospfd.c 21 Nov 2024 13:38:14 -0000 1.124 +++ usr.sbin/ospfd/ospfd.c 5 May 2026 12:21:52 -0000 @@ -313,12 +313,6 @@ ospfd_shutdown(void) int status; struct redistribute *r; - /* close pipes */ - imsgbuf_clear(&iev_ospfe->ibuf); - close(iev_ospfe->ibuf.fd); - imsgbuf_clear(&iev_rde->ibuf); - close(iev_rde->ibuf.fd); - control_cleanup(); while ((r = SIMPLEQ_FIRST(&ospfd_conf->redist_list)) != NULL) { SIMPLEQ_REMOVE_HEAD(&ospfd_conf->redist_list, entry); @@ -338,6 +332,12 @@ ospfd_shutdown(void) (pid == rde_pid) ? "route decision engine" : "ospf engine", WTERMSIG(status)); } while (pid != -1 || (pid == -1 && errno == EINTR)); + + /* close pipes */ + imsgbuf_clear(&iev_ospfe->ibuf); + close(iev_ospfe->ibuf.fd); + imsgbuf_clear(&iev_rde->ibuf); + close(iev_rde->ibuf.fd); free(iev_ospfe); free(iev_rde);