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

commit e806d16b065c5db27206d69f76a724ce593659bc
Author:     Pierre Schweitzer <pie...@reactos.org>
AuthorDate: Fri Aug 31 19:43:04 2018 +0200
Commit:     Pierre Schweitzer <pie...@reactos.org>
CommitDate: Fri Aug 31 19:48:32 2018 +0200

    [NTOSKRNL] Warn about unimplemented feature in CcMapData() (in all callers)
    
    Currently, our CcMapData() behavior (same goes for CcPinRead()) is broken
    and is the total opposite of what Windows kernel does. By default, the later
    will let you map a view in memory without even attempting to bring its
    data in memory. On first access, there will be a fault and memory will
    be read from the hardware and brought to memory. If you want to force read
    on mapping/pinning, you have to set the MAP_NO_READ (or PIN_NO_READ) flag
    where kernel will fault on your behalf (hence the need for 
MAP_WAIT/PIN_WAIT).
    
    On ReactOS, by default, on mapping (and thus pinning), we will force a view
    read so that data is in memory. The way our cache memory is managed at the
    moment seems not to allow to fault on invalid access and if we don't force
    read, the memory content will just be zeroed.
    So trying to match Windows behavior, by default, now CcMapData() will 
enforce
    the MAP_NO_READ flag and warn once about this behavior change.
---
 ntoskrnl/cc/pin.c | 16 ++++++++++++++--
 1 file changed, 14 insertions(+), 2 deletions(-)

diff --git a/ntoskrnl/cc/pin.c b/ntoskrnl/cc/pin.c
index 65525eed83..7373981119 100644
--- a/ntoskrnl/cc/pin.c
+++ b/ntoskrnl/cc/pin.c
@@ -86,6 +86,18 @@ CcMapData (
         return FALSE;
     }
 
+    if (!BooleanFlagOn(Flags, MAP_NO_READ))
+    {
+        static int Warned = 0;
+
+        SetFlag(Flags, MAP_NO_READ);
+        if (!Warned)
+        {
+            DPRINT1("Mapping/pinning with no read not implemented. Forcing 
read, might fail if wait not allowed\n");
+            Warned++;
+        }
+    }
+
     ROffset = ROUND_DOWN(ReadOffset, VACB_MAPPING_GRANULARITY);
     Status = CcRosRequestVacb(SharedCacheMap,
                               ROffset,
@@ -100,9 +112,9 @@ CcMapData (
         return FALSE;
     }
 
-    if (!Valid)
+    if (!Valid && BooleanFlagOn(Flags, MAP_NO_READ))
     {
-        if (!(Flags & MAP_WAIT))
+        if (!BooleanFlagOn(Flags, MAP_WAIT))
         {
             CcRosReleaseVacb(SharedCacheMap, Vacb, FALSE, FALSE, FALSE);
             CCTRACE(CC_API_DEBUG, "FileObject=%p FileOffset=%p Length=%lu 
Flags=0x%lx -> FALSE\n",

Reply via email to