Chromium Code Reviews| 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/code_generator.h" | 10 #include "vm/code_generator.h" |
| (...skipping 242 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 253 Isolate* isolate = Isolate::Current(); | 253 Isolate* isolate = Isolate::Current(); |
| 254 HANDLESCOPE(isolate); | 254 HANDLESCOPE(isolate); |
| 255 | 255 |
| 256 // We may reattempt compilation if the function needs to be assembled using | 256 // We may reattempt compilation if the function needs to be assembled using |
| 257 // far branches on ARM and MIPS. In the else branch of the setjmp call, | 257 // far branches on ARM and MIPS. In the else branch of the setjmp call, |
| 258 // done is set to false, and use_far_branches is set to true if there is a | 258 // done is set to false, and use_far_branches is set to true if there is a |
| 259 // longjmp from the ARM or MIPS assemblers. In all other paths through this | 259 // longjmp from the ARM or MIPS assemblers. In all other paths through this |
| 260 // while loop, done is set to true. use_far_branches is always false on ia32 | 260 // while loop, done is set to true. use_far_branches is always false on ia32 |
| 261 // and x64. | 261 // and x64. |
| 262 bool done = false; | 262 bool done = false; |
| 263 // static to evade gcc's longjmp variable smashing checks. | 263 // volatile because the variable may be clobbered by a longjmp. |
| 264 static bool use_far_branches = false; | 264 volatile bool use_far_branches = false; |
| 265 while (!done) { | 265 while (!done) { |
| 266 const intptr_t prev_deopt_id = isolate->deopt_id(); | 266 const intptr_t prev_deopt_id = isolate->deopt_id(); |
| 267 isolate->set_deopt_id(0); | 267 isolate->set_deopt_id(0); |
| 268 LongJump* old_base = isolate->long_jump_base(); | 268 LongJump* old_base = isolate->long_jump_base(); |
| 269 LongJump bailout_jump; | 269 LongJump bailout_jump; |
| 270 isolate->set_long_jump_base(&bailout_jump); | 270 isolate->set_long_jump_base(&bailout_jump); |
| 271 if (setjmp(*bailout_jump.Set()) == 0) { | 271 if (setjmp(*bailout_jump.Set()) == 0) { |
| 272 FlowGraph* flow_graph = NULL; | 272 FlowGraph* flow_graph = NULL; |
| 273 // TimerScope needs an isolate to be properly terminated in case of a | 273 // TimerScope needs an isolate to be properly terminated in case of a |
| 274 // LongJump. | 274 // LongJump. |
| (...skipping 269 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 544 ASSERT(CodePatcher::CodeIsPatchable(code)); | 544 ASSERT(CodePatcher::CodeIsPatchable(code)); |
| 545 } | 545 } |
| 546 } | 546 } |
| 547 is_compiled = true; | 547 is_compiled = true; |
| 548 done = true; | 548 done = true; |
| 549 } else { | 549 } else { |
| 550 // We bailed out. | 550 // We bailed out. |
| 551 const Error& bailout_error = Error::Handle( | 551 const Error& bailout_error = Error::Handle( |
| 552 isolate->object_store()->sticky_error()); | 552 isolate->object_store()->sticky_error()); |
| 553 | 553 |
| 554 ASSERT(bailout_error.IsLanguageError()); | 554 ASSERT(bailout_error.IsLanguageError()); |
|
Ivan Posva
2013/08/09 17:07:25
We should be prepared to handle different errors h
zra
2013/08/09 17:12:20
Yes. I'll make the change in a new CL.
| |
| 555 const LanguageError& le = LanguageError::CheckedHandle( | 555 const LanguageError& le = LanguageError::CheckedHandle( |
| 556 isolate->object_store()->sticky_error()); | 556 isolate->object_store()->sticky_error()); |
| 557 const String& msg = String::Handle(le.message()); | 557 const String& msg = String::Handle(le.message()); |
| 558 if (msg.Equals("Branch offset overflow")) { | 558 if (msg.Equals("Branch offset overflow")) { |
| 559 done = false; | 559 done = false; |
| 560 ASSERT(!use_far_branches); | 560 ASSERT(!use_far_branches); |
| 561 use_far_branches = true; | 561 use_far_branches = true; |
| 562 } else { | 562 } else { |
| 563 // If not for a branch offset overflow, we only bail out from | 563 // If not for a branch offset overflow, we only bail out from |
| 564 // generating ssa code. | 564 // generating ssa code. |
| 565 if (FLAG_trace_bailout) { | 565 if (FLAG_trace_bailout) { |
| 566 OS::Print("%s\n", bailout_error.ToErrorCString()); | 566 OS::Print("%s\n", bailout_error.ToErrorCString()); |
| 567 } | 567 } |
| 568 done = true; | 568 done = true; |
| 569 ASSERT(optimized); | 569 ASSERT(optimized); |
| 570 } | 570 } |
| 571 | 571 |
| 572 isolate->object_store()->clear_sticky_error(); | 572 isolate->object_store()->clear_sticky_error(); |
| 573 is_compiled = false; | 573 is_compiled = false; |
| 574 } | 574 } |
| 575 // Reset global isolate state. | 575 // Reset global isolate state. |
| 576 isolate->set_long_jump_base(old_base); | 576 isolate->set_long_jump_base(old_base); |
| 577 isolate->set_deopt_id(prev_deopt_id); | 577 isolate->set_deopt_id(prev_deopt_id); |
| 578 } | 578 } |
| 579 use_far_branches = false; | |
| 580 return is_compiled; | 579 return is_compiled; |
| 581 } | 580 } |
| 582 | 581 |
| 583 | 582 |
| 584 static void DisassembleCode(const Function& function, bool optimized) { | 583 static void DisassembleCode(const Function& function, bool optimized) { |
| 585 const char* function_fullname = function.ToFullyQualifiedCString(); | 584 const char* function_fullname = function.ToFullyQualifiedCString(); |
| 586 OS::Print("Code for %sfunction '%s' {\n", | 585 OS::Print("Code for %sfunction '%s' {\n", |
| 587 optimized ? "optimized " : "", | 586 optimized ? "optimized " : "", |
| 588 function_fullname); | 587 function_fullname); |
| 589 const Code& code = Code::Handle(function.CurrentCode()); | 588 const Code& code = Code::Handle(function.CurrentCode()); |
| (...skipping 319 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 909 Object::Handle(isolate->object_store()->sticky_error()); | 908 Object::Handle(isolate->object_store()->sticky_error()); |
| 910 isolate->object_store()->clear_sticky_error(); | 909 isolate->object_store()->clear_sticky_error(); |
| 911 isolate->set_long_jump_base(base); | 910 isolate->set_long_jump_base(base); |
| 912 return result.raw(); | 911 return result.raw(); |
| 913 } | 912 } |
| 914 UNREACHABLE(); | 913 UNREACHABLE(); |
| 915 return Object::null(); | 914 return Object::null(); |
| 916 } | 915 } |
| 917 | 916 |
| 918 } // namespace dart | 917 } // namespace dart |
| OLD | NEW |