diff --git a/src/compiler/crystal/tools/context.cr b/src/compiler/crystal/tools/context.cr index d58d1557afc5..6cda421c2b0e 100644 --- a/src/compiler/crystal/tools/context.cr +++ b/src/compiler/crystal/tools/context.cr @@ -104,6 +104,7 @@ module Crystal @contexts = Array(HashStringType).new @context = HashStringType.new @def_with_yield = nil + @in_defs = false end def process_instance_defs(type) @@ -157,6 +158,7 @@ module Crystal end def process(result : Compiler::Result) + @in_defs = true result.program.def_instances.each_value do |typed_def| visit_and_append_context typed_def end @@ -164,6 +166,7 @@ module Crystal result.program.types?.try &.values.each do |type| process_type type end + @in_defs = false if @contexts.empty? @context = HashStringType.new @@ -289,9 +292,10 @@ module Crystal private def contains_target(node) if loc_start = node.location loc_end = node.end_location || loc_start - # if it is not between, it could be the case that node is the top level Expressions + # if it is not between, it could be the case that node is the top level Expressions, # in which the (start) location might be in one file and the end location in another. - @target_location.between?(loc_start, loc_end) || loc_start.filename != loc_end.filename + @target_location.between?(loc_start, loc_end) || (!@in_defs && loc_start.filename != loc_end.filename) + # When node generated by macro and macro has yielding block, it also makes `loc_start.filename != loc_end.filename` true. else # if node has no location, assume they may contain the target. # for example with the main expressions ast node this matters