1// Copyright 2021 the V8 project authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5#ifndef V8_BASE_VIRTUAL_ADDRESS_SPACE_PAGE_ALLOCATOR_H_
6#define V8_BASE_VIRTUAL_ADDRESS_SPACE_PAGE_ALLOCATOR_H_
7
8#include <unordered_map>
9
10#include "include/v8-platform.h"
11#include "src/base/base-export.h"
12#include "src/base/platform/platform.h"
13
14namespace v8 {
15namespace base {
16
17// This class bridges a VirtualAddressSpace, the future memory management API,
18// to a PageAllocator, the current API.
19class V8_BASE_EXPORT VirtualAddressSpacePageAllocator
20    : public v8::PageAllocator {
21 public:
22  using Address = uintptr_t;
23
24  explicit VirtualAddressSpacePageAllocator(v8::VirtualAddressSpace* vas);
25
26  VirtualAddressSpacePageAllocator(const VirtualAddressSpacePageAllocator&) =
27      delete;
28  VirtualAddressSpacePageAllocator& operator=(
29      const VirtualAddressSpacePageAllocator&) = delete;
30  ~VirtualAddressSpacePageAllocator() override = default;
31
32  size_t AllocatePageSize() override { return vas_->allocation_granularity(); }
33
34  size_t CommitPageSize() override { return vas_->page_size(); }
35
36  void SetRandomMmapSeed(int64_t seed) override { vas_->SetRandomSeed(seed); }
37
38  void* GetRandomMmapAddr() override {
39    return reinterpret_cast<void*>(vas_->RandomPageAddress());
40  }
41
42  void* AllocatePages(void* hint, size_t size, size_t alignment,
43                      Permission access) override;
44
45  bool FreePages(void* address, size_t size) override;
46
47  bool ReleasePages(void* address, size_t size, size_t new_size) override;
48
49  bool SetPermissions(void* address, size_t size, Permission access) override;
50
51  bool DiscardSystemPages(void* address, size_t size) override;
52
53  bool DecommitPages(void* address, size_t size) override;
54
55 private:
56  // Client of this class must keep the VirtualAddressSpace alive during the
57  // lifetime of this instance.
58  v8::VirtualAddressSpace* vas_;
59
60  // As the VirtualAddressSpace class doesn't support ReleasePages, this map is
61  // required to keep track of the original size of resized page allocations.
62  // See the ReleasePages implementation.
63  std::unordered_map<Address, size_t> resized_allocations_;
64
65  // Mutex guarding the above map.
66  Mutex mutex_;
67};
68
69}  // namespace base
70}  // namespace v8
71
72#endif  // V8_BASE_VIRTUAL_ADDRESS_SPACE_PAGE_ALLOCATOR_H_
73