Skip to content

Commit 590c555

Browse files
committed
fix up
1 parent 07595d1 commit 590c555

File tree

3 files changed

+70
-30
lines changed

3 files changed

+70
-30
lines changed

src/codeedges.jl

Lines changed: 23 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -325,7 +325,7 @@ function add_links!(target::Pair{Union{SSAValue,SlotNumber,GlobalRef},Links}, @n
325325
cl.namesuccs[stmt] = namestore = Links()
326326
end
327327
push!(namestore, targetid)
328-
elseif isa(stmt, Expr) && stmt.head !== :copyast
328+
elseif isa(stmt, Expr) && stmt.head !== :copyast && stmt.head !== :globaldecl
329329
stmt = stmt::Expr
330330
arng = 1:length(stmt.args)
331331
if stmt.head === :call
@@ -338,6 +338,20 @@ function add_links!(target::Pair{Union{SSAValue,SlotNumber,GlobalRef},Links}, @n
338338
for i in arng
339339
add_links!(target, stmt.args[i], cl)
340340
end
341+
elseif isexpr(stmt, :globaldecl)
342+
for i = 1:length(stmt.args)
343+
a = stmt.args[i]
344+
if a isa GlobalRef
345+
namestore = get(cl.namepreds, a, nothing)
346+
if namestore === nothing
347+
cl.namepreds[a] = namestore = Links()
348+
end
349+
push!(namestore, targetid)
350+
if targetid isa SSAValue
351+
push!(namestore, SSAValue(targetid.id+1)) # +1 for :latestworld
352+
end
353+
end
354+
end
341355
elseif stmt isa Core.GotoIfNot
342356
add_links!(target, stmt.cond, cl)
343357
elseif stmt isa Core.ReturnNode
@@ -383,7 +397,6 @@ struct Variable
383397
preds::Vector{Int}
384398
succs::Vector{Int}
385399
end
386-
Variable() = Variable(Int[], Int[], Int[])
387400

388401
function Base.show(io::IO, v::Variable)
389402
print(io, "assigned on ", showempty(v.assigned))
@@ -736,10 +749,17 @@ function add_succs!(isrequired, idx, edges::CodeEdges, succs, norequire)
736749
end
737750
return chngd
738751
end
739-
function add_obj!(isrequired, objs, obj, edges::CodeEdges, norequire)
752+
function add_obj!(isrequired, objs, obj::GlobalRef, edges::CodeEdges, norequire)
740753
chngd = false
754+
for p in edges.byname[obj].preds
755+
p norequire && continue
756+
isrequired[p] && continue
757+
isrequired[p] = true
758+
chngd = true
759+
end
741760
for d in edges.byname[obj].assigned
742761
d norequire && continue
762+
isrequired[d] && continue
743763
isrequired[d] || add_preds!(isrequired, d, edges, norequire)
744764
isrequired[d] = true
745765
chngd = true

test/codeedges.jl

Lines changed: 46 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -66,24 +66,24 @@ module ModSelective end
6666
Core.eval(ModEval, ex)
6767
isrequired = lines_required(GlobalRef(ModSelective, :x), src, edges)
6868
# theere is too much diversity in lowering across Julia versions to make it useful to test `sum(isrequired)`
69-
selective_eval_fromstart!(frame, isrequired)
69+
selective_eval_fromstart!(frame, isrequired, #=istoplevel=#true)
7070
@test ModSelective.x === ModEval.x
7171
@test allmissing(ModSelective, (:y, :z, :a, :b, :k))
7272
@test !allmissing(ModSelective, (:x, :y)) # add :y here to test the `all` part of the test itself
7373
# To evaluate z we need to do all the computations for y
7474
isrequired = lines_required(GlobalRef(ModSelective, :z), src, edges)
75-
selective_eval_fromstart!(frame, isrequired)
75+
selective_eval_fromstart!(frame, isrequired, #=istoplevel=#true)
7676
@test ModSelective.y === ModEval.y
7777
@test ModSelective.z === ModEval.z
7878
@test allmissing(ModSelective, (:a, :b, :k)) # ... but not a and b
7979
isrequired = lines_required(length(src.code)-1, src, edges) # this should be the assignment of b
80-
selective_eval_fromstart!(frame, isrequired)
80+
selective_eval_fromstart!(frame, isrequired, #=istoplevel=#true)
8181
@test ModSelective.a === ModEval.a
8282
@test ModSelective.b === ModEval.b
8383
# Test that we get two separate evaluations of k
8484
@test allmissing(ModSelective, (:k,))
8585
isrequired = lines_required(GlobalRef(ModSelective, :k), src, edges)
86-
selective_eval_fromstart!(frame, isrequired)
86+
selective_eval_fromstart!(frame, isrequired, #=istoplevel=#true)
8787
@test ModSelective.k != ModEval.k
8888

8989
# Control-flow
@@ -124,7 +124,7 @@ module ModSelective end
124124
src = frame.framecode.src
125125
edges = CodeEdges(ModSelective, src)
126126
isrequired = lines_required(GlobalRef(ModSelective, :a3), src, edges)
127-
selective_eval_fromstart!(frame, isrequired)
127+
selective_eval_fromstart!(frame, isrequired, #=istoplevel=#true)
128128
Core.eval(ModEval, ex)
129129
@test ModSelective.a3 === ModEval.a3 == 2
130130
@test allmissing(ModSelective, (:z3, :x3, :y3))
@@ -143,7 +143,7 @@ module ModSelective end
143143
src = frame.framecode.src
144144
edges = CodeEdges(ModSelective, src)
145145
isrequired = lines_required(GlobalRef(ModSelective, :valcf), src, edges)
146-
selective_eval_fromstart!(frame, isrequired)
146+
selective_eval_fromstart!(frame, isrequired, #=istoplevel=#true)
147147
@test ModSelective.valcf == 4
148148

149149
ex = quote
@@ -161,7 +161,7 @@ module ModSelective end
161161
edges = CodeEdges(ModSelective, src)
162162
isrequired = lines_required(GlobalRef(ModSelective, :c_os), src, edges)
163163
@test sum(isrequired) >= length(isrequired) - 3
164-
selective_eval_fromstart!(frame, isrequired)
164+
selective_eval_fromstart!(frame, isrequired, #=istoplevel=#true)
165165
Core.eval(ModEval, ex)
166166
@test ModSelective.c_os === ModEval.c_os == Sys.iswindows()
167167

@@ -187,7 +187,7 @@ module ModSelective end
187187
@test sum(isrequired) == 1
188188
isrequired[edges.succs[findfirst(isrequired)]] .= true # add lines that use Core.eval
189189
lines_required!(isrequired, src, edges)
190-
selective_eval_fromstart!(frame, isrequired)
190+
selective_eval_fromstart!(frame, isrequired, #=istoplevel=#true)
191191
@test ModSelective.feval1(1.0f0) == 1
192192
@test ModSelective.feval1(1.0) == 1
193193
@test_throws MethodError ModSelective.feval1(1)
@@ -206,13 +206,13 @@ module ModSelective end
206206
end
207207
end
208208
frame = Frame(ModSelective, ex)
209-
JuliaInterpreter.finish_and_return!(frame, true)
209+
JuliaInterpreter.finish_and_return!(frame, #=istoplevel=#true)
210210
@test ModSelective.k11 == 11
211211
@test 3 <= ModSelective.s11 <= 15
212212
Core.eval(ModSelective, :(k11 = 0; s11 = -1))
213213
edges = CodeEdges(ModSelective, frame.framecode.src)
214214
isrequired = lines_required(GlobalRef(ModSelective, :s11), frame.framecode.src, edges)
215-
selective_eval_fromstart!(frame, isrequired, true)
215+
selective_eval_fromstart!(frame, isrequired, #=istoplevel=#true)
216216
@test ModSelective.k11 == 0
217217
@test 3 <= ModSelective.s11 <= 15
218218

@@ -224,15 +224,15 @@ module ModSelective end
224224
# Check that the StructParent name is discovered everywhere it is used
225225
var = edges.byname[GlobalRef(ModSelective, :StructParent)]
226226
isrequired = minimal_evaluation(hastrackedexpr, src, edges)
227-
selective_eval_fromstart!(frame, isrequired, true)
227+
selective_eval_fromstart!(frame, isrequired, #=istoplevel=#true)
228228
@test supertype(ModSelective.StructParent) === AbstractArray
229229
# Also check redefinition (it's OK when the definition doesn't change)
230230
Core.eval(ModEval, ex)
231231
frame = Frame(ModEval, ex)
232232
src = frame.framecode.src
233233
edges = CodeEdges(ModEval, src)
234234
isrequired = minimal_evaluation(hastrackedexpr, src, edges)
235-
selective_eval_fromstart!(frame, isrequired, true)
235+
selective_eval_fromstart!(frame, isrequired, #=istoplevel=#true)
236236
@test supertype(ModEval.StructParent) === AbstractArray
237237

238238
# Finding all dependencies in a struct definition
@@ -241,9 +241,19 @@ module ModSelective end
241241
frame = Frame(ModSelective, ex)
242242
src = frame.framecode.src
243243
edges = CodeEdges(ModSelective, src)
244-
isrequired = minimal_evaluation(@nospecialize(stmt)->(LoweredCodeUtils.ismethod_with_name(src, stmt, "NoParam"),false), src, edges) # initially mark only the constructor
245-
selective_eval_fromstart!(frame, isrequired, true)
246-
@test isa(ModSelective.NoParam(), ModSelective.NoParam)
244+
isrequired = minimal_evaluation(src, edges) do @nospecialize stmt
245+
# initially mark only the constructor
246+
@static if VERSION v"1.12-"
247+
return (Meta.isexpr(stmt, :call) && stmt.args[1] == GlobalRef(Core, :_defaultctors), false)
248+
else
249+
return (LoweredCodeUtils.ismethod_with_name(src, stmt, "NoParam"), false)
250+
end
251+
end
252+
selective_eval_fromstart!(frame, isrequired, #=istoplevel=#true)
253+
let NoParam = @invokelatest ModSelective.NoParam
254+
@test isa(NoParam(), NoParam)
255+
end
256+
247257
# Parametric
248258
ex = quote
249259
struct Struct{T} <: StructParent{T,1}
@@ -253,9 +263,19 @@ module ModSelective end
253263
frame = Frame(ModSelective, ex)
254264
src = frame.framecode.src
255265
edges = CodeEdges(ModSelective, src)
256-
isrequired = minimal_evaluation(@nospecialize(stmt)->(LoweredCodeUtils.ismethod_with_name(src, stmt, "Struct"),false), src, edges) # initially mark only the constructor
257-
selective_eval_fromstart!(frame, isrequired, true)
258-
@test isa(ModSelective.Struct([1,2,3]), ModSelective.Struct{Int})
266+
isrequired = minimal_evaluation(src, edges) do @nospecialize stmt
267+
# initially mark only the constructor
268+
@static if VERSION v"1.12-"
269+
return (Meta.isexpr(stmt, :call) && stmt.args[1] == GlobalRef(Core, :_defaultctors), false)
270+
else
271+
return (LoweredCodeUtils.ismethod_with_name(src, stmt, "Struct"), false)
272+
end
273+
end
274+
selective_eval_fromstart!(frame, isrequired, #=istoplevel=#true)
275+
let Struct = @invokelatest ModSelective.Struct
276+
@test isa(Struct([1,2,3]), Struct{Int})
277+
end
278+
259279
# Keyword constructor (this generates :copyast expressions)
260280
ex = quote
261281
struct KWStruct
@@ -271,7 +291,7 @@ module ModSelective end
271291
src = frame.framecode.src
272292
edges = CodeEdges(ModSelective, src)
273293
isrequired = minimal_evaluation(@nospecialize(stmt)->(LoweredCodeUtils.ismethod3(stmt),false), src, edges) # initially mark only the constructor
274-
selective_eval_fromstart!(frame, isrequired, true)
294+
selective_eval_fromstart!(frame, isrequired, #=istoplevel=#true)
275295
kws = ModSelective.KWStruct(y=5.0f0)
276296
@test kws.y === 5.0f0
277297

@@ -281,14 +301,15 @@ module ModSelective end
281301
src = frame.framecode.src
282302
edges = CodeEdges(ModSelective, src)
283303
isrequired = fill(false, length(src.code))
284-
j = length(src.code) - 1
285-
while !Meta.isexpr(src.code[j], :method, 3)
286-
j -= 1
304+
let j = length(src.code) - 1
305+
while !Meta.isexpr(src.code[j], :method, 3)
306+
j -= 1
307+
end
308+
@assert Meta.isexpr(src.code[j], :method, 3)
309+
isrequired[j] = true
287310
end
288-
@assert Meta.isexpr(src.code[j], :method, 3)
289-
isrequired[j] = true
290311
lines_required!(isrequired, src, edges)
291-
selective_eval_fromstart!(frame, isrequired, true)
312+
selective_eval_fromstart!(frame, isrequired, #=istoplevel=#true)
292313
@test ModSelective.max_values(Int16) === 65536
293314

294315
# Avoid redefining types

test/signatures.jl

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -477,8 +477,7 @@ macro deffoogr_sandbox()
477477
$gr(args...) = length(args)
478478
end
479479
end
480-
let
481-
ex = quote
480+
let ex = quote
482481
@deffoogr_sandbox
483482
@show sandboxgr.foogr_sandbox(1,2,3)
484483
end

0 commit comments

Comments
 (0)