File tree Expand file tree Collapse file tree 2 files changed +25
-10
lines changed Expand file tree Collapse file tree 2 files changed +25
-10
lines changed Original file line number Diff line number Diff line change @@ -31,8 +31,8 @@ May be used to mark a region in parallel code to be executed by a single task on
31
31
See [`try_enter!`](@ref) and [`reset!`](@ref).
32
32
"""
33
33
mutable struct OnlyOneRegion
34
- @atomic latch :: Bool
35
- OnlyOneRegion () = new (false )
34
+ @atomic task :: Union{Task, Nothing}
35
+ OnlyOneRegion () = new (nothing )
36
36
end
37
37
38
38
"""
62
62
```
63
63
"""
64
64
function try_enter! (f, s:: OnlyOneRegion )
65
- latch = @atomic :monotonic s. latch
66
- if latch
65
+ ct = current_task ()
66
+ t = @atomic :monotonic s. task
67
+ if ! isnothing (t) && ct != t
67
68
return
68
69
end
69
- (_, success) = @atomicreplace s. latch false => true
70
- if ! success
71
- return
70
+ if ct == t || (@atomicreplace s. task nothing => ct). success
71
+ f ()
72
72
end
73
- f ()
74
73
return
75
74
end
76
75
77
76
"""
78
77
Reset the `OnlyOneRegion` (so that it can be used again).
79
78
"""
80
79
function reset! (s:: OnlyOneRegion )
81
- @atomicreplace s. latch true => false
82
- nothing
80
+ @atomic s. task = nothing
81
+ return
83
82
end
84
83
85
84
"""
Original file line number Diff line number Diff line change 454
454
catch ErrorException
455
455
@test false
456
456
end
457
+
458
+ x = 0
459
+ y = 0
460
+ try
461
+ @tasks for i in 1 : 10
462
+ @set ntasks = 2
463
+
464
+ y += 1 # not safe (race condition)
465
+ @only_one begin
466
+ x += 1 # parallel-safe because only a single task will execute this
467
+ end
468
+ end
469
+ @test x == 5 # a single task should have incremented x 5 times
470
+ catch ErrorException
471
+ @test false
472
+ end
457
473
end
458
474
459
475
@testset " @only_one + @one_by_one" begin
You can’t perform that action at this time.
0 commit comments