Issue 6688 - OpenLDAP 2.4.23 doesn't enforce ACLs on back-perl subordinate database
Summary: OpenLDAP 2.4.23 doesn't enforce ACLs on back-perl subordinate database
Status: VERIFIED SUSPENDED
Alias: None
Product: OpenLDAP
Classification: Unclassified
Component: slapd (show other issues)
Version: 2.4.23
Hardware: All All
: --- normal
Target Milestone: ---
Assignee: OpenLDAP project
URL:
Keywords:
Depends on:
Blocks:
 
Reported: 2010-10-28 15:12 UTC by mark.cave-ayland@siriusit.co.uk
Modified: 2021-08-03 17:59 UTC (History)
0 users

See Also:


Attachments

Note You need to log in before you can comment on or make changes to this issue.
Description mark.cave-ayland@siriusit.co.uk 2010-10-28 15:12:52 UTC
Full_Name: Mark Cave-Ayland
Version: 2.4.23
OS: Linux/Debian
URL: ftp://ftp.openldap.org/incoming/
Submission from: (NULL) (81.187.123.11)


Hi all,

We have an issue on one of our production systems whereby openldap is not
enforcing the ACLs on a back-perl subordinate database.

In this particular system, the membership of certain groups stored within LDAP
is determined by some customised logic in a Perl module which dynamically
generates LDAP objects with posixGroup/groupOfNames entries conditionally based
upon the values of existing LDAP attributes within the tree. However, since
these internal LDAP attribute lookups can be quite slow, we wish to hide them
from all but a small minority of bind DNs. Unfortunately what we are finding is
that the back-perl module is not respecting the ACLs in slapd.conf.

The following files can be used to reproduce this issue with openldap 2.4.23:

http://pastebin.siriusit.co.uk/perlacl/slapd.conf
http://pastebin.siriusit.co.uk/perlacl/perlacl.ldif
http://pastebin.siriusit.co.uk/perlacl/PerlACL.pm

The password for both the "cn=admin,dc=my-domain,dc=com" and the
"cn=restricted,dc=my-domain,dc=com" DNs is secret.

The ACLs in the above slapd.conf look like this:

access to dn.subtree="ou=perl,dc=my-domain,dc=com"
        by dn="cn=admin,dc=my-domain,dc=com" read
        by dn="cn=restricted,dc=my-domain,dc=com" none

access to dn.subtree="ou=hidden,dc=my-domain,dc=com"
        by dn="cn=admin,dc=my-domain,dc=com" read
        by dn="cn=restricted,dc=my-domain,dc=com" none

access to *
        by dn="cn=admin,dc=my-domain,dc=com" write
        by dn="cn=restricted,dc=my-domain,dc=com" read
        by * auth

Using these ACLs, I would expect that cn=admin should be able to read the whole
directory, whereas cn=restricted should not be able to see either the
"ou=hidden,dc=my-domain,dc=com" DN subtree nor the "ou=perl,dc=my-domain,dc=com"
DN subtree.

However, performing an LDAP search binding as cn=restricted gives the following
output:

build@zeno:~$ ldapsearch -LLL -H ldap://localhost:10389 -D
'cn=restricted,dc=my-domain,dc=com' -b 'dc=my-domain,dc=com' -xW
Enter LDAP Password:
dn: dc=my-domain,dc=com
objectClass: top
objectClass: dcObject
objectClass: organization
o:: bXlkb21haW4uY29tIA==
dc: my-domain

dn: ou=real,dc=my-domain,dc=com
objectClass: organizationalUnit
objectClass: top
ou: real

dn: ou=realtest1,ou=real,dc=my-domain,dc=com
objectClass: organizationalUnit
objectClass: top
ou: realtest1

dn: ou=realtest2,ou=real,dc=my-domain,dc=com
objectClass: organizationalUnit
objectClass: top
ou: realtest2

dn: ou=realtest3,ou=real,dc=my-domain,dc=com
objectClass: organizationalUnit
objectClass: top
ou: realtest3

dn: ou=realtest4,ou=real,dc=my-domain,dc=com
objectClass: organizationalUnit
objectClass: top
ou: realtest4

dn: ou=realtest5,ou=real,dc=my-domain,dc=com
objectClass: organizationalUnit
objectClass: top
ou: realtest5

dn: cn=restricted,dc=my-domain,dc=com
objectClass: simpleSecurityObject
objectClass: organizationalRole
cn: restricted
description: restricted user
userPassword:: e1NIQX01ZW42RzZNZXpScm9UM1hLcWtkUE9tWS9CZlE9

dn: cn=admin,dc=my-domain,dc=com
objectClass: simpleSecurityObject
objectClass: organizationalRole
cn:: YWRtaW4g
description: admin user
userPassword:: e1NIQX01ZW42RzZNZXpScm9UM1hLcWtkUE9tWS9CZlE9

dn: ou=perltest5,ou=perl,dc=my-domain,dc=com
objectClass: organizationalUnit
objectClass: top
ou: perltest5

dn: ou=perltest4,ou=perl,dc=my-domain,dc=com
objectClass: organizationalUnit
objectClass: top
ou: perltest4

dn: ou=perltest3,ou=perl,dc=my-domain,dc=com
objectClass: organizationalUnit
objectClass: top
ou: perltest3

dn: ou=perltest2,ou=perl,dc=my-domain,dc=com
objectClass: organizationalUnit
objectClass: top
ou: perltest2

dn: ou=perltest1,ou=perl,dc=my-domain,dc=com
objectClass: organizationalUnit
objectClass: top
ou: perltest1


In other words, the "ou=hidden,dc=my-domain,dc=com" subtree is correctly hidden
from the cn=restricted user, whereas the "ou=perl,dc=my-domain,dc=com" subtree
is not.
Comment 1 mark.cave-ayland@siriusit.co.uk 2010-10-29 16:34:37 UTC
Hi all,

An update on this bug report: with a modified slapd.conf and a small 
patch to the back-perl module, I can use the ACL mask to ensure that the 
perl search function doesn't get invoked if disallowed by the ACLs.

The patch works by creating a "fake" empty entry whose DN is the base of 
the search, and then passing this entry into access_allowed() using code 
borrowed from one of the other backends to either deny or allow access.

http://pastebin.siriusit.co.uk/perlacl/slapd2.conf
http://pastebin.siriusit.co.uk/perlacl/openldap-backperl-acls.patch

Is this something that could be considered for inclusion upstream or 
does it require more work?


ATB,

Mark.

-- 
Mark Cave-Ayland - Senior Technical Architect
PostgreSQL - PostGIS
Sirius Corporation plc - control through freedom
http://www.siriusit.co.uk
t: +44 870 608 0063

Sirius Labs: http://www.siriusit.co.uk/labs

Comment 2 Quanah Gibson-Mount 2011-06-08 23:21:20 UTC
--On Friday, October 29, 2010 4:35 PM +0000 mark.cave-ayland@siriusit.co.uk 
wrote:

> Hi all,
>
> An update on this bug report: with a modified slapd.conf and a small
> patch to the back-perl module, I can use the ACL mask to ensure that the
> perl search function doesn't get invoked if disallowed by the ACLs.
>
> The patch works by creating a "fake" empty entry whose DN is the base of
> the search, and then passing this entry into access_allowed() using code
> borrowed from one of the other backends to either deny or allow access.
>
> http://pastebin.siriusit.co.uk/perlacl/slapd2.conf
> http://pastebin.siriusit.co.uk/perlacl/openldap-backperl-acls.patch

These are not accessible.

--Quanah

--

Quanah Gibson-Mount
Sr. Member of Technical Staff
Zimbra, Inc
A Division of VMware, Inc.
--------------------
Zimbra ::  the leader in open source messaging and collaboration

Comment 3 mark.cave-ayland@siriusit.co.uk 2011-06-09 15:38:34 UTC
On 09/06/11 00:21, Quanah Gibson-Mount wrote:

>> An update on this bug report: with a modified slapd.conf and a small
>> patch to the back-perl module, I can use the ACL mask to ensure that the
>> perl search function doesn't get invoked if disallowed by the ACLs.
>>
>> The patch works by creating a "fake" empty entry whose DN is the base of
>> the search, and then passing this entry into access_allowed() using code
>> borrowed from one of the other backends to either deny or allow access.
>>
>> http://pastebin.siriusit.co.uk/perlacl/slapd2.conf
>> http://pastebin.siriusit.co.uk/perlacl/openldap-backperl-acls.patch
>
> These are not accessible.

Hi Quanah,

Ah yes indeed - that server was decommissioned last month. I've since 
reinstated the files from a backup onto a new server and updated DNS to 
point to it. Can you verify that you can now download them?


Many thanks,

Mark.

-- 
Mark Cave-Ayland - Senior Technical Architect
PostgreSQL - PostGIS
Sirius Corporation plc - control through freedom
http://www.siriusit.co.uk
t: +44 870 608 0063

Sirius Labs: http://www.siriusit.co.uk/labs

Comment 4 Howard Chu 2011-06-09 22:15:52 UTC
mark.cave-ayland@siriusit.co.uk wrote:
> On 09/06/11 00:21, Quanah Gibson-Mount wrote:
>
>>> An update on this bug report: with a modified slapd.conf and a small
>>> patch to the back-perl module, I can use the ACL mask to ensure that the
>>> perl search function doesn't get invoked if disallowed by the ACLs.
>>>
>>> The patch works by creating a "fake" empty entry whose DN is the base of
>>> the search, and then passing this entry into access_allowed() using code
>>> borrowed from one of the other backends to either deny or allow access.
>>>
>>> http://pastebin.siriusit.co.uk/perlacl/slapd2.conf
>>> http://pastebin.siriusit.co.uk/perlacl/openldap-backperl-acls.patch
>>
>> These are not accessible.
>
> Hi Quanah,
>
> Ah yes indeed - that server was decommissioned last month. I've since
> reinstated the files from a backup onto a new server and updated DNS to
> point to it. Can you verify that you can now download them?

Thanks, got it now. The patch leaks memory. I'll commit a fixed version of it 
shortly.

-- 
   -- Howard Chu
   CTO, Symas Corp.           http://www.symas.com
   Director, Highland Sun     http://highlandsun.com/hyc/
   Chief Architect, OpenLDAP  http://www.openldap.org/project/

Comment 5 Howard Chu 2011-06-09 22:29:17 UTC
mark.cave-ayland@siriusit.co.uk wrote:
> Full_Name: Mark Cave-Ayland
> Version: 2.4.23
> OS: Linux/Debian
> URL: ftp://ftp.openldap.org/incoming/
> Submission from: (NULL) (81.187.123.11)
>
>
> Hi all,
>
> We have an issue on one of our production systems whereby openldap is not
> enforcing the ACLs on a back-perl subordinate database.

Keep in mind, this is back-perl's documented behavior.

 >>>
ACCESS CONTROL
        The perl backend does not honor any of  the  access  control  semantics
        described  in  slapd.access(5);  all access control is delegated to the
        underlying PERL scripting.  Only read (=r) access to the entry  pseudo-
        attribute  and to the other attribute values of the entries returned by
        the search operation is honored, which is performed by the frontend.
<<<

Treating this as an enhancement request.

> In this particular system, the membership of certain groups stored within LDAP
> is determined by some customised logic in a Perl module which dynamically
> generates LDAP objects with posixGroup/groupOfNames entries conditionally based
> upon the values of existing LDAP attributes within the tree. However, since
> these internal LDAP attribute lookups can be quite slow, we wish to hide them
> from all but a small minority of bind DNs. Unfortunately what we are finding is
> that the back-perl module is not respecting the ACLs in slapd.conf.
>
> The following files can be used to reproduce this issue with openldap 2.4.23:
>
> http://pastebin.siriusit.co.uk/perlacl/slapd.conf
> http://pastebin.siriusit.co.uk/perlacl/perlacl.ldif
> http://pastebin.siriusit.co.uk/perlacl/PerlACL.pm
>
> The password for both the "cn=admin,dc=my-domain,dc=com" and the
> "cn=restricted,dc=my-domain,dc=com" DNs is secret.
>
> The ACLs in the above slapd.conf look like this:
>
> access to dn.subtree="ou=perl,dc=my-domain,dc=com"
>          by dn="cn=admin,dc=my-domain,dc=com" read
>          by dn="cn=restricted,dc=my-domain,dc=com" none
>
> access to dn.subtree="ou=hidden,dc=my-domain,dc=com"
>          by dn="cn=admin,dc=my-domain,dc=com" read
>          by dn="cn=restricted,dc=my-domain,dc=com" none
>
> access to *
>          by dn="cn=admin,dc=my-domain,dc=com" write
>          by dn="cn=restricted,dc=my-domain,dc=com" read
>          by * auth
>
> Using these ACLs, I would expect that cn=admin should be able to read the whole
> directory, whereas cn=restricted should not be able to see either the
> "ou=hidden,dc=my-domain,dc=com" DN subtree nor the "ou=perl,dc=my-domain,dc=com"
> DN subtree.
>
> However, performing an LDAP search binding as cn=restricted gives the following
> output:
>
> build@zeno:~$ ldapsearch -LLL -H ldap://localhost:10389 -D
> 'cn=restricted,dc=my-domain,dc=com' -b 'dc=my-domain,dc=com' -xW
> Enter LDAP Password:
> dn: dc=my-domain,dc=com
> objectClass: top
> objectClass: dcObject
> objectClass: organization
> o:: bXlkb21haW4uY29tIA==
> dc: my-domain
>
> dn: ou=real,dc=my-domain,dc=com
> objectClass: organizationalUnit
> objectClass: top
> ou: real
>
> dn: ou=realtest1,ou=real,dc=my-domain,dc=com
> objectClass: organizationalUnit
> objectClass: top
> ou: realtest1
>
> dn: ou=realtest2,ou=real,dc=my-domain,dc=com
> objectClass: organizationalUnit
> objectClass: top
> ou: realtest2
>
> dn: ou=realtest3,ou=real,dc=my-domain,dc=com
> objectClass: organizationalUnit
> objectClass: top
> ou: realtest3
>
> dn: ou=realtest4,ou=real,dc=my-domain,dc=com
> objectClass: organizationalUnit
> objectClass: top
> ou: realtest4
>
> dn: ou=realtest5,ou=real,dc=my-domain,dc=com
> objectClass: organizationalUnit
> objectClass: top
> ou: realtest5
>
> dn: cn=restricted,dc=my-domain,dc=com
> objectClass: simpleSecurityObject
> objectClass: organizationalRole
> cn: restricted
> description: restricted user
> userPassword:: e1NIQX01ZW42RzZNZXpScm9UM1hLcWtkUE9tWS9CZlE9
>
> dn: cn=admin,dc=my-domain,dc=com
> objectClass: simpleSecurityObject
> objectClass: organizationalRole
> cn:: YWRtaW4g
> description: admin user
> userPassword:: e1NIQX01ZW42RzZNZXpScm9UM1hLcWtkUE9tWS9CZlE9
>
> dn: ou=perltest5,ou=perl,dc=my-domain,dc=com
> objectClass: organizationalUnit
> objectClass: top
> ou: perltest5
>
> dn: ou=perltest4,ou=perl,dc=my-domain,dc=com
> objectClass: organizationalUnit
> objectClass: top
> ou: perltest4
>
> dn: ou=perltest3,ou=perl,dc=my-domain,dc=com
> objectClass: organizationalUnit
> objectClass: top
> ou: perltest3
>
> dn: ou=perltest2,ou=perl,dc=my-domain,dc=com
> objectClass: organizationalUnit
> objectClass: top
> ou: perltest2
>
> dn: ou=perltest1,ou=perl,dc=my-domain,dc=com
> objectClass: organizationalUnit
> objectClass: top
> ou: perltest1
>
>
> In other words, the "ou=hidden,dc=my-domain,dc=com" subtree is correctly hidden
> from the cn=restricted user, whereas the "ou=perl,dc=my-domain,dc=com" subtree
> is not.
>
>


-- 
   -- Howard Chu
   CTO, Symas Corp.           http://www.symas.com
   Director, Highland Sun     http://highlandsun.com/hyc/
   Chief Architect, OpenLDAP  http://www.openldap.org/project/

Comment 6 Howard Chu 2011-06-09 22:33:10 UTC
changed notes
changed state Open to Suspended
Comment 7 Howard Chu 2011-06-09 22:38:28 UTC
moved from Incoming to Software Enhancements
Comment 8 OpenLDAP project 2014-08-01 21:04:55 UTC
works as designed/documented