* Removed my old doubly linked list implementation, and stay with Ingo's.

* Adapt other sources where needed (the boot loader's RootFileSystem still
  used the old implementation).
* Implemented RootFileSystem::Rewind().


git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@16889 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
Axel Dörfler 2006-03-27 10:27:05 +00:00
parent a722407264
commit c918a987a0
8 changed files with 71 additions and 167 deletions

View File

@ -1,7 +1,7 @@
/*
** Copyright 2003, Axel Dörfler, axeld@pinc-software.de. All rights reserved.
** Distributed under the terms of the OpenBeOS License.
*/
* Copyright 2005-2006, Ingo Weinhold, bonefish@users.sf.net. All rights reserved.
* Distributed under the terms of the MIT License.
*/
#ifndef KERNEL_UTIL_DOUBLY_LINKED_LIST_H
#define KERNEL_UTIL_DOUBLY_LINKED_LIST_H
@ -12,135 +12,6 @@
#ifdef __cplusplus
/* This header defines a doubly-linked list. It differentiates between a link
* and an item.
* It's the C++ version of <util/list.h> it's very small and efficient, but
* has not been perfectly C++-ified yet.
* The link must be part of the item, it cannot be allocated on demand yet.
*/
namespace DoublyLinked {
class Link {
public:
Link *next;
Link *prev;
};
template<class Item, Link Item::* LinkMember = &Item::fLink> class Iterator;
template<class Item, Link Item::* LinkMember = &Item::fLink>
class List {
public:
//typedef typename Item ValueType;
typedef Iterator<Item, LinkMember> IteratorType;
List()
{
fLink.next = fLink.prev = &fLink;
}
void Add(Item *item)
{
//Link *link = &item->*LinkMember;
(item->*LinkMember).next = &fLink;
(item->*LinkMember).prev = fLink.prev;
fLink.prev->next = &(item->*LinkMember);
fLink.prev = &(item->*LinkMember);
}
static void Remove(Item *item)
{
(item->*LinkMember).next->prev = (item->*LinkMember).prev;
(item->*LinkMember).prev->next = (item->*LinkMember).next;
}
Item *RemoveHead()
{
if (IsEmpty())
return NULL;
Item *item = GetItem(fLink.next);
Remove(item);
return item;
}
IteratorType Iterator()
{
return IteratorType(*this);
}
bool IsEmpty()
{
return fLink.next == &fLink;
}
Link *Head()
{
return fLink.next;
}
static inline size_t Offset()
{
return (size_t)&(((Item *)1)->*LinkMember) - 1;
}
static inline Item *GetItem(Link *link)
{
return (Item *)((uint8 *)link - Offset());
}
private:
friend class DoublyLinked::Iterator<Item, LinkMember>;
Link fLink;
};
template<class Item, Link Item::* LinkMember>
class Iterator {
public:
typedef List<Item, LinkMember> ListType;
Iterator() : fCurrent(NULL) {}
Iterator(ListType &list) : fList(&list), fCurrent(list.Head()) {}
Item *Next()
{
if (fCurrent == &fList->fLink)
return NULL;
Link *current = fCurrent;
fCurrent = fCurrent->next;
return ListType::GetItem(current);
}
private:
ListType *fList;
Link *fCurrent;
};
} // namespace DoublyLinked
#endif /* __cplusplus */
#endif /* KERNEL_UTIL_DOUBLY_LINKED_LIST_H */
/*
* Copyright 2005, Ingo Weinhold, bonefish@users.sf.net. All rights reserved.
* Distributed under the terms of the MIT License.
*/
#ifndef _KERNEL_UTIL_DOUBLY_LINKED_LIST_H
#define _KERNEL_UTIL_DOUBLY_LINKED_LIST_H
#ifdef __cplusplus
#include <SupportDefs.h>
// DoublyLinkedListLink
template<typename Element>
class DoublyLinkedListLink {
@ -225,10 +96,10 @@ public:
class Iterator {
public:
Iterator(List *list)
: fList(list),
fCurrent(NULL),
fNext(fList->First())
:
fList(list)
{
Rewind();
}
Iterator(const Iterator &other)
@ -240,7 +111,7 @@ public:
{
return fNext;
}
Element *Next()
{
fCurrent = fNext;
@ -248,7 +119,7 @@ public:
fNext = fList->GetNext(fNext);
return fCurrent;
}
Element *Remove()
{
Element *element = fCurrent;
@ -266,7 +137,13 @@ public:
fNext = other.fNext;
return *this;
}
void Rewind()
{
fCurrent = NULL;
fNext = fList->First();
}
private:
List *fList;
Element *fCurrent;
@ -276,9 +153,10 @@ public:
class ConstIterator {
public:
ConstIterator(const List *list)
: fList(list),
fNext(list->First())
:
fList(list)
{
Rewind();
}
ConstIterator(const ConstIterator &other)
@ -290,7 +168,7 @@ public:
{
return fNext;
}
Element *Next()
{
Element *element = fNext;
@ -298,14 +176,20 @@ public:
fNext = fList->GetNext(fNext);
return element;
}
ConstIterator &operator=(const ConstIterator &other)
{
fList = other.fList;
fNext = other.fNext;
return *this;
}
void Rewind()
{
fCurrent = NULL;
fNext = fList->First();
}
private:
const List *fList;
Element *fNext;
@ -334,6 +218,8 @@ public:
inline Element *Head() const { return fFirst; }
inline Element *Tail() const { return fLast; }
inline Element *RemoveHead();
inline Element *GetPrevious(Element *element) const;
inline Element *GetNext(Element *element) const;
@ -483,6 +369,16 @@ DOUBLY_LINKED_LIST_CLASS_NAME::RemoveAll()
fLast = NULL;
}
// RemoveHead
DOUBLY_LINKED_LIST_TEMPLATE_LIST
Element *
DOUBLY_LINKED_LIST_CLASS_NAME::RemoveHead()
{
Element *element = Head();
Remove(element);
return element;
}
// GetPrevious
DOUBLY_LINKED_LIST_TEMPLATE_LIST
Element *

View File

@ -1,7 +1,7 @@
/*
** Copyright 2003-2004, Axel Dörfler, axeld@pinc-software.de. All rights reserved.
** Distributed under the terms of the OpenBeOS License.
*/
* Copyright 2003-2006, Axel Dörfler, axeld@pinc-software.de. All rights reserved.
* Distributed under the terms of the MIT License.
*/
#include "RootFileSystem.h"
@ -32,10 +32,10 @@ RootFileSystem::~RootFileSystem()
status_t
RootFileSystem::Open(void **_cookie, int mode)
{
EntryIterator *iterator = new EntryIterator(fList.Iterator());
EntryIterator *iterator = new (std::nothrow) EntryIterator(&fList);
if (iterator == NULL)
return B_NO_MEMORY;
*_cookie = iterator;
return B_OK;
@ -53,7 +53,7 @@ RootFileSystem::Close(void *cookie)
Node *
RootFileSystem::Lookup(const char *name, bool /*traverseLinks*/)
{
EntryIterator iterator = fLinks.Iterator();
EntryIterator iterator = fLinks.GetIterator();
struct entry *entry;
// first check the links
@ -67,7 +67,7 @@ RootFileSystem::Lookup(const char *name, bool /*traverseLinks*/)
// then all mounted file systems
iterator = fList.Iterator();
iterator = fList.GetIterator();
while ((entry = iterator.Next()) != NULL) {
char entryName[B_OS_NAME_LENGTH];
@ -116,7 +116,9 @@ RootFileSystem::GetNextNode(void *_cookie, Node **_node)
status_t
RootFileSystem::Rewind(void *_cookie)
{
// ToDo: implement
EntryIterator *iterator = (EntryIterator *)_cookie;
iterator->Rewind();
return B_OK;
}
@ -131,7 +133,7 @@ RootFileSystem::IsEmpty()
status_t
RootFileSystem::AddVolume(Directory *volume, Partition *partition)
{
struct entry *entry = new RootFileSystem::entry();
struct entry *entry = new (std::nothrow) RootFileSystem::entry();
if (entry == NULL)
return B_NO_MEMORY;
@ -149,7 +151,7 @@ RootFileSystem::AddVolume(Directory *volume, Partition *partition)
status_t
RootFileSystem::AddLink(const char *name, Directory *target)
{
struct entry *entry = new RootFileSystem::entry();
struct entry *entry = new (std::nothrow) RootFileSystem::entry();
if (entry == NULL)
return B_NO_MEMORY;
@ -166,7 +168,7 @@ RootFileSystem::AddLink(const char *name, Directory *target)
status_t
RootFileSystem::GetPartitionFor(Directory *volume, Partition **_partition)
{
EntryIterator iterator = fList.Iterator();
EntryIterator iterator = fList.GetIterator();
struct entry *entry;
while ((entry = iterator.Next()) != NULL) {

View File

@ -1,7 +1,7 @@
/*
** Copyright 2003-2004, Axel Dörfler, axeld@pinc-software.de. All rights reserved.
** Distributed under the terms of the OpenBeOS License.
*/
* Copyright 2003-2006, Axel Dörfler, axeld@pinc-software.de. All rights reserved.
* Distributed under the terms of the MIT License.
*/
#ifndef ROOT_FILE_SYSTEM_H
#define ROOT_FILE_SYSTEM_H
@ -33,14 +33,13 @@ class RootFileSystem : public Directory {
status_t GetPartitionFor(Directory *volume, Partition **_partition);
private:
struct entry {
DoublyLinked::Link link;
struct entry : public DoublyLinkedListLinkImpl<entry> {
const char *name;
Directory *root;
Partition *partition;
};
typedef DoublyLinked::Iterator<entry, &entry::link> EntryIterator;
typedef DoublyLinked::List<entry, &entry::link> EntryList;
typedef DoublyLinkedList<entry>::Iterator EntryIterator;
typedef DoublyLinkedList<entry> EntryList;
EntryList fList;
EntryList fLinks;

View File

@ -20,6 +20,7 @@
#include <drivers/driver_settings.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>

View File

@ -13,6 +13,8 @@
#include <util/AutoLock.h>
#include <util/khash.h>
#include <new>
#include <stdlib.h>
#include <string.h>

View File

@ -1,5 +1,5 @@
/*
* Copyright 2002-2005, Axel Dörfler, axeld@pinc-software.de. All rights reserved.
* Copyright 2002-2006, Axel Dörfler, axeld@pinc-software.de. All rights reserved.
* Distributed under the terms of the MIT License.
*
* Copyright 2001-2002, Travis Geiselbrecht. All rights reserved.

View File

@ -1,5 +1,5 @@
/*
* Copyright 2002-2005, Axel Dörfler, axeld@pinc-software.de. All rights reserved.
* Copyright 2002-2006, Axel Dörfler, axeld@pinc-software.de. All rights reserved.
* Distributed under the terms of the MIT License.
*/
@ -11,6 +11,7 @@
#include "vfs_select.h"
#include <sys/select.h>
#include <new>
#include <poll.h>
#include <stdlib.h>
#include <string.h>
@ -340,7 +341,7 @@ add_select_sync_pool_entry(select_sync_pool *pool, selectsync *sync,
select_sync_pool_entry *entry = find_select_sync_pool_entry(pool, sync,
ref);
if (!entry) {
entry = new(nothrow) select_sync_pool_entry;
entry = new (std::nothrow) select_sync_pool_entry;
if (!entry)
return B_NO_MEMORY;
@ -364,7 +365,7 @@ add_select_sync_pool_entry(select_sync_pool **_pool, selectsync *sync,
// create the pool, if necessary
select_sync_pool *pool = *_pool;
if (!pool) {
pool = new(nothrow) select_sync_pool;
pool = new (std::nothrow) select_sync_pool;
if (!pool)
return B_NO_MEMORY;

View File

@ -1,11 +1,10 @@
/*
* Copyright 2005, Axel Dörfler, axeld@pinc-software.de.
* Copyright 2005-2006, Axel Dörfler, axeld@pinc-software.de.
* Distributed under the terms of the MIT License.
*/
#include <KernelExport.h>
#include <signal.h>
#include <vm_low_memory.h>
#include <vm_page.h>
@ -13,6 +12,10 @@
#include <util/DoublyLinkedList.h>
#include <util/AutoLock.h>
#include <new>
#include <signal.h>
#include <stdlib.h>
//#define TRACE_LOW_MEMORY
#ifdef TRACE_LOW_MEMORY