summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to '')
-rw-r--r--src/common/CMakeLists.txt2
-rw-r--r--src/common/mem_arena.cpp394
-rw-r--r--src/common/mem_arena.h70
-rw-r--r--src/core/mem_map.cpp113
-rw-r--r--src/core/mem_map.h12
5 files changed, 31 insertions, 560 deletions
diff --git a/src/common/CMakeLists.txt b/src/common/CMakeLists.txt
index b5b129a09..11659c3c5 100644
--- a/src/common/CMakeLists.txt
+++ b/src/common/CMakeLists.txt
@@ -10,7 +10,6 @@ set(SRCS
10 logging/text_formatter.cpp 10 logging/text_formatter.cpp
11 logging/backend.cpp 11 logging/backend.cpp
12 math_util.cpp 12 math_util.cpp
13 mem_arena.cpp
14 memory_util.cpp 13 memory_util.cpp
15 misc.cpp 14 misc.cpp
16 profiler.cpp 15 profiler.cpp
@@ -43,7 +42,6 @@ set(HEADERS
43 logging/backend.h 42 logging/backend.h
44 make_unique.h 43 make_unique.h
45 math_util.h 44 math_util.h
46 mem_arena.h
47 memory_util.h 45 memory_util.h
48 platform.h 46 platform.h
49 profiler.h 47 profiler.h
diff --git a/src/common/mem_arena.cpp b/src/common/mem_arena.cpp
deleted file mode 100644
index 689fdb92b..000000000
--- a/src/common/mem_arena.cpp
+++ /dev/null
@@ -1,394 +0,0 @@
1// Copyright (C) 2003 Dolphin Project.
2
3// This program is free software: you can redistribute it and/or modify
4// it under the terms of the GNU General Public License as published by
5// the Free Software Foundation, version 2.0 or later versions.
6
7// This program is distributed in the hope that it will be useful,
8// but WITHOUT ANY WARRANTY; without even the implied warranty of
9// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10// GNU General Public License 2.0 for more details.
11
12// A copy of the GPL 2.0 should have been included with the program.
13// If not, see http://www.gnu.org/licenses/
14
15// Official SVN repository and contact information can be found at
16// http://code.google.com/p/dolphin-emu/
17
18#include <string>
19
20#include "common/logging/log.h"
21#include "common/mem_arena.h"
22#include "common/memory_util.h"
23#include "common/platform.h"
24#include "common/string_util.h"
25
26#ifndef _WIN32
27#include <fcntl.h>
28#include <string.h>
29#include <unistd.h>
30
31#ifdef ANDROID
32#include <sys/ioctl.h>
33#include <linux/ashmem.h>
34#endif
35#endif
36
37#ifdef ANDROID
38
39// Hopefully this ABI will never change...
40
41
42#define ASHMEM_DEVICE "/dev/ashmem"
43
44/*
45* ashmem_create_region - creates a new ashmem region and returns the file
46* descriptor, or <0 on error
47*
48* `name' is an optional label to give the region (visible in /proc/pid/maps)
49* `size' is the size of the region, in page-aligned bytes
50*/
51int ashmem_create_region(const char *name, size_t size)
52{
53 int fd, ret;
54
55 fd = open(ASHMEM_DEVICE, O_RDWR);
56 if (fd < 0)
57 return fd;
58
59 if (name) {
60 char buf[ASHMEM_NAME_LEN];
61
62 strncpy(buf, name, sizeof(buf));
63 ret = ioctl(fd, ASHMEM_SET_NAME, buf);
64 if (ret < 0)
65 goto error;
66 }
67
68 ret = ioctl(fd, ASHMEM_SET_SIZE, size);
69 if (ret < 0)
70 goto error;
71
72 return fd;
73
74error:
75 LOG_ERROR(Common_Memory, "NASTY ASHMEM ERROR: ret = %08x", ret);
76 close(fd);
77 return ret;
78}
79
80int ashmem_set_prot_region(int fd, int prot)
81{
82 return ioctl(fd, ASHMEM_SET_PROT_MASK, prot);
83}
84
85int ashmem_pin_region(int fd, size_t offset, size_t len)
86{
87 struct ashmem_pin pin = { offset, len };
88 return ioctl(fd, ASHMEM_PIN, &pin);
89}
90
91int ashmem_unpin_region(int fd, size_t offset, size_t len)
92{
93 struct ashmem_pin pin = { offset, len };
94 return ioctl(fd, ASHMEM_UNPIN, &pin);
95}
96#endif // Android
97
98
99#if defined(_WIN32)
100SYSTEM_INFO sysInfo;
101#endif
102
103
104// Windows mappings need to be on 64K boundaries, due to Alpha legacy.
105#ifdef _WIN32
106size_t roundup(size_t x) {
107 int gran = sysInfo.dwAllocationGranularity ? sysInfo.dwAllocationGranularity : 0x10000;
108 return (x + gran - 1) & ~(gran - 1);
109}
110#else
111size_t roundup(size_t x) {
112 return x;
113}
114#endif
115
116
117void MemArena::GrabLowMemSpace(size_t size)
118{
119#ifdef _WIN32
120 hMemoryMapping = CreateFileMapping(INVALID_HANDLE_VALUE, nullptr, PAGE_READWRITE, 0, (DWORD)(size), nullptr);
121 GetSystemInfo(&sysInfo);
122#elif defined(ANDROID)
123 // Use ashmem so we don't have to allocate a file on disk!
124 fd = ashmem_create_region("Citra_RAM", size);
125 // Note that it appears that ashmem is pinned by default, so no need to pin.
126 if (fd < 0)
127 {
128 LOG_ERROR(Common_Memory, "Failed to grab ashmem space of size: %08x errno: %d", (int)size, (int)(errno));
129 return;
130 }
131#else
132 // Try to find a non-existing filename for our shared memory.
133 // In most cases the first one will be available, but it's nicer to search
134 // a bit more.
135 for (int i = 0; i < 10000; i++)
136 {
137 std::string file_name = Common::StringFromFormat("/citramem.%d", i);
138 fd = shm_open(file_name.c_str(), O_RDWR | O_CREAT | O_EXCL, 0600);
139 if (fd != -1)
140 {
141 shm_unlink(file_name.c_str());
142 break;
143 }
144 else if (errno != EEXIST)
145 {
146 LOG_ERROR(Common_Memory, "shm_open failed: %s", strerror(errno));
147 return;
148 }
149 }
150 if (ftruncate(fd, size) < 0)
151 LOG_ERROR(Common_Memory, "Failed to allocate low memory space");
152#endif
153}
154
155
156void MemArena::ReleaseSpace()
157{
158#ifdef _WIN32
159 CloseHandle(hMemoryMapping);
160 hMemoryMapping = 0;
161#else
162 close(fd);
163#endif
164}
165
166
167void *MemArena::CreateView(s64 offset, size_t size, void *base)
168{
169#ifdef _WIN32
170 size = roundup(size);
171 void *ptr = MapViewOfFileEx(hMemoryMapping, FILE_MAP_ALL_ACCESS, 0, (DWORD)((u64)offset), size, base);
172 return ptr;
173#else
174 void *retval = mmap(base, size, PROT_READ | PROT_WRITE, MAP_SHARED |
175 // Do not sync memory to underlying file. Linux has this by default.
176#ifdef __FreeBSD__
177 MAP_NOSYNC |
178#endif
179 ((base == nullptr) ? 0 : MAP_FIXED), fd, offset);
180
181 if (retval == MAP_FAILED)
182 {
183 LOG_ERROR(Common_Memory, "mmap failed");
184 return nullptr;
185 }
186 return retval;
187#endif
188}
189
190
191void MemArena::ReleaseView(void* view, size_t size)
192{
193#ifdef _WIN32
194 UnmapViewOfFile(view);
195#else
196 munmap(view, size);
197#endif
198}
199
200u8* MemArena::Find4GBBase()
201{
202#if EMU_ARCH_BITS == 64
203#ifdef _WIN32
204 // 64 bit
205 u8* base = (u8*)VirtualAlloc(0, 0xE1000000, MEM_RESERVE, PAGE_READWRITE);
206 VirtualFree(base, 0, MEM_RELEASE);
207 return base;
208#else
209 // Very precarious - mmap cannot return an error when trying to map already used pages.
210 // This makes the Windows approach above unusable on Linux, so we will simply pray...
211 return reinterpret_cast<u8*>(0x2300000000ULL);
212#endif
213
214#else // 32 bit
215
216#ifdef _WIN32
217 u8* base = (u8*)VirtualAlloc(0, 0x10000000, MEM_RESERVE, PAGE_READWRITE);
218 if (base) {
219 VirtualFree(base, 0, MEM_RELEASE);
220 }
221 return base;
222#else
223 void* base = mmap(0, 0x10000000, PROT_READ | PROT_WRITE,
224 MAP_ANON | MAP_SHARED, -1, 0);
225 if (base == MAP_FAILED) {
226 LOG_ERROR(Common_Memory, "Failed to map 256 MB of memory space: %s", strerror(errno));
227 return 0;
228 }
229 munmap(base, 0x10000000);
230 return static_cast<u8*>(base);
231#endif
232#endif
233}
234
235
236// yeah, this could also be done in like two bitwise ops...
237#define SKIP(a_flags, b_flags)
238//if (!(a_flags & MV_WII_ONLY) && (b_flags & MV_WII_ONLY))
239// continue;
240//if (!(a_flags & MV_FAKE_VMEM) && (b_flags & MV_FAKE_VMEM))
241// continue;
242
243static bool Memory_TryBase(u8 *base, const MemoryView *views, int num_views, u32 flags, MemArena *arena) {
244 // OK, we know where to find free space. Now grab it!
245 // We just mimic the popular BAT setup.
246 size_t position = 0;
247 size_t last_position = 0;
248
249 // Zero all the pointers to be sure.
250 for (int i = 0; i < num_views; i++)
251 {
252 if (views[i].out_ptr_low)
253 *views[i].out_ptr_low = 0;
254 if (views[i].out_ptr)
255 *views[i].out_ptr = 0;
256 }
257
258 int i;
259 for (i = 0; i < num_views; i++)
260 {
261 const MemoryView &view = views[i];
262 if (view.size == 0)
263 continue;
264 SKIP(flags, view.flags);
265 if (view.flags & MV_MIRROR_PREVIOUS) {
266 position = last_position;
267 }
268 else {
269 *(view.out_ptr_low) = (u8*)arena->CreateView(position, view.size);
270 if (!*view.out_ptr_low)
271 goto bail;
272 }
273#if EMU_ARCH_BITS == 64
274 *view.out_ptr = (u8*)arena->CreateView(
275 position, view.size, base + view.virtual_address);
276#else
277 if (view.flags & MV_MIRROR_PREVIOUS) { // TODO: should check if the two & 0x3FFFFFFF are identical.
278 // No need to create multiple identical views.
279 *view.out_ptr = *views[i - 1].out_ptr;
280 }
281 else {
282 *view.out_ptr = (u8*)arena->CreateView(
283 position, view.size, base + (view.virtual_address & 0x3FFFFFFF));
284 if (!*view.out_ptr)
285 goto bail;
286 }
287#endif
288
289 last_position = position;
290 position += roundup(view.size);
291 }
292
293 return true;
294
295bail:
296 // Argh! ERROR! Free what we grabbed so far so we can try again.
297 for (int j = 0; j <= i; j++)
298 {
299 if (views[i].size == 0)
300 continue;
301 SKIP(flags, views[i].flags);
302 if (views[j].out_ptr_low && *views[j].out_ptr_low)
303 {
304 arena->ReleaseView(*views[j].out_ptr_low, views[j].size);
305 *views[j].out_ptr_low = nullptr;
306 }
307 if (*views[j].out_ptr)
308 {
309#if EMU_ARCH_BITS == 64
310 arena->ReleaseView(*views[j].out_ptr, views[j].size);
311#else
312 if (!(views[j].flags & MV_MIRROR_PREVIOUS))
313 {
314 arena->ReleaseView(*views[j].out_ptr, views[j].size);
315 }
316#endif
317 *views[j].out_ptr = nullptr;
318 }
319 }
320 return false;
321}
322
323u8 *MemoryMap_Setup(const MemoryView *views, int num_views, u32 flags, MemArena *arena)
324{
325 size_t total_mem = 0;
326 int base_attempts = 0;
327
328 for (int i = 0; i < num_views; i++)
329 {
330 if (views[i].size == 0)
331 continue;
332 SKIP(flags, views[i].flags);
333 if ((views[i].flags & MV_MIRROR_PREVIOUS) == 0)
334 total_mem += roundup(views[i].size);
335 }
336 // Grab some pagefile backed memory out of the void ...
337 arena->GrabLowMemSpace(total_mem);
338
339 // Now, create views in high memory where there's plenty of space.
340#if EMU_ARCH_BITS == 64
341 u8 *base = MemArena::Find4GBBase();
342 // This really shouldn't fail - in 64-bit, there will always be enough
343 // address space.
344 if (!Memory_TryBase(base, views, num_views, flags, arena))
345 {
346 LOG_ERROR(Common_Memory, "MemoryMap_Setup: Failed finding a memory base.");
347 return 0;
348 }
349#elif defined(_WIN32)
350 // Try a whole range of possible bases. Return once we got a valid one.
351 u32 max_base_addr = 0x7FFF0000 - 0x10000000;
352 u8 *base = nullptr;
353
354 for (u32 base_addr = 0x01000000; base_addr < max_base_addr; base_addr += 0x400000)
355 {
356 base_attempts++;
357 base = (u8 *)base_addr;
358 if (Memory_TryBase(base, views, num_views, flags, arena))
359 {
360 LOG_DEBUG(Common_Memory, "Found valid memory base at %p after %i tries.", base, base_attempts);
361 base_attempts = 0;
362 break;
363 }
364 }
365#else
366 // Linux32 is fine with the x64 method, although limited to 32-bit with no automirrors.
367 u8 *base = MemArena::Find4GBBase();
368 if (!Memory_TryBase(base, views, num_views, flags, arena))
369 {
370 LOG_ERROR(Common_Memory, "MemoryMap_Setup: Failed finding a memory base.");
371 return 0;
372 }
373#endif
374 if (base_attempts)
375 LOG_ERROR(Common_Memory, "No possible memory base pointer found!");
376 return base;
377}
378
379void MemoryMap_Shutdown(const MemoryView *views, int num_views, u32 flags, MemArena *arena)
380{
381 for (int i = 0; i < num_views; i++)
382 {
383 if (views[i].size == 0)
384 continue;
385 SKIP(flags, views[i].flags);
386 if (views[i].out_ptr_low && *views[i].out_ptr_low)
387 arena->ReleaseView(*views[i].out_ptr_low, views[i].size);
388 if (*views[i].out_ptr && (views[i].out_ptr_low && *views[i].out_ptr != *views[i].out_ptr_low))
389 arena->ReleaseView(*views[i].out_ptr, views[i].size);
390 *views[i].out_ptr = nullptr;
391 if (views[i].out_ptr_low)
392 *views[i].out_ptr_low = nullptr;
393 }
394}
diff --git a/src/common/mem_arena.h b/src/common/mem_arena.h
deleted file mode 100644
index d514fe58c..000000000
--- a/src/common/mem_arena.h
+++ /dev/null
@@ -1,70 +0,0 @@
1// Copyright (C) 2003 Dolphin Project.
2
3// This program is free software: you can redistribute it and/or modify
4// it under the terms of the GNU General Public License as published by
5// the Free Software Foundation, version 2.0 or later versions.
6
7// This program is distributed in the hope that it will be useful,
8// but WITHOUT ANY WARRANTY; without even the implied warranty of
9// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10// GNU General Public License 2.0 for more details.
11
12// A copy of the GPL 2.0 should have been included with the program.
13// If not, see http://www.gnu.org/licenses/
14
15// Official SVN repository and contact information can be found at
16// http://code.google.com/p/dolphin-emu/
17
18#pragma once
19
20#ifdef _WIN32
21#include <windows.h>
22#endif
23
24#include "common/common_types.h"
25
26// This class lets you create a block of anonymous RAM, and then arbitrarily map views into it.
27// Multiple views can mirror the same section of the block, which makes it very convient for emulating
28// memory mirrors.
29
30class MemArena
31{
32public:
33 void GrabLowMemSpace(size_t size);
34 void ReleaseSpace();
35 void *CreateView(s64 offset, size_t size, void *base = 0);
36 void ReleaseView(void *view, size_t size);
37
38 // This only finds 1 GB in 32-bit
39 static u8 *Find4GBBase();
40private:
41
42#ifdef _WIN32
43 HANDLE hMemoryMapping;
44#else
45 int fd;
46#endif
47};
48
49enum {
50 MV_MIRROR_PREVIOUS = 1,
51 // MV_FAKE_VMEM = 2,
52 // MV_WII_ONLY = 4,
53 MV_IS_PRIMARY_RAM = 0x100,
54 MV_IS_EXTRA1_RAM = 0x200,
55 MV_IS_EXTRA2_RAM = 0x400,
56};
57
58struct MemoryView
59{
60 u8 **out_ptr_low;
61 u8 **out_ptr;
62 u32 virtual_address;
63 u32 size;
64 u32 flags;
65};
66
67// Uses a memory arena to set up an emulator-friendly memory map according to
68// a passed-in list of MemoryView structures.
69u8 *MemoryMap_Setup(const MemoryView *views, int num_views, u32 flags, MemArena *arena);
70void MemoryMap_Shutdown(const MemoryView *views, int num_views, u32 flags, MemArena *arena);
diff --git a/src/core/mem_map.cpp b/src/core/mem_map.cpp
index ae88cfb11..46e271c80 100644
--- a/src/core/mem_map.cpp
+++ b/src/core/mem_map.cpp
@@ -2,10 +2,8 @@
2// Licensed under GPLv2 or any later version 2// Licensed under GPLv2 or any later version
3// Refer to the license.txt file included. 3// Refer to the license.txt file included.
4 4
5#include "common/common_funcs.h"
6#include "common/common_types.h" 5#include "common/common_types.h"
7#include "common/logging/log.h" 6#include "common/logging/log.h"
8#include "common/mem_arena.h"
9 7
10#include "core/mem_map.h" 8#include "core/mem_map.h"
11 9
@@ -13,100 +11,51 @@
13 11
14namespace Memory { 12namespace Memory {
15 13
16u8* g_base; ///< The base pointer to the auto-mirrored arena. 14u8* g_exefs_code; ///< ExeFS:/.code is loaded here
15u8* g_system_mem; ///< System memory
16u8* g_heap; ///< Application heap (main memory)
17u8* g_heap_linear; ///< Linear heap
18u8* g_vram; ///< Video memory (VRAM) pointer
19u8* g_shared_mem; ///< Shared memory
20u8* g_dsp_mem; ///< DSP memory
21u8* g_kernel_mem; ///< Kernel memory
17 22
18static MemArena arena; ///< The MemArena class 23namespace {
19 24
20u8* g_exefs_code; ///< ExeFS:/.code is loaded here 25struct MemoryArea {
21u8* g_system_mem; ///< System memory 26 u8** ptr;
22u8* g_heap; ///< Application heap (main memory) 27 size_t size;
23u8* g_heap_linear; ///< Linear heap
24u8* g_vram; ///< Video memory (VRAM) pointer
25u8* g_shared_mem; ///< Shared memory
26u8* g_dsp_mem; ///< DSP memory
27u8* g_kernel_mem; ///< Kernel memory
28
29static u8* physical_bootrom; ///< Bootrom physical memory
30static u8* uncached_bootrom;
31
32static u8* physical_exefs_code; ///< Phsical ExeFS:/.code is loaded here
33static u8* physical_system_mem; ///< System physical memory
34static u8* physical_fcram; ///< Main physical memory (FCRAM)
35static u8* physical_heap_gsp; ///< GSP heap physical memory
36static u8* physical_vram; ///< Video physical memory (VRAM)
37static u8* physical_shared_mem; ///< Physical shared memory
38static u8* physical_dsp_mem; ///< Physical DSP memory
39static u8* physical_kernel_mem; ///< Kernel memory
40
41// We don't declare the IO region in here since its handled by other means.
42static MemoryView g_views[] = {
43 {&g_exefs_code, &physical_exefs_code, EXEFS_CODE_VADDR, EXEFS_CODE_SIZE, 0},
44 {&g_vram, &physical_vram, VRAM_VADDR, VRAM_SIZE, 0},
45 {&g_heap, &physical_fcram, HEAP_VADDR, HEAP_SIZE, MV_IS_PRIMARY_RAM},
46 {&g_shared_mem, &physical_shared_mem, SHARED_MEMORY_VADDR, SHARED_MEMORY_SIZE, 0},
47 {&g_system_mem, &physical_system_mem, SYSTEM_MEMORY_VADDR, SYSTEM_MEMORY_SIZE, 0},
48 {&g_dsp_mem, &physical_dsp_mem, DSP_MEMORY_VADDR, DSP_MEMORY_SIZE, 0},
49 {&g_kernel_mem, &physical_kernel_mem, KERNEL_MEMORY_VADDR, KERNEL_MEMORY_SIZE, 0},
50 {&g_heap_linear, &physical_heap_gsp, HEAP_LINEAR_VADDR, HEAP_LINEAR_SIZE, 0},
51}; 28};
52 29
53/*static MemoryView views[] = 30// We don't declare the IO regions in here since its handled by other means.
54{ 31static MemoryArea memory_areas[] = {
55 {&m_pScratchPad, &m_pPhysicalScratchPad, 0x00010000, SCRATCHPAD_SIZE, 0}, 32 {&g_exefs_code, EXEFS_CODE_SIZE },
56 {NULL, &m_pUncachedScratchPad, 0x40010000, SCRATCHPAD_SIZE, MV_MIRROR_PREVIOUS}, 33 {&g_vram, VRAM_SIZE },
57 {&m_pVRAM, &m_pPhysicalVRAM, 0x04000000, 0x00800000, 0}, 34 {&g_heap, HEAP_SIZE },
58 {NULL, &m_pUncachedVRAM, 0x44000000, 0x00800000, MV_MIRROR_PREVIOUS}, 35 {&g_shared_mem, SHARED_MEMORY_SIZE},
59 {&m_pRAM, &m_pPhysicalRAM, 0x08000000, g_MemorySize, MV_IS_PRIMARY_RAM}, // only from 0x08800000 is it usable (last 24 megs) 36 {&g_system_mem, SYSTEM_MEMORY_SIZE},
60 {NULL, &m_pUncachedRAM, 0x48000000, g_MemorySize, MV_MIRROR_PREVIOUS | MV_IS_PRIMARY_RAM}, 37 {&g_dsp_mem, DSP_MEMORY_SIZE },
61 {NULL, &m_pKernelRAM, 0x88000000, g_MemorySize, MV_MIRROR_PREVIOUS | MV_IS_PRIMARY_RAM}, 38 {&g_kernel_mem, KERNEL_MEMORY_SIZE},
62 39 {&g_heap_linear, HEAP_LINEAR_SIZE },
63 // TODO: There are a few swizzled mirrors of VRAM, not sure about the best way to 40};
64 // implement those.
65};*/
66 41
67static const int kNumMemViews = sizeof(g_views) / sizeof(MemoryView); ///< Number of mem views 42}
68 43
69void Init() { 44void Init() {
70 int flags = 0; 45 for (MemoryArea& area : memory_areas) {
71 46 *area.ptr = new u8[area.size];
72 for (size_t i = 0; i < ARRAY_SIZE(g_views); i++) {
73 if (g_views[i].flags & MV_IS_PRIMARY_RAM)
74 g_views[i].size = FCRAM_SIZE;
75 } 47 }
76
77 g_base = MemoryMap_Setup(g_views, kNumMemViews, flags, &arena);
78 MemBlock_Init(); 48 MemBlock_Init();
79 49
80 LOG_DEBUG(HW_Memory, "initialized OK, RAM at %p (mirror at 0 @ %p)", g_heap, 50 LOG_DEBUG(HW_Memory, "initialized OK, RAM at %p", g_heap);
81 physical_fcram);
82} 51}
83 52
84void Shutdown() { 53void Shutdown() {
85 u32 flags = 0;
86 MemoryMap_Shutdown(g_views, kNumMemViews, flags, &arena);
87 arena.ReleaseSpace();
88 MemBlock_Shutdown(); 54 MemBlock_Shutdown();
89 55 for (MemoryArea& area : memory_areas) {
90 g_base = nullptr; 56 delete[] *area.ptr;
91 g_exefs_code = nullptr; 57 *area.ptr = nullptr;
92 g_system_mem = nullptr; 58 }
93 g_heap = nullptr;
94 g_heap_linear = nullptr;
95 g_vram = nullptr;
96 g_shared_mem = nullptr;
97 g_dsp_mem = nullptr;
98 g_kernel_mem = nullptr;
99
100 physical_bootrom = nullptr;
101 uncached_bootrom = nullptr;
102 physical_exefs_code = nullptr;
103 physical_system_mem = nullptr;
104 physical_fcram = nullptr;
105 physical_heap_gsp = nullptr;
106 physical_vram = nullptr;
107 physical_shared_mem = nullptr;
108 physical_dsp_mem = nullptr;
109 physical_kernel_mem = nullptr;
110 59
111 LOG_DEBUG(HW_Memory, "shutdown OK"); 60 LOG_DEBUG(HW_Memory, "shutdown OK");
112} 61}
diff --git a/src/core/mem_map.h b/src/core/mem_map.h
index b11f2ea68..1fb77c94a 100644
--- a/src/core/mem_map.h
+++ b/src/core/mem_map.h
@@ -105,18 +105,6 @@ struct MemoryBlock {
105 105
106//////////////////////////////////////////////////////////////////////////////////////////////////// 106////////////////////////////////////////////////////////////////////////////////////////////////////
107 107
108// Base is a pointer to the base of the memory map. Yes, some MMU tricks
109// are used to set up a full GC or Wii memory map in process memory. on
110// 32-bit, you have to mask your offsets with 0x3FFFFFFF. This means that
111// some things are mirrored too many times, but eh... it works.
112
113// In 64-bit, this might point to "high memory" (above the 32-bit limit),
114// so be sure to load it into a 64-bit register.
115extern u8 *g_base;
116
117// These are guaranteed to point to "low memory" addresses (sub-32-bit).
118// 64-bit: Pointers to low-mem (sub-0x10000000) mirror
119// 32-bit: Same as the corresponding physical/virtual pointers.
120extern u8* g_heap_linear; ///< Linear heap (main memory) 108extern u8* g_heap_linear; ///< Linear heap (main memory)
121extern u8* g_heap; ///< Application heap (main memory) 109extern u8* g_heap; ///< Application heap (main memory)
122extern u8* g_vram; ///< Video memory (VRAM) 110extern u8* g_vram; ///< Video memory (VRAM)