修改代码如下,然后用命令x /1b 1000 用于dump从内存1000开始的1个字节
#define DUMP_FILE_NAME "d:\\dump.bin" void bx_dbg_examine_command(char *command, char *format, bx_bool format_passed, bx_address addr, bx_bool addr_passed) { unsigned repeat_count, i; char ch, display_format, unit_size; bx_bool iteration, memory_dump = false; unsigned data_size; Bit8u data8; Bit16u data16; Bit32u data32; unsigned columns, per_line, offset; bx_bool is_linear; unsigned char databuf[8]; dbg_printf("[bochs]:\\n"); ::remove(DUMP_FILE_NAME); // If command was the extended "xp" command, meaning eXamine Physical memory, // then flag memory address as physical, rather than linear. if (strcmp(command, "xp") == 0) { is_linear = 0; } else { is_linear = 1; } if (addr_passed==0) addr = bx_debugger.default_addr; if (format_passed==0) { display_format = bx_debugger.default_display_format; unit_size = bx_debugger.default_unit_size; repeat_count = 1; } else { if (format==NULL) { dbg_printf("dbg_examine: format NULL\\n"); bx_dbg_exit(1); } if (strlen(format) < 2) { dbg_printf("dbg_examine: invalid format passed.\\n"); bx_dbg_exit(1); } if (format[0] != '/') { dbg_printf("dbg_examine: '/' is not first char of format.\\n"); bx_dbg_exit(1); } format++; repeat_count = 0; ch = *format; iteration = 0; while ((ch>='0') && (ch<='9')) { iteration = 1; repeat_count = 10*repeat_count + (ch-'0'); format++; ch = *format; } if (iteration==0) { // if no count given, use default repeat_count = 1; } else if (repeat_count==0) { // count give, but zero is an error dbg_printf("dbg_examine: repeat count given but is zero.\\n"); return; } // set up the default display format and unit size parameters display_format = bx_debugger.default_display_format; unit_size = bx_debugger.default_unit_size; for (i = 0; format [i]; i++) { switch (ch = format [i]) { case 'x': // hex case 'd': // signed decimal case 'u': // unsigned decimal case 'o': // octal case 't': // binary case 'c': // chars case 's': // null terminated string case 'i': // machine instruction display_format = ch; break; case 'b': // bytes case 'h': // halfwords (two bytes) case 'w': // words (4 bytes) case 'g': // giant words (8 bytes) unit_size = ch; break; case 'm': // memory dump memory_dump = true; break; default: dbg_printf("dbg_examine: invalid format passed. \\'%c\\'\\n", ch); bx_dbg_exit(1); break; } } } if ((display_format == 'i') || (display_format == 's')) { dbg_printf("error: dbg_examine: 'i' and 's' formats not supported.\\n"); return; } if (unit_size == 'g') { dbg_printf("error: dbg_examine: 'g' (8-byte) unit size not supported.\\n"); return; } if (format_passed) { // store current options as default bx_debugger.default_display_format = display_format; bx_debugger.default_unit_size = unit_size; } data_size = 0; per_line = 0; offset = 0; if (memory_dump) { if (display_format == 'c') { // Display character dump in lines of 64 characters unit_size = 'b'; data_size = 1; per_line = 64; } else switch (unit_size) { case 'b': data_size = 1; per_line = 16; break; case 'h': data_size = 2; per_line = 8; break; case 'w': data_size = 4; per_line = 4; break; //case 'g': data_size = 8; per_line = 2; break; } // binary format is quite large if (display_format == 't') per_line /= 4; } else { switch (unit_size) { case 'b': data_size = 1; per_line = 8; break; case 'h': data_size = 2; per_line = 8; break; case 'w': data_size = 4; per_line = 4; break; //case 'g': data_size = 8; per_line = 2; break; } } columns = per_line + 1; // set current number columns past limit for (i=1; i<=repeat_count; i++) { if (columns > per_line) { // if not 1st run, need a newline from last line if (i!=1) dbg_printf("\\n"); if (memory_dump) dbg_printf("0x" FMT_ADDRX ":", addr); else dbg_printf("0x" FMT_ADDRX " <bogus+%8u>:", addr, offset); columns = 1; } /* Put a space in the middle of dump, for readability */ if ((columns - 1) == per_line / 2 && memory_dump && display_format != 'c') dbg_printf(" "); if (is_linear) { if (! bx_dbg_read_linear(dbg_cpu, addr, data_size, databuf)) return; } else { // address is already physical address BX_MEM(0)->dbg_fetch_mem(BX_CPU(dbg_cpu), (bx_phy_address) addr, data_size, databuf); } //FIXME HanishKVC The char display for data to be properly integrated // so that repeat_count, columns, etc. can be set or used properly. // Also for data_size of 2 and 4 how to display the individual // characters i.e in which order to be decided. switch (data_size) { case 1: data8 = databuf[0]; { FILE* fp = fopen(DUMP_FILE_NAME, "ab+"); if (fp != NULL) { fwrite(&data8, 1, 1, fp); fclose(fp); } } if (memory_dump) switch (display_format) { case 'd': dbg_printf("%03d ", data8); break; case 'u': dbg_printf("%03u ", data8); break; case 'o': dbg_printf("%03o ", data8); break; case 't': dbg_printf_binary ("%s ", data8, 8); break; case 'c': dbg_printf("%c", isprint(data8) ? data8 : '.'); break; default : dbg_printf("%02X ", data8); break; } else switch (display_format) { case 'x': dbg_printf("\\t0x%02x", (unsigned) data8); break; case 'd': dbg_printf("\\t%d", (int) (Bit8s) data8); break; case 'u': dbg_printf("\\t%u", (unsigned) data8); break; case 'o': dbg_printf("\\t%o", (unsigned) data8); break; case 't': dbg_printf_binary("\\t%s", data8, 8); break; case 'c': bx_print_char(data8); break; } break; case 2: #ifdef BX_LITTLE_ENDIAN data16 = * (Bit16u *) databuf; #else data16 = (databuf[1]<<8) | databuf[0]; #endif if (memory_dump) switch (display_format) { case 'd': dbg_printf("%05d ", data16); break; case 'u': dbg_printf("%05u ", data16); break; case 'o': dbg_printf("%06o ", data16); break; case 't': dbg_printf_binary ("%s ", data16, 16); break; default : dbg_printf("%04X ", data16); break; } else switch (display_format) { case 'x': dbg_printf("\\t0x%04x", (unsigned) data16); break; case 'd': dbg_printf("\\t%d", (int) (Bit16s) data16); break; case 'u': dbg_printf("\\t%u", (unsigned) data16); break; case 'o': dbg_printf("\\t%o", (unsigned) data16); break; case 't': dbg_printf_binary("\\t%s", data16, 16); break; case 'c': bx_print_char(data16>>8); bx_print_char(data16 & 0xff); break; } break; case 4: #ifdef BX_LITTLE_ENDIAN data32 = * (Bit32u *) databuf; #else data32 = (databuf[3]<<24) | (databuf[2]<<16) | (databuf[1]<<8) | databuf[0]; #endif if (memory_dump) switch (display_format) { case 'd': dbg_printf("%10d ", data32); break; case 'u': dbg_printf("%10u ", data32); break; case 'o': dbg_printf("%12o ", data32); break; case 't': dbg_printf_binary ("%s ", data32, 32); break; default : dbg_printf("%08X ", data32); break; } else switch (display_format) { case 'x': dbg_printf("\\t0x%08x", (unsigned) data32); break; case 'd': dbg_printf("\\t%d", (int) (Bit32s) data32); break; case 'u': dbg_printf("\\t%u", (unsigned) data32); break; case 'o': dbg_printf("\\t%o", (unsigned) data32); break; case 't': dbg_printf_binary("\\t%s", data32, 32); break; case 'c': bx_print_char(0xff & (data32>>24)); bx_print_char(0xff & (data32>>16)); bx_print_char(0xff & (data32>> 8)); bx_print_char(0xff & (data32>> 0)); break; } break; } addr += data_size; bx_debugger.default_addr = addr; columns++; offset += data_size; } dbg_printf("\\n"); }