x86_64: add support for pie executables
This commit is contained in:
committed by
Andrew Kelley
parent
178ee8aef1
commit
0bf8617d96
@@ -526,10 +526,10 @@ pub const Nav = struct {
|
||||
/// The type of this `Nav` is resolved; the value is queued for resolution.
|
||||
type_resolved: struct {
|
||||
type: InternPool.Index,
|
||||
is_const: bool,
|
||||
alignment: Alignment,
|
||||
@"linksection": OptionalNullTerminatedString,
|
||||
@"addrspace": std.builtin.AddressSpace,
|
||||
is_const: bool,
|
||||
is_threadlocal: bool,
|
||||
/// This field is whether this `Nav` is a literal `extern` definition.
|
||||
/// It does *not* tell you whether this might alias an extern fn (see #21027).
|
||||
@@ -538,6 +538,7 @@ pub const Nav = struct {
|
||||
/// The value of this `Nav` is resolved.
|
||||
fully_resolved: struct {
|
||||
val: InternPool.Index,
|
||||
is_const: bool,
|
||||
alignment: Alignment,
|
||||
@"linksection": OptionalNullTerminatedString,
|
||||
@"addrspace": std.builtin.AddressSpace,
|
||||
@@ -727,12 +728,12 @@ pub const Nav = struct {
|
||||
const Bits = packed struct(u16) {
|
||||
status: enum(u2) { unresolved, type_resolved, fully_resolved, type_resolved_extern_decl },
|
||||
/// Populated only if `bits.status != .unresolved`.
|
||||
is_const: bool,
|
||||
/// Populated only if `bits.status != .unresolved`.
|
||||
alignment: Alignment,
|
||||
/// Populated only if `bits.status != .unresolved`.
|
||||
@"addrspace": std.builtin.AddressSpace,
|
||||
/// Populated only if `bits.status == .type_resolved`.
|
||||
is_const: bool,
|
||||
/// Populated only if `bits.status == .type_resolved`.
|
||||
is_threadlocal: bool,
|
||||
is_usingnamespace: bool,
|
||||
};
|
||||
@@ -753,15 +754,16 @@ pub const Nav = struct {
|
||||
.unresolved => .unresolved,
|
||||
.type_resolved, .type_resolved_extern_decl => .{ .type_resolved = .{
|
||||
.type = repr.type_or_val,
|
||||
.is_const = repr.bits.is_const,
|
||||
.alignment = repr.bits.alignment,
|
||||
.@"linksection" = repr.@"linksection",
|
||||
.@"addrspace" = repr.bits.@"addrspace",
|
||||
.is_const = repr.bits.is_const,
|
||||
.is_threadlocal = repr.bits.is_threadlocal,
|
||||
.is_extern_decl = repr.bits.status == .type_resolved_extern_decl,
|
||||
} },
|
||||
.fully_resolved => .{ .fully_resolved = .{
|
||||
.val = repr.type_or_val,
|
||||
.is_const = repr.bits.is_const,
|
||||
.alignment = repr.bits.alignment,
|
||||
.@"linksection" = repr.@"linksection",
|
||||
.@"addrspace" = repr.bits.@"addrspace",
|
||||
@@ -792,26 +794,26 @@ pub const Nav = struct {
|
||||
.bits = switch (nav.status) {
|
||||
.unresolved => .{
|
||||
.status = .unresolved,
|
||||
.is_const = false,
|
||||
.alignment = .none,
|
||||
.@"addrspace" = .generic,
|
||||
.is_usingnamespace = nav.is_usingnamespace,
|
||||
.is_const = false,
|
||||
.is_threadlocal = false,
|
||||
},
|
||||
.type_resolved => |r| .{
|
||||
.status = if (r.is_extern_decl) .type_resolved_extern_decl else .type_resolved,
|
||||
.is_const = r.is_const,
|
||||
.alignment = r.alignment,
|
||||
.@"addrspace" = r.@"addrspace",
|
||||
.is_usingnamespace = nav.is_usingnamespace,
|
||||
.is_const = r.is_const,
|
||||
.is_threadlocal = r.is_threadlocal,
|
||||
},
|
||||
.fully_resolved => |r| .{
|
||||
.status = .fully_resolved,
|
||||
.is_const = r.is_const,
|
||||
.alignment = r.alignment,
|
||||
.@"addrspace" = r.@"addrspace",
|
||||
.is_usingnamespace = nav.is_usingnamespace,
|
||||
.is_const = false,
|
||||
.is_threadlocal = false,
|
||||
},
|
||||
},
|
||||
@@ -2221,7 +2223,6 @@ pub const Key = union(enum) {
|
||||
init: Index,
|
||||
owner_nav: Nav.Index,
|
||||
is_threadlocal: bool,
|
||||
is_weak_linkage: bool,
|
||||
};
|
||||
|
||||
pub const Extern = struct {
|
||||
@@ -2234,10 +2235,12 @@ pub const Key = union(enum) {
|
||||
/// For example `extern "c" fn write(...) usize` would have 'c' as library name.
|
||||
/// Index into the string table bytes.
|
||||
lib_name: OptionalNullTerminatedString,
|
||||
is_const: bool,
|
||||
linkage: std.builtin.GlobalLinkage,
|
||||
visibility: std.builtin.SymbolVisibility,
|
||||
is_threadlocal: bool,
|
||||
is_weak_linkage: bool,
|
||||
is_dll_import: bool,
|
||||
relocation: std.builtin.ExternOptions.Relocation,
|
||||
is_const: bool,
|
||||
alignment: Alignment,
|
||||
@"addrspace": std.builtin.AddressSpace,
|
||||
/// The ZIR instruction which created this extern; used only for source locations.
|
||||
@@ -2844,9 +2847,10 @@ pub const Key = union(enum) {
|
||||
|
||||
.@"extern" => |e| Hash.hash(seed, asBytes(&e.name) ++
|
||||
asBytes(&e.ty) ++ asBytes(&e.lib_name) ++
|
||||
asBytes(&e.is_const) ++ asBytes(&e.is_threadlocal) ++
|
||||
asBytes(&e.is_weak_linkage) ++ asBytes(&e.alignment) ++
|
||||
asBytes(&e.is_dll_import) ++ asBytes(&e.@"addrspace") ++
|
||||
asBytes(&e.linkage) ++ asBytes(&e.visibility) ++
|
||||
asBytes(&e.is_threadlocal) ++ asBytes(&e.is_dll_import) ++
|
||||
asBytes(&e.relocation) ++
|
||||
asBytes(&e.is_const) ++ asBytes(&e.alignment) ++ asBytes(&e.@"addrspace") ++
|
||||
asBytes(&e.zir_index)),
|
||||
};
|
||||
}
|
||||
@@ -2928,21 +2932,22 @@ pub const Key = union(enum) {
|
||||
|
||||
.variable => |a_info| {
|
||||
const b_info = b.variable;
|
||||
return a_info.owner_nav == b_info.owner_nav and
|
||||
a_info.ty == b_info.ty and
|
||||
return a_info.ty == b_info.ty and
|
||||
a_info.init == b_info.init and
|
||||
a_info.is_threadlocal == b_info.is_threadlocal and
|
||||
a_info.is_weak_linkage == b_info.is_weak_linkage;
|
||||
a_info.owner_nav == b_info.owner_nav and
|
||||
a_info.is_threadlocal == b_info.is_threadlocal;
|
||||
},
|
||||
.@"extern" => |a_info| {
|
||||
const b_info = b.@"extern";
|
||||
return a_info.name == b_info.name and
|
||||
a_info.ty == b_info.ty and
|
||||
a_info.lib_name == b_info.lib_name and
|
||||
a_info.is_const == b_info.is_const and
|
||||
a_info.linkage == b_info.linkage and
|
||||
a_info.visibility == b_info.visibility and
|
||||
a_info.is_threadlocal == b_info.is_threadlocal and
|
||||
a_info.is_weak_linkage == b_info.is_weak_linkage and
|
||||
a_info.is_dll_import == b_info.is_dll_import and
|
||||
a_info.relocation == b_info.relocation and
|
||||
a_info.is_const == b_info.is_const and
|
||||
a_info.alignment == b_info.alignment and
|
||||
a_info.@"addrspace" == b_info.@"addrspace" and
|
||||
a_info.zir_index == b_info.zir_index;
|
||||
@@ -4889,6 +4894,7 @@ pub const Index = enum(u32) {
|
||||
float_c_longdouble_f128: struct { data: *Float128 },
|
||||
float_comptime_float: struct { data: *Float128 },
|
||||
variable: struct { data: *Tag.Variable },
|
||||
threadlocal_variable: struct { data: *Tag.Variable },
|
||||
@"extern": struct { data: *Tag.Extern },
|
||||
func_decl: struct {
|
||||
const @"data.analysis.inferred_error_set" = opaque {};
|
||||
@@ -5548,6 +5554,9 @@ pub const Tag = enum(u8) {
|
||||
/// A global variable.
|
||||
/// data is extra index to Variable.
|
||||
variable,
|
||||
/// A global threadlocal variable.
|
||||
/// data is extra index to Variable.
|
||||
threadlocal_variable,
|
||||
/// An extern function or variable.
|
||||
/// data is extra index to Extern.
|
||||
/// Some parts of the key are stored in `owner_nav`.
|
||||
@@ -5863,6 +5872,7 @@ pub const Tag = enum(u8) {
|
||||
.float_c_longdouble_f128 = .{ .summary = .@"@as(c_longdouble, {.payload%value})", .payload = f128 },
|
||||
.float_comptime_float = .{ .summary = .@"{.payload%value}", .payload = f128 },
|
||||
.variable = .{ .summary = .@"{.payload.owner_nav.fqn%summary#\"}", .payload = Variable },
|
||||
.threadlocal_variable = .{ .summary = .@"{.payload.owner_nav.fqn%summary#\"}", .payload = Variable },
|
||||
.@"extern" = .{ .summary = .@"{.payload.owner_nav.fqn%summary#\"}", .payload = Extern },
|
||||
.func_decl = .{
|
||||
.summary = .@"{.payload.owner_nav.fqn%summary#\"}",
|
||||
@@ -5913,24 +5923,24 @@ pub const Tag = enum(u8) {
|
||||
/// May be `none`.
|
||||
init: Index,
|
||||
owner_nav: Nav.Index,
|
||||
flags: Flags,
|
||||
|
||||
pub const Flags = packed struct(u32) {
|
||||
is_const: bool,
|
||||
is_threadlocal: bool,
|
||||
is_weak_linkage: bool,
|
||||
is_dll_import: bool,
|
||||
_: u28 = 0,
|
||||
};
|
||||
};
|
||||
|
||||
pub const Extern = struct {
|
||||
// name, alignment, addrspace come from `owner_nav`.
|
||||
// name, is_const, alignment, addrspace come from `owner_nav`.
|
||||
ty: Index,
|
||||
lib_name: OptionalNullTerminatedString,
|
||||
flags: Variable.Flags,
|
||||
flags: Flags,
|
||||
owner_nav: Nav.Index,
|
||||
zir_index: TrackedInst.Index,
|
||||
|
||||
pub const Flags = packed struct(u32) {
|
||||
linkage: std.builtin.GlobalLinkage,
|
||||
visibility: std.builtin.SymbolVisibility,
|
||||
is_threadlocal: bool,
|
||||
is_dll_import: bool,
|
||||
relocation: std.builtin.ExternOptions.Relocation,
|
||||
_: u25 = 0,
|
||||
};
|
||||
};
|
||||
|
||||
/// Trailing:
|
||||
@@ -7248,14 +7258,17 @@ pub fn indexToKey(ip: *const InternPool, index: Index) Key {
|
||||
.ty = .comptime_float_type,
|
||||
.storage = .{ .f128 = extraData(unwrapped_index.getExtra(ip), Float128, data).get() },
|
||||
} },
|
||||
.variable => {
|
||||
.variable, .threadlocal_variable => {
|
||||
const extra = extraData(unwrapped_index.getExtra(ip), Tag.Variable, data);
|
||||
return .{ .variable = .{
|
||||
.ty = extra.ty,
|
||||
.init = extra.init,
|
||||
.owner_nav = extra.owner_nav,
|
||||
.is_threadlocal = extra.flags.is_threadlocal,
|
||||
.is_weak_linkage = extra.flags.is_weak_linkage,
|
||||
.is_threadlocal = switch (item.tag) {
|
||||
else => unreachable,
|
||||
.variable => false,
|
||||
.threadlocal_variable => true,
|
||||
},
|
||||
} };
|
||||
},
|
||||
.@"extern" => {
|
||||
@@ -7265,10 +7278,12 @@ pub fn indexToKey(ip: *const InternPool, index: Index) Key {
|
||||
.name = nav.name,
|
||||
.ty = extra.ty,
|
||||
.lib_name = extra.lib_name,
|
||||
.is_const = extra.flags.is_const,
|
||||
.linkage = extra.flags.linkage,
|
||||
.visibility = extra.flags.visibility,
|
||||
.is_threadlocal = extra.flags.is_threadlocal,
|
||||
.is_weak_linkage = extra.flags.is_weak_linkage,
|
||||
.is_dll_import = extra.flags.is_dll_import,
|
||||
.relocation = extra.flags.relocation,
|
||||
.is_const = nav.status.fully_resolved.is_const,
|
||||
.alignment = nav.status.fully_resolved.alignment,
|
||||
.@"addrspace" = nav.status.fully_resolved.@"addrspace",
|
||||
.zir_index = extra.zir_index,
|
||||
@@ -7895,17 +7910,14 @@ pub fn get(ip: *InternPool, gpa: Allocator, tid: Zcu.PerThread.Id, key: Key) All
|
||||
const has_init = variable.init != .none;
|
||||
if (has_init) assert(variable.ty == ip.typeOf(variable.init));
|
||||
items.appendAssumeCapacity(.{
|
||||
.tag = .variable,
|
||||
.tag = switch (variable.is_threadlocal) {
|
||||
false => .variable,
|
||||
true => .threadlocal_variable,
|
||||
},
|
||||
.data = try addExtra(extra, Tag.Variable{
|
||||
.ty = variable.ty,
|
||||
.init = variable.init,
|
||||
.owner_nav = variable.owner_nav,
|
||||
.flags = .{
|
||||
.is_const = false,
|
||||
.is_threadlocal = variable.is_threadlocal,
|
||||
.is_weak_linkage = variable.is_weak_linkage,
|
||||
.is_dll_import = false,
|
||||
},
|
||||
}),
|
||||
});
|
||||
},
|
||||
@@ -9128,6 +9140,7 @@ pub fn getExtern(
|
||||
.name = key.name,
|
||||
.fqn = key.name,
|
||||
.val = extern_index,
|
||||
.is_const = key.is_const,
|
||||
.alignment = key.alignment,
|
||||
.@"linksection" = .none,
|
||||
.@"addrspace" = key.@"addrspace",
|
||||
@@ -9136,10 +9149,11 @@ pub fn getExtern(
|
||||
.ty = key.ty,
|
||||
.lib_name = key.lib_name,
|
||||
.flags = .{
|
||||
.is_const = key.is_const,
|
||||
.linkage = key.linkage,
|
||||
.visibility = key.visibility,
|
||||
.is_threadlocal = key.is_threadlocal,
|
||||
.is_weak_linkage = key.is_weak_linkage,
|
||||
.is_dll_import = key.is_dll_import,
|
||||
.relocation = key.relocation,
|
||||
},
|
||||
.zir_index = key.zir_index,
|
||||
.owner_nav = owner_nav,
|
||||
@@ -9714,6 +9728,7 @@ fn finishFuncInstance(
|
||||
.name = nav_name,
|
||||
.fqn = try ip.namespacePtr(fn_namespace).internFullyQualifiedName(ip, gpa, tid, nav_name),
|
||||
.val = func_index,
|
||||
.is_const = fn_owner_nav.status.fully_resolved.is_const,
|
||||
.alignment = fn_owner_nav.status.fully_resolved.alignment,
|
||||
.@"linksection" = fn_owner_nav.status.fully_resolved.@"linksection",
|
||||
.@"addrspace" = fn_owner_nav.status.fully_resolved.@"addrspace",
|
||||
@@ -10300,13 +10315,13 @@ fn addExtraAssumeCapacity(extra: Local.Extra.Mutable, item: anytype) u32 {
|
||||
u32,
|
||||
i32,
|
||||
FuncAnalysis,
|
||||
Tag.Extern.Flags,
|
||||
Tag.TypePointer.Flags,
|
||||
Tag.TypeFunction.Flags,
|
||||
Tag.TypePointer.PackedOffset,
|
||||
Tag.TypeUnion.Flags,
|
||||
Tag.TypeStruct.Flags,
|
||||
Tag.TypeStructPacked.Flags,
|
||||
Tag.Variable.Flags,
|
||||
=> @bitCast(@field(item, field.name)),
|
||||
|
||||
else => @compileError("bad field type: " ++ @typeName(field.type)),
|
||||
@@ -10361,13 +10376,13 @@ fn extraDataTrail(extra: Local.Extra, comptime T: type, index: u32) struct { dat
|
||||
|
||||
u32,
|
||||
i32,
|
||||
Tag.Extern.Flags,
|
||||
Tag.TypePointer.Flags,
|
||||
Tag.TypeFunction.Flags,
|
||||
Tag.TypePointer.PackedOffset,
|
||||
Tag.TypeUnion.Flags,
|
||||
Tag.TypeStruct.Flags,
|
||||
Tag.TypeStructPacked.Flags,
|
||||
Tag.Variable.Flags,
|
||||
FuncAnalysis,
|
||||
=> @bitCast(extra_item),
|
||||
|
||||
@@ -11162,7 +11177,7 @@ fn dumpStatsFallible(ip: *const InternPool, arena: Allocator) anyerror!void {
|
||||
.float_c_longdouble_f80 => @sizeOf(Float80),
|
||||
.float_c_longdouble_f128 => @sizeOf(Float128),
|
||||
.float_comptime_float => @sizeOf(Float128),
|
||||
.variable => @sizeOf(Tag.Variable),
|
||||
.variable, .threadlocal_variable => @sizeOf(Tag.Variable),
|
||||
.@"extern" => @sizeOf(Tag.Extern),
|
||||
.func_decl => @sizeOf(Tag.FuncDecl),
|
||||
.func_instance => b: {
|
||||
@@ -11282,6 +11297,7 @@ fn dumpAllFallible(ip: *const InternPool) anyerror!void {
|
||||
.float_c_longdouble_f128,
|
||||
.float_comptime_float,
|
||||
.variable,
|
||||
.threadlocal_variable,
|
||||
.@"extern",
|
||||
.func_decl,
|
||||
.func_instance,
|
||||
@@ -11414,6 +11430,7 @@ pub fn createNav(
|
||||
name: NullTerminatedString,
|
||||
fqn: NullTerminatedString,
|
||||
val: InternPool.Index,
|
||||
is_const: bool,
|
||||
alignment: Alignment,
|
||||
@"linksection": OptionalNullTerminatedString,
|
||||
@"addrspace": std.builtin.AddressSpace,
|
||||
@@ -11430,6 +11447,7 @@ pub fn createNav(
|
||||
.analysis = null,
|
||||
.status = .{ .fully_resolved = .{
|
||||
.val = opts.val,
|
||||
.is_const = opts.is_const,
|
||||
.alignment = opts.alignment,
|
||||
.@"linksection" = opts.@"linksection",
|
||||
.@"addrspace" = opts.@"addrspace",
|
||||
@@ -11482,10 +11500,10 @@ pub fn resolveNavType(
|
||||
nav: Nav.Index,
|
||||
resolved: struct {
|
||||
type: InternPool.Index,
|
||||
is_const: bool,
|
||||
alignment: Alignment,
|
||||
@"linksection": OptionalNullTerminatedString,
|
||||
@"addrspace": std.builtin.AddressSpace,
|
||||
is_const: bool,
|
||||
is_threadlocal: bool,
|
||||
is_extern_decl: bool,
|
||||
},
|
||||
@@ -11512,9 +11530,9 @@ pub fn resolveNavType(
|
||||
|
||||
var bits = nav_bits[unwrapped.index];
|
||||
bits.status = if (resolved.is_extern_decl) .type_resolved_extern_decl else .type_resolved;
|
||||
bits.is_const = resolved.is_const;
|
||||
bits.alignment = resolved.alignment;
|
||||
bits.@"addrspace" = resolved.@"addrspace";
|
||||
bits.is_const = resolved.is_const;
|
||||
bits.is_threadlocal = resolved.is_threadlocal;
|
||||
@atomicStore(Nav.Repr.Bits, &nav_bits[unwrapped.index], bits, .release);
|
||||
}
|
||||
@@ -11526,6 +11544,7 @@ pub fn resolveNavValue(
|
||||
nav: Nav.Index,
|
||||
resolved: struct {
|
||||
val: InternPool.Index,
|
||||
is_const: bool,
|
||||
alignment: Alignment,
|
||||
@"linksection": OptionalNullTerminatedString,
|
||||
@"addrspace": std.builtin.AddressSpace,
|
||||
@@ -11553,6 +11572,7 @@ pub fn resolveNavValue(
|
||||
|
||||
var bits = nav_bits[unwrapped.index];
|
||||
bits.status = .fully_resolved;
|
||||
bits.is_const = resolved.is_const;
|
||||
bits.alignment = resolved.alignment;
|
||||
bits.@"addrspace" = resolved.@"addrspace";
|
||||
@atomicStore(Nav.Repr.Bits, &nav_bits[unwrapped.index], bits, .release);
|
||||
@@ -12007,6 +12027,7 @@ pub fn typeOf(ip: *const InternPool, index: Index) Index {
|
||||
.error_union_error,
|
||||
.enum_tag,
|
||||
.variable,
|
||||
.threadlocal_variable,
|
||||
.@"extern",
|
||||
.func_decl,
|
||||
.func_instance,
|
||||
@@ -12391,6 +12412,7 @@ pub fn zigTypeTag(ip: *const InternPool, index: Index) std.builtin.TypeId {
|
||||
.float_c_longdouble_f128,
|
||||
.float_comptime_float,
|
||||
.variable,
|
||||
.threadlocal_variable,
|
||||
.@"extern",
|
||||
.func_decl,
|
||||
.func_instance,
|
||||
|
||||
Reference in New Issue
Block a user