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 420 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
431 } | 431 } |
432 PendingScript* first = m_scriptsToExecuteAfterParsing.takeFirst(); | 432 PendingScript* first = m_scriptsToExecuteAfterParsing.takeFirst(); |
433 executePendingScriptAndDispatchEvent(first, ScriptStreamer::Deferred); | 433 executePendingScriptAndDispatchEvent(first, ScriptStreamer::Deferred); |
434 // FIXME: What is this m_document check for? | 434 // FIXME: What is this m_document check for? |
435 if (!m_document) | 435 if (!m_document) |
436 return false; | 436 return false; |
437 } | 437 } |
438 return true; | 438 return true; |
439 } | 439 } |
440 | 440 |
| 441 // 2nd Clause, Step 23 of https://html.spec.whatwg.org/#prepare-a-script |
441 void HTMLParserScriptRunner::requestParsingBlockingScript(Element* element) { | 442 void HTMLParserScriptRunner::requestParsingBlockingScript(Element* element) { |
| 443 // "The element is the pending parsing-blocking script of the Document of |
| 444 // the parser that created the element. |
| 445 // (There can only be one such script per Document at a time.)" |
442 if (!requestPendingScript(m_parserBlockingScript.get(), element)) | 446 if (!requestPendingScript(m_parserBlockingScript.get(), element)) |
443 return; | 447 return; |
444 | 448 |
445 DCHECK(m_parserBlockingScript->resource()); | 449 DCHECK(m_parserBlockingScript->resource()); |
446 | 450 |
447 // We only care about a load callback if resource is not already in the cache. | 451 // We only care about a load callback if resource is not already in the cache. |
448 // Callers will attempt to run the m_parserBlockingScript if possible before | 452 // Callers will attempt to run the m_parserBlockingScript if possible before |
449 // returning control to the parser. | 453 // returning control to the parser. |
450 if (!m_parserBlockingScript->isReady()) { | 454 if (!m_parserBlockingScript->isReady()) { |
451 if (m_document->frame()) { | 455 if (m_document->frame()) { |
452 ScriptState* scriptState = ScriptState::forMainWorld(m_document->frame()); | 456 ScriptState* scriptState = ScriptState::forMainWorld(m_document->frame()); |
453 if (scriptState) { | 457 if (scriptState) { |
454 ScriptStreamer::startStreaming( | 458 ScriptStreamer::startStreaming( |
455 m_parserBlockingScript.get(), ScriptStreamer::ParsingBlocking, | 459 m_parserBlockingScript.get(), ScriptStreamer::ParsingBlocking, |
456 m_document->frame()->settings(), scriptState, | 460 m_document->frame()->settings(), scriptState, |
457 TaskRunnerHelper::get(TaskType::Networking, m_document)); | 461 TaskRunnerHelper::get(TaskType::Networking, m_document)); |
458 } | 462 } |
459 } | 463 } |
460 | 464 |
461 m_parserBlockingScript->watchForLoad(this); | 465 m_parserBlockingScript->watchForLoad(this); |
462 } | 466 } |
463 } | 467 } |
464 | 468 |
| 469 // 1st Clause, Step 23 of https://html.spec.whatwg.org/#prepare-a-script |
465 void HTMLParserScriptRunner::requestDeferredScript(Element* element) { | 470 void HTMLParserScriptRunner::requestDeferredScript(Element* element) { |
466 PendingScript* pendingScript = PendingScript::create(nullptr, nullptr); | 471 PendingScript* pendingScript = PendingScript::create(nullptr, nullptr); |
467 if (!requestPendingScript(pendingScript, element)) | 472 if (!requestPendingScript(pendingScript, element)) |
468 return; | 473 return; |
469 | 474 |
470 if (m_document->frame() && !pendingScript->isReady()) { | 475 if (m_document->frame() && !pendingScript->isReady()) { |
471 ScriptState* scriptState = ScriptState::forMainWorld(m_document->frame()); | 476 ScriptState* scriptState = ScriptState::forMainWorld(m_document->frame()); |
472 if (scriptState) { | 477 if (scriptState) { |
473 ScriptStreamer::startStreaming( | 478 ScriptStreamer::startStreaming( |
474 pendingScript, ScriptStreamer::Deferred, | 479 pendingScript, ScriptStreamer::Deferred, |
475 m_document->frame()->settings(), scriptState, | 480 m_document->frame()->settings(), scriptState, |
476 TaskRunnerHelper::get(TaskType::Networking, m_document)); | 481 TaskRunnerHelper::get(TaskType::Networking, m_document)); |
477 } | 482 } |
478 } | 483 } |
479 | 484 |
480 DCHECK(pendingScript->resource()); | 485 DCHECK(pendingScript->resource()); |
| 486 |
| 487 // "Add the element to the end of the list of scripts that will execute |
| 488 // when the document has finished parsing associated with the Document |
| 489 // of the parser that created the element." |
481 m_scriptsToExecuteAfterParsing.append(pendingScript); | 490 m_scriptsToExecuteAfterParsing.append(pendingScript); |
482 } | 491 } |
483 | 492 |
484 bool HTMLParserScriptRunner::requestPendingScript(PendingScript* pendingScript, | 493 bool HTMLParserScriptRunner::requestPendingScript(PendingScript* pendingScript, |
485 Element* script) const { | 494 Element* script) const { |
486 DCHECK(!pendingScript->element()); | 495 DCHECK(!pendingScript->element()); |
487 pendingScript->setElement(script); | 496 pendingScript->setElement(script); |
488 // This should correctly return 0 for empty or invalid srcValues. | 497 // This should correctly return 0 for empty or invalid srcValues. |
489 ScriptResource* resource = toScriptLoaderIfPossible(script)->resource(); | 498 ScriptResource* resource = toScriptLoaderIfPossible(script)->resource(); |
490 if (!resource) { | 499 if (!resource) { |
(...skipping 27 matching lines...) Expand all Loading... |
518 if (!isExecutingScript()) | 527 if (!isExecutingScript()) |
519 Microtask::performCheckpoint(V8PerIsolateData::mainThreadIsolate()); | 528 Microtask::performCheckpoint(V8PerIsolateData::mainThreadIsolate()); |
520 | 529 |
521 InsertionPointRecord insertionPointRecord(m_host->inputStream()); | 530 InsertionPointRecord insertionPointRecord(m_host->inputStream()); |
522 HTMLParserReentryPermit::ScriptNestingLevelIncrementer | 531 HTMLParserReentryPermit::ScriptNestingLevelIncrementer |
523 nestingLevelIncrementer = | 532 nestingLevelIncrementer = |
524 m_reentryPermit->incrementScriptNestingLevel(); | 533 m_reentryPermit->incrementScriptNestingLevel(); |
525 | 534 |
526 scriptLoader->prepareScript(scriptStartPosition); | 535 scriptLoader->prepareScript(scriptStartPosition); |
527 | 536 |
| 537 // A part of Step 23 of https://html.spec.whatwg.org/#prepare-a-script: |
528 if (!scriptLoader->willBeParserExecuted()) | 538 if (!scriptLoader->willBeParserExecuted()) |
529 return; | 539 return; |
530 | 540 |
531 if (scriptLoader->willExecuteWhenDocumentFinishedParsing()) { | 541 if (scriptLoader->willExecuteWhenDocumentFinishedParsing()) { |
| 542 // 1st Clause of Step 23. |
532 requestDeferredScript(script); | 543 requestDeferredScript(script); |
533 } else if (scriptLoader->readyToBeParserExecuted()) { | 544 } else if (scriptLoader->readyToBeParserExecuted()) { |
| 545 // 5th Clause of Step 23. |
| 546 // "If ... it's an HTML parser |
| 547 // whose script nesting level is not greater than one" |
534 if (m_reentryPermit->scriptNestingLevel() == 1u) { | 548 if (m_reentryPermit->scriptNestingLevel() == 1u) { |
| 549 // "The element is the pending parsing-blocking script of the |
| 550 // Document of the parser that created the element. |
| 551 // (There can only be one such script per Document at a time.)" |
535 m_parserBlockingScript->setElement(script); | 552 m_parserBlockingScript->setElement(script); |
536 m_parserBlockingScript->setStartingPosition(scriptStartPosition); | 553 m_parserBlockingScript->setStartingPosition(scriptStartPosition); |
537 } else { | 554 } else { |
| 555 // 6th Clause of Step 23. |
| 556 // "Immediately execute the script block, |
| 557 // even if other scripts are already executing." |
| 558 // TODO(hiroshige): Merge the block into ScriptLoader::prepareScript(). |
538 DCHECK_GT(m_reentryPermit->scriptNestingLevel(), 1u); | 559 DCHECK_GT(m_reentryPermit->scriptNestingLevel(), 1u); |
539 m_parserBlockingScript->dispose(); | 560 m_parserBlockingScript->dispose(); |
540 ScriptSourceCode sourceCode(script->textContent(), | 561 ScriptSourceCode sourceCode(script->textContent(), |
541 documentURLForScriptExecution(m_document), | 562 documentURLForScriptExecution(m_document), |
542 scriptStartPosition); | 563 scriptStartPosition); |
543 doExecuteScript(script, sourceCode, scriptStartPosition); | 564 doExecuteScript(script, sourceCode, scriptStartPosition); |
544 } | 565 } |
545 } else { | 566 } else { |
| 567 // 2nd Clause of Step 23. |
546 requestParsingBlockingScript(script); | 568 requestParsingBlockingScript(script); |
547 } | 569 } |
548 } | 570 } |
549 } | 571 } |
550 | 572 |
551 DEFINE_TRACE(HTMLParserScriptRunner) { | 573 DEFINE_TRACE(HTMLParserScriptRunner) { |
552 visitor->trace(m_document); | 574 visitor->trace(m_document); |
553 visitor->trace(m_host); | 575 visitor->trace(m_host); |
554 visitor->trace(m_parserBlockingScript); | 576 visitor->trace(m_parserBlockingScript); |
555 visitor->trace(m_scriptsToExecuteAfterParsing); | 577 visitor->trace(m_scriptsToExecuteAfterParsing); |
556 PendingScriptClient::trace(visitor); | 578 PendingScriptClient::trace(visitor); |
557 } | 579 } |
558 | 580 |
559 } // namespace blink | 581 } // namespace blink |
OLD | NEW |