Hi Alex, The feature is due to be merged in 5.11 so presumably we should wait until then. I have no updates for the patch; at this point I am hoping for comments (or a Reviewed-by) from Dave. I saw your s/.IR/.I/ and I will do that once I have another update for the patch. Peter On Fri, Dec 18, 2020 at 2:27 AM Alejandro Colomar (man-pages) <alx.manpages@xxxxxxxxx> wrote: > > Hi Peter, > > Linux 5.10 has been recently released. > Was this merged to 5.10 or 5.11? > Do you have any updates for this patch? > > Thanks, > > Alex > > On 11/18/20 3:04 PM, Alejandro Colomar (man-pages) wrote: > > > > > > On 11/18/20 12:42 PM, Alejandro Colomar (man-pages) wrote: > >> [[ Removed some CCs because gmail > >> didn't allow me to send it with so many CCs: > >> Kevin B., Andrey K., Helge D., David S. > >> ]] > >> > >> On 11/18/20 12:54 AM, Peter Collingbourne wrote: > >>> Signed-off-by: Peter Collingbourne <pcc@xxxxxxxxxx> > >>> --- > >>> These features are implemented in this patch series: > >>> > >> https://lore.kernel.org/linux-arm-kernel/cover.1605235762.git.pcc@xxxxxxxxxx/ > >>> which is still under review, so the patch should not be applied > >>> yet. > >>> > >>> Alejandro, thanks for the review. Since the patch was almost > >>> rewritten I didn't base this on your patch, instead I tried to > >>> use the correct formatting in this patch. > >> > >> Hi Peter, > >> > >> Fine. > >> See below a small fix. > > > > D'oh! > > Fixing the CCs I forgot to add the fix to the code. > > See below now. > > > >> > >> Cheers, > >> > >> Alex > >> > >>> > >>> v2: > >>> - fix formatting > >>> - address feedback from Dave > >>> > >>> man2/sigaction.2 | 125 +++++++++++++++++++++++++++++++++++++++++++++++ > >>> 1 file changed, 125 insertions(+) > >>> > >>> diff --git a/man2/sigaction.2 b/man2/sigaction.2 > >>> index 6a8142324..0e4236a43 100644 > >>> --- a/man2/sigaction.2 > >>> +++ b/man2/sigaction.2 > >>> @@ -250,6 +250,44 @@ This flag is meaningful only when establishing a > >> signal handler. > >>> .\" .I sa_sigaction > >>> .\" field was added in Linux 2.1.86.) > >>> .\" > >>> +.TP > >>> +.BR SA_UNSUPPORTED > >>> +Used to dynamically probe for flag bit support. > >>> +.IP > >>> +If an attempt to register a handler succeeds with this flag set in > >>> +.I act->sa_flags > >>> +alongside other flags that are potentially unsupported by the kernel, > >>> +and an immediately subsequent > >>> +.BR sigaction () > >>> +call specifying the same signal number n and with non-NULL > >>> +.I oldact > >>> +yields > >>> +.B SA_UNSUPPORTED > >>> +.I clear > >>> +in > >>> +.IR oldact->sa_flags , > >>> +then > >>> +.IR oldact->sa_flags > > > > s/.IR/.I/ > > > > There's no roman part there. > > > >>> +may be used as a bitmask > >>> +describing which of the potentially unsupported flags are, > >>> +in fact, supported. > >>> +See the section "Dynamically probing for flag bit support" > >>> +below for more details. > >>> +.TP > >>> +.BR SA_EXPOSE_TAGBITS " (since Linux 5.x)" > >>> +Normally, when delivering a signal, > >>> +an architecture-specific set of tag bits are cleared from the > >>> +.I si_addr > >>> +field of > >>> +.IR siginfo_t . > >>> +If this flag is set, > >>> +an architecture-specific subset of the tag bits will be preserved in > >>> +.IR si_addr . > >>> +.IP > >>> +Programs that need to be compatible with Linux versions older than 5.x > >>> +must use > >>> +.B SA_UNSUPPORTED > >>> +to probe for support. > >>> .SS The siginfo_t argument to a SA_SIGINFO handler > >>> When the > >>> .B SA_SIGINFO > >>> @@ -833,6 +871,93 @@ Triggered by a > >>> .BR seccomp (2) > >>> filter rule. > >>> .RE > >>> +.SS Dynamically probing for flag bit support > >>> +The > >>> +.BR sigaction () > >>> +call on Linux accepts unknown bits set in > >>> +.I act->sa_flags > >>> +without error. > >>> +The behavior of the kernel starting with Linux 5.x is that a second > >>> +.BR sigaction () > >>> +will clear unknown bits from > >>> +.IR oldact->sa_flags . > >>> +However, historically, a second > >>> +.BR sigaction () > >>> +call would typically leave those bits set in > >>> +.IR oldact->sa_flags . > >>> +.PP > >>> +This means that support for new flags cannot be detected > >>> +simply by testing for a flag in > >>> +.IR sa_flags , > >>> +and a program must test that > >>> +.B SA_UNSUPPORTED > >>> +has been cleared before relying on the contents of > >>> +.IR sa_flags . > >>> +.PP > >>> +Since the behavior of the signal handler cannot be guaranteed > >>> +unless the check passes, > >>> +it is wise to either block the affected signal > >>> +while registering the handler and performing the check in this case, > >>> +or where this is not possible, > >>> +for example if the signal is synchronous, to issue the second > >>> +.BR sigaction () > >>> +in the signal handler itself. > >>> +.PP > >>> +In kernels that do not support a specific flag, > >>> +the kernel's behavior is as if the flag was not set, > >>> +even if the flag was set in > >>> +.IR act->sa_flags . > >>> +.PP > >>> +The flags > >>> +.BR SA_NOCLDSTOP , > >>> +.BR SA_NOCLDWAIT , > >>> +.BR SA_SIGINFO , > >>> +.BR SA_ONSTACK , > >>> +.BR SA_RESTART , > >>> +.BR SA_NODEFER , > >>> +.BR SA_RESETHAND , > >>> +and, if defined by the architecture, > >>> +.B SA_RESTORER > >>> +may not be reliably probed for using this mechanism, > >>> +because they were introduced before Linux 5.x. > >>> +However, in general, programs may assume that these flags are supported, > >>> +since they have all been supported since Linux 2.6, > >>> +which was released in the year 2003. > >>> +.PP > >>> +The following example program exits with status 0 if > >>> +.B SA_EXPOSE_TAGBITS > >>> +is determined to be supported, and 1 otherwise. > >>> +.PP > >>> +.EX > >>> +#include <signal.h> > >>> +#include <stdio.h> > >>> +#include <unistd.h> > >>> + > >>> +void handler(int signo, siginfo_t *info, void *context) { > >>> + struct sigaction oldact; > >>> + if (sigaction(SIGSEGV, 0, &oldact) == 0 && > >>> + !(oldact.sa_flags & SA_UNSUPPORTED) && > >>> + (oldact.sa_flags & SA_EXPOSE_TAGBITS)) { > >>> + _exit(0); > >>> + } else { > >>> + _exit(1); > >>> + } > >>> +} > >>> + > >>> +int main(void) { > >>> + struct sigaction act = {}; > >>> + act.sa_flags = SA_SIGINFO | SA_UNSUPPORTED | SA_EXPOSE_TAGBITS; > >>> + act.sa_sigaction = handler; > >>> + if (sigaction(SIGSEGV, &act, 0) != 0) { > >>> + perror("sigaction"); > >>> + return 1; > >>> + } > >>> + > >>> + /* Force a SIGSEGV. */ > >>> + *(volatile int *)0 = 0; > >>> + return 1; > >>> +} > >>> +.EE > >>> .SH RETURN VALUE > >>> .BR sigaction () > >>> returns 0 on success; on error, \-1 is returned, and > >>> > > -- > Alejandro Colomar > Linux man-pages comaintainer; https://www.kernel.org/doc/man-pages/ > http://www.alejandro-colomar.es/