From: "Denis V. Lunev" <den@openvz.org>
Cc: Michael Roth <mdroth@linux.vnet.ibm.com>,
Olga Krishtal <okrishtal@parallels.com>,
qemu-devel@nongnu.org, "Denis V. Lunev" <den@openvz.org>
Subject: [Qemu-devel] [PATCH 3/4] qga: added bus type and disk location path
Date: Sat, 2 May 2015 13:13:20 +0300 [thread overview]
Message-ID: <1430561601-19184-4-git-send-email-den@openvz.org> (raw)
In-Reply-To: <1430561601-19184-1-git-send-email-den@openvz.org>
From: Olga Krishtal <okrishtal@parallels.com>
According to Microsoft disk location path can be obtained via
IOCTL_SCSI_GET_ADDRESS. Unfortunately this ioctl can not be used for all
devices. There are certain bus types which could be obtained with this
API. Please refer to the following link for more details
https://technet.microsoft.com/en-us/library/ee851589(v=ws.10).aspx
Bus type could be obtained using IOCTL_STORAGE_QUERY_PROPERTY. Enum
STORAGE_BUS_TYPE describes all buses supported by OS.
Windows defines more bus types that Linux. Thus some values have been added
to GuestDiskBusType.
Signed-off-by: Olga Krishtal <okrishtal@parallels.com>
Signed-off-by: Denis V. Lunev <den@openvz.org>
CC: Michael Roth <mdroth@linux.vnet.ibm.com>
---
qga/commands-win32.c | 120 ++++++++++++++++++++++++++++++++++++++++++++++++++-
qga/qapi-schema.json | 15 ++++++-
2 files changed, 132 insertions(+), 3 deletions(-)
diff --git a/qga/commands-win32.c b/qga/commands-win32.c
index d26fd59..f3569e9 100644
--- a/qga/commands-win32.c
+++ b/qga/commands-win32.c
@@ -16,6 +16,8 @@
#include <powrprof.h>
#include <stdio.h>
#include <string.h>
+#include <winioctl.h>
+#include <ntddscsi.h>
#include "qga/guest-agent-core.h"
#include "qga/vss-win32.h"
#include "qga-qmp-commands.h"
@@ -84,6 +86,36 @@ static OpenFlags *find_open_flag(const char *mode_str)
return NULL;
}
+static STORAGE_BUS_TYPE win2qemu[] = {
+ [BusTypeUnknown] = GUEST_DISK_BUS_TYPE_UNKNOWN,
+ [BusTypeScsi] = GUEST_DISK_BUS_TYPE_SCSI,
+ [BusTypeAtapi] = GUEST_DISK_BUS_TYPE_IDE,
+ [BusTypeAta] = GUEST_DISK_BUS_TYPE_IDE,
+ [BusType1394] = GUEST_DISK_BUS_TYPE_1394,
+ [BusTypeSsa] = GUEST_DISK_BUS_TYPE_SSA,
+ [BusTypeFibre] = GUEST_DISK_BUS_TYPE_SSA,
+ [BusTypeUsb] = GUEST_DISK_BUS_TYPE_USB,
+ [BusTypeRAID] = GUEST_DISK_BUS_TYPE_RAID,
+#if (_WIN32_WINNT >= 0x0600)
+ [BusTypeiScsi] = GUEST_DISK_BUS_TYPE_I_SCSI,
+ [BusTypeSas] = GUEST_DISK_BUS_TYPE_SAS,
+ [BusTypeSata] = GUEST_DISK_BUS_TYPE_SATA,
+ [BusTypeSd] = GUEST_DISK_BUS_TYPE_SD,
+ [BusTypeMmc] = GUEST_DISK_BUS_TYPE_MMC,
+ [BusTypeVirtual] = GUEST_DISK_BUS_TYPE_VIRTUAL,
+ [BusTypeFileBackedVirtuaul] = GUEST_DISK_BUS_TYPE_FBIRTUAL,
+ [BusTypeSpaces] = GUEST_DISK_BUS_TYPE_SPACES
+#endif
+};
+
+static GuestDiskBusType find_bus_type(STORAGE_BUS_TYPE bus)
+{
+ if (bus > ARRAY_SIZE(win2qemu) || (int)bus < 0) {
+ return GUEST_DISK_BUS_TYPE_UNKNOWN;
+ }
+ return win2qemu[(int)bus];
+}
+
static int64_t guest_file_handle_add(HANDLE fh, Error **errp)
{
GuestFileHandle *gfh;
@@ -382,6 +414,92 @@ static void guest_file_init(void)
QTAILQ_INIT(&guest_file_state.filehandles);
}
+static GuestPCIAddress *get_pci_info(char *guid, Error **errp)
+{
+ return NULL;
+}
+
+static int get_disk_bus_type(HANDLE vol_h, Error **errp)
+{
+ STORAGE_PROPERTY_QUERY query;
+ STORAGE_DEVICE_DESCRIPTOR *dev_desc, buf;
+ DWORD received;
+
+ dev_desc = &buf;
+ dev_desc->Size = sizeof(buf);
+ query.PropertyId = StorageDeviceProperty;
+ query.QueryType = PropertyStandardQuery;
+
+ if (!DeviceIoControl(vol_h, IOCTL_STORAGE_QUERY_PROPERTY, &query,
+ sizeof(STORAGE_PROPERTY_QUERY), dev_desc,
+ dev_desc->Size, &received, NULL)) {
+ error_setg_win32(errp, GetLastError(), "failed to get bus type");
+ return -1;
+ }
+
+ return dev_desc->BusType;
+}
+
+/* VSS provider works with volumes, thus there is no difference if
+ * the volume consist of spanned disks. Info about the first disk in the
+ * volume is returned for the spanned disk group (LVM) */
+static GuestDiskAddressList *build_guest_disk_info(char *guid, Error **errp)
+{
+ GuestDiskAddressList *list = NULL;
+ GuestDiskAddress *disk;
+ DWORD len;
+ int bus;
+ HANDLE vol_h;
+ char *name = g_strndup(guid, strlen(guid)-1);
+
+ vol_h = CreateFile(name, 0, FILE_SHARE_READ, NULL, OPEN_EXISTING,
+ NULL, NULL);
+ if (vol_h == INVALID_HANDLE_VALUE) {
+ error_setg_win32(errp, GetLastError(), "failed to open volume");
+ goto out_free;
+ }
+
+ bus = get_disk_bus_type(vol_h, errp);
+ if (bus < 0) {
+ goto out_close;
+ }
+
+ disk = g_malloc0(sizeof(*disk));
+ disk->bus_type = find_bus_type(bus);
+ if (bus == BusTypeScsi || bus == BusTypeAta || bus == BusTypeRAID
+#if (_WIN32_WINNT >= 0x0600)
+ /* This bus type is not supported before Windows Server 2003 SP1 */
+ || bus == BusTypeSas
+#endif
+ ) {
+ SCSI_ADDRESS addr;
+
+ /* We are able to use the same ioctls for different bus types
+ * according to Microsoft docs
+ * https://technet.microsoft.com/en-us/library/ee851589(v=ws.10).aspx */
+ if (DeviceIoControl(vol_h, IOCTL_SCSI_GET_ADDRESS, NULL, 0, &addr,
+ sizeof(SCSI_ADDRESS), &len, NULL)) {
+ disk->unit = addr.Lun;
+ disk->target = addr.TargetId;
+ disk->bus = addr.PathId;
+ disk->pci_controller = get_pci_info(name, errp);
+ }
+ /* We do not set error in this case, because we still have enough
+ * information about volume. */
+ } else {
+ disk->pci_controller = NULL;
+ }
+
+ list = g_malloc0(sizeof(*list));
+ list->value = disk;
+ list->next = NULL;
+out_close:
+ CloseHandle(vol_h);
+out_free:
+ g_free(name);
+ return list;
+}
+
static GuestFilesystemInfo *build_guest_fsinfo(char *guid, Error **errp)
{
DWORD info_size;
@@ -424,7 +542,7 @@ static GuestFilesystemInfo *build_guest_fsinfo(char *guid, Error **errp)
fs->mountpoint = g_strndup(mnt_point, len);
}
fs->type = g_strdup(fs_name);
- fs->disk = NULL;
+ fs->disk = build_guest_disk_info(guid, errp);
free:
g_free(mnt_point);
return fs;
diff --git a/qga/qapi-schema.json b/qga/qapi-schema.json
index 5c4cd40..6eaa7c1 100644
--- a/qga/qapi-schema.json
+++ b/qga/qapi-schema.json
@@ -667,6 +667,7 @@
# @GuestDiskBusType
#
# An enumeration of bus type of disks
+# it is different for Linux and Windows guest
#
# @ide: IDE disks
# @fdc: floppy disks
@@ -677,12 +678,22 @@
# @uml: UML disks
# @sata: SATA disks
# @sd: SD cards
-#
+# @unknown: Unknown bus type
+# @1394: Win IEEE 1394 bus type
+# @ssa: Win SSA bus type
+# @fibre: Win fiber channel bus type
+# @raid: Win RAID bus type
+# @iscsi: Win iScsi bus type
+# @sas: Win serial-attaches SCSI bus type
+# @mmc: Win multimedia card (MMC) bus type
+# @virtual: Win virtual bus type
+# @file-backed virtual: Win file-backed bus type
# Since: 2.2
##
{ 'enum': 'GuestDiskBusType',
'data': [ 'ide', 'fdc', 'scsi', 'virtio', 'xen', 'usb', 'uml', 'sata',
- 'sd' ] }
+ 'sd', 'unknown', '1394', 'ssa', 'fibre', 'raid', 'iscsi',
+ 'sas', 'mmc', 'virtual', 'file-backed-virtual' ] }
##
# @GuestPCIAddress:
--
1.9.1
next prev parent reply other threads:[~2015-05-02 10:24 UTC|newest]
Thread overview: 14+ messages / expand[flat|nested] mbox.gz Atom feed top
2015-05-02 10:13 [Qemu-devel] [PATCH 0/4] qga: disk and volume info for Windows guest Denis V. Lunev
2015-05-02 10:13 ` [Qemu-devel] [PATCH 1/4] qga: added empty qmp_quest_get_fsinfo functionality Denis V. Lunev
2015-05-02 10:13 ` [Qemu-devel] [PATCH 2/4] qga: added mountpoint and filesystem type for single Denis V. Lunev
2015-05-02 10:13 ` Denis V. Lunev [this message]
2015-05-02 10:13 ` [Qemu-devel] [PATCH 4/4] qga: added GuestPCIAddress information Denis V. Lunev
2015-05-12 5:51 ` [Qemu-devel] [PATCH 0/4] qga: disk and volume info for Windows guest Denis V. Lunev
2015-05-20 7:48 ` Denis V. Lunev
2015-05-27 7:07 ` Denis V. Lunev
2015-06-08 6:43 ` Denis V. Lunev
2015-06-15 7:07 ` Denis V. Lunev
2015-06-16 12:48 ` Stefan Hajnoczi
2015-06-16 12:57 ` Denis V. Lunev
2015-06-16 14:37 ` Eric Blake
2015-06-16 16:43 ` Denis V. Lunev
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=1430561601-19184-4-git-send-email-den@openvz.org \
--to=den@openvz.org \
--cc=mdroth@linux.vnet.ibm.com \
--cc=okrishtal@parallels.com \
--cc=qemu-devel@nongnu.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).