1 /* $Cambridge: exim/src/src/auths/call_radius.c,v 1.1 2004/10/07 13:10:01 ph10 Exp $ */
3 /*************************************************
4 * Exim - an Internet mail transport agent *
5 *************************************************/
7 /* Copyright (c) University of Cambridge 1995 - 2004 */
8 /* See the file NOTICE for conditions of use and distribution. */
10 /* This file was originally supplied by Ian Kirk. The libradius support came
15 /* This module contains functions that call the Radius authentication
18 We can't just compile this code and allow the library mechanism to omit the
19 functions if they are not wanted, because we need to have the Radius headers
20 available for compiling. Therefore, compile these functions only if
21 RADIUS_CONFIG_FILE is defined. However, some compilers don't like compiling
22 empty modules, so keep them happy with a dummy when skipping the rest. Make it
23 reference itself to stop picky compilers complaining that it is unused, and put
24 in a dummy argument to stop even pickier compilers complaining about infinite
27 #ifndef RADIUS_CONFIG_FILE
28 static void dummy(int x) { dummy(x-1); }
29 #else /* RADIUS_CONFIG_FILE */
32 /* Two different Radius libraries are supported. The default is radiusclient. */
34 #ifdef RADIUS_LIB_RADLIB
37 #ifndef RADIUS_LIB_RADIUSCLIENT
38 #define RADIUS_LIB_RADIUSCLIENT
40 #include <radiusclient.h>
45 /*************************************************
46 * Perform RADIUS authentication *
47 *************************************************/
49 /* This function calls the Radius authentication mechanism, passing over one or
53 s a colon-separated list of strings
54 errptr where to point an error message
56 Returns: OK if authentication succeeded
57 FAIL if authentication failed
58 ERROR some other error condition
62 auth_call_radius(uschar *s, uschar **errptr)
65 uschar *radius_args = s;
69 #ifdef RADIUS_LIB_RADLIB
72 VALUE_PAIR *send = NULL;
74 unsigned int service = PW_AUTHENTICATE_ONLY;
79 user = string_nextinlist(&radius_args, &sep, big_buffer, big_buffer_size);
80 if (user == NULL) user = US"";
82 DEBUG(D_auth) debug_printf("Running RADIUS authentication for user \"%s\" "
83 "and \"%s\"\n", user, radius_args);
88 /* Authenticate using the radiusclient library */
90 #ifdef RADIUS_LIB_RADIUSCLIENT
94 if (rc_read_config(RADIUS_CONFIG_FILE) != 0)
95 *errptr = string_sprintf("RADIUS: can't open %s", RADIUS_CONFIG_FILE);
97 else if (rc_read_dictionary(rc_conf_str("dictionary")) != 0)
98 *errptr = string_sprintf("RADIUS: can't read dictionary");
100 else if (rc_avpair_add(&send, PW_USER_NAME, user, 0) == NULL)
101 *errptr = string_sprintf("RADIUS: add user name failed\n");
103 else if (rc_avpair_add(&send, PW_USER_PASSWORD, CS radius_args, 0) == NULL)
104 *errptr = string_sprintf("RADIUS: add password failed\n");
106 else if (rc_avpair_add(&send, PW_SERVICE_TYPE, &service, 0) == NULL)
107 *errptr = string_sprintf("RADIUS: add service type failed\n");
111 DEBUG(D_auth) debug_printf("%s\n", *errptr);
115 result = rc_auth(0, send, &received, msg);
116 DEBUG(D_auth) debug_printf("RADIUS code returned %d\n", result);
127 *errptr = US"RADIUS: timed out";
132 *errptr = string_sprintf("RADIUS: unexpected response (%d)", result);
136 #else /* RADIUS_LIB_RADIUSCLIENT not set => RADIUS_LIB_RADLIB is set */
138 /* Authenticate using the libradius library */
143 *errptr = string_sprintf("RADIUS: can't initialise libradius");
146 if (rad_config(h, RADIUS_CONFIG_FILE) != 0 ||
147 rad_create_request(h, RAD_ACCESS_REQUEST) != 0 ||
148 rad_put_string(h, RAD_USER_NAME, CS user) != 0 ||
149 rad_put_string(h, RAD_USER_PASSWORD, CS radius_args) != 0 ||
150 rad_put_int(h, RAD_SERVICE_TYPE, RAD_AUTHENTICATE_ONLY) != 0)
152 *errptr = string_sprintf("RADIUS: %s", rad_strerror(h));
157 result = rad_send_request(h);
161 case RAD_ACCESS_ACCEPT:
165 case RAD_ACCESS_REJECT:
170 *errptr = string_sprintf("RADIUS: %s", rad_strerror(h));
175 *errptr = string_sprintf("RADIUS: unexpected response (%d)", result);
181 if (*errptr != NULL) DEBUG(D_auth) debug_printf("%s\n", *errptr);
185 #endif /* RADIUS_LIB_RADLIB */
188 #endif /* RADIUS_CONFIG_FILE */
190 /* End of call_radius.c */