>Synopsis:      The search time/size limit bounds seem badly evaluated in ldapd
>Category:      system
>Environment:
        System      : OpenBSD 6.3
        Details     : OpenBSD 6.3 (GENERIC.MP) #2: Sun May  6 20:07:33 CEST 2018
                         
[email protected]:/usr/src/sys/arch/amd64/compile/GENERIC.MP

        Architecture: OpenBSD.amd64
        Machine     : amd64
>Description:
        The client search request time and size limits in ldapd seem to be badly
        evaluated. An error is risen when the time or the size limit is reached:


        * Without size limit

        $ ldapsearch -x -D xxx -W "cn=Christophe Simon" dn
        # extended LDIF
        #
        # LDAPv3
        # base <dc=pipeless,dc=org> (default) with scope subtree
        # filter: cn=Christophe Simon
        # requesting: dn
        #

        # christophe simon, users, pipeless.org
        dn: cn=christophe simon,xxx

        # search result
        search: 2
        result: 0 Success

        # numResponses: 2
        # numEntries: 1


        * With size limit

        $ ldapsearch -x -D xxx -W -z 1 "cn=Christophe Simon" dn
        # extended LDIF
        #
        # LDAPv3
        # base <dc=pipeless,dc=org> (default) with scope subtree
        # filter: cn=Christophe Simon
        # requesting: dn
        #

        # christophe simon, users, pipeless.org
        dn: cn=christophe simon,ou=users,dc=pipeless,dc=org

        # search result
        search: 2
        result: 4 Size limit exceeded

        # numResponses: 2
        # numEntries: 1


        The same query ran against OpenLDAP returns the correct response code.

        RFC 4511 in section A.2 tells that this error should be risen if the
        limit is exceeded (not only reached):

        timeLimitExceeded (3)
            Indicates that the time limit specified by the client was
            exceeded before the operation could be completed.

        sizeLimitExceeded (4)
            Indicates that the size limit specified by the client was
            exceeded before the operation could be completed.

        This breaks software such as Cyrus saslauthd that specify LDAP search
        limit to 1 when trying to find an user using the ldap plugin.
>How-To-Repeat:
        Do an LDAP search request with a size limit equal to the number of
        matching entries.
>Fix:
        Here's a patch fixing the entries/limit time/limit comparison.

        Is it OK for you, or is there a particular reason explaining the
        current behaviour ?


Index: usr.sbin/ldapd/search.c
===================================================================
RCS file: /cvs/src/usr.sbin/ldapd/search.c,v
retrieving revision 1.18
diff -u -p -r1.18 search.c
--- usr.sbin/ldapd/search.c     20 Jan 2017 11:55:08 -0000      1.18
+++ usr.sbin/ldapd/search.c     15 May 2018 11:12:47 -0000
@@ -437,8 +437,8 @@ conn_search(struct search *search)

                /* Check if we have passed the size limit. */
                if (rc == BT_SUCCESS && search->szlim > 0 &&
-                   search->nmatched >= search->szlim) {
-                       log_debug("search %d/%lld has reached size limit (%u)",
+                   search->nmatched > search->szlim) {
+                       log_debug("search %d/%lld has exceeded size limit (%u)",
                            search->conn->fd, search->req->msgid,
                            search->szlim);
                        reason = LDAP_SIZELIMIT_EXCEEDED;
@@ -449,8 +449,8 @@ conn_search(struct search *search)
        /* Check if we have passed the time limit. */
        now = time(0);
        if (rc == 0 && search->tmlim > 0 &&
-           search->started_at + search->tmlim <= now) {
-               log_debug("search %d/%lld has reached time limit (%u)",
+           search->started_at + search->tmlim < now) {
+               log_debug("search %d/%lld has exceeded time limit (%u)",
                    search->conn->fd, search->req->msgid,
                    search->tmlim);
                reason = LDAP_TIMELIMIT_EXCEEDED;

Reply via email to