FS: Stub card SPI and some other things

This commit is contained in:
wheremyfoodat 2024-12-09 19:08:30 +02:00
parent 055dbc7fb6
commit cc669d7cab
12 changed files with 139 additions and 21 deletions

View file

@ -0,0 +1,40 @@
#include <algorithm>
#include <memory>
#include "fs/archive_card_spi.hpp"
namespace fs = std::filesystem;
HorizonResult CardSPIArchive::createFile(const FSPath& path, u64 size) {
Helpers::panic("[Card SPI] CreateFile not yet supported");
return Result::Success;
}
HorizonResult CardSPIArchive::deleteFile(const FSPath& path) {
Helpers::panic("[Card SPI] Unimplemented DeleteFile");
return Result::Success;
}
HorizonResult CardSPIArchive::createDirectory(const FSPath& path) {
Helpers::panic("[Card SPI] CreateDirectory not yet supported");
return Result::Success;
}
FileDescriptor CardSPIArchive::openFile(const FSPath& path, const FilePerms& perms) {
Helpers::panic("[Card SPI] OpenFile not yet supported");
return FileError;
}
Rust::Result<ArchiveBase*, HorizonResult> CardSPIArchive::openArchive(const FSPath& path) {
if (path.type != PathType::Empty) {
Helpers::panic("Unimplemented path type for CardSPIArchive::OpenArchive");
}
Helpers::warn("Unimplemented: Card SPI archive");
return Err(Result::FailurePlaceholder);
}
Rust::Result<DirectorySession, HorizonResult> CardSPIArchive::openDirectory(const FSPath& path) {
Helpers::panic("[Card SPI] OpenDirectory not yet supported");
return Err(Result::FailurePlaceholder);
}

View file

@ -28,7 +28,8 @@ namespace DSPCommands {
RegisterInterruptEvents = 0x00150082,
GetSemaphoreEventHandle = 0x00160000,
SetSemaphoreMask = 0x00170040,
GetHeadphoneStatus = 0x001F0000
GetHeadphoneStatus = 0x001F0000,
ForceHeadphoneOut = 0x00200040,
};
}
@ -42,6 +43,7 @@ namespace Result {
void DSPService::reset() {
totalEventCount = 0;
semaphoreMask = 0;
headphonesInserted = true;
semaphoreEvent = std::nullopt;
interrupt0 = std::nullopt;
@ -60,6 +62,7 @@ void DSPService::handleSyncRequest(u32 messagePointer) {
case DSPCommands::ConvertProcessAddressFromDspDram: convertProcessAddressFromDspDram(messagePointer); break;
case DSPCommands::FlushDataCache: flushDataCache(messagePointer); break;
case DSPCommands::InvalidateDataCache: invalidateDCache(messagePointer); break;
case DSPCommands::ForceHeadphoneOut: forceHeadphoneOut(messagePointer); break;
case DSPCommands::GetHeadphoneStatus: getHeadphoneStatus(messagePointer); break;
case DSPCommands::GetSemaphoreEventHandle: getSemaphoreEventHandle(messagePointer); break;
case DSPCommands::LoadComponent: loadComponent(messagePointer); break;
@ -210,7 +213,8 @@ void DSPService::getHeadphoneStatus(u32 messagePointer) {
mem.write32(messagePointer, IPC::responseHeader(0x1F, 2, 0));
mem.write32(messagePointer + 4, Result::Success);
mem.write32(messagePointer + 8, Result::HeadphonesInserted); // This should be toggleable for shits and giggles
// This should be toggleable for shits and giggles
mem.write32(messagePointer + 8, headphonesInserted ? Result::HeadphonesInserted : Result::HeadphonesNotInserted);
}
void DSPService::getSemaphoreEventHandle(u32 messagePointer) {
@ -278,6 +282,17 @@ void DSPService::invalidateDCache(u32 messagePointer) {
mem.write32(messagePointer + 4, Result::Success);
}
void DSPService::forceHeadphoneOut(u32 messagePointer) {
const bool force = mem.read8(messagePointer + 4) != 0;
if (force) {
headphonesInserted = false;
}
log("DSP::ForceHeadphoneOut\n");
mem.write32(messagePointer, IPC::responseHeader(0x20, 1, 0));
mem.write32(messagePointer + 4, Result::Success);
}
DSPService::ComponentDumpResult DSPService::dumpComponent(const std::filesystem::path& path) {
if (loadedComponent.empty()) {
return ComponentDumpResult::NotLoaded;

View file

@ -102,6 +102,7 @@ ArchiveBase* FSService::getArchiveFromID(u32 id, const FSPath& archivePath) {
case ArchiveID::TwlPhoto: return &twlPhoto;
case ArchiveID::TwlSound: return &twlSound;
case ArchiveID::CardSPI: return &cardSpi;
default:
Helpers::panic("Unknown archive. ID: %d\n", id);

View file

@ -14,6 +14,7 @@ namespace ServiceCommands {
WriteHwRegsWithMask = 0x00020084,
SetBufferSwap = 0x00050200,
FlushDataCache = 0x00080082,
InvalidateDataCache = 0x00090082,
SetLCDForceBlack = 0x000B0040,
TriggerCmdReqQueue = 0x000C0000,
ReleaseRight = 0x00170000,
@ -21,7 +22,7 @@ namespace ServiceCommands {
SaveVramSysArea = 0x00190000,
RestoreVramSysArea = 0x001A0000,
SetInternalPriorities = 0x001E0080,
StoreDataCache = 0x001F0082
StoreDataCache = 0x001F0082,
};
}
@ -63,6 +64,7 @@ void GPUService::handleSyncRequest(u32 messagePointer) {
case ServiceCommands::ReadHwRegs: readHwRegs(messagePointer); break;
case ServiceCommands::WriteHwRegs: writeHwRegs(messagePointer); break;
case ServiceCommands::WriteHwRegsWithMask: writeHwRegsWithMask(messagePointer); break;
case ServiceCommands::InvalidateDataCache: invalidateDataCache(messagePointer); break;
default: Helpers::panic("GPU service requested. Command: %08X\n", command);
}
}
@ -278,6 +280,16 @@ void GPUService::flushDataCache(u32 messagePointer) {
mem.write32(messagePointer + 4, Result::Success);
}
void GPUService::invalidateDataCache(u32 messagePointer) {
u32 address = mem.read32(messagePointer + 4);
u32 size = mem.read32(messagePointer + 8);
u32 processHandle = handle = mem.read32(messagePointer + 16);
log("GSP::GPU::InvalidateDataCache(address = %08X, size = %X, process = %X)\n", address, size, processHandle);
mem.write32(messagePointer, IPC::responseHeader(0x9, 1, 0));
mem.write32(messagePointer + 4, Result::Success);
}
void GPUService::storeDataCache(u32 messagePointer) {
u32 address = mem.read32(messagePointer + 4);
u32 size = mem.read32(messagePointer + 8);

View file

@ -1,10 +1,12 @@
#include "services/mcu/mcu_hwc.hpp"
#include "ipc.hpp"
#include "result/result.hpp"
#include "services/mcu/mcu_hwc.hpp"
namespace MCU::HWCCommands {
enum : u32 {
GetBatteryLevel = 0x00050000,
SetInfoLedPattern = 0x000A0640,
};
}
@ -14,6 +16,7 @@ void MCU::HWCService::handleSyncRequest(u32 messagePointer) {
const u32 command = mem.read32(messagePointer);
switch (command) {
case HWCCommands::GetBatteryLevel: getBatteryLevel(messagePointer); break;
case HWCCommands::SetInfoLedPattern: setInfoLEDPattern(messagePointer); break;
default: Helpers::panic("MCU::HWC service requested. Command: %08X\n", command);
}
}
@ -24,4 +27,12 @@ void MCU::HWCService::getBatteryLevel(u32 messagePointer) {
mem.write32(messagePointer, IPC::responseHeader(0x5, 2, 0));
mem.write32(messagePointer + 4, Result::Success);
mem.write8(messagePointer + 8, config.batteryPercentage);
}
void MCU::HWCService::setInfoLEDPattern(u32 messagePointer) {
log("MCU::HWC::SetInfoLedPattern\n");
// 25 parameters to make some notification LEDs blink...
mem.write32(messagePointer, IPC::responseHeader(0xA, 1, 0));
mem.write32(messagePointer + 4, Result::Success);
}