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

rseq/selftests: Add support for OpenRISC

Add support for OpenRISC in the rseq selftests. OpenRISC is 32-bit
only.

Tested this with:

Compiler: gcc version 14.2.0 (GCC)
Binutils: GNU assembler version 2.43.1 (or1k-smh-linux-gnu) using BFD version (GNU Binutils) 2.43.1.20241207
Linux: Linux buildroot 6.13.0-rc2-00005-g1fa73dd6c2d3-dirty #213 SMP Sat Dec 28 22:18:39 GMT 2024 openrisc GNU/Linux
Glibc: 2024-12-13 e4e49583d9 Stafford Horne or1k: Update libm-test-ulps

Signed-off-by: Stafford Horne <shorne@gmail.com>
Reviewed-by: Mathieu Desnoyers <mathieu.desnoyers@efficios.com>
Acked-by: Shuah Khan <skhan@linuxfoundation.org>

+634
+24
tools/testing/selftests/rseq/param_test.c
··· 226 226 "addi " INJECT_ASM_REG "," INJECT_ASM_REG ", -1\n\t" \ 227 227 "bnez " INJECT_ASM_REG ", 222b\n\t" \ 228 228 "333:\n\t" 229 + #elif defined(__or1k__) 229 230 231 + #define RSEQ_INJECT_INPUT \ 232 + , [loop_cnt_1]"m"(loop_cnt[1]) \ 233 + , [loop_cnt_2]"m"(loop_cnt[2]) \ 234 + , [loop_cnt_3]"m"(loop_cnt[3]) \ 235 + , [loop_cnt_4]"m"(loop_cnt[4]) \ 236 + , [loop_cnt_5]"m"(loop_cnt[5]) \ 237 + , [loop_cnt_6]"m"(loop_cnt[6]) 230 238 239 + #define INJECT_ASM_REG "r31" 240 + 241 + #define RSEQ_INJECT_CLOBBER \ 242 + , INJECT_ASM_REG 243 + 244 + #define RSEQ_INJECT_ASM(n) \ 245 + "l.lwz " INJECT_ASM_REG ", %[loop_cnt_" #n "]\n\t" \ 246 + "l.sfeqi " INJECT_ASM_REG ", 0\n\t" \ 247 + "l.bf 333f\n\t" \ 248 + " l.nop\n\t" \ 249 + "222:\n\t" \ 250 + "l.addi " INJECT_ASM_REG "," INJECT_ASM_REG ", -1\n\t" \ 251 + "l.sfeqi " INJECT_ASM_REG ", 0\n\t" \ 252 + "l.bf 222f\n\t" \ 253 + " l.nop\n\t" \ 254 + "333:\n\t" 231 255 #else 232 256 #error unsupported target 233 257 #endif
+412
tools/testing/selftests/rseq/rseq-or1k-bits.h
··· 1 + /* SPDX-License-Identifier: LGPL-2.1 OR MIT */ 2 + 3 + #include "rseq-bits-template.h" 4 + 5 + #if defined(RSEQ_TEMPLATE_MO_RELAXED) && \ 6 + (defined(RSEQ_TEMPLATE_CPU_ID) || defined(RSEQ_TEMPLATE_MM_CID)) 7 + 8 + static inline __always_inline 9 + int RSEQ_TEMPLATE_IDENTIFIER(rseq_cmpeqv_storev)(intptr_t *v, intptr_t expect, intptr_t newv, 10 + int cpu) 11 + { 12 + RSEQ_INJECT_C(9) 13 + 14 + __asm__ __volatile__ goto(RSEQ_ASM_DEFINE_TABLE(1, 2f, 3f, 4f) 15 + RSEQ_ASM_DEFINE_EXIT_POINT(2f, "%l[cmpfail]") 16 + #ifdef RSEQ_COMPARE_TWICE 17 + RSEQ_ASM_DEFINE_EXIT_POINT(2f, "%l[error1]") 18 + RSEQ_ASM_DEFINE_EXIT_POINT(2f, "%l[error2]") 19 + #endif 20 + RSEQ_ASM_STORE_RSEQ_CS(2, 1b, rseq_cs) 21 + RSEQ_ASM_CMP_CPU_ID(cpu_id, current_cpu_id, 4f) 22 + RSEQ_INJECT_ASM(3) 23 + RSEQ_ASM_OP_CMPEQ(v, expect, "%l[cmpfail]") 24 + RSEQ_INJECT_ASM(4) 25 + #ifdef RSEQ_COMPARE_TWICE 26 + RSEQ_ASM_CMP_CPU_ID(cpu_id, current_cpu_id, "%l[error1]") 27 + RSEQ_ASM_OP_CMPEQ(v, expect, "%l[error2]") 28 + #endif 29 + RSEQ_ASM_OP_FINAL_STORE(v, newv, 3) 30 + RSEQ_INJECT_ASM(5) 31 + RSEQ_ASM_DEFINE_ABORT(4, abort) 32 + : /* gcc asm goto does not allow outputs */ 33 + : [cpu_id] "r" (cpu), 34 + [current_cpu_id] "m" (rseq_get_abi()->RSEQ_TEMPLATE_CPU_ID_FIELD), 35 + [rseq_cs] "m" (rseq_get_abi()->rseq_cs.arch.ptr), 36 + [v] "m" (*v), 37 + [expect] "r" (expect), 38 + [newv] "r" (newv) 39 + RSEQ_INJECT_INPUT 40 + : "memory", RSEQ_ASM_TMP_REG_1 41 + RSEQ_INJECT_CLOBBER 42 + : abort, cmpfail 43 + #ifdef RSEQ_COMPARE_TWICE 44 + , error1, error2 45 + #endif 46 + ); 47 + 48 + return 0; 49 + abort: 50 + RSEQ_INJECT_FAILED 51 + return -1; 52 + cmpfail: 53 + return 1; 54 + #ifdef RSEQ_COMPARE_TWICE 55 + error1: 56 + rseq_bug("cpu_id comparison failed"); 57 + error2: 58 + rseq_bug("expected value comparison failed"); 59 + #endif 60 + } 61 + 62 + static inline __always_inline 63 + int RSEQ_TEMPLATE_IDENTIFIER(rseq_cmpnev_storeoffp_load)(intptr_t *v, intptr_t expectnot, 64 + off_t voffp, intptr_t *load, int cpu) 65 + { 66 + RSEQ_INJECT_C(9) 67 + 68 + __asm__ __volatile__ goto(RSEQ_ASM_DEFINE_TABLE(1, 2f, 3f, 4f) 69 + RSEQ_ASM_DEFINE_EXIT_POINT(2f, "%l[cmpfail]") 70 + #ifdef RSEQ_COMPARE_TWICE 71 + RSEQ_ASM_DEFINE_EXIT_POINT(2f, "%l[error1]") 72 + RSEQ_ASM_DEFINE_EXIT_POINT(2f, "%l[error2]") 73 + #endif 74 + RSEQ_ASM_STORE_RSEQ_CS(2, 1b, rseq_cs) 75 + RSEQ_ASM_CMP_CPU_ID(cpu_id, current_cpu_id, 4f) 76 + RSEQ_INJECT_ASM(3) 77 + RSEQ_ASM_OP_CMPNE(v, expectnot, "%l[cmpfail]") 78 + RSEQ_INJECT_ASM(4) 79 + #ifdef RSEQ_COMPARE_TWICE 80 + RSEQ_ASM_CMP_CPU_ID(cpu_id, current_cpu_id, "%l[error1]") 81 + RSEQ_ASM_OP_CMPNE(v, expectnot, "%l[error2]") 82 + #endif 83 + RSEQ_ASM_OP_R_LOAD(v) 84 + RSEQ_ASM_OP_R_STORE(load) 85 + RSEQ_ASM_OP_R_LOAD_OFF(voffp) 86 + RSEQ_ASM_OP_R_FINAL_STORE(v, 3) 87 + RSEQ_INJECT_ASM(5) 88 + RSEQ_ASM_DEFINE_ABORT(4, abort) 89 + : /* gcc asm goto does not allow outputs */ 90 + : [cpu_id] "r" (cpu), 91 + [current_cpu_id] "m" (rseq_get_abi()->RSEQ_TEMPLATE_CPU_ID_FIELD), 92 + [rseq_cs] "m" (rseq_get_abi()->rseq_cs.arch.ptr), 93 + [v] "m" (*v), 94 + [expectnot] "r" (expectnot), 95 + [load] "m" (*load), 96 + [voffp] "Ir" (voffp) 97 + RSEQ_INJECT_INPUT 98 + : "memory", RSEQ_ASM_TMP_REG_1 99 + RSEQ_INJECT_CLOBBER 100 + : abort, cmpfail 101 + #ifdef RSEQ_COMPARE_TWICE 102 + , error1, error2 103 + #endif 104 + ); 105 + return 0; 106 + abort: 107 + RSEQ_INJECT_FAILED 108 + return -1; 109 + cmpfail: 110 + return 1; 111 + #ifdef RSEQ_COMPARE_TWICE 112 + error1: 113 + rseq_bug("cpu_id comparison failed"); 114 + error2: 115 + rseq_bug("expected value comparison failed"); 116 + #endif 117 + } 118 + 119 + static inline __always_inline 120 + int RSEQ_TEMPLATE_IDENTIFIER(rseq_addv)(intptr_t *v, intptr_t count, int cpu) 121 + { 122 + RSEQ_INJECT_C(9) 123 + 124 + __asm__ __volatile__ goto(RSEQ_ASM_DEFINE_TABLE(1, 2f, 3f, 4f) 125 + #ifdef RSEQ_COMPARE_TWICE 126 + RSEQ_ASM_DEFINE_EXIT_POINT(2f, "%l[error1]") 127 + #endif 128 + RSEQ_ASM_STORE_RSEQ_CS(2, 1b, rseq_cs) 129 + RSEQ_ASM_CMP_CPU_ID(cpu_id, current_cpu_id, 4f) 130 + RSEQ_INJECT_ASM(3) 131 + #ifdef RSEQ_COMPARE_TWICE 132 + RSEQ_ASM_CMP_CPU_ID(cpu_id, current_cpu_id, "%l[error1]") 133 + #endif 134 + RSEQ_ASM_OP_R_LOAD(v) 135 + RSEQ_ASM_OP_R_ADD(count) 136 + RSEQ_ASM_OP_R_FINAL_STORE(v, 3) 137 + RSEQ_INJECT_ASM(4) 138 + RSEQ_ASM_DEFINE_ABORT(4, abort) 139 + : /* gcc asm goto does not allow outputs */ 140 + : [cpu_id] "r" (cpu), 141 + [current_cpu_id] "m" (rseq_get_abi()->RSEQ_TEMPLATE_CPU_ID_FIELD), 142 + [rseq_cs] "m" (rseq_get_abi()->rseq_cs.arch.ptr), 143 + [v] "m" (*v), 144 + [count] "r" (count) 145 + RSEQ_INJECT_INPUT 146 + : "memory", RSEQ_ASM_TMP_REG_1 147 + RSEQ_INJECT_CLOBBER 148 + : abort 149 + #ifdef RSEQ_COMPARE_TWICE 150 + , error1 151 + #endif 152 + ); 153 + return 0; 154 + abort: 155 + RSEQ_INJECT_FAILED 156 + return -1; 157 + #ifdef RSEQ_COMPARE_TWICE 158 + error1: 159 + rseq_bug("cpu_id comparison failed"); 160 + #endif 161 + } 162 + 163 + static inline __always_inline 164 + int RSEQ_TEMPLATE_IDENTIFIER(rseq_cmpeqv_cmpeqv_storev)(intptr_t *v, intptr_t expect, 165 + intptr_t *v2, intptr_t expect2, 166 + intptr_t newv, int cpu) 167 + { 168 + RSEQ_INJECT_C(9) 169 + 170 + __asm__ __volatile__ goto(RSEQ_ASM_DEFINE_TABLE(1, 2f, 3f, 4f) 171 + RSEQ_ASM_DEFINE_EXIT_POINT(2f, "%l[cmpfail]") 172 + #ifdef RSEQ_COMPARE_TWICE 173 + RSEQ_ASM_DEFINE_EXIT_POINT(2f, "%l[error1]") 174 + RSEQ_ASM_DEFINE_EXIT_POINT(2f, "%l[error2]") 175 + RSEQ_ASM_DEFINE_EXIT_POINT(2f, "%l[error3]") 176 + #endif 177 + RSEQ_ASM_STORE_RSEQ_CS(2, 1b, rseq_cs) 178 + RSEQ_ASM_CMP_CPU_ID(cpu_id, current_cpu_id, 4f) 179 + RSEQ_INJECT_ASM(3) 180 + RSEQ_ASM_OP_CMPEQ(v, expect, "%l[cmpfail]") 181 + RSEQ_INJECT_ASM(4) 182 + RSEQ_ASM_OP_CMPEQ(v2, expect2, "%l[cmpfail]") 183 + RSEQ_INJECT_ASM(5) 184 + #ifdef RSEQ_COMPARE_TWICE 185 + RSEQ_ASM_CMP_CPU_ID(cpu_id, current_cpu_id, "%l[error1]") 186 + RSEQ_ASM_OP_CMPEQ(v, expect, "%l[error2]") 187 + RSEQ_ASM_OP_CMPEQ(v2, expect2, "%l[error3]") 188 + #endif 189 + RSEQ_ASM_OP_FINAL_STORE(v, newv, 3) 190 + RSEQ_INJECT_ASM(6) 191 + RSEQ_ASM_DEFINE_ABORT(4, abort) 192 + : /* gcc asm goto does not allow outputs */ 193 + : [cpu_id] "r" (cpu), 194 + [current_cpu_id] "m" (rseq_get_abi()->RSEQ_TEMPLATE_CPU_ID_FIELD), 195 + [rseq_cs] "m" (rseq_get_abi()->rseq_cs.arch.ptr), 196 + [v] "m" (*v), 197 + [expect] "r" (expect), 198 + [v2] "m" (*v2), 199 + [expect2] "r" (expect2), 200 + [newv] "r" (newv) 201 + RSEQ_INJECT_INPUT 202 + : "memory", RSEQ_ASM_TMP_REG_1 203 + RSEQ_INJECT_CLOBBER 204 + : abort, cmpfail 205 + #ifdef RSEQ_COMPARE_TWICE 206 + , error1, error2, error3 207 + #endif 208 + ); 209 + 210 + return 0; 211 + abort: 212 + RSEQ_INJECT_FAILED 213 + return -1; 214 + cmpfail: 215 + return 1; 216 + #ifdef RSEQ_COMPARE_TWICE 217 + error1: 218 + rseq_bug("cpu_id comparison failed"); 219 + error2: 220 + rseq_bug("expected value comparison failed"); 221 + error3: 222 + rseq_bug("2nd expected value comparison failed"); 223 + #endif 224 + } 225 + 226 + #define RSEQ_ARCH_HAS_OFFSET_DEREF_ADDV 227 + 228 + /* 229 + * pval = *(ptr+off) 230 + * *pval += inc; 231 + */ 232 + static inline __always_inline 233 + int RSEQ_TEMPLATE_IDENTIFIER(rseq_offset_deref_addv)(intptr_t *ptr, off_t off, intptr_t inc, 234 + int cpu) 235 + { 236 + RSEQ_INJECT_C(9) 237 + 238 + __asm__ __volatile__ goto(RSEQ_ASM_DEFINE_TABLE(1, 2f, 3f, 4f) 239 + #ifdef RSEQ_COMPARE_TWICE 240 + RSEQ_ASM_DEFINE_EXIT_POINT(2f, "%l[error1]") 241 + #endif 242 + RSEQ_ASM_STORE_RSEQ_CS(2, 1b, rseq_cs) 243 + RSEQ_ASM_CMP_CPU_ID(cpu_id, current_cpu_id, 4f) 244 + RSEQ_INJECT_ASM(3) 245 + #ifdef RSEQ_COMPARE_TWICE 246 + RSEQ_ASM_CMP_CPU_ID(cpu_id, current_cpu_id, "%l[error1]") 247 + #endif 248 + RSEQ_ASM_OP_R_DEREF_ADDV(ptr, off, inc, 3) 249 + RSEQ_INJECT_ASM(4) 250 + RSEQ_ASM_DEFINE_ABORT(4, abort) 251 + : /* gcc asm goto does not allow outputs */ 252 + : [cpu_id] "r" (cpu), 253 + [current_cpu_id] "m" (rseq_get_abi()->RSEQ_TEMPLATE_CPU_ID_FIELD), 254 + [rseq_cs] "m" (rseq_get_abi()->rseq_cs.arch.ptr), 255 + [ptr] "r" (ptr), 256 + [off] "r" (off), 257 + [inc] "r" (inc) 258 + RSEQ_INJECT_INPUT 259 + : "memory", RSEQ_ASM_TMP_REG_1 260 + RSEQ_INJECT_CLOBBER 261 + : abort 262 + #ifdef RSEQ_COMPARE_TWICE 263 + , error1 264 + #endif 265 + ); 266 + return 0; 267 + abort: 268 + RSEQ_INJECT_FAILED 269 + return -1; 270 + #ifdef RSEQ_COMPARE_TWICE 271 + error1: 272 + rseq_bug("cpu_id comparison failed"); 273 + #endif 274 + } 275 + 276 + #endif /* #if defined(RSEQ_TEMPLATE_MO_RELAXED) && 277 + (defined(RSEQ_TEMPLATE_CPU_ID) || defined(RSEQ_TEMPLATE_MM_CID)) */ 278 + 279 + #if (defined(RSEQ_TEMPLATE_MO_RELAXED) || defined(RSEQ_TEMPLATE_MO_RELEASE)) && \ 280 + (defined(RSEQ_TEMPLATE_CPU_ID) || defined(RSEQ_TEMPLATE_MM_CID)) 281 + 282 + static inline __always_inline 283 + int RSEQ_TEMPLATE_IDENTIFIER(rseq_cmpeqv_trystorev_storev)(intptr_t *v, intptr_t expect, 284 + intptr_t *v2, intptr_t newv2, 285 + intptr_t newv, int cpu) 286 + { 287 + RSEQ_INJECT_C(9) 288 + 289 + __asm__ __volatile__ goto(RSEQ_ASM_DEFINE_TABLE(1, 2f, 3f, 4f) 290 + RSEQ_ASM_DEFINE_EXIT_POINT(2f, "%l[cmpfail]") 291 + #ifdef RSEQ_COMPARE_TWICE 292 + RSEQ_ASM_DEFINE_EXIT_POINT(2f, "%l[error1]") 293 + RSEQ_ASM_DEFINE_EXIT_POINT(2f, "%l[error2]") 294 + #endif 295 + RSEQ_ASM_STORE_RSEQ_CS(2, 1b, rseq_cs) 296 + RSEQ_ASM_CMP_CPU_ID(cpu_id, current_cpu_id, 4f) 297 + RSEQ_INJECT_ASM(3) 298 + RSEQ_ASM_OP_CMPEQ(v, expect, "%l[cmpfail]") 299 + RSEQ_INJECT_ASM(4) 300 + #ifdef RSEQ_COMPARE_TWICE 301 + RSEQ_ASM_CMP_CPU_ID(cpu_id, current_cpu_id, "%l[error1]") 302 + RSEQ_ASM_OP_CMPEQ(v, expect, "%l[error2]") 303 + #endif 304 + RSEQ_ASM_OP_STORE(v2, newv2) 305 + RSEQ_INJECT_ASM(5) 306 + #ifdef RSEQ_TEMPLATE_MO_RELEASE 307 + RSEQ_ASM_OP_FINAL_STORE_RELEASE(v, newv, 3) 308 + #else 309 + RSEQ_ASM_OP_FINAL_STORE(v, newv, 3) 310 + #endif 311 + RSEQ_INJECT_ASM(6) 312 + RSEQ_ASM_DEFINE_ABORT(4, abort) 313 + : /* gcc asm goto does not allow outputs */ 314 + : [cpu_id] "r" (cpu), 315 + [current_cpu_id] "m" (rseq_get_abi()->RSEQ_TEMPLATE_CPU_ID_FIELD), 316 + [rseq_cs] "m" (rseq_get_abi()->rseq_cs.arch.ptr), 317 + [expect] "r" (expect), 318 + [v] "m" (*v), 319 + [newv] "r" (newv), 320 + [v2] "m" (*v2), 321 + [newv2] "r" (newv2) 322 + RSEQ_INJECT_INPUT 323 + : "memory", RSEQ_ASM_TMP_REG_1 324 + RSEQ_INJECT_CLOBBER 325 + : abort, cmpfail 326 + #ifdef RSEQ_COMPARE_TWICE 327 + , error1, error2 328 + #endif 329 + ); 330 + 331 + return 0; 332 + abort: 333 + RSEQ_INJECT_FAILED 334 + return -1; 335 + cmpfail: 336 + return 1; 337 + #ifdef RSEQ_COMPARE_TWICE 338 + error1: 339 + rseq_bug("cpu_id comparison failed"); 340 + error2: 341 + rseq_bug("expected value comparison failed"); 342 + #endif 343 + } 344 + 345 + static inline __always_inline 346 + int RSEQ_TEMPLATE_IDENTIFIER(rseq_cmpeqv_trymemcpy_storev)(intptr_t *v, intptr_t expect, 347 + void *dst, void *src, size_t len, 348 + intptr_t newv, int cpu) 349 + { 350 + RSEQ_INJECT_C(9) 351 + __asm__ __volatile__ goto(RSEQ_ASM_DEFINE_TABLE(1, 2f, 3f, 4f) 352 + RSEQ_ASM_DEFINE_EXIT_POINT(2f, "%l[cmpfail]") 353 + #ifdef RSEQ_COMPARE_TWICE 354 + RSEQ_ASM_DEFINE_EXIT_POINT(2f, "%l[error1]") 355 + RSEQ_ASM_DEFINE_EXIT_POINT(2f, "%l[error2]") 356 + #endif 357 + RSEQ_ASM_STORE_RSEQ_CS(2, 1b, rseq_cs) 358 + RSEQ_ASM_CMP_CPU_ID(cpu_id, current_cpu_id, 4f) 359 + RSEQ_INJECT_ASM(3) 360 + RSEQ_ASM_OP_CMPEQ(v, expect, "%l[cmpfail]") 361 + RSEQ_INJECT_ASM(4) 362 + #ifdef RSEQ_COMPARE_TWICE 363 + RSEQ_ASM_CMP_CPU_ID(cpu_id, current_cpu_id, "%l[error1]") 364 + RSEQ_ASM_OP_CMPEQ(v, expect, "%l[error2]") 365 + #endif 366 + RSEQ_ASM_OP_R_BAD_MEMCPY(dst, src, len) 367 + RSEQ_INJECT_ASM(5) 368 + #ifdef RSEQ_TEMPLATE_MO_RELEASE 369 + RSEQ_ASM_OP_FINAL_STORE_RELEASE(v, newv, 3) 370 + #else 371 + RSEQ_ASM_OP_FINAL_STORE(v, newv, 3) 372 + #endif 373 + RSEQ_INJECT_ASM(6) 374 + RSEQ_ASM_DEFINE_ABORT(4, abort) 375 + : /* gcc asm goto does not allow outputs */ 376 + : [cpu_id] "r" (cpu), 377 + [current_cpu_id] "m" (rseq_get_abi()->RSEQ_TEMPLATE_CPU_ID_FIELD), 378 + [rseq_cs] "m" (rseq_get_abi()->rseq_cs.arch.ptr), 379 + [expect] "r" (expect), 380 + [v] "m" (*v), 381 + [newv] "r" (newv), 382 + [dst] "r" (dst), 383 + [src] "r" (src), 384 + [len] "r" (len) 385 + RSEQ_INJECT_INPUT 386 + : "memory", RSEQ_ASM_TMP_REG_1, RSEQ_ASM_TMP_REG_2, 387 + RSEQ_ASM_TMP_REG_3, RSEQ_ASM_TMP_REG_4 388 + RSEQ_INJECT_CLOBBER 389 + : abort, cmpfail 390 + #ifdef RSEQ_COMPARE_TWICE 391 + , error1, error2 392 + #endif 393 + ); 394 + 395 + return 0; 396 + abort: 397 + RSEQ_INJECT_FAILED 398 + return -1; 399 + cmpfail: 400 + return 1; 401 + #ifdef RSEQ_COMPARE_TWICE 402 + error1: 403 + rseq_bug("cpu_id comparison failed"); 404 + error2: 405 + rseq_bug("expected value comparison failed"); 406 + #endif 407 + } 408 + 409 + #endif /* #if (defined(RSEQ_TEMPLATE_MO_RELAXED) || defined(RSEQ_TEMPLATE_MO_RELEASE)) && 410 + (defined(RSEQ_TEMPLATE_CPU_ID) || defined(RSEQ_TEMPLATE_MM_CID)) */ 411 + 412 + #include "rseq-bits-reset.h"
+13
tools/testing/selftests/rseq/rseq-or1k-thread-pointer.h
··· 1 + /* SPDX-License-Identifier: LGPL-2.1-only OR MIT */ 2 + #ifndef _RSEQ_OR1K_THREAD_POINTER 3 + #define _RSEQ_OR1K_THREAD_POINTER 4 + 5 + static inline void *rseq_thread_pointer(void) 6 + { 7 + void *__thread_register; 8 + 9 + __asm__ ("l.or %0, r10, r0" : "=r" (__thread_register)); 10 + return __thread_register; 11 + } 12 + 13 + #endif
+181
tools/testing/selftests/rseq/rseq-or1k.h
··· 1 + /* SPDX-License-Identifier: LGPL-2.1 OR MIT */ 2 + 3 + /* 4 + * Select the instruction "l.nop 0x35" as the RSEQ_SIG. 5 + */ 6 + #define RSEQ_SIG 0x15000035 7 + 8 + #define rseq_smp_mb() __asm__ __volatile__ ("l.msync" ::: "memory") 9 + #define rseq_smp_rmb() rseq_smp_mb() 10 + #define rseq_smp_wmb() rseq_smp_mb() 11 + #define RSEQ_ASM_TMP_REG_1 "r31" 12 + #define RSEQ_ASM_TMP_REG_2 "r29" 13 + #define RSEQ_ASM_TMP_REG_3 "r27" 14 + #define RSEQ_ASM_TMP_REG_4 "r25" 15 + 16 + #define rseq_smp_load_acquire(p) \ 17 + __extension__ ({ \ 18 + rseq_unqual_scalar_typeof(*(p)) ____p1 = RSEQ_READ_ONCE(*(p)); \ 19 + rseq_smp_mb(); \ 20 + ____p1; \ 21 + }) 22 + 23 + #define rseq_smp_acquire__after_ctrl_dep() rseq_smp_rmb() 24 + 25 + #define rseq_smp_store_release(p, v) \ 26 + do { \ 27 + rseq_smp_mb(); \ 28 + RSEQ_WRITE_ONCE(*(p), v); \ 29 + } while (0) 30 + 31 + #define __RSEQ_ASM_DEFINE_TABLE(label, version, flags, start_ip, \ 32 + post_commit_offset, abort_ip) \ 33 + ".pushsection __rseq_cs, \"aw\"\n" \ 34 + ".balign 32\n" \ 35 + __rseq_str(label) ":\n" \ 36 + ".long " __rseq_str(version) ", " __rseq_str(flags) "\n" \ 37 + ".long 0x0, " __rseq_str(start_ip) ", " \ 38 + "0x0, " __rseq_str(post_commit_offset) ", " \ 39 + "0x0, " __rseq_str(abort_ip) "\n" \ 40 + ".popsection\n\t" \ 41 + ".pushsection __rseq_cs_ptr_array, \"aw\"\n" \ 42 + ".long 0x0, " __rseq_str(label) "b\n" \ 43 + ".popsection\n" 44 + 45 + #define RSEQ_ASM_DEFINE_TABLE(label, start_ip, post_commit_ip, abort_ip) \ 46 + __RSEQ_ASM_DEFINE_TABLE(label, 0x0, 0x0, start_ip, \ 47 + ((post_commit_ip) - (start_ip)), abort_ip) 48 + 49 + /* 50 + * Exit points of a rseq critical section consist of all instructions outside 51 + * of the critical section where a critical section can either branch to or 52 + * reach through the normal course of its execution. The abort IP and the 53 + * post-commit IP are already part of the __rseq_cs section and should not be 54 + * explicitly defined as additional exit points. Knowing all exit points is 55 + * useful to assist debuggers stepping over the critical section. 56 + */ 57 + #define RSEQ_ASM_DEFINE_EXIT_POINT(start_ip, exit_ip) \ 58 + ".pushsection __rseq_exit_point_array, \"aw\"\n" \ 59 + ".long 0x0, " __rseq_str(start_ip) ", 0x0, " __rseq_str(exit_ip) "\n" \ 60 + ".popsection\n" 61 + 62 + #define RSEQ_ASM_STORE_RSEQ_CS(label, cs_label, rseq_cs) \ 63 + RSEQ_INJECT_ASM(1) \ 64 + "l.movhi " RSEQ_ASM_TMP_REG_1 ", hi(" __rseq_str(cs_label) ")\n"\ 65 + "l.ori " RSEQ_ASM_TMP_REG_1 ", " RSEQ_ASM_TMP_REG_1 \ 66 + ", lo(" __rseq_str(cs_label) ")\n"\ 67 + "l.sw %[" __rseq_str(rseq_cs) "], " RSEQ_ASM_TMP_REG_1 "\n" \ 68 + __rseq_str(label) ":\n" 69 + 70 + #define RSEQ_ASM_DEFINE_ABORT(label, abort_label) \ 71 + "l.j 222f\n" \ 72 + " l.nop\n" \ 73 + ".balign 4\n" \ 74 + ".long " __rseq_str(RSEQ_SIG) "\n" \ 75 + __rseq_str(label) ":\n" \ 76 + "l.j %l[" __rseq_str(abort_label) "]\n" \ 77 + " l.nop\n" \ 78 + "222:\n" 79 + 80 + #define RSEQ_ASM_OP_STORE(var, value) \ 81 + "l.sw %[" __rseq_str(var) "], %[" __rseq_str(value) "]\n" 82 + 83 + #define RSEQ_ASM_OP_CMPEQ(var, expect, label) \ 84 + "l.lwz " RSEQ_ASM_TMP_REG_1 ", %[" __rseq_str(var) "]\n" \ 85 + "l.sfne " RSEQ_ASM_TMP_REG_1 ", %[" __rseq_str(expect) "]\n" \ 86 + "l.bf " __rseq_str(label) "\n" \ 87 + " l.nop\n" 88 + 89 + #define RSEQ_ASM_OP_CMPNE(var, expect, label) \ 90 + "l.lwz " RSEQ_ASM_TMP_REG_1 ", %[" __rseq_str(var) "]\n" \ 91 + "l.sfeq " RSEQ_ASM_TMP_REG_1 ", %[" __rseq_str(expect) "]\n" \ 92 + "l.bf " __rseq_str(label) "\n" \ 93 + " l.nop\n" 94 + 95 + #define RSEQ_ASM_CMP_CPU_ID(cpu_id, current_cpu_id, label) \ 96 + RSEQ_INJECT_ASM(2) \ 97 + RSEQ_ASM_OP_CMPEQ(current_cpu_id, cpu_id, label) 98 + 99 + #define RSEQ_ASM_OP_R_LOAD(var) \ 100 + "l.lwz " RSEQ_ASM_TMP_REG_1 ", %[" __rseq_str(var) "]\n" 101 + 102 + #define RSEQ_ASM_OP_R_STORE(var) \ 103 + "l.sw %[" __rseq_str(var) "], " RSEQ_ASM_TMP_REG_1 "\n" 104 + 105 + #define RSEQ_ASM_OP_R_LOAD_OFF(offset) \ 106 + "l.lwz " RSEQ_ASM_TMP_REG_1 ", " \ 107 + "%[" __rseq_str(offset) "](" RSEQ_ASM_TMP_REG_1 ")\n" 108 + 109 + #define RSEQ_ASM_OP_R_ADD(count) \ 110 + "l.add " RSEQ_ASM_TMP_REG_1 ", " RSEQ_ASM_TMP_REG_1 \ 111 + ", %[" __rseq_str(count) "]\n" 112 + 113 + #define RSEQ_ASM_OP_FINAL_STORE(var, value, post_commit_label) \ 114 + RSEQ_ASM_OP_STORE(var, value) \ 115 + __rseq_str(post_commit_label) ":\n" 116 + 117 + #define RSEQ_ASM_OP_FINAL_STORE_RELEASE(var, value, post_commit_label) \ 118 + "l.msync\n" \ 119 + RSEQ_ASM_OP_STORE(var, value) \ 120 + __rseq_str(post_commit_label) ":\n" 121 + 122 + #define RSEQ_ASM_OP_R_FINAL_STORE(var, post_commit_label) \ 123 + "l.sw %[" __rseq_str(var) "], " RSEQ_ASM_TMP_REG_1 "\n" \ 124 + __rseq_str(post_commit_label) ":\n" 125 + 126 + #define RSEQ_ASM_OP_R_BAD_MEMCPY(dst, src, len) \ 127 + "l.sfeq %[" __rseq_str(len) "], r0\n" \ 128 + "l.bf 333f\n" \ 129 + " l.nop\n" \ 130 + "l.ori " RSEQ_ASM_TMP_REG_1 ", %[" __rseq_str(len) "], 0\n" \ 131 + "l.ori " RSEQ_ASM_TMP_REG_2 ", %[" __rseq_str(src) "], 0\n" \ 132 + "l.ori " RSEQ_ASM_TMP_REG_3 ", %[" __rseq_str(dst) "], 0\n" \ 133 + "222:\n" \ 134 + "l.lbz " RSEQ_ASM_TMP_REG_4 ", 0(" RSEQ_ASM_TMP_REG_2 ")\n" \ 135 + "l.sb 0(" RSEQ_ASM_TMP_REG_3 "), " RSEQ_ASM_TMP_REG_4 "\n" \ 136 + "l.addi " RSEQ_ASM_TMP_REG_1 ", " RSEQ_ASM_TMP_REG_1 ", -1\n" \ 137 + "l.addi " RSEQ_ASM_TMP_REG_2 ", " RSEQ_ASM_TMP_REG_2 ", 1\n" \ 138 + "l.addi " RSEQ_ASM_TMP_REG_3 ", " RSEQ_ASM_TMP_REG_3 ", 1\n" \ 139 + "l.sfne " RSEQ_ASM_TMP_REG_1 ", r0\n" \ 140 + "l.bf 222b\n" \ 141 + " l.nop\n" \ 142 + "333:\n" 143 + 144 + #define RSEQ_ASM_OP_R_DEREF_ADDV(ptr, off, inc, post_commit_label) \ 145 + "l.ori " RSEQ_ASM_TMP_REG_1 ", %[" __rseq_str(ptr) "], 0\n" \ 146 + RSEQ_ASM_OP_R_ADD(off) \ 147 + "l.lwz " RSEQ_ASM_TMP_REG_1 ", 0(" RSEQ_ASM_TMP_REG_1 ")\n" \ 148 + RSEQ_ASM_OP_R_ADD(inc) \ 149 + __rseq_str(post_commit_label) ":\n" 150 + 151 + /* Per-cpu-id indexing. */ 152 + 153 + #define RSEQ_TEMPLATE_CPU_ID 154 + #define RSEQ_TEMPLATE_MO_RELAXED 155 + #include "rseq-or1k-bits.h" 156 + #undef RSEQ_TEMPLATE_MO_RELAXED 157 + 158 + #define RSEQ_TEMPLATE_MO_RELEASE 159 + #include "rseq-or1k-bits.h" 160 + #undef RSEQ_TEMPLATE_MO_RELEASE 161 + #undef RSEQ_TEMPLATE_CPU_ID 162 + 163 + /* Per-mm-cid indexing. */ 164 + 165 + #define RSEQ_TEMPLATE_MM_CID 166 + #define RSEQ_TEMPLATE_MO_RELAXED 167 + #include "rseq-or1k-bits.h" 168 + #undef RSEQ_TEMPLATE_MO_RELAXED 169 + 170 + #define RSEQ_TEMPLATE_MO_RELEASE 171 + #include "rseq-or1k-bits.h" 172 + #undef RSEQ_TEMPLATE_MO_RELEASE 173 + #undef RSEQ_TEMPLATE_MM_CID 174 + 175 + /* APIs which are not based on cpu ids. */ 176 + 177 + #define RSEQ_TEMPLATE_CPU_ID_NONE 178 + #define RSEQ_TEMPLATE_MO_RELAXED 179 + #include "rseq-or1k-bits.h" 180 + #undef RSEQ_TEMPLATE_MO_RELAXED 181 + #undef RSEQ_TEMPLATE_CPU_ID_NONE
+2
tools/testing/selftests/rseq/rseq-thread-pointer.h
··· 12 12 #include "rseq-x86-thread-pointer.h" 13 13 #elif defined(__PPC__) 14 14 #include "rseq-ppc-thread-pointer.h" 15 + #elif defined(__or1k__) 16 + #include "rseq-or1k-thread-pointer.h" 15 17 #else 16 18 #include "rseq-generic-thread-pointer.h" 17 19 #endif
+2
tools/testing/selftests/rseq/rseq.h
··· 122 122 #include <rseq-s390.h> 123 123 #elif defined(__riscv) 124 124 #include <rseq-riscv.h> 125 + #elif defined(__or1k__) 126 + #include <rseq-or1k.h> 125 127 #else 126 128 #error unsupported target 127 129 #endif