http://ftp.x.org/contrib/applications/xscreensaver-3.07.tar.gz
[xscreensaver] / driver / xscreensaver.c
index d0efd9b0359f7942e5c2bef28f37c4e81c8c0ba8..000b9d91d694b171fa0d0ded9539c75368b41669 100644 (file)
@@ -1,4 +1,4 @@
-/* xscreensaver, Copyright (c) 1991-1998 Jamie Zawinski <jwz@jwz.org>
+/* xscreensaver, Copyright (c) 1991-1999 Jamie Zawinski <jwz@jwz.org>
  *
  * Permission to use, copy, modify, distribute, and sell this software and its
  * documentation for any purpose is hereby granted without fee, provided that
 #include "yarandom.h"
 #include "resources.h"
 #include "visual.h"
+#include "usleep.h"
 
 saver_info *global_si_kludge = 0;      /* I hate C so much... */
 
@@ -287,6 +288,8 @@ saver_ehandler (Display *dpy, XErrorEvent *error)
 {
   saver_info *si = global_si_kludge;   /* I hate C so much... */
 
+  if (!real_stderr) real_stderr = stderr;
+
   fprintf (real_stderr, "\n"
           "#######################################"
           "#######################################\n\n"
@@ -303,11 +306,25 @@ saver_ehandler (Display *dpy, XErrorEvent *error)
        }
       else
        {
-         fprintf(real_stderr,
-                 "%s: to dump a core file, re-run with `-sync'.\n"
-                 "%s: see http://www.jwz.org/xscreensaver/bugs.html\n"
-                 "\t\tfor bug reporting information.\n\n",
-                 blurb(), blurb());
+          fprintf (real_stderr,
+                   "#######################################"
+                   "#######################################\n\n");
+          fprintf (real_stderr,
+   "    If at all possible, please re-run xscreensaver with the command line\n"
+   "    arguments `-sync -verbose', and reproduce this bug.  That will cause\n"
+   "    xscreensaver to dump a `core' file to the current directory.  Please\n"
+   "    include the stack trace from that core file in your bug report.\n"
+   "\n"
+   "    http://www.jwz.org/xscreensaver/bugs.html explains how to create the\n"
+   "    most useful bug reports, and how to examine core files.\n"
+   "\n"
+   "    The more information you can provide, the better.  But please report\n"
+   "    report this bug, regardless!\n"
+   "\n");
+          fprintf (real_stderr,
+                   "#######################################"
+                   "#######################################\n\n");
+
          saver_exit (si, -1, 0);
        }
     }
@@ -316,6 +333,50 @@ saver_ehandler (Display *dpy, XErrorEvent *error)
   return 0;
 }
 
+
+/* This error handler is used only while the X connection is being set up;
+   after we've got a connection, we don't use this handler again.  The only
+   reason for having this is so that we can present a more idiot-proof error
+   message than "cannot open display."
+ */
+static void 
+startup_ehandler (String name, String type, String class,
+                  String defalt,  /* one can't even spel properly
+                                     in this joke of a language */
+                  String *av, Cardinal *ac)
+{
+  char fmt[512];
+  String p[10];
+  saver_info *si = global_si_kludge;   /* I hate C so much... */
+  XrmDatabase *db = XtAppGetErrorDatabase(si->app);
+  *fmt = 0;
+  XtAppGetErrorDatabaseText(si->app, name, type, class, defalt,
+                            fmt, sizeof(fmt)-1, *db);
+
+  fprintf (stderr, "%s: ", blurb());
+
+  memset (p, 0, sizeof(p));
+  if (*ac > countof (p)) *ac = countof (p);
+  memcpy ((char *) p, (char *) av, (*ac) * sizeof(*av));
+  fprintf (stderr, fmt,                /* Did I mention that I hate C? */
+           p[0], p[1], p[2], p[3], p[4], p[5], p[6], p[7], p[8], p[9]);
+  fprintf (stderr, "\n");
+
+  describe_uids (si, stderr);
+  fprintf (stderr, "\n"
+           "%s: Errors at startup are usually authorization problems.\n"
+           "              Did you read the manual?  Specifically, the parts\n"
+           "              that talk about XAUTH, XDM, and root logins?\n"
+           "\n"
+           "              http://www.jwz.org/xscreensaver/man.html\n"
+           "\n",
+           blurb());
+
+  fflush (stderr);
+  fflush (stdout);
+  exit (1);
+}
+
 \f
 /* The zillions of initializations.
  */
@@ -360,7 +421,8 @@ privileged_initialization (saver_info *si, int *argc, char **argv)
   si->nolock_reason = "not compiled with locking support";
 #else /* !NO_LOCKING */
   si->locking_disabled_p = False;
-  if (! lock_init (*argc, argv)) /* before hack_uid() for proper permissions */
+  /* before hack_uid() for proper permissions */
+  if (! lock_init (*argc, argv, si->prefs.verbose_p))
     {
       si->locking_disabled_p = True;
       si->nolock_reason = "error getting password";
@@ -381,9 +443,12 @@ connect_to_server (saver_info *si, int *argc, char **argv)
   Widget toplevel_shell;
 
   XSetErrorHandler (saver_ehandler);
+
+  XtAppSetErrorMsgHandler (si->app, startup_ehandler);
   toplevel_shell = XtAppInitialize (&si->app, progclass,
                                    options, XtNumber (options),
                                    argc, argv, defaults, 0, 0);
+  XtAppSetErrorMsgHandler (si->app, 0);
 
   si->dpy = XtDisplay (toplevel_shell);
   si->prefs.db = XtDatabase (si->dpy);
@@ -633,6 +698,10 @@ initialize_server_extensions (saver_info *si)
   Bool server_has_sgi_saver_extension_p = False;
   Bool server_has_mit_saver_extension_p = False;
 
+  si->using_xidle_extension = p->use_xidle_extension;
+  si->using_sgi_saver_extension = p->use_sgi_saver_extension;
+  si->using_mit_saver_extension = p->use_mit_saver_extension;
+
 #ifdef HAVE_XIDLE_EXTENSION
   server_has_xidle_extension_p = query_xidle_extension (si);
 #endif
@@ -644,20 +713,20 @@ initialize_server_extensions (saver_info *si)
 #endif
 
   if (!server_has_xidle_extension_p)
-    p->use_xidle_extension = False;
+    si->using_xidle_extension = False;
   else if (p->verbose_p)
     {
-      if (p->use_xidle_extension)
+      if (si->using_xidle_extension)
        fprintf (stderr, "%s: using XIDLE extension.\n", blurb());
       else
        fprintf (stderr, "%s: not using server's XIDLE extension.\n", blurb());
     }
 
   if (!server_has_sgi_saver_extension_p)
-    p->use_sgi_saver_extension = False;
+    si->using_sgi_saver_extension = False;
   else if (p->verbose_p)
     {
-      if (p->use_sgi_saver_extension)
+      if (si->using_sgi_saver_extension)
        fprintf (stderr, "%s: using SGI SCREEN_SAVER extension.\n", blurb());
       else
        fprintf (stderr,
@@ -666,10 +735,10 @@ initialize_server_extensions (saver_info *si)
     }
 
   if (!server_has_mit_saver_extension_p)
-    p->use_mit_saver_extension = False;
+    si->using_mit_saver_extension = False;
   else if (p->verbose_p)
     {
-      if (p->use_mit_saver_extension)
+      if (si->using_mit_saver_extension)
        fprintf (stderr, "%s: using lame MIT-SCREEN-SAVER extension.\n",
                 blurb());
       else
@@ -692,9 +761,9 @@ select_events (saver_info *si)
   saver_preferences *p = &si->prefs;
   int i;
 
-  if (p->use_xidle_extension ||
-      p->use_mit_saver_extension ||
-      p->use_sgi_saver_extension)
+  if (si->using_xidle_extension ||
+      si->using_mit_saver_extension ||
+      si->using_sgi_saver_extension)
     return;
 
   if (p->initial_delay)
@@ -947,7 +1016,6 @@ clientmessage_response (saver_info *si, Window w, Bool error,
 Bool
 handle_clientmessage (saver_info *si, XEvent *event, Bool until_idle_p)
 {
-  saver_preferences *p = &si->prefs;
   Atom type = 0;
   Window window = event->xclient.window;
 
@@ -980,7 +1048,7 @@ handle_clientmessage (saver_info *si, XEvent *event, Bool until_idle_p)
                                 "activating.");
          si->selection_mode = 0;
          si->demoing_p = False;
-         if (p->use_mit_saver_extension || p->use_sgi_saver_extension)
+         if (si->using_mit_saver_extension || si->using_sgi_saver_extension)
            {
              XForceScreenSaver (si->dpy, ScreenSaverActive);
              return False;
@@ -1001,7 +1069,7 @@ handle_clientmessage (saver_info *si, XEvent *event, Bool until_idle_p)
          clientmessage_response(si, window, False,
                                 "DEACTIVATE ClientMessage received.",
                                 "deactivating.");
-         if (p->use_mit_saver_extension || p->use_sgi_saver_extension)
+         if (si->using_mit_saver_extension || si->using_sgi_saver_extension)
            {
              XForceScreenSaver (si->dpy, ScreenSaverReset);
              return False;
@@ -1204,7 +1272,8 @@ handle_clientmessage (saver_info *si, XEvent *event, Bool until_idle_p)
 
          if (until_idle_p)
            {
-             if (p->use_mit_saver_extension || p->use_sgi_saver_extension)
+             if (si->using_mit_saver_extension ||
+                  si->using_sgi_saver_extension)
                {
                  XForceScreenSaver (si->dpy, ScreenSaverActive);
                  return False;