Add xcb_xlib_lock and xcb_xlib_unlock, a special-purpose two-level recursive lock just for libX11.
This commit is contained in:
parent
57b0cd8fea
commit
40589db812
|
@ -59,6 +59,18 @@ static int set_fd_flags(const int fd)
|
|||
return 1;
|
||||
}
|
||||
|
||||
static int _xcb_xlib_init(_xcb_xlib *xlib)
|
||||
{
|
||||
xlib->lock = 0;
|
||||
pthread_cond_init(&xlib->cond, 0);
|
||||
return 1;
|
||||
}
|
||||
|
||||
static void _xcb_xlib_destroy(_xcb_xlib *xlib)
|
||||
{
|
||||
pthread_cond_destroy(&xlib->cond);
|
||||
}
|
||||
|
||||
static int write_setup(xcb_connection_t *c, xcb_auth_info_t *auth_info)
|
||||
{
|
||||
static const char pad[3];
|
||||
|
@ -215,6 +227,7 @@ xcb_connection_t *xcb_connect_to_fd(int fd, xcb_auth_info_t *auth_info)
|
|||
if(!(
|
||||
set_fd_flags(fd) &&
|
||||
pthread_mutex_init(&c->iolock, 0) == 0 &&
|
||||
_xcb_xlib_init(&c->xlib) &&
|
||||
_xcb_in_init(&c->in) &&
|
||||
_xcb_out_init(&c->out) &&
|
||||
write_setup(c, auth_info) &&
|
||||
|
@ -239,6 +252,7 @@ void xcb_disconnect(xcb_connection_t *c)
|
|||
close(c->fd);
|
||||
|
||||
pthread_mutex_destroy(&c->iolock);
|
||||
_xcb_xlib_destroy(&c->xlib);
|
||||
_xcb_in_destroy(&c->in);
|
||||
_xcb_out_destroy(&c->out);
|
||||
|
||||
|
@ -258,6 +272,12 @@ void _xcb_conn_shutdown(xcb_connection_t *c)
|
|||
void _xcb_lock_io(xcb_connection_t *c)
|
||||
{
|
||||
pthread_mutex_lock(&c->iolock);
|
||||
while(c->xlib.lock)
|
||||
{
|
||||
if(pthread_equal(c->xlib.thread, pthread_self()))
|
||||
break;
|
||||
pthread_cond_wait(&c->xlib.cond, &c->iolock);
|
||||
}
|
||||
}
|
||||
|
||||
void _xcb_unlock_io(xcb_connection_t *c)
|
||||
|
|
|
@ -26,6 +26,8 @@
|
|||
#include "xcbxlib.h"
|
||||
#include "xcbint.h"
|
||||
|
||||
#include <assert.h>
|
||||
|
||||
unsigned int xcb_get_request_sent(xcb_connection_t *c)
|
||||
{
|
||||
if(c->has_error)
|
||||
|
@ -39,3 +41,22 @@ pthread_mutex_t *xcb_get_io_lock(xcb_connection_t *c)
|
|||
return 0;
|
||||
return &c->iolock;
|
||||
}
|
||||
|
||||
void xcb_xlib_lock(xcb_connection_t *c)
|
||||
{
|
||||
_xcb_lock_io(c);
|
||||
assert(!c->xlib.lock);
|
||||
c->xlib.lock = 1;
|
||||
c->xlib.thread = pthread_self();
|
||||
_xcb_unlock_io(c);
|
||||
}
|
||||
|
||||
void xcb_xlib_unlock(xcb_connection_t *c)
|
||||
{
|
||||
_xcb_lock_io(c);
|
||||
assert(c->xlib.lock);
|
||||
assert(pthread_equal(c->xlib.thread, pthread_self()));
|
||||
c->xlib.lock = 0;
|
||||
pthread_cond_broadcast(&c->xlib.cond);
|
||||
_xcb_unlock_io(c);
|
||||
}
|
||||
|
|
18
src/xcbint.h
18
src/xcbint.h
|
@ -113,6 +113,15 @@ int _xcb_in_read(xcb_connection_t *c);
|
|||
int _xcb_in_read_block(xcb_connection_t *c, void *buf, int nread);
|
||||
|
||||
|
||||
/* xcb_xlib.c */
|
||||
|
||||
typedef struct _xcb_xlib {
|
||||
int lock;
|
||||
pthread_t thread;
|
||||
pthread_cond_t cond;
|
||||
} _xcb_xlib;
|
||||
|
||||
|
||||
/* xcb_xid.c */
|
||||
|
||||
typedef struct _xcb_xid {
|
||||
|
@ -150,6 +159,7 @@ struct xcb_connection_t {
|
|||
|
||||
/* I/O data */
|
||||
pthread_mutex_t iolock;
|
||||
_xcb_xlib xlib;
|
||||
_xcb_in in;
|
||||
_xcb_out out;
|
||||
|
||||
|
@ -159,8 +169,6 @@ struct xcb_connection_t {
|
|||
};
|
||||
|
||||
void _xcb_conn_shutdown(xcb_connection_t *c);
|
||||
void _xcb_lock_io(xcb_connection_t *c);
|
||||
void _xcb_unlock_io(xcb_connection_t *c);
|
||||
int _xcb_conn_wait(xcb_connection_t *c, pthread_cond_t *cond, struct iovec **vector, int *count);
|
||||
|
||||
|
||||
|
@ -172,4 +180,10 @@ int _xcb_get_auth_info(int fd, xcb_auth_info_t *info);
|
|||
#pragma GCC visibility pop
|
||||
#endif
|
||||
|
||||
|
||||
/* xcb_conn.c symbols visible to xcb-xlib */
|
||||
|
||||
void _xcb_lock_io(xcb_connection_t *c);
|
||||
void _xcb_unlock_io(xcb_connection_t *c);
|
||||
|
||||
#endif
|
||||
|
|
|
@ -36,4 +36,7 @@ unsigned int xcb_get_request_sent(xcb_connection_t *c);
|
|||
|
||||
pthread_mutex_t *xcb_get_io_lock(xcb_connection_t *c);
|
||||
|
||||
void xcb_xlib_lock(xcb_connection_t *c);
|
||||
void xcb_xlib_unlock(xcb_connection_t *c);
|
||||
|
||||
#endif
|
||||
|
|
Loading…
Reference in New Issue