From afa4e4034d0c3b88b11867d55a640c2e99885969 Mon Sep 17 00:00:00 2001 From: patrickvl Date: Sun, 21 Jan 2018 22:20:38 +0100 Subject: [PATCH] The NV2A is now registered as a hardware device, just like all other devices. Like the NVNet device, it's implementation is currently just a forward to the existing code. Still, this removes a dependency from EmuX86 on the NV2A device - from now on it's reached via the generic device framework. --- build/win32/Cxbx.vcxproj | 2 + build/win32/Cxbx.vcxproj.filters | 6 ++ src/CxbxKrnl/CxbxKrnl.cpp | 3 - src/CxbxKrnl/EmuX86.cpp | 17 +--- src/CxbxKrnl/Xbox.cpp | 4 + src/CxbxKrnl/devices/video/nv2a.cpp | 122 ++++++++++++++++++++++++++++ src/CxbxKrnl/devices/video/nv2a.h | 54 ++++++++++++ 7 files changed, 190 insertions(+), 18 deletions(-) create mode 100644 src/CxbxKrnl/devices/video/nv2a.cpp create mode 100644 src/CxbxKrnl/devices/video/nv2a.h diff --git a/build/win32/Cxbx.vcxproj b/build/win32/Cxbx.vcxproj index c5b271a41..5074bfe6d 100644 --- a/build/win32/Cxbx.vcxproj +++ b/build/win32/Cxbx.vcxproj @@ -190,6 +190,7 @@ + @@ -359,6 +360,7 @@ + diff --git a/build/win32/Cxbx.vcxproj.filters b/build/win32/Cxbx.vcxproj.filters index 53da67549..546c0b4c5 100644 --- a/build/win32/Cxbx.vcxproj.filters +++ b/build/win32/Cxbx.vcxproj.filters @@ -226,6 +226,9 @@ Hardware + + Hardware + @@ -441,6 +444,9 @@ Hardware + + Hardware + diff --git a/src/CxbxKrnl/CxbxKrnl.cpp b/src/CxbxKrnl/CxbxKrnl.cpp index 29eb29666..70d63a912 100644 --- a/src/CxbxKrnl/CxbxKrnl.cpp +++ b/src/CxbxKrnl/CxbxKrnl.cpp @@ -1017,9 +1017,6 @@ __declspec(noreturn) void CxbxKrnlInit // Now the hardware devices exist, couple the EEPROM buffer to it's device g_EEPROM->SetEEPROM((uint8_t*)EEPROM); - // Always initialise NV2A: We may need it for disabled HLE patches too! - EmuNV2A_Init(); - if (bLLE_GPU) { DbgPrintf("INIT: Initializing OpenGL.\n"); diff --git a/src/CxbxKrnl/EmuX86.cpp b/src/CxbxKrnl/EmuX86.cpp index 379eba313..15bc5c9ff 100644 --- a/src/CxbxKrnl/EmuX86.cpp +++ b/src/CxbxKrnl/EmuX86.cpp @@ -47,10 +47,8 @@ #include "mnemonics.h" #include "CxbxKrnl.h" -#include "Emu.h" +#include "Emu.h" // For EmuWarning #include "EmuX86.h" -#include "EmuNV2A.h" -#include "EmuNVNet.h" #include "HLEIntercept.h" // for bLLE_GPU #include @@ -177,11 +175,7 @@ uint32_t EmuX86_Read(xbaddr addr, int size) uint32_t value; - if (addr >= NV2A_ADDR && addr < NV2A_ADDR + NV2A_SIZE) { - // Access NV2A regardless weither HLE is disabled or not (ignoring bLLE_GPU) - value = EmuNV2A_Read(addr - NV2A_ADDR, size); - // Note : EmuNV2A_Read does it's own logging - } else if (addr >= XBOX_FLASH_ROM_BASE) { // 0xFFF00000 - 0xFFFFFFF + if (addr >= XBOX_FLASH_ROM_BASE) { // 0xFFF00000 - 0xFFFFFFF value = EmuFlash_Read32(addr - XBOX_FLASH_ROM_BASE); // TODO : Make flash access size-aware } else { // Pass the Read to the PCI Bus, this will handle devices with BARs set to MMIO addresses @@ -211,13 +205,6 @@ void EmuX86_Write(xbaddr addr, uint32_t value, int size) return; } - if (addr >= NV2A_ADDR && addr < NV2A_ADDR + NV2A_SIZE) { - // Access NV2A regardless weither HLE is disabled or not (ignoring bLLE_GPU) - EmuNV2A_Write(addr - NV2A_ADDR, value, size); - // Note : EmuNV2A_Write does it's own logging - return; - } - if (addr >= XBOX_FLASH_ROM_BASE) { // 0xFFF00000 - 0xFFFFFFF EmuWarning("EmuX86_Write(0x%08X, 0x%08X) [FLASH_ROM]", addr, value); return; diff --git a/src/CxbxKrnl/Xbox.cpp b/src/CxbxKrnl/Xbox.cpp index 2e6c4c10e..e354bbb4b 100644 --- a/src/CxbxKrnl/Xbox.cpp +++ b/src/CxbxKrnl/Xbox.cpp @@ -40,12 +40,14 @@ #include "SMCDevice.h" // For SMCDevice #include "EEPROMDevice.h" // For EEPROMDevice #include "EmuNVNet.h" // For NVNetDevice +#include "devices\video\nv2a.h" // For NV2ADevice PCIBus* g_PCIBus; SMBus* g_SMBus; SMCDevice* g_SMC; EEPROMDevice* g_EEPROM; NVNetDevice* g_NVNet; +NV2ADevice* g_NV2A; #define SMBUS_TV_ENCODER_ID_CONEXANT 0x8A // = Write; Read = 08B #define SMBUS_TV_ENCODER_ID_FOCUS 0xD4 // = Write; Read = 0D5 @@ -57,12 +59,14 @@ void InitXboxHardware() g_SMC = new SMCDevice(Revision1_1); // TODO : Make configurable g_EEPROM = new EEPROMDevice(); g_NVNet = new NVNetDevice(); + g_NV2A = new NV2ADevice(); g_SMBus->ConnectDevice(SMBUS_SMC_SLAVE_ADDRESS, g_SMC); g_SMBus->ConnectDevice(SMBUS_EEPROM_ADDRESS, g_EEPROM); g_PCIBus->ConnectDevice(PCI_DEVID(0, PCI_DEVFN(1, 1)), g_SMBus); g_PCIBus->ConnectDevice(PCI_DEVID(0, PCI_DEVFN(4, 0)), g_NVNet); + g_PCIBus->ConnectDevice(PCI_DEVID(1, PCI_DEVFN(0, 0)), g_NV2A); // TODO : Handle other SMBUS Addresses, like PIC_ADDRESS, XCALIBUR_ADDRESS // Resources : http://pablot.com/misc/fancontroller.cpp diff --git a/src/CxbxKrnl/devices/video/nv2a.cpp b/src/CxbxKrnl/devices/video/nv2a.cpp new file mode 100644 index 000000000..3ea6c6972 --- /dev/null +++ b/src/CxbxKrnl/devices/video/nv2a.cpp @@ -0,0 +1,122 @@ +// This is an open source non-commercial project. Dear PVS-Studio, please check it. +// PVS-Studio Static Code Analyzer for C, C++ and C#: http://www.viva64.com +// ****************************************************************** +// * +// * .,-::::: .,:: .::::::::. .,:: .: +// * ,;;;'````' `;;;, .,;; ;;;'';;' `;;;, .,;; +// * [[[ '[[,,[[' [[[__[[\. '[[,,[[' +// * $$$ Y$$$P $$""""Y$$ Y$$$P +// * `88bo,__,o, oP"``"Yo, _88o,,od8P oP"``"Yo, +// * "YUMMMMMP",m" "Mm,""YUMMMP" ,m" "Mm, +// * +// * src->devices->video->nv2a.cpp +// * +// * This file is part of the Cxbx project. +// * +// * Cxbx and Cxbe are free software; you can redistribute them +// * and/or modify them under the terms of the GNU General Public +// * License as published by the Free Software Foundation; either +// * version 2 of the license, or (at your option) any later version. +// * +// * 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 for more details. +// * +// * You should have recieved a copy of the GNU General Public License +// * along with this program; see the file COPYING. +// * If not, write to the Free Software Foundation, Inc., +// * 59 Temple Place - Suite 330, Bostom, MA 02111-1307, USA. +// * +// * (c) 2017-2018 Luke Usher +// * (c) 2018 Patrick van Logchem +// * +// * All rights reserved +// * +// ****************************************************************** +#define _XBOXKRNL_DEFEXTRN_ + +#define LOG_PREFIX "NV2A" + +#include "../../CxbxKrnl/CxbxKrnl.h" // For XBOX_MEMORY_SIZE, DWORD, etc +#include "../../CxbxKrnl/EmuNV2A.h" // For now, use EmuNV2A + +#include "nv2a.h" + +/* NV2ADevice */ + +// PCI Device functions + +void NV2ADevice::Init() +{ + PCIBarRegister r; + + // Register Memory bar : + r.Raw.type = PCI_BAR_TYPE_MEMORY; + r.Memory.address = NV2A_ADDR >> 4; + RegisterBAR(0, NV2A_SIZE, r.value); + + // Register physical memory on bar 1 + r.Memory.address = 0; + RegisterBAR(1, XBOX_MEMORY_SIZE, r.value); // TODO : Read g_PhysicalMemory->Size + + m_DeviceId = 0x02A5; + m_VendorId = PCI_VENDOR_ID_NVIDIA; + + // For now, forward to EmuNv2A + EmuNV2A_Init(); +} + +void NV2ADevice::Reset() +{ +} + +uint32_t NV2ADevice::IORead(int barIndex, uint32_t port, unsigned size) +{ + return 0; +} + +void NV2ADevice::IOWrite(int barIndex, uint32_t port, uint32_t value, unsigned size) +{ +} + +uint32_t NV2ADevice::MMIORead(int barIndex, uint32_t addr, unsigned size) +{ + switch (barIndex) { + case 0: + uint32_t value; + // For now, forward to EmuNV2A + { + // Access NV2A regardless weither HLE is disabled or not (ignoring bLLE_GPU) + value = EmuNV2A_Read(addr, size); + // Note : EmuNV2A_Read does it's own logging + } + // TODO : call block handler + return value; + case 1: + return 0; // TODO : access physical memory + } + + // TODO : Log unexpected bar access + return 0; +} + +void NV2ADevice::MMIOWrite(int barIndex, uint32_t addr, uint32_t value, unsigned size) +{ + switch (barIndex) { + case 0: + // For now, forward to EmuNV2A + { + // Access NV2A regardless weither HLE is disabled or not (ignoring bLLE_GPU) + EmuNV2A_Write(addr, value, size); + // Note : EmuNV2A_Write does it's own logging + } + // TODO : call block handler + return; + case 1: + // TODO : access physical memory + return; + } + + // TODO : Log unexpected bar access +} diff --git a/src/CxbxKrnl/devices/video/nv2a.h b/src/CxbxKrnl/devices/video/nv2a.h new file mode 100644 index 000000000..be6c90324 --- /dev/null +++ b/src/CxbxKrnl/devices/video/nv2a.h @@ -0,0 +1,54 @@ +// ****************************************************************** +// * +// * .,-::::: .,:: .::::::::. .,:: .: +// * ,;;;'````' `;;;, .,;; ;;;'';;' `;;;, .,;; +// * [[[ '[[,,[[' [[[__[[\. '[[,,[[' +// * $$$ Y$$$P $$""""Y$$ Y$$$P +// * `88bo,__,o, oP"``"Yo, _88o,,od8P oP"``"Yo, +// * "YUMMMMMP",m" "Mm,""YUMMMP" ,m" "Mm, +// * +// * src->devices->video->nv2a.h +// * +// * This file is part of the Cxbx project. +// * +// * Cxbx and Cxbe are free software; you can redistribute them +// * and/or modify them under the terms of the GNU General Public +// * License as published by the Free Software Foundation; either +// * version 2 of the license, or (at your option) any later version. +// * +// * 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 for more details. +// * +// * You should have recieved a copy of the GNU General Public License +// * along with this program; see the file COPYING. +// * If not, write to the Free Software Foundation, Inc., +// * 59 Temple Place - Suite 330, Bostom, MA 02111-1307, USA. +// * +// * (c) 2017-2018 Luke Usher +// * (c) 2018 Patrick van Logchem +// * +// * All rights reserved +// * +// ****************************************************************** +#pragma once + +#include "../../CxbxKrnl/PCIDevice.h" // For PCIDevice + +#define NV2A_ADDR 0xFD000000 +#define NV2A_SIZE 0x01000000 + +class NV2ADevice : public PCIDevice { +public: + // PCI Device functions + void Init(); + void Reset(); + + uint32_t IORead(int barIndex, uint32_t port, unsigned size); + void IOWrite(int barIndex, uint32_t port, uint32_t value, unsigned size); + uint32_t MMIORead(int barIndex, uint32_t addr, unsigned size); + void MMIOWrite(int barIndex, uint32_t addr, uint32_t value, unsigned size); +}; + +extern NV2ADevice* g_NV2A;