OLD | NEW |
---|---|
1 /* | 1 /* |
2 * Copyright (C) 2010 Google, Inc. All Rights Reserved. | 2 * Copyright (C) 2010 Google, Inc. All Rights Reserved. |
3 * | 3 * |
4 * Redistribution and use in source and binary forms, with or without | 4 * Redistribution and use in source and binary forms, with or without |
5 * modification, are permitted provided that the following conditions | 5 * modification, are permitted provided that the following conditions |
6 * are met: | 6 * are met: |
7 * 1. Redistributions of source code must retain the above copyright | 7 * 1. Redistributions of source code must retain the above copyright |
8 * notice, this list of conditions and the following disclaimer. | 8 * notice, this list of conditions and the following disclaimer. |
9 * 2. Redistributions in binary form must reproduce the above copyright | 9 * 2. Redistributions in binary form must reproduce the above copyright |
10 * notice, this list of conditions and the following disclaimer in the | 10 * notice, this list of conditions and the following disclaimer in the |
(...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
47 : m_document(document) | 47 : m_document(document) |
48 , m_host(host) | 48 , m_host(host) |
49 , m_scriptNestingLevel(0) | 49 , m_scriptNestingLevel(0) |
50 , m_hasScriptsWaitingForResources(false) | 50 , m_hasScriptsWaitingForResources(false) |
51 { | 51 { |
52 ASSERT(m_host); | 52 ASSERT(m_host); |
53 } | 53 } |
54 | 54 |
55 HTMLScriptRunner::~HTMLScriptRunner() | 55 HTMLScriptRunner::~HTMLScriptRunner() |
56 { | 56 { |
57 // FIXME: Should we be passed a "done loading/parsing" callback sooner than destruction? | 57 #if ENABLE(OILPAN) |
58 // If the document is destructed without having explicitly | |
59 // detached the parser (and this script runner object), perform | |
60 // detach steps now. This will happen if the Document, the parser | |
61 // and this script runner object are swept out in the same GC. | |
haraken
2014/05/29 11:32:08
Understood. Then I get back to the eseidel's quest
sof
2014/05/29 20:39:54
We have to have Document::detachParser() behave as
haraken
2014/05/30 01:28:51
Makes sense, sorry I was behind what you've alread
| |
62 detach(); | |
63 #else | |
64 // Verify that detach() has been called. | |
65 ASSERT(!m_document); | |
66 #endif | |
67 } | |
68 | |
69 void HTMLScriptRunner::detach() | |
70 { | |
71 if (!m_document) | |
72 return; | |
73 | |
58 if (m_parserBlockingScript.resource() && m_parserBlockingScript.watchingForL oad()) | 74 if (m_parserBlockingScript.resource() && m_parserBlockingScript.watchingForL oad()) |
59 stopWatchingForLoad(m_parserBlockingScript); | 75 stopWatchingForLoad(m_parserBlockingScript); |
60 | 76 |
61 while (!m_scriptsToExecuteAfterParsing.isEmpty()) { | 77 while (!m_scriptsToExecuteAfterParsing.isEmpty()) { |
62 PendingScript pendingScript = m_scriptsToExecuteAfterParsing.takeFirst() ; | 78 PendingScript pendingScript = m_scriptsToExecuteAfterParsing.takeFirst() ; |
63 if (pendingScript.resource() && pendingScript.watchingForLoad()) | 79 if (pendingScript.resource() && pendingScript.watchingForLoad()) |
64 stopWatchingForLoad(pendingScript); | 80 stopWatchingForLoad(pendingScript); |
65 } | 81 } |
66 } | 82 m_document = nullptr; |
67 | |
68 void HTMLScriptRunner::detach() | |
69 { | |
70 m_document = 0; | |
71 } | 83 } |
72 | 84 |
73 static KURL documentURLForScriptExecution(Document* document) | 85 static KURL documentURLForScriptExecution(Document* document) |
74 { | 86 { |
75 if (!document) | 87 if (!document) |
76 return KURL(); | 88 return KURL(); |
77 | 89 |
78 if (!document->frame()) { | 90 if (!document->frame()) { |
79 if (document->importsController()) | 91 if (document->importsController()) |
80 return document->url(); | 92 return document->url(); |
(...skipping 54 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
135 Microtask::performCheckpoint(); | 147 Microtask::performCheckpoint(); |
136 if (pendingScriptType == PendingScriptBlockingParser) { | 148 if (pendingScriptType == PendingScriptBlockingParser) { |
137 m_hasScriptsWaitingForResources = !m_document->isScriptExecutionRead y(); | 149 m_hasScriptsWaitingForResources = !m_document->isScriptExecutionRead y(); |
138 // The parser cannot be unblocked as a microtask requested another r esource | 150 // The parser cannot be unblocked as a microtask requested another r esource |
139 if (m_hasScriptsWaitingForResources) | 151 if (m_hasScriptsWaitingForResources) |
140 return; | 152 return; |
141 } | 153 } |
142 } | 154 } |
143 | 155 |
144 // Clear the pending script before possible rentrancy from executeScript() | 156 // Clear the pending script before possible rentrancy from executeScript() |
145 RefPtr<Element> element = pendingScript.releaseElementAndClear(); | 157 RefPtrWillBeRawPtr<Element> element = pendingScript.releaseElementAndClear() ; |
146 if (ScriptLoader* scriptLoader = toScriptLoaderIfPossible(element.get())) { | 158 if (ScriptLoader* scriptLoader = toScriptLoaderIfPossible(element.get())) { |
147 NestingLevelIncrementer nestingLevelIncrementer(m_scriptNestingLevel); | 159 NestingLevelIncrementer nestingLevelIncrementer(m_scriptNestingLevel); |
148 IgnoreDestructiveWriteCountIncrementer ignoreDestructiveWriteCountIncrem enter(m_document); | 160 IgnoreDestructiveWriteCountIncrementer ignoreDestructiveWriteCountIncrem enter(m_document); |
149 if (errorOccurred) | 161 if (errorOccurred) |
150 scriptLoader->dispatchErrorEvent(); | 162 scriptLoader->dispatchErrorEvent(); |
151 else { | 163 else { |
152 ASSERT(isExecutingScript()); | 164 ASSERT(isExecutingScript()); |
153 scriptLoader->executeScript(sourceCode); | 165 scriptLoader->executeScript(sourceCode); |
154 element->dispatchEvent(createScriptLoadEvent()); | 166 element->dispatchEvent(createScriptLoadEvent()); |
155 } | 167 } |
156 } | 168 } |
157 ASSERT(!isExecutingScript()); | 169 ASSERT(!isExecutingScript()); |
158 } | 170 } |
159 | 171 |
160 void HTMLScriptRunner::watchForLoad(PendingScript& pendingScript) | 172 void HTMLScriptRunner::watchForLoad(PendingScript& pendingScript) |
161 { | 173 { |
162 ASSERT(!pendingScript.watchingForLoad()); | 174 ASSERT(!pendingScript.watchingForLoad()); |
163 m_host->watchForLoad(pendingScript.resource()); | 175 ASSERT(!pendingScript.resource()->isLoaded()); |
176 // addClient() will call notifyFinished() if the load is complete. | |
177 // Callers do not expect to be re-entered from this call, so they | |
178 // should not become a client of an already-loaded Resource. | |
179 pendingScript.resource()->addClient(this); | |
164 pendingScript.setWatchingForLoad(true); | 180 pendingScript.setWatchingForLoad(true); |
165 } | 181 } |
166 | 182 |
167 void HTMLScriptRunner::stopWatchingForLoad(PendingScript& pendingScript) | 183 void HTMLScriptRunner::stopWatchingForLoad(PendingScript& pendingScript) |
168 { | 184 { |
169 ASSERT(pendingScript.watchingForLoad()); | 185 ASSERT(pendingScript.watchingForLoad()); |
170 m_host->stopWatchingForLoad(pendingScript.resource()); | 186 pendingScript.resource()->removeClient(this); |
171 pendingScript.setWatchingForLoad(false); | 187 pendingScript.setWatchingForLoad(false); |
172 } | 188 } |
173 | 189 |
190 void HTMLScriptRunner::notifyFinished(Resource* cachedResource) | |
191 { | |
192 m_host->notifyScriptLoaded(cachedResource); | |
193 } | |
194 | |
174 // Implements the steps for 'An end tag whose tag name is "script"' | 195 // Implements the steps for 'An end tag whose tag name is "script"' |
175 // http://whatwg.org/html#scriptEndTag | 196 // http://whatwg.org/html#scriptEndTag |
176 // Script handling lives outside the tree builder to keep each class simple. | 197 // Script handling lives outside the tree builder to keep each class simple. |
177 void HTMLScriptRunner::execute(PassRefPtr<Element> scriptElement, const TextPosi tion& scriptStartPosition) | 198 void HTMLScriptRunner::execute(PassRefPtrWillBeRawPtr<Element> scriptElement, co nst TextPosition& scriptStartPosition) |
178 { | 199 { |
179 ASSERT(scriptElement); | 200 ASSERT(scriptElement); |
180 // FIXME: If scripting is disabled, always just return. | 201 // FIXME: If scripting is disabled, always just return. |
181 | 202 |
182 bool hadPreloadScanner = m_host->hasPreloadScanner(); | 203 bool hadPreloadScanner = m_host->hasPreloadScanner(); |
183 | 204 |
184 // Try to execute the script given to us. | 205 // Try to execute the script given to us. |
185 runScript(scriptElement.get(), scriptStartPosition); | 206 runScript(scriptElement.get(), scriptStartPosition); |
186 | 207 |
187 if (hasParserBlockingScript()) { | 208 if (hasParserBlockingScript()) { |
(...skipping 133 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
321 } else { | 342 } else { |
322 ScriptSourceCode sourceCode(script->textContent(), documentURLFo rScriptExecution(m_document), scriptStartPosition); | 343 ScriptSourceCode sourceCode(script->textContent(), documentURLFo rScriptExecution(m_document), scriptStartPosition); |
323 scriptLoader->executeScript(sourceCode); | 344 scriptLoader->executeScript(sourceCode); |
324 } | 345 } |
325 } else { | 346 } else { |
326 requestParsingBlockingScript(script); | 347 requestParsingBlockingScript(script); |
327 } | 348 } |
328 } | 349 } |
329 } | 350 } |
330 | 351 |
352 void HTMLScriptRunner::trace(Visitor* visitor) | |
353 { | |
354 visitor->trace(m_document); | |
355 visitor->trace(m_parserBlockingScript); | |
356 visitor->trace(m_scriptsToExecuteAfterParsing); | |
331 } | 357 } |
358 | |
359 } | |
OLD | NEW |