Quiet clang scan
[freeradius.git] / src / modules / rlm_ldap / ldap.h
1 /**
2  * $Id$
3  * @file ldap.h
4  * @brief LDAP authorization and authentication module headers.
5  *
6  * @author Arran Cudbard-Bell <a.cudbardb@freeradius.org>
7  * @copyright 2015 Arran Cudbard-Bell <a.cudbardb@freeradius.org>
8  * @copyright 2013 Network RADIUS SARL<info@networkradius.com>
9  * @copyright 2013-2015 The FreeRADIUS Server Project.
10  */
11 #ifndef _RLM_LDAP_H
12 #define _RLM_LDAP_H
13
14 #include <freeradius-devel/radiusd.h>
15 #include <freeradius-devel/modules.h>
16
17 /*
18  *      We're mostly using the new API now, but ldap_bind
19  *      is in the list of deprecated functions, at we may
20  *      always need to support that.
21  */
22 #define LDAP_DEPRECATED 1
23 #include <lber.h>
24 #include <ldap.h>
25 #include "config.h"
26
27 /*
28  *      Ensure the have the ldap_create_sort_keylist()
29  *      function too, else we can't use ldap_create_sort_control()
30  */
31 #if !defined(LDAP_CREATE_SORT_KEYLIST) || !defined(LDAP_FREE_SORT_KEYLIST)
32 #  undef HAVE_LDAP_CREATE_SORT_CONTROL
33 #endif
34
35 /*
36  *      Because the LTB people define LDAP_VENDOR_VERSION_PATCH
37  *      as X, which precludes its use in printf statements *sigh*
38  *
39  *      Identifiers that are not macros, all evaluate to 0,
40  *      which is why this works.
41  */
42 #if !defined(LDAP_VENDOR_VERSION_PATCH) || LDAP_VENDOR_VERSION_PATCH == 0
43 #  undef LDAP_VENDOR_VERSION_PATCH
44 #  define LDAP_VENDOR_VERSION_PATCH 0
45 #endif
46
47 /*
48  *      For compatibility with other LDAP libraries
49  */
50 #if !defined(LDAP_SCOPE_BASE) && defined(LDAP_SCOPE_BASEOBJECT)
51 #  define LDAP_SCOPE_BASE LDAP_SCOPE_BASEOBJECT
52 #endif
53
54 #if !defined(LDAP_SCOPE_ONE) && defined(LDAP_SCOPE_ONELEVEL)
55 #  define LDAP_SCOPE_ONE LDAP_SCOPE_ONELEVEL
56 #endif
57
58 #if !defined(LDAP_SCOPE_SUB) && defined(LDAP_SCOPE_SUBTREE)
59 #  define LDAP_SCOPE_SUB LDAP_SCOPE_SUBTREE
60 #endif
61
62 #if !defined(LDAP_OPT_RESULT_CODE) && defined(LDAP_OPT_ERROR_NUMBER)
63 #  define LDAP_OPT_RESULT_CODE LDAP_OPT_ERROR_NUMBER
64 #endif
65
66 #ifndef LDAP_CONST
67 #  define LDAP_CONST
68 #endif
69
70 #if defined(HAVE_LDAP_URL_PARSE) && defined(HAVE_LDAP_IS_LDAP_URL) && defined(HAVE_LDAP_URL_DESC2STR)
71 #  define LDAP_CAN_PARSE_URLS
72 #endif
73
74 #define MOD_PREFIX                      "rlm_ldap"      //!< The name of the module.
75
76 #define LDAP_MAX_ATTRMAP                128             //!< Maximum number of mappings between LDAP and
77                                                         //!< FreeRADIUS attributes.
78 #define LDAP_MAP_RESERVED               4               //!< Number of additional items to allocate in expanded
79                                                         //!< attribute name arrays. Currently for enable attribute,
80                                                         //!< group membership attribute, valuepair attribute,
81                                                         //!< and profile attribute.
82
83 #define LDAP_MAX_CACHEABLE              64              //!< Maximum number of groups we retrieve from the server for
84                                                         //!< a given user. If more than this number are retrieve the
85                                                         //!< module returns invalid.
86
87 #define LDAP_MAX_GROUP_NAME_LEN         128             //!< Maximum name of a group name.
88 #define LDAP_MAX_ATTR_STR_LEN           256             //!< Maximum length of an xlat expanded LDAP attribute.
89 #define LDAP_MAX_FILTER_STR_LEN         1024            //!< Maximum length of an xlat expanded filter.
90 #define LDAP_MAX_DN_STR_LEN             1024            //!< Maximum length of an xlat expanded DN.
91
92 #define LDAP_VIRTUAL_DN_ATTR            "dn"            //!< 'Virtual' attribute which maps to the DN of the object.
93
94 typedef struct ldap_acct_section {
95         CONF_SECTION    *cs;                            //!< Section configuration.
96
97         char const      *reference;                     //!< Configuration reference string.
98 } ldap_acct_section_t;
99
100 typedef struct ldap_sasl {
101         char const      *mech;                          //!< SASL mech(s) to try.
102         char const      *proxy;                         //!< Identity to proxy.
103         char const      *realm;                         //!< Kerberos realm.
104 } ldap_sasl;
105
106 typedef struct ldap_sasl_dynamic {
107         vp_tmpl_t       *mech;                          //!< SASL mech(s) to try.
108         vp_tmpl_t       *proxy;                         //!< Identity to proxy.
109         vp_tmpl_t       *realm;                         //!< Kerberos realm.
110 } ldap_sasl_dynamic;
111
112 typedef struct ldap_instance {
113         CONF_SECTION    *cs;                            //!< Main configuration section for this instance.
114         fr_connection_pool_t *pool;                     //!< Connection pool instance.
115
116         char const      *config_server;                 //!< Server set in the config.
117         char            *server;                        //!< Initial server to bind to.
118         uint16_t        port;                           //!< Port to use when binding to the server.
119
120         char const      *admin_identity;                //!< Identity we bind as when we need to query the LDAP
121                                                         //!< directory.
122         char const      *admin_password;                //!< Password used in administrative bind.
123
124         ldap_sasl       admin_sasl;                     //!< SASL parameters used when binding as the admin.
125
126         char const      *dereference_str;               //!< When to dereference (never, searching, finding, always)
127         int             dereference;                    //!< libldap value specifying dereferencing behaviour.
128
129         bool            chase_referrals;                //!< If the LDAP server returns a referral to another server
130                                                         //!< or point in the tree, follow it, establishing new
131                                                         //!< connections and binding where necessary.
132         bool            chase_referrals_unset;          //!< If true, use the OpenLDAP defaults for chase_referrals.
133
134         bool            rebind;                         //!< Controls whether we set an ldad_rebind_proc function
135                                                         //!< and so determines if we can bind to other servers whilst
136                                                         //!< chasing referrals. If this is false, we will still chase
137                                                         //!< referrals on the same server, but won't bind to other
138                                                         //!< servers.
139
140         uint32_t        ldap_debug;                     //!< Debug flag for the SDK.
141
142         char const      *name;                          //!< Instance name.
143
144         bool            expect_password;                //!< True if the user_map included a mapping between an LDAP
145                                                         //!< attribute and one of our password reference attributes.
146
147         /*
148          *      RADIUS attribute to LDAP attribute maps
149          */
150         vp_map_t        *user_map;                      //!< Attribute map applied to users and profiles.
151
152         /*
153          *      User object attributes and filters
154          */
155         vp_tmpl_t       *userobj_filter;                //!< Filter to retrieve only user objects.
156         vp_tmpl_t       *userobj_base_dn;               //!< DN to search for users under.
157         char const      *userobj_scope_str;             //!< Scope (sub, one, base).
158         char const      *userobj_sort_by;               //!< List of attributes to sort by.
159         LDAPControl     *userobj_sort_ctrl;             //!< Server side sort control.
160
161         int             userobj_scope;                  //!< Search scope.
162
163         char const      *userobj_membership_attr;       //!< Attribute that describes groups the user is a member of.
164         char const      *userobj_access_attr;           //!< Attribute to check to see if the user should be locked out.
165         bool            access_positive;                //!< If true the presence of the attribute will allow access,
166                                                         //!< else it will deny access.
167
168         char const      *valuepair_attr;                //!< Generic dynamic mapping attribute, contains a RADIUS
169                                                         //!< attribute and value.
170
171         ldap_sasl_dynamic user_sasl;                    //!< SASL parameters used when binding as the user.
172
173         /*
174          *      Group object attributes and filters
175          */
176         char const      *groupobj_filter;               //!< Filter to retrieve only group objects.
177         vp_tmpl_t       *groupobj_base_dn;              //!< DN to search for users under.
178         char const      *groupobj_scope_str;            //!< Scope (sub, one, base).
179         int             groupobj_scope;                 //!< Search scope.
180
181         char const      *groupobj_name_attr;            //!< The name of the group.
182         char const      *groupobj_membership_filter;    //!< Filter to only retrieve groups which contain
183                                                         //!< the user as a member.
184
185         bool            cacheable_group_name;           //!< If true the server will determine complete set of group
186                                                         //!< memberships for the current user object, and perform any
187                                                         //!< resolution necessary to determine the names of those
188                                                         //!< groups, then right them to the control list (LDAP-Group).
189
190         bool            cacheable_group_dn;             //!< If true the server will determine complete set of group
191                                                         //!< memberships for the current user object, and perform any
192                                                         //!< resolution necessary to determine the DNs of those groups,
193                                                         //!< then right them to the control list (LDAP-GroupDN).
194
195         char const      *cache_attribute;               //!< Sets the attribute we use when creating and retrieving
196                                                         //!< cached group memberships.
197
198         DICT_ATTR const *cache_da;                      //!< The DA associated with this specific instance of the
199                                                         //!< rlm_ldap module.
200
201         DICT_ATTR const *group_da;                      //!< The DA associated with this specific instance of the
202                                                         //!< rlm_ldap module.
203
204         /*
205          *      Dynamic clients
206          */
207         char const      *clientobj_filter;              //!< Filter to retrieve only client objects.
208         char const      *clientobj_base_dn;             //!< DN to search for clients under.
209         char const      *clientobj_scope_str;           //!< Scope (sub, one, base).
210         int             clientobj_scope;                //!< Search scope.
211
212         bool            do_clients;                     //!< If true, attempt to load clients on instantiation.
213
214         /*
215          *      Profiles
216          */
217         vp_tmpl_t       *default_profile;               //!< If this is set, we will search for a profile object
218                                                         //!< with this name, and map any attributes it contains.
219                                                         //!< No value should be set if profiles are not being used
220                                                         //!< as there is an associated performance penalty.
221         char const      *profile_attr;                  //!< Attribute that identifies profiles to apply. May appear
222                                                         //!< in userobj or groupobj.
223         vp_tmpl_t       *profile_filter;                //!< Filter to retrieve only retrieve group objects.
224
225         /*
226          *      Accounting
227          */
228         ldap_acct_section_t *postauth;                  //!< Modify mappings for post-auth.
229         ldap_acct_section_t *accounting;                //!< Modify mappings for accounting.
230
231         /*
232          *      TLS items.  We should really normalize these with the
233          *      TLS code in 3.0.
234          */
235         int             tls_mode;
236         bool            start_tls;                      //!< Send the Start TLS message to the LDAP directory
237                                                         //!< to start encrypted communications using the standard
238                                                         //!< LDAP port.
239
240         char const      *tls_ca_file;                   //!< Sets the full path to a CA certificate (used to validate
241                                                         //!< the certificate the server presents).
242
243         char const      *tls_ca_path;                   //!< Sets the path to a directory containing CA certificates.
244
245         char const      *tls_certificate_file;          //!< Sets the path to the public certificate file we present
246                                                         //!< to the servers.
247
248         char const      *tls_private_key_file;          //!< Sets the path to the private key for our public
249                                                         //!< certificate.
250
251         char const      *tls_random_file;               //!< Path to the random file if /dev/random and /dev/urandom
252                                                         //!< are unavailable.
253
254         char const      *tls_require_cert_str;          //!< Sets requirements for validating the certificate the
255                                                         //!< server presents.
256
257         int             tls_require_cert;               //!< OpenLDAP constant representing the require cert string.
258
259         /*
260          *      Options
261          */
262         uint32_t        net_timeout;                    //!< How long we wait for new connections to the LDAP server
263                                                         //!< to be established.
264         uint32_t        res_timeout;                    //!< How long we wait for a result from the server.
265         uint32_t        srv_timelimit;                  //!< How long the server should spent on a single request
266                                                         //!< (also bounded by value on the server).
267
268 #ifdef WITH_EDIR
269         /*
270          *      eDir support
271          */
272         bool            edir;                           //!< If true attempt to retrieve the user's cleartext password
273                                                         //!< using the Universal Password feature of Novell eDirectory.
274         bool            edir_autz;                      //!< If true, and we have the Universal Password, bind with it
275                                                         //!< to perform additional authorisation checks.
276 #endif
277         /*
278          *      For keep-alives.
279          */
280 #ifdef LDAP_OPT_X_KEEPALIVE_IDLE
281         uint32_t        keepalive_idle;                 //!< Number of seconds a connections needs to remain idle
282                                                         //!< before TCP starts sending keepalive probes.
283 #endif
284 #ifdef LDAP_OPT_X_KEEPALIVE_PROBES
285         uint32_t        keepalive_probes;               //!< Number of missed timeouts before the connection is
286                                                         //!< dropped.
287 #endif
288 #ifdef LDAP_OPT_X_KEEPALIVE_INTERVAL
289         uint32_t        keepalive_interval;             //!< Interval between keepalive probes.
290 #endif
291
292         LDAP            *handle;                        //!< Hack for OpenLDAP libldap global initialisation.
293 } rlm_ldap_t;
294
295 /** Tracks the state of a libldap connection handle
296  *
297  */
298 typedef struct ldap_handle {
299         LDAP            *handle;                        //!< libldap handle.
300         bool            rebound;                        //!< Whether the connection has been rebound to something
301                                                         //!< other than the admin user.
302         bool            referred;                       //!< Whether the connection is now established a server
303                                                         //!< other than the configured one.
304         rlm_ldap_t      *inst;                          //!< rlm_ldap configuration.
305 } ldap_handle_t;
306
307 /** Result of expanding the RHS of a set of maps
308  *
309  * Used to store the array of attributes we'll be querying for.
310  */
311 typedef struct rlm_ldap_map_exp {
312         vp_map_t const *maps;                           //!< Head of list of maps we expanded the RHS of.
313         char const      *attrs[LDAP_MAX_ATTRMAP + LDAP_MAP_RESERVED + 1]; //!< Reserve some space for access attributes
314                                                         //!< and NULL termination.
315         TALLOC_CTX      *ctx;                           //!< Context to allocate new attributes in.
316         int             count;                          //!< Index on next free element.
317 } rlm_ldap_map_exp_t;
318
319 /** Contains a collection of values
320  *
321  */
322 typedef struct rlm_ldap_result {
323         struct berval   **values;                       //!< libldap struct containing bv_val (char *)
324                                                         //!< and length bv_len.
325         int             count;                          //!< Number of values.
326 } rlm_ldap_result_t;
327
328 /** Codes returned by rlm_ldap internal functions
329  *
330  */
331 typedef enum {
332         LDAP_PROC_CONTINUE = 1,                         //!< Operation is in progress.
333         LDAP_PROC_SUCCESS = 0,                          //!< Operation was successfull.
334
335         LDAP_PROC_ERROR = -1,                           //!< Unrecoverable library/server error.
336
337         LDAP_PROC_RETRY = -2,                           //!< Transitory error, caller should retry the operation
338                                                         //!< with a new connection.
339
340         LDAP_PROC_NOT_PERMITTED = -3,                   //!< Operation was not permitted, either current user was
341                                                         //!< locked out in the case of binds, or has insufficient
342                                                         //!< access.
343
344         LDAP_PROC_REJECT = -4,                          //!< Bind failed, user was rejected.
345
346         LDAP_PROC_BAD_DN = -5,                          //!< Specified an invalid object in a bind or search DN.
347
348         LDAP_PROC_NO_RESULT = -6                        //!< Got no results.
349 } ldap_rcode_t;
350
351 /*
352  *      Some functions may be called with a NULL request structure, this
353  *      simplifies switching certain messages from the request log to
354  *      the main log.
355  */
356 #define LDAP_INFO(fmt, ...) INFO("rlm_ldap (%s): " fmt, inst->name, ##__VA_ARGS__)
357 #define LDAP_WARN(fmt, ...) WARN("rlm_ldap (%s): " fmt, inst->name, ##__VA_ARGS__)
358
359 #define LDAP_DBGW(fmt, ...) radlog(L_DBG_WARN, "rlm_ldap (%s): " fmt, inst->name, ##__VA_ARGS__)
360 #define LDAP_DBGW_REQ(fmt, ...) do { if (request) {RWDEBUG(fmt, ##__VA_ARGS__);} else {LDAP_DBGW(fmt, ##__VA_ARGS__);}} while (0)
361
362 #define LDAP_DBG(fmt, ...) radlog(L_DBG, "rlm_ldap (%s): " fmt, inst->name, ##__VA_ARGS__)
363 #define LDAP_DBG_REQ(fmt, ...) do { if (request) {RDEBUG(fmt, ##__VA_ARGS__);} else {LDAP_DBG(fmt, ##__VA_ARGS__);}} while (0)
364
365 #define LDAP_DBG2(fmt, ...) if (rad_debug_lvl >= L_DBG_LVL_2) radlog(L_DBG, "rlm_ldap (%s): " fmt, inst->name, ##__VA_ARGS__)
366 #define LDAP_DBG_REQ2(fmt, ...) do { if (request) {RDEBUG2(fmt, ##__VA_ARGS__);} else if (rad_debug_lvl >= L_DBG_LVL_2) {LDAP_DBG(fmt, ##__VA_ARGS__);}} while (0)
367
368 #define LDAP_DBG3(fmt, ...) if (rad_debug_lvl >= L_DBG_LVL_3) radlog(L_DBG, "rlm_ldap (%s): " fmt, inst->name, ##__VA_ARGS__)
369 #define LDAP_DBG_REQ3(fmt, ...) do { if (request) {RDEBUG3(fmt, ##__VA_ARGS__);} else if (rad_debug_lvl >= L_DBG_LVL_3) {LDAP_DBG(fmt, ##__VA_ARGS__);}} while (0)
370
371 #define LDAP_ERR(fmt, ...) ERROR("rlm_ldap (%s): " fmt, inst->name, ##__VA_ARGS__)
372 #define LDAP_ERR_REQ(fmt, ...) do { if (request) {REDEBUG(fmt, ##__VA_ARGS__);} else {LDAP_ERR(fmt, ##__VA_ARGS__);}} while (0)
373
374 #define LDAP_EXT() if (extra) LDAP_ERR(extra)
375 #define LDAP_EXT_REQ() do { if (extra) { if (request) REDEBUG("%s", extra); else LDAP_ERR("%s", extra); }} while (0)
376
377 extern FR_NAME_NUMBER const ldap_scope[];
378 extern FR_NAME_NUMBER const ldap_tls_require_cert[];
379
380 /*
381  *      ldap.c - Wrappers arounds OpenLDAP functions.
382  */
383 size_t rlm_ldap_escape_func(UNUSED REQUEST *request, char *out, size_t outlen, char const *in, UNUSED void *arg);
384
385 bool rlm_ldap_is_dn(char const *in, size_t inlen);
386
387 size_t rlm_ldap_normalise_dn(char *out, char const *in);
388
389 ssize_t rlm_ldap_xlat_filter(REQUEST *request, char const **sub, size_t sublen, char *out, size_t outlen);
390
391 ldap_rcode_t rlm_ldap_bind(rlm_ldap_t const *inst, REQUEST *request, ldap_handle_t **pconn, char const *dn,
392                            char const *password, ldap_sasl *sasl, bool retry);
393
394 char const *rlm_ldap_error_str(ldap_handle_t const *conn);
395
396 ldap_rcode_t rlm_ldap_search(LDAPMessage **result, rlm_ldap_t const *inst, REQUEST *request,
397                              ldap_handle_t **pconn,
398                              char const *dn, int scope, char const *filter, char const * const *attrs,
399                              LDAPControl **serverctrls, LDAPControl **clientctrls);
400
401 ldap_rcode_t rlm_ldap_modify(rlm_ldap_t const *inst, REQUEST *request, ldap_handle_t **pconn,
402                              char const *dn, LDAPMod *mods[]);
403
404 char const *rlm_ldap_find_user(rlm_ldap_t const *inst, REQUEST *request, ldap_handle_t **pconn,
405                                char const *attrs[], bool force, LDAPMessage **result, rlm_rcode_t *rcode);
406
407 rlm_rcode_t rlm_ldap_check_access(rlm_ldap_t const *inst, REQUEST *request, ldap_handle_t const *conn,
408                                   LDAPMessage *entry);
409
410 void rlm_ldap_check_reply(rlm_ldap_t const *inst, REQUEST *request);
411
412 /*
413  *      ldap.c - Callbacks for the connection pool API.
414  */
415 ldap_rcode_t rlm_ldap_result(rlm_ldap_t const *inst, ldap_handle_t const *conn, int msgid, char const *dn,
416                              LDAPMessage **result, char const **error, char **extra);
417
418 char *rlm_ldap_berval_to_string(TALLOC_CTX *ctx, struct berval const *in);
419
420 int rlm_ldap_global_init(rlm_ldap_t *inst) CC_HINT(nonnull);
421
422 void *mod_conn_create(TALLOC_CTX *ctx, void *instance);
423
424 ldap_handle_t *mod_conn_get(rlm_ldap_t const *inst, REQUEST *request);
425
426 void mod_conn_release(rlm_ldap_t const *inst, ldap_handle_t *conn);
427
428 /*
429  *      groups.c - Group membership functions.
430  */
431 rlm_rcode_t rlm_ldap_cacheable_userobj(rlm_ldap_t const *inst, REQUEST *request, ldap_handle_t **pconn,
432                                        LDAPMessage *entry, char const *attr);
433
434 rlm_rcode_t rlm_ldap_cacheable_groupobj(rlm_ldap_t const *inst, REQUEST *request, ldap_handle_t **pconn);
435
436 rlm_rcode_t rlm_ldap_check_groupobj_dynamic(rlm_ldap_t const *inst, REQUEST *request, ldap_handle_t **pconn,
437                                             VALUE_PAIR *check);
438
439 rlm_rcode_t rlm_ldap_check_userobj_dynamic(rlm_ldap_t const *inst, REQUEST *request, ldap_handle_t **pconn,
440                                            char const *dn, VALUE_PAIR *check);
441
442 rlm_rcode_t rlm_ldap_check_cached(rlm_ldap_t const *inst, REQUEST *request, VALUE_PAIR *check);
443
444 /*
445  *      attrmap.c - Attribute mapping code.
446  */
447 int rlm_ldap_map_getvalue(TALLOC_CTX *ctx, VALUE_PAIR **out, REQUEST *request, vp_map_t const *map, void *uctx);
448
449 int rlm_ldap_map_verify(vp_map_t *map, void *instance);
450
451 int rlm_ldap_map_expand(rlm_ldap_map_exp_t *expanded, REQUEST *request, vp_map_t const *maps);
452
453 int rlm_ldap_map_do(rlm_ldap_t const *inst, REQUEST *request, LDAP *handle,
454                     rlm_ldap_map_exp_t const *expanded, LDAPMessage *entry);
455
456 /*
457  *      clients.c - Dynamic clients (bulk load).
458  */
459 int  rlm_ldap_client_load(rlm_ldap_t const *inst, CONF_SECTION *tmpl, CONF_SECTION *cs);
460
461 /*
462  *      edir.c - Magic extensions for Novell
463  */
464 int nmasldap_get_password(LDAP *ld, char const *dn, char *password, size_t *len);
465
466 char const *edir_errstr(int code);
467
468 /*
469  *      sasl.s - SASL bind functions
470  */
471 ldap_rcode_t rlm_ldap_sasl_interactive(rlm_ldap_t const *inst, REQUEST *request,
472                                        ldap_handle_t *pconn, char const *dn,
473                                        char const *password, ldap_sasl *sasl,
474                                        char const **error, char **error_extra);
475 #endif