Skip site navigation (1)Skip section navigation (2)
Date:      Tue, 30 Jan 2024 00:41:42 GMT
From:      "Jason E. Hale" <jhale@FreeBSD.org>
To:        ports-committers@FreeBSD.org, dev-commits-ports-all@FreeBSD.org, dev-commits-ports-main@FreeBSD.org
Subject:   git: 21b0f3d56ce0 - main - www/qt6-webengine: Address security vulnerabilities
Message-ID:  <202401300041.40U0fgxA026405@gitrepo.freebsd.org>

next in thread | raw e-mail | index | archive | help
The branch main has been updated by jhale:

URL: https://cgit.FreeBSD.org/ports/commit/?id=21b0f3d56ce0febf1955eaa06240a1a5110bd1ea

commit 21b0f3d56ce0febf1955eaa06240a1a5110bd1ea
Author:     Jason E. Hale <jhale@FreeBSD.org>
AuthorDate: 2024-01-30 00:24:43 +0000
Commit:     Jason E. Hale <jhale@FreeBSD.org>
CommitDate: 2024-01-30 00:41:36 +0000

    www/qt6-webengine: Address security vulnerabilities
    
    Patched with security patches up to Chromium version: 120.0.6099.225
    
    MFH:            2024Q1
    Security:       a25b323a-bed9-11ee-bdd6-4ccc6adda413
---
 www/qt6-webengine/Makefile                    |    2 +-
 www/qt6-webengine/files/patch-security-rollup | 2607 +++++++++++++++++++++++++
 2 files changed, 2608 insertions(+), 1 deletion(-)

diff --git a/www/qt6-webengine/Makefile b/www/qt6-webengine/Makefile
index c3b1d2e759a6..d7371916a4f4 100644
--- a/www/qt6-webengine/Makefile
+++ b/www/qt6-webengine/Makefile
@@ -12,7 +12,7 @@
 
 PORTNAME?=	webengine
 DISTVERSION=	${QT6_VERSION}
-PORTREVISION?=	2 # Master port for print/qt6-pdf. Please keep this line.
+PORTREVISION?=	3 # Master port for print/qt6-pdf. Please keep this line.
 CATEGORIES?=	www
 PKGNAMEPREFIX=	qt6-
 
diff --git a/www/qt6-webengine/files/patch-security-rollup b/www/qt6-webengine/files/patch-security-rollup
index 8b32c0fe79cf..bb16a291c80d 100644
--- a/www/qt6-webengine/files/patch-security-rollup
+++ b/www/qt6-webengine/files/patch-security-rollup
@@ -8,6 +8,23 @@ Addresses the following security issues:
 - CVE-2023-6347
 - CVE-2023-6510
 - Security bug 1485266
+- CVE-2023-6702
+- CVE-2023-6703
+- CVE-2023-6705
+- CVE-2023-6706
+- Security bug 1506726
+- Security bug 1505632
+- Security bug 1488199
+- CVE-2023-7024
+- CVE-2024-0333
+- CVE-2024-0225
+- CVE-2024-0224
+- CVE-2024-0223
+- CVE-2024-0222
+- Security bug 1511689
+- CVE-2024-0519
+- CVE-2025-0518
+- Security bug 1506535
 
 From 669506a53474e3d7637666d3c53f6101fb94d96f Mon Sep 17 00:00:00 2001
 From: Nidhi Jaju <nidhijaju@chromium.org>
@@ -653,3 +670,2593 @@ index dc308525002..48d30860e5e 100644
    absl::optional<DragStart> drag_start_;
  
    // Responsible for handling gesture-nav and pull-to-refresh UI.
+From fe07848de4cd69e57f79528a70c75075ca2951dc Mon Sep 17 00:00:00 2001
+From: Zakhar Voit <voit@google.com>
+Date: Thu, 14 Dec 2023 11:11:43 +0000
+Subject: [PATCH] [Backport] CVE-2023-6702: Type Confusion in V8
+MIME-Version: 1.0
+Content-Type: text/plain; charset=UTF-8
+Content-Transfer-Encoding: 8bit
+
+Cherry-pick of patch originally reviewed on
+https://chromium-review.googlesource.com/c/v8/v8/+/5110982:
+Fix the case when the closure has run
+
+M114 changes:
+- replace IsNativeContext(*context) by context->IsNativeContext()
+
+We were using the closure pointing to NativeContext as a marker that the
+closure has run, but async stack trace code was confused about it.
+
+(cherry picked from commit bde3d360097607f36cd1d17cbe8412b84eae0a7f)
+
+Bug: chromium:1501326
+Change-Id: I30d438f3b2e3fdd7562ea9a79dde4561ce9b0083
+Cr-Original-Commit-Position: refs/heads/main@{#90949}
+Reviewed-on: https://chromium-review.googlesource.com/c/v8/v8/+/5110982
+Commit-Queue: Marja Hölttä <marja@chromium.org>
+Auto-Submit: Marja Hölttä <marja@chromium.org>
+Cr-Commit-Position: refs/branch-heads/12.0@{#18}
+Cr-Branched-From: ed7b4caf1fb8184ad9e24346c84424055d4d430a-refs/heads/12.0.267@{#1}
+Cr-Branched-From: 210e75b19db4352c9b78dce0bae11c2dc3077df4-refs/heads/main@{#90651}
+(cherry picked from commit cbd09b2ca928f1fd929ef52e173aa81213e38cb8)
+Reviewed-on: https://codereview.qt-project.org/c/qt/qtwebengine-chromium/+/526344
+Reviewed-by: Michal Klocek <michal.klocek@qt.io>
+---
+ chromium/v8/src/execution/isolate.cc | 24 +++++++++++++++++++++---
+ 1 file changed, 21 insertions(+), 3 deletions(-)
+
+diff --git a/chromium/v8/src/execution/isolate.cc b/chromium/v8/src/execution/isolate.cc
+index 1c6c464dd6f..d0dc49cd754 100644
+--- src/3rdparty/chromium/v8/src/execution/isolate.cc.orig
++++ src/3rdparty/chromium/v8/src/execution/isolate.cc
+@@ -974,7 +974,13 @@ void CaptureAsyncStackTrace(Isolate* isolate, Handle<JSPromise> promise,
+                                     isolate);
+       builder->AppendPromiseCombinatorFrame(function, combinator);
+ 
+-      // Now peak into the Promise.all() resolve element context to
++      if (context->IsNativeContext()) {
++        // NativeContext is used as a marker that the closure was already
++        // called. We can't access the reject element context any more.
++        return;
++      }
++
++      // Now peek into the Promise.all() resolve element context to
+       // find the promise capability that's being resolved when all
+       // the concurrent promises resolve.
+       int const index =
+@@ -993,7 +999,13 @@ void CaptureAsyncStackTrace(Isolate* isolate, Handle<JSPromise> promise,
+           context->native_context().promise_all_settled(), isolate);
+       builder->AppendPromiseCombinatorFrame(function, combinator);
+ 
+-      // Now peak into the Promise.allSettled() resolve element context to
++      if (context->IsNativeContext()) {
++        // NativeContext is used as a marker that the closure was already
++        // called. We can't access the reject element context any more.
++        return;
++      }
++
++      // Now peek into the Promise.allSettled() resolve element context to
+       // find the promise capability that's being resolved when all
+       // the concurrent promises resolve.
+       int const index =
+@@ -1011,7 +1023,13 @@ void CaptureAsyncStackTrace(Isolate* isolate, Handle<JSPromise> promise,
+                                     isolate);
+       builder->AppendPromiseCombinatorFrame(function, combinator);
+ 
+-      // Now peak into the Promise.any() reject element context to
++      if (context->IsNativeContext()) {
++        // NativeContext is used as a marker that the closure was already
++        // called. We can't access the reject element context any more.
++        return;
++      }
++
++      // Now peek into the Promise.any() reject element context to
+       // find the promise capability that's being resolved when any of
+       // the concurrent promises resolve.
+       int const index = PromiseBuiltins::kPromiseAnyRejectElementCapabilitySlot;
+From e935bf78711c7b8e3938eb3b58d6d61fa7fc2127 Mon Sep 17 00:00:00 2001
+From: Paul Semel <paulsemel@chromium.org>
+Date: Wed, 6 Dec 2023 15:52:56 +0000
+Subject: [PATCH] [Backport] CVE-2023-6703: Use after free in Blink
+
+Cherry-pick of patch originally reviewed on
+https://chromium-review.googlesource.com/c/chromium/src/+/5071252:
+[M120] ImageBitmapFactory: fix empty context dcheck
+
+Approved by:
+https://bugs.chromium.org/p/chromium/issues/detail?id=1502102#c34
+
+(cherry picked from commit c4d2f15b8f97076c8fd0f9aa5814b94db698b75c)
+
+Fixed: 1502102
+Change-Id: Ib42d2897d62136ae835561bcf56884b5624060a5
+Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/5071252
+Commit-Queue: Paul Semel <paulsemel@chromium.org>
+Reviewed-by: Jean-Philippe Gravel <jpgravel@chromium.org>
+Cr-Original-Commit-Position: refs/heads/main@{#1230617}
+Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/5088373
+Auto-Submit: Arthur Sonzogni <arthursonzogni@google.com>
+Reviewed-by: Paul Semel <paulsemel@chromium.org>
+Cr-Commit-Position: refs/branch-heads/6099@{#1416}
+Cr-Branched-From: e6ee4500f7d6549a9ac1354f8d056da49ef406be-refs/heads/main@{#1217362}
+Reviewed-on: https://codereview.qt-project.org/c/qt/qtwebengine-chromium/+/526345
+Reviewed-by: Michal Klocek <michal.klocek@qt.io>
+---
+ .../modules/canvas/imagebitmap/image_bitmap_factories.cc      | 4 +++-
+ 1 file changed, 3 insertions(+), 1 deletion(-)
+
+diff --git a/chromium/third_party/blink/renderer/modules/canvas/imagebitmap/image_bitmap_factories.cc b/chromium/third_party/blink/renderer/modules/canvas/imagebitmap/image_bitmap_factories.cc
+index 99feb736a50..3a546a64fe8 100644
+--- src/3rdparty/chromium/third_party/blink/renderer/modules/canvas/imagebitmap/image_bitmap_factories.cc.orig
++++ src/3rdparty/chromium/third_party/blink/renderer/modules/canvas/imagebitmap/image_bitmap_factories.cc
+@@ -156,7 +156,9 @@ ScriptPromise ImageBitmapFactories::CreateImageBitmapFromBlob(
+     ImageBitmapSource* bitmap_source,
+     absl::optional<gfx::Rect> crop_rect,
+     const ImageBitmapOptions* options) {
+-  DCHECK(script_state->ContextIsValid());
++  if (!script_state->ContextIsValid()) {
++    return ScriptPromise();
++  }
+ 
+   // imageOrientation: 'from-image' will be used to replace imageOrientation:
+   // 'none'. Adding a deprecation warning when 'none' is called in
+From d5f5cda70cad9ce87e306a1843cf5970bda04236 Mon Sep 17 00:00:00 2001
+From: Guido Urdaneta <guidou@chromium.org>
+Date: Fri, 1 Dec 2023 08:19:24 +0000
+Subject: [PATCH] [Backport] CVE-2023-6705: Use after free in WebRTC
+
+Cherry-pick of patch originally reviewed on
+https://chromium-review.googlesource.com/c/chromium/src/+/5077845:
+Drop frames received on the wrong task runner
+
+It can happen during transfer that a frame is posted from the
+background media thread to the task runner of the old execution
+context, which can lead to races and UAF.
+
+This CL makes underlying sources drop frames received on the
+wrong task runner to avoid the problem.
+
+Bug: 1505708
+Change-Id: I686228d88cb1c48bdf8c0b6bf85edd280a54300a
+Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/5077845
+Commit-Queue: Guido Urdaneta <guidou@chromium.org>
+Reviewed-by: Tony Herre <toprice@chromium.org>
+Cr-Commit-Position: refs/heads/main@{#1231802}
+Reviewed-on: https://codereview.qt-project.org/c/qt/qtwebengine-chromium/+/526346
+Reviewed-by: Michal Klocek <michal.klocek@qt.io>
+---
+ .../rtc_encoded_audio_underlying_source.cc             | 10 +++++++++-
+ .../rtc_encoded_video_underlying_source.cc             | 10 +++++++++-
+ 2 files changed, 18 insertions(+), 2 deletions(-)
+
+diff --git a/chromium/third_party/blink/renderer/modules/peerconnection/rtc_encoded_audio_underlying_source.cc b/chromium/third_party/blink/renderer/modules/peerconnection/rtc_encoded_audio_underlying_source.cc
+index 56926ce628fb..64348f4a273e 100644
+--- src/3rdparty/chromium/third_party/blink/renderer/modules/peerconnection/rtc_encoded_audio_underlying_source.cc.orig
++++ src/3rdparty/chromium/third_party/blink/renderer/modules/peerconnection/rtc_encoded_audio_underlying_source.cc
+@@ -60,7 +60,15 @@ void RTCEncodedAudioUnderlyingSource::Trace(Visitor* visitor) const {
+ 
+ void RTCEncodedAudioUnderlyingSource::OnFrameFromSource(
+     std::unique_ptr<webrtc::TransformableFrameInterface> webrtc_frame) {
+-  DCHECK(task_runner_->BelongsToCurrentThread());
++  // It can happen that a frame is posted to the task runner of the old
++  // execution context during a stream transfer to a new context.
++  // TODO(https://crbug.com/1506631): Make the state updates related to the
++  // transfer atomic and turn this into a DCHECK.
++  if (!task_runner_->BelongsToCurrentThread()) {
++    DVLOG(1) << "Dropped frame posted to incorrect task runner. This can "
++                "happen during transfer.";
++    return;
++  }
+   // If the source is canceled or there are too many queued frames,
+   // drop the new frame.
+   if (!disconnect_callback_ || !GetExecutionContext()) {
+diff --git a/chromium/third_party/blink/renderer/modules/peerconnection/rtc_encoded_video_underlying_source.cc b/chromium/third_party/blink/renderer/modules/peerconnection/rtc_encoded_video_underlying_source.cc
+index 54ca7d1529b1..8fb1d8460e28 100644
+--- src/3rdparty/chromium/third_party/blink/renderer/modules/peerconnection/rtc_encoded_video_underlying_source.cc.orig
++++ src/3rdparty/chromium/third_party/blink/renderer/modules/peerconnection/rtc_encoded_video_underlying_source.cc
+@@ -58,7 +58,15 @@ void RTCEncodedVideoUnderlyingSource::Trace(Visitor* visitor) const {
+ 
+ void RTCEncodedVideoUnderlyingSource::OnFrameFromSource(
+     std::unique_ptr<webrtc::TransformableVideoFrameInterface> webrtc_frame) {
+-  DCHECK(task_runner_->BelongsToCurrentThread());
++  // It can happen that a frame is posted to the task runner of the old
++  // execution context during a stream transfer to a new context.
++  // TODO(https://crbug.com/1506631): Make the state updates related to the
++  // transfer atomic and turn this into a DCHECK.
++  if (!task_runner_->BelongsToCurrentThread()) {
++    DVLOG(1) << "Dropped frame posted to incorrect task runner. This can "
++                "happen during transfer.";
++    return;
++  }
+   // If the source is canceled or there are too many queued frames,
+   // drop the new frame.
+   if (!disconnect_callback_ || !GetExecutionContext()) {
+From 9050bef97ea5f15232210e6d1096e9badc04d13e Mon Sep 17 00:00:00 2001
+From: Yi Gu <yigu@chromium.org>
+Date: Tue, 28 Nov 2023 15:51:40 +0000
+Subject: [PATCH] [Backport] CVE-2023-6706: Use after free in FedCM
+
+Manual cherry-pick of patch originally reviewed on
+https://chromium-review.googlesource.com/c/chromium/src/+/5095846:
+[M114-LTS][FedCM] Check API permission before showing accounts UI
+
+M114 merge issues:
+  content/browser/webid/federated_auth_request_impl.h/cc:
+    - The GetApiPermissionStatus() doesn't exist in 114, it uses api_permission_delegate_
+    directly.
+
+The accounts fetch could be delayed for legitimate reasons. A user may be
+able to disable FedCM API (e.g. via settings or dismissing another FedCM
+UI on the same RP origin) before the browser receives the accounts
+response.
+
+This patch checks the API permission before showing the accounts UI.
+
+Change-Id: Idbbe88912941113ec3f54d7f222845cd774dc897
+Bug: 1500921
+Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/5064052
+Commit-Queue: Yi Gu <yigu@chromium.org>
+Cr-Commit-Position: refs/heads/main@{#1229912}
+(cherry picked from commit 98676a2f66c4b4b802316eef70f4aab77e631f85)
+Reviewed-on: https://codereview.qt-project.org/c/qt/qtwebengine-chromium/+/526347
+Reviewed-by: Michal Klocek <michal.klocek@qt.io>
+---
+ .../browser/webid/federated_auth_request_impl.cc    | 13 +++++++++++++
+ 1 file changed, 13 insertions(+)
+
+diff --git a/chromium/content/browser/webid/federated_auth_request_impl.cc b/chromium/content/browser/webid/federated_auth_request_impl.cc
+index cbae35e588c..8242b6cc502 100644
+--- src/3rdparty/chromium/content/browser/webid/federated_auth_request_impl.cc.orig
++++ src/3rdparty/chromium/content/browser/webid/federated_auth_request_impl.cc
+@@ -867,6 +867,19 @@ void FederatedAuthRequestImpl::MaybeShowAccountsDialog() {
+     return;
+   }
+ 
++  // The accounts fetch could be delayed for legitimate reasons. A user may be
++  // able to disable FedCM API (e.g. via settings or dismissing another FedCM UI
++  // on the same RP origin) before the browser receives the accounts response.
++  // We should exit early without showing any UI.
++  if (api_permission_delegate_->GetApiPermissionStatus(GetEmbeddingOrigin()) !=
++      FederatedApiPermissionStatus::GRANTED) {
++    CompleteRequestWithError(
++        FederatedAuthRequestResult::kErrorDisabledInSettings,
++        TokenStatus::kDisabledInSettings,
++        /*should_delay_callback=*/true);
++    return;
++  }
++
+   // The RenderFrameHost may be alive but not visible in the following
+   // situations:
+   // Situation #1: User switched tabs
+From 4f5687248f9993cf1dacdc034a203b9e2d61c324 Mon Sep 17 00:00:00 2001
+From: Vasiliy Telezhnikov <vasilyt@chromium.org>
+Date: Fri, 1 Dec 2023 17:45:27 +0000
+Subject: [PATCH] [Backport] Security bug 1506726
+
+Manual cherry-pick of patch originally reviewed on
+https://chromium-review.googlesource.com/c/chromium/src/+/5078779:
+Check for slugs count before deserializing Slugs in DrawSlugOp
+
+Count is part of serialized data and while we never serialize values
+less then 1, it can be any value when coming over IPC, we should check
+that it's positive before substacting one.
+
+Bug: 1506726
+Change-Id: I244f50a682f2e852b22ba88f1e9cddddb0fdfcb9
+Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/5078779
+Reviewed-by: Peng Huang <penghuang@chromium.org>
+Commit-Queue: Vasiliy Telezhnikov <vasilyt@chromium.org>
+Cr-Commit-Position: refs/heads/main@{#1232013}
+Reviewed-on: https://codereview.qt-project.org/c/qt/qtwebengine-chromium/+/526348
+Reviewed-by: Michal Klocek <michal.klocek@qt.io>
+---
+ chromium/cc/paint/paint_op.cc | 10 ++++++----
+ 1 file changed, 6 insertions(+), 4 deletions(-)
+
+diff --git a/chromium/cc/paint/paint_op.cc b/chromium/cc/paint/paint_op.cc
+index 225630cb462..6f8c3df3d22 100644
+--- src/3rdparty/chromium/cc/paint/paint_op.cc.orig
++++ src/3rdparty/chromium/cc/paint/paint_op.cc
+@@ -971,10 +971,12 @@ PaintOp* DrawSlugOp::Deserialize(PaintOpReader& reader, void* output) {
+   reader.Read(&op->flags);
+   unsigned int count = 0;
+   reader.Read(&count);
+-  reader.Read(&op->slug);
+-  op->extra_slugs.resize(count - 1);
+-  for (auto& extra_slug : op->extra_slugs) {
+-    reader.Read(&extra_slug);
++  if (count > 0) {
++    reader.Read(&op->slug);
++    op->extra_slugs.resize(count - 1);
++    for (auto& extra_slug : op->extra_slugs) {
++      reader.Read(&extra_slug);
++    }
+   }
+   return op;
+ }
+From 6237d58de03877b9ff5bf5bfad1e0eeb6a4c4b4c Mon Sep 17 00:00:00 2001
+From: Kai Ninomiya <kainino@chromium.org>
+Date: Wed, 29 Nov 2023 17:44:48 +0000
+Subject: [PATCH] [Backport] Security bug 1505632
+
+Manual cherry-pick of patch originally reviewed on
+https://chromium-review.googlesource.com/c/chromium/src/+/5069480:
+Fix reinit order in ContextProviderCommandBuffer::BindToCurrentSequence
+
+See comments for explanation.
+
+Bug: 1505632
+Change-Id: I0f43821a9708af91303048332e9fae5e100deee5
+Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/5069480
+Reviewed-by: Saifuddin Hitawala <hitawala@chromium.org>
+Commit-Queue: Kai Ninomiya <kainino@chromium.org>
+Reviewed-by: Brendon Tiszka <tiszka@chromium.org>
+Cr-Commit-Position: refs/heads/main@{#1230735}
+Reviewed-on: https://codereview.qt-project.org/c/qt/qtwebengine-chromium/+/526349
+Reviewed-by: Michal Klocek <michal.klocek@qt.io>
+---
+ .../gpu/context_provider_command_buffer.cc    | 24 +++++++++-----
+ .../cpp/gpu/context_provider_command_buffer.h | 31 ++++++++++++++++---
+ 2 files changed, 44 insertions(+), 11 deletions(-)
+
+diff --git a/chromium/services/viz/public/cpp/gpu/context_provider_command_buffer.cc b/chromium/services/viz/public/cpp/gpu/context_provider_command_buffer.cc
+index 6637a9f89dc..d29c926a49e 100644
+--- src/3rdparty/chromium/services/viz/public/cpp/gpu/context_provider_command_buffer.cc.orig
++++ src/3rdparty/chromium/services/viz/public/cpp/gpu/context_provider_command_buffer.cc
+@@ -169,13 +169,13 @@ gpu::ContextResult ContextProviderCommandBuffer::BindToCurrentSequence() {
+     }
+ 
+     // The transfer buffer is used to serialize Dawn commands
+-    transfer_buffer_ =
++    auto transfer_buffer =
+         std::make_unique<gpu::TransferBuffer>(webgpu_helper.get());
+ 
+     // The WebGPUImplementation exposes the WebGPUInterface, as well as the
+     // gpu::ContextSupport interface.
+     auto webgpu_impl = std::make_unique<gpu::webgpu::WebGPUImplementation>(
+-        webgpu_helper.get(), transfer_buffer_.get(), command_buffer_.get());
++        webgpu_helper.get(), transfer_buffer.get(), command_buffer_.get());
+     bind_result_ = webgpu_impl->Initialize(memory_limits_);
+     if (bind_result_ != gpu::ContextResult::kSuccess) {
+       DLOG(ERROR) << "Failed to initialize WebGPUImplementation.";
+@@ -187,8 +187,11 @@ gpu::ContextResult ContextProviderCommandBuffer::BindToCurrentSequence() {
+     std::string unique_context_name =
+         base::StringPrintf("%s-%p", type_name.c_str(), webgpu_impl.get());
+ 
++    // IMPORTANT: These hold raw_ptrs to each other, so must be set together.
++    // See note in the header (and keep it up to date if things change).
+     impl_ = webgpu_impl.get();
+     webgpu_interface_ = std::move(webgpu_impl);
++    transfer_buffer_ = std::move(transfer_buffer);
+     helper_ = std::move(webgpu_helper);
+   } else if (attributes_.enable_raster_interface &&
+              !attributes_.enable_gles2_interface &&
+@@ -206,14 +209,14 @@ gpu::ContextResult ContextProviderCommandBuffer::BindToCurrentSequence() {
+     }
+     // The transfer buffer is used to copy resources between the client
+     // process and the GPU process.
+-    transfer_buffer_ =
++    auto transfer_buffer =
+         std::make_unique<gpu::TransferBuffer>(raster_helper.get());
+ 
+     // The RasterImplementation exposes the RasterInterface, as well as the
+     // gpu::ContextSupport interface.
+     DCHECK(channel_);
+     auto raster_impl = std::make_unique<gpu::raster::RasterImplementation>(
+-        raster_helper.get(), transfer_buffer_.get(),
++        raster_helper.get(), transfer_buffer.get(),
+         attributes_.bind_generates_resource,
+         attributes_.lose_context_when_out_of_memory, command_buffer_.get(),
+         channel_->image_decode_accelerator_proxy());
+@@ -230,8 +233,11 @@ gpu::ContextResult ContextProviderCommandBuffer::BindToCurrentSequence() {
+     raster_impl->TraceBeginCHROMIUM("gpu_toplevel",
+                                     unique_context_name.c_str());
+ 
++    // IMPORTANT: These hold raw_ptrs to each other, so must be set together.
++    // See note in the header (and keep it up to date if things change).
+     impl_ = raster_impl.get();
+     raster_interface_ = std::move(raster_impl);
++    transfer_buffer_ = std::move(transfer_buffer);
+     helper_ = std::move(raster_helper);
+   } else {
+     // The GLES2 helper writes the command buffer protocol.
+@@ -246,7 +252,7 @@ gpu::ContextResult ContextProviderCommandBuffer::BindToCurrentSequence() {
+ 
+     // The transfer buffer is used to copy resources between the client
+     // process and the GPU process.
+-    transfer_buffer_ =
++    auto transfer_buffer =
+         std::make_unique<gpu::TransferBuffer>(gles2_helper.get());
+ 
+     // The GLES2Implementation exposes the OpenGLES2 API, as well as the
+@@ -259,13 +265,13 @@ gpu::ContextResult ContextProviderCommandBuffer::BindToCurrentSequence() {
+       // we only use it if grcontext_support was requested.
+       gles2_impl = std::make_unique<
+           skia_bindings::GLES2ImplementationWithGrContextSupport>(
+-          gles2_helper.get(), /*share_group=*/nullptr, transfer_buffer_.get(),
++          gles2_helper.get(), /*share_group=*/nullptr, transfer_buffer.get(),
+           attributes_.bind_generates_resource,
+           attributes_.lose_context_when_out_of_memory,
+           support_client_side_arrays, command_buffer_.get());
+     } else {
+       gles2_impl = std::make_unique<gpu::gles2::GLES2Implementation>(
+-          gles2_helper.get(), /*share_group=*/nullptr, transfer_buffer_.get(),
++          gles2_helper.get(), /*share_group=*/nullptr, transfer_buffer.get(),
+           attributes_.bind_generates_resource,
+           attributes_.lose_context_when_out_of_memory,
+           support_client_side_arrays, command_buffer_.get());
+@@ -276,8 +282,11 @@ gpu::ContextResult ContextProviderCommandBuffer::BindToCurrentSequence() {
+       return bind_result_;
+     }
+ 
++    // IMPORTANT: These hold raw_ptrs to each other, so must be set together.
++    // See note in the header (and keep it up to date if things change).
+     impl_ = gles2_impl.get();
+     gles2_impl_ = std::move(gles2_impl);
++    transfer_buffer_ = std::move(transfer_buffer);
+     helper_ = std::move(gles2_helper);
+   }
+ 
+@@ -311,6 +320,7 @@ gpu::ContextResult ContextProviderCommandBuffer::BindToCurrentSequence() {
+             switches::kEnableGpuClientTracing)) {
+       // This wraps the real GLES2Implementation and we should always use this
+       // instead when it's present.
++      // IMPORTANT: This holds a raw_ptr to gles2_impl_.
+       trace_impl_ = std::make_unique<gpu::gles2::GLES2TraceImplementation>(
+           gles2_impl_.get());
+       gl = trace_impl_.get();
+diff --git a/chromium/services/viz/public/cpp/gpu/context_provider_command_buffer.h b/chromium/services/viz/public/cpp/gpu/context_provider_command_buffer.h
+index e434c1b4fc4..b25506f3b32 100644
+--- src/3rdparty/chromium/services/viz/public/cpp/gpu/context_provider_command_buffer.h.orig
++++ src/3rdparty/chromium/services/viz/public/cpp/gpu/context_provider_command_buffer.h
+@@ -162,19 +162,42 @@ class ContextProviderCommandBuffer
+   // associated shared images are destroyed.
+   std::unique_ptr<gpu::ClientSharedImageInterface> shared_image_interface_;
+ 
+-  base::Lock context_lock_;  // Referenced by command_buffer_.
++  //////////////////////////////////////////////////////////////////////////////
++  // IMPORTANT NOTE: All of the objects in this block are part of a complex   //
++  // graph of raw pointers (holder or pointee of various raw_ptrs). They are  //
++  // defined in topological order: only later items point to earlier items.   //
++  // - When writing any member, always ensure its pointers to earlier members
++  //   are guaranteed to stay alive.
++  // - When clearing OR overwriting any member, always ensure objects that
++  //   point to it have already been cleared.
++  //     - The topological order of definitions guarantees that the
++  //       destructors will be called in the correct order (bottom to top).
++  //     - When overwriting multiple members, similarly do so in reverse order.
++  //
++  // Please note these comments are likely not to stay perfectly up-to-date.
++
++  base::Lock context_lock_;
++  // Points to the context_lock_ field of `this`.
+   std::unique_ptr<gpu::CommandBufferProxyImpl> command_buffer_;
++
++  // Points to command_buffer_.
+   std::unique_ptr<gpu::CommandBufferHelper> helper_;
++  // Points to helper_.
+   std::unique_ptr<gpu::TransferBuffer> transfer_buffer_;
+ 
++  // Points to transfer_buffer_, helper_, and command_buffer_.
+   std::unique_ptr<gpu::gles2::GLES2Implementation> gles2_impl_;
++  // Points to gles2_impl_.
+   std::unique_ptr<gpu::gles2::GLES2TraceImplementation> trace_impl_;
++  // Points to transfer_buffer_, helper_, and command_buffer_.
+   std::unique_ptr<gpu::raster::RasterInterface> raster_interface_;
++  // Points to transfer_buffer_, helper_, and command_buffer_.
+   std::unique_ptr<gpu::webgpu::WebGPUInterface> webgpu_interface_;
++  // This is an alias for gles2_impl_, raster_interface_, or webgpu_interface_.
++  raw_ptr<gpu::ImplementationBase> impl_ = nullptr;
+ 
+-  // Owned by one of gles2_impl_, raster_interface_, or webgpu_interface_. It
+-  // must be declared last and cleared first.
+-  raw_ptr<gpu::ImplementationBase> impl_;
++  // END IMPORTANT NOTE                                                       //
++  //////////////////////////////////////////////////////////////////////////////
+ 
+   std::unique_ptr<skia_bindings::GrContextForGLES2Interface> gr_context_;
+ #if BUILDFLAG(SKIA_USE_DAWN)
+From 536f81c3de46e6e1ac2b23ed610f9526bce14fe4 Mon Sep 17 00:00:00 2001
+From: pthier <pthier@chromium.org>
+Date: Tue, 24 Oct 2023 13:28:22 +0200
+Subject: [PATCH] [Backport] Security bug 1488199 (1/3)
+
+Manual cherry-pick of patch originally reviewed on
+https://chromium-review.googlesource.com/c/v8/v8/+/4971832:
+[regexp] Fix stack check in native code when interrupt was requested
+
+When an interrupt was requested at the time we hit the stack check, the
+check to ensure we have enough space for local variables was skipped.
+
+Bug: chromium:1488199
+Change-Id: I95d82fe737420d2ef43c1ace35560cfd5860829b
+Reviewed-on: https://chromium-review.googlesource.com/c/v8/v8/+/4971832
+Commit-Queue: Patrick Thier <pthier@chromium.org>
+Reviewed-by: Jakob Linke <jgruber@chromium.org>
+Cr-Commit-Position: refs/heads/main@{#90560}
+Reviewed-on: https://codereview.qt-project.org/c/qt/qtwebengine-chromium/+/523712
+Reviewed-by: Michal Klocek <michal.klocek@qt.io>
+---
+ .../regexp/arm/regexp-macro-assembler-arm.cc  | 23 +++++++-----
+ .../regexp/arm/regexp-macro-assembler-arm.h   |  5 +--
+ .../arm64/regexp-macro-assembler-arm64.cc     | 21 ++++++-----
+ .../arm64/regexp-macro-assembler-arm64.h      |  6 ++--
+ .../ia32/regexp-macro-assembler-ia32.cc       | 19 ++++++----
+ .../regexp/ia32/regexp-macro-assembler-ia32.h |  5 +--
+ .../v8/src/regexp/regexp-macro-assembler.cc   |  5 +--
+ .../v8/src/regexp/regexp-macro-assembler.h    |  2 +-
+ .../regexp/x64/regexp-macro-assembler-x64.cc  | 36 +++++++++++--------
+ .../regexp/x64/regexp-macro-assembler-x64.h   |  4 +--
+ 10 files changed, 78 insertions(+), 48 deletions(-)
+
+diff --git a/chromium/v8/src/regexp/arm/regexp-macro-assembler-arm.cc b/chromium/v8/src/regexp/arm/regexp-macro-assembler-arm.cc
+index 8aa815db2ac..6b167fe3dc2 100644
+--- src/3rdparty/chromium/v8/src/regexp/arm/regexp-macro-assembler-arm.cc
++++ src/3rdparty/chromium/v8/src/regexp/arm/regexp-macro-assembler-arm.cc
+@@ -754,11 +754,13 @@ Handle<HeapObject> RegExpMacroAssemblerARM::GetCode(Handle<String> source) {
+     __ mov(r0, Operand(stack_limit));
+     __ ldr(r0, MemOperand(r0));
+     __ sub(r0, sp, r0, SetCC);
++    Operand extra_space_for_variables(num_registers_ * kSystemPointerSize);
++
+     // Handle it if the stack pointer is already below the stack limit.
+     __ b(ls, &stack_limit_hit);
+     // Check if there is room for the variable number of registers above
+     // the stack limit.
+-    __ cmp(r0, Operand(num_registers_ * kSystemPointerSize));
++    __ cmp(r0, extra_space_for_variables);
+     __ b(hs, &stack_ok);
+     // Exit with OutOfMemory exception. There is not enough space on the stack
+     // for our working registers.
+@@ -766,7 +768,7 @@ Handle<HeapObject> RegExpMacroAssemblerARM::GetCode(Handle<String> source) {
+     __ jmp(&return_r0);
+ 
+     __ bind(&stack_limit_hit);
+-    CallCheckStackGuardState();
++    CallCheckStackGuardState(extra_space_for_variables);
+     __ cmp(r0, Operand::Zero());
+     // If returned value is non-zero, we exit with the returned value as result.
+     __ b(ne, &return_r0);
+@@ -1158,16 +1160,18 @@ void RegExpMacroAssemblerARM::ClearRegisters(int reg_from, int reg_to) {
+ 
+ // Private methods:
+ 
+-void RegExpMacroAssemblerARM::CallCheckStackGuardState() {
++void RegExpMacroAssemblerARM::CallCheckStackGuardState(Operand extra_space) {
+   DCHECK(!isolate()->IsGeneratingEmbeddedBuiltins());
+   DCHECK(!masm_->options().isolate_independent_code);
+ 
+-  __ PrepareCallCFunction(3);
++  __ PrepareCallCFunction(4);
+ 
++  // Extra space for variables to consider in stack check.
++  __ mov(arg_reg_4, extra_space);
+   // RegExp code frame pointer.
+-  __ mov(r2, frame_pointer());
++  __ mov(arg_reg_3, frame_pointer());
+   // InstructionStream of self.
+-  __ mov(r1, Operand(masm_->CodeObject()));
++  __ mov(arg_reg_2, Operand(masm_->CodeObject()));
+ 
+   // We need to make room for the return address on the stack.
+   int stack_alignment = base::OS::ActivationFrameAlignment();
+@@ -1195,7 +1199,6 @@ void RegExpMacroAssemblerARM::CallCheckStackGuardState() {
+   __ mov(code_pointer(), Operand(masm_->CodeObject()));
+ }
+ 
+-
+ // Helper function for reading a value out of a stack frame.
+ template <typename T>
+ static T& frame_entry(Address re_frame, int frame_offset) {
+@@ -1210,7 +1213,8 @@ static T* frame_entry_address(Address re_frame, int frame_offset) {
+ 
+ int RegExpMacroAssemblerARM::CheckStackGuardState(Address* return_address,
+                                                   Address raw_code,
+-                                                  Address re_frame) {
++                                                  Address re_frame,
++                                                  uintptr_t extra_space) {
+   InstructionStream re_code = InstructionStream::cast(Object(raw_code));
+   return NativeRegExpMacroAssembler::CheckStackGuardState(
+       frame_entry<Isolate*>(re_frame, kIsolateOffset),
+@@ -1220,7 +1224,8 @@ int RegExpMacroAssemblerARM::CheckStackGuardState(Address* return_address,
+       return_address, re_code,
+       frame_entry_address<Address>(re_frame, kInputStringOffset),
+       frame_entry_address<const byte*>(re_frame, kInputStartOffset),
+-      frame_entry_address<const byte*>(re_frame, kInputEndOffset));
++      frame_entry_address<const byte*>(re_frame, kInputEndOffset),
++      extra_space);
+ }
+ 
+ 
+diff --git a/chromium/v8/src/regexp/arm/regexp-macro-assembler-arm.h b/chromium/v8/src/regexp/arm/regexp-macro-assembler-arm.h
+index 44be0d920b6..e8d9f6d76de 100644
+--- src/3rdparty/chromium/v8/src/regexp/arm/regexp-macro-assembler-arm.h
++++ src/3rdparty/chromium/v8/src/regexp/arm/regexp-macro-assembler-arm.h
+@@ -88,7 +88,7 @@ class V8_EXPORT_PRIVATE RegExpMacroAssemblerARM
+   // returning.
+   // {raw_code} is an Address because this is called via ExternalReference.
+   static int CheckStackGuardState(Address* return_address, Address raw_code,
+-                                  Address re_frame);
++                                  Address re_frame, uintptr_t extra_space);
+ 
+  private:
+   // Offsets from frame_pointer() of function parameters and stored registers.
+@@ -152,7 +152,8 @@ class V8_EXPORT_PRIVATE RegExpMacroAssemblerARM
+   // Check whether we are exceeding the stack limit on the backtrack stack.
+   void CheckStackLimit();
+ 
+-  void CallCheckStackGuardState();
++  void CallCheckStackGuardState(
++      Operand extra_space_for_variables = Operand::Zero());
+   void CallIsCharacterInRangeArray(const ZoneList<CharacterRange>* ranges);
+ 
+   // The ebp-relative location of a regexp register.
+diff --git a/chromium/v8/src/regexp/arm64/regexp-macro-assembler-arm64.cc b/chromium/v8/src/regexp/arm64/regexp-macro-assembler-arm64.cc
+index d453922f6bf..e8d48236621 100644
+--- src/3rdparty/chromium/v8/src/regexp/arm64/regexp-macro-assembler-arm64.cc
++++ src/3rdparty/chromium/v8/src/regexp/arm64/regexp-macro-assembler-arm64.cc
+@@ -866,13 +866,14 @@ Handle<HeapObject> RegExpMacroAssemblerARM64::GetCode(Handle<String> source) {
+     __ Mov(x10, stack_limit);
+     __ Ldr(x10, MemOperand(x10));
+     __ Subs(x10, sp, x10);
++    Operand extra_space_for_variables(num_wreg_to_allocate * kWRegSize);
+ 
+     // Handle it if the stack pointer is already below the stack limit.
+     __ B(ls, &stack_limit_hit);
+ 
+     // Check if there is room for the variable number of registers above
+     // the stack limit.
+-    __ Cmp(x10, num_wreg_to_allocate * kWRegSize);
++    __ Cmp(x10, extra_space_for_variables);
+     __ B(hs, &stack_ok);
+ 
+     // Exit with OutOfMemory exception. There is not enough space on the stack
+@@ -881,7 +882,7 @@ Handle<HeapObject> RegExpMacroAssemblerARM64::GetCode(Handle<String> source) {
+     __ B(&return_w0);
+ 
+     __ Bind(&stack_limit_hit);
+-    CallCheckStackGuardState(x10);
++    CallCheckStackGuardState(x10, extra_space_for_variables);
+     // If returned value is non-zero, we exit with the returned value as result.
+     __ Cbnz(w0, &return_w0);
+ 
+@@ -1433,7 +1434,8 @@ static T* frame_entry_address(Address re_frame, int frame_offset) {
+ 
+ int RegExpMacroAssemblerARM64::CheckStackGuardState(
+     Address* return_address, Address raw_code, Address re_frame,
+-    int start_index, const byte** input_start, const byte** input_end) {
++    int start_index, const byte** input_start, const byte** input_end,
++    uintptr_t extra_space) {
+   InstructionStream re_code = InstructionStream::cast(Object(raw_code));
+   return NativeRegExpMacroAssembler::CheckStackGuardState(
+       frame_entry<Isolate*>(re_frame, kIsolateOffset), start_index,
+@@ -1441,7 +1443,7 @@ int RegExpMacroAssemblerARM64::CheckStackGuardState(
+           frame_entry<int>(re_frame, kDirectCallOffset)),
+       return_address, re_code,
+       frame_entry_address<Address>(re_frame, kInputStringOffset), input_start,
+-      input_end);
++      input_end, extra_space);
+ }
+ 
+ 
+@@ -1460,21 +1462,24 @@ void RegExpMacroAssemblerARM64::CheckPosition(int cp_offset,
+ 
+ // Private methods:
+ 
+-void RegExpMacroAssemblerARM64::CallCheckStackGuardState(Register scratch) {
++void RegExpMacroAssemblerARM64::CallCheckStackGuardState(Register scratch,
++                                                         Operand extra_space) {
+   DCHECK(!isolate()->IsGeneratingEmbeddedBuiltins());
+   DCHECK(!masm_->options().isolate_independent_code);
+ 
+   // Allocate space on the stack to store the return address. The
+   // CheckStackGuardState C++ function will override it if the code
+-  // moved. Allocate extra space for 2 arguments passed by pointers.
+-  // AAPCS64 requires the stack to be 16 byte aligned.
++  // moved. Allocate extra space for 3 arguments (2 for input start/end and 1
++  // for gap). AAPCS64 requires the stack to be 16 byte aligned.
+   int alignment = masm_->ActivationFrameAlignment();
+   DCHECK_EQ(alignment % 16, 0);
+   int align_mask = (alignment / kXRegSize) - 1;
+-  int xreg_to_claim = (3 + align_mask) & ~align_mask;
++  int xreg_to_claim = (4 + align_mask) & ~align_mask;
+ 
+   __ Claim(xreg_to_claim);
+ 
++  __ Mov(x0, extra_space);
++  __ Poke(x0, 3 * kSystemPointerSize);
+   // CheckStackGuardState needs the end and start addresses of the input string.
+   __ Poke(input_end(), 2 * kSystemPointerSize);
+   __ Add(x5, sp, 2 * kSystemPointerSize);
+diff --git a/chromium/v8/src/regexp/arm64/regexp-macro-assembler-arm64.h b/chromium/v8/src/regexp/arm64/regexp-macro-assembler-arm64.h
+index a5164472b71..05b4eb5bd7b 100644
+--- src/3rdparty/chromium/v8/src/regexp/arm64/regexp-macro-assembler-arm64.h
++++ src/3rdparty/chromium/v8/src/regexp/arm64/regexp-macro-assembler-arm64.h
+@@ -95,7 +95,8 @@ class V8_EXPORT_PRIVATE RegExpMacroAssemblerARM64
+   static int CheckStackGuardState(Address* return_address, Address raw_code,
+                                   Address re_frame, int start_offset,
+                                   const byte** input_start,
+-                                  const byte** input_end);
++                                  const byte** input_end,
++                                  uintptr_t extra_space);
+ 
+  private:
+   static constexpr int kFramePointerOffset = 0;
+@@ -174,7 +175,8 @@ class V8_EXPORT_PRIVATE RegExpMacroAssemblerARM64
+   // Check whether we are exceeding the stack limit on the backtrack stack.
+   void CheckStackLimit();
+ 
+-  void CallCheckStackGuardState(Register scratch);
++  void CallCheckStackGuardState(Register scratch,
++                                Operand extra_space = Operand(0));
+   void CallIsCharacterInRangeArray(const ZoneList<CharacterRange>* ranges);
+ 
+   // Location of a 32 bit position register.
+diff --git a/chromium/v8/src/regexp/ia32/regexp-macro-assembler-ia32.cc b/chromium/v8/src/regexp/ia32/regexp-macro-assembler-ia32.cc
+index 6370e7e57da..8dff4abcb25 100644
+--- src/3rdparty/chromium/v8/src/regexp/ia32/regexp-macro-assembler-ia32.cc
++++ src/3rdparty/chromium/v8/src/regexp/ia32/regexp-macro-assembler-ia32.cc
+@@ -801,11 +801,13 @@ Handle<HeapObject> RegExpMacroAssemblerIA32::GetCode(Handle<String> source) {
+         ExternalReference::address_of_jslimit(isolate());
+     __ mov(eax, esp);
+     __ sub(eax, StaticVariable(stack_limit));
++    Immediate extra_space_for_variables(num_registers_ * kSystemPointerSize);
++
+     // Handle it if the stack pointer is already below the stack limit.
+     __ j(below_equal, &stack_limit_hit);
+     // Check if there is room for the variable number of registers above
+     // the stack limit.
+-    __ cmp(eax, num_registers_ * kSystemPointerSize);
++    __ cmp(eax, extra_space_for_variables);
+     __ j(above_equal, &stack_ok);
+     // Exit with OutOfMemory exception. There is not enough space on the stack
+     // for our working registers.
+@@ -814,7 +816,7 @@ Handle<HeapObject> RegExpMacroAssemblerIA32::GetCode(Handle<String> source) {
+ 
+     __ bind(&stack_limit_hit);
+     __ push(backtrack_stackpointer());
+-    CallCheckStackGuardState(ebx);
++    CallCheckStackGuardState(ebx, extra_space_for_variables);
+     __ pop(backtrack_stackpointer());
+     __ or_(eax, eax);
+     // If returned value is non-zero, we exit with the returned value as result.
+@@ -1214,9 +1216,12 @@ void RegExpMacroAssemblerIA32::ClearRegisters(int reg_from, int reg_to) {
+ 
+ // Private methods:
+ 
+-void RegExpMacroAssemblerIA32::CallCheckStackGuardState(Register scratch) {
+-  static const int num_arguments = 3;
++void RegExpMacroAssemblerIA32::CallCheckStackGuardState(Register scratch,
++                                                        Immediate extra_space) {
++  static const int num_arguments = 4;
+   __ PrepareCallCFunction(num_arguments, scratch);
++  // Extra space for variables.
++  __ mov(Operand(esp, 3 * kSystemPointerSize), extra_space);
+   // RegExp code frame pointer.
+   __ mov(Operand(esp, 2 * kSystemPointerSize), ebp);
+   // InstructionStream of self.
+@@ -1247,7 +1252,8 @@ static T* frame_entry_address(Address re_frame, int frame_offset) {
+ 
+ int RegExpMacroAssemblerIA32::CheckStackGuardState(Address* return_address,
+                                                    Address raw_code,
+-                                                   Address re_frame) {
++                                                   Address re_frame,
++                                                   uintptr_t extra_space) {
+   InstructionStream re_code = InstructionStream::cast(Object(raw_code));
+   return NativeRegExpMacroAssembler::CheckStackGuardState(
+       frame_entry<Isolate*>(re_frame, kIsolateOffset),
+@@ -1257,7 +1263,8 @@ int RegExpMacroAssemblerIA32::CheckStackGuardState(Address* return_address,
+       return_address, re_code,
+       frame_entry_address<Address>(re_frame, kInputStringOffset),
+       frame_entry_address<const byte*>(re_frame, kInputStartOffset),
+-      frame_entry_address<const byte*>(re_frame, kInputEndOffset));
++      frame_entry_address<const byte*>(re_frame, kInputEndOffset),
++      extra_space);
+ }
+ 
+ 
+diff --git a/chromium/v8/src/regexp/ia32/regexp-macro-assembler-ia32.h b/chromium/v8/src/regexp/ia32/regexp-macro-assembler-ia32.h
+index 649c61d880e..a33b687c8c3 100644
+--- src/3rdparty/chromium/v8/src/regexp/ia32/regexp-macro-assembler-ia32.h
++++ src/3rdparty/chromium/v8/src/regexp/ia32/regexp-macro-assembler-ia32.h
+@@ -89,7 +89,7 @@ class V8_EXPORT_PRIVATE RegExpMacroAssemblerIA32
+   // returning.
+   // {raw_code} is an Address because this is called via ExternalReference.
+   static int CheckStackGuardState(Address* return_address, Address raw_code,
+-                                  Address re_frame);
++                                  Address re_frame, uintptr_t extra_space);
+ 
+  private:
+   Operand StaticVariable(const ExternalReference& ext);
+@@ -159,7 +159,8 @@ class V8_EXPORT_PRIVATE RegExpMacroAssemblerIA32
+   // Check whether we are exceeding the stack limit on the backtrack stack.
+   void CheckStackLimit();
+ 
+-  void CallCheckStackGuardState(Register scratch);
++  void CallCheckStackGuardState(Register scratch,
++                                Immediate extra_space = Immediate(0));
+   void CallIsCharacterInRangeArray(const ZoneList<CharacterRange>* ranges);
+ 
+   // The ebp-relative location of a regexp register.
+diff --git a/chromium/v8/src/regexp/regexp-macro-assembler.cc b/chromium/v8/src/regexp/regexp-macro-assembler.cc
+index 2fcb0a425ec..19c4cc9c8dd 100644
+--- src/3rdparty/chromium/v8/src/regexp/regexp-macro-assembler.cc
++++ src/3rdparty/chromium/v8/src/regexp/regexp-macro-assembler.cc
+@@ -284,14 +284,15 @@ bool NativeRegExpMacroAssembler::CanReadUnaligned() const {
+ int NativeRegExpMacroAssembler::CheckStackGuardState(
+     Isolate* isolate, int start_index, RegExp::CallOrigin call_origin,
+     Address* return_address, InstructionStream re_code, Address* subject,
+-    const byte** input_start, const byte** input_end) {
++    const byte** input_start, const byte** input_end,
++    uintptr_t gap) {
+   DisallowGarbageCollection no_gc;
+   Address old_pc = PointerAuthentication::AuthenticatePC(return_address, 0);
+   DCHECK_LE(re_code.instruction_start(), old_pc);
+   DCHECK_LE(old_pc, re_code.instruction_end());
+ 
+   StackLimitCheck check(isolate);
+-  bool js_has_overflowed = check.JsHasOverflowed();
++  bool js_has_overflowed = check.JsHasOverflowed(gap);
+ 
+   if (call_origin == RegExp::CallOrigin::kFromJs) {
+     // Direct calls from JavaScript can be interrupted in two ways:
+diff --git a/chromium/v8/src/regexp/regexp-macro-assembler.h b/chromium/v8/src/regexp/regexp-macro-assembler.h
+index 2ba9e2d28d0..4d16f8a98ad 100644
+--- src/3rdparty/chromium/v8/src/regexp/regexp-macro-assembler.h
++++ src/3rdparty/chromium/v8/src/regexp/regexp-macro-assembler.h
+@@ -334,7 +334,7 @@ class NativeRegExpMacroAssembler: public RegExpMacroAssembler {
+                                   Address* return_address,
+                                   InstructionStream re_code, Address* subject,
+                                   const byte** input_start,
+-                                  const byte** input_end);
++                                  const byte** input_end, uintptr_t gap);
+ 
+   static Address word_character_map_address() {
+     return reinterpret_cast<Address>(&word_character_map[0]);
+diff --git a/chromium/v8/src/regexp/x64/regexp-macro-assembler-x64.cc b/chromium/v8/src/regexp/x64/regexp-macro-assembler-x64.cc
+index b6b2f5f5606..83f5cbf2d29 100644
+--- src/3rdparty/chromium/v8/src/regexp/x64/regexp-macro-assembler-x64.cc
++++ src/3rdparty/chromium/v8/src/regexp/x64/regexp-macro-assembler-x64.cc
+@@ -842,11 +842,13 @@ Handle<HeapObject> RegExpMacroAssemblerX64::GetCode(Handle<String> source) {
+     __ movq(r9, rsp);
+     __ Move(kScratchRegister, stack_limit);
+     __ subq(r9, Operand(kScratchRegister, 0));
++    Immediate extra_space_for_variables(num_registers_ * kSystemPointerSize);
++
+     // Handle it if the stack pointer is already below the stack limit.
+     __ j(below_equal, &stack_limit_hit);
+     // Check if there is room for the variable number of registers above
+     // the stack limit.
+-    __ cmpq(r9, Immediate(num_registers_ * kSystemPointerSize));
++    __ cmpq(r9, extra_space_for_variables);
+     __ j(above_equal, &stack_ok);
+     // Exit with OutOfMemory exception. There is not enough space on the stack
+     // for our working registers.
+@@ -856,7 +858,8 @@ Handle<HeapObject> RegExpMacroAssemblerX64::GetCode(Handle<String> source) {
+     __ bind(&stack_limit_hit);
+     __ Move(code_object_pointer(), masm_.CodeObject());
+     __ pushq(backtrack_stackpointer());
+-    CallCheckStackGuardState();  // Preserves no registers beside rbp and rsp.
++    // CallCheckStackGuardState preserves no registers beside rbp and rsp.
++    CallCheckStackGuardState(extra_space_for_variables);
+     __ popq(backtrack_stackpointer());
+     __ testq(rax, rax);
+     // If returned value is non-zero, we exit with the returned value as result.
+@@ -1267,35 +1270,38 @@ void RegExpMacroAssemblerX64::ClearRegisters(int reg_from, int reg_to) {
+ 
+ // Private methods:
+ 
+-void RegExpMacroAssemblerX64::CallCheckStackGuardState() {
++void RegExpMacroAssemblerX64::CallCheckStackGuardState(Immediate extra_space) {
+   // This function call preserves no register values. Caller should
+   // store anything volatile in a C call or overwritten by this function.
+-  static const int num_arguments = 3;
++  static const int num_arguments = 4;
+   __ PrepareCallCFunction(num_arguments);
+ #ifdef V8_TARGET_OS_WIN
++  // Fourth argument: Extra space for variables.
++  __ movq(arg_reg_4, extra_space);
+   // Second argument: InstructionStream of self. (Do this before overwriting
+-  // r8).
+-  __ movq(rdx, code_object_pointer());
++  // r8 (arg_reg_3)).
++  __ movq(arg_reg_2, code_object_pointer());
+   // Third argument: RegExp code frame pointer.
+-  __ movq(r8, rbp);
++  __ movq(arg_reg_3, rbp);
+   // First argument: Next address on the stack (will be address of
+   // return address).
+-  __ leaq(rcx, Operand(rsp, -kSystemPointerSize));
++  __ leaq(arg_reg_1, Operand(rsp, -kSystemPointerSize));
+ #else
++  // Fourth argument: Extra space for variables.
++  __ movq(arg_reg_4, extra_space);
+   // Third argument: RegExp code frame pointer.
+-  __ movq(rdx, rbp);
++  __ movq(arg_reg_3, rbp);
+   // Second argument: InstructionStream of self.
+-  __ movq(rsi, code_object_pointer());
++  __ movq(arg_reg_2, code_object_pointer());
+   // First argument: Next address on the stack (will be address of
+   // return address).
+-  __ leaq(rdi, Operand(rsp, -kSystemPointerSize));
++  __ leaq(arg_reg_1, Operand(rsp, -kSystemPointerSize));
+ #endif
+   ExternalReference stack_check =
+       ExternalReference::re_check_stack_guard_state();
+   CallCFunctionFromIrregexpCode(stack_check, num_arguments);
+ }
+ 
+-
+ // Helper function for reading a value out of a stack frame.
*** 1670 LINES SKIPPED ***



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?202401300041.40U0fgxA026405>