Hey everyone,
After more than one year of living next to the compression bug we were able to
find the reason for it. The exceptions where several but in general they looked
like this:
2007.04.24 23:29:04
[org.jivesoftware.openfire.nio.ConnectionHandler.exceptionCaught(ConnectionHand
ler.java:109)]
java.lang.ArrayIndexOutOfBoundsException: -2147483646
at com.jcraft.jzlib.Deflate.deflate_slow(Deflate.java:1131)
at com.jcraft.jzlib.Deflate.deflate(Deflate.java:1567)
at com.jcraft.jzlib.ZStream.deflate(ZStream.java:133)
at org.apache.mina.filter.support.Zlib.deflate(Zlib.java:176)
at
org.apache.mina.filter.CompressionFilter.filterWrite(CompressionFilter.java:198
)
at
org.apache.mina.common.support.AbstractIoFilterChain.callPreviousFilterWrite(Ab
stractIoFilterChain.java:445)
at
org.apache.mina.common.support.AbstractIoFilterChain.access$1400(AbstractIoFilt
erChain.java:54)
at
org.apache.mina.common.support.AbstractIoFilterChain$EntryImpl$1.filterWrite(Ab
stractIoFilterChain.java:824)
at
org.apache.mina.filter.executor.ExecutorFilter.filterWrite(ExecutorFilter.java:
292)
at
org.apache.mina.common.support.AbstractIoFilterChain.callPreviousFilterWrite(Ab
stractIoFilterChain.java:445)
at
org.apache.mina.common.support.AbstractIoFilterChain.access$1400(AbstractIoFilt
erChain.java:54)
at
org.apache.mina.common.support.AbstractIoFilterChain$EntryImpl$1.filterWrite(Ab
stractIoFilterChain.java:824)
at
org.apache.mina.filter.codec.ProtocolCodecFilter.filterWrite(ProtocolCodecFilte
r.java:227)
at
org.apache.mina.common.support.AbstractIoFilterChain.callPreviousFilterWrite(Ab
stractIoFilterChain.java:445)
at
org.apache.mina.common.support.AbstractIoFilterChain.access$1400(AbstractIoFilt
erChain.java:54)
at
org.apache.mina.common.support.AbstractIoFilterChain$EntryImpl$1.filterWrite(Ab
stractIoFilterChain.java:824)
at
org.apache.mina.common.support.AbstractIoFilterChain$TailFilter.filterWrite(Abs
tractIoFilterChain.java:727)
at
org.apache.mina.common.support.AbstractIoFilterChain.callPreviousFilterWrite(Ab
stractIoFilterChain.java:445)
at
org.apache.mina.common.support.AbstractIoFilterChain.fireFilterWrite(AbstractIo
FilterChain.java:436)
at
org.apache.mina.transport.socket.nio.SocketSessionImpl.write0(SocketSessionImpl
.java:196)
at org.apache.mina.common.support.BaseIoSession.write(BaseIoSession.java:149)
at org.apache.mina.common.support.BaseIoSession.write(BaseIoSession.java:135)
at org.jivesoftware.openfire.nio.NIOConnection.deliver(NIOConnection.java:201)
The problem was hard to detect since it was a concurrency problem. Here is a
diff for MINA 1.1.8:
Index:
filter-compression/src/main/java/org/apache/mina/filter/CompressionFilter.java
===================================================================
---
filter-compression/src/main/java/org/apache/mina/filter/CompressionFilter.java
(revision 719471)
+++
filter-compression/src/main/java/org/apache/mina/filter/CompressionFilter.java
(working copy)
@@ -188,7 +188,10 @@
// Ignore empty buffers
nextFilter.filterWrite(session, writeRequest);
} else {
- ByteBuffer outBuf = deflater.deflate(inBuffer);
+ ByteBuffer outBuf;
+ synchronized (deflater) {
+ outBuf = deflater.deflate(inBuffer);
+ }
inBuffer.release();
nextFilter.filterWrite(session, new WriteRequest(outBuf,
writeRequest.getFuture()));
Hope that helps.
Regards,
-- Gato