Based on a patch by Louis Lenders.
Signed-off-by: Gijs Vermeulen gijsvrm@gmail.com ---
This patchset fixes: https://bugs.winehq.org/show_bug.cgi?id=42577
include/Makefile.in | 1 + include/virtdisk.h | 200 ++++++++++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 201 insertions(+) create mode 100644 include/virtdisk.h
diff --git a/include/Makefile.in b/include/Makefile.in index 78ab095d77..900e326653 100644 --- a/include/Makefile.in +++ b/include/Makefile.in @@ -631,6 +631,7 @@ SOURCES = \ verrsrc.h \ vfw.h \ vfwmsgs.h \ + virtdisk.h \ vmr9.idl \ vmrender.idl \ vss.idl \ diff --git a/include/virtdisk.h b/include/virtdisk.h new file mode 100644 index 0000000000..0e79bf8b2d --- /dev/null +++ b/include/virtdisk.h @@ -0,0 +1,200 @@ +/* + * Copyright 2017 Louis Lenders + * Copyright 2018 Gijs Vermeulen + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA + */ + +#ifndef __WINE_VIRTDISK_DLL_H +#define __WINE_VIRTDISK_DLL_H + +#include <windows.h> + +#ifdef __cplusplus +extern "C" { +#endif + +#define VIRTUAL_STORAGE_TYPE_DEVICE_UNKNOWN 0 +#define VIRTUAL_STORAGE_TYPE_DEVICE_ISO 1 +#define VIRTUAL_STORAGE_TYPE_DEVICE_VHD 2 + +typedef enum _ATTACH_VIRTUAL_DISK_FLAG { + ATTACH_VIRTUAL_DISK_FLAG_NONE = 0x00000000, + ATTACH_VIRTUAL_DISK_FLAG_READ_ONLY = 0x00000001, + ATTACH_VIRTUAL_DISK_FLAG_NO_DRIVE_LETTER = 0x00000002, + ATTACH_VIRTUAL_DISK_FLAG_PERMANENT_LIFETIME = 0x00000004, + ATTACH_VIRTUAL_DISK_FLAG_NO_LOCAL_HOST = 0x00000008 +} ATTACH_VIRTUAL_DISK_FLAG; + +typedef enum _ATTACH_VIRTUAL_DISK_VERSION { + ATTACH_VIRTUAL_DISK_VERSION_UNSPECIFIED = 0, + ATTACH_VIRTUAL_DISK_VERSION_1 = 1 +} ATTACH_VIRTUAL_DISK_VERSION; + +typedef enum _COMPACT_VIRTUAL_DISK_FLAG { + COMPACT_VIRTUAL_DISK_FLAG_NONE = 0x00000000 +} COMPACT_VIRTUAL_DISK_FLAG; + +typedef enum _COMPACT_VIRTUAL_DISK_VERSION { + COMPACT_VIRTUAL_DISK_VERSION_UNSPECIFIED = 0, + COMPACT_VIRTUAL_DISK_VERSION_1 = 1 +} COMPACT_VIRTUAL_DISK_VERSION; + +typedef enum _DEPENDENT_DISK_FLAG +{ + DEPENDENT_DISK_FLAG_NONE = 0x00000000, + DEPENDENT_DISK_FLAG_MULT_BACKING_FILES = 0x00000001, + DEPENDENT_DISK_FLAG_FULLY_ALLOCATED = 0x00000002, + DEPENDENT_DISK_FLAG_READ_ONLY = 0x00000004, + DEPENDENT_DISK_FLAG_REMOTE = 0x00000008, + DEPENDENT_DISK_FLAG_SYSTEM_VOLUME = 0x00000010, + DEPENDENT_DISK_FLAG_SYSTEM_VOLUME_PARENT = 0x00000020, + DEPENDENT_DISK_FLAG_REMOVABLE = 0x00000040, + DEPENDENT_DISK_FLAG_NO_DRIVE_LETTER = 0x00000080, + DEPENDENT_DISK_FLAG_PARENT = 0x00000100, + DEPENDENT_DISK_FLAG_NO_HOST_DISK = 0x00000200, + DEPENDENT_DISK_FLAG_PERMANENT_LIFETIME = 0x00000400 +} DEPENDENT_DISK_FLAG; + +typedef enum _EXPAND_VIRTUAL_DISK_VERSION { + EXPAND_VIRTUAL_DISK_VERSION_UNSPECIFIED = 0, + EXPAND_VIRTUAL_DISK_VERSION_1 = 1 +} EXPAND_VIRTUAL_DISK_VERSION; + +typedef enum _DETACH_VIRTUAL_DISK_FLAG { + DETACH_VIRTUAL_DISK_FLAG_NONE = 0x00000000 +} DETACH_VIRTUAL_DISK_FLAG; + +typedef enum _EXPAND_VIRTUAL_DISK_FLAG { + EXPAND_VIRTUAL_DISK_FLAG_NONE = 0x00000000 +} EXPAND_VIRTUAL_DISK_FLAG; + +typedef enum _GET_STORAGE_DEPENDENCY_FLAG +{ + GET_STORAGE_DEPENDENCY_FLAG_NONE = 0x00000000, + GET_STORAGE_DEPENDENCY_FLAG_HOST_VOLUMES = 0x00000001, + GET_STORAGE_DEPENDENCY_FLAG_DISK_HANDLE = 0x00000002 +} GET_STORAGE_DEPENDENCY_FLAG; + +typedef enum _MIRROR_VIRTUAL_DISK_FLAG { + MIRROR_VIRTUAL_DISK_FLAG_NONE = 0x00000000, + MIRROR_VIRTUAL_DISK_FLAG_EXISTING_FILE = 0x00000001 +} MIRROR_VIRTUAL_DISK_FLAG; + +typedef enum _MIRROR_VIRTUAL_DISK_VERSION { + MIRROR_VIRTUAL_DISK_VERSION_UNSPECIFIED = 0, + MIRROR_VIRTUAL_DISK_VERSION_1 = 1 +} MIRROR_VIRTUAL_DISK_VERSION; + +typedef enum _MERGE_VIRTUAL_DISK_FLAG { + MERGE_VIRTUAL_DISK_FLAG_NONE = 0x00000000 +} MERGE_VIRTUAL_DISK_FLAG; + +typedef enum _STORAGE_DEPENDENCY_INFO_VERSION +{ + STORAGE_DEPENDENCY_INFO_VERSION_UNSPECIFIED = 0x0, + STORAGE_DEPENDENCY_INFO_VERSION_1 = 0x1, + STORAGE_DEPENDENCY_INFO_VERSION_2 = 0x2 +} STORAGE_DEPENDENCY_INFO_VERSION; + +typedef enum _VIRTUAL_DISK_ACCESS_MASK { + VIRTUAL_DISK_ACCESS_NONE = 0x00000000, + VIRTUAL_DISK_ACCESS_ATTACH_RO = 0x00010000, + VIRTUAL_DISK_ACCESS_ATTACH_RW = 0x00020000, + VIRTUAL_DISK_ACCESS_DETACH = 0x00040000, + VIRTUAL_DISK_ACCESS_GET_INFO = 0x00080000, + VIRTUAL_DISK_ACCESS_CREATE = 0x00100000, + VIRTUAL_DISK_ACCESS_METAOPS = 0x00200000, + VIRTUAL_DISK_ACCESS_READ = 0x000d0000, + VIRTUAL_DISK_ACCESS_ALL = 0x003f0000, + VIRTUAL_DISK_ACCESS_WRITABLE = 0x00320000 +} VIRTUAL_DISK_ACCESS_MASK; + +typedef struct _VIRTUAL_STORAGE_TYPE +{ + ULONG DeviceId; + GUID VendorId; +} VIRTUAL_STORAGE_TYPE, *PVIRTUAL_STORAGE_TYPE; + +typedef struct _ATTACH_VIRTUAL_DISK_PARAMETERS { + ATTACH_VIRTUAL_DISK_VERSION Version; + __C89_NAMELESS union { + struct { + ULONG Reserved; + } Version1; + } DUMMYUNIONNAME; +} ATTACH_VIRTUAL_DISK_PARAMETERS, *PATTACH_VIRTUAL_DISK_PARAMETERS; + +typedef struct _COMPACT_VIRTUAL_DISK_PARAMETERS { + COMPACT_VIRTUAL_DISK_VERSION Version; + __C89_NAMELESS union { + struct { + ULONG Reserved; + } Version1; + } DUMMYUNIONNAME; +} COMPACT_VIRTUAL_DISK_PARAMETERS, *PCOMPACT_VIRTUAL_DISK_PARAMETERS; + +typedef struct _EXPAND_VIRTUAL_DISK_PARAMETERS { + EXPAND_VIRTUAL_DISK_VERSION Version; + __C89_NAMELESS union { + struct { + ULONGLONG NewSize; + } Version1; + } DUMMYUNIONNAME; +} EXPAND_VIRTUAL_DISK_PARAMETERS, *PEXPAND_VIRTUAL_DISK_PARAMETERS; + +typedef struct _STORAGE_DEPENDENCY_INFO_TYPE_1 +{ + DEPENDENT_DISK_FLAG DependencyTypeFlags; + ULONG ProviderSpecificFlags; + VIRTUAL_STORAGE_TYPE VirtualStorageType; +} STORAGE_DEPENDENCY_INFO_TYPE_1, *PSTORAGE_DEPENDENCY_INFO_TYPE_1; + +typedef struct _STORAGE_DEPENDENCY_INFO_TYPE_2 +{ + DEPENDENT_DISK_FLAG DependencyTypeFlags; + ULONG ProviderSpecificFlags; + VIRTUAL_STORAGE_TYPE VirtualStorageType; + ULONG AncestorLevel; + PWSTR DependencyDeviceName; + PWSTR HostVolumeName; + PWSTR DependentVolumeName; + PWSTR DependentVolumeRelativePath; +} STORAGE_DEPENDENCY_INFO_TYPE_2, *PSTORAGE_DEPENDENCY_INFO_TYPE_2; + +typedef struct _STORAGE_DEPENDENCY_INFO +{ + STORAGE_DEPENDENCY_INFO_VERSION Version; + ULONG NumberEntries; + __C89_NAMELESS union + { + STORAGE_DEPENDENCY_INFO_TYPE_1 Version1Entries[1]; + STORAGE_DEPENDENCY_INFO_TYPE_2 Version2Entries[1]; + } __C89_NAMELESSUNIONNAME; +} STORAGE_DEPENDENCY_INFO, *PSTORAGE_DEPENDENCY_INFO; + +typedef struct _VIRTUAL_DISK_PROGRESS { + DWORD OperationStatus; + ULONGLONG CurrentValue; + ULONGLONG CompletionValue; +} VIRTUAL_DISK_PROGRESS, *PVIRTUAL_DISK_PROGRESS; + +DWORD WINAPI GetStorageDependencyInformation(HANDLE obj, GET_STORAGE_DEPENDENCY_FLAG flags, ULONG size, STORAGE_DEPENDENCY_INFO *info, ULONG *used); + +#ifdef __cplusplus +} +#endif + +#endif /* __WINE_VIRTDISK_DLL_H */
From: Michael Müller michael@fds-team.de
Signed-off-by: Gijs Vermeulen gijsvrm@gmail.com ---
Changed return value when function gets passed invalid parameter values. Original staging patch returned ERROR_SUCCESS, but tests show that ERROR_INVALID_PARAMETER is the correct value.
dlls/virtdisk/virtdisk.spec | 2 +- dlls/virtdisk/virtdisk_main.c | 19 +++++++++++++++++++ 2 files changed, 20 insertions(+), 1 deletion(-)
diff --git a/dlls/virtdisk/virtdisk.spec b/dlls/virtdisk/virtdisk.spec index 2946b66d50..6bd5f146db 100644 --- a/dlls/virtdisk/virtdisk.spec +++ b/dlls/virtdisk/virtdisk.spec @@ -8,7 +8,7 @@ @ stub EnumerateVirtualDiskMetadata @ stub ExpandVirtualDisk @ stub GetAllAttachedVirtualDiskPhysicalPaths -@ stub GetStorageDependencyInformation +@ stdcall GetStorageDependencyInformation(long long long ptr ptr) @ stub GetVirtualDiskInformation @ stub GetVirtualDiskMetadata @ stub GetVirtualDiskOperationProgress diff --git a/dlls/virtdisk/virtdisk_main.c b/dlls/virtdisk/virtdisk_main.c index 0da0dca461..0f13404b76 100644 --- a/dlls/virtdisk/virtdisk_main.c +++ b/dlls/virtdisk/virtdisk_main.c @@ -22,6 +22,8 @@
#include "windef.h" #include "winbase.h" +#include "virtdisk.h" + #include "wine/debug.h"
WINE_DEFAULT_DEBUG_CHANNEL(virtdisk); @@ -44,3 +46,20 @@ BOOL WINAPI DllMain(HINSTANCE hinst, DWORD reason, void *reserved)
return TRUE; } + +DWORD WINAPI GetStorageDependencyInformation(HANDLE obj, GET_STORAGE_DEPENDENCY_FLAG flags, ULONG size, STORAGE_DEPENDENCY_INFO *info, ULONG *used) +{ + FIXME("(%p, 0x%x, %u, %p, %p): stub\n", obj, flags, size, info, used); + + if (used) *used = sizeof(STORAGE_DEPENDENCY_INFO); + + if (!info || !size) + return ERROR_INVALID_PARAMETER; + + if (size < sizeof(STORAGE_DEPENDENCY_INFO)) + return ERROR_INSUFFICIENT_BUFFER; + + info->NumberEntries = 0; + + return ERROR_SUCCESS; +}
Signed-off-by: Gijs Vermeulen gijsvrm@gmail.com --- configure | 1 + configure.ac | 1 + dlls/virtdisk/tests/Makefile.in | 4 +++ dlls/virtdisk/tests/virtdisk.c | 61 +++++++++++++++++++++++++++++++++++++++++ 4 files changed, 67 insertions(+) create mode 100644 dlls/virtdisk/tests/Makefile.in create mode 100644 dlls/virtdisk/tests/virtdisk.c
diff --git a/configure b/configure index 2960b34c93..9240ec8966 100755 --- a/configure +++ b/configure @@ -19213,6 +19213,7 @@ wine_fn_config_makefile dlls/ver.dll16 enable_win16 wine_fn_config_makefile dlls/version enable_version wine_fn_config_makefile dlls/version/tests enable_tests wine_fn_config_makefile dlls/virtdisk enable_virtdisk +wine_fn_config_makefile dlls/virtdisk/tests enable_tests wine_fn_config_makefile dlls/vmm.vxd enable_win16 wine_fn_config_makefile dlls/vnbt.vxd enable_win16 wine_fn_config_makefile dlls/vnetbios.vxd enable_win16 diff --git a/configure.ac b/configure.ac index 3a6a3a1762..4eec8aa52a 100644 --- a/configure.ac +++ b/configure.ac @@ -3715,6 +3715,7 @@ WINE_CONFIG_MAKEFILE(dlls/ver.dll16,enable_win16) WINE_CONFIG_MAKEFILE(dlls/version) WINE_CONFIG_MAKEFILE(dlls/version/tests) WINE_CONFIG_MAKEFILE(dlls/virtdisk) +WINE_CONFIG_MAKEFILE(dlls/virtdisk/tests) WINE_CONFIG_MAKEFILE(dlls/vmm.vxd,enable_win16) WINE_CONFIG_MAKEFILE(dlls/vnbt.vxd,enable_win16) WINE_CONFIG_MAKEFILE(dlls/vnetbios.vxd,enable_win16) diff --git a/dlls/virtdisk/tests/Makefile.in b/dlls/virtdisk/tests/Makefile.in new file mode 100644 index 0000000000..d0557cb08d --- /dev/null +++ b/dlls/virtdisk/tests/Makefile.in @@ -0,0 +1,4 @@ +TESTDLL = virtdisk.dll + +C_SRCS = \ + virtdisk.c diff --git a/dlls/virtdisk/tests/virtdisk.c b/dlls/virtdisk/tests/virtdisk.c new file mode 100644 index 0000000000..f64a69cb7f --- /dev/null +++ b/dlls/virtdisk/tests/virtdisk.c @@ -0,0 +1,61 @@ +/* + * Copyright 2018 Gijs Vermeulen + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA + */ + +#include "virtdisk.h" +#include "wine/test.h" + +static DWORD (WINAPI *pGetStorageDependencyInformation)(HANDLE,GET_STORAGE_DEPENDENCY_FLAG,ULONG,STORAGE_DEPENDENCY_INFO*,ULONG*); + +static void test_GetStorageDependencyInformation(void) +{ + DWORD ret; + HANDLE handle; + STORAGE_DEPENDENCY_INFO *info; + ULONG size; + + handle = CreateFileA("C:", 0, 0, NULL, OPEN_EXISTING, FILE_FLAG_BACKUP_SEMANTICS, 0); + ok(handle != NULL, "Expected a handle\n"); + + size = sizeof(STORAGE_DEPENDENCY_INFO); + info = HeapAlloc(GetProcessHeap(), 0, size); + + ret = pGetStorageDependencyInformation(handle, GET_STORAGE_DEPENDENCY_FLAG_DISK_HANDLE, 0, info, 0); + ok(ret == ERROR_INVALID_PARAMETER, "Expected ERROR_INVALID_PARAMETER, got %d\n", ret); + + ret = pGetStorageDependencyInformation(handle, GET_STORAGE_DEPENDENCY_FLAG_DISK_HANDLE, size, NULL, 0); + ok(ret == ERROR_INVALID_PARAMETER, "Expected ERROR_INVALID_PARAMETER, got %d\n", ret); + + HeapFree(GetProcessHeap(), 0, info); + CloseHandle(handle); +} + +START_TEST(virtdisk) +{ + HMODULE module = LoadLibraryA("virtdisk.dll"); + if(!module) + { + win_skip("virtdisk.dll not installed\n"); + return; + } + + pGetStorageDependencyInformation = (void *)GetProcAddress( module, "GetStorageDependencyInformation" ); + if (pGetStorageDependencyInformation) + test_GetStorageDependencyInformation(); + else + win_skip("GetStorageDependencyInformation is not available\n"); +}
Gijs Vermeulen gijsvrm@gmail.com writes:
+static void test_GetStorageDependencyInformation(void) +{
- DWORD ret;
- HANDLE handle;
- STORAGE_DEPENDENCY_INFO *info;
- ULONG size;
- handle = CreateFileA("C:", 0, 0, NULL, OPEN_EXISTING, FILE_FLAG_BACKUP_SEMANTICS, 0);
- ok(handle != NULL, "Expected a handle\n");
CreateFileA returns INVALID_HANDLE_VALUE on error.
Gijs Vermeulen gijsvrm@gmail.com writes:
+typedef struct _STORAGE_DEPENDENCY_INFO +{
- STORAGE_DEPENDENCY_INFO_VERSION Version;
- ULONG NumberEntries;
- __C89_NAMELESS union
- {
STORAGE_DEPENDENCY_INFO_TYPE_1 Version1Entries[1];
STORAGE_DEPENDENCY_INFO_TYPE_2 Version2Entries[1];
- } __C89_NAMELESSUNIONNAME;
+} STORAGE_DEPENDENCY_INFO, *PSTORAGE_DEPENDENCY_INFO;
This doesn't match the Windows definition and is going to yield the wrong size for the structure.
On Mon, May 28, 2018 at 1:55 PM Gijs Vermeulen gijsvrm@gmail.com wrote:
- PWSTR DependencyDeviceName;
- PWSTR HostVolumeName;
- PWSTR DependentVolumeName;
- PWSTR DependentVolumeRelativePath;
WCHAR * is generally preferred over PWSTR.
-Alex
Alex Henrie alexhenrie24@gmail.com wrote:
On Mon, May 28, 2018 at 1:55 PM Gijs Vermeulen gijsvrm@gmail.com wrote:
- PWSTR DependencyDeviceName;
- PWSTR HostVolumeName;
- PWSTR DependentVolumeName;
- PWSTR DependentVolumeRelativePath;
WCHAR * is generally preferred over PWSTR.
In the public headers it's strongly advised to follow the PSDK types, otherwise compiling with Wine headers may either lead to unpredictable debug information in PE builds or warnings in C++.
On Tue, May 29, 2018 at 8:57 PM Dmitry Timoshkov dmitry@baikal.ru wrote:
Alex Henrie alexhenrie24@gmail.com wrote:
On Mon, May 28, 2018 at 1:55 PM Gijs Vermeulen gijsvrm@gmail.com
wrote:
- PWSTR DependencyDeviceName;
- PWSTR HostVolumeName;
- PWSTR DependentVolumeName;
- PWSTR DependentVolumeRelativePath;
WCHAR * is generally preferred over PWSTR.
In the public headers it's strongly advised to follow the PSDK types, otherwise compiling with Wine headers may either lead to unpredictable debug information in PE builds or warnings in C++.
Why would the compiler warn about using versus not using a typedef? Can you provide a minimal C++ program that would trigger such a warning?
-Alex
Alex Henrie alexhenrie24@gmail.com wrote:
WCHAR * is generally preferred over PWSTR.
In the public headers it's strongly advised to follow the PSDK types, otherwise compiling with Wine headers may either lead to unpredictable debug information in PE builds or warnings in C++.
Why would the compiler warn about using versus not using a typedef? Can you provide a minimal C++ program that would trigger such a warning?
Probably not in this particular case, but it's still stands that following the PSDK types should be the best way of defining things in a public header.