diff options
author | Mark Cave-Ayland <mark.cave-ayland@ilande.co.uk> | 2025-07-11 21:46:35 +0100 |
---|---|---|
committer | Philippe Mathieu-Daudé <philmd@linaro.org> | 2025-07-15 00:25:17 +0200 |
commit | ab1207401edc19d17fad6cb473cd6beae31b1dd1 (patch) | |
tree | 2c55e0707b2468d02b73d94af09d12ecaee2dbbe | |
parent | 28a579a349015a7ed5a57cb4bdcdc5c60ba6b6fc (diff) | |
download | qemu-ab1207401edc19d17fad6cb473cd6beae31b1dd1.zip qemu-ab1207401edc19d17fad6cb473cd6beae31b1dd1.tar.gz qemu-ab1207401edc19d17fad6cb473cd6beae31b1dd1.tar.bz2 |
esp.c: add asc_mode property to indicate the current ESP mode
Add a new asc_mode property to ESPState which indicates the current mode of
the ESP and update the ESP state machine accordingly.
Bump the vmstate version and include migration logic to ensure that asc_mode
is set to initiator mode such that any commands in progress will always
continue.
Signed-off-by: Mark Cave-Ayland <mark.cave-ayland@ilande.co.uk>
Tested-by: Philippe Mathieu-Daudé <philmd@linaro.org>
Message-ID: <20250711204636.542964-7-mark.cave-ayland@ilande.co.uk>
Signed-off-by: Philippe Mathieu-Daudé <philmd@linaro.org>
-rw-r--r-- | hw/scsi/esp.c | 21 | ||||
-rw-r--r-- | include/hw/scsi/esp.h | 7 |
2 files changed, 27 insertions, 1 deletions
diff --git a/hw/scsi/esp.c b/hw/scsi/esp.c index 1c7bad8..4aa58f9 100644 --- a/hw/scsi/esp.c +++ b/hw/scsi/esp.c @@ -275,6 +275,7 @@ static int esp_select(ESPState *s) if (!s->current_dev) { /* No such drive */ s->rregs[ESP_RSTAT] = 0; + s->asc_mode = ESP_ASC_MODE_DIS; s->rregs[ESP_RINTR] = INTR_DC; esp_raise_irq(s); return -1; @@ -284,6 +285,7 @@ static int esp_select(ESPState *s) * Note that we deliberately don't raise the IRQ here: this will be done * either in esp_transfer_data() or esp_command_complete() */ + s->asc_mode = ESP_ASC_MODE_INI; return 0; } @@ -308,6 +310,7 @@ static void do_command_phase(ESPState *s) if (!current_lun) { /* No such drive */ s->rregs[ESP_RSTAT] = 0; + s->asc_mode = ESP_ASC_MODE_DIS; s->rregs[ESP_RINTR] = INTR_DC; s->rregs[ESP_RSEQ] = SEQ_0; esp_raise_irq(s); @@ -1102,6 +1105,7 @@ void esp_hard_reset(ESPState *s) fifo8_reset(&s->cmdfifo); s->dma = 0; s->dma_cb = NULL; + s->asc_mode = ESP_ASC_MODE_DIS; s->rregs[ESP_CFG1] = 7; } @@ -1170,6 +1174,7 @@ static void esp_run_cmd(ESPState *s) break; case CMD_MSGACC: trace_esp_mem_writeb_cmd_msgacc(cmd); + s->asc_mode = ESP_ASC_MODE_DIS; s->rregs[ESP_RINTR] |= INTR_DC; s->rregs[ESP_RSEQ] = 0; s->rregs[ESP_RFLAGS] = 0; @@ -1337,6 +1342,14 @@ static bool esp_is_between_version_5_and_6(void *opaque, int version_id) return version_id >= 5 && version_id <= 6; } +static bool esp_is_version_8(void *opaque, int version_id) +{ + ESPState *s = ESP(opaque); + + version_id = MIN(version_id, s->mig_version_id); + return version_id >= 8; +} + int esp_pre_save(void *opaque) { ESPState *s = ESP(object_resolve_path_component( @@ -1368,13 +1381,18 @@ static int esp_post_load(void *opaque, int version_id) } } + if (version_id < 8) { + /* Assume initiator mode to allow all commands to continue */ + s->asc_mode = ESP_ASC_MODE_INI; + } + s->mig_version_id = vmstate_esp.version_id; return 0; } const VMStateDescription vmstate_esp = { .name = "esp", - .version_id = 7, + .version_id = 8, .minimum_version_id = 3, .post_load = esp_post_load, .fields = (const VMStateField[]) { @@ -1406,6 +1424,7 @@ const VMStateDescription vmstate_esp = { esp_is_between_version_5_and_6), VMSTATE_UINT8_TEST(lun, ESPState, esp_is_version_6), VMSTATE_BOOL(drq_state, ESPState), + VMSTATE_UINT8_TEST(asc_mode, ESPState, esp_is_version_8), VMSTATE_END_OF_LIST() }, }; diff --git a/include/hw/scsi/esp.h b/include/hw/scsi/esp.h index c9afcb7..6327060 100644 --- a/include/hw/scsi/esp.h +++ b/include/hw/scsi/esp.h @@ -14,6 +14,12 @@ typedef void (*ESPDMAMemoryReadWriteFunc)(void *opaque, uint8_t *buf, int len); #define ESP_FIFO_SZ 16 #define ESP_CMDFIFO_SZ 32 +enum ESPASCMode { + ESP_ASC_MODE_DIS = 0, /* Disconnected */ + ESP_ASC_MODE_INI = 1, /* Initiator */ + ESP_ASC_MODE_TGT = 2 /* Target */ +}; + #define TYPE_ESP "esp" OBJECT_DECLARE_SIMPLE_TYPE(ESPState, ESP) @@ -38,6 +44,7 @@ struct ESPState { uint8_t cmdfifo_cdb_offset; uint8_t lun; uint32_t do_cmd; + uint8_t asc_mode; bool data_ready; int dma_enabled; |