proxy_init.c revision d9577dbd92555b0755881e37724019ef9c578404
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher Stephen Gallagher <sgallagh@redhat.com>
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher Copyright (C) 2010 Red Hat
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher This program is free software; you can redistribute it and/or modify
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher it under the terms of the GNU General Public License as published by
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher the Free Software Foundation; either version 3 of the License, or
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher (at your option) any later version.
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher This program is distributed in the hope that it will be useful,
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher but WITHOUT ANY WARRANTY; without even the implied warranty of
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher GNU General Public License for more details.
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher You should have received a copy of the GNU General Public License
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher along with this program. If not, see <http://www.gnu.org/licenses/>.
d9577dbd92555b0755881e37724019ef9c578404Stef Walterstatic int client_registration(struct sbus_request *dbus_req);
769347ad4d35d43488eb98f980143495b0db415dStef Walterstatic struct data_provider_iface proxy_methods = {
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagherstatic void proxy_shutdown(struct be_req *req)
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher /* TODO: Clean up any internal data */
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagherstatic void proxy_auth_shutdown(struct be_req *req)
03abdaa21ecf562b714f204ca42379ff08626f75Simo Sorce talloc_free(be_ctx->bet_info[BET_AUTH].pvt_bet_data);
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagherstatic void *proxy_dlsym(void *handle, const char *functemp, char *libname)
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher funcname = talloc_asprintf(NULL, functemp, libname);
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagherint sssm_proxy_id_init(struct be_ctx *bectx,
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher ctx = talloc_zero(bectx, struct proxy_id_ctx);
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher ret = confdb_get_string(bectx->cdb, ctx, bectx->conf_path,
51773686d354b82081830444c048706d83d43d65Jakub Hrozek ret = confdb_get_bool(bectx->cdb, bectx->conf_path,
51773686d354b82081830444c048706d83d43d65Jakub Hrozek CONFDB_PROXY_FAST_ALIAS, false, &ctx->fast_alias);
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher libpath = talloc_asprintf(ctx, "libnss_%s.so.2", libname);
83bf46f4066e3d5e838a32357c201de9bd6ecdfdNikolai Kondrashov "Unable to load %s module with path, error: %s\n",
e4c0aa467500c2919c76776d3667f4b08f1ad09dSumit Bose ctx->ops.getpwnam_r = proxy_dlsym(ctx->handle, "_nss_%s_getpwnam_r",
83bf46f4066e3d5e838a32357c201de9bd6ecdfdNikolai Kondrashov "Failed to load NSS fns, error: %s\n", dlerror());
e4c0aa467500c2919c76776d3667f4b08f1ad09dSumit Bose ctx->ops.getpwuid_r = proxy_dlsym(ctx->handle, "_nss_%s_getpwuid_r",
83bf46f4066e3d5e838a32357c201de9bd6ecdfdNikolai Kondrashov "Failed to load NSS fns, error: %s\n", dlerror());
e4c0aa467500c2919c76776d3667f4b08f1ad09dSumit Bose ctx->ops.setpwent = proxy_dlsym(ctx->handle, "_nss_%s_setpwent", libname);
83bf46f4066e3d5e838a32357c201de9bd6ecdfdNikolai Kondrashov "Failed to load NSS fns, error: %s\n", dlerror());
e4c0aa467500c2919c76776d3667f4b08f1ad09dSumit Bose ctx->ops.getpwent_r = proxy_dlsym(ctx->handle, "_nss_%s_getpwent_r",
83bf46f4066e3d5e838a32357c201de9bd6ecdfdNikolai Kondrashov "Failed to load NSS fns, error: %s\n", dlerror());
e4c0aa467500c2919c76776d3667f4b08f1ad09dSumit Bose ctx->ops.endpwent = proxy_dlsym(ctx->handle, "_nss_%s_endpwent", libname);
83bf46f4066e3d5e838a32357c201de9bd6ecdfdNikolai Kondrashov "Failed to load NSS fns, error: %s\n", dlerror());
e4c0aa467500c2919c76776d3667f4b08f1ad09dSumit Bose ctx->ops.getgrnam_r = proxy_dlsym(ctx->handle, "_nss_%s_getgrnam_r",
83bf46f4066e3d5e838a32357c201de9bd6ecdfdNikolai Kondrashov "Failed to load NSS fns, error: %s\n", dlerror());
e4c0aa467500c2919c76776d3667f4b08f1ad09dSumit Bose ctx->ops.getgrgid_r = proxy_dlsym(ctx->handle, "_nss_%s_getgrgid_r",
83bf46f4066e3d5e838a32357c201de9bd6ecdfdNikolai Kondrashov "Failed to load NSS fns, error: %s\n", dlerror());
e4c0aa467500c2919c76776d3667f4b08f1ad09dSumit Bose ctx->ops.setgrent = proxy_dlsym(ctx->handle, "_nss_%s_setgrent", libname);
83bf46f4066e3d5e838a32357c201de9bd6ecdfdNikolai Kondrashov "Failed to load NSS fns, error: %s\n", dlerror());
e4c0aa467500c2919c76776d3667f4b08f1ad09dSumit Bose ctx->ops.getgrent_r = proxy_dlsym(ctx->handle, "_nss_%s_getgrent_r",
83bf46f4066e3d5e838a32357c201de9bd6ecdfdNikolai Kondrashov "Failed to load NSS fns, error: %s\n", dlerror());
e4c0aa467500c2919c76776d3667f4b08f1ad09dSumit Bose ctx->ops.endgrent = proxy_dlsym(ctx->handle, "_nss_%s_endgrent", libname);
83bf46f4066e3d5e838a32357c201de9bd6ecdfdNikolai Kondrashov "Failed to load NSS fns, error: %s\n", dlerror());
e4c0aa467500c2919c76776d3667f4b08f1ad09dSumit Bose ctx->ops.initgroups_dyn = proxy_dlsym(ctx->handle, "_nss_%s_initgroups_dyn",
83bf46f4066e3d5e838a32357c201de9bd6ecdfdNikolai Kondrashov DEBUG(SSSDBG_CRIT_FAILURE, "The '%s' library does not provides the "
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher "_nss_XXX_initgroups_dyn function!\n"
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher "initgroups will be slow as it will require "
e4c0aa467500c2919c76776d3667f4b08f1ad09dSumit Bose ctx->ops.setnetgrent = proxy_dlsym(ctx->handle, "_nss_%s_setnetgrent",
83bf46f4066e3d5e838a32357c201de9bd6ecdfdNikolai Kondrashov "Failed to load _nss_%s_setnetgrent, error: %s. "
d7dc57bcc2468bee756bcd568daee0644e5b888dSumit Bose "The library does not support netgroups.\n", libname,
e4c0aa467500c2919c76776d3667f4b08f1ad09dSumit Bose ctx->ops.getnetgrent_r = proxy_dlsym(ctx->handle, "_nss_%s_getnetgrent_r",
83bf46f4066e3d5e838a32357c201de9bd6ecdfdNikolai Kondrashov "Failed to load _nss_%s_getnetgrent_r, error: %s. "
d7dc57bcc2468bee756bcd568daee0644e5b888dSumit Bose "The library does not support netgroups.\n", libname,
e4c0aa467500c2919c76776d3667f4b08f1ad09dSumit Bose ctx->ops.endnetgrent = proxy_dlsym(ctx->handle, "_nss_%s_endnetgrent",
83bf46f4066e3d5e838a32357c201de9bd6ecdfdNikolai Kondrashov "Failed to load _nss_%s_endnetgrent, error: %s. "
d7dc57bcc2468bee756bcd568daee0644e5b888dSumit Bose "The library does not support netgroups.\n", libname,
aec5785126354bd8b192f63fe04ea08dae9c0705Stephen Gallagher ctx->ops.getservbyname_r = proxy_dlsym(ctx->handle,
aec5785126354bd8b192f63fe04ea08dae9c0705Stephen Gallagher "_nss_%s_getservbyname_r",
a3c8390d19593b1e5277d95bfb4ab206d4785150Nikolai Kondrashov "Failed to load _nss_%s_getservbyname_r, error: %s. "
aec5785126354bd8b192f63fe04ea08dae9c0705Stephen Gallagher "The library does not support services.\n",
aec5785126354bd8b192f63fe04ea08dae9c0705Stephen Gallagher ctx->ops.getservbyport_r = proxy_dlsym(ctx->handle,
aec5785126354bd8b192f63fe04ea08dae9c0705Stephen Gallagher "_nss_%s_getservbyport_r",
a3c8390d19593b1e5277d95bfb4ab206d4785150Nikolai Kondrashov "Failed to load _nss_%s_getservbyport_r, error: %s. "
aec5785126354bd8b192f63fe04ea08dae9c0705Stephen Gallagher "The library does not support services.\n",
627d83dff183219826489949cb55ef71945e94abStephen Gallagher ctx->ops.setservent = proxy_dlsym(ctx->handle,
627d83dff183219826489949cb55ef71945e94abStephen Gallagher "_nss_%s_setservent",
a3c8390d19593b1e5277d95bfb4ab206d4785150Nikolai Kondrashov "Failed to load _nss_%s_setservent, error: %s. "
627d83dff183219826489949cb55ef71945e94abStephen Gallagher "The library does not support services.\n",
627d83dff183219826489949cb55ef71945e94abStephen Gallagher ctx->ops.getservent_r = proxy_dlsym(ctx->handle,
627d83dff183219826489949cb55ef71945e94abStephen Gallagher "_nss_%s_getservent_r",
a3c8390d19593b1e5277d95bfb4ab206d4785150Nikolai Kondrashov "Failed to load _nss_%s_getservent_r, error: %s. "
627d83dff183219826489949cb55ef71945e94abStephen Gallagher "The library does not support services.\n",
627d83dff183219826489949cb55ef71945e94abStephen Gallagher ctx->ops.endservent = proxy_dlsym(ctx->handle,
627d83dff183219826489949cb55ef71945e94abStephen Gallagher "_nss_%s_endservent",
a3c8390d19593b1e5277d95bfb4ab206d4785150Nikolai Kondrashov "Failed to load _nss_%s_endservent, error: %s. "
627d83dff183219826489949cb55ef71945e94abStephen Gallagher "The library does not support services.\n",
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagherstatic void init_timeout(struct tevent_context *ev,
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagherstatic int proxy_client_init(struct sbus_connection *conn, void *data)
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher proxy_auth_ctx = talloc_get_type(data, struct proxy_auth_ctx);
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher /* hang off this memory to the connection so that when the connection
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher * is freed we can potentially call a destructor */
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher proxy_cli = talloc_zero(conn, struct proxy_client);
83bf46f4066e3d5e838a32357c201de9bd6ecdfdNikolai Kondrashov DEBUG(SSSDBG_FATAL_FAILURE,"Out of memory?!\n");
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher proxy_cli->proxy_auth_ctx = proxy_auth_ctx;
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher /* 5 seconds should be plenty */
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher proxy_cli->timeout = tevent_add_timer(proxy_auth_ctx->be->ev, proxy_cli,
83bf46f4066e3d5e838a32357c201de9bd6ecdfdNikolai Kondrashov DEBUG(SSSDBG_FATAL_FAILURE,"Out of memory?!\n");
83bf46f4066e3d5e838a32357c201de9bd6ecdfdNikolai Kondrashov "Set-up proxy client ID timeout [%p]\n", proxy_cli->timeout);
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher /* Attach the client context to the connection context, so that it is
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher * always available when we need to manage the connection. */
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher sbus_conn_set_private_data(conn, proxy_cli);
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagherstatic void init_timeout(struct tevent_context *ev,
83bf46f4066e3d5e838a32357c201de9bd6ecdfdNikolai Kondrashov "Client timed out before Identification [%p]!\n", te);
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher proxy_cli = talloc_get_type(ptr, struct proxy_client);
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher /* If we time out here, we will also time out to
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher * pc_init_timeout(), so we'll finish the request
d9577dbd92555b0755881e37724019ef9c578404Stef Walterstatic int client_registration(struct sbus_request *dbus_req)
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher dbus_uint16_t version = DATA_PROVIDER_VERSION;
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher proxy_cli = talloc_get_type(data, struct proxy_client);
83bf46f4066e3d5e838a32357c201de9bd6ecdfdNikolai Kondrashov DEBUG(SSSDBG_FATAL_FAILURE, "Connection holds no valid init data\n");
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher /* First thing, cancel the timeout */
83bf46f4066e3d5e838a32357c201de9bd6ecdfdNikolai Kondrashov "Cancel proxy client ID timeout [%p]\n", proxy_cli->timeout);
d9577dbd92555b0755881e37724019ef9c578404Stef Walter dbret = dbus_message_get_args(dbus_req->message, &dbus_error,
83bf46f4066e3d5e838a32357c201de9bd6ecdfdNikolai Kondrashov "Failed to parse message, killing connection\n");
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher if (dbus_error_is_set(&dbus_error)) dbus_error_free(&dbus_error);
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher /* FIXME: should we just talloc_zfree(conn) ? */
a3c8390d19593b1e5277d95bfb4ab206d4785150Nikolai Kondrashov DEBUG(SSSDBG_FUNC_DATA, "Proxy client [%"PRIu32"] connected\n", cli_id);
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher /* Check the hash table */
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher if (!hash_has_key(proxy_cli->proxy_auth_ctx->request_table, &key)) {
83bf46f4066e3d5e838a32357c201de9bd6ecdfdNikolai Kondrashov "Unknown child ID. Killing the connection\n");
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher /* reply that all is ok */
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher hret = hash_lookup(proxy_cli->proxy_auth_ctx->request_table, &key, &value);
83bf46f4066e3d5e838a32357c201de9bd6ecdfdNikolai Kondrashov "Hash error [%d][%s]\n", hret, hash_error_string(hret));
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher /* Signal that the child is up and ready to receive the request */
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher req = talloc_get_type(value.ptr, struct tevent_req);
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher child_ctx = tevent_req_data(req, struct proxy_child_ctx);
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher /* This should hopefully be impossible, but protect
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher * against it anyway. If we're not marked running, then
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher * the init_req will be NULL below and things will
83bf46f4066e3d5e838a32357c201de9bd6ecdfdNikolai Kondrashov DEBUG(SSSDBG_CRIT_FAILURE, "Client connection from a request "
a3c8390d19593b1e5277d95bfb4ab206d4785150Nikolai Kondrashov "that's not marked as running\n");
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher init_ctx = tevent_req_data(child_ctx->init_req, struct pc_init_ctx);
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagherint sssm_proxy_auth_init(struct be_ctx *bectx,
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher /* If we're already set up, just return that */
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher strcmp("proxy", bectx->bet_info[BET_AUTH].mod_name) == 0) {
83bf46f4066e3d5e838a32357c201de9bd6ecdfdNikolai Kondrashov "Re-using proxy_auth_ctx for this provider\n");
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher *pvt_data = bectx->bet_info[BET_AUTH].pvt_bet_data;
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher ctx = talloc_zero(bectx, struct proxy_auth_ctx);
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher ctx->timeout_ms = SSS_CLI_SOCKET_TIMEOUT/4;
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher ret = confdb_get_string(bectx->cdb, ctx, bectx->conf_path,
83bf46f4066e3d5e838a32357c201de9bd6ecdfdNikolai Kondrashov DEBUG(SSSDBG_CRIT_FAILURE, "Missing option proxy_pam_target.\n");
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher sbus_address = talloc_asprintf(ctx, "unix:path=%s/%s_%s", PIPE_PATH,
83bf46f4066e3d5e838a32357c201de9bd6ecdfdNikolai Kondrashov DEBUG(SSSDBG_CRIT_FAILURE, "talloc_asprintf failed.\n");
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher ret = sbus_new_server(ctx, bectx->ev, sbus_address, &proxy_interface,
2c9a76e553f9239eaa91f32ccaf18b7a68316ce5Jakub Hrozek false, &ctx->sbus_srv, proxy_client_init, ctx);
83bf46f4066e3d5e838a32357c201de9bd6ecdfdNikolai Kondrashov DEBUG(SSSDBG_FATAL_FAILURE, "Could not set up sbus server.\n");
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher /* Set up request hash table */
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher /* FIXME: get max_children from configuration file */
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher hret = hash_create(ctx->max_children * 2, &ctx->request_table,
83bf46f4066e3d5e838a32357c201de9bd6ecdfdNikolai Kondrashov DEBUG(SSSDBG_FATAL_FAILURE, "Could not initialize request table\n");
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagherint sssm_proxy_access_init(struct be_ctx *bectx,
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagher ret = sssm_proxy_auth_init(bectx, ops, pvt_data);
2dd3faebcd3cfd00efda38ffd2585d675e696b12Stephen Gallagherint sssm_proxy_chpass_init(struct be_ctx *bectx,