TARGET := $(TARGETNAME)$(L)
endif
-SOURCES := $(TARGETNAME).c groups.c user.c
+SOURCES := $(TARGETNAME).c groups.c user.c profile.c
SRC_CFLAGS += -I$(top_builddir)/src/modules/rlm_ldap
TGT_PREREQS := libfreeradius-ldap$(L)
--- /dev/null
+/*
+ * This program is is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or (at
+ * your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
+ */
+
+/**
+ * $Id$
+ * @file rlm_ldap.c
+ * @brief LDAP authorization and authentication module.
+ *
+ * @author Arran Cudbard-Bell (a.cudbardb@freeradius.org)
+ * @author Alan DeKok (aland@freeradius.org)
+ *
+ * @copyright 2012,2015 Arran Cudbard-Bell (a.cudbardb@freeradius.org)
+ * @copyright 2013,2015 Network RADIUS SAS (legal@networkradius.com)
+ * @copyright 2012 Alan DeKok (aland@freeradius.org)
+ * @copyright 1999-2013 The FreeRADIUS Server Project.
+ */
+RCSID("$Id$")
+
+USES_APPLE_DEPRECATED_API
+
+#include "rlm_ldap.h"
+#include <freeradius-devel/ldap/conf.h>
+
+#include <freeradius-devel/server/map_proc.h>
+#include <freeradius-devel/server/module_rlm.h>
+
+/** Holds state of in progress async profile lookups
+ *
+ */
+typedef struct {
+ fr_ldap_query_t *query;
+ char const *dn;
+ rlm_ldap_t const *inst;
+ fr_ldap_map_exp_t const *expanded;
+} ldap_profile_ctx_t;
+
+/** Process the results of a profile lookup
+ *
+ */
+static unlang_action_t ldap_map_profile_resume(rlm_rcode_t *p_result, UNUSED int *priority, request_t *request,
+ void *uctx)
+{
+ ldap_profile_ctx_t *profile_ctx = talloc_get_type_abort(uctx, ldap_profile_ctx_t);
+ fr_ldap_query_t *query = profile_ctx->query;
+ LDAP *handle;
+ LDAPMessage *entry = NULL;
+ int ldap_errno;
+ rlm_rcode_t rcode = RLM_MODULE_OK;
+
+ switch (query->ret) {
+ case LDAP_RESULT_SUCCESS:
+ break;
+
+ case LDAP_RESULT_NO_RESULT:
+ case LDAP_RESULT_BAD_DN:
+ RDEBUG2("Profile object \"%s\" not found", profile_ctx->dn);
+ rcode = RLM_MODULE_NOTFOUND;
+ goto finish;
+
+ default:
+ rcode = RLM_MODULE_FAIL;
+ goto finish;
+ }
+
+ fr_assert(query->result);
+ handle = query->ldap_conn->handle;
+
+ entry = ldap_first_entry(handle, query->result);
+ if (!entry) {
+ ldap_get_option(handle, LDAP_OPT_RESULT_CODE, &ldap_errno);
+ REDEBUG("Failed retrieving entry: %s", ldap_err2string(ldap_errno));
+ rcode = RLM_MODULE_NOTFOUND;
+ goto finish;
+ }
+
+ RDEBUG2("Processing profile attributes");
+ RINDENT();
+ if (fr_ldap_map_do(request, profile_ctx->inst->valuepair_attr,
+ profile_ctx->expanded, entry) > 0) rcode = RLM_MODULE_UPDATED;
+ REXDENT();
+
+finish:
+ talloc_free(profile_ctx);
+ RETURN_MODULE_RCODE(rcode);
+}
+
+/** Cancel an in progress profile lookup
+ *
+ */
+static void ldap_map_profile_cancel(UNUSED request_t *request, UNUSED fr_signal_t action, void *uctx)
+{
+ ldap_profile_ctx_t *profile_ctx = talloc_get_type_abort(uctx, ldap_profile_ctx_t);
+
+ if (!profile_ctx->query || !profile_ctx->query->treq) return;
+
+ fr_trunk_request_signal_cancel(profile_ctx->query->treq);
+}
+
+/** Search for and apply an LDAP profile
+ *
+ * LDAP profiles are mapped using the same attribute map as user objects, they're used to add common
+ * sets of attributes to the request.
+ *
+ * @param[in] request Current request.
+ * @param[in] dn of profile object to apply.
+ * @param[in] scope to apply when looking up profiles.
+ * @param[in] filter to apply when looking up profiles.
+ * @param[in] expanded Structure containing a list of xlat
+ * expanded attribute names and mapping information.
+ * @return One of the RLM_MODULE_* values.
+ */
+unlang_action_t rlm_ldap_map_profile(rlm_ldap_t const *inst, request_t *request, fr_ldap_thread_trunk_t *ttrunk,
+ char const *dn, int scope, char const *filter, fr_ldap_map_exp_t const *expanded)
+{
+ ldap_profile_ctx_t *profile_ctx;
+
+ if (!dn || !*dn) return UNLANG_ACTION_CALCULATE_RESULT;
+
+ MEM(profile_ctx = talloc(unlang_interpret_frame_talloc_ctx(request), ldap_profile_ctx_t));
+ *profile_ctx = (ldap_profile_ctx_t) {
+ .dn = dn,
+ .expanded = expanded,
+ .inst = inst
+ };
+
+ if (unlang_function_push(request, NULL, ldap_map_profile_resume, ldap_map_profile_cancel,
+ ~FR_SIGNAL_CANCEL, UNLANG_SUB_FRAME, profile_ctx) < 0) {
+ talloc_free(profile_ctx);
+ return UNLANG_ACTION_FAIL;
+ }
+
+ return fr_ldap_trunk_search(NULL, profile_ctx, &profile_ctx->query, request, ttrunk, dn,
+ scope, filter,
+ expanded->attrs, NULL, NULL);
+}
ldap_auth_call_env_t *call_env;
} ldap_auth_ctx_t;
-/** Holds state of in progress async profile lookups
- *
- */
-typedef struct {
- fr_ldap_query_t *query;
- char const *dn;
- rlm_ldap_t const *inst;
- fr_ldap_map_exp_t const *expanded;
-} ldap_profile_ctx_t;
-
/** Holds state of in progress ldap user modifications
*
*/
return UNLANG_ACTION_PUSHED_CHILD;
}
-/** Process the results of a profile lookup
- *
- */
-static unlang_action_t ldap_map_profile_resume(rlm_rcode_t *p_result, UNUSED int *priority, request_t *request,
- void *uctx)
-{
- ldap_profile_ctx_t *profile_ctx = talloc_get_type_abort(uctx, ldap_profile_ctx_t);
- fr_ldap_query_t *query = profile_ctx->query;
- LDAP *handle;
- LDAPMessage *entry = NULL;
- int ldap_errno;
- rlm_rcode_t rcode = RLM_MODULE_OK;
-
- switch (query->ret) {
- case LDAP_RESULT_SUCCESS:
- break;
-
- case LDAP_RESULT_NO_RESULT:
- case LDAP_RESULT_BAD_DN:
- RDEBUG2("Profile object \"%s\" not found", profile_ctx->dn);
- rcode = RLM_MODULE_NOTFOUND;
- goto finish;
-
- default:
- rcode = RLM_MODULE_FAIL;
- goto finish;
- }
-
- fr_assert(query->result);
- handle = query->ldap_conn->handle;
-
- entry = ldap_first_entry(handle, query->result);
- if (!entry) {
- ldap_get_option(handle, LDAP_OPT_RESULT_CODE, &ldap_errno);
- REDEBUG("Failed retrieving entry: %s", ldap_err2string(ldap_errno));
- rcode = RLM_MODULE_NOTFOUND;
- goto finish;
- }
-
- RDEBUG2("Processing profile attributes");
- RINDENT();
- if (fr_ldap_map_do(request, profile_ctx->inst->valuepair_attr,
- profile_ctx->expanded, entry) > 0) rcode = RLM_MODULE_UPDATED;
- REXDENT();
-
-finish:
- talloc_free(profile_ctx);
- RETURN_MODULE_RCODE(rcode);
-}
-
-/** Cancel an in progress profile lookup
- *
- */
-static void ldap_map_profile_cancel(UNUSED request_t *request, UNUSED fr_signal_t action, void *uctx)
-{
- ldap_profile_ctx_t *profile_ctx = talloc_get_type_abort(uctx, ldap_profile_ctx_t);
-
- if (!profile_ctx->query || !profile_ctx->query->treq) return;
-
- fr_trunk_request_signal_cancel(profile_ctx->query->treq);
-}
-
-/** Search for and apply an LDAP profile
- *
- * LDAP profiles are mapped using the same attribute map as user objects, they're used to add common
- * sets of attributes to the request.
- *
- * @param[in] request Current request.
- * @param[in] autz_ctx Authorization context being processed.
- * @param[in] dn of profile object to apply.
- * @param[in] expanded Structure containing a list of xlat
- * expanded attribute names and mapping information.
- * @return One of the RLM_MODULE_* values.
- */
-static unlang_action_t rlm_ldap_map_profile(request_t *request, ldap_autz_ctx_t *autz_ctx,
- char const *dn, fr_ldap_map_exp_t const *expanded)
-{
- rlm_ldap_t const *inst = autz_ctx->inst;
- fr_ldap_thread_trunk_t *ttrunk = autz_ctx->ttrunk;
- ldap_profile_ctx_t *profile_ctx;
- rlm_rcode_t ret;
-
- if (!dn || !*dn) return UNLANG_ACTION_CALCULATE_RESULT;
-
- MEM(profile_ctx = talloc(unlang_interpret_frame_talloc_ctx(request), ldap_profile_ctx_t));
- *profile_ctx = (ldap_profile_ctx_t) {
- .dn = dn,
- .expanded = expanded,
- .inst = inst
- };
-
- if (unlang_function_push(request, NULL, ldap_map_profile_resume, ldap_map_profile_cancel,
- ~FR_SIGNAL_CANCEL, UNLANG_SUB_FRAME, profile_ctx) < 0) {
- talloc_free(profile_ctx);
- return UNLANG_ACTION_FAIL;
- }
-
- return fr_ldap_trunk_search(&ret, profile_ctx, &profile_ctx->query, request, ttrunk, dn,
- inst->profile_scope, autz_ctx->call_env->profile_filter.vb_strvalue,
- expanded->attrs, NULL, NULL);
-}
-
/** Start LDAP authorization with async lookup of user DN
*
*/
unlang_action_t ret;
REPEAT_MOD_AUTHORIZE_RESUME;
- ret = rlm_ldap_map_profile(request, autz_ctx, call_env->default_profile.vb_strvalue,
- &autz_ctx->expanded);
+ ret = rlm_ldap_map_profile(inst, request, autz_ctx->ttrunk, autz_ctx->profile_value,
+ inst->profile_scope, call_env->default_profile.vb_strvalue, &autz_ctx->expanded);
switch (ret) {
case UNLANG_ACTION_FAIL:
rcode = RLM_MODULE_FAIL;
autz_ctx->profile_value = fr_ldap_berval_to_string(autz_ctx, autz_ctx->profile_values[autz_ctx->value_idx++]);
REPEAT_MOD_AUTHORIZE_RESUME;
- ret = rlm_ldap_map_profile(request, autz_ctx, autz_ctx->profile_value, &autz_ctx->expanded);
+ ret = rlm_ldap_map_profile(inst, request, autz_ctx->ttrunk, autz_ctx->profile_value,
+ inst->profile_scope, autz_ctx->call_env->profile_filter.vb_strvalue, &autz_ctx->expanded);
switch (ret) {
case UNLANG_ACTION_FAIL:
rcode = RLM_MODULE_FAIL;
unlang_action_t rlm_ldap_check_cached(rlm_rcode_t *p_result,
rlm_ldap_t const *inst, request_t *request, fr_value_box_t const *check);
+
+unlang_action_t rlm_ldap_map_profile(rlm_ldap_t const *inst, request_t *request, fr_ldap_thread_trunk_t *ttrunk,
+ char const *dn, int scope, char const *filter, fr_ldap_map_exp_t const *expanded);