<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN"
"http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head><meta http-equiv="content-type" content="text/html; charset=utf-8" />
<title>[269525] trunk</title>
</head>
<body>

<style type="text/css"><!--
#msg dl.meta { border: 1px #006 solid; background: #369; padding: 6px; color: #fff; }
#msg dl.meta dt { float: left; width: 6em; font-weight: bold; }
#msg dt:after { content:':';}
#msg dl, #msg dt, #msg ul, #msg li, #header, #footer, #logmsg { font-family: verdana,arial,helvetica,sans-serif; font-size: 10pt;  }
#msg dl a { font-weight: bold}
#msg dl a:link    { color:#fc3; }
#msg dl a:active  { color:#ff0; }
#msg dl a:visited { color:#cc6; }
h3 { font-family: verdana,arial,helvetica,sans-serif; font-size: 10pt; font-weight: bold; }
#msg pre { overflow: auto; background: #ffc; border: 1px #fa0 solid; padding: 6px; }
#logmsg { background: #ffc; border: 1px #fa0 solid; padding: 1em 1em 0 1em; }
#logmsg p, #logmsg pre, #logmsg blockquote { margin: 0 0 1em 0; }
#logmsg p, #logmsg li, #logmsg dt, #logmsg dd { line-height: 14pt; }
#logmsg h1, #logmsg h2, #logmsg h3, #logmsg h4, #logmsg h5, #logmsg h6 { margin: .5em 0; }
#logmsg h1:first-child, #logmsg h2:first-child, #logmsg h3:first-child, #logmsg h4:first-child, #logmsg h5:first-child, #logmsg h6:first-child { margin-top: 0; }
#logmsg ul, #logmsg ol { padding: 0; list-style-position: inside; margin: 0 0 0 1em; }
#logmsg ul { text-indent: -1em; padding-left: 1em; }#logmsg ol { text-indent: -1.5em; padding-left: 1.5em; }
#logmsg > ul, #logmsg > ol { margin: 0 0 1em 0; }
#logmsg pre { background: #eee; padding: 1em; }
#logmsg blockquote { border: 1px solid #fa0; border-left-width: 10px; padding: 1em 1em 0 1em; background: white;}
#logmsg dl { margin: 0; }
#logmsg dt { font-weight: bold; }
#logmsg dd { margin: 0; padding: 0 0 0.5em 0; }
#logmsg dd:before { content:'\00bb';}
#logmsg table { border-spacing: 0px; border-collapse: collapse; border-top: 4px solid #fa0; border-bottom: 1px solid #fa0; background: #fff; }
#logmsg table th { text-align: left; font-weight: normal; padding: 0.2em 0.5em; border-top: 1px dotted #fa0; }
#logmsg table td { text-align: right; border-top: 1px dotted #fa0; padding: 0.2em 0.5em; }
#logmsg table thead th { text-align: center; border-bottom: 1px solid #fa0; }
#logmsg table th.Corner { text-align: left; }
#logmsg hr { border: none 0; border-top: 2px dashed #fa0; height: 1px; }
#header, #footer { color: #fff; background: #636; border: 1px #300 solid; padding: 6px; }
#patch { width: 100%; }
#patch h4 {font-family: verdana,arial,helvetica,sans-serif;font-size:10pt;padding:8px;background:#369;color:#fff;margin:0;}
#patch .propset h4, #patch .binary h4 {margin:0;}
#patch pre {padding:0;line-height:1.2em;margin:0;}
#patch .diff {width:100%;background:#eee;padding: 0 0 10px 0;overflow:auto;}
#patch .propset .diff, #patch .binary .diff  {padding:10px 0;}
#patch span {display:block;padding:0 10px;}
#patch .modfile, #patch .addfile, #patch .delfile, #patch .propset, #patch .binary, #patch .copfile {border:1px solid #ccc;margin:10px 0;}
#patch ins {background:#dfd;text-decoration:none;display:block;padding:0 10px;}
#patch del {background:#fdd;text-decoration:none;display:block;padding:0 10px;}
#patch .lines, .info {color:#888;background:#fff;}
--></style>
<div id="msg">
<dl class="meta">
<dt>Revision</dt> <dd><a href="http://trac.webkit.org/projects/webkit/changeset/269525">269525</a></dd>
<dt>Author</dt> <dd>wenson_hsieh@apple.com</dd>
<dt>Date</dt> <dd>2020-11-06 10:54:52 -0800 (Fri, 06 Nov 2020)</dd>
</dl>

<h3>Log Message</h3>
<pre>[Concurrent display lists] Encode display list items directly into shared memory
https://bugs.webkit.org/show_bug.cgi?id=218406

Reviewed by Tim Horton.

Source/WebCore:

This patch refactors display lists (and display list items) in preparation for upcoming changes to allow the
GPU and web processes to concurrently read and write display list item data, which allows us to achieve
significant improvements in performance on many graphics benchmarks in MotionMark by removing overhead involved
in serializing and deserializing display list items over IPC. To implement this, rather than using IPC to encode
and decode each item, we will instead store display list items directly in memory shared between the web and GPU
processes.

This strategy, of course, will not work for display list items that contain pointers. Unfortunately, this
affects all display list items at the moment, since all items are subclasses of `DisplayList::Item`, and
therefore contain vtable pointers, even if all members are plain data types. Thus, the first step towards being
able to read and write items directly in shared memory is to remove this vtable pointer by making display list
items no longer inherit from `DrawingItem` or `Item`.

Currently, display lists are backed by `Vector<Ref<Item>>`; however, this no longer works once none of the
display list items are descended from a common base class. To address this, we introduce
`DisplayList::ItemBuffer`, which encapsulates logic to manage one or more data segments that contain display
list item data (i.e. display list items stacked adjacent to each other in memory). Display lists now append
inline display list items by constructing these items directly inside the item buffer using placement-new.

However, many types of display list items do not consist entirely of inline data; some of these are obvious,
such as `DrawImage`, `DrawGlyphs`, or `StrokePath` (since a `Path` may be arbitrarily complex). Other out-of-
line item types are less obvious: for instance, `FillRoundedRect` is an out-of-line item due to the fact that
the color of the rect (`FillRoundedRect::m_color`) may be an extended color, which then contains a pointer. In
these cases, we can't simply encode the item in shared memory and read it in the GPU process, since the pointer
(if it pointed to anything other than null in the web process) will point to arbitrary memory in the GPU
process. Instead, we can leverage our existing IPC infrastructure here by encoding each of these out-of-line
items as data and decoding them from this data in the GPU process. To do this, we delegate out to WebKit2 to
encode out-of-line display list items using WebKit's `IPC::Encoder`, and pass back a `SharedBuffer` which we
then copy into the item buffer. This delegation happens through the `ItemBufferWritingClient` class, which has
an implementation in WebKit2. On the decoding side in the GPU process, we then ask `ItemBufferReadingClient` (if
set) to convert this encoded data back into a display list item. In WebKit2, we implement this interface and use
the corresponding `IPC::Decoder` to decode the data we serialized earlier.

If no client is specified or the client does not require custom encoding/decoding for the given item type, we
fall back to constructing the item directly inside the writable item buffer data.

To make it easier to reason about these new (inheritance-free) display list items, we additionally introduce
`ItemHandle`, which wraps a pointer to a display list item and provides several helper methods. The first byte
of each item handle always points to an `ItemType`, and the following `N` bytes contain the item itself, where
`N` is the size of the item class. Here are some examples of how to use an `ItemHandle`:

        `DisplayList::ItemType type = itemHandle.type();` (This matches the current inheritance model)

        `if (itemHandle.is<StrokePath>()) {...` (Replaces is<> in the current model)

        `auto& setStateItem = itemHandle.get<SetState>();` (Replaces downcast<> in the current model)

        `itemHandle.apply(myGraphicsContext);` (This matches the current inheritance model)

        `bool isDrawingItem = itemHandle.isDrawingItem();` (Replaces checks for `is<DrawingItem>(item)`)

When writing display lists for the GPU process, the writing client (a `ItemBufferWritingClient`) will be asked
to provide `ItemBufferHandle`s where the item buffer will place item data (whether encoded, or as an inline
object). However, when using display lists outside of this context (e.g. in other parts of WebCore, such as the
glyph drawing cache), we don't have a `ItemBufferWritingClient`. To handle this, the item buffer instead
allocates its own (non-shared-memory) buffers, which it manages and deletes when it is done. If any out-of-line
items are constructed within these buffers, `ItemBuffer` will additionally call their destructors prior to
deleting these buffers.

See per-change comments below for more details.

* Headers.cmake:
* Sources.txt:
* WebCore.xcodeproj/project.pbxproj:
* platform/graphics/GraphicsContext.h:
* platform/graphics/displaylists/DisplayList.cpp:
(WebCore::DisplayList::DisplayList::DisplayList):
(WebCore::DisplayList::DisplayList::operator=):

Implement the move assignment operator and move constructor by exchanging ownership of the item buffer.

(WebCore::DisplayList::DisplayList::clear):
(WebCore::DisplayList::DisplayList::shouldDumpForFlags):
(WebCore::DisplayList::DisplayList::asText const):
(WebCore::DisplayList::DisplayList::dump const):

Adjust the format when printing display lists to `TextStream`. Now that drawing item extents are tracked on the
display list rather than being on each drawing item, we print them out after each item (as opposed to being in
the middle of each item).

(WebCore::DisplayList::DisplayList::sizeInBytes const):

Tally up the size of the display list by taking the sum of the sizes of each readonly segment, as well as the
writable buffer size.

(WebCore::DisplayList::DisplayList::isEmpty const):

A DisplayList is empty if it contains no item data: in other words, there are no readonly buffer segments, and
there is also nothing written to the writable buffer segment.

(WebCore::DisplayList::DisplayList::itemBuffer):
(WebCore::DisplayList::DisplayList::setItemBufferClient):
(WebCore::DisplayList::DisplayList::forEachItemBuffer const):

Add a helper to iterate over each ItemBufferHandle in the display list. This includes all readonly handles, and
then the writable handle (if it exists).

(WebCore::DisplayList::DisplayList::setTracksDrawingItemExtents):

Add an option to allow the display list to track drawing item extents. Currently, display lists always track
extents for drawing items; however, when propagating display lists to the GPU process for playback, these
extents were never sent along with IPC, and so this ended up just being unnecessary work. Additionally, the
initial clip in the GPU process is also never set, so computing these extents never helped.

That said, drawing item extents are still printed out for the purposes of testing, so we need to keep this
logic intact; this refactoring only disables extent computation for display lists being sent to the GPU process
via remote image buffers. In a future patch, we could refactor this so that drawing items contain extent rects
as inline data that can be consulted in the GPU process.

(WebCore::DisplayList::DisplayList::append):

Display list items are no longer constructed ahead of time, and then appended to the display list. Instead,
`append` now takes the type of the item to append as a template typename argument, as well as the arguments that
will be used to construct the item.

(WebCore::DisplayList::DisplayList::iterator::atEnd const):
(WebCore::DisplayList::DisplayList::iterator::updateCurrentItem):
(WebCore::DisplayList::DisplayList::iterator::advance):
(WebCore::DisplayList::DisplayList::iterator::clearCurrentItem):
(WebCore::DisplayList::DisplayList::iterator::moveToEnd):
(WebCore::DisplayList::DisplayList::iterator::moveCursorToStartOfCurrentBuffer):

Implement a C++ iterator for DisplayList. This makes it possible to write code like this:
```
// Suppose displayList is an instance of DisplayList::DisplayList.
for (auto [item, extent] : displayList) {
        // Do things with item, which is a DisplayList::ItemHandle.
        // Maybe do things with extent, which is an Optional<FloatRect>.
}
```

* platform/graphics/displaylists/DisplayList.h:
(WebCore::DisplayList::DisplayList::tracksDrawingItemExtents const):
(WebCore::DisplayList::DisplayList::iterator::iterator):
(WebCore::DisplayList::DisplayList::iterator::~iterator):
(WebCore::DisplayList::DisplayList::iterator::operator==):
(WebCore::DisplayList::DisplayList::iterator::operator!=):
(WebCore::DisplayList::DisplayList::iterator::operator++):
(WebCore::DisplayList::DisplayList::iterator::operator* const):
(WebCore::DisplayList::DisplayList::begin const):
(WebCore::DisplayList::DisplayList::end const):
(WebCore::DisplayList::DisplayList::itemBufferIfExists const):
(WebCore::DisplayList::DisplayList::addDrawingItemExtent):
(WebCore::DisplayList::DisplayList::append):
(WebCore::DisplayList::Item::type const): Deleted.
(WebCore::DisplayList::Item::isDrawingItem const): Deleted.
(WebCore::DisplayList::DisplayList::list const): Deleted.
(WebCore::DisplayList::DisplayList::itemAt): Deleted.
(WebCore::DisplayList::DisplayList::isEmpty const): Deleted.
(WebCore::DisplayList::DisplayList::appendItem): Deleted.
(WebCore::DisplayList::DisplayList::list): Deleted.
(WebCore::DisplayList::DisplayList::encode const): Deleted.
(WebCore::DisplayList::DisplayList::decode): Deleted.

Remove the ability to `encode` and `decode` display lists, for the time being. For the communication between the
web and GPU processes, we now use `SharedDisplayListHandle`.

Unfortunately, this does mean that the extant `ClipToDrawingCommands` display list item will be broken for the
time being. In a followup patch, I plan to reimplement `DisplayList::encode` and `decode` in the new inline item
model by encoding each item (either as inline data or via `IPC::Encoder::encodeSingleObject`). However, this is
contingent on all display list item types (e.g. `DrawImage` and `DrawGlyph`) not relying on `IPC::Attachment`
for encoding, so support for `ClipToDrawingCommands` will need to wait until after fonts and images are working.

* platform/graphics/displaylists/DisplayListDrawGlyphsRecorderCoreText.cpp:
(WebCore::DisplayList::DrawGlyphsRecorder::recordDrawGlyphs):
(WebCore::DisplayList::DrawGlyphsRecorder::recordDrawImage):
* platform/graphics/displaylists/DisplayListDrawGlyphsRecorderHarfBuzz.cpp:
(WebCore::DisplayList::DrawGlyphsRecorder::drawGlyphs):
* platform/graphics/displaylists/DisplayListDrawGlyphsRecorderWin.cpp:
(WebCore::DisplayList::DrawGlyphsRecorder::drawGlyphs):

Change these to use the new templated `DisplayList::append` method.

* platform/graphics/displaylists/DisplayListDrawingContext.h:
(WebCore::DisplayList::DrawingContext::takeDisplayList):

Use `std::exchange` instead of `WTFMove`. This is actually necessary in order to ensure correctness (i.e. no
leaks or double-freeing), since the `DisplayList` instance that is being moved from needs to be empty so that it
does not try to call destructors on the items formerly inside of it.

* platform/graphics/displaylists/DisplayListItemBuffer.cpp: Added.
(WebCore::DisplayList::ItemHandle::apply):
(WebCore::DisplayList::ItemHandle::destroy):

Add helper methods to apply a display list item to a `GraphicsContext` and call the display list item's
destructor, respectively.

(WebCore::DisplayList::ItemHandle::copyTo const):

Add a helper method to copy the item into the destination handle (calling the copy constructor of the item type
in the process). This is used when copying a validated display list item into the temporary item buffer in
`DisplayList::iterator`.

(WebCore::DisplayList::ItemBuffer::ItemBuffer):
(WebCore::DisplayList::ItemBuffer::~ItemBuffer):
(WebCore::DisplayList::m_allocatedBuffers):

In the case where there is no `m_writingClient` (for instance, when using in-process `DisplayList`s to optimize
text painting), the display list item buffer is responsible for creating and managing data buffers. As such, it
needs to remember to free any buffers that it allocated when appending, and must also destroy any out-of-line
display list items (i.e. items with nontrivial destructors) when it is finished.

(WebCore::DisplayList::m_readOnlyBuffers):
(WebCore::DisplayList::m_writableBuffer):
(WebCore::DisplayList::m_writtenNumberOfBytes):

See main ChangeLog entry above for more details.

(WebCore::DisplayList::ItemBuffer::operator=):
(WebCore::DisplayList::ItemBuffer::createItemBuffer):
(WebCore::DisplayList::ItemBuffer::forEachItemBuffer const):
(WebCore::DisplayList::ItemBuffer::clear):
(WebCore::DisplayList::ItemBuffer::swapWritableBufferIfNeeded):
(WebCore::DisplayList::ItemBuffer::appendDataAndLength):
* platform/graphics/displaylists/DisplayListItemBuffer.h: Added.
(WebCore::DisplayList::ItemBufferHandle::operator bool const):
(WebCore::DisplayList::ItemBufferHandle::operator! const):
(WebCore::DisplayList::ItemHandle::operator bool const):
(WebCore::DisplayList::ItemHandle::operator! const):
(WebCore::DisplayList::ItemHandle::type const):
(WebCore::DisplayList::ItemHandle::size const):
(WebCore::DisplayList::ItemHandle::is const):
(WebCore::DisplayList::ItemHandle::get const):
(WebCore::DisplayList::ItemBufferWritingClient::~ItemBufferWritingClient):
(WebCore::DisplayList::ItemBufferReadingClient::~ItemBufferReadingClient):
(WebCore::DisplayList::ItemBuffer::sizeInBytes const):
(WebCore::DisplayList::ItemBuffer::isEmpty const):
(WebCore::DisplayList::ItemBuffer::append):
(WebCore::DisplayList::ItemBuffer::setClient):
(WebCore::DisplayList::ItemBuffer::readOnlyBuffers const):
(WebCore::DisplayList::ItemBuffer::uncheckedAppend):
* platform/graphics/displaylists/DisplayListItems.cpp:

The changes in this file make up most of the code churn in this patch, but the changes are mostly mechanical. In
summary, this patch:
- Add static constexprs for the `ItemType` of each display list item class, as well as whether or not each class
  is inline, and also whether or not each class is a drawing item.
- Remove `encode` and `decode` methods from inline item classes.
- Remove all overridden methods; each class now implements individual methods to `apply`, compute
  `globalBounds` (if applicable), and compute `localBounds` (again, if applicable).
- Adjusts textstream dumping helpers, so that they no longer dump as a `DrawingItem` before dumping each member.

(WebCore::DisplayList::SetInlineFillGradient::SetInlineFillGradient):
(WebCore::DisplayList::SetState::SetState):
(WebCore::DisplayList::DrawGlyphs::DrawGlyphs):
(WebCore::DisplayList::DrawGlyphs::generateGlyphBuffer const):
(WebCore::DisplayList::DrawGlyphs::apply const):
(WebCore::DisplayList::operator<<):
(WebCore::DisplayList::DrawNativeImage::DrawNativeImage):
(WebCore::DisplayList::DrawPattern::DrawPattern):
(WebCore::DisplayList::DrawLinesForText::DrawLinesForText):
(WebCore::DisplayList::DrawFocusRingRects::DrawFocusRingRects):
(WebCore::DisplayList::FillRectWithGradient::FillRectWithGradient):
(WebCore::DisplayList::PutImageData::PutImageData):
(WebCore::DisplayList::PaintFrameForMedia::PaintFrameForMedia):
(WebCore::DisplayList::Item::Item): Deleted.
(WebCore::DisplayList::Item::sizeInBytes): Deleted.
(WebCore::DisplayList::DrawingItem::DrawingItem): Deleted.
(WebCore::DisplayList::Save::Save): Deleted.
(WebCore::DisplayList::Restore::Restore): Deleted.
(WebCore::DisplayList::Translate::Translate): Deleted.
(WebCore::DisplayList::Rotate::Rotate): Deleted.
(WebCore::DisplayList::Scale::Scale): Deleted.
(WebCore::DisplayList::SetCTM::SetCTM): Deleted.
(WebCore::DisplayList::ConcatenateCTM::ConcatenateCTM): Deleted.
(WebCore::DisplayList::SetInlineFillGradient::create): Deleted.
(WebCore::DisplayList::SetInlineFillColor::create): Deleted.
(WebCore::DisplayList::SetInlineStrokeColor::create): Deleted.
(WebCore::DisplayList::SetStrokeThickness::create): Deleted.
(WebCore::DisplayList::SetLineCap::SetLineCap): Deleted.
(WebCore::DisplayList::SetLineDash::SetLineDash): Deleted.
(WebCore::DisplayList::SetLineJoin::SetLineJoin): Deleted.
(WebCore::DisplayList::SetMiterLimit::SetMiterLimit): Deleted.
(WebCore::DisplayList::ClearShadow::ClearShadow): Deleted.
(WebCore::DisplayList::Clip::Clip): Deleted.
(WebCore::DisplayList::ClipOut::ClipOut): Deleted.
(WebCore::DisplayList::ClipOutToPath::ClipOutToPath): Deleted.
(WebCore::DisplayList::ClipPath::ClipPath): Deleted.
(WebCore::DisplayList::ClipToDrawingCommands::ClipToDrawingCommands): Deleted.
(WebCore::DisplayList::DrawGlyphs::localBounds const): Deleted.
(WebCore::DisplayList::DrawImage::DrawImage): Deleted.
(WebCore::DisplayList::DrawTiledImage::DrawTiledImage): Deleted.
(WebCore::DisplayList::DrawTiledScaledImage::DrawTiledScaledImage): Deleted.
(WebCore::DisplayList::DrawImageBuffer::DrawImageBuffer): Deleted.
(WebCore::DisplayList::DrawRect::DrawRect): Deleted.
(WebCore::DisplayList::DrawLine::DrawLine): Deleted.
(WebCore::DisplayList::DrawDotsForDocumentMarker::DrawDotsForDocumentMarker): Deleted.
(WebCore::DisplayList::DrawEllipse::DrawEllipse): Deleted.
(WebCore::DisplayList::DrawPath::DrawPath): Deleted.
(WebCore::DisplayList::DrawFocusRingPath::DrawFocusRingPath): Deleted.
(WebCore::DisplayList::FillRect::FillRect): Deleted.
(WebCore::DisplayList::FillRectWithColor::FillRectWithColor): Deleted.
(WebCore::DisplayList::FillCompositedRect::FillCompositedRect): Deleted.
(WebCore::DisplayList::FillRoundedRect::FillRoundedRect): Deleted.
(WebCore::DisplayList::FillRectWithRoundedHole::FillRectWithRoundedHole): Deleted.
(WebCore::DisplayList::FillInlinePath::FillInlinePath): Deleted.
(WebCore::DisplayList::FillPath::FillPath): Deleted.
(WebCore::DisplayList::FillEllipse::FillEllipse): Deleted.
(WebCore::DisplayList::PaintFrameForMedia::create): Deleted.
(WebCore::DisplayList::StrokeRect::StrokeRect): Deleted.
(WebCore::DisplayList::StrokeEllipse::StrokeEllipse): Deleted.
(WebCore::DisplayList::StrokeInlinePath::StrokeInlinePath): Deleted.
(WebCore::DisplayList::StrokePath::StrokePath): Deleted.
(WebCore::DisplayList::ClearRect::ClearRect): Deleted.
(WebCore::DisplayList::BeginTransparencyLayer::BeginTransparencyLayer): Deleted.
(WebCore::DisplayList::EndTransparencyLayer::EndTransparencyLayer): Deleted.
(WebCore::DisplayList::ApplyStrokePattern::ApplyStrokePattern): Deleted.
(WebCore::DisplayList::ApplyFillPattern::ApplyFillPattern): Deleted.
(WebCore::DisplayList::ApplyDeviceScaleFactor::ApplyDeviceScaleFactor): Deleted.
* platform/graphics/displaylists/DisplayListItems.h:
(WebCore::DisplayList::Save::localBounds const):
(WebCore::DisplayList::Save::globalBounds const):
(WebCore::DisplayList::Restore::localBounds const):
(WebCore::DisplayList::Restore::globalBounds const):
(WebCore::DisplayList::Translate::Translate):
(WebCore::DisplayList::Translate::localBounds const):
(WebCore::DisplayList::Translate::globalBounds const):
(WebCore::DisplayList::Rotate::Rotate):
(WebCore::DisplayList::Rotate::localBounds const):
(WebCore::DisplayList::Rotate::globalBounds const):
(WebCore::DisplayList::Scale::Scale):
(WebCore::DisplayList::Scale::localBounds const):
(WebCore::DisplayList::Scale::globalBounds const):
(WebCore::DisplayList::SetCTM::SetCTM):
(WebCore::DisplayList::SetCTM::localBounds const):
(WebCore::DisplayList::SetCTM::globalBounds const):
(WebCore::DisplayList::ConcatenateCTM::ConcatenateCTM):
(WebCore::DisplayList::ConcatenateCTM::localBounds const):
(WebCore::DisplayList::ConcatenateCTM::globalBounds const):
(WebCore::DisplayList::SetInlineFillGradient::localBounds const):
(WebCore::DisplayList::SetInlineFillGradient::globalBounds const):
(WebCore::DisplayList::SetInlineFillColor::SetInlineFillColor):
(WebCore::DisplayList::SetInlineFillColor::color const):
(WebCore::DisplayList::SetInlineFillColor::localBounds const):
(WebCore::DisplayList::SetInlineFillColor::globalBounds const):
(WebCore::DisplayList::SetInlineStrokeColor::SetInlineStrokeColor):
(WebCore::DisplayList::SetInlineStrokeColor::color const):
(WebCore::DisplayList::SetInlineStrokeColor::localBounds const):
(WebCore::DisplayList::SetInlineStrokeColor::globalBounds const):
(WebCore::DisplayList::SetStrokeThickness::SetStrokeThickness):
(WebCore::DisplayList::SetStrokeThickness::thickness const):
(WebCore::DisplayList::SetStrokeThickness::localBounds const):
(WebCore::DisplayList::SetStrokeThickness::globalBounds const):
(WebCore::DisplayList::SetState::localBounds const):
(WebCore::DisplayList::SetState::globalBounds const):
(WebCore::DisplayList::SetState::decode):
(WebCore::DisplayList::SetLineCap::SetLineCap):
(WebCore::DisplayList::SetLineCap::localBounds const):
(WebCore::DisplayList::SetLineCap::globalBounds const):
(WebCore::DisplayList::SetLineDash::SetLineDash):
(WebCore::DisplayList::SetLineDash::localBounds const):
(WebCore::DisplayList::SetLineDash::globalBounds const):
(WebCore::DisplayList::SetLineDash::decode):
(WebCore::DisplayList::SetLineJoin::SetLineJoin):
(WebCore::DisplayList::SetLineJoin::localBounds const):
(WebCore::DisplayList::SetLineJoin::globalBounds const):
(WebCore::DisplayList::SetMiterLimit::SetMiterLimit):
(WebCore::DisplayList::SetMiterLimit::localBounds const):
(WebCore::DisplayList::SetMiterLimit::globalBounds const):
(WebCore::DisplayList::ClearShadow::localBounds const):
(WebCore::DisplayList::ClearShadow::globalBounds const):
(WebCore::DisplayList::Clip::Clip):
(WebCore::DisplayList::Clip::rect const):
(WebCore::DisplayList::Clip::localBounds const):
(WebCore::DisplayList::Clip::globalBounds const):
(WebCore::DisplayList::ClipOut::ClipOut):
(WebCore::DisplayList::ClipOut::rect const):
(WebCore::DisplayList::ClipOut::localBounds const):
(WebCore::DisplayList::ClipOut::globalBounds const):
(WebCore::DisplayList::ClipOutToPath::ClipOutToPath):
(WebCore::DisplayList::ClipOutToPath::localBounds const):
(WebCore::DisplayList::ClipOutToPath::globalBounds const):
(WebCore::DisplayList::ClipOutToPath::decode):
(WebCore::DisplayList::ClipPath::ClipPath):
(WebCore::DisplayList::ClipPath::localBounds const):
(WebCore::DisplayList::ClipPath::globalBounds const):
(WebCore::DisplayList::ClipPath::decode):
(WebCore::DisplayList::ClipToDrawingCommands::ClipToDrawingCommands):
(WebCore::DisplayList::ClipToDrawingCommands::localBounds const):
(WebCore::DisplayList::ClipToDrawingCommands::globalBounds const):
(WebCore::DisplayList::ClipToDrawingCommands::encode const):
(WebCore::DisplayList::ClipToDrawingCommands::decode):
(WebCore::DisplayList::DrawGlyphs::globalBounds const):
(WebCore::DisplayList::DrawGlyphs::localBounds const):
(WebCore::DisplayList::DrawGlyphs::encode const):
(WebCore::DisplayList::DrawGlyphs::decode):
(WebCore::DisplayList::DrawImage::DrawImage):
(WebCore::DisplayList::DrawImage::globalBounds const):
(WebCore::DisplayList::DrawImage::localBounds const):
(WebCore::DisplayList::DrawImage::decode):
(WebCore::DisplayList::DrawTiledImage::DrawTiledImage):
(WebCore::DisplayList::DrawTiledImage::globalBounds const):
(WebCore::DisplayList::DrawTiledImage::localBounds const):
(WebCore::DisplayList::DrawTiledImage::decode):
(WebCore::DisplayList::DrawTiledScaledImage::DrawTiledScaledImage):
(WebCore::DisplayList::DrawTiledScaledImage::globalBounds const):
(WebCore::DisplayList::DrawTiledScaledImage::localBounds const):
(WebCore::DisplayList::DrawTiledScaledImage::decode):
(WebCore::DisplayList::DrawImageBuffer::DrawImageBuffer):
(WebCore::DisplayList::DrawImageBuffer::globalBounds const):
(WebCore::DisplayList::DrawImageBuffer::localBounds const):
(WebCore::DisplayList::DrawImageBuffer::decode):
(WebCore::DisplayList::DrawNativeImage::source const):
(WebCore::DisplayList::DrawNativeImage::destinationRect const):
(WebCore::DisplayList::DrawNativeImage::globalBounds const):
(WebCore::DisplayList::DrawNativeImage::localBounds const):
(WebCore::DisplayList::DrawNativeImage::decode):
(WebCore::DisplayList::DrawPattern::DrawPattern):
(WebCore::DisplayList::DrawPattern::globalBounds const):
(WebCore::DisplayList::DrawPattern::localBounds const):
(WebCore::DisplayList::DrawPattern::decode):
(WebCore::DisplayList::BeginTransparencyLayer::BeginTransparencyLayer):
(WebCore::DisplayList::BeginTransparencyLayer::localBounds const):
(WebCore::DisplayList::BeginTransparencyLayer::globalBounds const):
(WebCore::DisplayList::EndTransparencyLayer::localBounds const):
(WebCore::DisplayList::EndTransparencyLayer::globalBounds const):
(WebCore::DisplayList::DrawRect::DrawRect):
(WebCore::DisplayList::DrawRect::globalBounds const):
(WebCore::DisplayList::DrawRect::localBounds const):
(WebCore::DisplayList::DrawLine::DrawLine):
(WebCore::DisplayList::DrawLine::globalBounds const):
(WebCore::DisplayList::DrawLinesForText::globalBounds const):
(WebCore::DisplayList::DrawLinesForText::decode):
(WebCore::DisplayList::DrawDotsForDocumentMarker::DrawDotsForDocumentMarker):
(WebCore::DisplayList::DrawDotsForDocumentMarker::globalBounds const):
(WebCore::DisplayList::DrawEllipse::DrawEllipse):
(WebCore::DisplayList::DrawEllipse::rect const):
(WebCore::DisplayList::DrawEllipse::globalBounds const):
(WebCore::DisplayList::DrawEllipse::localBounds const):
(WebCore::DisplayList::DrawPath::DrawPath):
(WebCore::DisplayList::DrawPath::globalBounds const):
(WebCore::DisplayList::DrawPath::localBounds const):
(WebCore::DisplayList::DrawPath::decode):
(WebCore::DisplayList::DrawFocusRingPath::DrawFocusRingPath):
(WebCore::DisplayList::DrawFocusRingPath::globalBounds const):
(WebCore::DisplayList::DrawFocusRingPath::decode):
(WebCore::DisplayList::DrawFocusRingRects::globalBounds const):
(WebCore::DisplayList::DrawFocusRingRects::decode):
(WebCore::DisplayList::FillRect::FillRect):
(WebCore::DisplayList::FillRect::rect const):
(WebCore::DisplayList::FillRect::globalBounds const):
(WebCore::DisplayList::FillRect::localBounds const):
(WebCore::DisplayList::FillRectWithColor::FillRectWithColor):
(WebCore::DisplayList::FillRectWithColor::globalBounds const):
(WebCore::DisplayList::FillRectWithColor::localBounds const):
(WebCore::DisplayList::FillRectWithColor::decode):
(WebCore::DisplayList::FillRectWithGradient::rect const):
(WebCore::DisplayList::FillRectWithGradient::gradient const):
(WebCore::DisplayList::FillRectWithGradient::globalBounds const):
(WebCore::DisplayList::FillRectWithGradient::localBounds const):
(WebCore::DisplayList::FillRectWithGradient::decode):
(WebCore::DisplayList::FillCompositedRect::FillCompositedRect):
(WebCore::DisplayList::FillCompositedRect::globalBounds const):
(WebCore::DisplayList::FillCompositedRect::localBounds const):
(WebCore::DisplayList::FillCompositedRect::decode):
(WebCore::DisplayList::FillRoundedRect::FillRoundedRect):
(WebCore::DisplayList::FillRoundedRect::globalBounds const):
(WebCore::DisplayList::FillRoundedRect::localBounds const):
(WebCore::DisplayList::FillRoundedRect::decode):
(WebCore::DisplayList::FillRectWithRoundedHole::FillRectWithRoundedHole):
(WebCore::DisplayList::FillRectWithRoundedHole::globalBounds const):
(WebCore::DisplayList::FillRectWithRoundedHole::localBounds const):
(WebCore::DisplayList::FillRectWithRoundedHole::decode):
(WebCore::DisplayList::FillInlinePath::FillInlinePath):
(WebCore::DisplayList::FillInlinePath::globalBounds const):
(WebCore::DisplayList::FillInlinePath::localBounds const):
(WebCore::DisplayList::FillPath::FillPath):
(WebCore::DisplayList::FillPath::globalBounds const):
(WebCore::DisplayList::FillPath::localBounds const):
(WebCore::DisplayList::FillPath::decode):
(WebCore::DisplayList::FillEllipse::FillEllipse):
(WebCore::DisplayList::FillEllipse::globalBounds const):
(WebCore::DisplayList::FillEllipse::localBounds const):
(WebCore::DisplayList::PutImageData::imageData const):
(WebCore::DisplayList::PutImageData::localBounds const):
(WebCore::DisplayList::PutImageData::globalBounds const):
(WebCore::DisplayList::PutImageData::encode const):
(WebCore::DisplayList::PutImageData::decode):
(WebCore::DisplayList::PaintFrameForMedia::localBounds const):
(WebCore::DisplayList::PaintFrameForMedia::globalBounds const):
(WebCore::DisplayList::StrokeRect::StrokeRect):
(WebCore::DisplayList::StrokeRect::globalBounds const):
(WebCore::DisplayList::StrokeInlinePath::StrokeInlinePath):
(WebCore::DisplayList::StrokeInlinePath::globalBounds const):
(WebCore::DisplayList::StrokePath::StrokePath):
(WebCore::DisplayList::StrokePath::globalBounds const):
(WebCore::DisplayList::StrokePath::decode):
(WebCore::DisplayList::StrokeEllipse::StrokeEllipse):
(WebCore::DisplayList::StrokeEllipse::rect const):
(WebCore::DisplayList::StrokeEllipse::globalBounds const):
(WebCore::DisplayList::ClearRect::ClearRect):
(WebCore::DisplayList::ClearRect::rect const):
(WebCore::DisplayList::ClearRect::globalBounds const):
(WebCore::DisplayList::ClearRect::localBounds const):
(WebCore::DisplayList::ApplyStrokePattern::localBounds const):
(WebCore::DisplayList::ApplyStrokePattern::globalBounds const):
(WebCore::DisplayList::ApplyFillPattern::localBounds const):
(WebCore::DisplayList::ApplyFillPattern::globalBounds const):
(WebCore::DisplayList::ApplyDeviceScaleFactor::ApplyDeviceScaleFactor):
(WebCore::DisplayList::ApplyDeviceScaleFactor::localBounds const):
(WebCore::DisplayList::ApplyDeviceScaleFactor::globalBounds const):
(WebCore::DisplayList::DrawingItem::setExtent): Deleted.
(WebCore::DisplayList::DrawingItem::extent const): Deleted.
(WebCore::DisplayList::DrawingItem::extentKnown const): Deleted.
(WebCore::DisplayList::DrawingItem::localBounds const): Deleted.
(WebCore::DisplayList::DrawingItem::globalBounds const): Deleted.
(WebCore::DisplayList::Save::create): Deleted.
(WebCore::DisplayList::Save::encode const): Deleted.
(WebCore::DisplayList::Save::decode): Deleted.
(WebCore::DisplayList::Restore::create): Deleted.
(WebCore::DisplayList::Restore::encode const): Deleted.
(WebCore::DisplayList::Restore::decode): Deleted.
(WebCore::DisplayList::Translate::create): Deleted.
(WebCore::DisplayList::Translate::encode const): Deleted.
(WebCore::DisplayList::Translate::decode): Deleted.
(WebCore::DisplayList::Rotate::create): Deleted.
(WebCore::DisplayList::Rotate::encode const): Deleted.
(WebCore::DisplayList::Rotate::decode): Deleted.
(WebCore::DisplayList::Scale::create): Deleted.
(WebCore::DisplayList::Scale::encode const): Deleted.
(WebCore::DisplayList::Scale::decode): Deleted.
(WebCore::DisplayList::SetCTM::create): Deleted.
(WebCore::DisplayList::SetCTM::encode const): Deleted.
(WebCore::DisplayList::SetCTM::decode): Deleted.
(WebCore::DisplayList::ConcatenateCTM::create): Deleted.
(WebCore::DisplayList::ConcatenateCTM::encode const): Deleted.
(WebCore::DisplayList::ConcatenateCTM::decode): Deleted.
(WebCore::DisplayList::SetInlineFillGradient::create): Deleted.
(WebCore::DisplayList::SetInlineFillGradient::encode const): Deleted.
(WebCore::DisplayList::SetInlineFillGradient::decode): Deleted.
(WebCore::DisplayList::SetInlineFillColor::encode const): Deleted.
(WebCore::DisplayList::SetInlineFillColor::decode): Deleted.
(WebCore::DisplayList::SetInlineStrokeColor::encode const): Deleted.
(WebCore::DisplayList::SetInlineStrokeColor::decode): Deleted.
(WebCore::DisplayList::SetStrokeThickness::encode const): Deleted.
(WebCore::DisplayList::SetStrokeThickness::decode): Deleted.
(WebCore::DisplayList::SetState::create): Deleted.
(WebCore::DisplayList::SetLineCap::create): Deleted.
(WebCore::DisplayList::SetLineCap::encode const): Deleted.
(WebCore::DisplayList::SetLineCap::decode): Deleted.
(WebCore::DisplayList::SetLineDash::create): Deleted.
(WebCore::DisplayList::SetLineJoin::create): Deleted.
(WebCore::DisplayList::SetLineJoin::encode const): Deleted.
(WebCore::DisplayList::SetLineJoin::decode): Deleted.
(WebCore::DisplayList::SetMiterLimit::create): Deleted.
(WebCore::DisplayList::SetMiterLimit::encode const): Deleted.
(WebCore::DisplayList::SetMiterLimit::decode): Deleted.
(WebCore::DisplayList::ClearShadow::create): Deleted.
(WebCore::DisplayList::ClearShadow::encode const): Deleted.
(WebCore::DisplayList::ClearShadow::decode): Deleted.
(WebCore::DisplayList::Clip::create): Deleted.
(WebCore::DisplayList::Clip::encode const): Deleted.
(WebCore::DisplayList::Clip::decode): Deleted.
(WebCore::DisplayList::ClipOut::create): Deleted.
(WebCore::DisplayList::ClipOut::encode const): Deleted.
(WebCore::DisplayList::ClipOut::decode): Deleted.
(WebCore::DisplayList::ClipOutToPath::create): Deleted.
(WebCore::DisplayList::ClipPath::create): Deleted.
(WebCore::DisplayList::ClipToDrawingCommands::create): Deleted.
(WebCore::DisplayList::DrawGlyphs::create): Deleted.
(WebCore::DisplayList::DrawImage::create): Deleted.
(WebCore::DisplayList::DrawTiledImage::create): Deleted.
(WebCore::DisplayList::DrawTiledScaledImage::create): Deleted.
(WebCore::DisplayList::DrawImageBuffer::create): Deleted.
(WebCore::DisplayList::DrawNativeImage::create): Deleted.
(WebCore::DisplayList::DrawPattern::create): Deleted.
(WebCore::DisplayList::BeginTransparencyLayer::create): Deleted.
(WebCore::DisplayList::BeginTransparencyLayer::encode const): Deleted.
(WebCore::DisplayList::BeginTransparencyLayer::decode): Deleted.
(WebCore::DisplayList::EndTransparencyLayer::create): Deleted.
(WebCore::DisplayList::EndTransparencyLayer::encode const): Deleted.
(WebCore::DisplayList::EndTransparencyLayer::decode): Deleted.
(WebCore::DisplayList::DrawRect::create): Deleted.
(WebCore::DisplayList::DrawRect::encode const): Deleted.
(WebCore::DisplayList::DrawRect::decode): Deleted.
(WebCore::DisplayList::DrawLine::create): Deleted.
(WebCore::DisplayList::DrawLine::encode const): Deleted.
(WebCore::DisplayList::DrawLine::decode): Deleted.
(WebCore::DisplayList::DrawLinesForText::create): Deleted.
(WebCore::DisplayList::DrawDotsForDocumentMarker::create): Deleted.
(WebCore::DisplayList::DrawDotsForDocumentMarker::encode const): Deleted.
(WebCore::DisplayList::DrawDotsForDocumentMarker::decode): Deleted.
(WebCore::DisplayList::DrawEllipse::create): Deleted.
(WebCore::DisplayList::DrawEllipse::encode const): Deleted.
(WebCore::DisplayList::DrawEllipse::decode): Deleted.
(WebCore::DisplayList::DrawPath::create): Deleted.
(WebCore::DisplayList::DrawFocusRingPath::create): Deleted.
(WebCore::DisplayList::DrawFocusRingRects::create): Deleted.
(WebCore::DisplayList::FillRect::create): Deleted.
(WebCore::DisplayList::FillRect::encode const): Deleted.
(WebCore::DisplayList::FillRect::decode): Deleted.
(WebCore::DisplayList::FillRectWithColor::create): Deleted.
(WebCore::DisplayList::FillRectWithGradient::create): Deleted.
(WebCore::DisplayList::FillCompositedRect::create): Deleted.
(WebCore::DisplayList::FillRoundedRect::create): Deleted.
(WebCore::DisplayList::FillRectWithRoundedHole::create): Deleted.
(WebCore::DisplayList::FillInlinePath::create): Deleted.
(WebCore::DisplayList::FillInlinePath::encode const): Deleted.
(WebCore::DisplayList::FillInlinePath::decode): Deleted.
(WebCore::DisplayList::FillPath::create): Deleted.
(WebCore::DisplayList::FillEllipse::create): Deleted.
(WebCore::DisplayList::FillEllipse::encode const): Deleted.
(WebCore::DisplayList::FillEllipse::decode): Deleted.
(WebCore::DisplayList::PutImageData::create): Deleted.
(WebCore::DisplayList::PaintFrameForMedia::encode const): Deleted.
(WebCore::DisplayList::PaintFrameForMedia::decode): Deleted.
(WebCore::DisplayList::StrokeRect::create): Deleted.
(WebCore::DisplayList::StrokeRect::encode const): Deleted.
(WebCore::DisplayList::StrokeRect::decode): Deleted.
(WebCore::DisplayList::StrokeInlinePath::create): Deleted.
(WebCore::DisplayList::StrokeInlinePath::encode const): Deleted.
(WebCore::DisplayList::StrokeInlinePath::decode): Deleted.
(WebCore::DisplayList::StrokePath::create): Deleted.
(WebCore::DisplayList::StrokeEllipse::create): Deleted.
(WebCore::DisplayList::StrokeEllipse::encode const): Deleted.
(WebCore::DisplayList::StrokeEllipse::decode): Deleted.
(WebCore::DisplayList::ClearRect::create): Deleted.
(WebCore::DisplayList::ClearRect::encode const): Deleted.
(WebCore::DisplayList::ClearRect::decode): Deleted.
(WebCore::DisplayList::ApplyStrokePattern::create): Deleted.
(WebCore::DisplayList::ApplyStrokePattern::encode const): Deleted.
(WebCore::DisplayList::ApplyStrokePattern::decode): Deleted.
(WebCore::DisplayList::ApplyFillPattern::create): Deleted.
(WebCore::DisplayList::ApplyFillPattern::encode const): Deleted.
(WebCore::DisplayList::ApplyFillPattern::decode): Deleted.
(WebCore::DisplayList::ApplyDeviceScaleFactor::create): Deleted.
(WebCore::DisplayList::ApplyDeviceScaleFactor::encode const): Deleted.
(WebCore::DisplayList::ApplyDeviceScaleFactor::decode): Deleted.
(WebCore::DisplayList::Item::encode const): Deleted.
(WebCore::DisplayList::Item::decode): Deleted.

Delete the generic `Item::encode` and `Item::decode` methods, since only out-of-line display list items have
encode and decode functions now.

* platform/graphics/displaylists/DisplayListRecorder.cpp:
(WebCore::DisplayList::Recorder::putImageData):
(WebCore::DisplayList::Recorder::appendStateChangeItem):
(WebCore::DisplayList::Recorder::clearShadow):
(WebCore::DisplayList::Recorder::setLineCap):
(WebCore::DisplayList::Recorder::setLineDash):
(WebCore::DisplayList::Recorder::setLineJoin):
(WebCore::DisplayList::Recorder::setMiterLimit):
(WebCore::DisplayList::Recorder::drawImage):
(WebCore::DisplayList::Recorder::drawTiledImage):
(WebCore::DisplayList::Recorder::drawImageBuffer):
(WebCore::DisplayList::Recorder::drawNativeImage):
(WebCore::DisplayList::Recorder::drawPattern):
(WebCore::DisplayList::Recorder::save):
(WebCore::DisplayList::Recorder::restore):
(WebCore::DisplayList::Recorder::translate):
(WebCore::DisplayList::Recorder::rotate):
(WebCore::DisplayList::Recorder::scale):
(WebCore::DisplayList::Recorder::concatCTM):
(WebCore::DisplayList::Recorder::setCTM):
(WebCore::DisplayList::Recorder::beginTransparencyLayer):
(WebCore::DisplayList::Recorder::endTransparencyLayer):
(WebCore::DisplayList::Recorder::drawRect):
(WebCore::DisplayList::Recorder::drawLine):
(WebCore::DisplayList::Recorder::drawLinesForText):
(WebCore::DisplayList::Recorder::drawDotsForDocumentMarker):
(WebCore::DisplayList::Recorder::drawEllipse):
(WebCore::DisplayList::Recorder::drawPath):
(WebCore::DisplayList::Recorder::drawFocusRing):
(WebCore::DisplayList::Recorder::fillRect):
(WebCore::DisplayList::Recorder::fillRoundedRect):
(WebCore::DisplayList::Recorder::fillRectWithRoundedHole):
(WebCore::DisplayList::Recorder::fillPath):
(WebCore::DisplayList::Recorder::fillEllipse):
(WebCore::DisplayList::Recorder::strokeRect):
(WebCore::DisplayList::Recorder::strokePath):
(WebCore::DisplayList::Recorder::strokeEllipse):
(WebCore::DisplayList::Recorder::clearRect):
(WebCore::DisplayList::Recorder::applyStrokePattern):
(WebCore::DisplayList::Recorder::applyFillPattern):
(WebCore::DisplayList::Recorder::clip):
(WebCore::DisplayList::Recorder::clipOut):
(WebCore::DisplayList::Recorder::clipPath):
(WebCore::DisplayList::Recorder::clipToDrawingCommands):
(WebCore::DisplayList::Recorder::paintFrameForMedia):
(WebCore::DisplayList::Recorder::applyDeviceScaleFactor):

Change these methods that append display list items en masse, such that they go from this:

        `m_displayList.append(Foo::create(arg1, arg2, arg3));`

...to this:

        `m_displayList.append<Foo>(arg1, arg2, arg3);`

(WebCore::DisplayList::Recorder::extentFromLocalBounds const):
(WebCore::DisplayList::Recorder::appendItemAndUpdateExtent): Deleted.
(WebCore::DisplayList::Recorder::appendItem): Deleted.
(WebCore::DisplayList::Recorder::updateItemExtent const): Deleted.

Extents are now automatically updated (unless otherwise specified) for any drawing items that are appended.

* platform/graphics/displaylists/DisplayListRecorder.h:
(WebCore::DisplayList::Recorder::append):
* platform/graphics/displaylists/DisplayListReplayer.cpp:
(WebCore::DisplayList::Replayer::replay):
* platform/graphics/displaylists/DisplayListReplayer.h:
(WebCore::DisplayList::Replayer::Delegate::apply):

Source/WebKit:

Adjust for changes to display lists and display list items in WebCore (see Source/WebCore/ChangeLog for more
information). In particular, we implement the reading and writing client hooks consulted by ItemBuffer, and we
also add a temporary mechanism that allows RemoteRenderingBackendProxy (in the web process) to send display list
item data through shared memory to the RemoteRenderingBackend (in the GPU process). This temporary mechanism
does not attempt to make any reading or writing in shared memory concurrent between the GPU and web processes,
and exists only to make sure that rendering with the GPU process still works using these new display list items.

In the next patch, I will add a simple concurrent reader/writer model for display list processing between the
web and GPU processes, and (in doing so) revert most of the changes in `RemoteRenderingBackend` and
`RemoteRenderingBackendProxy` below.

See comments below for more detail.

* GPUProcess/graphics/RemoteImageBuffer.h:
(WebKit::RemoteImageBuffer::decodeAndCreate):
* GPUProcess/graphics/RemoteRenderingBackend.cpp:
(WebKit::RemoteRenderingBackend::applyResourceItem):
(WebKit::RemoteRenderingBackend::applyMediaItem):

Refactor these to take `WebCore::DisplayList::ItemHandle`.

(WebKit::RemoteRenderingBackend::applyDisplayList):
(WebKit::RemoteRenderingBackend::flushDisplayList):
(WebKit::RemoteRenderingBackend::flushDisplayListAndCommit):
(WebKit::RemoteRenderingBackend::didCreateSharedItemData):
* GPUProcess/graphics/RemoteRenderingBackend.h:
* GPUProcess/graphics/RemoteRenderingBackend.messages.in:
* Scripts/webkit/messages.py:
* Shared/SharedDisplayListHandle.cpp: Added.
(WebKit::SharedDisplayListHandle::SharedDisplayListHandle):
(WebKit::SharedDisplayListHandle::createDisplayList const):
* Shared/SharedDisplayListHandle.h: Added.

Add a WebKit2 helper class that represents display list data in shared memory that is propagated from the web
process to the GPU process. In the next patch, this class will be rewritten to support concurrent display list
reading and writing, with specialized subclasses in service of both the reader (i.e. the GPU process) and the
writer (i.e. the web process).

(WebKit::SharedDisplayListHandle::SharedDisplayListHandle):
(WebKit::SharedDisplayListHandle::encode const):
(WebKit::SharedDisplayListHandle::decode):
* Sources.txt:
* WebKit.xcodeproj/project.pbxproj:
* WebProcess/GPU/graphics/RemoteImageBufferProxy.h:
(WebKit::RemoteImageBufferProxy::RemoteImageBufferProxy):
* WebProcess/GPU/graphics/RemoteRenderingBackendProxy.cpp:
(WebKit::RemoteRenderingBackendProxy::flushDisplayList):
(WebKit::RemoteRenderingBackendProxy::flushDisplayListAndCommit):
(WebKit::RemoteRenderingBackendProxy::createItemBuffer):
* WebProcess/GPU/graphics/RemoteRenderingBackendProxy.h:
* WebProcess/GPU/graphics/RemoteRenderingBackendProxy.messages.in:
* WebProcess/GPU/graphics/RemoteResourceCacheProxy.cpp:

LayoutTests:

Rebaseline several existing (non-GPU-process) display list tests to account for a slight tweak in the format in
which display lists are dumped as text. More specifically, drawing item extents are now dumped after each
drawing item, rather than before.

* displaylists/canvas-display-list-expected.txt:
* displaylists/extent-includes-shadow-expected.txt:
* displaylists/extent-includes-transforms-expected.txt:
* displaylists/layer-dispay-list-expected.txt:
* displaylists/replay-skip-clipped-rect-expected.txt:</pre>

<h3>Modified Paths</h3>
<ul>
<li><a href="#trunkLayoutTestsChangeLog">trunk/LayoutTests/ChangeLog</a></li>
<li><a href="#trunkLayoutTestsdisplaylistscanvasdisplaylistexpectedtxt">trunk/LayoutTests/displaylists/canvas-display-list-expected.txt</a></li>
<li><a href="#trunkLayoutTestsdisplaylistsextentincludesshadowexpectedtxt">trunk/LayoutTests/displaylists/extent-includes-shadow-expected.txt</a></li>
<li><a href="#trunkLayoutTestsdisplaylistsextentincludestransformsexpectedtxt">trunk/LayoutTests/displaylists/extent-includes-transforms-expected.txt</a></li>
<li><a href="#trunkLayoutTestsdisplaylistslayerdispaylistexpectedtxt">trunk/LayoutTests/displaylists/layer-dispay-list-expected.txt</a></li>
<li><a href="#trunkLayoutTestsdisplaylistsreplayskipclippedrectexpectedtxt">trunk/LayoutTests/displaylists/replay-skip-clipped-rect-expected.txt</a></li>
<li><a href="#trunkSourceWebCoreChangeLog">trunk/Source/WebCore/ChangeLog</a></li>
<li><a href="#trunkSourceWebCoreHeaderscmake">trunk/Source/WebCore/Headers.cmake</a></li>
<li><a href="#trunkSourceWebCoreSourcestxt">trunk/Source/WebCore/Sources.txt</a></li>
<li><a href="#trunkSourceWebCoreWebCorexcodeprojprojectpbxproj">trunk/Source/WebCore/WebCore.xcodeproj/project.pbxproj</a></li>
<li><a href="#trunkSourceWebCoreplatformgraphicsGraphicsContexth">trunk/Source/WebCore/platform/graphics/GraphicsContext.h</a></li>
<li><a href="#trunkSourceWebCoreplatformgraphicsdisplaylistsDisplayListcpp">trunk/Source/WebCore/platform/graphics/displaylists/DisplayList.cpp</a></li>
<li><a href="#trunkSourceWebCoreplatformgraphicsdisplaylistsDisplayListh">trunk/Source/WebCore/platform/graphics/displaylists/DisplayList.h</a></li>
<li><a href="#trunkSourceWebCoreplatformgraphicsdisplaylistsDisplayListDrawGlyphsRecorderCoreTextcpp">trunk/Source/WebCore/platform/graphics/displaylists/DisplayListDrawGlyphsRecorderCoreText.cpp</a></li>
<li><a href="#trunkSourceWebCoreplatformgraphicsdisplaylistsDisplayListDrawGlyphsRecorderHarfBuzzcpp">trunk/Source/WebCore/platform/graphics/displaylists/DisplayListDrawGlyphsRecorderHarfBuzz.cpp</a></li>
<li><a href="#trunkSourceWebCoreplatformgraphicsdisplaylistsDisplayListDrawGlyphsRecorderWincpp">trunk/Source/WebCore/platform/graphics/displaylists/DisplayListDrawGlyphsRecorderWin.cpp</a></li>
<li><a href="#trunkSourceWebCoreplatformgraphicsdisplaylistsDisplayListDrawingContexth">trunk/Source/WebCore/platform/graphics/displaylists/DisplayListDrawingContext.h</a></li>
<li><a href="#trunkSourceWebCoreplatformgraphicsdisplaylistsDisplayListItemscpp">trunk/Source/WebCore/platform/graphics/displaylists/DisplayListItems.cpp</a></li>
<li><a href="#trunkSourceWebCoreplatformgraphicsdisplaylistsDisplayListItemsh">trunk/Source/WebCore/platform/graphics/displaylists/DisplayListItems.h</a></li>
<li><a href="#trunkSourceWebCoreplatformgraphicsdisplaylistsDisplayListRecordercpp">trunk/Source/WebCore/platform/graphics/displaylists/DisplayListRecorder.cpp</a></li>
<li><a href="#trunkSourceWebCoreplatformgraphicsdisplaylistsDisplayListRecorderh">trunk/Source/WebCore/platform/graphics/displaylists/DisplayListRecorder.h</a></li>
<li><a href="#trunkSourceWebCoreplatformgraphicsdisplaylistsDisplayListReplayercpp">trunk/Source/WebCore/platform/graphics/displaylists/DisplayListReplayer.cpp</a></li>
<li><a href="#trunkSourceWebCoreplatformgraphicsdisplaylistsDisplayListReplayerh">trunk/Source/WebCore/platform/graphics/displaylists/DisplayListReplayer.h</a></li>
<li><a href="#trunkSourceWebKitChangeLog">trunk/Source/WebKit/ChangeLog</a></li>
<li><a href="#trunkSourceWebKitGPUProcessgraphicsRemoteImageBufferh">trunk/Source/WebKit/GPUProcess/graphics/RemoteImageBuffer.h</a></li>
<li><a href="#trunkSourceWebKitGPUProcessgraphicsRemoteRenderingBackendcpp">trunk/Source/WebKit/GPUProcess/graphics/RemoteRenderingBackend.cpp</a></li>
<li><a href="#trunkSourceWebKitGPUProcessgraphicsRemoteRenderingBackendh">trunk/Source/WebKit/GPUProcess/graphics/RemoteRenderingBackend.h</a></li>
<li><a href="#trunkSourceWebKitGPUProcessgraphicsRemoteRenderingBackendmessagesin">trunk/Source/WebKit/GPUProcess/graphics/RemoteRenderingBackend.messages.in</a></li>
<li><a href="#trunkSourceWebKitScriptswebkitmessagespy">trunk/Source/WebKit/Scripts/webkit/messages.py</a></li>
<li><a href="#trunkSourceWebKitSourcestxt">trunk/Source/WebKit/Sources.txt</a></li>
<li><a href="#trunkSourceWebKitWebKitxcodeprojprojectpbxproj">trunk/Source/WebKit/WebKit.xcodeproj/project.pbxproj</a></li>
<li><a href="#trunkSourceWebKitWebProcessGPUgraphicsRemoteImageBufferProxyh">trunk/Source/WebKit/WebProcess/GPU/graphics/RemoteImageBufferProxy.h</a></li>
<li><a href="#trunkSourceWebKitWebProcessGPUgraphicsRemoteRenderingBackendProxycpp">trunk/Source/WebKit/WebProcess/GPU/graphics/RemoteRenderingBackendProxy.cpp</a></li>
<li><a href="#trunkSourceWebKitWebProcessGPUgraphicsRemoteRenderingBackendProxyh">trunk/Source/WebKit/WebProcess/GPU/graphics/RemoteRenderingBackendProxy.h</a></li>
<li><a href="#trunkSourceWebKitWebProcessGPUgraphicsRemoteRenderingBackendProxymessagesin">trunk/Source/WebKit/WebProcess/GPU/graphics/RemoteRenderingBackendProxy.messages.in</a></li>
<li><a href="#trunkSourceWebKitWebProcessGPUgraphicsRemoteResourceCacheProxycpp">trunk/Source/WebKit/WebProcess/GPU/graphics/RemoteResourceCacheProxy.cpp</a></li>
</ul>

<h3>Added Paths</h3>
<ul>
<li><a href="#trunkSourceWebCoreplatformgraphicsdisplaylistsDisplayListItemBuffercpp">trunk/Source/WebCore/platform/graphics/displaylists/DisplayListItemBuffer.cpp</a></li>
<li><a href="#trunkSourceWebCoreplatformgraphicsdisplaylistsDisplayListItemBufferh">trunk/Source/WebCore/platform/graphics/displaylists/DisplayListItemBuffer.h</a></li>
<li><a href="#trunkSourceWebKitSharedSharedDisplayListHandlecpp">trunk/Source/WebKit/Shared/SharedDisplayListHandle.cpp</a></li>
<li><a href="#trunkSourceWebKitSharedSharedDisplayListHandleh">trunk/Source/WebKit/Shared/SharedDisplayListHandle.h</a></li>
</ul>

</div>
<div id="patch">
<h3>Diff</h3>
<a id="trunkLayoutTestsChangeLog"></a>
<div class="modfile"><h4>Modified: trunk/LayoutTests/ChangeLog (269524 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/ChangeLog      2020-11-06 18:44:09 UTC (rev 269524)
+++ trunk/LayoutTests/ChangeLog 2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -1,3 +1,20 @@
</span><ins>+2020-11-06  Wenson Hsieh  <wenson_hsieh@apple.com>
+
+        [Concurrent display lists] Encode display list items directly into shared memory
+        https://bugs.webkit.org/show_bug.cgi?id=218406
+
+        Reviewed by Tim Horton.
+
+        Rebaseline several existing (non-GPU-process) display list tests to account for a slight tweak in the format in
+        which display lists are dumped as text. More specifically, drawing item extents are now dumped after each
+        drawing item, rather than before.
+
+        * displaylists/canvas-display-list-expected.txt:
+        * displaylists/extent-includes-shadow-expected.txt:
+        * displaylists/extent-includes-transforms-expected.txt:
+        * displaylists/layer-dispay-list-expected.txt:
+        * displaylists/replay-skip-clipped-rect-expected.txt:
+
</ins><span class="cx"> 2020-11-06  Jer Noble  <jer.noble@apple.com>
</span><span class="cx"> 
</span><span class="cx">         Do not allow pages to enter fullscreen while an exit fullscreen operation is ongoing.
</span></span></pre></div>
<a id="trunkLayoutTestsdisplaylistscanvasdisplaylistexpectedtxt"></a>
<div class="modfile"><h4>Modified: trunk/LayoutTests/displaylists/canvas-display-list-expected.txt (269524 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/displaylists/canvas-display-list-expected.txt  2020-11-06 18:44:09 UTC (rev 269524)
+++ trunk/LayoutTests/displaylists/canvas-display-list-expected.txt     2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -6,10 +6,8 @@
</span><span class="cx">   (fill-color #C80000)
</span><span class="cx">   (shadows-ignore-transforms 1))
</span><span class="cx"> (fill-rect
</span><del>-  (extent at (10,140) size 55x50)
-  (rect at (10,10) size 55x50))
</del><ins>+  (rect at (10,10) size 55x50) extent at (10,140) size 55x50)
</ins><span class="cx"> (set-inline-fill-color
</span><span class="cx">   (color #0000C880))
</span><span class="cx"> (fill-rect
</span><del>-  (extent at (30,120) size 55x50)
-  (rect at (30,30) size 55x50))
</del><ins>+  (rect at (30,30) size 55x50) extent at (30,120) size 55x50)
</ins></span></pre></div>
<a id="trunkLayoutTestsdisplaylistsextentincludesshadowexpectedtxt"></a>
<div class="modfile"><h4>Modified: trunk/LayoutTests/displaylists/extent-includes-shadow-expected.txt (269524 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/displaylists/extent-includes-shadow-expected.txt       2020-11-06 18:44:09 UTC (rev 269524)
+++ trunk/LayoutTests/displaylists/extent-includes-shadow-expected.txt  2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -9,9 +9,8 @@
</span><span class="cx">   (shadow-offset width=10 height=20)
</span><span class="cx">   (shadows-use-legacy-radius 0))
</span><span class="cx"> (fill-composited-rect
</span><del>-  (extent at (43,50) size 134x137)
</del><span class="cx">   (rect at (50,50) size 100x100)
</span><span class="cx">   (color #0000FF)
</span><span class="cx">   (composite-operation source-over)
</span><del>-  (blend-mode normal))
</del><ins>+  (blend-mode normal) extent at (43,50) size 134x137)
</ins><span class="cx"> (restore)
</span></span></pre></div>
<a id="trunkLayoutTestsdisplaylistsextentincludestransformsexpectedtxt"></a>
<div class="modfile"><h4>Modified: trunk/LayoutTests/displaylists/extent-includes-transforms-expected.txt (269524 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/displaylists/extent-includes-transforms-expected.txt   2020-11-06 18:44:09 UTC (rev 269524)
+++ trunk/LayoutTests/displaylists/extent-includes-transforms-expected.txt      2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -11,11 +11,10 @@
</span><span class="cx">   (shadow-offset width=10 height=20)
</span><span class="cx">   (shadows-use-legacy-radius 0))
</span><span class="cx"> (fill-composited-rect
</span><del>-  (extent at (7.14,0.20) size 184.55x185.65)
</del><span class="cx">   (rect at (0,0) size 100x100)
</span><span class="cx">   (color #0000FF)
</span><span class="cx">   (composite-operation source-over)
</span><del>-  (blend-mode normal))
</del><ins>+  (blend-mode normal) extent at (7.14,0.20) size 184.55x185.65)
</ins><span class="cx"> (restore)
</span><span class="cx"> (set-ctm
</span><span class="cx">   (set-ctm {m=((1.00,0.00)(0.00,1.00)) t=(0.00,22.00)}))
</span></span></pre></div>
<a id="trunkLayoutTestsdisplaylistslayerdispaylistexpectedtxt"></a>
<div class="modfile"><h4>Modified: trunk/LayoutTests/displaylists/layer-dispay-list-expected.txt (269524 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/displaylists/layer-dispay-list-expected.txt    2020-11-06 18:44:09 UTC (rev 269524)
+++ trunk/LayoutTests/displaylists/layer-dispay-list-expected.txt       2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -3,11 +3,10 @@
</span><span class="cx">   (x 0.00)
</span><span class="cx">   (y 0.00))
</span><span class="cx"> (fill-composited-rect
</span><del>-  (extent at (0,0) size 104x104)
</del><span class="cx">   (rect at (0,0) size 104x104)
</span><span class="cx">   (color #008000)
</span><span class="cx">   (composite-operation source-over)
</span><del>-  (blend-mode normal))
</del><ins>+  (blend-mode normal) extent at (0,0) size 104x104)
</ins><span class="cx"> (set-state
</span><span class="cx">   (change-flags 32960)
</span><span class="cx">   (fill-color #0000FF)
</span><span class="lines">@@ -14,18 +13,14 @@
</span><span class="cx">   (stroke-style 0)
</span><span class="cx">   (should-antialias 0))
</span><span class="cx"> (draw-rect
</span><del>-  (extent at (0,0) size 104x2)
</del><span class="cx">   (rect at (0,0) size 104x2)
</span><del>-  (border-thickness 1.00))
</del><ins>+  (border-thickness 1.00) extent at (0,0) size 104x2)
</ins><span class="cx"> (draw-rect
</span><del>-  (extent at (0,102) size 104x2)
</del><span class="cx">   (rect at (0,102) size 104x2)
</span><del>-  (border-thickness 1.00))
</del><ins>+  (border-thickness 1.00) extent at (0,102) size 104x2)
</ins><span class="cx"> (draw-rect
</span><del>-  (extent at (0,0) size 2x104)
</del><span class="cx">   (rect at (0,0) size 2x104)
</span><del>-  (border-thickness 1.00))
</del><ins>+  (border-thickness 1.00) extent at (0,0) size 2x104)
</ins><span class="cx"> (draw-rect
</span><del>-  (extent at (102,0) size 2x104)
</del><span class="cx">   (rect at (102,0) size 2x104)
</span><del>-  (border-thickness 1.00))
</del><ins>+  (border-thickness 1.00) extent at (102,0) size 2x104)
</ins></span></pre></div>
<a id="trunkLayoutTestsdisplaylistsreplayskipclippedrectexpectedtxt"></a>
<div class="modfile"><h4>Modified: trunk/LayoutTests/displaylists/replay-skip-clipped-rect-expected.txt (269524 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/LayoutTests/displaylists/replay-skip-clipped-rect-expected.txt     2020-11-06 18:44:09 UTC (rev 269524)
+++ trunk/LayoutTests/displaylists/replay-skip-clipped-rect-expected.txt        2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -3,11 +3,10 @@
</span><span class="cx">   (x 0.00)
</span><span class="cx">   (y 0.00))
</span><span class="cx"> (fill-composited-rect
</span><del>-  (extent at (412,0) size 100x100)
</del><span class="cx">   (rect at (412,0) size 100x100)
</span><span class="cx">   (color #0000FF)
</span><span class="cx">   (composite-operation source-over)
</span><del>-  (blend-mode normal))
</del><ins>+  (blend-mode normal) extent at (412,0) size 100x100)
</ins><span class="cx"> 
</span><span class="cx"> replayed:
</span><span class="cx"> (
</span></span></pre></div>
<a id="trunkSourceWebCoreChangeLog"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/ChangeLog (269524 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/ChangeLog   2020-11-06 18:44:09 UTC (rev 269524)
+++ trunk/Source/WebCore/ChangeLog      2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -1,3 +1,713 @@
</span><ins>+2020-11-06  Wenson Hsieh  <wenson_hsieh@apple.com>
+
+        [Concurrent display lists] Encode display list items directly into shared memory
+        https://bugs.webkit.org/show_bug.cgi?id=218406
+
+        Reviewed by Tim Horton.
+
+        This patch refactors display lists (and display list items) in preparation for upcoming changes to allow the
+        GPU and web processes to concurrently read and write display list item data, which allows us to achieve
+        significant improvements in performance on many graphics benchmarks in MotionMark by removing overhead involved
+        in serializing and deserializing display list items over IPC. To implement this, rather than using IPC to encode
+        and decode each item, we will instead store display list items directly in memory shared between the web and GPU
+        processes.
+
+        This strategy, of course, will not work for display list items that contain pointers. Unfortunately, this
+        affects all display list items at the moment, since all items are subclasses of `DisplayList::Item`, and
+        therefore contain vtable pointers, even if all members are plain data types. Thus, the first step towards being
+        able to read and write items directly in shared memory is to remove this vtable pointer by making display list
+        items no longer inherit from `DrawingItem` or `Item`.
+
+        Currently, display lists are backed by `Vector<Ref<Item>>`; however, this no longer works once none of the
+        display list items are descended from a common base class. To address this, we introduce
+        `DisplayList::ItemBuffer`, which encapsulates logic to manage one or more data segments that contain display
+        list item data (i.e. display list items stacked adjacent to each other in memory). Display lists now append
+        inline display list items by constructing these items directly inside the item buffer using placement-new.
+
+        However, many types of display list items do not consist entirely of inline data; some of these are obvious,
+        such as `DrawImage`, `DrawGlyphs`, or `StrokePath` (since a `Path` may be arbitrarily complex). Other out-of-
+        line item types are less obvious: for instance, `FillRoundedRect` is an out-of-line item due to the fact that
+        the color of the rect (`FillRoundedRect::m_color`) may be an extended color, which then contains a pointer. In
+        these cases, we can't simply encode the item in shared memory and read it in the GPU process, since the pointer
+        (if it pointed to anything other than null in the web process) will point to arbitrary memory in the GPU
+        process. Instead, we can leverage our existing IPC infrastructure here by encoding each of these out-of-line
+        items as data and decoding them from this data in the GPU process. To do this, we delegate out to WebKit2 to
+        encode out-of-line display list items using WebKit's `IPC::Encoder`, and pass back a `SharedBuffer` which we
+        then copy into the item buffer. This delegation happens through the `ItemBufferWritingClient` class, which has
+        an implementation in WebKit2. On the decoding side in the GPU process, we then ask `ItemBufferReadingClient` (if
+        set) to convert this encoded data back into a display list item. In WebKit2, we implement this interface and use
+        the corresponding `IPC::Decoder` to decode the data we serialized earlier.
+
+        If no client is specified or the client does not require custom encoding/decoding for the given item type, we
+        fall back to constructing the item directly inside the writable item buffer data.
+
+        To make it easier to reason about these new (inheritance-free) display list items, we additionally introduce
+        `ItemHandle`, which wraps a pointer to a display list item and provides several helper methods. The first byte
+        of each item handle always points to an `ItemType`, and the following `N` bytes contain the item itself, where
+        `N` is the size of the item class. Here are some examples of how to use an `ItemHandle`:
+
+                `DisplayList::ItemType type = itemHandle.type();` (This matches the current inheritance model)
+
+                `if (itemHandle.is<StrokePath>()) {...` (Replaces is<> in the current model)
+
+                `auto& setStateItem = itemHandle.get<SetState>();` (Replaces downcast<> in the current model)
+
+                `itemHandle.apply(myGraphicsContext);` (This matches the current inheritance model)
+
+                `bool isDrawingItem = itemHandle.isDrawingItem();` (Replaces checks for `is<DrawingItem>(item)`)
+
+        When writing display lists for the GPU process, the writing client (a `ItemBufferWritingClient`) will be asked
+        to provide `ItemBufferHandle`s where the item buffer will place item data (whether encoded, or as an inline
+        object). However, when using display lists outside of this context (e.g. in other parts of WebCore, such as the
+        glyph drawing cache), we don't have a `ItemBufferWritingClient`. To handle this, the item buffer instead
+        allocates its own (non-shared-memory) buffers, which it manages and deletes when it is done. If any out-of-line
+        items are constructed within these buffers, `ItemBuffer` will additionally call their destructors prior to
+        deleting these buffers.
+
+        See per-change comments below for more details.
+
+        * Headers.cmake:
+        * Sources.txt:
+        * WebCore.xcodeproj/project.pbxproj:
+        * platform/graphics/GraphicsContext.h:
+        * platform/graphics/displaylists/DisplayList.cpp:
+        (WebCore::DisplayList::DisplayList::DisplayList):
+        (WebCore::DisplayList::DisplayList::operator=):
+
+        Implement the move assignment operator and move constructor by exchanging ownership of the item buffer.
+
+        (WebCore::DisplayList::DisplayList::clear):
+        (WebCore::DisplayList::DisplayList::shouldDumpForFlags):
+        (WebCore::DisplayList::DisplayList::asText const):
+        (WebCore::DisplayList::DisplayList::dump const):
+
+        Adjust the format when printing display lists to `TextStream`. Now that drawing item extents are tracked on the
+        display list rather than being on each drawing item, we print them out after each item (as opposed to being in
+        the middle of each item).
+
+        (WebCore::DisplayList::DisplayList::sizeInBytes const):
+
+        Tally up the size of the display list by taking the sum of the sizes of each readonly segment, as well as the
+        writable buffer size.
+
+        (WebCore::DisplayList::DisplayList::isEmpty const):
+
+        A DisplayList is empty if it contains no item data: in other words, there are no readonly buffer segments, and
+        there is also nothing written to the writable buffer segment.
+
+        (WebCore::DisplayList::DisplayList::itemBuffer):
+        (WebCore::DisplayList::DisplayList::setItemBufferClient):
+        (WebCore::DisplayList::DisplayList::forEachItemBuffer const):
+
+        Add a helper to iterate over each ItemBufferHandle in the display list. This includes all readonly handles, and
+        then the writable handle (if it exists).
+
+        (WebCore::DisplayList::DisplayList::setTracksDrawingItemExtents):
+
+        Add an option to allow the display list to track drawing item extents. Currently, display lists always track
+        extents for drawing items; however, when propagating display lists to the GPU process for playback, these
+        extents were never sent along with IPC, and so this ended up just being unnecessary work. Additionally, the
+        initial clip in the GPU process is also never set, so computing these extents never helped.
+
+        That said, drawing item extents are still printed out for the purposes of testing, so we need to keep this
+        logic intact; this refactoring only disables extent computation for display lists being sent to the GPU process
+        via remote image buffers. In a future patch, we could refactor this so that drawing items contain extent rects
+        as inline data that can be consulted in the GPU process.
+
+        (WebCore::DisplayList::DisplayList::append):
+
+        Display list items are no longer constructed ahead of time, and then appended to the display list. Instead,
+        `append` now takes the type of the item to append as a template typename argument, as well as the arguments that
+        will be used to construct the item.
+
+        (WebCore::DisplayList::DisplayList::iterator::atEnd const):
+        (WebCore::DisplayList::DisplayList::iterator::updateCurrentItem):
+        (WebCore::DisplayList::DisplayList::iterator::advance):
+        (WebCore::DisplayList::DisplayList::iterator::clearCurrentItem):
+        (WebCore::DisplayList::DisplayList::iterator::moveToEnd):
+        (WebCore::DisplayList::DisplayList::iterator::moveCursorToStartOfCurrentBuffer):
+
+        Implement a C++ iterator for DisplayList. This makes it possible to write code like this:
+        ```
+        // Suppose displayList is an instance of DisplayList::DisplayList.
+        for (auto [item, extent] : displayList) {
+                // Do things with item, which is a DisplayList::ItemHandle.
+                // Maybe do things with extent, which is an Optional<FloatRect>.
+        }
+        ```
+
+        * platform/graphics/displaylists/DisplayList.h:
+        (WebCore::DisplayList::DisplayList::tracksDrawingItemExtents const):
+        (WebCore::DisplayList::DisplayList::iterator::iterator):
+        (WebCore::DisplayList::DisplayList::iterator::~iterator):
+        (WebCore::DisplayList::DisplayList::iterator::operator==):
+        (WebCore::DisplayList::DisplayList::iterator::operator!=):
+        (WebCore::DisplayList::DisplayList::iterator::operator++):
+        (WebCore::DisplayList::DisplayList::iterator::operator* const):
+        (WebCore::DisplayList::DisplayList::begin const):
+        (WebCore::DisplayList::DisplayList::end const):
+        (WebCore::DisplayList::DisplayList::itemBufferIfExists const):
+        (WebCore::DisplayList::DisplayList::addDrawingItemExtent):
+        (WebCore::DisplayList::DisplayList::append):
+        (WebCore::DisplayList::Item::type const): Deleted.
+        (WebCore::DisplayList::Item::isDrawingItem const): Deleted.
+        (WebCore::DisplayList::DisplayList::list const): Deleted.
+        (WebCore::DisplayList::DisplayList::itemAt): Deleted.
+        (WebCore::DisplayList::DisplayList::isEmpty const): Deleted.
+        (WebCore::DisplayList::DisplayList::appendItem): Deleted.
+        (WebCore::DisplayList::DisplayList::list): Deleted.
+        (WebCore::DisplayList::DisplayList::encode const): Deleted.
+        (WebCore::DisplayList::DisplayList::decode): Deleted.
+
+        Remove the ability to `encode` and `decode` display lists, for the time being. For the communication between the
+        web and GPU processes, we now use `SharedDisplayListHandle`.
+
+        Unfortunately, this does mean that the extant `ClipToDrawingCommands` display list item will be broken for the
+        time being. In a followup patch, I plan to reimplement `DisplayList::encode` and `decode` in the new inline item
+        model by encoding each item (either as inline data or via `IPC::Encoder::encodeSingleObject`). However, this is
+        contingent on all display list item types (e.g. `DrawImage` and `DrawGlyph`) not relying on `IPC::Attachment`
+        for encoding, so support for `ClipToDrawingCommands` will need to wait until after fonts and images are working.
+
+        * platform/graphics/displaylists/DisplayListDrawGlyphsRecorderCoreText.cpp:
+        (WebCore::DisplayList::DrawGlyphsRecorder::recordDrawGlyphs):
+        (WebCore::DisplayList::DrawGlyphsRecorder::recordDrawImage):
+        * platform/graphics/displaylists/DisplayListDrawGlyphsRecorderHarfBuzz.cpp:
+        (WebCore::DisplayList::DrawGlyphsRecorder::drawGlyphs):
+        * platform/graphics/displaylists/DisplayListDrawGlyphsRecorderWin.cpp:
+        (WebCore::DisplayList::DrawGlyphsRecorder::drawGlyphs):
+
+        Change these to use the new templated `DisplayList::append` method.
+
+        * platform/graphics/displaylists/DisplayListDrawingContext.h:
+        (WebCore::DisplayList::DrawingContext::takeDisplayList):
+
+        Use `std::exchange` instead of `WTFMove`. This is actually necessary in order to ensure correctness (i.e. no
+        leaks or double-freeing), since the `DisplayList` instance that is being moved from needs to be empty so that it
+        does not try to call destructors on the items formerly inside of it.
+
+        * platform/graphics/displaylists/DisplayListItemBuffer.cpp: Added.
+        (WebCore::DisplayList::ItemHandle::apply):
+        (WebCore::DisplayList::ItemHandle::destroy):
+
+        Add helper methods to apply a display list item to a `GraphicsContext` and call the display list item's
+        destructor, respectively.
+
+        (WebCore::DisplayList::ItemHandle::copyTo const):
+
+        Add a helper method to copy the item into the destination handle (calling the copy constructor of the item type
+        in the process). This is used when copying a validated display list item into the temporary item buffer in
+        `DisplayList::iterator`.
+
+        (WebCore::DisplayList::ItemBuffer::ItemBuffer):
+        (WebCore::DisplayList::ItemBuffer::~ItemBuffer):
+        (WebCore::DisplayList::m_allocatedBuffers):
+
+        In the case where there is no `m_writingClient` (for instance, when using in-process `DisplayList`s to optimize
+        text painting), the display list item buffer is responsible for creating and managing data buffers. As such, it
+        needs to remember to free any buffers that it allocated when appending, and must also destroy any out-of-line
+        display list items (i.e. items with nontrivial destructors) when it is finished.
+
+        (WebCore::DisplayList::m_readOnlyBuffers):
+        (WebCore::DisplayList::m_writableBuffer):
+        (WebCore::DisplayList::m_writtenNumberOfBytes):
+
+        See main ChangeLog entry above for more details.
+
+        (WebCore::DisplayList::ItemBuffer::operator=):
+        (WebCore::DisplayList::ItemBuffer::createItemBuffer):
+        (WebCore::DisplayList::ItemBuffer::forEachItemBuffer const):
+        (WebCore::DisplayList::ItemBuffer::clear):
+        (WebCore::DisplayList::ItemBuffer::swapWritableBufferIfNeeded):
+        (WebCore::DisplayList::ItemBuffer::appendDataAndLength):
+        * platform/graphics/displaylists/DisplayListItemBuffer.h: Added.
+        (WebCore::DisplayList::ItemBufferHandle::operator bool const):
+        (WebCore::DisplayList::ItemBufferHandle::operator! const):
+        (WebCore::DisplayList::ItemHandle::operator bool const):
+        (WebCore::DisplayList::ItemHandle::operator! const):
+        (WebCore::DisplayList::ItemHandle::type const):
+        (WebCore::DisplayList::ItemHandle::size const):
+        (WebCore::DisplayList::ItemHandle::is const):
+        (WebCore::DisplayList::ItemHandle::get const):
+        (WebCore::DisplayList::ItemBufferWritingClient::~ItemBufferWritingClient):
+        (WebCore::DisplayList::ItemBufferReadingClient::~ItemBufferReadingClient):
+        (WebCore::DisplayList::ItemBuffer::sizeInBytes const):
+        (WebCore::DisplayList::ItemBuffer::isEmpty const):
+        (WebCore::DisplayList::ItemBuffer::append):
+        (WebCore::DisplayList::ItemBuffer::setClient):
+        (WebCore::DisplayList::ItemBuffer::readOnlyBuffers const):
+        (WebCore::DisplayList::ItemBuffer::uncheckedAppend):
+        * platform/graphics/displaylists/DisplayListItems.cpp:
+
+        The changes in this file make up most of the code churn in this patch, but the changes are mostly mechanical. In
+        summary, this patch:
+        - Add static constexprs for the `ItemType` of each display list item class, as well as whether or not each class
+          is inline, and also whether or not each class is a drawing item.
+        - Remove `encode` and `decode` methods from inline item classes.
+        - Remove all overridden methods; each class now implements individual methods to `apply`, compute
+          `globalBounds` (if applicable), and compute `localBounds` (again, if applicable).
+        - Adjusts textstream dumping helpers, so that they no longer dump as a `DrawingItem` before dumping each member.
+
+        (WebCore::DisplayList::SetInlineFillGradient::SetInlineFillGradient):
+        (WebCore::DisplayList::SetState::SetState):
+        (WebCore::DisplayList::DrawGlyphs::DrawGlyphs):
+        (WebCore::DisplayList::DrawGlyphs::generateGlyphBuffer const):
+        (WebCore::DisplayList::DrawGlyphs::apply const):
+        (WebCore::DisplayList::operator<<):
+        (WebCore::DisplayList::DrawNativeImage::DrawNativeImage):
+        (WebCore::DisplayList::DrawPattern::DrawPattern):
+        (WebCore::DisplayList::DrawLinesForText::DrawLinesForText):
+        (WebCore::DisplayList::DrawFocusRingRects::DrawFocusRingRects):
+        (WebCore::DisplayList::FillRectWithGradient::FillRectWithGradient):
+        (WebCore::DisplayList::PutImageData::PutImageData):
+        (WebCore::DisplayList::PaintFrameForMedia::PaintFrameForMedia):
+        (WebCore::DisplayList::Item::Item): Deleted.
+        (WebCore::DisplayList::Item::sizeInBytes): Deleted.
+        (WebCore::DisplayList::DrawingItem::DrawingItem): Deleted.
+        (WebCore::DisplayList::Save::Save): Deleted.
+        (WebCore::DisplayList::Restore::Restore): Deleted.
+        (WebCore::DisplayList::Translate::Translate): Deleted.
+        (WebCore::DisplayList::Rotate::Rotate): Deleted.
+        (WebCore::DisplayList::Scale::Scale): Deleted.
+        (WebCore::DisplayList::SetCTM::SetCTM): Deleted.
+        (WebCore::DisplayList::ConcatenateCTM::ConcatenateCTM): Deleted.
+        (WebCore::DisplayList::SetInlineFillGradient::create): Deleted.
+        (WebCore::DisplayList::SetInlineFillColor::create): Deleted.
+        (WebCore::DisplayList::SetInlineStrokeColor::create): Deleted.
+        (WebCore::DisplayList::SetStrokeThickness::create): Deleted.
+        (WebCore::DisplayList::SetLineCap::SetLineCap): Deleted.
+        (WebCore::DisplayList::SetLineDash::SetLineDash): Deleted.
+        (WebCore::DisplayList::SetLineJoin::SetLineJoin): Deleted.
+        (WebCore::DisplayList::SetMiterLimit::SetMiterLimit): Deleted.
+        (WebCore::DisplayList::ClearShadow::ClearShadow): Deleted.
+        (WebCore::DisplayList::Clip::Clip): Deleted.
+        (WebCore::DisplayList::ClipOut::ClipOut): Deleted.
+        (WebCore::DisplayList::ClipOutToPath::ClipOutToPath): Deleted.
+        (WebCore::DisplayList::ClipPath::ClipPath): Deleted.
+        (WebCore::DisplayList::ClipToDrawingCommands::ClipToDrawingCommands): Deleted.
+        (WebCore::DisplayList::DrawGlyphs::localBounds const): Deleted.
+        (WebCore::DisplayList::DrawImage::DrawImage): Deleted.
+        (WebCore::DisplayList::DrawTiledImage::DrawTiledImage): Deleted.
+        (WebCore::DisplayList::DrawTiledScaledImage::DrawTiledScaledImage): Deleted.
+        (WebCore::DisplayList::DrawImageBuffer::DrawImageBuffer): Deleted.
+        (WebCore::DisplayList::DrawRect::DrawRect): Deleted.
+        (WebCore::DisplayList::DrawLine::DrawLine): Deleted.
+        (WebCore::DisplayList::DrawDotsForDocumentMarker::DrawDotsForDocumentMarker): Deleted.
+        (WebCore::DisplayList::DrawEllipse::DrawEllipse): Deleted.
+        (WebCore::DisplayList::DrawPath::DrawPath): Deleted.
+        (WebCore::DisplayList::DrawFocusRingPath::DrawFocusRingPath): Deleted.
+        (WebCore::DisplayList::FillRect::FillRect): Deleted.
+        (WebCore::DisplayList::FillRectWithColor::FillRectWithColor): Deleted.
+        (WebCore::DisplayList::FillCompositedRect::FillCompositedRect): Deleted.
+        (WebCore::DisplayList::FillRoundedRect::FillRoundedRect): Deleted.
+        (WebCore::DisplayList::FillRectWithRoundedHole::FillRectWithRoundedHole): Deleted.
+        (WebCore::DisplayList::FillInlinePath::FillInlinePath): Deleted.
+        (WebCore::DisplayList::FillPath::FillPath): Deleted.
+        (WebCore::DisplayList::FillEllipse::FillEllipse): Deleted.
+        (WebCore::DisplayList::PaintFrameForMedia::create): Deleted.
+        (WebCore::DisplayList::StrokeRect::StrokeRect): Deleted.
+        (WebCore::DisplayList::StrokeEllipse::StrokeEllipse): Deleted.
+        (WebCore::DisplayList::StrokeInlinePath::StrokeInlinePath): Deleted.
+        (WebCore::DisplayList::StrokePath::StrokePath): Deleted.
+        (WebCore::DisplayList::ClearRect::ClearRect): Deleted.
+        (WebCore::DisplayList::BeginTransparencyLayer::BeginTransparencyLayer): Deleted.
+        (WebCore::DisplayList::EndTransparencyLayer::EndTransparencyLayer): Deleted.
+        (WebCore::DisplayList::ApplyStrokePattern::ApplyStrokePattern): Deleted.
+        (WebCore::DisplayList::ApplyFillPattern::ApplyFillPattern): Deleted.
+        (WebCore::DisplayList::ApplyDeviceScaleFactor::ApplyDeviceScaleFactor): Deleted.
+        * platform/graphics/displaylists/DisplayListItems.h:
+        (WebCore::DisplayList::Save::localBounds const):
+        (WebCore::DisplayList::Save::globalBounds const):
+        (WebCore::DisplayList::Restore::localBounds const):
+        (WebCore::DisplayList::Restore::globalBounds const):
+        (WebCore::DisplayList::Translate::Translate):
+        (WebCore::DisplayList::Translate::localBounds const):
+        (WebCore::DisplayList::Translate::globalBounds const):
+        (WebCore::DisplayList::Rotate::Rotate):
+        (WebCore::DisplayList::Rotate::localBounds const):
+        (WebCore::DisplayList::Rotate::globalBounds const):
+        (WebCore::DisplayList::Scale::Scale):
+        (WebCore::DisplayList::Scale::localBounds const):
+        (WebCore::DisplayList::Scale::globalBounds const):
+        (WebCore::DisplayList::SetCTM::SetCTM):
+        (WebCore::DisplayList::SetCTM::localBounds const):
+        (WebCore::DisplayList::SetCTM::globalBounds const):
+        (WebCore::DisplayList::ConcatenateCTM::ConcatenateCTM):
+        (WebCore::DisplayList::ConcatenateCTM::localBounds const):
+        (WebCore::DisplayList::ConcatenateCTM::globalBounds const):
+        (WebCore::DisplayList::SetInlineFillGradient::localBounds const):
+        (WebCore::DisplayList::SetInlineFillGradient::globalBounds const):
+        (WebCore::DisplayList::SetInlineFillColor::SetInlineFillColor):
+        (WebCore::DisplayList::SetInlineFillColor::color const):
+        (WebCore::DisplayList::SetInlineFillColor::localBounds const):
+        (WebCore::DisplayList::SetInlineFillColor::globalBounds const):
+        (WebCore::DisplayList::SetInlineStrokeColor::SetInlineStrokeColor):
+        (WebCore::DisplayList::SetInlineStrokeColor::color const):
+        (WebCore::DisplayList::SetInlineStrokeColor::localBounds const):
+        (WebCore::DisplayList::SetInlineStrokeColor::globalBounds const):
+        (WebCore::DisplayList::SetStrokeThickness::SetStrokeThickness):
+        (WebCore::DisplayList::SetStrokeThickness::thickness const):
+        (WebCore::DisplayList::SetStrokeThickness::localBounds const):
+        (WebCore::DisplayList::SetStrokeThickness::globalBounds const):
+        (WebCore::DisplayList::SetState::localBounds const):
+        (WebCore::DisplayList::SetState::globalBounds const):
+        (WebCore::DisplayList::SetState::decode):
+        (WebCore::DisplayList::SetLineCap::SetLineCap):
+        (WebCore::DisplayList::SetLineCap::localBounds const):
+        (WebCore::DisplayList::SetLineCap::globalBounds const):
+        (WebCore::DisplayList::SetLineDash::SetLineDash):
+        (WebCore::DisplayList::SetLineDash::localBounds const):
+        (WebCore::DisplayList::SetLineDash::globalBounds const):
+        (WebCore::DisplayList::SetLineDash::decode):
+        (WebCore::DisplayList::SetLineJoin::SetLineJoin):
+        (WebCore::DisplayList::SetLineJoin::localBounds const):
+        (WebCore::DisplayList::SetLineJoin::globalBounds const):
+        (WebCore::DisplayList::SetMiterLimit::SetMiterLimit):
+        (WebCore::DisplayList::SetMiterLimit::localBounds const):
+        (WebCore::DisplayList::SetMiterLimit::globalBounds const):
+        (WebCore::DisplayList::ClearShadow::localBounds const):
+        (WebCore::DisplayList::ClearShadow::globalBounds const):
+        (WebCore::DisplayList::Clip::Clip):
+        (WebCore::DisplayList::Clip::rect const):
+        (WebCore::DisplayList::Clip::localBounds const):
+        (WebCore::DisplayList::Clip::globalBounds const):
+        (WebCore::DisplayList::ClipOut::ClipOut):
+        (WebCore::DisplayList::ClipOut::rect const):
+        (WebCore::DisplayList::ClipOut::localBounds const):
+        (WebCore::DisplayList::ClipOut::globalBounds const):
+        (WebCore::DisplayList::ClipOutToPath::ClipOutToPath):
+        (WebCore::DisplayList::ClipOutToPath::localBounds const):
+        (WebCore::DisplayList::ClipOutToPath::globalBounds const):
+        (WebCore::DisplayList::ClipOutToPath::decode):
+        (WebCore::DisplayList::ClipPath::ClipPath):
+        (WebCore::DisplayList::ClipPath::localBounds const):
+        (WebCore::DisplayList::ClipPath::globalBounds const):
+        (WebCore::DisplayList::ClipPath::decode):
+        (WebCore::DisplayList::ClipToDrawingCommands::ClipToDrawingCommands):
+        (WebCore::DisplayList::ClipToDrawingCommands::localBounds const):
+        (WebCore::DisplayList::ClipToDrawingCommands::globalBounds const):
+        (WebCore::DisplayList::ClipToDrawingCommands::encode const):
+        (WebCore::DisplayList::ClipToDrawingCommands::decode):
+        (WebCore::DisplayList::DrawGlyphs::globalBounds const):
+        (WebCore::DisplayList::DrawGlyphs::localBounds const):
+        (WebCore::DisplayList::DrawGlyphs::encode const):
+        (WebCore::DisplayList::DrawGlyphs::decode):
+        (WebCore::DisplayList::DrawImage::DrawImage):
+        (WebCore::DisplayList::DrawImage::globalBounds const):
+        (WebCore::DisplayList::DrawImage::localBounds const):
+        (WebCore::DisplayList::DrawImage::decode):
+        (WebCore::DisplayList::DrawTiledImage::DrawTiledImage):
+        (WebCore::DisplayList::DrawTiledImage::globalBounds const):
+        (WebCore::DisplayList::DrawTiledImage::localBounds const):
+        (WebCore::DisplayList::DrawTiledImage::decode):
+        (WebCore::DisplayList::DrawTiledScaledImage::DrawTiledScaledImage):
+        (WebCore::DisplayList::DrawTiledScaledImage::globalBounds const):
+        (WebCore::DisplayList::DrawTiledScaledImage::localBounds const):
+        (WebCore::DisplayList::DrawTiledScaledImage::decode):
+        (WebCore::DisplayList::DrawImageBuffer::DrawImageBuffer):
+        (WebCore::DisplayList::DrawImageBuffer::globalBounds const):
+        (WebCore::DisplayList::DrawImageBuffer::localBounds const):
+        (WebCore::DisplayList::DrawImageBuffer::decode):
+        (WebCore::DisplayList::DrawNativeImage::source const):
+        (WebCore::DisplayList::DrawNativeImage::destinationRect const):
+        (WebCore::DisplayList::DrawNativeImage::globalBounds const):
+        (WebCore::DisplayList::DrawNativeImage::localBounds const):
+        (WebCore::DisplayList::DrawNativeImage::decode):
+        (WebCore::DisplayList::DrawPattern::DrawPattern):
+        (WebCore::DisplayList::DrawPattern::globalBounds const):
+        (WebCore::DisplayList::DrawPattern::localBounds const):
+        (WebCore::DisplayList::DrawPattern::decode):
+        (WebCore::DisplayList::BeginTransparencyLayer::BeginTransparencyLayer):
+        (WebCore::DisplayList::BeginTransparencyLayer::localBounds const):
+        (WebCore::DisplayList::BeginTransparencyLayer::globalBounds const):
+        (WebCore::DisplayList::EndTransparencyLayer::localBounds const):
+        (WebCore::DisplayList::EndTransparencyLayer::globalBounds const):
+        (WebCore::DisplayList::DrawRect::DrawRect):
+        (WebCore::DisplayList::DrawRect::globalBounds const):
+        (WebCore::DisplayList::DrawRect::localBounds const):
+        (WebCore::DisplayList::DrawLine::DrawLine):
+        (WebCore::DisplayList::DrawLine::globalBounds const):
+        (WebCore::DisplayList::DrawLinesForText::globalBounds const):
+        (WebCore::DisplayList::DrawLinesForText::decode):
+        (WebCore::DisplayList::DrawDotsForDocumentMarker::DrawDotsForDocumentMarker):
+        (WebCore::DisplayList::DrawDotsForDocumentMarker::globalBounds const):
+        (WebCore::DisplayList::DrawEllipse::DrawEllipse):
+        (WebCore::DisplayList::DrawEllipse::rect const):
+        (WebCore::DisplayList::DrawEllipse::globalBounds const):
+        (WebCore::DisplayList::DrawEllipse::localBounds const):
+        (WebCore::DisplayList::DrawPath::DrawPath):
+        (WebCore::DisplayList::DrawPath::globalBounds const):
+        (WebCore::DisplayList::DrawPath::localBounds const):
+        (WebCore::DisplayList::DrawPath::decode):
+        (WebCore::DisplayList::DrawFocusRingPath::DrawFocusRingPath):
+        (WebCore::DisplayList::DrawFocusRingPath::globalBounds const):
+        (WebCore::DisplayList::DrawFocusRingPath::decode):
+        (WebCore::DisplayList::DrawFocusRingRects::globalBounds const):
+        (WebCore::DisplayList::DrawFocusRingRects::decode):
+        (WebCore::DisplayList::FillRect::FillRect):
+        (WebCore::DisplayList::FillRect::rect const):
+        (WebCore::DisplayList::FillRect::globalBounds const):
+        (WebCore::DisplayList::FillRect::localBounds const):
+        (WebCore::DisplayList::FillRectWithColor::FillRectWithColor):
+        (WebCore::DisplayList::FillRectWithColor::globalBounds const):
+        (WebCore::DisplayList::FillRectWithColor::localBounds const):
+        (WebCore::DisplayList::FillRectWithColor::decode):
+        (WebCore::DisplayList::FillRectWithGradient::rect const):
+        (WebCore::DisplayList::FillRectWithGradient::gradient const):
+        (WebCore::DisplayList::FillRectWithGradient::globalBounds const):
+        (WebCore::DisplayList::FillRectWithGradient::localBounds const):
+        (WebCore::DisplayList::FillRectWithGradient::decode):
+        (WebCore::DisplayList::FillCompositedRect::FillCompositedRect):
+        (WebCore::DisplayList::FillCompositedRect::globalBounds const):
+        (WebCore::DisplayList::FillCompositedRect::localBounds const):
+        (WebCore::DisplayList::FillCompositedRect::decode):
+        (WebCore::DisplayList::FillRoundedRect::FillRoundedRect):
+        (WebCore::DisplayList::FillRoundedRect::globalBounds const):
+        (WebCore::DisplayList::FillRoundedRect::localBounds const):
+        (WebCore::DisplayList::FillRoundedRect::decode):
+        (WebCore::DisplayList::FillRectWithRoundedHole::FillRectWithRoundedHole):
+        (WebCore::DisplayList::FillRectWithRoundedHole::globalBounds const):
+        (WebCore::DisplayList::FillRectWithRoundedHole::localBounds const):
+        (WebCore::DisplayList::FillRectWithRoundedHole::decode):
+        (WebCore::DisplayList::FillInlinePath::FillInlinePath):
+        (WebCore::DisplayList::FillInlinePath::globalBounds const):
+        (WebCore::DisplayList::FillInlinePath::localBounds const):
+        (WebCore::DisplayList::FillPath::FillPath):
+        (WebCore::DisplayList::FillPath::globalBounds const):
+        (WebCore::DisplayList::FillPath::localBounds const):
+        (WebCore::DisplayList::FillPath::decode):
+        (WebCore::DisplayList::FillEllipse::FillEllipse):
+        (WebCore::DisplayList::FillEllipse::globalBounds const):
+        (WebCore::DisplayList::FillEllipse::localBounds const):
+        (WebCore::DisplayList::PutImageData::imageData const):
+        (WebCore::DisplayList::PutImageData::localBounds const):
+        (WebCore::DisplayList::PutImageData::globalBounds const):
+        (WebCore::DisplayList::PutImageData::encode const):
+        (WebCore::DisplayList::PutImageData::decode):
+        (WebCore::DisplayList::PaintFrameForMedia::localBounds const):
+        (WebCore::DisplayList::PaintFrameForMedia::globalBounds const):
+        (WebCore::DisplayList::StrokeRect::StrokeRect):
+        (WebCore::DisplayList::StrokeRect::globalBounds const):
+        (WebCore::DisplayList::StrokeInlinePath::StrokeInlinePath):
+        (WebCore::DisplayList::StrokeInlinePath::globalBounds const):
+        (WebCore::DisplayList::StrokePath::StrokePath):
+        (WebCore::DisplayList::StrokePath::globalBounds const):
+        (WebCore::DisplayList::StrokePath::decode):
+        (WebCore::DisplayList::StrokeEllipse::StrokeEllipse):
+        (WebCore::DisplayList::StrokeEllipse::rect const):
+        (WebCore::DisplayList::StrokeEllipse::globalBounds const):
+        (WebCore::DisplayList::ClearRect::ClearRect):
+        (WebCore::DisplayList::ClearRect::rect const):
+        (WebCore::DisplayList::ClearRect::globalBounds const):
+        (WebCore::DisplayList::ClearRect::localBounds const):
+        (WebCore::DisplayList::ApplyStrokePattern::localBounds const):
+        (WebCore::DisplayList::ApplyStrokePattern::globalBounds const):
+        (WebCore::DisplayList::ApplyFillPattern::localBounds const):
+        (WebCore::DisplayList::ApplyFillPattern::globalBounds const):
+        (WebCore::DisplayList::ApplyDeviceScaleFactor::ApplyDeviceScaleFactor):
+        (WebCore::DisplayList::ApplyDeviceScaleFactor::localBounds const):
+        (WebCore::DisplayList::ApplyDeviceScaleFactor::globalBounds const):
+        (WebCore::DisplayList::DrawingItem::setExtent): Deleted.
+        (WebCore::DisplayList::DrawingItem::extent const): Deleted.
+        (WebCore::DisplayList::DrawingItem::extentKnown const): Deleted.
+        (WebCore::DisplayList::DrawingItem::localBounds const): Deleted.
+        (WebCore::DisplayList::DrawingItem::globalBounds const): Deleted.
+        (WebCore::DisplayList::Save::create): Deleted.
+        (WebCore::DisplayList::Save::encode const): Deleted.
+        (WebCore::DisplayList::Save::decode): Deleted.
+        (WebCore::DisplayList::Restore::create): Deleted.
+        (WebCore::DisplayList::Restore::encode const): Deleted.
+        (WebCore::DisplayList::Restore::decode): Deleted.
+        (WebCore::DisplayList::Translate::create): Deleted.
+        (WebCore::DisplayList::Translate::encode const): Deleted.
+        (WebCore::DisplayList::Translate::decode): Deleted.
+        (WebCore::DisplayList::Rotate::create): Deleted.
+        (WebCore::DisplayList::Rotate::encode const): Deleted.
+        (WebCore::DisplayList::Rotate::decode): Deleted.
+        (WebCore::DisplayList::Scale::create): Deleted.
+        (WebCore::DisplayList::Scale::encode const): Deleted.
+        (WebCore::DisplayList::Scale::decode): Deleted.
+        (WebCore::DisplayList::SetCTM::create): Deleted.
+        (WebCore::DisplayList::SetCTM::encode const): Deleted.
+        (WebCore::DisplayList::SetCTM::decode): Deleted.
+        (WebCore::DisplayList::ConcatenateCTM::create): Deleted.
+        (WebCore::DisplayList::ConcatenateCTM::encode const): Deleted.
+        (WebCore::DisplayList::ConcatenateCTM::decode): Deleted.
+        (WebCore::DisplayList::SetInlineFillGradient::create): Deleted.
+        (WebCore::DisplayList::SetInlineFillGradient::encode const): Deleted.
+        (WebCore::DisplayList::SetInlineFillGradient::decode): Deleted.
+        (WebCore::DisplayList::SetInlineFillColor::encode const): Deleted.
+        (WebCore::DisplayList::SetInlineFillColor::decode): Deleted.
+        (WebCore::DisplayList::SetInlineStrokeColor::encode const): Deleted.
+        (WebCore::DisplayList::SetInlineStrokeColor::decode): Deleted.
+        (WebCore::DisplayList::SetStrokeThickness::encode const): Deleted.
+        (WebCore::DisplayList::SetStrokeThickness::decode): Deleted.
+        (WebCore::DisplayList::SetState::create): Deleted.
+        (WebCore::DisplayList::SetLineCap::create): Deleted.
+        (WebCore::DisplayList::SetLineCap::encode const): Deleted.
+        (WebCore::DisplayList::SetLineCap::decode): Deleted.
+        (WebCore::DisplayList::SetLineDash::create): Deleted.
+        (WebCore::DisplayList::SetLineJoin::create): Deleted.
+        (WebCore::DisplayList::SetLineJoin::encode const): Deleted.
+        (WebCore::DisplayList::SetLineJoin::decode): Deleted.
+        (WebCore::DisplayList::SetMiterLimit::create): Deleted.
+        (WebCore::DisplayList::SetMiterLimit::encode const): Deleted.
+        (WebCore::DisplayList::SetMiterLimit::decode): Deleted.
+        (WebCore::DisplayList::ClearShadow::create): Deleted.
+        (WebCore::DisplayList::ClearShadow::encode const): Deleted.
+        (WebCore::DisplayList::ClearShadow::decode): Deleted.
+        (WebCore::DisplayList::Clip::create): Deleted.
+        (WebCore::DisplayList::Clip::encode const): Deleted.
+        (WebCore::DisplayList::Clip::decode): Deleted.
+        (WebCore::DisplayList::ClipOut::create): Deleted.
+        (WebCore::DisplayList::ClipOut::encode const): Deleted.
+        (WebCore::DisplayList::ClipOut::decode): Deleted.
+        (WebCore::DisplayList::ClipOutToPath::create): Deleted.
+        (WebCore::DisplayList::ClipPath::create): Deleted.
+        (WebCore::DisplayList::ClipToDrawingCommands::create): Deleted.
+        (WebCore::DisplayList::DrawGlyphs::create): Deleted.
+        (WebCore::DisplayList::DrawImage::create): Deleted.
+        (WebCore::DisplayList::DrawTiledImage::create): Deleted.
+        (WebCore::DisplayList::DrawTiledScaledImage::create): Deleted.
+        (WebCore::DisplayList::DrawImageBuffer::create): Deleted.
+        (WebCore::DisplayList::DrawNativeImage::create): Deleted.
+        (WebCore::DisplayList::DrawPattern::create): Deleted.
+        (WebCore::DisplayList::BeginTransparencyLayer::create): Deleted.
+        (WebCore::DisplayList::BeginTransparencyLayer::encode const): Deleted.
+        (WebCore::DisplayList::BeginTransparencyLayer::decode): Deleted.
+        (WebCore::DisplayList::EndTransparencyLayer::create): Deleted.
+        (WebCore::DisplayList::EndTransparencyLayer::encode const): Deleted.
+        (WebCore::DisplayList::EndTransparencyLayer::decode): Deleted.
+        (WebCore::DisplayList::DrawRect::create): Deleted.
+        (WebCore::DisplayList::DrawRect::encode const): Deleted.
+        (WebCore::DisplayList::DrawRect::decode): Deleted.
+        (WebCore::DisplayList::DrawLine::create): Deleted.
+        (WebCore::DisplayList::DrawLine::encode const): Deleted.
+        (WebCore::DisplayList::DrawLine::decode): Deleted.
+        (WebCore::DisplayList::DrawLinesForText::create): Deleted.
+        (WebCore::DisplayList::DrawDotsForDocumentMarker::create): Deleted.
+        (WebCore::DisplayList::DrawDotsForDocumentMarker::encode const): Deleted.
+        (WebCore::DisplayList::DrawDotsForDocumentMarker::decode): Deleted.
+        (WebCore::DisplayList::DrawEllipse::create): Deleted.
+        (WebCore::DisplayList::DrawEllipse::encode const): Deleted.
+        (WebCore::DisplayList::DrawEllipse::decode): Deleted.
+        (WebCore::DisplayList::DrawPath::create): Deleted.
+        (WebCore::DisplayList::DrawFocusRingPath::create): Deleted.
+        (WebCore::DisplayList::DrawFocusRingRects::create): Deleted.
+        (WebCore::DisplayList::FillRect::create): Deleted.
+        (WebCore::DisplayList::FillRect::encode const): Deleted.
+        (WebCore::DisplayList::FillRect::decode): Deleted.
+        (WebCore::DisplayList::FillRectWithColor::create): Deleted.
+        (WebCore::DisplayList::FillRectWithGradient::create): Deleted.
+        (WebCore::DisplayList::FillCompositedRect::create): Deleted.
+        (WebCore::DisplayList::FillRoundedRect::create): Deleted.
+        (WebCore::DisplayList::FillRectWithRoundedHole::create): Deleted.
+        (WebCore::DisplayList::FillInlinePath::create): Deleted.
+        (WebCore::DisplayList::FillInlinePath::encode const): Deleted.
+        (WebCore::DisplayList::FillInlinePath::decode): Deleted.
+        (WebCore::DisplayList::FillPath::create): Deleted.
+        (WebCore::DisplayList::FillEllipse::create): Deleted.
+        (WebCore::DisplayList::FillEllipse::encode const): Deleted.
+        (WebCore::DisplayList::FillEllipse::decode): Deleted.
+        (WebCore::DisplayList::PutImageData::create): Deleted.
+        (WebCore::DisplayList::PaintFrameForMedia::encode const): Deleted.
+        (WebCore::DisplayList::PaintFrameForMedia::decode): Deleted.
+        (WebCore::DisplayList::StrokeRect::create): Deleted.
+        (WebCore::DisplayList::StrokeRect::encode const): Deleted.
+        (WebCore::DisplayList::StrokeRect::decode): Deleted.
+        (WebCore::DisplayList::StrokeInlinePath::create): Deleted.
+        (WebCore::DisplayList::StrokeInlinePath::encode const): Deleted.
+        (WebCore::DisplayList::StrokeInlinePath::decode): Deleted.
+        (WebCore::DisplayList::StrokePath::create): Deleted.
+        (WebCore::DisplayList::StrokeEllipse::create): Deleted.
+        (WebCore::DisplayList::StrokeEllipse::encode const): Deleted.
+        (WebCore::DisplayList::StrokeEllipse::decode): Deleted.
+        (WebCore::DisplayList::ClearRect::create): Deleted.
+        (WebCore::DisplayList::ClearRect::encode const): Deleted.
+        (WebCore::DisplayList::ClearRect::decode): Deleted.
+        (WebCore::DisplayList::ApplyStrokePattern::create): Deleted.
+        (WebCore::DisplayList::ApplyStrokePattern::encode const): Deleted.
+        (WebCore::DisplayList::ApplyStrokePattern::decode): Deleted.
+        (WebCore::DisplayList::ApplyFillPattern::create): Deleted.
+        (WebCore::DisplayList::ApplyFillPattern::encode const): Deleted.
+        (WebCore::DisplayList::ApplyFillPattern::decode): Deleted.
+        (WebCore::DisplayList::ApplyDeviceScaleFactor::create): Deleted.
+        (WebCore::DisplayList::ApplyDeviceScaleFactor::encode const): Deleted.
+        (WebCore::DisplayList::ApplyDeviceScaleFactor::decode): Deleted.
+        (WebCore::DisplayList::Item::encode const): Deleted.
+        (WebCore::DisplayList::Item::decode): Deleted.
+
+        Delete the generic `Item::encode` and `Item::decode` methods, since only out-of-line display list items have
+        encode and decode functions now.
+
+        * platform/graphics/displaylists/DisplayListRecorder.cpp:
+        (WebCore::DisplayList::Recorder::putImageData):
+        (WebCore::DisplayList::Recorder::appendStateChangeItem):
+        (WebCore::DisplayList::Recorder::clearShadow):
+        (WebCore::DisplayList::Recorder::setLineCap):
+        (WebCore::DisplayList::Recorder::setLineDash):
+        (WebCore::DisplayList::Recorder::setLineJoin):
+        (WebCore::DisplayList::Recorder::setMiterLimit):
+        (WebCore::DisplayList::Recorder::drawImage):
+        (WebCore::DisplayList::Recorder::drawTiledImage):
+        (WebCore::DisplayList::Recorder::drawImageBuffer):
+        (WebCore::DisplayList::Recorder::drawNativeImage):
+        (WebCore::DisplayList::Recorder::drawPattern):
+        (WebCore::DisplayList::Recorder::save):
+        (WebCore::DisplayList::Recorder::restore):
+        (WebCore::DisplayList::Recorder::translate):
+        (WebCore::DisplayList::Recorder::rotate):
+        (WebCore::DisplayList::Recorder::scale):
+        (WebCore::DisplayList::Recorder::concatCTM):
+        (WebCore::DisplayList::Recorder::setCTM):
+        (WebCore::DisplayList::Recorder::beginTransparencyLayer):
+        (WebCore::DisplayList::Recorder::endTransparencyLayer):
+        (WebCore::DisplayList::Recorder::drawRect):
+        (WebCore::DisplayList::Recorder::drawLine):
+        (WebCore::DisplayList::Recorder::drawLinesForText):
+        (WebCore::DisplayList::Recorder::drawDotsForDocumentMarker):
+        (WebCore::DisplayList::Recorder::drawEllipse):
+        (WebCore::DisplayList::Recorder::drawPath):
+        (WebCore::DisplayList::Recorder::drawFocusRing):
+        (WebCore::DisplayList::Recorder::fillRect):
+        (WebCore::DisplayList::Recorder::fillRoundedRect):
+        (WebCore::DisplayList::Recorder::fillRectWithRoundedHole):
+        (WebCore::DisplayList::Recorder::fillPath):
+        (WebCore::DisplayList::Recorder::fillEllipse):
+        (WebCore::DisplayList::Recorder::strokeRect):
+        (WebCore::DisplayList::Recorder::strokePath):
+        (WebCore::DisplayList::Recorder::strokeEllipse):
+        (WebCore::DisplayList::Recorder::clearRect):
+        (WebCore::DisplayList::Recorder::applyStrokePattern):
+        (WebCore::DisplayList::Recorder::applyFillPattern):
+        (WebCore::DisplayList::Recorder::clip):
+        (WebCore::DisplayList::Recorder::clipOut):
+        (WebCore::DisplayList::Recorder::clipPath):
+        (WebCore::DisplayList::Recorder::clipToDrawingCommands):
+        (WebCore::DisplayList::Recorder::paintFrameForMedia):
+        (WebCore::DisplayList::Recorder::applyDeviceScaleFactor):
+
+        Change these methods that append display list items en masse, such that they go from this:
+
+                `m_displayList.append(Foo::create(arg1, arg2, arg3));`
+
+        ...to this:
+
+                `m_displayList.append<Foo>(arg1, arg2, arg3);`
+
+        (WebCore::DisplayList::Recorder::extentFromLocalBounds const):
+        (WebCore::DisplayList::Recorder::appendItemAndUpdateExtent): Deleted.
+        (WebCore::DisplayList::Recorder::appendItem): Deleted.
+        (WebCore::DisplayList::Recorder::updateItemExtent const): Deleted.
+
+        Extents are now automatically updated (unless otherwise specified) for any drawing items that are appended.
+
+        * platform/graphics/displaylists/DisplayListRecorder.h:
+        (WebCore::DisplayList::Recorder::append):
+        * platform/graphics/displaylists/DisplayListReplayer.cpp:
+        (WebCore::DisplayList::Replayer::replay):
+        * platform/graphics/displaylists/DisplayListReplayer.h:
+        (WebCore::DisplayList::Replayer::Delegate::apply):
+
</ins><span class="cx"> 2020-11-06  Truitt Savell  <tsavell@apple.com>
</span><span class="cx"> 
</span><span class="cx">         Unreviewed, reverting r269486.
</span></span></pre></div>
<a id="trunkSourceWebCoreHeaderscmake"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/Headers.cmake (269524 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/Headers.cmake       2020-11-06 18:44:09 UTC (rev 269524)
+++ trunk/Source/WebCore/Headers.cmake  2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -1253,6 +1253,7 @@
</span><span class="cx">     platform/graphics/displaylists/DisplayListDrawGlyphsRecorder.h
</span><span class="cx">     platform/graphics/displaylists/DisplayListDrawingContext.h
</span><span class="cx">     platform/graphics/displaylists/DisplayListImageBuffer.h
</span><ins>+    platform/graphics/displaylists/DisplayListItemBuffer.h
</ins><span class="cx">     platform/graphics/displaylists/DisplayListItemType.h
</span><span class="cx">     platform/graphics/displaylists/DisplayListItems.h
</span><span class="cx">     platform/graphics/displaylists/DisplayListRecorder.h
</span></span></pre></div>
<a id="trunkSourceWebCoreSourcestxt"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/Sources.txt (269524 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/Sources.txt 2020-11-06 18:44:09 UTC (rev 269524)
+++ trunk/Source/WebCore/Sources.txt    2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -1963,6 +1963,7 @@
</span><span class="cx"> platform/graphics/displaylists/DisplayList.cpp
</span><span class="cx"> platform/graphics/displaylists/DisplayListDrawingContext.cpp
</span><span class="cx"> platform/graphics/displaylists/DisplayListItems.cpp
</span><ins>+platform/graphics/displaylists/DisplayListItemBuffer.cpp
</ins><span class="cx"> platform/graphics/displaylists/DisplayListItemType.cpp
</span><span class="cx"> platform/graphics/displaylists/DisplayListRecorder.cpp
</span><span class="cx"> platform/graphics/displaylists/DisplayListReplayer.cpp
</span></span></pre></div>
<a id="trunkSourceWebCoreWebCorexcodeprojprojectpbxproj"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/WebCore.xcodeproj/project.pbxproj (269524 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/WebCore.xcodeproj/project.pbxproj   2020-11-06 18:44:09 UTC (rev 269524)
+++ trunk/Source/WebCore/WebCore.xcodeproj/project.pbxproj      2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -5202,6 +5202,7 @@
</span><span class="cx">          F4C5F2072479E88200E9B4F5 /* ClipboardImageReader.h in Headers */ = {isa = PBXBuildFile; fileRef = F4C5F2052479E7EE00E9B4F5 /* ClipboardImageReader.h */; };
</span><span class="cx">          F4D07558234D822D00881E73 /* ClipboardItemDataSource.h in Headers */ = {isa = PBXBuildFile; fileRef = F46C447A2346535E0039A79D /* ClipboardItemDataSource.h */; };
</span><span class="cx">          F4D07559234D823300881E73 /* ClipboardItemPasteboardDataSource.h in Headers */ = {isa = PBXBuildFile; fileRef = F46C44802346547A0039A79D /* ClipboardItemPasteboardDataSource.h */; };
</span><ins>+               F4D40BC9255463BF00721349 /* DisplayListItemBuffer.h in Headers */ = {isa = PBXBuildFile; fileRef = F422B8B5253F7065004E77E8 /* DisplayListItemBuffer.h */; settings = {ATTRIBUTES = (Private, ); }; };
</ins><span class="cx">           F4D43D662188038B00ECECAC /* SerializedAttachmentData.h in Headers */ = {isa = PBXBuildFile; fileRef = F4D43D64218802E600ECECAC /* SerializedAttachmentData.h */; settings = {ATTRIBUTES = (Private, ); }; };
</span><span class="cx">          F4E57EDC213F3F5F004EA98E /* FontAttributeChanges.h in Headers */ = {isa = PBXBuildFile; fileRef = F4E57EDA213F3F5F004EA98E /* FontAttributeChanges.h */; settings = {ATTRIBUTES = (Private, ); }; };
</span><span class="cx">          F4E57EE1213F434A004EA98E /* WebCoreNSFontManagerExtras.h in Headers */ = {isa = PBXBuildFile; fileRef = F4E57EDF213F434A004EA98E /* WebCoreNSFontManagerExtras.h */; settings = {ATTRIBUTES = (Private, ); }; };
</span><span class="lines">@@ -16338,6 +16339,8 @@
</span><span class="cx">          F3D461471161D53200CA0D09 /* JSErrorHandler.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = JSErrorHandler.h; sourceTree = "<group>"; };
</span><span class="cx">          F403E7852363B58C00044550 /* EnterKeyHint.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = EnterKeyHint.h; sourceTree = "<group>"; };
</span><span class="cx">          F403E7862363B58C00044550 /* EnterKeyHint.cpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; path = EnterKeyHint.cpp; sourceTree = "<group>"; };
</span><ins>+               F422B8B5253F7065004E77E8 /* DisplayListItemBuffer.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = DisplayListItemBuffer.h; sourceTree = "<group>"; };
+               F422B8B6253F7065004E77E8 /* DisplayListItemBuffer.cpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; path = DisplayListItemBuffer.cpp; sourceTree = "<group>"; };
</ins><span class="cx">           F429261725264D4400007898 /* MediaPlayerIdentifier.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = MediaPlayerIdentifier.h; sourceTree = "<group>"; };
</span><span class="cx">          F42CEB54214031EE002DCA72 /* FontAttributeChangesCocoa.mm */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.objcpp; path = FontAttributeChangesCocoa.mm; sourceTree = "<group>"; };
</span><span class="cx">          F433E9021DBBDBA200EF0D14 /* StaticPasteboard.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = StaticPasteboard.h; sourceTree = "<group>"; };
</span><span class="lines">@@ -17647,6 +17650,8 @@
</span><span class="cx">                          55C0A29523FE2CE000F2CB93 /* DisplayListDrawingContext.cpp */,
</span><span class="cx">                          72EA09F923FCCC6A008504A5 /* DisplayListDrawingContext.h */,
</span><span class="cx">                          72EA09F723FCCB3D008504A5 /* DisplayListImageBuffer.h */,
</span><ins>+                               F422B8B6253F7065004E77E8 /* DisplayListItemBuffer.cpp */,
+                               F422B8B5253F7065004E77E8 /* DisplayListItemBuffer.h */,
</ins><span class="cx">                           0FE5FBCC1C3DD51E0007A2CA /* DisplayListItems.cpp */,
</span><span class="cx">                          0FE5FBCD1C3DD51E0007A2CA /* DisplayListItems.h */,
</span><span class="cx">                          F4377D562551C9C60080ABFE /* DisplayListItemType.cpp */,
</span><span class="lines">@@ -31486,6 +31491,7 @@
</span><span class="cx">                          1CAF56DB25301AC80017B472 /* DisplayListDrawGlyphsRecorder.h in Headers */,
</span><span class="cx">                          55AD09402408964000DE4D2F /* DisplayListDrawingContext.h in Headers */,
</span><span class="cx">                          55AD093E2408963500DE4D2F /* DisplayListImageBuffer.h in Headers */,
</span><ins>+                               F4D40BC9255463BF00721349 /* DisplayListItemBuffer.h in Headers */,
</ins><span class="cx">                           0FE5FBD51C3DD51E0007A2CA /* DisplayListItems.h in Headers */,
</span><span class="cx">                          F4377D572551C9C60080ABFE /* DisplayListItemType.h in Headers */,
</span><span class="cx">                          0FE5FBD71C3DD51E0007A2CA /* DisplayListRecorder.h in Headers */,
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformgraphicsGraphicsContexth"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/graphics/GraphicsContext.h (269524 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/graphics/GraphicsContext.h 2020-11-06 18:44:09 UTC (rev 269524)
+++ trunk/Source/WebCore/platform/graphics/GraphicsContext.h    2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -163,10 +163,10 @@
</span><span class="cx">     WEBCORE_EXPORT ~GraphicsContextState();
</span><span class="cx"> 
</span><span class="cx">     GraphicsContextState(const GraphicsContextState&);
</span><del>-    GraphicsContextState(GraphicsContextState&&);
</del><ins>+    WEBCORE_EXPORT GraphicsContextState(GraphicsContextState&&);
</ins><span class="cx"> 
</span><span class="cx">     GraphicsContextState& operator=(const GraphicsContextState&);
</span><del>-    GraphicsContextState& operator=(GraphicsContextState&&);
</del><ins>+    WEBCORE_EXPORT GraphicsContextState& operator=(GraphicsContextState&&);
</ins><span class="cx"> 
</span><span class="cx">     enum Change : uint32_t {
</span><span class="cx">         StrokeGradientChange                    = 1 << 0,
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformgraphicsdisplaylistsDisplayListcpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/graphics/displaylists/DisplayList.cpp (269524 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/graphics/displaylists/DisplayList.cpp      2020-11-06 18:44:09 UTC (rev 269524)
+++ trunk/Source/WebCore/platform/graphics/displaylists/DisplayList.cpp 2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -26,8 +26,10 @@
</span><span class="cx"> #include "config.h"
</span><span class="cx"> #include "DisplayList.h"
</span><span class="cx"> 
</span><ins>+#include "DisplayListItemBuffer.h"
</ins><span class="cx"> #include "DisplayListItems.h"
</span><span class="cx"> #include "Logging.h"
</span><ins>+#include <wtf/FastMalloc.h>
</ins><span class="cx"> #include <wtf/StdLibExtras.h>
</span><span class="cx"> #include <wtf/text/TextStream.h>
</span><span class="cx"> 
</span><span class="lines">@@ -48,18 +50,43 @@
</span><span class="cx"> }
</span><span class="cx"> #endif
</span><span class="cx"> 
</span><ins>+DisplayList::DisplayList(DisplayList&& other)
+    : m_imageBuffers(std::exchange(other.m_imageBuffers, { }))
+    , m_items(std::exchange(other.m_items, nullptr))
+    , m_drawingItemExtents(std::exchange(other.m_drawingItemExtents, { }))
+{
+}
+
+DisplayList::DisplayList(ItemBufferHandles&& handles)
+    : m_items(makeUnique<ItemBuffer>(WTFMove(handles)))
+{
+}
+
+DisplayList::DisplayList() = default;
+DisplayList::~DisplayList() = default;
+
+DisplayList& DisplayList::operator=(DisplayList&& other)
+{
+    m_imageBuffers = std::exchange(other.m_imageBuffers, { });
+    m_items = std::exchange(other.m_items, nullptr);
+    m_drawingItemExtents = std::exchange(other.m_drawingItemExtents, { });
+    return *this;
+}
+
</ins><span class="cx"> void DisplayList::clear()
</span><span class="cx"> {
</span><del>-    m_list.clear();
</del><ins>+    if (m_items)
+        m_items->clear();
+    m_drawingItemExtents.clear();
</ins><span class="cx">     m_imageBuffers.clear();
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-bool DisplayList::shouldDumpForFlags(AsTextFlags flags, const Item& item)
</del><ins>+bool DisplayList::shouldDumpForFlags(AsTextFlags flags, ItemHandle item)
</ins><span class="cx"> {
</span><span class="cx">     switch (item.type()) {
</span><span class="cx">     case ItemType::SetState:
</span><span class="cx">         if (!(flags & AsTextFlag::IncludesPlatformOperations)) {
</span><del>-            const auto& stateItem = downcast<SetState>(item);
</del><ins>+            const auto& stateItem = item.get<SetState>();
</ins><span class="cx">             // FIXME: for now, only drop the item if the only state-change flags are platform-specific.
</span><span class="cx">             if (stateItem.state().m_changeFlags == GraphicsContextState::ShouldSubpixelQuantizeFontsChange)
</span><span class="cx">                 return false;
</span><span class="lines">@@ -84,10 +111,14 @@
</span><span class="cx"> String DisplayList::asText(AsTextFlags flags) const
</span><span class="cx"> {
</span><span class="cx">     TextStream stream(TextStream::LineMode::MultipleLine, TextStream::Formatting::SVGStyleRect);
</span><del>-    for (auto& item : m_list) {
</del><ins>+    for (auto [item, extent] : *this) {
</ins><span class="cx">         if (!shouldDumpForFlags(flags, item))
</span><span class="cx">             continue;
</span><ins>+
+        TextStream::GroupScope group(stream);
</ins><span class="cx">         stream << item;
</span><ins>+        if (item.isDrawingItem())
+            stream << " extent " << extent;
</ins><span class="cx">     }
</span><span class="cx">     return stream.release();
</span><span class="cx"> }
</span><span class="lines">@@ -97,10 +128,11 @@
</span><span class="cx">     TextStream::GroupScope group(ts);
</span><span class="cx">     ts << "display list";
</span><span class="cx"> 
</span><del>-    size_t numItems = m_list.size();
-    for (size_t i = 0; i < numItems; ++i) {
-        TextStream::GroupScope scope(ts);
-        ts << i << " " << m_list[i].get();
</del><ins>+    for (auto [item, extent] : *this) {
+        TextStream::GroupScope group(ts);
+        ts << item;
+        if (item.isDrawingItem())
+            ts << " extent " << extent;
</ins><span class="cx">     }
</span><span class="cx">     ts.startGroup();
</span><span class="cx">     ts << "size in bytes: " << sizeInBytes();
</span><span class="lines">@@ -109,13 +141,275 @@
</span><span class="cx"> 
</span><span class="cx"> size_t DisplayList::sizeInBytes() const
</span><span class="cx"> {
</span><del>-    size_t result = 0;
-    for (auto& ref : m_list)
-        result += Item::sizeInBytes(ref);
</del><ins>+    return m_items ? m_items->sizeInBytes() : 0;
+}
</ins><span class="cx"> 
</span><del>-    return result;
</del><ins>+bool DisplayList::isEmpty() const
+{
+    return !m_items || m_items->isEmpty();
</ins><span class="cx"> }
</span><span class="cx"> 
</span><ins>+ItemBuffer& DisplayList::itemBuffer()
+{
+    if (!m_items)
+        m_items = makeUnique<ItemBuffer>();
+    return *m_items;
+}
+
+void DisplayList::setItemBufferClient(ItemBufferReadingClient* client)
+{
+    itemBuffer().setClient(client);
+}
+
+void DisplayList::setItemBufferClient(ItemBufferWritingClient* client)
+{
+    itemBuffer().setClient(client);
+}
+
+void DisplayList::forEachItemBuffer(Function<void(const ItemBufferHandle&)>&& mapFunction) const
+{
+    if (m_items)
+        m_items->forEachItemBuffer(WTFMove(mapFunction));
+}
+
+void DisplayList::setTracksDrawingItemExtents(bool value)
+{
+    RELEASE_ASSERT(!m_items || m_items->isEmpty());
+    m_tracksDrawingItemExtents = value;
+}
+
+void DisplayList::append(ItemHandle item)
+{
+    switch (item.type()) {
+    case ItemType::Save:
+        return append<Save>(item.get<Save>());
+    case ItemType::Restore:
+        return append<Restore>(item.get<Restore>());
+    case ItemType::Translate:
+        return append<Translate>(item.get<Translate>());
+    case ItemType::Rotate:
+        return append<Rotate>(item.get<Rotate>());
+    case ItemType::Scale:
+        return append<Scale>(item.get<Scale>());
+    case ItemType::ConcatenateCTM:
+        return append<ConcatenateCTM>(item.get<ConcatenateCTM>());
+    case ItemType::SetCTM:
+        return append<SetCTM>(item.get<SetCTM>());
+    case ItemType::SetInlineFillGradient:
+        return append<SetInlineFillGradient>(item.get<SetInlineFillGradient>());
+    case ItemType::SetInlineFillColor:
+        return append<SetInlineFillColor>(item.get<SetInlineFillColor>());
+    case ItemType::SetInlineStrokeColor:
+        return append<SetInlineStrokeColor>(item.get<SetInlineStrokeColor>());
+    case ItemType::SetStrokeThickness:
+        return append<SetStrokeThickness>(item.get<SetStrokeThickness>());
+    case ItemType::SetState:
+        return append<SetState>(item.get<SetState>());
+    case ItemType::SetLineCap:
+        return append<SetLineCap>(item.get<SetLineCap>());
+    case ItemType::SetLineDash:
+        return append<SetLineDash>(item.get<SetLineDash>());
+    case ItemType::SetLineJoin:
+        return append<SetLineJoin>(item.get<SetLineJoin>());
+    case ItemType::SetMiterLimit:
+        return append<SetMiterLimit>(item.get<SetMiterLimit>());
+    case ItemType::ClearShadow:
+        return append<ClearShadow>(item.get<ClearShadow>());
+    case ItemType::Clip:
+        return append<Clip>(item.get<Clip>());
+    case ItemType::ClipOut:
+        return append<ClipOut>(item.get<ClipOut>());
+    case ItemType::ClipOutToPath:
+        return append<ClipOutToPath>(item.get<ClipOutToPath>());
+    case ItemType::ClipPath:
+        return append<ClipPath>(item.get<ClipPath>());
+    case ItemType::ClipToDrawingCommands: {
+        ASSERT_NOT_REACHED();
+        return; // FIXME: Support the ability to clone display lists (this is currently only used for display list tracking).
+    }
+    case ItemType::DrawGlyphs:
+        return append<DrawGlyphs>(item.get<DrawGlyphs>());
+    case ItemType::DrawImage:
+        return append<DrawImage>(item.get<DrawImage>());
+    case ItemType::DrawTiledImage:
+        return append<DrawTiledImage>(item.get<DrawTiledImage>());
+    case ItemType::DrawTiledScaledImage:
+        return append<DrawTiledScaledImage>(item.get<DrawTiledScaledImage>());
+    case ItemType::DrawImageBuffer:
+        return append<DrawImageBuffer>(item.get<DrawImageBuffer>());
+    case ItemType::DrawNativeImage:
+        return append<DrawNativeImage>(item.get<DrawNativeImage>());
+    case ItemType::DrawPattern:
+        return append<DrawPattern>(item.get<DrawPattern>());
+    case ItemType::DrawRect:
+        return append<DrawRect>(item.get<DrawRect>());
+    case ItemType::DrawLine:
+        return append<DrawLine>(item.get<DrawLine>());
+    case ItemType::DrawLinesForText:
+        return append<DrawLinesForText>(item.get<DrawLinesForText>());
+    case ItemType::DrawDotsForDocumentMarker:
+        return append<DrawDotsForDocumentMarker>(item.get<DrawDotsForDocumentMarker>());
+    case ItemType::DrawEllipse:
+        return append<DrawEllipse>(item.get<DrawEllipse>());
+    case ItemType::DrawPath:
+        return append<DrawPath>(item.get<DrawPath>());
+    case ItemType::DrawFocusRingPath:
+        return append<DrawFocusRingPath>(item.get<DrawFocusRingPath>());
+    case ItemType::DrawFocusRingRects:
+        return append<DrawFocusRingRects>(item.get<DrawFocusRingRects>());
+    case ItemType::FillRect:
+        return append<FillRect>(item.get<FillRect>());
+    case ItemType::FillRectWithColor:
+        return append<FillRectWithColor>(item.get<FillRectWithColor>());
+    case ItemType::FillRectWithGradient:
+        return append<FillRectWithGradient>(item.get<FillRectWithGradient>());
+    case ItemType::FillCompositedRect:
+        return append<FillCompositedRect>(item.get<FillCompositedRect>());
+    case ItemType::FillRoundedRect:
+        return append<FillRoundedRect>(item.get<FillRoundedRect>());
+    case ItemType::FillRectWithRoundedHole:
+        return append<FillRectWithRoundedHole>(item.get<FillRectWithRoundedHole>());
+#if ENABLE(INLINE_PATH_DATA)
+    case ItemType::FillInlinePath:
+        return append<FillInlinePath>(item.get<FillInlinePath>());
+#endif
+    case ItemType::FillPath:
+        return append<FillPath>(item.get<FillPath>());
+    case ItemType::FillEllipse:
+        return append<FillEllipse>(item.get<FillEllipse>());
+    case ItemType::PutImageData:
+        return append<PutImageData>(item.get<PutImageData>());
+    case ItemType::PaintFrameForMedia:
+        return append<PaintFrameForMedia>(item.get<PaintFrameForMedia>());
+    case ItemType::StrokeRect:
+        return append<StrokeRect>(item.get<StrokeRect>());
+#if ENABLE(INLINE_PATH_DATA)
+    case ItemType::StrokeInlinePath:
+        return append<StrokeInlinePath>(item.get<StrokeInlinePath>());
+#endif
+    case ItemType::StrokePath:
+        return append<StrokePath>(item.get<StrokePath>());
+    case ItemType::StrokeEllipse:
+        return append<StrokeEllipse>(item.get<StrokeEllipse>());
+    case ItemType::ClearRect:
+        return append<ClearRect>(item.get<ClearRect>());
+    case ItemType::BeginTransparencyLayer:
+        return append<BeginTransparencyLayer>(item.get<BeginTransparencyLayer>());
+    case ItemType::EndTransparencyLayer:
+        return append<EndTransparencyLayer>(item.get<EndTransparencyLayer>());
+#if USE(CG)
+    case ItemType::ApplyStrokePattern:
+        return append<ApplyStrokePattern>(item.get<ApplyStrokePattern>());
+    case ItemType::ApplyFillPattern:
+        return append<ApplyFillPattern>(item.get<ApplyFillPattern>());
+#endif
+    case ItemType::ApplyDeviceScaleFactor:
+        return append<ApplyDeviceScaleFactor>(item.get<ApplyDeviceScaleFactor>());
+    }
+}
+
+bool DisplayList::iterator::atEnd() const
+{
+    if (m_displayList.isEmpty())
+        return true;
+
+    auto& items = *m_displayList.m_items;
+    auto endCursor = items.m_writableBuffer.data + items.m_writtenNumberOfBytes;
+    return m_cursor == endCursor;
+}
+
+void DisplayList::iterator::updateCurrentItem()
+{
+    clearCurrentItem();
+
+    if (atEnd())
+        return;
+
+    auto& items = *m_displayList.m_items;
+    auto itemType = static_cast<ItemType>(m_cursor[0]);
+    if (isDrawingItem(itemType) && !m_displayList.m_drawingItemExtents.isEmpty()) {
+        m_currentExtent = m_displayList.m_drawingItemExtents[m_drawingItemIndex];
+        m_drawingItemIndex++;
+    } else
+        m_currentExtent = WTF::nullopt;
+
+    auto* client = items.m_readingClient;
+    auto sizeOfTypeAndItem = sizeOfItemInBytes(itemType) + sizeof(ItemType);
+    m_currentBufferForItem = sizeOfTypeAndItem <= sizeOfFixedBufferForCurrentItem ? m_fixedBufferForCurrentItem : reinterpret_cast<uint8_t*>(fastMalloc(sizeOfTypeAndItem));
+    if (!isInlineItem(itemType) && client) {
+        auto sizeOfData = reinterpret_cast<size_t*>(m_cursor + sizeof(ItemType))[0];
+        auto* startOfPadding = m_cursor + sizeof(ItemType) + sizeof(size_t);
+        size_t padding = (alignof(uint64_t) - reinterpret_cast<uintptr_t>(startOfPadding) % alignof(uint64_t)) % alignof(uint64_t);
+        auto decodedItemHandle = client->decodeItem(startOfPadding + padding, sizeOfData, itemType, m_currentBufferForItem);
+        if (!decodedItemHandle) {
+            // FIXME: Instead of crashing, this needs to fail gracefully and inform the caller.
+            // For the time being, this assertion makes bugs in item buffer encoding logic easier
+            // to catch by avoiding mysterious out-of-bounds reads and incorrectly aligned items
+            // down the line.
+            RELEASE_ASSERT_NOT_REACHED();
+        }
+        m_currentBufferForItem[0] = static_cast<uint8_t>(itemType);
+        m_currentItemSizeInBuffer = sizeof(ItemType) + sizeof(size_t) + padding + sizeOfData;
+    } else {
+        ItemHandle { m_cursor }.copyTo({ m_currentBufferForItem });
+        m_currentItemSizeInBuffer = sizeOfTypeAndItem;
+    }
+}
+
+void DisplayList::iterator::advance()
+{
+    if (atEnd())
+        return;
+
+    m_cursor += m_currentItemSizeInBuffer;
+
+    if (m_cursor == m_currentEndOfBuffer && m_readOnlyBufferIndex < m_displayList.m_items->m_readOnlyBuffers.size()) {
+        m_readOnlyBufferIndex++;
+        moveCursorToStartOfCurrentBuffer();
+    }
+
+    updateCurrentItem();
+}
+
+void DisplayList::iterator::clearCurrentItem()
+{
+    if (m_currentBufferForItem) {
+        ItemHandle { m_currentBufferForItem }.destroy();
+        if (UNLIKELY(m_currentBufferForItem != m_fixedBufferForCurrentItem))
+            fastFree(m_currentBufferForItem);
+    }
+
+    m_currentItemSizeInBuffer = 0;
+    m_currentBufferForItem = nullptr;
+}
+
+void DisplayList::iterator::moveToEnd()
+{
+    if (auto& items = m_displayList.m_items) {
+        m_cursor = items->m_writableBuffer.data + items->m_writtenNumberOfBytes;
+        m_currentEndOfBuffer = m_cursor;
+        m_readOnlyBufferIndex = items->m_readOnlyBuffers.size();
+    }
+}
+
+void DisplayList::iterator::moveCursorToStartOfCurrentBuffer()
+{
+    auto& items = m_displayList.m_items;
+    if (!items)
+        return;
+
+    auto numberOfReadOnlyBuffers = items->m_readOnlyBuffers.size();
+    if (m_readOnlyBufferIndex < numberOfReadOnlyBuffers) {
+        auto& nextBufferHandle = items->m_readOnlyBuffers[m_readOnlyBufferIndex];
+        m_cursor = nextBufferHandle.data;
+        m_currentEndOfBuffer = m_cursor + nextBufferHandle.capacity;
+    } else if (m_readOnlyBufferIndex == numberOfReadOnlyBuffers) {
+        m_cursor = items->m_writableBuffer.data;
+        m_currentEndOfBuffer = m_cursor + items->m_writtenNumberOfBytes;
+    }
+}
+
+
</ins><span class="cx"> } // namespace DisplayList
</span><span class="cx"> 
</span><span class="cx"> TextStream& operator<<(TextStream& ts, const DisplayList::DisplayList& displayList)
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformgraphicsdisplaylistsDisplayListh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/graphics/displaylists/DisplayList.h (269524 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/graphics/displaylists/DisplayList.h        2020-11-06 18:44:09 UTC (rev 269524)
+++ trunk/Source/WebCore/platform/graphics/displaylists/DisplayList.h   2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -25,6 +25,7 @@
</span><span class="cx"> 
</span><span class="cx"> #pragma once
</span><span class="cx"> 
</span><ins>+#include "DisplayListItemBuffer.h"
</ins><span class="cx"> #include "DisplayListItemType.h"
</span><span class="cx"> #include "FloatRect.h"
</span><span class="cx"> #include "GraphicsContext.h"
</span><span class="lines">@@ -32,6 +33,8 @@
</span><span class="cx"> #include <wtf/FastMalloc.h>
</span><span class="cx"> #include <wtf/HashSet.h>
</span><span class="cx"> #include <wtf/Noncopyable.h>
</span><ins>+#include <wtf/ObjectIdentifier.h>
+#include <wtf/Vector.h>
</ins><span class="cx"> #include <wtf/text/WTFString.h>
</span><span class="cx"> 
</span><span class="cx"> namespace WTF {
</span><span class="lines">@@ -42,34 +45,6 @@
</span><span class="cx"> 
</span><span class="cx"> namespace DisplayList {
</span><span class="cx"> 
</span><del>-class Item : public RefCounted<Item> {
-public:
-    Item() = delete;
-
-    WEBCORE_EXPORT Item(ItemType);
-    WEBCORE_EXPORT virtual ~Item();
-
-    ItemType type() const
-    {
-        return m_type;
-    }
-
-    virtual void apply(GraphicsContext&) const = 0;
-
-    virtual bool isDrawingItem() const { return false; }
-
-#if !defined(NDEBUG) || !LOG_DISABLED
-    WTF::CString description() const;
-#endif
-    static size_t sizeInBytes(const Item&);
-
-    template<class Encoder> void encode(Encoder&) const;
-    template<class Decoder> static Optional<Ref<Item>> decode(Decoder&);
-
-private:
-    ItemType m_type;
-};
-
</del><span class="cx"> enum AsTextFlag {
</span><span class="cx">     None                            = 0,
</span><span class="cx">     IncludesPlatformOperations      = 1 << 0,
</span><span class="lines">@@ -82,48 +57,97 @@
</span><span class="cx">     friend class Recorder;
</span><span class="cx">     friend class Replayer;
</span><span class="cx"> public:
</span><del>-    DisplayList() = default;
-    DisplayList(DisplayList&&) = default;
</del><ins>+    WEBCORE_EXPORT DisplayList();
+    WEBCORE_EXPORT DisplayList(DisplayList&&);
+    WEBCORE_EXPORT DisplayList(ItemBufferHandles&&);
</ins><span class="cx"> 
</span><del>-    DisplayList& operator=(DisplayList&&) = default;
</del><ins>+    WEBCORE_EXPORT ~DisplayList();
</ins><span class="cx"> 
</span><ins>+    WEBCORE_EXPORT DisplayList& operator=(DisplayList&&);
+
</ins><span class="cx">     void dump(WTF::TextStream&) const;
</span><span class="cx"> 
</span><del>-    const Vector<Ref<Item>>& list() const { return m_list; }
-    Item& itemAt(size_t index)
-    {
-        ASSERT(index < m_list.size());
-        return m_list[index].get();
-    }
-
</del><span class="cx">     WEBCORE_EXPORT void clear();
</span><ins>+    WEBCORE_EXPORT bool isEmpty() const;
+    WEBCORE_EXPORT size_t sizeInBytes() const;
</ins><span class="cx"> 
</span><del>-    bool isEmpty() const { return m_list.isEmpty(); }
-    size_t sizeInBytes() const;
-    
</del><span class="cx">     String asText(AsTextFlags) const;
</span><span class="cx"> 
</span><span class="cx">     const ImageBufferHashMap& imageBuffers() const { return m_imageBuffers; }
</span><span class="cx"> 
</span><ins>+    WEBCORE_EXPORT void setItemBufferClient(ItemBufferReadingClient*);
+    WEBCORE_EXPORT void setItemBufferClient(ItemBufferWritingClient*);
+
</ins><span class="cx"> #if !defined(NDEBUG) || !LOG_DISABLED
</span><span class="cx">     WTF::CString description() const;
</span><span class="cx">     WEBCORE_EXPORT void dump() const;
</span><span class="cx"> #endif
</span><span class="cx"> 
</span><del>-    template<class Encoder> void encode(Encoder&) const;
-    template<class Decoder> static Optional<DisplayList> decode(Decoder&);
</del><ins>+    WEBCORE_EXPORT void forEachItemBuffer(Function<void(const ItemBufferHandle&)>&&) const;
</ins><span class="cx"> 
</span><ins>+    template<typename T, class... Args> void append(Args&&... args);
+    void append(ItemHandle);
+
+    bool tracksDrawingItemExtents() const { return m_tracksDrawingItemExtents; }
+    WEBCORE_EXPORT void setTracksDrawingItemExtents(bool);
+
+    class iterator {
+    public:
+        enum class ImmediatelyMoveToEnd { No, Yes };
+        iterator(const DisplayList& displayList, ImmediatelyMoveToEnd immediatelyMoveToEnd = ImmediatelyMoveToEnd::No)
+            : m_displayList(displayList)
+        {
+            if (immediatelyMoveToEnd == ImmediatelyMoveToEnd::Yes)
+                moveToEnd();
+            else {
+                moveCursorToStartOfCurrentBuffer();
+                updateCurrentItem();
+            }
+        }
+
+        ~iterator()
+        {
+            clearCurrentItem();
+        }
+
+        bool operator==(const iterator& other) { return &m_displayList == &other.m_displayList && m_cursor == other.m_cursor; }
+        bool operator!=(const iterator& other) { return !(*this == other); }
+        void operator++() { advance(); }
+        std::pair<ItemHandle, Optional<FloatRect>> operator*() const { return { ItemHandle { m_currentBufferForItem }, m_currentExtent }; }
+
+    private:
+        static constexpr size_t sizeOfFixedBufferForCurrentItem = 256;
+
+        WEBCORE_EXPORT void moveCursorToStartOfCurrentBuffer();
+        WEBCORE_EXPORT void moveToEnd();
+        WEBCORE_EXPORT void clearCurrentItem();
+        WEBCORE_EXPORT void updateCurrentItem();
+        WEBCORE_EXPORT void advance();
+        bool atEnd() const;
+
+        const DisplayList& m_displayList;
+        uint8_t* m_cursor { nullptr };
+        size_t m_readOnlyBufferIndex { 0 };
+        size_t m_drawingItemIndex { 0 };
+        uint8_t* m_currentEndOfBuffer { nullptr };
+
+        uint8_t m_fixedBufferForCurrentItem[sizeOfFixedBufferForCurrentItem] { 0 };
+        uint8_t* m_currentBufferForItem { nullptr };
+        Optional<FloatRect> m_currentExtent;
+        size_t m_currentItemSizeInBuffer { 0 };
+    };
+
+    iterator begin() const { return { *this }; }
+    iterator end() const { return { *this, iterator::ImmediatelyMoveToEnd::Yes }; }
+
</ins><span class="cx"> private:
</span><del>-    Item& append(Ref<Item>&& item)
-    {
-        m_list.append(WTFMove(item));
-        return m_list.last().get();
-    }
</del><ins>+    ItemBuffer* itemBufferIfExists() const { return m_items.get(); }
+    WEBCORE_EXPORT ItemBuffer& itemBuffer();
</ins><span class="cx"> 
</span><del>-    // Less efficient append, only used for tracking replay.
-    void appendItem(Item& item)
</del><ins>+    void addDrawingItemExtent(Optional<FloatRect>&& extent)
</ins><span class="cx">     {
</span><del>-        m_list.append(item);
</del><ins>+        ASSERT(m_tracksDrawingItemExtents);
+        m_drawingItemExtents.append(WTFMove(extent));
</ins><span class="cx">     }
</span><span class="cx"> 
</span><span class="cx">     void cacheImageBuffer(Ref<WebCore::ImageBuffer>&& imageBuffer)
</span><span class="lines">@@ -131,46 +155,20 @@
</span><span class="cx">         m_imageBuffers.add(imageBuffer->renderingResourceIdentifier(), WTFMove(imageBuffer));
</span><span class="cx">     }
</span><span class="cx"> 
</span><del>-    static bool shouldDumpForFlags(AsTextFlags, const Item&);
</del><ins>+    static bool shouldDumpForFlags(AsTextFlags, ItemHandle);
</ins><span class="cx"> 
</span><del>-    Vector<Ref<Item>>& list() { return m_list; }
-
-    Vector<Ref<Item>> m_list;
</del><span class="cx">     ImageBufferHashMap m_imageBuffers;
</span><ins>+    std::unique_ptr<ItemBuffer> m_items;
+    Vector<Optional<FloatRect>> m_drawingItemExtents;
+    bool m_tracksDrawingItemExtents { true };
</ins><span class="cx"> };
</span><span class="cx"> 
</span><del>-
-template<class Encoder>
-void DisplayList::encode(Encoder& encoder) const
</del><ins>+template<typename T, class... Args>
+void DisplayList::append(Args&&... args)
</ins><span class="cx"> {
</span><del>-    encoder << static_cast<uint64_t>(m_list.size());
-
-    for (auto& item : m_list)
-        encoder << item.get();
</del><ins>+    itemBuffer().append<T>(std::forward<Args>(args)...);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><del>-template<class Decoder>
-Optional<DisplayList> DisplayList::decode(Decoder& decoder)
-{
-    Optional<uint64_t> itemCount;
-    decoder >> itemCount;
-    if (!itemCount)
-        return WTF::nullopt;
-
-    DisplayList displayList;
-
-    for (uint64_t i = 0; i < *itemCount; i++) {
-        auto item = Item::decode(decoder);
-        // FIXME: Once we can decode all types, failing to decode an item should turn into a decode failure.
-        // For now, we just have to ignore it.
-        if (!item)
-            continue;
-        displayList.append(WTFMove(*item));
-    }
-
-    return displayList;
-}
-
</del><span class="cx"> } // DisplayList
</span><span class="cx"> 
</span><span class="cx"> WTF::TextStream& operator<<(WTF::TextStream&, const DisplayList::DisplayList&);
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformgraphicsdisplaylistsDisplayListDrawGlyphsRecorderCoreTextcpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/graphics/displaylists/DisplayListDrawGlyphsRecorderCoreText.cpp (269524 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/graphics/displaylists/DisplayListDrawGlyphsRecorderCoreText.cpp    2020-11-06 18:44:09 UTC (rev 269524)
+++ trunk/Source/WebCore/platform/graphics/displaylists/DisplayListDrawGlyphsRecorderCoreText.cpp       2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -334,7 +334,7 @@
</span><span class="cx">     updateStrokeColor(CGGStateGetStrokeColor(gstate));
</span><span class="cx">     updateShadow(CGGStateGetStyle(gstate));
</span><span class="cx"> 
</span><del>-    m_owner.appendItemAndUpdateExtent(DrawGlyphs::create(*m_originalFont, glyphs, computeAdvancesFromPositions(positions, count, currentTextMatrix).data(), count, currentTextMatrix.mapPoint(positions[0]), m_smoothingMode));
</del><ins>+    m_owner.append<DrawGlyphs>(*m_originalFont, glyphs, computeAdvancesFromPositions(positions, count, currentTextMatrix).data(), count, currentTextMatrix.mapPoint(positions[0]), m_smoothingMode);
</ins><span class="cx"> 
</span><span class="cx">     m_owner.concatCTM(inverseCTMFixup);
</span><span class="cx"> }
</span><span class="lines">@@ -353,7 +353,7 @@
</span><span class="cx">     m_owner.scale(FloatSize(1, -1));
</span><span class="cx"> 
</span><span class="cx">     auto image = BitmapImage::create(cgImage);
</span><del>-    m_owner.appendItemAndUpdateExtent(DrawImage::create(image, rect, {{ }, image->size()}, { ImageOrientation::OriginTopLeft }));
</del><ins>+    m_owner.append<DrawImage>(image, FloatRect(rect), FloatRect {{ }, image->size()}, ImagePaintingOptions { ImageOrientation::OriginTopLeft });
</ins><span class="cx"> 
</span><span class="cx">     // Undo the above y-flip to restore the context.
</span><span class="cx">     m_owner.scale(FloatSize(1, -1));
</span><span class="lines">@@ -363,7 +363,7 @@
</span><span class="cx"> void DrawGlyphsRecorder::drawGlyphs(const Font& font, const GlyphBuffer& glyphBuffer, unsigned from, unsigned numGlyphs, const FloatPoint& startPoint, FontSmoothingMode smoothingMode)
</span><span class="cx"> {
</span><span class="cx">     if (m_drawGlyphsDeconstruction == DrawGlyphsDeconstruction::DontDeconstruct) {
</span><del>-        m_owner.appendItemAndUpdateExtent(DrawGlyphs::create(font, glyphBuffer.glyphs(from), glyphBuffer.advances(from), numGlyphs, startPoint, smoothingMode));
</del><ins>+        m_owner.append<DrawGlyphs>(font, glyphBuffer.glyphs(from), glyphBuffer.advances(from), numGlyphs, startPoint, smoothingMode);
</ins><span class="cx">         return;
</span><span class="cx">     }
</span><span class="cx"> 
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformgraphicsdisplaylistsDisplayListDrawGlyphsRecorderHarfBuzzcpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/graphics/displaylists/DisplayListDrawGlyphsRecorderHarfBuzz.cpp (269524 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/graphics/displaylists/DisplayListDrawGlyphsRecorderHarfBuzz.cpp    2020-11-06 18:44:09 UTC (rev 269524)
+++ trunk/Source/WebCore/platform/graphics/displaylists/DisplayListDrawGlyphsRecorderHarfBuzz.cpp       2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -43,7 +43,7 @@
</span><span class="cx"> 
</span><span class="cx"> void DrawGlyphsRecorder::drawGlyphs(const Font& font, const GlyphBuffer& glyphBuffer, unsigned from, unsigned numGlyphs, const FloatPoint& startPoint, FontSmoothingMode smoothingMode)
</span><span class="cx"> {
</span><del>-    m_owner.appendItemAndUpdateExtent(DrawGlyphs::create(font, glyphBuffer.glyphs(from), glyphBuffer.advances(from), numGlyphs, startPoint, smoothingMode));
</del><ins>+    m_owner.append<DrawGlyphs>(font, glyphBuffer.glyphs(from), glyphBuffer.advances(from), numGlyphs, startPoint, smoothingMode);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> } // namespace DisplayList
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformgraphicsdisplaylistsDisplayListDrawGlyphsRecorderWincpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/graphics/displaylists/DisplayListDrawGlyphsRecorderWin.cpp (269524 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/graphics/displaylists/DisplayListDrawGlyphsRecorderWin.cpp 2020-11-06 18:44:09 UTC (rev 269524)
+++ trunk/Source/WebCore/platform/graphics/displaylists/DisplayListDrawGlyphsRecorderWin.cpp    2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -43,7 +43,7 @@
</span><span class="cx"> 
</span><span class="cx"> void DrawGlyphsRecorder::drawGlyphs(const Font& font, const GlyphBuffer& glyphBuffer, unsigned from, unsigned numGlyphs, const FloatPoint& startPoint, FontSmoothingMode smoothingMode)
</span><span class="cx"> {
</span><del>-    m_owner.appendItemAndUpdateExtent(DrawGlyphs::create(font, glyphBuffer.glyphs(from), glyphBuffer.advances(from), numGlyphs, startPoint, smoothingMode));
</del><ins>+    m_owner.append<DrawGlyphs>(font, glyphBuffer.glyphs(from), glyphBuffer.advances(from), numGlyphs, startPoint, smoothingMode);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> } // namespace DisplayList
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformgraphicsdisplaylistsDisplayListDrawingContexth"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/graphics/displaylists/DisplayListDrawingContext.h (269524 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/graphics/displaylists/DisplayListDrawingContext.h  2020-11-06 18:44:09 UTC (rev 269524)
+++ trunk/Source/WebCore/platform/graphics/displaylists/DisplayListDrawingContext.h     2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -39,7 +39,7 @@
</span><span class="cx"> 
</span><span class="cx">     GraphicsContext& context() const { return const_cast<DrawingContext&>(*this).m_context; }
</span><span class="cx">     WEBCORE_EXPORT Recorder& recorder();
</span><del>-    DisplayList takeDisplayList() { return WTFMove(m_displayList); }
</del><ins>+    DisplayList takeDisplayList() { return std::exchange(m_displayList, { }); }
</ins><span class="cx">     DisplayList& displayList() { return m_displayList; }
</span><span class="cx">     const DisplayList& displayList() const { return m_displayList; }
</span><span class="cx">     const DisplayList* replayedDisplayList() const { return m_replayedDisplayList.get(); }
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformgraphicsdisplaylistsDisplayListItemBuffercpp"></a>
<div class="addfile"><h4>Added: trunk/Source/WebCore/platform/graphics/displaylists/DisplayListItemBuffer.cpp (0 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/graphics/displaylists/DisplayListItemBuffer.cpp                            (rev 0)
+++ trunk/Source/WebCore/platform/graphics/displaylists/DisplayListItemBuffer.cpp       2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -0,0 +1,878 @@
</span><ins>+/*
+ * Copyright (C) 2020 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include "config.h"
+#include "DisplayListItemBuffer.h"
+
+#include "DisplayListItems.h"
+#include <wtf/FastMalloc.h>
+
+namespace WebCore {
+namespace DisplayList {
+
+#if !defined(NDEBUG) || !LOG_DISABLED
+CString ItemHandle::description() const
+{
+    TextStream ts;
+    ts << *this;
+    return ts.release().utf8();
+}
+#endif
+
+void ItemHandle::apply(GraphicsContext& context)
+{
+    switch (type()) {
+    case ItemType::Save: {
+        get<Save>().apply(context);
+        return;
+    }
+    case ItemType::Restore: {
+        get<Restore>().apply(context);
+        return;
+    }
+    case ItemType::Translate: {
+        get<Translate>().apply(context);
+        return;
+    }
+    case ItemType::Rotate: {
+        get<Rotate>().apply(context);
+        return;
+    }
+    case ItemType::Scale: {
+        get<Scale>().apply(context);
+        return;
+    }
+    case ItemType::ConcatenateCTM: {
+        get<ConcatenateCTM>().apply(context);
+        return;
+    }
+    case ItemType::SetCTM: {
+        get<SetCTM>().apply(context);
+        return;
+    }
+    case ItemType::SetInlineFillGradient: {
+        get<SetInlineFillGradient>().apply(context);
+        return;
+    }
+    case ItemType::SetInlineFillColor: {
+        get<SetInlineFillColor>().apply(context);
+        return;
+    }
+    case ItemType::SetInlineStrokeColor: {
+        get<SetInlineStrokeColor>().apply(context);
+        return;
+    }
+    case ItemType::SetStrokeThickness: {
+        get<SetStrokeThickness>().apply(context);
+        return;
+    }
+    case ItemType::SetState: {
+        get<SetState>().apply(context);
+        return;
+    }
+    case ItemType::SetLineCap: {
+        get<SetLineCap>().apply(context);
+        return;
+    }
+    case ItemType::SetLineDash: {
+        get<SetLineDash>().apply(context);
+        return;
+    }
+    case ItemType::SetLineJoin: {
+        get<SetLineJoin>().apply(context);
+        return;
+    }
+    case ItemType::SetMiterLimit: {
+        get<SetMiterLimit>().apply(context);
+        return;
+    }
+    case ItemType::ClearShadow: {
+        get<ClearShadow>().apply(context);
+        return;
+    }
+    case ItemType::Clip: {
+        get<Clip>().apply(context);
+        return;
+    }
+    case ItemType::ClipOut: {
+        get<ClipOut>().apply(context);
+        return;
+    }
+    case ItemType::ClipOutToPath: {
+        get<ClipOutToPath>().apply(context);
+        return;
+    }
+    case ItemType::ClipPath: {
+        get<ClipPath>().apply(context);
+        return;
+    }
+    case ItemType::ClipToDrawingCommands: {
+        get<ClipToDrawingCommands>().apply(context);
+        return;
+    }
+    case ItemType::DrawGlyphs: {
+        get<DrawGlyphs>().apply(context);
+        return;
+    }
+    case ItemType::DrawImage: {
+        get<DrawImage>().apply(context);
+        return;
+    }
+    case ItemType::DrawTiledImage: {
+        get<DrawTiledImage>().apply(context);
+        return;
+    }
+    case ItemType::DrawTiledScaledImage: {
+        get<DrawTiledScaledImage>().apply(context);
+        return;
+    }
+    case ItemType::DrawImageBuffer: {
+        get<DrawImageBuffer>().apply(context);
+        return;
+    }
+    case ItemType::DrawNativeImage: {
+        get<DrawNativeImage>().apply(context);
+        return;
+    }
+    case ItemType::DrawPattern: {
+        get<DrawPattern>().apply(context);
+        return;
+    }
+    case ItemType::DrawRect: {
+        get<DrawRect>().apply(context);
+        return;
+    }
+    case ItemType::DrawLine: {
+        get<DrawLine>().apply(context);
+        return;
+    }
+    case ItemType::DrawLinesForText: {
+        get<DrawLinesForText>().apply(context);
+        return;
+    }
+    case ItemType::DrawDotsForDocumentMarker: {
+        get<DrawDotsForDocumentMarker>().apply(context);
+        return;
+    }
+    case ItemType::DrawEllipse: {
+        get<DrawEllipse>().apply(context);
+        return;
+    }
+    case ItemType::DrawPath: {
+        get<DrawPath>().apply(context);
+        return;
+    }
+    case ItemType::DrawFocusRingPath: {
+        get<DrawFocusRingPath>().apply(context);
+        return;
+    }
+    case ItemType::DrawFocusRingRects: {
+        get<DrawFocusRingRects>().apply(context);
+        return;
+    }
+    case ItemType::FillRect: {
+        get<FillRect>().apply(context);
+        return;
+    }
+    case ItemType::FillRectWithColor: {
+        get<FillRectWithColor>().apply(context);
+        return;
+    }
+    case ItemType::FillRectWithGradient: {
+        get<FillRectWithGradient>().apply(context);
+        return;
+    }
+    case ItemType::FillCompositedRect: {
+        get<FillCompositedRect>().apply(context);
+        return;
+    }
+    case ItemType::FillRoundedRect: {
+        get<FillRoundedRect>().apply(context);
+        return;
+    }
+    case ItemType::FillRectWithRoundedHole: {
+        get<FillRectWithRoundedHole>().apply(context);
+        return;
+    }
+#if ENABLE(INLINE_PATH_DATA)
+    case ItemType::FillInlinePath: {
+        get<FillInlinePath>().apply(context);
+        return;
+    }
+#endif
+    case ItemType::FillPath: {
+        get<FillPath>().apply(context);
+        return;
+    }
+    case ItemType::FillEllipse: {
+        get<FillEllipse>().apply(context);
+        return;
+    }
+    case ItemType::PutImageData: {
+        get<PutImageData>().apply(context);
+        return;
+    }
+    case ItemType::PaintFrameForMedia: {
+        get<PaintFrameForMedia>().apply(context);
+        return;
+    }
+    case ItemType::StrokeRect: {
+        get<StrokeRect>().apply(context);
+        return;
+    }
+#if ENABLE(INLINE_PATH_DATA)
+    case ItemType::StrokeInlinePath: {
+        get<StrokeInlinePath>().apply(context);
+        return;
+    }
+#endif
+    case ItemType::StrokePath: {
+        get<StrokePath>().apply(context);
+        return;
+    }
+    case ItemType::StrokeEllipse: {
+        get<StrokeEllipse>().apply(context);
+        return;
+    }
+    case ItemType::ClearRect: {
+        get<ClearRect>().apply(context);
+        return;
+    }
+    case ItemType::BeginTransparencyLayer: {
+        get<BeginTransparencyLayer>().apply(context);
+        return;
+    }
+    case ItemType::EndTransparencyLayer: {
+        get<EndTransparencyLayer>().apply(context);
+        return;
+    }
+#if USE(CG)
+    case ItemType::ApplyStrokePattern: {
+        get<ApplyStrokePattern>().apply(context);
+        return;
+    }
+    case ItemType::ApplyFillPattern: {
+        get<ApplyFillPattern>().apply(context);
+        return;
+    }
+#endif
+    case ItemType::ApplyDeviceScaleFactor: {
+        get<ApplyDeviceScaleFactor>().apply(context);
+        return;
+    }
+    }
+}
+
+void ItemHandle::destroy()
+{
+    switch (type()) {
+    case ItemType::ClipOutToPath: {
+        get<ClipOutToPath>().~ClipOutToPath();
+        return;
+    }
+    case ItemType::ClipPath: {
+        get<ClipPath>().~ClipPath();
+        return;
+    }
+    case ItemType::ClipToDrawingCommands: {
+        get<ClipToDrawingCommands>().~ClipToDrawingCommands();
+        return;
+    }
+    case ItemType::DrawFocusRingPath: {
+        get<DrawFocusRingPath>().~DrawFocusRingPath();
+        return;
+    }
+    case ItemType::DrawFocusRingRects: {
+        get<DrawFocusRingRects>().~DrawFocusRingRects();
+        return;
+    }
+    case ItemType::DrawGlyphs: {
+        get<DrawGlyphs>().~DrawGlyphs();
+        return;
+    }
+    case ItemType::DrawImage: {
+        get<DrawImage>().~DrawImage();
+        return;
+    }
+    case ItemType::DrawLinesForText: {
+        get<DrawLinesForText>().~DrawLinesForText();
+        return;
+    }
+    case ItemType::DrawNativeImage: {
+        get<DrawNativeImage>().~DrawNativeImage();
+        return;
+    }
+    case ItemType::DrawPath: {
+        get<DrawPath>().~DrawPath();
+        return;
+    }
+    case ItemType::DrawPattern: {
+        get<DrawPattern>().~DrawPattern();
+        return;
+    }
+    case ItemType::DrawTiledImage: {
+        get<DrawTiledImage>().~DrawTiledImage();
+        return;
+    }
+    case ItemType::DrawTiledScaledImage: {
+        get<DrawTiledScaledImage>().~DrawTiledScaledImage();
+        return;
+    }
+    case ItemType::FillCompositedRect: {
+        get<FillCompositedRect>().~FillCompositedRect();
+        return;
+    }
+    case ItemType::FillPath: {
+        get<FillPath>().~FillPath();
+        return;
+    }
+    case ItemType::FillRectWithColor: {
+        get<FillRectWithColor>().~FillRectWithColor();
+        return;
+    }
+    case ItemType::FillRectWithGradient: {
+        get<FillRectWithGradient>().~FillRectWithGradient();
+        return;
+    }
+    case ItemType::FillRectWithRoundedHole: {
+        get<FillRectWithRoundedHole>().~FillRectWithRoundedHole();
+        return;
+    }
+    case ItemType::FillRoundedRect: {
+        get<FillRoundedRect>().~FillRoundedRect();
+        return;
+    }
+    case ItemType::PutImageData: {
+        get<PutImageData>().~PutImageData();
+        return;
+    }
+    case ItemType::SetLineDash: {
+        get<SetLineDash>().~SetLineDash();
+        return;
+    }
+    case ItemType::SetState: {
+        get<SetState>().~SetState();
+        return;
+    }
+    case ItemType::StrokePath: {
+        get<StrokePath>().~StrokePath();
+        return;
+    }
+    case ItemType::ApplyDeviceScaleFactor: {
+        static_assert(std::is_trivially_destructible<ApplyDeviceScaleFactor>::value);
+        return;
+    }
+#if USE(CG)
+    case ItemType::ApplyFillPattern: {
+        static_assert(std::is_trivially_destructible<ApplyFillPattern>::value);
+        return;
+    }
+    case ItemType::ApplyStrokePattern: {
+        static_assert(std::is_trivially_destructible<ApplyStrokePattern>::value);
+        return;
+    }
+#endif
+    case ItemType::BeginTransparencyLayer: {
+        static_assert(std::is_trivially_destructible<BeginTransparencyLayer>::value);
+        return;
+    }
+    case ItemType::ClearRect: {
+        static_assert(std::is_trivially_destructible<ClearRect>::value);
+        return;
+    }
+    case ItemType::ClearShadow: {
+        static_assert(std::is_trivially_destructible<ClearShadow>::value);
+        return;
+    }
+    case ItemType::Clip: {
+        static_assert(std::is_trivially_destructible<Clip>::value);
+        return;
+    }
+    case ItemType::ClipOut: {
+        static_assert(std::is_trivially_destructible<ClipOut>::value);
+        return;
+    }
+    case ItemType::ConcatenateCTM: {
+        static_assert(std::is_trivially_destructible<ConcatenateCTM>::value);
+        return;
+    }
+    case ItemType::DrawDotsForDocumentMarker: {
+        static_assert(std::is_trivially_destructible<DrawDotsForDocumentMarker>::value);
+        return;
+    }
+    case ItemType::DrawEllipse: {
+        static_assert(std::is_trivially_destructible<DrawEllipse>::value);
+        return;
+    }
+    case ItemType::DrawImageBuffer: {
+        static_assert(std::is_trivially_destructible<DrawImageBuffer>::value);
+        return;
+    }
+    case ItemType::DrawLine: {
+        static_assert(std::is_trivially_destructible<DrawLine>::value);
+        return;
+    }
+    case ItemType::DrawRect: {
+        static_assert(std::is_trivially_destructible<DrawRect>::value);
+        return;
+    }
+    case ItemType::EndTransparencyLayer: {
+        static_assert(std::is_trivially_destructible<EndTransparencyLayer>::value);
+        return;
+    }
+    case ItemType::FillEllipse: {
+        static_assert(std::is_trivially_destructible<FillEllipse>::value);
+        return;
+    }
+#if ENABLE(INLINE_PATH_DATA)
+    case ItemType::FillInlinePath: {
+        static_assert(std::is_trivially_destructible<FillInlinePath>::value);
+        return;
+    }
+#endif
+    case ItemType::FillRect: {
+        static_assert(std::is_trivially_destructible<FillRect>::value);
+        return;
+    }
+    case ItemType::PaintFrameForMedia: {
+        static_assert(std::is_trivially_destructible<PaintFrameForMedia>::value);
+        return;
+    }
+    case ItemType::Restore: {
+        static_assert(std::is_trivially_destructible<Restore>::value);
+        return;
+    }
+    case ItemType::Rotate: {
+        static_assert(std::is_trivially_destructible<Rotate>::value);
+        return;
+    }
+    case ItemType::Save: {
+        static_assert(std::is_trivially_destructible<Save>::value);
+        return;
+    }
+    case ItemType::Scale: {
+        static_assert(std::is_trivially_destructible<Scale>::value);
+        return;
+    }
+    case ItemType::SetCTM: {
+        static_assert(std::is_trivially_destructible<SetCTM>::value);
+        return;
+    }
+    case ItemType::SetInlineFillColor: {
+        static_assert(std::is_trivially_destructible<SetInlineFillColor>::value);
+        return;
+    }
+    case ItemType::SetInlineFillGradient: {
+        static_assert(std::is_trivially_destructible<SetInlineFillGradient>::value);
+        return;
+    }
+    case ItemType::SetInlineStrokeColor: {
+        static_assert(std::is_trivially_destructible<SetInlineStrokeColor>::value);
+        return;
+    }
+    case ItemType::SetLineCap: {
+        static_assert(std::is_trivially_destructible<SetLineCap>::value);
+        return;
+    }
+    case ItemType::SetLineJoin: {
+        static_assert(std::is_trivially_destructible<SetLineJoin>::value);
+        return;
+    }
+    case ItemType::SetMiterLimit: {
+        static_assert(std::is_trivially_destructible<SetMiterLimit>::value);
+        return;
+    }
+    case ItemType::SetStrokeThickness: {
+        static_assert(std::is_trivially_destructible<SetStrokeThickness>::value);
+        return;
+    }
+    case ItemType::StrokeEllipse: {
+        static_assert(std::is_trivially_destructible<StrokeEllipse>::value);
+        return;
+    }
+#if ENABLE(INLINE_PATH_DATA)
+    case ItemType::StrokeInlinePath: {
+        static_assert(std::is_trivially_destructible<StrokeInlinePath>::value);
+        return;
+    }
+#endif
+    case ItemType::StrokeRect: {
+        static_assert(std::is_trivially_destructible<StrokeRect>::value);
+        return;
+    }
+    case ItemType::Translate: {
+        static_assert(std::is_trivially_destructible<Translate>::value);
+        return;
+    }
+    }
+}
+
+void ItemHandle::copyTo(ItemHandle destination) const
+{
+    auto itemType = type();
+    destination.data[0] = static_cast<uint8_t>(itemType);
+    switch (itemType) {
+    case ItemType::ClipOutToPath: {
+        new (destination.data + sizeof(ItemType)) ClipOutToPath(get<ClipOutToPath>());
+        return;
+    }
+    case ItemType::ClipPath: {
+        new (destination.data + sizeof(ItemType)) ClipPath(get<ClipPath>());
+        return;
+    }
+    case ItemType::ClipToDrawingCommands: {
+        new (destination.data + sizeof(ItemType)) ClipToDrawingCommands(get<ClipToDrawingCommands>());
+        return;
+    }
+    case ItemType::DrawFocusRingPath: {
+        new (destination.data + sizeof(ItemType)) DrawFocusRingPath(get<DrawFocusRingPath>());
+        return;
+    }
+    case ItemType::DrawFocusRingRects: {
+        new (destination.data + sizeof(ItemType)) DrawFocusRingRects(get<DrawFocusRingRects>());
+        return;
+    }
+    case ItemType::DrawGlyphs: {
+        new (destination.data + sizeof(ItemType)) DrawGlyphs(get<DrawGlyphs>());
+        return;
+    }
+    case ItemType::DrawImage: {
+        new (destination.data + sizeof(ItemType)) DrawImage(get<DrawImage>());
+        return;
+    }
+    case ItemType::DrawImageBuffer: {
+        new (destination.data + sizeof(ItemType)) DrawImageBuffer(get<DrawImageBuffer>());
+        return;
+    }
+    case ItemType::DrawLinesForText: {
+        new (destination.data + sizeof(ItemType)) DrawLinesForText(get<DrawLinesForText>());
+        return;
+    }
+    case ItemType::DrawNativeImage: {
+        new (destination.data + sizeof(ItemType)) DrawNativeImage(get<DrawNativeImage>());
+        return;
+    }
+    case ItemType::DrawPath: {
+        new (destination.data + sizeof(ItemType)) DrawPath(get<DrawPath>());
+        return;
+    }
+    case ItemType::DrawPattern: {
+        new (destination.data + sizeof(ItemType)) DrawPattern(get<DrawPattern>());
+        return;
+    }
+    case ItemType::DrawTiledImage: {
+        new (destination.data + sizeof(ItemType)) DrawTiledImage(get<DrawTiledImage>());
+        return;
+    }
+    case ItemType::DrawTiledScaledImage: {
+        new (destination.data + sizeof(ItemType)) DrawTiledScaledImage(get<DrawTiledScaledImage>());
+        return;
+    }
+    case ItemType::FillCompositedRect: {
+        new (destination.data + sizeof(ItemType)) FillCompositedRect(get<FillCompositedRect>());
+        return;
+    }
+    case ItemType::FillPath: {
+        new (destination.data + sizeof(ItemType)) FillPath(get<FillPath>());
+        return;
+    }
+    case ItemType::FillRectWithColor: {
+        new (destination.data + sizeof(ItemType)) FillRectWithColor(get<FillRectWithColor>());
+        return;
+    }
+    case ItemType::FillRectWithGradient: {
+        new (destination.data + sizeof(ItemType)) FillRectWithGradient(get<FillRectWithGradient>());
+        return;
+    }
+    case ItemType::FillRectWithRoundedHole: {
+        new (destination.data + sizeof(ItemType)) FillRectWithRoundedHole(get<FillRectWithRoundedHole>());
+        return;
+    }
+    case ItemType::FillRoundedRect: {
+        new (destination.data + sizeof(ItemType)) FillRoundedRect(get<FillRoundedRect>());
+        return;
+    }
+    case ItemType::PutImageData: {
+        new (destination.data + sizeof(ItemType)) PutImageData(get<PutImageData>());
+        return;
+    }
+    case ItemType::SetLineDash: {
+        new (destination.data + sizeof(ItemType)) SetLineDash(get<SetLineDash>());
+        return;
+    }
+    case ItemType::SetState: {
+        new (destination.data + sizeof(ItemType)) SetState(get<SetState>());
+        return;
+    }
+    case ItemType::StrokePath: {
+        new (destination.data + sizeof(ItemType)) StrokePath(get<StrokePath>());
+        return;
+    }
+    case ItemType::ApplyDeviceScaleFactor: {
+        new (destination.data + sizeof(ItemType)) ApplyDeviceScaleFactor(get<ApplyDeviceScaleFactor>());
+        return;
+    }
+#if USE(CG)
+    case ItemType::ApplyFillPattern: {
+        new (destination.data + sizeof(ItemType)) ApplyFillPattern(get<ApplyFillPattern>());
+        return;
+    }
+    case ItemType::ApplyStrokePattern: {
+        new (destination.data + sizeof(ItemType)) ApplyStrokePattern(get<ApplyStrokePattern>());
+        return;
+    }
+#endif
+    case ItemType::BeginTransparencyLayer: {
+        new (destination.data + sizeof(ItemType)) BeginTransparencyLayer(get<BeginTransparencyLayer>());
+        return;
+    }
+    case ItemType::ClearRect: {
+        new (destination.data + sizeof(ItemType)) ClearRect(get<ClearRect>());
+        return;
+    }
+    case ItemType::ClearShadow: {
+        new (destination.data + sizeof(ItemType)) ClearShadow(get<ClearShadow>());
+        return;
+    }
+    case ItemType::Clip: {
+        new (destination.data + sizeof(ItemType)) Clip(get<Clip>());
+        return;
+    }
+    case ItemType::ClipOut: {
+        new (destination.data + sizeof(ItemType)) ClipOut(get<ClipOut>());
+        return;
+    }
+    case ItemType::ConcatenateCTM: {
+        new (destination.data + sizeof(ItemType)) ConcatenateCTM(get<ConcatenateCTM>());
+        return;
+    }
+    case ItemType::DrawDotsForDocumentMarker: {
+        new (destination.data + sizeof(ItemType)) DrawDotsForDocumentMarker(get<DrawDotsForDocumentMarker>());
+        return;
+    }
+    case ItemType::DrawEllipse: {
+        new (destination.data + sizeof(ItemType)) DrawEllipse(get<DrawEllipse>());
+        return;
+    }
+    case ItemType::DrawLine: {
+        new (destination.data + sizeof(ItemType)) DrawLine(get<DrawLine>());
+        return;
+    }
+    case ItemType::DrawRect: {
+        new (destination.data + sizeof(ItemType)) DrawRect(get<DrawRect>());
+        return;
+    }
+    case ItemType::EndTransparencyLayer: {
+        new (destination.data + sizeof(ItemType)) EndTransparencyLayer(get<EndTransparencyLayer>());
+        return;
+    }
+    case ItemType::FillEllipse: {
+        new (destination.data + sizeof(ItemType)) FillEllipse(get<FillEllipse>());
+        return;
+    }
+#if ENABLE(INLINE_PATH_DATA)
+    case ItemType::FillInlinePath: {
+        new (destination.data + sizeof(ItemType)) FillInlinePath(get<FillInlinePath>());
+        return;
+    }
+#endif
+    case ItemType::FillRect: {
+        new (destination.data + sizeof(ItemType)) FillRect(get<FillRect>());
+        return;
+    }
+    case ItemType::PaintFrameForMedia: {
+        new (destination.data + sizeof(ItemType)) PaintFrameForMedia(get<PaintFrameForMedia>());
+        return;
+    }
+    case ItemType::Restore: {
+        new (destination.data + sizeof(ItemType)) Restore(get<Restore>());
+        return;
+    }
+    case ItemType::Rotate: {
+        new (destination.data + sizeof(ItemType)) Rotate(get<Rotate>());
+        return;
+    }
+    case ItemType::Save: {
+        new (destination.data + sizeof(ItemType)) Save(get<Save>());
+        return;
+    }
+    case ItemType::Scale: {
+        new (destination.data + sizeof(ItemType)) Scale(get<Scale>());
+        return;
+    }
+    case ItemType::SetCTM: {
+        new (destination.data + sizeof(ItemType)) SetCTM(get<SetCTM>());
+        return;
+    }
+    case ItemType::SetInlineFillColor: {
+        new (destination.data + sizeof(ItemType)) SetInlineFillColor(get<SetInlineFillColor>());
+        return;
+    }
+    case ItemType::SetInlineFillGradient: {
+        new (destination.data + sizeof(ItemType)) SetInlineFillGradient(get<SetInlineFillGradient>());
+        return;
+    }
+    case ItemType::SetInlineStrokeColor: {
+        new (destination.data + sizeof(ItemType)) SetInlineStrokeColor(get<SetInlineStrokeColor>());
+        return;
+    }
+    case ItemType::SetLineCap: {
+        new (destination.data + sizeof(ItemType)) SetLineCap(get<SetLineCap>());
+        return;
+    }
+    case ItemType::SetLineJoin: {
+        new (destination.data + sizeof(ItemType)) SetLineJoin(get<SetLineJoin>());
+        return;
+    }
+    case ItemType::SetMiterLimit: {
+        new (destination.data + sizeof(ItemType)) SetMiterLimit(get<SetMiterLimit>());
+        return;
+    }
+    case ItemType::SetStrokeThickness: {
+        new (destination.data + sizeof(ItemType)) SetStrokeThickness(get<SetStrokeThickness>());
+        return;
+    }
+    case ItemType::StrokeEllipse: {
+        new (destination.data + sizeof(ItemType)) StrokeEllipse(get<StrokeEllipse>());
+        return;
+    }
+#if ENABLE(INLINE_PATH_DATA)
+    case ItemType::StrokeInlinePath: {
+        new (destination.data + sizeof(ItemType)) StrokeInlinePath(get<StrokeInlinePath>());
+        return;
+    }
+#endif
+    case ItemType::StrokeRect: {
+        new (destination.data + sizeof(ItemType)) StrokeRect(get<StrokeRect>());
+        return;
+    }
+    case ItemType::Translate: {
+        new (destination.data + sizeof(ItemType)) Translate(get<Translate>());
+        return;
+    }
+    }
+}
+
+ItemBuffer::ItemBuffer(ItemBufferHandles&& handles)
+    : m_readOnlyBuffers(WTFMove(handles))
+{
+}
+
+ItemBuffer::ItemBuffer() = default;
+
+ItemBuffer::~ItemBuffer()
+{
+    clear();
+}
+
+ItemBuffer::ItemBuffer(ItemBuffer&& other)
+    : m_readingClient(std::exchange(other.m_readingClient, nullptr))
+    , m_writingClient(std::exchange(other.m_writingClient, nullptr))
+    , m_itemsToDestroyInAllocatedBuffers(std::exchange(other.m_itemsToDestroyInAllocatedBuffers, { }))
+    , m_allocatedBuffers(std::exchange(other.m_allocatedBuffers, { }))
+    , m_readOnlyBuffers(std::exchange(other.m_readOnlyBuffers, { }))
+    , m_writableBuffer(std::exchange(other.m_writableBuffer, { }))
+    , m_writtenNumberOfBytes(std::exchange(other.m_writtenNumberOfBytes, 0))
+{
+}
+
+ItemBuffer& ItemBuffer::operator=(ItemBuffer&& other)
+{
+    m_readingClient = std::exchange(other.m_readingClient, nullptr);
+    m_writingClient = std::exchange(other.m_writingClient, nullptr);
+    m_itemsToDestroyInAllocatedBuffers = std::exchange(other.m_itemsToDestroyInAllocatedBuffers, { });
+    m_allocatedBuffers = std::exchange(other.m_allocatedBuffers, { });
+    m_readOnlyBuffers = std::exchange(other.m_readOnlyBuffers, { });
+    m_writableBuffer = std::exchange(other.m_writableBuffer, { });
+    m_writtenNumberOfBytes = std::exchange(other.m_writtenNumberOfBytes, 0);
+    return *this;
+}
+
+ItemBufferHandle ItemBuffer::createItemBuffer(size_t capacity)
+{
+    if (m_writingClient) {
+        if (auto handle = m_writingClient->createItemBuffer(capacity))
+            return handle;
+    }
+
+    constexpr size_t defaultItemBufferCapacity = 1 << 10;
+
+    auto newBufferCapacity = std::max(capacity, defaultItemBufferCapacity);
+    auto* buffer = reinterpret_cast<uint8_t*>(fastMalloc(newBufferCapacity));
+    m_allocatedBuffers.append(buffer);
+    return { ItemBufferIdentifier::generate(), buffer, newBufferCapacity };
+}
+
+void ItemBuffer::forEachItemBuffer(Function<void(const ItemBufferHandle&)>&& mapFunction) const
+{
+    for (auto& handle : m_readOnlyBuffers)
+        mapFunction(handle);
+
+    if (m_writableBuffer && m_writtenNumberOfBytes)
+        mapFunction({ m_writableBuffer.identifier, m_writableBuffer.data, m_writtenNumberOfBytes });
+}
+
+void ItemBuffer::clear()
+{
+    for (auto item : std::exchange(m_itemsToDestroyInAllocatedBuffers, { }))
+        item.destroy();
+
+    for (auto* buffer : std::exchange(m_allocatedBuffers, { }))
+        fastFree(buffer);
+
+    m_readOnlyBuffers.clear();
+    m_writableBuffer = { };
+    m_writtenNumberOfBytes = 0;
+}
+
+void ItemBuffer::swapWritableBufferIfNeeded(size_t numberOfBytes)
+{
+    if (m_writtenNumberOfBytes + numberOfBytes <= m_writableBuffer.capacity)
+        return;
+
+    auto nextBuffer = createItemBuffer(numberOfBytes);
+    bool hadPreviousBuffer = m_writableBuffer;
+    auto previousBuffer = std::exchange(m_writableBuffer, { });
+    previousBuffer.capacity = std::exchange(m_writtenNumberOfBytes, 0);
+    if (hadPreviousBuffer)
+        m_readOnlyBuffers.append(WTFMove(previousBuffer));
+
+    m_writableBuffer = WTFMove(nextBuffer);
+}
+
+void ItemBuffer::appendDataAndLength(Ref<SharedBuffer>&& data, uint8_t* location)
+{
+    reinterpret_cast<size_t*>(location)[0] = data->size();
+
+    auto* startOfPadding = location + sizeof(size_t);
+    size_t padding = (alignof(uint64_t) - reinterpret_cast<uintptr_t>(startOfPadding) % alignof(uint64_t)) % alignof(uint64_t);
+    auto* startOfData = startOfPadding + padding;
+    memcpy(startOfData, data->dataAsUInt8Ptr(), data->size());
+
+    m_writtenNumberOfBytes += sizeof(ItemType) + sizeof(size_t) + padding + data->size();
+}
+
+} // namespace DisplayList
+} // namespace WebCore
</ins></span></pre></div>
<a id="trunkSourceWebCoreplatformgraphicsdisplaylistsDisplayListItemBufferh"></a>
<div class="addfile"><h4>Added: trunk/Source/WebCore/platform/graphics/displaylists/DisplayListItemBuffer.h (0 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/graphics/displaylists/DisplayListItemBuffer.h                              (rev 0)
+++ trunk/Source/WebCore/platform/graphics/displaylists/DisplayListItemBuffer.h 2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -0,0 +1,197 @@
</span><ins>+/*
+ * Copyright (C) 2020 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#pragma once
+
+#include "DisplayListItemType.h"
+#include "SharedBuffer.h"
+#include <wtf/FastMalloc.h>
+#include <wtf/ObjectIdentifier.h>
+
+namespace WebCore {
+
+class GraphicsContext;
+
+namespace DisplayList {
+
+class DisplayList;
+
+enum ItemBufferIdentifierType { };
+using ItemBufferIdentifier = ObjectIdentifier<ItemBufferIdentifierType>;
+
+// An ItemBufferHandle wraps a pointer to a buffer that contains display list item data.
+struct ItemBufferHandle {
+    ItemBufferIdentifier identifier;
+    uint8_t* data { nullptr };
+    size_t capacity { 0 };
+
+    operator bool() const { return !!(*this); }
+    bool operator!() const { return !data; }
+};
+
+using ItemBufferHandles = Vector<ItemBufferHandle, 2>;
+
+// An ItemHandle wraps a pointer to an ItemType, followed immediately by an item of that type.
+struct ItemHandle {
+    uint8_t* data { nullptr };
+
+    void apply(GraphicsContext&);
+    void destroy();
+    bool isDrawingItem() const { return WebCore::DisplayList::isDrawingItem(type()); }
+
+    operator bool() const { return !!(*this); }
+    bool operator!() const { return !data; }
+
+#if !defined(NDEBUG) || !LOG_DISABLED
+    CString description() const;
+#endif
+
+    ItemType type() const { return static_cast<ItemType>(data[0]); }
+    size_t size() const { return sizeof(ItemType) + sizeOfItemInBytes(type()); }
+
+    template<typename T> bool is() const { return type() == T::itemType; }
+    template<typename T> T& get() const
+    {
+        ASSERT(is<T>());
+        return *reinterpret_cast<T*>(&data[sizeof(ItemType)]);
+    }
+
+    void copyTo(ItemHandle destination) const;
+};
+
+class ItemBufferWritingClient {
+public:
+    virtual ~ItemBufferWritingClient() { }
+
+    virtual ItemBufferHandle createItemBuffer(size_t) = 0;
+    virtual RefPtr<SharedBuffer> encodeItem(ItemHandle) const = 0;
+};
+
+class ItemBufferReadingClient {
+public:
+    virtual ~ItemBufferReadingClient() { }
+
+    virtual Optional<ItemHandle> WARN_UNUSED_RETURN decodeItem(const uint8_t* data, size_t dataLength, ItemType, uint8_t* handleLocation) = 0;
+};
+
+// An ItemBuffer contains display list item data, and consists of a readwrite ItemBufferHandle (to which display
+// list items are appended) as well as a number of readonly ItemBufferHandles. Items are appended to the readwrite
+// buffer until all available capacity is exhausted, at which point we will move this writable handle to the list
+// of readonly handles.
+class ItemBuffer {
+    WTF_MAKE_NONCOPYABLE(ItemBuffer); WTF_MAKE_FAST_ALLOCATED;
+public:
+    friend class DisplayList;
+
+    WEBCORE_EXPORT ItemBuffer();
+    WEBCORE_EXPORT ~ItemBuffer();
+    ItemBuffer(ItemBufferHandles&&);
+
+    WEBCORE_EXPORT ItemBuffer(ItemBuffer&&);
+    WEBCORE_EXPORT ItemBuffer& operator=(ItemBuffer&&);
+
+    size_t sizeInBytes() const
+    {
+        size_t result = 0;
+        for (auto buffer : m_readOnlyBuffers)
+            result += buffer.capacity;
+        result += m_writtenNumberOfBytes;
+        return result;
+    }
+
+    void clear();
+
+    bool isEmpty() const
+    {
+        return !m_writtenNumberOfBytes && m_readOnlyBuffers.isEmpty();
+    }
+
+    WEBCORE_EXPORT ItemBufferHandle createItemBuffer(size_t);
+
+    // ItemBuffer::append<T>(...) appends a display list item of type T to the end of the current
+    // writable buffer handle; if remaining buffer capacity is insufficient to store the item, a
+    // new buffer will be allocated (either by the ItemBufferWritingClient, if set, or by the item
+    // buffer itself if there is no client). Items are placed back-to-back in these item buffers,
+    // with an ItemType separating each item.
+    //
+    // If a writing client is present and requires custom encoding for the given item type T, the
+    // item buffer will ask the client for an opaque SharedBuffer containing encoded data for the
+    // item. This encoded data is then appended to the item buffer, with padding to ensure that
+    // the start of this data is aligned to 8 bytes, if necessary. When consuming encoded item
+    // data, a corresponding ItemBufferReadingClient will be required to convert this encoded data
+    // back into an item of type T.
+    template<typename T, class... Args> void append(Args&&... args)
+    {
+        static_assert(std::is_trivially_destructible<T>::value || !T::isInlineItem);
+        constexpr auto sizeOfTypeAndItem = sizeof(ItemType) + sizeof(T);
+
+        if (!T::isInlineItem && m_writingClient) {
+            static uint8_t itemBuffer[sizeOfTypeAndItem];
+            itemBuffer[0] = static_cast<uint8_t>(T::itemType);
+            new (itemBuffer + sizeof(ItemType)) T(std::forward<Args>(args)...);
+            if (auto sharedBuffer = m_writingClient->encodeItem({ itemBuffer })) {
+                swapWritableBufferIfNeeded(sharedBuffer->size() + sizeof(ItemType) + sizeof(size_t) + alignof(uint64_t));
+                m_writableBuffer.data[m_writtenNumberOfBytes] = static_cast<uint8_t>(T::itemType);
+                appendDataAndLength(sharedBuffer.releaseNonNull(), m_writableBuffer.data + m_writtenNumberOfBytes + sizeof(ItemType));
+            }
+            return;
+        }
+
+        swapWritableBufferIfNeeded(sizeOfTypeAndItem);
+
+        if (!std::is_trivially_destructible<T>::value)
+            m_itemsToDestroyInAllocatedBuffers.append({ &m_writableBuffer.data[m_writtenNumberOfBytes] });
+
+        uncheckedAppend<T>(std::forward<Args>(args)...);
+    }
+
+    void setClient(ItemBufferWritingClient* client) { m_writingClient = client; }
+    void setClient(ItemBufferReadingClient* client) { m_readingClient = client; }
+
+private:
+    const ItemBufferHandles& readOnlyBuffers() const { return m_readOnlyBuffers; }
+    void forEachItemBuffer(Function<void(const ItemBufferHandle&)>&&) const;
+
+    WEBCORE_EXPORT void swapWritableBufferIfNeeded(size_t numberOfBytes);
+    WEBCORE_EXPORT void appendDataAndLength(Ref<SharedBuffer>&&, uint8_t*);
+    template<typename T, class... Args> void uncheckedAppend(Args&&... args)
+    {
+        auto* startOfItem = &m_writableBuffer.data[m_writtenNumberOfBytes];
+        startOfItem[0] = static_cast<uint8_t>(T::itemType);
+        new (startOfItem + sizeof(ItemType)) T(std::forward<Args>(args)...);
+        m_writtenNumberOfBytes += sizeof(ItemType) + sizeOfItemInBytes(T::itemType);
+    }
+
+    ItemBufferReadingClient* m_readingClient { nullptr };
+    ItemBufferWritingClient* m_writingClient { nullptr };
+    Vector<ItemHandle> m_itemsToDestroyInAllocatedBuffers;
+    Vector<uint8_t*> m_allocatedBuffers;
+    ItemBufferHandles m_readOnlyBuffers;
+    ItemBufferHandle m_writableBuffer;
+    size_t m_writtenNumberOfBytes { 0 };
+};
+
+} // namespace DisplayList
+} // namespace WebCore
</ins></span></pre></div>
<a id="trunkSourceWebCoreplatformgraphicsdisplaylistsDisplayListItemscpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/graphics/displaylists/DisplayListItems.cpp (269524 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/graphics/displaylists/DisplayListItems.cpp 2020-11-06 18:44:09 UTC (rev 269524)
+++ trunk/Source/WebCore/platform/graphics/displaylists/DisplayListItems.cpp    2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -44,204 +44,16 @@
</span><span class="cx"> // Should match RenderTheme::platformFocusRingWidth()
</span><span class="cx"> static const float platformFocusRingWidth = 3;
</span><span class="cx"> 
</span><del>-#if !defined(NDEBUG) || !LOG_DISABLED
-WTF::CString Item::description() const
-{
-    TextStream ts;
-    ts << *this;
-    return ts.release().utf8();
-}
-#endif
-
-Item::Item(ItemType type)
-    : m_type(type)
-{
-}
-
-Item::~Item() = default;
-
-size_t Item::sizeInBytes(const Item& item)
-{
-    switch (item.type()) {
-    case ItemType::Save:
-        return sizeof(downcast<Save>(item));
-    case ItemType::Restore:
-        return sizeof(downcast<Restore>(item));
-    case ItemType::Translate:
-        return sizeof(downcast<Translate>(item));
-    case ItemType::Rotate:
-        return sizeof(downcast<Rotate>(item));
-    case ItemType::Scale:
-        return sizeof(downcast<Scale>(item));
-    case ItemType::SetCTM:
-        return sizeof(downcast<SetCTM>(item));
-    case ItemType::ConcatenateCTM:
-        return sizeof(downcast<ConcatenateCTM>(item));
-    case ItemType::SetInlineFillGradient:
-        return sizeof(downcast<SetInlineFillGradient>(item));
-    case ItemType::SetInlineFillColor:
-        return sizeof(downcast<SetInlineFillColor>(item));
-    case ItemType::SetInlineStrokeColor:
-        return sizeof(downcast<SetInlineStrokeColor>(item));
-    case ItemType::SetStrokeThickness:
-        return sizeof(downcast<SetStrokeThickness>(item));
-    case ItemType::SetState:
-        return sizeof(downcast<SetState>(item));
-    case ItemType::SetLineCap:
-        return sizeof(downcast<SetLineCap>(item));
-    case ItemType::SetLineDash:
-        return sizeof(downcast<SetLineDash>(item));
-    case ItemType::SetLineJoin:
-        return sizeof(downcast<SetLineJoin>(item));
-    case ItemType::SetMiterLimit:
-        return sizeof(downcast<SetMiterLimit>(item));
-    case ItemType::ClearShadow:
-        return sizeof(downcast<ClearShadow>(item));
-    case ItemType::Clip:
-        return sizeof(downcast<Clip>(item));
-    case ItemType::ClipOut:
-        return sizeof(downcast<ClipOut>(item));
-    case ItemType::ClipOutToPath:
-        return sizeof(downcast<ClipOutToPath>(item));
-    case ItemType::ClipPath:
-        return sizeof(downcast<ClipPath>(item));
-    case ItemType::ClipToDrawingCommands:
-        return sizeof(downcast<ClipToDrawingCommands>(item));
-    case ItemType::DrawGlyphs:
-        return sizeof(downcast<DrawGlyphs>(item));
-    case ItemType::DrawImage:
-        return sizeof(downcast<DrawImage>(item));
-    case ItemType::DrawTiledImage:
-        return sizeof(downcast<DrawTiledImage>(item));
-    case ItemType::DrawTiledScaledImage:
-        return sizeof(downcast<DrawTiledScaledImage>(item));
-    case ItemType::DrawImageBuffer:
-        return sizeof(downcast<DrawImageBuffer>(item));
-    case ItemType::DrawNativeImage:
-        return sizeof(downcast<DrawNativeImage>(item));
-    case ItemType::DrawPattern:
-        return sizeof(downcast<DrawPattern>(item));
-    case ItemType::DrawRect:
-        return sizeof(downcast<DrawRect>(item));
-    case ItemType::DrawLine:
-        return sizeof(downcast<DrawLine>(item));
-    case ItemType::DrawLinesForText:
-        return sizeof(downcast<DrawLinesForText>(item));
-    case ItemType::DrawDotsForDocumentMarker:
-        return sizeof(downcast<DrawDotsForDocumentMarker>(item));
-    case ItemType::DrawEllipse:
-        return sizeof(downcast<DrawEllipse>(item));
-    case ItemType::DrawPath:
-        return sizeof(downcast<DrawPath>(item));
-    case ItemType::DrawFocusRingPath:
-        return sizeof(downcast<DrawFocusRingPath>(item));
-    case ItemType::DrawFocusRingRects:
-        return sizeof(downcast<DrawFocusRingRects>(item));
-    case ItemType::FillRect:
-        return sizeof(downcast<FillRect>(item));
-    case ItemType::FillRectWithColor:
-        return sizeof(downcast<FillRectWithColor>(item));
-    case ItemType::FillRectWithGradient:
-        return sizeof(downcast<FillRectWithGradient>(item));
-    case ItemType::FillCompositedRect:
-        return sizeof(downcast<FillCompositedRect>(item));
-    case ItemType::FillRoundedRect:
-        return sizeof(downcast<FillRoundedRect>(item));
-    case ItemType::FillRectWithRoundedHole:
-        return sizeof(downcast<FillRectWithRoundedHole>(item));
-#if ENABLE(INLINE_PATH_DATA)
-    case ItemType::FillInlinePath:
-        return sizeof(downcast<FillInlinePath>(item));
-#endif
-    case ItemType::FillPath:
-        return sizeof(downcast<FillPath>(item));
-    case ItemType::FillEllipse:
-        return sizeof(downcast<FillEllipse>(item));
-    case ItemType::PutImageData:
-        return sizeof(downcast<PutImageData>(item));
-    case ItemType::PaintFrameForMedia:
-        return sizeof(downcast<PaintFrameForMedia>(item));
-    case ItemType::StrokeRect:
-        return sizeof(downcast<StrokeRect>(item));
-#if ENABLE(INLINE_PATH_DATA)
-    case ItemType::StrokeInlinePath:
-        return sizeof(downcast<StrokeInlinePath>(item));
-#endif
-    case ItemType::StrokePath:
-        return sizeof(downcast<StrokePath>(item));
-    case ItemType::StrokeEllipse:
-        return sizeof(downcast<StrokeEllipse>(item));
-    case ItemType::ClearRect:
-        return sizeof(downcast<ClearRect>(item));
-    case ItemType::BeginTransparencyLayer:
-        return sizeof(downcast<BeginTransparencyLayer>(item));
-    case ItemType::EndTransparencyLayer:
-        return sizeof(downcast<EndTransparencyLayer>(item));
-#if USE(CG)
-    case ItemType::ApplyStrokePattern:
-        return sizeof(downcast<ApplyStrokePattern>(item));
-    case ItemType::ApplyFillPattern:
-        return sizeof(downcast<ApplyFillPattern>(item));
-#endif
-    case ItemType::ApplyDeviceScaleFactor:
-        return sizeof(downcast<ApplyDeviceScaleFactor>(item));
-    }
-    return 0;
-}
-
-static TextStream& operator<<(TextStream& ts, const DrawingItem& item)
-{
-    ts.startGroup();
-    ts << "extent ";
-    if (item.extentKnown())
-        ts << item.extent();
-    else
-        ts << "unknown";
-    
-    ts.endGroup();
-    return ts;
-}
-
-DrawingItem::DrawingItem(ItemType type)
-    : Item(type)
-{
-}
-
-DrawingItem::~DrawingItem() = default;
-
-Save::Save()
-    : Item(ItemType::Save)
-{
-}
-
-Save::~Save() = default;
-
</del><span class="cx"> void Save::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.save();
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-Restore::Restore()
-    : Item(ItemType::Restore)
-{
-}
-
-Restore::~Restore() = default;
-
</del><span class="cx"> void Restore::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.restore();
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-Translate::Translate(float x, float y)
-    : Item(ItemType::Translate)
-    , m_x(x)
-    , m_y(y)
-{
-}
-
-Translate::~Translate() = default;
-
</del><span class="cx"> void Translate::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.translate(m_x, m_y);
</span><span class="lines">@@ -255,14 +67,6 @@
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-Rotate::Rotate(float angle)
-    : Item(ItemType::Rotate)
-    , m_angle(angle)
-{
-}
-
-Rotate::~Rotate() = default;
-
</del><span class="cx"> void Rotate::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.rotate(m_angle);
</span><span class="lines">@@ -275,14 +79,6 @@
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-Scale::Scale(const FloatSize& size)
-    : Item(ItemType::Scale)
-    , m_size(size)
-{
-}
-
-Scale::~Scale() = default;
-
</del><span class="cx"> void Scale::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.scale(m_size);
</span><span class="lines">@@ -295,14 +91,6 @@
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-SetCTM::SetCTM(const AffineTransform& transform)
-    : Item(ItemType::SetCTM)
-    , m_transform(transform)
-{
-}
-
-SetCTM::~SetCTM() = default;
-
</del><span class="cx"> void SetCTM::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.setCTM(m_transform);
</span><span class="lines">@@ -315,14 +103,6 @@
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-ConcatenateCTM::ConcatenateCTM(const AffineTransform& transform)
-    : Item(ItemType::ConcatenateCTM)
-    , m_transform(transform)
-{
-}
-
-ConcatenateCTM::~ConcatenateCTM() = default;
-
</del><span class="cx"> void ConcatenateCTM::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.concatCTM(m_transform);
</span><span class="lines">@@ -336,8 +116,7 @@
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> SetInlineFillGradient::SetInlineFillGradient(const Gradient& gradient)
</span><del>-    : Item(ItemType::SetInlineFillGradient)
-    , m_data(gradient.data())
</del><ins>+    : m_data(gradient.data())
</ins><span class="cx">     , m_gradientSpaceTransformation(gradient.gradientSpaceTransform())
</span><span class="cx">     , m_spreadMethod(gradient.spreadMethod())
</span><span class="cx">     , m_colorStopCount(static_cast<uint8_t>(gradient.stops().size()))
</span><span class="lines">@@ -359,14 +138,8 @@
</span><span class="cx">     return gradient;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-Ref<SetInlineFillGradient> SetInlineFillGradient::create(const Gradient& gradient)
-{
-    return adoptRef(*new SetInlineFillGradient(gradient));
-}
-
</del><span class="cx"> SetInlineFillGradient::SetInlineFillGradient(float offsets[maxColorStopCount], SRGBA<uint8_t> colors[maxColorStopCount], const Gradient::Data& data, const AffineTransform& gradientSpaceTransformation, GradientSpreadMethod spreadMethod, uint8_t colorStopCount)
</span><del>-    : Item(ItemType::SetInlineFillGradient)
-    , m_data(data)
</del><ins>+    : m_data(data)
</ins><span class="cx">     , m_gradientSpaceTransformation(gradientSpaceTransformation)
</span><span class="cx">     , m_spreadMethod(spreadMethod)
</span><span class="cx">     , m_colorStopCount(colorStopCount)
</span><span class="lines">@@ -378,8 +151,6 @@
</span><span class="cx">     }
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-SetInlineFillGradient::~SetInlineFillGradient() = default;
-
</del><span class="cx"> void SetInlineFillGradient::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     if (m_colorStopCount <= maxColorStopCount)
</span><span class="lines">@@ -405,13 +176,6 @@
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-Ref<SetInlineFillColor> SetInlineFillColor::create(SRGBA<uint8_t> colorData)
-{
-    return adoptRef(*new SetInlineFillColor(colorData));
-}
-
-SetInlineFillColor::~SetInlineFillColor() = default;
-
</del><span class="cx"> void SetInlineFillColor::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.setFillColor(color());
</span><span class="lines">@@ -423,13 +187,6 @@
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-Ref<SetInlineStrokeColor> SetInlineStrokeColor::create(SRGBA<uint8_t> colorData)
-{
-    return adoptRef(*new SetInlineStrokeColor(colorData));
-}
-
-SetInlineStrokeColor::~SetInlineStrokeColor() = default;
-
</del><span class="cx"> void SetInlineStrokeColor::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.setStrokeColor(color());
</span><span class="lines">@@ -441,13 +198,6 @@
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-Ref<SetStrokeThickness> SetStrokeThickness::create(float thickness)
-{
-    return adoptRef(*new SetStrokeThickness(thickness));
-}
-
-SetStrokeThickness::~SetStrokeThickness() = default;
-
</del><span class="cx"> void SetStrokeThickness::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.setStrokeThickness(m_thickness);
</span><span class="lines">@@ -460,19 +210,15 @@
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> SetState::SetState(const GraphicsContextState& state, GraphicsContextState::StateChangeFlags flags)
</span><del>-    : Item(ItemType::SetState)
-    , m_state(state, flags)
</del><ins>+    : m_state(state, flags)
</ins><span class="cx"> {
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> SetState::SetState(const GraphicsContextStateChange& stateChange)
</span><del>-    : Item(ItemType::SetState)
-    , m_state(stateChange)
</del><ins>+    : m_state(stateChange)
</ins><span class="cx"> {
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-SetState::~SetState() = default;
-
</del><span class="cx"> void SetState::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     m_state.apply(context);
</span><span class="lines">@@ -484,14 +230,6 @@
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-SetLineCap::SetLineCap(LineCap lineCap)
-    : Item(ItemType::SetLineCap)
-    , m_lineCap(lineCap)
-{
-}
-
-SetLineCap::~SetLineCap() = default;
-
</del><span class="cx"> void SetLineCap::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.setLineCap(m_lineCap);
</span><span class="lines">@@ -503,15 +241,6 @@
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-SetLineDash::SetLineDash(const DashArray& dashArray, float dashOffset)
-    : Item(ItemType::SetLineDash)
-    , m_dashArray(dashArray)
-    , m_dashOffset(dashOffset)
-{
-}
-
-SetLineDash::~SetLineDash() = default;
-
</del><span class="cx"> void SetLineDash::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.setLineDash(m_dashArray, m_dashOffset);
</span><span class="lines">@@ -524,14 +253,6 @@
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-SetLineJoin::SetLineJoin(LineJoin lineJoin)
-    : Item(ItemType::SetLineJoin)
-    , m_lineJoin(lineJoin)
-{
-}
-
-SetLineJoin::~SetLineJoin() = default;
-
</del><span class="cx"> void SetLineJoin::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.setLineJoin(m_lineJoin);
</span><span class="lines">@@ -543,14 +264,6 @@
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-SetMiterLimit::SetMiterLimit(float miterLimit)
-    : Item(ItemType::SetMiterLimit)
-    , m_miterLimit(miterLimit)
-{
-}
-
-SetMiterLimit::~SetMiterLimit() = default;
-
</del><span class="cx"> void SetMiterLimit::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.setMiterLimit(m_miterLimit);
</span><span class="lines">@@ -562,26 +275,11 @@
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-ClearShadow::ClearShadow()
-    : Item(ItemType::ClearShadow)
-{
-}
-
-ClearShadow::~ClearShadow() = default;
-
</del><span class="cx"> void ClearShadow::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.clearShadow();
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-Clip::Clip(const FloatRect& rect)
-    : Item(ItemType::Clip)
-    , m_rect(rect)
-{
-}
-
-Clip::~Clip() = default;
-
</del><span class="cx"> void Clip::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.clip(m_rect);
</span><span class="lines">@@ -593,14 +291,6 @@
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-ClipOut::ClipOut(const FloatRect& rect)
-    : Item(ItemType::ClipOut)
-    , m_rect(rect)
-{
-}
-
-ClipOut::~ClipOut() = default;
-
</del><span class="cx"> void ClipOut::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.clipOut(m_rect);
</span><span class="lines">@@ -612,14 +302,6 @@
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-ClipOutToPath::ClipOutToPath(const Path& path)
-    : Item(ItemType::ClipOutToPath)
-    , m_path(path)
-{
-}
-
-ClipOutToPath::~ClipOutToPath() = default;
-
</del><span class="cx"> void ClipOutToPath::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.clipOut(m_path);
</span><span class="lines">@@ -631,15 +313,6 @@
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-ClipPath::ClipPath(const Path& path, WindRule windRule)
-    : Item(ItemType::ClipPath)
-    , m_path(path)
-    , m_windRule(windRule)
-{
-}
-
-ClipPath::~ClipPath() = default;
-
</del><span class="cx"> void ClipPath::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.clipPath(m_path, m_windRule);
</span><span class="lines">@@ -652,16 +325,6 @@
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-ClipToDrawingCommands::ClipToDrawingCommands(const FloatRect& destination, ColorSpace colorSpace, DisplayList&& drawingCommands)
-    : Item(ItemType::ClipToDrawingCommands)
-    , m_destination(destination)
-    , m_colorSpace(colorSpace)
-    , m_drawingCommands(WTFMove(drawingCommands))
-{
-}
-
-ClipToDrawingCommands::~ClipToDrawingCommands() = default;
-
</del><span class="cx"> void ClipToDrawingCommands::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.clipToDrawingCommands(m_destination, m_colorSpace, [&] (GraphicsContext& clippingContext) {
</span><span class="lines">@@ -678,8 +341,7 @@
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> DrawGlyphs::DrawGlyphs(const Font& font, Vector<GlyphBufferGlyph, 128>&& glyphs, Vector<GlyphBufferAdvance, 128>&& advances, const FloatPoint& localAnchor, FontSmoothingMode smoothingMode)
</span><del>-    : DrawingItem(ItemType::DrawGlyphs)
-    , m_font(const_cast<Font&>(font))
</del><ins>+    : m_font(makeRefPtr(const_cast<Font&>(font)))
</ins><span class="cx">     , m_glyphs(WTFMove(glyphs))
</span><span class="cx">     , m_advances(WTFMove(advances))
</span><span class="cx">     , m_localAnchor(localAnchor)
</span><span class="lines">@@ -689,8 +351,7 @@
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> DrawGlyphs::DrawGlyphs(const Font& font, const GlyphBufferGlyph* glyphs, const GlyphBufferAdvance* advances, unsigned count, const FloatPoint& localAnchor, FontSmoothingMode smoothingMode)
</span><del>-    : DrawingItem(ItemType::DrawGlyphs)
-    , m_font(const_cast<Font&>(font))
</del><ins>+    : m_font(makeRefPtr(const_cast<Font&>(font)))
</ins><span class="cx">     , m_localAnchor(localAnchor)
</span><span class="cx">     , m_smoothingMode(smoothingMode)
</span><span class="cx"> {
</span><span class="lines">@@ -703,19 +364,17 @@
</span><span class="cx">     computeBounds();
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-DrawGlyphs::~DrawGlyphs() = default;
-
</del><span class="cx"> inline GlyphBuffer DrawGlyphs::generateGlyphBuffer() const
</span><span class="cx"> {
</span><span class="cx">     GlyphBuffer result;
</span><span class="cx">     for (size_t i = 0; i < m_glyphs.size(); ++i)
</span><del>-        result.add(m_glyphs[i], m_font.get(), m_advances[i], GlyphBuffer::noOffset);
</del><ins>+        result.add(m_glyphs[i], *m_font, m_advances[i], GlyphBuffer::noOffset);
</ins><span class="cx">     return result;
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void DrawGlyphs::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><del>-    context.drawGlyphs(m_font, generateGlyphBuffer(), 0, m_glyphs.size(), anchorPoint(), m_smoothingMode);
</del><ins>+    context.drawGlyphs(*m_font, generateGlyphBuffer(), 0, m_glyphs.size(), anchorPoint(), m_smoothingMode);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void DrawGlyphs::computeBounds()
</span><span class="lines">@@ -735,14 +394,8 @@
</span><span class="cx">     }
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-Optional<FloatRect> DrawGlyphs::localBounds(const GraphicsContext&) const
-{
-    return m_bounds;
-}
-
</del><span class="cx"> static TextStream& operator<<(TextStream& ts, const DrawGlyphs& item)
</span><span class="cx"> {
</span><del>-    ts << static_cast<const DrawingItem&>(item);
</del><span class="cx">     // FIXME: dump more stuff.
</span><span class="cx">     ts.dumpProperty("local-anchor", item.localAnchor());
</span><span class="cx">     ts.dumpProperty("anchor-point", item.anchorPoint());
</span><span class="lines">@@ -751,17 +404,6 @@
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-DrawImage::DrawImage(Image& image, const FloatRect& destination, const FloatRect& source, const ImagePaintingOptions& imagePaintingOptions)
-    : DrawingItem(ItemType::DrawImage)
-    , m_image(image)
-    , m_destination(destination)
-    , m_source(source)
-    , m_imagePaintingOptions(imagePaintingOptions)
-{
-}
-
-DrawImage::~DrawImage() = default;
-
</del><span class="cx"> void DrawImage::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.drawImage(m_image.get(), m_destination, m_source, m_imagePaintingOptions);
</span><span class="lines">@@ -769,7 +411,6 @@
</span><span class="cx"> 
</span><span class="cx"> static TextStream& operator<<(TextStream& ts, const DrawImage& item)
</span><span class="cx"> {
</span><del>-    ts << static_cast<const DrawingItem&>(item);
</del><span class="cx">     ts.dumpProperty("image", item.image());
</span><span class="cx">     ts.dumpProperty("source-rect", item.source());
</span><span class="cx">     ts.dumpProperty("dest-rect", item.destination());
</span><span class="lines">@@ -776,19 +417,6 @@
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-DrawTiledImage::DrawTiledImage(Image& image, const FloatRect& destination, const FloatPoint& source, const FloatSize& tileSize, const FloatSize& spacing, const ImagePaintingOptions& imagePaintingOptions)
-    : DrawingItem(ItemType::DrawTiledImage)
-    , m_image(image)
-    , m_destination(destination)
-    , m_source(source)
-    , m_tileSize(tileSize)
-    , m_spacing(spacing)
-    , m_imagePaintingOptions(imagePaintingOptions)
-{
-}
-
-DrawTiledImage::~DrawTiledImage() = default;
-
</del><span class="cx"> void DrawTiledImage::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.drawTiledImage(m_image.get(), m_destination, m_source, m_tileSize, m_spacing, m_imagePaintingOptions);
</span><span class="lines">@@ -796,7 +424,6 @@
</span><span class="cx"> 
</span><span class="cx"> static TextStream& operator<<(TextStream& ts, const DrawTiledImage& item)
</span><span class="cx"> {
</span><del>-    ts << static_cast<const DrawingItem&>(item);
</del><span class="cx">     ts.dumpProperty("image", item.image());
</span><span class="cx">     ts.dumpProperty("source-point", item.source());
</span><span class="cx">     ts.dumpProperty("dest-rect", item.destination());
</span><span class="lines">@@ -805,20 +432,6 @@
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-DrawTiledScaledImage::DrawTiledScaledImage(Image& image, const FloatRect& destination, const FloatRect& source, const FloatSize& tileScaleFactor, Image::TileRule hRule, Image::TileRule vRule, const ImagePaintingOptions& imagePaintingOptions)
-    : DrawingItem(ItemType::DrawTiledScaledImage)
-    , m_image(image)
-    , m_destination(destination)
-    , m_source(source)
-    , m_tileScaleFactor(tileScaleFactor)
-    , m_hRule(hRule)
-    , m_vRule(vRule)
-    , m_imagePaintingOptions(imagePaintingOptions)
-{
-}
-
-DrawTiledScaledImage::~DrawTiledScaledImage() = default;
-
</del><span class="cx"> void DrawTiledScaledImage::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.drawTiledImage(m_image.get(), m_destination, m_source, m_tileScaleFactor, m_hRule, m_vRule, m_imagePaintingOptions);
</span><span class="lines">@@ -826,7 +439,6 @@
</span><span class="cx"> 
</span><span class="cx"> static TextStream& operator<<(TextStream& ts, const DrawTiledScaledImage& item)
</span><span class="cx"> {
</span><del>-    ts << static_cast<const DrawingItem&>(item);
</del><span class="cx">     ts.dumpProperty("image", item.image());
</span><span class="cx">     ts.dumpProperty("source-rect", item.source());
</span><span class="cx">     ts.dumpProperty("dest-rect", item.destination());
</span><span class="lines">@@ -833,20 +445,8 @@
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-DrawImageBuffer::DrawImageBuffer(RenderingResourceIdentifier renderingResourceIdentifier, const FloatRect& destRect, const FloatRect& srcRect, const ImagePaintingOptions& options)
-    : DrawingItem(ItemType::DrawImageBuffer)
-    , m_renderingResourceIdentifier(renderingResourceIdentifier)
-    , m_destinationRect(destRect)
-    , m_srcRect(srcRect)
-    , m_options(options)
</del><ins>+NO_RETURN_DUE_TO_ASSERT void DrawImageBuffer::apply(GraphicsContext&) const
</ins><span class="cx"> {
</span><del>-    ASSERT(m_renderingResourceIdentifier);
-}
-
-DrawImageBuffer::~DrawImageBuffer() = default;
-
-void DrawImageBuffer::apply(GraphicsContext&) const
-{
</del><span class="cx">     ASSERT_NOT_REACHED();
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="lines">@@ -857,8 +457,7 @@
</span><span class="cx"> 
</span><span class="cx"> static TextStream& operator<<(TextStream& ts, const DrawImageBuffer& item)
</span><span class="cx"> {
</span><del>-    ts << static_cast<const DrawingItem&>(item);
-    ts.dumpProperty("remote-resource-identifier", item.renderingResourceIdentifier());
</del><ins>+    ts.dumpProperty("rendering-resource-identifier", item.renderingResourceIdentifier());
</ins><span class="cx">     ts.dumpProperty("source-rect", item.source());
</span><span class="cx">     ts.dumpProperty("dest-rect", item.destinationRect());
</span><span class="cx">     return ts;
</span><span class="lines">@@ -865,8 +464,7 @@
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> DrawNativeImage::DrawNativeImage(const NativeImagePtr& image, const FloatSize& imageSize, const FloatRect& destRect, const FloatRect& srcRect, const ImagePaintingOptions& options)
</span><del>-    : DrawingItem(ItemType::DrawNativeImage)
-    , m_image(image)
</del><ins>+    : m_image(image)
</ins><span class="cx">     , m_imageSize(imageSize)
</span><span class="cx">     , m_destinationRect(destRect)
</span><span class="cx">     , m_srcRect(srcRect)
</span><span class="lines">@@ -874,8 +472,6 @@
</span><span class="cx"> {
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-DrawNativeImage::~DrawNativeImage() = default;
-
</del><span class="cx"> void DrawNativeImage::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.drawNativeImage(m_image, m_imageSize, m_destinationRect, m_srcRect, m_options);
</span><span class="lines">@@ -883,7 +479,6 @@
</span><span class="cx"> 
</span><span class="cx"> static TextStream& operator<<(TextStream& ts, const DrawNativeImage& item)
</span><span class="cx"> {
</span><del>-    ts << static_cast<const DrawingItem&>(item);
</del><span class="cx">     // FIXME: dump more stuff.
</span><span class="cx">     ts.dumpProperty("source-rect", item.source());
</span><span class="cx">     ts.dumpProperty("dest-rect", item.destinationRect());
</span><span class="lines">@@ -891,8 +486,7 @@
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> DrawPattern::DrawPattern(Image& image, const FloatRect& destRect, const FloatRect& tileRect, const AffineTransform& patternTransform, const FloatPoint& phase, const FloatSize& spacing, const ImagePaintingOptions& options)
</span><del>-    : DrawingItem(ItemType::DrawPattern)
-    , m_image(image)
</del><ins>+    : m_image(image)
</ins><span class="cx">     , m_patternTransform(patternTransform)
</span><span class="cx">     , m_tileRect(tileRect)
</span><span class="cx">     , m_destination(destRect)
</span><span class="lines">@@ -902,8 +496,6 @@
</span><span class="cx"> {
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-DrawPattern::~DrawPattern() = default;
-
</del><span class="cx"> void DrawPattern::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.drawPattern(m_image.get(), m_destination, m_tileRect, m_patternTransform, m_phase, m_spacing, m_options);
</span><span class="lines">@@ -911,7 +503,6 @@
</span><span class="cx"> 
</span><span class="cx"> static TextStream& operator<<(TextStream& ts, const DrawPattern& item)
</span><span class="cx"> {
</span><del>-    ts << static_cast<const DrawingItem&>(item);
</del><span class="cx">     ts.dumpProperty("image", item.image());
</span><span class="cx">     ts.dumpProperty("pattern-transform", item.patternTransform());
</span><span class="cx">     ts.dumpProperty("tile-rect", item.tileRect());
</span><span class="lines">@@ -921,15 +512,6 @@
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-DrawRect::DrawRect(const FloatRect& rect, float borderThickness)
-    : DrawingItem(ItemType::DrawRect)
-    , m_rect(rect)
-    , m_borderThickness(borderThickness)
-{
-}
-
-DrawRect::~DrawRect() = default;
-
</del><span class="cx"> void DrawRect::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.drawRect(m_rect, m_borderThickness);
</span><span class="lines">@@ -937,21 +519,11 @@
</span><span class="cx"> 
</span><span class="cx"> static TextStream& operator<<(TextStream& ts, const DrawRect& item)
</span><span class="cx"> {
</span><del>-    ts << static_cast<const DrawingItem&>(item);
</del><span class="cx">     ts.dumpProperty("rect", item.rect());
</span><span class="cx">     ts.dumpProperty("border-thickness", item.borderThickness());
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-DrawLine::DrawLine(const FloatPoint& point1, const FloatPoint& point2)
-    : DrawingItem(ItemType::DrawLine)
-    , m_point1(point1)
-    , m_point2(point2)
-{
-}
-
-DrawLine::~DrawLine() = default;
-
</del><span class="cx"> Optional<FloatRect> DrawLine::localBounds(const GraphicsContext&) const
</span><span class="cx"> {
</span><span class="cx">     FloatRect bounds;
</span><span class="lines">@@ -966,7 +538,6 @@
</span><span class="cx"> 
</span><span class="cx"> static TextStream& operator<<(TextStream& ts, const DrawLine& item)
</span><span class="cx"> {
</span><del>-    ts << static_cast<const DrawingItem&>(item);
</del><span class="cx">     ts.dumpProperty("point-1", item.point1());
</span><span class="cx">     ts.dumpProperty("point-2", item.point2());
</span><span class="cx">     return ts;
</span><span class="lines">@@ -973,8 +544,7 @@
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> DrawLinesForText::DrawLinesForText(const FloatPoint& blockLocation, const FloatSize& localAnchor, float thickness, const DashArray& widths, bool printing, bool doubleLines)
</span><del>-    : DrawingItem(ItemType::DrawLinesForText)
-    , m_blockLocation(blockLocation)
</del><ins>+    : m_blockLocation(blockLocation)
</ins><span class="cx">     , m_localAnchor(localAnchor)
</span><span class="cx">     , m_widths(widths)
</span><span class="cx">     , m_thickness(thickness)
</span><span class="lines">@@ -983,8 +553,6 @@
</span><span class="cx"> {
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-DrawLinesForText::~DrawLinesForText() = default;
-
</del><span class="cx"> void DrawLinesForText::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.drawLinesForText(point(), m_thickness, m_widths, m_printing, m_doubleLines);
</span><span class="lines">@@ -1004,7 +572,6 @@
</span><span class="cx"> 
</span><span class="cx"> static TextStream& operator<<(TextStream& ts, const DrawLinesForText& item)
</span><span class="cx"> {
</span><del>-    ts << static_cast<const DrawingItem&>(item);
</del><span class="cx">     ts.dumpProperty("block-location", item.blockLocation());
</span><span class="cx">     ts.dumpProperty("local-anchor", item.localAnchor());
</span><span class="cx">     ts.dumpProperty("point", item.point());
</span><span class="lines">@@ -1016,15 +583,6 @@
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-DrawDotsForDocumentMarker::DrawDotsForDocumentMarker(const FloatRect& rect, DocumentMarkerLineStyle style)
-    : DrawingItem(ItemType::DrawDotsForDocumentMarker)
-    , m_rect(rect)
-    , m_style(style)
-{
-}
-
-DrawDotsForDocumentMarker::~DrawDotsForDocumentMarker() = default;
-
</del><span class="cx"> void DrawDotsForDocumentMarker::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.drawDotsForDocumentMarker(m_rect, m_style);
</span><span class="lines">@@ -1037,19 +595,10 @@
</span><span class="cx"> 
</span><span class="cx"> static TextStream& operator<<(TextStream& ts, const DrawDotsForDocumentMarker& item)
</span><span class="cx"> {
</span><del>-    ts << static_cast<const DrawingItem&>(item);
</del><span class="cx">     ts.dumpProperty("rect", item.rect());
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-DrawEllipse::DrawEllipse(const FloatRect& rect)
-    : DrawingItem(ItemType::DrawEllipse)
-    , m_rect(rect)
-{
-}
-
-DrawEllipse::~DrawEllipse() = default;
-
</del><span class="cx"> void DrawEllipse::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.drawEllipse(m_rect);
</span><span class="lines">@@ -1061,14 +610,6 @@
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-DrawPath::DrawPath(const Path& path)
-    : DrawingItem(ItemType::DrawPath)
-    , m_path(path)
-{
-}
-
-DrawPath::~DrawPath() = default;
-
</del><span class="cx"> void DrawPath::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx"> #if USE(CG)
</span><span class="lines">@@ -1078,24 +619,12 @@
</span><span class="cx"> #endif
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-static TextStream& operator<<(TextStream& ts, const DrawPath& item)
</del><ins>+static TextStream& operator<<(TextStream& ts, const DrawPath&)
</ins><span class="cx"> {
</span><del>-    ts << static_cast<const DrawingItem&>(item);
-//    ts.dumpProperty("path", item.path()); // FIXME: add logging for paths.
</del><ins>+    // FIXME: add logging for paths.
</ins><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-DrawFocusRingPath::DrawFocusRingPath(const Path& path, float width, float offset, const Color& color)
-    : DrawingItem(ItemType::DrawFocusRingPath)
-    , m_path(path)
-    , m_width(width)
-    , m_offset(offset)
-    , m_color(color)
-{
-}
-
-DrawFocusRingPath::~DrawFocusRingPath() = default;
-
</del><span class="cx"> void DrawFocusRingPath::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.drawFocusRing(m_path, m_width, m_offset, m_color);
</span><span class="lines">@@ -1110,7 +639,6 @@
</span><span class="cx"> 
</span><span class="cx"> static TextStream& operator<<(TextStream& ts, const DrawFocusRingPath& item)
</span><span class="cx"> {
</span><del>-    ts << static_cast<const DrawingItem&>(item);
</del><span class="cx"> //    ts.dumpProperty("path", item.path()); // FIXME: add logging for paths.
</span><span class="cx">     ts.dumpProperty("width", item.width());
</span><span class="cx">     ts.dumpProperty("offset", item.offset());
</span><span class="lines">@@ -1119,8 +647,7 @@
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> DrawFocusRingRects::DrawFocusRingRects(const Vector<FloatRect>& rects, float width, float offset, const Color& color)
</span><del>-    : DrawingItem(ItemType::DrawFocusRingRects)
-    , m_rects(rects)
</del><ins>+    : m_rects(rects)
</ins><span class="cx">     , m_width(width)
</span><span class="cx">     , m_offset(offset)
</span><span class="cx">     , m_color(color)
</span><span class="lines">@@ -1127,8 +654,6 @@
</span><span class="cx"> {
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-DrawFocusRingRects::~DrawFocusRingRects() = default;
-
</del><span class="cx"> void DrawFocusRingRects::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.drawFocusRing(m_rects, m_width, m_offset, m_color);
</span><span class="lines">@@ -1145,7 +670,6 @@
</span><span class="cx"> 
</span><span class="cx"> static TextStream& operator<<(TextStream& ts, const DrawFocusRingRects& item)
</span><span class="cx"> {
</span><del>-    ts << static_cast<const DrawingItem&>(item);
</del><span class="cx">     ts.dumpProperty("rects", item.rects());
</span><span class="cx">     ts.dumpProperty("width", item.width());
</span><span class="cx">     ts.dumpProperty("offset", item.offset());
</span><span class="lines">@@ -1153,14 +677,6 @@
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-FillRect::FillRect(const FloatRect& rect)
-    : DrawingItem(ItemType::FillRect)
-    , m_rect(rect)
-{
-}
-
-FillRect::~FillRect() = default;
-
</del><span class="cx"> void FillRect::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.fillRect(m_rect);
</span><span class="lines">@@ -1168,20 +684,10 @@
</span><span class="cx"> 
</span><span class="cx"> static TextStream& operator<<(TextStream& ts, const FillRect& item)
</span><span class="cx"> {
</span><del>-    ts << static_cast<const DrawingItem&>(item);
</del><span class="cx">     ts.dumpProperty("rect", item.rect());
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-FillRectWithColor::FillRectWithColor(const FloatRect& rect, const Color& color)
-    : DrawingItem(ItemType::FillRectWithColor)
-    , m_rect(rect)
-    , m_color(color)
-{
-}
-
-FillRectWithColor::~FillRectWithColor() = default;
-
</del><span class="cx"> void FillRectWithColor::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.fillRect(m_rect, m_color);
</span><span class="lines">@@ -1189,7 +695,6 @@
</span><span class="cx"> 
</span><span class="cx"> static TextStream& operator<<(TextStream& ts, const FillRectWithColor& item)
</span><span class="cx"> {
</span><del>-    ts << static_cast<const DrawingItem&>(item);
</del><span class="cx">     ts.dumpProperty("rect", item.rect());
</span><span class="cx">     ts.dumpProperty("color", item.color());
</span><span class="cx">     return ts;
</span><span class="lines">@@ -1196,14 +701,11 @@
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> FillRectWithGradient::FillRectWithGradient(const FloatRect& rect, Gradient& gradient)
</span><del>-    : DrawingItem(ItemType::FillRectWithGradient)
-    , m_rect(rect)
</del><ins>+    : m_rect(rect)
</ins><span class="cx">     , m_gradient(gradient)
</span><span class="cx"> {
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-FillRectWithGradient::~FillRectWithGradient() = default;
-
</del><span class="cx"> void FillRectWithGradient::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.fillRect(m_rect, m_gradient.get());
</span><span class="lines">@@ -1211,23 +713,11 @@
</span><span class="cx"> 
</span><span class="cx"> static TextStream& operator<<(TextStream& ts, const FillRectWithGradient& item)
</span><span class="cx"> {
</span><del>-    ts << static_cast<const DrawingItem&>(item);
</del><span class="cx">     // FIXME: log gradient.
</span><span class="cx">     ts.dumpProperty("rect", item.rect());
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-FillCompositedRect::FillCompositedRect(const FloatRect& rect, const Color& color, CompositeOperator op, BlendMode blendMode)
-    : DrawingItem(ItemType::FillCompositedRect)
-    , m_rect(rect)
-    , m_color(color)
-    , m_op(op)
-    , m_blendMode(blendMode)
-{
-}
-
-FillCompositedRect::~FillCompositedRect() = default;
-
</del><span class="cx"> void FillCompositedRect::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.fillRect(m_rect, m_color, m_op, m_blendMode);
</span><span class="lines">@@ -1235,7 +725,6 @@
</span><span class="cx"> 
</span><span class="cx"> static TextStream& operator<<(TextStream& ts, const FillCompositedRect& item)
</span><span class="cx"> {
</span><del>-    ts << static_cast<const DrawingItem&>(item);
</del><span class="cx">     ts.dumpProperty("rect", item.rect());
</span><span class="cx">     ts.dumpProperty("color", item.color());
</span><span class="cx">     ts.dumpProperty("composite-operation", item.compositeOperator());
</span><span class="lines">@@ -1243,16 +732,6 @@
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-FillRoundedRect::FillRoundedRect(const FloatRoundedRect& rect, const Color& color, BlendMode blendMode)
-    : DrawingItem(ItemType::FillRoundedRect)
-    , m_rect(rect)
-    , m_color(color)
-    , m_blendMode(blendMode)
-{
-}
-
-FillRoundedRect::~FillRoundedRect() = default;
-
</del><span class="cx"> void FillRoundedRect::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.fillRoundedRect(m_rect, m_color, m_blendMode);
</span><span class="lines">@@ -1260,7 +739,6 @@
</span><span class="cx"> 
</span><span class="cx"> static TextStream& operator<<(TextStream& ts, const FillRoundedRect& item)
</span><span class="cx"> {
</span><del>-    ts << static_cast<const DrawingItem&>(item);
</del><span class="cx">     ts.dumpProperty("rect", item.roundedRect());
</span><span class="cx">     ts.dumpProperty("color", item.color());
</span><span class="cx">     ts.dumpProperty("blend-mode", item.blendMode());
</span><span class="lines">@@ -1267,16 +745,6 @@
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-FillRectWithRoundedHole::FillRectWithRoundedHole(const FloatRect& rect, const FloatRoundedRect& roundedHoleRect, const Color& color)
-    : DrawingItem(ItemType::FillRectWithRoundedHole)
-    , m_rect(rect)
-    , m_roundedHoleRect(roundedHoleRect)
-    , m_color(color)
-{
-}
-
-FillRectWithRoundedHole::~FillRectWithRoundedHole() = default;
-
</del><span class="cx"> void FillRectWithRoundedHole::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.fillRectWithRoundedHole(m_rect, m_roundedHoleRect, m_color);
</span><span class="lines">@@ -1284,7 +752,6 @@
</span><span class="cx"> 
</span><span class="cx"> static TextStream& operator<<(TextStream& ts, const FillRectWithRoundedHole& item)
</span><span class="cx"> {
</span><del>-    ts << static_cast<const DrawingItem&>(item);
</del><span class="cx">     ts.dumpProperty("rect", item.rect());
</span><span class="cx">     ts.dumpProperty("rounded-hole-rect", item.roundedHoleRect());
</span><span class="cx">     ts.dumpProperty("color", item.color());
</span><span class="lines">@@ -1293,14 +760,6 @@
</span><span class="cx"> 
</span><span class="cx"> #if ENABLE(INLINE_PATH_DATA)
</span><span class="cx"> 
</span><del>-FillInlinePath::FillInlinePath(const InlinePathData& pathData)
-    : DrawingItem(ItemType::FillInlinePath)
-    , m_pathData(pathData)
-{
-}
-
-FillInlinePath::~FillInlinePath() = default;
-
</del><span class="cx"> void FillInlinePath::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.fillPath(path());
</span><span class="lines">@@ -1308,7 +767,6 @@
</span><span class="cx"> 
</span><span class="cx"> static TextStream& operator<<(TextStream& ts, const FillInlinePath& item)
</span><span class="cx"> {
</span><del>-    ts << static_cast<const DrawingItem&>(item);
</del><span class="cx">     ts.dumpProperty("path", item.path());
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="lines">@@ -1315,14 +773,6 @@
</span><span class="cx"> 
</span><span class="cx"> #endif // ENABLE(INLINE_PATH_DATA)
</span><span class="cx"> 
</span><del>-FillPath::FillPath(const Path& path)
-    : DrawingItem(ItemType::FillPath)
-    , m_path(path)
-{
-}
-
-FillPath::~FillPath() = default;
-
</del><span class="cx"> void FillPath::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.fillPath(m_path);
</span><span class="lines">@@ -1330,19 +780,10 @@
</span><span class="cx"> 
</span><span class="cx"> static TextStream& operator<<(TextStream& ts, const FillPath& item)
</span><span class="cx"> {
</span><del>-    ts << static_cast<const DrawingItem&>(item);
</del><span class="cx">     ts.dumpProperty("path", item.path());
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-FillEllipse::FillEllipse(const FloatRect& rect)
-    : DrawingItem(ItemType::FillEllipse)
-    , m_rect(rect)
-{
-}
-
-FillEllipse::~FillEllipse() = default;
-
</del><span class="cx"> void FillEllipse::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.fillEllipse(m_rect);
</span><span class="lines">@@ -1350,14 +791,12 @@
</span><span class="cx"> 
</span><span class="cx"> static TextStream& operator<<(TextStream& ts, const FillEllipse& item)
</span><span class="cx"> {
</span><del>-    ts << static_cast<const DrawingItem&>(item);
</del><span class="cx">     ts.dumpProperty("rect", item.rect());
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> PutImageData::PutImageData(AlphaPremultiplication inputFormat, const ImageData& imageData, const IntRect& srcRect, const IntPoint& destPoint, AlphaPremultiplication destFormat)
</span><del>-    : DrawingItem(ItemType::PutImageData)
-    , m_srcRect(srcRect)
</del><ins>+    : m_srcRect(srcRect)
</ins><span class="cx">     , m_destPoint(destPoint)
</span><span class="cx">     , m_imageData(imageData.deepClone()) // This copy is actually required to preserve the semantics of putImageData().
</span><span class="cx">     , m_inputFormat(inputFormat)
</span><span class="lines">@@ -1366,8 +805,7 @@
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> PutImageData::PutImageData(AlphaPremultiplication inputFormat, Ref<ImageData>&& imageData, const IntRect& srcRect, const IntPoint& destPoint, AlphaPremultiplication destFormat)
</span><del>-    : DrawingItem(ItemType::PutImageData)
-    , m_srcRect(srcRect)
</del><ins>+    : m_srcRect(srcRect)
</ins><span class="cx">     , m_destPoint(destPoint)
</span><span class="cx">     , m_imageData(WTFMove(imageData))
</span><span class="cx">     , m_inputFormat(inputFormat)
</span><span class="lines">@@ -1375,9 +813,7 @@
</span><span class="cx"> {
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-PutImageData::~PutImageData() = default;
-
-void PutImageData::apply(GraphicsContext&) const
</del><ins>+NO_RETURN_DUE_TO_ASSERT void PutImageData::apply(GraphicsContext&) const
</ins><span class="cx"> {
</span><span class="cx">     // Should be handled by the delegate.
</span><span class="cx">     ASSERT_NOT_REACHED();
</span><span class="lines">@@ -1385,7 +821,6 @@
</span><span class="cx"> 
</span><span class="cx"> static TextStream& operator<<(TextStream& ts, const PutImageData& item)
</span><span class="cx"> {
</span><del>-    ts << static_cast<const DrawingItem&>(item);
</del><span class="cx">     ts.dumpProperty("inputFormat", item.inputFormat());
</span><span class="cx">     ts.dumpProperty("imageDataSize", item.imageData().size());
</span><span class="cx">     ts.dumpProperty("srcRect", item.srcRect());
</span><span class="lines">@@ -1394,34 +829,14 @@
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-Ref<PaintFrameForMedia> PaintFrameForMedia::create(MediaPlayer& player, const FloatRect& destination)
-{
-    return adoptRef(*new PaintFrameForMedia(player, destination));
-}
-
-Ref<PaintFrameForMedia> PaintFrameForMedia::create(MediaPlayerIdentifier identifier, const FloatRect& destination)
-{
-    return adoptRef(*new PaintFrameForMedia(identifier, destination));
-}
-
</del><span class="cx"> PaintFrameForMedia::PaintFrameForMedia(MediaPlayer& player, const FloatRect& destination)
</span><del>-    : DrawingItem(ItemType::PaintFrameForMedia)
-    , m_identifier(player.identifier())
</del><ins>+    : m_identifier(player.identifier())
</ins><span class="cx">     , m_destination(destination)
</span><span class="cx"> {
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-PaintFrameForMedia::PaintFrameForMedia(MediaPlayerIdentifier identifier, const FloatRect& destination)
-    : DrawingItem(ItemType::PaintFrameForMedia)
-    , m_identifier(identifier)
-    , m_destination(destination)
</del><ins>+NO_RETURN_DUE_TO_ASSERT void PaintFrameForMedia::apply(GraphicsContext&) const
</ins><span class="cx"> {
</span><del>-}
-
-PaintFrameForMedia::~PaintFrameForMedia() = default;
-
-void PaintFrameForMedia::apply(GraphicsContext&) const
-{
</del><span class="cx">     // Should be handled by the delegate.
</span><span class="cx">     ASSERT_NOT_REACHED();
</span><span class="cx"> }
</span><span class="lines">@@ -1428,20 +843,10 @@
</span><span class="cx"> 
</span><span class="cx"> static TextStream& operator<<(TextStream& ts, const PaintFrameForMedia& item)
</span><span class="cx"> {
</span><del>-    ts << static_cast<const DrawingItem&>(item);
</del><span class="cx">     ts.dumpProperty("destination", item.destination());
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-StrokeRect::StrokeRect(const FloatRect& rect, float lineWidth)
-    : DrawingItem(ItemType::StrokeRect)
-    , m_rect(rect)
-    , m_lineWidth(lineWidth)
-{
-}
-
-StrokeRect::~StrokeRect() = default;
-
</del><span class="cx"> Optional<FloatRect> StrokeRect::localBounds(const GraphicsContext&) const
</span><span class="cx"> {
</span><span class="cx">     FloatRect bounds = m_rect;
</span><span class="lines">@@ -1456,7 +861,6 @@
</span><span class="cx"> 
</span><span class="cx"> static TextStream& operator<<(TextStream& ts, const StrokeRect& item)
</span><span class="cx"> {
</span><del>-    ts << static_cast<const DrawingItem&>(item);
</del><span class="cx">     ts.dumpProperty("rect", item.rect());
</span><span class="cx">     ts.dumpProperty("line-width", item.lineWidth());
</span><span class="cx">     return ts;
</span><span class="lines">@@ -1479,19 +883,10 @@
</span><span class="cx"> 
</span><span class="cx"> static TextStream& operator<<(TextStream& ts, const StrokePath& item)
</span><span class="cx"> {
</span><del>-    ts << static_cast<const DrawingItem&>(item);
</del><span class="cx">     ts.dumpProperty("path", item.path());
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-StrokeEllipse::StrokeEllipse(const FloatRect& rect)
-    : DrawingItem(ItemType::StrokeEllipse)
-    , m_rect(rect)
-{
-}
-
-StrokeEllipse::~StrokeEllipse() = default;
-
</del><span class="cx"> Optional<FloatRect> StrokeEllipse::localBounds(const GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     float strokeThickness = context.strokeThickness();
</span><span class="lines">@@ -1508,7 +903,6 @@
</span><span class="cx"> 
</span><span class="cx"> static TextStream& operator<<(TextStream& ts, const StrokeEllipse& item)
</span><span class="cx"> {
</span><del>-    ts << static_cast<const DrawingItem&>(item);
</del><span class="cx">     ts.dumpProperty("rect", item.rect());
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="lines">@@ -1532,37 +926,12 @@
</span><span class="cx"> 
</span><span class="cx"> static TextStream& operator<<(TextStream& ts, const StrokeInlinePath& item)
</span><span class="cx"> {
</span><del>-    ts << static_cast<const DrawingItem&>(item);
</del><span class="cx">     ts.dumpProperty("path", item.path());
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-StrokeInlinePath::StrokeInlinePath(const InlinePathData& pathData)
-    : DrawingItem(ItemType::StrokeInlinePath)
-    , m_pathData(pathData)
-{
-}
-
-StrokeInlinePath::~StrokeInlinePath() = default;
-
</del><span class="cx"> #endif // ENABLE(INLINE_PATH_DATA)
</span><span class="cx"> 
</span><del>-StrokePath::StrokePath(const Path& path)
-    : DrawingItem(ItemType::StrokePath)
-    , m_path(path)
-{
-}
-
-StrokePath::~StrokePath() = default;
-
-ClearRect::ClearRect(const FloatRect& rect)
-    : DrawingItem(ItemType::ClearRect)
-    , m_rect(rect)
-{
-}
-
-ClearRect::~ClearRect() = default;
-
</del><span class="cx"> void ClearRect::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.clearRect(m_rect);
</span><span class="lines">@@ -1570,19 +939,10 @@
</span><span class="cx"> 
</span><span class="cx"> static TextStream& operator<<(TextStream& ts, const ClearRect& item)
</span><span class="cx"> {
</span><del>-    ts << static_cast<const DrawingItem&>(item);
</del><span class="cx">     ts.dumpProperty("rect", item.rect());
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-BeginTransparencyLayer::BeginTransparencyLayer(float opacity)
-    : DrawingItem(ItemType::BeginTransparencyLayer)
-    , m_opacity(opacity)
-{
-}
-
-BeginTransparencyLayer::~BeginTransparencyLayer() = default;
-
</del><span class="cx"> void BeginTransparencyLayer::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.beginTransparencyLayer(m_opacity);
</span><span class="lines">@@ -1590,18 +950,10 @@
</span><span class="cx"> 
</span><span class="cx"> static TextStream& operator<<(TextStream& ts, const BeginTransparencyLayer& item)
</span><span class="cx"> {
</span><del>-    ts << static_cast<const DrawingItem&>(item);
</del><span class="cx">     ts.dumpProperty("opacity", item.opacity());
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-EndTransparencyLayer::EndTransparencyLayer()
-    : DrawingItem(ItemType::EndTransparencyLayer)
-{
-}
-
-EndTransparencyLayer::~EndTransparencyLayer() = default;
-
</del><span class="cx"> void EndTransparencyLayer::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.endTransparencyLayer();
</span><span class="lines">@@ -1608,25 +960,12 @@
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> #if USE(CG)
</span><del>-ApplyStrokePattern::ApplyStrokePattern()
-    : Item(ItemType::ApplyStrokePattern)
-{
-}
</del><span class="cx"> 
</span><del>-ApplyStrokePattern::~ApplyStrokePattern() = default;
-
</del><span class="cx"> void ApplyStrokePattern::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.applyStrokePattern();
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-ApplyFillPattern::ApplyFillPattern()
-    : Item(ItemType::ApplyFillPattern)
-{
-}
-
-ApplyFillPattern::~ApplyFillPattern() = default;
-
</del><span class="cx"> void ApplyFillPattern::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.applyFillPattern();
</span><span class="lines">@@ -1633,14 +972,6 @@
</span><span class="cx"> }
</span><span class="cx"> #endif
</span><span class="cx"> 
</span><del>-ApplyDeviceScaleFactor::ApplyDeviceScaleFactor(float scaleFactor)
-    : Item(ItemType::ApplyDeviceScaleFactor)
-    , m_scaleFactor(scaleFactor)
-{
-}
-
-ApplyDeviceScaleFactor::~ApplyDeviceScaleFactor() = default;
-
</del><span class="cx"> void ApplyDeviceScaleFactor::apply(GraphicsContext& context) const
</span><span class="cx"> {
</span><span class="cx">     context.applyDeviceScaleFactor(m_scaleFactor);
</span><span class="lines">@@ -1652,7 +983,7 @@
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-static TextStream& operator<<(TextStream& ts, const ItemType& type)
</del><ins>+static TextStream& operator<<(TextStream& ts, ItemType type)
</ins><span class="cx"> {
</span><span class="cx">     switch (type) {
</span><span class="cx">     case ItemType::Save: ts << "save"; break;
</span><span class="lines">@@ -1723,172 +1054,170 @@
</span><span class="cx">     return ts;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-TextStream& operator<<(TextStream& ts, const Item& item)
</del><ins>+TextStream& operator<<(TextStream& ts, ItemHandle item)
</ins><span class="cx"> {
</span><del>-    TextStream::GroupScope group(ts);
</del><span class="cx">     ts << item.type();
</span><span class="cx"> 
</span><del>-    // FIXME: Make a macro which takes a macro for all these enumeration switches
</del><span class="cx">     switch (item.type()) {
</span><span class="cx">     case ItemType::Translate:
</span><del>-        ts << downcast<Translate>(item);
</del><ins>+        ts << item.get<Translate>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::Rotate:
</span><del>-        ts << downcast<Rotate>(item);
</del><ins>+        ts << item.get<Rotate>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::Scale:
</span><del>-        ts << downcast<Scale>(item);
</del><ins>+        ts << item.get<Scale>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::SetCTM:
</span><del>-        ts << downcast<SetCTM>(item);
</del><ins>+        ts << item.get<SetCTM>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::ConcatenateCTM:
</span><del>-        ts << downcast<ConcatenateCTM>(item);
</del><ins>+        ts << item.get<ConcatenateCTM>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::SetInlineFillGradient:
</span><del>-        ts << downcast<SetInlineFillGradient>(item);
</del><ins>+        ts << item.get<SetInlineFillGradient>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::SetInlineFillColor:
</span><del>-        ts << downcast<SetInlineFillColor>(item);
</del><ins>+        ts << item.get<SetInlineFillColor>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::SetInlineStrokeColor:
</span><del>-        ts << downcast<SetInlineStrokeColor>(item);
</del><ins>+        ts << item.get<SetInlineStrokeColor>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::SetStrokeThickness:
</span><del>-        ts << downcast<SetStrokeThickness>(item);
</del><ins>+        ts << item.get<SetStrokeThickness>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::SetState:
</span><del>-        ts << downcast<SetState>(item);
</del><ins>+        ts << item.get<SetState>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::SetLineCap:
</span><del>-        ts << downcast<SetLineCap>(item);
</del><ins>+        ts << item.get<SetLineCap>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::SetLineDash:
</span><del>-        ts << downcast<SetLineDash>(item);
</del><ins>+        ts << item.get<SetLineDash>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::SetLineJoin:
</span><del>-        ts << downcast<SetLineJoin>(item);
</del><ins>+        ts << item.get<SetLineJoin>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::SetMiterLimit:
</span><del>-        ts << downcast<SetMiterLimit>(item);
</del><ins>+        ts << item.get<SetMiterLimit>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::Clip:
</span><del>-        ts << downcast<Clip>(item);
</del><ins>+        ts << item.get<Clip>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::ClipOut:
</span><del>-        ts << downcast<ClipOut>(item);
</del><ins>+        ts << item.get<ClipOut>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::ClipOutToPath:
</span><del>-        ts << downcast<ClipOutToPath>(item);
</del><ins>+        ts << item.get<ClipOutToPath>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::ClipPath:
</span><del>-        ts << downcast<ClipPath>(item);
</del><ins>+        ts << item.get<ClipPath>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::ClipToDrawingCommands:
</span><del>-        ts << downcast<ClipToDrawingCommands>(item);
</del><ins>+        ts << item.get<ClipToDrawingCommands>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::DrawGlyphs:
</span><del>-        ts << downcast<DrawGlyphs>(item);
</del><ins>+        ts << item.get<DrawGlyphs>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::DrawImage:
</span><del>-        ts << downcast<DrawImage>(item);
</del><ins>+        ts << item.get<DrawImage>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::DrawTiledImage:
</span><del>-        ts << downcast<DrawTiledImage>(item);
</del><ins>+        ts << item.get<DrawTiledImage>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::DrawTiledScaledImage:
</span><del>-        ts << downcast<DrawTiledScaledImage>(item);
</del><ins>+        ts << item.get<DrawTiledScaledImage>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::DrawImageBuffer:
</span><del>-        ts << downcast<DrawImageBuffer>(item);
</del><ins>+        ts << item.get<DrawImageBuffer>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::DrawNativeImage:
</span><del>-        ts << downcast<DrawNativeImage>(item);
</del><ins>+        ts << item.get<DrawNativeImage>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::DrawPattern:
</span><del>-        ts << downcast<DrawPattern>(item);
</del><ins>+        ts << item.get<DrawPattern>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::DrawRect:
</span><del>-        ts << downcast<DrawRect>(item);
</del><ins>+        ts << item.get<DrawRect>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::DrawLine:
</span><del>-        ts << downcast<DrawLine>(item);
</del><ins>+        ts << item.get<DrawLine>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::DrawLinesForText:
</span><del>-        ts << downcast<DrawLinesForText>(item);
</del><ins>+        ts << item.get<DrawLinesForText>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::DrawDotsForDocumentMarker:
</span><del>-        ts << downcast<DrawDotsForDocumentMarker>(item);
</del><ins>+        ts << item.get<DrawDotsForDocumentMarker>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::DrawEllipse:
</span><del>-        ts << downcast<DrawEllipse>(item);
</del><ins>+        ts << item.get<DrawEllipse>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::DrawPath:
</span><del>-        ts << downcast<DrawPath>(item);
</del><ins>+        ts << item.get<DrawPath>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::DrawFocusRingPath:
</span><del>-        ts << downcast<DrawFocusRingPath>(item);
</del><ins>+        ts << item.get<DrawFocusRingPath>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::DrawFocusRingRects:
</span><del>-        ts << downcast<DrawFocusRingRects>(item);
</del><ins>+        ts << item.get<DrawFocusRingRects>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::FillRect:
</span><del>-        ts << downcast<FillRect>(item);
</del><ins>+        ts << item.get<FillRect>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::FillRectWithColor:
</span><del>-        ts << downcast<FillRectWithColor>(item);
</del><ins>+        ts << item.get<FillRectWithColor>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::FillRectWithGradient:
</span><del>-        ts << downcast<FillRectWithGradient>(item);
</del><ins>+        ts << item.get<FillRectWithGradient>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::FillCompositedRect:
</span><del>-        ts << downcast<FillCompositedRect>(item);
</del><ins>+        ts << item.get<FillCompositedRect>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::FillRoundedRect:
</span><del>-        ts << downcast<FillRoundedRect>(item);
</del><ins>+        ts << item.get<FillRoundedRect>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::FillRectWithRoundedHole:
</span><del>-        ts << downcast<FillRectWithRoundedHole>(item);
</del><ins>+        ts << item.get<FillRectWithRoundedHole>();
</ins><span class="cx">         break;
</span><span class="cx"> #if ENABLE(INLINE_PATH_DATA)
</span><span class="cx">     case ItemType::FillInlinePath:
</span><del>-        ts << downcast<FillInlinePath>(item);
</del><ins>+        ts << item.get<FillInlinePath>();
</ins><span class="cx">         break;
</span><span class="cx"> #endif
</span><span class="cx">     case ItemType::FillPath:
</span><del>-        ts << downcast<FillPath>(item);
</del><ins>+        ts << item.get<FillPath>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::FillEllipse:
</span><del>-        ts << downcast<FillEllipse>(item);
</del><ins>+        ts << item.get<FillEllipse>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::PutImageData:
</span><del>-        ts << downcast<PutImageData>(item);
</del><ins>+        ts << item.get<PutImageData>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::PaintFrameForMedia:
</span><del>-        ts << downcast<PaintFrameForMedia>(item);
</del><ins>+        ts << item.get<PaintFrameForMedia>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::StrokeRect:
</span><del>-        ts << downcast<StrokeRect>(item);
</del><ins>+        ts << item.get<StrokeRect>();
</ins><span class="cx">         break;
</span><span class="cx"> #if ENABLE(INLINE_PATH_DATA)
</span><span class="cx">     case ItemType::StrokeInlinePath:
</span><del>-        ts << downcast<StrokeInlinePath>(item);
</del><ins>+        ts << item.get<StrokeInlinePath>();
</ins><span class="cx">         break;
</span><span class="cx"> #endif
</span><span class="cx">     case ItemType::StrokePath:
</span><del>-        ts << downcast<StrokePath>(item);
</del><ins>+        ts << item.get<StrokePath>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::StrokeEllipse:
</span><del>-        ts << downcast<StrokeEllipse>(item);
</del><ins>+        ts << item.get<StrokeEllipse>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::ClearRect:
</span><del>-        ts << downcast<ClearRect>(item);
</del><ins>+        ts << item.get<ClearRect>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::BeginTransparencyLayer:
</span><del>-        ts << downcast<BeginTransparencyLayer>(item);
</del><ins>+        ts << item.get<BeginTransparencyLayer>();
</ins><span class="cx">         break;
</span><span class="cx">     case ItemType::ApplyDeviceScaleFactor:
</span><del>-        ts << downcast<ApplyDeviceScaleFactor>(item);
</del><ins>+        ts << item.get<ApplyDeviceScaleFactor>();
</ins><span class="cx">         break;
</span><span class="cx"> 
</span><span class="cx">     // Items with no additional data.
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformgraphicsdisplaylistsDisplayListItemsh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/graphics/displaylists/DisplayListItems.h (269524 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/graphics/displaylists/DisplayListItems.h   2020-11-06 18:44:09 UTC (rev 269524)
+++ trunk/Source/WebCore/platform/graphics/displaylists/DisplayListItems.h      2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -51,320 +51,163 @@
</span><span class="cx"> 
</span><span class="cx"> namespace DisplayList {
</span><span class="cx"> 
</span><del>-class DrawingItem : public Item {
</del><ins>+class Save {
</ins><span class="cx"> public:
</span><del>-    WEBCORE_EXPORT explicit DrawingItem(ItemType);
</del><ins>+    static constexpr ItemType itemType = ItemType::Save;
+    static constexpr bool isInlineItem = true;
+    static constexpr bool isDrawingItem = false;
</ins><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~DrawingItem();
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><del>-    void setExtent(const FloatRect& r) { m_extent = r; }
-    const FloatRect& extent() const { return m_extent.value(); }
-
-    bool extentKnown() const { return static_cast<bool>(m_extent); }
-
-    // Return bounds of this drawing operation in local coordinates.
-    // Does not include effets of transform, shadow etc in the state.
-    virtual Optional<FloatRect> localBounds(const GraphicsContext&) const { return WTF::nullopt; }
-
-    // Some operations (e.g. putImageData) operate in global bounds. For these operations, override this method.
-    // If applicable, the return value needs to include the effects of shadows, clipping, etc.
-    virtual Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
-
-private:
-    bool isDrawingItem() const override { return true; }
-
-    Optional<FloatRect> m_extent; // In base coordinates, taking shadows and transforms into account.
</del><ins>+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return WTF::nullopt; }
+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
</ins><span class="cx"> };
</span><span class="cx"> 
</span><del>-class Save : public Item {
</del><ins>+class Restore {
</ins><span class="cx"> public:
</span><del>-    static Ref<Save> create()
-    {
-        return adoptRef(*new Save);
-    }
</del><ins>+    static constexpr ItemType itemType = ItemType::Restore;
+    static constexpr bool isInlineItem = true;
+    static constexpr bool isDrawingItem = false;
</ins><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~Save();
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><del>-    template<class Encoder> void encode(Encoder&) const;
-    template<class Decoder> static Optional<Ref<Save>> decode(Decoder&);
-
-private:
-    WEBCORE_EXPORT Save();
-
-    void apply(GraphicsContext&) const override;
</del><ins>+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return WTF::nullopt; }
+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
</ins><span class="cx"> };
</span><span class="cx"> 
</span><del>-template<class Encoder>
-void Save::encode(Encoder&) const
-{
-}
-
-template<class Decoder>
-Optional<Ref<Save>> Save::decode(Decoder&)
-{
-    return Save::create();
-}
-
-class Restore : public Item {
</del><ins>+class Translate {
</ins><span class="cx"> public:
</span><del>-    static Ref<Restore> create()
-    {
-        return adoptRef(*new Restore);
-    }
</del><ins>+    static constexpr ItemType itemType = ItemType::Translate;
+    static constexpr bool isInlineItem = true;
+    static constexpr bool isDrawingItem = false;
</ins><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~Restore();
-
-    template<class Encoder> void encode(Encoder&) const;
-    template<class Decoder> static Optional<Ref<Restore>> decode(Decoder&);
-
-private:
-    WEBCORE_EXPORT Restore();
-
-    void apply(GraphicsContext&) const override;
-};
-
-template<class Encoder>
-void Restore::encode(Encoder&) const
-{
-}
-
-template<class Decoder>
-Optional<Ref<Restore>> Restore::decode(Decoder&)
-{
-    return Restore::create();
-}
-
-class Translate : public Item {
-public:
-    static Ref<Translate> create(float x, float y)
</del><ins>+    Translate(float x, float y)
+        : m_x(x)
+        , m_y(y)
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new Translate(x, y));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~Translate();
-
</del><span class="cx">     float x() const { return m_x; }
</span><span class="cx">     float y() const { return m_y; }
</span><span class="cx"> 
</span><del>-    template<class Encoder> void encode(Encoder&) const;
-    template<class Decoder> static Optional<Ref<Translate>> decode(Decoder&);
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><ins>+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return WTF::nullopt; }
+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+
</ins><span class="cx"> private:
</span><del>-    WEBCORE_EXPORT Translate(float x, float y);
-
-    void apply(GraphicsContext&) const override;
-
-    float m_x;
-    float m_y;
</del><ins>+    float m_x { 0 };
+    float m_y { 0 };
</ins><span class="cx"> };
</span><span class="cx"> 
</span><del>-template<class Encoder>
-void Translate::encode(Encoder& encoder) const
-{
-    encoder << m_x;
-    encoder << m_y;
-}
</del><ins>+class Rotate {
+public:
+    static constexpr ItemType itemType = ItemType::Rotate;
+    static constexpr bool isInlineItem = true;
+    static constexpr bool isDrawingItem = false;
</ins><span class="cx"> 
</span><del>-template<class Decoder>
-Optional<Ref<Translate>> Translate::decode(Decoder& decoder)
-{
-    Optional<float> x;
-    decoder >> x;
-    if (!x)
-        return WTF::nullopt;
-
-    Optional<float> y;
-    decoder >> y;
-    if (!y)
-        return WTF::nullopt;
-
-    return Translate::create(*x, *y);
-}
-
-class Rotate : public Item {
-public:
-    static Ref<Rotate> create(float angleInRadians)
</del><ins>+    Rotate(float angle)
+        : m_angle(angle)
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new Rotate(angleInRadians));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~Rotate();
-
</del><span class="cx">     float angle() const { return m_angle; }
</span><span class="cx"> 
</span><del>-    template<class Encoder> void encode(Encoder&) const;
-    template<class Decoder> static Optional<Ref<Rotate>> decode(Decoder&);
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><ins>+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return WTF::nullopt; }
+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+
</ins><span class="cx"> private:
</span><del>-    WEBCORE_EXPORT Rotate(float angle);
-
-    void apply(GraphicsContext&) const override;
-
-    float m_angle; // In radians.
</del><ins>+    float m_angle { 0 }; // In radians.
</ins><span class="cx"> };
</span><span class="cx"> 
</span><del>-template<class Encoder>
-void Rotate::encode(Encoder& encoder) const
-{
-    encoder << m_angle;
-}
</del><ins>+class Scale {
+public:
+    static constexpr ItemType itemType = ItemType::Scale;
+    static constexpr bool isInlineItem = true;
+    static constexpr bool isDrawingItem = false;
</ins><span class="cx"> 
</span><del>-template<class Decoder>
-Optional<Ref<Rotate>> Rotate::decode(Decoder& decoder)
-{
-    Optional<float> angle;
-    decoder >> angle;
-    if (!angle)
-        return WTF::nullopt;
-
-    return Rotate::create(*angle);
-}
-
-class Scale : public Item {
-public:
-    static Ref<Scale> create(const FloatSize& size)
</del><ins>+    Scale(const FloatSize& size)
+        : m_size(size)
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new Scale(size));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~Scale();
-
</del><span class="cx">     const FloatSize& amount() const { return m_size; }
</span><span class="cx"> 
</span><del>-    template<class Encoder> void encode(Encoder&) const;
-    template<class Decoder> static Optional<Ref<Scale>> decode(Decoder&);
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><ins>+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return WTF::nullopt; }
+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+
</ins><span class="cx"> private:
</span><del>-    WEBCORE_EXPORT Scale(const FloatSize&);
-
-    void apply(GraphicsContext&) const override;
-
</del><span class="cx">     FloatSize m_size;
</span><span class="cx"> };
</span><span class="cx"> 
</span><del>-template<class Encoder>
-void Scale::encode(Encoder& encoder) const
-{
-    encoder << m_size;
-}
</del><ins>+class SetCTM {
+public:
+    static constexpr ItemType itemType = ItemType::SetCTM;
+    static constexpr bool isInlineItem = true;
+    static constexpr bool isDrawingItem = false;
</ins><span class="cx"> 
</span><del>-template<class Decoder>
-Optional<Ref<Scale>> Scale::decode(Decoder& decoder)
-{
-    Optional<FloatSize> scale;
-    decoder >> scale;
-    if (!scale)
-        return WTF::nullopt;
-
-    return Scale::create(*scale);
-}
-
-class SetCTM : public Item {
-public:
-    static Ref<SetCTM> create(const AffineTransform& matrix)
</del><ins>+    SetCTM(const AffineTransform& transform)
+        : m_transform(transform)
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new SetCTM(matrix));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~SetCTM();
-
</del><span class="cx">     const AffineTransform& transform() const { return m_transform; }
</span><span class="cx"> 
</span><del>-    template<class Encoder> void encode(Encoder&) const;
-    template<class Decoder> static Optional<Ref<SetCTM>> decode(Decoder&);
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><ins>+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return WTF::nullopt; }
+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+
</ins><span class="cx"> private:
</span><del>-    WEBCORE_EXPORT SetCTM(const AffineTransform&);
-
-    void apply(GraphicsContext&) const override;
-
</del><span class="cx">     AffineTransform m_transform;
</span><span class="cx"> };
</span><span class="cx"> 
</span><del>-template<class Encoder>
-void SetCTM::encode(Encoder& encoder) const
-{
-    encoder << m_transform;
-}
</del><ins>+class ConcatenateCTM {
+public:
+    static constexpr ItemType itemType = ItemType::ConcatenateCTM;
+    static constexpr bool isInlineItem = true;
+    static constexpr bool isDrawingItem = false;
</ins><span class="cx"> 
</span><del>-template<class Decoder>
-Optional<Ref<SetCTM>> SetCTM::decode(Decoder& decoder)
-{
-    Optional<AffineTransform> transform;
-    decoder >> transform;
-    if (!transform)
-        return WTF::nullopt;
-
-    return SetCTM::create(*transform);
-}
-
-class ConcatenateCTM : public Item {
-public:
-    static Ref<ConcatenateCTM> create(const AffineTransform& matrix)
</del><ins>+    ConcatenateCTM(const AffineTransform& transform)
+        : m_transform(transform)
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new ConcatenateCTM(matrix));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~ConcatenateCTM();
-
</del><span class="cx">     const AffineTransform& transform() const { return m_transform; }
</span><span class="cx"> 
</span><del>-    template<class Encoder> void encode(Encoder&) const;
-    template<class Decoder> static Optional<Ref<ConcatenateCTM>> decode(Decoder&);
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><ins>+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return WTF::nullopt; }
+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+
</ins><span class="cx"> private:
</span><del>-    WEBCORE_EXPORT ConcatenateCTM(const AffineTransform&);
-
-    void apply(GraphicsContext&) const override;
-
</del><span class="cx">     AffineTransform m_transform;
</span><span class="cx"> };
</span><span class="cx"> 
</span><del>-template<class Encoder>
-void ConcatenateCTM::encode(Encoder& encoder) const
-{
-    encoder << m_transform;
-}
-
-template<class Decoder>
-Optional<Ref<ConcatenateCTM>> ConcatenateCTM::decode(Decoder& decoder)
-{
-    Optional<AffineTransform> transform;
-    decoder >> transform;
-    if (!transform)
-        return WTF::nullopt;
-
-    return ConcatenateCTM::create(*transform);
-}
-
-class SetInlineFillGradient : public Item {
</del><ins>+class SetInlineFillGradient {
</ins><span class="cx"> public:
</span><ins>+    static constexpr ItemType itemType = ItemType::SetInlineFillGradient;
+    static constexpr bool isInlineItem = true;
+    static constexpr bool isDrawingItem = false;
</ins><span class="cx">     static constexpr uint8_t maxColorStopCount = 4;
</span><span class="cx"> 
</span><del>-    static Ref<SetInlineFillGradient> create(const Gradient&);
</del><ins>+    SetInlineFillGradient(const Gradient&);
+    WEBCORE_EXPORT SetInlineFillGradient(float offsets[maxColorStopCount], SRGBA<uint8_t> colors[maxColorStopCount], const Gradient::Data&,
+        const AffineTransform& gradientSpaceTransformation, GradientSpreadMethod, uint8_t colorStopCount);
+
</ins><span class="cx">     static bool isInline(const Gradient&);
</span><ins>+    Ref<Gradient> gradient() const;
</ins><span class="cx"> 
</span><del>-    virtual ~SetInlineFillGradient();
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><del>-    Ref<Gradient> gradient() const;
</del><ins>+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return WTF::nullopt; }
+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
</ins><span class="cx"> 
</span><del>-    template<class Encoder> void encode(Encoder&) const;
-    template<class Decoder> static Optional<Ref<SetInlineFillGradient>> decode(Decoder&);
-
</del><span class="cx"> private:
</span><del>-    static Ref<SetInlineFillGradient> create(float offsets[maxColorStopCount], SRGBA<uint8_t> colors[maxColorStopCount],
-        const Gradient::Data& data, const AffineTransform& gradientSpaceTransformation, GradientSpreadMethod spreadMethod, uint8_t colorStopCount)
-    {
-        return adoptRef(*new SetInlineFillGradient(offsets, colors, data, gradientSpaceTransformation, spreadMethod, colorStopCount));
-    }
-
-    WEBCORE_EXPORT SetInlineFillGradient(float offsets[maxColorStopCount], SRGBA<uint8_t> colors[maxColorStopCount], const Gradient::Data&,
-        const AffineTransform& gradientSpaceTransformation, GradientSpreadMethod, uint8_t colorStopCount);
-
-    SetInlineFillGradient(const Gradient&);
-
-    void apply(GraphicsContext&) const override;
-
</del><span class="cx">     float m_offsets[maxColorStopCount];
</span><span class="cx">     SRGBA<uint8_t> m_colors[maxColorStopCount];
</span><span class="cx">     Gradient::Data m_data;
</span><span class="lines">@@ -373,198 +216,79 @@
</span><span class="cx">     uint8_t m_colorStopCount { 0 };
</span><span class="cx"> };
</span><span class="cx"> 
</span><del>-template<class Encoder>
-void SetInlineFillGradient::encode(Encoder& encoder) const
-{
-    encoder << m_colorStopCount;
-    for (uint8_t i = 0; i < m_colorStopCount; ++i) {
-        encoder << m_offsets[i];
-        encoder << PackedColor::RGBA { m_colors[i] }.value;
-    }
-    encoder << m_data;
-    encoder << m_gradientSpaceTransformation;
-    encoder << m_spreadMethod;
-}
</del><ins>+class SetInlineFillColor {
+public:
+    static constexpr ItemType itemType = ItemType::SetInlineFillColor;
+    static constexpr bool isInlineItem = true;
+    static constexpr bool isDrawingItem = false;
</ins><span class="cx"> 
</span><del>-template<class Decoder>
-Optional<Ref<SetInlineFillGradient>> SetInlineFillGradient::decode(Decoder& decoder)
-{
-    Optional<uint8_t> colorStopCount;
-    decoder >> colorStopCount;
-    if (!colorStopCount)
-        return WTF::nullopt;
-
-    if (*colorStopCount > maxColorStopCount)
-        return WTF::nullopt;
-
-    float offsets[maxColorStopCount];
-    SRGBA<uint8_t> colors[maxColorStopCount];
-    for (uint8_t i = 0; i < *colorStopCount; ++i) {
-        Optional<float> offset;
-        decoder >> offset;
-        if (!offset)
-            return WTF::nullopt;
-
-        Optional<uint32_t> color;
-        decoder >> color;
-        if (!color)
-            return WTF::nullopt;
-
-        colors[i] = asSRGBA(PackedColor::RGBA { *color });
-        offsets[i] = *offset;
</del><ins>+    SetInlineFillColor(SRGBA<uint8_t> colorData)
+        : m_colorData(colorData)
+    {
</ins><span class="cx">     }
</span><span class="cx"> 
</span><del>-    Optional<Gradient::Data> data;
-    decoder >> data;
-    if (!data)
-        return WTF::nullopt;
-
-    Optional<AffineTransform> gradientSpaceTransformation;
-    decoder >> gradientSpaceTransformation;
-    if (!gradientSpaceTransformation)
-        return WTF::nullopt;
-
-    Optional<GradientSpreadMethod> spreadMethod;
-    decoder >> spreadMethod;
-    if (!spreadMethod)
-        return WTF::nullopt;
-
-    return { SetInlineFillGradient::create(offsets, colors, *data, *gradientSpaceTransformation, *spreadMethod, *colorStopCount) };
-}
-
-class SetInlineFillColor : public Item {
-public:
-    WEBCORE_EXPORT static Ref<SetInlineFillColor> create(SRGBA<uint8_t>);
-
-    WEBCORE_EXPORT virtual ~SetInlineFillColor();
-
</del><span class="cx">     Color color() const { return { m_colorData }; }
</span><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><del>-    template<class Encoder> void encode(Encoder&) const;
-    template<class Decoder> static Optional<Ref<SetInlineFillColor>> decode(Decoder&);
</del><ins>+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return WTF::nullopt; }
+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
</ins><span class="cx"> 
</span><span class="cx"> private:
</span><del>-    SetInlineFillColor(SRGBA<uint8_t> colorData)
-        : Item(ItemType::SetInlineFillColor)
-        , m_colorData(colorData)
-    {
-    }
-
-    void apply(GraphicsContext&) const override;
-
</del><span class="cx">     SRGBA<uint8_t> m_colorData;
</span><span class="cx"> };
</span><span class="cx"> 
</span><del>-template<class Encoder>
-void SetInlineFillColor::encode(Encoder& encoder) const
-{
-    encoder << PackedColor::RGBA { m_colorData }.value;
-}
-
-template<class Decoder>
-Optional<Ref<SetInlineFillColor>> SetInlineFillColor::decode(Decoder& decoder)
-{
-    Optional<uint32_t> value;
-    decoder >> value;
-    if (!value)
-        return WTF::nullopt;
-
-    return SetInlineFillColor::create(asSRGBA(PackedColor::RGBA { *value }));
-}
-
-class SetInlineStrokeColor : public Item {
</del><ins>+class SetInlineStrokeColor {
</ins><span class="cx"> public:
</span><del>-    WEBCORE_EXPORT static Ref<SetInlineStrokeColor> create(SRGBA<uint8_t>);
</del><ins>+    static constexpr ItemType itemType = ItemType::SetInlineStrokeColor;
+    static constexpr bool isInlineItem = true;
+    static constexpr bool isDrawingItem = false;
</ins><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~SetInlineStrokeColor();
</del><ins>+    SetInlineStrokeColor(SRGBA<uint8_t> colorData)
+        : m_colorData(colorData)
+    {
+    }
</ins><span class="cx"> 
</span><span class="cx">     Color color() const { return { m_colorData }; }
</span><span class="cx"> 
</span><del>-    template<class Encoder> void encode(Encoder&) const;
-    template<class Decoder> static Optional<Ref<SetInlineStrokeColor>> decode(Decoder&);
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><ins>+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return WTF::nullopt; }
+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+
</ins><span class="cx"> private:
</span><del>-    SetInlineStrokeColor(SRGBA<uint8_t> colorData)
-        : Item(ItemType::SetInlineStrokeColor)
-        , m_colorData(colorData)
-    {
-    }
-
-    void apply(GraphicsContext&) const override;
-
</del><span class="cx">     SRGBA<uint8_t> m_colorData;
</span><span class="cx"> };
</span><span class="cx"> 
</span><del>-template<class Encoder>
-void SetInlineStrokeColor::encode(Encoder& encoder) const
-{
-    encoder << PackedColor::RGBA { m_colorData }.value;
-}
-
-template<class Decoder>
-Optional<Ref<SetInlineStrokeColor>> SetInlineStrokeColor::decode(Decoder& decoder)
-{
-    Optional<uint32_t> value;
-    decoder >> value;
-    if (!value)
-        return WTF::nullopt;
-
-    return SetInlineStrokeColor::create(asSRGBA(PackedColor::RGBA { *value }));
-}
-
-class SetStrokeThickness : public Item {
</del><ins>+class SetStrokeThickness {
</ins><span class="cx"> public:
</span><del>-    WEBCORE_EXPORT static Ref<SetStrokeThickness> create(float thickness);
</del><ins>+    static constexpr ItemType itemType = ItemType::SetStrokeThickness;
+    static constexpr bool isInlineItem = true;
+    static constexpr bool isDrawingItem = false;
</ins><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~SetStrokeThickness();
</del><ins>+    SetStrokeThickness(float thickness)
+        : m_thickness(thickness)
+    {
+    }
</ins><span class="cx"> 
</span><span class="cx">     float thickness() const { return m_thickness; }
</span><span class="cx"> 
</span><del>-    template<class Encoder> void encode(Encoder&) const;
-    template<class Decoder> static Optional<Ref<SetStrokeThickness>> decode(Decoder&);
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><ins>+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return WTF::nullopt; }
+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+
</ins><span class="cx"> private:
</span><del>-    SetStrokeThickness(float thickness)
-        : Item(ItemType::SetStrokeThickness)
-        , m_thickness(thickness)
-    {
-    }
-
-    void apply(GraphicsContext&) const override;
-
</del><span class="cx">     float m_thickness { 0 };
</span><span class="cx"> };
</span><span class="cx"> 
</span><del>-template<class Encoder>
-void SetStrokeThickness::encode(Encoder& encoder) const
-{
-    encoder << m_thickness;
-}
-
-template<class Decoder>
-Optional<Ref<SetStrokeThickness>> SetStrokeThickness::decode(Decoder& decoder)
-{
-    Optional<float> thickness;
-    decoder >> thickness;
-    if (!thickness)
-        return WTF::nullopt;
-
-    return SetStrokeThickness::create(*thickness);
-}
-
-class SetState : public Item {
</del><ins>+class SetState {
</ins><span class="cx"> public:
</span><del>-    static Ref<SetState> create(const GraphicsContextState& state, GraphicsContextState::StateChangeFlags flags)
-    {
-        return adoptRef(*new SetState(state, flags));
-    }
</del><ins>+    static constexpr ItemType itemType = ItemType::SetState;
+    static constexpr bool isInlineItem = false;
+    static constexpr bool isDrawingItem = false;
</ins><span class="cx"> 
</span><del>-    static Ref<SetState> create(const GraphicsContextStateChange& stateChange)
-    {
-        return adoptRef(*new SetState(stateChange));
-    }
-
-    WEBCORE_EXPORT virtual ~SetState();
</del><ins>+    WEBCORE_EXPORT SetState(const GraphicsContextState&, GraphicsContextState::StateChangeFlags);
+    WEBCORE_EXPORT SetState(const GraphicsContextStateChange&);
</ins><span class="cx">     
</span><span class="cx">     const GraphicsContextStateChange& state() const { return m_state; }
</span><span class="cx"> 
</span><span class="lines">@@ -573,14 +297,14 @@
</span><span class="cx">     static void dumpStateChanges(WTF::TextStream&, const GraphicsContextState&, GraphicsContextState::StateChangeFlags);
</span><span class="cx"> 
</span><span class="cx">     template<class Encoder> void encode(Encoder&) const;
</span><del>-    template<class Decoder> static Optional<Ref<SetState>> decode(Decoder&);
</del><ins>+    template<class Decoder> static Optional<SetState> decode(Decoder&);
</ins><span class="cx"> 
</span><del>-private:
-    WEBCORE_EXPORT SetState(const GraphicsContextState&, GraphicsContextState::StateChangeFlags);
-    WEBCORE_EXPORT SetState(const GraphicsContextStateChange&);
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><del>-    void apply(GraphicsContext&) const override;
</del><ins>+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return WTF::nullopt; }
+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
</ins><span class="cx"> 
</span><ins>+private:
</ins><span class="cx">     GraphicsContextStateChange m_state;
</span><span class="cx"> };
</span><span class="cx"> 
</span><span class="lines">@@ -669,7 +393,7 @@
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> template<class Decoder>
</span><del>-Optional<Ref<SetState>> SetState::decode(Decoder& decoder)
</del><ins>+Optional<SetState> SetState::decode(Decoder& decoder)
</ins><span class="cx"> {
</span><span class="cx">     Optional<GraphicsContextState::StateChangeFlags> changeFlags;
</span><span class="cx">     decoder >> changeFlags;
</span><span class="lines">@@ -896,68 +620,55 @@
</span><span class="cx">         stateChange.m_state.shadowsIgnoreTransforms = *shadowsIgnoreTransforms;
</span><span class="cx">     }
</span><span class="cx"> 
</span><del>-    return SetState::create(stateChange);
</del><ins>+    return { stateChange };
</ins><span class="cx"> }
</span><span class="cx"> 
</span><del>-class SetLineCap : public Item {
</del><ins>+class SetLineCap {
</ins><span class="cx"> public:
</span><del>-    static Ref<SetLineCap> create(LineCap lineCap)
</del><ins>+    static constexpr ItemType itemType = ItemType::SetLineCap;
+    static constexpr bool isInlineItem = true;
+    static constexpr bool isDrawingItem = false;
+
+    SetLineCap(LineCap lineCap)
+        : m_lineCap(lineCap)
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new SetLineCap(lineCap));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~SetLineCap();
-    
</del><span class="cx">     LineCap lineCap() const { return m_lineCap; }
</span><span class="cx"> 
</span><del>-    template<class Encoder> void encode(Encoder&) const;
-    template<class Decoder> static Optional<Ref<SetLineCap>> decode(Decoder&);
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><ins>+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return WTF::nullopt; }
+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+
</ins><span class="cx"> private:
</span><del>-    WEBCORE_EXPORT SetLineCap(LineCap);
-
-    void apply(GraphicsContext&) const override;
-
</del><span class="cx">     LineCap m_lineCap;
</span><span class="cx"> };
</span><span class="cx"> 
</span><del>-template<class Encoder>
-void SetLineCap::encode(Encoder& encoder) const
-{
-    encoder << m_lineCap;
-}
</del><ins>+class SetLineDash {
+public:
+    static constexpr ItemType itemType = ItemType::SetLineDash;
+    static constexpr bool isInlineItem = false;
+    static constexpr bool isDrawingItem = false;
</ins><span class="cx"> 
</span><del>-template<class Decoder>
-Optional<Ref<SetLineCap>> SetLineCap::decode(Decoder& decoder)
-{
-    Optional<LineCap> lineCap;
-    decoder >> lineCap;
-    if (!lineCap)
-        return WTF::nullopt;
-
-    return SetLineCap::create(*lineCap);
-}
-
-class SetLineDash : public Item {
-public:
-    static Ref<SetLineDash> create(const DashArray& dashArray, float dashOffset)
</del><ins>+    SetLineDash(const DashArray& dashArray, float dashOffset)
+        : m_dashArray(dashArray)
+        , m_dashOffset(dashOffset)
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new SetLineDash(dashArray, dashOffset));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~SetLineDash();
-
</del><span class="cx">     const DashArray& dashArray() const { return m_dashArray; }
</span><span class="cx">     float dashOffset() const { return m_dashOffset; }
</span><span class="cx"> 
</span><ins>+    void apply(GraphicsContext&) const;
+
+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return WTF::nullopt; }
+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+
</ins><span class="cx">     template<class Encoder> void encode(Encoder&) const;
</span><del>-    template<class Decoder> static Optional<Ref<SetLineDash>> decode(Decoder&);
</del><ins>+    template<class Decoder> static Optional<SetLineDash> decode(Decoder&);
</ins><span class="cx"> 
</span><span class="cx"> private:
</span><del>-    WEBCORE_EXPORT SetLineDash(const DashArray&, float dashOffset);
-
-    void apply(GraphicsContext&) const override;
-
</del><span class="cx">     DashArray m_dashArray;
</span><span class="cx">     float m_dashOffset;
</span><span class="cx"> };
</span><span class="lines">@@ -970,7 +681,7 @@
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> template<class Decoder>
</span><del>-Optional<Ref<SetLineDash>> SetLineDash::decode(Decoder& decoder)
</del><ins>+Optional<SetLineDash> SetLineDash::decode(Decoder& decoder)
</ins><span class="cx"> {
</span><span class="cx">     Optional<DashArray> dashArray;
</span><span class="cx">     decoder >> dashArray;
</span><span class="lines">@@ -982,215 +693,138 @@
</span><span class="cx">     if (!dashOffset)
</span><span class="cx">         return WTF::nullopt;
</span><span class="cx"> 
</span><del>-    return SetLineDash::create(*dashArray, *dashOffset);
</del><ins>+    return {{ *dashArray, *dashOffset }};
</ins><span class="cx"> }
</span><span class="cx"> 
</span><del>-class SetLineJoin : public Item {
</del><ins>+class SetLineJoin {
</ins><span class="cx"> public:
</span><del>-    static Ref<SetLineJoin> create(LineJoin lineJoin)
</del><ins>+    static constexpr ItemType itemType = ItemType::SetLineJoin;
+    static constexpr bool isInlineItem = true;
+    static constexpr bool isDrawingItem = false;
+
+    SetLineJoin(LineJoin lineJoin)
+        : m_lineJoin(lineJoin)
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new SetLineJoin(lineJoin));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~SetLineJoin();
-    
</del><span class="cx">     LineJoin lineJoin() const { return m_lineJoin; }
</span><span class="cx"> 
</span><del>-    template<class Encoder> void encode(Encoder&) const;
-    template<class Decoder> static Optional<Ref<SetLineJoin>> decode(Decoder&);
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><ins>+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return WTF::nullopt; }
+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+
</ins><span class="cx"> private:
</span><del>-    WEBCORE_EXPORT SetLineJoin(LineJoin);
-
-    void apply(GraphicsContext&) const override;
-
</del><span class="cx">     LineJoin m_lineJoin;
</span><span class="cx"> };
</span><span class="cx"> 
</span><del>-template<class Encoder>
-void SetLineJoin::encode(Encoder& encoder) const
-{
-    encoder << m_lineJoin;
-}
</del><ins>+class SetMiterLimit {
+public:
+    static constexpr ItemType itemType = ItemType::SetMiterLimit;
+    static constexpr bool isInlineItem = true;
+    static constexpr bool isDrawingItem = false;
</ins><span class="cx"> 
</span><del>-template<class Decoder>
-Optional<Ref<SetLineJoin>> SetLineJoin::decode(Decoder& decoder)
-{
-    Optional<LineJoin> lineJoin;
-    decoder >> lineJoin;
-    if (!lineJoin)
-        return WTF::nullopt;
-
-    return SetLineJoin::create(*lineJoin);
-}
-
-class SetMiterLimit : public Item {
-public:
-    static Ref<SetMiterLimit> create(float limit)
</del><ins>+    SetMiterLimit(float miterLimit)
+        : m_miterLimit(miterLimit)
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new SetMiterLimit(limit));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~SetMiterLimit();
-
</del><span class="cx">     float miterLimit() const { return m_miterLimit; }
</span><span class="cx"> 
</span><del>-    template<class Encoder> void encode(Encoder&) const;
-    template<class Decoder> static Optional<Ref<SetMiterLimit>> decode(Decoder&);
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><ins>+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return WTF::nullopt; }
+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+
</ins><span class="cx"> private:
</span><del>-    WEBCORE_EXPORT SetMiterLimit(float);
-
-    void apply(GraphicsContext&) const override;
-
</del><span class="cx">     float m_miterLimit;
</span><span class="cx"> };
</span><span class="cx"> 
</span><del>-template<class Encoder>
-void SetMiterLimit::encode(Encoder& encoder) const
-{
-    encoder << m_miterLimit;
-}
-
-template<class Decoder>
-Optional<Ref<SetMiterLimit>> SetMiterLimit::decode(Decoder& decoder)
-{
-    Optional<float> miterLimit;
-    decoder >> miterLimit;
-    if (!miterLimit)
-        return WTF::nullopt;
-
-    return SetMiterLimit::create(*miterLimit);
-}
-
-class ClearShadow : public Item {
</del><ins>+class ClearShadow {
</ins><span class="cx"> public:
</span><del>-    static Ref<ClearShadow> create()
-    {
-        return adoptRef(*new ClearShadow);
-    }
</del><ins>+    static constexpr ItemType itemType = ItemType::ClearShadow;
+    static constexpr bool isInlineItem = true;
+    static constexpr bool isDrawingItem = false;
</ins><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~ClearShadow();
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><del>-    template<class Encoder> void encode(Encoder&) const;
-    template<class Decoder> static Optional<Ref<ClearShadow>> decode(Decoder&);
-
-private:
-    WEBCORE_EXPORT ClearShadow();
-
-    void apply(GraphicsContext&) const override;
</del><ins>+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return WTF::nullopt; }
+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
</ins><span class="cx"> };
</span><span class="cx"> 
</span><del>-template<class Encoder>
-void ClearShadow::encode(Encoder&) const
-{
-}
</del><ins>+// FIXME: treat as drawing item?
+class Clip {
+public:
+    static constexpr ItemType itemType = ItemType::Clip;
+    static constexpr bool isInlineItem = true;
+    static constexpr bool isDrawingItem = false;
</ins><span class="cx"> 
</span><del>-template<class Decoder>
-Optional<Ref<ClearShadow>> ClearShadow::decode(Decoder&)
-{
-    return ClearShadow::create();
-}
-
-// FIXME: treat as DrawingItem?
-class Clip : public Item {
-public:
-    static Ref<Clip> create(const FloatRect& rect)
</del><ins>+    Clip(const FloatRect& rect)
+        : m_rect(rect)
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new Clip(rect));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~Clip();
</del><ins>+    const FloatRect& rect() const { return m_rect; }
</ins><span class="cx"> 
</span><del>-    FloatRect rect() const { return m_rect; }
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><del>-    template<class Encoder> void encode(Encoder&) const;
-    template<class Decoder> static Optional<Ref<Clip>> decode(Decoder&);
</del><ins>+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return WTF::nullopt; }
+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
</ins><span class="cx"> 
</span><span class="cx"> private:
</span><del>-    WEBCORE_EXPORT Clip(const FloatRect&);
-
-    void apply(GraphicsContext&) const override;
-
</del><span class="cx">     FloatRect m_rect;
</span><span class="cx"> };
</span><span class="cx"> 
</span><del>-template<class Encoder>
-void Clip::encode(Encoder& encoder) const
-{
-    encoder << m_rect;
-}
</del><ins>+class ClipOut {
+public:
+    static constexpr ItemType itemType = ItemType::ClipOut;
+    static constexpr bool isInlineItem = true;
+    static constexpr bool isDrawingItem = false;
</ins><span class="cx"> 
</span><del>-template<class Decoder>
-Optional<Ref<Clip>> Clip::decode(Decoder& decoder)
-{
-    Optional<FloatRect> rect;
-    decoder >> rect;
-    if (!rect)
-        return WTF::nullopt;
-
-    return Clip::create(*rect);
-}
-
-class ClipOut : public Item {
-public:
-    static Ref<ClipOut> create(const FloatRect& rect)
</del><ins>+    ClipOut(const FloatRect& rect)
+        : m_rect(rect)
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new ClipOut(rect));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~ClipOut();
</del><ins>+    const FloatRect& rect() const { return m_rect; }
</ins><span class="cx"> 
</span><del>-    FloatRect rect() const { return m_rect; }
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><del>-    template<class Encoder> void encode(Encoder&) const;
-    template<class Decoder> static Optional<Ref<ClipOut>> decode(Decoder&);
</del><ins>+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return WTF::nullopt; }
+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
</ins><span class="cx"> 
</span><span class="cx"> private:
</span><del>-    WEBCORE_EXPORT ClipOut(const FloatRect&);
-
-    void apply(GraphicsContext&) const override;
-
</del><span class="cx">     FloatRect m_rect;
</span><span class="cx"> };
</span><span class="cx"> 
</span><del>-template<class Encoder>
-void ClipOut::encode(Encoder& encoder) const
-{
-    encoder << m_rect;
-}
</del><ins>+class ClipOutToPath {
+public:
+    static constexpr ItemType itemType = ItemType::ClipOutToPath;
+    static constexpr bool isInlineItem = false;
+    static constexpr bool isDrawingItem = false;
</ins><span class="cx"> 
</span><del>-template<class Decoder>
-Optional<Ref<ClipOut>> ClipOut::decode(Decoder& decoder)
-{
-    Optional<FloatRect> rect;
-    decoder >> rect;
-    if (!rect)
-        return WTF::nullopt;
</del><ins>+    ClipOutToPath(Path&& path)
+        : m_path(WTFMove(path))
+    {
+    }
</ins><span class="cx"> 
</span><del>-    return ClipOut::create(*rect);
-}
-
-class ClipOutToPath : public Item {
-public:
-    static Ref<ClipOutToPath> create(const Path& path)
</del><ins>+    ClipOutToPath(const Path& path)
+        : m_path(path)
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new ClipOutToPath(path));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~ClipOutToPath();
-
</del><span class="cx">     const Path& path() const { return m_path; }
</span><span class="cx"> 
</span><span class="cx">     template<class Encoder> void encode(Encoder&) const;
</span><del>-    template<class Decoder> static Optional<Ref<ClipOutToPath>> decode(Decoder&);
</del><ins>+    template<class Decoder> static Optional<ClipOutToPath> decode(Decoder&);
</ins><span class="cx"> 
</span><del>-private:
-    WEBCORE_EXPORT ClipOutToPath(const Path&);
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><del>-    void apply(GraphicsContext&) const override;
</del><ins>+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return WTF::nullopt; }
+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
</ins><span class="cx"> 
</span><del>-    const Path m_path;
</del><ins>+private:
+    Path m_path;
</ins><span class="cx"> };
</span><span class="cx"> 
</span><span class="cx"> template<class Encoder>
</span><span class="lines">@@ -1200,7 +834,7 @@
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> template<class Decoder>
</span><del>-Optional<Ref<ClipOutToPath>> ClipOutToPath::decode(Decoder& decoder)
</del><ins>+Optional<ClipOutToPath> ClipOutToPath::decode(Decoder& decoder)
</ins><span class="cx"> {
</span><span class="cx">     Optional<Path> path;
</span><span class="cx">     decoder >> path;
</span><span class="lines">@@ -1207,30 +841,40 @@
</span><span class="cx">     if (!path)
</span><span class="cx">         return WTF::nullopt;
</span><span class="cx"> 
</span><del>-    return ClipOutToPath::create(*path);
</del><ins>+    return {{ WTFMove(*path) }};
</ins><span class="cx"> }
</span><span class="cx"> 
</span><del>-class ClipPath : public Item {
</del><ins>+class ClipPath {
</ins><span class="cx"> public:
</span><del>-    static Ref<ClipPath> create(const Path& path, WindRule windRule)
</del><ins>+    static constexpr ItemType itemType = ItemType::ClipPath;
+    static constexpr bool isInlineItem = false;
+    static constexpr bool isDrawingItem = false;
+
+    ClipPath(Path&& path, WindRule windRule)
+        : m_path(WTFMove(path))
+        , m_windRule(windRule)
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new ClipPath(path, windRule));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT ~ClipPath();
</del><ins>+    ClipPath(const Path& path, WindRule windRule)
+        : m_path(path)
+        , m_windRule(windRule)
+    {
+    }
</ins><span class="cx"> 
</span><span class="cx">     const Path& path() const { return m_path; }
</span><span class="cx">     WindRule windRule() const { return m_windRule; }
</span><span class="cx"> 
</span><ins>+    void apply(GraphicsContext&) const;
+
+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return WTF::nullopt; }
+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+
</ins><span class="cx">     template<class Encoder> void encode(Encoder&) const;
</span><del>-    template<class Decoder> static Optional<Ref<ClipPath>> decode(Decoder&);
</del><ins>+    template<class Decoder> static Optional<ClipPath> decode(Decoder&);
</ins><span class="cx"> 
</span><span class="cx"> private:
</span><del>-    WEBCORE_EXPORT ClipPath(const Path&, WindRule);
-
-    void apply(GraphicsContext&) const override;
-
-    const Path m_path;
</del><ins>+    Path m_path;
</ins><span class="cx">     WindRule m_windRule;
</span><span class="cx"> };
</span><span class="cx"> 
</span><span class="lines">@@ -1242,7 +886,7 @@
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> template<class Decoder>
</span><del>-Optional<Ref<ClipPath>> ClipPath::decode(Decoder& decoder)
</del><ins>+Optional<ClipPath> ClipPath::decode(Decoder& decoder)
</ins><span class="cx"> {
</span><span class="cx">     Optional<Path> path;
</span><span class="cx">     decoder >> path;
</span><span class="lines">@@ -1254,30 +898,50 @@
</span><span class="cx">     if (!windRule)
</span><span class="cx">         return WTF::nullopt;
</span><span class="cx"> 
</span><del>-    return ClipPath::create(*path, *windRule);
</del><ins>+    return {{ WTFMove(*path), *windRule }};
</ins><span class="cx"> }
</span><span class="cx"> 
</span><del>-class ClipToDrawingCommands : public Item {
</del><ins>+class ClipToDrawingCommands {
</ins><span class="cx"> public:
</span><del>-    static Ref<ClipToDrawingCommands> create(const FloatRect& destination, ColorSpace colorSpace, DisplayList&& drawingCommands)
</del><ins>+    static constexpr ItemType itemType = ItemType::ClipToDrawingCommands;
+    static constexpr bool isInlineItem = false;
+    static constexpr bool isDrawingItem = false;
+
+    ClipToDrawingCommands(const FloatRect& destination, ColorSpace colorSpace, DisplayList&& drawingCommands)
+        : m_destination(destination)
+        , m_colorSpace(colorSpace)
+        , m_drawingCommands(WTFMove(drawingCommands))
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new ClipToDrawingCommands(destination, colorSpace, WTFMove(drawingCommands)));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT ~ClipToDrawingCommands();
</del><ins>+    ClipToDrawingCommands(const ClipToDrawingCommands& other)
+        : m_destination(other.m_destination)
+        , m_colorSpace(other.m_colorSpace)
+    {
+        // FIXME: Copy m_drawingCommands.
+    }
</ins><span class="cx"> 
</span><ins>+    ClipToDrawingCommands& operator=(const ClipToDrawingCommands& other)
+    {
+        m_destination = other.m_destination;
+        m_colorSpace = other.m_colorSpace;
+        // FIXME: Copy m_drawingCommands.
+        return *this;
+    }
+
</ins><span class="cx">     const FloatRect& destination() const { return m_destination; }
</span><span class="cx">     ColorSpace colorSpace() const { return m_colorSpace; }
</span><span class="cx">     const DisplayList& drawingCommands() const { return m_drawingCommands; }
</span><span class="cx"> 
</span><span class="cx">     template<class Encoder> void encode(Encoder&) const;
</span><del>-    template<class Decoder> static Optional<Ref<ClipToDrawingCommands>> decode(Decoder&);
</del><ins>+    template<class Decoder> static Optional<ClipToDrawingCommands> decode(Decoder&);
</ins><span class="cx"> 
</span><del>-private:
-    WEBCORE_EXPORT ClipToDrawingCommands(const FloatRect& destination, ColorSpace, DisplayList&& drawingCommands);
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><del>-    void apply(GraphicsContext&) const override;
</del><ins>+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return WTF::nullopt; }
+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
</ins><span class="cx"> 
</span><ins>+private:
</ins><span class="cx">     FloatRect m_destination;
</span><span class="cx">     ColorSpace m_colorSpace;
</span><span class="cx">     DisplayList m_drawingCommands;
</span><span class="lines">@@ -1288,11 +952,11 @@
</span><span class="cx"> {
</span><span class="cx">     encoder << m_destination;
</span><span class="cx">     encoder << m_colorSpace;
</span><del>-    encoder << m_drawingCommands;
</del><ins>+    // FIXME: Implement a way to encode in-memory display lists.
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> template<class Decoder>
</span><del>-Optional<Ref<ClipToDrawingCommands>> ClipToDrawingCommands::decode(Decoder& decoder)
</del><ins>+Optional<ClipToDrawingCommands> ClipToDrawingCommands::decode(Decoder& decoder)
</ins><span class="cx"> {
</span><span class="cx">     Optional<FloatRect> destination;
</span><span class="cx">     decoder >> destination;
</span><span class="lines">@@ -1304,28 +968,17 @@
</span><span class="cx">     if (!colorSpace)
</span><span class="cx">         return WTF::nullopt;
</span><span class="cx"> 
</span><del>-    Optional<DisplayList> drawingCommands;
-    decoder >> drawingCommands;
-    if (!drawingCommands)
-        return WTF::nullopt;
-
-    return ClipToDrawingCommands::create(*destination, *colorSpace, WTFMove(*drawingCommands));
</del><ins>+    // FIXME: Implement a way to decode in-memory display lists.
+    DisplayList drawingCommands;
+    return {{ *destination, *colorSpace, WTFMove(drawingCommands) }};
</ins><span class="cx"> }
</span><span class="cx"> 
</span><del>-class DrawGlyphs : public DrawingItem {
</del><ins>+class DrawGlyphs {
</ins><span class="cx"> public:
</span><del>-    static Ref<DrawGlyphs> create(const Font& font, const GlyphBufferGlyph* glyphs, const GlyphBufferAdvance* advances, unsigned count, const FloatPoint& localAnchor, FontSmoothingMode smoothingMode)
-    {
-        return adoptRef(*new DrawGlyphs(font, glyphs, advances, count, localAnchor, smoothingMode));
-    }
</del><ins>+    static constexpr ItemType itemType = ItemType::DrawGlyphs;
+    static constexpr bool isInlineItem = false;
+    static constexpr bool isDrawingItem = true;
</ins><span class="cx"> 
</span><del>-    static Ref<DrawGlyphs> create(const Font& font, Vector<GlyphBufferGlyph, 128>&& glyphs, Vector<GlyphBufferAdvance, 128>&& advances, const FloatPoint& localAnchor, FontSmoothingMode smoothingMode)
-    {
-        return adoptRef(*new DrawGlyphs(font, WTFMove(glyphs), WTFMove(advances), localAnchor, smoothingMode));
-    }
-
-    WEBCORE_EXPORT virtual ~DrawGlyphs();
-
</del><span class="cx">     const FloatPoint& localAnchor() const { return m_localAnchor; }
</span><span class="cx"> 
</span><span class="cx">     FloatPoint anchorPoint() const { return m_localAnchor; }
</span><span class="lines">@@ -1333,21 +986,21 @@
</span><span class="cx">     const Vector<GlyphBufferGlyph, 128>& glyphs() const { return m_glyphs; }
</span><span class="cx"> 
</span><span class="cx">     template<class Encoder> void encode(Encoder&) const;
</span><del>-    template<class Decoder> static Optional<Ref<DrawGlyphs>> decode(Decoder&);
</del><ins>+    template<class Decoder> static Optional<DrawGlyphs> decode(Decoder&);
</ins><span class="cx"> 
</span><del>-private:
</del><span class="cx">     DrawGlyphs(const Font&, const GlyphBufferGlyph*, const GlyphBufferAdvance*, unsigned count, const FloatPoint& localAnchor, FontSmoothingMode);
</span><span class="cx">     WEBCORE_EXPORT DrawGlyphs(const Font&, Vector<GlyphBufferGlyph, 128>&&, Vector<GlyphBufferAdvance, 128>&&, const FloatPoint& localAnchor, FontSmoothingMode);
</span><span class="cx"> 
</span><del>-    void computeBounds();
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><del>-    void apply(GraphicsContext&) const override;
</del><ins>+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return m_bounds; }
</ins><span class="cx"> 
</span><del>-    Optional<FloatRect> localBounds(const GraphicsContext&) const override;
-
</del><ins>+private:
+    void computeBounds();
</ins><span class="cx">     GlyphBuffer generateGlyphBuffer() const;
</span><span class="cx"> 
</span><del>-    Ref<Font> m_font;
</del><ins>+    RefPtr<Font> m_font;
</ins><span class="cx">     Vector<GlyphBufferGlyph, 128> m_glyphs;
</span><span class="cx">     Vector<GlyphBufferAdvance, 128> m_advances;
</span><span class="cx">     FloatRect m_bounds;
</span><span class="lines">@@ -1358,7 +1011,7 @@
</span><span class="cx"> template<class Encoder>
</span><span class="cx"> void DrawGlyphs::encode(Encoder& encoder) const
</span><span class="cx"> {
</span><del>-    encoder << m_font;
</del><ins>+    encoder << makeRef(*m_font);
</ins><span class="cx">     encoder << m_glyphs;
</span><span class="cx">     encoder << m_advances;
</span><span class="cx">     encoder << m_localAnchor;
</span><span class="lines">@@ -1366,7 +1019,7 @@
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> template<class Decoder>
</span><del>-Optional<Ref<DrawGlyphs>> DrawGlyphs::decode(Decoder& decoder)
</del><ins>+Optional<DrawGlyphs> DrawGlyphs::decode(Decoder& decoder)
</ins><span class="cx"> {
</span><span class="cx">     Optional<Ref<Font>> font;
</span><span class="cx">     decoder >> font;
</span><span class="lines">@@ -1396,32 +1049,36 @@
</span><span class="cx">     if (!smoothingMode)
</span><span class="cx">         return WTF::nullopt;
</span><span class="cx"> 
</span><del>-    return DrawGlyphs::create(font->get(), WTFMove(*glyphs), WTFMove(*advances), *localAnchor, *smoothingMode);
</del><ins>+    return {{ font->get(), WTFMove(*glyphs), WTFMove(*advances), *localAnchor, *smoothingMode }};
</ins><span class="cx"> }
</span><span class="cx"> 
</span><del>-class DrawImage : public DrawingItem {
</del><ins>+class DrawImage {
</ins><span class="cx"> public:
</span><del>-    static Ref<DrawImage> create(Image& image, const FloatRect& destination, const FloatRect& source, const ImagePaintingOptions& imagePaintingOptions)
</del><ins>+    static constexpr ItemType itemType = ItemType::DrawImage;
+    static constexpr bool isInlineItem = false;
+    static constexpr bool isDrawingItem = true;
+
+    DrawImage(Image& image, const FloatRect& destination, const FloatRect& source, const ImagePaintingOptions& imagePaintingOptions)
+        : m_image(image)
+        , m_destination(destination)
+        , m_source(source)
+        , m_imagePaintingOptions(imagePaintingOptions)
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new DrawImage(image, destination, source, imagePaintingOptions));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~DrawImage();
-
</del><span class="cx">     const Image& image() const { return m_image.get(); }
</span><span class="cx">     FloatRect source() const { return m_source; }
</span><span class="cx">     FloatRect destination() const { return m_destination; }
</span><span class="cx"> 
</span><span class="cx">     template<class Encoder> void encode(Encoder&) const;
</span><del>-    template<class Decoder> static Optional<Ref<DrawImage>> decode(Decoder&);
</del><ins>+    template<class Decoder> static Optional<DrawImage> decode(Decoder&);
</ins><span class="cx"> 
</span><del>-private:
-    WEBCORE_EXPORT DrawImage(Image&, const FloatRect& destination, const FloatRect& source, const ImagePaintingOptions&);
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><del>-    void apply(GraphicsContext&) const override;
</del><ins>+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return m_destination; }
</ins><span class="cx"> 
</span><del>-    Optional<FloatRect> localBounds(const GraphicsContext&) const override { return m_destination; }
-
</del><ins>+private:
</ins><span class="cx">     mutable Ref<Image> m_image; // FIXME: Drawing images can cause their animations to progress. This shouldn't have to be mutable.
</span><span class="cx">     FloatRect m_destination;
</span><span class="cx">     FloatRect m_source;
</span><span class="lines">@@ -1441,7 +1098,7 @@
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> template<class Decoder>
</span><del>-Optional<Ref<DrawImage>> DrawImage::decode(Decoder& decoder)
</del><ins>+Optional<DrawImage> DrawImage::decode(Decoder& decoder)
</ins><span class="cx"> {
</span><span class="cx">     Optional<ImageHandle> imageHandle;
</span><span class="cx">     decoder >> imageHandle;
</span><span class="lines">@@ -1463,18 +1120,15 @@
</span><span class="cx">     if (!imagePaintingOptions)
</span><span class="cx">         return WTF::nullopt;
</span><span class="cx"> 
</span><del>-    return DrawImage::create(*imageHandle->image, *destination, *source, *imagePaintingOptions);
</del><ins>+    return {{ *imageHandle->image, *destination, *source, *imagePaintingOptions }};
</ins><span class="cx"> }
</span><span class="cx"> 
</span><del>-class DrawTiledImage : public DrawingItem {
</del><ins>+class DrawTiledImage {
</ins><span class="cx"> public:
</span><del>-    static Ref<DrawTiledImage> create(Image& image, const FloatRect& destination, const FloatPoint& source, const FloatSize& tileSize, const FloatSize& spacing, const ImagePaintingOptions& imagePaintingOptions)
-    {
-        return adoptRef(*new DrawTiledImage(image, destination, source, tileSize, spacing, imagePaintingOptions));
-    }
</del><ins>+    static constexpr ItemType itemType = ItemType::DrawTiledImage;
+    static constexpr bool isInlineItem = false;
+    static constexpr bool isDrawingItem = true;
</ins><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~DrawTiledImage();
-
</del><span class="cx">     const Image& image() const { return m_image.get(); }
</span><span class="cx">     FloatPoint source() const { return m_source; }
</span><span class="cx">     FloatRect destination() const { return m_destination; }
</span><span class="lines">@@ -1482,16 +1136,25 @@
</span><span class="cx">     FloatSize tileSize() const { return m_tileSize; }
</span><span class="cx">     FloatSize spacing() const { return m_spacing; }
</span><span class="cx"> 
</span><del>-    template<class Encoder> void encode(Encoder&) const;
-    template<class Decoder> static Optional<Ref<DrawTiledImage>> decode(Decoder&);
</del><ins>+    DrawTiledImage(Image& image, const FloatRect& destination, const FloatPoint& source, const FloatSize& tileSize, const FloatSize& spacing, const ImagePaintingOptions& imagePaintingOptions)
+        : m_image(image)
+        , m_destination(destination)
+        , m_source(source)
+        , m_tileSize(tileSize)
+        , m_spacing(spacing)
+        , m_imagePaintingOptions(imagePaintingOptions)
+    {
+    }
</ins><span class="cx"> 
</span><del>-private:
-    WEBCORE_EXPORT DrawTiledImage(Image&, const FloatRect& destination, const FloatPoint& source, const FloatSize& tileSize, const FloatSize& spacing, const ImagePaintingOptions&);
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><del>-    void apply(GraphicsContext&) const override;
</del><ins>+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return m_destination; }
</ins><span class="cx"> 
</span><del>-    Optional<FloatRect> localBounds(const GraphicsContext&) const override { return m_destination; }
</del><ins>+    template<class Encoder> void encode(Encoder&) const;
+    template<class Decoder> static Optional<DrawTiledImage> decode(Decoder&);
</ins><span class="cx"> 
</span><ins>+private:
</ins><span class="cx">     mutable Ref<Image> m_image; // FIXME: Drawing images can cause their animations to progress. This shouldn't have to be mutable.
</span><span class="cx">     FloatRect m_destination;
</span><span class="cx">     FloatPoint m_source;
</span><span class="lines">@@ -1514,7 +1177,7 @@
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> template<class Decoder>
</span><del>-Optional<Ref<DrawTiledImage>> DrawTiledImage::decode(Decoder& decoder)
</del><ins>+Optional<DrawTiledImage> DrawTiledImage::decode(Decoder& decoder)
</ins><span class="cx"> {
</span><span class="cx">     Optional<ImageHandle> imageHandle;
</span><span class="cx">     decoder >> imageHandle;
</span><span class="lines">@@ -1546,32 +1209,39 @@
</span><span class="cx">     if (!imagePaintingOptions)
</span><span class="cx">         return WTF::nullopt;
</span><span class="cx"> 
</span><del>-    return DrawTiledImage::create(*imageHandle->image, *destination, *source, *tileSize, *spacing, *imagePaintingOptions);
</del><ins>+    return {{ *imageHandle->image, *destination, *source, *tileSize, *spacing, *imagePaintingOptions }};
</ins><span class="cx"> }
</span><span class="cx"> 
</span><del>-class DrawTiledScaledImage : public DrawingItem {
</del><ins>+class DrawTiledScaledImage {
</ins><span class="cx"> public:
</span><del>-    static Ref<DrawTiledScaledImage> create(Image& image, const FloatRect& destination, const FloatRect& source, const FloatSize& tileScaleFactor, Image::TileRule hRule, Image::TileRule vRule, const ImagePaintingOptions& imagePaintingOptions)
</del><ins>+    static constexpr ItemType itemType = ItemType::DrawTiledScaledImage;
+    static constexpr bool isInlineItem = false;
+    static constexpr bool isDrawingItem = true;
+
+    DrawTiledScaledImage(Image& image, const FloatRect& destination, const FloatRect& source, const FloatSize& tileScaleFactor, Image::TileRule hRule, Image::TileRule vRule, const ImagePaintingOptions& imagePaintingOptions)
+        : m_image(image)
+        , m_destination(destination)
+        , m_source(source)
+        , m_tileScaleFactor(tileScaleFactor)
+        , m_hRule(hRule)
+        , m_vRule(vRule)
+        , m_imagePaintingOptions(imagePaintingOptions)
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new DrawTiledScaledImage(image, destination, source, tileScaleFactor, hRule, vRule, imagePaintingOptions));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~DrawTiledScaledImage();
-
</del><span class="cx">     const Image& image() const { return m_image.get(); }
</span><span class="cx">     FloatRect source() const { return m_source; }
</span><span class="cx">     FloatRect destination() const { return m_destination; }
</span><span class="cx"> 
</span><span class="cx">     template<class Encoder> void encode(Encoder&) const;
</span><del>-    template<class Decoder> static Optional<Ref<DrawTiledScaledImage>> decode(Decoder&);
</del><ins>+    template<class Decoder> static Optional<DrawTiledScaledImage> decode(Decoder&);
</ins><span class="cx"> 
</span><del>-private:
-    WEBCORE_EXPORT DrawTiledScaledImage(Image&, const FloatRect& destination, const FloatRect& source, const FloatSize& tileScaleFactor, Image::TileRule hRule, Image::TileRule vRule, const ImagePaintingOptions&);
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><del>-    void apply(GraphicsContext&) const override;
</del><ins>+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return m_destination; }
</ins><span class="cx"> 
</span><del>-    Optional<FloatRect> localBounds(const GraphicsContext&) const override { return m_destination; }
-
</del><ins>+private:
</ins><span class="cx">     mutable Ref<Image> m_image; // FIXME: Drawing images can cause their animations to progress. This shouldn't have to be mutable.
</span><span class="cx">     FloatRect m_destination;
</span><span class="cx">     FloatRect m_source;
</span><span class="lines">@@ -1596,7 +1266,7 @@
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> template<class Decoder>
</span><del>-Optional<Ref<DrawTiledScaledImage>> DrawTiledScaledImage::decode(Decoder& decoder)
</del><ins>+Optional<DrawTiledScaledImage> DrawTiledScaledImage::decode(Decoder& decoder)
</ins><span class="cx"> {
</span><span class="cx">     Optional<ImageHandle> imageHandle;
</span><span class="cx">     decoder >> imageHandle;
</span><span class="lines">@@ -1631,18 +1301,23 @@
</span><span class="cx">     if (!imagePaintingOptions)
</span><span class="cx">         return WTF::nullopt;
</span><span class="cx"> 
</span><del>-    return DrawTiledScaledImage::create(*imageHandle->image, *destination, *source, *tileScaleFactor, hRule, vRule, *imagePaintingOptions);
</del><ins>+    return {{ *imageHandle->image, *destination, *source, *tileScaleFactor, hRule, vRule, *imagePaintingOptions }};
</ins><span class="cx"> }
</span><span class="cx"> 
</span><del>-class DrawImageBuffer : public DrawingItem {
</del><ins>+class DrawImageBuffer {
</ins><span class="cx"> public:
</span><del>-    static Ref<DrawImageBuffer> create(RenderingResourceIdentifier renderingResourceIdentifier, const FloatRect& destination, const FloatRect& source, const ImagePaintingOptions& options)
</del><ins>+    static constexpr ItemType itemType = ItemType::DrawImageBuffer;
+    static constexpr bool isInlineItem = true;
+    static constexpr bool isDrawingItem = true;
+
+    DrawImageBuffer(RenderingResourceIdentifier renderingResourceIdentifier, const FloatRect& destRect, const FloatRect& srcRect, const ImagePaintingOptions& options)
+        : m_renderingResourceIdentifier(renderingResourceIdentifier)
+        , m_destinationRect(destRect)
+        , m_srcRect(srcRect)
+        , m_options(options)
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new DrawImageBuffer(renderingResourceIdentifier, destination, source, options));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~DrawImageBuffer();
-
</del><span class="cx">     RenderingResourceIdentifier renderingResourceIdentifier() const { return m_renderingResourceIdentifier; }
</span><span class="cx">     FloatRect source() const { return m_srcRect; }
</span><span class="cx">     FloatRect destinationRect() const { return m_destinationRect; }
</span><span class="lines">@@ -1653,13 +1328,12 @@
</span><span class="cx">     template<class Encoder> void encode(Encoder&) const;
</span><span class="cx">     template<class Decoder> static Optional<Ref<DrawImageBuffer>> decode(Decoder&);
</span><span class="cx"> 
</span><del>-private:
-    WEBCORE_EXPORT DrawImageBuffer(RenderingResourceIdentifier, const FloatRect& destination, const FloatRect& source, const ImagePaintingOptions&);
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><del>-    void apply(GraphicsContext&) const override;
</del><ins>+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return m_destinationRect; }
</ins><span class="cx"> 
</span><del>-    Optional<FloatRect> localBounds(const GraphicsContext&) const override { return m_destinationRect; }
-
</del><ins>+private:
</ins><span class="cx">     RenderingResourceIdentifier m_renderingResourceIdentifier;
</span><span class="cx">     FloatRect m_destinationRect;
</span><span class="cx">     FloatRect m_srcRect;
</span><span class="lines">@@ -1666,63 +1340,26 @@
</span><span class="cx">     ImagePaintingOptions m_options;
</span><span class="cx"> };
</span><span class="cx"> 
</span><del>-template<class Encoder>
-void DrawImageBuffer::encode(Encoder& encoder) const
-{
-    encoder << m_renderingResourceIdentifier;
-    encoder << m_destinationRect;
-    encoder << m_srcRect;
-    encoder << m_options;
-}
</del><ins>+class DrawNativeImage {
+public:
+    static constexpr ItemType itemType = ItemType::DrawNativeImage;
+    static constexpr bool isInlineItem = false;
+    static constexpr bool isDrawingItem = true;
</ins><span class="cx"> 
</span><del>-template<class Decoder>
-Optional<Ref<DrawImageBuffer>> DrawImageBuffer::decode(Decoder& decoder)
-{
-    Optional<RenderingResourceIdentifier> renderingResourceIdentifier;
-    decoder >> renderingResourceIdentifier;
-    if (!renderingResourceIdentifier)
-        return WTF::nullopt;
</del><ins>+    WEBCORE_EXPORT DrawNativeImage(const NativeImagePtr&, const FloatSize& selfSize, const FloatRect& destRect, const FloatRect& srcRect, const ImagePaintingOptions&);
</ins><span class="cx"> 
</span><del>-    Optional<FloatRect> destination;
-    decoder >> destination;
-    if (!destination)
-        return WTF::nullopt;
</del><ins>+    const FloatRect& source() const { return m_srcRect; }
+    const FloatRect& destinationRect() const { return m_destinationRect; }
</ins><span class="cx"> 
</span><del>-    Optional<FloatRect> source;
-    decoder >> source;
-    if (!source)
-        return WTF::nullopt;
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><del>-    Optional<ImagePaintingOptions> options;
-    decoder >> options;
-    if (!options)
-        return WTF::nullopt;
</del><ins>+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return m_destinationRect; }
</ins><span class="cx"> 
</span><del>-    return DrawImageBuffer::create(*renderingResourceIdentifier, *destination, *source, *options);
-}
-
-class DrawNativeImage : public DrawingItem {
-public:
-    static Ref<DrawNativeImage> create(const NativeImagePtr& image, const FloatSize& imageSize, const FloatRect& destRect, const FloatRect& srcRect, const ImagePaintingOptions& options)
-    {
-        return adoptRef(*new DrawNativeImage(image, imageSize, destRect, srcRect, options));
-    }
-
-    WEBCORE_EXPORT virtual ~DrawNativeImage();
-
-    FloatRect source() const { return m_srcRect; }
-    FloatRect destinationRect() const { return m_destinationRect; }
-
</del><span class="cx">     template<class Encoder> void encode(Encoder&) const;
</span><del>-    template<class Decoder> static Optional<Ref<DrawNativeImage>> decode(Decoder&);
</del><ins>+    template<class Decoder> static Optional<DrawNativeImage> decode(Decoder&);
</ins><span class="cx"> 
</span><span class="cx"> private:
</span><del>-    WEBCORE_EXPORT DrawNativeImage(const NativeImagePtr&, const FloatSize& selfSize, const FloatRect& destRect, const FloatRect& srcRect, const ImagePaintingOptions&);
-
-    void apply(GraphicsContext&) const override;
-
-    Optional<FloatRect> localBounds(const GraphicsContext&) const override { return m_destinationRect; }
-
</del><span class="cx">     NativeImagePtr m_image;
</span><span class="cx">     FloatSize m_imageSize;
</span><span class="cx">     FloatRect m_destinationRect;
</span><span class="lines">@@ -1741,7 +1378,7 @@
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> template<class Decoder>
</span><del>-Optional<Ref<DrawNativeImage>> DrawNativeImage::decode(Decoder& decoder)
</del><ins>+Optional<DrawNativeImage> DrawNativeImage::decode(Decoder& decoder)
</ins><span class="cx"> {
</span><span class="cx">     Optional<NativeImagePtr> image;
</span><span class="cx">     decoder >> image;
</span><span class="lines">@@ -1768,17 +1405,16 @@
</span><span class="cx">     if (!options)
</span><span class="cx">         return WTF::nullopt;
</span><span class="cx"> 
</span><del>-    return DrawNativeImage::create(*image, *imageSize, *destinationRect, *srcRect, *options);
</del><ins>+    return {{ *image, *imageSize, *destinationRect, *srcRect, *options }};
</ins><span class="cx"> }
</span><span class="cx"> 
</span><del>-class DrawPattern : public DrawingItem {
</del><ins>+class DrawPattern {
</ins><span class="cx"> public:
</span><del>-    static Ref<DrawPattern> create(Image& image, const FloatRect& destRect, const FloatRect& tileRect, const AffineTransform& patternTransform, const FloatPoint& phase, const FloatSize& spacing, const ImagePaintingOptions& options)
-    {
-        return adoptRef(*new DrawPattern(image, destRect, tileRect, patternTransform, phase, spacing, options));
-    }
</del><ins>+    static constexpr ItemType itemType = ItemType::DrawPattern;
+    static constexpr bool isInlineItem = false;
+    static constexpr bool isDrawingItem = true;
</ins><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~DrawPattern();
</del><ins>+    WEBCORE_EXPORT DrawPattern(Image&, const FloatRect& destRect, const FloatRect& srcRect, const AffineTransform&, const FloatPoint& phase, const FloatSize& spacing, const ImagePaintingOptions& = { });
</ins><span class="cx"> 
</span><span class="cx">     const Image& image() const { return m_image.get(); }
</span><span class="cx">     const AffineTransform& patternTransform() const { return m_patternTransform; }
</span><span class="lines">@@ -1787,16 +1423,15 @@
</span><span class="cx">     FloatPoint phase() const { return m_phase; }
</span><span class="cx">     FloatSize spacing() const { return m_spacing; }
</span><span class="cx"> 
</span><ins>+    void apply(GraphicsContext&) const;
+
+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return m_destination; }
+
</ins><span class="cx">     template<class Encoder> void encode(Encoder&) const;
</span><del>-    template<class Decoder> static Optional<Ref<DrawPattern>> decode(Decoder&);
</del><ins>+    template<class Decoder> static Optional<DrawPattern> decode(Decoder&);
</ins><span class="cx"> 
</span><span class="cx"> private:
</span><del>-    WEBCORE_EXPORT DrawPattern(Image&, const FloatRect& destRect, const FloatRect& srcRect, const AffineTransform&, const FloatPoint& phase, const FloatSize& spacing, const ImagePaintingOptions& = { });
-
-    void apply(GraphicsContext&) const override;
-
-    Optional<FloatRect> localBounds(const GraphicsContext&) const override { return m_destination; }
-
</del><span class="cx">     mutable Ref<Image> m_image; // FIXME: Drawing images can cause their animations to progress. This shouldn't have to be mutable.
</span><span class="cx">     AffineTransform m_patternTransform;
</span><span class="cx">     FloatRect m_tileRect;
</span><span class="lines">@@ -1821,7 +1456,7 @@
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> template<class Decoder>
</span><del>-Optional<Ref<DrawPattern>> DrawPattern::decode(Decoder& decoder)
</del><ins>+Optional<DrawPattern> DrawPattern::decode(Decoder& decoder)
</ins><span class="cx"> {
</span><span class="cx">     Optional<ImageHandle> imageHandle;
</span><span class="cx">     decoder >> imageHandle;
</span><span class="lines">@@ -1858,182 +1493,100 @@
</span><span class="cx">     if (!options)
</span><span class="cx">         return WTF::nullopt;
</span><span class="cx"> 
</span><del>-    return DrawPattern::create(*imageHandle->image, *destination, *tileRect, *patternTransform, *phase, *spacing, *options);
</del><ins>+    return {{ *imageHandle->image, *destination, *tileRect, *patternTransform, *phase, *spacing, *options }};
</ins><span class="cx"> }
</span><span class="cx"> 
</span><del>-// Is DrawingItem because the size of the transparency layer is implicitly the clip bounds.
-class BeginTransparencyLayer : public DrawingItem {
</del><ins>+class BeginTransparencyLayer {
</ins><span class="cx"> public:
</span><del>-    static Ref<BeginTransparencyLayer> create(float opacity)
</del><ins>+    static constexpr ItemType itemType = ItemType::BeginTransparencyLayer;
+    static constexpr bool isInlineItem = true;
+    static constexpr bool isDrawingItem = true; // Is drawing item because the size of the transparency layer is implicitly the clip bounds.
+
+    BeginTransparencyLayer(float opacity)
+        : m_opacity(opacity)
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new BeginTransparencyLayer(opacity));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~BeginTransparencyLayer();
-
</del><span class="cx">     float opacity() const { return m_opacity; }
</span><span class="cx"> 
</span><del>-    template<class Encoder> void encode(Encoder&) const;
-    template<class Decoder> static Optional<Ref<BeginTransparencyLayer>> decode(Decoder&);
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><ins>+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return WTF::nullopt; }
+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+
</ins><span class="cx"> private:
</span><del>-    WEBCORE_EXPORT BeginTransparencyLayer(float opacity);
-
-    void apply(GraphicsContext&) const override;
-
</del><span class="cx">     float m_opacity;
</span><span class="cx"> };
</span><span class="cx"> 
</span><del>-template<class Encoder>
-void BeginTransparencyLayer::encode(Encoder& encoder) const
-{
-    encoder << m_opacity;
-}
-
-template<class Decoder>
-Optional<Ref<BeginTransparencyLayer>> BeginTransparencyLayer::decode(Decoder& decoder)
-{
-    Optional<float> opacity;
-    decoder >> opacity;
-    if (!opacity)
-        return WTF::nullopt;
-
-    return BeginTransparencyLayer::create(*opacity);
-}
-
-class EndTransparencyLayer : public DrawingItem {
</del><ins>+class EndTransparencyLayer {
</ins><span class="cx"> public:
</span><del>-    static Ref<EndTransparencyLayer> create()
-    {
-        return adoptRef(*new EndTransparencyLayer);
-    }
</del><ins>+    static constexpr ItemType itemType = ItemType::EndTransparencyLayer;
+    static constexpr bool isInlineItem = true;
+    static constexpr bool isDrawingItem = true;
</ins><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~EndTransparencyLayer();
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><del>-    template<class Encoder> void encode(Encoder&) const;
-    template<class Decoder> static Optional<Ref<EndTransparencyLayer>> decode(Decoder&);
-
-private:
-    WEBCORE_EXPORT EndTransparencyLayer();
-
-    void apply(GraphicsContext&) const override;
</del><ins>+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return WTF::nullopt; }
+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
</ins><span class="cx"> };
</span><span class="cx"> 
</span><del>-template<class Encoder>
-void EndTransparencyLayer::encode(Encoder&) const
-{
-}
</del><ins>+class DrawRect {
+public:
+    static constexpr ItemType itemType = ItemType::DrawRect;
+    static constexpr bool isInlineItem = true;
+    static constexpr bool isDrawingItem = true;
</ins><span class="cx"> 
</span><del>-template<class Decoder>
-Optional<Ref<EndTransparencyLayer>> EndTransparencyLayer::decode(Decoder&)
-{
-    return EndTransparencyLayer::create();
-}
-
-class DrawRect : public DrawingItem {
-public:
-    static Ref<DrawRect> create(const FloatRect& rect, float borderThickness)
</del><ins>+    DrawRect(FloatRect rect, float borderThickness)
+        : m_rect(rect)
+        , m_borderThickness(borderThickness)
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new DrawRect(rect, borderThickness));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~DrawRect();
-
</del><span class="cx">     FloatRect rect() const { return m_rect; }
</span><span class="cx">     float borderThickness() const { return m_borderThickness; }
</span><span class="cx"> 
</span><del>-    template<class Encoder> void encode(Encoder&) const;
-    template<class Decoder> static Optional<Ref<DrawRect>> decode(Decoder&);
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><ins>+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return m_rect; }
+
</ins><span class="cx"> private:
</span><del>-    WEBCORE_EXPORT DrawRect(const FloatRect&, float borderThickness);
-
-    void apply(GraphicsContext&) const override;
-    Optional<FloatRect> localBounds(const GraphicsContext&) const override { return m_rect; }
-
</del><span class="cx">     FloatRect m_rect;
</span><span class="cx">     float m_borderThickness;
</span><span class="cx"> };
</span><span class="cx"> 
</span><del>-template<class Encoder>
-void DrawRect::encode(Encoder& encoder) const
-{
-    encoder << m_rect;
-    encoder << m_borderThickness;
-}
</del><ins>+class DrawLine {
+public:
+    static constexpr ItemType itemType = ItemType::DrawLine;
+    static constexpr bool isInlineItem = true;
+    static constexpr bool isDrawingItem = true;
</ins><span class="cx"> 
</span><del>-template<class Decoder>
-Optional<Ref<DrawRect>> DrawRect::decode(Decoder& decoder)
-{
-    Optional<FloatRect> rect;
-    decoder >> rect;
-    if (!rect)
-        return WTF::nullopt;
-
-    Optional<float> borderThickness;
-    decoder >> borderThickness;
-    if (!borderThickness)
-        return WTF::nullopt;
-
-    return DrawRect::create(*rect, *borderThickness);
-}
-
-class DrawLine : public DrawingItem {
-public:
-    static Ref<DrawLine> create(const FloatPoint& point1, const FloatPoint& point2)
</del><ins>+    DrawLine(FloatPoint point1, FloatPoint point2)
+        : m_point1(point1)
+        , m_point2(point2)
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new DrawLine(point1, point2));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~DrawLine();
-
</del><span class="cx">     FloatPoint point1() const { return m_point1; }
</span><span class="cx">     FloatPoint point2() const { return m_point2; }
</span><span class="cx"> 
</span><del>-    template<class Encoder> void encode(Encoder&) const;
-    template<class Decoder> static Optional<Ref<DrawLine>> decode(Decoder&);
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><ins>+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+    Optional<FloatRect> localBounds(const GraphicsContext&) const;
+
</ins><span class="cx"> private:
</span><del>-    WEBCORE_EXPORT DrawLine(const FloatPoint&, const FloatPoint&);
-
-    void apply(GraphicsContext&) const override;
-    Optional<FloatRect> localBounds(const GraphicsContext&) const override;
-
</del><span class="cx">     FloatPoint m_point1;
</span><span class="cx">     FloatPoint m_point2;
</span><span class="cx"> };
</span><span class="cx"> 
</span><del>-template<class Encoder>
-void DrawLine::encode(Encoder& encoder) const
-{
-    encoder << m_point1;
-    encoder << m_point2;
-}
-
-template<class Decoder>
-Optional<Ref<DrawLine>> DrawLine::decode(Decoder& decoder)
-{
-    Optional<FloatPoint> point1;
-    decoder >> point1;
-    if (!point1)
-        return WTF::nullopt;
-
-    Optional<FloatPoint> point2;
-    decoder >> point2;
-    if (!point2)
-        return WTF::nullopt;
-
-    return DrawLine::create(*point1, *point2);
-}
-
-class DrawLinesForText : public DrawingItem {
</del><ins>+class DrawLinesForText {
</ins><span class="cx"> public:
</span><del>-    static Ref<DrawLinesForText> create(const FloatPoint& blockLocation, const FloatSize& localAnchor, float thickness, const DashArray& widths, bool printing, bool doubleLines)
-    {
-        return adoptRef(*new DrawLinesForText(blockLocation, localAnchor, thickness, widths, printing, doubleLines));
-    }
</del><ins>+    static constexpr ItemType itemType = ItemType::DrawLinesForText;
+    static constexpr bool isInlineItem = false;
+    static constexpr bool isDrawingItem = true;
</ins><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~DrawLinesForText();
</del><ins>+    WEBCORE_EXPORT DrawLinesForText(const FloatPoint& blockLocation, const FloatSize& localAnchor, float thickness, const DashArray& widths, bool printing, bool doubleLines);
</ins><span class="cx"> 
</span><span class="cx">     void setBlockLocation(const FloatPoint& blockLocation) { m_blockLocation = blockLocation; }
</span><span class="cx">     const FloatPoint& blockLocation() const { return m_blockLocation; }
</span><span class="lines">@@ -2044,16 +1597,15 @@
</span><span class="cx">     bool isPrinting() const { return m_printing; }
</span><span class="cx">     bool doubleLines() const { return m_doubleLines; }
</span><span class="cx"> 
</span><ins>+    void apply(GraphicsContext&) const;
+
+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+    Optional<FloatRect> localBounds(const GraphicsContext&) const;
+
</ins><span class="cx">     template<class Encoder> void encode(Encoder&) const;
</span><del>-    template<class Decoder> static Optional<Ref<DrawLinesForText>> decode(Decoder&);
</del><ins>+    template<class Decoder> static Optional<DrawLinesForText> decode(Decoder&);
</ins><span class="cx"> 
</span><span class="cx"> private:
</span><del>-    WEBCORE_EXPORT DrawLinesForText(const FloatPoint& blockLocation, const FloatSize& localAnchor, float thickness, const DashArray& widths, bool printing, bool doubleLines);
-
-    void apply(GraphicsContext&) const override;
-
-    Optional<FloatRect> localBounds(const GraphicsContext&) const override;
-
</del><span class="cx">     FloatPoint m_blockLocation;
</span><span class="cx">     FloatSize m_localAnchor;
</span><span class="cx">     DashArray m_widths;
</span><span class="lines">@@ -2074,7 +1626,7 @@
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> template<class Decoder>
</span><del>-Optional<Ref<DrawLinesForText>> DrawLinesForText::decode(Decoder& decoder)
</del><ins>+Optional<DrawLinesForText> DrawLinesForText::decode(Decoder& decoder)
</ins><span class="cx"> {
</span><span class="cx">     Optional<FloatPoint> blockLocation;
</span><span class="cx">     decoder >> blockLocation;
</span><span class="lines">@@ -2106,119 +1658,83 @@
</span><span class="cx">     if (!doubleLines)
</span><span class="cx">         return WTF::nullopt;
</span><span class="cx"> 
</span><del>-    return DrawLinesForText::create(*blockLocation, *localAnchor, *thickness, *widths, *printing, *doubleLines);
</del><ins>+    return {{ *blockLocation, *localAnchor, *thickness, *widths, *printing, *doubleLines }};
</ins><span class="cx"> }
</span><span class="cx"> 
</span><del>-class DrawDotsForDocumentMarker : public DrawingItem {
</del><ins>+class DrawDotsForDocumentMarker {
</ins><span class="cx"> public:
</span><del>-    static Ref<DrawDotsForDocumentMarker> create(const FloatRect& rect, DocumentMarkerLineStyle style)
</del><ins>+    static constexpr ItemType itemType = ItemType::DrawDotsForDocumentMarker;
+    static constexpr bool isInlineItem = true;
+    static constexpr bool isDrawingItem = true;
+
+    DrawDotsForDocumentMarker(const FloatRect& rect, DocumentMarkerLineStyle style)
+        : m_rect(rect)
+        , m_style(style)
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new DrawDotsForDocumentMarker(rect, style));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~DrawDotsForDocumentMarker();
-
</del><span class="cx">     FloatRect rect() const { return m_rect; }
</span><span class="cx"> 
</span><del>-    template<class Encoder> void encode(Encoder&) const;
-    template<class Decoder> static Optional<Ref<DrawDotsForDocumentMarker>> decode(Decoder&);
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><ins>+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+    Optional<FloatRect> localBounds(const GraphicsContext&) const;
+
</ins><span class="cx"> private:
</span><del>-    WEBCORE_EXPORT DrawDotsForDocumentMarker(const FloatRect&, DocumentMarkerLineStyle);
-
-    void apply(GraphicsContext&) const override;
-
-    Optional<FloatRect> localBounds(const GraphicsContext&) const override;
-
</del><span class="cx">     FloatRect m_rect;
</span><span class="cx">     DocumentMarkerLineStyle m_style;
</span><span class="cx"> };
</span><span class="cx"> 
</span><del>-template<class Encoder>
-void DrawDotsForDocumentMarker::encode(Encoder& encoder) const
-{
-    encoder << m_rect;
-    encoder << m_style;
-}
</del><ins>+class DrawEllipse {
+public:
+    static constexpr ItemType itemType = ItemType::DrawEllipse;
+    static constexpr bool isInlineItem = true;
+    static constexpr bool isDrawingItem = true;
</ins><span class="cx"> 
</span><del>-template<class Decoder>
-Optional<Ref<DrawDotsForDocumentMarker>> DrawDotsForDocumentMarker::decode(Decoder& decoder)
-{
-    Optional<FloatRect> rect;
-    decoder >> rect;
-    if (!rect)
-        return WTF::nullopt;
-
-    Optional<DocumentMarkerLineStyle> style;
-    decoder >> style;
-    if (!style)
-        return WTF::nullopt;
-
-    return DrawDotsForDocumentMarker::create(*rect, *style);
-}
-
-class DrawEllipse : public DrawingItem {
-public:
-    static Ref<DrawEllipse> create(const FloatRect& rect)
</del><ins>+    DrawEllipse(const FloatRect& rect)
+        : m_rect(rect)
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new DrawEllipse(rect));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT ~DrawEllipse();
-
</del><span class="cx">     FloatRect rect() const { return m_rect; }
</span><span class="cx"> 
</span><del>-    template<class Encoder> void encode(Encoder&) const;
-    template<class Decoder> static Optional<Ref<DrawEllipse>> decode(Decoder&);
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><ins>+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return m_rect; }
+
</ins><span class="cx"> private:
</span><del>-    WEBCORE_EXPORT DrawEllipse(const FloatRect&);
-
-    void apply(GraphicsContext&) const override;
-    Optional<FloatRect> localBounds(const GraphicsContext&) const override { return m_rect; }
-
</del><span class="cx">     FloatRect m_rect;
</span><span class="cx"> };
</span><span class="cx"> 
</span><del>-template<class Encoder>
-void DrawEllipse::encode(Encoder& encoder) const
-{
-    encoder << m_rect;
-}
</del><ins>+class DrawPath {
+public:
+    static constexpr ItemType itemType = ItemType::DrawPath;
+    static constexpr bool isInlineItem = false;
+    static constexpr bool isDrawingItem = true;
</ins><span class="cx"> 
</span><del>-template<class Decoder>
-Optional<Ref<DrawEllipse>> DrawEllipse::decode(Decoder& decoder)
-{
-    Optional<FloatRect> rect;
-    decoder >> rect;
-    if (!rect)
-        return WTF::nullopt;
</del><ins>+    DrawPath(const Path& path)
+        : m_path(path)
+    {
+    }
</ins><span class="cx"> 
</span><del>-    return DrawEllipse::create(*rect);
-}
-
-class DrawPath : public DrawingItem {
-public:
-    static Ref<DrawPath> create(const Path& path)
</del><ins>+    DrawPath(Path&& path)
+        : m_path(WTFMove(path))
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new DrawPath(path));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~DrawPath();
-
</del><span class="cx">     const Path& path() const { return m_path; }
</span><span class="cx"> 
</span><span class="cx">     template<class Encoder> void encode(Encoder&) const;
</span><del>-    template<class Decoder> static Optional<Ref<DrawPath>> decode(Decoder&);
</del><ins>+    template<class Decoder> static Optional<DrawPath> decode(Decoder&);
</ins><span class="cx"> 
</span><del>-private:
-    WEBCORE_EXPORT DrawPath(const Path&);
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><del>-    void apply(GraphicsContext&) const override;
</del><ins>+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return m_path.fastBoundingRect(); }
</ins><span class="cx"> 
</span><del>-    Optional<FloatRect> localBounds(const GraphicsContext&) const override { return m_path.fastBoundingRect(); }
-
-    const Path m_path;
</del><ins>+private:
+    Path m_path;
</ins><span class="cx"> };
</span><span class="cx"> 
</span><span class="cx"> template<class Encoder>
</span><span class="lines">@@ -2228,7 +1744,7 @@
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> template<class Decoder>
</span><del>-Optional<Ref<DrawPath>> DrawPath::decode(Decoder& decoder)
</del><ins>+Optional<DrawPath> DrawPath::decode(Decoder& decoder)
</ins><span class="cx"> {
</span><span class="cx">     Optional<Path> path;
</span><span class="cx">     decoder >> path;
</span><span class="lines">@@ -2235,17 +1751,30 @@
</span><span class="cx">     if (!path)
</span><span class="cx">         return WTF::nullopt;
</span><span class="cx"> 
</span><del>-    return DrawPath::create(*path);
</del><ins>+    return {{ WTFMove(*path) }};
</ins><span class="cx"> }
</span><span class="cx"> 
</span><del>-class DrawFocusRingPath : public DrawingItem {
</del><ins>+class DrawFocusRingPath {
</ins><span class="cx"> public:
</span><del>-    static Ref<DrawFocusRingPath> create(const Path& path, float width, float offset, const Color& color)
</del><ins>+    static constexpr ItemType itemType = ItemType::DrawFocusRingPath;
+    static constexpr bool isInlineItem = false;
+    static constexpr bool isDrawingItem = true;
+
+    DrawFocusRingPath(Path&& path, float width, float offset, Color color)
+        : m_path(WTFMove(path))
+        , m_width(width)
+        , m_offset(offset)
+        , m_color(color)
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new DrawFocusRingPath(path, width, offset, color));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~DrawFocusRingPath();
</del><ins>+    DrawFocusRingPath(const Path& path, float width, float offset, Color color)
+        : m_path(path)
+        , m_width(width)
+        , m_offset(offset)
+        , m_color(color)
+    {
+    }
</ins><span class="cx"> 
</span><span class="cx">     const Path& path() const { return m_path; }
</span><span class="cx">     float width() const { return m_width; }
</span><span class="lines">@@ -2253,16 +1782,15 @@
</span><span class="cx">     const Color& color() const { return m_color; }
</span><span class="cx"> 
</span><span class="cx">     template<class Encoder> void encode(Encoder&) const;
</span><del>-    template<class Decoder> static Optional<Ref<DrawFocusRingPath>> decode(Decoder&);
</del><ins>+    template<class Decoder> static Optional<DrawFocusRingPath> decode(Decoder&);
</ins><span class="cx"> 
</span><del>-private:
-    WEBCORE_EXPORT DrawFocusRingPath(const Path&, float width, float offset, const Color&);
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><del>-    void apply(GraphicsContext&) const override;
</del><ins>+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+    Optional<FloatRect> localBounds(const GraphicsContext&) const;
</ins><span class="cx"> 
</span><del>-    Optional<FloatRect> localBounds(const GraphicsContext&) const override;
-
-    const Path m_path;
</del><ins>+private:
+    Path m_path;
</ins><span class="cx">     float m_width;
</span><span class="cx">     float m_offset;
</span><span class="cx">     Color m_color;
</span><span class="lines">@@ -2278,7 +1806,7 @@
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> template<class Decoder>
</span><del>-Optional<Ref<DrawFocusRingPath>> DrawFocusRingPath::decode(Decoder& decoder)
</del><ins>+Optional<DrawFocusRingPath> DrawFocusRingPath::decode(Decoder& decoder)
</ins><span class="cx"> {
</span><span class="cx">     Optional<Path> path;
</span><span class="cx">     decoder >> path;
</span><span class="lines">@@ -2300,17 +1828,16 @@
</span><span class="cx">     if (!color)
</span><span class="cx">         return WTF::nullopt;
</span><span class="cx"> 
</span><del>-    return DrawFocusRingPath::create(*path, *width, *offset, *color);
</del><ins>+    return {{ WTFMove(*path), *width, *offset, *color }};
</ins><span class="cx"> }
</span><span class="cx"> 
</span><del>-class DrawFocusRingRects : public DrawingItem {
</del><ins>+class DrawFocusRingRects {
</ins><span class="cx"> public:
</span><del>-    static Ref<DrawFocusRingRects> create(const Vector<FloatRect>& rects, float width, float offset, const Color& color)
-    {
-        return adoptRef(*new DrawFocusRingRects(rects, width, offset, color));
-    }
</del><ins>+    static constexpr ItemType itemType = ItemType::DrawFocusRingRects;
+    static constexpr bool isInlineItem = false;
+    static constexpr bool isDrawingItem = true;
</ins><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~DrawFocusRingRects();
</del><ins>+    WEBCORE_EXPORT DrawFocusRingRects(const Vector<FloatRect>&, float width, float offset, const Color&);
</ins><span class="cx"> 
</span><span class="cx">     const Vector<FloatRect> rects() const { return m_rects; }
</span><span class="cx">     float width() const { return m_width; }
</span><span class="lines">@@ -2317,16 +1844,15 @@
</span><span class="cx">     float offset() const { return m_offset; }
</span><span class="cx">     const Color& color() const { return m_color; }
</span><span class="cx"> 
</span><ins>+    void apply(GraphicsContext&) const;
+
+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+    Optional<FloatRect> localBounds(const GraphicsContext&) const;
+
</ins><span class="cx">     template<class Encoder> void encode(Encoder&) const;
</span><del>-    template<class Decoder> static Optional<Ref<DrawFocusRingRects>> decode(Decoder&);
</del><ins>+    template<class Decoder> static Optional<DrawFocusRingRects> decode(Decoder&);
</ins><span class="cx"> 
</span><span class="cx"> private:
</span><del>-    WEBCORE_EXPORT DrawFocusRingRects(const Vector<FloatRect>&, float width, float offset, const Color&);
-
-    void apply(GraphicsContext&) const override;
-
-    Optional<FloatRect> localBounds(const GraphicsContext&) const override;
-
</del><span class="cx">     Vector<FloatRect> m_rects;
</span><span class="cx">     float m_width;
</span><span class="cx">     float m_offset;
</span><span class="lines">@@ -2343,7 +1869,7 @@
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> template<class Decoder>
</span><del>-Optional<Ref<DrawFocusRingRects>> DrawFocusRingRects::decode(Decoder& decoder)
</del><ins>+Optional<DrawFocusRingRects> DrawFocusRingRects::decode(Decoder& decoder)
</ins><span class="cx"> {
</span><span class="cx">     Optional<Vector<FloatRect>> rects;
</span><span class="cx">     decoder >> rects;
</span><span class="lines">@@ -2365,71 +1891,55 @@
</span><span class="cx">     if (!color)
</span><span class="cx">         return WTF::nullopt;
</span><span class="cx"> 
</span><del>-    return DrawFocusRingRects::create(*rects, *width, *offset, *color);
</del><ins>+    return {{ *rects, *width, *offset, *color }};
</ins><span class="cx"> }
</span><span class="cx"> 
</span><del>-class FillRect : public DrawingItem {
</del><ins>+class FillRect {
</ins><span class="cx"> public:
</span><del>-    static Ref<FillRect> create(const FloatRect& rect)
</del><ins>+    static constexpr ItemType itemType = ItemType::FillRect;
+    static constexpr bool isInlineItem = true;
+    static constexpr bool isDrawingItem = true;
+
+    FillRect(const FloatRect& rect)
+        : m_rect(rect)
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new FillRect(rect));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~FillRect();
</del><ins>+    const FloatRect& rect() const { return m_rect; }
</ins><span class="cx"> 
</span><del>-    FloatRect rect() const { return m_rect; }
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><del>-    template<class Encoder> void encode(Encoder&) const;
-    template<class Decoder> static Optional<Ref<FillRect>> decode(Decoder&);
</del><ins>+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return m_rect; }
</ins><span class="cx"> 
</span><span class="cx"> private:
</span><del>-    WEBCORE_EXPORT FillRect(const FloatRect&);
-
-    void apply(GraphicsContext&) const override;
-    Optional<FloatRect> localBounds(const GraphicsContext&) const override { return m_rect; }
-
</del><span class="cx">     FloatRect m_rect;
</span><span class="cx"> };
</span><span class="cx"> 
</span><del>-template<class Encoder>
-void FillRect::encode(Encoder& encoder) const
-{
-    encoder << m_rect;
-}
</del><ins>+class FillRectWithColor {
+public:
+    static constexpr ItemType itemType = ItemType::FillRectWithColor;
+    static constexpr bool isInlineItem = false;
+    static constexpr bool isDrawingItem = true;
</ins><span class="cx"> 
</span><del>-template<class Decoder>
-Optional<Ref<FillRect>> FillRect::decode(Decoder& decoder)
-{
-    Optional<FloatRect> rect;
-    decoder >> rect;
-    if (!rect)
-        return WTF::nullopt;
-
-    return FillRect::create(*rect);
-}
-
-// FIXME: Make these inherit from FillRect proper.
-class FillRectWithColor : public DrawingItem {
-public:
-    static Ref<FillRectWithColor> create(const FloatRect& rect, const Color& color)
</del><ins>+    FillRectWithColor(const FloatRect& rect, const Color& color)
+        : m_rect(rect)
+        , m_color(color)
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new FillRectWithColor(rect, color));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~FillRectWithColor();
-
</del><span class="cx">     FloatRect rect() const { return m_rect; }
</span><span class="cx">     const Color& color() const { return m_color; }
</span><span class="cx"> 
</span><ins>+    void apply(GraphicsContext&) const;
+
+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return m_rect; }
+
</ins><span class="cx">     template<class Encoder> void encode(Encoder&) const;
</span><del>-    template<class Decoder> static Optional<Ref<FillRectWithColor>> decode(Decoder&);
</del><ins>+    template<class Decoder> static Optional<FillRectWithColor> decode(Decoder&);
</ins><span class="cx"> 
</span><span class="cx"> private:
</span><del>-    WEBCORE_EXPORT FillRectWithColor(const FloatRect&, const Color&);
-
-    void apply(GraphicsContext&) const override;
-    Optional<FloatRect> localBounds(const GraphicsContext&) const override { return m_rect; }
-
</del><span class="cx">     FloatRect m_rect;
</span><span class="cx">     Color m_color;
</span><span class="cx"> };
</span><span class="lines">@@ -2442,7 +1952,7 @@
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> template<class Decoder>
</span><del>-Optional<Ref<FillRectWithColor>> FillRectWithColor::decode(Decoder& decoder)
</del><ins>+Optional<FillRectWithColor> FillRectWithColor::decode(Decoder& decoder)
</ins><span class="cx"> {
</span><span class="cx">     Optional<FloatRect> rect;
</span><span class="cx">     decoder >> rect;
</span><span class="lines">@@ -2454,29 +1964,29 @@
</span><span class="cx">     if (!color)
</span><span class="cx">         return WTF::nullopt;
</span><span class="cx"> 
</span><del>-    return FillRectWithColor::create(*rect, *color);
</del><ins>+    return {{ *rect, *color }};
</ins><span class="cx"> }
</span><span class="cx"> 
</span><del>-class FillRectWithGradient : public DrawingItem {
</del><ins>+class FillRectWithGradient {
</ins><span class="cx"> public:
</span><del>-    static Ref<FillRectWithGradient> create(const FloatRect& rect, Gradient& gradient)
-    {
-        return adoptRef(*new FillRectWithGradient(rect, gradient));
-    }
</del><ins>+    static constexpr ItemType itemType = ItemType::FillRectWithGradient;
+    static constexpr bool isInlineItem = false;
+    static constexpr bool isDrawingItem = true;
</ins><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~FillRectWithGradient();
</del><ins>+    WEBCORE_EXPORT FillRectWithGradient(const FloatRect&, Gradient&);
</ins><span class="cx"> 
</span><del>-    FloatRect rect() const { return m_rect; }
</del><ins>+    const FloatRect& rect() const { return m_rect; }
+    const Gradient& gradient() const { return m_gradient.get(); }
</ins><span class="cx"> 
</span><ins>+    void apply(GraphicsContext&) const;
+
+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return m_rect; }
+
</ins><span class="cx">     template<class Encoder> void encode(Encoder&) const;
</span><del>-    template<class Decoder> static Optional<Ref<FillRectWithGradient>> decode(Decoder&);
</del><ins>+    template<class Decoder> static Optional<FillRectWithGradient> decode(Decoder&);
</ins><span class="cx"> 
</span><span class="cx"> private:
</span><del>-    WEBCORE_EXPORT FillRectWithGradient(const FloatRect&, Gradient&);
-
-    void apply(GraphicsContext&) const override;
-    Optional<FloatRect> localBounds(const GraphicsContext&) const override { return m_rect; }
-
</del><span class="cx">     FloatRect m_rect;
</span><span class="cx">     mutable Ref<Gradient> m_gradient; // FIXME: Make this not mutable
</span><span class="cx"> };
</span><span class="lines">@@ -2489,7 +1999,7 @@
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> template<class Decoder>
</span><del>-Optional<Ref<FillRectWithGradient>> FillRectWithGradient::decode(Decoder& decoder)
</del><ins>+Optional<FillRectWithGradient> FillRectWithGradient::decode(Decoder& decoder)
</ins><span class="cx"> {
</span><span class="cx">     Optional<FloatRect> rect;
</span><span class="cx">     decoder >> rect;
</span><span class="lines">@@ -2500,32 +2010,37 @@
</span><span class="cx">     if (!gradient)
</span><span class="cx">         return WTF::nullopt;
</span><span class="cx"> 
</span><del>-    return FillRectWithGradient::create(*rect, gradient->get());
</del><ins>+    return {{ *rect, gradient->get() }};
</ins><span class="cx"> }
</span><span class="cx"> 
</span><del>-class FillCompositedRect : public DrawingItem {
</del><ins>+class FillCompositedRect {
</ins><span class="cx"> public:
</span><del>-    static Ref<FillCompositedRect> create(const FloatRect& rect, const Color& color, CompositeOperator op, BlendMode blendMode)
</del><ins>+    static constexpr ItemType itemType = ItemType::FillCompositedRect;
+    static constexpr bool isInlineItem = false;
+    static constexpr bool isDrawingItem = true;
+
+    FillCompositedRect(const FloatRect& rect, const Color& color, CompositeOperator op, BlendMode blendMode)
+        : m_rect(rect)
+        , m_color(color)
+        , m_op(op)
+        , m_blendMode(blendMode)
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new FillCompositedRect(rect, color, op, blendMode));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~FillCompositedRect();
-
</del><span class="cx">     FloatRect rect() const { return m_rect; }
</span><span class="cx">     const Color& color() const { return m_color; }
</span><span class="cx">     CompositeOperator compositeOperator() const { return m_op; }
</span><span class="cx">     BlendMode blendMode() const { return m_blendMode; }
</span><span class="cx"> 
</span><ins>+    void apply(GraphicsContext&) const;
+
+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return m_rect; }
+
</ins><span class="cx">     template<class Encoder> void encode(Encoder&) const;
</span><del>-    template<class Decoder> static Optional<Ref<FillCompositedRect>> decode(Decoder&);
</del><ins>+    template<class Decoder> static Optional<FillCompositedRect> decode(Decoder&);
</ins><span class="cx"> 
</span><span class="cx"> private:
</span><del>-    WEBCORE_EXPORT FillCompositedRect(const FloatRect&, const Color&, CompositeOperator, BlendMode);
-
-    void apply(GraphicsContext&) const override;
-    Optional<FloatRect> localBounds(const GraphicsContext&) const override { return m_rect; }
-
</del><span class="cx">     FloatRect m_rect;
</span><span class="cx">     Color m_color;
</span><span class="cx">     CompositeOperator m_op;
</span><span class="lines">@@ -2542,7 +2057,7 @@
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> template<class Decoder>
</span><del>-Optional<Ref<FillCompositedRect>> FillCompositedRect::decode(Decoder& decoder)
</del><ins>+Optional<FillCompositedRect> FillCompositedRect::decode(Decoder& decoder)
</ins><span class="cx"> {
</span><span class="cx">     Optional<FloatRect> rect;
</span><span class="cx">     decoder >> rect;
</span><span class="lines">@@ -2564,31 +2079,35 @@
</span><span class="cx">     if (!blendMode)
</span><span class="cx">         return WTF::nullopt;
</span><span class="cx"> 
</span><del>-    return FillCompositedRect::create(*rect, *color, *op, *blendMode);
</del><ins>+    return {{ *rect, *color, *op, *blendMode }};
</ins><span class="cx"> }
</span><span class="cx"> 
</span><del>-class FillRoundedRect : public DrawingItem {
</del><ins>+class FillRoundedRect {
</ins><span class="cx"> public:
</span><del>-    static Ref<FillRoundedRect> create(const FloatRoundedRect& rect, const Color& color, BlendMode blendMode)
</del><ins>+    static constexpr ItemType itemType = ItemType::FillRoundedRect;
+    static constexpr bool isInlineItem = false;
+    static constexpr bool isDrawingItem = true;
+
+    FillRoundedRect(const FloatRoundedRect& rect, const Color& color, BlendMode blendMode)
+        : m_rect(rect)
+        , m_color(color)
+        , m_blendMode(blendMode)
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new FillRoundedRect(rect, color, blendMode));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~FillRoundedRect();
-
</del><span class="cx">     const FloatRoundedRect& roundedRect() const { return m_rect; }
</span><span class="cx">     const Color& color() const { return m_color; }
</span><span class="cx">     BlendMode blendMode() const { return m_blendMode; }
</span><span class="cx"> 
</span><span class="cx">     template<class Encoder> void encode(Encoder&) const;
</span><del>-    template<class Decoder> static Optional<Ref<FillRoundedRect>> decode(Decoder&);
</del><ins>+    template<class Decoder> static Optional<FillRoundedRect> decode(Decoder&);
</ins><span class="cx"> 
</span><del>-private:
-    WEBCORE_EXPORT FillRoundedRect(const FloatRoundedRect&, const Color&, BlendMode);
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><del>-    void apply(GraphicsContext&) const override;
-    Optional<FloatRect> localBounds(const GraphicsContext&) const override { return m_rect.rect(); }
</del><ins>+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return m_rect.rect(); }
</ins><span class="cx"> 
</span><ins>+private:
</ins><span class="cx">     FloatRoundedRect m_rect;
</span><span class="cx">     Color m_color;
</span><span class="cx">     BlendMode m_blendMode;
</span><span class="lines">@@ -2603,7 +2122,7 @@
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> template<class Decoder>
</span><del>-Optional<Ref<FillRoundedRect>> FillRoundedRect::decode(Decoder& decoder)
</del><ins>+Optional<FillRoundedRect> FillRoundedRect::decode(Decoder& decoder)
</ins><span class="cx"> {
</span><span class="cx">     Optional<FloatRoundedRect> rect;
</span><span class="cx">     decoder >> rect;
</span><span class="lines">@@ -2620,31 +2139,35 @@
</span><span class="cx">     if (!blendMode)
</span><span class="cx">         return WTF::nullopt;
</span><span class="cx"> 
</span><del>-    return FillRoundedRect::create(*rect, *color, *blendMode);
</del><ins>+    return {{ *rect, *color, *blendMode }};
</ins><span class="cx"> }
</span><span class="cx"> 
</span><del>-class FillRectWithRoundedHole : public DrawingItem {
</del><ins>+class FillRectWithRoundedHole {
</ins><span class="cx"> public:
</span><del>-    static Ref<FillRectWithRoundedHole> create(const FloatRect& rect, const FloatRoundedRect& roundedHoleRect, const Color& color)
</del><ins>+    static constexpr ItemType itemType = ItemType::FillRectWithRoundedHole;
+    static constexpr bool isInlineItem = false;
+    static constexpr bool isDrawingItem = true;
+
+    FillRectWithRoundedHole(const FloatRect& rect, const FloatRoundedRect& roundedHoleRect, const Color& color)
+        : m_rect(rect)
+        , m_roundedHoleRect(roundedHoleRect)
+        , m_color(color)
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new FillRectWithRoundedHole(rect, roundedHoleRect, color));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~FillRectWithRoundedHole();
-
</del><span class="cx">     const FloatRect& rect() const { return m_rect; }
</span><span class="cx">     const FloatRoundedRect& roundedHoleRect() const { return m_roundedHoleRect; }
</span><span class="cx">     const Color& color() const { return m_color; }
</span><span class="cx"> 
</span><span class="cx">     template<class Encoder> void encode(Encoder&) const;
</span><del>-    template<class Decoder> static Optional<Ref<FillRectWithRoundedHole>> decode(Decoder&);
</del><ins>+    template<class Decoder> static Optional<FillRectWithRoundedHole> decode(Decoder&);
</ins><span class="cx"> 
</span><del>-private:
-    WEBCORE_EXPORT FillRectWithRoundedHole(const FloatRect&, const FloatRoundedRect&, const Color&);
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><del>-    void apply(GraphicsContext&) const override;
-    Optional<FloatRect> localBounds(const GraphicsContext&) const override { return m_rect; }
</del><ins>+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return m_rect; }
</ins><span class="cx"> 
</span><ins>+private:
</ins><span class="cx">     FloatRect m_rect;
</span><span class="cx">     FloatRoundedRect m_roundedHoleRect;
</span><span class="cx">     Color m_color;
</span><span class="lines">@@ -2659,7 +2182,7 @@
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> template<class Decoder>
</span><del>-Optional<Ref<FillRectWithRoundedHole>> FillRectWithRoundedHole::decode(Decoder& decoder)
</del><ins>+Optional<FillRectWithRoundedHole> FillRectWithRoundedHole::decode(Decoder& decoder)
</ins><span class="cx"> {
</span><span class="cx">     Optional<FloatRect> rect;
</span><span class="cx">     decoder >> rect;
</span><span class="lines">@@ -2676,74 +2199,63 @@
</span><span class="cx">     if (!color)
</span><span class="cx">         return WTF::nullopt;
</span><span class="cx"> 
</span><del>-    return FillRectWithRoundedHole::create(*rect, *roundedHoleRect, *color);
</del><ins>+    return {{ *rect, *roundedHoleRect, *color }};
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> #if ENABLE(INLINE_PATH_DATA)
</span><span class="cx"> 
</span><del>-class FillInlinePath : public DrawingItem {
</del><ins>+class FillInlinePath {
</ins><span class="cx"> public:
</span><del>-    static Ref<FillInlinePath> create(const InlinePathData& pathData)
</del><ins>+    static constexpr ItemType itemType = ItemType::FillInlinePath;
+    static constexpr bool isInlineItem = true;
+    static constexpr bool isDrawingItem = true;
+
+    FillInlinePath(const InlinePathData& pathData)
+        : m_pathData(pathData)
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new FillInlinePath(pathData));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~FillInlinePath();
-
</del><span class="cx">     Path path() const { return Path::from(m_pathData); }
</span><span class="cx"> 
</span><del>-    template<class Encoder> void encode(Encoder&) const;
-    template<class Decoder> static Optional<Ref<FillInlinePath>> decode(Decoder&);
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><ins>+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return path().fastBoundingRect(); }
+
</ins><span class="cx"> private:
</span><del>-    WEBCORE_EXPORT FillInlinePath(const InlinePathData&);
-
-    void apply(GraphicsContext&) const override;
-    Optional<FloatRect> localBounds(const GraphicsContext&) const override { return path().fastBoundingRect(); }
-
</del><span class="cx">     InlinePathData m_pathData;
</span><span class="cx"> };
</span><span class="cx"> 
</span><del>-template<class Encoder>
-void FillInlinePath::encode(Encoder& encoder) const
-{
-    encoder << m_pathData;
-}
-
-template<class Decoder>
-Optional<Ref<FillInlinePath>> FillInlinePath::decode(Decoder& decoder)
-{
-    Optional<InlinePathData> pathData;
-    decoder >> pathData;
-    if (!pathData)
-        return WTF::nullopt;
-
-    return FillInlinePath::create(WTFMove(*pathData));
-}
-
</del><span class="cx"> #endif // ENABLE(INLINE_PATH_DATA)
</span><span class="cx"> 
</span><del>-class FillPath : public DrawingItem {
</del><ins>+class FillPath {
</ins><span class="cx"> public:
</span><del>-    static Ref<FillPath> create(const Path& path)
</del><ins>+    static constexpr ItemType itemType = ItemType::FillPath;
+    static constexpr bool isInlineItem = false;
+    static constexpr bool isDrawingItem = true;
+
+    FillPath(Path&& path)
+        : m_path(WTFMove(path))
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new FillPath(path));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~FillPath();
</del><ins>+    FillPath(const Path& path)
+        : m_path(path)
+    {
+    }
</ins><span class="cx"> 
</span><span class="cx">     const Path& path() const { return m_path; }
</span><span class="cx"> 
</span><span class="cx">     template<class Encoder> void encode(Encoder&) const;
</span><del>-    template<class Decoder> static Optional<Ref<FillPath>> decode(Decoder&);
</del><ins>+    template<class Decoder> static Optional<FillPath> decode(Decoder&);
</ins><span class="cx"> 
</span><del>-private:
-    WEBCORE_EXPORT FillPath(const Path&);
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><del>-    void apply(GraphicsContext&) const override;
-    Optional<FloatRect> localBounds(const GraphicsContext&) const override { return m_path.fastBoundingRect(); }
</del><ins>+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return m_path.fastBoundingRect(); }
</ins><span class="cx"> 
</span><del>-    const Path m_path;
</del><ins>+private:
+    Path m_path;
</ins><span class="cx"> };
</span><span class="cx"> 
</span><span class="cx"> template<class Encoder>
</span><span class="lines">@@ -2753,7 +2265,7 @@
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> template<class Decoder>
</span><del>-Optional<Ref<FillPath>> FillPath::decode(Decoder& decoder)
</del><ins>+Optional<FillPath> FillPath::decode(Decoder& decoder)
</ins><span class="cx"> {
</span><span class="cx">     Optional<Path> path;
</span><span class="cx">     decoder >> path;
</span><span class="lines">@@ -2760,83 +2272,58 @@
</span><span class="cx">     if (!path)
</span><span class="cx">         return WTF::nullopt;
</span><span class="cx"> 
</span><del>-    return FillPath::create(*path);
</del><ins>+    return {{ WTFMove(*path) }};
</ins><span class="cx"> }
</span><span class="cx"> 
</span><del>-class FillEllipse : public DrawingItem {
</del><ins>+class FillEllipse {
</ins><span class="cx"> public:
</span><del>-    static Ref<FillEllipse> create(const FloatRect& rect)
</del><ins>+    static constexpr ItemType itemType = ItemType::FillEllipse;
+    static constexpr bool isInlineItem = true;
+    static constexpr bool isDrawingItem = true;
+
+    FillEllipse(const FloatRect& rect)
+        : m_rect(rect)
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new FillEllipse(rect));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~FillEllipse();
-
</del><span class="cx">     FloatRect rect() const { return m_rect; }
</span><span class="cx"> 
</span><del>-    template<class Encoder> void encode(Encoder&) const;
-    template<class Decoder> static Optional<Ref<FillEllipse>> decode(Decoder&);
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><ins>+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return m_rect; }
+
</ins><span class="cx"> private:
</span><del>-    WEBCORE_EXPORT FillEllipse(const FloatRect&);
-
-    void apply(GraphicsContext&) const override;
-
-    Optional<FloatRect> localBounds(const GraphicsContext&) const override { return m_rect; }
-
</del><span class="cx">     FloatRect m_rect;
</span><span class="cx"> };
</span><span class="cx"> 
</span><del>-template<class Encoder>
-void FillEllipse::encode(Encoder& encoder) const
-{
-    encoder << m_rect;
-}
-
-template<class Decoder>
-Optional<Ref<FillEllipse>> FillEllipse::decode(Decoder& decoder)
-{
-    Optional<FloatRect> rect;
-    decoder >> rect;
-    if (!rect)
-        return WTF::nullopt;
-
-    return FillEllipse::create(*rect);
-}
-
-class PutImageData : public DrawingItem {
</del><ins>+class PutImageData {
</ins><span class="cx"> public:
</span><del>-    static Ref<PutImageData> create(AlphaPremultiplication inputFormat, const ImageData& imageData, const IntRect& srcRect, const IntPoint& destPoint, AlphaPremultiplication destFormat)
-    {
-        return adoptRef(*new PutImageData(inputFormat, imageData, srcRect, destPoint, destFormat));
-    }
-    static Ref<PutImageData> create(AlphaPremultiplication inputFormat, Ref<ImageData>&& imageData, const IntRect& srcRect, const IntPoint& destPoint, AlphaPremultiplication destFormat)
-    {
-        return adoptRef(*new PutImageData(inputFormat, WTFMove(imageData), srcRect, destPoint, destFormat));
-    }
</del><ins>+    static constexpr ItemType itemType = ItemType::PutImageData;
+    static constexpr bool isInlineItem = false;
+    static constexpr bool isDrawingItem = true;
</ins><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~PutImageData();
</del><ins>+    WEBCORE_EXPORT PutImageData(AlphaPremultiplication inputFormat, const ImageData&, const IntRect& srcRect, const IntPoint& destPoint, AlphaPremultiplication destFormat);
+    WEBCORE_EXPORT PutImageData(AlphaPremultiplication inputFormat, Ref<ImageData>&&, const IntRect& srcRect, const IntPoint& destPoint, AlphaPremultiplication destFormat);
</ins><span class="cx"> 
</span><span class="cx">     AlphaPremultiplication inputFormat() const { return m_inputFormat; }
</span><del>-    ImageData& imageData() const { return m_imageData; }
</del><ins>+    ImageData& imageData() const { return *m_imageData; }
</ins><span class="cx">     IntRect srcRect() const { return m_srcRect; }
</span><span class="cx">     IntPoint destPoint() const { return m_destPoint; }
</span><span class="cx">     AlphaPremultiplication destFormat() const { return m_destFormat; }
</span><span class="cx"> 
</span><ins>+    void apply(GraphicsContext&) const;
+
+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return WTF::nullopt; }
+    Optional<FloatRect> globalBounds() const { return {{ m_destPoint, m_srcRect.size() }}; }
+
</ins><span class="cx">     template<class Encoder> void encode(Encoder&) const;
</span><del>-    template<class Decoder> static Optional<Ref<PutImageData>> decode(Decoder&);
</del><ins>+    template<class Decoder> static Optional<PutImageData> decode(Decoder&);
</ins><span class="cx"> 
</span><span class="cx"> private:
</span><del>-    WEBCORE_EXPORT PutImageData(AlphaPremultiplication inputFormat, const ImageData&, const IntRect& srcRect, const IntPoint& destPoint, AlphaPremultiplication destFormat);
-    WEBCORE_EXPORT PutImageData(AlphaPremultiplication inputFormat, Ref<ImageData>&&, const IntRect& srcRect, const IntPoint& destPoint, AlphaPremultiplication destFormat);
-
-    void apply(GraphicsContext&) const override;
-
-    Optional<FloatRect> globalBounds() const override { return FloatRect(m_destPoint, m_srcRect.size()); }
-
</del><span class="cx">     IntRect m_srcRect;
</span><span class="cx">     IntPoint m_destPoint;
</span><del>-    Ref<ImageData> m_imageData;
</del><ins>+    RefPtr<ImageData> m_imageData;
</ins><span class="cx">     AlphaPremultiplication m_inputFormat;
</span><span class="cx">     AlphaPremultiplication m_destFormat;
</span><span class="cx"> };
</span><span class="lines">@@ -2845,7 +2332,7 @@
</span><span class="cx"> void PutImageData::encode(Encoder& encoder) const
</span><span class="cx"> {
</span><span class="cx">     encoder << m_inputFormat;
</span><del>-    encoder << m_imageData;
</del><ins>+    encoder << makeRef(*m_imageData);
</ins><span class="cx">     encoder << m_srcRect;
</span><span class="cx">     encoder << m_destPoint;
</span><span class="cx">     encoder << m_destFormat;
</span><span class="lines">@@ -2852,7 +2339,7 @@
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> template<class Decoder>
</span><del>-Optional<Ref<PutImageData>> PutImageData::decode(Decoder& decoder)
</del><ins>+Optional<PutImageData> PutImageData::decode(Decoder& decoder)
</ins><span class="cx"> {
</span><span class="cx">     Optional<AlphaPremultiplication> inputFormat;
</span><span class="cx">     Optional<Ref<ImageData>> imageData;
</span><span class="lines">@@ -2880,169 +2367,109 @@
</span><span class="cx">     if (!destFormat)
</span><span class="cx">         return WTF::nullopt;
</span><span class="cx"> 
</span><del>-    return PutImageData::create(*inputFormat, WTFMove(*imageData), *srcRect, *destPoint, *destFormat);
</del><ins>+    return {{ *inputFormat, WTFMove(*imageData), *srcRect, *destPoint, *destFormat }};
</ins><span class="cx"> }
</span><span class="cx"> 
</span><del>-class PaintFrameForMedia : public DrawingItem {
</del><ins>+class PaintFrameForMedia {
</ins><span class="cx"> public:
</span><del>-    static Ref<PaintFrameForMedia> create(MediaPlayer&, const FloatRect& destination);
</del><ins>+    static constexpr ItemType itemType = ItemType::PaintFrameForMedia;
+    static constexpr bool isInlineItem = true;
+    static constexpr bool isDrawingItem = true;
</ins><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~PaintFrameForMedia();
</del><ins>+    PaintFrameForMedia(MediaPlayer&, const FloatRect& destination);
</ins><span class="cx"> 
</span><span class="cx">     const FloatRect& destination() const { return m_destination; }
</span><span class="cx">     MediaPlayerIdentifier identifier() const { return m_identifier; }
</span><span class="cx"> 
</span><del>-    template<class Encoder> void encode(Encoder&) const;
-    template<class Decoder> static Optional<Ref<PaintFrameForMedia>> decode(Decoder&);
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><ins>+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return WTF::nullopt; }
+    Optional<FloatRect> globalBounds() const { return { m_destination }; }
+
</ins><span class="cx"> private:
</span><del>-    WEBCORE_EXPORT static Ref<PaintFrameForMedia> create(MediaPlayerIdentifier, const FloatRect& destination);
-
-    PaintFrameForMedia(MediaPlayer&, const FloatRect& destination);
-    PaintFrameForMedia(MediaPlayerIdentifier, const FloatRect& destination);
-
-    void apply(GraphicsContext&) const override;
-
</del><span class="cx">     MediaPlayerIdentifier m_identifier;
</span><span class="cx">     FloatRect m_destination;
</span><span class="cx"> };
</span><span class="cx"> 
</span><del>-template<class Encoder>
-void PaintFrameForMedia::encode(Encoder& encoder) const
-{
-    encoder << m_identifier;
-    encoder << m_destination;
-}
</del><ins>+class StrokeRect {
+public:
+    static constexpr ItemType itemType = ItemType::StrokeRect;
+    static constexpr bool isInlineItem = true;
+    static constexpr bool isDrawingItem = true;
</ins><span class="cx"> 
</span><del>-template<class Decoder>
-Optional<Ref<PaintFrameForMedia>> PaintFrameForMedia::decode(Decoder& decoder)
-{
-    Optional<MediaPlayerIdentifier> identifier;
-    decoder >> identifier;
-    if (!identifier)
-        return WTF::nullopt;
-
-    Optional<FloatRect> destination;
-    decoder >> destination;
-    if (!destination)
-        return WTF::nullopt;
-
-    return PaintFrameForMedia::create(*identifier, *destination);
-}
-
-class StrokeRect : public DrawingItem {
-public:
-    static Ref<StrokeRect> create(const FloatRect& rect, float lineWidth)
</del><ins>+    StrokeRect(const FloatRect& rect, float lineWidth)
+        : m_rect(rect)
+        , m_lineWidth(lineWidth)
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new StrokeRect(rect, lineWidth));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~StrokeRect();
-
</del><span class="cx">     FloatRect rect() const { return m_rect; }
</span><span class="cx">     float lineWidth() const { return m_lineWidth; }
</span><span class="cx"> 
</span><del>-    template<class Encoder> void encode(Encoder&) const;
-    template<class Decoder> static Optional<Ref<StrokeRect>> decode(Decoder&);
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><ins>+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+    Optional<FloatRect> localBounds(const GraphicsContext&) const;
+
</ins><span class="cx"> private:
</span><del>-    WEBCORE_EXPORT StrokeRect(const FloatRect&, float);
-
-    void apply(GraphicsContext&) const override;
-    Optional<FloatRect> localBounds(const GraphicsContext&) const override;
-
</del><span class="cx">     FloatRect m_rect;
</span><span class="cx">     float m_lineWidth;
</span><span class="cx"> };
</span><span class="cx"> 
</span><del>-template<class Encoder>
-void StrokeRect::encode(Encoder& encoder) const
-{
-    encoder << m_rect;
-    encoder << m_lineWidth;
-}
-
-template<class Decoder>
-Optional<Ref<StrokeRect>> StrokeRect::decode(Decoder& decoder)
-{
-    Optional<FloatRect> rect;
-    decoder >> rect;
-    if (!rect)
-        return WTF::nullopt;
-
-    Optional<float> lineWidth;
-    decoder >> lineWidth;
-    if (!lineWidth)
-        return WTF::nullopt;
-
-    return StrokeRect::create(*rect, *lineWidth);
-}
-
</del><span class="cx"> #if ENABLE(INLINE_PATH_DATA)
</span><span class="cx"> 
</span><del>-class StrokeInlinePath : public DrawingItem {
</del><ins>+class StrokeInlinePath {
</ins><span class="cx"> public:
</span><del>-    static Ref<StrokeInlinePath> create(const InlinePathData& pathData)
</del><ins>+    static constexpr ItemType itemType = ItemType::StrokeInlinePath;
+    static constexpr bool isInlineItem = true;
+    static constexpr bool isDrawingItem = true;
+
+    StrokeInlinePath(const InlinePathData& pathData)
+        : m_pathData(pathData)
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new StrokeInlinePath(pathData));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~StrokeInlinePath();
-
</del><span class="cx">     Path path() const { return Path::from(m_pathData); }
</span><span class="cx"> 
</span><del>-    template<class Encoder> void encode(Encoder&) const;
-    template<class Decoder> static Optional<Ref<StrokeInlinePath>> decode(Decoder&);
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><ins>+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+    Optional<FloatRect> localBounds(const GraphicsContext&) const;
+
</ins><span class="cx"> private:
</span><del>-    WEBCORE_EXPORT StrokeInlinePath(const InlinePathData&);
-
-    void apply(GraphicsContext&) const override;
-    Optional<FloatRect> localBounds(const GraphicsContext&) const override;
-
</del><span class="cx">     InlinePathData m_pathData;
</span><span class="cx"> };
</span><span class="cx"> 
</span><del>-template<class Encoder>
-void StrokeInlinePath::encode(Encoder& encoder) const
-{
-    encoder << m_pathData;
-}
-
-template<class Decoder>
-Optional<Ref<StrokeInlinePath>> StrokeInlinePath::decode(Decoder& decoder)
-{
-    Optional<InlinePathData> pathData;
-    decoder >> pathData;
-    if (!pathData)
-        return WTF::nullopt;
-
-    return StrokeInlinePath::create(WTFMove(*pathData));
-}
-
</del><span class="cx"> #endif // ENABLE(INLINE_PATH_DATA)
</span><span class="cx"> 
</span><del>-class StrokePath : public DrawingItem {
</del><ins>+class StrokePath {
</ins><span class="cx"> public:
</span><del>-    static Ref<StrokePath> create(const Path& path)
</del><ins>+    static constexpr ItemType itemType = ItemType::StrokePath;
+    static constexpr bool isInlineItem = false;
+    static constexpr bool isDrawingItem = true;
+
+    StrokePath(Path&& path)
+        : m_path(WTFMove(path))
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new StrokePath(path));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~StrokePath();
</del><ins>+    StrokePath(const Path& path)
+        : m_path(path)
+    {
+    }
</ins><span class="cx"> 
</span><span class="cx">     const Path& path() const { return m_path; }
</span><span class="cx"> 
</span><span class="cx">     template<class Encoder> void encode(Encoder&) const;
</span><del>-    template<class Decoder> static Optional<Ref<StrokePath>> decode(Decoder&);
</del><ins>+    template<class Decoder> static Optional<StrokePath> decode(Decoder&);
</ins><span class="cx"> 
</span><del>-private:
-    WEBCORE_EXPORT StrokePath(const Path&);
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><del>-    void apply(GraphicsContext&) const override;
-    Optional<FloatRect> localBounds(const GraphicsContext&) const override;
</del><ins>+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+    Optional<FloatRect> localBounds(const GraphicsContext&) const;
</ins><span class="cx"> 
</span><del>-    const Path m_path;
</del><ins>+private:
+    Path m_path;
</ins><span class="cx"> };
</span><span class="cx"> 
</span><span class="cx"> template<class Encoder>
</span><span class="lines">@@ -3052,7 +2479,7 @@
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> template<class Decoder>
</span><del>-Optional<Ref<StrokePath>> StrokePath::decode(Decoder& decoder)
</del><ins>+Optional<StrokePath> StrokePath::decode(Decoder& decoder)
</ins><span class="cx"> {
</span><span class="cx">     Optional<Path> path;
</span><span class="cx">     decoder >> path;
</span><span class="lines">@@ -3059,714 +2486,108 @@
</span><span class="cx">     if (!path)
</span><span class="cx">         return WTF::nullopt;
</span><span class="cx"> 
</span><del>-    return StrokePath::create(*path);
</del><ins>+    return {{ WTFMove(*path) }};
</ins><span class="cx"> }
</span><span class="cx"> 
</span><del>-class StrokeEllipse : public DrawingItem {
</del><ins>+class StrokeEllipse {
</ins><span class="cx"> public:
</span><del>-    static Ref<StrokeEllipse> create(const FloatRect& rect)
</del><ins>+    static constexpr ItemType itemType = ItemType::StrokeEllipse;
+    static constexpr bool isInlineItem = true;
+    static constexpr bool isDrawingItem = true;
+
+    StrokeEllipse(const FloatRect& rect)
+        : m_rect(rect)
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new StrokeEllipse(rect));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT ~StrokeEllipse();
</del><ins>+    const FloatRect& rect() const { return m_rect; }
</ins><span class="cx"> 
</span><del>-    FloatRect rect() const { return m_rect; }
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><del>-    template<class Encoder> void encode(Encoder&) const;
-    template<class Decoder> static Optional<Ref<StrokeEllipse>> decode(Decoder&);
</del><ins>+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+    Optional<FloatRect> localBounds(const GraphicsContext&) const;
</ins><span class="cx"> 
</span><span class="cx"> private:
</span><del>-    WEBCORE_EXPORT StrokeEllipse(const FloatRect&);
-
-    void apply(GraphicsContext&) const override;
-    Optional<FloatRect> localBounds(const GraphicsContext&) const override;
-
</del><span class="cx">     FloatRect m_rect;
</span><span class="cx"> };
</span><span class="cx"> 
</span><del>-template<class Encoder>
-void StrokeEllipse::encode(Encoder& encoder) const
-{
-    encoder << m_rect;
-}
</del><ins>+class ClearRect {
+public:
+    static constexpr ItemType itemType = ItemType::ClearRect;
+    static constexpr bool isInlineItem = true;
+    static constexpr bool isDrawingItem = true;
</ins><span class="cx"> 
</span><del>-template<class Decoder>
-Optional<Ref<StrokeEllipse>> StrokeEllipse::decode(Decoder& decoder)
-{
-    Optional<FloatRect> rect;
-    decoder >> rect;
-    if (!rect)
-        return WTF::nullopt;
-
-    return StrokeEllipse::create(*rect);
-}
-
-class ClearRect : public DrawingItem {
-public:
-    static Ref<ClearRect> create(const FloatRect& rect)
</del><ins>+    ClearRect(const FloatRect& rect)
+        : m_rect(rect)
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new ClearRect(rect));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~ClearRect();
</del><ins>+    const FloatRect& rect() const { return m_rect; }
</ins><span class="cx"> 
</span><del>-    FloatRect rect() const { return m_rect; }
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><del>-    template<class Encoder> void encode(Encoder&) const;
-    template<class Decoder> static Optional<Ref<ClearRect>> decode(Decoder&);
</del><ins>+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return m_rect; }
</ins><span class="cx"> 
</span><span class="cx"> private:
</span><del>-    WEBCORE_EXPORT ClearRect(const FloatRect&);
-
-    void apply(GraphicsContext&) const override;
-    Optional<FloatRect> localBounds(const GraphicsContext&) const override { return m_rect; }
-
</del><span class="cx">     FloatRect m_rect;
</span><span class="cx"> };
</span><span class="cx"> 
</span><del>-template<class Encoder>
-void ClearRect::encode(Encoder& encoder) const
-{
-    encoder << m_rect;
-}
</del><ins>+#if USE(CG)
</ins><span class="cx"> 
</span><del>-template<class Decoder>
-Optional<Ref<ClearRect>> ClearRect::decode(Decoder& decoder)
-{
-    Optional<FloatRect> rect;
-    decoder >> rect;
-    if (!rect)
-        return WTF::nullopt;
-
-    return ClearRect::create(*rect);
-}
-
-#if USE(CG)
-class ApplyStrokePattern : public Item {
</del><ins>+class ApplyStrokePattern {
</ins><span class="cx"> public:
</span><del>-    static Ref<ApplyStrokePattern> create()
-    {
-        return adoptRef(*new ApplyStrokePattern);
-    }
</del><ins>+    static constexpr ItemType itemType = ItemType::ApplyStrokePattern;
+    static constexpr bool isInlineItem = true;
+    static constexpr bool isDrawingItem = false;
</ins><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~ApplyStrokePattern();
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><del>-    template<class Encoder> void encode(Encoder&) const;
-    template<class Decoder> static Optional<Ref<ApplyStrokePattern>> decode(Decoder&);
-
-private:
-    WEBCORE_EXPORT ApplyStrokePattern();
-
-    void apply(GraphicsContext&) const override;
</del><ins>+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return WTF::nullopt; }
+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
</ins><span class="cx"> };
</span><span class="cx"> 
</span><del>-template<class Encoder>
-void ApplyStrokePattern::encode(Encoder&) const
-{
-}
-
-template<class Decoder>
-Optional<Ref<ApplyStrokePattern>> ApplyStrokePattern::decode(Decoder&)
-{
-    return ApplyStrokePattern::create();
-}
-
-class ApplyFillPattern : public Item {
</del><ins>+class ApplyFillPattern {
</ins><span class="cx"> public:
</span><del>-    static Ref<ApplyFillPattern> create()
-    {
-        return adoptRef(*new ApplyFillPattern);
-    }
</del><ins>+    static constexpr ItemType itemType = ItemType::ApplyFillPattern;
+    static constexpr bool isInlineItem = true;
+    static constexpr bool isDrawingItem = false;
</ins><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~ApplyFillPattern();
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><del>-    template<class Encoder> void encode(Encoder&) const;
-    template<class Decoder> static Optional<Ref<ApplyFillPattern>> decode(Decoder&);
-
-private:
-    WEBCORE_EXPORT ApplyFillPattern();
-
-    void apply(GraphicsContext&) const override;
</del><ins>+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return WTF::nullopt; }
+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
</ins><span class="cx"> };
</span><span class="cx"> 
</span><del>-template<class Encoder>
-void ApplyFillPattern::encode(Encoder&) const
-{
-}
-
-template<class Decoder>
-Optional<Ref<ApplyFillPattern>> ApplyFillPattern::decode(Decoder&)
-{
-    return ApplyFillPattern::create();
-}
</del><span class="cx"> #endif
</span><span class="cx"> 
</span><del>-class ApplyDeviceScaleFactor : public Item {
</del><ins>+class ApplyDeviceScaleFactor {
</ins><span class="cx"> public:
</span><del>-    static Ref<ApplyDeviceScaleFactor> create(float scaleFactor)
</del><ins>+    static constexpr ItemType itemType = ItemType::ApplyDeviceScaleFactor;
+    static constexpr bool isInlineItem = true;
+    static constexpr bool isDrawingItem = false;
+
+    ApplyDeviceScaleFactor(float scaleFactor)
+        : m_scaleFactor(scaleFactor)
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new ApplyDeviceScaleFactor(scaleFactor));
</del><span class="cx">     }
</span><span class="cx"> 
</span><del>-    WEBCORE_EXPORT virtual ~ApplyDeviceScaleFactor();
-
</del><span class="cx">     float scaleFactor() const { return m_scaleFactor; }
</span><span class="cx"> 
</span><del>-    template<class Encoder> void encode(Encoder&) const;
-    template<class Decoder> static Optional<Ref<ApplyDeviceScaleFactor>> decode(Decoder&);
</del><ins>+    void apply(GraphicsContext&) const;
</ins><span class="cx"> 
</span><ins>+    Optional<FloatRect> localBounds(const GraphicsContext&) const { return WTF::nullopt; }
+    Optional<FloatRect> globalBounds() const { return WTF::nullopt; }
+
</ins><span class="cx"> private:
</span><del>-    WEBCORE_EXPORT ApplyDeviceScaleFactor(float scaleFactor);
-
-    void apply(GraphicsContext&) const override;
-
-    float m_scaleFactor;
</del><ins>+    float m_scaleFactor { 1 };
</ins><span class="cx"> };
</span><span class="cx"> 
</span><del>-template<class Encoder>
-void ApplyDeviceScaleFactor::encode(Encoder& encoder) const
-{
-    encoder << m_scaleFactor;
-}
</del><ins>+TextStream& operator<<(TextStream&, ItemHandle);
</ins><span class="cx"> 
</span><del>-template<class Decoder>
-Optional<Ref<ApplyDeviceScaleFactor>> ApplyDeviceScaleFactor::decode(Decoder& decoder)
-{
-    Optional<float> scaleFactor;
-    decoder >> scaleFactor;
-    if (!scaleFactor)
-        return WTF::nullopt;
-
-    return ApplyDeviceScaleFactor::create(*scaleFactor);
-}
-
-
-WTF::TextStream& operator<<(WTF::TextStream&, const Item&);
-
-template<class Encoder>
-void Item::encode(Encoder& encoder) const
-{
-    encoder << m_type;
-
-    switch (m_type) {
-    case ItemType::Save:
-        encoder << downcast<Save>(*this);
-        break;
-    case ItemType::Restore:
-        encoder << downcast<Restore>(*this);
-        break;
-    case ItemType::Translate:
-        encoder << downcast<Translate>(*this);
-        break;
-    case ItemType::Rotate:
-        encoder << downcast<Rotate>(*this);
-        break;
-    case ItemType::Scale:
-        encoder << downcast<Scale>(*this);
-        break;
-    case ItemType::SetCTM:
-        encoder << downcast<SetCTM>(*this);
-        break;
-    case ItemType::ConcatenateCTM:
-        encoder << downcast<ConcatenateCTM>(*this);
-        break;
-    case ItemType::SetInlineFillGradient:
-        encoder << downcast<SetInlineFillGradient>(*this);
-        break;
-    case ItemType::SetInlineFillColor:
-        encoder << downcast<SetInlineFillColor>(*this);
-        break;
-    case ItemType::SetInlineStrokeColor:
-        encoder << downcast<SetInlineStrokeColor>(*this);
-        break;
-    case ItemType::SetStrokeThickness:
-        encoder << downcast<SetStrokeThickness>(*this);
-        break;
-    case ItemType::SetState:
-        encoder << downcast<SetState>(*this);
-        break;
-    case ItemType::SetLineCap:
-        encoder << downcast<SetLineCap>(*this);
-        break;
-    case ItemType::SetLineDash:
-        encoder << downcast<SetLineDash>(*this);
-        break;
-    case ItemType::SetLineJoin:
-        encoder << downcast<SetLineJoin>(*this);
-        break;
-    case ItemType::SetMiterLimit:
-        encoder << downcast<SetMiterLimit>(*this);
-        break;
-    case ItemType::ClearShadow:
-        encoder << downcast<ClearShadow>(*this);
-        break;
-    case ItemType::Clip:
-        encoder << downcast<Clip>(*this);
-        break;
-    case ItemType::ClipOut:
-        encoder << downcast<ClipOut>(*this);
-        break;
-    case ItemType::ClipOutToPath:
-        encoder << downcast<ClipOutToPath>(*this);
-        break;
-    case ItemType::ClipPath:
-        encoder << downcast<ClipPath>(*this);
-        break;
-    case ItemType::ClipToDrawingCommands:
-        encoder << downcast<ClipToDrawingCommands>(*this);
-        break;
-    case ItemType::DrawGlyphs:
-        encoder << downcast<DrawGlyphs>(*this);
-        break;
-    case ItemType::DrawImage:
-        encoder << downcast<DrawImage>(*this);
-        break;
-    case ItemType::DrawTiledImage:
-        encoder << downcast<DrawTiledImage>(*this);
-        break;
-    case ItemType::DrawTiledScaledImage:
-        encoder << downcast<DrawTiledScaledImage>(*this);
-        break;
-    case ItemType::DrawImageBuffer:
-        encoder << downcast<DrawImageBuffer>(*this);
-        break;
-    case ItemType::DrawNativeImage:
-        encoder << downcast<DrawNativeImage>(*this);
-        break;
-    case ItemType::DrawPattern:
-        encoder << downcast<DrawPattern>(*this);
-        break;
-    case ItemType::DrawRect:
-        encoder << downcast<DrawRect>(*this);
-        break;
-    case ItemType::DrawLine:
-        encoder << downcast<DrawLine>(*this);
-        break;
-    case ItemType::DrawLinesForText:
-        encoder << downcast<DrawLinesForText>(*this);
-        break;
-    case ItemType::DrawDotsForDocumentMarker:
-        encoder << downcast<DrawDotsForDocumentMarker>(*this);
-        break;
-    case ItemType::DrawEllipse:
-        encoder << downcast<DrawEllipse>(*this);
-        break;
-    case ItemType::DrawPath:
-        encoder << downcast<DrawPath>(*this);
-        break;
-    case ItemType::DrawFocusRingPath:
-        encoder << downcast<DrawFocusRingPath>(*this);
-        break;
-    case ItemType::DrawFocusRingRects:
-        encoder << downcast<DrawFocusRingRects>(*this);
-        break;
-    case ItemType::FillRect:
-        encoder << downcast<FillRect>(*this);
-        break;
-    case ItemType::FillRectWithColor:
-        encoder << downcast<FillRectWithColor>(*this);
-        break;
-    case ItemType::FillRectWithGradient:
-        encoder << downcast<FillRectWithGradient>(*this);
-        break;
-    case ItemType::FillCompositedRect:
-        encoder << downcast<FillCompositedRect>(*this);
-        break;
-    case ItemType::FillRoundedRect:
-        encoder << downcast<FillRoundedRect>(*this);
-        break;
-    case ItemType::FillRectWithRoundedHole:
-        encoder << downcast<FillRectWithRoundedHole>(*this);
-        break;
-#if ENABLE(INLINE_PATH_DATA)
-    case ItemType::FillInlinePath:
-        encoder << downcast<FillInlinePath>(*this);
-        break;
-#endif
-    case ItemType::FillPath:
-        encoder << downcast<FillPath>(*this);
-        break;
-    case ItemType::FillEllipse:
-        encoder << downcast<FillEllipse>(*this);
-        break;
-    case ItemType::PutImageData:
-        encoder << downcast<PutImageData>(*this);
-        break;
-    case ItemType::PaintFrameForMedia:
-        encoder << downcast<PaintFrameForMedia>(*this);
-        break;
-    case ItemType::StrokeRect:
-        encoder << downcast<StrokeRect>(*this);
-        break;
-#if ENABLE(INLINE_PATH_DATA)
-    case ItemType::StrokeInlinePath:
-        encoder << downcast<StrokeInlinePath>(*this);
-        break;
-#endif
-    case ItemType::StrokePath:
-        encoder << downcast<StrokePath>(*this);
-        break;
-    case ItemType::StrokeEllipse:
-        encoder << downcast<StrokeEllipse>(*this);
-        break;
-    case ItemType::ClearRect:
-        encoder << downcast<ClearRect>(*this);
-        break;
-    case ItemType::BeginTransparencyLayer:
-        encoder << downcast<BeginTransparencyLayer>(*this);
-        break;
-    case ItemType::EndTransparencyLayer:
-        encoder << downcast<EndTransparencyLayer>(*this);
-        break;
-#if USE(CG)
-    case ItemType::ApplyStrokePattern:
-        encoder << downcast<ApplyStrokePattern>(*this);
-        break;
-    case ItemType::ApplyFillPattern:
-        encoder << downcast<ApplyFillPattern>(*this);
-        break;
-#endif
-    case ItemType::ApplyDeviceScaleFactor:
-        encoder << downcast<ApplyDeviceScaleFactor>(*this);
-        break;
-    }
-}
-
-template<class Decoder>
-Optional<Ref<Item>> Item::decode(Decoder& decoder)
-{
-    Optional<ItemType> itemType;
-    decoder >> itemType;
-    if (!itemType)
-        return WTF::nullopt;
-
-    switch (*itemType) {
-    case ItemType::Save:
-        if (auto item = Save::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::Restore:
-        if (auto item = Restore::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::Translate:
-        if (auto item = Translate::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::Rotate:
-        if (auto item = Rotate::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::Scale:
-        if (auto item = Scale::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::SetCTM:
-        if (auto item = SetCTM::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::ConcatenateCTM:
-        if (auto item = ConcatenateCTM::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::SetInlineFillGradient: {
-        if (auto item = SetInlineFillGradient::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    }
-    case ItemType::SetInlineFillColor:
-        if (auto item = SetInlineFillColor::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::SetInlineStrokeColor:
-        if (auto item = SetInlineStrokeColor::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::SetStrokeThickness:
-        if (auto item = SetStrokeThickness::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::SetState:
-        if (auto item = SetState::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::SetLineCap:
-        if (auto item = SetLineCap::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::SetLineDash:
-        if (auto item = SetLineDash::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::SetLineJoin:
-        if (auto item = SetLineJoin::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::SetMiterLimit:
-        if (auto item = SetMiterLimit::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::ClearShadow:
-        if (auto item = ClearShadow::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::Clip:
-        if (auto item = Clip::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::ClipOut:
-        if (auto item = ClipOut::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::ClipOutToPath:
-        if (auto item = ClipOutToPath::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::ClipPath:
-        if (auto item = ClipPath::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::ClipToDrawingCommands:
-        if (auto item = ClipToDrawingCommands::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::DrawGlyphs:
-        if (auto item = DrawGlyphs::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::DrawImage:
-        if (auto item = DrawImage::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::DrawTiledImage:
-        if (auto item = DrawTiledImage::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::DrawTiledScaledImage:
-        if (auto item = DrawTiledScaledImage::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::DrawImageBuffer:
-        if (auto item = DrawImageBuffer::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::DrawNativeImage:
-        if (auto item = DrawNativeImage::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::DrawPattern:
-        if (auto item = DrawPattern::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::DrawRect:
-        if (auto item = DrawRect::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::DrawLine:
-        if (auto item = DrawLine::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::DrawLinesForText:
-        if (auto item = DrawLinesForText::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::DrawDotsForDocumentMarker:
-        if (auto item = DrawDotsForDocumentMarker::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::DrawEllipse:
-        if (auto item = DrawEllipse::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::DrawPath:
-        if (auto item = DrawPath::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::DrawFocusRingPath:
-        if (auto item = DrawFocusRingPath::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::DrawFocusRingRects:
-        if (auto item = DrawFocusRingRects::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::FillRect:
-        if (auto item = FillRect::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::FillRectWithColor:
-        if (auto item = FillRectWithColor::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::FillRectWithGradient:
-        if (auto item = FillRectWithGradient::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::FillCompositedRect:
-        if (auto item = FillCompositedRect::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::FillRoundedRect:
-        if (auto item = FillRoundedRect::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::FillRectWithRoundedHole:
-        if (auto item = FillRectWithRoundedHole::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-#if ENABLE(INLINE_PATH_DATA)
-    case ItemType::FillInlinePath:
-        if (auto item = FillInlinePath::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-#endif
-    case ItemType::FillPath:
-        if (auto item = FillPath::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::FillEllipse:
-        if (auto item = FillEllipse::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::PutImageData:
-        if (auto item = PutImageData::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::PaintFrameForMedia:
-        if (auto item = PaintFrameForMedia::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::StrokeRect:
-        if (auto item = StrokeRect::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-#if ENABLE(INLINE_PATH_DATA)
-    case ItemType::StrokeInlinePath:
-        if (auto item = StrokeInlinePath::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-#endif
-    case ItemType::StrokePath:
-        if (auto item = StrokePath::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::StrokeEllipse:
-        if (auto item = StrokeEllipse::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::ClearRect:
-        if (auto item = ClearRect::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::BeginTransparencyLayer:
-        if (auto item = BeginTransparencyLayer::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::EndTransparencyLayer:
-        if (auto item = EndTransparencyLayer::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-#if USE(CG)
-    case ItemType::ApplyStrokePattern:
-        if (auto item = ApplyStrokePattern::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    case ItemType::ApplyFillPattern:
-        if (auto item = ApplyFillPattern::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-#endif
-    case ItemType::ApplyDeviceScaleFactor:
-        if (auto item = ApplyDeviceScaleFactor::decode(decoder))
-            return static_reference_cast<Item>(WTFMove(*item));
-        break;
-    }
-
-    return WTF::nullopt;
-}
-
</del><span class="cx"> } // namespace DisplayList
</span><span class="cx"> } // namespace WebCore
</span><span class="cx"> 
</span><del>-
-#define SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_DRAWINGITEM(ToValueTypeName, predicate) \
-SPECIALIZE_TYPE_TRAITS_BEGIN(WebCore::DisplayList::ToValueTypeName) \
-    static bool isType(const WebCore::DisplayList::Item& object) { return object.predicate; } \
-SPECIALIZE_TYPE_TRAITS_END()
-
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_DRAWINGITEM(DrawingItem, isDrawingItem())
-
-#define SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(ToValueTypeName) \
-SPECIALIZE_TYPE_TRAITS_BEGIN(WebCore::DisplayList::ToValueTypeName) \
-    static bool isType(const WebCore::DisplayList::Item& item) { return item.type() == WebCore::DisplayList::ItemType::ToValueTypeName; } \
-SPECIALIZE_TYPE_TRAITS_END()
-
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(Save)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(Restore)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(Translate)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(Rotate)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(Scale)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(SetCTM)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(ConcatenateCTM)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(SetInlineFillGradient)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(SetInlineFillColor)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(SetInlineStrokeColor)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(SetStrokeThickness)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(SetState)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(SetLineCap)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(SetLineDash)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(SetLineJoin)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(SetMiterLimit)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(Clip)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(ClipOut)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(ClipOutToPath)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(ClipPath)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(ClipToDrawingCommands)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(DrawGlyphs)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(DrawImage)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(DrawTiledImage)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(DrawTiledScaledImage)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(DrawImageBuffer)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(DrawNativeImage)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(DrawPattern)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(DrawRect)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(DrawLine)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(DrawLinesForText)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(DrawDotsForDocumentMarker)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(DrawEllipse)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(DrawPath)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(DrawFocusRingPath)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(DrawFocusRingRects)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(FillRect)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(FillRectWithColor)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(FillRectWithGradient)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(FillCompositedRect)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(FillRoundedRect)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(FillRectWithRoundedHole)
-#if ENABLE(INLINE_PATH_DATA)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(FillInlinePath)
-#endif
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(FillPath)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(FillEllipse)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(PutImageData)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(PaintFrameForMedia)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(StrokeRect)
-#if ENABLE(INLINE_PATH_DATA)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(StrokeInlinePath)
-#endif
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(StrokePath)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(StrokeEllipse)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(ClearRect)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(BeginTransparencyLayer)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(EndTransparencyLayer)
-#if USE(CG)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(ApplyStrokePattern)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(ApplyFillPattern)
-#endif
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(ApplyDeviceScaleFactor)
-SPECIALIZE_TYPE_TRAITS_DISPLAYLIST_ITEM(ClearShadow)
-
</del><span class="cx"> namespace WTF {
</span><span class="cx"> 
</span><span class="cx"> template<> struct EnumTraits<WebCore::DisplayList::ItemType> {
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformgraphicsdisplaylistsDisplayListRecordercpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/graphics/displaylists/DisplayListRecorder.cpp (269524 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/graphics/displaylists/DisplayListRecorder.cpp      2020-11-06 18:44:09 UTC (rev 269524)
+++ trunk/Source/WebCore/platform/graphics/displaylists/DisplayListRecorder.cpp 2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -56,7 +56,7 @@
</span><span class="cx"> 
</span><span class="cx"> void Recorder::putImageData(WebCore::AlphaPremultiplication inputFormat, const WebCore::ImageData& imageData, const WebCore::IntRect& srcRect, const WebCore::IntPoint& destPoint, WebCore::AlphaPremultiplication destFormat)
</span><span class="cx"> {
</span><del>-    appendItem(WebCore::DisplayList::PutImageData::create(inputFormat, imageData, srcRect, destPoint, destFormat));
</del><ins>+    append<PutImageData>(inputFormat, imageData, srcRect, destPoint, destFormat);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> static bool containsOnlyInlineStateChanges(const GraphicsContextStateChange& changes, GraphicsContextState::StateChangeFlags changeFlags)
</span><span class="lines">@@ -87,21 +87,21 @@
</span><span class="cx"> void Recorder::appendStateChangeItem(const GraphicsContextStateChange& changes, GraphicsContextState::StateChangeFlags changeFlags)
</span><span class="cx"> {
</span><span class="cx">     if (!containsOnlyInlineStateChanges(changes, changeFlags)) {
</span><del>-        m_displayList.appendItem(SetState::create(changes.m_state, changeFlags));
</del><ins>+        append<SetState>(changes.m_state, changeFlags);
</ins><span class="cx">         return;
</span><span class="cx">     }
</span><span class="cx"> 
</span><span class="cx">     if (changeFlags.contains(GraphicsContextState::StrokeColorChange))
</span><del>-        m_displayList.appendItem(SetInlineStrokeColor::create(changes.m_state.strokeColor.asInline()));
</del><ins>+        append<SetInlineStrokeColor>(changes.m_state.strokeColor.asInline());
</ins><span class="cx"> 
</span><span class="cx">     if (changeFlags.contains(GraphicsContextState::StrokeThicknessChange))
</span><del>-        m_displayList.appendItem(SetStrokeThickness::create(changes.m_state.strokeThickness));
</del><ins>+        append<SetStrokeThickness>(changes.m_state.strokeThickness);
</ins><span class="cx"> 
</span><span class="cx">     if (changeFlags.contains(GraphicsContextState::FillColorChange))
</span><del>-        m_displayList.appendItem(SetInlineFillColor::create(changes.m_state.fillColor.asInline()));
</del><ins>+        append<SetInlineFillColor>(changes.m_state.fillColor.asInline());
</ins><span class="cx"> 
</span><span class="cx">     if (changeFlags.contains(GraphicsContextState::FillGradientChange))
</span><del>-        m_displayList.appendItem(SetInlineFillGradient::create(*changes.m_state.fillGradient));
</del><ins>+        append<SetInlineFillGradient>(*changes.m_state.fillGradient);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::willAppendItemOfType(ItemType type)
</span><span class="lines">@@ -139,27 +139,27 @@
</span><span class="cx"> 
</span><span class="cx"> void Recorder::clearShadow()
</span><span class="cx"> {
</span><del>-    appendItem(ClearShadow::create());
</del><ins>+    append<ClearShadow>();
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::setLineCap(LineCap lineCap)
</span><span class="cx"> {
</span><del>-    appendItem(SetLineCap::create(lineCap));
</del><ins>+    append<SetLineCap>(lineCap);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::setLineDash(const DashArray& dashArray, float dashOffset)
</span><span class="cx"> {
</span><del>-    appendItem(SetLineDash::create(dashArray, dashOffset));
</del><ins>+    append<SetLineDash>(dashArray, dashOffset);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::setLineJoin(LineJoin lineJoin)
</span><span class="cx"> {
</span><del>-    appendItem(SetLineJoin::create(lineJoin));
</del><ins>+    append<SetLineJoin>(lineJoin);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::setMiterLimit(float miterLimit)
</span><span class="cx"> {
</span><del>-    appendItem(SetMiterLimit::create(miterLimit));
</del><ins>+    append<SetMiterLimit>(miterLimit);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::drawGlyphs(const Font& font, const GlyphBuffer& glyphBuffer, unsigned from, unsigned numGlyphs, const FloatPoint& startPoint, FontSmoothingMode smoothingMode)
</span><span class="lines">@@ -169,19 +169,19 @@
</span><span class="cx"> 
</span><span class="cx"> ImageDrawResult Recorder::drawImage(Image& image, const FloatRect& destination, const FloatRect& source, const ImagePaintingOptions& imagePaintingOptions)
</span><span class="cx"> {
</span><del>-    appendItemAndUpdateExtent(DrawImage::create(image, destination, source, imagePaintingOptions));
</del><ins>+    append<DrawImage>(image, destination, source, imagePaintingOptions);
</ins><span class="cx">     return ImageDrawResult::DidRecord;
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> ImageDrawResult Recorder::drawTiledImage(Image& image, const FloatRect& destination, const FloatPoint& source, const FloatSize& tileSize, const FloatSize& spacing, const ImagePaintingOptions& imagePaintingOptions)
</span><span class="cx"> {
</span><del>-    appendItemAndUpdateExtent(DrawTiledImage::create(image, destination, source, tileSize, spacing, imagePaintingOptions));
</del><ins>+    append<DrawTiledImage>(image, destination, source, tileSize, spacing, imagePaintingOptions);
</ins><span class="cx">     return ImageDrawResult::DidRecord;
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> ImageDrawResult Recorder::drawTiledImage(Image& image, const FloatRect& destination, const FloatRect& source, const FloatSize& tileScaleFactor, Image::TileRule hRule, Image::TileRule vRule, const ImagePaintingOptions& imagePaintingOptions)
</span><span class="cx"> {
</span><del>-    appendItemAndUpdateExtent(DrawTiledScaledImage::create(image, destination, source, tileScaleFactor, hRule, vRule, imagePaintingOptions));
</del><ins>+    append<DrawTiledScaledImage>(image, destination, source, tileScaleFactor, hRule, vRule, imagePaintingOptions);
</ins><span class="cx">     return ImageDrawResult::DidRecord;
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="lines">@@ -189,22 +189,22 @@
</span><span class="cx"> {
</span><span class="cx">     imageBuffer.flushDrawingContext();
</span><span class="cx">     m_displayList.cacheImageBuffer(makeRef(imageBuffer));
</span><del>-    appendItemAndUpdateExtent(DrawImageBuffer::create(imageBuffer.renderingResourceIdentifier(), destRect, srcRect, options));
</del><ins>+    append<DrawImageBuffer>(imageBuffer.renderingResourceIdentifier(), destRect, srcRect, options);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::drawNativeImage(const NativeImagePtr& image, const FloatSize& imageSize, const FloatRect& destRect, const FloatRect& srcRect, const ImagePaintingOptions& options)
</span><span class="cx"> {
</span><del>-    appendItemAndUpdateExtent(DrawNativeImage::create(image, imageSize, destRect, srcRect, options));
</del><ins>+    append<DrawNativeImage>(image, imageSize, destRect, srcRect, options);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::drawPattern(Image& image, const FloatRect& destRect, const FloatRect& tileRect, const AffineTransform& patternTransform, const FloatPoint& phase, const FloatSize& spacing, const ImagePaintingOptions& options)
</span><span class="cx"> {
</span><del>-    appendItemAndUpdateExtent(DrawPattern::create(image, destRect, tileRect, patternTransform, phase, spacing, options));
</del><ins>+    append<DrawPattern>(image, destRect, tileRect, patternTransform, phase, spacing, options);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::save()
</span><span class="cx"> {
</span><del>-    appendItem(Save::create());
</del><ins>+    append<Save>();
</ins><span class="cx">     m_stateStack.append(m_stateStack.last().cloneForSave());
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="lines">@@ -219,25 +219,25 @@
</span><span class="cx">     // Have to avoid eliding nested Save/Restore when a descendant state contains drawing items.
</span><span class="cx">     currentState().wasUsedForDrawing |= stateUsedForDrawing;
</span><span class="cx"> 
</span><del>-    appendItem(Restore::create());
</del><ins>+    append<Restore>();
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::translate(float x, float y)
</span><span class="cx"> {
</span><span class="cx">     currentState().translate(x, y);
</span><del>-    appendItem(Translate::create(x, y));
</del><ins>+    append<Translate>(x, y);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::rotate(float angleInRadians)
</span><span class="cx"> {
</span><span class="cx">     currentState().rotate(angleInRadians);
</span><del>-    appendItem(Rotate::create(angleInRadians));
</del><ins>+    append<Rotate>(angleInRadians);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::scale(const FloatSize& size)
</span><span class="cx"> {
</span><span class="cx">     currentState().scale(size);
</span><del>-    appendItem(Scale::create(size));
</del><ins>+    append<Scale>(size);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::concatCTM(const AffineTransform& transform)
</span><span class="lines">@@ -246,13 +246,13 @@
</span><span class="cx">         return;
</span><span class="cx"> 
</span><span class="cx">     currentState().concatCTM(transform);
</span><del>-    appendItem(ConcatenateCTM::create(transform));
</del><ins>+    append<ConcatenateCTM>(transform);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::setCTM(const AffineTransform& transform)
</span><span class="cx"> {
</span><span class="cx">     currentState().setCTM(transform);
</span><del>-    appendItem(SetCTM::create(transform));
</del><ins>+    append<SetCTM>(transform);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> AffineTransform Recorder::getCTM(GraphicsContext::IncludeDeviceScale)
</span><span class="lines">@@ -263,82 +263,82 @@
</span><span class="cx"> 
</span><span class="cx"> void Recorder::beginTransparencyLayer(float opacity)
</span><span class="cx"> {
</span><del>-    appendItemAndUpdateExtent(BeginTransparencyLayer::create(opacity));
</del><ins>+    append<BeginTransparencyLayer>(opacity);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::endTransparencyLayer()
</span><span class="cx"> {
</span><del>-    appendItem(EndTransparencyLayer::create());
</del><ins>+    append<EndTransparencyLayer>();
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::drawRect(const FloatRect& rect, float borderThickness)
</span><span class="cx"> {
</span><del>-    appendItemAndUpdateExtent(DrawRect::create(rect, borderThickness));
</del><ins>+    append<DrawRect>(rect, borderThickness);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::drawLine(const FloatPoint& point1, const FloatPoint& point2)
</span><span class="cx"> {
</span><del>-    appendItemAndUpdateExtent(DrawLine::create(point1, point2));
</del><ins>+    append<DrawLine>(point1, point2);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::drawLinesForText(const FloatPoint& point, float thickness, const DashArray& widths, bool printing, bool doubleLines)
</span><span class="cx"> {
</span><del>-    appendItemAndUpdateExtent(DrawLinesForText::create(FloatPoint(), toFloatSize(point), thickness, widths, printing, doubleLines));
</del><ins>+    append<DrawLinesForText>(FloatPoint(), toFloatSize(point), thickness, widths, printing, doubleLines);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::drawDotsForDocumentMarker(const FloatRect& rect, DocumentMarkerLineStyle style)
</span><span class="cx"> {
</span><del>-    appendItemAndUpdateExtent(DrawDotsForDocumentMarker::create(rect, style));
</del><ins>+    append<DrawDotsForDocumentMarker>(rect, style);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::drawEllipse(const FloatRect& rect)
</span><span class="cx"> {
</span><del>-    appendItemAndUpdateExtent(DrawEllipse::create(rect));
</del><ins>+    append<DrawEllipse>(rect);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::drawPath(const Path& path)
</span><span class="cx"> {
</span><del>-    appendItemAndUpdateExtent(DrawPath::create(path));
</del><ins>+    append<DrawPath>(path);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::drawFocusRing(const Path& path, float width, float offset, const Color& color)
</span><span class="cx"> {
</span><del>-    appendItemAndUpdateExtent(DrawFocusRingPath::create(path, width, offset, color));
</del><ins>+    append<DrawFocusRingPath>(path, width, offset, color);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::drawFocusRing(const Vector<FloatRect>& rects, float width, float offset, const Color& color)
</span><span class="cx"> {
</span><del>-    appendItemAndUpdateExtent(DrawFocusRingRects::create(rects, width, offset, color));
</del><ins>+    append<DrawFocusRingRects>(rects, width, offset, color);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::fillRect(const FloatRect& rect)
</span><span class="cx"> {
</span><del>-    appendItemAndUpdateExtent(FillRect::create(rect));
</del><ins>+    append<FillRect>(rect);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::fillRect(const FloatRect& rect, const Color& color)
</span><span class="cx"> {
</span><del>-    appendItemAndUpdateExtent(FillRectWithColor::create(rect, color));
</del><ins>+    append<FillRectWithColor>(rect, color);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::fillRect(const FloatRect& rect, Gradient& gradient)
</span><span class="cx"> {
</span><del>-    appendItemAndUpdateExtent(FillRectWithGradient::create(rect, gradient));
</del><ins>+    append<FillRectWithGradient>(rect, gradient);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::fillRect(const FloatRect& rect, const Color& color, CompositeOperator op, BlendMode blendMode)
</span><span class="cx"> {
</span><del>-    appendItemAndUpdateExtent(FillCompositedRect::create(rect, color, op, blendMode));
</del><ins>+    append<FillCompositedRect>(rect, color, op, blendMode);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::fillRoundedRect(const FloatRoundedRect& rect, const Color& color, BlendMode blendMode)
</span><span class="cx"> {
</span><del>-    appendItemAndUpdateExtent(FillRoundedRect::create(rect, color, blendMode));
</del><ins>+    append<FillRoundedRect>(rect, color, blendMode);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::fillRectWithRoundedHole(const FloatRect& rect, const FloatRoundedRect& roundedHoleRect, const Color& color)
</span><span class="cx"> {
</span><del>-    appendItemAndUpdateExtent(FillRectWithRoundedHole::create(rect, roundedHoleRect, color));
</del><ins>+    append<FillRectWithRoundedHole>(rect, roundedHoleRect, color);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::fillPath(const Path& path)
</span><span class="lines">@@ -345,21 +345,21 @@
</span><span class="cx"> {
</span><span class="cx"> #if ENABLE(INLINE_PATH_DATA)
</span><span class="cx">     if (path.hasInlineData()) {
</span><del>-        appendItemAndUpdateExtent(FillInlinePath::create(path.inlineData()));
</del><ins>+        append<FillInlinePath>(path.inlineData());
</ins><span class="cx">         return;
</span><span class="cx">     }
</span><span class="cx"> #endif
</span><del>-    appendItemAndUpdateExtent(FillPath::create(path));
</del><ins>+    append<FillPath>(path);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::fillEllipse(const FloatRect& rect)
</span><span class="cx"> {
</span><del>-    appendItemAndUpdateExtent(FillEllipse::create(rect));
</del><ins>+    append<FillEllipse>(rect);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::strokeRect(const FloatRect& rect, float lineWidth)
</span><span class="cx"> {
</span><del>-    appendItemAndUpdateExtent(StrokeRect::create(rect, lineWidth));
</del><ins>+    append<StrokeRect>(rect, lineWidth);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::strokePath(const Path& path)
</span><span class="lines">@@ -366,32 +366,32 @@
</span><span class="cx"> {
</span><span class="cx"> #if ENABLE(INLINE_PATH_DATA)
</span><span class="cx">     if (path.hasInlineData()) {
</span><del>-        appendItemAndUpdateExtent(StrokeInlinePath::create(path.inlineData()));
</del><ins>+        append<StrokeInlinePath>(path.inlineData());
</ins><span class="cx">         return;
</span><span class="cx">     }
</span><span class="cx"> #endif
</span><del>-    appendItemAndUpdateExtent(StrokePath::create(path));
</del><ins>+    append<StrokePath>(path);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::strokeEllipse(const FloatRect& rect)
</span><span class="cx"> {
</span><del>-    appendItemAndUpdateExtent(StrokeEllipse::create(rect));
</del><ins>+    append<StrokeEllipse>(rect);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::clearRect(const FloatRect& rect)
</span><span class="cx"> {
</span><del>-    appendItemAndUpdateExtent(ClearRect::create(rect));
</del><ins>+    append<ClearRect>(rect);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> #if USE(CG)
</span><span class="cx"> void Recorder::applyStrokePattern()
</span><span class="cx"> {
</span><del>-    appendItem(ApplyStrokePattern::create());
</del><ins>+    append<ApplyStrokePattern>();
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::applyFillPattern()
</span><span class="cx"> {
</span><del>-    appendItem(ApplyFillPattern::create());
</del><ins>+    append<ApplyFillPattern>();
</ins><span class="cx"> }
</span><span class="cx"> #endif
</span><span class="cx"> 
</span><span class="lines">@@ -398,23 +398,23 @@
</span><span class="cx"> void Recorder::clip(const FloatRect& rect)
</span><span class="cx"> {
</span><span class="cx">     currentState().clipBounds.intersect(rect);
</span><del>-    appendItem(Clip::create(rect));
</del><ins>+    append<Clip>(rect);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::clipOut(const FloatRect& rect)
</span><span class="cx"> {
</span><del>-    appendItem(ClipOut::create(rect));
</del><ins>+    append<ClipOut>(rect);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::clipOut(const Path& path)
</span><span class="cx"> {
</span><del>-    appendItem(ClipOutToPath::create(path));
</del><ins>+    append<ClipOutToPath>(path);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::clipPath(const Path& path, WindRule windRule)
</span><span class="cx"> {
</span><span class="cx">     currentState().clipBounds.intersect(path.fastBoundingRect());
</span><del>-    appendItem(ClipPath::create(path, windRule));
</del><ins>+    append<ClipPath>(path, windRule);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> IntRect Recorder::clipBounds()
</span><span class="lines">@@ -442,12 +442,12 @@
</span><span class="cx"> 
</span><span class="cx">     auto recordingContext = makeUnique<DrawingContext>(destination.size(), initialCTM);
</span><span class="cx">     drawingFunction(recordingContext->context());
</span><del>-    appendItem(ClipToDrawingCommands::create(destination, colorSpace, recordingContext->takeDisplayList()));
</del><ins>+    append<ClipToDrawingCommands>(destination, colorSpace, recordingContext->takeDisplayList());
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::paintFrameForMedia(MediaPlayer& player, const FloatRect& destination)
</span><span class="cx"> {
</span><del>-    appendItem(PaintFrameForMedia::create(player, destination));
</del><ins>+    append<PaintFrameForMedia>(player, destination);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void Recorder::applyDeviceScaleFactor(float deviceScaleFactor)
</span><span class="lines">@@ -454,7 +454,7 @@
</span><span class="cx"> {
</span><span class="cx">     // FIXME: this changes the baseCTM, which will invalidate all of our cached extents.
</span><span class="cx">     // Assert that it's only called early on?
</span><del>-    appendItem(ApplyDeviceScaleFactor::create(deviceScaleFactor));
</del><ins>+    append<ApplyDeviceScaleFactor>(deviceScaleFactor);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> FloatRect Recorder::roundToDevicePixels(const FloatRect& rect, GraphicsContext::RoundingMode)
</span><span class="lines">@@ -463,30 +463,6 @@
</span><span class="cx">     return rect;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-void Recorder::appendItemAndUpdateExtent(Ref<DrawingItem>&& item)
-{
-    DrawingItem& newItem = item.get();
-    appendItem(WTFMove(item));
-    updateItemExtent(newItem);
-}
-
-void Recorder::appendItem(Ref<Item>&& item)
-{
-    Item& newItem = item.get();
-    auto type = newItem.type();
-    willAppendItemOfType(type);
-    m_displayList.append(WTFMove(item));
-    didAppendItemOfType(type);
-}
-
-void Recorder::updateItemExtent(DrawingItem& item) const
-{
-    if (Optional<FloatRect> rect = item.localBounds(graphicsContext()))
-        item.setExtent(extentFromLocalBounds(rect.value()));
-    else if (Optional<FloatRect> rect = item.globalBounds())
-        item.setExtent(rect.value());
-}
-
</del><span class="cx"> // FIXME: share with ShadowData
</span><span class="cx"> static inline float shadowPaintingExtent(float blurRadius)
</span><span class="cx"> {
</span><span class="lines">@@ -506,7 +482,7 @@
</span><span class="cx">     float shadowRadius;
</span><span class="cx">     Color shadowColor;
</span><span class="cx">     if (graphicsContext().getShadow(shadowOffset, shadowRadius, shadowColor)) {
</span><del>-        FloatRect shadowExtent= bounds;
</del><ins>+        FloatRect shadowExtent = bounds;
</ins><span class="cx">         shadowExtent.move(shadowOffset);
</span><span class="cx">         shadowExtent.inflate(shadowPaintingExtent(shadowRadius));
</span><span class="cx">         bounds.unite(shadowExtent);
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformgraphicsdisplaylistsDisplayListRecorderh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/graphics/displaylists/DisplayListRecorder.h (269524 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/graphics/displaylists/DisplayListRecorder.h        2020-11-06 18:44:09 UTC (rev 269524)
+++ trunk/Source/WebCore/platform/graphics/displaylists/DisplayListRecorder.h   2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -27,6 +27,7 @@
</span><span class="cx"> 
</span><span class="cx"> #include "DisplayList.h"
</span><span class="cx"> #include "DisplayListDrawGlyphsRecorder.h"
</span><ins>+#include "DisplayListItems.h"
</ins><span class="cx"> #include "GraphicsContextImpl.h"
</span><span class="cx"> #include "Image.h" // For Image::TileRule.
</span><span class="cx"> #include "TextFlags.h"
</span><span class="lines">@@ -48,8 +49,6 @@
</span><span class="cx"> 
</span><span class="cx"> namespace DisplayList {
</span><span class="cx"> 
</span><del>-class DrawingItem;
-
</del><span class="cx"> class Recorder : public GraphicsContextImpl {
</span><span class="cx">     WTF_MAKE_FAST_ALLOCATED;
</span><span class="cx">     WTF_MAKE_NONCOPYABLE(Recorder);
</span><span class="lines">@@ -147,15 +146,34 @@
</span><span class="cx"> 
</span><span class="cx">     FloatRect roundToDevicePixels(const FloatRect&, GraphicsContext::RoundingMode) override;
</span><span class="cx"> 
</span><del>-    void appendItem(Ref<Item>&&);
</del><ins>+    template<typename T, class... Args>
+    void append(Args&&... args)
+    {
+        willAppendItemOfType(T::itemType);
+        m_displayList.append<T>(std::forward<Args>(args)...);
+        didAppendItemOfType(T::itemType);
+
+        if (!T::isDrawingItem)
+            return;
+
+        if (LIKELY(!m_displayList.tracksDrawingItemExtents()))
+            return;
+
+        auto item = T(std::forward<Args>(args)...);
+        if (auto rect = item.localBounds(graphicsContext()))
+            m_displayList.addDrawingItemExtent(extentFromLocalBounds(*rect));
+        else if (auto rect = item.globalBounds())
+            m_displayList.addDrawingItemExtent(*rect);
+        else
+            m_displayList.addDrawingItemExtent(WTF::nullopt);
+    }
+
</ins><span class="cx">     void willAppendItemOfType(ItemType);
</span><span class="cx">     void didAppendItemOfType(ItemType);
</span><del>-    void appendItemAndUpdateExtent(Ref<DrawingItem>&&);
</del><span class="cx"> 
</span><span class="cx">     void appendStateChangeItem(const GraphicsContextStateChange&, GraphicsContextState::StateChangeFlags);
</span><span class="cx"> 
</span><span class="cx">     FloatRect extentFromLocalBounds(const FloatRect&) const;
</span><del>-    void updateItemExtent(DrawingItem&) const;
</del><span class="cx">     
</span><span class="cx">     const AffineTransform& ctm() const;
</span><span class="cx">     const FloatRect& clipBounds() const;
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformgraphicsdisplaylistsDisplayListReplayercpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/graphics/displaylists/DisplayListReplayer.cpp (269524 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/graphics/displaylists/DisplayListReplayer.cpp      2020-11-06 18:44:09 UTC (rev 269524)
+++ trunk/Source/WebCore/platform/graphics/displaylists/DisplayListReplayer.cpp 2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -44,18 +44,18 @@
</span><span class="cx"> 
</span><span class="cx"> Replayer::~Replayer() = default;
</span><span class="cx"> 
</span><del>-void Replayer::applyItem(Item& item)
</del><ins>+void Replayer::applyItem(ItemHandle item)
</ins><span class="cx"> {
</span><span class="cx">     if (m_delegate && m_delegate->apply(item, m_context))
</span><span class="cx">         return;
</span><del>-    
-    if (item.type() == ItemType::DrawImageBuffer) {
-        auto& drawItem = static_cast<DrawImageBuffer&>(item);
</del><ins>+
+    if (item.is<DrawImageBuffer>()) {
+        auto& drawItem = item.get<DrawImageBuffer>();
</ins><span class="cx">         if (auto* imageBuffer = m_imageBuffers.get(drawItem.renderingResourceIdentifier()))
</span><span class="cx">             drawItem.apply(m_context, *imageBuffer);
</span><span class="cx">         return;
</span><span class="cx">     }
</span><del>-    
</del><ins>+
</ins><span class="cx">     item.apply(m_context);
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="lines">@@ -68,25 +68,25 @@
</span><span class="cx">     if (UNLIKELY(trackReplayList))
</span><span class="cx">         replayList = makeUnique<DisplayList>();
</span><span class="cx"> 
</span><del>-    auto& items = m_displayList.list();
-    for (size_t i = 0; i < items.size(); ++i) {
-        auto& item = items[i].get();
-
-        if (!initialClip.isZero() && is<DrawingItem>(item)) {
-            const DrawingItem& drawingItem = downcast<DrawingItem>(item);
-            if (drawingItem.extentKnown() && !drawingItem.extent().intersects(initialClip)) {
-                LOG_WITH_STREAM(DisplayLists, stream << "skipping " << i << " " << item);
-                continue;
-            }
</del><ins>+#if !LOG_DISABLED
+    size_t i = 0;
+#endif
+    for (auto [item, extent] : m_displayList) {
+        if (!initialClip.isZero() && extent && !extent->intersects(initialClip)) {
+            LOG_WITH_STREAM(DisplayLists, stream << "skipping " << i++ << " " << item);
+            continue;
</ins><span class="cx">         }
</span><span class="cx"> 
</span><span class="cx">         LOG_WITH_STREAM(DisplayLists, stream << "applying " << i << " " << item);
</span><span class="cx">         applyItem(item);
</span><span class="cx"> 
</span><del>-        if (UNLIKELY(trackReplayList))
-            replayList->appendItem(const_cast<Item&>(item));
</del><ins>+        if (UNLIKELY(trackReplayList)) {
+            replayList->append(item);
+            if (item.isDrawingItem())
+                replayList->addDrawingItemExtent(WTFMove(extent));
+        }
</ins><span class="cx">     }
</span><del>-    
</del><ins>+
</ins><span class="cx">     return replayList;
</span><span class="cx"> }
</span><span class="cx"> 
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformgraphicsdisplaylistsDisplayListReplayerh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/graphics/displaylists/DisplayListReplayer.h (269524 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/graphics/displaylists/DisplayListReplayer.h        2020-11-06 18:44:09 UTC (rev 269524)
+++ trunk/Source/WebCore/platform/graphics/displaylists/DisplayListReplayer.h   2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -50,11 +50,11 @@
</span><span class="cx">     class Delegate {
</span><span class="cx">     public:
</span><span class="cx">         virtual ~Delegate() { }
</span><del>-        virtual bool apply(Item&, GraphicsContext&) { return false; }
</del><ins>+        virtual bool apply(ItemHandle, GraphicsContext&) { return false; }
</ins><span class="cx">     };
</span><span class="cx">     
</span><span class="cx"> private:
</span><del>-    void applyItem(Item&);
</del><ins>+    void applyItem(ItemHandle);
</ins><span class="cx">     
</span><span class="cx">     GraphicsContext& m_context;
</span><span class="cx">     const DisplayList& m_displayList;
</span></span></pre></div>
<a id="trunkSourceWebKitChangeLog"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit/ChangeLog (269524 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit/ChangeLog    2020-11-06 18:44:09 UTC (rev 269524)
+++ trunk/Source/WebKit/ChangeLog       2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -1,3 +1,63 @@
</span><ins>+2020-11-06  Wenson Hsieh  <wenson_hsieh@apple.com>
+
+        [Concurrent display lists] Encode display list items directly into shared memory
+        https://bugs.webkit.org/show_bug.cgi?id=218406
+
+        Reviewed by Tim Horton.
+
+        Adjust for changes to display lists and display list items in WebCore (see Source/WebCore/ChangeLog for more
+        information). In particular, we implement the reading and writing client hooks consulted by ItemBuffer, and we
+        also add a temporary mechanism that allows RemoteRenderingBackendProxy (in the web process) to send display list
+        item data through shared memory to the RemoteRenderingBackend (in the GPU process). This temporary mechanism
+        does not attempt to make any reading or writing in shared memory concurrent between the GPU and web processes,
+        and exists only to make sure that rendering with the GPU process still works using these new display list items.
+
+        In the next patch, I will add a simple concurrent reader/writer model for display list processing between the
+        web and GPU processes, and (in doing so) revert most of the changes in `RemoteRenderingBackend` and
+        `RemoteRenderingBackendProxy` below.
+
+        See comments below for more detail.
+
+        * GPUProcess/graphics/RemoteImageBuffer.h:
+        (WebKit::RemoteImageBuffer::decodeAndCreate):
+        * GPUProcess/graphics/RemoteRenderingBackend.cpp:
+        (WebKit::RemoteRenderingBackend::applyResourceItem):
+        (WebKit::RemoteRenderingBackend::applyMediaItem):
+
+        Refactor these to take `WebCore::DisplayList::ItemHandle`.
+
+        (WebKit::RemoteRenderingBackend::applyDisplayList):
+        (WebKit::RemoteRenderingBackend::flushDisplayList):
+        (WebKit::RemoteRenderingBackend::flushDisplayListAndCommit):
+        (WebKit::RemoteRenderingBackend::didCreateSharedItemData):
+        * GPUProcess/graphics/RemoteRenderingBackend.h:
+        * GPUProcess/graphics/RemoteRenderingBackend.messages.in:
+        * Scripts/webkit/messages.py:
+        * Shared/SharedDisplayListHandle.cpp: Added.
+        (WebKit::SharedDisplayListHandle::SharedDisplayListHandle):
+        (WebKit::SharedDisplayListHandle::createDisplayList const):
+        * Shared/SharedDisplayListHandle.h: Added.
+
+        Add a WebKit2 helper class that represents display list data in shared memory that is propagated from the web
+        process to the GPU process. In the next patch, this class will be rewritten to support concurrent display list
+        reading and writing, with specialized subclasses in service of both the reader (i.e. the GPU process) and the
+        writer (i.e. the web process).
+
+        (WebKit::SharedDisplayListHandle::SharedDisplayListHandle):
+        (WebKit::SharedDisplayListHandle::encode const):
+        (WebKit::SharedDisplayListHandle::decode):
+        * Sources.txt:
+        * WebKit.xcodeproj/project.pbxproj:
+        * WebProcess/GPU/graphics/RemoteImageBufferProxy.h:
+        (WebKit::RemoteImageBufferProxy::RemoteImageBufferProxy):
+        * WebProcess/GPU/graphics/RemoteRenderingBackendProxy.cpp:
+        (WebKit::RemoteRenderingBackendProxy::flushDisplayList):
+        (WebKit::RemoteRenderingBackendProxy::flushDisplayListAndCommit):
+        (WebKit::RemoteRenderingBackendProxy::createItemBuffer):
+        * WebProcess/GPU/graphics/RemoteRenderingBackendProxy.h:
+        * WebProcess/GPU/graphics/RemoteRenderingBackendProxy.messages.in:
+        * WebProcess/GPU/graphics/RemoteResourceCacheProxy.cpp:
+
</ins><span class="cx"> 2020-11-06  Truitt Savell  <tsavell@apple.com>
</span><span class="cx"> 
</span><span class="cx">         Unreviewed, reverting r269486.
</span></span></pre></div>
<a id="trunkSourceWebKitGPUProcessgraphicsRemoteImageBufferh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit/GPUProcess/graphics/RemoteImageBuffer.h (269524 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit/GPUProcess/graphics/RemoteImageBuffer.h      2020-11-06 18:44:09 UTC (rev 269524)
+++ trunk/Source/WebKit/GPUProcess/graphics/RemoteImageBuffer.h 2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -27,14 +27,17 @@
</span><span class="cx"> 
</span><span class="cx"> #if ENABLE(GPU_PROCESS)
</span><span class="cx"> 
</span><ins>+#include "Decoder.h"
</ins><span class="cx"> #include "GPUConnectionToWebProcess.h"
</span><span class="cx"> #include <WebCore/ConcreteImageBuffer.h>
</span><ins>+#include <WebCore/DisplayList.h>
+#include <WebCore/DisplayListItems.h>
</ins><span class="cx"> #include <WebCore/DisplayListReplayer.h>
</span><span class="cx"> 
</span><span class="cx"> namespace WebKit {
</span><span class="cx"> 
</span><span class="cx"> template<typename BackendType>
</span><del>-class RemoteImageBuffer : public WebCore::ConcreteImageBuffer<BackendType>, public WebCore::DisplayList::Replayer::Delegate {
</del><ins>+class RemoteImageBuffer : public WebCore::ConcreteImageBuffer<BackendType>, public WebCore::DisplayList::Replayer::Delegate, public WebCore::DisplayList::ItemBufferReadingClient {
</ins><span class="cx">     using BaseConcreteImageBuffer = WebCore::ConcreteImageBuffer<BackendType>;
</span><span class="cx">     using BaseConcreteImageBuffer::context;
</span><span class="cx">     using BaseConcreteImageBuffer::m_backend;
</span><span class="lines">@@ -71,10 +74,10 @@
</span><span class="cx">         }
</span><span class="cx">     }
</span><span class="cx"> 
</span><del>-    bool apply(WebCore::DisplayList::Item& item, WebCore::GraphicsContext& context) override
</del><ins>+    bool apply(WebCore::DisplayList::ItemHandle item, WebCore::GraphicsContext& context) override
</ins><span class="cx">     {
</span><del>-        if (item.type() == WebCore::DisplayList::ItemType::PutImageData) {
-            auto& putImageDataItem = static_cast<WebCore::DisplayList::PutImageData&>(item);
</del><ins>+        if (item.is<WebCore::DisplayList::PutImageData>()) {
+            auto& putImageDataItem = item.get<WebCore::DisplayList::PutImageData>();
</ins><span class="cx">             putImageData(putImageDataItem.inputFormat(), putImageDataItem.imageData(), putImageDataItem.srcRect(), putImageDataItem.destPoint(), putImageDataItem.destFormat());
</span><span class="cx">             return true;
</span><span class="cx">         }
</span><span class="lines">@@ -82,6 +85,114 @@
</span><span class="cx">         return m_remoteRenderingBackend.applyMediaItem(item, context);
</span><span class="cx">     }
</span><span class="cx"> 
</span><ins>+    Optional<WebCore::DisplayList::ItemHandle> WARN_UNUSED_RETURN decodeItem(const uint8_t* data, size_t length, WebCore::DisplayList::ItemType type, uint8_t* handleLocation) override
+    {
+        switch (type) {
+        case WebCore::DisplayList::ItemType::ClipOutToPath:
+            return decodeAndCreate<WebCore::DisplayList::ClipOutToPath>(data, length, handleLocation);
+        case WebCore::DisplayList::ItemType::ClipPath:
+            return decodeAndCreate<WebCore::DisplayList::ClipPath>(data, length, handleLocation);
+        case WebCore::DisplayList::ItemType::ClipToDrawingCommands:
+            return decodeAndCreate<WebCore::DisplayList::ClipToDrawingCommands>(data, length, handleLocation);
+        case WebCore::DisplayList::ItemType::DrawFocusRingPath:
+            return decodeAndCreate<WebCore::DisplayList::DrawFocusRingPath>(data, length, handleLocation);
+        case WebCore::DisplayList::ItemType::DrawFocusRingRects:
+            return decodeAndCreate<WebCore::DisplayList::DrawFocusRingRects>(data, length, handleLocation);
+        case WebCore::DisplayList::ItemType::DrawGlyphs:
+            return decodeAndCreate<WebCore::DisplayList::DrawGlyphs>(data, length, handleLocation);
+        case WebCore::DisplayList::ItemType::DrawImage:
+            return decodeAndCreate<WebCore::DisplayList::DrawImage>(data, length, handleLocation);
+        case WebCore::DisplayList::ItemType::DrawLinesForText:
+            return decodeAndCreate<WebCore::DisplayList::DrawLinesForText>(data, length, handleLocation);
+        case WebCore::DisplayList::ItemType::DrawNativeImage:
+            return decodeAndCreate<WebCore::DisplayList::DrawNativeImage>(data, length, handleLocation);
+        case WebCore::DisplayList::ItemType::DrawPath:
+            return decodeAndCreate<WebCore::DisplayList::DrawPath>(data, length, handleLocation);
+        case WebCore::DisplayList::ItemType::DrawPattern:
+            return decodeAndCreate<WebCore::DisplayList::DrawPattern>(data, length, handleLocation);
+        case WebCore::DisplayList::ItemType::DrawTiledImage:
+            return decodeAndCreate<WebCore::DisplayList::DrawTiledImage>(data, length, handleLocation);
+        case WebCore::DisplayList::ItemType::DrawTiledScaledImage:
+            return decodeAndCreate<WebCore::DisplayList::DrawTiledScaledImage>(data, length, handleLocation);
+        case WebCore::DisplayList::ItemType::FillCompositedRect:
+            return decodeAndCreate<WebCore::DisplayList::FillCompositedRect>(data, length, handleLocation);
+        case WebCore::DisplayList::ItemType::FillPath:
+            return decodeAndCreate<WebCore::DisplayList::FillPath>(data, length, handleLocation);
+        case WebCore::DisplayList::ItemType::FillRectWithColor:
+            return decodeAndCreate<WebCore::DisplayList::FillRectWithColor>(data, length, handleLocation);
+        case WebCore::DisplayList::ItemType::FillRectWithGradient:
+            return decodeAndCreate<WebCore::DisplayList::FillRectWithGradient>(data, length, handleLocation);
+        case WebCore::DisplayList::ItemType::FillRectWithRoundedHole:
+            return decodeAndCreate<WebCore::DisplayList::FillRectWithRoundedHole>(data, length, handleLocation);
+        case WebCore::DisplayList::ItemType::FillRoundedRect:
+            return decodeAndCreate<WebCore::DisplayList::FillRoundedRect>(data, length, handleLocation);
+        case WebCore::DisplayList::ItemType::PutImageData:
+            return decodeAndCreate<WebCore::DisplayList::PutImageData>(data, length, handleLocation);
+        case WebCore::DisplayList::ItemType::SetLineDash:
+            return decodeAndCreate<WebCore::DisplayList::SetLineDash>(data, length, handleLocation);
+        case WebCore::DisplayList::ItemType::SetState:
+            return decodeAndCreate<WebCore::DisplayList::SetState>(data, length, handleLocation);
+        case WebCore::DisplayList::ItemType::StrokePath:
+            return decodeAndCreate<WebCore::DisplayList::StrokePath>(data, length, handleLocation);
+        case WebCore::DisplayList::ItemType::ApplyDeviceScaleFactor:
+#if USE(CG)
+        case WebCore::DisplayList::ItemType::ApplyFillPattern:
+        case WebCore::DisplayList::ItemType::ApplyStrokePattern:
+#endif
+        case WebCore::DisplayList::ItemType::BeginTransparencyLayer:
+        case WebCore::DisplayList::ItemType::ClearRect:
+        case WebCore::DisplayList::ItemType::ClearShadow:
+        case WebCore::DisplayList::ItemType::Clip:
+        case WebCore::DisplayList::ItemType::ClipOut:
+        case WebCore::DisplayList::ItemType::ConcatenateCTM:
+        case WebCore::DisplayList::ItemType::DrawDotsForDocumentMarker:
+        case WebCore::DisplayList::ItemType::DrawEllipse:
+        case WebCore::DisplayList::ItemType::DrawImageBuffer:
+        case WebCore::DisplayList::ItemType::DrawLine:
+        case WebCore::DisplayList::ItemType::DrawRect:
+        case WebCore::DisplayList::ItemType::EndTransparencyLayer:
+        case WebCore::DisplayList::ItemType::FillEllipse:
+#if ENABLE(INLINE_PATH_DATA)
+        case WebCore::DisplayList::ItemType::FillInlinePath:
+#endif
+        case WebCore::DisplayList::ItemType::FillRect:
+        case WebCore::DisplayList::ItemType::PaintFrameForMedia:
+        case WebCore::DisplayList::ItemType::Restore:
+        case WebCore::DisplayList::ItemType::Rotate:
+        case WebCore::DisplayList::ItemType::Save:
+        case WebCore::DisplayList::ItemType::Scale:
+        case WebCore::DisplayList::ItemType::SetCTM:
+        case WebCore::DisplayList::ItemType::SetInlineFillColor:
+        case WebCore::DisplayList::ItemType::SetInlineFillGradient:
+        case WebCore::DisplayList::ItemType::SetInlineStrokeColor:
+        case WebCore::DisplayList::ItemType::SetLineCap:
+        case WebCore::DisplayList::ItemType::SetLineJoin:
+        case WebCore::DisplayList::ItemType::SetMiterLimit:
+        case WebCore::DisplayList::ItemType::SetStrokeThickness:
+        case WebCore::DisplayList::ItemType::StrokeEllipse:
+#if ENABLE(INLINE_PATH_DATA)
+        case WebCore::DisplayList::ItemType::StrokeInlinePath:
+#endif
+        case WebCore::DisplayList::ItemType::StrokeRect:
+        case WebCore::DisplayList::ItemType::Translate: {
+            ASSERT_NOT_REACHED();
+            break;
+        }
+        }
+        ASSERT_NOT_REACHED();
+        return WTF::nullopt;
+    }
+
+    template<typename T>
+    Optional<WebCore::DisplayList::ItemHandle> WARN_UNUSED_RETURN decodeAndCreate(const uint8_t* data, size_t length, uint8_t* handleLocation)
+    {
+        if (auto item = IPC::Decoder::decodeSingleObject<T>(data, length)) {
+            new (handleLocation + sizeof(WebCore::DisplayList::ItemType)) T(WTFMove(*item));
+            return {{ handleLocation }};
+        }
+        return WTF::nullopt;
+    }
+
</ins><span class="cx">     RemoteRenderingBackend& m_remoteRenderingBackend;
</span><span class="cx"> };
</span><span class="cx"> 
</span></span></pre></div>
<a id="trunkSourceWebKitGPUProcessgraphicsRemoteRenderingBackendcpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit/GPUProcess/graphics/RemoteRenderingBackend.cpp (269524 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit/GPUProcess/graphics/RemoteRenderingBackend.cpp       2020-11-06 18:44:09 UTC (rev 269524)
+++ trunk/Source/WebKit/GPUProcess/graphics/RemoteRenderingBackend.cpp  2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -72,13 +72,12 @@
</span><span class="cx">     return m_renderingBackendIdentifier.toUInt64();
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-bool RemoteRenderingBackend::applyMediaItem(const DisplayList::Item& item, GraphicsContext& context)
</del><ins>+bool RemoteRenderingBackend::applyMediaItem(DisplayList::ItemHandle item, GraphicsContext& context)
</ins><span class="cx"> {
</span><del>-    if (item.type() != WebCore::DisplayList::ItemType::PaintFrameForMedia)
</del><ins>+    if (!item.is<DisplayList::PaintFrameForMedia>())
</ins><span class="cx">         return false;
</span><span class="cx"> 
</span><del>-    auto& mediaItem = static_cast<const DisplayList::PaintFrameForMedia&>(item);
-
</del><ins>+    auto& mediaItem = item.get<DisplayList::PaintFrameForMedia>();
</ins><span class="cx">     auto process = gpuConnectionToWebProcess();
</span><span class="cx">     if (!process)
</span><span class="cx">         return false;
</span><span class="lines">@@ -125,21 +124,47 @@
</span><span class="cx">     m_remoteResourceCache.cacheImageBuffer(makeRef(*imageBuffer));
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-void RemoteRenderingBackend::flushDisplayList(const DisplayList::DisplayList& displayList, RenderingResourceIdentifier renderingResourceIdentifier)
</del><ins>+void RemoteRenderingBackend::applyDisplayList(const SharedDisplayListHandle& handle, RenderingResourceIdentifier renderingResourceIdentifier, ShouldFlushContext flushContext)
</ins><span class="cx"> {
</span><del>-    if (auto imageBuffer = m_remoteResourceCache.cachedImageBuffer(renderingResourceIdentifier))
-        imageBuffer->flushDisplayList(displayList);
</del><ins>+    auto displayList = handle.createDisplayList([&] (WebCore::DisplayList::ItemBufferIdentifier identifier) -> uint8_t* {
+        if (auto sharedMemory = m_sharedItemBuffers.take(identifier))
+            return reinterpret_cast<uint8_t*>(sharedMemory->data());
+        return nullptr;
+    });
+
+    if (!displayList) {
+        // FIXME: Add a message check to terminate the web process.
+        return;
+    }
+
+    auto imageBuffer = m_remoteResourceCache.cachedImageBuffer(renderingResourceIdentifier);
+    if (!imageBuffer) {
+        // FIXME: Add a message check to terminate the web process.
+        return;
+    }
+
+    if (imageBuffer->isAccelerated())
+        displayList->setItemBufferClient(static_cast<AcceleratedRemoteImageBuffer*>(imageBuffer));
+    else
+        displayList->setItemBufferClient(static_cast<UnacceleratedRemoteImageBuffer*>(imageBuffer));
+
+    imageBuffer->flushDisplayList(*displayList);
+
+    if (flushContext == ShouldFlushContext::Yes)
+        imageBuffer->flushContext();
</ins><span class="cx"> }
</span><span class="cx"> 
</span><del>-void RemoteRenderingBackend::flushDisplayListAndCommit(const DisplayList::DisplayList& displayList, DisplayListFlushIdentifier flushIdentifier, RenderingResourceIdentifier renderingResourceIdentifier)
</del><ins>+void RemoteRenderingBackend::flushDisplayList(const SharedDisplayListHandle& handle, RenderingResourceIdentifier renderingResourceIdentifier)
</ins><span class="cx"> {
</span><del>-    if (auto imageBuffer = m_remoteResourceCache.cachedImageBuffer(renderingResourceIdentifier)) {
-        imageBuffer->flushDisplayList(displayList);
-        imageBuffer->flushContext();
-        flushDisplayListWasCommitted(flushIdentifier, renderingResourceIdentifier);
-    }
</del><ins>+    applyDisplayList(handle, renderingResourceIdentifier, ShouldFlushContext::No);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><ins>+void RemoteRenderingBackend::flushDisplayListAndCommit(const SharedDisplayListHandle& handle, DisplayListFlushIdentifier flushIdentifier, RenderingResourceIdentifier renderingResourceIdentifier)
+{
+    applyDisplayList(handle, renderingResourceIdentifier, ShouldFlushContext::Yes);
+    flushDisplayListWasCommitted(flushIdentifier, renderingResourceIdentifier);
+}
+
</ins><span class="cx"> void RemoteRenderingBackend::getImageData(AlphaPremultiplication outputFormat, IntRect srcRect, RenderingResourceIdentifier renderingResourceIdentifier, CompletionHandler<void(IPC::ImageDataReference&&)>&& completionHandler)
</span><span class="cx"> {
</span><span class="cx">     RefPtr<ImageData> imageData;
</span><span class="lines">@@ -153,6 +178,12 @@
</span><span class="cx">     m_remoteResourceCache.releaseRemoteResource(renderingResourceIdentifier);
</span><span class="cx"> }
</span><span class="cx"> 
</span><ins>+void RemoteRenderingBackend::didCreateSharedItemData(DisplayList::ItemBufferIdentifier identifier, const SharedMemory::IPCHandle& handle)
+{
+    if (auto sharedMemory = SharedMemory::map(handle.handle, SharedMemory::Protection::ReadOnly))
+        m_sharedItemBuffers.set(identifier, WTFMove(sharedMemory));
+}
+
</ins><span class="cx"> } // namespace WebKit
</span><span class="cx"> 
</span><span class="cx"> #endif // ENABLE(GPU_PROCESS)
</span></span></pre></div>
<a id="trunkSourceWebKitGPUProcessgraphicsRemoteRenderingBackendh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit/GPUProcess/graphics/RemoteRenderingBackend.h (269524 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit/GPUProcess/graphics/RemoteRenderingBackend.h 2020-11-06 18:44:09 UTC (rev 269524)
+++ trunk/Source/WebKit/GPUProcess/graphics/RemoteRenderingBackend.h    2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -35,7 +35,9 @@
</span><span class="cx"> #include "MessageSender.h"
</span><span class="cx"> #include "RemoteResourceCache.h"
</span><span class="cx"> #include "RenderingBackendIdentifier.h"
</span><ins>+#include "SharedDisplayListHandle.h"
</ins><span class="cx"> #include <WebCore/ColorSpace.h>
</span><ins>+#include <WebCore/DisplayList.h>
</ins><span class="cx"> #include <WebCore/DisplayListItems.h>
</span><span class="cx"> #include <wtf/WeakPtr.h>
</span><span class="cx"> 
</span><span class="lines">@@ -64,7 +66,7 @@
</span><span class="cx">     RemoteResourceCache& remoteResourceCache() { return m_remoteResourceCache; }
</span><span class="cx"> 
</span><span class="cx">     // Rendering operations.
</span><del>-    bool applyMediaItem(const WebCore::DisplayList::Item&, WebCore::GraphicsContext&);
</del><ins>+    bool applyMediaItem(WebCore::DisplayList::ItemHandle, WebCore::GraphicsContext&);
</ins><span class="cx"> 
</span><span class="cx">     // Messages to be sent.
</span><span class="cx">     void imageBufferBackendWasCreated(const WebCore::FloatSize& logicalSize, const WebCore::IntSize& backendSize, float resolutionScale, WebCore::ColorSpace, ImageBufferBackendHandle, WebCore::RenderingResourceIdentifier);
</span><span class="lines">@@ -73,6 +75,9 @@
</span><span class="cx"> private:
</span><span class="cx">     RemoteRenderingBackend(GPUConnectionToWebProcess&, RenderingBackendIdentifier);
</span><span class="cx"> 
</span><ins>+    enum class ShouldFlushContext : bool { No, Yes };
+    void applyDisplayList(const SharedDisplayListHandle&, WebCore::RenderingResourceIdentifier, ShouldFlushContext);
+
</ins><span class="cx">     // IPC::MessageSender.
</span><span class="cx">     IPC::Connection* messageSenderConnection() const override;
</span><span class="cx">     uint64_t messageSenderDestinationID() const override;
</span><span class="lines">@@ -83,14 +88,16 @@
</span><span class="cx"> 
</span><span class="cx">     // Messages to be received.
</span><span class="cx">     void createImageBuffer(const WebCore::FloatSize& logicalSize, WebCore::RenderingMode, float resolutionScale, WebCore::ColorSpace, WebCore::RenderingResourceIdentifier);
</span><del>-    void flushDisplayList(const WebCore::DisplayList::DisplayList&, WebCore::RenderingResourceIdentifier);
-    void flushDisplayListAndCommit(const WebCore::DisplayList::DisplayList&, DisplayListFlushIdentifier, WebCore::RenderingResourceIdentifier);
</del><ins>+    void flushDisplayList(const SharedDisplayListHandle&, WebCore::RenderingResourceIdentifier);
+    void flushDisplayListAndCommit(const SharedDisplayListHandle&, DisplayListFlushIdentifier, WebCore::RenderingResourceIdentifier);
</ins><span class="cx">     void getImageData(WebCore::AlphaPremultiplication outputFormat, WebCore::IntRect srcRect, WebCore::RenderingResourceIdentifier, CompletionHandler<void(IPC::ImageDataReference&&)>&&);
</span><span class="cx">     void releaseRemoteResource(WebCore::RenderingResourceIdentifier);
</span><ins>+    void didCreateSharedItemData(WebCore::DisplayList::ItemBufferIdentifier, const SharedMemory::IPCHandle&);
</ins><span class="cx"> 
</span><span class="cx">     RemoteResourceCache m_remoteResourceCache;
</span><span class="cx">     WeakPtr<GPUConnectionToWebProcess> m_gpuConnectionToWebProcess;
</span><span class="cx">     RenderingBackendIdentifier m_renderingBackendIdentifier;
</span><ins>+    HashMap<WebCore::DisplayList::ItemBufferIdentifier, RefPtr<SharedMemory>> m_sharedItemBuffers;
</ins><span class="cx"> };
</span><span class="cx"> 
</span><span class="cx"> } // namespace WebKit
</span></span></pre></div>
<a id="trunkSourceWebKitGPUProcessgraphicsRemoteRenderingBackendmessagesin"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit/GPUProcess/graphics/RemoteRenderingBackend.messages.in (269524 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit/GPUProcess/graphics/RemoteRenderingBackend.messages.in       2020-11-06 18:44:09 UTC (rev 269524)
+++ trunk/Source/WebKit/GPUProcess/graphics/RemoteRenderingBackend.messages.in  2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -23,11 +23,12 @@
</span><span class="cx"> #if ENABLE(GPU_PROCESS)
</span><span class="cx"> 
</span><span class="cx"> messages -> RemoteRenderingBackend NotRefCounted {
</span><del>-    void CreateImageBuffer(WebCore::FloatSize logicalSize, WebCore::RenderingMode renderingMode, float resolutionScale, WebCore::ColorSpace colorSpace, WebCore::RenderingResourceIdentifier renderingResourceIdentifier)
-    void FlushDisplayList(WebCore::DisplayList::DisplayList displayList, WebCore::RenderingResourceIdentifier renderingResourceIdentifier)
-    void FlushDisplayListAndCommit(WebCore::DisplayList::DisplayList displayList, WebKit::DisplayListFlushIdentifier flushIdentifier, WebCore::RenderingResourceIdentifier renderingResourceIdentifier)
</del><ins>+    CreateImageBuffer(WebCore::FloatSize logicalSize, WebCore::RenderingMode renderingMode, float resolutionScale, WebCore::ColorSpace colorSpace, WebCore::RenderingResourceIdentifier renderingResourceIdentifier)
+    FlushDisplayList(WebKit::SharedDisplayListHandle displayList, WebCore::RenderingResourceIdentifier renderingResourceIdentifier)
+    FlushDisplayListAndCommit(WebKit::SharedDisplayListHandle displayList, WebKit::DisplayListFlushIdentifier flushIdentifier, WebCore::RenderingResourceIdentifier renderingResourceIdentifier)
</ins><span class="cx">     GetImageData(enum:uint8_t WebCore::AlphaPremultiplication outputFormat, WebCore::IntRect srcRect, WebCore::RenderingResourceIdentifier renderingResourceIdentifier) -> (IPC::ImageDataReference imageData) Synchronous
</span><del>-    void ReleaseRemoteResource(WebCore::RenderingResourceIdentifier renderingResourceIdentifier)
</del><ins>+    DidCreateSharedItemData(WebCore::DisplayList::ItemBufferIdentifier identifier, WebKit::SharedMemory::IPCHandle handle)
+    ReleaseRemoteResource(WebCore::RenderingResourceIdentifier renderingResourceIdentifier)
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> #endif // ENABLE(GPU_PROCESS)
</span></span></pre></div>
<a id="trunkSourceWebKitScriptswebkitmessagespy"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit/Scripts/webkit/messages.py (269524 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit/Scripts/webkit/messages.py   2020-11-06 18:44:09 UTC (rev 269524)
+++ trunk/Source/WebKit/Scripts/webkit/messages.py      2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -208,6 +208,7 @@
</span><span class="cx">         'String',
</span><span class="cx">         'WebCore::ColorSpace',
</span><span class="cx">         'WebCore::DictationContext',
</span><ins>+        'WebCore::DisplayList::ItemBufferIdentifier',
</ins><span class="cx">         'WebCore::DragApplicationFlags',
</span><span class="cx">         'WebCore::DocumentIdentifier',
</span><span class="cx">         'WebCore::DocumentOrWorkerIdentifier',
</span><span class="lines">@@ -587,6 +588,7 @@
</span><span class="cx">         'JSC::MessageSource': ['<JavaScriptCore/ConsoleTypes.h>'],
</span><span class="cx">         'Inspector::InspectorTargetType': ['<JavaScriptCore/InspectorTarget.h>'],
</span><span class="cx">         'Inspector::FrontendChannel::ConnectionType': ['<JavaScriptCore/InspectorFrontendChannel.h>'],
</span><ins>+        'WebCore::DisplayList::ItemBufferIdentifier': ['<WebCore/DisplayList.h>'],
</ins><span class="cx">         'MediaTime': ['<wtf/MediaTime.h>'],
</span><span class="cx">         'MonotonicTime': ['<wtf/MonotonicTime.h>'],
</span><span class="cx">         'Seconds': ['<wtf/Seconds.h>'],
</span></span></pre></div>
<a id="trunkSourceWebKitSharedSharedDisplayListHandlecppfromrev269524trunkSourceWebKitWebProcessGPUgraphicsRemoteResourceCacheProxycpp"></a>
<div class="copfile"><h4>Copied: trunk/Source/WebKit/Shared/SharedDisplayListHandle.cpp (from rev 269524, trunk/Source/WebKit/WebProcess/GPU/graphics/RemoteResourceCacheProxy.cpp) (0 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit/Shared/SharedDisplayListHandle.cpp                           (rev 0)
+++ trunk/Source/WebKit/Shared/SharedDisplayListHandle.cpp      2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -0,0 +1,53 @@
</span><ins>+/*
+ * Copyright (C) 2020 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include "config.h"
+#include "SharedDisplayListHandle.h"
+
+namespace WebKit {
+using namespace WebCore;
+
+SharedDisplayListHandle::SharedDisplayListHandle(const DisplayList::DisplayList& displayList)
+{
+    displayList.forEachItemBuffer([&] (auto& handle) {
+        m_buffers.append({ handle.identifier, handle.capacity });
+    });
+}
+
+std::unique_ptr<DisplayList::DisplayList> SharedDisplayListHandle::createDisplayList(ItemBufferProvider&& bufferProvider) const
+{
+    DisplayList::ItemBufferHandles handles;
+    handles.reserveInitialCapacity(m_buffers.size());
+    for (auto& [identifier, capacity] : m_buffers) {
+        auto* data = bufferProvider(identifier);
+        if (!data)
+            return nullptr;
+
+        handles.uncheckedAppend({ identifier, data, capacity });
+    }
+    return makeUnique<DisplayList::DisplayList>(WTFMove(handles));
+}
+
+} // namespace WebKit
</ins></span></pre></div>
<a id="trunkSourceWebKitSharedSharedDisplayListHandlehfromrev269524trunkSourceWebKitWebProcessGPUgraphicsRemoteResourceCacheProxycpp"></a>
<div class="copfile"><h4>Copied: trunk/Source/WebKit/Shared/SharedDisplayListHandle.h (from rev 269524, trunk/Source/WebKit/WebProcess/GPU/graphics/RemoteResourceCacheProxy.cpp) (0 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit/Shared/SharedDisplayListHandle.h                             (rev 0)
+++ trunk/Source/WebKit/Shared/SharedDisplayListHandle.h        2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -0,0 +1,66 @@
</span><ins>+/*
+ * Copyright (C) 2020 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#pragma once
+
+#include <WebCore/DisplayList.h>
+
+namespace WebKit {
+
+class SharedDisplayListHandle {
+public:
+    using ItemBufferProvider = Function<uint8_t*(WebCore::DisplayList::ItemBufferIdentifier)>;
+
+    SharedDisplayListHandle(const WebCore::DisplayList::DisplayList&);
+    std::unique_ptr<WebCore::DisplayList::DisplayList> createDisplayList(ItemBufferProvider&&) const;
+
+    template<class Encoder> void encode(Encoder&) const;
+    template<class Decoder> static Optional<SharedDisplayListHandle> decode(Decoder&);
+
+private:
+    SharedDisplayListHandle(Vector<std::pair<WebCore::DisplayList::ItemBufferIdentifier, size_t>>&& buffers)
+        : m_buffers(WTFMove(buffers))
+    {
+    }
+
+    Vector<std::pair<WebCore::DisplayList::ItemBufferIdentifier, size_t>> m_buffers;
+};
+
+template<class Encoder> void SharedDisplayListHandle::encode(Encoder& encoder) const
+{
+    encoder << m_buffers;
+}
+
+template<class Decoder> Optional<SharedDisplayListHandle> SharedDisplayListHandle::decode(Decoder& decoder)
+{
+    Optional<Vector<std::pair<WebCore::DisplayList::ItemBufferIdentifier, size_t>>> buffers;
+    decoder >> buffers;
+    if (!buffers)
+        return WTF::nullopt;
+
+    return {{ WTFMove(*buffers) }};
+}
+
+} // namespace WebKit
</ins></span></pre></div>
<a id="trunkSourceWebKitSourcestxt"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit/Sources.txt (269524 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit/Sources.txt  2020-11-06 18:44:09 UTC (rev 269524)
+++ trunk/Source/WebKit/Sources.txt     2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -173,6 +173,7 @@
</span><span class="cx"> Shared/SessionState.cpp
</span><span class="cx"> Shared/ShareableBitmap.cpp @no-unify
</span><span class="cx"> Shared/ShareableResource.cpp
</span><ins>+Shared/SharedDisplayListHandle.cpp
</ins><span class="cx"> Shared/SharedStringHashStore.cpp
</span><span class="cx"> Shared/SharedStringHashTableReadOnly.cpp
</span><span class="cx"> Shared/SharedStringHashTable.cpp
</span></span></pre></div>
<a id="trunkSourceWebKitWebKitxcodeprojprojectpbxproj"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit/WebKit.xcodeproj/project.pbxproj (269524 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit/WebKit.xcodeproj/project.pbxproj     2020-11-06 18:44:09 UTC (rev 269524)
+++ trunk/Source/WebKit/WebKit.xcodeproj/project.pbxproj        2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -1883,6 +1883,7 @@
</span><span class="cx">          F44DFEB21E9E752F0038D196 /* WebIconUtilities.h in Headers */ = {isa = PBXBuildFile; fileRef = F44DFEB01E9E752F0038D196 /* WebIconUtilities.h */; };
</span><span class="cx">          F48D2A8521583A7E00C6752B /* AppKitSPI.h in Headers */ = {isa = PBXBuildFile; fileRef = F48D2A8421583A0200C6752B /* AppKitSPI.h */; };
</span><span class="cx">          F496A4311F58A272004C1757 /* DragDropInteractionState.h in Headers */ = {isa = PBXBuildFile; fileRef = F496A42F1F58A272004C1757 /* DragDropInteractionState.h */; };
</span><ins>+               F4A6D6BC254CA3E900B65FAA /* SharedDisplayListHandle.h in Headers */ = {isa = PBXBuildFile; fileRef = F4A6D6BB254CA3E900B65FAA /* SharedDisplayListHandle.h */; };
</ins><span class="cx">           F4CB09E5225D5A0900891487 /* WebsiteMediaSourcePolicy.h in Headers */ = {isa = PBXBuildFile; fileRef = F4CB09E4225D5A0300891487 /* WebsiteMediaSourcePolicy.h */; };
</span><span class="cx">          F4D5F51D206087A10038BBA8 /* WKTextInputListViewController.h in Headers */ = {isa = PBXBuildFile; fileRef = F4D5F519206087A00038BBA8 /* WKTextInputListViewController.h */; };
</span><span class="cx">          F4D5F51F206087A10038BBA8 /* WKQuickboardListViewController.h in Headers */ = {isa = PBXBuildFile; fileRef = F4D5F51B206087A10038BBA8 /* WKQuickboardListViewController.h */; };
</span><span class="lines">@@ -5486,6 +5487,8 @@
</span><span class="cx">          F48D2A8421583A0200C6752B /* AppKitSPI.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = AppKitSPI.h; sourceTree = "<group>"; };
</span><span class="cx">          F496A42F1F58A272004C1757 /* DragDropInteractionState.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; name = DragDropInteractionState.h; path = ios/DragDropInteractionState.h; sourceTree = "<group>"; };
</span><span class="cx">          F496A4301F58A272004C1757 /* DragDropInteractionState.mm */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.objcpp; name = DragDropInteractionState.mm; path = ios/DragDropInteractionState.mm; sourceTree = "<group>"; };
</span><ins>+               F4A6D6BB254CA3E900B65FAA /* SharedDisplayListHandle.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = SharedDisplayListHandle.h; sourceTree = "<group>"; };
+               F4A6D6BD254CA52200B65FAA /* SharedDisplayListHandle.cpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; path = SharedDisplayListHandle.cpp; sourceTree = "<group>"; };
</ins><span class="cx">           F4AC655E22A3140E00A05607 /* WebPreferencesDefaultValuesIOS.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; name = WebPreferencesDefaultValuesIOS.mm; path = ios/WebPreferencesDefaultValuesIOS.mm; sourceTree = "<group>"; };
</span><span class="cx">          F4B378D021DDBBAB0095A378 /* WebUndoStepID.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = WebUndoStepID.h; sourceTree = "<group>"; };
</span><span class="cx">          F4CB09E4225D5A0300891487 /* WebsiteMediaSourcePolicy.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = WebsiteMediaSourcePolicy.h; sourceTree = "<group>"; };
</span><span class="lines">@@ -6193,6 +6196,8 @@
</span><span class="cx">                          1A6420E312DCE2FF00CAAE2C /* ShareableBitmap.h */,
</span><span class="cx">                          5121745E164C20E30037A5C1 /* ShareableResource.cpp */,
</span><span class="cx">                          5121745F164C20E30037A5C1 /* ShareableResource.h */,
</span><ins>+                               F4A6D6BD254CA52200B65FAA /* SharedDisplayListHandle.cpp */,
+                               F4A6D6BB254CA3E900B65FAA /* SharedDisplayListHandle.h */,
</ins><span class="cx">                           8313F7EA1F7DAE0400B944EB /* SharedStringHashStore.cpp */,
</span><span class="cx">                          8313F7E91F7DAE0300B944EB /* SharedStringHashStore.h */,
</span><span class="cx">                          8313F7E81F7DAE0300B944EB /* SharedStringHashTable.cpp */,
</span><span class="lines">@@ -11360,6 +11365,7 @@
</span><span class="cx">                          51217461164C20E30037A5C1 /* ShareableResource.h in Headers */,
</span><span class="cx">                          A183494224EF467800BDC9A8 /* SharedBufferCopy.h in Headers */,
</span><span class="cx">                          2DC18FF6EF2A3130C1301767 /* SharedBufferDataReference.h in Headers */,
</span><ins>+                               F4A6D6BC254CA3E900B65FAA /* SharedDisplayListHandle.h in Headers */,
</ins><span class="cx">                           1A24BED5120894D100FBB059 /* SharedMemory.h in Headers */,
</span><span class="cx">                          CD4B4D9D1E765E0000D27092 /* SharedRingBufferStorage.h in Headers */,
</span><span class="cx">                          8313F7EC1F7DAE0800B944EB /* SharedStringHashStore.h in Headers */,
</span></span></pre></div>
<a id="trunkSourceWebKitWebProcessGPUgraphicsRemoteImageBufferProxyh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit/WebProcess/GPU/graphics/RemoteImageBufferProxy.h (269524 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit/WebProcess/GPU/graphics/RemoteImageBufferProxy.h     2020-11-06 18:44:09 UTC (rev 269524)
+++ trunk/Source/WebKit/WebProcess/GPU/graphics/RemoteImageBufferProxy.h        2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -27,6 +27,10 @@
</span><span class="cx"> 
</span><span class="cx"> #if ENABLE(GPU_PROCESS)
</span><span class="cx"> 
</span><ins>+#include "Encoder.h"
+#include "RemoteRenderingBackendProxy.h"
+#include "SharedMemory.h"
+#include <WebCore/DisplayList.h>
</ins><span class="cx"> #include <WebCore/DisplayListImageBuffer.h>
</span><span class="cx"> #include <WebCore/DisplayListItems.h>
</span><span class="cx"> #include <WebCore/DisplayListRecorder.h>
</span><span class="lines">@@ -36,7 +40,7 @@
</span><span class="cx"> class RemoteRenderingBackend;
</span><span class="cx"> 
</span><span class="cx"> template<typename BackendType>
</span><del>-class RemoteImageBufferProxy : public WebCore::DisplayList::ImageBuffer<BackendType>, public WebCore::DisplayList::Recorder::Delegate {
</del><ins>+class RemoteImageBufferProxy : public WebCore::DisplayList::ImageBuffer<BackendType>, public WebCore::DisplayList::Recorder::Delegate, public WebCore::DisplayList::ItemBufferWritingClient {
</ins><span class="cx">     using BaseDisplayListImageBuffer = WebCore::DisplayList::ImageBuffer<BackendType>;
</span><span class="cx">     using BaseDisplayListImageBuffer::m_backend;
</span><span class="cx">     using BaseDisplayListImageBuffer::m_drawingContext;
</span><span class="lines">@@ -76,6 +80,8 @@
</span><span class="cx">         , m_remoteRenderingBackendProxy(makeWeakPtr(remoteRenderingBackendProxy))
</span><span class="cx">     {
</span><span class="cx">         ASSERT(m_remoteRenderingBackendProxy);
</span><ins>+        m_drawingContext.displayList().setItemBufferClient(this);
+        m_drawingContext.displayList().setTracksDrawingItemExtents(false);
</ins><span class="cx">     }
</span><span class="cx"> 
</span><span class="cx">     bool isPendingFlush() const { return m_sentFlushIdentifier != m_receivedFlushIdentifier; }
</span><span class="lines">@@ -173,6 +179,109 @@
</span><span class="cx">         displayList.clear();
</span><span class="cx">     }
</span><span class="cx"> 
</span><ins>+    WebCore::DisplayList::ItemBufferHandle createItemBuffer(size_t capacity) override
+    {
+        if (m_remoteRenderingBackendProxy)
+            return m_remoteRenderingBackendProxy->createItemBuffer(capacity);
+
+        ASSERT_NOT_REACHED();
+        return { };
+    }
+
+    RefPtr<WebCore::SharedBuffer> encodeItem(WebCore::DisplayList::ItemHandle item) const override
+    {
+        switch (item.type()) {
+        case WebCore::DisplayList::ItemType::ClipOutToPath:
+            return IPC::Encoder::encodeSingleObject<WebCore::DisplayList::ClipOutToPath>(item.get<WebCore::DisplayList::ClipOutToPath>());
+        case WebCore::DisplayList::ItemType::ClipPath:
+            return IPC::Encoder::encodeSingleObject<WebCore::DisplayList::ClipPath>(item.get<WebCore::DisplayList::ClipPath>());
+        case WebCore::DisplayList::ItemType::ClipToDrawingCommands:
+            return IPC::Encoder::encodeSingleObject<WebCore::DisplayList::ClipToDrawingCommands>(item.get<WebCore::DisplayList::ClipToDrawingCommands>());
+        case WebCore::DisplayList::ItemType::DrawFocusRingPath:
+            return IPC::Encoder::encodeSingleObject<WebCore::DisplayList::DrawFocusRingPath>(item.get<WebCore::DisplayList::DrawFocusRingPath>());
+        case WebCore::DisplayList::ItemType::DrawFocusRingRects:
+            return IPC::Encoder::encodeSingleObject<WebCore::DisplayList::DrawFocusRingRects>(item.get<WebCore::DisplayList::DrawFocusRingRects>());
+        case WebCore::DisplayList::ItemType::DrawGlyphs:
+            return IPC::Encoder::encodeSingleObject<WebCore::DisplayList::DrawGlyphs>(item.get<WebCore::DisplayList::DrawGlyphs>());
+        case WebCore::DisplayList::ItemType::DrawImage:
+            return IPC::Encoder::encodeSingleObject<WebCore::DisplayList::DrawImage>(item.get<WebCore::DisplayList::DrawImage>());
+        case WebCore::DisplayList::ItemType::DrawLinesForText:
+            return IPC::Encoder::encodeSingleObject<WebCore::DisplayList::DrawLinesForText>(item.get<WebCore::DisplayList::DrawLinesForText>());
+        case WebCore::DisplayList::ItemType::DrawNativeImage:
+            return IPC::Encoder::encodeSingleObject<WebCore::DisplayList::DrawNativeImage>(item.get<WebCore::DisplayList::DrawNativeImage>());
+        case WebCore::DisplayList::ItemType::DrawPath:
+            return IPC::Encoder::encodeSingleObject<WebCore::DisplayList::DrawPath>(item.get<WebCore::DisplayList::DrawPath>());
+        case WebCore::DisplayList::ItemType::DrawPattern:
+            return IPC::Encoder::encodeSingleObject<WebCore::DisplayList::DrawPattern>(item.get<WebCore::DisplayList::DrawPattern>());
+        case WebCore::DisplayList::ItemType::DrawTiledImage:
+            return IPC::Encoder::encodeSingleObject<WebCore::DisplayList::DrawTiledImage>(item.get<WebCore::DisplayList::DrawTiledImage>());
+        case WebCore::DisplayList::ItemType::DrawTiledScaledImage:
+            return IPC::Encoder::encodeSingleObject<WebCore::DisplayList::DrawTiledScaledImage>(item.get<WebCore::DisplayList::DrawTiledScaledImage>());
+        case WebCore::DisplayList::ItemType::FillCompositedRect:
+            return IPC::Encoder::encodeSingleObject<WebCore::DisplayList::FillCompositedRect>(item.get<WebCore::DisplayList::FillCompositedRect>());
+        case WebCore::DisplayList::ItemType::FillPath:
+            return IPC::Encoder::encodeSingleObject<WebCore::DisplayList::FillPath>(item.get<WebCore::DisplayList::FillPath>());
+        case WebCore::DisplayList::ItemType::FillRectWithColor:
+            return IPC::Encoder::encodeSingleObject<WebCore::DisplayList::FillRectWithColor>(item.get<WebCore::DisplayList::FillRectWithColor>());
+        case WebCore::DisplayList::ItemType::FillRectWithGradient:
+            return IPC::Encoder::encodeSingleObject<WebCore::DisplayList::FillRectWithGradient>(item.get<WebCore::DisplayList::FillRectWithGradient>());
+        case WebCore::DisplayList::ItemType::FillRectWithRoundedHole:
+            return IPC::Encoder::encodeSingleObject<WebCore::DisplayList::FillRectWithRoundedHole>(item.get<WebCore::DisplayList::FillRectWithRoundedHole>());
+        case WebCore::DisplayList::ItemType::FillRoundedRect:
+            return IPC::Encoder::encodeSingleObject<WebCore::DisplayList::FillRoundedRect>(item.get<WebCore::DisplayList::FillRoundedRect>());
+        case WebCore::DisplayList::ItemType::PutImageData:
+            return IPC::Encoder::encodeSingleObject<WebCore::DisplayList::PutImageData>(item.get<WebCore::DisplayList::PutImageData>());
+        case WebCore::DisplayList::ItemType::SetLineDash:
+            return IPC::Encoder::encodeSingleObject<WebCore::DisplayList::SetLineDash>(item.get<WebCore::DisplayList::SetLineDash>());
+        case WebCore::DisplayList::ItemType::SetState:
+            return IPC::Encoder::encodeSingleObject<WebCore::DisplayList::SetState>(item.get<WebCore::DisplayList::SetState>());
+        case WebCore::DisplayList::ItemType::StrokePath:
+            return IPC::Encoder::encodeSingleObject<WebCore::DisplayList::StrokePath>(item.get<WebCore::DisplayList::StrokePath>());
+        case WebCore::DisplayList::ItemType::ApplyDeviceScaleFactor:
+#if USE(CG)
+        case WebCore::DisplayList::ItemType::ApplyFillPattern:
+        case WebCore::DisplayList::ItemType::ApplyStrokePattern:
+#endif
+        case WebCore::DisplayList::ItemType::BeginTransparencyLayer:
+        case WebCore::DisplayList::ItemType::ClearRect:
+        case WebCore::DisplayList::ItemType::ClearShadow:
+        case WebCore::DisplayList::ItemType::Clip:
+        case WebCore::DisplayList::ItemType::ClipOut:
+        case WebCore::DisplayList::ItemType::ConcatenateCTM:
+        case WebCore::DisplayList::ItemType::DrawDotsForDocumentMarker:
+        case WebCore::DisplayList::ItemType::DrawEllipse:
+        case WebCore::DisplayList::ItemType::DrawImageBuffer:
+        case WebCore::DisplayList::ItemType::DrawLine:
+        case WebCore::DisplayList::ItemType::DrawRect:
+        case WebCore::DisplayList::ItemType::EndTransparencyLayer:
+        case WebCore::DisplayList::ItemType::FillEllipse:
+#if ENABLE(INLINE_PATH_DATA)
+        case WebCore::DisplayList::ItemType::FillInlinePath:
+#endif
+        case WebCore::DisplayList::ItemType::FillRect:
+        case WebCore::DisplayList::ItemType::PaintFrameForMedia:
+        case WebCore::DisplayList::ItemType::Restore:
+        case WebCore::DisplayList::ItemType::Rotate:
+        case WebCore::DisplayList::ItemType::Save:
+        case WebCore::DisplayList::ItemType::Scale:
+        case WebCore::DisplayList::ItemType::SetCTM:
+        case WebCore::DisplayList::ItemType::SetInlineFillColor:
+        case WebCore::DisplayList::ItemType::SetInlineFillGradient:
+        case WebCore::DisplayList::ItemType::SetInlineStrokeColor:
+        case WebCore::DisplayList::ItemType::SetLineCap:
+        case WebCore::DisplayList::ItemType::SetLineJoin:
+        case WebCore::DisplayList::ItemType::SetMiterLimit:
+        case WebCore::DisplayList::ItemType::SetStrokeThickness:
+        case WebCore::DisplayList::ItemType::StrokeEllipse:
+#if ENABLE(INLINE_PATH_DATA)
+        case WebCore::DisplayList::ItemType::StrokeInlinePath:
+#endif
+        case WebCore::DisplayList::ItemType::StrokeRect:
+        case WebCore::DisplayList::ItemType::Translate:
+            RELEASE_ASSERT_NOT_REACHED();
+        }
+    }
+
</ins><span class="cx">     void didAppendItemOfType(WebCore::DisplayList::ItemType type) override
</span><span class="cx">     {
</span><span class="cx">         if (type == WebCore::DisplayList::ItemType::DrawImageBuffer)
</span></span></pre></div>
<a id="trunkSourceWebKitWebProcessGPUgraphicsRemoteRenderingBackendProxycpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit/WebProcess/GPU/graphics/RemoteRenderingBackendProxy.cpp (269524 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit/WebProcess/GPU/graphics/RemoteRenderingBackendProxy.cpp      2020-11-06 18:44:09 UTC (rev 269524)
+++ trunk/Source/WebKit/WebProcess/GPU/graphics/RemoteRenderingBackendProxy.cpp 2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -34,6 +34,8 @@
</span><span class="cx"> #include "PlatformRemoteImageBufferProxy.h"
</span><span class="cx"> #include "RemoteRenderingBackendMessages.h"
</span><span class="cx"> #include "RemoteRenderingBackendProxyMessages.h"
</span><ins>+#include "SharedDisplayListHandle.h"
+#include "SharedMemory.h"
</ins><span class="cx"> #include "WebProcess.h"
</span><span class="cx"> 
</span><span class="cx"> namespace WebKit {
</span><span class="lines">@@ -115,13 +117,15 @@
</span><span class="cx"> 
</span><span class="cx"> void RemoteRenderingBackendProxy::flushDisplayList(const DisplayList::DisplayList& displayList, RenderingResourceIdentifier renderingResourceIdentifier)
</span><span class="cx"> {
</span><del>-    send(Messages::RemoteRenderingBackend::FlushDisplayList(displayList, renderingResourceIdentifier), m_renderingBackendIdentifier);
</del><ins>+    send(Messages::RemoteRenderingBackend::FlushDisplayList({ displayList }, renderingResourceIdentifier), m_renderingBackendIdentifier);
+    m_sharedItemBuffers.clear();
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> DisplayListFlushIdentifier RemoteRenderingBackendProxy::flushDisplayListAndCommit(const DisplayList::DisplayList& displayList, RenderingResourceIdentifier renderingResourceIdentifier)
</span><span class="cx"> {
</span><span class="cx">     DisplayListFlushIdentifier sentFlushIdentifier = DisplayListFlushIdentifier::generate();
</span><del>-    send(Messages::RemoteRenderingBackend::FlushDisplayListAndCommit(displayList, sentFlushIdentifier, renderingResourceIdentifier), m_renderingBackendIdentifier);
</del><ins>+    send(Messages::RemoteRenderingBackend::FlushDisplayListAndCommit({ displayList }, sentFlushIdentifier, renderingResourceIdentifier), m_renderingBackendIdentifier);
+    m_sharedItemBuffers.clear();
</ins><span class="cx">     return sentFlushIdentifier;
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="lines">@@ -155,6 +159,23 @@
</span><span class="cx">         downcast<UnacceleratedRemoteImageBufferProxy>(*imageBuffer).commitFlushDisplayList(flushIdentifier);
</span><span class="cx"> }
</span><span class="cx"> 
</span><ins>+DisplayList::ItemBufferHandle RemoteRenderingBackendProxy::createItemBuffer(size_t capacity)
+{
+    static constexpr size_t defaultSharedItemBufferSize = 1 << 16;
+
+    auto sharedMemory = SharedMemory::allocate(std::max(defaultSharedItemBufferSize, capacity));
+    if (!sharedMemory)
+        return { };
+
+    auto identifier = DisplayList::ItemBufferIdentifier::generate();
+    SharedMemory::Handle sharedMemoryHandle;
+    sharedMemory->createHandle(sharedMemoryHandle, SharedMemory::Protection::ReadOnly);
+    send(Messages::RemoteRenderingBackend::DidCreateSharedItemData(identifier, { WTFMove(sharedMemoryHandle), sharedMemory->size() }), m_renderingBackendIdentifier);
+    m_sharedItemBuffers.set(identifier, sharedMemory.copyRef());
+
+    return { identifier, reinterpret_cast<uint8_t*>(sharedMemory->data()), sharedMemory->size() };
+}
+
</ins><span class="cx"> } // namespace WebKit
</span><span class="cx"> 
</span><span class="cx"> #endif // ENABLE(GPU_PROCESS)
</span></span></pre></div>
<a id="trunkSourceWebKitWebProcessGPUgraphicsRemoteRenderingBackendProxyh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit/WebProcess/GPU/graphics/RemoteRenderingBackendProxy.h (269524 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit/WebProcess/GPU/graphics/RemoteRenderingBackendProxy.h        2020-11-06 18:44:09 UTC (rev 269524)
+++ trunk/Source/WebKit/WebProcess/GPU/graphics/RemoteRenderingBackendProxy.h   2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -33,6 +33,7 @@
</span><span class="cx"> #include "MessageSender.h"
</span><span class="cx"> #include "RemoteResourceCacheProxy.h"
</span><span class="cx"> #include "RenderingBackendIdentifier.h"
</span><ins>+#include <WebCore/DisplayList.h>
</ins><span class="cx"> #include <WebCore/RenderingResourceIdentifier.h>
</span><span class="cx"> #include <wtf/WeakPtr.h>
</span><span class="cx"> 
</span><span class="lines">@@ -60,6 +61,7 @@
</span><span class="cx">     ~RemoteRenderingBackendProxy();
</span><span class="cx"> 
</span><span class="cx">     RemoteResourceCacheProxy& remoteResourceCacheProxy() { return m_remoteResourceCacheProxy; }
</span><ins>+    WebCore::DisplayList::ItemBufferHandle createItemBuffer(size_t);
</ins><span class="cx"> 
</span><span class="cx">     // IPC::MessageSender.
</span><span class="cx">     IPC::Connection* messageSenderConnection() const override;
</span><span class="lines">@@ -86,6 +88,7 @@
</span><span class="cx">     void flushDisplayListWasCommitted(DisplayListFlushIdentifier, WebCore::RenderingResourceIdentifier);
</span><span class="cx"> 
</span><span class="cx">     RemoteResourceCacheProxy m_remoteResourceCacheProxy;
</span><ins>+    HashMap<WebCore::DisplayList::ItemBufferIdentifier, RefPtr<SharedMemory>> m_sharedItemBuffers;
</ins><span class="cx">     RenderingBackendIdentifier m_renderingBackendIdentifier { RenderingBackendIdentifier::generate() };
</span><span class="cx"> };
</span><span class="cx"> 
</span></span></pre></div>
<a id="trunkSourceWebKitWebProcessGPUgraphicsRemoteRenderingBackendProxymessagesin"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit/WebProcess/GPU/graphics/RemoteRenderingBackendProxy.messages.in (269524 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit/WebProcess/GPU/graphics/RemoteRenderingBackendProxy.messages.in      2020-11-06 18:44:09 UTC (rev 269524)
+++ trunk/Source/WebKit/WebProcess/GPU/graphics/RemoteRenderingBackendProxy.messages.in 2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -23,8 +23,8 @@
</span><span class="cx"> #if ENABLE(GPU_PROCESS)
</span><span class="cx"> 
</span><span class="cx"> messages -> RemoteRenderingBackendProxy NotRefCounted {
</span><del>-    void ImageBufferBackendWasCreated(WebCore::FloatSize logicalSize, WebCore::IntSize backendSize, float resolutionScale, WebCore::ColorSpace colorSpace, WebKit::ImageBufferBackendHandle handle, WebCore::RenderingResourceIdentifier renderingResourceIdentifier)
-    void FlushDisplayListWasCommitted(WebKit::DisplayListFlushIdentifier flushIdentifier, WebCore::RenderingResourceIdentifier renderingResourceIdentifier)
</del><ins>+    ImageBufferBackendWasCreated(WebCore::FloatSize logicalSize, WebCore::IntSize backendSize, float resolutionScale, WebCore::ColorSpace colorSpace, WebKit::ImageBufferBackendHandle handle, WebCore::RenderingResourceIdentifier renderingResourceIdentifier)
+    FlushDisplayListWasCommitted(WebKit::DisplayListFlushIdentifier flushIdentifier, WebCore::RenderingResourceIdentifier renderingResourceIdentifier)
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> #endif // ENABLE(GPU_PROCESS)
</span></span></pre></div>
<a id="trunkSourceWebKitWebProcessGPUgraphicsRemoteResourceCacheProxycpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit/WebProcess/GPU/graphics/RemoteResourceCacheProxy.cpp (269524 => 269525)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit/WebProcess/GPU/graphics/RemoteResourceCacheProxy.cpp 2020-11-06 18:44:09 UTC (rev 269524)
+++ trunk/Source/WebKit/WebProcess/GPU/graphics/RemoteResourceCacheProxy.cpp    2020-11-06 18:54:52 UTC (rev 269525)
</span><span class="lines">@@ -28,6 +28,9 @@
</span><span class="cx"> 
</span><span class="cx"> #if ENABLE(GPU_PROCESS)
</span><span class="cx"> 
</span><ins>+#include "RemoteRenderingBackendProxy.h"
+#include <WebCore/ImageBuffer.h>
+
</ins><span class="cx"> namespace WebKit {
</span><span class="cx"> using namespace WebCore;
</span><span class="cx"> 
</span></span></pre>
</div>
</div>

</body>
</html>