1 /* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
2 /* vim: set ts=2 sw=2 et tw=78: */
3 /* This Source Code Form is subject to the terms of the Mozilla Public
4  * License, v. 2.0. If a copy of the MPL was not distributed with this
5  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6 
7 #include "nsHtml5DocumentBuilder.h"
8 
9 #include "nsIStyleSheetLinkingElement.h"
10 #include "nsStyleLinkElement.h"
11 #include "nsScriptLoader.h"
12 #include "nsIHTMLDocument.h"
13 
NS_IMPL_CYCLE_COLLECTION_INHERITED(nsHtml5DocumentBuilder,nsContentSink,mOwnedElements)14 NS_IMPL_CYCLE_COLLECTION_INHERITED(nsHtml5DocumentBuilder, nsContentSink,
15                                    mOwnedElements)
16 
17 NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION_INHERITED(nsHtml5DocumentBuilder)
18 NS_INTERFACE_MAP_END_INHERITING(nsContentSink)
19 
20 NS_IMPL_ADDREF_INHERITED(nsHtml5DocumentBuilder, nsContentSink)
21 NS_IMPL_RELEASE_INHERITED(nsHtml5DocumentBuilder, nsContentSink)
22 
23 nsHtml5DocumentBuilder::nsHtml5DocumentBuilder(bool aRunsToCompletion)
24 {
25   mRunsToCompletion = aRunsToCompletion;
26 }
27 
28 nsresult
Init(nsIDocument * aDoc,nsIURI * aURI,nsISupports * aContainer,nsIChannel * aChannel)29 nsHtml5DocumentBuilder::Init(nsIDocument* aDoc,
30                             nsIURI* aURI,
31                             nsISupports* aContainer,
32                             nsIChannel* aChannel)
33 {
34   return nsContentSink::Init(aDoc, aURI, aContainer, aChannel);
35 }
36 
~nsHtml5DocumentBuilder()37 nsHtml5DocumentBuilder::~nsHtml5DocumentBuilder()
38 {
39 }
40 
41 nsresult
MarkAsBroken(nsresult aReason)42 nsHtml5DocumentBuilder::MarkAsBroken(nsresult aReason)
43 {
44   mBroken = aReason;
45   return aReason;
46 }
47 
48 void
SetDocumentCharsetAndSource(nsACString & aCharset,int32_t aCharsetSource)49 nsHtml5DocumentBuilder::SetDocumentCharsetAndSource(nsACString& aCharset, int32_t aCharsetSource)
50 {
51   if (mDocument) {
52     mDocument->SetDocumentCharacterSetSource(aCharsetSource);
53     mDocument->SetDocumentCharacterSet(aCharset);
54   }
55 }
56 
57 void
UpdateStyleSheet(nsIContent * aElement)58 nsHtml5DocumentBuilder::UpdateStyleSheet(nsIContent* aElement)
59 {
60   // Break out of the doc update created by Flush() to zap a runnable
61   // waiting to call UpdateStyleSheet without the right observer
62   EndDocUpdate();
63 
64   if (MOZ_UNLIKELY(!mParser)) {
65     // EndDocUpdate ran stuff that called nsIParser::Terminate()
66     return;
67   }
68 
69   nsCOMPtr<nsIStyleSheetLinkingElement> ssle(do_QueryInterface(aElement));
70   NS_ASSERTION(ssle, "Node didn't QI to style.");
71 
72   ssle->SetEnableUpdates(true);
73 
74   bool willNotify;
75   bool isAlternate;
76   nsresult rv = ssle->UpdateStyleSheet(mRunsToCompletion ? nullptr : this,
77                                        &willNotify,
78                                        &isAlternate);
79   if (NS_SUCCEEDED(rv) && willNotify && !isAlternate && !mRunsToCompletion) {
80     ++mPendingSheetCount;
81     mScriptLoader->AddParserBlockingScriptExecutionBlocker();
82   }
83 
84   // Re-open update
85   BeginDocUpdate();
86 }
87 
88 void
SetDocumentMode(nsHtml5DocumentMode m)89 nsHtml5DocumentBuilder::SetDocumentMode(nsHtml5DocumentMode m)
90 {
91   nsCompatibility mode = eCompatibility_NavQuirks;
92   switch (m) {
93     case STANDARDS_MODE:
94       mode = eCompatibility_FullStandards;
95       break;
96     case ALMOST_STANDARDS_MODE:
97       mode = eCompatibility_AlmostStandards;
98       break;
99     case QUIRKS_MODE:
100       mode = eCompatibility_NavQuirks;
101       break;
102   }
103   nsCOMPtr<nsIHTMLDocument> htmlDocument = do_QueryInterface(mDocument);
104   NS_ASSERTION(htmlDocument, "Document didn't QI into HTML document.");
105   htmlDocument->SetCompatibilityMode(mode);
106 }
107 
108 // nsContentSink overrides
109 
110 void
UpdateChildCounts()111 nsHtml5DocumentBuilder::UpdateChildCounts()
112 {
113   // No-op
114 }
115 
116 nsresult
FlushTags()117 nsHtml5DocumentBuilder::FlushTags()
118 {
119   return NS_OK;
120 }
121