Return a usize from @abs if given an isize

Also:
- `c_ushort` for `c_short`
- `c_uint` for `c_int`
- `c_ulong` for `c_long`
- `c_ulonglong` for `c_longlong`
This commit is contained in:
fn ⌃ ⌥ 2025-04-16 11:59:47 -07:00 committed by mlugg
parent 44e99edd7a
commit bfe3317059
2 changed files with 70 additions and 7 deletions

View file

@ -3445,13 +3445,22 @@ pub fn optEuBaseType(ty: Type, zcu: *const Zcu) Type {
pub fn toUnsigned(ty: Type, pt: Zcu.PerThread) !Type {
const zcu = pt.zcu;
return switch (ty.zigTypeTag(zcu)) {
return switch (ty.toIntern()) {
// zig fmt: off
.usize_type, .isize_type => .usize,
.c_ushort_type, .c_short_type => .c_ushort,
.c_uint_type, .c_int_type => .c_uint,
.c_ulong_type, .c_long_type => .c_ulong,
.c_ulonglong_type, .c_longlong_type => .c_ulonglong,
// zig fmt: on
else => switch (ty.zigTypeTag(zcu)) {
.int => pt.intType(.unsigned, ty.intInfo(zcu).bits),
.vector => try pt.vectorType(.{
.len = ty.vectorLen(zcu),
.child = (try ty.childType(zcu).toUnsigned(pt)).toIntern(),
}),
else => unreachable,
},
};
}

View file

@ -1,5 +1,6 @@
const builtin = @import("builtin");
const std = @import("std");
const assert = std.debug.assert;
const expect = std.testing.expect;
test "@abs integers" {
@ -48,6 +49,33 @@ fn testAbsIntegers() !void {
}
}
test "@abs signed C ABI integers" {
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_sparc64) return error.SkipZigTest; // TODO
if (builtin.zig_backend == .stage2_riscv64) return error.SkipZigTest; // TODO
const S = struct {
fn doTheTest() !void {
try testOne(isize, usize);
try testOne(c_short, c_ushort);
try testOne(c_int, c_uint);
try testOne(c_long, c_ulong);
if (!builtin.cpu.arch.isSpirV()) try testOne(c_longlong, c_ulonglong);
}
fn testOne(comptime Signed: type, comptime Unsigned: type) !void {
var negative_one: Signed = undefined;
negative_one = -1;
const one = @abs(negative_one);
comptime assert(@TypeOf(one) == Unsigned);
try expect(one == 1);
}
};
try S.doTheTest();
try comptime S.doTheTest();
}
test "@abs unsigned integers" {
if (builtin.zig_backend == .stage2_arm) return error.SkipZigTest; // TODO
if (builtin.zig_backend == .stage2_sparc64) return error.SkipZigTest; // TODO
@ -87,6 +115,32 @@ fn testAbsUnsignedIntegers() !void {
}
}
test "@abs unsigned C ABI integers" {
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_sparc64) return error.SkipZigTest; // TODO
const S = struct {
fn doTheTest() !void {
try testOne(usize);
try testOne(c_ushort);
try testOne(c_uint);
try testOne(c_ulong);
if (!builtin.cpu.arch.isSpirV()) try testOne(c_ulonglong);
}
fn testOne(comptime Unsigned: type) !void {
var one: Unsigned = undefined;
one = 1;
const still_one = @abs(one);
comptime assert(@TypeOf(still_one) == Unsigned);
try expect(still_one == 1);
}
};
try S.doTheTest();
try comptime S.doTheTest();
}
test "@abs big int <= 128 bits" {
if (builtin.zig_backend == .stage2_arm) return error.SkipZigTest; // TODO
if (builtin.zig_backend == .stage2_sparc64) return error.SkipZigTest; // TODO