Patch by Bryce Groff with small changes by myself: Implemented partition

creation (ATM BFS only) and deletion.


git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@31237 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
Ingo Weinhold
2009-06-25 15:44:17 +00:00
parent 6eb9c264e7
commit dc59ebe78b
9 changed files with 470 additions and 222 deletions
+230
View File
@@ -0,0 +1,230 @@
/*
* Copyright 2008-2009 Haiku Inc. All rights reserved.
* Distributed under the terms of the MIT license.
*
* Authors:
* Stephan Aßmus <[email protected]>
* Bryce Groff <[email protected]>
*/
#include "CreateParamsPanel.h"
#include "Support.h"
#include <Button.h>
#include <GridLayoutBuilder.h>
#include <GroupLayoutBuilder.h>
#include <GroupView.h>
#include <MenuField.h>
#include <MenuItem.h>
#include <Message.h>
#include <MessageFilter.h>
#include <PopUpMenu.h>
#include <Slider.h>
#include <SpaceLayoutItem.h>
#include <String.h>
class CreateParamsPanel::EscapeFilter : public BMessageFilter {
public:
EscapeFilter(CreateParamsPanel* target)
: BMessageFilter(B_ANY_DELIVERY, B_ANY_SOURCE),
fPanel(target)
{
}
virtual ~EscapeFilter()
{
}
virtual filter_result Filter(BMessage* message, BHandler** target)
{
filter_result result = B_DISPATCH_MESSAGE;
switch (message->what) {
case B_KEY_DOWN:
case B_UNMAPPED_KEY_DOWN: {
uint32 key;
if (message->FindInt32("raw_char", (int32*)&key) >= B_OK) {
if (key == B_ESCAPE) {
result = B_SKIP_MESSAGE;
fPanel->Cancel();
}
}
break;
}
default:
break;
}
return result;
}
private:
CreateParamsPanel* fPanel;
};
// #pragma mark -
enum {
MSG_OK = 'okok',
MSG_CANCEL = 'cncl',
MSG_PARTITION_TYPE = 'prty'
};
CreateParamsPanel::CreateParamsPanel(BWindow* window, off_t offset, off_t size)
: BWindow(BRect(300.0, 200.0, 600.0, 300.0), 0, B_MODAL_WINDOW_LOOK,
B_MODAL_SUBSET_WINDOW_FEEL,
B_ASYNCHRONOUS_CONTROLS | B_AUTO_UPDATE_SIZE_LIMITS),
fEscapeFilter(new EscapeFilter(this)),
fExitSemaphore(create_sem(0, "CreateParamsPanel exit")),
fWindow(window),
fReturnValue(GO_CANCELED)
{
AddCommonFilter(fEscapeFilter);
_CreateViewControls(offset, size);
}
CreateParamsPanel::~CreateParamsPanel()
{
RemoveCommonFilter(fEscapeFilter);
delete fEscapeFilter;
delete_sem(fExitSemaphore);
}
bool
CreateParamsPanel::QuitRequested()
{
release_sem(fExitSemaphore);
return false;
}
void
CreateParamsPanel::MessageReceived(BMessage* message)
{
switch (message->what) {
case MSG_CANCEL:
Cancel();
break;
case MSG_OK:
fReturnValue = GO_SUCCESS;
release_sem(fExitSemaphore);
break;
default:
BWindow::MessageReceived(message);
}
}
int32
CreateParamsPanel::Go(off_t& offset, off_t& size, BString& type)
{
// run the window thread, to get an initial layout of the controls
Hide();
Show();
if (!Lock())
return GO_CANCELED;
// center the panel above the parent window
BRect frame = Frame();
BRect parentFrame = fWindow->Frame();
MoveTo((parentFrame.left + parentFrame.right - frame.Width()) / 2.0,
(parentFrame.top + parentFrame.bottom - frame.Height()) / 2.0);
Show();
Unlock();
// block this thread now, but keep the window repainting
while (true) {
status_t err = acquire_sem_etc(fExitSemaphore, 1,
B_CAN_INTERRUPT | B_RELATIVE_TIMEOUT, 50000);
if (err != B_TIMED_OUT && err != B_INTERRUPTED)
break;
fWindow->UpdateIfNeeded();
}
if (!Lock())
return GO_CANCELED;
if (fReturnValue == GO_SUCCESS) {
if (BMenuItem* item = fTypeMenuField->Menu()->FindMarked()) {
const char* _type;
BMessage* message = item->Message();
if (!message || message->FindString("type", &_type) < B_OK)
_type = "BFS Filesystem";
type << _type;
}
size = fSizeSlider->Value();
}
int32 value = fReturnValue;
Quit();
// NOTE: this object is toast now!
return value;
}
void
CreateParamsPanel::Cancel()
{
fReturnValue = GO_CANCELED;
release_sem(fExitSemaphore);
}
void
CreateParamsPanel::_CreateViewControls(off_t offset, off_t size)
{
// Setup the controls
//TODO Add all the partition types that we want/can use
fTypePopUpMenu = new BPopUpMenu("Partition Type");
BMessage* message = new BMessage(MSG_PARTITION_TYPE);
message->AddString("type", "BFS Filesystem");
BMenuItem *item = new BMenuItem("BFS Filesystem", message);
fTypePopUpMenu->AddItem(item);
item->SetMarked(true);
fTypeMenuField = new BMenuField("Partition Type", fTypePopUpMenu, NULL);
fSizeSlider = new SizeSlider("Slider", "Partition Size", NULL, offset,
size);
fSizeSlider->SetPosition(1.0);
fOKButton = new BButton("Create", new BMessage(MSG_OK));
fCancelButton = new BButton("Cancel", new BMessage(MSG_CANCEL));
BView* rootView = BGroupLayoutBuilder(B_VERTICAL, 4)
.Add(BSpaceLayoutItem::CreateVerticalStrut(10))
// test views
.Add(BGridLayoutBuilder(10, 10)
// row 1
.Add(BSpaceLayoutItem::CreateHorizontalStrut(5), 0, 0)
.Add(fSizeSlider, 1, 0)
.Add(BSpaceLayoutItem::CreateVerticalStrut(5), 1, 0)
.Add(fTypeMenuField, 1, 1)
)
// controls
.AddGroup(B_HORIZONTAL, 10)
.Add(BSpaceLayoutItem::CreateHorizontalStrut(5))
.AddGlue()
.Add(fCancelButton)
.Add(fOKButton)
.Add(BSpaceLayoutItem::CreateHorizontalStrut(5))
.End()
.Add(BSpaceLayoutItem::CreateVerticalStrut(5))
;
SetLayout(new BGroupLayout(B_HORIZONTAL));
AddChild(rootView);
SetDefaultButton(fOKButton);
AddToSubset(fWindow);
}
+52
View File
@@ -0,0 +1,52 @@
/*
* Copyright 2008 Haiku Inc. All rights reserved.
* Distributed under the terms of the MIT license.
*
* Authors:
* Stephan Aßmus <[email protected]>
* Bryce Groff <[email protected]>
*/
#ifndef CREATE_PARAMS_PANEL_H
#define CREATE_PARAMS_PANEL_H
#include "Support.h"
#include <Window.h>
#include <InterfaceKit.h>
#include <Partition.h>
class BMenuField;
class BTextControl;
class SizeSlider;
class CreateParamsPanel : public BWindow {
public:
CreateParamsPanel(BWindow* window,
off_t offset, off_t size);
virtual ~CreateParamsPanel();
virtual bool QuitRequested();
virtual void MessageReceived(BMessage* message);
int32 Go(off_t& offset, off_t& size,
BString& parameters);
void Cancel();
private:
void _CreateViewControls(off_t offset, off_t size);
class EscapeFilter;
EscapeFilter* fEscapeFilter;
sem_id fExitSemaphore;
BWindow* fWindow;
int32 fReturnValue;
BPopUpMenu* fTypePopUpMenu;
BMenuField* fTypeMenuField;
SizeSlider* fSizeSlider;
BButton* fOKButton;
BButton* fCancelButton;
};
#endif // CREATE_PARAMS_PANEL_H
+1 -1
View File
@@ -13,7 +13,7 @@ resource app_version {
internal = 0, internal = 0,
short_info = "DriveSetup", short_info = "DriveSetup",
long_info = "DriveSetup ©2002-2008 Haiku" long_info = "DriveSetup ©2002-2009 Haiku"
}; };
resource app_flags B_SINGLE_LAUNCH; resource app_flags B_SINGLE_LAUNCH;
+2 -4
View File
@@ -8,15 +8,13 @@
#ifndef INIT_PARAMS_PANEL_H #ifndef INIT_PARAMS_PANEL_H
#define INIT_PARAMS_PANEL_H #define INIT_PARAMS_PANEL_H
#include "Support.h"
#include <Window.h> #include <Window.h>
class BMenuField; class BMenuField;
class BTextControl; class BTextControl;
enum {
GO_CANCELED = 0,
GO_SUCCESS
};
class InitParamsPanel : public BWindow { class InitParamsPanel : public BWindow {
public: public:
+1
View File
@@ -5,6 +5,7 @@ AddSubDirSupportedPlatforms libbe_test ;
UsePrivateHeaders interface shared storage tracker ; UsePrivateHeaders interface shared storage tracker ;
Preference DriveSetup : Preference DriveSetup :
CreateParamsPanel.cpp
DiskView.cpp DiskView.cpp
DriveSetup.cpp DriveSetup.cpp
InitParamsPanel.cpp InitParamsPanel.cpp
+129 -217
View File
@@ -12,6 +12,7 @@
#include "MainWindow.h" #include "MainWindow.h"
#include "DiskView.h" #include "DiskView.h"
#include "InitParamsPanel.h" #include "InitParamsPanel.h"
#include "CreateParamsPanel.h"
#include "PartitionList.h" #include "PartitionList.h"
#include "Support.h" #include "Support.h"
#include "tracker_private.h" #include "tracker_private.h"
@@ -23,8 +24,10 @@
#include <Application.h> #include <Application.h>
#include <ColumnListView.h> #include <ColumnListView.h>
#include <ColumnTypes.h> #include <ColumnTypes.h>
#include <Debug.h>
#include <DiskDevice.h> #include <DiskDevice.h>
#include <DiskDeviceVisitor.h> #include <DiskDeviceVisitor.h>
#include <DiskDeviceTypes.h>
#include <DiskSystem.h> #include <DiskSystem.h>
#include <MenuItem.h> #include <MenuItem.h>
#include <MenuBar.h> #include <MenuBar.h>
@@ -37,33 +40,6 @@
#include <Volume.h> #include <Volume.h>
#include <VolumeRoster.h> #include <VolumeRoster.h>
//static void
//print_partition_table_header()
//{
//printf(" Index Start Size Content Type "
//"Content Name\n");
//printf("--------------------------------------------------------------"
//"------------\n");
//}
//static void
//print_partition(BPartition* partition, int level, int index)
//{
//BString offset, size;
//get_size_string(partition->Offset(), offset);
//get_size_string(partition->Size(), size);
//printf("%*s%02d%*s %8s %8s %26.26s %16.16s\n", 2 * level, "",
//index,
//2 * max_c(3 - level, 0), "",
//offset.String(), size.String(),
//(partition->ContentType() ? partition->ContentType() : "-"),
//(partition->ContentName() ? partition->ContentName() : ""));
//}
class ListPopulatorVisitor : public BDiskDeviceVisitor { class ListPopulatorVisitor : public BDiskDeviceVisitor {
public: public:
ListPopulatorVisitor(PartitionListView* list, int32& diskCount, ListPopulatorVisitor(PartitionListView* list, int32& diskCount,
@@ -192,9 +168,7 @@ MainWindow::MainWindow(BRect frame)
new BMessage(MSG_SURFACE_TEST)); new BMessage(MSG_SURFACE_TEST));
fRescanMI = new BMenuItem("Rescan", new BMessage(MSG_RESCAN)); fRescanMI = new BMenuItem("Rescan", new BMessage(MSG_RESCAN));
fDeleteMI = new BMenuItem("Delete (not implemented)", fDeleteMI = new BMenuItem("Delete", new BMessage(MSG_DELETE), 'D');
new BMessage(MSG_DELETE));
fDeleteMI->SetEnabled(false);
fMountMI = new BMenuItem("Mount", new BMessage(MSG_MOUNT), 'M'); fMountMI = new BMenuItem("Mount", new BMessage(MSG_MOUNT), 'M');
fUnmountMI = new BMenuItem("Unmount", new BMessage(MSG_UNMOUNT), 'U'); fUnmountMI = new BMenuItem("Unmount", new BMessage(MSG_UNMOUNT), 'U');
@@ -214,7 +188,7 @@ MainWindow::MainWindow(BRect frame)
// Parition menu // Parition menu
fPartitionMenu = new BMenu("Partition"); fPartitionMenu = new BMenu("Partition");
fCreateMenu = new BMenu("Create (not implemented)"); fCreateMenu = new BMenu("Create");
fPartitionMenu->AddItem(fCreateMenu); fPartitionMenu->AddItem(fCreateMenu);
fInitMenu = new BMenu("Initialize"); fInitMenu = new BMenu("Initialize");
@@ -288,9 +262,13 @@ MainWindow::MessageReceived(BMessage* message)
printf("MSG_FORMAT\n"); printf("MSG_FORMAT\n");
break; break;
case MSG_CREATE: case MSG_CREATE: {
printf("MSG_CREATE\n"); BString diskSystemName;
//if (message->FindString("disk system", &diskSystemName) != B_OK)
// break;
_Create(fCurrentDisk, fCurrentPartitionID, diskSystemName);
break; break;
}
case MSG_INITIALIZE: { case MSG_INITIALIZE: {
BString diskSystemName; BString diskSystemName;
@@ -301,7 +279,7 @@ MainWindow::MessageReceived(BMessage* message)
} }
case MSG_DELETE: case MSG_DELETE:
printf("MSG_DELETE\n"); _Delete(fCurrentDisk, fCurrentPartitionID);
break; break;
case MSG_EJECT: case MSG_EJECT:
@@ -462,6 +440,7 @@ MainWindow::_SetToDiskAndPartition(partition_id disk, partition_id partition,
{ {
printf("MainWindow::_SetToDiskAndPartition(disk: %ld, partition: %ld, " printf("MainWindow::_SetToDiskAndPartition(disk: %ld, partition: %ld, "
"parent: %ld)\n", disk, partition, parent); "parent: %ld)\n", disk, partition, parent);
BDiskDevice* oldDisk = NULL; BDiskDevice* oldDisk = NULL;
if (!fCurrentDisk || fCurrentDisk->ID() != disk) { if (!fCurrentDisk || fCurrentDisk->ID() != disk) {
oldDisk = fCurrentDisk; oldDisk = fCurrentDisk;
@@ -490,10 +469,6 @@ void
MainWindow::_UpdateMenus(BDiskDevice* disk, MainWindow::_UpdateMenus(BDiskDevice* disk,
partition_id selectedPartition, partition_id parentID) partition_id selectedPartition, partition_id parentID)
{ {
printf("MainWindow::_UpdateMenus(disk: %p, "
"selectedPartition: %ld, parentID: %ld)\n", disk, selectedPartition,
parentID);
// clean out Create and Init menu // clean out Create and Init menu
while (BMenuItem* item = fCreateMenu->RemoveItem(0L)) while (BMenuItem* item = fCreateMenu->RemoveItem(0L))
delete item; delete item;
@@ -526,11 +501,10 @@ printf("MainWindow::_UpdateMenus(disk: %p, "
partition = disk; partition = disk;
bool prepared = disk->PrepareModifications() == B_OK; bool prepared = disk->PrepareModifications() == B_OK;
printf(" prepared: %d\n", prepared); fCreateMenu->SetEnabled(prepared);
// fCreateMenu->SetEnabled(prepared);
// TODO: Enable once _Create() is implemented...
fCreateMenu->SetEnabled(false);
fInitMenu->SetEnabled(prepared); fInitMenu->SetEnabled(prepared);
fDeleteMI->SetEnabled(prepared);
BDiskSystem diskSystem; BDiskSystem diskSystem;
fDDRoster.RewindDiskSystems(); fDDRoster.RewindDiskSystems();
@@ -559,7 +533,6 @@ fCreateMenu->SetEnabled(false);
} }
if (parentPartition != NULL) { if (parentPartition != NULL) {
printf(" parent partition: %p\n", parentPartition);
BString supportedChildType; BString supportedChildType;
int32 cookie = 0; int32 cookie = 0;
status_t ret; status_t ret;
@@ -577,7 +550,6 @@ printf(" parent partition: %p\n", parentPartition);
fprintf(stderr, "Failed to get supported child types: %s\n", fprintf(stderr, "Failed to get supported child types: %s\n",
strerror(ret)); strerror(ret));
} else { } else {
printf(" no parent partition\n");
fCreateMenu->SetEnabled(false); fCreateMenu->SetEnabled(false);
} }
@@ -587,8 +559,7 @@ printf(" no parent partition\n");
// Mount items // Mount items
if (partition) { if (partition) {
fInitMenu->SetEnabled(!partition->IsMounted()); fInitMenu->SetEnabled(!partition->IsMounted());
// fDeleteMI->SetEnabled(!partition->IsMounted()); fDeleteMI->SetEnabled(!partition->IsMounted());
fDeleteMI->SetEnabled(false);
fMountMI->SetEnabled(!partition->IsMounted()); fMountMI->SetEnabled(!partition->IsMounted());
bool unMountable = false; bool unMountable = false;
@@ -742,6 +713,7 @@ public:
status_t ret = fDisk->CommitModifications(); status_t ret = fDisk->CommitModifications();
if (ret == B_OK) if (ret == B_OK)
fModificationStatus = B_ERROR; fModificationStatus = B_ERROR;
return ret; return ret;
} }
@@ -907,210 +879,150 @@ void
MainWindow::_Create(BDiskDevice* disk, partition_id selectedPartition, MainWindow::_Create(BDiskDevice* disk, partition_id selectedPartition,
const BString& partitionType) const BString& partitionType)
{ {
printf("_Create(disk: %p, selectedPartition: %ld)\n", disk,
selectedPartition);
if (disk->IsReadOnly()) { if (disk->IsReadOnly()) {
_DisplayPartitionError("The selected disk is read-only."); _DisplayPartitionError("The selected disk is read-only.");
return; return;
} }
//BPartition* partition = disk->FindDescendant(selectedPartition); BPartition* partition = disk->FindDescendant(selectedPartition);
//if (!partition) { if (partition) {
//_DisplayPartitionError("Unable to find the selected partition by id."); _DisplayPartitionError("The selected partition contains a file "
//return; "system");
//}
#if 0
// get the parent partition
BPartition* partition = NULL;
int32 partitionIndex;
if (!_SelectPartition("parent partition index [-1 to abort]: ",
partition, partitionIndex)) {
return; return;
} }
printf("\nselected partition:\n\n"); if (!disk->ContainsPartitioningSystem()) {
print_partition_table_header(); _DisplayPartitionError("The selected partition does not contain "
print_partition(partition, 0, partitionIndex); "a partitioning system.\n");
if (!partition->ContainsPartitioningSystem()) {
printf("The selected partition does not contain a partitioning "
"system.\n");
return; return;
} }
// get supported types ModificationPreparer modificationPreparer(disk);
BObjectList<BString> supportedTypes(20, true); status_t ret = modificationPreparer.ModificationStatus();
BString typeBuffer; if (ret != B_OK) {
int32 cookie = 0; _DisplayPartitionError("There was an error preparing the "
while (partition->GetNextSupportedChildType(&cookie, &typeBuffer) "disk for modifications.", NULL, ret);
== B_OK) {
supportedTypes.AddItem(new BString(typeBuffer));
}
if (supportedTypes.IsEmpty()) {
printf("The partitioning system is not able to create any "
"child partition (no supported types).\n");
return; return;
} }
// get partitioning info // get partitioning info
BPartitioningInfo partitioningInfo; BPartitioningInfo partitioningInfo;
status_t error = partition->GetPartitioningInfo(&partitioningInfo); status_t error = disk->GetPartitioningInfo(&partitioningInfo);
if (error != B_OK) { if (error != B_OK) {
printf("Failed to get partitioning info for partition: %s\n", _DisplayPartitionError("Could not aquire partitioning information.\n");
strerror(error));
return; return;
} }
// TODO: Find out which partition is the currently selected partition and get
// the information about the offset and how large of a partition we can create.
int32 spacesCount = partitioningInfo.CountPartitionableSpaces(); int32 spacesCount = partitioningInfo.CountPartitionableSpaces();
if (spacesCount == 0) { if (spacesCount == 0) {
printf("There's no space on the partition where a child partition " _DisplayPartitionError("There's no space on the partition where a "
"could be created\n"); "child partition could be created\n");
return; return;
} }
// let the user select the partition type, if there's more than one BString name, type, parameters;
int64 typeIndex = 0; off_t offset, size;
int32 supportedTypesCount = supportedTypes.CountItems(); partitioningInfo.GetPartitionableSpaceAt(0, &offset, &size);
if (supportedTypesCount > 1) {
// list them
printf("Possible partition types:\n");
for (int32 i = 0; i < supportedTypesCount; i++)
printf("%2ld %s\n", i, supportedTypes.ItemAt(i)->String());
if (!_ReadNumber("supported type index [-1 to abort]: ", 0, CreateParamsPanel* panel = new CreateParamsPanel(this, offset, size);
supportedTypesCount - 1, -1, "invalid index", typeIndex)) { if (panel->Go(offset, size, type) == GO_CANCELED)
return; return;
}
ret = disk->ValidateCreateChild(&offset, &size, type.String(),
NULL, NULL);
if (ret != B_OK) {
_DisplayPartitionError("Validation of the given creation "
"parameters failed.");
return;
} }
const char* type = supportedTypes.ItemAt(typeIndex)->String(); // Warn the user one more time...
BString message = "Are you sure you want to write the changes back to "
"disk now?\n\n";
message << "All data on the partition";
message << " will be irrevertably lost if you do so!";
BAlert* alert = new BAlert("final notice", message.String(),
"Write Changes", "Cancel", NULL, B_WIDTH_FROM_WIDEST, B_WARNING_ALERT);
int32 choice = alert->Go();
// list partitionable spaces if (choice == 1)
printf("Unused regions where the new partition could be created:\n"); return;
for (int32 i = 0; i < spacesCount; i++) {
off_t _offset; ret = disk->CreateChild(offset, size, type.String(),
off_t _size; NULL, parameters.String());
partitioningInfo.GetPartitionableSpaceAt(i, &_offset, &_size);
BString offset, size; if (ret != B_OK) {
get_size_string(_offset, offset); _DisplayPartitionError("Creation of the partition has failed\n");
get_size_string(_size, size); return;
printf("%2ld start: %8s, size: %8s\n", i, offset.String(),
size.String());
} }
// let the user select the partitionable space, if there's more than one // commit
int64 spaceIndex = 0; ret = modificationPreparer.CommitModifications();
if (spacesCount > 1) {
if (!_ReadNumber("unused region index [-1 to abort]: ", 0, if (ret != B_OK) {
spacesCount - 1, -1, "invalid index", spaceIndex)) { _DisplayPartitionError("Failed to initialize the partition. "
return; "This operation is exiting.\nNo changes have been made!\n");
} return;
} }
off_t spaceOffset; // The disk layout has changed, update disk information
off_t spaceSize; bool updated;
partitioningInfo.GetPartitionableSpaceAt(spaceIndex, &spaceOffset, ret = disk->Update(&updated);
&spaceSize);
_ScanDrives();
off_t start; }
off_t size;
BString parameters; void
while (true) { MainWindow::_Delete(BDiskDevice* disk, partition_id selectedPartition)
// let the user enter start, size, and parameters {
if (disk->IsReadOnly()) {
// start _DisplayPartitionError("The selected disk is read-only.");
while (true) { return;
BString spaceOffsetString; }
get_size_string(spaceOffset, spaceOffsetString);
BString prompt("partition start [default: "); BPartition* partition = disk->FindDescendant(selectedPartition);
prompt << spaceOffsetString << "]: "; if (!partition) {
if (!_ReadSize(prompt.String(), spaceOffset, start)) _DisplayPartitionError("Unable to find the selected partition by id.");
return; return;
}
if (start >= spaceOffset && start <= spaceOffset + spaceSize)
break; ModificationPreparer modificationPreparer(disk);
status_t ret = modificationPreparer.ModificationStatus();
printf("invalid partition start\n"); if (ret != B_OK) {
} _DisplayPartitionError("There was an error preparing the "
"disk for modifications.", NULL, ret);
// size return;
off_t maxSize = spaceOffset + spaceSize - start; }
while (true) {
BString maxSizeString; if (!disk->CanDeleteChild(partition->Index())) {
get_size_string(maxSize, maxSizeString); _DisplayPartitionError("Cannot delete the selected partition");
BString prompt("partition size [default: "); return;
prompt << maxSizeString << "]: "; }
if (!_ReadSize(prompt.String(), maxSize, size))
return; // Warn the user one more time...
BString message = "Are you sure you want to delete the selected ";
if (size >= 0 && start + size <= spaceOffset + spaceSize) message << "partition?\n\nAll data on the partition";
break; message << " will be irrevertably lost if you do so!";
BAlert* alert = new BAlert("final notice", message.String(),
printf("invalid partition size\n"); "Delete Partition", "Cancel", NULL, B_WIDTH_FROM_WIDEST,
} B_WARNING_ALERT);
int32 choice = alert->Go();
// parameters
if (!_ReadLine("partition parameters: ", parameters)) if (choice == 1)
return; return;
// validate parameters ret = disk->DeleteChild(partition->Index());
off_t validatedStart = start; if (ret != B_OK) {
off_t validatedSize = size; PRINT(("MainWindow::_Delete(): DeleteChild() failed: %s\n",
// TODO: Support the name parameter! strerror(ret)));
if (partition->ValidateCreateChild(&start, &size, type, NULL, _DisplayPartitionError("Could not delete the selected partition");
parameters.String()) != B_OK) { return;
printf("Validation of the given values failed. Sorry, can't " }
"continue.\n");
return; modificationPreparer.CommitModifications();
}
// did the disk system change offset or size?
if (validatedStart == start && validatedSize == size) {
printf("Everything looks dandy.\n");
} else {
BString startString, sizeString;
get_size_string(validatedStart, startString);
get_size_string(validatedSize, sizeString);
printf("The disk system adjusted the partition start and "
"size to %lld (%s) and %lld (%s).\n",
validatedStart, startString.String(), validatedSize,
sizeString.String());
start = validatedStart;
size = validatedSize;
}
// let the user decide whether to continue, change parameters, or
// abort
bool changeParameters = false;
while (true) {
BString line;
_ReadLine("[c]ontinue, change [p]arameters, or [a]bort? ", line);
if (line == "a")
return;
if (line == "p") {
changeParameters = true;
break;
}
if (line == "c")
break;
printf("invalid input\n");
}
if (!changeParameters)
break;
}
// create child
error = partition->CreateChild(start, size, type, NULL,
parameters.String());
if (error != B_OK)
printf("Creating the partition failed: %s\n", strerror(error));
#endif // 0
_ScanDrives(); _ScanDrives();
} }
+2
View File
@@ -69,6 +69,8 @@ private:
void _Create(BDiskDevice* disk, void _Create(BDiskDevice* disk,
partition_id selectedPartition, partition_id selectedPartition,
const BString& partitionType); const BString& partitionType);
void _Delete(BDiskDevice* disk,
partition_id selectedPartition);
BDiskDeviceRoster fDDRoster; BDiskDeviceRoster fDDRoster;
+33
View File
@@ -16,6 +16,9 @@
#include <String.h> #include <String.h>
uint32 kMegaByte = 1048576;
const char* const char*
string_for_size(off_t size, char *string) string_for_size(off_t size, char *string)
{ {
@@ -111,3 +114,33 @@ SpaceIDMap::SpaceIDFor(partition_id parentID, off_t spaceOffset)
return newID; return newID;
} }
SizeSlider::SizeSlider(const char* name, const char* label,
BMessage* message, int32 minValue, int32 maxValue)
: BSlider(name, label, message, minValue, maxValue, B_HORIZONTAL,
B_TRIANGLE_THUMB),
fOffset(minValue),
fSize(maxValue)
{
SetBarColor((rgb_color){ 0, 80, 255, 255 });
BString offset, size;
offset << fOffset / kMegaByte; offset << " MB";
size << fSize / kMegaByte; size << " MB";
SetLimitLabels(offset.String(), size.String());
}
SizeSlider::~SizeSlider()
{
}
const char*
SizeSlider::UpdateText() const
{
fStatusLabel.Truncate(0);
fStatusLabel << (Value() / kMegaByte);
fStatusLabel << " MB";
return fStatusLabel.String();
}
+20
View File
@@ -9,6 +9,8 @@
#include <DiskDeviceDefs.h> #include <DiskDeviceDefs.h>
#include <HashMap.h> #include <HashMap.h>
#include <HashString.h> #include <HashString.h>
#include <Slider.h>
#include <String.h>
class BPartition; class BPartition;
@@ -20,6 +22,10 @@ void dump_partition_info(const BPartition* partition);
bool is_valid_partitionable_space(size_t size); bool is_valid_partitionable_space(size_t size);
enum {
GO_CANCELED = 0,
GO_SUCCESS
};
class SpaceIDMap : public HashMap<HashString, partition_id> { class SpaceIDMap : public HashMap<HashString, partition_id> {
public: public:
@@ -33,5 +39,19 @@ private:
partition_id fNextSpaceID; partition_id fNextSpaceID;
}; };
class SizeSlider : public BSlider {
public:
SizeSlider(const char* name, const char* label,
BMessage* message, int32 minValue,
int32 maxValue);
virtual ~SizeSlider();
virtual const char* UpdateText() const;
private:
off_t fOffset;
off_t fSize;
mutable BString fStatusLabel;
};
#endif // SUPPORT_H #endif // SUPPORT_H