diff src/console-x.c @ 0:376386a54a3c r19-14

Import from CVS: tag r19-14
author cvs
date Mon, 13 Aug 2007 08:45:50 +0200
parents
children 0293115a14e9
line wrap: on
line diff
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/console-x.c	Mon Aug 13 08:45:50 2007 +0200
@@ -0,0 +1,282 @@
+/* Console functions for X windows.
+   Copyright (C) 1996 Ben Wing.
+
+This file is part of XEmacs.
+
+XEmacs is free software; you can redistribute it and/or modify it
+under the terms of the GNU General Public License as published by the
+Free Software Foundation; either version 2, or (at your option) any
+later version.
+
+XEmacs is distributed in the hope that it will be useful, but WITHOUT
+ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+for more details.
+
+You should have received a copy of the GNU General Public License
+along with XEmacs; see the file COPYING.  If not, write to
+the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+Boston, MA 02111-1307, USA.  */
+
+/* Synched up with: Not in FSF. */
+
+/* Authorship:
+
+   Ben Wing: January 1996, for 19.14.
+ */
+
+#include <config.h>
+#include "lisp.h"
+
+#include "console-x.h"
+#include "process.h" /* canonicalize_host_name */
+#include "redisplay.h" /* for display_arg */
+
+DEFINE_CONSOLE_TYPE (x);
+
+static int
+x_initially_selected_for_input (struct console *con)
+{
+  return 1;
+}
+
+static void
+split_up_display_spec (Lisp_Object display, int *hostname_length,
+		       int *display_length, int *screen_length)
+{
+  char *dotptr;
+
+  dotptr = strrchr ((char *) string_data (XSTRING (display)), ':');
+  if (!dotptr)
+    {
+      *hostname_length = string_length (XSTRING (display));
+      *display_length = 0;
+    }
+  else
+    {
+      *hostname_length = dotptr - (char *) string_data (XSTRING (display));
+
+      dotptr = strchr (dotptr, '.');
+      if (dotptr)
+	*display_length = (dotptr - (char *) string_data (XSTRING (display))
+			   - *hostname_length);
+      else
+	*display_length = string_length (XSTRING (display)) - *hostname_length;
+    }
+
+  *screen_length = (string_length (XSTRING (display)) - *display_length
+		    - *hostname_length);
+}
+
+/* Remember, in all of the following functions, we have to verify
+   the integrity of our input, because the generic functions don't. */
+
+static Lisp_Object
+x_device_to_console_connection (Lisp_Object connection, Error_behavior errb)
+{
+  /* Strip the trailing .# off of the connection, if it's there. */
+
+  if (NILP (connection))
+    return Qnil;
+  else
+    {
+      int hostname_length, display_length, screen_length;
+
+      if (!ERRB_EQ (errb, ERROR_ME))
+	{
+	  if (!STRINGP (connection))
+	    return Qunbound;
+	}
+      else
+	CHECK_STRING (connection);
+
+      split_up_display_spec (connection, &hostname_length, &display_length,
+			     &screen_length);
+      connection = make_string (string_data (XSTRING (connection)),
+				hostname_length + display_length);
+    }
+
+  return connection;
+}
+
+static Lisp_Object
+get_display_arg_connection (void)
+{
+  CONST char *disp_name;
+
+  /* If the user didn't explicitly specifify a display to use when
+     they called make-x-device, then we first check to see if a
+     display was specified on the command line with -display.  If
+     so, we set disp_name to it.  Otherwise we use XDisplayName to
+     see what DISPLAY is set to.  XtOpenDisplay knows how to do
+     both of these things, but we need to know the name to use. */
+  if (display_arg)
+    {
+      int elt;
+      int argc;
+      char **argv;
+      Lisp_Object conn;
+
+      make_argc_argv (Vx_initial_argv_list, &argc, &argv);
+
+      disp_name = NULL;
+      for (elt = 0; elt < argc; elt++)
+	{
+	  if (!strcmp (argv[elt], "-d") || !strcmp (argv[elt], "-display"))
+	    {
+	      if (elt + 1 == argc)
+		{
+		  suppress_early_backtrace = 1;
+		  error ("-display specified with no arg");
+		}
+	      else
+		{
+		  disp_name = argv[elt + 1];
+		  break;
+		}
+	    }
+	}
+
+      /* assert: display_arg is only set if we found the display
+	 arg earlier so we can't fail to find it now. */
+      assert (disp_name != NULL);
+      conn = build_ext_string (disp_name, FORMAT_CTEXT);
+      free_argc_argv (argv);
+      return conn;
+    }
+  else
+    return build_ext_string (XDisplayName (0), FORMAT_CTEXT);
+}
+
+/* "semi-canonicalize" means convert to a nicer form for printing, but
+   don't completely canonicalize (into some likely ugly form) */
+
+static Lisp_Object
+x_semi_canonicalize_console_connection (Lisp_Object connection,
+					Error_behavior errb)
+{
+  struct gcpro gcpro1;
+
+  GCPRO1 (connection);
+
+  if (NILP (connection))
+    connection = get_display_arg_connection ();
+  else
+    {
+      if (!ERRB_EQ (errb, ERROR_ME))
+	{
+	  if (!STRINGP (connection))
+	    RETURN_UNGCPRO (Qunbound);
+	}
+      else
+	CHECK_STRING (connection);
+    }
+
+
+  /* Be lenient, allow people to specify a device connection instead of
+     a console connection -- e.g. "foo:0.0" instead of "foo:0".  This
+     only happens in `find-console' and `get-console'. */
+  connection = x_device_to_console_connection (connection, errb);
+
+  /* Check for a couple of standard special cases */
+  if (string_byte (XSTRING (connection), 0) == ':')
+    connection = concat2 (build_string ("localhost"), connection);
+  else if (!strncmp ((CONST char *) string_data (XSTRING (connection)),
+		     "unix:", 5))
+    connection = concat2 (build_string ("localhost:"),
+			  Fsubstring (connection, make_int (5), Qnil));
+
+  RETURN_UNGCPRO (connection);
+}
+
+static Lisp_Object
+x_canonicalize_console_connection (Lisp_Object connection, Error_behavior errb)
+{
+  Lisp_Object hostname = Qnil;
+  struct gcpro gcpro1, gcpro2;
+
+  GCPRO2 (connection, hostname);
+
+  connection = x_semi_canonicalize_console_connection (connection, errb);
+  if (UNBOUNDP (connection))
+    RETURN_UNGCPRO (Qunbound);
+
+  {
+    int hostname_length, display_length, screen_length;
+
+    split_up_display_spec (connection, &hostname_length, &display_length,
+			   &screen_length);
+    hostname = Fsubstring (connection, Qzero, make_int (hostname_length));
+    hostname = canonicalize_host_name (hostname);
+    connection = concat2 (hostname,
+			  make_string (string_data (XSTRING (connection))
+				       + hostname_length, display_length));
+  }
+
+  RETURN_UNGCPRO (connection);
+}
+
+static Lisp_Object
+x_semi_canonicalize_device_connection (Lisp_Object connection,
+				       Error_behavior errb)
+{
+  int hostname_length, display_length, screen_length;
+  struct gcpro gcpro1;
+
+  GCPRO1 (connection);
+  if (NILP (connection))
+    connection = get_display_arg_connection ();
+  else
+    {
+      if (!ERRB_EQ (errb, ERROR_ME))
+	{
+	  if (!STRINGP (connection))
+	    RETURN_UNGCPRO (Qunbound);
+	}
+      else
+	CHECK_STRING (connection);
+    }
+
+  split_up_display_spec (connection, &hostname_length, &display_length,
+			 &screen_length);
+
+  if (!screen_length)
+    connection = concat2 (connection, build_string (".0"));
+  RETURN_UNGCPRO (connection);
+}
+
+static Lisp_Object
+x_canonicalize_device_connection (Lisp_Object connection, Error_behavior errb)
+{
+  int hostname_length, display_length, screen_length;
+  Lisp_Object screen_str = Qnil;
+  struct gcpro gcpro1, gcpro2;
+
+  GCPRO2 (screen_str, connection);
+  connection = x_semi_canonicalize_device_connection (connection, errb);
+  if (UNBOUNDP (connection))
+    RETURN_UNGCPRO (Qunbound);
+
+  split_up_display_spec (connection, &hostname_length, &display_length,
+			 &screen_length);
+
+  screen_str = build_string ((CONST char *) string_data (XSTRING (connection))
+			     + hostname_length + display_length);
+  connection = x_canonicalize_console_connection (connection, errb);
+
+  RETURN_UNGCPRO (concat2 (connection, screen_str));
+}
+
+void
+console_type_create_x (void)
+{
+  INITIALIZE_CONSOLE_TYPE (x, "x", "console-x-p");
+  
+  CONSOLE_HAS_METHOD (x, semi_canonicalize_console_connection);
+  CONSOLE_HAS_METHOD (x, canonicalize_console_connection);
+  CONSOLE_HAS_METHOD (x, semi_canonicalize_device_connection);
+  CONSOLE_HAS_METHOD (x, canonicalize_device_connection);
+  CONSOLE_HAS_METHOD (x, device_to_console_connection);
+  CONSOLE_HAS_METHOD (x, initially_selected_for_input);
+}
+