⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 util_ldap.c

📁 最新apache的源代码
💻 C
📖 第 1 页 / 共 4 页
字号:
                l->bound = 0;                util_ldap_strdup((char**)&(l->binddn), binddn);                util_ldap_strdup((char**)&(l->bindpw), bindpw);                break;            }#if APR_HAS_THREADS                /* If this connection didn't match the criteria, then we                 * need to unlock the mutex so it is available to be reused.                 */                apr_thread_mutex_unlock(l->lock);            }#endif            p = l;        }    }/* artificially disable cache *//* l = NULL; */    /* If no connection what found after the second search, we     * must create one.     */    if (!l) {        /*          * Add the new connection entry to the linked list. Note that we         * don't actually establish an LDAP connection yet; that happens         * the first time authentication is requested.         */        /* create the details to the pool in st */        l = apr_pcalloc(st->pool, sizeof(util_ldap_connection_t));#if APR_HAS_THREADS        apr_thread_mutex_create(&l->lock, APR_THREAD_MUTEX_DEFAULT, st->pool);        apr_thread_mutex_lock(l->lock);#endif        l->pool = st->pool;        l->bound = 0;        l->host = apr_pstrdup(st->pool, host);        l->port = port;        l->deref = deref;        util_ldap_strdup((char**)&(l->binddn), binddn);        util_ldap_strdup((char**)&(l->bindpw), bindpw);        l->secure = secure;        /* add the cleanup to the pool */        apr_pool_cleanup_register(l->pool, l,                                  util_ldap_connection_cleanup,                                  apr_pool_cleanup_null);        if (p) {            p->next = l;        }        else {            st->connections = l;        }    }#if APR_HAS_THREADS    apr_thread_mutex_unlock(st->mutex);#endif    return l;}/* ------------------------------------------------------------------ *//* * Compares two DNs to see if they're equal. The only way to do this correctly is to  * search for the dn and then do ldap_get_dn() on the result. This should match the  * initial dn, since it would have been also retrieved with ldap_get_dn(). This is * expensive, so if the configuration value compare_dn_on_server is * false, just does an ordinary strcmp. * * The lock for the ldap cache should already be acquired. */LDAP_DECLARE(int) util_ldap_cache_comparedn(request_rec *r, util_ldap_connection_t *ldc,                             const char *url, const char *dn, const char *reqdn,                             int compare_dn_on_server){    int result = 0;    util_url_node_t *curl;     util_url_node_t curnode;    util_dn_compare_node_t *node;    util_dn_compare_node_t newnode;    int failures = 0;    LDAPMessage *res, *entry;    char *searchdn;    util_ldap_state_t *st =  (util_ldap_state_t *)ap_get_module_config(r->server->module_config, &ldap_module);    /* get cache entry (or create one) */    LDAP_CACHE_LOCK();    curnode.url = url;    curl = util_ald_cache_fetch(st->util_ldap_cache, &curnode);    if (curl == NULL) {        curl = util_ald_create_caches(st, url);    }    LDAP_CACHE_UNLOCK();    /* a simple compare? */    if (!compare_dn_on_server) {        /* unlock this read lock */        if (strcmp(dn, reqdn)) {            ldc->reason = "DN Comparison FALSE (direct strcmp())";            return LDAP_COMPARE_FALSE;        }        else {            ldc->reason = "DN Comparison TRUE (direct strcmp())";            return LDAP_COMPARE_TRUE;        }    }    if (curl) {        /* no - it's a server side compare */        LDAP_CACHE_LOCK();            /* is it in the compare cache? */        newnode.reqdn = (char *)reqdn;        node = util_ald_cache_fetch(curl->dn_compare_cache, &newnode);        if (node != NULL) {            /* If it's in the cache, it's good */            /* unlock this read lock */            LDAP_CACHE_UNLOCK();            ldc->reason = "DN Comparison TRUE (cached)";            return LDAP_COMPARE_TRUE;        }            /* unlock this read lock */        LDAP_CACHE_UNLOCK();    }start_over:    if (failures++ > 10) {	/* too many failures */        return result;    }    /* make a server connection */    if (LDAP_SUCCESS != (result = util_ldap_connection_open(r, ldc))) {	/* connect to server failed */        return result;    }    /* search for reqdn */    if ((result = ldap_search_ext_s(ldc->ldap, const_cast(reqdn), LDAP_SCOPE_BASE, 				    "(objectclass=*)", NULL, 1, 				    NULL, NULL, NULL, -1, &res)) == LDAP_SERVER_DOWN) {        ldc->reason = "DN Comparison ldap_search_ext_s() failed with server down";        util_ldap_connection_unbind(ldc);        goto start_over;    }    if (result != LDAP_SUCCESS) {        /* search for reqdn failed - no match */        ldc->reason = "DN Comparison ldap_search_ext_s() failed";        return result;    }    entry = ldap_first_entry(ldc->ldap, res);    searchdn = ldap_get_dn(ldc->ldap, entry);    ldap_msgfree(res);    if (strcmp(dn, searchdn) != 0) {        /* compare unsuccessful */        ldc->reason = "DN Comparison FALSE (checked on server)";        result = LDAP_COMPARE_FALSE;    }    else {        if (curl) {            /* compare successful - add to the compare cache */            LDAP_CACHE_LOCK();            newnode.reqdn = (char *)reqdn;            newnode.dn = (char *)dn;                        node = util_ald_cache_fetch(curl->dn_compare_cache, &newnode);            if ((node == NULL) ||                 (strcmp(reqdn, node->reqdn) != 0) || (strcmp(dn, node->dn) != 0)) {                util_ald_cache_insert(curl->dn_compare_cache, &newnode);            }            LDAP_CACHE_UNLOCK();        }        ldc->reason = "DN Comparison TRUE (checked on server)";        result = LDAP_COMPARE_TRUE;    }    ldap_memfree(searchdn);    return result;}/* * Does an generic ldap_compare operation. It accepts a cache that it will use * to lookup the compare in the cache. We cache two kinds of compares  * (require group compares) and (require user compares). Each compare has a different * cache node: require group includes the DN; require user does not because the * require user cache is owned by the  * */LDAP_DECLARE(int) util_ldap_cache_compare(request_rec *r, util_ldap_connection_t *ldc,                          const char *url, const char *dn,                          const char *attrib, const char *value){    int result = 0;    util_url_node_t *curl;     util_url_node_t curnode;    util_compare_node_t *compare_nodep;    util_compare_node_t the_compare_node;    apr_time_t curtime = 0; /* silence gcc -Wall */    int failures = 0;    util_ldap_state_t *st =         (util_ldap_state_t *)ap_get_module_config(r->server->module_config,        &ldap_module);    /* get cache entry (or create one) */    LDAP_CACHE_LOCK();    curnode.url = url;    curl = util_ald_cache_fetch(st->util_ldap_cache, &curnode);    if (curl == NULL) {        curl = util_ald_create_caches(st, url);    }    LDAP_CACHE_UNLOCK();    if (curl) {        /* make a comparison to the cache */        LDAP_CACHE_LOCK();        curtime = apr_time_now();            the_compare_node.dn = (char *)dn;        the_compare_node.attrib = (char *)attrib;        the_compare_node.value = (char *)value;        the_compare_node.result = 0;            compare_nodep = util_ald_cache_fetch(curl->compare_cache, &the_compare_node);            if (compare_nodep != NULL) {            /* found it... */            if (curtime - compare_nodep->lastcompare > st->compare_cache_ttl) {                /* ...but it is too old */                util_ald_cache_remove(curl->compare_cache, compare_nodep);            }            else {                /* ...and it is good */                /* unlock this read lock */                LDAP_CACHE_UNLOCK();                if (LDAP_COMPARE_TRUE == compare_nodep->result) {                    ldc->reason = "Comparison true (cached)";                    return compare_nodep->result;                }                else if (LDAP_COMPARE_FALSE == compare_nodep->result) {                    ldc->reason = "Comparison false (cached)";                    return compare_nodep->result;                }                else if (LDAP_NO_SUCH_ATTRIBUTE == compare_nodep->result) {                    ldc->reason = "Comparison no such attribute (cached)";                    return compare_nodep->result;                }                else {                    ldc->reason = "Comparison undefined (cached)";                    return compare_nodep->result;                }            }        }        /* unlock this read lock */        LDAP_CACHE_UNLOCK();    }start_over:    if (failures++ > 10) {        /* too many failures */        return result;    }    if (LDAP_SUCCESS != (result = util_ldap_connection_open(r, ldc))) {        /* connect failed */        return result;    }    if ((result = ldap_compare_s(ldc->ldap, const_cast(dn), const_cast(attrib), const_cast(value)))        == LDAP_SERVER_DOWN) {         /* connection failed - try again */        ldc->reason = "ldap_compare_s() failed with server down";        util_ldap_connection_unbind(ldc);        goto start_over;    }    ldc->reason = "Comparison complete";    if ((LDAP_COMPARE_TRUE == result) ||         (LDAP_COMPARE_FALSE == result) ||        (LDAP_NO_SUCH_ATTRIBUTE == result)) {        if (curl) {            /* compare completed; caching result */            LDAP_CACHE_LOCK();            the_compare_node.lastcompare = curtime;            the_compare_node.result = result;            /* If the node doesn't exist then insert it, otherwise just update it with               the last results */            compare_nodep = util_ald_cache_fetch(curl->compare_cache, &the_compare_node);            if ((compare_nodep == NULL) ||                 (strcmp(the_compare_node.dn, compare_nodep->dn) != 0) ||                 (strcmp(the_compare_node.attrib, compare_nodep->attrib) != 0) ||                 (strcmp(the_compare_node.value, compare_nodep->value) != 0)) {                util_ald_cache_insert(curl->compare_cache, &the_compare_node);            }            else {                compare_nodep->lastcompare = curtime;                compare_nodep->result = result;            }            LDAP_CACHE_UNLOCK();        }        if (LDAP_COMPARE_TRUE == result) {            ldc->reason = "Comparison true (adding to cache)";            return LDAP_COMPARE_TRUE;        }        else if (LDAP_COMPARE_FALSE == result) {            ldc->reason = "Comparison false (adding to cache)";            return LDAP_COMPARE_FALSE;        }        else {            ldc->reason = "Comparison no such attribute (adding to cache)";            return LDAP_NO_SUCH_ATTRIBUTE;        }    }    return result;}LDAP_DECLARE(int) util_ldap_cache_checkuserid(request_rec *r, util_ldap_connection_t *ldc,                              const char *url, const char *basedn, int scope, char **attrs,                              const char *filter, const char *bindpw, const char **binddn,                              const char ***retvals){    const char **vals = NULL;    int numvals = 0;    int result = 0;    LDAPMessage *res, *entry;    char *dn;    int count;    int failures = 0;    util_url_node_t *curl;		/* Cached URL node */    util_url_node_t curnode;    util_search_node_t *search_nodep;	/* Cached search node */    util_search_node_t the_search_node;    apr_time_t curtime;    util_ldap_state_t *st =         (util_ldap_state_t *)ap_get_module_config(r->server->module_config,        &ldap_module);    /* Get the cache node for this url */    LDAP_CACHE_LOCK();    curnode.url = url;    curl = (util_url_node_t *)util_ald_cache_fetch(st->util_ldap_cache, &curnode);    if (curl == NULL) {        curl = util_ald_create_caches(st, url);    }    LDAP_CACHE_UNLOCK();    if (curl) {        LDAP_CACHE_LOCK();        the_search_node.username = filter;        search_nodep = util_ald_cache_fetch(curl->search_cache, &the_search_node);        if (search_nodep != NULL) {                /* found entry in search cache... */            curtime = apr_time_now();                /*             * Remove this item from the cache if its expired.             * If the sent password doesn't match the stored password,             * the entry will be removed and readded later if the             * credentials pass authentication.             */            if ((curtime - search_nodep->lastbind) > st->search_cache_ttl) {                /* ...but entry is too old */                util_ald_cache_remove(curl->search_cache, search_nodep);            }            else if ((search_nodep->bindpw) &&                (search_nodep->bindpw[0] != '\0') &&                (strcmp(search_nodep->bindpw, bindpw) == 0)) {                /* ...and entry is valid */                *binddn = search_nodep->dn;                *retvals = search_nodep->vals;                LDAP_CACHE_UNLOCK();                ldc->reason = "Authentication successful (cached)";                return LDAP_SUCCESS;            }        }        /* unlock this read lock */        LDAP_CACHE_UNLOCK();    }    /*	     * At this point, there is no valid cached search, so lets do the search.     */    /*     * If any LDAP operation fails due to LDAP_SERVER_DOWN, control returns here.     */start_over:    if (failures++ > 10) {        return result;    }    if (LDAP_SUCCESS != (result = util_ldap_connection_open(r, ldc))) {        return result;    }    /* try do the search */    if ((result = ldap_search_ext_s(ldc->ldap,				    const_cast(basedn), scope, 				    const_cast(filter), attrs, 0, 				    NULL, NULL, NULL, -1, &res)) == LDAP_SERVER_DOWN) {        ldc->reason = "ldap_search_ext_s() for user failed with server down";        util_ldap_connection_unbind(ldc);        goto start_over;    }    /* if there is an error (including LDAP_NO_SUCH_OBJECT) return now */    if (result != LDAP_SUCCESS) {        ldc->reason = "ldap_search_ext_s() for user failed";        return result;    }    /*      * We should have found exactly one entry; to find a different     * number is an error.     */    count = ldap_count_entries(ldc->ldap, res);    if (count != 1)     {        if (count == 0 )            ldc->reason = "User not found";        else            ldc->reason = "User is not unique (search found two or more matches)";        ldap_msgfree(res);        return LDAP_NO_SUCH_OBJECT;    }    entry = ldap_first_entry(ldc->ldap, res);

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -