gpt: early work in progress of a disk system add-on.
* It currently allows to initialize a disk using GPT. However, this then fails somewhere in the kernel.
This commit is contained in:
@@ -1,5 +1,6 @@
|
|||||||
SubDir HAIKU_TOP src add-ons disk_systems ;
|
SubDir HAIKU_TOP src add-ons disk_systems ;
|
||||||
|
|
||||||
SubInclude HAIKU_TOP src add-ons disk_systems bfs ;
|
SubInclude HAIKU_TOP src add-ons disk_systems bfs ;
|
||||||
|
SubInclude HAIKU_TOP src add-ons disk_systems gpt ;
|
||||||
SubInclude HAIKU_TOP src add-ons disk_systems intel ;
|
SubInclude HAIKU_TOP src add-ons disk_systems intel ;
|
||||||
SubInclude HAIKU_TOP src add-ons disk_systems ntfs ;
|
SubInclude HAIKU_TOP src add-ons disk_systems ntfs ;
|
||||||
|
|||||||
@@ -0,0 +1,155 @@
|
|||||||
|
/*
|
||||||
|
* Copyright 2013, Axel Dörfler, [email protected].
|
||||||
|
* Distributed under the terms of the MIT License.
|
||||||
|
*/
|
||||||
|
|
||||||
|
|
||||||
|
#include "GPTDiskAddOn.h"
|
||||||
|
|
||||||
|
#include <new>
|
||||||
|
#include <stdio.h>
|
||||||
|
|
||||||
|
#include <DiskDeviceTypes.h>
|
||||||
|
#include <MutablePartition.h>
|
||||||
|
#include <PartitioningInfo.h>
|
||||||
|
#include <PartitionParameterEditor.h>
|
||||||
|
|
||||||
|
#include <AutoDeleter.h>
|
||||||
|
#include <disk_device_types.h>
|
||||||
|
|
||||||
|
#include "efi_gpt.h"
|
||||||
|
|
||||||
|
#include "GPTPartitionHandle.h"
|
||||||
|
#include "Utility.h"
|
||||||
|
|
||||||
|
|
||||||
|
//#define TRACE_GPT_DISK_ADD_ON
|
||||||
|
#undef TRACE
|
||||||
|
#ifdef TRACE_GPT_DISK_ADD_ON
|
||||||
|
# define TRACE(x...) printf(x)
|
||||||
|
#else
|
||||||
|
# define TRACE(x...) do {} while (false)
|
||||||
|
#endif
|
||||||
|
|
||||||
|
|
||||||
|
static const uint32 kDiskSystemFlags =
|
||||||
|
0
|
||||||
|
// | B_DISK_SYSTEM_SUPPORTS_CHECKING
|
||||||
|
// | B_DISK_SYSTEM_SUPPORTS_REPAIRING
|
||||||
|
// | B_DISK_SYSTEM_SUPPORTS_RESIZING
|
||||||
|
// | B_DISK_SYSTEM_SUPPORTS_MOVING
|
||||||
|
// | B_DISK_SYSTEM_SUPPORTS_SETTING_CONTENT_NAME
|
||||||
|
// | B_DISK_SYSTEM_SUPPORTS_SETTING_CONTENT_PARAMETERS
|
||||||
|
| B_DISK_SYSTEM_SUPPORTS_INITIALIZING
|
||||||
|
// | B_DISK_SYSTEM_SUPPORTS_CONTENT_NAME
|
||||||
|
|
||||||
|
// | B_DISK_SYSTEM_SUPPORTS_RESIZING_CHILD
|
||||||
|
// | B_DISK_SYSTEM_SUPPORTS_MOVING_CHILD
|
||||||
|
// | B_DISK_SYSTEM_SUPPORTS_SETTING_NAME
|
||||||
|
| B_DISK_SYSTEM_SUPPORTS_SETTING_TYPE
|
||||||
|
// | B_DISK_SYSTEM_SUPPORTS_SETTING_PARAMETERS
|
||||||
|
| B_DISK_SYSTEM_SUPPORTS_CREATING_CHILD
|
||||||
|
| B_DISK_SYSTEM_SUPPORTS_DELETING_CHILD
|
||||||
|
// | B_DISK_SYSTEM_SUPPORTS_NAME
|
||||||
|
;
|
||||||
|
|
||||||
|
|
||||||
|
// #pragma mark - GPTDiskAddOn
|
||||||
|
|
||||||
|
|
||||||
|
GPTDiskAddOn::GPTDiskAddOn()
|
||||||
|
:
|
||||||
|
BDiskSystemAddOn(EFI_PARTITION_NAME, kDiskSystemFlags)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
GPTDiskAddOn::~GPTDiskAddOn()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
status_t
|
||||||
|
GPTDiskAddOn::CreatePartitionHandle(BMutablePartition* partition,
|
||||||
|
BPartitionHandle** _handle)
|
||||||
|
{
|
||||||
|
GPTPartitionHandle* handle
|
||||||
|
= new(std::nothrow) GPTPartitionHandle(partition);
|
||||||
|
if (handle == NULL)
|
||||||
|
return B_NO_MEMORY;
|
||||||
|
|
||||||
|
status_t error = handle->Init();
|
||||||
|
if (error != B_OK) {
|
||||||
|
delete handle;
|
||||||
|
return error;
|
||||||
|
}
|
||||||
|
|
||||||
|
*_handle = handle;
|
||||||
|
return B_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
bool
|
||||||
|
GPTDiskAddOn::CanInitialize(const BMutablePartition* partition)
|
||||||
|
{
|
||||||
|
// If it's big enough, we can initialize it.
|
||||||
|
return partition->Size() >= round_up(partition->BlockSize()
|
||||||
|
+ EFI_PARTITION_ENTRY_COUNT * EFI_PARTITION_ENTRY_SIZE,
|
||||||
|
partition->BlockSize());
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
status_t
|
||||||
|
GPTDiskAddOn::GetInitializationParameterEditor(
|
||||||
|
const BMutablePartition* partition, BPartitionParameterEditor** editor)
|
||||||
|
{
|
||||||
|
// Nothing to edit, really.
|
||||||
|
*editor = NULL;
|
||||||
|
return B_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
status_t
|
||||||
|
GPTDiskAddOn::ValidateInitialize(const BMutablePartition* partition,
|
||||||
|
BString* name, const char* parameters)
|
||||||
|
{
|
||||||
|
if (!CanInitialize(partition)
|
||||||
|
|| (parameters != NULL && parameters[0] != '\0'))
|
||||||
|
return B_BAD_VALUE;
|
||||||
|
|
||||||
|
// we don't support a content name
|
||||||
|
if (name != NULL)
|
||||||
|
name->Truncate(0);
|
||||||
|
|
||||||
|
return B_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
status_t
|
||||||
|
GPTDiskAddOn::Initialize(BMutablePartition* partition, const char* name,
|
||||||
|
const char* parameters, BPartitionHandle** _handle)
|
||||||
|
{
|
||||||
|
if (!CanInitialize(partition)
|
||||||
|
|| (name != NULL && name[0] != '\0')
|
||||||
|
|| (parameters != NULL && parameters[0] != '\0'))
|
||||||
|
return B_BAD_VALUE;
|
||||||
|
|
||||||
|
GPTPartitionHandle* handle
|
||||||
|
= new(std::nothrow) GPTPartitionHandle(partition);
|
||||||
|
if (handle == NULL)
|
||||||
|
return B_NO_MEMORY;
|
||||||
|
|
||||||
|
status_t status = partition->SetContentType(Name());
|
||||||
|
if (status != B_OK) {
|
||||||
|
delete handle;
|
||||||
|
return status;
|
||||||
|
}
|
||||||
|
|
||||||
|
partition->SetContentName(NULL);
|
||||||
|
partition->SetContentParameters(NULL);
|
||||||
|
partition->SetContentSize(
|
||||||
|
round_down(partition->Size(), partition->BlockSize()));
|
||||||
|
|
||||||
|
*_handle = handle;
|
||||||
|
return B_OK;
|
||||||
|
}
|
||||||
@@ -0,0 +1,35 @@
|
|||||||
|
/*
|
||||||
|
* Copyright 2013, Axel Dörfler, [email protected].
|
||||||
|
* Distributed under the terms of the MIT License.
|
||||||
|
*/
|
||||||
|
#ifndef GPT_DISK_ADD_ON_H
|
||||||
|
#define GPT_DISK_ADD_ON_H
|
||||||
|
|
||||||
|
|
||||||
|
#include <DiskSystemAddOn.h>
|
||||||
|
|
||||||
|
|
||||||
|
class GPTDiskAddOn : public BDiskSystemAddOn {
|
||||||
|
public:
|
||||||
|
GPTDiskAddOn();
|
||||||
|
virtual ~GPTDiskAddOn();
|
||||||
|
|
||||||
|
virtual status_t CreatePartitionHandle(
|
||||||
|
BMutablePartition* partition,
|
||||||
|
BPartitionHandle** handle);
|
||||||
|
|
||||||
|
virtual bool CanInitialize(
|
||||||
|
const BMutablePartition* partition);
|
||||||
|
virtual status_t GetInitializationParameterEditor(
|
||||||
|
const BMutablePartition* partition,
|
||||||
|
BPartitionParameterEditor** editor);
|
||||||
|
virtual status_t ValidateInitialize(
|
||||||
|
const BMutablePartition* partition,
|
||||||
|
BString* name, const char* parameters);
|
||||||
|
virtual status_t Initialize(BMutablePartition* partition,
|
||||||
|
const char* name, const char* parameters,
|
||||||
|
BPartitionHandle** handle);
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
#endif // GPT_DISK_ADD_ON_H
|
||||||
@@ -0,0 +1,15 @@
|
|||||||
|
/*
|
||||||
|
* IntelDiskAddOn.rdef
|
||||||
|
*/
|
||||||
|
|
||||||
|
resource app_signature "application/x-vnd.Haiku-IntelDiskAddOn";
|
||||||
|
|
||||||
|
resource app_version {
|
||||||
|
major = 1,
|
||||||
|
middle = 0,
|
||||||
|
minor = 0,
|
||||||
|
variety = 0,
|
||||||
|
internal = 0,
|
||||||
|
short_info = "1.0.0",
|
||||||
|
long_info = "Haiku Intel disk add-on."
|
||||||
|
};
|
||||||
@@ -0,0 +1,24 @@
|
|||||||
|
/*
|
||||||
|
* Copyright 2013, Axel Dörfler, [email protected].
|
||||||
|
* Distributed under the terms of the MIT License.
|
||||||
|
*/
|
||||||
|
|
||||||
|
|
||||||
|
#include <new>
|
||||||
|
|
||||||
|
#include <List.h>
|
||||||
|
|
||||||
|
#include "GPTDiskAddOn.h"
|
||||||
|
|
||||||
|
|
||||||
|
status_t
|
||||||
|
get_disk_system_add_ons(BList* addOns)
|
||||||
|
{
|
||||||
|
GPTDiskAddOn* addOn = new(std::nothrow) GPTDiskAddOn();
|
||||||
|
if (!addOns->AddItem(addOn)) {
|
||||||
|
delete addOn;
|
||||||
|
return B_NO_MEMORY;
|
||||||
|
}
|
||||||
|
|
||||||
|
return B_OK;
|
||||||
|
}
|
||||||
@@ -0,0 +1,155 @@
|
|||||||
|
/*
|
||||||
|
* Copyright 2013, Axel Dörfler, [email protected].
|
||||||
|
* Distributed under the terms of the MIT License.
|
||||||
|
*/
|
||||||
|
|
||||||
|
|
||||||
|
#include "GPTPartitionHandle.h"
|
||||||
|
|
||||||
|
#include <new>
|
||||||
|
#include <stdio.h>
|
||||||
|
|
||||||
|
#include <DiskDeviceTypes.h>
|
||||||
|
#include <MutablePartition.h>
|
||||||
|
#include <PartitioningInfo.h>
|
||||||
|
#include <PartitionParameterEditor.h>
|
||||||
|
|
||||||
|
#include <AutoDeleter.h>
|
||||||
|
|
||||||
|
#include "gpt_known_guids.h"
|
||||||
|
|
||||||
|
|
||||||
|
//#define TRACE_GPT_PARTITION_HANDLE
|
||||||
|
#undef TRACE
|
||||||
|
#ifdef TRACE_GPT_PARTITION_HANDLE
|
||||||
|
# define TRACE(x...) printf(x)
|
||||||
|
#else
|
||||||
|
# define TRACE(x...) do {} while (false)
|
||||||
|
#endif
|
||||||
|
|
||||||
|
|
||||||
|
GPTPartitionHandle::GPTPartitionHandle(BMutablePartition* partition)
|
||||||
|
:
|
||||||
|
BPartitionHandle(partition)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
GPTPartitionHandle::~GPTPartitionHandle()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
status_t
|
||||||
|
GPTPartitionHandle::Init()
|
||||||
|
{
|
||||||
|
return B_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
uint32
|
||||||
|
GPTPartitionHandle::SupportedOperations(uint32 mask)
|
||||||
|
{
|
||||||
|
uint32 flags = B_DISK_SYSTEM_SUPPORTS_RESIZING
|
||||||
|
| B_DISK_SYSTEM_SUPPORTS_MOVING
|
||||||
|
| B_DISK_SYSTEM_SUPPORTS_SETTING_CONTENT_PARAMETERS
|
||||||
|
| B_DISK_SYSTEM_SUPPORTS_INITIALIZING;
|
||||||
|
|
||||||
|
// creating child
|
||||||
|
if ((mask & B_DISK_SYSTEM_SUPPORTS_CREATING_CHILD) != 0) {
|
||||||
|
BPartitioningInfo info;
|
||||||
|
if (GetPartitioningInfo(&info) == B_OK
|
||||||
|
&& info.CountPartitionableSpaces() > 1) {
|
||||||
|
flags |= B_DISK_SYSTEM_SUPPORTS_CREATING_CHILD;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return flags;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
uint32
|
||||||
|
GPTPartitionHandle::SupportedChildOperations(const BMutablePartition* child,
|
||||||
|
uint32 mask)
|
||||||
|
{
|
||||||
|
return B_DISK_SYSTEM_SUPPORTS_RESIZING_CHILD
|
||||||
|
| B_DISK_SYSTEM_SUPPORTS_MOVING_CHILD
|
||||||
|
| B_DISK_SYSTEM_SUPPORTS_SETTING_TYPE
|
||||||
|
| B_DISK_SYSTEM_SUPPORTS_DELETING_CHILD;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
status_t
|
||||||
|
GPTPartitionHandle::GetNextSupportedType(const BMutablePartition* child,
|
||||||
|
int32* cookie, BString* type)
|
||||||
|
{
|
||||||
|
int32 index = *cookie;
|
||||||
|
TRACE("GPTPartitionHandle::GetNextSupportedType(child: %p, cookie: %ld)\n",
|
||||||
|
child, index);
|
||||||
|
|
||||||
|
if (index >= int32(sizeof(kTypeMap) / sizeof(kTypeMap[0])))
|
||||||
|
return B_ENTRY_NOT_FOUND;
|
||||||
|
|
||||||
|
type->SetTo(kTypeMap[index].type);
|
||||||
|
*cookie = index + 1;
|
||||||
|
|
||||||
|
return B_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
status_t
|
||||||
|
GPTPartitionHandle::GetPartitioningInfo(BPartitioningInfo* info)
|
||||||
|
{
|
||||||
|
// init to the full size (minus the first sector)
|
||||||
|
off_t size = Partition()->ContentSize();
|
||||||
|
status_t error = info->SetTo(Partition()->BlockSize(),
|
||||||
|
size - Partition()->BlockSize());
|
||||||
|
if (error != B_OK)
|
||||||
|
return error;
|
||||||
|
|
||||||
|
// TODO: exclude the space of the existing partitions
|
||||||
|
|
||||||
|
return B_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
status_t
|
||||||
|
GPTPartitionHandle::GetParameterEditor(B_PARAMETER_EDITOR_TYPE type,
|
||||||
|
BPartitionParameterEditor** editor)
|
||||||
|
{
|
||||||
|
*editor = NULL;
|
||||||
|
if (type == B_CREATE_PARAMETER_EDITOR) {
|
||||||
|
try {
|
||||||
|
*editor = new BPartitionParameterEditor();
|
||||||
|
} catch (std::bad_alloc) {
|
||||||
|
return B_NO_MEMORY;
|
||||||
|
}
|
||||||
|
return B_OK;
|
||||||
|
}
|
||||||
|
return B_NOT_SUPPORTED;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
status_t
|
||||||
|
GPTPartitionHandle::ValidateCreateChild(off_t* _offset, off_t* _size,
|
||||||
|
const char* typeString, BString* name, const char* parameters)
|
||||||
|
{
|
||||||
|
return B_BAD_VALUE;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
status_t
|
||||||
|
GPTPartitionHandle::CreateChild(off_t offset, off_t size,
|
||||||
|
const char* typeString, const char* name, const char* parameters,
|
||||||
|
BMutablePartition** _child)
|
||||||
|
{
|
||||||
|
return B_BAD_VALUE;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
status_t
|
||||||
|
GPTPartitionHandle::DeleteChild(BMutablePartition* child)
|
||||||
|
{
|
||||||
|
BMutablePartition* parent = child->Parent();
|
||||||
|
return parent->DeleteChild(child);
|
||||||
|
}
|
||||||
@@ -0,0 +1,45 @@
|
|||||||
|
/*
|
||||||
|
* Copyright 2013, Axel Dörfler, [email protected].
|
||||||
|
* Distributed under the terms of the MIT License.
|
||||||
|
*/
|
||||||
|
#ifndef GPT_PARTITION_HANDLE_H
|
||||||
|
#define GPT_PARTITION_HANDLE_H
|
||||||
|
|
||||||
|
|
||||||
|
#include <DiskSystemAddOn.h>
|
||||||
|
|
||||||
|
|
||||||
|
class GPTPartitionHandle : public BPartitionHandle {
|
||||||
|
public:
|
||||||
|
GPTPartitionHandle(
|
||||||
|
BMutablePartition* partition);
|
||||||
|
virtual ~GPTPartitionHandle();
|
||||||
|
|
||||||
|
status_t Init();
|
||||||
|
|
||||||
|
virtual uint32 SupportedOperations(uint32 mask);
|
||||||
|
virtual uint32 SupportedChildOperations(
|
||||||
|
const BMutablePartition* child,
|
||||||
|
uint32 mask);
|
||||||
|
|
||||||
|
virtual status_t GetNextSupportedType(
|
||||||
|
const BMutablePartition* child,
|
||||||
|
int32* cookie, BString* type);
|
||||||
|
|
||||||
|
virtual status_t GetPartitioningInfo(BPartitioningInfo* info);
|
||||||
|
|
||||||
|
virtual status_t GetParameterEditor(
|
||||||
|
B_PARAMETER_EDITOR_TYPE type,
|
||||||
|
BPartitionParameterEditor** editor);
|
||||||
|
virtual status_t ValidateCreateChild(off_t* offset,
|
||||||
|
off_t* size, const char* type,
|
||||||
|
BString* name, const char* parameters);
|
||||||
|
virtual status_t CreateChild(off_t offset, off_t size,
|
||||||
|
const char* type, const char* name,
|
||||||
|
const char* parameters,
|
||||||
|
BMutablePartition** child);
|
||||||
|
virtual status_t DeleteChild(BMutablePartition* child);
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
#endif // GPT_PARTITION_HANDLE_H
|
||||||
@@ -0,0 +1,17 @@
|
|||||||
|
SubDir HAIKU_TOP src add-ons disk_systems gpt ;
|
||||||
|
|
||||||
|
UsePrivateHeaders shared storage ;
|
||||||
|
UsePrivateSystemHeaders ;
|
||||||
|
|
||||||
|
SEARCH_SOURCE
|
||||||
|
+= [ FDirName $(HAIKU_TOP) src add-ons kernel partitioning_systems efi ] ;
|
||||||
|
|
||||||
|
AddResources <disk_system>gpt : GPTDiskAddOn.rdef ;
|
||||||
|
|
||||||
|
Addon <disk_system>gpt :
|
||||||
|
GPTDiskSystem.cpp
|
||||||
|
GPTDiskAddOn.cpp
|
||||||
|
GPTPartitionHandle.cpp
|
||||||
|
|
||||||
|
: be $(TARGET_LIBSUPC++)
|
||||||
|
;
|
||||||
@@ -0,0 +1,26 @@
|
|||||||
|
/*
|
||||||
|
* Copyright 2013, Axel Dörfler, [email protected].
|
||||||
|
* Distributed under the terms of the MIT License.
|
||||||
|
*/
|
||||||
|
#ifndef UTILITY_H
|
||||||
|
#define UTILITY_H
|
||||||
|
|
||||||
|
|
||||||
|
#include <SupportDefs.h>
|
||||||
|
|
||||||
|
|
||||||
|
static inline off_t
|
||||||
|
round_down(off_t a, uint32 b)
|
||||||
|
{
|
||||||
|
return a / b * b;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
static inline off_t
|
||||||
|
round_up(off_t a, uint32 b)
|
||||||
|
{
|
||||||
|
return round_down(a + b - 1, b);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
#endif // UTILITY_H
|
||||||
Reference in New Issue
Block a user