1 #ifndef EXEC_LISTS_H 2 #define EXEC_LISTS_H 3 4 /* 5 exec list definitions (V50) 6 7 Copyright © 2002 The MorphOS Development Team, All Rights Reserved. 8 */ 9 10 #ifndef EXEC_NODES_H 11 # include <exec/nodes.h> 12 #endif 13 14 #pragma pack(2) 15 16 17 struct List 18 { 19 struct Node *lh_Head; 20 struct Node *lh_Tail; 21 struct Node *lh_TailPred; 22 UBYTE lh_Type; 23 UBYTE lh_pad; 24 }; 25 26 struct MinList 27 { 28 struct MinNode *mlh_Head; 29 struct MinNode *mlh_Tail; 30 struct MinNode *mlh_TailPred; 31 }; 32 33 #ifdef __GNUC__ 34 #define IsListEmpty(x) ({struct List *__tmpl = x; (APTR)__tmpl->lh_TailPred == (APTR)__tmpl;}) 35 #define IsMsgPortEmpty(x) ({struct List *__tmpl = &(x)->mp_MsgList; (APTR)__tmpl->lh_TailPred == (APTR)__tmpl;}) 36 #else 37 #define IsListEmpty(x) (((x)->lh_TailPred) == (struct Node *)(x)) 38 #define IsMsgPortEmpty(x) (((x)->mp_MsgList.lh_TailPred) == (struct Node *)(&(x)->mp_MsgList)) 39 #endif 40 41 /* 42 * Some useful macros 43 */ 44 #ifndef NO_LIST_MACROS 45 46 #ifndef NEWLIST 47 #define NEWLIST(MyList) \ 48 do { \ 49 struct MinList *_MyList = (struct MinList *)(MyList); \ 50 _MyList->mlh_TailPred = (struct MinNode *)_MyList; \ 51 _MyList->mlh_Tail = (struct MinNode *)NULL; \ 52 _MyList->mlh_Head = (struct MinNode *)&_MyList->mlh_Tail; \ 53 } while (0) 54 #endif /* !NEWLIST */ 55 56 #ifndef REMHEAD 57 #define REMHEAD(MyList) \ 58 ({ \ 59 struct MinList *_MyList = (struct MinList *)(MyList); \ 60 struct MinNode *RemovedNode; \ 61 struct MinNode *Result; \ 62 if ((RemovedNode = _MyList->mlh_Head)->mln_Succ) \ 63 { \ 64 _MyList->mlh_Head = RemovedNode->mln_Succ; \ 65 _MyList->mlh_Head->mln_Pred = (struct MinNode *)&_MyList->mlh_Head; \ 66 Result = RemovedNode; \ 67 } \ 68 else \ 69 { \ 70 Result = NULL; \ 71 } \ 72 (APTR)Result; \ 73 }) 74 #endif /* !REMHEAD */ 75 76 #ifndef REMTAIL 77 #define REMTAIL(MyList) \ 78 ({ \ 79 struct MinList *_MyList = (struct MinList *)(MyList); \ 80 struct MinNode *RemovedNode; \ 81 struct MinNode *Result; \ 82 if ((RemovedNode = _MyList->mlh_TailPred)->mln_Pred) \ 83 { \ 84 _MyList->mlh_TailPred = RemovedNode->mln_Pred; \ 85 _MyList->mlh_TailPred->mln_Succ = (struct MinNode *)&_MyList->mlh_Tail; \ 86 Result = RemovedNode; \ 87 } \ 88 else \ 89 { \ 90 Result = NULL; \ 91 } \ 92 (APTR)Result; \ 93 }) 94 #endif /* !REMTAIL */ 95 96 #ifndef ADDHEAD 97 #define ADDHEAD(MyList,MyNode) \ 98 do { \ 99 struct MinList *_MyList = (struct MinList *)(MyList); \ 100 struct MinNode *_MyNode = (struct MinNode *)(MyNode); \ 101 struct MinNode *OldHeadNode; \ 102 OldHeadNode = _MyList->mlh_Head; \ 103 _MyNode->mln_Succ = OldHeadNode; \ 104 OldHeadNode->mln_Pred = _MyNode; \ 105 _MyNode->mln_Pred = (struct MinNode *)_MyList; \ 106 _MyList->mlh_Head = _MyNode; \ 107 } while (0) 108 #endif /* !ADDHEAD */ 109 110 #ifndef ADDTAIL 111 #define ADDTAIL(MyList,MyNode) \ 112 do { \ 113 struct MinList *_MyList = (struct MinList *)(MyList); \ 114 struct MinNode *_MyNode = (struct MinNode *)(MyNode); \ 115 struct MinNode *OldPredNode; \ 116 OldPredNode = _MyList->mlh_TailPred; \ 117 _MyNode->mln_Succ = (struct MinNode *)&_MyList->mlh_Tail; \ 118 _MyNode->mln_Pred = OldPredNode; \ 119 OldPredNode->mln_Succ = _MyNode; \ 120 _MyList->mlh_TailPred = _MyNode; \ 121 } while (0) 122 #endif /* !ADDTAIL */ 123 124 #ifndef REMOVE 125 #define REMOVE(MyNode) \ 126 ({ \ 127 struct MinNode *_MyNode = (struct MinNode *)(MyNode); \ 128 struct MinNode *PredNode; \ 129 struct MinNode *SuccNode; \ 130 PredNode = _MyNode->mln_Pred; \ 131 SuccNode = _MyNode->mln_Succ; \ 132 PredNode->mln_Succ = SuccNode; \ 133 SuccNode->mln_Pred = PredNode; \ 134 _MyNode; \ 135 }) 136 #endif /* !REMOVE */ 137 138 #ifndef SWAPNODES 139 #define SWAPNODES(MyNode1,MyNode2) \ 140 do { \ 141 struct MinNode *_MyNode1 = (struct MinNode *)(MyNode1); \ 142 struct MinNode *_MyNode2 = (struct MinNode *)(MyNode2); \ 143 if (_MyNode1 != _MyNode2) \ 144 { \ 145 struct MinNode *SuccNode2, *PredNode2; \ 146 SuccNode2 = _MyNode2->mln_Succ; \ 147 PredNode2 = _MyNode2->mln_Pred; \ 148 PredNode2->mln_Succ = _MyNode1; \ 149 SuccNode2->mln_Pred = _MyNode1; \ 150 _MyNode2->mln_Succ = _MyNode1->mln_Succ; \ 151 _MyNode2->mln_Pred = _MyNode1->mln_Pred; \ 152 _MyNode1->mln_Succ = SuccNode2; \ 153 _MyNode1->mln_Pred = PredNode2; \ 154 _MyNode2->mln_Pred->mln_Succ = _MyNode2; \ 155 _MyNode2->mln_Succ->mln_Pred = _MyNode2; \ 156 } \ 157 } while (0) 158 #endif /* !SWAPNODES */ 159 160 #ifndef INSERT 161 #define INSERT(MyList,MyNode,MyListNode) \ 162 do { \ 163 struct MinList *_MyList = (struct MinList *)(MyList); \ 164 struct MinNode *_MyNode = (struct MinNode *)(MyNode); \ 165 struct MinNode *_MyListNode = (struct MinNode *)(MyListNode); \ 166 if (_MyListNode) \ 167 { \ 168 struct MinNode *MyListNodeSucc; \ 169 if ((MyListNodeSucc = _MyListNode->mln_Succ)) \ 170 { \ 171 _MyNode->mln_Succ = MyListNodeSucc; \ 172 _MyNode->mln_Pred = _MyListNode; \ 173 MyListNodeSucc->mln_Pred = _MyNode; \ 174 _MyListNode->mln_Succ = _MyNode; \ 175 } else { \ 176 struct MinNode *MyListNodePred; \ 177 _MyNode->mln_Succ = _MyListNode; \ 178 MyListNodePred = _MyListNode->mln_Pred; \ 179 _MyNode->mln_Pred = MyListNodePred; \ 180 _MyListNode->mln_Pred = _MyNode; \ 181 MyListNodePred->mln_Succ = _MyNode; \ 182 } \ 183 } else { \ 184 struct MinNode *OldHeadNode; \ 185 OldHeadNode = _MyList->mlh_Head; \ 186 _MyNode->mln_Succ = OldHeadNode; \ 187 OldHeadNode->mln_Pred = _MyNode; \ 188 _MyNode->mln_Pred = (struct MinNode *)_MyList; \ 189 _MyList->mlh_Head = _MyNode; \ 190 } \ 191 } while (0) 192 #endif /* !INSERT */ 193 194 #endif /* !NO_LIST_MACROS */ 195 196 #ifdef AROS_ALMOST_COMPATIBLE 197 198 #define GetHead(_l) \ 199 ({ struct List *l = (struct List *)(_l); \ 200 l->lh_Head->ln_Succ ? l->lh_Head : (struct Node *)0; \ 201 }) 202 203 #define GetTail(_l) \ 204 ({ struct List *l = (struct List *)(_l); \ 205 l->lh_TailPred->ln_Pred ? l->lh_TailPred : (struct Node *)0; \ 206 }) 207 208 #define GetSucc(_n) \ 209 ({ struct Node *n = (struct Node *)(_n); \ 210 n->ln_Succ->ln_Succ ? n->ln_Succ : (struct Node *)0; \ 211 }) 212 213 #define GetPred(_n) \ 214 ({ struct Node *n = (struct Node *)(_n); \ 215 n->ln_Pred->ln_Pred ? n->ln_Pred : (struct Node *)0; \ 216 }) 217 218 #define ForeachNode(l,n) \ 219 for ( \ 220 n = (void *)(((struct List *)(l))->lh_Head); \ 221 ((struct Node *)(n))->ln_Succ; \ 222 n = (void *)(((struct Node *)(n))->ln_Succ) \ 223 ) 224 225 #define ForeachNodeSafe(l,n,n2) \ 226 for ( \ 227 n = (void *)(((struct List *)(l))->lh_Head); \ 228 (n2 = (void *)((struct Node *)(n))->ln_Succ); \ 229 n = (void *)n2 \ 230 ) 231 232 #define SetNodeName(node,name) (((struct Node *)(node))->ln_Name = (char *)(name)) 233 #define GetNodeName(node) (((struct Node *)(node))->ln_Name) 234 235 #define ListLength(list,count) \ 236 do { \ 237 struct Node *n; \ 238 count = 0; \ 239 ForeachNode(list,n) count++; \ 240 } while (0) 241 242 #endif /* AROS_ALMOST_COMPATIBLE */ 243 244 245 #pragma pack() 246 247 #endif