diff options
| author | Alejandro Soto <alejandro@34project.org> | 2022-12-12 12:59:41 -0600 |
|---|---|---|
| committer | Alejandro Soto <alejandro@34project.org> | 2022-12-16 16:29:10 -0600 |
| commit | 7c38613cff247fbc7715064291b74426b4ef5b40 (patch) | |
| tree | 58834f085aa1bf4b6db8762a64697c8abb02bae3 | |
| parent | bb38130bb8e2b8ec17cb6347173af435c5ceef18 (diff) | |
Implement page walks in patch-mem
| -rw-r--r-- | tb/top/conspiracion.cpp | 87 |
1 files changed, 46 insertions, 41 deletions
diff --git a/tb/top/conspiracion.cpp b/tb/top/conspiracion.cpp index 5e16505..11516b6 100644 --- a/tb/top/conspiracion.cpp +++ b/tb/top/conspiracion.cpp @@ -446,59 +446,58 @@ int main(int argc, char **argv) std::fputs("=== end-regs ===\n", ctrl); }; - auto do_mem_dump = [&](const mem_region *dumps, std::size_t count) + auto pagewalk = [&](std::uint32_t &addr) { - bool mmu_enabled = core.mmu->mmu_enable; + if(!core.mmu->mmu_enable) + { + return true; + } + std::uint32_t ttbr = core.mmu->mmu_ttbr; - auto pagewalk = [&](std::uint32_t &addr) + std::uint32_t entry; + if(!avl.dump(ttbr << 12 | addr >> 18, entry)) { - if(!mmu_enabled) - { + return false; + } + + switch(entry & 0b11) + { + case 0b01: + break; + + case 0b10: + addr = (entry & ~((1 << 20) - 1)) >> 2 | (addr & ((1 << 18) - 1)); return true; - } - std::uint32_t entry; - if(!avl.dump(ttbr << 12 | addr >> 18, entry)) - { + default: return false; - } + } - switch(entry & 0b11) - { - case 0b01: - break; + std::uint32_t entryaddr = (entry & ~((1 << 10) - 1)) >> 2 | ((addr >> 10) & ((1 << 8) - 1)); + if(!avl.dump(entryaddr, entry)) + { + return false; + } - case 0b10: - addr = (entry & ~((1 << 20) - 1)) >> 2 | (addr & ((1 << 18) - 1)); - return true; + switch(entry & 0b11) + { + case 0b01: + addr = (entry & ~((1 << 16) - 1)) >> 2 | (addr & ((1 << 14) - 1)); + return true; - default: - return false; - } + case 0b10: + case 0b11: + addr = (entry & ~((1 << 12) - 1)) >> 2 | (addr & ((1 << 10) - 1)); + return true; - std::uint32_t entryaddr = (entry & ~((1 << 10) - 1)) >> 2 | ((addr >> 10) & ((1 << 8) - 1)); - if(!avl.dump(entryaddr, entry)) - { + default: return false; - } - - switch(entry & 0b11) - { - case 0b01: - addr = (entry & ~((1 << 16) - 1)) >> 2 | (addr & ((1 << 14) - 1)); - return true; - - case 0b10: - case 0b11: - addr = (entry & ~((1 << 12) - 1)) >> 2 | (addr & ((1 << 10) - 1)); - return true; - - default: - return false; - } - }; + } + }; + auto do_mem_dump = [&](const mem_region *dumps, std::size_t count) + { std::fputs("=== dump-mem ===\n", ctrl); for(std::size_t i = 0; i < count; ++i) { @@ -616,7 +615,13 @@ halt_or_fail: | ((word >> 16) & 0xff) << 8 | ((word >> 24) & 0xff); - avl.patch(addr++, word); + std::uint32_t phys = addr++; + if(!pagewalk(phys)) + { + break; + } + + avl.patch(phys, word); } } else if(!std::strcmp(cmd, "patch-reg")) { |
