#include "Iop_LibSd.h" #include "Log.h" #include "string_format.h" //Not an actual implementation of the LIBSD module //It is only used for debugging purposes (ie.: function names) using namespace Iop; #define FUNCTION_INIT "Init" #define FUNCTION_SETPARAM "SetParam" #define FUNCTION_GETPARAM "GetParam" #define FUNCTION_SETSWITCH "SetSwitch" #define FUNCTION_GETSWITCH "GetSwitch" #define FUNCTION_SETADDR "SetAddr" #define FUNCTION_GETADDR "GetAddr" #define FUNCTION_SETCOREATTR "SetCoreAttr" #define FUNCTION_PROCBATCH "ProcBatch" #define FUNCTION_VOICETRANS "VoiceTrans" #define FUNCTION_BLOCKTRANS "BlockTrans" #define FUNCTION_VOICETRANSSTATUS "VoiceTransStatus" #define FUNCTION_BLOCKTRANSSTATUS "BlockTransStatus" #define FUNCTION_SETTRANSCALLBACK "SetTransCallback" #define FUNCTION_SETEFFECTATTR "SetEffectAttr" #define FUNCTION_SETTRANSINTRHANDLER "SetTransIntrHandler" #define FUNCTION_SETSPU2INTRHANDLER "SetSpu2IntrHandler" #define LOG_NAME "iop_libsd" std::string CLibSd::GetId() const { return "libsd"; } std::string CLibSd::GetFunctionName(unsigned int functionId) const { switch(functionId) { case 4: return FUNCTION_INIT; break; case 5: return FUNCTION_SETPARAM; break; case 6: return FUNCTION_GETPARAM; break; case 7: return FUNCTION_SETSWITCH; break; case 8: return FUNCTION_GETSWITCH; break; case 9: return FUNCTION_SETADDR; break; case 10: return FUNCTION_GETADDR; break; case 11: return FUNCTION_SETCOREATTR; break; case 15: return FUNCTION_PROCBATCH; break; case 17: return FUNCTION_VOICETRANS; break; case 18: return FUNCTION_BLOCKTRANS; break; case 19: return FUNCTION_VOICETRANSSTATUS; break; case 20: return FUNCTION_BLOCKTRANSSTATUS; break; case 21: return FUNCTION_SETTRANSCALLBACK; break; case 23: return FUNCTION_SETEFFECTATTR; break; case 26: return FUNCTION_SETTRANSINTRHANDLER; break; case 27: return FUNCTION_SETSPU2INTRHANDLER; break; default: return "unknown"; break; } } void CLibSd::Invoke(CMIPS&, unsigned int) { } static std::string DecodeAddress(uint16 addressId) { std::string result; bool voiceAddress = false; switch(addressId >> 8) { case 0x1F: result = "IRQA"; break; case 0x20: result = "SSA"; voiceAddress = true; break; case 0x21: result = "LSAX"; voiceAddress = true; break; case 0x22: result = "NAX"; voiceAddress = true; break; default: result = string_format("unknown (0x%02X)", addressId >> 8); break; } if(voiceAddress) { result += string_format(", CORE%d, VOICE%d", addressId & 1, (addressId & 0x3E) >> 1); } else { result += string_format(", CORE%d", addressId & 1); } return result; } static std::string DecodeParam(uint16 paramId) { std::string result; uint16 paramIdx = (paramId >> 8); bool voiceParam = (paramIdx < 8); switch(paramIdx) { case 0x00: result = "VOLL"; break; case 0x01: result = "VOLR"; break; case 0x02: result = "PITCH"; break; case 0x03: result = "ADSR1"; break; case 0x04: result = "ADSR2"; break; case 0x05: result = "ENVX"; break; case 0x06: result = "VOLXL"; break; case 0x07: result = "VOLXR"; break; case 0x08: result = "MMIX"; break; case 0x09: result = "MVOLL"; break; case 0x0A: result = "MVOLR"; break; case 0x0B: result = "EVOLL"; break; case 0x0C: result = "EVOLR"; break; case 0x0D: result = "AVOLL"; break; case 0x0E: result = "AVOLR"; break; case 0x0F: result = "BVOLL"; break; case 0x10: result = "BVOLR"; break; default: result = string_format("unknown (0x%02X)", paramIdx); break; } if(voiceParam) { result += string_format(", CORE%d, VOICE%d", paramId & 1, (paramId & 0x3E) >> 1); } else { result += string_format(", CORE%d", paramId & 1); } return result; } static std::string DecodeSwitch(uint16 switchId) { std::string result; switch(switchId >> 8) { case 0x13: result = "PMON"; break; case 0x14: result = "NON"; break; case 0x15: result = "KON"; break; case 0x16: result = "KOFF"; break; case 0x17: result = "ENDX"; break; case 0x18: result = "VMIXL"; break; case 0x19: result = "VMIXEL"; break; case 0x1A: result = "VMIXR"; break; case 0x1B: result = "VMIXER"; break; default: result = string_format("unknown (0x%02X)", switchId >> 8); break; } result += string_format(", CORE%d", switchId & 1); return result; } void CLibSd::TraceCall(CMIPS& context, unsigned int functionId) { switch(functionId) { case 4: CLog::GetInstance().Print(LOG_NAME, FUNCTION_INIT "(flag = %d);\r\n", context.m_State.nGPR[CMIPS::A0].nV0); break; case 5: CLog::GetInstance().Print(LOG_NAME, FUNCTION_SETPARAM "(entry = 0x%04X, value = 0x%04X); //(%s)\r\n", context.m_State.nGPR[CMIPS::A0].nV0, context.m_State.nGPR[CMIPS::A1].nV0, DecodeParam(static_cast(context.m_State.nGPR[CMIPS::A0].nV0)).c_str()); break; case 6: CLog::GetInstance().Print(LOG_NAME, FUNCTION_GETPARAM "(entry = 0x%04X); //(%s)\r\n", context.m_State.nGPR[CMIPS::A0].nV0, DecodeParam(static_cast(context.m_State.nGPR[CMIPS::A0].nV0)).c_str()); break; case 7: CLog::GetInstance().Print(LOG_NAME, FUNCTION_SETSWITCH "(entry = 0x%04X, value = 0x%08X); //(%s)\r\n", context.m_State.nGPR[CMIPS::A0].nV0, context.m_State.nGPR[CMIPS::A1].nV0, DecodeSwitch(static_cast(context.m_State.nGPR[CMIPS::A0].nV0)).c_str()); break; case 8: CLog::GetInstance().Print(LOG_NAME, FUNCTION_GETSWITCH "(entry = 0x%04X); //(%s)\r\n", context.m_State.nGPR[CMIPS::A0].nV0, DecodeSwitch(static_cast(context.m_State.nGPR[CMIPS::A0].nV0)).c_str()); break; case 9: CLog::GetInstance().Print(LOG_NAME, FUNCTION_SETADDR "(entry = 0x%04X, value = 0x%08X); //(%s)\r\n", context.m_State.nGPR[CMIPS::A0].nV0, context.m_State.nGPR[CMIPS::A1].nV0, DecodeAddress(static_cast(context.m_State.nGPR[CMIPS::A0].nV0)).c_str()); break; case 10: CLog::GetInstance().Print(LOG_NAME, FUNCTION_GETADDR "(entry = 0x%04X); //(%s)\r\n", context.m_State.nGPR[CMIPS::A0].nV0, DecodeAddress(static_cast(context.m_State.nGPR[CMIPS::A0].nV0)).c_str()); break; case 11: CLog::GetInstance().Print(LOG_NAME, FUNCTION_SETCOREATTR "(entry = 0x%04X, value = 0x%04X);\r\n", context.m_State.nGPR[CMIPS::A0].nV0, context.m_State.nGPR[CMIPS::A1].nV0); break; case 17: CLog::GetInstance().Print(LOG_NAME, FUNCTION_VOICETRANS "(channel = 0x%04X, mode = 0x%04X, maddr = 0x%08X, saddr = 0x%08X, size = 0x%08X);\r\n", context.m_State.nGPR[CMIPS::A0].nV0, context.m_State.nGPR[CMIPS::A1].nV0, context.m_State.nGPR[CMIPS::A2].nV0, context.m_State.nGPR[CMIPS::A3].nV0, context.m_pMemoryMap->GetWord(context.m_State.nGPR[CMIPS::SP].nV0 + 0x10)); break; case 18: CLog::GetInstance().Print(LOG_NAME, FUNCTION_BLOCKTRANS "(channel = 0x%04X, mode = 0x%04X, maddr = 0x%08X, size = 0x%08X);\r\n", context.m_State.nGPR[CMIPS::A0].nV0, context.m_State.nGPR[CMIPS::A1].nV0, context.m_State.nGPR[CMIPS::A2].nV0, context.m_State.nGPR[CMIPS::A3].nV0); break; case 19: CLog::GetInstance().Print(LOG_NAME, FUNCTION_VOICETRANSSTATUS "(channel = 0x%04X, flag = 0x%04X);\r\n", context.m_State.nGPR[CMIPS::A0].nV0, context.m_State.nGPR[CMIPS::A1].nV0); break; case 20: CLog::GetInstance().Print(LOG_NAME, FUNCTION_BLOCKTRANSSTATUS "(channel = 0x%04X, flag = 0x%04X);\r\n", context.m_State.nGPR[CMIPS::A0].nV0, context.m_State.nGPR[CMIPS::A1].nV0); break; case 21: CLog::GetInstance().Print(LOG_NAME, FUNCTION_SETTRANSCALLBACK "(channel = 0x%04X, function = 0x%08X);\r\n", context.m_State.nGPR[CMIPS::A0].nV0, context.m_State.nGPR[CMIPS::A1].nV0); break; case 23: CLog::GetInstance().Print(LOG_NAME, FUNCTION_SETEFFECTATTR "(core = 0x%04X, attr = 0x%08X);\r\n", context.m_State.nGPR[CMIPS::A0].nV0, context.m_State.nGPR[CMIPS::A1].nV0); break; case 26: CLog::GetInstance().Print(LOG_NAME, FUNCTION_SETTRANSINTRHANDLER "(channel = 0x%04X, function = 0x%08X, arg = 0x%08X);\r\n", context.m_State.nGPR[CMIPS::A0].nV0, context.m_State.nGPR[CMIPS::A1].nV0, context.m_State.nGPR[CMIPS::A2].nV0); break; case 27: CLog::GetInstance().Print(LOG_NAME, FUNCTION_SETSPU2INTRHANDLER "(function = 0x%08X, arg = 0x%08X);\r\n", context.m_State.nGPR[CMIPS::A0].nV0, context.m_State.nGPR[CMIPS::A1].nV0); break; default: CLog::GetInstance().Print(LOG_NAME, "unknownlibsd(%d);\r\n", functionId); break; } }