From b84fa499e712b23b2488678bf691a15584bd6dbb Mon Sep 17 00:00:00 2001 From: Eric Kohl Date: Mon, 5 Jan 2026 23:14:32 +0100 Subject: [PATCH] [DISKPART] Implement the format command - A lot of volume manager and mount manager related stuff is still missing. - The label is not set yet. --- base/system/diskpart/format.c | 272 +++++++++++++++++++++++++++++ base/system/diskpart/lang/de-DE.rc | 7 + base/system/diskpart/lang/en-US.rc | 7 + base/system/diskpart/lang/it-IT.rc | 7 + base/system/diskpart/lang/pl-PL.rc | 7 + base/system/diskpart/lang/pt-PT.rc | 7 + base/system/diskpart/lang/ro-RO.rc | 7 + base/system/diskpart/lang/ru-RU.rc | 7 + base/system/diskpart/lang/sq-AL.rc | 7 + base/system/diskpart/lang/tr-TR.rc | 7 + base/system/diskpart/lang/zh-CN.rc | 7 + base/system/diskpart/lang/zh-TW.rc | 7 + base/system/diskpart/resource.h | 16 +- 13 files changed, 359 insertions(+), 6 deletions(-) diff --git a/base/system/diskpart/format.c b/base/system/diskpart/format.c index 157efe2499a..de170c6508a 100644 --- a/base/system/diskpart/format.c +++ b/base/system/diskpart/format.c @@ -8,10 +8,282 @@ #include "diskpart.h" +#include + +#define NDEBUG +#include + +static +BOOL +GetFsModule( + _In_ PWSTR pszFileSystem, + _Out_ HMODULE *phModule) +{ + WCHAR szDllNameBuffer[32]; + HKEY hKey; + DWORD dwLength, dwErr; + + *phModule = NULL; + + dwErr = RegOpenKeyExW(HKEY_LOCAL_MACHINE, + L"SOFTWARE\\ReactOS\\ReactOS\\CurrentVersion\\IFS", + 0, + KEY_READ, + &hKey); + if (dwErr != ERROR_SUCCESS) + { + DPRINT1("Failed to open!\n"); + return FALSE; + } + + dwLength = sizeof(szDllNameBuffer); + dwErr = RegQueryValueExW(hKey, + pszFileSystem, + NULL, + NULL, + (PBYTE)szDllNameBuffer, + &dwLength); + + RegCloseKey(hKey); + + if (dwErr != ERROR_SUCCESS) + { + DPRINT1("Failed to query!\n"); + return FALSE; + } + + *phModule = LoadLibraryW(szDllNameBuffer); + if (*phModule == NULL) + { + DPRINT1("Failed to load!\n"); + return FALSE; + } + + return TRUE; +} + + +BOOLEAN +WINAPI +FormatCallback( + CALLBACKCOMMAND Command, + ULONG Size, + PVOID Argument) +{ + PDWORD percent; + + switch (Command) + { + case PROGRESS: + percent = (PDWORD)Argument; + ConResPrintf(StdOut, IDS_FORMAT_PROGRESS, *percent); + break; + + case DONE: + break; + + default: + DPRINT1("Callback (%u %lu %p)\n", Command, Size, Argument); + break; + } + + return TRUE; +} + + EXIT_CODE format_main( _In_ INT argc, _In_ PWSTR *argv) { + UNICODE_STRING usDriveRoot; + UNICODE_STRING LabelString; + PWSTR pszSuffix = NULL; + PWSTR pszFileSystem = NULL; + PWSTR pszLabel = NULL; + BOOLEAN bQuickFormat = FALSE; + ULONG ulClusterSize = 0; + HMODULE hModule = NULL; + PULIB_FORMAT pFormat = NULL; +// FMIFS_MEDIA_FLAG MediaType = FMIFS_HARDDISK; + INT i; + BOOLEAN Success = FALSE; + + + if (CurrentVolume == NULL) + { + ConResPuts(StdOut, IDS_SELECT_NO_VOLUME); + return EXIT_SUCCESS; + } + + for (i = 1; i < argc; i++) + { + if (_wcsicmp(argv[i], L"noerr") == 0) + { + /* noerr */ + DPRINT("NoErr\n", pszSuffix); + ConPuts(StdOut, L"The NOERR option is not supported yet!\n"); +#if 0 + bNoErr = TRUE; +#endif + } + } + + for (i = 1; i < argc; i++) + { + ConPrintf(StdOut, L"%s\n", argv[i]); + + if (HasPrefix(argv[i], L"fs=", &pszSuffix)) + { + /* fs= */ + pszFileSystem = pszSuffix; + } + else if (HasPrefix(argv[i], L"revision=", &pszSuffix)) + { + /* revision= */ + ConPuts(StdOut, L"The REVISION option is not supported yet!\n"); + } + else if (HasPrefix(argv[i], L"label=", &pszSuffix)) + { + /* label=<"label"> */ + pszLabel = pszSuffix; + } + else if (HasPrefix(argv[i], L"unit=", &pszSuffix)) + { + /* unit= */ + ulClusterSize = wcstoul(pszSuffix, NULL, 0); + if ((ulClusterSize == 0) && (errno == ERANGE)) + { + ConResPuts(StdErr, IDS_ERROR_INVALID_ARGS); + goto done; + } + } + else if (_wcsicmp(argv[i], L"recommended") == 0) + { + /* recommended */ + ConPuts(StdOut, L"The RECOMMENDED option is not supported yet!\n"); + } + else if (_wcsicmp(argv[i], L"quick") == 0) + { + /* quick */ + bQuickFormat = TRUE; + } + else if (_wcsicmp(argv[i], L"compress") == 0) + { + /* compress */ + ConPuts(StdOut, L"The COMPRESS option is not supported yet!\n"); + } + else if (_wcsicmp(argv[i], L"override") == 0) + { + /* override */ + ConPuts(StdOut, L"The OVERRIDE option is not supported yet!\n"); + } + else if (_wcsicmp(argv[i], L"duplicate") == 0) + { + /* duplicate */ + ConPuts(StdOut, L"The DUPLICATE option is not supported yet!\n"); + } + else if (_wcsicmp(argv[i], L"nowait") == 0) + { + /* nowait */ + ConPuts(StdOut, L"The NOWAIT option is not supported yet!\n"); + } + else if (_wcsicmp(argv[i], L"noerr") == 0) + { + /* noerr - Already handled above */ + } + else + { + ConResPuts(StdErr, IDS_ERROR_INVALID_ARGS); + return EXIT_SUCCESS; + } + } + + DPRINT("VolumeName : %S\n", CurrentVolume->VolumeName); + DPRINT("DeviceName : %S\n", CurrentVolume->DeviceName); + DPRINT("DriveLetter : %C\n", CurrentVolume->DriveLetter); +#if 0 + switch (CurrentVolume->VolumeType) + { + case VOLUME_TYPE_CDROM: + MediaType = FMIFS_REMOVABLE; // ??? + break; + + case VOLUME_TYPE_PARTITION: + MediaType = FMIFS_HARDDISK; + break; + + case VOLUME_TYPE_REMOVABLE: + MediaType = FMIFS_REMOVABLE; // ??? + break; + + case VOLUME_TYPE_UNKNOWN: + default: + MediaType = FMIFS_REMOVABLE; // ??? + break; + } +#endif + + DPRINT("FileSystem: %S\n", pszFileSystem); + DPRINT("Label: %S\n", pszLabel); + DPRINT("Quick: %d\n", bQuickFormat); + DPRINT("ClusterSize: %lu\n", ulClusterSize); + + RtlDosPathNameToNtPathName_U(CurrentVolume->VolumeName, &usDriveRoot, NULL, NULL); + + /* Remove trailing backslash */ + if (usDriveRoot.Buffer[(usDriveRoot.Length / sizeof(WCHAR)) - 1] == L'\\') + { + usDriveRoot.Buffer[(usDriveRoot.Length / sizeof(WCHAR)) - 1] = UNICODE_NULL; + usDriveRoot.Length -= sizeof(WCHAR); + } + + DPRINT("DriveRoot: %wZ\n", &usDriveRoot); + + /* Use the FAT filesystem as default */ + if (pszFileSystem == NULL) + pszFileSystem = L"FAT"; + + BOOLEAN bBackwardCompatible = FALSE; // Default to latest FS versions. + if (_wcsicmp(pszFileSystem, L"FAT") == 0) + bBackwardCompatible = TRUE; + // else if (wcsicmp(pszFileSystem, L"FAT32") == 0) + // bBackwardCompatible = FALSE; + + if (pszLabel == NULL) + pszLabel = L""; + + RtlInitUnicodeString(&LabelString, pszLabel); + + if (!GetFsModule(pszFileSystem, &hModule)) + { + DPRINT1("GetFsModule() failed\n"); + goto done; + } + + pFormat = (PULIB_FORMAT)GetProcAddress(hModule, "Format"); + if (pFormat) + { + Success = (pFormat)(&usDriveRoot, + FormatCallback, + bQuickFormat, + bBackwardCompatible, + FMIFS_HARDDISK, //MediaType, + &LabelString, + ulClusterSize); + } + +done: + ConPuts(StdOut, L"\n"); + if (Success) + ConResPrintf(StdOut, IDS_FORMAT_SUCCESS); + else + ConResPrintf(StdOut, IDS_FORMAT_FAIL); + + if (hModule) + FreeLibrary(hModule); + + RtlFreeUnicodeString(&usDriveRoot); + return EXIT_SUCCESS; } diff --git a/base/system/diskpart/lang/de-DE.rc b/base/system/diskpart/lang/de-DE.rc index 1865c4be9f6..2e7210f1926 100644 --- a/base/system/diskpart/lang/de-DE.rc +++ b/base/system/diskpart/lang/de-DE.rc @@ -111,6 +111,13 @@ BEGIN IDS_FILESYSTEMS_DEFAULT " (Standard)" END +STRINGTABLE +BEGIN + IDS_FORMAT_FAIL "\nDiskPart failed to format the selected volume.\n" + IDS_FORMAT_SUCCESS "\nDiskPart successfully formated the selected volume.\n" + IDS_FORMAT_PROGRESS "\r %3lu percent completed" +END + STRINGTABLE BEGIN IDS_GPT_FAIL "\nDiskPart failed to assign atttributes to the selected GPT partition.\n" diff --git a/base/system/diskpart/lang/en-US.rc b/base/system/diskpart/lang/en-US.rc index c36839b4db3..f88e0d68303 100644 --- a/base/system/diskpart/lang/en-US.rc +++ b/base/system/diskpart/lang/en-US.rc @@ -111,6 +111,13 @@ BEGIN IDS_FILESYSTEMS_DEFAULT " (Default)" END +STRINGTABLE +BEGIN + IDS_FORMAT_FAIL "\nDiskPart failed to format the selected volume.\n" + IDS_FORMAT_SUCCESS "\nDiskPart successfully formated the selected volume.\n" + IDS_FORMAT_PROGRESS "\r %3lu percent completed" +END + STRINGTABLE BEGIN IDS_GPT_FAIL "\nDiskPart failed to assign atttributes to the selected GPT partition.\n" diff --git a/base/system/diskpart/lang/it-IT.rc b/base/system/diskpart/lang/it-IT.rc index 47ec62573a8..d15c3c6911d 100644 --- a/base/system/diskpart/lang/it-IT.rc +++ b/base/system/diskpart/lang/it-IT.rc @@ -118,6 +118,13 @@ BEGIN IDS_FILESYSTEMS_DEFAULT " (Default)" END +STRINGTABLE +BEGIN + IDS_FORMAT_FAIL "\nDiskPart failed to format the selected volume.\n" + IDS_FORMAT_SUCCESS "\nDiskPart successfully formated the selected volume.\n" + IDS_FORMAT_PROGRESS "\r %3lu percent completed" +END + STRINGTABLE BEGIN IDS_GPT_FAIL "\nDiskPart failed to assign atttributes to the selected GPT partition.\n" diff --git a/base/system/diskpart/lang/pl-PL.rc b/base/system/diskpart/lang/pl-PL.rc index 14cea6fee98..1f2484bbfc2 100644 --- a/base/system/diskpart/lang/pl-PL.rc +++ b/base/system/diskpart/lang/pl-PL.rc @@ -111,6 +111,13 @@ BEGIN IDS_FILESYSTEMS_DEFAULT " (Default)" END +STRINGTABLE +BEGIN + IDS_FORMAT_FAIL "\nDiskPart failed to format the selected volume.\n" + IDS_FORMAT_SUCCESS "\nDiskPart successfully formated the selected volume.\n" + IDS_FORMAT_PROGRESS "\r %3lu percent completed" +END + STRINGTABLE BEGIN IDS_GPT_FAIL "\nDiskPart failed to assign atttributes to the selected GPT partition.\n" diff --git a/base/system/diskpart/lang/pt-PT.rc b/base/system/diskpart/lang/pt-PT.rc index 5fb15965aa0..ce4673624cb 100644 --- a/base/system/diskpart/lang/pt-PT.rc +++ b/base/system/diskpart/lang/pt-PT.rc @@ -113,6 +113,13 @@ BEGIN IDS_FILESYSTEMS_DEFAULT " (Default)" END +STRINGTABLE +BEGIN + IDS_FORMAT_FAIL "\nDiskPart failed to format the selected volume.\n" + IDS_FORMAT_SUCCESS "\nDiskPart successfully formated the selected volume.\n" + IDS_FORMAT_PROGRESS "\r %3lu percent completed" +END + STRINGTABLE BEGIN IDS_GPT_FAIL "\nDiskPart failed to assign atttributes to the selected GPT partition.\n" diff --git a/base/system/diskpart/lang/ro-RO.rc b/base/system/diskpart/lang/ro-RO.rc index 84109f407ee..418c463b296 100644 --- a/base/system/diskpart/lang/ro-RO.rc +++ b/base/system/diskpart/lang/ro-RO.rc @@ -119,6 +119,13 @@ BEGIN IDS_FILESYSTEMS_DEFAULT " (Default)" END +STRINGTABLE +BEGIN + IDS_FORMAT_FAIL "\nDiskPart failed to format the selected volume.\n" + IDS_FORMAT_SUCCESS "\nDiskPart successfully formated the selected volume.\n" + IDS_FORMAT_PROGRESS "\r %3lu percent completed" +END + STRINGTABLE BEGIN IDS_GPT_FAIL "\nDiskPart failed to assign atttributes to the selected GPT partition.\n" diff --git a/base/system/diskpart/lang/ru-RU.rc b/base/system/diskpart/lang/ru-RU.rc index ae3a4edcd2d..a0adb3f60e1 100644 --- a/base/system/diskpart/lang/ru-RU.rc +++ b/base/system/diskpart/lang/ru-RU.rc @@ -113,6 +113,13 @@ BEGIN IDS_FILESYSTEMS_DEFAULT " (Default)" END +STRINGTABLE +BEGIN + IDS_FORMAT_FAIL "\nDiskPart failed to format the selected volume.\n" + IDS_FORMAT_SUCCESS "\nDiskPart successfully formated the selected volume.\n" + IDS_FORMAT_PROGRESS "\r %3lu percent completed" +END + STRINGTABLE BEGIN IDS_GPT_FAIL "\nDiskPart failed to assign atttributes to the selected GPT partition.\n" diff --git a/base/system/diskpart/lang/sq-AL.rc b/base/system/diskpart/lang/sq-AL.rc index b81becd2f36..0b62fc9d6a5 100644 --- a/base/system/diskpart/lang/sq-AL.rc +++ b/base/system/diskpart/lang/sq-AL.rc @@ -115,6 +115,13 @@ BEGIN IDS_FILESYSTEMS_DEFAULT " (Default)" END +STRINGTABLE +BEGIN + IDS_FORMAT_FAIL "\nDiskPart failed to format the selected volume.\n" + IDS_FORMAT_SUCCESS "\nDiskPart successfully formated the selected volume.\n" + IDS_FORMAT_PROGRESS "\r %3lu percent completed" +END + STRINGTABLE BEGIN IDS_GPT_FAIL "\nDiskPart failed to assign atttributes to the selected GPT partition.\n" diff --git a/base/system/diskpart/lang/tr-TR.rc b/base/system/diskpart/lang/tr-TR.rc index cab648ac4ac..5983c66cf0e 100644 --- a/base/system/diskpart/lang/tr-TR.rc +++ b/base/system/diskpart/lang/tr-TR.rc @@ -121,6 +121,13 @@ BEGIN IDS_FILESYSTEMS_DEFAULT " (Default)" END +STRINGTABLE +BEGIN + IDS_FORMAT_FAIL "\nDiskPart failed to format the selected volume.\n" + IDS_FORMAT_SUCCESS "\nDiskPart successfully formated the selected volume.\n" + IDS_FORMAT_PROGRESS "\r %3lu percent completed" +END + STRINGTABLE BEGIN IDS_GPT_FAIL "\nDiskPart failed to assign atttributes to the selected GPT partition.\n" diff --git a/base/system/diskpart/lang/zh-CN.rc b/base/system/diskpart/lang/zh-CN.rc index 29ff9a90f85..d665c5dd216 100644 --- a/base/system/diskpart/lang/zh-CN.rc +++ b/base/system/diskpart/lang/zh-CN.rc @@ -120,6 +120,13 @@ BEGIN IDS_FILESYSTEMS_DEFAULT " (Default)" END +STRINGTABLE +BEGIN + IDS_FORMAT_FAIL "\nDiskPart failed to format the selected volume.\n" + IDS_FORMAT_SUCCESS "\nDiskPart successfully formated the selected volume.\n" + IDS_FORMAT_PROGRESS "\r %3lu percent completed" +END + STRINGTABLE BEGIN IDS_GPT_FAIL "\nDiskPart failed to assign atttributes to the selected GPT partition.\n" diff --git a/base/system/diskpart/lang/zh-TW.rc b/base/system/diskpart/lang/zh-TW.rc index ba4f9c7188e..8c9fe9cf416 100644 --- a/base/system/diskpart/lang/zh-TW.rc +++ b/base/system/diskpart/lang/zh-TW.rc @@ -120,6 +120,13 @@ BEGIN IDS_FILESYSTEMS_DEFAULT " (Default)" END +STRINGTABLE +BEGIN + IDS_FORMAT_FAIL "\nDiskPart failed to format the selected volume.\n" + IDS_FORMAT_SUCCESS "\nDiskPart successfully formated the selected volume.\n" + IDS_FORMAT_PROGRESS "\r %3lu percent completed" +END + STRINGTABLE BEGIN IDS_GPT_FAIL "\nDiskPart failed to assign atttributes to the selected GPT partition.\n" diff --git a/base/system/diskpart/resource.h b/base/system/diskpart/resource.h index fc3fafab93c..313d75fe1f0 100644 --- a/base/system/diskpart/resource.h +++ b/base/system/diskpart/resource.h @@ -77,12 +77,16 @@ #define IDS_DETAIL_NO_DISKS 1137 #define IDS_DETAIL_NO_VOLUME 1138 -#define IDS_FILESYSTEMS_CURRENT 1180 -#define IDS_FILESYSTEMS_FORMATTING 1181 -#define IDS_FILESYSTEMS_TYPE 1182 -#define IDS_FILESYSTEMS_CLUSTERSIZE 1183 -#define IDS_FILESYSTEMS_SERIAL_NUMBER 1184 -#define IDS_FILESYSTEMS_DEFAULT 1185 +#define IDS_FILESYSTEMS_CURRENT 1170 +#define IDS_FILESYSTEMS_FORMATTING 1171 +#define IDS_FILESYSTEMS_TYPE 1172 +#define IDS_FILESYSTEMS_CLUSTERSIZE 1173 +#define IDS_FILESYSTEMS_SERIAL_NUMBER 1174 +#define IDS_FILESYSTEMS_DEFAULT 1175 + +#define IDS_FORMAT_FAIL 1180 +#define IDS_FORMAT_SUCCESS 1181 +#define IDS_FORMAT_PROGRESS 1182 #define IDS_GPT_FAIL 1190 #define IDS_GPT_SUCCESS 1191