CVE-2026-9885
Overview
Changed Functions
| Function | Change | Notes |
|---|---|---|
forcontent/app_shim_remote_cocoa/web_menu_runner_mac.mm |
modified |
Files Changed
content/app_shim_remote_cocoa/web_menu_runner_mac.mmthird_party/blink/renderer/core/style/computed_style_constants.h
Patch
From 44241f776394c53f5f373e8a71930cace1619cf2 Mon Sep 17 00:00:00 2001
From: Avi Drissman <avi@chromium.org>
Date: Mon, 04 May 2026 08:54:35 -0700
Subject: [PATCH] Cap font sizes for popup menus on Mac
Blink caps font sizes on the renderer side, but browser-side code should
not rely on that. Cap the font sizes on the browser side for popup
menus.
Fixed: 508452241
Link: https://chromium-review.googlesource.com/id/Ibc50186dff0979ae55b6f39e594460686a6a6964
Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/7806727
Commit-Queue: Avi Drissman <avi@chromium.org>
Reviewed-by: Mark Mentovai <mark@chromium.org>
Reviewed-by: Daniil Sakhapov <sakhapov@chromium.org>
Cr-Commit-Position: refs/heads/main@{#1624714}
---
diff --git a/content/app_shim_remote_cocoa/web_menu_runner_mac.mm b/content/app_shim_remote_cocoa/web_menu_runner_mac.mm
index 0a7029b..053c47ff 100644
--- a/content/app_shim_remote_cocoa/web_menu_runner_mac.mm
+++ b/content/app_shim_remote_cocoa/web_menu_runner_mac.mm
@@ -50,7 +50,12 @@
if ((self = [super init])) {
_menu = [[NSMenu alloc] initWithTitle:@""];
_menu.autoenablesItems = NO;
- _fontSize = fontSize;
+ // LINT.IfChange(fontSize)
+ // Blink caps font sizes to 10,000 but browser process code can't rely on
+ // the renderer to behave correctly.
+ // https://crbug.com/508452241
+ _fontSize = std::min(fontSize, 10'000.0);
+ // LINT.ThenChange(//third_party/blink/renderer/core/style/computed_style_constants.h:kMaximumAllowedFontSize)
_rightAligned = rightAligned;
for (const auto& item : items) {
[self addItem:item];
diff --git a/third_party/blink/renderer/core/style/computed_style_constants.h b/third_party/blink/renderer/core/style/computed_style_constants.h
index 4ad7dc5..0884520 100644
--- a/third_party/blink/renderer/core/style/computed_style_constants.h
+++ b/third_party/blink/renderer/core/style/computed_style_constants.h
@@ -475,9 +475,11 @@
kStretch
};
-// Reasonable maximum to prevent insane font sizes from causing crashes on some
+// LINT.IfChange(kMaximumAllowedFontSize)
+// A maximum to prevent unreasonable font sizes from causing crashes on some
// platforms (such as Windows).
static const float kMaximumAllowedFontSize = 10000.0f;
+// LINT.ThenChange(//content/app_shim_remote_cocoa/web_menu_runner_mac.mm:fontSize)
enum class CSSBoxType : unsigned {
kMissing,
Original Bug Report
Potential Heap Buffer Overflow in Mac WebMenuRunner via unvalidated item_font_size IPC
Flapjack, an experimental security project, has identified the following potential security issue. If you’re a feature owner CC-ed on this bug, please do your best to review these reports without the Chrome Security team. Please see https://chromium.googlesource.com/chromium/src/+/main/docs/security/ai-generated-security-bugs-faq.md for more information.
Overview: A compromised renderer can send a maliciously large item_font_size via the ShowPopupMenu IPC to the browser process. This unvalidated value is passed to macOS text rendering APIs, which may trigger an integer overflow during buffer allocation. This can result in a heap buffer overflow in the unsandboxed browser or App Shim process.
Affected files:
content/app_shim_remote_cocoa/web_menu_runner_mac.mmcontent/app_shim_remote_cocoa/render_widget_host_ns_view_bridge.mmcontent/browser/renderer_host/popup_menu_helper_mac.mmcontent/common/render_widget_host_ns_view.mojom
Estimated timestamp from git blame: 2024-02-09
Description
A potential heap buffer overflow exists in the macOS implementation of popup menus. The issue occurs because the font_size parameter passed from the renderer process via the blink.mojom.LocalFrameHost.ShowPopupMenu IPC is not validated or clamped by the browser process.
While Blink internally caps font sizes (e.g., to 10,000) during style resolution, a compromised renderer can bypass Blink and send an arbitrarily large double value (e.g., 1e30) directly over the Mojo IPC.
The browser process (RenderFrameHostImpl::ShowPopupMenu) receives this value and passes it unmodified through the PopupMenuHelper to the Remote Cocoa process via the RenderWidgetHostNSView::DisplayPopupMenu IPC. In content/app_shim_remote_cocoa/web_menu_runner_mac.mm, the unsanitized value is passed directly to the native macOS API:
attrs[NSFontAttributeName] = [NSFont menuFontOfSize:_fontSize];
When macOS AppKit and CoreGraphics prepare the menu for display, they compute the dimensions of the text to calculate the required backing store memory buffer (width * height * bytes_per_pixel). An astronomically large font size can cause this calculation to overflow the 64-bit integer limit, wrapping around to a small positive value. The system then allocates an undersized buffer. When CoreGraphics attempts to rasterize the massive glyphs into this small buffer, it results in an out-of-bounds write (Heap Buffer Overflow).
Because this UI rendering occurs in the unsandboxed browser process or App Shim process, memory corruption here can be leveraged to achieve a full sandbox escape and arbitrary code execution.
Potential Steps to Reproduce
Note: These are suggested steps for exploitation, as our tooling agent does not currently have the ability to run code to produce a working proof-of-concept.
- An attacker compromises the renderer process (e.g., via a V8 vulnerability).
- The compromised renderer connects to the
blink.mojom.LocalFrameHostMojo interface in the browser process. - The attacker calls the
ShowPopupMenumethod, providing aPopupMenuClient, bounds, and setting thefont_sizeparameter to an extreme value like1e30. - The browser process passes the value to the macOS App Shim process.
WebMenuRunnerinvokes[NSFont menuFontOfSize:1e30], triggering the OS-level integer overflow during menu rasterization and causing a heap buffer overflow.
Suggested Fix
Clamp the font_size parameter in RenderFrameHostImpl::ShowPopupMenu (in content/browser/renderer_host/render_frame_host_impl.cc) to a safe maximum before it is used or passed to platform-specific UI code. A maximum of 10000.0 would match Blink’s internal kMaximumAllowedFontSize and prevent malicious values from reaching the OS APIs.
Evaluated with Chrome root at commit: cc901875d53bf4e4fe0e01f02843871da4106e70
Results so far have been promising, but there can be wrong deductions. If this proves to be a false positive, please close as WAI; data from false positives will be used to improve accuracy over time. And please feel free to reach out to me directly if you have concerns or feedback on the project.