Add Node::Init() flags parameter

* Add Node::Init() flags:
  - NODE_FLAG_KEEP_NAME: Take over ownership of the name.
  - NODE_FLAG_CONST_NAME: Don't copy the name -- it's a constant that
    lives at least as long as the object.
* Remove Init() implementations in derived classes that just call the
  base class version.
This commit is contained in:
Ingo Weinhold 2011-06-24 12:42:16 +02:00
parent 1d8edd93e2
commit 724fba1b09
14 changed files with 49 additions and 54 deletions

View File

@ -31,13 +31,13 @@ Directory::~Directory()
status_t
Directory::Init(Directory* parent, const char* name)
Directory::Init(Directory* parent, const char* name, uint32 flags)
{
status_t error = fChildTable.Init();
status_t error = Node::Init(parent, name, flags);
if (error != B_OK)
return error;
return Node::Init(parent, name);
return fChildTable.Init();
}

View File

@ -27,7 +27,8 @@ public:
Directory(ino_t id);
virtual ~Directory();
virtual status_t Init(Directory* parent, const char* name);
virtual status_t Init(Directory* parent, const char* name,
uint32 flags);
virtual status_t Read(off_t offset, void* buffer,
size_t* bufferSize);

View File

@ -16,7 +16,8 @@ Node::Node(ino_t id)
:
fID(id),
fParent(NULL),
fName(NULL)
fName(NULL),
fFlags(0)
{
rw_lock_init(&fLock, "packagefs node");
}
@ -24,19 +25,28 @@ Node::Node(ino_t id)
Node::~Node()
{
PRINT("%p->Node::~Node()\n", this);
free(fName);
if ((fFlags & NODE_FLAG_OWNS_NAME) != 0)
free(fName);
rw_lock_destroy(&fLock);
}
status_t
Node::Init(Directory* parent, const char* name)
Node::Init(Directory* parent, const char* name, uint32 flags)
{
fParent = parent;
fName = strdup(name);
if (fName == NULL)
RETURN_ERROR(B_NO_MEMORY);
fFlags = flags;
if ((flags & NODE_FLAG_CONST_NAME) != 0
|| (flags & NODE_FLAG_KEEP_NAME) != 0) {
fName = const_cast<char*>(name);
} else {
fName = strdup(name);
if (fName == NULL)
RETURN_ERROR(B_NO_MEMORY);
fFlags |= NODE_FLAG_OWNS_NAME;
}
return B_OK;
}

View File

@ -23,6 +23,18 @@ class Directory;
class PackageNode;
// node flags
enum {
NODE_FLAG_KEEP_NAME = 0x01,
// Init(): Take over ownership of the given name (i.e. free in
// destructor).
NODE_FLAG_CONST_NAME = 0x02,
// Init(): The given name is a constant that won't go away during the
// lifetime of the object. No need to copy.
NODE_FLAG_OWNS_NAME = NODE_FLAG_CONST_NAME
};
class Node : public BReferenceable, public DoublyLinkedListLinkImpl<Node> {
public:
Node(ino_t id);
@ -42,7 +54,10 @@ public:
Node*& IDHashTableNext()
{ return fIDHashTableNext; }
virtual status_t Init(Directory* parent, const char* name);
virtual status_t Init(Directory* parent, const char* name,
uint32 flags);
// If specified to keep the name, it does
// so also on error.
virtual status_t VFSInit(dev_t deviceID);
virtual void VFSUninit();
@ -75,6 +90,7 @@ protected:
char* fName;
Node* fNameHashTableNext;
Node* fIDHashTableNext;
uint32 fFlags;
};

View File

@ -60,7 +60,7 @@ PackageFSRoot::Init()
return B_NO_MEMORY;
status_t error = fPackageLinksDirectory->Init(NULL,
kPackageLinksDirectoryName);
kPackageLinksDirectoryName, 0);
if (error != B_OK)
RETURN_ERROR(error);

View File

@ -61,11 +61,6 @@ public:
{
}
virtual status_t Init(Directory* parent, const char* name)
{
return Node::Init(parent, name);
}
virtual mode_t Mode() const
{
return S_IFLNK | S_IRUSR | S_IXUSR | S_IRGRP | S_IXGRP | S_IROTH
@ -162,7 +157,7 @@ PackageLinkDirectory::Init(Directory* parent, Package* package)
if (fSelfLink == NULL)
return B_NO_MEMORY;
status_t error = fSelfLink->Init(this, kSelfLinkName);
status_t error = fSelfLink->Init(this, kSelfLinkName, NODE_FLAG_CONST_NAME);
if (error != B_OK)
RETURN_ERROR(error);
@ -182,7 +177,6 @@ PackageLinkDirectory::Init(Directory* parent, Package* package)
char* name = (char*)malloc(size);
if (name == NULL)
return B_NO_MEMORY;
MemoryDeleter nameDeleter(name);
memcpy(name, package->Name(), nameLength + 1);
if (version != NULL) {
@ -191,8 +185,7 @@ PackageLinkDirectory::Init(Directory* parent, Package* package)
}
// init the directory/node
error = Init(parent, name);
// TODO: This copies the name unnecessarily!
error = Init(parent, name, NODE_FLAG_KEEP_NAME);
if (error != B_OK)
RETURN_ERROR(error);
@ -204,9 +197,9 @@ PackageLinkDirectory::Init(Directory* parent, Package* package)
status_t
PackageLinkDirectory::Init(Directory* parent, const char* name)
PackageLinkDirectory::Init(Directory* parent, const char* name, uint32 flags)
{
return Directory::Init(parent, name);
return Directory::Init(parent, name, flags);
}

View File

@ -19,7 +19,8 @@ public:
virtual ~PackageLinkDirectory();
status_t Init(Directory* parent, Package* package);
virtual status_t Init(Directory* parent, const char* name);
virtual status_t Init(Directory* parent, const char* name,
uint32 flags);
virtual mode_t Mode() const;
virtual uid_t UserID() const;

View File

@ -30,13 +30,6 @@ PackageLinksDirectory::~PackageLinksDirectory()
}
status_t
PackageLinksDirectory::Init(Directory* parent, const char* name)
{
return Directory::Init(parent, name);
}
mode_t
PackageLinksDirectory::Mode() const
{

View File

@ -18,8 +18,6 @@ public:
PackageLinksDirectory();
virtual ~PackageLinksDirectory();
virtual status_t Init(Directory* parent, const char* name);
virtual mode_t Mode() const;
virtual uid_t UserID() const;
virtual gid_t GroupID() const;

View File

@ -27,13 +27,6 @@ UnpackingDirectory::~UnpackingDirectory()
}
status_t
UnpackingDirectory::Init(Directory* parent, const char* name)
{
return Directory::Init(parent, name);
}
mode_t
UnpackingDirectory::Mode() const
{

View File

@ -16,8 +16,6 @@ public:
UnpackingDirectory(ino_t id);
virtual ~UnpackingDirectory();
virtual status_t Init(Directory* parent, const char* name);
virtual mode_t Mode() const;
virtual uid_t UserID() const;
virtual gid_t GroupID() const;

View File

@ -27,13 +27,6 @@ UnpackingLeafNode::~UnpackingLeafNode()
}
status_t
UnpackingLeafNode::Init(Directory* parent, const char* name)
{
return Node::Init(parent, name);
}
status_t
UnpackingLeafNode::VFSInit(dev_t deviceID)
{

View File

@ -16,8 +16,6 @@ public:
UnpackingLeafNode(ino_t id);
virtual ~UnpackingLeafNode();
virtual status_t Init(Directory* parent, const char* name);
virtual status_t VFSInit(dev_t deviceID);
virtual void VFSUninit();

View File

@ -511,7 +511,8 @@ Volume::Mount(const char* parameterString)
= new(std::nothrow) ::RootDirectory(kRootDirectoryID, st.st_mtim);
if (fRootDirectory == NULL)
RETURN_ERROR(B_NO_MEMORY);
fRootDirectory->Init(NULL, volumeName != NULL ? volumeName : "Package FS");
fRootDirectory->Init(NULL, volumeName != NULL ? volumeName : "Package FS",
0);
fNodes.Insert(fRootDirectory);
// get our mount point
@ -1101,7 +1102,7 @@ Volume::_CreateUnpackingNode(mode_t mode, Directory* parent, const char* name,
Node* node = unpackingNode->GetNode();
BReference<Node> nodeReference(node, true);
status_t error = node->Init(parent, name);
status_t error = node->Init(parent, name, 0);
if (error != B_OK)
RETURN_ERROR(error);