Pointer Authentication (PAuth) is a security feature introduced in ARMv8.3.
It introduces instructions to sign addresses and later check for potential
corruption using a second modifier value and one of a set of keys. The
signature, in the form of the Pointer Authentication Code (PAC), is stored
in some of the top unused bits of the virtual address (e.g. [54: 49] if
TBID0 is enabled and TnSZ is set to use a 48 bit VA space). A set of
controls are present to enable/disable groups of instructions (which use
certain keys) for compatibility with libraries that do not utilize the
feature. PAuth is used to verify the integrity of return addresses on the
stack with less memory than the stack canary.
This patchset adds kselftests to verify the kernel's configuration of the
feature and its runtime behaviour. There are 7 tests which verify that:
* an authentication failure leads to a SIGSEGV
* the data/instruction instruction groups are enabled
* the generic instructions are enabled
* all 5 keys are unique for a single thread
* exec() changes all keys to new unique ones
* context switching preserves the 4 data/instruction keys
* context switching preserves the generic keys
The tests have been verified to work on qemu without a working PAUTH
Implementation and on ARM's FVP with a full or partial PAuth
implementation.
Note: This patchset is only verified for ARMv8.3 and there will be some
changes required for ARMv8.6. More details can be found here [1]. Once
ARMv8.6 PAuth is merged the first test in this series will required to be
updated.
[1] https://lore.kernel.org/linux-arm-kernel/1597734671-23407-1-git-send-email-…
Cc: Shuah Khan <shuah(a)kernel.org>
Cc: Catalin Marinas <catalin.marinas(a)arm.com>
Cc: Will Deacon <will(a)kernel.org>
Signed-off-by: Boyan Karatotev <boyan.karatotev(a)arm.com>
Boyan Karatotev (4):
kselftests/arm64: add a basic Pointer Authentication test
kselftests/arm64: add nop checks for PAuth tests
kselftests/arm64: add PAuth test for whether exec() changes keys
kselftests/arm64: add PAuth tests for single threaded consistency and
key uniqueness
tools/testing/selftests/arm64/Makefile | 2 +-
.../testing/selftests/arm64/pauth/.gitignore | 2 +
tools/testing/selftests/arm64/pauth/Makefile | 29 ++
.../selftests/arm64/pauth/exec_target.c | 35 ++
tools/testing/selftests/arm64/pauth/helper.c | 41 +++
tools/testing/selftests/arm64/pauth/helper.h | 30 ++
tools/testing/selftests/arm64/pauth/pac.c | 347 ++++++++++++++++++
.../selftests/arm64/pauth/pac_corruptor.S | 36 ++
8 files changed, 521 insertions(+), 1 deletion(-)
create mode 100644 tools/testing/selftests/arm64/pauth/.gitignore
create mode 100644 tools/testing/selftests/arm64/pauth/Makefile
create mode 100644 tools/testing/selftests/arm64/pauth/exec_target.c
create mode 100644 tools/testing/selftests/arm64/pauth/helper.c
create mode 100644 tools/testing/selftests/arm64/pauth/helper.h
create mode 100644 tools/testing/selftests/arm64/pauth/pac.c
create mode 100644 tools/testing/selftests/arm64/pauth/pac_corruptor.S
--
2.17.1
On 14/09/20 21:42, Thomas Gleixner wrote:
> CONFIG_PREEMPT_COUNT is now unconditionally enabled and will be
> removed. Cleanup the leftovers before doing so.
>
> Signed-off-by: Thomas Gleixner <tglx(a)linutronix.de>
> Cc: Ingo Molnar <mingo(a)redhat.com>
> Cc: Peter Zijlstra <peterz(a)infradead.org>
> Cc: Juri Lelli <juri.lelli(a)redhat.com>
> Cc: Vincent Guittot <vincent.guittot(a)linaro.org>
> Cc: Dietmar Eggemann <dietmar.eggemann(a)arm.com>
> Cc: Steven Rostedt <rostedt(a)goodmis.org>
> Cc: Ben Segall <bsegall(a)google.com>
> Cc: Mel Gorman <mgorman(a)suse.de>
> Cc: Daniel Bristot de Oliveira <bristot(a)redhat.com>
Small nit below;
Reviewed-by: Valentin Schneider <valentin.schneider(a)arm.com>
> ---
> kernel/sched/core.c | 6 +-----
> lib/Kconfig.debug | 1 -
> 2 files changed, 1 insertion(+), 6 deletions(-)
>
> --- a/kernel/sched/core.c
> +++ b/kernel/sched/core.c
> @@ -3706,8 +3706,7 @@ asmlinkage __visible void schedule_tail(
> * finish_task_switch() for details.
> *
> * finish_task_switch() will drop rq->lock() and lower preempt_count
> - * and the preempt_enable() will end up enabling preemption (on
> - * PREEMPT_COUNT kernels).
I suppose this wanted to be s/PREEMPT_COUNT/PREEMPT/ in the first place,
which ought to be still relevant.
> + * and the preempt_enable() will end up enabling preemption.
> */
>
> rq = finish_task_switch(prev);
On 14/09/20 21:42, Thomas Gleixner wrote:
> CONFIG_PREEMPT_COUNT is now unconditionally enabled and will be
> removed. Cleanup the leftovers before doing so.
>
> Signed-off-by: Thomas Gleixner <tglx(a)linutronix.de>
> Cc: Ingo Molnar <mingo(a)kernel.org>
> Cc: Peter Zijlstra <peterz(a)infradead.org>
> Cc: Juri Lelli <juri.lelli(a)redhat.com>
> Cc: Vincent Guittot <vincent.guittot(a)linaro.org>
> Cc: Dietmar Eggemann <dietmar.eggemann(a)arm.com>
> Cc: Steven Rostedt <rostedt(a)goodmis.org>
> Cc: Ben Segall <bsegall(a)google.com>
> Cc: Mel Gorman <mgorman(a)suse.de>
> Cc: Daniel Bristot de Oliveira <bristot(a)redhat.com>
Reviewed-by: Valentin Schneider <valentin.schneider(a)arm.com>
On Mon, Sep 14, 2020 at 01:59:15PM -0700, Linus Torvalds wrote:
> On Mon, Sep 14, 2020 at 1:45 PM Thomas Gleixner <tglx(a)linutronix.de> wrote:
> >
> > Recently merged code does:
> >
> > gfp = preemptible() ? GFP_KERNEL : GFP_ATOMIC;
> >
> > Looks obviously correct, except for the fact that preemptible() is
> > unconditionally false for CONFIF_PREEMPT_COUNT=n, i.e. all allocations in
> > that code use GFP_ATOMIC on such kernels.
>
> I don't think this is a good reason to entirely get rid of the no-preempt thing.
>
> The above is just garbage. It's bogus. You can't do it.
>
> Blaming the no-preempt code for this bug is extremely unfair, imho.
>
> And the no-preempt code does help make for much better code generation
> for simple spinlocks.
>
> Where is that horribly buggy recent code? It's not in that exact
> format, certainly, since 'grep' doesn't find it.
It would be convenient for that "gfp =" code to work, as this would
allow better cache locality while invoking RCU callbacks, and would
further provide better robustness to callback floods. The full story
is quite long, but here are alternatives have not yet been proven to be
abject failures:
1. Use workqueues to do the allocations in a clean context.
While waiting for the allocations, the callbacks are queued
in the old cache-busting manner. This functions correctly,
but in the meantime (which on busy systems can be some time)
the cache locality and robustness are lost.
2. Provide the ability to allocate memory in raw atomic context.
This is extremely effective, especially when used in combination
with #1 above, but as you might suspect, the MM guys don't like
it much.
In contrast, with Thomas's patch series, call_rcu() and kvfree_rcu()
could just look at preemptible() to see whether or not it was safe to
allocate memory, even in !PREEMPT kernels -- and in the common case,
it almost always would be safe. It is quite possible that this approach
would work in isolation, or failing that, that adding #1 above would do
the trick.
I understand that this is all very hand-wavy, and I do apologize for that.
If you really want the full sad story with performance numbers and the
works, let me know!
Thanx, Paul
Hi,
This fixes a couple of minor aggravating factors that I ran across while
trying to do some changes in selftests/vm. These are simple things, but
like most things with GNU Make, it's rarely obvious what's wrong until
you understand *the entire Makefile and all of its includes*.
So while there is, of course, joy in learning those details, I thought I'd
fix these little things, so as to allow others to skip out on the Joy if
they so choose. :)
First of all, if you have an item (let's choose userfaultfd for an
example) that fails to build, you might do this:
$ make -j32
# ...you observe a failed item in the threaded output
# OK, let's get a closer look
$ make
# ...but now the build quietly "succeeds".
That's what Patch 0001 fixes.
Second, if you instead attempt this approach for your closer look (a casual
mistake, as it's not supported):
$ make userfaultfd
# ...userfaultfd fails to link, due to incomplete LDLIBS
That's what Patch 0002 fixes.
John Hubbard (2):
selftests/vm: fix false build success on the second and later attempts
selftests/vm: fix incorrect gcc invocation in some cases
tools/testing/selftests/vm/Makefile | 17 +++++++++++++++++
1 file changed, 17 insertions(+)
--
2.28.0