Skip to main content
aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorSarika Sinha2017-03-04 08:27:55 -0500
committerSarika Sinha2017-03-04 08:27:55 -0500
commitf8b78f2946e2965bc5bcd90c199e3982e844a831 (patch)
tree71df3906aa9f25a810aa7f66191c079ec3166c85
parentfd0dda7c8cf10980c2b9e0f2e83d640d8455f7b9 (diff)
downloadeclipse.platform.debug-f8b78f2946e2965bc5bcd90c199e3982e844a831.tar.gz
eclipse.platform.debug-f8b78f2946e2965bc5bcd90c199e3982e844a831.tar.xz
eclipse.platform.debug-f8b78f2946e2965bc5bcd90c199e3982e844a831.zip
at buffer boundaries correctly Change-Id: Iee66ccfd74f93760b1c0e26c7114d4b48cee6324
-rw-r--r--org.eclipse.debug.tests/src/org/eclipse/debug/tests/console/ConsoleTests.java25
-rw-r--r--org.eclipse.ui.console/src/org/eclipse/ui/console/IOConsoleOutputStream.java15
-rw-r--r--org.eclipse.ui.console/src/org/eclipse/ui/internal/console/StreamDecoder.java21
3 files changed, 50 insertions, 11 deletions
diff --git a/org.eclipse.debug.tests/src/org/eclipse/debug/tests/console/ConsoleTests.java b/org.eclipse.debug.tests/src/org/eclipse/debug/tests/console/ConsoleTests.java
index 3939c4d3a..b683fe22e 100644
--- a/org.eclipse.debug.tests/src/org/eclipse/debug/tests/console/ConsoleTests.java
+++ b/org.eclipse.debug.tests/src/org/eclipse/debug/tests/console/ConsoleTests.java
@@ -55,6 +55,31 @@ public class ConsoleTests extends TestCase {
TestHelper.waitForJobs();
TestCase.assertEquals("whole test string should be written", testString, document.get()); //$NON-NLS-1$
}
+ TestHelper.waitForJobs();
+ // after closing the stream, the document content should still be the
+ // same
+ TestCase.assertEquals("closing the stream should not alter the document", testString, document.get()); //$NON-NLS-1$
+ }
+
+ public void testConsoleOutputStreamLastR() throws IOException, InterruptedException {
+ String testString = "a\r"; //$NON-NLS-1$
+ byte[] testStringBuffer = testString.getBytes(StandardCharsets.UTF_8);
+ TestCase.assertEquals("Test string \"" + testString + "\" should consist of 2 UTF-8 bytes", 2, testStringBuffer.length); //$NON-NLS-1$ //$NON-NLS-2$
+ MessageConsole console = new MessageConsole("Test Console", //$NON-NLS-1$
+ IConsoleConstants.MESSAGE_CONSOLE_TYPE, null, StandardCharsets.UTF_8.name(), true);
+ IDocument document = console.getDocument();
+ TestHelper.waitForJobs();
+ TestCase.assertEquals("Document should be empty", "", document.get()); //$NON-NLS-1$ //$NON-NLS-2$
+ try (IOConsoleOutputStream outStream = console.newOutputStream()) {
+ outStream.write(testStringBuffer);
+ // everything but pending \r should be written
+ TestHelper.waitForJobs();
+ TestCase.assertEquals("First char should be written", testString.substring(0, 1), document.get()); //$NON-NLS-1$
+ }
+ TestHelper.waitForJobs();
+ // after closing the stream, the document content should still be the
+ // same
+ TestCase.assertEquals("closing the stream should write the pending \\r", testString, document.get()); //$NON-NLS-1$
}
}
diff --git a/org.eclipse.ui.console/src/org/eclipse/ui/console/IOConsoleOutputStream.java b/org.eclipse.ui.console/src/org/eclipse/ui/console/IOConsoleOutputStream.java
index 7e78ddf6a..8ee47071f 100644
--- a/org.eclipse.ui.console/src/org/eclipse/ui/console/IOConsoleOutputStream.java
+++ b/org.eclipse.ui.console/src/org/eclipse/ui/console/IOConsoleOutputStream.java
@@ -168,10 +168,15 @@ public class IOConsoleOutputStream extends OutputStream {
// Closeable#close() has no effect if already closed
return;
}
+ StringBuilder builder = new StringBuilder();
if (prependCR) { // force writing of last /r
prependCR = false;
- notifyParitioner("\r"); //$NON-NLS-1$
+ builder.append('\r');
}
+ this.decoder.finish(builder);
+ if (builder.length() > 0) {
+ notifyParitioner(builder.toString());
+ }
console.streamClosed(this);
closed = true;
partitioner = null;
@@ -193,7 +198,7 @@ public class IOConsoleOutputStream extends OutputStream {
* @see java.io.OutputStream#write(byte[], int, int)
*/
@Override
- public void write(byte[] b, int off, int len) throws IOException {
+ public synchronized void write(byte[] b, int off, int len) throws IOException {
StringBuilder builder = new StringBuilder();
this.decoder.decode(builder, b, off, len);
encodedWrite(builder.toString());
@@ -317,10 +322,12 @@ public class IOConsoleOutputStream extends OutputStream {
* @throws IOException if the stream is closed
* @since 3.7
*/
- public void setCharset(Charset charset) throws IOException {
+ public synchronized void setCharset(Charset charset) throws IOException {
StringBuilder builder = new StringBuilder();
this.decoder.finish(builder);
- this.encodedWrite(builder.toString());
+ if (builder.length() > 0) {
+ this.encodedWrite(builder.toString());
+ }
this.decoder = new StreamDecoder(charset);
}
diff --git a/org.eclipse.ui.console/src/org/eclipse/ui/internal/console/StreamDecoder.java b/org.eclipse.ui.console/src/org/eclipse/ui/internal/console/StreamDecoder.java
index dde14fdcd..aeb0179f1 100644
--- a/org.eclipse.ui.console/src/org/eclipse/ui/internal/console/StreamDecoder.java
+++ b/org.eclipse.ui.console/src/org/eclipse/ui/internal/console/StreamDecoder.java
@@ -29,6 +29,7 @@ public class StreamDecoder {
private final CharsetDecoder decoder;
private final ByteBuffer inputBuffer;
private final CharBuffer outputBuffer;
+ private boolean finished;
public StreamDecoder(Charset charset) {
this.decoder = charset.newDecoder();
@@ -37,6 +38,7 @@ public class StreamDecoder {
this.inputBuffer = ByteBuffer.allocate(StreamDecoder.BUFFER_SIZE);
this.inputBuffer.flip();
this.outputBuffer = CharBuffer.allocate(StreamDecoder.BUFFER_SIZE);
+ this.finished = false;
}
private void consume(StringBuilder consumer) {
@@ -45,15 +47,15 @@ public class StreamDecoder {
this.outputBuffer.clear();
}
- private void internalDecode(StringBuilder consumer, byte[] buffer, int offset, int length, boolean last) {
+ private void internalDecode(StringBuilder consumer, byte[] buffer, int offset, int length) {
assert (offset >= 0);
assert (length >= 0);
int position = offset;
int end = offset + length;
assert (end <= buffer.length);
- boolean finished = false;
+ boolean finishedReading = false;
do {
- CoderResult result = this.decoder.decode(this.inputBuffer, this.outputBuffer, last);
+ CoderResult result = this.decoder.decode(this.inputBuffer, this.outputBuffer, false);
if (result.isOverflow()) {
this.consume(consumer);
} else if (result.isUnderflow()) {
@@ -65,23 +67,28 @@ public class StreamDecoder {
this.inputBuffer.put(buffer, position, read);
position += read;
} else {
- finished = true;
+ finishedReading = true;
}
this.inputBuffer.flip();
} else {
assert false;
}
- } while (!finished);
+ } while (!finishedReading);
}
public void decode(StringBuilder consumer, byte[] buffer, int offset, int length) {
- this.internalDecode(consumer, buffer, offset, length, false);
+ this.internalDecode(consumer, buffer, offset, length);
this.consume(consumer);
}
public void finish(StringBuilder consumer) {
- this.internalDecode(consumer, new byte[0], 0, 0, true);
+ if (this.finished) {
+ return;
+ }
+ this.finished = true;
CoderResult result;
+ result = this.decoder.decode(this.inputBuffer, this.outputBuffer, true);
+ assert (result.isOverflow() || result.isUnderflow());
do {
result = this.decoder.flush(this.outputBuffer);
if (result.isOverflow()) {

Back to the top