MCPcopy Create free account
hub / github.com/clementgallet/libTAS / locatePointers

Method locatePointers

src/program/ui/PointerScanModel.cpp:35–129  ·  view source on GitHub ↗

Source from the content-addressed store, hash-verified

33PointerScanModel::PointerScanModel(Context* c, QObject *parent) : QAbstractTableModel(parent), context(c) {}
34
35void PointerScanModel::locatePointers()
36{
37 pointer_map.clear();
38 static_pointer_map.clear();
39
40 std::unique_ptr<MemLayout> memlayout (new MemLayout(context->game_pid));
41
42 std::vector<MemSection> memory_sections;
43 file_mapping_sections.clear();
44
45 int type_flag = (MemSection::MemDataRW | MemSection::MemBSS | MemSection::MemHeap | MemSection::MemAnonymousMappingRW | MemSection::MemFileMappingRW | MemSection::MemStack);
46 uint64_t total_size = memlayout->totalSize(type_flag, 0);
47
48 MemSection section;
49 while (memlayout->nextSection(type_flag, 0, section)) {
50 /* Only store sections that could contain pointers */
51 memory_sections.push_back(section);
52
53 /* Keep the file mapping to access to the file and offsets */
54 if (section.type & (MemSection::MemDataRW | MemSection::MemBSS | MemSection::MemFileMappingRW | MemSection::MemStack)) {
55 file_mapping_sections.push_back(section);
56 }
57 }
58
59 /* Read all memory and store all pointers */
60 int cur_size = 0;
61 int game_addr_size = MemAccess::getAddrSize();
62 for (const MemSection &section : memory_sections) {
63
64 for (uintptr_t addr = section.addr; addr < section.endaddr; addr += 4096) {
65
66 /* Read values in chunks of 4096 bytes so we lower the number of calls. */
67
68 /* The following code is a bit awkward to support both 32-bit and
69 * 64-bit pointers while conforming aliasing rules. A better coder
70 * than me may write more elegant code */
71 uint64_t chunk64[4096/sizeof(uint64_t)];
72 uint32_t chunk32[4096/sizeof(uint32_t)];
73 int readValues;
74
75 if (game_addr_size == 4) {
76 readValues = MemAccess::read(chunk32, reinterpret_cast<void*>(addr), 4096);
77 }
78 else {
79 readValues = MemAccess::read(chunk64, reinterpret_cast<void*>(addr), 4096);
80 }
81
82 if (readValues < 0) {
83 continue;
84 }
85
86 /* Update progress bar */
87 emit signalProgress((int)(100 * ((float)cur_size / total_size)));
88
89 unsigned int chunk_data_size = readValues/game_addr_size;
90
91 for (unsigned int i = 0; i < chunk_data_size; i++, cur_size += game_addr_size) {
92 /* Check if the value could be a pointer */

Callers

nothing calls this directly

Calls 4

totalSizeMethod · 0.80
nextSectionMethod · 0.80
clearMethod · 0.45
insertMethod · 0.45

Tested by

no test coverage detected