File: TestSharedMappingCommit.cpp

package info (click to toggle)
firefox 147.0.3-1
  • links: PTS, VCS
  • area: main
  • in suites: sid
  • size: 4,683,320 kB
  • sloc: cpp: 7,607,359; javascript: 6,533,295; ansic: 3,775,223; python: 1,415,500; xml: 634,561; asm: 438,949; java: 186,241; sh: 62,752; makefile: 18,079; objc: 13,092; perl: 12,808; yacc: 4,583; cs: 3,846; pascal: 3,448; lex: 1,720; ruby: 1,003; php: 436; lisp: 258; awk: 247; sql: 66; sed: 54; csh: 10; exp: 6
file content (129 lines) | stat: -rw-r--r-- 4,310 bytes parent folder | download | duplicates (2)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* vim: set ts=8 sts=2 et sw=2 tw=80: */
/* This Source Code Form is subject to the terms of the Mozilla Public
 * License, v. 2.0. If a copy of the MPL was not distributed with this
 * file, You can obtain one at https://mozilla.org/MPL/2.0/. */

#include <cstdint>
#include <cstdio>
#include <windows.h>

// Tests that when there are multiple views to a unique mapping, committing
// memory pages for one of the views actually commits them for all views. We
// rely on this behavior in `mozglue/interceptor/MMPolicies.h` and in
// `security/sandbox/chromium/sandbox/win/src/interception.cc`.
bool TestSharedMappingCommit() {
  constexpr size_t kMappingSize = 64 * 1024;
  constexpr size_t kCommitOffset = 32 * 1024;
  constexpr size_t kCommitSize = 4 * 1024;

  HANDLE mapping = ::CreateFileMappingW(INVALID_HANDLE_VALUE, nullptr,
                                        PAGE_EXECUTE_READWRITE | SEC_RESERVE, 0,
                                        kMappingSize, nullptr);
  if (!mapping) {
    printf(
        "TEST-FAIL | SharedMappingCommit | Failed to create a pagefile-backed "
        "mapping\n");
    return false;
  }

  void* rwView =
      ::MapViewOfFile(mapping, FILE_MAP_READ | FILE_MAP_WRITE, 0, 0, 0);
  if (!rwView) {
    printf(
        "TEST-FAIL | SharedMappingCommit | Failed to get a read/write view\n");
    return false;
  }

  void* rxView =
      ::MapViewOfFile(mapping, FILE_MAP_READ | FILE_MAP_EXECUTE, 0, 0, 0);
  if (!rxView) {
    printf(
        "TEST-FAIL | SharedMappingCommit | Failed to get a read/execute "
        "view\n");
    return false;
  }

  auto* rwCommitAddress =
      static_cast<void*>(static_cast<uint8_t*>(rwView) + kCommitOffset);
  auto* rxCommitAddress =
      static_cast<void*>(static_cast<uint8_t*>(rxView) + kCommitOffset);

  {
    MEMORY_BASIC_INFORMATION info{};
    if (::VirtualQuery(rxCommitAddress, &info, sizeof(info)) != sizeof(info)) {
      printf(
          "TEST-FAIL | SharedMappingCommit | Failed to query basic information "
          "about the read/execute memory pages\n");
      return false;
    }
    if (info.State != MEM_RESERVE) {
      printf(
          "TEST-FAIL | SharedMappingCommit | Unexpected initial state for the "
          "read/execute memory pages: %lu\n",
          info.State);
      return false;
    }
  }

  rwCommitAddress = ::VirtualAlloc(static_cast<void*>(rwCommitAddress),
                                   kCommitSize, MEM_COMMIT, PAGE_READWRITE);
  if (!rwCommitAddress) {
    printf(
        "TEST-FAIL | SharedMappingCommit | Failed to commit read/write "
        "memory pages\n");
    return false;
  }

  {
    MEMORY_BASIC_INFORMATION info{};
    if (::VirtualQuery(rxCommitAddress, &info, sizeof(info)) != sizeof(info)) {
      printf(
          "TEST-FAIL | SharedMappingCommit | Failed to query basic information "
          "about the read/execute memory pages\n");
      return false;
    }
    if (info.State != MEM_COMMIT) {
      printf(
          "TEST-FAIL | SharedMappingCommit | Read/write commit hasn't changed "
          "the state of the read/execute memory pages: %lu\n",
          info.State);
      return false;
    }
    if (info.Protect != PAGE_EXECUTE_READ) {
      printf(
          "TEST-FAIL | SharedMappingCommit | Unexpected protection for the "
          "read/execute memory pages: %lu\n",
          info.Protect);
      return false;
    }
  }

  constexpr uint32_t kMagic = 0xdeadbeef;

  uint32_t* rwMagicAddr = static_cast<uint32_t*>(rwCommitAddress);
  *rwMagicAddr = kMagic;

  const uint32_t* rxMagicAddr = static_cast<const uint32_t*>(rxCommitAddress);
  if (*rxMagicAddr != kMagic) {
    printf(
        "TEST-FAIL | SharedMappingCommit | Read a different value through the "
        "read/execute view than was written through the read/write view\n");
    return false;
  }

  printf(
      "TEST-PASS | SharedMappingCommit | Committing memory pages through the "
      "read/write view also commited the corresponding pages in the "
      "read/execute view\n");
  return true;
}

int wmain(int argc, wchar_t* argv[]) {
  if (!TestSharedMappingCommit()) {
    return 1;
  }

  printf("TEST-PASS | SharedMappingCommit | All tests ran successfully\n");
  return 0;
}