From 86fbeb6fcd638e2350b09a43dde355f9830e75da Mon Sep 17 00:00:00 2001
From: David Degazio <d_degazio@apple.com>
Date: Tue, 8 Nov 2022 19:54:33 -0800
Subject: [PATCH] Intl.Locale.prototype.hourCycles leaks empty JSValue to
 script https://bugs.webkit.org/show_bug.cgi?id=247562 rdar://102031379

Reviewed by Mark Lam.

We currently don't check if IntlLocale::hourCycles returns a null JSArray, which allows it
to be encoded as an empty JSValue and exposed to user code. This patch throws a TypeError
when udatpg_open returns a failed status.

* JSTests/stress/intl-locale-invalid-hourCycles.js: Added.
(main):
* Source/JavaScriptCore/runtime/IntlLocale.cpp:
(JSC::IntlLocale::hourCycles):

Canonical link: https://commits.webkit.org/256473@main

CVE:CVE-2022-46700

Upstream-Status: Backport
[https://github.com/WebKit/WebKit/commit/86fbeb6fcd638e2350b09a43dde355f9830e75da]

Signed-off-by: Yogita Urade <yogita.urade@windriver.com>
---
 JSTests/stress/intl-locale-invalid-hourCycles.js | 12 ++++++++++++
 Source/JavaScriptCore/runtime/IntlLocale.cpp     |  4 +++-
 2 files changed, 15 insertions(+), 1 deletion(-)
 create mode 100644 JSTests/stress/intl-locale-invalid-hourCycles.js

diff --git a/JSTests/stress/intl-locale-invalid-hourCycles.js b/JSTests/stress/intl-locale-invalid-hourCycles.js
new file mode 100644
index 000000000000..7b94eb844764
--- /dev/null
+++ b/JSTests/stress/intl-locale-invalid-hourCycles.js
@@ -0,0 +1,12 @@
+function main() {
+    const v24 = new Intl.Locale("trimEnd", { 'numberingSystem': "foobar" });
+    let empty = v24.hourCycles;
+    print(empty);
+}
+
+try {
+    main();
+} catch (e) {
+    if (!(e instanceof TypeError))
+        throw e;
+}
diff --git a/Source/JavaScriptCore/runtime/IntlLocale.cpp b/Source/JavaScriptCore/runtime/IntlLocale.cpp
index c3c346163a18..bef424727a8a 100644
--- a/Source/JavaScriptCore/runtime/IntlLocale.cpp
+++ b/Source/JavaScriptCore/runtime/IntlLocale.cpp
@@ -632,8 +632,10 @@ JSArray* IntlLocale::hourCycles(JSGlobalObject* globalObject)

     UErrorCode status = U_ZERO_ERROR;
     auto generator = std::unique_ptr<UDateTimePatternGenerator, ICUDeleter<udatpg_close>>(udatpg_open(m_localeID.data(), &status));
-    if (U_FAILURE(status))
+    if (U_FAILURE(status)) {
+        throwTypeError(globalObject, scope, "invalid locale"_s);
         return nullptr;
+    }

     // Use "j" skeleton and parse pattern to retrieve the configured hour-cycle information.
     constexpr const UChar skeleton[] = { 'j', 0 };
--
2.40.0
