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

Side by Side Diff: runtime/vm/compiler.cc

Issue 1433243003: Background compilation work: (Closed) Base URL: https://github.com/dart-lang/sdk.git@master
Patch Set: d Created 5 years, 1 month 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 unified diff | Download patch
« no previous file with comments | « runtime/vm/compiler.h ('k') | runtime/vm/flow_graph.h » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file 1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file
2 // for details. All rights reserved. Use of this source code is governed by a 2 // for details. All rights reserved. Use of this source code is governed by a
3 // BSD-style license that can be found in the LICENSE file. 3 // BSD-style license that can be found in the LICENSE file.
4 4
5 #include "vm/compiler.h" 5 #include "vm/compiler.h"
6 6
7 #include "vm/assembler.h" 7 #include "vm/assembler.h"
8 8
9 #include "vm/ast_printer.h" 9 #include "vm/ast_printer.h"
10 #include "vm/block_scheduler.h" 10 #include "vm/block_scheduler.h"
(...skipping 759 matching lines...) Expand 10 before | Expand all | Expand 10 after
770 graph_compiler.FinalizePcDescriptors(code); 770 graph_compiler.FinalizePcDescriptors(code);
771 code.set_deopt_info_array(deopt_info_array); 771 code.set_deopt_info_array(deopt_info_array);
772 772
773 graph_compiler.FinalizeStackmaps(code); 773 graph_compiler.FinalizeStackmaps(code);
774 graph_compiler.FinalizeVarDescriptors(code); 774 graph_compiler.FinalizeVarDescriptors(code);
775 graph_compiler.FinalizeExceptionHandlers(code); 775 graph_compiler.FinalizeExceptionHandlers(code);
776 graph_compiler.FinalizeStaticCallTargetsTable(code); 776 graph_compiler.FinalizeStaticCallTargetsTable(code);
777 777
778 if (optimized) { 778 if (optimized) {
779 if (result != NULL) { 779 if (result != NULL) {
780 // Background compilation, store compilation result in 'result'.
780 ASSERT(!Thread::Current()->IsMutatorThread()); 781 ASSERT(!Thread::Current()->IsMutatorThread());
781 // Do not install code, but return it instead. 782 // Do not install code, but return it instead.
782 // Since code dependencies (CHA, fields) are defined eagerly, 783 // Since code dependencies (CHA, fields) are defined eagerly,
783 // the code may be disabled before installing it. 784 // the code may be disabled before installing it.
784 code.set_owner(function); 785 code.set_owner(function);
785 result->set_result_code(code); 786 result->set_result_code(code);
786 // Disable invalidation counters that are not relevant. 787 // Disable invalidation counters that are not relevant.
787 if (thread->cha()->leaf_classes().is_empty()) { 788 if (thread->cha()->leaf_classes().is_empty()) {
788 result->ClearCHAInvalidationGen(); 789 result->ClearCHAInvalidationGen();
789 } 790 }
790 if (flow_graph->guarded_fields()->is_empty()) { 791 if (flow_graph->guarded_fields()->is_empty()) {
791 result->ClearFieldInvalidationGen(); 792 result->ClearFieldInvalidationGen();
792 } 793 }
793 if (!parsed_function->HasDeferredPrefixes()) { 794 if (!parsed_function->HasDeferredPrefixes()) {
794 result->ClearPrefixInvalidationGen(); 795 result->ClearPrefixInvalidationGen();
795 } 796 }
796 } else { 797 } else {
797 const bool is_osr = osr_id != Compiler::kNoOSRDeoptId; 798 const bool is_osr = osr_id != Compiler::kNoOSRDeoptId;
798 function.InstallOptimizedCode(code, is_osr); 799 function.InstallOptimizedCode(code, is_osr);
799 } 800 }
800 801
801 // TODO(srdjan): In background compilation, verify that CHA and field
802 // guards have not been invalidated in the meantime.
803 // Register code with the classes it depends on because of CHA and 802 // Register code with the classes it depends on because of CHA and
804 // fields it depends on because of store guards, unless we cannot 803 // fields it depends on because of store guards, unless we cannot
805 // deopt. 804 // deopt.
806 if (Compiler::allow_recompilation()) { 805 if (Compiler::allow_recompilation()) {
807 for (intptr_t i = 0; 806 if (result != NULL) {
808 i < thread->cha()->leaf_classes().length(); 807 // Background compilation: delay registering code until we are
809 ++i) { 808 // in the MutatorThread.
810 thread->cha()->leaf_classes()[i]->RegisterCHACode(code); 809 result->SetLeafClasses(thread->cha()->leaf_classes());
811 } 810 result->SetGuardedFields(*flow_graph->guarded_fields());
812 for (intptr_t i = 0; 811 result->SetDeoptimizeDependentFields(
813 i < flow_graph->guarded_fields()->length(); 812 flow_graph->deoptimize_dependent_code());
814 i++) { 813 } else {
815 const Field* field = (*flow_graph->guarded_fields())[i]; 814 for (intptr_t i = 0;
816 field->RegisterDependentCode(code); 815 i < thread->cha()->leaf_classes().length();
816 ++i) {
817 thread->cha()->leaf_classes()[i]->RegisterCHACode(code);
818 }
819 for (intptr_t i = 0;
820 i < flow_graph->guarded_fields()->length();
821 i++) {
822 const Field* field = (*flow_graph->guarded_fields())[i];
823 field->RegisterDependentCode(code);
824 }
825 for (intptr_t i = 0;
826 i < flow_graph->deoptimize_dependent_code().length();
827 i++) {
828 const Field* field = flow_graph->deoptimize_dependent_code()[i];
829 field->DeoptimizeDependentCode();
830 }
817 } 831 }
818 } 832 }
819 } else { // not optimized. 833 } else { // not optimized.
820 if (!Compiler::always_optimize() && 834 if (!Compiler::always_optimize() &&
821 (function.ic_data_array() == Array::null())) { 835 (function.ic_data_array() == Array::null())) {
822 function.SaveICDataMap( 836 function.SaveICDataMap(
823 graph_compiler.deopt_id_to_ic_data(), 837 graph_compiler.deopt_id_to_ic_data(),
824 Array::Handle(zone, graph_compiler.edge_counters_array())); 838 Array::Handle(zone, graph_compiler.edge_counters_array()));
825 } 839 }
826 function.set_unoptimized_code(code); 840 function.set_unoptimized_code(code);
(...skipping 647 matching lines...) Expand 10 before | Expand all | Expand 10 after
1474 return Object::null(); 1488 return Object::null();
1475 } 1489 }
1476 1490
1477 1491
1478 // C-heap allocated background compilation queue element. 1492 // C-heap allocated background compilation queue element.
1479 class QueueElement { 1493 class QueueElement {
1480 public: 1494 public:
1481 explicit QueueElement(const Function& function) 1495 explicit QueueElement(const Function& function)
1482 : next_(NULL), 1496 : next_(NULL),
1483 obj_(function.raw()), 1497 obj_(function.raw()),
1498 leaf_classes_(Array::null()),
1499 guarded_fields_(Array::null()),
1500 deoptimize_dependent_fields_(Array::null()),
1484 cha_invalidation_gen_(Isolate::kInvalidGen), 1501 cha_invalidation_gen_(Isolate::kInvalidGen),
1485 field_invalidation_gen_(Isolate::kInvalidGen), 1502 field_invalidation_gen_(Isolate::kInvalidGen),
1486 prefix_invalidation_gen_(Isolate::kInvalidGen) { 1503 prefix_invalidation_gen_(Isolate::kInvalidGen) {
1487 ASSERT(Thread::Current()->IsMutatorThread()); 1504 ASSERT(Thread::Current()->IsMutatorThread());
1488 } 1505 }
1489 1506
1490 ~QueueElement() { 1507 ~QueueElement() {
1491 ASSERT(Thread::Current()->IsMutatorThread()); 1508 ASSERT(Thread::Current()->IsMutatorThread());
1492 obj_ = Object::null(); 1509 obj_ = Object::null();
1493 } 1510 }
1494 1511
1495 RawFunction* Function() const { return Function::RawCast(obj_); } 1512 RawFunction* Function() const { return Function::RawCast(obj_); }
1496 RawCode* Code() const { return Code::RawCast(obj_); } 1513 RawCode* Code() const { return Code::RawCast(obj_); }
1497 1514
1515 RawArray* leaf_classes() const { return leaf_classes_; }
1516 RawArray* guarded_fields() const { return guarded_fields_; }
1517 RawArray* deoptimize_dependent_fields() const {
1518 return deoptimize_dependent_fields_;
1519 }
1520
1498 uint32_t cha_invalidation_gen() const { return cha_invalidation_gen_; } 1521 uint32_t cha_invalidation_gen() const { return cha_invalidation_gen_; }
1499 uint32_t field_invalidation_gen() const { return field_invalidation_gen_; } 1522 uint32_t field_invalidation_gen() const { return field_invalidation_gen_; }
1500 uint32_t prefix_invalidation_gen() const { return prefix_invalidation_gen_; } 1523 uint32_t prefix_invalidation_gen() const { return prefix_invalidation_gen_; }
1501 1524
1502 void set_next(QueueElement* elem) { next_ = elem; } 1525 void set_next(QueueElement* elem) { next_ = elem; }
1503 QueueElement* next() const { return next_; } 1526 QueueElement* next() const { return next_; }
1504 1527
1528 RawObject* obj() const { return obj_; }
1505 RawObject** obj_ptr() { return &obj_; } 1529 RawObject** obj_ptr() { return &obj_; }
1506 RawObject* obj() const { return obj_; } 1530
1531 RawObject** leaf_classses_ptr() {
1532 return reinterpret_cast<RawObject**>(&leaf_classes_);
1533 }
1534
1535 RawObject** guarded_fields_ptr() {
1536 return reinterpret_cast<RawObject**>(&guarded_fields_);
1537 }
1538
1539 RawObject** deoptimize_dependent_fields_ptr() {
1540 return reinterpret_cast<RawObject**>(&deoptimize_dependent_fields_);
1541 }
1507 1542
1508 void SetFromResult(const BackgroundCompilationResult& value) { 1543 void SetFromResult(const BackgroundCompilationResult& value) {
1509 ASSERT(!value.result_code().IsNull()); 1544 ASSERT(!value.result_code().IsNull());
1510 obj_ = value.result_code().raw(); 1545 obj_ = value.result_code().raw();
1546 leaf_classes_ = value.leaf_classes().raw();
1547 guarded_fields_ = value.guarded_fields().raw();
1548 deoptimize_dependent_fields_ = value.deoptimize_dependent_fields().raw();
1511 cha_invalidation_gen_ = value.cha_invalidation_gen(); 1549 cha_invalidation_gen_ = value.cha_invalidation_gen();
1512 field_invalidation_gen_ = value.field_invalidation_gen(); 1550 field_invalidation_gen_ = value.field_invalidation_gen();
1513 prefix_invalidation_gen_ = value.prefix_invalidation_gen(); 1551 prefix_invalidation_gen_ = value.prefix_invalidation_gen();
1514 } 1552 }
1515 1553
1516 private: 1554 private:
1517 QueueElement* next_; 1555 QueueElement* next_;
1518 1556
1519 RawObject* obj_; // Code or Function. 1557 RawObject* obj_; // Code or Function.
1558 RawArray* leaf_classes_;
1559 RawArray* guarded_fields_;
1560 RawArray* deoptimize_dependent_fields_;
1520 uint32_t cha_invalidation_gen_; 1561 uint32_t cha_invalidation_gen_;
1521 uint32_t field_invalidation_gen_; 1562 uint32_t field_invalidation_gen_;
1522 uint32_t prefix_invalidation_gen_; 1563 uint32_t prefix_invalidation_gen_;
1523 1564
1524 DISALLOW_COPY_AND_ASSIGN(QueueElement); 1565 DISALLOW_COPY_AND_ASSIGN(QueueElement);
1525 }; 1566 };
1526 1567
1527 1568
1528 // Allocated in C-heap. Handles both input and output of background compilation. 1569 // Allocated in C-heap. Handles both input and output of background compilation.
1529 // It implements a FIFO queue, using Peek, Add, Remove operations. 1570 // It implements a FIFO queue, using Peek, Add, Remove operations.
1530 class BackgroundCompilationQueue { 1571 class BackgroundCompilationQueue {
1531 public: 1572 public:
1532 BackgroundCompilationQueue() : first_(NULL), last_(NULL) {} 1573 BackgroundCompilationQueue() : first_(NULL), last_(NULL) {}
1533 ~BackgroundCompilationQueue() { 1574 ~BackgroundCompilationQueue() {
1534 while (!IsEmpty()) { 1575 while (!IsEmpty()) {
1535 QueueElement* e = Remove(); 1576 QueueElement* e = Remove();
1536 delete e; 1577 delete e;
1537 } 1578 }
1538 ASSERT((first_ == NULL) && (last_ == NULL)); 1579 ASSERT((first_ == NULL) && (last_ == NULL));
1539 } 1580 }
1540 1581
1541 void VisitObjectPointers(ObjectPointerVisitor* visitor) { 1582 void VisitObjectPointers(ObjectPointerVisitor* visitor) {
1542 ASSERT(visitor != NULL); 1583 ASSERT(visitor != NULL);
1543 QueueElement* p = first_; 1584 QueueElement* p = first_;
1544 while (p != NULL) { 1585 while (p != NULL) {
1545 visitor->VisitPointer(p->obj_ptr()); 1586 visitor->VisitPointer(p->obj_ptr());
1587 visitor->VisitPointer(p->leaf_classses_ptr());
1588 visitor->VisitPointer(p->guarded_fields_ptr());
1589 visitor->VisitPointer(p->deoptimize_dependent_fields_ptr());
1546 p = p->next(); 1590 p = p->next();
1547 } 1591 }
1548 } 1592 }
1549 1593
1550 bool IsEmpty() const { return first_ == NULL; } 1594 bool IsEmpty() const { return first_ == NULL; }
1551 1595
1552 void Add(QueueElement* value) { 1596 void Add(QueueElement* value) {
1553 ASSERT(value != NULL); 1597 ASSERT(value != NULL);
1554 if (first_ == NULL) { 1598 if (first_ == NULL) {
1555 first_ = value; 1599 first_ = value;
(...skipping 41 matching lines...) Expand 10 before | Expand all | Expand 10 after
1597 private: 1641 private:
1598 QueueElement* first_; 1642 QueueElement* first_;
1599 QueueElement* last_; 1643 QueueElement* last_;
1600 1644
1601 DISALLOW_COPY_AND_ASSIGN(BackgroundCompilationQueue); 1645 DISALLOW_COPY_AND_ASSIGN(BackgroundCompilationQueue);
1602 }; 1646 };
1603 1647
1604 1648
1605 BackgroundCompilationResult::BackgroundCompilationResult() 1649 BackgroundCompilationResult::BackgroundCompilationResult()
1606 : result_code_(Code::Handle()), 1650 : result_code_(Code::Handle()),
1651 leaf_classes_(Array::Handle()),
1652 guarded_fields_(Array::Handle()),
1653 deoptimize_dependent_fields_(Array::Handle()),
1607 cha_invalidation_gen_(Isolate::kInvalidGen), 1654 cha_invalidation_gen_(Isolate::kInvalidGen),
1608 field_invalidation_gen_(Isolate::kInvalidGen), 1655 field_invalidation_gen_(Isolate::kInvalidGen),
1609 prefix_invalidation_gen_(Isolate::kInvalidGen) { 1656 prefix_invalidation_gen_(Isolate::kInvalidGen) {
1610 } 1657 }
1611 1658
1612 1659
1613 void BackgroundCompilationResult::Init() { 1660 void BackgroundCompilationResult::Init() {
1614 Isolate* i = Isolate::Current(); 1661 Isolate* i = Isolate::Current();
1615 result_code_ = Code::null(); 1662 result_code_ = Code::null();
1663 leaf_classes_ = Array::null();
1664 guarded_fields_ = Array::null();
1665 deoptimize_dependent_fields_ = Array::null();
1616 cha_invalidation_gen_ = i->cha_invalidation_gen(); 1666 cha_invalidation_gen_ = i->cha_invalidation_gen();
1617 field_invalidation_gen_ = i->field_invalidation_gen(); 1667 field_invalidation_gen_ = i->field_invalidation_gen();
1618 prefix_invalidation_gen_ = i->prefix_invalidation_gen(); 1668 prefix_invalidation_gen_ = i->prefix_invalidation_gen();
1619 } 1669 }
1620 1670
1621 1671
1622 void BackgroundCompilationResult::SetFromQElement(QueueElement* value) { 1672 void BackgroundCompilationResult::SetFromQElement(QueueElement* value) {
1623 ASSERT(value != NULL); 1673 ASSERT(value != NULL);
1624 result_code_ = value->Code(); 1674 result_code_ = value->Code();
1675 leaf_classes_ = value->leaf_classes();
1676 guarded_fields_ = value->guarded_fields();
1677 deoptimize_dependent_fields_ = value->deoptimize_dependent_fields();
1625 cha_invalidation_gen_ = value->cha_invalidation_gen(); 1678 cha_invalidation_gen_ = value->cha_invalidation_gen();
1626 field_invalidation_gen_ = value->field_invalidation_gen(); 1679 field_invalidation_gen_ = value->field_invalidation_gen();
1627 prefix_invalidation_gen_ = value->prefix_invalidation_gen(); 1680 prefix_invalidation_gen_ = value->prefix_invalidation_gen();
1628 } 1681 }
1629 1682
1630 1683
1684 void BackgroundCompilationResult::SetLeafClasses(
1685 const GrowableArray<Class*>& leaf_classes) {
1686 const Array& a = Array::Handle(Array::New(leaf_classes.length(), Heap::kOld));
1687 for (intptr_t i = 0; i < leaf_classes.length(); i++) {
1688 a.SetAt(i, *leaf_classes[i]);
1689 }
1690 leaf_classes_ = a.raw();
1691 }
1692
1693
1694 void BackgroundCompilationResult::SetGuardedFields(
1695 const ZoneGrowableArray<const Field*>& guarded_fields) {
1696 const Array& a =
1697 Array::Handle(Array::New(guarded_fields.length(), Heap::kOld));
1698 for (intptr_t i = 0; i < guarded_fields.length(); i++) {
1699 a.SetAt(i, *guarded_fields[i]);
1700 }
1701 guarded_fields_ = a.raw();
1702 }
1703
1704
1705 void BackgroundCompilationResult::SetDeoptimizeDependentFields(
1706 const GrowableArray<const Field*>& fields) {
1707 const Array& a = Array::Handle(Array::New(fields.length(), Heap::kOld));
1708 for (intptr_t i = 0; i < fields.length(); i++) {
1709 a.SetAt(i, *fields[i]);
1710 }
1711 deoptimize_dependent_fields_ = a.raw();
1712 }
1713
1714
1631 bool BackgroundCompilationResult::IsValid() const { 1715 bool BackgroundCompilationResult::IsValid() const {
1632 if (result_code().IsNull() || result_code().IsDisabled()) { 1716 if (result_code().IsNull() || result_code().IsDisabled()) {
1633 return false; 1717 return false;
1634 } 1718 }
1635 Isolate* i = Isolate::Current(); 1719 Isolate* i = Isolate::Current();
1636 if ((cha_invalidation_gen_ != Isolate::kInvalidGen) && 1720 if ((cha_invalidation_gen_ != Isolate::kInvalidGen) &&
1637 (cha_invalidation_gen_ != i->cha_invalidation_gen())) { 1721 (cha_invalidation_gen_ != i->cha_invalidation_gen())) {
1638 return false; 1722 return false;
1639 } 1723 }
1640 if ((field_invalidation_gen_ != Isolate::kInvalidGen) && 1724 if ((field_invalidation_gen_ != Isolate::kInvalidGen) &&
(...skipping 108 matching lines...) Expand 10 before | Expand all | Expand 10 after
1749 } 1833 }
1750 QueueElement* elem = new QueueElement(function); 1834 QueueElement* elem = new QueueElement(function);
1751 function_queue()->Add(elem); 1835 function_queue()->Add(elem);
1752 ml.Notify(); 1836 ml.Notify();
1753 } 1837 }
1754 1838
1755 1839
1756 void BackgroundCompiler::InstallGeneratedCode() { 1840 void BackgroundCompiler::InstallGeneratedCode() {
1757 ASSERT(Thread::Current()->IsMutatorThread()); 1841 ASSERT(Thread::Current()->IsMutatorThread());
1758 MonitorLocker ml(queue_monitor_); 1842 MonitorLocker ml(queue_monitor_);
1759 Object& owner = Object::Handle(); 1843 Function& function = Function::Handle();
1760 while (result_queue()->Peek() != NULL) { 1844 while (result_queue()->Peek() != NULL) {
1761 BackgroundCompilationResult result; 1845 BackgroundCompilationResult result;
1762 QueueElement* elem = result_queue()->Remove(); 1846 QueueElement* elem = result_queue()->Remove();
1763 ASSERT(elem != NULL); 1847 ASSERT(elem != NULL);
1764 result.SetFromQElement(elem); 1848 result.SetFromQElement(elem);
1765 delete elem; 1849 delete elem;
1766 1850
1767 owner = result.result_code().owner(); 1851 const Code& code = result.result_code();
1768 const Function& function = Function::Cast(owner); 1852 function ^= code.owner();
1769 if (result.IsValid()) { 1853 if (result.IsValid()) {
1770 function.InstallOptimizedCode(result.result_code(), false /* not OSR */); 1854 function.InstallOptimizedCode(result.result_code(), false /* not OSR */);
1855 // Install leaf classes and fields dependencies.
1856 Class& cls = Class::Handle();
1857 for (intptr_t i = 0; i < result.leaf_classes().Length(); i++) {
1858 cls ^= result.leaf_classes().At(i);
1859 cls.RegisterCHACode(code);
1860 }
1861 Field& field = Field::Handle();
1862 for (intptr_t i = 0; i < result.guarded_fields().Length(); i++) {
1863 field ^= result.guarded_fields().At(i);
1864 field.RegisterDependentCode(code);
1865 }
1866 for (intptr_t i = 0; i < result.deoptimize_dependent_fields().Length();
1867 i++) {
1868 field ^= result.deoptimize_dependent_fields().At(i);
1869 field.DeoptimizeDependentCode();
1870 }
1771 } else if (FLAG_trace_compiler) { 1871 } else if (FLAG_trace_compiler) {
1772 THR_Print("Drop code generated in the background compiler:\n"); 1872 THR_Print("Drop code generated in the background compiler:\n");
1773 result.PrintValidity(); 1873 result.PrintValidity();
1774 } 1874 }
1775 if (function.usage_counter() < 0) { 1875 if (function.usage_counter() < 0) {
1776 // Reset to 0 so that it can be recompiled if needed. 1876 // Reset to 0 so that it can be recompiled if needed.
1777 function.set_usage_counter(0); 1877 function.set_usage_counter(0);
1778 } 1878 }
1779 } 1879 }
1780 } 1880 }
(...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after
1815 delete task_done; 1915 delete task_done;
1816 delete done_monitor; 1916 delete done_monitor;
1817 delete queue_monitor; 1917 delete queue_monitor;
1818 delete function_queue; 1918 delete function_queue;
1819 delete result_queue; 1919 delete result_queue;
1820 Isolate::Current()->set_background_compiler(NULL); 1920 Isolate::Current()->set_background_compiler(NULL);
1821 } 1921 }
1822 1922
1823 1923
1824 void BackgroundCompiler::EnsureInit(Thread* thread) { 1924 void BackgroundCompiler::EnsureInit(Thread* thread) {
1925 ASSERT(thread->IsMutatorThread());
1926 // Finalize NoSuchMethodError, _Mint; occasionally needed in optimized
1927 // compilation.
1928 Class& cls = Class::Handle(thread->zone(),
1929 Library::LookupCoreClass(Symbols::NoSuchMethodError()));
1930 Error& error = Error::Handle(thread->zone(),
1931 cls.EnsureIsFinalized(thread));
1932 ASSERT(error.IsNull());
1933 cls = Library::LookupCoreClass(Symbols::_Mint());
1934 error = cls.EnsureIsFinalized(thread);
1935 ASSERT(error.IsNull());
1936
1825 bool start_task = false; 1937 bool start_task = false;
1826 Isolate* isolate = thread->isolate(); 1938 Isolate* isolate = thread->isolate();
1827 { 1939 {
1828 MutexLocker ml(isolate->mutex()); 1940 MutexLocker ml(isolate->mutex());
1829 if (isolate->background_compiler() == NULL) { 1941 if (isolate->background_compiler() == NULL) {
1830 BackgroundCompiler* task = new BackgroundCompiler(isolate); 1942 BackgroundCompiler* task = new BackgroundCompiler(isolate);
1831 isolate->set_background_compiler(task); 1943 isolate->set_background_compiler(task);
1832 start_task = true; 1944 start_task = true;
1833 } 1945 }
1834 } 1946 }
1835 if (start_task) { 1947 if (start_task) {
1836 Dart::thread_pool()->Run(isolate->background_compiler()); 1948 Dart::thread_pool()->Run(isolate->background_compiler());
1837 } 1949 }
1838 } 1950 }
1839 1951
1840 } // namespace dart 1952 } // namespace dart
OLDNEW
« no previous file with comments | « runtime/vm/compiler.h ('k') | runtime/vm/flow_graph.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698