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

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

Issue 403643002: One more iteration of PcDescriptor iterator improvement: do not copy record but access individual … (Closed) Base URL: http://dart.googlecode.com/svn/branches/bleeding_edge/dart/
Patch Set: Created 6 years, 5 months 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 | Annotate | Revision Log
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/debugger.h" 5 #include "vm/debugger.h"
6 6
7 #include "include/dart_api.h" 7 #include "include/dart_api.h"
8 8
9 #include "vm/code_generator.h" 9 #include "vm/code_generator.h"
10 #include "vm/code_patcher.h" 10 #include "vm/code_patcher.h"
(...skipping 345 matching lines...) Expand 10 before | Expand all | Expand 10 after
356 356
357 357
358 // Compute token_pos_ and try_index_ and token_pos_initialized_. 358 // Compute token_pos_ and try_index_ and token_pos_initialized_.
359 intptr_t ActivationFrame::TokenPos() { 359 intptr_t ActivationFrame::TokenPos() {
360 if (!token_pos_initialized_) { 360 if (!token_pos_initialized_) {
361 token_pos_initialized_ = true; 361 token_pos_initialized_ = true;
362 token_pos_ = Scanner::kNoSourcePos; 362 token_pos_ = Scanner::kNoSourcePos;
363 GetPcDescriptors(); 363 GetPcDescriptors();
364 PcDescriptors::Iterator iter(pc_desc_, RawPcDescriptors::kAnyKind); 364 PcDescriptors::Iterator iter(pc_desc_, RawPcDescriptors::kAnyKind);
365 while (iter.HasNext()) { 365 while (iter.HasNext()) {
366 RawPcDescriptors::PcDescriptorRec rec; 366 const uword pc = iter.NextPc();
367 iter.NextRec(&rec); 367 if (pc == pc_) {
368 if (rec.pc() == pc_) { 368 try_index_ = iter.current_try_index();
369 try_index_ = rec.try_index(); 369 token_pos_ = iter.current_token_pos();
370 token_pos_ = rec.token_pos();
371 break; 370 break;
372 } 371 }
373 } 372 }
374 } 373 }
375 return token_pos_; 374 return token_pos_;
376 } 375 }
377 376
378 377
379 intptr_t ActivationFrame::TryIndex() { 378 intptr_t ActivationFrame::TryIndex() {
380 if (!token_pos_initialized_) { 379 if (!token_pos_initialized_) {
(...skipping 543 matching lines...) Expand 10 before | Expand all | Expand 10 after
924 } 923 }
925 } 924 }
926 925
927 926
928 const uint8_t kSafepointKind = 927 const uint8_t kSafepointKind =
929 RawPcDescriptors::kIcCall | RawPcDescriptors::kOptStaticCall | 928 RawPcDescriptors::kIcCall | RawPcDescriptors::kOptStaticCall |
930 RawPcDescriptors::kUnoptStaticCall | RawPcDescriptors::kClosureCall | 929 RawPcDescriptors::kUnoptStaticCall | RawPcDescriptors::kClosureCall |
931 RawPcDescriptors::kRuntimeCall; 930 RawPcDescriptors::kRuntimeCall;
932 931
933 932
934 static bool HasTokenPos(const RawPcDescriptors::PcDescriptorRec& rec) {
935 return rec.token_pos() != Scanner::kNoSourcePos;
936 }
937
938
939 CodeBreakpoint::CodeBreakpoint(const Code& code, 933 CodeBreakpoint::CodeBreakpoint(const Code& code,
940 const RawPcDescriptors::PcDescriptorRec& rec) 934 intptr_t token_pos,
935 uword pc,
936 RawPcDescriptors::Kind kind)
941 : code_(code.raw()), 937 : code_(code.raw()),
942 token_pos_(rec.token_pos()), 938 token_pos_(token_pos),
943 pc_(rec.pc()), 939 pc_(pc),
944 line_number_(-1), 940 line_number_(-1),
945 is_enabled_(false), 941 is_enabled_(false),
946 src_bpt_(NULL), 942 src_bpt_(NULL),
947 next_(NULL), 943 next_(NULL),
948 breakpoint_kind_(rec.kind()), 944 breakpoint_kind_(kind),
949 saved_value_(0) { 945 saved_value_(0) {
950 ASSERT(!code.IsNull()); 946 ASSERT(!code.IsNull());
951 ASSERT(token_pos_ > 0); 947 ASSERT(token_pos_ > 0);
952 ASSERT(pc_ != 0); 948 ASSERT(pc_ != 0);
953 ASSERT((breakpoint_kind_ & kSafepointKind) != 0); 949 ASSERT((breakpoint_kind_ & kSafepointKind) != 0);
954 } 950 }
955 951
956 952
957 CodeBreakpoint::~CodeBreakpoint() { 953 CodeBreakpoint::~CodeBreakpoint() {
958 // Make sure we don't leave patched code behind. 954 // Make sure we don't leave patched code behind.
(...skipping 239 matching lines...) Expand 10 before | Expand all | Expand 10 after
1198 } 1194 }
1199 // Hang on to the code object before deoptimizing, in case deoptimization 1195 // Hang on to the code object before deoptimizing, in case deoptimization
1200 // might cause the GC to run. 1196 // might cause the GC to run.
1201 Code& code = Code::Handle(isolate, target_function.unoptimized_code()); 1197 Code& code = Code::Handle(isolate, target_function.unoptimized_code());
1202 ASSERT(!code.IsNull()); 1198 ASSERT(!code.IsNull());
1203 DeoptimizeWorld(); 1199 DeoptimizeWorld();
1204 ASSERT(!target_function.HasOptimizedCode()); 1200 ASSERT(!target_function.HasOptimizedCode());
1205 PcDescriptors& desc = PcDescriptors::Handle(isolate, code.pc_descriptors()); 1201 PcDescriptors& desc = PcDescriptors::Handle(isolate, code.pc_descriptors());
1206 PcDescriptors::Iterator iter(desc, kSafepointKind); 1202 PcDescriptors::Iterator iter(desc, kSafepointKind);
1207 while (iter.HasNext()) { 1203 while (iter.HasNext()) {
1208 RawPcDescriptors::PcDescriptorRec rec; 1204 const intptr_t token_pos = iter.NextTokenPos();
1209 iter.NextRec(&rec); 1205 if (token_pos != Scanner::kNoSourcePos) {
1210 if (HasTokenPos(rec)) { 1206 CodeBreakpoint* bpt = GetCodeBreakpoint(iter.current_pc());
1211 CodeBreakpoint* bpt = GetCodeBreakpoint(rec.pc());
1212 if (bpt != NULL) { 1207 if (bpt != NULL) {
1213 // There is already a breakpoint for this address. Make sure 1208 // There is already a breakpoint for this address. Make sure
1214 // it is enabled. 1209 // it is enabled.
1215 bpt->Enable(); 1210 bpt->Enable();
1216 continue; 1211 continue;
1217 } 1212 }
1218 bpt = new CodeBreakpoint(code, rec); 1213 bpt = new CodeBreakpoint(code, iter.current_token_pos(),
1214 iter.current_pc(), iter.current_kind());
1219 RegisterCodeBreakpoint(bpt); 1215 RegisterCodeBreakpoint(bpt);
1220 bpt->Enable(); 1216 bpt->Enable();
1221 } 1217 }
1222 } 1218 }
1223 } 1219 }
1224 1220
1225 1221
1226 void Debugger::SignalBpResolved(SourceBreakpoint* bpt) { 1222 void Debugger::SignalBpResolved(SourceBreakpoint* bpt) {
1227 if (HasEventHandler()) { 1223 if (HasEventHandler()) {
1228 DebuggerEvent event(isolate_, DebuggerEvent::kBreakpointResolved); 1224 DebuggerEvent event(isolate_, DebuggerEvent::kBreakpointResolved);
(...skipping 317 matching lines...) Expand 10 before | Expand all | Expand 10 after
1546 } 1542 }
1547 1543
1548 Code& code = Code::Handle(func.unoptimized_code()); 1544 Code& code = Code::Handle(func.unoptimized_code());
1549 ASSERT(!code.IsNull()); 1545 ASSERT(!code.IsNull());
1550 PcDescriptors& desc = PcDescriptors::Handle(code.pc_descriptors()); 1546 PcDescriptors& desc = PcDescriptors::Handle(code.pc_descriptors());
1551 intptr_t best_fit_pos = INT_MAX; 1547 intptr_t best_fit_pos = INT_MAX;
1552 uword lowest_pc = kUwordMax; 1548 uword lowest_pc = kUwordMax;
1553 intptr_t lowest_pc_token_pos = INT_MAX; 1549 intptr_t lowest_pc_token_pos = INT_MAX;
1554 PcDescriptors::Iterator iter(desc, kSafepointKind); 1550 PcDescriptors::Iterator iter(desc, kSafepointKind);
1555 while (iter.HasNext()) { 1551 while (iter.HasNext()) {
1556 RawPcDescriptors::PcDescriptorRec rec; 1552 const intptr_t desc_token_pos = iter.NextTokenPos();
1557 iter.NextRec(&rec);
1558 intptr_t desc_token_pos = rec.token_pos();
1559 ASSERT(desc_token_pos >= 0); 1553 ASSERT(desc_token_pos >= 0);
1560 if (HasTokenPos(rec)) { 1554 if (desc_token_pos != Scanner::kNoSourcePos) {
1561 if ((desc_token_pos < requested_token_pos) || 1555 if ((desc_token_pos < requested_token_pos) ||
1562 (desc_token_pos > last_token_pos)) { 1556 (desc_token_pos > last_token_pos)) {
1563 // This descriptor is outside the desired token range. 1557 // This descriptor is outside the desired token range.
1564 continue; 1558 continue;
1565 } 1559 }
1566 if (desc_token_pos < best_fit_pos) { 1560 if (desc_token_pos < best_fit_pos) {
1567 // So far, this descriptor has the lowest token position after 1561 // So far, this descriptor has the lowest token position after
1568 // the first acceptable token position. 1562 // the first acceptable token position.
1569 best_fit_pos = desc_token_pos; 1563 best_fit_pos = desc_token_pos;
1570 } 1564 }
1571 if (rec.pc() < lowest_pc) { 1565 if (iter.current_pc() < lowest_pc) {
1572 // This descriptor so far has the lowest code address. 1566 // This descriptor so far has the lowest code address.
1573 lowest_pc = rec.pc(); 1567 lowest_pc = iter.current_pc();
1574 lowest_pc_token_pos = desc_token_pos; 1568 lowest_pc_token_pos = desc_token_pos;
1575 } 1569 }
1576 } 1570 }
1577 } 1571 }
1578 if (lowest_pc_token_pos != INT_MAX) { 1572 if (lowest_pc_token_pos != INT_MAX) {
1579 // We found the pc descriptor that has the lowest execution address. 1573 // We found the pc descriptor that has the lowest execution address.
1580 // This is the first possible breakpoint after the requested token 1574 // This is the first possible breakpoint after the requested token
1581 // position. We use this instead of the nearest PC descriptor 1575 // position. We use this instead of the nearest PC descriptor
1582 // measured in token index distance. 1576 // measured in token index distance.
1583 return lowest_pc_token_pos; 1577 return lowest_pc_token_pos;
1584 } 1578 }
1585 if (best_fit_pos != INT_MAX) { 1579 if (best_fit_pos != INT_MAX) {
1586 return best_fit_pos; 1580 return best_fit_pos;
1587 } 1581 }
1588 // We didn't find a safe point in the given token range. Try and find 1582 // We didn't find a safe point in the given token range. Try and find
1589 // a safe point in the remaining source code of the function. 1583 // a safe point in the remaining source code of the function.
1590 if (last_token_pos < func.end_token_pos()) { 1584 if (last_token_pos < func.end_token_pos()) {
1591 return ResolveBreakpointPos(func, last_token_pos, func.end_token_pos()); 1585 return ResolveBreakpointPos(func, last_token_pos, func.end_token_pos());
1592 } 1586 }
1593 return -1; 1587 return -1;
1594 } 1588 }
1595 1589
1596 1590
1597 void Debugger::MakeCodeBreakpointAt(const Function& func, 1591 void Debugger::MakeCodeBreakpointAt(const Function& func,
1598 SourceBreakpoint* bpt) { 1592 SourceBreakpoint* bpt) {
1593 ASSERT(bpt->token_pos_ != Scanner::kNoSourcePos);
1599 ASSERT((bpt != NULL) && bpt->IsResolved()); 1594 ASSERT((bpt != NULL) && bpt->IsResolved());
1600 ASSERT(!func.HasOptimizedCode()); 1595 ASSERT(!func.HasOptimizedCode());
1601 Code& code = Code::Handle(func.unoptimized_code()); 1596 Code& code = Code::Handle(func.unoptimized_code());
1602 ASSERT(!code.IsNull()); 1597 ASSERT(!code.IsNull());
1603 PcDescriptors& desc = PcDescriptors::Handle(code.pc_descriptors()); 1598 PcDescriptors& desc = PcDescriptors::Handle(code.pc_descriptors());
1604 uword lowest_pc = kUwordMax; 1599 uword lowest_pc = kUwordMax;
1600 RawPcDescriptors::Kind lowest_kind = RawPcDescriptors::kAnyKind;
1605 // Find the safe point with the lowest compiled code address 1601 // Find the safe point with the lowest compiled code address
1606 // that maps to the token position of the source breakpoint. 1602 // that maps to the token position of the source breakpoint.
1607 PcDescriptors::Iterator iter(desc, kSafepointKind); 1603 PcDescriptors::Iterator iter(desc, kSafepointKind);
1608 RawPcDescriptors::PcDescriptorRec lowest_rec;
1609 while (iter.HasNext()) { 1604 while (iter.HasNext()) {
1610 RawPcDescriptors::PcDescriptorRec rec; 1605 intptr_t desc_token_pos = iter.NextTokenPos();
1611 iter.NextRec(&rec); 1606 if (desc_token_pos == bpt->token_pos_) {
1612 intptr_t desc_token_pos = rec.token_pos(); 1607 if (iter.current_pc() < lowest_pc) {
1613 if ((desc_token_pos == bpt->token_pos_) && HasTokenPos(rec)) { 1608 lowest_pc = iter.current_pc();
1614 if (rec.pc() < lowest_pc) { 1609 lowest_kind = iter.current_kind();
1615 lowest_pc = rec.pc();
1616 lowest_rec = rec;
1617 } 1610 }
1618 } 1611 }
1619 } 1612 }
1620 if (lowest_pc == kUwordMax) { 1613 if (lowest_pc == kUwordMax) {
1621 return; 1614 return;
1622 } 1615 }
1623 CodeBreakpoint* code_bpt = GetCodeBreakpoint(lowest_rec.pc()); 1616 CodeBreakpoint* code_bpt = GetCodeBreakpoint(lowest_pc);
1624 if (code_bpt == NULL) { 1617 if (code_bpt == NULL) {
1625 // No code breakpoint for this code exists; create one. 1618 // No code breakpoint for this code exists; create one.
1626 code_bpt = new CodeBreakpoint(code, lowest_rec); 1619 code_bpt = new CodeBreakpoint(code, bpt->token_pos_,
1620 lowest_pc, lowest_kind);
1627 RegisterCodeBreakpoint(code_bpt); 1621 RegisterCodeBreakpoint(code_bpt);
1628 } 1622 }
1629 code_bpt->set_src_bpt(bpt); 1623 code_bpt->set_src_bpt(bpt);
1630 if (bpt->IsEnabled()) { 1624 if (bpt->IsEnabled()) {
1631 code_bpt->Enable(); 1625 code_bpt->Enable();
1632 } 1626 }
1633 } 1627 }
1634 1628
1635 1629
1636 void Debugger::FindCompiledFunctions(const Script& script, 1630 void Debugger::FindCompiledFunctions(const Script& script,
(...skipping 941 matching lines...) Expand 10 before | Expand all | Expand 10 after
2578 } 2572 }
2579 2573
2580 2574
2581 void Debugger::RegisterCodeBreakpoint(CodeBreakpoint* bpt) { 2575 void Debugger::RegisterCodeBreakpoint(CodeBreakpoint* bpt) {
2582 ASSERT(bpt->next() == NULL); 2576 ASSERT(bpt->next() == NULL);
2583 bpt->set_next(code_breakpoints_); 2577 bpt->set_next(code_breakpoints_);
2584 code_breakpoints_ = bpt; 2578 code_breakpoints_ = bpt;
2585 } 2579 }
2586 2580
2587 } // namespace dart 2581 } // namespace dart
OLDNEW
« no previous file with comments | « runtime/vm/debugger.h ('k') | runtime/vm/object.h » ('j') | runtime/vm/object.h » ('J')

Powered by Google App Engine
This is Rietveld 408576698