Firefox · Graphics
CVE-2026-74964
Integer Overflow in Graphics
Overview
Medium
Severity
—
CVSS
No
Exploited ITW
Fixed
Fix Status
Changed Functions
| Function | Change | Notes |
|---|---|---|
ifgfx/cairo/cairo/src/win32/cairo-win32-printing-surface.c |
modified | |
forgfx/cairo/cairo/src/win32/cairo-win32-printing-surface.c |
modified | |
forgfx/cairo/patches/0042-win32-printing-linear-pattern.patch |
modified |
Files Changed
gfx/cairo/cairo/src/win32/cairo-win32-printing-surface.cgfx/cairo/patches/0042-win32-printing-linear-pattern.patch
Patch
diff --git a/gfx/cairo/cairo/src/win32/cairo-win32-printing-surface.c b/gfx/cairo/cairo/src/win32/cairo-win32-printing-surface.c
index c5b5f5cab62..ab5680948e6 100644
--- a/gfx/cairo/cairo/src/win32/cairo-win32-printing-surface.c
+++ b/gfx/cairo/cairo/src/win32/cairo-win32-printing-surface.c
@@ -963,8 +963,8 @@ static cairo_int_status_t
_cairo_win32_printing_surface_paint_linear_pattern (cairo_win32_printing_surface_t *surface,
cairo_linear_pattern_t *pattern)
{
- TRIVERTEX *vert;
- GRADIENT_RECT *rect;
+ TRIVERTEX *vert = NULL;
+ GRADIENT_RECT *rect = NULL;
RECT clip;
XFORM xform;
int i, num_stops;
@@ -974,6 +974,7 @@ _cairo_win32_printing_surface_paint_linear_pattern (cairo_win32_printing_surface
int range_start, range_stop, num_ranges, num_rects, stop;
int total_verts, total_rects;
cairo_status_t status;
+ cairo_uint64_t alloc_size;
extend = cairo_pattern_get_extend (&pattern->base.base);
SaveDC (surface->win32.dc);
@@ -1006,7 +1007,8 @@ _cairo_win32_printing_surface_paint_linear_pattern (cairo_win32_printing_surface
if (!SetWorldTransform (surface->win32.dc, &xform)) {
fprintf (stderr, "%s:%s\n", __FUNCTION__, "SetWorldTransform");
- return _cairo_error (CAIRO_STATUS_WIN32_GDI_ERROR);
+ status = _cairo_error (CAIRO_STATUS_WIN32_GDI_ERROR);
+ goto cleanup;
}
GetClipBox (surface->win32.dc, &clip);
@@ -1023,8 +1025,24 @@ _cairo_win32_printing_surface_paint_linear_pattern (cairo_win32_printing_surface
num_rects = num_stops - 1;
/* Add an extra four points and two rectangles for EXTEND_PAD */
- vert = _cairo_malloc (sizeof (TRIVERTEX) * (num_rects*2*num_ranges + 4));
- rect = _cairo_malloc (sizeof (GRADIENT_RECT) * (num_rects*num_ranges + 2));
+ alloc_size = sizeof (TRIVERTEX) * ((cairo_uint64_t)num_rects * 2 * (cairo_uint64_t)num_ranges + 4);
+ if (alloc_size > (cairo_uint64_t)SIZE_MAX) {
+ status = _cairo_error (CAIRO_INT_STATUS_UNSUPPORTED);
+ goto cleanup;
+ }
+ vert = _cairo_malloc (alloc_size);
+
+ alloc_size = sizeof (GRADIENT_RECT) * ((cairo_uint64_t)num_rects * (cairo_uint64_t)num_ranges + 2);
+ if (alloc_size > (cairo_uint64_t)SIZE_MAX) {
+ status = _cairo_error (CAIRO_INT_STATUS_UNSUPPORTED);
+ goto cleanup;
+ }
+ rect = _cairo_malloc (alloc_size);
+
+ if (!vert || !rect) {
+ status = _cairo_error (CAIRO_STATUS_NO_MEMORY);
+ goto cleanup;
+ }
for (i = 0; i < num_ranges*num_rects; i++) {
vert[i*2].y = (LONG) clip.top;
@@ -1098,14 +1116,15 @@ _cairo_win32_printing_surface_paint_linear_pattern (cairo_win32_printing_surface
GRADIENT_FILL_RECT_H))
{
fprintf (stderr, "%s:%s\n", __FUNCTION__, "GradientFill");
- return _cairo_error (CAIRO_STATUS_WIN32_GDI_ERROR);
+ status = _cairo_error (CAIRO_STATUS_WIN32_GDI_ERROR);
}
+cleanup:
free (rect);
free (vert);
RestoreDC (surface->win32.dc, -1);
- return 0;
+ return status;
}
static cairo_int_status_t
diff --git a/gfx/cairo/patches/0042-win32-printing-linear-pattern.patch b/gfx/cairo/patches/0042-win32-printing-linear-pattern.patch
new file mode 100644
index 00000000000..cbc546ab8fb
--- /dev/null
+++ b/gfx/cairo/patches/0042-win32-printing-linear-pattern.patch
@@ -0,0 +1,87 @@
+# HG changeset patch
+# User Jonathan Kew <[email protected]>
+# Date 1783696818 -3600
+# Fri Jul 10 16:20:18 2026 +0100
+# Node ID d4da049a5516d841cd873bcde3d097acf3ad7668
+# Parent 0b220ddc96596d5a21631503936a1f67608a309b
+Bug 2053327 - Check allocations in _cairo_win32_printing_surface_paint_linear_pattern. r=#gfx-reviewers
+
+Differential Revision: https://phabricator.services.mozilla.com/D311550
+
+diff --git a/gfx/cairo/cairo/src/win32/cairo-win32-printing-surface.c b/gfx/cairo/cairo/src/win32/cairo-win32-printing-surface.c
+--- a/gfx/cairo/cairo/src/win32/cairo-win32-printing-surface.c
++++ b/gfx/cairo/cairo/src/win32/cairo-win32-printing-surface.c
+@@ -963,8 +963,8 @@ static cairo_int_status_t
+ _cairo_win32_printing_surface_paint_linear_pattern (cairo_win32_printing_surface_t *surface,
+ cairo_linear_pattern_t *pattern)
+ {
+- TRIVERTEX *vert;
+- GRADIENT_RECT *rect;
++ TRIVERTEX *vert = NULL;
++ GRADIENT_RECT *rect = NULL;
+ RECT clip;
+ XFORM xform;
+ int i, num_stops;
+@@ -974,6 +974,7 @@ _cairo_win32_printing_surface_paint_line
+ int range_start, range_stop, num_ranges, num_rects, stop;
+ int total_verts, total_rects;
+ cairo_status_t status;
++ cairo_uint64_t alloc_size;
+
+ extend = cairo_pattern_get_extend (&pattern->base.base);
+ SaveDC (surface->win32.dc);
+@@ -1006,7 +1007,8 @@ _cairo_win32_printing_surface_paint_line
+
+ if (!SetWorldTransform (surface->win32.dc, &xform)) {
+ fprintf (stderr, "%s:%s\n", __FUNCTION__, "SetWorldTransform");
+- return _cairo_error (CAIRO_STATUS_WIN32_GDI_ERROR);
++ status = _cairo_error (CAIRO_STATUS_WIN32_GDI_ERROR);
++ goto cleanup;
+ }
+
+ GetClipBox (surface->win32.dc, &clip);
+@@ -1023,8 +1025,24 @@ _cairo_win32_printing_surface_paint_line
+ num_rects = num_stops - 1;
+
+ /* Add an extra four points and two rectangles for EXTEND_PAD */
+- vert = _cairo_malloc (sizeof (TRIVERTEX) * (num_rects*2*num_ranges + 4));
+- rect = _cairo_malloc (sizeof (GRADIENT_RECT) * (num_rects*num_ranges + 2));
++ alloc_size = sizeof (TRIVERTEX) * ((cairo_uint64_t)num_rects * 2 * (cairo_uint64_t)num_ranges + 4);
++ if (alloc_size > (cairo_uint64_t)SIZE_MAX) {
++ status = _cairo_error (CAIRO_INT_STATUS_UNSUPPORTED);
++ goto cleanup;
++ }
++ vert = _cairo_malloc (alloc_size);
++
++ alloc_size = sizeof (GRADIENT_RECT) * ((cairo_uint64_t)num_rects * (cairo_uint64_t)num_ranges + 2);
++ if (alloc_size > (cairo_uint64_t)SIZE_MAX) {
++ status = _cairo_error (CAIRO_INT_STATUS_UNSUPPORTED);
++ goto cleanup;
++ }
++ rect = _cairo_malloc (alloc_size);
++
++ if (!vert || !rect) {
++ status = _cairo_error (CAIRO_STATUS_NO_MEMORY);
++ goto cleanup;
++ }
+
+ for (i = 0; i < num_ranges*num_rects; i++) {
+ vert[i*2].y = (LONG) clip.top;
+@@ -1098,14 +1116,15 @@ _cairo_win32_printing_surface_paint_line
+ GRADIENT_FILL_RECT_H))
+ {
+ fprintf (stderr, "%s:%s\n", __FUNCTION__, "GradientFill");
+- return _cairo_error (CAIRO_STATUS_WIN32_GDI_ERROR);
++ status = _cairo_error (CAIRO_STATUS_WIN32_GDI_ERROR);
+ }
+
++cleanup:
+ free (rect);
+ free (vert);
+ RestoreDC (surface->win32.dc, -1);
+
+- return 0;
++ return status;
+ }
+
+ static cairo_int_status_t
Loading diff…
References
On This Page