Merge pull request #16875 from mlugg/astgen-rl-pass

AstGen: add result location analysis pass
This commit is contained in:
Andrew Kelley
2023-08-20 15:38:36 -07:00
committed by GitHub
13 changed files with 1430 additions and 1167 deletions

View File

@@ -515,6 +515,7 @@ set(ZIG_STAGE2_SOURCES
"${CMAKE_SOURCE_DIR}/lib/std/zig/tokenizer.zig"
"${CMAKE_SOURCE_DIR}/src/Air.zig"
"${CMAKE_SOURCE_DIR}/src/AstGen.zig"
"${CMAKE_SOURCE_DIR}/src/AstRlAnnotate.zig"
"${CMAKE_SOURCE_DIR}/src/Compilation.zig"
"${CMAKE_SOURCE_DIR}/src/Liveness.zig"
"${CMAKE_SOURCE_DIR}/src/Module.zig"

View File

@@ -370,10 +370,9 @@ fn render_cmake(
}
},
else => {
break :blk value;
},
else => {},
}
break :blk value;
};
if (booldefine) {

File diff suppressed because it is too large Load Diff

1088
src/AstRlAnnotate.zig Normal file

File diff suppressed because it is too large Load Diff

View File

@@ -1346,11 +1346,6 @@ fn analyzeBodyInner(
i += 1;
continue;
},
.store_to_block_ptr => {
try sema.zirStoreToBlockPtr(block, inst);
i += 1;
continue;
},
.store_to_inferred_ptr => {
try sema.zirStoreToInferredPtr(block, inst);
i += 1;
@@ -5269,35 +5264,6 @@ fn addDeclaredHereNote(sema: *Sema, parent: *Module.ErrorMsg, decl_ty: Type) !vo
try mod.errNoteNonLazy(src_loc, parent, "{s} declared here", .{category});
}
fn zirStoreToBlockPtr(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!void {
const tracy = trace(@src());
defer tracy.end();
const bin_inst = sema.code.instructions.items(.data)[inst].bin;
const ptr = sema.inst_map.get(Zir.refToIndex(bin_inst.lhs).?) orelse {
// This is an elided instruction, but AstGen was unable to omit it.
return;
};
const operand = try sema.resolveInst(bin_inst.rhs);
const src: LazySrcLoc = sema.src;
blk: {
const ptr_inst = Air.refToIndex(ptr) orelse break :blk;
switch (sema.air_instructions.items(.tag)[ptr_inst]) {
.inferred_alloc_comptime => {
const iac = &sema.air_instructions.items(.data)[ptr_inst].inferred_alloc_comptime;
return sema.storeToInferredAllocComptime(block, src, operand, iac);
},
.inferred_alloc => {
const ia = sema.unresolved_inferred_allocs.getPtr(ptr_inst).?;
return sema.storeToInferredAlloc(block, ptr, operand, ia);
},
else => break :blk,
}
}
return sema.storePtr(block, src, ptr, operand);
}
fn zirStoreToInferredPtr(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!void {
const tracy = trace(@src());
defer tracy.end();

View File

@@ -602,20 +602,9 @@ pub const Inst = struct {
/// Same as `store` except provides a source location.
/// Uses the `pl_node` union field. Payload is `Bin`.
store_node,
/// This instruction is not really supposed to be emitted from AstGen; nevertheless it
/// is sometimes emitted due to deficiencies in AstGen. When Sema sees this instruction,
/// it must clean up after AstGen's mess by looking at various context clues and
/// then treating it as one of the following:
/// * no-op
/// * store_to_inferred_ptr
/// * store
/// Uses the `bin` union field with LHS as the pointer to store to.
store_to_block_ptr,
/// Same as `store` but the type of the value being stored will be used to infer
/// the pointer type.
/// Uses the `bin` union field - Astgen.zig depends on the ability to change
/// the tag of an instruction from `store_to_block_ptr` to `store_to_inferred_ptr`
/// without changing the data.
/// Uses the `bin` union field.
store_to_inferred_ptr,
/// String Literal. Makes an anonymous Decl and then takes a pointer to it.
/// Uses the `str` union field.
@@ -1109,7 +1098,6 @@ pub const Inst = struct {
.shr,
.store,
.store_node,
.store_to_block_ptr,
.store_to_inferred_ptr,
.str,
.sub,
@@ -1295,7 +1283,6 @@ pub const Inst = struct {
.atomic_store,
.store,
.store_node,
.store_to_block_ptr,
.store_to_inferred_ptr,
.resolve_inferred_alloc,
.validate_array_init_ty,
@@ -1667,7 +1654,6 @@ pub const Inst = struct {
.slice_length = .pl_node,
.store = .bin,
.store_node = .pl_node,
.store_to_block_ptr = .bin,
.store_to_inferred_ptr = .bin,
.str = .str,
.negate = .un_node,

View File

@@ -4285,7 +4285,7 @@ fn airBlock(f: *Function, inst: Air.Inst.Index) !CValue {
const writer = f.object.writer();
const inst_ty = f.typeOfIndex(inst);
const result = if (inst_ty.ip_index != .void_type and !f.liveness.isUnused(inst))
const result = if (inst_ty.hasRuntimeBitsIgnoreComptime(mod) and !f.liveness.isUnused(inst))
try f.allocLocal(inst, inst_ty)
else
.none;

View File

@@ -10092,8 +10092,8 @@ fn vectorTypeAssumeCapacity(
.data = self.addTypeExtraAssumeCapacity(data),
});
if (self.useLibLlvm()) self.llvm.types.appendAssumeCapacity(switch (kind) {
.normal => llvm.Type.vectorType,
.scalable => llvm.Type.scalableVectorType,
.normal => &llvm.Type.vectorType,
.scalable => &llvm.Type.scalableVectorType,
}(child.toLlvm(self), @intCast(len)));
}
return @enumFromInt(gop.index);
@@ -11274,8 +11274,8 @@ fn gepConstAssumeCapacity(
for (llvm_indices, indices) |*llvm_index, index| llvm_index.* = index.toLlvm(self);
self.llvm.constants.appendAssumeCapacity(switch (kind) {
.normal => llvm.Type.constGEP,
.inbounds => llvm.Type.constInBoundsGEP,
.normal => &llvm.Type.constGEP,
.inbounds => &llvm.Type.constInBoundsGEP,
}(ty.toLlvm(self), base.toLlvm(self), llvm_indices.ptr, @intCast(llvm_indices.len)));
}
}

View File

@@ -145,7 +145,6 @@ const Writer = struct {
switch (tag) {
.as,
.store,
.store_to_block_ptr,
.store_to_inferred_ptr,
=> try self.writeBin(stream, inst),

View File

@@ -1176,10 +1176,10 @@ typedef signed __int128 zig_i128;
#if zig_little_endian
typedef struct { zig_align(16) uint64_t lo; uint64_t hi; } zig_u128;
typedef struct { zig_align(16) uint64_t lo; int64_t hi; } zig_i128;
typedef struct { zig_align(16) uint64_t lo; int64_t hi; } zig_i128;
#else
typedef struct { zig_align(16) uint64_t hi; uint64_t lo; } zig_u128;
typedef struct { zig_align(16) int64_t hi; uint64_t lo; } zig_i128;
typedef struct { zig_align(16) int64_t hi; uint64_t lo; } zig_i128;
#endif
#define zig_make_u128(hi, lo) ((zig_u128){ .h##i = (hi), .l##o = (lo) })
@@ -3197,11 +3197,9 @@ zig_convert_builtin(zig_compiler_rt_f16, zig_f16, trunc, zig_f64,
zig_convert_builtin(zig_f16, zig_f16, trunc, zig_f80, zig_f80, 2)
zig_convert_builtin(zig_f16, zig_f16, trunc, zig_f128, zig_f128, 2)
zig_convert_builtin(zig_f32, zig_f32, extend, zig_compiler_rt_f16, zig_f16, 2)
zig_convert_builtin(zig_f32, zig_f32, trunc, zig_f64, zig_f64, 2)
zig_convert_builtin(zig_f32, zig_f32, trunc, zig_f80, zig_f80, 2)
zig_convert_builtin(zig_f32, zig_f32, trunc, zig_f128, zig_f128, 2)
zig_convert_builtin(zig_f64, zig_f64, extend, zig_compiler_rt_f16, zig_f16, 2)
zig_convert_builtin(zig_f64, zig_f64, extend, zig_f32, zig_f32, 2)
zig_convert_builtin(zig_f64, zig_f64, trunc, zig_f80, zig_f80, 2)
zig_convert_builtin(zig_f64, zig_f64, trunc, zig_f128, zig_f128, 2)
zig_convert_builtin(zig_f80, zig_f80, extend, zig_f16, zig_f16, 2)
@@ -3213,6 +3211,21 @@ zig_convert_builtin(zig_f128, zig_f128, extend, zig_f32,
zig_convert_builtin(zig_f128, zig_f128, extend, zig_f64, zig_f64, 2)
zig_convert_builtin(zig_f128, zig_f128, extend, zig_f80, zig_f80, 2)
#ifdef __ARM_EABI__
zig_extern zig_callconv(pcs("aapcs")) zig_f32 __aeabi_d2f(zig_f64);
static inline zig_f32 zig_truncdfsf(zig_f64 arg) { return __aeabi_d2f(arg); }
zig_extern zig_callconv(pcs("aapcs")) zig_f64 __aeabi_f2d(zig_f32);
static inline zig_f64 zig_extendsfdf(zig_f32 arg) { return __aeabi_f2d(arg); }
#else /* __ARM_EABI__ */
zig_convert_builtin(zig_f32, zig_f32, trunc, zig_f64, zig_f64, 2)
zig_convert_builtin(zig_f64, zig_f64, extend, zig_f32, zig_f32, 2)
#endif /* __ARM_EABI__ */
#define zig_float_negate_builtin_0(w, c, sb) \
zig_expand_concat(zig_xor_, zig_repr_f##w)(arg, zig_make_f##w(-0x0.0p0, c sb))
#define zig_float_negate_builtin_1(w, c, sb) -arg
@@ -3255,17 +3268,11 @@ zig_float_negate_builtin(128, zig_make_u128, (UINT64_C(1) << 63, UINT64_C(0)))
return lhs operator rhs; \
}
#define zig_float_builtins(w) \
zig_convert_builtin( int32_t, int32_t, fix, zig_f##w, zig_f##w, ) \
zig_convert_builtin(uint32_t, uint32_t, fixuns, zig_f##w, zig_f##w, ) \
#define zig_common_float_builtins(w) \
zig_convert_builtin( int64_t, int64_t, fix, zig_f##w, zig_f##w, ) \
zig_convert_builtin(uint64_t, uint64_t, fixuns, zig_f##w, zig_f##w, ) \
zig_convert_builtin(zig_i128, zig_i128, fix, zig_f##w, zig_f##w, ) \
zig_convert_builtin(zig_u128, zig_u128, fixuns, zig_f##w, zig_f##w, ) \
zig_convert_builtin(zig_f##w, zig_f##w, float, int32_t, int32_t, ) \
zig_convert_builtin(zig_f##w, zig_f##w, floatun, uint32_t, uint32_t, ) \
zig_convert_builtin(zig_f##w, zig_f##w, float, int64_t, int64_t, ) \
zig_convert_builtin(zig_f##w, zig_f##w, floatun, uint64_t, uint64_t, ) \
zig_convert_builtin(zig_f##w, zig_f##w, float, zig_i128, zig_i128, ) \
zig_convert_builtin(zig_f##w, zig_f##w, floatun, zig_u128, zig_u128, ) \
zig_expand_concat(zig_float_less_builtin_, zig_has_f##w)(f##w, cmp) \
@@ -3309,12 +3316,68 @@ zig_float_negate_builtin(128, zig_make_u128, (UINT64_C(1) << 63, UINT64_C(0)))
static inline zig_f##w zig_mod_f##w(zig_f##w lhs, zig_f##w rhs) { \
return zig_sub_f##w(lhs, zig_mul_f##w(zig_div_floor_f##w(lhs, rhs), rhs)); \
}
zig_common_float_builtins(16)
zig_common_float_builtins(32)
zig_common_float_builtins(64)
zig_common_float_builtins(80)
zig_common_float_builtins(128)
#define zig_float_builtins(w) \
zig_convert_builtin( int32_t, int32_t, fix, zig_f##w, zig_f##w, ) \
zig_convert_builtin(uint32_t, uint32_t, fixuns, zig_f##w, zig_f##w, ) \
zig_convert_builtin(uint64_t, uint64_t, fixuns, zig_f##w, zig_f##w, ) \
zig_convert_builtin(zig_f##w, zig_f##w, float, int32_t, int32_t, ) \
zig_convert_builtin(zig_f##w, zig_f##w, floatun, uint32_t, uint32_t, ) \
zig_convert_builtin(zig_f##w, zig_f##w, floatun, uint64_t, uint64_t, )
zig_float_builtins(16)
zig_float_builtins(32)
zig_float_builtins(64)
zig_float_builtins(80)
zig_float_builtins(128)
#ifdef __ARM_EABI__
zig_extern zig_callconv(pcs("aapcs")) int32_t __aeabi_f2iz(zig_f32);
static inline int32_t zig_fixsfsi(zig_f32 arg) { return __aeabi_f2iz(arg); }
zig_extern zig_callconv(pcs("aapcs")) uint32_t __aeabi_f2uiz(zig_f32);
static inline uint32_t zig_fixunssfsi(zig_f32 arg) { return __aeabi_f2uiz(arg); }
zig_extern zig_callconv(pcs("aapcs")) uint64_t __aeabi_f2ulz(zig_f32);
static inline uint64_t zig_fixunssfdi(zig_f32 arg) { return __aeabi_f2ulz(arg); }
zig_extern zig_callconv(pcs("aapcs")) zig_f32 __aeabi_i2f(int32_t);
static inline zig_f32 zig_floatsisf(int32_t arg) { return __aeabi_i2f(arg); }
zig_extern zig_callconv(pcs("aapcs")) zig_f32 __aeabi_ui2f(uint32_t);
static inline zig_f32 zig_floatunsisf(uint32_t arg) { return __aeabi_ui2f(arg); }
zig_extern zig_callconv(pcs("aapcs")) zig_f32 __aeabi_ul2f(uint64_t);
static inline zig_f32 zig_floatundisf(uint64_t arg) { return __aeabi_ul2f(arg); }
zig_extern zig_callconv(pcs("aapcs")) int32_t __aeabi_d2iz(zig_f64);
static inline int32_t zig_fixdfsi(zig_f64 arg) { return __aeabi_d2iz(arg); }
zig_extern zig_callconv(pcs("aapcs")) uint32_t __aeabi_d2uiz(zig_f64);
static inline uint32_t zig_fixunsdfsi(zig_f64 arg) { return __aeabi_d2uiz(arg); }
zig_extern zig_callconv(pcs("aapcs")) uint64_t __aeabi_d2ulz(zig_f64);
static inline uint64_t zig_fixunsdfdi(zig_f64 arg) { return __aeabi_d2ulz(arg); }
zig_extern zig_callconv(pcs("aapcs")) zig_f64 __aeabi_i2d(int32_t);
static inline zig_f64 zig_floatsidf(int32_t arg) { return __aeabi_i2d(arg); }
zig_extern zig_callconv(pcs("aapcs")) zig_f64 __aeabi_ui2d(uint32_t);
static inline zig_f64 zig_floatunsidf(uint32_t arg) { return __aeabi_ui2d(arg); }
zig_extern zig_callconv(pcs("aapcs")) zig_f64 __aeabi_ul2d(uint64_t);
static inline zig_f64 zig_floatundidf(uint64_t arg) { return __aeabi_ul2d(arg); }
#else /* __ARM_EABI__ */
zig_float_builtins(32)
zig_float_builtins(64)
#endif /* __ARM_EABI__ */
/* ============================ Atomics Support ============================= */
/* Note that atomics should be implemented as macros because most

Binary file not shown.

View File

@@ -29,4 +29,4 @@ export fn f4() void {
// :2:22: error: expected type 'usize', found 'void'
// :7:9: error: expected type 'usize', found 'void'
// :14:9: error: expected type 'usize', found 'void'
// :19:27: error: expected type 'usize', found 'void'
// :20:9: error: expected type 'usize', found 'void'

View File

@@ -34,8 +34,7 @@ export fn entry() void {
// backend=stage2
// target=native
//
// :2:20: error: incompatible types: 'i32' and 'void'
// :2:30: note: type 'i32' here
// :2:20: error: expected type 'i32', found 'void'
// :8:15: error: incompatible types: 'i32' and 'void'
// :8:25: note: type 'i32' here
// :16:16: error: expected type 'tmp.h.T', found 'void'