OLD | NEW |
1 // Copyright 2008 the V8 project authors. All rights reserved. | 1 // Copyright 2008 the V8 project authors. All rights reserved. |
2 // Redistribution and use in source and binary forms, with or without | 2 // Redistribution and use in source and binary forms, with or without |
3 // modification, are permitted provided that the following conditions are | 3 // modification, are permitted provided that the following conditions are |
4 // met: | 4 // met: |
5 // | 5 // |
6 // * Redistributions of source code must retain the above copyright | 6 // * Redistributions of source code must retain the above copyright |
7 // notice, this list of conditions and the following disclaimer. | 7 // notice, this list of conditions and the following disclaimer. |
8 // * Redistributions in binary form must reproduce the above | 8 // * Redistributions in binary form must reproduce the above |
9 // copyright notice, this list of conditions and the following | 9 // copyright notice, this list of conditions and the following |
10 // disclaimer in the documentation and/or other materials provided | 10 // disclaimer in the documentation and/or other materials provided |
(...skipping 99 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
110 const kNoFrame = -1; | 110 const kNoFrame = -1; |
111 Debug.State = { | 111 Debug.State = { |
112 currentFrame: kNoFrame, | 112 currentFrame: kNoFrame, |
113 displaySourceStartLine: -1, | 113 displaySourceStartLine: -1, |
114 displaySourceEndLine: -1, | 114 displaySourceEndLine: -1, |
115 currentSourceLine: -1 | 115 currentSourceLine: -1 |
116 } | 116 } |
117 var trace_compile = false; // Tracing all compile events? | 117 var trace_compile = false; // Tracing all compile events? |
118 var trace_debug_json = false; // Tracing all debug json packets? | 118 var trace_debug_json = false; // Tracing all debug json packets? |
119 var last_cmd_line = ''; | 119 var last_cmd_line = ''; |
| 120 //var lol_is_enabled; // Set to true in d8.cc if LIVE_OBJECT_LIST is defined. |
| 121 var lol_next_dump_index = 0; |
| 122 const kDefaultLolLinesToPrintAtATime = 10; |
| 123 const kMaxLolLinesToPrintAtATime = 1000; |
120 var repeat_cmd_line = ''; | 124 var repeat_cmd_line = ''; |
121 var is_running = true; | 125 var is_running = true; |
122 | 126 |
123 // Copied from debug-delay.js. This is needed below: | 127 // Copied from debug-delay.js. This is needed below: |
124 function ScriptTypeFlag(type) { | 128 function ScriptTypeFlag(type) { |
125 return (1 << type); | 129 return (1 << type); |
126 } | 130 } |
127 | 131 |
128 | 132 |
129 // Process a debugger JSON message into a display text and a running status. | 133 // Process a debugger JSON message into a display text and a running status. |
(...skipping 358 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
488 this.traceCommand_(args); | 492 this.traceCommand_(args); |
489 break; | 493 break; |
490 | 494 |
491 case 'help': | 495 case 'help': |
492 case '?': | 496 case '?': |
493 this.helpCommand_(args); | 497 this.helpCommand_(args); |
494 // Return undefined to indicate command handled internally (no JSON). | 498 // Return undefined to indicate command handled internally (no JSON). |
495 this.request_ = void 0; | 499 this.request_ = void 0; |
496 break; | 500 break; |
497 | 501 |
| 502 case 'liveobjectlist': |
| 503 case 'lol': |
| 504 if (lol_is_enabled) { |
| 505 this.request_ = this.lolToJSONRequest_(args, is_repeating); |
| 506 break; |
| 507 } |
| 508 |
498 default: | 509 default: |
499 throw new Error('Unknown command "' + cmd + '"'); | 510 throw new Error('Unknown command "' + cmd + '"'); |
500 } | 511 } |
501 } | 512 } |
502 | 513 |
503 DebugRequest.prototype.JSONRequest = function() { | 514 DebugRequest.prototype.JSONRequest = function() { |
504 return this.request_; | 515 return this.request_; |
505 } | 516 } |
506 | 517 |
507 | 518 |
(...skipping 24 matching lines...) Expand all Loading... |
532 json += '}'; | 543 json += '}'; |
533 return json; | 544 return json; |
534 } | 545 } |
535 | 546 |
536 | 547 |
537 DebugRequest.prototype.createRequest = function(command) { | 548 DebugRequest.prototype.createRequest = function(command) { |
538 return new RequestPacket(command); | 549 return new RequestPacket(command); |
539 }; | 550 }; |
540 | 551 |
541 | 552 |
| 553 // Note: we use detected command repetition as a signal for continuation here. |
| 554 DebugRequest.prototype.createLOLRequest = function(command, |
| 555 start_index, |
| 556 lines_to_dump, |
| 557 is_continuation) { |
| 558 if (is_continuation) { |
| 559 start_index = lol_next_dump_index; |
| 560 } |
| 561 |
| 562 if (lines_to_dump) { |
| 563 lines_to_dump = parseInt(lines_to_dump); |
| 564 } else { |
| 565 lines_to_dump = kDefaultLolLinesToPrintAtATime; |
| 566 } |
| 567 if (lines_to_dump > kMaxLolLinesToPrintAtATime) { |
| 568 lines_to_dump = kMaxLolLinesToPrintAtATime; |
| 569 } |
| 570 |
| 571 // Save the next start_index to dump from: |
| 572 lol_next_dump_index = start_index + lines_to_dump; |
| 573 |
| 574 var request = this.createRequest(command); |
| 575 request.arguments = {}; |
| 576 request.arguments.start = start_index; |
| 577 request.arguments.count = lines_to_dump; |
| 578 |
| 579 return request; |
| 580 }; |
| 581 |
| 582 |
542 // Create a JSON request for the evaluation command. | 583 // Create a JSON request for the evaluation command. |
543 DebugRequest.prototype.makeEvaluateJSONRequest_ = function(expression) { | 584 DebugRequest.prototype.makeEvaluateJSONRequest_ = function(expression) { |
544 // Global varaible used to store whether a handle was requested. | 585 // Global varaible used to store whether a handle was requested. |
545 lookup_handle = null; | 586 lookup_handle = null; |
| 587 |
| 588 if (lol_is_enabled) { |
| 589 // Check if the expression is a obj id in the form @<obj id>. |
| 590 var obj_id_match = expression.match(/^@([0-9]+)$/); |
| 591 if (obj_id_match) { |
| 592 var obj_id = parseInt(obj_id_match[1]); |
| 593 // Build a dump request. |
| 594 var request = this.createRequest('getobj'); |
| 595 request.arguments = {}; |
| 596 request.arguments.obj_id = obj_id; |
| 597 return request.toJSONProtocol(); |
| 598 } |
| 599 } |
| 600 |
546 // Check if the expression is a handle id in the form #<handle>#. | 601 // Check if the expression is a handle id in the form #<handle>#. |
547 var handle_match = expression.match(/^#([0-9]*)#$/); | 602 var handle_match = expression.match(/^#([0-9]*)#$/); |
548 if (handle_match) { | 603 if (handle_match) { |
549 // Remember the handle requested in a global variable. | 604 // Remember the handle requested in a global variable. |
550 lookup_handle = parseInt(handle_match[1]); | 605 lookup_handle = parseInt(handle_match[1]); |
551 // Build a lookup request. | 606 // Build a lookup request. |
552 var request = this.createRequest('lookup'); | 607 var request = this.createRequest('lookup'); |
553 request.arguments = {}; | 608 request.arguments = {}; |
554 request.arguments.handles = [ lookup_handle ]; | 609 request.arguments.handles = [ lookup_handle ]; |
555 return request.toJSONProtocol(); | 610 return request.toJSONProtocol(); |
(...skipping 540 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1096 request = this.createRequest('listbreakpoints'); | 1151 request = this.createRequest('listbreakpoints'); |
1097 last_cmd = 'info break'; | 1152 last_cmd = 'info break'; |
1098 } else if (args && (args == 'locals' || args == 'lo')) { | 1153 } else if (args && (args == 'locals' || args == 'lo')) { |
1099 // Build a evaluate request from the text command. | 1154 // Build a evaluate request from the text command. |
1100 request = this.createRequest('frame'); | 1155 request = this.createRequest('frame'); |
1101 last_cmd = 'info locals'; | 1156 last_cmd = 'info locals'; |
1102 } else if (args && (args == 'args' || args == 'ar')) { | 1157 } else if (args && (args == 'args' || args == 'ar')) { |
1103 // Build a evaluate request from the text command. | 1158 // Build a evaluate request from the text command. |
1104 request = this.createRequest('frame'); | 1159 request = this.createRequest('frame'); |
1105 last_cmd = 'info args'; | 1160 last_cmd = 'info args'; |
| 1161 } else if (lol_is_enabled && |
| 1162 args && (args == 'liveobjectlist' || args == 'lol')) { |
| 1163 // Build a evaluate request from the text command. |
| 1164 return this.liveObjectListToJSONRequest_(null); |
1106 } else { | 1165 } else { |
1107 throw new Error('Invalid info arguments.'); | 1166 throw new Error('Invalid info arguments.'); |
1108 } | 1167 } |
1109 | 1168 |
1110 return request.toJSONProtocol(); | 1169 return request.toJSONProtocol(); |
1111 }; | 1170 }; |
1112 | 1171 |
1113 | 1172 |
1114 DebugRequest.prototype.v8FlagsToJSONRequest_ = function(args) { | 1173 DebugRequest.prototype.v8FlagsToJSONRequest_ = function(args) { |
1115 var request; | 1174 var request; |
(...skipping 30 matching lines...) Expand all Loading... |
1146 break; | 1205 break; |
1147 } | 1206 } |
1148 // Else fall thru to the default case below to report the error. | 1207 // Else fall thru to the default case below to report the error. |
1149 default: | 1208 default: |
1150 throw new Error('Missing arguments after ' + cmd + '.'); | 1209 throw new Error('Missing arguments after ' + cmd + '.'); |
1151 } | 1210 } |
1152 return request.toJSONProtocol(); | 1211 return request.toJSONProtocol(); |
1153 }; | 1212 }; |
1154 | 1213 |
1155 | 1214 |
| 1215 // Args: [v[erbose]] [<N>] [i[ndex] <i>] [t[ype] <type>] [sp[ace] <space>] |
| 1216 DebugRequest.prototype.lolMakeListRequest = |
| 1217 function(cmd, args, first_arg_index, is_repeating) { |
| 1218 |
| 1219 var request; |
| 1220 var start_index = 0; |
| 1221 var dump_limit = void 0; |
| 1222 var type_filter = void 0; |
| 1223 var space_filter = void 0; |
| 1224 var prop_filter = void 0; |
| 1225 var is_verbose = false; |
| 1226 var i; |
| 1227 |
| 1228 for (i = first_arg_index; i < args.length; i++) { |
| 1229 var arg = args[i]; |
| 1230 // Check for [v[erbose]]: |
| 1231 if (arg === 'verbose' || arg === 'v') { |
| 1232 // Nothing to do. This is already implied by args.length > 3. |
| 1233 is_verbose = true; |
| 1234 |
| 1235 // Check for [<N>]: |
| 1236 } else if (arg.match(/^[0-9]+$/)) { |
| 1237 dump_limit = arg; |
| 1238 is_verbose = true; |
| 1239 |
| 1240 // Check for i[ndex] <i>: |
| 1241 } else if (arg === 'index' || arg === 'i') { |
| 1242 i++; |
| 1243 if (args.length < i) { |
| 1244 throw new Error('Missing index after ' + arg + '.'); |
| 1245 } |
| 1246 start_index = parseInt(args[i]); |
| 1247 // The user input start index starts at 1: |
| 1248 if (start_index <= 0) { |
| 1249 throw new Error('Invalid index ' + args[i] + '.'); |
| 1250 } |
| 1251 start_index -= 1; |
| 1252 is_verbose = true; |
| 1253 |
| 1254 // Check for t[ype] <type>: |
| 1255 } else if (arg === 'type' || arg === 't') { |
| 1256 i++; |
| 1257 if (args.length < i) { |
| 1258 throw new Error('Missing type after ' + arg + '.'); |
| 1259 } |
| 1260 type_filter = args[i]; |
| 1261 |
| 1262 // Check for space <heap space name>: |
| 1263 } else if (arg === 'space' || arg === 'sp') { |
| 1264 i++; |
| 1265 if (args.length < i) { |
| 1266 throw new Error('Missing space name after ' + arg + '.'); |
| 1267 } |
| 1268 space_filter = args[i]; |
| 1269 |
| 1270 // Check for property <prop name>: |
| 1271 } else if (arg === 'property' || arg === 'prop') { |
| 1272 i++; |
| 1273 if (args.length < i) { |
| 1274 throw new Error('Missing property name after ' + arg + '.'); |
| 1275 } |
| 1276 prop_filter = args[i]; |
| 1277 |
| 1278 } else { |
| 1279 throw new Error('Unknown args at ' + arg + '.'); |
| 1280 } |
| 1281 } |
| 1282 |
| 1283 // Build the verbose request: |
| 1284 if (is_verbose) { |
| 1285 request = this.createLOLRequest('lol-'+cmd, |
| 1286 start_index, |
| 1287 dump_limit, |
| 1288 is_repeating); |
| 1289 request.arguments.verbose = true; |
| 1290 } else { |
| 1291 request = this.createRequest('lol-'+cmd); |
| 1292 request.arguments = {}; |
| 1293 } |
| 1294 |
| 1295 request.arguments.filter = {}; |
| 1296 if (type_filter) { |
| 1297 request.arguments.filter.type = type_filter; |
| 1298 } |
| 1299 if (space_filter) { |
| 1300 request.arguments.filter.space = space_filter; |
| 1301 } |
| 1302 if (prop_filter) { |
| 1303 request.arguments.filter.prop = prop_filter; |
| 1304 } |
| 1305 |
| 1306 return request; |
| 1307 } |
| 1308 |
| 1309 |
| 1310 function extractObjId(args) { |
| 1311 var id = args; |
| 1312 id = id.match(/^@([0-9]+)$/); |
| 1313 if (id) { |
| 1314 id = id[1]; |
| 1315 } else { |
| 1316 throw new Error('Invalid obj id ' + args + '.'); |
| 1317 } |
| 1318 return parseInt(id); |
| 1319 } |
| 1320 |
| 1321 |
| 1322 DebugRequest.prototype.lolToJSONRequest_ = function(args, is_repeating) { |
| 1323 var request; |
| 1324 // Use default command if one is not specified: |
| 1325 if (!args) { |
| 1326 args = 'info'; |
| 1327 } |
| 1328 |
| 1329 var orig_args = args; |
| 1330 var first_arg_index; |
| 1331 |
| 1332 var arg, i; |
| 1333 var args = args.split(/\s+/g); |
| 1334 var cmd = args[0]; |
| 1335 var id; |
| 1336 |
| 1337 // Command: <id> [v[erbose]] ... |
| 1338 if (cmd.match(/^[0-9]+$/)) { |
| 1339 // Convert to the padded list command: |
| 1340 // Command: l[ist] <dummy> <id> [v[erbose]] ... |
| 1341 |
| 1342 // Insert the implicit 'list' in front and process as normal: |
| 1343 cmd = 'list'; |
| 1344 args.unshift(cmd); |
| 1345 } |
| 1346 |
| 1347 switch(cmd) { |
| 1348 // Command: c[apture] |
| 1349 case 'capture': |
| 1350 case 'c': |
| 1351 request = this.createRequest('lol-capture'); |
| 1352 break; |
| 1353 |
| 1354 // Command: clear|d[elete] <id>|all |
| 1355 case 'clear': |
| 1356 case 'delete': |
| 1357 case 'del': { |
| 1358 if (args.length < 2) { |
| 1359 throw new Error('Missing argument after ' + cmd + '.'); |
| 1360 } else if (args.length > 2) { |
| 1361 throw new Error('Too many arguments after ' + cmd + '.'); |
| 1362 } |
| 1363 id = args[1]; |
| 1364 if (id.match(/^[0-9]+$/)) { |
| 1365 // Delete a specific lol record: |
| 1366 request = this.createRequest('lol-delete'); |
| 1367 request.arguments = {}; |
| 1368 request.arguments.id = parseInt(id); |
| 1369 } else if (id === 'all') { |
| 1370 // Delete all: |
| 1371 request = this.createRequest('lol-reset'); |
| 1372 } else { |
| 1373 throw new Error('Invalid argument after ' + cmd + '.'); |
| 1374 } |
| 1375 break; |
| 1376 } |
| 1377 |
| 1378 // Command: diff <id1> <id2> [<dump options>] |
| 1379 case 'diff': |
| 1380 first_arg_index = 3; |
| 1381 |
| 1382 // Command: list <dummy> <id> [<dump options>] |
| 1383 case 'list': |
| 1384 |
| 1385 // Command: ret[ainers] <obj id> [<dump options>] |
| 1386 case 'retainers': |
| 1387 case 'ret': |
| 1388 case 'retaining-paths': |
| 1389 case 'rp': { |
| 1390 if (cmd === 'ret') cmd = 'retainers'; |
| 1391 else if (cmd === 'rp') cmd = 'retaining-paths'; |
| 1392 |
| 1393 if (!first_arg_index) first_arg_index = 2; |
| 1394 |
| 1395 if (args.length < first_arg_index) { |
| 1396 throw new Error('Too few arguments after ' + cmd + '.'); |
| 1397 } |
| 1398 |
| 1399 var request_cmd = (cmd === 'list') ? 'diff':cmd; |
| 1400 request = this.lolMakeListRequest(request_cmd, |
| 1401 args, |
| 1402 first_arg_index, |
| 1403 is_repeating); |
| 1404 |
| 1405 if (cmd === 'diff') { |
| 1406 request.arguments.id1 = parseInt(args[1]); |
| 1407 request.arguments.id2 = parseInt(args[2]); |
| 1408 } else if (cmd == 'list') { |
| 1409 request.arguments.id1 = 0; |
| 1410 request.arguments.id2 = parseInt(args[1]); |
| 1411 } else { |
| 1412 request.arguments.id = extractObjId(args[1]); |
| 1413 } |
| 1414 break; |
| 1415 } |
| 1416 |
| 1417 // Command: getid |
| 1418 case 'getid': { |
| 1419 request = this.createRequest('lol-getid'); |
| 1420 request.arguments = {}; |
| 1421 request.arguments.address = args[1]; |
| 1422 break; |
| 1423 } |
| 1424 |
| 1425 // Command: inf[o] [<N>] |
| 1426 case 'info': |
| 1427 case 'inf': { |
| 1428 if (args.length > 2) { |
| 1429 throw new Error('Too many arguments after ' + cmd + '.'); |
| 1430 } |
| 1431 // Built the info request: |
| 1432 request = this.createLOLRequest('lol-info', 0, args[1], is_repeating); |
| 1433 break; |
| 1434 } |
| 1435 |
| 1436 // Command: path <obj id 1> <obj id 2> |
| 1437 case 'path': { |
| 1438 request = this.createRequest('lol-path'); |
| 1439 request.arguments = {}; |
| 1440 if (args.length > 2) { |
| 1441 request.arguments.id1 = extractObjId(args[1]); |
| 1442 request.arguments.id2 = extractObjId(args[2]); |
| 1443 } else { |
| 1444 request.arguments.id1 = 0; |
| 1445 request.arguments.id2 = extractObjId(args[1]); |
| 1446 } |
| 1447 break; |
| 1448 } |
| 1449 |
| 1450 // Command: print |
| 1451 case 'print': { |
| 1452 request = this.createRequest('lol-print'); |
| 1453 request.arguments = {}; |
| 1454 request.arguments.id = extractObjId(args[1]); |
| 1455 break; |
| 1456 } |
| 1457 |
| 1458 // Command: reset |
| 1459 case 'reset': { |
| 1460 request = this.createRequest('lol-reset'); |
| 1461 break; |
| 1462 } |
| 1463 |
| 1464 default: |
| 1465 throw new Error('Invalid arguments.'); |
| 1466 } |
| 1467 return request.toJSONProtocol(); |
| 1468 }; |
| 1469 |
| 1470 |
1156 // Create a JSON request for the threads command. | 1471 // Create a JSON request for the threads command. |
1157 DebugRequest.prototype.threadsCommandToJSONRequest_ = function(args) { | 1472 DebugRequest.prototype.threadsCommandToJSONRequest_ = function(args) { |
1158 // Build a threads request from the text command. | 1473 // Build a threads request from the text command. |
1159 var request = this.createRequest('threads'); | 1474 var request = this.createRequest('threads'); |
1160 return request.toJSONProtocol(); | 1475 return request.toJSONProtocol(); |
1161 }; | 1476 }; |
1162 | 1477 |
1163 | 1478 |
1164 // Handle the trace command. | 1479 // Handle the trace command. |
1165 DebugRequest.prototype.traceCommand_ = function(args) { | 1480 DebugRequest.prototype.traceCommand_ = function(args) { |
(...skipping 66 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1232 print('set <var> = <expression> - executes the specified statement'); | 1547 print('set <var> = <expression> - executes the specified statement'); |
1233 print(''); | 1548 print(''); |
1234 print('l[ist] - list the source code around for the curren
t pc'); | 1549 print('l[ist] - list the source code around for the curren
t pc'); |
1235 print('l[ist] [- | <start>,<end>] - list the specified range of source code'); | 1550 print('l[ist] [- | <start>,<end>] - list the specified range of source code'); |
1236 print('source [from line [num lines]]'); | 1551 print('source [from line [num lines]]'); |
1237 print('scr[ipts] [native|extensions|all]'); | 1552 print('scr[ipts] [native|extensions|all]'); |
1238 print('scr[ipts] [<filter text>] - list scripts with the specified text in it
s description'); | 1553 print('scr[ipts] [<filter text>] - list scripts with the specified text in it
s description'); |
1239 print(''); | 1554 print(''); |
1240 print('gc - runs the garbage collector'); | 1555 print('gc - runs the garbage collector'); |
1241 print(''); | 1556 print(''); |
| 1557 |
| 1558 if (lol_is_enabled) { |
| 1559 print('liveobjectlist|lol <command> - live object list tracking.'); |
| 1560 print(' where <command> can be:'); |
| 1561 print(' c[apture] - captures a LOL list.'); |
| 1562 print(' clear|del[ete] <id>|all - clears LOL of id <id>.'); |
| 1563 print(' If \'all\' is unspecified instead, will c
lear all.'); |
| 1564 print(' diff <id1> <id2> [<dump options>]'); |
| 1565 print(' - prints the diff between LOLs id1 and id2.
'); |
| 1566 print(' - also see <dump options> below.'); |
| 1567 print(' getid <address> - gets the obj id for the specified address
if available.'); |
| 1568 print(' The address must be in hex form prefixed
with 0x.'); |
| 1569 print(' inf[o] [<N>] - lists summary info of all LOL lists.'); |
| 1570 print(' If N is specified, will print N items at
a time.'); |
| 1571 print(' [l[ist]] <id> [<dump options>]'); |
| 1572 print(' - prints the listing of objects in LOL id.'
); |
| 1573 print(' - also see <dump options> below.'); |
| 1574 print(' reset - clears all LOL lists.'); |
| 1575 print(' ret[ainers] <id> [<dump options>]'); |
| 1576 print(' - prints the list of retainers of obj id.')
; |
| 1577 print(' - also see <dump options> below.'); |
| 1578 print(' path <id1> <id2> - prints the retaining path from obj id1 to
id2.'); |
| 1579 print(' If only one id is specified, will print t
he path from'); |
| 1580 print(' roots to the specified object if availabl
e.'); |
| 1581 print(' print <id> - prints the obj for the specified obj id i
f available.'); |
| 1582 print(''); |
| 1583 print(' <dump options> includes:'); |
| 1584 print(' [v[erbose]] - do verbose dump.'); |
| 1585 print(' [<N>] - dump N items at a time. Implies verbos
e dump.'); |
| 1586 print(' If unspecified, N will default to '+ |
| 1587 kDefaultLolLinesToPrintAtATime+'. Max N is '+ |
| 1588 kMaxLolLinesToPrintAtATime+'.'); |
| 1589 print(' [i[ndex] <i>] - start dump from index i. Implies verbo
se dump.'); |
| 1590 print(' [t[ype] <type>] - filter by type.'); |
| 1591 print(' [sp[ace] <space name>] - filter by heap space where <space name>
is one of'); |
| 1592 print(' { cell, code, lo, map, new, old-data, o
ld-pointer }.'); |
| 1593 print(''); |
| 1594 print(' If the verbose option, or an option that implies a verbose dump'
); |
| 1595 print(' is specified, then a verbose dump will requested. Else, a summa
ry dump'); |
| 1596 print(' will be requested.'); |
| 1597 print(''); |
| 1598 } |
| 1599 |
1242 print('trace compile'); | 1600 print('trace compile'); |
1243 // hidden command: trace debug json - toggles tracing of debug json packets | 1601 // hidden command: trace debug json - toggles tracing of debug json packets |
1244 print(''); | 1602 print(''); |
1245 print('disconnect|exit|quit - disconnects and quits the debugger'); | 1603 print('disconnect|exit|quit - disconnects and quits the debugger'); |
1246 print('help - prints this help information'); | 1604 print('help - prints this help information'); |
1247 } | 1605 } |
1248 | 1606 |
1249 | 1607 |
1250 function formatHandleReference_(value) { | 1608 function formatHandleReference_(value) { |
1251 if (value.handle() >= 0) { | 1609 if (value.handle() >= 0) { |
(...skipping 80 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1332 result = '"' + value.value() + '"'; | 1690 result = '"' + value.value() + '"'; |
1333 } else if (value.isPrimitive()) { | 1691 } else if (value.isPrimitive()) { |
1334 result = value.valueString(); | 1692 result = value.valueString(); |
1335 } else if (value.isObject()) { | 1693 } else if (value.isObject()) { |
1336 result += formatObject_(value, true); | 1694 result += formatObject_(value, true); |
1337 } | 1695 } |
1338 return result; | 1696 return result; |
1339 } | 1697 } |
1340 | 1698 |
1341 | 1699 |
| 1700 function decodeLolCaptureResponse(body) { |
| 1701 var result; |
| 1702 result = 'Captured live object list '+ body.id + |
| 1703 ': count '+ body.count + ' size ' + body.size; |
| 1704 return result; |
| 1705 } |
| 1706 |
| 1707 |
| 1708 function decodeLolDeleteResponse(body) { |
| 1709 var result; |
| 1710 result = 'Deleted live object list '+ body.id; |
| 1711 return result; |
| 1712 } |
| 1713 |
| 1714 |
| 1715 function digitsIn(value) { |
| 1716 var digits = 0; |
| 1717 if (value === 0) value = 1; |
| 1718 while (value >= 1) { |
| 1719 digits++; |
| 1720 value /= 10; |
| 1721 } |
| 1722 return digits; |
| 1723 } |
| 1724 |
| 1725 |
| 1726 function padding(value, max_digits) { |
| 1727 var padding_digits = max_digits - digitsIn(value); |
| 1728 var padding = ''; |
| 1729 while (padding_digits > 0) { |
| 1730 padding += ' '; |
| 1731 padding_digits--; |
| 1732 } |
| 1733 return padding; |
| 1734 } |
| 1735 |
| 1736 |
| 1737 function decodeLolInfoResponse(body) { |
| 1738 var result; |
| 1739 var lists = body.lists; |
| 1740 var length = lists.length; |
| 1741 var first_index = body.first_index + 1; |
| 1742 var has_more = ((first_index + length) <= body.count); |
| 1743 result = 'captured live object lists'; |
| 1744 if (has_more || (first_index != 1)) { |
| 1745 result += ' ['+ length +' of '+ body.count + |
| 1746 ': starting from '+ first_index +']'; |
| 1747 } |
| 1748 result += ':\n'; |
| 1749 var max_digits = digitsIn(body.count); |
| 1750 var last_count = 0; |
| 1751 var last_size = 0; |
| 1752 for (var i = 0; i < length; i++) { |
| 1753 var entry = lists[i]; |
| 1754 var count = entry.count; |
| 1755 var size = entry.size; |
| 1756 var index = first_index + i; |
| 1757 result += ' [' + padding(index, max_digits) + index + '] id '+ entry.id + |
| 1758 ': count '+ count; |
| 1759 if (last_count > 0) { |
| 1760 result += '(+' + (count - last_count) + ')'; |
| 1761 } |
| 1762 result += ' size '+ size; |
| 1763 if (last_size > 0) { |
| 1764 result += '(+' + (size - last_size) + ')'; |
| 1765 } |
| 1766 result += '\n'; |
| 1767 last_count = count; |
| 1768 last_size = size; |
| 1769 } |
| 1770 result += ' total: '+length+' lists\n'; |
| 1771 if (has_more) { |
| 1772 result += ' -- press <enter> for more --\n'; |
| 1773 } else { |
| 1774 repeat_cmd_line = ''; |
| 1775 } |
| 1776 if (length === 0) result += ' none\n'; |
| 1777 |
| 1778 return result; |
| 1779 } |
| 1780 |
| 1781 |
| 1782 function decodeLolListResponse(body, title) { |
| 1783 |
| 1784 var result; |
| 1785 var total_count = body.count; |
| 1786 var total_size = body.size; |
| 1787 var length; |
| 1788 var max_digits; |
| 1789 var i; |
| 1790 var entry; |
| 1791 var index; |
| 1792 |
| 1793 var max_count_digits = digitsIn(total_count); |
| 1794 var max_size_digits; |
| 1795 |
| 1796 var summary = body.summary; |
| 1797 if (summary) { |
| 1798 |
| 1799 var roots_count = 0; |
| 1800 var found_root = body.found_root || 0; |
| 1801 var found_weak_root = body.found_weak_root || 0; |
| 1802 |
| 1803 // Print the summary result: |
| 1804 result = 'summary of objects:\n'; |
| 1805 length = summary.length; |
| 1806 if (found_root !== 0) { |
| 1807 roots_count++; |
| 1808 } |
| 1809 if (found_weak_root !== 0) { |
| 1810 roots_count++; |
| 1811 } |
| 1812 max_digits = digitsIn(length + roots_count); |
| 1813 max_size_digits = digitsIn(total_size); |
| 1814 |
| 1815 index = 1; |
| 1816 if (found_root !== 0) { |
| 1817 result += ' [' + padding(index, max_digits) + index + '] ' + |
| 1818 ' count '+ 1 + padding(0, max_count_digits) + |
| 1819 ' '+ padding(0, max_size_digits+1) + |
| 1820 ' : <root>\n'; |
| 1821 index++; |
| 1822 } |
| 1823 if (found_weak_root !== 0) { |
| 1824 result += ' [' + padding(index, max_digits) + index + '] ' + |
| 1825 ' count '+ 1 + padding(0, max_count_digits) + |
| 1826 ' '+ padding(0, max_size_digits+1) + |
| 1827 ' : <weak root>\n'; |
| 1828 index++; |
| 1829 } |
| 1830 |
| 1831 for (i = 0; i < length; i++) { |
| 1832 entry = summary[i]; |
| 1833 var count = entry.count; |
| 1834 var size = entry.size; |
| 1835 result += ' [' + padding(index, max_digits) + index + '] ' + |
| 1836 ' count '+ count + padding(count, max_count_digits) + |
| 1837 ' size '+ size + padding(size, max_size_digits) + |
| 1838 ' : <' + entry.desc + '>\n'; |
| 1839 index++; |
| 1840 } |
| 1841 result += '\n total count: '+(total_count+roots_count)+'\n'; |
| 1842 if (body.size) { |
| 1843 result += ' total size: '+body.size+'\n'; |
| 1844 } |
| 1845 |
| 1846 } else { |
| 1847 // Print the full dump result: |
| 1848 var first_index = body.first_index + 1; |
| 1849 var elements = body.elements; |
| 1850 length = elements.length; |
| 1851 var has_more = ((first_index + length) <= total_count); |
| 1852 result = title; |
| 1853 if (has_more || (first_index != 1)) { |
| 1854 result += ' ['+ length +' of '+ total_count + |
| 1855 ': starting from '+ first_index +']'; |
| 1856 } |
| 1857 result += ':\n'; |
| 1858 if (length === 0) result += ' none\n'; |
| 1859 max_digits = digitsIn(length); |
| 1860 |
| 1861 var max_id = 0; |
| 1862 var max_size = 0; |
| 1863 for (i = 0; i < length; i++) { |
| 1864 entry = elements[i]; |
| 1865 if (entry.id > max_id) max_id = entry.id; |
| 1866 if (entry.size > max_size) max_size = entry.size; |
| 1867 } |
| 1868 var max_id_digits = digitsIn(max_id); |
| 1869 max_size_digits = digitsIn(max_size); |
| 1870 |
| 1871 for (i = 0; i < length; i++) { |
| 1872 entry = elements[i]; |
| 1873 index = first_index + i; |
| 1874 result += ' ['+ padding(index, max_digits) + index +']'; |
| 1875 if (entry.id !== 0) { |
| 1876 result += ' @' + entry.id + padding(entry.id, max_id_digits) + |
| 1877 ': size ' + entry.size + ', ' + |
| 1878 padding(entry.size, max_size_digits) + entry.desc + '\n'; |
| 1879 } else { |
| 1880 // Must be a root or weak root: |
| 1881 result += ' ' + entry.desc + '\n'; |
| 1882 } |
| 1883 } |
| 1884 if (has_more) { |
| 1885 result += ' -- press <enter> for more --\n'; |
| 1886 } else { |
| 1887 repeat_cmd_line = ''; |
| 1888 } |
| 1889 if (length === 0) result += ' none\n'; |
| 1890 } |
| 1891 |
| 1892 return result; |
| 1893 } |
| 1894 |
| 1895 |
| 1896 function decodeLolDiffResponse(body) { |
| 1897 var title = 'objects'; |
| 1898 return decodeLolListResponse(body, title); |
| 1899 } |
| 1900 |
| 1901 |
| 1902 function decodeLolRetainersResponse(body) { |
| 1903 var title = 'retainers for @' + body.id; |
| 1904 return decodeLolListResponse(body, title); |
| 1905 } |
| 1906 |
| 1907 |
| 1908 function decodeLolPathResponse(body) { |
| 1909 return body.path; |
| 1910 } |
| 1911 |
| 1912 |
| 1913 function decodeLolResetResponse(body) { |
| 1914 return 'Reset all live object lists.'; |
| 1915 } |
| 1916 |
| 1917 |
| 1918 function decodeLolGetIdResponse(body) { |
| 1919 if (body.id == 0) { |
| 1920 return 'Address is invalid, or object has been moved or collected'; |
| 1921 } |
| 1922 return 'obj id is @' + body.id; |
| 1923 } |
| 1924 |
| 1925 |
| 1926 function decodeLolPrintResponse(body) { |
| 1927 return body.dump; |
| 1928 } |
| 1929 |
| 1930 |
1342 // Rounds number 'num' to 'length' decimal places. | 1931 // Rounds number 'num' to 'length' decimal places. |
1343 function roundNumber(num, length) { | 1932 function roundNumber(num, length) { |
1344 var factor = Math.pow(10, length); | 1933 var factor = Math.pow(10, length); |
1345 return Math.round(num * factor) / factor; | 1934 return Math.round(num * factor) / factor; |
1346 } | 1935 } |
1347 | 1936 |
1348 | 1937 |
1349 // Convert a JSON response to text for display in a text based debugger. | 1938 // Convert a JSON response to text for display in a text based debugger. |
1350 function DebugResponseDetails(response) { | 1939 function DebugResponseDetails(response) { |
1351 details = {text:'', running:false} | 1940 details = {text:'', running:false} |
(...skipping 151 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1503 case 'scope': | 2092 case 'scope': |
1504 result += formatScope_(body); | 2093 result += formatScope_(body); |
1505 result += '\n'; | 2094 result += '\n'; |
1506 var scope_object_value = response.lookup(body.object.ref); | 2095 var scope_object_value = response.lookup(body.object.ref); |
1507 result += formatObject_(scope_object_value, true); | 2096 result += formatObject_(scope_object_value, true); |
1508 details.text = result; | 2097 details.text = result; |
1509 break; | 2098 break; |
1510 | 2099 |
1511 case 'evaluate': | 2100 case 'evaluate': |
1512 case 'lookup': | 2101 case 'lookup': |
| 2102 case 'getobj': |
1513 if (last_cmd == 'p' || last_cmd == 'print') { | 2103 if (last_cmd == 'p' || last_cmd == 'print') { |
1514 result = body.text; | 2104 result = body.text; |
1515 } else { | 2105 } else { |
1516 var value; | 2106 var value; |
1517 if (lookup_handle) { | 2107 if (lookup_handle) { |
1518 value = response.bodyValue(lookup_handle); | 2108 value = response.bodyValue(lookup_handle); |
1519 } else { | 2109 } else { |
1520 value = response.bodyValue(); | 2110 value = response.bodyValue(); |
1521 } | 2111 } |
1522 if (value.isObject()) { | 2112 if (value.isObject()) { |
(...skipping 141 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1664 details.text += | 2254 details.text += |
1665 " (" + roundNumber(body.before/(1024*1024), 1) + "M => " + | 2255 " (" + roundNumber(body.before/(1024*1024), 1) + "M => " + |
1666 roundNumber(body.after/(1024*1024), 1) + "M)"; | 2256 roundNumber(body.after/(1024*1024), 1) + "M)"; |
1667 } else if (body.after > 1024) { | 2257 } else if (body.after > 1024) { |
1668 details.text += | 2258 details.text += |
1669 " (" + roundNumber(body.before/1024, 1) + "K => " + | 2259 " (" + roundNumber(body.before/1024, 1) + "K => " + |
1670 roundNumber(body.after/1024, 1) + "K)"; | 2260 roundNumber(body.after/1024, 1) + "K)"; |
1671 } | 2261 } |
1672 break; | 2262 break; |
1673 | 2263 |
| 2264 case 'lol-capture': |
| 2265 details.text = decodeLolCaptureResponse(body); |
| 2266 break; |
| 2267 case 'lol-delete': |
| 2268 details.text = decodeLolDeleteResponse(body); |
| 2269 break; |
| 2270 case 'lol-diff': |
| 2271 details.text = decodeLolDiffResponse(body); |
| 2272 break; |
| 2273 case 'lol-getid': |
| 2274 details.text = decodeLolGetIdResponse(body); |
| 2275 break; |
| 2276 case 'lol-info': |
| 2277 details.text = decodeLolInfoResponse(body); |
| 2278 break; |
| 2279 case 'lol-print': |
| 2280 details.text = decodeLolPrintResponse(body); |
| 2281 break; |
| 2282 case 'lol-reset': |
| 2283 details.text = decodeLolResetResponse(body); |
| 2284 break; |
| 2285 case 'lol-retainers': |
| 2286 details.text = decodeLolRetainersResponse(body); |
| 2287 break; |
| 2288 case 'lol-path': |
| 2289 details.text = decodeLolPathResponse(body); |
| 2290 break; |
| 2291 |
1674 default: | 2292 default: |
1675 details.text = | 2293 details.text = |
1676 'Response for unknown command \'' + response.command() + '\'' + | 2294 'Response for unknown command \'' + response.command() + '\'' + |
1677 ' (' + response.raw_json() + ')'; | 2295 ' (' + response.raw_json() + ')'; |
1678 } | 2296 } |
1679 } catch (e) { | 2297 } catch (e) { |
1680 details.text = 'Error: "' + e + '" formatting response'; | 2298 details.text = 'Error: "' + e + '" formatting response'; |
1681 } | 2299 } |
1682 | 2300 |
1683 return details; | 2301 return details; |
(...skipping 487 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2171 json += NumberToJSON_(elem); | 2789 json += NumberToJSON_(elem); |
2172 } else if (typeof(elem) === 'string') { | 2790 } else if (typeof(elem) === 'string') { |
2173 json += StringToJSON_(elem); | 2791 json += StringToJSON_(elem); |
2174 } else { | 2792 } else { |
2175 json += elem; | 2793 json += elem; |
2176 } | 2794 } |
2177 } | 2795 } |
2178 json += ']'; | 2796 json += ']'; |
2179 return json; | 2797 return json; |
2180 } | 2798 } |
OLD | NEW |