diff --git a/BizHawk.Client.Common/IPS.cs b/BizHawk.Client.Common/IPS.cs index 621ebe6a40..ccc9122b4f 100644 --- a/BizHawk.Client.Common/IPS.cs +++ b/BizHawk.Client.Common/IPS.cs @@ -5,7 +5,7 @@ namespace BizHawk.Client.Common { public static class IPS { - public static void Patch(byte[] rom, Stream patch) + public static byte[] Patch(byte[] rom, Stream patch) { var ipsHeader = new byte[5]; patch.Read(ipsHeader, 0, 5); @@ -16,32 +16,40 @@ namespace BizHawk.Client.Common if (ipsHeader[i] != header[i]) { Console.WriteLine("Patch file specified is invalid."); - return; + return null; } } // header verified, loop over patch entries uint EOF = ('E' * 0x10000 + 'O' * 0x100 + 'F'); + var ret = new MemoryStream(rom.Length); + ret.Write(rom, 0, rom.Length); + while (true) { uint offset = Read24(patch); - if (offset == EOF) return; + if (offset == EOF) + return ret.ToArray(); ushort size = Read16(patch); + ret.Seek(offset, SeekOrigin.Begin); + if (size != 0) // non-RLE patch { var patchData = new byte[size]; patch.Read(patchData, 0, size); - for (int i = 0; i < size; i++) - rom[offset++] = patchData[i]; + + ret.Write(patchData, 0, patchData.Length); } else // RLE patch { size = Read16(patch); byte value = (byte)patch.ReadByte(); for (int i = 0; i < size; i++) - rom[offset++] = value; + { + ret.WriteByte(value); + } } } } diff --git a/BizHawk.Client.Common/RomGame.cs b/BizHawk.Client.Common/RomGame.cs index 8c526cb2fd..8e4cbdcc1f 100644 --- a/BizHawk.Client.Common/RomGame.cs +++ b/BizHawk.Client.Common/RomGame.cs @@ -90,7 +90,7 @@ namespace BizHawk.Client.Common patchFile.BindFirstOf("IPS"); if (patchFile.IsBound) { - IPS.Patch(RomData, patchFile.GetStream()); + RomData = IPS.Patch(RomData, patchFile.GetStream()); } } }