You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@mina.apache.org by ng...@apache.org on 2011/02/07 23:57:25 UTC

svn commit: r1068204 - in /mina/vysper/trunk/nbxml/src: main/java/org/apache/vysper/xml/sax/impl/XMLParser.java main/java/org/apache/vysper/xml/sax/impl/XMLTokenizer.java test/java/org/apache/vysper/xml/sax/impl/ParseElementsTestCase.java

Author: ngn
Date: Mon Feb  7 22:57:24 2011
New Revision: 1068204

URL: http://svn.apache.org/viewvc?rev=1068204&view=rev
Log:
Fixing bug when getting split buffers during XML parsing (VYSPER-265). Patch by Eilon Yardeni, thanks

Modified:
    mina/vysper/trunk/nbxml/src/main/java/org/apache/vysper/xml/sax/impl/XMLParser.java
    mina/vysper/trunk/nbxml/src/main/java/org/apache/vysper/xml/sax/impl/XMLTokenizer.java
    mina/vysper/trunk/nbxml/src/test/java/org/apache/vysper/xml/sax/impl/ParseElementsTestCase.java

Modified: mina/vysper/trunk/nbxml/src/main/java/org/apache/vysper/xml/sax/impl/XMLParser.java
URL: http://svn.apache.org/viewvc/mina/vysper/trunk/nbxml/src/main/java/org/apache/vysper/xml/sax/impl/XMLParser.java?rev=1068204&r1=1068203&r2=1068204&view=diff
==============================================================================
--- mina/vysper/trunk/nbxml/src/main/java/org/apache/vysper/xml/sax/impl/XMLParser.java (original)
+++ mina/vysper/trunk/nbxml/src/main/java/org/apache/vysper/xml/sax/impl/XMLParser.java Mon Feb  7 22:57:24 2011
@@ -335,6 +335,7 @@ public class XMLParser implements TokenL
         elements.clear();
         nsResolver = new ParserNamespaceResolver();
         sentStartDocument = false;
+        tokenizer.restart();
     }
 
     private void xmlDeclaration() {

Modified: mina/vysper/trunk/nbxml/src/main/java/org/apache/vysper/xml/sax/impl/XMLTokenizer.java
URL: http://svn.apache.org/viewvc/mina/vysper/trunk/nbxml/src/main/java/org/apache/vysper/xml/sax/impl/XMLTokenizer.java?rev=1068204&r1=1068203&r2=1068204&view=diff
==============================================================================
--- mina/vysper/trunk/nbxml/src/main/java/org/apache/vysper/xml/sax/impl/XMLTokenizer.java (original)
+++ mina/vysper/trunk/nbxml/src/main/java/org/apache/vysper/xml/sax/impl/XMLTokenizer.java Mon Feb  7 22:57:24 2011
@@ -38,7 +38,7 @@ public class XMLTokenizer {
         START, IN_TAG, IN_STRING, IN_DOUBLE_ATTRIBUTE_VALUE, IN_SINGLE_ATTRIBUTE_VALUE, IN_TEXT, CLOSED
     }
 
-    private int lastPosition = 0;
+    private final IoBuffer buffer = IoBuffer.allocate(16).setAutoExpand(true);
 
     private State state = State.START;
 
@@ -59,8 +59,6 @@ public class XMLTokenizer {
      * @throws Exception
      */
     public void parse(IoBuffer byteBuffer, CharsetDecoder decoder) throws SAXException {
-        lastPosition = byteBuffer.position();
-
         while (byteBuffer.hasRemaining() && state != State.CLOSED) {
             char c = (char) byteBuffer.get();
 
@@ -70,12 +68,15 @@ public class XMLTokenizer {
                     state = State.IN_TAG;
                 } else {
                     state = State.IN_TEXT;
+                    buffer.put((byte) c);
                 }
             } else if (state == State.IN_TEXT) {
                 if (c == '<') {
                     emit(byteBuffer, decoder);
                     emit(c, byteBuffer);
                     state = State.IN_TAG;
+                } else {
+                    buffer.put((byte) c);
                 }
             } else if (state == State.IN_TAG) {
                 if (c == '>') {
@@ -92,9 +93,10 @@ public class XMLTokenizer {
                 } else if (isControlChar(c)) {
                     emit(c, byteBuffer);
                 } else if (Character.isWhitespace(c)) {
-                    lastPosition = byteBuffer.position();
+                    buffer.clear();
                 } else {
                     state = State.IN_STRING;
+                    buffer.put((byte) c);
                 }
             } else if (state == State.IN_STRING) {
                 if (c == '>') {
@@ -109,28 +111,35 @@ public class XMLTokenizer {
                     emit(byteBuffer, CharsetUtil.UTF8_DECODER);
                     state = State.IN_TAG;
                 } else {
-                    // do nothing
+                    buffer.put((byte) c);
                 }
             } else if (state == State.IN_DOUBLE_ATTRIBUTE_VALUE) {
                 if (c == '"') {
                     emit(byteBuffer, decoder);
                     emit(c, byteBuffer);
                     state = State.IN_TAG;
+                } else {
+                    buffer.put((byte) c);
                 }
             } else if (state == State.IN_SINGLE_ATTRIBUTE_VALUE) {
                 if (c == '\'') {
                     emit(byteBuffer, decoder);
                     emit(c, byteBuffer);
                     state = State.IN_TAG;
+                } else {
+                    buffer.put((byte) c);
                 }
             }
         }
-
-        byteBuffer.position(lastPosition);
     }
 
     public void close() {
         state = State.CLOSED;
+        buffer.clear();
+    }
+
+    public void restart() {
+        buffer.clear();
     }
 
     private boolean isControlChar(char c) {
@@ -139,24 +148,15 @@ public class XMLTokenizer {
 
     private void emit(char token, IoBuffer byteBuffer) throws SAXException {
         listener.token(token, null);
-
-        lastPosition = byteBuffer.position();
     }
 
     private void emit(IoBuffer byteBuffer, CharsetDecoder decoder) throws SAXException {
-        int endPosition = byteBuffer.position();
-        int oldLimit = byteBuffer.limit();
-        byteBuffer.position(lastPosition);
-        byteBuffer.limit(endPosition - 1);
-
         try {
-            listener.token(NO_CHAR, byteBuffer.getString(decoder));
+            buffer.flip();
+            listener.token(NO_CHAR, buffer.getString(decoder));
+            buffer.clear();
         } catch (CharacterCodingException e) {
             throw new SAXException(e);
         }
-        byteBuffer.limit(oldLimit);
-        byteBuffer.position(endPosition);
-        lastPosition = byteBuffer.position();
-
     }
 }

Modified: mina/vysper/trunk/nbxml/src/test/java/org/apache/vysper/xml/sax/impl/ParseElementsTestCase.java
URL: http://svn.apache.org/viewvc/mina/vysper/trunk/nbxml/src/test/java/org/apache/vysper/xml/sax/impl/ParseElementsTestCase.java?rev=1068204&r1=1068203&r2=1068204&view=diff
==============================================================================
--- mina/vysper/trunk/nbxml/src/test/java/org/apache/vysper/xml/sax/impl/ParseElementsTestCase.java (original)
+++ mina/vysper/trunk/nbxml/src/test/java/org/apache/vysper/xml/sax/impl/ParseElementsTestCase.java Mon Feb  7 22:57:24 2011
@@ -20,7 +20,11 @@
 package org.apache.vysper.xml.sax.impl;
 
 import java.util.Iterator;
+import java.util.Map.Entry;
 
+import org.apache.mina.core.buffer.IoBuffer;
+import org.apache.vysper.charset.CharsetUtil;
+import org.apache.vysper.xml.sax.NonBlockingXMLReader;
 import org.apache.vysper.xml.sax.impl.TestHandler.TestEvent;
 
 /**
@@ -166,4 +170,28 @@ public class ParseElementsTestCase exten
 
         assertNoMoreevents(events);
     }
+    
+    public void testSplitBuffers() throws Exception {
+        TestHandler handler = new TestHandler();
+        NonBlockingXMLReader reader = new DefaultNonBlockingXMLReader();
+
+        reader.setContentHandler(handler);
+        reader.setErrorHandler(handler);
+
+        String xml1 = "<root></r";
+        String xml2 = "oot>";
+        
+        reader.parse(IoBuffer.wrap(xml1.getBytes("UTF-8")), CharsetUtil.UTF8_DECODER);
+        reader.parse(IoBuffer.wrap(xml2.getBytes("UTF-8")), CharsetUtil.UTF8_DECODER);
+
+        Iterator<TestEvent> events = handler.getEvents().iterator();
+ 
+        assertStartDocument(events.next());
+        assertStartElement("", "root", "root", events.next());
+        assertEndElement("", "root", "root", events.next());
+        assertEndDocument(events.next());
+
+        assertNoMoreevents(events);
+    }
+
 }
\ No newline at end of file