Re: [AD] X11 locking

[ Thread Index | Date Index | More lists.liballeg.org/allegro-developers Archives ]


Evert Glebbeek wrote:
That's annoying. Both shwo up for me. I've tar.gzipped up my local tree (updated five minutes ago) and uploaded it at http://www.eglebbk.dds.nl/allegro-cvs-20040903.tar.gz

Thanks for that, but Peter gave me dev access. Attached is the patch that takes care of the discolored drawing, and attempts to keep the screen from being locked by multiple threads.

- Kitty Cat
Index: src/x/xvtable.c
===================================================================
RCS file: /cvsroot/alleg/allegro/src/x/xvtable.c,v
retrieving revision 1.13
diff -u -r1.13 xvtable.c
--- src/x/xvtable.c	30 Aug 2004 16:24:03 -0000	1.13
+++ src/x/xvtable.c	3 Sep 2004 10:29:32 -0000
@@ -20,6 +20,9 @@
 #include "allegro/platform/aintunix.h"
 #include "xwin.h"
 
+#ifdef ALLEGRO_MULTITHREADED
+#include <pthread.h>
+#endif
 
 
 static GFX_VTABLE _xwin_vtable;
@@ -51,15 +54,6 @@
 			      int dx, int dy, int w, int h);
 static void _xwin_clear_to_color(BITMAP *dst, int color);
 
-/* True if the GC is using the proper drawing mode */
-static int _xwin_drawmode_ok = TRUE;
-
-/* The drawing mode the current GC is actually in */
-static int _xwin_real_drawmode = GXcopy;
-
-/* A counter for the number of locks held on the X display */
-static int _xwin_lock_count = 0;
-
 
 
 /* _xwin_drawing_mode:
@@ -69,26 +63,26 @@
 {
    if (!_xwin.matching_formats) {
       if (_drawing_mode == DRAW_MODE_SOLID)
-	 _xwin_drawmode_ok = TRUE;
+	 _xwin.drawing_mode_ok = TRUE;
       else
-	 _xwin_drawmode_ok = FALSE;
+	 _xwin.drawing_mode_ok = FALSE;
 
-      _xwin_real_drawmode = GXcopy;
+      _xwin.real_drawing_mode = GXcopy;
       XSetState(_xwin.display, _xwin.gc, 0, 0, GXcopy, -1);
       return;
    }
 
-   _xwin_drawmode_ok = TRUE;
+   _xwin.drawing_mode_ok = TRUE;
    if(_drawing_mode == DRAW_MODE_SOLID)
-      _xwin_real_drawmode = GXcopy;
+      _xwin.real_drawing_mode = GXcopy;
    else if (_drawing_mode == DRAW_MODE_XOR)
-      _xwin_real_drawmode = GXxor;
+      _xwin.real_drawing_mode = GXxor;
    else {
-      _xwin_drawmode_ok = FALSE;
-      _xwin_real_drawmode = GXcopy;
+      _xwin.drawing_mode_ok = FALSE;
+      _xwin.real_drawing_mode = GXcopy;
    }
 
-   XSetState(_xwin.display, _xwin.gc, 0, 0, _xwin_real_drawmode, -1);
+   XSetState(_xwin.display, _xwin.gc, 0, 0, _xwin.real_drawing_mode, -1);
 }
 
 
@@ -133,14 +127,23 @@
 
 
 /* _xwin_lock:
- *  Lock X for drawing onto the display. Unlike XLOCK, this allows nested
- *  locks so be sure it's only called from one thread!
+ *  Lock X for drawing onto the display.
  */
 void _xwin_lock(BITMAP *bmp)
 {
-   if (_xwin_lock_count == 0)
+#ifdef ALLEGRO_MULTITHREADED
+   /* We want to force another mutex lock if another thread is trying to
+    * acquire the screen
+    */
+   if ((_xwin.screen_lock_count == 0) ||
+       (_xwin.locked_thread != pthread_self())) {
+#else
+   if (_xwin.screen_lock_count == 0) {
+#endif
       XLOCK();
-   _xwin_lock_count++;
+      _xwin.locked_thread = pthread_self();
+   }
+   _xwin.screen_lock_count++;
 }
 
 
@@ -151,8 +154,8 @@
  */
 void _xwin_unlock(BITMAP *bmp)
 {
-   _xwin_lock_count--;
-   if (_xwin_lock_count == 0)
+   _xwin.screen_lock_count--;
+   if (_xwin.screen_lock_count == 0)
       XUNLOCK();
 }
 
@@ -163,7 +166,13 @@
  */
 static void _xwin_update_video_bitmap(BITMAP *dst, int x, int y, int w, int h)
 {
+   if (_xwin.real_drawing_mode != GXcopy)
+      XSetState(_xwin.display, _xwin.gc, 0, 0, GXcopy, -1);
+
    _xwin_update_screen(x + dst->x_ofs, y + dst->y_ofs, w, h);
+
+   if (_xwin.real_drawing_mode != GXcopy)
+      XSetState(_xwin.display, _xwin.gc, 0, 0, _xwin.real_drawing_mode, -1);
 }
 
 
@@ -185,7 +194,7 @@
    _xwin_vtable.putpixel(dst, dx, dy, color);
    _xwin_in_gfx_call = 0;
 
-   if (_xwin.matching_formats && _xwin_drawmode_ok)
+   if (_xwin.matching_formats && _xwin.drawing_mode_ok)
    {
       dx += dst->x_ofs - _xwin.scroll_x;
       dy += dst->y_ofs - _xwin.scroll_y;
@@ -234,7 +243,7 @@
    _xwin_vtable.hline(dst, dx1, dy, dx2, color);
    _xwin_in_gfx_call = 0;
 
-   if (_xwin.matching_formats && _xwin_drawmode_ok) {
+   if (_xwin.matching_formats && _xwin.drawing_mode_ok) {
       dx1 += dst->x_ofs - _xwin.scroll_x;
       dx2 += dst->x_ofs - _xwin.scroll_x;
       dy += dst->y_ofs - _xwin.scroll_y;
@@ -286,7 +295,7 @@
    _xwin_vtable.vline(dst, dx, dy1, dy2, color);
    _xwin_in_gfx_call = 0;
 
-   if (_xwin.matching_formats && _xwin_drawmode_ok) {
+   if (_xwin.matching_formats && _xwin.drawing_mode_ok) {
       dx += dst->x_ofs - _xwin.scroll_x;
       dy1 += dst->y_ofs - _xwin.scroll_y;
       dy2 += dst->y_ofs - _xwin.scroll_y;
@@ -351,7 +360,7 @@
    _xwin_vtable.rectfill(dst, dx1, dy1, dx2, dy2, color);
    _xwin_in_gfx_call = 0;
 
-   if (_xwin.matching_formats && _xwin_drawmode_ok) {
+   if (_xwin.matching_formats && _xwin.drawing_mode_ok) {
       dx1 += dst->x_ofs - _xwin.scroll_x;
       dx2 += dst->x_ofs - _xwin.scroll_x;
       dy1 += dst->y_ofs - _xwin.scroll_y;
@@ -441,12 +450,7 @@
    _xwin_in_gfx_call = 1;
    _xwin_vtable.blit_from_memory(src, dst, sx, sy, dx, dy, w, h);
    _xwin_in_gfx_call = 0;
-
-   if (_xwin_real_drawmode != GXcopy)
-      XSetState(_xwin.display, _xwin.gc, 0, 0, GXcopy, -1);
    _xwin_update_video_bitmap(dst, dx, dy, w, h);
-   if (_xwin_real_drawmode != GXcopy)
-      XSetState(_xwin.display, _xwin.gc, 0, 0, _xwin_real_drawmode, -1);
 }
 
 
@@ -465,12 +469,7 @@
    _xwin_in_gfx_call = 1;
    _xwin_vtable.blit_to_self_backward(src, dst, sx, sy, dx, dy, w, h);
    _xwin_in_gfx_call = 0;
-
-   if (_xwin_real_drawmode != GXcopy)
-      XSetState(_xwin.display, _xwin.gc, 0, 0, GXcopy, -1);
    _xwin_update_video_bitmap(dst, dx, dy, w, h);
-   if (_xwin_real_drawmode != GXcopy)
-      XSetState(_xwin.display, _xwin.gc, 0, 0, _xwin_real_drawmode, -1);
 }
 
 
@@ -489,12 +488,7 @@
    _xwin_in_gfx_call = 1;
    _xwin_vtable.masked_blit(src, dst, sx, sy, dx, dy, w, h);
    _xwin_in_gfx_call = 0;
-
-   if (_xwin_real_drawmode != GXcopy)
-      XSetState(_xwin.display, _xwin.gc, 0, 0, GXcopy, -1);
    _xwin_update_video_bitmap(dst, dx, dy, w, h);
-   if (_xwin_real_drawmode != GXcopy)
-      XSetState(_xwin.display, _xwin.gc, 0, 0, _xwin_real_drawmode, -1);
 }
 
 
@@ -549,12 +543,7 @@
    _xwin_in_gfx_call = 1;
    _xwin_vtable.draw_sprite(dst, src, dx, dy);
    _xwin_in_gfx_call = 0;
-
-   if (_xwin_real_drawmode != GXcopy)
-      XSetState(_xwin.display, _xwin.gc, 0, 0, GXcopy, -1);
    _xwin_update_video_bitmap(dst, dxbeg, dybeg, w, h);
-   if (_xwin_real_drawmode != GXcopy)
-      XSetState(_xwin.display, _xwin.gc, 0, 0, _xwin_real_drawmode, -1);
 }
 
 
@@ -576,12 +565,7 @@
    _xwin_in_gfx_call = 1;
    _xwin_vtable.draw_256_sprite(dst, src, dx, dy);
    _xwin_in_gfx_call = 0;
-
-   if (_xwin_real_drawmode != GXcopy)
-      XSetState(_xwin.display, _xwin.gc, 0, 0, GXcopy, -1);
    _xwin_update_video_bitmap(dst, dxbeg, dybeg, w, h);
-   if (_xwin_real_drawmode != GXcopy)
-      XSetState(_xwin.display, _xwin.gc, 0, 0, _xwin_real_drawmode, -1);
 }
 
 
@@ -603,12 +587,7 @@
    _xwin_in_gfx_call = 1;
    _xwin_vtable.draw_sprite_v_flip(dst, src, dx, dy);
    _xwin_in_gfx_call = 0;
-
-   if (_xwin_real_drawmode != GXcopy)
-      XSetState(_xwin.display, _xwin.gc, 0, 0, GXcopy, -1);
    _xwin_update_video_bitmap(dst, dxbeg, dybeg, w, h);
-   if (_xwin_real_drawmode != GXcopy)
-      XSetState(_xwin.display, _xwin.gc, 0, 0, _xwin_real_drawmode, -1);
 }
 
 
@@ -630,12 +609,7 @@
    _xwin_in_gfx_call = 1;
    _xwin_vtable.draw_sprite_h_flip(dst, src, dx, dy);
    _xwin_in_gfx_call = 0;
-
-   if (_xwin_real_drawmode != GXcopy)
-      XSetState(_xwin.display, _xwin.gc, 0, 0, GXcopy, -1);
    _xwin_update_video_bitmap(dst, dxbeg, dybeg, w, h);
-   if (_xwin_real_drawmode != GXcopy)
-      XSetState(_xwin.display, _xwin.gc, 0, 0, _xwin_real_drawmode, -1);
 }
 
 
@@ -657,12 +631,7 @@
    _xwin_in_gfx_call = 1;
    _xwin_vtable.draw_sprite_vh_flip(dst, src, dx, dy);
    _xwin_in_gfx_call = 0;
-
-   if (_xwin_real_drawmode != GXcopy)
-      XSetState(_xwin.display, _xwin.gc, 0, 0, GXcopy, -1);
    _xwin_update_video_bitmap(dst, dxbeg, dybeg, w, h);
-   if (_xwin_real_drawmode != GXcopy)
-      XSetState(_xwin.display, _xwin.gc, 0, 0, _xwin_real_drawmode, -1);
 }
 
 
@@ -684,12 +653,7 @@
    _xwin_in_gfx_call = 1;
    _xwin_vtable.draw_trans_sprite(dst, src, dx, dy);
    _xwin_in_gfx_call = 0;
-
-   if (_xwin_real_drawmode != GXcopy)
-      XSetState(_xwin.display, _xwin.gc, 0, 0, GXcopy, -1);
    _xwin_update_video_bitmap(dst, dxbeg, dybeg, w, h);
-   if (_xwin_real_drawmode != GXcopy)
-      XSetState(_xwin.display, _xwin.gc, 0, 0, _xwin_real_drawmode, -1);
 }
 
 
@@ -711,12 +675,7 @@
    _xwin_in_gfx_call = 1;
    _xwin_vtable.draw_trans_rgba_sprite(dst, src, dx, dy);
    _xwin_in_gfx_call = 0;
-
-   if (_xwin_real_drawmode != GXcopy)
-      XSetState(_xwin.display, _xwin.gc, 0, 0, GXcopy, -1);
    _xwin_update_video_bitmap(dst, dxbeg, dybeg, w, h);
-   if (_xwin_real_drawmode != GXcopy)
-      XSetState(_xwin.display, _xwin.gc, 0, 0, _xwin_real_drawmode, -1);
 }
 
 
@@ -738,12 +697,7 @@
    _xwin_in_gfx_call = 1;
    _xwin_vtable.draw_lit_sprite(dst, src, dx, dy, color);
    _xwin_in_gfx_call = 0;
-
-   if (_xwin_real_drawmode != GXcopy)
-      XSetState(_xwin.display, _xwin.gc, 0, 0, GXcopy, -1);
    _xwin_update_video_bitmap(dst, dxbeg, dybeg, w, h);
-   if (_xwin_real_drawmode != GXcopy)
-      XSetState(_xwin.display, _xwin.gc, 0, 0, _xwin_real_drawmode, -1);
 }
 
 
@@ -765,12 +719,7 @@
    _xwin_in_gfx_call = 1;
    _xwin_vtable.draw_character(dst, src, dx, dy, color, bg);
    _xwin_in_gfx_call = 0;
-
-   if (_xwin_real_drawmode != GXcopy)
-      XSetState(_xwin.display, _xwin.gc, 0, 0, GXcopy, -1);
    _xwin_update_video_bitmap(dst, dxbeg, dybeg, w, h);
-   if (_xwin_real_drawmode != GXcopy)
-      XSetState(_xwin.display, _xwin.gc, 0, 0, _xwin_real_drawmode, -1);
 }
 
 
@@ -792,12 +741,7 @@
    _xwin_in_gfx_call = 1;
    _xwin_vtable.draw_glyph(dst, src, dx, dy, color, bg);
    _xwin_in_gfx_call = 0;
-
-   if (_xwin_real_drawmode != GXcopy)
-      XSetState(_xwin.display, _xwin.gc, 0, 0, GXcopy, -1);
    _xwin_update_video_bitmap(dst, dxbeg, dybeg, w, h);
-   if (_xwin_real_drawmode != GXcopy)
-      XSetState(_xwin.display, _xwin.gc, 0, 0, _xwin_real_drawmode, -1);
 }
 
 
@@ -819,12 +763,7 @@
    _xwin_in_gfx_call = 1;
    _xwin_vtable.draw_rle_sprite(dst, src, dx, dy);
    _xwin_in_gfx_call = 0;
-
-   if (_xwin_real_drawmode != GXcopy)
-      XSetState(_xwin.display, _xwin.gc, 0, 0, GXcopy, -1);
    _xwin_update_video_bitmap(dst, dxbeg, dybeg, w, h);
-   if (_xwin_real_drawmode != GXcopy)
-      XSetState(_xwin.display, _xwin.gc, 0, 0, _xwin_real_drawmode, -1);
 }
 
 
@@ -846,12 +785,7 @@
    _xwin_in_gfx_call = 1;
    _xwin_vtable.draw_trans_rle_sprite(dst, src, dx, dy);
    _xwin_in_gfx_call = 0;
-
-   if (_xwin_real_drawmode != GXcopy)
-      XSetState(_xwin.display, _xwin.gc, 0, 0, GXcopy, -1);
    _xwin_update_video_bitmap(dst, dxbeg, dybeg, w, h);
-   if (_xwin_real_drawmode != GXcopy)
-      XSetState(_xwin.display, _xwin.gc, 0, 0, _xwin_real_drawmode, -1);
 }
 
 
@@ -873,12 +807,7 @@
    _xwin_in_gfx_call = 1;
    _xwin_vtable.draw_trans_rgba_rle_sprite(dst, src, dx, dy);
    _xwin_in_gfx_call = 0;
-
-   if (_xwin_real_drawmode != GXcopy)
-      XSetState(_xwin.display, _xwin.gc, 0, 0, GXcopy, -1);
    _xwin_update_video_bitmap(dst, dxbeg, dybeg, w, h);
-   if (_xwin_real_drawmode != GXcopy)
-      XSetState(_xwin.display, _xwin.gc, 0, 0, _xwin_real_drawmode, -1);
 }
 
 
@@ -900,10 +829,5 @@
    _xwin_in_gfx_call = 1;
    _xwin_vtable.draw_lit_rle_sprite(dst, src, dx, dy, color);
    _xwin_in_gfx_call = 0;
-
-   if (_xwin_real_drawmode != GXcopy)
-      XSetState(_xwin.display, _xwin.gc, 0, 0, GXcopy, -1);
    _xwin_update_video_bitmap(dst, dxbeg, dybeg, w, h);
-   if (_xwin_real_drawmode != GXcopy)
-      XSetState(_xwin.display, _xwin.gc, 0, 0, _xwin_real_drawmode, -1);
 }
Index: src/x/xwin.c
===================================================================
RCS file: /cvsroot/alleg/allegro/src/x/xwin.c,v
retrieving revision 1.69
diff -u -r1.69 xwin.c
--- src/x/xwin.c	31 Aug 2004 07:29:29 -0000	1.69
+++ src/x/xwin.c	3 Sep 2004 10:29:33 -0000
@@ -136,6 +136,14 @@
    XWIN_DEFAULT_APPLICATION_NAME,       /* application_name */
    XWIN_DEFAULT_APPLICATION_CLASS,      /* application_class */
 
+   0,           /* screen_lock_count */
+   GXcopy,      /* real_drawing_mode */
+   TRUE,        /* drawing_mode_ok */
+
+#ifdef ALLEGRO_MULTITHREADED
+   (pthread_t)0, /* locked_thread */
+#endif
+
    NULL         /* window close hook */
 };
 
Index: include/xalleg.h
===================================================================
RCS file: /cvsroot/alleg/allegro/include/xalleg.h,v
retrieving revision 1.18
diff -u -r1.18 xalleg.h
--- include/xalleg.h	31 Aug 2004 07:29:28 -0000	1.18
+++ include/xalleg.h	3 Sep 2004 10:29:33 -0000
@@ -132,6 +132,14 @@
    char application_name[1024];
    char application_class[1024];
 
+   int screen_lock_count;
+   int real_drawing_mode;
+   int drawing_mode_ok;
+
+#ifdef ALLEGRO_MULTITHREADED
+   pthread_t locked_thread;
+#endif
+
    void (*close_button_callback)(void);
 } _xwin;
 


Mail converted by MHonArc 2.6.19+ http://listengine.tuxfamily.org/