Skip to content

Commit ce3356e

Browse files
committed
Zir: represent declarations via an instruction
This commit changes how declarations (`const`, `fn`, `usingnamespace`, etc) are represented in ZIR. Previously, these were represented in the container type's extra data (e.g. as trailing data on a `struct_decl`). However, this introduced the complexity of the ZIR mapping logic having to also correlate some ZIR extra data indices. That isn't really a problem today, but it's tricky for the introduction of `TrackedInst` in the commit following this one. Instead, these type declarations now simply contain a trailing list of ZIR indices to `declaration` instructions, which directly encode all data related to the declaration (including containing the declaration's body). Additionally, the ZIR for `align` etc have been split out into their own bodies. This is not strictly necessary, but it's much simpler to understand for an insignificant cost in bytes, and will simplify the resolution of ziglang#131 (where we may need to evaluate the pointer type, including align etc, without immediately evaluating the value body).
1 parent 993a830 commit ce3356e

File tree

8 files changed

+880
-922
lines changed

8 files changed

+880
-922
lines changed

src/AstGen.zig

Lines changed: 225 additions & 159 deletions
Large diffs are not rendered by default.

src/Autodoc.zig

Lines changed: 119 additions & 183 deletions
Large diffs are not rendered by default.

src/InternPool.zig

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -6186,8 +6186,6 @@ fn finishFuncInstance(
61866186
.generation = generation,
61876187
.is_pub = fn_owner_decl.is_pub,
61886188
.is_exported = fn_owner_decl.is_exported,
6189-
.has_linksection_or_addrspace = fn_owner_decl.has_linksection_or_addrspace,
6190-
.has_align = fn_owner_decl.has_align,
61916189
.alive = true,
61926190
.kind = .anon,
61936191
});

src/Module.zig

Lines changed: 233 additions & 243 deletions
Large diffs are not rendered by default.

src/Sema.zig

Lines changed: 20 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -1224,6 +1224,10 @@ fn analyzeBodyInner(
12241224
.trap => break sema.zirTrap(block, inst),
12251225
// zig fmt: on
12261226

1227+
// This instruction never exists in an analyzed body. It exists only in the declaration
1228+
// list for a container type.
1229+
.declaration => unreachable,
1230+
12271231
.extended => ext: {
12281232
const extended = datas[@intFromEnum(inst)].extended;
12291233
break :ext switch (extended.opcode) {
@@ -2736,7 +2740,9 @@ pub fn getStructType(
27362740
}
27372741
}
27382742

2739-
extra_index = try mod.scanNamespace(namespace, extra_index, decls_len, mod.declPtr(decl));
2743+
const decls = sema.code.bodySlice(extra_index, decls_len);
2744+
try mod.scanNamespace(namespace, decls, mod.declPtr(decl));
2745+
extra_index += decls_len;
27402746

27412747
const ty = try ip.getStructType(gpa, .{
27422748
.decl = decl,
@@ -2973,7 +2979,9 @@ fn zirEnumDecl(
29732979
const new_namespace = mod.namespacePtr(new_namespace_index);
29742980
errdefer if (!done) mod.destroyNamespace(new_namespace_index);
29752981

2976-
extra_index = try mod.scanNamespace(new_namespace_index, extra_index, decls_len, new_decl);
2982+
const decls = sema.code.bodySlice(extra_index, decls_len);
2983+
try mod.scanNamespace(new_namespace_index, decls, new_decl);
2984+
extra_index += decls_len;
29772985

29782986
const body = sema.code.bodySlice(extra_index, body_len);
29792987
extra_index += body.len;
@@ -3263,7 +3271,8 @@ fn zirUnionDecl(
32633271
new_decl.val = Value.fromInterned(union_ty);
32643272
new_namespace.ty = Type.fromInterned(union_ty);
32653273

3266-
_ = try mod.scanNamespace(new_namespace_index, extra_index, decls_len, new_decl);
3274+
const decls = sema.code.bodySlice(extra_index, decls_len);
3275+
try mod.scanNamespace(new_namespace_index, decls, new_decl);
32673276

32683277
const decl_val = sema.analyzeDeclVal(block, src, new_decl_index);
32693278
try mod.finalizeAnonDecl(new_decl_index);
@@ -3326,7 +3335,8 @@ fn zirOpaqueDecl(
33263335
new_decl.val = Value.fromInterned(opaque_ty);
33273336
new_namespace.ty = Type.fromInterned(opaque_ty);
33283337

3329-
extra_index = try mod.scanNamespace(new_namespace_index, extra_index, decls_len, new_decl);
3338+
const decls = sema.code.bodySlice(extra_index, decls_len);
3339+
try mod.scanNamespace(new_namespace_index, decls, new_decl);
33303340

33313341
const decl_val = sema.analyzeDeclVal(block, src, new_decl_index);
33323342
try mod.finalizeAnonDecl(new_decl_index);
@@ -36331,9 +36341,7 @@ fn structZirInfo(zir: Zir, zir_index: Zir.Inst.Index) struct {
3633136341
}
3633236342

3633336343
// Skip over decls.
36334-
var decls_it = zir.declIteratorInner(extra_index, decls_len);
36335-
while (decls_it.next()) |_| {}
36336-
extra_index = decls_it.extra_index;
36344+
extra_index += decls_len;
3633736345

3633836346
return .{ fields_len, small, extra_index };
3633936347
}
@@ -36802,9 +36810,7 @@ fn semaUnionFields(mod: *Module, arena: Allocator, union_type: InternPool.Key.Un
3680236810
} else 0;
3680336811

3680436812
// Skip over decls.
36805-
var decls_it = zir.declIteratorInner(extra_index, decls_len);
36806-
while (decls_it.next()) |_| {}
36807-
extra_index = decls_it.extra_index;
36813+
extra_index += decls_len;
3680836814

3680936815
const body = zir.bodySlice(extra_index, body_len);
3681036816
extra_index += body.len;
@@ -37801,10 +37807,12 @@ pub fn analyzeAddressSpace(
3780137807
ctx: AddressSpaceContext,
3780237808
) !std.builtin.AddressSpace {
3780337809
const mod = sema.mod;
37804-
const addrspace_tv = try sema.resolveInstConst(block, src, zir_ref, .{
37810+
const air_ref = try sema.resolveInst(zir_ref);
37811+
const coerced = try sema.coerce(block, Type.fromInterned(.address_space_type), air_ref, src);
37812+
const addrspace_val = try sema.resolveConstDefinedValue(block, src, coerced, .{
3780537813
.needed_comptime_reason = "address space must be comptime-known",
3780637814
});
37807-
const address_space = mod.toEnum(std.builtin.AddressSpace, addrspace_tv.val);
37815+
const address_space = mod.toEnum(std.builtin.AddressSpace, addrspace_val);
3780837816
const target = sema.mod.getTarget();
3780937817
const arch = target.cpu.arch;
3781037818

0 commit comments

Comments
 (0)