mirror of
https://github.com/odin-lang/Odin.git
synced 2026-02-12 22:33:36 +00:00
Fixed some issues with in and not_in on constant bit_sets.
This addresses two issues: - With a `bit_set` having no underlying type and a non-zero lower bound, `in` and `not_in` were returning incorrect results when done at compile-time. - With a `bit_set` of more than 128 bits, `in` always returns false on values that fall within the upper 64 bits.
This commit is contained in:
@@ -4125,15 +4125,19 @@ gb_internal void check_binary_expr(CheckerContext *c, Operand *x, Ast *node, Typ
|
||||
i64 upper = yt->BitSet.upper;
|
||||
|
||||
if (lower <= key && key <= upper) {
|
||||
i64 bit = 1ll<<key;
|
||||
i64 bits = big_int_to_i64(&v.value_integer);
|
||||
BigInt idx = big_int_make_i64(key - lower);
|
||||
BigInt bit = big_int_make_i64(1);
|
||||
big_int_shl_eq(&bit, &idx);
|
||||
|
||||
BigInt mask = {};
|
||||
big_int_and(&mask, &bit, &v.value_integer);
|
||||
|
||||
x->mode = Addressing_Constant;
|
||||
x->type = t_untyped_bool;
|
||||
if (op.kind == Token_in) {
|
||||
x->value = exact_value_bool((bit & bits) != 0);
|
||||
x->value = exact_value_bool(!big_int_is_zero(&mask));
|
||||
} else {
|
||||
x->value = exact_value_bool((bit & bits) == 0);
|
||||
x->value = exact_value_bool(big_int_is_zero(&mask));
|
||||
}
|
||||
x->expr = node;
|
||||
return;
|
||||
|
||||
Reference in New Issue
Block a user