All of lore.kernel.org
 help / color / mirror / Atom feed
From: Jann Horn <jann-XZ1E9jl8jIdeoWH0uzbU5w@public.gmane.org>
To: "Michael Kerrisk (man-pages)"
	<mtk.manpages-Re5JQEeQqe8AvxtiuMwx3w@public.gmane.org>
Cc: linux-man-u79uwXL29TY76Z2rM5mHXA@public.gmane.org
Subject: Re: [PATCH] prctl.2: PR_SET_PDEATHSIG by orphan process
Date: Sun, 17 Jan 2016 19:15:45 +0100	[thread overview]
Message-ID: <20160117181545.GA11795@pc.thejh.net> (raw)
In-Reply-To: <56900BA1.6000708-Re5JQEeQqe8AvxtiuMwx3w@public.gmane.org>

[-- Attachment #1: Type: text/plain, Size: 6508 bytes --]

On Fri, Jan 08, 2016 at 08:18:57PM +0100, Michael Kerrisk (man-pages) wrote:
> Hi Jann,
> 
> On 01/08/2016 05:39 PM, Jann Horn wrote:
> > On Fri, Jan 08, 2016 at 05:21:55PM +0100, Michael Kerrisk (man-pages) wrote:
> >> Hi Jann,
> >>
> >> Your mail is a little cryptic. It would be best to start with
> >> a brief summary of your point--something like the text of your
> >> patch at the end of the mail.
> > 
> > Ok, will do that next time. I wanted to avoid duplicating the content.
> 
> But you did it again :-). See below.
> 
> >> On 01/06/2016 07:23 PM, Jann Horn wrote:
> >>> Proof:
> >>> In kernel/sys.c:
> >>>
> >>> 	case PR_SET_PDEATHSIG:
> >>> 		if (!valid_signal(arg2)) {
> >>> 			error = -EINVAL;
> >>> 			break;
> >>> 		}
> >>> 		me->pdeath_signal = arg2;
> >>> 		break;
> >>
> >> I don't understand how the code above relates to the point you
> >> want to make. (Or maybe you mean: "look, there's no check here
> >> to see that if the parent is already dead"; but it would help
> >> to state that explicitly).
> > 
> > Yes, that's what I meant.
> > 
> > 
> >>> Testcase:
> >>>
> >>> #include <sys/prctl.h>
> >>> #include <err.h>
> >>> #include <unistd.h>
> >>> #include <signal.h>
> >>> #include <stdio.h>
> >>>
> >>> void ponk(int s) {
> >>>   puts("ponk!");
> >>> }
> >>>
> >>> int main(void) {
> >>>   if (fork() == 0) {
> >>>     if (fork() == 0) {
> >>>       sleep(1);
> >>>       signal(SIGUSR1, ponk);
> >>>       prctl(PR_SET_PDEATHSIG, SIGUSR1, 0, 0, 0);
> >>>       sleep(1);
> >>>       return 0;
> >>>     }
> >>>     return 0;
> >>>   }
> >>>
> >>>   sleep(3);
> >>>   return 0;
> >>> }
> >>> ---
> >>>  man2/prctl.2 | 3 +++
> >>>  1 file changed, 3 insertions(+)
> >>>
> >>> diff --git a/man2/prctl.2 b/man2/prctl.2
> >>> index 5cea3bb..3dce8e9 100644
> >>> --- a/man2/prctl.2
> >>> +++ b/man2/prctl.2
> >>> @@ -670,6 +670,9 @@ In other words, the signal will be sent when that thread terminates
> >>>  (via, for example,
> >>>  .BR pthread_exit (3)),
> >>>  rather than after all of the threads in the parent process terminate.
> >>> +
> >>> +If the parent has already died by the time the parent death signal
> >>> +is set, the new parent death signal will not be sent.
> >>
> >> In a way, this seems almost obvious. But perhaps it is better to make the
> >> point explicitly, as you suggest. But, because there may have been a
> >> previous PR_SET_PDEATHSIG, I'd prefer something like this:
> >>
> >> [[
> >> If the caller's parent has already died by the time of this
> >> PR_SET_PDEATHSIG operation, the operation shall have no effect.
> >> ]]
> >>
> >> What do you think?
> > 
> > I don't think "no effect" would be strictly correct because weird stuff
> > happens on subreaper death - I'm not sure whether this is intended or a
> > bug though:
> 
> Pause. Please begin with a short explanation of what you're about to
> demonstrate with the following code.... As it is, I am (again) not at
> all clear about the point you are trying to make.
> 
> > $ cat deathsig2.c
> > #include <sys/prctl.h>
> > #include <err.h>
> > #include <unistd.h>
> > #include <signal.h>
> > #include <stdio.h>
> > 
> > void ponk(int s) {
> >   puts("ponk!");
> > }
> > 
> > int main(void) {
> >   if (fork() == 0) {
> >     prctl(PR_SET_CHILD_SUBREAPER, 1, 0, 0, 0);
> >     puts("enabled subreaper");
> >     if (fork() == 0) {
> >       if (fork() == 0) {
> >         sleep(1);
> >         puts("setting deathsig...");
> >         signal(SIGUSR1, ponk);
> >         prctl(PR_SET_PDEATHSIG, SIGUSR1, 0, 0, 0);
> >         sleep(2);
> >         return 0;
> >       }
> >       puts("parent will die now, causing reparent to subreaper");
> >       return 0;
> >     }
> >     sleep(2);
> >     puts("subreaper will die now");
> >     return 0;
> >   }
> >   sleep(4);
> >   return 0;
> > }
> > $ gcc -o deathsig2 deathsig2.c
> > $ cat deathsig3.c
> > #include <sys/prctl.h>
> > #include <err.h>
> > #include <unistd.h>
> > #include <signal.h>
> > #include <stdio.h>
> > 
> > void ponk(int s) {
> >   puts("ponk!");
> > }
> > 
> > int main(void) {
> >   if (fork() == 0) {
> >     prctl(PR_SET_CHILD_SUBREAPER, 1, 0, 0, 0);
> >     puts("enabled subreaper");
> >     if (fork() == 0) {
> >       if (fork() == 0) {
> >         puts("setting deathsig...");
> >         signal(SIGUSR1, ponk);
> >         prctl(PR_SET_PDEATHSIG, SIGUSR1, 0, 0, 0);
> >         sleep(3);
> >         return 0;
> >       }
> >       sleep(1);
> >       puts("parent will die now, causing reparent to subreaper");
> >       return 0;
> >     }
> >     sleep(2);
> >     puts("subreaper will die now");
> >     return 0;
> >   }
> >   sleep(4);
> >   return 0;
> > }
> > $ gcc -o deathsig3 deathsig3.c
> > $ ./deathsig2
> > enabled subreaper
> > parent will die now, causing reparent to subreaper
> > setting deathsig...
> > subreaper will die now
> > ponk!
> > $ ./deathsig3
> > enabled subreaper
> > setting deathsig...
> > parent will die now, causing reparent to subreaper
> > ponk!
> > subreaper will die now
> > $ 
> > 
> > I didn't manage to find the reason for that in the code.
> 
> The reason for *what*? I am none the wiser.... What do you
> see as anomalous in the above? Please explain, so I can
> follow you.
> 
> > Sorry, I probably should have tried to figure out the details of
> > this before sending a manpages patch.
> 
> FWIW, all of the above looks legitimate and expected to me, but
> again, I'm not sure, because you didn't explain your point, just
> showed some code...

Setting a parent death signal while the parent is still alive causes
a death signal to be sent when the parent dies, but no death signal
is sent on subsequent subreaper parent deaths.

Setting a parent death signal when the parent is already dead, as
far as I can tell, causes a death signal to be sent on the death of
the first subreaper - but not on further subreaper deaths after the
reported one. 

This means that the statement "If the caller's parent has already
died by the time of this PR_SET_PDEATHSIG operation, the operation
shall have no effect." would be false because the operation could
still have the effect of sending a signal when the subreaper dies.
deathsig2.c demonstrates this: PR_SET_PDEATHSIG is used after the
parent has died and still has the effect of causing a signal
handler invocation.

[-- Attachment #2: Digital signature --]
[-- Type: application/pgp-signature, Size: 819 bytes --]

      parent reply	other threads:[~2016-01-17 18:15 UTC|newest]

Thread overview: 6+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2016-01-06 18:23 [PATCH] prctl.2: PR_SET_PDEATHSIG by orphan process Jann Horn
     [not found] ` <1452104606-25569-1-git-send-email-jann-XZ1E9jl8jIdeoWH0uzbU5w@public.gmane.org>
2016-01-08 16:21   ` Michael Kerrisk (man-pages)
     [not found]     ` <568FE223.20209-Re5JQEeQqe8AvxtiuMwx3w@public.gmane.org>
2016-01-08 16:39       ` Jann Horn
     [not found]         ` <20160108163949.GA4313-J1fxOzX/cBvk1uMJSBkQmQ@public.gmane.org>
2016-01-08 19:18           ` Michael Kerrisk (man-pages)
     [not found]             ` <56900BA1.6000708-Re5JQEeQqe8AvxtiuMwx3w@public.gmane.org>
2016-01-17 18:13               ` Michael Kerrisk (man-pages)
2016-01-17 18:15               ` Jann Horn [this message]

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20160117181545.GA11795@pc.thejh.net \
    --to=jann-xz1e9jl8jideowh0uzbu5w@public.gmane.org \
    --cc=linux-man-u79uwXL29TY76Z2rM5mHXA@public.gmane.org \
    --cc=mtk.manpages-Re5JQEeQqe8AvxtiuMwx3w@public.gmane.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.