This patch will improve performance by reducing time spent in creating scanner buffers.
Also changes the internal entity buffer size to 512.



Ankit Pasricha
XML Parser Development
IBM Toronto Lab
8200 Warden Avenue, Ontario L6G 1C7
Phone: (905) 413 4941
Index: XMLEntityManager.java
===================================================================
RCS file: 
/home/cvspublic/xml-xerces/java/src/org/apache/xerces/impl/XMLEntityManager.java,v
retrieving revision 1.89
diff -u -r1.89 XMLEntityManager.java
--- XMLEntityManager.java       4 Oct 2004 21:45:49 -0000       1.89
+++ XMLEntityManager.java       19 Oct 2004 18:08:57 -0000
@@ -16,19 +16,19 @@
 
 package org.apache.xerces.impl;
 
-import java.lang.reflect.Method;
 import java.io.IOException;
 import java.io.InputStream;
 import java.io.InputStreamReader;
 import java.io.Reader;
 import java.io.StringReader;
+import java.lang.reflect.Method;
 import java.net.HttpURLConnection;
 import java.net.URL;
 import java.net.URLConnection;
 import java.util.Hashtable;
 import java.util.Iterator;
-import java.util.Map;
 import java.util.Locale;
+import java.util.Map;
 import java.util.Stack;
 
 import org.apache.xerces.impl.io.ASCIIReader;
@@ -53,6 +53,9 @@
 import org.apache.xerces.xni.parser.XMLConfigurationException;
 import org.apache.xerces.xni.parser.XMLEntityResolver;
 import org.apache.xerces.xni.parser.XMLInputSource;
+import org.xml.sax.SAXException;
+import org.xml.sax.SAXNotRecognizedException;
+import org.xml.sax.SAXNotSupportedException;
 
 /**
  * The entity manager handles the registration of general and parameter
@@ -93,8 +96,8 @@
     /** Default buffer size before we've finished with the XMLDecl:  */
     public static final int DEFAULT_XMLDECL_BUFFER_SIZE = 64;
 
-    /** Default internal entity buffer size (1024). */
-    public static final int DEFAULT_INTERNAL_BUFFER_SIZE = 1024;
+    /** Default internal entity buffer size (512). */
+    public static final int DEFAULT_INTERNAL_BUFFER_SIZE = 512;
 
     // feature identifiers
 
@@ -349,6 +352,8 @@
     
     /** Augmentations for entities. */
     private final Augmentations fEntityAugs = new AugmentationsImpl();
+    
+    private CharacterBufferPool fBufferPool = new CharacterBufferPool(fBufferSize, 
DEFAULT_INTERNAL_BUFFER_SIZE);
 
     //
     // Constructors
@@ -1408,6 +1413,7 @@
                     bufferSize.intValue() > DEFAULT_XMLDECL_BUFFER_SIZE) {
                     fBufferSize = bufferSize.intValue();
                     fEntityScanner.setBufferSize(fBufferSize);
+                    fBufferPool.setExternalBufferSize(fBufferSize);
                 }
             }
             if (suffixLength == Constants.SECURITY_MANAGER_PROPERTY.length() && 
@@ -1778,6 +1784,9 @@
             fReaderStack.pop();
         } 
 
+        //Release the character buffer back to the pool for reuse
+        fBufferPool.returnToPool(fCurrentEntity.fBuffer);
+        
         // Pop entity stack.
         fCurrentEntity = fEntityStack.size() > 0
                        ? (ScannedEntity)fEntityStack.pop() : null;
@@ -2418,6 +2427,9 @@
 
         // to allow the reader/inputStream to behave efficiently:
         public boolean mayReadChunks;
+        
+        private CharacterBuffer fBuffer;
+        
 
         //
         // Constructors
@@ -2436,7 +2448,8 @@
             this.literal = literal;
             this.mayReadChunks = mayReadChunks;
             this.isExternal = isExternal;
-            this.ch = new char[isExternal ? fBufferSize : 
DEFAULT_INTERNAL_BUFFER_SIZE];
+            this.fBuffer = fBufferPool.getBuffer(isExternal);
+            this.ch = fBuffer.ch;
         } // <init>(StringXMLResourceIdentifier,InputStream,Reader,String,boolean, 
boolean)
 
         //
Index: CharacterBuffer.java
===================================================================
RCS file: CharacterBuffer.java
diff -N CharacterBuffer.java
--- /dev/null   1 Jan 1970 00:00:00 -0000
+++ CharacterBuffer.java        1 Jan 1970 00:00:00 -0000
@@ -0,0 +1,38 @@
+/*
+ * Copyright 2004 The Apache Software Foundation.
+ * 
+ * Licensed 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.
+ */
+package org.apache.xerces.impl;
+
+/**
+ * Buffer used in entity manager to reuse character arrays instead
+ * of creating new ones every time.
+ * 
+ * @xerces.internal
+ * 
+ * @author Ankit Pasricha, IBM
+ */
+class CharacterBuffer {
+
+       char[] ch;
+       boolean isExternal;
+       
+       /**
+        * 
+        */
+       CharacterBuffer(boolean isExternal, int size) {
+               this.isExternal = isExternal;
+               ch = new char[size];
+       }
+}
Index: CharacterBufferPool.java
===================================================================
RCS file: CharacterBufferPool.java
diff -N CharacterBufferPool.java
--- /dev/null   1 Jan 1970 00:00:00 -0000
+++ CharacterBufferPool.java    1 Jan 1970 00:00:00 -0000
@@ -0,0 +1,112 @@
+/*
+ * Copyright 2004 The Apache Software Foundation.
+ * 
+ * Licensed 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.
+ */
+package org.apache.xerces.impl;
+
+
+/**
+ * Stores a number of character buffers and provides it to the entity
+ * manager to use when an entity is seen.
+ * 
+ * @xerces.internal 
+ * 
+ * @author Ankit Pasricha, IBM
+ */
+class CharacterBufferPool {
+
+       private static final int DEFAULT_POOL_SIZE = 3;
+       
+       private CharacterBuffer[] fInternalBufferPool;
+       private CharacterBuffer[] fExternalBufferPool;
+
+       int fExternalBufferSize;
+       int fInternalBufferSize;
+       int poolSize;
+       
+       private int fInternalTop;
+       private int fExternalTop;
+       /**
+        * 
+        */
+       CharacterBufferPool(int externalBufferSize, int internalBufferSize) {
+               this(DEFAULT_POOL_SIZE, externalBufferSize, internalBufferSize);
+       }
+       
+       /**
+        * 
+        */
+       CharacterBufferPool(int poolSize, int externalBufferSize, int 
internalBufferSize) {
+               
+               this.fExternalBufferSize = externalBufferSize;
+               this.fInternalBufferSize = internalBufferSize;
+               this.poolSize = poolSize;
+               
+               init();
+       }
+       
+       /**
+        * @param poolSize
+        * @param externalBufferSize
+        * @param internalBufferSize
+        */
+       private void init() {
+               fInternalBufferPool = new CharacterBuffer[poolSize];
+               fExternalBufferPool = new CharacterBuffer[poolSize];
+               
+               for(int i = 0; i < poolSize; i++) {
+                       fInternalBufferPool[i] = new CharacterBuffer(false, 
fExternalBufferSize);
+                       fExternalBufferPool[i] = new CharacterBuffer(true, 
fInternalBufferSize);
+               }
+               fInternalTop = poolSize - 1;
+               fExternalTop = poolSize - 1;
+       }
+
+       CharacterBuffer getBuffer(boolean external) {
+               if(external) {
+                       if(fExternalTop > -1) {
+                               return 
(CharacterBuffer)fExternalBufferPool[fExternalTop--];
+                       }
+                       else {
+                               return new CharacterBuffer(true, fExternalBufferSize);
+                       }
+               }
+               else {
+                       if(fInternalTop > -1) {
+                               return 
(CharacterBuffer)fInternalBufferPool[fInternalTop--];
+                       }
+                       else {
+                               return new CharacterBuffer(false, fInternalBufferSize);
+                       }
+               }
+       }
+       
+       void returnToPool(CharacterBuffer buffer) {
+               if(buffer.isExternal) {
+                       if(fExternalTop < fExternalBufferPool.length - 1)
+                               fExternalBufferPool[++fExternalTop] = buffer;
+               }
+               else if(fInternalTop < fInternalBufferPool.length - 1) {
+                       fInternalBufferPool[++fInternalTop] = buffer;
+               }
+       }
+
+       /**
+        * @param bufferSize
+        */
+       public void setExternalBufferSize(int bufferSize) {
+               this.fExternalBufferSize = bufferSize;
+               init();
+       }
+}
---------------------------------------------------------------------
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]

Reply via email to