mirror of
https://github.com/wheremyfoodat/Panda3DS.git
synced 2025-04-06 06:05:40 +12:00
[GSP::GPU] Implement writeHwRegs
This commit is contained in:
parent
a5384095df
commit
99e795c141
4 changed files with 35 additions and 3 deletions
|
@ -15,6 +15,7 @@ class GPUService {
|
|||
// Service commands
|
||||
void acquireRight(u32 messagePointer);
|
||||
void registerInterruptRelayQueue(u32 messagePointer);
|
||||
void writeHwRegs(u32 messagePointer);
|
||||
|
||||
public:
|
||||
GPUService(Memory& mem, u32& currentPID) : mem(mem), currentPID(currentPID) {}
|
||||
|
|
|
@ -45,11 +45,12 @@ std::optional<u32> Memory::loadELF(std::ifstream& file) {
|
|||
Helpers::warn("Rounding ELF segment size to %08X\n", memorySize);
|
||||
}
|
||||
|
||||
// This should also assert that findPaddr doesn't fail
|
||||
u32 fcramAddr = findPaddr(memorySize).value();
|
||||
std::memcpy(&fcram[fcramAddr], data, fileSize);
|
||||
|
||||
// Allocate the segment on the OS side
|
||||
allocateMemory(vaddr, fcramAddr, memorySize, true);
|
||||
allocateMemory(vaddr, fcramAddr, memorySize, true, r, w, x);
|
||||
}
|
||||
|
||||
return static_cast<u32>(reader.get_entry());
|
||||
|
|
|
@ -55,7 +55,7 @@ void Kernel::controlMemory() {
|
|||
|
||||
switch (operation & 0xFF) {
|
||||
case Operation::Commit: {
|
||||
std::optional<u32> address = mem.allocateMemory(addr0, 0, size, linear);
|
||||
std::optional<u32> address = mem.allocateMemory(addr0, 0, size, linear, r, w, x);
|
||||
if (!address.has_value())
|
||||
Helpers::panic("ControlMemory: Failed to allocate memory");
|
||||
|
||||
|
|
|
@ -3,7 +3,8 @@
|
|||
namespace GPUCommands {
|
||||
enum : u32 {
|
||||
AcquireRight = 0x00160042,
|
||||
RegisterInterruptRelayQueue = 0x00130042
|
||||
RegisterInterruptRelayQueue = 0x00130042,
|
||||
WriteHwRegs = 0x00010082
|
||||
};
|
||||
}
|
||||
|
||||
|
@ -23,6 +24,7 @@ void GPUService::handleSyncRequest(u32 messagePointer) {
|
|||
switch (command) {
|
||||
case GPUCommands::AcquireRight: acquireRight(messagePointer); break;
|
||||
case GPUCommands::RegisterInterruptRelayQueue: registerInterruptRelayQueue(messagePointer); break;
|
||||
case GPUCommands::WriteHwRegs: writeHwRegs(messagePointer); break;
|
||||
; default: Helpers::panic("GPU service requested. Command: %08X\n", command);
|
||||
}
|
||||
}
|
||||
|
@ -57,4 +59,32 @@ void GPUService::registerInterruptRelayQueue(u32 messagePointer) {
|
|||
mem.write32(messagePointer + 8, 0); // TODO: GSP module thread index
|
||||
mem.write32(messagePointer + 12, 0); // Translation descriptor
|
||||
mem.write32(messagePointer + 16, 0); // TODO: shared memory handle
|
||||
}
|
||||
|
||||
void GPUService::writeHwRegs(u32 messagePointer) {
|
||||
u32 ioAddr = mem.read32(messagePointer + 4); // GPU address based at 0x1EB00000, word aligned
|
||||
const u32 size = mem.read32(messagePointer + 8); // Size in bytes
|
||||
u32 dataPointer = mem.read32(messagePointer + 16);
|
||||
printf("GSP::GPU::writeHwRegs (GPU address = %08X, size = %X, data address = %08X)\n", ioAddr, size, dataPointer);
|
||||
|
||||
// Check for alignment
|
||||
if ((size & 3) || (ioAddr & 3)) {
|
||||
Helpers::panic("GSP::GPU::writeHwRegs misalignment");
|
||||
}
|
||||
|
||||
if (size > 0x80) {
|
||||
Helpers::panic("GSP::GPU::writeHwRegs size too big");
|
||||
}
|
||||
|
||||
if (ioAddr >= 0x420000) {
|
||||
Helpers::panic("GSP::GPU::writeHwRegs offset too big");
|
||||
}
|
||||
|
||||
for (u32 i = 0; i < size; i += 4) {
|
||||
const u32 value = mem.read32(dataPointer);
|
||||
printf("GSP::GPU: Wrote %08X to GPU register %X\n", value, ioAddr);
|
||||
dataPointer += 4;
|
||||
ioAddr += 4;
|
||||
}
|
||||
mem.write32(messagePointer + 4, Result::Success);
|
||||
}
|
Loading…
Add table
Reference in a new issue