OLD | NEW |
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 191 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
202 const String& script_url = String::Handle(script.url()); | 202 const String& script_url = String::Handle(script.url()); |
203 // TODO(iposva): Extract script kind. | 203 // TODO(iposva): Extract script kind. |
204 THR_Print("Compiling %s '%s'\n", "", script_url.ToCString()); | 204 THR_Print("Compiling %s '%s'\n", "", script_url.ToCString()); |
205 } | 205 } |
206 const String& library_key = String::Handle(library.private_key()); | 206 const String& library_key = String::Handle(library.private_key()); |
207 script.Tokenize(library_key); | 207 script.Tokenize(library_key); |
208 Parser::ParseCompilationUnit(library, script); | 208 Parser::ParseCompilationUnit(library, script); |
209 return Error::null(); | 209 return Error::null(); |
210 } else { | 210 } else { |
211 Thread* const thread = Thread::Current(); | 211 Thread* const thread = Thread::Current(); |
212 Isolate* const isolate = thread->isolate(); | |
213 StackZone zone(thread); | 212 StackZone zone(thread); |
214 Error& error = Error::Handle(); | 213 Error& error = Error::Handle(); |
215 error = isolate->object_store()->sticky_error(); | 214 error = thread->sticky_error(); |
216 isolate->object_store()->clear_sticky_error(); | 215 thread->clear_sticky_error(); |
217 return error.raw(); | 216 return error.raw(); |
218 } | 217 } |
219 UNREACHABLE(); | 218 UNREACHABLE(); |
220 return Error::null(); | 219 return Error::null(); |
221 } | 220 } |
222 | 221 |
223 | 222 |
224 static void AddRelatedClassesToList( | 223 static void AddRelatedClassesToList( |
225 const Class& cls, | 224 const Class& cls, |
226 GrowableHandlePtrArray<const Class>* parse_list, | 225 GrowableHandlePtrArray<const Class>* parse_list, |
(...skipping 58 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
285 const Class& closure_cls = Class::Handle( | 284 const Class& closure_cls = Class::Handle( |
286 Isolate::Current()->object_store()->closure_class()); | 285 Isolate::Current()->object_store()->closure_class()); |
287 ASSERT(closure_cls.is_finalized()); | 286 ASSERT(closure_cls.is_finalized()); |
288 #endif | 287 #endif |
289 LongJumpScope jump; | 288 LongJumpScope jump; |
290 if (setjmp(*jump.Set()) == 0) { | 289 if (setjmp(*jump.Set()) == 0) { |
291 ClassFinalizer::FinalizeClass(cls); | 290 ClassFinalizer::FinalizeClass(cls); |
292 return Error::null(); | 291 return Error::null(); |
293 } else { | 292 } else { |
294 Thread* thread = Thread::Current(); | 293 Thread* thread = Thread::Current(); |
295 Isolate* isolate = thread->isolate(); | |
296 Error& error = Error::Handle(thread->zone()); | 294 Error& error = Error::Handle(thread->zone()); |
297 error = isolate->object_store()->sticky_error(); | 295 error = thread->sticky_error(); |
298 isolate->object_store()->clear_sticky_error(); | 296 thread->clear_sticky_error(); |
299 return error.raw(); | 297 return error.raw(); |
300 } | 298 } |
301 } | 299 } |
302 | 300 |
303 Thread* const thread = Thread::Current(); | 301 Thread* const thread = Thread::Current(); |
304 Isolate* const isolate = thread->isolate(); | |
305 StackZone zone(thread); | 302 StackZone zone(thread); |
306 // We remember all the classes that are being compiled in these lists. This | 303 // We remember all the classes that are being compiled in these lists. This |
307 // also allows us to reset the marked_for_parsing state in case we see an | 304 // also allows us to reset the marked_for_parsing state in case we see an |
308 // error. | 305 // error. |
309 VMTagScope tagScope(thread, VMTag::kCompileClassTagId); | 306 VMTagScope tagScope(thread, VMTag::kCompileClassTagId); |
310 TimelineDurationScope tds(thread, | 307 TimelineDurationScope tds(thread, |
311 thread->isolate()->GetCompilerStream(), | 308 thread->isolate()->GetCompilerStream(), |
312 "CompileClass"); | 309 "CompileClass"); |
313 if (tds.enabled()) { | 310 if (tds.enabled()) { |
314 tds.SetNumArguments(1); | 311 tds.SetNumArguments(1); |
(...skipping 63 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
378 parse_class.reset_is_marked_for_parsing(); | 375 parse_class.reset_is_marked_for_parsing(); |
379 } | 376 } |
380 } | 377 } |
381 for (intptr_t i = 0; i < patch_list.length(); i++) { | 378 for (intptr_t i = 0; i < patch_list.length(); i++) { |
382 const Class& parse_class = patch_list.At(i); | 379 const Class& parse_class = patch_list.At(i); |
383 if (parse_class.is_marked_for_parsing()) { | 380 if (parse_class.is_marked_for_parsing()) { |
384 parse_class.reset_is_marked_for_parsing(); | 381 parse_class.reset_is_marked_for_parsing(); |
385 } | 382 } |
386 } | 383 } |
387 Error& error = Error::Handle(zone.GetZone()); | 384 Error& error = Error::Handle(zone.GetZone()); |
388 error = isolate->object_store()->sticky_error(); | 385 error = thread->sticky_error(); |
389 isolate->object_store()->clear_sticky_error(); | 386 thread->clear_sticky_error(); |
390 return error.raw(); | 387 return error.raw(); |
391 } | 388 } |
392 UNREACHABLE(); | 389 UNREACHABLE(); |
393 return Error::null(); | 390 return Error::null(); |
394 } | 391 } |
395 | 392 |
396 | 393 |
397 class CompileParsedFunctionHelper : public ValueObject { | 394 class CompileParsedFunctionHelper : public ValueObject { |
398 public: | 395 public: |
399 CompileParsedFunctionHelper(ParsedFunction* parsed_function, | 396 CompileParsedFunctionHelper(ParsedFunction* parsed_function, |
(...skipping 666 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1066 } | 1063 } |
1067 } | 1064 } |
1068 } | 1065 } |
1069 // Mark that this isolate now has compiled code. | 1066 // Mark that this isolate now has compiled code. |
1070 isolate()->set_has_compiled_code(true); | 1067 isolate()->set_has_compiled_code(true); |
1071 // Exit the loop and the function with the correct result value. | 1068 // Exit the loop and the function with the correct result value. |
1072 is_compiled = true; | 1069 is_compiled = true; |
1073 done = true; | 1070 done = true; |
1074 } else { | 1071 } else { |
1075 // We bailed out or we encountered an error. | 1072 // We bailed out or we encountered an error. |
1076 const Error& error = Error::Handle( | 1073 const Error& error = Error::Handle(thread()->sticky_error()); |
1077 isolate()->object_store()->sticky_error()); | |
1078 | 1074 |
1079 if (error.raw() == Object::branch_offset_error().raw()) { | 1075 if (error.raw() == Object::branch_offset_error().raw()) { |
1080 // Compilation failed due to an out of range branch offset in the | 1076 // Compilation failed due to an out of range branch offset in the |
1081 // assembler. We try again (done = false) with far branches enabled. | 1077 // assembler. We try again (done = false) with far branches enabled. |
1082 done = false; | 1078 done = false; |
1083 ASSERT(!use_far_branches); | 1079 ASSERT(!use_far_branches); |
1084 use_far_branches = true; | 1080 use_far_branches = true; |
1085 } else if (error.raw() == Object::speculative_inlining_error().raw()) { | 1081 } else if (error.raw() == Object::speculative_inlining_error().raw()) { |
1086 // The return value of setjmp is the deopt id of the check instruction | 1082 // The return value of setjmp is the deopt id of the check instruction |
1087 // that caused the bailout. | 1083 // that caused the bailout. |
(...skipping 20 matching lines...) Expand all Loading... |
1108 // compiling (is_compiled = false). | 1104 // compiling (is_compiled = false). |
1109 if (FLAG_trace_bailout) { | 1105 if (FLAG_trace_bailout) { |
1110 THR_Print("%s\n", error.ToErrorCString()); | 1106 THR_Print("%s\n", error.ToErrorCString()); |
1111 } | 1107 } |
1112 done = true; | 1108 done = true; |
1113 } | 1109 } |
1114 | 1110 |
1115 // Clear the error if it was not a real error, but just a bailout. | 1111 // Clear the error if it was not a real error, but just a bailout. |
1116 if (error.IsLanguageError() && | 1112 if (error.IsLanguageError() && |
1117 (LanguageError::Cast(error).kind() == Report::kBailout)) { | 1113 (LanguageError::Cast(error).kind() == Report::kBailout)) { |
1118 isolate()->object_store()->clear_sticky_error(); | 1114 thread()->clear_sticky_error(); |
1119 } | 1115 } |
1120 is_compiled = false; | 1116 is_compiled = false; |
1121 } | 1117 } |
1122 // Reset global isolate state. | 1118 // Reset global isolate state. |
1123 thread()->set_deopt_id(prev_deopt_id); | 1119 thread()->set_deopt_id(prev_deopt_id); |
1124 } | 1120 } |
1125 return is_compiled; | 1121 return is_compiled; |
1126 } | 1122 } |
1127 | 1123 |
1128 | 1124 |
(...skipping 217 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1346 } else if (FLAG_trace_failed_optimization_attempts) { | 1342 } else if (FLAG_trace_failed_optimization_attempts) { |
1347 THR_Print("Cannot optimize: %s\n", | 1343 THR_Print("Cannot optimize: %s\n", |
1348 function.ToFullyQualifiedCString()); | 1344 function.ToFullyQualifiedCString()); |
1349 } | 1345 } |
1350 function.SetIsOptimizable(false); | 1346 function.SetIsOptimizable(false); |
1351 return Error::null(); | 1347 return Error::null(); |
1352 } else { | 1348 } else { |
1353 // Encountered error. | 1349 // Encountered error. |
1354 Error& error = Error::Handle(); | 1350 Error& error = Error::Handle(); |
1355 // We got an error during compilation. | 1351 // We got an error during compilation. |
1356 error = isolate->object_store()->sticky_error(); | 1352 error = thread->sticky_error(); |
1357 isolate->object_store()->clear_sticky_error(); | 1353 thread->clear_sticky_error(); |
1358 ASSERT(error.IsLanguageError() && | 1354 ASSERT(error.IsLanguageError() && |
1359 LanguageError::Cast(error).kind() != Report::kBailout); | 1355 LanguageError::Cast(error).kind() != Report::kBailout); |
1360 return error.raw(); | 1356 return error.raw(); |
1361 } | 1357 } |
1362 } | 1358 } |
1363 | 1359 |
1364 per_compile_timer.Stop(); | 1360 per_compile_timer.Stop(); |
1365 | 1361 |
1366 if (trace_compiler && success) { | 1362 if (trace_compiler && success) { |
1367 THR_Print("--> '%s' entry: %#" Px " size: %" Pd " time: %" Pd64 " us\n", | 1363 THR_Print("--> '%s' entry: %#" Px " size: %" Pd " time: %" Pd64 " us\n", |
(...skipping 16 matching lines...) Expand all Loading... |
1384 THR_Print("*** BEGIN CODE\n"); | 1380 THR_Print("*** BEGIN CODE\n"); |
1385 DisassembleCode(function, true); | 1381 DisassembleCode(function, true); |
1386 THR_Print("*** END CODE\n"); | 1382 THR_Print("*** END CODE\n"); |
1387 } | 1383 } |
1388 #if defined(DEBUG) | 1384 #if defined(DEBUG) |
1389 CheckInliningIntervals(function); | 1385 CheckInliningIntervals(function); |
1390 #endif | 1386 #endif |
1391 return Error::null(); | 1387 return Error::null(); |
1392 } else { | 1388 } else { |
1393 Thread* const thread = Thread::Current(); | 1389 Thread* const thread = Thread::Current(); |
1394 Isolate* const isolate = thread->isolate(); | |
1395 StackZone stack_zone(thread); | 1390 StackZone stack_zone(thread); |
1396 Error& error = Error::Handle(); | 1391 Error& error = Error::Handle(); |
1397 // We got an error during compilation. | 1392 // We got an error during compilation. |
1398 error = isolate->object_store()->sticky_error(); | 1393 error = thread->sticky_error(); |
1399 isolate->object_store()->clear_sticky_error(); | 1394 thread->clear_sticky_error(); |
1400 // Unoptimized compilation or precompilation may encounter compile-time | 1395 // Unoptimized compilation or precompilation may encounter compile-time |
1401 // errors, but regular optimized compilation should not. | 1396 // errors, but regular optimized compilation should not. |
1402 ASSERT(!optimized || FLAG_precompilation); | 1397 ASSERT(!optimized || FLAG_precompilation); |
1403 // Do not attempt to optimize functions that can cause errors. | 1398 // Do not attempt to optimize functions that can cause errors. |
1404 function.set_is_optimizable(false); | 1399 function.set_is_optimizable(false); |
1405 return error.raw(); | 1400 return error.raw(); |
1406 } | 1401 } |
1407 UNREACHABLE(); | 1402 UNREACHABLE(); |
1408 return Error::null(); | 1403 return Error::null(); |
1409 } | 1404 } |
(...skipping 85 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1495 if (setjmp(*jump.Set()) == 0) { | 1490 if (setjmp(*jump.Set()) == 0) { |
1496 // Non-optimized code generator. | 1491 // Non-optimized code generator. |
1497 DartCompilationPipeline pipeline; | 1492 DartCompilationPipeline pipeline; |
1498 CompileParsedFunctionHelper helper(parsed_function, false, kNoOSRDeoptId); | 1493 CompileParsedFunctionHelper helper(parsed_function, false, kNoOSRDeoptId); |
1499 helper.Compile(&pipeline); | 1494 helper.Compile(&pipeline); |
1500 if (FLAG_disassemble) { | 1495 if (FLAG_disassemble) { |
1501 DisassembleCode(parsed_function->function(), false); | 1496 DisassembleCode(parsed_function->function(), false); |
1502 } | 1497 } |
1503 return Error::null(); | 1498 return Error::null(); |
1504 } else { | 1499 } else { |
1505 Isolate* const isolate = Isolate::Current(); | |
1506 Error& error = Error::Handle(); | 1500 Error& error = Error::Handle(); |
| 1501 Thread* thread = Thread::Current(); |
1507 // We got an error during compilation. | 1502 // We got an error during compilation. |
1508 error = isolate->object_store()->sticky_error(); | 1503 error = thread->sticky_error(); |
1509 isolate->object_store()->clear_sticky_error(); | 1504 thread->clear_sticky_error(); |
1510 return error.raw(); | 1505 return error.raw(); |
1511 } | 1506 } |
1512 UNREACHABLE(); | 1507 UNREACHABLE(); |
1513 return Error::null(); | 1508 return Error::null(); |
1514 } | 1509 } |
1515 | 1510 |
1516 | 1511 |
1517 void Compiler::ComputeLocalVarDescriptors(const Code& code) { | 1512 void Compiler::ComputeLocalVarDescriptors(const Code& code) { |
1518 ASSERT(!code.is_optimized()); | 1513 ASSERT(!code.is_optimized()); |
1519 const Function& function = Function::Handle(code.function()); | 1514 const Function& function = Function::Handle(code.function()); |
(...skipping 94 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1614 initializer = parsed_function->function().raw(); | 1609 initializer = parsed_function->function().raw(); |
1615 Code::Handle(initializer.unoptimized_code()).set_var_descriptors( | 1610 Code::Handle(initializer.unoptimized_code()).set_var_descriptors( |
1616 Object::empty_var_descriptors()); | 1611 Object::empty_var_descriptors()); |
1617 } else { | 1612 } else { |
1618 initializer ^= field.PrecompiledInitializer(); | 1613 initializer ^= field.PrecompiledInitializer(); |
1619 } | 1614 } |
1620 // Invoke the function to evaluate the expression. | 1615 // Invoke the function to evaluate the expression. |
1621 return DartEntry::InvokeFunction(initializer, Object::empty_array()); | 1616 return DartEntry::InvokeFunction(initializer, Object::empty_array()); |
1622 } else { | 1617 } else { |
1623 Thread* const thread = Thread::Current(); | 1618 Thread* const thread = Thread::Current(); |
1624 Isolate* const isolate = thread->isolate(); | |
1625 StackZone zone(thread); | 1619 StackZone zone(thread); |
1626 const Error& error = | 1620 const Error& error = Error::Handle(thread->zone(), thread->sticky_error()); |
1627 Error::Handle(thread->zone(), isolate->object_store()->sticky_error()); | 1621 thread->clear_sticky_error(); |
1628 isolate->object_store()->clear_sticky_error(); | |
1629 return error.raw(); | 1622 return error.raw(); |
1630 } | 1623 } |
1631 UNREACHABLE(); | 1624 UNREACHABLE(); |
1632 return Object::null(); | 1625 return Object::null(); |
1633 } | 1626 } |
1634 | 1627 |
1635 | 1628 |
1636 | 1629 |
1637 RawObject* Compiler::ExecuteOnce(SequenceNode* fragment) { | 1630 RawObject* Compiler::ExecuteOnce(SequenceNode* fragment) { |
1638 LongJumpScope jump; | 1631 LongJumpScope jump; |
(...skipping 41 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1680 CompileParsedFunctionHelper helper(parsed_function, false, kNoOSRDeoptId); | 1673 CompileParsedFunctionHelper helper(parsed_function, false, kNoOSRDeoptId); |
1681 helper.Compile(&pipeline); | 1674 helper.Compile(&pipeline); |
1682 Code::Handle(func.unoptimized_code()).set_var_descriptors( | 1675 Code::Handle(func.unoptimized_code()).set_var_descriptors( |
1683 Object::empty_var_descriptors()); | 1676 Object::empty_var_descriptors()); |
1684 | 1677 |
1685 const Object& result = PassiveObject::Handle( | 1678 const Object& result = PassiveObject::Handle( |
1686 DartEntry::InvokeFunction(func, Object::empty_array())); | 1679 DartEntry::InvokeFunction(func, Object::empty_array())); |
1687 return result.raw(); | 1680 return result.raw(); |
1688 } else { | 1681 } else { |
1689 Thread* const thread = Thread::Current(); | 1682 Thread* const thread = Thread::Current(); |
1690 Isolate* const isolate = thread->isolate(); | 1683 const Object& result = PassiveObject::Handle(thread->sticky_error()); |
1691 const Object& result = | 1684 thread->clear_sticky_error(); |
1692 PassiveObject::Handle(isolate->object_store()->sticky_error()); | |
1693 isolate->object_store()->clear_sticky_error(); | |
1694 return result.raw(); | 1685 return result.raw(); |
1695 } | 1686 } |
1696 UNREACHABLE(); | 1687 UNREACHABLE(); |
1697 return Object::null(); | 1688 return Object::null(); |
1698 } | 1689 } |
1699 | 1690 |
1700 | 1691 |
1701 // C-heap allocated background compilation queue element. | 1692 // C-heap allocated background compilation queue element. |
1702 class QueueElement { | 1693 class QueueElement { |
1703 public: | 1694 public: |
(...skipping 340 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2044 } | 2035 } |
2045 | 2036 |
2046 | 2037 |
2047 void BackgroundCompiler::EnsureInit(Thread* thread) { | 2038 void BackgroundCompiler::EnsureInit(Thread* thread) { |
2048 UNREACHABLE(); | 2039 UNREACHABLE(); |
2049 } | 2040 } |
2050 | 2041 |
2051 #endif // DART_PRECOMPILED_RUNTIME | 2042 #endif // DART_PRECOMPILED_RUNTIME |
2052 | 2043 |
2053 } // namespace dart | 2044 } // namespace dart |
OLD | NEW |