Diff
Modified: trunk/JSTests/ChangeLog (287545 => 287546)
--- trunk/JSTests/ChangeLog 2022-01-03 17:00:53 UTC (rev 287545)
+++ trunk/JSTests/ChangeLog 2022-01-03 17:46:10 UTC (rev 287546)
@@ -1,5 +1,16 @@
2022-01-03 Yusuke Suzuki <[email protected]>
+ [JSC] Fix Intl.PluralRules.selectRange input validation
+ https://bugs.webkit.org/show_bug.cgi?id=234817
+
+ Reviewed by Alexey Shvayka.
+
+ * stress/intl-pluralrules-select-range-validate-inputs.js: Added.
+ (shouldThrow):
+ (Intl.PluralRules.prototype.selectRange.shouldThrow):
+
+2022-01-03 Yusuke Suzuki <[email protected]>
+
[JSC] Update UCD to Unicode 14.0.0
https://bugs.webkit.org/show_bug.cgi?id=234811
Added: trunk/JSTests/stress/intl-pluralrules-select-range-validate-inputs.js (0 => 287546)
--- trunk/JSTests/stress/intl-pluralrules-select-range-validate-inputs.js (rev 0)
+++ trunk/JSTests/stress/intl-pluralrules-select-range-validate-inputs.js 2022-01-03 17:46:10 UTC (rev 287546)
@@ -0,0 +1,42 @@
+function shouldThrow(func, errorMessage) {
+ var errorThrown = false;
+ var error = null;
+ try {
+ func();
+ } catch (e) {
+ errorThrown = true;
+ error = e;
+ }
+ if (!errorThrown)
+ throw new Error('not thrown');
+ if (String(error) !== errorMessage)
+ throw new Error(`bad error: ${String(error)}`);
+}
+
+if (Intl.PluralRules.prototype.selectRange) {
+ let pl = new Intl.PluralRules('en-US');
+ shouldThrow(() => {
+ pl.selectRange();
+ }, `TypeError: start or end is undefined`);
+ shouldThrow(() => {
+ pl.selectRange(0, undefined);
+ }, `TypeError: start or end is undefined`);
+ shouldThrow(() => {
+ pl.selectRange(undefined, 0);
+ }, `TypeError: start or end is undefined`);
+ shouldThrow(() => {
+ pl.selectRange(undefined, undefined);
+ }, `TypeError: start or end is undefined`);
+ shouldThrow(() => {
+ pl.selectRange(NaN, 0);
+ }, `RangeError: Passed numbers are out of range`);
+ shouldThrow(() => {
+ pl.selectRange(0, NaN);
+ }, `RangeError: Passed numbers are out of range`);
+ shouldThrow(() => {
+ pl.selectRange(NaN, NaN);
+ }, `RangeError: Passed numbers are out of range`);
+ shouldThrow(() => {
+ pl.selectRange(0, -0);
+ }, `RangeError: start is larger than end`);
+}
Modified: trunk/Source/_javascript_Core/ChangeLog (287545 => 287546)
--- trunk/Source/_javascript_Core/ChangeLog 2022-01-03 17:00:53 UTC (rev 287545)
+++ trunk/Source/_javascript_Core/ChangeLog 2022-01-03 17:46:10 UTC (rev 287546)
@@ -1,5 +1,21 @@
2022-01-03 Yusuke Suzuki <[email protected]>
+ [JSC] Fix Intl.PluralRules.selectRange input validation
+ https://bugs.webkit.org/show_bug.cgi?id=234817
+
+ Reviewed by Alexey Shvayka.
+
+ Add specified argument validation[1] to Intl.PluralRules.selectRange.
+
+ [1]: https://tc39.es/proposal-intl-numberformat-v3/out/pluralrules/proposed.html#sec-intl.pluralrules.prototype.selectrange
+
+ * runtime/IntlPluralRules.cpp:
+ (JSC::IntlPluralRules::selectRange const):
+ * runtime/IntlPluralRulesPrototype.cpp:
+ (JSC::JSC_DEFINE_HOST_FUNCTION):
+
+2022-01-03 Yusuke Suzuki <[email protected]>
+
[JSC] Update UCD to Unicode 14.0.0
https://bugs.webkit.org/show_bug.cgi?id=234811
Modified: trunk/Source/_javascript_Core/runtime/IntlPluralRules.cpp (287545 => 287546)
--- trunk/Source/_javascript_Core/runtime/IntlPluralRules.cpp 2022-01-03 17:00:53 UTC (rev 287545)
+++ trunk/Source/_javascript_Core/runtime/IntlPluralRules.cpp 2022-01-03 17:46:10 UTC (rev 287546)
@@ -279,11 +279,15 @@
VM& vm = globalObject->vm();
auto scope = DECLARE_THROW_SCOPE(vm);
- if (start > end) {
- throwRangeError(globalObject, scope, "start is larger than end"_s);
- return { };
- }
+ if (std::isnan(start) || std::isnan(end))
+ return throwRangeError(globalObject, scope, "Passed numbers are out of range"_s);
+ if (end < start)
+ return throwRangeError(globalObject, scope, "start is larger than end"_s);
+
+ if (isNegativeZero(end) && start >= 0)
+ return throwRangeError(globalObject, scope, "start is larger than end"_s);
+
UErrorCode status = U_ZERO_ERROR;
auto range = std::unique_ptr<UFormattedNumberRange, ICUDeleter<unumrf_closeResult>>(unumrf_openResult(&status));
if (U_FAILURE(status))
Modified: trunk/Source/_javascript_Core/runtime/IntlPluralRulesPrototype.cpp (287545 => 287546)
--- trunk/Source/_javascript_Core/runtime/IntlPluralRulesPrototype.cpp 2022-01-03 17:00:53 UTC (rev 287545)
+++ trunk/Source/_javascript_Core/runtime/IntlPluralRulesPrototype.cpp 2022-01-03 17:46:10 UTC (rev 287546)
@@ -110,10 +110,16 @@
if (!pluralRules)
return JSValue::encode(throwTypeError(globalObject, scope, "Intl.PluralRules.prototype.selectRange called on value that's not a PluralRules"_s));
- double start = callFrame->argument(0).toNumber(globalObject);
+ JSValue startValue = callFrame->argument(0);
+ JSValue endValue = callFrame->argument(1);
+
+ if (startValue.isUndefined() || endValue.isUndefined())
+ return throwVMTypeError(globalObject, scope, "start or end is undefined"_s);
+
+ double start = startValue.toNumber(globalObject);
RETURN_IF_EXCEPTION(scope, { });
- double end = callFrame->argument(1).toNumber(globalObject);
+ double end = endValue.toNumber(globalObject);
RETURN_IF_EXCEPTION(scope, { });
RELEASE_AND_RETURN(scope, JSValue::encode(pluralRules->selectRange(globalObject, start, end)));