Title: [271495] trunk/Source/WebKit
Revision
271495
Author
[email protected]
Date
2021-01-14 12:19:22 -0800 (Thu, 14 Jan 2021)

Log Message

[Hardening] Protect against overflows in calculateBytesPerRow()
https://bugs.webkit.org/show_bug.cgi?id=220625
<rdar://73040899>

Reviewed by Alex Christensen.

Protect against overflows in calculateBytesPerRow().

* Shared/ShareableBitmap.h:
* Shared/cairo/ShareableBitmapCairo.cpp:
(WebKit::ShareableBitmap::calculateBytesPerPixel):
* Shared/cg/ShareableBitmapCG.cpp:
(WebKit::ShareableBitmap::calculateBytesPerRow):
(WebKit::ShareableBitmap::calculateBytesPerPixel):
(WebKit::ShareableBitmap::createGraphicsContext):
(WebKit::ShareableBitmap::createCGImage const):
* Shared/win/ShareableBitmapDirect2D.cpp:
(WebKit::ShareableBitmap::calculateBytesPerPixel):

Modified Paths

Diff

Modified: trunk/Source/WebKit/ChangeLog (271494 => 271495)


--- trunk/Source/WebKit/ChangeLog	2021-01-14 18:47:24 UTC (rev 271494)
+++ trunk/Source/WebKit/ChangeLog	2021-01-14 20:19:22 UTC (rev 271495)
@@ -1,3 +1,24 @@
+2021-01-14  Chris Dumez  <[email protected]>
+
+        [Hardening] Protect against overflows in calculateBytesPerRow()
+        https://bugs.webkit.org/show_bug.cgi?id=220625
+        <rdar://73040899>
+
+        Reviewed by Alex Christensen.
+
+        Protect against overflows in calculateBytesPerRow().
+
+        * Shared/ShareableBitmap.h:
+        * Shared/cairo/ShareableBitmapCairo.cpp:
+        (WebKit::ShareableBitmap::calculateBytesPerPixel):
+        * Shared/cg/ShareableBitmapCG.cpp:
+        (WebKit::ShareableBitmap::calculateBytesPerRow):
+        (WebKit::ShareableBitmap::calculateBytesPerPixel):
+        (WebKit::ShareableBitmap::createGraphicsContext):
+        (WebKit::ShareableBitmap::createCGImage const):
+        * Shared/win/ShareableBitmapDirect2D.cpp:
+        (WebKit::ShareableBitmap::calculateBytesPerPixel):
+
 2021-01-14  Geoffrey Garen  <[email protected]>
 
         Removed most uses of dispatch_async(dispatch_get_main_queue(), ...)

Modified: trunk/Source/WebKit/Shared/ShareableBitmap.h (271494 => 271495)


--- trunk/Source/WebKit/Shared/ShareableBitmap.h	2021-01-14 18:47:24 UTC (rev 271494)
+++ trunk/Source/WebKit/Shared/ShareableBitmap.h	2021-01-14 20:19:22 UTC (rev 271495)
@@ -153,7 +153,7 @@
 
     static Checked<unsigned, RecordOverflow> numBytesForSize(WebCore::IntSize, const ShareableBitmap::Configuration&);
     static Checked<unsigned, RecordOverflow> calculateBytesPerRow(WebCore::IntSize, const Configuration&);
-    static unsigned calculateBytesPerPixel(const Configuration&);
+    static Checked<unsigned, RecordOverflow> calculateBytesPerPixel(const Configuration&);
 
 #if USE(CG)
     RetainPtr<CGImageRef> createCGImage(CGDataProviderRef) const;

Modified: trunk/Source/WebKit/Shared/cairo/ShareableBitmapCairo.cpp (271494 => 271495)


--- trunk/Source/WebKit/Shared/cairo/ShareableBitmapCairo.cpp	2021-01-14 18:47:24 UTC (rev 271494)
+++ trunk/Source/WebKit/Shared/cairo/ShareableBitmapCairo.cpp	2021-01-14 20:19:22 UTC (rev 271495)
@@ -45,7 +45,7 @@
     return cairo_format_stride_for_width(cairoFormat, size.width());
 }
 
-unsigned ShareableBitmap::calculateBytesPerPixel(const Configuration&)
+Checked<unsigned, RecordOverflow> ShareableBitmap::calculateBytesPerPixel(const Configuration&)
 {
     return 4;
 }

Modified: trunk/Source/WebKit/Shared/cg/ShareableBitmapCG.cpp (271494 => 271495)


--- trunk/Source/WebKit/Shared/cg/ShareableBitmapCG.cpp	2021-01-14 18:47:24 UTC (rev 271494)
+++ trunk/Source/WebKit/Shared/cg/ShareableBitmapCG.cpp	2021-01-14 20:19:22 UTC (rev 271495)
@@ -72,15 +72,17 @@
 
 Checked<unsigned, RecordOverflow> ShareableBitmap::calculateBytesPerRow(WebCore::IntSize size, const Configuration& configuration)
 {
-    unsigned bytesPerRow = calculateBytesPerPixel(configuration) * size.width();
+    Checked<unsigned, RecordOverflow> bytesPerRow = calculateBytesPerPixel(configuration) * size.width();
+    if (bytesPerRow.hasOverflowed())
+        return bytesPerRow;
 #if HAVE(IOSURFACE)
-    return IOSurfaceAlignProperty(kIOSurfaceBytesPerRow, bytesPerRow);
+    return IOSurfaceAlignProperty(kIOSurfaceBytesPerRow, bytesPerRow.unsafeGet());
 #else
     return bytesPerRow;
 #endif
 }
 
-unsigned ShareableBitmap::calculateBytesPerPixel(const Configuration& configuration)
+Checked<unsigned, RecordOverflow> ShareableBitmap::calculateBytesPerPixel(const Configuration& configuration)
 {
     return wantsExtendedRange(configuration) ? 8 : 4;
 }
@@ -88,13 +90,21 @@
 std::unique_ptr<GraphicsContext> ShareableBitmap::createGraphicsContext()
 {
     ASSERT(RunLoop::isMain());
-    ref(); // Balanced by deref in releaseBitmapContextData.
 
-    unsigned bytesPerPixel = calculateBytesPerPixel(m_configuration);
-    RetainPtr<CGContextRef> bitmapContext = adoptCF(CGBitmapContextCreateWithData(data(), m_size.width(), m_size.height(), bytesPerPixel * 8 / 4, calculateBytesPerRow(m_size, m_configuration).unsafeGet(), colorSpace(m_configuration), bitmapInfo(m_configuration), releaseBitmapContextData, this));
+    auto bitsPerComponent = calculateBytesPerPixel(m_configuration) * 8 / 4;
+    if (bitsPerComponent.hasOverflowed())
+        return nullptr;
+
+    auto bytesPerRow = calculateBytesPerRow(m_size, m_configuration);
+    if (bytesPerRow.hasOverflowed())
+        return nullptr;
+
+    RetainPtr<CGContextRef> bitmapContext = adoptCF(CGBitmapContextCreateWithData(data(), m_size.width(), m_size.height(), bitsPerComponent.unsafeGet(), bytesPerRow.unsafeGet(), colorSpace(m_configuration), bitmapInfo(m_configuration), releaseBitmapContextData, this));
     if (!bitmapContext)
         return nullptr;
 
+    ref(); // Balanced by deref in releaseBitmapContextData.
+
     ASSERT(bitmapContext.get());
 
     // We want the origin to be in the top left corner so we flip the backing store context.
@@ -150,8 +160,15 @@
 RetainPtr<CGImageRef> ShareableBitmap::createCGImage(CGDataProviderRef dataProvider) const
 {
     ASSERT_ARG(dataProvider, dataProvider);
-    unsigned bytesPerPixel = calculateBytesPerPixel(m_configuration);
-    RetainPtr<CGImageRef> image = adoptCF(CGImageCreate(m_size.width(), m_size.height(), bytesPerPixel * 8 / 4, bytesPerPixel * 8, calculateBytesPerRow(m_size, m_configuration).unsafeGet(), colorSpace(m_configuration), bitmapInfo(m_configuration), dataProvider, 0, false, kCGRenderingIntentDefault));
+    auto bitsPerPixel = calculateBytesPerPixel(m_configuration) * 8;
+    if (bitsPerPixel.hasOverflowed())
+        return nullptr;
+
+    auto bytesPerRow = calculateBytesPerRow(m_size, m_configuration);
+    if (bytesPerRow.hasOverflowed())
+        return nullptr;
+
+    RetainPtr<CGImageRef> image = adoptCF(CGImageCreate(m_size.width(), m_size.height(), bitsPerPixel.unsafeGet() / 4, bitsPerPixel.unsafeGet(), bytesPerRow.unsafeGet(), colorSpace(m_configuration), bitmapInfo(m_configuration), dataProvider, 0, false, kCGRenderingIntentDefault));
     return image;
 }
 

Modified: trunk/Source/WebKit/Shared/win/ShareableBitmapDirect2D.cpp (271494 => 271495)


--- trunk/Source/WebKit/Shared/win/ShareableBitmapDirect2D.cpp	2021-01-14 18:47:24 UTC (rev 271494)
+++ trunk/Source/WebKit/Shared/win/ShareableBitmapDirect2D.cpp	2021-01-14 20:19:22 UTC (rev 271495)
@@ -58,7 +58,7 @@
     return calculateBytesPerPixel(configuration) * size.width();
 }
 
-unsigned ShareableBitmap::calculateBytesPerPixel(const Configuration&)
+Checked<unsigned, RecordOverflow> ShareableBitmap::calculateBytesPerPixel(const Configuration&)
 {
     return 4;
 }
_______________________________________________
webkit-changes mailing list
[email protected]
https://lists.webkit.org/mailman/listinfo/webkit-changes

Reply via email to