From 73a685f5a17852b6990c0810d0f1f0984c2c358f Mon Sep 17 00:00:00 2001 From: Ian C Date: Sat, 28 Oct 2006 23:28:31 +0000 Subject: Updates from work away --- source/zx81.c | 124 ++++++++++++++++++++++++++++++++++++++++++++++++++++++---- 1 file changed, 116 insertions(+), 8 deletions(-) (limited to 'source/zx81.c') diff --git a/source/zx81.c b/source/zx81.c index 0b7e729..6173701 100644 --- a/source/zx81.c +++ b/source/zx81.c @@ -19,7 +19,7 @@ ------------------------------------------------------------------------- - Provides the emulation for the ZX81 + Provides the emulation for the zX81 */ #include @@ -29,6 +29,7 @@ #include #include "zx81.h" +#include "gui.h" #include "zx81_bin.h" @@ -40,6 +41,8 @@ #define FALSE 0 #endif +#define MAX_FNAME_LEN 30 + /* ---------------------------------------- STATICS */ @@ -86,6 +89,7 @@ static Z80Word RAMLEN=0; /* Tape */ +static int enable_filesystem; static const Z80Byte *tape_image; static int tape_len; @@ -244,17 +248,85 @@ static Z80Byte FromASCII(char c) } -static void LoadTape(Z80 *z80) +/* Open a tape file the passed address +*/ +static FILE *OpenTapeFile(Z80Word addr) { - if (tape_image) + FILE *fp; + char fn[MAX_FNAME_LEN]; + int f; + int done; + + f=0; + done=FALSE; + + while(f<(MAX_FNAME_LEN-3) && !done) + { + int ch; + + ch=mem[addr++]; + + if (ch&0x80) + { + done=TRUE; + ch&=0x7f; + } + + switch(ch) + { + case 22: + fn[f++]='-'; + break; + + case 27: + fn[f++]='.'; + + default: + if (ch>=28 && ch<=37) + { + fn[f++]='0'+(ch-28); + } + else if (ch>=38 && ch<=63) + { + fn[f++]='A'+(ch-38); + } + break; + } + } + + fn[f++]='.'; + fn[f++]='P'; + fn[f]=0; + + if (!(fp=fopen(fn,"rb"))) { - memcpy(mem+0x4009,tape_image,tape_len); + char full_fn[MAX_FNAME_LEN+11]="\\ZX81SNAP\\"; + + strcat(full_fn,fn); + fp=fopen(full_fn,"rb"); } + + return fp; } -static void SaveTape(Z80 *z80) +static void LoadInternalTape(Z80 *z80) { + memcpy(mem+0x4009,tape_image,tape_len); +} + + +static void LoadExternalTape(FILE *tape, Z80 *z80) +{ + int c; + Z80Byte *a; + + a=mem+0x4009; + + while((c=getc(tape))!=EOF) + { + *a++=c; + } } @@ -371,7 +443,6 @@ static void ZX81HouseKeeping(Z80 *z80) } } - /* if ((lastk1 || lastk2) && (lastk1!=prev_lk1 || lastk2!=prev_lk2)) */ if (lastk1 && (lastk1!=prev_lk1 || lastk2!=prev_lk2)) { mem[CDFLAG]|=1; @@ -429,11 +500,42 @@ static int EDCallback(Z80 *z80, Z80Val data) switch((Z80Byte)data) { case ED_SAVE: - SaveTape(z80); break; case ED_LOAD: - LoadTape(z80); + /* Try and load the external file if a name given. Otherwise, we + try the internal one. Some of this is slightly dodgy -- it was + never intended for the emulator to be doing any GUI related + nonsense (like the alerts) but simply emulating. + */ + if (enable_filesystem && z80->DE.w<0x8000) + { + FILE *fp; + + if ((fp=OpenTapeFile(z80->DE.w))) + { + LoadExternalTape(fp,z80); + fclose(fp); + } + else + { + GUI_Alert(FALSE,"Couldn't open tape"); + SK_DisplayKeyboard(BG_GFX_SUB); + } + } + else + { + if (tape_image) + { + LoadInternalTape(z80); + } + else + { + GUI_Alert(FALSE,"No tape image selected"); + SK_DisplayKeyboard(BG_GFX_SUB); + } + } + mem[CDFLAG]=0xc0; break; @@ -629,6 +731,12 @@ void ZX81Reset(Z80 *z80) } +void ZX81EnableFileSystem(int enable) +{ + enable_filesystem=enable; +} + + void ZX81SetTape(const Z80Byte *image, int len) { tape_image=image; -- cgit v1.2.3