http://ftp.x.org/contrib/applications/xscreensaver-2.24.tar.gz
[xscreensaver] / driver / xset.c
index c4fb6d6b150ca90ce05cf774d671e2fec05b35cd..305ce846367944d2d8d4dfb2e4e3ca50a630c59f 100644 (file)
@@ -1,5 +1,5 @@
 /* xset.c --- interacting with server extensions and the builtin screensaver.
 /* xset.c --- interacting with server extensions and the builtin screensaver.
- * xscreensaver, Copyright (c) 1991-1997 Jamie Zawinski <jwz@netscape.com>
+ * xscreensaver, Copyright (c) 1991-1998 Jamie Zawinski <jwz@netscape.com>
  *
  * Permission to use, copy, modify, distribute, and sell this software and its
  * documentation for any purpose is hereby granted without fee, provided that
  *
  * Permission to use, copy, modify, distribute, and sell this software and its
  * documentation for any purpose is hereby granted without fee, provided that
@@ -124,7 +124,7 @@ init_sgi_saver_extension (saver_info *si)
          fprintf (stderr,
        "%s: SGI SCREEN_SAVER extension exists, but can't be initialized;\n\
                perhaps some other screensaver program is already running?\n",
          fprintf (stderr,
        "%s: SGI SCREEN_SAVER extension exists, but can't be initialized;\n\
                perhaps some other screensaver program is already running?\n",
-                  progname);
+                  blurb());
          p->use_sgi_saver_extension = False;
          return;
        }
          p->use_sgi_saver_extension = False;
          return;
        }
@@ -134,7 +134,7 @@ init_sgi_saver_extension (saver_info *si)
 #endif /* HAVE_SGI_SAVER_EXTENSION */
 
 \f
 #endif /* HAVE_SGI_SAVER_EXTENSION */
 
 \f
-/* Figuring out what the appropriate XSetScreenSaver() paramters are
+/* Figuring out what the appropriate XSetScreenSaver() parameters are
    (one wouldn't expect this to be rocket science.)
  */
 
    (one wouldn't expect this to be rocket science.)
  */
 
@@ -157,32 +157,16 @@ disable_builtin_screensaver (saver_info *si, Bool turn_off_p)
 
   /* On SGIs, if interval is non-zero, it is the number of seconds after
      screen saving starts at which the monitor should be powered down.
 
   /* On SGIs, if interval is non-zero, it is the number of seconds after
      screen saving starts at which the monitor should be powered down.
-     Obviously I don't want that, so make sure it's a large positive number.
+     Obviously I don't want that, so set it to 0 (meaning "never".)
 
      Power saving is disabled if DontPreferBlanking, but in that case,
      we don't get extension events either.  So we can't turn it off that way.
 
 
      Power saving is disabled if DontPreferBlanking, but in that case,
      we don't get extension events either.  So we can't turn it off that way.
 
-     The man page for `XSetScreenSaver' says that setting interval to 0 will
-     disable powering down of the monitor, but this turns out not to be the
-     case on Irix 6.3 (O2); the monitor powers down anyway.  It didn't do
-     this on 6.2, so someone screwed up.
-
-     Extra Sucky Factoid #2: the number can't be more than 15 bits, which
-     is only a bit over nine hours.  So there's just *no fucking way* to make
-     an SGI O2 leave its monitor powered on and idle for more than nine hours.
-     You fucking losers!
-
-     [...Later...]  Ok, it's worse than that.  The above doesn't work either.
-     Setting it to a small number will cause it to power down early; but even
-     if you set it to a large number, it still seems to power down in about
-     an hour.  You fucking fucking fucking losers!
+     Note: if you're running Irix 6.3 (O2), you may find that your monitor is
+     powering down anyway, regardless of the xset settings.  This is fixed by
+     installing SGI patches 2447 and 2537.
    */
    */
-#ifdef HAVE_SGI_SAVER_EXTENSION
-  if (p->use_sgi_saver_extension)
-    desired_server_interval = 32767;
-  else
-#endif
-    desired_server_interval = 0;
+  desired_server_interval = 0;
 
   /* I suspect (but am not sure) that DontAllowExposures might have
      something to do with powering off the monitor as well. */
 
   /* I suspect (but am not sure) that DontAllowExposures might have
      something to do with powering off the monitor as well. */
@@ -214,11 +198,11 @@ disable_builtin_screensaver (saver_info *si, Bool turn_off_p)
       if (desired_server_timeout == 0)
        printf ("%s%sisabling server builtin screensaver.\n\
        You can re-enable it with \"xset s on\".\n",
       if (desired_server_timeout == 0)
        printf ("%s%sisabling server builtin screensaver.\n\
        You can re-enable it with \"xset s on\".\n",
-               (p->verbose_p ? "" : progname),
+               (p->verbose_p ? "" : blurb()),
                (p->verbose_p ? "\n\tD" : ": d"));
 
       if (p->verbose_p)
                (p->verbose_p ? "\n\tD" : ": d"));
 
       if (p->verbose_p)
-       fprintf (stderr, "%s: (xset s %d %d %s %s)\n", progname,
+       fprintf (stderr, "%s: (xset s %d %d %s %s)\n", blurb(),
                 desired_server_timeout, desired_server_interval,
                 (desired_prefer_blank ? "blank" : "noblank"),
                 (desired_allow_exp ? "noexpose" : "expose"));
                 desired_server_timeout, desired_server_interval,
                 (desired_prefer_blank ? "blank" : "noblank"),
                 (desired_allow_exp ? "noexpose" : "expose"));
@@ -250,3 +234,121 @@ disable_builtin_screensaver (saver_info *si, Bool turn_off_p)
     /* Turn off the server builtin saver if it is now running. */
     XForceScreenSaver (si->dpy, ScreenSaverReset);
 }
     /* Turn off the server builtin saver if it is now running. */
     XForceScreenSaver (si->dpy, ScreenSaverReset);
 }
+
+\f
+/* Display Power Management System (DPMS.)
+
+   On XFree86 systems, "man xset" reports:
+
+       -dpms    The -dpms option disables DPMS (Energy Star) features.
+       +dpms    The +dpms option enables DPMS (Energy Star) features.
+
+       dpms flags...
+                The dpms option allows the DPMS (Energy Star)
+                parameters to be set.  The option can take up to three
+                numerical values, or the `force' flag followed by a
+                DPMS state.  The `force' flags forces the server to
+                immediately switch to the DPMS state specified.  The
+                DPMS state can be one of `standby', `suspend', or
+                `off'.  When numerical values are given, they set the
+                inactivity period before the three modes are activated.
+                The first value given is for the `standby' mode, the
+                second is for the `suspend' mode, and the third is for
+                the `off' mode.  Setting these values implicitly
+                enables the DPMS features.  A value of zero disables a
+                particular mode.
+
+   However, note that the implementation is more than a little bogus,
+   in that there is code in /usr/X11R6/lib/libXdpms.a to implement all
+   the usual server-extension-querying utilities -- but there are no
+   prototypes in any header file!  Thus, the prototypes here.  (The
+   stuff in X11/extensions/dpms.h and X11/extensions/dpmsstr.h define
+   the raw X protcol, they don't define the API to libXdpms.a.)
+ */
+
+#ifdef HAVE_DPMS_EXTENSION
+
+#include <X11/Xproto.h>                        /* for CARD16 */
+#include <X11/extensions/dpms.h>
+#include <X11/extensions/dpmsstr.h>
+
+extern Bool DPMSQueryExtension (Display *dpy, int *event_ret, int *error_ret);
+extern Bool DPMSCapable (Display *dpy);
+extern Status DPMSForceLevel (Display *dpy, CARD16 level);
+extern Status DPMSInfo (Display *dpy, CARD16 *power_level, BOOL *state);
+
+#if 0 /* others we don't use */
+extern Status DPMSGetVersion (Display *dpy, int *major_ret, int *minor_ret);
+extern Status DPMSSetTimeouts (Display *dpy,
+                              CARD16 standby, CARD16 suspend, CARD16 off);
+extern Bool DPMSGetTimeouts (Display *dpy,
+                            CARD16 *standby, CARD16 *suspend, CARD16 *off);
+extern Status DPMSEnable (Display *dpy);
+extern Status DPMSDisable (Display *dpy);
+#endif /* 0 */
+
+
+Bool
+monitor_powered_on_p (saver_info *si)
+{
+  Bool result;
+  int event_number, error_number;
+  BOOL onoff = False;
+  CARD16 state;
+
+  if (!DPMSQueryExtension(si->dpy, &event_number, &error_number))
+    /* Server doesn't know -- assume the monitor is on. */
+    result = True;
+
+  else if (!DPMSCapable(si->dpy))
+    /* Server says the monitor doesn't do power management -- so it's on. */
+    result = True;
+
+  else
+    {
+      DPMSInfo(si->dpy, &state, &onoff);
+      if (!onoff)
+       /* Server says DPMS is disabled -- so the monitor is on. */
+       result = True;
+      else
+       switch (state) {
+       case DPMSModeOn:      result = True;  break;  /* really on */
+       case DPMSModeStandby: result = False; break;  /* kinda off */
+       case DPMSModeSuspend: result = False; break;  /* pretty off */
+       case DPMSModeOff:     result = False; break;  /* really off */
+       default:              result = True;  break;  /* protocol error? */
+       }
+    }
+
+  return result;
+}
+
+void
+monitor_power_on (saver_info *si)
+{
+  if (!monitor_powered_on_p (si))
+    {
+      DPMSForceLevel(si->dpy, DPMSModeOn);
+      XSync(si->dpy, False);
+      if (!monitor_powered_on_p (si))
+       fprintf (stderr,
+       "%s: DPMSForceLevel(dpy, DPMSModeOn) did not power the monitor on?\n",
+                blurb());
+    }
+}
+
+#else  /* !HAVE_DPMS_EXTENSION */
+
+Bool
+monitor_powered_on_p (saver_info *si) 
+{
+  return True; 
+}
+
+void
+monitor_power_on (saver_info *si)
+{
+  return; 
+}
+
+#endif /* !HAVE_DPMS_EXTENSION */