Author: trustin
Date: Mon Nov  5 10:54:39 2007
New Revision: 592116

URL: http://svn.apache.org/viewvc?rev=592116&view=rev
Log:
* Added small I/O spin loop for better performance to SocketIoProcessor and 
AbstractIoProcessor
* Restricted CachedBufferAllocator from caching too big buffers



Modified:
    
mina/branches/1.0/core/src/main/java/org/apache/mina/transport/socket/nio/SocketIoProcessor.java
    
mina/branches/1.1/core/src/main/java/org/apache/mina/transport/socket/nio/SocketIoProcessor.java
    
mina/trunk/core/src/main/java/org/apache/mina/common/AbstractIoProcessor.java
    
mina/trunk/core/src/main/java/org/apache/mina/common/CachedBufferAllocator.java
    mina/trunk/core/src/main/java/org/apache/mina/util/CircularQueue.java
    
mina/trunk/example/src/main/java/org/apache/mina/example/echoserver/Main.java

Modified: 
mina/branches/1.0/core/src/main/java/org/apache/mina/transport/socket/nio/SocketIoProcessor.java
URL: 
http://svn.apache.org/viewvc/mina/branches/1.0/core/src/main/java/org/apache/mina/transport/socket/nio/SocketIoProcessor.java?rev=592116&r1=592115&r2=592116&view=diff
==============================================================================
--- 
mina/branches/1.0/core/src/main/java/org/apache/mina/transport/socket/nio/SocketIoProcessor.java
 (original)
+++ 
mina/branches/1.0/core/src/main/java/org/apache/mina/transport/socket/nio/SocketIoProcessor.java
 Mon Nov  5 10:54:39 2007
@@ -43,6 +43,9 @@
  * @version $Rev$, $Date$,
  */
 class SocketIoProcessor {
+
+    private static final int IO_SPIN_COUNT = 3;
+    
     private final Object lock = new Object();
 
     private final String threadName;
@@ -238,11 +241,16 @@
 
         try {
             int readBytes = 0;
-            int ret;
+            int ret = 0;
 
             try {
-                while ((ret = ch.read(buf.buf())) > 0) {
-                    readBytes += ret;
+                for (int i = IO_SPIN_COUNT; i > 0; i --) {
+                    while ((ret = ch.read(buf.buf())) > 0) {
+                        readBytes += ret;
+                    }
+                    if (readBytes != 0) {
+                        break;
+                    }
                 }
             } finally {
                 buf.flip();
@@ -450,7 +458,14 @@
                     continue;
                 }
     
-                int localWrittenBytes = ch.write(buf.buf());
+                int localWrittenBytes = 0;
+                for (int i = IO_SPIN_COUNT; i > 0; i --) {
+                    localWrittenBytes = ch.write(buf.buf());
+                    if (localWrittenBytes != 0 || !buf.hasRemaining()) {
+                        break;
+                    }
+                }
+
                 writtenBytes += localWrittenBytes;
 
                 if (localWrittenBytes == 0 || writtenBytes >= maxWrittenBytes) 
{

Modified: 
mina/branches/1.1/core/src/main/java/org/apache/mina/transport/socket/nio/SocketIoProcessor.java
URL: 
http://svn.apache.org/viewvc/mina/branches/1.1/core/src/main/java/org/apache/mina/transport/socket/nio/SocketIoProcessor.java?rev=592116&r1=592115&r2=592116&view=diff
==============================================================================
--- 
mina/branches/1.1/core/src/main/java/org/apache/mina/transport/socket/nio/SocketIoProcessor.java
 (original)
+++ 
mina/branches/1.1/core/src/main/java/org/apache/mina/transport/socket/nio/SocketIoProcessor.java
 Mon Nov  5 10:54:39 2007
@@ -42,6 +42,9 @@
  * @version $Rev$, $Date$,
  */
 class SocketIoProcessor {
+
+    private static final int IO_SPIN_COUNT = 3;
+    
     private final Object lock = new Object();
 
     private final String threadName;
@@ -202,11 +205,16 @@
 
         try {
             int readBytes = 0;
-            int ret;
+            int ret = 0;
 
             try {
-                while ((ret = ch.read(buf.buf())) > 0) {
-                    readBytes += ret;
+                for (int i = IO_SPIN_COUNT; i > 0; i --) {
+                    while ((ret = ch.read(buf.buf())) > 0) {
+                        readBytes += ret;
+                    }
+                    if (readBytes != 0) {
+                        break;
+                    }
                 }
             } finally {
                 buf.flip();
@@ -399,7 +407,14 @@
                     continue;
                 }
 
-                int localWrittenBytes = ch.write(buf.buf());
+                int localWrittenBytes = 0;
+                for (int i = IO_SPIN_COUNT; i > 0; i --) {
+                    localWrittenBytes = ch.write(buf.buf());
+                    if (localWrittenBytes != 0 || !buf.hasRemaining()) {
+                        break;
+                    }
+                }
+
                 writtenBytes += localWrittenBytes;
 
                 if (localWrittenBytes == 0 || writtenBytes >= maxWrittenBytes) 
{

Modified: 
mina/trunk/core/src/main/java/org/apache/mina/common/AbstractIoProcessor.java
URL: 
http://svn.apache.org/viewvc/mina/trunk/core/src/main/java/org/apache/mina/common/AbstractIoProcessor.java?rev=592116&r1=592115&r2=592116&view=diff
==============================================================================
--- 
mina/trunk/core/src/main/java/org/apache/mina/common/AbstractIoProcessor.java 
(original)
+++ 
mina/trunk/core/src/main/java/org/apache/mina/common/AbstractIoProcessor.java 
Mon Nov  5 10:54:39 2007
@@ -38,7 +38,9 @@
  * @version $Rev$, $Date$
  */
 public abstract class AbstractIoProcessor implements IoProcessor {
-
+    
+    private static final int IO_SPIN_COUNT = 3;
+    
     private final Object lock = new Object();
     private final String threadName;
     private final Executor executor;
@@ -287,15 +289,25 @@
 
         try {
             int readBytes = 0;
-            int ret;
+            int ret = 0;
 
             try {
                 if (session.getTransportMetadata().hasFragmentation()) {
-                    while ((ret = read(session, buf)) > 0) {
-                        readBytes += ret;
+                    for (int i = IO_SPIN_COUNT; i > 0; i --) {
+                        while ((ret = read(session, buf)) > 0) {
+                            readBytes += ret;
+                        }
+                        if (readBytes != 0) {
+                            break;
+                        }
                     }
                 } else {
-                    ret = read(session, buf);
+                    for (int i = IO_SPIN_COUNT; i > 0; i --) {
+                        ret = read(session, buf);
+                        if (ret != 0) {
+                            break;
+                        }
+                    }
                     if (ret > 0) {
                         readBytes = ret;
                     }
@@ -442,7 +454,7 @@
                 break;
             }
 
-            long localWrittenBytes;
+            long localWrittenBytes = 0;
             Object message = req.getMessage();
             if (message instanceof FileRegion) {
                 FileRegion region = (FileRegion) message;
@@ -466,7 +478,12 @@
                     continue;
                 }
 
-                localWrittenBytes = write(session, buf);
+                for (int i = IO_SPIN_COUNT; i > 0; i --) {
+                    localWrittenBytes = write(session, buf);
+                    if (localWrittenBytes != 0 || !buf.hasRemaining()) {
+                        break;
+                    }
+                }
             }
             
             writtenBytes += localWrittenBytes;

Modified: 
mina/trunk/core/src/main/java/org/apache/mina/common/CachedBufferAllocator.java
URL: 
http://svn.apache.org/viewvc/mina/trunk/core/src/main/java/org/apache/mina/common/CachedBufferAllocator.java?rev=592116&r1=592115&r2=592116&view=diff
==============================================================================
--- 
mina/trunk/core/src/main/java/org/apache/mina/common/CachedBufferAllocator.java 
(original)
+++ 
mina/trunk/core/src/main/java/org/apache/mina/common/CachedBufferAllocator.java 
Mon Nov  5 10:54:39 2007
@@ -62,6 +62,7 @@
 public class CachedBufferAllocator implements IoBufferAllocator {
 
     private static final int MAX_POOL_SIZE = 8;
+    private static final int MAX_CACHED_BUFFER_SIZE = 1 << 18; // 256KB
     
     private static Map<Integer, Queue<CachedBuffer>> newPoolMap() {
         Map<Integer, Queue<CachedBuffer>> poolMap =
@@ -92,24 +93,33 @@
             
     public IoBuffer allocate(int capacity, boolean direct) {
         capacity = normalizeCapacity(capacity);
-        Queue<CachedBuffer> pool;
-        if (direct) {
-            pool = directBuffers.get().get(capacity);
-        } else {
-            pool = heapBuffers.get().get(capacity);
-        }
-        
-        // Recycle if possible.
-        IoBuffer buf = pool.poll();
-        if (buf != null) {
-            buf.clear();
-            buf.setAutoExpand(false);
-            buf.order(ByteOrder.BIG_ENDIAN);
-        } else {
+        IoBuffer buf ;
+        if (capacity > MAX_CACHED_BUFFER_SIZE) {
             if (direct) {
                 buf = wrap(ByteBuffer.allocateDirect(capacity));
             } else {
                 buf = wrap(ByteBuffer.allocate(capacity));
+            }
+        } else {
+            Queue<CachedBuffer> pool;
+            if (direct) {
+                pool = directBuffers.get().get(capacity);
+            } else {
+                pool = heapBuffers.get().get(capacity);
+            }
+            
+            // Recycle if possible.
+            buf = pool.poll();
+            if (buf != null) {
+                buf.clear();
+                buf.setAutoExpand(false);
+                buf.order(ByteOrder.BIG_ENDIAN);
+            } else {
+                if (direct) {
+                    buf = wrap(ByteBuffer.allocateDirect(capacity));
+                } else {
+                    buf = wrap(ByteBuffer.allocate(capacity));
+                }
             }
         }
         return buf;

Modified: mina/trunk/core/src/main/java/org/apache/mina/util/CircularQueue.java
URL: 
http://svn.apache.org/viewvc/mina/trunk/core/src/main/java/org/apache/mina/util/CircularQueue.java?rev=592116&r1=592115&r2=592116&view=diff
==============================================================================
--- mina/trunk/core/src/main/java/org/apache/mina/util/CircularQueue.java 
(original)
+++ mina/trunk/core/src/main/java/org/apache/mina/util/CircularQueue.java Mon 
Nov  5 10:54:39 2007
@@ -88,6 +88,10 @@
         Object ret = items[first];
         items[first] = null;
         decreaseSize();
+        
+        if (first == last) {
+            first = last = 0;
+        }
 
         return (E) ret;
     }

Modified: 
mina/trunk/example/src/main/java/org/apache/mina/example/echoserver/Main.java
URL: 
http://svn.apache.org/viewvc/mina/trunk/example/src/main/java/org/apache/mina/example/echoserver/Main.java?rev=592116&r1=592115&r2=592116&view=diff
==============================================================================
--- 
mina/trunk/example/src/main/java/org/apache/mina/example/echoserver/Main.java 
(original)
+++ 
mina/trunk/example/src/main/java/org/apache/mina/example/echoserver/Main.java 
Mon Nov  5 10:54:39 2007
@@ -60,7 +60,6 @@
         // Bind
         acceptor.setLocalAddress(new InetSocketAddress(PORT));
         acceptor.setHandler(new EchoProtocolHandler());
-        // acceptor.getFilterChain().addLast("x", new 
WriteThrottleFilter(WriteThrottlePolicy.LOG, 0, 1048576, 0, 0, 0, 0));
         acceptor.bind();
 
         System.out.println("Listening on port " + PORT);


Reply via email to