Skip to content

Interpreter crashes with error: has no type (Exception) #16486

@cyangle

Description

@cyangle

This error only happens with interpreter, the compiled binary works fine.

Code to reproduce the error(reduced by AI):

# Minimal reproducer for Crystal interpreter bug
# Issue: Type narrowing fails in the interpreter when:
# 1. Inside an if block with a return statement
# 2. A union type is narrowed with a nil check and return
# 3. The narrowed variable is used in a method call

class Model
  def self.foreign_key_for_association(sym : Symbol) : Symbol | Nil
    nil
  end

  def self.through_key_for_association(sym : Symbol) : Symbol | Nil
    nil
  end
end

class Query
  def self.where(key : Symbol, ids : Array) : Query
    new
  end

  def initialize
  end
end

def delete_dependents(queryable, destroy_assoc, ids, tx)
  through_key = queryable.through_key_for_association(destroy_assoc)
  if through_key.nil?
    foreign_key = queryable.foreign_key_for_association(destroy_assoc)
    return if foreign_key.nil?
    q = Query.where(foreign_key, ids)
  end
end

delete_dependents(Model, :test, [1, 2], nil)
puts "done"

The error:

BUG: `foreign_key = queryable.foreign_key_for_association(destroy_assoc)
if true
  return
end
Query
foreign_key
` at spec/min_repro.cr:29:5 has no type (Exception)
  from /home/chao/git/personal/crystal/src/compiler/crystal/semantic/bindings.cr:86:7 in 'visit'
  from /home/chao/git/personal/crystal/src/enumerable.cr:510:7 in 'accept'
  from /home/chao/git/personal/crystal/src/compiler/crystal/semantic/bindings.cr:86:7 in 'compile_def'
  from /home/chao/git/personal/crystal/src/compiler/crystal/interpreter/compiler.cr:2175:5 in 'create_compiled_def'
  from /home/chao/git/personal/crystal/src/compiler/crystal/interpreter/compiler.cr:1910:22 in 'visit'
  from /home/chao/git/personal/crystal/src/enumerable.cr:510:7 in 'accept'
  from /home/chao/git/personal/crystal/src/compiler/crystal/semantic/bindings.cr:86:7 in 'visit'
  from /home/chao/git/personal/crystal/src/enumerable.cr:510:7 in 'accept'
  from /home/chao/git/personal/crystal/src/compiler/crystal/interpreter/compiler.cr:3518:11 in 'compile'
  from /home/chao/git/personal/crystal/src/compiler/crystal/interpreter/interpreter.cr:232:5 in 'interpret'
  from /home/chao/git/personal/crystal/src/compiler/crystal/interpreter/repl.cr:98:5 in 'interpret_and_exit_on_error'
  from /home/chao/git/personal/crystal/src/gc/boehm.cr:193:7 in 'repl'
  from /home/chao/git/personal/crystal/src/compiler/crystal/command.cr:105:7 in 'run'
  from /home/chao/git/personal/crystal/src/compiler/crystal/command.cr:56:5 in '__crystal_main'
  from /home/chao/git/personal/crystal/src/crystal/main.cr:129:5 in 'main'
  from /home/chao/git/personal/crystal/src/crystal/system/unix/main.cr:10:3 in 'main'
  from /lib/x86_64-linux-gnu/libc.so.6 in '??'
  from /lib/x86_64-linux-gnu/libc.so.6 in '__libc_start_main'
  from /home/chao/git/personal/crystal/.build/crystal in '_start'
  from ???

Metadata

Metadata

Assignees

No one assigned

    Labels

    Type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions