This is an old revision of the document!
FreeRADIUS with LDAP
Introduction
- FreeRADIUS includes support for LDAP integration.
- To ensure maximum benefit of RADIUSdesk we will use a hybrid setup for LDAP integration.
- The next section will be used as a basic introduction to FreeRADIUS and LDAP
Basic FreeRADIUS with LDAP
OpenLDAP
Install OpenLDAP
- We will install OpenLDAP and do a basic setup that can be used by FreeRADIUS.
- When you install OpenLDAP (slapd) the package installer will ask you to provide a password.
- Provide one but keep in mind that we will reconfigure everything after the install.
- OpenLDAP server is called slapd.
- The program to extract info from the OpenLDAP directory is called slapcat.
# Update repository lists sudo apt update # Install OpenLDAP and standard utility tools sudo apt install -y slapd ldap-utils # Install the FreeRADIUS LDAP module (rlm_ldap) sudo apt install -y freeradius-ldap
Configure OpenLDAP
- After the slapd package installed we can run the following command to reconfigure slapd and provide a basic setup.
# Configure or reconfigure slapd defaults interactively sudo dpkg-reconfigure slapd
- Omit OpenLDAP server configuration? No.
- DNS domain name: Enter your domain (e.g., radiusdesk.com creating dc=radiusdesk,dc=com).
- Organization name: Enter your organization name (We specified radiusdesk).
- Administrator password: We used a simple password since we're testing.
- After you answered these questions slapd should be reconfigured with those items.
Check OpenLDAP
- You can confirm it by issuing the following command
sudo slapcat dn: dc=radiusdesk,dc=com objectClass: top objectClass: dcObject objectClass: organization o: radiusdesk dc: radiusdesk structuralObjectClass: organization entryUUID: 8c68dc16-1a3f-1041-9add-250d07e316fc creatorsName: cn=admin,dc=radiusdesk,dc=com createTimestamp: 20260722173600Z entryCSN: 20260722173600.213629Z#000000#000#000000 modifiersName: cn=admin,dc=radiusdesk,dc=com modifyTimestamp: 20260722173600Z
- This confirms the basic setup of slapd.
- Next we will add an Organizational Unit (OU) under which we can add our users. (Remember LDAP is a directory/hierarchy)
Create the Organizational Unit (OU)
- Create a file named ou.ldif to set up a dedicated container for your network accounts.
- ou.ldif
dn: ou=people,dc=radiusdesk,dc=com objectClass: organizationalUnit ou: people
- Apply this file to your OpenLDAP directory:
ldapadd -x -D "cn=admin,dc=radiusdesk,dc=com" -W -f ou.ldif
Create the User Account
- Create a file named user.ldif.
- This template creates a user named testuser with the password mysecretpassword.
- user.ldif
dn: uid=testuser,ou=people,dc=radiusdesk,dc=com objectClass: top objectClass: account objectClass: simpleSecurityObject uid: testuser userPassword: mysecretpassword description: RADIUS Test User
- Apply this file to your OpenLDAP directory:
ldapadd -x -D "cn=admin,dc=radiusdesk,dc=com" -W -f user.ldif
- If you run slapcat again these items should be in the reply.
sudo slapcat dn: dc=radiusdesk,dc=com objectClass: top objectClass: dcObject objectClass: organization o: radiusdesk dc: radiusdesk structuralObjectClass: organization entryUUID: 8c68dc16-1a3f-1041-9add-250d07e316fc creatorsName: cn=admin,dc=radiusdesk,dc=com createTimestamp: 20260722173600Z entryCSN: 20260722173600.213629Z#000000#000#000000 modifiersName: cn=admin,dc=radiusdesk,dc=com modifyTimestamp: 20260722173600Z dn: ou=people,dc=radiusdesk,dc=com objectClass: organizationalUnit ou: people structuralObjectClass: organizationalUnit entryUUID: a6c420c6-1a48-1041-895a-41f787ad35f7 creatorsName: cn=admin,dc=radiusdesk,dc=com createTimestamp: 20260722184109Z entryCSN: 20260722184109.903088Z#000000#000#000000 modifiersName: cn=admin,dc=radiusdesk,dc=com modifyTimestamp: 20260722184109Z dn: uid=testuser,ou=people,dc=radiusdesk,dc=com objectClass: top objectClass: account objectClass: simpleSecurityObject uid: testuser userPassword:: bXlzZWNyZXRwYXNzd29yZA== description: RADIUS Test User structuralObjectClass: account entryUUID: f0928490-1a48-1041-895b-41f787ad35f7 creatorsName: cn=admin,dc=radiusdesk,dc=com createTimestamp: 20260722184313Z entryCSN: 20260722184313.729405Z#000000#000#000000 modifiersName: cn=admin,dc=radiusdesk,dc=com modifyTimestamp: 20260722184313Z
- Now that we have a working LDAP setup we can configure FreeRADIUS to work with this LDAP server.
FreeRADIUS + LDAP
- We assume the following:
- You have installed the OpenLDAP server on the same host that FreeRADIUS is installed on.
- You have a clean install of FreeRADIUS. (default config)
- If you have installed RADIUSdesk on the host it will have a modified FreeRADIUS config.
- You can however activate the default config again with the following steps
sudo su service freeradius stop cd /etc mv /etc/freeradius /etc/freeradius.rd cp -r /etc/freeradius.orig /etc/freeradius chown -R freerad:freerad /etc/freeradius
Enable the FreeRADIUS LDAP Module
- FreeRADIUS keeps available modules in one directory and active ones in another.
- Enable the LDAP module by creating a symbolic link.
sudo su # Navigate to the enabled modules directory cd /etc/freeradius/3.0/mods-enabled/ # Link the LDAP configuration module sudo ln -s ../mods-available/ldap .
Map FreeRADIUS to OpenLDAP
- Edit the module configuration file to point FreeRADIUS to your local OpenLDAP instance.
- Edit /etc/freeradius/3.0/mods-available/ldap and update these core lines:
ldap { # LDAP server connection parameters server = "localhost" port = 389 # Identity used to search the directory identity = "cn=admin,dc=radiusdesk,dc=com" password = testing123 # Base DN where user lookups will begin base_dn = "dc=radiusdesk,dc=com" # User lookup mapping filter update { control:Password-With-Header += 'userPassword' } user { base_dn = "ou=people,dc=radiusdesk,dc=com" filter = "(uid=%{%{Stripped-User-Name}:-%{User-Name}})" } }
Check the Default Virtual Server
- You must instruct FreeRADIUS to check the LDAP backend during incoming connection requests.
- Open /etc/freeradius/3.0/sites-enabled/default and confirm the following is in the authorize block
# # The ldap module reads passwords from the LDAP database. -ldap
- The - prefix to ldap means it will silently be ignored when the LDAP module is not enabled.
Test it out
- Test the RADIUS authentication to confirm if it is working as intended
- Start FreeRADIUS in debug mode
sudo systemctl stop freeradius sudo freeradius -X
- Use the radtest program to do a test authentication.
radtest testuser mysecretpassword localhost 1812 testing123 #This is the return on my setup Sent Access-Request Id 249 from 0.0.0.0:56819 to 127.0.0.1:1812 length 78 User-Name = "testuser" User-Password = "mysecretpassword" NAS-IP-Address = 127.0.1.1 NAS-Port = 1812 Message-Authenticator = 0x00 Cleartext-Password = "mysecretpassword" Received Access-Accept Id 249 from 127.0.0.1:1812 to 127.0.0.1:56819 length 38 Message-Authenticator = 0x216fe46614354e897d645ce27ec9e0d8
- Lets look at the LDAP module's debug output in FreeRADIUS
rlm_ldap (ldap): Reserved connection (1) (2) ldap: EXPAND (uid=%{%{Stripped-User-Name}:-%{User-Name}}) (2) ldap: --> (uid=testuser) (2) ldap: Performing search in "ou=people,dc=radiusdesk,dc=com" with filter "(uid=testuser)", scope "sub" (2) ldap: Waiting for search result... (2) ldap: User object found at DN "uid=testuser,ou=people,dc=radiusdesk,dc=com" (2) ldap: Processing user attributes (2) ldap: control:Password-With-Header += 'mysecretpassword' rlm_ldap (ldap): Released connection (1) Need 1 more connections to reach min connections (3) Need more connections to reach 10 spares rlm_ldap (ldap): Opening additional connection (7), 1 of 30 pending slots used rlm_ldap (ldap): Connecting to ldap://localhost:389 rlm_ldap (ldap): Waiting for bind result... rlm_ldap (ldap): Bind successful (2) [ldap] = updated (2) [expiration] = noop (2) [logintime] = noop (2) pap: No {...} in Password-With-Header, re-writing to Cleartext-Password (2) pap: Removing &control:Password-With-Header (2) [pap] = updated (2) } # authorize = updated (2) Found Auth-Type = PAP
- Based on the debug output we can see the following happens when the ldap module is angaged
- The LDAP module does a search for the user.
- When the LDAP server replies with a result the LDAP module looks for the userPassword LDAP reply attribute.
- This is the clear-text password of the user and not all LDAP servers provides it.
- OpenLDAP does provide it (control:Password-With-Header += 'mysecretpassword')
- It then tries an LDAP bind as the user to confirm the password is working.
- If this worked it sets the Cleartext-Password so we can do PAP authentication. (Auth-Type = PAP)
- Not all LDAP authentications works like this since not all LDAP servers will return the user's password in cleartext.
- We will cover those later in the document.
FreeRADIUS with Secure LDAP
- When you plan to use any external LDAP server with FreeRADIUS they will typically be forcing you to connect securely via SSL/TLS on port 636.
- In this section we will:
- Create a PKI. This includes creating a CA with cert and key for slapd (OpenLDAP)
- Configure OpenLDAP to also support ldaps.
- Configure FreeRADIUS to communicate via ldaps with slapd (OpenLDAP).
Create PKI
Create the CA
- Create a working directory
mkdir -p ~/pki cd ~/pki
- Generate the CA key
openssl genpkey -algorithm RSA -out ca.key -pkeyopt rsa_keygen_bits:4096
- Create the CA certificate
openssl req -new -x509 -days 3650 -key ca.key -sha256 -out ca.crt #### This is what we filled in #### You are about to be asked to enter information that will be incorporated into your certificate request. What you are about to enter is what is called a Distinguished Name or a DN. There are quite a few fields but you can leave some blank For some fields there will be a default value, If you enter '.', the field will be left blank. ----- Country Name (2 letter code) [AU]:ZA State or Province Name (full name) [Some-State]:Gauteng Locality Name (eg, city) []:Johannesburg Organization Name (eg, company) [Internet Widgits Pty Ltd]:RADIUSdesk.com Organizational Unit Name (eg, section) []:PKI Common Name (e.g. server FQDN or YOUR name) []:RADIUSdesk Internal Root CA Email Address []:dirk@gmail.com
- Keep ca.key secret.
Generate the LDAP server key
- Issue the following command:
openssl genpkey -algorithm RSA -out ldap.key -pkeyopt rsa_keygen_bits:4096
Create an OpenSSL configuration
- Create ldap.conf. Use the following as reference.
[req] default_bits = 4096 prompt = no distinguished_name = dn req_extensions = req_ext [dn] CN = ldap.radiusdesk.com [req_ext] subjectAltName = @alt_names [alt_names] DNS.1 = ldap.radiusdesk.com DNS.2 = ldap IP.1 = 127.0.0.1
- Please Note: The subjectAltName (SAN) is important. Modern TLS ignores the Common Name.
Create the CSR
- The following command will create the sign request:
openssl req -new -key ldap.key -out ldap.csr -config ldap.cnf
Sign the request
- The following command will use the sign request to create a certificate:
openssl x509 -req -in ldap.csr -CA ca.crt -CAkey ca.key -CAcreateserial -out ldap.crt -days 825 -sha256 -copy_extensions copy
*
- Now you have the following files:
- ca.crt - The CA public file
- ca.key - The CA private file
- ldap.key - The LDAP private file
- ldap.crt - The LDAP public file