Berry upstream fix mod 0 (#21174)

* Berry upstream fix mod 0

* Add test case
This commit is contained in:
s-hadinger 2024-04-14 14:55:20 +02:00 committed by GitHub
parent a2ad349487
commit 105aa03198
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
2 changed files with 76 additions and 21 deletions

View File

@ -723,22 +723,20 @@ newframe: /* a new call frame */
}
} else if (var_isnumber(a) && var_isnumber(b)) {
#if CONFIG_IDF_TARGET_ESP32 /* when running on ESP32 in IRAM, there is a bug in early chip revision */
union bvaldata x, y; // TASMOTA workaround for ESP32 rev0 bug
x.i = a->v.i;
if (var_isint(a)) { x.r = (breal) x.i; }
y.i = b->v.i;
if (var_isint(b)) { y.r = (breal) y.i; }
if (y.r == cast(breal, 0)) {
vm_error(vm, "divzero_error", "division by zero");
}
var_setreal(dst, x.r / y.r);
union bvaldata x0, y0; // TASMOTA workaround for ESP32 rev0 bug
x0.i = a->v.i;
if (var_isint(a)) { x0.r = (breal) x0.i; }
y0.i = b->v.i;
if (var_isint(b)) { y0.r = (breal) y0.i; }
breal x = x0.r, y = y0.r;
#else // CONFIG_IDF_TARGET_ESP32
breal x = var2real(a), y = var2real(b);
#endif // CONFIG_IDF_TARGET_ESP32
if (y == cast(breal, 0)) {
vm_error(vm, "divzero_error", "division by zero");
} else {
var_setreal(dst, x / y);
}
var_setreal(dst, x / y);
#endif // CONFIG_IDF_TARGET_ESP32
} else if (var_isinstance(a)) {
ins_binop(vm, "/", ins);
} else {
@ -749,18 +747,28 @@ newframe: /* a new call frame */
opcase(MOD): {
bvalue *dst = RA(), *a = RKB(), *b = RKC();
if (var_isint(a) && var_isint(b)) {
var_setint(dst, ibinop(%, a, b));
bint x = var_toint(a), y = var_toint(b);
if (y == 0) {
vm_error(vm, "divzero_error", "division by zero");
} else {
var_setint(dst, x % y);
}
} else if (var_isnumber(a) && var_isnumber(b)) {
#if CONFIG_IDF_TARGET_ESP32 /* when running on ESP32 in IRAM, there is a bug in early chip revision */
union bvaldata x, y; // TASMOTA workaround for ESP32 rev0 bug
x.i = a->v.i;
if (var_isint(a)) { x.r = (breal) x.i; }
y.i = b->v.i;
if (var_isint(b)) { y.r = (breal) y.i; }
var_setreal(dst, mathfunc(fmod)(x.r, y.r));
#else // CONFIG_IDF_TARGET_ESP32
var_setreal(dst, mathfunc(fmod)(var_toreal(a), var_toreal(b)));
#endif // CONFIG_IDF_TARGET_ESP32
union bvaldata x0, y0; // TASMOTA workaround for ESP32 rev0 bug
x0.i = a->v.i;
if (var_isint(a)) { x0.r = (breal) x0.i; }
y0.i = b->v.i;
if (var_isint(b)) { y0.r = (breal) y0.i; }
breal x = x0.r, y = y0.r;
#else
breal x = var2real(a), y = var2real(b);
#endif
if (y == cast(breal, 0)) {
vm_error(vm, "divzero_error", "division by zero");
} else {
var_setreal(dst, mathfunc(fmod)(x, y));
}
} else if (var_isinstance(a)) {
ins_binop(vm, "%", ins);
} else {

View File

@ -0,0 +1,47 @@
try
# Test integer division
var div = 1/0
assert(false) # Should not reach this point
except .. as e,m
assert(e == "divzero_error")
assert(m == "division by zero")
end
try
# Test integer modulo
var div = 1%0
assert(false)
except .. as e,m
assert(e == "divzero_error")
assert(m == "division by zero")
end
try
# Test float division
var div = 1.1/0.0
assert(false)
except .. as e,m
assert(e == "divzero_error")
assert(m == "division by zero")
end
try
# Test float modulo
var div = 1.1%0.0
assert(false)
except .. as e,m
assert(e == "divzero_error")
assert(m == "division by zero")
end
# Check normal division & modulo
assert(1/2 == 0)
assert(1%2 == 1)
assert(1.0/2.0 == 0.5)
assert(1.0%2.0 == 1.0)
assert(4/2 == 2)
assert(4%2 == 0)