Compare commits

..

8 Commits

Author SHA1 Message Date
lightningterror
50bc0193ac Core: Bump savestate version.
[SAVEVERSION+]
2025-06-02 01:30:50 +02:00
refractionpcsx2
2162a72831 GS: Bump GS Dump version and add transfer parameters to dump 2025-06-02 00:40:03 +02:00
refractionpcsx2
313666f85b GS: Store entire GS transfer state at TRXDIR write 2025-06-02 00:40:03 +02:00
TheTechnician27
e9d79263b4 UI: Fix Discord Rich Presence not activating in FSUI 2025-06-01 23:21:39 +02:00
JordanTheToaster
4ede6d65fd GameDB: Fix half right issue with Xtreme Bowling 2025-06-01 13:28:25 -04:00
PCSX2 Bot
14d2eee371 [ci skip] Qt: Update Base Translation. 2025-05-31 20:46:33 -04:00
chaoticgd
717f370be0 Debugger: Improve DockTabBar ownership workaround 2025-05-31 03:30:13 +02:00
refractionpcsx2
d05e4b9727 GS/HW: Adjust SpriteNoGaps check for vertical strips 2025-05-31 03:25:47 +02:00
8 changed files with 312 additions and 108 deletions

View File

@@ -25934,6 +25934,8 @@ SLES-54364:
SLES-54365:
name: "AMF Xtreme Bowling 2006"
region: "PAL-M6"
gsHWFixes:
textureInsideRT: 1 # Fixes half right.
SLES-54366:
name: "David Douillet Judo"
region: "PAL-NL-F"
@@ -69943,6 +69945,8 @@ SLUS-21347:
name: "AMF Xtreme Bowling"
region: "NTSC-U"
compat: 5
gsHWFixes:
textureInsideRT: 1 # Fixes half right.
SLUS-21348:
name: "Yakuza"
region: "NTSC-U"

View File

@@ -149,7 +149,9 @@ DockTabBar::DockTabBar(KDDockWidgets::Core::TabBar* controller, QWidget* parent)
// that ends up taking ownerhsip of the style for the entire application!
if (QProxyStyle* proxy_style = qobject_cast<QProxyStyle*>(style()))
{
proxy_style->baseStyle()->setParent(qApp);
if (proxy_style->baseStyle() == qApp->style())
proxy_style->baseStyle()->setParent(qApp);
proxy_style->setBaseStyle(QStyleFactory::create(qApp->style()->name()));
}
}

View File

@@ -5469,52 +5469,52 @@ Do you want to overwrite?</source>
<context>
<name>DockTabBar</name>
<message>
<location filename="../Debugger/Docking/DockViews.cpp" line="175"/>
<location filename="../Debugger/Docking/DockViews.cpp" line="177"/>
<source>Rename</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../Debugger/Docking/DockViews.cpp" line="186"/>
<location filename="../Debugger/Docking/DockViews.cpp" line="188"/>
<source>Rename Window</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../Debugger/Docking/DockViews.cpp" line="186"/>
<location filename="../Debugger/Docking/DockViews.cpp" line="188"/>
<source>New name:</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../Debugger/Docking/DockViews.cpp" line="192"/>
<location filename="../Debugger/Docking/DockViews.cpp" line="194"/>
<source>Invalid Name</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../Debugger/Docking/DockViews.cpp" line="192"/>
<location filename="../Debugger/Docking/DockViews.cpp" line="194"/>
<source>The specified name is too long.</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../Debugger/Docking/DockViews.cpp" line="199"/>
<location filename="../Debugger/Docking/DockViews.cpp" line="201"/>
<source>Reset Name</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../Debugger/Docking/DockViews.cpp" line="213"/>
<location filename="../Debugger/Docking/DockViews.cpp" line="215"/>
<source>Primary</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../Debugger/Docking/DockViews.cpp" line="228"/>
<location filename="../Debugger/Docking/DockViews.cpp" line="230"/>
<source>Set Target</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../Debugger/Docking/DockViews.cpp" line="249"/>
<location filename="../Debugger/Docking/DockViews.cpp" line="251"/>
<source>Inherit From Layout</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../Debugger/Docking/DockViews.cpp" line="257"/>
<location filename="../Debugger/Docking/DockViews.cpp" line="259"/>
<source>Close</source>
<translation type="unfinished"></translation>
</message>
@@ -9193,22 +9193,22 @@ Do you want to load this save and continue?</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/ImGui/FullscreenUI.cpp" line="7903"/>
<location filename="../../pcsx2/ImGui/FullscreenUI.cpp" line="7905"/>
<source>Controller Settings</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/ImGui/FullscreenUI.cpp" line="7904"/>
<location filename="../../pcsx2/ImGui/FullscreenUI.cpp" line="7906"/>
<source>Hotkey Settings</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/ImGui/FullscreenUI.cpp" line="7905"/>
<location filename="../../pcsx2/ImGui/FullscreenUI.cpp" line="7904"/>
<source>Achievements Settings</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/ImGui/FullscreenUI.cpp" line="7906"/>
<location filename="../../pcsx2/ImGui/FullscreenUI.cpp" line="7903"/>
<source>Folder Settings</source>
<translation type="unfinished"></translation>
</message>
@@ -11344,113 +11344,263 @@ graphical quality, but this will increase system requirements.</source>
<context>
<name>GameList</name>
<message>
<location filename="../../pcsx2/GameList.cpp" line="102"/>
<location filename="../../pcsx2/GameList.cpp" line="97"/>
<source>PS2 Disc</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="102"/>
<location filename="../../pcsx2/GameList.cpp" line="98"/>
<source>PS1 Disc</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="102"/>
<location filename="../../pcsx2/GameList.cpp" line="99"/>
<source>ELF</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="109"/>
<source>Other</source>
<location filename="../../pcsx2/GameList.cpp" line="100"/>
<source>Invalid</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="113"/>
<source>NTSC-B</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="114"/>
<source>NTSC-C</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="115"/>
<source>NTSC-HK</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="116"/>
<source>NTSC-J</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="117"/>
<source>NTSC-K</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="118"/>
<source>NTSC-T</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="119"/>
<source>NTSC-U</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="120"/>
<source>Unknown</source>
<source>Other</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="121"/>
<source>Nothing</source>
<source>PAL-A</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="122"/>
<source>Intro</source>
<source>PAL-AF</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="123"/>
<source>Menu</source>
<source>PAL-AU</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="124"/>
<source>In-Game</source>
<source>PAL-BE</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="125"/>
<source>Playable</source>
<source>PAL-E</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="126"/>
<source>PAL-F</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="127"/>
<source>PAL-FI</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="128"/>
<source>PAL-G</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="129"/>
<source>PAL-GR</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="130"/>
<source>PAL-I</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="131"/>
<source>PAL-IN</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="132"/>
<source>PAL-M</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="133"/>
<source>PAL-NL</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="134"/>
<source>PAL-NO</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="135"/>
<source>PAL-P</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="136"/>
<source>PAL-PL</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="137"/>
<source>PAL-R</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="138"/>
<source>PAL-S</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="139"/>
<source>PAL-SC</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="140"/>
<source>PAL-SW</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="141"/>
<source>PAL-SWI</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="142"/>
<source>PAL-UK</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="158"/>
<source>Unknown</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="161"/>
<source>Nothing</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="164"/>
<source>Intro</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="167"/>
<source>Menu</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="170"/>
<source>In-Game</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="173"/>
<source>Playable</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="176"/>
<source>Perfect</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="595"/>
<location filename="../../pcsx2/GameList.cpp" line="653"/>
<source>Scanning directory {} (recursively)...</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="596"/>
<location filename="../../pcsx2/GameList.cpp" line="656"/>
<source>Scanning directory {}...</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="625"/>
<location filename="../../pcsx2/GameList.cpp" line="684"/>
<source>Scanning {}...</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="1083"/>
<location filename="../../pcsx2/GameList.cpp" line="1142"/>
<source>Never</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="1100"/>
<location filename="../../pcsx2/GameList.cpp" line="1159"/>
<source>Today</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="1105"/>
<location filename="../../pcsx2/GameList.cpp" line="1164"/>
<source>Yesterday</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="1128"/>
<location filename="../../pcsx2/GameList.cpp" line="1187"/>
<source>{}h {}m</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="1130"/>
<location filename="../../pcsx2/GameList.cpp" line="1189"/>
<source>{}h {}m {}s</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="1132"/>
<location filename="../../pcsx2/GameList.cpp" line="1191"/>
<source>{}m {}s</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="1134"/>
<location filename="../../pcsx2/GameList.cpp" line="1193"/>
<source>{}s</source>
<translation type="unfinished"></translation>
</message>
<message numerus="yes">
<location filename="../GameList/GameListModel.cpp" line="268"/>
<location filename="../../pcsx2/GameList.cpp" line="1141"/>
<location filename="../../pcsx2/GameList.cpp" line="1200"/>
<source>%n hours</source>
<translation type="unfinished">
<numerusform></numerusform>
@@ -11459,7 +11609,7 @@ graphical quality, but this will increase system requirements.</source>
</message>
<message numerus="yes">
<location filename="../GameList/GameListModel.cpp" line="270"/>
<location filename="../../pcsx2/GameList.cpp" line="1143"/>
<location filename="../../pcsx2/GameList.cpp" line="1202"/>
<source>%n minutes</source>
<translation type="unfinished">
<numerusform></numerusform>
@@ -11467,7 +11617,7 @@ graphical quality, but this will increase system requirements.</source>
</translation>
</message>
<message>
<location filename="../../pcsx2/GameList.cpp" line="1303"/>
<location filename="../../pcsx2/GameList.cpp" line="1362"/>
<source>Downloading cover for {0} [{1}]...</source>
<translation type="unfinished"></translation>
</message>
@@ -12055,111 +12205,111 @@ Scanning recursively takes more time, but will identify files in subdirectories.
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../Settings/GameSummaryWidget.cpp" line="76"/>
<location filename="../Settings/GameSummaryWidget.cpp" line="77"/>
<source>%0%1</source>
<extracomment>First arg is a GameList compat; second is a string with space followed by star rating OR empty if Unknown compat</extracomment>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../Settings/GameSummaryWidget.cpp" line="84"/>
<location filename="../Settings/GameSummaryWidget.cpp" line="85"/>
<source> %0%1</source>
<extracomment>First arg is filled-in stars for game compatibility; second is empty stars; should be swapped for RTL languages</extracomment>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../Settings/GameSummaryWidget.cpp" line="173"/>
<location filename="../Settings/GameSummaryWidget.cpp" line="174"/>
<source>Select Disc Path</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../Settings/GameSummaryWidget.cpp" line="186"/>
<location filename="../Settings/GameSummaryWidget.cpp" line="187"/>
<source>Game is not a CD/DVD.</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../Settings/GameSummaryWidget.cpp" line="193"/>
<location filename="../Settings/GameSummaryWidget.cpp" line="194"/>
<source>Track list unavailable while virtual machine is running.</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../Settings/GameSummaryWidget.cpp" line="218"/>
<location filename="../Settings/GameSummaryWidget.cpp" line="219"/>
<source>#</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../Settings/GameSummaryWidget.cpp" line="221"/>
<source>Mode</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../Settings/GameSummaryWidget.cpp" line="222"/>
<location filename="../Settings/GameSummaryWidget.cpp" line="230"/>
<source>Start</source>
<source>Mode</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../Settings/GameSummaryWidget.cpp" line="223"/>
<location filename="../Settings/GameSummaryWidget.cpp" line="231"/>
<source>Sectors</source>
<source>Start</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../Settings/GameSummaryWidget.cpp" line="224"/>
<location filename="../Settings/GameSummaryWidget.cpp" line="232"/>
<source>Size</source>
<source>Sectors</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../Settings/GameSummaryWidget.cpp" line="225"/>
<location filename="../Settings/GameSummaryWidget.cpp" line="233"/>
<source>MD5</source>
<source>Size</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../Settings/GameSummaryWidget.cpp" line="226"/>
<location filename="../Settings/GameSummaryWidget.cpp" line="234"/>
<source>MD5</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../Settings/GameSummaryWidget.cpp" line="227"/>
<location filename="../Settings/GameSummaryWidget.cpp" line="235"/>
<source>Status</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../Settings/GameSummaryWidget.cpp" line="242"/>
<location filename="../Settings/GameSummaryWidget.cpp" line="247"/>
<location filename="../Settings/GameSummaryWidget.cpp" line="243"/>
<location filename="../Settings/GameSummaryWidget.cpp" line="248"/>
<location filename="../Settings/GameSummaryWidget.cpp" line="249"/>
<location filename="../Settings/GameSummaryWidget.cpp" line="255"/>
<location filename="../Settings/GameSummaryWidget.cpp" line="250"/>
<location filename="../Settings/GameSummaryWidget.cpp" line="256"/>
<location filename="../Settings/GameSummaryWidget.cpp" line="257"/>
<location filename="../Settings/GameSummaryWidget.cpp" line="258"/>
<source>%1</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../Settings/GameSummaryWidget.cpp" line="250"/>
<location filename="../Settings/GameSummaryWidget.cpp" line="258"/>
<location filename="../Settings/GameSummaryWidget.cpp" line="251"/>
<location filename="../Settings/GameSummaryWidget.cpp" line="259"/>
<source>&lt;not computed&gt;</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../Settings/GameSummaryWidget.cpp" line="274"/>
<location filename="../Settings/GameSummaryWidget.cpp" line="275"/>
<source>Error</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../Settings/GameSummaryWidget.cpp" line="274"/>
<location filename="../Settings/GameSummaryWidget.cpp" line="275"/>
<source>Cannot verify image while a game is running.</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../Settings/GameSummaryWidget.cpp" line="304"/>
<location filename="../Settings/GameSummaryWidget.cpp" line="305"/>
<source>One or more tracks is missing.</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../Settings/GameSummaryWidget.cpp" line="341"/>
<location filename="../Settings/GameSummaryWidget.cpp" line="342"/>
<source>Verified as %1 [%2] (Version %3).</source>
<translation type="unfinished"></translation>
</message>
<message>
<location filename="../Settings/GameSummaryWidget.cpp" line="348"/>
<location filename="../Settings/GameSummaryWidget.cpp" line="349"/>
<source>Verified as %1 [%2].</source>
<translation type="unfinished"></translation>
</message>

View File

@@ -32,7 +32,7 @@ static __fi bool IsFirstProvokingVertex()
return (GSIsHardwareRenderer() && !g_gs_device->Features().provoking_vertex_last);
}
constexpr int GSState::GetSaveStateSize()
constexpr int GSState::GetSaveStateSize(int version)
{
int size = 0;
@@ -78,6 +78,19 @@ constexpr int GSState::GetSaveStateSize()
size += sizeof(m_tr.x);
size += sizeof(m_tr.y);
if (version >= 9)
{
size += sizeof(m_tr.w);
size += sizeof(m_tr.h);
size += sizeof(m_tr.m_blit);
size += sizeof(m_tr.m_pos);
size += sizeof(m_tr.m_reg);
size += sizeof(m_tr.rect);
size += sizeof(m_tr.total);
size += sizeof(m_tr.start);
size += sizeof(m_tr.end);
size += sizeof(m_tr.write);
}
size += GSLocalMemory::m_vmsize;
size += (sizeof(GIFPath::tag) + sizeof(GIFPath::reg)) * 4 /* std::size(GSState::m_path) */; // std::size won't work without an instance.
size += sizeof(m_q);
@@ -1445,10 +1458,10 @@ void GSState::GIFRegHandlerTRXDIR(const GIFReg* RESTRICT r)
switch (m_env.TRXDIR.XDIR)
{
case 0: // host -> local
m_tr.Init(m_env.TRXPOS.DSAX, m_env.TRXPOS.DSAY, m_env.BITBLTBUF, true);
m_tr.Init(m_env.TRXPOS, m_env.TRXREG, m_env.BITBLTBUF, true);
break;
case 1: // local -> host
m_tr.Init(m_env.TRXPOS.SSAX, m_env.TRXPOS.SSAY, m_env.BITBLTBUF, false);
m_tr.Init(m_env.TRXPOS, m_env.TRXREG, m_env.BITBLTBUF, false);
break;
case 2: // local -> local
CheckWriteOverlap(true, true);
@@ -1549,16 +1562,13 @@ void GSState::FlushWrite()
GSVector4i r;
r.left = m_env.TRXPOS.DSAX;
r.top = m_env.TRXPOS.DSAY;
r.right = r.left + m_env.TRXREG.RRW;
r.bottom = r.top + m_env.TRXREG.RRH;
r = m_tr.rect;
InvalidateVideoMem(m_env.BITBLTBUF, r);
const GSLocalMemory::writeImage wi = GSLocalMemory::m_psm[m_env.BITBLTBUF.DPSM].wi;
wi(m_mem, m_tr.x, m_tr.y, &m_tr.buff[m_tr.start], len, m_env.BITBLTBUF, m_env.TRXPOS, m_env.TRXREG);
wi(m_mem, m_tr.x, m_tr.y, &m_tr.buff[m_tr.start], len, m_tr.m_blit, m_tr.m_pos, m_tr.m_reg);
m_tr.start += len;
@@ -1931,12 +1941,9 @@ void GSState::Write(const u8* mem, int len)
if (m_env.TRXDIR.XDIR == 3)
return;
const int w = m_env.TRXREG.RRW;
const int h = m_env.TRXREG.RRH;
CheckWriteOverlap(true, false);
if (!m_tr.Update(w, h, GSLocalMemory::m_psm[m_env.BITBLTBUF.DPSM].trbpp, len))
if (!m_tr.Update(m_tr.w, m_tr.h, GSLocalMemory::m_psm[m_tr.m_blit.DPSM].trbpp, len))
{
m_env.TRXDIR.XDIR = 3;
return;
@@ -1949,10 +1956,7 @@ void GSState::Write(const u8* mem, int len)
{
GSVector4i r;
r.left = m_env.TRXPOS.DSAX;
r.top = m_env.TRXPOS.DSAY;
r.right = r.left + m_env.TRXREG.RRW;
r.bottom = r.top + m_env.TRXREG.RRH;
r = m_tr.rect;
s_last_transfer_draw_n = s_n;
// Store the transfer for preloading new RT's.
@@ -1974,15 +1978,15 @@ void GSState::Write(const u8* mem, int len)
GL_CACHE("Write! %u ... => 0x%x W:%d F:%s (DIR %d%d), dPos(%d %d) size(%d %d) draw %d", s_transfer_n,
blit.DBP, blit.DBW, psm_str(blit.DPSM),
m_env.TRXPOS.DIRX, m_env.TRXPOS.DIRY,
m_env.TRXPOS.DSAX, m_env.TRXPOS.DSAY, w, h, s_n);
m_tr.m_pos.DIRX, m_tr.m_pos.DIRY,
m_tr.x, m_tr.y, m_tr.w, m_tr.h, s_n);
if (len >= m_tr.total)
{
// received all data in one piece, no need to buffer it
InvalidateVideoMem(blit, r);
psm.wi(m_mem, m_tr.x, m_tr.y, mem, m_tr.total, blit, m_env.TRXPOS, m_env.TRXREG);
psm.wi(m_mem, m_tr.x, m_tr.y, mem, m_tr.total, blit, m_tr.m_pos, m_tr.m_reg);
m_tr.start = m_tr.end = m_tr.total;
@@ -2334,7 +2338,7 @@ void GSState::ReadLocalMemoryUnsync(u8* mem, int qwc, GIFRegBITBLTBUF BITBLTBUF,
GSTransferBuffer tb;
if(m_tr.end >= m_tr.total || m_tr.write == true)
tb.Init(TRXPOS.SSAX, TRXPOS.SSAY, BITBLTBUF, false);
tb.Init(TRXPOS, TRXREG, BITBLTBUF, false);
int len = qwc * 16;
if (!tb.Update(w, h, bpp, len))
@@ -2578,13 +2582,14 @@ static void ReadState(T* dst, u8*& src, size_t len = sizeof(T))
int GSState::Freeze(freezeData* fd, bool sizeonly)
{
const u32 version = STATE_VERSION;
if (sizeonly)
{
fd->size = GetSaveStateSize();
fd->size = GetSaveStateSize(version);
return 0;
}
if (!fd->data || fd->size < GetSaveStateSize())
if (!fd->data || fd->size < GetSaveStateSize(version))
return -1;
Flush(GSFlushReason::SAVESTATE);
@@ -2593,7 +2598,6 @@ int GSState::Freeze(freezeData* fd, bool sizeonly)
ReadbackTextureCache();
u8* data = fd->data;
const u32 version = STATE_VERSION;
WriteState(data, &version);
WriteState(data, &m_env.PRIM);
@@ -2636,6 +2640,18 @@ int GSState::Freeze(freezeData* fd, bool sizeonly)
data += sizeof(GIFReg); // obsolite
WriteState(data, &m_tr.x);
WriteState(data, &m_tr.y);
// Version 9 up.
WriteState(data, &m_tr.w);
WriteState(data, &m_tr.h);
WriteState(data, &m_tr.m_blit);
WriteState(data, &m_tr.m_pos);
WriteState(data, &m_tr.m_reg);
WriteState(data, &m_tr.rect);
WriteState(data, &m_tr.total);
WriteState(data, &m_tr.start);
WriteState(data, &m_tr.end);
WriteState(data, &m_tr.write);
// End of version 9 changes.
WriteState(data, m_mem.m_vm8, m_mem.m_vmsize);
for (GIFPath& path : m_path)
@@ -2663,15 +2679,15 @@ int GSState::Defrost(const freezeData* fd)
if (!fd || !fd->data || fd->size == 0)
return -1;
if (fd->size < GetSaveStateSize())
return -1;
u8* data = fd->data;
u32 version;
ReadState(&version, data);
if (fd->size < GetSaveStateSize(version))
return -1;
if (version > STATE_VERSION)
{
Console.Error("GS: Savestate version is incompatible. Load aborted.");
@@ -2701,12 +2717,6 @@ int GSState::Defrost(const freezeData* fd)
ReadState(&m_env.TRXPOS, data);
ReadState(&m_env.TRXREG, data);
ReadState(&m_env.TRXREG, data); // obsolete
// Technically this value ought to be saved like m_tr.x/y (break
// compatibility) but so far only a single game (Motocross Mania) really
// depends on this value (i.e != BITBLTBUF) Savestates are likely done at
// VSYNC, so not in the middle of a texture transfer, therefore register
// will be set again properly
m_tr.m_blit = m_env.BITBLTBUF;
for (int i = 0; i < 2; i++)
{
@@ -2742,9 +2752,36 @@ int GSState::Defrost(const freezeData* fd)
data += sizeof(GIFReg); // obsolite
ReadState(&m_tr.x, data);
ReadState(&m_tr.y, data);
ReadState(m_mem.m_vm8, data, m_mem.m_vmsize);
m_tr.total = 0; // TODO: restore transfer state
if (version >= 9)
{
ReadState(&m_tr.w, data);
ReadState(&m_tr.h, data);
ReadState(&m_tr.m_blit, data);
ReadState(&m_tr.m_pos, data);
ReadState(&m_tr.m_reg, data);
ReadState(&m_tr.rect, data);
ReadState(&m_tr.total, data);
ReadState(&m_tr.start, data);
ReadState(&m_tr.end, data);
ReadState(&m_tr.write, data);
}
else
{
m_tr.w = m_env.TRXREG.RRW;
m_tr.h = m_env.TRXREG.RRH;
m_tr.m_blit = m_env.BITBLTBUF;
m_tr.m_pos = m_env.TRXPOS;
m_tr.m_reg = m_env.TRXREG;
// Assume the last transfer was a write (but nuke it).
m_tr.rect = GSVector4i(m_env.TRXPOS.DSAX, m_env.TRXPOS.DSAY, m_env.TRXPOS.DSAX + m_tr.w, m_env.TRXPOS.DSAY + m_tr.h);
m_tr.total = 0;
m_tr.start = 0;
m_tr.end = 0;
m_tr.write = true;
}
ReadState(m_mem.m_vm8, data, m_mem.m_vmsize);
for (GIFPath& path : m_path)
{
@@ -3140,7 +3177,8 @@ bool GSState::SpriteDrawWithoutGaps()
}
else
{
if ((std::abs(dpX - first_dpX) >= 16 && (i + 2) < m_vertex.next) || std::abs(this_start_X - last_pX) >= 16)
const int dpY = v[i + 1].XYZ.Y - v[i].XYZ.Y;
if ((std::abs(dpY - first_dpY) >= 16 && (i + 2) < m_vertex.next) || std::abs(this_start_X - last_pX) >= 16)
return false;
}
}
@@ -4562,14 +4600,19 @@ GSState::GSTransferBuffer::~GSTransferBuffer()
_aligned_free(buff);
}
void GSState::GSTransferBuffer::Init(int tx, int ty, const GIFRegBITBLTBUF& blit, bool is_write)
void GSState::GSTransferBuffer::Init(GIFRegTRXPOS& TRXPOS, GIFRegTRXREG& TRXREG, const GIFRegBITBLTBUF& blit, bool is_write)
{
x = tx;
y = ty;
x = is_write ? TRXPOS.DSAX : TRXPOS.SSAX;
y = is_write ? TRXPOS.DSAY : TRXPOS.SSAY;
w = TRXREG.RRW;
h = TRXREG.RRH;
rect = GSVector4i(x, y, x + w, y + h);
total = 0;
start = 0;
end = 0;
m_blit = blit;
m_pos = TRXPOS;
m_reg = TRXREG;
write = is_write;
}

View File

@@ -21,7 +21,7 @@ public:
GSState();
virtual ~GSState();
static constexpr int GetSaveStateSize();
static constexpr int GetSaveStateSize(int version);
private:
// RESTRICT prevents multiple loads of the same part of the register when accessing its bitfields (the compiler is happy to know that memory writes in-between will not go there)
@@ -108,15 +108,19 @@ private:
struct GSTransferBuffer
{
int x = 0, y = 0;
int w = 0, h = 0;
int start = 0, end = 0, total = 0;
u8* buff = nullptr;
GSVector4i rect = GSVector4i::zero();
GIFRegBITBLTBUF m_blit = {};
GIFRegTRXPOS m_pos = {};
GIFRegTRXREG m_reg = {};
bool write = false;
GSTransferBuffer();
~GSTransferBuffer();
void Init(int tx, int ty, const GIFRegBITBLTBUF& blit, bool write);
void Init(GIFRegTRXPOS& TRXPOS, GIFRegTRXREG& TRXREG, const GIFRegBITBLTBUF& blit, bool is_write);
bool Update(int tw, int th, int bpp, int& len);
} m_tr;
@@ -259,7 +263,7 @@ public:
static int s_last_transfer_draw_n;
static int s_transfer_n;
static constexpr u32 STATE_VERSION = 8;
static constexpr u32 STATE_VERSION = 9;
enum REG_DIRTY
{

View File

@@ -3559,7 +3559,7 @@ void FullscreenUI::DrawInterfaceSettingsPage()
MenuHeading(FSUI_CSTR("Integration"));
DrawToggleSetting(bsi, FSUI_ICONSTR(ICON_FA_USER_CIRCLE, "Enable Discord Presence"),
FSUI_CSTR("Shows the game you are currently playing as part of your profile on Discord."), "UI", "DiscordPresence", false);
FSUI_CSTR("Shows the game you are currently playing as part of your profile on Discord."), "EmuCore", "EnableDiscordPresence", false);
MenuHeading(FSUI_CSTR("Game Display"));
DrawToggleSetting(bsi, FSUI_ICONSTR(ICON_FA_TV, "Start Fullscreen"),

View File

@@ -1898,6 +1898,7 @@ Pcsx2Config::Pcsx2Config()
UseSavestateSelector = true;
BackupSavestate = true;
WarnAboutUnsafeSettings = true;
EnableDiscordPresence = false;
ManuallySetRealTimeClock = false;
// To be moved to FileMemoryCard pluign (someday)

View File

@@ -25,7 +25,7 @@ enum class FreezeAction
// [SAVEVERSION+]
// This informs the auto updater that the users savestates will be invalidated.
static const u32 g_SaveVersion = (0x9A53 << 16) | 0x0000;
static const u32 g_SaveVersion = (0x9A54 << 16) | 0x0000;
// the freezing data between submodules and core