| 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/stack_frame.h" | 5 #include "vm/stack_frame.h" |
| 6 | 6 |
| 7 #include "vm/assembler_macros.h" | 7 #include "vm/assembler_macros.h" |
| 8 #include "vm/deopt_instructions.h" | 8 #include "vm/deopt_instructions.h" |
| 9 #include "vm/isolate.h" | 9 #include "vm/isolate.h" |
| 10 #include "vm/object.h" | 10 #include "vm/object.h" |
| (...skipping 264 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 275 entry_.sp_ = frames_.sp_; | 275 entry_.sp_ = frames_.sp_; |
| 276 entry_.fp_ = frames_.fp_; | 276 entry_.fp_ = frames_.fp_; |
| 277 SetupNextExitFrameData(); // Setup data for next exit frame in chain. | 277 SetupNextExitFrameData(); // Setup data for next exit frame in chain. |
| 278 ASSERT(entry_.IsValid()); | 278 ASSERT(entry_.IsValid()); |
| 279 return &entry_; | 279 return &entry_; |
| 280 } | 280 } |
| 281 | 281 |
| 282 | 282 |
| 283 InlinedFunctionsInDartFrameIterator::InlinedFunctionsInDartFrameIterator( | 283 InlinedFunctionsInDartFrameIterator::InlinedFunctionsInDartFrameIterator( |
| 284 StackFrame* frame) : index_(0), | 284 StackFrame* frame) : index_(0), |
| 285 frame_(frame), | 285 deopt_instructions_(), |
| 286 func_(Function::Handle()), | |
| 287 deopt_info_(DeoptInfo::Handle()), | |
| 288 object_table_(Array::Handle()) { | 286 object_table_(Array::Handle()) { |
| 289 ASSERT(frame_ != NULL); | 287 ASSERT(frame != NULL); |
| 290 const Code& code = Code::Handle(frame_->LookupDartCode()); | 288 const Code& code = Code::Handle(frame->LookupDartCode()); |
| 291 ASSERT(code.is_optimized()); | 289 ASSERT(code.is_optimized()); |
| 292 func_ = code.function(); | |
| 293 intptr_t deopt_reason = kDeoptUnknown; | 290 intptr_t deopt_reason = kDeoptUnknown; |
| 294 deopt_info_ = code.GetDeoptInfoAtPc(frame_->pc(), &deopt_reason); | 291 const DeoptInfo& deopt_info = DeoptInfo::Handle( |
| 292 code.GetDeoptInfoAtPc(frame->pc(), &deopt_reason)); |
| 293 ASSERT(!deopt_info.IsNull()); |
| 294 |
| 295 // Unpack deopt info into instructions (translate away suffixes). |
| 296 const Array& deopt_table = Array::Handle(code.deopt_info_array()); |
| 297 ASSERT(!deopt_table.IsNull()); |
| 298 deopt_info.ToInstructions(deopt_table, &deopt_instructions_); |
| 299 |
| 295 object_table_ = code.object_table(); | 300 object_table_ = code.object_table(); |
| 296 } | 301 } |
| 297 | 302 |
| 298 | 303 |
| 299 RawFunction* InlinedFunctionsInDartFrameIterator::GetNextFunction(uword* pc) { | 304 RawFunction* InlinedFunctionsInDartFrameIterator::GetNextFunction(uword* pc) { |
| 300 if (index_ == -1) { | 305 if (index_ == -1) { |
| 301 return Function::null(); | 306 return Function::null(); |
| 302 } | 307 } |
| 303 if (deopt_info_.IsNull()) { | 308 |
| 304 // We are at a PC that has no deoptimization info so there are no | |
| 305 // inlined functions to iterate over, we return the function. | |
| 306 index_ = -1; // No more functions. | |
| 307 *pc = frame_->pc(); | |
| 308 return func_.raw(); | |
| 309 } | |
| 310 // Iterate over the deopt instructions and determine the inlined | 309 // Iterate over the deopt instructions and determine the inlined |
| 311 // functions if any and iterate over them. | 310 // functions if any and iterate over them. |
| 312 ASSERT(deopt_info_.Length() != 0); | 311 Function& func = Function::Handle(); |
| 313 while (index_ < deopt_info_.Length()) { | 312 ASSERT(deopt_instructions_.length() != 0); |
| 314 intptr_t cur_index = index_; | 313 while (index_ < deopt_instructions_.length()) { |
| 315 index_ += 1; | 314 DeoptInstr* deopt_instr = deopt_instructions_[index_++]; |
| 316 intptr_t deopt_instr = deopt_info_.Instruction(cur_index); | 315 ASSERT(deopt_instr->kind() != DeoptInstr::kRetBeforeAddress); |
| 317 ASSERT(deopt_instr != DeoptInstr::kRetBeforeAddress); | 316 if (deopt_instr->kind() == DeoptInstr::kRetAfterAddress) { |
| 318 if (deopt_instr == DeoptInstr::kRetAfterAddress) { | 317 *pc = DeoptInstr::GetRetAfterAddress(deopt_instr, |
| 319 intptr_t deopt_from_index = deopt_info_.FromIndex(cur_index); | |
| 320 *pc = DeoptInstr::GetRetAfterAddress(deopt_from_index, | |
| 321 object_table_, | 318 object_table_, |
| 322 &func_); | 319 &func); |
| 323 return func_.raw(); | 320 return func.raw(); |
| 324 } | 321 } |
| 325 } | 322 } |
| 326 index_ = -1; | 323 index_ = -1; |
| 327 return Function::null(); | 324 return Function::null(); |
| 328 } | 325 } |
| 329 | 326 |
| 330 } // namespace dart | 327 } // namespace dart |
| OLD | NEW |