mirror of
https://github.com/ziglang/zig.git
synced 2026-01-11 18:05:11 +00:00
Merge pull request #11155 from ziglang/stage2-float-fixes
stage2 float fixes
This commit is contained in:
commit
5919b10048
@ -2515,13 +2515,14 @@ test "null terminated array" {
|
||||
|
||||
{#header_open|Vectors#}
|
||||
<p>
|
||||
A vector is a group of booleans, {#link|Integers#}, {#link|Floats#}, or {#link|Pointers#} which are operated on
|
||||
in parallel using SIMD instructions. Vector types are created with the builtin function {#link|@Type#},
|
||||
or using the shorthand function {#syntax#}std.meta.Vector{#endsyntax#}.
|
||||
A vector is a group of booleans, {#link|Integers#}, {#link|Floats#}, or
|
||||
{#link|Pointers#} which are operated on in parallel, using SIMD instructions if possible.
|
||||
Vector types are created with the builtin function {#link|@Vector#}.
|
||||
</p>
|
||||
<p>
|
||||
Vectors support the same builtin operators as their underlying base types. These operations are performed
|
||||
element-wise, and return a vector of the same length as the input vectors. This includes:
|
||||
Vectors support the same builtin operators as their underlying base types.
|
||||
These operations are performed element-wise, and return a vector of the same length
|
||||
as the input vectors. This includes:
|
||||
</p>
|
||||
<ul>
|
||||
<li>Arithmetic ({#syntax#}+{#endsyntax#}, {#syntax#}-{#endsyntax#}, {#syntax#}/{#endsyntax#}, {#syntax#}*{#endsyntax#},
|
||||
@ -2532,10 +2533,11 @@ test "null terminated array" {
|
||||
<li>Comparison operators ({#syntax#}<{#endsyntax#}, {#syntax#}>{#endsyntax#}, {#syntax#}=={#endsyntax#}, etc.)</li>
|
||||
</ul>
|
||||
<p>
|
||||
It is prohibited to use a math operator on a mixture of scalars (individual numbers) and vectors.
|
||||
Zig provides the {#link|@splat#} builtin to easily convert from scalars to vectors, and it supports {#link|@reduce#}
|
||||
and array indexing syntax to convert from vectors to scalars. Vectors also support assignment to and from
|
||||
fixed-length arrays with comptime known length.
|
||||
It is prohibited to use a math operator on a mixture of scalars (individual numbers)
|
||||
and vectors. Zig provides the {#link|@splat#} builtin to easily convert from scalars
|
||||
to vectors, and it supports {#link|@reduce#} and array indexing syntax to convert
|
||||
from vectors to scalars. Vectors also support assignment to and from fixed-length
|
||||
arrays with comptime known length.
|
||||
</p>
|
||||
<p>
|
||||
For rearranging elements within and between vectors, Zig provides the {#link|@shuffle#} and {#link|@select#} functions.
|
||||
@ -2550,16 +2552,14 @@ test "null terminated array" {
|
||||
</p>
|
||||
{#code_begin|test|vector_example#}
|
||||
const std = @import("std");
|
||||
const Vector = std.meta.Vector;
|
||||
const expectEqual = std.testing.expectEqual;
|
||||
|
||||
test "Basic vector usage" {
|
||||
// Vectors have a compile-time known length and base type,
|
||||
// and can be assigned to using array literal syntax
|
||||
const a: Vector(4, i32) = [_]i32{ 1, 2, 3, 4 };
|
||||
const b: Vector(4, i32) = [_]i32{ 5, 6, 7, 8 };
|
||||
// Vectors have a compile-time known length and base type.
|
||||
const a = @Vector(4, i32){ 1, 2, 3, 4 };
|
||||
const b = @Vector(4, i32){ 5, 6, 7, 8 };
|
||||
|
||||
// Math operations take place element-wise
|
||||
// Math operations take place element-wise.
|
||||
const c = a + b;
|
||||
|
||||
// Individual vector elements can be accessed using array indexing syntax.
|
||||
@ -2572,19 +2572,19 @@ test "Basic vector usage" {
|
||||
test "Conversion between vectors, arrays, and slices" {
|
||||
// Vectors and fixed-length arrays can be automatically assigned back and forth
|
||||
var arr1: [4]f32 = [_]f32{ 1.1, 3.2, 4.5, 5.6 };
|
||||
var vec: Vector(4, f32) = arr1;
|
||||
var vec: @Vector(4, f32) = arr1;
|
||||
var arr2: [4]f32 = vec;
|
||||
try expectEqual(arr1, arr2);
|
||||
|
||||
// You can also assign from a slice with comptime-known length to a vector using .*
|
||||
const vec2: Vector(2, f32) = arr1[1..3].*;
|
||||
const vec2: @Vector(2, f32) = arr1[1..3].*;
|
||||
|
||||
var slice: []const f32 = &arr1;
|
||||
var offset: u32 = 1;
|
||||
// To extract a comptime-known length from a runtime-known offset,
|
||||
// first extract a new slice from the starting offset, then an array of
|
||||
// comptime known length
|
||||
const vec3: Vector(2, f32) = slice[offset..][0..2].*;
|
||||
const vec3: @Vector(2, f32) = slice[offset..][0..2].*;
|
||||
try expectEqual(slice[offset], vec2[0]);
|
||||
try expectEqual(slice[offset + 1], vec2[1]);
|
||||
try expectEqual(vec2, vec3);
|
||||
@ -9084,7 +9084,7 @@ pub const PrefetchOptions = struct {
|
||||
{#header_close#}
|
||||
|
||||
{#header_open|@select#}
|
||||
<pre>{#syntax#}@select(comptime T: type, pred: std.meta.Vector(len, bool), a: std.meta.Vector(len, T), b: std.meta.Vector(len, T)) std.meta.Vector(len, T){#endsyntax#}</pre>
|
||||
<pre>{#syntax#}@select(comptime T: type, pred: @Vector(len, bool), a: @Vector(len, T), b: @Vector(len, T)) @Vector(len, T){#endsyntax#}</pre>
|
||||
<p>
|
||||
Selects values element-wise from {#syntax#}a{#endsyntax#} or {#syntax#}b{#endsyntax#} based on {#syntax#}pred{#endsyntax#}. If {#syntax#}pred[i]{#endsyntax#} is {#syntax#}true{#endsyntax#}, the corresponding element in the result will be {#syntax#}a[i]{#endsyntax#} and otherwise {#syntax#}b[i]{#endsyntax#}.
|
||||
</p>
|
||||
@ -9252,7 +9252,7 @@ test "@setRuntimeSafety" {
|
||||
{#header_close#}
|
||||
|
||||
{#header_open|@shuffle#}
|
||||
<pre>{#syntax#}@shuffle(comptime E: type, a: std.meta.Vector(a_len, E), b: std.meta.Vector(b_len, E), comptime mask: std.meta.Vector(mask_len, i32)) std.meta.Vector(mask_len, E){#endsyntax#}</pre>
|
||||
<pre>{#syntax#}@shuffle(comptime E: type, a: @Vector(a_len, E), b: @Vector(b_len, E), comptime mask: @Vector(mask_len, i32)) @Vector(mask_len, E){#endsyntax#}</pre>
|
||||
<p>
|
||||
Constructs a new {#link|vector|Vectors#} by selecting elements from {#syntax#}a{#endsyntax#} and
|
||||
{#syntax#}b{#endsyntax#} based on {#syntax#}mask{#endsyntax#}.
|
||||
@ -9287,22 +9287,21 @@ test "@setRuntimeSafety" {
|
||||
</p>
|
||||
{#code_begin|test|vector_shuffle#}
|
||||
const std = @import("std");
|
||||
const Vector = std.meta.Vector;
|
||||
const expect = std.testing.expect;
|
||||
|
||||
test "vector @shuffle" {
|
||||
const a: Vector(7, u8) = [_]u8{ 'o', 'l', 'h', 'e', 'r', 'z', 'w' };
|
||||
const b: Vector(4, u8) = [_]u8{ 'w', 'd', '!', 'x' };
|
||||
const a = @Vector(7, u8){ 'o', 'l', 'h', 'e', 'r', 'z', 'w' };
|
||||
const b = @Vector(4, u8){ 'w', 'd', '!', 'x' };
|
||||
|
||||
// To shuffle within a single vector, pass undefined as the second argument.
|
||||
// Notice that we can re-order, duplicate, or omit elements of the input vector
|
||||
const mask1: Vector(5, i32) = [_]i32{ 2, 3, 1, 1, 0 };
|
||||
const res1: Vector(5, u8) = @shuffle(u8, a, undefined, mask1);
|
||||
const mask1 = @Vector(5, i32){ 2, 3, 1, 1, 0 };
|
||||
const res1: @Vector(5, u8) = @shuffle(u8, a, undefined, mask1);
|
||||
try expect(std.mem.eql(u8, &@as([5]u8, res1), "hello"));
|
||||
|
||||
// Combining two vectors
|
||||
const mask2: Vector(6, i32) = [_]i32{ -1, 0, 4, 1, -2, -3 };
|
||||
const res2: Vector(6, u8) = @shuffle(u8, a, b, mask2);
|
||||
const mask2 = @Vector(6, i32){ -1, 0, 4, 1, -2, -3 };
|
||||
const res2: @Vector(6, u8) = @shuffle(u8, a, b, mask2);
|
||||
try expect(std.mem.eql(u8, &@as([6]u8, res2), "world!"));
|
||||
}
|
||||
{#code_end#}
|
||||
@ -9329,7 +9328,7 @@ test "vector @shuffle" {
|
||||
{#header_close#}
|
||||
|
||||
{#header_open|@splat#}
|
||||
<pre>{#syntax#}@splat(comptime len: u32, scalar: anytype) std.meta.Vector(len, @TypeOf(scalar)){#endsyntax#}</pre>
|
||||
<pre>{#syntax#}@splat(comptime len: u32, scalar: anytype) @Vector(len, @TypeOf(scalar)){#endsyntax#}</pre>
|
||||
<p>
|
||||
Produces a vector of length {#syntax#}len{#endsyntax#} where each element is the value
|
||||
{#syntax#}scalar{#endsyntax#}:
|
||||
@ -9341,7 +9340,7 @@ const expect = std.testing.expect;
|
||||
test "vector @splat" {
|
||||
const scalar: u32 = 5;
|
||||
const result = @splat(4, scalar);
|
||||
comptime try expect(@TypeOf(result) == std.meta.Vector(4, u32));
|
||||
comptime try expect(@TypeOf(result) == @Vector(4, u32));
|
||||
try expect(std.mem.eql(u32, &@as([4]u32, result), &[_]u32{ 5, 5, 5, 5 }));
|
||||
}
|
||||
{#code_end#}
|
||||
@ -9381,10 +9380,10 @@ const std = @import("std");
|
||||
const expect = std.testing.expect;
|
||||
|
||||
test "vector @reduce" {
|
||||
const value: std.meta.Vector(4, i32) = [_]i32{ 1, -1, 1, -1 };
|
||||
const value = @Vector(4, i32){ 1, -1, 1, -1 };
|
||||
const result = value > @splat(4, @as(i32, 0));
|
||||
// result is { true, false, true, false };
|
||||
comptime try expect(@TypeOf(result) == std.meta.Vector(4, bool));
|
||||
comptime try expect(@TypeOf(result) == @Vector(4, bool));
|
||||
const is_all_true = @reduce(.And, result);
|
||||
comptime try expect(@TypeOf(is_all_true) == bool);
|
||||
try expect(is_all_true == false);
|
||||
@ -9743,6 +9742,12 @@ fn foo(comptime T: type, ptr: *T) T {
|
||||
{#syntax#}@unionInit{#endsyntax#} forwards its {#link|result location|Result Location Semantics#} to {#syntax#}init_expr{#endsyntax#}.
|
||||
</p>
|
||||
{#header_close#}
|
||||
|
||||
|
||||
{#header_open|@Vector#}
|
||||
<pre>{#syntax#}@Vector(len: comptime_int, Element: type) type{#endsyntax#}</pre>
|
||||
<p>Creates {#link|Vectors#}.</p>
|
||||
{#header_close#}
|
||||
{#header_close#}
|
||||
|
||||
{#header_open|Build Mode#}
|
||||
|
||||
@ -20,6 +20,10 @@ pub fn round(x: anytype) @TypeOf(x) {
|
||||
f32 => round32(x),
|
||||
f64 => round64(x),
|
||||
f128 => round128(x),
|
||||
|
||||
// TODO this is not correct for some targets
|
||||
c_longdouble => @floatCast(c_longdouble, round128(x)),
|
||||
|
||||
else => @compileError("round not implemented for " ++ @typeName(T)),
|
||||
};
|
||||
}
|
||||
|
||||
@ -930,6 +930,7 @@ test "std.meta.Float" {
|
||||
try testing.expectEqual(f128, Float(128));
|
||||
}
|
||||
|
||||
/// Deprecated. Use `@Vector`.
|
||||
pub fn Vector(comptime len: u32, comptime child: type) type {
|
||||
return @Type(.{
|
||||
.Vector = .{
|
||||
|
||||
@ -421,7 +421,7 @@ pub fn MultiArrayList(comptime S: type) type {
|
||||
}
|
||||
|
||||
fn capacityInBytes(capacity: usize) usize {
|
||||
const sizes_vector: std.meta.Vector(sizes.bytes.len, usize) = sizes.bytes;
|
||||
const sizes_vector: @Vector(sizes.bytes.len, usize) = sizes.bytes;
|
||||
const capacity_vector = @splat(sizes.bytes.len, capacity);
|
||||
return @reduce(.Add, capacity_vector * sizes_vector);
|
||||
}
|
||||
|
||||
@ -98,6 +98,7 @@ comptime {
|
||||
|
||||
@export(round, .{ .name = "round", .linkage = .Strong });
|
||||
@export(roundf, .{ .name = "roundf", .linkage = .Strong });
|
||||
@export(roundl, .{ .name = "roundl", .linkage = .Strong });
|
||||
|
||||
@export(fmin, .{ .name = "fmin", .linkage = .Strong });
|
||||
@export(fminf, .{ .name = "fminf", .linkage = .Strong });
|
||||
@ -575,11 +576,18 @@ fn fabsf(a: f32) callconv(.C) f32 {
|
||||
return math.fabs(a);
|
||||
}
|
||||
|
||||
fn roundf(a: f32) callconv(.C) f32 {
|
||||
return math.round(a);
|
||||
}
|
||||
|
||||
fn round(a: f64) callconv(.C) f64 {
|
||||
return math.round(a);
|
||||
}
|
||||
|
||||
fn roundf(a: f32) callconv(.C) f32 {
|
||||
fn roundl(a: c_longdouble) callconv(.C) c_longdouble {
|
||||
if (!long_double_is_f128) {
|
||||
@panic("TODO implement this");
|
||||
}
|
||||
return math.round(a);
|
||||
}
|
||||
|
||||
|
||||
62
src/Sema.zig
62
src/Sema.zig
@ -4195,7 +4195,15 @@ fn zirDbgVar(
|
||||
const str_op = sema.code.instructions.items(.data)[inst].str_op;
|
||||
const operand = sema.resolveInst(str_op.operand);
|
||||
const operand_ty = sema.typeOf(operand);
|
||||
if (!(try sema.typeHasRuntimeBits(block, sema.src, operand_ty))) return;
|
||||
switch (air_tag) {
|
||||
.dbg_var_ptr => {
|
||||
if (!(try sema.typeHasRuntimeBits(block, sema.src, operand_ty.childType()))) return;
|
||||
},
|
||||
.dbg_var_val => {
|
||||
if (!(try sema.typeHasRuntimeBits(block, sema.src, operand_ty))) return;
|
||||
},
|
||||
else => unreachable,
|
||||
}
|
||||
const name = str_op.getStr(sema.code);
|
||||
|
||||
// Add the name to the AIR.
|
||||
@ -13268,7 +13276,7 @@ fn checkFloatType(
|
||||
ty: Type,
|
||||
) CompileError!void {
|
||||
switch (ty.zigTypeTag()) {
|
||||
.ComptimeFloat, .Float => {},
|
||||
.ComptimeInt, .ComptimeFloat, .Float => {},
|
||||
else => return sema.fail(block, ty_src, "expected float type, found '{}'", .{ty}),
|
||||
}
|
||||
}
|
||||
@ -17169,10 +17177,25 @@ fn storePtr2(
|
||||
return;
|
||||
}
|
||||
|
||||
// TODO do the same thing for anon structs as for tuples above.
|
||||
|
||||
// Detect if we are storing an array operand to a bitcasted vector pointer.
|
||||
// If so, we instead reach through the bitcasted pointer to the vector pointer,
|
||||
// bitcast the array operand to a vector, and then lower this as a store of
|
||||
// a vector value to a vector pointer. This generally results in better code,
|
||||
// as well as working around an LLVM bug:
|
||||
// https://github.com/ziglang/zig/issues/11154
|
||||
if (sema.obtainBitCastedVectorPtr(ptr)) |vector_ptr| {
|
||||
const vector_ty = sema.typeOf(vector_ptr).childType();
|
||||
const vector = try sema.coerce(block, vector_ty, uncasted_operand, operand_src);
|
||||
try sema.storePtr2(block, src, vector_ptr, ptr_src, vector, operand_src, .store);
|
||||
return;
|
||||
}
|
||||
|
||||
const operand = try sema.coerce(block, elem_ty, uncasted_operand, operand_src);
|
||||
const maybe_operand_val = try sema.resolveMaybeUndefVal(block, operand_src, operand);
|
||||
|
||||
const runtime_src = if (try sema.resolveDefinedValue(block, ptr_src, ptr)) |ptr_val| rs: {
|
||||
const maybe_operand_val = try sema.resolveMaybeUndefVal(block, operand_src, operand);
|
||||
const operand_val = maybe_operand_val orelse {
|
||||
try sema.checkPtrIsNotComptimeMutable(block, ptr_val, ptr_src, operand_src);
|
||||
break :rs operand_src;
|
||||
@ -17195,6 +17218,39 @@ fn storePtr2(
|
||||
_ = try block.addBinOp(air_tag, ptr, operand);
|
||||
}
|
||||
|
||||
/// Traverse an arbitrary number of bitcasted pointers and return the underyling vector
|
||||
/// pointer. Only if the final element type matches the vector element type, and the
|
||||
/// lengths match.
|
||||
fn obtainBitCastedVectorPtr(sema: *Sema, ptr: Air.Inst.Ref) ?Air.Inst.Ref {
|
||||
const array_ty = sema.typeOf(ptr).childType();
|
||||
if (array_ty.zigTypeTag() != .Array) return null;
|
||||
var ptr_inst = Air.refToIndex(ptr) orelse return null;
|
||||
const air_datas = sema.air_instructions.items(.data);
|
||||
const air_tags = sema.air_instructions.items(.tag);
|
||||
const prev_ptr = while (air_tags[ptr_inst] == .bitcast) {
|
||||
const prev_ptr = air_datas[ptr_inst].ty_op.operand;
|
||||
const prev_ptr_ty = sema.typeOf(prev_ptr);
|
||||
const prev_ptr_child_ty = switch (prev_ptr_ty.tag()) {
|
||||
.single_mut_pointer => prev_ptr_ty.castTag(.single_mut_pointer).?.data,
|
||||
.pointer => prev_ptr_ty.castTag(.pointer).?.data.pointee_type,
|
||||
else => return null,
|
||||
};
|
||||
if (prev_ptr_child_ty.zigTypeTag() == .Vector) break prev_ptr;
|
||||
ptr_inst = Air.refToIndex(prev_ptr) orelse return null;
|
||||
} else return null;
|
||||
|
||||
// We have a pointer-to-array and a pointer-to-vector. If the elements and
|
||||
// lengths match, return the result.
|
||||
const vector_ty = sema.typeOf(prev_ptr).childType();
|
||||
if (array_ty.childType().eql(vector_ty.childType()) and
|
||||
array_ty.arrayLen() == vector_ty.vectorLen())
|
||||
{
|
||||
return prev_ptr;
|
||||
} else {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
/// Call when you have Value objects rather than Air instructions, and you want to
|
||||
/// assert the store must be done at comptime.
|
||||
fn storePtrVal(
|
||||
|
||||
@ -3709,10 +3709,11 @@ pub const FuncGen = struct {
|
||||
|
||||
const ty_op = self.air.instructions.items(.data)[inst].ty_op;
|
||||
const operand = try self.resolveInst(ty_op.operand);
|
||||
const operand_ty = self.air.typeOf(ty_op.operand);
|
||||
const dest_ty = self.air.typeOfIndex(inst);
|
||||
const dest_llvm_ty = try self.dg.llvmType(dest_ty);
|
||||
|
||||
if (dest_ty.isSignedInt()) {
|
||||
if (operand_ty.isSignedInt()) {
|
||||
return self.builder.buildSIToFP(operand, dest_llvm_ty, "");
|
||||
} else {
|
||||
return self.builder.buildUIToFP(operand, dest_llvm_ty, "");
|
||||
@ -3984,13 +3985,14 @@ pub const FuncGen = struct {
|
||||
const pl_op = self.air.instructions.items(.data)[inst].pl_op;
|
||||
const operand = try self.resolveInst(pl_op.operand);
|
||||
const name = self.air.nullTerminatedString(pl_op.payload);
|
||||
const ptr_ty = self.air.typeOf(pl_op.operand);
|
||||
|
||||
const di_local_var = dib.createAutoVariable(
|
||||
self.di_scope.?,
|
||||
name.ptr,
|
||||
self.di_file.?,
|
||||
self.prev_dbg_line,
|
||||
try self.dg.lowerDebugType(self.air.typeOf(pl_op.operand)),
|
||||
try self.dg.lowerDebugType(ptr_ty.childType()),
|
||||
true, // always preserve
|
||||
0, // flags
|
||||
);
|
||||
|
||||
@ -2573,15 +2573,14 @@ pub const Type = extern union {
|
||||
.array_u8_sentinel_0 => self.castTag(.array_u8_sentinel_0).?.data + 1,
|
||||
.array, .vector => {
|
||||
const payload = self.cast(Payload.Array).?.data;
|
||||
const elem_size = @maximum(payload.elem_type.abiAlignment(target), payload.elem_type.abiSize(target));
|
||||
const elem_size = payload.elem_type.abiSize(target);
|
||||
assert(elem_size >= payload.elem_type.abiAlignment(target));
|
||||
return payload.len * elem_size;
|
||||
},
|
||||
.array_sentinel => {
|
||||
const payload = self.castTag(.array_sentinel).?.data;
|
||||
const elem_size = std.math.max(
|
||||
payload.elem_type.abiAlignment(target),
|
||||
payload.elem_type.abiSize(target),
|
||||
);
|
||||
const elem_size = payload.elem_type.abiSize(target);
|
||||
assert(elem_size >= payload.elem_type.abiAlignment(target));
|
||||
return (payload.len + 1) * elem_size;
|
||||
},
|
||||
.i16, .u16 => return 2,
|
||||
|
||||
@ -3931,15 +3931,12 @@ pub const Value = extern union {
|
||||
},
|
||||
80 => {
|
||||
if (true) {
|
||||
@panic("TODO implement compiler_rt fabs for f80");
|
||||
@panic("TODO implement compiler_rt fabs for f80 (__fabsx)");
|
||||
}
|
||||
const f = val.toFloat(f80);
|
||||
return Value.Tag.float_80.create(arena, @fabs(f));
|
||||
},
|
||||
128 => {
|
||||
if (true) {
|
||||
@panic("TODO implement compiler_rt fabs for f128");
|
||||
}
|
||||
const f = val.toFloat(f128);
|
||||
return Value.Tag.float_128.create(arena, @fabs(f));
|
||||
},
|
||||
@ -3963,15 +3960,12 @@ pub const Value = extern union {
|
||||
},
|
||||
80 => {
|
||||
if (true) {
|
||||
@panic("TODO implement compiler_rt floor for f80");
|
||||
@panic("TODO implement compiler_rt floor for f80 (__floorx)");
|
||||
}
|
||||
const f = val.toFloat(f80);
|
||||
return Value.Tag.float_80.create(arena, @floor(f));
|
||||
},
|
||||
128 => {
|
||||
if (true) {
|
||||
@panic("TODO implement compiler_rt floor for f128");
|
||||
}
|
||||
const f = val.toFloat(f128);
|
||||
return Value.Tag.float_128.create(arena, @floor(f));
|
||||
},
|
||||
@ -4001,9 +3995,6 @@ pub const Value = extern union {
|
||||
return Value.Tag.float_80.create(arena, @ceil(f));
|
||||
},
|
||||
128 => {
|
||||
if (true) {
|
||||
@panic("TODO implement compiler_rt ceil for f128");
|
||||
}
|
||||
const f = val.toFloat(f128);
|
||||
return Value.Tag.float_128.create(arena, @ceil(f));
|
||||
},
|
||||
@ -4033,9 +4024,6 @@ pub const Value = extern union {
|
||||
return Value.Tag.float_80.create(arena, @round(f));
|
||||
},
|
||||
128 => {
|
||||
if (true) {
|
||||
@panic("TODO implement compiler_rt round for f128");
|
||||
}
|
||||
const f = val.toFloat(f128);
|
||||
return Value.Tag.float_128.create(arena, @round(f));
|
||||
},
|
||||
@ -4065,9 +4053,6 @@ pub const Value = extern union {
|
||||
return Value.Tag.float_80.create(arena, @trunc(f));
|
||||
},
|
||||
128 => {
|
||||
if (true) {
|
||||
@panic("TODO implement compiler_rt trunc for f128");
|
||||
}
|
||||
const f = val.toFloat(f128);
|
||||
return Value.Tag.float_128.create(arena, @trunc(f));
|
||||
},
|
||||
|
||||
@ -95,8 +95,29 @@ test "comptime_int @intToFloat" {
|
||||
}
|
||||
}
|
||||
|
||||
test "@intToFloat" {
|
||||
if (builtin.zig_backend == .stage2_wasm) return error.SkipZigTest; // TODO
|
||||
if (builtin.zig_backend == .stage2_aarch64) return error.SkipZigTest; // TODO
|
||||
if (builtin.zig_backend == .stage2_x86_64) return error.SkipZigTest; // TODO
|
||||
if (builtin.zig_backend == .stage2_arm) return error.SkipZigTest; // TODO
|
||||
|
||||
const S = struct {
|
||||
fn doTheTest() !void {
|
||||
try testIntToFloat(-2);
|
||||
}
|
||||
|
||||
fn testIntToFloat(k: i32) !void {
|
||||
const f = @intToFloat(f32, k);
|
||||
const i = @floatToInt(i32, f);
|
||||
try expect(i == k);
|
||||
}
|
||||
};
|
||||
try S.doTheTest();
|
||||
comptime try S.doTheTest();
|
||||
}
|
||||
|
||||
test "@floatToInt" {
|
||||
if (builtin.zig_backend == .stage2_aarch64) return error.SkipZigTest;
|
||||
if (builtin.zig_backend == .stage2_aarch64) return error.SkipZigTest; // TODO
|
||||
if (builtin.zig_backend == .stage2_x86_64) return error.SkipZigTest; // TODO
|
||||
if (builtin.zig_backend == .stage2_arm) return error.SkipZigTest; // TODO
|
||||
|
||||
@ -1007,8 +1028,6 @@ test "peer type resolve array pointer and unknown pointer" {
|
||||
}
|
||||
|
||||
test "comptime float casts" {
|
||||
if (builtin.zig_backend != .stage1) return error.SkipZigTest; // TODO
|
||||
|
||||
const a = @intToFloat(comptime_float, 1);
|
||||
try expect(a == 1);
|
||||
try expect(@TypeOf(a) == comptime_float);
|
||||
|
||||
@ -333,7 +333,6 @@ fn testLog() !void {
|
||||
}
|
||||
|
||||
test "@log with vectors" {
|
||||
if (builtin.zig_backend == .stage2_llvm) return error.SkipZigTest; // TODO
|
||||
if (builtin.zig_backend == .stage2_wasm) return error.SkipZigTest; // TODO
|
||||
if (builtin.zig_backend == .stage2_x86_64) return error.SkipZigTest; // TODO
|
||||
if (builtin.zig_backend == .stage2_aarch64) return error.SkipZigTest; // TODO
|
||||
@ -343,15 +342,19 @@ test "@log with vectors" {
|
||||
{
|
||||
var v: @Vector(4, f32) = [_]f32{ 1.1, 2.2, 0.3, 0.4 };
|
||||
var result = @log(v);
|
||||
try expect(math.approxEqAbs(f32, @log(@as(f32, 1.1)), result[0], epsilon));
|
||||
try expect(math.approxEqAbs(f32, @log(@as(f32, 2.2)), result[1], epsilon));
|
||||
try expect(@log(@as(f32, 1.1)) == result[0]);
|
||||
try expect(@log(@as(f32, 2.2)) == result[1]);
|
||||
try expect(@log(@as(f32, 0.3)) == result[2]);
|
||||
try expect(math.approxEqAbs(f32, @log(@as(f32, 0.4)), result[3], epsilon));
|
||||
try expect(@log(@as(f32, 0.4)) == result[3]);
|
||||
}
|
||||
}
|
||||
|
||||
test "@log2" {
|
||||
if (builtin.zig_backend != .stage1) return error.SkipZigTest; // TODO
|
||||
if (builtin.zig_backend == .stage2_wasm) return error.SkipZigTest; // TODO
|
||||
if (builtin.zig_backend == .stage2_x86_64) return error.SkipZigTest; // TODO
|
||||
if (builtin.zig_backend == .stage2_aarch64) return error.SkipZigTest; // TODO
|
||||
if (builtin.zig_backend == .stage2_arm) return error.SkipZigTest; // TODO
|
||||
if (builtin.zig_backend == .stage2_c) return error.SkipZigTest; // TODO
|
||||
|
||||
comptime try testLog2();
|
||||
try testLog2();
|
||||
@ -368,15 +371,19 @@ fn testLog2() !void {
|
||||
{
|
||||
var v: Vector(4, f32) = [_]f32{ 1.1, 2.2, 0.3, 0.4 };
|
||||
var result = @log2(v);
|
||||
try expect(math.approxEqAbs(f32, @log2(@as(f32, 1.1)), result[0], epsilon));
|
||||
try expect(math.approxEqAbs(f32, @log2(@as(f32, 2.2)), result[1], epsilon));
|
||||
try expect(math.approxEqAbs(f32, @log2(@as(f32, 0.3)), result[2], epsilon));
|
||||
try expect(math.approxEqAbs(f32, @log2(@as(f32, 0.4)), result[3], epsilon));
|
||||
try expect(@log2(@as(f32, 1.1)) == result[0]);
|
||||
try expect(@log2(@as(f32, 2.2)) == result[1]);
|
||||
try expect(@log2(@as(f32, 0.3)) == result[2]);
|
||||
try expect(@log2(@as(f32, 0.4)) == result[3]);
|
||||
}
|
||||
}
|
||||
|
||||
test "@log10" {
|
||||
if (builtin.zig_backend != .stage1) return error.SkipZigTest; // TODO
|
||||
if (builtin.zig_backend == .stage2_wasm) return error.SkipZigTest; // TODO
|
||||
if (builtin.zig_backend == .stage2_x86_64) return error.SkipZigTest; // TODO
|
||||
if (builtin.zig_backend == .stage2_aarch64) return error.SkipZigTest; // TODO
|
||||
if (builtin.zig_backend == .stage2_arm) return error.SkipZigTest; // TODO
|
||||
if (builtin.zig_backend == .stage2_c) return error.SkipZigTest; // TODO
|
||||
|
||||
comptime try testLog10();
|
||||
try testLog10();
|
||||
@ -393,10 +400,10 @@ fn testLog10() !void {
|
||||
{
|
||||
var v: Vector(4, f32) = [_]f32{ 1.1, 2.2, 0.3, 0.4 };
|
||||
var result = @log10(v);
|
||||
try expect(math.approxEqAbs(f32, @log10(@as(f32, 1.1)), result[0], epsilon));
|
||||
try expect(math.approxEqAbs(f32, @log10(@as(f32, 2.2)), result[1], epsilon));
|
||||
try expect(math.approxEqAbs(f32, @log10(@as(f32, 0.3)), result[2], epsilon));
|
||||
try expect(math.approxEqAbs(f32, @log10(@as(f32, 0.4)), result[3], epsilon));
|
||||
try expect(@log10(@as(f32, 1.1)) == result[0]);
|
||||
try expect(@log10(@as(f32, 2.2)) == result[1]);
|
||||
try expect(@log10(@as(f32, 0.3)) == result[2]);
|
||||
try expect(@log10(@as(f32, 0.4)) == result[3]);
|
||||
}
|
||||
}
|
||||
|
||||
@ -537,7 +544,71 @@ fn testTrunc() !void {
|
||||
}
|
||||
}
|
||||
|
||||
test "negation" {
|
||||
test "negation f16" {
|
||||
if (builtin.zig_backend == .stage2_c) return error.SkipZigTest; // TODO
|
||||
if (builtin.zig_backend == .stage2_x86_64) return error.SkipZigTest; // TODO
|
||||
if (builtin.zig_backend == .stage2_arm) return error.SkipZigTest; // TODO
|
||||
if (builtin.zig_backend == .stage2_aarch64) return error.SkipZigTest; // TODO
|
||||
|
||||
if (builtin.os.tag == .freebsd) {
|
||||
// TODO file issue to track this failure
|
||||
return error.SkipZigTest;
|
||||
}
|
||||
|
||||
const S = struct {
|
||||
fn doTheTest() !void {
|
||||
var a: f16 = 1;
|
||||
a = -a;
|
||||
try expect(a == -1);
|
||||
a = -a;
|
||||
try expect(a == 1);
|
||||
}
|
||||
};
|
||||
|
||||
try S.doTheTest();
|
||||
comptime try S.doTheTest();
|
||||
}
|
||||
|
||||
test "negation f32" {
|
||||
if (builtin.zig_backend == .stage2_x86_64) return error.SkipZigTest; // TODO
|
||||
if (builtin.zig_backend == .stage2_arm) return error.SkipZigTest; // TODO
|
||||
if (builtin.zig_backend == .stage2_aarch64) return error.SkipZigTest; // TODO
|
||||
if (builtin.zig_backend == .stage2_c) return error.SkipZigTest; // TODO
|
||||
|
||||
const S = struct {
|
||||
fn doTheTest() !void {
|
||||
var a: f32 = 1;
|
||||
a = -a;
|
||||
try expect(a == -1);
|
||||
a = -a;
|
||||
try expect(a == 1);
|
||||
}
|
||||
};
|
||||
|
||||
try S.doTheTest();
|
||||
comptime try S.doTheTest();
|
||||
}
|
||||
|
||||
test "negation f64" {
|
||||
if (builtin.zig_backend == .stage2_x86_64) return error.SkipZigTest; // TODO
|
||||
if (builtin.zig_backend == .stage2_arm) return error.SkipZigTest; // TODO
|
||||
if (builtin.zig_backend == .stage2_aarch64) return error.SkipZigTest; // TODO
|
||||
|
||||
const S = struct {
|
||||
fn doTheTest() !void {
|
||||
var a: f64 = 1;
|
||||
a = -a;
|
||||
try expect(a == -1);
|
||||
a = -a;
|
||||
try expect(a == 1);
|
||||
}
|
||||
};
|
||||
|
||||
try S.doTheTest();
|
||||
comptime try S.doTheTest();
|
||||
}
|
||||
|
||||
test "negation f80" {
|
||||
if (builtin.zig_backend != .stage1) return error.SkipZigTest; // TODO
|
||||
|
||||
if (builtin.os.tag == .freebsd) {
|
||||
@ -547,11 +618,37 @@ test "negation" {
|
||||
|
||||
const S = struct {
|
||||
fn doTheTest() !void {
|
||||
inline for ([_]type{ f16, f32, f64, f80, f128 }) |T| {
|
||||
var a: T = 1;
|
||||
a = -a;
|
||||
try expect(a == -1);
|
||||
}
|
||||
var a: f80 = 1;
|
||||
a = -a;
|
||||
try expect(a == -1);
|
||||
a = -a;
|
||||
try expect(a == 1);
|
||||
}
|
||||
};
|
||||
|
||||
try S.doTheTest();
|
||||
comptime try S.doTheTest();
|
||||
}
|
||||
|
||||
test "negation f128" {
|
||||
if (builtin.zig_backend == .stage2_x86_64) return error.SkipZigTest; // TODO
|
||||
if (builtin.zig_backend == .stage2_arm) return error.SkipZigTest; // TODO
|
||||
if (builtin.zig_backend == .stage2_aarch64) return error.SkipZigTest; // TODO
|
||||
if (builtin.zig_backend == .stage2_c) return error.SkipZigTest; // TODO
|
||||
if (builtin.zig_backend == .stage2_wasm) return error.SkipZigTest; // TODO
|
||||
|
||||
if (builtin.os.tag == .freebsd) {
|
||||
// TODO file issue to track this failure
|
||||
return error.SkipZigTest;
|
||||
}
|
||||
|
||||
const S = struct {
|
||||
fn doTheTest() !void {
|
||||
var a: f128 = 1;
|
||||
a = -a;
|
||||
try expect(a == -1);
|
||||
a = -a;
|
||||
try expect(a == 1);
|
||||
}
|
||||
};
|
||||
|
||||
@ -583,7 +680,13 @@ test "float literal at compile time not lossy" {
|
||||
}
|
||||
|
||||
test "f128 at compile time is lossy" {
|
||||
if (builtin.zig_backend != .stage1) return error.SkipZigTest; // TODO
|
||||
if (builtin.zig_backend != .stage1) {
|
||||
// this one is happening because we represent comptime-known f128 integers with
|
||||
// Value.Tag.bigint and only convert to f128 representation if it stops being an
|
||||
// integer. Is this something we want? need to have a lang spec discussion on this
|
||||
// topic.
|
||||
return error.SkipZigTest; // TODO
|
||||
}
|
||||
|
||||
try expect(@as(f128, 10384593717069655257060992658440192.0) + 1 == 10384593717069655257060992658440192.0);
|
||||
}
|
||||
|
||||
@ -6,7 +6,6 @@ const expectEqualSlices = std.testing.expectEqualSlices;
|
||||
const maxInt = std.math.maxInt;
|
||||
const minInt = std.math.minInt;
|
||||
const mem = std.mem;
|
||||
const has_f80_rt = builtin.cpu.arch == .x86_64;
|
||||
|
||||
test "assignment operators" {
|
||||
if (builtin.zig_backend == .stage2_x86_64) return error.SkipZigTest; // TODO
|
||||
@ -1046,12 +1045,14 @@ fn testSqrt(comptime T: type, x: T) !void {
|
||||
}
|
||||
|
||||
test "@fabs" {
|
||||
if (builtin.zig_backend != .stage1) return error.SkipZigTest; // TODO
|
||||
if (builtin.zig_backend == .stage2_wasm) return error.SkipZigTest; // TODO
|
||||
if (builtin.zig_backend == .stage2_arm) return error.SkipZigTest; // TODO
|
||||
if (builtin.zig_backend == .stage2_aarch64) return error.SkipZigTest; // TODO
|
||||
if (builtin.zig_backend == .stage2_x86_64) return error.SkipZigTest; // TODO
|
||||
if (builtin.zig_backend == .stage2_c) return error.SkipZigTest; // TODO
|
||||
|
||||
try testFabs(f128, 12.0);
|
||||
comptime try testFabs(f128, 12.0);
|
||||
if (has_f80_rt) try testFabs(f80, 12.0);
|
||||
// comptime try testFabs(f80, 12.0);
|
||||
try testFabs(f64, 12.0);
|
||||
comptime try testFabs(f64, 12.0);
|
||||
try testFabs(f32, 12.0);
|
||||
@ -1065,20 +1066,25 @@ test "@fabs" {
|
||||
comptime try expectEqual(x, z);
|
||||
}
|
||||
|
||||
test "@fabs f80" {
|
||||
if (true) {
|
||||
// https://github.com/ziglang/zig/issues/11030
|
||||
return error.SkipZigTest;
|
||||
}
|
||||
|
||||
try testFabs(f80, 12.0);
|
||||
comptime try testFabs(f80, 12.0);
|
||||
}
|
||||
|
||||
fn testFabs(comptime T: type, x: T) !void {
|
||||
const y = -x;
|
||||
const z = @fabs(y);
|
||||
try expectEqual(x, z);
|
||||
try expect(x == z);
|
||||
}
|
||||
|
||||
test "@floor" {
|
||||
if (builtin.zig_backend != .stage1) return error.SkipZigTest; // TODO
|
||||
|
||||
// FIXME: Generates a floorl function call
|
||||
// testFloor(f128, 12.0);
|
||||
comptime try testFloor(f128, 12.0);
|
||||
// try testFloor(f80, 12.0);
|
||||
comptime try testFloor(f80, 12.0);
|
||||
try testFloor(f64, 12.0);
|
||||
comptime try testFloor(f64, 12.0);
|
||||
try testFloor(f32, 12.0);
|
||||
@ -1089,23 +1095,39 @@ test "@floor" {
|
||||
const x = 14.0;
|
||||
const y = x + 0.7;
|
||||
const z = @floor(y);
|
||||
comptime try expectEqual(x, z);
|
||||
comptime try expect(x == z);
|
||||
}
|
||||
|
||||
test "@floor f80" {
|
||||
if (true) {
|
||||
// https://github.com/ziglang/zig/issues/11030
|
||||
return error.SkipZigTest;
|
||||
}
|
||||
try testFloor(f80, 12.0);
|
||||
comptime try testFloor(f80, 12.0);
|
||||
}
|
||||
|
||||
test "@floor f128" {
|
||||
if (builtin.zig_backend == .stage1) {
|
||||
// Fails because it incorrectly lowers to a floorl function call.
|
||||
return error.SkipZigTest;
|
||||
}
|
||||
|
||||
if (builtin.zig_backend != .stage1) return error.SkipZigTest; // TODO
|
||||
|
||||
testFloor(f128, 12.0);
|
||||
comptime try testFloor(f128, 12.0);
|
||||
}
|
||||
|
||||
fn testFloor(comptime T: type, x: T) !void {
|
||||
const y = x + 0.6;
|
||||
const z = @floor(y);
|
||||
try expectEqual(x, z);
|
||||
try expect(x == z);
|
||||
}
|
||||
|
||||
test "@ceil" {
|
||||
if (builtin.zig_backend != .stage1) return error.SkipZigTest; // TODO
|
||||
|
||||
// FIXME: Generates a ceill function call
|
||||
//testCeil(f128, 12.0);
|
||||
comptime try testCeil(f128, 12.0);
|
||||
// try testCeil(f80, 12.0);
|
||||
comptime try testCeil(f80, 12.0);
|
||||
try testCeil(f64, 12.0);
|
||||
comptime try testCeil(f64, 12.0);
|
||||
try testCeil(f32, 12.0);
|
||||
@ -1116,29 +1138,40 @@ test "@ceil" {
|
||||
const x = 14.0;
|
||||
const y = x - 0.7;
|
||||
const z = @ceil(y);
|
||||
comptime try expectEqual(x, z);
|
||||
comptime try expect(x == z);
|
||||
}
|
||||
|
||||
test "@ceil f80" {
|
||||
if (true) {
|
||||
// https://github.com/ziglang/zig/issues/11030
|
||||
return error.SkipZigTest;
|
||||
}
|
||||
|
||||
try testCeil(f80, 12.0);
|
||||
comptime try testCeil(f80, 12.0);
|
||||
}
|
||||
|
||||
test "@ceil f128" {
|
||||
if (builtin.zig_backend == .stage1) {
|
||||
// Fails because it incorrectly lowers to a ceill function call.
|
||||
return error.SkipZigTest;
|
||||
}
|
||||
|
||||
if (builtin.zig_backend != .stage1) return error.SkipZigTest; // TODO
|
||||
|
||||
testCeil(f128, 12.0);
|
||||
comptime try testCeil(f128, 12.0);
|
||||
}
|
||||
|
||||
fn testCeil(comptime T: type, x: T) !void {
|
||||
const y = x - 0.8;
|
||||
const z = @ceil(y);
|
||||
try expectEqual(x, z);
|
||||
try expect(x == z);
|
||||
}
|
||||
|
||||
test "@trunc" {
|
||||
if (builtin.zig_backend != .stage1) return error.SkipZigTest; // TODO
|
||||
|
||||
// FIXME: Generates a truncl function call
|
||||
//testTrunc(f128, 12.0);
|
||||
comptime try testTrunc(f128, 12.0);
|
||||
// try testTrunc(f80, 12.0);
|
||||
// comptime try testTrunc(f80, 12.0);
|
||||
comptime {
|
||||
const x: f80 = 12.0;
|
||||
const y = x + 0.8;
|
||||
const z = @trunc(y);
|
||||
try expectEqual(x, z);
|
||||
}
|
||||
try testTrunc(f64, 12.0);
|
||||
comptime try testTrunc(f64, 12.0);
|
||||
try testTrunc(f32, 12.0);
|
||||
@ -1149,31 +1182,54 @@ test "@trunc" {
|
||||
const x = 14.0;
|
||||
const y = x + 0.7;
|
||||
const z = @trunc(y);
|
||||
comptime try expectEqual(x, z);
|
||||
comptime try expect(x == z);
|
||||
}
|
||||
|
||||
test "@trunc f80" {
|
||||
if (true) {
|
||||
// https://github.com/ziglang/zig/issues/11030
|
||||
return error.SkipZigTest;
|
||||
}
|
||||
|
||||
try testTrunc(f80, 12.0);
|
||||
comptime try testTrunc(f80, 12.0);
|
||||
comptime {
|
||||
const x: f80 = 12.0;
|
||||
const y = x + 0.8;
|
||||
const z = @trunc(y);
|
||||
try expect(x == z);
|
||||
}
|
||||
}
|
||||
|
||||
test "@trunc f128" {
|
||||
if (builtin.zig_backend == .stage1) {
|
||||
// Fails because it incorrectly lowers to a truncl function call.
|
||||
return error.SkipZigTest;
|
||||
}
|
||||
|
||||
if (builtin.zig_backend != .stage1) return error.SkipZigTest; // TODO
|
||||
|
||||
testTrunc(f128, 12.0);
|
||||
comptime try testTrunc(f128, 12.0);
|
||||
}
|
||||
|
||||
fn testTrunc(comptime T: type, x: T) !void {
|
||||
{
|
||||
const y = x + 0.8;
|
||||
const z = @trunc(y);
|
||||
try expectEqual(x, z);
|
||||
try expect(x == z);
|
||||
}
|
||||
|
||||
{
|
||||
const y = -x - 0.8;
|
||||
const z = @trunc(y);
|
||||
try expectEqual(-x, z);
|
||||
try expect(-x == z);
|
||||
}
|
||||
}
|
||||
|
||||
test "@round" {
|
||||
if (builtin.zig_backend != .stage1) return error.SkipZigTest; // TODO
|
||||
|
||||
// FIXME: Generates a roundl function call
|
||||
//testRound(f128, 12.0);
|
||||
comptime try testRound(f128, 12.0);
|
||||
// try testRound(f80, 12.0);
|
||||
comptime try testRound(f80, 12.0);
|
||||
try testRound(f64, 12.0);
|
||||
comptime try testRound(f64, 12.0);
|
||||
try testRound(f32, 12.0);
|
||||
@ -1184,13 +1240,35 @@ test "@round" {
|
||||
const x = 14.0;
|
||||
const y = x + 0.4;
|
||||
const z = @round(y);
|
||||
comptime try expectEqual(x, z);
|
||||
comptime try expect(x == z);
|
||||
}
|
||||
|
||||
test "@round f80" {
|
||||
if (true) {
|
||||
// https://github.com/ziglang/zig/issues/11030
|
||||
return error.SkipZigTest;
|
||||
}
|
||||
|
||||
try testRound(f80, 12.0);
|
||||
comptime try testRound(f80, 12.0);
|
||||
}
|
||||
|
||||
test "@round f128" {
|
||||
if (builtin.zig_backend == .stage1) {
|
||||
// Fails because it incorrectly lowers to a roundl function call.
|
||||
return error.SkipZigTest;
|
||||
}
|
||||
|
||||
if (builtin.zig_backend != .stage1) return error.SkipZigTest; // TODO
|
||||
|
||||
testRound(f128, 12.0);
|
||||
comptime try testRound(f128, 12.0);
|
||||
}
|
||||
|
||||
fn testRound(comptime T: type, x: T) !void {
|
||||
const y = x - 0.5;
|
||||
const z = @round(y);
|
||||
try expectEqual(x, z);
|
||||
try expect(x == z);
|
||||
}
|
||||
|
||||
test "vector integer addition" {
|
||||
@ -1225,10 +1303,15 @@ test "NaN comparison" {
|
||||
comptime try testNanEqNan(f32);
|
||||
comptime try testNanEqNan(f64);
|
||||
comptime try testNanEqNan(f128);
|
||||
}
|
||||
|
||||
// TODO https://github.com/ziglang/zig/issues/11030
|
||||
// try testNanEqNan(f80);
|
||||
// comptime try testNanEqNan(f80);
|
||||
test "NaN comparison f80" {
|
||||
if (true) {
|
||||
// https://github.com/ziglang/zig/issues/11030
|
||||
return error.SkipZigTest;
|
||||
}
|
||||
try testNanEqNan(f80);
|
||||
comptime try testNanEqNan(f80);
|
||||
}
|
||||
|
||||
fn testNanEqNan(comptime F: type) !void {
|
||||
|
||||
@ -16,5 +16,6 @@ pub fn addCases(ctx: *TestContext) !void {
|
||||
try @import("stage2/riscv64.zig").addCases(ctx);
|
||||
try @import("stage2/plan9.zig").addCases(ctx);
|
||||
try @import("stage2/x86_64.zig").addCases(ctx);
|
||||
try @import("stage2/nvptx.zig").addCases(ctx);
|
||||
// https://github.com/ziglang/zig/issues/10968
|
||||
//try @import("stage2/nvptx.zig").addCases(ctx);
|
||||
}
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user