Author: pauls
Date: Sun Apr 13 12:10:39 2008
New Revision: 647612

URL: http://svn.apache.org/viewvc?rev=647612&view=rev
Log:
Cache filters and create an index for objectclass to improve service lookup 
performance.

Modified:
    
felix/trunk/framework/src/main/java/org/apache/felix/framework/FilterImpl.java
    
felix/trunk/framework/src/main/java/org/apache/felix/framework/util/ldap/Parser.java

Modified: 
felix/trunk/framework/src/main/java/org/apache/felix/framework/FilterImpl.java
URL: 
http://svn.apache.org/viewvc/felix/trunk/framework/src/main/java/org/apache/felix/framework/FilterImpl.java?rev=647612&r1=647611&r2=647612&view=diff
==============================================================================
--- 
felix/trunk/framework/src/main/java/org/apache/felix/framework/FilterImpl.java 
(original)
+++ 
felix/trunk/framework/src/main/java/org/apache/felix/framework/FilterImpl.java 
Sun Apr 13 12:10:39 2008
@@ -35,6 +35,7 @@
 **/
 public class FilterImpl implements Filter
 {
+    private static final WeakHashMap m_programCache = new WeakHashMap();
     private final ThreadLocal m_cache = new ThreadLocal();
     private final Logger m_logger;
     private final Object[] m_program;
@@ -57,29 +58,44 @@
         {
             throw new InvalidSyntaxException("Filter cannot be null", null);
         }
-
-        CharArrayReader car = new CharArrayReader(expr.toCharArray());
-        LdapLexer lexer = new LdapLexer(car);
-        Parser parser = new Parser(lexer);
-        try
+        Object[] program = null;
+        synchronized (m_programCache)
+        {
+            program = (Object[]) m_programCache.get(expr);
+        }
+        if (program == null)
         {
-            if (!parser.start())
+            CharArrayReader car = new CharArrayReader(expr.toCharArray());
+            LdapLexer lexer = new LdapLexer(car);
+            Parser parser = new Parser(lexer);
+            try
+            {
+                if (!parser.start())
+                {
+                    throw new InvalidSyntaxException(
+                        "Failed to parse LDAP query.", expr);
+                }
+            }
+            catch (ParseException ex)
             {
                 throw new InvalidSyntaxException(
-                    "Failed to parse LDAP query.", expr);
+                   ex.getMessage(), expr);
+            }
+            catch (IOException ex)
+            {
+                throw new InvalidSyntaxException(
+                    ex.getMessage(), expr);
+            }
+            program = parser.getProgram();
+            synchronized (m_programCache)
+            {
+                if (!m_programCache.containsKey(expr))
+                {
+                    m_programCache.put(expr, program);
+                }
             }
         }
-        catch (ParseException ex)
-        {
-            throw new InvalidSyntaxException(
-               ex.getMessage(), expr);
-        }
-        catch (IOException ex)
-        {
-            throw new InvalidSyntaxException(
-                ex.getMessage(), expr);
-        }
-        m_program = parser.getProgram();
+        m_program = program;
     }
 
     /**
@@ -254,7 +270,7 @@
         public void setSource(Dictionary dict, boolean caseSensitive)
         {
             // Create a map if we don't have one.
-            
+
             if (m_map == null)
             {
                 m_map = new StringMap();

Modified: 
felix/trunk/framework/src/main/java/org/apache/felix/framework/util/ldap/Parser.java
URL: 
http://svn.apache.org/viewvc/felix/trunk/framework/src/main/java/org/apache/felix/framework/util/ldap/Parser.java?rev=647612&r1=647611&r2=647612&view=diff
==============================================================================
--- 
felix/trunk/framework/src/main/java/org/apache/felix/framework/util/ldap/Parser.java
 (original)
+++ 
felix/trunk/framework/src/main/java/org/apache/felix/framework/util/ldap/Parser.java
 Sun Apr 13 12:10:39 2008
@@ -257,6 +257,11 @@
         switch (kind)
         {
             case SIMPLE :
+                if ("objectClass".equals(attr.toString()) && (op == '='))
+                {
+                    program.add(new ObjectClassOperator((String) 
pieces.get(0)));
+                    return true;
+                }
                 // Code: Push(attr); Constant(pieces.get(0)); <operator>();
                 program.add(new PushOperator(attr.toString()));
                 program.add(new ConstOperator(pieces.get(0)));
@@ -534,8 +539,7 @@
     }
 
     // Exclusive inner classes
-
-    private static class AndOperator extends Operator
+    private static final class AndOperator extends Operator
     {
         private int operandCount;
 
@@ -600,7 +604,7 @@
         }
     }
 
-    private static class OrOperator extends Operator
+    private static final class OrOperator extends Operator
     {
         private int operandCount;
 
@@ -665,7 +669,7 @@
         }
     }
 
-    private static class NotOperator extends Operator
+    private static final class NotOperator extends Operator
     {
         public NotOperator()
         {
@@ -706,7 +710,50 @@
         }
     }
 
-    private static class EqualOperator extends Operator
+    private static final class ObjectClassOperator extends Operator
+    {
+        public final String m_target;
+        
+        public ObjectClassOperator(String target)
+        {
+            m_target = target;
+        }
+
+        public void buildTree(Stack operands)
+        {
+            operands.push(this);
+        }
+
+        public void execute(Stack operands, Mapper mapper)
+            throws EvaluationException
+        {
+            String[] objectClass = (String[]) mapper.lookup("objectClass");
+            if (objectClass != null)
+            {
+                for (int i = 0; i < objectClass.length; i++)
+                {
+                    if (m_target.equals(objectClass[i]))
+                    {
+                        operands.push(Boolean.TRUE);
+                        return;
+                    }
+                }
+            }
+            operands.push(Boolean.FALSE);
+        }
+
+        public String toString()
+        {
+            return "=()";
+        }
+
+        public void toStringInfix(StringBuffer b)
+        {
+            b.append('(').append("objectClass=").append(m_target).append(')');
+        }
+    }
+
+    private static final class EqualOperator extends Operator
     {
         public EqualOperator()
         {
@@ -766,7 +813,7 @@
         }
     }
 
-    private static class GreaterEqualOperator extends Operator
+    private static final class GreaterEqualOperator extends Operator
     {
         public GreaterEqualOperator()
         {
@@ -823,7 +870,7 @@
         }
     }
 
-    private static class LessEqualOperator extends Operator
+    private static final class LessEqualOperator extends Operator
     {
         public LessEqualOperator()
         {
@@ -879,7 +926,7 @@
         }
     }
 
-    private static class ApproxOperator extends Operator
+    private static final class ApproxOperator extends Operator
     {
         public ApproxOperator()
         {
@@ -935,7 +982,7 @@
         }
     }
 
-    private static class PresentOperator extends Operator
+    private static final class PresentOperator extends Operator
     {
         String attribute;
 
@@ -969,7 +1016,7 @@
         }
     }
 
-    private static class PushOperator extends Operator
+    private static final class PushOperator extends Operator
     {
         String attribute;
 
@@ -1012,7 +1059,7 @@
         }
     }
 
-    private static class ConstOperator extends Operator
+    private static final class ConstOperator extends Operator
     {
         Object val;
 
@@ -1048,7 +1095,7 @@
         }
     }
 
-    private static class SubStringOperator extends Operator
+    private static final class SubStringOperator extends Operator
         implements OperatorConstants
     {
         String[] pieces;


Reply via email to