diff --git a/Source/Core/Core/Src/IPC_HLE/WII_IPC_HLE.cpp b/Source/Core/Core/Src/IPC_HLE/WII_IPC_HLE.cpp index c9d19f71c0..ee3d635097 100644 --- a/Source/Core/Core/Src/IPC_HLE/WII_IPC_HLE.cpp +++ b/Source/Core/Core/Src/IPC_HLE/WII_IPC_HLE.cpp @@ -41,7 +41,6 @@ They will also generate a true or false return for UpdateInterrupts() in WII_IPC #include "CommonPaths.h" #include "WII_IPC_HLE.h" #include "WII_IPC_HLE_Device.h" -#include "WII_IPC_HLE_Device_Error.h" #include "WII_IPC_HLE_Device_DI.h" #include "WII_IPC_HLE_Device_FileIO.h" #include "WII_IPC_HLE_Device_stm.h" @@ -76,7 +75,6 @@ typedef std::queue ipc_msg_queue; static ipc_msg_queue request_queue; // ppc -> arm static ipc_msg_queue reply_queue; // arm -> ppc -// General IPC functions void Init() { _dbg_assert_msg_(WII_IPC_HLE, g_DeviceMap.empty(), "DeviceMap isnt empty on init"); @@ -93,11 +91,9 @@ void Init() g_DeviceMap[i] = new CWII_IPC_HLE_Device_net_kd_time(i, std::string("/dev/net/kd/time")); i++; g_DeviceMap[i] = new CWII_IPC_HLE_Device_net_ncd_manage(i, std::string("/dev/net/ncd/manage")); i++; g_DeviceMap[i] = new CWII_IPC_HLE_Device_net_ip_top(i, std::string("/dev/net/ip/top")); i++; - g_DeviceMap[i] = new CWII_IPC_HLE_Device_usb_oh0(i, std::string("/dev/usb/oh0")); i++; g_DeviceMap[i] = new CWII_IPC_HLE_Device_usb_kbd(i, std::string("/dev/usb/kbd")); i++; - g_DeviceMap[i] = new CWII_IPC_HLE_Device_usb_hid(i, std::string("/dev/usb/hid")); i++; g_DeviceMap[i] = new CWII_IPC_HLE_Device_sdio_slot0(i, std::string("/dev/sdio/slot0")); i++; - g_DeviceMap[i] = new CWII_IPC_HLE_Device_Error(i, std::string("_Unknown_Device_")); i++; + g_DeviceMap[i] = new IWII_IPC_HLE_Device(i, std::string("_Unimplemented_Device_")); g_LastDeviceID = IPC_FIRST_FILEIO_ID; } @@ -151,7 +147,7 @@ u32 GetDeviceIDByName(const std::string& _rDeviceName) ++itr; } - return 0; + return -1; } IWII_IPC_HLE_Device* AccessDeviceByID(u32 _ID) @@ -284,22 +280,29 @@ void ExecuteCommand(u32 _Address) DeviceID = GetDeviceIDByName(DeviceName); // check if a device with this name has been created already - if (DeviceID == 0) + if (DeviceID == -1) { if (DeviceName.find("/dev/") != std::string::npos) { - ERROR_LOG(WII_IPC_FILEIO, "Unknown device: %s", DeviceName.c_str()); + WARN_LOG(WII_IPC_HLE, "Unimplemented device: %s", DeviceName.c_str()); + + pDevice = AccessDeviceByID(GetDeviceIDByName(std::string("_Unimplemented_Device_"))); + CmdSuccess = pDevice->Open(_Address, Mode); } - u32 CurrentDeviceID = g_LastDeviceID; - pDevice = CreateFileIO(CurrentDeviceID, DeviceName); - g_DeviceMap[CurrentDeviceID] = pDevice; - g_FileNameMap[CurrentDeviceID] = DeviceName; - g_LastDeviceID++; + else + { + // create new file handle + u32 CurrentDeviceID = g_LastDeviceID; + pDevice = CreateFileIO(CurrentDeviceID, DeviceName); + g_DeviceMap[CurrentDeviceID] = pDevice; + g_FileNameMap[CurrentDeviceID] = DeviceName; + g_LastDeviceID++; + + CmdSuccess = pDevice->Open(_Address, Mode); - CmdSuccess = pDevice->Open(_Address, Mode); - - INFO_LOG(WII_IPC_FILEIO, "IOP: Open File (Device=%s, ID=%08x, Mode=%i)", - pDevice->GetDeviceName().c_str(), CurrentDeviceID, Mode); + INFO_LOG(WII_IPC_FILEIO, "IOP: Open File (Device=%s, ID=%08x, Mode=%i)", + pDevice->GetDeviceName().c_str(), CurrentDeviceID, Mode); + } } else { @@ -356,31 +359,50 @@ void ExecuteCommand(u32 _Address) case COMMAND_CLOSE_DEVICE: if (pDevice) { - pDevice->Close(_Address); + CmdSuccess = pDevice->Close(_Address); // Don't delete hardware if (!pDevice->IsHardware()) DeleteDeviceByID(DeviceID); - CmdSuccess = true; + } + else + { + Memory::Write_U32(FS_EINVAL, _Address + 4); + CmdSuccess = true; } break; case COMMAND_READ: - if (pDevice != NULL) + if (pDevice) CmdSuccess = pDevice->Read(_Address); + else + { + Memory::Write_U32(FS_EINVAL, _Address + 4); + CmdSuccess = true; + } break; case COMMAND_WRITE: - if (pDevice != NULL) + if (pDevice) CmdSuccess = pDevice->Write(_Address); + else + { + Memory::Write_U32(FS_EINVAL, _Address + 4); + CmdSuccess = true; + } break; case COMMAND_SEEK: - if (pDevice != NULL) + if (pDevice) CmdSuccess = pDevice->Seek(_Address); + else + { + Memory::Write_U32(FS_EINVAL, _Address + 4); + CmdSuccess = true; + } break; case COMMAND_IOCTL: - if (pDevice != NULL) + if (pDevice) CmdSuccess = pDevice->IOCtl(_Address); break; @@ -395,7 +417,7 @@ void ExecuteCommand(u32 _Address) } // It seems that the original hardware overwrites the command after it has been - // executed. We write 8 which is not any valid command, and what IOS does + // executed. We write 8 which is not any valid command, and what IOS does Memory::Write_U32(8, _Address); // IOS seems to write back the command that was responded to Memory::Write_U32(Command, _Address + 8); @@ -407,7 +429,14 @@ void ExecuteCommand(u32 _Address) } else { - //DEBUG_LOG(WII_IPC_HLE, "<<-- Failed or Not Ready to Reply to IPC Request @ 0x%08x ", _Address); + if (pDevice) + { + INFO_LOG(WII_IPC_HLE, "<<-- Reply Failed to %s IPC Request %i @ 0x%08x ", pDevice->GetDeviceName().c_str(), Command, _Address); + } + else + { + INFO_LOG(WII_IPC_HLE, "<<-- Reply Failed to Unknown (%08x) IPC Request %i @ 0x%08x ", DeviceID, Command, _Address); + } } } diff --git a/Source/Core/Core/Src/IPC_HLE/WII_IPC_HLE.h b/Source/Core/Core/Src/IPC_HLE/WII_IPC_HLE.h index 959c7c0e05..177a3f02ce 100644 --- a/Source/Core/Core/Src/IPC_HLE/WII_IPC_HLE.h +++ b/Source/Core/Core/Src/IPC_HLE/WII_IPC_HLE.h @@ -25,8 +25,8 @@ class IWII_IPC_HLE_Device; namespace WII_IPC_HLE_Interface { -#define IPC_FIRST_HARDWARE_ID 0x13370000 // first IPC device ID -#define IPC_FIRST_FILEIO_ID 0x13380000 // first IPC file ID +#define IPC_FIRST_HARDWARE_ID 0 // first IPC device ID +#define IPC_FIRST_FILEIO_ID 33 // first IPC file ID // Init void Init(); diff --git a/Source/Core/Core/Src/IPC_HLE/WII_IPC_HLE_Device.h b/Source/Core/Core/Src/IPC_HLE/WII_IPC_HLE_Device.h index b413f2aff1..c41c64fb12 100644 --- a/Source/Core/Core/Src/IPC_HLE/WII_IPC_HLE_Device.h +++ b/Source/Core/Core/Src/IPC_HLE/WII_IPC_HLE_Device.h @@ -23,6 +23,31 @@ class PointerWrap; + +#define FS_SUCCESS (u32)0 // Success +#define FS_EACCES (u32)-1 // Permission denied +#define FS_EEXIST (u32)-2 // File exists +#define FS_EINVAL (u32)-4 // Invalid argument Invalid FD +#define FS_ENOENT (u32)-6 // File not found +#define FS_EBUSY (u32)-8 // Resource busy +#define FS_EIO (u32)-12 // returned on ECC error +#define FS_ENOMEM (u32)-22 // Alloc failed during request +#define FS_EFATAL (u32)-101 // Fatal error +#define FS_EACCESS (u32)-102 // Permission denied +#define FS_ECORRUPT (u32)-103 // returned for "corrupted" NAND +#define FS_EEXIST2 (u32)-105 // File exists +#define FS_ENOENT2 (u32)-106 // File not found +#define FS_ENFILE (u32)-107 // Too many fds open +#define FS_EFBIG (u32)-108 // max block count reached? +#define FS_ENFILE2 (u32)-109 // Too many fds open +#define FS_ENAMELEN (u32)-110 // pathname is too long +#define FS_EFDOPEN (u32)-111 // FD is already open +#define FS_EIO2 (u32)-114 // returned on ECC error +#define FS_ENOTEMPTY (u32)-115 // Directory not empty +#define FS_EDIRDEPTH (u32)-116 // max directory depth exceeded +#define FS_EBUSY2 (u32)-118 // Resource busy +//#define FS_EFATAL (u32)-119 // fatal error not used by IOS as fatal ERROR + class IWII_IPC_HLE_Device { public: @@ -42,19 +67,21 @@ public: u32 GetDeviceID() const { return m_DeviceID; } virtual bool Open(u32 _CommandAddress, u32 _Mode) { - (void)_CommandAddress; (void)_Mode; - _dbg_assert_msg_(WII_IPC_HLE, 0, "%s does not support Open()", m_Name.c_str()); + (void)_Mode; + WARN_LOG(WII_IPC_HLE, "%s does not support Open()", m_Name.c_str()); + Memory::Write_U32(FS_ENOENT, _CommandAddress + 4); m_Active = true; return true; } virtual bool Close(u32 _CommandAddress, bool _bForce = false) { - (void)_CommandAddress; (void)_bForce; - _dbg_assert_msg_(WII_IPC_HLE, 0, "%s does not support Close()", m_Name.c_str()); + WARN_LOG(WII_IPC_HLE, "%s does not support Close()", m_Name.c_str()); + if (!_bForce) + Memory::Write_U32(FS_EINVAL, _CommandAddress + 4); m_Active = false; return true; } -#define UNIMPLEMENTED_CMD(cmd) _dbg_assert_msg_(WII_IPC_HLE, 0, "%s does not support "#cmd"()", m_Name.c_str()); return true; +#define UNIMPLEMENTED_CMD(cmd) WARN_LOG(WII_IPC_HLE, "%s does not support "#cmd"()", m_Name.c_str()); return true; virtual bool Seek (u32) { UNIMPLEMENTED_CMD(Seek) } virtual bool Read (u32) { UNIMPLEMENTED_CMD(Read) } virtual bool Write (u32) { UNIMPLEMENTED_CMD(Write) } @@ -80,46 +107,43 @@ protected: // A struct for IOS ioctlv calls struct SIOCtlVBuffer { - SIOCtlVBuffer(u32 _Address) - : m_Address(_Address) + SIOCtlVBuffer(u32 _Address) : m_Address(_Address) { // These are the Ioctlv parameters in the IOS communication. The BufferVector // is a memory address offset at where the in and out buffer addresses are // stored. - Parameter = Memory::Read_U32(m_Address + 0x0C); // command 3, arg0 - NumberInBuffer = Memory::Read_U32(m_Address + 0x10); // 4, arg1 - NumberPayloadBuffer = Memory::Read_U32(m_Address + 0x14); // 5, arg2 - BufferVector = Memory::Read_U32(m_Address + 0x18); // 6, arg3 + Parameter = Memory::Read_U32(m_Address + 0x0C); // command 3, arg0 + NumberInBuffer = Memory::Read_U32(m_Address + 0x10); // 4, arg1 + NumberPayloadBuffer = Memory::Read_U32(m_Address + 0x14); // 5, arg2 + BufferVector = Memory::Read_U32(m_Address + 0x18); // 6, arg3 // The start of the out buffer u32 BufferVectorOffset = BufferVector; - //if(Parameter = 0x1d) PanicAlert("%i: %i", Parameter, NumberInBuffer); - // Write the address and size for all in messages for (u32 i = 0; i < NumberInBuffer; i++) { SBuffer Buffer; - Buffer.m_Address = Memory::Read_U32(BufferVectorOffset); + Buffer.m_Address = Memory::Read_U32(BufferVectorOffset); BufferVectorOffset += 4; - Buffer.m_Size = Memory::Read_U32(BufferVectorOffset); + Buffer.m_Size = Memory::Read_U32(BufferVectorOffset); BufferVectorOffset += 4; + InBuffer.push_back(Buffer); DEBUG_LOG(WII_IPC_HLE, "SIOCtlVBuffer in%i: 0x%08x, 0x%x", i, Buffer.m_Address, Buffer.m_Size); - InBuffer.push_back(Buffer); } // Write the address and size for all out or in-out messages for (u32 i = 0; i < NumberPayloadBuffer; i++) { SBuffer Buffer; - Buffer.m_Address = Memory::Read_U32(BufferVectorOffset); + Buffer.m_Address = Memory::Read_U32(BufferVectorOffset); BufferVectorOffset += 4; - Buffer.m_Size = Memory::Read_U32(BufferVectorOffset); + Buffer.m_Size = Memory::Read_U32(BufferVectorOffset); BufferVectorOffset += 4; + PayloadBuffer.push_back(Buffer); DEBUG_LOG(WII_IPC_HLE, "SIOCtlVBuffer io%i: 0x%08x, 0x%x", i, Buffer.m_Address, Buffer.m_Size); - PayloadBuffer.push_back(Buffer); } } diff --git a/Source/Core/Core/Src/IPC_HLE/WII_IPC_HLE_Device_Error.h b/Source/Core/Core/Src/IPC_HLE/WII_IPC_HLE_Device_Error.h deleted file mode 100644 index 9bdf1f4e88..0000000000 --- a/Source/Core/Core/Src/IPC_HLE/WII_IPC_HLE_Device_Error.h +++ /dev/null @@ -1,52 +0,0 @@ -// Copyright (C) 2003 Dolphin Project. - -// This program is free software: you can redistribute it and/or modify -// it under the terms of the GNU General Public License as published by -// the Free Software Foundation, version 2.0. - -// This program is distributed in the hope that it will be useful, -// but WITHOUT ANY WARRANTY; without even the implied warranty of -// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -// GNU General Public License 2.0 for more details. - -// A copy of the GPL 2.0 should have been included with the program. -// If not, see http://www.gnu.org/licenses/ - -// Official SVN repository and contact information can be found at -// http://code.google.com/p/dolphin-emu/ - -#ifndef _WII_IPC_HLE_DEVICE_ERROR_H_ -#define _WII_IPC_HLE_DEVICE_ERROR_H_ - -#include "WII_IPC_HLE_Device.h" - -class CWII_IPC_HLE_Device_Error : public IWII_IPC_HLE_Device -{ -public: - - CWII_IPC_HLE_Device_Error(u32 _DeviceID, const std::string& _rDeviceName ) : - IWII_IPC_HLE_Device(_DeviceID, _rDeviceName) - {} - - virtual ~CWII_IPC_HLE_Device_Error() - {} - - virtual bool Open(u32 _CommandAddress, u32 _Mode) - { - //PanicAlert("CWII_IPC_HLE_Device_Error"); - Memory::Write_U32(GetDeviceID(), _CommandAddress + 4); - m_Active = true; - return true; - } - - virtual bool Close(u32 _CommandAddress, bool _bForce) - { - if (!_bForce) - Memory::Write_U32(0, _CommandAddress + 4); - m_Active = false; - return true; - } -}; - -#endif -