[linked-list] add Find() and GetTail() methods (#4388)

The `LinkedList::Find()` method searches for a given entry in the
linked list and if found returns a pointer to the previous entry
behind it. The `LinkedList::GetTail()` returns the tail of the list
(last entry in the list). This commit also updates the unit test
`test_linked_list` to verify the behavior of newly added methods.
This commit is contained in:
Abtin Keshavarzian
2019-12-12 08:56:08 -08:00
committed by Jonathan Hui
parent db1f7d2eac
commit 802c9dfcbc
2 changed files with 76 additions and 0 deletions
+66
View File
@@ -303,6 +303,72 @@ public:
return error;
}
/**
* This method searches within the linked list to find an entry and if found returns a pointer to previous entry.
*
* @param[in] aEntry A reference to an entry to find.
* @param[out] aPrevEntry A pointer to output previous entry on success (when @p aEntry is found is the list).
* @p aPrevEntry is set to NULL if the @p aEntry is head of the list. Otherwise it
* is updated to point to previous entry before @p aEntry in the list.
*
* @retval OT_ERROR_NONE The entry was found in the list and @p aPrevEntry was updated successfully.
* @retval OT_ERROR_NOT_FOUND The entry was not found in the list.
*
*/
otError Find(const Type &aEntry, Type *&aPrevEntry) const
{
otError error = OT_ERROR_NOT_FOUND;
if (mHead == &aEntry)
{
aPrevEntry = NULL;
error = OT_ERROR_NONE;
}
else
{
for (Type *cur = mHead; cur->GetNext() != NULL; cur = cur->GetNext())
{
if (cur->GetNext() == &aEntry)
{
aPrevEntry = cur;
error = OT_ERROR_NONE;
break;
}
}
}
return error;
}
/**
* This method returns the tail of the linked list (i.e., the last entry in the list).
*
* @returns A pointer to tail entry in the linked list or NULL if list is empty.
*
*/
const Type *GetTail(void) const
{
const Type *tail = mHead;
if (tail != NULL)
{
while (tail->GetNext() != NULL)
{
tail = tail->GetNext();
}
}
return tail;
}
/**
* This method returns the tail of the linked list (i.e., the last entry in the list).
*
* @returns A pointer to tail entry in the linked list or NULL if list is empty.
*
*/
Type *GetTail(void) { return const_cast<Type *>(const_cast<const LinkedList<Type> *>(this)->GetTail()); }
private:
Type *mHead;
};
+10
View File
@@ -52,19 +52,29 @@ void VerifyLinkedListContent(const ot::LinkedList<Entry> &aList, ...)
{
va_list args;
Entry * argEntry;
Entry * argPrev = NULL;
va_start(args, aList);
for (const Entry *entry = aList.GetHead(); entry; entry = entry->GetNext())
{
Entry *prev;
argEntry = va_arg(args, Entry *);
VerifyOrQuit(argEntry != NULL, "List contains more entries than expected");
VerifyOrQuit(argEntry == entry, "List does not contain the same entry");
VerifyOrQuit(aList.Contains(*argEntry), "List::Contains() failed");
SuccessOrQuit(aList.Find(*argEntry, prev), "List::Find() failed");
VerifyOrQuit(prev == argPrev, "List::Find() returned prev entry is incorrect");
argPrev = argEntry;
}
argEntry = va_arg(args, Entry *);
VerifyOrQuit(argEntry == NULL, "List contains less entries than expected");
VerifyOrQuit(aList.GetTail() == argPrev, "List::GetTail() failed");
}
void TestLinkedList(void)