db_textdump.c (193066) | db_textdump.c (242424) |
---|---|
1/*- 2 * Copyright (c) 2007 Robert N. M. Watson 3 * All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions 7 * are met: 8 * 1. Redistributions of source code must retain the above copyright --- 43 unchanged lines hidden (view full) --- 52 * TODO 53 * ---- 54 * 55 * - Allow subsytems to register to submit files for inclusion in the text 56 * dump in a generic way. 57 */ 58 59#include <sys/cdefs.h> | 1/*- 2 * Copyright (c) 2007 Robert N. M. Watson 3 * All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions 7 * are met: 8 * 1. Redistributions of source code must retain the above copyright --- 43 unchanged lines hidden (view full) --- 52 * TODO 53 * ---- 54 * 55 * - Allow subsytems to register to submit files for inclusion in the text 56 * dump in a generic way. 57 */ 58 59#include <sys/cdefs.h> |
60__FBSDID("$FreeBSD: head/sys/ddb/db_textdump.c 193066 2009-05-29 21:27:12Z jamie $"); | 60__FBSDID("$FreeBSD: head/sys/ddb/db_textdump.c 242424 2012-11-01 04:07:08Z alfred $"); |
61 62#include "opt_config.h" 63 | 61 62#include "opt_config.h" 63 |
64#include "opt_ddb.h" 65 |
|
64#include <sys/param.h> 65#include <sys/conf.h> 66#include <sys/kernel.h> 67#include <sys/kerneldump.h> 68#include <sys/msgbuf.h> 69#include <sys/sysctl.h> 70#include <sys/systm.h> 71 --- 41 unchanged lines hidden (view full) --- 113 */ 114CTASSERT(sizeof(struct kerneldumpheader) == TEXTDUMP_BLOCKSIZE); 115CTASSERT(sizeof(struct ustar_header) == TEXTDUMP_BLOCKSIZE); 116 117/* 118 * Is a textdump scheduled? If so, the shutdown code will invoke our dumpsys 119 * routine instead of the machine-dependent kernel dump routine. 120 */ | 66#include <sys/param.h> 67#include <sys/conf.h> 68#include <sys/kernel.h> 69#include <sys/kerneldump.h> 70#include <sys/msgbuf.h> 71#include <sys/sysctl.h> 72#include <sys/systm.h> 73 --- 41 unchanged lines hidden (view full) --- 115 */ 116CTASSERT(sizeof(struct kerneldumpheader) == TEXTDUMP_BLOCKSIZE); 117CTASSERT(sizeof(struct ustar_header) == TEXTDUMP_BLOCKSIZE); 118 119/* 120 * Is a textdump scheduled? If so, the shutdown code will invoke our dumpsys 121 * routine instead of the machine-dependent kernel dump routine. 122 */ |
121int textdump_pending; | 123#ifdef TEXTDUMP_PREFERRED 124int textdump_pending = 1; 125#else 126int textdump_pending = 0; 127#endif |
122SYSCTL_INT(_debug_ddb_textdump, OID_AUTO, pending, CTLFLAG_RW, 123 &textdump_pending, 0, 124 "Perform textdump instead of regular kernel dump."); 125 126/* 127 * Various constants for tar headers and contents. 128 */ 129#define TAR_USER "root" --- 66 unchanged lines hidden (view full) --- 196 * Each file in the tarball has a block-sized header with its name and other, 197 * largely hard-coded, properties. 198 */ 199void 200textdump_mkustar(char *block_buffer, const char *filename, u_int size) 201{ 202 struct ustar_header *uhp; 203 | 128SYSCTL_INT(_debug_ddb_textdump, OID_AUTO, pending, CTLFLAG_RW, 129 &textdump_pending, 0, 130 "Perform textdump instead of regular kernel dump."); 131 132/* 133 * Various constants for tar headers and contents. 134 */ 135#define TAR_USER "root" --- 66 unchanged lines hidden (view full) --- 202 * Each file in the tarball has a block-sized header with its name and other, 203 * largely hard-coded, properties. 204 */ 205void 206textdump_mkustar(char *block_buffer, const char *filename, u_int size) 207{ 208 struct ustar_header *uhp; 209 |
210#ifdef TEXTDUMP_VERBOSE 211 if (textdump_error == 0) 212 printf("textdump: creating '%s'.\n", filename); 213#endif |
|
204 uhp = (struct ustar_header *)block_buffer; 205 bzero(uhp, sizeof(*uhp)); 206 strlcpy(uhp->uh_filename, filename, sizeof(uhp->uh_filename)); 207 strlcpy(uhp->uh_mode, TAR_MODE, sizeof(uhp->uh_mode)); 208 snprintf(uhp->uh_size, sizeof(uhp->uh_size), "%o", size); 209 strlcpy(uhp->uh_tar_owner, TAR_UID, sizeof(uhp->uh_tar_owner)); 210 strlcpy(uhp->uh_tar_group, TAR_GID, sizeof(uhp->uh_tar_group)); 211 strlcpy(uhp->uh_owner, TAR_USER, sizeof(uhp->uh_owner)); --- 20 unchanged lines hidden (view full) --- 232 if (textdump_error) 233 return (textdump_error); 234 if (offset + TEXTDUMP_BLOCKSIZE > di->mediasize) 235 return (EIO); 236 if (offset < SIZEOF_METADATA) 237 return (ENOSPC); 238 textdump_error = dump_write(di, buffer, 0, offset + di->mediaoffset, 239 TEXTDUMP_BLOCKSIZE); | 214 uhp = (struct ustar_header *)block_buffer; 215 bzero(uhp, sizeof(*uhp)); 216 strlcpy(uhp->uh_filename, filename, sizeof(uhp->uh_filename)); 217 strlcpy(uhp->uh_mode, TAR_MODE, sizeof(uhp->uh_mode)); 218 snprintf(uhp->uh_size, sizeof(uhp->uh_size), "%o", size); 219 strlcpy(uhp->uh_tar_owner, TAR_UID, sizeof(uhp->uh_tar_owner)); 220 strlcpy(uhp->uh_tar_group, TAR_GID, sizeof(uhp->uh_tar_group)); 221 strlcpy(uhp->uh_owner, TAR_USER, sizeof(uhp->uh_owner)); --- 20 unchanged lines hidden (view full) --- 242 if (textdump_error) 243 return (textdump_error); 244 if (offset + TEXTDUMP_BLOCKSIZE > di->mediasize) 245 return (EIO); 246 if (offset < SIZEOF_METADATA) 247 return (ENOSPC); 248 textdump_error = dump_write(di, buffer, 0, offset + di->mediaoffset, 249 TEXTDUMP_BLOCKSIZE); |
250 if (textdump_error) 251 printf("textdump_writeblock: offset %jd, error %d\n", (intmax_t)offset, 252 textdump_error); |
|
240 return (textdump_error); 241} 242 243/* 244 * Interfaces to save and restore the dump offset, so that printers can go 245 * back to rewrite a header if required, while avoiding their knowing about 246 * the global layout of the blocks. 247 * --- 177 unchanged lines hidden (view full) --- 425 426 /* 427 * We don't know a priori how large the dump will be, but we do know 428 * that we need to reserve space for metadata and that we need two 429 * dump headers. Also leave room for one ustar header and one block 430 * of data. 431 */ 432 if (di->mediasize < SIZEOF_METADATA + 2 * sizeof(kdh)) { | 253 return (textdump_error); 254} 255 256/* 257 * Interfaces to save and restore the dump offset, so that printers can go 258 * back to rewrite a header if required, while avoiding their knowing about 259 * the global layout of the blocks. 260 * --- 177 unchanged lines hidden (view full) --- 438 439 /* 440 * We don't know a priori how large the dump will be, but we do know 441 * that we need to reserve space for metadata and that we need two 442 * dump headers. Also leave room for one ustar header and one block 443 * of data. 444 */ 445 if (di->mediasize < SIZEOF_METADATA + 2 * sizeof(kdh)) { |
433 printf("Insufficient space on dump partition.\n"); | 446 printf("Insufficient space on dump partition for minimal textdump.\n"); |
434 return; 435 } 436 textdump_error = 0; 437 438 /* 439 * Position the start of the dump so that we'll write the kernel dump 440 * trailer immediately before the end of the partition, and then work 441 * our way back. We will rewrite this header later to reflect the --- 33 unchanged lines hidden (view full) --- 475 (void)textdump_writenextblock(di, (char *)&kdh); 476 477 /* 478 * Terminate the dump, report any errors, and clear the pending flag. 479 */ 480 if (textdump_error == 0) 481 (void)dump_write(di, NULL, 0, 0, 0); 482 if (textdump_error == ENOSPC) | 447 return; 448 } 449 textdump_error = 0; 450 451 /* 452 * Position the start of the dump so that we'll write the kernel dump 453 * trailer immediately before the end of the partition, and then work 454 * our way back. We will rewrite this header later to reflect the --- 33 unchanged lines hidden (view full) --- 488 (void)textdump_writenextblock(di, (char *)&kdh); 489 490 /* 491 * Terminate the dump, report any errors, and clear the pending flag. 492 */ 493 if (textdump_error == 0) 494 (void)dump_write(di, NULL, 0, 0, 0); 495 if (textdump_error == ENOSPC) |
483 printf("Insufficient space on dump partition\n"); | 496 printf("Textdump: Insufficient space on dump partition\n"); |
484 else if (textdump_error != 0) | 497 else if (textdump_error != 0) |
485 printf("Error %d writing dump\n", textdump_error); | 498 printf("Textdump: Error %d writing dump\n", textdump_error); |
486 else 487 printf("Textdump complete.\n"); 488 textdump_pending = 0; 489} 490 491/*- 492 * DDB(4) command to manage textdumps: 493 * 494 * textdump set - request a textdump 495 * textdump status - print DDB output textdump status 496 * textdump unset - clear textdump request 497 */ 498static void 499db_textdump_usage(void) 500{ 501 | 499 else 500 printf("Textdump complete.\n"); 501 textdump_pending = 0; 502} 503 504/*- 505 * DDB(4) command to manage textdumps: 506 * 507 * textdump set - request a textdump 508 * textdump status - print DDB output textdump status 509 * textdump unset - clear textdump request 510 */ 511static void 512db_textdump_usage(void) 513{ 514 |
502 db_printf("textdump [unset|set|status]\n"); | 515 db_printf("textdump [unset|set|status|dump]\n"); |
503} 504 505void 506db_textdump_cmd(db_expr_t addr, boolean_t have_addr, db_expr_t count, 507 char *modif) 508{ 509 int t; 510 --- 12 unchanged lines hidden (view full) --- 523 } else if (strcmp(db_tok_string, "status") == 0) { 524 if (textdump_pending) 525 db_printf("textdump is set\n"); 526 else 527 db_printf("textdump is not set\n"); 528 } else if (strcmp(db_tok_string, "unset") == 0) { 529 textdump_pending = 0; 530 db_printf("textdump unset\n"); | 516} 517 518void 519db_textdump_cmd(db_expr_t addr, boolean_t have_addr, db_expr_t count, 520 char *modif) 521{ 522 int t; 523 --- 12 unchanged lines hidden (view full) --- 536 } else if (strcmp(db_tok_string, "status") == 0) { 537 if (textdump_pending) 538 db_printf("textdump is set\n"); 539 else 540 db_printf("textdump is not set\n"); 541 } else if (strcmp(db_tok_string, "unset") == 0) { 542 textdump_pending = 0; 543 db_printf("textdump unset\n"); |
531 } else | 544 } else if (strcmp(db_tok_string, "dump") == 0) { 545 textdump_pending = 1; 546 doadump(TRUE); 547 } else { |
532 db_textdump_usage(); | 548 db_textdump_usage(); |
549 } |
|
533} | 550} |