78 lines · c
1// SPDX-License-Identifier: GPL-2.0-only2/*3 * Copyright 2015, Michael Neuling, IBM Corp.4 *5 * Test the kernel's signal delievery code to ensure that we don't6 * trelaim twice in the kernel signal delivery code. This can happen7 * if we trigger a signal when in a transaction and the stack pointer8 * is bogus.9 *10 * This test case registers a SEGV handler, sets the stack pointer11 * (r1) to NULL, starts a transaction and then generates a SEGV. The12 * SEGV should be handled but we exit here as the stack pointer is13 * invalid and hance we can't sigreturn. We only need to check that14 * this flow doesn't crash the kernel.15 */16 17#include <unistd.h>18#include <sys/types.h>19#include <sys/wait.h>20#include <stdlib.h>21#include <stdio.h>22#include <signal.h>23 24#include "utils.h"25#include "tm.h"26 27void signal_segv(int signum)28{29 /* This should never actually run since stack is foobar */30 exit(1);31}32 33int tm_signal_stack()34{35 int pid;36 37 SKIP_IF(!have_htm());38 SKIP_IF(htm_is_synthetic());39 40 pid = fork();41 if (pid < 0)42 exit(1);43 44 if (pid) { /* Parent */45 /*46 * It's likely the whole machine will crash here so if47 * the child ever exits, we are good.48 */49 wait(NULL);50 return 0;51 }52 53 /*54 * The flow here is:55 * 1) register a signal handler (so signal delievery occurs)56 * 2) make stack pointer (r1) = NULL57 * 3) start transaction58 * 4) cause segv59 */60 if (signal(SIGSEGV, signal_segv) == SIG_ERR)61 exit(1);62 asm volatile("li 1, 0 ;" /* stack ptr == NULL */63 "1:"64 "tbegin.;"65 "beq 1b ;" /* retry forever */66 "tsuspend.;"67 "ld 2, 0(1) ;" /* trigger segv" */68 : : : "memory");69 70 /* This should never get here due to above segv */71 return 1;72}73 74int main(void)75{76 return test_harness(tm_signal_stack, "tm_signal_stack");77}78