Landin library reference discuss source

compiler/tests/fixtures/runtime/thread-creation-and-join-order-writes/main.ldn

1--  D227's two edges for hosted threads, and nothing else: the routine
2--  writes `published` with ordinary stores, admits two threads that each
3--  read their half and write `results` with ordinary stores, and reads
4--  every result once `join` has returned.  No atomic, fence or lock of the
5--  program's own orders any of it, so a value read wrong on either side
6--  is an edge the thread facility did not supply.  The threads run at
7--  once, each on a stack of the group's backing.
8import core/failure
9import hosted/system
10import hosted/thread
11
12--  How many words each thread reads and writes.
13half: usize = 512
14
15mut published: [2 * half]u64 = zeroed
16mut results: [2 * half]u64 = zeroed
17
18part: type = struct
19    first: usize
20    count: usize
21end part
22
23--  Read the published words of its part and write their results.
24work: (inout state: part) -> none ! failure.reason =
25    for index in state.first..<state.first + state.count do
26        results[index] = published[index] * 3 + 1
27    end for
28end work
29
30--  Two stacks, with room for Darwin's whole 16 KiB pages.
31mut backing: [3 * 32768]u8 = zeroed
32
33run: (host: system.host) -> none ! failure.reason =
34    mut workers := try thread.group_over(host, backing, 2)
35    defer thread.join(workers) else none
36    low: part = (first: 0, count: half)
37    try thread.admit(workers, work, low)
38    high: part = (first: half, count: half)
39    try thread.admit(workers, work, high)
40    try thread.join(workers)
41end run
42
43public main: () -> (code: i32) =
44    code = 1
45    for index in usize(0)..<2 * half do
46        published[index] = u64(index) * 7 + 5
47    end for
48    run(system.new()) else none
49    code = 2
50    for index in usize(0)..<2 * half do
51        return when results[index] <> (u64(index) * 7 + 5) * 3 + 1
52    end for
53    code = 42
54end main