9ae3a8
From 04ab93423b97ab5bc175032e0e4e1da288840805 Mon Sep 17 00:00:00 2001
9ae3a8
From: John Snow <jsnow@redhat.com>
9ae3a8
Date: Thu, 2 Aug 2018 15:53:34 +0200
9ae3a8
Subject: [PATCH 1/4] scsi-disk: support reporting of rotation rate
9ae3a8
9ae3a8
RH-Author: John Snow <jsnow@redhat.com>
9ae3a8
Message-id: <20180802155336.10347-2-jsnow@redhat.com>
9ae3a8
Patchwork-id: 81613
9ae3a8
O-Subject: [RHEL-7.6 qemu-kvm PATCH 1/3] scsi-disk: support reporting of rotation rate
9ae3a8
Bugzilla: 1583807
9ae3a8
RH-Acked-by: Daniel P. Berrange <berrange@redhat.com>
9ae3a8
RH-Acked-by: Laszlo Ersek <lersek@redhat.com>
9ae3a8
RH-Acked-by: Thomas Huth <thuth@redhat.com>
9ae3a8
9ae3a8
From: "Daniel P. Berrange" <berrange@redhat.com>
9ae3a8
9ae3a8
The Linux kernel will query the SCSI "Block device characteristics"
9ae3a8
VPD to determine the rotations per minute of the disk. If this has
9ae3a8
the value 1, it is taken to be an SSD and so Linux sets the
9ae3a8
'rotational' flag to 0 for the I/O queue and will stop using that
9ae3a8
disk as a source of random entropy. Other operating systems may
9ae3a8
also take into account rotation rate when setting up default
9ae3a8
behaviour.
9ae3a8
9ae3a8
Mgmt apps should be able to set the rotation rate for virtualized
9ae3a8
block devices, based on characteristics of the host storage in use,
9ae3a8
so that the guest OS gets sensible behaviour out of the box. This
9ae3a8
patch thus adds a 'rotation-rate' parameter for 'scsi-hd' and
9ae3a8
'scsi-block' device types. For the latter, this parameter will be
9ae3a8
ignored unless the host device has TYPE_DISK.
9ae3a8
9ae3a8
Signed-off-by: Daniel P. Berrange <berrange@redhat.com>
9ae3a8
Message-Id: <20171004114008.14849-2-berrange@redhat.com>
9ae3a8
Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
9ae3a8
(cherry picked from commit 070f80095ad5b1143b50d2faffd2b1a84292e00d)
9ae3a8
Signed-off-by: John Snow <jsnow@redhat.com>
9ae3a8
Signed-off-by: Miroslav Rezanina <mrezanin@redhat.com>
9ae3a8
---
9ae3a8
 hw/scsi/scsi-disk.c | 20 ++++++++++++++++++++
9ae3a8
 1 file changed, 20 insertions(+)
9ae3a8
9ae3a8
diff --git a/hw/scsi/scsi-disk.c b/hw/scsi/scsi-disk.c
9ae3a8
index 8a8b0ab..911c7b7 100644
9ae3a8
--- a/hw/scsi/scsi-disk.c
9ae3a8
+++ b/hw/scsi/scsi-disk.c
9ae3a8
@@ -83,6 +83,14 @@ struct SCSIDiskState
9ae3a8
     char *product;
9ae3a8
     bool tray_open;
9ae3a8
     bool tray_locked;
9ae3a8
+    /*
9ae3a8
+     * 0x0000        - rotation rate not reported
9ae3a8
+     * 0x0001        - non-rotating medium (SSD)
9ae3a8
+     * 0x0002-0x0400 - reserved
9ae3a8
+     * 0x0401-0xffe  - rotations per minute
9ae3a8
+     * 0xffff        - reserved
9ae3a8
+     */
9ae3a8
+    uint16_t rotation_rate;
9ae3a8
 };
9ae3a8
 
9ae3a8
 static int scsi_handle_rw_error(SCSIDiskReq *r, int error);
9ae3a8
@@ -565,6 +573,7 @@ static int scsi_disk_emulate_inquiry(SCSIRequest *req, uint8_t *outbuf)
9ae3a8
             outbuf[buflen++] = 0x83; // device identification
9ae3a8
             if (s->qdev.type == TYPE_DISK) {
9ae3a8
                 outbuf[buflen++] = 0xb0; // block limits
9ae3a8
+                outbuf[buflen++] = 0xb1; /* block device characteristics */
9ae3a8
                 outbuf[buflen++] = 0xb2; // thin provisioning
9ae3a8
             }
9ae3a8
             break;
9ae3a8
@@ -670,6 +679,15 @@ static int scsi_disk_emulate_inquiry(SCSIRequest *req, uint8_t *outbuf)
9ae3a8
             outbuf[31] = unmap_sectors & 0xff;
9ae3a8
             break;
9ae3a8
         }
9ae3a8
+        case 0xb1: /* block device characteristics */
9ae3a8
+        {
9ae3a8
+            buflen = 8;
9ae3a8
+            outbuf[4] = (s->rotation_rate >> 8) & 0xff;
9ae3a8
+            outbuf[5] = s->rotation_rate & 0xff;
9ae3a8
+            outbuf[6] = 0;
9ae3a8
+            outbuf[7] = 0;
9ae3a8
+            break;
9ae3a8
+        }
9ae3a8
         case 0xb2: /* thin provisioning */
9ae3a8
         {
9ae3a8
             buflen = 8;
9ae3a8
@@ -2543,6 +2561,7 @@ static Property scsi_hd_properties[] = {
9ae3a8
     DEFINE_PROP_HEX64("wwn", SCSIDiskState, wwn, 0),
9ae3a8
     DEFINE_PROP_UINT64("max_unmap_size", SCSIDiskState, max_unmap_size,
9ae3a8
                        DEFAULT_MAX_UNMAP_SIZE),
9ae3a8
+    DEFINE_PROP_UINT16("rotation_rate", SCSIDiskState, rotation_rate, 0),
9ae3a8
     DEFINE_BLOCK_CHS_PROPERTIES(SCSIDiskState, qdev.conf),
9ae3a8
     DEFINE_PROP_END_OF_LIST(),
9ae3a8
 };
9ae3a8
@@ -2619,6 +2638,7 @@ static const TypeInfo scsi_cd_info = {
9ae3a8
 static Property scsi_block_properties[] = {
9ae3a8
     DEFINE_PROP_DRIVE("drive", SCSIDiskState, qdev.conf.bs),
9ae3a8
     DEFINE_PROP_INT32("bootindex", SCSIDiskState, qdev.conf.bootindex, -1),
9ae3a8
+    DEFINE_PROP_UINT16("rotation_rate", SCSIDiskState, rotation_rate, 0),
9ae3a8
     DEFINE_PROP_END_OF_LIST(),
9ae3a8
 };
9ae3a8
 
9ae3a8
-- 
9ae3a8
1.8.3.1
9ae3a8