Merge remote-tracking branch 'jeremyhu/master'
This commit is contained in:
commit
918a9c99cf
10
configure.ac
10
configure.ac
|
@ -725,9 +725,9 @@ case $host_os in
|
|||
save_LDFLAGS=$LDFLAGS
|
||||
LDFLAGS="$LDFLAGS -framework Carbon"
|
||||
AC_LINK_IFELSE([char FSFindFolder(); int main() { FSFindFolder(); return 0;}],
|
||||
[xorg_cv_Carbon_framework=yes],
|
||||
[xorg_cv_Carbon_framework=no])
|
||||
LDFLAGS=$save_LDFLAGS])
|
||||
[xorg_cv_Carbon_framework=yes],
|
||||
[xorg_cv_Carbon_framework=no])
|
||||
LDFLAGS=$save_LDFLAGS])
|
||||
|
||||
if test "X$xorg_cv_Carbon_framework" = Xyes; then
|
||||
XQUARTZ=yes
|
||||
|
@ -736,6 +736,10 @@ case $host_os in
|
|||
fi
|
||||
fi
|
||||
|
||||
AC_CHECK_FUNC(dispatch_async,
|
||||
AC_DEFINE([HAVE_LIBDISPATCH], 1, [Define to 1 if you have the libdispatch (GCD) available]),
|
||||
[])
|
||||
|
||||
if test "x$XQUARTZ" = xyes ; then
|
||||
XQUARTZ=yes
|
||||
XVFB=no
|
||||
|
|
|
@ -61,6 +61,12 @@ extern int xpbproxy_run (void);
|
|||
#define XSERVER_VERSION "?"
|
||||
#endif
|
||||
|
||||
#ifdef HAVE_LIBDISPATCH
|
||||
#include <dispatch/dispatch.h>
|
||||
|
||||
static dispatch_queue_t eventTranslationQueue;
|
||||
#endif
|
||||
|
||||
/* Stuck modifier / button state... force release when we context switch */
|
||||
static NSEventType keyState[NUM_KEYCODES];
|
||||
|
||||
|
@ -385,7 +391,15 @@ static void message_kit_thread (SEL selector, NSObject *arg) {
|
|||
|
||||
if (for_appkit) [super sendEvent:e];
|
||||
|
||||
if (for_x) [self sendX11NSEvent:e];
|
||||
if (for_x) {
|
||||
#ifdef HAVE_LIBDISPATCH
|
||||
dispatch_async(eventTranslationQueue, ^{
|
||||
#endif
|
||||
[self sendX11NSEvent:e];
|
||||
#ifdef HAVE_LIBDISPATCH
|
||||
});
|
||||
#endif
|
||||
}
|
||||
}
|
||||
|
||||
- (void) set_window_menu:(NSArray *)list {
|
||||
|
@ -950,7 +964,7 @@ environment the next time you start X11?", @"Startup xinitrc dialog");
|
|||
[X11App prefs_synchronize];
|
||||
}
|
||||
|
||||
static inline pthread_t create_thread(void *func, void *arg) {
|
||||
static inline pthread_t create_thread(void *(*func)(void *), void *arg) {
|
||||
pthread_attr_t attr;
|
||||
pthread_t tid;
|
||||
|
||||
|
@ -999,6 +1013,11 @@ void X11ApplicationMain (int argc, char **argv, char **envp) {
|
|||
aquaMenuBarHeight = NSHeight([[NSScreen mainScreen] frame]) -
|
||||
NSMaxY([[NSScreen mainScreen] visibleFrame]);
|
||||
|
||||
#ifdef HAVE_LIBDISPATCH
|
||||
eventTranslationQueue = dispatch_queue_create(LAUNCHD_ID_PREFIX".X11.NSEventsToX11EventsQueue", NULL);
|
||||
assert(eventTranslationQueue != NULL);
|
||||
#endif
|
||||
|
||||
/* Set the key layout seed before we start the server */
|
||||
#if MAC_OS_X_VERSION_MIN_REQUIRED >= 1050
|
||||
last_key_layout = TISCopyCurrentKeyboardLayoutInputSource();
|
||||
|
@ -1079,13 +1098,29 @@ static const char *untrusted_str(NSEvent *e) {
|
|||
#endif
|
||||
|
||||
- (void) sendX11NSEvent:(NSEvent *)e {
|
||||
NSPoint location = NSZeroPoint, tilt = NSZeroPoint;
|
||||
NSPoint location = NSZeroPoint;
|
||||
int ev_button, ev_type;
|
||||
float pressure = 0.0;
|
||||
static float pressure = 0.0; // static so ProximityOut will have the value from the previous tablet event
|
||||
static NSPoint tilt; // static so ProximityOut will have the value from the previous tablet event
|
||||
static DeviceIntPtr darwinTabletCurrent = NULL;
|
||||
static BOOL needsProximityIn = NO; // Do we do need to handle a pending ProximityIn once we have pressure/tilt?
|
||||
DeviceIntPtr pDev;
|
||||
int modifierFlags;
|
||||
BOOL isMouseOrTabletEvent, isTabletEvent;
|
||||
|
||||
#ifdef HAVE_LIBDISPATCH
|
||||
static dispatch_once_t once_pred;
|
||||
dispatch_once(&once_pred, ^{
|
||||
tilt = NSZeroPoint;
|
||||
darwinTabletCurrent = darwinTabletStylus;
|
||||
});
|
||||
#else
|
||||
if(!darwinTabletCurrent) {
|
||||
tilt = NSZeroPoint;
|
||||
darwinTabletCurrent = darwinTabletStylus;
|
||||
}
|
||||
#endif
|
||||
|
||||
isMouseOrTabletEvent = [e type] == NSLeftMouseDown || [e type] == NSOtherMouseDown || [e type] == NSRightMouseDown ||
|
||||
[e type] == NSLeftMouseUp || [e type] == NSOtherMouseUp || [e type] == NSRightMouseUp ||
|
||||
[e type] == NSLeftMouseDragged || [e type] == NSOtherMouseDragged || [e type] == NSRightMouseDragged ||
|
||||
|
@ -1207,19 +1242,14 @@ static const char *untrusted_str(NSEvent *e) {
|
|||
darwinTabletCurrent=darwinTabletCursor;
|
||||
break;
|
||||
}
|
||||
|
||||
/* NSTabletProximityEventSubtype doesn't encode pressure ant tilt
|
||||
* So we just pretend the motion was caused by the mouse. Hopefully
|
||||
* we'll have a better solution for this in the future (like maybe
|
||||
* NSTabletProximityEventSubtype will come from NSTabletPoint
|
||||
* rather than NSMouseMoved.
|
||||
pressure = [e pressure];
|
||||
tilt = [e tilt];
|
||||
pDev = darwinTabletCurrent;
|
||||
*/
|
||||
|
||||
DarwinSendProximityEvents([e isEnteringProximity] ? ProximityIn : ProximityOut,
|
||||
location.x, location.y);
|
||||
if([e isEnteringProximity])
|
||||
needsProximityIn = YES;
|
||||
else
|
||||
DarwinSendProximityEvents(darwinTabletCurrent, ProximityOut,
|
||||
location.x, location.y, pressure,
|
||||
tilt.x, tilt.y);
|
||||
return;
|
||||
}
|
||||
|
||||
if ([e type] == NSTabletPoint || [e subtype] == NSTabletPointEventSubtype) {
|
||||
|
@ -1227,6 +1257,14 @@ static const char *untrusted_str(NSEvent *e) {
|
|||
tilt = [e tilt];
|
||||
|
||||
pDev = darwinTabletCurrent;
|
||||
|
||||
if(needsProximityIn) {
|
||||
DarwinSendProximityEvents(darwinTabletCurrent, ProximityIn,
|
||||
location.x, location.y, pressure,
|
||||
tilt.x, tilt.y);
|
||||
|
||||
needsProximityIn = NO;
|
||||
}
|
||||
}
|
||||
|
||||
if(!XQuartzServerVisible && noTestExtensions) {
|
||||
|
@ -1280,8 +1318,12 @@ static const char *untrusted_str(NSEvent *e) {
|
|||
break;
|
||||
}
|
||||
|
||||
DarwinSendProximityEvents([e isEnteringProximity] ? ProximityIn : ProximityOut,
|
||||
location.x, location.y);
|
||||
if([e isEnteringProximity])
|
||||
needsProximityIn = YES;
|
||||
else
|
||||
DarwinSendProximityEvents(darwinTabletCurrent, ProximityOut,
|
||||
location.x, location.y, pressure,
|
||||
tilt.x, tilt.y);
|
||||
break;
|
||||
|
||||
case NSScrollWheel:
|
||||
|
|
|
@ -117,7 +117,6 @@ unsigned int windowItemModMask = NX_COMMANDMASK;
|
|||
// devices
|
||||
DeviceIntPtr darwinKeyboard = NULL;
|
||||
DeviceIntPtr darwinPointer = NULL;
|
||||
DeviceIntPtr darwinTabletCurrent = NULL;
|
||||
DeviceIntPtr darwinTabletStylus = NULL;
|
||||
DeviceIntPtr darwinTabletCursor = NULL;
|
||||
DeviceIntPtr darwinTabletEraser = NULL;
|
||||
|
@ -492,8 +491,6 @@ void InitInput( int argc, char **argv )
|
|||
darwinTabletEraser = AddInputDevice(serverClient, DarwinTabletProc, TRUE);
|
||||
darwinTabletEraser->name = strdup("eraser");
|
||||
|
||||
darwinTabletCurrent = darwinTabletStylus;
|
||||
|
||||
DarwinEQInit();
|
||||
|
||||
QuartzInitInput(argc, argv);
|
||||
|
|
|
@ -56,7 +56,6 @@ extern io_connect_t darwinParamConnect;
|
|||
extern int darwinEventReadFD;
|
||||
extern int darwinEventWriteFD;
|
||||
extern DeviceIntPtr darwinPointer;
|
||||
extern DeviceIntPtr darwinTabletCurrent;
|
||||
extern DeviceIntPtr darwinTabletCursor;
|
||||
extern DeviceIntPtr darwinTabletStylus;
|
||||
extern DeviceIntPtr darwinTabletEraser;
|
||||
|
|
|
@ -61,6 +61,7 @@ in this Software without prior written authorization from The Open Group.
|
|||
#include <unistd.h>
|
||||
#include <pthread.h>
|
||||
#include <errno.h>
|
||||
#include <time.h>
|
||||
|
||||
#include <IOKit/hidsystem/IOLLEvent.h>
|
||||
|
||||
|
@ -93,7 +94,7 @@ static pthread_mutex_t mieq_lock = PTHREAD_MUTEX_INITIALIZER;
|
|||
static pthread_cond_t mieq_ready_cond = PTHREAD_COND_INITIALIZER;
|
||||
|
||||
/*** Pthread Magics ***/
|
||||
static pthread_t create_thread(void *func, void *arg) {
|
||||
static pthread_t create_thread(void *(*func)(void *), void *arg) {
|
||||
pthread_attr_t attr;
|
||||
pthread_t tid;
|
||||
|
||||
|
@ -304,7 +305,28 @@ void DarwinListenOnOpenFD(int fd) {
|
|||
pthread_mutex_unlock(&fd_add_lock);
|
||||
}
|
||||
|
||||
static void DarwinProcessFDAdditionQueue_thread(void *args) {
|
||||
static void *DarwinProcessFDAdditionQueue_thread(void *args) {
|
||||
/* TODO: Possibly adjust this to no longer be a race... maybe trigger this
|
||||
* once a client connects and claims to be the WM.
|
||||
*
|
||||
* From ajax:
|
||||
* There's already an internal callback chain for setting selection [in 1.5]
|
||||
* ownership. See the CallSelectionCallback at the bottom of
|
||||
* ProcSetSelectionOwner, and xfixes/select.c for an example of how to hook
|
||||
* into it.
|
||||
*/
|
||||
|
||||
struct timespec sleep_for;
|
||||
struct timespec sleep_remaining;
|
||||
|
||||
sleep_for.tv_sec = 3;
|
||||
sleep_for.tv_nsec = 0;
|
||||
|
||||
ErrorF("X11.app: DarwinProcessFDAdditionQueue_thread: Sleeping to allow xinitrc to catchup.\n");
|
||||
while(nanosleep(&sleep_for, &sleep_remaining) != 0) {
|
||||
sleep_for = sleep_remaining;
|
||||
}
|
||||
|
||||
pthread_mutex_lock(&fd_add_lock);
|
||||
while(true) {
|
||||
while(fd_add_count) {
|
||||
|
@ -312,6 +334,8 @@ static void DarwinProcessFDAdditionQueue_thread(void *args) {
|
|||
}
|
||||
pthread_cond_wait(&fd_add_ready_cond, &fd_add_lock);
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
Bool DarwinEQInit(void) {
|
||||
|
@ -465,7 +489,7 @@ void DarwinSendPointerEvents(DeviceIntPtr pDev, int ev_type, int ev_button, floa
|
|||
DarwinPrepareValuators(pDev, valuators, screen, pointer_x, pointer_y, pressure, tilt_x, tilt_y);
|
||||
darwinEvents_lock(); {
|
||||
ValuatorMask mask;
|
||||
valuator_mask_set_range(&mask, 0, (pDev == darwinTabletCurrent) ? 5 : 2, valuators);
|
||||
valuator_mask_set_range(&mask, 0, (pDev == darwinPointer) ? 2 : 5, valuators);
|
||||
num_events = GetPointerEvents(darwinEvents, pDev, ev_type, ev_button,
|
||||
POINTER_ABSOLUTE, &mask);
|
||||
for(i=0; i<num_events; i++) mieqEnqueue (pDev, (InternalEvent*)darwinEvents[i].event);
|
||||
|
@ -488,18 +512,18 @@ void DarwinSendKeyboardEvents(int ev_type, int keycode) {
|
|||
} darwinEvents_unlock();
|
||||
}
|
||||
|
||||
void DarwinSendProximityEvents(int ev_type, float pointer_x, float pointer_y) {
|
||||
int i, num_events;
|
||||
void DarwinSendProximityEvents(DeviceIntPtr pDev, int ev_type, float pointer_x, float pointer_y,
|
||||
float pressure, float tilt_x, float tilt_y) {
|
||||
int i, num_events;
|
||||
ScreenPtr screen;
|
||||
DeviceIntPtr pDev = darwinTabletCurrent;
|
||||
int valuators[5];
|
||||
|
||||
DEBUG_LOG("DarwinSendProximityEvents(%d, %f, %f)\n", ev_type, pointer_x, pointer_y);
|
||||
DEBUG_LOG("DarwinSendProximityEvents: %d l:%f,%f p:%f t:%f,%f\n", ev_type, pointer_x, pointer_y, pressure, tilt_x, tilt_y);
|
||||
|
||||
if(!darwinEvents) {
|
||||
DEBUG_LOG("DarwinSendProximityEvents called before darwinEvents was initialized\n");
|
||||
return;
|
||||
}
|
||||
if(!darwinEvents) {
|
||||
DEBUG_LOG("DarwinSendProximityEvents called before darwinEvents was initialized\n");
|
||||
return;
|
||||
}
|
||||
|
||||
screen = miPointerGetScreen(pDev);
|
||||
if(!screen) {
|
||||
|
@ -507,7 +531,7 @@ void DarwinSendProximityEvents(int ev_type, float pointer_x, float pointer_y) {
|
|||
return;
|
||||
}
|
||||
|
||||
DarwinPrepareValuators(pDev, valuators, screen, pointer_x, pointer_y, 0.0f, 0.0f, 0.0f);
|
||||
DarwinPrepareValuators(pDev, valuators, screen, pointer_x, pointer_y, pressure, tilt_x, tilt_y);
|
||||
darwinEvents_lock(); {
|
||||
ValuatorMask mask;
|
||||
valuator_mask_set_range(&mask, 0, 5, valuators);
|
||||
|
|
|
@ -37,7 +37,8 @@ void DarwinEQPointerPost(DeviceIntPtr pDev, xEventPtr e);
|
|||
void DarwinEQSwitchScreen(ScreenPtr pScreen, Bool fromDIX);
|
||||
void DarwinSendPointerEvents(DeviceIntPtr pDev, int ev_type, int ev_button, float pointer_x, float pointer_y,
|
||||
float pressure, float tilt_x, float tilt_y);
|
||||
void DarwinSendProximityEvents(int ev_type, float pointer_x, float pointer_y);
|
||||
void DarwinSendProximityEvents(DeviceIntPtr pDev, int ev_type, float pointer_x, float pointer_y,
|
||||
float pressure, float tilt_x, float tilt_y);
|
||||
void DarwinSendKeyboardEvents(int ev_type, int keycode);
|
||||
void DarwinSendScrollEvents(float count_x, float count_y, float pointer_x, float pointer_y,
|
||||
float pressure, float tilt_x, float tilt_y);
|
||||
|
|
|
@ -40,14 +40,18 @@
|
|||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <stdlib.h>
|
||||
#include <pthread.h>
|
||||
#include <stdbool.h>
|
||||
#include <signal.h>
|
||||
|
||||
#ifdef HAVE_LIBDISPATCH
|
||||
#include <dispatch/dispatch.h>
|
||||
#else
|
||||
#include <pthread.h>
|
||||
#endif
|
||||
|
||||
#include <sys/socket.h>
|
||||
#include <sys/un.h>
|
||||
|
||||
#include <sys/time.h>
|
||||
#include <fcntl.h>
|
||||
|
||||
#include <mach/mach.h>
|
||||
|
@ -95,8 +99,9 @@ int server_main(int argc, char **argv, char **envp);
|
|||
static int execute(const char *command);
|
||||
static char *command_from_prefs(const char *key, const char *default_value);
|
||||
|
||||
#ifndef HAVE_LIBDISPATCH
|
||||
/*** Pthread Magics ***/
|
||||
static pthread_t create_thread(void *func, void *arg) {
|
||||
static pthread_t create_thread(void *(*func)(void *), void *arg) {
|
||||
pthread_attr_t attr;
|
||||
pthread_t tid;
|
||||
|
||||
|
@ -108,6 +113,7 @@ static pthread_t create_thread(void *func, void *arg) {
|
|||
|
||||
return tid;
|
||||
}
|
||||
#endif
|
||||
|
||||
/*** Mach-O IPC Stuffs ***/
|
||||
|
||||
|
@ -200,11 +206,15 @@ typedef struct {
|
|||
/* This thread accepts an incoming connection and hands off the file
|
||||
* descriptor for the new connection to accept_fd_handoff()
|
||||
*/
|
||||
static void socket_handoff_thread(void *arg) {
|
||||
#ifdef HAVE_LIBDISPATCH
|
||||
static void socket_handoff(socket_handoff_t *handoff_data) {
|
||||
#else
|
||||
static void *socket_handoff_thread(void *arg) {
|
||||
socket_handoff_t *handoff_data = (socket_handoff_t *)arg;
|
||||
#endif
|
||||
|
||||
int launchd_fd = -1;
|
||||
int connected_fd;
|
||||
unsigned remain;
|
||||
|
||||
/* Now actually get the passed file descriptor from this connection
|
||||
* If we encounter an error, keep listening.
|
||||
|
@ -227,22 +237,13 @@ static void socket_handoff_thread(void *arg) {
|
|||
close(handoff_data->fd);
|
||||
unlink(handoff_data->filename);
|
||||
free(handoff_data);
|
||||
|
||||
/* TODO: Clean up this race better... giving xinitrc time to run... need to wait for 1.5 branch:
|
||||
*
|
||||
* From ajax:
|
||||
* There's already an internal callback chain for setting selection [in 1.5]
|
||||
* ownership. See the CallSelectionCallback at the bottom of
|
||||
* ProcSetSelectionOwner, and xfixes/select.c for an example of how to hook
|
||||
* into it.
|
||||
*/
|
||||
|
||||
remain = 3000000;
|
||||
fprintf(stderr, "X11.app: Received new $DISPLAY fd: %d ... sleeping to allow xinitrc to catchup.\n", launchd_fd);
|
||||
while((remain = usleep(remain)) > 0);
|
||||
|
||||
|
||||
fprintf(stderr, "X11.app Handing off fd to server thread via DarwinListenOnOpenFD(%d)\n", launchd_fd);
|
||||
DarwinListenOnOpenFD(launchd_fd);
|
||||
|
||||
#ifndef HAVE_LIBDISPATCH
|
||||
return NULL;
|
||||
#endif
|
||||
}
|
||||
|
||||
static int create_socket(char *filename_out) {
|
||||
|
@ -311,8 +312,14 @@ kern_return_t do_request_fd_handoff_socket(mach_port_t port, string_t filename)
|
|||
}
|
||||
|
||||
strlcpy(filename, handoff_data->filename, STRING_T_SIZE);
|
||||
|
||||
|
||||
#ifdef HAVE_LIBDISPATCH
|
||||
dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT,0), ^{
|
||||
socket_handoff(handoff_data);
|
||||
});
|
||||
#else
|
||||
create_thread(socket_handoff_thread, handoff_data);
|
||||
#endif
|
||||
|
||||
#ifdef DEBUG
|
||||
fprintf(stderr, "X11.app: Thread created for handoff. Returning success to tell caller to connect and push the fd.\n");
|
||||
|
|
|
@ -136,6 +136,9 @@
|
|||
/* Define to 1 if you have the `m' library (-lm). */
|
||||
#undef HAVE_LIBM
|
||||
|
||||
/* Define to 1 if you have the libdispatch (GCD) available */
|
||||
#undef HAVE_LIBDISPATCH
|
||||
|
||||
/* Define to 1 if you have the `link' function. */
|
||||
#undef HAVE_LINK
|
||||
|
||||
|
|
Loading…
Reference in New Issue
Block a user