From 600e0429c58081c080cc283a0d4619dff920296f Mon Sep 17 00:00:00 2001 From: Simo Sorce Date: Mar 17 2016 08:18:26 +0000 Subject: Responders: Fix client destructor To close a socket associated to an fd event we must set the close function of the event and not associate a destructor to a parent context. Otherwise the destructor will close() the socket before the fd event is freed, and this may cause invalid calls on a closed file descriptor to poll/epoll/etc. Discovered by looking at strace output. Resolves: https://fedorahosted.org/sssd/ticket/2973 Reviewed-by: Pavel Březina --- diff --git a/src/responder/common/responder_common.c b/src/responder/common/responder_common.c index 6ac1ea2..9823186 100644 --- a/src/responder/common/responder_common.c +++ b/src/responder/common/responder_common.c @@ -66,9 +66,12 @@ static errno_t set_close_on_exec(int fd) return EOK; } -static int client_destructor(struct cli_ctx *ctx) +static void client_close_fn(struct tevent_context *ev, + struct tevent_fd *fde, int fd, + void *ptr) { errno_t ret; + struct cli_ctx *ctx = talloc_get_type(ptr, struct cli_ctx); if ((ctx->cfd > 0) && close(ctx->cfd) < 0) { ret = errno; @@ -80,7 +83,8 @@ static int client_destructor(struct cli_ctx *ctx) DEBUG(SSSDBG_TRACE_INTERNAL, "Terminated client [%p][%d]\n", ctx, ctx->cfd); - return 0; + + ctx->cfd = -1; } static errno_t get_client_cred(struct cli_ctx *cctx) @@ -474,12 +478,11 @@ static void accept_fd_handler(struct tevent_context *ev, accept_ctx->is_private ? " on privileged pipe" : ""); return; } + tevent_fd_set_close_fn(cctx->cfde, client_close_fn); cctx->ev = ev; cctx->rctx = rctx; - talloc_set_destructor(cctx, client_destructor); - /* Set up the idle timer */ ret = reset_idle_timer(cctx); if (ret != EOK) {