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/stack_frame.h" | 5 #include "vm/stack_frame.h" |
| 6 | 6 |
| 7 #include "vm/assembler.h" | 7 #include "vm/assembler.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 10 matching lines...) Expand all Loading... | |
| 21 | 21 |
| 22 bool StackFrame::IsStubFrame() const { | 22 bool StackFrame::IsStubFrame() const { |
| 23 ASSERT(!(IsEntryFrame() || IsExitFrame())); | 23 ASSERT(!(IsEntryFrame() || IsExitFrame())); |
| 24 uword saved_pc = | 24 uword saved_pc = |
| 25 *(reinterpret_cast<uword*>(fp() + (kPcMarkerSlotFromFp * kWordSize))); | 25 *(reinterpret_cast<uword*>(fp() + (kPcMarkerSlotFromFp * kWordSize))); |
| 26 return (saved_pc == 0); | 26 return (saved_pc == 0); |
| 27 } | 27 } |
| 28 | 28 |
| 29 | 29 |
| 30 const char* StackFrame::ToCString() const { | 30 const char* StackFrame::ToCString() const { |
| 31 ASSERT(isolate_ == Isolate::Current()); | |
| 31 Zone* zone = Isolate::Current()->current_zone(); | 32 Zone* zone = Isolate::Current()->current_zone(); |
| 32 if (IsDartFrame()) { | 33 if (IsDartFrame()) { |
| 33 const Code& code = Code::Handle(LookupDartCode()); | 34 const Code& code = Code::Handle(LookupDartCode()); |
| 34 ASSERT(!code.IsNull()); | 35 ASSERT(!code.IsNull()); |
| 35 const Object& owner = Object::Handle(code.owner()); | 36 const Object& owner = Object::Handle(code.owner()); |
| 36 ASSERT(!owner.IsNull()); | 37 ASSERT(!owner.IsNull()); |
| 37 if (owner.IsFunction()) { | 38 if (owner.IsFunction()) { |
| 38 const Function& function = Function::Cast(owner); | 39 const Function& function = Function::Cast(owner); |
| 39 return zone->PrintToString( | 40 return zone->PrintToString( |
| 40 "[%-8s : sp(%#" Px ") fp(%#" Px ") pc(%#" Px ") %s ]", | 41 "[%-8s : sp(%#" Px ") fp(%#" Px ") pc(%#" Px ") %s ]", |
| (...skipping 18 matching lines...) Expand all Loading... | |
| 59 } | 60 } |
| 60 | 61 |
| 61 | 62 |
| 62 RawContext* EntryFrame::SavedContext() const { | 63 RawContext* EntryFrame::SavedContext() const { |
| 63 return *(reinterpret_cast<RawContext**>( | 64 return *(reinterpret_cast<RawContext**>( |
| 64 fp() + (kSavedContextSlotFromEntryFp * kWordSize))); | 65 fp() + (kSavedContextSlotFromEntryFp * kWordSize))); |
| 65 } | 66 } |
| 66 | 67 |
| 67 | 68 |
| 68 void EntryFrame::VisitObjectPointers(ObjectPointerVisitor* visitor) { | 69 void EntryFrame::VisitObjectPointers(ObjectPointerVisitor* visitor) { |
| 70 ASSERT(isolate() == Isolate::Current()); | |
| 69 // Visit objects between SP and (FP - callee_save_area). | 71 // Visit objects between SP and (FP - callee_save_area). |
| 70 ASSERT(visitor != NULL); | 72 ASSERT(visitor != NULL); |
| 71 RawObject** first = reinterpret_cast<RawObject**>(sp()); | 73 RawObject** first = reinterpret_cast<RawObject**>(sp()); |
| 72 RawObject** last = reinterpret_cast<RawObject**>( | 74 RawObject** last = reinterpret_cast<RawObject**>( |
| 73 fp() + (kExitLinkSlotFromEntryFp - 1) * kWordSize); | 75 fp() + (kExitLinkSlotFromEntryFp - 1) * kWordSize); |
| 74 visitor->VisitPointers(first, last); | 76 visitor->VisitPointers(first, last); |
| 75 } | 77 } |
| 76 | 78 |
| 77 | 79 |
| 78 void StackFrame::VisitObjectPointers(ObjectPointerVisitor* visitor) { | 80 void StackFrame::VisitObjectPointers(ObjectPointerVisitor* visitor) { |
| 79 // NOTE: This code runs while GC is in progress and runs within | 81 // NOTE: This code runs while GC is in progress and runs within |
| 80 // a NoHandleScope block. Hence it is not ok to use regular Zone or | 82 // a NoHandleScope block. Hence it is not ok to use regular Zone or |
| 81 // Scope handles. We use direct stack handles, the raw pointers in | 83 // Scope handles. We use direct stack handles, the raw pointers in |
| 82 // these handles are not traversed. The use of handles is mainly to | 84 // these handles are not traversed. The use of handles is mainly to |
| 83 // be able to reuse the handle based code and avoid having to add | 85 // be able to reuse the handle based code and avoid having to add |
| 84 // helper functions to the raw object interface. | 86 // helper functions to the raw object interface. |
| 87 ASSERT(isolate_ == Isolate::Current()); | |
| 85 ASSERT(visitor != NULL); | 88 ASSERT(visitor != NULL); |
| 86 NoGCScope no_gc; | 89 NoGCScope no_gc; |
| 87 Code code; | 90 Code code; |
| 88 code = LookupDartCode(); | 91 code = LookupDartCode(); |
| 89 if (!code.IsNull()) { | 92 if (!code.IsNull()) { |
| 90 // Visit the code object. | 93 // Visit the code object. |
| 91 RawObject* raw_code = code.raw(); | 94 RawObject* raw_code = code.raw(); |
| 92 visitor->VisitPointer(&raw_code); | 95 visitor->VisitPointer(&raw_code); |
| 93 | 96 |
| 94 // Optimized frames have a stack map. We need to visit the frame based | 97 // Optimized frames have a stack map. We need to visit the frame based |
| (...skipping 57 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 152 // For normal unoptimized Dart frames and Stub frames each slot | 155 // For normal unoptimized Dart frames and Stub frames each slot |
| 153 // between the first and last included are tagged objects. | 156 // between the first and last included are tagged objects. |
| 154 RawObject** first = reinterpret_cast<RawObject**>(sp()); | 157 RawObject** first = reinterpret_cast<RawObject**>(sp()); |
| 155 RawObject** last = reinterpret_cast<RawObject**>( | 158 RawObject** last = reinterpret_cast<RawObject**>( |
| 156 fp() + (kFirstObjectSlotFromFp * kWordSize)); | 159 fp() + (kFirstObjectSlotFromFp * kWordSize)); |
| 157 visitor->VisitPointers(first, last); | 160 visitor->VisitPointers(first, last); |
| 158 } | 161 } |
| 159 | 162 |
| 160 | 163 |
| 161 RawFunction* StackFrame::LookupDartFunction() const { | 164 RawFunction* StackFrame::LookupDartFunction() const { |
| 165 ASSERT(isolate_ == Isolate::Current()); | |
| 162 const Code& code = Code::Handle(LookupDartCode()); | 166 const Code& code = Code::Handle(LookupDartCode()); |
| 163 if (!code.IsNull()) { | 167 if (!code.IsNull()) { |
| 164 return code.function(); | 168 return code.function(); |
| 165 } | 169 } |
| 166 return Function::null(); | 170 return Function::null(); |
| 167 } | 171 } |
| 168 | 172 |
| 169 | 173 |
| 170 RawCode* StackFrame::LookupDartCode() const { | 174 RawCode* StackFrame::LookupDartCode() const { |
| 175 ASSERT(isolate_ == Isolate::Current()); | |
| 171 // We add a no gc scope to ensure that the code below does not trigger | 176 // We add a no gc scope to ensure that the code below does not trigger |
| 172 // a GC as we are handling raw object references here. It is possible | 177 // a GC as we are handling raw object references here. It is possible |
| 173 // that the code is called while a GC is in progress, that is ok. | 178 // that the code is called while a GC is in progress, that is ok. |
| 174 NoGCScope no_gc; | 179 NoGCScope no_gc; |
| 175 RawCode* code = GetCodeObject(); | 180 RawCode* code = GetCodeObject(); |
| 176 ASSERT(code == Code::null() || code->ptr()->owner_ != Function::null()); | 181 ASSERT(code == Code::null() || code->ptr()->owner_ != Function::null()); |
| 177 return code; | 182 return code; |
| 178 } | 183 } |
| 179 | 184 |
| 180 | 185 |
| (...skipping 90 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 271 | 276 |
| 272 void StackFrameIterator::SetupNextExitFrameData() { | 277 void StackFrameIterator::SetupNextExitFrameData() { |
| 273 uword exit_address = entry_.fp() + (kExitLinkSlotFromEntryFp * kWordSize); | 278 uword exit_address = entry_.fp() + (kExitLinkSlotFromEntryFp * kWordSize); |
| 274 uword exit_marker = *reinterpret_cast<uword*>(exit_address); | 279 uword exit_marker = *reinterpret_cast<uword*>(exit_address); |
| 275 frames_.fp_ = exit_marker; | 280 frames_.fp_ = exit_marker; |
| 276 frames_.sp_ = 0; | 281 frames_.sp_ = 0; |
| 277 frames_.pc_ = 0; | 282 frames_.pc_ = 0; |
| 278 } | 283 } |
| 279 | 284 |
| 280 | 285 |
| 281 StackFrameIterator::StackFrameIterator(bool validate) | 286 StackFrameIterator::StackFrameIterator(bool validate, Isolate* isolate) |
| 282 : validate_(validate), entry_(), exit_(), current_frame_(NULL) { | 287 : validate_(validate), |
| 288 entry_(isolate), | |
| 289 exit_(isolate), | |
| 290 frames_(isolate), | |
| 291 current_frame_(NULL), | |
| 292 isolate_(isolate) { | |
| 293 #if !defined(TARGET_OS_WINDOWS) | |
| 294 // On Windows, the call to InInvocationStub may be called from the thread | |
| 295 // suspender. | |
|
siva
2014/06/30 23:26:44
This comment I feel should be more detailed explai
Cutch
2014/07/01 14:26:09
Done.
| |
| 296 ASSERT(isolate_ == Isolate::Current()); | |
| 297 #endif | |
|
siva
2014/06/30 23:26:44
The #ifdef looks weird here, maybe you could code
Cutch
2014/07/01 14:26:09
Done.
| |
| 283 SetupLastExitFrameData(); // Setup data for last exit frame. | 298 SetupLastExitFrameData(); // Setup data for last exit frame. |
| 284 } | 299 } |
| 285 | 300 |
| 286 | 301 |
| 287 StackFrameIterator::StackFrameIterator(uword last_fp, bool validate) | 302 StackFrameIterator::StackFrameIterator(uword last_fp, bool validate, |
| 288 : validate_(validate), entry_(), exit_(), current_frame_(NULL) { | 303 Isolate* isolate) |
| 304 : validate_(validate), | |
| 305 entry_(isolate), | |
| 306 exit_(isolate), | |
| 307 frames_(isolate), | |
| 308 current_frame_(NULL), | |
| 309 isolate_(isolate) { | |
| 310 #if !defined(TARGET_OS_WINDOWS) | |
| 311 // On Windows, the call to InInvocationStub may be called from the thread | |
| 312 // suspender. | |
| 313 ASSERT(isolate_ == Isolate::Current()); | |
| 314 #endif | |
| 289 frames_.fp_ = last_fp; | 315 frames_.fp_ = last_fp; |
| 290 frames_.sp_ = 0; | 316 frames_.sp_ = 0; |
| 291 frames_.pc_ = 0; | 317 frames_.pc_ = 0; |
| 292 } | 318 } |
| 293 | 319 |
| 294 | 320 |
| 295 StackFrameIterator::StackFrameIterator(uword fp, uword sp, uword pc, | 321 StackFrameIterator::StackFrameIterator(uword fp, uword sp, uword pc, |
| 296 bool validate) | 322 bool validate, Isolate* isolate) |
| 297 : validate_(validate), entry_(), exit_(), current_frame_(NULL) { | 323 : validate_(validate), |
| 324 entry_(isolate), | |
| 325 exit_(isolate), | |
| 326 frames_(isolate), | |
| 327 current_frame_(NULL), | |
| 328 isolate_(isolate) { | |
| 329 #if !defined(TARGET_OS_WINDOWS) | |
| 330 // On Windows, the call to InInvocationStub may be called from the thread | |
| 331 // suspender. | |
| 332 ASSERT(isolate_ == Isolate::Current()); | |
| 333 #endif | |
| 298 frames_.fp_ = fp; | 334 frames_.fp_ = fp; |
| 299 frames_.sp_ = sp; | 335 frames_.sp_ = sp; |
| 300 frames_.pc_ = pc; | 336 frames_.pc_ = pc; |
| 301 } | 337 } |
| 302 | 338 |
| 303 | 339 |
| 304 StackFrame* StackFrameIterator::NextFrame() { | 340 StackFrame* StackFrameIterator::NextFrame() { |
| 305 // When we are at the start of iteration after having created an | 341 // When we are at the start of iteration after having created an |
| 306 // iterator object, current_frame_ will be NULL as we haven't seen | 342 // iterator object, current_frame_ will be NULL as we haven't seen |
| 307 // any frames yet (unless we start iterating in the simulator from a given | 343 // any frames yet (unless we start iterating in the simulator from a given |
| (...skipping 148 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 456 if (deopt_instr->kind() == DeoptInstr::kCallerFp) { | 492 if (deopt_instr->kind() == DeoptInstr::kCallerFp) { |
| 457 return (index - num_materializations_); | 493 return (index - num_materializations_); |
| 458 } | 494 } |
| 459 } | 495 } |
| 460 UNREACHABLE(); | 496 UNREACHABLE(); |
| 461 return 0; | 497 return 0; |
| 462 } | 498 } |
| 463 | 499 |
| 464 | 500 |
| 465 } // namespace dart | 501 } // namespace dart |
| OLD | NEW |