Function getFnInfo [src]

Prototype

pub fn getFnInfo(zir: Zir, fn_inst: Inst.Index) FnInfo

Parameters

zir: Zirfn_inst: Inst.Index

Source

pub fn getFnInfo(zir: Zir, fn_inst: Inst.Index) FnInfo { const tags = zir.instructions.items(.tag); const datas = zir.instructions.items(.data); const info: struct { param_block: Inst.Index, body: []const Inst.Index, ret_ty_ref: Inst.Ref, ret_ty_body: []const Inst.Index, ret_ty_is_generic: bool, ies: bool, } = switch (tags[@intFromEnum(fn_inst)]) { .func, .func_inferred => |tag| blk: { const inst_data = datas[@intFromEnum(fn_inst)].pl_node; const extra = zir.extraData(Inst.Func, inst_data.payload_index); var extra_index: usize = extra.end; var ret_ty_ref: Inst.Ref = .none; var ret_ty_body: []const Inst.Index = &.{}; switch (extra.data.ret_ty.body_len) { 0 => { ret_ty_ref = .void_type; }, 1 => { ret_ty_ref = @enumFromInt(zir.extra[extra_index]); extra_index += 1; }, else => { ret_ty_body = zir.bodySlice(extra_index, extra.data.ret_ty.body_len); extra_index += ret_ty_body.len; }, } const body = zir.bodySlice(extra_index, extra.data.body_len); extra_index += body.len; break :blk .{ .param_block = extra.data.param_block, .ret_ty_ref = ret_ty_ref, .ret_ty_body = ret_ty_body, .body = body, .ret_ty_is_generic = extra.data.ret_ty.is_generic, .ies = tag == .func_inferred, }; }, .func_fancy => blk: { const inst_data = datas[@intFromEnum(fn_inst)].pl_node; const extra = zir.extraData(Inst.FuncFancy, inst_data.payload_index); var extra_index: usize = extra.end; var ret_ty_ref: Inst.Ref = .none; var ret_ty_body: []const Inst.Index = &.{}; if (extra.data.bits.has_cc_body) { extra_index += zir.extra[extra_index] + 1; } else if (extra.data.bits.has_cc_ref) { extra_index += 1; } if (extra.data.bits.has_ret_ty_body) { const body_len = zir.extra[extra_index]; extra_index += 1; ret_ty_body = zir.bodySlice(extra_index, body_len); extra_index += ret_ty_body.len; } else if (extra.data.bits.has_ret_ty_ref) { ret_ty_ref = @enumFromInt(zir.extra[extra_index]); extra_index += 1; } else { ret_ty_ref = .void_type; } extra_index += @intFromBool(extra.data.bits.has_any_noalias); const body = zir.bodySlice(extra_index, extra.data.body_len); extra_index += body.len; break :blk .{ .param_block = extra.data.param_block, .ret_ty_ref = ret_ty_ref, .ret_ty_body = ret_ty_body, .body = body, .ret_ty_is_generic = extra.data.bits.ret_ty_is_generic, .ies = extra.data.bits.is_inferred_error, }; }, else => unreachable, }; const param_body = zir.getParamBody(fn_inst); var total_params_len: u32 = 0; for (param_body) |inst| { switch (tags[@intFromEnum(inst)]) { .param, .param_comptime, .param_anytype, .param_anytype_comptime => { total_params_len += 1; }, else => continue, } } return .{ .param_body = param_body, .param_body_inst = info.param_block, .ret_ty_body = info.ret_ty_body, .ret_ty_ref = info.ret_ty_ref, .body = info.body, .total_params_len = total_params_len, .ret_ty_is_generic = info.ret_ty_is_generic, .inferred_error_set = info.ies, }; }