Date: Thu, 09 May 2019 03:52:10 +0000 From: bugzilla-noreply@freebsd.org To: net@FreeBSD.org Subject: [Bug 233955] [panic] Page fault in in6_purgeaddr upon tun create/destroy (net/wireguard affected) Message-ID: <bug-233955-7501-PVyUe6bqkl@https.bugs.freebsd.org/bugzilla/> In-Reply-To: <bug-233955-7501@https.bugs.freebsd.org/bugzilla/> References: <bug-233955-7501@https.bugs.freebsd.org/bugzilla/>
next in thread | previous in thread | raw e-mail | index | archive | help
https://bugs.freebsd.org/bugzilla/show_bug.cgi?id=3D233955 --- Comment #33 from commit-hook@freebsd.org --- A commit references this bug: Author: kevans Date: Thu May 9 03:51:35 UTC 2019 New revision: 347378 URL: https://svnweb.freebsd.org/changeset/base/347378 Log: MFC r346602, r346670-r346671, r347183: tun/tap race fixes r346602: tun(4): Defer clearing TUN_OPEN until much later tun destruction will not continue until TUN_OPEN is cleared. There are br= ief moments in tunclose where the mutex is dropped and we've already cleared TUN_OPEN, so tun_destroy would be able to proceed while we're in the midd= le of cleaning up the tun still. tun_destroy should be blocked until these parts (address/route purges, mostly) are complete. r346670: tun/tap: close race between destroy/ioctl handler It seems that there should be a better way to handle this, but this seems= to be the more common approach and it should likely get replaced in all of t= he places it happens... Basically, thread 1 is in the process of destroying = the tun/tap while thread 2 is executing one of the ioctls that requires the tun/tap mutex and the mutex is destroyed before the ioctl handler can acquire it. This is only one of the races described/found in PR 233955. r346671: tun(4): Don't allow open of open or dying devices Previously, a pid check was used to prevent open of the tun(4); this work= s, but may not make the most sense as we don't prevent the owner process from opening the tun device multiple times. The potential race described near tun_pid should not be an issue: if a tun(4) is to be handed off, its fd has to have been sent via control mess= age or some other mechanism that duplicates the fd to the receiving process so that it may set the pid. Otherwise, the pid gets cleared when the original process closes it and you have no effective handoff mechanism. Close up another potential issue with handing a tun(4) off by not clobber= ing state if the closer isn't the controller anymore. If we want some state to be cleared, we should do that a little more surgically. Additionally, nothing prevents a dying tun(4) from being "reopened" in the middle of tun_destroy as soon as the mutex is unlocked, quickly leading t= o a bad time. Return EBUSY if we're marked for destruction, as well, and the consumer will need to deal with it. The associated character device will = be destroyed in short order. r347183: geom: fix initialization order There's a race between the initialization of devsoftc.mtx (by devinit) and the creation of the geom worker thread g_run_events, which calls devctl_queue_data_f. Both of those are initialized at SI_SUB_DRIVERS and SI_ORDER_FIRST, which means the geom worked thread can be created before the mutex has been initialized, leading to the panic below: wpanic: mtx_lock() of spin mutex (null) @ /usr/home/osstest/build.135317.build-amd64-freebsd/freebsd/sys/kern/subr_bu= s.c:620 cpuid =3D 3 time =3D 1 KDB: stack backtrace: db_trace_self_wrapper() at db_trace_self_wrapper+0x2b/frame 0xfffffe003b968710 vpanic() at vpanic+0x19d/frame 0xfffffe003b968760 panic() at panic+0x43/frame 0xfffffe003b9687c0 __mtx_lock_flags() at __mtx_lock_flags+0x145/frame 0xfffffe003b968810 devctl_queue_data_f() at devctl_queue_data_f+0x6a/frame 0xfffffe003b9688= 40 g_dev_taste() at g_dev_taste+0x463/frame 0xfffffe003b968a00 g_load_class() at g_load_class+0x1bc/frame 0xfffffe003b968a30 g_run_events() at g_run_events+0x197/frame 0xfffffe003b968a70 fork_exit() at fork_exit+0x84/frame 0xfffffe003b968ab0 fork_trampoline() at fork_trampoline+0xe/frame 0xfffffe003b968ab0 --- trap 0, rip =3D 0, rsp =3D 0, rbp =3D 0 --- KDB: enter: panic [ thread pid 13 tid 100029 ] Stopped at kdb_enter+0x3b: movq $0,kdb_why Fix this by initializing geom at SI_ORDER_SECOND instead of SI_ORDER_FIRST. PR: 233955 Changes: _U stable/11/ stable/11/sys/geom/geom.h stable/11/sys/net/if_tap.c stable/11/sys/net/if_tun.c _U stable/12/ stable/12/sys/geom/geom.h stable/12/sys/net/if_tap.c stable/12/sys/net/if_tun.c --=20 You are receiving this mail because: You are the assignee for the bug.=
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?bug-233955-7501-PVyUe6bqkl>