Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

tools/nolibc: MIPS: add support for N64 and N32 ABIs

Add support for the MIPS 64bit N64 and ILP32 N32 ABIs.

In addition to different byte orders and ABIs there are also different
releases of the MIPS architecture. To avoid blowing up the test matrix,
only add a subset of all possible test combinations.

Signed-off-by: Thomas Weißschuh <linux@weissschuh.net>
Tested-by: Sebastian Andrzej Siewior <sebastian@breakpoint.cc>
Link: https://lore.kernel.org/r/20250623-nolibc-mips-n32-v3-4-6ae2d89f4259@weissschuh.net

+117 -16
+90 -15
tools/include/nolibc/arch-mips.h
··· 10 10 #include "compiler.h" 11 11 #include "crt.h" 12 12 13 - #if !defined(_ABIO32) 13 + #if !defined(_ABIO32) && !defined(_ABIN32) && !defined(_ABI64) 14 14 #error Unsupported MIPS ABI 15 15 #endif 16 16 ··· 32 32 * - the arguments are cast to long and assigned into the target registers 33 33 * which are then simply passed as registers to the asm code, so that we 34 34 * don't have to experience issues with register constraints. 35 + * 36 + * Syscalls for MIPS ABI N32, same as ABI O32 with the following differences : 37 + * - arguments are in a0, a1, a2, a3, t0, t1, t2, t3. 38 + * t0..t3 are also known as a4..a7. 39 + * - stack is 16-byte aligned 35 40 */ 41 + 42 + #if defined(_ABIO32) 36 43 37 44 #define _NOLIBC_SYSCALL_CLOBBERLIST \ 38 45 "memory", "cc", "at", "v1", "hi", "lo", \ 39 46 "t0", "t1", "t2", "t3", "t4", "t5", "t6", "t7", "t8", "t9" 47 + #define _NOLIBC_SYSCALL_STACK_RESERVE "addiu $sp, $sp, -32\n" 48 + #define _NOLIBC_SYSCALL_STACK_UNRESERVE "addiu $sp, $sp, 32\n" 49 + 50 + #else /* _ABIN32 || _ABI64 */ 51 + 52 + /* binutils, GCC and clang disagree about register aliases, use numbers instead. */ 53 + #define _NOLIBC_SYSCALL_CLOBBERLIST \ 54 + "memory", "cc", "at", "v1", \ 55 + "10", "11", "12", "13", "14", "15", "24", "25" 56 + 57 + #define _NOLIBC_SYSCALL_STACK_RESERVE 58 + #define _NOLIBC_SYSCALL_STACK_UNRESERVE 59 + 60 + #endif /* _ABIO32 */ 40 61 41 62 #define my_syscall0(num) \ 42 63 ({ \ ··· 65 44 register long _arg4 __asm__ ("a3"); \ 66 45 \ 67 46 __asm__ volatile ( \ 68 - "addiu $sp, $sp, -32\n" \ 47 + _NOLIBC_SYSCALL_STACK_RESERVE \ 69 48 "syscall\n" \ 70 - "addiu $sp, $sp, 32\n" \ 49 + _NOLIBC_SYSCALL_STACK_UNRESERVE \ 71 50 : "=r"(_num), "=r"(_arg4) \ 72 51 : "r"(_num) \ 73 52 : _NOLIBC_SYSCALL_CLOBBERLIST \ ··· 82 61 register long _arg4 __asm__ ("a3"); \ 83 62 \ 84 63 __asm__ volatile ( \ 85 - "addiu $sp, $sp, -32\n" \ 64 + _NOLIBC_SYSCALL_STACK_RESERVE \ 86 65 "syscall\n" \ 87 - "addiu $sp, $sp, 32\n" \ 66 + _NOLIBC_SYSCALL_STACK_UNRESERVE \ 88 67 : "=r"(_num), "=r"(_arg4) \ 89 68 : "0"(_num), \ 90 69 "r"(_arg1) \ ··· 101 80 register long _arg4 __asm__ ("a3"); \ 102 81 \ 103 82 __asm__ volatile ( \ 104 - "addiu $sp, $sp, -32\n" \ 83 + _NOLIBC_SYSCALL_STACK_RESERVE \ 105 84 "syscall\n" \ 106 - "addiu $sp, $sp, 32\n" \ 85 + _NOLIBC_SYSCALL_STACK_UNRESERVE \ 107 86 : "=r"(_num), "=r"(_arg4) \ 108 87 : "0"(_num), \ 109 88 "r"(_arg1), "r"(_arg2) \ ··· 121 100 register long _arg4 __asm__ ("a3"); \ 122 101 \ 123 102 __asm__ volatile ( \ 124 - "addiu $sp, $sp, -32\n" \ 103 + _NOLIBC_SYSCALL_STACK_RESERVE \ 125 104 "syscall\n" \ 126 - "addiu $sp, $sp, 32\n" \ 105 + _NOLIBC_SYSCALL_STACK_UNRESERVE \ 127 106 : "=r"(_num), "=r"(_arg4) \ 128 107 : "0"(_num), \ 129 108 "r"(_arg1), "r"(_arg2), "r"(_arg3) \ ··· 141 120 register long _arg4 __asm__ ("a3") = (long)(arg4); \ 142 121 \ 143 122 __asm__ volatile ( \ 144 - "addiu $sp, $sp, -32\n" \ 123 + _NOLIBC_SYSCALL_STACK_RESERVE \ 145 124 "syscall\n" \ 146 - "addiu $sp, $sp, 32\n" \ 125 + _NOLIBC_SYSCALL_STACK_UNRESERVE \ 147 126 : "=r" (_num), "=r"(_arg4) \ 148 127 : "0"(_num), \ 149 128 "r"(_arg1), "r"(_arg2), "r"(_arg3), "r"(_arg4) \ ··· 151 130 ); \ 152 131 _arg4 ? -_num : _num; \ 153 132 }) 133 + 134 + #if defined(_ABIO32) 154 135 155 136 #define my_syscall5(num, arg1, arg2, arg3, arg4, arg5) \ 156 137 ({ \ ··· 164 141 register long _arg5 = (long)(arg5); \ 165 142 \ 166 143 __asm__ volatile ( \ 167 - "addiu $sp, $sp, -32\n" \ 144 + _NOLIBC_SYSCALL_STACK_RESERVE \ 168 145 "sw %7, 16($sp)\n" \ 169 146 "syscall\n" \ 170 - "addiu $sp, $sp, 32\n" \ 147 + _NOLIBC_SYSCALL_STACK_UNRESERVE \ 171 148 : "=r" (_num), "=r"(_arg4) \ 172 149 : "0"(_num), \ 173 150 "r"(_arg1), "r"(_arg2), "r"(_arg3), "r"(_arg4), "r"(_arg5) \ ··· 187 164 register long _arg6 = (long)(arg6); \ 188 165 \ 189 166 __asm__ volatile ( \ 190 - "addiu $sp, $sp, -32\n" \ 167 + _NOLIBC_SYSCALL_STACK_RESERVE \ 191 168 "sw %7, 16($sp)\n" \ 192 169 "sw %8, 20($sp)\n" \ 193 170 "syscall\n" \ 194 - "addiu $sp, $sp, 32\n" \ 171 + _NOLIBC_SYSCALL_STACK_UNRESERVE \ 195 172 : "=r" (_num), "=r"(_arg4) \ 196 173 : "0"(_num), \ 197 174 "r"(_arg1), "r"(_arg2), "r"(_arg3), "r"(_arg4), "r"(_arg5), \ ··· 201 178 _arg4 ? -_num : _num; \ 202 179 }) 203 180 181 + #else /* _ABIN32 || _ABI64 */ 182 + 183 + #define my_syscall5(num, arg1, arg2, arg3, arg4, arg5) \ 184 + ({ \ 185 + register long _num __asm__ ("v0") = (num); \ 186 + register long _arg1 __asm__ ("$4") = (long)(arg1); \ 187 + register long _arg2 __asm__ ("$5") = (long)(arg2); \ 188 + register long _arg3 __asm__ ("$6") = (long)(arg3); \ 189 + register long _arg4 __asm__ ("$7") = (long)(arg4); \ 190 + register long _arg5 __asm__ ("$8") = (long)(arg5); \ 191 + \ 192 + __asm__ volatile ( \ 193 + "syscall\n" \ 194 + : "=r" (_num), "=r"(_arg4) \ 195 + : "0"(_num), \ 196 + "r"(_arg1), "r"(_arg2), "r"(_arg3), "r"(_arg4), "r"(_arg5) \ 197 + : _NOLIBC_SYSCALL_CLOBBERLIST \ 198 + ); \ 199 + _arg4 ? -_num : _num; \ 200 + }) 201 + 202 + #define my_syscall6(num, arg1, arg2, arg3, arg4, arg5, arg6) \ 203 + ({ \ 204 + register long _num __asm__ ("v0") = (num); \ 205 + register long _arg1 __asm__ ("$4") = (long)(arg1); \ 206 + register long _arg2 __asm__ ("$5") = (long)(arg2); \ 207 + register long _arg3 __asm__ ("$6") = (long)(arg3); \ 208 + register long _arg4 __asm__ ("$7") = (long)(arg4); \ 209 + register long _arg5 __asm__ ("$8") = (long)(arg5); \ 210 + register long _arg6 __asm__ ("$9") = (long)(arg6); \ 211 + \ 212 + __asm__ volatile ( \ 213 + "syscall\n" \ 214 + : "=r" (_num), "=r"(_arg4) \ 215 + : "0"(_num), \ 216 + "r"(_arg1), "r"(_arg2), "r"(_arg3), "r"(_arg4), "r"(_arg5), \ 217 + "r"(_arg6) \ 218 + : _NOLIBC_SYSCALL_CLOBBERLIST \ 219 + ); \ 220 + _arg4 ? -_num : _num; \ 221 + }) 222 + 223 + #endif /* _ABIO32 */ 224 + 204 225 /* startup code, note that it's called __start on MIPS */ 205 226 void __start(void); 206 227 void __attribute__((weak, noreturn)) __nolibc_entrypoint __no_stack_protector __start(void) 207 228 { 208 229 __asm__ volatile ( 209 230 "move $a0, $sp\n" /* save stack pointer to $a0, as arg1 of _start_c */ 231 + #if defined(_ABIO32) 210 232 "addiu $sp, $sp, -16\n" /* the callee expects to save a0..a3 there */ 233 + #endif /* _ABIO32 */ 211 234 "lui $t9, %hi(_start_c)\n" /* ABI requires current function address in $t9 */ 212 235 "ori $t9, %lo(_start_c)\n" 236 + #if defined(_ABI64) 237 + "lui $t0, %highest(_start_c)\n" 238 + "ori $t0, %higher(_start_c)\n" 239 + "dsll $t0, 0x20\n" 240 + "or $t9, $t0\n" 241 + #endif /* _ABI64 */ 213 242 "jalr $t9\n" /* transfer to c runtime */ 214 243 ); 215 244 __nolibc_entrypoint_epilogue();
+26
tools/testing/selftests/nolibc/Makefile.nolibc
··· 53 53 ARCH_ppc64le = powerpc 54 54 ARCH_mips32le = mips 55 55 ARCH_mips32be = mips 56 + ARCH_mipsn32le = mips 57 + ARCH_mipsn32be = mips 58 + ARCH_mips64le = mips 59 + ARCH_mips64be = mips 56 60 ARCH_riscv32 = riscv 57 61 ARCH_riscv64 = riscv 58 62 ARCH_s390x = s390 ··· 73 69 IMAGE_armthumb = arch/arm/boot/zImage 74 70 IMAGE_mips32le = vmlinuz 75 71 IMAGE_mips32be = vmlinuz 72 + IMAGE_mipsn32le = vmlinuz 73 + IMAGE_mipsn32be = vmlinuz 74 + IMAGE_mips64le = vmlinuz 75 + IMAGE_mips64be = vmlinuz 76 76 IMAGE_ppc = vmlinux 77 77 IMAGE_ppc64 = vmlinux 78 78 IMAGE_ppc64le = arch/powerpc/boot/zImage ··· 101 93 DEFCONFIG_armthumb = multi_v7_defconfig 102 94 DEFCONFIG_mips32le = malta_defconfig 103 95 DEFCONFIG_mips32be = malta_defconfig generic/eb.config 96 + DEFCONFIG_mipsn32le = malta_defconfig generic/64r2.config 97 + DEFCONFIG_mipsn32be = malta_defconfig generic/64r6.config generic/eb.config 98 + DEFCONFIG_mips64le = malta_defconfig generic/64r6.config 99 + DEFCONFIG_mips64be = malta_defconfig generic/64r2.config generic/eb.config 104 100 DEFCONFIG_ppc = pmac32_defconfig 105 101 DEFCONFIG_ppc64 = powernv_be_defconfig 106 102 DEFCONFIG_ppc64le = powernv_defconfig ··· 136 124 QEMU_ARCH_armthumb = arm 137 125 QEMU_ARCH_mips32le = mipsel # works with malta_defconfig 138 126 QEMU_ARCH_mips32be = mips 127 + QEMU_ARCH_mipsn32le = mips64el 128 + QEMU_ARCH_mipsn32be = mips64 129 + QEMU_ARCH_mips64le = mips64el 130 + QEMU_ARCH_mips64be = mips64 139 131 QEMU_ARCH_ppc = ppc 140 132 QEMU_ARCH_ppc64 = ppc64 141 133 QEMU_ARCH_ppc64le = ppc64 ··· 155 139 QEMU_ARCH = $(QEMU_ARCH_$(XARCH)) 156 140 157 141 QEMU_ARCH_USER_ppc64le = ppc64le 142 + QEMU_ARCH_USER_mipsn32le = mipsn32el 143 + QEMU_ARCH_USER_mipsn32be = mipsn32 158 144 QEMU_ARCH_USER = $(or $(QEMU_ARCH_USER_$(XARCH)),$(QEMU_ARCH_$(XARCH))) 159 145 160 146 QEMU_BIOS_DIR = /usr/share/edk2/ ··· 175 157 QEMU_ARGS_armthumb = -M virt -append "panic=-1 $(TEST:%=NOLIBC_TEST=%)" 176 158 QEMU_ARGS_mips32le = -M malta -append "panic=-1 $(TEST:%=NOLIBC_TEST=%)" 177 159 QEMU_ARGS_mips32be = -M malta -append "panic=-1 $(TEST:%=NOLIBC_TEST=%)" 160 + QEMU_ARGS_mipsn32le = -M malta -cpu 5KEc -append "panic=-1 $(TEST:%=NOLIBC_TEST=%)" 161 + QEMU_ARGS_mipsn32be = -M malta -cpu I6400 -append "panic=-1 $(TEST:%=NOLIBC_TEST=%)" 162 + QEMU_ARGS_mips64le = -M malta -cpu I6400 -append "panic=-1 $(TEST:%=NOLIBC_TEST=%)" 163 + QEMU_ARGS_mips64be = -M malta -cpu 5KEc -append "panic=-1 $(TEST:%=NOLIBC_TEST=%)" 178 164 QEMU_ARGS_ppc = -M g3beige -append "console=ttyS0 panic=-1 $(TEST:%=NOLIBC_TEST=%)" 179 165 QEMU_ARGS_ppc64 = -M powernv -append "console=hvc0 panic=-1 $(TEST:%=NOLIBC_TEST=%)" 180 166 QEMU_ARGS_ppc64le = -M powernv -append "console=hvc0 panic=-1 $(TEST:%=NOLIBC_TEST=%)" ··· 213 191 CFLAGS_s390 = -m31 214 192 CFLAGS_mips32le = -EL -mabi=32 -fPIC 215 193 CFLAGS_mips32be = -EB -mabi=32 194 + CFLAGS_mipsn32le = -EL -mabi=n32 -fPIC -march=mips64r2 195 + CFLAGS_mipsn32be = -EB -mabi=n32 -march=mips64r6 196 + CFLAGS_mips64le = -EL -mabi=64 -march=mips64r6 197 + CFLAGS_mips64be = -EB -mabi=64 -march=mips64r2 216 198 CFLAGS_sparc32 = $(call cc-option,-m32) 217 199 ifeq ($(origin XARCH),command line) 218 200 CFLAGS_XARCH = $(CFLAGS_$(XARCH))
+1 -1
tools/testing/selftests/nolibc/run-tests.sh
··· 20 20 all_archs=( 21 21 i386 x86_64 22 22 arm64 arm armthumb 23 - mips32le mips32be 23 + mips32le mips32be mipsn32le mipsn32be mips64le mips64be 24 24 ppc ppc64 ppc64le 25 25 riscv32 riscv64 26 26 s390x s390