struct LLVM::FunctionCollection def initialize(@mod : Module) end def add(name, arg_types : Array(LLVM::Type), ret_type, varargs = false) # check_types_context(name, arg_types, ret_type) add(name, LLVM::Type.function(arg_types, ret_type, varargs)) end def add(name, arg_types : Array(LLVM::Type), ret_type, varargs = false, &) func = add(name, arg_types, ret_type, varargs) yield func func end def add(name, fun_type : LLVM::Type) func = LibLLVM.add_function(@mod, name, fun_type) Function.new(func) end def add(name, fun_type : LLVM::Type, &) func = add(name, fun_type) yield func func end def [](name) func = self[name]? func || raise "Undefined llvm function: #{name}" end def []?(name) func = {% if LibLLVM::IS_LT_200 %} LibLLVM.get_named_function(@mod, name) {% else %} LibLLVM.get_named_function_with_length(@mod, name, name.bytesize) {% end %} func ? Function.new(func) : nil end def each(&) : Nil f = LibLLVM.get_first_function(@mod) while f yield LLVM::Function.new f f = LibLLVM.get_next_function(f) end end # The next lines are for ease debugging when a types/values # are incorrectly used across contexts. # private def check_types_context(name, arg_types, ret_type) # ctx = @mod.context # arg_types.each_with_index do |arg_type, index| # if arg_type.context != ctx # Context.wrong(ctx, arg_type.context, "wrong context for function #{name} in #{@mod.name}, index #{index}, type #{arg_type}") # end # end # if ret_type.context != ctx # Context.wrong(ctx, ret_type.context, "wrong context for function #{name} in #{@mod.name}, return type #{ret_type}") # end # end end