struct Declaration [src]
Trailing:
name: NullTerminatedString // if flags.id.hasName()
lib_name: NullTerminatedString // if flags.id.hasLibName()
type_body_len: u32 // if flags.id.hasTypeBody()
align_body_len: u32 // if flags.id.hasSpecialBodies()
linksection_body_len: u32 // if flags.id.hasSpecialBodies()
addrspace_body_len: u32 // if flags.id.hasSpecialBodies()
value_body_len: u32 // if flags.id.hasValueBody()
type_body_inst: Zir.Inst.Index
for each type_body_len
body to be exited via break_inline to this declaration instruction
align_body_inst: Zir.Inst.Index
for each align_body_len
body to be exited via break_inline to this declaration instruction
linksection_body_inst: Zir.Inst.Index
for each linksection_body_len
body to be exited via break_inline to this declaration instruction
addrspace_body_inst: Zir.Inst.Index
for each addrspace_body_len
body to be exited via break_inline to this declaration instruction
value_body_inst: Zir.Inst.Index
for each value_body_len
body to be exited via break_inline to this declaration instruction
within this body, the declaration instruction refers to the resolved type from the type body
Fields
src_hash_0: u32
src_hash_1: u32
src_hash_2: u32
src_hash_3: u32
flags_0: u32
flags_1: u32
Members
Source
pub const Declaration = struct {
// These fields should be concatenated and reinterpreted as a `std.zig.SrcHash`.
src_hash_0: u32,
src_hash_1: u32,
src_hash_2: u32,
src_hash_3: u32,
// These fields should be concatenated and reinterpreted as a `Flags`.
flags_0: u32,
flags_1: u32,
pub const Unwrapped = struct {
pub const Kind = enum {
unnamed_test,
@"test",
decltest,
@"comptime",
@"usingnamespace",
@"const",
@"var",
};
pub const Linkage = enum {
normal,
@"extern",
@"export",
};
src_node: Ast.Node.Index,
src_line: u32,
src_column: u32,
kind: Kind,
/// Always `.empty` for `kind` of `unnamed_test`, `.@"comptime"`, `.@"usingnamespace"`.
name: NullTerminatedString,
/// Always `false` for `kind` of `unnamed_test`, `.@"test"`, `.decltest`, `.@"comptime"`.
is_pub: bool,
/// Always `false` for `kind != .@"var"`.
is_threadlocal: bool,
/// Always `.normal` for `kind != .@"const" and kind != .@"var"`.
linkage: Linkage,
/// Always `.empty` for `linkage != .@"extern"`.
lib_name: NullTerminatedString,
/// Always populated for `linkage == .@"extern".
type_body: ?[]const Inst.Index,
align_body: ?[]const Inst.Index,
linksection_body: ?[]const Inst.Index,
addrspace_body: ?[]const Inst.Index,
/// Always populated for `linkage != .@"extern".
value_body: ?[]const Inst.Index,
};
pub const Flags = packed struct(u64) {
src_line: u30,
src_column: u29,
id: Id,
pub const Id = enum(u5) {
unnamed_test,
@"test",
decltest,
@"comptime",
@"usingnamespace",
pub_usingnamespace,
const_simple,
const_typed,
@"const",
pub_const_simple,
pub_const_typed,
pub_const,
extern_const_simple,
extern_const,
pub_extern_const_simple,
pub_extern_const,
export_const,
pub_export_const,
var_simple,
@"var",
var_threadlocal,
pub_var_simple,
pub_var,
pub_var_threadlocal,
extern_var,
extern_var_threadlocal,
pub_extern_var,
pub_extern_var_threadlocal,
export_var,
export_var_threadlocal,
pub_export_var,
pub_export_var_threadlocal,
pub fn hasName(id: Id) bool {
return switch (id) {
.unnamed_test,
.@"comptime",
.@"usingnamespace",
.pub_usingnamespace,
=> false,
else => true,
};
}
pub fn hasLibName(id: Id) bool {
return switch (id) {
.extern_const,
.pub_extern_const,
.extern_var,
.extern_var_threadlocal,
.pub_extern_var,
.pub_extern_var_threadlocal,
=> true,
else => false,
};
}
pub fn hasTypeBody(id: Id) bool {
return switch (id) {
.unnamed_test,
.@"test",
.decltest,
.@"comptime",
.@"usingnamespace",
.pub_usingnamespace,
=> false, // these constructs are untyped
.const_simple,
.pub_const_simple,
.var_simple,
.pub_var_simple,
=> false, // these reprs omit type bodies
else => true,
};
}
pub fn hasValueBody(id: Id) bool {
return switch (id) {
.extern_const_simple,
.extern_const,
.pub_extern_const_simple,
.pub_extern_const,
.extern_var,
.extern_var_threadlocal,
.pub_extern_var,
.pub_extern_var_threadlocal,
=> false, // externs do not have values
else => true,
};
}
pub fn hasSpecialBodies(id: Id) bool {
return switch (id) {
.unnamed_test,
.@"test",
.decltest,
.@"comptime",
.@"usingnamespace",
.pub_usingnamespace,
=> false, // these constructs are untyped
.const_simple,
.const_typed,
.pub_const_simple,
.pub_const_typed,
.extern_const_simple,
.pub_extern_const_simple,
.var_simple,
.pub_var_simple,
=> false, // these reprs omit special bodies
else => true,
};
}
pub fn linkage(id: Id) Declaration.Unwrapped.Linkage {
return switch (id) {
.extern_const_simple,
.extern_const,
.pub_extern_const_simple,
.pub_extern_const,
.extern_var,
.extern_var_threadlocal,
.pub_extern_var,
.pub_extern_var_threadlocal,
=> .@"extern",
.export_const,
.pub_export_const,
.export_var,
.export_var_threadlocal,
.pub_export_var,
.pub_export_var_threadlocal,
=> .@"export",
else => .normal,
};
}
pub fn kind(id: Id) Declaration.Unwrapped.Kind {
return switch (id) {
.unnamed_test => .unnamed_test,
.@"test" => .@"test",
.decltest => .decltest,
.@"comptime" => .@"comptime",
.@"usingnamespace", .pub_usingnamespace => .@"usingnamespace",
.const_simple,
.const_typed,
.@"const",
.pub_const_simple,
.pub_const_typed,
.pub_const,
.extern_const_simple,
.extern_const,
.pub_extern_const_simple,
.pub_extern_const,
.export_const,
.pub_export_const,
=> .@"const",
.var_simple,
.@"var",
.var_threadlocal,
.pub_var_simple,
.pub_var,
.pub_var_threadlocal,
.extern_var,
.extern_var_threadlocal,
.pub_extern_var,
.pub_extern_var_threadlocal,
.export_var,
.export_var_threadlocal,
.pub_export_var,
.pub_export_var_threadlocal,
=> .@"var",
};
}
pub fn isPub(id: Id) bool {
return switch (id) {
.pub_usingnamespace,
.pub_const_simple,
.pub_const_typed,
.pub_const,
.pub_extern_const_simple,
.pub_extern_const,
.pub_export_const,
.pub_var_simple,
.pub_var,
.pub_var_threadlocal,
.pub_extern_var,
.pub_extern_var_threadlocal,
.pub_export_var,
.pub_export_var_threadlocal,
=> true,
else => false,
};
}
pub fn isThreadlocal(id: Id) bool {
return switch (id) {
.var_threadlocal,
.pub_var_threadlocal,
.extern_var_threadlocal,
.pub_extern_var_threadlocal,
.export_var_threadlocal,
.pub_export_var_threadlocal,
=> true,
else => false,
};
}
};
};
pub const Name = enum(u32) {
@"comptime" = std.math.maxInt(u32),
@"usingnamespace" = std.math.maxInt(u32) - 1,
unnamed_test = std.math.maxInt(u32) - 2,
/// Other values are `NullTerminatedString` values, i.e. index into
/// `string_bytes`. If the byte referenced is 0, the decl is a named
/// test, and the actual name begins at the following byte.
_,
pub fn isNamedTest(name: Name, zir: Zir) bool {
return switch (name) {
.@"comptime", .@"usingnamespace", .unnamed_test => false,
_ => zir.string_bytes[@intFromEnum(name)] == 0,
};
}
pub fn toString(name: Name, zir: Zir) ?NullTerminatedString {
switch (name) {
.@"comptime", .@"usingnamespace", .unnamed_test => return null,
_ => {},
}
const idx: u32 = @intFromEnum(name);
if (zir.string_bytes[idx] == 0) {
// Named test
return @enumFromInt(idx + 1);
}
return @enumFromInt(idx);
}
};
pub const Bodies = struct {
type_body: ?[]const Index,
align_body: ?[]const Index,
linksection_body: ?[]const Index,
addrspace_body: ?[]const Index,
value_body: ?[]const Index,
};
pub fn getBodies(declaration: Declaration, extra_end: u32, zir: Zir) Bodies {
var extra_index: u32 = extra_end;
const value_body_len = declaration.value_body_len;
const type_body_len: u32 = len: {
if (!declaration.flags().kind.hasTypeBody()) break :len 0;
const len = zir.extra[extra_index];
extra_index += 1;
break :len len;
};
const align_body_len, const linksection_body_len, const addrspace_body_len = lens: {
if (!declaration.flags.kind.hasSpecialBodies()) {
break :lens .{ 0, 0, 0 };
}
const lens = zir.extra[extra_index..][0..3].*;
extra_index += 3;
break :lens lens;
};
return .{
.type_body = if (type_body_len == 0) null else b: {
const b = zir.bodySlice(extra_index, type_body_len);
extra_index += type_body_len;
break :b b;
},
.align_body = if (align_body_len == 0) null else b: {
const b = zir.bodySlice(extra_index, align_body_len);
extra_index += align_body_len;
break :b b;
},
.linksection_body = if (linksection_body_len == 0) null else b: {
const b = zir.bodySlice(extra_index, linksection_body_len);
extra_index += linksection_body_len;
break :b b;
},
.addrspace_body = if (addrspace_body_len == 0) null else b: {
const b = zir.bodySlice(extra_index, addrspace_body_len);
extra_index += addrspace_body_len;
break :b b;
},
.value_body = if (value_body_len == 0) null else b: {
const b = zir.bodySlice(extra_index, value_body_len);
extra_index += value_body_len;
break :b b;
},
};
}
}