[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[Qemu-devel] [PATCH v4 5/5] raw-posix: Introduce hdev_is_sg()
From: |
Dimitris Aragiorgis |
Subject: |
[Qemu-devel] [PATCH v4 5/5] raw-posix: Introduce hdev_is_sg() |
Date: |
Wed, 20 May 2015 12:57:39 +0300 |
Until now, an SG device was identified only by checking if its path
started with "/dev/sg". Then, hdev_open() set bs->sg accordingly.
This is very fragile, e.g. it fails with symlinks or relative paths.
We should rely on the actual properties of the device instead of the
specified file path.
Test for an SG device (e.g. /dev/sg0) by ensuring that all of the
following holds:
- The device supports the SG_GET_VERSION_NUM ioctl
- The device supports the SG_GET_SCSI_ID ioctl
- The specified file name corresponds to a character device
Signed-off-by: Dimitris Aragiorgis <address@hidden>
---
block/raw-posix.c | 39 ++++++++++++++++++++++++++++-----------
1 file changed, 28 insertions(+), 11 deletions(-)
diff --git a/block/raw-posix.c b/block/raw-posix.c
index ace228f..d84e5a0 100644
--- a/block/raw-posix.c
+++ b/block/raw-posix.c
@@ -57,6 +57,7 @@
#include <linux/fd.h>
#include <linux/fs.h>
#include <linux/hdreg.h>
+#include <scsi/sg.h>
#ifdef __s390__
#include <asm/dasd.h>
#endif
@@ -2081,15 +2082,38 @@ static void hdev_parse_filename(const char *filename,
QDict *options,
qdict_put_obj(options, "filename", QOBJECT(qstring_from_str(filename)));
}
+static int hdev_is_sg(BlockDriverState *bs)
+{
+
+#if defined(__linux__)
+
+ struct stat st;
+ struct sg_scsi_id scsiid;
+ int sg_version;
+
+ if (!bdrv_ioctl(bs, SG_GET_VERSION_NUM, &sg_version) &&
+ !bdrv_ioctl(bs, SG_GET_SCSI_ID, &scsiid) &&
+ stat(bs->filename, &st) >= 0 && S_ISCHR(st.st_mode)) {
+ DPRINTF("SG device found: type=%d, version=%d\n",
+ scsiid.scsi_type, sg_version);
+ return 1;
+ }
+
+#endif
+
+ return 0;
+}
+
static int hdev_open(BlockDriverState *bs, QDict *options, int flags,
Error **errp)
{
BDRVRawState *s = bs->opaque;
Error *local_err = NULL;
int ret;
- const char *filename = qdict_get_str(options, "filename");
#if defined(__APPLE__) && defined(__MACH__)
+ const char *filename = qdict_get_str(options, "filename");
+
if (strstart(filename, "/dev/cdrom", NULL)) {
kern_return_t kernResult;
io_iterator_t mediaIterator;
@@ -2118,16 +2142,6 @@ static int hdev_open(BlockDriverState *bs, QDict
*options, int flags,
#endif
s->type = FTYPE_FILE;
-#if defined(__linux__)
- {
- char resolved_path[ MAXPATHLEN ], *temp;
-
- temp = realpath(filename, resolved_path);
- if (temp && strstart(temp, "/dev/sg", NULL)) {
- bs->sg = 1;
- }
- }
-#endif
ret = raw_open_common(bs, options, flags, 0, &local_err);
if (ret < 0) {
@@ -2137,6 +2151,9 @@ static int hdev_open(BlockDriverState *bs, QDict
*options, int flags,
return ret;
}
+ /* Since this does ioctl the device must be already opened */
+ bs->sg = hdev_is_sg(bs);
+
if (flags & BDRV_O_RDWR) {
ret = check_hdev_writable(s);
if (ret < 0) {
--
1.7.10.4
- [Qemu-devel] [PATCH v4 0/5] Some fixes related to scsi-generic, Dimitris Aragiorgis, 2015/05/20
- [Qemu-devel] [PATCH v4 4/5] raw-posix: Use DPRINTF for DEBUG_FLOPPY, Dimitris Aragiorgis, 2015/05/20
- [Qemu-devel] [PATCH v4 1/5] block: Use bdrv_is_sg() everywhere, Dimitris Aragiorgis, 2015/05/20
- [Qemu-devel] [PATCH v4 2/5] Fix migration in case of scsi-generic, Dimitris Aragiorgis, 2015/05/20
- [Qemu-devel] [PATCH v4 3/5] raw-posix: DPRINTF instead of DEBUG_BLOCK_PRINT, Dimitris Aragiorgis, 2015/05/20
- [Qemu-devel] [PATCH v4 5/5] raw-posix: Introduce hdev_is_sg(),
Dimitris Aragiorgis <=
- Re: [Qemu-devel] [PATCH v4 0/5] Some fixes related to scsi-generic, Dimitris Aragiorgis, 2015/05/29