2. Call chkdsk to fix the volume before shrink.
terminal_output console
chainloader /EFI/Microsoft/Boot/bootmgfw.efi
boot
+ elif [ -f ($vtoydev,$partid)/efi/Microsoft/Boot/bootmgfw.efi ]; then
+ set root=($vtoydev,$partid)
+ terminal_output console
+ chainloader /efi/Microsoft/Boot/bootmgfw.efi
+ boot
fi
else
break
terminal_output console
chainloader /EFI/Microsoft/Boot/bootmgfw.efi
boot
+ elif search -n -s -f /efi/Microsoft/Boot/bootmgfw.efi; then
+ terminal_output console
+ chainloader /efi/Microsoft/Boot/bootmgfw.efi
+ boot
else
echo "Windows NOT found ..."
fi
--- /dev/null
+/******************************************************************************\r
+* DiskService.c\r
+*\r
+* Copyright (c) 2021, longpanda <admin@ventoy.net>\r
+*\r
+* This program is free software; you can redistribute it and/or\r
+* modify it under the terms of the GNU General Public License as\r
+* published by the Free Software Foundation; either version 3 of the\r
+* License, or (at your option) any later version.\r
+*\r
+* This program is distributed in the hope that it will be useful, but\r
+* WITHOUT ANY WARRANTY; without even the implied warranty of\r
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU\r
+* General Public License for more details.\r
+*\r
+* You should have received a copy of the GNU General Public License\r
+* along with this program; if not, see <http://www.gnu.org/licenses/>.\r
+*\r
+*/\r
+\r
+#include <Windows.h>\r
+#include <winternl.h>\r
+#include <commctrl.h>\r
+#include <initguid.h>\r
+#include <vds.h>\r
+#include "Ventoy2Disk.h"\r
+#include "DiskService.h"\r
+\r
+BOOL DISK_CleanDisk(int DriveIndex)\r
+{\r
+ BOOL ret;\r
+\r
+ ret = VDS_CleanDisk(DriveIndex);\r
+ if (!ret)\r
+ {\r
+ ret = PSHELL_CleanDisk(DriveIndex);\r
+ }\r
+\r
+ return ret;\r
+}\r
+\r
+\r
+BOOL DISK_DeleteVtoyEFIPartition(int DriveIndex, UINT64 EfiPartOffset)\r
+{\r
+ BOOL ret;\r
+\r
+ ret = VDS_DeleteVtoyEFIPartition(DriveIndex, EfiPartOffset);\r
+ if (!ret)\r
+ {\r
+ ret = PSHELL_DeleteVtoyEFIPartition(DriveIndex, EfiPartOffset);\r
+ }\r
+\r
+ return ret;\r
+}\r
+\r
+BOOL DISK_ChangeVtoyEFI2ESP(int DriveIndex, UINT64 Offset)\r
+{\r
+ BOOL ret;\r
+\r
+ ret = VDS_ChangeVtoyEFI2ESP(DriveIndex, Offset);\r
+ if (!ret)\r
+ {\r
+ ret = PSHELL_ChangeVtoyEFI2ESP(DriveIndex, Offset);\r
+ }\r
+\r
+ return ret;\r
+}\r
+\r
+\r
+BOOL DISK_ChangeVtoyEFI2Basic(int DriveIndex, UINT64 Offset)\r
+{\r
+ BOOL ret;\r
+\r
+ ret = VDS_ChangeVtoyEFI2Basic(DriveIndex, Offset);\r
+ if (!ret)\r
+ {\r
+ ret = PSHELL_ChangeVtoyEFI2Basic(DriveIndex, Offset);\r
+ }\r
+\r
+ return ret;\r
+}\r
+\r
+BOOL DISK_ChangeVtoyEFIAttr(int DriveIndex, UINT64 Offset, UINT64 Attr)\r
+{\r
+ BOOL ret;\r
+\r
+ ret = VDS_ChangeVtoyEFIAttr(DriveIndex, Offset, Attr);\r
+ \r
+ return ret;\r
+}\r
+\r
+BOOL DISK_ShrinkVolume(int DriveIndex, const char* VolumeGuid, CHAR DriveLetter, UINT64 OldBytes, UINT64 ReduceBytes)\r
+{\r
+ BOOL ret;\r
+\r
+ ret = VDS_ShrinkVolume(DriveIndex, VolumeGuid, DriveLetter, OldBytes, ReduceBytes);\r
+ if (!ret)\r
+ {\r
+ if (LASTERR == VDS_E_SHRINK_DIRTY_VOLUME)\r
+ {\r
+ Log("VDS shrink return dirty, no need to run powershell.");\r
+ }\r
+ else\r
+ {\r
+ ret = PSHELL_ShrinkVolume(DriveIndex, VolumeGuid, DriveLetter, OldBytes, ReduceBytes);\r
+ }\r
+ }\r
+\r
+ return ret;\r
+}\r
+\r
WCHAR Name[36];\r
ULONG NameLen;\r
ULONGLONG Offset;\r
+ CHAR DriveLetter;\r
}VDS_PARA;\r
\r
+//DISK API\r
+BOOL DISK_CleanDisk(int DriveIndex);\r
+BOOL DISK_DeleteVtoyEFIPartition(int DriveIndex, UINT64 EfiPartOffset);\r
+BOOL DISK_ChangeVtoyEFIAttr(int DriveIndex, UINT64 Offset, UINT64 Attr);\r
+BOOL DISK_ChangeVtoyEFI2ESP(int DriveIndex, UINT64 Offset);\r
+BOOL DISK_ChangeVtoyEFI2Basic(int DriveIndex, UINT64 Offset);\r
+BOOL DISK_ShrinkVolume(int DriveIndex, const char* VolumeGuid, CHAR DriveLetter, UINT64 OldBytes, UINT64 ReduceBytes);\r
+\r
+\r
\r
//VDS com\r
-int VDS_Init(void);\r
BOOL VDS_CleanDisk(int DriveIndex);\r
BOOL VDS_DeleteAllPartitions(int DriveIndex);\r
-BOOL VDS_DeleteVtoyEFIPartition(int DriveIndex);\r
-BOOL VDS_ChangeVtoyEFIAttr(int DriveIndex, UINT64 Attr);\r
-BOOL VDS_CreateVtoyEFIPart(int DriveIndex, UINT64 Offset);\r
+BOOL VDS_DeleteVtoyEFIPartition(int DriveIndex, UINT64 EfiPartOffset);\r
+BOOL VDS_ChangeVtoyEFIAttr(int DriveIndex, UINT64 Offset, UINT64 Attr);\r
BOOL VDS_ChangeVtoyEFI2ESP(int DriveIndex, UINT64 Offset);\r
BOOL VDS_ChangeVtoyEFI2Basic(int DriveIndex, UINT64 Offset);\r
-BOOL VDS_FormatVtoyEFIPart(int DriveIndex, UINT64 Offset);\r
-BOOL VDS_ShrinkVolume(const char* VolumeGuid, UINT64 ReduceBytes);\r
+BOOL VDS_ShrinkVolume(int DriveIndex, const char* VolumeGuid, CHAR DriveLetter, UINT64 OldBytes, UINT64 ReduceBytes);\r
+BOOL VDS_IsLastAvaliable(void);\r
+\r
\r
//diskpart.exe\r
BOOL DSPT_CleanDisk(int DriveIndex);\r
\r
+//powershell.exe\r
+BOOL PSHELL_CleanDisk(int DriveIndex);\r
+BOOL PSHELL_DeleteVtoyEFIPartition(int DriveIndex, UINT64 EfiPartOffset);\r
+BOOL PSHELL_ChangeVtoyEFI2ESP(int DriveIndex, UINT64 Offset);\r
+BOOL PSHELL_ChangeVtoyEFI2Basic(int DriveIndex, UINT64 Offset);\r
+BOOL PSHELL_ShrinkVolume(int DriveIndex, const char* VolumeGuid, CHAR DriveLetter, UINT64 OldBytes, UINT64 ReduceBytes);\r
\r
//\r
// Internel define\r
WaitForSingleObject(Pi.hProcess, INFINITE);\r
Log("Process finished...");\r
\r
+ CHECK_CLOSE_HANDLE(Pi.hProcess);\r
+ CHECK_CLOSE_HANDLE(Pi.hThread);\r
+\r
DeleteFileA(CmdFile);\r
return TRUE;\r
}\r
return "The offline operation failed.";\r
case 0x80042598: // VDS_E_BAD_REVISION_NUMBER\r
return "The operation could not be completed because the specified revision number is not supported.";\r
+ case 0x80042599: // VDS_E_SHRINK_USER_CANCELLED\r
+ return "The shrink operation was cancelled by the user.";\r
+ case 0x8004259a: // VDS_E_SHRINK_DIRTY_VOLUME\r
+ return "The volume you have selected to shrink may be corrupted. Use Chkdsk to fix the corruption problem, and then try again.";\r
case 0x00042700: // VDS_S_NAME_TRUNCATED\r
return "The name was set successfully but had to be truncated.";\r
case 0x80042701: // VDS_E_NAME_NOT_UNIQUE\r
\r
typedef BOOL(*VDS_Callback_PF)(void *pInterface, VDS_DISK_PROP *pDiskProp, UINT64 data);\r
\r
+static BOOL g_vds_available = TRUE;\r
+\r
+BOOL VDS_IsLastAvaliable(void)\r
+{\r
+ return g_vds_available;\r
+}\r
+\r
STATIC IVdsService * VDS_InitService(void)\r
{\r
HRESULT hr;\r
{\r
VDS_SET_ERROR(hr);\r
Log("Could not load VDS Service: 0x%x", LASTERR);\r
+ g_vds_available = FALSE;\r
return NULL;\r
}\r
\r
}\r
\r
Log("VDS init OK, service %p", pService);\r
+ g_vds_available = TRUE;\r
return pService;\r
}\r
\r
HRESULT hr;\r
VDS_PARTITION_PROP* prop_array = NULL;\r
LONG i, prop_array_size;\r
- ULONG PartNumber = (ULONG)data;\r
+ UINT64 PartOffset = data;\r
IVdsAdvancedDisk *pAdvancedDisk = (IVdsAdvancedDisk *)pInterface;\r
\r
- if (PartNumber == 0)\r
+ if (PartOffset == 0)\r
{\r
Log("Deleting ALL partitions from disk '%S':", pDiskProp->pwszName);\r
}\r
else\r
{\r
- Log("Deleting partition(%ld) from disk '%S':", PartNumber, pDiskProp->pwszName);\r
+ Log("Deleting partition(offset=%llu) from disk '%S':", PartOffset, pDiskProp->pwszName);\r
}\r
\r
// Query the partition data, so we can get the start offset, which we need for deletion\r
r = TRUE;\r
for (i = 0; i < prop_array_size; i++) \r
{\r
- if (PartNumber == 0 || PartNumber == prop_array[i].ulPartitionNumber)\r
+ if (PartOffset == 0 || PartOffset == prop_array[i].ullOffset)\r
{\r
Log("* Partition %d (offset: %lld, size: %llu) delete it.",\r
prop_array[i].ulPartitionNumber, prop_array[i].ullOffset, (ULONGLONG)prop_array[i].ullSize);\r
return ret;\r
}\r
\r
-BOOL VDS_DeleteVtoyEFIPartition(int DriveIndex)\r
+BOOL VDS_DeleteVtoyEFIPartition(int DriveIndex, UINT64 EfiPartOffset)\r
{\r
- BOOL ret = VDS_DiskCommProc(INTF_ADVANCEDDISK, DriveIndex, VDS_CallBack_DeletePartition, 2);\r
+ BOOL ret = VDS_DiskCommProc(INTF_ADVANCEDDISK, DriveIndex, VDS_CallBack_DeletePartition, EfiPartOffset);\r
Log("VDS_DeleteVtoyEFIPartition %d ret:%d (%s)", DriveIndex, ret, ret ? "SUCCESS" : "FAIL");\r
return ret;\r
}\r
{\r
BOOL r = FALSE;\r
HRESULT hr;\r
+ VDS_PARA *VdsPara = (VDS_PARA *)data;\r
VDS_PARTITION_PROP* prop_array = NULL;\r
LONG i, prop_array_size;\r
CHANGE_ATTRIBUTES_PARAMETERS AttrPara;\r
{\r
if (prop_array[i].ullSize == VENTOY_EFI_PART_SIZE &&\r
prop_array[i].PartitionStyle == VDS_PST_GPT &&\r
- memcmp(prop_array[i].Gpt.name, L"VTOYEFI", 7 * 2) == 0)\r
+ memcmp(prop_array[i].Gpt.name, L"VTOYEFI", 7 * 2) == 0 &&\r
+ VdsPara->Offset == prop_array[i].ullOffset)\r
{\r
- Log("* Partition %d (offset: %lld, size: %llu, Attr:0x%llx)", prop_array[i].ulPartitionNumber,\r
+ Log("** Partition %d (offset: %lld, size: %llu, Attr:0x%llx)", prop_array[i].ulPartitionNumber,\r
prop_array[i].ullOffset, (ULONGLONG)prop_array[i].ullSize, prop_array[i].Gpt.attributes);\r
\r
- if (prop_array[i].Gpt.attributes == data)\r
+ if (prop_array[i].Gpt.attributes == VdsPara->Attr)\r
{\r
Log("Attribute match, No need to change.");\r
r = TRUE;\r
else\r
{\r
AttrPara.style = VDS_PST_GPT;\r
- AttrPara.GptPartInfo.attributes = data;\r
+ AttrPara.GptPartInfo.attributes = VdsPara->Attr;\r
hr = IVdsAdvancedDisk_ChangeAttributes(pAdvancedDisk, prop_array[i].ullOffset, &AttrPara);\r
if (hr == S_OK)\r
{\r
return r;\r
}\r
\r
-BOOL VDS_ChangeVtoyEFIAttr(int DriveIndex, UINT64 Attr)\r
+BOOL VDS_ChangeVtoyEFIAttr(int DriveIndex, UINT64 Offset, UINT64 Attr)\r
{\r
- BOOL ret = VDS_DiskCommProc(INTF_ADVANCEDDISK, DriveIndex, VDS_CallBack_ChangeEFIAttr, Attr); \r
- Log("VDS_ChangeVtoyEFIAttr %d ret:%d (%s)", DriveIndex, ret, ret ? "SUCCESS" : "FAIL");\r
+ VDS_PARA Para;\r
+\r
+ Para.Attr = Attr;\r
+ Para.Offset = Offset;\r
+\r
+ BOOL ret = VDS_DiskCommProc(INTF_ADVANCEDDISK, DriveIndex, VDS_CallBack_ChangeEFIAttr, (UINT64)&Para);\r
+ Log("VDS_ChangeVtoyEFIAttr %d (offset:%llu) ret:%d (%s)", DriveIndex, Offset, ret, ret ? "SUCCESS" : "FAIL");\r
return ret;\r
}\r
\r
return ret;\r
}\r
\r
+\r
BOOL VDS_ChangeVtoyEFI2Basic(int DriveIndex, UINT64 Offset)\r
{\r
VDS_PARA Para;\r
return ret;\r
}\r
\r
-\r
-STATIC BOOL VDS_CallBack_CreateVtoyEFI(void *pInterface, VDS_DISK_PROP *pDiskProp, UINT64 data)\r
+STATIC BOOL CHKDSK_Volume(CHAR LogicalDrive)\r
{\r
- HRESULT hr, hr2;\r
- ULONG completed;\r
- IVdsAsync* pAsync;\r
- CREATE_PARTITION_PARAMETERS para;\r
- IVdsCreatePartitionEx *pCreatePartitionEx = (IVdsCreatePartitionEx *)pInterface;\r
- VDS_PARA *VdsPara = (VDS_PARA *)data;\r
-\r
- (void)pDiskProp;\r
-\r
- memset(¶, 0, sizeof(para));\r
- para.style = VDS_PST_GPT;\r
- memcpy(&(para.GptPartInfo.partitionType), &VdsPara->Type, sizeof(GUID));\r
- memcpy(&(para.GptPartInfo.partitionId), &VdsPara->Id, sizeof(GUID));\r
- para.GptPartInfo.attributes = VdsPara->Attr;\r
- memcpy(para.GptPartInfo.name, VdsPara->Name, sizeof(WCHAR)* VdsPara->NameLen);\r
+ CHAR CmdBuf[1024];\r
+ STARTUPINFOA Si;\r
+ PROCESS_INFORMATION Pi;\r
\r
- hr = IVdsCreatePartitionEx_CreatePartitionEx(pCreatePartitionEx, VdsPara->Offset, VENTOY_EFI_PART_SIZE, 512, ¶, &pAsync);\r
- while (SUCCEEDED(hr))\r
- {\r
- hr = IVdsAsync_QueryStatus(pAsync, &hr2, &completed);\r
- if (SUCCEEDED(hr))\r
- {\r
- hr = hr2;\r
- if (hr == S_OK)\r
- {\r
- Log("Disk create partition QueryStatus OK, %lu%%", completed);\r
- break;\r
- }\r
- else if (hr == VDS_E_OPERATION_PENDING)\r
- {\r
- Log("Disk partition finish: %lu%%", completed);\r
- hr = S_OK;\r
- }\r
- else\r
- {\r
- Log("QueryStatus invalid status:0x%lx", hr);\r
- }\r
- }\r
- Sleep(1000);\r
- }\r
+ if ((!IsFileExist("C:\\Windows\\System32\\chkdsk.exe")) || (LogicalDrive == 0))\r
+ {\r
+ return FALSE;\r
+ }\r
\r
- if (hr != S_OK)\r
- {\r
- VDS_SET_ERROR(hr);\r
- Log("Could not create partition, err:0x%lx(%s)", LASTERR, WindowsErrorString(hr));\r
- return FALSE;\r
- }\r
+ GetStartupInfoA(&Si);\r
+ Si.dwFlags |= STARTF_USESHOWWINDOW;\r
+ Si.wShowWindow = SW_HIDE;\r
\r
- return TRUE;\r
-}\r
+ sprintf_s(CmdBuf, sizeof(CmdBuf), "C:\\Windows\\System32\\chkdsk.exe %C: /f", LogicalDrive);\r
\r
-BOOL VDS_CreateVtoyEFIPart(int DriveIndex, UINT64 Offset)\r
-{\r
- VDS_PARA Para;\r
- GUID WindowsDataPartType = { 0xebd0a0a2, 0xb9e5, 0x4433, { 0x87, 0xc0, 0x68, 0xb6, 0xb7, 0x26, 0x99, 0xc7 } };\r
- GUID EspPartType = { 0xc12a7328, 0xf81f, 0x11d2, { 0xba, 0x4b, 0x00, 0xa0, 0xc9, 0x3e, 0xc9, 0x3b } };\r
+ Log("CreateProcess <%s>", CmdBuf);\r
+ CreateProcessA(NULL, CmdBuf, NULL, NULL, FALSE, 0, NULL, NULL, &Si, &Pi);\r
\r
- Log("VDS_CreateVtoyEFIPart %u Offset:%llu Sector:%llu", DriveIndex, Offset, Offset / 512);\r
+ Log("Wair process ...");\r
+ WaitForSingleObject(Pi.hProcess, INFINITE);\r
+ Log("Process finished...");\r
\r
- memset(&Para, 0, sizeof(Para));\r
- Para.Attr = 0x8000000000000000ULL;\r
- Para.Offset = Offset;\r
- memcpy(Para.Name, L"VTOYEFI", 7 * 2);\r
- Para.NameLen = 7;\r
- memcpy(&(Para.Type), &EspPartType, sizeof(GUID));\r
- CoCreateGuid(&(Para.Id));\r
+ CHECK_CLOSE_HANDLE(Pi.hProcess);\r
+ CHECK_CLOSE_HANDLE(Pi.hThread);\r
\r
- BOOL ret = VDS_DiskCommProc(INTF_CREATEPARTITIONEX, DriveIndex, VDS_CallBack_CreateVtoyEFI, (UINT64)&Para);\r
- Log("VDS_CreateVtoyEFIPart %d ret:%d (%s)", DriveIndex, ret, ret ? "SUCCESS" : "FAIL");\r
- return ret; \r
+ return TRUE;\r
}\r
\r
\r
-STATIC BOOL VDS_CallBack_FormatVtoyEFI(void *pInterface, VDS_DISK_PROP *pDiskProp, UINT64 data)\r
+STATIC BOOL VDS_CallBack_ShrinkVolume(void* pInterface, VDS_DISK_PROP* pDiskProp, UINT64 data)\r
{\r
+ int i;\r
HRESULT hr, hr2;\r
+ IVdsVolume* pVolume = (IVdsVolume*)pInterface;\r
ULONG completed;\r
- IVdsAsync* pAsync; \r
- IVdsDiskPartitionMF *pPartitionMF = (IVdsDiskPartitionMF *)pInterface;\r
+ IVdsAsync* pAsync;\r
VDS_PARA *VdsPara = (VDS_PARA *)data;\r
\r
(void)pDiskProp;\r
- \r
- hr = IVdsPartitionMF_FormatPartitionEx(pPartitionMF, VdsPara->Offset, L"FAT", 0x0100, 0, VdsPara->Name, TRUE, TRUE, FALSE, &pAsync);\r
- while (SUCCEEDED(hr))\r
+\r
+ Log("VDS_CallBack_ShrinkVolume (%C:) (%llu) ...", VdsPara->DriveLetter, (ULONGLONG)VdsPara->Offset);\r
+\r
+ hr = IVdsVolume_Shrink(pVolume, (ULONGLONG)VdsPara->Offset, &pAsync);\r
+ if (hr == VDS_E_SHRINK_DIRTY_VOLUME)\r
{\r
- hr = IVdsAsync_QueryStatus(pAsync, &hr2, &completed);\r
- if (SUCCEEDED(hr))\r
+ Log("Volume %C: is dirty, run chkdsk and retry.", VdsPara->DriveLetter);\r
+ CHKDSK_Volume(VdsPara->DriveLetter);\r
+\r
+ hr = IVdsVolume_Shrink(pVolume, (ULONGLONG)VdsPara->Offset, &pAsync);\r
+ if (hr == VDS_E_SHRINK_DIRTY_VOLUME)\r
{\r
- hr = hr2;\r
- if (hr == S_OK)\r
- {\r
- Log("Disk format partition QueryStatus OK, %lu%%", completed);\r
- break;\r
- }\r
- else if (hr == VDS_E_OPERATION_PENDING)\r
+ Log("################################################################");\r
+ Log("################################################################");\r
+ for (i = 0; i < 20; i++)\r
{\r
- Log("Disk format finish: %lu%%", completed);\r
- hr = S_OK;\r
- }\r
- else\r
- {\r
- Log("QueryStatus invalid status:0x%lx", hr);\r
+ Log("###### Volume dirty, Please run \"chkdsk /f %C:\" and retry. ######", VdsPara->Name[0]);\r
}\r
+ Log("################################################################");\r
+ Log("################################################################");\r
}\r
- Sleep(1000);\r
- }\r
-\r
- if (hr != S_OK)\r
- {\r
- VDS_SET_ERROR(hr);\r
- Log("Could not format partition, err:0x%lx (%s)", LASTERR, WindowsErrorString(hr));\r
- return FALSE;\r
}\r
\r
- return TRUE;\r
-}\r
-\r
-// Not supported for removable disk\r
-BOOL VDS_FormatVtoyEFIPart(int DriveIndex, UINT64 Offset)\r
-{\r
- VDS_PARA Para;\r
-\r
- memset(&Para, 0, sizeof(Para));\r
- Para.Offset = Offset;\r
- memcpy(Para.Name, L"VTOYEFI", 7 * 2);\r
-\r
- BOOL ret = VDS_DiskCommProc(INTF_PARTITIONMF, DriveIndex, VDS_CallBack_FormatVtoyEFI, (UINT64)&Para);\r
- Log("VDS_FormatVtoyEFIPart %d ret:%d (%s)", DriveIndex, ret, ret ? "SUCCESS" : "FAIL");\r
- return ret;\r
-}\r
-\r
-STATIC BOOL VDS_CallBack_ShrinkVolume(void* pInterface, VDS_DISK_PROP* pDiskProp, UINT64 data)\r
-{\r
- HRESULT hr, hr2;\r
- IVdsVolume* pVolume = (IVdsVolume*)pInterface;\r
- ULONG completed;\r
- IVdsAsync* pAsync;\r
-\r
- (void)pDiskProp;\r
-\r
- Log("VDS_CallBack_ShrinkVolume (%llu) ...", (ULONGLONG)data);\r
-\r
- hr = IVdsVolume_Shrink(pVolume, (ULONGLONG)data, &pAsync);\r
-\r
while (SUCCEEDED(hr))\r
{\r
hr = IVdsAsync_QueryStatus(pAsync, &hr2, &completed);\r
{\r
VDS_SET_ERROR(hr);\r
Log("Could not ShrinkVolume, 0x%x err:0x%lx (%s)", hr, LASTERR, WindowsErrorString(hr));\r
+\r
+ VDS_SET_ERROR(hr);\r
return FALSE;\r
}\r
\r
return TRUE;\r
}\r
\r
-BOOL VDS_ShrinkVolume(const char* VolumeGuid, UINT64 ReduceBytes)\r
+BOOL VDS_ShrinkVolume(int DriveIndex, const char* VolumeGuid, CHAR DriveLetter, UINT64 OldBytes, UINT64 ReduceBytes)\r
{\r
int i;\r
BOOL ret = FALSE;\r
WCHAR wGuid[128] = { 0 };\r
const char *guid = NULL;\r
+ VDS_PARA Para;\r
+\r
+ (VOID)DriveIndex;\r
+ (VOID)OldBytes;\r
\r
guid = strstr(VolumeGuid, "{");\r
if (!guid)\r
wGuid[i] = guid[i];\r
}\r
\r
- ret = VDS_VolumeCommProc(INTF_VOLUME, wGuid, VDS_CallBack_ShrinkVolume, ReduceBytes);\r
- Log("VDS_ShrinkVolume ret:%d (%s)", ret, ret ? "SUCCESS" : "FAIL");\r
+ Para.Offset = ReduceBytes;\r
+ Para.DriveLetter = DriveLetter;\r
+\r
+ ret = VDS_VolumeCommProc(INTF_VOLUME, wGuid, VDS_CallBack_ShrinkVolume, (UINT64)&Para);\r
+ Log("VDS_ShrinkVolume %C: ret:%d (%s)", DriveLetter, ret, ret ? "SUCCESS" : "FAIL");\r
return ret;\r
}
\ No newline at end of file
#include <commctrl.h>\r
#include <initguid.h>\r
#include <vds.h>\r
+#include <VersionHelpers.h>\r
#include "Ventoy2Disk.h"\r
#include "DiskService.h"\r
+\r
+STATIC BOOL IsPowershellExist(void)\r
+{\r
+ BOOL ret;\r
+\r
+ if (!IsWindows8OrGreater())\r
+ {\r
+ Log("This is before Windows8 powershell disk not supported.");\r
+ return FALSE;\r
+ }\r
+\r
+ ret = IsFileExist("C:\\Windows\\system32\\WindowsPowerShell\\v1.0\\powershell.exe");\r
+ if (!ret)\r
+ {\r
+ Log("powershell.exe not exist");\r
+ }\r
+\r
+ return ret;\r
+}\r
+\r
+int PSHELL_GetPartitionNumber(int PhyDrive, UINT64 Offset)\r
+{\r
+ int partnum = -1;\r
+ DWORD i = 0;\r
+ DWORD BufLen = 0;\r
+ DWORD dwBytes = 0;\r
+ BOOL bRet;\r
+ HANDLE hDrive;\r
+ LONGLONG PartStart;\r
+ DRIVE_LAYOUT_INFORMATION_EX *pDriveLayout = NULL;\r
+\r
+ Log("PSHELL_GetPartitionNumber PhyDrive:%d Offset:%llu", PhyDrive, Offset);\r
+\r
+ hDrive = GetPhysicalHandle(PhyDrive, FALSE, FALSE, FALSE);\r
+ if (hDrive == INVALID_HANDLE_VALUE)\r
+ {\r
+ return -1;\r
+ }\r
+\r
+ BufLen = (DWORD)(sizeof(PARTITION_INFORMATION_EX)* 256);\r
+\r
+ pDriveLayout = malloc(BufLen);\r
+ if (!pDriveLayout)\r
+ {\r
+ goto out;\r
+ }\r
+ memset(pDriveLayout, 0, BufLen);\r
+\r
+ bRet = DeviceIoControl(hDrive,\r
+ IOCTL_DISK_GET_DRIVE_LAYOUT_EX, NULL,\r
+ 0,\r
+ pDriveLayout,\r
+ BufLen,\r
+ &dwBytes,\r
+ NULL);\r
+ if (!bRet)\r
+ {\r
+ Log("Failed to ioctrl get drive layout ex %u", LASTERR);\r
+ goto out;\r
+ }\r
+\r
+ Log("PhyDrive:%d PartitionStyle=%s PartitionCount=%u", PhyDrive,\r
+ (pDriveLayout->PartitionStyle == PARTITION_STYLE_MBR) ? "MBR" : "GPT", pDriveLayout->PartitionCount);\r
+\r
+ for (i = 0; i < pDriveLayout->PartitionCount; i++)\r
+ {\r
+ PartStart = pDriveLayout->PartitionEntry[i].StartingOffset.QuadPart;\r
+ if (PartStart == (LONGLONG)Offset)\r
+ {\r
+ Log("[*] [%d] PartitionNumber=%u Offset=%lld Length=%lld ",\r
+ i,\r
+ pDriveLayout->PartitionEntry[i].PartitionNumber,\r
+ pDriveLayout->PartitionEntry[i].StartingOffset.QuadPart,\r
+ pDriveLayout->PartitionEntry[i].PartitionLength.QuadPart\r
+ );\r
+ partnum = (int)pDriveLayout->PartitionEntry[i].PartitionNumber;\r
+ }\r
+ else\r
+ {\r
+ Log("[ ] [%d] PartitionNumber=%u Offset=%lld Length=%lld ",\r
+ i,\r
+ pDriveLayout->PartitionEntry[i].PartitionNumber,\r
+ pDriveLayout->PartitionEntry[i].StartingOffset.QuadPart,\r
+ pDriveLayout->PartitionEntry[i].PartitionLength.QuadPart\r
+ );\r
+ }\r
+ }\r
+\r
+out:\r
+\r
+ CHECK_CLOSE_HANDLE(hDrive);\r
+ CHECK_FREE(pDriveLayout);\r
+\r
+ return partnum;\r
+}\r
+\r
+\r
+STATIC BOOL PSHELL_CommProc(const char *Cmd)\r
+{\r
+ CHAR CmdBuf[4096];\r
+ STARTUPINFOA Si;\r
+ PROCESS_INFORMATION Pi;\r
+\r
+ if (!IsPowershellExist())\r
+ {\r
+ return FALSE;\r
+ }\r
+\r
+ GetStartupInfoA(&Si);\r
+ Si.dwFlags |= STARTF_USESHOWWINDOW;\r
+ Si.wShowWindow = SW_HIDE;\r
+\r
+ sprintf_s(CmdBuf, sizeof(CmdBuf), "C:\\Windows\\system32\\WindowsPowerShell\\v1.0\\powershell.exe -Command \"&{ %s }\"", Cmd);\r
+\r
+ Log("CreateProcess <%s>", CmdBuf);\r
+ CreateProcessA(NULL, CmdBuf, NULL, NULL, FALSE, 0, NULL, NULL, &Si, &Pi);\r
+\r
+ Log("Wair process ...");\r
+ WaitForSingleObject(Pi.hProcess, INFINITE);\r
+ Log("Process finished...");\r
+\r
+ CHECK_CLOSE_HANDLE(Pi.hProcess);\r
+ CHECK_CLOSE_HANDLE(Pi.hThread);\r
+\r
+ return TRUE;\r
+}\r
+\r
+\r
+BOOL PSHELL_CleanDisk(int DriveIndex)\r
+{\r
+ BOOL ret;\r
+ CHAR CmdBuf[512];\r
+\r
+ sprintf_s(CmdBuf, sizeof(CmdBuf), "Clear-Disk -Number %d -RemoveData -RemoveOEM -Confirm:$false", DriveIndex);\r
+ ret = PSHELL_CommProc(CmdBuf);\r
+ Log("CleanDiskByPowershell<%d> ret:%d (%s)", DriveIndex, ret, ret ? "SUCCESS" : "FAIL");\r
+\r
+ return ret;\r
+}\r
+\r
+\r
+BOOL PSHELL_DeleteVtoyEFIPartition(int DriveIndex, UINT64 EfiPartOffset)\r
+{\r
+ int Part;\r
+ BOOL ret;\r
+ CHAR CmdBuf[512];\r
+\r
+ Part = PSHELL_GetPartitionNumber(DriveIndex, EfiPartOffset);\r
+ if (Part < 0)\r
+ {\r
+ ret = FALSE;\r
+ }\r
+ else\r
+ {\r
+ sprintf_s(CmdBuf, sizeof(CmdBuf), "Remove-Partition -DiskNumber %d -PartitionNumber %d -Confirm:$false", DriveIndex, Part);\r
+ ret = PSHELL_CommProc(CmdBuf);\r
+ }\r
+ \r
+ Log("PSHELL_DeleteVtoyEFIPartition<%d> ret:%d (%s)", DriveIndex, ret, ret ? "SUCCESS" : "FAIL");\r
+ return ret;\r
+}\r
+\r
+\r
+BOOL PSHELL_ChangeVtoyEFI2ESP(int DriveIndex, UINT64 Offset)\r
+{\r
+ int Part;\r
+ BOOL ret;\r
+ CHAR CmdBuf[512];\r
+\r
+ Part = PSHELL_GetPartitionNumber(DriveIndex, Offset);\r
+ if (Part < 0)\r
+ {\r
+ ret = FALSE;\r
+ }\r
+ else\r
+ {\r
+ sprintf_s(CmdBuf, sizeof(CmdBuf), "Set-Partition -DiskNumber %d -PartitionNumber %d -gpttype '{C12A7328-F81F-11D2-BA4B-00A0C93EC93B}' -Confirm:$false", DriveIndex, Part);\r
+ ret = PSHELL_CommProc(CmdBuf);\r
+ }\r
+\r
+ Log("PSHELL_ChangeVtoyEFI2ESP<%d> ret:%d (%s)", DriveIndex, ret, ret ? "SUCCESS" : "FAIL");\r
+ return ret;\r
+}\r
+\r
+\r
+BOOL PSHELL_ChangeVtoyEFI2Basic(int DriveIndex, UINT64 Offset)\r
+{\r
+ int Part;\r
+ BOOL ret;\r
+ CHAR CmdBuf[512];\r
+\r
+ Part = PSHELL_GetPartitionNumber(DriveIndex, Offset);\r
+ if (Part < 0)\r
+ {\r
+ ret = FALSE;\r
+ }\r
+ else\r
+ {\r
+ sprintf_s(CmdBuf, sizeof(CmdBuf), "Set-Partition -DiskNumber %d -PartitionNumber %d -gpttype '{ebd0a0a2-b9e5-4433-87c0-68b6b72699c7}' -Confirm:$false", DriveIndex, Part);\r
+ ret = PSHELL_CommProc(CmdBuf);\r
+ }\r
+ \r
+ Log("PSHELL_ChangeVtoyEFI2Basic<%d> ret:%d (%s)", DriveIndex, ret, ret ? "SUCCESS" : "FAIL");\r
+ return ret;\r
+}\r
+\r
+BOOL PSHELL_ShrinkVolume(int DriveIndex, const char* VolumeGuid, CHAR DriveLetter, UINT64 OldBytes, UINT64 ReduceBytes)\r
+{\r
+ int Part;\r
+ BOOL ret;\r
+ CHAR CmdBuf[512];\r
+\r
+ (void)VolumeGuid;\r
+\r
+ Part = PSHELL_GetPartitionNumber(DriveIndex, SIZE_1MB);\r
+ if (Part < 0)\r
+ {\r
+ ret = FALSE;\r
+ }\r
+ else\r
+ {\r
+ sprintf_s(CmdBuf, sizeof(CmdBuf), "Resize-Partition -DiskNumber %d -PartitionNumber %d -Size %llu -Confirm:$false", \r
+ DriveIndex, Part, OldBytes - ReduceBytes);\r
+ ret = PSHELL_CommProc(CmdBuf);\r
+ }\r
+\r
+ Log("PSHELL_ShrinkVolume<%d> %C: ret:%d (%s)", DriveIndex, DriveLetter, ret, ret ? "SUCCESS" : "FAIL");\r
+ return ret;\r
+}\r
\r
Log("Formatting Part1 exFAT ...");\r
\r
+ disk_io_reset_write_error();\r
+\r
Ret = f_mkfs(TEXT("0:"), &Option, 0, 8 * 1024 * 1024);\r
if (FR_OK == Ret)\r
{\r
+ if (disk_io_is_write_error())\r
+ {\r
+ Log("Formatting Part1 exFAT failed, write error.");\r
+ return 1;\r
+ }\r
+\r
Log("Formatting Part1 exFAT success");\r
return 0;\r
}\r
}\r
else\r
{\r
+ PROGRESS_BAR_SET_POS(PT_LOCK_FOR_CLEAN);\r
+\r
FindProcessOccupyDisk(hDrive, pPhyDrive);\r
+\r
+ if (!VDS_IsLastAvaliable())\r
+ {\r
+ Log("###### [Error:] Virtual Disk Service (VDS) Unavailable ######");\r
+ Log("###### [Error:] Virtual Disk Service (VDS) Unavailable ######");\r
+ Log("###### [Error:] Virtual Disk Service (VDS) Unavailable ######");\r
+ Log("###### [Error:] Virtual Disk Service (VDS) Unavailable ######");\r
+ Log("###### [Error:] Virtual Disk Service (VDS) Unavailable ######");\r
+ }\r
}\r
\r
if (pGptInfo)\r
if (pPhyDrive->ResizeNoShrink == FALSE)\r
{\r
Log("Need to shrink the volume");\r
- if (VDS_ShrinkVolume(pPhyDrive->ResizeVolumeGuid, RecudeBytes))\r
+ if (DISK_ShrinkVolume(pPhyDrive->PhyDrive, pPhyDrive->ResizeVolumeGuid, pPhyDrive->Part1DriveLetter, pPhyDrive->ResizeOldPart1Size, RecudeBytes))\r
{\r
Log("Shrink volume success, now check again");\r
\r
memcpy(pMBR->PartTbl + (j + 1), pMBR->PartTbl + j, sizeof(PART_TABLE));\r
}\r
\r
+ memset(pMBR->PartTbl + 1, 0, sizeof(PART_TABLE));\r
VentoyFillMBRLocation(pPhyDrive->SizeInBytes, (UINT32)pPhyDrive->ResizePart2StartSector, VENTOY_EFI_PART_SIZE / 512, pMBR->PartTbl + 1);\r
pMBR->PartTbl[0].Active = 0x80; // bootable\r
pMBR->PartTbl[1].Active = 0x00;\r
pMBR->BootCode[92] = 0x22;\r
\r
// to fix windows issue\r
+ memset(pGPT->PartTbl + 1, 0, sizeof(VTOY_GPT_PART_TBL));\r
memcpy(&(pGPT->PartTbl[1].PartType), &WindowsDataPartType, sizeof(GUID));\r
CoCreateGuid(&(pGPT->PartTbl[1].PartGuid));\r
\r
\r
//Update CRC\r
pGPT->Head.PartTblCrc = VentoyCrc32(pGPT->PartTbl, sizeof(pGPT->PartTbl));\r
+ pGPT->Head.Crc = 0;\r
pGPT->Head.Crc = VentoyCrc32(&(pGPT->Head), pGPT->Head.Length);\r
\r
Log("pGPT->Head.EfiStartLBA=%llu", (ULONGLONG)pGPT->Head.EfiStartLBA);\r
BOOL Esp2Basic = FALSE;\r
BOOL ChangeAttr = FALSE;\r
BOOL CleanDisk = FALSE;\r
+ BOOL DelEFI = FALSE;\r
BOOL bWriteBack = TRUE;\r
HANDLE hVolume;\r
HANDLE hDrive;\r
MBR_HEAD MBR;\r
BYTE *pBackup = NULL;\r
VTOY_GPT_INFO *pGptInfo = NULL;\r
+ VTOY_GPT_INFO *pGptBkup = NULL;\r
UINT8 ReservedData[4096];\r
\r
Log("#####################################################");\r
\r
if (pPhyDrive->PartStyle)\r
{\r
- pGptInfo = malloc(sizeof(VTOY_GPT_INFO));\r
+ pGptInfo = malloc(2 * sizeof(VTOY_GPT_INFO));\r
if (!pGptInfo)\r
{\r
return 1;\r
}\r
\r
- memset(pGptInfo, 0, sizeof(VTOY_GPT_INFO));\r
+ memset(pGptInfo, 0, 2 * sizeof(VTOY_GPT_INFO));\r
+ pGptBkup = pGptInfo + 1;\r
\r
// Read GPT Info\r
SetFilePointer(hDrive, 0, NULL, FILE_BEGIN);\r
ReadFile(hDrive, pGptInfo, sizeof(VTOY_GPT_INFO), &dwSize, NULL);\r
+ memcpy(pGptBkup, pGptInfo, sizeof(VTOY_GPT_INFO));\r
\r
//MBR will be used to compare with local boot image\r
memcpy(&MBR, &pGptInfo->MBR, sizeof(MBR_HEAD));\r
if (TryId == 1)\r
{\r
Log("Change GPT partition type to ESP");\r
- if (VDS_ChangeVtoyEFI2ESP(pPhyDrive->PhyDrive, StartSector * 512))\r
+ if (DISK_ChangeVtoyEFI2ESP(pPhyDrive->PhyDrive, StartSector * 512ULL))\r
{\r
Esp2Basic = TRUE;\r
Sleep(3000);\r
else if (TryId == 2)\r
{\r
Log("Change GPT partition attribute");\r
- if (VDS_ChangeVtoyEFIAttr(pPhyDrive->PhyDrive, 0x8000000000000001))\r
+ if (DISK_ChangeVtoyEFIAttr(pPhyDrive->PhyDrive, StartSector * 512ULL, 0x8000000000000001))\r
{\r
ChangeAttr = TRUE;\r
Sleep(2000);\r
}\r
}\r
else if (TryId == 3)\r
+ {\r
+ DISK_DeleteVtoyEFIPartition(pPhyDrive->PhyDrive, StartSector * 512ULL);\r
+ DelEFI = TRUE;\r
+ }\r
+ else if (TryId == 4)\r
{\r
Log("Clean disk GPT partition table");\r
if (BackupDataBeforeCleanDisk(pPhyDrive->PhyDrive, pPhyDrive->SizeInBytes, &pBackup))\r
\r
Log("Success to backup data before clean");\r
CleanDisk = TRUE;\r
- if (!VDS_CleanDisk(pPhyDrive->PhyDrive))\r
- {\r
- Sleep(3000);\r
- DSPT_CleanDisk(pPhyDrive->PhyDrive);\r
- }\r
+ DISK_CleanDisk(pPhyDrive->PhyDrive);\r
Sleep(3000);\r
}\r
else\r
\r
Status = ERROR_NOT_FOUND;\r
}\r
+ else if (DelEFI)\r
+ {\r
+ Status = ERROR_NOT_FOUND;\r
+ }\r
else if (Esp2Basic)\r
{\r
Status = ERROR_NOT_FOUND;\r
CHECK_CLOSE_HANDLE(hDrive);\r
\r
Log("Now delete partition 2...");\r
- VDS_DeleteVtoyEFIPartition(pPhyDrive->PhyDrive);\r
+ DISK_DeleteVtoyEFIPartition(pPhyDrive->PhyDrive, StartSector * 512ULL);\r
\r
hDrive = GetPhysicalHandle(pPhyDrive->PhyDrive, TRUE, TRUE, FALSE);\r
if (hDrive == INVALID_HANDLE_VALUE)\r
\r
Sleep(1000);\r
}\r
+ else if (DelEFI)\r
+ {\r
+ VTOY_GPT_HDR BackupHdr;\r
+\r
+ VentoyFillBackupGptHead(pGptBkup, &BackupHdr);\r
+ if (!WriteBackupDataToDisk(hDrive, 512 * pGptBkup->Head.EfiBackupLBA, (BYTE*)(&BackupHdr), 512))\r
+ {\r
+ bWriteBack = FALSE;\r
+ }\r
+\r
+ if (!WriteBackupDataToDisk(hDrive, 512 * (pGptBkup->Head.EfiBackupLBA - 32), (BYTE*)(pGptBkup->PartTbl), 32 * 512))\r
+ {\r
+ bWriteBack = FALSE;\r
+ }\r
+\r
+ if (!WriteBackupDataToDisk(hDrive, 512, (BYTE*)pGptBkup + 512, 33 * 512))\r
+ {\r
+ bWriteBack = FALSE;\r
+ }\r
+\r
+ if (bWriteBack)\r
+ {\r
+ Log("Write backup partition table success");\r
+ }\r
+ else\r
+ {\r
+ Log("Write backup partition table failed");\r
+ }\r
+\r
+ Sleep(1000);\r
+ }\r
\r
//Refresh Drive Layout\r
DeviceIoControl(hDrive, IOCTL_DISK_UPDATE_PROPERTIES, NULL, 0, NULL, 0, &dwSize, NULL);\r
}\r
else\r
{\r
+ PROGRESS_BAR_SET_POS(PT_LOCK_FOR_CLEAN);\r
FindProcessOccupyDisk(hDrive, pPhyDrive);\r
}\r
\r
if (Esp2Basic)\r
{\r
Log("Recover GPT partition type to basic");\r
- VDS_ChangeVtoyEFI2Basic(pPhyDrive->PhyDrive, StartSector * 512);\r
+ DISK_ChangeVtoyEFI2Basic(pPhyDrive->PhyDrive, StartSector * 512);\r
}\r
\r
if (pPhyDrive->PartStyle == 1)\r
if (ChangeAttr || ((pPhyDrive->Part2GPTAttr >> 56) != 0xC0))\r
{\r
Log("Change EFI partition attr %u <0x%llx> to <0x%llx>", ChangeAttr, pPhyDrive->Part2GPTAttr, 0xC000000000000001ULL);\r
- if (VDS_ChangeVtoyEFIAttr(pPhyDrive->PhyDrive, 0xC000000000000001ULL))\r
+ if (DISK_ChangeVtoyEFIAttr(pPhyDrive->PhyDrive, StartSector * 512ULL, 0xC000000000000001ULL))\r
{\r
Log("Change EFI partition attr success");\r
pPhyDrive->Part2GPTAttr = 0xC000000000000001ULL;\r
\r
}\r
\r
+const char* GUID2String(void *guid, char *buf, int len)\r
+{\r
+ GUID* pGUID = (GUID*)guid;\r
+ sprintf_s(buf, len, "{%08x-%04x-%04x-%02x%02x-%02x%02x%02x%02x%02x%02x}",\r
+ pGUID->Data1, pGUID->Data2, pGUID->Data3,\r
+ pGUID->Data4[0], pGUID->Data4[1],\r
+ pGUID->Data4[2], pGUID->Data4[3], pGUID->Data4[4], pGUID->Data4[5], pGUID->Data4[6], pGUID->Data4[7]\r
+ );\r
+ return buf;\r
+}\r
+\r
BOOL IsPathExist(BOOL Dir, const char *Fmt, ...)\r
{\r
va_list Arg;\r
typedef BOOL(WINAPI *LPFN_ISWOW64PROCESS)(HANDLE, PBOOL);\r
LPFN_ISWOW64PROCESS fnIsWow64Process;\r
BOOL bIsWow64 = FALSE;\r
+ CHAR Wow64Dir[MAX_PATH];\r
\r
fnIsWow64Process = (LPFN_ISWOW64PROCESS)GetProcAddress(GetModuleHandleA("kernel32"), "IsWow64Process");\r
if (NULL != fnIsWow64Process)\r
fnIsWow64Process(GetCurrentProcess(), &bIsWow64);\r
}\r
\r
+ if (!bIsWow64)\r
+ {\r
+ if (GetSystemWow64DirectoryA(Wow64Dir, sizeof(Wow64Dir)))\r
+ {\r
+ Log("GetSystemWow64DirectoryA=<%s>", Wow64Dir);\r
+ bIsWow64 = TRUE;\r
+ }\r
+ }\r
+\r
return bIsWow64;\r
}\r
\r
UINT32 PartStartSector;\r
UINT32 PartSectorCount;\r
CHAR PhyDrivePath[128];\r
+ CHAR GUIDStr[128];\r
+ GUID ZeroGuid = { 0 };\r
VTOY_GPT_INFO *pGpt = NULL;\r
\r
safe_sprintf(PhyDrivePath, "\\\\.\\PhysicalDrive%d", PhyDrive);\r
return FALSE;\r
}\r
\r
- for (i = 0; i < 4; i++)\r
- {\r
- Log("=========== Disk%d Partition Table %d ============", PhyDrive, i + 1);\r
- Log("PartTbl.Active = 0x%x", MBR.PartTbl[i].Active);\r
- Log("PartTbl.FsFlag = 0x%x", MBR.PartTbl[i].FsFlag);\r
- Log("PartTbl.StartSectorId = %u", MBR.PartTbl[i].StartSectorId);\r
- Log("PartTbl.SectorCount = %u", MBR.PartTbl[i].SectorCount);\r
- Log("PartTbl.StartHead = %u", MBR.PartTbl[i].StartHead);\r
- Log("PartTbl.StartSector = %u", MBR.PartTbl[i].StartSector);\r
- Log("PartTbl.StartCylinder = %u", MBR.PartTbl[i].StartCylinder);\r
- Log("PartTbl.EndHead = %u", MBR.PartTbl[i].EndHead);\r
- Log("PartTbl.EndSector = %u", MBR.PartTbl[i].EndSector);\r
- Log("PartTbl.EndCylinder = %u", MBR.PartTbl[i].EndCylinder);\r
- }\r
+ \r
\r
if (MBR.PartTbl[0].FsFlag == 0xEE)\r
{\r
return FALSE;\r
}\r
\r
+ for (i = 0; i < 128; i++)\r
+ {\r
+ if (memcmp(&(pGpt->PartTbl[i].PartGuid), &ZeroGuid, sizeof(GUID)) == 0)\r
+ {\r
+ continue;\r
+ }\r
+\r
+ Log("=========== Disk%d GPT Partition %d ============", PhyDrive, i + 1);\r
+ \r
+ Log("PartTbl.PartType = %s", GUID2String(&pGpt->PartTbl[i].PartType, GUIDStr, sizeof(GUIDStr)));\r
+ Log("PartTbl.PartGuid = %s", GUID2String(&pGpt->PartTbl[i].PartGuid, GUIDStr, sizeof(GUIDStr)));\r
+ Log("PartTbl.StartLBA = %llu", (ULONGLONG)pGpt->PartTbl[i].StartLBA);\r
+ Log("PartTbl.LastLBA = %llu", (ULONGLONG)pGpt->PartTbl[i].LastLBA);\r
+ Log("PartTbl.Attribute = 0x%llx", pGpt->PartTbl[i].Attr);\r
+ Log("PartTbl.Name = %S", pGpt->PartTbl[i].Name);\r
+ }\r
+\r
if (memcmp(pGpt->PartTbl[1].Name, L"VTOYEFI", 7 * 2))\r
{\r
if (pGpt->PartTbl[1].Name[0])\r
{\r
CHECK_CLOSE_HANDLE(hDrive);\r
\r
+ for (i = 0; i < 4; i++)\r
+ {\r
+ Log("=========== Disk%d MBR Partition %d ============", PhyDrive, i + 1);\r
+ Log("PartTbl.Active = 0x%x", MBR.PartTbl[i].Active);\r
+ Log("PartTbl.FsFlag = 0x%x", MBR.PartTbl[i].FsFlag);\r
+ Log("PartTbl.StartSectorId = %u", MBR.PartTbl[i].StartSectorId);\r
+ Log("PartTbl.SectorCount = %u", MBR.PartTbl[i].SectorCount);\r
+ Log("PartTbl.StartHead = %u", MBR.PartTbl[i].StartHead);\r
+ Log("PartTbl.StartSector = %u", MBR.PartTbl[i].StartSector);\r
+ Log("PartTbl.StartCylinder = %u", MBR.PartTbl[i].StartCylinder);\r
+ Log("PartTbl.EndHead = %u", MBR.PartTbl[i].EndHead);\r
+ Log("PartTbl.EndSector = %u", MBR.PartTbl[i].EndSector);\r
+ Log("PartTbl.EndCylinder = %u", MBR.PartTbl[i].EndCylinder);\r
+ }\r
+\r
if (MBR.PartTbl[0].StartSectorId != 2048)\r
{\r
Log("Part1 not match %u", MBR.PartTbl[0].StartSectorId);\r
UINT64 Part2GPTAttr;\r
\r
BOOL ResizeNoShrink;\r
+ UINT64 ResizeOldPart1Size;\r
+ CHAR Part1DriveLetter;\r
CHAR ResizeVolumeGuid[64];\r
CHAR FsName[64];\r
UINT64 ResizePart2StartSector;\r
\r
HANDLE GetPhysicalHandle(int Drive, BOOLEAN bLockDrive, BOOLEAN bWriteAccess, BOOLEAN bWriteShare);\r
void InitComboxCtrl(HWND hWnd, int PhyDrive);\r
+int disk_io_is_write_error(void);\r
+void disk_io_reset_write_error(void);\r
+const char* GUID2String(void* guid, char* buf, int len);\r
\r
#define VTSI_SUPPORT 1\r
\r
</ItemDefinitionGroup>
<ItemGroup>
<ClCompile Include="crc32.c" />
+ <ClCompile Include="DiskService.c" />
<ClCompile Include="DiskService_diskpart.c" />
<ClCompile Include="DiskService_vds.c" />
<ClCompile Include="DiskService_wmsa.c" />
<ClCompile Include="DiskService_wmsa.c">
<Filter>源文件</Filter>
</ClCompile>
+ <ClCompile Include="DiskService.c">
+ <Filter>源文件</Filter>
+ </ClCompile>
</ItemGroup>
<ItemGroup>
<ClInclude Include="Ventoy2Disk.h">
int g_VentoyMaxSeg = 0;
int g_VentoyCurSeg = -1;
UINT64 g_VentoyDataOffset = 0;
+int g_write_error = 0;
+int g_error_print_cnt = 0;
+
+void disk_io_reset_write_error(void)
+{
+ g_write_error = 0;
+ g_error_print_cnt = 0;
+}
+
+
+int disk_io_is_write_error(void)
+{
+ return g_write_error;
+}
void disk_io_set_param(HANDLE Handle, UINT64 SectorCount)
{
bRet = WriteFile(g_hPhyDrive, buff, count * 512, &dwSize, NULL);
- if (dwSize != count * 512)
+ if ((!bRet) || (dwSize != count * 512))
{
- Log("WriteFile error bRet:%u WriteSize:%u dwSize:%u ErrCode:%u", bRet, count * 512, dwSize, GetLastError());
+ g_write_error = 1;
+ g_error_print_cnt++;
+
+ if (g_error_print_cnt <= 10)
+ {
+ Log("WriteFile error bRet:%u WriteSize:%u dwSize:%u ErrCode:%u", bRet, count * 512, dwSize, GetLastError());
+ }
}
return RES_OK;