You are viewing a plain text version of this content. The canonical link for it is here.
Posted to server-dev@james.apache.org by no...@apache.org on 2011/08/18 20:20:59 UTC
svn commit: r1159343 - in /james/imap/trunk: ./ message/
message/src/main/java/org/apache/james/imap/decode/
message/src/main/java/org/apache/james/imap/encode/base/
message/src/main/java/org/apache/james/imap/utils/
message/src/main/java/org/apache/ja...
Author: norman
Date: Thu Aug 18 18:20:59 2011
New Revision: 1159343
URL: http://svn.apache.org/viewvc?rev=1159343&view=rev
Log:
Replace ByteArrayOutputStream with FastByteArrayOutputStream to remove unnecessary synchronization. See IMAP-331
Added:
james/imap/trunk/message/src/main/java/org/apache/james/imap/utils/
james/imap/trunk/message/src/main/java/org/apache/james/imap/utils/io/
james/imap/trunk/message/src/main/java/org/apache/james/imap/utils/io/FastByteArrayOutputStream.java
Modified:
james/imap/trunk/message/pom.xml
james/imap/trunk/message/src/main/java/org/apache/james/imap/decode/ImapRequestLineReader.java
james/imap/trunk/message/src/main/java/org/apache/james/imap/encode/base/ImapResponseComposerImpl.java
james/imap/trunk/pom.xml
Modified: james/imap/trunk/message/pom.xml
URL: http://svn.apache.org/viewvc/james/imap/trunk/message/pom.xml?rev=1159343&r1=1159342&r2=1159343&view=diff
==============================================================================
--- james/imap/trunk/message/pom.xml (original)
+++ james/imap/trunk/message/pom.xml Thu Aug 18 18:20:59 2011
@@ -48,10 +48,6 @@
<artifactId>commons-lang</artifactId>
</dependency>
<dependency>
- <groupId>commons-io</groupId>
- <artifactId>commons-io</artifactId>
- </dependency>
- <dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<scope>test</scope>
Modified: james/imap/trunk/message/src/main/java/org/apache/james/imap/decode/ImapRequestLineReader.java
URL: http://svn.apache.org/viewvc/james/imap/trunk/message/src/main/java/org/apache/james/imap/decode/ImapRequestLineReader.java?rev=1159343&r1=1159342&r2=1159343&view=diff
==============================================================================
--- james/imap/trunk/message/src/main/java/org/apache/james/imap/decode/ImapRequestLineReader.java (original)
+++ james/imap/trunk/message/src/main/java/org/apache/james/imap/decode/ImapRequestLineReader.java Thu Aug 18 18:20:59 2011
@@ -19,7 +19,6 @@
package org.apache.james.imap.decode;
-import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.nio.ByteBuffer;
@@ -37,13 +36,13 @@ import java.util.List;
import javax.mail.Flags;
-import org.apache.commons.io.IOUtils;
import org.apache.james.imap.api.ImapConstants;
import org.apache.james.imap.api.display.HumanReadableText;
import org.apache.james.imap.api.message.IdRange;
import org.apache.james.imap.api.message.request.DayMonthYear;
import org.apache.james.imap.api.process.ImapSession;
import org.apache.james.imap.api.process.SearchResUtil;
+import org.apache.james.imap.utils.io.FastByteArrayOutputStream;
/**
* Wraps the client input reader with a bunch of convenience methods, allowing
@@ -357,15 +356,31 @@ public abstract class ImapRequestLineRea
if (charset == null) {
return consumeLiteral(US_ASCII);
} else {
- ByteArrayOutputStream out = new ByteArrayOutputStream();
+ FastByteArrayOutputStream out = new FastByteArrayOutputStream();
+ InputStream in = null;
try {
- IOUtils.copy(consumeLiteral(false), out);
+ in = consumeLiteral(false);
+ byte[] buf = new byte[ 0xFFFF ];
+
+ for (int len; (len = in.read(buf)) != -1; )
+ out.write( buf, 0, len );
+
+ final byte[] bytes = out.toByteArray();
+ final ByteBuffer buffer = ByteBuffer.wrap(bytes);
+ return decode(charset, buffer);
+
} catch (IOException e) {
throw new DecodingException(HumanReadableText.BAD_IO_ENCODING, "Bad character encoding", e);
+ } finally {
+ if (in != null) {
+ try {
+ in.close();
+ } catch (IOException e) {
+ // ignore on close
+ }
+ }
}
- final byte[] bytes = out.toByteArray();
- final ByteBuffer buffer = ByteBuffer.wrap(bytes);
- return decode(charset, buffer);
+
}
}
Modified: james/imap/trunk/message/src/main/java/org/apache/james/imap/encode/base/ImapResponseComposerImpl.java
URL: http://svn.apache.org/viewvc/james/imap/trunk/message/src/main/java/org/apache/james/imap/encode/base/ImapResponseComposerImpl.java?rev=1159343&r1=1159342&r2=1159343&view=diff
==============================================================================
--- james/imap/trunk/message/src/main/java/org/apache/james/imap/encode/base/ImapResponseComposerImpl.java (original)
+++ james/imap/trunk/message/src/main/java/org/apache/james/imap/encode/base/ImapResponseComposerImpl.java Thu Aug 18 18:20:59 2011
@@ -25,13 +25,13 @@ import java.nio.charset.Charset;
import javax.mail.Flags;
-import org.apache.commons.io.output.ByteArrayOutputStream;
import org.apache.james.imap.api.ImapCommand;
import org.apache.james.imap.api.ImapConstants;
import org.apache.james.imap.api.message.IdRange;
import org.apache.james.imap.encode.ImapResponseComposer;
import org.apache.james.imap.encode.ImapResponseWriter;
import org.apache.james.imap.message.response.Literal;
+import org.apache.james.imap.utils.io.FastByteArrayOutputStream;
/**
* Class providing methods to send response messages from the server to the
@@ -42,21 +42,27 @@ public class ImapResponseComposerImpl im
public static final String FLAGS = "FLAGS";
public static final String FAILED = "failed.";
-
+ private static final int LOWER_CASE_OFFSET = 'a' - 'A';
+ public final static int DEFAULT_BUFFER_SIZE = 2048;
+
+
private final ImapResponseWriter writer;
- private final ByteArrayOutputStream buffer = new ByteArrayOutputStream();
-
- private static final int LOWER_CASE_OFFSET = 'a' - 'A';
+ private final FastByteArrayOutputStream buffer;
private final Charset usAscii;
private boolean skipNextSpace;
- public ImapResponseComposerImpl(final ImapResponseWriter writer) {
+ public ImapResponseComposerImpl(final ImapResponseWriter writer, int bufferSize) {
skipNextSpace = false;
usAscii = Charset.forName("US-ASCII");
this.writer = writer;
+ this.buffer = new FastByteArrayOutputStream(bufferSize);
+ }
+
+ public ImapResponseComposerImpl(final ImapResponseWriter writer) {
+ this(writer, DEFAULT_BUFFER_SIZE);
}
/*
Added: james/imap/trunk/message/src/main/java/org/apache/james/imap/utils/io/FastByteArrayOutputStream.java
URL: http://svn.apache.org/viewvc/james/imap/trunk/message/src/main/java/org/apache/james/imap/utils/io/FastByteArrayOutputStream.java?rev=1159343&view=auto
==============================================================================
--- james/imap/trunk/message/src/main/java/org/apache/james/imap/utils/io/FastByteArrayOutputStream.java (added)
+++ james/imap/trunk/message/src/main/java/org/apache/james/imap/utils/io/FastByteArrayOutputStream.java Thu Aug 18 18:20:59 2011
@@ -0,0 +1,233 @@
+package org.apache.james.imap.utils.io;
+
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+import java.io.ByteArrayOutputStream;
+import java.io.IOException;
+import java.io.OutputStream;
+import java.io.UnsupportedEncodingException;
+
+/**
+ * This class was forked from cassandra:
+ *
+ * http://svn.apache.org/viewvc/cassandra/trunk/src/java/org/apache/cassandra/io/util/FastByteArrayOutputStream.java?view=co
+ */
+
+/**
+ * A specialized {@link OutputStream} for class for writing content to an
+ * (internal) byte array. As bytes are written to this stream, the byte array
+ * may be expanded to hold more bytes. When the writing is considered to be
+ * finished, a copy of the byte array can be requested from the class.
+ *
+ * @see ByteArrayOutputStream
+ */
+public class FastByteArrayOutputStream extends OutputStream {
+ /**
+ * The byte array containing the bytes written.
+ */
+ protected byte[] buf;
+
+ /**
+ * The number of bytes written.
+ */
+ protected int count;
+
+ /**
+ * Constructs a new ByteArrayOutputStream with a default size of 32 bytes.
+ * If more than 32 bytes are written to this instance, the underlying byte
+ * array will expand.
+ */
+ public FastByteArrayOutputStream() {
+ buf = new byte[32];
+ }
+
+ /**
+ * Constructs a new {@code ByteArrayOutputStream} with a default size of
+ * {@code size} bytes. If more than {@code size} bytes are written to this
+ * instance, the underlying byte array will expand.
+ *
+ * @param size
+ * initial size for the underlying byte array, must be
+ * non-negative.
+ * @throws IllegalArgumentException
+ * if {@code size} < 0.
+ */
+ public FastByteArrayOutputStream(int size) {
+ if (size >= 0) {
+ buf = new byte[size];
+ } else {
+ throw new IllegalArgumentException();
+ }
+ }
+
+ private void expand(int i) {
+ /* Can the buffer handle @i more bytes, if not expand it */
+ if (count + i <= buf.length) {
+ return;
+ }
+
+ byte[] newbuf = new byte[(count + i) * 2];
+ System.arraycopy(buf, 0, newbuf, 0, count);
+ buf = newbuf;
+ }
+
+ /**
+ * Resets this stream to the beginning of the underlying byte array. All
+ * subsequent writes will overwrite any bytes previously stored in this
+ * stream.
+ */
+ public void reset() {
+ count = 0;
+ }
+
+ /**
+ * Returns the total number of bytes written to this stream so far.
+ *
+ * @return the number of bytes written to this stream.
+ */
+ public int size() {
+ return count;
+ }
+
+ /**
+ * Returns the contents of this ByteArrayOutputStream as a byte array. Any
+ * changes made to the receiver after returning will not be reflected in the
+ * byte array returned to the caller.
+ *
+ * @return this stream's current contents as a byte array.
+ */
+ public byte[] toByteArray() {
+ byte[] newArray = new byte[count];
+ System.arraycopy(buf, 0, newArray, 0, count);
+ return newArray;
+ }
+
+ /**
+ * Returns the contents of this ByteArrayOutputStream as a string. Any
+ * changes made to the receiver after returning will not be reflected in the
+ * string returned to the caller.
+ *
+ * @return this stream's current contents as a string.
+ */
+
+ @Override
+ public String toString() {
+ return new String(buf, 0, count);
+ }
+
+ /**
+ * Returns the contents of this ByteArrayOutputStream as a string. Each byte
+ * {@code b} in this stream is converted to a character {@code c} using the
+ * following function:
+ * {@code c == (char)(((hibyte & 0xff) << 8) | (b & 0xff))}. This method is
+ * deprecated and either {@link #toString()} or {@link #toString(String)}
+ * should be used.
+ *
+ * @param hibyte
+ * the high byte of each resulting Unicode character.
+ * @return this stream's current contents as a string with the high byte set
+ * to {@code hibyte}.
+ * @deprecated Use {@link #toString()}.
+ */
+ @Deprecated
+ public String toString(int hibyte) {
+ char[] newBuf = new char[size()];
+ for (int i = 0; i < newBuf.length; i++) {
+ newBuf[i] = (char) (((hibyte & 0xff) << 8) | (buf[i] & 0xff));
+ }
+ return new String(newBuf);
+ }
+
+ /**
+ * Returns the contents of this ByteArrayOutputStream as a string converted
+ * according to the encoding declared in {@code enc}.
+ *
+ * @param enc
+ * a string representing the encoding to use when translating
+ * this stream to a string.
+ * @return this stream's current contents as an encoded string.
+ * @throws UnsupportedEncodingException
+ * if the provided encoding is not supported.
+ */
+ public String toString(String enc) throws UnsupportedEncodingException {
+ return new String(buf, 0, count, enc);
+ }
+
+ /**
+ * Writes {@code count} bytes from the byte array {@code buffer} starting at
+ * offset {@code index} to this stream.
+ *
+ * @param buffer
+ * the buffer to be written.
+ * @param offset
+ * the initial position in {@code buffer} to retrieve bytes.
+ * @param len
+ * the number of bytes of {@code buffer} to write.
+ * @throws NullPointerException
+ * if {@code buffer} is {@code null}.
+ * @throws IndexOutOfBoundsException
+ * if {@code offset < 0} or {@code len < 0}, or if
+ * {@code offset + len} is greater than the length of
+ * {@code buffer}.
+ */
+ @Override
+ public void write(byte[] buffer, int offset, int len) {
+ // avoid int overflow
+ if (offset < 0 || offset > buffer.length || len < 0
+ || len > buffer.length - offset) {
+ throw new IndexOutOfBoundsException();
+ }
+ if (len == 0) {
+ return;
+ }
+
+ /* Expand if necessary */
+ expand(len);
+ System.arraycopy(buffer, offset, buf, this.count, len);
+ this.count += len;
+ }
+
+ /**
+ * Writes the specified byte {@code oneByte} to the OutputStream. Only the
+ * low order byte of {@code oneByte} is written.
+ *
+ * @param oneByte
+ * the byte to be written.
+ */
+ @Override
+ public void write(int oneByte) {
+ if (count == buf.length) {
+ expand(1);
+ }
+ buf[count++] = (byte) oneByte;
+ }
+
+ /**
+ * Takes the contents of this stream and writes it to the output stream
+ * {@code out}.
+ *
+ * @param out
+ * an OutputStream on which to write the contents of this stream.
+ * @throws IOException
+ * if an error occurs while writing to {@code out}.
+ */
+ public void writeTo(OutputStream out) throws IOException {
+ out.write(buf, 0, count);
+ }
+}
+
Modified: james/imap/trunk/pom.xml
URL: http://svn.apache.org/viewvc/james/imap/trunk/pom.xml?rev=1159343&r1=1159342&r2=1159343&view=diff
==============================================================================
--- james/imap/trunk/pom.xml (original)
+++ james/imap/trunk/pom.xml Thu Aug 18 18:20:59 2011
@@ -551,11 +551,6 @@
<version>${version.jmock}</version>
<scope>test</scope>
</dependency>
- <dependency>
- <groupId>commons-io</groupId>
- <artifactId>commons-io</artifactId>
- <version>2.0.1</version>
- </dependency>
<!--
---------------------------------------------------------------------
To unsubscribe, e-mail: server-dev-unsubscribe@james.apache.org
For additional commands, e-mail: server-dev-help@james.apache.org