Having issues interpreting ldap search/filter attributes

Steve Phillips steve at focb.co.nz
Tue Aug 18 03:55:07 CEST 2020


Hi There,

Firstly, can I say thanks for the previous mail, it helped quite a bit when it came to understanding how to check the rlm_ldap 'search' parameter against ldapsearch to see what comes back. I've since noticed some interesting things.

Firstly, nested groups, I can say we are not searching for nested groups, the group being searched against (Lets call it "ACCESS_2FA") is happily returning the user object when a search is done using ldapsearch on this group.

I think I have found the issue though but I am unsure on how to fix it.

When I perform the initial bind, I am doing this as a user supplied in the user-name radius attribute, and this is then converted to "username at domain" as an LDAP-UserDN using the 'sites-enabled' section as follows

authorize {
        auth_log
        if (&User-Password) {
                # If !State and User-Password (PAP) then force LDAP
                update control {
                        Ldap-UserDN := "%{User-Name}@example.com"
                        Auth-Type := LDAP
                }
        }
}

>From here, authentication happens

authenticate {
        Auth-Type LDAP {
                # Attempt to authenticate with a direct bind
                ldap
        }
}

And this seems to succeed. (I was using files for authorization to perform the LDAP-Group match but changed to post-auth)

post-auth {
        update {
                &reply: += &session-state:
        }
        if (LDAP-Group == "ACCESS_2FA") {
                update reply {
                        Reply-Message = "OMG, it worked"
                }
        }
}

No problem, and now I can see it is trying to check that the LDAP-Group matches for the LDAP-UserDN username OR username at example.com

(From the modules-enabled/ldap) 

group {
   membership_filter = "(|(sAMAccountName=%{%{Stripped-User-Name}:-%{User-Name}}))"
}

Which seems to fail, as the group match is looking for CN=<fullname>,OU=Users,DC=example,DC=com. I can verify this by changing the membership_filter to

membership_filter = '(|(member=CN=Steve Phillips,OU=Users,DC=example, 
DC=com)(memberUid=%{%{Stripped-User-Name}:-%{User-Name}}))'

And this actually works (though is obviously not practical as no one logs in with their 'full name')

No problem, we are getting somewhere, I had read that we can also perform a lookup on the user object rather than the group object (filter = '(objectclass=user)') as this way I can match the account name using the sAMAccountName and then perform a match on memberOf object using the full "CN=<group>

Checking with ldapsearch, I worked out that the search (&(objectclass=user)(sAMAccountName=%{%{Stripped-User-Name}:-%{User-Name}})) 

Returns the user object, but when I try to implement this in the ldap module it seems to want to turn the search into..

Debug: (0)     Searching for user in group "ACCESS_2FA"
...
Debug: (0)       EXPAND (&(cn=ACCESS_2FA)(objectclass=user)(|(sAMAccountName=%{%{Stripped-User-Name}:-%{User-Name}})))
Debug: (0)          --> (&(cn=ACCESS_2FA)(objectclass=user)(|(sAMAccountName=user001)))

And the check fails again.

My ldap module is as follows

ldap {
        server = '10.0.0.50'
        basedn = "dc=example,dc=com"
        identity = 'CN=Steve Phillips,OU=Users,DC=example,DC=com'
        password = MyPassword

        user {
                basedn = "dc=example,dc=com"
                filter = "(sAMAccountName=%{%{Stripped-User-Name}:-%{User-Name}})"
        }
        group {
                name_attribute = cn
                scope = 'sub'
                basedn = "dc=example,dc=com"
                membership_filter = "(|(sAMAccountName=%{%{Stripped-User-Name}:-%{User-Name}}))"
                #membership_filter = '(|(member=CN=Steve Phillips,OU=Users,DC=example,DC=com)(memberUid=%{%{Stripped-User-Name}:-%{User-Name}}))'
                cacheable_name = 'yes'
                membership_attribute = 'memberOf'
                #membership_attribute = 'member'
                filter = '(objectclass=user)'
                chase_referrals = yes
                rebind = yes
        }
        edir_account_policy_check = 'no'

        options {
                chase_referrals = yes
                rebind = yes
                ldap_debug = 0x0028
        }
}

(I am also having issues with rebinding with this config but will work that later hence the identity section and the multiple 'rebind=yes' clauses)

Am I missing a directive to say 'please lookup the user objectClass not the group objectClass' to get it to lookup the group in the user object rather than the user in the group object? - I couldn’t see anything in the rlm_ldap comments.

Sorry if I'm missing something obvious, I'm currently looking through the source code to see if I can figure out the logic behind how this works but it's quite slow going ( 

Apologies for the long e-mail.

Thanks in advance!

-- 
Steve.

On 10/8/20, 10:20 pm, "Freeradius-Users on behalf of Alan DeKok" <freeradius-users-bounces+steve=focb.co.nz at lists.freeradius.org on behalf of aland at deployingradius.com> wrote:


    On Aug 10, 2020, at 4:07 AM, Steve Phillips <steve at focb.co.nz> wrote:
    > Freeradius version: 3.0.13 (installed via rpm on  rhel 7)

      Updated RPMs are available at http://packages.networkradius.com

    > I have a reasonably simple (to my mind) setup that for some reason doesn’t seem to exist on the internet after much fruitless searching.
    > 
    > In essence, I am performing PAP auth to free radius which then binds as the user to AD via LDAP and performs an authentication

      That's pretty common.

    > It then is supposed to return the groups the user is a member of and then I use the “files” directive to match a group and return a reply attribute

      LDAP doesn't return the groups.  You use "LDAP-Group = ..." to *match* a group.  There's a difference.

    > I’m now busy pulling my hair out trying to work out how to debug what’s going on in the background, as I am having amazingly bad luck trying to work out how the group filter works (and yes, I did read the ldap module comments and couldn’t work anything out from this, or the rlm_ldap wiki)

      The module now has some updated comments.  It describes how to convert the ldap module configuration into ldapsearch parameters:

    https://github.com/FreeRADIUS/freeradius-server/blob/v3.0.x/raddb/mods-available/ldap

    > Running radiusd -X gives some information that it is attempting to check groups but claims the user is not a group member

      Likely because the user is a member of a nested group.  There's special LDAP magic to get AD to search nested groups.  See the above link.

    > With some of these just hoping to get _anything_ to return (#groupmembership_filter = "(sAMAccountName=%{User-Name})")

      It doesn't "return" the list of groups.

    > About the only thing I’ve had success in plugging into ldapsearch was the “(sAMAccountName=<my username>)” hence the attempt at doing that because it DID actually return “memberOf” attributes.
    > 
    > I guess what I’m trying to do, is work out what I am supposed to plug into ldap search as every time I try it returns nothing.

      See the above link.

    > Is there a way to tell freeradius to print out what it thinks the various variables are? Like, %{Ldap-UserDN} I can see from the “sites-enabled” file as I can see it being set with..

      Yes, just expand them, and the debug output will print their values;

    	update control {
    		Tmp-String-0 := "%{control:LDAP-UserDN}"
    	}

    > Is there an easy to follow guide for ldapsearch that describes that the (|(&(<attribute>=<value>)(<attribute>=<value>))) bits even mean? (primarily the (|(&( bit, as I can do a single <attribute>=<value> Search and get that to work)

      See the lapsearch documentation for documentation on how ldapsearch works.

      Alan DeKok.


    -
    List info/subscribe/unsubscribe? See http://www.freeradius.org/list/users.html
-------------- next part --------------
A non-text attachment was scrubbed...
Name: smime.p7s
Type: application/pkcs7-signature
Size: 5033 bytes
Desc: not available
URL: <http://lists.freeradius.org/pipermail/freeradius-users/attachments/20200818/658c46bb/attachment-0001.bin>


More information about the Freeradius-Users mailing list