summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorGeorge Lebl <jirka@5z.com>2003-08-04 16:38:09 +0000
committerGeorge Lebl <jirka@src.gnome.org>2003-08-04 16:38:09 +0000
commitecd67810edcfb68aa07bd08cef131cc6bfd31a0f (patch)
tree321d4cfdcc08333042b9211a0a82266e197b4e3e
parent879cc9d014022f9e96a7d983446709dad5819100 (diff)
downloadgdm-ecd67810edcfb68aa07bd08cef131cc6bfd31a0f.tar.gz
Instead of hand fixing the errorgui setup of old, just port the devel
Mon Aug 04 09:33:46 2003 George Lebl <jirka@5z.com> * daemon/auth.[ch], daemon/errorgui.[ch], daemon/slave.c, daemon/gdm.h: Instead of hand fixing the errorgui setup of old, just port the devel setup here whacking bits I don't need in this old version. Much easier.
-rw-r--r--ChangeLog7
-rw-r--r--daemon/auth.c6
-rw-r--r--daemon/auth.h3
-rw-r--r--daemon/errorgui.c375
-rw-r--r--daemon/errorgui.h7
-rw-r--r--daemon/gdm.h6
-rw-r--r--daemon/slave.c8
7 files changed, 229 insertions, 183 deletions
diff --git a/ChangeLog b/ChangeLog
index 4eff8885..403ceee8 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,10 @@
+Mon Aug 04 09:33:46 2003 George Lebl <jirka@5z.com>
+
+ * daemon/auth.[ch], daemon/errorgui.[ch], daemon/slave.c,
+ daemon/gdm.h: Instead of hand fixing the errorgui setup of old,
+ just port the devel setup here whacking bits I don't need in
+ this old version. Much easier.
+
Thu Jul 31 14:10:58 2003 George Lebl <jirka@5z.com>
* Release 2.4.1.5
diff --git a/daemon/auth.c b/daemon/auth.c
index 8ab5c529..cb2995d9 100644
--- a/daemon/auth.c
+++ b/daemon/auth.c
@@ -670,5 +670,11 @@ gdm_auth_purge (GdmDisplay *d, FILE *af)
g_slist_free (keep);
}
+void
+gdm_auth_set_local_auth (GdmDisplay *d)
+{
+ XSetAuthorization ((char *)"MIT-MAGIC-COOKIE-1", (int) strlen ("MIT-MAGIC-COOKIE-1"),
+ (char *)d->bcookie, (int) 16);
+}
/* EOF */
diff --git a/daemon/auth.h b/daemon/auth.h
index 5ae1c2ee..122ae633 100644
--- a/daemon/auth.h
+++ b/daemon/auth.h
@@ -25,6 +25,9 @@ gboolean gdm_auth_secure_display (GdmDisplay *d);
gboolean gdm_auth_user_add (GdmDisplay *d, uid_t user, const char *homedir);
void gdm_auth_user_remove (GdmDisplay *d, uid_t user);
+/* Call XSetAuthorization */
+void gdm_auth_set_local_auth (GdmDisplay *d);
+
#endif /* GDM_AUTH_H */
/* EOF */
diff --git a/daemon/errorgui.c b/daemon/errorgui.c
index 8246f6e7..eb4091a9 100644
--- a/daemon/errorgui.c
+++ b/daemon/errorgui.c
@@ -25,12 +25,14 @@
#include <gdk/gdkx.h>
#include <unistd.h>
#include <syslog.h>
+#include <grp.h>
#include <sys/types.h>
#include <sys/wait.h>
-#include <sys/stat.h>
#include <fcntl.h>
+#include <sys/stat.h>
#include "gdm.h"
#include "misc.h"
+#include "auth.h"
#include <vicious.h>
@@ -41,6 +43,12 @@ extern char **stored_argv;
extern int stored_argc;
extern char *stored_path;
+/* Configuration option variables */
+extern gchar *GdmUser;
+extern gchar *GdmServAuthDir;
+extern uid_t GdmUserId;
+extern gid_t GdmGroupId;
+
static int screenx = 0;
static int screeny = 0;
static int screenwidth = 0;
@@ -100,71 +108,68 @@ get_screen_size (GdmDisplay *d)
static void
center_window (GtkWidget *window)
{
- GtkRequisition req;
+ int w, h;
+
+ /* sanity, should never happen */
+ if (window == NULL)
+ return;
- gtk_widget_size_request (window, &req);
+ gtk_window_get_size (GTK_WINDOW (window), &w, &h);
gtk_window_move (GTK_WINDOW (window),
screenx +
(screenwidth / 2) -
- (req.width / 2),
+ (w / 2),
screeny +
(screenheight / 2) -
- (req.height / 2));
+ (h / 2));
}
static void
show_errors (GtkWidget *button, gpointer data)
{
- const char *file = data;
- char *details;
- FILE *fp;
- struct stat s;
- GtkWidget *sw;
- GtkWidget *label;
- GtkWidget *dlg = gtk_widget_get_toplevel (button);
- GtkWidget *parent = button->parent;
- GString *gs = g_string_new (NULL);
- gboolean valid_utf8 = TRUE;
-
- fp = NULL;
- if (stat (file, &s) == 0) {
- if (S_ISREG (s.st_mode))
- fp = fopen (file, "r");
- else {
- g_string_printf (gs, "%s not a regular file!\n", file);
- }
- }
+ GtkRequisition req;
+ GtkWidget *textsw = data;
+ GtkWidget *dlg = g_object_get_data (G_OBJECT (button), "dlg");
- if (fp != NULL) {
- char buf[128];
- int lines = 0;
- while (fgets (buf, sizeof (buf), fp)) {
- if ( ! g_utf8_validate (buf, -1, NULL))
- valid_utf8 = FALSE;
- g_string_append (gs, buf);
- /* cap lines at 100 */
- if (lines ++ > 100) {
- g_string_append (gs, "\n... File too long to display ...\n");
- break;
- }
- }
- fclose (fp);
+ if (GTK_TOGGLE_BUTTON (button)->active) {
+ gtk_widget_show (textsw);
} else {
- char *loc;
- loc = gdm_locale_to_utf8 (_("%s could not be opened"));
- g_string_append_printf (gs, loc, file);
- g_free (loc);
+ gtk_widget_hide (textsw);
}
- gtk_widget_destroy (button);
+ /* keep window at the size request size */
+ gtk_widget_size_request (dlg, &req);
+ gtk_window_resize (GTK_WINDOW (dlg), req.width, req.height);
+}
+
+static GtkWidget *
+get_error_text_view (const char *details)
+{
+ GtkWidget *sw;
+ GtkWidget *tv;
+ GtkTextBuffer *buf;
+ GtkTextIter iter;
+
+ tv = gtk_text_view_new ();
+ buf = gtk_text_view_get_buffer (GTK_TEXT_VIEW (tv));
+ gtk_text_view_set_editable (GTK_TEXT_VIEW (tv), FALSE);
+ gtk_text_buffer_create_tag (buf, "foo",
+ "editable", FALSE,
+ "family", "monospace",
+ NULL);
+ gtk_text_buffer_get_iter_at_offset (buf, &iter, 0);
+
+ gtk_text_buffer_insert_with_tags_by_name
+ (buf, &iter,
+ ve_sure_string (details), -1,
+ "foo", NULL);
sw = gtk_scrolled_window_new (NULL, NULL);
if (gdk_screen_width () >= 800)
gtk_widget_set_size_request (sw, 500, 150);
else
gtk_widget_set_size_request (sw, 200, 150);
- gtk_widget_show (sw);
gtk_scrolled_window_set_policy (GTK_SCROLLED_WINDOW (sw),
GTK_POLICY_AUTOMATIC,
@@ -173,27 +178,70 @@ show_errors (GtkWidget *button, gpointer data)
gtk_scrolled_window_set_shadow_type (GTK_SCROLLED_WINDOW (sw),
GTK_SHADOW_IN);
- details = g_string_free (gs, FALSE);
+ gtk_container_add (GTK_CONTAINER (sw), tv);
+ gtk_widget_show (tv);
+
+ return sw;
+}
- if ( ! valid_utf8) {
- char *tmp = gdm_locale_to_utf8 (details);
- g_free (details);
- details = tmp;
+static void
+setup_dialog (GdmDisplay *d, const char *name, int closefdexcept, gboolean set_ids)
+{
+ int argc = 1;
+ char **argv;
+
+ closelog ();
+
+ gdm_close_all_descriptors (0 /* from */, closefdexcept /* except */);
+
+ /* No error checking here - if it's messed the best response
+ * is to ignore & try to continue */
+ gdm_open_dev_null (O_RDONLY); /* open stdin - fd 0 */
+ gdm_open_dev_null (O_RDWR); /* open stdout - fd 1 */
+ gdm_open_dev_null (O_RDWR); /* open stderr - fd 2 */
+
+ if (set_ids) {
+ setgid (GdmGroupId);
+ initgroups (GdmUser, GdmGroupId);
+ setuid (GdmUserId);
}
- label = gtk_label_new (details);
- gtk_scrolled_window_add_with_viewport (GTK_SCROLLED_WINDOW (sw), label);
- gtk_widget_show (label);
+ gdm_desetuid ();
+
+ /* restore initial environment */
+ gdm_restoreenv ();
+
+ openlog ("gdm", LOG_PID, LOG_DAEMON);
+
+ gnome_setenv ("LOGNAME", GdmUser, TRUE);
+ gnome_setenv ("USER", GdmUser, TRUE);
+ gnome_setenv ("USERNAME", GdmUser, TRUE);
- gtk_box_pack_start (GTK_BOX (parent),
- sw, TRUE, TRUE, 0);
+ gnome_setenv ("DISPLAY", d->name, TRUE);
+ gnome_unsetenv ("XAUTHORITY");
- center_window (dlg);
+ gdm_auth_set_local_auth (d);
+
+ /* sanity env stuff */
+ gnome_setenv ("SHELL", "/bin/sh", TRUE);
+ /* set HOME to /, we don't need no stinking HOME anyway */
+ if (set_ids)
+ gnome_setenv ("HOME", "/", TRUE);
+ else
+ gnome_setenv ("HOME", ve_sure_string (GdmServAuthDir), TRUE);
+
+ argv = g_new0 (char *, 2);
+ argv[0] = (char *)name;
+
+ gtk_init (&argc, &argv);
+
+ get_screen_size (d);
}
void
gdm_error_box_full (GdmDisplay *d, GtkMessageType type, const char *error,
- const char *details_label, const char *details_file)
+ const char *details_label, const char *details_file,
+ uid_t uid, gid_t gid)
{
pid_t pid;
@@ -201,48 +249,76 @@ gdm_error_box_full (GdmDisplay *d, GtkMessageType type, const char *error,
if (pid == 0) {
guint sid;
- int argc = 1;
- char **argv;
GtkWidget *dlg;
GtkWidget *button;
char *loc;
- char *display;
- char *xauthority;
-
- closelog ();
-
- gdm_close_all_descriptors (0 /* from */, -1 /* except */);
+ char *details;
- /* No error checking here - if it's messed the best response
- * is to ignore & try to continue */
- gdm_open_dev_null (O_RDONLY); /* open stdin - fd 0 */
- gdm_open_dev_null (O_RDWR); /* open stdout - fd 1 */
- gdm_open_dev_null (O_RDWR); /* open stderr - fd 2 */
+ if (uid != 0) {
+ gid_t groups[1] = { gid };
- gdm_desetuid ();
+ setgid (gid);
+ setgroups (1, groups);
+ setuid (uid);
- display = g_strdup (g_getenv ("DISPLAY"));
- xauthority = g_strdup (g_getenv ("XAUTHORITY"));
-
- /* restore initial environment */
- gdm_restoreenv ();
-
- if (display != NULL)
- gnome_setenv ("DISPLAY", display, TRUE);
- if (xauthority != NULL)
- gnome_setenv ("XAUTHORITY", xauthority, TRUE);
- /* sanity env stuff */
- gnome_setenv ("SHELL", "/bin/bash", TRUE);
- gnome_setenv ("HOME", "/", TRUE);
+ gdm_desetuid ();
+ }
- openlog ("gdm", LOG_PID, LOG_DAEMON);
+ /* First read the details if they exist */
+ if (details_file) {
+ FILE *fp;
+ struct stat s;
+ int r;
+ gboolean valid_utf8 = TRUE;
+ GString *gs = g_string_new (NULL);
+
+ fp = NULL;
+ IGNORE_EINTR (r = lstat (details_file, &s));
+ if (r == 0) {
+ if (S_ISREG (s.st_mode))
+ fp = fopen (details_file, "r");
+ else {
+ loc = gdm_locale_to_utf8 ("%s not a regular file!\n");
+ g_string_printf (gs, loc, details_file);
+ g_free (loc);
+ }
+ }
+ if (fp != NULL) {
+ char buf[256];
+ int lines = 0;
+ while (fgets (buf, sizeof (buf), fp)) {
+ if ( ! g_utf8_validate (buf, -1, NULL))
+ valid_utf8 = FALSE;
+ g_string_append (gs, buf);
+ /* cap the lines at 500, that's already
+ a possibility of 128k of crap */
+ if (lines ++ > 500) {
+ loc = gdm_locale_to_utf8 ("\n... File too long to display ...\n");
+ g_string_append (gs, loc);
+ g_free (loc);
+ break;
+ }
+ }
+ fclose (fp);
+ } else {
+ loc = gdm_locale_to_utf8 (_("%s could not be opened"));
+ g_string_append_printf (gs, loc, details_file);
+ g_free (loc);
+ }
- argv = g_new0 (char *, 2);
- argv[0] = "gtk-error-box";
+ details = g_string_free (gs, FALSE);
- gtk_init (&argc, &argv);
+ if ( ! valid_utf8) {
+ char *tmp = gdm_locale_to_utf8 (details);
+ g_free (details);
+ details = tmp;
+ }
+ } else {
+ details = NULL;
+ }
- get_screen_size (d);
+ setup_dialog (d, "gtk-error-box", -1,
+ (uid == 0 || uid == GdmUserId) /* set_ids */);
loc = gdm_locale_to_utf8 (error);
@@ -256,19 +332,26 @@ gdm_error_box_full (GdmDisplay *d, GtkMessageType type, const char *error,
gtk_dialog_set_has_separator (GTK_DIALOG (dlg), FALSE);
if (details_label != NULL) {
+ GtkWidget *text = get_error_text_view (details);
+
loc = gdm_locale_to_utf8 (details_label);
- button = gtk_button_new_with_label (loc);
+ button = gtk_check_button_new_with_label (loc);
g_free (loc);
gtk_widget_show (button);
- g_signal_connect (button, "clicked",
+ g_object_set_data (G_OBJECT (button), "dlg", dlg);
+ g_signal_connect (button, "toggled",
G_CALLBACK (show_errors),
- /* leak? who cares we exit right
- * away */
- g_strdup (details_file));
+ text);
gtk_box_pack_start (GTK_BOX (GTK_DIALOG (dlg)->vbox),
- button, FALSE, FALSE, 3);
+ button, FALSE, FALSE, 6);
+ gtk_box_pack_start (GTK_BOX (GTK_DIALOG (dlg)->vbox),
+ text, FALSE, FALSE, 6);
+
+ g_signal_connect_after (dlg, "size_allocate",
+ G_CALLBACK (center_window),
+ NULL);
}
button = gtk_dialog_add_button (GTK_DIALOG (dlg),
@@ -325,7 +408,10 @@ press_ok (GtkWidget *entry, gpointer data)
void
gdm_error_box (GdmDisplay *d, GtkMessageType type, const char *error)
{
- gdm_error_box_full (d, type, error, NULL, NULL);
+ gdm_error_box_full (d, type, error, NULL, NULL,
+ /* zero for uid/gid doesn't mean root, but
+ it means to use the gdm user/group */
+ 0, 0);
}
char *
@@ -342,47 +428,10 @@ gdm_failsafe_question (GdmDisplay *d,
pid = gdm_fork_extra ();
if (pid == 0) {
guint sid;
- int argc = 1;
- char **argv;
GtkWidget *dlg, *label, *entry;
char *loc;
- char *display;
- char *xauthority;
-
- closelog ();
-
- gdm_close_all_descriptors (0 /* from */, p[1] /* except */);
-
- /* No error checking here - if it's messed the best response
- * is to ignore & try to continue */
- gdm_open_dev_null (O_RDONLY); /* open stdin - fd 0 */
- gdm_open_dev_null (O_RDWR); /* open stdout - fd 1 */
- gdm_open_dev_null (O_RDWR); /* open stderr - fd 2 */
-
- gdm_desetuid ();
-
- display = g_strdup (g_getenv ("DISPLAY"));
- xauthority = g_strdup (g_getenv ("XAUTHORITY"));
-
- /* restore initial environment */
- gdm_restoreenv ();
- if (display != NULL)
- gnome_setenv ("DISPLAY", display, TRUE);
- if (xauthority != NULL)
- gnome_setenv ("XAUTHORITY", xauthority, TRUE);
- /* sanity env stuff */
- gnome_setenv ("SHELL", "/bin/bash", TRUE);
- gnome_setenv ("HOME", "/", TRUE);
-
- openlog ("gdm", LOG_PID, LOG_DAEMON);
-
- argv = g_new0 (char *, 2);
- argv[0] = "gtk-failsafe-question";
-
- gtk_init (&argc, &argv);
-
- get_screen_size (d);
+ setup_dialog (d, "gtk-failsafe-question", p[1], TRUE /* set_ids */);
loc = gdm_locale_to_utf8 (question);
@@ -392,6 +441,7 @@ gdm_failsafe_question (GdmDisplay *d,
GTK_STOCK_OK,
GTK_RESPONSE_OK,
NULL);
+ gtk_dialog_set_has_separator (GTK_DIALOG (dlg), FALSE);
g_signal_connect (G_OBJECT (dlg), "delete_event",
G_CALLBACK (gtk_true), NULL);
@@ -451,17 +501,17 @@ gdm_failsafe_question (GdmDisplay *d,
char buf[BUFSIZ];
int bytes;
- close (p[1]);
+ IGNORE_EINTR (close (p[1]));
gdm_wait_for_extra (NULL);
- bytes = read (p[0], buf, BUFSIZ-1);
+ IGNORE_EINTR (bytes = read (p[0], buf, BUFSIZ-1));
if (bytes > 0) {
- close (p[0]);
+ IGNORE_EINTR (close (p[0]));
buf[bytes] = '\0';
return g_strdup (buf);
}
- close (p[0]);
+ IGNORE_EINTR (close (p[0]));
} else {
gdm_error (_("gdm_failsafe_question: Cannot fork to display error/info box"));
}
@@ -481,47 +531,10 @@ gdm_failsafe_yesno (GdmDisplay *d,
pid = gdm_fork_extra ();
if (pid == 0) {
guint sid;
- int argc = 1;
- char **argv;
GtkWidget *dlg;
char *loc;
- char *display;
- char *xauthority;
-
- closelog ();
-
- gdm_close_all_descriptors (0 /* from */, p[1] /* except */);
-
- /* No error checking here - if it's messed the best response
- * is to ignore & try to continue */
- gdm_open_dev_null (O_RDONLY); /* open stdin - fd 0 */
- gdm_open_dev_null (O_RDWR); /* open stdout - fd 1 */
- gdm_open_dev_null (O_RDWR); /* open stderr - fd 2 */
-
- gdm_desetuid ();
-
- display = g_strdup (g_getenv ("DISPLAY"));
- xauthority = g_strdup (g_getenv ("XAUTHORITY"));
-
- /* restore initial environment */
- gdm_restoreenv ();
-
- if (display != NULL)
- gnome_setenv ("DISPLAY", display, TRUE);
- if (xauthority != NULL)
- gnome_setenv ("XAUTHORITY", xauthority, TRUE);
- /* sanity env stuff */
- gnome_setenv ("SHELL", "/bin/bash", TRUE);
- gnome_setenv ("HOME", "/", TRUE);
-
- openlog ("gdm", LOG_PID, LOG_DAEMON);
-
- argv = g_new0 (char *, 2);
- argv[0] = "gtk-failsafe-yesno";
-
- gtk_init (&argc, &argv);
- get_screen_size (d);
+ setup_dialog (d, "gtk-failsafe-yesno", p[1], TRUE /* set_ids */);
loc = gdm_locale_to_utf8 (question);
@@ -558,9 +571,9 @@ gdm_failsafe_yesno (GdmDisplay *d,
setup_cursor (GDK_LEFT_PTR);
if (gtk_dialog_run (GTK_DIALOG (dlg)) == GTK_RESPONSE_YES)
- gdm_fdprintf (STDOUT_FILENO, "yes\n");
+ gdm_fdprintf (p[1], "yes\n");
else
- gdm_fdprintf (STDOUT_FILENO, "no\n");
+ gdm_fdprintf (p[1], "no\n");
XSetInputFocus (GDK_DISPLAY (),
PointerRoot,
@@ -572,19 +585,19 @@ gdm_failsafe_yesno (GdmDisplay *d,
char buf[BUFSIZ];
int bytes;
- close (p[1]);
+ IGNORE_EINTR (close (p[1]));
gdm_wait_for_extra (NULL);
- bytes = read (p[0], buf, BUFSIZ-1);
+ IGNORE_EINTR (bytes = read (p[0], buf, BUFSIZ-1));
if (bytes > 0) {
- close (p[0]);
+ IGNORE_EINTR (close (p[0]));
if (buf[0] == 'y')
return TRUE;
else
return FALSE;
}
- close (p[0]);
+ IGNORE_EINTR (close (p[0]));
} else {
gdm_error (_("gdm_failsafe_question: Cannot fork to display error/info box"));
}
diff --git a/daemon/errorgui.h b/daemon/errorgui.h
index 4daa8eaf..6581c5ad 100644
--- a/daemon/errorgui.h
+++ b/daemon/errorgui.h
@@ -26,7 +26,12 @@ void gdm_error_box_full (GdmDisplay *d,
GtkMessageType type,
const char *error,
const char *details_label,
- const char *details_file);
+ const char *details_file,
+ /* zero doesn't mean root,
+ we never wish to run as root,
+ zero means use the gdm user */
+ uid_t uid,
+ gid_t gid);
void gdm_error_box (GdmDisplay *d,
GtkMessageType type,
diff --git a/daemon/gdm.h b/daemon/gdm.h
index 86a0abfb..c4e2500f 100644
--- a/daemon/gdm.h
+++ b/daemon/gdm.h
@@ -623,6 +623,12 @@ enum {
* from a local display we started */
};
+#define IGNORE_EINTR(expr) \
+ do { \
+ errno = 0; \
+ expr; \
+ } while (errno == EINTR);
+
#endif /* GDM_H */
/* EOF */
diff --git a/daemon/slave.c b/daemon/slave.c
index 89440fbf..5cc2877b 100644
--- a/daemon/slave.c
+++ b/daemon/slave.c
@@ -2597,6 +2597,8 @@ gdm_slave_session_start (void)
time_t session_start_time, end_time;
gboolean failsafe = FALSE;
pid_t pid;
+ uid_t uid;
+ gid_t gid;
gdm_debug ("gdm_slave_session_start: Attempting session for user '%s'",
login);
@@ -2611,6 +2613,9 @@ gdm_slave_session_start (void)
_("gdm_slave_session_start: User passed auth but getpwnam(%s) failed!"), login);
}
+ uid = pwent->pw_uid;
+ gid = pwent->pw_gid;
+
if (pwent->pw_dir == NULL ||
! g_file_test (pwent->pw_dir, G_FILE_TEST_IS_DIR)) {
char *msg = g_strdup_printf (
@@ -2897,7 +2902,8 @@ gdm_slave_session_start (void)
(home_dir_ok && ! failsafe) ?
_("View details (~/.xsession-errors file)") :
NULL,
- errfile);
+ errfile,
+ uid, gid);
g_free (errfile);
}