[Date Prev][Date Next] [Thread Prev][Thread Next] [Date Index] [Thread Index]

Bug#511989: xserver-xorg-input-evtouch: more robust debugging system



Package: xserver-xorg-input-evtouch
Version: 0.8.7-3
Severity: wishlist
Tags: patch


This patch improves the debugging support in evtouch.

Major changes:
* Reimplementation of debug macros are less likely to cause unintended
  side effects (e.g. merging with adjacent statements, mismatched else's).
* debug_level controls all debugging.
* Globally changable reporting levels for features.
* More features instrumented.
* Live reporting mode for location information.

Quortech open source packages can be found at:
  ftp://ftp.quortech.com/eclipse/deb-packages/

This patch is included in xf86-input-evtouch_0.8.7-3quortech3.dsc.

-- System Information:
Debian Release: 4.0
  APT prefers stable
  APT policy: (500, 'stable')
Architecture: i386 (i686)
Shell:  /bin/sh linked to /bin/bash
Kernel: Linux 2.6.22-14-generic
Locale: LANG=en_CA.UTF-8, LC_CTYPE=en_CA.UTF-8 (charmap=UTF-8)
# Description: This patch improves the debugging support in evtouch.
#
# Changes
#   o Statements_M : Utility macro to make debugging macros simpler and
#     more robust.
#   o debug_level : Combine to single global provided by libtouch.c.
#   o DBG : Move to libtouch.h to be shared with evtouch.c.  Make more
#     robust.  Allow entire blocks of debugging statements to be skipped.
#   o DBGOUT : Move to evtouch.c, the only place it's currently used.
#   o DBGOUT : Local control through DebugLevel option of output.
#     Avoids uncontrolled output size in /var/log/Xorg.0.log with noisy
#     touch screen.  Encapsulate debugging statements that weren't using.
#   o DBGOUT : Make robust to surrounding statements.
#   o DBGXF86, DBGLOC : Globally changable reporting levels for features.
#   o DBGXF86 : Instrument tracing of xf86 calls.
#   o dbg_loc : Report location information as received and transmitted.
#   o DBGLOC_INLINE : Overwrites location information in place on ASCII
#     terminal.  Useful for live testing of accuracy of touch screen.
#   o EVTouchDumpPacketToLog : Reduce single usage to DBGOUT call.
#
# Feel free to send comments, critics, suggestions to wuth@acm.org
# To apply simply change into the toplevel directory of the source to be modified and enter:
# patch -p1 < <PATH_TO_PATCH>
# 
# All patches are available under the GNU GPL, I hope they might be useful for you (-:
# - Brett Wuth
#
Index: xf86-input-evtouch-0.8.7/evtouch.c
===================================================================
--- xf86-input-evtouch-0.8.7.orig/evtouch.c	2009-01-15 14:55:33.000000000 -0700
+++ xf86-input-evtouch-0.8.7/evtouch.c	2009-01-15 15:38:41.000000000 -0700
@@ -92,6 +92,14 @@
 #include "libtouch.h"
 #include "evtouch.h"
 
+/* The verbosity levels at which to output various */
+#define DBGXF86 (9) /* XF86 calls */
+#define DBGLOC  (1) /* location information */
+
+#define DBGLOC_INLINE (1) /* whether to display location information
+			   * on one line continously updated (1), or
+			   * on multiple lines (0) */
+
 /*****************************************************************************
  *        Variables without includable headers
  ****************************************************************************/
@@ -106,7 +114,17 @@
 static void
 EVTouchPtrCtrl(DeviceIntPtr device, PtrCtrl *ctrl);
 
-static int debug_level = 0;
+#ifdef EVDBG
+  /* Only output the debug statement if it meets *our* debug_level.
+   */
+#define DBGOUT(lvl, ...) DBG( (lvl), xf86ErrorFVerb( (lvl), __VA_ARGS__ ); )
+#else
+  /* Do nothing, but require the user to include trailing ";"
+   * so that syntax rules of normal statements are maintained.
+   * Compiler will optimize this statement away.
+   */
+#define DBGOUT(lvl, ...) Statements_M()
+#endif
 
 InputDriverRec EVTOUCH = {
         1,
@@ -150,9 +168,12 @@
       int *errmaj,
       int *errmin )
 {
-        xf86AddModuleInfo(&EVTouchInfo, module);
-        xf86AddInputDriver(&EVTOUCH, module, 0);
-        return module;
+  DBGOUT( DBGXF86, "EVTouch: xf86AddModuleInfo(&EVTouchInfo, module)\n" );
+  xf86AddModuleInfo(&EVTouchInfo, module);
+
+  DBGOUT( DBGXF86, "EVTouch: xf86AddInputDriver(&EVTOUCH, module, 0)\n" );
+  xf86AddInputDriver(&EVTOUCH, module, 0);
+  return module;
 }
 
 
@@ -201,6 +222,39 @@
  ****************************************************************************/
 
 
+/* Report the current location information as received and as sent on to X */
+static void
+dbg_loc( int *in_x,  /* the received X location, NULL if no change */
+	 int *in_y,  /* the received Y location, NULL if no change */
+	 int *out_x, /* the sent X location, NULL if no change */
+	 int *out_y  /* the sent Y location, NULL if no change */
+	 )
+{
+  static int last_in_x, last_in_y, last_out_x, last_out_y;
+
+  if (in_x) last_in_x = *in_x;
+  if (in_y) last_in_y = *in_y;
+  if (out_x) last_out_x = *out_x;
+  if (out_y) last_out_y = *out_y;
+
+  /* Print the current location as received and sent.
+   * Fields that have been updated are marked with a leading '*'.
+   */
+  DBGOUT( DBGLOC,
+	  "EVTouch in = (%c%5d, %c%5d), out = (%c%5d, %c%5d)%c",
+	  in_x ? '*' : ' ',
+	  last_in_x,
+	  in_y ? '*' : ' ',
+	  last_in_y,
+	  out_x ? '*' : ' ',
+	  last_out_x,
+	  out_y ? '*' : ' ',
+	  last_out_y,
+	  DBGLOC_INLINE ? '\r' : '\n'
+	  );
+}
+
+
 static CARD32
 emulate3Timer(OsTimerPtr timer, CARD32 now, pointer _local)
 {
@@ -212,7 +266,9 @@
         EVTouchPrivatePtr priv = (EVTouchPrivatePtr) local->private;
 
 
+	DBGOUT( DBGXF86, "EVTouch: xf86BlockSIGIO()\n" );
         sigstate = xf86BlockSIGIO();
+	DBGOUT( DBGXF86, "EVTouch: returned sigstate = %d\n", sigstate );
 
         PostMotionEvent(local);
 
@@ -240,6 +296,8 @@
         }
 
         priv->emulate3_timer_expired = TRUE;
+
+	DBGOUT( DBGXF86, "EVTouch: xf86UnblockSIGIO(sigstate=%d)\n", sigstate );
         xf86UnblockSIGIO(sigstate);
 
         return 0;
@@ -291,6 +349,8 @@
         ev = &priv->ev;
 
         if ( (ev->code == ABS_X) || (ev->code == ABS_Z) ) {
+	        dbg_loc( &ev->value, NULL, NULL, NULL );
+
  		if ((priv->cur_x - ev->value < priv->move_limit)
                         && (priv->cur_x - ev->value > -priv->move_limit))
                         return;
@@ -299,6 +359,8 @@
 	}
 
         if ( (ev->code == ABS_Y) || (ev->code == ABS_RX) ) {
+	        dbg_loc( NULL, &ev->value, NULL, NULL );
+
 		if ((priv->cur_y - ev->value < priv->move_limit)
                         && (priv->cur_y - ev->value > -priv->move_limit))
                         return;
@@ -469,7 +531,9 @@
         LocalDevicePtr local = (LocalDevicePtr) dev->public.devicePrivate;
         EVTouchPrivatePtr priv = (EVTouchPrivatePtr) (local->private);
 
+	DBGOUT( DBGXF86, "EVTouch: xf86OpenSerial(local->options)\n" );
         local->fd = xf86OpenSerial(local->options);
+	DBGOUT( DBGXF86, "EVTouch: returned local->fd = %d\n", local->fd );
 
         DBGOUT(2, "EVTouch: %s\n", __FUNCTION__ );
 
@@ -486,9 +550,10 @@
 
         if (!priv->buffer)
         {
-                xf86CloseSerial(local->fd);
-                local->fd = -1;
-                return (!Success);
+	  DBGOUT( DBGXF86, "EVTouch: xf86CloseSerial(local->fd=%d)\n", local->fd );
+	  xf86CloseSerial(local->fd);
+	  local->fd = -1;
+	  return (!Success);
         }
 
         if (QueryHardware(local) != Success)
@@ -497,6 +562,7 @@
                 return (!Success);
         }
 
+	DBGOUT( DBGXF86, "EVTouch: xf86FlushInput(local->fd=%d)\n", local->fd );
         xf86FlushInput(local->fd);
 
         if (ioctl(local->fd, EVIOCGRAB, (void *)1))
@@ -504,6 +570,7 @@
 
 
 #ifndef XFREE86_V4
+	DBGOUT( DBGXF86, "EVTouch: xf86AddEnabledDevice(local)\n" );
         xf86AddEnabledDevice(local);
 #else
         AddEnabledDevice(local->fd);
@@ -528,12 +595,14 @@
         if (local->fd != -1)
         {
                 ioctl(local->fd, EVIOCGRAB, (void *)0);
-                xf86RemoveEnabledDevice (local);
+		DBGOUT( DBGXF86, "EVTouch: xf86RemoveEnabledDevice(local)\n" );
+                xf86RemoveEnabledDevice(local);
                 if (priv->buffer)
                 {
                         XisbFree(priv->buffer);
                         priv->buffer = NULL;
                 }
+		DBGOUT( DBGXF86, "EVTouch: xf86CloseSerial(local->fd=%d)\n", local->fd );
                 xf86CloseSerial(local->fd);
                 local->fd = -1;
         }
@@ -605,6 +674,8 @@
         DBGOUT(2, "EVTouch: %s btn_count=%d\n", __FUNCTION__,
                priv->btn_count);
         priv->btn_actions = xcalloc(priv->btn_count, sizeof(BtnAction));
+
+	DBGOUT( DBGXF86, "EVTouch: xf86memset(...)\n" );
         xf86memset(priv->btn_actions, 0,
                    priv->btn_count * sizeof(BtnAction));
 
@@ -627,26 +698,40 @@
                 return !Success;
         }
 #if GET_ABI_MAJOR(ABI_XINPUT_VERSION) == 2
+	DBGOUT( DBGXF86, "EVTouch: xf86InitValuatorAxisStruct(...)\n" );
         xf86InitValuatorAxisStruct(dev, 0, 0, priv->screen_width,
                                    1024,
                                    EV_AXIS_MIN_RES /* min_res */ ,
                                    EV_AXIS_MAX_RES /* max_res */ );
+
+	DBGOUT( DBGXF86, "EVTouch: xf86InitValuatorDefaults(dev,0)\n" );
         xf86InitValuatorDefaults(dev, 0);
+
+	DBGOUT( DBGXF86, "EVTouch: xf86InitValuatorAxisStruct(...)\n" );
         xf86InitValuatorAxisStruct(dev, 1, 0, priv->screen_height,
                                    1024,
                                    EV_AXIS_MIN_RES /* min_res */ ,
                                    EV_AXIS_MAX_RES /* max_res */ );
+
+	DBGOUT( DBGXF86, "EVTouch: xf86InitValuatorDefaults(dev,1)\n" );
         xf86InitValuatorDefaults(dev, 1);
 #else
+	DBGOUT( DBGXF86, "EVTouch: xf86InitValuatorAxisStruct(...)\n" );
 	xf86InitValuatorAxisStruct(dev, 0, priv->min_x, priv->max_x,
                                    1024,
                                    EV_AXIS_MIN_RES /* min_res */ ,
                                    EV_AXIS_MAX_RES /* max_res */ );
+
+	DBGOUT( DBGXF86, "EVTouch: xf86InitValuatorDefaults(dev,0)\n" );
         xf86InitValuatorDefaults(dev, 0);
+
+	DBGOUT( DBGXF86, "EVTouch: xf86InitValuatorAxisStruct(...)\n" );
         xf86InitValuatorAxisStruct(dev, 1, priv->min_y, priv->max_y,
                                    1024,
                                    EV_AXIS_MIN_RES /* min_res */ ,
                                    EV_AXIS_MAX_RES /* max_res */ );
+
+	DBGOUT( DBGXF86, "EVTouch: xf86InitValuatorDefaults(dev,1)\n" );
         xf86InitValuatorDefaults(dev, 1);
 #endif
         /* Initial position of pointer on screen: Centered */
@@ -670,7 +755,8 @@
         /*
          * Allocate the motion events buffer.
          */
-        xf86MotionHistoryAllocate (local);
+	DBGOUT( DBGXF86, "EVTouch: xf86MotionHistoryAllocate(local)\n" );
+        xf86MotionHistoryAllocate(local);
         return (Success);
 }
 
@@ -708,9 +794,10 @@
 static void
 EVTouchNewPacket (EVTouchPrivatePtr priv)
 {
-        xf86memset(&priv->ev, 0, sizeof(struct input_event));
-        priv->packeti = 0;
-        priv->binary_pkt = FALSE;
+  DBGOUT( DBGXF86, "EVTouch: xf86memset(...)\n" );
+  xf86memset(&priv->ev, 0, sizeof(struct input_event));
+  priv->packeti = 0;
+  priv->binary_pkt = FALSE;
 }
 
 
@@ -736,7 +823,11 @@
 
                 if (sizeof(priv->ev) == count) {
                         count = 0;
-                        EVTouchDumpPacketToLog(priv);
+#ifdef LOG_RAW_PACKET
+			DBGOUT( 2,
+				"EVTOUCHPCKT type=0x%02x code=0x%02x value=0x%02x\n",
+				priv->ev.type, priv->ev.code, priv->ev.value );
+#endif
 
                         return Success;
                 }
@@ -876,9 +967,6 @@
         int xc = 0, yc = 0;
         int screen_width  = 0;
         int screen_height = 0;
-#ifdef EVDBG
-        int i = 0;
-#endif
 
         EVTouchPrivatePtr priv = (EVTouchPrivatePtr) (local->private);
 	ScrnInfoPtr pScrn = xf86Screens[priv->screen_num];
@@ -1003,14 +1091,20 @@
 
 
 #ifdef EVDBG
-                for (i=0; i<3; i++)
-                        xf86ErrorFVerb(2, "cx[%d]=%f   cy[%d]=%f\n", i, cx[i]
-                                       ,i, cy[i]);
-
-                DBGOUT(2, "EVTouch: ViewPort_X0=%d   ViewPort_Y0=%d\n",
-                    *(priv->pViewPort_X0),
-                    *(priv->pViewPort_Y0));
-                DBGOUT(2, "EVTouch: dx=%f   dy=%f\n", dx, dy);
+		DBG( 2,
+		     {
+		       int i = 0;
+		       for (i=0; i<3; i++)
+			 DBGOUT( 2,
+				 "cx[%d]=%f   cy[%d]=%f\n",
+				 i, cx[i], i, cy[i] );
+
+		       DBGOUT( 2,
+			       "EVTouch: ViewPort_X0=%d   ViewPort_Y0=%d\n",
+			       *(priv->pViewPort_X0),
+			       *(priv->pViewPort_Y0) );
+		       DBGOUT( 2, "EVTouch: dx=%f   dy=%f\n", dx, dy );
+		     } );
 #endif
 
                 xc = ( ((float)xc / max_x) * screen_width ) + dx;
@@ -1100,7 +1194,9 @@
         if (!priv)
                 return NULL;
 
+	DBGOUT( DBGXF86, "EVTouch: xf86AllocateInput(drv, 0)\n" );
         local = xf86AllocateInput(drv, 0);
+	DBGOUT( DBGXF86, "EVTouch: returned local=%p\n", local );
         if (!local) {
                 xfree(priv);
                 return NULL;
@@ -1123,15 +1219,18 @@
         local->flags = XI86_POINTER_CAPABLE | XI86_SEND_DRAG_EVENTS;
         local->conf_idev = dev;
 
+
+	DBGOUT( DBGXF86, "EVTouch: xf86CollectInputOptions(local, default_options, NULL)\n" );
         xf86CollectInputOptions(local, default_options, NULL);
 
+	DBGOUT( DBGXF86, "EVTouch: xf86OptionListReport(local->options)\n" );
         xf86OptionListReport(local->options);
 
 
 	priv->libtouch = xcalloc(1, sizeof(LibTouchRec));
 	libtouchInit(priv->libtouch, local,PostButtonEvent);
 
-        priv->screen_num    = xf86SetIntOption(local->options, "ScreenNumber", 0 );
+        priv->screen_num = xf86SetIntOption(local->options, "ScreenNumber", 0 );
 
         priv->calibrate = xf86SetIntOption(local->options, "Calibrate", 0);
 
@@ -1207,6 +1306,7 @@
         }
 
 #if GET_ABI_MAJOR(ABI_XINPUT_VERSION) == 0
+	DBGOUT( DBGXF86, "EVTouch: xf86AlwaysCore(local, TRUE)\n" );
         xf86AlwaysCore(local, TRUE);
 #endif
         priv->touch_flags = 0;
@@ -1222,14 +1322,17 @@
         if (priv->calibrate) {
                 priv->fifo = open("/tmp/ev_calibrate", O_RDWR, 0);
                 if (priv->fifo < 0)
-                        xf86ErrorFVerb(2, "open FIFO FAILED\n");
+		  DBGOUT( 2, "open FIFO FAILED\n" );
         }
 
         /* this results in an xstrdup that must be freed later */
         local->name = xf86SetStrOption( local->options, "DeviceName", "EVTouch TouchScreen" );
+
+	DBGOUT( DBGXF86, "EVTouch: xf86ProcessCommonOptions(local, local->options)\n" );
         xf86ProcessCommonOptions(local, local->options);
         local->flags |= XI86_CONFIGURED;
 
+	DBGOUT( DBGXF86, "EVTouch: xf86CloseSerial(local->fd = %d)\n", local->fd );
         xf86CloseSerial(local->fd);
         local->fd = -1;
 
@@ -1248,52 +1351,64 @@
 
 static void
 PostMotionEvent(LocalDevicePtr local) {
-int cur_x, cur_y;
-EVTouchPrivatePtr priv = (EVTouchPrivatePtr) (local->private);
+  int cur_x, cur_y;
+  EVTouchPrivatePtr priv = (EVTouchPrivatePtr) (local->private);
 
- cur_x = priv->cur_x;
- cur_y = priv->cur_y;
+  cur_x = priv->cur_x;
+  cur_y = priv->cur_y;
 #if GET_ABI_MAJOR(ABI_XINPUT_VERSION) == 2
- ConvertProc(local,0,2,priv->cur_x,priv->cur_y,0,0,0,0,&cur_x,&cur_y);
+  ConvertProc(local,0,2,priv->cur_x,priv->cur_y,0,0,0,0,&cur_x,&cur_y);
 #endif
 
-xf86PostMotionEvent (local->dev, TRUE, 0, 2, cur_x, cur_y);
+  dbg_loc( NULL, NULL, &cur_x, &cur_y );
+
+  DBGOUT( DBGXF86, "EVTouch: xf86PostMotionEvent (local->dev, TRUE, 0, 2, cur_x=%d, cur_y=%d)\n", cur_x, cur_y );
+  xf86PostMotionEvent (local->dev, TRUE, 0, 2, cur_x, cur_y);
 }
 
 static void
 PostProximityEvent(LocalDevicePtr local, int is_in) {
-int cur_x, cur_y;
-EVTouchPrivatePtr priv = (EVTouchPrivatePtr) (local->private);
+  int cur_x, cur_y;
+  EVTouchPrivatePtr priv = (EVTouchPrivatePtr) (local->private);
 
- cur_x = priv->cur_x;
- cur_y = priv->cur_y;
+  cur_x = priv->cur_x;
+  cur_y = priv->cur_y;
 #if GET_ABI_MAJOR(ABI_XINPUT_VERSION) == 2
- ConvertProc(local,0,2,priv->cur_x,priv->cur_y,0,0,0,0,&cur_x,&cur_y);
+  ConvertProc(local,0,2,priv->cur_x,priv->cur_y,0,0,0,0,&cur_x,&cur_y);
 #endif
 
-xf86PostProximityEvent(local->dev, is_in, 0, 2, cur_x,cur_y);
+  dbg_loc( NULL, NULL, &cur_x, &cur_y );
+
+  DBGOUT( DBGXF86, "EVTouch: xf86PostProximityEvent(local->dev, is_in=%d, 0, 2, cur_x=%d,cur_y=%d)\n", is_in, cur_x, cur_y );
+  xf86PostProximityEvent(local->dev, is_in, 0, 2, cur_x,cur_y);
 }
 
 static void
 PostButtonEvent(LocalDevicePtr local, int button, int is_down,int x, int y) {
 #if GET_ABI_MAJOR(ABI_XINPUT_VERSION) == 2
- ConvertProc(local,0,2,x,y,0,0,0,0,&x,&y);
+  ConvertProc(local,0,2,x,y,0,0,0,0,&x,&y);
 #endif
 
-xf86PostButtonEvent (local->dev, TRUE, button, is_down, 0, 2, x, y);
+  dbg_loc( NULL, NULL, &x, &y );
+
+  DBGOUT( DBGXF86, "EVTouch: xf86PostButtonEvent( local->dev, TRUE, button = %d, is_down = %d, 0, 2, x = %d, y = %d )\n", button, is_down, x, y );
+  xf86PostButtonEvent( local->dev, TRUE, button, is_down, 0, 2, x, y );
 }
 
 
 static void InputSetScreen(LocalDevicePtr local) {
-int cur_x, cur_y;
-EVTouchPrivatePtr priv = (EVTouchPrivatePtr) (local->private);
+  int cur_x, cur_y;
+  EVTouchPrivatePtr priv = (EVTouchPrivatePtr) (local->private);
 
- cur_x = priv->cur_x;
- cur_y = priv->cur_y;
+  cur_x = priv->cur_x;
+  cur_y = priv->cur_y;
 #if GET_ABI_MAJOR(ABI_XINPUT_VERSION) == 2
- ConvertProc(local,0,2,priv->cur_x,priv->cur_y,0,0,0,0,&cur_x,&cur_y);
+  ConvertProc(local,0,2,priv->cur_x,priv->cur_y,0,0,0,0,&cur_x,&cur_y);
 #endif
 
-xf86XInputSetScreen(local,priv->screen_num,cur_x,cur_y);
+  dbg_loc( NULL, NULL, &cur_x, &cur_y );
+
+  DBGOUT( DBGXF86, "EVTouch: xf86XInputSetScreen(local,priv->screen_num=%d,cur_x=%d,cur_y=%d)\n", priv->screen_num, cur_x, cur_y );
+  xf86XInputSetScreen(local,priv->screen_num,cur_x,cur_y);
 }
 
Index: xf86-input-evtouch-0.8.7/evtouch.h
===================================================================
--- xf86-input-evtouch-0.8.7.orig/evtouch.h	2009-01-15 14:55:33.000000000 -0700
+++ xf86-input-evtouch-0.8.7/evtouch.h	2009-01-15 15:37:31.000000000 -0700
@@ -29,12 +29,6 @@
 #define _evtouch_H_
 
 
-#ifdef EVDBG
-#define DBGOUT(lvl, ...) (xf86ErrorFVerb(lvl, __VA_ARGS__))
-#else 
-#define DBGOUT(lvl, ...)
-#endif
-
 /******************************************************************************
  *  Definitions
  *  structs, typedefs, #defines, enums
@@ -148,12 +142,6 @@
  *  Declarations
  *****************************************************************************/
 
-#ifdef LOG_RAW_PACKET
-#define EVTouchDumpPacketToLog(priv) ( xf86ErrorFVerb(2, "EVTOUCHPCKT type=0x%02x code=0x%02x value=0x%02x\n",                                       priv->ev.type, priv->ev.code, priv->ev.value ) )
-#else
-#define EVTouchDumpPacketToLog(priv)
-#endif
-
 void trigger_sm(EVTouchPrivatePtr priv);
 
 /* 
Index: xf86-input-evtouch-0.8.7/libtouch.c
===================================================================
--- xf86-input-evtouch-0.8.7.orig/libtouch.c	2009-01-15 14:55:33.000000000 -0700
+++ xf86-input-evtouch-0.8.7/libtouch.c	2009-01-15 15:23:07.000000000 -0700
@@ -40,12 +40,8 @@
 
 #include "libtouch.h"
 
-#ifdef DBG
-#undef DBG
-#endif
-
-static int debug_level = 0;
-#define DBG(lvl, f) {if ((lvl) <= debug_level) f;}
+/* Maximum level of debug information to be displayed */
+extern int debug_level = 0;
 
 typedef struct state {
         void (*enter_state)(LibTouchRecPtr priv);
Index: xf86-input-evtouch-0.8.7/libtouch.h
===================================================================
--- xf86-input-evtouch-0.8.7.orig/libtouch.h	2009-01-15 14:55:33.000000000 -0700
+++ xf86-input-evtouch-0.8.7/libtouch.h	2009-01-15 15:23:07.000000000 -0700
@@ -3,6 +3,103 @@
 #include <xf86_ansic.h>
 #include <os.h>
 
+/* Macro to allow arbitrary statements to be executed as a single
+ * statement.  This is a helper macro creating other macros.  This
+ * macro must be followed by a ";" (like any other statement) and will
+ * accept only a ";" as the next character.  Embedded Stmts must each
+ * be properly terminated.  E.g.:
+ *
+ *   Statements_M();
+ *   Statements_M( foo(); bar(); );
+ *   Statements_M( if (foo) bar(); );
+ *   Statements_M( {
+ *                 int foo;
+ *                 bar( &foo );
+ *                 } );
+ *   Statements_M( if (foo)
+ *                   break;
+ *                 if (bar)
+ *                   continue;
+ *               );
+ *
+ *
+ * Warnings:
+ *
+ * Because the implementation use an if/else construct, if the caller
+ * uses something like:
+ *
+ *   if (foo) Statements_M( ... );
+ *
+ * some compilers will "helpfully" produce a warning like:
+ *
+ *   warning: suggest explicit braces to avoid ambiguous 'else'
+ *
+ * For this macro, the warning is inappropriate and can be ignored.
+ * To avoid the warning, rewrite the code as:
+ *
+ *   if (foo) { Statements_M( ... ); }
+ *
+ * FIXME: Investigate compiler-specific pragmas/markup to turn off
+ * just for this macro.
+ *
+ *
+ * Implementation:
+ *
+ * Squiggly brackets "{ ... }" handle arbitrary statements.
+ *
+ * "do ... while (0)" is optimized away but syntactically can only be
+ * followed by a ";".  Other solutions could accidentally merge
+ * following statements if the ";" was forgotten by the caller.
+ *
+ * "if (1) ... else ..." composes the whole thing as a single
+ * statement.  A following "else" won't match our "if", because it's
+ * already been matched.  Embedded break and continue statements are
+ * allowed.  The compiler will optimize the if statement away.
+ */
+#define Statements_M( Stmts ) \
+  if (1) { Stmts } else do ; while (0)
+
+
+/* Maximum level of debug information to be displayed */
+extern int debug_level;
+
+/* Only execute the debug statement(s) if it meets our debug_level.
+ *
+ * The ";" after the statement is optional, as has been the convention
+ * in earlier implementations of this macro. E.g.:
+ *
+ *    DBG( 1, bar() );
+ *
+ * More complex statements are also possible.  E.g.:
+ *
+ *    DBG( 1, bar(); );
+ *    DBG( 1, bar(); baz(); );
+ *    DBG( 1, while (foo) baz(); );
+ *    DBG( 1, {
+ *              int i;
+ *              for (i = 0; i < foo; i++)
+ *                bar();
+ *            } );
+ *
+ *
+ * Implementation:
+ *
+ * The ";" after the "f" makes including a ";" optional.
+ *
+ * "{ ... }" avoids: "warning: suggest explicit braces to avoid
+ * ambiguous 'else'"
+ */
+#ifdef DBG
+#undef DBG
+#endif
+#define DBG( lvl, f ) \
+  Statements_M( if ((lvl) <= debug_level) \
+		  { \
+		    Statements_M( f; ); \
+		  } \
+		)
+
+
 #define TOUCHED 0x01
 #define X_COORD 0x02
 #define Y_COORD 0x04

Reply to: