init_signals.cc revision 11235
110453SAndrew.Bardsley@arm.com/* 211235Sandreas.sandberg@arm.com * Copyright (c) 2012, 2015 ARM Limited 310453SAndrew.Bardsley@arm.com * All rights reserved 410453SAndrew.Bardsley@arm.com * 510453SAndrew.Bardsley@arm.com * The license below extends only to copyright in the software and shall 610453SAndrew.Bardsley@arm.com * not be construed as granting a license to any other intellectual 710453SAndrew.Bardsley@arm.com * property including but not limited to intellectual property relating 810453SAndrew.Bardsley@arm.com * to a hardware implementation of the functionality of the software 910453SAndrew.Bardsley@arm.com * licensed hereunder. You may use the software subject to the license 1010453SAndrew.Bardsley@arm.com * terms below provided that you ensure that this notice is replicated 1110453SAndrew.Bardsley@arm.com * unmodified and in its entirety in all distributions of the software, 1210453SAndrew.Bardsley@arm.com * modified or unmodified, in source code or in binary form. 1310453SAndrew.Bardsley@arm.com * 1410453SAndrew.Bardsley@arm.com * Copyright (c) 2000-2005 The Regents of The University of Michigan 1510453SAndrew.Bardsley@arm.com * Copyright (c) 2008 The Hewlett-Packard Development Company 1610453SAndrew.Bardsley@arm.com * All rights reserved. 1710453SAndrew.Bardsley@arm.com * 1810453SAndrew.Bardsley@arm.com * Redistribution and use in source and binary forms, with or without 1910453SAndrew.Bardsley@arm.com * modification, are permitted provided that the following conditions are 2010453SAndrew.Bardsley@arm.com * met: redistributions of source code must retain the above copyright 2110453SAndrew.Bardsley@arm.com * notice, this list of conditions and the following disclaimer; 2210453SAndrew.Bardsley@arm.com * redistributions in binary form must reproduce the above copyright 2310453SAndrew.Bardsley@arm.com * notice, this list of conditions and the following disclaimer in the 2410453SAndrew.Bardsley@arm.com * documentation and/or other materials provided with the distribution; 2510453SAndrew.Bardsley@arm.com * neither the name of the copyright holders nor the names of its 2610453SAndrew.Bardsley@arm.com * contributors may be used to endorse or promote products derived from 2710453SAndrew.Bardsley@arm.com * this software without specific prior written permission. 2810453SAndrew.Bardsley@arm.com * 2910453SAndrew.Bardsley@arm.com * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 3010453SAndrew.Bardsley@arm.com * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 3110453SAndrew.Bardsley@arm.com * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 3210453SAndrew.Bardsley@arm.com * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 3310453SAndrew.Bardsley@arm.com * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 3410453SAndrew.Bardsley@arm.com * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 3510453SAndrew.Bardsley@arm.com * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 3610453SAndrew.Bardsley@arm.com * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 3710453SAndrew.Bardsley@arm.com * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 3810453SAndrew.Bardsley@arm.com * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 3910453SAndrew.Bardsley@arm.com * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 4010453SAndrew.Bardsley@arm.com * 4110453SAndrew.Bardsley@arm.com * Authors: Nathan Binkert 4210453SAndrew.Bardsley@arm.com */ 4310453SAndrew.Bardsley@arm.com 4411235Sandreas.sandberg@arm.com#include "sim/init_signals.hh" 4511235Sandreas.sandberg@arm.com 4611235Sandreas.sandberg@arm.com#include <sys/types.h> 4711235Sandreas.sandberg@arm.com#include <unistd.h> 4811235Sandreas.sandberg@arm.com 4910453SAndrew.Bardsley@arm.com#include <csignal> 5010453SAndrew.Bardsley@arm.com#include <iostream> 5110453SAndrew.Bardsley@arm.com#include <string> 5210453SAndrew.Bardsley@arm.com 5311235Sandreas.sandberg@arm.com#include "base/atomicio.hh" 5410453SAndrew.Bardsley@arm.com#include "base/cprintf.hh" 5510453SAndrew.Bardsley@arm.com#include "sim/async.hh" 5611235Sandreas.sandberg@arm.com#include "sim/backtrace.hh" 5710453SAndrew.Bardsley@arm.com#include "sim/core.hh" 5810476Sandreas.hansson@arm.com#include "sim/eventq.hh" 5910453SAndrew.Bardsley@arm.com 6010453SAndrew.Bardsley@arm.comusing namespace std; 6110453SAndrew.Bardsley@arm.com 6211235Sandreas.sandberg@arm.com// Use an separate stack for fatal signal handlers 6311235Sandreas.sandberg@arm.comstatic uint8_t fatalSigStack[2 * SIGSTKSZ]; 6411235Sandreas.sandberg@arm.com 6511235Sandreas.sandberg@arm.comstatic bool 6611235Sandreas.sandberg@arm.comsetupAltStack() 6711235Sandreas.sandberg@arm.com{ 6811235Sandreas.sandberg@arm.com stack_t stack; 6911235Sandreas.sandberg@arm.com stack.ss_sp = fatalSigStack; 7011235Sandreas.sandberg@arm.com stack.ss_size = sizeof(fatalSigStack); 7111235Sandreas.sandberg@arm.com stack.ss_flags = 0; 7211235Sandreas.sandberg@arm.com 7311235Sandreas.sandberg@arm.com return sigaltstack(&stack, NULL) == 0; 7411235Sandreas.sandberg@arm.com} 7511235Sandreas.sandberg@arm.com 7611235Sandreas.sandberg@arm.comstatic void 7711235Sandreas.sandberg@arm.cominstallSignalHandler(int signal, void (*handler)(int sigtype), 7811235Sandreas.sandberg@arm.com int flags = SA_RESTART) 7911235Sandreas.sandberg@arm.com{ 8011235Sandreas.sandberg@arm.com struct sigaction sa; 8111235Sandreas.sandberg@arm.com 8211235Sandreas.sandberg@arm.com memset(&sa, 0, sizeof(sa)); 8311235Sandreas.sandberg@arm.com sigemptyset(&sa.sa_mask); 8411235Sandreas.sandberg@arm.com sa.sa_handler = handler; 8511235Sandreas.sandberg@arm.com sa.sa_flags = flags; 8611235Sandreas.sandberg@arm.com 8711235Sandreas.sandberg@arm.com if (sigaction(signal, &sa, NULL) == -1) 8811235Sandreas.sandberg@arm.com panic("Failed to setup handler for signal %i\n", signal); 8911235Sandreas.sandberg@arm.com} 9011235Sandreas.sandberg@arm.com 9111235Sandreas.sandberg@arm.comstatic void 9211235Sandreas.sandberg@arm.comraiseFatalSignal(int signo) 9311235Sandreas.sandberg@arm.com{ 9411235Sandreas.sandberg@arm.com // The signal handler should have been reset and unmasked (it was 9511235Sandreas.sandberg@arm.com // registered with SA_RESETHAND | SA_NODEFER), just raise the 9611235Sandreas.sandberg@arm.com // signal again to invoke the default handler. 9711235Sandreas.sandberg@arm.com pthread_kill(pthread_self(), signo); 9811235Sandreas.sandberg@arm.com 9911235Sandreas.sandberg@arm.com // Something is really wrong if the process is alive at this 10011235Sandreas.sandberg@arm.com // point, manually try to exit it. 10111235Sandreas.sandberg@arm.com STATIC_ERR("Failed to execute default signal handler!\n"); 10211235Sandreas.sandberg@arm.com _exit(127); 10311235Sandreas.sandberg@arm.com} 10411235Sandreas.sandberg@arm.com 10510453SAndrew.Bardsley@arm.com/// Stats signal handler. 10610453SAndrew.Bardsley@arm.comvoid 10710453SAndrew.Bardsley@arm.comdumpStatsHandler(int sigtype) 10810453SAndrew.Bardsley@arm.com{ 10910453SAndrew.Bardsley@arm.com async_event = true; 11010453SAndrew.Bardsley@arm.com async_statdump = true; 11110476Sandreas.hansson@arm.com /* Wake up some event queue to handle event */ 11210476Sandreas.hansson@arm.com getEventQueue(0)->wakeup(); 11310453SAndrew.Bardsley@arm.com} 11410453SAndrew.Bardsley@arm.com 11510453SAndrew.Bardsley@arm.comvoid 11610453SAndrew.Bardsley@arm.comdumprstStatsHandler(int sigtype) 11710453SAndrew.Bardsley@arm.com{ 11810453SAndrew.Bardsley@arm.com async_event = true; 11910453SAndrew.Bardsley@arm.com async_statdump = true; 12010453SAndrew.Bardsley@arm.com async_statreset = true; 12110476Sandreas.hansson@arm.com /* Wake up some event queue to handle event */ 12210476Sandreas.hansson@arm.com getEventQueue(0)->wakeup(); 12310453SAndrew.Bardsley@arm.com} 12410453SAndrew.Bardsley@arm.com 12510453SAndrew.Bardsley@arm.com/// Exit signal handler. 12610453SAndrew.Bardsley@arm.comvoid 12710453SAndrew.Bardsley@arm.comexitNowHandler(int sigtype) 12810453SAndrew.Bardsley@arm.com{ 12910453SAndrew.Bardsley@arm.com async_event = true; 13010453SAndrew.Bardsley@arm.com async_exit = true; 13110476Sandreas.hansson@arm.com /* Wake up some event queue to handle event */ 13210476Sandreas.hansson@arm.com getEventQueue(0)->wakeup(); 13310453SAndrew.Bardsley@arm.com} 13410453SAndrew.Bardsley@arm.com 13510453SAndrew.Bardsley@arm.com/// Abort signal handler. 13610453SAndrew.Bardsley@arm.comvoid 13710453SAndrew.Bardsley@arm.comabortHandler(int sigtype) 13810453SAndrew.Bardsley@arm.com{ 13911235Sandreas.sandberg@arm.com const EventQueue *const eq(curEventQueue()); 14011235Sandreas.sandberg@arm.com if (eq) { 14111235Sandreas.sandberg@arm.com ccprintf(cerr, "Program aborted at tick %llu\n", eq->getCurTick()); 14211235Sandreas.sandberg@arm.com } else { 14311235Sandreas.sandberg@arm.com STATIC_ERR("Program aborted\n\n"); 14411235Sandreas.sandberg@arm.com } 14511235Sandreas.sandberg@arm.com 14611235Sandreas.sandberg@arm.com print_backtrace(); 14711235Sandreas.sandberg@arm.com raiseFatalSignal(sigtype); 14811235Sandreas.sandberg@arm.com} 14911235Sandreas.sandberg@arm.com 15011235Sandreas.sandberg@arm.com/// Segmentation fault signal handler. 15111235Sandreas.sandberg@arm.comstatic void 15211235Sandreas.sandberg@arm.comsegvHandler(int sigtype) 15311235Sandreas.sandberg@arm.com{ 15411235Sandreas.sandberg@arm.com STATIC_ERR("gem5 has encountered a segmentation fault!\n\n"); 15511235Sandreas.sandberg@arm.com 15611235Sandreas.sandberg@arm.com print_backtrace(); 15711235Sandreas.sandberg@arm.com raiseFatalSignal(SIGSEGV); 15810453SAndrew.Bardsley@arm.com} 15910453SAndrew.Bardsley@arm.com 16010453SAndrew.Bardsley@arm.com// Handle SIGIO 16110453SAndrew.Bardsley@arm.comstatic void 16210453SAndrew.Bardsley@arm.comioHandler(int sigtype) 16310453SAndrew.Bardsley@arm.com{ 16410453SAndrew.Bardsley@arm.com async_event = true; 16510453SAndrew.Bardsley@arm.com async_io = true; 16610476Sandreas.hansson@arm.com /* Wake up some event queue to handle event */ 16710476Sandreas.hansson@arm.com getEventQueue(0)->wakeup(); 16810453SAndrew.Bardsley@arm.com} 16910453SAndrew.Bardsley@arm.com 17010453SAndrew.Bardsley@arm.com/* 17110453SAndrew.Bardsley@arm.com * M5 can do several special things when various signals are sent. 17210453SAndrew.Bardsley@arm.com * None are mandatory. 17310453SAndrew.Bardsley@arm.com */ 17410453SAndrew.Bardsley@arm.comvoid 17510453SAndrew.Bardsley@arm.cominitSignals() 17610453SAndrew.Bardsley@arm.com{ 17710453SAndrew.Bardsley@arm.com // Floating point exceptions may happen on misspeculated paths, so 17810453SAndrew.Bardsley@arm.com // ignore them 17910453SAndrew.Bardsley@arm.com signal(SIGFPE, SIG_IGN); 18010453SAndrew.Bardsley@arm.com 18110453SAndrew.Bardsley@arm.com // We use SIGTRAP sometimes for debugging 18210453SAndrew.Bardsley@arm.com signal(SIGTRAP, SIG_IGN); 18310453SAndrew.Bardsley@arm.com 18410453SAndrew.Bardsley@arm.com // Dump intermediate stats 18510453SAndrew.Bardsley@arm.com installSignalHandler(SIGUSR1, dumpStatsHandler); 18610453SAndrew.Bardsley@arm.com 18710453SAndrew.Bardsley@arm.com // Dump intermediate stats and reset them 18810453SAndrew.Bardsley@arm.com installSignalHandler(SIGUSR2, dumprstStatsHandler); 18910453SAndrew.Bardsley@arm.com 19010453SAndrew.Bardsley@arm.com // Exit cleanly on Interrupt (Ctrl-C) 19110453SAndrew.Bardsley@arm.com installSignalHandler(SIGINT, exitNowHandler); 19210453SAndrew.Bardsley@arm.com 19311235Sandreas.sandberg@arm.com // Print the current cycle number and a backtrace on abort. Make 19411235Sandreas.sandberg@arm.com // sure the signal is unmasked and the handler reset when a signal 19511235Sandreas.sandberg@arm.com // is delivered to be able to invoke the default handler. 19611235Sandreas.sandberg@arm.com installSignalHandler(SIGABRT, abortHandler, SA_RESETHAND | SA_NODEFER); 19711235Sandreas.sandberg@arm.com 19811235Sandreas.sandberg@arm.com // Setup a SIGSEGV handler with a private stack 19911235Sandreas.sandberg@arm.com if (setupAltStack()) { 20011235Sandreas.sandberg@arm.com installSignalHandler(SIGSEGV, segvHandler, 20111235Sandreas.sandberg@arm.com SA_RESETHAND | SA_NODEFER | SA_ONSTACK); 20211235Sandreas.sandberg@arm.com } else { 20311235Sandreas.sandberg@arm.com warn("Failed to setup stack for SIGSEGV handler, " 20411235Sandreas.sandberg@arm.com "using default signal handler.\n"); 20511235Sandreas.sandberg@arm.com } 20610453SAndrew.Bardsley@arm.com 20710453SAndrew.Bardsley@arm.com // Install a SIGIO handler to handle asynchronous file IO. See the 20810453SAndrew.Bardsley@arm.com // PollQueue class. 20910453SAndrew.Bardsley@arm.com installSignalHandler(SIGIO, ioHandler); 21010453SAndrew.Bardsley@arm.com} 21110453SAndrew.Bardsley@arm.com 212