yet ANOTHER EAP-TTLS/PAP with OpenLDAP problem ...
I've been working on this for a while, and have yet to find a way to configure this correctly, despite lots of reading through the mailing list archives, documentation included with FreeRADIUS, and third-party documentation. In fact, I've been trying to get this working for years with older versions of FreeRADIUS, and have succeeded only with FreeRADIUS<=1.1.6, using configurations that readers of this list are repeatedly told not to use (such as setting Auth-Type in the users file). [ASIDE] With the older versions of FreeRADIUS we're having performance problems with the authentication. Research on this list has uncovered no end of responses that such problems are normally caused by the back-end, not radiusd, but our backend (OpenLDAP) responds to an identical query as that sent by radius in approximately 6ms (7ms when it's slow), yet radiusd is still not responding after 30 seconds. We have thousands of users trying to use our service simultaneously, through hundreds of wireless access points. I would be willing to accept that the configuration I'm using (setting Auth-Type in users) causes radiusd to perform poorly, but that this isn't radiusd's "fault", since it's an un-advised configuration, but I just don't see that the problem we're seeing there is because the backend is slow to respond. Regardless of the cause here, I decided to upgrade to FreeRADIUS-2.0.3, hoping that a) I could get that configured according in a recommended way to accomplish what I want, and b) that this would result in better performance than we're seeing now. Getting TTLS/PAP/OpenLDAP working correctly with FreeRADIUS-2.0.3 is the problem I'd like to solve from this message. [/ASIDE] Converting from a working, though technically incorrect configuration to a "correct" configuration hasn't been particularly easy, but I believe I've accomplished that, with very little change to the default configurations (unified context diffs of my configurations against the defaults are appended below my signature for completeness). What I have seems to pass tests that have been recommended as "get these working before moving on", but I can't seem to figure out how to get from here to being able to unleash my access points on this and have successful authentications. I see (from -X output) that the TTLS tunnel is successfully built (that seems to be several steps), a query against LDAP for authorization (and to retrieve the user's encypted password) succeeds, but when the request finally gets to the authentication, radiusd reports: ... rlm_ldap: performing user authorization for j_doe expand: %{Stripped-User-Name} -> expand: %{User-Name} -> j_doe expand: (&(cn=%{%{Stripped-User-Name}:-%{User-Name}})(search filter trimmed for brevity)) -> (&(cn=j_doe)(search filter trimmed for brevity)) expand: ou=people,dc=concordia,dc=ca -> ou=people,dc=concordia,dc=ca rlm_ldap: ldap_get_conn: Checking Id: 0 rlm_ldap: ldap_get_conn: Got Id: 0 rlm_ldap: performing search in ou=people,dc=concordia,dc=ca, with filter (&(cn=j_doe)(search filter trimmed for brevity)) rlm_ldap: Added User-Password = {SSHA}*SANITIZED*e2E52K+sO/SC+wvE*SANITIZED*== in check items rlm_ldap: looking for check items in directory... rlm_ldap: looking for reply items in directory... rlm_ldap: user j_doe authorized to use remote access rlm_ldap: ldap_release_conn: Release Id: 0 ++[ldap] returns ok ++[expiration] returns noop ++[logintime] returns noop ++[pap] returns noop WARNING: You set Proxy-To-Realm = LOCAL, but it is a LOCAL realm! Cancelling invalid proxy request. !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! !!! Replacing User-Password in config items with Cleartext-Password. !!! !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! !!! Please update your configuration so that the "known good" !!! !!! clear text password is in Cleartext-Password, and not in User-Password. !!! !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! auth: type Local auth: user supplied User-Password does NOT match local User-Password auth: Failed to validate the user. Login incorrect: [j_doe/*SANITIZED*] (from client wireless-mcconnell port 0) TTLS: Got tunneled Access-Reject rlm_eap: Handler failed in EAP/ttls rlm_eap: RT Modif EAP-Type = 0 EAP-LENGTH = 0 rlm_eap: Failed in EAP select ++[eap] returns invalid auth: Failed to validate the user. Login incorrect: [j_doe/<via Auth-Type = EAP>] (from client wireless-mcconnell port 5800234 cli 0019.d290.6e22) Found Post-Auth-Type Reject +- entering group REJECT expand: %{User-Name} -> j_doe attr_filter: Matched entry DEFAULT at line 11 ++[attr_filter.access_reject] returns updated Delaying reject of request 8 for 1 seconds Going to the next request Waking up in 0.9 seconds. ... Now, of the above, beside the fact that the authentication failed when I believe it should have succeeded, I'm concerned about two items. First: WARNING: You set Proxy-To-Realm = LOCAL, but it is a LOCAL realm! Cancelling invalid proxy request. Is this caused by the following in raddb/sites-*/inner-tunnel? # If you want the inner tunnel request to be proxied, delete # the next few lines. # update control { Proxy-To-Realm := LOCAL } Do I worry about it, or just accept that radiusd cancels the request? Second: !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! !!! Replacing User-Password in config items with Cleartext-Password. !!! !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! !!! Please update your configuration so that the "known good" !!! !!! clear text password is in Cleartext-Password, and not in User-Password. !!! !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! The text "User-Password" appears in exactly the following places in my raddb directory (not counting comment lines): ./attrs.pre-proxy: User-Password =* ANY, ./sql/mysql/dialup.conf: '%{%{User-Password}:-%{Chap-Password}}', \ ./sql/postgresql/dialup.conf: VALUES ('%{User-Name}', '%{%{User-Password}:-Chap-Password}', '%{reply:Packet-Type}', NOW())" These files are as shipped with FreeRADIUS-2.0.3. I'm trying to get this done with minimal change to the default configuration, since it appears that's what is expected. Which of the above needs to change? (attrs.pre-proxy?) The above issues of course still don't address what I see as the real problem: Login incorrect: [j_doe/*SANITIZED*] ... Somebody please tell me where I should be looking to make this work correctly. I can run the new server on an alternate port for the preliminary tests, such as using radtest against a user in LDAP (success), and radeapclient against a user in the users file (success using md5 as the default_eap_type, but not ttls), but I can't seem to get a successful test (using ttls; the passwords in LDAP aren't plain-text so md5 won't work for testing that) with radeapclient against a user in LDAP, or successful authentication when running in place of our current in-production RADIUS server. radtest against user in LDAP: radtest j_doe '*SANITIZED*' localhost:1814 1 testing123 User-Name = "syl" User-Password = "*SANITIZED*" NAS-IP-Address = 192.168.7.47 NAS-Port = 1 Older versions of radtest would report receiving "Access-Accept", while this one silently exists. However, radiusd in this case says: Ready to process requests. User-Name = "j_doe" User-Password = "*SANITIZED*" NAS-IP-Address = 192.168.7.47 NAS-Port = 1 +- entering group authorize ++[preprocess] returns ok ++[chap] returns noop ++[mschap] returns noop rlm_realm: No '@' in User-Name = "j_doe", looking up realm NULL rlm_realm: No such realm "NULL" ++[suffix] returns noop rlm_eap: No EAP-Message, not doing EAP ++[eap] returns noop ++[unix] returns notfound ++[files] returns noop rlm_ldap: - authorize rlm_ldap: performing user authorization for j_doe expand: %{Stripped-User-Name} -> expand: %{User-Name} -> j_doe expand: (&(cn=%{%{Stripped-User-Name}:-%{User-Name}})(search filter trimmed for brevity)) -> (&(cn=j_doe)(search filter trimmed for brevity)) expand: ou=people,dc=concordia,dc=ca -> ou=people,dc=concordia,dc=ca rlm_ldap: ldap_get_conn: Checking Id: 0 rlm_ldap: ldap_get_conn: Got Id: 0 rlm_ldap: attempting LDAP reconnection rlm_ldap: (re)connect to localhost boris:389, authentication 0 rlm_ldap: bind as cn=iits_neg,ou=AdminRoles,dc=concordia,dc=ca/*SANITIZED* to localhost boris:389 rlm_ldap: waiting for bind result ... rlm_ldap: Bind was successful rlm_ldap: performing search in ou=people,dc=concordia,dc=ca, with filter (&(cn=j_doe)(search filter trimmed for brevity)) rlm_ldap: Added User-Password = {SSHA}*SANITIZED*QDmffXBQkU42Wt9x*SANITIZED*== in check items rlm_ldap: looking for check items in directory... rlm_ldap: looking for reply items in directory... rlm_ldap: user j_doe authorized to use remote access rlm_ldap: ldap_release_conn: Release Id: 0 ++[ldap] returns ok ++[expiration] returns noop ++[logintime] returns noop ++[pap] returns updated rad_check_password: Found Auth-Type auth: type "PAP" +- entering group PAP rlm_pap: login attempt with password "*SANITIZED*" rlm_pap: Using SSHA encryption. rlm_pap: Normalizing SSHA1-Password from base64 encoding rlm_pap: User authenticated successfully ++[pap] returns ok Login OK: [j_doe/*SANITIZED*] (from client localhost port 1) Finished request 0. Going to the next request Ok, good ... radeapclient against a user listed in the users file still performs the ldap query for authorization (I actually don't want that; I'd like the users file to over-ride the LDAP listing, if an entry is matched in the users file), but then seems to stop short of setting up the TTLS tunnel and performing any authentication: radeapclient says: +++> About to send encoded packet: User-Name = "j_doe" Cleartext-Password = "*SANITIZED*" NAS-IP-Address = 192.168.198.20 NAS-Port-Type = Wireless-802.11 EAP-Code = Response EAP-Id = 210 EAP-Type-Identity = "j_doe" Message-Authenticator = 0x00 NAS-Port = 0 <+++ EAP decoded packet: Service-Type = Dialout-Framed-User EAP-Message = 0x01d300061520 Message-Authenticator = 0x796172e3b17c8b07c0409d2a811f0996 State = 0x99802cfd9953395efbafe88eb97f8c71 EAP-Id = 211 EAP-Code = Request EAP-Type-LEAP = 0x20 ^^^^ ???? I don't want LEAP! Where did it get this from? Radiusd says: rlm_ldap: performing search in ou=people,dc=concordia,dc=ca, with filter (&(cn=syl)(search filter trimmed for brevity)) rlm_ldap: Added User-Password = {SSHA}*SANITIZED*QDmffXBQkU42Wt9x*SANITIZED*== in check items rlm_ldap: looking for check items in directory... rlm_ldap: looking for reply items in directory... rlm_ldap: user syl authorized to use remote access rlm_ldap: ldap_release_conn: Release Id: 0 ++[ldap] returns ok ++[expiration] returns noop ++[logintime] returns noop rlm_pap: Found existing Auth-Type, not changing it. ++[pap] returns noop rad_check_password: Found Auth-Type EAP auth: type "EAP" +- entering group authenticate rlm_eap: EAP Identity rlm_eap: processing type tls rlm_eap_tls: Initiate rlm_eap_tls: Start returned 1 rlm_eap: RT Modif EAP-Type = 21 EAP-LENGTH = 1 ++[eap] returns handled Service-Type = Dialout-Framed-User EAP-Message = 0x01d300061520 Message-Authenticator = 0x00000000000000000000000000000000 State = 0x99802cfd9953395efbafe88eb97f8c71 Finished request 2. Going to the next request Waking up in 4.9 seconds. Cleaning up request 2 ID 243 with timestamp +465 Ready to process requests. I'm certainly prepared to be told that I'm doing it wrong, but in that case, I'd sure like to know WHAT I'm doing wrong, because I believe I've followed documented instructions completely, and haven't strayed any further than necessary from the default configuration as shipped with FreeRADIUS-2.0.3. Can someone please tell me where I should be looking? As promised, the unified context diff of my configuration against the default is appended below my signature. -- ---------------------------------------------------------------------- Sylvain Robitaille syl@alcor.concordia.ca Systems and Network analyst Concordia University Instructional & Information Technology Montreal, Quebec, Canada ---------------------------------------------------------------------- diff -ur raddb/clients.conf ../root-freeradius-2.0.3/etc/raddb/clients.conf --- raddb/clients.conf 2008-02-13 04:41:14.000000000 -0500 +++ ../root-freeradius-2.0.3/etc/raddb/clients.conf 2008-03-28 11:11:49.000000000 -0500 @@ -227,3 +227,96 @@ # secret = testing123 # } #} + +client hostname.concordia.ca { + secret = *SANITIZED* + shortname = LOCAL/LOCALTEST +} ### more entries in the same format, for other RADIUS clients ### diff -ur raddb/eap.conf ../root-freeradius-2.0.3/etc/raddb/eap.conf --- raddb/eap.conf 2008-02-26 04:32:29.000000000 -0500 +++ ../root-freeradius-2.0.3/etc/raddb/eap.conf 2008-03-28 12:15:53.000000000 -0500 @@ -27,7 +27,7 @@ # then that EAP type takes precedence over the # default type configured here. # - default_eap_type = md5 + default_eap_type = ttls # A list is maintained to correlate EAP-Response # packets with EAP-Request packets. After a @@ -145,7 +145,7 @@ cadir = ${confdir}/certs private_key_password = whatever - private_key_file = ${certdir}/server.pem + private_key_file = /public/apache/ssl/netnames-1_private.pem # If Private key & Certificate are located in # the same file, then private_key_file & @@ -157,7 +157,7 @@ # only the server certificate, but ALSO all # of the CA certificates used to sign the # server certificate. - certificate_file = ${certdir}/server.pem + certificate_file = /public/apache/ssl/netnames-1.pem # Trusted Root CA list # @@ -174,7 +174,7 @@ # not use client certificates, and you do not want # to permit EAP-TLS authentication, then delete # this configuration item. - CA_file = ${cadir}/ca.pem + CA_file = /public/apache/ssl/cacert.pem # # For DH cipher suites to work, you have to --- raddb/radiusd.conf 2008-03-27 12:42:15.000000000 -0500 +++ ../root-freeradius-2.0.3/etc/raddb/radiusd.conf 2008-03-28 13:27:03.000000000 -0500 @@ -56,13 +56,13 @@ sysconfdir = ${prefix}/etc localstatedir = ${prefix}/var sbindir = /local/pkg/freeradius/root-freeradius-2.0.3/bin -logdir = ${localstatedir}/log/radius +logdir = ${localstatedir}/log raddbdir = ${sysconfdir}/raddb radacctdir = ${logdir}/radacct # Location of config and logfiles. confdir = ${raddbdir} -run_dir = ${localstatedir}/run/radiusd +run_dir = ${localstatedir}/run # Should likely be ${localstatedir}/lib/radiusd db_dir = $(raddbdir) @@ -134,8 +134,8 @@ # that the debugging mode server is running as a user that can read the # shadow info, and the user listed below can not. # -#user = nobody -#group = nobody +user = nul-rad +group = nul-rad # max_request_time: The maximum time (in seconds) to handle a request. # @@ -191,7 +191,7 @@ # # Useful range of values: 256 to infinity # -max_requests = 1024 +max_requests = 262144 # listen: Make the server listen on a particular IP address, and send # replies out from that address. This directive is most useful for @@ -239,7 +239,8 @@ # Allowed values are: # integer port number (1812) # 0 means "use /etc/services for the proper port" - port = 0 + #port = 0 + port = 1814 # Some systems support binding to an interface, in addition # to the IP address. This feature isn't strictly necessary, @@ -274,7 +275,8 @@ listen { ipaddr = * # ipv6addr = :: - port = 0 + #port = 0 + port = 1815 type = acct # interface = eth0 # clients = per_socket_clients @@ -361,7 +363,7 @@ # # allowed values: {no, yes} # - auth = no + auth = yes # Log passwords with the authentication requests. # auth_badpass - logs password if it's rejected @@ -592,7 +594,7 @@ # with the correct value. It will also automatically handle # Base-64 encoded data, hex strings, and binary data. pap { - auto_header = no + auto_header = yes } # CHAP module @@ -737,12 +739,14 @@ # # Note that this needs to match the name in the LDAP # server certificate, if you're using ldaps. - server = "ldap.your.domain" - #identity = "cn=admin,o=My Org,c=UA" - #password = mypass - basedn = "o=My Org,c=UA" - filter = "(uid=%{Stripped-User-Name:-%{User-Name}})" - #base_filter = "(objectclass=radiusprofile)" + server = "localhost another_host" + identity = "cn=iits_neg,ou=AdminRoles,dc=concordia,dc=ca" + password = "*SANITIZED*" + basedn = "ou=people,dc=concordia,dc=ca" + #filter = "(cn=%{%{Stripped-User-Name}:-%{User-Name}})" + filter = "(&(cn=%{%{Stripped-User-Name}:-%{User-Name}})(search filter trimmed for brevity))" + + base_filter = "(objectclass=ConcordiaPerson)" # How many connections to keep open to the LDAP server. # This saves time over opening a new LDAP socket for @@ -820,7 +825,8 @@ # Novell may require TLS encrypted sessions before returning # the user's password. # - # password_attribute = userPassword + password_attribute = userPassword + password_radius_attribute = "SSHA-Password" # Un-comment the following to disable Novell # eDirectory account policy check and intruder diff -ur raddb/sites-available/default ../root-freeradius-2.0.3/etc/raddb/sites-available/default --- raddb/sites-available/default 2008-01-17 01:42:07.000000000 -0500 +++ ../root-freeradius-2.0.3/etc/raddb/sites-available/default 2008-03-28 10:14:12.000000000 -0500 @@ -132,7 +132,7 @@ # # The ldap module will set Auth-Type to LDAP if it has not # already been set -# ldap + ldap # # Enforce daily limits on time spent logged in. @@ -243,9 +243,9 @@ # Note that this means "check plain-text password against # the ldap database", which means that EAP won't work, # as it does not supply a plain-text password. -# Auth-Type LDAP { -# ldap -# } + Auth-Type LDAP { + ldap + } # # Allow EAP authentication. diff -ur raddb/sites-available/inner-tunnel ../root-freeradius-2.0.3/etc/raddb/sites-available/inner-tunnel --- raddb/sites-available/inner-tunnel 2008-02-26 04:32:29.000000000 -0500 +++ ../root-freeradius-2.0.3/etc/raddb/sites-available/inner-tunnel 2008-03-28 11:05:55.000000000 -0500 @@ -113,7 +113,7 @@ # # The ldap module will set Auth-Type to LDAP if it has not # already been set -# ldap + ldap # # Enforce daily limits on time spent logged in. @@ -201,9 +201,9 @@ # Note that this means "check plain-text password against # the ldap database", which means that EAP won't work, # as it does not supply a plain-text password. -# Auth-Type LDAP { -# ldap -# } + Auth-Type LDAP { + ldap + } # # Allow EAP authentication. diff -ur raddb/sites-enabled/default ../root-freeradius-2.0.3/etc/raddb/sites-enabled/default --- raddb/sites-enabled/default 2008-01-17 01:42:07.000000000 -0500 +++ ../root-freeradius-2.0.3/etc/raddb/sites-enabled/default 2008-03-28 10:14:12.000000000 -0500 @@ -132,7 +132,7 @@ # # The ldap module will set Auth-Type to LDAP if it has not # already been set -# ldap + ldap # # Enforce daily limits on time spent logged in. @@ -243,9 +243,9 @@ # Note that this means "check plain-text password against # the ldap database", which means that EAP won't work, # as it does not supply a plain-text password. -# Auth-Type LDAP { -# ldap -# } + Auth-Type LDAP { + ldap + } # # Allow EAP authentication. diff -ur raddb/users ../root-freeradius-2.0.3/etc/raddb/users --- raddb/users 2007-10-23 09:41:23.000000000 -0400 +++ ../root-freeradius-2.0.3/etc/raddb/users 2008-03-28 12:04:13.000000000 -0500 @@ -201,3 +201,343 @@ # Service-Type = Administrative-User # On no match, the user is denied access. + +# Wireless WDS: +username1 Auth-Type := EAP, Cleartext-Password := "*SANITIZED*" + Service-Type = Outbound-User + +# 2008/03/12 Sylvain Robitaille: for testing: +j_doe Cleartext-Password := "*SANITIZED*" + Service-Type = Outbound-User + #### Lots more in the same format, plus some of this type: + +# 2008/03/19 Sylvain Robitaille: copyright violation +blocked_user Calling-Station-ID == "0019.7e70.cdf9", Auth-Type := Reject + Reply-Message = "This system is blocked from our network ...." + +# Wireless (expect to need to list each access point) +DEFAULT NAS-Port-Type == Wireless-802.11 + Service-Type = Outbound-User +# Autz-Type := wireless +# Autz-Type := wireless, +# Fall-Through = Yes +# +#DEFAULT NAS-Port-Type == Wireless-802.11, EAP-Message !* "Matches if not EAP" +# Auth-Type := wireless + +#DEFAULT EAP-Type == EAP-TTLS, Proxy-To-Realm := LOCAL + +# On no match, the user is denied access.
I tried to compile freeradius-1.1.7 and freeradius-server-2.0.3, but encountered the following error. Could someone help? Kevin SZ [szhang@www ~]$ more /etc/redhat-release Red Hat Enterprise Linux ES release 4 (Nahant Update 4) [szhang@www ~]$ ient.lo libeap/libeap.la -lnsl -lresolv -lpthread -lcrypto -lssl -lcrypto gcc -o .libs/radeapclient .libs/radeapclient.o libeap/.libs/libeap.so /home/szhang/freeradius-1.1.7/src/lib/.libs/libradius.so -lcrypt -lnsl -lresolv -lpthread -lssl -lcrypto libeap/.libs/libeap.so: undefined reference to `EVP_MD_size' collect2: ld returned 1 exit status gmake[6]: *** [radeapclient] Error 1 gmake[6]: Leaving directory `/home/szhang/freeradius-1.1.7/src/modules/rlm_eap' gmake[5]: *** [common] Error 2 gmake[5]: Leaving directory `/home/szhang/freeradius-1.1.7/src/modules' gmake[4]: *** [all] Error 2 gmake[4]: Leaving directory `/home/szhang/freeradius-1.1.7/src/modules' gmake[3]: *** [common] Error 2 gmake[3]: Leaving directory `/home/szhang/freeradius-1.1.7/src' gmake[2]: *** [all] Error 2 gmake[2]: Leaving directory `/home/szhang/freeradius-1.1.7/src' gmake[1]: *** [common] Error 2 gmake[1]: Leaving directory `/home/szhang/freeradius-1.1.7' make: *** [all] Error 2
Kevin Zhang wrote:
I tried to compile freeradius-1.1.7 and freeradius-server-2.0.3, but encountered the following error. Could someone help? ... ient.lo libeap/libeap.la -lnsl -lresolv -lpthread -lcrypto -lssl -lcrypto gcc -o .libs/radeapclient .libs/radeapclient.o libeap/.libs/libeap.so /home/szhang/freeradius-1.1.7/src/lib/.libs/libradius.so -lcrypt -lnsl -lresolv -lpthread -lssl -lcrypto libeap/.libs/libeap.so: undefined reference to `EVP_MD_size'
Your OpenSSL libraries don't have the right functions needed by FreeRADIUS. i.e. your OpenSSL libraries are probably very old. Alan DeKok.
rlm_ldap: Added User-Password = {SSHA}*SANITIZED*e2E52K+sO/SC+wvE*SANITIZED*== in check items
You have obviously ignored the warnings about storing User-Password attribute: !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! !!! Replacing User-Password in config items with Cleartext-Password. !!! !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! !!! Please update your configuration so that the "known good" !!! !!! clear text password is in Cleartext-Password, and not in User-Password. !!! !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! Should they be more obvious? So server translates User-Password to Cleartext-Password and the check fails since the password is encrypted. Configure ldap section to use SSHA-Password as password attribute instead. Ivan Kalik Kalik Informatika ISP
On Fri, 28 Mar 2008, Ivan Kalik wrote:
You have obviously ignored the warnings about storing User-Password attribute:
No, I don't believe that I can be said to have ignored it at all. In fact, I'm under the impresseion that I made very clear in my earlier message that I'm not ignoring this warning. I may not be doing the right thing to deal correctly with what causes it, but that's another matter entirely, and why I am putting myself at the mercy of experts for help. I wrote:
The text "User-Password" appears in exactly the following places in my raddb directory (not counting comment lines):
./attrs.pre-proxy: User-Password =* ANY, ./sql/mysql/dialup.conf: '%{%{User-Password}:-%{Chap-Password}}', \ ./sql/postgresql/dialup.conf: VALUES ('%{User-Name}', '%{%{User-Password}:-Chap-Password}', '%{reply:Packet-Type}', NOW())"
These files are as shipped with FreeRADIUS-2.0.3. I'm trying to get this done with minimal change to the default configuration, since it appears that's what is expected. Which of the above needs to change? (attrs.pre-proxy?)
... So server translates User-Password to Cleartext-Password and the check fails since the password is encrypted.
Understood, yes.
Configure ldap section to use SSHA-Password as password attribute instead.
That's what I believed I HAD done with the following, from the diff of my radiusd.conf file against the default radiusd.conf that ships with 2.0.3, orignally included after the signature in my first message:
@@ -820,7 +825,8 @@ # Novell may require TLS encrypted sessions before returning # the user's password. # - # password_attribute = userPassword + password_attribute = userPassword + password_radius_attribute = "SSHA-Password"
If the above is not the correct way to accomplish what I am trying to do, I would be very grateful if someone would point me in the right direction to find what is the correct way. The radtest test against a user in the LDAP data succeeds. How do I get from here to having successful authentication through TTLS against the same LDAP data, without the above warning?
radtest j_doe '*SANITIZED*' localhost:1814 1 testing123 User-Name = "j_doe" User-Password = "*SANITIZED*" NAS-IP-Address = 192.168.7.47 NAS-Port = 1
Older versions of radtest would report receiving "Access-Accept", while this one silently exists. However, radiusd in this case says:
Ready to process requests. User-Name = "j_doe" User-Password = "*SANITIZED*" NAS-IP-Address = 192.168.7.47 NAS-Port = 1 +- entering group authorize ++[preprocess] returns ok ++[chap] returns noop ++[mschap] returns noop rlm_realm: No '@' in User-Name = "j_doe", looking up realm NULL rlm_realm: No such realm "NULL" ++[suffix] returns noop rlm_eap: No EAP-Message, not doing EAP ++[eap] returns noop ++[unix] returns notfound ++[files] returns noop rlm_ldap: - authorize rlm_ldap: performing user authorization for j_doe expand: %{Stripped-User-Name} -> expand: %{User-Name} -> j_doe expand: (&(cn=%{%{Stripped-User-Name}:-%{User-Name}})(search filter trimmed for brevity)) -> (&(cn=j_doe)(search filter trimmed for brevity)) expand: ou=people,dc=concordia,dc=ca -> ou=people,dc=concordia,dc=ca rlm_ldap: ldap_get_conn: Checking Id: 0 rlm_ldap: ldap_get_conn: Got Id: 0 rlm_ldap: attempting LDAP reconnection rlm_ldap: (re)connect to localhost boris:389, authentication 0 rlm_ldap: bind as cn=iits_neg,ou=AdminRoles,dc=concordia,dc=ca/*SANITIZED* to localhost boris:389 rlm_ldap: waiting for bind result ... rlm_ldap: Bind was successful rlm_ldap: performing search in ou=people,dc=concordia,dc=ca, with filter (&(cn=j_doe)(search filter trimmed for brevity)) rlm_ldap: Added User-Password = {SSHA}*SANITIZED*QDmffXBQkU42Wt9x*SANITIZED*== in check items rlm_ldap: looking for check items in directory... rlm_ldap: looking for reply items in directory... rlm_ldap: user j_doe authorized to use remote access rlm_ldap: ldap_release_conn: Release Id: 0 ++[ldap] returns ok ++[expiration] returns noop ++[logintime] returns noop ++[pap] returns updated rad_check_password: Found Auth-Type auth: type "PAP" +- entering group PAP rlm_pap: login attempt with password "*SANITIZED*" rlm_pap: Using SSHA encryption. rlm_pap: Normalizing SSHA1-Password from base64 encoding rlm_pap: User authenticated successfully ++[pap] returns ok Login OK: [j_doe/*SANITIZED*] (from client localhost port 1) Finished request 0. Going to the next request
Thanks for following up, and for any additional help ... -- ---------------------------------------------------------------------- Sylvain Robitaille syl@alcor.concordia.ca Systems and Network analyst Concordia University Instructional & Information Technology Montreal, Quebec, Canada ----------------------------------------------------------------------
... So server translates User-Password to Cleartext-Password and the check fails since the password is encrypted.
Understood, yes.
So at the moment the server is reading your password hash out of the LDAP directory and treating it as a plaintext password string. You can test this by providing the password hash as your password during PAP authentication. I Noticed from that sample hash, your passwords have the correct {SSHA} prefix, this means you should be able to use ldap { auto_header = yes } And the server will automatically write the hash to the correct internal attribute. Least thats how it works on ours, and were using an OpenLDAP setup similar to your.
Configure ldap section to use SSHA-Password as password attribute instead.
That's what I believed I HAD done with the following, from the diff of my radiusd.conf file against the default radiusd.conf that ships with 2.0.3, orignally included after the signature in my first message:
@@ -820,7 +825,8 @@ # Novell may require TLS encrypted sessions before returning # the user's password. # - # password_attribute = userPassword + password_attribute = userPassword + password_radius_attribute = "SSHA-Password"
I have no idea what password_radius_attribute is ?? Is that a legacy configuration item ? If your password is indeed stored in the LDAP 'userPassword' attribute which is the default then: # Set password_attribute = nspmPassword to get the # user's password from a Novell eDirectory # backend. This will work ONLY IF FreeRADIUS has been # built with the --with-edir configure option. # password_attribute = userPassword should suffice. The other way you can do this is by using the LDAP module as an authentication module. When used in the authentication section it'll attempt to bind to the LDAP server using the users UID and Password. I wouldn't recommend it in your case though, as binds are comparatively slow, and it'll only work with PAP.
If the above is not the correct way to accomplish what I am trying to do, I would be very grateful if someone would point me in the right direction to find what is the correct way.
The radtest test against a user in the LDAP data succeeds. How do I get from here to having successful authentication through TTLS against the same LDAP data, without the above warning?
radtest j_doe '*SANITIZED*' localhost:1814 1 testing123 User-Name = "j_doe" User-Password = "*SANITIZED*" NAS-IP-Address = 192.168.7.47 NAS-Port = 1
Older versions of radtest would report receiving "Access-Accept", while this one silently exists. However, radiusd in this case says:
Ready to process requests. User-Name = "j_doe" User-Password = "*SANITIZED*" NAS-IP-Address = 192.168.7.47 NAS-Port = 1 +- entering group authorize ++[preprocess] returns ok ++[chap] returns noop ++[mschap] returns noop rlm_realm: No '@' in User-Name = "j_doe", looking up realm NULL rlm_realm: No such realm "NULL" ++[suffix] returns noop rlm_eap: No EAP-Message, not doing EAP ++[eap] returns noop ++[unix] returns notfound ++[files] returns noop rlm_ldap: - authorize rlm_ldap: performing user authorization for j_doe expand: %{Stripped-User-Name} -> expand: %{User-Name} -> j_doe expand: (&(cn=%{%{Stripped-User-Name}:-%{User-Name}})(search filter trimmed for brevity)) -> (&(cn=j_doe)(search filter trimmed for brevity)) expand: ou=people,dc=concordia,dc=ca -> ou=people,dc=concordia,dc=ca rlm_ldap: ldap_get_conn: Checking Id: 0 rlm_ldap: ldap_get_conn: Got Id: 0 rlm_ldap: attempting LDAP reconnection rlm_ldap: (re)connect to localhost boris:389, authentication 0 rlm_ldap: bind as cn=iits_neg,ou=AdminRoles,dc=concordia,dc=ca/*SANITIZED* to localhost boris:389 rlm_ldap: waiting for bind result ... rlm_ldap: Bind was successful rlm_ldap: performing search in ou=people,dc=concordia,dc=ca, with filter (&(cn=j_doe)(search filter trimmed for brevity)) rlm_ldap: Added User-Password = {SSHA}*SANITIZED*QDmffXBQkU42Wt9x*SANITIZED*== in check items rlm_ldap: looking for check items in directory... rlm_ldap: looking for reply items in directory... rlm_ldap: user j_doe authorized to use remote access rlm_ldap: ldap_release_conn: Release Id: 0 ++[ldap] returns ok ++[expiration] returns noop ++[logintime] returns noop ++[pap] returns updated rad_check_password: Found Auth-Type auth: type "PAP" +- entering group PAP rlm_pap: login attempt with password "*SANITIZED*" rlm_pap: Using SSHA encryption. rlm_pap: Normalizing SSHA1-Password from base64 encoding rlm_pap: User authenticated successfully ++[pap] returns ok Login OK: [j_doe/*SANITIZED*] (from client localhost port 1) Finished request 0. Going to the next request
Thanks for following up, and for any additional help ...
Sylvain Robitaille wrote:
In fact, I've been trying to get this working for years with older versions of FreeRADIUS, and have succeeded only with FreeRADIUS<=1.1.6, using configurations that readers of this list are repeatedly told not to use (such as setting Auth-Type in the users file).
It really depends on what you're doing. The recommendations against setting Auth-Type are there because almost everyone gets it wrong. There *are* situations where setting it is the right thing to do. But it's almost always wrong...
[ASIDE] With the older versions of FreeRADIUS we're having performance problems with the authentication. Research on this list has uncovered no end of responses that such problems are normally caused by the back-end, not radiusd, but our backend (OpenLDAP) responds to an identical query as that sent by radius in approximately 6ms (7ms when it's slow), yet radiusd is still not responding after 30 seconds. We have thousands of users trying to use our service simultaneously, through hundreds of wireless access points.
Run it in debugging mode to see what the problem is. There isn't really a whole lot that can go wrong with the server. If it's waiting more than 30 seconds to respond, then the likelihood is that it's doing DNS lookups, and DNS is broken.
What I have seems to pass tests that have been recommended as "get these working before moving on", but I can't seem to figure out how to get from here to being able to unleash my access points on this and have successful authentications. I see (from -X output) that the TTLS tunnel is successfully built (that seems to be several steps), a query against LDAP for authorization (and to retrieve the user's encypted password) succeeds, but when the request finally gets to the authentication, radiusd reports:
You may need to install "sites-available/inner-tunnel". There's a symlink from 'sites-enables/inner-tunnel" to "sites-availabe/inner-tunnel"... which isn't installed in 2.0.3, due to a bug in the Makefile.
WARNING: You set Proxy-To-Realm = LOCAL, but it is a LOCAL realm! Cancelling invalid proxy request.
Is this caused by the following in raddb/sites-*/inner-tunnel?
Yes. The message is there to warn people about common misconfigurations. Don't worry about it.
The text "User-Password" appears in exactly the following places in my raddb directory (not counting comment lines):
That's not the issue. The issue is that the rlm_ldap module is reading the "userPassword" ldap field, and creating a User-Password attribute. It could really be fixed.
The above issues of course still don't address what I see as the real problem:
Login incorrect: [j_doe/*SANITIZED*] ...
Somebody please tell me where I should be looking to make this work correctly.
It doesn't work because the PAP module isn't doing anything. The PAP module *should* be taking the crypt'd password, and doing something useful with it. (See "man rlm_pap")
I can run the new server on an alternate port for the preliminary tests, such as using radtest against a user in LDAP (success),
Yes... because it's behaving differently. See the debug output for what differences there are.
and radeapclient against a user in the users file (success using md5 as the default_eap_type, but not ttls),
Because you're putting a clear-text password in the "users" file, not a SSHA encrypted blob like you're getting from LDAP. Compare apples to apples, not apples to oranges. If you put the *same* SSHA blob you get from ldap into the "users" file, then it would likely behave differently... Alan DeKok.
Somebody please tell me where I should be looking to make this work correctly.
It doesn't work because the PAP module isn't doing anything. The PAP module *should* be taking the crypt'd password, and doing something useful with it. (See "man rlm_pap")
I don't have a copy of 2.0.3 handy, but this looks like a bug to me at ~line 383 of rlm_pap.c: case PW_PROXY_TO_REALM: { REALM *realm = realm_find(vp->vp_strvalue); if (realm && !realm->auth_pool) { return RLM_MODULE_NOOP; } break; } Shouldn't that be: if (realm && realm->auth_pool) i.e. if the realm is known/real *and* has servers i.e. isn't local, then no-op?
Phil Mayers wrote:
I don't have a copy of 2.0.3 handy, but this looks like a bug to me at ~line 383 of rlm_pap.c:
Yes. That explains some of the unnecessary debug messages I've been seeing (proxied requests still get complaints from rlm_pap). I've committed a fix, thanks. Alan DeKok.
First things first - can I clarify that your goal is to have users, using EAP TTLS/PAP, authenticating against LDAP entries. The LDAP entries are of the form: dn: cn=j_doe,ou=... cn: j_doe userPassword: {SSHA}bhjqewhtqothethwe== Correct? Looking at the first LDAP debug you show, we see:
...
...you've trimmed the debug lines above this - not helpful, but I think I can see the problem:
rlm_ldap: performing user authorization for j_doe expand: %{Stripped-User-Name} -> expand: %{User-Name} -> j_doe expand: (&(cn=%{%{Stripped-User-Name}:-%{User-Name}})(search filter trimmed for brevity)) -> (&(cn=j_doe)(search filter trimmed for brevity)) expand: ou=people,dc=concordia,dc=ca -> ou=people,dc=concordia,dc=ca rlm_ldap: ldap_get_conn: Checking Id: 0 rlm_ldap: ldap_get_conn: Got Id: 0 rlm_ldap: performing search in ou=people,dc=concordia,dc=ca, with filter (&(cn=j_doe)(search filter trimmed for brevity)) rlm_ldap: Added User-Password = {SSHA}*SANITIZED*e2E52K+sO/SC+wvE*SANITIZED*== in check items rlm_ldap: looking for check items in directory... rlm_ldap: looking for reply items in directory... rlm_ldap: user j_doe authorized to use remote access rlm_ldap: ldap_release_conn: Release Id: 0 ++[ldap] returns ok ++[expiration] returns noop ++[logintime] returns noop ++[pap] returns noop
Notice that "pap" does a no-op here. As far as I can see, rlm_pap should update the request, and from the source the only times it will no-op *SILENTLY* are: * if the config items contains Proxy-To-Realm AND the value of that attribute is a valid realm in proxy.conf AND the realm has no servers (and I think that last boolean is a bug/inverted) * or, there's no password attribute found AND: * the request is being proxied * or, the request is EAP-PEAP or EAP-TTLS or EAP-TLS do some buggy stuff... * or it's an Access-Challenge Basically, I think there is a logic check inverted in rlm_pap that means it's doing a no-op when it shouldn't
WARNING: You set Proxy-To-Realm = LOCAL, but it is a LOCAL realm! Cancelling invalid proxy request.
...try removing the "Proxy-To-Realm" stuff - it's not needed in your case.
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
!!! Replacing User-Password in config items with Cleartext-Password. !!! !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
!!! Please update your configuration so that the "known good" !!! !!! clear text password is in Cleartext-Password, and not in User-Password. !!! !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
These warnings appear because the Auth-Type defaults to Local
auth: type Local auth: user supplied User-Password does NOT match local User-Password auth: Failed to validate the user.
...and the "Local" auth type is handled internally by the server core, and doesn't do the magic required to recognize the {SSHA} in the User-Password config item.
Login incorrect: [j_doe/*SANITIZED*] (from client wireless-mcconnell
...hence login fails. Much later in your email, you list the output of a radtest against LDAP. Because that isn't EAP-TTLS, there's no tunnel and thus the rlm_pap bug isn't triggered.
radeapclient against a user listed in the users file still performs the ldap query for authorization (I actually don't want that; I'd like the users file to over-ride the LDAP listing, if an entry is matched in the users file),
In that case, you will need to configure the server appropriately - in older versions of the server you'd do this: authorize { preprocess files Autz-Type LDAP { ldap } } ...and in users: j_doe Cleartext-Password := "foo" DEFAULT Calling-Station-Id == "0011.2233.4455", Auth-Type := Reject DEFAULT Autz-Type := LDAP ...or something like: authorize { preprocess redundant { files ldap } } ...in 2.x versions of the server you might want to use "unlang"
but then seems to stop short of setting up the TTLS tunnel and performing any authentication:
radeapclient says:
In my opinion, radeapclient is not terribly useful. I would recommend compiling eapol_test from the "wpa_supplicant" package; it can do a full EAP TTLS/PAP request against a radius server.
Can someone please tell me where I should be looking? As promised, the unified context diff of my configuration against the default is appended below my signature.
As has been pointed out in another email, you have set: modules { ldap { ... password_radius_attribute = "SSHA-Password" } } "password_radius_attribute" is not a valid config item for the LDAP module; the ldap module will be ignoring it. You don't need it.
I appreciate all the replies so far. I'm responding to several at once here, in order of appearance in my mail spool ... On Sat, 29 Mar 2008, Arran Cudbard-Bell wrote:
I Noticed from that sample hash, your passwords have the correct {SSHA} prefix, this means you should be able to use
ldap { auto_header = yes
}
And the server will automatically write the hash to the correct internal attribute. ...
I will definitely give that a try on Monday morning. I wasn't aware that the ldap module also had an auto_header parameter. I have it set for the pap module already, but will try with the ldap module and report back.
I have no idea what password_radius_attribute is ?? Is that a legacy configuration item ?
I don't think so. I only learned about it this week, though that isn't to suggest that it wasn't around previously. I learned about this from reading doc/rlm_ldap that ships with freeradius-server-2.0.3. That file says the following about this parameter: # password_radius_attribute: Defined the RADIUS attribute where # the extracted user password will be stored to. Can be used to # set it to NT-Password or any other similar attribute instead of # the default # # default: User-Password # # password_radius_attribute = "NT-Password"
If your password is indeed stored in the LDAP 'userPassword' attribute which is the default then: ... password_attribute = userPassword should suffice.
Agreed, but I wasn't able to get even radtest working against users in LDAP with that. I came to understand that this was because in that case rlm_pap wasn't receiving the password in User-Password and therefore it was comparing the plaintext password from the authentication request with the encrypted password from the LDAP backend. Of course that wouldn't match.
The other way you can do this is by using the LDAP module as an authentication module. When used in the authentication section it'll attempt to bind to the LDAP server using the users UID and Password. I wouldn't recommend it in your case though, as binds are comparatively slow, and it'll only work with PAP.
That is what we have in place now, with FreeRADIUS-1.1.6, and which works, but indeed is giving us performance headaches. I wasn't aware that binds are slower than queries, though I suppose it makes sense that they would be, and I don't doubt that a different configuration would have it working better. On Sat, 29 Mar 2008, Alan DeKok wrote:
It really depends on what you're doing. The recommendations against setting Auth-Type are there because almost everyone gets it wrong. There *are* situations where setting it is the right thing to do. But it's almost always wrong...
I can accept that, and I'm not convinced that it's necessarily the "best" way to get what I want in our installation (after all, what I really want is the LDAP query to provide the *authorization*, and let the authentication be done by the PAP module). However, at the time I did it, it seemed to be the only thing I was able to do to get it working against LDAP data at all, after much research and trial and error. I din't feel I could argue very much with "it works". ;-)
[ASIDE] With the older versions of FreeRADIUS we're having performance problems with the authentication. ...
Run it in debugging mode to see what the problem is. ...
To be honest, my interest now is primarily in getting the setup I've been working on with 2.0.3 working correctly and replacing the old setup with that. I know I'm close and I feel that I'm aiming in a more technically "correct" direction, so it seems better to me to focus my efforts on that right now. It might still be interesting just to _know_ what's slowing the RADIUS server down, though.
There isn't really a whole lot that can go wrong with the server. If it's waiting more than 30 seconds to respond, then the likelihood is that it's doing DNS lookups, and DNS is broken.
Hrmmm... I have "hostname_lookups = no" on both my existing (1.1.6) installation and the new one I'm working on (2.0.3), but of course *some* DNS lookups would still be expected (I have multiple LDAP servers configured, by hostname, for example), and although I don't have any other evidence that there is anything at all wrong with our DNS resolvers, I have to admit that I hadn't even considered this possibility, and it obviously shouldn't be overlooked. I could rule it out (or work around it) by setting up a caching resolver on the system. I'll consider doing that if I'm no further ahead with 2.0.3 by the end of Monday.
You may need to install "sites-available/inner-tunnel".
I did. I spotted the hanging sym-link, and references to it in earlier discussion on this mailing list. Once I'd gotten that done, I thought I'd gotten it all in place, but I'm still stuck. :-(
WARNING: You set Proxy-To-Realm = LOCAL, but it is a LOCAL realm! Cancelling invalid proxy request.
Is this caused by the following in raddb/sites-*/inner-tunnel?
Yes. The message is there to warn people about common misconfigurations. Don't worry about it.
Thanks.
The text "User-Password" appears in exactly the following places in my raddb directory (not counting comment lines):
That's not the issue. The issue is that the rlm_ldap module is reading the "userPassword" ldap field, and creating a User-Password attribute. It could really be fixed.
By patching rlm_ldap, you mean, or by adjusting my configuration?
It doesn't work because the PAP module isn't doing anything. The PAP module *should* be taking the crypt'd password, and doing something useful with it. (See "man rlm_pap")
Agreed. I'm pretty sure that it was after reading "man rlm_pap" that I went on a search that led me to the password_radius_attribute parameter in my configuration for the ldap module (which I'm told in a later message quoted below is not recognized by rlm_ldap anyway). The exact sequence of what I read when is a little blurry by now, I have to admit.
Yes... because it's behaving differently. See the debug output for what differences there are.
Ok, but what I'm stuck on is *why* the differences are there. I don't doubt I've done something wrong, but I'm unable to figure out what it is that I've done wrong.
and radeapclient against a user in the users file (success using md5 as the default_eap_type, but not ttls),
Because you're putting a clear-text password in the "users" file, not a SSHA encrypted blob like you're getting from LDAP.
Yes.
Compare apples to apples, not apples to oranges. If you put the *same* SSHA blob you get from ldap into the "users" file, then it would likely behave differently...
Ok, and then I'll need to put the blob in a SSHA-Password attribute, correct? (I will try this on Monday, if I haven't found or gotten an answer to it already by then). In which case I'm left still trying to get the ldap module to do the same, which I thought I had done, but perhaps haven't done correctly? On Sat, 29 Mar 2008, Phil Mayers wrote:
I don't have a copy of 2.0.3 handy, but this looks like a bug to me at ~line 383 of rlm_pap.c:
case PW_PROXY_TO_REALM: { REALM *realm = realm_find(vp->vp_strvalue); if (realm && !realm->auth_pool) { return RLM_MODULE_NOOP; } break; }
I've compared the above (from 2.0.3) with the same section of code in rlm_pap.c from 1.1.6: 384 case PW_PROXY_TO_REALM: 385 { 386 REALM *realm = realm_find(vp->strvalue, 0); 387 if (realm && 388 (realm->ipaddr != htonl(INADDR_NONE))) { 389 return RLM_MODULE_NOOP; 390 } 391 break; 392 }
Shouldn't that be:
if (realm && realm->auth_pool)
i.e. if the realm is known/real *and* has servers i.e. isn't local, then no-op?
I would certainly be willing to act as a Guinea-Pig for this on Monday. What you're saying makes sense to me and I'd certainly like to see that the solution is this simple. If no one says outright that the above code (from 2.0.3) is correct as it is, I'll invert the condition on Monday morning and try some more. On Sat, 29 Mar 2008, Phil Mayers wrote:
First things first - can I clarify that your goal is to have users, using EAP TTLS/PAP, authenticating against LDAP entries. The LDAP entries are of the form:
dn: cn=j_doe,ou=... cn: j_doe userPassword: {SSHA}bhjqewhtqothethwe==
Correct?
Yes.
...you've trimmed the debug lines above this - not helpful, ...
Sorry. I didn't expect those lines would be helpful with identifying the source of the problem. They looked to me like "everything is normal up to here ..." I can repost that, if you think it would help.
but I think I can see the problem:
... ++[ldap] returns ok ++[expiration] returns noop ++[logintime] returns noop ++[pap] returns noop
Notice that "pap" does a no-op here. As far as I can see, rlm_pap should update the request, ...
Your point above. I'm nowhere near being a RADIUS expert (no way I could have *found* that myself), but at least I feel I'm following along ... :-)
WARNING: You set Proxy-To-Realm = LOCAL, but it is a LOCAL realm! Cancelling invalid proxy request.
...try removing the "Proxy-To-Realm" stuff - it's not needed in your case.
I can do that, but Alan's point above is that this message is harmless, and is not relevant to my problem. Either way is fine with me if I get the intended result, though certainly "cleaner" is "better".
Replacing User-Password in config items with Cleartext-Password. Please update your configuration so that the "known good" clear text password is in Cleartext-Password, and not in User-Password.
These warnings appear because the Auth-Type defaults to Local
because rlm_pap did a noop above?
auth: type Local auth: user supplied User-Password does NOT match local User-Password auth: Failed to validate the user.
...and the "Local" auth type is handled internally by the server core, and doesn't do the magic required to recognize the {SSHA} in the User-Password config item.
Right, that's rlm_pap's job.
Login incorrect: [j_doe/*SANITIZED*] (from client wireless-mcconnell
...hence login fails.
and my users complain. :-(
Much later in your email, you list the output of a radtest against LDAP. Because that isn't EAP-TTLS, there's no tunnel and thus the rlm_pap bug isn't triggered.
I think I'm still following ...
radeapclient against a user listed in the users file still performs the ldap query for authorization (I actually don't want that; I'd like the users file to over-ride the LDAP listing, if an entry is matched in the users file),
In that case, you will need to configure the server appropriately - in older versions of the server you'd do this:
authorize { preprocess files Autz-Type LDAP { ldap } }
Yes.
...and in users:
j_doe Cleartext-Password := "foo"
DEFAULT Calling-Station-Id == "0011.2233.4455", Auth-Type := Reject
DEFAULT Autz-Type := LDAP
Yes.
...or something like:
authorize { preprocess redundant { files ldap } }
I only learned about "redundant" this week. I expect that will be useful to me for listing multiple LDAP servers (with parallel copies of the data), but no, I don't have this.
...in 2.x versions of the server you might want to use "unlang"
I'll re-read that, but will worry about this matter only after I get the authentication working as I intend.
In my opinion, radeapclient is not terribly useful.
I would recommend compiling eapol_test from the "wpa_supplicant" package; it can do a full EAP TTLS/PAP request against a radius server.
Thanks. I'll set that up for testing.
As has been pointed out in another email, you have set:
modules { ldap { ... password_radius_attribute = "SSHA-Password" } }
yes.
"password_radius_attribute" is not a valid config item for the LDAP module; the ldap module will be ignoring it. You don't need it.
Ugh! See above for where I learned about that parameter in the first place (doc/rlm_ldap in the freeradius-server-2.0.3 source tree). Here I was under the impression that I was doing exactly as needed! :-( Indeed the string "password_radius_attribute" shows up _only_ in doc/rlm_ldap, and not in any source (or header) files. I should have thought to check for that in the first place ... To summarize, the main things I need to look at Monday are: - invert the PW_PROXY_TO_REALM test in rlm_pap.c, unless it's declared that the test is correct as it is. - confure "auto_header = yes" for the ldap module. - Consider adding a caching DNS resolver to the systems running RADIUS servers. - Test with an SSHA hash as the password in the users file, and understand exactly what attribute it needs to be in. Make sure that the ldap module is placing the users' passwords in that attribute. -- ---------------------------------------------------------------------- Sylvain Robitaille syl@alcor.concordia.ca Systems and Network analyst Concordia University Instructional & Information Technology Montreal, Quebec, Canada ----------------------------------------------------------------------
Sylvain Robitaille wrote: ...
ldap { auto_header = yes ... I will definitely give that a try on Monday morning. I wasn't aware that the ldap module also had an auto_header parameter. I have it set for the pap module already, but will try with the ldap module and report back.
I would very much prefer that the PAP module be used for the password mangling, rather than rlm_ldap. The code in the PAP module does more, and is more used than the similar code in rlm_ldap. I think that functionality will be removed from rlm_ldap.
have no idea what password_radius_attribute is ?? Is that a legacy configuration item ?
Yes.
I don't think so. I only learned about it this week, though that isn't to suggest that it wasn't around previously. I learned about this from reading doc/rlm_ldap that ships with freeradius-server-2.0.3. That file says the following about this parameter:
I've deleted that text from the documentation. The configuration item hasn't been in rlm_ldap for a long time.
Agreed, but I wasn't able to get even radtest working against users in LDAP with that. I came to understand that this was because in that case rlm_pap wasn't receiving the password in User-Password and therefore it was comparing the plaintext password from the authentication request with the encrypted password from the LDAP backend. Of course that wouldn't match.
You need to tell FreeRADIUS *how* you have encrypted the passwords. If there's a {ssha} header on the password, then the PAP module should figure it out.
It might still be interesting just to _know_ what's slowing the RADIUS server down, though.
30 second delays are almost always DNS.
There isn't really a whole lot that can go wrong with the server. If it's waiting more than 30 seconds to respond, then the likelihood is that it's doing DNS lookups, and DNS is broken.
Hrmmm... I have "hostname_lookups = no" on both my existing (1.1.6) installation and the new one I'm working on (2.0.3), but of course *some* DNS lookups would still be expected (I have multiple LDAP servers configured, by hostname, for example),
Yes. That configuration item controls IP address -> hostname lookups for printing. It has *no* effect on hostname -> IP mapping, such as looking up ldap servers by hostname.
and although I don't have any other evidence that there is anything at all wrong with our DNS resolvers, I have to admit that I hadn't even considered this possibility, and it obviously shouldn't be overlooked. I could rule it out (or work around it) by setting up a caching resolver on the system. I'll consider doing that if I'm no further ahead with 2.0.3 by the end of Monday.
Run the server in debugging mode. If there is a problem with DNS, you will see it *stop* for 30 seconds while it looks up a name.
That's not the issue. The issue is that the rlm_ldap module is reading the "userPassword" ldap field, and creating a User-Password attribute. It could really be fixed.
By patching rlm_ldap, you mean, or by adjusting my configuration?
Patching rlm_ldap, probably. The "userPassword" should be mapped to User-Password via ldap.attrmap, just like everything else.
Ok, but what I'm stuck on is *why* the differences are there. I don't doubt I've done something wrong, but I'm unable to figure out what it is that I've done wrong.
It may be the bug in rlm_pap. Grab a current CVS snapshot, and see if that works any better.
Ok, and then I'll need to put the blob in a SSHA-Password attribute, correct?
Yes. And it will likely work. But... the LDAP module is putting it into the User-Password attribute. So you might want to test that, too.
I only learned about "redundant" this week. I expect that will be useful to me for listing multiple LDAP servers (with parallel copies of the data), but no, I don't have this.
$ man unlang You probably want "redundant-load-balance". It's a bit of effort to type, but it results in a pretty robust system.
To summarize, the main things I need to look at Monday are:
- invert the PW_PROXY_TO_REALM test in rlm_pap.c, unless it's declared that the test is correct as it is.
Grab the updated code from CVS.
- confure "auto_header = yes" for the ldap module.
I really don't think that's necessary. If you're not proxying, then the PAP module *should* take care of fixing the password up.
- Consider adding a caching DNS resolver to the systems running RADIUS servers.
Yes.
- Test with an SSHA hash as the password in the users file, and understand exactly what attribute it needs to be in. Make sure that the ldap module is placing the users' passwords in that attribute.
Also, test with a User-Password := "{ssha}...". Check that the PAP module "fixes" it, and turns it into a SSHA-Password attribute. Alan DeKok.
On Sat, 29 Mar 2008, Alan DeKok wrote:
ldap { auto_header = yes ... I will definitely give that a try on Monday morning. ...
I would very much prefer that the PAP module be used for the password mangling, rather than rlm_ldap. The code in the PAP module does more, and is more used than the similar code in rlm_ldap. I think that functionality will be removed from rlm_ldap.
Ok, fair enough. What you're saying is if I've done everything else correctly (and using a freeradius-server version that has the fixed rlm_pap), I shouldn't need ldap's auto_header functionality. [password_radius_attribute]
I've deleted that text from the documentation. The configuration item hasn't been in rlm_ldap for a long time.
I should have checked the source before attempting to use the parameter. I would have been able to see for myself that the parameter simply doesn't exist.
You need to tell FreeRADIUS *how* you have encrypted the passwords. If there's a {ssha} header on the password, then the PAP module should figure it out.
The header is there, as "{SSHA}". I imagine (I'm not trying to avoid *checking* for myself; I can do so on Monday when I'm back at work ...) that it isn't case-sensitive.
30 second delays are almost always DNS.
Understood.
Hrmmm... I have "hostname_lookups = no" ...
Yes. That configuration item controls IP address -> hostname lookups for printing. It has *no* effect on hostname -> IP mapping, such as looking up ldap servers by hostname.
Right, and I wouldn't have kidded myself that it had anything to do with that. Of course, if that's the problem (and if the server is performing that lookup for every LDAP query, and in my current installation, every bind to LDAP for authentication, it occurs to me that the DNS resolvers just might be throttling their responses due to the sheer number of queries they would be seeing from the same small number of systems), I could work-around it just as easily by using IP addresses for the LDAP server configurations, or simply list the LDAP servers in the system's /etc/hosts file (assuming appropriate configuration of nsswitch). That's getting a bit off-topic for freeradius-users, though. Still, thank you again for bringing this up; I had completely overlooked it as a possibility. And yes, I've quite well received your point: "run in debug mode and SEE why my current radiusd is taking so long to respond to the authentication requests". This might be an easy-enough "fix" that would at least buy me time to return to getting 2.0.3 properly configured and running.
... The issue is that the rlm_ldap module is reading the "userPassword" ldap field, and creating a User-Password attribute. It could really be fixed.
By patching rlm_ldap, you mean, or by adjusting my configuration?
Patching rlm_ldap, probably. The "userPassword" should be mapped to User-Password via ldap.attrmap, just like everything else.
If it's that simple, I definitely can go ahead and do that.
Ok, but what I'm stuck on is *why* the differences are there. I don't doubt I've done something wrong, but I'm unable to figure out what it is that I've done wrong.
It may be the bug in rlm_pap. Grab a current CVS snapshot, and see if that works any better.
I will do that Monday and report back. Thank you.
Ok, and then I'll need to put the blob in a SSHA-Password attribute, correct?
Yes. And it will likely work. But... the LDAP module is putting it into the User-Password attribute. So you might want to test that, too.
Alright.
I only learned about "redundant" this week. ...
$ man unlang
You probably want "redundant-load-balance". It's a bit of effort to type, but it results in a pretty robust system.
I have read "man unlang" and will read it again. I agree that redundant-load-balance is more likely to be what I want, and came to the same conclusion when I did read "man unlang" (only yesterday). A "pretty robust system" is definitely what I'm after, yes. :-)
- confure "auto_header = yes" for the ldap module.
I really don't think that's necessary. If you're not proxying, then the PAP module *should* take care of fixing the password up.
Ok, will try without it first, and report back.
Also, test with a User-Password := "{ssha}...". Check that the PAP module "fixes" it, and turns it into a SSHA-Password attribute.
Right. Thanks very much. I think I'm well on my way to getting this going, and even to fixing the original problem I was trying to solve in the first place (performance of the RADIUS server during peak usage hours). -- ---------------------------------------------------------------------- Sylvain Robitaille syl@alcor.concordia.ca Systems and Network analyst Concordia University Instructional & Information Technology Montreal, Quebec, Canada ----------------------------------------------------------------------
As promised, I'm reporting back with results from items discussed over the weekend ...
On Sat, 29 Mar 2008, Arran Cudbard-Bell wrote:
ldap { auto_header = yes }
As discussed, this duplicates functionality that is better handled by the rlm_pap module. I'm following Alan DeKok's reccomendation on this, and leaving that out, so that rlm_pap can perform all handling of the encrypted password.
On Sat, 29 Mar 2008, Alan DeKok wrote:
There isn't really a whole lot that can go wrong with the server. If it's waiting more than 30 seconds to respond, then the likelihood is that it's doing DNS lookups, and DNS is broken.
I haven't run our existing FreeRadius-1.1.6 server in debug mode to verify this, but I've put in the LDAP server(s) in the /etc/hosts file, to reduce its likelihood. After taking further actions (described below), I'm now running with 2.0.3. So far it's performing better than 1.1.6, but that's with a significantly different configuration than 1.1.6 has (I'm much closer to an uneditted default config with 2.0.3).
That's not the issue. The issue is that the rlm_ldap module is reading the "userPassword" ldap field, and creating a User-Password attribute. It could really be fixed.
It seems, at least according to further developments, that rlm_ldap already is putting the "userPassword" in the correct attribute for rlm_pap, so I don't think anything needs to be done to followup on that, at least not specifically for my case.
On Sat, 29 Mar 2008, Phil Mayers wrote:
I don't have a copy of 2.0.3 handy, but this looks like a bug to me at ~line 383 of rlm_pap.c:
case PW_PROXY_TO_REALM: { REALM *realm = realm_find(vp->vp_strvalue); if (realm && !realm->auth_pool) { return RLM_MODULE_NOOP; } break; }
I patched my copy here, recompiled, and tested: reversing this condition indeed produces an rlm_pap that seems to do the right thing.
On Sat, 29 Mar 2008, Alan DeKok wrote:
It may be the bug in rlm_pap. Grab a current CVS snapshot, and see if that works any better.
Hrmmm... That one segfaults on the first authentication request it receives. Correction: it's an accounting request for a "stop". I'm not sure if it's segfaulting because of anything I did wrong, or not. Debug output is fine for all config-file processing; the configuration is identical to my now functioning (patched) 2.0.3 installation. If the debug output prior to what follows is still desired, I'll repost, but the segfault occurs after what looks like a perfectly normal startup: ... radiusd: #### Opening IP addresses and Ports #### listen { type = "auth" ipaddr = * port = 0 } listen { type = "acct" ipaddr = * port = 0 } Listening on authentication address * port 1812 Listening on accounting address * port 1813 Listening on proxy address * port 1814 Ready to process requests. rad_recv: Accounting-Request packet from host 192.168.154.6 port 1646, id=243, length=144 Acct-Session-Id = "00012E2D" Called-Station-Id = "0009.b739.6eaf" Calling-Station-Id = "0012.f01b.9a62" User-Name = "j_smith" Acct-Session-Time = 0 Acct-Input-Octets = 0 Acct-Output-Octets = 178 Acct-Input-Packets = 0 Acct-Output-Packets = 2 Acct-Terminate-Cause = Lost-Carrier Acct-Status-Type = Stop NAS-Port-Type = Wireless-802.11 NAS-Port = 13349 Service-Type = Framed-User NAS-IP-Address = 192.168.154.6 Acct-Delay-Time = 96 +- entering group preacct Segmentation fault I tried this again on non-"production" ports, with input from radeaptest, and that also fails, after "+- entering group authorize": ... Listening on authentication address * port 1815 Listening on accounting address * port 1816 Listening on proxy address * port 1817 Ready to process requests. rad_recv: Access-Request packet from host 127.0.0.1 port 42735, id=81, length=71 User-Name = "j_doe" NAS-IP-Address = 192.168.198.20 NAS-Port-Type = Wireless-802.11 Message-Authenticator = 0xace3cf4de87a5f544d3a216c910a5542 NAS-Port = 0 EAP-Message = 0x02d200080173796c +- entering group authorize For some reason, I seem unable to get this to produce a core file to try and track it down any further ("limit coredumpsize unlimited" as root hasn't helped). I'm not really able to spend more time on that, given that I have a working 2.0.3, with patched rlm_pap, but if there's something I can do to help gather more information I'm certainly willing to try. I'm going to return to configuring 2.0.3 with different authorization queries for the various services we're using RADIUS with. Hopefully now I'll be able to do what I need without any further adventure. Thanks to all who have followed along with this, and especially, of course, to all who followed up with suggestions, recommendations, and fixes. Thanks also to those who put in so much time into creating and maintaining this package. You're making other people's jobs easier! -- ---------------------------------------------------------------------- Sylvain Robitaille syl@alcor.concordia.ca Systems and Network analyst Concordia University Instructional & Information Technology Montreal, Quebec, Canada ----------------------------------------------------------------------
Sylvain Robitaille wrote:
... So far it's performing better than 1.1.6, but that's with a significantly different configuration than 1.1.6 has (I'm much closer to an uneditted default config with 2.0.3).
Remember: the default configuration *works*. :)
Hrmmm... That one segfaults on the first authentication request it receives. Correction: it's an accounting request for a "stop".
Likely because of version numbers, etc. If you re-build && install *one* module, it might not work. If you install everything from the same source tree, it should work.
For some reason, I seem unable to get this to produce a core file to try and track it down any further ("limit coredumpsize unlimited" as root hasn't helped). I'm not really able to spend more time on that, given that I have a working 2.0.3, with patched rlm_pap, but if there's something I can do to help gather more information I'm certainly willing to try.
Don't worry about it.
Thanks to all who have followed along with this, and especially, of course, to all who followed up with suggestions, recommendations, and fixes. Thanks also to those who put in so much time into creating and maintaining this package. You're making other people's jobs easier!
That's the goal. :) Alan DeKok.
On Tue, 1 Apr 2008, Alan DeKok wrote:
Remember: the default configuration *works*. :)
So you keep saying! ;-)
Hrmmm... That one segfaults on the first authentication request it receives. Correction: it's an accounting request for a "stop".
Likely because of version numbers, etc. If you re-build && install *one* module, it might not work. If you install everything from the same source tree, it should work.
That's what I did, though (installed everything from the same source tree). As I just wrote, I'll get back to looking at that after I'm finished getting 2.0.3 doing everything I need (authorizing for multiple services). I'll probably find something I did wrong, perhaps during the pre-compilation configure run? -- ---------------------------------------------------------------------- Sylvain Robitaille syl@alcor.concordia.ca Systems and Network analyst Concordia University Instructional & Information Technology Montreal, Quebec, Canada ----------------------------------------------------------------------
I'm back. Small reminder, since it appears that list members are helping a sufficient number of folks that remembering my particular setup would be non-trivial: - I'm running FreeRADIUS-2.0.3 (rlm_pap is patched as was discussed on this mailing list), with TTLS/PAP using OpenLDAP as the source of user authorization and authentication. - My configuration files are nearly "stock", with the exception of the necessary configuration to get the ldap module talking to the LDAP server. - This setup has been running like this now for a couple of days without any trouble. What I'm aiming to accomplish, however, is that the FreeRADIUS server will authorize users for different services based on a slightly different LDAP query. The users are in various groups, which can be checked by supplying an LDAP query filter that checks the "memberOf" attribute; Users in group "wireless" should be permitted to use the wireless service; users in group "vpn" should be able to use the VPN service; users in both groups could use either, and users in neither group should be refused for either, etc. I've been trying to configure this by adding instances of the ldap module configuration ("ldap ldap_wireless" for example) in the "modules" section of radiusd.conf, and setting "Autz-Type" in the users file based on the NAS-IP-Address ("huntgroups" would likely be more appropriate for our wireless access points, but at the moment I'm trying to do this one step at a time, and in fact am testing with only 127.0.0.1 as the NAS-IP-Address anyway). Running radiusd in debug mode shows that the ldap module is using the configuration for its un-named instance (the default one from the stock config files, with minimal configuration to permit it to lookup users in our LDAP). I can tell the difference in which LDAP module configuration stanza is used by the query filter shown in the debug output. If the correct way to accomplish what I'm trying for is documented somewhere, I may have overlooked it, so I would appreciate it if someone could point me at it. I'm happy to read documentation, especially if it leads me to better understand how to accomplish desired tasks. Otherwise, if someone can see from the above what I'm doing wrong, I'd certainly appreciate any advice, suggestions or other useful input. Thanks again in advance ... -- ---------------------------------------------------------------------- Sylvain Robitaille syl@alcor.concordia.ca Systems and Network analyst Concordia University Instructional & Information Technology Montreal, Quebec, Canada ----------------------------------------------------------------------
Sylvain Robitaille wrote:
I'm back. Small reminder, since it appears that list members are helping a sufficient number of folks that remembering my particular setup would be non-trivial:
I have trouble remembering messages from 10 minutes ago. It's easier that way. ...
- My configuration files are nearly "stock", with the exception of the necessary configuration to get the ldap module talking to the LDAP server. - This setup has been running like this now for a couple of days without any trouble.
And yes, it really is that easy. (That's mostly for the people who think it's hard... because they butcher the default configs.)
What I'm aiming to accomplish, however, is that the FreeRADIUS server will authorize users for different services based on a slightly different LDAP query. The users are in various groups, which can be checked by supplying an LDAP query filter that checks the "memberOf" attribute; Users in group "wireless" should be permitted to use the wireless service; users in group "vpn" should be able to use the VPN service; users in both groups could use either, and users in neither group should be refused for either, etc.
You should be able to do this with multiple LDAP modules, or maybe by dynamically editing the ldap query.
... Running radiusd in debug mode shows that the ldap module is using the configuration for its un-named instance (the default one from the stock config files, with minimal configuration to permit it to lookup users in our LDAP).
You have to change the reference to "ldap" in sites-available/default. to the instance name. e.g. "ldap_wireless".
I can tell the difference in which LDAP module configuration stanza is used by the query filter shown in the debug output.
Thankfully. Isn't debug output nice? More people should use it... Alan DeKok.
On Thu, 3 Apr 2008, Alan DeKok wrote:
I have trouble remembering messages from 10 minutes ago. It's easier that way.
There were messages 10 minutes ago? ;-)
...
- My configuration files are nearly "stock", with the exception of the necessary configuration to get the ldap module talking to the LDAP server. - This setup has been running like this now for a couple of days without any trouble.
And yes, it really is that easy. ...
And quite frankly, darned amazing! All (?!? nearly all?) the third-party documentation out there makes it *seem* difficult. If nothing else, not trying to set the Auth-Type anywhere (and letting the server do the Right Thing) results in a noticeable improvement in RADIUS performance (at least in the case here, where our old configuration explicitly sets Auth-Type to LDAP, causing an LDAP-bind for every authentication request, and we're getting LOTS of authentication requests). Had I persisted more at getting this right (rather than simply "working") a couple of years ago when I originally set it up, I likely would have saved myself many headaches!
What I'm aiming to accomplish, however, is that the FreeRADIUS server will authorize users for different services based on a slightly different LDAP query. ...
You should be able to do this with multiple LDAP modules, or maybe by dynamically editing the ldap query.
Dynamically editting the query hadn't occurred to me. I've been trying to configure multiple instances of the LDAP module. Even now considering dynamically editing the ldap query, I suspect that the multiple module approach is likely simpler to configure and maintain.
You have to change the reference to "ldap" in sites-available/default. to the instance name. e.g. "ldap_wireless".
In the "authorize" stanza, then? So I replace # # The ldap module will set Auth-Type to LDAP if it has not # already been set ldap with # # The ldap module will set Auth-Type to LDAP if it has not # already been set ldap_wireless or # # The ldap module will set Auth-Type to LDAP if it has not # already been set ldap ldap_wireless ? Can I then add an "ldap_vpn" as well, in the same place? Is this where I should be using Autz-Type wireless { ldap_wireless } Autz-Type vpn { ldap_vpn } ... ? I'm placing the ldap module-instance configuration in radiusd.conf, and setting Autz-Type in users. Are these the "correct" places for those items? Is there specific documentation I should be re-reading to properly understand this? I feel as though I "sort-of" understand the sequence, from examining debug output, but I don't feel I really know (yet) how to make the server do my bidding. -- ---------------------------------------------------------------------- Sylvain Robitaille syl@alcor.concordia.ca Systems and Network analyst Concordia University Instructional & Information Technology Montreal, Quebec, Canada ----------------------------------------------------------------------
Sylvain Robitaille wrote:
And yes, it really is that easy. ...
And quite frankly, darned amazing! All (?!? nearly all?) the third-party documentation out there makes it *seem* difficult.
2 reasons: (1) that "documentation" is usually written be people who don't understand how the server works, and (2) if they admitted it was that easy, their "howto" pages would be 4 lines long.
You have to change the reference to "ldap" in sites-available/default. to the instance name. e.g. "ldap_wireless".
In the "authorize" stanza, then? So I replace
Yes. You replace "ldap" with "ldap_authorize".
Can I then add an "ldap_vpn" as well, in the same place?
Depending on what you want, perhaps.
Is this where I should be using
Autz-Type wireless {
In 2.0, you don't really need Autz-Type. I would suggest pretending that it doesn't exist. Instead, use "unlang".
I'm placing the ldap module-instance configuration in radiusd.conf, and setting Autz-Type in users. Are these the "correct" places for those items?
radiusd.conf configures everything in the server. The "users" file has a much more limited scope.
Is there specific documentation I should be re-reading to properly understand this? I feel as though I "sort-of" understand the sequence, from examining debug output, but I don't feel I really know (yet) how to make the server do my bidding.
doc/aaa.txt. The sections are processed top to bottom, as a linear list. If you want to make the server do your bidding, write "if/else" statements using "unlang". i.e. write the conditions you want to match in plain english, and what you want it to do. Then, translate that pretty much directly into "unlang". Alan DeKok.
On Apr 2, 2008, at 5:52 PM, Alan DeKok wrote:
Sylvain Robitaille wrote:
What I'm aiming to accomplish, however, is that the FreeRADIUS server will authorize users for different services based on a slightly different LDAP query. The users are in various groups, which can be checked by supplying an LDAP query filter that checks the "memberOf" attribute; Users in group "wireless" should be permitted to use the wireless service; users in group "vpn" should be able to use the VPN service; users in both groups could use either, and users in neither group should be refused for either, etc.
You should be able to do this with multiple LDAP modules, or maybe by dynamically editing the ldap query.
... Running radiusd in debug mode shows that the ldap module is using the configuration for its un-named instance (the default one from the stock config files, with minimal configuration to permit it to lookup users in our LDAP).
You have to change the reference to "ldap" in sites-available/ default. to the instance name. e.g. "ldap_wireless".
I'm looking to do something similar. What is the proper way to call a specific LDAP module based on NAS-IP- Address (or huntgroup, probably)? I don't want anything other than files (for overriding LDAP for testing) then LDAP. Obviously, I want to stay as close to the default config as possible. :)
Chris wrote:
What is the proper way to call a specific LDAP module based on NAS-IP-Address (or huntgroup, probably)?
authorize { ... if (NAS-IP-Address == 1.2.3.4) { ldap_1 } elsif (NAS-IP-Address == 3.4.5.6) { ldap_2 } ... } Or, use "switch". See "man unlang".
I don't want anything other than files (for overriding LDAP for testing) then LDAP.
Don't use the "users" file for things like this. It doesn't know about modules, or module order. The "unlang" parser does know.
Obviously, I want to stay as close to the default config as possible. :)
As always, a good idea. Alan DeKok.
On Thu, 3 Apr 2008, Alan DeKok wrote:
You have to change the reference to "ldap" in sites-available/default. to the instance name. e.g. "ldap_wireless". ... In 2.0, you don't really need Autz-Type. I would suggest pretending that it doesn't exist. Instead, use "unlang". ... The sections are processed top to bottom, as a linear list. If you want to make the server do your bidding, write "if/else" statements using "unlang".
i.e. write the conditions you want to match in plain english, and what you want it to do. Then, translate that pretty much directly into "unlang".
and in a response to a different message:
What is the proper way to call a specific LDAP module based on NAS-IP-Address (or huntgroup, probably)?
authorize { ... if (NAS-IP-Address == 1.2.3.4) { ldap_1 } elsif (NAS-IP-Address == 3.4.5.6) { ldap_2 } ... }
Or, use "switch". See "man unlang". ... Don't use the "users" file for things like this. It doesn't know about modules, or module order. The "unlang" parser does know.
On the one hand, "OH!!!" I think I'm starting to understand, but on the other hand, I appear to still not be doing it quite right. I put into the "authorize" section of sites-available/default: ... # # The ldap module will set Auth-Type to LDAP if it has not # already been set #ldap # wireless if (NAS-Port-Type == Wireless-802.11) { ldap_wireless } ... I also tried NAS-IP-Address with the same result so far, but I can clearly see from the debug output that this part is now functioning as expected. If the user does not match the search filter configured in my ldap_wireless instance of the ldap module, this section returns "notfound", otherwise it returns "ok". However, then the request carries on to the inner-tunnel of the TTLS transaction (whether or not the outer authorization succeeded or returned not found; is it possible to equate "notfound" to "fail" or "reject"?). If I configure sites-available/inner-tunnel's authorization section as above, when it gets to that point, debug output says: ++? if (NAS-Port-Type == Wireless-802.11) (Attribute NAS-Port-Type was not found) The user is rejected shortly after, even when the ldap search is expected to succeed, with the following in debug output: auth: No authenticate method (Auth-Type) configuration found for the request: Rejecting the user auth: Failed to validate the user. In other words, despite having found the user in the ldap_wireless search in sites-available/default, the inner-tunnel seems to not receive sufficient information about the request to decide to use the ldap_wireless module, leaving the RADIUS server with no way to authenticate the user. This is despite ldap_wireless in sites-available/default having produced: rlm_ldap: checking if remote access for j_doe is allowed by cn rlm_ldap: Added User-Password = {SSHA}*SANITIZED*QDmffXBQkU42Wt9x*SANITIZED*== in check items rlm_ldap: looking for check items in directory... rlm_ldap: looking for reply items in directory... rlm_ldap: user j_doe authorized to use remote access rlm_ldap: ldap_release_conn: Release Id: 0 +++[ldap_wireless] returns ok ++- if (NAS-Port-Type == Wireless-802.11) returns ok ie. we have a password and have already determined authorization for this user. And also despite the debug output of the request arriving at inner-tunnel *appearing* to contain items sufficient for me to select on: User-Name = "j_doe" NAS-IP-Address = 127.0.0.1 Calling-Station-Id = "02-00-00-00-00-01" Framed-MTU = 1400 NAS-Port-Type = Wireless-802.11 Connect-Info = "CONNECT 11Mbps 802.11b" EAP-Message = 0x02050070150017030100207ec2e216f79ef34a114bb34054277beb1a45fd25505d975be42b62d449e1be8c1703010040ca0cbb9c6b5abfef1e656ccc100c8350cae810edc08d9b6c3135dabbcac32a2ef26c2a3824cb7eaf7423d00c83432cfaceb08721d92faa5c3579908e3be88ba3 State = 0x6f66f2676b63e70a05f25e914c848f96 Message-Authenticator = 0x314bc723b23efd033689667de8c0ca7a If I put in inner-tunnel: authorize { ... ldap ... } Then it seems to authorize access for users that "ldap_wireless" in "default" didn't find. I can get the intended result for *this* service with inner-tunnel containing instead: authorize { ... ldap_wireless ... } but that doesn't help me for other services for which I want to use RADIUS. Help? -- ---------------------------------------------------------------------- Sylvain Robitaille syl@alcor.concordia.ca Systems and Network analyst Concordia University Instructional & Information Technology Montreal, Quebec, Canada ----------------------------------------------------------------------
Sylvain Robitaille wrote:
On the one hand, "OH!!!" I think I'm starting to understand, but on the other hand, I appear to still not be doing it quite right. I put into the "authorize" section of sites-available/default: ... However, then the request carries on to the inner-tunnel of the TTLS transaction (whether or not the outer authorization succeeded or returned not found; is it possible to equate "notfound" to "fail" or "reject"?).
Yes. if (notfound) { fail }
If I configure sites-available/inner-tunnel's authorization section as above, when it gets to that point, debug output says:
++? if (NAS-Port-Type == Wireless-802.11) (Attribute NAS-Port-Type was not found)
Set copy_request_to_tunnel in eap.conf. Or, do: if (outer.NAS-Port-Type == Wireless-802.11) { ... Again, "man unlang" explains "outer.*".
In other words, despite having found the user in the ldap_wireless search in sites-available/default, the inner-tunnel seems to not receive sufficient information about the request to decide to use the ldap_wireless module, leaving the RADIUS server with no way to authenticate the user. This is despite ldap_wireless in sites-available/default having produced:
If you're using TTLS, you *don't* want to do username/password lookups in ldap for sites-enabled/default. That's what the "inner-tunnel" server is for. Do the LDAP calls there.
And also despite the debug output of the request arriving at inner-tunnel *appearing* to contain items sufficient for me to select on:
No... that looks like the *outer* tunnel data. Inner tunnel requests do *not* have a Message-Authenticator attribute.
If I put in inner-tunnel: ... Then
Stop. You are trying too many options, and too many different configurations. It's not worth it. Keep the outer and inner tunnel configurations separate. That's why they are in different virtual servers... because they are separate. In the inner tunnel server, use "outer.Attribute-Name" to access attributes *outside* of the tunnel. Honestly, it's not that difficult. Find *something* in the outer request that is there only for wireless requests. Key off of that in the *inner* tunnel to select the users from the correct LDAP instance. if (outer.NAS-Port-Type == foo) { ldap_foo } elsif (outer.NAS-Port-Type == bar) { ldap_bar } Alan DeKok.
On Thu, 3 Apr 2008, Alan DeKok wrote:
... is it possible to equate "notfound" to "fail" or "reject"?).
Yes.
if (notfound) { fail }
Hrmmm... I thought I'd tried that before writing the above, but I didn't keep a copy of it, so I can't recheck if I maybe simply tried it in the wrong place. However, I believe you're setting me straight, and showing me that although this is possible, it isn't the best way to accomplish what I'm trying to do ...
Set copy_request_to_tunnel in eap.conf. Or, do:
if (outer.NAS-Port-Type == Wireless-802.11) { ... Again, "man unlang" explains "outer.*".
Ah, yes! That works. (I know: see you not look surprised!) I apologize if I'm seeming dense, or leaving the impression that I haven't read documentation that you've already pointed me at. I *have* read that documentation, but I think the problem is that I'm struggling to wrap my head around the details, perhaps because it seems that not only are there many options, but there seem to be indeed several ways that the same result *might* be achieved. It's looking like what I'm finding are all the ways that won't actually do what I want, though. I feel as though *conceptually* I understand what I need to do, but I haven't yet understood how to apply that to my configuration.
If you're using TTLS, you *don't* want to do username/password lookups in ldap for sites-enabled/default. That's what the "inner-tunnel" server is for. Do the LDAP calls there.
Ok, this is definitely the bottom line of where I've been going wrong. I *was* trying to get the ldap authorization done in "default". Corrected.
No... that looks like the *outer* tunnel data. Inner tunnel requests do *not* have a Message-Authenticator attribute.
Hrmmm... In that case the inner-tunnel isn't printing to debug output the request as it is received at that point? Ok, I think I see it now. The debug output from the inner-tunnel starts here then? ... rlm_eap_ttls: Session established. Proceeding to decode tunneled attributes. +- entering group authorize ++[chap] returns noop ++[mschap] returns noop ++[unix] returns notfound rlm_realm: No '@' in User-Name = "j_doe", looking up realm NULL rlm_realm: No such realm "NULL" ++[suffix] returns noop ++[control] returns noop rlm_eap: No EAP-Message, not doing EAP ++[eap] returns noop ++[files] returns noop ++? if (outer.NAS-Port-Type == Wireless-802.11) ? Evaluating (outer.NAS-Port-Type == Wireless-802.11) -> TRUE ++? if (outer.NAS-Port-Type == Wireless-802.11) -> TRUE ++- entering if (outer.NAS-Port-Type == Wireless-802.11) rlm_ldap: - authorize ...
Stop. You are trying too many options, and too many different configurations. It's not worth it.
Well, I'm trying these options and configurations because I do really want to accomplish the result I'm after. That I've been doing it all wrong is simply an indication that I *still* haven't understood the way the server functions. I promise that it isn't because I'm not trying. :-(
Keep the outer and inner tunnel configurations separate. That's why they are in different virtual servers... because they are separate.
I expected that, but made the mistake of adding things in "default" first, seeing the server do *some* of what I was after, then trying to get it to do the *remainder* by attempting to configure (sometimes similar) items in "inner-tunnel", though not with complete success.
In the inner tunnel server, use "outer.Attribute-Name" to access attributes *outside* of the tunnel.
Hrmmm... I just spotted why I didn't understand that previously from "man unlang", but rather needed you to explain it to me directly: : natasha[syl] ~; man unlang |grep -w outer also reference "outer.request", "outer.reply", and "outer.control". Those references will update the rele- vant list in the outer tunnel session. "outer.request", "outer.reply", or "outer.control", It talks about being able to *update* items in the outer request (to which my mind certainly replied, "no, that's not what I'm trying to do ...") but not specifically about being able to access *incoming* attributes from the outer tunnel. Probably the following text (from "man unlang") is intended to make that clear, but with my very limitted knowledge of the server's function, it didn't: For EAP methods with tunneled authentication sessions (i.e. PEAP and EAP-TTLS), the inner tunnel session can also reference "outer.request", "outer.reply", and "outer.control". ... Ie. In hindsight, "outer.request" should probably have been my clue, but it was completely overlooked because this occurs in the "update" section of KEYWORDS. I saw it, but didn't really "see" what it was telling me. I'd offer to patch the documentation to make it clear that the inner-tunnel can reference *attributes* from the outer request using "outer.Attribute-Name", but it seems despite all I've learned from all of these experiments and from the help I've gotten on the mailing list, I have only scratched the surface of what there is to know about FreeRadius, and I would likely write yet more partially-correct-at-best third-party documentation that folks really shouldn't follow. :-(
Honestly, it's not that difficult. Find *something* in the outer request that is there only for wireless requests. Key off of that in the *inner* tunnel to select the users from the correct LDAP instance.
I had the first part of that right: I was looking for a unique attribute. I appreciate the time you've taken to teach me *where* I should have been looking for that attribute.
if (outer.NAS-Port-Type == foo) { ldap_foo } elsif (outer.NAS-Port-Type == bar) { ldap_bar }
That's EXACTLY what I need to do, yes. Once again, thanks for ALL the help. I think I now have everything I need to do exactly what I want. -- ---------------------------------------------------------------------- Sylvain Robitaille syl@alcor.concordia.ca Systems and Network analyst Concordia University Instructional & Information Technology Montreal, Quebec, Canada ----------------------------------------------------------------------
Sylvain Robitaille wrote:
I apologize if I'm seeming dense, or leaving the impression that I haven't read documentation that you've already pointed me at. I *have* read that documentation, but I think the problem is that I'm struggling to wrap my head around the details, perhaps because it seems that not only are there many options, but there seem to be indeed several ways that the same result *might* be achieved.
There is functionality in the server that's historical. The new "unlang" is generally preferred for anything resembling a complex configuration.
Ok, I think I see it now. The debug output from the inner-tunnel starts here then?
Yes. EAP-TTLS does PAP inside of a Diameter AVP inside of a TLS tunnel, which is encapsulated in the TTLS EAP method, which is encapsulated inside of a RADIUS EAP-Message attribute, which goes into a RADIUS packet, over UDP, IP, and Ethernet. See? Nothing could be simpler. <umm..>
Well, I'm trying these options and configurations because I do really want to accomplish the result I'm after. That I've been doing it all wrong is simply an indication that I *still* haven't understood the way the server functions. I promise that it isn't because I'm not trying. :-(
EAP-TTLS sets up a TLS tunnel between the server and the end machine (XP, Linux, etc.). It then does a normal authentication request inside of the tunnel. But since the NAS can't see inside of the tunnel, there are no NAS attributes inside of the tunnel.
Hrmmm... I just spotted why I didn't understand that previously from "man unlang", but rather needed you to explain it to me directly: .. It talks about being able to *update* items in the outer request
In the documentation about the "update" section. The later documentation about attribute references says you can make references to lists...
I'd offer to patch the documentation to make it clear that the inner-tunnel can reference *attributes* from the outer request using "outer.Attribute-Name", but it seems despite all I've learned from all of these experiments and from the help I've gotten on the mailing list, I have only scratched the surface of what there is to know about FreeRadius, and I would likely write yet more partially-correct-at-best third-party documentation that folks really shouldn't follow. :-(
I'm trying to write a book, honest. I think I should probably just give up, and put the 200 pages I have up on the net for review.
Once again, thanks for ALL the help. I think I now have everything I need to do exactly what I want.
See? It's easy... just run into a couple of bugs, bang your head against the wall, and you've got it made... Alan DeKok.
Earlier, I wrote:
For some reason, I seem unable to get this to produce a core file to try and track it down any further ("limit coredumpsize unlimited" as root hasn't helped). ...
Sigh ... while reviewing the configuration for my now-in-production installation, I spotted the "allow_core_dumps" parameter. I will finish with what I'm doing now, then return to getting more information of when and where the CVS version is seg-faulting. If the problem is of my own creation, I'll just fix it. Otherwise I'll report back with any additional information I can provide. -- ---------------------------------------------------------------------- Sylvain Robitaille syl@alcor.concordia.ca Systems and Network analyst Concordia University Instructional & Information Technology Montreal, Quebec, Canada ----------------------------------------------------------------------
I've to set up my FR to let a User telnet into my Cisco Router. Whithout further contact to my client until Friday, I will test my environment in advance. Accepting a session using this attributes will work fine. I'll get an IP and can connect to the router using telnet. Session-Timeout : 14400 Idle-Timeout : 600 AVPair : ip:wins-servers=10.1.1.223 Framed-IP-Address : 10.1.7.150 AVPair : ip:dns-servers=145.253.2.11 but accepting a session using the following attributes fails to connect. Login-IP-Host : 10.1.7.201 Framed-IP-Address : 10.1.7.155 Login-Service : Telnet Login-TCP-Port : 23 What application might I use to test this environment using a Windows XP system? I thought I have to dialup the normal way and then start my Telnet Client to configure the router? If I configure my dialup settings to use PPP, I got refused/disconnectes emmediately If I configure my dialup settings to use SLIP, I will be disconnected after about 22s. What is the expected differnece or the advantage of using Login-Service=Telnet? Thank You. Regards Stefan
What application might I use to test this environment using a Windows XP system?
A device called UTP cable that you plug into the local switch and a C:\ prompt. "my Cisco router" implies that you have access to it.
I thought I have to dialup the normal way and then start my Telnet Client to configure the router?
No. That depends on the setup. You can telnet over the LAN if you are local. Or dial into any ISP in the world and still telnet to that router (if it has a public IP address and no firewall protection). If there is a firewall that will dictate your options. Hint - it's a good idea to have different usernames for dialup and router administration. Ivan Kalik Kalik Informatika ISP
Alan DeKok wrote:
Sylvain Robitaille wrote: ...
ldap { auto_header = yes ... I will definitely give that a try on Monday morning. I wasn't aware that the ldap module also had an auto_header parameter. I have it set for the pap module already, but will try with the ldap module and report back.
I would very much prefer that the PAP module be used for the password mangling, rather than rlm_ldap. The code in the PAP module does more, and is more used than the similar code in rlm_ldap. I think that functionality will be removed from rlm_ldap.
Yes, it is duplicate functionality. Lots of our configuration files are still based on CVS versions from when FR 2 was being developed, I should really merge them with the standard 2.0.3 configs at some point. I just couldn't understand why the PAP module wasn't processing the header on the User-Password, and I know the autoheader option works for us with rlm_ldap. It's actually very useful because it'll allow the migration from crypt *sigh* to ssha1 at some point in the future, but if rlm_pap does the same thing then i'll switch to that.
have no idea what password_radius_attribute is ?? Is that a legacy configuration item ?
Yes.
I don't think so. I only learned about it this week, though that isn't to suggest that it wasn't around previously. I learned about this from reading doc/rlm_ldap that ships with freeradius-server-2.0.3. That file says the following about this parameter:
I've deleted that text from the documentation. The configuration item hasn't been in rlm_ldap for a long time.
You need to tell FreeRADIUS *how* you have encrypted the passwords. If there's a {ssha} header on the password, then the PAP module should figure it out.
But it doesn't appear to be... you have got the autoheader option set in the PAP module? pap { auto_header = yes } Doesn't matter where it's set for testing, it just needs to be set *somewhere*. *nothing* will work until you get the hash into the correct attribute with the header stripped off. Fudging it by creating a static mapping userPassword -> SSHA-Password in ldap.attrmap won't work because the header will still be present in the hash... If you really stumped something like: authorize { ldap if(ok && ("%{control:User-Password}" ~= /^{ssha}(.*)/i)){ update control{ SSHA-Password := "%{1}" } } } Will do the work of the LDAP / PAP module. But it's a bodge, really rlm_pap should be doing that.
It might still be interesting just to _know_ what's slowing the RADIUS server down, though.
30 second delays are almost always DNS.
There isn't really a whole lot that can go wrong with the server. If it's waiting more than 30 seconds to respond, then the likelihood is that it's doing DNS lookups, and DNS is broken. Hrmmm... I have "hostname_lookups = no" on both my existing (1.1.6) installation and the new one I'm working on (2.0.3), but of course *some* DNS lookups would still be expected (I have multiple LDAP servers configured, by hostname, for example),
Yes. That configuration item controls IP address -> hostname lookups for printing. It has *no* effect on hostname -> IP mapping, such as looking up ldap servers by hostname.
We have the LDAP servers in a DNS round robin. Does FR resolve the hostname each time a new connection is established, or will it resolve it once during startup when the configuration entry is parsed? Thanks, Arran
On Sat, 29 Mar 2008, Arran Cudbard-Bell wrote:
If there's a {ssha} header on the password, then the PAP module should figure it out.
But it doesn't appear to be... you have got the autoheader option set in the PAP module?
pap { auto_header = yes }
Yes, that's configured.
*nothing* will work until you get the hash into the correct attribute with the header stripped off.
Right. As already noted, radtest against a user entry in our LDAP data *does* work. I just need to get this working inside the TTLS tunnel.
Fudging it by creating a static mapping userPassword -> SSHA-Password in ldap.attrmap won't work because the header will still be present in the hash...
Ok, which suggests that my attempt to use "password_radius_attribute" (if that parameter still existed) in the ldap configuration would have still failed, because I was trying to set it to SSHA-Password there. Alan's suggestion was to map it tp User-Password, though, which is where rlm_pap *would* know how to deal with it. Thanks, of course, for your continued interest ... -- ---------------------------------------------------------------------- Sylvain Robitaille syl@alcor.concordia.ca Systems and Network analyst Concordia University Instructional & Information Technology Montreal, Quebec, Canada ----------------------------------------------------------------------
participants (8)
-
Alan DeKok -
Arran Cudbard-Bell -
Chris -
Ivan Kalik -
Kevin Zhang -
Phil Mayers -
Stefan A. -
Sylvain Robitaille