Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Slot2: Add Slide Controller #737

Draft
wants to merge 7 commits into
base: master
Choose a base branch
from
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions desmume/src/Makefile.am
Original file line number Diff line number Diff line change
Expand Up @@ -96,6 +96,7 @@ libdesmume_a_SOURCES = \
addons/slot2_rumblepak.cpp \
addons/slot2_guitarGrip.cpp \
addons/slot2_hcv1000.cpp \
addons/slot2_slideController.cpp \
addons/slot2_expMemory.cpp \
addons/slot2_piano.cpp \
addons/slot2_passme.cpp \
Expand Down
2 changes: 0 additions & 2 deletions desmume/src/addons/slot2_rumblepak.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -18,8 +18,6 @@

#include "../slot2.h"

void (*FeedbackON)(bool enable) = NULL;

class Slot2_RumblePak : public ISlot2Interface
{
private:
Expand Down
277 changes: 277 additions & 0 deletions desmume/src/addons/slot2_slideController.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,277 @@
//Serial handling code heavily inspired by the Magic Reader code in GBE+
//https://github.com/shonumi/gbe-plus/blob/7986317958a672d72ff54ea33f31bcca13cf8330/src/nds/slot2.cpp#L155

/*
Copyright (C) 2023 DeSmuME team

This file 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 of the License, or
(at your option) any later version.

This file 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 the this software. If not, see <http://www.gnu.org/licenses/>.
*/

//Absolute barebones implementation of the Slide Controller add-on.

#include "../slot2.h"
#include "../emufile.h"

static u8 delta_x;
static u8 delta_y;
//Product ID, Revision ID, Motion status, X delta, Y delta, Surface quality
//Average pixel, Maximum pixel, Reserved, Reserved, Configuration, Reserved
//Data out lower, Data out upper, Shutter lower, Shutter upper, Frame period lower, Frame period upper
static u8 sc_regs[18] =
{ 0x03, 0x20, 0x00, 0x00, 0x00, 0x80,
0x20, 0x3F, 0x00, 0x00, 0x00, 0x00,
0x00, 0x00, 0x64, 0x00, 0x20, 0xD1
};

class Slot2_SlideController : public ISlot2Interface
{
private:
u8 old_rumble;

struct
{
u16 in_data;
u16 out_data;
u8 counter;
u8 state;
u8 sck;
u8 reg_sel;
u8 tmp;
} slideCon = {};

void slideCon_reset()
{
delta_x = 0;
delta_y = 0;

old_rumble = 0;
if (FeedbackON)
FeedbackON(false);

slideCon.in_data = 0;
slideCon.out_data = 0;
slideCon.counter = 0;
slideCon.state = 0;
slideCon.sck = 0;
slideCon.reg_sel = 0;
slideCon.tmp = 0;

sc_regs[0x02] = 0x00; //Motion status
sc_regs[0x03] = 0x00; //X delta
sc_regs[0x04] = 0x00; //Y delta
sc_regs[0x0A] = 0x00; //Config bits
sc_regs[0x10] = 0x20; //Frame period lower
sc_regs[0x11] = 0xD1; //Frame period upper
}

void slideCon_process()
{
//Serial clock in bit 1
u8 new_sck = (slideCon.in_data & 0x2) >> 1;
//Serial data in bit 0
u8 sd = slideCon.in_data & 0x1;
//Rumble in bit 8
u8 rumble = (slideCon.in_data & 0x100) >> 8;

if (FeedbackON && (old_rumble != rumble))
{
old_rumble = rumble;
FeedbackON(rumble);
}

switch (slideCon.state)
{
case 0: //Reg select
//Build reg select byte
if ((slideCon.sck == 0) && (new_sck == 1) && (slideCon.counter < 8))
{
slideCon.reg_sel = (slideCon.reg_sel << 1) | sd;
slideCon.counter++;
}
else if (slideCon.counter == 8)
{
//Check if it's a read or a write by MSB
if (slideCon.reg_sel & 0x80)
{
slideCon.state = 1;
slideCon.reg_sel &= 0x7F;
slideCon.tmp = 0;
}
else
{
slideCon.state = 2;

if (slideCon.reg_sel == 0x02)
{
//Set motion flag if there has been movement
if (delta_x || delta_y)
sc_regs[0x02] |= 0x80;
//Freeze motion deltas
sc_regs[0x03] = delta_x;
sc_regs[0x04] = delta_y;
delta_x = delta_y = 0;
}
}
slideCon.counter = 0;
}
break;
case 1: //Write reg
if ((slideCon.sck == 0) && (new_sck == 1) && (slideCon.counter < 8))
{
slideCon.tmp = (slideCon.tmp << 1) | sd;
slideCon.counter++;
}
else if ((slideCon.sck == 0) && (new_sck == 0) && (slideCon.counter == 8))
{
//printf("SLIDECON WRITE REG: %02X = %02X\n", slideCon.reg_sel, slideCon.tmp);
slideCon.state = 0;
slideCon.counter = 0;

if (slideCon.reg_sel <= 0x11)
sc_regs[slideCon.reg_sel] = slideCon.tmp;
}
break;
case 2: //Read reg
if ((slideCon.sck == 0) && (new_sck == 1) && (slideCon.counter < 8))
{
if (slideCon.reg_sel <= 0x11)
slideCon.out_data = (sc_regs[slideCon.reg_sel] >> (7 - slideCon.counter)) & 1;
else
slideCon.out_data = 0;
slideCon.counter++;
}
else if ((slideCon.sck == 0) && (new_sck == 0) && (slideCon.counter == 8))
{
//printf("SLIDECON READ REG: %02X = %02X\n", slideCon.reg_sel, sc_regs[slideCon.reg_sel]);
slideCon.state = 0;
slideCon.counter = 0;

//Reset motion flag if reg was motion status
if (slideCon.reg_sel == 0x02)
sc_regs[0x02] &= 0x7F;
//Reset motion deltas if they were read
if ((slideCon.reg_sel == 0x03) || (slideCon.reg_sel == 0x04))
sc_regs[slideCon.reg_sel] = 0x00;
}
break;
}

slideCon.sck = new_sck;

if (sc_regs[0x0A] & 0x80) //Reset
{
slideCon_reset();
}
}

public:

virtual Slot2Info const* info()
{
static Slot2InfoSimple info("Slide Controller", "Slide Controller add-on", 0x0A);
return &info;
}

virtual void connect()
{
slideCon_reset();
}

virtual void disconnect()
{
if (FeedbackON)
FeedbackON(false);
}

virtual void writeWord(u8 PROCNUM, u32 addr, u16 val)
{
if (addr == 0x081E0000)
{
slideCon.in_data = val;
slideCon_process();
}
}

virtual u8 readByte(u8 PROCNUM, u32 addr)
{
if (addr == 0x080000B2)
return 0x96;
else
return 0xFF;
}

virtual u16 readWord(u8 PROCNUM, u32 addr)
{
u16 outWord = 0xFFFF;

if (addr < 0x08000100)
outWord = 0xFEF0;
else if (addr == 0x081E0000)
outWord = slideCon.out_data;

return outWord;
}

virtual u32 readLong(u8 PROCNUM, u32 addr) { return 0xFEF0FEF0; }

virtual void savestate(EMUFILE& os)
{
s32 version = 0;
os.write_32LE(version);

os.write_u8(delta_x);
os.write_u8(delta_y);
for (int i = 0; i < 18; i++)
os.write_u8(sc_regs[i]);
os.write_16LE(slideCon.in_data);
os.write_16LE(slideCon.out_data);
os.write_u8(slideCon.counter);
os.write_u8(slideCon.state);
os.write_u8(slideCon.sck);
os.write_u8(slideCon.reg_sel);
os.write_u8(slideCon.tmp);
}

virtual void loadstate(EMUFILE& is)
{
s32 version = is.read_s32LE();

if (version == 0)
{
is.read_u8(delta_x);
is.read_u8(delta_y);
for (int i = 0; i < 18; i++)
sc_regs[i] = is.read_u8();
is.read_16LE(slideCon.in_data);
is.read_16LE(slideCon.out_data);
is.read_u8(slideCon.counter);
is.read_u8(slideCon.state);
is.read_u8(slideCon.sck);
is.read_u8(slideCon.reg_sel);
is.read_u8(slideCon.tmp);
}

old_rumble = 0;
if (FeedbackON)
FeedbackON(false);
}
};

ISlot2Interface* construct_Slot2_SlideController() { return new Slot2_SlideController(); }

void slideController_updateMotion(s8 x, s8 y)
{
delta_x = (u8)x;
delta_y = (u8)y;
}
2 changes: 1 addition & 1 deletion desmume/src/frontend/interface/meson.build
Original file line number Diff line number Diff line change
Expand Up @@ -109,7 +109,7 @@ libdesmume_src += [
'../../utils/tinyxml/tinyxmlerror.cpp',
'../../utils/tinyxml/tinyxmlparser.cpp',
'../../utils/colorspacehandler/colorspacehandler.cpp',
'../../addons/slot2_auto.cpp', '../../addons/slot2_mpcf.cpp', '../../addons/slot2_paddle.cpp', '../../addons/slot2_gbagame.cpp', '../../addons/slot2_none.cpp', '../../addons/slot2_rumblepak.cpp', '../../addons/slot2_guitarGrip.cpp', '../../addons/slot2_hcv1000.cpp', '../../addons/slot2_expMemory.cpp', '../../addons/slot2_piano.cpp', '../../addons/slot2_passme.cpp', '../../addons/slot1_none.cpp', '../../addons/slot1_r4.cpp', '../../addons/slot1_retail_nand.cpp', '../../addons/slot1_retail_auto.cpp', '../../addons/slot1_retail_mcrom.cpp', '../../addons/slot1_retail_mcrom_debug.cpp', '../../addons/slot1comp_mc.cpp', '../../addons/slot1comp_rom.cpp', '../../addons/slot1comp_protocol.cpp',
'../../addons/slot2_auto.cpp', '../../addons/slot2_mpcf.cpp', '../../addons/slot2_paddle.cpp', '../../addons/slot2_gbagame.cpp', '../../addons/slot2_none.cpp', '../../addons/slot2_rumblepak.cpp', '../../addons/slot2_guitarGrip.cpp', '../../addons/slot2_hcv1000.cpp', '../../addons/slot2_slideController.cpp', '../../addons/slot2_expMemory.cpp', '../../addons/slot2_piano.cpp', '../../addons/slot2_passme.cpp', '../../addons/slot1_none.cpp', '../../addons/slot1_r4.cpp', '../../addons/slot1_retail_nand.cpp', '../../addons/slot1_retail_auto.cpp', '../../addons/slot1_retail_mcrom.cpp', '../../addons/slot1_retail_mcrom_debug.cpp', '../../addons/slot1comp_mc.cpp', '../../addons/slot1comp_rom.cpp', '../../addons/slot1comp_protocol.cpp',
'../../cheatSystem.cpp',
'../../texcache.cpp', '../../rasterize.cpp',
'../../metaspu/metaspu.cpp',
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -269,6 +269,7 @@
<ClCompile Include="..\..\..\addons\slot2_gbagame.cpp" />
<ClCompile Include="..\..\..\addons\slot2_guitarGrip.cpp" />
<ClCompile Include="..\..\..\addons\slot2_hcv1000.cpp" />
<ClCompile Include="..\..\..\addons\slot2_slideController.cpp" />
<ClCompile Include="..\..\..\addons\slot2_none.cpp" />
<ClCompile Include="..\..\..\addons\slot2_rumblepak.cpp" />
<ClCompile Include="..\..\..\utils\guid.cpp" />
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -135,6 +135,9 @@
<ClCompile Include="..\..\..\addons\slot2_hcv1000.cpp">
<Filter>addons</Filter>
</ClCompile>
<ClCompile Include="..\..\..\addons\slot2_slideController.cpp">
<Filter>addons</Filter>
</ClCompile>
<ClCompile Include="..\..\..\addons\slot2_none.cpp">
<Filter>addons</Filter>
</ClCompile>
Expand Down
2 changes: 1 addition & 1 deletion desmume/src/frontend/posix/Makefile.am
Original file line number Diff line number Diff line change
Expand Up @@ -98,7 +98,7 @@ libdesmume_a_SOURCES = \
../../utils/tinyxml/tinyxmlparser.cpp \
../../utils/glcorearb.h \
../../utils/colorspacehandler/colorspacehandler.cpp ../../utils/colorspacehandler/colorspacehandler.h \
../../addons/slot2_auto.cpp ../../addons/slot2_mpcf.cpp ../../addons/slot2_paddle.cpp ../../addons/slot2_gbagame.cpp ../../addons/slot2_none.cpp ../../addons/slot2_rumblepak.cpp ../../addons/slot2_guitarGrip.cpp ../../addons/slot2_hcv1000.cpp ../../addons/slot2_expMemory.cpp ../../addons/slot2_piano.cpp ../../addons/slot2_passme.cpp ../../addons/slot1_none.cpp ../../addons/slot1_r4.cpp ../../addons/slot1_retail_nand.cpp ../../addons/slot1_retail_auto.cpp ../../addons/slot1_retail_mcrom.cpp ../../addons/slot1_retail_mcrom_debug.cpp ../../addons/slot1comp_mc.cpp ../../addons/slot1comp_mc.h ../../addons/slot1comp_rom.h ../../addons/slot1comp_rom.cpp ../../addons/slot1comp_protocol.h ../../addons/slot1comp_protocol.cpp \
../../addons/slot2_auto.cpp ../../addons/slot2_mpcf.cpp ../../addons/slot2_paddle.cpp ../../addons/slot2_gbagame.cpp ../../addons/slot2_none.cpp ../../addons/slot2_rumblepak.cpp ../../addons/slot2_guitarGrip.cpp ../../addons/slot2_hcv1000.cpp ../../addons/slot2_slideController.cpp ../../addons/slot2_expMemory.cpp ../../addons/slot2_piano.cpp ../../addons/slot2_passme.cpp ../../addons/slot1_none.cpp ../../addons/slot1_r4.cpp ../../addons/slot1_retail_nand.cpp ../../addons/slot1_retail_auto.cpp ../../addons/slot1_retail_mcrom.cpp ../../addons/slot1_retail_mcrom_debug.cpp ../../addons/slot1comp_mc.cpp ../../addons/slot1comp_mc.h ../../addons/slot1comp_rom.h ../../addons/slot1comp_rom.cpp ../../addons/slot1comp_protocol.h ../../addons/slot1comp_protocol.cpp \
../../cheatSystem.cpp ../../cheatSystem.h \
../../texcache.cpp ../../texcache.h ../../rasterize.cpp ../../rasterize.h \
../../metaspu/metaspu.cpp ../../metaspu/metaspu.h \
Expand Down
2 changes: 1 addition & 1 deletion desmume/src/frontend/posix/meson.build
Original file line number Diff line number Diff line change
Expand Up @@ -104,7 +104,7 @@ libdesmume_src = [
'../../utils/tinyxml/tinyxmlerror.cpp',
'../../utils/tinyxml/tinyxmlparser.cpp',
'../../utils/colorspacehandler/colorspacehandler.cpp',
'../../addons/slot2_auto.cpp', '../../addons/slot2_mpcf.cpp', '../../addons/slot2_paddle.cpp', '../../addons/slot2_gbagame.cpp', '../../addons/slot2_none.cpp', '../../addons/slot2_rumblepak.cpp', '../../addons/slot2_guitarGrip.cpp', '../../addons/slot2_hcv1000.cpp', '../../addons/slot2_expMemory.cpp', '../../addons/slot2_piano.cpp', '../../addons/slot2_passme.cpp', '../../addons/slot1_none.cpp', '../../addons/slot1_r4.cpp', '../../addons/slot1_retail_nand.cpp', '../../addons/slot1_retail_auto.cpp', '../../addons/slot1_retail_mcrom.cpp', '../../addons/slot1_retail_mcrom_debug.cpp', '../../addons/slot1comp_mc.cpp', '../../addons/slot1comp_rom.cpp', '../../addons/slot1comp_protocol.cpp',
'../../addons/slot2_auto.cpp', '../../addons/slot2_mpcf.cpp', '../../addons/slot2_paddle.cpp', '../../addons/slot2_gbagame.cpp', '../../addons/slot2_none.cpp', '../../addons/slot2_rumblepak.cpp', '../../addons/slot2_guitarGrip.cpp', '../../addons/slot2_hcv1000.cpp', '../../addons/slot2_slideController.cpp', '../../addons/slot2_expMemory.cpp', '../../addons/slot2_piano.cpp', '../../addons/slot2_passme.cpp', '../../addons/slot1_none.cpp', '../../addons/slot1_r4.cpp', '../../addons/slot1_retail_nand.cpp', '../../addons/slot1_retail_auto.cpp', '../../addons/slot1_retail_mcrom.cpp', '../../addons/slot1_retail_mcrom_debug.cpp', '../../addons/slot1comp_mc.cpp', '../../addons/slot1comp_rom.cpp', '../../addons/slot1comp_protocol.cpp',
'../../cheatSystem.cpp',
'../../texcache.cpp', '../../rasterize.cpp',
'../../metaspu/metaspu.cpp',
Expand Down
1 change: 1 addition & 0 deletions desmume/src/frontend/windows/DeSmuME.vcxproj
Original file line number Diff line number Diff line change
Expand Up @@ -73,6 +73,7 @@
<ClCompile Include="..\..\addons\slot1_retail_nand.cpp" />
<ClCompile Include="..\..\addons\slot2_mpcf.cpp" />
<ClCompile Include="..\..\addons\slot2_paddle.cpp" />
<ClCompile Include="..\..\addons\slot2_slideController.cpp" />
<ClCompile Include="..\..\arm_instructions.cpp" />
<ClCompile Include="..\..\armcpu.cpp" />
<ClCompile Include="..\..\arm_jit.cpp" />
Expand Down
3 changes: 3 additions & 0 deletions desmume/src/frontend/windows/DeSmuME.vcxproj.filters
Original file line number Diff line number Diff line change
Expand Up @@ -933,6 +933,9 @@
<ClCompile Include="..\..\addons\slot2_hcv1000.cpp">
<Filter>addons</Filter>
</ClCompile>
<ClCompile Include="..\..\addons\slot2_slideController.cpp">
<Filter>addons</Filter>
</ClCompile>
</ItemGroup>
<ItemGroup>
<ClInclude Include="..\..\utils\guid.h">
Expand Down
Loading