From 1803370cb24c0f78fdcea5a7cb4f00c1404422fc Mon Sep 17 00:00:00 2001 From: Thomas Haller Date: Tue, 17 Aug 2021 11:16:51 +0200 Subject: [PATCH] glib-aux: add nm_dedup_multi_iter_init_reverse() to iterate in reverse order (cherry picked from commit 57a519cc035a55ed51c5e5fd1390eb387d342e8f) --- src/libnm-glib-aux/nm-dedup-multi.h | 40 +++++++++++++++++++++++++++-- 1 file changed, 38 insertions(+), 2 deletions(-) diff --git a/src/libnm-glib-aux/nm-dedup-multi.h b/src/libnm-glib-aux/nm-dedup-multi.h index 9a995ec5d4..75cc193363 100644 --- a/src/libnm-glib-aux/nm-dedup-multi.h +++ b/src/libnm-glib-aux/nm-dedup-multi.h @@ -309,8 +309,11 @@ guint nm_dedup_multi_index_dirty_remove_idx(NMDedupMultiIndex * self, /*****************************************************************************/ typedef struct _NMDedupMultiIter { - const CList * _head; - const CList * _next; + const CList *_head; + union { + const CList *_next; + const CList *_prev; + }; const NMDedupMultiEntry *current; } NMDedupMultiIter; @@ -329,6 +332,21 @@ nm_dedup_multi_iter_init(NMDedupMultiIter *iter, const NMDedupMultiHeadEntry *he iter->current = NULL; } +static inline void +nm_dedup_multi_iter_init_reverse(NMDedupMultiIter *iter, const NMDedupMultiHeadEntry *head) +{ + g_return_if_fail(iter); + + if (head && !c_list_is_empty(&head->lst_entries_head)) { + iter->_head = &head->lst_entries_head; + iter->_prev = head->lst_entries_head.prev; + } else { + iter->_head = NULL; + iter->_prev = NULL; + } + iter->current = NULL; +} + static inline gboolean nm_dedup_multi_iter_next(NMDedupMultiIter *iter) { @@ -347,6 +365,24 @@ nm_dedup_multi_iter_next(NMDedupMultiIter *iter) return TRUE; } +static inline gboolean +nm_dedup_multi_iter_prev(NMDedupMultiIter *iter) +{ + g_return_val_if_fail(iter, FALSE); + + if (!iter->_prev) + return FALSE; + + /* we always look ahead for the prev. This way, the user + * may delete the current entry (but no other entries). */ + iter->current = c_list_entry(iter->_prev, NMDedupMultiEntry, lst_entries); + if (iter->_prev->prev == iter->_head) + iter->_prev = NULL; + else + iter->_prev = iter->_prev->prev; + return TRUE; +} + #define nm_dedup_multi_iter_for_each(iter, head_entry) \ for (nm_dedup_multi_iter_init((iter), (head_entry)); nm_dedup_multi_iter_next((iter));)