From 1f91fc0f94fd303e63c96bc8e1d19f0b6f06282b Mon Sep 17 00:00:00 2001
From: Taylor R Campbell <campbell@mumble.net>
Date: Thu, 14 Oct 2010 03:02:18 +0000
Subject: [PATCH] Fix some signedness issues in the X11 primitives.

Times are always unsigned; reflect this.

Screen coordinates are signed, and not always nonnegative; project
negative ones onto the border.  Widths and heights are technically
signed too, according to my Xlib.h, but I haven't observed negative
values, and negative values can't possibly make sense, whereas I have
observed negative coordinates in the wild (button down in-window,
button up out-of-window).
---
 src/microcode/x11base.c  |  2 +-
 src/microcode/x11graph.c |  6 ++++--
 src/microcode/x11term.c  | 25 ++++++++++++++-----------
 3 files changed, 19 insertions(+), 14 deletions(-)

diff --git a/src/microcode/x11base.c b/src/microcode/x11base.c
index 9ef4bbe26..8f624affd 100644
--- a/src/microcode/x11base.c
+++ b/src/microcode/x11base.c
@@ -1295,7 +1295,7 @@ x_event_to_object (XEvent * event)
 		  {
 		    result
 		      = (make_event_object (xw, event_type_take_focus, 1));
-		    EVENT_INTEGER
+		    EVENT_ULONG_INTEGER
 		      (result, EVENT_0, (((event->xclient) . data . l) [1]));
 		  }
 	      }
diff --git a/src/microcode/x11graph.c b/src/microcode/x11graph.c
index 30cde37f4..d625cc4c6 100644
--- a/src/microcode/x11graph.c
+++ b/src/microcode/x11graph.c
@@ -1113,7 +1113,8 @@ DEFINE_PRIMITIVE ("X-GRAPHICS-MAP-X-COORDINATE", Prim_x_graphics_map_x_coordinat
   PRIMITIVE_HEADER (2);
   {
     struct xwindow * xw = (x_window_arg (1));
-    unsigned int xp = (arg_ulong_integer (2));
+    int signed_xp = (arg_integer (2));
+    unsigned int xp = ((signed_xp < 0) ? 0 : ((unsigned int) signed_xp));
     int bx = (xp - (XW_INTERNAL_BORDER_WIDTH (xw)));
     PRIMITIVE_RETURN
       (x_coordinate_map
@@ -1129,7 +1130,8 @@ DEFINE_PRIMITIVE ("X-GRAPHICS-MAP-Y-COORDINATE", Prim_x_graphics_map_y_coordinat
   PRIMITIVE_HEADER (2);
   {
     struct xwindow * xw = (x_window_arg (1));
-    unsigned int yp = (arg_ulong_integer (2));
+    int signed_yp = (arg_integer (2));
+    unsigned int yp = ((signed_yp < 0) ? 0 : ((unsigned int) signed_yp));
     int by = (yp - (XW_INTERNAL_BORDER_WIDTH (xw)));
     PRIMITIVE_RETURN
       (y_coordinate_map
diff --git a/src/microcode/x11term.c b/src/microcode/x11term.c
index 35c0fa498..00c91b884 100644
--- a/src/microcode/x11term.c
+++ b/src/microcode/x11term.c
@@ -273,34 +273,35 @@ xterm_dump_contents (struct xwindow * xw,
 	}
     }
 }
-
+
 static void
 xterm_dump_rectangle (struct xwindow * xw,
-		      unsigned int x,
-		      unsigned int y,
+		      int signed_x,
+		      int signed_y,
 		      unsigned int width,
 		      unsigned int height)
 {
   XFontStruct * font = (XW_FONT (xw));
+  int x, y;
   unsigned int fwidth = (FONT_WIDTH (font));
   unsigned int fheight = (FONT_HEIGHT (font));
   unsigned int border = (XW_INTERNAL_BORDER_WIDTH (xw));
-  if (x < border)
+  if ((signed_x < 0) || (((unsigned int) signed_x) < border))
     {
       width -= (border - x);
       x = 0;
     }
   else
-    x -= border;
+    x = (((unsigned int) signed_x) - border);
   if ((x + width) > (XW_X_SIZE (xw)))
     width = ((XW_X_SIZE (xw)) - x);
-  if (y < border)
+  if ((signed_y < 0) || (((unsigned int) signed_y) < border))
     {
       height -= (border - y);
       y = 0;
     }
   else
-    y -= border;
+    y = (((unsigned int) signed_y) - border);
   if ((y + height) > (XW_Y_SIZE (xw)))
     height = ((XW_Y_SIZE (xw)) - y);
   {
@@ -407,8 +408,8 @@ DEFINE_PRIMITIVE ("XTERM-DUMP-RECTANGLE", Prim_xterm_dump_rectangle, 5, 5, 0)
 {
   PRIMITIVE_HEADER (5);
   xterm_dump_rectangle ((x_window_arg (1)),
-			(arg_ulong_integer (2)),
-			(arg_ulong_integer (3)),
+			(arg_integer (2)),
+			(arg_integer (3)),
 			(arg_ulong_integer (4)),
 			(arg_ulong_integer (5)));
   PRIMITIVE_RETURN (UNSPECIFIC);
@@ -419,7 +420,8 @@ DEFINE_PRIMITIVE ("XTERM-MAP-X-COORDINATE", Prim_xterm_map_x_coordinate, 2, 2, 0
   PRIMITIVE_HEADER (2);
   {
     struct xwindow * xw = (x_window_arg (1));
-    unsigned int xp = (arg_ulong_integer (2));
+    int signed_xp = (arg_integer (2));
+    unsigned int xp = ((signed_xp < 0) ? 0 : ((unsigned int) signed_xp));
     int bx = (xp - (XW_INTERNAL_BORDER_WIDTH (xw)));
     PRIMITIVE_RETURN
       (long_to_integer
@@ -435,7 +437,8 @@ DEFINE_PRIMITIVE ("XTERM-MAP-Y-COORDINATE", Prim_xterm_map_y_coordinate, 2, 2, 0
   PRIMITIVE_HEADER (2);
   {
     struct xwindow * xw = (x_window_arg (1));
-    unsigned int yp = (arg_ulong_integer (2));
+    int signed_yp = (arg_integer (2));
+    unsigned int yp = ((signed_yp < 0) ? 0 : ((unsigned int) signed_yp));
     int by = (yp - (XW_INTERNAL_BORDER_WIDTH (xw)));
     PRIMITIVE_RETURN
       (long_to_integer
-- 
2.25.1