@salang/sa 0.1.2 → 0.1.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/bin/sa.js +19 -1
- package/package.json +8 -7
- package/sa_std/alloc/layout.sal +12 -0
- package/sa_std/alloc/prelude.sa +1 -0
- package/sa_std/alloc/prelude.sal +1 -0
- package/sa_std/alloc/string.sa +3 -0
- package/sa_std/alloc/vec.sa +684 -0
- package/sa_std/alloc/vec.sal +4 -0
- package/sa_std/any.sa +130 -0
- package/sa_std/any.sal +23 -0
- package/sa_std/array.sa +1876 -0
- package/sa_std/ascii.sa +2 -0
- package/sa_std/ascii.sal +1 -0
- package/sa_std/async.sla +116 -0
- package/sa_std/binary_heap.sa +3003 -0
- package/sa_std/binary_heap.sal +7 -0
- package/sa_std/borrow.sa +171 -0
- package/sa_std/borrow.sal +13 -0
- package/sa_std/btree_map.sa +2210 -0
- package/sa_std/btree_map.sal +11 -0
- package/sa_std/btree_set.sa +1072 -0
- package/sa_std/btree_set.sal +6 -0
- package/sa_std/char.sa +1309 -0
- package/sa_std/char.sal +50 -0
- package/sa_std/cmp.sa +554 -0
- package/sa_std/cmp.sal +14 -0
- package/sa_std/collections/binary_heap.sa +1 -0
- package/sa_std/collections/btree_map.sa +1 -0
- package/sa_std/collections/btree_set.sa +1 -0
- package/sa_std/collections/hashmap.sa +1 -0
- package/sa_std/collections/hashset.sa +1 -0
- package/sa_std/collections/linked_list.sa +1120 -0
- package/sa_std/collections/linked_list.sal +10 -0
- package/sa_std/collections/prelude.sa +7 -0
- package/sa_std/collections/prelude.sal +1 -0
- package/sa_std/collections/vec_deque.sa +1 -0
- package/sa_std/collections.sal +13 -0
- package/sa_std/convert.sa +1115 -0
- package/sa_std/convert.sal +24 -0
- package/sa_std/core/arc.sa +233 -0
- package/sa_std/core/arc.sal +4 -0
- package/sa_std/core/ascii.sa +784 -0
- package/sa_std/core/ascii.sal +34 -0
- package/sa_std/core/bit.sa +41 -0
- package/sa_std/core/box.sa +1 -0
- package/sa_std/core/box.sal +2 -0
- package/sa_std/core/cell.sa +108 -0
- package/sa_std/core/cell.sal +5 -0
- package/sa_std/core/cleanup.sa +26 -0
- package/sa_std/core/control.sa +20 -0
- package/sa_std/core/derive.sa +60 -0
- package/sa_std/core/derive.sal +1 -0
- package/sa_std/core/dispatch.sa +7 -0
- package/sa_std/core/dispatch.sal +5 -0
- package/sa_std/core/future.sa +777 -0
- package/sa_std/core/future.sal +73 -0
- package/sa_std/core/hash.sa +48 -0
- package/sa_std/core/iter.sa +2805 -0
- package/sa_std/core/iter.sal +4 -0
- package/sa_std/core/loop.sa +60 -0
- package/sa_std/core/mem.sa +220 -0
- package/sa_std/core/option.sa +825 -0
- package/sa_std/core/option.sal +11 -0
- package/sa_std/core/panic.sa +23 -0
- package/sa_std/core/panic.sal +12 -0
- package/sa_std/core/prelude.sa +18 -0
- package/sa_std/core/prelude.sal +18 -0
- package/sa_std/core/rc.sa +225 -0
- package/sa_std/core/rc.sal +4 -0
- package/sa_std/core/refcell.sa +283 -0
- package/sa_std/core/refcell.sal +13 -0
- package/sa_std/core/result.sa +708 -0
- package/sa_std/core/result.sal +6 -0
- package/sa_std/core/rust_patterns.sal +295 -0
- package/sa_std/core/sa_core.sa +84 -0
- package/sa_std/core/slice.sa +4021 -0
- package/sa_std/core/slice.sal +7 -0
- package/sa_std/core/task.sa +112 -0
- package/sa_std/core/task.sal +15 -0
- package/sa_std/core/trait_object.sa +26 -0
- package/sa_std/core/trait_object.sal +4 -0
- package/sa_std/core/waker.sa +289 -0
- package/sa_std/core/waker.sal +31 -0
- package/sa_std/core/weak.sa +2 -0
- package/sa_std/core/weak.sal +4 -0
- package/sa_std/cow.sa +3 -0
- package/sa_std/cow.sal +2 -0
- package/sa_std/cstring.sa +3 -0
- package/sa_std/cstring.sal +2 -0
- package/sa_std/default.sa +99 -0
- package/sa_std/duration.sa +3 -0
- package/sa_std/duration.sal +2 -0
- package/sa_std/encoding/json.sa +259 -0
- package/sa_std/encoding/json.sai +54 -0
- package/sa_std/encoding/json.sal +35 -0
- package/sa_std/encoding/prelude.sa +1 -0
- package/sa_std/encoding/prelude.sal +0 -0
- package/sa_std/env.sa +390 -0
- package/sa_std/env.sai +25 -0
- package/sa_std/error.sa +253 -0
- package/sa_std/error.sal +44 -0
- package/sa_std/ffi/cstring.sa +3 -0
- package/sa_std/ffi/cstring.sal +1 -0
- package/sa_std/ffi/prelude.sa +2 -0
- package/sa_std/ffi/prelude.sal +2 -0
- package/sa_std/ffi.sa +635 -0
- package/sa_std/ffi.sal +51 -0
- package/sa_std/fmt.sa +2 -0
- package/sa_std/fmt.sai +18 -0
- package/sa_std/fmt.sal +35 -0
- package/sa_std/fs.sa +1023 -0
- package/sa_std/fs.sai +127 -0
- package/sa_std/fs.sal +51 -0
- package/sa_std/future.sa +2 -0
- package/sa_std/future.sal +1 -0
- package/sa_std/hash.sa +1486 -0
- package/sa_std/hash.sal +13 -0
- package/sa_std/hashmap.sa +1962 -0
- package/sa_std/hashmap.sal +20 -0
- package/sa_std/hashset.sa +1004 -0
- package/sa_std/hashset.sal +18 -0
- package/sa_std/http2.sa +78 -0
- package/sa_std/http2.sai +26 -0
- package/sa_std/http2.sal +36 -0
- package/sa_std/instant.sa +3 -0
- package/sa_std/instant.sal +2 -0
- package/sa_std/io/buf_reader.sa +43 -0
- package/sa_std/io/buf_writer.sa +35 -0
- package/sa_std/io/bufio.sa +4 -0
- package/sa_std/io/bufio.sal +4 -0
- package/sa_std/io/prelude.sa +1 -0
- package/sa_std/io/prelude.sal +1 -0
- package/sa_std/io/print.sa +2 -0
- package/sa_std/io/print.sai +3 -0
- package/sa_std/io.sa +925 -0
- package/sa_std/io.sai +25 -0
- package/sa_std/io.sal +84 -0
- package/sa_std/iter.sa +2 -0
- package/sa_std/iter.sal +1 -0
- package/sa_std/join_handle.sa +3 -0
- package/sa_std/join_handle.sal +2 -0
- package/sa_std/libsa_async.sa +80 -0
- package/sa_std/m_async.sa +137 -0
- package/sa_std/m_async.sal +30 -0
- package/sa_std/m_async.sla +2 -0
- package/sa_std/manually_drop.sa +3 -0
- package/sa_std/manually_drop.sal +2 -0
- package/sa_std/marker/phantom_data.sa +3 -0
- package/sa_std/marker/phantom_data.sal +1 -0
- package/sa_std/marker/prelude.sa +4 -0
- package/sa_std/marker/prelude.sal +4 -0
- package/sa_std/marker.sa +220 -0
- package/sa_std/marker.sal +15 -0
- package/sa_std/math.sa +84 -0
- package/sa_std/math.sai +10 -0
- package/sa_std/mem/manually_drop.sa +3 -0
- package/sa_std/mem/manually_drop.sal +1 -0
- package/sa_std/mem/prelude.sa +2 -0
- package/sa_std/mem/prelude.sal +2 -0
- package/sa_std/mem.sa +564 -0
- package/sa_std/mem.sal +40 -0
- package/sa_std/modstate.sai +19 -0
- package/sa_std/net.sa +4227 -0
- package/sa_std/net.sai +239 -0
- package/sa_std/net.sal +159 -0
- package/sa_std/netx.sa +85 -0
- package/sa_std/netx.sai +11 -0
- package/sa_std/netx.sal +39 -0
- package/sa_std/nonzero.sa +3 -0
- package/sa_std/nonzero.sal +2 -0
- package/sa_std/num/nonzero.sa +3 -0
- package/sa_std/num/nonzero.sal +1 -0
- package/sa_std/num/prelude.sa +3 -0
- package/sa_std/num/prelude.sal +3 -0
- package/sa_std/num.sa +17302 -0
- package/sa_std/num.sai +11 -0
- package/sa_std/num.sal +341 -0
- package/sa_std/ops.sa +1884 -0
- package/sa_std/ops.sal +68 -0
- package/sa_std/option.sa +2 -0
- package/sa_std/option.sal +1 -0
- package/sa_std/os/fd.sa +96 -0
- package/sa_std/os/fd.sai +7 -0
- package/sa_std/os/fd.sal +11 -0
- package/sa_std/os/prelude.sa +2 -0
- package/sa_std/os/prelude.sal +1 -0
- package/sa_std/os/unix_ffi.sa +271 -0
- package/sa_std/panic.sa +1 -0
- package/sa_std/panic.sal +1 -0
- package/sa_std/path.sa +3170 -0
- package/sa_std/path.sal +12 -0
- package/sa_std/phantom_data.sa +3 -0
- package/sa_std/phantom_data.sal +2 -0
- package/sa_std/pin.sa +79 -0
- package/sa_std/pin.sal +5 -0
- package/sa_std/plugin_async.sa +90 -0
- package/sa_std/plugin_async.sal +29 -0
- package/sa_std/plugin_async.sla +4 -0
- package/sa_std/plugin_http_async.sa +46 -0
- package/sa_std/plugin_http_server.sa +61 -0
- package/sa_std/plugin_http_server.sla +2 -0
- package/sa_std/plugin_sqlite.sa +106 -0
- package/sa_std/plugin_sqlite.sla +2 -0
- package/sa_std/prelude.sa +60 -0
- package/sa_std/prelude.sal +55 -0
- package/sa_std/process.sa +916 -0
- package/sa_std/process.sai +57 -0
- package/sa_std/process.sal +27 -0
- package/sa_std/ptr.sa +503 -0
- package/sa_std/ptr.sal +2 -0
- package/sa_std/result.sa +2 -0
- package/sa_std/result.sal +1 -0
- package/sa_std/rust_core.sa +51 -0
- package/sa_std/rust_core.sal +26 -0
- package/sa_std/sa.mod +7 -0
- package/sa_std/sort.sa +156 -0
- package/sa_std/str.sla +13 -0
- package/sa_std/string.sa +12240 -0
- package/sa_std/string.sai +25 -0
- package/sa_std/string.sal +17 -0
- package/sa_std/string_format.sa +269 -0
- package/sa_std/sync/atomic.sa +1500 -0
- package/sa_std/sync/atomic.sal +45 -0
- package/sa_std/sync/barrier.sa +105 -0
- package/sa_std/sync/barrier.sal +7 -0
- package/sa_std/sync/condvar.sa +240 -0
- package/sa_std/sync/condvar.sal +4 -0
- package/sa_std/sync/mpsc.sa +758 -0
- package/sa_std/sync/mpsc.sal +42 -0
- package/sa_std/sync/mpsc_list.sa +255 -0
- package/sa_std/sync/mpsc_list.sal +3 -0
- package/sa_std/sync/mutex.sa +182 -0
- package/sa_std/sync/mutex.sal +7 -0
- package/sa_std/sync/once.sa +371 -0
- package/sa_std/sync/once.sal +31 -0
- package/sa_std/sync/poison.sa +36 -0
- package/sa_std/sync/poison.sal +11 -0
- package/sa_std/sync/prelude.sa +8 -0
- package/sa_std/sync/prelude.sal +7 -0
- package/sa_std/sync/rwlock.sa +369 -0
- package/sa_std/sync/rwlock.sal +13 -0
- package/sa_std/task.sa +2 -0
- package/sa_std/task.sal +1 -0
- package/sa_std/term.sa +2 -0
- package/sa_std/term.sai +10 -0
- package/sa_std/term.sal +33 -0
- package/sa_std/testing/assert.sai +4 -0
- package/sa_std/testing/mock_io.sa +174 -0
- package/sa_std/testing/mock_io.sal +5 -0
- package/sa_std/testing/prelude.sa +2 -0
- package/sa_std/testing/prelude.sal +1 -0
- package/sa_std/text/prelude.sa +1 -0
- package/sa_std/text/prelude.sal +1 -0
- package/sa_std/text/regex.sa +2 -0
- package/sa_std/text/regex.sai +9 -0
- package/sa_std/text/regex.sal +33 -0
- package/sa_std/thread/join_handle.sa +3 -0
- package/sa_std/thread/join_handle.sal +1 -0
- package/sa_std/thread/prelude.sa +4 -0
- package/sa_std/thread/prelude.sal +3 -0
- package/sa_std/thread.sa +160 -0
- package/sa_std/thread.sai +11 -0
- package/sa_std/thread.sal +4 -0
- package/sa_std/thread_local.sa +45 -0
- package/sa_std/thread_local.sai +9 -0
- package/sa_std/time/duration.sa +3 -0
- package/sa_std/time/duration.sal +1 -0
- package/sa_std/time/instant.sa +3 -0
- package/sa_std/time/instant.sal +1 -0
- package/sa_std/time/prelude.sa +4 -0
- package/sa_std/time/prelude.sal +4 -0
- package/sa_std/time.sa +850 -0
- package/sa_std/time.sai +37 -0
- package/sa_std/time.sal +35 -0
- package/sa_std/time.sla +67 -0
- package/sa_std/tls_client.sai +39 -0
- package/sa_std/vec.sa +5754 -0
- package/sa_std/vec.sal +1 -0
- package/sa_std/vec_deque.sa +4925 -0
- package/sa_std/vec_deque.sal +8 -0
- package/sa_std/vec_runtime_macros.sa +11 -0
- package/sa_std/ws_client.sai +57 -0
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
#def Mpsc_SIZE = 32
|
|
2
|
+
#def Mpsc_cap = +0
|
|
3
|
+
#def Mpsc_head = +8
|
|
4
|
+
#def Mpsc_tail = +16
|
|
5
|
+
#def Mpsc_data = +32
|
|
6
|
+
|
|
7
|
+
#def Mpsc_SLOT_SIZE = 16
|
|
8
|
+
#def Mpsc_SLOT_value = +0
|
|
9
|
+
#def Mpsc_SLOT_ready = +8
|
|
10
|
+
#def Mpsc_SLOT_EMPTY = 0
|
|
11
|
+
#def Mpsc_SLOT_READY = 1
|
|
12
|
+
|
|
13
|
+
#def SendErrorU64_SIZE = 8
|
|
14
|
+
#def SendErrorU64_ALIGN = 8
|
|
15
|
+
#def SendErrorU64_value = +0
|
|
16
|
+
|
|
17
|
+
#def RecvError_SIZE = 0
|
|
18
|
+
#def RecvError_ALIGN = 1
|
|
19
|
+
|
|
20
|
+
#def TryRecvError_SIZE = 8
|
|
21
|
+
#def TryRecvError_ALIGN = 8
|
|
22
|
+
#def TryRecvError_kind = +0
|
|
23
|
+
#def TRY_RECV_ERROR_EMPTY = 0
|
|
24
|
+
#def TRY_RECV_ERROR_DISCONNECTED = 1
|
|
25
|
+
|
|
26
|
+
#def RecvTimeoutError_SIZE = 8
|
|
27
|
+
#def RecvTimeoutError_ALIGN = 8
|
|
28
|
+
#def RecvTimeoutError_kind = +0
|
|
29
|
+
#def RECV_TIMEOUT_ERROR_TIMEOUT = 0
|
|
30
|
+
#def RECV_TIMEOUT_ERROR_DISCONNECTED = 1
|
|
31
|
+
|
|
32
|
+
#def TrySendErrorU64_SIZE = 16
|
|
33
|
+
#def TrySendErrorU64_ALIGN = 8
|
|
34
|
+
#def TrySendErrorU64_kind = +0
|
|
35
|
+
#def TrySendErrorU64_value = +8
|
|
36
|
+
#def TRY_SEND_ERROR_FULL = 0
|
|
37
|
+
#def TRY_SEND_ERROR_DISCONNECTED = 1
|
|
38
|
+
|
|
39
|
+
#def MpscSender_SIZE = 8
|
|
40
|
+
#def MpscSender_chan = +0
|
|
41
|
+
#def MpscReceiver_SIZE = 8
|
|
42
|
+
#def MpscReceiver_chan = +0
|
|
@@ -0,0 +1,255 @@
|
|
|
1
|
+
// Unbounded channel backed by LinkedList + Mutex (single-producer multi not optimized).
|
|
2
|
+
// Models supportable unbounded mpsc semantics without growable ring complexity.
|
|
3
|
+
@import "mpsc_list.sal"
|
|
4
|
+
@import "mutex.sa"
|
|
5
|
+
@import "../collections/linked_list.sa"
|
|
6
|
+
@import "mpsc.sal"
|
|
7
|
+
@import "../time.sai"
|
|
8
|
+
|
|
9
|
+
@sa_mpsc_list_new() -> ^ptr:
|
|
10
|
+
L_ENTRY:
|
|
11
|
+
chan = alloc MpscList_SIZE
|
|
12
|
+
EXPAND MUTEX_NEW mtx
|
|
13
|
+
EXPAND LINKED_LIST_NEW list
|
|
14
|
+
store chan+MpscList_mutex, mtx as ptr
|
|
15
|
+
store chan+MpscList_list, list as ptr
|
|
16
|
+
return chan
|
|
17
|
+
|
|
18
|
+
@sa_mpsc_list_send(&chan: ptr, value: u64) -> void:
|
|
19
|
+
L_ENTRY:
|
|
20
|
+
mtx = load chan+MpscList_mutex as ptr
|
|
21
|
+
list = load chan+MpscList_list as ptr
|
|
22
|
+
null_ptr = 0 as ptr
|
|
23
|
+
disconnected = eq mtx, null_ptr
|
|
24
|
+
br disconnected -> L_SEND_DISCONNECTED, L_SEND_LOCK
|
|
25
|
+
L_SEND_LOCK:
|
|
26
|
+
EXPAND MUTEX_LOCK mtx
|
|
27
|
+
EXPAND LINKED_LIST_PUSH_BACK list, value
|
|
28
|
+
EXPAND MUTEX_UNLOCK mtx
|
|
29
|
+
!disconnected
|
|
30
|
+
!null_ptr
|
|
31
|
+
!list
|
|
32
|
+
!mtx
|
|
33
|
+
!value
|
|
34
|
+
return
|
|
35
|
+
L_SEND_DISCONNECTED:
|
|
36
|
+
!disconnected
|
|
37
|
+
!null_ptr
|
|
38
|
+
!list
|
|
39
|
+
!mtx
|
|
40
|
+
!value
|
|
41
|
+
return
|
|
42
|
+
|
|
43
|
+
@sa_mpsc_list_try_recv(&chan: ptr, &out_value: ptr) -> i32:
|
|
44
|
+
L_ENTRY:
|
|
45
|
+
mtx = load chan+MpscList_mutex as ptr
|
|
46
|
+
list = load chan+MpscList_list as ptr
|
|
47
|
+
null_ptr = 0 as ptr
|
|
48
|
+
disconnected = eq mtx, null_ptr
|
|
49
|
+
br disconnected -> L_RECV_DISCONNECTED, L_RECV_LOCK
|
|
50
|
+
L_RECV_LOCK:
|
|
51
|
+
EXPAND MUTEX_LOCK mtx
|
|
52
|
+
ok = call @sa_linked_list_try_pop_front(&list, &out_value)
|
|
53
|
+
EXPAND MUTEX_UNLOCK mtx
|
|
54
|
+
!disconnected
|
|
55
|
+
!null_ptr
|
|
56
|
+
!list
|
|
57
|
+
!mtx
|
|
58
|
+
!chan
|
|
59
|
+
!out_value
|
|
60
|
+
return ok
|
|
61
|
+
L_RECV_DISCONNECTED:
|
|
62
|
+
store out_value+0, 0 as u64
|
|
63
|
+
!disconnected
|
|
64
|
+
!null_ptr
|
|
65
|
+
!list
|
|
66
|
+
!mtx
|
|
67
|
+
!chan
|
|
68
|
+
!out_value
|
|
69
|
+
return 0
|
|
70
|
+
|
|
71
|
+
@sa_mpsc_list_free(&chan: ptr) -> void:
|
|
72
|
+
L_ENTRY:
|
|
73
|
+
list = load chan+MpscList_list as ptr
|
|
74
|
+
mtx = load chan+MpscList_mutex as ptr
|
|
75
|
+
null_ptr = 0 as ptr
|
|
76
|
+
closed = eq mtx, null_ptr
|
|
77
|
+
br closed -> L_FREE_ALREADY, L_FREE_CLOSE
|
|
78
|
+
L_FREE_ALREADY:
|
|
79
|
+
!mtx
|
|
80
|
+
!closed
|
|
81
|
+
!null_ptr
|
|
82
|
+
jmp L_FREE_DONE
|
|
83
|
+
L_FREE_CLOSE:
|
|
84
|
+
EXPAND LINKED_LIST_FREE list
|
|
85
|
+
EXPAND MUTEX_FREE mtx
|
|
86
|
+
store chan+MpscList_list, null_ptr as ptr
|
|
87
|
+
store chan+MpscList_mutex, null_ptr as ptr
|
|
88
|
+
!closed
|
|
89
|
+
!null_ptr
|
|
90
|
+
jmp L_FREE_DONE
|
|
91
|
+
L_FREE_DONE:
|
|
92
|
+
!chan
|
|
93
|
+
return
|
|
94
|
+
@sa_mpsc_list_try_recv_timeout(&chan: ptr, &out_value: ptr, timeout_ns: u64) -> i32:
|
|
95
|
+
L_ENTRY:
|
|
96
|
+
start = call @sa_time_instant_ns()
|
|
97
|
+
backoff_slot = stack_alloc 8
|
|
98
|
+
store backoff_slot+0, 1 as u64
|
|
99
|
+
L_TRY:
|
|
100
|
+
ok = call @sa_mpsc_list_try_recv(&chan, &out_value)
|
|
101
|
+
br ok -> L_OK, L_CHECK
|
|
102
|
+
L_OK:
|
|
103
|
+
!ok
|
|
104
|
+
!start
|
|
105
|
+
!timeout_ns
|
|
106
|
+
!chan
|
|
107
|
+
!out_value
|
|
108
|
+
return 1
|
|
109
|
+
L_CHECK:
|
|
110
|
+
now = call @sa_time_instant_ns()
|
|
111
|
+
elapsed = sub now, start
|
|
112
|
+
timed_out = uge elapsed, timeout_ns
|
|
113
|
+
br timed_out -> L_TIMEOUT, L_BACKOFF
|
|
114
|
+
L_BACKOFF:
|
|
115
|
+
backoff_ns = load backoff_slot+0 as u64
|
|
116
|
+
call @sa_time_sleep_ns(backoff_ns)
|
|
117
|
+
at_limit = uge backoff_ns, 1024
|
|
118
|
+
br at_limit -> L_KEEP, L_GROW
|
|
119
|
+
L_GROW:
|
|
120
|
+
next_backoff = shl backoff_ns, 1
|
|
121
|
+
store backoff_slot+0, next_backoff as u64
|
|
122
|
+
!next_backoff
|
|
123
|
+
!at_limit
|
|
124
|
+
!backoff_ns
|
|
125
|
+
!timed_out
|
|
126
|
+
!elapsed
|
|
127
|
+
!now
|
|
128
|
+
!ok
|
|
129
|
+
jmp L_TRY
|
|
130
|
+
L_KEEP:
|
|
131
|
+
!at_limit
|
|
132
|
+
!backoff_ns
|
|
133
|
+
!timed_out
|
|
134
|
+
!elapsed
|
|
135
|
+
!now
|
|
136
|
+
!ok
|
|
137
|
+
jmp L_TRY
|
|
138
|
+
L_TIMEOUT:
|
|
139
|
+
!timed_out
|
|
140
|
+
!elapsed
|
|
141
|
+
!now
|
|
142
|
+
!ok
|
|
143
|
+
!start
|
|
144
|
+
!timeout_ns
|
|
145
|
+
!chan
|
|
146
|
+
!out_value
|
|
147
|
+
return 0
|
|
148
|
+
|
|
149
|
+
[MACRO] MPSC_LIST_NEW %out_chan
|
|
150
|
+
%out_chan = call @sa_mpsc_list_new()
|
|
151
|
+
[END_MACRO]
|
|
152
|
+
|
|
153
|
+
[MACRO] MPSC_LIST_SEND %chan, %value
|
|
154
|
+
call @sa_mpsc_list_send(&%chan, %value)
|
|
155
|
+
[END_MACRO]
|
|
156
|
+
|
|
157
|
+
[MACRO] MPSC_LIST_TRY_RECV %out_ok, %out_value, %chan
|
|
158
|
+
__mpl_slot_%out_ok = stack_alloc 8
|
|
159
|
+
store __mpl_slot_%out_ok+0, 0 as u64
|
|
160
|
+
%out_ok = call @sa_mpsc_list_try_recv(&%chan, &__mpl_slot_%out_ok)
|
|
161
|
+
%out_value = load __mpl_slot_%out_ok+0 as u64
|
|
162
|
+
[END_MACRO]
|
|
163
|
+
|
|
164
|
+
[MACRO] MPSC_LIST_TRY_RECV_TIMEOUT_NS %out_ok, %out_value, %chan, %timeout_ns
|
|
165
|
+
__mpl_timeout_slot_%out_ok = stack_alloc 8
|
|
166
|
+
store __mpl_timeout_slot_%out_ok+0, 0 as u64
|
|
167
|
+
%out_ok = call @sa_mpsc_list_try_recv_timeout(&%chan, &__mpl_timeout_slot_%out_ok, %timeout_ns)
|
|
168
|
+
%out_value = load __mpl_timeout_slot_%out_ok+0 as u64
|
|
169
|
+
[END_MACRO]
|
|
170
|
+
|
|
171
|
+
[MACRO] MPSC_LIST_TRY_RECV_TIMEOUT_MS %out_ok, %out_value, %chan, %timeout_ms
|
|
172
|
+
EXPAND NUM_U64_CHECKED_MUL __mpl_timeout_mul_ok_%out_ok, __mpl_timeout_ns_%out_ok, %timeout_ms, 1000000
|
|
173
|
+
br __mpl_timeout_mul_ok_%out_ok -> L_MPSC_LIST_TIMEOUT_MS_OK_%out_ok, L_MPSC_LIST_TIMEOUT_MS_FAIL_%out_ok
|
|
174
|
+
L_MPSC_LIST_TIMEOUT_MS_OK_%out_ok:
|
|
175
|
+
EXPAND MPSC_LIST_TRY_RECV_TIMEOUT_NS %out_ok, %out_value, %chan, __mpl_timeout_ns_%out_ok
|
|
176
|
+
!__mpl_timeout_ns_%out_ok
|
|
177
|
+
!__mpl_timeout_mul_ok_%out_ok
|
|
178
|
+
jmp L_MPSC_LIST_TIMEOUT_MS_DONE_%out_ok
|
|
179
|
+
L_MPSC_LIST_TIMEOUT_MS_FAIL_%out_ok:
|
|
180
|
+
%out_ok = add 0, 0
|
|
181
|
+
%out_value = add 0, 0
|
|
182
|
+
!__mpl_timeout_ns_%out_ok
|
|
183
|
+
!__mpl_timeout_mul_ok_%out_ok
|
|
184
|
+
L_MPSC_LIST_TIMEOUT_MS_DONE_%out_ok:
|
|
185
|
+
[END_MACRO]
|
|
186
|
+
|
|
187
|
+
[MACRO] MPSC_LIST_FREE %chan
|
|
188
|
+
call @sa_mpsc_list_free(&%chan)
|
|
189
|
+
[END_MACRO]
|
|
190
|
+
|
|
191
|
+
[MACRO] MPSC_LIST_DROP %chan
|
|
192
|
+
EXPAND MPSC_LIST_FREE %chan
|
|
193
|
+
[END_MACRO]
|
|
194
|
+
|
|
195
|
+
[MACRO] MPSC_LIST_IS_DISCONNECTED %out_bool, %chan
|
|
196
|
+
__mpl_disc_mtx_%out_bool = load %chan+MpscList_mutex as ptr
|
|
197
|
+
__mpl_disc_list_%out_bool = load %chan+MpscList_list as ptr
|
|
198
|
+
__mpl_disc_null_%out_bool = 0 as ptr
|
|
199
|
+
__mpl_disc_mtx_zero_%out_bool = eq __mpl_disc_mtx_%out_bool, __mpl_disc_null_%out_bool
|
|
200
|
+
__mpl_disc_list_zero_%out_bool = eq __mpl_disc_list_%out_bool, __mpl_disc_null_%out_bool
|
|
201
|
+
%out_bool = and __mpl_disc_mtx_zero_%out_bool, __mpl_disc_list_zero_%out_bool
|
|
202
|
+
!__mpl_disc_list_zero_%out_bool
|
|
203
|
+
!__mpl_disc_mtx_zero_%out_bool
|
|
204
|
+
!__mpl_disc_null_%out_bool
|
|
205
|
+
!__mpl_disc_list_%out_bool
|
|
206
|
+
!__mpl_disc_mtx_%out_bool
|
|
207
|
+
[END_MACRO]
|
|
208
|
+
|
|
209
|
+
[MACRO] MPSC_LIST_LEN %out_len, %chan
|
|
210
|
+
__mpl_len_mtx_%out_len = load %chan+MpscList_mutex as ptr
|
|
211
|
+
__mpl_list_%out_len = load %chan+MpscList_list as ptr
|
|
212
|
+
__mpl_len_null_%out_len = 0 as ptr
|
|
213
|
+
__mpl_len_disconnected_%out_len = eq __mpl_len_mtx_%out_len, __mpl_len_null_%out_len
|
|
214
|
+
br __mpl_len_disconnected_%out_len -> L_MPSC_LIST_LEN_DISCONNECTED_%out_len, L_MPSC_LIST_LEN_LOCK_%out_len
|
|
215
|
+
L_MPSC_LIST_LEN_LOCK_%out_len:
|
|
216
|
+
EXPAND MUTEX_LOCK __mpl_len_mtx_%out_len
|
|
217
|
+
EXPAND LINKED_LIST_LEN %out_len, __mpl_list_%out_len
|
|
218
|
+
EXPAND MUTEX_UNLOCK __mpl_len_mtx_%out_len
|
|
219
|
+
!__mpl_len_disconnected_%out_len
|
|
220
|
+
!__mpl_len_null_%out_len
|
|
221
|
+
!__mpl_list_%out_len
|
|
222
|
+
!__mpl_len_mtx_%out_len
|
|
223
|
+
jmp L_MPSC_LIST_LEN_DONE_%out_len
|
|
224
|
+
L_MPSC_LIST_LEN_DISCONNECTED_%out_len:
|
|
225
|
+
%out_len = add 0, 0
|
|
226
|
+
!__mpl_len_disconnected_%out_len
|
|
227
|
+
!__mpl_len_null_%out_len
|
|
228
|
+
!__mpl_list_%out_len
|
|
229
|
+
!__mpl_len_mtx_%out_len
|
|
230
|
+
L_MPSC_LIST_LEN_DONE_%out_len:
|
|
231
|
+
[END_MACRO]
|
|
232
|
+
|
|
233
|
+
[MACRO] MPSC_LIST_IS_EMPTY %out_bool, %chan
|
|
234
|
+
__mpl_empty_mtx_%out_bool = load %chan+MpscList_mutex as ptr
|
|
235
|
+
__mpl_list_e_%out_bool = load %chan+MpscList_list as ptr
|
|
236
|
+
__mpl_empty_null_%out_bool = 0 as ptr
|
|
237
|
+
__mpl_empty_disconnected_%out_bool = eq __mpl_empty_mtx_%out_bool, __mpl_empty_null_%out_bool
|
|
238
|
+
br __mpl_empty_disconnected_%out_bool -> L_MPSC_LIST_EMPTY_DISCONNECTED_%out_bool, L_MPSC_LIST_EMPTY_LOCK_%out_bool
|
|
239
|
+
L_MPSC_LIST_EMPTY_LOCK_%out_bool:
|
|
240
|
+
EXPAND MUTEX_LOCK __mpl_empty_mtx_%out_bool
|
|
241
|
+
EXPAND LINKED_LIST_IS_EMPTY %out_bool, __mpl_list_e_%out_bool
|
|
242
|
+
EXPAND MUTEX_UNLOCK __mpl_empty_mtx_%out_bool
|
|
243
|
+
!__mpl_empty_disconnected_%out_bool
|
|
244
|
+
!__mpl_empty_null_%out_bool
|
|
245
|
+
!__mpl_list_e_%out_bool
|
|
246
|
+
!__mpl_empty_mtx_%out_bool
|
|
247
|
+
jmp L_MPSC_LIST_EMPTY_DONE_%out_bool
|
|
248
|
+
L_MPSC_LIST_EMPTY_DISCONNECTED_%out_bool:
|
|
249
|
+
%out_bool = add 0, 1
|
|
250
|
+
!__mpl_empty_disconnected_%out_bool
|
|
251
|
+
!__mpl_empty_null_%out_bool
|
|
252
|
+
!__mpl_list_e_%out_bool
|
|
253
|
+
!__mpl_empty_mtx_%out_bool
|
|
254
|
+
L_MPSC_LIST_EMPTY_DONE_%out_bool:
|
|
255
|
+
[END_MACRO]
|
|
@@ -0,0 +1,182 @@
|
|
|
1
|
+
// Concrete mutex/spinlock macros built on atomic xchg and release unlock.
|
|
2
|
+
@import "mutex.sal"
|
|
3
|
+
@import "../time.sa"
|
|
4
|
+
@import "../time.sai"
|
|
5
|
+
|
|
6
|
+
@__mutex_lock_spin(lock: ptr) -> void:
|
|
7
|
+
L_MUTEX_LOCK_INIT:
|
|
8
|
+
backoff_slot = stack_alloc 8
|
|
9
|
+
store backoff_slot+0, 1 as u64
|
|
10
|
+
|
|
11
|
+
L_MUTEX_LOCK_TRY:
|
|
12
|
+
prev = atomic_rmw_xchg lock+Mutex_lock, 1 as u64 acq_rel
|
|
13
|
+
free = eq prev, 0
|
|
14
|
+
br free -> L_MUTEX_LOCK_DONE, L_MUTEX_LOCK_WAIT
|
|
15
|
+
|
|
16
|
+
L_MUTEX_LOCK_WAIT:
|
|
17
|
+
backoff_ns = load backoff_slot+0 as u64
|
|
18
|
+
call @sa_time_sleep_ns(backoff_ns)
|
|
19
|
+
backoff_at_limit = uge backoff_ns, 1024
|
|
20
|
+
br backoff_at_limit -> L_MUTEX_LOCK_KEEP_BACKOFF, L_MUTEX_LOCK_GROW_BACKOFF
|
|
21
|
+
|
|
22
|
+
L_MUTEX_LOCK_GROW_BACKOFF:
|
|
23
|
+
next_backoff = shl backoff_ns, 1
|
|
24
|
+
store backoff_slot+0, next_backoff as u64
|
|
25
|
+
!next_backoff
|
|
26
|
+
!backoff_at_limit
|
|
27
|
+
!backoff_ns
|
|
28
|
+
!free
|
|
29
|
+
!prev
|
|
30
|
+
jmp L_MUTEX_LOCK_TRY
|
|
31
|
+
|
|
32
|
+
L_MUTEX_LOCK_KEEP_BACKOFF:
|
|
33
|
+
!backoff_at_limit
|
|
34
|
+
!backoff_ns
|
|
35
|
+
!free
|
|
36
|
+
!prev
|
|
37
|
+
jmp L_MUTEX_LOCK_TRY
|
|
38
|
+
|
|
39
|
+
L_MUTEX_LOCK_DONE:
|
|
40
|
+
!free
|
|
41
|
+
!prev
|
|
42
|
+
return
|
|
43
|
+
|
|
44
|
+
[MACRO] MUTEX_NEW %out_mutex
|
|
45
|
+
%out_mutex = alloc Mutex_SIZE
|
|
46
|
+
store %out_mutex+Mutex_lock, 0 as u64
|
|
47
|
+
[END_MACRO]
|
|
48
|
+
|
|
49
|
+
[MACRO] MUTEX_NEW_I32 %out_mutex, %value
|
|
50
|
+
%out_mutex = alloc 16
|
|
51
|
+
store %out_mutex+Mutex_lock, 0 as u64
|
|
52
|
+
store %out_mutex+Mutex_data, %value as i32
|
|
53
|
+
[END_MACRO]
|
|
54
|
+
|
|
55
|
+
[MACRO] MUTEX_LOCK %lock_ptr
|
|
56
|
+
call @__mutex_lock_spin(%lock_ptr)
|
|
57
|
+
[END_MACRO]
|
|
58
|
+
|
|
59
|
+
[MACRO] MUTEX_TRY_LOCK %out_ok, %lock_ptr
|
|
60
|
+
__mutex_try_prev_%out_ok = atomic_rmw_xchg %lock_ptr+Mutex_lock, 1 as u64 acq_rel
|
|
61
|
+
%out_ok = eq __mutex_try_prev_%out_ok, 0
|
|
62
|
+
!__mutex_try_prev_%out_ok
|
|
63
|
+
[END_MACRO]
|
|
64
|
+
|
|
65
|
+
[MACRO] MUTEX_IS_LOCKED %out_bool, %lock_ptr
|
|
66
|
+
__mutex_state_%out_bool = atomic_load %lock_ptr+Mutex_lock as u64 acquire
|
|
67
|
+
%out_bool = ne __mutex_state_%out_bool, 0
|
|
68
|
+
!__mutex_state_%out_bool
|
|
69
|
+
[END_MACRO]
|
|
70
|
+
|
|
71
|
+
[MACRO] MUTEX_UNLOCK %lock_ptr
|
|
72
|
+
atomic_store %lock_ptr+Mutex_lock, 0 as u64 release
|
|
73
|
+
[END_MACRO]
|
|
74
|
+
|
|
75
|
+
[MACRO] MUTEX_TRY_UNLOCK %out_ok, %lock_ptr
|
|
76
|
+
__mutex_unlock_state_%out_ok, %out_ok = cmpxchg %lock_ptr+Mutex_lock, 1, 0 as u64 acq_rel acquire
|
|
77
|
+
!__mutex_unlock_state_%out_ok
|
|
78
|
+
[END_MACRO]
|
|
79
|
+
|
|
80
|
+
[MACRO] MUTEX_FORCE_UNLOCKED %lock_ptr
|
|
81
|
+
atomic_store %lock_ptr+Mutex_lock, 0 as u64 release
|
|
82
|
+
[END_MACRO]
|
|
83
|
+
|
|
84
|
+
[MACRO] MUTEX_FREE %lock_ptr
|
|
85
|
+
!%lock_ptr
|
|
86
|
+
[END_MACRO]
|
|
87
|
+
|
|
88
|
+
[MACRO] MUTEX_DEFAULT %out_mutex
|
|
89
|
+
EXPAND MUTEX_NEW %out_mutex
|
|
90
|
+
[END_MACRO]
|
|
91
|
+
|
|
92
|
+
// Rust-style into_inner for MUTEX_NEW_I32 layout: returns stored i32 and releases lock word.
|
|
93
|
+
[MACRO] MUTEX_INTO_INNER_I32 %out_value, %mutex_reg
|
|
94
|
+
%out_value = load %mutex_reg+Mutex_data as i32
|
|
95
|
+
atomic_store %mutex_reg+Mutex_lock, 0 as u64 release
|
|
96
|
+
[END_MACRO]
|
|
97
|
+
|
|
98
|
+
// Guard layout helper: store mutex ptr in guard for unlock symmetry.
|
|
99
|
+
[MACRO] MUTEX_GUARD_NEW %out_guard, %mutex_reg
|
|
100
|
+
%out_guard = alloc MutexGuard_SIZE
|
|
101
|
+
store %out_guard+MutexGuard_mutex, %mutex_reg as ptr
|
|
102
|
+
[END_MACRO]
|
|
103
|
+
|
|
104
|
+
[MACRO] MUTEX_GUARD_UNLOCK %guard_reg
|
|
105
|
+
__mutex_guard_ptr_%guard_reg = load %guard_reg+MutexGuard_mutex as ptr
|
|
106
|
+
EXPAND MUTEX_UNLOCK __mutex_guard_ptr_%guard_reg
|
|
107
|
+
!__mutex_guard_ptr_%guard_reg
|
|
108
|
+
[END_MACRO]
|
|
109
|
+
|
|
110
|
+
|
|
111
|
+
[MACRO] MUTEX_GET_MUT_I32 %out_ptr, %mutex_reg
|
|
112
|
+
%out_ptr = ptr_add %mutex_reg, Mutex_data
|
|
113
|
+
[END_MACRO]
|
|
114
|
+
|
|
115
|
+
@__mutex_try_lock_timeout_ns(lock: ptr, timeout_ns: u64) -> i32:
|
|
116
|
+
L_ENTRY:
|
|
117
|
+
start = call @sa_time_instant_ns()
|
|
118
|
+
backoff_slot = stack_alloc 8
|
|
119
|
+
store backoff_slot+0, 1 as u64
|
|
120
|
+
jmp L_MT_TRY
|
|
121
|
+
L_MT_TRY:
|
|
122
|
+
prev = atomic_rmw_xchg lock+Mutex_lock, 1 as u64 acq_rel
|
|
123
|
+
free = eq prev, 0
|
|
124
|
+
!prev
|
|
125
|
+
br free -> L_MT_OK, L_MT_CHECK
|
|
126
|
+
L_MT_OK:
|
|
127
|
+
!lock
|
|
128
|
+
!free
|
|
129
|
+
!start
|
|
130
|
+
!timeout_ns
|
|
131
|
+
return 1
|
|
132
|
+
L_MT_CHECK:
|
|
133
|
+
!free
|
|
134
|
+
now = call @sa_time_instant_ns()
|
|
135
|
+
elapsed = sub now, start
|
|
136
|
+
timed_out = uge elapsed, timeout_ns
|
|
137
|
+
!now
|
|
138
|
+
!elapsed
|
|
139
|
+
br timed_out -> L_MT_TIMEOUT, L_MT_BACKOFF
|
|
140
|
+
L_MT_BACKOFF:
|
|
141
|
+
backoff_ns = load backoff_slot+0 as u64
|
|
142
|
+
call @sa_time_sleep_ns(backoff_ns)
|
|
143
|
+
at_limit = uge backoff_ns, 1024
|
|
144
|
+
br at_limit -> L_MT_KEEP, L_MT_GROW
|
|
145
|
+
L_MT_GROW:
|
|
146
|
+
next = shl backoff_ns, 1
|
|
147
|
+
store backoff_slot+0, next as u64
|
|
148
|
+
!next
|
|
149
|
+
!at_limit
|
|
150
|
+
!backoff_ns
|
|
151
|
+
!timed_out
|
|
152
|
+
jmp L_MT_TRY
|
|
153
|
+
L_MT_KEEP:
|
|
154
|
+
!at_limit
|
|
155
|
+
!backoff_ns
|
|
156
|
+
!timed_out
|
|
157
|
+
jmp L_MT_TRY
|
|
158
|
+
L_MT_TIMEOUT:
|
|
159
|
+
!lock
|
|
160
|
+
!timed_out
|
|
161
|
+
!start
|
|
162
|
+
!timeout_ns
|
|
163
|
+
return 0
|
|
164
|
+
|
|
165
|
+
[MACRO] MUTEX_TRY_LOCK_TIMEOUT_NS %out_ok, %lock_ptr, %timeout_ns
|
|
166
|
+
%out_ok = call @__mutex_try_lock_timeout_ns(%lock_ptr, %timeout_ns)
|
|
167
|
+
[END_MACRO]
|
|
168
|
+
|
|
169
|
+
[MACRO] MUTEX_TRY_LOCK_TIMEOUT_MS %out_ok, %lock_ptr, %timeout_ms
|
|
170
|
+
EXPAND TIME_CHECKED_MUL_NS __mutex_timeout_ms_ok_%out_ok, __mutex_timeout_ns_%out_ok, %timeout_ms, Time_NS_PER_MS
|
|
171
|
+
br __mutex_timeout_ms_ok_%out_ok -> L_MUTEX_TIMEOUT_MS_OK_%out_ok, L_MUTEX_TIMEOUT_MS_FAIL_%out_ok
|
|
172
|
+
L_MUTEX_TIMEOUT_MS_OK_%out_ok:
|
|
173
|
+
EXPAND MUTEX_TRY_LOCK_TIMEOUT_NS %out_ok, %lock_ptr, __mutex_timeout_ns_%out_ok
|
|
174
|
+
!__mutex_timeout_ms_ok_%out_ok
|
|
175
|
+
!__mutex_timeout_ns_%out_ok
|
|
176
|
+
jmp L_MUTEX_TIMEOUT_MS_DONE_%out_ok
|
|
177
|
+
L_MUTEX_TIMEOUT_MS_FAIL_%out_ok:
|
|
178
|
+
%out_ok = add 0, 0
|
|
179
|
+
!__mutex_timeout_ms_ok_%out_ok
|
|
180
|
+
!__mutex_timeout_ns_%out_ok
|
|
181
|
+
L_MUTEX_TIMEOUT_MS_DONE_%out_ok:
|
|
182
|
+
[END_MACRO]
|