1 /* 2 * Copyright (C) 2012 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 #include <stddef.h> 18 #include <stdbool.h> 19 #include <stdlib.h> 20 #include <signal.h> 21 #include <string.h> 22 #include <stdio.h> 23 #include <fcntl.h> 24 #include <errno.h> 25 #include <dirent.h> 26 #include <time.h> 27 #include <sys/ptrace.h> 28 #include <sys/stat.h> 29 30 #include <private/android_filesystem_config.h> 31 32 #include <log/logger.h> 33 #include <cutils/properties.h> 34 35 #include <corkscrew/demangle.h> 36 #include <corkscrew/backtrace.h> 37 38 #include <sys/socket.h> 39 #include <linux/un.h> 40 41 #include <selinux/android.h> 42 43 #include "machine.h" 44 #include "tombstone.h" 45 #include "utility.h" 46 47 #define STACK_DEPTH 32 48 #define STACK_WORDS 16 49 50 #define MAX_TOMBSTONES 10 51 #define TOMBSTONE_DIR "/data/tombstones" 52 53 /* Must match the path defined in NativeCrashListener.java */ 54 #define NCRASH_SOCKET_PATH "/data/system/ndebugsocket" 55 56 #define typecheck(x,y) { \ 57 typeof(x) __dummy1; \ 58 typeof(y) __dummy2; \ 59 (void)(&__dummy1 == &__dummy2); } 60 61 62 static bool signal_has_address(int sig) { 63 switch (sig) { 64 case SIGILL: 65 case SIGFPE: 66 case SIGSEGV: 67 case SIGBUS: 68 return true; 69 default: 70 return false; 71 } 72 } 73 74 static const char *get_signame(int sig) 75 { 76 switch(sig) { 77 case SIGILL: return "SIGILL"; 78 case SIGABRT: return "SIGABRT"; 79 case SIGBUS: return "SIGBUS"; 80 case SIGFPE: return "SIGFPE"; 81 case SIGSEGV: return "SIGSEGV"; 82 case SIGPIPE: return "SIGPIPE"; 83 #ifdef SIGSTKFLT 84 case SIGSTKFLT: return "SIGSTKFLT"; 85 #endif 86 case SIGSTOP: return "SIGSTOP"; 87 default: return "?"; 88 } 89 } 90 91 static const char *get_sigcode(int signo, int code) 92 { 93 // Try the signal-specific codes... 94 switch (signo) { 95 case SIGILL: 96 switch (code) { 97 case ILL_ILLOPC: return "ILL_ILLOPC"; 98 case ILL_ILLOPN: return "ILL_ILLOPN"; 99 case ILL_ILLADR: return "ILL_ILLADR"; 100 case ILL_ILLTRP: return "ILL_ILLTRP"; 101 case ILL_PRVOPC: return "ILL_PRVOPC"; 102 case ILL_PRVREG: return "ILL_PRVREG"; 103 case ILL_COPROC: return "ILL_COPROC"; 104 case ILL_BADSTK: return "ILL_BADSTK"; 105 } 106 break; 107 case SIGBUS: 108 switch (code) { 109 case BUS_ADRALN: return "BUS_ADRALN"; 110 case BUS_ADRERR: return "BUS_ADRERR"; 111 case BUS_OBJERR: return "BUS_OBJERR"; 112 } 113 break; 114 case SIGFPE: 115 switch (code) { 116 case FPE_INTDIV: return "FPE_INTDIV"; 117 case FPE_INTOVF: return "FPE_INTOVF"; 118 case FPE_FLTDIV: return "FPE_FLTDIV"; 119 case FPE_FLTOVF: return "FPE_FLTOVF"; 120 case FPE_FLTUND: return "FPE_FLTUND"; 121 case FPE_FLTRES: return "FPE_FLTRES"; 122 case FPE_FLTINV: return "FPE_FLTINV"; 123 case FPE_FLTSUB: return "FPE_FLTSUB"; 124 } 125 break; 126 case SIGSEGV: 127 switch (code) { 128 case SEGV_MAPERR: return "SEGV_MAPERR"; 129 case SEGV_ACCERR: return "SEGV_ACCERR"; 130 } 131 break; 132 case SIGTRAP: 133 switch (code) { 134 case TRAP_BRKPT: return "TRAP_BRKPT"; 135 case TRAP_TRACE: return "TRAP_TRACE"; 136 } 137 break; 138 } 139 // Then the other codes... 140 switch (code) { 141 case SI_USER: return "SI_USER"; 142 #if defined(SI_KERNEL) 143 case SI_KERNEL: return "SI_KERNEL"; 144 #endif 145 case SI_QUEUE: return "SI_QUEUE"; 146 case SI_TIMER: return "SI_TIMER"; 147 case SI_MESGQ: return "SI_MESGQ"; 148 case SI_ASYNCIO: return "SI_ASYNCIO"; 149 #if defined(SI_SIGIO) 150 case SI_SIGIO: return "SI_SIGIO"; 151 #endif 152 #if defined(SI_TKILL) 153 case SI_TKILL: return "SI_TKILL"; 154 #endif 155 } 156 // Then give up... 157 return "?"; 158 } 159 160 static void dump_revision_info(log_t* log) 161 { 162 char revision[PROPERTY_VALUE_MAX]; 163 164 property_get("ro.revision", revision, "unknown"); 165 166 _LOG(log, SCOPE_AT_FAULT, "Revision: '%s'\n", revision); 167 } 168 169 static void dump_build_info(log_t* log) 170 { 171 char fingerprint[PROPERTY_VALUE_MAX]; 172 173 property_get("ro.build.fingerprint", fingerprint, "unknown"); 174 175 _LOG(log, SCOPE_AT_FAULT, "Build fingerprint: '%s'\n", fingerprint); 176 } 177 178 static void dump_fault_addr(log_t* log, pid_t tid, int sig) 179 { 180 siginfo_t si; 181 182 memset(&si, 0, sizeof(si)); 183 if(ptrace(PTRACE_GETSIGINFO, tid, 0, &si)){ 184 _LOG(log, SCOPE_AT_FAULT, "cannot get siginfo: %s\n", strerror(errno)); 185 } else if (signal_has_address(sig)) { 186 _LOG(log, SCOPE_AT_FAULT, "signal %d (%s), code %d (%s), fault addr %08x\n", 187 sig, get_signame(sig), 188 si.si_code, get_sigcode(sig, si.si_code), 189 (uintptr_t) si.si_addr); 190 } else { 191 _LOG(log, SCOPE_AT_FAULT, "signal %d (%s), code %d (%s), fault addr --------\n", 192 sig, get_signame(sig), si.si_code, get_sigcode(sig, si.si_code)); 193 } 194 } 195 196 static void dump_thread_info(log_t* log, pid_t pid, pid_t tid, bool at_fault) { 197 char path[64]; 198 char threadnamebuf[1024]; 199 char* threadname = NULL; 200 FILE *fp; 201 202 snprintf(path, sizeof(path), "/proc/%d/comm", tid); 203 if ((fp = fopen(path, "r"))) { 204 threadname = fgets(threadnamebuf, sizeof(threadnamebuf), fp); 205 fclose(fp); 206 if (threadname) { 207 size_t len = strlen(threadname); 208 if (len && threadname[len - 1] == '\n') { 209 threadname[len - 1] = '\0'; 210 } 211 } 212 } 213 214 if (at_fault) { 215 char procnamebuf[1024]; 216 char* procname = NULL; 217 218 snprintf(path, sizeof(path), "/proc/%d/cmdline", pid); 219 if ((fp = fopen(path, "r"))) { 220 procname = fgets(procnamebuf, sizeof(procnamebuf), fp); 221 fclose(fp); 222 } 223 224 _LOG(log, SCOPE_AT_FAULT, "pid: %d, tid: %d, name: %s >>> %s <<<\n", pid, tid, 225 threadname ? threadname : "UNKNOWN", 226 procname ? procname : "UNKNOWN"); 227 } else { 228 _LOG(log, 0, "pid: %d, tid: %d, name: %s\n", 229 pid, tid, threadname ? threadname : "UNKNOWN"); 230 } 231 } 232 233 static void dump_backtrace(const ptrace_context_t* context __attribute((unused)), 234 log_t* log, pid_t tid __attribute((unused)), bool at_fault, 235 const backtrace_frame_t* backtrace, size_t frames) { 236 int scopeFlags = at_fault ? SCOPE_AT_FAULT : 0; 237 _LOG(log, scopeFlags, "\nbacktrace:\n"); 238 239 backtrace_symbol_t backtrace_symbols[STACK_DEPTH]; 240 get_backtrace_symbols_ptrace(context, backtrace, frames, backtrace_symbols); 241 for (size_t i = 0; i < frames; i++) { 242 char line[MAX_BACKTRACE_LINE_LENGTH]; 243 format_backtrace_line(i, &backtrace[i], &backtrace_symbols[i], 244 line, MAX_BACKTRACE_LINE_LENGTH); 245 _LOG(log, scopeFlags, " %s\n", line); 246 } 247 free_backtrace_symbols(backtrace_symbols, frames); 248 } 249 250 static void dump_stack_segment(const ptrace_context_t* context, log_t* log, pid_t tid, 251 int scopeFlags, uintptr_t* sp, size_t words, int label) { 252 for (size_t i = 0; i < words; i++) { 253 uint32_t stack_content; 254 if (!try_get_word_ptrace(tid, *sp, &stack_content)) { 255 break; 256 } 257 258 const map_info_t* mi; 259 const symbol_t* symbol; 260 find_symbol_ptrace(context, stack_content, &mi, &symbol); 261 262 if (symbol) { 263 char* demangled_name = demangle_symbol_name(symbol->name); 264 const char* symbol_name = demangled_name ? demangled_name : symbol->name; 265 uint32_t offset = stack_content - (mi->start + symbol->start); 266 if (!i && label >= 0) { 267 if (offset) { 268 _LOG(log, scopeFlags, " #%02d %08x %08x %s (%s+%u)\n", 269 label, *sp, stack_content, mi ? mi->name : "", symbol_name, offset); 270 } else { 271 _LOG(log, scopeFlags, " #%02d %08x %08x %s (%s)\n", 272 label, *sp, stack_content, mi ? mi->name : "", symbol_name); 273 } 274 } else { 275 if (offset) { 276 _LOG(log, scopeFlags, " %08x %08x %s (%s+%u)\n", 277 *sp, stack_content, mi ? mi->name : "", symbol_name, offset); 278 } else { 279 _LOG(log, scopeFlags, " %08x %08x %s (%s)\n", 280 *sp, stack_content, mi ? mi->name : "", symbol_name); 281 } 282 } 283 free(demangled_name); 284 } else { 285 if (!i && label >= 0) { 286 _LOG(log, scopeFlags, " #%02d %08x %08x %s\n", 287 label, *sp, stack_content, mi ? mi->name : ""); 288 } else { 289 _LOG(log, scopeFlags, " %08x %08x %s\n", 290 *sp, stack_content, mi ? mi->name : ""); 291 } 292 } 293 294 *sp += sizeof(uint32_t); 295 } 296 } 297 298 static void dump_stack(const ptrace_context_t* context, log_t* log, pid_t tid, bool at_fault, 299 const backtrace_frame_t* backtrace, size_t frames) { 300 bool have_first = false; 301 size_t first, last; 302 for (size_t i = 0; i < frames; i++) { 303 if (backtrace[i].stack_top) { 304 if (!have_first) { 305 have_first = true; 306 first = i; 307 } 308 last = i; 309 } 310 } 311 if (!have_first) { 312 return; 313 } 314 315 int scopeFlags = SCOPE_SENSITIVE | (at_fault ? SCOPE_AT_FAULT : 0); 316 _LOG(log, scopeFlags, "\nstack:\n"); 317 318 // Dump a few words before the first frame. 319 uintptr_t sp = backtrace[first].stack_top - STACK_WORDS * sizeof(uint32_t); 320 dump_stack_segment(context, log, tid, scopeFlags, &sp, STACK_WORDS, -1); 321 322 // Dump a few words from all successive frames. 323 // Only log the first 3 frames, put the rest in the tombstone. 324 for (size_t i = first; i <= last; i++) { 325 const backtrace_frame_t* frame = &backtrace[i]; 326 if (sp != frame->stack_top) { 327 _LOG(log, scopeFlags, " ........ ........\n"); 328 sp = frame->stack_top; 329 } 330 if (i - first == 3) { 331 scopeFlags &= (~SCOPE_AT_FAULT); 332 } 333 if (i == last) { 334 dump_stack_segment(context, log, tid, scopeFlags, &sp, STACK_WORDS, i); 335 if (sp < frame->stack_top + frame->stack_size) { 336 _LOG(log, scopeFlags, " ........ ........\n"); 337 } 338 } else { 339 size_t words = frame->stack_size / sizeof(uint32_t); 340 if (words == 0) { 341 words = 1; 342 } else if (words > STACK_WORDS) { 343 words = STACK_WORDS; 344 } 345 dump_stack_segment(context, log, tid, scopeFlags, &sp, words, i); 346 } 347 } 348 } 349 350 static void dump_backtrace_and_stack(const ptrace_context_t* context, log_t* log, pid_t tid, 351 bool at_fault) { 352 backtrace_frame_t backtrace[STACK_DEPTH]; 353 ssize_t frames = unwind_backtrace_ptrace(tid, context, backtrace, 0, STACK_DEPTH); 354 if (frames > 0) { 355 dump_backtrace(context, log, tid, at_fault, backtrace, frames); 356 dump_stack(context, log, tid, at_fault, backtrace, frames); 357 } 358 } 359 360 static void dump_map(log_t* log, map_info_t* m, const char* what, int scopeFlags) { 361 if (m != NULL) { 362 _LOG(log, scopeFlags, " %08x-%08x %c%c%c %s\n", m->start, m->end, 363 m->is_readable ? 'r' : '-', 364 m->is_writable ? 'w' : '-', 365 m->is_executable ? 'x' : '-', 366 m->name); 367 } else { 368 _LOG(log, scopeFlags, " (no %s)\n", what); 369 } 370 } 371 372 static void dump_nearby_maps(const ptrace_context_t* context, log_t* log, pid_t tid, bool at_fault) { 373 int scopeFlags = SCOPE_SENSITIVE | (at_fault ? SCOPE_AT_FAULT : 0); 374 siginfo_t si; 375 memset(&si, 0, sizeof(si)); 376 if (ptrace(PTRACE_GETSIGINFO, tid, 0, &si)) { 377 _LOG(log, scopeFlags, "cannot get siginfo for %d: %s\n", 378 tid, strerror(errno)); 379 return; 380 } 381 if (!signal_has_address(si.si_signo)) { 382 return; 383 } 384 385 uintptr_t addr = (uintptr_t) si.si_addr; 386 addr &= ~0xfff; /* round to 4K page boundary */ 387 if (addr == 0) { /* null-pointer deref */ 388 return; 389 } 390 391 _LOG(log, scopeFlags, "\nmemory map around fault addr %08x:\n", (int)si.si_addr); 392 393 /* 394 * Search for a match, or for a hole where the match would be. The list 395 * is backward from the file content, so it starts at high addresses. 396 */ 397 map_info_t* map = context->map_info_list; 398 map_info_t *next = NULL; 399 map_info_t *prev = NULL; 400 while (map != NULL) { 401 if (addr >= map->start && addr < map->end) { 402 next = map->next; 403 break; 404 } else if (addr >= map->end) { 405 /* map would be between "prev" and this entry */ 406 next = map; 407 map = NULL; 408 break; 409 } 410 411 prev = map; 412 map = map->next; 413 } 414 415 /* 416 * Show "next" then "match" then "prev" so that the addresses appear in 417 * ascending order (like /proc/pid/maps). 418 */ 419 dump_map(log, next, "map below", scopeFlags); 420 dump_map(log, map, "map for address", scopeFlags); 421 dump_map(log, prev, "map above", scopeFlags); 422 } 423 424 static void dump_thread(const ptrace_context_t* context, log_t* log, pid_t tid, bool at_fault, 425 int* total_sleep_time_usec) { 426 wait_for_stop(tid, total_sleep_time_usec); 427 428 dump_registers(context, log, tid, at_fault); 429 dump_backtrace_and_stack(context, log, tid, at_fault); 430 if (at_fault) { 431 dump_memory_and_code(context, log, tid, at_fault); 432 dump_nearby_maps(context, log, tid, at_fault); 433 } 434 } 435 436 /* Return true if some thread is not detached cleanly */ 437 static bool dump_sibling_thread_report(const ptrace_context_t* context, 438 log_t* log, pid_t pid, pid_t tid, int* total_sleep_time_usec) { 439 char task_path[64]; 440 snprintf(task_path, sizeof(task_path), "/proc/%d/task", pid); 441 442 DIR* d = opendir(task_path); 443 /* Bail early if cannot open the task directory */ 444 if (d == NULL) { 445 XLOG("Cannot open /proc/%d/task\n", pid); 446 return false; 447 } 448 449 bool detach_failed = false; 450 struct dirent* de; 451 while ((de = readdir(d)) != NULL) { 452 /* Ignore "." and ".." */ 453 if (!strcmp(de->d_name, ".") || !strcmp(de->d_name, "..")) { 454 continue; 455 } 456 457 /* The main thread at fault has been handled individually */ 458 char* end; 459 pid_t new_tid = strtoul(de->d_name, &end, 10); 460 if (*end || new_tid == tid) { 461 continue; 462 } 463 464 /* Skip this thread if cannot ptrace it */ 465 if (ptrace(PTRACE_ATTACH, new_tid, 0, 0) < 0) { 466 continue; 467 } 468 469 _LOG(log, 0, "--- --- --- --- --- --- --- --- --- --- --- --- --- --- --- ---\n"); 470 dump_thread_info(log, pid, new_tid, false); 471 dump_thread(context, log, new_tid, false, total_sleep_time_usec); 472 473 if (ptrace(PTRACE_DETACH, new_tid, 0, 0) != 0) { 474 LOG("ptrace detach from %d failed: %s\n", new_tid, strerror(errno)); 475 detach_failed = true; 476 } 477 } 478 479 closedir(d); 480 return detach_failed; 481 } 482 483 /* 484 * Reads the contents of the specified log device, filters out the entries 485 * that don't match the specified pid, and writes them to the tombstone file. 486 * 487 * If "tailOnly" is set, we only print the last few lines. 488 */ 489 static void dump_log_file(log_t* log, pid_t pid, const char* filename, 490 bool tailOnly) 491 { 492 bool first = true; 493 494 /* circular buffer, for "tailOnly" mode */ 495 const int kShortLogMaxLines = 5; 496 const int kShortLogLineLen = 256; 497 char shortLog[kShortLogMaxLines][kShortLogLineLen]; 498 int shortLogCount = 0; 499 int shortLogNext = 0; 500 501 int logfd = open(filename, O_RDONLY | O_NONBLOCK); 502 if (logfd < 0) { 503 XLOG("Unable to open %s: %s\n", filename, strerror(errno)); 504 return; 505 } 506 507 union { 508 unsigned char buf[LOGGER_ENTRY_MAX_LEN + 1]; 509 struct logger_entry entry; 510 } log_entry; 511 512 while (true) { 513 ssize_t actual = read(logfd, log_entry.buf, LOGGER_ENTRY_MAX_LEN); 514 if (actual < 0) { 515 if (errno == EINTR) { 516 /* interrupted by signal, retry */ 517 continue; 518 } else if (errno == EAGAIN) { 519 /* non-blocking EOF; we're done */ 520 break; 521 } else { 522 _LOG(log, 0, "Error while reading log: %s\n", 523 strerror(errno)); 524 break; 525 } 526 } else if (actual == 0) { 527 _LOG(log, 0, "Got zero bytes while reading log: %s\n", 528 strerror(errno)); 529 break; 530 } 531 532 /* 533 * NOTE: if you XLOG something here, this will spin forever, 534 * because you will be writing as fast as you're reading. Any 535 * high-frequency debug diagnostics should just be written to 536 * the tombstone file. 537 */ 538 539 struct logger_entry* entry = &log_entry.entry; 540 541 if (entry->pid != (int32_t) pid) { 542 /* wrong pid, ignore */ 543 continue; 544 } 545 546 if (first) { 547 _LOG(log, 0, "--------- %slog %s\n", 548 tailOnly ? "tail end of " : "", filename); 549 first = false; 550 } 551 552 /* 553 * Msg format is: <priority:1><tag:N>\0<message:N>\0 554 * 555 * We want to display it in the same format as "logcat -v threadtime" 556 * (although in this case the pid is redundant). 557 * 558 * TODO: scan for line breaks ('\n') and display each text line 559 * on a separate line, prefixed with the header, like logcat does. 560 */ 561 static const char* kPrioChars = "!.VDIWEFS"; 562 unsigned char prio = entry->msg[0]; 563 char* tag = entry->msg + 1; 564 char* msg = tag + strlen(tag) + 1; 565 566 /* consume any trailing newlines */ 567 char* eatnl = msg + strlen(msg) - 1; 568 while (eatnl >= msg && *eatnl == '\n') { 569 *eatnl-- = '\0'; 570 } 571 572 char prioChar = (prio < strlen(kPrioChars) ? kPrioChars[prio] : '?'); 573 574 char timeBuf[32]; 575 time_t sec = (time_t) entry->sec; 576 struct tm tmBuf; 577 struct tm* ptm; 578 ptm = localtime_r(&sec, &tmBuf); 579 strftime(timeBuf, sizeof(timeBuf), "%m-%d %H:%M:%S", ptm); 580 581 if (tailOnly) { 582 snprintf(shortLog[shortLogNext], kShortLogLineLen, 583 "%s.%03d %5d %5d %c %-8s: %s", 584 timeBuf, entry->nsec / 1000000, entry->pid, entry->tid, 585 prioChar, tag, msg); 586 shortLogNext = (shortLogNext + 1) % kShortLogMaxLines; 587 shortLogCount++; 588 } else { 589 _LOG(log, 0, "%s.%03d %5d %5d %c %-8s: %s\n", 590 timeBuf, entry->nsec / 1000000, entry->pid, entry->tid, 591 prioChar, tag, msg); 592 } 593 } 594 595 if (tailOnly) { 596 int i; 597 598 /* 599 * If we filled the buffer, we want to start at "next", which has 600 * the oldest entry. If we didn't, we want to start at zero. 601 */ 602 if (shortLogCount < kShortLogMaxLines) { 603 shortLogNext = 0; 604 } else { 605 shortLogCount = kShortLogMaxLines; /* cap at window size */ 606 } 607 608 for (i = 0; i < shortLogCount; i++) { 609 _LOG(log, 0, "%s\n", shortLog[shortLogNext]); 610 shortLogNext = (shortLogNext + 1) % kShortLogMaxLines; 611 } 612 } 613 614 close(logfd); 615 } 616 617 /* 618 * Dumps the logs generated by the specified pid to the tombstone, from both 619 * "system" and "main" log devices. Ideally we'd interleave the output. 620 */ 621 static void dump_logs(log_t* log, pid_t pid, bool tailOnly) 622 { 623 dump_log_file(log, pid, "/dev/log/system", tailOnly); 624 dump_log_file(log, pid, "/dev/log/main", tailOnly); 625 } 626 627 static void dump_abort_message(log_t* log, pid_t tid, uintptr_t address) { 628 if (address == 0) { 629 return; 630 } 631 632 address += sizeof(size_t); // Skip the buffer length. 633 634 char msg[512]; 635 memset(msg, 0, sizeof(msg)); 636 char* p = &msg[0]; 637 while (p < &msg[sizeof(msg)]) { 638 uint32_t data; 639 if (!try_get_word_ptrace(tid, address, &data)) { 640 break; 641 } 642 address += sizeof(uint32_t); 643 644 if ((*p++ = (data >> 0) & 0xff) == 0) { 645 break; 646 } 647 if ((*p++ = (data >> 8) & 0xff) == 0) { 648 break; 649 } 650 if ((*p++ = (data >> 16) & 0xff) == 0) { 651 break; 652 } 653 if ((*p++ = (data >> 24) & 0xff) == 0) { 654 break; 655 } 656 } 657 msg[sizeof(msg) - 1] = '\0'; 658 659 _LOG(log, SCOPE_AT_FAULT, "Abort message: '%s'\n", msg); 660 } 661 662 /* 663 * Dumps all information about the specified pid to the tombstone. 664 */ 665 static bool dump_crash(log_t* log, pid_t pid, pid_t tid, int signal, uintptr_t abort_msg_address, 666 bool dump_sibling_threads, int* total_sleep_time_usec) 667 { 668 /* don't copy log messages to tombstone unless this is a dev device */ 669 char value[PROPERTY_VALUE_MAX]; 670 property_get("ro.debuggable", value, "0"); 671 bool want_logs = (value[0] == '1'); 672 673 if (log->amfd >= 0) { 674 /* 675 * Activity Manager protocol: binary 32-bit network-byte-order ints for the 676 * pid and signal number, followed by the raw text of the dump, culminating 677 * in a zero byte that marks end-of-data. 678 */ 679 uint32_t datum = htonl(pid); 680 TEMP_FAILURE_RETRY( write(log->amfd, &datum, 4) ); 681 datum = htonl(signal); 682 TEMP_FAILURE_RETRY( write(log->amfd, &datum, 4) ); 683 } 684 685 _LOG(log, SCOPE_AT_FAULT, 686 "*** *** *** *** *** *** *** *** *** *** *** *** *** *** *** ***\n"); 687 dump_build_info(log); 688 dump_revision_info(log); 689 dump_thread_info(log, pid, tid, true); 690 if (signal) { 691 dump_fault_addr(log, tid, signal); 692 } 693 dump_abort_message(log, tid, abort_msg_address); 694 695 ptrace_context_t* context = load_ptrace_context(tid); 696 dump_thread(context, log, tid, true, total_sleep_time_usec); 697 698 if (want_logs) { 699 dump_logs(log, pid, true); 700 } 701 702 bool detach_failed = false; 703 if (dump_sibling_threads) { 704 detach_failed = dump_sibling_thread_report(context, log, pid, tid, total_sleep_time_usec); 705 } 706 707 free_ptrace_context(context); 708 709 if (want_logs) { 710 dump_logs(log, pid, false); 711 } 712 713 /* send EOD to the Activity Manager, then wait for its ack to avoid racing ahead 714 * and killing the target out from under it */ 715 if (log->amfd >= 0) { 716 uint8_t eodMarker = 0; 717 TEMP_FAILURE_RETRY( write(log->amfd, &eodMarker, 1) ); 718 /* 3 sec timeout reading the ack; we're fine if that happens */ 719 TEMP_FAILURE_RETRY( read(log->amfd, &eodMarker, 1) ); 720 } 721 722 return detach_failed; 723 } 724 725 /* 726 * find_and_open_tombstone - find an available tombstone slot, if any, of the 727 * form tombstone_XX where XX is 00 to MAX_TOMBSTONES-1, inclusive. If no 728 * file is available, we reuse the least-recently-modified file. 729 * 730 * Returns the path of the tombstone file, allocated using malloc(). Caller must free() it. 731 */ 732 static char* find_and_open_tombstone(int* fd) 733 { 734 unsigned long mtime = ULONG_MAX; 735 struct stat sb; 736 737 /* 738 * XXX: Our stat.st_mtime isn't time_t. If it changes, as it probably ought 739 * to, our logic breaks. This check will generate a warning if that happens. 740 */ 741 typecheck(mtime, sb.st_mtime); 742 743 /* 744 * In a single wolf-like pass, find an available slot and, in case none 745 * exist, find and record the least-recently-modified file. 746 */ 747 char path[128]; 748 int oldest = 0; 749 for (int i = 0; i < MAX_TOMBSTONES; i++) { 750 snprintf(path, sizeof(path), TOMBSTONE_DIR"/tombstone_%02d", i); 751 752 if (!stat(path, &sb)) { 753 if (sb.st_mtime < mtime) { 754 oldest = i; 755 mtime = sb.st_mtime; 756 } 757 continue; 758 } 759 if (errno != ENOENT) 760 continue; 761 762 *fd = open(path, O_CREAT | O_EXCL | O_WRONLY, 0600); 763 if (*fd < 0) 764 continue; /* raced ? */ 765 766 fchown(*fd, AID_SYSTEM, AID_SYSTEM); 767 return strdup(path); 768 } 769 770 /* we didn't find an available file, so we clobber the oldest one */ 771 snprintf(path, sizeof(path), TOMBSTONE_DIR"/tombstone_%02d", oldest); 772 *fd = open(path, O_CREAT | O_TRUNC | O_WRONLY, 0600); 773 if (*fd < 0) { 774 LOG("failed to open tombstone file '%s': %s\n", path, strerror(errno)); 775 return NULL; 776 } 777 fchown(*fd, AID_SYSTEM, AID_SYSTEM); 778 return strdup(path); 779 } 780 781 static int activity_manager_connect() { 782 int amfd = socket(PF_UNIX, SOCK_STREAM, 0); 783 if (amfd >= 0) { 784 struct sockaddr_un address; 785 int err; 786 787 memset(&address, 0, sizeof(address)); 788 address.sun_family = AF_UNIX; 789 strncpy(address.sun_path, NCRASH_SOCKET_PATH, sizeof(address.sun_path)); 790 err = TEMP_FAILURE_RETRY( connect(amfd, (struct sockaddr*) &address, sizeof(address)) ); 791 if (!err) { 792 struct timeval tv; 793 memset(&tv, 0, sizeof(tv)); 794 tv.tv_sec = 1; // tight leash 795 err = setsockopt(amfd, SOL_SOCKET, SO_SNDTIMEO, &tv, sizeof(tv)); 796 if (!err) { 797 tv.tv_sec = 3; // 3 seconds on handshake read 798 err = setsockopt(amfd, SOL_SOCKET, SO_RCVTIMEO, &tv, sizeof(tv)); 799 } 800 } 801 if (err) { 802 close(amfd); 803 amfd = -1; 804 } 805 } 806 807 return amfd; 808 } 809 810 char* engrave_tombstone(pid_t pid, pid_t tid, int signal, uintptr_t abort_msg_address, 811 bool dump_sibling_threads, bool quiet, bool* detach_failed, 812 int* total_sleep_time_usec) { 813 mkdir(TOMBSTONE_DIR, 0755); 814 chown(TOMBSTONE_DIR, AID_SYSTEM, AID_SYSTEM); 815 816 if (selinux_android_restorecon(TOMBSTONE_DIR) == -1) { 817 *detach_failed = false; 818 return NULL; 819 } 820 821 int fd; 822 char* path = find_and_open_tombstone(&fd); 823 if (!path) { 824 *detach_failed = false; 825 return NULL; 826 } 827 828 log_t log; 829 log.tfd = fd; 830 log.amfd = activity_manager_connect(); 831 log.quiet = quiet; 832 *detach_failed = dump_crash(&log, pid, tid, signal, abort_msg_address, dump_sibling_threads, 833 total_sleep_time_usec); 834 835 close(log.amfd); 836 close(fd); 837 return path; 838 } 839