source: doc/theses/colby_parsons_MMAth/code/swap_queues.cfa @ b0fcd0e

Last change on this file since b0fcd0e was 6e1e2d0, checked in by caparsons <caparson@…>, 18 months ago

resolved merge conflicts

  • Property mode set to 100644
File size: 1.7 KB
Line 
1// sequential equivalent swap
2void swap( uint victim_idx, uint my_idx  ) {
3    // Step 0:
4    work_queue * my_queue = request_queues[my_idx];
5    work_queue * vic_queue = request_queues[victim_idx];
6    // Step 2:
7    request_queues[my_idx] = 0p;
8    // Step 3:
9    request_queues[victim_idx] = my_queue;
10    // Step 4:
11    request_queues[my_idx] = vic_queue;
12}
13
14// This routine is atomic
15bool CAS( work_queue ** ptr, work_queue ** old, work_queue * new ) {
16    if ( *ptr != *old )
17        return false;
18    *ptr = new;
19    return true;
20}
21
22bool try_swap_queues( worker & this, uint victim_idx, uint my_idx ) with(this) {
23    // Step 0:
24    // request_queues is the shared array of all sharded queues
25    work_queue * my_queue = request_queues[my_idx];
26    work_queue * vic_queue = request_queues[victim_idx];
27
28    // Step 1:
29    // If either queue is 0p then they are in the process of being stolen
30    // 0p is CForAll's equivalent of C++'s nullptr
31    if ( vic_queue == 0p ) return false;
32
33    // Step 2:
34    // Try to set thief's queue ptr to be 0p.
35    // If this CAS fails someone stole thief's queue so return false
36    if ( !CAS( &request_queues[my_idx], &my_queue, 0p ) )
37        return false;
38   
39    // Step 3:
40    // Try to set victim queue ptr to be thief's queue ptr.
41    // If it fails someone stole the other queue, so fix up then return false
42    if ( !CAS( &request_queues[victim_idx], &vic_queue, my_queue ) ) {
43        request_queues[my_idx] = my_queue; // reset queue ptr back to prev val
44        return false;
45    }
46
47    // Step 4:
48    // Successfully swapped.
49    // Thief's ptr is 0p so no one will touch it
50    // Write back without CAS is safe
51    request_queues[my_idx] = vic_queue;
52    return true;
53}
Note: See TracBrowser for help on using the repository browser.