blob: ec284908ed726e898abcfb44190d7a3fe1cf20e3 (
plain)
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
|
#include "KingSystem/Resource/resOffsetReadFileDevice.h"
#include <heap/seadHeapMgr.h>
#include <math/seadMathCalcCommon.h>
#include "KingSystem/Resource/resSystem.h"
namespace ksys::res {
OffsetReadFileDevice::OffsetReadFileDevice(sead::Heap* heap) : sead::MainFileDevice(heap) {
resetOffsetRead();
}
void OffsetReadFileDevice::setFileDevice(sead::FileDevice* device) {
OffsetRead::setFileDevice(device);
}
/// This is a modified version of `sead::FileDevice::doLoad_`.
u8* OffsetReadFileDevice::doLoad_(sead::FileDevice::LoadArg& arg) {
if (arg.buffer && arg.buffer_size == 0) {
stubbedLogFunction();
return nullptr;
}
sead::FileDevice* device = mOffsetReadFileDevice;
if (!device)
device = this;
sead::FileHandle handle;
if (!device->tryOpen(&handle, arg.path, FileDevice::cFileOpenFlag_ReadOnly, arg.div_size))
return nullptr;
u32 bytesToRead = arg.buffer_size;
if (!arg.buffer || arg.check_read_entire_file) {
u32 fileSize = 0;
if (!device->tryGetFileSize(&fileSize, &handle))
return nullptr;
if (fileSize == 0) {
stubbedLogFunction();
return nullptr;
}
if (bytesToRead != 0) {
if (bytesToRead < fileSize) {
stubbedLogFunction();
return nullptr;
}
} else {
bytesToRead = mOffsetReadOffset +
sead::Mathi::roundUpPow2(fileSize, FileDevice::cBufferMinAlignment);
}
}
u8* buf = arg.buffer;
bool allocated = false;
if (buf == nullptr) {
const s32 sign = (arg.alignment < 0) ? -1 : 1;
s32 alignment = sead::Mathi::abs(arg.alignment);
alignment = sign * ((alignment < cBufferMinAlignment) ? cBufferMinAlignment : alignment);
sead::Heap* heap = arg.heap;
if (!heap)
heap = sead::HeapMgr::instance()->getCurrentHeap();
void* raw_buf = heap->tryAlloc(bytesToRead, alignment);
if (!raw_buf)
return nullptr;
buf = new (raw_buf) u8[bytesToRead];
allocated = true;
}
u32 bytesRead = 0;
if (!device->tryRead(&bytesRead, &handle, buf + mOffsetReadOffset,
bytesToRead - mOffsetReadOffset)) {
if (allocated)
delete[] buf;
return nullptr;
}
if (!device->tryClose(&handle)) {
if (allocated)
delete[] buf;
return nullptr;
}
arg.read_size = bytesRead;
arg.roundup_size = bytesToRead;
arg.need_unload = allocated;
return buf;
}
} // namespace ksys::res
|