Author: norman Date: Sat Feb 13 08:59:59 2010 New Revision: 909776 URL: http://svn.apache.org/viewvc?rev=909776&view=rev Log: More performant + correct handling of MaxLineLength detection
Modified: james/server/trunk/mina-socket/src/main/java/org/apache/james/socket/mina/codec/CRLFTerminatedLineDecoder.java james/server/trunk/smtpserver/src/main/java/org/apache/james/smtpserver/mina/SMTPIoHandler.java james/server/trunk/smtpserver/src/test/java/org/apache/james/smtpserver/AsyncSMTPServerTest.java Modified: james/server/trunk/mina-socket/src/main/java/org/apache/james/socket/mina/codec/CRLFTerminatedLineDecoder.java URL: http://svn.apache.org/viewvc/james/server/trunk/mina-socket/src/main/java/org/apache/james/socket/mina/codec/CRLFTerminatedLineDecoder.java?rev=909776&r1=909775&r2=909776&view=diff ============================================================================== --- james/server/trunk/mina-socket/src/main/java/org/apache/james/socket/mina/codec/CRLFTerminatedLineDecoder.java (original) +++ james/server/trunk/mina-socket/src/main/java/org/apache/james/socket/mina/codec/CRLFTerminatedLineDecoder.java Sat Feb 13 08:59:59 2010 @@ -68,15 +68,17 @@ // Now find the first CRLF in the buffer. byte previous = 0; - int count = 0; + + if (maxLineLength != -1 && in.remaining() > maxLineLength) { + + // clear the buffer before throw exception + in.clear(); + + throw new LineLengthExceededException(maxLineLength, in.remaining()); + } while (in.hasRemaining()) { byte current = in.get(); - count++; - - // max line lenth exceed. Throw exception to prevent DOS - if (maxLineLength != -1 && count > maxLineLength) { - throw new LineLengthExceededException(maxLineLength, in.capacity()); - } + if (previous == '\r' && current == '\n') { // Remember the current position and limit. Modified: james/server/trunk/smtpserver/src/main/java/org/apache/james/smtpserver/mina/SMTPIoHandler.java URL: http://svn.apache.org/viewvc/james/server/trunk/smtpserver/src/main/java/org/apache/james/smtpserver/mina/SMTPIoHandler.java?rev=909776&r1=909775&r2=909776&view=diff ============================================================================== --- james/server/trunk/smtpserver/src/main/java/org/apache/james/smtpserver/mina/SMTPIoHandler.java (original) +++ james/server/trunk/smtpserver/src/main/java/org/apache/james/smtpserver/mina/SMTPIoHandler.java Sat Feb 13 08:59:59 2010 @@ -28,7 +28,9 @@ import org.apache.james.protocols.smtp.SMTPRetCode; import org.apache.james.protocols.smtp.SMTPSession; import org.apache.james.socket.mina.AbstractIoHandler; +import org.apache.james.socket.mina.codec.LineLengthExceededException; import org.apache.mina.core.session.IoSession; +import org.apache.mina.filter.codec.ProtocolDecoderException; import org.apache.mina.filter.ssl.SslContextFactory; /** @@ -60,12 +62,22 @@ */ public void exceptionCaught(IoSession session, Throwable exception) throws Exception { - logger.error("Caught exception: " + session.getCurrentWriteMessage(), + logger.debug("Caught exception: " + session.getCurrentWriteMessage(), exception); - + if (exception instanceof ProtocolDecoderException) { + ProtocolDecoderException e = (ProtocolDecoderException) exception; + if (e.getCause() instanceof LineLengthExceededException) { + session.write(new SMTPResponse(SMTPRetCode.SYNTAX_ERROR_COMMAND_UNRECOGNIZED, "Line length exceeded. See RFC 2821 #4.5.3.1.")); + return; + } + } + + if (session.isConnected()) { session.write(new SMTPResponse(SMTPRetCode.LOCAL_ERROR, "Unable to process smtp request")); } + + } @Override Modified: james/server/trunk/smtpserver/src/test/java/org/apache/james/smtpserver/AsyncSMTPServerTest.java URL: http://svn.apache.org/viewvc/james/server/trunk/smtpserver/src/test/java/org/apache/james/smtpserver/AsyncSMTPServerTest.java?rev=909776&r1=909775&r2=909776&view=diff ============================================================================== --- james/server/trunk/smtpserver/src/test/java/org/apache/james/smtpserver/AsyncSMTPServerTest.java (original) +++ james/server/trunk/smtpserver/src/test/java/org/apache/james/smtpserver/AsyncSMTPServerTest.java Sat Feb 13 08:59:59 2010 @@ -50,6 +50,7 @@ import org.apache.james.services.MailServer; import org.apache.james.smtpserver.mina.AsyncSMTPServer; import org.apache.james.socket.ProtocolHandlerChainImpl; +import org.apache.james.socket.mina.codec.CRLFTerminatedLineDecoder; import org.apache.james.test.mock.DummyVirtualUserTableStore; import org.apache.james.test.mock.avalon.MockStore; import org.apache.james.test.mock.james.MockFileSystem; @@ -160,6 +161,8 @@ protected void setUp() throws Exception { setUpFakeLoader(); + SimpleLog log = new SimpleLog("Mock"); + log.setLevel(SimpleLog.LOG_LEVEL_ALL); m_testConfiguration = new SMTPTestConfiguration(m_smtpListenerPort); m_smtpServer = new AsyncSMTPServer(); @@ -168,11 +171,11 @@ chain = new ProtocolHandlerChainImpl(); chain.setInstanceFactory(m_serviceManager); - chain.setLog(new SimpleLog("ChainLog")); + chain.setLog(log); m_smtpServer.setProtocolHandlerChain(chain); - m_smtpServer.setLog(new SimpleLog("Mock")); + m_smtpServer.setLog(log); m_smtpServer.setMailServer(m_mailServer); } @@ -264,6 +267,28 @@ // mail was propagated by SMTPServer assertNotNull("mail received by mail server", m_mailServer.getLastMail()); } + + public void testMaxLineLength() throws Exception { + finishSetUp(m_testConfiguration); + + SMTPClient smtpProtocol = new SMTPClient(); + smtpProtocol.connect("127.0.0.1", m_smtpListenerPort); + + StringBuffer sb = new StringBuffer(); + for (int i = 0; i < CRLFTerminatedLineDecoder.DEFAULT_MAX_LINE_LENTH; i++) { + sb.append("A"); + } + smtpProtocol.sendCommand("EHLO " + sb.toString()); + System.out.println(smtpProtocol.getReplyString()); + assertEquals("Line length exceed", 500, smtpProtocol.getReplyCode()); + + smtpProtocol.sendCommand("EHLO test"); + assertEquals("Line length ok", 250, smtpProtocol.getReplyCode()); + + + smtpProtocol.quit(); + smtpProtocol.disconnect(); + } public void testStartTLSInEHLO() throws Exception { m_testConfiguration.setStartTLS(); --------------------------------------------------------------------- To unsubscribe, e-mail: server-dev-unsubscr...@james.apache.org For additional commands, e-mail: server-dev-h...@james.apache.org