summaryrefslogtreecommitdiff
path: root/daemon/gdm-xdmcp-display-factory.c
diff options
context:
space:
mode:
authorWilliam Jon McCann <mccann@jhu.edu>2008-01-31 00:51:46 +0000
committerWilliam Jon McCann <mccann@src.gnome.org>2008-01-31 00:51:46 +0000
commit98917b1ee7d15660bafd4ab8d2441f78afa974c1 (patch)
tree5aeff2f3cbabe5081e89b56cfcd13487fad3768e /daemon/gdm-xdmcp-display-factory.c
parent17014d50d4e48c6145660df86c27324f566621b4 (diff)
downloadgdm-98917b1ee7d15660bafd4ab8d2441f78afa974c1.tar.gz
Initial support for XDMCP IndirectQuery choosers. Also fix broken
2008-01-30 William Jon McCann <mccann@jhu.edu> * common/gdm-address.c: (add_local_siocgifconf), (add_local_addrinfo), (gdm_address_peek_local_list): * daemon/Makefile.am: * daemon/gdm-chooser-server.c: (generate_address), (handle_select_hostname), (handle_disconnect), (chooser_handle_child_message), (do_introspect), (chooser_server_message_handler), (chooser_server_unregister_handler), (connection_filter_function), (allow_user_function), (handle_connection), (gdm_chooser_server_start), (gdm_chooser_server_stop), (gdm_chooser_server_get_address), (_gdm_chooser_server_set_display_id), (_gdm_chooser_server_set_user_name), (_gdm_chooser_server_set_group_name), (gdm_chooser_server_set_property), (gdm_chooser_server_get_property), (gdm_chooser_server_constructor), (gdm_chooser_server_class_init), (gdm_chooser_server_init), (gdm_chooser_server_finalize), (gdm_chooser_server_new): * daemon/gdm-chooser-server.h: * daemon/gdm-chooser-session.c: (listify_hash), (get_chooser_environment), (chooser_session_child_watch), (spawn_child_setup), (spawn_command_line_sync_as_user), (spawn_command_line_async_as_user), (parse_value_as_integer), (parse_dbus_launch_output), (start_dbus_daemon), (stop_dbus_daemon), (gdm_chooser_session_spawn), (gdm_chooser_session_start), (wait_on_child), (chooser_session_died), (gdm_chooser_session_stop), (gdm_chooser_session_set_server_address), (_gdm_chooser_session_set_x11_display_name), (_gdm_chooser_session_set_x11_display_hostname), (_gdm_chooser_session_set_x11_display_device), (_gdm_chooser_session_set_x11_authority_file), (_gdm_chooser_session_set_user_name), (_gdm_chooser_session_set_group_name), (gdm_chooser_session_set_property), (gdm_chooser_session_get_property), (gdm_chooser_session_constructor), (gdm_chooser_session_class_init), (gdm_chooser_session_init), (gdm_chooser_session_finalize), (gdm_chooser_session_new): * daemon/gdm-chooser-session.h: * daemon/gdm-display.c: (gdm_display_real_set_slave_bus_name), (gdm_display_set_slave_bus_name), (gdm_display_class_init): * daemon/gdm-display.h: * daemon/gdm-display.xml: * daemon/gdm-factory-slave.c: * daemon/gdm-greeter-server.c: * daemon/gdm-greeter-session.c: (gdm_greeter_session_init): * daemon/gdm-product-slave.c: * daemon/gdm-simple-slave.c: * daemon/gdm-slave.c: (gdm_slave_set_slave_bus_name), (gdm_slave_real_start), (register_slave), (gdm_slave_constructor): * daemon/gdm-xdmcp-chooser-display.c: (on_hostname_selected), (gdm_xdmcp_chooser_display_set_slave_bus_name), (gdm_xdmcp_chooser_display_manage), (gdm_xdmcp_chooser_display_class_init), (gdm_xdmcp_chooser_display_init), (gdm_xdmcp_chooser_display_finalize), (gdm_xdmcp_chooser_display_new): * daemon/gdm-xdmcp-chooser-display.h: * daemon/gdm-xdmcp-chooser-display.xml: * daemon/gdm-xdmcp-chooser-slave.c: (on_chooser_session_start), (on_chooser_session_stop), (on_chooser_session_exited), (on_chooser_session_died), (on_chooser_hostname_selected), (on_chooser_disconnected), (on_chooser_connected), (setup_server), (run_chooser), (idle_connect_to_display), (gdm_xdmcp_chooser_slave_run), (gdm_xdmcp_chooser_slave_start), (gdm_xdmcp_chooser_slave_stop), (gdm_xdmcp_chooser_slave_set_property), (gdm_xdmcp_chooser_slave_get_property), (gdm_xdmcp_chooser_slave_constructor), (gdm_xdmcp_chooser_slave_class_init), (gdm_xdmcp_chooser_slave_init), (gdm_xdmcp_chooser_slave_finalize), (gdm_xdmcp_chooser_slave_new): * daemon/gdm-xdmcp-chooser-slave.h: * daemon/gdm-xdmcp-display-factory.c: (set_port_for_request), (gdm_xdmcp_send_forward_query), (indirect_client_create), (indirect_client_destroy), (indirect_client_lookup_by_chosen), (indirect_client_lookup), (gdm_xdmcp_handle_indirect_query), (forward_query_destroy), (remove_oldest_forward), (forward_query_create), (forward_query_lookup), (gdm_xdmcp_handle_forward_query), (gdm_xdmcp_send_decline), (on_hostname_selected), (gdm_xdmcp_display_create), (gdm_xdmcp_handle_request), (gdm_xdmcp_send_refuse), (gdm_xdmcp_handle_manage), (gdm_xdmcp_handle_managed_forward): * daemon/gdm-xdmcp-display.c: (gdm_xdmcp_display_class_init), (gdm_xdmcp_display_finalize): * daemon/gdm-xdmcp-display.h: * daemon/gdm-xdmcp-display.xml: * daemon/gdm-xdmcp-greeter-display.c: (gdm_xdmcp_greeter_display_class_init), (gdm_xdmcp_greeter_display_init), (gdm_xdmcp_greeter_display_finalize), (gdm_xdmcp_greeter_display_new): * daemon/gdm-xdmcp-greeter-display.h: * daemon/xdmcp-chooser-slave-main.c: (get_system_bus), (signal_cb), (on_slave_stopped), (main): * data/gdm.conf: * gui/simple-chooser/Makefile.am: * gui/simple-chooser/chooser-main.c: (assistive_registry_launch), (filter_watch), (filter_timeout), (assistive_registry_start), (at_set_gtk_modules), (load_a11y), (main): * gui/simple-chooser/gdm-chooser-client.c: (gdm_chooser_client_error_quark), (send_dbus_string_method), (send_dbus_void_method), (gdm_chooser_client_call_select_hostname), (gdm_chooser_client_call_disconnect), (client_dbus_handle_message), (client_dbus_filter_function), (gdm_chooser_client_start), (gdm_chooser_client_stop), (gdm_chooser_client_set_property), (gdm_chooser_client_get_property), (gdm_chooser_client_constructor), (gdm_chooser_client_dispose), (gdm_chooser_client_class_init), (gdm_chooser_client_init), (gdm_chooser_client_finalize), (gdm_chooser_client_new): * gui/simple-chooser/gdm-chooser-client.h: * gui/simple-chooser/gdm-chooser-session.c: (launch_compiz), (launch_metacity), (start_window_manager), (start_settings_daemon), (on_dialog_response), (gdm_chooser_session_start), (gdm_chooser_session_stop), (gdm_chooser_session_set_property), (gdm_chooser_session_get_property), (gdm_chooser_session_constructor), (gdm_chooser_session_dispose), (gdm_chooser_session_class_init), (gdm_chooser_session_init), (gdm_chooser_session_finalize), (gdm_chooser_session_new): * gui/simple-chooser/gdm-chooser-session.h: * gui/simple-chooser/test-host-chooser.c: (assistive_registry_launch), (filter_watch), (filter_timeout), (assistive_registry_start), (at_set_gtk_modules), (load_a11y), (main): * gui/simple-greeter/greeter-main.c: (load_a11y), (main): Initial support for XDMCP IndirectQuery choosers. Also fix broken gdm_address_is_local. svn path=/trunk/; revision=5645
Diffstat (limited to 'daemon/gdm-xdmcp-display-factory.c')
-rw-r--r--daemon/gdm-xdmcp-display-factory.c438
1 files changed, 333 insertions, 105 deletions
diff --git a/daemon/gdm-xdmcp-display-factory.c b/daemon/gdm-xdmcp-display-factory.c
index 4f6fe1f4..33ce282a 100644
--- a/daemon/gdm-xdmcp-display-factory.c
+++ b/daemon/gdm-xdmcp-display-factory.c
@@ -52,7 +52,8 @@
#include <X11/Xdmcp.h>
#include "gdm-common.h"
-#include "gdm-xdmcp-display.h"
+#include "gdm-xdmcp-greeter-display.h"
+#include "gdm-xdmcp-chooser-display.h"
#include "gdm-display-factory.h"
#include "gdm-xdmcp-display-factory.h"
#include "gdm-display-store.h"
@@ -136,17 +137,24 @@ static XdmAuthRec serv_authlist = {
};
/* NOTE: Timeout and max are hardcoded */
-typedef struct _GdmForwardQuery {
+typedef struct _ForwardQuery {
time_t acctime;
GdmAddress *dsp_address;
GdmAddress *from_address;
-} GdmForwardQuery;
+} ForwardQuery;
+
+typedef struct _IndirectClient {
+ int id;
+ GdmAddress *dsp_address;
+ GdmAddress *chosen_address;
+ time_t acctime;
+} IndirectClient;
typedef struct {
- int times;
- guint handler;
- GdmAddress *manager;
- GdmAddress *origin;
+ int times;
+ guint handler;
+ GdmAddress *manager;
+ GdmAddress *origin;
GdmXdmcpDisplayFactory *xdmcp_display_factory;
} ManagedForward;
@@ -154,6 +162,7 @@ struct GdmXdmcpDisplayFactoryPrivate
{
GSList *forward_queries;
GSList *managed_forwards;
+ GSList *indirect_clients;
int socket_fd;
gint32 session_serial;
@@ -873,8 +882,6 @@ gdm_xdmcp_send_unwilling (GdmXdmcpDisplayFactory *factory,
#define SIN(__s) ((struct sockaddr_in *) __s)
#define SIN6(__s) ((struct sockaddr_in6 *) __s)
-#if 0
-/* FIXME: Add chooser support */
static void
set_port_for_request (GdmAddress *address,
ARRAY8 *port)
@@ -898,7 +905,6 @@ set_port_for_request (GdmAddress *address,
break;
}
}
-#endif
static void
set_address_for_request (GdmAddress *address,
@@ -925,11 +931,9 @@ set_address_for_request (GdmAddress *address,
}
-#if 0
-/* FIXME: Add chooser support */
static void
gdm_xdmcp_send_forward_query (GdmXdmcpDisplayFactory *factory,
- GdmIndirectDisplay *id,
+ IndirectClient *ic,
GdmAddress *address,
GdmAddress *display_address,
ARRAYofARRAY8Ptr authlist)
@@ -941,11 +945,11 @@ gdm_xdmcp_send_forward_query (GdmXdmcpDisplayFactory *factory,
char *host;
char *serv;
- g_assert (id != NULL);
- g_assert (id->chosen_host != NULL);
+ g_assert (ic != NULL);
+ g_assert (ic->chosen_address != NULL);
host = NULL;
- gdm_address_get_numeric_info (id->chosen_host, &host, NULL);
+ gdm_address_get_numeric_info (ic->chosen_address, &host, NULL);
g_debug ("GdmXdmcpDisplayFactory: Sending forward query to %s",
host);
g_free (host);
@@ -978,13 +982,12 @@ gdm_xdmcp_send_forward_query (GdmXdmcpDisplayFactory *factory,
XdmcpFlush (factory->priv->socket_fd,
&factory->priv->buf,
- (XdmcpNetaddr)gdm_address_peek_sockaddr_storage (id->chosen_host),
+ (XdmcpNetaddr)gdm_address_peek_sockaddr_storage (ic->chosen_address),
(int)sizeof (struct sockaddr_storage));
g_free (port.data);
g_free (addr.data);
}
-#endif
static void
handle_any_query (GdmXdmcpDisplayFactory *factory,
@@ -1051,15 +1054,167 @@ gdm_xdmcp_handle_query (GdmXdmcpDisplayFactory *factory,
}
}
+static IndirectClient *
+indirect_client_create (GdmXdmcpDisplayFactory *factory,
+ GdmAddress *dsp_address)
+{
+ IndirectClient *ic;
+ int count;
+
+ count = g_slist_length (factory->priv->indirect_clients);
+
+ ic = g_new0 (IndirectClient, 1);
+ ic->dsp_address = gdm_address_copy (dsp_address);
+
+ factory->priv->indirect_clients = g_slist_prepend (factory->priv->indirect_clients, ic);
+
+ return ic;
+}
+
+static void
+indirect_client_destroy (GdmXdmcpDisplayFactory *factory,
+ IndirectClient *ic)
+{
+ if (ic == NULL) {
+ return;
+ }
+
+ factory->priv->indirect_clients = g_slist_remove (factory->priv->indirect_clients, ic);
+
+ ic->acctime = 0;
+
+ {
+ char *host;
+
+ host = NULL;
+ gdm_address_get_numeric_info (ic->dsp_address, &host, NULL);
+ g_debug ("GdmXdmcpDisplayFactory: Disposing IndirectClient for %s", host);
+ g_free (host);
+ }
+
+ g_free (ic->dsp_address);
+ ic->dsp_address = NULL;
+ g_free (ic->chosen_address);
+ ic->chosen_address = NULL;
+
+ g_free (ic);
+}
+
+static IndirectClient *
+indirect_client_lookup_by_chosen (GdmXdmcpDisplayFactory *factory,
+ GdmAddress *chosen_address,
+ GdmAddress *origin_address)
+{
+ GSList *li;
+ char *host;
+ IndirectClient *ret;
+
+ g_assert (chosen_address != NULL);
+ g_assert (origin_address != NULL);
+
+ ret = NULL;
+
+ for (li = factory->priv->indirect_clients; li != NULL; li = li->next) {
+ IndirectClient *ic = li->data;
+
+ if (ic != NULL
+ && ic->chosen_address != NULL
+ && gdm_address_equal (ic->chosen_address, chosen_address)) {
+ if (gdm_address_equal (ic->dsp_address, origin_address)) {
+ ret = ic;
+ goto out;
+ } else if (gdm_address_is_loopback (ic->dsp_address)
+ && gdm_address_is_local (origin_address)) {
+ ret = ic;
+ goto out;
+ }
+ }
+ }
+
+ gdm_address_get_numeric_info (chosen_address, &host, NULL);
+
+ g_debug ("GdmXdmcpDisplayFactory: Chosen %s host not found", host);
+ g_free (host);
+ out:
+ return ret;
+}
+
+/* lookup by origin */
+static IndirectClient *
+indirect_client_lookup (GdmXdmcpDisplayFactory *factory,
+ GdmAddress *address)
+{
+ GSList *li;
+ GSList *qlist;
+ IndirectClient *ret;
+ time_t curtime;
+
+ g_assert (address != NULL);
+
+ curtime = time (NULL);
+ ret = NULL;
+
+ qlist = g_slist_copy (factory->priv->indirect_clients);
+
+ for (li = qlist; li != NULL; li = li->next) {
+ IndirectClient *ic;
+ char *host;
+ char *serv;
+
+ ic = (IndirectClient *) li->data;
+
+ if (ic == NULL) {
+ continue;
+ }
+
+ host = NULL;
+ serv = NULL;
+ gdm_address_get_numeric_info (ic->dsp_address, &host, &serv);
+
+ g_debug ("GdmXdmcpDisplayFactory: comparing %s:%s", host, serv);
+ if (gdm_address_equal (ic->dsp_address, address)) {
+ ret = ic;
+ g_free (host);
+ g_free (serv);
+ break;
+ }
+
+ if (ic->acctime > 0 && curtime > ic->acctime + factory->priv->max_wait) {
+ g_debug ("GdmXdmcpDisplayFactory: Disposing stale forward query from %s:%s",
+ host, serv);
+
+ indirect_client_destroy (factory, ic);
+ }
+
+ g_free (host);
+ g_free (serv);
+ }
+
+ g_slist_free (qlist);
+
+ if (ret == NULL) {
+ char *host;
+
+ host = NULL;
+ gdm_address_get_numeric_info (address, &host, NULL);
+ g_debug ("GdmXdmcpDisplayFactory: Host %s not found",
+ host);
+ g_free (host);
+ }
+
+ return ret;
+}
+
static void
gdm_xdmcp_handle_indirect_query (GdmXdmcpDisplayFactory *factory,
GdmAddress *address,
int len)
{
- ARRAYofARRAY8 clnt_authlist;
- int expected_len;
- int i;
- int res;
+ ARRAYofARRAY8 clnt_authlist;
+ int expected_len;
+ int i;
+ int res;
+ IndirectClient *ic;
if (! gdm_xdmcp_host_allow (address)) {
/* ignore the request */
@@ -1071,6 +1226,13 @@ gdm_xdmcp_handle_indirect_query (GdmXdmcpDisplayFactory *factory,
return;
}
+ if (factory->priv->num_sessions > factory->priv->max_displays ||
+ (!gdm_address_is_local (address) &&
+ gdm_xdmcp_num_displays_from_host (factory, address) > factory->priv->max_displays_per_host)) {
+ g_debug ("GdmXdmcpDisplayFactory: reached maximum number of clients - ignoring indirect query");
+ return;
+ }
+
res = XdmcpReadARRAYofARRAY8 (&factory->priv->buf, &clnt_authlist);
if G_UNLIKELY (! res) {
g_warning (_("Could not extract authlist from packet"));
@@ -1085,7 +1247,7 @@ gdm_xdmcp_handle_indirect_query (GdmXdmcpDisplayFactory *factory,
/* Try to look up the display in
* the pending list. If found send a FORWARD_QUERY to the
- * chosen factory. Otherwise alloc a new indirect display. */
+ * chosen manager. Otherwise alloc a new indirect display. */
if (len != expected_len) {
g_warning (_("Error in checksum"));
@@ -1093,18 +1255,16 @@ gdm_xdmcp_handle_indirect_query (GdmXdmcpDisplayFactory *factory,
}
-#if 0
- GdmIndirectDisplay *id;
- /* FIXME: Add chooser support */
+ ic = indirect_client_lookup (factory, address);
- id = gdm_choose_indirect_lookup (address);
-
- if (id != NULL && id->chosen_host != NULL) {
+ if (ic != NULL && ic->chosen_address != NULL) {
/* if user chose us, then just send willing */
- if (gdm_address_is_local (id->chosen_host)) {
+ if (gdm_address_is_local (ic->chosen_address)) {
+ g_debug ("GdmXdmcpDisplayFactory: the chosen address is local - dropping indirect");
+
/* get rid of indirect, so that we don't get
* the chooser */
- gdm_choose_indirect_dispose (id);
+ indirect_client_destroy (factory, ic);
gdm_xdmcp_send_willing (factory, address);
} else if (gdm_address_is_loopback (address)) {
/* woohoo! fun, I have no clue how to get
@@ -1112,13 +1272,15 @@ gdm_xdmcp_handle_indirect_query (GdmXdmcpDisplayFactory *factory,
* queries with all the different IPs */
const GList *list = gdm_address_peek_local_list ();
+ g_debug ("GdmXdmcpDisplayFactory: the chosen address is a loopback");
+
while (list != NULL) {
GdmAddress *saddr = list->data;
if (! gdm_address_is_loopback (saddr)) {
/* forward query to * chosen host */
gdm_xdmcp_send_forward_query (factory,
- id,
+ ic,
address,
saddr,
&clnt_authlist);
@@ -1129,28 +1291,27 @@ gdm_xdmcp_handle_indirect_query (GdmXdmcpDisplayFactory *factory,
} else {
/* or send forward query to chosen host */
gdm_xdmcp_send_forward_query (factory,
- id,
+ ic,
address,
address,
&clnt_authlist);
}
- } else if (id == NULL) {
- id = gdm_choose_indirect_alloc (address);
- if (id != NULL) {
+ } else if (ic == NULL) {
+ ic = indirect_client_create (factory, address);
+ if (ic != NULL) {
gdm_xdmcp_send_willing (factory, address);
}
} else {
gdm_xdmcp_send_willing (factory, address);
}
-#endif
out:
XdmcpDisposeARRAYofARRAY8 (&clnt_authlist);
}
static void
-gdm_forward_query_dispose (GdmXdmcpDisplayFactory *factory,
- GdmForwardQuery *q)
+forward_query_destroy (GdmXdmcpDisplayFactory *factory,
+ ForwardQuery *q)
{
if (q == NULL) {
return;
@@ -1180,11 +1341,11 @@ gdm_forward_query_dispose (GdmXdmcpDisplayFactory *factory,
static gboolean
remove_oldest_forward (GdmXdmcpDisplayFactory *factory)
{
- GSList *li;
- GdmForwardQuery *oldest = NULL;
+ GSList *li;
+ ForwardQuery *oldest = NULL;
for (li = factory->priv->forward_queries; li != NULL; li = li->next) {
- GdmForwardQuery *query = li->data;
+ ForwardQuery *query = li->data;
if (oldest == NULL || query->acctime < oldest->acctime) {
oldest = query;
@@ -1192,20 +1353,20 @@ remove_oldest_forward (GdmXdmcpDisplayFactory *factory)
}
if (oldest != NULL) {
- gdm_forward_query_dispose (factory, oldest);
+ forward_query_destroy (factory, oldest);
return TRUE;
} else {
return FALSE;
}
}
-static GdmForwardQuery *
-gdm_forward_query_alloc (GdmXdmcpDisplayFactory *factory,
+static ForwardQuery *
+forward_query_create (GdmXdmcpDisplayFactory *factory,
GdmAddress *mgr_address,
GdmAddress *dsp_address)
{
- GdmForwardQuery *q;
- int count;
+ ForwardQuery *q;
+ int count;
count = g_slist_length (factory->priv->forward_queries);
@@ -1213,7 +1374,7 @@ gdm_forward_query_alloc (GdmXdmcpDisplayFactory *factory,
count--;
}
- q = g_new0 (GdmForwardQuery, 1);
+ q = g_new0 (ForwardQuery, 1);
q->dsp_address = gdm_address_copy (dsp_address);
q->from_address = gdm_address_copy (mgr_address);
@@ -1222,14 +1383,14 @@ gdm_forward_query_alloc (GdmXdmcpDisplayFactory *factory,
return q;
}
-static GdmForwardQuery *
-gdm_forward_query_lookup (GdmXdmcpDisplayFactory *factory,
+static ForwardQuery *
+forward_query_lookup (GdmXdmcpDisplayFactory *factory,
GdmAddress *address)
{
- GSList *li;
- GSList *qlist;
- GdmForwardQuery *ret;
- time_t curtime;
+ GSList *li;
+ GSList *qlist;
+ ForwardQuery *ret;
+ time_t curtime;
curtime = time (NULL);
ret = NULL;
@@ -1237,11 +1398,11 @@ gdm_forward_query_lookup (GdmXdmcpDisplayFactory *factory,
qlist = g_slist_copy (factory->priv->forward_queries);
for (li = qlist; li != NULL; li = li->next) {
- GdmForwardQuery *q;
- char *host;
- char *serv;
+ ForwardQuery *q;
+ char *host;
+ char *serv;
- q = (GdmForwardQuery *) li->data;
+ q = (ForwardQuery *) li->data;
if (q == NULL) {
continue;
@@ -1263,7 +1424,7 @@ gdm_forward_query_lookup (GdmXdmcpDisplayFactory *factory,
g_debug ("GdmXdmcpDisplayFactory: Disposing stale forward query from %s:%s",
host, serv);
- gdm_forward_query_dispose (factory, q);
+ forward_query_destroy (factory, q);
}
g_free (host);
@@ -1482,14 +1643,14 @@ gdm_xdmcp_handle_forward_query (GdmXdmcpDisplayFactory *factory,
/* Check with tcp_wrappers if display is allowed to access */
if (gdm_xdmcp_host_allow (disp_address)) {
- GdmForwardQuery *q;
+ ForwardQuery *q;
- q = gdm_forward_query_lookup (factory, disp_address);
+ q = forward_query_lookup (factory, disp_address);
if (q != NULL) {
- gdm_forward_query_dispose (factory, q);
+ forward_query_destroy (factory, q);
}
- gdm_forward_query_alloc (factory, address, disp_address);
+ forward_query_create (factory, address, disp_address);
gdm_xdmcp_send_willing (factory, disp_address);
}
@@ -1751,7 +1912,7 @@ gdm_xdmcp_send_decline (GdmXdmcpDisplayFactory *factory,
ARRAY8 authentype;
ARRAY8 authendata;
ARRAY8 status;
- GdmForwardQuery *fq;
+ ForwardQuery *fq;
char *host;
host = NULL;
@@ -1786,28 +1947,100 @@ gdm_xdmcp_send_decline (GdmXdmcpDisplayFactory *factory,
/* Send MANAGED_FORWARD to indicate that the connection
* reached some sort of resolution */
- fq = gdm_forward_query_lookup (factory, address);
+ fq = forward_query_lookup (factory, address);
if (fq != NULL) {
gdm_xdmcp_send_managed_forward (factory, fq->from_address, address);
- gdm_forward_query_dispose (factory, fq);
+ forward_query_destroy (factory, fq);
}
}
+static void
+on_hostname_selected (GdmXdmcpChooserDisplay *display,
+ const char *hostname,
+ GdmXdmcpDisplayFactory *factory)
+{
+ struct addrinfo hints;
+ struct addrinfo *ai_list;
+ struct addrinfo *ai;
+ int gaierr;
+ GdmAddress *address;
+ IndirectClient *ic;
+
+ g_debug ("GdmXdmcpDisplayFactory: hostname selected: %s", hostname);
+
+ address = gdm_xdmcp_display_get_remote_address (GDM_XDMCP_DISPLAY (display));
+
+ g_assert (address != NULL);
+
+ ic = indirect_client_lookup (factory, address);
+
+ if (ic->chosen_address != NULL) {
+ gdm_address_free (ic->chosen_address);
+ ic->chosen_address = NULL;
+ }
+
+ memset (&hints, 0, sizeof (hints));
+ hints.ai_family = gdm_address_get_family_type (address);
+ hints.ai_flags = AI_V4MAPPED; /* this should convert IPv4 address to IPv6 if needed */
+ if ((gaierr = getaddrinfo (hostname, NULL, &hints, &ai_list)) != 0) {
+ g_warning ("Unable get address: %s", gai_strerror (gaierr));
+ return;
+ }
+
+ /* just take the first one */
+ ai = ai_list;
+
+ if (ai != NULL) {
+ char *ip;
+ ic->chosen_address = gdm_address_new_from_sockaddr (ai->ai_addr, ai->ai_addrlen);
+
+ ip = NULL;
+ gdm_address_get_numeric_info (ic->chosen_address, &ip, NULL);
+ g_debug ("GdmXdmcpDisplayFactory: hostname resolves to %s", ip);
+ g_free (ip);
+ }
+
+ freeaddrinfo (ai_list);
+}
+
static GdmDisplay *
-gdm_xdmcp_display_alloc (GdmXdmcpDisplayFactory *factory,
- const char *hostname,
- GdmAddress *address,
- int displaynum)
+gdm_xdmcp_display_create (GdmXdmcpDisplayFactory *factory,
+ const char *hostname,
+ GdmAddress *address,
+ int displaynum)
{
GdmDisplay *display;
GdmDisplayStore *store;
+ gboolean use_chooser;
g_debug ("GdmXdmcpDisplayFactory: Creating xdmcp display for %s:%d", hostname, displaynum);
- display = gdm_xdmcp_display_new (hostname,
- displaynum,
- address,
- get_next_session_serial (factory));
+ use_chooser = FALSE;
+ if (factory->priv->honor_indirect) {
+ IndirectClient *ic;
+
+ ic = indirect_client_lookup (factory, address);
+
+ /* This was an indirect thingie and nothing was yet chosen,
+ * use a chooser */
+ if (ic != NULL && ic->chosen_address == NULL) {
+ use_chooser = TRUE;
+ }
+ }
+
+ if (use_chooser) {
+ display = gdm_xdmcp_chooser_display_new (hostname,
+ displaynum,
+ address,
+ get_next_session_serial (factory));
+ g_signal_connect (display, "hostname-selected", G_CALLBACK (on_hostname_selected), factory);
+ } else {
+ display = gdm_xdmcp_greeter_display_new (hostname,
+ displaynum,
+ address,
+ get_next_session_serial (factory));
+ }
+
if (display == NULL) {
goto out;
}
@@ -2036,10 +2269,10 @@ gdm_xdmcp_handle_request (GdmXdmcpDisplayFactory *factory,
} else {
GdmDisplay *display;
- display = gdm_xdmcp_display_alloc (factory,
- hostname,
- address,
- clnt_dspnum);
+ display = gdm_xdmcp_display_create (factory,
+ hostname,
+ address,
+ clnt_dspnum);
if (display != NULL) {
ARRAY8 authentication_name;
@@ -2196,8 +2429,8 @@ gdm_xdmcp_send_refuse (GdmXdmcpDisplayFactory *factory,
GdmAddress *address,
CARD32 sessid)
{
- XdmcpHeader header;
- GdmForwardQuery *fq;
+ XdmcpHeader header;
+ ForwardQuery *fq;
g_debug ("GdmXdmcpDisplayFactory: Sending REFUSE to %ld",
(long)sessid);
@@ -2218,10 +2451,10 @@ gdm_xdmcp_send_refuse (GdmXdmcpDisplayFactory *factory,
* This was from a forwarded query quite apparently so
* send MANAGED_FORWARD
*/
- fq = gdm_forward_query_lookup (factory, address);
+ fq = forward_query_lookup (factory, address);
if (fq != NULL) {
gdm_xdmcp_send_managed_forward (factory, fq->from_address, address);
- gdm_forward_query_dispose (factory, fq);
+ forward_query_destroy (factory, fq);
}
}
@@ -2234,7 +2467,7 @@ gdm_xdmcp_handle_manage (GdmXdmcpDisplayFactory *factory,
CARD16 clnt_dspnum;
ARRAY8 clnt_dspclass;
GdmDisplay *display;
- GdmForwardQuery *fq;
+ ForwardQuery *fq;
char *host;
host = NULL;
@@ -2292,36 +2525,34 @@ gdm_xdmcp_handle_manage (GdmXdmcpDisplayFactory *factory,
g_debug ("GdmXdmcpDisplayFactory: Looked up %s", name);
g_free (name);
-#if 0
- /* FIXME: Add chooser support */
if (factory->priv->honor_indirect) {
- GdmIndirectDisplay *id;
+ IndirectClient *ic;
- id = gdm_choose_indirect_lookup (address);
+ ic = indirect_client_lookup (factory, address);
/* This was an indirect thingie and nothing was yet chosen,
* use a chooser */
- if (id != NULL &&
- id->chosen_host == NULL) {
- d->use_chooser = TRUE;
- d->indirect_id = id->id;
+ if (ic != NULL && ic->chosen_address == NULL) {
+ g_debug ("GdmXdmcpDisplayFactory: use chooser");
+ /*d->use_chooser = TRUE;
+ d->indirect_id = ic->id;*/
} else {
- d->indirect_id = 0;
- d->use_chooser = FALSE;
- if (id != NULL) {
- gdm_choose_indirect_dispose (id);
+ /*d->indirect_id = 0;
+ d->use_chooser = FALSE;*/
+ if (ic != NULL) {
+ indirect_client_destroy (factory, ic);
}
}
} else {
}
-#endif
+
/* this was from a forwarded query quite apparently so
* send MANAGED_FORWARD */
- fq = gdm_forward_query_lookup (factory, address);
+ fq = forward_query_lookup (factory, address);
if (fq != NULL) {
gdm_xdmcp_send_managed_forward (factory, fq->from_address, address);
- gdm_forward_query_dispose (factory, fq);
+ forward_query_destroy (factory, fq);
}
factory->priv->num_sessions++;
@@ -2355,6 +2586,7 @@ gdm_xdmcp_handle_managed_forward (GdmXdmcpDisplayFactory *factory,
ARRAY8 clnt_address;
char *host;
GdmAddress *disp_address;
+ IndirectClient *ic;
host = NULL;
gdm_address_get_numeric_info (address, &host, NULL);
@@ -2384,14 +2616,10 @@ gdm_xdmcp_handle_managed_forward (GdmXdmcpDisplayFactory *factory,
return;
}
-#if 0
- GdmIndirectDisplay *id;
- /* FIXME: Add chooser support */
- id = gdm_choose_indirect_lookup_by_chosen (address, disp_address);
- if (id != NULL) {
- gdm_choose_indirect_dispose (id);
+ ic = indirect_client_lookup_by_chosen (factory, address, disp_address);
+ if (ic != NULL) {
+ indirect_client_destroy (factory, ic);
}
-#endif
/* Note: we send GOT even on not found, just in case our previous
* didn't get through and this was a second managed forward */