diff options
Diffstat (limited to 'litmus/binheap.c')
-rw-r--r-- | litmus/binheap.c | 126 |
1 files changed, 63 insertions, 63 deletions
diff --git a/litmus/binheap.c b/litmus/binheap.c index 22feea614e50..8d42403ad52c 100644 --- a/litmus/binheap.c +++ b/litmus/binheap.c | |||
@@ -9,11 +9,11 @@ int binheap_is_in_this_heap(struct binheap_node *node, | |||
9 | if(!binheap_is_in_heap(node)) { | 9 | if(!binheap_is_in_heap(node)) { |
10 | return 0; | 10 | return 0; |
11 | } | 11 | } |
12 | 12 | ||
13 | while(node->parent != NULL) { | 13 | while(node->parent != NULL) { |
14 | node = node->parent; | 14 | node = node->parent; |
15 | } | 15 | } |
16 | 16 | ||
17 | return (node == heap->root); | 17 | return (node == heap->root); |
18 | } | 18 | } |
19 | 19 | ||
@@ -23,7 +23,7 @@ static void __update_ref(struct binheap_node *parent, | |||
23 | { | 23 | { |
24 | *(parent->ref_ptr) = child; | 24 | *(parent->ref_ptr) = child; |
25 | *(child->ref_ptr) = parent; | 25 | *(child->ref_ptr) = parent; |
26 | 26 | ||
27 | swap(parent->ref_ptr, child->ref_ptr); | 27 | swap(parent->ref_ptr, child->ref_ptr); |
28 | } | 28 | } |
29 | 29 | ||
@@ -35,7 +35,7 @@ static void __binheap_swap(struct binheap_node *parent, | |||
35 | // dump_node_data(parent, child); | 35 | // dump_node_data(parent, child); |
36 | // BUG(); | 36 | // BUG(); |
37 | // } | 37 | // } |
38 | 38 | ||
39 | swap(parent->data, child->data); | 39 | swap(parent->data, child->data); |
40 | __update_ref(parent, child); | 40 | __update_ref(parent, child); |
41 | } | 41 | } |
@@ -50,14 +50,14 @@ static void __binheap_swap_safe(struct binheap_handle *handle, | |||
50 | { | 50 | { |
51 | swap(a->data, b->data); | 51 | swap(a->data, b->data); |
52 | __update_ref(a, b); | 52 | __update_ref(a, b); |
53 | 53 | ||
54 | if((a->parent != NULL) && (a->parent == b->parent)) { | 54 | if((a->parent != NULL) && (a->parent == b->parent)) { |
55 | /* special case: shared parent */ | 55 | /* special case: shared parent */ |
56 | swap(a->parent->left, a->parent->right); | 56 | swap(a->parent->left, a->parent->right); |
57 | } | 57 | } |
58 | else { | 58 | else { |
59 | /* Update pointers to swap parents. */ | 59 | /* Update pointers to swap parents. */ |
60 | 60 | ||
61 | if(a->parent) { | 61 | if(a->parent) { |
62 | if(a == a->parent->left) { | 62 | if(a == a->parent->left) { |
63 | a->parent->left = b; | 63 | a->parent->left = b; |
@@ -66,7 +66,7 @@ static void __binheap_swap_safe(struct binheap_handle *handle, | |||
66 | a->parent->right = b; | 66 | a->parent->right = b; |
67 | } | 67 | } |
68 | } | 68 | } |
69 | 69 | ||
70 | if(b->parent) { | 70 | if(b->parent) { |
71 | if(b == b->parent->left) { | 71 | if(b == b->parent->left) { |
72 | b->parent->left = a; | 72 | b->parent->left = a; |
@@ -75,48 +75,48 @@ static void __binheap_swap_safe(struct binheap_handle *handle, | |||
75 | b->parent->right = a; | 75 | b->parent->right = a; |
76 | } | 76 | } |
77 | } | 77 | } |
78 | 78 | ||
79 | swap(a->parent, b->parent); | 79 | swap(a->parent, b->parent); |
80 | } | 80 | } |
81 | 81 | ||
82 | /* swap children */ | 82 | /* swap children */ |
83 | 83 | ||
84 | if(a->left) { | 84 | if(a->left) { |
85 | a->left->parent = b; | 85 | a->left->parent = b; |
86 | 86 | ||
87 | if(a->right) { | 87 | if(a->right) { |
88 | a->right->parent = b; | 88 | a->right->parent = b; |
89 | } | 89 | } |
90 | } | 90 | } |
91 | 91 | ||
92 | if(b->left) { | 92 | if(b->left) { |
93 | b->left->parent = a; | 93 | b->left->parent = a; |
94 | 94 | ||
95 | if(b->right) { | 95 | if(b->right) { |
96 | b->right->parent = a; | 96 | b->right->parent = a; |
97 | } | 97 | } |
98 | } | 98 | } |
99 | 99 | ||
100 | swap(a->left, b->left); | 100 | swap(a->left, b->left); |
101 | swap(a->right, b->right); | 101 | swap(a->right, b->right); |
102 | 102 | ||
103 | 103 | ||
104 | /* update next/last/root pointers */ | 104 | /* update next/last/root pointers */ |
105 | 105 | ||
106 | if(a == handle->next) { | 106 | if(a == handle->next) { |
107 | handle->next = b; | 107 | handle->next = b; |
108 | } | 108 | } |
109 | else if(b == handle->next) { | 109 | else if(b == handle->next) { |
110 | handle->next = a; | 110 | handle->next = a; |
111 | } | 111 | } |
112 | 112 | ||
113 | if(a == handle->last) { | 113 | if(a == handle->last) { |
114 | handle->last = b; | 114 | handle->last = b; |
115 | } | 115 | } |
116 | else if(b == handle->last) { | 116 | else if(b == handle->last) { |
117 | handle->last = a; | 117 | handle->last = a; |
118 | } | 118 | } |
119 | 119 | ||
120 | if(a == handle->root) { | 120 | if(a == handle->root) { |
121 | handle->root = b; | 121 | handle->root = b; |
122 | } | 122 | } |
@@ -133,29 +133,29 @@ static void __binheap_swap_safe(struct binheap_handle *handle, | |||
133 | static void __binheap_update_last(struct binheap_handle *handle) | 133 | static void __binheap_update_last(struct binheap_handle *handle) |
134 | { | 134 | { |
135 | struct binheap_node *temp = handle->last; | 135 | struct binheap_node *temp = handle->last; |
136 | 136 | ||
137 | /* find a "bend" in the tree. */ | 137 | /* find a "bend" in the tree. */ |
138 | while(temp->parent && (temp == temp->parent->left)) { | 138 | while(temp->parent && (temp == temp->parent->left)) { |
139 | temp = temp->parent; | 139 | temp = temp->parent; |
140 | } | 140 | } |
141 | 141 | ||
142 | /* step over to sibling if we're not at root */ | 142 | /* step over to sibling if we're not at root */ |
143 | if(temp->parent != NULL) { | 143 | if(temp->parent != NULL) { |
144 | temp = temp->parent->left; | 144 | temp = temp->parent->left; |
145 | } | 145 | } |
146 | 146 | ||
147 | /* now travel right as far as possible. */ | 147 | /* now travel right as far as possible. */ |
148 | while(temp->right != NULL) { | 148 | while(temp->right != NULL) { |
149 | temp = temp->right; | 149 | temp = temp->right; |
150 | } | 150 | } |
151 | 151 | ||
152 | /* take one step to the left if we're not at the bottom-most level. */ | 152 | /* take one step to the left if we're not at the bottom-most level. */ |
153 | if(temp->left != NULL) { | 153 | if(temp->left != NULL) { |
154 | temp = temp->left; | 154 | temp = temp->left; |
155 | } | 155 | } |
156 | 156 | ||
157 | //BUG_ON(!(temp->left == NULL && temp->right == NULL)); | 157 | //BUG_ON(!(temp->left == NULL && temp->right == NULL)); |
158 | 158 | ||
159 | handle->last = temp; | 159 | handle->last = temp; |
160 | } | 160 | } |
161 | 161 | ||
@@ -166,22 +166,22 @@ static void __binheap_update_last(struct binheap_handle *handle) | |||
166 | static void __binheap_update_next(struct binheap_handle *handle) | 166 | static void __binheap_update_next(struct binheap_handle *handle) |
167 | { | 167 | { |
168 | struct binheap_node *temp = handle->next; | 168 | struct binheap_node *temp = handle->next; |
169 | 169 | ||
170 | /* find a "bend" in the tree. */ | 170 | /* find a "bend" in the tree. */ |
171 | while(temp->parent && (temp == temp->parent->right)) { | 171 | while(temp->parent && (temp == temp->parent->right)) { |
172 | temp = temp->parent; | 172 | temp = temp->parent; |
173 | } | 173 | } |
174 | 174 | ||
175 | /* step over to sibling if we're not at root */ | 175 | /* step over to sibling if we're not at root */ |
176 | if(temp->parent != NULL) { | 176 | if(temp->parent != NULL) { |
177 | temp = temp->parent->right; | 177 | temp = temp->parent->right; |
178 | } | 178 | } |
179 | 179 | ||
180 | /* now travel left as far as possible. */ | 180 | /* now travel left as far as possible. */ |
181 | while(temp->left != NULL) { | 181 | while(temp->left != NULL) { |
182 | temp = temp->left; | 182 | temp = temp->left; |
183 | } | 183 | } |
184 | 184 | ||
185 | handle->next = temp; | 185 | handle->next = temp; |
186 | } | 186 | } |
187 | 187 | ||
@@ -198,13 +198,13 @@ static void __binheap_bubble_up( | |||
198 | // dump_node_data2(handle, node); | 198 | // dump_node_data2(handle, node); |
199 | // BUG(); | 199 | // BUG(); |
200 | // } | 200 | // } |
201 | 201 | ||
202 | while((node->parent != NULL) && | 202 | while((node->parent != NULL) && |
203 | ((node->data == BINHEAP_POISON) /* let BINHEAP_POISON data bubble to the top */ || | 203 | ((node->data == BINHEAP_POISON) /* let BINHEAP_POISON data bubble to the top */ || |
204 | handle->compare(node, node->parent))) { | 204 | handle->compare(node, node->parent))) { |
205 | __binheap_swap(node->parent, node); | 205 | __binheap_swap(node->parent, node); |
206 | node = node->parent; | 206 | node = node->parent; |
207 | 207 | ||
208 | // if(!binheap_is_in_heap(node)) | 208 | // if(!binheap_is_in_heap(node)) |
209 | // { | 209 | // { |
210 | // dump_node_data2(handle, node); | 210 | // dump_node_data2(handle, node); |
@@ -218,7 +218,7 @@ static void __binheap_bubble_up( | |||
218 | static void __binheap_bubble_down(struct binheap_handle *handle) | 218 | static void __binheap_bubble_down(struct binheap_handle *handle) |
219 | { | 219 | { |
220 | struct binheap_node *node = handle->root; | 220 | struct binheap_node *node = handle->root; |
221 | 221 | ||
222 | while(node->left != NULL) { | 222 | while(node->left != NULL) { |
223 | if(node->right && handle->compare(node->right, node->left)) { | 223 | if(node->right && handle->compare(node->right, node->left)) { |
224 | if(handle->compare(node->right, node)) { | 224 | if(handle->compare(node->right, node)) { |
@@ -252,11 +252,11 @@ void __binheap_add(struct binheap_node *new_node, | |||
252 | // dump_node_data2(handle, new_node); | 252 | // dump_node_data2(handle, new_node); |
253 | // BUG(); | 253 | // BUG(); |
254 | // } | 254 | // } |
255 | 255 | ||
256 | new_node->data = data; | 256 | new_node->data = data; |
257 | new_node->ref = new_node; | 257 | new_node->ref = new_node; |
258 | new_node->ref_ptr = &(new_node->ref); | 258 | new_node->ref_ptr = &(new_node->ref); |
259 | 259 | ||
260 | if(!binheap_empty(handle)) { | 260 | if(!binheap_empty(handle)) { |
261 | /* insert left side first */ | 261 | /* insert left side first */ |
262 | if(handle->next->left == NULL) { | 262 | if(handle->next->left == NULL) { |
@@ -264,9 +264,9 @@ void __binheap_add(struct binheap_node *new_node, | |||
264 | new_node->parent = handle->next; | 264 | new_node->parent = handle->next; |
265 | new_node->left = NULL; | 265 | new_node->left = NULL; |
266 | new_node->right = NULL; | 266 | new_node->right = NULL; |
267 | 267 | ||
268 | handle->last = new_node; | 268 | handle->last = new_node; |
269 | 269 | ||
270 | __binheap_bubble_up(handle, new_node); | 270 | __binheap_bubble_up(handle, new_node); |
271 | } | 271 | } |
272 | else { | 272 | else { |
@@ -275,20 +275,20 @@ void __binheap_add(struct binheap_node *new_node, | |||
275 | new_node->parent = handle->next; | 275 | new_node->parent = handle->next; |
276 | new_node->left = NULL; | 276 | new_node->left = NULL; |
277 | new_node->right = NULL; | 277 | new_node->right = NULL; |
278 | 278 | ||
279 | handle->last = new_node; | 279 | handle->last = new_node; |
280 | 280 | ||
281 | __binheap_update_next(handle); | 281 | __binheap_update_next(handle); |
282 | __binheap_bubble_up(handle, new_node); | 282 | __binheap_bubble_up(handle, new_node); |
283 | } | 283 | } |
284 | } | 284 | } |
285 | else { | 285 | else { |
286 | /* first node in heap */ | 286 | /* first node in heap */ |
287 | 287 | ||
288 | new_node->parent = NULL; | 288 | new_node->parent = NULL; |
289 | new_node->left = NULL; | 289 | new_node->left = NULL; |
290 | new_node->right = NULL; | 290 | new_node->right = NULL; |
291 | 291 | ||
292 | handle->root = new_node; | 292 | handle->root = new_node; |
293 | handle->next = new_node; | 293 | handle->next = new_node; |
294 | handle->last = new_node; | 294 | handle->last = new_node; |
@@ -308,27 +308,27 @@ void __binheap_delete_root(struct binheap_handle *handle, | |||
308 | struct binheap_node *container) | 308 | struct binheap_node *container) |
309 | { | 309 | { |
310 | struct binheap_node *root = handle->root; | 310 | struct binheap_node *root = handle->root; |
311 | 311 | ||
312 | // if(!binheap_is_in_heap(container)) | 312 | // if(!binheap_is_in_heap(container)) |
313 | // { | 313 | // { |
314 | // dump_node_data2(handle, container); | 314 | // dump_node_data2(handle, container); |
315 | // BUG(); | 315 | // BUG(); |
316 | // } | 316 | // } |
317 | 317 | ||
318 | if(root != container) { | 318 | if(root != container) { |
319 | /* coalesce */ | 319 | /* coalesce */ |
320 | __binheap_swap_safe(handle, root, container); | 320 | __binheap_swap_safe(handle, root, container); |
321 | root = container; | 321 | root = container; |
322 | } | 322 | } |
323 | 323 | ||
324 | if(handle->last != root) { | 324 | if(handle->last != root) { |
325 | /* swap 'last' node up to root and bubble it down. */ | 325 | /* swap 'last' node up to root and bubble it down. */ |
326 | 326 | ||
327 | struct binheap_node *to_move = handle->last; | 327 | struct binheap_node *to_move = handle->last; |
328 | 328 | ||
329 | if(to_move->parent != root) { | 329 | if(to_move->parent != root) { |
330 | handle->next = to_move->parent; | 330 | handle->next = to_move->parent; |
331 | 331 | ||
332 | if(handle->next->right == to_move) { | 332 | if(handle->next->right == to_move) { |
333 | /* disconnect from parent */ | 333 | /* disconnect from parent */ |
334 | to_move->parent->right = NULL; | 334 | to_move->parent->right = NULL; |
@@ -337,16 +337,16 @@ void __binheap_delete_root(struct binheap_handle *handle, | |||
337 | else { | 337 | else { |
338 | /* find new 'last' before we disconnect */ | 338 | /* find new 'last' before we disconnect */ |
339 | __binheap_update_last(handle); | 339 | __binheap_update_last(handle); |
340 | 340 | ||
341 | /* disconnect from parent */ | 341 | /* disconnect from parent */ |
342 | to_move->parent->left = NULL; | 342 | to_move->parent->left = NULL; |
343 | } | 343 | } |
344 | } | 344 | } |
345 | else { | 345 | else { |
346 | /* 'last' is direct child of root */ | 346 | /* 'last' is direct child of root */ |
347 | 347 | ||
348 | handle->next = to_move; | 348 | handle->next = to_move; |
349 | 349 | ||
350 | if(to_move == to_move->parent->right) { | 350 | if(to_move == to_move->parent->right) { |
351 | to_move->parent->right = NULL; | 351 | to_move->parent->right = NULL; |
352 | handle->last = to_move->parent->left; | 352 | handle->last = to_move->parent->left; |
@@ -357,7 +357,7 @@ void __binheap_delete_root(struct binheap_handle *handle, | |||
357 | } | 357 | } |
358 | } | 358 | } |
359 | to_move->parent = NULL; | 359 | to_move->parent = NULL; |
360 | 360 | ||
361 | /* reconnect as root. We can't just swap data ptrs since root node | 361 | /* reconnect as root. We can't just swap data ptrs since root node |
362 | * may be freed after this function returns. | 362 | * may be freed after this function returns. |
363 | */ | 363 | */ |
@@ -369,9 +369,9 @@ void __binheap_delete_root(struct binheap_handle *handle, | |||
369 | if(to_move->right != NULL) { | 369 | if(to_move->right != NULL) { |
370 | to_move->right->parent = to_move; | 370 | to_move->right->parent = to_move; |
371 | } | 371 | } |
372 | 372 | ||
373 | handle->root = to_move; | 373 | handle->root = to_move; |
374 | 374 | ||
375 | /* bubble down */ | 375 | /* bubble down */ |
376 | __binheap_bubble_down(handle); | 376 | __binheap_bubble_down(handle); |
377 | } | 377 | } |
@@ -381,7 +381,7 @@ void __binheap_delete_root(struct binheap_handle *handle, | |||
381 | handle->next = NULL; | 381 | handle->next = NULL; |
382 | handle->last = NULL; | 382 | handle->last = NULL; |
383 | } | 383 | } |
384 | 384 | ||
385 | /* mark as removed */ | 385 | /* mark as removed */ |
386 | container->parent = BINHEAP_POISON; | 386 | container->parent = BINHEAP_POISON; |
387 | } | 387 | } |
@@ -396,25 +396,25 @@ void __binheap_delete(struct binheap_node *node_to_delete, | |||
396 | { | 396 | { |
397 | struct binheap_node *target = node_to_delete->ref; | 397 | struct binheap_node *target = node_to_delete->ref; |
398 | void *temp_data = target->data; | 398 | void *temp_data = target->data; |
399 | 399 | ||
400 | // if(!binheap_is_in_heap(node_to_delete)) | 400 | // if(!binheap_is_in_heap(node_to_delete)) |
401 | // { | 401 | // { |
402 | // dump_node_data2(handle, node_to_delete); | 402 | // dump_node_data2(handle, node_to_delete); |
403 | // BUG(); | 403 | // BUG(); |
404 | // } | 404 | // } |
405 | // | 405 | // |
406 | // if(!binheap_is_in_heap(target)) | 406 | // if(!binheap_is_in_heap(target)) |
407 | // { | 407 | // { |
408 | // dump_node_data2(handle, target); | 408 | // dump_node_data2(handle, target); |
409 | // BUG(); | 409 | // BUG(); |
410 | // } | 410 | // } |
411 | 411 | ||
412 | /* temporarily set data to null to allow node to bubble up to the top. */ | 412 | /* temporarily set data to null to allow node to bubble up to the top. */ |
413 | target->data = BINHEAP_POISON; | 413 | target->data = BINHEAP_POISON; |
414 | 414 | ||
415 | __binheap_bubble_up(handle, target); | 415 | __binheap_bubble_up(handle, target); |
416 | __binheap_delete_root(handle, node_to_delete); | 416 | __binheap_delete_root(handle, node_to_delete); |
417 | 417 | ||
418 | node_to_delete->data = temp_data; /* restore node data pointer */ | 418 | node_to_delete->data = temp_data; /* restore node data pointer */ |
419 | //node_to_delete->parent = BINHEAP_POISON; /* poison the node */ | 419 | //node_to_delete->parent = BINHEAP_POISON; /* poison the node */ |
420 | } | 420 | } |
@@ -426,18 +426,18 @@ void __binheap_decrease(struct binheap_node *orig_node, | |||
426 | struct binheap_handle *handle) | 426 | struct binheap_handle *handle) |
427 | { | 427 | { |
428 | struct binheap_node *target = orig_node->ref; | 428 | struct binheap_node *target = orig_node->ref; |
429 | 429 | ||
430 | // if(!binheap_is_in_heap(orig_node)) | 430 | // if(!binheap_is_in_heap(orig_node)) |
431 | // { | 431 | // { |
432 | // dump_node_data2(handle, orig_node); | 432 | // dump_node_data2(handle, orig_node); |
433 | // BUG(); | 433 | // BUG(); |
434 | // } | 434 | // } |
435 | // | 435 | // |
436 | // if(!binheap_is_in_heap(target)) | 436 | // if(!binheap_is_in_heap(target)) |
437 | // { | 437 | // { |
438 | // dump_node_data2(handle, target); | 438 | // dump_node_data2(handle, target); |
439 | // BUG(); | 439 | // BUG(); |
440 | // } | 440 | // } |
441 | // | 441 | // |
442 | __binheap_bubble_up(handle, target); | 442 | __binheap_bubble_up(handle, target); |
443 | } | 443 | } |