1.1 --- a/src/cx/iterator.h Thu May 23 19:29:14 2024 +0200 1.2 +++ b/src/cx/iterator.h Thu May 23 20:29:28 2024 +0200 1.3 @@ -38,45 +38,54 @@ 1.4 1.5 #include "common.h" 1.6 1.7 -#define CX_ITERATOR_BASE \ 1.8 - /** \ 1.9 - * True iff the iterator points to valid data. \ 1.10 - */ \ 1.11 - __attribute__ ((__nonnull__)) \ 1.12 - bool (*valid)(void const *); \ 1.13 - /** \ 1.14 - * Returns a pointer to the current element. \ 1.15 - * \ 1.16 - * When valid returns false, the behavior of this function is undefined. \ 1.17 - */ \ 1.18 - __attribute__ ((__nonnull__)) \ 1.19 - void *(*current)(void const *); \ 1.20 - /** \ 1.21 - * Original implementation in case the function needs to be wrapped. \ 1.22 - */ \ 1.23 - __attribute__ ((__nonnull__)) \ 1.24 - void *(*current_impl)(void const *); \ 1.25 - /** \ 1.26 - * Advances the iterator. \ 1.27 - * \ 1.28 - * When valid returns false, the behavior of this function is undefined. \ 1.29 - */ \ 1.30 - __attribute__ ((__nonnull__)) \ 1.31 - void (*next)(void *); \ 1.32 - /** \ 1.33 - * Indicates whether this iterator may remove elements. \ 1.34 - */ \ 1.35 - bool mutating; \ 1.36 - /** \ 1.37 - * Internal flag for removing the current element when advancing. \ 1.38 - */ \ 1.39 +struct cx_iterator_base_s { 1.40 + /** 1.41 + * True iff the iterator points to valid data. 1.42 + */ 1.43 + __attribute__ ((__nonnull__)) 1.44 + bool (*valid)(void const *); 1.45 + 1.46 + /** 1.47 + * Returns a pointer to the current element. 1.48 + * 1.49 + * When valid returns false, the behavior of this function is undefined. 1.50 + */ 1.51 + __attribute__ ((__nonnull__)) 1.52 + void *(*current)(void const *); 1.53 + 1.54 + /** 1.55 + * Original implementation in case the function needs to be wrapped. 1.56 + */ 1.57 + __attribute__ ((__nonnull__)) 1.58 + void *(*current_impl)(void const *); 1.59 + 1.60 + /** 1.61 + * Advances the iterator. 1.62 + * 1.63 + * When valid returns false, the behavior of this function is undefined. 1.64 + */ 1.65 + __attribute__ ((__nonnull__)) 1.66 + void (*next)(void *); 1.67 + /** 1.68 + * Indicates whether this iterator may remove elements. 1.69 + */ 1.70 + bool mutating; 1.71 + /** 1.72 + * Internal flag for removing the current element when advancing. 1.73 + */ 1.74 bool remove; 1.75 +}; 1.76 + 1.77 +/** 1.78 + * Declares base attributes for an iterator. 1.79 + */ 1.80 +#define CX_ITERATOR_BASE struct cx_iterator_base_s base 1.81 1.82 /** 1.83 * Internal iterator struct - use CxIterator. 1.84 */ 1.85 struct cx_iterator_s { 1.86 - CX_ITERATOR_BASE 1.87 + CX_ITERATOR_BASE; 1.88 1.89 /** 1.90 * Handle for the current element. 1.91 @@ -157,7 +166,7 @@ 1.92 * @param iter the iterator 1.93 * @return true iff the iterator points to valid data 1.94 */ 1.95 -#define cxIteratorValid(iter) (iter).valid(&(iter)) 1.96 +#define cxIteratorValid(iter) (iter).base.valid(&(iter)) 1.97 1.98 /** 1.99 * Returns a pointer to the current element. 1.100 @@ -167,21 +176,21 @@ 1.101 * @param iter the iterator 1.102 * @return a pointer to the current element 1.103 */ 1.104 -#define cxIteratorCurrent(iter) (iter).current(&iter) 1.105 +#define cxIteratorCurrent(iter) (iter).base.current(&iter) 1.106 1.107 /** 1.108 * Advances the iterator to the next element. 1.109 * 1.110 * @param iter the iterator 1.111 */ 1.112 -#define cxIteratorNext(iter) (iter).next(&iter) 1.113 +#define cxIteratorNext(iter) (iter).base.next(&iter) 1.114 1.115 /** 1.116 * Flags the current element for removal, if this iterator is mutating. 1.117 * 1.118 * @param iter the iterator 1.119 */ 1.120 -#define cxIteratorFlagRemoval(iter) (iter).remove |= (iter).mutating 1.121 +#define cxIteratorFlagRemoval(iter) (iter).base.remove |= (iter).base.mutating 1.122 1.123 /** 1.124 * Loops over an iterator.