- [NEW] [zx_disk] READ DATA command (0x06)

This commit is contained in:
2025-08-07 10:35:49 +02:00
parent 8b36807e3b
commit 884e509d67

View File

@@ -18,6 +18,7 @@
#define ZX_FDC_COMMAND_SENSE_INTERRUPT_STATUS 0x08
#define ZX_FDC_COMMAND_SEEK 0x0F
#define ZX_FDC_COMMAND_READ_ID 0x0A
#define ZX_FDC_COMMAND_READ_DATA 0x06
#define ZX_FDC_MAIN_DRIVE0_BUSY 1
#define ZX_FDC_MAIN_DRIVE1_BUSY 2
@@ -71,6 +72,12 @@ namespace zx_disk
uint8_t current_drive = 0;
uint8_t current_track = 0;
uint8_t current_sector = 0;
uint8_t current_byte = 0;
uint16_t bytes_to_read = 0;
uint8_t eot = 0;
uint8_t st1 = 0;
uint8_t st2 = 0;
int zx_fdc_main_status_port_in(int port);
int zx_fdc_data_port_in(int port);
@@ -158,7 +165,7 @@ namespace zx_disk
int zx_fdc_main_status_port_in(int port)
{
printf("FDC port 0x2ffd IN\n");
if (mode != ZX_FDC_MODE_EXECUTION) printf("FDC port 0x2ffd IN\n");
return main_status_register();
}
@@ -184,10 +191,11 @@ namespace zx_disk
uint8_t process_command_sense_interrupt_status(uint8_t command);
uint8_t process_command_seek(uint8_t command);
uint8_t process_command_read_id(uint8_t command);
uint8_t process_command_read_data(uint8_t command);
int zx_fdc_data_port_in(int port)
{
printf("FDC port 0x3ffd IN\n");
if (mode != ZX_FDC_MODE_EXECUTION) printf("FDC port 0x3ffd IN\n");
if (mode == ZX_FDC_MODE_COMMAND) {
printf("IGNORED!\n");
return 0;
@@ -240,6 +248,9 @@ namespace zx_disk
case ZX_FDC_COMMAND_READ_ID:
process_current_command = process_command_read_id;
break;
case ZX_FDC_COMMAND_READ_DATA:
process_current_command = process_command_read_data;
break;
default:
{
process_current_command = process_command_unknown;
@@ -422,7 +433,7 @@ namespace zx_disk
case 3:
{
call_count++;
const uint8_t val = current_track+1;
const uint8_t val = current_track;
printf("--> (returning 0x%02x)\n", val);
return val;
}
@@ -454,4 +465,146 @@ namespace zx_disk
}
return 0;
}
// ===================================================================
// FDC COMMAND: READ DATA (0x06)
// ===================================================================
uint8_t process_command_read_data(uint8_t command)
{
switch (mode)
{
case ZX_FDC_MODE_COMMAND:
switch (call_count)
{
case 1:
call_count++;
current_head = (command & 0x4)>>2;
current_drive = command & 0x3;
break;
case 2:
call_count++;
current_track = command;
break;
case 3:
call_count++;
current_head = command;
break;
case 4:
call_count++;
current_sector = command-1;
break;
case 5:
call_count++;
bytes_to_read = command;
break;
case 6:
call_count++;
eot = command;
break;
case 7:
call_count++;
// GPL;
break;
case 8:
call_count++;
if ( (bytes_to_read==0) && (command != 0xff) ) bytes_to_read = command;
bytes_to_read = bytes_to_read << 8;
current_byte = 0;
call_count = 0;
mode = ZX_FDC_MODE_EXECUTION;
break;
}
break;
case ZX_FDC_MODE_EXECUTION:
{
const uint8_t val = disk.tracks[current_track].sectors[current_sector].data[current_byte];
bytes_to_read--;
if (bytes_to_read==0) {
st1 = disk.tracks[current_track].sectors[current_sector].st1;
st2 = disk.tracks[current_track].sectors[current_sector].st2;
if (current_sector+1 == disk.tracks[current_track].num_sectors) {
current_track++;
current_sector = 0;
} else {
current_sector++;
}
current_byte = 0;
mode = ZX_FDC_MODE_RESULT;
} else {
current_byte++;
if (current_byte == disk.tracks[current_track].sectors[current_sector].data_length) {
current_byte = 0;
current_sector++;
// [TODO] Detectar si s'ha acabat la pista
}
}
return val;
break;
}
case ZX_FDC_MODE_RESULT:
{
switch (call_count)
{
case 0:
{
call_count++;
fdd0busy = 1;
const uint8_t val = ST0();
fdd0busy = 0;
printf("--> (returning 0x%02x)\n", val);
return val;
}
case 1:
{
call_count++;
const uint8_t val = st1;
printf("--> (returning 0x%02x)\n", val);
return val;
}
case 2:
{
call_count++;
const uint8_t val = st2;
printf("--> (returning 0x%02x)\n", val);
return val;
}
case 3:
{
call_count++;
const uint8_t val = current_track;
printf("--> (returning 0x%02x)\n", val);
return val;
}
case 4:
{
call_count++;
const uint8_t val = current_head;
printf("--> (returning 0x%02x)\n", val);
return val;
}
case 5:
{
call_count++;
const uint8_t val = current_sector+1;
printf("--> (returning 0x%02x)\n", val);
return val;
}
case 6:
{
call_count = 0;
process_current_command = nullptr;
mode = ZX_FDC_MODE_IDLE;
const uint8_t val = disk.tracks[current_track].sectors[current_sector].size;
printf("--> (returning 0x%02x)\n", val);
return val;
}
}
break;
}
}
return 0;
}
}