From 5e7607b700e85967febb635862645aff3c8957f3 Mon Sep 17 00:00:00 2001 From: Shawn Hoffman Date: Mon, 21 Dec 2009 07:39:57 +0000 Subject: [PATCH] replace SI_DUMMY with SI_NONE, an actual null device. tweak SI a little so that it doesn't block things which block on the status reg. git-svn-id: https://dolphin-emu.googlecode.com/svn/trunk@4713 8ced0084-cf51-0410-be5f-012b33b47a6e --- Source/Core/Core/Src/ConfigManager.cpp | 2 +- Source/Core/Core/Src/HW/SI.cpp | 219 +++++++++--------- Source/Core/Core/Src/HW/SI.h | 2 +- Source/Core/Core/Src/HW/SI_Device.cpp | 39 ++-- Source/Core/Core/Src/HW/SI_Device.h | 4 +- .../Core/Src/HW/SI_DeviceGCController.cpp | 1 + Source/Core/DolphinWX/Src/ConfigMain.cpp | 4 +- Source/Core/DolphinWX/Src/NetFunctions.cpp | 2 +- Source/TestSuite/SI/Makefile | 4 +- Source/TestSuite/SI/source/dolphintest_si.cpp | 99 +++++++- 10 files changed, 217 insertions(+), 159 deletions(-) diff --git a/Source/Core/Core/Src/ConfigManager.cpp b/Source/Core/Core/Src/ConfigManager.cpp index 3e9257825b..485de6bfd5 100644 --- a/Source/Core/Core/Src/ConfigManager.cpp +++ b/Source/Core/Core/Src/ConfigManager.cpp @@ -228,7 +228,7 @@ void SConfig::LoadSettings() for (int i = 0; i < 4; ++i) { sprintf(sidevicenum, "SIDevice%i", i); - ini.Get("Core", sidevicenum, (u32*)&m_SIDevice[i], i==0 ? SI_GC_CONTROLLER:SI_DUMMY); + ini.Get("Core", sidevicenum, (u32*)&m_SIDevice[i], i==0 ? SI_GC_CONTROLLER:SI_NONE); } ini.Get("Core", "RunCompareServer", &m_LocalCoreStartupParameter.bRunCompareServer, false); diff --git a/Source/Core/Core/Src/HW/SI.cpp b/Source/Core/Core/Src/HW/SI.cpp index 63f7f04388..ead17c08e7 100644 --- a/Source/Core/Core/Src/HW/SI.cpp +++ b/Source/Core/Core/Src/HW/SI.cpp @@ -75,10 +75,10 @@ union USIChannelOut u32 Hex; struct { - unsigned OUTPUT1 : 8; - unsigned OUTPUT0 : 8; - unsigned CMD : 8; - unsigned : 8; + u32 OUTPUT1 : 8; + u32 OUTPUT0 : 8; + u32 CMD : 8; + u32 : 8; }; }; @@ -88,12 +88,12 @@ union USIChannelIn_Hi u32 Hex; struct { - unsigned INPUT3 : 8; - unsigned INPUT2 : 8; - unsigned INPUT1 : 8; - unsigned INPUT0 : 6; - unsigned ERRLATCH : 1; // 0: no error 1: Error latched. Check SISR. - unsigned ERRSTAT : 1; // 0: no error 1: error on last transfer + u32 INPUT3 : 8; + u32 INPUT2 : 8; + u32 INPUT1 : 8; + u32 INPUT0 : 6; + u32 ERRLATCH : 1; // 0: no error 1: Error latched. Check SISR. + u32 ERRSTAT : 1; // 0: no error 1: error on last transfer }; }; @@ -103,10 +103,10 @@ union USIChannelIn_Lo u32 Hex; struct { - unsigned INPUT7 : 8; - unsigned INPUT6 : 8; - unsigned INPUT5 : 8; - unsigned INPUT4 : 8; + u32 INPUT7 : 8; + u32 INPUT6 : 8; + u32 INPUT5 : 8; + u32 INPUT4 : 8; }; }; @@ -125,17 +125,17 @@ union USIPoll u32 Hex; struct { - unsigned VBCPY3 : 1; // 1: write to output buffer only on vblank - unsigned VBCPY2 : 1; - unsigned VBCPY1 : 1; - unsigned VBCPY0 : 1; - unsigned EN3 : 1; // Enable polling of channel - unsigned EN2 : 1; // does not affect communication RAM transfers - unsigned EN1 : 1; - unsigned EN0 : 1; - unsigned Y : 8; // Polls per frame - unsigned X : 10; // Polls per X lines. begins at vsync, min 7, max depends on video mode - unsigned : 6; + u32 VBCPY3 : 1; // 1: write to output buffer only on vblank + u32 VBCPY2 : 1; + u32 VBCPY1 : 1; + u32 VBCPY0 : 1; + u32 EN3 : 1; // Enable polling of channel + u32 EN2 : 1; // does not affect communication RAM transfers + u32 EN1 : 1; + u32 EN0 : 1; + u32 Y : 8; // Polls per frame + u32 X : 10; // Polls per X lines. begins at vsync, min 7, max depends on video mode + u32 : 6; }; }; @@ -145,22 +145,22 @@ union USIComCSR u32 Hex; struct { - unsigned TSTART : 1; // write: start transfer read: transfer status - unsigned CHANNEL : 2; // determines which SI channel will be used on the communication interface. - unsigned : 3; - unsigned CALLBEN : 1; // Callback enable - unsigned CMDEN : 1; // Command enable? - unsigned INLNGTH : 7; - unsigned : 1; - unsigned OUTLNGTH : 7; // Communication Channel Output Length in bytes - unsigned : 1; - unsigned CHANEN : 1; // Channel enable? - unsigned CHANNUM : 2; // Channel number? - unsigned RDSTINTMSK : 1; // Read Status Interrupt Status Mask - unsigned RDSTINT : 1; // Read Status Interrupt Status - unsigned COMERR : 1; // Communication Error (set 0) - unsigned TCINTMSK : 1; // Transfer Complete Interrupt Mask - unsigned TCINT : 1; // Transfer Complete Interrupt + u32 TSTART : 1; // write: start transfer read: transfer status + u32 CHANNEL : 2; // determines which SI channel will be used on the communication interface. + u32 : 3; + u32 CALLBEN : 1; // Callback enable + u32 CMDEN : 1; // Command enable? + u32 INLNGTH : 7; + u32 : 1; + u32 OUTLNGTH : 7; // Communication Channel Output Length in bytes + u32 : 1; + u32 CHANEN : 1; // Channel enable? + u32 CHANNUM : 2; // Channel number? + u32 RDSTINTMSK : 1; // Read Status Interrupt Status Mask + u32 RDSTINT : 1; // Read Status Interrupt Status + u32 COMERR : 1; // Communication Error (set 0) + u32 TCINTMSK : 1; // Transfer Complete Interrupt Mask + u32 TCINT : 1; // Transfer Complete Interrupt }; USIComCSR() {Hex = 0;} USIComCSR(u32 _hex) {Hex = _hex;} @@ -172,35 +172,35 @@ union USIStatusReg u32 Hex; struct { - unsigned UNRUN3 : 1; // (RWC) write 1: bit cleared read 1: main proc underrun error - unsigned OVRUN3 : 1; // (RWC) write 1: bit cleared read 1: overrun error - unsigned COLL3 : 1; // (RWC) write 1: bit cleared read 1: collision error - unsigned NOREP3 : 1; // (RWC) write 1: bit cleared read 1: response error - unsigned WRST3 : 1; // (R) 1: buffer channel0 not copied - unsigned RDST3 : 1; // (R) 1: new Data available - unsigned : 2; // 7:6 - unsigned UNRUN2 : 1; // (RWC) write 1: bit cleared read 1: main proc underrun error - unsigned OVRUN2 : 1; // (RWC) write 1: bit cleared read 1: overrun error - unsigned COLL2 : 1; // (RWC) write 1: bit cleared read 1: collision error - unsigned NOREP2 : 1; // (RWC) write 1: bit cleared read 1: response error - unsigned WRST2 : 1; // (R) 1: buffer channel0 not copied - unsigned RDST2 : 1; // (R) 1: new Data available - unsigned : 2; // 15:14 - unsigned UNRUN1 : 1; // (RWC) write 1: bit cleared read 1: main proc underrun error - unsigned OVRUN1 : 1; // (RWC) write 1: bit cleared read 1: overrun error - unsigned COLL1 : 1; // (RWC) write 1: bit cleared read 1: collision error - unsigned NOREP1 : 1; // (RWC) write 1: bit cleared read 1: response error - unsigned WRST1 : 1; // (R) 1: buffer channel0 not copied - unsigned RDST1 : 1; // (R) 1: new Data available - unsigned : 2; // 23:22 - unsigned UNRUN0 : 1; // (RWC) write 1: bit cleared read 1: main proc underrun error - unsigned OVRUN0 : 1; // (RWC) write 1: bit cleared read 1: overrun error - unsigned COLL0 : 1; // (RWC) write 1: bit cleared read 1: collision error - unsigned NOREP0 : 1; // (RWC) write 1: bit cleared read 1: response error - unsigned WRST0 : 1; // (R) 1: buffer channel0 not copied - unsigned RDST0 : 1; // (R) 1: new Data available - unsigned : 1; - unsigned WR : 1; // (RW) write 1 start copy, read 0 copy done + u32 UNRUN3 : 1; // (RWC) write 1: bit cleared read 1: main proc underrun error + u32 OVRUN3 : 1; // (RWC) write 1: bit cleared read 1: overrun error + u32 COLL3 : 1; // (RWC) write 1: bit cleared read 1: collision error + u32 NOREP3 : 1; // (RWC) write 1: bit cleared read 1: response error + u32 WRST3 : 1; // (R) 1: buffer channel0 not copied + u32 RDST3 : 1; // (R) 1: new Data available + u32 : 2; // 7:6 + u32 UNRUN2 : 1; // (RWC) write 1: bit cleared read 1: main proc underrun error + u32 OVRUN2 : 1; // (RWC) write 1: bit cleared read 1: overrun error + u32 COLL2 : 1; // (RWC) write 1: bit cleared read 1: collision error + u32 NOREP2 : 1; // (RWC) write 1: bit cleared read 1: response error + u32 WRST2 : 1; // (R) 1: buffer channel0 not copied + u32 RDST2 : 1; // (R) 1: new Data available + u32 : 2; // 15:14 + u32 UNRUN1 : 1; // (RWC) write 1: bit cleared read 1: main proc underrun error + u32 OVRUN1 : 1; // (RWC) write 1: bit cleared read 1: overrun error + u32 COLL1 : 1; // (RWC) write 1: bit cleared read 1: collision error + u32 NOREP1 : 1; // (RWC) write 1: bit cleared read 1: response error + u32 WRST1 : 1; // (R) 1: buffer channel0 not copied + u32 RDST1 : 1; // (R) 1: new Data available + u32 : 2; // 23:22 + u32 UNRUN0 : 1; // (RWC) write 1: bit cleared read 1: main proc underrun error + u32 OVRUN0 : 1; // (RWC) write 1: bit cleared read 1: overrun error + u32 COLL0 : 1; // (RWC) write 1: bit cleared read 1: collision error + u32 NOREP0 : 1; // (RWC) write 1: bit cleared read 1: response error + u32 WRST0 : 1; // (R) 1: buffer channel0 not copied + u32 RDST0 : 1; // (R) 1: new Data available + u32 : 1; + u32 WR : 1; // (RW) write 1 start copy, read 0 copy done }; USIStatusReg() {Hex = 0;} USIStatusReg(u32 _hex) {Hex = _hex;} @@ -212,8 +212,8 @@ union USIEXIClockCount u32 Hex; struct { - unsigned LOCK : 1; // 1: prevents CPU from setting EXI clock to 32MHz - unsigned : 30; + u32 LOCK : 1; // 1: prevents CPU from setting EXI clock to 32MHz + u32 : 0; }; }; @@ -249,9 +249,13 @@ void Init() g_Poll.Hex = 0; g_Poll.X = 7; + g_ComCSR.Hex = 0; + g_StatusReg.Hex = 0; + g_EXIClockCount.Hex = 0; + g_EXIClockCount.LOCK = 1; memset(g_SIBuffer, 0, 128); changeDevice = CoreTiming::RegisterEvent("ChangeSIDevice", ChangeDeviceCallback); @@ -286,13 +290,11 @@ void Read32(u32& _uReturnValue, const u32 _iAddress) return; case SI_CHANNEL_0_IN_HI: - g_StatusReg.RDST0 = 0; UpdateInterrupts(); _uReturnValue = g_Channel[0].m_InHi.Hex; return; case SI_CHANNEL_0_IN_LO: - g_StatusReg.RDST0 = 0; UpdateInterrupts(); _uReturnValue = g_Channel[0].m_InLo.Hex; return; @@ -305,13 +307,11 @@ void Read32(u32& _uReturnValue, const u32 _iAddress) return; case SI_CHANNEL_1_IN_HI: - g_StatusReg.RDST1 = 0; UpdateInterrupts(); _uReturnValue = g_Channel[1].m_InHi.Hex; return; case SI_CHANNEL_1_IN_LO: - g_StatusReg.RDST1 = 0; UpdateInterrupts(); _uReturnValue = g_Channel[1].m_InLo.Hex; return; @@ -324,13 +324,11 @@ void Read32(u32& _uReturnValue, const u32 _iAddress) return; case SI_CHANNEL_2_IN_HI: - g_StatusReg.RDST2 = 0; UpdateInterrupts(); _uReturnValue = g_Channel[2].m_InHi.Hex; return; case SI_CHANNEL_2_IN_LO: - g_StatusReg.RDST2 = 0; UpdateInterrupts(); _uReturnValue = g_Channel[2].m_InLo.Hex; return; @@ -343,13 +341,11 @@ void Read32(u32& _uReturnValue, const u32 _iAddress) return; case SI_CHANNEL_3_IN_HI: - g_StatusReg.RDST3 = 0; UpdateInterrupts(); _uReturnValue = g_Channel[3].m_InHi.Hex; return; case SI_CHANNEL_3_IN_LO: - g_StatusReg.RDST3 = 0; UpdateInterrupts(); _uReturnValue = g_Channel[3].m_InLo.Hex; return; @@ -402,7 +398,7 @@ void Write32(const u32 _iValue, const u32 _iAddress) case SI_CHANNEL_3_IN_LO: g_Channel[3].m_InLo.Hex = _iValue; break; case SI_POLL: - INFO_LOG(SERIALINTERFACE, "Poll: X=%03d Y=%03d %s%s%s%s%s%s%s%s", + INFO_LOG(SERIALINTERFACE, "Wrote Poll: X=%03d Y=%03d %s%s%s%s%s%s%s%s", g_Poll.X, g_Poll.Y, g_Poll.EN0 ? "EN0 ":" ", g_Poll.EN1 ? "EN1 ":" ", g_Poll.EN2 ? "EN2 ":" ", g_Poll.EN3 ? "EN3 ":" ", @@ -478,12 +474,12 @@ void Write32(const u32 _iValue, const u32 _iAddress) g_EXIClockCount.Hex = _iValue; break; - case 0x80: + case 0x80: // Bogus? never seen it with ma own eyes INFO_LOG(SERIALINTERFACE, "WII something at 0xCD006480"); break; default: - _dbg_assert_(SERIALINTERFACE,0); + _dbg_assert_(SERIALINTERFACE, 0); break; } } @@ -522,11 +518,8 @@ void GenerateSIInterrupt(SIInterruptType _SIInterrupt) void RemoveDevice(int _iDeviceNumber) { - if (g_Channel[_iDeviceNumber].m_pDevice != NULL) - { - delete g_Channel[_iDeviceNumber].m_pDevice; - g_Channel[_iDeviceNumber].m_pDevice = NULL; - } + delete g_Channel[_iDeviceNumber].m_pDevice; + g_Channel[_iDeviceNumber].m_pDevice = NULL; } void AddDevice(const TSIDevices _device, int _iDeviceNumber) @@ -538,54 +531,50 @@ void AddDevice(const TSIDevices _device, int _iDeviceNumber) // create the new one g_Channel[_iDeviceNumber].m_pDevice = SIDevice_Create(_device, _iDeviceNumber); - _dbg_assert_(SERIALINTERFACE, g_Channel[_iDeviceNumber].m_pDevice != NULL); +} + +void SetNoResponse(u32 channel) +{ + // raise the NO RESPONSE error + switch (channel) + { + case 0: g_StatusReg.NOREP0 = 1; break; + case 1: g_StatusReg.NOREP1 = 1; break; + case 2: g_StatusReg.NOREP2 = 1; break; + case 3: g_StatusReg.NOREP3 = 1; break; + } + g_ComCSR.COMERR = 1; } void ChangeDeviceCallback(u64 userdata, int cyclesLate) { u8 channel = (u8)(userdata >> 32); - // doubt this matters... + g_Channel[channel].m_Out.Hex = 0; g_Channel[channel].m_InHi.Hex = 0; g_Channel[channel].m_InLo.Hex = 0; - // raise the NO RESPONSE error - switch (channel) - { - case 0: - g_StatusReg.NOREP0 = 1; - break; - case 1: - g_StatusReg.NOREP1 = 1; - break; - case 2: - g_StatusReg.NOREP2 = 1; - break; - case 3: - g_StatusReg.NOREP3 = 1; - break; - } + SetNoResponse(channel); AddDevice((TSIDevices)(u32)userdata, channel); } -void ChangeDevice(TSIDevices device, int deviceNumber) +void ChangeDevice(TSIDevices device, int channel) { // Called from GUI, so we need to make it thread safe. // Let the hardware see no device for .5b cycles - CoreTiming::ScheduleEvent_Threadsafe(0, changeDevice, (SI_DUMMY | (u64)deviceNumber << 32)); - CoreTiming::ScheduleEvent_Threadsafe(500000000, changeDevice, (device | (u64)deviceNumber << 32)); + CoreTiming::ScheduleEvent_Threadsafe(0, changeDevice, ((u64)channel << 32) | SI_NONE); + CoreTiming::ScheduleEvent_Threadsafe(500000000, changeDevice, ((u64)channel << 32) | device); } void UpdateDevices() { - // Update channels - g_StatusReg.RDST0 = g_Channel[0].m_pDevice->GetData(g_Channel[0].m_InHi.Hex, g_Channel[0].m_InLo.Hex) ? 1 : 0; - g_StatusReg.RDST1 = g_Channel[1].m_pDevice->GetData(g_Channel[1].m_InHi.Hex, g_Channel[1].m_InLo.Hex) ? 1 : 0; - g_StatusReg.RDST2 = g_Channel[2].m_pDevice->GetData(g_Channel[2].m_InHi.Hex, g_Channel[2].m_InLo.Hex) ? 1 : 0; - g_StatusReg.RDST3 = g_Channel[3].m_pDevice->GetData(g_Channel[3].m_InHi.Hex, g_Channel[3].m_InLo.Hex) ? 1 : 0; + // Update channels and set the status bit if there's new data + g_StatusReg.RDST0 = !!g_Channel[0].m_pDevice->GetData(g_Channel[0].m_InHi.Hex, g_Channel[0].m_InLo.Hex); + g_StatusReg.RDST1 = !!g_Channel[1].m_pDevice->GetData(g_Channel[1].m_InHi.Hex, g_Channel[1].m_InLo.Hex); + g_StatusReg.RDST2 = !!g_Channel[2].m_pDevice->GetData(g_Channel[2].m_InHi.Hex, g_Channel[2].m_InLo.Hex); + g_StatusReg.RDST3 = !!g_Channel[3].m_pDevice->GetData(g_Channel[3].m_InHi.Hex, g_Channel[3].m_InLo.Hex); - // Update interrupts UpdateInterrupts(); } diff --git a/Source/Core/Core/Src/HW/SI.h b/Source/Core/Core/Src/HW/SI.h index 5a76df1212..59e38df9c8 100644 --- a/Source/Core/Core/Src/HW/SI.h +++ b/Source/Core/Core/Src/HW/SI.h @@ -34,7 +34,7 @@ void RemoveDevice(int _iDeviceNumber); void AddDevice(const TSIDevices _device, int _iDeviceNumber); void ChangeDeviceCallback(u64 userdata, int cyclesLate); -void ChangeDevice(TSIDevices device, int deviceNumber); +void ChangeDevice(TSIDevices device, int channel); void Read32(u32& _uReturnValue, const u32 _iAddress); void Write32(const u32 _iValue, const u32 _iAddress); diff --git a/Source/Core/Core/Src/HW/SI_Device.cpp b/Source/Core/Core/Src/HW/SI_Device.cpp index c747c1a368..100e78c3e3 100644 --- a/Source/Core/Core/Src/HW/SI_Device.cpp +++ b/Source/Core/Core/Src/HW/SI_Device.cpp @@ -48,30 +48,22 @@ int ISIDevice::RunBuffer(u8* _pBuffer, int _iLength) }; -// --- class CSIDummy --- -// Just a dummy that logs reads and writes -// to be used for SI devices we haven't emulated -// DOES NOT FUNCTION AS "NO DEVICE INSERTED" -> Appears as unknown device -class CSIDevice_Dummy : public ISIDevice +// Stub class for saying nothing is attached, and not having to deal with null pointers :) +class CSIDevice_Null : public ISIDevice { public: - CSIDevice_Dummy(int _iDeviceNumber) : - ISIDevice(_iDeviceNumber) - {} + CSIDevice_Null(int _iDeviceNumber) : ISIDevice(_iDeviceNumber) {} + virtual ~CSIDevice_Null() {} - virtual ~CSIDevice_Dummy(){} - - int RunBuffer(u8* _pBuffer, int _iLength) - { - // Debug logging - ISIDevice::RunBuffer(_pBuffer, _iLength); - - reinterpret_cast(_pBuffer)[0] = 0x00000000; + int RunBuffer(u8* _pBuffer, int _iLength) { + reinterpret_cast(_pBuffer)[0] = SI_ERROR_NO_RESPONSE; return 4; } - - bool GetData(u32& _Hi, u32& _Low) {DEBUG_LOG(SERIALINTERFACE, "SI DUMMY %i GetData", this->m_iDeviceNumber); return false;} - void SendCommand(u32 _Cmd, u8 _Poll){DEBUG_LOG(SERIALINTERFACE, "SI DUMMY %i SendCommand: %08x", this->m_iDeviceNumber, _Cmd);} + bool GetData(u32& _Hi, u32& _Low) { + _Hi = 0x80000000; + return true; + } + void SendCommand(u32 _Cmd, u8 _Poll) {} }; @@ -80,10 +72,6 @@ ISIDevice* SIDevice_Create(TSIDevices _SIDevice, int _iDeviceNumber) { switch(_SIDevice) { - case SI_DUMMY: - return new CSIDevice_Dummy(_iDeviceNumber); - break; - case SI_GC_CONTROLLER: return new CSIDevice_GCController(_iDeviceNumber); break; @@ -96,10 +84,9 @@ ISIDevice* SIDevice_Create(TSIDevices _SIDevice, int _iDeviceNumber) return new CSIDevice_AMBaseboard(_iDeviceNumber); break; + case SI_NONE: default: - return new CSIDevice_Dummy(_iDeviceNumber); + return new CSIDevice_Null(_iDeviceNumber); break; } - - return NULL; } diff --git a/Source/Core/Core/Src/HW/SI_Device.h b/Source/Core/Core/Src/HW/SI_Device.h index 65d7e4bfb0..642a54d918 100644 --- a/Source/Core/Core/Src/HW/SI_Device.h +++ b/Source/Core/Core/Src/HW/SI_Device.h @@ -20,7 +20,7 @@ #include "Common.h" -// Devices can reply with these, but idk if we'll ever use them... +// Devices can reply with these #define SI_ERROR_NO_RESPONSE 0x0008 // Nothing is attached #define SI_ERROR_UNKNOWN 0x0040 // Unknown device is attached #define SI_ERROR_BUSY 0x0080 // Still detecting @@ -60,7 +60,7 @@ public: // SI Device IDs enum TSIDevices { - SI_DUMMY = 0, + SI_NONE = SI_ERROR_NO_RESPONSE, SI_N64_MIC = 0x00010000, SI_N64_KEYBOARD = 0x00020000, SI_N64_MOUSE = 0x02000000, diff --git a/Source/Core/Core/Src/HW/SI_DeviceGCController.cpp b/Source/Core/Core/Src/HW/SI_DeviceGCController.cpp index a16b684828..50cde1edfe 100644 --- a/Source/Core/Core/Src/HW/SI_DeviceGCController.cpp +++ b/Source/Core/Core/Src/HW/SI_DeviceGCController.cpp @@ -214,6 +214,7 @@ bool CSIDevice_GCController::GetData(u32& _Hi, u32& _Low) } // Keep track of the special button combos (embedded in controller hardware... :( ) + // Should technically be in "gc time", but we just use host system time :) EButtonCombo tempCombo; if ((PadStatus.button & 0xff00) == (PAD_BUTTON_Y|PAD_BUTTON_X|PAD_BUTTON_START)) tempCombo = COMBO_ORIGIN; diff --git a/Source/Core/DolphinWX/Src/ConfigMain.cpp b/Source/Core/DolphinWX/Src/ConfigMain.cpp index 532159e58c..fa61fb0837 100644 --- a/Source/Core/DolphinWX/Src/ConfigMain.cpp +++ b/Source/Core/DolphinWX/Src/ConfigMain.cpp @@ -411,7 +411,7 @@ void CConfigMain::CreateGUIControls() GCSIDeviceText[1] = new wxStaticText(GamecubePage, ID_GC_SIDEVICE_TEXT, wxT("Port 2"), wxDefaultPosition, wxDefaultSize); GCSIDeviceText[2] = new wxStaticText(GamecubePage, ID_GC_SIDEVICE_TEXT, wxT("Port 3"), wxDefaultPosition, wxDefaultSize); GCSIDeviceText[3] = new wxStaticText(GamecubePage, ID_GC_SIDEVICE_TEXT, wxT("Port 4"), wxDefaultPosition, wxDefaultSize); - const wxString SIDevices[] = {wxT(DEV_DUMMY_STR),wxT(SIDEV_STDCONT_STR),wxT(SIDEV_GBA_STR),wxT(SIDEV_AM_BB_STR)}; + const wxString SIDevices[] = {wxT(DEV_NONE_STR),wxT(SIDEV_STDCONT_STR),wxT(SIDEV_GBA_STR),wxT(SIDEV_AM_BB_STR)}; static const int numSIDevices = sizeof(SIDevices)/sizeof(wxString); GCSIDevice[0] = new wxChoice(GamecubePage, ID_GC_SIDEVICE0, wxDefaultPosition, wxDefaultSize, numSIDevices, SIDevices, 0, wxDefaultValidator); GCSIDevice[1] = new wxChoice(GamecubePage, ID_GC_SIDEVICE1, wxDefaultPosition, wxDefaultSize, numSIDevices, SIDevices, 0, wxDefaultValidator); @@ -793,7 +793,7 @@ void CConfigMain::ChooseSIDevice(std::string deviceName, int deviceNum) else if (!deviceName.compare(SIDEV_AM_BB_STR)) tempType = SI_AM_BASEBOARD; else - tempType = SI_DUMMY; + tempType = SI_NONE; SConfig::GetInstance().m_SIDevice[deviceNum] = tempType; diff --git a/Source/Core/DolphinWX/Src/NetFunctions.cpp b/Source/Core/DolphinWX/Src/NetFunctions.cpp index 8c2a93ec0b..4faf04f677 100644 --- a/Source/Core/DolphinWX/Src/NetFunctions.cpp +++ b/Source/Core/DolphinWX/Src/NetFunctions.cpp @@ -230,7 +230,7 @@ bool NetPlay::GetNetPads(u8 padnb, SPADStatus PadStatus, u32 *netValues) // Better disable unused ports for (int i = m_numClients+1; i < 4; i++) - SerialInterface::ChangeDevice(SI_DUMMY, i); + SerialInterface::ChangeDevice(SI_NONE, i); } if (m_timer.GetTimeDifference() > 1000) diff --git a/Source/TestSuite/SI/Makefile b/Source/TestSuite/SI/Makefile index 8cde430ac6..29142c708b 100644 --- a/Source/TestSuite/SI/Makefile +++ b/Source/TestSuite/SI/Makefile @@ -7,7 +7,7 @@ ifeq ($(strip $(DEVKITPPC)),) $(error "Please set DEVKITPPC in your environment. export DEVKITPPC=devkitPPC") endif -include $(DEVKITPPC)/gamecube_rules +include $(DEVKITPPC)/wii_rules #--------------------------------------------------------------------------------- # TARGET is the name of the output @@ -33,7 +33,7 @@ LDFLAGS = -g $(MACHDEP) -Wl,-Map,$(notdir $@).map #--------------------------------------------------------------------------------- # any extra libraries we wish to link with the project #--------------------------------------------------------------------------------- -LIBS := -logc -lm +LIBS := -lfat -logc -lm #--------------------------------------------------------------------------------- # list of directories containing libraries, this must be the top level containing diff --git a/Source/TestSuite/SI/source/dolphintest_si.cpp b/Source/TestSuite/SI/source/dolphintest_si.cpp index 5884b05f74..f20cab8976 100644 --- a/Source/TestSuite/SI/source/dolphintest_si.cpp +++ b/Source/TestSuite/SI/source/dolphintest_si.cpp @@ -7,28 +7,106 @@ #include #include #include +#include + +#ifdef HW_RVL +#include +#include +#endif static void *xfb; static GXRModeObj *rmode; void Initialise(); +void (*reboot)() = (void(*)())0x80001800; +static u32* const SI_REG = (u32*)0xCD006400; +static bool haveInit = false; +static int counter = 0; +static bool logWritten = false; +void AppendSDLog() +{ +#ifdef HW_RVL + FILE *f = fopen("sd:/si_log.txt", "a"); + if (f) + { + fprintf(f, "\n-------------------------------------\n"); + for (int i = 0; i < 4; i++) + fprintf(f, "%i\tstatus: %x\t type:%x\n", i, SI_GetStatus(i), SI_GetType(i)); + u32 x = 0; + fprintf(f, "-------------------------------------\n"); + fprintf(f, "SI_CHANNEL_0_OUT\t%08x\n", SI_REG[x++]); + fprintf(f, "SI_CHANNEL_0_IN_HI\t%08x\n", SI_REG[x++]); + fprintf(f, "SI_CHANNEL_0_IN_LO\t%08x\n", SI_REG[x++]); + fprintf(f, "SI_CHANNEL_1_OUT\t%08x\n", SI_REG[x++]); + fprintf(f, "SI_CHANNEL_1_IN_HI\t%08x\n", SI_REG[x++]); + fprintf(f, "SI_CHANNEL_1_IN_LO\t%08x\n", SI_REG[x++]); + fprintf(f, "SI_CHANNEL_2_OUT\t%08x\n", SI_REG[x++]); + fprintf(f, "SI_CHANNEL_2_IN_HI\t%08x\n", SI_REG[x++]); + fprintf(f, "SI_CHANNEL_2_IN_LO\t%08x\n", SI_REG[x++]); + fprintf(f, "SI_CHANNEL_3_OUT\t%08x\n", SI_REG[x++]); + fprintf(f, "SI_CHANNEL_3_IN_HI\t%08x\n", SI_REG[x++]); + fprintf(f, "SI_CHANNEL_3_IN_LO\t%08x\n", SI_REG[x++]); + fprintf(f, "SI_POLL\t\t\t%08x\n", SI_REG[x++]); + fprintf(f, "SI_COM_CSR\t\t\t%08x\n", SI_REG[x++]); + fprintf(f, "SI_STATUS_REG\t\t%08x\n", SI_REG[x++]); + fprintf(f, "SI_EXI_CLOCK_COUNT\t%08x\n", SI_REG[x++]); + fprintf(f, "-------------------------------------\n"); + fclose(f); + } +#endif +} int main(int argc, char **argv) { Initialise(); while(1) { - PAD_ScanPads(); - VIDEO_ClearFrameBuffer(rmode, xfb, 0); - std::cout<<"\x1b[0;0H"; // Position the cursor (at 0, 0) + if (haveInit) PAD_ScanPads(); + + VIDEO_ClearFrameBuffer(rmode, xfb, COLOR_BLACK); + + printf("\x1b[4;0H"); + for(int Chan = 0; Chan < 4; Chan++) + printf("%i\tstatus: %x\t type:%x\n", Chan, SI_GetStatus(Chan), SI_GetType(Chan)); + + printf("SI Regs: (cc006000)\n"); + for (u32 i = 0; i < 16/*num SI regs*/; ++i) { - std::cout << "Chan " << Chan << std::endl; - std::cout << "Status is " << SI_GetStatus(Chan) << std::endl; - std::cout << "Type is 0x" << std::setbase(16) << SI_GetType(Chan) << std::setbase(10) << std::endl << std::endl; + printf("%08x ", SI_REG[i]); + if ((i+1)%8==0) printf("\n"); } + + if (haveInit) + printf("\nPAD_Init\n"); + VIDEO_WaitVSync(); + + if (haveInit) + { + if (PAD_ButtonsDown(0) & PAD_BUTTON_START) + { + AppendSDLog(); + #ifdef HW_RVL + fatUnmount("sd"); + __io_wiisd.shutdown(); + #endif + reboot(); + } + } + + counter++; + AppendSDLog(); + if (counter > 5 && !haveInit) + { + PAD_Init(); + haveInit = true; + } + else if (haveInit && !logWritten) + { + logWritten = true; + } } return 0; @@ -39,9 +117,6 @@ void Initialise() // Initialise the video system VIDEO_Init(); - // This function initialises the attached controllers - PAD_Init(); - // Obtain the preferred video mode from the system // This will correspond to the settings in the Wii menu rmode = VIDEO_GetPreferredMode(NULL); @@ -67,4 +142,10 @@ void Initialise() // Wait for Video setup to complete VIDEO_WaitVSync(); if(rmode->viTVMode&VI_NON_INTERLACE) VIDEO_WaitVSync(); + +#ifdef HW_RVL + // Initialize FAT so we can write to SD. + __io_wiisd.startup(); + fatMountSimple("sd", &__io_wiisd); +#endif }