void split_at(size_t pos, mem_chunk &left, mem_chunk &right) const { uint8_t *p = this->p; size_t size = this->sz; pos = std::min(pos, size); left = mem_chunk(p, pos); right = mem_chunk(p + pos, size - pos); }
static void ownership(u32 base, const char *pname, const char *devmem) { u8 *buf; int i; /* read the ownership tag */ if((buf=mem_chunk(base, 0x51, devmem))==NULL) { perror(pname); return; } /* chop the trailing garbage */ i=0x4f; while(i>=0 && (buf[i]==0x20 || buf[i]==0x00)) i--; buf[i+1]='\0'; /* filter and print */ if(i>=0) { for(; i>=0; i--) { if(buf[i]<32 || (buf[i]>=127 && buf[i]<160)) buf[i]='?'; } printf("%s\n", (char *)buf); } free(buf); }
int main(int argc, char * const argv[]) { u8 *buf; off_t fp; int ok=0; if(sizeof(u8)!=1 || sizeof(u32)!=4) { fprintf(stderr, "%s: compiler incompatibility\n", argv[0]); exit(255); } /* Set default option values */ opt.devmem=DEFAULT_MEM_DEV; opt.flags=0; if(parse_command_line(argc, argv)<0) exit(2); if(opt.flags & FLAG_HELP) { print_help(); return 0; } if(opt.flags & FLAG_VERSION) { printf("%s\n", VERSION); return 0; } if((buf=mem_chunk(0xE0000, 0x20000, opt.devmem))==NULL) exit(1); for(fp=0; !ok && fp<=0x1FFF0; fp+=16) { u8 *p=buf+fp; if(memcmp((char *)p, "32OS", 4)==0) { off_t len=p[4]*10+5; if(fp+len-1<=0x1FFFF) { u32 base; if((base=decode(p))) { ok=1; ownership(base, argv[0], opt.devmem); } } } } free(buf); return 0; }
int dump(const char *memdev, const char *dumpfile) { /* On success, return found, otherwise return -1 */ int ret = 0; int found = 0; size_t fp; int efi; u8 *buf; /* First try EFI (ia64, Intel-based Mac) */ efi = address_from_efi(NULL, &fp); if(efi == EFI_NOT_FOUND) { /* Fallback to memory scan (x86, x86_64) */ if((buf = mem_chunk(NULL, 0xF0000, 0x10000, memdev)) != NULL) { for(fp = 0; fp <= 0xFFF0; fp += 16) { if(memcmp(buf + fp, "_SM_", 4) == 0 && fp <= 0xFFE0) { if(dumpling(buf + fp, dumpfile, NON_LEGACY)) found++; fp += 16; } else if(memcmp(buf + fp, "_DMI_", 5) == 0) { if(dumpling(buf + fp, dumpfile, LEGACY)) found++; } } } else ret = -1; } else if(efi == EFI_NO_SMBIOS) { ret = -1; } else { if((buf = mem_chunk(NULL, fp, 0x20, memdev)) == NULL) ret = -1; else if(dumpling(buf, dumpfile, NON_LEGACY)) found++; } if(ret == 0) { free(buf); if(!found) { ret = -1; } } return ret == 0 ? found : ret; }
int dumpling(u8 * buf, const char *dumpfile, u8 mode) { u32 base; u16 len; if(mode == NON_LEGACY) { if(!checksum(buf, buf[0x05]) || !memcmp(buf + 0x10, "_DMI_", 5) == 0 || !checksum(buf + 0x10, 0x0F)) return 0; base = DWORD(buf + 0x18); len = WORD(buf + 0x16); } else { if(!checksum(buf, 0x0F)) return 0; base = DWORD(buf + 0x08); len = WORD(buf + 0x06); } u8 *buff; if((buff = mem_chunk(NULL, base, len, DEFAULT_MEM_DEV)) != NULL) { //. Part 1. #ifdef NDEBUG printf("# Writing %d bytes to %s.\n", len, dumpfile); #endif write_dump(32, len, buff, dumpfile, 0); free(buff); //. Part 2. if(mode != LEGACY) { u8 crafted[32]; memcpy(crafted, buf, 32); overwrite_dmi_address(crafted + 0x10); #ifdef NDEBUG printf("# Writing %d bytes to %s.\n", crafted[0x05], dumpfile); #endif write_dump(0, crafted[0x05], crafted, dumpfile, 1); } else { u8 crafted[16]; memcpy(crafted, buf, 16); overwrite_dmi_address(crafted); #ifdef NDEBUG printf("# Writing %d bytes to %s.\n", 0x0F, dumpfile); #endif write_dump(0, 0x0F, crafted, dumpfile, 1); } } else { fprintf(stderr, "Failed to read table, sorry.\n"); } //. TODO: Cleanup return 1; }
int main(int argc, char ** argv) { if (argc != 3) { fprintf(stderr, "usage: %s <input> <output>\n", argv[0]); return EXIT_FAILURE; } try { size_t size = get_available_mem_size(); void *p = mmap(NULL, size, PROT_READ|PROT_WRITE, MAP_ANON|MAP_PRIVATE, -1, 0); if (p==MAP_FAILED) { throw std::runtime_error( format_message_with_errno( errno, "Allocating %zu bytes of memory", size)); } sort_element::base = p; mem_chunk available_mem = mem_chunk(p, size).aligned(); file_id_t src_file = file_id::create_with_path(argv[1]); file_id_t dest_file = file_id::create_with_path(argv[2]); dest_file->set_auto_unlink(true); std::deque<file_id_t> transient_files; split_and_sort(available_mem, src_file, dest_file, transient_files); merge_sorted(available_mem, src_file, dest_file, transient_files); dest_file->set_auto_unlink(false); return EXIT_SUCCESS; } catch (const std::logic_error &e) { fprintf(stderr, "%s: Internal error: %s\n", argv[0], e.what()); return EXIT_FAILURE; } catch (const std::exception &e) { fprintf(stderr, "%s: %s\n", argv[0], e.what()); return EXIT_FAILURE; } }
mem_chunk get_body() const { record_header2 &hd = const_cast<record_header2 &>(get_header()); return mem_chunk(hd.body, hd.is_body_present ? hd.body_size : 0); }
mem_chunk sub_chunk(size_t offset, size_t size) const { size_t origin = std::min(offset, sz); return mem_chunk(p + origin, std::min(size, sz - origin)); }
int main(int argc, char * const argv[]) { u8 *buf; int found = 0; unsigned int fp; if (sizeof(u8) != 1) { fprintf(stderr, "%s: compiler incompatibility\n", argv[0]); exit(255); } /* Set default option values */ opt.devmem = DEFAULT_MEM_DEV; opt.flags = 0; if (parse_command_line(argc, argv)<0) exit(2); if (opt.flags & FLAG_HELP) { print_help(); return 0; } if (opt.flags & FLAG_VERSION) { printf("%s\n", VERSION); return 0; } if (!(opt.flags & FLAG_QUIET)) printf("# vpddecode %s\n", VERSION); if ((buf = mem_chunk(0xF0000, 0x10000, opt.devmem)) == NULL) exit(1); for (fp = 0; fp <= 0xFFF0; fp += 4) { u8 *p = buf + fp; if (memcmp((char *)p, "\252\125VPD", 5) == 0 && fp + p[5] - 1 <= 0xFFFF) { if (fp % 16 && !(opt.flags & FLAG_QUIET)) printf("# Unaligned address (%#x)\n", 0xf0000 + fp); if (opt.flags & FLAG_DUMP) { dump(p, p[5]); found++; } else { if (decode(p)) found++; } } } free(buf); if (!found && !(opt.flags & FLAG_QUIET)) printf("# No VPD structure found, sorry.\n"); return 0; }