c4025101e7
Changing streaming mode default to off for spice (bz #1038336) Fix guest scsi verify command (bz #1001617)
91 lines
3.6 KiB
Diff
91 lines
3.6 KiB
Diff
From ddc0dda3d6352e4c28e0bd11cce1d90734dce0db Mon Sep 17 00:00:00 2001
|
|
From: Paolo Bonzini <pbonzini@redhat.com>
|
|
Date: Thu, 28 Nov 2013 11:18:56 +0100
|
|
Subject: [PATCH] scsi-disk: fix VERIFY emulation
|
|
MIME-Version: 1.0
|
|
Content-Type: text/plain; charset=UTF-8
|
|
Content-Transfer-Encoding: 8bit
|
|
|
|
VERIFY emulation was completely botched (and remained botched through
|
|
all the refactorings). The command must be emulated both in check-medium
|
|
mode (BYTCHK=00, which we implement by doing nothing) and in check-bytes
|
|
mode (which we do not implement yet). Unlike WRITE AND VERIFY (which we
|
|
treat simply as WRITE with FUA bit set), VERIFY cannot be handled like
|
|
READ. In fact the device is _receiving_ data for VERIFY, not _sending_
|
|
it like READ.
|
|
|
|
Cc: qemu-stable@nongnu.org
|
|
Tested-by: Hervé Poussineau <hpoussin@reactos.org>
|
|
Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
|
|
(cherry picked from commit d97e7730816094a71cd1f19a56d7a73f77cdbf96)
|
|
|
|
Conflicts:
|
|
hw/scsi/scsi-disk.c
|
|
---
|
|
hw/scsi/scsi-disk.c | 26 +++++++++++++++++++-------
|
|
1 file changed, 19 insertions(+), 7 deletions(-)
|
|
|
|
diff --git a/hw/scsi/scsi-disk.c b/hw/scsi/scsi-disk.c
|
|
index 74e6a14..1fd1c26 100644
|
|
--- a/hw/scsi/scsi-disk.c
|
|
+++ b/hw/scsi/scsi-disk.c
|
|
@@ -1597,6 +1597,14 @@ static void scsi_disk_emulate_write_data(SCSIRequest *req)
|
|
scsi_disk_emulate_unmap(r, r->iov.iov_base);
|
|
break;
|
|
|
|
+ case VERIFY_10:
|
|
+ case VERIFY_12:
|
|
+ case VERIFY_16:
|
|
+ if (r->req.status == -1) {
|
|
+ scsi_check_condition(r, SENSE_CODE(INVALID_FIELD));
|
|
+ }
|
|
+ break;
|
|
+
|
|
default:
|
|
abort();
|
|
}
|
|
@@ -1837,6 +1845,14 @@ static int32_t scsi_disk_emulate_command(SCSIRequest *req, uint8_t *buf)
|
|
case UNMAP:
|
|
DPRINTF("Unmap (len %lu)\n", (long)r->req.cmd.xfer);
|
|
break;
|
|
+ case VERIFY_10:
|
|
+ case VERIFY_12:
|
|
+ case VERIFY_16:
|
|
+ DPRINTF("Verify (bytchk %lu)\n", (r->req.buf[1] >> 1) & 3);
|
|
+ if (req->cmd.buf[1] & 6) {
|
|
+ goto illegal_request;
|
|
+ }
|
|
+ break;
|
|
case WRITE_SAME_10:
|
|
case WRITE_SAME_16:
|
|
nb_sectors = scsi_data_cdb_length(r->req.cmd.buf);
|
|
@@ -1936,10 +1952,6 @@ static int32_t scsi_disk_dma_command(SCSIRequest *req, uint8_t *buf)
|
|
scsi_check_condition(r, SENSE_CODE(WRITE_PROTECTED));
|
|
return 0;
|
|
}
|
|
- /* fallthrough */
|
|
- case VERIFY_10:
|
|
- case VERIFY_12:
|
|
- case VERIFY_16:
|
|
DPRINTF("Write %s(sector %" PRId64 ", count %u)\n",
|
|
(command & 0xe) == 0xe ? "And Verify " : "",
|
|
r->req.cmd.lba, len);
|
|
@@ -2207,14 +2219,14 @@ static const SCSIReqOps *const scsi_disk_reqops_dispatch[256] = {
|
|
[UNMAP] = &scsi_disk_emulate_reqops,
|
|
[WRITE_SAME_10] = &scsi_disk_emulate_reqops,
|
|
[WRITE_SAME_16] = &scsi_disk_emulate_reqops,
|
|
+ [VERIFY_10] = &scsi_disk_emulate_reqops,
|
|
+ [VERIFY_12] = &scsi_disk_emulate_reqops,
|
|
+ [VERIFY_16] = &scsi_disk_emulate_reqops,
|
|
|
|
[READ_6] = &scsi_disk_dma_reqops,
|
|
[READ_10] = &scsi_disk_dma_reqops,
|
|
[READ_12] = &scsi_disk_dma_reqops,
|
|
[READ_16] = &scsi_disk_dma_reqops,
|
|
- [VERIFY_10] = &scsi_disk_dma_reqops,
|
|
- [VERIFY_12] = &scsi_disk_dma_reqops,
|
|
- [VERIFY_16] = &scsi_disk_dma_reqops,
|
|
[WRITE_6] = &scsi_disk_dma_reqops,
|
|
[WRITE_10] = &scsi_disk_dma_reqops,
|
|
[WRITE_12] = &scsi_disk_dma_reqops,
|