diff options
author | Patrick Mooney <pmooney@pfmooney.com> | 2016-05-09 20:10:32 +0000 |
---|---|---|
committer | Patrick Mooney <pmooney@pfmooney.com> | 2016-05-09 21:20:02 +0000 |
commit | 27a01456dc8f0848242e768b7ff8c6e8d057b160 (patch) | |
tree | 16c738f4be0c9b02f6ec157e4ba7423900922a2a | |
parent | 8f9f8986fdd3d337ed7d2b6950d4362d82cbae06 (diff) | |
download | illumos-joyent-27a01456dc8f0848242e768b7ff8c6e8d057b160.tar.gz |
OS-5392 lxbrand thread race in clone(CLONE_VFORK)
Reviewed by: Jerry Jelinek <jerry.jelinek@joyent.com>
-rw-r--r-- | usr/src/lib/brand/lx/lx_brand/common/clone.c | 30 |
1 files changed, 15 insertions, 15 deletions
diff --git a/usr/src/lib/brand/lx/lx_brand/common/clone.c b/usr/src/lib/brand/lx/lx_brand/common/clone.c index f6cc2fff31..59037a38b8 100644 --- a/usr/src/lib/brand/lx/lx_brand/common/clone.c +++ b/usr/src/lib/brand/lx/lx_brand/common/clone.c @@ -425,16 +425,15 @@ lx_clone(uintptr_t p1, uintptr_t p2, uintptr_t p3, uintptr_t p4, uintptr_t p5) * path here. */ if (rval != 0) { - if (!IS_VFORK(flags) || rval < 0) { - /* - * Run the stack management postfork handler in - * the parent. If this was a vfork(2), we only - * run it in the parent if the fork operation - * failed; the vfork(2) child has already run - * it for our address space. - */ - lx_stack_postfork(); - } + /* + * Run the stack management postfork handler in the + * parent. In the CLONE_VFORK case, where it only + * needs to be performed once due to the shared address + * space, it is critical that this step is performed in + * the parent and not the child. The latter can result + * in un-woken threads blocked on lx_stack_list_lock. + */ + lx_stack_postfork(); /* * Since we've already forked, we can't do much if @@ -464,13 +463,14 @@ lx_clone(uintptr_t p1, uintptr_t p2, uintptr_t p3, uintptr_t p4, uintptr_t p5) * process. */ - /* - * Run the stack management postfork handler in the child. - */ - lx_stack_postfork(); - if (!IS_VFORK(flags)) { /* + * For non-vfork children run the stack management + * postfork handler. + */ + lx_stack_postfork(); + + /* * We must free the stacks and thread-specific data * objects for every thread except the one duplicated * from the parent by forkx(). |