ad_machine_pw_renewal.c revision 45e11be651dbd3855a35de4abd2922e5b9d4b963
2454dfa32c93c20a8522c6ed42fe057baaac9f9aStephan Bosch/*
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen SSSD
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen Authors:
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen Sumit Bose <sbose@redhat.com>
1f366614aaafcc9496ff85b25988f19c3254ab7cTimo Sirainen
1f366614aaafcc9496ff85b25988f19c3254ab7cTimo Sirainen Copyright (C) 2016 Red Hat
39ea5717264668e2c7f9f7986eb821d21785f47fTimo Sirainen
97943a36e08923d625898f5ca8ffd38325a3986dTimo Sirainen This program is free software; you can redistribute it and/or modify
3bc62efe513ebc7450cffe9a4e8f0b07424bf190Timo Sirainen it under the terms of the GNU General Public License as published by
f739c92a9237db03327dc82e3792e39c160a1e4dTimo Sirainen the Free Software Foundation; either version 3 of the License, or
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen (at your option) any later version.
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen This program is distributed in the hope that it will be useful,
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen but WITHOUT ANY WARRANTY; without even the implied warranty of
8bf42ce5ef783b96a2ded67524173e95e9b45adaTimo Sirainen MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen GNU General Public License for more details.
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen
f739c92a9237db03327dc82e3792e39c160a1e4dTimo Sirainen You should have received a copy of the GNU General Public License
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen along with this program. If not, see <http://www.gnu.org/licenses/>.
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen*/
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen#include "util/util.h"
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen#include "util/strtonum.h"
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen#include "providers/dp_ptask.h"
f739c92a9237db03327dc82e3792e39c160a1e4dTimo Sirainen#include "providers/ad/ad_common.h"
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen#ifndef RENEWAL_PROG_PATH
678d0463849ba777106eb7875f27db07a5d8e3dfTimo Sirainen#define RENEWAL_PROG_PATH "/usr/sbin/adcli"
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen#endif
f739c92a9237db03327dc82e3792e39c160a1e4dTimo Sirainen
f739c92a9237db03327dc82e3792e39c160a1e4dTimo Sirainenstruct renewal_data {
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen struct be_ctx *be_ctx;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen char *prog_path;
9c7f6dbf65ca01026e5f9c8c8b67c7e629c0b5e7Timo Sirainen const char **extra_args;
9c7f6dbf65ca01026e5f9c8c8b67c7e629c0b5e7Timo Sirainen};
2ac5f36aa7c2e7a07ba8815d43a6d7483f62e74cTimo Sirainen
9c7f6dbf65ca01026e5f9c8c8b67c7e629c0b5e7Timo Sirainenstatic errno_t get_adcli_extra_args(const char *ad_domain,
9c7f6dbf65ca01026e5f9c8c8b67c7e629c0b5e7Timo Sirainen const char *ad_hostname,
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen const char *ad_keytab,
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen size_t pw_lifetime_in_days,
9c7f6dbf65ca01026e5f9c8c8b67c7e629c0b5e7Timo Sirainen size_t period,
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen size_t initial_delay,
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen struct renewal_data *renewal_data)
9c7f6dbf65ca01026e5f9c8c8b67c7e629c0b5e7Timo Sirainen{
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen const char **args;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen size_t c = 0;
055389c58fa3915e12fb4e72ec86782ce77c5c72Timo Sirainen
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen if (ad_domain == NULL || ad_hostname == NULL) {
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen DEBUG(SSSDBG_CRIT_FAILURE, "Missing AD domain or hostname.\n");
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen return EINVAL;
f323e3f0de9841f399aba5919e3f25652a88fa65Timo Sirainen }
f323e3f0de9841f399aba5919e3f25652a88fa65Timo Sirainen
f323e3f0de9841f399aba5919e3f25652a88fa65Timo Sirainen renewal_data->prog_path = talloc_strdup(renewal_data, RENEWAL_PROG_PATH);
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen if (renewal_data->prog_path == NULL) {
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen DEBUG(SSSDBG_OP_FAILURE, "talloc_strdup failed.\n");
10399559650f552a23949772be79eb6a80198c5aTimo Sirainen return ENOMEM;
10399559650f552a23949772be79eb6a80198c5aTimo Sirainen }
a6a6ad107e509cf8952a28f740eb2023284497b9Timo Sirainen
39ea5717264668e2c7f9f7986eb821d21785f47fTimo Sirainen args = talloc_array(renewal_data, const char *, 8);
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen if (args == NULL) {
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen DEBUG(SSSDBG_OP_FAILURE, "talloc_array failed.\n");
a6a6ad107e509cf8952a28f740eb2023284497b9Timo Sirainen return ENOMEM;
f739c92a9237db03327dc82e3792e39c160a1e4dTimo Sirainen }
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen
bdb0f594a5673a0c5a16b92dc49eb2a8a66bdaceTimo Sirainen /* extra_args are added in revers order */
bdb0f594a5673a0c5a16b92dc49eb2a8a66bdaceTimo Sirainen /* first add NULL as a placeholder for the server name which is determined
bdb0f594a5673a0c5a16b92dc49eb2a8a66bdaceTimo Sirainen * at runtime */
bdb0f594a5673a0c5a16b92dc49eb2a8a66bdaceTimo Sirainen args[c++] = NULL;
bdb0f594a5673a0c5a16b92dc49eb2a8a66bdaceTimo Sirainen args[c++] = talloc_asprintf(args, "--computer-password-lifetime=%zu",
a6a6ad107e509cf8952a28f740eb2023284497b9Timo Sirainen pw_lifetime_in_days);
f739c92a9237db03327dc82e3792e39c160a1e4dTimo Sirainen args[c++] = talloc_asprintf(args, "--host-fqdn=%s", ad_hostname);
a6a6ad107e509cf8952a28f740eb2023284497b9Timo Sirainen if (ad_keytab != NULL) {
bdb0f594a5673a0c5a16b92dc49eb2a8a66bdaceTimo Sirainen args[c++] = talloc_asprintf(args, "--host-keytab=%s", ad_keytab);
bdb0f594a5673a0c5a16b92dc49eb2a8a66bdaceTimo Sirainen }
bdb0f594a5673a0c5a16b92dc49eb2a8a66bdaceTimo Sirainen args[c++] = talloc_asprintf(args, "--domain=%s", ad_domain);
bdb0f594a5673a0c5a16b92dc49eb2a8a66bdaceTimo Sirainen if (DEBUG_IS_SET(SSSDBG_TRACE_LIBS)) {
8f2eb1ee9ec07661bd50275da99b5f351972a49aTimo Sirainen args[c++] = talloc_strdup(args, "--verbose");
eca38954bcf972618f6b85932a3690acbd2b673aTimo Sirainen }
8f2eb1ee9ec07661bd50275da99b5f351972a49aTimo Sirainen args[c++] = talloc_strdup(args, "update");
8f2eb1ee9ec07661bd50275da99b5f351972a49aTimo Sirainen args[c] = NULL;
8f2eb1ee9ec07661bd50275da99b5f351972a49aTimo Sirainen
f739c92a9237db03327dc82e3792e39c160a1e4dTimo Sirainen do {
a6a6ad107e509cf8952a28f740eb2023284497b9Timo Sirainen if (args[--c] == NULL) {
a6a6ad107e509cf8952a28f740eb2023284497b9Timo Sirainen DEBUG(SSSDBG_OP_FAILURE,
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen "talloc failed while copying arguments.\n");
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen talloc_free(args);
678d0463849ba777106eb7875f27db07a5d8e3dfTimo Sirainen return ENOMEM;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen }
10399559650f552a23949772be79eb6a80198c5aTimo Sirainen } while (c != 1); /* is is expected that the first element is NULL */
dc599de6096c51e6c922e069bfbbcb7d68c50ffaStephan Bosch
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen renewal_data->extra_args = args;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen return EOK;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen}
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainenstruct renewal_state {
a943ed0f901e312445fd393249b91932797bba79Josef 'Jeff' Sipek int child_status;
3ccab0bac68040f179a7de45c516cec258e28fdbTimo Sirainen struct sss_child_ctx_old *child_ctx;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen struct tevent_timer *timeout_handler;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen struct tevent_context *ev;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen struct child_io_fds *io;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen};
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainenstatic void ad_machine_account_password_renewal_done(struct tevent_req *subreq);
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainenstatic void
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainenad_machine_account_password_renewal_timeout(struct tevent_context *ev,
37fed1bc1545f7eb1755b61d6a5ac4d083a693b3Timo Sirainen struct tevent_timer *te,
37fed1bc1545f7eb1755b61d6a5ac4d083a693b3Timo Sirainen struct timeval tv, void *pvt);
37fed1bc1545f7eb1755b61d6a5ac4d083a693b3Timo Sirainen
37fed1bc1545f7eb1755b61d6a5ac4d083a693b3Timo Sirainenstatic struct tevent_req *
37fed1bc1545f7eb1755b61d6a5ac4d083a693b3Timo Sirainenad_machine_account_password_renewal_send(TALLOC_CTX *mem_ctx,
37fed1bc1545f7eb1755b61d6a5ac4d083a693b3Timo Sirainen struct tevent_context *ev,
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen struct be_ctx *be_ctx,
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen struct be_ptask *be_ptask,
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen void *pvt)
62ff6002b1e37a42303c2c0107f324860232e204Timo Sirainen{
62ff6002b1e37a42303c2c0107f324860232e204Timo Sirainen struct renewal_data *renewal_data;
62ff6002b1e37a42303c2c0107f324860232e204Timo Sirainen struct renewal_state *state;
62ff6002b1e37a42303c2c0107f324860232e204Timo Sirainen struct tevent_req *req;
62ff6002b1e37a42303c2c0107f324860232e204Timo Sirainen struct tevent_req *subreq;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen pid_t child_pid;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen struct timeval tv;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen int pipefd_to_child[2] = PIPE_INIT;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen int pipefd_from_child[2] = PIPE_INIT;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen int ret;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen const char **extra_args;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen const char *server_name;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen req = tevent_req_create(mem_ctx, &state, struct renewal_state);
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen if (req == NULL) {
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen DEBUG(SSSDBG_OP_FAILURE, "tevent_req_create failed.\n");
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen return NULL;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen }
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen renewal_data = talloc_get_type(pvt, struct renewal_data);
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen state->ev = ev;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen state->child_status = EFAULT;
b5052fbfdbc2678cc8f12899afe55c998f43b740Timo Sirainen state->io = talloc(state, struct child_io_fds);
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen if (state->io == NULL) {
f739c92a9237db03327dc82e3792e39c160a1e4dTimo Sirainen DEBUG(SSSDBG_CRIT_FAILURE, "talloc failed.\n");
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen ret = ENOMEM;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen goto done;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen }
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen state->io->write_to_child_fd = -1;
a943ed0f901e312445fd393249b91932797bba79Josef 'Jeff' Sipek state->io->read_from_child_fd = -1;
f739c92a9237db03327dc82e3792e39c160a1e4dTimo Sirainen talloc_set_destructor((void *) state->io, child_io_destructor);
f739c92a9237db03327dc82e3792e39c160a1e4dTimo Sirainen
f739c92a9237db03327dc82e3792e39c160a1e4dTimo Sirainen server_name = be_fo_get_active_server_name(be_ctx, AD_SERVICE_NAME);
f739c92a9237db03327dc82e3792e39c160a1e4dTimo Sirainen talloc_zfree(renewal_data->extra_args[0]);
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen if (server_name != NULL) {
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen renewal_data->extra_args[0] = talloc_asprintf(renewal_data->extra_args,
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen "--domain-controller=%s",
3bc62efe513ebc7450cffe9a4e8f0b07424bf190Timo Sirainen server_name);
b5052fbfdbc2678cc8f12899afe55c998f43b740Timo Sirainen /* if talloc_asprintf() fails we let adcli try to find a server */
3bc62efe513ebc7450cffe9a4e8f0b07424bf190Timo Sirainen }
b5052fbfdbc2678cc8f12899afe55c998f43b740Timo Sirainen
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen extra_args = renewal_data->extra_args;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen if (extra_args[0] == NULL) {
f739c92a9237db03327dc82e3792e39c160a1e4dTimo Sirainen extra_args = &renewal_data->extra_args[1];
f739c92a9237db03327dc82e3792e39c160a1e4dTimo Sirainen }
f739c92a9237db03327dc82e3792e39c160a1e4dTimo Sirainen
f739c92a9237db03327dc82e3792e39c160a1e4dTimo Sirainen ret = pipe(pipefd_from_child);
b5052fbfdbc2678cc8f12899afe55c998f43b740Timo Sirainen if (ret == -1) {
f739c92a9237db03327dc82e3792e39c160a1e4dTimo Sirainen ret = errno;
f739c92a9237db03327dc82e3792e39c160a1e4dTimo Sirainen DEBUG(SSSDBG_CRIT_FAILURE,
f739c92a9237db03327dc82e3792e39c160a1e4dTimo Sirainen "pipe failed [%d][%s].\n", ret, strerror(ret));
f739c92a9237db03327dc82e3792e39c160a1e4dTimo Sirainen goto done;
b5052fbfdbc2678cc8f12899afe55c998f43b740Timo Sirainen }
f739c92a9237db03327dc82e3792e39c160a1e4dTimo Sirainen ret = pipe(pipefd_to_child);
37fed1bc1545f7eb1755b61d6a5ac4d083a693b3Timo Sirainen if (ret == -1) {
f739c92a9237db03327dc82e3792e39c160a1e4dTimo Sirainen ret = errno;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen DEBUG(SSSDBG_CRIT_FAILURE,
3ccab0bac68040f179a7de45c516cec258e28fdbTimo Sirainen "pipe failed [%d][%s].\n", ret, strerror(ret));
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen goto done;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen }
bdb0f594a5673a0c5a16b92dc49eb2a8a66bdaceTimo Sirainen
e93184a9055c2530366dfe617e07199603c399ddMartti Rannanjärvi child_pid = fork();
3350b29fce44f8bc8fa015dad57024a8de301d38Timo Sirainen if (child_pid == 0) { /* child */
3350b29fce44f8bc8fa015dad57024a8de301d38Timo Sirainen exec_child_ex(state, pipefd_to_child, pipefd_from_child,
3350b29fce44f8bc8fa015dad57024a8de301d38Timo Sirainen renewal_data->prog_path, -1,
1f366614aaafcc9496ff85b25988f19c3254ab7cTimo Sirainen extra_args, true,
3350b29fce44f8bc8fa015dad57024a8de301d38Timo Sirainen STDIN_FILENO, STDERR_FILENO);
3350b29fce44f8bc8fa015dad57024a8de301d38Timo Sirainen
3350b29fce44f8bc8fa015dad57024a8de301d38Timo Sirainen /* We should never get here */
3350b29fce44f8bc8fa015dad57024a8de301d38Timo Sirainen DEBUG(SSSDBG_CRIT_FAILURE, "Could not exec renewal child\n");
1f366614aaafcc9496ff85b25988f19c3254ab7cTimo Sirainen } else if (child_pid > 0) { /* parent */
c224fff79d18480a65e9b4504b891b8ea176f5b1Timo Sirainen
bdb0f594a5673a0c5a16b92dc49eb2a8a66bdaceTimo Sirainen state->io->read_from_child_fd = pipefd_from_child[0];
bdb0f594a5673a0c5a16b92dc49eb2a8a66bdaceTimo Sirainen PIPE_FD_CLOSE(pipefd_from_child[1]);
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen sss_fd_nonblocking(state->io->read_from_child_fd);
f739c92a9237db03327dc82e3792e39c160a1e4dTimo Sirainen
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen state->io->write_to_child_fd = pipefd_to_child[1];
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen PIPE_FD_CLOSE(pipefd_to_child[0]);
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen sss_fd_nonblocking(state->io->write_to_child_fd);
b5052fbfdbc2678cc8f12899afe55c998f43b740Timo Sirainen
b5052fbfdbc2678cc8f12899afe55c998f43b740Timo Sirainen /* Set up SIGCHLD handler */
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen ret = child_handler_setup(ev, child_pid, NULL, NULL, &state->child_ctx);
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen if (ret != EOK) {
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen DEBUG(SSSDBG_OP_FAILURE, "Could not set up child handlers [%d]: %s\n",
b5052fbfdbc2678cc8f12899afe55c998f43b740Timo Sirainen ret, sss_strerror(ret));
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen ret = ERR_RENEWAL_CHILD;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen goto done;
3ccab0bac68040f179a7de45c516cec258e28fdbTimo Sirainen }
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen /* Set up timeout handler */
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen tv = tevent_timeval_current_ofs(be_ptask_get_timeout(be_ptask), 0);
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen state->timeout_handler = tevent_add_timer(ev, req, tv,
9c7f6dbf65ca01026e5f9c8c8b67c7e629c0b5e7Timo Sirainen ad_machine_account_password_renewal_timeout,
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen req);
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen if(state->timeout_handler == NULL) {
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen ret = ERR_RENEWAL_CHILD;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen goto done;
9c7f6dbf65ca01026e5f9c8c8b67c7e629c0b5e7Timo Sirainen }
b5052fbfdbc2678cc8f12899afe55c998f43b740Timo Sirainen
9c7f6dbf65ca01026e5f9c8c8b67c7e629c0b5e7Timo Sirainen subreq = read_pipe_send(state, ev, state->io->read_from_child_fd);
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen if (subreq == NULL) {
9c7f6dbf65ca01026e5f9c8c8b67c7e629c0b5e7Timo Sirainen DEBUG(SSSDBG_OP_FAILURE, "read_pipe_send failed.\n");
9c7f6dbf65ca01026e5f9c8c8b67c7e629c0b5e7Timo Sirainen ret = ERR_RENEWAL_CHILD;
8ad53e0bb29f61350f608fc519210f2442c20775Timo Sirainen goto done;
9c7f6dbf65ca01026e5f9c8c8b67c7e629c0b5e7Timo Sirainen }
9c7f6dbf65ca01026e5f9c8c8b67c7e629c0b5e7Timo Sirainen tevent_req_set_callback(subreq,
9c7f6dbf65ca01026e5f9c8c8b67c7e629c0b5e7Timo Sirainen ad_machine_account_password_renewal_done, req);
9c7f6dbf65ca01026e5f9c8c8b67c7e629c0b5e7Timo Sirainen
9c7f6dbf65ca01026e5f9c8c8b67c7e629c0b5e7Timo Sirainen /* Now either wait for the timeout to fire or the child
9c7f6dbf65ca01026e5f9c8c8b67c7e629c0b5e7Timo Sirainen * to finish
9c7f6dbf65ca01026e5f9c8c8b67c7e629c0b5e7Timo Sirainen */
9c7f6dbf65ca01026e5f9c8c8b67c7e629c0b5e7Timo Sirainen } else { /* error */
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen ret = errno;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen DEBUG(SSSDBG_CRIT_FAILURE, "fork failed [%d][%s].\n",
055389c58fa3915e12fb4e72ec86782ce77c5c72Timo Sirainen ret, sss_strerror(ret));
055389c58fa3915e12fb4e72ec86782ce77c5c72Timo Sirainen goto done;
37fed1bc1545f7eb1755b61d6a5ac4d083a693b3Timo Sirainen }
37fed1bc1545f7eb1755b61d6a5ac4d083a693b3Timo Sirainen
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen ret = EOK;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainendone:
9c7f6dbf65ca01026e5f9c8c8b67c7e629c0b5e7Timo Sirainen if (ret != EOK) {
9c7f6dbf65ca01026e5f9c8c8b67c7e629c0b5e7Timo Sirainen PIPE_CLOSE(pipefd_from_child);
9c7f6dbf65ca01026e5f9c8c8b67c7e629c0b5e7Timo Sirainen PIPE_CLOSE(pipefd_to_child);
9c7f6dbf65ca01026e5f9c8c8b67c7e629c0b5e7Timo Sirainen tevent_req_error(req, ret);
9c7f6dbf65ca01026e5f9c8c8b67c7e629c0b5e7Timo Sirainen tevent_req_post(req, ev);
9c7f6dbf65ca01026e5f9c8c8b67c7e629c0b5e7Timo Sirainen }
9c7f6dbf65ca01026e5f9c8c8b67c7e629c0b5e7Timo Sirainen return req;
9c7f6dbf65ca01026e5f9c8c8b67c7e629c0b5e7Timo Sirainen}
9c7f6dbf65ca01026e5f9c8c8b67c7e629c0b5e7Timo Sirainen
9c7f6dbf65ca01026e5f9c8c8b67c7e629c0b5e7Timo Sirainenstatic void ad_machine_account_password_renewal_done(struct tevent_req *subreq)
9c7f6dbf65ca01026e5f9c8c8b67c7e629c0b5e7Timo Sirainen{
9c7f6dbf65ca01026e5f9c8c8b67c7e629c0b5e7Timo Sirainen uint8_t *buf;
9c7f6dbf65ca01026e5f9c8c8b67c7e629c0b5e7Timo Sirainen ssize_t buf_len;
8d25b6ad05b99e75613cb045a121efd51e6afbb6Timo Sirainen struct tevent_req *req = tevent_req_callback_data(subreq,
8d25b6ad05b99e75613cb045a121efd51e6afbb6Timo Sirainen struct tevent_req);
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen struct renewal_state *state = tevent_req_data(req, struct renewal_state);
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen int ret;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen
9c7f6dbf65ca01026e5f9c8c8b67c7e629c0b5e7Timo Sirainen talloc_zfree(state->timeout_handler);
678d0463849ba777106eb7875f27db07a5d8e3dfTimo Sirainen
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen ret = read_pipe_recv(subreq, state, &buf, &buf_len);
c73415e93ecf1c699ef054d2b179b10976fa23f3Timo Sirainen talloc_zfree(subreq);
c73415e93ecf1c699ef054d2b179b10976fa23f3Timo Sirainen if (ret != EOK) {
c73415e93ecf1c699ef054d2b179b10976fa23f3Timo Sirainen tevent_req_error(req, ret);
9c7f6dbf65ca01026e5f9c8c8b67c7e629c0b5e7Timo Sirainen return;
9c7f6dbf65ca01026e5f9c8c8b67c7e629c0b5e7Timo Sirainen }
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen DEBUG(SSSDBG_TRACE_LIBS, "--- adcli output start---\n"
76b4207273534f71365bc7f900c23a5160692802Timo Sirainen "%.*s"
76b4207273534f71365bc7f900c23a5160692802Timo Sirainen "---adcli output end---\n",
76b4207273534f71365bc7f900c23a5160692802Timo Sirainen (int) buf_len, buf);
76b4207273534f71365bc7f900c23a5160692802Timo Sirainen
76b4207273534f71365bc7f900c23a5160692802Timo Sirainen tevent_req_done(req);
76b4207273534f71365bc7f900c23a5160692802Timo Sirainen return;
76b4207273534f71365bc7f900c23a5160692802Timo Sirainen}
76b4207273534f71365bc7f900c23a5160692802Timo Sirainen
76b4207273534f71365bc7f900c23a5160692802Timo Sirainenstatic void
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainenad_machine_account_password_renewal_timeout(struct tevent_context *ev,
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen struct tevent_timer *te,
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen struct timeval tv, void *pvt)
8d25b6ad05b99e75613cb045a121efd51e6afbb6Timo Sirainen{
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen struct tevent_req *req = talloc_get_type(pvt, struct tevent_req);
8d25b6ad05b99e75613cb045a121efd51e6afbb6Timo Sirainen struct renewal_state *state = tevent_req_data(req, struct renewal_state);
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen DEBUG(SSSDBG_CRIT_FAILURE, "Timeout reached for AD renewal child.\n");
055389c58fa3915e12fb4e72ec86782ce77c5c72Timo Sirainen child_handler_destroy(state->child_ctx);
055389c58fa3915e12fb4e72ec86782ce77c5c72Timo Sirainen state->child_ctx = NULL;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen state->child_status = ETIMEDOUT;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen tevent_req_error(req, ERR_RENEWAL_CHILD);
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen}
055389c58fa3915e12fb4e72ec86782ce77c5c72Timo Sirainen
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainenstatic errno_t
055389c58fa3915e12fb4e72ec86782ce77c5c72Timo Sirainenad_machine_account_password_renewal_recv(struct tevent_req *req)
3ccab0bac68040f179a7de45c516cec258e28fdbTimo Sirainen{
9c7f6dbf65ca01026e5f9c8c8b67c7e629c0b5e7Timo Sirainen
8d25b6ad05b99e75613cb045a121efd51e6afbb6Timo Sirainen TEVENT_REQ_RETURN_ON_ERROR(req);
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen return EOK;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen}
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainenerrno_t ad_machine_account_password_renewal_init(struct be_ctx *be_ctx,
8bf42ce5ef783b96a2ded67524173e95e9b45adaTimo Sirainen struct ad_options *ad_opts)
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen{
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen int ret;
dba8af1faaf9fd3957254bb6f2234b285f77096fTimo Sirainen struct renewal_data *renewal_data;
8bf42ce5ef783b96a2ded67524173e95e9b45adaTimo Sirainen int lifetime;
8bf42ce5ef783b96a2ded67524173e95e9b45adaTimo Sirainen size_t period;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen size_t initial_delay;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen const char *dummy;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen char **opt_list;
8bf42ce5ef783b96a2ded67524173e95e9b45adaTimo Sirainen int opt_list_size;
8bf42ce5ef783b96a2ded67524173e95e9b45adaTimo Sirainen char *endptr;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen ret = access(RENEWAL_PROG_PATH, X_OK);
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen if (ret != 0) {
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen ret = errno;
678d0463849ba777106eb7875f27db07a5d8e3dfTimo Sirainen DEBUG(SSSDBG_CONF_SETTINGS,
8bf42ce5ef783b96a2ded67524173e95e9b45adaTimo Sirainen "The helper program ["RENEWAL_PROG_PATH"] for renewal "
2ac5f36aa7c2e7a07ba8815d43a6d7483f62e74cTimo Sirainen "doesn't exist [%d]: %s\n", ret, strerror(ret));
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen return EOK;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen }
7bd72e4deca3cbf757dd1ea298486d9f3bc24226Timo Sirainen
a75d470c9223a75801418fcdda258885c36317e0Timo Sirainen lifetime = dp_opt_get_int(ad_opts->basic,
a75d470c9223a75801418fcdda258885c36317e0Timo Sirainen AD_MAXIMUM_MACHINE_ACCOUNT_PASSWORD_AGE);
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen if (lifetime == 0) {
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen DEBUG(SSSDBG_CONF_SETTINGS, "Automatic machine account renewal disabled.\n");
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen return EOK;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen }
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen if (lifetime < 0) {
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen DEBUG(SSSDBG_CRIT_FAILURE,
7bd72e4deca3cbf757dd1ea298486d9f3bc24226Timo Sirainen "Illegal value [%d] for password lifetime.\n", lifetime);
8bf42ce5ef783b96a2ded67524173e95e9b45adaTimo Sirainen return EINVAL;
3954326e793bdef1e94e0ad781ed6cc7e48beebbTimo Sirainen }
8bf42ce5ef783b96a2ded67524173e95e9b45adaTimo Sirainen
3954326e793bdef1e94e0ad781ed6cc7e48beebbTimo Sirainen renewal_data = talloc(be_ctx, struct renewal_data);
3954326e793bdef1e94e0ad781ed6cc7e48beebbTimo Sirainen if (renewal_data == NULL) {
e48f289d2e5b2546a2c5dcc90f7ab624cc58cca2Stephan Bosch DEBUG(SSSDBG_OP_FAILURE, "talloc failed.\n");
e48f289d2e5b2546a2c5dcc90f7ab624cc58cca2Stephan Bosch return ENOMEM;
e48f289d2e5b2546a2c5dcc90f7ab624cc58cca2Stephan Bosch }
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen dummy = dp_opt_get_cstring(ad_opts->basic,
3c63c219ae7854b4f1d44a671a65572aa242cbcfTimo Sirainen AD_MACHINE_ACCOUNT_PASSWORD_RENEWAL_OPTS);
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen ret = split_on_separator(renewal_data, dummy, ':', true, false,
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen &opt_list, &opt_list_size);
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen if (ret != EOK) {
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen DEBUG(SSSDBG_OP_FAILURE, "split_on_separator failed.\n");
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen goto done;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen }
8bf42ce5ef783b96a2ded67524173e95e9b45adaTimo Sirainen
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen if (opt_list_size != 2) {
7bd72e4deca3cbf757dd1ea298486d9f3bc24226Timo Sirainen DEBUG(SSSDBG_CRIT_FAILURE, "Wrong number of renewal options.\n");
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen ret = EINVAL;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen goto done;
7bd72e4deca3cbf757dd1ea298486d9f3bc24226Timo Sirainen }
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen
3ccab0bac68040f179a7de45c516cec258e28fdbTimo Sirainen errno = 0;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen period = strtouint32(opt_list[0], &endptr, 10);
8bf42ce5ef783b96a2ded67524173e95e9b45adaTimo Sirainen if (errno != 0 || *endptr != '\0' || opt_list[0] == endptr) {
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen DEBUG(SSSDBG_CRIT_FAILURE, "Unable to parse first renewal option.\n");
3ccab0bac68040f179a7de45c516cec258e28fdbTimo Sirainen ret = EINVAL;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen goto done;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen }
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen errno = 0;
e3fabe8d0faa9aab7cae2d0eee9653f581a3061dTimo Sirainen initial_delay = strtouint32(opt_list[1], &endptr, 10);
e5ff2112aea089f3de2badf9b1635677791d1384Timo Sirainen if (errno != 0 || *endptr != '\0' || opt_list[0] == endptr) {
e5ff2112aea089f3de2badf9b1635677791d1384Timo Sirainen DEBUG(SSSDBG_CRIT_FAILURE, "Unable to parse second renewal option.\n");
e5ff2112aea089f3de2badf9b1635677791d1384Timo Sirainen ret = EINVAL;
b141c303bf09b6ae43e1eb4aac1e1a6b796b9d35Timo Sirainen goto done;
e5ff2112aea089f3de2badf9b1635677791d1384Timo Sirainen }
b141c303bf09b6ae43e1eb4aac1e1a6b796b9d35Timo Sirainen
b141c303bf09b6ae43e1eb4aac1e1a6b796b9d35Timo Sirainen ret = get_adcli_extra_args(dp_opt_get_cstring(ad_opts->basic, AD_DOMAIN),
b141c303bf09b6ae43e1eb4aac1e1a6b796b9d35Timo Sirainen dp_opt_get_cstring(ad_opts->basic, AD_HOSTNAME),
b141c303bf09b6ae43e1eb4aac1e1a6b796b9d35Timo Sirainen dp_opt_get_cstring(ad_opts->id_ctx->sdap_id_ctx->opts->basic,
b141c303bf09b6ae43e1eb4aac1e1a6b796b9d35Timo Sirainen SDAP_KRB5_KEYTAB),
b141c303bf09b6ae43e1eb4aac1e1a6b796b9d35Timo Sirainen lifetime, period, initial_delay, renewal_data);
e5ff2112aea089f3de2badf9b1635677791d1384Timo Sirainen if (ret != EOK) {
e5ff2112aea089f3de2badf9b1635677791d1384Timo Sirainen DEBUG(SSSDBG_OP_FAILURE, "get_adcli_extra_args failed.\n");
e5ff2112aea089f3de2badf9b1635677791d1384Timo Sirainen goto done;
e5ff2112aea089f3de2badf9b1635677791d1384Timo Sirainen }
e5ff2112aea089f3de2badf9b1635677791d1384Timo Sirainen
b141c303bf09b6ae43e1eb4aac1e1a6b796b9d35Timo Sirainen ret = be_ptask_create(be_ctx, be_ctx, period, initial_delay, 0, 0, 60,
e5ff2112aea089f3de2badf9b1635677791d1384Timo Sirainen BE_PTASK_OFFLINE_DISABLE, 0,
b141c303bf09b6ae43e1eb4aac1e1a6b796b9d35Timo Sirainen ad_machine_account_password_renewal_send,
b141c303bf09b6ae43e1eb4aac1e1a6b796b9d35Timo Sirainen ad_machine_account_password_renewal_recv,
b141c303bf09b6ae43e1eb4aac1e1a6b796b9d35Timo Sirainen renewal_data,
b141c303bf09b6ae43e1eb4aac1e1a6b796b9d35Timo Sirainen "AD machine account password renewal", NULL);
e5ff2112aea089f3de2badf9b1635677791d1384Timo Sirainen if (ret != EOK) {
e5ff2112aea089f3de2badf9b1635677791d1384Timo Sirainen DEBUG(SSSDBG_OP_FAILURE, "be_ptask_create failed.\n");
b141c303bf09b6ae43e1eb4aac1e1a6b796b9d35Timo Sirainen goto done;
e5ff2112aea089f3de2badf9b1635677791d1384Timo Sirainen }
b141c303bf09b6ae43e1eb4aac1e1a6b796b9d35Timo Sirainen
b141c303bf09b6ae43e1eb4aac1e1a6b796b9d35Timo Sirainen ret = EOK;
b141c303bf09b6ae43e1eb4aac1e1a6b796b9d35Timo Sirainen
b141c303bf09b6ae43e1eb4aac1e1a6b796b9d35Timo Sirainendone:
b141c303bf09b6ae43e1eb4aac1e1a6b796b9d35Timo Sirainen if (ret != EOK) {
b141c303bf09b6ae43e1eb4aac1e1a6b796b9d35Timo Sirainen talloc_free(renewal_data);
e5ff2112aea089f3de2badf9b1635677791d1384Timo Sirainen }
e5ff2112aea089f3de2badf9b1635677791d1384Timo Sirainen
e5ff2112aea089f3de2badf9b1635677791d1384Timo Sirainen return ret;
e5ff2112aea089f3de2badf9b1635677791d1384Timo Sirainen}
e5ff2112aea089f3de2badf9b1635677791d1384Timo Sirainen