Massive disk refactoring sourced from AppleWin

- Attempts to be byte-stream compatible with how AppleWin handles DOS-order, ProDOS-order, and NIB images
    - Adds support for ProDOS-order images
    - First cut at VBL support: (//e FlappyBird boots now!)
This commit is contained in:
Aaron Culliney 2014-12-28 13:07:13 -08:00
parent d339ec1e23
commit e01e437842
9 changed files with 804 additions and 704 deletions

1394
src/disk.c

File diff suppressed because it is too large Load Diff

View File

@ -19,51 +19,53 @@
#include "common.h"
struct diskette {
#define DSK_SIZE 143360
#define NIB_SIZE 232960
#define NI2_SIZE 223440
#define NUM_TRACKS 35
#define NUM_SECTORS 16
#define DSK_TRACK_SIZE 0x1000 // DOS order, ProDOS order
#define NIB_TRACK_SIZE 0x1A00 // NIB format
#define NI2_TRACK_SIZE 0x18F0 // NI2 format
#define PHASE_BYTES (NIB_TRACK_SIZE/2)
#define NIB_SEC_SIZE (NIB_TRACK_SIZE/NUM_SECTORS)
#define DSK_VOLUME 254
typedef struct diskette_t {
uint8_t track_image[NIB_TRACK_SIZE];
char file_name[1024];
bool compressed;
bool nibblized;
bool is_protected;
bool phase_change;
bool track_valid;
bool track_dirty;
int *skew_table;
int sector;
long file_size;
long nib_count;
int phase;
int run_byte;
FILE *fp;
int file_pos;
};
} diskette_t;
struct drive {
typedef struct drive_t {
int motor;
int drive;
int ddrw;
int disk_byte;
int volume;
int checksum;
int exor_value;
unsigned char disk_data[258];
struct diskette disk[2];
};
diskette_t disk[2];
} drive_t;
extern struct drive disk6;
extern drive_t disk6;
void c_init_6(void);
const char *c_new_diskette_6(int drive, const char * const file_name, int force);
const char *c_eject_6(int drive);
void disk_io_initialize(unsigned int slot);
void disk_read_nop(void),
disk_read_phase(void),
disk_read_motor_off(void),
disk_read_motor_on(void),
disk_read_select_a(void),
disk_read_select_b(void),
disk_read_byte(void),
disk_read_latch(void),
disk_write_latch(void),
disk_read_prepare_in(void),
disk_read_prepare_out(void);
#if DISK_TRACING
void c_toggle_disk_trace_6(const char *read_file, const char *write_file);
void c_begin_disk_trace_6(const char *read_file, const char *write_file);

View File

@ -24,6 +24,7 @@
#if VM_TRACING
#define GLUE_C_WRITE(func) \
extern void func(void); \
void c__##func(uint16_t ea, uint8_t b); \
void c_##func(uint16_t ea, uint8_t b) { \
c__##func(ea, b); \
@ -36,6 +37,7 @@
void c__##func(uint16_t ea, uint8_t b)
#define GLUE_C_READ(func) \
extern void func(void); \
uint8_t c__##func(uint16_t ea); \
uint8_t c_##func(uint16_t ea) { \
uint8_t b = c__##func(ea); \
@ -51,9 +53,11 @@
#else
#define GLUE_C_WRITE(func) \
extern void func(void); \
void c_##func(uint16_t ea, uint8_t b)
#define GLUE_C_READ(func) \
extern void func(void); \
uint8_t c_##func(uint16_t ea)
#endif

View File

@ -306,6 +306,11 @@ static int disk_select(const struct dirent *e)
return 1;
}
if (!strncmp(p + len - 3, ".po", 3))
{
return 1;
}
return 0;
}

View File

@ -868,7 +868,7 @@ ADDRS [0-9a-fA-F]+
c_toggle_disk_trace_6(buf, NULL);
free(buf);
#else
LOG("CPU tracing not enabled...");
LOG("Disk tracing not enabled...");
#endif
}

View File

@ -1009,8 +1009,8 @@ void show_disk_info() {
sprintf(second_buf[i++], "byte = %02X", disk6.disk_byte);
if (!disk6.disk[disk6.drive].nibblized)
{
sprintf(second_buf[i++], "volume = %d", disk6.volume);
sprintf(second_buf[i++], "checksum = %d", disk6.checksum);
//sprintf(second_buf[i++], "volume = %d", disk6.volume);
//sprintf(second_buf[i++], "checksum = %d", disk6.checksum);
}
sprintf(second_buf[i++], "-------------------------------------");
@ -1038,16 +1038,16 @@ void show_disk_info() {
}
memset(second_buf[++i], ' ', BUF_X);
*(second_buf[i] + sprintf(second_buf[i], "%s %d bytes", (disk6.disk[0].nibblized) ? ".nib" : ".dsk", (int)disk6.disk[0].file_size)) = ' ';
sprintf(second_buf[i++]+off, "%s %d bytes", (disk6.disk[1].nibblized) ? ".nib" : ".dsk", (int)disk6.disk[1].file_size);
*(second_buf[i] + sprintf(second_buf[i], "%s", (disk6.disk[0].nibblized) ? ".nib" : ".dsk")) = ' ';
sprintf(second_buf[i++]+off, "%s", (disk6.disk[1].nibblized) ? ".nib" : ".dsk");
memset(second_buf[i], ' ', BUF_X);
*(second_buf[i] + sprintf(second_buf[i], "write %s", (disk6.disk[0].is_protected) ? "protected" : "enabled")) = ' ';
sprintf(second_buf[i++]+off, "write %s", (disk6.disk[1].is_protected) ? "protected" : "enabled");
memset(second_buf[i], ' ', BUF_X);
*(second_buf[i] + sprintf(second_buf[i], "phase %d %s", disk6.disk[0].phase, (disk6.disk[0].phase_change) ? "(new)" : "")) = ' ';
sprintf(second_buf[i++]+off, "phase %d %s", disk6.disk[1].phase, (disk6.disk[1].phase_change) ? "(new)" : "");
*(second_buf[i] + sprintf(second_buf[i], "phase %d", disk6.disk[0].phase)) = ' ';
sprintf(second_buf[i++]+off, "phase %d", disk6.disk[1].phase);
memset(second_buf[i], ' ', BUF_X);
if (!disk6.disk[0].nibblized)

View File

@ -272,8 +272,7 @@ void c_initialize_tables() {
cpu65_vmem_r[0xC015] = iie_check_cxrom;
/* RDVBLBAR switch */
cpu65_vmem_r[0xC019] =
iie_check_vbl;
cpu65_vmem_r[0xC019] = iie_check_vbl;
/* random number generator */
for (i = 0xC020; i < 0xC030; i++)

View File

@ -60,8 +60,8 @@ static void sha1_to_str(const uint8_t * const md, char *buf) {
// ----------------------------------------------------------------------------
// VM TESTS ...
#define EXPECTED_DISK_TRACE_FILE_SIZE 128794
#define EXPECTED_DISK_TRACE_SHA "43960E8F2A588D1C59DDBC1F2C9F6CCFE0725CE0"
#define EXPECTED_DISK_TRACE_FILE_SIZE 141350
#define EXPECTED_DISK_TRACE_SHA "471EB3D01917B1C6EF9F13C5C7BC1ACE4E74C851"
TEST test_boot_disk_bytes() {
char *homedir = getenv("HOME");
char *disk = NULL;
@ -99,10 +99,9 @@ TEST test_boot_disk_bytes() {
PASS();
}
// This test is fairly abusive ... it creates an ~90MB file in $HOME
// This test is majorly abusive ... it creates an ~800MB file in $HOME
// ... but if it's correct, you're fairly assured the cpu/vm is working =)
#define EXPECTED_CPU_TRACE_FILE_SIZE 89130253
#define EXPECTED_CPU_TRACE_SHA "0E9D690959A26A34DC9456B141CB91A2BDF3798E"
#define EXPECTED_CPU_TRACE_FILE_SIZE 809430487
TEST test_boot_disk_cputrace() {
char *homedir = getenv("HOME");
char *output = NULL;
@ -134,8 +133,11 @@ TEST test_boot_disk_cputrace() {
SHA1(buf, EXPECTED_CPU_TRACE_FILE_SIZE, md);
FREE(buf);
#if 0
// this is no longer a stable value to check due to random return values from disk VM routines
sha1_to_str(md, mdstr);
ASSERT(strcmp(mdstr, EXPECTED_CPU_TRACE_SHA) == 0);
#endif
} while(0);
unlink(output);
@ -144,8 +146,7 @@ TEST test_boot_disk_cputrace() {
PASS();
}
#define EXPECTED_VM_TRACE_FILE_SIZE 2352827
#define EXPECTED_VM_TRACE_SHA "D137B7D312A66F4F19E5846D1BBC56C2A53A8C3F"
#define EXPECTED_VM_TRACE_FILE_SIZE 2830810
TEST test_boot_disk_vmtrace() {
char *homedir = getenv("HOME");
char *disk = NULL;
@ -173,8 +174,11 @@ TEST test_boot_disk_vmtrace() {
SHA1(buf, EXPECTED_VM_TRACE_FILE_SIZE, md);
FREE(buf);
#if 0
// this is no longer a stable value to check due to random return values from disk VM routines
sha1_to_str(md, mdstr);
ASSERT(strcmp(mdstr, EXPECTED_VM_TRACE_SHA) == 0);
#endif
} while(0);
unlink(disk);

View File

@ -122,6 +122,12 @@ typedef struct vm_trace_range_t {
} vm_trace_range_t;
#endif
static uint16_t video_scanner_get_address(uint8_t *vbl_bar /*, current_executed_cycles*/) {
// HACK HACK HACK of course this is wrong ...
*vbl_bar = (c_read_random(0x0) < 0x40) ? 0x80 : 0x0;
return 0x000;
}
GLUE_C_READ(ram_nop)
{
return 0x0;
@ -886,8 +892,16 @@ GLUE_C_READ(iie_check_dhires)
GLUE_C_READ(iie_check_vbl)
{
// HACK FIXME TODO : enable vertical blanking timing/detection */
return 0x0;
uint8_t vbl_bar = 0;
video_scanner_get_address(&vbl_bar /*, current_executed_cycles*/);
uint8_t key = c_read_keyboard(0xC000);
if (vbl_bar) {
vbl_bar = 0x80;
}
return (key & ~0x80) | vbl_bar;
}
GLUE_C_READ(iie_c3rom_peripheral)