[Pkg-fedora-ds-maintainers] 389-ds-base: Changes to 'upstream'
Timo Aaltonen
tjaalton at moszumanska.debian.org
Mon Aug 29 07:56:43 UTC 2016
Makefile.am | 3
Makefile.in | 3
VERSION.sh | 2
dirsrvtests/create_test.py | 171 +
dirsrvtests/tests/suites/paged_results/paged_results_test.py | 1138 ++++++++++-
dirsrvtests/tests/suites/paged_results/sss_control.py | 127 +
dirsrvtests/tests/suites/password/pwp_history_test.py | 264 ++
dirsrvtests/tests/tickets/ticket1347760_test.py | 440 ++++
dirsrvtests/tests/tickets/ticket47462_test.py | 160 +
dirsrvtests/tests/tickets/ticket48109_test.py | 41
dirsrvtests/tests/tickets/ticket48497_test.py | 4
dirsrvtests/tests/tickets/ticket48745_test.py | 2
dirsrvtests/tests/tickets/ticket48746_test.py | 2
dirsrvtests/tests/tickets/ticket48755_test.py | 261 ++
dirsrvtests/tests/tickets/ticket48798_test.py | 141 +
dirsrvtests/tests/tickets/ticket48799_test.py | 170 +
dirsrvtests/tests/tickets/ticket48808_test.py | 337 +++
ldap/admin/src/logconv.pl | 60
ldap/admin/src/scripts/91reindex.pl.in | 103
ldap/admin/src/scripts/91subtreereindex.pl | 8
ldap/admin/src/scripts/repl-monitor.pl.in | 72
ldap/admin/src/scripts/setup-ds.res.in | 1
ldap/ldif/template-dse.ldif.in | 1
ldap/schema/01core389.ldif | 6
ldap/servers/plugins/replication/cl5_api.c | 171 -
ldap/servers/plugins/replication/cl5_clcache.c | 292 +-
ldap/servers/plugins/replication/cl5_clcache.h | 2
ldap/servers/plugins/replication/repl5.h | 14
ldap/servers/plugins/replication/repl5_inc_protocol.c | 106 -
ldap/servers/plugins/replication/repl5_plugins.c | 3
ldap/servers/plugins/replication/repl5_replica.c | 137 +
ldap/servers/plugins/replication/repl5_replica_config.c | 32
ldap/servers/plugins/replication/repl5_tot_protocol.c | 169 +
ldap/servers/plugins/replication/repl_globals.c | 1
ldap/servers/slapd/back-ldbm/back-ldbm.h | 6
ldap/servers/slapd/back-ldbm/dblayer.c | 5
ldap/servers/slapd/back-ldbm/dn2entry.c | 17
ldap/servers/slapd/back-ldbm/filterindex.c | 21
ldap/servers/slapd/back-ldbm/findentry.c | 139 +
ldap/servers/slapd/back-ldbm/idl_new.c | 87
ldap/servers/slapd/back-ldbm/import-threads.c | 7
ldap/servers/slapd/back-ldbm/index.c | 22
ldap/servers/slapd/back-ldbm/init.c | 2
ldap/servers/slapd/back-ldbm/ldbm_add.c | 21
ldap/servers/slapd/back-ldbm/ldbm_attr.c | 18
ldap/servers/slapd/back-ldbm/ldbm_bind.c | 11
ldap/servers/slapd/back-ldbm/ldbm_compare.c | 2
ldap/servers/slapd/back-ldbm/ldbm_delete.c | 9
ldap/servers/slapd/back-ldbm/ldbm_index_config.c | 6
ldap/servers/slapd/back-ldbm/ldbm_modify.c | 30
ldap/servers/slapd/back-ldbm/ldbm_modrdn.c | 17
ldap/servers/slapd/back-ldbm/ldbm_search.c | 35
ldap/servers/slapd/back-ldbm/misc.c | 3
ldap/servers/slapd/back-ldbm/proto-back-ldbm.h | 14
ldap/servers/slapd/back-ldbm/vlv_srch.c | 2
ldap/servers/slapd/bind.c | 126 -
ldap/servers/slapd/daemon.c | 226 --
ldap/servers/slapd/defbackend.c | 82
ldap/servers/slapd/entry.c | 4
ldap/servers/slapd/modify.c | 4
ldap/servers/slapd/opshared.c | 11
ldap/servers/slapd/pagedresults.c | 5
ldap/servers/slapd/pblock.c | 13
ldap/servers/slapd/proto-slap.h | 1
ldap/servers/slapd/pw.c | 33
ldap/servers/slapd/result.c | 27
ldap/servers/slapd/saslbind.c | 4
ldap/servers/slapd/schema.c | 66
ldap/servers/slapd/slap.h | 5
ldap/servers/slapd/slapi-plugin.h | 9
ldap/servers/slapd/slapi-private.h | 1
ldap/servers/slapd/ssl.c | 77
ldap/servers/slapd/task.c | 346 +++
ldap/servers/slapd/tools/ldclt/ldcltU.c | 2
man/man1/ldclt.1 | 2
man/man1/repl-monitor.1 | 58
wrappers/systemd.template.sysconfig | 3
77 files changed, 5054 insertions(+), 969 deletions(-)
New commits:
commit 695f0b73e9a4e6ce682526265fb1ec7f18ba7970
Author: Noriko Hosoi <nhosoi at redhat.com>
Date: Thu Aug 11 15:11:57 2016 -0700
bump version to 1.3.4.14
diff --git a/VERSION.sh b/VERSION.sh
index 42e3e7e..0309bf5 100644
--- a/VERSION.sh
+++ b/VERSION.sh
@@ -10,7 +10,7 @@ vendor="389 Project"
# PACKAGE_VERSION is constructed from these
VERSION_MAJOR=1
VERSION_MINOR=3
-VERSION_MAINT=4.13
+VERSION_MAINT=4.14
# if this is a PRERELEASE, set VERSION_PREREL
# otherwise, comment it out
# be sure to include the dot prefix in the prerel
commit c5521864b2996db2ae18f24ef34acb6aec92ad78
Author: Ludwig Krispenz <lkrispen at redhat.com>
Date: Thu Aug 4 11:45:49 2016 -0700
Bug 1347760 - CVE-2016-4992 389-ds-base: Information disclosure via repeated use of LDAP ADD operation, etc.
Description: do not overwrite rc used to decide if bind was successful.
When the bind is through ldapi/autobind, an entry does not exist to be
checked with slapi_check_account_lock. In that case, a variable rc is
not supposed to be modified which confuses the following code path.
Reviewed by nhosoi at redhat.com.
(cherry picked from commit caa351ae0cc81cbf2309a43c5f74b359cda152d0)
diff --git a/ldap/servers/slapd/bind.c b/ldap/servers/slapd/bind.c
index 8f5375a..399eaf7 100644
--- a/ldap/servers/slapd/bind.c
+++ b/ldap/servers/slapd/bind.c
@@ -775,10 +775,12 @@ do_bind( Slapi_PBlock *pb )
*/
if (!slapi_be_is_flag_set(be, SLAPI_BE_FLAG_REMOTE_DATA)) {
bind_target_entry = get_entry(pb, slapi_sdn_get_ndn(sdn));
- rc = slapi_check_account_lock(pb, bind_target_entry, pw_response_requested, 1, 1);
- if (1 == rc) { /* account is locked */
+ myrc = slapi_check_account_lock(pb, bind_target_entry, pw_response_requested, 1, 1);
+ if (1 == myrc) { /* account is locked */
+ rc = myrc;
goto account_locked;
}
+ myrc = 0;
}
if (!auto_bind) {
/*
commit e88a1ba32ec1b02f278e7febef6024f4e6bf9f55
Author: Noriko Hosoi <nhosoi at redhat.com>
Date: Tue Jul 26 18:08:38 2016 -0700
Bug 1347760 - CVE-2016-4992 389-ds-base: Information disclosure via repeated use of LDAP ADD operation, etc.
Description:
1. When an account is inactivated, the error UNWILLING_TO_PERFORM with
the inactivated message should be returned only when the bind is
successful.
2. When SASL bind fails, instead of returning the cause of the failure
directly to the client, but logging it in the access log.
https://bugzilla.redhat.com/show_bug.cgi?id=1347760
Reviewed by wibrown at redhat.com (Thank you, William!)
(cherry picked from commit b8767d510d11c7cbfede24daaae3348b9f028f47)
diff --git a/ldap/servers/slapd/bind.c b/ldap/servers/slapd/bind.c
index 6763fc3..8f5375a 100644
--- a/ldap/servers/slapd/bind.c
+++ b/ldap/servers/slapd/bind.c
@@ -720,25 +720,6 @@ do_bind( Slapi_PBlock *pb )
}
}
}
-
- /*
- * Is this account locked ?
- * could be locked through the account inactivation
- * or by the password policy
- *
- * rc=0: account not locked
- * rc=1: account locked, can not bind, result has been sent
- * rc!=0 and rc!=1: error. Result was not sent, lets be_bind
- * deal with it.
- *
- */
-
- /* get the entry now, so that we can give it to slapi_check_account_lock and reslimit_update_from_dn */
- if (! slapi_be_is_flag_set(be, SLAPI_BE_FLAG_REMOTE_DATA)) {
- bind_target_entry = get_entry(pb, slapi_sdn_get_ndn(sdn));
- rc = slapi_check_account_lock ( pb, bind_target_entry, pw_response_requested, 1, 1);
- }
-
slapi_pblock_set( pb, SLAPI_PLUGIN, be->be_database );
set_db_default_result_handlers(pb);
if ( (rc != 1) &&
@@ -777,6 +758,28 @@ do_bind( Slapi_PBlock *pb )
if ( rc == SLAPI_BIND_SUCCESS ) {
int myrc = 0;
+ /*
+ * The bind is successful.
+ * We can give it to slapi_check_account_lock and reslimit_update_from_dn.
+ */
+ /*
+ * Is this account locked ?
+ * could be locked through the account inactivation
+ * or by the password policy
+ *
+ * rc=0: account not locked
+ * rc=1: account locked, can not bind, result has been sent
+ * rc!=0 and rc!=1: error. Result was not sent, lets be_bind
+ * deal with it.
+ *
+ */
+ if (!slapi_be_is_flag_set(be, SLAPI_BE_FLAG_REMOTE_DATA)) {
+ bind_target_entry = get_entry(pb, slapi_sdn_get_ndn(sdn));
+ rc = slapi_check_account_lock(pb, bind_target_entry, pw_response_requested, 1, 1);
+ if (1 == rc) { /* account is locked */
+ goto account_locked;
+ }
+ }
if (!auto_bind) {
/*
* There could be a race that bind_target_entry was not added
@@ -787,13 +790,7 @@ do_bind( Slapi_PBlock *pb )
if (!slapi_be_is_flag_set(be, SLAPI_BE_FLAG_REMOTE_DATA) &&
!bind_target_entry) {
bind_target_entry = get_entry(pb, slapi_sdn_get_ndn(sdn));
- if (bind_target_entry) {
- myrc = slapi_check_account_lock(pb, bind_target_entry,
- pw_response_requested, 1, 1);
- if (1 == myrc) { /* account is locked */
- goto account_locked;
- }
- } else {
+ if (!bind_target_entry) {
slapi_pblock_set(pb, SLAPI_PB_RESULT_TEXT, "No such entry");
send_ldap_result(pb, LDAP_INVALID_CREDENTIALS, NULL, "", 0, NULL);
goto free_and_return;
diff --git a/ldap/servers/slapd/saslbind.c b/ldap/servers/slapd/saslbind.c
index 76294ac..d56f0ed 100644
--- a/ldap/servers/slapd/saslbind.c
+++ b/ldap/servers/slapd/saslbind.c
@@ -1049,8 +1049,8 @@ sasl_check_result:
errstr = sasl_errdetail(sasl_conn);
PR_ExitMonitor(pb->pb_conn->c_mutex); /* BIG LOCK */
- send_ldap_result(pb, LDAP_INVALID_CREDENTIALS, NULL,
- (char*)errstr, 0, NULL);
+ slapi_pblock_set(pb, SLAPI_PB_RESULT_TEXT, (void *)errstr);
+ send_ldap_result(pb, LDAP_INVALID_CREDENTIALS, NULL, NULL, 0, NULL);
break;
}
commit 5e810f82fd36d606f48d9a1218d2b8937bdf04ef
Author: Mark Reynolds <mreynolds at redhat.com>
Date: Tue Jul 26 15:31:32 2016 -0400
Ticket 48935 - Update dirsrv.systemd file
BUg Description: Two issues here. First the default system startup timeout
is set to 1 minute 30 seconds. But in the start-dirsrv script
it attempts to use a 10 minute timeout.
Second, starting in F23 systemd does not work well with valgrind.
systemd does not accept the notification once the DS starts.
So the start command actually fails after it times out.
Fix Description: For the first issue set the system startup timeout to match the
start-dirsrv script by setting:
TimeoutStartSecs=10min
Second, allow valgrind's startup success message to be
recognized/accepted we set:
NotifyAccess=all
https://fedorahosted.org/389/ticket/48935
Reviewed by: nhosoi(Thanks!)
(cherry picked from commit ce44176803aa52ab8001113136bfbb7ff4a50972)
diff --git a/wrappers/systemd.template.sysconfig b/wrappers/systemd.template.sysconfig
index d88bdcd..e653c86 100644
--- a/wrappers/systemd.template.sysconfig
+++ b/wrappers/systemd.template.sysconfig
@@ -1,3 +1,6 @@
[Service]
+TimeoutStartSec=10m
+NotifyAccess=all
+
# uncomment this line to raise the file descriptor limit
# LimitNOFILE=8192
commit c8e7fc567ca9b00969e3911bf3aa6245ebdffe5b
Author: Mark Reynolds <mreynolds at redhat.com>
Date: Tue Jul 19 18:28:06 2016 -0400
Ticket 48930 - Paged result search can hang the server
Bug Description: If a pages result has sent all its entry it's possible that
the connection lock/monitor is not exited. This can lead
to a deadlock when a new connection comes in.
Fix Description: Move the monitor exit to the proper location, and also set
the result to success if all the entries have been sent.
https://fedorahosted.org/389/ticket/48930
Reviewed by: nhosoi(Thanks!)
(cherry picked from commit bff1dd433f5de807ded1114e5961d66e2c0494e2)
diff --git a/ldap/servers/slapd/opshared.c b/ldap/servers/slapd/opshared.c
index 84e4c71..93334a1 100644
--- a/ldap/servers/slapd/opshared.c
+++ b/ldap/servers/slapd/opshared.c
@@ -694,11 +694,12 @@ op_shared_search (Slapi_PBlock *pb, int send_result)
/* search result could be reset in the backend/dse */
slapi_pblock_get(pb, SLAPI_SEARCH_RESULT_SET, &sr);
pagedresults_set_search_result(pb->pb_conn, operation, sr, 1/*locked*/, pr_idx);
- PR_ExitMonitor(pb->pb_conn->c_mutex);
}
} else {
pr_stat = PAGEDRESULTS_SEARCH_END;
+ rc = LDAP_SUCCESS;
}
+ PR_ExitMonitor(pb->pb_conn->c_mutex);
pagedresults_unlock(pb->pb_conn, pr_idx);
if ((PAGEDRESULTS_SEARCH_END == pr_stat) || (0 == pnentries)) {
commit 7738a00e7334c191421be274bae3ada964e4279a
Author: Simon Pichugin <spichugi at redhat.com>
Date: Thu Jul 14 14:14:12 2016 +0200
Ticket 48752 - Add CI test
Description: Test that search with simple paged result control works
properly on two suffixes (one is parent of the other) and the logs
show right pr_cookie values.
https://fedorahosted.org/389/ticket/48752
Reviewed by: mreynolds (Thanks!)
(cherry picked from commit fc97900fc6637d888a103c69adbf303f6e78e233)
diff --git a/dirsrvtests/tests/suites/paged_results/paged_results_test.py b/dirsrvtests/tests/suites/paged_results/paged_results_test.py
index 6fec5c7..2248fd2 100644
--- a/dirsrvtests/tests/suites/paged_results/paged_results_test.py
+++ b/dirsrvtests/tests/suites/paged_results/paged_results_test.py
@@ -12,8 +12,7 @@ import logging
import pytest
from random import sample
from ldap.controls import SimplePagedResultsControl
-from lib389 import DirSrv, Entry, tools, tasks
-from lib389.tools import DirSrvTools
+from lib389 import DirSrv, Entry
from lib389._constants import *
from lib389.properties import *
from lib389.tasks import *
@@ -24,8 +23,14 @@ logging.getLogger(__name__).setLevel(logging.DEBUG)
log = logging.getLogger(__name__)
TEST_USER_NAME = 'simplepaged_test'
-TEST_USER_DN = 'uid=%s,%s' % (TEST_USER_NAME, DEFAULT_SUFFIX)
+TEST_USER_DN = 'uid={},{}'.format(TEST_USER_NAME, DEFAULT_SUFFIX)
TEST_USER_PWD = 'simplepaged_test'
+NEW_SUFFIX_1_NAME = 'test_parent'
+NEW_SUFFIX_1 = 'o={}'.format(NEW_SUFFIX_1_NAME)
+NEW_SUFFIX_2_NAME = 'child'
+NEW_SUFFIX_2 = 'ou={},{}'.format(NEW_SUFFIX_2_NAME, NEW_SUFFIX_1)
+NEW_BACKEND_1 = 'parent_base'
+NEW_BACKEND_2 = 'child_base'
class TopologyStandalone(object):
@@ -62,9 +67,10 @@ def topology(request):
@pytest.fixture(scope="module")
-def test_user(topology):
+def test_user(topology, request):
"""User for binding operation"""
+ log.info('Adding user {}'.format(TEST_USER_DN))
try:
topology.standalone.add_s(Entry((TEST_USER_DN, {
'objectclass': 'top person'.split(),
@@ -81,8 +87,63 @@ def test_user(topology):
e.message['desc']))
raise e
+ def fin():
+ log.info('Deleting user {}'.format(TEST_USER_DN))
+ topology.standalone.delete_s(TEST_USER_DN)
+ request.addfinalizer(fin)
+
+
+ at pytest.fixture(scope="module")
+def new_suffixes(topology):
+ """Add two suffixes with backends, one is a parent
+ of the another
+ """
+
+ log.info('Adding suffix:{} and backend: {}'.format(NEW_SUFFIX_1, NEW_BACKEND_1))
+ topology.standalone.backend.create(NEW_SUFFIX_1,
+ {BACKEND_NAME: NEW_BACKEND_1})
+ topology.standalone.mappingtree.create(NEW_SUFFIX_1,
+ bename=NEW_BACKEND_1)
+ try:
+ topology.standalone.add_s(Entry((NEW_SUFFIX_1, {
+ 'objectclass': 'top',
+ 'objectclass': 'organization',
+ 'o': NEW_SUFFIX_1_NAME
+ })))
+ except ldap.LDAPError as e:
+ log.error('Failed to add suffix ({}): error ({})'.format(NEW_SUFFIX_1,
+ e.message['desc']))
+ raise
-def add_users(topology, users_num):
+ log.info('Adding suffix:{} and backend: {}'.format(NEW_SUFFIX_2, NEW_BACKEND_2))
+ topology.standalone.backend.create(NEW_SUFFIX_2,
+ {BACKEND_NAME: NEW_BACKEND_2})
+ topology.standalone.mappingtree.create(NEW_SUFFIX_2,
+ bename=NEW_BACKEND_2,
+ parent=NEW_SUFFIX_1)
+
+ try:
+ topology.standalone.add_s(Entry((NEW_SUFFIX_2, {
+ 'objectclass': 'top',
+ 'objectclass': 'organizationalunit',
+ 'ou': NEW_SUFFIX_2_NAME
+ })))
+ except ldap.LDAPError as e:
+ log.error('Failed to add suffix ({}): error ({})'.format(NEW_SUFFIX_2,
+ e.message['desc']))
+ raise
+
+ log.info('Adding ACI to allow our test user to search')
+ ACI_TARGET = '(targetattr != "userPassword || aci")'
+ ACI_ALLOW = '(version 3.0; acl "Enable anonymous access";allow (read, search, compare)'
+ ACI_SUBJECT = '(userdn = "ldap:///anyone");)'
+ ACI_BODY = ACI_TARGET + ACI_ALLOW + ACI_SUBJECT
+
+ mod = [(ldap.MOD_ADD, 'aci', ACI_BODY)]
+ topology.standalone.modify_s(NEW_SUFFIX_1, mod)
+
+
+def add_users(topology, users_num, suffix):
"""Add users to the default suffix
Return the list of added user DNs.
@@ -93,7 +154,7 @@ def add_users(topology, users_num):
for num in sample(range(1000), users_num):
num_ran = int(round(num))
USER_NAME = 'test%05d' % num_ran
- USER_DN = 'uid=%s,%s' % (USER_NAME, DEFAULT_SUFFIX)
+ USER_DN = 'uid=%s,%s' % (USER_NAME, suffix)
users_list.append(USER_DN)
try:
topology.standalone.add_s(Entry((USER_DN, {
@@ -154,7 +215,7 @@ def change_conf_attr(topology, suffix, attr_name, attr_value):
return attr_value_bck
-def paged_search(topology, controls, search_flt, searchreq_attrlist):
+def paged_search(topology, suffix, controls, search_flt, searchreq_attrlist):
"""Search at the DEFAULT_SUFFIX with ldap.SCOPE_SUBTREE
using Simple Paged Control(should the first item in the
list controls.
@@ -167,7 +228,7 @@ def paged_search(topology, controls, search_flt, searchreq_attrlist):
pctrls = []
all_results = []
req_ctrl = controls[0]
- msgid = topology.standalone.search_ext(DEFAULT_SUFFIX,
+ msgid = topology.standalone.search_ext(suffix,
ldap.SCOPE_SUBTREE,
search_flt,
searchreq_attrlist,
@@ -187,7 +248,7 @@ def paged_search(topology, controls, search_flt, searchreq_attrlist):
if pctrls[0].cookie:
# Copy cookie from response control to request control
req_ctrl.cookie = pctrls[0].cookie
- msgid = topology.standalone.search_ext(DEFAULT_SUFFIX,
+ msgid = topology.standalone.search_ext(suffix,
ldap.SCOPE_SUBTREE,
search_flt,
searchreq_attrlist,
@@ -219,7 +280,7 @@ def test_search_success(topology, test_user, page_size, users_num):
@Assert: All users should be found
"""
- users_list = add_users(topology, users_num)
+ users_list = add_users(topology, users_num, DEFAULT_SUFFIX)
search_flt = r'(uid=test*)'
searchreq_attrlist = ['dn', 'sn']
@@ -230,7 +291,7 @@ def test_search_success(topology, test_user, page_size, users_num):
log.info('Create simple paged results control instance')
req_ctrl = SimplePagedResultsControl(True, size=page_size, cookie='')
- all_results = paged_search(topology, [req_ctrl],
+ all_results = paged_search(topology, DEFAULT_SUFFIX, [req_ctrl],
search_flt, searchreq_attrlist)
log.info('%d results' % len(all_results))
@@ -272,7 +333,7 @@ def test_search_limits_fail(topology, test_user, page_size, users_num,
@Assert: Should fail with appropriate exception
"""
- users_list = add_users(topology, users_num)
+ users_list = add_users(topology, users_num, DEFAULT_SUFFIX)
attr_value_bck = change_conf_attr(topology, suffix, attr_name, attr_value)
conf_param_dict = {attr_name: attr_value}
search_flt = r'(uid=test*)'
@@ -362,7 +423,7 @@ def test_search_sort_success(topology, test_user):
users_num = 50
page_size = 5
- users_list = add_users(topology, users_num)
+ users_list = add_users(topology, users_num, DEFAULT_SUFFIX)
search_flt = r'(uid=test*)'
searchreq_attrlist = ['dn', 'sn']
@@ -377,7 +438,7 @@ def test_search_sort_success(topology, test_user):
log.info('Initiate ldapsearch with created control instance')
log.info('Collect data with sorting')
controls = [req_ctrl, sort_ctrl]
- results_sorted = paged_search(topology, controls,
+ results_sorted = paged_search(topology, DEFAULT_SUFFIX, controls,
search_flt, searchreq_attrlist)
log.info('Substring numbers from user DNs')
@@ -411,7 +472,7 @@ def test_search_abandon(topology, test_user):
users_num = 10
page_size = 2
- users_list = add_users(topology, users_num)
+ users_list = add_users(topology, users_num, DEFAULT_SUFFIX)
search_flt = r'(uid=test*)'
searchreq_attrlist = ['dn', 'sn']
@@ -464,7 +525,7 @@ def test_search_with_timelimit(topology, test_user):
users_num = 100
page_size = 50
timelimit = 5
- users_list = add_users(topology, users_num)
+ users_list = add_users(topology, users_num, DEFAULT_SUFFIX)
search_flt = r'(uid=test*)'
searchreq_attrlist = ['dn', 'sn']
@@ -547,7 +608,7 @@ def test_search_dns_ip_aci(topology, test_user, aci_subject):
users_num = 100
page_size = 5
- users_list = add_users(topology, users_num)
+ users_list = add_users(topology, users_num, DEFAULT_SUFFIX)
search_flt = r'(uid=test*)'
searchreq_attrlist = ['dn', 'sn']
@@ -578,7 +639,7 @@ def test_search_dns_ip_aci(topology, test_user, aci_subject):
log.info('Initiate three searches with a paged results control')
for ii in range(3):
log.info('%d search' % (ii + 1))
- all_results = paged_search(topology, controls,
+ all_results = paged_search(topology, DEFAULT_SUFFIX, controls,
search_flt, searchreq_attrlist)
log.info('%d results' % len(all_results))
assert len(all_results) == len(users_list)
@@ -618,7 +679,7 @@ def test_search_multiple_paging(topology, test_user):
users_num = 100
page_size = 30
- users_list = add_users(topology, users_num)
+ users_list = add_users(topology, users_num, DEFAULT_SUFFIX)
search_flt = r'(uid=test*)'
searchreq_attrlist = ['dn', 'sn']
@@ -679,7 +740,7 @@ def test_search_invalid_cookie(topology, test_user, invalid_cookie):
users_num = 100
page_size = 50
- users_list = add_users(topology, users_num)
+ users_list = add_users(topology, users_num, DEFAULT_SUFFIX)
search_flt = r'(uid=test*)'
searchreq_attrlist = ['dn', 'sn']
@@ -732,7 +793,7 @@ def test_search_abandon_with_zero_size(topology, test_user):
users_num = 10
page_size = 0
- users_list = add_users(topology, users_num)
+ users_list = add_users(topology, users_num, DEFAULT_SUFFIX)
search_flt = r'(uid=test*)'
searchreq_attrlist = ['dn', 'sn']
@@ -787,7 +848,7 @@ def test_search_pagedsizelimit_success(topology, test_user):
attr_value = '20'
attr_value_bck = change_conf_attr(topology, DN_CONFIG,
attr_name, attr_value)
- users_list = add_users(topology, users_num)
+ users_list = add_users(topology, users_num, DEFAULT_SUFFIX)
search_flt = r'(uid=test*)'
searchreq_attrlist = ['dn', 'sn']
@@ -799,7 +860,7 @@ def test_search_pagedsizelimit_success(topology, test_user):
req_ctrl = SimplePagedResultsControl(True, size=page_size, cookie='')
controls = [req_ctrl]
- all_results = paged_search(topology, controls,
+ all_results = paged_search(topology, DEFAULT_SUFFIX, controls,
search_flt, searchreq_attrlist)
log.info('%d results' % len(all_results))
@@ -846,7 +907,7 @@ def test_search_nspagedsizelimit(topology, test_user,
users_num = 10
page_size = 10
- users_list = add_users(topology, users_num)
+ users_list = add_users(topology, users_num, DEFAULT_SUFFIX)
search_flt = r'(uid=test*)'
searchreq_attrlist = ['dn', 'sn']
conf_attr_bck = change_conf_attr(topology, DN_CONFIG,
@@ -865,11 +926,11 @@ def test_search_nspagedsizelimit(topology, test_user,
if expected_rs == ldap.SIZELIMIT_EXCEEDED:
log.info('Expect to fail with SIZELIMIT_EXCEEDED')
with pytest.raises(expected_rs):
- all_results = paged_search(topology, controls,
+ all_results = paged_search(topology, DEFAULT_SUFFIX, controls,
search_flt, searchreq_attrlist)
elif expected_rs == 'PASS':
log.info('Expect to pass')
- all_results = paged_search(topology, controls,
+ all_results = paged_search(topology, DEFAULT_SUFFIX, controls,
search_flt, searchreq_attrlist)
log.info('%d results' % len(all_results))
assert len(all_results) == len(users_list)
@@ -917,7 +978,7 @@ def test_search_paged_limits(topology, test_user, conf_attr_values, expected_rs)
users_num = 101
page_size = 10
- users_list = add_users(topology, users_num)
+ users_list = add_users(topology, users_num, DEFAULT_SUFFIX)
search_flt = r'(uid=test*)'
searchreq_attrlist = ['dn', 'sn']
size_attr_bck = change_conf_attr(topology, DN_CONFIG,
@@ -940,11 +1001,11 @@ def test_search_paged_limits(topology, test_user, conf_attr_values, expected_rs)
if expected_rs == ldap.ADMINLIMIT_EXCEEDED:
log.info('Expect to fail with ADMINLIMIT_EXCEEDED')
with pytest.raises(expected_rs):
- all_results = paged_search(topology, controls,
+ all_results = paged_search(topology, DEFAULT_SUFFIX, controls,
search_flt, searchreq_attrlist)
elif expected_rs == 'PASS':
log.info('Expect to pass')
- all_results = paged_search(topology, controls,
+ all_results = paged_search(topology, DEFAULT_SUFFIX, controls,
search_flt, searchreq_attrlist)
log.info('%d results' % len(all_results))
assert len(all_results) == len(users_list)
@@ -996,7 +1057,7 @@ def test_search_paged_user_limits(topology, test_user, conf_attr_values, expecte
users_num = 101
page_size = 10
- users_list = add_users(topology, users_num)
+ users_list = add_users(topology, users_num, DEFAULT_SUFFIX)
search_flt = r'(uid=test*)'
searchreq_attrlist = ['dn', 'sn']
lookthrough_attr_bck = change_conf_attr(topology, 'cn=config,%s' % DN_LDBM,
@@ -1019,11 +1080,11 @@ def test_search_paged_user_limits(topology, test_user, conf_attr_values, expecte
if expected_rs == ldap.ADMINLIMIT_EXCEEDED:
log.info('Expect to fail with ADMINLIMIT_EXCEEDED')
with pytest.raises(expected_rs):
- all_results = paged_search(topology, controls,
+ all_results = paged_search(topology, DEFAULT_SUFFIX, controls,
search_flt, searchreq_attrlist)
elif expected_rs == 'PASS':
log.info('Expect to pass')
- all_results = paged_search(topology, controls,
+ all_results = paged_search(topology, DEFAULT_SUFFIX, controls,
search_flt, searchreq_attrlist)
log.info('%d results' % len(all_results))
assert len(all_results) == len(users_list)
@@ -1041,6 +1102,62 @@ def test_search_paged_user_limits(topology, test_user, conf_attr_values, expecte
'nsPagedLookthroughLimit', user_lookthrough_attr_bck)
+def test_multi_suffix_search(topology, test_user, new_suffixes):
+ """Verify that page result search returns empty cookie
+ if there is no returned entry.
+
+ :Feature: Simple paged results
+
+ :Setup: Standalone instance, test user for binding,
+ two suffixes with backends, one is inserted into another,
+ 10 users for the search base within each suffix
+
+ :Steps: 1. Bind as test user
+ 2. Search through all 20 added users with a simple paged control
+ using page_size = 4
+ 3. Wait some time logs to be updated
+ 3. Check access log
+
+ :Assert: All users should be found, the access log should contain
+ the pr_cookie for each page request and it should be equal 0,
+ except the last one should be equal -1
+ """
+
+ search_flt = r'(uid=test*)'
+ searchreq_attrlist = ['dn', 'sn']
+ page_size = 4
+ users_num = 20
+
+ users_list_1 = add_users(topology, users_num / 2, NEW_SUFFIX_1)
+ users_list_2 = add_users(topology, users_num / 2, NEW_SUFFIX_2)
+
+ try:
+ log.info('Set DM bind')
+ topology.standalone.simple_bind_s(DN_DM, PASSWORD)
+
+ log.info('Create simple paged results control instance')
+ req_ctrl = SimplePagedResultsControl(True, size=page_size, cookie='')
+
+ all_results = paged_search(topology, NEW_SUFFIX_1, [req_ctrl],
+ search_flt, searchreq_attrlist)
+
+ log.info('{} results'.format(len(all_results)))
+ assert len(all_results) == users_num
+
+ log.info('Waiting for logs to be updated')
+ time.sleep(30)
+ access_log_lines = topology.standalone.ds_access_log.match('.*pr_cookie=.*')
+ pr_cookie_list = ([line.rsplit('=', 1)[-1] for line in access_log_lines])
+ pr_cookie_list = [int(pr_cookie) for pr_cookie in pr_cookie_list]
+ log.info('Assert that last pr_cookie == -1 and others pr_cookie == 0')
+ assert all((pr_cookie == 0 for pr_cookie in pr_cookie_list[0:-1]))
+ assert pr_cookie_list[-1] == -1
+ finally:
+ log.info('Remove added users')
+ del_users(topology, users_list_1)
+ del_users(topology, users_list_2)
+
+
if __name__ == '__main__':
# Run isolated
# -s for DEBUG mode
commit 42fcf976d9c8bc223a9c7a6c0a0857b3fd9463e6
Author: Noriko Hosoi <nhosoi at redhat.com>
Date: Fri Jul 15 14:19:16 2016 -0700
bump version to 1.3.4.13
diff --git a/VERSION.sh b/VERSION.sh
index f4a1fda..42e3e7e 100644
--- a/VERSION.sh
+++ b/VERSION.sh
@@ -10,7 +10,7 @@ vendor="389 Project"
# PACKAGE_VERSION is constructed from these
VERSION_MAJOR=1
VERSION_MINOR=3
-VERSION_MAINT=4.12
+VERSION_MAINT=4.13
# if this is a PRERELEASE, set VERSION_PREREL
# otherwise, comment it out
# be sure to include the dot prefix in the prerel
commit b338616f66d4d51536b94edd9ae7f0dd10fbebd0
Author: Noriko Hosoi <nhosoi at redhat.com>
Date: Tue Jul 12 14:33:17 2016 -0700
Bug 1347760 - CI test: test case for bug 1347760
Description: Information disclosure via repeated use of LDAP ADD operation, etc.
(cherry picked from commit 8bfe4bbf3d61d4eaf4abac6515c95b38ac39b195)
diff --git a/dirsrvtests/tests/tickets/ticket1347760_test.py b/dirsrvtests/tests/tickets/ticket1347760_test.py
new file mode 100644
index 0000000..d2e9e37
--- /dev/null
+++ b/dirsrvtests/tests/tickets/ticket1347760_test.py
@@ -0,0 +1,440 @@
+# --- BEGIN COPYRIGHT BLOCK ---
+# Copyright (C) 2016 Red Hat, Inc.
+# All rights reserved.
+#
+# License: GPL (version 3 or any later version).
+# See LICENSE for details.
+# --- END COPYRIGHT BLOCK ---
+#
+import os
+import sys
+import time
+import ldap
+import logging
+import pytest
+from lib389 import DirSrv, Entry, tools, tasks
+from lib389.tools import DirSrvTools
+from lib389._constants import *
+from lib389.properties import *
+from lib389.tasks import *
+from lib389.utils import *
+
+logging.getLogger(__name__).setLevel(logging.DEBUG)
+log = logging.getLogger(__name__)
+
+installation1_prefix = None
+
+CONFIG_DN = 'cn=config'
+BOU = 'BOU'
+BINDOU = 'ou=%s,%s' % (BOU, DEFAULT_SUFFIX)
+BUID = 'buser123'
+TUID = 'tuser0'
+BINDDN = 'uid=%s,%s' % (BUID, BINDOU)
+BINDPW = BUID
+TESTDN = 'uid=%s,ou=people,%s' % (TUID, DEFAULT_SUFFIX)
+TESTPW = TUID
+BOGUSDN = 'uid=bogus,%s' % DEFAULT_SUFFIX
+BOGUSDN2 = 'uid=bogus,ou=people,%s' % DEFAULT_SUFFIX
+BOGUSSUFFIX = 'uid=bogus,ou=people,dc=bogus'
+GROUPOU = 'ou=groups,%s' % DEFAULT_SUFFIX
+BOGUSOU = 'ou=OU,%s' % DEFAULT_SUFFIX
+
+logging.getLogger(__name__).setLevel(logging.DEBUG)
+log = logging.getLogger(__name__)
+
+installation1_prefix = None
+
+class TopologyStandalone(object):
+ def __init__(self, standalone):
+ standalone.open()
+ self.standalone = standalone
+
+
+ at pytest.fixture(scope="module")
+def topology(request):
+ global installation1_prefix
+ if installation1_prefix:
+ args_instance[SER_DEPLOYED_DIR] = installation1_prefix
+
+ # Creating standalone instance ...
+ standalone = DirSrv(verbose=False)
+ args_instance[SER_HOST] = HOST_STANDALONE
+ args_instance[SER_PORT] = PORT_STANDALONE
+ args_instance[SER_SERVERID_PROP] = SERVERID_STANDALONE
+ args_instance[SER_CREATION_SUFFIX] = DEFAULT_SUFFIX
+ args_standalone = args_instance.copy()
+ standalone.allocate(args_standalone)
+ instance_standalone = standalone.exists()
+ if instance_standalone:
+ standalone.delete()
+ standalone.create()
+ standalone.open()
+
+ # Delete each instance in the end
+# def fin():
+# standalone.delete()
+# request.addfinalizer(fin)
+
+ # Clear out the tmp dir
+ standalone.clearTmpDir(__file__)
+
+ return TopologyStandalone(standalone)
+
+def pattern_accesslog(file, log_pattern):
+ try:
+ pattern_accesslog.last_pos += 1
+ except AttributeError:
+ pattern_accesslog.last_pos = 0
+
+ found = None
+ file.seek(pattern_accesslog.last_pos)
+
+ # Use a while true iteration because 'for line in file: hit a
+ # python bug that break file.tell()
+ while True:
+ line = file.readline()
+ found = log_pattern.search(line)
+ if ((line == '') or (found)):
+ break
+
+ pattern_accesslog.last_pos = file.tell()
+ if found:
+ return line
+ else:
+ return None
+
+def check_op_result(server, op, dn, superior, exists, rc):
+ targetdn = dn
+ if op == 'search':
+ if exists:
+ opstr = 'Searching existing entry'
+ else:
+ opstr = 'Searching non-existing entry'
+ elif op == 'add':
+ if exists:
+ opstr = 'Adding existing entry'
+ else:
+ opstr = 'Adding non-existing entry'
+ elif op == 'modify':
+ if exists:
+ opstr = 'Modifying existing entry'
+ else:
+ opstr = 'Modifying non-existing entry'
+ elif op == 'modrdn':
+ if superior != None:
+ targetdn = superior
+ if exists:
+ opstr = 'Moving to existing superior'
+ else:
+ opstr = 'Moving to non-existing superior'
+ else:
+ if exists:
+ opstr = 'Renaming existing entry'
+ else:
+ opstr = 'Renaming non-existing entry'
+ elif op == 'delete':
+ if exists:
+ opstr = 'Deleting existing entry'
+ else:
+ opstr = 'Deleting non-existing entry'
+
+ if ldap.SUCCESS == rc:
+ expstr = 'be ok'
+ else:
+ expstr = 'fail with %s' % rc.__name__
+
+ log.info('%s %s, which should %s.' % (opstr, targetdn, expstr))
+ hit = 0
+ try:
+ if op == 'search':
+ centry = server.search_s(dn, ldap.SCOPE_BASE, 'objectclass=*')
+ elif op == 'add':
+ server.add_s(Entry((dn, {'objectclass': 'top extensibleObject'.split(),
+ 'cn': 'test entry'})))
+ elif op == 'modify':
+ server.modify_s(dn, [(ldap.MOD_REPLACE, 'description', 'test')])
+ elif op == 'modrdn':
+ if superior != None:
+ server.rename_s(dn, 'uid=new', newsuperior=superior, delold=1)
+ else:
+ server.rename_s(dn, 'uid=new', delold=1)
+ elif op == 'delete':
+ server.delete_s(dn)
+ else:
+ log.fatal('Unknown operation %s' % op)
+ assert False
+ except ldap.LDAPError as e:
+ hit = 1
+ log.info("Exception (expected): %s" % type(e).__name__)
+ log.info('Desc ' + e.message['desc'])
+ assert isinstance(e, rc)
+ if e.message.has_key('matched'):
+ log.info('Matched is returned: ' + e.message['matched'])
+ if rc != ldap.NO_SUCH_OBJECT:
+ assert False
+
+ if ldap.SUCCESS == rc:
+ if op == 'search':
+ log.info('Search should return none')
+ assert len(centry) == 0
+ else:
+ if 0 == hit:
+ log.info('Expected to fail with %s, but passed' % rc.__name__)
+ assert False
+
+ log.info('PASSED\n')
+
+def test_ticket1347760(topology):
+ """
+ Prevent revealing the entry info to whom has no access rights.
+ """
+ log.info('Testing Bug 1347760 - Information disclosure via repeated use of LDAP ADD operation, etc.')
+
+ log.info('Disabling accesslog logbuffering')
+ topology.standalone.modify_s(CONFIG_DN, [(ldap.MOD_REPLACE, 'nsslapd-accesslog-logbuffering', 'off')])
+
+ log.info('Bind as {%s,%s}' % (DN_DM, PASSWORD))
+ topology.standalone.simple_bind_s(DN_DM, PASSWORD)
+
+ log.info('Adding ou=%s a bind user belongs to.' % BOU)
+ topology.standalone.add_s(Entry((BINDOU, {
+ 'objectclass': 'top organizationalunit'.split(),
+ 'ou': BOU})))
+
+ log.info('Adding a bind user.')
+ topology.standalone.add_s(Entry((BINDDN,
+ {'objectclass': "top person organizationalPerson inetOrgPerson".split(),
+ 'cn': 'bind user',
+ 'sn': 'user',
+ 'userPassword': BINDPW})))
+
+ log.info('Adding a test user.')
+ topology.standalone.add_s(Entry((TESTDN,
+ {'objectclass': "top person organizationalPerson inetOrgPerson".split(),
+ 'cn': 'test user',
+ 'sn': 'user',
+ 'userPassword': TESTPW})))
+
+ log.info('Deleting aci in %s.' % DEFAULT_SUFFIX)
+ topology.standalone.modify_s(DEFAULT_SUFFIX, [(ldap.MOD_DELETE, 'aci', None)])
+
+ log.info('Bind case 1. the bind user has no rights to read the entry itself, bind should be successful.')
+ log.info('Bind as {%s,%s} who has no access rights.' % (BINDDN, BINDPW))
+ try:
More information about the Pkg-fedora-ds-maintainers
mailing list