Something went wrong. Try again.
Reactos
Something went wrong. Try again.
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101/* * PROJECT: ReactOS DiskPart * LICENSE: GPL - See COPYING in the top level directory * FILE: base/system/diskpart/create.c * PURPOSE: Manages all the partitions of the OS in an interactive way. * PROGRAMMERS: Lee Schroeder */
#include "diskpart.h"
#define NDEBUG#include <debug.h>
staticPPARTENTRYInsertGptPartition( _In_ PDISKENTRY pDisk, _In_ ULONGLONG ullSectorSize, _In_ const GUID *pPartitionType){ PPARTENTRY PartEntry, NewPartEntry; PLIST_ENTRY ListEntry;
for (ListEntry = pDisk->PrimaryPartListHead.Flink; ListEntry != &CurrentDisk->PrimaryPartListHead; ListEntry = ListEntry->Flink) { PartEntry = CONTAINING_RECORD(ListEntry, PARTENTRY, ListEntry); if (PartEntry->IsPartitioned) continue;
if (ullSectorSize == 0ULL) { DPRINT("Claim whole unused space!\n"); PartEntry->IsPartitioned = TRUE; PartEntry->New = TRUE; CopyMemory(&PartEntry->Gpt.PartitionType, pPartitionType, sizeof(GUID)); CreateGUID(&PartEntry->Gpt.PartitionId); PartEntry->Gpt.Attributes = 0ULL; PartEntry->PartitionNumber = 0; PartEntry->FormatState = Unformatted; PartEntry->FileSystemName[0] = L'\0';
return PartEntry; } else { if (ullSectorSize == PartEntry->SectorCount.QuadPart) { DPRINT("Claim matching unused space!\n"); PartEntry->IsPartitioned = TRUE; PartEntry->New = TRUE; CopyMemory(&PartEntry->Gpt.PartitionType, pPartitionType, sizeof(GUID)); CreateGUID(&PartEntry->Gpt.PartitionId); PartEntry->Gpt.Attributes = 0ULL; PartEntry->PartitionNumber = 0; PartEntry->FormatState = Unformatted; PartEntry->FileSystemName[0] = L'\0';
return PartEntry; } else if (ullSectorSize < PartEntry->SectorCount.QuadPart) { DPRINT("Claim part of unused space\n"); NewPartEntry = RtlAllocateHeap(RtlGetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(PPARTENTRY)); if (NewPartEntry == NULL) { ConPuts(StdOut, L"Memory allocation failed!\n"); return NULL; }
NewPartEntry->DiskEntry = PartEntry->DiskEntry;
NewPartEntry->StartSector.QuadPart = PartEntry->StartSector.QuadPart; NewPartEntry->SectorCount.QuadPart = ullSectorSize;
NewPartEntry->LogicalPartition = FALSE; NewPartEntry->IsPartitioned = TRUE; NewPartEntry->New = TRUE; CopyMemory(&NewPartEntry->Gpt.PartitionType, pPartitionType, sizeof(GUID)); CreateGUID(&NewPartEntry->Gpt.PartitionId); NewPartEntry->Gpt.Attributes = 0ULL; NewPartEntry->PartitionNumber = 0; NewPartEntry->FormatState = Unformatted; NewPartEntry->FileSystemName[0] = L'\0';
PartEntry->StartSector.QuadPart += ullSectorSize; PartEntry->SectorCount.QuadPart -= ullSectorSize;
InsertTailList(ListEntry, &NewPartEntry->ListEntry);
return NewPartEntry; } } }
return NULL;}
EXIT_CODECreateEfiPartition( _In_ INT argc, _In_ PWSTR *argv){ PPARTENTRY PartEntry; ULONGLONG ullSize = 0ULL; ULONGLONG ullSectorCount;#if 0 BOOL bNoErr = FALSE;#endif INT i; PWSTR pszSuffix = NULL; NTSTATUS Status;
DPRINT1("CreateEfiPartition()\n");
if (CurrentDisk == NULL) { ConResPuts(StdOut, IDS_SELECT_NO_DISK); return EXIT_SUCCESS; }
if (CurrentDisk->PartitionStyle != PARTITION_STYLE_GPT) { ConResPuts(StdOut, IDS_CREATE_PARTITION_INVALID_STYLE); return EXIT_SUCCESS; }
for (i = 3; 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 = 3; i < argc; i++) { if (HasPrefix(argv[i], L"size=", &pszSuffix)) { /* size=<N> (MB) */ DPRINT("Size : %s\n", pszSuffix);
ullSize = _wcstoui64(pszSuffix, NULL, 10); if ((ullSize == 0) && (errno == ERANGE)) { ConResPuts(StdErr, IDS_ERROR_INVALID_ARGS); return EXIT_SUCCESS; } } else if (HasPrefix(argv[i], L"offset=", &pszSuffix)) { /* offset=<N> (KB) */ DPRINT("Offset : %s\n", pszSuffix); ConPuts(StdOut, L"The OFFSET option is not supported yet!\n");#if 0 ullOffset = _wcstoui64(pszSuffix, NULL, 10); if ((ullOffset == 0) && (errno == ERANGE)) { ConResPuts(StdErr, IDS_ERROR_INVALID_ARGS); return EXIT_SUCCESS; }#endif } else if (_wcsicmp(argv[i], L"noerr") == 0) { /* noerr - Already handled above */ } else { ConResPuts(StdErr, IDS_ERROR_INVALID_ARGS); return EXIT_SUCCESS; } }
DPRINT1("Size: %I64u\n", ullSize);#if 0 DPRINT1("Offset: %I64u\n", ullOffset);#endif
/* Size */ if (ullSize != 0) ullSectorCount = (ullSize * 1024 * 1024) / CurrentDisk->BytesPerSector; else ullSectorCount = 0;
DPRINT1("SectorCount: %I64u\n", ullSectorCount);
#ifdef DUMP_PARTITION_LIST DumpPartitionList(CurrentDisk);#endif
PartEntry = InsertGptPartition(CurrentDisk, ullSectorCount, &PARTITION_SYSTEM_GUID); if (PartEntry == FALSE) { ConResPuts(StdOut, IDS_CREATE_PARTITION_FAIL); CurrentPartition = NULL; return EXIT_SUCCESS; }
CurrentPartition = PartEntry; CurrentDisk->Dirty = TRUE;
#ifdef DUMP_PARTITION_LIST DumpPartitionList(CurrentDisk);#endif
UpdateGptDiskLayout(CurrentDisk, FALSE); Status = WriteGptPartitions(CurrentDisk); if (!NT_SUCCESS(Status)) { ConResPuts(StdOut, IDS_CREATE_PARTITION_FAIL); CurrentPartition = NULL; return EXIT_SUCCESS; }
ConResPuts(StdOut, IDS_CREATE_PARTITION_SUCCESS);
return EXIT_SUCCESS;}
EXIT_CODECreateExtendedPartition( _In_ INT argc, _In_ PWSTR *argv){ PPARTENTRY PartEntry, NewPartEntry; PLIST_ENTRY ListEntry; ULONGLONG ullSize = 0ULL; ULONGLONG ullSectorCount;#if 0 ULONGLONG ullOffset = 0ULL; BOOL bNoErr = FALSE;#endif INT i; PWSTR pszSuffix = NULL; NTSTATUS Status;
if (CurrentDisk == NULL) { ConResPuts(StdOut, IDS_SELECT_NO_DISK); return EXIT_SUCCESS; }
if (CurrentDisk->PartitionStyle == PARTITION_STYLE_GPT) { ConResPuts(StdOut, IDS_CREATE_PARTITION_INVALID_STYLE); return EXIT_SUCCESS; } else if (CurrentDisk->PartitionStyle == PARTITION_STYLE_RAW) { CREATE_DISK DiskInfo; NTSTATUS Status;
DiskInfo.PartitionStyle = PARTITION_STYLE_MBR; CreateSignature(&DiskInfo.Mbr.Signature);
Status = CreateDisk(CurrentDisk->DiskNumber, &DiskInfo); if (!NT_SUCCESS(Status)) { DPRINT1("CreateDisk() failed!\n"); return EXIT_SUCCESS; }
CurrentDisk->StartSector.QuadPart = (ULONGLONG)CurrentDisk->SectorAlignment; CurrentDisk->EndSector.QuadPart = min(CurrentDisk->SectorCount.QuadPart, 0x100000000) - 1;
ScanForUnpartitionedMbrDiskSpace(CurrentDisk); }
for (i = 3; 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 = 3; i < argc; i++) { if (HasPrefix(argv[i], L"size=", &pszSuffix)) { /* size=<N> (MB) */ DPRINT("Size : %s\n", pszSuffix);
ullSize = _wcstoui64(pszSuffix, NULL, 10); if ((ullSize == 0) && (errno == ERANGE)) { ConResPuts(StdErr, IDS_ERROR_INVALID_ARGS); return EXIT_SUCCESS; } } else if (HasPrefix(argv[i], L"offset=", &pszSuffix)) { /* offset=<N> (KB) */ DPRINT("Offset : %s\n", pszSuffix); ConPuts(StdOut, L"The OFFSET option is not supported yet!\n");#if 0 ullOffset = _wcstoui64(pszSuffix, NULL, 10); if ((ullOffset == 0) && (errno == ERANGE)) { ConResPuts(StdErr, IDS_ERROR_INVALID_ARGS); return EXIT_SUCCESS; }#endif } else if (HasPrefix(argv[i], L"align=", &pszSuffix)) { /* align=<N> */ DPRINT("Align : %s\n", pszSuffix); ConPuts(StdOut, L"The ALIGN option is not supported yet!\n");#if 0 bAlign = TRUE;#endif } else if (_wcsicmp(argv[i], L"noerr") == 0) { /* noerr - Already handled above */ } else { ConResPuts(StdErr, IDS_ERROR_INVALID_ARGS); return EXIT_SUCCESS; } }
DPRINT1("Size: %I64u\n", ullSize);#if 0 DPRINT1("Offset: %I64u\n", ullOffset);#endif
if (GetPrimaryPartitionCount(CurrentDisk) >= 4) { ConPuts(StdOut, L"No space left for an extended partition!\n"); return EXIT_SUCCESS; }
if (CurrentDisk->ExtendedPartition != NULL) { ConPuts(StdOut, L"We already have an extended partition on this disk!\n"); return EXIT_SUCCESS; }
if (ullSize != 0) ullSectorCount = (ullSize * 1024 * 1024) / CurrentDisk->BytesPerSector; else ullSectorCount = 0;
DPRINT1("SectorCount: %I64u\n", ullSectorCount);
ListEntry = CurrentDisk->PrimaryPartListHead.Blink;
PartEntry = CONTAINING_RECORD(ListEntry, PARTENTRY, ListEntry); if (PartEntry->IsPartitioned) { ConPuts(StdOut, L"No disk space left for an extended partition!\n"); return EXIT_SUCCESS; }
if (ullSectorCount == 0) { PartEntry->IsPartitioned = TRUE; PartEntry->New = TRUE; PartEntry->Mbr.PartitionType = PARTITION_EXTENDED; PartEntry->FormatState = Unformatted; PartEntry->FileSystemName[0] = L'\0';
CurrentPartition = PartEntry; CurrentDisk->Dirty = TRUE; } else { if (PartEntry->SectorCount.QuadPart == ullSectorCount) { PartEntry->IsPartitioned = TRUE; PartEntry->New = TRUE; PartEntry->Mbr.PartitionType = PARTITION_EXTENDED; PartEntry->FormatState = Unformatted; PartEntry->FileSystemName[0] = L'\0';
CurrentPartition = PartEntry; CurrentDisk->Dirty = TRUE; } else if (PartEntry->SectorCount.QuadPart > ullSectorCount) { NewPartEntry = RtlAllocateHeap(RtlGetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(PPARTENTRY)); if (NewPartEntry == NULL) { ConPuts(StdOut, L"Memory allocation failed!\n"); return TRUE; }
NewPartEntry->DiskEntry = PartEntry->DiskEntry;
NewPartEntry->StartSector.QuadPart = PartEntry->StartSector.QuadPart; NewPartEntry->SectorCount.QuadPart = ullSectorCount;
NewPartEntry->LogicalPartition = FALSE; NewPartEntry->IsPartitioned = TRUE; NewPartEntry->New = TRUE; NewPartEntry->Mbr.PartitionType = PARTITION_EXTENDED; NewPartEntry->FormatState = Unformatted; NewPartEntry->FileSystemName[0] = L'\0';
PartEntry->StartSector.QuadPart += ullSectorCount; PartEntry->SectorCount.QuadPart -= ullSectorCount;
InsertTailList(ListEntry, &NewPartEntry->ListEntry);
CurrentPartition = NewPartEntry; CurrentDisk->Dirty = TRUE; } }
UpdateMbrDiskLayout(CurrentDisk); Status = WriteMbrPartitions(CurrentDisk); if (!NT_SUCCESS(Status)) { ConResPuts(StdOut, IDS_CREATE_PARTITION_FAIL); CurrentPartition = NULL; return EXIT_SUCCESS; }
ConResPuts(StdOut, IDS_CREATE_PARTITION_SUCCESS);
return EXIT_SUCCESS;}
EXIT_CODECreateLogicalPartition( _In_ INT argc, _In_ PWSTR *argv){ PPARTENTRY PartEntry, NewPartEntry; PLIST_ENTRY ListEntry; ULONGLONG ullSize = 0ULL; ULONGLONG ullSectorCount;#if 0 ULONGLONG ullOffset = 0ULL; BOOL bNoErr = FALSE;#endif UCHAR PartitionType = PARTITION_HUGE; INT i, length; PWSTR pszSuffix = NULL; NTSTATUS Status;
if (CurrentDisk == NULL) { ConResPuts(StdOut, IDS_SELECT_NO_DISK); return EXIT_SUCCESS; }
if (CurrentDisk->PartitionStyle != PARTITION_STYLE_MBR) { ConResPuts(StdOut, IDS_CREATE_PARTITION_INVALID_STYLE); return EXIT_SUCCESS; }
for (i = 3; 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 = 3; i < argc; i++) { if (HasPrefix(argv[i], L"size=", &pszSuffix)) { /* size=<N> (MB) */ DPRINT("Size : %s\n", pszSuffix);
ullSize = _wcstoui64(pszSuffix, NULL, 10); if ((ullSize == 0) && (errno == ERANGE)) { ConResPuts(StdErr, IDS_ERROR_INVALID_ARGS); return EXIT_SUCCESS; } } else if (HasPrefix(argv[i], L"offset=", &pszSuffix)) { /* offset=<N> (KB) */ DPRINT("Offset : %s\n", pszSuffix); ConPuts(StdOut, L"The OFFSET option is not supported yet!\n");#if 0 ullOffset = _wcstoui64(pszSuffix, NULL, 10); if ((ullOffset == 0) && (errno == ERANGE)) { ConResPuts(StdErr, IDS_ERROR_INVALID_ARGS); return EXIT_SUCCESS; }#endif } else if (HasPrefix(argv[i], L"id=", &pszSuffix)) { /* id=<Byte> */ DPRINT("Id : %s\n", pszSuffix);
length = wcslen(pszSuffix); if ((length == 1) || (length == 2)) { /* Byte */ PartitionType = (UCHAR)wcstoul(pszSuffix, NULL, 16); if ((PartitionType == 0) && (errno == ERANGE)) { ConResPuts(StdErr, IDS_ERROR_INVALID_ARGS); return EXIT_SUCCESS; } } else { ConResPuts(StdErr, IDS_ERROR_INVALID_ARGS); return EXIT_SUCCESS; } } else if (HasPrefix(argv[i], L"align=", &pszSuffix)) { /* align=<N> */ DPRINT("Align : %s\n", pszSuffix); ConPuts(StdOut, L"The ALIGN option is not supported yet!\n");#if 0 bAlign = TRUE;#endif } else if (_wcsicmp(argv[i], L"noerr") == 0) { /* noerr - Already handled above */ } else { ConResPuts(StdErr, IDS_ERROR_INVALID_ARGS); return EXIT_SUCCESS; } }
DPRINT1("Size: %I64u\n", ullSize);#if 0 DPRINT1("Offset: %I64u\n", ullOffset);#endif DPRINT1("Partition Type: %hx\n", PartitionType);
if (ullSize != 0) ullSectorCount = (ullSize * 1024 * 1024) / CurrentDisk->BytesPerSector; else ullSectorCount = 0;
DPRINT1("SectorCount: %I64u\n", ullSectorCount);
for (ListEntry = CurrentDisk->LogicalPartListHead.Flink; ListEntry != &CurrentDisk->LogicalPartListHead; ListEntry = ListEntry->Flink) { PartEntry = CONTAINING_RECORD(ListEntry, PARTENTRY, ListEntry); if (PartEntry->IsPartitioned) continue;
if (ullSectorCount == 0) { PartEntry->IsPartitioned = TRUE; PartEntry->New = TRUE; PartEntry->Mbr.PartitionType = PartitionType; PartEntry->FormatState = Unformatted; PartEntry->FileSystemName[0] = L'\0';
CurrentPartition = PartEntry; CurrentDisk->Dirty = TRUE; break; } else { if (PartEntry->SectorCount.QuadPart == ullSectorCount) { PartEntry->IsPartitioned = TRUE; PartEntry->New = TRUE; PartEntry->Mbr.PartitionType = PartitionType; PartEntry->FormatState = Unformatted; PartEntry->FileSystemName[0] = L'\0';
CurrentPartition = PartEntry; CurrentDisk->Dirty = TRUE; break; } else if (PartEntry->SectorCount.QuadPart > ullSectorCount) { NewPartEntry = RtlAllocateHeap(RtlGetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(PPARTENTRY)); if (NewPartEntry == NULL) { ConPuts(StdOut, L"Memory allocation failed!\n"); return TRUE; }
NewPartEntry->DiskEntry = PartEntry->DiskEntry;
NewPartEntry->StartSector.QuadPart = PartEntry->StartSector.QuadPart; NewPartEntry->SectorCount.QuadPart = ullSectorCount;
NewPartEntry->LogicalPartition = TRUE; NewPartEntry->IsPartitioned = TRUE; NewPartEntry->New = TRUE; NewPartEntry->Mbr.PartitionType = PartitionType; NewPartEntry->FormatState = Unformatted; NewPartEntry->FileSystemName[0] = L'\0';
PartEntry->StartSector.QuadPart += ullSectorCount; PartEntry->SectorCount.QuadPart -= ullSectorCount;
InsertTailList(ListEntry, &NewPartEntry->ListEntry);
CurrentPartition = NewPartEntry; CurrentDisk->Dirty = TRUE; break; } } }
UpdateMbrDiskLayout(CurrentDisk); Status = WriteMbrPartitions(CurrentDisk); if (!NT_SUCCESS(Status)) { ConResPuts(StdOut, IDS_CREATE_PARTITION_FAIL); CurrentPartition = NULL; return EXIT_SUCCESS; }
ConResPuts(StdOut, IDS_CREATE_PARTITION_SUCCESS);
return EXIT_SUCCESS;}
EXIT_CODECreateMsrPartition( _In_ INT argc, _In_ PWSTR *argv){ PPARTENTRY PartEntry; ULONGLONG ullSize = 0ULL; ULONGLONG ullSectorSize;#if 0 BOOL bNoErr = FALSE;#endif INT i; PWSTR pszSuffix = NULL; NTSTATUS Status;
DPRINT1("CreateMsrPartition()\n");
if (CurrentDisk == NULL) { ConResPuts(StdOut, IDS_SELECT_NO_DISK); return EXIT_SUCCESS; }
if (CurrentDisk->PartitionStyle != PARTITION_STYLE_GPT) { ConResPuts(StdOut, IDS_CREATE_PARTITION_INVALID_STYLE); return EXIT_SUCCESS; }
for (i = 3; 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 = 3; i < argc; i++) { if (HasPrefix(argv[i], L"size=", &pszSuffix)) { /* size=<N> (MB) */ DPRINT("Size : %s\n", pszSuffix);
ullSize = _wcstoui64(pszSuffix, NULL, 10); if ((ullSize == 0) && (errno == ERANGE)) { ConResPuts(StdErr, IDS_ERROR_INVALID_ARGS); return EXIT_SUCCESS; } } else if (HasPrefix(argv[i], L"offset=", &pszSuffix)) { /* offset=<N> (KB) */ DPRINT("Offset : %s\n", pszSuffix); ConPuts(StdOut, L"The OFFSET option is not supported yet!\n");#if 0 ullOffset = _wcstoui64(pszSuffix, NULL, 10); if ((ullOffset == 0) && (errno == ERANGE)) { ConResPuts(StdErr, IDS_ERROR_INVALID_ARGS); return EXIT_SUCCESS; }#endif } else if (_wcsicmp(argv[i], L"noerr") == 0) { /* noerr - Already handled above */ } else { ConResPuts(StdErr, IDS_ERROR_INVALID_ARGS); return EXIT_SUCCESS; } }
DPRINT1("Size: %I64u\n", ullSize);#if 0 DPRINT1("Offset: %I64u\n", ullOffset);#endif
/* Size */ if (ullSize != 0) ullSectorSize = (ullSize * 1024 * 1024) / CurrentDisk->BytesPerSector; else ullSectorSize = 0;
DPRINT1("SectorSize: %I64u\n", ullSectorSize);
#ifdef DUMP_PARTITION_LIST DumpPartitionList(CurrentDisk);#endif
PartEntry = InsertGptPartition(CurrentDisk, ullSectorSize, &PARTITION_MSFT_RESERVED_GUID); if (PartEntry == FALSE) { ConResPuts(StdOut, IDS_CREATE_PARTITION_FAIL); CurrentPartition = NULL; return EXIT_SUCCESS; }
CurrentPartition = PartEntry; CurrentDisk->Dirty = TRUE;
#ifdef DUMP_PARTITION_LIST DumpPartitionList(CurrentDisk);#endif
UpdateGptDiskLayout(CurrentDisk, FALSE); Status = WriteGptPartitions(CurrentDisk); if (!NT_SUCCESS(Status)) { ConResPuts(StdOut, IDS_CREATE_PARTITION_FAIL); CurrentPartition = NULL; return EXIT_SUCCESS; }
ConResPuts(StdOut, IDS_CREATE_PARTITION_SUCCESS);
return EXIT_SUCCESS;}
staticVOIDCreatePrimaryMbrPartition( _In_ ULONGLONG ullSize, _In_ PWSTR pszPartitionType){ PPARTENTRY PartEntry, NewPartEntry; PLIST_ENTRY ListEntry; ULONGLONG ullSectorCount; UCHAR PartitionType; INT length; NTSTATUS Status;
if (pszPartitionType) { length = wcslen(pszPartitionType); if ((length != 1) && (length != 2)) { ConResPuts(StdErr, IDS_ERROR_INVALID_ARGS); return; }
PartitionType = (UCHAR)wcstoul(pszPartitionType, NULL, 16); if ((PartitionType == 0) && (errno == ERANGE)) { ConResPuts(StdErr, IDS_ERROR_INVALID_ARGS); return; } } else { PartitionType = PARTITION_HUGE; }
if (GetPrimaryPartitionCount(CurrentDisk) >= 4) { ConPuts(StdOut, L"No space left for another primary partition!\n"); return; }
if (ullSize != 0) ullSectorCount = (ullSize * 1024 * 1024) / CurrentDisk->BytesPerSector; else ullSectorCount = 0;
DPRINT1("SectorCount: %I64u\n", ullSectorCount);
for (ListEntry = CurrentDisk->PrimaryPartListHead.Flink; ListEntry != &CurrentDisk->PrimaryPartListHead; ListEntry = ListEntry->Flink) { PartEntry = CONTAINING_RECORD(ListEntry, PARTENTRY, ListEntry); if (PartEntry->IsPartitioned) continue;
if (ullSectorCount == 0) { PartEntry->IsPartitioned = TRUE; PartEntry->New = TRUE; PartEntry->Mbr.PartitionType = PartitionType; PartEntry->FormatState = Unformatted; PartEntry->FileSystemName[0] = L'\0';
CurrentPartition = PartEntry; CurrentDisk->Dirty = TRUE; break; } else { if (PartEntry->SectorCount.QuadPart == ullSectorCount) { PartEntry->IsPartitioned = TRUE; PartEntry->New = TRUE; PartEntry->Mbr.PartitionType = PartitionType; PartEntry->FormatState = Unformatted; PartEntry->FileSystemName[0] = L'\0';
CurrentPartition = PartEntry; CurrentDisk->Dirty = TRUE; break; } else if (PartEntry->SectorCount.QuadPart > ullSectorCount) { NewPartEntry = RtlAllocateHeap(RtlGetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(PPARTENTRY)); if (NewPartEntry == NULL) { ConPuts(StdOut, L"Memory allocation failed!\n"); return; }
NewPartEntry->DiskEntry = PartEntry->DiskEntry;
NewPartEntry->StartSector.QuadPart = PartEntry->StartSector.QuadPart; NewPartEntry->SectorCount.QuadPart = ullSectorCount;
NewPartEntry->LogicalPartition = FALSE; NewPartEntry->IsPartitioned = TRUE; NewPartEntry->New = TRUE; NewPartEntry->Mbr.PartitionType = PartitionType; NewPartEntry->FormatState = Unformatted; NewPartEntry->FileSystemName[0] = L'\0';
PartEntry->StartSector.QuadPart += ullSectorCount; PartEntry->SectorCount.QuadPart -= ullSectorCount;
InsertTailList(ListEntry, &NewPartEntry->ListEntry);
CurrentPartition = NewPartEntry; CurrentDisk->Dirty = TRUE; break; } } }
UpdateMbrDiskLayout(CurrentDisk); Status = WriteMbrPartitions(CurrentDisk); if (!NT_SUCCESS(Status)) { ConResPuts(StdOut, IDS_CREATE_PARTITION_FAIL); CurrentPartition = NULL; return; }
ConResPuts(StdOut, IDS_CREATE_PARTITION_SUCCESS);}
staticVOIDCreatePrimaryGptPartition( _In_ ULONGLONG ullSize, _In_ PWSTR pszPartitionType){ PPARTENTRY PartEntry; ULONGLONG ullSectorCount; GUID guidPartitionType; NTSTATUS Status;
/* Partition Type */ if (pszPartitionType) { if (!StringToGUID(&guidPartitionType, pszPartitionType)) { ConResPuts(StdErr, IDS_ERROR_INVALID_ARGS); return; } } else { CopyMemory(&guidPartitionType, &PARTITION_BASIC_DATA_GUID, sizeof(GUID)); }
/* Size */ if (ullSize != 0) ullSectorCount = (ullSize * 1024 * 1024) / CurrentDisk->BytesPerSector; else ullSectorCount = 0;
DPRINT1("SectorCount: %I64u\n", ullSectorCount);
#ifdef DUMP_PARTITION_LIST DumpPartitionList(CurrentDisk);#endif
PartEntry = InsertGptPartition(CurrentDisk, ullSectorCount, &guidPartitionType); if (PartEntry == FALSE) { ConResPuts(StdOut, IDS_CREATE_PARTITION_FAIL); CurrentPartition = NULL; return; }
CurrentPartition = PartEntry; CurrentDisk->Dirty = TRUE;
#ifdef DUMP_PARTITION_LIST DumpPartitionList(CurrentDisk);#endif
UpdateGptDiskLayout(CurrentDisk, FALSE); Status = WriteGptPartitions(CurrentDisk); if (!NT_SUCCESS(Status)) { ConResPuts(StdOut, IDS_CREATE_PARTITION_FAIL); CurrentPartition = NULL; return; }
ConResPuts(StdOut, IDS_CREATE_PARTITION_SUCCESS);}
EXIT_CODECreatePrimaryPartition( _In_ INT argc, _In_ PWSTR *argv){ ULONGLONG ullSize = 0ULL;#if 0 ULONGLONG ullOffset = 0ULL; BOOL bNoErr = FALSE;#endif INT i; PWSTR pszSuffix = NULL; PWSTR pszPartitionType = NULL;
if (CurrentDisk == NULL) { ConResPuts(StdOut, IDS_SELECT_NO_DISK); return EXIT_SUCCESS; }
if (CurrentDisk->PartitionStyle == PARTITION_STYLE_RAW) { CREATE_DISK DiskInfo; NTSTATUS Status;
DiskInfo.PartitionStyle = PARTITION_STYLE_MBR; CreateSignature(&DiskInfo.Mbr.Signature);
Status = CreateDisk(CurrentDisk->DiskNumber, &DiskInfo); if (!NT_SUCCESS(Status)) { DPRINT1("CreateDisk() failed!\n"); return EXIT_SUCCESS; }
CurrentDisk->StartSector.QuadPart = (ULONGLONG)CurrentDisk->SectorAlignment; CurrentDisk->EndSector.QuadPart = min(CurrentDisk->SectorCount.QuadPart, 0x100000000) - 1;
ScanForUnpartitionedMbrDiskSpace(CurrentDisk); }
for (i = 3; 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 = 3; i < argc; i++) { if (HasPrefix(argv[i], L"size=", &pszSuffix)) { /* size=<N> (MB) */ DPRINT("Size : %s\n", pszSuffix);
ullSize = _wcstoui64(pszSuffix, NULL, 10); if ((ullSize == 0) && (errno == ERANGE)) { ConResPuts(StdErr, IDS_ERROR_INVALID_ARGS); return EXIT_SUCCESS; } } else if (HasPrefix(argv[i], L"offset=", &pszSuffix)) { /* offset=<N> (KB) */ DPRINT("Offset : %s\n", pszSuffix); ConPuts(StdOut, L"The OFFSET option is not supported yet!\n");#if 0 ullOffset = _wcstoui64(pszSuffix, NULL, 10); if ((ullOffset == 0) && (errno == ERANGE)) { ConResPuts(StdErr, IDS_ERROR_INVALID_ARGS); return EXIT_SUCCESS; }#endif } else if (HasPrefix(argv[i], L"id=", &pszSuffix)) { /* id=<Byte>|<GUID> */ DPRINT("Id : %s\n", pszSuffix); pszPartitionType = pszSuffix; } else if (HasPrefix(argv[i], L"align=", &pszSuffix)) { /* align=<N> */ DPRINT("Align : %s\n", pszSuffix); ConPuts(StdOut, L"The ALIGN option is not supported yet!\n");#if 0 bAlign = TRUE;#endif } else if (_wcsicmp(argv[i], L"noerr") == 0) { /* noerr - Alread handled above */ } else { ConResPuts(StdErr, IDS_ERROR_INVALID_ARGS); return EXIT_SUCCESS; } }
DPRINT("Size: %I64u\n", ullSize);#if 0 DPRINT1("Offset: %I64u\n", ullOffset);#endif
if (CurrentDisk->PartitionStyle == PARTITION_STYLE_MBR) { DPRINT("Partition Type: %s\n", pszPartitionType); CreatePrimaryMbrPartition(ullSize, pszPartitionType); } else if (CurrentDisk->PartitionStyle == PARTITION_STYLE_GPT) { CreatePrimaryGptPartition(ullSize, pszPartitionType); }
return EXIT_SUCCESS;}