diff options
-rw-r--r-- | server/monitor/monitor.c | 397 | ||||
-rw-r--r-- | server/monitor/monitor_interfaces.h | 12 | ||||
-rw-r--r-- | server/monitor/monitor_sbus.c | 154 | ||||
-rw-r--r-- | server/monitor/monitor_sbus.h | 6 | ||||
-rw-r--r-- | server/providers/data_provider.c | 86 | ||||
-rw-r--r-- | server/providers/data_provider_be.c | 92 | ||||
-rw-r--r-- | server/responder/common/responder.h | 2 | ||||
-rw-r--r-- | server/responder/common/responder_common.c | 16 | ||||
-rw-r--r-- | server/responder/nss/nsssrv.c | 79 | ||||
-rw-r--r-- | server/responder/pam/pamsrv.c | 77 | ||||
-rw-r--r-- | server/sbus/sssd_dbus_connection.c | 7 |
11 files changed, 421 insertions, 507 deletions
diff --git a/server/monitor/monitor.c b/server/monitor/monitor.c index ead921c06..f9dc9b0cb 100644 --- a/server/monitor/monitor.c +++ b/server/monitor/monitor.c @@ -58,16 +58,15 @@ #define MONITOR_DEF_PING_TIME 10 #define MONITOR_CONF_ENTRY "config/services/monitor" -struct mt_conn { - struct sbus_connection *conn; - struct mt_svc *svc_ptr; -}; +struct svc_spy; struct mt_svc { struct mt_svc *prev; struct mt_svc *next; - struct mt_conn *mt_conn; + struct sbus_connection *conn; + struct svc_spy *conn_spy; + struct mt_ctx *mt_ctx; char *provider; @@ -121,8 +120,7 @@ struct mt_ctx { static int start_service(struct mt_svc *mt_svc); -static int dbus_service_init(struct sbus_connection *conn, void *data); -static void identity_check(DBusPendingCall *pending, void *data); +static int monitor_service_init(struct sbus_connection *conn, void *data); static int service_send_ping(struct mt_svc *svc); static void ping_check(DBusPendingCall *pending, void *data); @@ -147,17 +145,18 @@ static int monitor_cleanup(void); /* dbus_get_monitor_version * Return the monitor version over D-BUS */ -static int dbus_get_monitor_version(DBusMessage *message, - struct sbus_connection *conn) +static int get_monitor_version(DBusMessage *message, + struct sbus_connection *conn) { - const char *version = MONITOR_VERSION; + dbus_uint16_t version = MONITOR_VERSION; DBusMessage *reply; dbus_bool_t ret; reply = dbus_message_new_method_return(message); if (!reply) return ENOMEM; - ret = dbus_message_append_args(reply, DBUS_TYPE_STRING, - &version, DBUS_TYPE_INVALID); + ret = dbus_message_append_args(reply, + DBUS_TYPE_UINT16, &version, + DBUS_TYPE_INVALID); if (!ret) { dbus_message_unref(reply); return EIO; @@ -170,14 +169,164 @@ static int dbus_get_monitor_version(DBusMessage *message, return EOK; } +struct mon_init_conn { + struct mt_ctx *ctx; + struct sbus_connection *conn; + struct tevent_timer *timeout; +}; + +static int add_svc_conn_spy(struct mt_svc *svc); + +/* registers a new client. + * if operation is successful also sends back the Monitor version */ +static int client_registration(DBusMessage *message, + struct sbus_connection *conn) +{ + dbus_uint16_t version = MONITOR_VERSION; + struct mon_init_conn *mini; + struct mt_svc *svc; + void *data; + DBusMessage *reply; + DBusError dbus_error; + dbus_uint16_t svc_ver; + char *svc_name; + dbus_bool_t dbret; + int ret; + + data = sbus_conn_get_private_data(conn); + mini = talloc_get_type(data, struct mon_init_conn); + if (!mini) { + DEBUG(0, ("Connection holds no valid init data\n")); + return EINVAL; + } + + /* First thing, cancel the timeout */ + talloc_zfree(mini->timeout); + + dbus_error_init(&dbus_error); + + dbret = dbus_message_get_args(message, &dbus_error, + DBUS_TYPE_STRING, &svc_name, + DBUS_TYPE_UINT16, &svc_ver, + DBUS_TYPE_INVALID); + if (!dbret) { + DEBUG(1, ("Failed to parse message, killing connection\n")); + if (dbus_error_is_set(&dbus_error)) dbus_error_free(&dbus_error); + sbus_disconnect(conn); + /* FIXME: should we just talloc_zfree(conn) ? */ + goto done; + } + + DEBUG(4, ("Received ID registration: (%s,%d)\n", svc_name, svc_ver)); + + /* search this service in the list */ + svc = mini->ctx->svc_list; + while (svc) { + ret = strcasecmp(svc->identity, svc_name); + if (ret == 0) { + break; + } + svc = svc->next; + } + if (!svc) { + DEBUG(0, ("Unable to find peer [%s] in list of services," + " killing connection!\n", svc_name)); + sbus_disconnect(conn); + /* FIXME: should we just talloc_zfree(conn) ? */ + goto done; + } + + /* Fill in svc structure with connection data */ + svc->conn = mini->conn; + + /* we need to attach a spy to the connection structure so that if some code + * frees it we can zero it out in the service structure. Otherwise we may + * try to access or even free, freed memory. */ + ret = add_svc_conn_spy(svc); + if (ret) { + DEBUG(0, ("Failed to attch spy\n")); + goto done; + } + + /* reply that all is ok */ + reply = dbus_message_new_method_return(message); + if (!reply) return ENOMEM; + + dbret = dbus_message_append_args(reply, + DBUS_TYPE_UINT16, &version, + DBUS_TYPE_INVALID); + if (!dbret) { + dbus_message_unref(reply); + return EIO; + } + + /* send reply back */ + sbus_conn_send_reply(conn, reply); + dbus_message_unref(reply); + +done: + /* init complete, get rid of temp init context */ + talloc_zfree(mini); + + return EOK; +} + +struct svc_spy { + struct mt_svc *svc; +}; + +static int svc_destructor(void *mem) +{ + struct mt_svc *svc = talloc_get_type(mem, struct mt_svc); + if (!svc) { + /* ?!?!? */ + return 0; + } + + /* svc is beeing freed, neutralize the spy */ + if (svc->conn_spy) { + talloc_set_destructor((TALLOC_CTX *)svc->conn_spy, NULL); + talloc_zfree(svc->conn_spy); + } + return 0; +} + +static int svc_spy_destructor(void *mem) +{ + struct svc_spy *spy = talloc_get_type(mem, struct svc_spy); + if (!spy) { + /* ?!?!? */ + return 0; + } + + /* svc->conn has been freed, NULL the pointer in svc */ + spy->svc->conn = NULL; + return 0; +} + +static int add_svc_conn_spy(struct mt_svc *svc) +{ + struct svc_spy *spy; + + spy = talloc(svc->conn, struct svc_spy); + if (!spy) return ENOMEM; + + spy->svc = svc; + talloc_set_destructor((TALLOC_CTX *)spy, svc_spy_destructor); + svc->conn_spy = spy; + + return EOK; +} + struct sbus_method monitor_methods[] = { - { MON_SRV_METHOD_VERSION, dbus_get_monitor_version }, + { MON_SRV_METHOD_VERSION, get_monitor_version }, + { MON_SRV_METHOD_REGISTER, client_registration }, { NULL, NULL } }; struct sbus_interface monitor_server_interface = { - MONITOR_DBUS_INTERFACE, - MONITOR_DBUS_PATH, + MON_SRV_INTERFACE, + MON_SRV_PATH, SBUS_DEFAULT_VTABLE, monitor_methods, NULL @@ -198,7 +347,7 @@ static int monitor_dbus_init(struct mt_ctx *ctx) ret = sbus_new_server(ctx, ctx->ev, monitor_address, &monitor_server_interface, - &ctx->sbus_srv, dbus_service_init, ctx); + &ctx->sbus_srv, monitor_service_init, ctx); talloc_free(monitor_address); @@ -394,10 +543,8 @@ static void shutdown_reply(DBusPendingCall *pending, void *data) { DBusMessage *reply; int type; - struct sbus_connection *conn; struct mt_svc *svc = talloc_get_type(data, struct mt_svc); - conn = svc->mt_conn->conn; reply = dbus_pending_call_steal_reply(pending); if (!reply) { /* reply should never be null. This function shouldn't be called @@ -448,7 +595,7 @@ static int monitor_shutdown_service(struct mt_svc *svc) /* Stop the service checker */ - dbus_conn = sbus_get_connection(svc->mt_conn->conn); + dbus_conn = sbus_get_connection(svc->conn); /* Construct a shutdown message */ msg = dbus_message_new_method_call(NULL, @@ -482,10 +629,8 @@ static int monitor_shutdown_service(struct mt_svc *svc) static void reload_reply(DBusPendingCall *pending, void *data) { DBusMessage *reply; - struct sbus_connection *conn; struct mt_svc *svc = talloc_get_type(data, struct mt_svc); - conn = svc->mt_conn->conn; reply = dbus_pending_call_steal_reply(pending); if (!reply) { /* reply should never be null. This function shouldn't be called @@ -496,7 +641,7 @@ static void reload_reply(DBusPendingCall *pending, void *data) " and no timeout occurred\n")); /* Destroy this connection */ - sbus_disconnect(conn); + sbus_disconnect(svc->conn); goto done; } @@ -558,7 +703,7 @@ static int service_signal(struct mt_svc *svc, const char *svc_signal) return EOK; } - if (!svc->mt_conn) { + if (!svc->conn) { /* Avoid a race condition where we are trying to * order a service to reload that hasn't started * yet. @@ -567,7 +712,7 @@ static int service_signal(struct mt_svc *svc, const char *svc_signal) return EIO; } - dbus_conn = sbus_get_connection(svc->mt_conn->conn); + dbus_conn = sbus_get_connection(svc->conn); msg = dbus_message_new_method_call(NULL, MONITOR_PATH, MONITOR_INTERFACE, @@ -809,6 +954,8 @@ static int get_provider_config(struct mt_ctx *ctx, const char *name, } svc->mt_ctx = ctx; + talloc_set_destructor((TALLOC_CTX *)svc, svc_destructor); + svc->name = talloc_strdup(svc, name); if (!svc->name) { talloc_free(svc); @@ -1745,195 +1892,60 @@ int monitor_process_init(TALLOC_CTX *mem_ctx, return EOK; } -static int mt_conn_destructor(void *ptr) +static void init_timeout(struct tevent_context *ev, + struct tevent_timer *te, + struct timeval t, void *ptr) { - struct mt_conn *mt_conn; - struct mt_svc *svc; + struct mon_init_conn *mini; - mt_conn = talloc_get_type(ptr, struct mt_conn); - svc = mt_conn->svc_ptr; + DEBUG(2, ("Client timed out before Identification!\n")); - /* now clear up so that the rest of the code will know there - * is no connection attached to the service anymore */ - svc->mt_conn = NULL; + mini = talloc_get_type(ptr, struct mon_init_conn); - return 0; + sbus_disconnect(mini->conn); + talloc_zfree(mini); } /* - * dbus_service_init - * This function should initiate a query to the newly connected - * service to discover the service's identity (invoke the getIdentity - * method on the new client). The reply callback for this request - * should set the connection destructor appropriately. + * monitor_service_init + * Set up a timeout function and temporary connection structure. + * If the client does not identify before the timeout kicks in, + * the client is forcibly disconnected. */ -static int dbus_service_init(struct sbus_connection *conn, void *data) +static int monitor_service_init(struct sbus_connection *conn, void *data) { struct mt_ctx *ctx; - struct mt_svc *svc; - struct mt_conn *mt_conn; - DBusMessage *msg; - DBusPendingCall *pending_reply; - DBusConnection *dbus_conn; - dbus_bool_t dbret; + struct mon_init_conn *mini; + struct timeval tv; DEBUG(3, ("Initializing D-BUS Service\n")); ctx = talloc_get_type(data, struct mt_ctx); - dbus_conn = sbus_get_connection(conn); - /* hang off this memory to the connection so that when the connection - * is freed we can call a destructor to clear up the structure and - * have a way to know we need to restart the service */ - mt_conn = talloc(conn, struct mt_conn); - if (!mt_conn) { + mini = talloc(conn, struct mon_init_conn); + if (!mini) { DEBUG(0,("Out of memory?!\n")); - talloc_free(conn); - return ENOMEM; - } - mt_conn->conn = conn; - - /* at this stage we still do not know what service is this - * we will know only after we get its identity, so we make - * up a temporary fake service and complete the operation - * when we receive the reply */ - svc = talloc_zero(mt_conn, struct mt_svc); - if (!svc) { - talloc_free(conn); + talloc_zfree(conn); return ENOMEM; } - svc->mt_ctx = ctx; - svc->mt_conn = mt_conn; + mini->ctx = ctx; + mini->conn = conn; - mt_conn->svc_ptr = svc; - talloc_set_destructor((TALLOC_CTX *)mt_conn, mt_conn_destructor); + /* 5 seconds should be plenty */ + tv = tevent_timeval_current_ofs(5, 0); - /* - * Set up identity request - * This should be a well-known path and method - * for all services - */ - msg = dbus_message_new_method_call(NULL, - MONITOR_PATH, - MONITOR_INTERFACE, - MON_CLI_METHOD_IDENTITY); - if (msg == NULL) { + mini->timeout = tevent_add_timer(ctx->ev, mini, tv, init_timeout, mini); + if (!mini->timeout) { DEBUG(0,("Out of memory?!\n")); - talloc_free(conn); + talloc_zfree(conn); return ENOMEM; } - dbret = dbus_connection_send_with_reply(dbus_conn, msg, &pending_reply, - ctx->service_id_timeout); - if (!dbret || pending_reply == NULL) { - /* - * Critical Failure - * We can't communicate on this connection - * We'll drop it using the default destructor. - */ - DEBUG(0, ("D-BUS send failed.\n")); - dbus_message_unref(msg); - talloc_free(conn); - return EIO; - } - /* Set up the reply handler */ - dbus_pending_call_set_notify(pending_reply, identity_check, svc, NULL); - dbus_message_unref(msg); + sbus_conn_set_private_data(conn, mini); return EOK; } -static void identity_check(DBusPendingCall *pending, void *data) -{ - struct mt_svc *fake_svc; - struct mt_svc *svc; - struct sbus_connection *conn; - DBusMessage *reply; - DBusError dbus_error; - dbus_uint16_t svc_ver; - char *svc_name; - dbus_bool_t ret; - int type; - - fake_svc = talloc_get_type(data, struct mt_svc); - conn = fake_svc->mt_conn->conn; - dbus_error_init(&dbus_error); - - reply = dbus_pending_call_steal_reply(pending); - if (!reply) { - /* reply should never be null. This function shouldn't be called - * until reply is valid or timeout has occurred. If reply is NULL - * here, something is seriously wrong and we should bail out. - */ - DEBUG(0, ("Serious error. A reply callback was called but no reply was received and no timeout occurred\n")); - - /* Destroy this connection */ - sbus_disconnect(conn); - goto done; - } - - type = dbus_message_get_type(reply); - switch (type) { - case DBUS_MESSAGE_TYPE_METHOD_RETURN: - ret = dbus_message_get_args(reply, &dbus_error, - DBUS_TYPE_STRING, &svc_name, - DBUS_TYPE_UINT16, &svc_ver, - DBUS_TYPE_INVALID); - if (!ret) { - DEBUG(1,("Failed, to parse message, killing connection\n")); - if (dbus_error_is_set(&dbus_error)) dbus_error_free(&dbus_error); - sbus_disconnect(conn); - goto done; - } - - DEBUG(4,("Received ID reply: (%s,%d)\n", svc_name, svc_ver)); - - /* search this service in the list */ - svc = fake_svc->mt_ctx->svc_list; - while (svc) { - ret = strcasecmp(svc->identity, svc_name); - if (ret == 0) { - break; - } - svc = svc->next; - } - if (!svc) { - DEBUG(0,("Unable to find peer [%s] in list of services, killing connection!\n", svc_name)); - sbus_disconnect(conn); - goto done; - } - - /* transfer all from the fake service and get rid of it */ - fake_svc->mt_conn->svc_ptr = svc; - svc->mt_conn = fake_svc->mt_conn; - talloc_free(fake_svc); - - DEBUG(1, ("Service %s connected\n", svc->name)); - - /* Set up the destructor for this service */ - break; - - case DBUS_MESSAGE_TYPE_ERROR: - DEBUG(0,("getIdentity returned an error [%s], closing connection.\n", - dbus_message_get_error_name(reply))); - /* Falling through to default intentionally*/ - default: - /* - * Timeout or other error occurred or something - * unexpected happened. - * It doesn't matter which, because either way we - * know that this connection isn't trustworthy. - * We'll destroy it now. - */ - sbus_disconnect(conn); - return; - } - -done: - dbus_pending_call_unref(pending); - dbus_message_unref(reply); -} - /* service_send_ping * this function send a dbus ping to a service. * It returns EOK if all is fine or ENXIO if the connection is @@ -1947,13 +1959,14 @@ static int service_send_ping(struct mt_svc *svc) DBusConnection *dbus_conn; dbus_bool_t dbret; - if (!svc->mt_conn) { + if (!svc->conn) { + DEBUG(8, ("Service not yet initialized\n")); return ENXIO; } DEBUG(4,("Pinging %s\n", svc->name)); - dbus_conn = sbus_get_connection(svc->mt_conn->conn); + dbus_conn = sbus_get_connection(svc->conn); /* * Set up identity request @@ -1966,7 +1979,7 @@ static int service_send_ping(struct mt_svc *svc) MON_CLI_METHOD_PING); if (!msg) { DEBUG(0,("Out of memory?!\n")); - talloc_free(svc->mt_conn->conn); + talloc_zfree(svc->conn); return ENOMEM; } @@ -1979,7 +1992,7 @@ static int service_send_ping(struct mt_svc *svc) * We'll drop it using the default destructor. */ DEBUG(0, ("D-BUS send failed.\n")); - talloc_free(svc->mt_conn->conn); + talloc_zfree(svc->conn); return EIO; } @@ -1993,13 +2006,11 @@ static int service_send_ping(struct mt_svc *svc) static void ping_check(DBusPendingCall *pending, void *data) { struct mt_svc *svc; - struct sbus_connection *conn; DBusMessage *reply; const char *dbus_error_name; int type; svc = talloc_get_type(data, struct mt_svc); - conn = svc->mt_conn->conn; reply = dbus_pending_call_steal_reply(pending); if (!reply) { @@ -2011,7 +2022,7 @@ static void ping_check(DBusPendingCall *pending, void *data) " and no timeout occurred\n")); /* Destroy this connection */ - sbus_disconnect(conn); + sbus_disconnect(svc->conn); goto done; } @@ -2045,7 +2056,7 @@ static void ping_check(DBusPendingCall *pending, void *data) * know that this connection isn't trustworthy. * We'll destroy it now. */ - sbus_disconnect(conn); + sbus_disconnect(svc->conn); } done: diff --git a/server/monitor/monitor_interfaces.h b/server/monitor/monitor_interfaces.h index 5c58066d5..211c25dd2 100644 --- a/server/monitor/monitor_interfaces.h +++ b/server/monitor/monitor_interfaces.h @@ -21,15 +21,17 @@ /*** Monitor ***/ -#define MONITOR_VERSION "0.1" -#define MONITOR_DBUS_INTERFACE "org.freedesktop.sssd.monitor" -#define MONITOR_DBUS_PATH "/org/freedesktop/sssd/monitor" +#define MONITOR_VERSION 0x0001 + +/*** Monitor SRV Interface ***/ +#define MON_SRV_PATH "/org/freedesktop/sssd/monitor" +#define MON_SRV_INTERFACE "org.freedesktop.sssd.monitor" /* Monitor SRV Methods */ #define MON_SRV_METHOD_VERSION "getVersion" +#define MON_SRV_METHOD_REGISTER "RegisterService" -/*** Monitor Interface ***/ - +/*** Monitor CLI Interface ***/ #define MONITOR_PATH "/org/freedesktop/sssd/service" #define MONITOR_INTERFACE "org.freedesktop.sssd.service" diff --git a/server/monitor/monitor_sbus.c b/server/monitor/monitor_sbus.c index 817b42ae6..777a47fed 100644 --- a/server/monitor/monitor_sbus.c +++ b/server/monitor/monitor_sbus.c @@ -19,6 +19,11 @@ along with this program. If not, see <http://www.gnu.org/licenses/>. */ +/* Needed for res_init() */ +#include <netinet/in.h> +#include <arpa/nameser.h> +#include <resolv.h> + #include "util/util.h" #include "confdb/confdb.h" #include "sbus/sssd_dbus.h" @@ -54,3 +59,152 @@ done: return ret; } +static void id_callback(DBusPendingCall *pending, void *ptr) +{ + DBusMessage *reply; + DBusError dbus_error; + dbus_bool_t ret; + dbus_uint16_t mon_ver; + int type; + + dbus_error_init(&dbus_error); + + reply = dbus_pending_call_steal_reply(pending); + if (!reply) { + /* reply should never be null. This function shouldn't be called + * until reply is valid or timeout has occurred. If reply is NULL + * here, something is seriously wrong and we should bail out. + */ + DEBUG(0, ("Severe error. A reply callback was called but no" + " reply was received and no timeout occurred\n")); + + /* FIXME: Destroy this connection ? */ + goto done; + } + + type = dbus_message_get_type(reply); + switch (type) { + case DBUS_MESSAGE_TYPE_METHOD_RETURN: + ret = dbus_message_get_args(reply, &dbus_error, + DBUS_TYPE_UINT16, &mon_ver, + DBUS_TYPE_INVALID); + if (!ret) { + DEBUG(1, ("Failed to parse message\n")); + if (dbus_error_is_set(&dbus_error)) dbus_error_free(&dbus_error); + /* FIXME: Destroy this connection ? */ + goto done; + } + + DEBUG(4, ("Got id ack and version (%d) from Monitor\n", mon_ver)); + + break; + + case DBUS_MESSAGE_TYPE_ERROR: + DEBUG(0,("The Monitor returned an error [%s]\n", + dbus_message_get_error_name(reply))); + /* Falling through to default intentionally*/ + default: + /* + * Timeout or other error occurred or something + * unexpected happened. + * It doesn't matter which, because either way we + * know that this connection isn't trustworthy. + * We'll destroy it now. + */ + + /* FIXME: Destroy this connection ? */ + break; + } + +done: + dbus_pending_call_unref(pending); + dbus_message_unref(reply); +} + +int monitor_common_send_id(struct sbus_connection *conn, + const char *name, uint16_t version) +{ + DBusPendingCall *pending_reply; + DBusConnection *dbus_conn; + DBusMessage *msg; + dbus_bool_t ret; + + dbus_conn = sbus_get_connection(conn); + + /* create the message */ + msg = dbus_message_new_method_call(NULL, + MON_SRV_PATH, + MON_SRV_INTERFACE, + MON_SRV_METHOD_REGISTER); + if (msg == NULL) { + DEBUG(0, ("Out of memory?!\n")); + return ENOMEM; + } + + DEBUG(4, ("Sending ID: (%s,%d)\n", name, version)); + + ret = dbus_message_append_args(msg, + DBUS_TYPE_STRING, &name, + DBUS_TYPE_UINT16, &version, + DBUS_TYPE_INVALID); + if (!ret) { + DEBUG(1, ("Failed to build message\n")); + return EIO; + } + + ret = dbus_connection_send_with_reply(dbus_conn, msg, &pending_reply, + 30000 /* TODO: set timeout */); + if (!ret || !pending_reply) { + /* + * Critical Failure + * We can't communicate on this connection + * We'll drop it using the default destructor. + */ + DEBUG(0, ("D-BUS send failed.\n")); + dbus_message_unref(msg); + return EIO; + } + + /* Set up the reply handler */ + dbus_pending_call_set_notify(pending_reply, id_callback, NULL, NULL); + dbus_message_unref(msg); + + return EOK; +} + +int monitor_common_pong(DBusMessage *message, + struct sbus_connection *conn) +{ + DBusMessage *reply; + dbus_bool_t ret; + + reply = dbus_message_new_method_return(message); + if (!reply) return ENOMEM; + + ret = dbus_message_append_args(reply, DBUS_TYPE_INVALID); + if (!ret) { + dbus_message_unref(reply); + return EIO; + } + + /* send reply back */ + sbus_conn_send_reply(conn, reply); + dbus_message_unref(reply); + + return EOK; +} + +int monitor_common_res_init(DBusMessage *message, + struct sbus_connection *conn) +{ + int ret; + + ret = res_init(); + if(ret != 0) { + return EIO; + } + + /* Send an empty reply to acknowledge receipt */ + return monitor_common_pong(message, conn); +} + diff --git a/server/monitor/monitor_sbus.h b/server/monitor/monitor_sbus.h index bc36e88eb..d84954bd1 100644 --- a/server/monitor/monitor_sbus.h +++ b/server/monitor/monitor_sbus.h @@ -24,5 +24,11 @@ int monitor_get_sbus_address(TALLOC_CTX *mem_ctx, struct confdb_ctx *confdb, char **address); +int monitor_common_send_id(struct sbus_connection *conn, + const char *name, uint16_t version); +int monitor_common_pong(DBusMessage *message, + struct sbus_connection *conn); +int monitor_common_res_init(DBusMessage *message, + struct sbus_connection *conn); #endif /* MONITOR_SBUS_H_ */ diff --git a/server/providers/data_provider.c b/server/providers/data_provider.c index f0ecd30bb..7fcd168db 100644 --- a/server/providers/data_provider.c +++ b/server/providers/data_provider.c @@ -31,11 +31,6 @@ #include <errno.h> #include <security/pam_modules.h> -/* Needed for res_init() */ -#include <netinet/in.h> -#include <arpa/nameser.h> -#include <resolv.h> - #include "popt.h" #include "util/util.h" #include "confdb/confdb.h" @@ -84,16 +79,12 @@ struct dp_frontend { static int dp_backend_destructor(void *ctx); static int dp_frontend_destructor(void *ctx); -static int service_identity(DBusMessage *message, struct sbus_connection *conn); -static int service_pong(DBusMessage *message, struct sbus_connection *conn); static int service_reload(DBusMessage *message, struct sbus_connection *conn); -static int service_res_init(DBusMessage *message, struct sbus_connection *conn); struct sbus_method monitor_dp_methods[] = { - { MON_CLI_METHOD_IDENTITY, service_identity }, - { MON_CLI_METHOD_PING, service_pong }, + { MON_CLI_METHOD_PING, monitor_common_pong }, { MON_CLI_METHOD_RELOAD, service_reload }, - { MON_CLI_METHOD_RES_INIT, service_res_init }, + { MON_CLI_METHOD_RES_INIT, monitor_common_res_init }, { NULL, NULL } }; @@ -136,55 +127,6 @@ struct dp_be_request { struct dp_backend *be; }; -static int service_identity(DBusMessage *message, struct sbus_connection *conn) -{ - dbus_uint16_t version = DATA_PROVIDER_VERSION; - const char *name = DATA_PROVIDER_SERVICE_NAME; - DBusMessage *reply; - dbus_bool_t ret; - - DEBUG(4, ("Sending identity data [%s,%d]\n", name, version)); - - reply = dbus_message_new_method_return(message); - if (!reply) return ENOMEM; - - ret = dbus_message_append_args(reply, - DBUS_TYPE_STRING, &name, - DBUS_TYPE_UINT16, &version, - DBUS_TYPE_INVALID); - if (!ret) { - dbus_message_unref(reply); - return EIO; - } - - /* send reply back */ - sbus_conn_send_reply(conn, reply); - dbus_message_unref(reply); - - return EOK; -} - -static int service_pong(DBusMessage *message, struct sbus_connection *conn) -{ - DBusMessage *reply; - dbus_bool_t ret; - - reply = dbus_message_new_method_return(message); - if (!reply) return ENOMEM; - - ret = dbus_message_append_args(reply, DBUS_TYPE_INVALID); - if (!ret) { - dbus_message_unref(reply); - return EIO; - } - - /* send reply back */ - sbus_conn_send_reply(conn, reply); - dbus_message_unref(reply); - - return EOK; -} - static int service_reload(DBusMessage *message, struct sbus_connection *conn) { /* Monitor calls this function when we need to reload @@ -193,19 +135,7 @@ static int service_reload(DBusMessage *message, struct sbus_connection *conn) */ /* Send an empty reply to acknowledge receipt */ - return service_pong(message, conn); -} - -static int service_res_init(DBusMessage *message, struct sbus_connection *conn) -{ - int ret; - - ret = res_init(); - if(ret != 0) { - return EIO; - } - - return service_pong(message, conn); + return monitor_common_pong(message, conn); } static int dp_monitor_init(struct dp_ctx *dpctx) @@ -229,8 +159,14 @@ static int dp_monitor_init(struct dp_ctx *dpctx) return ret; } - /* Set up DP-specific listeners */ - /* None currently used */ + /* Identify ourselves to the monitor */ + ret = monitor_common_send_id(conn, + DATA_PROVIDER_SERVICE_NAME, + DATA_PROVIDER_VERSION); + if (ret != EOK) { + DEBUG(0, ("Failed to identify to the monitor!\n")); + return ret; + } return EOK; } diff --git a/server/providers/data_provider_be.c b/server/providers/data_provider_be.c index 49885edc6..46f8db51d 100644 --- a/server/providers/data_provider_be.c +++ b/server/providers/data_provider_be.c @@ -34,11 +34,6 @@ #include <security/pam_appl.h> #include <security/pam_modules.h> -/* Needed for res_init() */ -#include <netinet/in.h> -#include <arpa/nameser.h> -#include <resolv.h> - #include "popt.h" #include "util/util.h" #include "confdb/confdb.h" @@ -53,14 +48,9 @@ #define BE_CONF_ENTRY "config/domains/%s" -static int service_identity(DBusMessage *message, struct sbus_connection *conn); -static int service_pong(DBusMessage *message, struct sbus_connection *conn); -static int service_res_init(DBusMessage *message, struct sbus_connection *conn); - struct sbus_method monitor_be_methods[] = { - { MON_CLI_METHOD_IDENTITY, service_identity }, - { MON_CLI_METHOD_PING, service_pong }, - { MON_CLI_METHOD_RES_INIT, service_res_init }, + { MON_CLI_METHOD_PING, monitor_common_pong }, + { MON_CLI_METHOD_RES_INIT, monitor_common_res_init }, { NULL, NULL } }; @@ -102,75 +92,6 @@ static struct bet_data bet_data[] = { {BET_MAX, NULL, NULL} }; - - -static int service_identity(DBusMessage *message, struct sbus_connection *conn) -{ - dbus_uint16_t version = DATA_PROVIDER_VERSION; - struct be_ctx *ctx; - DBusMessage *reply; - dbus_bool_t ret; - void *user_data; - - user_data = sbus_conn_get_private_data(conn); - if (!user_data) return EINVAL; - ctx = talloc_get_type(user_data, struct be_ctx); - if (!ctx) return EINVAL; - - DEBUG(4,("Sending ID reply: (%s,%d)\n", ctx->identity, version)); - - reply = dbus_message_new_method_return(message); - if (!reply) return ENOMEM; - - ret = dbus_message_append_args(reply, - DBUS_TYPE_STRING, &ctx->identity, - DBUS_TYPE_UINT16, &version, - DBUS_TYPE_INVALID); - if (!ret) { - dbus_message_unref(reply); - return EIO; - } - - /* send reply back */ - sbus_conn_send_reply(conn, reply); - dbus_message_unref(reply); - - return EOK; -} - -static int service_pong(DBusMessage *message, struct sbus_connection *conn) -{ - DBusMessage *reply; - dbus_bool_t ret; - - reply = dbus_message_new_method_return(message); - if (!reply) return ENOMEM; - - ret = dbus_message_append_args(reply, DBUS_TYPE_INVALID); - if (!ret) { - dbus_message_unref(reply); - return EIO; - } - - /* send reply back */ - sbus_conn_send_reply(conn, reply); - dbus_message_unref(reply); - - return EOK; -} - -static int service_res_init(DBusMessage *message, struct sbus_connection *conn) -{ - int ret; - - ret = res_init(); - if(ret != 0) { - return EIO; - } - - return service_pong(message, conn); -} - static int be_identity(DBusMessage *message, struct sbus_connection *conn) { dbus_uint16_t version = DATA_PROVIDER_VERSION; @@ -704,6 +625,15 @@ static int mon_cli_init(struct be_ctx *ctx) return ret; } + /* Identify ourselves to the monitor */ + ret = monitor_common_send_id(ctx->mon_conn, + ctx->identity, + DATA_PROVIDER_VERSION); + if (ret != EOK) { + DEBUG(0, ("Failed to identify to the monitor!\n")); + return ret; + } + return EOK; } diff --git a/server/responder/common/responder.h b/server/responder/common/responder.h index 0f0908317..f41876508 100644 --- a/server/responder/common/responder.h +++ b/server/responder/common/responder.h @@ -102,6 +102,8 @@ int sss_process_init(TALLOC_CTX *mem_ctx, const char *sss_pipe_name, const char *sss_priv_pipe_name, const char *confdb_service_path, + const char *svc_name, + uint16_t svc_version, struct sbus_interface *dp_intf, struct sbus_interface *monitor_intf, struct resp_ctx **responder_ctx); diff --git a/server/responder/common/responder_common.c b/server/responder/common/responder_common.c index f3df7c65c..75e721030 100644 --- a/server/responder/common/responder_common.c +++ b/server/responder/common/responder_common.c @@ -286,7 +286,9 @@ static void accept_fd_handler(struct tevent_context *ev, } static int sss_monitor_init(struct resp_ctx *rctx, - struct sbus_interface *intf) + struct sbus_interface *intf, + const char *svc_name, + uint16_t svc_version) { char *sbus_address; int ret; @@ -306,8 +308,12 @@ static int sss_monitor_init(struct resp_ctx *rctx, return ret; } - /* Set up NSS-specific listeners */ - /* None currently used */ + /* Identify ourselves to the monitor */ + ret = monitor_common_send_id(rctx->mon_conn, svc_name, svc_version); + if (ret != EOK) { + DEBUG(0, ("Failed to identify to the monitor!\n")); + return ret; + } return EOK; } @@ -447,6 +453,8 @@ int sss_process_init(TALLOC_CTX *mem_ctx, const char *sss_pipe_name, const char *sss_priv_pipe_name, const char *confdb_service_path, + const char *svc_name, + uint16_t svc_version, struct sbus_interface *dp_intf, struct sbus_interface *monitor_intf, struct resp_ctx **responder_ctx) @@ -472,7 +480,7 @@ int sss_process_init(TALLOC_CTX *mem_ctx, return ret; } - ret = sss_monitor_init(rctx, monitor_intf); + ret = sss_monitor_init(rctx, monitor_intf, svc_name, svc_version); if (ret != EOK) { DEBUG(0, ("fatal error setting up message bus\n")); return ret; diff --git a/server/responder/nss/nsssrv.c b/server/responder/nss/nsssrv.c index 418e2f9f6..e4b121bf2 100644 --- a/server/responder/nss/nsssrv.c +++ b/server/responder/nss/nsssrv.c @@ -30,11 +30,6 @@ #include <sys/time.h> #include <errno.h> -/* Needed for res_init() */ -#include <netinet/in.h> -#include <arpa/nameser.h> -#include <resolv.h> - #include "popt.h" #include "util/util.h" #include "responder/nss/nsssrv.h" @@ -52,16 +47,12 @@ #define SSS_NSS_PIPE_NAME "nss" -static int service_identity(DBusMessage *message, struct sbus_connection *conn); -static int service_pong(DBusMessage *message, struct sbus_connection *conn); static int service_reload(DBusMessage *message, struct sbus_connection *conn); -static int service_res_init(DBusMessage *message, struct sbus_connection *conn); struct sbus_method monitor_nss_methods[] = { - { MON_CLI_METHOD_IDENTITY, service_identity }, - { MON_CLI_METHOD_PING, service_pong }, + { MON_CLI_METHOD_PING, monitor_common_pong }, { MON_CLI_METHOD_RELOAD, service_reload }, - { MON_CLI_METHOD_RES_INIT, service_res_init }, + { MON_CLI_METHOD_RES_INIT, monitor_common_res_init }, { NULL, NULL } }; @@ -73,56 +64,6 @@ struct sbus_interface monitor_nss_interface = { NULL }; -static int service_identity(DBusMessage *message, struct sbus_connection *conn) -{ - dbus_uint16_t version = NSS_SBUS_SERVICE_VERSION; - const char *name = NSS_SBUS_SERVICE_NAME; - DBusMessage *reply; - dbus_bool_t ret; - - DEBUG(4,("Sending ID reply: (%s,%d)\n", - name, version)); - - reply = dbus_message_new_method_return(message); - if (!reply) return ENOMEM; - - ret = dbus_message_append_args(reply, - DBUS_TYPE_STRING, &name, - DBUS_TYPE_UINT16, &version, - DBUS_TYPE_INVALID); - if (!ret) { - dbus_message_unref(reply); - return EIO; - } - - /* send reply back */ - sbus_conn_send_reply(conn, reply); - dbus_message_unref(reply); - - return EOK; -} - -static int service_pong(DBusMessage *message, struct sbus_connection *conn) -{ - DBusMessage *reply; - dbus_bool_t ret; - - reply = dbus_message_new_method_return(message); - if (!reply) return ENOMEM; - - ret = dbus_message_append_args(reply, DBUS_TYPE_INVALID); - if (!ret) { - dbus_message_unref(reply); - return EIO; - } - - /* send reply back */ - sbus_conn_send_reply(conn, reply); - dbus_message_unref(reply); - - return EOK; -} - static int service_reload(DBusMessage *message, struct sbus_connection *conn) { /* Monitor calls this function when we need to reload @@ -131,19 +72,7 @@ static int service_reload(DBusMessage *message, struct sbus_connection *conn) */ /* Send an empty reply to acknowledge receipt */ - return service_pong(message, conn); -} - -static int service_res_init(DBusMessage *message, struct sbus_connection *conn) -{ - int ret; - - ret = res_init(); - if(ret != 0) { - return EIO; - } - - return service_pong(message, conn); + return monitor_common_pong(message, conn); } static int nss_get_config(struct nss_ctx *nctx, @@ -303,6 +232,8 @@ int nss_process_init(TALLOC_CTX *mem_ctx, nss_cmds, SSS_NSS_SOCKET_NAME, NULL, NSS_SRV_CONFIG, + NSS_SBUS_SERVICE_NAME, + NSS_SBUS_SERVICE_VERSION, nss_dp_interface, &monitor_nss_interface, &nctx->rctx); diff --git a/server/responder/pam/pamsrv.c b/server/responder/pam/pamsrv.c index bff2f7cc9..c0f0ca40e 100644 --- a/server/responder/pam/pamsrv.c +++ b/server/responder/pam/pamsrv.c @@ -31,11 +31,6 @@ #include <sys/time.h> #include <errno.h> -/* Needed for res_init() */ -#include <netinet/in.h> -#include <arpa/nameser.h> -#include <resolv.h> - #include "popt.h" #include "util/util.h" #include "db/sysdb.h" @@ -54,16 +49,12 @@ #define PAM_SBUS_SERVICE_NAME "pam" #define PAM_SRV_CONFIG "config/services/pam" -static int service_identity(DBusMessage *message, struct sbus_connection *conn); -static int service_pong(DBusMessage *message, struct sbus_connection *conn); static int service_reload(DBusMessage *message, struct sbus_connection *conn); -static int service_res_init(DBusMessage *message, struct sbus_connection *conn); struct sbus_method monitor_pam_methods[] = { - { MON_CLI_METHOD_IDENTITY, service_identity }, - { MON_CLI_METHOD_PING, service_pong }, + { MON_CLI_METHOD_PING, monitor_common_pong }, { MON_CLI_METHOD_RELOAD, service_reload }, - { MON_CLI_METHOD_RES_INIT, service_res_init }, + { MON_CLI_METHOD_RES_INIT, monitor_common_res_init }, { NULL, NULL } }; @@ -75,66 +66,6 @@ struct sbus_interface monitor_pam_interface = { NULL }; -static int service_identity(DBusMessage *message, struct sbus_connection *conn) -{ - dbus_uint16_t version = PAM_SBUS_SERVICE_VERSION; - const char *name = PAM_SBUS_SERVICE_NAME; - DBusMessage *reply; - dbus_bool_t ret; - - DEBUG(4,("Sending ID reply: (%s,%d)\n", name, version)); - - reply = dbus_message_new_method_return(message); - if (!reply) return ENOMEM; - - ret = dbus_message_append_args(reply, - DBUS_TYPE_STRING, &name, - DBUS_TYPE_UINT16, &version, - DBUS_TYPE_INVALID); - if (!ret) { - dbus_message_unref(reply); - return EIO; - } - - /* send reply back */ - sbus_conn_send_reply(conn, reply); - dbus_message_unref(reply); - - return EOK; -} - -static int service_pong(DBusMessage *message, struct sbus_connection *conn) -{ - DBusMessage *reply; - dbus_bool_t ret; - - reply = dbus_message_new_method_return(message); - if (!reply) return ENOMEM; - - ret = dbus_message_append_args(reply, DBUS_TYPE_INVALID); - if (!ret) { - return EIO; - } - - /* send reply back */ - sbus_conn_send_reply(conn, reply); - dbus_message_unref(reply); - - return EOK; -} - -static int service_res_init(DBusMessage *message, struct sbus_connection *conn) -{ - int ret; - - ret = res_init(); - if(ret != 0) { - return EIO; - } - - return service_pong(message, conn); -} - static void pam_shutdown(struct resp_ctx *ctx); static int service_reload(DBusMessage *message, struct sbus_connection *conn) { @@ -144,7 +75,7 @@ static int service_reload(DBusMessage *message, struct sbus_connection *conn) { */ /* Send an empty reply to acknowledge receipt */ - return service_pong(message, conn); + return monitor_common_pong(message, conn); } static void pam_dp_reconnect_init(struct sbus_connection *conn, int status, void *pvt) @@ -242,6 +173,8 @@ int main(int argc, const char *argv[]) SSS_PAM_SOCKET_NAME, SSS_PAM_PRIV_SOCKET_NAME, PAM_SRV_CONFIG, + PAM_SBUS_SERVICE_NAME, + PAM_SBUS_SERVICE_VERSION, pam_dp_interface, &monitor_pam_interface, &rctx); diff --git a/server/sbus/sssd_dbus_connection.c b/server/sbus/sssd_dbus_connection.c index ab414da05..396a1f27f 100644 --- a/server/sbus/sssd_dbus_connection.c +++ b/server/sbus/sssd_dbus_connection.c @@ -111,7 +111,8 @@ static void sbus_conn_wakeup_main(void *data) struct tevent_timer *te; conn = talloc_get_type(data, struct sbus_connection); - gettimeofday(&tv, NULL); + + tv = tevent_timeval_current(); /* D-BUS calls this function when it is time to do a dispatch */ te = tevent_add_timer(conn->ev, conn, tv, sbus_dispatch, conn); @@ -147,13 +148,13 @@ int sbus_init_connection(TALLOC_CTX *ctx, conn->dbus.conn = dbus_conn; conn->connection_type = connection_type; - ret = sbus_conn_set_fns(conn); + ret = sbus_conn_add_interface(conn, intf); if (ret != EOK) { talloc_free(conn); return ret; } - ret = sbus_conn_add_interface(conn, intf); + ret = sbus_conn_set_fns(conn); if (ret != EOK) { talloc_free(conn); return ret; |