snes-some beginning steps on graphics debugging tools. nothing to see yet, move along

This commit is contained in:
zeromus 2012-09-06 08:32:25 +00:00
parent fd1560177e
commit ad6910fd74
16 changed files with 1311 additions and 220 deletions

View File

@ -258,6 +258,7 @@
<Compile Include="Consoles\Nintendo\NES\PPU.regs.cs" />
<Compile Include="Consoles\Nintendo\NES\PPU.run.cs" />
<Compile Include="Consoles\Nintendo\SNES\LibsnesCore.cs" />
<Compile Include="Consoles\Nintendo\SNES\SNESGraphicsDecoder.cs" />
<Compile Include="Consoles\PC Engine\ADPCM.cs" />
<Compile Include="Consoles\PC Engine\ArcadeCard.cs" />
<Compile Include="Consoles\PC Engine\MemoryMap.TurboCD.cs" />

View File

@ -1,4 +1,6 @@
//TODO
//http://wiki.superfamicom.org/snes/show/Backgrounds
//TODO
//libsnes needs to be modified to support multiple instances - THIS IS NECESSARY - or else loading one game and then another breaks things
//rename snes.dll so nobody thinks it's a stock snes.dll (we'll be editing it substantially at some point)
//wrap dll code around some kind of library-accessing interface so that it doesnt malfunction if the dll is unavailable
@ -88,6 +90,38 @@ namespace BizHawk.Emulation.Consoles.Nintendo.SNES
[MarshalAs(UnmanagedType.U1)]
bool enable
);
[DllImport("snes.dll", CallingConvention = CallingConvention.Cdecl)]
public static extern int snes_peek_logical_register(SNES_REG reg);
public enum SNES_REG : int
{
//$2105
BG_MODE = 0,
BG3_PRIORITY = 1,
BG1_TILESIZE = 2,
BG2_TILESIZE = 3,
BG3_TILESIZE = 4,
BG4_TILESIZE = 5,
//$2107
BG1_SCADDR = 10,
BG1_SCSIZE = 11,
//$2108
BG2_SCADDR = 12,
BG2_SCSIZE = 13,
//$2109
BG3_SCADDR = 14,
BG3_SCSIZE = 15,
//$210A
BG4_SCADDR = 16,
BG4_SCSIZE = 17,
//$210B
BG1_TDADDR = 20,
BG2_TDADDR = 21,
//$210C
BG3_TDADDR = 22,
BG4_TDADDR = 23
}
public enum SNES_MEMORY : uint
{
@ -142,6 +176,7 @@ namespace BizHawk.Emulation.Consoles.Nintendo.SNES
}
}
public unsafe class LibsnesCore : IEmulator, IVideoProvider, ISoundProvider
{
bool disposed = false;
@ -448,6 +483,8 @@ namespace BizHawk.Emulation.Consoles.Nintendo.SNES
/// <summary>stores samples that have been converted to 44100hz</summary>
Queue<short> AudioOutBuffer = new Queue<short>();
GCHandle _gc_snes_audio_sample;
/// <summary>total number of samples (left and right combined) in the InBuffer before we ask for resampling</summary>
const int resamplechunk = 1000;
/// <summary>actual sampling factor used</summary>

View File

@ -84,6 +84,11 @@ namespace BizHawk
public static class Extensions
{
public static string ToHexString(this int n, int numdigits)
{
return string.Format("{0:X" + numdigits + "}", n);
}
public static void CopyTo(this Stream src, Stream dest)
{
int size = (src.CanSeek) ? Math.Min((int)(src.Length - src.Position), 0x2000) : 0x2000;

View File

@ -326,6 +326,15 @@
</Compile>
<Compile Include="Program.cs" />
<Compile Include="Properties\AssemblyInfo.cs" />
<Compile Include="SNESTools\SNESGraphicsDebugger.cs">
<SubType>Form</SubType>
</Compile>
<Compile Include="SNESTools\SNESGraphicsDebugger.Designer.cs">
<DependentUpon>SNESGraphicsDebugger.cs</DependentUpon>
</Compile>
<Compile Include="SNESTools\SNESGraphicsViewer.cs">
<SubType>Component</SubType>
</Compile>
<Compile Include="tools\HexColor.cs">
<SubType>Form</SubType>
</Compile>
@ -408,6 +417,9 @@
<EmbeddedResource Include="SMStools\SMSGraphicsConfig.resx">
<DependentUpon>SMSGraphicsConfig.cs</DependentUpon>
</EmbeddedResource>
<EmbeddedResource Include="SNESTools\SNESGraphicsDebugger.resx">
<DependentUpon>SNESGraphicsDebugger.cs</DependentUpon>
</EmbeddedResource>
<EmbeddedResource Include="tools\HexColor.resx">
<DependentUpon>HexColor.cs</DependentUpon>
</EmbeddedResource>

File diff suppressed because it is too large Load Diff

View File

@ -10,6 +10,7 @@ namespace BizHawk.MultiClient
{
partial class MainForm
{
private void recordAVIToolStripMenuItem_Click(object sender, EventArgs e)
{
RecordAVI();
@ -504,6 +505,11 @@ namespace BizHawk.MultiClient
}
}
private void SNESGraphicsDebuggerToolStripMenuItem_Click(object sender, EventArgs e)
{
LoadSNESGraphicsDebugger();
}
private void hexEditorToolStripMenuItem_Click(object sender, EventArgs e)
{
LoadHexEditor();

View File

@ -70,6 +70,7 @@ namespace BizHawk.MultiClient
public RamWatch RamWatch1 = new RamWatch();
public RamSearch RamSearch1 = new RamSearch();
public HexEditor HexEditor1 = new HexEditor();
public SNESGraphicsDebugger SNESGraphicsDebugger1 = new SNESGraphicsDebugger();
public NESNameTableViewer NESNameTableViewer1 = new NESNameTableViewer();
public NESPPU NESPPU1 = new NESPPU();
public NESDebugger NESDebug1 = new NESDebugger();
@ -2090,6 +2091,7 @@ namespace BizHawk.MultiClient
NESPPU1.UpdateValues();
PCEBGViewer1.UpdateValues();
GBDebugger.UpdateValues();
SNESGraphicsDebugger1.UpdateValues();
}
/// <summary>
@ -2342,6 +2344,17 @@ namespace BizHawk.MultiClient
gg.Show();
}
public void LoadSNESGraphicsDebugger()
{
if (!SNESGraphicsDebugger1.IsHandleCreated || SNESGraphicsDebugger1.IsDisposed)
{
SNESGraphicsDebugger1 = new SNESGraphicsDebugger();
SNESGraphicsDebugger1.Show();
}
else
SNESGraphicsDebugger1.Focus();
}
public void LoadHexEditor()
{
if (!HexEditor1.IsHandleCreated || HexEditor1.IsDisposed)
@ -3405,5 +3418,6 @@ namespace BizHawk.MultiClient
var file = new FileInfo(PathManager.SaveRamPath(Global.Game));
if (file.Exists) file.Delete();
}
}
}

View File

@ -117,11 +117,14 @@
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<metadata name="menuStrip1.TrayLocation" type="System.Drawing.Point, System.Drawing, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a">
<value>17, 17</value>
</metadata>
<metadata name="StatusSlot0.TrayLocation" type="System.Drawing.Point, System.Drawing, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a">
<value>126, 17</value>
</metadata>
<metadata name="contextMenuStrip1.TrayLocation" type="System.Drawing.Point, System.Drawing, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a">
<value>236, 17</value>
<value>233, 17</value>
</metadata>
<metadata name="$this.TrayHeight" type="System.Int32, mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089">
<value>43</value>

View File

@ -0,0 +1,662 @@
namespace BizHawk.MultiClient
{
partial class SNESGraphicsDebugger
{
/// <summary>
/// Required designer variable.
/// </summary>
private System.ComponentModel.IContainer components = null;
/// <summary>
/// Clean up any resources being used.
/// </summary>
/// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param>
protected override void Dispose(bool disposing)
{
if (disposing && (components != null))
{
components.Dispose();
}
base.Dispose(disposing);
}
#region Windows Form Designer generated code
/// <summary>
/// Required method for Designer support - do not modify
/// the contents of this method with the code editor.
/// </summary>
private void InitializeComponent()
{
this.label1 = new System.Windows.Forms.Label();
this.groupBox1 = new System.Windows.Forms.GroupBox();
this.label13 = new System.Windows.Forms.Label();
this.txtBG1Colors = new System.Windows.Forms.TextBox();
this.txtBG1Bpp = new System.Windows.Forms.TextBox();
this.label12 = new System.Windows.Forms.Label();
this.txtBG1TDAddrDescr = new System.Windows.Forms.TextBox();
this.label11 = new System.Windows.Forms.Label();
this.txtBG1SCAddrDescr = new System.Windows.Forms.TextBox();
this.label9 = new System.Windows.Forms.Label();
this.txtBG1TDAddrBits = new System.Windows.Forms.TextBox();
this.label10 = new System.Windows.Forms.Label();
this.txtBG1SizeInPixels = new System.Windows.Forms.TextBox();
this.label3 = new System.Windows.Forms.Label();
this.txtBG1SCAddrBits = new System.Windows.Forms.TextBox();
this.txtBG1SizeInTiles = new System.Windows.Forms.TextBox();
this.label2 = new System.Windows.Forms.Label();
this.txtBG1SizeBits = new System.Windows.Forms.TextBox();
this.txtModeBits = new System.Windows.Forms.TextBox();
this.txtScreenBG1Bpp = new System.Windows.Forms.TextBox();
this.label4 = new System.Windows.Forms.Label();
this.label5 = new System.Windows.Forms.Label();
this.label6 = new System.Windows.Forms.Label();
this.label7 = new System.Windows.Forms.Label();
this.label8 = new System.Windows.Forms.Label();
this.txtScreenBG2Bpp = new System.Windows.Forms.TextBox();
this.txtScreenBG3Bpp = new System.Windows.Forms.TextBox();
this.txtScreenBG4Bpp = new System.Windows.Forms.TextBox();
this.groupBox2 = new System.Windows.Forms.GroupBox();
this.comboDisplayType = new System.Windows.Forms.ComboBox();
this.radioButton1 = new System.Windows.Forms.RadioButton();
this.radioButton2 = new System.Windows.Forms.RadioButton();
this.radioButton3 = new System.Windows.Forms.RadioButton();
this.radioButton4 = new System.Windows.Forms.RadioButton();
this.radioButton5 = new System.Windows.Forms.RadioButton();
this.radioButton6 = new System.Windows.Forms.RadioButton();
this.radioButton7 = new System.Windows.Forms.RadioButton();
this.radioButton8 = new System.Windows.Forms.RadioButton();
this.radioButton9 = new System.Windows.Forms.RadioButton();
this.radioButton10 = new System.Windows.Forms.RadioButton();
this.radioButton11 = new System.Windows.Forms.RadioButton();
this.radioButton12 = new System.Windows.Forms.RadioButton();
this.radioButton13 = new System.Windows.Forms.RadioButton();
this.label14 = new System.Windows.Forms.Label();
this.viewer = new BizHawk.MultiClient.SNESGraphicsViewer();
this.groupBox1.SuspendLayout();
this.groupBox2.SuspendLayout();
this.SuspendLayout();
//
// label1
//
this.label1.AutoSize = true;
this.label1.Location = new System.Drawing.Point(37, 30);
this.label1.Name = "label1";
this.label1.Size = new System.Drawing.Size(34, 13);
this.label1.TabIndex = 0;
this.label1.Text = "Mode";
//
// groupBox1
//
this.groupBox1.Controls.Add(this.label13);
this.groupBox1.Controls.Add(this.txtBG1Colors);
this.groupBox1.Controls.Add(this.txtBG1Bpp);
this.groupBox1.Controls.Add(this.label12);
this.groupBox1.Controls.Add(this.txtBG1TDAddrDescr);
this.groupBox1.Controls.Add(this.label11);
this.groupBox1.Controls.Add(this.txtBG1SCAddrDescr);
this.groupBox1.Controls.Add(this.label9);
this.groupBox1.Controls.Add(this.txtBG1TDAddrBits);
this.groupBox1.Controls.Add(this.label10);
this.groupBox1.Controls.Add(this.txtBG1SizeInPixels);
this.groupBox1.Controls.Add(this.label3);
this.groupBox1.Controls.Add(this.txtBG1SCAddrBits);
this.groupBox1.Controls.Add(this.txtBG1SizeInTiles);
this.groupBox1.Controls.Add(this.label2);
this.groupBox1.Controls.Add(this.txtBG1SizeBits);
this.groupBox1.Location = new System.Drawing.Point(12, 102);
this.groupBox1.Name = "groupBox1";
this.groupBox1.Size = new System.Drawing.Size(327, 189);
this.groupBox1.TabIndex = 3;
this.groupBox1.TabStop = false;
this.groupBox1.Text = "BG1";
//
// label13
//
this.label13.AutoSize = true;
this.label13.Location = new System.Drawing.Point(236, 24);
this.label13.Name = "label13";
this.label13.Size = new System.Drawing.Size(36, 13);
this.label13.TabIndex = 20;
this.label13.Text = "Colors";
//
// txtBG1Colors
//
this.txtBG1Colors.Location = new System.Drawing.Point(205, 21);
this.txtBG1Colors.Multiline = true;
this.txtBG1Colors.Name = "txtBG1Colors";
this.txtBG1Colors.ReadOnly = true;
this.txtBG1Colors.Size = new System.Drawing.Size(25, 17);
this.txtBG1Colors.TabIndex = 19;
this.txtBG1Colors.Text = "00";
//
// txtBG1Bpp
//
this.txtBG1Bpp.Location = new System.Drawing.Point(150, 21);
this.txtBG1Bpp.Multiline = true;
this.txtBG1Bpp.Name = "txtBG1Bpp";
this.txtBG1Bpp.ReadOnly = true;
this.txtBG1Bpp.Size = new System.Drawing.Size(18, 17);
this.txtBG1Bpp.TabIndex = 18;
this.txtBG1Bpp.Text = "8";
//
// label12
//
this.label12.AutoSize = true;
this.label12.Location = new System.Drawing.Point(170, 24);
this.label12.Name = "label12";
this.label12.Size = new System.Drawing.Size(32, 13);
this.label12.TabIndex = 17;
this.label12.Text = "Bpp; ";
//
// txtBG1TDAddrDescr
//
this.txtBG1TDAddrDescr.Location = new System.Drawing.Point(98, 86);
this.txtBG1TDAddrDescr.Multiline = true;
this.txtBG1TDAddrDescr.Name = "txtBG1TDAddrDescr";
this.txtBG1TDAddrDescr.ReadOnly = true;
this.txtBG1TDAddrDescr.Size = new System.Drawing.Size(71, 19);
this.txtBG1TDAddrDescr.TabIndex = 15;
this.txtBG1TDAddrDescr.Text = "1024z1024";
//
// label11
//
this.label11.AutoSize = true;
this.label11.Location = new System.Drawing.Point(37, 91);
this.label11.Name = "label11";
this.label11.Size = new System.Drawing.Size(47, 13);
this.label11.TabIndex = 14;
this.label11.Text = "TD.Addr";
//
// txtBG1SCAddrDescr
//
this.txtBG1SCAddrDescr.Location = new System.Drawing.Point(98, 65);
this.txtBG1SCAddrDescr.Multiline = true;
this.txtBG1SCAddrDescr.Name = "txtBG1SCAddrDescr";
this.txtBG1SCAddrDescr.ReadOnly = true;
this.txtBG1SCAddrDescr.Size = new System.Drawing.Size(71, 19);
this.txtBG1SCAddrDescr.TabIndex = 12;
this.txtBG1SCAddrDescr.Text = "1024z1024";
//
// label9
//
this.label9.AutoSize = true;
this.label9.Location = new System.Drawing.Point(277, 45);
this.label9.Name = "label9";
this.label9.Size = new System.Drawing.Size(34, 13);
this.label9.TabIndex = 9;
this.label9.Text = "Pixels";
//
// txtBG1TDAddrBits
//
this.txtBG1TDAddrBits.Location = new System.Drawing.Point(6, 88);
this.txtBG1TDAddrBits.Multiline = true;
this.txtBG1TDAddrBits.Name = "txtBG1TDAddrBits";
this.txtBG1TDAddrBits.ReadOnly = true;
this.txtBG1TDAddrBits.Size = new System.Drawing.Size(25, 17);
this.txtBG1TDAddrBits.TabIndex = 13;
this.txtBG1TDAddrBits.Text = "00";
//
// label10
//
this.label10.AutoSize = true;
this.label10.Location = new System.Drawing.Point(37, 68);
this.label10.Name = "label10";
this.label10.Size = new System.Drawing.Size(46, 13);
this.label10.TabIndex = 11;
this.label10.Text = "SC.Addr";
//
// txtBG1SizeInPixels
//
this.txtBG1SizeInPixels.Location = new System.Drawing.Point(205, 42);
this.txtBG1SizeInPixels.Multiline = true;
this.txtBG1SizeInPixels.Name = "txtBG1SizeInPixels";
this.txtBG1SizeInPixels.ReadOnly = true;
this.txtBG1SizeInPixels.Size = new System.Drawing.Size(71, 19);
this.txtBG1SizeInPixels.TabIndex = 8;
this.txtBG1SizeInPixels.Text = "1024z1024";
//
// label3
//
this.label3.AutoSize = true;
this.label3.Location = new System.Drawing.Point(170, 45);
this.label3.Name = "label3";
this.label3.Size = new System.Drawing.Size(32, 13);
this.label3.TabIndex = 7;
this.label3.Text = "Tiles;";
//
// txtBG1SCAddrBits
//
this.txtBG1SCAddrBits.Location = new System.Drawing.Point(6, 65);
this.txtBG1SCAddrBits.Multiline = true;
this.txtBG1SCAddrBits.Name = "txtBG1SCAddrBits";
this.txtBG1SCAddrBits.ReadOnly = true;
this.txtBG1SCAddrBits.Size = new System.Drawing.Size(25, 17);
this.txtBG1SCAddrBits.TabIndex = 10;
this.txtBG1SCAddrBits.Text = "00";
//
// txtBG1SizeInTiles
//
this.txtBG1SizeInTiles.Location = new System.Drawing.Point(98, 42);
this.txtBG1SizeInTiles.Multiline = true;
this.txtBG1SizeInTiles.Name = "txtBG1SizeInTiles";
this.txtBG1SizeInTiles.ReadOnly = true;
this.txtBG1SizeInTiles.Size = new System.Drawing.Size(71, 17);
this.txtBG1SizeInTiles.TabIndex = 6;
this.txtBG1SizeInTiles.Text = "64x64";
//
// label2
//
this.label2.AutoSize = true;
this.label2.Location = new System.Drawing.Point(37, 45);
this.label2.Name = "label2";
this.label2.Size = new System.Drawing.Size(27, 13);
this.label2.TabIndex = 4;
this.label2.Text = "Size";
//
// txtBG1SizeBits
//
this.txtBG1SizeBits.Location = new System.Drawing.Point(6, 42);
this.txtBG1SizeBits.Multiline = true;
this.txtBG1SizeBits.Name = "txtBG1SizeBits";
this.txtBG1SizeBits.ReadOnly = true;
this.txtBG1SizeBits.Size = new System.Drawing.Size(25, 17);
this.txtBG1SizeBits.TabIndex = 5;
this.txtBG1SizeBits.Text = "00";
//
// txtModeBits
//
this.txtModeBits.Location = new System.Drawing.Point(6, 28);
this.txtModeBits.Multiline = true;
this.txtModeBits.Name = "txtModeBits";
this.txtModeBits.ReadOnly = true;
this.txtModeBits.Size = new System.Drawing.Size(25, 17);
this.txtModeBits.TabIndex = 6;
this.txtModeBits.Text = "000";
//
// txtScreenBG1Bpp
//
this.txtScreenBG1Bpp.Location = new System.Drawing.Point(78, 28);
this.txtScreenBG1Bpp.Multiline = true;
this.txtScreenBG1Bpp.Name = "txtScreenBG1Bpp";
this.txtScreenBG1Bpp.ReadOnly = true;
this.txtScreenBG1Bpp.Size = new System.Drawing.Size(18, 17);
this.txtScreenBG1Bpp.TabIndex = 8;
this.txtScreenBG1Bpp.Text = "8";
//
// label4
//
this.label4.AutoSize = true;
this.label4.Location = new System.Drawing.Point(74, 12);
this.label4.Name = "label4";
this.label4.Size = new System.Drawing.Size(28, 13);
this.label4.TabIndex = 9;
this.label4.Text = "BG1";
//
// label5
//
this.label5.AutoSize = true;
this.label5.Location = new System.Drawing.Point(98, 12);
this.label5.Name = "label5";
this.label5.Size = new System.Drawing.Size(28, 13);
this.label5.TabIndex = 10;
this.label5.Text = "BG2";
//
// label6
//
this.label6.AutoSize = true;
this.label6.Location = new System.Drawing.Point(123, 12);
this.label6.Name = "label6";
this.label6.Size = new System.Drawing.Size(28, 13);
this.label6.TabIndex = 11;
this.label6.Text = "BG3";
//
// label7
//
this.label7.AutoSize = true;
this.label7.Location = new System.Drawing.Point(147, 12);
this.label7.Name = "label7";
this.label7.Size = new System.Drawing.Size(28, 13);
this.label7.TabIndex = 12;
this.label7.Text = "BG4";
//
// label8
//
this.label8.AutoSize = true;
this.label8.Location = new System.Drawing.Point(175, 30);
this.label8.Name = "label8";
this.label8.Size = new System.Drawing.Size(25, 13);
this.label8.TabIndex = 7;
this.label8.Text = "bpp";
//
// txtScreenBG2Bpp
//
this.txtScreenBG2Bpp.Location = new System.Drawing.Point(102, 28);
this.txtScreenBG2Bpp.Multiline = true;
this.txtScreenBG2Bpp.Name = "txtScreenBG2Bpp";
this.txtScreenBG2Bpp.ReadOnly = true;
this.txtScreenBG2Bpp.Size = new System.Drawing.Size(18, 17);
this.txtScreenBG2Bpp.TabIndex = 13;
this.txtScreenBG2Bpp.Text = "8";
//
// txtScreenBG3Bpp
//
this.txtScreenBG3Bpp.Location = new System.Drawing.Point(126, 28);
this.txtScreenBG3Bpp.Multiline = true;
this.txtScreenBG3Bpp.Name = "txtScreenBG3Bpp";
this.txtScreenBG3Bpp.ReadOnly = true;
this.txtScreenBG3Bpp.Size = new System.Drawing.Size(18, 17);
this.txtScreenBG3Bpp.TabIndex = 14;
this.txtScreenBG3Bpp.Text = "8";
//
// txtScreenBG4Bpp
//
this.txtScreenBG4Bpp.Location = new System.Drawing.Point(151, 28);
this.txtScreenBG4Bpp.Multiline = true;
this.txtScreenBG4Bpp.Name = "txtScreenBG4Bpp";
this.txtScreenBG4Bpp.ReadOnly = true;
this.txtScreenBG4Bpp.Size = new System.Drawing.Size(18, 17);
this.txtScreenBG4Bpp.TabIndex = 15;
this.txtScreenBG4Bpp.Text = "8";
//
// groupBox2
//
this.groupBox2.Controls.Add(this.txtScreenBG4Bpp);
this.groupBox2.Controls.Add(this.label1);
this.groupBox2.Controls.Add(this.txtScreenBG3Bpp);
this.groupBox2.Controls.Add(this.txtModeBits);
this.groupBox2.Controls.Add(this.txtScreenBG2Bpp);
this.groupBox2.Controls.Add(this.label8);
this.groupBox2.Controls.Add(this.label7);
this.groupBox2.Controls.Add(this.txtScreenBG1Bpp);
this.groupBox2.Controls.Add(this.label6);
this.groupBox2.Controls.Add(this.label4);
this.groupBox2.Controls.Add(this.label5);
this.groupBox2.Location = new System.Drawing.Point(12, 11);
this.groupBox2.Name = "groupBox2";
this.groupBox2.Size = new System.Drawing.Size(230, 80);
this.groupBox2.TabIndex = 16;
this.groupBox2.TabStop = false;
this.groupBox2.Text = "Screen";
//
// comboDisplayType
//
this.comboDisplayType.DropDownStyle = System.Windows.Forms.ComboBoxStyle.DropDownList;
this.comboDisplayType.FormattingEnabled = true;
this.comboDisplayType.Items.AddRange(new object[] {
"BG1",
"BG2",
"BG3",
"BG4",
"Tiles as 2bpp",
"Tiles as 4bpp",
"Tiles as 8bpp",
"Tiles as 2bpp (@0K)",
"Tiles as 2bpp (@16K)",
"Tiles as 2bpp (@24K)",
"Tiles as 2bpp (@40K)",
"Tiles as 4bpp (@0K)",
"Tiles as 4bpp (@32K)"});
this.comboDisplayType.Location = new System.Drawing.Point(472, 8);
this.comboDisplayType.Name = "comboDisplayType";
this.comboDisplayType.Size = new System.Drawing.Size(195, 21);
this.comboDisplayType.TabIndex = 18;
this.comboDisplayType.SelectedIndexChanged += new System.EventHandler(this.comboDisplayType_SelectedIndexChanged);
//
// radioButton1
//
this.radioButton1.AutoSize = true;
this.radioButton1.Enabled = false;
this.radioButton1.Location = new System.Drawing.Point(588, 103);
this.radioButton1.Name = "radioButton1";
this.radioButton1.Size = new System.Drawing.Size(46, 17);
this.radioButton1.TabIndex = 19;
this.radioButton1.TabStop = true;
this.radioButton1.Text = "BG1";
this.radioButton1.UseVisualStyleBackColor = true;
//
// radioButton2
//
this.radioButton2.AutoSize = true;
this.radioButton2.Enabled = false;
this.radioButton2.Location = new System.Drawing.Point(640, 103);
this.radioButton2.Name = "radioButton2";
this.radioButton2.Size = new System.Drawing.Size(46, 17);
this.radioButton2.TabIndex = 20;
this.radioButton2.TabStop = true;
this.radioButton2.Text = "BG2";
this.radioButton2.UseVisualStyleBackColor = true;
//
// radioButton3
//
this.radioButton3.AutoSize = true;
this.radioButton3.Enabled = false;
this.radioButton3.Location = new System.Drawing.Point(692, 103);
this.radioButton3.Name = "radioButton3";
this.radioButton3.Size = new System.Drawing.Size(46, 17);
this.radioButton3.TabIndex = 21;
this.radioButton3.TabStop = true;
this.radioButton3.Text = "BG3";
this.radioButton3.UseVisualStyleBackColor = true;
//
// radioButton4
//
this.radioButton4.AutoSize = true;
this.radioButton4.Enabled = false;
this.radioButton4.Location = new System.Drawing.Point(744, 103);
this.radioButton4.Name = "radioButton4";
this.radioButton4.Size = new System.Drawing.Size(46, 17);
this.radioButton4.TabIndex = 22;
this.radioButton4.TabStop = true;
this.radioButton4.Text = "BG4";
this.radioButton4.UseVisualStyleBackColor = true;
//
// radioButton5
//
this.radioButton5.AutoSize = true;
this.radioButton5.Enabled = false;
this.radioButton5.Location = new System.Drawing.Point(384, 102);
this.radioButton5.Name = "radioButton5";
this.radioButton5.Size = new System.Drawing.Size(49, 17);
this.radioButton5.TabIndex = 23;
this.radioButton5.TabStop = true;
this.radioButton5.Text = "2bpp";
this.radioButton5.UseVisualStyleBackColor = true;
//
// radioButton6
//
this.radioButton6.AutoSize = true;
this.radioButton6.Enabled = false;
this.radioButton6.Location = new System.Drawing.Point(384, 79);
this.radioButton6.Name = "radioButton6";
this.radioButton6.Size = new System.Drawing.Size(76, 17);
this.radioButton6.TabIndex = 24;
this.radioButton6.TabStop = true;
this.radioButton6.Text = "2bpp @0K";
this.radioButton6.UseVisualStyleBackColor = true;
//
// radioButton7
//
this.radioButton7.AutoSize = true;
this.radioButton7.Enabled = false;
this.radioButton7.Location = new System.Drawing.Point(384, 56);
this.radioButton7.Name = "radioButton7";
this.radioButton7.Size = new System.Drawing.Size(82, 17);
this.radioButton7.TabIndex = 25;
this.radioButton7.TabStop = true;
this.radioButton7.Text = "2bpp @16K";
this.radioButton7.UseVisualStyleBackColor = true;
//
// radioButton8
//
this.radioButton8.AutoSize = true;
this.radioButton8.Enabled = false;
this.radioButton8.Location = new System.Drawing.Point(384, 35);
this.radioButton8.Name = "radioButton8";
this.radioButton8.Size = new System.Drawing.Size(82, 17);
this.radioButton8.TabIndex = 26;
this.radioButton8.TabStop = true;
this.radioButton8.Text = "2bpp @24K";
this.radioButton8.UseVisualStyleBackColor = true;
//
// radioButton9
//
this.radioButton9.AutoSize = true;
this.radioButton9.Enabled = false;
this.radioButton9.Location = new System.Drawing.Point(384, 12);
this.radioButton9.Name = "radioButton9";
this.radioButton9.Size = new System.Drawing.Size(82, 17);
this.radioButton9.TabIndex = 27;
this.radioButton9.TabStop = true;
this.radioButton9.Text = "2bpp @32K";
this.radioButton9.UseVisualStyleBackColor = true;
//
// radioButton10
//
this.radioButton10.AutoSize = true;
this.radioButton10.Enabled = false;
this.radioButton10.Location = new System.Drawing.Point(465, 103);
this.radioButton10.Name = "radioButton10";
this.radioButton10.Size = new System.Drawing.Size(49, 17);
this.radioButton10.TabIndex = 28;
this.radioButton10.TabStop = true;
this.radioButton10.Text = "4bpp";
this.radioButton10.UseVisualStyleBackColor = true;
//
// radioButton11
//
this.radioButton11.AutoSize = true;
this.radioButton11.Enabled = false;
this.radioButton11.Location = new System.Drawing.Point(465, 56);
this.radioButton11.Name = "radioButton11";
this.radioButton11.Size = new System.Drawing.Size(82, 17);
this.radioButton11.TabIndex = 29;
this.radioButton11.TabStop = true;
this.radioButton11.Text = "4bpp @32K";
this.radioButton11.UseVisualStyleBackColor = true;
//
// radioButton12
//
this.radioButton12.AutoSize = true;
this.radioButton12.Enabled = false;
this.radioButton12.Location = new System.Drawing.Point(465, 79);
this.radioButton12.Name = "radioButton12";
this.radioButton12.Size = new System.Drawing.Size(76, 17);
this.radioButton12.TabIndex = 30;
this.radioButton12.TabStop = true;
this.radioButton12.Text = "4bpp @0K";
this.radioButton12.UseVisualStyleBackColor = true;
//
// radioButton13
//
this.radioButton13.AutoSize = true;
this.radioButton13.Enabled = false;
this.radioButton13.Location = new System.Drawing.Point(535, 103);
this.radioButton13.Name = "radioButton13";
this.radioButton13.Size = new System.Drawing.Size(49, 17);
this.radioButton13.TabIndex = 31;
this.radioButton13.TabStop = true;
this.radioButton13.Text = "8bpp";
this.radioButton13.UseVisualStyleBackColor = true;
//
// label14
//
this.label14.AutoSize = true;
this.label14.Location = new System.Drawing.Point(939, 158);
this.label14.Name = "label14";
this.label14.Size = new System.Drawing.Size(114, 13);
this.label14.TabIndex = 32;
this.label14.Text = "Palette goes over here";
//
// viewer
//
this.viewer.BackColor = System.Drawing.Color.Transparent;
this.viewer.Location = new System.Drawing.Point(384, 129);
this.viewer.Name = "viewer";
this.viewer.Size = new System.Drawing.Size(512, 512);
this.viewer.TabIndex = 17;
this.viewer.TabStop = false;
//
// SNESGraphicsDebugger
//
this.AutoScaleDimensions = new System.Drawing.SizeF(6F, 13F);
this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
this.ClientSize = new System.Drawing.Size(1215, 650);
this.Controls.Add(this.groupBox2);
this.Controls.Add(this.label14);
this.Controls.Add(this.radioButton13);
this.Controls.Add(this.radioButton12);
this.Controls.Add(this.radioButton11);
this.Controls.Add(this.radioButton10);
this.Controls.Add(this.radioButton9);
this.Controls.Add(this.radioButton8);
this.Controls.Add(this.radioButton7);
this.Controls.Add(this.radioButton6);
this.Controls.Add(this.radioButton5);
this.Controls.Add(this.radioButton4);
this.Controls.Add(this.radioButton3);
this.Controls.Add(this.radioButton2);
this.Controls.Add(this.radioButton1);
this.Controls.Add(this.comboDisplayType);
this.Controls.Add(this.viewer);
this.Controls.Add(this.groupBox1);
this.Name = "SNESGraphicsDebugger";
this.Text = "SNES Graphics Debugger";
this.groupBox1.ResumeLayout(false);
this.groupBox1.PerformLayout();
this.groupBox2.ResumeLayout(false);
this.groupBox2.PerformLayout();
this.ResumeLayout(false);
this.PerformLayout();
}
#endregion
private System.Windows.Forms.Label label1;
private System.Windows.Forms.GroupBox groupBox1;
private System.Windows.Forms.Label label2;
private System.Windows.Forms.TextBox txtBG1SizeBits;
private System.Windows.Forms.TextBox txtModeBits;
private System.Windows.Forms.TextBox txtBG1SizeInTiles;
private System.Windows.Forms.TextBox txtScreenBG1Bpp;
private System.Windows.Forms.Label label4;
private System.Windows.Forms.Label label5;
private System.Windows.Forms.Label label6;
private System.Windows.Forms.Label label7;
private System.Windows.Forms.Label label8;
private System.Windows.Forms.TextBox txtScreenBG2Bpp;
private System.Windows.Forms.TextBox txtScreenBG3Bpp;
private System.Windows.Forms.TextBox txtScreenBG4Bpp;
private System.Windows.Forms.GroupBox groupBox2;
private System.Windows.Forms.TextBox txtBG1SizeInPixels;
private System.Windows.Forms.Label label3;
private System.Windows.Forms.Label label9;
private System.Windows.Forms.Label label10;
private System.Windows.Forms.TextBox txtBG1SCAddrBits;
private System.Windows.Forms.TextBox txtBG1SCAddrDescr;
private System.Windows.Forms.TextBox txtBG1Bpp;
private System.Windows.Forms.Label label12;
private System.Windows.Forms.TextBox txtBG1TDAddrDescr;
private System.Windows.Forms.Label label11;
private System.Windows.Forms.TextBox txtBG1TDAddrBits;
private System.Windows.Forms.Label label13;
private System.Windows.Forms.TextBox txtBG1Colors;
private SNESGraphicsViewer viewer;
private System.Windows.Forms.ComboBox comboDisplayType;
private System.Windows.Forms.RadioButton radioButton1;
private System.Windows.Forms.RadioButton radioButton2;
private System.Windows.Forms.RadioButton radioButton3;
private System.Windows.Forms.RadioButton radioButton4;
private System.Windows.Forms.RadioButton radioButton5;
private System.Windows.Forms.RadioButton radioButton6;
private System.Windows.Forms.RadioButton radioButton7;
private System.Windows.Forms.RadioButton radioButton8;
private System.Windows.Forms.RadioButton radioButton9;
private System.Windows.Forms.RadioButton radioButton10;
private System.Windows.Forms.RadioButton radioButton11;
private System.Windows.Forms.RadioButton radioButton12;
private System.Windows.Forms.RadioButton radioButton13;
private System.Windows.Forms.Label label14;
}
}

View File

@ -0,0 +1,118 @@
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using BizHawk.Emulation.Consoles.Nintendo.SNES;
namespace BizHawk.MultiClient
{
public unsafe partial class SNESGraphicsDebugger : Form
{
SwappableDisplaySurfaceSet surfaceSet = new SwappableDisplaySurfaceSet();
public SNESGraphicsDebugger()
{
InitializeComponent();
comboDisplayType.SelectedIndex = 0;
}
string FormatBpp(int bpp)
{
if (bpp == 0) return "---";
else return bpp.ToString();
}
string FormatScreenSizeInTiles(SNESGraphicsDecoder.ScreenSize screensize)
{
var dims = SNESGraphicsDecoder.SizeInTilesForBGSize(screensize);
int size = dims.Width * dims.Height * 2 / 1024;
return string.Format("{0} ({1}K)", dims, size);
}
string FormatVramAddress(int address)
{
int excess = address & 1023;
if (excess != 0) return "@" + address.ToHexString(4);
else return string.Format("@{0} ({1}K)", address.ToHexString(4), address / 1024);
}
public void UpdateValues()
{
if (!this.IsHandleCreated || this.IsDisposed) return;
var snes = Global.Emulator as LibsnesCore;
if (snes == null) return;
var gd = new SNESGraphicsDecoder();
var si = gd.ScanScreenInfo();
txtModeBits.Text = si.Mode.MODE.ToString();
txtBG1Bpp.Text = txtScreenBG1Bpp.Text = FormatBpp(si.BG.BG1.Bpp);
txtScreenBG2Bpp.Text = FormatBpp(si.BG.BG2.Bpp);
txtScreenBG3Bpp.Text = FormatBpp(si.BG.BG3.Bpp);
txtScreenBG4Bpp.Text = FormatBpp(si.BG.BG4.Bpp);
txtBG1SizeBits.Text = si.BG.BG1.SCSIZE.ToString();
txtBG1SizeInTiles.Text = FormatScreenSizeInTiles(si.BG.BG1.ScreenSize);
txtBG1SCAddrBits.Text = si.BG.BG1.SCADDR.ToString();
txtBG1SCAddrDescr.Text = FormatVramAddress(si.BG.BG1.SCADDR << 9);
txtBG1Colors.Text = (1 << si.BG.BG1.Bpp).ToString();
txtBG1TDAddrBits.Text = si.BG.BG1.TDADDR.ToString();
txtBG1TDAddrDescr.Text = FormatVramAddress(si.BG.BG1.TDADDR << 13);
RenderView();
}
//todo - something smarter to cycle through bitmaps without repeatedly trashing them (use the dispose callback on the viewer)
void RenderView()
{
Bitmap bmp = null;
System.Drawing.Imaging.BitmapData bmpdata = null;
int* pixelptr = null;
int stride = 0;
Action<int,int> allocate = (w, h) =>
{
bmp = new Bitmap(w, h);
bmpdata = bmp.LockBits(new Rectangle(0, 0, w, h), System.Drawing.Imaging.ImageLockMode.WriteOnly, System.Drawing.Imaging.PixelFormat.Format32bppArgb);
pixelptr = (int*)bmpdata.Scan0.ToPointer();
stride = bmpdata.Stride;
};
var gd = new SNESGraphicsDecoder();
string selection = comboDisplayType.SelectedItem as string;
if (selection == "Tiles as 2bpp")
{
allocate(512, 512);
gd.DecodeTiles2bpp(pixelptr, stride / 4, 0);
}
if (selection == "Tiles as 4bpp")
{
allocate(512, 512);
gd.DecodeTiles4bpp(pixelptr, stride / 4, 0);
}
if (selection == "Tiles as 8bpp")
{
allocate(256, 256);
gd.DecodeTiles8bpp(pixelptr, stride / 4, 0);
}
if (bmp != null)
{
bmp.UnlockBits(bmpdata);
viewer.SetBitmap(bmp);
}
}
private void comboDisplayType_SelectedIndexChanged(object sender, EventArgs e)
{
UpdateValues();
}
}
}

View File

@ -0,0 +1,120 @@
<?xml version="1.0" encoding="utf-8"?>
<root>
<!--
Microsoft ResX Schema
Version 2.0
The primary goals of this format is to allow a simple XML format
that is mostly human readable. The generation and parsing of the
various data types are done through the TypeConverter classes
associated with the data types.
Example:
... ado.net/XML headers & schema ...
<resheader name="resmimetype">text/microsoft-resx</resheader>
<resheader name="version">2.0</resheader>
<resheader name="reader">System.Resources.ResXResourceReader, System.Windows.Forms, ...</resheader>
<resheader name="writer">System.Resources.ResXResourceWriter, System.Windows.Forms, ...</resheader>
<data name="Name1"><value>this is my long string</value><comment>this is a comment</comment></data>
<data name="Color1" type="System.Drawing.Color, System.Drawing">Blue</data>
<data name="Bitmap1" mimetype="application/x-microsoft.net.object.binary.base64">
<value>[base64 mime encoded serialized .NET Framework object]</value>
</data>
<data name="Icon1" type="System.Drawing.Icon, System.Drawing" mimetype="application/x-microsoft.net.object.bytearray.base64">
<value>[base64 mime encoded string representing a byte array form of the .NET Framework object]</value>
<comment>This is a comment</comment>
</data>
There are any number of "resheader" rows that contain simple
name/value pairs.
Each data row contains a name, and value. The row also contains a
type or mimetype. Type corresponds to a .NET class that support
text/value conversion through the TypeConverter architecture.
Classes that don't support this are serialized and stored with the
mimetype set.
The mimetype is used for serialized objects, and tells the
ResXResourceReader how to depersist the object. This is currently not
extensible. For a given mimetype the value must be set accordingly:
Note - application/x-microsoft.net.object.binary.base64 is the format
that the ResXResourceWriter will generate, however the reader can
read any of the formats listed below.
mimetype: application/x-microsoft.net.object.binary.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Binary.BinaryFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.soap.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Soap.SoapFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.bytearray.base64
value : The object must be serialized into a byte array
: using a System.ComponentModel.TypeConverter
: and then encoded with base64 encoding.
-->
<xsd:schema id="root" xmlns="" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:msdata="urn:schemas-microsoft-com:xml-msdata">
<xsd:import namespace="http://www.w3.org/XML/1998/namespace" />
<xsd:element name="root" msdata:IsDataSet="true">
<xsd:complexType>
<xsd:choice maxOccurs="unbounded">
<xsd:element name="metadata">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" />
</xsd:sequence>
<xsd:attribute name="name" use="required" type="xsd:string" />
<xsd:attribute name="type" type="xsd:string" />
<xsd:attribute name="mimetype" type="xsd:string" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="assembly">
<xsd:complexType>
<xsd:attribute name="alias" type="xsd:string" />
<xsd:attribute name="name" type="xsd:string" />
</xsd:complexType>
</xsd:element>
<xsd:element name="data">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
<xsd:element name="comment" type="xsd:string" minOccurs="0" msdata:Ordinal="2" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" msdata:Ordinal="1" />
<xsd:attribute name="type" type="xsd:string" msdata:Ordinal="3" />
<xsd:attribute name="mimetype" type="xsd:string" msdata:Ordinal="4" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="resheader">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" />
</xsd:complexType>
</xsd:element>
</xsd:choice>
</xsd:complexType>
</xsd:element>
</xsd:schema>
<resheader name="resmimetype">
<value>text/microsoft-resx</value>
</resheader>
<resheader name="version">
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
</root>

View File

@ -0,0 +1,37 @@
using System;
using System.Drawing;
using System.Windows.Forms;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Globalization;
using System.IO;
using System.Drawing.Imaging;
using BizHawk.Core;
namespace BizHawk.MultiClient
{
public class SNESGraphicsViewer : RetainedViewportPanel
{
public SNESGraphicsViewer()
{
SetStyle(ControlStyles.SupportsTransparentBackColor, true);
this.BackColor = Color.Transparent;
}
protected override void OnPaint(PaintEventArgs e)
{
Display(e.Graphics);
base.OnPaint(e);
}
void Display(Graphics g)
{
g.InterpolationMode = System.Drawing.Drawing2D.InterpolationMode.NearestNeighbor;
g.PixelOffsetMode = System.Drawing.Drawing2D.PixelOffsetMode.Half;
}
//todo - screenshot?
}
}

Binary file not shown.

View File

@ -40,6 +40,8 @@ namespace BizHawk.Core
SetStyle(ControlStyles.DoubleBuffer, false);
SetStyle(ControlStyles.Opaque, true);
SetStyle(ControlStyles.UserMouse, true);
SetBitmap(new Bitmap(2, 2));
}

View File

@ -229,6 +229,41 @@ bool snes_check_cartridge(const uint8_t *rom_data, unsigned rom_size)
return temp.type != SnesCartridge::TypeUnknown && temp.type != SnesCartridge::TypeGameBoy;
}
//zero 05-sep-2012
int snes_peek_logical_register(int reg)
{
switch(reg)
{
//$2105
case SNES_REG_BG_MODE: return SNES::ppu.regs.bg_mode;
case SNES_REG_BG3_PRIORITY: return SNES::ppu.regs.bg3_priority;
case SNES_REG_BG1_TILESIZE: return SNES::ppu.regs.bg_tilesize[SNES::PPU::BG1];
case SNES_REG_BG2_TILESIZE: return SNES::ppu.regs.bg_tilesize[SNES::PPU::BG2];
case SNES_REG_BG3_TILESIZE: return SNES::ppu.regs.bg_tilesize[SNES::PPU::BG3];
case SNES_REG_BG4_TILESIZE: return SNES::ppu.regs.bg_tilesize[SNES::PPU::BG4];
//$2107
case SNES_REG_BG1_SCADDR: return SNES::ppu.regs.bg_scaddr[SNES::PPU::BG1]>>9;
case SNES_REG_BG1_SCSIZE: return SNES::ppu.regs.bg_scsize[SNES::PPU::BG1];
//$2108
case SNES_REG_BG2_SCADDR: return SNES::ppu.regs.bg_scaddr[SNES::PPU::BG2]>>9;
case SNES_REG_BG2_SCSIZE: return SNES::ppu.regs.bg_scsize[SNES::PPU::BG2];
//$2109
case SNES_REG_BG3_SCADDR: return SNES::ppu.regs.bg_scaddr[SNES::PPU::BG3]>>9;
case SNES_REG_BG3_SCSIZE: return SNES::ppu.regs.bg_scsize[SNES::PPU::BG3];
//$210A
case SNES_REG_BG4_SCADDR: return SNES::ppu.regs.bg_scaddr[SNES::PPU::BG4]>>9;
case SNES_REG_BG4_SCSIZE: return SNES::ppu.regs.bg_scsize[SNES::PPU::BG4];
//$210B
case SNES_REG_BG1_TDADDR: return SNES::ppu.regs.bg_tdaddr[SNES::PPU::BG1]>>13;
case SNES_REG_BG2_TDADDR: return SNES::ppu.regs.bg_tdaddr[SNES::PPU::BG2]>>13;
//$210C
case SNES_REG_BG3_TDADDR: return SNES::ppu.regs.bg_tdaddr[SNES::PPU::BG3]>>13;
case SNES_REG_BG4_TDADDR: return SNES::ppu.regs.bg_tdaddr[SNES::PPU::BG4]>>13;
}
return 0;
}
bool snes_load_cartridge_normal(
const char *rom_xml, const uint8_t *rom_data, unsigned rom_size
) {
@ -413,3 +448,4 @@ unsigned snes_get_memory_size(unsigned id) {
if(size == -1U) size = 0;
return size;
}

View File

@ -132,6 +132,34 @@ unsigned snes_get_memory_size(unsigned id);
bool snes_check_cartridge(const uint8_t *rom_data, unsigned rom_size);
void snes_set_layer_enable(int layer, int priority, bool enable);
//$2105
#define SNES_REG_BG_MODE 0
#define SNES_REG_BG3_PRIORITY 1
#define SNES_REG_BG1_TILESIZE 2
#define SNES_REG_BG2_TILESIZE 3
#define SNES_REG_BG3_TILESIZE 4
#define SNES_REG_BG4_TILESIZE 5
//$2107
#define SNES_REG_BG1_SCADDR 10
#define SNES_REG_BG1_SCSIZE 11
//$2108
#define SNES_REG_BG2_SCADDR 12
#define SNES_REG_BG2_SCSIZE 13
//$2109
#define SNES_REG_BG3_SCADDR 14
#define SNES_REG_BG3_SCSIZE 15
//$210A
#define SNES_REG_BG4_SCADDR 16
#define SNES_REG_BG4_SCSIZE 17
//$210B
#define SNES_REG_BG1_TDADDR 20
#define SNES_REG_BG2_TDADDR 21
//$210C
#define SNES_REG_BG3_TDADDR 22
#define SNES_REG_BG4_TDADDR 23
int snes_peek_logical_register(int reg);
#ifdef __cplusplus
}
#endif