Resolve unresolved-import calls to a module/NID in the "Unknown syscall" log

A call through a still-pending import gets written as a generic "invalid
syscall" opcode (WriteFuncMissingStub) that no longer carries the
original module name or NID by the time it's actually invoked - but the
address of the syscall instruction itself is exactly the stubAddr every
pending FuncSymbolImport already records. Added
KernelFindImportByStubAddr() to search loaded modules' importedFuncs for
a match, and use it in GetSyscallFuncPointer's unknown-syscall path.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
This commit is contained in:
Henrik Rydgård
2026-07-25 14:52:19 +02:00
co-authored by Claude Sonnet 5
parent a6e4d691ef
commit ca34a14fd8
3 changed files with 36 additions and 1 deletions
+24
View File
@@ -766,6 +766,30 @@ void UnexportFuncSymbol(const FuncSymbolExport &func) {
}
}
// Used to add detail to the "Unknown syscall" log in HLE.cpp's GetSyscallFuncPointer - a call
// through a still-unresolved import ends up as a generic "invalid syscall" opcode that no
// longer carries the original module name/NID, but the (fixed, unique) address of the syscall
// instruction itself does - it's exactly the stubAddr every pending FuncSymbolImport recorded
// when it was written by WriteFuncMissingStub.
bool KernelFindImportByStubAddr(u32 stubAddr, std::string *importModuleName, u32 *nid, std::string *importingModuleName) {
u32 error;
for (SceUID moduleId : loadedModules) {
PSPModule *module = kernelObjects.Get<PSPModule>(moduleId, error);
if (!module) {
continue;
}
for (const auto &func : module->importedFuncs) {
if (func.stubAddr == stubAddr) {
*importModuleName = func.moduleName;
*nid = func.nid;
*importingModuleName = module->GetName();
return true;
}
}
}
return false;
}
void PSPModule::Cleanup() {
MIPSAnalyst::ForgetFunctions(textStart, textEnd);