git: 9e48c30e25a7 - main - rtld: Add arm64 variant pcs tests
- Go to: [ bottom of page ] [ top of archives ] [ this month ]
Date: Fri, 17 May 2024 10:21:52 UTC
The branch main has been updated by andrew: URL: https://cgit.FreeBSD.org/src/commit/?id=9e48c30e25a743a268d17a6215b9c2d859543547 commit 9e48c30e25a743a268d17a6215b9c2d859543547 Author: Andrew Turner <andrew@FreeBSD.org> AuthorDate: 2024-04-19 10:07:53 +0000 Commit: Andrew Turner <andrew@FreeBSD.org> CommitDate: 2024-05-17 09:37:23 +0000 rtld: Add arm64 variant pcs tests When marking a function as variant pcs we can use registers not normally used in procedure calls. Add a test that uses this and stores all general purpose registers to a buffer and compare this buffer with the expected value later. Sponsored by: Arm Ltd Differential Revision: https://reviews.freebsd.org/D44870 --- libexec/rtld-elf/tests/Makefile | 3 + libexec/rtld-elf/tests/aarch64/Makefile | 16 ++++ libexec/rtld-elf/tests/aarch64/Makefile.common | 3 + libexec/rtld-elf/tests/aarch64/Makefile.inc | 3 + libexec/rtld-elf/tests/aarch64/variant_pcs.c | 64 +++++++++++++++ libexec/rtld-elf/tests/aarch64/variant_pcs_dso.S | 54 +++++++++++++ .../tests/aarch64/variant_pcs_dso/Makefile | 13 ++++ .../rtld-elf/tests/aarch64/variant_pcs_helper.S | 91 ++++++++++++++++++++++ 8 files changed, 247 insertions(+) diff --git a/libexec/rtld-elf/tests/Makefile b/libexec/rtld-elf/tests/Makefile index e380e9850fc1..b8f1e9c49174 100644 --- a/libexec/rtld-elf/tests/Makefile +++ b/libexec/rtld-elf/tests/Makefile @@ -1,6 +1,9 @@ SUBDIR+= libpythagoras libdeep libval libval2 target TESTS_SUBDIRS+= rtld_deepbind +.if exists(${MACHINE_CPUARCH}) +TESTS_SUBDIRS+= ${MACHINE_CPUARCH} +.endif SUBDIR_DEPEND_libdeep= libval2 SUBDIR_DEPEND_rtld_deepbind= libval diff --git a/libexec/rtld-elf/tests/aarch64/Makefile b/libexec/rtld-elf/tests/aarch64/Makefile new file mode 100644 index 000000000000..a6f04ae49f26 --- /dev/null +++ b/libexec/rtld-elf/tests/aarch64/Makefile @@ -0,0 +1,16 @@ + +.include "Makefile.common" + +SUBDIR= variant_pcs_dso + +ATF_TESTS_C= variant_pcs + +SRCS.variant_pcs= variant_pcs.c variant_pcs_helper.S +DPADD.variant_pcs+= ${.OBJDIR}/dso/libh_variant_pcs.so +LDFLAGS.variant_pcs+= -Wl,-rpath,${TESTSDIR} -L${.OBJDIR}/variant_pcs_dso +LDADD.variant_pcs+= -lh_variant_pcs + +# Ensure the dso is built first +variant_pcs: variant_pcs_dso + +.include <bsd.test.mk> diff --git a/libexec/rtld-elf/tests/aarch64/Makefile.common b/libexec/rtld-elf/tests/aarch64/Makefile.common new file mode 100644 index 000000000000..3181b82aef44 --- /dev/null +++ b/libexec/rtld-elf/tests/aarch64/Makefile.common @@ -0,0 +1,3 @@ + +TESTSDIR?= ${TESTSBASE}/libexec/rtld-elf/aarch64 +LIBDIR= ${TESTSDIR} diff --git a/libexec/rtld-elf/tests/aarch64/Makefile.inc b/libexec/rtld-elf/tests/aarch64/Makefile.inc new file mode 100644 index 000000000000..3712e208f1fc --- /dev/null +++ b/libexec/rtld-elf/tests/aarch64/Makefile.inc @@ -0,0 +1,3 @@ + +.include "Makefile.common" +.include "../Makefile.inc" diff --git a/libexec/rtld-elf/tests/aarch64/variant_pcs.c b/libexec/rtld-elf/tests/aarch64/variant_pcs.c new file mode 100644 index 000000000000..5792dfd29723 --- /dev/null +++ b/libexec/rtld-elf/tests/aarch64/variant_pcs.c @@ -0,0 +1,64 @@ +/*- + * SPDX-License-Identifier: BSD-2-Clause + * + * Copyright (c) 2024 Arm Ltd + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#include <sys/param.h> +#include <inttypes.h> +#include <string.h> +#include <atf-c.h> + +extern uint32_t variant_pcs_test_ret[]; +void variant_pcs_helper(void *); + +ATF_TC_WITHOUT_HEAD(variant_gpr); +ATF_TC_BODY(variant_gpr, tc) +{ + uint64_t regs[31]; + + memset(regs, 99, sizeof(regs)); + variant_pcs_helper(regs); + + ATF_REQUIRE(regs[0] == (uintptr_t)®s[0]); + ATF_REQUIRE(regs[30] == (uintptr_t)&variant_pcs_test_ret); + + for (uint64_t i = 1; i < 30; i++) { + /* + * x16 and x17 are ilp0 and ilp1 respectively. They are used + * in the PLT code so are trashed, even with variant PCS. + */ + if (i == 16 || i == 17) + continue; + + ATF_REQUIRE(regs[i] == i); + } +} + +ATF_TP_ADD_TCS(tp) +{ + ATF_TP_ADD_TC(tp, variant_gpr); + + return atf_no_error(); +} diff --git a/libexec/rtld-elf/tests/aarch64/variant_pcs_dso.S b/libexec/rtld-elf/tests/aarch64/variant_pcs_dso.S new file mode 100644 index 000000000000..0e6f05d84e15 --- /dev/null +++ b/libexec/rtld-elf/tests/aarch64/variant_pcs_dso.S @@ -0,0 +1,54 @@ +/*- + * SPDX-License-Identifier: BSD-2-Clause + * + * Copyright (c) 2024 Arm Ltd + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#include <machine/asm.h> + +/* + * Mark variant_pcs_test as a variant pcs function so we can check the + * saved register values later. The buffer to store the registers is + * passed in x0. + */ +.variant_pcs variant_pcs_test +ENTRY(variant_pcs_test) + stp x0, x1, [x0, #(0 * 8)] + stp x2, x3, [x0, #(2 * 8)] + stp x4, x5, [x0, #(4 * 8)] + stp x6, x7, [x0, #(6 * 8)] + stp x8, x9, [x0, #(8 * 8)] + stp x10, x11, [x0, #(10 * 8)] + stp x12, x13, [x0, #(12 * 8)] + stp x14, x15, [x0, #(14 * 8)] + stp x16, x17, [x0, #(16 * 8)] + stp x18, x19, [x0, #(18 * 8)] + stp x20, x21, [x0, #(20 * 8)] + stp x22, x23, [x0, #(22 * 8)] + stp x24, x25, [x0, #(24 * 8)] + stp x26, x27, [x0, #(26 * 8)] + stp x28, x29, [x0, #(28 * 8)] + str x30, [x0, #(30 * 8)] + ret +END(variant_pcs_test) diff --git a/libexec/rtld-elf/tests/aarch64/variant_pcs_dso/Makefile b/libexec/rtld-elf/tests/aarch64/variant_pcs_dso/Makefile new file mode 100644 index 000000000000..08f1eec00b06 --- /dev/null +++ b/libexec/rtld-elf/tests/aarch64/variant_pcs_dso/Makefile @@ -0,0 +1,13 @@ + +.PATH: ${.CURDIR:H} +SHLIB= h_variant_pcs +SHLIB_NAME= libh_variant_pcs.so +SHLIB_MAJOR= 1 + +WITHOUT_STATIC= +WITHOUT_PROFILE= +WITHOUT_PIC= + +SRCS= variant_pcs_dso.S + +.include <bsd.lib.mk> diff --git a/libexec/rtld-elf/tests/aarch64/variant_pcs_helper.S b/libexec/rtld-elf/tests/aarch64/variant_pcs_helper.S new file mode 100644 index 000000000000..9480ba629c2e --- /dev/null +++ b/libexec/rtld-elf/tests/aarch64/variant_pcs_helper.S @@ -0,0 +1,91 @@ +/*- + * SPDX-License-Identifier: BSD-2-Clause + * + * Copyright (c) 2024 Arm Ltd + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#include <machine/asm.h> + +.global variant_pcs_test_ret + +/* + * void variant_pcs_helper(void *buffer); + * + * This follows the aapcs64 convention so needs to save and restore + * the callee-saved registers. It puts a known value in each register + * other than x0 and x30 as x0 contains the buffer used to store the + * register data, and x30 is the link register so will be trashed by + * the branch and link to variant_pcs_test. + */ +ENTRY(variant_pcs_helper) + sub sp, sp, #(14 * 8) + stp x29, x30, [sp, #(12 * 8)] + stp x27, x28, [sp, #(10 * 8)] + stp x25, x26, [sp, #( 8 * 8)] + stp x23, x24, [sp, #( 6 * 8)] + stp x22, x23, [sp, #( 4 * 8)] + stp x21, x22, [sp, #( 2 * 8)] + stp x19, x20, [sp, #( 0 * 8)] + add x29, sp, #(12 * 8) + mov x1, #1 + mov x2, #2 + mov x3, #3 + mov x4, #4 + mov x5, #5 + mov x6, #6 + mov x7, #7 + mov x8, #8 + mov x9, #9 + mov x10, #10 + mov x11, #11 + mov x12, #12 + mov x13, #13 + mov x14, #14 + mov x15, #15 + mov x16, #16 + mov x17, #17 + mov x18, #18 + mov x19, #19 + mov x20, #20 + mov x21, #21 + mov x22, #22 + mov x23, #23 + mov x24, #24 + mov x25, #25 + mov x26, #26 + mov x27, #27 + mov x28, #28 + mov x29, #29 + bl variant_pcs_test +variant_pcs_test_ret: + ldp x19, x20, [sp, #( 0 * 8)] + ldp x21, x22, [sp, #( 2 * 8)] + ldp x22, x23, [sp, #( 4 * 8)] + ldp x23, x24, [sp, #( 6 * 8)] + ldp x25, x26, [sp, #( 8 * 8)] + ldp x27, x28, [sp, #(10 * 8)] + ldp x29, x30, [sp, #(12 * 8)] + add sp, sp, #(14 * 8) + ret +END(variant_pcs_helper)