qemu-sparc queue
-----BEGIN PGP SIGNATURE----- iQFSBAABCgA8FiEEzGIauY6CIA2RXMnEW8LFb64PMh8FAmYOtvEeHG1hcmsuY2F2 ZS1heWxhbmRAaWxhbmRlLmNvLnVrAAoJEFvCxW+uDzIf+5oIAJtRPiTP5aUmN4nU s72NBtgARBJ+5hHl0fqFFlCrG9elO28F1vhT9DwwBOLwihZCnfIXf+SCoE+pvqDw c+AMN/RnDu+1F4LF93W0ZIr305yGDfVlU+S3vKGtB9G4rcLeBDmNlhui2d0Bqx9R jwX1y57vcPclObE0KL6AVOfSDPYiVEVQSiTr3j4oW8TqAs2bduEZMRh6esb3XMIA hmj8mhZAszfh1YvX8ufbxtPQsnNuFMM+Fxgxp0pux8QaI0addDHwVNObRUYlTUZ1 o4xCw7TRXXotaHde/OqZApFECs+md3R7rC2wj7s3ae0ynohHHDFfaB5t1f4pm+kA /6UN/Jc= =XwaI -----END PGP SIGNATURE----- Merge tag 'qemu-sparc-20240404' of https://github.com/mcayland/qemu into staging qemu-sparc queue # -----BEGIN PGP SIGNATURE----- # # iQFSBAABCgA8FiEEzGIauY6CIA2RXMnEW8LFb64PMh8FAmYOtvEeHG1hcmsuY2F2 # ZS1heWxhbmRAaWxhbmRlLmNvLnVrAAoJEFvCxW+uDzIf+5oIAJtRPiTP5aUmN4nU # s72NBtgARBJ+5hHl0fqFFlCrG9elO28F1vhT9DwwBOLwihZCnfIXf+SCoE+pvqDw # c+AMN/RnDu+1F4LF93W0ZIr305yGDfVlU+S3vKGtB9G4rcLeBDmNlhui2d0Bqx9R # jwX1y57vcPclObE0KL6AVOfSDPYiVEVQSiTr3j4oW8TqAs2bduEZMRh6esb3XMIA # hmj8mhZAszfh1YvX8ufbxtPQsnNuFMM+Fxgxp0pux8QaI0addDHwVNObRUYlTUZ1 # o4xCw7TRXXotaHde/OqZApFECs+md3R7rC2wj7s3ae0ynohHHDFfaB5t1f4pm+kA # /6UN/Jc= # =XwaI # -----END PGP SIGNATURE----- # gpg: Signature made Thu 04 Apr 2024 15:19:29 BST # gpg: using RSA key CC621AB98E82200D915CC9C45BC2C56FAE0F321F # gpg: issuer "mark.cave-ayland@ilande.co.uk" # gpg: Good signature from "Mark Cave-Ayland <mark.cave-ayland@ilande.co.uk>" [full] # Primary key fingerprint: CC62 1AB9 8E82 200D 915C C9C4 5BC2 C56F AE0F 321F * tag 'qemu-sparc-20240404' of https://github.com/mcayland/qemu: esp.c: remove explicit setting of DRQ within ESP state machine esp.c: ensure esp_pdma_write() always calls esp_fifo_push() esp.c: update esp_fifo_{push, pop}() to call esp_update_drq() esp.c: introduce esp_update_drq() and update esp_fifo_{push, pop}_buf() to use it esp.c: move esp_set_phase() and esp_get_phase() towards the beginning of the file esp.c: prevent cmdfifo overflow in esp_cdb_ready() esp.c: rework esp_cdb_length() into esp_cdb_ready() esp.c: don't assert() if FIFO empty when executing non-DMA SELATNS esp.c: introduce esp_fifo_push_buf() function for pushing to the FIFO esp.c: change esp_fifo_pop_buf() to take ESPState esp.c: use esp_fifo_push() instead of fifo8_push() esp.c: change esp_fifo_pop() to take ESPState esp.c: change esp_fifo_push() to take ESPState esp.c: replace cmdfifo use of esp_fifo_pop() in do_message_phase() esp.c: replace esp_fifo_pop_buf() with esp_fifo8_pop_buf() in do_message_phase() esp.c: replace esp_fifo_pop_buf() with esp_fifo8_pop_buf() in do_command_phase() esp.c: move esp_fifo_pop_buf() internals to new esp_fifo8_pop_buf() function Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
This commit is contained in:
commit
ce64e6224a
211
hw/scsi/esp.c
211
hw/scsi/esp.c
@ -79,6 +79,24 @@ static void esp_lower_drq(ESPState *s)
|
||||
}
|
||||
}
|
||||
|
||||
static const char *esp_phase_names[8] = {
|
||||
"DATA OUT", "DATA IN", "COMMAND", "STATUS",
|
||||
"(reserved)", "(reserved)", "MESSAGE OUT", "MESSAGE IN"
|
||||
};
|
||||
|
||||
static void esp_set_phase(ESPState *s, uint8_t phase)
|
||||
{
|
||||
s->rregs[ESP_RSTAT] &= ~7;
|
||||
s->rregs[ESP_RSTAT] |= phase;
|
||||
|
||||
trace_esp_set_phase(esp_phase_names[phase]);
|
||||
}
|
||||
|
||||
static uint8_t esp_get_phase(ESPState *s)
|
||||
{
|
||||
return s->rregs[ESP_RSTAT] & 7;
|
||||
}
|
||||
|
||||
void esp_dma_enable(ESPState *s, int irq, int level)
|
||||
{
|
||||
if (level) {
|
||||
@ -106,26 +124,80 @@ void esp_request_cancelled(SCSIRequest *req)
|
||||
}
|
||||
}
|
||||
|
||||
static void esp_fifo_push(Fifo8 *fifo, uint8_t val)
|
||||
static void esp_update_drq(ESPState *s)
|
||||
{
|
||||
if (fifo8_num_used(fifo) == fifo->capacity) {
|
||||
trace_esp_error_fifo_overrun();
|
||||
bool to_device;
|
||||
|
||||
switch (esp_get_phase(s)) {
|
||||
case STAT_MO:
|
||||
case STAT_CD:
|
||||
case STAT_DO:
|
||||
to_device = true;
|
||||
break;
|
||||
|
||||
case STAT_DI:
|
||||
case STAT_ST:
|
||||
case STAT_MI:
|
||||
to_device = false;
|
||||
break;
|
||||
|
||||
default:
|
||||
return;
|
||||
}
|
||||
|
||||
fifo8_push(fifo, val);
|
||||
if (s->dma) {
|
||||
/* DMA request so update DRQ according to transfer direction */
|
||||
if (to_device) {
|
||||
if (fifo8_num_free(&s->fifo) < 2) {
|
||||
esp_lower_drq(s);
|
||||
} else {
|
||||
esp_raise_drq(s);
|
||||
}
|
||||
} else {
|
||||
if (fifo8_num_used(&s->fifo) < 2) {
|
||||
esp_lower_drq(s);
|
||||
} else {
|
||||
esp_raise_drq(s);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
/* Not a DMA request */
|
||||
esp_lower_drq(s);
|
||||
}
|
||||
}
|
||||
|
||||
static uint8_t esp_fifo_pop(Fifo8 *fifo)
|
||||
static void esp_fifo_push(ESPState *s, uint8_t val)
|
||||
{
|
||||
if (fifo8_is_empty(fifo)) {
|
||||
return 0;
|
||||
if (fifo8_num_used(&s->fifo) == s->fifo.capacity) {
|
||||
trace_esp_error_fifo_overrun();
|
||||
} else {
|
||||
fifo8_push(&s->fifo, val);
|
||||
}
|
||||
|
||||
return fifo8_pop(fifo);
|
||||
esp_update_drq(s);
|
||||
}
|
||||
|
||||
static uint32_t esp_fifo_pop_buf(Fifo8 *fifo, uint8_t *dest, int maxlen)
|
||||
static void esp_fifo_push_buf(ESPState *s, uint8_t *buf, int len)
|
||||
{
|
||||
fifo8_push_all(&s->fifo, buf, len);
|
||||
esp_update_drq(s);
|
||||
}
|
||||
|
||||
static uint8_t esp_fifo_pop(ESPState *s)
|
||||
{
|
||||
uint8_t val;
|
||||
|
||||
if (fifo8_is_empty(&s->fifo)) {
|
||||
val = 0;
|
||||
} else {
|
||||
val = fifo8_pop(&s->fifo);
|
||||
}
|
||||
|
||||
esp_update_drq(s);
|
||||
return val;
|
||||
}
|
||||
|
||||
static uint32_t esp_fifo8_pop_buf(Fifo8 *fifo, uint8_t *dest, int maxlen)
|
||||
{
|
||||
const uint8_t *buf;
|
||||
uint32_t n, n2;
|
||||
@ -155,6 +227,14 @@ static uint32_t esp_fifo_pop_buf(Fifo8 *fifo, uint8_t *dest, int maxlen)
|
||||
return n;
|
||||
}
|
||||
|
||||
static uint32_t esp_fifo_pop_buf(ESPState *s, uint8_t *dest, int maxlen)
|
||||
{
|
||||
uint32_t len = esp_fifo8_pop_buf(&s->fifo, dest, maxlen);
|
||||
|
||||
esp_update_drq(s);
|
||||
return len;
|
||||
}
|
||||
|
||||
static uint32_t esp_get_tc(ESPState *s)
|
||||
{
|
||||
uint32_t dmalen;
|
||||
@ -190,29 +270,11 @@ static uint32_t esp_get_stc(ESPState *s)
|
||||
return dmalen;
|
||||
}
|
||||
|
||||
static const char *esp_phase_names[8] = {
|
||||
"DATA OUT", "DATA IN", "COMMAND", "STATUS",
|
||||
"(reserved)", "(reserved)", "MESSAGE OUT", "MESSAGE IN"
|
||||
};
|
||||
|
||||
static void esp_set_phase(ESPState *s, uint8_t phase)
|
||||
{
|
||||
s->rregs[ESP_RSTAT] &= ~7;
|
||||
s->rregs[ESP_RSTAT] |= phase;
|
||||
|
||||
trace_esp_set_phase(esp_phase_names[phase]);
|
||||
}
|
||||
|
||||
static uint8_t esp_get_phase(ESPState *s)
|
||||
{
|
||||
return s->rregs[ESP_RSTAT] & 7;
|
||||
}
|
||||
|
||||
static uint8_t esp_pdma_read(ESPState *s)
|
||||
{
|
||||
uint8_t val;
|
||||
|
||||
val = esp_fifo_pop(&s->fifo);
|
||||
val = esp_fifo_pop(s);
|
||||
return val;
|
||||
}
|
||||
|
||||
@ -220,15 +282,13 @@ static void esp_pdma_write(ESPState *s, uint8_t val)
|
||||
{
|
||||
uint32_t dmalen = esp_get_tc(s);
|
||||
|
||||
if (dmalen == 0) {
|
||||
return;
|
||||
}
|
||||
|
||||
esp_fifo_push(&s->fifo, val);
|
||||
esp_fifo_push(s, val);
|
||||
|
||||
if (dmalen && s->drq_state) {
|
||||
dmalen--;
|
||||
esp_set_tc(s, dmalen);
|
||||
}
|
||||
}
|
||||
|
||||
static int esp_select(ESPState *s)
|
||||
{
|
||||
@ -275,7 +335,7 @@ static void do_command_phase(ESPState *s)
|
||||
if (!cmdlen || !s->current_dev) {
|
||||
return;
|
||||
}
|
||||
esp_fifo_pop_buf(&s->cmdfifo, buf, cmdlen);
|
||||
esp_fifo8_pop_buf(&s->cmdfifo, buf, cmdlen);
|
||||
|
||||
current_lun = scsi_device_find(&s->bus, 0, s->current_dev->id, s->lun);
|
||||
if (!current_lun) {
|
||||
@ -310,7 +370,8 @@ static void do_command_phase(ESPState *s)
|
||||
static void do_message_phase(ESPState *s)
|
||||
{
|
||||
if (s->cmdfifo_cdb_offset) {
|
||||
uint8_t message = esp_fifo_pop(&s->cmdfifo);
|
||||
uint8_t message = fifo8_is_empty(&s->cmdfifo) ? 0 :
|
||||
fifo8_pop(&s->cmdfifo);
|
||||
|
||||
trace_esp_do_identify(message);
|
||||
s->lun = message & 7;
|
||||
@ -320,7 +381,7 @@ static void do_message_phase(ESPState *s)
|
||||
/* Ignore extended messages for now */
|
||||
if (s->cmdfifo_cdb_offset) {
|
||||
int len = MIN(s->cmdfifo_cdb_offset, fifo8_num_used(&s->cmdfifo));
|
||||
esp_fifo_pop_buf(&s->cmdfifo, NULL, len);
|
||||
esp_fifo8_pop_buf(&s->cmdfifo, NULL, len);
|
||||
s->cmdfifo_cdb_offset = 0;
|
||||
}
|
||||
}
|
||||
@ -414,20 +475,30 @@ static void write_response(ESPState *s)
|
||||
}
|
||||
}
|
||||
|
||||
static int esp_cdb_length(ESPState *s)
|
||||
static bool esp_cdb_ready(ESPState *s)
|
||||
{
|
||||
int len = fifo8_num_used(&s->cmdfifo) - s->cmdfifo_cdb_offset;
|
||||
const uint8_t *pbuf;
|
||||
int cmdlen, len;
|
||||
uint32_t n;
|
||||
int cdblen;
|
||||
|
||||
cmdlen = fifo8_num_used(&s->cmdfifo);
|
||||
if (cmdlen < s->cmdfifo_cdb_offset) {
|
||||
return 0;
|
||||
if (len <= 0) {
|
||||
return false;
|
||||
}
|
||||
|
||||
pbuf = fifo8_peek_buf(&s->cmdfifo, cmdlen, NULL);
|
||||
len = scsi_cdb_length((uint8_t *)&pbuf[s->cmdfifo_cdb_offset]);
|
||||
pbuf = fifo8_peek_buf(&s->cmdfifo, len, &n);
|
||||
if (n < len) {
|
||||
/*
|
||||
* In normal use the cmdfifo should never wrap, but include this check
|
||||
* to prevent a malicious guest from reading past the end of the
|
||||
* cmdfifo data buffer below
|
||||
*/
|
||||
return false;
|
||||
}
|
||||
|
||||
return len;
|
||||
cdblen = scsi_cdb_length((uint8_t *)&pbuf[s->cmdfifo_cdb_offset]);
|
||||
|
||||
return cdblen < 0 ? false : (len >= cdblen);
|
||||
}
|
||||
|
||||
static void esp_dma_ti_check(ESPState *s)
|
||||
@ -435,7 +506,6 @@ static void esp_dma_ti_check(ESPState *s)
|
||||
if (esp_get_tc(s) == 0 && fifo8_num_used(&s->fifo) < 2) {
|
||||
s->rregs[ESP_RINTR] |= INTR_BS;
|
||||
esp_raise_irq(s);
|
||||
esp_lower_drq(s);
|
||||
}
|
||||
}
|
||||
|
||||
@ -453,9 +523,8 @@ static void esp_do_dma(ESPState *s)
|
||||
s->dma_memory_read(s->dma_opaque, buf, len);
|
||||
esp_set_tc(s, esp_get_tc(s) - len);
|
||||
} else {
|
||||
len = esp_fifo_pop_buf(&s->fifo, buf, fifo8_num_used(&s->fifo));
|
||||
len = esp_fifo_pop_buf(s, buf, fifo8_num_used(&s->fifo));
|
||||
len = MIN(fifo8_num_free(&s->cmdfifo), len);
|
||||
esp_raise_drq(s);
|
||||
}
|
||||
|
||||
fifo8_push_all(&s->cmdfifo, buf, len);
|
||||
@ -509,10 +578,9 @@ static void esp_do_dma(ESPState *s)
|
||||
fifo8_push_all(&s->cmdfifo, buf, len);
|
||||
esp_set_tc(s, esp_get_tc(s) - len);
|
||||
} else {
|
||||
len = esp_fifo_pop_buf(&s->fifo, buf, fifo8_num_used(&s->fifo));
|
||||
len = esp_fifo_pop_buf(s, buf, fifo8_num_used(&s->fifo));
|
||||
len = MIN(fifo8_num_free(&s->cmdfifo), len);
|
||||
fifo8_push_all(&s->cmdfifo, buf, len);
|
||||
esp_raise_drq(s);
|
||||
}
|
||||
trace_esp_handle_ti_cmd(cmdlen);
|
||||
s->ti_size = 0;
|
||||
@ -543,8 +611,7 @@ static void esp_do_dma(ESPState *s)
|
||||
/* Copy FIFO data to device */
|
||||
len = MIN(s->async_len, ESP_FIFO_SZ);
|
||||
len = MIN(len, fifo8_num_used(&s->fifo));
|
||||
len = esp_fifo_pop_buf(&s->fifo, s->async_buf, len);
|
||||
esp_raise_drq(s);
|
||||
len = esp_fifo_pop_buf(s, s->async_buf, len);
|
||||
}
|
||||
|
||||
s->async_buf += len;
|
||||
@ -595,8 +662,7 @@ static void esp_do_dma(ESPState *s)
|
||||
} else {
|
||||
/* Copy device data to FIFO */
|
||||
len = MIN(len, fifo8_num_free(&s->fifo));
|
||||
fifo8_push_all(&s->fifo, s->async_buf, len);
|
||||
esp_raise_drq(s);
|
||||
esp_fifo_push_buf(s, s->async_buf, len);
|
||||
}
|
||||
|
||||
s->async_buf += len;
|
||||
@ -644,7 +710,7 @@ static void esp_do_dma(ESPState *s)
|
||||
if (s->dma_memory_write) {
|
||||
s->dma_memory_write(s->dma_opaque, buf, len);
|
||||
} else {
|
||||
fifo8_push_all(&s->fifo, buf, len);
|
||||
esp_fifo_push_buf(s, buf, len);
|
||||
}
|
||||
|
||||
esp_set_tc(s, esp_get_tc(s) - len);
|
||||
@ -662,7 +728,6 @@ static void esp_do_dma(ESPState *s)
|
||||
if (fifo8_num_used(&s->fifo) < 2) {
|
||||
s->rregs[ESP_RINTR] |= INTR_BS;
|
||||
esp_raise_irq(s);
|
||||
esp_lower_drq(s);
|
||||
}
|
||||
break;
|
||||
}
|
||||
@ -679,7 +744,7 @@ static void esp_do_dma(ESPState *s)
|
||||
if (s->dma_memory_write) {
|
||||
s->dma_memory_write(s->dma_opaque, buf, len);
|
||||
} else {
|
||||
fifo8_push_all(&s->fifo, buf, len);
|
||||
esp_fifo_push_buf(s, buf, len);
|
||||
}
|
||||
|
||||
esp_set_tc(s, esp_get_tc(s) - len);
|
||||
@ -707,7 +772,7 @@ static void esp_nodma_ti_dataout(ESPState *s)
|
||||
}
|
||||
len = MIN(s->async_len, ESP_FIFO_SZ);
|
||||
len = MIN(len, fifo8_num_used(&s->fifo));
|
||||
esp_fifo_pop_buf(&s->fifo, s->async_buf, len);
|
||||
esp_fifo_pop_buf(s, s->async_buf, len);
|
||||
s->async_buf += len;
|
||||
s->async_len -= len;
|
||||
s->ti_size += len;
|
||||
@ -732,7 +797,7 @@ static void esp_do_nodma(ESPState *s)
|
||||
switch (s->rregs[ESP_CMD]) {
|
||||
case CMD_SELATN:
|
||||
/* Copy FIFO into cmdfifo */
|
||||
len = esp_fifo_pop_buf(&s->fifo, buf, fifo8_num_used(&s->fifo));
|
||||
len = esp_fifo_pop_buf(s, buf, fifo8_num_used(&s->fifo));
|
||||
len = MIN(fifo8_num_free(&s->cmdfifo), len);
|
||||
fifo8_push_all(&s->cmdfifo, buf, len);
|
||||
|
||||
@ -751,7 +816,8 @@ static void esp_do_nodma(ESPState *s)
|
||||
|
||||
case CMD_SELATNS:
|
||||
/* Copy one byte from FIFO into cmdfifo */
|
||||
len = esp_fifo_pop_buf(&s->fifo, buf, 1);
|
||||
len = esp_fifo_pop_buf(s, buf,
|
||||
MIN(fifo8_num_used(&s->fifo), 1));
|
||||
len = MIN(fifo8_num_free(&s->cmdfifo), len);
|
||||
fifo8_push_all(&s->cmdfifo, buf, len);
|
||||
|
||||
@ -768,7 +834,7 @@ static void esp_do_nodma(ESPState *s)
|
||||
|
||||
case CMD_TI:
|
||||
/* Copy FIFO into cmdfifo */
|
||||
len = esp_fifo_pop_buf(&s->fifo, buf, fifo8_num_used(&s->fifo));
|
||||
len = esp_fifo_pop_buf(s, buf, fifo8_num_used(&s->fifo));
|
||||
len = MIN(fifo8_num_free(&s->cmdfifo), len);
|
||||
fifo8_push_all(&s->cmdfifo, buf, len);
|
||||
|
||||
@ -786,7 +852,7 @@ static void esp_do_nodma(ESPState *s)
|
||||
switch (s->rregs[ESP_CMD]) {
|
||||
case CMD_TI:
|
||||
/* Copy FIFO into cmdfifo */
|
||||
len = esp_fifo_pop_buf(&s->fifo, buf, fifo8_num_used(&s->fifo));
|
||||
len = esp_fifo_pop_buf(s, buf, fifo8_num_used(&s->fifo));
|
||||
len = MIN(fifo8_num_free(&s->cmdfifo), len);
|
||||
fifo8_push_all(&s->cmdfifo, buf, len);
|
||||
|
||||
@ -794,8 +860,7 @@ static void esp_do_nodma(ESPState *s)
|
||||
trace_esp_handle_ti_cmd(cmdlen);
|
||||
|
||||
/* CDB may be transferred in one or more TI commands */
|
||||
if (esp_cdb_length(s) && esp_cdb_length(s) ==
|
||||
fifo8_num_used(&s->cmdfifo) - s->cmdfifo_cdb_offset) {
|
||||
if (esp_cdb_ready(s)) {
|
||||
/* Command has been received */
|
||||
do_cmd(s);
|
||||
} else {
|
||||
@ -815,13 +880,12 @@ static void esp_do_nodma(ESPState *s)
|
||||
case CMD_SEL | CMD_DMA:
|
||||
case CMD_SELATN | CMD_DMA:
|
||||
/* Copy FIFO into cmdfifo */
|
||||
len = esp_fifo_pop_buf(&s->fifo, buf, fifo8_num_used(&s->fifo));
|
||||
len = esp_fifo_pop_buf(s, buf, fifo8_num_used(&s->fifo));
|
||||
len = MIN(fifo8_num_free(&s->cmdfifo), len);
|
||||
fifo8_push_all(&s->cmdfifo, buf, len);
|
||||
|
||||
/* Handle when DMA transfer is terminated by non-DMA FIFO write */
|
||||
if (esp_cdb_length(s) && esp_cdb_length(s) ==
|
||||
fifo8_num_used(&s->cmdfifo) - s->cmdfifo_cdb_offset) {
|
||||
if (esp_cdb_ready(s)) {
|
||||
/* Command has been received */
|
||||
do_cmd(s);
|
||||
}
|
||||
@ -830,7 +894,7 @@ static void esp_do_nodma(ESPState *s)
|
||||
case CMD_SEL:
|
||||
case CMD_SELATN:
|
||||
/* FIFO already contain entire CDB: copy to cmdfifo and execute */
|
||||
len = esp_fifo_pop_buf(&s->fifo, buf, fifo8_num_used(&s->fifo));
|
||||
len = esp_fifo_pop_buf(s, buf, fifo8_num_used(&s->fifo));
|
||||
len = MIN(fifo8_num_free(&s->cmdfifo), len);
|
||||
fifo8_push_all(&s->cmdfifo, buf, len);
|
||||
|
||||
@ -852,7 +916,7 @@ static void esp_do_nodma(ESPState *s)
|
||||
return;
|
||||
}
|
||||
if (fifo8_is_empty(&s->fifo)) {
|
||||
fifo8_push(&s->fifo, s->async_buf[0]);
|
||||
esp_fifo_push(s, s->async_buf[0]);
|
||||
s->async_buf++;
|
||||
s->async_len--;
|
||||
s->ti_size--;
|
||||
@ -875,7 +939,7 @@ static void esp_do_nodma(ESPState *s)
|
||||
case STAT_ST:
|
||||
switch (s->rregs[ESP_CMD]) {
|
||||
case CMD_ICCS:
|
||||
fifo8_push(&s->fifo, s->status);
|
||||
esp_fifo_push(s, s->status);
|
||||
esp_set_phase(s, STAT_MI);
|
||||
|
||||
/* Process any message in phase data */
|
||||
@ -887,7 +951,7 @@ static void esp_do_nodma(ESPState *s)
|
||||
case STAT_MI:
|
||||
switch (s->rregs[ESP_CMD]) {
|
||||
case CMD_ICCS:
|
||||
fifo8_push(&s->fifo, 0);
|
||||
esp_fifo_push(s, 0);
|
||||
|
||||
/* Raise end of command interrupt */
|
||||
s->rregs[ESP_RINTR] |= INTR_FC;
|
||||
@ -951,9 +1015,6 @@ void esp_command_complete(SCSIRequest *req, size_t resid)
|
||||
s->rregs[ESP_RINTR] |= INTR_BS;
|
||||
esp_raise_irq(s);
|
||||
|
||||
/* Ensure DRQ is set correctly for TC underflow or normal completion */
|
||||
esp_dma_ti_check(s);
|
||||
|
||||
if (s->current_req) {
|
||||
scsi_req_unref(s->current_req);
|
||||
s->current_req = NULL;
|
||||
@ -1178,7 +1239,7 @@ uint64_t esp_reg_read(ESPState *s, uint32_t saddr)
|
||||
|
||||
switch (saddr) {
|
||||
case ESP_FIFO:
|
||||
s->rregs[ESP_FIFO] = esp_fifo_pop(&s->fifo);
|
||||
s->rregs[ESP_FIFO] = esp_fifo_pop(s);
|
||||
val = s->rregs[ESP_FIFO];
|
||||
break;
|
||||
case ESP_RINTR:
|
||||
@ -1234,7 +1295,7 @@ void esp_reg_write(ESPState *s, uint32_t saddr, uint64_t val)
|
||||
break;
|
||||
case ESP_FIFO:
|
||||
if (!fifo8_is_full(&s->fifo)) {
|
||||
esp_fifo_push(&s->fifo, val);
|
||||
esp_fifo_push(s, val);
|
||||
}
|
||||
esp_do_nodma(s);
|
||||
break;
|
||||
|
Loading…
Reference in New Issue
Block a user