Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 1 | /* |
| 2 | * sigcatcher.c --- print a backtrace on a SIGSEGV, et. al |
| 3 | * |
| 4 | * Copyright (C) 2011 Theodore Ts'o. |
| 5 | * |
| 6 | * %Begin-Header% |
| 7 | * This file may be redistributed under the terms of the GNU Public |
| 8 | * License. |
| 9 | * %End-Header% |
| 10 | */ |
| 11 | |
Theodore Ts'o | d1154eb | 2011-09-18 17:34:37 -0400 | [diff] [blame] | 12 | #include "config.h" |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 13 | #include <stdio.h> |
| 14 | #include <stdlib.h> |
| 15 | #include <signal.h> |
| 16 | #include <string.h> |
| 17 | #ifdef HAVE_EXECINFO_H |
| 18 | #include <execinfo.h> |
| 19 | #endif |
| 20 | |
| 21 | #include "e2fsck.h" |
| 22 | |
| 23 | struct str_table { |
| 24 | int num; |
| 25 | const char *name; |
| 26 | }; |
| 27 | |
| 28 | #define DEFINE_ENTRY(SYM) { SYM, #SYM }, |
| 29 | #define END_TABLE { 0, 0 } |
| 30 | |
| 31 | static struct str_table sig_table[] = { |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 32 | #ifdef SIGHUP |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 33 | DEFINE_ENTRY(SIGHUP) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 34 | #endif |
| 35 | #ifdef SIGINT |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 36 | DEFINE_ENTRY(SIGINT) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 37 | #endif |
| 38 | #ifdef SIGQUIT |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 39 | DEFINE_ENTRY(SIGQUIT) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 40 | #endif |
| 41 | #ifdef SIGILL |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 42 | DEFINE_ENTRY(SIGILL) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 43 | #endif |
| 44 | #ifdef SIGTRAP |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 45 | DEFINE_ENTRY(SIGTRAP) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 46 | #endif |
| 47 | #ifdef SIGABRT |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 48 | DEFINE_ENTRY(SIGABRT) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 49 | #endif |
| 50 | #ifdef SIGIOT |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 51 | DEFINE_ENTRY(SIGIOT) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 52 | #endif |
| 53 | #ifdef SIGBUS |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 54 | DEFINE_ENTRY(SIGBUS) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 55 | #endif |
| 56 | #ifdef SIGFPE |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 57 | DEFINE_ENTRY(SIGFPE) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 58 | #endif |
| 59 | #ifdef SIGKILL |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 60 | DEFINE_ENTRY(SIGKILL) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 61 | #endif |
| 62 | #ifdef SIGUSR1 |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 63 | DEFINE_ENTRY(SIGUSR1) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 64 | #endif |
| 65 | #ifdef SIGSEGV |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 66 | DEFINE_ENTRY(SIGSEGV) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 67 | #endif |
| 68 | #ifdef SIGUSR2 |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 69 | DEFINE_ENTRY(SIGUSR2) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 70 | #endif |
| 71 | #ifdef SIGPIPE |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 72 | DEFINE_ENTRY(SIGPIPE) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 73 | #endif |
| 74 | #ifdef SIGALRM |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 75 | DEFINE_ENTRY(SIGALRM) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 76 | #endif |
| 77 | #ifdef SIGTERM |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 78 | DEFINE_ENTRY(SIGTERM) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 79 | #endif |
| 80 | #ifdef SIGSTKFLT |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 81 | DEFINE_ENTRY(SIGSTKFLT) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 82 | #endif |
| 83 | #ifdef SIGCHLD |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 84 | DEFINE_ENTRY(SIGCHLD) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 85 | #endif |
| 86 | #ifdef SIGCONT |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 87 | DEFINE_ENTRY(SIGCONT) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 88 | #endif |
| 89 | #ifdef SIGSTOP |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 90 | DEFINE_ENTRY(SIGSTOP) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 91 | #endif |
| 92 | #ifdef SIGTSTP |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 93 | DEFINE_ENTRY(SIGTSTP) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 94 | #endif |
| 95 | #ifdef SIGTTIN |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 96 | DEFINE_ENTRY(SIGTTIN) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 97 | #endif |
| 98 | #ifdef SIGTTOU |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 99 | DEFINE_ENTRY(SIGTTOU) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 100 | #endif |
| 101 | #ifdef SIGURG |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 102 | DEFINE_ENTRY(SIGURG) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 103 | #endif |
| 104 | #ifdef SIGXCPU |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 105 | DEFINE_ENTRY(SIGXCPU) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 106 | #endif |
| 107 | #ifdef SIGXFSZ |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 108 | DEFINE_ENTRY(SIGXFSZ) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 109 | #endif |
| 110 | #ifdef SIGVTALRM |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 111 | DEFINE_ENTRY(SIGVTALRM) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 112 | #endif |
| 113 | #ifdef SIGPROF |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 114 | DEFINE_ENTRY(SIGPROF) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 115 | #endif |
| 116 | #ifdef SIGWINCH |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 117 | DEFINE_ENTRY(SIGWINCH) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 118 | #endif |
| 119 | #ifdef SIGIO |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 120 | DEFINE_ENTRY(SIGIO) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 121 | #endif |
| 122 | #ifdef SIGPOLL |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 123 | DEFINE_ENTRY(SIGPOLL) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 124 | #endif |
| 125 | #ifdef SIGPWR |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 126 | DEFINE_ENTRY(SIGPWR) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 127 | #endif |
| 128 | #ifdef SIGSYS |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 129 | DEFINE_ENTRY(SIGSYS) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 130 | #endif |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 131 | END_TABLE |
| 132 | }; |
| 133 | |
| 134 | static struct str_table generic_code_table[] = { |
Theodore Ts'o | 1c5ffb6 | 2011-10-04 10:36:47 -0400 | [diff] [blame] | 135 | #ifdef SI_ASYNCNL |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 136 | DEFINE_ENTRY(SI_ASYNCNL) |
Theodore Ts'o | 1c5ffb6 | 2011-10-04 10:36:47 -0400 | [diff] [blame] | 137 | #endif |
| 138 | #ifdef SI_TKILL |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 139 | DEFINE_ENTRY(SI_TKILL) |
Theodore Ts'o | 1c5ffb6 | 2011-10-04 10:36:47 -0400 | [diff] [blame] | 140 | #endif |
| 141 | #ifdef SI_SIGIO |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 142 | DEFINE_ENTRY(SI_SIGIO) |
Theodore Ts'o | 1c5ffb6 | 2011-10-04 10:36:47 -0400 | [diff] [blame] | 143 | #endif |
| 144 | #ifdef SI_ASYNCIO |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 145 | DEFINE_ENTRY(SI_ASYNCIO) |
Theodore Ts'o | 1c5ffb6 | 2011-10-04 10:36:47 -0400 | [diff] [blame] | 146 | #endif |
| 147 | #ifdef SI_MESGQ |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 148 | DEFINE_ENTRY(SI_MESGQ) |
Theodore Ts'o | 1c5ffb6 | 2011-10-04 10:36:47 -0400 | [diff] [blame] | 149 | #endif |
| 150 | #ifdef SI_TIMER |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 151 | DEFINE_ENTRY(SI_TIMER) |
Theodore Ts'o | 1c5ffb6 | 2011-10-04 10:36:47 -0400 | [diff] [blame] | 152 | #endif |
| 153 | #ifdef SI_QUEUE |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 154 | DEFINE_ENTRY(SI_QUEUE) |
Theodore Ts'o | 1c5ffb6 | 2011-10-04 10:36:47 -0400 | [diff] [blame] | 155 | #endif |
| 156 | #ifdef SI_USER |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 157 | DEFINE_ENTRY(SI_USER) |
Theodore Ts'o | 1c5ffb6 | 2011-10-04 10:36:47 -0400 | [diff] [blame] | 158 | #endif |
| 159 | #ifdef SI_KERNEL |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 160 | DEFINE_ENTRY(SI_KERNEL) |
Theodore Ts'o | 1c5ffb6 | 2011-10-04 10:36:47 -0400 | [diff] [blame] | 161 | #endif |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 162 | END_TABLE |
| 163 | }; |
| 164 | |
| 165 | static struct str_table sigill_code_table[] = { |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 166 | #ifdef ILL_ILLOPC |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 167 | DEFINE_ENTRY(ILL_ILLOPC) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 168 | #endif |
| 169 | #ifdef ILL_ILLOPN |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 170 | DEFINE_ENTRY(ILL_ILLOPN) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 171 | #endif |
| 172 | #ifdef ILL_ILLADR |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 173 | DEFINE_ENTRY(ILL_ILLADR) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 174 | #endif |
| 175 | #ifdef ILL_ILLTRP |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 176 | DEFINE_ENTRY(ILL_ILLTRP) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 177 | #endif |
| 178 | #ifdef ILL_PRVOPC |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 179 | DEFINE_ENTRY(ILL_PRVOPC) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 180 | #endif |
| 181 | #ifdef ILL_PRVREG |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 182 | DEFINE_ENTRY(ILL_PRVREG) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 183 | #endif |
| 184 | #ifdef ILL_COPROC |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 185 | DEFINE_ENTRY(ILL_COPROC) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 186 | #endif |
| 187 | #ifdef ILL_BADSTK |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 188 | DEFINE_ENTRY(ILL_BADSTK) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 189 | #endif |
| 190 | #ifdef BUS_ADRALN |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 191 | DEFINE_ENTRY(BUS_ADRALN) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 192 | #endif |
| 193 | #ifdef BUS_ADRERR |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 194 | DEFINE_ENTRY(BUS_ADRERR) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 195 | #endif |
| 196 | #ifdef BUS_OBJERR |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 197 | DEFINE_ENTRY(BUS_OBJERR) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 198 | #endif |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 199 | END_TABLE |
| 200 | }; |
| 201 | |
| 202 | static struct str_table sigfpe_code_table[] = { |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 203 | #ifdef FPE_INTDIV |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 204 | DEFINE_ENTRY(FPE_INTDIV) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 205 | #endif |
| 206 | #ifdef FPE_INTOVF |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 207 | DEFINE_ENTRY(FPE_INTOVF) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 208 | #endif |
| 209 | #ifdef FPE_FLTDIV |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 210 | DEFINE_ENTRY(FPE_FLTDIV) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 211 | #endif |
| 212 | #ifdef FPE_FLTOVF |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 213 | DEFINE_ENTRY(FPE_FLTOVF) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 214 | #endif |
| 215 | #ifdef FPE_FLTUND |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 216 | DEFINE_ENTRY(FPE_FLTUND) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 217 | #endif |
| 218 | #ifdef FPE_FLTRES |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 219 | DEFINE_ENTRY(FPE_FLTRES) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 220 | #endif |
| 221 | #ifdef FPE_FLTINV |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 222 | DEFINE_ENTRY(FPE_FLTINV) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 223 | #endif |
| 224 | #ifdef FPE_FLTSUB |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 225 | DEFINE_ENTRY(FPE_FLTSUB) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 226 | #endif |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 227 | END_TABLE |
| 228 | }; |
| 229 | |
| 230 | static struct str_table sigsegv_code_table[] = { |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 231 | #ifdef SEGV_MAPERR |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 232 | DEFINE_ENTRY(SEGV_MAPERR) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 233 | #endif |
| 234 | #ifdef SEGV_ACCERR |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 235 | DEFINE_ENTRY(SEGV_ACCERR) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 236 | #endif |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 237 | END_TABLE |
| 238 | }; |
| 239 | |
| 240 | |
| 241 | static struct str_table sigbus_code_table[] = { |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 242 | #ifdef BUS_ADRALN |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 243 | DEFINE_ENTRY(BUS_ADRALN) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 244 | #endif |
| 245 | #ifdef BUS_ADRERR |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 246 | DEFINE_ENTRY(BUS_ADRERR) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 247 | #endif |
| 248 | #ifdef BUS_OBJERR |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 249 | DEFINE_ENTRY(BUS_OBJERR) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 250 | #endif |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 251 | END_TABLE |
| 252 | }; |
| 253 | |
Andreas Dilger | 00eb0ee | 2012-11-29 05:47:53 -0700 | [diff] [blame] | 254 | #if 0 /* should this be hooked in somewhere? */ |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 255 | static struct str_table sigstrap_code_table[] = { |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 256 | #ifdef TRAP_BRKPT |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 257 | DEFINE_ENTRY(TRAP_BRKPT) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 258 | #endif |
| 259 | #ifdef TRAP_TRACE |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 260 | DEFINE_ENTRY(TRAP_TRACE) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 261 | #endif |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 262 | END_TABLE |
| 263 | }; |
Andreas Dilger | 00eb0ee | 2012-11-29 05:47:53 -0700 | [diff] [blame] | 264 | #endif |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 265 | |
| 266 | static struct str_table sigcld_code_table[] = { |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 267 | #ifdef CLD_EXITED |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 268 | DEFINE_ENTRY(CLD_EXITED) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 269 | #endif |
| 270 | #ifdef CLD_KILLED |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 271 | DEFINE_ENTRY(CLD_KILLED) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 272 | #endif |
| 273 | #ifdef CLD_DUMPED |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 274 | DEFINE_ENTRY(CLD_DUMPED) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 275 | #endif |
| 276 | #ifdef CLD_TRAPPED |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 277 | DEFINE_ENTRY(CLD_TRAPPED) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 278 | #endif |
| 279 | #ifdef CLD_STOPPED |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 280 | DEFINE_ENTRY(CLD_STOPPED) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 281 | #endif |
| 282 | #ifdef CLD_CONTINUED |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 283 | DEFINE_ENTRY(CLD_CONTINUED) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 284 | #endif |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 285 | END_TABLE |
| 286 | }; |
| 287 | |
Andreas Dilger | 00eb0ee | 2012-11-29 05:47:53 -0700 | [diff] [blame] | 288 | #if 0 /* should this be hooked in somewhere? */ |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 289 | static struct str_table sigpoll_code_table[] = { |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 290 | #ifdef POLL_IN |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 291 | DEFINE_ENTRY(POLL_IN) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 292 | #endif |
| 293 | #ifdef POLL_OUT |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 294 | DEFINE_ENTRY(POLL_OUT) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 295 | #endif |
| 296 | #ifdef POLL_MSG |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 297 | DEFINE_ENTRY(POLL_MSG) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 298 | #endif |
| 299 | #ifdef POLL_ERR |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 300 | DEFINE_ENTRY(POLL_ERR) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 301 | #endif |
| 302 | #ifdef POLL_PRI |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 303 | DEFINE_ENTRY(POLL_PRI) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 304 | #endif |
| 305 | #ifdef POLL_HUP |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 306 | DEFINE_ENTRY(POLL_HUP) |
Theodore Ts'o | 0dbb256 | 2011-09-28 22:09:14 -0400 | [diff] [blame] | 307 | #endif |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 308 | END_TABLE |
| 309 | }; |
Andreas Dilger | 00eb0ee | 2012-11-29 05:47:53 -0700 | [diff] [blame] | 310 | #endif |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 311 | |
| 312 | static const char *lookup_table(int num, struct str_table *table) |
| 313 | { |
| 314 | struct str_table *p; |
| 315 | |
| 316 | for (p=table; p->name; p++) |
| 317 | if (num == p->num) |
| 318 | return(p->name); |
| 319 | return NULL; |
| 320 | } |
| 321 | |
| 322 | static const char *lookup_table_fallback(int num, struct str_table *table) |
| 323 | { |
| 324 | static char buf[32]; |
| 325 | const char *ret = lookup_table(num, table); |
| 326 | |
| 327 | if (ret) |
| 328 | return ret; |
| 329 | snprintf(buf, sizeof(buf), "%d", num); |
| 330 | buf[sizeof(buf)-1] = 0; |
| 331 | return buf; |
| 332 | } |
| 333 | |
| 334 | static void die_signal_handler(int signum, siginfo_t *siginfo, void *context) |
| 335 | { |
| 336 | void *stack_syms[32]; |
| 337 | int frames; |
| 338 | const char *cp; |
| 339 | |
| 340 | fprintf(stderr, "Signal (%d) %s ", signum, |
| 341 | lookup_table_fallback(signum, sig_table)); |
| 342 | if (siginfo->si_code == SI_USER) |
| 343 | fprintf(stderr, "(sent from pid %u) ", siginfo->si_pid); |
| 344 | cp = lookup_table(siginfo->si_code, generic_code_table); |
| 345 | if (cp) |
| 346 | fprintf(stderr, "si_code=%s ", cp); |
| 347 | else if (signum == SIGILL) |
| 348 | fprintf(stderr, "si_code=%s ", |
| 349 | lookup_table_fallback(siginfo->si_code, |
| 350 | sigill_code_table)); |
| 351 | else if (signum == SIGFPE) |
| 352 | fprintf(stderr, "si_code=%s ", |
| 353 | lookup_table_fallback(siginfo->si_code, |
| 354 | sigfpe_code_table)); |
| 355 | else if (signum == SIGSEGV) |
| 356 | fprintf(stderr, "si_code=%s ", |
| 357 | lookup_table_fallback(siginfo->si_code, |
| 358 | sigsegv_code_table)); |
| 359 | else if (signum == SIGBUS) |
| 360 | fprintf(stderr, "si_code=%s ", |
| 361 | lookup_table_fallback(siginfo->si_code, |
| 362 | sigbus_code_table)); |
Theodore Ts'o | 048c0e4 | 2011-10-05 14:47:09 -0400 | [diff] [blame] | 363 | else if (signum == SIGCHLD) |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 364 | fprintf(stderr, "si_code=%s ", |
| 365 | lookup_table_fallback(siginfo->si_code, |
| 366 | sigcld_code_table)); |
| 367 | else |
| 368 | fprintf(stderr, "si code=%d ", siginfo->si_code); |
| 369 | if ((siginfo->si_code != SI_USER) && |
| 370 | (signum == SIGILL || signum == SIGFPE || |
| 371 | signum == SIGSEGV || signum == SIGBUS)) |
| 372 | fprintf(stderr, "fault addr=%p", siginfo->si_addr); |
| 373 | fprintf(stderr, "\n"); |
| 374 | |
| 375 | #ifdef HAVE_BACKTRACE |
| 376 | frames = backtrace(stack_syms, 32); |
| 377 | backtrace_symbols_fd(stack_syms, frames, 2); |
| 378 | #endif |
| 379 | exit(FSCK_ERROR); |
| 380 | } |
| 381 | |
| 382 | void sigcatcher_setup(void) |
| 383 | { |
| 384 | struct sigaction sa; |
| 385 | |
Theodore Ts'o | dd62d85 | 2011-09-03 09:43:50 -0400 | [diff] [blame] | 386 | memset(&sa, 0, sizeof(struct sigaction)); |
Theodore Ts'o | 9b3018a | 2011-08-11 14:56:49 -0400 | [diff] [blame] | 387 | sa.sa_sigaction = die_signal_handler; |
| 388 | sa.sa_flags = SA_SIGINFO; |
| 389 | |
| 390 | sigaction(SIGFPE, &sa, 0); |
| 391 | sigaction(SIGILL, &sa, 0); |
| 392 | sigaction(SIGBUS, &sa, 0); |
| 393 | sigaction(SIGSEGV, &sa, 0); |
| 394 | } |
| 395 | |
| 396 | |
| 397 | #ifdef DEBUG |
| 398 | #include <getopt.h> |
| 399 | |
| 400 | void usage(void) |
| 401 | { |
| 402 | fprintf(stderr, "tst_sigcatcher: [-akfn]\n"); |
| 403 | exit(1); |
| 404 | } |
| 405 | |
| 406 | int main(int argc, char** argv) |
| 407 | { |
| 408 | struct sigaction sa; |
| 409 | char *p = 0; |
| 410 | int i, c; |
| 411 | volatile x=0; |
| 412 | |
| 413 | memset(&sa, 0, sizeof(struct sigaction)); |
| 414 | sa.sa_sigaction = die_signal_handler; |
| 415 | sa.sa_flags = SA_SIGINFO; |
| 416 | for (i=1; i < 31; i++) |
| 417 | sigaction(i, &sa, 0); |
| 418 | |
| 419 | while ((c = getopt (argc, argv, "afkn")) != EOF) |
| 420 | switch (c) { |
| 421 | case 'a': |
| 422 | abort(); |
| 423 | break; |
| 424 | case 'f': |
| 425 | printf("%d\n", 42/x); |
| 426 | case 'k': |
| 427 | kill(getpid(), SIGTERM); |
| 428 | break; |
| 429 | case 'n': |
| 430 | *p = 42; |
| 431 | default: |
| 432 | usage (); |
| 433 | } |
| 434 | |
| 435 | printf("Sleeping for 10 seconds, send kill signal to pid %u...\n", |
| 436 | getpid()); |
| 437 | fflush(stdout); |
| 438 | sleep(10); |
| 439 | exit(0); |
| 440 | } |
| 441 | #endif |