diff options
| author | Veikka Tuominen <git@vexu.eu> | 2022-02-26 12:38:25 +0200 |
|---|---|---|
| committer | Veikka Tuominen <git@vexu.eu> | 2022-02-26 18:08:11 +0200 |
| commit | ff72b8a8194573bc1d7f95cbf3228b363194c775 (patch) | |
| tree | d5608b46018c2cd5c38314134e4d4e10100f7c04 /src/Sema.zig | |
| parent | db82c1b9820449f2d1e6ef54dd32ec3ffd3c583f (diff) | |
| download | zig-ff72b8a8194573bc1d7f95cbf3228b363194c775.tar.gz zig-ff72b8a8194573bc1d7f95cbf3228b363194c775.zip | |
stage2: evaluate TypeOf arguments in a separate scope
Diffstat (limited to 'src/Sema.zig')
| -rw-r--r-- | src/Sema.zig | 44 |
1 files changed, 43 insertions, 1 deletions
diff --git a/src/Sema.zig b/src/Sema.zig index ef9ba41bec..eca88f8922 100644 --- a/src/Sema.zig +++ b/src/Sema.zig @@ -124,6 +124,7 @@ pub const Block = struct { runtime_index: u32 = 0, is_comptime: bool, + is_typeof: bool = false, /// when null, it is determined by build mode, changed by @setRuntimeSafety want_safety: ?bool = null, @@ -181,6 +182,7 @@ pub const Block = struct { .label = null, .inlining = parent.inlining, .is_comptime = parent.is_comptime, + .is_typeof = parent.is_typeof, .runtime_cond = parent.runtime_cond, .runtime_loop = parent.runtime_loop, .runtime_index = parent.runtime_index, @@ -682,6 +684,7 @@ fn analyzeBodyInner( .size_of => try sema.zirSizeOf(block, inst), .bit_size_of => try sema.zirBitSizeOf(block, inst), .typeof => try sema.zirTypeof(block, inst), + .typeof_builtin => try sema.zirTypeofBuiltin(block, inst), .log2_int_type => try sema.zirLog2IntType(block, inst), .typeof_log2_int_type => try sema.zirTypeofLog2IntType(block, inst), .xor => try sema.zirBitwise(block, inst, .xor), @@ -10574,6 +10577,29 @@ fn zirTypeof(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!Air. return sema.addType(operand_ty); } +fn zirTypeofBuiltin(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!Air.Inst.Ref { + const pl_node = sema.code.instructions.items(.data)[inst].pl_node; + const extra = sema.code.extraData(Zir.Inst.Block, pl_node.payload_index); + const body = sema.code.extra[extra.end..][0..extra.data.body_len]; + + var child_block: Block = .{ + .parent = block, + .sema = sema, + .src_decl = block.src_decl, + .namespace = block.namespace, + .wip_capture_scope = block.wip_capture_scope, + .instructions = .{}, + .inlining = block.inlining, + .is_comptime = false, + .is_typeof = true, + }; + defer child_block.instructions.deinit(sema.gpa); + + const operand = try sema.resolveBody(&child_block, body, inst); + const operand_ty = sema.typeOf(operand); + return sema.addType(operand_ty); +} + fn zirTypeofLog2IntType(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!Air.Inst.Ref { const inst_data = sema.code.instructions.items(.data)[inst].un_node; const src = inst_data.src(); @@ -10624,8 +10650,24 @@ fn zirTypeofPeer( const tracy = trace(@src()); defer tracy.end(); - const extra = sema.code.extraData(Zir.Inst.NodeMultiOp, extended.operand); + const extra = sema.code.extraData(Zir.Inst.TypeOfPeer, extended.operand); const src: LazySrcLoc = .{ .node_offset = extra.data.src_node }; + const body = sema.code.extra[extra.data.body_index..][0..extra.data.body_len]; + + var child_block: Block = .{ + .parent = block, + .sema = sema, + .src_decl = block.src_decl, + .namespace = block.namespace, + .wip_capture_scope = block.wip_capture_scope, + .instructions = .{}, + .inlining = block.inlining, + .is_comptime = false, + .is_typeof = true, + }; + defer child_block.instructions.deinit(sema.gpa); + _ = try sema.analyzeBody(&child_block, body); + const args = sema.code.refSlice(extra.end, extended.small); const inst_list = try sema.gpa.alloc(Air.Inst.Ref, args.len); |
