Implement TODO: Check for non-empty directories before removing an entry. This
fixes #4358, there changing the Tracker preferences causes some default directories to be created, like "home" and "config", which were previously simply killing off the real ones. git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@32822 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
@@ -116,6 +116,8 @@ public:
|
||||
void SetParentDir(OverlayInode *parentDir);
|
||||
OverlayInode * ParentDir() { return fParentDir; }
|
||||
|
||||
bool IsNonEmptyDirectory();
|
||||
|
||||
status_t Lookup(const char *name, ino_t *inodeNumber);
|
||||
void SetName(const char *name);
|
||||
status_t GetName(char *buffer, size_t bufferSize);
|
||||
@@ -287,6 +289,22 @@ OverlayInode::SetParentDir(OverlayInode *parentDir)
|
||||
}
|
||||
|
||||
|
||||
bool
|
||||
OverlayInode::IsNonEmptyDirectory()
|
||||
{
|
||||
if (!fHasStat)
|
||||
ReadStat(NULL);
|
||||
|
||||
if (!S_ISDIR(fStat.st_mode))
|
||||
return false;
|
||||
|
||||
if (!fHasDirents)
|
||||
_PopulateDirents();
|
||||
|
||||
return fDirentCount > 2; // accounting for "." and ".." entries
|
||||
}
|
||||
|
||||
|
||||
status_t
|
||||
OverlayInode::Lookup(const char *name, ino_t *inodeNumber)
|
||||
{
|
||||
@@ -829,10 +847,26 @@ OverlayInode::RemoveEntry(const char *name, overlay_dirent **_entry)
|
||||
if (!fHasDirents)
|
||||
_PopulateDirents();
|
||||
|
||||
// TODO: we may not simply remove non-empty directories
|
||||
for (uint32 i = 0; i < fDirentCount; i++) {
|
||||
overlay_dirent *entry = fDirents[i];
|
||||
if (strcmp(entry->name, name) == 0) {
|
||||
if (_entry == NULL) {
|
||||
// check for non-empty directories when trying
|
||||
// to dispose the entry
|
||||
OverlayInode *node = NULL;
|
||||
status_t result = get_vnode(Volume(), entry->inode_number,
|
||||
(void **)&node);
|
||||
if (result != B_OK)
|
||||
return result;
|
||||
|
||||
if (node->IsNonEmptyDirectory())
|
||||
result = B_DIRECTORY_NOT_EMPTY;
|
||||
|
||||
put_vnode(Volume(), entry->inode_number);
|
||||
if (result != B_OK)
|
||||
return result;
|
||||
}
|
||||
|
||||
for (uint32 j = i + 1; j < fDirentCount; j++)
|
||||
fDirents[j - 1] = fDirents[j];
|
||||
fDirentCount--;
|
||||
|
||||
Reference in New Issue
Block a user