From 37c2b8f74c5a5733505851502282625f17435371 Mon Sep 17 00:00:00 2001 From: Minep Date: Mon, 26 Aug 2024 15:37:45 +0100 Subject: [PATCH] add vm probing for x86_64 --- lunaix-os/live_debug.sh | 3 +- .../scripts/gdb/lunadbg/arch/__init__.py | 2 +- .../scripts/gdb/lunadbg/arch/x86/__init__.py | 2 +- lunaix-os/scripts/gdb/lunadbg/arch/x86/pte.py | 81 ++++++++++++++++++- lunaix-os/scripts/gdb/lunadbg/commands.py | 15 ++-- lunaix-os/scripts/gdb/lunadbg/mem.py | 13 +-- .../scripts/gdb/lunadbg/structs/pagetable.py | 3 +- 7 files changed, 104 insertions(+), 15 deletions(-) diff --git a/lunaix-os/live_debug.sh b/lunaix-os/live_debug.sh index d189329..0ecc759 100755 --- a/lunaix-os/live_debug.sh +++ b/lunaix-os/live_debug.sh @@ -15,4 +15,5 @@ make CMDLINE=${default_cmd} ARCH=${ARCH} MODE=${MODE:-debug} image -j5 || exit - -v EXT2_TEST_DISC=machine/test_part.ext2 \ -v ARCH=${ARCH} & -QMPORT=${hmp_port} gdb build/bin/kernel.bin -ex "target remote localhost:${gdb_port}" \ No newline at end of file +QMPORT=${hmp_port} ARCH=${ARCH} \ + gdb build/bin/kernel.bin -ex "target remote localhost:${gdb_port}" \ No newline at end of file diff --git a/lunaix-os/scripts/gdb/lunadbg/arch/__init__.py b/lunaix-os/scripts/gdb/lunadbg/arch/__init__.py index dbb00ce..682d6d0 100644 --- a/lunaix-os/scripts/gdb/lunadbg/arch/__init__.py +++ b/lunaix-os/scripts/gdb/lunadbg/arch/__init__.py @@ -1,4 +1,4 @@ import os -if os.environ["LUNADBG_ARCH"].startswith("x86_"): +if os.environ["ARCH"].startswith("x86_"): from .x86 import * \ No newline at end of file diff --git a/lunaix-os/scripts/gdb/lunadbg/arch/x86/__init__.py b/lunaix-os/scripts/gdb/lunadbg/arch/x86/__init__.py index 2ee9e2d..6eede5b 100644 --- a/lunaix-os/scripts/gdb/lunadbg/arch/x86/__init__.py +++ b/lunaix-os/scripts/gdb/lunadbg/arch/x86/__init__.py @@ -1,6 +1,6 @@ import os -if os.environ["LUNADBG_ARCH"] == 'x86_64': +if os.environ["ARCH"] == 'x86_64': from .pte import PageTableHelper64 as PageTableHelper else: from .pte import PageTableHelper32 as PageTableHelper diff --git a/lunaix-os/scripts/gdb/lunadbg/arch/x86/pte.py b/lunaix-os/scripts/gdb/lunadbg/arch/x86/pte.py index 444cb3f..1bf626e 100644 --- a/lunaix-os/scripts/gdb/lunadbg/arch/x86/pte.py +++ b/lunaix-os/scripts/gdb/lunadbg/arch/x86/pte.py @@ -44,6 +44,10 @@ class PageTableHelperBase: raise NotImplementedError() class PageTableHelper32(PageTableHelperBase): + @staticmethod + def null_mapping(pte): + return pte == 0 + @staticmethod def translation_level(level = -1): return [0, 1][level] @@ -108,6 +112,81 @@ class PageTableHelper32(PageTableHelperBase): @staticmethod def pte_size(): return 4 + + @staticmethod + def vm_mnt(): + return 0xFFC00000 class PageTableHelper64(PageTableHelperBase): - pass \ No newline at end of file + @staticmethod + def null_mapping(pte): + return pte == 0 + + @staticmethod + def translation_level(level = -1): + return [0, 1, 2, 3][level] + + @staticmethod + def pgtable_len(): + return (1 << 9) + + @staticmethod + def translation_shift_bits(level): + return [9, 9, 9, 0][level] + 12 + + @staticmethod + def mapping_present(pte): + return bool(pte & 1) + + @staticmethod + def huge_page(pte, po): + return bool(pte & (1 << 7)) and po + + @staticmethod + def protections(pte): + prot = ['R'] # RWXUP + if (pte & (1 << 1)): + prot.append('W') + if (pte & -1): + prot.append('X') + if (pte & (1 << 2)): + prot.append('U') + if (pte & (1)): + prot.append('P') + return prot + + @staticmethod + def other_attributes(level, pte): + attrs = [] + if pte & (1 << 5): + attrs.append("A") + if pte & (1 << 6): + attrs.append("D") + if pte & (1 << 3): + attrs.append("PWT") + if pte & (1 << 4): + attrs.append("PCD") + if PageTableHelper32.translation_level(level) == 1 and pte & (1 << 8): + attrs.append("G") + return attrs + + @staticmethod + def same_kind(pte1, pte2): + attr_mask = 0x19f # P, R/W, U/S, PWT, PCD, PS, G + return (pte1 & attr_mask) == (pte2 & attr_mask) + + @staticmethod + def physical_pfn(pte): + return pte >> 12 + + @staticmethod + def vaddr_width(): + return 48 + + @staticmethod + def pte_size(): + return 8 + + @staticmethod + def vm_mnt(): + return 0xffffff0000000000 \ No newline at end of file diff --git a/lunaix-os/scripts/gdb/lunadbg/commands.py b/lunaix-os/scripts/gdb/lunadbg/commands.py index ec3fe82..1e4d425 100644 --- a/lunaix-os/scripts/gdb/lunadbg/commands.py +++ b/lunaix-os/scripts/gdb/lunadbg/commands.py @@ -2,6 +2,7 @@ from gdb import Command, COMMAND_USER import argparse import shlex +import traceback class LunadbgCommand(Command): def __init__(self, name: str) -> None: @@ -20,10 +21,14 @@ class LunadbgCommand(Command): return None def invoke(self, argument: str, from_tty: bool) -> None: - parsed = self._parse_args(argument) - if not parsed: - return - self.on_execute(parsed, argument, from_tty) - + try: + parsed = self._parse_args(argument) + if not parsed: + return + self.on_execute(parsed, argument, from_tty) + except Exception as e: + traceback.print_exception(e) + + def on_execute(self, parsed, gdb_args, from_tty): raise NotImplementedError() \ No newline at end of file diff --git a/lunaix-os/scripts/gdb/lunadbg/mem.py b/lunaix-os/scripts/gdb/lunadbg/mem.py index 558ad3a..a51560c 100644 --- a/lunaix-os/scripts/gdb/lunadbg/mem.py +++ b/lunaix-os/scripts/gdb/lunadbg/mem.py @@ -2,6 +2,7 @@ from .commands import LunadbgCommand from .pp import MyPrettyPrinter from .profiling.pmstat import PhysicalMemProfile from .structs.pagetable import PageTable +from .arch.x86 import PageTableHelper class MMStats(LunadbgCommand): def __init__(self) -> None: @@ -60,13 +61,15 @@ class MMStats(LunadbgCommand): def vm_lookup(self, pp, va, optn): to_addr = int(optn.to_addr, 0) + vmt = PageTableHelper.vm_mnt() if not optn.n and not to_addr: - pp.print(self.__ptw.get_pte(va, level=optn.level)) + pp.print(self.__ptw.get_pte(va, level=optn.level, mnt=vmt)) + return + + if to_addr: + self.__ptw.print_ptes_between(pp, va, to_addr, optn.level, mnt=vmt) else: - if to_addr: - self.__ptw.print_ptes_between(pp, va, to_addr, optn.level) - else: - self.__ptw.print_ptes(pp, va, optn.n, optn.level) + self.__ptw.print_ptes(pp, va, optn.n, optn.level, mnt=vmt) def __do_stats(self, pp, optn): if optn.state_type == "pmem": diff --git a/lunaix-os/scripts/gdb/lunadbg/structs/pagetable.py b/lunaix-os/scripts/gdb/lunadbg/structs/pagetable.py index 58ed0c8..c58eedd 100644 --- a/lunaix-os/scripts/gdb/lunadbg/structs/pagetable.py +++ b/lunaix-os/scripts/gdb/lunadbg/structs/pagetable.py @@ -248,7 +248,8 @@ class PageTable(): ptep += TLB.pte_size() - self.__print_pte_ranged(pp, head_pte, prev_pte) + if head_pte: + self.__print_pte_ranged(pp, head_pte, prev_pte) def print_ptes_between(self, pp, va, va_end, level=-1, mnt=0xFFC00000): ptep_start = PageTable.mkptep_for(mnt, va) -- 2.27.0