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

Unified Diff: runtime/observatory/lib/src/elements/debugger.dart

Issue 1232193003: Provide stdout and stderr output in the Observatory debugger. (Closed) Base URL: git@github.com:dart-lang/sdk.git@master
Patch Set: before commit Created 5 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 side-by-side diff with in-line comments
Download patch
« no previous file with comments | « runtime/observatory/lib/service.dart ('k') | runtime/observatory/lib/src/elements/debugger.html » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: runtime/observatory/lib/src/elements/debugger.dart
diff --git a/runtime/observatory/lib/src/elements/debugger.dart b/runtime/observatory/lib/src/elements/debugger.dart
index 7b9bc053afd758eb68d056b57e69fc6e6e41e3b7..a11f046e66d5616d4b669b5be9bcde23239f5564 100644
--- a/runtime/observatory/lib/src/elements/debugger.dart
+++ b/runtime/observatory/lib/src/elements/debugger.dart
@@ -854,6 +854,67 @@ class RefreshCommand extends DebuggerCommand {
'Syntax: refresh <subcommand>\n';
}
+class _VMStreamPrinter {
+ ObservatoryDebugger _debugger;
+
+ _VMStreamPrinter(this._debugger);
+
+ String _savedStream;
+ String _savedIsolate;
+ String _savedLine;
+ List<String> _buffer = [];
+
+ void onEvent(String streamName, ServiceEvent event) {
+ String isolateName = event.isolate.name;
+ // If we get a line from a different isolate/stream, flush
+ // any pending output, even if it is not newline-terminated.
+ if ((_savedIsolate != null && isolateName != _savedIsolate) ||
+ (_savedStream != null && streamName != _savedStream)) {
+ flush();
+ }
+ String data = event.bytesAsString;
+ bool hasNewline = data.endsWith('\n');
+ if (_savedLine != null) {
+ data = _savedLine + data;
+ _savedIsolate = null;
+ _savedStream = null;
+ _savedLine = null;
+ }
+ var lines = data.split('\n').where((line) => line != '').toList();
+ if (lines.isEmpty) {
+ return;
+ }
+ int limit = (hasNewline ? lines.length : lines.length - 1);
+ for (int i = 0; i < limit; i++) {
+ _buffer.add(_format(isolateName, streamName, lines[i]));
+ }
+ // If there is no newline, we save the last line of output for next time.
+ if (!hasNewline) {
+ _savedIsolate = isolateName;
+ _savedStream = streamName;
+ _savedLine = lines[lines.length - 1];
+ }
+ }
+
+ void flush() {
+ // If there is any saved output, flush it now.
+ if (_savedLine != null) {
+ _buffer.add(_format(_savedIsolate, _savedStream, _savedLine));
+ _savedIsolate = null;
+ _savedStream = null;
+ _savedLine = null;
+ }
+ if (_buffer.isNotEmpty) {
+ _debugger.console.printStdio(_buffer);
+ _buffer.clear();
+ }
+ }
+
+ String _format(String isolateName, String streamName, String line) {
+ return '${isolateName}:${streamName}> ${line}';
+ }
+}
+
// Tracks the state for an isolate debugging session.
class ObservatoryDebugger extends Debugger {
RootCommand cmd;
@@ -898,6 +959,7 @@ class ObservatoryDebugger extends Debugger {
new IsolateCommand(this),
new RefreshCommand(this),
]);
+ _stdioPrinter = new _VMStreamPrinter(this);
}
VM get vm => page.app.vm;
@@ -997,6 +1059,7 @@ class ObservatoryDebugger extends Debugger {
}
void reportStatus() {
+ flushStdio();
if (_isolate == null) {
console.print('No current isolate');
} else if (_isolate.idle) {
@@ -1116,6 +1179,7 @@ class ObservatoryDebugger extends Debugger {
case ServiceEvent.kPauseException:
if (event.owner == isolate) {
_refreshStack(event).then((_) {
+ flushStdio();
_reportPause(event);
});
}
@@ -1123,6 +1187,7 @@ class ObservatoryDebugger extends Debugger {
case ServiceEvent.kResume:
if (event.owner == isolate) {
+ flushStdio();
console.print('Continuing...');
}
break;
@@ -1147,6 +1212,20 @@ class ObservatoryDebugger extends Debugger {
}
}
+ _VMStreamPrinter _stdioPrinter;
+
+ void flushStdio() {
+ _stdioPrinter.flush();
+ }
+
+ void onStdout(ServiceEvent event) {
+ _stdioPrinter.onEvent('stdout', event);
+ }
+
+ void onStderr(ServiceEvent event) {
+ _stdioPrinter.onEvent('stderr', event);
+ }
+
static String _commonPrefix(String a, String b) {
int pos = 0;
while (pos < a.length && pos < b.length) {
@@ -1236,6 +1315,8 @@ class DebuggerPageElement extends ObservatoryElement {
Future<StreamSubscription> _isolateSubscriptionFuture;
Future<StreamSubscription> _debugSubscriptionFuture;
+ Future<StreamSubscription> _stdoutSubscriptionFuture;
+ Future<StreamSubscription> _stderrSubscriptionFuture;
@override
void attached() {
@@ -1269,6 +1350,13 @@ class DebuggerPageElement extends ObservatoryElement {
app.vm.listenEventStream(VM.kIsolateStream, debugger.onEvent);
_debugSubscriptionFuture =
app.vm.listenEventStream(VM.kDebugStream, debugger.onEvent);
+ _stdoutSubscriptionFuture =
+ app.vm.listenEventStream(VM.kStdoutStream, debugger.onStdout);
+ _stderrSubscriptionFuture =
+ app.vm.listenEventStream(VM.kStderrStream, debugger.onStderr);
+
+ // Turn on the periodic poll timer for this page.
+ pollPeriod = const Duration(milliseconds:100);
onClick.listen((event) {
// Random clicks should focus on the text box. If the user selects
@@ -1280,12 +1368,20 @@ class DebuggerPageElement extends ObservatoryElement {
});
}
+ void onPoll() {
+ debugger.flushStdio();
+ }
+
@override
void detached() {
cancelFutureSubscription(_isolateSubscriptionFuture);
_isolateSubscriptionFuture = null;
cancelFutureSubscription(_debugSubscriptionFuture);
_debugSubscriptionFuture = null;
+ cancelFutureSubscription(_stdoutSubscriptionFuture);
+ _stdoutSubscriptionFuture = null;
+ cancelFutureSubscription(_stderrSubscriptionFuture);
+ _stderrSubscriptionFuture = null;
super.detached();
}
}
@@ -1665,6 +1761,21 @@ class DebuggerConsoleElement extends ObservatoryElement {
span.scrollIntoView();
}
+ void printStdio(List<String> lines) {
+ var lastSpan;
+ for (var line in lines) {
+ var span = new SpanElement();
+ span.classes.add('green');
+ span.appendText(line);
+ span.appendText('\n');
+ $['consoleText'].children.add(span);
+ lastSpan = span;
+ }
+ if (lastSpan != null) {
+ lastSpan.scrollIntoView();
+ }
+ }
+
void printRef(Instance ref, { bool newline:true }) {
var refElement = new Element.tag('instance-ref');
refElement.ref = ref;
« no previous file with comments | « runtime/observatory/lib/service.dart ('k') | runtime/observatory/lib/src/elements/debugger.html » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698