From cebd9e91870511c1d81b821fcabc50fe9986e1ce Mon Sep 17 00:00:00 2001 From: Alexey Tikhonov Date: Tue, 11 Nov 2025 18:30:50 +0100 Subject: [PATCH 01/16] IFP: use correct error code for timeout MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Reviewed-by: Pavel Březina Reviewed-by: Tomáš Halman --- src/responder/ifp/ifp_users.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/responder/ifp/ifp_users.c b/src/responder/ifp/ifp_users.c index 40b4bf74dd5..ab83e2b5880 100644 --- a/src/responder/ifp/ifp_users.c +++ b/src/responder/ifp/ifp_users.c @@ -1174,7 +1174,7 @@ static void p11_child_timeout(struct tevent_context *ev, struct tevent_req *req = talloc_get_type(pvt, struct tevent_req); DEBUG(SSSDBG_CRIT_FAILURE, "p11_child timed out\n"); - tevent_req_error(req, ERR_P11_CHILD); + tevent_req_error(req, ERR_P11_CHILD_TIMEOUT); } static void From 90cacef5c3b83a3e783da7b350e670922bbb0b20 Mon Sep 17 00:00:00 2001 From: Alexey Tikhonov Date: Tue, 11 Nov 2025 19:34:11 +0100 Subject: [PATCH 02/16] CHILD HANDLERS: add standard timeout handler MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit and make use of it in gpo/ifp/ssh code. Reviewed-by: Pavel Březina Reviewed-by: Tomáš Halman --- src/providers/ad/ad_gpo.c | 14 ++-------- src/responder/ifp/ifp_users.c | 18 +++--------- src/responder/ssh/ssh_cert_to_ssh_key.c | 15 +++------- src/util/child_common.h | 7 +++++ src/util/child_handlers.c | 37 +++++++++++++++++++++++++ 5 files changed, 55 insertions(+), 36 deletions(-) diff --git a/src/providers/ad/ad_gpo.c b/src/providers/ad/ad_gpo.c index af58fee1e6e..46aa3d73224 100644 --- a/src/providers/ad/ad_gpo.c +++ b/src/providers/ad/ad_gpo.c @@ -4701,16 +4701,6 @@ struct ad_gpo_process_cse_state { static void gpo_cse_step(struct tevent_req *subreq); static void gpo_cse_done(struct tevent_req *subreq); -static void handle_gpo_child_timeout(struct tevent_context *ev, - struct tevent_timer *te, - struct timeval tv, void *pvt) -{ - struct tevent_req *req = talloc_get_type(pvt, struct tevent_req); - - DEBUG(SSSDBG_CRIT_FAILURE, "Timeout reached for gpo_child.\n"); - tevent_req_error(req, EFAULT); -} - /* * This cse-specific function (GP_EXT_GUID_SECURITY) sends the input smb uri * components and cached_gpt_version to the gpo child, which, in turn, @@ -4783,7 +4773,9 @@ ad_gpo_process_cse_send(TALLOC_CTX *mem_ctx, GPO_CHILD_LOG_FILE, AD_GPO_CHILD_OUT_FILENO, /* no SIGCHLD cb */ NULL, NULL, timeout, - handle_gpo_child_timeout, req, true, + sss_child_handle_timeout, + sss_child_create_timeout_cb_pvt(req, EFAULT), + true, &(state->io)); /* Note that timeout timer is allocated on 'state' context, so once * request is completed and state is freed, timer is also cancelled diff --git a/src/responder/ifp/ifp_users.c b/src/responder/ifp/ifp_users.c index ab83e2b5880..dda53bd2571 100644 --- a/src/responder/ifp/ifp_users.c +++ b/src/responder/ifp/ifp_users.c @@ -1047,9 +1047,6 @@ struct ifp_users_find_by_valid_cert_state { const char *path; }; -static void p11_child_timeout(struct tevent_context *ev, - struct tevent_timer *te, - struct timeval tv, void *pvt); static void ifp_users_find_by_valid_cert_step(int child_status, struct tevent_signal *sige, @@ -1150,7 +1147,10 @@ ifp_users_find_by_valid_cert_send(TALLOC_CTX *mem_ctx, state->extra_args, false, state->logfile, -1, /* ifp cares only about exit code, so no 'io' */ ifp_users_find_by_valid_cert_step, req, - state->timeout, p11_child_timeout, req, true, + state->timeout, + sss_child_handle_timeout, + sss_child_create_timeout_cb_pvt(req, ERR_P11_CHILD_TIMEOUT), + true, NULL); if (ret != EOK) { DEBUG(SSSDBG_OP_FAILURE, "sss_child_start failed [%d]: %s\n", @@ -1167,16 +1167,6 @@ ifp_users_find_by_valid_cert_send(TALLOC_CTX *mem_ctx, return req; } -static void p11_child_timeout(struct tevent_context *ev, - struct tevent_timer *te, - struct timeval tv, void *pvt) -{ - struct tevent_req *req = talloc_get_type(pvt, struct tevent_req); - - DEBUG(SSSDBG_CRIT_FAILURE, "p11_child timed out\n"); - tevent_req_error(req, ERR_P11_CHILD_TIMEOUT); -} - static void ifp_users_find_by_valid_cert_step(int child_status, struct tevent_signal *sige, diff --git a/src/responder/ssh/ssh_cert_to_ssh_key.c b/src/responder/ssh/ssh_cert_to_ssh_key.c index 4a9228056bf..157c1a9c62c 100644 --- a/src/responder/ssh/ssh_cert_to_ssh_key.c +++ b/src/responder/ssh/ssh_cert_to_ssh_key.c @@ -154,16 +154,6 @@ struct tevent_req *cert_to_ssh_key_send(TALLOC_CTX *mem_ctx, return req; } -static void p11_child_timeout(struct tevent_context *ev, - struct tevent_timer *te, - struct timeval tv, void *pvt) -{ - struct tevent_req *req = talloc_get_type(pvt, struct tevent_req); - - DEBUG(SSSDBG_MINOR_FAILURE, "Timeout reached for p11_child.\n"); - tevent_req_error(req, ERR_P11_CHILD_TIMEOUT); -} - static errno_t cert_to_ssh_key_step(struct tevent_req *req) { struct cert_to_ssh_key_state *state = tevent_req_data(req, @@ -180,7 +170,10 @@ static errno_t cert_to_ssh_key_step(struct tevent_req *req) state->extra_args, false, state->logfile, -1, /* ssh cares only about exit code, so no 'io' */ cert_to_ssh_key_done, req, - (unsigned)(state->timeout), p11_child_timeout, req, true, + (unsigned)(state->timeout), + sss_child_handle_timeout, + sss_child_create_timeout_cb_pvt(req, ERR_P11_CHILD_TIMEOUT), + true, NULL); if (ret != EOK) { DEBUG(SSSDBG_OP_FAILURE, "sss_child_start failed [%d]: %s\n", diff --git a/src/util/child_common.h b/src/util/child_common.h index f4b64d0824e..d39698c42b9 100644 --- a/src/util/child_common.h +++ b/src/util/child_common.h @@ -88,6 +88,13 @@ errno_t sss_child_start(TALLOC_CTX *mem_ctx, /* Standard implementation of sss_child_sigchld_callback_t used by krb5/oidc */ void sss_child_handle_exited(int child_status, struct tevent_signal *sige, void *pvt); +/* Standard implementation of tevent_timer_handler_t that ends tevent_req + * with a given error code and a helper to create a pvt. + */ +void *sss_child_create_timeout_cb_pvt(struct tevent_req *req, int code); +void sss_child_handle_timeout(struct tevent_context *, struct tevent_timer *, + struct timeval, void *pvt); + /* Simple helper that sends SIGKILL if (pid != 0) */ void sss_child_terminate(pid_t pid); diff --git a/src/util/child_handlers.c b/src/util/child_handlers.c index 325f86be8ee..a69be1b033e 100644 --- a/src/util/child_handlers.c +++ b/src/util/child_handlers.c @@ -542,6 +542,40 @@ void sss_child_terminate(pid_t pid) } } +struct child_timeout_cb_pvt { + struct tevent_req *req; + int error_code; +}; + +void *sss_child_create_timeout_cb_pvt(struct tevent_req *req, int code) +{ + struct child_timeout_cb_pvt *ctx = talloc_zero(req, struct child_timeout_cb_pvt); + + if (ctx == NULL) { + DEBUG(SSSDBG_FATAL_FAILURE, "talloc_zero() failed\n"); + return NULL; + } + + ctx->req = req; + ctx->error_code = code; + return ctx; +} + +void sss_child_handle_timeout(struct tevent_context *, struct tevent_timer *, + struct timeval, void *pvt) +{ + struct child_timeout_cb_pvt *ctx; + + if (pvt == NULL) { + DEBUG(SSSDBG_CRIT_FAILURE, "Timeout callback called with NULL context.\n"); + return; + } + + ctx = talloc_get_type(pvt, struct child_timeout_cb_pvt); + + tevent_req_error(ctx->req, ctx->error_code); +} + struct child_timeout_ctx { tevent_timer_handler_t timeout_cb; void *timeout_pvt; @@ -559,6 +593,9 @@ static void child_handle_timeout(struct tevent_context *ev, bool auto_terminate = ctx->auto_terminate; pid_t pid = ctx->pid; + DEBUG(SSSDBG_OP_FAILURE, "Timeout reached for child process with pid = %d\n", + (int)pid); + if (ctx->timeout_cb) { ctx->timeout_cb(ev, te, tv, ctx->timeout_pvt); /* At this point 'ctx' might be already gone */ From d83d209c1aaeecbaac491b156bb3486c48154fc8 Mon Sep 17 00:00:00 2001 From: Alexey Tikhonov Date: Wed, 12 Nov 2025 11:41:12 +0100 Subject: [PATCH 03/16] ad_machine_pw_renewal: remove unused variables MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Reviewed-by: Pavel Březina Reviewed-by: Tomáš Halman --- src/providers/ad/ad_machine_pw_renewal.c | 8 -------- 1 file changed, 8 deletions(-) diff --git a/src/providers/ad/ad_machine_pw_renewal.c b/src/providers/ad/ad_machine_pw_renewal.c index bf6ea96e992..54b07ca6d23 100644 --- a/src/providers/ad/ad_machine_pw_renewal.c +++ b/src/providers/ad/ad_machine_pw_renewal.c @@ -184,9 +184,6 @@ static errno_t get_realm_extra_args(const char *ad_domain, } struct renewal_state { - int child_status; - struct tevent_context *ev; - struct child_io_fds *io; }; @@ -219,9 +216,6 @@ ad_machine_account_password_renewal_send(TALLOC_CTX *mem_ctx, renewal_data = talloc_get_type(pvt, struct renewal_data); - state->ev = ev; - state->child_status = EFAULT; - server_name = be_fo_get_active_server_name(be_ctx, AD_SERVICE_NAME); talloc_zfree(renewal_data->extra_args[0]); if ((renewal_data->renew_helper == RENEW_HELPER_ADCLI) @@ -304,10 +298,8 @@ ad_machine_account_password_renewal_timeout(struct tevent_context *ev, struct timeval tv, void *pvt) { struct tevent_req *req = talloc_get_type(pvt, struct tevent_req); - struct renewal_state *state = tevent_req_data(req, struct renewal_state); DEBUG(SSSDBG_CRIT_FAILURE, "Timeout reached for AD renewal child.\n"); - state->child_status = ETIMEDOUT; tevent_req_error(req, ERR_RENEWAL_CHILD); } From b1bdfa56144fd955020ec8f26de2682b8d7703da Mon Sep 17 00:00:00 2001 From: Alexey Tikhonov Date: Wed, 12 Nov 2025 11:45:03 +0100 Subject: [PATCH 04/16] ad_machine_pw_renewal: use sss_child_handle_timeout() MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Reviewed-by: Pavel Březina Reviewed-by: Tomáš Halman --- src/providers/ad/ad_machine_pw_renewal.c | 19 +++---------------- 1 file changed, 3 insertions(+), 16 deletions(-) diff --git a/src/providers/ad/ad_machine_pw_renewal.c b/src/providers/ad/ad_machine_pw_renewal.c index 54b07ca6d23..78b2602bb5b 100644 --- a/src/providers/ad/ad_machine_pw_renewal.c +++ b/src/providers/ad/ad_machine_pw_renewal.c @@ -188,10 +188,6 @@ struct renewal_state { }; static void ad_machine_account_password_renewal_done(struct tevent_req *subreq); -static void -ad_machine_account_password_renewal_timeout(struct tevent_context *ev, - struct tevent_timer *te, - struct timeval tv, void *pvt); static struct tevent_req * ad_machine_account_password_renewal_send(TALLOC_CTX *mem_ctx, @@ -236,7 +232,9 @@ ad_machine_account_password_renewal_send(TALLOC_CTX *mem_ctx, /* no log file */ NULL, STDERR_FILENO, /* no SIGCHLD cb */ NULL, NULL, (unsigned)(be_ptask_get_timeout(be_ptask)), - ad_machine_account_password_renewal_timeout, req, true, + sss_child_handle_timeout, + sss_child_create_timeout_cb_pvt(req, ERR_RENEWAL_CHILD), + true, &(state->io)); if (ret != EOK) { goto done; @@ -292,17 +290,6 @@ static void ad_machine_account_password_renewal_done(struct tevent_req *subreq) return; } -static void -ad_machine_account_password_renewal_timeout(struct tevent_context *ev, - struct tevent_timer *te, - struct timeval tv, void *pvt) -{ - struct tevent_req *req = talloc_get_type(pvt, struct tevent_req); - - DEBUG(SSSDBG_CRIT_FAILURE, "Timeout reached for AD renewal child.\n"); - tevent_req_error(req, ERR_RENEWAL_CHILD); -} - static errno_t ad_machine_account_password_renewal_recv(struct tevent_req *req) { From 8bf0306d03ac01e05e3238d69844dfabd86c9954 Mon Sep 17 00:00:00 2001 From: Alexey Tikhonov Date: Tue, 25 Nov 2025 19:03:37 +0100 Subject: [PATCH 05/16] PAM/P11: get rid of unused 'pam_check_cert_state::child_status' MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Reviewed-by: Pavel Březina Reviewed-by: Tomáš Halman --- src/responder/pam/pamsrv_p11.c | 6 ------ 1 file changed, 6 deletions(-) diff --git a/src/responder/pam/pamsrv_p11.c b/src/responder/pam/pamsrv_p11.c index ee3261e0e2f..f4784596a77 100644 --- a/src/responder/pam/pamsrv_p11.c +++ b/src/responder/pam/pamsrv_p11.c @@ -711,7 +711,6 @@ static errno_t parse_p11_child_response(TALLOC_CTX *mem_ctx, uint8_t *buf, } struct pam_check_cert_state { - int child_status; struct tevent_context *ev; struct sss_certmap_ctx *sss_certmap_ctx; struct child_io_fds *io; @@ -848,8 +847,6 @@ struct tevent_req *pam_check_cert_send(TALLOC_CTX *mem_ctx, state->ev = ev; state->sss_certmap_ctx = sss_certmap_ctx; - state->child_status = EFAULT; - ret = sss_child_start(state, ev, P11_CHILD_PATH, extra_args, false, @@ -975,13 +972,10 @@ static void p11_child_timeout(struct tevent_context *ev, struct timeval tv, void *pvt) { struct tevent_req *req = talloc_get_type(pvt, struct tevent_req); - struct pam_check_cert_state *state = - tevent_req_data(req, struct pam_check_cert_state); DEBUG(SSSDBG_CRIT_FAILURE, "Timeout reached for p11_child, " "consider increasing p11_child_timeout.\n"); - state->child_status = ETIMEDOUT; tevent_req_error(req, ERR_P11_CHILD_TIMEOUT); } From 42cd5b6c856ffacb9ad75fb9ff96fc2fdf8a8ef1 Mon Sep 17 00:00:00 2001 From: Alexey Tikhonov Date: Tue, 25 Nov 2025 19:10:36 +0100 Subject: [PATCH 06/16] PAM/P11: use sss_child_handle_timeout() MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Reviewed-by: Pavel Březina Reviewed-by: Tomáš Halman --- src/responder/pam/pamsrv_p11.c | 20 ++++---------------- 1 file changed, 4 insertions(+), 16 deletions(-) diff --git a/src/responder/pam/pamsrv_p11.c b/src/responder/pam/pamsrv_p11.c index f4784596a77..50be489f7da 100644 --- a/src/responder/pam/pamsrv_p11.c +++ b/src/responder/pam/pamsrv_p11.c @@ -720,9 +720,6 @@ struct pam_check_cert_state { static void p11_child_write_done(struct tevent_req *subreq); static void p11_child_done(struct tevent_req *subreq); -static void p11_child_timeout(struct tevent_context *ev, - struct tevent_timer *te, - struct timeval tv, void *pvt); struct tevent_req *pam_check_cert_send(TALLOC_CTX *mem_ctx, struct tevent_context *ev, @@ -852,7 +849,10 @@ struct tevent_req *pam_check_cert_send(TALLOC_CTX *mem_ctx, P11_CHILD_PATH, extra_args, false, P11_CHILD_LOG_FILE, STDOUT_FILENO, NULL, NULL, - (unsigned)(timeout), p11_child_timeout, req, true, + (unsigned)(timeout), + sss_child_handle_timeout, + sss_child_create_timeout_cb_pvt(req, ERR_P11_CHILD_TIMEOUT), + true, &(state->io)); if (ret != EOK) { DEBUG(SSSDBG_CRIT_FAILURE, "fork failed [%d][%s].\n", @@ -967,18 +967,6 @@ static void p11_child_done(struct tevent_req *subreq) return; } -static void p11_child_timeout(struct tevent_context *ev, - struct tevent_timer *te, - struct timeval tv, void *pvt) -{ - struct tevent_req *req = talloc_get_type(pvt, struct tevent_req); - - DEBUG(SSSDBG_CRIT_FAILURE, - "Timeout reached for p11_child, " - "consider increasing p11_child_timeout.\n"); - tevent_req_error(req, ERR_P11_CHILD_TIMEOUT); -} - errno_t pam_check_cert_recv(struct tevent_req *req, TALLOC_CTX *mem_ctx, struct cert_auth_info **cert_list) { From 677f5109dcac5d2e524b61e20a2ac7897c8578c1 Mon Sep 17 00:00:00 2001 From: Alexey Tikhonov Date: Tue, 25 Nov 2025 19:29:23 +0100 Subject: [PATCH 07/16] PAM/PASSKEY: use sss_child_handle_timeout() MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Reviewed-by: Pavel Březina Reviewed-by: Tomáš Halman --- src/responder/pam/pamsrv_passkey.c | 22 +++++----------------- 1 file changed, 5 insertions(+), 17 deletions(-) diff --git a/src/responder/pam/pamsrv_passkey.c b/src/responder/pam/pamsrv_passkey.c index b95856dd994..667e945faea 100644 --- a/src/responder/pam/pamsrv_passkey.c +++ b/src/responder/pam/pamsrv_passkey.c @@ -1029,22 +1029,6 @@ pam_passkey_auth_send(TALLOC_CTX *mem_ctx, return req; } -static void -passkey_child_timeout(struct tevent_context *ev, - struct tevent_timer *te, - struct timeval tv, void *pvt) -{ - struct tevent_req *req = - talloc_get_type(pvt, struct tevent_req); - struct pam_passkey_auth_send_state *state = - tevent_req_data(req, struct pam_passkey_auth_send_state); - - DEBUG(SSSDBG_CRIT_FAILURE, "Timeout reached for passkey child, " - "consider increasing passkey_child_timeout\n"); - state->child_status = ETIMEDOUT; - tevent_req_error(req, ERR_PASSKEY_CHILD_TIMEOUT); -} - static errno_t passkey_child_exec(struct tevent_req *req) { struct pam_passkey_auth_send_state *state; @@ -1054,12 +1038,16 @@ static errno_t passkey_child_exec(struct tevent_req *req) int ret; state = tevent_req_data(req, struct pam_passkey_auth_send_state); + state->child_status = ETIMEDOUT; ret = sss_child_start(state, state->ev, PASSKEY_CHILD_PATH, state->extra_args, false, state->logfile, STDOUT_FILENO, (state->kerberos_pa) ? NULL : pam_passkey_auth_done, req, - state->timeout, passkey_child_timeout, req, true, + state->timeout, + sss_child_handle_timeout, + sss_child_create_timeout_cb_pvt(req, ERR_PASSKEY_CHILD_TIMEOUT), + true, &(state->io)); if (ret != EOK) { return ERR_PASSKEY_CHILD; From 24da2f906cdfae3515eb7842b57150a15f45a42a Mon Sep 17 00:00:00 2001 From: Alexey Tikhonov Date: Tue, 25 Nov 2025 20:26:32 +0100 Subject: [PATCH 08/16] CHILD HELPERS: let generic timeout handler set 'io->in_use' MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Reviewed-by: Pavel Březina Reviewed-by: Tomáš Halman --- src/providers/idp/oidc_child_handler.c | 3 --- src/providers/krb5/krb5_child_handler.c | 3 --- src/util/child_common.h | 8 +++----- src/util/child_handlers.c | 9 ++++++++- 4 files changed, 11 insertions(+), 12 deletions(-) diff --git a/src/providers/idp/oidc_child_handler.c b/src/providers/idp/oidc_child_handler.c index 088f7f81912..cb128ba1093 100644 --- a/src/providers/idp/oidc_child_handler.c +++ b/src/providers/idp/oidc_child_handler.c @@ -48,9 +48,6 @@ static void oidc_child_timeout(struct tevent_context *ev, struct handle_oidc_child_state *state = tevent_req_data(req, struct handle_oidc_child_state); - /* No I/O expected anymore, make sure sockets are closed properly */ - state->io->in_use = false; - DEBUG(SSSDBG_IMPORTANT_INFO, "Timeout for child [%d] reached. In case IdP is distant or network " "is slow you may consider increasing value of idp_request_timeout.\n", diff --git a/src/providers/krb5/krb5_child_handler.c b/src/providers/krb5/krb5_child_handler.c index 936ba99a380..fea0111ace0 100644 --- a/src/providers/krb5/krb5_child_handler.c +++ b/src/providers/krb5/krb5_child_handler.c @@ -261,9 +261,6 @@ static void krb5_child_timeout(struct tevent_context *ev, struct handle_child_state *state = tevent_req_data(req, struct handle_child_state); - /* No I/O expected anymore, make sure sockets are closed properly */ - state->io->in_use = false; - DEBUG(SSSDBG_IMPORTANT_INFO, "Timeout for child [%d] reached. In case KDC is distant or network " "is slow you may consider increasing value of krb5_auth_timeout.\n", diff --git a/src/util/child_common.h b/src/util/child_common.h index d39698c42b9..26326f2b3d6 100644 --- a/src/util/child_common.h +++ b/src/util/child_common.h @@ -41,11 +41,9 @@ struct child_io_fds { pid_t pid; struct tevent_timer *timeout_handler; - /* Following two fields are kind of "user payload": - * not handled by general child helpers internally; - * currently used by krb5/oidc only as those have - * specific requirements (single process for multiple - * tevent reqs). + /* Following two fields are currently used by krb5/oidc + * only as those have specific requirements + * (single process for multiple tevent reqs). */ bool child_exited; bool in_use; diff --git a/src/util/child_handlers.c b/src/util/child_handlers.c index a69be1b033e..e097e378dac 100644 --- a/src/util/child_handlers.c +++ b/src/util/child_handlers.c @@ -581,6 +581,7 @@ struct child_timeout_ctx { void *timeout_pvt; bool auto_terminate; pid_t pid; + struct child_io_fds *io; }; static void child_handle_timeout(struct tevent_context *ev, @@ -596,6 +597,10 @@ static void child_handle_timeout(struct tevent_context *ev, DEBUG(SSSDBG_OP_FAILURE, "Timeout reached for child process with pid = %d\n", (int)pid); + if (ctx->io != NULL) { + ctx->io->in_use = false; + } + if (ctx->timeout_cb) { ctx->timeout_cb(ev, te, tv, ctx->timeout_pvt); /* At this point 'ctx' might be already gone */ @@ -609,6 +614,7 @@ static void child_handle_timeout(struct tevent_context *ev, static struct tevent_timer *activate_child_timeout_handler(TALLOC_CTX *mem_ctx, struct tevent_context *ev, pid_t pid, + struct child_io_fds *io, uint32_t timeout_seconds, tevent_timer_handler_t handler, void *handler_pvt_ctx, @@ -636,6 +642,7 @@ static struct tevent_timer *activate_child_timeout_handler(TALLOC_CTX *mem_ctx, ctx->timeout_cb = handler; ctx->timeout_pvt = handler_pvt_ctx; ctx->pid = pid; + ctx->io = io; tv = tevent_timeval_current(); tv = tevent_timeval_add(&tv, timeout_seconds, 0); @@ -756,7 +763,7 @@ errno_t sss_child_start(TALLOC_CTX *mem_ctx, } timeout_handler = activate_child_timeout_handler(mem_ctx, - ev, pid, + ev, pid, io, (uint32_t) timeout, timeout_cb, timeout_pvt, auto_terminate); if ((timeout > 0) && (timeout_handler == NULL)) { From 9ec1dd204676c13d01f8b97f2c41a45eb5183e58 Mon Sep 17 00:00:00 2001 From: Alexey Tikhonov Date: Tue, 25 Nov 2025 20:32:23 +0100 Subject: [PATCH 09/16] KRB5_CHILD: use sss_child_handle_timeout() MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Reviewed-by: Pavel Březina Reviewed-by: Tomáš Halman --- src/providers/krb5/krb5_child_handler.c | 24 +++--------------------- 1 file changed, 3 insertions(+), 21 deletions(-) diff --git a/src/providers/krb5/krb5_child_handler.c b/src/providers/krb5/krb5_child_handler.c index fea0111ace0..6d19f9db029 100644 --- a/src/providers/krb5/krb5_child_handler.c +++ b/src/providers/krb5/krb5_child_handler.c @@ -51,8 +51,6 @@ struct handle_child_state { uint8_t *buf; ssize_t len; - pid_t child_pid; - struct child_io_fds *io; }; @@ -253,22 +251,6 @@ static errno_t create_send_buffer(struct krb5child_req *kr, return EOK; } -static void krb5_child_timeout(struct tevent_context *ev, - struct tevent_timer *te, - struct timeval tv, void *pvt) -{ - struct tevent_req *req = talloc_get_type(pvt, struct tevent_req); - struct handle_child_state *state = tevent_req_data(req, - struct handle_child_state); - - DEBUG(SSSDBG_IMPORTANT_INFO, - "Timeout for child [%d] reached. In case KDC is distant or network " - "is slow you may consider increasing value of krb5_auth_timeout.\n", - state->child_pid); - - tevent_req_error(req, ETIMEDOUT); -} - errno_t set_extra_args(TALLOC_CTX *mem_ctx, struct krb5_ctx *krb5_ctx, struct sss_domain_info *domain, const char ***krb5_child_extra_args) @@ -453,7 +435,9 @@ static errno_t start_krb5_child(struct tevent_req *req) KRB5_CHILD_LOG_FILE, STDOUT_FILENO, sss_child_handle_exited, NULL, dp_opt_get_int(kr->krb5_ctx->opts, KRB5_AUTH_TIMEOUT), - krb5_child_timeout, req, true, + sss_child_handle_timeout, + sss_child_create_timeout_cb_pvt(req, ETIMEDOUT), + true, &io); if (ret != EOK) { goto done; @@ -488,7 +472,6 @@ static errno_t start_krb5_child(struct tevent_req *req) /* Steal 'io' so it can outlive this request if needed. */ talloc_steal(kr->krb5_ctx->io_table, io); - child_state->child_pid = io->pid; child_state->io = io; ret = EOK; @@ -528,7 +511,6 @@ struct tevent_req *handle_child_send(TALLOC_CTX *mem_ctx, state->kr = kr; state->buf = NULL; state->len = 0; - state->child_pid = -1; ret = create_send_buffer(kr, &buf); if (ret != EOK) { From 9b6b6016b323c449b3e4375cb42f71c44b1697ce Mon Sep 17 00:00:00 2001 From: Alexey Tikhonov Date: Tue, 25 Nov 2025 20:36:06 +0100 Subject: [PATCH 10/16] OIDC_CHILD: use sss_child_handle_timeout() MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Reviewed-by: Pavel Březina Reviewed-by: Tomáš Halman --- src/providers/idp/oidc_child_handler.c | 25 +++---------------------- 1 file changed, 3 insertions(+), 22 deletions(-) diff --git a/src/providers/idp/oidc_child_handler.c b/src/providers/idp/oidc_child_handler.c index cb128ba1093..ad3e3f6b1e2 100644 --- a/src/providers/idp/oidc_child_handler.c +++ b/src/providers/idp/oidc_child_handler.c @@ -34,28 +34,9 @@ struct handle_oidc_child_state { uint8_t *buf; ssize_t len; - pid_t child_pid; - struct child_io_fds *io; }; -/* TODO: krb5_child_handler.c is using similar */ -static void oidc_child_timeout(struct tevent_context *ev, - struct tevent_timer *te, - struct timeval tv, void *pvt) -{ - struct tevent_req *req = talloc_get_type(pvt, struct tevent_req); - struct handle_oidc_child_state *state = tevent_req_data(req, - struct handle_oidc_child_state); - - DEBUG(SSSDBG_IMPORTANT_INFO, - "Timeout for child [%d] reached. In case IdP is distant or network " - "is slow you may consider increasing value of idp_request_timeout.\n", - state->child_pid); - - tevent_req_error(req, ETIMEDOUT); -} - static errno_t create_send_buffer(struct idp_req *idp_req, struct io_buffer **io_buf) { @@ -118,7 +99,6 @@ struct tevent_req *handle_oidc_child_send(TALLOC_CTX *mem_ctx, state->idp_req = idp_req; state->buf = NULL; state->len = 0; - state->child_pid = -1; if (send_buffer == NULL) { ret = create_send_buffer(idp_req, &buf); @@ -136,7 +116,9 @@ struct tevent_req *handle_oidc_child_send(TALLOC_CTX *mem_ctx, OIDC_CHILD_LOG_FILE, STDOUT_FILENO, sss_child_handle_exited, NULL, dp_opt_get_int(idp_req->idp_options, IDP_REQ_TIMEOUT), - oidc_child_timeout, req, true, + sss_child_handle_timeout, + sss_child_create_timeout_cb_pvt(req, ETIMEDOUT), + true, &(state->io)); if (ret != EOK) { DEBUG(SSSDBG_CRIT_FAILURE, "sss_child_start() failed.\n"); @@ -145,7 +127,6 @@ struct tevent_req *handle_oidc_child_send(TALLOC_CTX *mem_ctx, /* Steal the io pair so it can outlive this request if needed. */ talloc_steal(idp_req->idp_options, state->io); - state->child_pid = state->io->pid; state->io->in_use = true; subreq = write_pipe_send(state, ev, buf->data, buf->size, state->io->write_to_child_fd); From 608c4f6e6b24a612b0c0a9031f47c9d243562f8f Mon Sep 17 00:00:00 2001 From: Alexey Tikhonov Date: Wed, 12 Nov 2025 11:52:29 +0100 Subject: [PATCH 11/16] DYNDNS: use a proper 'timeout_handler' MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 'nsupdate_child_state::timeout_handler' wasn't really used. Reviewed-by: Pavel Březina Reviewed-by: Tomáš Halman --- src/providers/be_dyndns.c | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/src/providers/be_dyndns.c b/src/providers/be_dyndns.c index 95b73d4544e..ed2601bf4e5 100644 --- a/src/providers/be_dyndns.c +++ b/src/providers/be_dyndns.c @@ -1184,7 +1184,6 @@ nsupdate_get_addrs_recv(struct tevent_req *req, struct nsupdate_child_state { struct tevent_context *ev; struct child_io_fds *io; - struct tevent_timer *timeout_handler; bool read_done; bool process_finished; errno_t result; @@ -1320,7 +1319,7 @@ void nsupdate_child_read_done(struct tevent_req *subreq) struct nsupdate_child_state *state = tevent_req_data(req, struct nsupdate_child_state); - talloc_zfree(state->timeout_handler); + talloc_zfree(state->io->timeout_handler); ret = read_pipe_recv(subreq, state, &buf, &buf_len); talloc_zfree(subreq); From ff31a8e83e504575d5e54eab68479c94a6f44b09 Mon Sep 17 00:00:00 2001 From: Alexey Tikhonov Date: Tue, 25 Nov 2025 21:25:57 +0100 Subject: [PATCH 12/16] DYNDNS: use sss_child_handle_timeout() MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Reviewed-by: Pavel Březina Reviewed-by: Tomáš Halman --- src/providers/be_dyndns.c | 25 +++++-------------------- 1 file changed, 5 insertions(+), 20 deletions(-) diff --git a/src/providers/be_dyndns.c b/src/providers/be_dyndns.c index ed2601bf4e5..0fae466797a 100644 --- a/src/providers/be_dyndns.c +++ b/src/providers/be_dyndns.c @@ -1191,10 +1191,6 @@ struct nsupdate_child_state { int child_status; }; -static void -nsupdate_child_timeout(struct tevent_context *ev, - struct tevent_timer *te, - struct timeval tv, void *pvt); static void nsupdate_child_handler(int child_status, struct tevent_signal *sige, @@ -1223,12 +1219,16 @@ nsupdate_child_send(TALLOC_CTX *mem_ctx, state->read_done = false; state->process_finished = false; state->result = ERR_DYNDNS_FAILED; + state->child_status = ETIMEDOUT; ret = sss_child_start(state, ev, NSUPDATE_PATH, args, true, NULL, STDERR_FILENO, nsupdate_child_handler, req, - DYNDNS_TIMEOUT, nsupdate_child_timeout, req, true, + DYNDNS_TIMEOUT, + sss_child_handle_timeout, + sss_child_create_timeout_cb_pvt(req, ERR_DYNDNS_TIMEOUT), + true, &(state->io)); if (ret != EOK) { DEBUG(SSSDBG_CRIT_FAILURE, "sss_child_start() failed\n"); @@ -1256,21 +1256,6 @@ nsupdate_child_send(TALLOC_CTX *mem_ctx, return req; } -static void -nsupdate_child_timeout(struct tevent_context *ev, - struct tevent_timer *te, - struct timeval tv, void *pvt) -{ - struct tevent_req *req = - talloc_get_type(pvt, struct tevent_req); - struct nsupdate_child_state *state = - tevent_req_data(req, struct nsupdate_child_state); - - DEBUG(SSSDBG_CRIT_FAILURE, "Timeout reached for dynamic DNS update\n"); - state->child_status = ETIMEDOUT; - tevent_req_error(req, ERR_DYNDNS_TIMEOUT); -} - static void nsupdate_child_stdin_done(struct tevent_req *subreq) { From 0fd6806c8afde95ac9759d80df1feaa57d0acafc Mon Sep 17 00:00:00 2001 From: Alexey Tikhonov Date: Wed, 26 Nov 2025 18:40:21 +0100 Subject: [PATCH 13/16] PROXY: provide 'dumpable' and 'backtrace' args to child process MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Reviewed-by: Pavel Březina Reviewed-by: Tomáš Halman --- src/providers/proxy/proxy_auth.c | 11 +++++++---- 1 file changed, 7 insertions(+), 4 deletions(-) diff --git a/src/providers/proxy/proxy_auth.c b/src/providers/proxy/proxy_auth.c index 7f6f3f252d6..dc44bb5d294 100644 --- a/src/providers/proxy/proxy_auth.c +++ b/src/providers/proxy/proxy_auth.c @@ -24,9 +24,11 @@ #include -#include "providers/proxy/proxy.h" -#include "sss_iface/sss_iface_async.h" #include "util/sss_chain_id.h" +#include "util/sss_prctl.h" +#include "sss_iface/sss_iface_async.h" +#include "providers/proxy/proxy.h" + struct pc_init_ctx; @@ -180,11 +182,12 @@ static struct tevent_req *proxy_child_init_send(TALLOC_CTX *mem_ctx, state->command = talloc_asprintf(req, "%s/proxy_child -d %#.4x --debug-timestamps=%d " "--debug-microseconds=%d --logger=%s --domain %s --id %d " - "--chain-id=%lu", + "--chain-id=%lu --dumpable=%d --backtrace=%d", SSSD_LIBEXEC_PATH, debug_level, debug_timestamps, debug_microseconds, sss_logger_str[sss_logger], auth_ctx->be->domain->name, - child_ctx->id, sss_chain_id_get()); + child_ctx->id, sss_chain_id_get(), sss_prctl_get_dumpable(), + sss_get_debug_backtrace_enable() ? 1 : 0); if (state->command == NULL) { DEBUG(SSSDBG_CRIT_FAILURE, "talloc_asprintf failed.\n"); return NULL; From 78a4c147ce508e1fbdf57c6b5e8a975bde50cd25 Mon Sep 17 00:00:00 2001 From: Alexey Tikhonov Date: Wed, 26 Nov 2025 18:51:22 +0100 Subject: [PATCH 14/16] PROXY: delete unused define MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Unused since c7e2d7a56d8969f26921811e5122f78b257fb51e Reviewed-by: Pavel Březina Reviewed-by: Tomáš Halman --- src/providers/proxy/proxy.h | 1 - 1 file changed, 1 deletion(-) diff --git a/src/providers/proxy/proxy.h b/src/providers/proxy/proxy.h index 6246eba1873..a7a05079521 100644 --- a/src/providers/proxy/proxy.h +++ b/src/providers/proxy/proxy.h @@ -100,7 +100,6 @@ struct pc_init_ctx { struct sbus_connection *conn; }; -#define PROXY_CHILD_PIPE "private/proxy_child" #define DEFAULT_BUFSIZE 4096 #define MAX_BUF_SIZE 1024*1024 /* max 1MiB */ From 7d15387dc5480b1b4ac4270cc016c9fdf57714ce Mon Sep 17 00:00:00 2001 From: Alexey Tikhonov Date: Wed, 26 Nov 2025 18:54:19 +0100 Subject: [PATCH 15/16] PROXY: use `sss_child_handle_timeout()` MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Reviewed-by: Pavel Březina Reviewed-by: Tomáš Halman --- src/providers/proxy/proxy_auth.c | 20 ++++---------------- 1 file changed, 4 insertions(+), 16 deletions(-) diff --git a/src/providers/proxy/proxy_auth.c b/src/providers/proxy/proxy_auth.c index dc44bb5d294..316dacbdb75 100644 --- a/src/providers/proxy/proxy_auth.c +++ b/src/providers/proxy/proxy_auth.c @@ -26,6 +26,7 @@ #include "util/sss_chain_id.h" #include "util/sss_prctl.h" +#include "util/child_common.h" #include "sss_iface/sss_iface_async.h" #include "providers/proxy/proxy.h" @@ -157,9 +158,6 @@ static int pc_init_destructor (TALLOC_CTX *ctx) static void pc_init_sig_handler(struct tevent_context *ev, struct tevent_signal *sige, int signum, int count, void *__siginfo, void *pvt); -static void pc_init_timeout(struct tevent_context *ev, - struct tevent_timer *te, - struct timeval t, void *ptr); static struct tevent_req *proxy_child_init_send(TALLOC_CTX *mem_ctx, struct proxy_child_ctx *child_ctx, struct proxy_auth_ctx *auth_ctx) @@ -246,8 +244,9 @@ static struct tevent_req *proxy_child_init_send(TALLOC_CTX *mem_ctx, * be faster here. */ tv = tevent_timeval_current_ofs(6, 0); - state->timeout = tevent_add_timer(auth_ctx->be->ev, req, - tv, pc_init_timeout, req); + state->timeout = tevent_add_timer(auth_ctx->be->ev, req, tv, + sss_child_handle_timeout, + sss_child_create_timeout_cb_pvt(req, ETIMEDOUT)); /* processing will continue once the connection is received * in proxy_client_init() @@ -315,17 +314,6 @@ static void pc_init_sig_handler(struct tevent_context *ev, } } -static void pc_init_timeout(struct tevent_context *ev, - struct tevent_timer *te, - struct timeval t, void *ptr) -{ - struct tevent_req *req; - - DEBUG(SSSDBG_OP_FAILURE, "Client timed out before Identification!\n"); - req = talloc_get_type(ptr, struct tevent_req); - tevent_req_error(req, ETIMEDOUT); -} - static errno_t proxy_child_init_recv(struct tevent_req *req, pid_t *pid, struct sbus_connection **conn) From 63f5a3c2404f04663d4bb08e79349b8321ef66e5 Mon Sep 17 00:00:00 2001 From: Alexey Tikhonov Date: Wed, 26 Nov 2025 19:03:04 +0100 Subject: [PATCH 16/16] PAM/P11: debug message fixed MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Reviewed-by: Pavel Březina Reviewed-by: Tomáš Halman --- src/responder/pam/pamsrv_p11.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/responder/pam/pamsrv_p11.c b/src/responder/pam/pamsrv_p11.c index 50be489f7da..de2b6d1fcb2 100644 --- a/src/responder/pam/pamsrv_p11.c +++ b/src/responder/pam/pamsrv_p11.c @@ -855,7 +855,7 @@ struct tevent_req *pam_check_cert_send(TALLOC_CTX *mem_ctx, true, &(state->io)); if (ret != EOK) { - DEBUG(SSSDBG_CRIT_FAILURE, "fork failed [%d][%s].\n", + DEBUG(SSSDBG_CRIT_FAILURE, "sss_child_start() failed [%d][%s].\n", ret, sss_strerror(ret)); ret = ERR_P11_CHILD; goto done;