commit 92b09c0d1863c4de1bae1fbbbf78bd02fad91a5e Author: Halton Huo Date: Thu May 27 14:40:41 2010 +0800 gdm-10-sol-notty.diff diff --git a/daemon/gdm-server.c b/daemon/gdm-server.c index 28c8238..2274286 100644 --- a/daemon/gdm-server.c +++ b/daemon/gdm-server.c @@ -77,6 +77,7 @@ struct GdmServerPrivate GPid pid; GPid fbconsolepid; + gboolean is_local; int priority; char *user_name; char *session_args; @@ -271,15 +272,43 @@ _gdm_server_query_ck_for_display_device (GdmServer *server) NULL, &status, &error); + g_free (command); + if (! res) { g_warning ("Could not run helper: %s", error->message); g_error_free (error); - } else { - out = g_strstrip (out); - g_debug ("GdmServer: Got tty: '%s'", out); + g_free (out); + return NULL; } - g_free (command); + out = g_strstrip (out); + + /* There are several scenarios that the device will be "?" + * 1. Local sessions without VT support. If the display is ":0", + * we set the device as "/dev/console" to gain device permissions. + * This only happens on those systems do not has VT support such as + * old Solaris. So far, Linux and OpenSolaris with VT support. + * 2. XDMCP sessions, we set device as "/dev/dtremote" + * 3. Local sessions like SunRay, Xvfb, Xvnc, we set device as + * "/dev/dtlocal" + */ + if (g_str_equal (out, "?")) { + if (!server->priv->is_local) { + /* This is for XDMCP sessions. */ + out = g_strdup ("/dev/dtremote"); + } else { + if (g_str_equal (server->priv->display_name, ":0")) { + /* This is for local session run on console. */ + out = g_strdup ("/dev/console"); + } else { + /* This is for local sessions like + * SunRay, Xvfb, Xvnc, etc. */ + out = g_strdup ("/dev/dtlocal"); + } + } + } + + g_debug ("GdmServer: Got tty: '%s'", out); return out; } @@ -1229,5 +1258,23 @@ gdm_server_new (const char *display_id) server->priv->auth_file = NULL; } + error = NULL; + res = dbus_g_proxy_call (proxy, + "IsLocal", + &error, + G_TYPE_INVALID, + G_TYPE_BOOLEAN, &server->priv->is_local, + G_TYPE_INVALID); + if (! res) { + if (error != NULL) { + g_warning ("Failed to get value: %s", error->message); + g_error_free (error); + } else { + g_warning ("Failed to get value"); + } + + exit (1); + } + return server; } diff --git a/daemon/gdm-simple-slave.c b/daemon/gdm-simple-slave.c index 4d0b498..c81c798 100644 --- a/daemon/gdm-simple-slave.c +++ b/daemon/gdm-simple-slave.c @@ -25,6 +25,8 @@ #include #include #include +#include +#include #include #include #include @@ -615,6 +617,46 @@ on_console_session_changed (GdmSession *session, } static void +create_device (const char *dev) +{ +#ifdef __sun + gchar buf[MAXPATHLEN + 1]; + struct stat st; + + if (dev == NULL || dev[0] == '\0') + return; + + if (strcmp (dev, "/dev/dtlocal") != 0 && + strcmp (dev, "/dev/dtremote") != 0 ) + return; + + memset (buf, 0, sizeof (gchar) * (MAXPATHLEN + 1)); + + if (stat (dev, &st) != 0) { + g_debug ("Creating pseudo-device %s", dev); + symlink ("/dev/null", dev); + } else if (readlink (dev, buf, MAXPATHLEN) > 0) { + if (strcmp (buf, "/dev/null") == 0) { + /* Touch symlink */ + struct utimbuf timebuf; + + timebuf.modtime = time ((time_t *) 0); + timebuf.actime = timebuf.modtime; + + if ((utime (dev, &timebuf)) != 0) + g_debug ("Problem updating access time of pseudo-device %s", dev); + else + g_debug ("Touching pseudo-device %s", dev); + } else { + g_debug ("Device %s points to %s", dev, buf); + } + } else { + g_debug ("Device %s is not a symlink", dev); + } +#endif +} + +static void create_new_session (GdmSimpleSlave *slave) { gboolean display_is_local; @@ -638,6 +680,9 @@ create_new_session (GdmSimpleSlave *slave) if (slave->priv->server != NULL) { display_device = gdm_server_get_display_device (slave->priv->server); } + if (!display_device && !display_is_local) + display_device = g_strdup ("/dev/dtremote"); + create_device (display_device); slave->priv->session = gdm_session_direct_new (display_id, display_name, @@ -963,6 +1008,10 @@ start_greeter (GdmSimpleSlave *slave) display_device = gdm_server_get_display_device (slave->priv->server); } + if (!display_device && !display_is_local) + display_device = g_strdup ("/dev/dtremote"); + create_device (display_device); + /* FIXME: send a signal back to the master */ /* If XDMCP setup pinging */