Shifts right. Overflowed bits are truncated. A negative shift amount results in a left shift.
pub fn shr(comptime T: type, a: T, shift_amt: anytype) T
pub fn shr(comptime T: type, a: T, shift_amt: anytype) T {
const is_shl = shift_amt < 0;
const abs_shift_amt = @abs(shift_amt);
const casted_shift_amt = casted_shift_amt: switch (@typeInfo(T)) {
.int => |info| {
if (abs_shift_amt < info.bits) break :casted_shift_amt @as(
Log2Int(T),
@intCast(abs_shift_amt),
);
if (info.signedness == .unsigned or is_shl) return 0;
return a >> (info.bits - 1);
},
.vector => |info| {
const Child = info.child;
const child_info = @typeInfo(Child).int;
if (abs_shift_amt < child_info.bits) break :casted_shift_amt @as(
@Vector(info.len, Log2Int(Child)),
@splat(@as(Log2Int(Child), @intCast(abs_shift_amt))),
);
if (child_info.signedness == .unsigned or is_shl) return @splat(0);
return a >> @splat(child_info.bits - 1);
},
else => comptime unreachable,
};
return if (is_shl) a << casted_shift_amt else a >> casted_shift_amt;
}