From 0a05f04d1bc7fe6dd5ebaa8204c720b43bede626 Mon Sep 17 00:00:00 2001 From: Daniel Bertalan Date: Fri, 6 Aug 2021 18:35:33 +0200 Subject: [PATCH] LibJS: Fix UB in `Number.IsSafeInteger` Casting a floating point number to an integer and comparing that against the original value is not a good way to test if it is a whole number. It may cause unnecessary narrowing conversion issues and UB. This was the case, which was caught be Clang's `-fsanitize=float-cast-overflow`. This commit changes the code to use `is_integral_number`, as suggested in ECMA-262. --- Userland/Libraries/LibJS/Runtime/NumberConstructor.cpp | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/Userland/Libraries/LibJS/Runtime/NumberConstructor.cpp b/Userland/Libraries/LibJS/Runtime/NumberConstructor.cpp index 82770468f4..d3e81d2768 100644 --- a/Userland/Libraries/LibJS/Runtime/NumberConstructor.cpp +++ b/Userland/Libraries/LibJS/Runtime/NumberConstructor.cpp @@ -129,8 +129,10 @@ JS_DEFINE_NATIVE_FUNCTION(NumberConstructor::is_safe_integer) { if (!vm.argument(0).is_number()) return Value(false); + if (!vm.argument(0).is_integral_number()) + return Value(false); auto value = vm.argument(0).as_double(); - return Value((int64_t)value == value && value >= MIN_SAFE_INTEGER_VALUE && value <= MAX_SAFE_INTEGER_VALUE); + return Value(value >= MIN_SAFE_INTEGER_VALUE && value <= MAX_SAFE_INTEGER_VALUE); } }