Updated IPS code. Now supports RLE, should fix problems if the ROM is expanded, and automatically view the ROM with a header.

This commit is contained in:
n-a-c-h
2003-08-18 20:13:58 +00:00
parent c324ad0ee7
commit 1cca98563b
6 changed files with 142 additions and 170 deletions

View File

@@ -57,7 +57,7 @@ WINDOSOBJ=${DOSDIR}/debug.o ${DOSDIR}/joy.o ${DOSDIR}/modemrtn.o ${DOSDIR}/vesa2
ZIPOBJ=${ZIPDIR}/zzip.o ${ZIPDIR}/unzip.o ${ZIPDIR}/zpng.o
MAINOBJ=cfgload.o endmem.o fixsin.o init.o initc.o ui.o vcache.o water.o smoke.o burn.o version.o
MAINOBJ=cfgload.o endmem.o fixsin.o init.o initc.o patch.o ui.o vcache.o water.o smoke.o burn.o version.o
OBJS=${CHIPSOBJ} ${CPUOBJ} ${WINOBJ} ${WINDOSOBJ} ${GUIOBJ} ${VIDEOBJ} ${ZIPOBJ} ${MAINOBJ}
@@ -96,6 +96,7 @@ ui.o: ui.asm macros.mac
cfgload.o:cfgload.asm macros.mac
init.o:init.asm macros.mac
initc.o:initc.c
patch.o:patch.c
ALL:
rm -f version.o
@@ -192,3 +193,4 @@ distclean:
rm -f ${CHIPDIR}/*.o ${CPUDIR}/*.o ${VIDEODIR}/*.o ${GUIDIR}/*.o ${DOSDIR}/*.o ${WINDIR}/*.o ${ZIPDIR}/*.o *.o @ZSNESEXE@ Makefile config.cache config.log config.status config.h

View File

@@ -95,7 +95,7 @@ EXTSYM GUIfindUSA,GUIfindEUR,GUIfindJAP,GUIfindZIP,GUIfind1,DTALoc,GUIfindall
EXTSYM spc7110romptr,allocspc7110
EXTSYM SRAMDir,SRAMDrive,cfgloadsdir,fnamest,statefileloc
EXTSYM ForcePal,ForceROMTiming,ForceHiLoROM,InitDir,InitDrive,enterpress,frameskip
EXTSYM maxromspace,curromspace,infoloc
EXTSYM maxromspace,curromspace,infoloc, patchfile
EXTSYM gotoroot,headdata,printnum,romispal
EXTSYM InitFxTables,SFXSRAM,SfxR1,SfxR2,SfxSCMR,SfxSFR,finterleave
EXTSYM initregr,initregw,memtabler16,DSP1Read16b3F,memaccessbankr16
@@ -3642,63 +3642,12 @@ NEWSYM printhex8
;*******************************************************
; Search for header size first which is filesize MOD 32768
NEWSYM RetrieveDataIPS
xor ah,ah
cmp ecx,10000
jne .notoverflow
push edx
push ecx
mov edx,wramdataa
mov ecx,10000
call Read_File
cmp eax,0
jne .notempty
mov ah,1
jmp .empty
.notempty
xor ah,ah
.empty
pop ecx
pop edx
xor ecx,ecx
.notoverflow
mov al,[wramdataa+ecx]
inc ecx
ret
SECTION .bss
IPSSL resd 1
SECTION .text
NEWSYM PatchIPS
%ifdef __LINUX__
pushad
call pushdir
popad
%endif
mov byte[IPSPatched],0
mov dword[IPSOffset],0
cmp byte[Header512],0
je .no512head
mov dword[IPSOffset],512
.no512head
mov dword[IPSLimit],4096*1024
cmp byte[Sup48mbit],0
je .not48
mov dword[IPSLimit],6144*1024
.not48
cmp byte[Sup16mbit],0
je .not16
mov dword[IPSLimit],2048*1024
.not16
; 1965-1970, >1969*1024+712 (812/850/1000)
; upper bound: 1969*1024+1024
; between 1965-<1970 / 1968,1970
; mov dword[IPSLimit],208062h
; mov dword[IPSSL],208832h
; font = 208062h-208832h
mov eax,fname+1
; search for . or 0
.next
@@ -3737,113 +3686,14 @@ NEWSYM PatchIPS
.nochangedir:
%endif
mov edx,fname+1
call Open_File
jc near .failed
mov bx,ax
mov edx,Headchek
mov ecx,5
call Read_File
cmp dword[Headchek],'PATC'
jne near .ipsfaileddet
cmp byte[Headchek+4],'H'
jne near .ipsfaileddet
mov ecx,10000
.ipxloop
.findnext
xor edx,edx
call RetrieveDataIPS
cmp ah,0
jne near .ipsfailed
mov dh,al
shl edx,8
call RetrieveDataIPS
cmp ah,0
jne near .ipsfailed
mov dh,al
call RetrieveDataIPS
cmp ah,0
jne near .ipsfailed
mov dl,al
cmp edx,454F46h
je near .ipsokay
call RetrieveDataIPS
cmp ah,0
jne near .ipsfailed
sub edx,[IPSOffset]
mov [IPSCount+1],al
call RetrieveDataIPS
cmp ah,0
jne near .ipsfailed
mov [IPSCount],al
cmp word[IPSCount],0
je .ipsclear
.loop
call RetrieveDataIPS
cmp ah,0
jne near .ipsfailed
; cmp edx,[IPSSL]
; jae .nolimit
cmp edx,[IPSLimit]
jae .limit
.nolimit
mov esi,[romdata]
mov [esi+edx],al
.limit
inc edx
dec word[IPSCount]
jnz .loop
jmp .findnext
.ipsclear
call RetrieveDataIPS
cmp ah,0
jne near .ipsfailed
mov [IPSCount+1],al
call RetrieveDataIPS
cmp ah,0
jne near .ipsfailed
mov [IPSCount],al
call RetrieveDataIPS
cmp ah,0
jne near .ipsfailed
cmp word[IPSCount],0
je near .findnext
mov esi,[romdata]
.loop2
cmp edx,[IPSLimit]
jae .limit2
mov [esi+edx],al
.limit2
inc edx
dec word[IPSCount]
jnz .loop2
jmp .findnext
.ipsokay
mov dword[Msgptr],.ipsokaymsg
mov dword[MessageOn],60*4
mov byte[IPSPatched],1
jmp .ipsfaileddet
.ipsfailed
mov dword[Msgptr],.ipsnokaymsg
mov dword[MessageOn],60*4
mov byte[IPSPatched],1
.ipsfaileddet
call Close_File
.failed
mov [patchfile],edx
EXTSYM PatchUsingIPS
pushad
call PatchUsingIPS
popad
pop eax
mov ebx,[Prevextn]
mov [eax],ebx
; font = 208062h-208832h
; mov esi,[romdata]
; mov [esi+208062h],0
;0-768, 3072-3072+256, 4096-4096+256
; mov edx,2079*1024 ;+2048+2048*40
; mov ecx,2048
; mov esi,[romdata]
;.ltop
; mov byte[esi+edx],0
; inc edx
; dec ecx
; jnz .ltop
%ifdef __LINUX__
pushad
call popdir
@@ -3851,18 +3701,10 @@ NEWSYM PatchIPS
%endif
ret
SECTION .data
.ipsokaymsg db 'IPS PATCHED.',0
.ipsnokaymsg db 'IPS IS CORRUPT.',0
SECTION .bss
NEWSYM Header512, resb 1
NEWSYM Prevextn, resd 1
NEWSYM Headchek, resb 5
NEWSYM IPSLimit, resd 1
NEWSYM IPSOffset, resd 1
NEWSYM IPSCount, resd 1
IPSPatched resb 1
NEWSYM IPSPatched, resb 1
SECTION .text
OpenCombFile:
@@ -6367,3 +6209,4 @@ SECTION .text
NEWSYM InitAsmEnd

View File

@@ -1,2 +1,3 @@
/Fezsnesw.exe chips\dsp1proc.obj dos\sw.obj dos\gppro.obj dos\vesa12.obj dos\zsipx.obj dos\modemrtn.obj dos\joy.obj dos\debug.obj dos\vesa2.obj dos\initvid.obj cfgload.obj endmem.obj fixsin.obj init.obj initc.obj ui.obj vcache.obj water.obj smoke.obj burn.obj version.obj video\procvid.obj win\copyvwin.obj win\winintrf.obj win\winlink.obj win\zloaderw.obj win\ztcp.obj win\zfilew.obj win\zipxw.obj video\makev16b.obj video\makev16t.obj video\makevid.obj video\mode716.obj video\mode716b.obj video\mode716d.obj video\mode716e.obj video\mode716t.obj video\mode7.obj video\mode7ext.obj video\mv16tms.obj video\newg162.obj video\newgfx16.obj video\newgfx2.obj video\newgfx.obj video\m716text.obj video\2xsaiw.obj video\sw_draw.obj video/hq3x16.obj video/hq3x32.obj gui\gui.obj gui\menu.obj cpu\addrni.obj cpu\dma.obj cpu\dsp.obj cpu\dspproc.obj cpu\execute.obj cpu\irq.obj cpu\memory.obj cpu\spc700.obj cpu\stable.obj cpu\table.obj cpu\tableb.obj cpu\tablec.obj chips\dsp1emu.obj chips\fxemu2.obj chips\fxemu2b.obj chips\fxemu2c.obj chips\fxtable.obj chips\sa1proc.obj chips\sa1regs.obj chips\sfxproc.obj zip\unzip.obj zip\zzip.obj zip\zpng.obj zlib.lib libpng.lib wsock32.lib user32.lib gdi32.lib shell32.lib winmm.lib ddraw.lib dsound.lib dinput8.lib d3dx.lib /link /section:.text,erw
/Fezsnesw.exe chips\dsp1proc.obj dos\sw.obj dos\gppro.obj dos\vesa12.obj dos\zsipx.obj dos\modemrtn.obj dos\joy.obj dos\debug.obj dos\vesa2.obj dos\initvid.obj cfgload.obj endmem.obj fixsin.obj init.obj initc.obj patch.obj ui.obj vcache.obj water.obj smoke.obj burn.obj version.obj video\procvid.obj win\copyvwin.obj win\winintrf.obj win\winlink.obj win\zloaderw.obj win\ztcp.obj win\zfilew.obj win\zipxw.obj video\makev16b.obj video\makev16t.obj video\makevid.obj video\mode716.obj video\mode716b.obj video\mode716d.obj video\mode716e.obj video\mode716t.obj video\mode7.obj video\mode7ext.obj video\mv16tms.obj video\newg162.obj video\newgfx16.obj video\newgfx2.obj video\newgfx.obj video\m716text.obj video\2xsaiw.obj video\sw_draw.obj video/hq3x16.obj video/hq3x32.obj gui\gui.obj gui\menu.obj cpu\addrni.obj cpu\dma.obj cpu\dsp.obj cpu\dspproc.obj cpu\execute.obj cpu\irq.obj cpu\memory.obj cpu\spc700.obj cpu\stable.obj cpu\table.obj cpu\tableb.obj cpu\tablec.obj chips\dsp1emu.obj chips\fxemu2.obj chips\fxemu2b.obj chips\fxemu2c.obj chips\fxtable.obj chips\sa1proc.obj chips\sa1regs.obj chips\sfxproc.obj zip\unzip.obj zip\zzip.obj zip\zpng.obj zlib.lib libpng.lib wsock32.lib user32.lib gdi32.lib shell32.lib winmm.lib ddraw.lib dsound.lib dinput8.lib d3dx.lib /link /section:.text,erw

View File

@@ -55,7 +55,7 @@ PREOBJ=${OBJDIR}/dosbuff.o ${OBJDIR}/ipx.o ${OBJDIR}/zipx.o
ZIPOBJ=${ZIPDIR}/zzip.o ${ZIPDIR}/unzip.o ${ZIPDIR}/zpng.o
MAINOBJ=cfgload.o endmem.o fixsin.o init.o initc.o ui.o vcache.o water.o smoke.o burn.o version.o
MAINOBJ=cfgload.o endmem.o fixsin.o init.o initc.o patch.o ui.o vcache.o water.o smoke.o burn.o version.o
OBJS=${CHIPSOBJ} ${CPUOBJ} ${DOSOBJ} ${GUIOBJ} ${VIDEOBJ} ${PREOBJ} ${MAINOBJ} ${ZIPOBJ}
@@ -110,6 +110,7 @@ ui.o: ui.asm macros.mac
cfgload.o:cfgload.asm macros.mac
init.o:init.asm macros.mac
initc.o:initc.c
patch.o:patch.c
ALL:
del version.o
@@ -203,3 +204,4 @@ clean:
del zsnes.exe

View File

@@ -64,7 +64,7 @@ PREOBJ=
ZIPOBJ=${ZIPDIR}/zzip.obj ${ZIPDIR}/unzip.obj ${ZIPDIR}/zpng.obj
MAINOBJ=cfgload.obj endmem.obj fixsin.obj init.obj initc.obj ui.obj vcache.obj water.obj smoke.obj burn.obj version.obj
MAINOBJ=cfgload.obj endmem.obj fixsin.obj init.obj initc.obj patch.obj ui.obj vcache.obj water.obj smoke.obj burn.obj version.obj
OBJS=${CHIPSOBJ} ${CPUOBJ} ${WINOBJ} ${GUIOBJ} ${VIDEOBJ} ${ZIPOBJ} ${MAINOBJ} ${WINDOSOBJ}
LIBS=
@@ -131,7 +131,7 @@ ui.obj: ui.asm macros.mac
cfgload.obj:cfgload.asm macros.mac
init.obj:init.asm macros.mac
initc.obj:initc.c
patch.obj:patch.c
ALL:
del version.obj
version.obj:version.c
@@ -229,3 +229,4 @@ clean:

123
zsnes/src/patch.c Normal file
View File

@@ -0,0 +1,123 @@
/*
Copyright (C) 2003 ZSNES Team ( zsknight@zsnes.com / _demo_@zsnes.com )
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 of the License, 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 this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <stdio.h>
extern int maxromspace;
extern int curromspace;
extern int NumofBytes;
extern int NumofBanks;
extern unsigned int *romdata;
extern unsigned char IPSPatched;
char *patchfile;
void PatchUsingIPS()
{
unsigned char *ROM = (unsigned char *)romdata;
int location = 0, length = 0;
IPSPatched = 0;
FILE *fp = 0;
fp = fopen(patchfile, "rb");
if (!fp) { return; }
//Yup, it's goto! :)
//See 'IPSDone:' for explanation
if (fgetc(fp) != 'P') { goto IPSDone; }
if (fgetc(fp) != 'A') { goto IPSDone; }
if (fgetc(fp) != 'T') { goto IPSDone; }
if (fgetc(fp) != 'C') { goto IPSDone; }
if (fgetc(fp) != 'H') { goto IPSDone; }
while (!feof(fp))
{
//Location is a 3 byte value (max 16MB)
int inloc = (fgetc(fp) << 16) | (fgetc(fp) << 8) | fgetc(fp);
if (inloc == 0x454f46) //EOF
{
break;
}
//We assume all IPS files are for ROMs with headers
location = inloc - 512;
//Length is a 2 byte value (max 64KB)
length = (fgetc(fp) << 8) | fgetc(fp);
if (length) // Not RLE
{
int i;
for (i = 0; i < length; i++, location++)
{
if (location >= 0)
{
if (location >= maxromspace) { goto IPSDone; }
ROM[location] = (unsigned char)fgetc(fp);
}
else
{
fgetc(fp); //Need to skip the bytes that write to header
}
}
}
else //RLE
{
int i;
unsigned char newVal;
length = (fgetc(fp) << 8) | fgetc(fp);
newVal = (unsigned char)fgetc(fp);
for (i = 0; i < length; i++, location++)
{
if (location >= 0)
{
if (location >= maxromspace) { goto IPSDone; }
ROM[location] = newVal;
}
}
}
}
//We use gotos to break out of the nested loops,
//as well as a simple way to check for 'PATCH' in
//some cases like this one, goto is the way to go.
IPSDone:
fclose(fp);
IPSPatched = 1;
//Adjust size values if the ROM was expanded
if (location > curromspace && location <= maxromspace)
{
curromspace = location;
NumofBytes = location;
NumofBanks = NumofBytes/32768;
}
/*
//Write out patched ROM
fp = fopen("zsnes.rom", "wb");
if (!fp) { asm volatile("int $3"); }
fwrite(ROM, 1, curromspace, fp);
fclose(fp);
*/
}