Skip to content

Commit

Permalink
cap error output to avoid running out of memory
Browse files Browse the repository at this point in the history
  • Loading branch information
JPMoresmau committed Mar 11, 2013
1 parent 6caec8f commit 80b0ad5
Show file tree
Hide file tree
Showing 6 changed files with 206 additions and 5 deletions.
2 changes: 1 addition & 1 deletion net.sf.eclipsefp.haskell-feature/feature.xml
Expand Up @@ -137,7 +137,7 @@ available at http://www.eclipse.org/legal/epl-v10.html.
id="net.sf.eclipsefp.haskell.util"
download-size="0"
install-size="0"
version="2.5.1"
version="2.5.2"
unpack="false"/>

<plugin
Expand Down
Expand Up @@ -10,7 +10,6 @@
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.OutputStreamWriter;
import java.io.StringWriter;
import java.io.Writer;
import java.util.HashMap;
import java.util.concurrent.atomic.AtomicBoolean;
Expand All @@ -30,6 +29,7 @@
import net.sf.eclipsefp.haskell.browser.items.Module;
import net.sf.eclipsefp.haskell.browser.items.Packaged;
import net.sf.eclipsefp.haskell.browser.util.BrowserText;
import net.sf.eclipsefp.haskell.util.CappedStringWriter;
import net.sf.eclipsefp.haskell.util.DispatchWriter;
import net.sf.eclipsefp.haskell.util.FileUtil;
import net.sf.eclipsefp.haskell.util.LangUtil;
Expand Down Expand Up @@ -63,7 +63,7 @@ public class StreamBrowserServer extends BrowserServer {

private boolean logError;

private StringWriter lastErrW=new StringWriter();
private CappedStringWriter lastErrW=new CappedStringWriter(10000);
private DispatchWriter allErrWs=new DispatchWriter();

public StreamBrowserServer(IPath serverExecutable,boolean logError) throws Exception {
Expand Down Expand Up @@ -178,7 +178,7 @@ public boolean sendAndReceiveBoolean(JSONObject input)

private void sendCommand(String command) throws IOException{
log(">> " + command);
lastErrW.getBuffer().setLength(0);
lastErrW.clear();
in.write(command + "\n");
in.flush();
}
Expand Down
Expand Up @@ -21,6 +21,7 @@ public static Test suite() {

suite.addTest( new JUnit4TestAdapter(CommandLineUtilTest.class ));
suite.addTestSuite( FileUtilTest.class );
suite.addTest( new JUnit4TestAdapter(CappedStringWriterTest.class ));
return suite;
}
}
@@ -0,0 +1,93 @@
/**
* Copyright (c) 2013 by JP Moresmau
* This code is made available under the terms of the Eclipse Public License,
* version 1.0 (EPL). See http://www.eclipse.org/legal/epl-v10.html
*/
package net.sf.eclipsefp.haskell.util;

import static org.junit.Assert.assertEquals;

import java.io.IOException;

import org.junit.Assert;
import org.junit.Test;


/**
* Tests for CappedStringWriter
* @author JP Moresmau
*
*/
public class CappedStringWriterTest {

@Test
public void testNormal() throws IOException{
CappedStringWriter w=new CappedStringWriter(100);
w.write("toto");
w.write("titi");
Assert.assertEquals("tototiti", w.toString());
}

@Test
public void testClear() throws IOException{
CappedStringWriter w=new CappedStringWriter(4);
w.write("toto");
w.clear();
w.write("titi");
Assert.assertEquals("titi", w.toString());
w=new CappedStringWriter(4);
w.write("toto");
w.clear();
w.write("tutu");
w.write("titi");
Assert.assertEquals("titi", w.toString());
}


@Test
public void testNull() throws IOException{
CappedStringWriter w=new CappedStringWriter(100);
w.write("toto");
w.write((String)null);
assertEquals("toto", w.toString());
}

@Test
public void testLimit() throws IOException{
CappedStringWriter w=new CappedStringWriter(4);
w.write("toto");
w.write("titi");
assertEquals("titi", w.toString());
}

@Test
public void testLimitMiddle() throws IOException{
CappedStringWriter w=new CappedStringWriter(6);
w.write("toto");
w.write("titi");
assertEquals("titi", w.toString());
}

@Test
public void testLimitMiddleAll() throws IOException{
CappedStringWriter w=new CappedStringWriter(2);
w.write("toto");
w.write("titi");
assertEquals("", w.toString());
}

@Test
public void testPerf() throws IOException{
CappedStringWriter w=new CappedStringWriter(100);
StringBuilder sb=new StringBuilder();
for (int a=0;a<100;a++){
sb.append("a");
}
String s=sb.toString();
assertEquals(100, s.length());
for (int a=0;a<10000;a++){
w.write(s);
}
assertEquals(s,w.toString());
}
}
2 changes: 1 addition & 1 deletion net.sf.eclipsefp.haskell.util/META-INF/MANIFEST.MF
Expand Up @@ -2,7 +2,7 @@ Manifest-Version: 1.0
Bundle-ManifestVersion: 2
Bundle-Name: %bundleName
Bundle-SymbolicName: net.sf.eclipsefp.haskell.util
Bundle-Version: 2.5.1
Bundle-Version: 2.5.2
Bundle-Activator: net.sf.eclipsefp.haskell.util.Activator
Require-Bundle: org.eclipse.core.runtime,
org.eclipse.core.resources,
Expand Down
@@ -0,0 +1,107 @@
/**
* Copyright (c) 2013 by JP Moresmau
* This code is made available under the terms of the Eclipse Public License,
* version 1.0 (EPL). See http://www.eclipse.org/legal/epl-v10.html
*/
package net.sf.eclipsefp.haskell.util;

import java.io.IOException;
import java.io.Writer;
import java.util.LinkedList;

/**
* A string writer that only keeps n max characters, discarding the first received characters
* @author JP Moresmau
*
*/
public class CappedStringWriter extends Writer {
private int maxSize;
private LinkedList<String> ls=new LinkedList<String>();
private int size;

public CappedStringWriter(int max){
maxSize=max;
lock=ls;
}


/* (non-Javadoc)
* @see java.io.Writer#write(char[], int, int)
*/
@Override
public void write(char[] cbuf, int off, int len) throws IOException {
synchronized (lock) {
ls.add(new String(cbuf,off,len));
size+=len;
checkSize();
}
}

/* (non-Javadoc)
* @see java.io.Writer#write(java.lang.String)
*/
@Override
public void write(String str) throws IOException {
synchronized (lock) {
if (str!=null){
ls.add(str);
size+=str.length();
checkSize();
}
}
}

/* (non-Javadoc)
* @see java.io.Writer#write(java.lang.String, int, int)
*/
@Override
public void write(String str, int off, int len) throws IOException {
write(str.substring(off, off+len));
}

private void checkSize(){
while (size>maxSize){
String s=ls.removeFirst();
size-=s.length();
}
}

/* (non-Javadoc)
* @see java.io.Writer#flush()
*/
@Override
public void flush() throws IOException {
// noop
}

/* (non-Javadoc)
* @see java.io.Writer#close()
*/
@Override
public void close() throws IOException {
// noop

}

/* (non-Javadoc)
* @see java.lang.Object#toString()
*/
@Override
public String toString() {
synchronized (lock) {
StringBuilder sb=new StringBuilder(size);
for (String s:ls){
sb.append(s);
}
return sb.toString();
}
}

public void clear(){
synchronized (lock) {
ls.clear();
size=0;
}

}
}

0 comments on commit 80b0ad5

Please sign in to comment.