mirror of
https://github.com/pbatard/rufus.git
synced 2024-08-14 23:57:05 +00:00
[core] invoke VDS to delete all partitions before format/write
This commit is contained in:
parent
7745edbb92
commit
c0526b3e8b
6 changed files with 397 additions and 17 deletions
|
@ -2,6 +2,7 @@ o Version 3.4 (2018.12.??)
|
||||||
Set the default image selection directory to Downloads\ instead of My Documents\
|
Set the default image selection directory to Downloads\ instead of My Documents\
|
||||||
Add ARM/ARM64 automatic update support
|
Add ARM/ARM64 automatic update support
|
||||||
Improve UEFI:NTFS compatibility
|
Improve UEFI:NTFS compatibility
|
||||||
|
Improve access issues by using VDS to delete all partitions
|
||||||
Update the .appx to include all architectures as well as request elevation
|
Update the .appx to include all architectures as well as request elevation
|
||||||
Fix broken detection of some EFI based images
|
Fix broken detection of some EFI based images
|
||||||
Fix broken update check due to new server
|
Fix broken update check due to new server
|
||||||
|
|
226
src/drive.c
226
src/drive.c
|
@ -26,6 +26,10 @@
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
#include <ctype.h>
|
#include <ctype.h>
|
||||||
#include <assert.h>
|
#include <assert.h>
|
||||||
|
#if !defined(__MINGW32__)
|
||||||
|
#include <initguid.h>
|
||||||
|
#endif
|
||||||
|
#include <vds.h>
|
||||||
|
|
||||||
#include "rufus.h"
|
#include "rufus.h"
|
||||||
#include "missing.h"
|
#include "missing.h"
|
||||||
|
@ -54,6 +58,16 @@ const GUID PARTITION_SYSTEM_GUID =
|
||||||
{ 0xc12a7328L, 0xf81f, 0x11d2, {0xba, 0x4b, 0x00, 0xa0, 0xc9, 0x3e, 0xc9, 0x3b} };
|
{ 0xc12a7328L, 0xf81f, 0x11d2, {0xba, 0x4b, 0x00, 0xa0, 0xc9, 0x3e, 0xc9, 0x3b} };
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#if defined(__MINGW32__)
|
||||||
|
const IID CLSID_VdsLoader = { 0x9c38ed61, 0xd565, 0x4728, { 0xae, 0xee, 0xc8, 0x09, 0x52, 0xf0, 0xec, 0xde } };
|
||||||
|
const IID IID_IVdsServiceLoader = { 0xe0393303, 0x90d4, 0x4a97, { 0xab, 0x71, 0xe9, 0xb6, 0x71, 0xee, 0x27, 0x29 } };
|
||||||
|
const IID IID_IVdsProvider = { 0x10c5e575, 0x7984, 0x4e81, { 0xa5, 0x6b, 0x43, 0x1f, 0x5f, 0x92, 0xae, 0x42 } };
|
||||||
|
const IID IID_IVdsSwProvider = { 0x9aa58360, 0xce33, 0x4f92, { 0xb6, 0x58, 0xed, 0x24, 0xb1, 0x44, 0x25, 0xb8 } };
|
||||||
|
const IID IID_IVdsPack = { 0x3b69d7f5, 0x9d94, 0x4648, { 0x91, 0xca, 0x79, 0x93, 0x9b, 0xa2, 0x63, 0xbf } };
|
||||||
|
const IID IID_IVdsDisk = { 0x07e5c822, 0xf00c, 0x47a1, { 0x8f, 0xce, 0xb2, 0x44, 0xda, 0x56, 0xfd, 0x06 } };
|
||||||
|
const IID IID_IVdsAdvancedDisk = { 0x6e6f6b40, 0x977c, 0x4069, { 0xbd, 0xdd, 0xac, 0x71, 0x00, 0x59, 0xf8, 0xc0 } };
|
||||||
|
#endif
|
||||||
|
|
||||||
PF_TYPE_DECL(NTAPI, NTSTATUS, NtQueryVolumeInformationFile, (HANDLE, PIO_STATUS_BLOCK, PVOID, ULONG, FS_INFORMATION_CLASS));
|
PF_TYPE_DECL(NTAPI, NTSTATUS, NtQueryVolumeInformationFile, (HANDLE, PIO_STATUS_BLOCK, PVOID, ULONG, FS_INFORMATION_CLASS));
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
@ -112,6 +126,7 @@ BOOL GetAutoMount(BOOL* enabled)
|
||||||
* the specific range [DRIVE_INDEX_MIN; DRIVE_INDEX_MAX].
|
* the specific range [DRIVE_INDEX_MIN; DRIVE_INDEX_MAX].
|
||||||
*/
|
*/
|
||||||
#define CheckDriveIndex(DriveIndex) do { \
|
#define CheckDriveIndex(DriveIndex) do { \
|
||||||
|
if ((int)DriveIndex < 0) goto out; \
|
||||||
assert((DriveIndex >= DRIVE_INDEX_MIN) && (DriveIndex <= DRIVE_INDEX_MAX)); \
|
assert((DriveIndex >= DRIVE_INDEX_MIN) && (DriveIndex <= DRIVE_INDEX_MAX)); \
|
||||||
if ((DriveIndex < DRIVE_INDEX_MIN) || (DriveIndex > DRIVE_INDEX_MAX)) goto out; \
|
if ((DriveIndex < DRIVE_INDEX_MIN) || (DriveIndex > DRIVE_INDEX_MAX)) goto out; \
|
||||||
DriveIndex -= DRIVE_INDEX_MIN; } while (0)
|
DriveIndex -= DRIVE_INDEX_MIN; } while (0)
|
||||||
|
@ -175,7 +190,6 @@ static HANDLE GetHandle(char* Path, BOOL bLockDrive, BOOL bWriteAccess, BOOL bWr
|
||||||
uprintf("I/O boundary checks disabled");
|
uprintf("I/O boundary checks disabled");
|
||||||
}
|
}
|
||||||
|
|
||||||
uprintf("Requesting lock...");
|
|
||||||
EndTime = GetTickCount64() + DRIVE_ACCESS_TIMEOUT;
|
EndTime = GetTickCount64() + DRIVE_ACCESS_TIMEOUT;
|
||||||
do {
|
do {
|
||||||
if (DeviceIoControl(hDrive, FSCTL_LOCK_VOLUME, NULL, 0, NULL, 0, &size, NULL))
|
if (DeviceIoControl(hDrive, FSCTL_LOCK_VOLUME, NULL, 0, NULL, 0, &size, NULL))
|
||||||
|
@ -208,7 +222,7 @@ char* GetPhysicalName(DWORD DriveIndex)
|
||||||
char physical_name[24];
|
char physical_name[24];
|
||||||
|
|
||||||
CheckDriveIndex(DriveIndex);
|
CheckDriveIndex(DriveIndex);
|
||||||
static_sprintf(physical_name, "\\\\.\\PHYSICALDRIVE%lu", DriveIndex);
|
static_sprintf(physical_name, "\\\\.\\PhysicalDrive%lu", DriveIndex);
|
||||||
success = TRUE;
|
success = TRUE;
|
||||||
out:
|
out:
|
||||||
return (success)?safe_strdup(physical_name):NULL;
|
return (success)?safe_strdup(physical_name):NULL;
|
||||||
|
@ -247,7 +261,7 @@ char* GetLogicalName(DWORD DriveIndex, BOOL bKeepTrailingBackslash, BOOL bSilent
|
||||||
|
|
||||||
CheckDriveIndex(DriveIndex);
|
CheckDriveIndex(DriveIndex);
|
||||||
|
|
||||||
for (i=0; hDrive == INVALID_HANDLE_VALUE; i++) {
|
for (i = 0; hDrive == INVALID_HANDLE_VALUE; i++) {
|
||||||
if (i == 0) {
|
if (i == 0) {
|
||||||
hVolume = FindFirstVolumeA(volume_name, sizeof(volume_name));
|
hVolume = FindFirstVolumeA(volume_name, sizeof(volume_name));
|
||||||
if (hVolume == INVALID_HANDLE_VALUE) {
|
if (hVolume == INVALID_HANDLE_VALUE) {
|
||||||
|
@ -265,10 +279,9 @@ char* GetLogicalName(DWORD DriveIndex, BOOL bKeepTrailingBackslash, BOOL bSilent
|
||||||
|
|
||||||
// Sanity checks
|
// Sanity checks
|
||||||
len = safe_strlen(volume_name);
|
len = safe_strlen(volume_name);
|
||||||
if ((len <= 1) || (safe_strnicmp(volume_name, volume_start, 4) != 0) || (volume_name[len-1] != '\\')) {
|
assert(len > 4);
|
||||||
suprintf("'%s' is not a GUID volume name", volume_name);
|
assert(safe_strnicmp(volume_name, volume_start, 4) == 0);
|
||||||
continue;
|
assert(volume_name[len - 1] == '\\');
|
||||||
}
|
|
||||||
|
|
||||||
drive_type = GetDriveTypeA(volume_name);
|
drive_type = GetDriveTypeA(volume_name);
|
||||||
if ((drive_type != DRIVE_REMOVABLE) && (drive_type != DRIVE_FIXED))
|
if ((drive_type != DRIVE_REMOVABLE) && (drive_type != DRIVE_FIXED))
|
||||||
|
@ -316,6 +329,205 @@ out:
|
||||||
return (success)?safe_strdup(volume_name):NULL;
|
return (success)?safe_strdup(volume_name):NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Delete all the partitions from a disk, using VDS
|
||||||
|
* Mostly copied from https://social.msdn.microsoft.com/Forums/vstudio/en-US/b90482ae-4e44-4b08-8731-81915030b32a/createpartition-using-vds-interface-throw-error-enointerface-dcom?forum=vcgeneral
|
||||||
|
*/
|
||||||
|
BOOL DeletePartitions(DWORD DriveIndex)
|
||||||
|
{
|
||||||
|
BOOL r = FALSE;
|
||||||
|
HRESULT hr;
|
||||||
|
ULONG ulFetched;
|
||||||
|
wchar_t wPhysicalName[24];
|
||||||
|
IVdsServiceLoader *pLoader;
|
||||||
|
IVdsService *pService;
|
||||||
|
IEnumVdsObject *pEnum;
|
||||||
|
IUnknown *pUnk;
|
||||||
|
|
||||||
|
CheckDriveIndex(DriveIndex);
|
||||||
|
wnsprintf(wPhysicalName, ARRAYSIZE(wPhysicalName), L"\\\\?\\PhysicalDrive%lu", DriveIndex);
|
||||||
|
|
||||||
|
// Initialize COM
|
||||||
|
IGNORE_RETVAL(CoInitializeEx(NULL, COINIT_APARTMENTTHREADED));
|
||||||
|
IGNORE_RETVAL(CoInitializeSecurity(NULL, -1, NULL, NULL, RPC_C_AUTHN_LEVEL_CONNECT,
|
||||||
|
RPC_C_IMP_LEVEL_IMPERSONATE, NULL, 0, NULL));
|
||||||
|
|
||||||
|
// Create a VDS Loader Instance
|
||||||
|
hr = CoCreateInstance(&CLSID_VdsLoader, NULL, CLSCTX_LOCAL_SERVER | CLSCTX_REMOTE_SERVER,
|
||||||
|
&IID_IVdsServiceLoader, (void **)&pLoader);
|
||||||
|
if (hr != S_OK) {
|
||||||
|
uprintf("Could not create VDS Loader Instance: hr=%X\n", hr);
|
||||||
|
goto out;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Load the VDS Service
|
||||||
|
hr = IVdsServiceLoader_LoadService(pLoader, L"", &pService);
|
||||||
|
IVdsServiceLoader_Release(pLoader);
|
||||||
|
if (hr != S_OK) {
|
||||||
|
uprintf("Could not load VDS Service: 0x%08X", hr);
|
||||||
|
goto out;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Query the VDS Service Providers
|
||||||
|
hr = IVdsService_QueryProviders(pService, VDS_QUERY_SOFTWARE_PROVIDERS, &pEnum);
|
||||||
|
if (hr != S_OK) {
|
||||||
|
uprintf("Could not query VDS Service Providers: 0x%08X", hr);
|
||||||
|
goto out;
|
||||||
|
}
|
||||||
|
|
||||||
|
while (IEnumVdsObject_Next(pEnum, 1, &pUnk, &ulFetched) == S_OK) {
|
||||||
|
IVdsProvider *pProvider;
|
||||||
|
IVdsSwProvider *pSwProvider;
|
||||||
|
IEnumVdsObject *pEnumPack;
|
||||||
|
IUnknown *pPackUnk;
|
||||||
|
|
||||||
|
// Get VDS Provider
|
||||||
|
hr = IUnknown_QueryInterface(pUnk, &IID_IVdsProvider, (void **)&pProvider);
|
||||||
|
IUnknown_Release(pUnk);
|
||||||
|
if (hr != S_OK) {
|
||||||
|
uprintf("Could not get VDS Provider: 0x%08X", hr);
|
||||||
|
goto out;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Get VDS Software Provider
|
||||||
|
hr = IVdsSwProvider_QueryInterface(pProvider, &IID_IVdsSwProvider, (void **)&pSwProvider);
|
||||||
|
IVdsProvider_Release(pProvider);
|
||||||
|
if (hr != S_OK) {
|
||||||
|
uprintf("Could not get VDS Software Provider: 0x%08X", hr);
|
||||||
|
goto out;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Get VDS Software Provider Packs
|
||||||
|
hr = IVdsSwProvider_QueryPacks(pSwProvider, &pEnumPack);
|
||||||
|
IVdsSwProvider_Release(pSwProvider);
|
||||||
|
if (hr != S_OK) {
|
||||||
|
uprintf("Could not get VDS Software Provider Packs: 0x%08X", hr);
|
||||||
|
goto out;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Enumerate Provider Packs
|
||||||
|
while (IEnumVdsObject_Next(pEnumPack, 1, &pPackUnk, &ulFetched) == S_OK) {
|
||||||
|
IVdsPack *pPack;
|
||||||
|
IEnumVdsObject *pEnumDisk;
|
||||||
|
IUnknown *pDiskUnk;
|
||||||
|
|
||||||
|
hr = IUnknown_QueryInterface(pPackUnk, &IID_IVdsPack, (void **)&pPack);
|
||||||
|
IUnknown_Release(pPackUnk);
|
||||||
|
if (hr != S_OK) {
|
||||||
|
uprintf("Could not query VDS Software Provider Pack: 0x%08X", hr);
|
||||||
|
goto out;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Use the pack interface to access the disks
|
||||||
|
hr = IVdsPack_QueryDisks(pPack, &pEnumDisk);
|
||||||
|
if (hr != S_OK) {
|
||||||
|
uprintf("Could not query VDS disks: 0x%08X", hr);
|
||||||
|
goto out;
|
||||||
|
}
|
||||||
|
|
||||||
|
// List disks
|
||||||
|
while (IEnumVdsObject_Next(pEnumDisk, 1, &pDiskUnk, &ulFetched) == S_OK) {
|
||||||
|
VDS_DISK_PROP diskprop;
|
||||||
|
VDS_PARTITION_PROP* prop_array;
|
||||||
|
LONG i, prop_array_size;
|
||||||
|
IVdsDisk *pDisk;
|
||||||
|
IVdsAdvancedDisk *pAdvancedDisk;
|
||||||
|
|
||||||
|
// Get the disk interface.
|
||||||
|
hr = IUnknown_QueryInterface(pDiskUnk, &IID_IVdsDisk, (void **)&pDisk);
|
||||||
|
if (hr != S_OK) {
|
||||||
|
uprintf("Could not query VDS Disk Interface: 0x%08X", hr);
|
||||||
|
goto out;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Get the disk properties
|
||||||
|
hr = IVdsDisk_GetProperties(pDisk, &diskprop);
|
||||||
|
if (hr != S_OK) {
|
||||||
|
uprintf("Could not query VDS Disk Properties: 0x%08X", hr);
|
||||||
|
goto out;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Isolate the disk we want
|
||||||
|
if (_wcsicmp(wPhysicalName, diskprop.pwszName) != 0) {
|
||||||
|
IVdsDisk_Release(pDisk);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Instantiate the AdvanceDisk interface for our disk.
|
||||||
|
hr = IVdsDisk_QueryInterface(pDisk, &IID_IVdsAdvancedDisk, (void **)&pAdvancedDisk);
|
||||||
|
IVdsDisk_Release(pDisk);
|
||||||
|
if (hr != S_OK) {
|
||||||
|
uprintf("Could not access VDS Advanced Disk interface: 0x%08X", hr);
|
||||||
|
goto out;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Query the partition data, so we can get the start offset, which we need for deletion
|
||||||
|
hr = IVdsAdvancedDisk_QueryPartitions(pAdvancedDisk, &prop_array, &prop_array_size);
|
||||||
|
if (hr != S_OK) {
|
||||||
|
uprintf("No partition to delete on disk '%ws'", diskprop.pwszName);
|
||||||
|
goto out;
|
||||||
|
}
|
||||||
|
|
||||||
|
uprintf("Deleting ALL partitions from disk '%ws':", diskprop.pwszName);
|
||||||
|
|
||||||
|
// Now go through each partition
|
||||||
|
r = (prop_array_size >= 1);
|
||||||
|
for (i = 0; i < prop_array_size; i++) {
|
||||||
|
uprintf("● Partition %d (offset: %lld, size: %s)", prop_array[i].ulPartitionNumber,
|
||||||
|
prop_array[i].ullOffset, SizeToHumanReadable(prop_array[i].ullSize, FALSE, FALSE));
|
||||||
|
hr = IVdsAdvancedDisk_DeletePartition(pAdvancedDisk, prop_array[i].ullOffset, TRUE, TRUE);
|
||||||
|
if (hr != S_OK) {
|
||||||
|
r = FALSE;
|
||||||
|
uprintf("Could not delete partitions: 0x%08X", hr);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
CoTaskMemFree(prop_array);
|
||||||
|
|
||||||
|
// NB: In the future, we could try something like this to format partitions:
|
||||||
|
#if 0
|
||||||
|
// Initiate formatting and wait for completion.
|
||||||
|
LPWSTR pwszLabel[8] = L"TEST";
|
||||||
|
ULONGLONG Offset = 1024 * 1024;
|
||||||
|
BOOL QuickFormat = TRUE;
|
||||||
|
BOOL EnableCompression = FALSE;
|
||||||
|
IVdsAsync* pAsync;
|
||||||
|
hr = IVdsAdvancedDisk_FormatPartition(pAdvancedDisk, Offset, FileSystemType,
|
||||||
|
pwszLabel, 0, TRUE, QuickFormat, EnableCompression, &pAsync);
|
||||||
|
if (hr != S_OK) {
|
||||||
|
uprintf("Could not start formatting: 0x%08X", hr);
|
||||||
|
goto out;
|
||||||
|
}
|
||||||
|
VDS_ASYNC_OUTPUT AsyncOut;
|
||||||
|
ULONG ulPercentCompleted;
|
||||||
|
HRESULT hr2 = E_FAIL;
|
||||||
|
do {
|
||||||
|
hr = IVdsAsync_QueryStatus(pAsync, &hr2, &ulPercentCompleted);
|
||||||
|
if (SUCCEEDED(hr)) {
|
||||||
|
printf("%ld%%", ulPercentCompleted);
|
||||||
|
if ((hr2 != S_OK) && (hr2 != VDS_E_OPERATION_PENDING)) {
|
||||||
|
uprintf("hr2: %X", hr2);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
if (hr2 == S_OK) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
Sleep(500);
|
||||||
|
} while (SUCCEEDED(hr));
|
||||||
|
hr = IVdsAsync_Wait(pAsync, &hr2, &AsyncOut);
|
||||||
|
IVdsAsync_Release(pAsync);
|
||||||
|
#endif
|
||||||
|
IVdsAdvancedDisk_Release(pAdvancedDisk);
|
||||||
|
goto out;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
out:
|
||||||
|
return r;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
/* Wait for a logical drive to reappear - Used when a drive has just been repartitioned */
|
/* Wait for a logical drive to reappear - Used when a drive has just been repartitioned */
|
||||||
BOOL WaitForLogical(DWORD DriveIndex)
|
BOOL WaitForLogical(DWORD DriveIndex)
|
||||||
{
|
{
|
||||||
|
|
154
src/drive.h
154
src/drive.h
|
@ -73,6 +73,159 @@ typedef struct _FILE_FS_DEVICE_INFORMATION {
|
||||||
DEVICE_TYPE DeviceType;
|
DEVICE_TYPE DeviceType;
|
||||||
ULONG Characteristics;
|
ULONG Characteristics;
|
||||||
} FILE_FS_DEVICE_INFORMATION, *PFILE_FS_DEVICE_INFORMATION;
|
} FILE_FS_DEVICE_INFORMATION, *PFILE_FS_DEVICE_INFORMATION;
|
||||||
|
#else
|
||||||
|
/* MinGW is currently missing all the VDS COM stuff */
|
||||||
|
#include <vds.h>
|
||||||
|
typedef interface IVdsServiceLoader IVdsServiceLoader;
|
||||||
|
typedef interface IVdsService IVdsService;
|
||||||
|
typedef interface IVdsProvider IVdsProvider;
|
||||||
|
typedef interface IVdsSwProvider IVdsSwProvider;
|
||||||
|
typedef interface IEnumVdsObject IEnumVdsObject;
|
||||||
|
typedef interface IVdsPack IVdsPack;
|
||||||
|
typedef interface IVdsDisk IVdsDisk;
|
||||||
|
typedef interface IVdsAdvancedDisk IVdsAdvancedDisk;
|
||||||
|
typedef interface IVdsAdviseSink IVdsAdviseSink;
|
||||||
|
typedef interface IVdsAsync IVdsAsync;
|
||||||
|
|
||||||
|
typedef struct IVdsServiceLoaderVtbl {
|
||||||
|
HRESULT(STDMETHODCALLTYPE *QueryInterface)(__RPC__in IVdsServiceLoader *This, __RPC__in REFIID riid, _COM_Outptr_ void **ppvObject);
|
||||||
|
ULONG(STDMETHODCALLTYPE *AddRef)(__RPC__in IVdsServiceLoader *This);
|
||||||
|
ULONG(STDMETHODCALLTYPE *Release)(__RPC__in IVdsServiceLoader *This);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *LoadService)(__RPC__in IVdsServiceLoader *This, __RPC__in_opt_string LPWSTR pwszMachineName, __RPC__deref_out_opt IVdsService **ppService);
|
||||||
|
} IVdsServiceLoaderVtbl;
|
||||||
|
interface IVdsServiceLoader {
|
||||||
|
CONST_VTBL struct IVdsServiceLoaderVtbl *lpVtbl;
|
||||||
|
};
|
||||||
|
|
||||||
|
typedef struct IVdsServiceVtbl {
|
||||||
|
HRESULT(STDMETHODCALLTYPE *QueryInterface)(__RPC__in IVdsService *This, __RPC__in REFIID riid, _COM_Outptr_ void **ppvObject);
|
||||||
|
ULONG(STDMETHODCALLTYPE *AddRef)(__RPC__in IVdsService *This);
|
||||||
|
ULONG(STDMETHODCALLTYPE *Release)(__RPC__in IVdsService *This);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *IsServiceReady)(__RPC__in IVdsService *This);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *WaitForServiceReady)(__RPC__in IVdsService *This);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *GetProperties)(__RPC__in IVdsService *This, __RPC__out VDS_SERVICE_PROP *pServiceProp);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *QueryProviders)(__RPC__in IVdsService *This, DWORD masks, __RPC__deref_out_opt IEnumVdsObject **ppEnum);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *QueryMaskedDisks)(__RPC__in IVdsService *This, __RPC__deref_out_opt IEnumVdsObject **ppEnum);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *QueryUnallocatedDisks)(__RPC__in IVdsService *This, __RPC__deref_out_opt IEnumVdsObject **ppEnum);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *GetObject)(__RPC__in IVdsService *This, VDS_OBJECT_ID ObjectId, VDS_OBJECT_TYPE type, __RPC__deref_out_opt IUnknown **ppObjectUnk);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *QueryDriveLetters)(__RPC__in IVdsService *This, WCHAR wcFirstLetter, DWORD count, __RPC__out_ecount_full(count) VDS_DRIVE_LETTER_PROP *pDriveLetterPropArray);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *QueryFileSystemTypes)(__RPC__in IVdsService *This, __RPC__deref_out_ecount_full_opt(*plNumberOfFileSystems) VDS_FILE_SYSTEM_TYPE_PROP **ppFileSystemTypeProps, __RPC__out LONG *plNumberOfFileSystems);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *Reenumerate)(__RPC__in IVdsService *This);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *Refresh)(__RPC__in IVdsService *This);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *CleanupObsoleteMountPoints)(__RPC__in IVdsService *This);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *Advise)(__RPC__in IVdsService *This, __RPC__in_opt IVdsAdviseSink *pSink, __RPC__out DWORD *pdwCookie);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *Unadvise)(__RPC__in IVdsService *This, DWORD dwCookie);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *Reboot)(__RPC__in IVdsService *This);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *SetFlags)(__RPC__in IVdsService *This, ULONG ulFlags);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *ClearFlags)(__RPC__in IVdsService *This, ULONG ulFlags);
|
||||||
|
} IVdsServiceVtbl;
|
||||||
|
interface IVdsService {
|
||||||
|
CONST_VTBL struct IVdsServiceVtbl *lpVtbl;
|
||||||
|
};
|
||||||
|
|
||||||
|
typedef struct IEnumVdsObjectVtbl {
|
||||||
|
HRESULT(STDMETHODCALLTYPE *QueryInterface)(__RPC__in IEnumVdsObject *This, __RPC__in REFIID riid, _COM_Outptr_ void **ppvObject);
|
||||||
|
ULONG(STDMETHODCALLTYPE *AddRef)(__RPC__in IEnumVdsObject *This);
|
||||||
|
ULONG(STDMETHODCALLTYPE *Release)(__RPC__in IEnumVdsObject *This);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *Next)(__RPC__in IEnumVdsObject *This, ULONG celt, __RPC__out_ecount_part(celt, *pcFetched) IUnknown **ppObjectArray, __RPC__out ULONG *pcFetched);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *Skip)(__RPC__in IEnumVdsObject *This, ULONG celt);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *Reset)(__RPC__in IEnumVdsObject *This);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *Clone)(__RPC__in IEnumVdsObject *This, __RPC__deref_out_opt IEnumVdsObject **ppEnum);
|
||||||
|
} IEnumVdsObjectVtbl;
|
||||||
|
interface IEnumVdsObject {
|
||||||
|
CONST_VTBL struct IEnumVdsObjectVtbl *lpVtbl;
|
||||||
|
};
|
||||||
|
|
||||||
|
typedef struct IVdsProviderVtbl {
|
||||||
|
HRESULT(STDMETHODCALLTYPE *QueryInterface)(__RPC__in IVdsProvider *This, __RPC__in REFIID riid, _COM_Outptr_ void **ppvObject);
|
||||||
|
ULONG(STDMETHODCALLTYPE *AddRef)(__RPC__in IVdsProvider *This);
|
||||||
|
ULONG(STDMETHODCALLTYPE *Release)(__RPC__in IVdsProvider *This);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *GetProperties)(__RPC__in IVdsProvider *This, __RPC__out VDS_PROVIDER_PROP *pProviderProp);
|
||||||
|
} IVdsProviderVtbl;
|
||||||
|
interface IVdsProvider {
|
||||||
|
CONST_VTBL struct IVdsProviderVtbl *lpVtbl;
|
||||||
|
};
|
||||||
|
|
||||||
|
typedef struct IVdsSwProviderVtbl {
|
||||||
|
HRESULT(STDMETHODCALLTYPE *QueryInterface)(__RPC__in IVdsSwProvider *This, __RPC__in REFIID riid, _COM_Outptr_ void **ppvObject);
|
||||||
|
ULONG(STDMETHODCALLTYPE *AddRef)(__RPC__in IVdsSwProvider *This);
|
||||||
|
ULONG(STDMETHODCALLTYPE *Release)(__RPC__in IVdsSwProvider *This);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *QueryPacks)(__RPC__in IVdsSwProvider *This, __RPC__deref_out_opt IEnumVdsObject **ppEnum);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *CreatePack)(__RPC__in IVdsSwProvider *This, __RPC__deref_out_opt IVdsPack **ppPack);
|
||||||
|
} IVdsSwProviderVtbl;
|
||||||
|
interface IVdsSwProvider {
|
||||||
|
CONST_VTBL struct IVdsSwProviderVtbl *lpVtbl;
|
||||||
|
};
|
||||||
|
|
||||||
|
typedef struct IVdsPackVtbl {
|
||||||
|
HRESULT(STDMETHODCALLTYPE *QueryInterface)(__RPC__in IVdsPack *This, __RPC__in REFIID riid, _COM_Outptr_ void **ppvObject);
|
||||||
|
ULONG(STDMETHODCALLTYPE *AddRef)(__RPC__in IVdsPack *This);
|
||||||
|
ULONG(STDMETHODCALLTYPE *Release)(__RPC__in IVdsPack *This);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *GetProperties)(__RPC__in IVdsPack *This, __RPC__out VDS_PACK_PROP *pPackProp);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *GetProvider)(__RPC__in IVdsPack *This, __RPC__deref_out_opt IVdsProvider **ppProvider);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *QueryVolumes)(__RPC__in IVdsPack *This, __RPC__deref_out_opt IEnumVdsObject **ppEnum);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *QueryDisks)(__RPC__in IVdsPack *This, __RPC__deref_out_opt IEnumVdsObject **ppEnum);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *CreateVolume)(__RPC__in IVdsPack *This, VDS_VOLUME_TYPE type, __RPC__in_ecount_full(lNumberOfDisks) VDS_INPUT_DISK *pInputDiskArray, LONG lNumberOfDisks, ULONG ulStripeSize, __RPC__deref_out_opt IVdsAsync **ppAsync);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *AddDisk)(__RPC__in IVdsPack *This, VDS_OBJECT_ID DiskId, VDS_PARTITION_STYLE PartitionStyle, BOOL bAsHotSpare);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *MigrateDisks)(__RPC__in IVdsPack *This, __RPC__in_ecount_full(lNumberOfDisks) VDS_OBJECT_ID *pDiskArray, LONG lNumberOfDisks, VDS_OBJECT_ID TargetPack, BOOL bForce, BOOL bQueryOnly, __RPC__out_ecount_full(lNumberOfDisks) HRESULT *pResults, __RPC__out BOOL *pbRebootNeeded);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *ReplaceDisk)(__RPC__in IVdsPack *This, VDS_OBJECT_ID OldDiskId, VDS_OBJECT_ID NewDiskId, __RPC__deref_out_opt IVdsAsync **ppAsync);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *RemoveMissingDisk)(__RPC__in IVdsPack *This, VDS_OBJECT_ID DiskId);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *Recover)(__RPC__in IVdsPack *This, __RPC__deref_out_opt IVdsAsync **ppAsync);
|
||||||
|
} IVdsPackVtbl;
|
||||||
|
interface IVdsPack {
|
||||||
|
CONST_VTBL struct IVdsPackVtbl *lpVtbl;
|
||||||
|
};
|
||||||
|
|
||||||
|
typedef struct IVdsDiskVtbl {
|
||||||
|
HRESULT(STDMETHODCALLTYPE *QueryInterface)(__RPC__in IVdsDisk *This, __RPC__in REFIID riid, _COM_Outptr_ void **ppvObject);
|
||||||
|
ULONG(STDMETHODCALLTYPE *AddRef)(__RPC__in IVdsDisk *This);
|
||||||
|
ULONG(STDMETHODCALLTYPE *Release)(__RPC__in IVdsDisk *This);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *GetProperties)(__RPC__in IVdsDisk *This, __RPC__out VDS_DISK_PROP *pDiskProperties);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *GetPack)(__RPC__in IVdsDisk *This, __RPC__deref_out_opt IVdsPack **ppPack);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *GetIdentificationData)(__RPC__in IVdsDisk *This, __RPC__out VDS_LUN_INFORMATION *pLunInfo);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *QueryExtents)(__RPC__in IVdsDisk *This, __RPC__deref_out_ecount_full_opt(*plNumberOfExtents) VDS_DISK_EXTENT **ppExtentArray, __RPC__out LONG *plNumberOfExtents);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *ConvertStyle)(__RPC__in IVdsDisk *This, VDS_PARTITION_STYLE NewStyle);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *SetFlags)(__RPC__in IVdsDisk *This, ULONG ulFlags);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *ClearFlags)(__RPC__in IVdsDisk *This, ULONG ulFlags);
|
||||||
|
} IVdsDiskVtbl;
|
||||||
|
interface IVdsDisk {
|
||||||
|
CONST_VTBL struct IVdsDiskVtbl *lpVtbl;
|
||||||
|
};
|
||||||
|
|
||||||
|
typedef struct IVdsAdvancedDiskVtbl {
|
||||||
|
HRESULT(STDMETHODCALLTYPE *QueryInterface)(__RPC__in IVdsAdvancedDisk *This, __RPC__in REFIID riid, _COM_Outptr_ void **ppvObject);
|
||||||
|
ULONG(STDMETHODCALLTYPE *AddRef)(__RPC__in IVdsAdvancedDisk *This);
|
||||||
|
ULONG(STDMETHODCALLTYPE *Release)(__RPC__in IVdsAdvancedDisk *This);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *GetPartitionProperties)(__RPC__in IVdsAdvancedDisk *This, ULONGLONG ullOffset, __RPC__out VDS_PARTITION_PROP *pPartitionProp);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *QueryPartitions)(__RPC__in IVdsAdvancedDisk *This, __RPC__deref_out_ecount_full_opt(*plNumberOfPartitions) VDS_PARTITION_PROP **ppPartitionPropArray, __RPC__out LONG *plNumberOfPartitions);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *CreatePartition)(__RPC__in IVdsAdvancedDisk *This, ULONGLONG ullOffset, ULONGLONG ullSize, __RPC__in CREATE_PARTITION_PARAMETERS *para, __RPC__deref_out_opt IVdsAsync **ppAsync);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *DeletePartition)(__RPC__in IVdsAdvancedDisk *This, ULONGLONG ullOffset, BOOL bForce, BOOL bForceProtected);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *ChangeAttributes)(__RPC__in IVdsAdvancedDisk *This, ULONGLONG ullOffset, __RPC__in CHANGE_ATTRIBUTES_PARAMETERS *para);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *AssignDriveLetter)(__RPC__in IVdsAdvancedDisk *This, ULONGLONG ullOffset, WCHAR wcLetter);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *DeleteDriveLetter)(__RPC__in IVdsAdvancedDisk *This, ULONGLONG ullOffset, WCHAR wcLetter);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *GetDriveLetter)(__RPC__in IVdsAdvancedDisk *This, ULONGLONG ullOffset, __RPC__out WCHAR *pwcLetter);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *FormatPartition)(__RPC__in IVdsAdvancedDisk *This, ULONGLONG ullOffset, VDS_FILE_SYSTEM_TYPE type, __RPC__in_string LPWSTR pwszLabel, DWORD dwUnitAllocationSize, BOOL bForce, BOOL bQuickFormat, BOOL bEnableCompression, __RPC__deref_out_opt IVdsAsync **ppAsync);
|
||||||
|
HRESULT(STDMETHODCALLTYPE *Clean)(__RPC__in IVdsAdvancedDisk *This, BOOL bForce, BOOL bForceOEM, BOOL bFullClean, __RPC__deref_out_opt IVdsAsync **ppAsync);
|
||||||
|
} IVdsAdvancedDiskVtbl;
|
||||||
|
interface IVdsAdvancedDisk {
|
||||||
|
CONST_VTBL struct IVdsAdvancedDiskVtbl *lpVtbl;
|
||||||
|
};
|
||||||
|
|
||||||
|
#define IVdsServiceLoader_LoadService(This,pwszMachineName,ppService) (This)->lpVtbl->LoadService(This,pwszMachineName,ppService)
|
||||||
|
#define IVdsServiceLoader_Release(This) (This)->lpVtbl->Release(This)
|
||||||
|
#define IVdsService_QueryProviders(This,masks,ppEnum) (This)->lpVtbl->QueryProviders(This,masks,ppEnum)
|
||||||
|
#define IVdsSwProvider_QueryInterface(This,riid,ppvObject) (This)->lpVtbl->QueryInterface(This,riid,ppvObject)
|
||||||
|
#define IVdsProvider_Release(This) (This)->lpVtbl->Release(This)
|
||||||
|
#define IVdsSwProvider_QueryPacks(This,ppEnum) (This)->lpVtbl->QueryPacks(This,ppEnum)
|
||||||
|
#define IVdsSwProvider_Release(This) (This)->lpVtbl->Release(This)
|
||||||
|
#define IVdsPack_QueryDisks(This,ppEnum) (This)->lpVtbl->QueryDisks(This,ppEnum)
|
||||||
|
#define IVdsDisk_GetProperties(This,pDiskProperties) (This)->lpVtbl->GetProperties(This,pDiskProperties)
|
||||||
|
#define IVdsDisk_Release(This) (This)->lpVtbl->Release(This)
|
||||||
|
#define IVdsDisk_QueryInterface(This,riid,ppvObject) (This)->lpVtbl->QueryInterface(This,riid,ppvObject)
|
||||||
|
#define IVdsAdvancedDisk_QueryPartitions(This,ppPartitionPropArray,plNumberOfPartitions) (This)->lpVtbl->QueryPartitions(This,ppPartitionPropArray,plNumberOfPartitions)
|
||||||
|
#define IVdsAdvancedDisk_DeletePartition(This,ullOffset,bForce,bForceProtected) (This)->lpVtbl->DeletePartition(This,ullOffset,bForce,bForceProtected)
|
||||||
|
#define IVdsAdvancedDisk_Release(This) (This)->lpVtbl->Release(This)
|
||||||
|
#define IEnumVdsObject_Next(This,celt,ppObjectArray,pcFetched) (This)->lpVtbl->Next(This,celt,ppObjectArray,pcFetched)
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
static __inline BOOL UnlockDrive(HANDLE hDrive) {
|
static __inline BOOL UnlockDrive(HANDLE hDrive) {
|
||||||
|
@ -105,6 +258,7 @@ extern RUFUS_DRIVE_INFO SelectedDrive;
|
||||||
BOOL SetAutoMount(BOOL enable);
|
BOOL SetAutoMount(BOOL enable);
|
||||||
BOOL GetAutoMount(BOOL* enabled);
|
BOOL GetAutoMount(BOOL* enabled);
|
||||||
char* GetPhysicalName(DWORD DriveIndex);
|
char* GetPhysicalName(DWORD DriveIndex);
|
||||||
|
BOOL DeletePartitions(DWORD DriveIndex);
|
||||||
HANDLE GetPhysicalHandle(DWORD DriveIndex, BOOL bLockDrive, BOOL bWriteAccess, BOOL bWriteShare);
|
HANDLE GetPhysicalHandle(DWORD DriveIndex, BOOL bLockDrive, BOOL bWriteAccess, BOOL bWriteShare);
|
||||||
char* GetLogicalName(DWORD DriveIndex, BOOL bKeepTrailingBackslash, BOOL bSilent);
|
char* GetLogicalName(DWORD DriveIndex, BOOL bKeepTrailingBackslash, BOOL bSilent);
|
||||||
BOOL WaitForLogical(DWORD DriveIndex);
|
BOOL WaitForLogical(DWORD DriveIndex);
|
||||||
|
|
21
src/format.c
21
src/format.c
|
@ -1760,13 +1760,13 @@ DWORD WINAPI FormatThread(void* param)
|
||||||
extra_partitions = XP_COMPAT;
|
extra_partitions = XP_COMPAT;
|
||||||
|
|
||||||
PrintInfoDebug(0, MSG_225);
|
PrintInfoDebug(0, MSG_225);
|
||||||
hPhysicalDrive = GetPhysicalHandle(DriveIndex, lock_drive, TRUE, !lock_drive);
|
hPhysicalDrive = GetPhysicalHandle(DriveIndex, lock_drive, FALSE, !lock_drive);
|
||||||
if (hPhysicalDrive == INVALID_HANDLE_VALUE) {
|
if (hPhysicalDrive == INVALID_HANDLE_VALUE) {
|
||||||
FormatStatus = ERROR_SEVERITY_ERROR|FAC(FACILITY_STORAGE)|ERROR_OPEN_FAILED;
|
FormatStatus = ERROR_SEVERITY_ERROR|FAC(FACILITY_STORAGE)|ERROR_OPEN_FAILED;
|
||||||
goto out;
|
goto out;
|
||||||
}
|
}
|
||||||
|
|
||||||
// At this stage we should have both a handle and a lock to the physical drive...
|
// At this stage we have both a handle and a lock to the physical drive
|
||||||
if (!GetDriveLetters(DriveIndex, drive_letters)) {
|
if (!GetDriveLetters(DriveIndex, drive_letters)) {
|
||||||
uprintf("Failed to get a drive letter\n");
|
uprintf("Failed to get a drive letter\n");
|
||||||
FormatStatus = ERROR_SEVERITY_ERROR|FAC(FACILITY_STORAGE)|APPERR(ERROR_CANT_ASSIGN_LETTER);
|
FormatStatus = ERROR_SEVERITY_ERROR|FAC(FACILITY_STORAGE)|APPERR(ERROR_CANT_ASSIGN_LETTER);
|
||||||
|
@ -1783,7 +1783,7 @@ DWORD WINAPI FormatThread(void* param)
|
||||||
} else {
|
} else {
|
||||||
// Unmount all mounted volumes that belong to this drive
|
// Unmount all mounted volumes that belong to this drive
|
||||||
// Do it in reverse so that we always end on the first volume letter
|
// Do it in reverse so that we always end on the first volume letter
|
||||||
for (i=(int)safe_strlen(drive_letters); i>0; i--) {
|
for (i = (int)safe_strlen(drive_letters); i > 0; i--) {
|
||||||
drive_name[0] = drive_letters[i-1];
|
drive_name[0] = drive_letters[i-1];
|
||||||
if (bt == BT_IMAGE) {
|
if (bt == BT_IMAGE) {
|
||||||
// If we are using an image, check that it isn't located on the drive we are trying to format
|
// If we are using an image, check that it isn't located on the drive we are trying to format
|
||||||
|
@ -1801,7 +1801,20 @@ DWORD WINAPI FormatThread(void* param)
|
||||||
}
|
}
|
||||||
uprintf("Will use '%c:' as volume mountpoint\n", drive_name[0]);
|
uprintf("Will use '%c:' as volume mountpoint\n", drive_name[0]);
|
||||||
|
|
||||||
// ...but we need a lock to the logical drive to be able to write anything to it
|
// It kind of blows, but we have to relinquish access to the physical drive
|
||||||
|
// for VDS to be able to delete the partitions that reside on it...
|
||||||
|
safe_unlockclose(hPhysicalDrive);
|
||||||
|
PrintInfoDebug(0, MSG_239);
|
||||||
|
DeletePartitions(DriveIndex);
|
||||||
|
|
||||||
|
// Now get RW access to the physical drive...
|
||||||
|
hPhysicalDrive = GetPhysicalHandle(DriveIndex, lock_drive, TRUE, !lock_drive);
|
||||||
|
if (hPhysicalDrive == INVALID_HANDLE_VALUE) {
|
||||||
|
FormatStatus = ERROR_SEVERITY_ERROR | FAC(FACILITY_STORAGE) | ERROR_OPEN_FAILED;
|
||||||
|
goto out;
|
||||||
|
}
|
||||||
|
|
||||||
|
// ...and get a lock to the logical drive so that we can actually write something
|
||||||
hLogicalVolume = GetLogicalHandle(DriveIndex, TRUE, FALSE, !lock_drive);
|
hLogicalVolume = GetLogicalHandle(DriveIndex, TRUE, FALSE, !lock_drive);
|
||||||
if (hLogicalVolume == INVALID_HANDLE_VALUE) {
|
if (hLogicalVolume == INVALID_HANDLE_VALUE) {
|
||||||
uprintf("Could not lock volume\n");
|
uprintf("Could not lock volume\n");
|
||||||
|
|
|
@ -1884,7 +1884,7 @@ static INT_PTR CALLBACK MainCallback(HWND hDlg, UINT message, WPARAM wParam, LPA
|
||||||
case WM_COMMAND:
|
case WM_COMMAND:
|
||||||
#ifdef RUFUS_TEST
|
#ifdef RUFUS_TEST
|
||||||
if (LOWORD(wParam) == IDC_TEST) {
|
if (LOWORD(wParam) == IDC_TEST) {
|
||||||
assert(1 == 0);
|
DeletePartitions((DWORD)ComboBox_GetItemData(hDeviceList, ComboBox_GetCurSel(hDeviceList)));
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
10
src/rufus.rc
10
src/rufus.rc
|
@ -33,7 +33,7 @@ LANGUAGE LANG_NEUTRAL, SUBLANG_NEUTRAL
|
||||||
IDD_DIALOG DIALOGEX 12, 12, 232, 326
|
IDD_DIALOG DIALOGEX 12, 12, 232, 326
|
||||||
STYLE DS_SETFONT | DS_MODALFRAME | DS_CENTER | WS_MINIMIZEBOX | WS_POPUP | WS_CAPTION | WS_SYSMENU
|
STYLE DS_SETFONT | DS_MODALFRAME | DS_CENTER | WS_MINIMIZEBOX | WS_POPUP | WS_CAPTION | WS_SYSMENU
|
||||||
EXSTYLE WS_EX_ACCEPTFILES
|
EXSTYLE WS_EX_ACCEPTFILES
|
||||||
CAPTION "Rufus 3.4.1427"
|
CAPTION "Rufus 3.4.1428"
|
||||||
FONT 9, "Segoe UI Symbol", 400, 0, 0x0
|
FONT 9, "Segoe UI Symbol", 400, 0, 0x0
|
||||||
BEGIN
|
BEGIN
|
||||||
LTEXT "Drive Properties",IDS_DRIVE_PROPERTIES_TXT,8,6,53,12,NOT WS_GROUP
|
LTEXT "Drive Properties",IDS_DRIVE_PROPERTIES_TXT,8,6,53,12,NOT WS_GROUP
|
||||||
|
@ -394,8 +394,8 @@ END
|
||||||
//
|
//
|
||||||
|
|
||||||
VS_VERSION_INFO VERSIONINFO
|
VS_VERSION_INFO VERSIONINFO
|
||||||
FILEVERSION 3,4,1427,0
|
FILEVERSION 3,4,1428,0
|
||||||
PRODUCTVERSION 3,4,1427,0
|
PRODUCTVERSION 3,4,1428,0
|
||||||
FILEFLAGSMASK 0x3fL
|
FILEFLAGSMASK 0x3fL
|
||||||
#ifdef _DEBUG
|
#ifdef _DEBUG
|
||||||
FILEFLAGS 0x1L
|
FILEFLAGS 0x1L
|
||||||
|
@ -413,13 +413,13 @@ BEGIN
|
||||||
VALUE "Comments", "https://akeo.ie"
|
VALUE "Comments", "https://akeo.ie"
|
||||||
VALUE "CompanyName", "Akeo Consulting"
|
VALUE "CompanyName", "Akeo Consulting"
|
||||||
VALUE "FileDescription", "Rufus"
|
VALUE "FileDescription", "Rufus"
|
||||||
VALUE "FileVersion", "3.4.1427"
|
VALUE "FileVersion", "3.4.1428"
|
||||||
VALUE "InternalName", "Rufus"
|
VALUE "InternalName", "Rufus"
|
||||||
VALUE "LegalCopyright", "© 2011-2018 Pete Batard (GPL v3)"
|
VALUE "LegalCopyright", "© 2011-2018 Pete Batard (GPL v3)"
|
||||||
VALUE "LegalTrademarks", "https://www.gnu.org/copyleft/gpl.html"
|
VALUE "LegalTrademarks", "https://www.gnu.org/copyleft/gpl.html"
|
||||||
VALUE "OriginalFilename", "rufus-3.4.exe"
|
VALUE "OriginalFilename", "rufus-3.4.exe"
|
||||||
VALUE "ProductName", "Rufus"
|
VALUE "ProductName", "Rufus"
|
||||||
VALUE "ProductVersion", "3.4.1427"
|
VALUE "ProductVersion", "3.4.1428"
|
||||||
END
|
END
|
||||||
END
|
END
|
||||||
BLOCK "VarFileInfo"
|
BLOCK "VarFileInfo"
|
||||||
|
|
Loading…
Reference in a new issue