source: libcfa/src/concurrency/locks.hfa @ 797a193

ADTarm-ehast-experimentalenumforall-pointer-decayjacob/cs343-translationnew-ast-unique-exprpthread-emulationqualifiedEnum
Last change on this file since 797a193 was 797a193, checked in by caparsons <caparson@…>, 3 years ago

cleaned up locks code and added comments

  • Property mode set to 100644
File size: 6.0 KB
RevLine 
[f4e35326]1#pragma once
2
[848439f]3#include <stdbool.h>
4
5#include "bits/algorithm.hfa"
6#include "bits/locks.hfa"
[cad1df1]7#include "bits/sequence.hfa"
[848439f]8
9#include "invoke.h"
10
11#include "time_t.hfa"
12#include "time.hfa"
13#include <sys/time.h>
[eeb5023]14#include "alarm.hfa"
[848439f]15
16///////////////////////////////////////////////////////////////////
17//// is_blocking_lock
18///////////////////////////////////////////////////////////////////
19
20trait is_blocking_lock(dtype L | sized(L)) {
[797a193]21        void on_notify( L &, struct $thread * );                        // For synchronization locks to use when acquiring
22        void on_wait( L & );                                                            // For synchronization locks to use when releasing
23        size_t get_recursion_count( L & );                                      // to get recursion count for cond lock to reset after waking
24        void set_recursion_count( L &, size_t recursion );      // to set recursion count after getting signalled;
[848439f]25};
26
27///////////////////////////////////////////////////////////////////
28//// info_thread
29///////////////////////////////////////////////////////////////////
30
[797a193]31// the info thread is a wrapper around a thread used
32// to store extra data for use in the condition variable
[848439f]33forall(dtype L | is_blocking_lock(L)) {
34        struct info_thread {
[797a193]35                inline Seqable;                                 // used to put info_thread on a dl queue (aka sequence)
36                struct $thread * t;                             // waiting thread
37                uintptr_t info;                                 // shadow field
38                L * lock;                                               // lock that is passed to wait() (if one is passed)
[dff1fd1]39                bool signalled;                                 // true when signalled and false when timeout wakes thread
[848439f]40        };
41
42
43        void ?{}( info_thread(L) & this, $thread * t );
44        void ?{}( info_thread(L) & this, $thread * t, uintptr_t info );
45        void ^?{}( info_thread(L) & this );
[c131a02]46
[797a193]47        // for use by sequence
[c131a02]48        info_thread(L) *& Back( info_thread(L) * this );
49        info_thread(L) *& Next( info_thread(L) * this );
[848439f]50}
51
52///////////////////////////////////////////////////////////////////
53//// Blocking Locks
54///////////////////////////////////////////////////////////////////
[6a8882c]55
[848439f]56struct blocking_lock {
57        // Spin lock used for mutual exclusion
58        __spinlock_t lock;
59
60        // List of blocked threads
[c131a02]61        Sequence( $thread ) blocked_threads;
[848439f]62
63        // Count of current blocked threads
64        size_t wait_count;
65
66        // Flag if the lock allows multiple acquisition
67        bool multi_acquisition;
68
69        // Flag if lock can be released by non owner
70        bool strict_owner;
71
72        // Current thread owning the lock
73        struct $thread * owner;
74
75        // Number of recursion level
76        size_t recursion_count;
77};
78
[6a8882c]79struct single_acquisition_lock {
[848439f]80        inline blocking_lock;
81};
82
83struct owner_lock {
84        inline blocking_lock;
85};
86
[6a8882c]87struct multiple_acquisition_lock {
[848439f]88        inline blocking_lock;
89};
90
91void ?{}( blocking_lock & this, bool multi_acquisition, bool strict_owner );
92void ^?{}( blocking_lock & this );
93
[6a8882c]94void ?{}( single_acquisition_lock & this );
95void ^?{}( single_acquisition_lock & this );
[848439f]96
97void ?{}( owner_lock & this );
98void ^?{}( owner_lock & this );
99
[6a8882c]100void ?{}( multiple_acquisition_lock & this );
101void ^?{}( multiple_acquisition_lock & this );
[848439f]102
103void lock( blocking_lock & this );
104bool try_lock( blocking_lock & this );
105void unlock( blocking_lock & this );
[797a193]106void on_notify( blocking_lock & this, struct $thread * t );
107void on_wait( blocking_lock & this );
[848439f]108size_t wait_count( blocking_lock & this );
109void set_recursion_count( blocking_lock & this, size_t recursion );
110size_t get_recursion_count( blocking_lock & this );
111
[6a8882c]112void lock( single_acquisition_lock & this );
113void unlock( single_acquisition_lock & this );
[797a193]114void on_notify( single_acquisition_lock & this, struct $thread * t );
115void on_wait( single_acquisition_lock & this );
[6a8882c]116void set_recursion_count( single_acquisition_lock & this, size_t recursion );
117size_t get_recursion_count( single_acquisition_lock & this );
118
119void lock( owner_lock & this );
120void unlock( owner_lock & this );
[797a193]121void on_notify( owner_lock & this, struct $thread * t );
122void on_wait( owner_lock & this );
[6a8882c]123void set_recursion_count( owner_lock & this, size_t recursion );
124size_t get_recursion_count( owner_lock & this );
125
126void lock( multiple_acquisition_lock & this );
127void unlock( multiple_acquisition_lock & this );
[797a193]128void on_notify( multiple_acquisition_lock & this, struct $thread * t );
129void on_wait( multiple_acquisition_lock & this );
[6a8882c]130void set_recursion_count( multiple_acquisition_lock & this, size_t recursion );
131size_t get_recursion_count( multiple_acquisition_lock & this );
[848439f]132
133///////////////////////////////////////////////////////////////////
134//// Synchronization Locks
135///////////////////////////////////////////////////////////////////
136forall(dtype L | is_blocking_lock(L)) {
[eeb5023]137        struct condition_variable {
[848439f]138                // Spin lock used for mutual exclusion
139                __spinlock_t lock;
140
141                // List of blocked threads
[cad1df1]142                Sequence( info_thread(L) ) blocked_threads;
[848439f]143
144                // Count of current blocked threads
145                int count;
146        };
147
148        void ?{}( condition_variable(L) & this );
149        void ^?{}( condition_variable(L) & this );
150
[eeb5023]151        struct alarm_node_wrap {
152                alarm_node_t alarm_node;
[848439f]153
[eeb5023]154                condition_variable(L) * cond;
[848439f]155
[cad1df1]156                info_thread(L) * i;
[eeb5023]157        };
[848439f]158
[4aeaee5]159        void ?{}( alarm_node_wrap(L) & this, Time alarm, Duration period, Alarm_Callback callback );
[eeb5023]160        void ^?{}( alarm_node_wrap(L) & this );
[848439f]161
[eeb5023]162        void alarm_node_callback( alarm_node_wrap(L) & this );
[848439f]163
[eeb5023]164        void alarm_node_wrap_cast( alarm_node_t & a );
[848439f]165
[eeb5023]166        bool notify_one( condition_variable(L) & this );
167        bool notify_all( condition_variable(L) & this );
[848439f]168
[eeb5023]169        uintptr_t front( condition_variable(L) & this );
[848439f]170
[eeb5023]171        bool empty( condition_variable(L) & this );
172        int counter( condition_variable(L) & this );
[848439f]173
[eeb5023]174        void wait( condition_variable(L) & this );
175        void wait( condition_variable(L) & this, uintptr_t info );
[dff1fd1]176        bool wait( condition_variable(L) & this, Duration duration );
177        bool wait( condition_variable(L) & this, uintptr_t info, Duration duration );
178        bool wait( condition_variable(L) & this, Time time );
179        bool wait( condition_variable(L) & this, uintptr_t info, Time time );
[848439f]180
[eeb5023]181        void wait( condition_variable(L) & this, L & l );
182        void wait( condition_variable(L) & this, L & l, uintptr_t info );
[dff1fd1]183        bool wait( condition_variable(L) & this, L & l, Duration duration );
184        bool wait( condition_variable(L) & this, L & l, uintptr_t info, Duration duration );
185        bool wait( condition_variable(L) & this, L & l, Time time );
186        bool wait( condition_variable(L) & this, L & l, uintptr_t info, Time time );
[eeb5023]187}
Note: See TracBrowser for help on using the repository browser.