directory-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From elecha...@apache.org
Subject svn commit: r427793 [2/6] - in /directory/branches/shared/0.9.5: asn1/src/main/java/org/apache/directory/shared/asn1/ber/ asn1/src/main/java/org/apache/directory/shared/asn1/ber/grammar/ ldap/ ldap/src/main/antlr/ ldap/src/main/java/org/apache/director...
Date Tue, 01 Aug 2006 23:35:23 GMT
Modified: directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/FilterGrammar.java
URL: http://svn.apache.org/viewvc/directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/FilterGrammar.java?rev=427793&r1=427792&r2=427793&view=diff
==============================================================================
--- directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/FilterGrammar.java (original)
+++ directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/FilterGrammar.java Tue Aug  1 16:35:20 2006
@@ -70,109 +70,106 @@
         // Create the transitions table
         super.transitions = new GrammarTransition[LdapStatesEnum.LAST_FILTER_STATE][256];
 
-        // ============================================================================================
+        //============================================================================================
         // Search Request And Filter
         // This is quite complicated, because we have a tree structure to build,
-        // and we may have many elements on each node. For instance, considering
-        // the
+        // and we may have many elements on each node. For instance, considering the 
         // search filter :
         // (& (| (a = b) (c = d)) (! (e = f)) (attr =* h))
         // We will have to create an And filter with three children :
-        // - an Or child,
-        // - a Not child
-        // - and a Present child.
+        //  - an Or child,
+        //  - a Not child
+        //  - and a Present child.
         // The Or child will also have two children.
         //
-        // We know when we have a children while decoding the PDU, because the
-        // length
+        // We know when we have a children while decoding the PDU, because the length
         // of its parent has not yet reached its expected length.
         //
         // This search filter :
         // (&(|(objectclass=top)(ou=contacts))(!(objectclass=ttt))(objectclass=*top))
         // is encoded like this :
-        // +----------------+---------------+
-        // | ExpectedLength | CurrentLength |
-        // +-----------------------------+----------------+---------------+
-        // |A0 52 | 82 | 0 | new level 1
-        // | A1 24 | 82 36 | 0 0 | new level 2
-        // | A3 12 | 82 36 18 | 0 0 0 | new level 3
-        // | 04 0B 'objectclass' | 82 36 18 | 0 0 13 |
-        // | 04 03 'top' | 82 36 18 | 0 20 18 |
-        // | | ^ ^ |
-        // | | | | |
-        // | | +---------------+ |
-        // +-----------------------------* end level 3 -------------------*
-        // | A3 0E | 82 36 14 | 0 0 0 | new level 3
-        // | 04 02 'ou' | 82 36 14 | 0 0 4 |
-        // | 04 08 'contacts' | 82 36 14 | 38 36 14 |
-        // | | ^ ^ ^ ^ |
-        // | | | | | | |
-        // | | | +-------------|--+ |
-        // | | +----------------+ |
-        // +-----------------------------* end level 3, end level 2 ------*
-        // | A2 14 | 82 20 | 38 0 | new level 2
-        // | A3 12 | 82 20 18 | 38 0 0 | new level 3
-        // | 04 0B 'objectclass' | 82 20 18 | 38 0 13 |
-        // | 04 03 'ttt' | 82 20 18 | 60 20 18 |
-        // | | ^ ^ ^ ^ |
-        // | | | | | | |
-        // | | | +-------------|--+ |
-        // | | +----------------+ |
-        // +-----------------------------* end level 3, end level 2 ------*
-        // | A4 14 | 82 20 | 60 0 | new level 2
-        // | 04 0B 'objectclass' | 82 20 | 60 13 |
-        // | 30 05 | 82 20 | 60 13 |
-        // | 82 03 'top' | 82 20 | 82 20 |
-        // | | ^ ^ ^ ^ |
-        // | | | | | | |
-        // | | | +-------------|--+ |
-        // | | +----------------+ |
-        // +-----------------------------* end level 2, end level 1 ------*
-        // +-----------------------------+----------------+---------------+
+        //                              +----------------+---------------+
+        //                              | ExpectedLength | CurrentLength |
+        //+-----------------------------+----------------+---------------+
+        //|A0 52                        | 82             | 0             | new level 1
+        //|   A1 24                     | 82 36          | 0 0           | new level 2
+        //|      A3 12                  | 82 36 18       | 0 0 0         | new level 3
+        //|         04 0B 'objectclass' | 82 36 18       | 0 0 13        |
+        //|         04 03 'top'         | 82 36 18       | 0 20 18       | 
+        //|                             |       ^               ^        |
+        //|                             |       |               |        |
+        //|                             |       +---------------+        |
+        //+-----------------------------* end level 3 -------------------*
+        //|      A3 0E                  | 82 36 14       | 0 0 0         | new level 3
+        //|         04 02 'ou'          | 82 36 14       | 0 0 4         |
+        //|         04 08 'contacts'    | 82 36 14       | 38 36 14      | 
+        //|                             |    ^  ^             ^  ^       |
+        //|                             |    |  |             |  |       |
+        //|                             |    |  +-------------|--+       |
+        //|                             |    +----------------+          |
+        //+-----------------------------* end level 3, end level 2 ------*
+        //|   A2 14                     | 82 20          | 38 0          | new level 2
+        //|      A3 12                  | 82 20 18       | 38 0 0        | new level 3
+        //|         04 0B 'objectclass' | 82 20 18       | 38 0 13       | 
+        //|         04 03 'ttt'         | 82 20 18       | 60 20 18      |
+        //|                             |    ^  ^             ^  ^       |
+        //|                             |    |  |             |  |       |
+        //|                             |    |  +-------------|--+       |
+        //|                             |    +----------------+          |
+        //+-----------------------------* end level 3, end level 2 ------*
+        //|   A4 14                     | 82 20          | 60 0          | new level 2
+        //|      04 0B 'objectclass'    | 82 20          | 60 13         |
+        //|      30 05                  | 82 20          | 60 13         |
+        //|         82 03 'top'         | 82 20          | 82 20         | 
+        //|                             | ^  ^             ^  ^          |
+        //|                             | |  |             |  |          |
+        //|                             | |  +-------------|--+          |
+        //|                             | +----------------+             |
+        //+-----------------------------* end level 2, end level 1 ------*
+        //+-----------------------------+----------------+---------------+
         //
         // When the current length equals the expected length of the parent PDU,
-        // then we are able to 'close' the parent : it has all its children.
-        // This
+        // then we are able to 'close' the parent : it has all its children. This
         // is propagated through all the tree, until either there are no more
         // parents, or the expected length of the parent is different from the
         // current length.
         //                              
-        // ============================================================================================
+        //============================================================================================
         // Filter ::= CHOICE {
-        // and [0] SET OF Filter, (Tag)
-        // ...
+        //     and             [0] SET OF Filter, (Tag)
+        //     ...
         // Nothing to do
         super.transitions[LdapStatesEnum.FILTER_TAG][LdapConstants.AND_FILTER_TAG] = new GrammarTransition(
             LdapStatesEnum.FILTER_TAG, LdapStatesEnum.FILTER_AND_VALUE, null );
 
         // Filter ::= CHOICE {
-        // ...
-        // or [1] SET OF Filter, (Tag)
-        // ...
+        //     ...
+        //     or              [1] SET OF Filter, (Tag)
+        //     ...
         // Nothing to do
         super.transitions[LdapStatesEnum.FILTER_TAG][LdapConstants.OR_FILTER_TAG] = new GrammarTransition(
             LdapStatesEnum.FILTER_TAG, LdapStatesEnum.FILTER_OR_VALUE, null );
 
         // Filter ::= CHOICE {
-        // ...
-        // not [2] Filter, (Tag)
-        // ...
+        //     ...
+        //     not             [2] Filter, (Tag)
+        //     ...
         // Nothing to do
         super.transitions[LdapStatesEnum.FILTER_TAG][LdapConstants.NOT_FILTER_TAG] = new GrammarTransition(
             LdapStatesEnum.FILTER_TAG, LdapStatesEnum.FILTER_NOT_VALUE, null );
 
         // Filter ::= CHOICE {
-        // ...
-        // equalityMatch [3] AttributeValueAssertion, (Tag)
-        // ...
+        //     ...
+        //     equalityMatch   [3] AttributeValueAssertion, (Tag)
+        //     ...
         // Nothing to do
         super.transitions[LdapStatesEnum.FILTER_TAG][LdapConstants.EQUALITY_MATCH_FILTER_TAG] = new GrammarTransition(
             LdapStatesEnum.FILTER_TAG, LdapStatesEnum.FILTER_EQUALITY_MATCH_VALUE, null );
 
         // Filter ::= CHOICE {
-        // ...
-        // substrings [4] SubstringFilter, (Tag)
-        // ...
+        //     ...
+        //     substrings      [4] SubstringFilter, (Tag)
+        //     ...
         // Nothing to do
         super.transitions[LdapStatesEnum.FILTER_TAG][LdapConstants.SUBSTRINGS_FILTER_TAG] = new GrammarTransition(
             LdapStatesEnum.FILTER_TAG, LdapStatesEnum.SUBSTRING_FILTER_GRAMMAR_SWITCH, new GrammarAction( "Allow pop" )
@@ -184,40 +181,40 @@
             } );
 
         // Filter ::= CHOICE {
-        // ...
-        // greaterOrEqual [5] AttributeValueAssertion, (Tag)
-        // ...
+        //     ...
+        //     greaterOrEqual  [5] AttributeValueAssertion, (Tag)
+        //     ...
         // Nothing to do
         super.transitions[LdapStatesEnum.FILTER_TAG][LdapConstants.GREATER_OR_EQUAL_FILTER_TAG] = new GrammarTransition(
             LdapStatesEnum.FILTER_TAG, LdapStatesEnum.FILTER_GREATER_OR_EQUAL_VALUE, null );
 
         // Filter ::= CHOICE {
-        // ...
-        // lessOrEqual [6] AttributeValueAssertion, (Tag)
-        // ...
+        //     ...
+        //     lessOrEqual     [6] AttributeValueAssertion, (Tag)
+        //     ...
         // Nothing to do
         super.transitions[LdapStatesEnum.FILTER_TAG][LdapConstants.LESS_OR_EQUAL_FILTER_TAG] = new GrammarTransition(
             LdapStatesEnum.FILTER_TAG, LdapStatesEnum.FILTER_LESS_OR_EQUAL_VALUE, null );
 
         // Filter ::= CHOICE {
-        // ...
-        // present [7] AttributeDescription, (Tag)
-        // ...
+        //     ...
+        //     present         [7] AttributeDescription, (Tag)
+        //     ...
         // Nothing to do
         super.transitions[LdapStatesEnum.FILTER_TAG][LdapConstants.PRESENT_FILTER_TAG] = new GrammarTransition(
             LdapStatesEnum.FILTER_TAG, LdapStatesEnum.FILTER_PRESENT_VALUE, null );
 
         // Filter ::= CHOICE {
-        // ...
-        // approxMatch [8] AttributeValueAssertion, (Tag)
-        // ...
+        //     ...
+        //     approxMatch     [8] AttributeValueAssertion, (Tag)
+        //     ...
         // Nothing to do
         super.transitions[LdapStatesEnum.FILTER_TAG][LdapConstants.APPROX_MATCH_FILTER_TAG] = new GrammarTransition(
             LdapStatesEnum.FILTER_TAG, LdapStatesEnum.FILTER_APPROX_MATCH_VALUE, null );
 
         // Filter ::= CHOICE {
-        // ...
-        // extensibleMatch [9] ExtensibleMatchFilter } (Tag)
+        //     ...
+        //     extensibleMatch [9] ExtensibleMatchFilter } (Tag)
         // Nothing to do
         super.transitions[LdapStatesEnum.FILTER_TAG][LdapConstants.EXTENSIBLE_MATCH_FILTER_TAG] = new GrammarTransition(
             LdapStatesEnum.FILTER_TAG, LdapStatesEnum.MATCHING_RULE_ASSERTION_GRAMMAR_SWITCH, new GrammarAction(
@@ -230,10 +227,9 @@
             } );
 
         // Filter ::= CHOICE {
-        // and [0] SET OF Filter, (Value)
-        // ...
-        // We just have to switch to the initial state of Filter, because this
-        // is what
+        //     and             [0] SET OF Filter, (Value)
+        //     ...
+        // We just have to switch to the initial state of Filter, because this is what
         // we will get !
         super.transitions[LdapStatesEnum.FILTER_AND_VALUE][LdapConstants.AND_FILTER_TAG] = new GrammarTransition(
             LdapStatesEnum.FILTER_AND_VALUE, LdapStatesEnum.FILTER_TAG, new GrammarAction( "Init And Filter" )
@@ -256,33 +252,16 @@
                     // We can allocate the SearchRequest
                     Filter andFilter = new AndFilter();
 
-                    // Get the parent, if any
-                    Filter currentFilter = searchRequest.getCurrentFilter();
-
-                    if ( currentFilter != null )
-                    {
-                        // Ok, we have a parent. The new Filter will be added to
-                        // this parent, then.
-                        ( ( ConnectorFilter ) currentFilter ).addFilter( andFilter );
-                        andFilter.setParent( currentFilter );
-                    }
-                    else
-                    {
-                        // No parent. This Filter will become the root.
-                        searchRequest.setFilter( andFilter );
-                        andFilter.setParent( searchRequest );
-                    }
-
-                    searchRequest.setCurrentFilter( andFilter );
+                    // Set the filter
+                    searchRequest.addCurrentFilter( andFilter );
                 }
             } );
 
         // Filter ::= CHOICE {
-        // ...
-        // or [1] SET OF Filter, (Value)
-        // ...
-        // We just have to switch to the initial state of Filter, because this
-        // is what
+        //     ...
+        //     or              [1] SET OF Filter, (Value)
+        //     ...
+        // We just have to switch to the initial state of Filter, because this is what
         // we will get !
         super.transitions[LdapStatesEnum.FILTER_OR_VALUE][LdapConstants.OR_FILTER_TAG] = new GrammarTransition(
             LdapStatesEnum.FILTER_OR_VALUE, LdapStatesEnum.FILTER_TAG, new GrammarAction( "Init Or Filter" )
@@ -305,33 +284,16 @@
                     // We can allocate the SearchRequest
                     Filter orFilter = new OrFilter();
 
-                    // Get the parent, if any
-                    Filter currentFilter = searchRequest.getCurrentFilter();
-
-                    if ( currentFilter != null )
-                    {
-                        // Ok, we have a parent. The new Filter will be added to
-                        // this parent, then.
-                        ( ( ConnectorFilter ) currentFilter ).addFilter( orFilter );
-                        orFilter.setParent( currentFilter );
-                    }
-                    else
-                    {
-                        // No parent. This Filter will become the root.
-                        searchRequest.setFilter( orFilter );
-                        orFilter.setParent( searchRequest );
-                    }
-
-                    searchRequest.setCurrentFilter( orFilter );
+                    // Set the filter
+                    searchRequest.addCurrentFilter( orFilter );
                 }
             } );
 
         // Filter ::= CHOICE {
-        // ...
-        // not [2] Filter, (Value)
-        // ...
-        // We just have to switch to the initial state of Filter, because this
-        // is what
+        //     ...
+        //     not             [2] Filter, (Value)
+        //     ...
+        // We just have to switch to the initial state of Filter, because this is what
         // we will get !
         super.transitions[LdapStatesEnum.FILTER_NOT_VALUE][LdapConstants.NOT_FILTER_TAG] = new GrammarTransition(
             LdapStatesEnum.FILTER_NOT_VALUE, LdapStatesEnum.FILTER_TAG, new GrammarAction( "Init Not Filter" )
@@ -354,33 +316,16 @@
                     // We can allocate the SearchRequest
                     Filter notFilter = new NotFilter();
 
-                    // Get the parent, if any
-                    Filter currentFilter = searchRequest.getCurrentFilter();
-
-                    if ( currentFilter != null )
-                    {
-                        // Ok, we have a parent. The new Filter will be added to
-                        // this parent, then.
-                        ( ( ConnectorFilter ) currentFilter ).addFilter( notFilter );
-                        notFilter.setParent( currentFilter );
-                    }
-                    else
-                    {
-                        // No parent. This Filter will become the root.
-                        searchRequest.setFilter( notFilter );
-                        notFilter.setParent( searchRequest );
-                    }
-
-                    searchRequest.setCurrentFilter( notFilter );
+                    // Set the filter
+                    searchRequest.addCurrentFilter( notFilter );
                 }
             } );
 
         // Filter ::= CHOICE {
-        // ...
-        // equalityMatch [3] AttributeValueAssertion, (Value)
-        // ...
-        // We will create the filter container (as this is an equalityMatch
-        // filter,
+        //     ...
+        //     equalityMatch   [3] AttributeValueAssertion, (Value)
+        //     ...
+        // We will create the filter container (as this is an equalityMatch filter,
         // we will create an AttributeValueAssertionFilter).
         super.transitions[LdapStatesEnum.FILTER_EQUALITY_MATCH_VALUE][LdapConstants.EQUALITY_MATCH_FILTER_TAG] = new GrammarTransition(
             LdapStatesEnum.FILTER_EQUALITY_MATCH_VALUE, LdapStatesEnum.FILTER_ATTRIBUTE_DESC_TAG, new GrammarAction(
@@ -388,16 +333,15 @@
             {
                 public void action( IAsn1Container container ) throws DecoderException
                 {
-                    compareFilterAction( container, LdapConstants.EQUALITY_MATCH_FILTER );
+                    terminalFilterAction( container, LdapConstants.EQUALITY_MATCH_FILTER );
                 }
             } );
 
         // Filter ::= CHOICE {
-        // ...
-        // greaterOrEqual [5] AttributeValueAssertion, (Value)
-        // ...
-        // We will create the filter container (as this is an GreaterOrEqual
-        // filter,
+        //     ...
+        //     greaterOrEqual  [5] AttributeValueAssertion, (Value)
+        //     ...
+        // We will create the filter container (as this is an GreaterOrEqual filter,
         // we will create an AttributeValueAssertionFilter).
         super.transitions[LdapStatesEnum.FILTER_GREATER_OR_EQUAL_VALUE][LdapConstants.GREATER_OR_EQUAL_FILTER_TAG] = new GrammarTransition(
             LdapStatesEnum.FILTER_GREATER_OR_EQUAL_VALUE, LdapStatesEnum.FILTER_ATTRIBUTE_DESC_TAG, new GrammarAction(
@@ -405,16 +349,15 @@
             {
                 public void action( IAsn1Container container ) throws DecoderException
                 {
-                    compareFilterAction( container, LdapConstants.GREATER_OR_EQUAL_FILTER );
+                    terminalFilterAction( container, LdapConstants.GREATER_OR_EQUAL_FILTER );
                 }
             } );
 
         // Filter ::= CHOICE {
-        // ...
-        // lessOrEqual [6] AttributeValueAssertion, (Value)
-        // ...
-        // We will create the filter container (as this is an lessOrEqual
-        // filter,
+        //     ...
+        //     lessOrEqual    [6] AttributeValueAssertion, (Value)
+        //     ...
+        // We will create the filter container (as this is an lessOrEqual filter,
         // we will create an AttributeValueAssertionFilter).
         super.transitions[LdapStatesEnum.FILTER_LESS_OR_EQUAL_VALUE][LdapConstants.LESS_OR_EQUAL_FILTER_TAG] = new GrammarTransition(
             LdapStatesEnum.FILTER_LESS_OR_EQUAL_VALUE, LdapStatesEnum.FILTER_ATTRIBUTE_DESC_TAG, new GrammarAction(
@@ -422,16 +365,15 @@
             {
                 public void action( IAsn1Container container ) throws DecoderException
                 {
-                    compareFilterAction( container, LdapConstants.LESS_OR_EQUAL_FILTER );
+                    terminalFilterAction( container, LdapConstants.LESS_OR_EQUAL_FILTER );
                 }
             } );
 
         // Filter ::= CHOICE {
-        // ...
-        // approxMatch [8] AttributeValueAssertion, (Value)
-        // ...
-        // We will create the filter container (as this is an approxMatch
-        // filter,
+        //     ...
+        //     approxMatch    [8] AttributeValueAssertion, (Value)
+        //     ...
+        // We will create the filter container (as this is an approxMatch filter,
         // we will create an AttributeValueAssertionFilter).
         super.transitions[LdapStatesEnum.FILTER_APPROX_MATCH_VALUE][LdapConstants.APPROX_MATCH_FILTER_TAG] = new GrammarTransition(
             LdapStatesEnum.FILTER_APPROX_MATCH_VALUE, LdapStatesEnum.FILTER_ATTRIBUTE_DESC_TAG, new GrammarAction(
@@ -439,20 +381,20 @@
             {
                 public void action( IAsn1Container container ) throws DecoderException
                 {
-                    compareFilterAction( container, LdapConstants.APPROX_MATCH_FILTER );
+                    terminalFilterAction( container, LdapConstants.APPROX_MATCH_FILTER );
                 }
             } );
 
         // AttributeValueAssertion ::= SEQUENCE {
-        // attributeDesc AttributeDescription, (TAG)
-        // ...
+        //    attributeDesc   AttributeDescription, (TAG)
+        //     ...
         // Nothing to do.
         super.transitions[LdapStatesEnum.FILTER_ATTRIBUTE_DESC_TAG][UniversalTag.OCTET_STRING_TAG] = new GrammarTransition(
             LdapStatesEnum.FILTER_ATTRIBUTE_DESC_TAG, LdapStatesEnum.FILTER_ATTRIBUTE_DESC_VALUE, null );
 
         // AttributeValueAssertion ::= SEQUENCE {
-        // attributeDesc AttributeDescription, (VALUE)
-        // ...
+        //    attributeDesc   AttributeDescription, (VALUE)
+        //     ...
         // We have to set the attribute description in the current filter.
         // It could be an equalityMatch, greaterOrEqual, lessOrEqual or an
         // approxMatch filter.
@@ -482,22 +424,22 @@
                         throw new DecoderException( "Invalid assertion description " + msg + ", : " + lsee.getMessage() );
                     }
 
-                    AttributeValueAssertionFilter currentFilter = ( AttributeValueAssertionFilter ) searchRequest
-                        .getCurrentFilter();
-                    currentFilter.setAssertion( assertion );
+                    AttributeValueAssertionFilter comparisonFilter = ( AttributeValueAssertionFilter ) searchRequest
+                        .getTerminalFilter();
+                    comparisonFilter.setAssertion( assertion );
                 }
             } );
 
         // AttributeValueAssertion ::= SEQUENCE {
-        // ...
-        // assertionValue AssertionValue } (TAG)
+        //     ...
+        //    assertionValue  AssertionValue } (TAG)
         // Nothing to do.
         super.transitions[LdapStatesEnum.FILTER_ASSERTION_VALUE_TAG][UniversalTag.OCTET_STRING_TAG] = new GrammarTransition(
             LdapStatesEnum.FILTER_ASSERTION_VALUE_TAG, LdapStatesEnum.FILTER_ASSERTION_VALUE_VALUE, null );
 
         // AttributeValueAssertion ::= SEQUENCE {
-        // ...
-        // assertionValue AssertionValue } (VALUE)
+        //     ...
+        //    assertionValue  AssertionValue } (VALUE)
         // We have to set the attribute description in the current filter.
         // It could be an equalityMatch, greaterOrEqual, lessOrEqual or an
         // approxMatch filter.
@@ -522,9 +464,9 @@
                         assertionValue = tlv.getValue().getData();
                     }
 
-                    AttributeValueAssertionFilter currentFilter = ( AttributeValueAssertionFilter ) searchRequest
-                        .getCurrentFilter();
-                    AttributeValueAssertion assertion = currentFilter.getAssertion();
+                    AttributeValueAssertionFilter terminalFilter = ( AttributeValueAssertionFilter ) searchRequest
+                        .getTerminalFilter();
+                    AttributeValueAssertion assertion = terminalFilter.getAssertion();
 
                     if ( ldapMessageContainer.isBinary( assertion.getAttributeDesc() ) )
                     {
@@ -537,14 +479,15 @@
 
                     // We now have to get back to the nearest filter which is
                     // not terminal.
-                    unstackFilters( container );
+                    searchRequest.unstackFilters( container );
+
                     container.grammarPopAllowed( true );
                 }
             } );
 
         // AttributeValueAssertion ::= SEQUENCE {
-        // attributeDesc AttributeDescription, (VALUE)
-        // ...
+        //    attributeDesc   AttributeDescription, (VALUE)
+        //     ...
         // We have to set the attribute description in the current filter.
         // It could be an equalityMatch, greaterOrEqual, lessOrEqual or an
         // approxMatch filter.
@@ -581,24 +524,24 @@
                             throw new DecoderException( "Invalid assertion value " + msg + ", : " + lsee.getMessage() );
                         }
 
-                        AttributeValueAssertionFilter currentFilter = ( AttributeValueAssertionFilter ) searchRequest
-                            .getCurrentFilter();
-                        currentFilter.setAssertion( assertion );
+                        AttributeValueAssertionFilter terminalFilter = ( AttributeValueAssertionFilter ) searchRequest
+                            .getTerminalFilter();
+                        terminalFilter.setAssertion( assertion );
                     }
                 }
             } );
 
         // AttributeValueAssertion ::= SEQUENCE {
-        // ...
-        // assertionValue AssertionValue } (TAG)
+        //     ...
+        //    assertionValue  AssertionValue } (TAG)
         // Nothing to do.
         super.transitions[LdapStatesEnum.FILTER_ASSERTION_VALUE_TAG][UniversalTag.OCTET_STRING_TAG] = new GrammarTransition(
             LdapStatesEnum.FILTER_ASSERTION_VALUE_TAG, LdapStatesEnum.FILTER_ASSERTION_VALUE_VALUE, null );
 
         // Filter ::= CHOICE {
-        // ...
-        // present [7] AttributeDescription, (Value)
-        // ...
+        //     ...
+        //     present    [7] AttributeDescription, (Value)
+        //     ...
         super.transitions[LdapStatesEnum.FILTER_PRESENT_VALUE][LdapConstants.PRESENT_FILTER_TAG] = new GrammarTransition(
             LdapStatesEnum.FILTER_PRESENT_VALUE, LdapStatesEnum.FILTER_TAG, new GrammarAction(
                 "Init present filter Value" )
@@ -614,23 +557,9 @@
                     // We can allocate the Attribute Value Assertion
                     PresentFilter presentFilter = new PresentFilter();
 
-                    // Get the parent, if any
-                    Filter currentFilter = searchRequest.getCurrentFilter();
-
-                    if ( currentFilter != null )
-                    {
-                        // Ok, we have a parent. The new Filter will be added to
-                        // this parent, then.
-                        ( ( ConnectorFilter ) currentFilter ).addFilter( presentFilter );
-                        presentFilter.setParent( currentFilter );
-                    }
-                    else
-                    {
-                        // No parent. This Filter will become the root.
-                        // searchRequest.setCurrentFilter(presentFilter);
-                        presentFilter.setParent( searchRequest );
-                        searchRequest.setFilter( presentFilter );
-                    }
+                    // add the filter to the request filter
+                    searchRequest.addCurrentFilter( presentFilter );
+                    searchRequest.setTerminalFilter( presentFilter );
 
                     String value = StringTools.utf8ToString( tlv.getValue().getData() );
 
@@ -657,7 +586,8 @@
 
                     // We now have to get back to the nearest filter which is
                     // not terminal.
-                    unstackFilters( container );
+                    searchRequest.unstackFilters( container );
+                    
                     container.grammarPopAllowed( true );
                 }
             } );
@@ -680,60 +610,22 @@
 
 
     /**
-     * This method is used to clear the filter's stack for terminated elements.
-     * An element is considered as terminated either if : - it's a final element
-     * (ie an element which cannot contains a Filter) - its current length
-     * equals its expected length.
-     * 
-     * @param container
-     *            The container being decoded
-     */
-    private void unstackFilters( IAsn1Container container )
-    {
-        LdapMessageContainer ldapMessageContainer = ( LdapMessageContainer ) container;
-        LdapMessage ldapMessage = ldapMessageContainer.getLdapMessage();
-        SearchRequest searchRequest = ldapMessage.getSearchRequest();
-
-        TLV tlv = ldapMessageContainer.getCurrentTLV();
-
-        // Get the parent, if any
-        Filter currentFilter = searchRequest.getCurrentFilter();
-
-        // We now have to check if the parent has been completed
-        if ( tlv.getParent().getExpectedLength() == 0 )
-        {
-            TLV parent = tlv.getParent();
-
-            // The parent has been completed, we have to switch it
-            while ( ( parent != null ) && ( parent.getExpectedLength() == 0 ) )
-            {
-                parent = parent.getParent();
-
-                if ( ( currentFilter != null ) && ( currentFilter.getParent() instanceof Filter ) )
-                {
-                    currentFilter = ( Filter ) currentFilter.getParent();
-                }
-                else
-                {
-                    currentFilter = null;
-                    break;
-                }
-            }
-
-            searchRequest.setCurrentFilter( currentFilter );
-        }
-    }
-
-
-    /**
      * This method is used by each comparaison filters (=, <=, >= or ~=).
      * 
+     * We have two cases :
+     * 1) there is no previous current filter : this filter is the top level
+     * filter
+     * 2) there is a previous currentFilter : its necesseraly a connector,
+     * and the filter is added to its set of filters. We also update the 
+     * currentTerminalFilter, to be able to store the terminal filter value
+     * in it.
+     * 
      * @param container
      *            The LdapContainer
      * @throws DecoderException
      *             If any error occurs.
      */
-    private void compareFilterAction( IAsn1Container container, int filterType ) throws DecoderException
+    private void terminalFilterAction( IAsn1Container container, int filterType ) throws DecoderException
     {
         LdapMessageContainer ldapMessageContainer = ( LdapMessageContainer ) container;
         LdapMessage ldapMessage = ldapMessageContainer.getLdapMessage();
@@ -742,23 +634,10 @@
         // We can allocate the Attribute Value Assertion
         Filter filter = new AttributeValueAssertionFilter( filterType );
 
-        // Get the parent, if any
-        Filter currentFilter = searchRequest.getCurrentFilter();
-
-        if ( currentFilter != null )
-        {
-            // Ok, we have a parent. The new Filter will be added to
-            // this parent, then.
-            ( ( ConnectorFilter ) currentFilter ).addFilter( filter );
-            filter.setParent( currentFilter );
-        }
-        else
-        {
-            // No parent. This Filter will become the root.
-            filter.setParent( searchRequest );
-            searchRequest.setFilter( filter );
-        }
-
-        searchRequest.setCurrentFilter( filter );
+        searchRequest.addCurrentFilter( filter );
+        
+        // Store the filter structure that still has to be
+        // fullfiled
+        searchRequest.setTerminalFilter( filter );
     }
 }

Modified: directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/MatchingRuleAssertionGrammar.java
URL: http://svn.apache.org/viewvc/directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/MatchingRuleAssertionGrammar.java?rev=427793&r1=427792&r2=427793&view=diff
==============================================================================
--- directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/MatchingRuleAssertionGrammar.java (original)
+++ directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/MatchingRuleAssertionGrammar.java Tue Aug  1 16:35:20 2006
@@ -53,6 +53,9 @@
     /** The logger */
     private static final Logger log = LoggerFactory.getLogger( MatchingRuleAssertionGrammar.class );
 
+    /** Speedup for logs */
+    private static final boolean IS_DEBUG = log.isDebugEnabled();
+
     /** The instance of grammar. FilterGrammar is a singleton */
     private static IGrammar instance = new MatchingRuleAssertionGrammar();
 
@@ -116,11 +119,8 @@
                         extensibleMatchFilter.setParent( searchRequest );
                     }
 
-                    searchRequest.setCurrentFilter( extensibleMatchFilter );
-
-                    // We now have to get back to the nearest filter which is
-                    // not terminal.
-                    unstackFilters( container );
+                    searchRequest.addCurrentFilter( extensibleMatchFilter );
+                    searchRequest.setTerminalFilter( extensibleMatchFilter );
                 }
             } );
 
@@ -151,7 +151,7 @@
 
                     // Store the value.
                     ExtensibleMatchFilter extensibleMatchFilter = ( ExtensibleMatchFilter ) searchRequest
-                        .getCurrentFilter();
+                        .getTerminalFilter();
 
                     if ( tlv.getLength().getLength() == 0 )
                     {
@@ -219,7 +219,7 @@
                     {
                         // Store the value.
                         ExtensibleMatchFilter extensibleMatchFilter = ( ExtensibleMatchFilter ) searchRequest
-                            .getCurrentFilter();
+                            .getTerminalFilter();
 
                         try
                         {
@@ -266,7 +266,7 @@
             LdapStatesEnum.MATCHING_RULE_ASSERTION_DN_ATTRIBUTES_TAG, new GrammarAction(
                 "Store matching match value Value" )
             {
-                public void action( IAsn1Container container )
+                public void action( IAsn1Container container ) throws DecoderException
                 {
                     LdapMessageContainer ldapMessageContainer = ( LdapMessageContainer ) container;
                     LdapMessage ldapMessage = ldapMessageContainer.getLdapMessage();
@@ -276,9 +276,12 @@
 
                     // Store the value.
                     ExtensibleMatchFilter extensibleMatchFilter = ( ExtensibleMatchFilter ) searchRequest
-                        .getCurrentFilter();
+                        .getTerminalFilter();
                     extensibleMatchFilter.setMatchValue( StringTools.utf8ToString( tlv.getValue().getData() ) );
 
+                    // unstack the filters if needed
+                    searchRequest.unstackFilters( container );
+                    
                     // We can have a pop transition
                     ldapMessageContainer.grammarPopAllowed( true );
                 }
@@ -310,7 +313,7 @@
 
                     // Store the value.
                     ExtensibleMatchFilter extensibleMatchFilter = ( ExtensibleMatchFilter ) searchRequest
-                        .getCurrentFilter();
+                        .getTerminalFilter();
 
                     // We get the value. If it's a 0, it's a FALSE. If it's
                     // a FF, it's a TRUE. Any other value should be an error,
@@ -332,10 +335,13 @@
                         throw new DecoderException( bde.getMessage() );
                     }
 
-                    if ( log.isDebugEnabled() )
+                    if ( IS_DEBUG )
                     {
                         log.debug( "DN Attributes : {}", new Boolean( extensibleMatchFilter.isDnAttributes() ) );
                     }
+                    
+                    // unstack the filters if needed
+                    searchRequest.unstackFilters( ldapMessageContainer );
 
                     // We can have a pop transition
                     ldapMessageContainer.grammarPopAllowed( true );
@@ -355,51 +361,5 @@
     public static IGrammar getInstance()
     {
         return instance;
-    }
-
-
-    /**
-     * This method is used to clear the filter's stack for terminated elements.
-     * An element is considered as terminated either if : - it's a final element
-     * (ie an element which cannot contains a Filter) - its current length
-     * equals its expected length.
-     * 
-     * @param container
-     *            The container being decoded
-     */
-    private void unstackFilters( IAsn1Container container )
-    {
-        LdapMessageContainer ldapMessageContainer = ( LdapMessageContainer ) container;
-        LdapMessage ldapMessage = ldapMessageContainer.getLdapMessage();
-        SearchRequest searchRequest = ldapMessage.getSearchRequest();
-
-        TLV tlv = ldapMessageContainer.getCurrentTLV();
-
-        // Get the parent, if any
-        Filter currentFilter = searchRequest.getCurrentFilter();
-
-        // We know have to check if the parent has been completed
-        if ( tlv.getParent().getExpectedLength() == 0 )
-        {
-            TLV parent = tlv.getParent();
-
-            // The parent has been completed, we have to switch it
-            while ( ( parent != null ) && ( parent.getExpectedLength() == 0 ) )
-            {
-                parent = parent.getParent();
-
-                if ( ( currentFilter != null ) && ( currentFilter.getParent() instanceof Filter ) )
-                {
-                    currentFilter = ( Filter ) currentFilter.getParent();
-                }
-                else
-                {
-                    currentFilter = null;
-                    break;
-                }
-            }
-
-            searchRequest.setCurrentFilter( currentFilter );
-        }
     }
 }

Modified: directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/SearchRequest.java
URL: http://svn.apache.org/viewvc/directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/SearchRequest.java?rev=427793&r1=427792&r2=427793&view=diff
==============================================================================
--- directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/SearchRequest.java (original)
+++ directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/SearchRequest.java Tue Aug  1 16:35:20 2006
@@ -17,12 +17,17 @@
 package org.apache.directory.shared.ldap.codec.search;
 
 
+import org.apache.directory.shared.asn1.Asn1Object;
+import org.apache.directory.shared.asn1.ber.IAsn1Container;
 import org.apache.directory.shared.asn1.ber.tlv.Length;
+import org.apache.directory.shared.asn1.ber.tlv.TLV;
 import org.apache.directory.shared.asn1.ber.tlv.UniversalTag;
 import org.apache.directory.shared.asn1.ber.tlv.Value;
+import org.apache.directory.shared.asn1.codec.DecoderException;
 import org.apache.directory.shared.asn1.codec.EncoderException;
 import org.apache.directory.shared.ldap.codec.LdapConstants;
 import org.apache.directory.shared.ldap.codec.LdapMessage;
+import org.apache.directory.shared.ldap.codec.LdapMessageContainer;
 import org.apache.directory.shared.ldap.codec.util.LdapString;
 import org.apache.directory.shared.ldap.name.LdapDN;
 import org.apache.directory.shared.ldap.util.StringTools;
@@ -80,13 +85,16 @@
 
     /** The filter tree */
     private Filter filter;
-
+    
     /** The list of attributes to get */
     private Attributes attributes;
 
     /** The current filter. This is used while decoding a PDU */
     private transient Filter currentFilter;
 
+    /** A temporary storage for a terminal Filter */
+    private transient Filter terminalFilter;
+    
     /** The searchRequest length */
     private transient int searchRequestLength;
 
@@ -317,6 +325,62 @@
         return currentFilter;
     }
 
+    /**
+     * Get the comparison dilter
+     * 
+     * @return Returns the comparisonFilter.
+     */
+    public Filter getTerminalFilter()
+    {
+        return terminalFilter;
+    }
+
+    /**
+     * Set the terminal filter
+     * 
+     * @param terminalFilter the teminalFilter.
+     */
+    public void setTerminalFilter( Filter terminalFilter )
+    {
+        this.terminalFilter = terminalFilter;
+    }
+
+
+    /**
+     * Add a current filter. We have two cases :
+     * - there is no previous current filter : the filter
+     * is the top level filter
+     * - there is a previous current filter : the filter is added 
+     * to the currentFilter set, and the current filter is changed
+     * 
+     * In any case, the previous current filter will always be a
+     * ConnectorFilter when this method is called.
+     * 
+     * @param currentFilter
+     *            The currentFilter to set.
+     */
+    public void addCurrentFilter( Filter filter ) throws DecoderException
+    {
+        if ( currentFilter != null )
+        {
+            // Ok, we have a parent. The new Filter will be added to
+            // this parent, and will become the currentFilter if it's a connector.
+            ( ( ConnectorFilter ) currentFilter ).addFilter( filter );
+            filter.setParent( currentFilter );
+            
+            if ( filter instanceof ConnectorFilter )
+            {
+                currentFilter = filter;
+            }
+        }
+        else
+        {
+            // No parent. This Filter will become the root.
+            currentFilter = filter;
+            currentFilter.setParent( this );
+            this.filter = filter;
+        }
+    }
 
     /**
      * Set the current dilter
@@ -324,11 +388,88 @@
      * @param currentFilter
      *            The currentFilter to set.
      */
-    public void setCurrentFilter( Filter currentFilter )
+    public void setCurrentFilter( Filter filter ) throws DecoderException
     {
-        this.currentFilter = currentFilter;
+        currentFilter = filter;
     }
 
+
+    /**
+     * This method is used to clear the filter's stack for terminated elements. An element
+     * is considered as terminated either if :
+     *  - it's a final element (ie an element which cannot contains a Filter)
+     *  - its current length equals its expected length.
+     * 
+     * @param container The container being decoded
+     */
+    public void unstackFilters( IAsn1Container container ) throws DecoderException
+    {
+        LdapMessageContainer ldapMessageContainer = ( LdapMessageContainer ) container;
+        //LdapMessage ldapMessage = ldapMessageContainer.getLdapMessage();
+        //SearchRequest searchRequest = ldapMessage.getSearchRequest();
+
+        TLV tlv = ldapMessageContainer.getCurrentTLV();
+        TLV parent = tlv.getParent();
+        Filter filter = terminalFilter;
+
+        // The parent has been completed, so fold it
+        while ( ( parent != null ) && ( parent.getExpectedLength() == 0 ) )
+        {
+            Asn1Object filterParent = filter.getParent();
+            
+            // We have a special case with PresentFilter, which has not been 
+            // pushed on the stack, so we need to get its parent's parent
+            if ( filter instanceof PresentFilter )
+            {
+                filterParent = filterParent.getParent();
+            }
+
+            if ( filterParent instanceof Filter )
+            {
+                // The parent is a filter ; it will become the new currentFilter
+                // and we will loop again. 
+                currentFilter = (Filter)filterParent;
+                filter = currentFilter;
+                parent = parent.getParent();
+            }
+            else
+            {
+                // We can stop the recursion, we have reached the searchResult Object
+                break;
+            }
+            
+            /*
+            if ( filterParent instanceof Filter )
+            {
+                // The terminalfilter set has been completed
+                // we can get its parent and add the terminal to it
+                // but onlyu if it's not a connector filter
+                if ( ! (filter instanceof ConnectorFilter ) )
+                {
+                    addCurrentFilter( filter );
+                }
+                
+                // and update the current filter with the parent
+                Asn1Object parentFilter = currentFilter.getParent();
+                
+                if ( parentFilter instanceof Filter )
+                {
+                    searchRequest.setCurrentFilter( (Filter)parentFilter );
+                }
+                
+                parent = parent.getParent();
+                filter = currentFilter;
+            }
+            else
+            {
+                // We have reached the top level, we can stop
+                // the loop after having updated the currentFilter
+                //searchRequest.setCurrentFilter( filter );
+                break;
+            }
+            */
+        }
+    }
 
     /**
      * Compute the SearchRequest length SearchRequest : 0x63 L1 | +--> 0x04 L2

Modified: directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/SearchRequestGrammar.java
URL: http://svn.apache.org/viewvc/directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/SearchRequestGrammar.java?rev=427793&r1=427792&r2=427793&view=diff
==============================================================================
--- directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/SearchRequestGrammar.java (original)
+++ directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/SearchRequestGrammar.java Tue Aug  1 16:35:20 2006
@@ -60,6 +60,9 @@
     /** The logger */
     private static final Logger log = LoggerFactory.getLogger( SearchRequestGrammar.class );
 
+    /** Speedup for logs */
+    private static final boolean IS_DEBUG = log.isDebugEnabled();
+
     /** The instance of grammar. SearchRequestGrammar is a singleton */
     private static IGrammar instance = new SearchRequestGrammar();
 
@@ -209,7 +212,7 @@
 
                     searchRequest.setScope( scope );
 
-                    if ( log.isDebugEnabled() )
+                    if ( IS_DEBUG )
                     {
                         switch ( scope )
                         {
@@ -282,7 +285,7 @@
 
                     searchRequest.setDerefAliases( derefAliases );
 
-                    if ( log.isDebugEnabled() )
+                    if ( IS_DEBUG )
                     {
                         switch ( derefAliases )
                         {
@@ -350,7 +353,7 @@
 
                     searchRequest.setSizeLimit( sizeLimit );
 
-                    if ( log.isDebugEnabled() )
+                    if ( IS_DEBUG )
                     {
                         log.debug( "The sizeLimit value is set to {} objects", new Integer( sizeLimit ) );
                     }
@@ -403,7 +406,7 @@
 
                     searchRequest.setTimeLimit( timeLimit );
 
-                    if ( log.isDebugEnabled() )
+                    if ( IS_DEBUG )
                     {
                         log.debug( "The timeLimit value is set to {} seconds", new Integer( timeLimit ) );
                     }
@@ -461,7 +464,7 @@
                         throw new DecoderException( bde.getMessage() );
                     }
 
-                    if ( log.isDebugEnabled() )
+                    if ( IS_DEBUG )
                     {
                         log.debug( "The search will return {}", ( searchRequest.isTypesOnly() ? "only attributs type"
                             : "attributes types and values" ) );
@@ -682,7 +685,7 @@
                     // We can have a pop transition
                     ldapMessageContainer.grammarPopAllowed( true );
 
-                    if ( log.isDebugEnabled() )
+                    if ( IS_DEBUG )
                     {
                         log.debug( "Decoded Attribute Description : {}", attributeDescription.getString() );
                     }

Modified: directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/SearchResultEntry.java
URL: http://svn.apache.org/viewvc/directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/SearchResultEntry.java?rev=427793&r1=427792&r2=427793&view=diff
==============================================================================
--- directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/SearchResultEntry.java (original)
+++ directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/SearchResultEntry.java Tue Aug  1 16:35:20 2006
@@ -42,13 +42,22 @@
 
 
 /**
- * A SearchResultEntry Message. Its syntax is : SearchResultEntry ::=
- * [APPLICATION 4] SEQUENCE { objectName LDAPDN, attributes PartialAttributeList }
- * PartialAttributeList ::= SEQUENCE OF SEQUENCE { type AttributeDescription,
- * vals SET OF AttributeValue } AttributeDescription ::= LDAPString
- * AttributeValue ::= OCTET STRING It contains an entry, with all its
- * attributes, and all the attributes values. If a search request is submited,
- * all the results are sent one by one, followed by a searchResultDone message.
+ * A SearchResultEntry Message. Its syntax is :
+ *   SearchResultEntry ::= [APPLICATION 4] SEQUENCE {
+ *       objectName      LDAPDN,
+ *       attributes      PartialAttributeList }
+ * 
+ *   PartialAttributeList ::= SEQUENCE OF SEQUENCE {
+ *       type    AttributeDescription,
+ *       vals    SET OF AttributeValue }
+ * 
+ *   AttributeDescription ::= LDAPString
+ * 
+ *   AttributeValue ::= OCTET STRING
+ * 
+ * It contains an entry, with all its attributes, and all the attributes
+ * values. If a search request is submited, all the results are sent one
+ * by one, followed by a searchResultDone message.
  * 
  * @author <a href="mailto:dev@directory.apache.org">Apache Directory Project</a>
  */
@@ -176,15 +185,44 @@
 
 
     /**
-     * Compute the SearchResultEntry length SearchResultEntry : 0x64 L1 | +-->
-     * 0x04 L2 objectName +--> 0x30 L3 (attributes) | +--> 0x30 L4-1 (partial
-     * attributes list) | | | +--> 0x04 L5-1 type | +--> 0x31 L6-1 (values) | | |
-     * +--> 0x04 L7-1-1 value | +--> ... | +--> 0x04 L7-1-n value | +--> 0x30
-     * L4-2 (partial attributes list) | | | +--> 0x04 L5-2 type | +--> 0x31 L6-2
-     * (values) | | | +--> 0x04 L7-2-1 value | +--> ... | +--> 0x04 L7-2-n value |
-     * +--> ... | +--> 0x30 L4-m (partial attributes list) | +--> 0x04 L5-m type
-     * +--> 0x31 L6-m (values) | +--> 0x04 L7-m-1 value +--> ... +--> 0x04
-     * L7-m-n value
+     * Compute the SearchResultEntry length
+     * 
+     * SearchResultEntry :
+     * 
+     * 0x64 L1
+     *  |
+     *  +--> 0x04 L2 objectName
+     *  +--> 0x30 L3 (attributes)
+     *        |
+     *        +--> 0x30 L4-1 (partial attributes list)
+     *        |     |
+     *        |     +--> 0x04 L5-1 type
+     *        |     +--> 0x31 L6-1 (values)
+     *        |           |
+     *        |           +--> 0x04 L7-1-1 value
+     *        |           +--> ...
+     *        |           +--> 0x04 L7-1-n value
+     *        |
+     *        +--> 0x30 L4-2 (partial attributes list)
+     *        |     |
+     *        |     +--> 0x04 L5-2 type
+     *        |     +--> 0x31 L6-2 (values)
+     *        |           |
+     *        |           +--> 0x04 L7-2-1 value
+     *        |           +--> ...
+     *        |           +--> 0x04 L7-2-n value
+     *        |
+     *        +--> ...
+     *        |
+     *        +--> 0x30 L4-m (partial attributes list)
+     *              |
+     *              +--> 0x04 L5-m type
+     *              +--> 0x31 L6-m (values)
+     *                    |
+     *                    +--> 0x04 L7-m-1 value
+     *                    +--> ...
+     *                    +--> 0x04 L7-m-n value
+     * 
      */
     public int computeLength()
     {
@@ -284,14 +322,28 @@
 
 
     /**
-     * Encode the SearchResultEntry message to a PDU. SearchResultEntry : 0x64
-     * LL 0x04 LL objectName 0x30 LL attributes 0x30 LL partialAttributeList
-     * 0x04 LL type 0x31 LL vals 0x04 LL attributeValue ... 0x04 LL
-     * attributeValue ... 0x30 LL partialAttributeList 0x04 LL type 0x31 LL vals
-     * 0x04 LL attributeValue ... 0x04 LL attributeValue
+     * Encode the SearchResultEntry message to a PDU.
+     * 
+     * SearchResultEntry :
+     * 
+     * 0x64 LL
+     *   0x04 LL objectName
+     *   0x30 LL attributes
+     *     0x30 LL partialAttributeList
+     *       0x04 LL type
+     *       0x31 LL vals
+     *         0x04 LL attributeValue
+     *         ... 
+     *         0x04 LL attributeValue
+     *     ... 
+     *     0x30 LL partialAttributeList
+     *       0x04 LL type
+     *       0x31 LL vals
+     *         0x04 LL attributeValue
+     *         ... 
+     *         0x04 LL attributeValue 
      * 
-     * @param buffer
-     *            The buffer where to put the PDU
+     * @param buffer The buffer where to put the PDU
      * @return The PDU.
      */
     public ByteBuffer encode( ByteBuffer buffer ) throws EncoderException

Modified: directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/SearchResultEntryGrammar.java
URL: http://svn.apache.org/viewvc/directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/SearchResultEntryGrammar.java?rev=427793&r1=427792&r2=427793&view=diff
==============================================================================
--- directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/SearchResultEntryGrammar.java (original)
+++ directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/SearchResultEntryGrammar.java Tue Aug  1 16:35:20 2006
@@ -58,6 +58,9 @@
     /** The logger */
     private static final Logger log = LoggerFactory.getLogger( SearchResultEntryGrammar.class );
 
+    /** Speedup for logs */
+    private static final boolean IS_DEBUG = log.isDebugEnabled();
+
     /** The instance of grammar. SearchResultEntryGrammar is a singleton */
     private static IGrammar instance = new SearchResultEntryGrammar();
 
@@ -155,7 +158,7 @@
                         searchResultEntry.setObjectName( objectName );
                     }
 
-                    if ( log.isDebugEnabled() )
+                    if ( IS_DEBUG )
                     {
                         log.debug( "Search Result Entry DN found : {}", searchResultEntry.getObjectName() );
                     }
@@ -330,7 +333,7 @@
                         {
                             value = tlv.getValue().getData();
 
-                            if ( log.isDebugEnabled() )
+                            if ( IS_DEBUG )
                             {
                                 log.debug( "Attribute value {}", StringTools.dumpBytes( ( byte[] ) value ) );
                             }

Modified: directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/SubstringFilterGrammar.java
URL: http://svn.apache.org/viewvc/directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/SubstringFilterGrammar.java?rev=427793&r1=427792&r2=427793&view=diff
==============================================================================
--- directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/SubstringFilterGrammar.java (original)
+++ directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/SubstringFilterGrammar.java Tue Aug  1 16:35:20 2006
@@ -109,25 +109,8 @@
                     // We can allocate the SearchRequest
                     Filter substringFilter = new SubstringFilter();
 
-                    // Get the parent, if any
-                    Filter currentFilter = searchRequest.getCurrentFilter();
-
-                    if ( currentFilter != null )
-                    {
-                        // Ok, we have a parent. The new Filter will be added to
-                        // this parent, then.
-                        ( ( ConnectorFilter ) currentFilter ).addFilter( substringFilter );
-                        substringFilter.setParent( currentFilter );
-                    }
-                    else
-                    {
-                        // No parent. This Filter will become the root.
-
-                        searchRequest.setFilter( substringFilter );
-                        substringFilter.setParent( searchRequest );
-                    }
-
-                    searchRequest.setCurrentFilter( substringFilter );
+                    searchRequest.addCurrentFilter( substringFilter );
+                    searchRequest.setTerminalFilter( substringFilter );
 
                     // As this is a new Constructed object, we have to init its
                     // length
@@ -162,7 +145,7 @@
                     TLV tlv = ldapMessageContainer.getCurrentTLV();
 
                     // Store the value.
-                    SubstringFilter substringFilter = ( SubstringFilter ) searchRequest.getCurrentFilter();
+                    SubstringFilter substringFilter = ( SubstringFilter ) searchRequest.getTerminalFilter();
 
                     if ( tlv.getLength().getLength() == 0 )
                     {
@@ -186,7 +169,7 @@
 
                         // We now have to get back to the nearest filter which
                         // is not terminal.
-                        unstackFilters( container );
+                        searchRequest.setTerminalFilter( substringFilter );
                     }
                 }
             } );
@@ -261,7 +244,7 @@
                     TLV tlv = ldapMessageContainer.getCurrentTLV();
 
                     // Store the value.
-                    SubstringFilter substringFilter = ( SubstringFilter ) searchRequest.getCurrentFilter();
+                    SubstringFilter substringFilter = ( SubstringFilter ) searchRequest.getTerminalFilter();
 
                     if ( tlv.getLength().getLength() == 0 )
                     {
@@ -283,7 +266,7 @@
 
                     // We now have to get back to the nearest filter which is
                     // not terminal.
-                    unstackFilters( container );
+                    searchRequest.unstackFilters( container );
 
                     // We can have a pop transition
                     container.grammarPopAllowed( true );
@@ -336,7 +319,7 @@
                     TLV tlv = ldapMessageContainer.getCurrentTLV();
 
                     // Store the value.
-                    SubstringFilter substringFilter = ( SubstringFilter ) searchRequest.getCurrentFilter();
+                    SubstringFilter substringFilter = ( SubstringFilter ) searchRequest.getTerminalFilter();
 
                     if ( tlv.getLength().getLength() == 0 )
                     {
@@ -357,7 +340,7 @@
 
                     // We now have to get back to the nearest filter which is
                     // not terminal.
-                    unstackFilters( container );
+                    searchRequest.unstackFilters( container );
 
                     // We can have a pop transition
                     container.grammarPopAllowed( true );
@@ -412,7 +395,7 @@
                     TLV tlv = ldapMessageContainer.getCurrentTLV();
 
                     // Store the value.
-                    SubstringFilter substringFilter = ( SubstringFilter ) searchRequest.getCurrentFilter();
+                    SubstringFilter substringFilter = ( SubstringFilter ) searchRequest.getTerminalFilter();
 
                     if ( tlv.getLength().getLength() == 0 )
                     {
@@ -434,12 +417,12 @@
 
                     // We now have to get back to the nearest filter which is
                     // not terminal.
-                    unstackFilters( container );
+                    searchRequest.unstackFilters( container );
+
                     // We can have a pop transition
                     container.grammarPopAllowed( true );
                 }
             } );
-
     }
 
 
@@ -454,51 +437,5 @@
     public static IGrammar getInstance()
     {
         return instance;
-    }
-
-
-    /**
-     * This method is used to clear the filter's stack for terminated elements.
-     * An element is considered as terminated either if : - it's a final element
-     * (ie an element which cannot contains a Filter) - its current length
-     * equals its expected length.
-     * 
-     * @param container
-     *            The container being decoded
-     */
-    private void unstackFilters( IAsn1Container container )
-    {
-        LdapMessageContainer ldapMessageContainer = ( LdapMessageContainer ) container;
-        LdapMessage ldapMessage = ldapMessageContainer.getLdapMessage();
-        SearchRequest searchRequest = ldapMessage.getSearchRequest();
-
-        TLV tlv = ldapMessageContainer.getCurrentTLV();
-
-        // Get the parent, if any
-        Filter currentFilter = searchRequest.getCurrentFilter();
-
-        // We know have to check if the parent has been completed
-        if ( tlv.getParent().getExpectedLength() == 0 )
-        {
-            TLV parent = tlv.getParent();
-
-            // The parent has been completed, we have to switch it
-            while ( ( parent != null ) && ( parent.getExpectedLength() == 0 ) )
-            {
-                parent = parent.getParent();
-
-                if ( ( currentFilter != null ) && ( currentFilter.getParent() instanceof Filter ) )
-                {
-                    currentFilter = ( Filter ) currentFilter.getParent();
-                }
-                else
-                {
-                    currentFilter = null;
-                    break;
-                }
-            }
-
-            searchRequest.setCurrentFilter( currentFilter );
-        }
     }
 }

Modified: directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/controls/EntryChangeControlGrammar.java
URL: http://svn.apache.org/viewvc/directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/controls/EntryChangeControlGrammar.java?rev=427793&r1=427792&r2=427793&view=diff
==============================================================================
--- directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/controls/EntryChangeControlGrammar.java (original)
+++ directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/controls/EntryChangeControlGrammar.java Tue Aug  1 16:35:20 2006
@@ -46,6 +46,9 @@
     /** The logger */
     private static final Logger log = LoggerFactory.getLogger( EntryChangeControlGrammar.class );
 
+    /** Speedup for logs */
+    private static final boolean IS_DEBUG = log.isDebugEnabled();
+
     /** The instance of grammar. EntryChangeControlGrammar is a singleton */
     private static IGrammar instance = new EntryChangeControlGrammar();
 
@@ -128,7 +131,7 @@
                         case ChangeType.MODIFY_VALUE:
                             ChangeType changeType = ChangeType.getChangeType( change );
 
-                            if ( log.isDebugEnabled() )
+                            if ( IS_DEBUG )
                             {
                                 log.debug( "changeType = " + changeType );
                             }
@@ -212,7 +215,7 @@
                         throw new DecoderException( "failed to decode the previous DN" );
                     }
 
-                    if ( log.isDebugEnabled() )
+                    if ( IS_DEBUG )
                     {
                         log.debug( "previousDN = " + previousDn );
                     }
@@ -277,7 +280,7 @@
                 {
                     int changeNumber = IntegerDecoder.parse( value );
 
-                    if ( log.isDebugEnabled() )
+                    if ( IS_DEBUG )
                     {
                         log.debug( "changeNumber = " + changeNumber );
                     }

Modified: directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/controls/PSearchControl.java
URL: http://svn.apache.org/viewvc/directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/controls/PSearchControl.java?rev=427793&r1=427792&r2=427793&view=diff
==============================================================================
--- directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/controls/PSearchControl.java (original)
+++ directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/controls/PSearchControl.java Tue Aug  1 16:35:20 2006
@@ -1,3 +1,19 @@
+/*
+ *   Copyright 2006 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.directory.shared.ldap.codec.search.controls;
 
 

Modified: directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/controls/PSearchControlGrammar.java
URL: http://svn.apache.org/viewvc/directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/controls/PSearchControlGrammar.java?rev=427793&r1=427792&r2=427793&view=diff
==============================================================================
--- directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/controls/PSearchControlGrammar.java (original)
+++ directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/codec/search/controls/PSearchControlGrammar.java Tue Aug  1 16:35:20 2006
@@ -45,6 +45,9 @@
     /** The logger */
     private static final Logger log = LoggerFactory.getLogger( PSearchControlGrammar.class );
 
+    /** Speedup for logs */
+    private static final boolean IS_DEBUG = log.isDebugEnabled();
+
     /** The instance of grammar. PSearchControlGrammar is a singleton */
     private static IGrammar instance = new PSearchControlGrammar();
 
@@ -91,7 +94,7 @@
                     {
                         int changeTypes = IntegerDecoder.parse( value );
 
-                        if ( log.isDebugEnabled() )
+                        if ( IS_DEBUG )
                         {
                             log.debug( "changeTypes = " + changeTypes );
                         }
@@ -123,7 +126,7 @@
                     {
                         boolean changesOnly = BooleanDecoder.parse( value );
 
-                        if ( log.isDebugEnabled() )
+                        if ( IS_DEBUG )
                         {
                             log.debug( "changesOnly = " + changesOnly );
                         }
@@ -155,7 +158,7 @@
                     {
                         boolean returnECs = BooleanDecoder.parse( value );
 
-                        if ( log.isDebugEnabled() )
+                        if ( IS_DEBUG )
                         {
                             log.debug( "returnECs = " + returnECs );
                         }

Modified: directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/ldif/LdifReader.java
URL: http://svn.apache.org/viewvc/directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/ldif/LdifReader.java?rev=427793&r1=427792&r2=427793&view=diff
==============================================================================
--- directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/ldif/LdifReader.java (original)
+++ directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/ldif/LdifReader.java Tue Aug  1 16:35:20 2006
@@ -1,3 +1,19 @@
+/*
+ *   Copyright 2006 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.directory.shared.ldap.ldif;
 
 import java.io.BufferedReader;

Modified: directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/message/LockableAttributeImpl.java
URL: http://svn.apache.org/viewvc/directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/message/LockableAttributeImpl.java?rev=427793&r1=427792&r2=427793&view=diff
==============================================================================
--- directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/message/LockableAttributeImpl.java (original)
+++ directory/branches/shared/0.9.5/ldap/src/main/java/org/apache/directory/shared/ldap/message/LockableAttributeImpl.java Tue Aug  1 16:35:20 2006
@@ -18,6 +18,8 @@
 
 
 import java.util.ArrayList;
+import java.util.Iterator;
+import java.util.List;
 
 import javax.naming.NamingEnumeration;
 import javax.naming.NamingException;
@@ -25,6 +27,7 @@
 import javax.naming.directory.Attribute;
 import javax.naming.directory.DirContext;
 
+import org.apache.directory.shared.ldap.util.StringTools;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
@@ -41,11 +44,17 @@
 
     private static final long serialVersionUID = -5158233254341746514L;
 
-    /** the name of the attribute */
-    private final String id;
+    /** the name of the attribute, case sensitive */
+    private final String upId;
 
+    /** In case we have only one value, just use this container */
+    private Object value;
+    
     /** the list of attribute values */
-    private final ArrayList list;
+    private List list;
+    
+    /** The number of values stored */
+    private int size = 0;
 
 
     // ------------------------------------------------------------------------
@@ -61,8 +70,10 @@
      */
     public LockableAttributeImpl(final String id)
     {
-        this.id = id;
-        list = new ArrayList();
+        upId = id;
+        value = null;
+        list = null; //new ArrayList();
+        size = 0;
     }
 
 
@@ -76,9 +87,10 @@
      */
     public LockableAttributeImpl(final String id, final Object value)
     {
-        this.id = id;
-        list = new ArrayList();
-        list.add( value );
+        upId = id;
+        list = null; // new ArrayList();
+        this.value = value; //list.add( value );
+        size = 1;
     }
 
 
@@ -92,9 +104,11 @@
      */
     public LockableAttributeImpl(final String id, final byte[] value)
     {
-        this.id = id;
-        list = new ArrayList();
-        list.add( value );
+        upId = id;
+        list = null; //new ArrayList();
+        this.value = value;
+        //list.add( value );
+        size = 1;
     }
 
 
@@ -107,10 +121,12 @@
      * @param list
      *            the list of values to start with
      */
-    private LockableAttributeImpl(final String id, final ArrayList list)
+    private LockableAttributeImpl(final String id, final List list)
     {
-        this.id = id;
+        upId = id;
         this.list = list;
+        value = null;
+        size = (list != null ? list.size() : 0);
     }
 
 
@@ -125,7 +141,35 @@
      */
     public NamingEnumeration getAll()
     {
-        return new IteratorNamingEnumeration( list.iterator() );
+    	if ( size < 2 )
+    	{
+    		return new IteratorNamingEnumeration( new Iterator()
+    		{
+    			private boolean done = (size != 0);
+    				
+    			public boolean hasNext() 
+    			{
+    				return done;
+    			}
+    			
+    			public Object next() 
+    			{
+    				done = false;
+    				return value;
+    			}
+    			
+    			public void remove() 
+    			{
+    				value = null;
+    				done = false;
+    				size = 0;
+    			}
+    		});
+    	}
+    	else
+    	{
+    		return new IteratorNamingEnumeration( list.iterator() );
+    	}
     }
 
 
@@ -136,12 +180,18 @@
      */
     public Object get()
     {
-        if ( list.isEmpty() )
+    	if ( list == null )
+    	{
+    		return value;
+    	}
+    	else if ( list.isEmpty() )
         {
             return null;
         }
-
-        return list.get( 0 );
+    	else
+    	{
+    		return list.get( 0 );
+    	}
     }
 
 
@@ -152,7 +202,7 @@
      */
     public int size()
     {
-        return list.size();
+    	return size;
     }
 
 
@@ -163,7 +213,7 @@
      */
     public String getID()
     {
-        return id;
+        return upId;
     }
 
 
@@ -176,7 +226,17 @@
      */
     public boolean contains( Object attrVal )
     {
-        return list.contains( attrVal );
+    	switch (size)
+    	{
+    		case 0 :
+    			return false;
+    			
+    		case 1 :
+    			return value == null ? attrVal == null : value.equals( attrVal );
+    			
+    		default :
+    			return list.contains( attrVal );
+    	}
     }
 
 
@@ -191,7 +251,32 @@
      */
     public boolean add( Object attrVal )
     {
-        return list.add( attrVal );
+    	boolean exists = false;
+    	
+    	switch ( size )
+    	{
+    		case 0 :
+    			value = attrVal;
+    			size++;
+    			return true;
+    			
+    		case 1 :
+    			exists = value.equals( attrVal );
+
+    			list = new ArrayList();
+    			list.add( value );
+    			list.add( attrVal );
+    			size++;
+    			value = null;
+    			return exists;
+    			
+    		default :
+    			exists = list.contains( attrVal ); 
+    		
+    			list.add( attrVal );
+    			size++;
+    			return exists;
+    	}
     }
 
 
@@ -205,7 +290,28 @@
      */
     public boolean remove( Object attrVal )
     {
-        return list.remove( attrVal );
+    	switch ( size )
+    	{
+    		case 0 :
+    			return false;
+    			
+    		case 1 :
+    			value = null;
+    			size--;
+    			return true;
+    			
+    		case 2 :
+    			list.remove( attrVal );
+    			value = list.get(0);
+    			size = 1;
+    			list = null;
+    			return true;
+    			
+    		default :
+    			list.remove( attrVal );
+    			size--;
+    			return true;
+    	}
     }
 
 
@@ -214,7 +320,21 @@
      */
     public void clear()
     {
-        list.clear();
+    	switch ( size )
+    	{
+    		case 0 :
+    			return;
+    			
+    		case 1 :
+    			value = null;
+    			size = 0;
+    			return;
+    			
+    		default :
+    			list = null;
+    			size = 0;
+    			return;
+    	}
     }
 
 
@@ -248,8 +368,17 @@
      */
     public Object clone()
     {
-        ArrayList l_list = ( ArrayList ) list.clone();
-        return new LockableAttributeImpl( id, l_list );
+    	switch ( size )
+    	{
+    		case 0 :
+    			return new LockableAttributeImpl( upId );
+    			
+    		case 1 :
+    			return new LockableAttributeImpl( upId, value );
+    			
+    		default :
+    			return new LockableAttributeImpl( upId, (List)((ArrayList)list).clone() );
+    	}
     }
 
 
@@ -274,7 +403,17 @@
      */
     public Object get( int index )
     {
-        return list.get( index );
+    	switch ( size )
+    	{
+    		case 0 :
+    			return null;
+    			
+    		case 1 :
+    			return value;
+    			
+    		default :
+    			return list.get( index );
+    	}
     }
 
 
@@ -288,7 +427,21 @@
      */
     public Object remove( int index )
     {
-        return list.remove( index );
+    	switch ( size )
+    	{
+    		case 0 :
+    			return null;
+    			
+    		case 1 :
+    			Object result = value;
+    			value = null;
+    			size = 0;
+    			return result;
+    			
+    		default :
+    			size--;
+    			return list.remove( index );
+    	}
     }
 
 
@@ -303,7 +456,36 @@
      */
     public void add( int index, Object attrVal )
     {
-        list.add( index, attrVal );
+    	switch ( size )
+    	{
+    		case 0 :
+    			size++;
+    			value = attrVal;
+    			return;
+    			
+    		case 1 :
+    			list = new ArrayList();
+    			
+    			if ( index == 0 )
+    			{
+	    			list.add( attrVal );
+	    			list.add( value );
+    			}
+    			else
+    			{
+	    			list.add( value );
+	    			list.add( attrVal );
+    			}
+
+    			size++;
+    			value = null;
+    			return;
+    			
+    		default :
+    			list.add( index, attrVal );
+    			size++;
+    			return;
+    	}
     }
 
 
@@ -318,7 +500,35 @@
      */
     public Object set( int index, Object attrVal )
     {
-        return list.set( index, attrVal );
+    	switch ( size )
+    	{
+    		case 0 :
+    			size++;
+    			value = attrVal;
+    			return null;
+    			
+    		case 1 :
+    			if ( index == 0 )
+    			{
+	    			Object result = value;
+	    			value = attrVal;
+	    			return result;
+    			}
+    			else
+    			{
+    				list = new ArrayList();
+    				list.add( value );
+    				list.add( attrVal );
+    				size = 2;
+    				value = null;
+    				return null;
+    			}
+    			
+    		default :
+    			Object oldValue = list.get( index );
+    			list.set( index, attrVal );
+    			return oldValue;
+    	}
     }
 
 
@@ -349,54 +559,112 @@
         }
 
         Attribute attr = ( Attribute ) obj;
-        if ( !id.equals( attr.getID() ) )
+        
+        if ( !upId.equals( attr.getID() ) )
         {
             return false;
         }
 
-        if ( attr.size() != list.size() )
+        if ( attr.size() != size )
         {
             return false;
         }
 
-        // if ( attr.isOrdered() )
-        // {
-        // for ( int ii = 0; ii < attr.size(); ii++ )
-        // {
-        // try
-        // {
-        // if ( ! list.get( ii).equals( attr.get( ii ) ) )
-        // {
-        // return false;
-        // }
-        // }
-        // catch ( NamingException e )
-        // {
-        // log.warn( "Failed to get an attribute from the specifid attribute: "
-        // + attr, e );
-        // return false;
-        // }
-        // }
-        // }
-        // else
-        // {
-        for ( int ii = 0; ii < attr.size(); ii++ )
+        switch ( size )
         {
-            try
-            {
-                if ( !list.contains( attr.get( ii ) ) )
+        	case 0 :
+        		return true;
+        		
+        	case 1 :
+                try
+                {
+                	return value.equals( attr.get( 0 ) );
+                }
+                catch ( NamingException e )
                 {
+                    log.warn( "Failed to get an attribute from the specifid attribute: " + attr, e );
                     return false;
                 }
-            }
-            catch ( NamingException e )
-            {
-                log.warn( "Failed to get an attribute from the specifid attribute: " + attr, e );
-                return false;
-            }
+        		
+        	default :
+                for ( int i = 0; i < size; i++ )
+                {
+                    try
+                    {
+                        if ( !list.contains( attr.get( i ) ) )
+                        {
+                            return false;
+                        }
+                    }
+                    catch ( NamingException e )
+                    {
+                        log.warn( "Failed to get an attribute from the specifid attribute: " + attr, e );
+                        return false;
+                    }
+                }
+        		
+        		return true;
         }
-        // }
-
-        return true;
+    }
+    
+    public String toString()
+    {
+    	StringBuffer sb = new StringBuffer();
+    	
+    	sb.append( "Attribute id : '" ).append( upId ).append( "', " );
+    	sb.append( " Values : [");
+    	
+    	switch (size)
+    	{
+    		case 0 :
+    			sb.append( "]\n" );
+    			break;
+    			
+    		case 1 :
+    			if ( value instanceof String ) 
+    			{
+    				sb.append( '\'' ).append( value ).append( '\'' );
+				}
+    			else
+    			{
+    				sb.append( StringTools.dumpBytes( (byte[])value ) );
+    			}
+    			
+    			sb.append( "]\n" );
+    			break;
+    			
+    		default :
+    			boolean isFirst = true;
+    		
+	    		Iterator values = list.iterator();
+	    		
+	    		while ( values.hasNext() )
+	    		{
+	    			Object v = values.next();
+	    			
+	    			if ( isFirst == false )
+	    			{
+	    				sb.append( ", " );
+	    			}
+	    			else
+	    			{
+	    				isFirst = false;
+	    			}
+	    			
+	    			if ( v instanceof String ) 
+	    			{
+	    				sb.append( '\'' ).append( v ).append( '\'' );
+					}
+	    			else
+	    			{
+	    				sb.append( StringTools.dumpBytes( (byte[])v ) );
+	    			}
+	    		}
+	    		
+	    		sb.append( "]\n" );
+	    		break;
+    	}
+    	
+    	return sb.toString();
     }
 }



Mime
View raw message