https://git.reactos.org/?p=reactos.git;a=commitdiff;h=1a02d3306b1a827dd3a059a68cdb7846dee391ad

commit 1a02d3306b1a827dd3a059a68cdb7846dee391ad
Author:     Hermès Bélusca-Maïto <hermes.belusca-ma...@reactos.org>
AuthorDate: Thu Nov 28 21:26:03 2024 +0100
Commit:     Hermès Bélusca-Maïto <hermes.belusca-ma...@reactos.org>
CommitDate: Tue Dec 3 22:13:57 2024 +0100

    [NTOS:KD64] Fix usage of the debugging banner code, based on when 
KdInitSystem() is called (#7540)
    
    - The debugging banner helpers *CANNOT* be in the INIT section, because
      it is possible for KdInitSystem() to enable the debugger **MUCH LATER**
      after boot time. (Reverts part of commit f239ca0f0 (r72922).)
    
      This can happen in two situations:
    
      * When the debugger is in CRASHDEBUG mode, i.e. initialized at boot
        time but not immediately enabled, and a BSOD happens later that
        enables the debugger with a `KdInitSystem(0, NULL)` call.
    
      * When the debugger was possibly manually disabled with a
        KdDisableDebugger() call, then later re-enabled with a
        KdEnableDebugger() call.
    
    - In the same cases as described above, the KeLoaderBlock is freed after
      boot time. Thus, KdpGetMemorySizeInMBs() cannot use it and enumerate
      the MemoryDescriptors to evaluate the number of physical memory pages
      available on the system. Instead, we can use what the memory manager
      has already computed, since the latter is already initialized by now.
    
    These two fixes avoid (invisible) crashes when (re-)enabling
    the debugger at non-boot run time.
---
 ntoskrnl/kd64/kdinit.c | 22 ++++++++++++++++------
 1 file changed, 16 insertions(+), 6 deletions(-)

diff --git a/ntoskrnl/kd64/kdinit.c b/ntoskrnl/kd64/kdinit.c
index 917061995fe..a49655ff6cb 100644
--- a/ntoskrnl/kd64/kdinit.c
+++ b/ntoskrnl/kd64/kdinit.c
@@ -23,17 +23,27 @@
  *
  * Strongly inspired by:
  * mm\ARM3\mminit.c : MiScanMemoryDescriptors(...)
- *
- * See also: kd\kdio.c
  */
-static CODE_SEG("INIT")
+static
 SIZE_T
-KdpGetMemorySizeInMBs(IN PLOADER_PARAMETER_BLOCK LoaderBlock)
+KdpGetMemorySizeInMBs(
+    _In_opt_ PLOADER_PARAMETER_BLOCK LoaderBlock)
 {
     PLIST_ENTRY ListEntry;
     PMEMORY_ALLOCATION_DESCRIPTOR Descriptor;
     SIZE_T NumberOfPhysicalPages = 0;
 
+    /*
+     * If no loader block is present (e.g. the debugger is initialized only
+     * much later after boot), just use the already-initialized Mm-computed
+     * number of physical pages. Otherwise do the evaluation ourselves.
+     */
+    if (!LoaderBlock)
+    {
+        NumberOfPhysicalPages = MmNumberOfPhysicalPages;
+        goto ReturnSize;
+    }
+
     /* Loop the memory descriptors */
     for (ListEntry = LoaderBlock->MemoryDescriptorListHead.Flink;
          ListEntry != &LoaderBlock->MemoryDescriptorListHead;
@@ -62,12 +72,12 @@ KdpGetMemorySizeInMBs(IN PLOADER_PARAMETER_BLOCK 
LoaderBlock)
         }
     }
 
+ReturnSize:
     /* Round size up. Assumed to better match actual physical RAM size */
     return ALIGN_UP_BY(NumberOfPhysicalPages * PAGE_SIZE, 1024 * 1024) / (1024 
* 1024);
 }
 
-/* See also: kd\kdio.c */
-static CODE_SEG("INIT")
+static
 VOID
 KdpPrintBanner(IN SIZE_T MemSizeMBs)
 {

Reply via email to