You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
The recent addition for overflow checking is good. This kind of error (albeit not as explicit as demonstrated here) should be caught: let foo: u8 = 200 * 5;. Clearly the value 1000 (one-thousand) can not fit into 8-bits and so an overflow error is raised.
HOWEVER these checks are triggering on bitwise operations, notably bitshifts. This is very, very bad. For integers bitwise operations cannot overflow their operands by design.
I don't know the exact reason within the compiler internals but if I had to guess I would say that the compiler is equating 200 << 5 to 200 ** 5 and checking if that value can be represented with 8-bits, here 320 000 000 000 cannot fit in 8-bits, except 200 << 5 is not 320 000 000 000 it's 0. Bits shift "off" the MSB side and bits shifted "on" the LSB side are 0. The value 0 can indeed be represented by an 8-bit integer.
Note, wrapping_mul is not appropriate here for bitshifts because the intention is not to multiply the value it's to move bits 5 places to the left with the "drop off" and "insert on" behaviour that every other programming language (and the design of bitwise operators) performs.
Happy Case
Revert the overflow checking on bitwise operations because by definition bitwise operations cannot overflow integer values.
Alternatives Considered
No response
Additional Context
No response
Would you like to submit a PR for this Issue?
No
Support Needs
No response
The text was updated successfully, but these errors were encountered:
It turns out that your comment is still valid though: let bar: u8 = 200 << 5; // INCORRECT OVERFLOW ERROR RAISED!
Rust overflows with <<8 but not with <<5 (for 8 bits unsigned), even if the result overflow the bit size.
I will fix this issue so that Noir behaviour is the same as Rust.
Problem
The recent addition for overflow checking is good. This kind of error (albeit not as explicit as demonstrated here) should be caught:
let foo: u8 = 200 * 5;
. Clearly the value1000
(one-thousand) can not fit into 8-bits and so an overflow error is raised.HOWEVER these checks are triggering on bitwise operations, notably bitshifts. This is very, very bad. For integers bitwise operations cannot overflow their operands by design.
I don't know the exact reason within the compiler internals but if I had to guess I would say that the compiler is equating
200 << 5
to200 ** 5
and checking if that value can be represented with 8-bits, here320 000 000 000
cannot fit in 8-bits, except200 << 5
is not320 000 000 000
it's0
. Bits shift "off" the MSB side and bits shifted "on" the LSB side are0
. The value0
can indeed be represented by an 8-bit integer.Note,
wrapping_mul
is not appropriate here for bitshifts because the intention is not to multiply the value it's to move bits 5 places to the left with the "drop off" and "insert on" behaviour that every other programming language (and the design of bitwise operators) performs.Happy Case
Revert the overflow checking on bitwise operations because by definition bitwise operations cannot overflow integer values.
Alternatives Considered
No response
Additional Context
No response
Would you like to submit a PR for this Issue?
No
Support Needs
No response
The text was updated successfully, but these errors were encountered: