mirror of https://github.com/PCSX2/pcsx2.git
gsdx: Remove psx/ps1 emulator compatibility.
ePSXe for example. There is little to no benefit in keeping it, especially when nobody was maintaining the code. If we ever want to reintroduce it we can do so from older branches like 1.6. Plus if we want to integrate plugins into pcsx2 itself this is a required step. PS1 games can ofc still be played within pcsx2.
This commit is contained in:
parent
2b884a7e7c
commit
0b9d68e60c
|
@ -53,14 +53,6 @@ if(OPENCL_FOUND)
|
||||||
endif()
|
endif()
|
||||||
|
|
||||||
set(GSdxSources
|
set(GSdxSources
|
||||||
PSX/GPU.cpp
|
|
||||||
PSX/GPUDrawScanline.cpp
|
|
||||||
PSX/GPUDrawScanlineCodeGenerator.cpp
|
|
||||||
PSX/GPULocalMemory.cpp
|
|
||||||
PSX/GPURenderer.cpp
|
|
||||||
PSX/GPURendererSW.cpp
|
|
||||||
PSX/GPUSetupPrimCodeGenerator.cpp
|
|
||||||
PSX/GPUState.cpp
|
|
||||||
GS.cpp
|
GS.cpp
|
||||||
GSAlignedClass.cpp
|
GSAlignedClass.cpp
|
||||||
GSBlock.cpp
|
GSBlock.cpp
|
||||||
|
@ -154,17 +146,6 @@ set(GSdxHeaders
|
||||||
GSVector8.h
|
GSVector8.h
|
||||||
GSVector8i.h
|
GSVector8i.h
|
||||||
stdafx.h
|
stdafx.h
|
||||||
PSX/GPUDrawingEnvironment.h
|
|
||||||
PSX/GPUDrawScanlineCodeGenerator.h
|
|
||||||
PSX/GPUDrawScanline.h
|
|
||||||
PSX/GPU.h
|
|
||||||
PSX/GPULocalMemory.h
|
|
||||||
PSX/GPURenderer.h
|
|
||||||
PSX/GPURendererSW.h
|
|
||||||
PSX/GPUScanlineEnvironment.h
|
|
||||||
PSX/GPUSetupPrimCodeGenerator.h
|
|
||||||
PSX/GPUState.h
|
|
||||||
PSX/GPUVertex.h
|
|
||||||
Renderers/Common/GSDevice.h
|
Renderers/Common/GSDevice.h
|
||||||
Renderers/Common/GSDirtyRect.h
|
Renderers/Common/GSDirtyRect.h
|
||||||
Renderers/Common/GSFastList.h
|
Renderers/Common/GSFastList.h
|
||||||
|
@ -224,7 +205,6 @@ if(Windows)
|
||||||
Window/GSSettingsDlg.cpp
|
Window/GSSettingsDlg.cpp
|
||||||
Window/GSWndDX.cpp
|
Window/GSWndDX.cpp
|
||||||
Window/GSWndWGL.cpp
|
Window/GSWndWGL.cpp
|
||||||
PSX/GPUSettingsDlg.cpp
|
|
||||||
)
|
)
|
||||||
|
|
||||||
LIST(APPEND GSdxHeaders
|
LIST(APPEND GSdxHeaders
|
||||||
|
@ -234,7 +214,6 @@ if(Windows)
|
||||||
Renderers/DX11/GSTextureCache11.h
|
Renderers/DX11/GSTextureCache11.h
|
||||||
Window/GSWndDX.h
|
Window/GSWndDX.h
|
||||||
Window/GSWndWGL.h
|
Window/GSWndWGL.h
|
||||||
PSX/GPUSettingsDlg.h
|
|
||||||
resource.h
|
resource.h
|
||||||
targetver.h
|
targetver.h
|
||||||
)
|
)
|
||||||
|
|
|
@ -22,7 +22,6 @@
|
||||||
#include "stdafx.h"
|
#include "stdafx.h"
|
||||||
#include "GSdx.h"
|
#include "GSdx.h"
|
||||||
#include "GS.h"
|
#include "GS.h"
|
||||||
#include "PSX/GPU.h"
|
|
||||||
#include <fstream>
|
#include <fstream>
|
||||||
|
|
||||||
static void* s_hModule;
|
static void* s_hModule;
|
||||||
|
@ -314,29 +313,6 @@ void GSdxApp::Init()
|
||||||
m_gs_tv_shaders.push_back(GSSetting(3, "Triangular filter", ""));
|
m_gs_tv_shaders.push_back(GSSetting(3, "Triangular filter", ""));
|
||||||
m_gs_tv_shaders.push_back(GSSetting(4, "Wave filter", ""));
|
m_gs_tv_shaders.push_back(GSSetting(4, "Wave filter", ""));
|
||||||
|
|
||||||
// PSX options that start with m_gpu.
|
|
||||||
m_gpu_renderers.push_back(GSSetting(static_cast<int8>(GPURendererType::D3D11_SW), "Direct3D 11", "Software"));
|
|
||||||
m_gpu_renderers.push_back(GSSetting(static_cast<int8>(GPURendererType::NULL_Renderer), "Null", ""));
|
|
||||||
|
|
||||||
m_gpu_filter.push_back(GSSetting(0, "Nearest", ""));
|
|
||||||
m_gpu_filter.push_back(GSSetting(1, "Bilinear (polygons only)", ""));
|
|
||||||
m_gpu_filter.push_back(GSSetting(2, "Bilinear", ""));
|
|
||||||
|
|
||||||
m_gpu_dithering.push_back(GSSetting(0, "Disabled", ""));
|
|
||||||
m_gpu_dithering.push_back(GSSetting(1, "Auto", ""));
|
|
||||||
|
|
||||||
m_gpu_aspectratio.push_back(GSSetting(0, "Stretch", ""));
|
|
||||||
m_gpu_aspectratio.push_back(GSSetting(1, "4:3", ""));
|
|
||||||
m_gpu_aspectratio.push_back(GSSetting(2, "16:9", ""));
|
|
||||||
|
|
||||||
m_gpu_scale.push_back(GSSetting(0 | (0 << 2), "H x 1 - V x 1", ""));
|
|
||||||
m_gpu_scale.push_back(GSSetting(1 | (0 << 2), "H x 2 - V x 1", ""));
|
|
||||||
m_gpu_scale.push_back(GSSetting(0 | (1 << 2), "H x 1 - V x 2", ""));
|
|
||||||
m_gpu_scale.push_back(GSSetting(1 | (1 << 2), "H x 2 - V x 2", ""));
|
|
||||||
m_gpu_scale.push_back(GSSetting(2 | (1 << 2), "H x 4 - V x 2", ""));
|
|
||||||
m_gpu_scale.push_back(GSSetting(1 | (2 << 2), "H x 2 - V x 4", ""));
|
|
||||||
m_gpu_scale.push_back(GSSetting(2 | (2 << 2), "H x 4 - V x 4", ""));
|
|
||||||
|
|
||||||
// Avoid to clutter the ini file with useless options
|
// Avoid to clutter the ini file with useless options
|
||||||
#ifdef _WIN32
|
#ifdef _WIN32
|
||||||
// Per OS option.
|
// Per OS option.
|
||||||
|
@ -344,15 +320,9 @@ void GSdxApp::Init()
|
||||||
m_default_configuration["CaptureFileName"] = "";
|
m_default_configuration["CaptureFileName"] = "";
|
||||||
m_default_configuration["CaptureVideoCodecDisplayName"] = "";
|
m_default_configuration["CaptureVideoCodecDisplayName"] = "";
|
||||||
m_default_configuration["dx_break_on_severity"] = "0";
|
m_default_configuration["dx_break_on_severity"] = "0";
|
||||||
|
m_default_configuration["windowed"] = "1";
|
||||||
// D3D Blending option
|
// D3D Blending option
|
||||||
m_default_configuration["accurate_blending_unit_d3d11"] = "1";
|
m_default_configuration["accurate_blending_unit_d3d11"] = "1";
|
||||||
|
|
||||||
// PSX option. Not supported on linux.
|
|
||||||
m_default_configuration["dithering"] = "1";
|
|
||||||
m_default_configuration["scale_x"] = "0";
|
|
||||||
m_default_configuration["scale_y"] = "0";
|
|
||||||
m_default_configuration["windowed"] = "1";
|
|
||||||
#else
|
#else
|
||||||
m_default_configuration["linux_replay"] = "1";
|
m_default_configuration["linux_replay"] = "1";
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -43,30 +43,3 @@ EXPORTS
|
||||||
GSReplay
|
GSReplay
|
||||||
GSBenchmark
|
GSBenchmark
|
||||||
GSgetTitleInfo2
|
GSgetTitleInfo2
|
||||||
PSEgetLibType
|
|
||||||
PSEgetLibName
|
|
||||||
PSEgetLibVersion
|
|
||||||
GPUinit
|
|
||||||
GPUshutdown
|
|
||||||
GPUopen
|
|
||||||
GPUclose
|
|
||||||
GPUconfigure
|
|
||||||
GPUabout
|
|
||||||
GPUtest
|
|
||||||
GPUwriteData
|
|
||||||
GPUwriteStatus
|
|
||||||
GPUreadData
|
|
||||||
GPUreadStatus
|
|
||||||
GPUdmaChain
|
|
||||||
GPUgetMode
|
|
||||||
GPUsetMode
|
|
||||||
GPUupdateLace
|
|
||||||
GPUmakeSnapshot
|
|
||||||
GPUwriteDataMem
|
|
||||||
GPUreadDataMem
|
|
||||||
GPUdisplayText
|
|
||||||
GPUdisplayFlags
|
|
||||||
GPUfreeze
|
|
||||||
GPUshowScreenPic
|
|
||||||
GPUgetScreenPic
|
|
||||||
GPUcursor
|
|
||||||
|
|
|
@ -81,12 +81,6 @@ public:
|
||||||
std::vector<GSSetting> m_gs_acc_blend_level;
|
std::vector<GSSetting> m_gs_acc_blend_level;
|
||||||
std::vector<GSSetting> m_gs_acc_blend_level_d3d11;
|
std::vector<GSSetting> m_gs_acc_blend_level_d3d11;
|
||||||
std::vector<GSSetting> m_gs_tv_shaders;
|
std::vector<GSSetting> m_gs_tv_shaders;
|
||||||
|
|
||||||
std::vector<GSSetting> m_gpu_renderers;
|
|
||||||
std::vector<GSSetting> m_gpu_filter;
|
|
||||||
std::vector<GSSetting> m_gpu_dithering;
|
|
||||||
std::vector<GSSetting> m_gpu_aspectratio;
|
|
||||||
std::vector<GSSetting> m_gpu_scale;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
struct GSDXError {};
|
struct GSDXError {};
|
||||||
|
|
|
@ -253,33 +253,6 @@ BEGIN
|
||||||
COMBOBOX IDC_COLORSPACE,102,47,48,32,CBS_DROPDOWNLIST | WS_TABSTOP
|
COMBOBOX IDC_COLORSPACE,102,47,48,32,CBS_DROPDOWNLIST | WS_TABSTOP
|
||||||
END
|
END
|
||||||
|
|
||||||
IDD_GPUCONFIG DIALOGEX 0, 0, 242, 189
|
|
||||||
STYLE DS_SETFONT | DS_MODALFRAME | DS_FIXEDSYS | WS_POPUP | WS_CAPTION | WS_SYSMENU
|
|
||||||
CAPTION "Settings..."
|
|
||||||
FONT 8, "MS Shell Dlg", 400, 0, 0x1
|
|
||||||
BEGIN
|
|
||||||
CONTROL IDB_LOGO11,IDC_LOGO11,"Static",SS_BITMAP | SS_REALSIZECONTROL,6,6,230,44
|
|
||||||
CONTROL IDB_NULL,IDC_NULL,"Static",SS_BITMAP | SS_REALSIZECONTROL,6,6,230,44
|
|
||||||
LTEXT "Renderer:",IDC_STATIC,7,59,34,8
|
|
||||||
COMBOBOX IDC_RENDERER,108,57,127,118,CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP
|
|
||||||
LTEXT "Resolution:",IDC_RESOLUTION_TEXT,7,74,37,8
|
|
||||||
COMBOBOX IDC_RESOLUTION,108,72,127,125,CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP
|
|
||||||
LTEXT "Texture Filter (Del):",IDC_FILTER_TEXT,7,90,64,8
|
|
||||||
COMBOBOX IDC_FILTER,108,87,127,98,CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP
|
|
||||||
LTEXT "Dithering (End):",IDC_DITHERING_TEXT,7,105,52,8
|
|
||||||
COMBOBOX IDC_DITHERING,108,102,127,98,CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP
|
|
||||||
LTEXT "Aspect Ratio (PgDn):",IDC_ASPECTRATIO_TEXT,7,120,68,8
|
|
||||||
COMBOBOX IDC_ASPECTRATIO,108,117,127,98,CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP
|
|
||||||
LTEXT "Internal Resolution:",IDC_SCALE_TEXT,7,135,64,8
|
|
||||||
COMBOBOX IDC_SCALE,108,132,127,98,CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP
|
|
||||||
CONTROL "Windowed",IDC_WINDOWED,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,149,49,10
|
|
||||||
LTEXT "Extra Rend. Threads:",IDC_SWTHREADS_TEXT,108,150,70,8
|
|
||||||
EDITTEXT IDC_SWTHREADS_EDIT,200,147,35,13,ES_AUTOHSCROLL | ES_NUMBER
|
|
||||||
CONTROL "",IDC_SWTHREADS,"msctls_updown32",UDS_SETBUDDYINT | UDS_ALIGNRIGHT | UDS_AUTOBUDDY | UDS_ARROWKEYS | UDS_NOTHOUSANDS,0,0,11,14
|
|
||||||
DEFPUSHBUTTON "OK",IDOK,68,168,50,14
|
|
||||||
PUSHBUTTON "Cancel",IDCANCEL,124,168,50,14
|
|
||||||
END
|
|
||||||
|
|
||||||
IDD_CONFIG DIALOGEX 0, 0, 242, 371
|
IDD_CONFIG DIALOGEX 0, 0, 242, 371
|
||||||
STYLE DS_SETFONT | DS_MODALFRAME | DS_FIXEDSYS | WS_POPUP | WS_CAPTION | WS_SYSMENU
|
STYLE DS_SETFONT | DS_MODALFRAME | DS_FIXEDSYS | WS_POPUP | WS_CAPTION | WS_SYSMENU
|
||||||
CAPTION "GSdx Settings"
|
CAPTION "GSdx Settings"
|
||||||
|
@ -380,16 +353,6 @@ BEGIN
|
||||||
HORZGUIDE, 54
|
HORZGUIDE, 54
|
||||||
END
|
END
|
||||||
|
|
||||||
IDD_GPUCONFIG, DIALOG
|
|
||||||
BEGIN
|
|
||||||
LEFTMARGIN, 7
|
|
||||||
RIGHTMARGIN, 182
|
|
||||||
VERTGUIDE, 80
|
|
||||||
VERTGUIDE, 182
|
|
||||||
TOPMARGIN, 7
|
|
||||||
BOTTOMMARGIN, 192
|
|
||||||
END
|
|
||||||
|
|
||||||
IDD_CONFIG, DIALOG
|
IDD_CONFIG, DIALOG
|
||||||
BEGIN
|
BEGIN
|
||||||
LEFTMARGIN, 6
|
LEFTMARGIN, 6
|
||||||
|
|
|
@ -162,15 +162,6 @@
|
||||||
<ClCompile Include="Window\GSWnd.cpp" />
|
<ClCompile Include="Window\GSWnd.cpp" />
|
||||||
<ClCompile Include="Window\GSWndDX.cpp" />
|
<ClCompile Include="Window\GSWndDX.cpp" />
|
||||||
<ClCompile Include="Window\GSWndWGL.cpp" />
|
<ClCompile Include="Window\GSWndWGL.cpp" />
|
||||||
<ClCompile Include="PSX\GPU.cpp" />
|
|
||||||
<ClCompile Include="PSX\GPUDrawScanline.cpp" />
|
|
||||||
<ClCompile Include="PSX\GPUDrawScanlineCodeGenerator.cpp" />
|
|
||||||
<ClCompile Include="PSX\GPULocalMemory.cpp" />
|
|
||||||
<ClCompile Include="PSX\GPURenderer.cpp" />
|
|
||||||
<ClCompile Include="PSX\GPURendererSW.cpp" />
|
|
||||||
<ClCompile Include="PSX\GPUSettingsDlg.cpp" />
|
|
||||||
<ClCompile Include="PSX\GPUSetupPrimCodeGenerator.cpp" />
|
|
||||||
<ClCompile Include="PSX\GPUState.cpp" />
|
|
||||||
<ClCompile Include="stdafx.cpp">
|
<ClCompile Include="stdafx.cpp">
|
||||||
<PrecompiledHeader>Create</PrecompiledHeader>
|
<PrecompiledHeader>Create</PrecompiledHeader>
|
||||||
</ClCompile>
|
</ClCompile>
|
||||||
|
@ -248,18 +239,6 @@
|
||||||
<ClInclude Include="Window\GSWnd.h" />
|
<ClInclude Include="Window\GSWnd.h" />
|
||||||
<ClInclude Include="Window\GSWndDX.h" />
|
<ClInclude Include="Window\GSWndDX.h" />
|
||||||
<ClInclude Include="Window\GSWndWGL.h" />
|
<ClInclude Include="Window\GSWndWGL.h" />
|
||||||
<ClInclude Include="PSX\GPU.h" />
|
|
||||||
<ClInclude Include="PSX\GPUDrawingEnvironment.h" />
|
|
||||||
<ClInclude Include="PSX\GPUDrawScanline.h" />
|
|
||||||
<ClInclude Include="PSX\GPUDrawScanlineCodeGenerator.h" />
|
|
||||||
<ClInclude Include="PSX\GPULocalMemory.h" />
|
|
||||||
<ClInclude Include="PSX\GPURenderer.h" />
|
|
||||||
<ClInclude Include="PSX\GPURendererSW.h" />
|
|
||||||
<ClInclude Include="PSX\GPUScanlineEnvironment.h" />
|
|
||||||
<ClInclude Include="PSX\GPUSettingsDlg.h" />
|
|
||||||
<ClInclude Include="PSX\GPUSetupPrimCodeGenerator.h" />
|
|
||||||
<ClInclude Include="PSX\GPUState.h" />
|
|
||||||
<ClInclude Include="PSX\GPUVertex.h" />
|
|
||||||
<ClInclude Include="stdafx.h" />
|
<ClInclude Include="stdafx.h" />
|
||||||
<ClInclude Include="svnrev.h" />
|
<ClInclude Include="svnrev.h" />
|
||||||
<ClInclude Include="resource.h" />
|
<ClInclude Include="resource.h" />
|
||||||
|
|
|
@ -234,33 +234,6 @@
|
||||||
<ClCompile Include="GSPng.cpp">
|
<ClCompile Include="GSPng.cpp">
|
||||||
<Filter>Source Files</Filter>
|
<Filter>Source Files</Filter>
|
||||||
</ClCompile>
|
</ClCompile>
|
||||||
<ClCompile Include="PSX\GPU.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="PSX\GPUDrawScanline.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="PSX\GPUDrawScanlineCodeGenerator.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="PSX\GPULocalMemory.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="PSX\GPURenderer.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="PSX\GPURendererSW.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="PSX\GPUSettingsDlg.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="PSX\GPUSetupPrimCodeGenerator.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="PSX\GPUState.cpp">
|
|
||||||
<Filter>Source Files</Filter>
|
|
||||||
</ClCompile>
|
|
||||||
<ClCompile Include="GSLzma.cpp">
|
<ClCompile Include="GSLzma.cpp">
|
||||||
<Filter>Source Files</Filter>
|
<Filter>Source Files</Filter>
|
||||||
</ClCompile>
|
</ClCompile>
|
||||||
|
@ -497,42 +470,6 @@
|
||||||
<ClInclude Include="GSPng.h">
|
<ClInclude Include="GSPng.h">
|
||||||
<Filter>Header Files</Filter>
|
<Filter>Header Files</Filter>
|
||||||
</ClInclude>
|
</ClInclude>
|
||||||
<ClInclude Include="PSX\GPU.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="PSX\GPUDrawingEnvironment.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="PSX\GPUDrawScanline.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="PSX\GPUDrawScanlineCodeGenerator.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="PSX\GPULocalMemory.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="PSX\GPURenderer.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="PSX\GPURendererSW.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="PSX\GPUScanlineEnvironment.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="PSX\GPUSettingsDlg.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="PSX\GPUSetupPrimCodeGenerator.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="PSX\GPUState.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="PSX\GPUVertex.h">
|
|
||||||
<Filter>Header Files</Filter>
|
|
||||||
</ClInclude>
|
|
||||||
<ClInclude Include="GSThread_CXX11.h">
|
<ClInclude Include="GSThread_CXX11.h">
|
||||||
<Filter>Header Files</Filter>
|
<Filter>Header Files</Filter>
|
||||||
</ClInclude>
|
</ClInclude>
|
||||||
|
|
|
@ -1,352 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2007-2009 Gabest
|
|
||||||
* http://www.gabest.org
|
|
||||||
*
|
|
||||||
* 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; either version 2, 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 received a copy of the GNU General Public License
|
|
||||||
* along with GNU Make; see the file COPYING. If not, write to
|
|
||||||
* the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA USA.
|
|
||||||
* http://www.gnu.org/copyleft/gpl.html
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
|
|
||||||
#include "stdafx.h"
|
|
||||||
#include "GSdx.h"
|
|
||||||
#include "GSUtil.h"
|
|
||||||
#include "Renderers/Null/GSDeviceNull.h"
|
|
||||||
#include "GPURendererSW.h"
|
|
||||||
|
|
||||||
#ifdef _WIN32
|
|
||||||
|
|
||||||
#include "GPUSettingsDlg.h"
|
|
||||||
#include "Renderers/DX11/GSDevice11.h"
|
|
||||||
|
|
||||||
static HRESULT s_hr = E_FAIL;
|
|
||||||
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#define PSE_LT_GPU 2
|
|
||||||
|
|
||||||
static GPURenderer* s_gpu = NULL;
|
|
||||||
|
|
||||||
EXPORT_C_(uint32) PSEgetLibType()
|
|
||||||
{
|
|
||||||
return PSE_LT_GPU;
|
|
||||||
}
|
|
||||||
|
|
||||||
EXPORT_C_(const char*) PSEgetLibName()
|
|
||||||
{
|
|
||||||
return GSUtil::GetLibName();
|
|
||||||
}
|
|
||||||
|
|
||||||
EXPORT_C_(uint32) PSEgetLibVersion()
|
|
||||||
{
|
|
||||||
static const uint32 version = 1;
|
|
||||||
static const uint32 revision = 1;
|
|
||||||
|
|
||||||
return version << 16 | revision << 8 | PLUGIN_VERSION;
|
|
||||||
}
|
|
||||||
|
|
||||||
static void InitVectors()
|
|
||||||
{
|
|
||||||
GSVector4i::InitVectors();
|
|
||||||
GSVector4::InitVectors();
|
|
||||||
#if _M_SSE >= 0x500
|
|
||||||
GSVector8::InitVectors();
|
|
||||||
#endif
|
|
||||||
#if _M_SSE >= 0x501
|
|
||||||
GSVector8i::InitVectors();
|
|
||||||
#endif
|
|
||||||
|
|
||||||
GPUDrawScanlineCodeGenerator::InitVectors();
|
|
||||||
GPULocalMemory::InitVectors();
|
|
||||||
GPUSetupPrimCodeGenerator::InitVectors();
|
|
||||||
}
|
|
||||||
|
|
||||||
EXPORT_C_(int32) GPUinit()
|
|
||||||
{
|
|
||||||
if(!GSUtil::CheckSSE())
|
|
||||||
{
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
theApp.Init();
|
|
||||||
|
|
||||||
InitVectors();
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
EXPORT_C_(int32) GPUshutdown()
|
|
||||||
{
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
EXPORT_C_(int32) GPUclose()
|
|
||||||
{
|
|
||||||
delete s_gpu;
|
|
||||||
|
|
||||||
s_gpu = NULL;
|
|
||||||
|
|
||||||
#ifdef _WIN32
|
|
||||||
GSDevice11::FreeD3DCompiler();
|
|
||||||
|
|
||||||
if(SUCCEEDED(s_hr))
|
|
||||||
{
|
|
||||||
::CoUninitialize();
|
|
||||||
|
|
||||||
s_hr = E_FAIL;
|
|
||||||
}
|
|
||||||
|
|
||||||
#endif
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
EXPORT_C_(int32) GPUopen(void* hWnd)
|
|
||||||
{
|
|
||||||
GPUclose();
|
|
||||||
|
|
||||||
if(!GSUtil::CheckSSE())
|
|
||||||
{
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
#ifdef _WIN32
|
|
||||||
|
|
||||||
s_hr = ::CoInitializeEx(NULL, COINIT_MULTITHREADED);
|
|
||||||
|
|
||||||
if(!GSUtil::CheckDirectX())
|
|
||||||
{
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!GSDevice11::LoadD3DCompiler())
|
|
||||||
return -1;
|
|
||||||
#endif
|
|
||||||
|
|
||||||
GPURendererType renderer = static_cast<GPURendererType>(theApp.GetConfigI("Renderer"));
|
|
||||||
int threads = theApp.GetConfigI("extrathreads");
|
|
||||||
|
|
||||||
switch(renderer)
|
|
||||||
{
|
|
||||||
#ifdef _WIN32
|
|
||||||
case GPURendererType::D3D11_SW: s_gpu = new GPURendererSW(new GSDevice11(), threads); break;
|
|
||||||
#endif
|
|
||||||
case GPURendererType::NULL_Renderer: s_gpu = new GPURendererSW(new GSDeviceNull(), threads); break;
|
|
||||||
default: // Fall back to D3D11/Null mode if unknown value is read. No one could possibly enter here anyway.
|
|
||||||
#ifdef _WIN32
|
|
||||||
s_gpu = new GPURendererSW(new GSDevice11(), threads); break;
|
|
||||||
#else
|
|
||||||
s_gpu = new GPURendererSW(new GSDeviceNull(), threads); break;
|
|
||||||
#endif
|
|
||||||
}
|
|
||||||
|
|
||||||
if(!s_gpu->Create(hWnd))
|
|
||||||
{
|
|
||||||
GPUclose();
|
|
||||||
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
EXPORT_C_(int32) GPUconfigure()
|
|
||||||
{
|
|
||||||
if(!GSUtil::CheckSSE())
|
|
||||||
{
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
theApp.Init();
|
|
||||||
|
|
||||||
#ifdef _WIN32
|
|
||||||
|
|
||||||
GPUSettingsDlg dlg;
|
|
||||||
|
|
||||||
if(IDOK == dlg.DoModal())
|
|
||||||
{
|
|
||||||
GPUshutdown();
|
|
||||||
GPUinit();
|
|
||||||
}
|
|
||||||
|
|
||||||
#else
|
|
||||||
|
|
||||||
// TODO: linux
|
|
||||||
#endif
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
EXPORT_C_(int32) GPUtest()
|
|
||||||
{
|
|
||||||
if(!GSUtil::CheckSSE())
|
|
||||||
{
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
EXPORT_C GPUabout()
|
|
||||||
{
|
|
||||||
// TODO
|
|
||||||
}
|
|
||||||
|
|
||||||
EXPORT_C GPUwriteDataMem(const uint8* mem, uint32 size)
|
|
||||||
{
|
|
||||||
s_gpu->WriteData(mem, size);
|
|
||||||
}
|
|
||||||
|
|
||||||
EXPORT_C GPUwriteData(uint32 data)
|
|
||||||
{
|
|
||||||
s_gpu->WriteData((uint8*)&data, 1);
|
|
||||||
}
|
|
||||||
|
|
||||||
EXPORT_C GPUreadDataMem(uint8* mem, uint32 size)
|
|
||||||
{
|
|
||||||
s_gpu->ReadData(mem, size);
|
|
||||||
}
|
|
||||||
|
|
||||||
EXPORT_C_(uint32) GPUreadData()
|
|
||||||
{
|
|
||||||
uint32 data = 0;
|
|
||||||
|
|
||||||
s_gpu->ReadData((uint8*)&data, 1);
|
|
||||||
|
|
||||||
return data;
|
|
||||||
}
|
|
||||||
|
|
||||||
EXPORT_C GPUwriteStatus(uint32 status)
|
|
||||||
{
|
|
||||||
s_gpu->WriteStatus(status);
|
|
||||||
}
|
|
||||||
|
|
||||||
EXPORT_C_(uint32) GPUreadStatus()
|
|
||||||
{
|
|
||||||
return s_gpu->ReadStatus();
|
|
||||||
}
|
|
||||||
|
|
||||||
EXPORT_C_(uint32) GPUdmaChain(const uint8* mem, uint32 addr)
|
|
||||||
{
|
|
||||||
uint32 last[3];
|
|
||||||
|
|
||||||
memset(last, 0xff, sizeof(last));
|
|
||||||
|
|
||||||
do
|
|
||||||
{
|
|
||||||
if(addr == last[1] || addr == last[2])
|
|
||||||
{
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
(addr < last[0] ? last[1] : last[2]) = addr;
|
|
||||||
|
|
||||||
last[0] = addr;
|
|
||||||
|
|
||||||
uint8 size = mem[addr + 3];
|
|
||||||
|
|
||||||
if(size > 0)
|
|
||||||
{
|
|
||||||
s_gpu->WriteData(&mem[addr + 4], size);
|
|
||||||
}
|
|
||||||
|
|
||||||
addr = *(uint32*)&mem[addr] & 0xffffff;
|
|
||||||
}
|
|
||||||
while(addr != 0xffffff);
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
EXPORT_C_(uint32) GPUgetMode()
|
|
||||||
{
|
|
||||||
// TODO
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
EXPORT_C GPUsetMode(uint32 mode)
|
|
||||||
{
|
|
||||||
// TODO
|
|
||||||
}
|
|
||||||
|
|
||||||
EXPORT_C GPUupdateLace()
|
|
||||||
{
|
|
||||||
s_gpu->VSync();
|
|
||||||
}
|
|
||||||
|
|
||||||
EXPORT_C GPUmakeSnapshot()
|
|
||||||
{
|
|
||||||
s_gpu->MakeSnapshot("c:/"); // TODO
|
|
||||||
}
|
|
||||||
|
|
||||||
EXPORT_C GPUdisplayText(char* text)
|
|
||||||
{
|
|
||||||
// TODO
|
|
||||||
}
|
|
||||||
|
|
||||||
EXPORT_C GPUdisplayFlags(uint32 flags)
|
|
||||||
{
|
|
||||||
// TODO
|
|
||||||
}
|
|
||||||
|
|
||||||
EXPORT_C_(int32) GPUfreeze(uint32 type, GPUFreezeData* data)
|
|
||||||
{
|
|
||||||
if(!data || data->version != 1)
|
|
||||||
{
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
if(type == 0)
|
|
||||||
{
|
|
||||||
s_gpu->Defrost(data);
|
|
||||||
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
else if(type == 1)
|
|
||||||
{
|
|
||||||
s_gpu->Freeze(data);
|
|
||||||
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
else if(type == 2)
|
|
||||||
{
|
|
||||||
int slot = *(int*)data + 1;
|
|
||||||
|
|
||||||
if(slot < 1 || slot > 9)
|
|
||||||
{
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
// TODO
|
|
||||||
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
EXPORT_C GPUgetScreenPic(uint8* mem)
|
|
||||||
{
|
|
||||||
// TODO
|
|
||||||
}
|
|
||||||
|
|
||||||
EXPORT_C GPUshowScreenPic(uint8* mem)
|
|
||||||
{
|
|
||||||
// TODO
|
|
||||||
}
|
|
||||||
|
|
||||||
EXPORT_C GPUcursor(int player, int x, int y)
|
|
||||||
{
|
|
||||||
// TODO
|
|
||||||
}
|
|
|
@ -1,282 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2007-2009 Gabest
|
|
||||||
* http://www.gabest.org
|
|
||||||
*
|
|
||||||
* 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; either version 2, 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 received a copy of the GNU General Public License
|
|
||||||
* along with GNU Make; see the file COPYING. If not, write to
|
|
||||||
* the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA USA.
|
|
||||||
* http://www.gnu.org/copyleft/gpl.html
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
|
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#pragma pack(push, 1)
|
|
||||||
|
|
||||||
#include "GS.h"
|
|
||||||
|
|
||||||
enum
|
|
||||||
{
|
|
||||||
GPU_POLYGON = 1,
|
|
||||||
GPU_LINE = 2,
|
|
||||||
GPU_SPRITE = 3,
|
|
||||||
};
|
|
||||||
|
|
||||||
REG32_(GPUReg, STATUS)
|
|
||||||
uint32 TX:4;
|
|
||||||
uint32 TY:1;
|
|
||||||
uint32 ABR:2;
|
|
||||||
uint32 TP:2;
|
|
||||||
uint32 DTD:1;
|
|
||||||
uint32 DFE:1;
|
|
||||||
uint32 MD:1;
|
|
||||||
uint32 ME:1;
|
|
||||||
uint32 _PAD0:3;
|
|
||||||
uint32 WIDTH1:1;
|
|
||||||
uint32 WIDTH0:2;
|
|
||||||
uint32 HEIGHT:1;
|
|
||||||
uint32 ISPAL:1;
|
|
||||||
uint32 ISRGB24:1;
|
|
||||||
uint32 ISINTER:1;
|
|
||||||
uint32 DEN:1;
|
|
||||||
uint32 _PAD1:2;
|
|
||||||
uint32 IDLE:1;
|
|
||||||
uint32 IMG:1;
|
|
||||||
uint32 COM:1;
|
|
||||||
uint32 DMA:2;
|
|
||||||
uint32 LCF:1;
|
|
||||||
/*
|
|
||||||
uint32 TX:4;
|
|
||||||
uint32 TY:1;
|
|
||||||
uint32 ABR:2;
|
|
||||||
uint32 TP:2;
|
|
||||||
uint32 DTD:1;
|
|
||||||
uint32 DFE:1;
|
|
||||||
uint32 PBW:1;
|
|
||||||
uint32 PBC:1;
|
|
||||||
uint32 _PAD0:3;
|
|
||||||
uint32 HRES2:1;
|
|
||||||
uint32 HRES1:2;
|
|
||||||
uint32 VRES:1;
|
|
||||||
uint32 ISPAL:1;
|
|
||||||
uint32 ISRGB24:1;
|
|
||||||
uint32 ISINTER:1;
|
|
||||||
uint32 ISSTOP:1;
|
|
||||||
uint32 _PAD1:1;
|
|
||||||
uint32 DMARDY:1;
|
|
||||||
uint32 IDIDLE:1;
|
|
||||||
uint32 DATARDY:1;
|
|
||||||
uint32 ISEMPTY:1;
|
|
||||||
uint32 TMODE:2;
|
|
||||||
uint32 ODE:1;
|
|
||||||
*/
|
|
||||||
REG_END
|
|
||||||
|
|
||||||
REG32_(GPUReg, PACKET)
|
|
||||||
uint32 _PAD:24;
|
|
||||||
uint32 OPTION:5;
|
|
||||||
uint32 TYPE:3;
|
|
||||||
REG_END
|
|
||||||
|
|
||||||
REG32_(GPUReg, PRIM)
|
|
||||||
uint32 VTX:24;
|
|
||||||
uint32 TGE:1;
|
|
||||||
uint32 ABE:1;
|
|
||||||
uint32 TME:1;
|
|
||||||
uint32 _PAD2:1;
|
|
||||||
uint32 IIP:1;
|
|
||||||
uint32 TYPE:3;
|
|
||||||
REG_END
|
|
||||||
|
|
||||||
REG32_(GPUReg, POLYGON)
|
|
||||||
uint32 _PAD:24;
|
|
||||||
uint32 TGE:1;
|
|
||||||
uint32 ABE:1;
|
|
||||||
uint32 TME:1;
|
|
||||||
uint32 VTX:1;
|
|
||||||
uint32 IIP:1;
|
|
||||||
uint32 TYPE:3;
|
|
||||||
REG_END
|
|
||||||
|
|
||||||
REG32_(GPUReg, LINE)
|
|
||||||
uint32 _PAD:24;
|
|
||||||
uint32 ZERO1:1;
|
|
||||||
uint32 ABE:1;
|
|
||||||
uint32 ZERO2:1;
|
|
||||||
uint32 PLL:1;
|
|
||||||
uint32 IIP:1;
|
|
||||||
uint32 TYPE:3;
|
|
||||||
REG_END
|
|
||||||
|
|
||||||
REG32_(GPUReg, SPRITE)
|
|
||||||
uint32 _PAD:24;
|
|
||||||
uint32 ZERO:1;
|
|
||||||
uint32 ABE:1;
|
|
||||||
uint32 TME:1;
|
|
||||||
uint32 SIZE:2;
|
|
||||||
uint32 TYPE:3;
|
|
||||||
REG_END
|
|
||||||
|
|
||||||
REG32_(GPUReg, RESET)
|
|
||||||
uint32 _PAD:32;
|
|
||||||
REG_END
|
|
||||||
|
|
||||||
REG32_(GPUReg, DEN)
|
|
||||||
uint32 DEN:1;
|
|
||||||
uint32 _PAD:31;
|
|
||||||
REG_END
|
|
||||||
|
|
||||||
REG32_(GPUReg, DMA)
|
|
||||||
uint32 DMA:2;
|
|
||||||
uint32 _PAD:30;
|
|
||||||
REG_END
|
|
||||||
|
|
||||||
REG32_(GPUReg, DAREA)
|
|
||||||
uint32 X:10;
|
|
||||||
uint32 Y:9;
|
|
||||||
uint32 _PAD:13;
|
|
||||||
REG_END
|
|
||||||
|
|
||||||
REG32_(GPUReg, DHRANGE)
|
|
||||||
uint32 X1:12;
|
|
||||||
uint32 X2:12;
|
|
||||||
uint32 _PAD:8;
|
|
||||||
REG_END
|
|
||||||
|
|
||||||
REG32_(GPUReg, DVRANGE)
|
|
||||||
uint32 Y1:10;
|
|
||||||
uint32 Y2:11;
|
|
||||||
uint32 _PAD:11;
|
|
||||||
REG_END
|
|
||||||
|
|
||||||
REG32_(GPUReg, DMODE)
|
|
||||||
uint32 WIDTH0:2;
|
|
||||||
uint32 HEIGHT:1;
|
|
||||||
uint32 ISPAL:1;
|
|
||||||
uint32 ISRGB24:1;
|
|
||||||
uint32 ISINTER:1;
|
|
||||||
uint32 WIDTH1:1;
|
|
||||||
uint32 REVERSE:1;
|
|
||||||
uint32 _PAD:24;
|
|
||||||
REG_END
|
|
||||||
|
|
||||||
REG32_(GPUReg, GPUINFO)
|
|
||||||
uint32 PARAM:24;
|
|
||||||
uint32 _PAD:8;
|
|
||||||
REG_END
|
|
||||||
|
|
||||||
REG32_(GPUReg, MODE)
|
|
||||||
uint32 TX:4;
|
|
||||||
uint32 TY:1;
|
|
||||||
uint32 ABR:2;
|
|
||||||
uint32 TP:2;
|
|
||||||
uint32 DTD:1;
|
|
||||||
uint32 DFE:1;
|
|
||||||
uint32 _PAD:21;
|
|
||||||
REG_END
|
|
||||||
|
|
||||||
REG32_(GPUReg, MASK)
|
|
||||||
uint32 MD:1;
|
|
||||||
uint32 ME:1;
|
|
||||||
uint32 _PAD:30;
|
|
||||||
REG_END
|
|
||||||
|
|
||||||
REG32_(GPUReg, DRAREA)
|
|
||||||
uint32 X:10;
|
|
||||||
uint32 Y:10;
|
|
||||||
uint32 _PAD:12;
|
|
||||||
REG_END
|
|
||||||
|
|
||||||
REG32_(GPUReg, DROFF)
|
|
||||||
int32 X:11;
|
|
||||||
int32 Y:11;
|
|
||||||
int32 _PAD:10;
|
|
||||||
REG_END
|
|
||||||
|
|
||||||
REG32_(GPUReg, RGB)
|
|
||||||
uint32 R:8;
|
|
||||||
uint32 G:8;
|
|
||||||
uint32 B:8;
|
|
||||||
uint32 _PAD:8;
|
|
||||||
REG_END
|
|
||||||
|
|
||||||
REG32_(GPUReg, XY)
|
|
||||||
int32 X:11;
|
|
||||||
int32 _PAD1:5;
|
|
||||||
int32 Y:11;
|
|
||||||
int32 _PAD2:5;
|
|
||||||
REG_END
|
|
||||||
|
|
||||||
REG32_(GPUReg, UV)
|
|
||||||
uint32 U:8;
|
|
||||||
uint32 V:8;
|
|
||||||
uint32 _PAD:16;
|
|
||||||
REG_END
|
|
||||||
|
|
||||||
REG32_(GPUReg, TWIN)
|
|
||||||
uint32 TWW:5;
|
|
||||||
uint32 TWH:5;
|
|
||||||
uint32 TWX:5;
|
|
||||||
uint32 TWY:5;
|
|
||||||
uint32 _PAD:12;
|
|
||||||
REG_END
|
|
||||||
|
|
||||||
REG32_(GPUReg, CLUT)
|
|
||||||
uint32 _PAD1:16;
|
|
||||||
uint32 X:6;
|
|
||||||
uint32 Y:9;
|
|
||||||
uint32 _PAD2:1;
|
|
||||||
REG_END
|
|
||||||
|
|
||||||
REG32_SET(GPUReg)
|
|
||||||
GPURegSTATUS STATUS;
|
|
||||||
GPURegPACKET PACKET;
|
|
||||||
GPURegPRIM PRIM;
|
|
||||||
GPURegPOLYGON POLYGON;
|
|
||||||
GPURegLINE LINE;
|
|
||||||
GPURegSPRITE SPRITE;
|
|
||||||
GPURegRESET RESET;
|
|
||||||
GPURegDEN DEN;
|
|
||||||
GPURegDMA DMA;
|
|
||||||
GPURegDAREA DAREA;
|
|
||||||
GPURegDHRANGE DHRANGE;
|
|
||||||
GPURegDVRANGE DVRANGE;
|
|
||||||
GPURegDMODE DMODE;
|
|
||||||
GPURegGPUINFO GPUINFO;
|
|
||||||
GPURegMODE MODE;
|
|
||||||
GPURegMASK MASK;
|
|
||||||
GPURegDRAREA DRAREA;
|
|
||||||
GPURegDROFF DROFF;
|
|
||||||
GPURegRGB RGB;
|
|
||||||
GPURegXY XY;
|
|
||||||
GPURegUV UV;
|
|
||||||
GPURegTWIN TWIN;
|
|
||||||
GPURegCLUT CLUT;
|
|
||||||
REG_SET_END
|
|
||||||
|
|
||||||
enum class GPURendererType : int8
|
|
||||||
{
|
|
||||||
D3D11_SW = 1,
|
|
||||||
NULL_Renderer = 2,
|
|
||||||
};
|
|
||||||
|
|
||||||
struct GPUFreezeData
|
|
||||||
{
|
|
||||||
uint32 version; // == 1
|
|
||||||
uint32 status;
|
|
||||||
uint32 control[256];
|
|
||||||
uint16 vram[1024 * 1024];
|
|
||||||
};
|
|
||||||
|
|
||||||
#pragma pack(pop)
|
|
||||||
|
|
|
@ -1,491 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2007-2009 Gabest
|
|
||||||
* http://www.gabest.org
|
|
||||||
*
|
|
||||||
* 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; either version 2, 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 received a copy of the GNU General Public License
|
|
||||||
* along with GNU Make; see the file COPYING. If not, write to
|
|
||||||
* the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA USA.
|
|
||||||
* http://www.gnu.org/copyleft/gpl.html
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
|
|
||||||
#include "stdafx.h"
|
|
||||||
#include "GPUDrawScanline.h"
|
|
||||||
|
|
||||||
GPUDrawScanline::GPUDrawScanline()
|
|
||||||
: m_sp_map("GPUSetupPrim", &m_local)
|
|
||||||
, m_ds_map("GPUDrawScanline", &m_local)
|
|
||||||
{
|
|
||||||
memset(&m_local, 0, sizeof(m_local));
|
|
||||||
|
|
||||||
m_local.gd = &m_global;
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPUDrawScanline::BeginDraw(const GSRasterizerData* data)
|
|
||||||
{
|
|
||||||
memcpy(&m_global, &((const SharedData*)data)->global, sizeof(m_global));
|
|
||||||
|
|
||||||
if(m_global.sel.tme && m_global.sel.twin)
|
|
||||||
{
|
|
||||||
uint32 u, v;
|
|
||||||
|
|
||||||
u = ~(m_global.twin.x << 3) & 0xff; // TWW
|
|
||||||
v = ~(m_global.twin.y << 3) & 0xff; // TWH
|
|
||||||
|
|
||||||
m_local.twin[0].u = GSVector4i((u << 16) | u);
|
|
||||||
m_local.twin[0].v = GSVector4i((v << 16) | v);
|
|
||||||
|
|
||||||
u = m_global.twin.z << 3; // TWX
|
|
||||||
v = m_global.twin.w << 3; // TWY
|
|
||||||
|
|
||||||
m_local.twin[1].u = GSVector4i((u << 16) | u) & ~m_local.twin[0].u;
|
|
||||||
m_local.twin[1].v = GSVector4i((v << 16) | v) & ~m_local.twin[0].v;
|
|
||||||
}
|
|
||||||
|
|
||||||
m_ds = m_ds_map[m_global.sel];
|
|
||||||
|
|
||||||
m_de = NULL;
|
|
||||||
|
|
||||||
m_dr = NULL; // TODO
|
|
||||||
|
|
||||||
// doesn't need all bits => less functions generated
|
|
||||||
|
|
||||||
GPUScanlineSelector sel;
|
|
||||||
|
|
||||||
sel.key = 0;
|
|
||||||
|
|
||||||
sel.iip = m_global.sel.iip;
|
|
||||||
sel.tfx = m_global.sel.tfx;
|
|
||||||
sel.twin = m_global.sel.twin;
|
|
||||||
sel.sprite = m_global.sel.sprite;
|
|
||||||
|
|
||||||
m_sp = m_sp_map[sel];
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPUDrawScanline::EndDraw(uint64 frame, uint64 ticks, int actual, int total)
|
|
||||||
{
|
|
||||||
m_ds_map.UpdateStats(frame, ticks, actual, total);
|
|
||||||
}
|
|
||||||
|
|
||||||
#ifndef ENABLE_JIT_RASTERIZER
|
|
||||||
|
|
||||||
void GPUDrawScanline::SetupPrim(const GSVertexSW* vertex, const uint32* index, const GSVertexSW& dscan)
|
|
||||||
{
|
|
||||||
GPUScanlineSelector sel = m_global.sel;
|
|
||||||
|
|
||||||
const GSVector4* shift = GPUSetupPrimCodeGenerator::m_shift;
|
|
||||||
|
|
||||||
if(sel.tme && !sel.twin)
|
|
||||||
{
|
|
||||||
if(sel.sprite)
|
|
||||||
{
|
|
||||||
GSVector4i t = (GSVector4i(vertex[index[1]].t) >> 8) - GSVector4i::x00000001();
|
|
||||||
|
|
||||||
t = t.ps32(t);
|
|
||||||
t = t.upl16(t);
|
|
||||||
|
|
||||||
m_local.twin[2].u = t.xxxx();
|
|
||||||
m_local.twin[2].v = t.yyyy();
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
// TODO: not really needed
|
|
||||||
|
|
||||||
m_local.twin[2].u = GSVector4i::x00ff();
|
|
||||||
m_local.twin[2].v = GSVector4i::x00ff();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if(sel.tme || sel.iip && sel.tfx != 3)
|
|
||||||
{
|
|
||||||
GSVector4 dt = dscan.t;
|
|
||||||
GSVector4 dc = dscan.c;
|
|
||||||
|
|
||||||
GSVector4i dtc8 = GSVector4i(dt * shift[0]).ps32(GSVector4i(dc * shift[0]));
|
|
||||||
|
|
||||||
if(sel.tme)
|
|
||||||
{
|
|
||||||
m_local.d8.st = dtc8.upl16(dtc8);
|
|
||||||
}
|
|
||||||
|
|
||||||
if(sel.iip && sel.tfx != 3)
|
|
||||||
{
|
|
||||||
m_local.d8.c = dtc8.uph16(dtc8);
|
|
||||||
}
|
|
||||||
|
|
||||||
if(sel.tme)
|
|
||||||
{
|
|
||||||
GSVector4 dtx = dt.xxxx();
|
|
||||||
GSVector4 dty = dt.yyyy();
|
|
||||||
|
|
||||||
m_local.d.s = GSVector4i(dtx * shift[1]).ps32(GSVector4i(dtx * shift[2]));
|
|
||||||
m_local.d.t = GSVector4i(dty * shift[1]).ps32(GSVector4i(dty * shift[2]));
|
|
||||||
}
|
|
||||||
|
|
||||||
if(sel.iip && sel.tfx != 3)
|
|
||||||
{
|
|
||||||
GSVector4 dcx = dc.xxxx();
|
|
||||||
GSVector4 dcy = dc.yyyy();
|
|
||||||
GSVector4 dcz = dc.zzzz();
|
|
||||||
|
|
||||||
m_local.d.r = GSVector4i(dcx * shift[1]).ps32(GSVector4i(dcx * shift[2]));
|
|
||||||
m_local.d.g = GSVector4i(dcy * shift[1]).ps32(GSVector4i(dcy * shift[2]));
|
|
||||||
m_local.d.b = GSVector4i(dcz * shift[1]).ps32(GSVector4i(dcz * shift[2]));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPUDrawScanline::DrawScanline(int pixels, int left, int top, const GSVertexSW& scan)
|
|
||||||
{
|
|
||||||
// TODO: not tested yet, probably bogus
|
|
||||||
|
|
||||||
GPUScanlineSelector sel = m_global.sel;
|
|
||||||
|
|
||||||
GSVector4i s, t;
|
|
||||||
GSVector4i uf, vf;
|
|
||||||
GSVector4i rf, gf, bf;
|
|
||||||
GSVector4i dither;
|
|
||||||
|
|
||||||
// Init
|
|
||||||
|
|
||||||
uint16* fb = (uint16*)m_global.vm + (top << (10 + sel.scalex)) + left;
|
|
||||||
|
|
||||||
int steps = pixels - 8;
|
|
||||||
|
|
||||||
if(sel.dtd)
|
|
||||||
{
|
|
||||||
dither = GSVector4i::load<false>(&GPUDrawScanlineCodeGenerator::m_dither[top & 3][left & 3]);
|
|
||||||
}
|
|
||||||
|
|
||||||
if(sel.tme)
|
|
||||||
{
|
|
||||||
GSVector4i vt = GSVector4i(scan.t).xxzzl();
|
|
||||||
|
|
||||||
s = vt.xxxx().add16(m_local.d.s);
|
|
||||||
t = vt.yyyy();
|
|
||||||
|
|
||||||
if(!sel.sprite)
|
|
||||||
{
|
|
||||||
t = t.add16(m_local.d.t);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
if(sel.ltf)
|
|
||||||
{
|
|
||||||
vf = t.sll16(1).srl16(1);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if(sel.tfx != 3)
|
|
||||||
{
|
|
||||||
GSVector4i vc = GSVector4i(scan.c).xxzzlh();
|
|
||||||
|
|
||||||
rf = vc.xxxx();
|
|
||||||
gf = vc.yyyy();
|
|
||||||
bf = vc.zzzz();
|
|
||||||
|
|
||||||
if(sel.iip)
|
|
||||||
{
|
|
||||||
rf = rf.add16(m_local.d.r);
|
|
||||||
gf = gf.add16(m_local.d.g);
|
|
||||||
bf = bf.add16(m_local.d.b);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
while(1)
|
|
||||||
{
|
|
||||||
do
|
|
||||||
{
|
|
||||||
GSVector4i test = GPUDrawScanlineCodeGenerator::m_test[7 + (steps & (steps >> 31))];
|
|
||||||
|
|
||||||
GSVector4i fd = GSVector4i::load(fb, fb + 8);
|
|
||||||
|
|
||||||
GSVector4i r, g, b, a;
|
|
||||||
|
|
||||||
// TestMask
|
|
||||||
|
|
||||||
if(sel.me)
|
|
||||||
{
|
|
||||||
test |= fd.sra16(15);
|
|
||||||
|
|
||||||
if(test.alltrue()) continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
// SampleTexture
|
|
||||||
|
|
||||||
if(sel.tme)
|
|
||||||
{
|
|
||||||
GSVector4i u0, v0, u1, v1;
|
|
||||||
GSVector4i addr00, addr01, addr10, addr11;
|
|
||||||
GSVector4i c00, c01, c10, c11;
|
|
||||||
|
|
||||||
if(sel.ltf)
|
|
||||||
{
|
|
||||||
u0 = s.sub16(GSVector4i(0x00200020)); // - 0.125f
|
|
||||||
v0 = t.sub16(GSVector4i(0x00200020)); // - 0.125f
|
|
||||||
|
|
||||||
uf = u0.sll16(8).srl16(1);
|
|
||||||
vf = v0.sll16(8).srl16(1);;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
u0 = s;
|
|
||||||
v0 = t;
|
|
||||||
}
|
|
||||||
|
|
||||||
u0 = u0.srl16(8);
|
|
||||||
v0 = v0.srl16(8);
|
|
||||||
|
|
||||||
if(sel.ltf)
|
|
||||||
{
|
|
||||||
u1 = u0.add16(GSVector4i::x0001());
|
|
||||||
v1 = v0.add16(GSVector4i::x0001());
|
|
||||||
|
|
||||||
if(sel.twin)
|
|
||||||
{
|
|
||||||
u0 = (u0 & m_local.twin[0].u).add16(m_local.twin[1].u);
|
|
||||||
v0 = (v0 & m_local.twin[0].v).add16(m_local.twin[1].v);
|
|
||||||
u1 = (u1 & m_local.twin[0].u).add16(m_local.twin[1].u);
|
|
||||||
v1 = (v1 & m_local.twin[0].v).add16(m_local.twin[1].v);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
u0 = u0.min_i16(m_local.twin[2].u);
|
|
||||||
v0 = v0.min_i16(m_local.twin[2].v);
|
|
||||||
u1 = u1.min_i16(m_local.twin[2].u);
|
|
||||||
v1 = v1.min_i16(m_local.twin[2].v);
|
|
||||||
}
|
|
||||||
|
|
||||||
addr00 = v0.sll16(8) | u0;
|
|
||||||
addr01 = v0.sll16(8) | u1;
|
|
||||||
addr10 = v1.sll16(8) | u0;
|
|
||||||
addr11 = v1.sll16(8) | u1;
|
|
||||||
|
|
||||||
// TODO
|
|
||||||
|
|
||||||
if(sel.tlu)
|
|
||||||
{
|
|
||||||
c00 = addr00.gather16_16((const uint16*)m_global.vm, m_global.clut);
|
|
||||||
c01 = addr01.gather16_16((const uint16*)m_global.vm, m_global.clut);
|
|
||||||
c10 = addr10.gather16_16((const uint16*)m_global.vm, m_global.clut);
|
|
||||||
c11 = addr11.gather16_16((const uint16*)m_global.vm, m_global.clut);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
c00 = addr00.gather16_16((const uint16*)m_global.vm);
|
|
||||||
c01 = addr01.gather16_16((const uint16*)m_global.vm);
|
|
||||||
c10 = addr10.gather16_16((const uint16*)m_global.vm);
|
|
||||||
c11 = addr11.gather16_16((const uint16*)m_global.vm);
|
|
||||||
}
|
|
||||||
|
|
||||||
GSVector4i r00 = c00.sll16(11).srl16(8);
|
|
||||||
GSVector4i r01 = c01.sll16(11).srl16(8);
|
|
||||||
GSVector4i r10 = c10.sll16(11).srl16(8);
|
|
||||||
GSVector4i r11 = c11.sll16(11).srl16(8);
|
|
||||||
|
|
||||||
r00 = r00.lerp16<0>(r01, uf);
|
|
||||||
r10 = r10.lerp16<0>(r11, uf);
|
|
||||||
|
|
||||||
GSVector4i g00 = c00.sll16(6).srl16(11).sll16(3);
|
|
||||||
GSVector4i g01 = c01.sll16(6).srl16(11).sll16(3);
|
|
||||||
GSVector4i g10 = c10.sll16(6).srl16(11).sll16(3);
|
|
||||||
GSVector4i g11 = c11.sll16(6).srl16(11).sll16(3);
|
|
||||||
|
|
||||||
g00 = g00.lerp16<0>(g01, uf);
|
|
||||||
g10 = g10.lerp16<0>(g11, uf);
|
|
||||||
|
|
||||||
GSVector4i b00 = c00.sll16(1).srl16(11).sll16(3);
|
|
||||||
GSVector4i b01 = c01.sll16(1).srl16(11).sll16(3);
|
|
||||||
GSVector4i b10 = c10.sll16(1).srl16(11).sll16(3);
|
|
||||||
GSVector4i b11 = c11.sll16(1).srl16(11).sll16(3);
|
|
||||||
|
|
||||||
b00 = b00.lerp16<0>(b01, uf);
|
|
||||||
b10 = b10.lerp16<0>(b11, uf);
|
|
||||||
|
|
||||||
GSVector4i a00 = c00.sra16(15).sll16(8);
|
|
||||||
GSVector4i a01 = c01.sra16(15).sll16(8);
|
|
||||||
GSVector4i a10 = c10.sra16(15).sll16(8);
|
|
||||||
GSVector4i a11 = c11.sra16(15).sll16(8);
|
|
||||||
|
|
||||||
a00 = a00.lerp16<0>(a01, uf);
|
|
||||||
a10 = a10.lerp16<0>(a11, uf);
|
|
||||||
|
|
||||||
r = r00.lerp16<0>(r10, vf);
|
|
||||||
g = g00.lerp16<0>(g10, vf);
|
|
||||||
b = b00.lerp16<0>(b10, vf);
|
|
||||||
a = a00.lerp16<0>(a10, vf);
|
|
||||||
|
|
||||||
test |= (r | g | b | a).eq16(GSVector4i::zero()); // mask out blank pixels (not perfect)
|
|
||||||
|
|
||||||
a = a.gt16(GSVector4i::zero());
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
if(sel.twin)
|
|
||||||
{
|
|
||||||
u0 = (u0 & m_local.twin[0].u).add16(m_local.twin[1].u);
|
|
||||||
v0 = (v0 & m_local.twin[0].v).add16(m_local.twin[1].v);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
u0 = u0.min_i16(m_local.twin[2].u);
|
|
||||||
v0 = v0.min_i16(m_local.twin[2].v);
|
|
||||||
}
|
|
||||||
|
|
||||||
addr00 = v0.sll16(8) | u0;
|
|
||||||
|
|
||||||
// TODO
|
|
||||||
|
|
||||||
if(sel.tlu)
|
|
||||||
{
|
|
||||||
c00 = addr00.gather16_16((const uint16*)m_global.vm, m_global.clut);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
c00 = addr00.gather16_16((const uint16*)m_global.vm);
|
|
||||||
}
|
|
||||||
|
|
||||||
r = (c00 << 3) & 0x00f800f8;
|
|
||||||
g = (c00 >> 2) & 0x00f800f8;
|
|
||||||
b = (c00 >> 7) & 0x00f800f8;
|
|
||||||
a = c00.sra16(15);
|
|
||||||
|
|
||||||
test |= c00.eq16(GSVector4i::zero()); // mask out blank pixels
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// ColorTFX
|
|
||||||
|
|
||||||
switch(sel.tfx)
|
|
||||||
{
|
|
||||||
case 0: // none (tfx = 0)
|
|
||||||
case 1: // none (tfx = tge)
|
|
||||||
r = rf.srl16(7);
|
|
||||||
g = gf.srl16(7);
|
|
||||||
b = bf.srl16(7);
|
|
||||||
break;
|
|
||||||
case 2: // modulate (tfx = tme | tge)
|
|
||||||
r = r.modulate16<1>(rf).clamp8();
|
|
||||||
g = g.modulate16<1>(gf).clamp8();
|
|
||||||
b = b.modulate16<1>(bf).clamp8();
|
|
||||||
break;
|
|
||||||
case 3: // decal (tfx = tme)
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
__assume(0);
|
|
||||||
}
|
|
||||||
|
|
||||||
// AlphaBlend
|
|
||||||
|
|
||||||
if(sel.abe)
|
|
||||||
{
|
|
||||||
GSVector4i rs = r;
|
|
||||||
GSVector4i gs = g;
|
|
||||||
GSVector4i bs = b;
|
|
||||||
GSVector4i rd = (fd & 0x001f001f) << 3;
|
|
||||||
GSVector4i gd = (fd & 0x03e003e0) >> 2;
|
|
||||||
GSVector4i bd = (fd & 0x7c007c00) >> 7;
|
|
||||||
|
|
||||||
switch(sel.abr)
|
|
||||||
{
|
|
||||||
case 0:
|
|
||||||
r = rd.avg8(rs);
|
|
||||||
g = gd.avg8(gs);
|
|
||||||
b = bd.avg8(bs);
|
|
||||||
break;
|
|
||||||
case 1:
|
|
||||||
r = rd.addus8(rs);
|
|
||||||
g = gd.addus8(gs);
|
|
||||||
b = bd.addus8(bs);
|
|
||||||
break;
|
|
||||||
case 2:
|
|
||||||
r = rd.subus8(rs);
|
|
||||||
g = gd.subus8(gs);
|
|
||||||
b = bd.subus8(bs);
|
|
||||||
break;
|
|
||||||
case 3:
|
|
||||||
r = rd.addus8(rs.srl16(2));
|
|
||||||
g = gd.addus8(gs.srl16(2));
|
|
||||||
b = bd.addus8(bs.srl16(2));
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
__assume(0);
|
|
||||||
}
|
|
||||||
|
|
||||||
if(sel.tme)
|
|
||||||
{
|
|
||||||
r = rs.blend8(rd, a);
|
|
||||||
g = gs.blend8(gd, a);
|
|
||||||
b = bs.blend8(bd, a);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Dither
|
|
||||||
|
|
||||||
if(sel.dtd)
|
|
||||||
{
|
|
||||||
r = r.addus8(dither);
|
|
||||||
g = g.addus8(dither);
|
|
||||||
b = b.addus8(dither);
|
|
||||||
}
|
|
||||||
|
|
||||||
// WriteFrame
|
|
||||||
|
|
||||||
GSVector4i fs = r | g | b | (sel.md ? GSVector4i(0x80008000) : sel.tme ? a : GSVector4i::zero());
|
|
||||||
|
|
||||||
fs = fs.blend8(fd, test);
|
|
||||||
|
|
||||||
GSVector4i::store(fb, fb + 8, fs);
|
|
||||||
}
|
|
||||||
while(0);
|
|
||||||
|
|
||||||
if(steps <= 0) break;
|
|
||||||
|
|
||||||
steps -= 8;
|
|
||||||
|
|
||||||
fb += 8;
|
|
||||||
|
|
||||||
if(sel.tme)
|
|
||||||
{
|
|
||||||
GSVector4i st = m_local.d8.st;
|
|
||||||
|
|
||||||
s = s.add16(st.xxxx());
|
|
||||||
t = t.add16(st.yyyy());
|
|
||||||
}
|
|
||||||
|
|
||||||
if(sel.tfx != 3) // != decal
|
|
||||||
{
|
|
||||||
if(sel.iip)
|
|
||||||
{
|
|
||||||
GSVector4i c = m_local.d8.c;
|
|
||||||
|
|
||||||
rf = rf.add16(c.xxxx());
|
|
||||||
gf = gf.add16(c.yyyy());
|
|
||||||
bf = bf.add16(c.zzzz());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPUDrawScanline::DrawEdge(int pixels, int left, int top, const GSVertexSW& scan)
|
|
||||||
{
|
|
||||||
ASSERT(0);
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPUDrawScanline::DrawRect(const GSVector4i& r, const GSVertexSW& v)
|
|
||||||
{
|
|
||||||
// TODO
|
|
||||||
}
|
|
||||||
|
|
||||||
#endif
|
|
|
@ -1,76 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2007-2009 Gabest
|
|
||||||
* http://www.gabest.org
|
|
||||||
*
|
|
||||||
* 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; either version 2, 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 received a copy of the GNU General Public License
|
|
||||||
* along with GNU Make; see the file COPYING. If not, write to
|
|
||||||
* the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA USA.
|
|
||||||
* http://www.gnu.org/copyleft/gpl.html
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
|
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include "GPUState.h"
|
|
||||||
#include "Renderers/SW/GSRasterizer.h"
|
|
||||||
#include "GPUScanlineEnvironment.h"
|
|
||||||
#include "GPUSetupPrimCodeGenerator.h"
|
|
||||||
#include "GPUDrawScanlineCodeGenerator.h"
|
|
||||||
|
|
||||||
class GPUDrawScanline : public IDrawScanline
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
class SharedData : public GSRasterizerData
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
GPUScanlineGlobalData global;
|
|
||||||
|
|
||||||
public:
|
|
||||||
SharedData()
|
|
||||||
{
|
|
||||||
global.clut = NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual ~SharedData()
|
|
||||||
{
|
|
||||||
if(global.clut) _aligned_free(global.clut);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
protected:
|
|
||||||
GPUScanlineGlobalData m_global;
|
|
||||||
GPUScanlineLocalData m_local;
|
|
||||||
|
|
||||||
GSCodeGeneratorFunctionMap<GPUSetupPrimCodeGenerator, uint32, SetupPrimPtr> m_sp_map;
|
|
||||||
GSCodeGeneratorFunctionMap<GPUDrawScanlineCodeGenerator, uint32, DrawScanlinePtr> m_ds_map;
|
|
||||||
|
|
||||||
public:
|
|
||||||
GPUDrawScanline();
|
|
||||||
virtual ~GPUDrawScanline() = default;
|
|
||||||
|
|
||||||
// IDrawScanline
|
|
||||||
|
|
||||||
void BeginDraw(const GSRasterizerData* data);
|
|
||||||
void EndDraw(uint64 frame, uint64 ticks, int actual, int total);
|
|
||||||
|
|
||||||
#ifndef ENABLE_JIT_RASTERIZER
|
|
||||||
|
|
||||||
void SetupPrim(const GSVertexSW* vertex, const uint32* index, const GSVertexSW& dscan);
|
|
||||||
void DrawScanline(int pixels, int left, int top, const GSVertexSW& scan);
|
|
||||||
void DrawEdge(int pixels, int left, int top, const GSVertexSW& scan);
|
|
||||||
void DrawRect(const GSVector4i& r, const GSVertexSW& v);
|
|
||||||
|
|
||||||
#endif
|
|
||||||
|
|
||||||
void PrintStats() {m_ds_map.PrintStats();}
|
|
||||||
};
|
|
File diff suppressed because it is too large
Load Diff
|
@ -1,62 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2007-2009 Gabest
|
|
||||||
* http://www.gabest.org
|
|
||||||
*
|
|
||||||
* 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; either version 2, 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 received a copy of the GNU General Public License
|
|
||||||
* along with GNU Make; see the file COPYING. If not, write to
|
|
||||||
* the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA USA.
|
|
||||||
* http://www.gnu.org/copyleft/gpl.html
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
|
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include "GPUScanlineEnvironment.h"
|
|
||||||
#include "Renderers/Common/GSFunctionMap.h"
|
|
||||||
|
|
||||||
using namespace Xbyak;
|
|
||||||
|
|
||||||
class GPUDrawScanlineCodeGenerator : public GSCodeGenerator
|
|
||||||
{
|
|
||||||
void operator = (const GPUDrawScanlineCodeGenerator&);
|
|
||||||
|
|
||||||
GPUScanlineSelector m_sel;
|
|
||||||
GPUScanlineLocalData& m_local;
|
|
||||||
|
|
||||||
void Generate();
|
|
||||||
|
|
||||||
void Init();
|
|
||||||
void Step();
|
|
||||||
void TestMask();
|
|
||||||
void SampleTexture();
|
|
||||||
void ColorTFX();
|
|
||||||
void AlphaBlend();
|
|
||||||
void Dither();
|
|
||||||
void WriteFrame();
|
|
||||||
|
|
||||||
void ReadTexel(const Xmm& dst, const Xmm& addr);
|
|
||||||
|
|
||||||
template<int shift> void modulate16(const Xmm& a, const Operand& f);
|
|
||||||
template<int shift> void lerp16(const Xmm& a, const Xmm& b, const Operand& f);
|
|
||||||
void alltrue();
|
|
||||||
void blend8(const Xmm& a, const Xmm& b);
|
|
||||||
void blend(const Xmm& a, const Xmm& b, const Xmm& mask);
|
|
||||||
|
|
||||||
public:
|
|
||||||
GPUDrawScanlineCodeGenerator(void* param, uint32 key, void* code, size_t maxsize);
|
|
||||||
|
|
||||||
static GSVector4i m_test[8];
|
|
||||||
alignas(32) static const uint16 m_dither[4][16];
|
|
||||||
|
|
||||||
static void InitVectors();
|
|
||||||
};
|
|
|
@ -1,75 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2007-2009 Gabest
|
|
||||||
* http://www.gabest.org
|
|
||||||
*
|
|
||||||
* 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; either version 2, 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 received a copy of the GNU General Public License
|
|
||||||
* along with GNU Make; see the file COPYING. If not, write to
|
|
||||||
* the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA USA.
|
|
||||||
* http://www.gnu.org/copyleft/gpl.html
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
|
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include "GPU.h"
|
|
||||||
|
|
||||||
class alignas(32) GPUDrawingEnvironment
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
GPURegSTATUS STATUS;
|
|
||||||
GPURegPRIM PRIM;
|
|
||||||
GPURegDAREA DAREA;
|
|
||||||
GPURegDHRANGE DHRANGE;
|
|
||||||
GPURegDVRANGE DVRANGE;
|
|
||||||
GPURegDRAREA DRAREATL;
|
|
||||||
GPURegDRAREA DRAREABR;
|
|
||||||
GPURegDROFF DROFF;
|
|
||||||
GPURegTWIN TWIN;
|
|
||||||
GPURegCLUT CLUT;
|
|
||||||
|
|
||||||
GPUDrawingEnvironment()
|
|
||||||
{
|
|
||||||
Reset();
|
|
||||||
}
|
|
||||||
|
|
||||||
void Reset()
|
|
||||||
{
|
|
||||||
memset(this, 0, sizeof(*this));
|
|
||||||
|
|
||||||
STATUS.IDLE = 1;
|
|
||||||
STATUS.COM = 1;
|
|
||||||
STATUS.WIDTH0 = 1;
|
|
||||||
DVRANGE.Y1 = 16;
|
|
||||||
DVRANGE.Y2 = 256;
|
|
||||||
}
|
|
||||||
|
|
||||||
GSVector4i GetDisplayRect()
|
|
||||||
{
|
|
||||||
static int s_width[] = {256, 320, 512, 640, 368, 384, 512, 640};
|
|
||||||
static int s_height[] = {240, 480};
|
|
||||||
|
|
||||||
GSVector4i r;
|
|
||||||
|
|
||||||
r.left = DAREA.X & ~7; // FIXME
|
|
||||||
r.top = DAREA.Y;
|
|
||||||
r.right = r.left + s_width[(STATUS.WIDTH1 << 2) | STATUS.WIDTH0];
|
|
||||||
r.bottom = r.top + (DVRANGE.Y2 - DVRANGE.Y1) * s_height[STATUS.HEIGHT] / 240;
|
|
||||||
|
|
||||||
return r.rintersect(GSVector4i(0, 0, 1024, 512));
|
|
||||||
}
|
|
||||||
|
|
||||||
float GetFPS()
|
|
||||||
{
|
|
||||||
return STATUS.ISPAL ? 50.0f : 59.94f;
|
|
||||||
}
|
|
||||||
};
|
|
|
@ -1,670 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2007-2009 Gabest
|
|
||||||
* http://www.gabest.org
|
|
||||||
*
|
|
||||||
* 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; either version 2, 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 received a copy of the GNU General Public License
|
|
||||||
* along with GNU Make; see the file COPYING. If not, write to
|
|
||||||
* the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA USA.
|
|
||||||
* http://www.gnu.org/copyleft/gpl.html
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
|
|
||||||
#include "stdafx.h"
|
|
||||||
#include "GPULocalMemory.h"
|
|
||||||
#include "GSdx.h"
|
|
||||||
|
|
||||||
GSVector4i GPULocalMemory::m_xxxa;
|
|
||||||
GSVector4i GPULocalMemory::m_xxbx;
|
|
||||||
GSVector4i GPULocalMemory::m_xgxx;
|
|
||||||
GSVector4i GPULocalMemory::m_rxxx;
|
|
||||||
|
|
||||||
#define VM_REAL_SIZE ((1 << (12 + 11)) * sizeof(uint16))
|
|
||||||
#define VM_ALLOC_SIZE (VM_REAL_SIZE * 2)
|
|
||||||
#define TEX_ALLOC_SIZE (256 * 256 * (1 + 1 + 4) * 32)
|
|
||||||
|
|
||||||
void GPULocalMemory::InitVectors()
|
|
||||||
{
|
|
||||||
m_xxxa = GSVector4i(0x00008000);
|
|
||||||
m_xxbx = GSVector4i(0x00007c00);
|
|
||||||
m_xgxx = GSVector4i(0x000003e0);
|
|
||||||
m_rxxx = GSVector4i(0x0000001f);
|
|
||||||
}
|
|
||||||
|
|
||||||
GPULocalMemory::GPULocalMemory()
|
|
||||||
{
|
|
||||||
m_scale.x = std::min<int>(std::max<int>(theApp.GetConfigI("scale_x"), 0), 2);
|
|
||||||
m_scale.y = std::min<int>(std::max<int>(theApp.GetConfigI("scale_y"), 0), 2);
|
|
||||||
|
|
||||||
//
|
|
||||||
|
|
||||||
int size = VM_REAL_SIZE;
|
|
||||||
|
|
||||||
m_vm = (uint16*)vmalloc(VM_ALLOC_SIZE, false);
|
|
||||||
|
|
||||||
memset(m_vm, 0, size);
|
|
||||||
|
|
||||||
//
|
|
||||||
|
|
||||||
m_clut.buff = m_vm + size;
|
|
||||||
m_clut.dirty = true;
|
|
||||||
|
|
||||||
//
|
|
||||||
|
|
||||||
size = TEX_ALLOC_SIZE;
|
|
||||||
|
|
||||||
m_texture.buff[0] = (uint8*)vmalloc(size, false);
|
|
||||||
m_texture.buff[1] = m_texture.buff[0] + 256 * 256 * 32;
|
|
||||||
m_texture.buff[2] = m_texture.buff[1] + 256 * 256 * 32;
|
|
||||||
|
|
||||||
memset(m_texture.buff[0], 0, size);
|
|
||||||
|
|
||||||
memset(m_texture.valid, 0, sizeof(m_texture.valid));
|
|
||||||
|
|
||||||
for(int y = 0, offset = 0; y < 2; y++)
|
|
||||||
{
|
|
||||||
for(int x = 0; x < 16; x++, offset += 256 * 256)
|
|
||||||
{
|
|
||||||
m_texture.page[0][y][x] = &((uint8*)m_texture.buff[0])[offset];
|
|
||||||
m_texture.page[1][y][x] = &((uint8*)m_texture.buff[1])[offset];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
for(int y = 0, offset = 0; y < 2; y++)
|
|
||||||
{
|
|
||||||
for(int x = 0; x < 16; x++, offset += 256 * 256)
|
|
||||||
{
|
|
||||||
m_texture.page[2][y][x] = &((uint32*)m_texture.buff[2])[offset];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
GPULocalMemory::~GPULocalMemory()
|
|
||||||
{
|
|
||||||
vmfree(m_vm, VM_ALLOC_SIZE);
|
|
||||||
|
|
||||||
vmfree(m_texture.buff[0], TEX_ALLOC_SIZE);
|
|
||||||
}
|
|
||||||
|
|
||||||
const uint16* GPULocalMemory::GetCLUT(int tp, int cx, int cy)
|
|
||||||
{
|
|
||||||
if(m_clut.dirty || m_clut.tp != tp || m_clut.cx != cx || m_clut.cy != cy)
|
|
||||||
{
|
|
||||||
uint16* src = GetPixelAddressScaled(cx << 4, cy);
|
|
||||||
uint16* dst = m_clut.buff;
|
|
||||||
|
|
||||||
if(m_scale.x == 0)
|
|
||||||
{
|
|
||||||
memcpy(dst, src, (tp == 0 ? 16 : 256) * 2);
|
|
||||||
}
|
|
||||||
else if(m_scale.x == 1)
|
|
||||||
{
|
|
||||||
if(tp == 0)
|
|
||||||
{
|
|
||||||
for(int i = 0; i < 16; i++)
|
|
||||||
{
|
|
||||||
dst[i] = src[i * 2];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else if(tp == 1)
|
|
||||||
{
|
|
||||||
for(int i = 0; i < 256; i++)
|
|
||||||
{
|
|
||||||
dst[i] = src[i * 2];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else if(m_scale.x == 2)
|
|
||||||
{
|
|
||||||
if(tp == 0)
|
|
||||||
{
|
|
||||||
for(int i = 0; i < 16; i++)
|
|
||||||
{
|
|
||||||
dst[i] = src[i * 4];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else if(tp == 1)
|
|
||||||
{
|
|
||||||
for(int i = 0; i < 256; i++)
|
|
||||||
{
|
|
||||||
dst[i] = src[i * 4];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
ASSERT(0);
|
|
||||||
}
|
|
||||||
|
|
||||||
m_clut.tp = tp;
|
|
||||||
m_clut.cx = cx;
|
|
||||||
m_clut.cy = cy;
|
|
||||||
m_clut.dirty = false;
|
|
||||||
}
|
|
||||||
|
|
||||||
return m_clut.buff;
|
|
||||||
}
|
|
||||||
|
|
||||||
const void* GPULocalMemory::GetTexture(int tp, int tx, int ty)
|
|
||||||
{
|
|
||||||
if(tp == 3)
|
|
||||||
{
|
|
||||||
ASSERT(0);
|
|
||||||
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
void* buff = m_texture.page[tp][ty][tx];
|
|
||||||
|
|
||||||
uint32 flag = 1 << tx;
|
|
||||||
|
|
||||||
if((m_texture.valid[tp][ty] & flag) == 0)
|
|
||||||
{
|
|
||||||
// int bpp = 0;
|
|
||||||
|
|
||||||
switch(tp)
|
|
||||||
{
|
|
||||||
case 0:
|
|
||||||
ReadPage4(tx, ty, (uint8*)buff);
|
|
||||||
// bpp = 4;
|
|
||||||
break;
|
|
||||||
case 1:
|
|
||||||
ReadPage8(tx, ty, (uint8*)buff);
|
|
||||||
// bpp = 8;
|
|
||||||
break;
|
|
||||||
case 2:
|
|
||||||
case 3:
|
|
||||||
ReadPage16(tx, ty, (uint16*)buff);
|
|
||||||
// bpp = 16;
|
|
||||||
default:
|
|
||||||
// FIXME: __assume(0); // vc9 generates bogus code in release mode
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
// TODO: m_state->m_perfmon.Put(GSPerfMon::Unswizzle, 256 * 256 * bpp >> 3);
|
|
||||||
|
|
||||||
m_texture.valid[tp][ty] |= flag;
|
|
||||||
}
|
|
||||||
|
|
||||||
return buff;
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPULocalMemory::Invalidate(const GSVector4i& r)
|
|
||||||
{
|
|
||||||
if(!m_clut.dirty)
|
|
||||||
{
|
|
||||||
if(r.top <= m_clut.cy && m_clut.cy < r.bottom)
|
|
||||||
{
|
|
||||||
int left = m_clut.cx << 4;
|
|
||||||
int right = left + (m_clut.tp == 0 ? 16 : 256);
|
|
||||||
|
|
||||||
if(r.left < right && r.right > left)
|
|
||||||
{
|
|
||||||
m_clut.dirty = true;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
for(int y = 0, ye = std::min(r.bottom, 512), j = 0; y < ye; y += 256, j++)
|
|
||||||
{
|
|
||||||
if(r.top >= y + 256) continue;
|
|
||||||
|
|
||||||
for(int x = 0, xe = std::min(r.right, 1024), i = 0; x < xe; x += 64, i++)
|
|
||||||
{
|
|
||||||
uint32 flag = 1 << i;
|
|
||||||
|
|
||||||
if(r.left >= x + 256) continue;
|
|
||||||
|
|
||||||
m_texture.valid[2][j] &= ~flag;
|
|
||||||
|
|
||||||
if(r.left >= x + 128) continue;
|
|
||||||
|
|
||||||
m_texture.valid[1][j] &= ~flag;
|
|
||||||
|
|
||||||
if(r.left >= x + 64) continue;
|
|
||||||
|
|
||||||
m_texture.valid[0][j] &= ~flag;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPULocalMemory::FillRect(const GSVector4i& r, uint16 c)
|
|
||||||
{
|
|
||||||
Invalidate(r);
|
|
||||||
|
|
||||||
uint16* RESTRICT dst = GetPixelAddressScaled(r.left, r.top);
|
|
||||||
|
|
||||||
int w = r.width() << m_scale.x;
|
|
||||||
int h = r.height() << m_scale.y;
|
|
||||||
|
|
||||||
int pitch = GetWidth();
|
|
||||||
|
|
||||||
for(int j = 0; j < h; j++, dst += pitch)
|
|
||||||
{
|
|
||||||
for(int i = 0; i < w; i++)
|
|
||||||
{
|
|
||||||
dst[i] = c;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPULocalMemory::WriteRect(const GSVector4i& r, const uint16* RESTRICT src)
|
|
||||||
{
|
|
||||||
Invalidate(r);
|
|
||||||
|
|
||||||
uint16* RESTRICT dst = GetPixelAddressScaled(r.left, r.top);
|
|
||||||
|
|
||||||
int w = r.width();
|
|
||||||
int h = r.height();
|
|
||||||
|
|
||||||
int pitch = GetWidth();
|
|
||||||
|
|
||||||
if(m_scale.x == 0)
|
|
||||||
{
|
|
||||||
for(int j = 0; j < h; j++, src += w)
|
|
||||||
{
|
|
||||||
for(int k = 1 << m_scale.y; k >= 1; k--, dst += pitch)
|
|
||||||
{
|
|
||||||
memcpy(dst, src, w * 2);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else if(m_scale.x == 1)
|
|
||||||
{
|
|
||||||
for(int j = 0; j < h; j++, src += w)
|
|
||||||
{
|
|
||||||
for(int k = 1 << m_scale.y; k >= 1; k--, dst += pitch)
|
|
||||||
{
|
|
||||||
for(int i = 0; i < w; i++)
|
|
||||||
{
|
|
||||||
dst[i * 2 + 0] = src[i];
|
|
||||||
dst[i * 2 + 1] = src[i];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else if(m_scale.x == 2)
|
|
||||||
{
|
|
||||||
for(int j = 0; j < h; j++, src += w)
|
|
||||||
{
|
|
||||||
for(int k = 1 << m_scale.y; k >= 1; k--, dst += pitch)
|
|
||||||
{
|
|
||||||
for(int i = 0; i < w; i++)
|
|
||||||
{
|
|
||||||
dst[i * 4 + 0] = src[i];
|
|
||||||
dst[i * 4 + 1] = src[i];
|
|
||||||
dst[i * 4 + 2] = src[i];
|
|
||||||
dst[i * 4 + 3] = src[i];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
ASSERT(0);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPULocalMemory::ReadRect(const GSVector4i& r, uint16* RESTRICT dst)
|
|
||||||
{
|
|
||||||
uint16* RESTRICT src = GetPixelAddressScaled(r.left, r.top);
|
|
||||||
|
|
||||||
int w = r.width();
|
|
||||||
int h = r.height();
|
|
||||||
|
|
||||||
int pitch = GetWidth() << m_scale.y;
|
|
||||||
|
|
||||||
if(m_scale.x == 0)
|
|
||||||
{
|
|
||||||
for(int j = 0; j < h; j++, src += pitch, dst += w)
|
|
||||||
{
|
|
||||||
memcpy(dst, src, w * 2);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else if(m_scale.x == 1)
|
|
||||||
{
|
|
||||||
for(int j = 0; j < h; j++, src += pitch, dst += w)
|
|
||||||
{
|
|
||||||
for(int i = 0; i < w; i++)
|
|
||||||
{
|
|
||||||
dst[i] = src[i * 2];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else if(m_scale.x == 2)
|
|
||||||
{
|
|
||||||
for(int j = 0; j < h; j++, src += pitch, dst += w)
|
|
||||||
{
|
|
||||||
for(int i = 0; i < w; i++)
|
|
||||||
{
|
|
||||||
dst[i] = src[i * 4];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
ASSERT(0);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPULocalMemory::MoveRect(int sx, int sy, int dx, int dy, int w, int h)
|
|
||||||
{
|
|
||||||
Invalidate(GSVector4i(dx, dy, dx + w, dy + h));
|
|
||||||
|
|
||||||
uint16* s = GetPixelAddressScaled(sx, sy);
|
|
||||||
uint16* d = GetPixelAddressScaled(dx, dy);
|
|
||||||
|
|
||||||
w <<= m_scale.x;
|
|
||||||
h <<= m_scale.y;
|
|
||||||
|
|
||||||
int pitch = GetWidth();
|
|
||||||
|
|
||||||
for(int i = 0; i < h; i++, s += pitch, d += pitch)
|
|
||||||
{
|
|
||||||
memcpy(d, s, w * sizeof(uint16));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPULocalMemory::ReadPage4(int tx, int ty, uint8* RESTRICT dst)
|
|
||||||
{
|
|
||||||
uint16* src = GetPixelAddressScaled(tx << 6, ty << 8);
|
|
||||||
|
|
||||||
int pitch = GetWidth() << m_scale.y;
|
|
||||||
|
|
||||||
if(m_scale.x == 0)
|
|
||||||
{
|
|
||||||
for(int j = 0; j < 256; j++, src += pitch, dst += 256)
|
|
||||||
{
|
|
||||||
for(int i = 0; i < 64; i++)
|
|
||||||
{
|
|
||||||
dst[i * 4 + 0] = (src[i] >> 0) & 0xf;
|
|
||||||
dst[i * 4 + 1] = (src[i] >> 4) & 0xf;
|
|
||||||
dst[i * 4 + 2] = (src[i] >> 8) & 0xf;
|
|
||||||
dst[i * 4 + 3] = (src[i] >> 12) & 0xf;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else if(m_scale.x == 1)
|
|
||||||
{
|
|
||||||
for(int j = 0; j < 256; j++, src += pitch, dst += 256)
|
|
||||||
{
|
|
||||||
for(int i = 0; i < 64; i++)
|
|
||||||
{
|
|
||||||
dst[i * 4 + 0] = (src[i * 2] >> 0) & 0xf;
|
|
||||||
dst[i * 4 + 1] = (src[i * 2] >> 4) & 0xf;
|
|
||||||
dst[i * 4 + 2] = (src[i * 2] >> 8) & 0xf;
|
|
||||||
dst[i * 4 + 3] = (src[i * 2] >> 12) & 0xf;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else if(m_scale.x == 2)
|
|
||||||
{
|
|
||||||
for(int j = 0; j < 256; j++, src += pitch, dst += 256)
|
|
||||||
{
|
|
||||||
for(int i = 0; i < 64; i++)
|
|
||||||
{
|
|
||||||
dst[i * 4 + 0] = (src[i * 4] >> 0) & 0xf;
|
|
||||||
dst[i * 4 + 1] = (src[i * 4] >> 4) & 0xf;
|
|
||||||
dst[i * 4 + 2] = (src[i * 4] >> 8) & 0xf;
|
|
||||||
dst[i * 4 + 3] = (src[i * 4] >> 12) & 0xf;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
ASSERT(0);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPULocalMemory::ReadPage8(int tx, int ty, uint8* RESTRICT dst)
|
|
||||||
{
|
|
||||||
uint16* src = GetPixelAddressScaled(tx << 6, ty << 8);
|
|
||||||
|
|
||||||
int pitch = GetWidth() << m_scale.y;
|
|
||||||
|
|
||||||
if(m_scale.x == 0)
|
|
||||||
{
|
|
||||||
for(int j = 0; j < 256; j++, src += pitch, dst += 256)
|
|
||||||
{
|
|
||||||
memcpy(dst, src, 256);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else if(m_scale.x == 1)
|
|
||||||
{
|
|
||||||
for(int j = 0; j < 256; j++, src += pitch, dst += 256)
|
|
||||||
{
|
|
||||||
for(int i = 0; i < 128; i++)
|
|
||||||
{
|
|
||||||
((uint16*)dst)[i] = src[i * 2];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else if(m_scale.x == 2)
|
|
||||||
{
|
|
||||||
for(int j = 0; j < 256; j++, src += pitch, dst += 256)
|
|
||||||
{
|
|
||||||
for(int i = 0; i < 128; i++)
|
|
||||||
{
|
|
||||||
((uint16*)dst)[i] = src[i * 4];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
ASSERT(0);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPULocalMemory::ReadPage16(int tx, int ty, uint16* RESTRICT dst)
|
|
||||||
{
|
|
||||||
uint16* src = GetPixelAddressScaled(tx << 6, ty << 8);
|
|
||||||
|
|
||||||
int pitch = GetWidth() << m_scale.y;
|
|
||||||
|
|
||||||
if(m_scale.x == 0)
|
|
||||||
{
|
|
||||||
for(int j = 0; j < 256; j++, src += pitch, dst += 256)
|
|
||||||
{
|
|
||||||
memcpy(dst, src, 512);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else if(m_scale.x == 1)
|
|
||||||
{
|
|
||||||
for(int j = 0; j < 256; j++, src += pitch, dst += 256)
|
|
||||||
{
|
|
||||||
for(int i = 0; i < 256; i++)
|
|
||||||
{
|
|
||||||
dst[i] = src[i * 2];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else if(m_scale.x == 2)
|
|
||||||
{
|
|
||||||
for(int j = 0; j < 256; j++, src += pitch, dst += 256)
|
|
||||||
{
|
|
||||||
for(int i = 0; i < 256; i++)
|
|
||||||
{
|
|
||||||
dst[i] = src[i * 4];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
ASSERT(0);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPULocalMemory::ReadFrame32(const GSVector4i& r, uint32* RESTRICT dst, bool rgb24)
|
|
||||||
{
|
|
||||||
uint16* src = GetPixelAddress(r.left, r.top);
|
|
||||||
|
|
||||||
int pitch = GetWidth();
|
|
||||||
|
|
||||||
if(rgb24)
|
|
||||||
{
|
|
||||||
for(int i = r.top; i < r.bottom; i++, src += pitch, dst += pitch)
|
|
||||||
{
|
|
||||||
Expand24(src, dst, r.width());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
for(int i = r.top; i < r.bottom; i++, src += pitch, dst += pitch)
|
|
||||||
{
|
|
||||||
Expand16(src, dst, r.width());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPULocalMemory::Expand16(const uint16* RESTRICT src, uint32* RESTRICT dst, int pixels)
|
|
||||||
{
|
|
||||||
GSVector4i rm = m_rxxx;
|
|
||||||
GSVector4i gm = m_xgxx;
|
|
||||||
GSVector4i bm = m_xxbx;
|
|
||||||
GSVector4i am = m_xxxa;
|
|
||||||
|
|
||||||
GSVector4i* s = (GSVector4i*)src;
|
|
||||||
GSVector4i* d = (GSVector4i*)dst;
|
|
||||||
|
|
||||||
for(int i = 0, j = pixels >> 3; i < j; i++)
|
|
||||||
{
|
|
||||||
GSVector4i c = s[i];
|
|
||||||
|
|
||||||
GSVector4i l = c.upl16();
|
|
||||||
GSVector4i h = c.uph16();
|
|
||||||
|
|
||||||
d[i * 2 + 0] = ((l & rm) << 3) | ((l & gm) << 6) | ((l & bm) << 9) | ((l & am) << 16);
|
|
||||||
d[i * 2 + 1] = ((h & rm) << 3) | ((h & gm) << 6) | ((h & bm) << 9) | ((h & am) << 16);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPULocalMemory::Expand24(const uint16* RESTRICT src, uint32* RESTRICT dst, int pixels)
|
|
||||||
{
|
|
||||||
uint8* s = (uint8*)src;
|
|
||||||
|
|
||||||
if(m_scale.x == 0)
|
|
||||||
{
|
|
||||||
for(int i = 0; i < pixels; i += 2, s += 6)
|
|
||||||
{
|
|
||||||
dst[i + 0] = (s[2] << 16) | (s[1] << 8) | s[0];
|
|
||||||
dst[i + 1] = (s[5] << 16) | (s[4] << 8) | s[3];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else if(m_scale.x == 1)
|
|
||||||
{
|
|
||||||
for(int i = 0; i < pixels; i += 4, s += 12)
|
|
||||||
{
|
|
||||||
dst[i + 0] = dst[i + 1] = (s[4] << 16) | (s[1] << 8) | s[0];
|
|
||||||
dst[i + 2] = dst[i + 3] = (s[9] << 16) | (s[8] << 8) | s[5];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else if(m_scale.x == 2)
|
|
||||||
{
|
|
||||||
for(int i = 0; i < pixels; i += 8, s += 24)
|
|
||||||
{
|
|
||||||
dst[i + 0] = dst[i + 1] = dst[i + 2] = dst[i + 3] = (s[8] << 16) | (s[1] << 8) | s[0];
|
|
||||||
dst[i + 4] = dst[i + 5] = dst[i + 6] = dst[i + 7] = (s[17] << 16) | (s[16] << 8) | s[9];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
ASSERT(0);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
#include "Renderers/SW/GSTextureSW.h"
|
|
||||||
|
|
||||||
void GPULocalMemory::SaveBMP(const std::string& fn, const GSVector4i& r2, int tp, int cx, int cy)
|
|
||||||
{
|
|
||||||
GSVector4i r;
|
|
||||||
|
|
||||||
r.left = r2.left << m_scale.x;
|
|
||||||
r.top = r2.top << m_scale.y;
|
|
||||||
r.right = r2.right << m_scale.x;
|
|
||||||
r.bottom = r2.bottom << m_scale.y;
|
|
||||||
|
|
||||||
r.left &= ~1;
|
|
||||||
r.right &= ~1;
|
|
||||||
|
|
||||||
GSTextureSW t(GSTexture::Offscreen, r.width(), r.height());
|
|
||||||
|
|
||||||
GSTexture::GSMap m;
|
|
||||||
|
|
||||||
if(t.Map(m, NULL))
|
|
||||||
{
|
|
||||||
int pitch = GetWidth();
|
|
||||||
|
|
||||||
const uint16* RESTRICT src = GetPixelAddress(r.left, r.top);
|
|
||||||
const uint16* RESTRICT clut = GetCLUT(tp, cx, cy);
|
|
||||||
|
|
||||||
uint8* RESTRICT dst = m.bits;
|
|
||||||
|
|
||||||
uint16* RESTRICT buff = (uint16*)_aligned_malloc(pitch * sizeof(uint16), 32);
|
|
||||||
uint32* RESTRICT buff32 = (uint32*)_aligned_malloc(pitch * sizeof(uint32), 32);
|
|
||||||
|
|
||||||
for(int j = r.top; j < r.bottom; j++, src += pitch, dst += m.pitch)
|
|
||||||
{
|
|
||||||
switch(tp)
|
|
||||||
{
|
|
||||||
case 0: // 4 bpp
|
|
||||||
|
|
||||||
for(int i = 0, k = r.width() / 2; i < k; i++)
|
|
||||||
{
|
|
||||||
buff[i * 2 + 0] = clut[((uint8*)src)[i] & 0xf];
|
|
||||||
buff[i * 2 + 1] = clut[((uint8*)src)[i] >> 4];
|
|
||||||
}
|
|
||||||
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 1: // 8 bpp
|
|
||||||
|
|
||||||
for(int i = 0, k = r.width(); i < k; i++)
|
|
||||||
{
|
|
||||||
buff[i] = clut[((uint8*)src)[i]];
|
|
||||||
}
|
|
||||||
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 2: // 16 bpp;
|
|
||||||
|
|
||||||
for(int i = 0, k = r.width(); i < k; i++)
|
|
||||||
{
|
|
||||||
buff[i] = src[i];
|
|
||||||
}
|
|
||||||
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 3: // 24 bpp
|
|
||||||
|
|
||||||
// TODO
|
|
||||||
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
Expand16(buff, buff32, r.width());
|
|
||||||
|
|
||||||
for(int i = 0, k = r.width(); i < k; i++)
|
|
||||||
{
|
|
||||||
buff32[i] = (buff32[i] & 0xff00ff00) | ((buff32[i] & 0x00ff0000) >> 16) | ((buff32[i] & 0x000000ff) << 16);
|
|
||||||
}
|
|
||||||
|
|
||||||
memcpy(dst, buff32, r.width() << 2);
|
|
||||||
}
|
|
||||||
|
|
||||||
_aligned_free(buff);
|
|
||||||
_aligned_free(buff32);
|
|
||||||
|
|
||||||
t.Unmap();
|
|
||||||
|
|
||||||
t.Save(fn);
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -1,86 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2007-2009 Gabest
|
|
||||||
* http://www.gabest.org
|
|
||||||
*
|
|
||||||
* 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; either version 2, 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 received a copy of the GNU General Public License
|
|
||||||
* along with GNU Make; see the file COPYING. If not, write to
|
|
||||||
* the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA USA.
|
|
||||||
* http://www.gnu.org/copyleft/gpl.html
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
|
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include "GPU.h"
|
|
||||||
#include "GSVector.h"
|
|
||||||
|
|
||||||
class GPULocalMemory
|
|
||||||
{
|
|
||||||
static GSVector4i m_xxxa;
|
|
||||||
static GSVector4i m_xxbx;
|
|
||||||
static GSVector4i m_xgxx;
|
|
||||||
static GSVector4i m_rxxx;
|
|
||||||
|
|
||||||
uint16* m_vm;
|
|
||||||
|
|
||||||
struct
|
|
||||||
{
|
|
||||||
uint16* buff;
|
|
||||||
int tp, cx, cy;
|
|
||||||
bool dirty;
|
|
||||||
} m_clut;
|
|
||||||
|
|
||||||
struct
|
|
||||||
{
|
|
||||||
uint8* buff[3];
|
|
||||||
void* page[3][2][16];
|
|
||||||
uint16 valid[3][2];
|
|
||||||
} m_texture;
|
|
||||||
|
|
||||||
GSVector2i m_scale;
|
|
||||||
|
|
||||||
public:
|
|
||||||
static void InitVectors();
|
|
||||||
|
|
||||||
GPULocalMemory();
|
|
||||||
virtual ~GPULocalMemory();
|
|
||||||
|
|
||||||
GSVector2i GetScale() {return m_scale;}
|
|
||||||
|
|
||||||
int GetWidth() {return 1 << (10 + m_scale.x);}
|
|
||||||
int GetHeight() {return 1 << (9 + m_scale.y);}
|
|
||||||
|
|
||||||
uint16* GetPixelAddress(int x, int y) const {return &m_vm[(y << (10 + m_scale.x)) + x];}
|
|
||||||
uint16* GetPixelAddressScaled(int x, int y) const {return &m_vm[((y << m_scale.y) << (10 + m_scale.x)) + (x << m_scale.x)];}
|
|
||||||
|
|
||||||
const uint16* GetCLUT(int tp, int cx, int cy);
|
|
||||||
const void* GetTexture(int tp, int tx, int ty);
|
|
||||||
|
|
||||||
void Invalidate(const GSVector4i& r);
|
|
||||||
|
|
||||||
void FillRect(const GSVector4i& r, uint16 c);
|
|
||||||
void WriteRect(const GSVector4i& r, const uint16* RESTRICT src);
|
|
||||||
void ReadRect(const GSVector4i& r, uint16* RESTRICT dst);
|
|
||||||
void MoveRect(int sx, int sy, int dx, int dy, int w, int h);
|
|
||||||
|
|
||||||
void ReadPage4(int tx, int ty, uint8* RESTRICT dst);
|
|
||||||
void ReadPage8(int tx, int ty, uint8* RESTRICT dst);
|
|
||||||
void ReadPage16(int tx, int ty, uint16* RESTRICT dst);
|
|
||||||
|
|
||||||
void ReadFrame32(const GSVector4i& r, uint32* RESTRICT dst, bool rgb24);
|
|
||||||
|
|
||||||
void Expand16(const uint16* RESTRICT src, uint32* RESTRICT dst, int pixels);
|
|
||||||
void Expand24(const uint16* RESTRICT src, uint32* RESTRICT dst, int pixels);
|
|
||||||
|
|
||||||
void SaveBMP(const std::string& fn, const GSVector4i& r, int tp, int cx, int cy);
|
|
||||||
};
|
|
|
@ -1,278 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2007-2009 Gabest
|
|
||||||
* http://www.gabest.org
|
|
||||||
*
|
|
||||||
* 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; either version 2, 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 received a copy of the GNU General Public License
|
|
||||||
* along with GNU Make; see the file COPYING. If not, write to
|
|
||||||
* the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA USA.
|
|
||||||
* http://www.gnu.org/copyleft/gpl.html
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
|
|
||||||
#include "stdafx.h"
|
|
||||||
#include "GPURenderer.h"
|
|
||||||
#include "GSdx.h"
|
|
||||||
|
|
||||||
#ifdef _WIN32
|
|
||||||
|
|
||||||
std::map<HWND, GPURenderer*> GPURenderer::m_wnd2gpu;
|
|
||||||
|
|
||||||
#endif
|
|
||||||
|
|
||||||
GPURenderer::GPURenderer(GSDevice* dev)
|
|
||||||
: m_dev(dev)
|
|
||||||
{
|
|
||||||
m_filter = theApp.GetConfigI("filter");
|
|
||||||
m_dither = theApp.GetConfigI("dithering");
|
|
||||||
m_aspectratio = theApp.GetConfigI("AspectRatio");
|
|
||||||
m_vsync = theApp.GetConfigI("vsync");
|
|
||||||
m_fxaa = theApp.GetConfigB("fxaa");
|
|
||||||
m_shaderfx = theApp.GetConfigB("shaderfx");
|
|
||||||
m_scale = m_mem.GetScale();
|
|
||||||
m_shadeboost = theApp.GetConfigB("ShadeBoost");
|
|
||||||
|
|
||||||
#ifdef _WIN32
|
|
||||||
|
|
||||||
m_hWnd = NULL;
|
|
||||||
m_wndproc = NULL;
|
|
||||||
|
|
||||||
m_wnd = std::make_shared<GSWndDX>();
|
|
||||||
|
|
||||||
#endif
|
|
||||||
}
|
|
||||||
|
|
||||||
GPURenderer::~GPURenderer()
|
|
||||||
{
|
|
||||||
#ifdef _WIN32
|
|
||||||
|
|
||||||
if(m_wndproc)
|
|
||||||
{
|
|
||||||
SetWindowLongPtr(m_hWnd, GWLP_WNDPROC, (LONG_PTR)m_wndproc);
|
|
||||||
|
|
||||||
m_wnd2gpu.erase(m_hWnd);
|
|
||||||
}
|
|
||||||
|
|
||||||
#endif
|
|
||||||
}
|
|
||||||
|
|
||||||
bool GPURenderer::Create(void* hWnd)
|
|
||||||
{
|
|
||||||
#ifdef _WIN32
|
|
||||||
|
|
||||||
// TODO: move subclassing inside GSWnd::Attach
|
|
||||||
|
|
||||||
m_hWnd = (HWND)hWnd;
|
|
||||||
|
|
||||||
m_wndproc = (WNDPROC)GetWindowLongPtr(m_hWnd, GWLP_WNDPROC);
|
|
||||||
|
|
||||||
SetWindowLongPtr(m_hWnd, GWLP_WNDPROC, (LONG_PTR)WndProc);
|
|
||||||
|
|
||||||
if(!m_wnd->Attach(m_hWnd))
|
|
||||||
{
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
m_wnd2gpu[m_hWnd] = this;
|
|
||||||
|
|
||||||
SetWindowLong(m_hWnd, GWL_STYLE, GetWindowLong(m_hWnd, GWL_STYLE) | WS_OVERLAPPEDWINDOW);
|
|
||||||
|
|
||||||
#endif
|
|
||||||
|
|
||||||
m_wnd->Show();
|
|
||||||
|
|
||||||
if(!m_dev->Create(m_wnd))
|
|
||||||
{
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
m_dev->SetVSync(m_vsync);
|
|
||||||
|
|
||||||
Reset();
|
|
||||||
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool GPURenderer::Merge()
|
|
||||||
{
|
|
||||||
GSTexture* st[3] = {GetOutput(), NULL, NULL};
|
|
||||||
|
|
||||||
if(!st[0])
|
|
||||||
{
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
GSVector2i s = st[0]->GetSize();
|
|
||||||
|
|
||||||
GSVector4 sr[2];
|
|
||||||
GSVector4 dr[2];
|
|
||||||
|
|
||||||
sr[0] = GSVector4(0, 0, 1, 1);
|
|
||||||
dr[0] = GSVector4(0, 0, s.x, s.y);
|
|
||||||
|
|
||||||
GSRegPMODE PMODE = {0};
|
|
||||||
PMODE.u32[0] = 0xFFFFFFFF;
|
|
||||||
GSRegEXTBUF EXTBUF = {0};
|
|
||||||
m_dev->Merge(st, sr, dr, s, PMODE, EXTBUF, GSVector4(0, 0, 0, 1));
|
|
||||||
|
|
||||||
if(m_shadeboost)
|
|
||||||
{
|
|
||||||
m_dev->ShadeBoost();
|
|
||||||
}
|
|
||||||
|
|
||||||
if (m_shaderfx)
|
|
||||||
{
|
|
||||||
m_dev->ExternalFX();
|
|
||||||
}
|
|
||||||
|
|
||||||
if(m_fxaa)
|
|
||||||
{
|
|
||||||
m_dev->FXAA();
|
|
||||||
}
|
|
||||||
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPURenderer::VSync()
|
|
||||||
{
|
|
||||||
GSPerfMonAutoTimer pmat(&m_perfmon);
|
|
||||||
|
|
||||||
m_perfmon.Put(GSPerfMon::Frame);
|
|
||||||
|
|
||||||
// m_env.STATUS.LCF = ~m_env.STATUS.LCF; // ?
|
|
||||||
|
|
||||||
#ifdef _WIN32
|
|
||||||
|
|
||||||
if(!IsWindow(m_hWnd)) return;
|
|
||||||
|
|
||||||
#endif
|
|
||||||
|
|
||||||
Flush();
|
|
||||||
|
|
||||||
if(!m_dev->IsLost(true))
|
|
||||||
{
|
|
||||||
if(!Merge())
|
|
||||||
{
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
ResetDevice();
|
|
||||||
}
|
|
||||||
|
|
||||||
// osd
|
|
||||||
|
|
||||||
if((m_perfmon.GetFrame() & 0x1f) == 0)
|
|
||||||
{
|
|
||||||
m_perfmon.Update();
|
|
||||||
|
|
||||||
double fps = 1000.0f / m_perfmon.Get(GSPerfMon::Frame);
|
|
||||||
|
|
||||||
GSVector4i r = m_env.GetDisplayRect();
|
|
||||||
|
|
||||||
int w = r.width() << m_scale.x;
|
|
||||||
int h = r.height() << m_scale.y;
|
|
||||||
|
|
||||||
std::string s = format(
|
|
||||||
"%lld | %d x %d | %.2f fps (%d%%) | %d/%d | %d%% CPU | %.2f | %.2f",
|
|
||||||
m_perfmon.GetFrame(), w, h, fps, (int)(100.0 * fps / m_env.GetFPS()),
|
|
||||||
(int)m_perfmon.Get(GSPerfMon::Prim),
|
|
||||||
(int)m_perfmon.Get(GSPerfMon::Draw),
|
|
||||||
m_perfmon.CPU(),
|
|
||||||
m_perfmon.Get(GSPerfMon::Swizzle) / 1024,
|
|
||||||
m_perfmon.Get(GSPerfMon::Unswizzle) / 1024
|
|
||||||
);
|
|
||||||
|
|
||||||
double fillrate = m_perfmon.Get(GSPerfMon::Fillrate);
|
|
||||||
|
|
||||||
if(fillrate > 0)
|
|
||||||
{
|
|
||||||
s = format("%s | %.2f mpps", s.c_str(), fps * fillrate / (1024 * 1024));
|
|
||||||
}
|
|
||||||
|
|
||||||
m_wnd->SetWindowText(s.c_str());
|
|
||||||
}
|
|
||||||
|
|
||||||
GSVector4i r = m_wnd->GetClientRect();
|
|
||||||
|
|
||||||
m_dev->Present(r.fit(m_aspectratio), 0);
|
|
||||||
}
|
|
||||||
|
|
||||||
bool GPURenderer::MakeSnapshot(const std::string& path)
|
|
||||||
{
|
|
||||||
time_t t = time(NULL);
|
|
||||||
|
|
||||||
char buff[16];
|
|
||||||
|
|
||||||
if(!strftime(buff, sizeof(buff), "%Y%m%d%H%M%S", localtime(&t)))
|
|
||||||
{
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
if(GSTexture* t = m_dev->GetCurrent())
|
|
||||||
{
|
|
||||||
return t->Save(format("%s_%s.bmp", path.c_str(), buff));
|
|
||||||
}
|
|
||||||
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
#ifdef _WIN32
|
|
||||||
|
|
||||||
LRESULT CALLBACK GPURenderer::WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
|
|
||||||
{
|
|
||||||
auto i = m_wnd2gpu.find(hWnd);
|
|
||||||
|
|
||||||
if(i != m_wnd2gpu.end())
|
|
||||||
{
|
|
||||||
return i->second->OnMessage(message, wParam, lParam);
|
|
||||||
}
|
|
||||||
|
|
||||||
ASSERT(0);
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
LRESULT GPURenderer::OnMessage(UINT message, WPARAM wParam, LPARAM lParam)
|
|
||||||
{
|
|
||||||
if(message == WM_KEYUP)
|
|
||||||
{
|
|
||||||
switch(wParam)
|
|
||||||
{
|
|
||||||
case VK_DELETE:
|
|
||||||
m_filter = (m_filter + 1) % 3;
|
|
||||||
theApp.SetConfig("filter", m_filter);
|
|
||||||
return 0;
|
|
||||||
case VK_END:
|
|
||||||
m_dither = m_dither ? 0 : 1;
|
|
||||||
theApp.SetConfig("dithering", m_dither);
|
|
||||||
return 0;
|
|
||||||
case VK_NEXT:
|
|
||||||
m_aspectratio = (m_aspectratio + 1) % 3;
|
|
||||||
theApp.SetConfig("AspectRatio", m_aspectratio);
|
|
||||||
return 0;
|
|
||||||
case VK_PRIOR:
|
|
||||||
m_fxaa = !m_fxaa;
|
|
||||||
theApp.SetConfig("fxaa", m_fxaa);
|
|
||||||
return 0;
|
|
||||||
case VK_HOME:
|
|
||||||
m_shaderfx = !m_shaderfx;
|
|
||||||
theApp.SetConfig("shaderfx", m_shaderfx);
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return CallWindowProc(m_wndproc, m_hWnd, message, wParam, lParam);
|
|
||||||
}
|
|
||||||
|
|
||||||
#endif
|
|
|
@ -1,202 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2007-2009 Gabest
|
|
||||||
* http://www.gabest.org
|
|
||||||
*
|
|
||||||
* 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; either version 2, 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 received a copy of the GNU General Public License
|
|
||||||
* along with GNU Make; see the file COPYING. If not, write to
|
|
||||||
* the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA USA.
|
|
||||||
* http://www.gnu.org/copyleft/gpl.html
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
|
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include "GPUState.h"
|
|
||||||
#include "Renderers/Common/GSVertexList.h"
|
|
||||||
#include "Renderers/Common/GSDevice.h"
|
|
||||||
#ifdef _WIN32
|
|
||||||
#include "Window/GSWndDX.h"
|
|
||||||
#endif
|
|
||||||
|
|
||||||
class GPURenderer : public GPUState
|
|
||||||
{
|
|
||||||
bool Merge();
|
|
||||||
|
|
||||||
protected:
|
|
||||||
GSDevice* m_dev;
|
|
||||||
int m_filter;
|
|
||||||
int m_dither;
|
|
||||||
int m_aspectratio;
|
|
||||||
int m_vsync;
|
|
||||||
bool m_shaderfx;
|
|
||||||
bool m_fxaa;
|
|
||||||
bool m_shadeboost;
|
|
||||||
GSVector2i m_scale;
|
|
||||||
|
|
||||||
virtual void ResetDevice() {}
|
|
||||||
virtual GSTexture* GetOutput() = 0;
|
|
||||||
|
|
||||||
#ifdef _WIN32
|
|
||||||
|
|
||||||
HWND m_hWnd;
|
|
||||||
WNDPROC m_wndproc;
|
|
||||||
static std::map<HWND, GPURenderer*> m_wnd2gpu;
|
|
||||||
|
|
||||||
static LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam);
|
|
||||||
LRESULT OnMessage(UINT message, WPARAM wParam, LPARAM lParam);
|
|
||||||
|
|
||||||
#endif
|
|
||||||
|
|
||||||
std::shared_ptr<GSWnd> m_wnd;
|
|
||||||
|
|
||||||
public:
|
|
||||||
GPURenderer(GSDevice* dev);
|
|
||||||
virtual ~GPURenderer();
|
|
||||||
|
|
||||||
virtual bool Create(void* hWnd);
|
|
||||||
virtual void VSync();
|
|
||||||
virtual bool MakeSnapshot(const std::string& path);
|
|
||||||
};
|
|
||||||
|
|
||||||
template<class Vertex>
|
|
||||||
class GPURendererT : public GPURenderer
|
|
||||||
{
|
|
||||||
protected:
|
|
||||||
Vertex* m_vertices;
|
|
||||||
int m_count;
|
|
||||||
int m_maxcount;
|
|
||||||
GSVertexList<Vertex> m_vl;
|
|
||||||
|
|
||||||
void Reset()
|
|
||||||
{
|
|
||||||
m_count = 0;
|
|
||||||
m_vl.RemoveAll();
|
|
||||||
|
|
||||||
GPURenderer::Reset();
|
|
||||||
}
|
|
||||||
|
|
||||||
void ResetPrim()
|
|
||||||
{
|
|
||||||
m_vl.RemoveAll();
|
|
||||||
}
|
|
||||||
|
|
||||||
void FlushPrim()
|
|
||||||
{
|
|
||||||
if(m_count > 0)
|
|
||||||
{
|
|
||||||
/*
|
|
||||||
Dump("db");
|
|
||||||
|
|
||||||
if(m_env.PRIM.TME)
|
|
||||||
{
|
|
||||||
GSVector4i r;
|
|
||||||
|
|
||||||
r.left = m_env.STATUS.TX << 6;
|
|
||||||
r.top = m_env.STATUS.TY << 8;
|
|
||||||
r.right = r.left + 256;
|
|
||||||
r.bottom = r.top + 256;
|
|
||||||
|
|
||||||
Dump(format("da_%d_%d_%d_%d_%d", m_env.STATUS.TP, r.left, r.top, r.right, r.bottom).c_str(), m_env.STATUS.TP, r, false);
|
|
||||||
}
|
|
||||||
*/
|
|
||||||
|
|
||||||
Draw();
|
|
||||||
|
|
||||||
m_count = 0;
|
|
||||||
|
|
||||||
//Dump("dc", false);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void GrowVertexBuffer()
|
|
||||||
{
|
|
||||||
int maxcount = std::max<int>(m_maxcount * 3 / 2, 10000);
|
|
||||||
Vertex* vertices = (Vertex*)_aligned_malloc(sizeof(Vertex) * maxcount, 32);
|
|
||||||
|
|
||||||
if(vertices == NULL)
|
|
||||||
{
|
|
||||||
printf("GSdx: failed to allocate %d bytes for verticles.\n", (int)sizeof(Vertex) * maxcount);
|
|
||||||
throw GSDXError();
|
|
||||||
}
|
|
||||||
|
|
||||||
if(m_vertices != NULL)
|
|
||||||
{
|
|
||||||
memcpy(vertices, m_vertices, sizeof(Vertex) * m_maxcount);
|
|
||||||
_aligned_free(m_vertices);
|
|
||||||
}
|
|
||||||
|
|
||||||
m_vertices = vertices;
|
|
||||||
m_maxcount = maxcount - 100;
|
|
||||||
}
|
|
||||||
|
|
||||||
__forceinline Vertex* DrawingKick(int& count)
|
|
||||||
{
|
|
||||||
count = (int)m_env.PRIM.VTX;
|
|
||||||
|
|
||||||
if(m_vl.GetCount() < count)
|
|
||||||
{
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
if(m_count >= m_maxcount)
|
|
||||||
{
|
|
||||||
GrowVertexBuffer();
|
|
||||||
}
|
|
||||||
|
|
||||||
Vertex* v = &m_vertices[m_count];
|
|
||||||
|
|
||||||
switch(m_env.PRIM.TYPE)
|
|
||||||
{
|
|
||||||
case GPU_POLYGON:
|
|
||||||
m_vl.GetAt(0, v[0]);
|
|
||||||
m_vl.GetAt(1, v[1]);
|
|
||||||
m_vl.GetAt(2, v[2]);
|
|
||||||
m_vl.RemoveAll();
|
|
||||||
break;
|
|
||||||
case GPU_LINE:
|
|
||||||
m_vl.GetAt(0, v[0]);
|
|
||||||
m_vl.GetAt(1, v[1]);
|
|
||||||
m_vl.RemoveAll();
|
|
||||||
break;
|
|
||||||
case GPU_SPRITE:
|
|
||||||
m_vl.GetAt(0, v[0]);
|
|
||||||
m_vl.GetAt(1, v[1]);
|
|
||||||
m_vl.RemoveAll();
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
ASSERT(0);
|
|
||||||
m_vl.RemoveAll();
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
return v;
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual void VertexKick() = 0;
|
|
||||||
|
|
||||||
virtual void Draw() = 0;
|
|
||||||
|
|
||||||
public:
|
|
||||||
GPURendererT(GSDevice* dev)
|
|
||||||
: GPURenderer(dev)
|
|
||||||
, m_vertices(NULL)
|
|
||||||
, m_count(0)
|
|
||||||
, m_maxcount(0)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual ~GPURendererT()
|
|
||||||
{
|
|
||||||
if(m_vertices) _aligned_free(m_vertices);
|
|
||||||
}
|
|
||||||
};
|
|
|
@ -1,205 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2007-2009 Gabest
|
|
||||||
* http://www.gabest.org
|
|
||||||
*
|
|
||||||
* 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; either version 2, 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 received a copy of the GNU General Public License
|
|
||||||
* along with GNU Make; see the file COPYING. If not, write to
|
|
||||||
* the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA USA.
|
|
||||||
* http://www.gnu.org/copyleft/gpl.html
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
|
|
||||||
#include "stdafx.h"
|
|
||||||
#include "GPURendererSW.h"
|
|
||||||
//#include "GSdx.h"
|
|
||||||
|
|
||||||
GPURendererSW::GPURendererSW(GSDevice* dev, int threads)
|
|
||||||
: GPURendererT<GSVertexSW>(dev)
|
|
||||||
, m_texture(NULL)
|
|
||||||
{
|
|
||||||
m_output = (uint32*)_aligned_malloc(m_mem.GetWidth() * m_mem.GetHeight() * sizeof(uint32), 32);
|
|
||||||
|
|
||||||
m_rl = GSRasterizerList::Create<GPUDrawScanline>(threads, &m_perfmon);
|
|
||||||
}
|
|
||||||
|
|
||||||
GPURendererSW::~GPURendererSW()
|
|
||||||
{
|
|
||||||
delete m_texture;
|
|
||||||
|
|
||||||
delete m_rl;
|
|
||||||
|
|
||||||
_aligned_free(m_output);
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPURendererSW::ResetDevice()
|
|
||||||
{
|
|
||||||
delete m_texture;
|
|
||||||
|
|
||||||
m_texture = NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
GSTexture* GPURendererSW::GetOutput()
|
|
||||||
{
|
|
||||||
GSVector4i r = m_env.GetDisplayRect();
|
|
||||||
|
|
||||||
r.left <<= m_scale.x;
|
|
||||||
r.top <<= m_scale.y;
|
|
||||||
r.right <<= m_scale.x;
|
|
||||||
r.bottom <<= m_scale.y;
|
|
||||||
|
|
||||||
if(m_dev->ResizeTexture(&m_texture, r.width(), r.height()))
|
|
||||||
{
|
|
||||||
m_mem.ReadFrame32(r, m_output, !!m_env.STATUS.ISRGB24);
|
|
||||||
|
|
||||||
m_texture->Update(r.rsize(), m_output, m_mem.GetWidth() * sizeof(uint32));
|
|
||||||
}
|
|
||||||
|
|
||||||
return m_texture;
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPURendererSW::Draw()
|
|
||||||
{
|
|
||||||
GPUDrawScanline::SharedData* sd = new GPUDrawScanline::SharedData();
|
|
||||||
|
|
||||||
std::shared_ptr<GSRasterizerData> data(sd);
|
|
||||||
|
|
||||||
GPUScanlineGlobalData& gd = sd->global;
|
|
||||||
|
|
||||||
const GPUDrawingEnvironment& env = m_env;
|
|
||||||
|
|
||||||
gd.sel.key = 0;
|
|
||||||
gd.sel.iip = env.PRIM.IIP;
|
|
||||||
gd.sel.me = env.STATUS.ME;
|
|
||||||
|
|
||||||
if(env.PRIM.ABE)
|
|
||||||
{
|
|
||||||
gd.sel.abe = env.PRIM.ABE;
|
|
||||||
gd.sel.abr = env.STATUS.ABR;
|
|
||||||
}
|
|
||||||
|
|
||||||
gd.sel.tge = env.PRIM.TGE;
|
|
||||||
|
|
||||||
if(env.PRIM.TME)
|
|
||||||
{
|
|
||||||
gd.sel.tme = env.PRIM.TME;
|
|
||||||
gd.sel.tlu = env.STATUS.TP < 2;
|
|
||||||
gd.sel.twin = (env.TWIN.u32 & 0xfffff) != 0;
|
|
||||||
gd.sel.ltf = m_filter == 1 && env.PRIM.TYPE == GPU_POLYGON || m_filter == 2 ? 1 : 0;
|
|
||||||
|
|
||||||
const void* t = m_mem.GetTexture(env.STATUS.TP, env.STATUS.TX, env.STATUS.TY);
|
|
||||||
|
|
||||||
if(!t) {ASSERT(0); return;}
|
|
||||||
|
|
||||||
gd.tex = t;
|
|
||||||
|
|
||||||
gd.clut = (uint16*)_aligned_malloc(sizeof(uint16) * 256, 32);
|
|
||||||
|
|
||||||
memcpy(gd.clut, m_mem.GetCLUT(env.STATUS.TP, env.CLUT.X, env.CLUT.Y), sizeof(uint16) * (env.STATUS.TP == 0 ? 16 : 256));
|
|
||||||
|
|
||||||
gd.twin = GSVector4i(env.TWIN.TWW, env.TWIN.TWH, env.TWIN.TWX, env.TWIN.TWY);
|
|
||||||
}
|
|
||||||
|
|
||||||
gd.sel.dtd = m_dither ? env.STATUS.DTD : 0;
|
|
||||||
gd.sel.md = env.STATUS.MD;
|
|
||||||
gd.sel.sprite = env.PRIM.TYPE == GPU_SPRITE;
|
|
||||||
gd.sel.scalex = m_mem.GetScale().x;
|
|
||||||
|
|
||||||
gd.vm = m_mem.GetPixelAddress(0, 0);
|
|
||||||
|
|
||||||
data->scissor.left = (int)m_env.DRAREATL.X << m_scale.x;
|
|
||||||
data->scissor.top = (int)m_env.DRAREATL.Y << m_scale.y;
|
|
||||||
data->scissor.right = std::min((int)(m_env.DRAREABR.X + 1) << m_scale.x, m_mem.GetWidth());
|
|
||||||
data->scissor.bottom = std::min((int)(m_env.DRAREABR.Y + 1) << m_scale.y, m_mem.GetHeight());
|
|
||||||
|
|
||||||
data->buff = (uint8*)_aligned_malloc(sizeof(GSVertexSW) * m_count, 32);
|
|
||||||
data->vertex = (GSVertexSW*)data->buff;
|
|
||||||
data->vertex_count = m_count;
|
|
||||||
|
|
||||||
memcpy(data->vertex, m_vertices, sizeof(GSVertexSW) * m_count);
|
|
||||||
|
|
||||||
data->frame = m_perfmon.GetFrame();
|
|
||||||
|
|
||||||
int prims = 0;
|
|
||||||
|
|
||||||
switch(env.PRIM.TYPE)
|
|
||||||
{
|
|
||||||
case GPU_POLYGON: data->primclass = GS_TRIANGLE_CLASS; prims = data->vertex_count / 3; break;
|
|
||||||
case GPU_LINE: data->primclass = GS_LINE_CLASS; prims = data->vertex_count / 2; break;
|
|
||||||
case GPU_SPRITE: data->primclass = GS_SPRITE_CLASS; prims = data->vertex_count / 2; break;
|
|
||||||
default: __assume(0);
|
|
||||||
}
|
|
||||||
|
|
||||||
// TODO: VertexTrace
|
|
||||||
|
|
||||||
GSVector4 tl(+1e10f);
|
|
||||||
GSVector4 br(-1e10f);
|
|
||||||
|
|
||||||
GSVertexSW* v = data->vertex;
|
|
||||||
|
|
||||||
for(int i = 0, j = data->vertex_count; i < j; i++)
|
|
||||||
{
|
|
||||||
GSVector4 p = v[i].p;
|
|
||||||
|
|
||||||
tl = tl.min(p);
|
|
||||||
br = br.max(p);
|
|
||||||
}
|
|
||||||
|
|
||||||
data->bbox = GSVector4i(tl.xyxy(br));
|
|
||||||
|
|
||||||
GSVector4i r = data->bbox.rintersect(data->scissor);
|
|
||||||
|
|
||||||
r.left >>= m_scale.x;
|
|
||||||
r.top >>= m_scale.y;
|
|
||||||
r.right >>= m_scale.x;
|
|
||||||
r.bottom >>= m_scale.y;
|
|
||||||
|
|
||||||
Invalidate(r);
|
|
||||||
|
|
||||||
m_rl->Queue(data);
|
|
||||||
|
|
||||||
m_rl->Sync();
|
|
||||||
|
|
||||||
m_perfmon.Put(GSPerfMon::Draw, 1);
|
|
||||||
m_perfmon.Put(GSPerfMon::Prim, prims);
|
|
||||||
m_perfmon.Put(GSPerfMon::Fillrate, m_rl->GetPixels());
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPURendererSW::VertexKick()
|
|
||||||
{
|
|
||||||
GSVertexSW& dst = m_vl.AddTail();
|
|
||||||
|
|
||||||
// TODO: x/y + off.x/y should wrap around at +/-1024
|
|
||||||
|
|
||||||
int x = (int)(m_v.XY.X + m_env.DROFF.X) << m_scale.x;
|
|
||||||
int y = (int)(m_v.XY.Y + m_env.DROFF.Y) << m_scale.y;
|
|
||||||
|
|
||||||
int u = m_v.UV.X;
|
|
||||||
int v = m_v.UV.Y;
|
|
||||||
|
|
||||||
GSVector4 pt(x, y, u, v);
|
|
||||||
|
|
||||||
dst.p = pt.xyxy(GSVector4::zero());
|
|
||||||
dst.t = (pt.zwzw(GSVector4::zero()) + GSVector4(0.125f)) * 256.0f;
|
|
||||||
// dst.c = GSVector4(m_v.RGB.u32) * 128.0f;
|
|
||||||
dst.c = GSVector4(GSVector4i::load((int)m_v.RGB.u32).u8to32() << 7);
|
|
||||||
|
|
||||||
int count = 0;
|
|
||||||
|
|
||||||
if(DrawingKick(count))
|
|
||||||
{
|
|
||||||
// TODO
|
|
||||||
|
|
||||||
m_count += count;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
|
@ -1,42 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2007-2009 Gabest
|
|
||||||
* http://www.gabest.org
|
|
||||||
*
|
|
||||||
* 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; either version 2, 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 received a copy of the GNU General Public License
|
|
||||||
* along with GNU Make; see the file COPYING. If not, write to
|
|
||||||
* the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA USA.
|
|
||||||
* http://www.gnu.org/copyleft/gpl.html
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
|
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include "GPURenderer.h"
|
|
||||||
#include "GPUDrawScanline.h"
|
|
||||||
|
|
||||||
class GPURendererSW : public GPURendererT<GSVertexSW>
|
|
||||||
{
|
|
||||||
protected:
|
|
||||||
IRasterizer* m_rl;
|
|
||||||
GSTexture* m_texture;
|
|
||||||
uint32* m_output;
|
|
||||||
|
|
||||||
void ResetDevice();
|
|
||||||
GSTexture* GetOutput();
|
|
||||||
void VertexKick();
|
|
||||||
void Draw();
|
|
||||||
|
|
||||||
public:
|
|
||||||
GPURendererSW(GSDevice* dev, int threads);
|
|
||||||
virtual ~GPURendererSW();
|
|
||||||
};
|
|
|
@ -1,78 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2007-2009 Gabest
|
|
||||||
* http://www.gabest.org
|
|
||||||
*
|
|
||||||
* 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; either version 2, 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 received a copy of the GNU General Public License
|
|
||||||
* along with GNU Make; see the file COPYING. If not, write to
|
|
||||||
* the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA USA.
|
|
||||||
* http://www.gnu.org/copyleft/gpl.html
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
|
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include "GSVector.h"
|
|
||||||
#include "GPULocalMemory.h"
|
|
||||||
|
|
||||||
union GPUScanlineSelector
|
|
||||||
{
|
|
||||||
struct
|
|
||||||
{
|
|
||||||
uint32 iip:1; // 0
|
|
||||||
uint32 me:1; // 1
|
|
||||||
uint32 abe:1; // 2
|
|
||||||
uint32 abr:2; // 3
|
|
||||||
uint32 tge:1; // 5
|
|
||||||
uint32 tme:1; // 6
|
|
||||||
uint32 twin:1; // 7
|
|
||||||
uint32 tlu:1; // 8
|
|
||||||
uint32 dtd:1; // 9
|
|
||||||
uint32 ltf:1; // 10
|
|
||||||
uint32 md:1; // 11
|
|
||||||
uint32 sprite:1; // 12
|
|
||||||
uint32 scalex:2; // 13
|
|
||||||
};
|
|
||||||
|
|
||||||
struct
|
|
||||||
{
|
|
||||||
uint32 _pad1:1; // 0
|
|
||||||
uint32 rfb:2; // 1
|
|
||||||
uint32 _pad2:2; // 3
|
|
||||||
uint32 tfx:2; // 5
|
|
||||||
};
|
|
||||||
|
|
||||||
uint32 key;
|
|
||||||
|
|
||||||
operator uint32() const {return key;}
|
|
||||||
};
|
|
||||||
|
|
||||||
struct alignas(32) GPUScanlineGlobalData
|
|
||||||
{
|
|
||||||
GPUScanlineSelector sel;
|
|
||||||
|
|
||||||
void* vm;
|
|
||||||
const void* tex;
|
|
||||||
uint16* clut;
|
|
||||||
GSVector4i twin; // TWW, TWH, TWX, TWY
|
|
||||||
};
|
|
||||||
|
|
||||||
struct alignas(32) GPUScanlineLocalData
|
|
||||||
{
|
|
||||||
const GPUScanlineGlobalData* gd;
|
|
||||||
|
|
||||||
struct {GSVector4i u, v;} twin[3];
|
|
||||||
struct {GSVector4i s, t, r, g, b, _pad[3];} d;
|
|
||||||
struct {GSVector4i st, c;} d8;
|
|
||||||
|
|
||||||
struct {GSVector4i s, t, r, b, g, uf, vf, dither, fd, test;} temp;
|
|
||||||
};
|
|
|
@ -1,126 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2007-2009 Gabest
|
|
||||||
* http://www.gabest.org
|
|
||||||
*
|
|
||||||
* 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; either version 2, 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 received a copy of the GNU General Public License
|
|
||||||
* along with GNU Make; see the file COPYING. If not, write to
|
|
||||||
* the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA USA.
|
|
||||||
* http://www.gnu.org/copyleft/gpl.html
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
|
|
||||||
#include "stdafx.h"
|
|
||||||
#include "GSdx.h"
|
|
||||||
#include "GSUtil.h"
|
|
||||||
#include "resource.h"
|
|
||||||
#include "GPU.h"
|
|
||||||
#include "GPUSettingsDlg.h"
|
|
||||||
|
|
||||||
GPUSettingsDlg::GPUSettingsDlg()
|
|
||||||
: GSDialog(IDD_GPUCONFIG)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPUSettingsDlg::OnInit()
|
|
||||||
{
|
|
||||||
__super::OnInit();
|
|
||||||
|
|
||||||
// FIXME: Someone can fix this to use D3D11 or OGL Device, D3D9 is no longer supported.
|
|
||||||
ComboBoxAppend(IDC_RESOLUTION, "Please select...");
|
|
||||||
|
|
||||||
ComboBoxInit(IDC_RENDERER, theApp.m_gpu_renderers, theApp.GetConfigI("Renderer"));
|
|
||||||
ComboBoxInit(IDC_FILTER, theApp.m_gpu_filter, theApp.GetConfigI("filter"));
|
|
||||||
ComboBoxInit(IDC_DITHERING, theApp.m_gpu_dithering, theApp.GetConfigI("dithering"));
|
|
||||||
ComboBoxInit(IDC_ASPECTRATIO, theApp.m_gpu_aspectratio, theApp.GetConfigI("AspectRatio"));
|
|
||||||
ComboBoxInit(IDC_SCALE, theApp.m_gpu_scale, theApp.GetConfigI("scale_x") | (theApp.GetConfigI("scale_y") << 2));
|
|
||||||
|
|
||||||
CheckDlgButton(m_hWnd, IDC_WINDOWED, theApp.GetConfigB("windowed"));
|
|
||||||
|
|
||||||
SendMessage(GetDlgItem(m_hWnd, IDC_SWTHREADS), UDM_SETRANGE, 0, MAKELPARAM(16, 0));
|
|
||||||
SendMessage(GetDlgItem(m_hWnd, IDC_SWTHREADS), UDM_SETPOS, 0, MAKELPARAM(theApp.GetConfigI("extrathreads"), 0));
|
|
||||||
|
|
||||||
UpdateControls();
|
|
||||||
}
|
|
||||||
|
|
||||||
bool GPUSettingsDlg::OnCommand(HWND hWnd, UINT id, UINT code)
|
|
||||||
{
|
|
||||||
if(id == IDC_RENDERER && code == CBN_SELCHANGE)
|
|
||||||
{
|
|
||||||
UpdateControls();
|
|
||||||
}
|
|
||||||
else if(id == IDOK)
|
|
||||||
{
|
|
||||||
INT_PTR data;
|
|
||||||
|
|
||||||
if(ComboBoxGetSelData(IDC_RENDERER, data))
|
|
||||||
{
|
|
||||||
theApp.SetConfig("Renderer", (int)data);
|
|
||||||
}
|
|
||||||
|
|
||||||
if(ComboBoxGetSelData(IDC_FILTER, data))
|
|
||||||
{
|
|
||||||
theApp.SetConfig("filter", (int)data);
|
|
||||||
}
|
|
||||||
|
|
||||||
if(ComboBoxGetSelData(IDC_DITHERING, data))
|
|
||||||
{
|
|
||||||
theApp.SetConfig("dithering", (int)data);
|
|
||||||
}
|
|
||||||
|
|
||||||
if(ComboBoxGetSelData(IDC_ASPECTRATIO, data))
|
|
||||||
{
|
|
||||||
theApp.SetConfig("AspectRatio", (int)data);
|
|
||||||
}
|
|
||||||
|
|
||||||
if(ComboBoxGetSelData(IDC_SCALE, data))
|
|
||||||
{
|
|
||||||
theApp.SetConfig("scale_x", data & 3);
|
|
||||||
theApp.SetConfig("scale_y", (data >> 2) & 3);
|
|
||||||
}
|
|
||||||
|
|
||||||
theApp.SetConfig("extrathreads", (int)SendMessage(GetDlgItem(m_hWnd, IDC_SWTHREADS), UDM_GETPOS, 0, 0));
|
|
||||||
theApp.SetConfig("windowed", (int)IsDlgButtonChecked(m_hWnd, IDC_WINDOWED));
|
|
||||||
}
|
|
||||||
|
|
||||||
return __super::OnCommand(hWnd, id, code);
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPUSettingsDlg::UpdateControls()
|
|
||||||
{
|
|
||||||
INT_PTR i;
|
|
||||||
|
|
||||||
if(ComboBoxGetSelData(IDC_RENDERER, i))
|
|
||||||
{
|
|
||||||
GPURendererType renderer = static_cast<GPURendererType>(i);
|
|
||||||
|
|
||||||
bool dx11 = renderer == GPURendererType::D3D11_SW;
|
|
||||||
bool null = renderer == GPURendererType::NULL_Renderer;
|
|
||||||
|
|
||||||
ShowWindow(GetDlgItem(m_hWnd, IDC_LOGO11), dx11 ? SW_SHOW : SW_HIDE);
|
|
||||||
ShowWindow(GetDlgItem(m_hWnd, IDC_NULL), null ? SW_SHOW : SW_HIDE);
|
|
||||||
|
|
||||||
EnableWindow(GetDlgItem(m_hWnd, IDC_RESOLUTION), false);
|
|
||||||
EnableWindow(GetDlgItem(m_hWnd, IDC_RESOLUTION_TEXT), false);
|
|
||||||
EnableWindow(GetDlgItem(m_hWnd, IDC_FILTER), dx11);
|
|
||||||
EnableWindow(GetDlgItem(m_hWnd, IDC_FILTER_TEXT), dx11);
|
|
||||||
EnableWindow(GetDlgItem(m_hWnd, IDC_DITHERING), dx11);
|
|
||||||
EnableWindow(GetDlgItem(m_hWnd, IDC_DITHERING_TEXT), dx11);
|
|
||||||
EnableWindow(GetDlgItem(m_hWnd, IDC_ASPECTRATIO), dx11);
|
|
||||||
EnableWindow(GetDlgItem(m_hWnd, IDC_ASPECTRATIO_TEXT), dx11);
|
|
||||||
EnableWindow(GetDlgItem(m_hWnd, IDC_SCALE), dx11);
|
|
||||||
EnableWindow(GetDlgItem(m_hWnd, IDC_SCALE_TEXT), dx11);
|
|
||||||
EnableWindow(GetDlgItem(m_hWnd, IDC_SWTHREADS), dx11);
|
|
||||||
EnableWindow(GetDlgItem(m_hWnd, IDC_SWTHREADS_TEXT), dx11);
|
|
||||||
EnableWindow(GetDlgItem(m_hWnd, IDC_SWTHREADS_EDIT), dx11);
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -1,37 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2007-2009 Gabest
|
|
||||||
* http://www.gabest.org
|
|
||||||
*
|
|
||||||
* 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; either version 2, 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 received a copy of the GNU General Public License
|
|
||||||
* along with GNU Make; see the file COPYING. If not, write to
|
|
||||||
* the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA USA.
|
|
||||||
* http://www.gnu.org/copyleft/gpl.html
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
|
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include "Window/GSDialog.h"
|
|
||||||
#include "Window/GSSetting.h"
|
|
||||||
|
|
||||||
class GPUSettingsDlg : public GSDialog
|
|
||||||
{
|
|
||||||
void UpdateControls();
|
|
||||||
|
|
||||||
protected:
|
|
||||||
void OnInit();
|
|
||||||
bool OnCommand(HWND hWnd, UINT id, UINT code);
|
|
||||||
|
|
||||||
public:
|
|
||||||
GPUSettingsDlg();
|
|
||||||
};
|
|
|
@ -1,236 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2007-2009 Gabest
|
|
||||||
* http://www.gabest.org
|
|
||||||
*
|
|
||||||
* 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; either version 2, 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 received a copy of the GNU General Public License
|
|
||||||
* along with GNU Make; see the file COPYING. If not, write to
|
|
||||||
* the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA USA.
|
|
||||||
* http://www.gnu.org/copyleft/gpl.html
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
|
|
||||||
// TODO: x64
|
|
||||||
|
|
||||||
#include "stdafx.h"
|
|
||||||
#include "GPUSetupPrimCodeGenerator.h"
|
|
||||||
#include "Renderers/SW/GSVertexSW.h"
|
|
||||||
|
|
||||||
using namespace Xbyak;
|
|
||||||
|
|
||||||
static const int _args = 0;
|
|
||||||
static const int _vertex = _args + 4;
|
|
||||||
static const int _index = _args + 8;
|
|
||||||
static const int _dscan = _args + 12;
|
|
||||||
|
|
||||||
GPUSetupPrimCodeGenerator::GPUSetupPrimCodeGenerator(void* param, uint32 key, void* code, size_t maxsize)
|
|
||||||
: GSCodeGenerator(code, maxsize)
|
|
||||||
, m_local(*(GPUScanlineLocalData*)param)
|
|
||||||
{
|
|
||||||
m_sel.key = key;
|
|
||||||
|
|
||||||
Generate();
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPUSetupPrimCodeGenerator::Generate()
|
|
||||||
{
|
|
||||||
if(m_sel.tme && !m_sel.twin)
|
|
||||||
{
|
|
||||||
pcmpeqd(xmm0, xmm0);
|
|
||||||
|
|
||||||
if(m_sel.sprite)
|
|
||||||
{
|
|
||||||
// t = (GSVector4i(vertices[1].t) >> 8) - GSVector4i::x00000001();
|
|
||||||
|
|
||||||
mov(ecx, ptr[esp + _index]);
|
|
||||||
mov(ecx, ptr[ecx + sizeof(uint32) * 1]);
|
|
||||||
shl(ecx, 6); // * sizeof(GSVertexSW)
|
|
||||||
add(ecx, ptr[esp + _vertex]);
|
|
||||||
|
|
||||||
cvttps2dq(xmm1, ptr[ecx + offsetof(GSVertexSW, t)]);
|
|
||||||
psrld(xmm1, 8);
|
|
||||||
psrld(xmm0, 31);
|
|
||||||
psubd(xmm1, xmm0);
|
|
||||||
|
|
||||||
// t = t.ps32(t);
|
|
||||||
// t = t.upl16(t);
|
|
||||||
|
|
||||||
packssdw(xmm1, xmm1);
|
|
||||||
punpcklwd(xmm1, xmm1);
|
|
||||||
|
|
||||||
// m_local.twin[2].u = t.xxxx();
|
|
||||||
// m_local.twin[2].v = t.yyyy();
|
|
||||||
|
|
||||||
pshufd(xmm2, xmm1, _MM_SHUFFLE(0, 0, 0, 0));
|
|
||||||
pshufd(xmm3, xmm1, _MM_SHUFFLE(1, 1, 1, 1));
|
|
||||||
|
|
||||||
movdqa(ptr[&m_local.twin[2].u], xmm2);
|
|
||||||
movdqa(ptr[&m_local.twin[2].v], xmm3);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
// TODO: not really needed
|
|
||||||
|
|
||||||
// m_local.twin[2].u = GSVector4i::x00ff();
|
|
||||||
// m_local.twin[2].v = GSVector4i::x00ff();
|
|
||||||
|
|
||||||
psrlw(xmm0, 8);
|
|
||||||
|
|
||||||
movdqa(ptr[&m_local.twin[2].u], xmm0);
|
|
||||||
movdqa(ptr[&m_local.twin[2].v], xmm0);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if(m_sel.tme || m_sel.iip && m_sel.tfx != 3)
|
|
||||||
{
|
|
||||||
mov(edx, dword[esp + _dscan]);
|
|
||||||
|
|
||||||
for(int i = 0; i < 3; i++)
|
|
||||||
{
|
|
||||||
movaps(Xmm(5 + i), ptr[&m_shift[i]]);
|
|
||||||
}
|
|
||||||
|
|
||||||
// GSVector4 dt = dscan.t;
|
|
||||||
// GSVector4 dc = dscan.c;
|
|
||||||
|
|
||||||
movaps(xmm4, ptr[edx + offsetof(GSVertexSW, c)]);
|
|
||||||
movaps(xmm3, ptr[edx + offsetof(GSVertexSW, t)]);
|
|
||||||
|
|
||||||
// GSVector4i dtc8 = GSVector4i(dt * 8.0f).ps32(GSVector4i(dc * 8.0f));
|
|
||||||
|
|
||||||
movaps(xmm1, xmm3);
|
|
||||||
mulps(xmm1, xmm5);
|
|
||||||
cvttps2dq(xmm1, xmm1);
|
|
||||||
movaps(xmm2, xmm4);
|
|
||||||
mulps(xmm2, xmm5);
|
|
||||||
cvttps2dq(xmm2, xmm2);
|
|
||||||
packssdw(xmm1, xmm2);
|
|
||||||
|
|
||||||
if(m_sel.tme)
|
|
||||||
{
|
|
||||||
// m_local.d8.st = dtc8.upl16(dtc8);
|
|
||||||
|
|
||||||
movdqa(xmm0, xmm1);
|
|
||||||
punpcklwd(xmm0, xmm0);
|
|
||||||
movdqa(ptr[&m_local.d8.st], xmm0);
|
|
||||||
}
|
|
||||||
|
|
||||||
if(m_sel.iip && m_sel.tfx != 3)
|
|
||||||
{
|
|
||||||
// m_local.d8.c = dtc8.uph16(dtc8);
|
|
||||||
|
|
||||||
punpckhwd(xmm1, xmm1);
|
|
||||||
movdqa(ptr[&m_local.d8.c], xmm1);
|
|
||||||
}
|
|
||||||
|
|
||||||
// xmm3 = dt
|
|
||||||
// xmm4 = dc
|
|
||||||
// xmm6 = ps0123
|
|
||||||
// xmm7 = ps4567
|
|
||||||
// xmm0, xmm1, xmm2, xmm5 = free
|
|
||||||
|
|
||||||
if(m_sel.tme)
|
|
||||||
{
|
|
||||||
// GSVector4 dtx = dt.xxxx();
|
|
||||||
// GSVector4 dty = dt.yyyy();
|
|
||||||
|
|
||||||
movaps(xmm0, xmm3);
|
|
||||||
shufps(xmm3, xmm3, _MM_SHUFFLE(0, 0, 0, 0));
|
|
||||||
shufps(xmm0, xmm0, _MM_SHUFFLE(1, 1, 1, 1));
|
|
||||||
|
|
||||||
// m_local.d.s = GSVector4i(dtx * ps0123).ps32(GSVector4i(dtx * ps4567));
|
|
||||||
|
|
||||||
movaps(xmm1, xmm3);
|
|
||||||
mulps(xmm3, xmm6);
|
|
||||||
mulps(xmm1, xmm7);
|
|
||||||
cvttps2dq(xmm3, xmm3);
|
|
||||||
cvttps2dq(xmm1, xmm1);
|
|
||||||
packssdw(xmm3, xmm1);
|
|
||||||
movdqa(ptr[&m_local.d.s], xmm3);
|
|
||||||
|
|
||||||
// m_local.d.t = GSVector4i(dty * ps0123).ps32(GSVector4i(dty * ps4567));
|
|
||||||
|
|
||||||
movaps(xmm1, xmm0);
|
|
||||||
mulps(xmm0, xmm6);
|
|
||||||
mulps(xmm1, xmm7);
|
|
||||||
cvttps2dq(xmm0, xmm0);
|
|
||||||
cvttps2dq(xmm1, xmm1);
|
|
||||||
packssdw(xmm0, xmm1);
|
|
||||||
movdqa(ptr[&m_local.d.t], xmm0);
|
|
||||||
}
|
|
||||||
|
|
||||||
// xmm4 = dc
|
|
||||||
// xmm6 = ps0123
|
|
||||||
// xmm7 = ps4567
|
|
||||||
// xmm0, xmm1, zmm2, xmm3, xmm5 = free
|
|
||||||
|
|
||||||
if(m_sel.iip && m_sel.tfx != 3)
|
|
||||||
{
|
|
||||||
// GSVector4 dcx = dc.xxxx();
|
|
||||||
// GSVector4 dcy = dc.yyyy();
|
|
||||||
// GSVector4 dcz = dc.zzzz();
|
|
||||||
|
|
||||||
movaps(xmm0, xmm4);
|
|
||||||
movaps(xmm1, xmm4);
|
|
||||||
shufps(xmm4, xmm4, _MM_SHUFFLE(0, 0, 0, 0));
|
|
||||||
shufps(xmm0, xmm0, _MM_SHUFFLE(1, 1, 1, 1));
|
|
||||||
shufps(xmm1, xmm1, _MM_SHUFFLE(2, 2, 2, 2));
|
|
||||||
|
|
||||||
// m_local.d.r = GSVector4i(dcx * ps0123).ps32(GSVector4i(dcx * ps4567));
|
|
||||||
|
|
||||||
movaps(xmm2, xmm4);
|
|
||||||
mulps(xmm4, xmm6);
|
|
||||||
mulps(xmm2, xmm7);
|
|
||||||
cvttps2dq(xmm4, xmm4);
|
|
||||||
cvttps2dq(xmm2, xmm2);
|
|
||||||
packssdw(xmm4, xmm2);
|
|
||||||
movdqa(ptr[&m_local.d.r], xmm4);
|
|
||||||
|
|
||||||
// m_local.d.g = GSVector4i(dcy * ps0123).ps32(GSVector4i(dcy * ps4567));
|
|
||||||
|
|
||||||
movaps(xmm2, xmm0);
|
|
||||||
mulps(xmm0, xmm6);
|
|
||||||
mulps(xmm2, xmm7);
|
|
||||||
cvttps2dq(xmm0, xmm0);
|
|
||||||
cvttps2dq(xmm2, xmm2);
|
|
||||||
packssdw(xmm0, xmm2);
|
|
||||||
movdqa(ptr[&m_local.d.g], xmm0);
|
|
||||||
|
|
||||||
// m_local.d.b = GSVector4i(dcz * ps0123).ps32(GSVector4i(dcz * ps4567));
|
|
||||||
|
|
||||||
movaps(xmm2, xmm1);
|
|
||||||
mulps(xmm1, xmm6);
|
|
||||||
mulps(xmm2, xmm7);
|
|
||||||
cvttps2dq(xmm1, xmm1);
|
|
||||||
cvttps2dq(xmm2, xmm2);
|
|
||||||
packssdw(xmm1, xmm2);
|
|
||||||
movdqa(ptr[&m_local.d.b], xmm1);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
ret();
|
|
||||||
}
|
|
||||||
|
|
||||||
GSVector4 GPUSetupPrimCodeGenerator::m_shift[3];
|
|
||||||
|
|
||||||
void GPUSetupPrimCodeGenerator::InitVectors()
|
|
||||||
{
|
|
||||||
GSVector4 shift[3] =
|
|
||||||
{
|
|
||||||
GSVector4(8.0f, 8.0f, 8.0f, 8.0f),
|
|
||||||
GSVector4(0.0f, 1.0f, 2.0f, 3.0f),
|
|
||||||
GSVector4(4.0f, 5.0f, 6.0f, 7.0f),
|
|
||||||
};
|
|
||||||
|
|
||||||
for (size_t n = 0; n < countof(shift); ++n)
|
|
||||||
m_shift[n] = shift[n];
|
|
||||||
}
|
|
|
@ -1,42 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2007-2009 Gabest
|
|
||||||
* http://www.gabest.org
|
|
||||||
*
|
|
||||||
* 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; either version 2, 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 received a copy of the GNU General Public License
|
|
||||||
* along with GNU Make; see the file COPYING. If not, write to
|
|
||||||
* the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA USA.
|
|
||||||
* http://www.gnu.org/copyleft/gpl.html
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
|
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include "GPUScanlineEnvironment.h"
|
|
||||||
#include "Renderers/Common/GSFunctionMap.h"
|
|
||||||
|
|
||||||
class GPUSetupPrimCodeGenerator : public GSCodeGenerator
|
|
||||||
{
|
|
||||||
void operator = (const GPUSetupPrimCodeGenerator&);
|
|
||||||
|
|
||||||
GPUScanlineSelector m_sel;
|
|
||||||
GPUScanlineLocalData& m_local;
|
|
||||||
|
|
||||||
void Generate();
|
|
||||||
|
|
||||||
public:
|
|
||||||
GPUSetupPrimCodeGenerator(void* param, uint32 key, void* code, size_t maxsize);
|
|
||||||
|
|
||||||
static GSVector4 m_shift[3];
|
|
||||||
|
|
||||||
static void InitVectors();
|
|
||||||
};
|
|
|
@ -1,805 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2007-2009 Gabest
|
|
||||||
* http://www.gabest.org
|
|
||||||
*
|
|
||||||
* 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; either version 2, 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 received a copy of the GNU General Public License
|
|
||||||
* along with GNU Make; see the file COPYING. If not, write to
|
|
||||||
* the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA USA.
|
|
||||||
* http://www.gnu.org/copyleft/gpl.html
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
|
|
||||||
#include "stdafx.h"
|
|
||||||
#include "GPUState.h"
|
|
||||||
|
|
||||||
GPUState::GPUState()
|
|
||||||
: s_n(0)
|
|
||||||
{
|
|
||||||
memset(m_status, 0, sizeof(m_status));
|
|
||||||
|
|
||||||
for(size_t i = 0; i < countof(m_fpGPUStatusCommandHandlers); i++)
|
|
||||||
{
|
|
||||||
m_fpGPUStatusCommandHandlers[i] = &GPUState::SCH_Null;
|
|
||||||
}
|
|
||||||
|
|
||||||
m_fpGPUStatusCommandHandlers[0x00] = &GPUState::SCH_ResetGPU;
|
|
||||||
m_fpGPUStatusCommandHandlers[0x01] = &GPUState::SCH_ResetCommandBuffer;
|
|
||||||
m_fpGPUStatusCommandHandlers[0x02] = &GPUState::SCH_ResetIRQ;
|
|
||||||
m_fpGPUStatusCommandHandlers[0x03] = &GPUState::SCH_DisplayEnable;
|
|
||||||
m_fpGPUStatusCommandHandlers[0x04] = &GPUState::SCH_DMASetup;
|
|
||||||
m_fpGPUStatusCommandHandlers[0x05] = &GPUState::SCH_StartOfDisplayArea;
|
|
||||||
m_fpGPUStatusCommandHandlers[0x06] = &GPUState::SCH_HorizontalDisplayRange;
|
|
||||||
m_fpGPUStatusCommandHandlers[0x07] = &GPUState::SCH_VerticalDisplayRange;
|
|
||||||
m_fpGPUStatusCommandHandlers[0x08] = &GPUState::SCH_DisplayMode;
|
|
||||||
m_fpGPUStatusCommandHandlers[0x10] = &GPUState::SCH_GPUInfo;
|
|
||||||
|
|
||||||
m_fpGPUPacketHandler[0] = &GPUState::PH_Command;
|
|
||||||
m_fpGPUPacketHandler[1] = &GPUState::PH_Polygon;
|
|
||||||
m_fpGPUPacketHandler[2] = &GPUState::PH_Line;
|
|
||||||
m_fpGPUPacketHandler[3] = &GPUState::PH_Sprite;
|
|
||||||
m_fpGPUPacketHandler[4] = &GPUState::PH_Move;
|
|
||||||
m_fpGPUPacketHandler[5] = &GPUState::PH_Write;
|
|
||||||
m_fpGPUPacketHandler[6] = &GPUState::PH_Read;
|
|
||||||
m_fpGPUPacketHandler[7] = &GPUState::PH_Environment;
|
|
||||||
|
|
||||||
Reset();
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPUState::Reset()
|
|
||||||
{
|
|
||||||
m_env.Reset();
|
|
||||||
|
|
||||||
m_mem.Invalidate(GSVector4i(0, 0, 1024, 512));
|
|
||||||
|
|
||||||
memset(&m_v, 0, sizeof(m_v));
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPUState::Flush()
|
|
||||||
{
|
|
||||||
FlushPrim();
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPUState::SetPrim(GPUReg* r)
|
|
||||||
{
|
|
||||||
if(m_env.PRIM.TYPE != r->PRIM.TYPE)
|
|
||||||
{
|
|
||||||
ResetPrim();
|
|
||||||
}
|
|
||||||
|
|
||||||
GPURegPRIM PRIM = r->PRIM;
|
|
||||||
|
|
||||||
PRIM.VTX = 0;
|
|
||||||
|
|
||||||
switch(r->PRIM.TYPE)
|
|
||||||
{
|
|
||||||
case GPU_POLYGON:
|
|
||||||
PRIM.u32 = (r->PRIM.u32 & 0xF7000000) | 3; // TYPE IIP TME ABE TGE
|
|
||||||
break;
|
|
||||||
case GPU_LINE:
|
|
||||||
PRIM.u32 = (r->PRIM.u32 & 0xF2000000) | 2; // TYPE IIP ABE
|
|
||||||
PRIM.TGE = 1; // ?
|
|
||||||
break;
|
|
||||||
case GPU_SPRITE:
|
|
||||||
PRIM.u32 = (r->PRIM.u32 & 0xE7000000) | 2; // TYPE TME ABE TGE
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
if(m_env.PRIM.u32 != PRIM.u32)
|
|
||||||
{
|
|
||||||
Flush();
|
|
||||||
|
|
||||||
m_env.PRIM = PRIM;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPUState::SetCLUT(GPUReg* r)
|
|
||||||
{
|
|
||||||
uint32 mask = 0xFFFF0000; // X Y
|
|
||||||
|
|
||||||
uint32 value = (m_env.CLUT.u32 & ~mask) | (r->u32 & mask);
|
|
||||||
|
|
||||||
if(m_env.CLUT.u32 != value)
|
|
||||||
{
|
|
||||||
Flush();
|
|
||||||
|
|
||||||
m_env.CLUT.u32 = value;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPUState::SetTPAGE(GPUReg* r)
|
|
||||||
{
|
|
||||||
uint32 mask = 0x000001FF; // TP ABR TY TX
|
|
||||||
|
|
||||||
uint32 value = (m_env.STATUS.u32 & ~mask) | ((r->u32 >> 16) & mask);
|
|
||||||
|
|
||||||
if(m_env.STATUS.u32 != value)
|
|
||||||
{
|
|
||||||
Flush();
|
|
||||||
|
|
||||||
m_env.STATUS.u32 = value;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPUState::Invalidate(const GSVector4i& r)
|
|
||||||
{
|
|
||||||
m_mem.Invalidate(r);
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPUState::WriteData(const uint8* mem, uint32 size)
|
|
||||||
{
|
|
||||||
GSPerfMonAutoTimer pmat(&m_perfmon);
|
|
||||||
|
|
||||||
size <<= 2;
|
|
||||||
|
|
||||||
m_write.Append(mem, size);
|
|
||||||
|
|
||||||
int i = 0;
|
|
||||||
|
|
||||||
while(i < m_write.bytes)
|
|
||||||
{
|
|
||||||
GPUReg* r = (GPUReg*)&m_write.buff[i];
|
|
||||||
|
|
||||||
int ret = (this->*m_fpGPUPacketHandler[r->PACKET.TYPE])(r, (m_write.bytes - i) >> 2);
|
|
||||||
|
|
||||||
if(ret == 0) return; // need more data
|
|
||||||
|
|
||||||
i += ret << 2;
|
|
||||||
}
|
|
||||||
|
|
||||||
m_write.Remove(i);
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPUState::ReadData(uint8* mem, uint32 size)
|
|
||||||
{
|
|
||||||
GSPerfMonAutoTimer pmat(&m_perfmon);
|
|
||||||
|
|
||||||
int remaining = m_read.bytes - m_read.cur;
|
|
||||||
|
|
||||||
int bytes = (int)size << 2;
|
|
||||||
|
|
||||||
if(bytes > remaining)
|
|
||||||
{
|
|
||||||
// ASSERT(0);
|
|
||||||
|
|
||||||
// printf"WARNING: ReadData\n");
|
|
||||||
|
|
||||||
// memset(&mem[remaining], 0, bytes - remaining);
|
|
||||||
|
|
||||||
bytes = remaining;
|
|
||||||
}
|
|
||||||
|
|
||||||
memcpy(mem, &m_read.buff[m_read.cur], bytes);
|
|
||||||
|
|
||||||
m_read.cur += bytes;
|
|
||||||
|
|
||||||
if(m_read.cur >= m_read.bytes)
|
|
||||||
{
|
|
||||||
m_env.STATUS.IMG = 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPUState::WriteStatus(uint32 status)
|
|
||||||
{
|
|
||||||
GSPerfMonAutoTimer pmat(&m_perfmon);
|
|
||||||
|
|
||||||
uint32 b = status >> 24;
|
|
||||||
|
|
||||||
m_status[b] = status;
|
|
||||||
|
|
||||||
(this->*m_fpGPUStatusCommandHandlers[b])((GPUReg*)&status);
|
|
||||||
}
|
|
||||||
|
|
||||||
uint32 GPUState::ReadStatus()
|
|
||||||
{
|
|
||||||
GSPerfMonAutoTimer pmat(&m_perfmon);
|
|
||||||
|
|
||||||
m_env.STATUS.LCF = ~m_env.STATUS.LCF; // ?
|
|
||||||
|
|
||||||
return m_env.STATUS.u32;
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPUState::Freeze(GPUFreezeData* data)
|
|
||||||
{
|
|
||||||
data->status = m_env.STATUS.u32;
|
|
||||||
memcpy(data->control, m_status, 256 * 4);
|
|
||||||
m_mem.ReadRect(GSVector4i(0, 0, 1024, 512), data->vram);
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPUState::Defrost(const GPUFreezeData* data)
|
|
||||||
{
|
|
||||||
m_env.STATUS.u32 = data->status;
|
|
||||||
memcpy(m_status, data->control, 256 * 4);
|
|
||||||
m_mem.WriteRect(GSVector4i(0, 0, 1024, 512), data->vram);
|
|
||||||
|
|
||||||
for(int i = 0; i <= 8; i++)
|
|
||||||
{
|
|
||||||
WriteStatus(m_status[i]);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPUState::SCH_Null(GPUReg* r)
|
|
||||||
{
|
|
||||||
ASSERT(0);
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPUState::SCH_ResetGPU(GPUReg* r)
|
|
||||||
{
|
|
||||||
Reset();
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPUState::SCH_ResetCommandBuffer(GPUReg* r)
|
|
||||||
{
|
|
||||||
// ?
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPUState::SCH_ResetIRQ(GPUReg* r)
|
|
||||||
{
|
|
||||||
// ?
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPUState::SCH_DisplayEnable(GPUReg* r)
|
|
||||||
{
|
|
||||||
m_env.STATUS.DEN = r->DEN.DEN;
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPUState::SCH_DMASetup(GPUReg* r)
|
|
||||||
{
|
|
||||||
m_env.STATUS.DMA = r->DMA.DMA;
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPUState::SCH_StartOfDisplayArea(GPUReg* r)
|
|
||||||
{
|
|
||||||
m_env.DAREA = r->DAREA;
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPUState::SCH_HorizontalDisplayRange(GPUReg* r)
|
|
||||||
{
|
|
||||||
m_env.DHRANGE = r->DHRANGE;
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPUState::SCH_VerticalDisplayRange(GPUReg* r)
|
|
||||||
{
|
|
||||||
m_env.DVRANGE = r->DVRANGE;
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPUState::SCH_DisplayMode(GPUReg* r)
|
|
||||||
{
|
|
||||||
m_env.STATUS.WIDTH0 = r->DMODE.WIDTH0;
|
|
||||||
m_env.STATUS.HEIGHT = r->DMODE.HEIGHT;
|
|
||||||
m_env.STATUS.ISPAL = r->DMODE.ISPAL;
|
|
||||||
m_env.STATUS.ISRGB24 = r->DMODE.ISRGB24;
|
|
||||||
m_env.STATUS.ISINTER = r->DMODE.ISINTER;
|
|
||||||
m_env.STATUS.WIDTH1 = r->DMODE.WIDTH1;
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPUState::SCH_GPUInfo(GPUReg* r)
|
|
||||||
{
|
|
||||||
uint32 value = 0;
|
|
||||||
|
|
||||||
switch(r->GPUINFO.PARAM)
|
|
||||||
{
|
|
||||||
case 0x2:
|
|
||||||
value = m_env.TWIN.u32;
|
|
||||||
break;
|
|
||||||
case 0x0:
|
|
||||||
case 0x1:
|
|
||||||
case 0x3:
|
|
||||||
value = m_env.DRAREATL.u32;
|
|
||||||
break;
|
|
||||||
case 0x4:
|
|
||||||
value = m_env.DRAREABR.u32;
|
|
||||||
break;
|
|
||||||
case 0x5:
|
|
||||||
case 0x6:
|
|
||||||
value = m_env.DROFF.u32;
|
|
||||||
break;
|
|
||||||
case 0x7:
|
|
||||||
value = 2;
|
|
||||||
break;
|
|
||||||
case 0x8:
|
|
||||||
case 0xf:
|
|
||||||
value = 0xBFC03720; // ?
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
ASSERT(0);
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
m_read.RemoveAll();
|
|
||||||
m_read.Append((uint8*)&value, 4);
|
|
||||||
m_read.cur = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
int GPUState::PH_Command(GPUReg* r, int size)
|
|
||||||
{
|
|
||||||
switch(r->PACKET.OPTION)
|
|
||||||
{
|
|
||||||
case 0: // ???
|
|
||||||
|
|
||||||
return 1;
|
|
||||||
|
|
||||||
case 1: // clear cache
|
|
||||||
|
|
||||||
return 1;
|
|
||||||
|
|
||||||
case 2: // fillrect
|
|
||||||
|
|
||||||
if(size < 3) return 0;
|
|
||||||
|
|
||||||
Flush();
|
|
||||||
|
|
||||||
GSVector4i r2;
|
|
||||||
|
|
||||||
r2.left = r[1].XY.X;
|
|
||||||
r2.top = r[1].XY.Y;
|
|
||||||
r2.right = r2.left + r[2].XY.X;
|
|
||||||
r2.bottom = r2.top + r[2].XY.Y;
|
|
||||||
|
|
||||||
uint16 c = (uint16)(((r[0].RGB.R >> 3) << 10) | ((r[0].RGB.R >> 3) << 5) | (r[0].RGB.R >> 3));
|
|
||||||
|
|
||||||
m_mem.FillRect(r2, c);
|
|
||||||
|
|
||||||
Invalidate(r2);
|
|
||||||
|
|
||||||
Dump("f");
|
|
||||||
|
|
||||||
return 3;
|
|
||||||
}
|
|
||||||
|
|
||||||
ASSERT(0);
|
|
||||||
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
int GPUState::PH_Polygon(GPUReg* r, int size)
|
|
||||||
{
|
|
||||||
int required = 1;
|
|
||||||
|
|
||||||
int vertices = r[0].POLYGON.VTX ? 4 : 3;
|
|
||||||
|
|
||||||
required += vertices;
|
|
||||||
|
|
||||||
if(r[0].POLYGON.TME) required += vertices;
|
|
||||||
|
|
||||||
if(r[0].POLYGON.IIP) required += vertices - 1;
|
|
||||||
|
|
||||||
if(size < required) return 0;
|
|
||||||
|
|
||||||
//
|
|
||||||
|
|
||||||
SetPrim(r);
|
|
||||||
|
|
||||||
if(r[0].POLYGON.TME)
|
|
||||||
{
|
|
||||||
SetCLUT(&r[2]);
|
|
||||||
|
|
||||||
SetTPAGE(&r[r[0].POLYGON.IIP ? 5 : 4]);
|
|
||||||
}
|
|
||||||
|
|
||||||
//
|
|
||||||
|
|
||||||
GPUVertex v[4];
|
|
||||||
|
|
||||||
for(int i = 0, j = 0; j < vertices; j++)
|
|
||||||
{
|
|
||||||
v[j].RGB = r[r[0].POLYGON.IIP ? i : 0].RGB;
|
|
||||||
|
|
||||||
if(j == 0 || r[0].POLYGON.IIP) i++;
|
|
||||||
|
|
||||||
v[j].XY = r[i++].XY;
|
|
||||||
|
|
||||||
if(r[0].POLYGON.TME)
|
|
||||||
{
|
|
||||||
v[j].UV.X = r[i].UV.U;
|
|
||||||
v[j].UV.Y = r[i].UV.V;
|
|
||||||
|
|
||||||
i++;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
for(int i = 0; i <= vertices - 3; i++)
|
|
||||||
{
|
|
||||||
// TODO: sse
|
|
||||||
|
|
||||||
int y0 = v[i + 0].XY.Y;
|
|
||||||
int y1 = v[i + 1].XY.Y;
|
|
||||||
int y2 = v[i + 2].XY.Y;
|
|
||||||
|
|
||||||
if(std::abs(y0 - y1) >= 512
|
|
||||||
|| std::abs(y0 - y2) >= 512
|
|
||||||
|| std::abs(y1 - y2) >= 512)
|
|
||||||
{
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
int x0 = v[i + 0].XY.X;
|
|
||||||
int x1 = v[i + 1].XY.X;
|
|
||||||
int x2 = v[i + 2].XY.X;
|
|
||||||
|
|
||||||
if(std::abs(x0 - x1) >= 1024
|
|
||||||
|| std::abs(x0 - x2) >= 1024
|
|
||||||
|| std::abs(x1 - x2) >= 1024)
|
|
||||||
{
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
//
|
|
||||||
|
|
||||||
for(int j = 0; j < 3; j++)
|
|
||||||
{
|
|
||||||
m_v = v[i + j];
|
|
||||||
|
|
||||||
VertexKick();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
//
|
|
||||||
|
|
||||||
return required;
|
|
||||||
}
|
|
||||||
|
|
||||||
int GPUState::PH_Line(GPUReg* r, int size)
|
|
||||||
{
|
|
||||||
int required = 1;
|
|
||||||
|
|
||||||
int vertices = 0;
|
|
||||||
|
|
||||||
if(r->LINE.PLL)
|
|
||||||
{
|
|
||||||
required++;
|
|
||||||
|
|
||||||
for(int i = 1; i < size; i++)
|
|
||||||
{
|
|
||||||
if((r[i].u32 & 0xf000f000) == 0x50005000)
|
|
||||||
{
|
|
||||||
vertices = i - 1;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if(vertices < 2)
|
|
||||||
{
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
vertices = 2;
|
|
||||||
}
|
|
||||||
|
|
||||||
required += vertices;
|
|
||||||
|
|
||||||
if(r->LINE.IIP) required += vertices - 1;
|
|
||||||
|
|
||||||
//
|
|
||||||
|
|
||||||
SetPrim(r);
|
|
||||||
|
|
||||||
//
|
|
||||||
|
|
||||||
for(int i = 0, j = 0; j < vertices; j++)
|
|
||||||
{
|
|
||||||
if(j >= 2) VertexKick();
|
|
||||||
|
|
||||||
m_v.RGB = r[r[0].LINE.IIP ? i : 0].RGB;
|
|
||||||
|
|
||||||
if(j == 0 || r[0].LINE.IIP) i++;
|
|
||||||
|
|
||||||
m_v.XY = r[i++].XY;
|
|
||||||
|
|
||||||
VertexKick();
|
|
||||||
}
|
|
||||||
|
|
||||||
//
|
|
||||||
|
|
||||||
return required;
|
|
||||||
}
|
|
||||||
|
|
||||||
int GPUState::PH_Sprite(GPUReg* r, int size)
|
|
||||||
{
|
|
||||||
int required = 2;
|
|
||||||
|
|
||||||
if(r[0].SPRITE.TME) required++;
|
|
||||||
if(r[0].SPRITE.SIZE == 0) required++;
|
|
||||||
|
|
||||||
if(size < required) return 0;
|
|
||||||
|
|
||||||
//
|
|
||||||
|
|
||||||
SetPrim(r);
|
|
||||||
|
|
||||||
if(r[0].SPRITE.TME)
|
|
||||||
{
|
|
||||||
SetCLUT(&r[2]);
|
|
||||||
}
|
|
||||||
|
|
||||||
//
|
|
||||||
|
|
||||||
int i = 0;
|
|
||||||
|
|
||||||
m_v.RGB = r[i++].RGB;
|
|
||||||
|
|
||||||
m_v.XY = r[i++].XY;
|
|
||||||
|
|
||||||
if(r[0].SPRITE.TME)
|
|
||||||
{
|
|
||||||
m_v.UV.X = r[i].UV.U;
|
|
||||||
m_v.UV.Y = r[i].UV.V;
|
|
||||||
|
|
||||||
i++;
|
|
||||||
}
|
|
||||||
|
|
||||||
VertexKick();
|
|
||||||
|
|
||||||
int w = 0;
|
|
||||||
int h = 0;
|
|
||||||
|
|
||||||
switch(r[0].SPRITE.SIZE)
|
|
||||||
{
|
|
||||||
case 0: w = r[i].XY.X; h = r[i].XY.Y; i++; break;
|
|
||||||
case 1: w = h = 1; break;
|
|
||||||
case 2: w = h = 8; break;
|
|
||||||
case 3: w = h = 16; break;
|
|
||||||
default: __assume(0);
|
|
||||||
}
|
|
||||||
|
|
||||||
m_v.XY.X += w;
|
|
||||||
m_v.XY.Y += h;
|
|
||||||
|
|
||||||
if(r[0].SPRITE.TME)
|
|
||||||
{
|
|
||||||
m_v.UV.X += w;
|
|
||||||
m_v.UV.Y += h;
|
|
||||||
}
|
|
||||||
|
|
||||||
VertexKick();
|
|
||||||
|
|
||||||
//
|
|
||||||
|
|
||||||
return required;
|
|
||||||
}
|
|
||||||
|
|
||||||
int GPUState::PH_Move(GPUReg* r, int size)
|
|
||||||
{
|
|
||||||
if(size < 4) return 0;
|
|
||||||
|
|
||||||
Flush();
|
|
||||||
|
|
||||||
int sx = r[1].XY.X;
|
|
||||||
int sy = r[1].XY.Y;
|
|
||||||
|
|
||||||
int dx = r[2].XY.X;
|
|
||||||
int dy = r[2].XY.Y;
|
|
||||||
|
|
||||||
int w = r[3].XY.X;
|
|
||||||
int h = r[3].XY.Y;
|
|
||||||
|
|
||||||
m_mem.MoveRect(sx, sy, dx, dy, w, h);
|
|
||||||
|
|
||||||
Invalidate(GSVector4i(dx, dy, dx + w, dy + h));
|
|
||||||
|
|
||||||
// Dump("m");
|
|
||||||
|
|
||||||
return 4;
|
|
||||||
}
|
|
||||||
|
|
||||||
int GPUState::PH_Write(GPUReg* r, int size)
|
|
||||||
{
|
|
||||||
if(size < 3) return 0;
|
|
||||||
|
|
||||||
int w = r[2].XY.X;
|
|
||||||
int h = r[2].XY.Y;
|
|
||||||
|
|
||||||
int required = 3 + ((w * h + 1) >> 1);
|
|
||||||
|
|
||||||
if(size < required) return 0;
|
|
||||||
|
|
||||||
Flush();
|
|
||||||
|
|
||||||
GSVector4i r2;
|
|
||||||
|
|
||||||
r2.left = r[1].XY.X;
|
|
||||||
r2.top = r[1].XY.Y;
|
|
||||||
r2.right = r2.left + w;
|
|
||||||
r2.bottom = r2.top + h;
|
|
||||||
|
|
||||||
m_mem.WriteRect(r2, (const uint16*)&r[3]);
|
|
||||||
|
|
||||||
Invalidate(r2);
|
|
||||||
|
|
||||||
Dump("w");
|
|
||||||
|
|
||||||
m_perfmon.Put(GSPerfMon::Swizzle, w * h * 2);
|
|
||||||
|
|
||||||
return required;
|
|
||||||
}
|
|
||||||
|
|
||||||
int GPUState::PH_Read(GPUReg* r, int size)
|
|
||||||
{
|
|
||||||
if(size < 3) return 0;
|
|
||||||
|
|
||||||
Flush();
|
|
||||||
|
|
||||||
int w = r[2].XY.X;
|
|
||||||
int h = r[2].XY.Y;
|
|
||||||
|
|
||||||
if(w > 0 && h > 0)
|
|
||||||
{
|
|
||||||
GSVector4i r2;
|
|
||||||
|
|
||||||
r2.left = r[1].XY.X;
|
|
||||||
r2.top = r[1].XY.Y;
|
|
||||||
r2.right = r2.left + w;
|
|
||||||
r2.bottom = r2.top + h;
|
|
||||||
|
|
||||||
m_read.bytes = ((w * h + 1) & ~1) * 2;
|
|
||||||
m_read.cur = 0;
|
|
||||||
m_read.Reserve(m_read.bytes);
|
|
||||||
|
|
||||||
m_mem.ReadRect(r2, (uint16*)m_read.buff);
|
|
||||||
|
|
||||||
Dump("r");
|
|
||||||
}
|
|
||||||
|
|
||||||
m_env.STATUS.IMG = 1;
|
|
||||||
|
|
||||||
return 3;
|
|
||||||
}
|
|
||||||
|
|
||||||
int GPUState::PH_Environment(GPUReg* r, int size)
|
|
||||||
{
|
|
||||||
switch(r->PACKET.OPTION)
|
|
||||||
{
|
|
||||||
case 1: // draw mode setting
|
|
||||||
|
|
||||||
if(((m_env.STATUS.u32 ^ r->MODE.u32) & 0x7ff) != 0)
|
|
||||||
{
|
|
||||||
Flush();
|
|
||||||
|
|
||||||
m_env.STATUS.TX = r->MODE.TX;
|
|
||||||
m_env.STATUS.TY = r->MODE.TY;
|
|
||||||
m_env.STATUS.ABR = r->MODE.ABR;
|
|
||||||
m_env.STATUS.TP = r->MODE.TP;
|
|
||||||
m_env.STATUS.DTD = r->MODE.DTD;
|
|
||||||
m_env.STATUS.DFE = r->MODE.DFE;
|
|
||||||
}
|
|
||||||
|
|
||||||
return 1;
|
|
||||||
|
|
||||||
case 2: // texture window setting
|
|
||||||
|
|
||||||
if(((m_env.TWIN.u32 ^ r->TWIN.u32) & 0xfffff) != 0)
|
|
||||||
{
|
|
||||||
Flush();
|
|
||||||
|
|
||||||
m_env.TWIN = r->TWIN;
|
|
||||||
}
|
|
||||||
|
|
||||||
return 1;
|
|
||||||
|
|
||||||
case 3: // set drawing area top left
|
|
||||||
|
|
||||||
if(((m_env.DRAREATL.u32 ^ r->DRAREA.u32) & 0xfffff) != 0)
|
|
||||||
{
|
|
||||||
Flush();
|
|
||||||
|
|
||||||
m_env.DRAREATL = r->DRAREA;
|
|
||||||
}
|
|
||||||
|
|
||||||
return 1;
|
|
||||||
|
|
||||||
case 4: // set drawing area bottom right
|
|
||||||
|
|
||||||
if(((m_env.DRAREABR.u32 ^ r->DRAREA.u32) & 0xfffff) != 0)
|
|
||||||
{
|
|
||||||
Flush();
|
|
||||||
|
|
||||||
m_env.DRAREABR = r->DRAREA;
|
|
||||||
}
|
|
||||||
|
|
||||||
return 1;
|
|
||||||
|
|
||||||
case 5: // drawing offset
|
|
||||||
|
|
||||||
if(((m_env.DROFF.u32 ^ r->DROFF.u32) & 0x3fffff) != 0)
|
|
||||||
{
|
|
||||||
Flush();
|
|
||||||
|
|
||||||
m_env.DROFF = r->DROFF;
|
|
||||||
}
|
|
||||||
|
|
||||||
return 1;
|
|
||||||
|
|
||||||
case 6: // mask setting
|
|
||||||
|
|
||||||
if(m_env.STATUS.MD != r->MASK.MD || m_env.STATUS.ME != r->MASK.ME)
|
|
||||||
{
|
|
||||||
Flush();
|
|
||||||
|
|
||||||
m_env.STATUS.MD = r->MASK.MD;
|
|
||||||
m_env.STATUS.ME = r->MASK.ME;
|
|
||||||
}
|
|
||||||
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
ASSERT(0);
|
|
||||||
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
//
|
|
||||||
|
|
||||||
GPUState::Buffer::Buffer()
|
|
||||||
{
|
|
||||||
bytes = 0;
|
|
||||||
maxbytes = 4096;
|
|
||||||
buff = (uint8*)_aligned_malloc(maxbytes, 32);
|
|
||||||
cur = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
GPUState::Buffer::~Buffer()
|
|
||||||
{
|
|
||||||
_aligned_free(buff);
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPUState::Buffer::Reserve(int size)
|
|
||||||
{
|
|
||||||
if(size > maxbytes)
|
|
||||||
{
|
|
||||||
int new_maxbytes = (maxbytes + size + 1023) & ~1023;
|
|
||||||
uint8* new_buff = (uint8*)_aligned_malloc(new_maxbytes, 32);
|
|
||||||
|
|
||||||
if(buff != NULL)
|
|
||||||
{
|
|
||||||
memcpy(new_buff, buff, maxbytes);
|
|
||||||
_aligned_free(buff);
|
|
||||||
}
|
|
||||||
|
|
||||||
maxbytes = new_maxbytes;
|
|
||||||
buff = new_buff;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPUState::Buffer::Append(const uint8* src, int size)
|
|
||||||
{
|
|
||||||
Reserve(bytes + (int)size);
|
|
||||||
|
|
||||||
memcpy(&buff[bytes], src, size);
|
|
||||||
|
|
||||||
bytes += size;
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPUState::Buffer::Remove(int size)
|
|
||||||
{
|
|
||||||
ASSERT(size <= bytes);
|
|
||||||
|
|
||||||
if(size < bytes)
|
|
||||||
{
|
|
||||||
memmove(&buff[0], &buff[size], bytes - size);
|
|
||||||
|
|
||||||
bytes -= size;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
bytes = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
#ifdef DEBUG
|
|
||||||
memset(&buff[bytes], 0xff, maxbytes - bytes);
|
|
||||||
#endif
|
|
||||||
}
|
|
||||||
|
|
||||||
void GPUState::Buffer::RemoveAll()
|
|
||||||
{
|
|
||||||
bytes = 0;
|
|
||||||
}
|
|
|
@ -1,145 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2007-2009 Gabest
|
|
||||||
* http://www.gabest.org
|
|
||||||
*
|
|
||||||
* 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; either version 2, 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 received a copy of the GNU General Public License
|
|
||||||
* along with GNU Make; see the file COPYING. If not, write to
|
|
||||||
* the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA USA.
|
|
||||||
* http://www.gnu.org/copyleft/gpl.html
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
|
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include "GPU.h"
|
|
||||||
#include "GPUDrawingEnvironment.h"
|
|
||||||
#include "GPULocalMemory.h"
|
|
||||||
#include "GPUVertex.h"
|
|
||||||
#include "GSAlignedClass.h"
|
|
||||||
#include "GSUtil.h"
|
|
||||||
#include "GSPerfMon.h"
|
|
||||||
|
|
||||||
class GPUState : public GSAlignedClass<32>
|
|
||||||
{
|
|
||||||
typedef void (GPUState::*GPUStatusCommandHandler)(GPUReg* r);
|
|
||||||
|
|
||||||
GPUStatusCommandHandler m_fpGPUStatusCommandHandlers[256];
|
|
||||||
|
|
||||||
void SCH_Null(GPUReg* r);
|
|
||||||
void SCH_ResetGPU(GPUReg* r);
|
|
||||||
void SCH_ResetCommandBuffer(GPUReg* r);
|
|
||||||
void SCH_ResetIRQ(GPUReg* r);
|
|
||||||
void SCH_DisplayEnable(GPUReg* r);
|
|
||||||
void SCH_DMASetup(GPUReg* r);
|
|
||||||
void SCH_StartOfDisplayArea(GPUReg* r);
|
|
||||||
void SCH_HorizontalDisplayRange(GPUReg* r);
|
|
||||||
void SCH_VerticalDisplayRange(GPUReg* r);
|
|
||||||
void SCH_DisplayMode(GPUReg* r);
|
|
||||||
void SCH_GPUInfo(GPUReg* r);
|
|
||||||
|
|
||||||
typedef int (GPUState::*GPUPacketHandler)(GPUReg* r, int size);
|
|
||||||
|
|
||||||
GPUPacketHandler m_fpGPUPacketHandler[8];
|
|
||||||
|
|
||||||
int PH_Command(GPUReg* r, int size);
|
|
||||||
int PH_Polygon(GPUReg* r, int size);
|
|
||||||
int PH_Line(GPUReg* r, int size);
|
|
||||||
int PH_Sprite(GPUReg* r, int size);
|
|
||||||
int PH_Move(GPUReg* r, int size);
|
|
||||||
int PH_Write(GPUReg* r, int size);
|
|
||||||
int PH_Read(GPUReg* r, int size);
|
|
||||||
int PH_Environment(GPUReg* r, int size);
|
|
||||||
|
|
||||||
class Buffer
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
int bytes;
|
|
||||||
int maxbytes;
|
|
||||||
uint8* buff;
|
|
||||||
int cur;
|
|
||||||
|
|
||||||
public:
|
|
||||||
Buffer();
|
|
||||||
~Buffer();
|
|
||||||
void Reserve(int size);
|
|
||||||
void Append(const uint8* src, int size);
|
|
||||||
void Remove(int size);
|
|
||||||
void RemoveAll();
|
|
||||||
};
|
|
||||||
|
|
||||||
Buffer m_write;
|
|
||||||
Buffer m_read;
|
|
||||||
|
|
||||||
void SetPrim(GPUReg* r);
|
|
||||||
void SetCLUT(GPUReg* r);
|
|
||||||
void SetTPAGE(GPUReg* r);
|
|
||||||
|
|
||||||
protected:
|
|
||||||
|
|
||||||
int s_n;
|
|
||||||
bool dump_enable = false;
|
|
||||||
|
|
||||||
void Dump(const std::string& s, uint32 TP, const GSVector4i& r, int inc = true)
|
|
||||||
{
|
|
||||||
//if(m_perfmon.GetFrame() < 1000)
|
|
||||||
//if((m_env.TWIN.u32 & 0xfffff) == 0)
|
|
||||||
//if(!m_env.STATUS.ME && !m_env.STATUS.MD)
|
|
||||||
if(!dump_enable)
|
|
||||||
return;
|
|
||||||
|
|
||||||
if(inc) s_n++;
|
|
||||||
|
|
||||||
//if(s_n < 86) return;
|
|
||||||
|
|
||||||
int dir = 1;
|
|
||||||
#ifdef DEBUG
|
|
||||||
dir = 2;
|
|
||||||
#endif
|
|
||||||
std::string path = format("c:\\temp%d\\%04d_%s.bmp", dir, s_n, s.c_str());
|
|
||||||
|
|
||||||
m_mem.SaveBMP(path, r, TP, m_env.CLUT.X, m_env.CLUT.Y);
|
|
||||||
}
|
|
||||||
|
|
||||||
void Dump(const std::string& s, int inc = true)
|
|
||||||
{
|
|
||||||
Dump(s, 2, GSVector4i(0, 0, 1024, 512), inc);
|
|
||||||
}
|
|
||||||
|
|
||||||
public:
|
|
||||||
GPUDrawingEnvironment m_env;
|
|
||||||
GPULocalMemory m_mem;
|
|
||||||
GPUVertex m_v;
|
|
||||||
GSPerfMon m_perfmon;
|
|
||||||
uint32 m_status[256];
|
|
||||||
|
|
||||||
public:
|
|
||||||
GPUState();
|
|
||||||
virtual ~GPUState() = default;
|
|
||||||
|
|
||||||
virtual void Reset();
|
|
||||||
virtual void Flush();
|
|
||||||
virtual void FlushPrim() = 0;
|
|
||||||
virtual void ResetPrim() = 0;
|
|
||||||
virtual void VertexKick() = 0;
|
|
||||||
virtual void Invalidate(const GSVector4i& r);
|
|
||||||
|
|
||||||
void WriteData(const uint8* mem, uint32 size);
|
|
||||||
void ReadData(uint8* mem, uint32 size);
|
|
||||||
|
|
||||||
void WriteStatus(uint32 status);
|
|
||||||
uint32 ReadStatus();
|
|
||||||
|
|
||||||
void Freeze(GPUFreezeData* data);
|
|
||||||
void Defrost(const GPUFreezeData* data);
|
|
||||||
};
|
|
||||||
|
|
|
@ -1,51 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2007-2009 Gabest
|
|
||||||
* http://www.gabest.org
|
|
||||||
*
|
|
||||||
* 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; either version 2, 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 received a copy of the GNU General Public License
|
|
||||||
* along with GNU Make; see the file COPYING. If not, write to
|
|
||||||
* the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA USA.
|
|
||||||
* http://www.gnu.org/copyleft/gpl.html
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
|
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include "GPU.h"
|
|
||||||
#include "GSVector.h"
|
|
||||||
|
|
||||||
#pragma pack(push, 1)
|
|
||||||
|
|
||||||
struct alignas(32) GPUVertex
|
|
||||||
{
|
|
||||||
union
|
|
||||||
{
|
|
||||||
struct
|
|
||||||
{
|
|
||||||
GPURegRGB RGB;
|
|
||||||
GPURegXY XY;
|
|
||||||
GPURegXY UV;
|
|
||||||
};
|
|
||||||
|
|
||||||
struct {__m128i m128i;};
|
|
||||||
struct {__m128 m128;};
|
|
||||||
};
|
|
||||||
|
|
||||||
GPUVertex() {memset(this, 0, sizeof(*this));}
|
|
||||||
};
|
|
||||||
|
|
||||||
struct GPUVertexNull
|
|
||||||
{
|
|
||||||
};
|
|
||||||
|
|
||||||
#pragma pack(pop)
|
|
|
@ -46,17 +46,6 @@
|
||||||
#define IDC_SWTHREADS 2063
|
#define IDC_SWTHREADS 2063
|
||||||
#define IDC_SWTHREADS_EDIT 2064
|
#define IDC_SWTHREADS_EDIT 2064
|
||||||
#define IDC_AUTO_FLUSH_SW 2065
|
#define IDC_AUTO_FLUSH_SW 2065
|
||||||
// PSX:
|
|
||||||
#define IDD_GPUCONFIG 2070
|
|
||||||
#define IDC_ASPECTRATIO 2071
|
|
||||||
#define IDC_ASPECTRATIO_TEXT 2072
|
|
||||||
#define IDC_DITHERING 2073
|
|
||||||
#define IDC_DITHERING_TEXT 2074
|
|
||||||
#define IDC_WINDOWED 2075
|
|
||||||
#define IDC_RESOLUTION 2076
|
|
||||||
#define IDC_RESOLUTION_TEXT 2077
|
|
||||||
#define IDC_SCALE 2078
|
|
||||||
#define IDC_SCALE_TEXT 2079
|
|
||||||
// Capture:
|
// Capture:
|
||||||
#define IDD_CAPTURE 2090
|
#define IDD_CAPTURE 2090
|
||||||
#define IDC_FILENAME 2091
|
#define IDC_FILENAME 2091
|
||||||
|
|
Loading…
Reference in New Issue