From: Dave Martin <Dave.Martin@arm.com>
To: "Bae, Chang Seok" <chang.seok.bae@intel.com>
Cc: "mingo@kernel.org" <mingo@kernel.org>,
"linux-kernel@vger.kernel.org" <linux-kernel@vger.kernel.org>,
"hjl.tools@gmail.com" <hjl.tools@gmail.com>,
"bp@suse.de" <bp@suse.de>,
"tglx@linutronix.de" <tglx@linutronix.de>,
"linux-api@vger.kernel.org" <linux-api@vger.kernel.org>,
"libc-alpha@sourceware.org" <libc-alpha@sourceware.org>,
"x86@kernel.org" <x86@kernel.org>,
"luto@kernel.org" <luto@kernel.org>,
"Shankar, Ravi V" <ravi.v.shankar@intel.com>,
"Hansen, Dave" <dave.hansen@intel.com>,
"Luck, Tony" <tony.luck@intel.com>,
"Brown, Len" <len.brown@intel.com>,
"linux-arch@vger.kernel.org" <linux-arch@vger.kernel.org>,
"mpe@ellerman.id.au" <mpe@ellerman.id.au>
Subject: Re: [RFC PATCH 1/4] x86/signal: Introduce helpers to get the maximum signal frame size
Date: Mon, 12 Oct 2020 14:26:39 +0100 [thread overview]
Message-ID: <20201012132638.GC32292@arm.com> (raw)
In-Reply-To: <20ae46ae9b74036723ff7b9f731374f78536dc88.camel@intel.com>
On Thu, Oct 08, 2020 at 10:43:50PM +0000, Bae, Chang Seok wrote:
> On Wed, 2020-10-07 at 11:05 +0100, Dave Martin wrote:
> > On Tue, Oct 06, 2020 at 05:45:24PM +0000, Bae, Chang Seok wrote:
> > > On Mon, 2020-10-05 at 14:42 +0100, Dave Martin wrote:
> > > > On Tue, Sep 29, 2020 at 01:57:43PM -0700, Chang S. Bae wrote:
> > > > >
> > > > > +/*
> > > > > + * The FP state frame contains an XSAVE buffer which must be 64-byte aligned.
> > > > > + * If a signal frame starts at an unaligned address, extra space is required.
> > > > > + * This is the max alignment padding, conservatively.
> > > > > + */
> > > > > +#define MAX_XSAVE_PADDING 63UL
> > > > > +
> > > > > +/*
> > > > > + * The frame data is composed of the following areas and laid out as:
> > > > > + *
> > > > > + * -------------------------
> > > > > + * | alignment padding |
> > > > > + * -------------------------
> > > > > + * | (f)xsave frame |
> > > > > + * -------------------------
> > > > > + * | fsave header |
> > > > > + * -------------------------
> > > > > + * | siginfo + ucontext |
> > > > > + * -------------------------
> > > > > + */
> > > > > +
> > > > > +/* max_frame_size tells userspace the worst case signal stack size. */
> > > > > +static unsigned long __ro_after_init max_frame_size;
> > > > > +
> > > > > +void __init init_sigframe_size(void)
> > > > > +{
> > > > > + /*
> > > > > + * Use the largest of possible structure formats. This might
> > > > > + * slightly oversize the frame for 64-bit apps.
> > > > > + */
> > > > > +
> > > > > + if (IS_ENABLED(CONFIG_X86_32) ||
> > > > > + IS_ENABLED(CONFIG_IA32_EMULATION))
> > > > > + max_frame_size = max((unsigned long)SIZEOF_sigframe_ia32,
> > > > > + (unsigned long)SIZEOF_rt_sigframe_ia32);
> > > > > +
> > > > > + if (IS_ENABLED(CONFIG_X86_X32_ABI))
> > > > > + max_frame_size = max(max_frame_size, (unsigned long)SIZEOF_rt_sigframe_x32);
> > > > > +
> > > > > + if (IS_ENABLED(CONFIG_X86_64))
> > > > > + max_frame_size = max(max_frame_size, (unsigned long)SIZEOF_rt_sigframe);
> > > > > +
> > > > > + max_frame_size += fpu__get_fpstate_sigframe_size() + MAX_XSAVE_PADDING;
> > > >
> > > > For arm64, we round the worst-case padding up by one.
> > > >
> > >
> > > Yeah, I saw that. The ARM code adds the max padding, too:
> > >
> > > signal_minsigstksz = sigframe_size(&user) +
> > > round_up(sizeof(struct frame_record), 16) +
> > > 16; /* max alignment padding */
> > >
> > >
> > > https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/tree/arch/arm64/kernel/signal.c#n973
> > >
> > > > I can't remember the full rationale for this, but it at least seemed a
> > > > bit weird to report a size that is not a multiple of the alignment.
> > > >
> > >
> > > Because the last state size of XSAVE may not be 64B aligned, the (reported)
> > > sum of xstate size here does not guarantee 64B alignment.
> > >
> > > > I'm can't think of a clear argument as to why it really matters, though.
> > >
> > > We care about the start of XSAVE buffer for the XSAVE instructions, to be
> > > 64B-aligned.
> >
> > Ah, I see. That makes sense.
> >
> > For arm64, there is no additional alignment padding inside the frame,
> > only the padding inserted after the frame to ensure that the base
> > address is 16-byte aligned.
> >
> > However, I wonder whether people will tend to assume that AT_MINSIGSTKSZ
> > is a sensible (if minimal) amount of stack to allocate. Allocating an
> > odd number of bytes, or any amount that isn't a multiple of the
> > architecture's preferred (or mandated) stack alignment probably doesn't
> > make sense.
> >
> > AArch64 has a mandatory stack alignment of 16 bytes; I'm not sure about
> > x86.
>
> The x86 ABI looks to require 16-byte alignment (for both 32-/64-bit modes).
> FWIW, the 32-bit ABI got changed from 4-byte alignement.
>
> Thank you for brining up the point. Ack. The kernel is expected to return a
> 16-byte aligned size. I made this change after a discussion with H.J.:
>
> diff --git a/arch/x86/kernel/signal.c b/arch/x86/kernel/signal.c
> index c042236ef52e..52815d7c08fb 100644
> --- a/arch/x86/kernel/signal.c
> +++ b/arch/x86/kernel/signal.c
> @@ -212,6 +212,11 @@ do {
> \
> * Set up a signal frame.
> */
>
> +/* x86 ABI requires 16-byte alignment */
> +#define FRAME_ALIGNMENT 16UL
> +
> +#define MAX_FRAME_PADDING FRAME_ALIGNMENT - 1
> +
You might want () here, to avoid future surpsises.
> /*
> * Determine which stack to use..
> */
> @@ -222,9 +227,9 @@ static unsigned long align_sigframe(unsigned long sp)
> * Align the stack pointer according to the i386 ABI,
> * i.e. so that on function entry ((sp + 4) & 15) == 0.
> */
> - sp = ((sp + 4) & -16ul) - 4;
> + sp = ((sp + 4) & -FRAME_ALIGNMENT) - 4;
> #else /* !CONFIG_X86_32 */
> - sp = round_down(sp, 16) - 8;
> + sp = round_down(sp, FRAME_ALIGNMENT) - 8;
> #endif
> return sp;
> }
> @@ -404,7 +409,7 @@ static int __setup_rt_frame(int sig, struct ksignal
> *ksig,
> unsafe_put_sigcontext(&frame->uc.uc_mcontext, fp, regs, set,
> Efault);
> unsafe_put_sigmask(set, frame, Efault);
> user_access_end();
> -
> +
> if (copy_siginfo_to_user(&frame->info, &ksig->info))
> return -EFAULT;
>
> @@ -685,6 +690,8 @@ SYSCALL_DEFINE0(rt_sigreturn)
> * -------------------------
> * | fsave header |
> * -------------------------
> + * | alignment padding |
> + * -------------------------
> * | siginfo + ucontext |
> * -------------------------
> */
> @@ -710,7 +717,12 @@ void __init init_sigframe_size(void)
> if (IS_ENABLED(CONFIG_X86_64))
> max_frame_size = max(max_frame_size, (unsigned
> long)SIZEOF_rt_sigframe);
>
> + max_frame_size += MAX_FRAME_PADDING;
> +
> max_frame_size += fpu__get_fpstate_sigframe_size() +
> MAX_XSAVE_PADDING;
> +
> + /* Userspace expects an aligned size. */
> + max_frame_size = round_up(max_frame_size, FRAME_ALIGNMENT);
> }
[...]
Seems reasonable, I guess.
(I won't comment on the x86 ABI specifics.)
Cheers
---Dave
next prev parent reply other threads:[~2020-10-12 13:26 UTC|newest]
Thread overview: 31+ messages / expand[flat|nested] mbox.gz Atom feed top
2020-09-29 20:57 [RFC PATCH 0/4] x86: Improve Minimum Alternate Stack Size Chang S. Bae
2020-09-29 20:57 ` [RFC PATCH 1/4] x86/signal: Introduce helpers to get the maximum signal frame size Chang S. Bae
2020-10-05 13:42 ` Dave Martin
2020-10-06 17:45 ` Bae, Chang Seok
2020-10-07 10:05 ` Dave Martin
2020-10-08 22:43 ` Bae, Chang Seok
2020-10-12 13:26 ` Dave Martin [this message]
2020-09-29 20:57 ` [RFC PATCH 2/4] x86/elf: Support a new ELF aux vector AT_MINSIGSTKSZ Chang S. Bae
2020-09-29 20:57 ` [RFC PATCH 3/4] x86/signal: Prevent an alternate stack overflow before a signal delivery Chang S. Bae
2020-09-29 20:57 ` [RFC PATCH 4/4] selftest/x86/signal: Include test cases for validating sigaltstack Chang S. Bae
2020-10-05 13:45 ` [RFC PATCH 0/4] x86: Improve Minimum Alternate Stack Size Dave Martin
2020-10-05 21:17 ` H.J. Lu
2020-10-06 9:25 ` Dave Martin
2020-10-06 12:12 ` H.J. Lu
2020-10-06 15:18 ` H.J. Lu
2020-10-06 15:43 ` Dave Martin
2020-10-06 16:52 ` H.J. Lu
2020-10-06 15:25 ` Dave Martin
2020-10-06 15:33 ` Dave Hansen
2020-10-06 17:00 ` Dave Martin
2020-10-06 18:21 ` Florian Weimer
2020-10-07 10:19 ` Dave Martin
2020-10-06 18:30 ` Dave Hansen
2020-10-07 10:20 ` Dave Martin
2020-10-06 15:34 ` H.J. Lu
2020-10-06 16:55 ` Dave Martin
2020-10-06 17:44 ` H.J. Lu
2020-10-07 10:47 ` Dave Martin
2020-10-07 13:30 ` H.J. Lu
2020-10-07 15:45 ` Dave Martin
2020-10-07 17:43 ` H.J. Lu
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=20201012132638.GC32292@arm.com \
--to=dave.martin@arm.com \
--cc=bp@suse.de \
--cc=chang.seok.bae@intel.com \
--cc=dave.hansen@intel.com \
--cc=hjl.tools@gmail.com \
--cc=len.brown@intel.com \
--cc=libc-alpha@sourceware.org \
--cc=linux-api@vger.kernel.org \
--cc=linux-arch@vger.kernel.org \
--cc=linux-kernel@vger.kernel.org \
--cc=luto@kernel.org \
--cc=mingo@kernel.org \
--cc=mpe@ellerman.id.au \
--cc=ravi.v.shankar@intel.com \
--cc=tglx@linutronix.de \
--cc=tony.luck@intel.com \
--cc=x86@kernel.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.