#define FTYPE_FILE 0
#define FTYPE_CD 1
+#define FTYPE_HARDDISK 2
typedef struct BDRVRawState {
HANDLE hfile;
s->hfile = CreateFile(filename, access_flags,
FILE_SHARE_READ, NULL,
create_flags, overlapped, NULL);
- if (s->hfile == INVALID_HANDLE_VALUE)
+ if (s->hfile == INVALID_HANDLE_VALUE) {
+ int err = GetLastError();
+
+ if (err == ERROR_ACCESS_DENIED)
+ return -EACCES;
return -1;
+ }
return 0;
}
BDRVRawState *s = bs->opaque;
LARGE_INTEGER l;
ULARGE_INTEGER available, total, total_free;
+ DISK_GEOMETRY dg;
+ DWORD count;
+ BOOL status;
switch(s->type) {
case FTYPE_FILE:
return -EIO;
l.QuadPart = total.QuadPart;
break;
+ case FTYPE_HARDDISK:
+ status = DeviceIoControl(s->hfile, IOCTL_DISK_GET_DRIVE_GEOMETRY,
+ NULL, 0, &dg, sizeof(dg), &count, NULL);
+ if (status != FALSE) {
+ l.QuadPart = dg.Cylinders.QuadPart * dg.TracksPerCylinder
+ * dg.SectorsPerTrack * dg.BytesPerSector;
+ }
+ break;
default:
return -EIO;
}
{
}
-void qemu_aio_flush(void)
-{
-}
-
void qemu_aio_wait_start(void)
{
}
if (strstart(filename, "\\\\.\\", &p) ||
strstart(filename, "//./", &p)) {
+ if (stristart(p, "PhysicalDrive", NULL))
+ return FTYPE_HARDDISK;
snprintf(s->drive_path, sizeof(s->drive_path), "%c:\\", p[0]);
type = GetDriveType(s->drive_path);
if (type == DRIVE_CDROM)
}
}
s->type = find_device_type(bs, filename);
-
+
if ((flags & BDRV_O_ACCESS) == O_RDWR) {
access_flags = GENERIC_READ | GENERIC_WRITE;
} else {
s->hfile = CreateFile(filename, access_flags,
FILE_SHARE_READ, NULL,
create_flags, overlapped, NULL);
- if (s->hfile == INVALID_HANDLE_VALUE)
+ if (s->hfile == INVALID_HANDLE_VALUE) {
+ int err = GetLastError();
+
+ if (err == ERROR_ACCESS_DENIED)
+ return -EACCES;
return -1;
+ }
return 0;
}