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
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
|
/* SCE CONFIDENTIAL
PlayStation(R)4 Programmer Tool Runtime Library Release 01.600.051
* Copyright (C) 2013 Sony Computer Entertainment Inc.
* All Rights Reserved.
*/
extern "C"
{
#include <stdlib.h>
#include <mspace.h>
#include <kernel.h>
#include "..\Minecraft.World\System.h"
static size_t s_heapLength;
static size_t s_memLength;
static SceLibcMspace s_mspace;
static off_t s_memStart;
static size_t s_memAlign = 2 * 1024 * 1024;
int user_malloc_init(void);
int user_malloc_finalize(void);
void *user_malloc(size_t size);
void user_free(void *ptr);
void *user_calloc(size_t nelem, size_t size);
void *user_realloc(void *ptr, size_t size);
void *user_memalign(size_t boundary, size_t size);
int user_posix_memalign(void **ptr, size_t boundary, size_t size);
void *user_reallocalign(void *ptr, size_t size, size_t boundary);
int user_malloc_stats(SceLibcMallocManagedSize *mmsize);
int user_malloc_stats_fast(SceLibcMallocManagedSize *mmsize);
size_t user_malloc_usable_size(void *ptr);
//E Replace _malloc_init function.
int user_malloc_init(void)
{
int res;
void *addr;
uint64_t dmemSize = SCE_KERNEL_MAIN_DMEM_SIZE;
s_heapLength = ((size_t)4608) * 1024 * 1024; // Initial allocation for the application
s_heapLength -= ((size_t)4) * 1024 * 1024; // Allocated for TLS
s_heapLength -= ((size_t)2) * 1024 * 1024; // 64K (sometimes?) allocated for razor - rounding up to 2MB here to match our alignment
s_heapLength -= ((size_t)24) * 1024 * 1024; // 24MB for save file, which is handled by virtual allocs
s_heapLength -= ((size_t)512) * 1024 * 1024; // 512MB allocated for GPU by renderer
s_heapLength -= ((size_t)112) * 1024 * 1024; // 112MB allocated for CPU by renderer
s_memLength = s_heapLength;
//E Allocate direct memory
res = sceKernelAllocateDirectMemory(0, SCE_KERNEL_MAIN_DMEM_SIZE, s_memLength, s_memAlign, SCE_KERNEL_WB_ONION, &s_memStart);
if (res < 0) {
//E Error handling
return 1;
}
addr = NULL;
//E Map direct memory to the process address space
res = sceKernelMapDirectMemory(&addr, s_heapLength, SCE_KERNEL_PROT_CPU_READ | SCE_KERNEL_PROT_CPU_WRITE, 0, s_memStart, s_memAlign);
if (res < 0) {
//E Error handling
return 1;
}
//E Generate mspace
s_mspace = sceLibcMspaceCreate("User Malloc", addr, s_heapLength, 0);
if (s_mspace == NULL) {
//E Error handling
return 1;
}
return 0;
}
//E Replace _malloc_finalize function.
int user_malloc_finalize(void)
{
int res;
if (s_mspace != NULL) {
//E Free mspace
//J mspace を解放する
res = sceLibcMspaceDestroy(s_mspace);
if (res != 0) {
//E Error handling
//J エラー処理
return 1;
}
}
//E Release direct memory
//J ダイレクトメモリを解放する
res = sceKernelReleaseDirectMemory(s_memStart, s_memLength);
if (res < 0) {
//E Error handling
//J エラー処理
return 1;
}
return 0;
}
//E Replace malloc function.
//J malloc 関数と置き換わる
void *user_malloc(size_t size)
{
#if 0
static int throttle = 0;
static int64_t lasttime = 0;
if( ( throttle % 100 ) == 0 )
{
int64_t nowtime = System::currentTimeMillis();
if( ( nowtime - lasttime ) > 20000 )
{
lasttime = nowtime;
SceLibcMallocManagedSize mmsize;
SCE_LIBC_INIT_MALLOC_MANAGED_SIZE(mmsize);
int ret = sceLibcMspaceMallocStats( s_mspace, &mmsize);
printf("%d max %d of %d\n",mmsize.currentInuseSize/(1024*1024),mmsize.maxInuseSize/(1024*1024),mmsize.currentSystemSize/(1024*1024));
}
}
throttle++;
#endif
return sceLibcMspaceMalloc(s_mspace, size);
}
//E Replace free function.
//J free 関数と置き換わる
void user_free(void *ptr)
{
sceLibcMspaceFree(s_mspace, ptr);
}
//E Replace calloc function.
//J calloc 関数と置き換わる
void *user_calloc(size_t nelem, size_t size)
{
return sceLibcMspaceCalloc(s_mspace, nelem, size);
}
//E Replace realloc function.
//J realloc 関数と置き換わる
void *user_realloc(void *ptr, size_t size)
{
return sceLibcMspaceRealloc(s_mspace, ptr, size);
}
//E Replace memalign function.
//J memalign 関数と置き換わる
void *user_memalign(size_t boundary, size_t size)
{
return sceLibcMspaceMemalign(s_mspace, boundary, size);
}
//E Replace posix_memalign function.
//J posix_memalign 関数と置き換わる
int user_posix_memalign(void **ptr, size_t boundary, size_t size)
{
return sceLibcMspacePosixMemalign(s_mspace, ptr, boundary, size);
}
//E Replace reallocalign function.
//J reallocalign 関数と置き換わる
void *user_reallocalign(void *ptr, size_t size, size_t boundary)
{
return sceLibcMspaceReallocalign(s_mspace, ptr, boundary, size);
}
//E Replace malloc_stats function.
//J malloc_stats 関数と置き換わる
int user_malloc_stats(SceLibcMallocManagedSize *mmsize)
{
return sceLibcMspaceMallocStats(s_mspace, mmsize);
}
//E Replace malloc_stats_fast function.
//J malloc_stata_fast 関数と置き換わる
int user_malloc_stats_fast(SceLibcMallocManagedSize *mmsize)
{
return sceLibcMspaceMallocStatsFast(s_mspace, mmsize);
}
//E Replace malloc_usable_size function.
//J malloc_usable_size 関数と置き換わる
size_t user_malloc_usable_size(void *ptr)
{
return sceLibcMspaceMallocUsableSize(ptr);
}
} // extern "c"
|