Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(502)

Unified Diff: Source/core/html/parser/BackgroundHTMLParser.cpp

Issue 100563004: Redirect HTML resource bytes directly to parser thread (Blink side CL) (Closed) Base URL: https://chromium.googlesource.com/chromium/blink.git@parserthread_decodermove
Patch Set: Cache parser thread pointer in HTMLDocumentParser Created 6 years, 11 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
Index: Source/core/html/parser/BackgroundHTMLParser.cpp
diff --git a/Source/core/html/parser/BackgroundHTMLParser.cpp b/Source/core/html/parser/BackgroundHTMLParser.cpp
index 77d11543259836602909d8da77ebeed03c3d073e..98964214e32dd45f2045b0f76c3f05be0b29a8ec 100644
--- a/Source/core/html/parser/BackgroundHTMLParser.cpp
+++ b/Source/core/html/parser/BackgroundHTMLParser.cpp
@@ -27,7 +27,6 @@
#include "core/html/parser/BackgroundHTMLParser.h"
#include "core/html/parser/HTMLDocumentParser.h"
-#include "core/html/parser/HTMLParserThread.h"
#include "core/html/parser/TextResourceDecoder.h"
#include "core/html/parser/XSSAuditor.h"
#include "wtf/MainThread.h"
@@ -94,11 +93,47 @@ BackgroundHTMLParser::BackgroundHTMLParser(PassRefPtr<WeakReference<BackgroundHT
, m_xssAuditor(config->xssAuditor.release())
, m_preloadScanner(config->preloadScanner.release())
, m_decoder(config->decoder.release())
+ , m_resourceProvider(config->resourceProvider.release())
+ , m_receivingDataOnlyFromResourceProvider(false)
{
+ // Tell the resource provider that we're ready to start receiving
+ // chunks of data directly from the parser thread.
+ if (m_resourceProvider)
+ m_resourceProvider->setBackgroundClient(this);
}
BackgroundHTMLParser::~BackgroundHTMLParser()
{
+ if (m_resourceProvider) {
+ // Tell the resource provider that calling into this instance
+ // is no longer safe and any further data received should be
+ // ignored.
+ m_resourceProvider->setBackgroundClient(0);
+ // The resource provider needs to be destructed on the main thread,
+ // as the filter it installs on the I/O thread can only be removed
abarth-chromium 2014/02/03 21:17:36 Blink doesn't know anything about I/O threads.
oystein (OOO til 10th of July) 2014/02/05 00:05:00 Removed that part of the comment; it was just a cl
+ // from the main thread...
+ // Note we can only call static functions on the HTMLDocumentParser at this point
+ // as the weakptr we have for it is likely invalidated now.
+ callOnMainThread(bind(&HTMLDocumentParser::destroyResourceProvider, m_resourceProvider.release()));
+ }
+}
+
+void BackgroundHTMLParser::didReceivedData(const char* data, size_t length)
+{
+ if (m_receivingDataOnlyFromResourceProvider && m_decoder) {
+ updateDocument(m_decoder->decode(data, length));
+ return;
+ }
+
+ // If the parser thread is not standalone yet, it means we may get
+ // further data packets from the main thread and will need to queue
+ // up any data coming directly from the parser thread until we're
+ // sure we're complete. This is also necessary if we've lost our
+ // decoder, until we get a new one passed from the main thread.
+
+ OwnPtr<Vector<char> > buffer = adoptPtr(new Vector<char>(length));
+ memcpy(buffer->data(), data, length);
abarth-chromium 2014/02/03 21:17:36 buffer.append(data, length)
oystein (OOO til 10th of July) 2014/02/05 00:05:00 Done.
+ m_queuedData.append(buffer.release());
}
void BackgroundHTMLParser::append(const String& input)
@@ -110,12 +145,18 @@ void BackgroundHTMLParser::append(const String& input)
void BackgroundHTMLParser::appendBytes(PassOwnPtr<Vector<char> > buffer)
{
+ ASSERT(!m_receivingDataOnlyFromResourceProvider);
updateDocument(m_decoder->decode(buffer->data(), buffer->size()));
}
void BackgroundHTMLParser::setDecoder(PassOwnPtr<TextResourceDecoder> decoder)
{
m_decoder = decoder;
+
+ // If our decoder got reset in mid-stream and got recreated, we may have
+ // some pending data here.
+ if (m_decoder)
+ flushQueuedData();
}
void BackgroundHTMLParser::flush()
@@ -129,7 +170,6 @@ void BackgroundHTMLParser::updateDocument(const String& decodedData)
if (encodingData != m_lastSeenEncodingData) {
m_lastSeenEncodingData = encodingData;
-
m_xssAuditor->setEncoding(encodingData.encoding());
callOnMainThread(bind(&HTMLDocumentParser::didReceiveEncodingDataFromBackgroundParser, m_parser, encodingData));
}
@@ -170,6 +210,30 @@ void BackgroundHTMLParser::stop()
delete this;
}
+void BackgroundHTMLParser::flushQueuedData()
+{
+ // We only process queued chunks if we have a decoder and if we know
+ // we won't be receiving any more chunks for the main thread. Otherwise
+ // we hang on to the chunks for a bit longer.
+ if (!m_decoder || !m_receivingDataOnlyFromResourceProvider)
+ return;
+
+ for (Vector<OwnPtr<Vector<char> > >::iterator entry = m_queuedData.begin(); entry != m_queuedData.end(); ++entry)
+ updateDocument(m_decoder->decode((*entry)->data(), (*entry)->size()));
abarth-chromium 2014/02/03 21:17:36 SharedBuffer has a better way of doing this sort o
oystein (OOO til 10th of July) 2014/02/05 00:05:00 Done.
+
+ m_queuedData.clear();
+}
+
+void BackgroundHTMLParser::resourceFilterAdded()
+{
+ m_receivingDataOnlyFromResourceProvider = true;
+
+ // At this point we know for sure that no further data will
+ // be coming from the main thread, so we can process anything
+ // we've received directly on the parser thread in the meantime.
+ flushQueuedData();
+}
+
void BackgroundHTMLParser::forcePlaintextForTextDocument()
{
// This is only used by the TextDocumentParser (a subclass of HTMLDocumentParser)

Powered by Google App Engine
This is Rietveld 408576698