gem5 v24.0.0.0
Loading...
Searching...
No Matches
multi_level_page_table.hh
Go to the documentation of this file.
1/*
2 * Copyright (c) 2014 Advanced Micro Devices, Inc.
3 * All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions are
7 * met: redistributions of source code must retain the above copyright
8 * notice, this list of conditions and the following disclaimer;
9 * redistributions in binary form must reproduce the above copyright
10 * notice, this list of conditions and the following disclaimer in the
11 * documentation and/or other materials provided with the distribution;
12 * neither the name of the copyright holders nor the names of its
13 * contributors may be used to endorse or promote products derived from
14 * this software without specific prior written permission.
15 *
16 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
17 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
18 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
19 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
20 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
21 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
22 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
23 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
24 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
25 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
26 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27 */
28
34#ifndef __MEM_MULTI_LEVEL_PAGE_TABLE_HH__
35#define __MEM_MULTI_LEVEL_PAGE_TABLE_HH__
36
37#include <string>
38
39#include "base/types.hh"
40#include "debug/MMU.hh"
41#include "mem/page_table.hh"
42#include "sim/se_workload.hh"
43#include "sim/system.hh"
44
45namespace gem5
46{
47
104namespace {
105
106template <class First, class ...Rest>
107Addr
108prepTopTable(System *system, Addr pageSize)
109{
110 auto *se_workload = dynamic_cast<SEWorkload *>(system->workload);
111 fatal_if(!se_workload, "Couldn't find an appropriate workload object.");
112 Addr addr = se_workload->allocPhysPages(First::tableSize());
113 PortProxy &p = system->physProxy;
114 p.memsetBlob(addr, 0, First::tableSize() * pageSize);
115 return addr;
116}
117
118template <class ...Types>
119struct LastType;
120
121template <class First, class Second, class ...Rest>
122struct LastType<First, Second, Rest...>
123{
124 typedef typename LastType<Second, Rest...>::type type;
125};
126
127template <class Only>
128struct LastType<Only>
129{
130 typedef Only type;
131};
132
133
134template <class ...Types>
135struct WalkWrapper;
136
137template <class Final, class Only>
138struct WalkWrapper<Final, Only>
139{
140 static void
141 walk(System *system, Addr pageSize, Addr table, Addr vaddr,
142 bool allocate, Final *entry)
143 {
144 entry->read(system->physProxy, table, vaddr);
145 }
146};
147
148template <class Final, class First, class Second, class ...Rest>
149struct WalkWrapper<Final, First, Second, Rest...>
150{
151 static void
152 walk(System *system, Addr pageSize, Addr table, Addr vaddr,
153 bool allocate, Final *entry)
154 {
155 First first;
156 first.read(system->physProxy, table, vaddr);
157
158 Addr next;
159 if (!first.present()) {
160 fatal_if(!allocate,
161 "Page fault while walking the page table.");
162 next = prepTopTable<Second>(system, pageSize);
163 first.reset(next);
164 first.write(system->physProxy);
165 } else {
166 next = first.paddr();
167 }
168 WalkWrapper<Final, Second, Rest...>::walk(
169 system, pageSize, next, vaddr, allocate, entry);
170 }
171};
172
173template <class ...EntryTypes>
174void
175walk(System *system, Addr pageSize, Addr table, Addr vaddr,
176 bool allocate, typename LastType<EntryTypes...>::type *entry)
177{
178 WalkWrapper<typename LastType<EntryTypes...>::type, EntryTypes...>::walk(
179 system, pageSize, table, vaddr, allocate, entry);
180}
181
182}
183
184
185template <class ...EntryTypes>
187{
188 typedef typename LastType<EntryTypes...>::type Final;
189
194
199
200public:
201 MultiLevelPageTable(const std::string &__name, uint64_t _pid,
202 System *_sys, Addr _pageSize) :
203 EmulationPageTable(__name, _pid, _pageSize), system(_sys)
204 {}
205
207
208 void
209 initState() override
210 {
211 if (shared)
212 return;
213
214 _basePtr = prepTopTable<EntryTypes...>(system, _pageSize);
215 }
216
217 Addr basePtr() { return _basePtr; }
218
219 void
220 map(Addr vaddr, Addr paddr, int64_t size, uint64_t flags = 0) override
221 {
222 EmulationPageTable::map(vaddr, paddr, size, flags);
223
224 Final entry;
225
226 for (int64_t offset = 0; offset < size; offset += _pageSize) {
227 walk<EntryTypes...>(system, _pageSize, _basePtr,
228 vaddr + offset, true, &entry);
229
230 entry.reset(paddr + offset, true, flags & Uncacheable,
231 flags & ReadOnly);
232 entry.write(system->physProxy);
233
234 DPRINTF(MMU, "New mapping: %#x-%#x\n",
235 vaddr + offset, paddr + offset);
236 }
237 }
238
239 void
240 remap(Addr vaddr, int64_t size, Addr new_vaddr) override
241 {
242 EmulationPageTable::remap(vaddr, size, new_vaddr);
243
244 Final old_entry, new_entry;
245
246 for (int64_t offset = 0; offset < size; offset += _pageSize) {
247 // Unmap the original mapping.
248 walk<EntryTypes...>(system, _pageSize, _basePtr, vaddr + offset,
249 false, &old_entry);
250 old_entry.present(false);
251 old_entry.write(system->physProxy);
252
253 // Map the new one.
254 walk<EntryTypes...>(system, _pageSize, _basePtr,
255 new_vaddr + offset, true, &new_entry);
256 new_entry.reset(old_entry.paddr(), true, old_entry.uncacheable(),
257 old_entry.readonly());
258 new_entry.write(system->physProxy);
259 }
260 }
261
262 void
263 unmap(Addr vaddr, int64_t size) override
264 {
266
267 Final entry;
268
269 for (int64_t offset = 0; offset < size; offset += _pageSize) {
270 walk<EntryTypes...>(system, _pageSize, _basePtr,
271 vaddr + offset, false, &entry);
272 fatal_if(!entry.present(),
273 "PageTable::unmap: Address %#x not mapped.", vaddr);
274 entry.present(false);
275 entry.write(system->physProxy);
276 DPRINTF(MMU, "Unmapping: %#x\n", vaddr);
277 }
278 }
279
280 void
281 serialize(CheckpointOut &cp) const override
282 {
288 paramOut(cp, "ptable.pointer", _basePtr);
289 }
290
291 void
293 {
295 paramIn(cp, "ptable.pointer", _basePtr);
296 }
297};
298
299} // namespace gem5
300
301#endif // __MEM_MULTI_LEVEL_PAGE_TABLE_HH__
#define DPRINTF(x,...)
Definition trace.hh:210
Defines global host-dependent types: Counter, Tick, and (indirectly) {int,uint}{8,...
virtual void map(Addr vaddr, Addr paddr, int64_t size, uint64_t flags=0)
Maps a virtual memory region to a physical memory region.
Definition page_table.cc:48
virtual void remap(Addr vaddr, int64_t size, Addr new_vaddr)
Definition page_table.cc:75
void serialize(CheckpointOut &cp) const override
Serialize an object.
virtual void unmap(Addr vaddr, int64_t size)
void unserialize(CheckpointIn &cp) override
Unserialize an object.
void unserialize(CheckpointIn &cp) override
Unserialize an object.
Addr _basePtr
Physical address to the last level of the page table.
void serialize(CheckpointOut &cp) const override
Serialize an object.
MultiLevelPageTable(const std::string &__name, uint64_t _pid, System *_sys, Addr _pageSize)
LastType< EntryTypes... >::type Final
void unmap(Addr vaddr, int64_t size) override
void remap(Addr vaddr, int64_t size, Addr new_vaddr) override
void map(Addr vaddr, Addr paddr, int64_t size, uint64_t flags=0) override
Maps a virtual memory region to a physical memory region.
System * system
Pointer to System object.
PortProxy physProxy
Port to physical memory used for writing object files into ram at boot.
Definition system.hh:323
#define fatal_if(cond,...)
Conditional fatal macro that checks the supplied condition and only causes a fatal error if the condi...
Definition logging.hh:236
uint8_t flags
Definition helpers.cc:87
Bitfield< 23, 0 > offset
Definition types.hh:144
Bitfield< 0 > p
Bitfield< 15 > system
Definition misc.hh:1032
Bitfield< 3 > addr
Definition types.hh:84
Copyright (c) 2024 - Pranith Kumar Copyright (c) 2020 Inria All rights reserved.
Definition binary32.hh:36
std::ostream CheckpointOut
Definition serialize.hh:66
uint64_t Addr
Address type This will probably be moved somewhere else in the near future.
Definition types.hh:147
void paramOut(CheckpointOut &cp, const std::string &name, ExtMachInst const &machInst)
Definition types.cc:40
void paramIn(CheckpointIn &cp, const std::string &name, ExtMachInst &machInst)
Definition types.cc:72
Declarations of a non-full system Page Table.

Generated on Tue Jun 18 2024 16:24:05 for gem5 by doxygen 1.11.0