* Volume::Unmount() never put the root node, and never deleted the volume's
block cache. * Some cleanup. git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@35069 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
@@ -1,9 +1,10 @@
|
||||
/*
|
||||
* Copyright 2008, Axel Dörfler, [email protected].
|
||||
* Copyright 2008-2010, Axel Dörfler, [email protected].
|
||||
* This file may be used under the terms of the MIT License.
|
||||
*/
|
||||
|
||||
//! super block, mounting, etc.
|
||||
|
||||
//! Super block, mounting, etc.
|
||||
|
||||
|
||||
#include "Volume.h"
|
||||
@@ -31,37 +32,37 @@
|
||||
|
||||
|
||||
class DeviceOpener {
|
||||
public:
|
||||
DeviceOpener(int fd, int mode);
|
||||
DeviceOpener(const char *device, int mode);
|
||||
~DeviceOpener();
|
||||
public:
|
||||
DeviceOpener(int fd, int mode);
|
||||
DeviceOpener(const char* device, int mode);
|
||||
~DeviceOpener();
|
||||
|
||||
int Open(const char *device, int mode);
|
||||
int Open(int fd, int mode);
|
||||
void *InitCache(off_t numBlocks, uint32 blockSize);
|
||||
void RemoveCache(bool allowWrites);
|
||||
int Open(const char* device, int mode);
|
||||
int Open(int fd, int mode);
|
||||
void* InitCache(off_t numBlocks, uint32 blockSize);
|
||||
void RemoveCache(bool allowWrites);
|
||||
|
||||
void Keep();
|
||||
void Keep();
|
||||
|
||||
int Device() const { return fDevice; }
|
||||
int Mode() const { return fMode; }
|
||||
bool IsReadOnly() const { return _IsReadOnly(fMode); }
|
||||
int Device() const { return fDevice; }
|
||||
int Mode() const { return fMode; }
|
||||
bool IsReadOnly() const { return _IsReadOnly(fMode); }
|
||||
|
||||
status_t GetSize(off_t *_size, uint32 *_blockSize = NULL);
|
||||
status_t GetSize(off_t* _size, uint32* _blockSize = NULL);
|
||||
|
||||
private:
|
||||
static bool _IsReadOnly(int mode)
|
||||
{ return (mode & O_RWMASK) == O_RDONLY;}
|
||||
static bool _IsReadWrite(int mode)
|
||||
{ return (mode & O_RWMASK) == O_RDWR;}
|
||||
private:
|
||||
static bool _IsReadOnly(int mode)
|
||||
{ return (mode & O_RWMASK) == O_RDONLY;}
|
||||
static bool _IsReadWrite(int mode)
|
||||
{ return (mode & O_RWMASK) == O_RDWR;}
|
||||
|
||||
int fDevice;
|
||||
int fMode;
|
||||
void *fBlockCache;
|
||||
int fDevice;
|
||||
int fMode;
|
||||
void* fBlockCache;
|
||||
};
|
||||
|
||||
|
||||
DeviceOpener::DeviceOpener(const char *device, int mode)
|
||||
DeviceOpener::DeviceOpener(const char* device, int mode)
|
||||
:
|
||||
fBlockCache(NULL)
|
||||
{
|
||||
@@ -87,7 +88,7 @@ DeviceOpener::~DeviceOpener()
|
||||
|
||||
|
||||
int
|
||||
DeviceOpener::Open(const char *device, int mode)
|
||||
DeviceOpener::Open(const char* device, int mode)
|
||||
{
|
||||
fDevice = open(device, mode | O_NOCACHE);
|
||||
if (fDevice < 0)
|
||||
@@ -131,7 +132,7 @@ DeviceOpener::Open(int fd, int mode)
|
||||
}
|
||||
|
||||
|
||||
void *
|
||||
void*
|
||||
DeviceOpener::InitCache(off_t numBlocks, uint32 blockSize)
|
||||
{
|
||||
return fBlockCache = block_cache_create(fDevice, numBlocks, blockSize,
|
||||
@@ -161,7 +162,7 @@ DeviceOpener::Keep()
|
||||
to compute the size, or fstat() if that failed.
|
||||
*/
|
||||
status_t
|
||||
DeviceOpener::GetSize(off_t *_size, uint32 *_blockSize)
|
||||
DeviceOpener::GetSize(off_t* _size, uint32* _blockSize)
|
||||
{
|
||||
device_geometry geometry;
|
||||
if (ioctl(fDevice, B_GET_GEOMETRY, &geometry) < 0) {
|
||||
@@ -304,7 +305,8 @@ Volume::Mount(const char* deviceName, uint32 flags)
|
||||
if (diskSize < (NumBlocks() << BlockShift()))
|
||||
return B_BAD_VALUE;
|
||||
|
||||
if ((fBlockCache = opener.InitCache(NumBlocks(), fBlockSize)) == NULL)
|
||||
fBlockCache = opener.InitCache(NumBlocks(), fBlockSize);
|
||||
if (fBlockCache == NULL)
|
||||
return B_ERROR;
|
||||
|
||||
status = get_vnode(fFSVolume, EXT2_ROOT_NODE, (void**)&fRootNode);
|
||||
@@ -339,8 +341,8 @@ Volume::Mount(const char* deviceName, uint32 flags)
|
||||
status_t
|
||||
Volume::Unmount()
|
||||
{
|
||||
//put_vnode(fVolume, ToVnode(Root()));
|
||||
//block_cache_delete(fBlockCache, !IsReadOnly());
|
||||
put_vnode(fFSVolume, RootNode()->ID());
|
||||
block_cache_delete(fBlockCache, !IsReadOnly());
|
||||
close(fDevice);
|
||||
|
||||
return B_OK;
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2008-2009, Axel Dörfler, [email protected].
|
||||
* Copyright 2008-2010, Axel Dörfler, [email protected].
|
||||
* This file may be used under the terms of the MIT License.
|
||||
*/
|
||||
#ifndef VOLUME_H
|
||||
@@ -12,67 +12,75 @@
|
||||
|
||||
class Inode;
|
||||
|
||||
|
||||
enum volume_flags {
|
||||
VOLUME_READ_ONLY = 0x0001
|
||||
};
|
||||
|
||||
|
||||
class Volume {
|
||||
public:
|
||||
Volume(fs_volume* volume);
|
||||
~Volume();
|
||||
Volume(fs_volume* volume);
|
||||
~Volume();
|
||||
|
||||
status_t Mount(const char* device, uint32 flags);
|
||||
status_t Unmount();
|
||||
status_t Mount(const char* device, uint32 flags);
|
||||
status_t Unmount();
|
||||
|
||||
bool IsValidSuperBlock();
|
||||
bool IsReadOnly() const { return fFlags & VOLUME_READ_ONLY; }
|
||||
bool IsValidSuperBlock();
|
||||
bool IsReadOnly() const
|
||||
{ return (fFlags & VOLUME_READ_ONLY) != 0; }
|
||||
|
||||
Inode* RootNode() const { return fRootNode; }
|
||||
int Device() const { return fDevice; }
|
||||
Inode* RootNode() const { return fRootNode; }
|
||||
int Device() const { return fDevice; }
|
||||
|
||||
dev_t ID() const { return fFSVolume ? fFSVolume->id : -1; }
|
||||
fs_volume* FSVolume() const { return fFSVolume; }
|
||||
const char* Name() const;
|
||||
dev_t ID() const
|
||||
{ return fFSVolume ? fFSVolume->id : -1; }
|
||||
fs_volume* FSVolume() const { return fFSVolume; }
|
||||
const char* Name() const;
|
||||
|
||||
off_t NumBlocks() const { return fSuperBlock.NumBlocks(); }
|
||||
off_t FreeBlocks() const { return fSuperBlock.FreeBlocks(); }
|
||||
off_t NumBlocks() const
|
||||
{ return fSuperBlock.NumBlocks(); }
|
||||
off_t FreeBlocks() const
|
||||
{ return fSuperBlock.FreeBlocks(); }
|
||||
|
||||
uint32 BlockSize() const { return fBlockSize; }
|
||||
uint32 BlockShift() const { return fBlockShift; }
|
||||
uint32 InodeSize() const { return fSuperBlock.InodeSize(); }
|
||||
ext2_super_block& SuperBlock() { return fSuperBlock; }
|
||||
uint32 BlockSize() const { return fBlockSize; }
|
||||
uint32 BlockShift() const { return fBlockShift; }
|
||||
uint32 InodeSize() const
|
||||
{ return fSuperBlock.InodeSize(); }
|
||||
ext2_super_block& SuperBlock() { return fSuperBlock; }
|
||||
|
||||
status_t GetInodeBlock(ino_t id, uint32& block);
|
||||
uint32 InodeBlockIndex(ino_t id) const;
|
||||
status_t GetBlockGroup(int32 index, ext2_block_group** _group);
|
||||
status_t GetInodeBlock(ino_t id, uint32& block);
|
||||
uint32 InodeBlockIndex(ino_t id) const;
|
||||
status_t GetBlockGroup(int32 index,
|
||||
ext2_block_group** _group);
|
||||
|
||||
// cache access
|
||||
void* BlockCache() { return fBlockCache; }
|
||||
void* BlockCache() { return fBlockCache; }
|
||||
|
||||
static status_t Identify(int fd, ext2_super_block* superBlock);
|
||||
static status_t Identify(int fd, ext2_super_block* superBlock);
|
||||
|
||||
private:
|
||||
static uint32 _UnsupportedIncompatibleFeatures(
|
||||
ext2_super_block& superBlock);
|
||||
off_t _GroupBlockOffset(uint32 blockIndex);
|
||||
static uint32 _UnsupportedIncompatibleFeatures(
|
||||
ext2_super_block& superBlock);
|
||||
off_t _GroupBlockOffset(uint32 blockIndex);
|
||||
|
||||
private:
|
||||
mutex fLock;
|
||||
fs_volume* fFSVolume;
|
||||
int fDevice;
|
||||
ext2_super_block fSuperBlock;
|
||||
char fName[32];
|
||||
uint32 fFlags;
|
||||
uint32 fBlockSize;
|
||||
uint32 fBlockShift;
|
||||
uint32 fFirstDataBlock;
|
||||
uint32 fNumGroups;
|
||||
uint32 fGroupsPerBlock;
|
||||
ext2_block_group** fGroupBlocks;
|
||||
uint32 fInodesPerBlock;
|
||||
mutex fLock;
|
||||
fs_volume* fFSVolume;
|
||||
int fDevice;
|
||||
ext2_super_block fSuperBlock;
|
||||
char fName[32];
|
||||
uint32 fFlags;
|
||||
uint32 fBlockSize;
|
||||
uint32 fBlockShift;
|
||||
uint32 fFirstDataBlock;
|
||||
uint32 fNumGroups;
|
||||
uint32 fGroupsPerBlock;
|
||||
ext2_block_group** fGroupBlocks;
|
||||
uint32 fInodesPerBlock;
|
||||
|
||||
void* fBlockCache;
|
||||
Inode* fRootNode;
|
||||
void* fBlockCache;
|
||||
Inode* fRootNode;
|
||||
};
|
||||
|
||||
#endif // VOLUME_H
|
||||
|
||||
Reference in New Issue
Block a user