Added B_TRIM_DEVICE support to BFS.
* It currently ignores the offset/size, though, and always trims everything. * Now only SCSI support is missing.
This commit is contained in:
@@ -1,5 +1,5 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright 2001-2012, Axel Dörfler, [email protected].
|
* Copyright 2001-2013, Axel Dörfler, [email protected].
|
||||||
* This file may be used under the terms of the MIT License.
|
* This file may be used under the terms of the MIT License.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
@@ -1190,6 +1190,62 @@ BlockAllocator::_CheckGroup(int32 groupIndex) const
|
|||||||
#endif // DEBUG_ALLOCATION_GROUPS
|
#endif // DEBUG_ALLOCATION_GROUPS
|
||||||
|
|
||||||
|
|
||||||
|
status_t
|
||||||
|
BlockAllocator::Trim(off_t offset, off_t size, off_t& trimmedSize)
|
||||||
|
{
|
||||||
|
RecursiveLocker locker(fLock);
|
||||||
|
|
||||||
|
// TODO: take given offset and size into account!
|
||||||
|
int32 lastGroup = fNumGroups - 1;
|
||||||
|
uint32 firstBlock = 0;
|
||||||
|
uint32 firstBit = 0;
|
||||||
|
off_t currentBlock = 0;
|
||||||
|
uint32 blockShift = fVolume->BlockShift();
|
||||||
|
|
||||||
|
off_t firstFree = -1;
|
||||||
|
size_t freeLength = 0;
|
||||||
|
trimmedSize = 0;
|
||||||
|
|
||||||
|
AllocationBlock cached(fVolume);
|
||||||
|
for (int32 groupIndex = 0; groupIndex <= lastGroup; groupIndex++) {
|
||||||
|
AllocationGroup& group = fGroups[groupIndex];
|
||||||
|
|
||||||
|
for (uint32 block = firstBlock; block < group.NumBlocks(); block++) {
|
||||||
|
cached.SetTo(group, block);
|
||||||
|
|
||||||
|
for (uint32 i = firstBit; i < cached.NumBlockBits(); i++) {
|
||||||
|
if (cached.IsUsed(i)) {
|
||||||
|
// Block is in use
|
||||||
|
if (freeLength > 0) {
|
||||||
|
status_t status = _TrimNext(firstFree << blockShift,
|
||||||
|
freeLength << blockShift, trimmedSize);
|
||||||
|
if (status != B_OK)
|
||||||
|
return status;
|
||||||
|
|
||||||
|
freeLength = 0;
|
||||||
|
}
|
||||||
|
} else if (freeLength++ == 0) {
|
||||||
|
// Block is free, start new free range
|
||||||
|
firstFree = currentBlock;
|
||||||
|
}
|
||||||
|
|
||||||
|
currentBlock++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
firstBlock = 0;
|
||||||
|
firstBit = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (freeLength > 0) {
|
||||||
|
return _TrimNext(firstFree << blockShift, freeLength << blockShift,
|
||||||
|
trimmedSize);
|
||||||
|
}
|
||||||
|
|
||||||
|
return B_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
// #pragma mark - Bitmap validity checking
|
// #pragma mark - Bitmap validity checking
|
||||||
|
|
||||||
// TODO: implement new FS checking API
|
// TODO: implement new FS checking API
|
||||||
@@ -2124,6 +2180,26 @@ BlockAllocator::_AddInodeToIndex(Inode* inode)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
status_t
|
||||||
|
BlockAllocator::_TrimNext(off_t offset, off_t size, off_t& trimmedSize)
|
||||||
|
{
|
||||||
|
PRINT(("_TrimNext(offset %lld, size %lld)\n", offset, size));
|
||||||
|
|
||||||
|
fs_trim_data trimData;
|
||||||
|
trimData.offset = offset;
|
||||||
|
trimData.size = size;
|
||||||
|
trimData.trimmed_size = 0;
|
||||||
|
|
||||||
|
if (ioctl(fVolume->Device(), B_TRIM_DEVICE, &trimData,
|
||||||
|
sizeof(fs_trim_data)) != 0) {
|
||||||
|
return errno;
|
||||||
|
}
|
||||||
|
|
||||||
|
trimmedSize += trimData.trimmed_size;
|
||||||
|
return B_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
// #pragma mark - debugger commands
|
// #pragma mark - debugger commands
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright 2001-2012, Axel Dörfler, [email protected].
|
* Copyright 2001-2013, Axel Dörfler, [email protected].
|
||||||
* This file may be used under the terms of the MIT License.
|
* This file may be used under the terms of the MIT License.
|
||||||
*/
|
*/
|
||||||
#ifndef BLOCK_ALLOCATOR_H
|
#ifndef BLOCK_ALLOCATOR_H
|
||||||
@@ -46,6 +46,8 @@ public:
|
|||||||
int32 group, uint16 start, uint16 numBlocks,
|
int32 group, uint16 start, uint16 numBlocks,
|
||||||
uint16 minimum, block_run& run);
|
uint16 minimum, block_run& run);
|
||||||
|
|
||||||
|
status_t Trim(off_t offset, off_t size, off_t& trimmedSize);
|
||||||
|
|
||||||
status_t StartChecking(const check_control* control);
|
status_t StartChecking(const check_control* control);
|
||||||
status_t StopChecking(check_control* control);
|
status_t StopChecking(check_control* control);
|
||||||
status_t CheckNextNode(check_control* control);
|
status_t CheckNextNode(check_control* control);
|
||||||
@@ -81,6 +83,8 @@ private:
|
|||||||
void _FreeIndices();
|
void _FreeIndices();
|
||||||
status_t _AddInodeToIndex(Inode* inode);
|
status_t _AddInodeToIndex(Inode* inode);
|
||||||
status_t _WriteBackCheckBitmap();
|
status_t _WriteBackCheckBitmap();
|
||||||
|
status_t _TrimNext(off_t offset, off_t size,
|
||||||
|
off_t& trimmedSize);
|
||||||
|
|
||||||
static status_t _Initialize(BlockAllocator* self);
|
static status_t _Initialize(BlockAllocator* self);
|
||||||
|
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright 2001-2010, Axel Dörfler, axeld@pinc-software.de.
|
* Copyright 2001-2013, Axel Dörfler, axeld@pinc-software.de.
|
||||||
* This file may be used under the terms of the MIT License.
|
* This file may be used under the terms of the MIT License.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
@@ -623,6 +623,20 @@ bfs_ioctl(fs_volume* _volume, fs_vnode* _node, void* _cookie, uint32 cmd,
|
|||||||
Volume* volume = (Volume*)_volume->private_volume;
|
Volume* volume = (Volume*)_volume->private_volume;
|
||||||
|
|
||||||
switch (cmd) {
|
switch (cmd) {
|
||||||
|
case B_TRIM_DEVICE:
|
||||||
|
{
|
||||||
|
fs_trim_data trimData;
|
||||||
|
if (user_memcpy(&trimData, buffer, sizeof(fs_trim_data)) != B_OK)
|
||||||
|
return B_BAD_ADDRESS;
|
||||||
|
|
||||||
|
status_t status = volume->Allocator().Trim(trimData.offset,
|
||||||
|
trimData.size, trimData.trimmed_size);
|
||||||
|
if (status != B_OK)
|
||||||
|
return status;
|
||||||
|
|
||||||
|
return user_memcpy(buffer, &trimData, sizeof(fs_trim_data));
|
||||||
|
}
|
||||||
|
|
||||||
case BFS_IOCTL_VERSION:
|
case BFS_IOCTL_VERSION:
|
||||||
{
|
{
|
||||||
uint32 version = 0x10000;
|
uint32 version = 0x10000;
|
||||||
|
|||||||
Reference in New Issue
Block a user