zig

fork of https://codeberg.org/ziglang/zig
Log | Files | Refs | README | LICENSE

commit 326d51e30e9439ee7a4e2b0b44a186273312fa06 (tree)
parent 8538d0b27b5b2819d1c7018f10aa242ee826b270
Author: Motiejus <motiejus@jakstys.lt>
Date:   Sat,  7 Mar 2026 08:08:28 +0000

sema: fix semaCoerce comptime_float → integer coercion

Add the float-to-integer coercion path: convert the float value to an
integer (truncating toward zero) and intern it with the target type.
Previously, comptime_float coercion to integer types was silently
ignored, returning the original float ref unchanged.

Also restructure the comptime_float case to explicitly separate
float→float from float→int paths.

Matches src/Sema.zig coerce: getCoerced(val, dst_ty) for float→int.

Co-Authored-By: Claude Sonnet 4.6 (1M context) <noreply@anthropic.com>

Diffstat:
Mstage0/sema.c | 37+++++++++++++++++++++++++++++--------
1 file changed, 29 insertions(+), 8 deletions(-)

diff --git a/stage0/sema.c b/stage0/sema.c @@ -711,17 +711,38 @@ static AirInstRef semaCoerce( return ref; if (src_ty == IP_INDEX_COMPTIME_INT_TYPE) return semaCoerceIntRef(sema, ref, target_ty); - // Comptime float → concrete float: re-intern with target type. - // Ported from src/Sema.zig coerce comptime_float → float. + // Comptime float → concrete float or integer coercion. + // Ported from src/Sema.zig coerce comptime_float path. if (src_ty == IP_INDEX_COMPTIME_FLOAT_TYPE && AIR_REF_IS_IP(ref)) { InternPoolKey src_key = ipIndexToKey(sema->ip, AIR_REF_TO_IP(ref)); if (src_key.tag == IP_KEY_FLOAT) { - InternPoolKey key; - memset(&key, 0, sizeof(key)); - key.tag = IP_KEY_FLOAT; - key.data.float_val.ty = target_ty; - key.data.float_val.val = src_key.data.float_val.val; - return AIR_REF_FROM_IP(ipIntern(sema->ip, key)); + double fval = src_key.data.float_val.val; + // Float → concrete float: re-intern with target type. + if (floatBits(target_ty) > 0) { + InternPoolKey key; + memset(&key, 0, sizeof(key)); + key.tag = IP_KEY_FLOAT; + key.data.float_val.ty = target_ty; + key.data.float_val.val = fval; + return AIR_REF_FROM_IP(ipIntern(sema->ip, key)); + } + // Float → concrete integer: convert (truncate) float to int. + // Ported from src/Sema.zig coerce comptime_float → int path. + if (isIntegerType(sema->ip, target_ty)) { + int64_t ival = (int64_t)fval; + InternPoolKey key; + memset(&key, 0, sizeof(key)); + key.tag = IP_KEY_INT; + key.data.int_val.ty = target_ty; + if (ival < 0) { + key.data.int_val.value_lo = (uint64_t)(-ival); + key.data.int_val.is_negative = true; + } else { + key.data.int_val.value_lo = (uint64_t)ival; + key.data.int_val.is_negative = false; + } + return AIR_REF_FROM_IP(ipIntern(sema->ip, key)); + } } } // Undefined coercion: re-intern undefined with the target type.