@@ -2,6 +2,26 @@ module Internals
2
2
3
3
import StableTasks: @spawn , @spawnat , @fetch , @fetchfrom , StableTask, AtomicRef
4
4
5
+ # * use `Base.infer_return_type` in preference to `Core.Compiler.return_type`
6
+ # * safe conservative fallback to `Any`, which is subtyped by each type
7
+ if (
8
+ isdefined (Base, :infer_return_type ) &&
9
+ applicable (Base. infer_return_type, identity, Tuple{})
10
+ )
11
+ infer_return_type (@nospecialize f:: Any ) = Base. infer_return_type (f, Tuple{})
12
+ elseif (
13
+ (@isdefined Core) &&
14
+ (Core isa Module) &&
15
+ isdefined (Core, :Compiler ) &&
16
+ (Core. Compiler isa Module) &&
17
+ isdefined (Core. Compiler, :return_type ) &&
18
+ applicable (Core. Compiler. return_type, identity, Tuple{})
19
+ )
20
+ infer_return_type (@nospecialize f:: Any ) = Core. Compiler. return_type (f, Tuple{})
21
+ else
22
+ infer_return_type (@nospecialize f:: Any ) = Any
23
+ end
24
+
5
25
Base. getindex (r:: AtomicRef ) = @atomic r. x
6
26
Base. setindex! (r:: AtomicRef{T} , x) where {T} = @atomic r. x = convert (T, x)
7
27
@@ -96,7 +116,7 @@ macro spawn(args...)
96
116
quote
97
117
let $ (letargs... )
98
118
f = $ thunk
99
- T = Core . Compiler . return_type (f, Tuple{} )
119
+ T = infer_return_type (f )
100
120
ref = AtomicRef {T} ()
101
121
f_wrap = () -> (ref[] = f (); nothing )
102
122
task = Task (f_wrap)
@@ -136,7 +156,7 @@ macro spawnat(thrdid, ex)
136
156
end
137
157
let $ (letargs... )
138
158
thunk = $ thunk
139
- RT = Core . Compiler . return_type (thunk, Tuple{} )
159
+ RT = infer_return_type (thunk)
140
160
ret = AtomicRef {RT} ()
141
161
thunk_wrap = () -> (ret[] = thunk (); nothing )
142
162
local task = Task (thunk_wrap)
0 commit comments