diff --git a/doc/langref.html.in b/doc/langref.html.in index 0afbe11fc6..d578be4ba8 100644 --- a/doc/langref.html.in +++ b/doc/langref.html.in @@ -6337,18 +6337,19 @@ comptime { {#header_close#} {#header_open|@clz#} -
{#syntax#}@clz(comptime T: type, integer: T) math.Log2Int(@intType(false, @typeInfo(T).Int.bits + 1)){#endsyntax#}
+
{#syntax#}@clz(comptime T: type, integer: T){#endsyntax#}

- This function counts the number of leading zeroes in {#syntax#}x{#endsyntax#} which is an integer - type {#syntax#}T{#endsyntax#}. + This function counts the number of leading zeroes in {#syntax#}integer{#endsyntax#}.

- If {#syntax#}integer{#endsyntax#} is known at {#link|comptime#}, the return type is {#syntax#}comptime_int{#endsyntax#}. + If {#syntax#}integer{#endsyntax#} is known at {#link|comptime#}, + the return type is {#syntax#}comptime_int{#endsyntax#}. Otherwise, the return type is an unsigned integer with the minimum number of bits that can represent the bit count of the integer type.

- If {#syntax#}x{#endsyntax#} is zero, {#syntax#}@clz{#endsyntax#} returns {#syntax#}T.bit_count{#endsyntax#}. + If {#syntax#}integer{#endsyntax#} is zero, {#syntax#}@clz{#endsyntax#} returns the bit width + of integer type {#syntax#}T{#endsyntax#}.

{#see_also|@ctz|@popCount#} {#header_close#} @@ -6478,18 +6479,19 @@ test "main" { {#header_close#} {#header_open|@ctz#} -
{#syntax#}@ctz(comptime T: type, integer: T) math.Log2Int(@intType(false, @typeInfo(T).Int.bits + 1)){#endsyntax#}
+
{#syntax#}@ctz(comptime T: type, integer: T){#endsyntax#}

- This function counts the number of trailing zeroes in {#syntax#}x{#endsyntax#} which is an integer - type {#syntax#}T{#endsyntax#}. + This function counts the number of trailing zeroes in {#syntax#}integer{#endsyntax#}.

- If {#syntax#}integer{#endsyntax#} is known at {#link|comptime#}, the return type is {#syntax#}comptime_int{#endsyntax#}. + If {#syntax#}integer{#endsyntax#} is known at {#link|comptime#}, + the return type is {#syntax#}comptime_int{#endsyntax#}. Otherwise, the return type is an unsigned integer with the minimum number of bits that can represent the bit count of the integer type.

- If {#syntax#}x{#endsyntax#} is zero, {#syntax#}@ctz{#endsyntax#} returns {#syntax#}T.bit_count{#endsyntax#}. + If {#syntax#}integer{#endsyntax#} is zero, {#syntax#}@ctz{#endsyntax#} returns + the bit width of integer type {#syntax#}T{#endsyntax#}.

{#see_also|@clz|@popCount#} {#header_close#} @@ -7036,10 +7038,11 @@ test "call foo" { {#header_close#} {#header_open|@popCount#} -
{#syntax#}@popCount(comptime T: type, integer: T) math.Log2Int(@intType(false, @typeInfo(T).Int.bits + 1)){#endsyntax#}
+
{#syntax#}@popCount(comptime T: type, integer: T){#endsyntax#}

Counts the number of bits set in an integer.

- If {#syntax#}integer{#endsyntax#} is known at {#link|comptime#}, the return type is {#syntax#}comptime_int{#endsyntax#}. + If {#syntax#}integer{#endsyntax#} is known at {#link|comptime#}, + the return type is {#syntax#}comptime_int{#endsyntax#}. Otherwise, the return type is an unsigned integer with the minimum number of bits that can represent the bit count of the integer type.

diff --git a/src/analyze.cpp b/src/analyze.cpp index f4e81ec042..57244aba6a 100644 --- a/src/analyze.cpp +++ b/src/analyze.cpp @@ -213,6 +213,15 @@ static ZigType *new_container_type_entry(CodeGen *g, ZigTypeId id, AstNode *sour return entry; } +static uint8_t bits_needed_for_unsigned(uint64_t x) { + if (x == 0) { + return 0; + } + uint8_t base = log2_u64(x); + uint64_t upper = (((uint64_t)1) << base) - 1; + return (upper >= x) ? base : (base + 1); +} + AstNode *type_decl_node(ZigType *type_entry) { switch (type_entry->id) { case ZigTypeIdInvalid: @@ -326,33 +335,10 @@ static bool is_slice(ZigType *type) { return type->id == ZigTypeIdStruct && type->data.structure.is_slice; } -static uint8_t bits_needed_for_unsigned(uint64_t x) { - if (x == 0) { - return 0; - } - uint8_t base = log2_u64(x); - uint64_t upper = (((uint64_t)1) << base) - 1; - return (upper >= x) ? base : (base + 1); -} - -static uint8_t bits_needed_for_popcount_unsigned(uint64_t x) { - uint8_t count = 0; - for (uint64_t s = x;s != 0;s >>= 1) - count++; - - return count; -} - ZigType *get_smallest_unsigned_int_type(CodeGen *g, uint64_t x) { return get_int_type(g, false, bits_needed_for_unsigned(x)); } -// This is not the same as above, because while shift by bit width is UB, @clz, @popCount, and @ctz -// can return bit width -ZigType *get_smallest_popcount_unsigned_int_type(CodeGen *g, uint64_t x) { - return get_int_type(g, false, bits_needed_for_popcount_unsigned(x)); -} - ZigType *get_promise_type(CodeGen *g, ZigType *result_type) { if (result_type != nullptr && result_type->promise_parent != nullptr) { return result_type->promise_parent; diff --git a/src/analyze.hpp b/src/analyze.hpp index f92b1922f9..d55733482f 100644 --- a/src/analyze.hpp +++ b/src/analyze.hpp @@ -34,7 +34,6 @@ ZigType *get_slice_type(CodeGen *g, ZigType *ptr_type); ZigType *get_partial_container_type(CodeGen *g, Scope *scope, ContainerKind kind, AstNode *decl_node, const char *full_name, Buf *bare_name, ContainerLayout layout); ZigType *get_smallest_unsigned_int_type(CodeGen *g, uint64_t x); -ZigType *get_smallest_popcount_unsigned_int_type(CodeGen *g, uint64_t x); ZigType *get_error_union_type(CodeGen *g, ZigType *err_set_type, ZigType *payload_type); ZigType *get_bound_fn_type(CodeGen *g, ZigFn *fn_entry); ZigType *get_opaque_type(CodeGen *g, Scope *scope, AstNode *source_node, const char *full_name, Buf *bare_name); diff --git a/src/codegen.cpp b/src/codegen.cpp index fd7134362f..c8903b7dbf 100644 --- a/src/codegen.cpp +++ b/src/codegen.cpp @@ -4126,19 +4126,11 @@ static LLVMValueRef get_int_builtin_fn(CodeGen *g, ZigType *int_type, BuiltinFnI char llvm_name[64]; sprintf(llvm_name, "llvm.%s.i%" PRIu32, fn_name, int_type->data.integral.bit_count); - LLVMTypeRef param_types[3]; - switch (n_args) { - case 1: - param_types[0] = get_llvm_type(g, int_type); - break; - case 2: // clz and ctz - param_types[0] = get_llvm_type(g, int_type); - param_types[1] = LLVMInt1Type(); - break; - default: - zig_unreachable(); - } - LLVMTypeRef fn_type = LLVMFunctionType(get_llvm_type(g, int_type), ¶m_types[0], n_args, false); + LLVMTypeRef param_types[] = { + get_llvm_type(g, int_type), + LLVMInt1Type(), + }; + LLVMTypeRef fn_type = LLVMFunctionType(get_llvm_type(g, int_type), param_types, n_args, false); LLVMValueRef fn_val = LLVMAddFunction(g->module, llvm_name, fn_type); assert(LLVMGetIntrinsicID(fn_val)); diff --git a/src/ir.cpp b/src/ir.cpp index afb032276c..8a3fd55c7e 100644 --- a/src/ir.cpp +++ b/src/ir.cpp @@ -10472,6 +10472,20 @@ static ZigType *ir_resolve_type(IrAnalyze *ira, IrInstruction *type_value) { return const_val->data.x_type; } +static ZigType *ir_resolve_int_type(IrAnalyze *ira, IrInstruction *type_value) { + ZigType *ty = ir_resolve_type(ira, type_value); + if (type_is_invalid(ty)) + return ira->codegen->builtin_types.entry_invalid; + + if (ty->id != ZigTypeIdInt) { + ir_add_error(ira, type_value, + buf_sprintf("expected integer type, found '%s'", buf_ptr(&ty->name))); + return ira->codegen->builtin_types.entry_invalid; + } + + return ty; +} + static ZigType *ir_resolve_error_set_type(IrAnalyze *ira, IrInstruction *op_source, IrInstruction *type_value) { if (type_is_invalid(type_value->value.type)) return ira->codegen->builtin_types.entry_invalid; @@ -17025,123 +17039,93 @@ static IrInstruction *ir_analyze_instruction_optional_unwrap_ptr(IrAnalyze *ira, } static IrInstruction *ir_analyze_instruction_ctz(IrAnalyze *ira, IrInstructionCtz *instruction) { - ZigType *int_type = ir_resolve_type(ira, instruction->type->child); + ZigType *int_type = ir_resolve_int_type(ira, instruction->type->child); if (type_is_invalid(int_type)) return ira->codegen->invalid_instruction; - IrInstruction *op = instruction->op->child; - - if (int_type->id != ZigTypeIdInt) { - ir_add_error(ira, instruction->type, - buf_sprintf("expected integer type, found '%s'", buf_ptr(&int_type->name))); - return ira->codegen->invalid_instruction; - } - - IrInstruction *casted_op = ir_implicit_cast(ira, op, int_type); - if (type_is_invalid(casted_op->value.type)) + IrInstruction *op = ir_implicit_cast(ira, instruction->op->child, int_type); + if (type_is_invalid(op->value.type)) return ira->codegen->invalid_instruction; - ZigType *return_type = get_smallest_popcount_unsigned_int_type(ira->codegen, int_type->data.integral.bit_count); + if (int_type->data.integral.bit_count == 0) + return ir_const_unsigned(ira, &instruction->base, 0); - if (int_type->data.integral.bit_count == 0) { - IrInstruction *result = ir_const(ira, &instruction->base, return_type); - bigint_init_unsigned(&result->value.data.x_bigint, 0); - return result; - } - - if (instr_is_comptime(casted_op)) { - size_t result_usize = bigint_ctz(&op->value.data.x_bigint, - op->value.type->data.integral.bit_count); - IrInstruction *result = ir_const(ira, &instruction->base, return_type); - bigint_init_unsigned(&result->value.data.x_bigint, result_usize); - return result; + if (instr_is_comptime(op)) { + ConstExprValue *val = ir_resolve_const(ira, op, UndefOk); + if (val == nullptr) + return ira->codegen->invalid_instruction; + if (val->special == ConstValSpecialUndef) + return ir_const_undef(ira, &instruction->base, ira->codegen->builtin_types.entry_num_lit_int); + size_t result_usize = bigint_ctz(&op->value.data.x_bigint, int_type->data.integral.bit_count); + return ir_const_unsigned(ira, &instruction->base, result_usize); } + ZigType *return_type = get_smallest_unsigned_int_type(ira->codegen, int_type->data.integral.bit_count); IrInstruction *result = ir_build_ctz(&ira->new_irb, instruction->base.scope, - instruction->base.source_node, nullptr, casted_op); + instruction->base.source_node, nullptr, op); result->value.type = return_type; return result; } static IrInstruction *ir_analyze_instruction_clz(IrAnalyze *ira, IrInstructionClz *instruction) { - ZigType *int_type = ir_resolve_type(ira, instruction->type->child); + ZigType *int_type = ir_resolve_int_type(ira, instruction->type->child); if (type_is_invalid(int_type)) return ira->codegen->invalid_instruction; - IrInstruction *op = instruction->op->child; - - if (int_type->id != ZigTypeIdInt) { - ir_add_error(ira, instruction->type, - buf_sprintf("expected integer type, found '%s'", buf_ptr(&int_type->name))); - return ira->codegen->invalid_instruction; - } - - IrInstruction *casted_op = ir_implicit_cast(ira, op, int_type); - if (type_is_invalid(casted_op->value.type)) + IrInstruction *op = ir_implicit_cast(ira, instruction->op->child, int_type); + if (type_is_invalid(op->value.type)) return ira->codegen->invalid_instruction; - ZigType *return_type = get_smallest_popcount_unsigned_int_type(ira->codegen, int_type->data.integral.bit_count); + if (int_type->data.integral.bit_count == 0) + return ir_const_unsigned(ira, &instruction->base, 0); - if (int_type->data.integral.bit_count == 0) { - IrInstruction *result = ir_const(ira, &instruction->base, return_type); - bigint_init_unsigned(&result->value.data.x_bigint, 0); - return result; - } - - if (instr_is_comptime(casted_op)) { - size_t result_usize = bigint_clz(&op->value.data.x_bigint, - op->value.type->data.integral.bit_count); - IrInstruction *result = ir_const(ira, &instruction->base, return_type); - bigint_init_unsigned(&result->value.data.x_bigint, result_usize); - return result; + if (instr_is_comptime(op)) { + ConstExprValue *val = ir_resolve_const(ira, op, UndefOk); + if (val == nullptr) + return ira->codegen->invalid_instruction; + if (val->special == ConstValSpecialUndef) + return ir_const_undef(ira, &instruction->base, ira->codegen->builtin_types.entry_num_lit_int); + size_t result_usize = bigint_clz(&op->value.data.x_bigint, int_type->data.integral.bit_count); + return ir_const_unsigned(ira, &instruction->base, result_usize); } + ZigType *return_type = get_smallest_unsigned_int_type(ira->codegen, int_type->data.integral.bit_count); IrInstruction *result = ir_build_clz(&ira->new_irb, instruction->base.scope, - instruction->base.source_node, nullptr, casted_op); + instruction->base.source_node, nullptr, op); result->value.type = return_type; return result; } static IrInstruction *ir_analyze_instruction_pop_count(IrAnalyze *ira, IrInstructionPopCount *instruction) { - ZigType *int_type = ir_resolve_type(ira, instruction->type->child); + ZigType *int_type = ir_resolve_int_type(ira, instruction->type->child); if (type_is_invalid(int_type)) return ira->codegen->invalid_instruction; - IrInstruction *op = instruction->op->child; - - if (int_type->id != ZigTypeIdInt) { - ir_add_error(ira, instruction->type, - buf_sprintf("expected integer type, found '%s'", buf_ptr(&int_type->name))); - return ira->codegen->invalid_instruction; - } - - IrInstruction *casted_op = ir_implicit_cast(ira, op, int_type); - if (type_is_invalid(casted_op->value.type)) + IrInstruction *op = ir_implicit_cast(ira, instruction->op->child, int_type); + if (type_is_invalid(op->value.type)) return ira->codegen->invalid_instruction; - ZigType *return_type = get_smallest_popcount_unsigned_int_type(ira->codegen, int_type->data.integral.bit_count); + if (int_type->data.integral.bit_count == 0) + return ir_const_unsigned(ira, &instruction->base, 0); - if (int_type->data.integral.bit_count == 0) { - IrInstruction *result = ir_const(ira, &instruction->base, return_type); - bigint_init_unsigned(&result->value.data.x_bigint, 0); - return result; - } - - if (instr_is_comptime(casted_op)) { - ConstExprValue *val = ir_resolve_const(ira, casted_op, UndefBad); - if (!val) + if (instr_is_comptime(op)) { + ConstExprValue *val = ir_resolve_const(ira, op, UndefOk); + if (val == nullptr) return ira->codegen->invalid_instruction; + if (val->special == ConstValSpecialUndef) + return ir_const_undef(ira, &instruction->base, ira->codegen->builtin_types.entry_num_lit_int); if (bigint_cmp_zero(&val->data.x_bigint) != CmpLT) { size_t result = bigint_popcount_unsigned(&val->data.x_bigint); return ir_const_unsigned(ira, &instruction->base, result); } - size_t result = bigint_popcount_signed(&val->data.x_bigint, op->value.type->data.integral.bit_count); + size_t result = bigint_popcount_signed(&val->data.x_bigint, int_type->data.integral.bit_count); return ir_const_unsigned(ira, &instruction->base, result); } + ZigType *return_type = get_smallest_unsigned_int_type(ira->codegen, int_type->data.integral.bit_count); IrInstruction *result = ir_build_pop_count(&ira->new_irb, instruction->base.scope, - instruction->base.source_node, nullptr, casted_op); + instruction->base.source_node, nullptr, op); result->value.type = return_type; return result; } @@ -23002,21 +22986,22 @@ static IrInstruction *ir_analyze_instruction_sqrt(IrAnalyze *ira, IrInstructionS } static IrInstruction *ir_analyze_instruction_bswap(IrAnalyze *ira, IrInstructionBswap *instruction) { - ZigType *int_type = ir_resolve_type(ira, instruction->type->child); + ZigType *int_type = ir_resolve_int_type(ira, instruction->type->child); if (type_is_invalid(int_type)) return ira->codegen->invalid_instruction; - IrInstruction *op = instruction->op->child; - - if (int_type->id != ZigTypeIdInt) { - ir_add_error(ira, instruction->type, - buf_sprintf("expected integer type, found '%s'", buf_ptr(&int_type->name))); + IrInstruction *op = ir_implicit_cast(ira, instruction->op->child, int_type); + if (type_is_invalid(op->value.type)) return ira->codegen->invalid_instruction; + + if (int_type->data.integral.bit_count == 0) { + IrInstruction *result = ir_const(ira, &instruction->base, int_type); + bigint_init_unsigned(&result->value.data.x_bigint, 0); + return result; } - IrInstruction *casted_op = ir_implicit_cast(ira, op, int_type); - if (type_is_invalid(casted_op->value.type)) - return ira->codegen->invalid_instruction; + if (int_type->data.integral.bit_count == 8) + return op; if (int_type->data.integral.bit_count % 8 != 0) { ir_add_error(ira, instruction->op, @@ -23025,20 +23010,12 @@ static IrInstruction *ir_analyze_instruction_bswap(IrAnalyze *ira, IrInstruction return ira->codegen->invalid_instruction; } - if (int_type->data.integral.bit_count == 0) { - IrInstruction *result = ir_const(ira, &instruction->base, int_type); - bigint_init_unsigned(&result->value.data.x_bigint, 0); - return result; - } - - if (int_type->data.integral.bit_count == 8) { - return op; - } - - if (instr_is_comptime(casted_op)) { - ConstExprValue *val = ir_resolve_const(ira, casted_op, UndefBad); - if (!val) + if (instr_is_comptime(op)) { + ConstExprValue *val = ir_resolve_const(ira, op, UndefOk); + if (val == nullptr) return ira->codegen->invalid_instruction; + if (val->special == ConstValSpecialUndef) + return ir_const_undef(ira, &instruction->base, int_type); IrInstruction *result = ir_const(ira, &instruction->base, int_type); size_t buf_size = int_type->data.integral.bit_count / 8; @@ -23050,26 +23027,18 @@ static IrInstruction *ir_analyze_instruction_bswap(IrAnalyze *ira, IrInstruction } IrInstruction *result = ir_build_bswap(&ira->new_irb, instruction->base.scope, - instruction->base.source_node, nullptr, casted_op); + instruction->base.source_node, nullptr, op); result->value.type = int_type; return result; } static IrInstruction *ir_analyze_instruction_bit_reverse(IrAnalyze *ira, IrInstructionBitReverse *instruction) { - ZigType *int_type = ir_resolve_type(ira, instruction->type->child); + ZigType *int_type = ir_resolve_int_type(ira, instruction->type->child); if (type_is_invalid(int_type)) return ira->codegen->invalid_instruction; - IrInstruction *op = instruction->op->child; - - if (int_type->id != ZigTypeIdInt) { - ir_add_error(ira, instruction->type, - buf_sprintf("expected integer type, found '%s'", buf_ptr(&int_type->name))); - return ira->codegen->invalid_instruction; - } - - IrInstruction *casted_op = ir_implicit_cast(ira, op, int_type); - if (type_is_invalid(casted_op->value.type)) + IrInstruction *op = ir_implicit_cast(ira, instruction->op->child, int_type); + if (type_is_invalid(op->value.type)) return ira->codegen->invalid_instruction; if (int_type->data.integral.bit_count == 0) { @@ -23078,10 +23047,12 @@ static IrInstruction *ir_analyze_instruction_bit_reverse(IrAnalyze *ira, IrInstr return result; } - if (instr_is_comptime(casted_op)) { - ConstExprValue *val = ir_resolve_const(ira, casted_op, UndefBad); - if (!val) + if (instr_is_comptime(op)) { + ConstExprValue *val = ir_resolve_const(ira, op, UndefOk); + if (val == nullptr) return ira->codegen->invalid_instruction; + if (val->special == ConstValSpecialUndef) + return ir_const_undef(ira, &instruction->base, int_type); IrInstruction *result = ir_const(ira, &instruction->base, int_type); size_t num_bits = int_type->data.integral.bit_count; @@ -23111,7 +23082,7 @@ static IrInstruction *ir_analyze_instruction_bit_reverse(IrAnalyze *ira, IrInstr } IrInstruction *result = ir_build_bit_reverse(&ira->new_irb, instruction->base.scope, - instruction->base.source_node, nullptr, casted_op); + instruction->base.source_node, nullptr, op); result->value.type = int_type; return result; } diff --git a/test/stage1/behavior/bitreverse.zig b/test/stage1/behavior/bitreverse.zig index d1de3997fb..2b0eb71fb6 100644 --- a/test/stage1/behavior/bitreverse.zig +++ b/test/stage1/behavior/bitreverse.zig @@ -9,17 +9,17 @@ test "@bitReverse" { fn testBitReverse() void { // using comptime_ints, unsigned - expect(@bitReverse(u0, u0(0)) == 0); - expect(@bitReverse(u5, u5(0x12)) == 0x9); - expect(@bitReverse(u8, u8(0x12)) == 0x48); - expect(@bitReverse(u16, u16(0x1234)) == 0x2c48); - expect(@bitReverse(u24, u24(0x123456)) == 0x6a2c48); - expect(@bitReverse(u32, u32(0x12345678)) == 0x1e6a2c48); - expect(@bitReverse(u40, u40(0x123456789a)) == 0x591e6a2c48); - expect(@bitReverse(u48, u48(0x123456789abc)) == 0x3d591e6a2c48); - expect(@bitReverse(u56, u56(0x123456789abcde)) == 0x7b3d591e6a2c48); - expect(@bitReverse(u64, u64(0x123456789abcdef1)) == 0x8f7b3d591e6a2c48); - expect(@bitReverse(u128, u128(0x123456789abcdef11121314151617181)) == 0x818e868a828c84888f7b3d591e6a2c48); + expect(@bitReverse(u0, 0) == 0); + expect(@bitReverse(u5, 0x12) == 0x9); + expect(@bitReverse(u8, 0x12) == 0x48); + expect(@bitReverse(u16, 0x1234) == 0x2c48); + expect(@bitReverse(u24, 0x123456) == 0x6a2c48); + expect(@bitReverse(u32, 0x12345678) == 0x1e6a2c48); + expect(@bitReverse(u40, 0x123456789a) == 0x591e6a2c48); + expect(@bitReverse(u48, 0x123456789abc) == 0x3d591e6a2c48); + expect(@bitReverse(u56, 0x123456789abcde) == 0x7b3d591e6a2c48); + expect(@bitReverse(u64, 0x123456789abcdef1) == 0x8f7b3d591e6a2c48); + expect(@bitReverse(u128, 0x123456789abcdef11121314151617181) == 0x818e868a828c84888f7b3d591e6a2c48); // using runtime uints, unsigned var num0: u0 = 0; diff --git a/test/stage1/behavior/bugs/2114.zig b/test/stage1/behavior/bugs/2114.zig index f24899649b..e266279564 100644 --- a/test/stage1/behavior/bugs/2114.zig +++ b/test/stage1/behavior/bugs/2114.zig @@ -3,7 +3,7 @@ const expect = std.testing.expect; const math = std.math; fn ctz(x: var) usize { - return @ctz(u128, x); + return @ctz(@typeOf(x), x); } test "fixed" { diff --git a/test/stage1/behavior/byteswap.zig b/test/stage1/behavior/byteswap.zig index 408210f3e1..3e7c34cb85 100644 --- a/test/stage1/behavior/byteswap.zig +++ b/test/stage1/behavior/byteswap.zig @@ -7,16 +7,16 @@ test "@byteSwap" { } fn testByteSwap() void { - expect(@byteSwap(u0, u0(0)) == 0); - expect(@byteSwap(u8, u8(0x12)) == 0x12); - expect(@byteSwap(u16, u16(0x1234)) == 0x3412); - expect(@byteSwap(u24, u24(0x123456)) == 0x563412); - expect(@byteSwap(u32, u32(0x12345678)) == 0x78563412); - expect(@byteSwap(u40, u40(0x123456789a)) == 0x9a78563412); - expect(@byteSwap(i48, u48(0x123456789abc)) == @bitCast(i48, u48(0xbc9a78563412))); - expect(@byteSwap(u56, u56(0x123456789abcde)) == 0xdebc9a78563412); - expect(@byteSwap(u64, u64(0x123456789abcdef1)) == 0xf1debc9a78563412); - expect(@byteSwap(u128, u128(0x123456789abcdef11121314151617181)) == 0x8171615141312111f1debc9a78563412); + expect(@byteSwap(u0, 0) == 0); + expect(@byteSwap(u8, 0x12) == 0x12); + expect(@byteSwap(u16, 0x1234) == 0x3412); + expect(@byteSwap(u24, 0x123456) == 0x563412); + expect(@byteSwap(u32, 0x12345678) == 0x78563412); + expect(@byteSwap(u40, 0x123456789a) == 0x9a78563412); + expect(@byteSwap(i48, 0x123456789abc) == @bitCast(i48, u48(0xbc9a78563412))); + expect(@byteSwap(u56, 0x123456789abcde) == 0xdebc9a78563412); + expect(@byteSwap(u64, 0x123456789abcdef1) == 0xf1debc9a78563412); + expect(@byteSwap(u128, 0x123456789abcdef11121314151617181) == 0x8171615141312111f1debc9a78563412); expect(@byteSwap(u0, u0(0)) == 0); expect(@byteSwap(i8, i8(-50)) == -50); diff --git a/test/stage1/behavior/math.zig b/test/stage1/behavior/math.zig index 83f09fae41..18e7fc9dcb 100644 --- a/test/stage1/behavior/math.zig +++ b/test/stage1/behavior/math.zig @@ -114,12 +114,12 @@ test "@clz" { } fn testClz() void { - expect(clz(u8, u8(0b10001010)) == 0); - expect(clz(u8, u8(0b00001010)) == 4); - expect(clz(u8, u8(0b00011010)) == 3); - expect(clz(u8, u8(0b00000000)) == 8); - expect(clz(u128, u128(0xffffffffffffffff)) == 64); - expect(clz(u128, u128(0x10000000000000000)) == 63); + expect(clz(u8, 0b10001010) == 0); + expect(clz(u8, 0b00001010) == 4); + expect(clz(u8, 0b00011010) == 3); + expect(clz(u8, 0b00000000) == 8); + expect(clz(u128, 0xffffffffffffffff) == 64); + expect(clz(u128, 0x10000000000000000) == 63); } fn clz(comptime T: type, x: T) usize { @@ -132,27 +132,16 @@ test "@ctz" { } fn testCtz() void { - expect(ctz(u8, u8(0b10100000)) == 5); - expect(ctz(u8, u8(0b10001010)) == 1); - expect(ctz(u8, u8(0b00000000)) == 8); - expect(ctz(u16, u16(0b00000000)) == 16); + expect(ctz(u8, 0b10100000) == 5); + expect(ctz(u8, 0b10001010) == 1); + expect(ctz(u8, 0b00000000) == 8); + expect(ctz(u16, 0b00000000) == 16); } fn ctz(comptime T: type, x: T) usize { return @ctz(T, x); } -pub fn Log2Int(comptime T: type) type { - // comptime ceil log2 - comptime var count = 0; - comptime var s = T.bit_count - 1; - inline while (s != 0) : (s >>= 1) { - count += 1; - } - - return @IntType(false, count); -} - test "assignment operators" { var i: u32 = 0; i += 5; diff --git a/test/stage1/behavior/popcount.zig b/test/stage1/behavior/popcount.zig index 02d4531758..327bee62a1 100644 --- a/test/stage1/behavior/popcount.zig +++ b/test/stage1/behavior/popcount.zig @@ -38,7 +38,7 @@ fn testPopCount() void { expect(@popCount(u8, @bitCast(u8, i8(-120))) == 2); } comptime { - expect(@popCount(i128, u128(0b11111111000110001100010000100001000011000011100101010001)) == 24); + expect(@popCount(i128, 0b11111111000110001100010000100001000011000011100101010001) == 24); } }