[SSSD] [PATCH] Keep deref controls until the whole request is finished
Jakub Hrozek
jhrozek at redhat.com
Tue Sep 6 10:43:55 UTC 2011
http://fedorahosted.org/sssd/ticket/989
John Hodrien found out that when paging is used while dereferencing an
entry, sssd_be may segfault on the second page.
This was because paging returned the control to sdap_generic_search
multiple times but sssd was freeing dereference control after the first
search invocation. The subsequend sdap searched accessed memory that was
already freed.
John confirmed off-list that this patch fixed his issue.
I was also considering copying the controls into the search request, but
it seemed like a pointless allocation.
-------------- next part --------------
>From f0f064137f22a04fec386242c249ef3c4b0a81c4 Mon Sep 17 00:00:00 2001
From: Jakub Hrozek <jhrozek at redhat.com>
Date: Tue, 6 Sep 2011 00:07:15 +0200
Subject: [PATCH] Keep deref controls until the whole request is finished
https://fedorahosted.org/sssd/ticket/989
John Hodrien found out that when paging is used while dereferencing an
entry, sssd_be may segfault on the second page.
This was because paging returned the control to sdap_generic_search
multiple times but sssd was freeing dereference control after the first
search invocation. The subsequend sdap searched accessed memory that was
already freed.
---
src/providers/ldap/sdap_async.c | 23 +++++++++++++++--------
1 files changed, 15 insertions(+), 8 deletions(-)
diff --git a/src/providers/ldap/sdap_async.c b/src/providers/ldap/sdap_async.c
index 5594dd5..556745c 100644
--- a/src/providers/ldap/sdap_async.c
+++ b/src/providers/ldap/sdap_async.c
@@ -1300,6 +1300,7 @@ struct sdap_x_deref_search_state {
struct sdap_handle *sh;
struct sdap_op *op;
struct sdap_attr_map_info *maps;
+ LDAPControl *ctrls[2];
struct sdap_deref_reply dreply;
int num_maps;
@@ -1315,7 +1316,6 @@ sdap_x_deref_search_send(TALLOC_CTX *memctx, struct tevent_context *ev,
struct tevent_req *req = NULL;
struct tevent_req *subreq = NULL;
struct sdap_x_deref_search_state *state;
- LDAPControl *ctrls[2] = { NULL, NULL };
int ret;
req = tevent_req_create(memctx, &state, struct sdap_x_deref_search_state);
@@ -1326,20 +1326,21 @@ sdap_x_deref_search_send(TALLOC_CTX *memctx, struct tevent_context *ev,
state->op = NULL;
state->num_maps = num_maps;
- ret = sdap_x_deref_create_control(sh, deref_attr, attrs, &ctrls[0]);
+ ret = sdap_x_deref_create_control(sh, deref_attr,
+ attrs, &state->ctrls[0]);
if (ret != EOK) {
DEBUG(1, ("Could not create OpenLDAP deref control\n"));
talloc_zfree(req);
return NULL;
}
+ state->ctrls[1] = NULL;
DEBUG(6, ("Dereferencing entry [%s] using OpenLDAP deref\n", base_dn));
subreq = sdap_get_generic_ext_send(state, ev, opts, sh, base_dn,
LDAP_SCOPE_BASE, NULL, attrs,
- false, ctrls, NULL, 0, timeout,
+ false, state->ctrls, NULL, 0, timeout,
sdap_x_deref_parse_entry,
state);
- ldap_control_free(ctrls[0]);
if (!subreq) {
talloc_zfree(req);
return NULL;
@@ -1464,9 +1465,12 @@ static void sdap_x_deref_search_done(struct tevent_req *subreq)
{
struct tevent_req *req = tevent_req_callback_data(subreq,
struct tevent_req);
+ struct sdap_x_deref_search_state *state = tevent_req_data(req,
+ struct sdap_x_deref_search_state);
int ret;
ret = sdap_get_generic_ext_recv(subreq);
+ ldap_control_free(state->ctrls[0]);
talloc_zfree(subreq);
if (ret) {
DEBUG(4, ("sdap_get_generic_ext_recv failed [%d]: %s\n",
@@ -1499,6 +1503,7 @@ sdap_x_deref_search_recv(struct tevent_req *req,
struct sdap_asq_search_state {
struct sdap_attr_map_info *maps;
int num_maps;
+ LDAPControl *ctrls[2];
struct sdap_deref_reply dreply;
};
@@ -1522,7 +1527,6 @@ sdap_asq_search_send(TALLOC_CTX *memctx, struct tevent_context *ev,
struct tevent_req *subreq = NULL;
struct sdap_asq_search_state *state;
int ret;
- LDAPControl *ctrls[2] = { NULL, NULL };
req = tevent_req_create(memctx, &state, struct sdap_asq_search_state);
if (!req) return NULL;
@@ -1530,20 +1534,20 @@ sdap_asq_search_send(TALLOC_CTX *memctx, struct tevent_context *ev,
state->maps = maps;
state->num_maps = num_maps;
- ret = sdap_asq_search_create_control(sh, deref_attr, &ctrls[0]);
+ ret = sdap_asq_search_create_control(sh, deref_attr, &state->ctrls[0]);
if (ret != EOK) {
talloc_zfree(req);
DEBUG(1, ("Could not create ASQ control\n"));
return NULL;
}
+ state->ctrls[1] = NULL;
DEBUG(6, ("Dereferencing entry [%s] using ASQ\n", base_dn));
subreq = sdap_get_generic_ext_send(state, ev, opts, sh, base_dn,
LDAP_SCOPE_BASE, NULL, attrs,
- false, ctrls, NULL, 0, timeout,
+ false, state->ctrls, NULL, 0, timeout,
sdap_asq_search_parse_entry,
state);
- ldap_control_free(ctrls[0]);
if (!subreq) {
talloc_zfree(req);
return NULL;
@@ -1670,9 +1674,12 @@ static void sdap_asq_search_done(struct tevent_req *subreq)
{
struct tevent_req *req = tevent_req_callback_data(subreq,
struct tevent_req);
+ struct sdap_asq_search_state *state = tevent_req_data(req,
+ struct sdap_asq_search_state);
int ret;
ret = sdap_get_generic_ext_recv(subreq);
+ ldap_control_free(state->ctrls[0]);
talloc_zfree(subreq);
if (ret) {
DEBUG(4, ("sdap_get_generic_ext_recv failed [%d]: %s\n",
--
1.7.6
More information about the sssd-devel
mailing list