aboutsummaryrefslogtreecommitdiff
path: root/xorg-server/hw
diff options
context:
space:
mode:
Diffstat (limited to 'xorg-server/hw')
-rw-r--r--xorg-server/hw/dmx/config/xdmxconfig.c8
-rw-r--r--xorg-server/hw/dmx/examples/xbell.c3
-rw-r--r--xorg-server/hw/xfree86/Makefile.am47
-rw-r--r--xorg-server/hw/xfree86/dri2/dri2.h574
-rw-r--r--xorg-server/hw/xfree86/dri2/dri2ext.c1299
-rw-r--r--xorg-server/hw/xfree86/loader/Makefile.am14
-rw-r--r--xorg-server/hw/xfree86/os-support/Makefile.am7
-rw-r--r--xorg-server/hw/xfree86/os-support/shared/posix_tty.c1310
-rw-r--r--xorg-server/hw/xfree86/sdksyms.sh (renamed from xorg-server/hw/xfree86/loader/sdksyms.sh)0
-rw-r--r--xorg-server/hw/xquartz/X11Application.m25
-rw-r--r--xorg-server/hw/xquartz/mach-startup/Makefile.am4
-rw-r--r--xorg-server/hw/xwin/windialogs.c2
-rw-r--r--xorg-server/hw/xwin/winmultiwindowwindow.c38
-rw-r--r--xorg-server/hw/xwin/winmultiwindowwndproc.c2117
-rw-r--r--xorg-server/hw/xwin/winwindow.h1
15 files changed, 2746 insertions, 2703 deletions
diff --git a/xorg-server/hw/dmx/config/xdmxconfig.c b/xorg-server/hw/dmx/config/xdmxconfig.c
index c67077aec..2de7f2b85 100644
--- a/xorg-server/hw/dmx/config/xdmxconfig.c
+++ b/xorg-server/hw/dmx/config/xdmxconfig.c
@@ -877,8 +877,8 @@ int main(int argc, char **argv)
Widget parent, menubox, bottombox, databox, canvasbox;
Widget filebutton, helpbutton;
Widget filemenu, openbutton, savebutton, quitbutton;
- Widget helpmenu, aboutbutton, aboutbox, abouttext, aboutok;
- Widget quitbox, quittext, quitok, quitcan;
+ Widget helpmenu, aboutbutton, aboutbox, aboutok;
+ Widget quitbox, quitok, quitcan;
Widget ncbutton;
Widget canbutton;
Widget ecbox, ecokbutton, eccanbutton;
@@ -1096,7 +1096,7 @@ int main(int argc, char **argv)
toplevel, NULL);
aboutbox = XtVaCreateManagedWidget("aboutbox", boxWidgetClass,
aboutpopup, NULL);
- abouttext = XtVaCreateManagedWidget("abouttext", labelWidgetClass,
+ XtVaCreateManagedWidget("abouttext", labelWidgetClass,
aboutbox,
XtNlabel, DMX_INFO,
NULL);
@@ -1108,7 +1108,7 @@ int main(int argc, char **argv)
toplevel, NULL);
quitbox = XtVaCreateManagedWidget("quitbox", boxWidgetClass,
quitpopup, NULL);
- quittext = XtVaCreateManagedWidget("quittext", labelWidgetClass,
+ XtVaCreateManagedWidget("quittext", labelWidgetClass,
quitbox,
XtNlabel,
"Changes to the configuration\n"
diff --git a/xorg-server/hw/dmx/examples/xbell.c b/xorg-server/hw/dmx/examples/xbell.c
index f3e3be1b8..79419d324 100644
--- a/xorg-server/hw/dmx/examples/xbell.c
+++ b/xorg-server/hw/dmx/examples/xbell.c
@@ -71,7 +71,6 @@ int main(int argc, char **argv)
XKeyboardControl kc;
XKeyboardState ks;
unsigned long vm;
- int percent;
if (argc != 5) {
printf("Usage: xbell percent baseVolume pitch duration\n");
@@ -81,7 +80,7 @@ int main(int argc, char **argv)
vm = (KBBellPercent
| KBBellPitch
| KBBellDuration);
- percent = atoi(argv[1]);
+ kc.key_click_percent = atoi(argv[1]);
kc.bell_percent = atoi(argv[2]);
kc.bell_pitch = atoi(argv[3]);
kc.bell_duration = atoi(argv[4]);
diff --git a/xorg-server/hw/xfree86/Makefile.am b/xorg-server/hw/xfree86/Makefile.am
index 6fa1dd29f..c3e006c1f 100644
--- a/xorg-server/hw/xfree86/Makefile.am
+++ b/xorg-server/hw/xfree86/Makefile.am
@@ -38,18 +38,18 @@ DIST_SUBDIRS = common ddc i2c x86emu int10 fbdevhw os-support \
utils doc man
bin_PROGRAMS = Xorg
-Xorg_SOURCES = xorg.c
+nodist_Xorg_SOURCES = sdksyms.c
AM_CFLAGS = $(DIX_CFLAGS) @XORG_CFLAGS@
-INCLUDES = @XORG_INCS@
+INCLUDES = $(XORG_INCS) -I$(srcdir)/parser -I$(top_srcdir)/miext/cw \
+ -I$(srcdir)/ddc -I$(srcdir)/i2c -I$(srcdir)/modes -I$(srcdir)/ramdac
-noinst_LTLIBRARIES = libxorg.la
-libxorg_la_SOURCES = libxorg.c
-libxorg_la_LIBADD = \
+LOCAL_LIBS = \
+ $(MAIN_LIB) \
$(XSERVER_LIBS) \
loader/libloader.la \
- os-support/libxorgos.la \
common/libcommon.la \
+ os-support/libxorgos.la \
parser/libxf86config_internal.la \
dixmods/libdixmods.la \
modes/libxf86modes.la \
@@ -57,31 +57,21 @@ libxorg_la_LIBADD = \
ddc/libddc.la \
i2c/libi2c.la \
dixmods/libxorgxkb.la \
+ $(XORG_LIBS) \
$(top_builddir)/mi/libmi.la \
- $(top_builddir)/os/libos.la \
- @XORG_LIBS@
-
-libxorg_la_DEPENDENCIES = $(libxorg_la_LIBADD)
-
-libxorg.c xorg.c:
- touch $@
-
-DISTCLEANFILES = libxorg.c xorg.c
-
-Xorg_DEPENDENCIES = libxorg.la
-Xorg_LDADD = $(MAIN_LIB) libxorg.la $(XORG_SYS_LIBS) $(XSERVER_SYS_LIBS)
+ $(top_builddir)/os/libos.la
+Xorg_LDADD = \
+ $(LOCAL_LIBS) \
+ $(XORG_SYS_LIBS) \
+ $(XSERVER_SYS_LIBS)
+Xorg_DEPENDENCIES = $(LOCAL_LIBS)
Xorg_LDFLAGS = $(LD_EXPORT_SYMBOLS_FLAG)
BUILT_SOURCES = xorg.conf.example
-DISTCLEANFILES += xorg.conf.example
+DISTCLEANFILES = xorg.conf.example
EXTRA_DIST = xorgconf.cpp
-if SPECIAL_DTRACE_OBJECTS
-# Re-add dtrace object code that gets lost when building static libraries
-Xorg_LDADD += $(XSERVER_LIBS)
-endif
-
if SOLARIS_ASM_INLINE
# Needs to be built before any files are compiled when using Sun compilers
# so in*/out* inline definitions are properly processed.
@@ -116,3 +106,12 @@ xorg.conf.example: xorgconf.cpp
relink:
$(AM_V_at)rm -f Xorg && $(MAKE) Xorg
+
+CLEANFILES = sdksyms.c sdksyms.dep
+EXTRA_DIST += sdksyms.sh
+
+sdksyms.dep sdksyms.c: sdksyms.sh
+ CPP='$(CPP)' AWK='$(AWK)' $(srcdir)/sdksyms.sh $(top_srcdir) $(CFLAGS) $(AM_CFLAGS) $(INCLUDES)
+
+SDKSYMS_DEP = sdksyms.dep
+include $(SDKSYMS_DEP)
diff --git a/xorg-server/hw/xfree86/dri2/dri2.h b/xorg-server/hw/xfree86/dri2/dri2.h
index afe2083de..2a41ead5b 100644
--- a/xorg-server/hw/xfree86/dri2/dri2.h
+++ b/xorg-server/hw/xfree86/dri2/dri2.h
@@ -1,287 +1,287 @@
-/*
- * Copyright © 2007 Red Hat, Inc.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Soft-
- * ware"), to deal in the Software without restriction, including without
- * limitation the rights to use, copy, modify, merge, publish, distribute,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, provided that the above copyright
- * notice(s) and this permission notice appear in all copies of the Soft-
- * ware and that both the above copyright notice(s) and this permission
- * notice appear in supporting documentation.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
- * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABIL-
- * ITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT OF THIRD PARTY
- * RIGHTS. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR HOLDERS INCLUDED IN
- * THIS NOTICE BE LIABLE FOR ANY CLAIM, OR ANY SPECIAL INDIRECT OR CONSE-
- * QUENTIAL DAMAGES, OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
- * DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
- * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFOR-
- * MANCE OF THIS SOFTWARE.
- *
- * Except as contained in this notice, the name of a copyright holder shall
- * not be used in advertising or otherwise to promote the sale, use or
- * other dealings in this Software without prior written authorization of
- * the copyright holder.
- *
- * Authors:
- * Kristian Høgsberg (krh@redhat.com)
- */
-
-#ifndef _DRI2_H_
-#define _DRI2_H_
-
-#include <X11/extensions/dri2tokens.h>
-
-/* Version 2 structure (with format at the end) */
-typedef struct {
- unsigned int attachment;
- unsigned int name;
- unsigned int pitch;
- unsigned int cpp;
- unsigned int flags;
- unsigned int format;
- void *driverPrivate;
-} DRI2BufferRec, *DRI2BufferPtr;
-
-extern CARD8 dri2_major; /* version of DRI2 supported by DDX */
-extern CARD8 dri2_minor;
-
-typedef DRI2BufferRec DRI2Buffer2Rec, *DRI2Buffer2Ptr;
-typedef void (*DRI2SwapEventPtr)(ClientPtr client, void *data, int type,
- CARD64 ust, CARD64 msc, CARD64 sbc);
-
-
-typedef DRI2BufferPtr (*DRI2CreateBuffersProcPtr)(DrawablePtr pDraw,
- unsigned int *attachments,
- int count);
-typedef void (*DRI2DestroyBuffersProcPtr)(DrawablePtr pDraw,
- DRI2BufferPtr buffers,
- int count);
-typedef void (*DRI2CopyRegionProcPtr)(DrawablePtr pDraw,
- RegionPtr pRegion,
- DRI2BufferPtr pDestBuffer,
- DRI2BufferPtr pSrcBuffer);
-typedef void (*DRI2WaitProcPtr)(WindowPtr pWin,
- unsigned int sequence);
-typedef int (*DRI2AuthMagicProcPtr)(int fd, uint32_t magic);
-
-/**
- * Schedule a buffer swap
- *
- * This callback is used to support glXSwapBuffers and the OML_sync_control
- * extension (see it for a description of the params).
- *
- * Drivers should queue an event for the frame count that satisfies the
- * parameters passed in. If the event is in the future (i.e. the conditions
- * aren't currently satisfied), the server may block the client at the next
- * GLX request using DRI2WaitSwap. When the event arrives, drivers should call
- * \c DRI2SwapComplete, which will handle waking the client and returning
- * the appropriate data.
- *
- * The DDX is responsible for doing a flip, exchange, or blit of the swap
- * when the corresponding event arrives. The \c DRI2CanFlip and
- * \c DRI2CanExchange functions can be used as helpers for this purpose.
- *
- * \param client client pointer (used for block/unblock)
- * \param pDraw drawable whose count we want
- * \param pDestBuffer current front buffer
- * \param pSrcBuffer current back buffer
- * \param target_msc frame count to wait for
- * \param divisor divisor for condition equation
- * \param remainder remainder for division equation
- * \param func function to call when the swap completes
- * \param data data for the callback \p func.
- */
-typedef int (*DRI2ScheduleSwapProcPtr)(ClientPtr client,
- DrawablePtr pDraw,
- DRI2BufferPtr pDestBuffer,
- DRI2BufferPtr pSrcBuffer,
- CARD64 *target_msc,
- CARD64 divisor,
- CARD64 remainder,
- DRI2SwapEventPtr func,
- void *data);
-typedef DRI2BufferPtr (*DRI2CreateBufferProcPtr)(DrawablePtr pDraw,
- unsigned int attachment,
- unsigned int format);
-typedef void (*DRI2DestroyBufferProcPtr)(DrawablePtr pDraw,
- DRI2BufferPtr buffer);
-/**
- * Get current media stamp counter values
- *
- * This callback is used to support the SGI_video_sync and OML_sync_control
- * extensions.
- *
- * Drivers should return the current frame counter and the timestamp from
- * when the returned frame count was last incremented.
- *
- * The count should correspond to the screen where the drawable is currently
- * visible. If the drawable isn't visible (e.g. redirected), the server
- * should return BadDrawable to the client, pending GLX spec updates to
- * define this behavior.
- *
- * \param pDraw drawable whose count we want
- * \param ust timestamp from when the count was last incremented.
- * \param mst current frame count
- */
-typedef int (*DRI2GetMSCProcPtr)(DrawablePtr pDraw, CARD64 *ust,
- CARD64 *msc);
-/**
- * Schedule a frame count related wait
- *
- * This callback is used to support the SGI_video_sync and OML_sync_control
- * extensions. See those specifications for details on how to handle
- * the divisor and remainder parameters.
- *
- * Drivers should queue an event for the frame count that satisfies the
- * parameters passed in. If the event is in the future (i.e. the conditions
- * aren't currently satisfied), the driver should block the client using
- * \c DRI2BlockClient. When the event arrives, drivers should call
- * \c DRI2WaitMSCComplete, which will handle waking the client and returning
- * the appropriate data.
- *
- * \param client client pointer (used for block/unblock)
- * \param pDraw drawable whose count we want
- * \param target_msc frame count to wait for
- * \param divisor divisor for condition equation
- * \param remainder remainder for division equation
- */
-typedef int (*DRI2ScheduleWaitMSCProcPtr)(ClientPtr client,
- DrawablePtr pDraw,
- CARD64 target_msc,
- CARD64 divisor,
- CARD64 remainder);
-
-typedef void (*DRI2InvalidateProcPtr)(DrawablePtr pDraw,
- void *data);
-
-/**
- * Version of the DRI2InfoRec structure defined in this header
- */
-#define DRI2INFOREC_VERSION 5
-
-typedef struct {
- unsigned int version; /**< Version of this struct */
- int fd;
- const char *driverName;
- const char *deviceName;
-
- DRI2CreateBufferProcPtr CreateBuffer;
- DRI2DestroyBufferProcPtr DestroyBuffer;
- DRI2CopyRegionProcPtr CopyRegion;
- DRI2WaitProcPtr Wait;
-
- /* added in version 4 */
-
- DRI2ScheduleSwapProcPtr ScheduleSwap;
- DRI2GetMSCProcPtr GetMSC;
- DRI2ScheduleWaitMSCProcPtr ScheduleWaitMSC;
-
- /* number of drivers in the driverNames array */
- unsigned int numDrivers;
- /* array of driver names, indexed by DRI2Driver* driver types */
- /* a name of NULL means that driver is not supported */
- const char * const *driverNames;
-
- /* added in version 5 */
-
- DRI2AuthMagicProcPtr AuthMagic;
-} DRI2InfoRec, *DRI2InfoPtr;
-
-extern _X_EXPORT int DRI2EventBase;
-
-extern _X_EXPORT Bool DRI2ScreenInit(ScreenPtr pScreen,
- DRI2InfoPtr info);
-
-extern _X_EXPORT void DRI2CloseScreen(ScreenPtr pScreen);
-
-extern _X_EXPORT Bool DRI2HasSwapControl(ScreenPtr pScreen);
-
-extern _X_EXPORT Bool DRI2Connect(ScreenPtr pScreen,
- unsigned int driverType,
- int *fd,
- const char **driverName,
- const char **deviceName);
-
-extern _X_EXPORT Bool DRI2Authenticate(ScreenPtr pScreen, uint32_t magic);
-
-extern _X_EXPORT int DRI2CreateDrawable(ClientPtr client,
- DrawablePtr pDraw,
- XID id,
- DRI2InvalidateProcPtr invalidate,
- void *priv);
-
-extern _X_EXPORT void DRI2DestroyDrawable(DrawablePtr pDraw);
-
-extern _X_EXPORT DRI2BufferPtr *DRI2GetBuffers(DrawablePtr pDraw,
- int *width,
- int *height,
- unsigned int *attachments,
- int count,
- int *out_count);
-
-extern _X_EXPORT int DRI2CopyRegion(DrawablePtr pDraw,
- RegionPtr pRegion,
- unsigned int dest,
- unsigned int src);
-
-/**
- * Determine the major and minor version of the DRI2 extension.
- *
- * Provides a mechanism to other modules (e.g., 2D drivers) to determine the
- * version of the DRI2 extension. While it is possible to peek directly at
- * the \c XF86ModuleData from a layered module, such a module will fail to
- * load (due to an unresolved symbol) if the DRI2 extension is not loaded.
- *
- * \param major Location to store the major verion of the DRI2 extension
- * \param minor Location to store the minor verion of the DRI2 extension
- *
- * \note
- * This interface was added some time after the initial release of the DRI2
- * module. Layered modules that wish to use this interface must first test
- * its existance by calling \c xf86LoaderCheckSymbol.
- */
-extern _X_EXPORT void DRI2Version(int *major, int *minor);
-
-extern _X_EXPORT DRI2BufferPtr *DRI2GetBuffersWithFormat(DrawablePtr pDraw,
- int *width, int *height, unsigned int *attachments, int count,
- int *out_count);
-
-extern _X_EXPORT void DRI2SwapInterval(DrawablePtr pDrawable, int interval);
-extern _X_EXPORT int DRI2SwapBuffers(ClientPtr client, DrawablePtr pDrawable,
- CARD64 target_msc, CARD64 divisor,
- CARD64 remainder, CARD64 *swap_target,
- DRI2SwapEventPtr func, void *data);
-extern _X_EXPORT Bool DRI2WaitSwap(ClientPtr client, DrawablePtr pDrawable);
-
-extern _X_EXPORT int DRI2GetMSC(DrawablePtr pDrawable, CARD64 *ust,
- CARD64 *msc, CARD64 *sbc);
-extern _X_EXPORT int DRI2WaitMSC(ClientPtr client, DrawablePtr pDrawable,
- CARD64 target_msc, CARD64 divisor,
- CARD64 remainder);
-extern _X_EXPORT int ProcDRI2WaitMSCReply(ClientPtr client, CARD64 ust,
- CARD64 msc, CARD64 sbc);
-extern _X_EXPORT int DRI2WaitSBC(ClientPtr client, DrawablePtr pDraw,
- CARD64 target_sbc);
-extern _X_EXPORT Bool DRI2ThrottleClient(ClientPtr client, DrawablePtr pDraw);
-
-extern _X_EXPORT Bool DRI2CanFlip(DrawablePtr pDraw);
-
-extern _X_EXPORT Bool DRI2CanExchange(DrawablePtr pDraw);
-
-/* Note: use *only* for MSC related waits */
-extern _X_EXPORT void DRI2BlockClient(ClientPtr client, DrawablePtr pDraw);
-
-extern _X_EXPORT void DRI2SwapComplete(ClientPtr client, DrawablePtr pDraw,
- int frame, unsigned int tv_sec,
- unsigned int tv_usec, int type,
- DRI2SwapEventPtr swap_complete,
- void *swap_data);
-extern _X_EXPORT void DRI2WaitMSCComplete(ClientPtr client, DrawablePtr pDraw,
- int frame, unsigned int tv_sec,
- unsigned int tv_usec);
-
-#endif
+/*
+ * Copyright © 2007 Red Hat, Inc.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Soft-
+ * ware"), to deal in the Software without restriction, including without
+ * limitation the rights to use, copy, modify, merge, publish, distribute,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, provided that the above copyright
+ * notice(s) and this permission notice appear in all copies of the Soft-
+ * ware and that both the above copyright notice(s) and this permission
+ * notice appear in supporting documentation.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
+ * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABIL-
+ * ITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT OF THIRD PARTY
+ * RIGHTS. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR HOLDERS INCLUDED IN
+ * THIS NOTICE BE LIABLE FOR ANY CLAIM, OR ANY SPECIAL INDIRECT OR CONSE-
+ * QUENTIAL DAMAGES, OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
+ * DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
+ * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFOR-
+ * MANCE OF THIS SOFTWARE.
+ *
+ * Except as contained in this notice, the name of a copyright holder shall
+ * not be used in advertising or otherwise to promote the sale, use or
+ * other dealings in this Software without prior written authorization of
+ * the copyright holder.
+ *
+ * Authors:
+ * Kristian Høgsberg (krh@redhat.com)
+ */
+
+#ifndef _DRI2_H_
+#define _DRI2_H_
+
+#include <X11/extensions/dri2tokens.h>
+
+/* Version 2 structure (with format at the end) */
+typedef struct {
+ unsigned int attachment;
+ unsigned int name;
+ unsigned int pitch;
+ unsigned int cpp;
+ unsigned int flags;
+ unsigned int format;
+ void *driverPrivate;
+} DRI2BufferRec, *DRI2BufferPtr;
+
+extern CARD8 dri2_major; /* version of DRI2 supported by DDX */
+extern CARD8 dri2_minor;
+
+typedef DRI2BufferRec DRI2Buffer2Rec, *DRI2Buffer2Ptr;
+typedef void (*DRI2SwapEventPtr)(ClientPtr client, void *data, int type,
+ CARD64 ust, CARD64 msc, CARD32 sbc);
+
+
+typedef DRI2BufferPtr (*DRI2CreateBuffersProcPtr)(DrawablePtr pDraw,
+ unsigned int *attachments,
+ int count);
+typedef void (*DRI2DestroyBuffersProcPtr)(DrawablePtr pDraw,
+ DRI2BufferPtr buffers,
+ int count);
+typedef void (*DRI2CopyRegionProcPtr)(DrawablePtr pDraw,
+ RegionPtr pRegion,
+ DRI2BufferPtr pDestBuffer,
+ DRI2BufferPtr pSrcBuffer);
+typedef void (*DRI2WaitProcPtr)(WindowPtr pWin,
+ unsigned int sequence);
+typedef int (*DRI2AuthMagicProcPtr)(int fd, uint32_t magic);
+
+/**
+ * Schedule a buffer swap
+ *
+ * This callback is used to support glXSwapBuffers and the OML_sync_control
+ * extension (see it for a description of the params).
+ *
+ * Drivers should queue an event for the frame count that satisfies the
+ * parameters passed in. If the event is in the future (i.e. the conditions
+ * aren't currently satisfied), the server may block the client at the next
+ * GLX request using DRI2WaitSwap. When the event arrives, drivers should call
+ * \c DRI2SwapComplete, which will handle waking the client and returning
+ * the appropriate data.
+ *
+ * The DDX is responsible for doing a flip, exchange, or blit of the swap
+ * when the corresponding event arrives. The \c DRI2CanFlip and
+ * \c DRI2CanExchange functions can be used as helpers for this purpose.
+ *
+ * \param client client pointer (used for block/unblock)
+ * \param pDraw drawable whose count we want
+ * \param pDestBuffer current front buffer
+ * \param pSrcBuffer current back buffer
+ * \param target_msc frame count to wait for
+ * \param divisor divisor for condition equation
+ * \param remainder remainder for division equation
+ * \param func function to call when the swap completes
+ * \param data data for the callback \p func.
+ */
+typedef int (*DRI2ScheduleSwapProcPtr)(ClientPtr client,
+ DrawablePtr pDraw,
+ DRI2BufferPtr pDestBuffer,
+ DRI2BufferPtr pSrcBuffer,
+ CARD64 *target_msc,
+ CARD64 divisor,
+ CARD64 remainder,
+ DRI2SwapEventPtr func,
+ void *data);
+typedef DRI2BufferPtr (*DRI2CreateBufferProcPtr)(DrawablePtr pDraw,
+ unsigned int attachment,
+ unsigned int format);
+typedef void (*DRI2DestroyBufferProcPtr)(DrawablePtr pDraw,
+ DRI2BufferPtr buffer);
+/**
+ * Get current media stamp counter values
+ *
+ * This callback is used to support the SGI_video_sync and OML_sync_control
+ * extensions.
+ *
+ * Drivers should return the current frame counter and the timestamp from
+ * when the returned frame count was last incremented.
+ *
+ * The count should correspond to the screen where the drawable is currently
+ * visible. If the drawable isn't visible (e.g. redirected), the server
+ * should return BadDrawable to the client, pending GLX spec updates to
+ * define this behavior.
+ *
+ * \param pDraw drawable whose count we want
+ * \param ust timestamp from when the count was last incremented.
+ * \param mst current frame count
+ */
+typedef int (*DRI2GetMSCProcPtr)(DrawablePtr pDraw, CARD64 *ust,
+ CARD64 *msc);
+/**
+ * Schedule a frame count related wait
+ *
+ * This callback is used to support the SGI_video_sync and OML_sync_control
+ * extensions. See those specifications for details on how to handle
+ * the divisor and remainder parameters.
+ *
+ * Drivers should queue an event for the frame count that satisfies the
+ * parameters passed in. If the event is in the future (i.e. the conditions
+ * aren't currently satisfied), the driver should block the client using
+ * \c DRI2BlockClient. When the event arrives, drivers should call
+ * \c DRI2WaitMSCComplete, which will handle waking the client and returning
+ * the appropriate data.
+ *
+ * \param client client pointer (used for block/unblock)
+ * \param pDraw drawable whose count we want
+ * \param target_msc frame count to wait for
+ * \param divisor divisor for condition equation
+ * \param remainder remainder for division equation
+ */
+typedef int (*DRI2ScheduleWaitMSCProcPtr)(ClientPtr client,
+ DrawablePtr pDraw,
+ CARD64 target_msc,
+ CARD64 divisor,
+ CARD64 remainder);
+
+typedef void (*DRI2InvalidateProcPtr)(DrawablePtr pDraw,
+ void *data);
+
+/**
+ * Version of the DRI2InfoRec structure defined in this header
+ */
+#define DRI2INFOREC_VERSION 5
+
+typedef struct {
+ unsigned int version; /**< Version of this struct */
+ int fd;
+ const char *driverName;
+ const char *deviceName;
+
+ DRI2CreateBufferProcPtr CreateBuffer;
+ DRI2DestroyBufferProcPtr DestroyBuffer;
+ DRI2CopyRegionProcPtr CopyRegion;
+ DRI2WaitProcPtr Wait;
+
+ /* added in version 4 */
+
+ DRI2ScheduleSwapProcPtr ScheduleSwap;
+ DRI2GetMSCProcPtr GetMSC;
+ DRI2ScheduleWaitMSCProcPtr ScheduleWaitMSC;
+
+ /* number of drivers in the driverNames array */
+ unsigned int numDrivers;
+ /* array of driver names, indexed by DRI2Driver* driver types */
+ /* a name of NULL means that driver is not supported */
+ const char * const *driverNames;
+
+ /* added in version 5 */
+
+ DRI2AuthMagicProcPtr AuthMagic;
+} DRI2InfoRec, *DRI2InfoPtr;
+
+extern _X_EXPORT int DRI2EventBase;
+
+extern _X_EXPORT Bool DRI2ScreenInit(ScreenPtr pScreen,
+ DRI2InfoPtr info);
+
+extern _X_EXPORT void DRI2CloseScreen(ScreenPtr pScreen);
+
+extern _X_EXPORT Bool DRI2HasSwapControl(ScreenPtr pScreen);
+
+extern _X_EXPORT Bool DRI2Connect(ScreenPtr pScreen,
+ unsigned int driverType,
+ int *fd,
+ const char **driverName,
+ const char **deviceName);
+
+extern _X_EXPORT Bool DRI2Authenticate(ScreenPtr pScreen, uint32_t magic);
+
+extern _X_EXPORT int DRI2CreateDrawable(ClientPtr client,
+ DrawablePtr pDraw,
+ XID id,
+ DRI2InvalidateProcPtr invalidate,
+ void *priv);
+
+extern _X_EXPORT void DRI2DestroyDrawable(DrawablePtr pDraw);
+
+extern _X_EXPORT DRI2BufferPtr *DRI2GetBuffers(DrawablePtr pDraw,
+ int *width,
+ int *height,
+ unsigned int *attachments,
+ int count,
+ int *out_count);
+
+extern _X_EXPORT int DRI2CopyRegion(DrawablePtr pDraw,
+ RegionPtr pRegion,
+ unsigned int dest,
+ unsigned int src);
+
+/**
+ * Determine the major and minor version of the DRI2 extension.
+ *
+ * Provides a mechanism to other modules (e.g., 2D drivers) to determine the
+ * version of the DRI2 extension. While it is possible to peek directly at
+ * the \c XF86ModuleData from a layered module, such a module will fail to
+ * load (due to an unresolved symbol) if the DRI2 extension is not loaded.
+ *
+ * \param major Location to store the major verion of the DRI2 extension
+ * \param minor Location to store the minor verion of the DRI2 extension
+ *
+ * \note
+ * This interface was added some time after the initial release of the DRI2
+ * module. Layered modules that wish to use this interface must first test
+ * its existance by calling \c xf86LoaderCheckSymbol.
+ */
+extern _X_EXPORT void DRI2Version(int *major, int *minor);
+
+extern _X_EXPORT DRI2BufferPtr *DRI2GetBuffersWithFormat(DrawablePtr pDraw,
+ int *width, int *height, unsigned int *attachments, int count,
+ int *out_count);
+
+extern _X_EXPORT void DRI2SwapInterval(DrawablePtr pDrawable, int interval);
+extern _X_EXPORT int DRI2SwapBuffers(ClientPtr client, DrawablePtr pDrawable,
+ CARD64 target_msc, CARD64 divisor,
+ CARD64 remainder, CARD64 *swap_target,
+ DRI2SwapEventPtr func, void *data);
+extern _X_EXPORT Bool DRI2WaitSwap(ClientPtr client, DrawablePtr pDrawable);
+
+extern _X_EXPORT int DRI2GetMSC(DrawablePtr pDrawable, CARD64 *ust,
+ CARD64 *msc, CARD64 *sbc);
+extern _X_EXPORT int DRI2WaitMSC(ClientPtr client, DrawablePtr pDrawable,
+ CARD64 target_msc, CARD64 divisor,
+ CARD64 remainder);
+extern _X_EXPORT int ProcDRI2WaitMSCReply(ClientPtr client, CARD64 ust,
+ CARD64 msc, CARD64 sbc);
+extern _X_EXPORT int DRI2WaitSBC(ClientPtr client, DrawablePtr pDraw,
+ CARD64 target_sbc);
+extern _X_EXPORT Bool DRI2ThrottleClient(ClientPtr client, DrawablePtr pDraw);
+
+extern _X_EXPORT Bool DRI2CanFlip(DrawablePtr pDraw);
+
+extern _X_EXPORT Bool DRI2CanExchange(DrawablePtr pDraw);
+
+/* Note: use *only* for MSC related waits */
+extern _X_EXPORT void DRI2BlockClient(ClientPtr client, DrawablePtr pDraw);
+
+extern _X_EXPORT void DRI2SwapComplete(ClientPtr client, DrawablePtr pDraw,
+ int frame, unsigned int tv_sec,
+ unsigned int tv_usec, int type,
+ DRI2SwapEventPtr swap_complete,
+ void *swap_data);
+extern _X_EXPORT void DRI2WaitMSCComplete(ClientPtr client, DrawablePtr pDraw,
+ int frame, unsigned int tv_sec,
+ unsigned int tv_usec);
+
+#endif
diff --git a/xorg-server/hw/xfree86/dri2/dri2ext.c b/xorg-server/hw/xfree86/dri2/dri2ext.c
index 6853fab9e..552b26b7c 100644
--- a/xorg-server/hw/xfree86/dri2/dri2ext.c
+++ b/xorg-server/hw/xfree86/dri2/dri2ext.c
@@ -1,650 +1,649 @@
-/*
- * Copyright © 2008 Red Hat, Inc.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Soft-
- * ware"), to deal in the Software without restriction, including without
- * limitation the rights to use, copy, modify, merge, publish, distribute,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, provided that the above copyright
- * notice(s) and this permission notice appear in all copies of the Soft-
- * ware and that both the above copyright notice(s) and this permission
- * notice appear in supporting documentation.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
- * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABIL-
- * ITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT OF THIRD PARTY
- * RIGHTS. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR HOLDERS INCLUDED IN
- * THIS NOTICE BE LIABLE FOR ANY CLAIM, OR ANY SPECIAL INDIRECT OR CONSE-
- * QUENTIAL DAMAGES, OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
- * DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
- * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFOR-
- * MANCE OF THIS SOFTWARE.
- *
- * Except as contained in this notice, the name of a copyright holder shall
- * not be used in advertising or otherwise to promote the sale, use or
- * other dealings in this Software without prior written authorization of
- * the copyright holder.
- *
- * Authors:
- * Kristian Høgsberg (krh@redhat.com)
- */
-
-#ifdef HAVE_XORG_CONFIG_H
-#include <xorg-config.h>
-#endif
-
-#include <X11/X.h>
-#include <X11/Xproto.h>
-#include <X11/extensions/dri2proto.h>
-#include <X11/extensions/xfixeswire.h>
-#include "dixstruct.h"
-#include "scrnintstr.h"
-#include "pixmapstr.h"
-#include "extnsionst.h"
-#include "xfixes.h"
-#include "dri2.h"
-#include "protocol-versions.h"
-
-/* The only xf86 include */
-#include "xf86Module.h"
-
-static ExtensionEntry *dri2Extension;
-
-static Bool
-validDrawable(ClientPtr client, XID drawable, Mask access_mode,
- DrawablePtr *pDrawable, int *status)
-{
- *status = dixLookupDrawable(pDrawable, drawable, client,
- M_DRAWABLE_WINDOW | M_DRAWABLE_PIXMAP,
- access_mode);
- if (*status != Success) {
- client->errorValue = drawable;
- return FALSE;
- }
-
- return TRUE;
-}
-
-static int
-ProcDRI2QueryVersion(ClientPtr client)
-{
- REQUEST(xDRI2QueryVersionReq);
- xDRI2QueryVersionReply rep;
- int n;
-
- if (client->swapped)
- swaps(&stuff->length, n);
-
- REQUEST_SIZE_MATCH(xDRI2QueryVersionReq);
- rep.type = X_Reply;
- rep.length = 0;
- rep.sequenceNumber = client->sequence;
- rep.majorVersion = dri2_major;
- rep.minorVersion = dri2_minor;
-
- if (client->swapped) {
- swaps(&rep.sequenceNumber, n);
- swapl(&rep.length, n);
- swapl(&rep.majorVersion, n);
- swapl(&rep.minorVersion, n);
- }
-
- WriteToClient(client, sizeof(xDRI2QueryVersionReply), &rep);
-
- return Success;
-}
-
-static int
-ProcDRI2Connect(ClientPtr client)
-{
- REQUEST(xDRI2ConnectReq);
- xDRI2ConnectReply rep;
- DrawablePtr pDraw;
- int fd, status;
- const char *driverName;
- const char *deviceName;
-
- REQUEST_SIZE_MATCH(xDRI2ConnectReq);
- if (!validDrawable(client, stuff->window, DixGetAttrAccess,
- &pDraw, &status))
- return status;
-
- rep.type = X_Reply;
- rep.length = 0;
- rep.sequenceNumber = client->sequence;
- rep.driverNameLength = 0;
- rep.deviceNameLength = 0;
-
- if (!DRI2Connect(pDraw->pScreen,
- stuff->driverType, &fd, &driverName, &deviceName))
- goto fail;
-
- rep.driverNameLength = strlen(driverName);
- rep.deviceNameLength = strlen(deviceName);
- rep.length = (rep.driverNameLength + 3) / 4 +
- (rep.deviceNameLength + 3) / 4;
-
- fail:
- WriteToClient(client, sizeof(xDRI2ConnectReply), &rep);
- WriteToClient(client, rep.driverNameLength, driverName);
- WriteToClient(client, rep.deviceNameLength, deviceName);
-
- return Success;
-}
-
-static int
-ProcDRI2Authenticate(ClientPtr client)
-{
- REQUEST(xDRI2AuthenticateReq);
- xDRI2AuthenticateReply rep;
- DrawablePtr pDraw;
- int status;
-
- REQUEST_SIZE_MATCH(xDRI2AuthenticateReq);
- if (!validDrawable(client, stuff->window, DixGetAttrAccess,
- &pDraw, &status))
- return status;
-
- rep.type = X_Reply;
- rep.sequenceNumber = client->sequence;
- rep.length = 0;
- rep.authenticated = DRI2Authenticate(pDraw->pScreen, stuff->magic);
- WriteToClient(client, sizeof(xDRI2AuthenticateReply), &rep);
-
- return Success;
-}
-
-static void
-DRI2InvalidateBuffersEvent(DrawablePtr pDraw, void *priv)
-{
- xDRI2InvalidateBuffers event;
- ClientPtr client = priv;
-
- event.type = DRI2EventBase + DRI2_InvalidateBuffers;
- event.drawable = pDraw->id;
-
- WriteEventsToClient(client, 1, (xEvent *)&event);
-}
-
-static int
-ProcDRI2CreateDrawable(ClientPtr client)
-{
- REQUEST(xDRI2CreateDrawableReq);
- DrawablePtr pDrawable;
- int status;
-
- REQUEST_SIZE_MATCH(xDRI2CreateDrawableReq);
-
- if (!validDrawable(client, stuff->drawable, DixAddAccess,
- &pDrawable, &status))
- return status;
-
- status = DRI2CreateDrawable(client, pDrawable, stuff->drawable,
- DRI2InvalidateBuffersEvent, client);
- if (status != Success)
- return status;
-
- return Success;
-}
-
-static int
-ProcDRI2DestroyDrawable(ClientPtr client)
-{
- REQUEST(xDRI2DestroyDrawableReq);
- DrawablePtr pDrawable;
- int status;
-
- REQUEST_SIZE_MATCH(xDRI2DestroyDrawableReq);
- if (!validDrawable(client, stuff->drawable, DixRemoveAccess,
- &pDrawable, &status))
- return status;
-
- return Success;
-}
-
-
-static int
-send_buffers_reply(ClientPtr client, DrawablePtr pDrawable,
- DRI2BufferPtr *buffers, int count, int width, int height)
-{
- xDRI2GetBuffersReply rep;
- int skip = 0;
- int i;
-
- if (buffers == NULL)
- return BadAlloc;
-
- if (pDrawable->type == DRAWABLE_WINDOW) {
- for (i = 0; i < count; i++) {
- /* Do not send the real front buffer of a window to the client.
- */
- if (buffers[i]->attachment == DRI2BufferFrontLeft) {
- skip++;
- continue;
- }
- }
- }
-
- rep.type = X_Reply;
- rep.length = (count - skip) * sizeof(xDRI2Buffer) / 4;
- rep.sequenceNumber = client->sequence;
- rep.width = width;
- rep.height = height;
- rep.count = count - skip;
- WriteToClient(client, sizeof(xDRI2GetBuffersReply), &rep);
-
- for (i = 0; i < count; i++) {
- xDRI2Buffer buffer;
-
- /* Do not send the real front buffer of a window to the client.
- */
- if ((pDrawable->type == DRAWABLE_WINDOW)
- && (buffers[i]->attachment == DRI2BufferFrontLeft)) {
- continue;
- }
-
- buffer.attachment = buffers[i]->attachment;
- buffer.name = buffers[i]->name;
- buffer.pitch = buffers[i]->pitch;
- buffer.cpp = buffers[i]->cpp;
- buffer.flags = buffers[i]->flags;
- WriteToClient(client, sizeof(xDRI2Buffer), &buffer);
- }
- return Success;
-}
-
-
-static int
-ProcDRI2GetBuffers(ClientPtr client)
-{
- REQUEST(xDRI2GetBuffersReq);
- DrawablePtr pDrawable;
- DRI2BufferPtr *buffers;
- int status, width, height, count;
- unsigned int *attachments;
-
- REQUEST_FIXED_SIZE(xDRI2GetBuffersReq, stuff->count * 4);
- if (!validDrawable(client, stuff->drawable, DixReadAccess | DixWriteAccess,
- &pDrawable, &status))
- return status;
-
- if (DRI2ThrottleClient(client, pDrawable))
- return Success;
-
- attachments = (unsigned int *) &stuff[1];
- buffers = DRI2GetBuffers(pDrawable, &width, &height,
- attachments, stuff->count, &count);
-
-
- return send_buffers_reply(client, pDrawable, buffers, count, width, height);
-
-}
-
-static int
-ProcDRI2GetBuffersWithFormat(ClientPtr client)
-{
- REQUEST(xDRI2GetBuffersReq);
- DrawablePtr pDrawable;
- DRI2BufferPtr *buffers;
- int status, width, height, count;
- unsigned int *attachments;
-
- REQUEST_FIXED_SIZE(xDRI2GetBuffersReq, stuff->count * (2 * 4));
- if (!validDrawable(client, stuff->drawable, DixReadAccess | DixWriteAccess,
- &pDrawable, &status))
- return status;
-
- if (DRI2ThrottleClient(client, pDrawable))
- return Success;
-
- attachments = (unsigned int *) &stuff[1];
- buffers = DRI2GetBuffersWithFormat(pDrawable, &width, &height,
- attachments, stuff->count, &count);
-
- return send_buffers_reply(client, pDrawable, buffers, count, width, height);
-}
-
-static int
-ProcDRI2CopyRegion(ClientPtr client)
-{
- REQUEST(xDRI2CopyRegionReq);
- xDRI2CopyRegionReply rep;
- DrawablePtr pDrawable;
- int status;
- RegionPtr pRegion;
-
- REQUEST_SIZE_MATCH(xDRI2CopyRegionReq);
-
- if (!validDrawable(client, stuff->drawable, DixWriteAccess,
- &pDrawable, &status))
- return status;
-
- VERIFY_REGION(pRegion, stuff->region, client, DixReadAccess);
-
- status = DRI2CopyRegion(pDrawable, pRegion, stuff->dest, stuff->src);
- if (status != Success)
- return status;
-
- /* CopyRegion needs to be a round trip to make sure the X server
- * queues the swap buffer rendering commands before the DRI client
- * continues rendering. The reply has a bitmask to signal the
- * presense of optional return values as well, but we're not using
- * that yet.
- */
-
- rep.type = X_Reply;
- rep.length = 0;
- rep.sequenceNumber = client->sequence;
-
- WriteToClient(client, sizeof(xDRI2CopyRegionReply), &rep);
-
- return Success;
-}
-
-static void
-load_swap_reply(xDRI2SwapBuffersReply *rep, CARD64 sbc)
-{
- rep->swap_hi = sbc >> 32;
- rep->swap_lo = sbc & 0xffffffff;
-}
-
-static CARD64
-vals_to_card64(CARD32 lo, CARD32 hi)
-{
- return (CARD64)hi << 32 | lo;
-}
-
-static void
-DRI2SwapEvent(ClientPtr client, void *data, int type, CARD64 ust, CARD64 msc,
- CARD64 sbc)
-{
- xDRI2BufferSwapComplete event;
- DrawablePtr pDrawable = data;
-
- event.type = DRI2EventBase + DRI2_BufferSwapComplete;
- event.event_type = type;
- event.drawable = pDrawable->id;
- event.ust_hi = (CARD64)ust >> 32;
- event.ust_lo = ust & 0xffffffff;
- event.msc_hi = (CARD64)msc >> 32;
- event.msc_lo = msc & 0xffffffff;
- event.sbc_hi = (CARD64)sbc >> 32;
- event.sbc_lo = sbc & 0xffffffff;
-
- WriteEventsToClient(client, 1, (xEvent *)&event);
-}
-
-static int
-ProcDRI2SwapBuffers(ClientPtr client)
-{
- REQUEST(xDRI2SwapBuffersReq);
- xDRI2SwapBuffersReply rep;
- DrawablePtr pDrawable;
- CARD64 target_msc, divisor, remainder, swap_target;
- int status;
-
- REQUEST_SIZE_MATCH(xDRI2SwapBuffersReq);
-
- if (!validDrawable(client, stuff->drawable,
- DixReadAccess | DixWriteAccess, &pDrawable, &status))
- return status;
-
- /*
- * Ensures an out of control client can't exhaust our swap queue, and
- * also orders swaps.
- */
- if (DRI2ThrottleClient(client, pDrawable))
- return Success;
-
- target_msc = vals_to_card64(stuff->target_msc_lo, stuff->target_msc_hi);
- divisor = vals_to_card64(stuff->divisor_lo, stuff->divisor_hi);
- remainder = vals_to_card64(stuff->remainder_lo, stuff->remainder_hi);
-
- status = DRI2SwapBuffers(client, pDrawable, target_msc, divisor, remainder,
- &swap_target, DRI2SwapEvent, pDrawable);
- if (status != Success)
- return BadDrawable;
-
- rep.type = X_Reply;
- rep.length = 0;
- rep.sequenceNumber = client->sequence;
- load_swap_reply(&rep, swap_target);
-
- WriteToClient(client, sizeof(xDRI2SwapBuffersReply), &rep);
-
- return Success;
-}
-
-static void
-load_msc_reply(xDRI2MSCReply *rep, CARD64 ust, CARD64 msc, CARD64 sbc)
-{
- rep->ust_hi = ust >> 32;
- rep->ust_lo = ust & 0xffffffff;
- rep->msc_hi = msc >> 32;
- rep->msc_lo = msc & 0xffffffff;
- rep->sbc_hi = sbc >> 32;
- rep->sbc_lo = sbc & 0xffffffff;
-}
-
-static int
-ProcDRI2GetMSC(ClientPtr client)
-{
- REQUEST(xDRI2GetMSCReq);
- xDRI2MSCReply rep;
- DrawablePtr pDrawable;
- CARD64 ust, msc, sbc;
- int status;
-
- REQUEST_SIZE_MATCH(xDRI2GetMSCReq);
-
- if (!validDrawable(client, stuff->drawable, DixReadAccess, &pDrawable,
- &status))
- return status;
-
- status = DRI2GetMSC(pDrawable, &ust, &msc, &sbc);
- if (status != Success)
- return status;
-
- rep.type = X_Reply;
- rep.length = 0;
- rep.sequenceNumber = client->sequence;
- load_msc_reply(&rep, ust, msc, sbc);
-
- WriteToClient(client, sizeof(xDRI2MSCReply), &rep);
-
- return Success;
-}
-
-static int
-ProcDRI2WaitMSC(ClientPtr client)
-{
- REQUEST(xDRI2WaitMSCReq);
- DrawablePtr pDrawable;
- CARD64 target, divisor, remainder;
- int status;
-
- /* FIXME: in restart case, client may be gone at this point */
-
- REQUEST_SIZE_MATCH(xDRI2WaitMSCReq);
-
- if (!validDrawable(client, stuff->drawable, DixReadAccess, &pDrawable,
- &status))
- return status;
-
- target = vals_to_card64(stuff->target_msc_lo, stuff->target_msc_hi);
- divisor = vals_to_card64(stuff->divisor_lo, stuff->divisor_hi);
- remainder = vals_to_card64(stuff->remainder_lo, stuff->remainder_hi);
-
- status = DRI2WaitMSC(client, pDrawable, target, divisor, remainder);
- if (status != Success)
- return status;
-
- return Success;
-}
-
-int
-ProcDRI2WaitMSCReply(ClientPtr client, CARD64 ust, CARD64 msc, CARD64 sbc)
-{
- xDRI2MSCReply rep;
-
- rep.type = X_Reply;
- rep.length = 0;
- rep.sequenceNumber = client->sequence;
- load_msc_reply(&rep, ust, msc, sbc);
-
- WriteToClient(client, sizeof(xDRI2MSCReply), &rep);
-
- return Success;
-}
-
-static int
-ProcDRI2SwapInterval(ClientPtr client)
-{
- REQUEST(xDRI2SwapIntervalReq);
- DrawablePtr pDrawable;
- int status;
-
- /* FIXME: in restart case, client may be gone at this point */
-
- REQUEST_SIZE_MATCH(xDRI2SwapIntervalReq);
-
- if (!validDrawable(client, stuff->drawable, DixReadAccess | DixWriteAccess,
- &pDrawable, &status))
- return status;
-
- DRI2SwapInterval(pDrawable, stuff->interval);
-
- return Success;
-}
-
-static int
-ProcDRI2WaitSBC(ClientPtr client)
-{
- REQUEST(xDRI2WaitSBCReq);
- DrawablePtr pDrawable;
- CARD64 target;
- int status;
-
- REQUEST_SIZE_MATCH(xDRI2WaitSBCReq);
-
- if (!validDrawable(client, stuff->drawable, DixReadAccess, &pDrawable,
- &status))
- return status;
-
- target = vals_to_card64(stuff->target_sbc_lo, stuff->target_sbc_hi);
- status = DRI2WaitSBC(client, pDrawable, target);
-
- return status;
-}
-
-static int
-ProcDRI2Dispatch (ClientPtr client)
-{
- REQUEST(xReq);
-
- switch (stuff->data) {
- case X_DRI2QueryVersion:
- return ProcDRI2QueryVersion(client);
- }
-
- if (!LocalClient(client))
- return BadRequest;
-
- switch (stuff->data) {
- case X_DRI2Connect:
- return ProcDRI2Connect(client);
- case X_DRI2Authenticate:
- return ProcDRI2Authenticate(client);
- case X_DRI2CreateDrawable:
- return ProcDRI2CreateDrawable(client);
- case X_DRI2DestroyDrawable:
- return ProcDRI2DestroyDrawable(client);
- case X_DRI2GetBuffers:
- return ProcDRI2GetBuffers(client);
- case X_DRI2CopyRegion:
- return ProcDRI2CopyRegion(client);
- case X_DRI2GetBuffersWithFormat:
- return ProcDRI2GetBuffersWithFormat(client);
- case X_DRI2SwapBuffers:
- return ProcDRI2SwapBuffers(client);
- case X_DRI2GetMSC:
- return ProcDRI2GetMSC(client);
- case X_DRI2WaitMSC:
- return ProcDRI2WaitMSC(client);
- case X_DRI2WaitSBC:
- return ProcDRI2WaitSBC(client);
- case X_DRI2SwapInterval:
- return ProcDRI2SwapInterval(client);
- default:
- return BadRequest;
- }
-}
-
-static int
-SProcDRI2Connect(ClientPtr client)
-{
- REQUEST(xDRI2ConnectReq);
- xDRI2ConnectReply rep;
- int n;
-
- /* If the client is swapped, it's not local. Talk to the hand. */
-
- swaps(&stuff->length, n);
- if (sizeof(*stuff) / 4 != client->req_len)
- return BadLength;
-
- rep.sequenceNumber = client->sequence;
- swaps(&rep.sequenceNumber, n);
- rep.length = 0;
- rep.driverNameLength = 0;
- rep.deviceNameLength = 0;
-
- return Success;
-}
-
-static int
-SProcDRI2Dispatch (ClientPtr client)
-{
- REQUEST(xReq);
-
- /*
- * Only local clients are allowed DRI access, but remote clients
- * still need these requests to find out cleanly.
- */
- switch (stuff->data)
- {
- case X_DRI2QueryVersion:
- return ProcDRI2QueryVersion(client);
- case X_DRI2Connect:
- return SProcDRI2Connect(client);
- default:
- return BadRequest;
- }
-}
-
-int DRI2EventBase;
-
-static void
-DRI2ExtensionInit(void)
-{
- dri2Extension = AddExtension(DRI2_NAME,
- DRI2NumberEvents,
- DRI2NumberErrors,
- ProcDRI2Dispatch,
- SProcDRI2Dispatch,
- NULL,
- StandardMinorOpcode);
-
- DRI2EventBase = dri2Extension->eventBase;
-}
-
-extern Bool noDRI2Extension;
-
-_X_HIDDEN ExtensionModule dri2ExtensionModule = {
- DRI2ExtensionInit,
- DRI2_NAME,
- &noDRI2Extension,
- NULL,
- NULL
-};
+/*
+ * Copyright © 2008 Red Hat, Inc.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Soft-
+ * ware"), to deal in the Software without restriction, including without
+ * limitation the rights to use, copy, modify, merge, publish, distribute,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, provided that the above copyright
+ * notice(s) and this permission notice appear in all copies of the Soft-
+ * ware and that both the above copyright notice(s) and this permission
+ * notice appear in supporting documentation.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
+ * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABIL-
+ * ITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT OF THIRD PARTY
+ * RIGHTS. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR HOLDERS INCLUDED IN
+ * THIS NOTICE BE LIABLE FOR ANY CLAIM, OR ANY SPECIAL INDIRECT OR CONSE-
+ * QUENTIAL DAMAGES, OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
+ * DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
+ * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFOR-
+ * MANCE OF THIS SOFTWARE.
+ *
+ * Except as contained in this notice, the name of a copyright holder shall
+ * not be used in advertising or otherwise to promote the sale, use or
+ * other dealings in this Software without prior written authorization of
+ * the copyright holder.
+ *
+ * Authors:
+ * Kristian Høgsberg (krh@redhat.com)
+ */
+
+#ifdef HAVE_XORG_CONFIG_H
+#include <xorg-config.h>
+#endif
+
+#include <X11/X.h>
+#include <X11/Xproto.h>
+#include <X11/extensions/dri2proto.h>
+#include <X11/extensions/xfixeswire.h>
+#include "dixstruct.h"
+#include "scrnintstr.h"
+#include "pixmapstr.h"
+#include "extnsionst.h"
+#include "xfixes.h"
+#include "dri2.h"
+#include "protocol-versions.h"
+
+/* The only xf86 include */
+#include "xf86Module.h"
+
+static ExtensionEntry *dri2Extension;
+
+static Bool
+validDrawable(ClientPtr client, XID drawable, Mask access_mode,
+ DrawablePtr *pDrawable, int *status)
+{
+ *status = dixLookupDrawable(pDrawable, drawable, client,
+ M_DRAWABLE_WINDOW | M_DRAWABLE_PIXMAP,
+ access_mode);
+ if (*status != Success) {
+ client->errorValue = drawable;
+ return FALSE;
+ }
+
+ return TRUE;
+}
+
+static int
+ProcDRI2QueryVersion(ClientPtr client)
+{
+ REQUEST(xDRI2QueryVersionReq);
+ xDRI2QueryVersionReply rep;
+ int n;
+
+ if (client->swapped)
+ swaps(&stuff->length, n);
+
+ REQUEST_SIZE_MATCH(xDRI2QueryVersionReq);
+ rep.type = X_Reply;
+ rep.length = 0;
+ rep.sequenceNumber = client->sequence;
+ rep.majorVersion = dri2_major;
+ rep.minorVersion = dri2_minor;
+
+ if (client->swapped) {
+ swaps(&rep.sequenceNumber, n);
+ swapl(&rep.length, n);
+ swapl(&rep.majorVersion, n);
+ swapl(&rep.minorVersion, n);
+ }
+
+ WriteToClient(client, sizeof(xDRI2QueryVersionReply), &rep);
+
+ return Success;
+}
+
+static int
+ProcDRI2Connect(ClientPtr client)
+{
+ REQUEST(xDRI2ConnectReq);
+ xDRI2ConnectReply rep;
+ DrawablePtr pDraw;
+ int fd, status;
+ const char *driverName;
+ const char *deviceName;
+
+ REQUEST_SIZE_MATCH(xDRI2ConnectReq);
+ if (!validDrawable(client, stuff->window, DixGetAttrAccess,
+ &pDraw, &status))
+ return status;
+
+ rep.type = X_Reply;
+ rep.length = 0;
+ rep.sequenceNumber = client->sequence;
+ rep.driverNameLength = 0;
+ rep.deviceNameLength = 0;
+
+ if (!DRI2Connect(pDraw->pScreen,
+ stuff->driverType, &fd, &driverName, &deviceName))
+ goto fail;
+
+ rep.driverNameLength = strlen(driverName);
+ rep.deviceNameLength = strlen(deviceName);
+ rep.length = (rep.driverNameLength + 3) / 4 +
+ (rep.deviceNameLength + 3) / 4;
+
+ fail:
+ WriteToClient(client, sizeof(xDRI2ConnectReply), &rep);
+ WriteToClient(client, rep.driverNameLength, driverName);
+ WriteToClient(client, rep.deviceNameLength, deviceName);
+
+ return Success;
+}
+
+static int
+ProcDRI2Authenticate(ClientPtr client)
+{
+ REQUEST(xDRI2AuthenticateReq);
+ xDRI2AuthenticateReply rep;
+ DrawablePtr pDraw;
+ int status;
+
+ REQUEST_SIZE_MATCH(xDRI2AuthenticateReq);
+ if (!validDrawable(client, stuff->window, DixGetAttrAccess,
+ &pDraw, &status))
+ return status;
+
+ rep.type = X_Reply;
+ rep.sequenceNumber = client->sequence;
+ rep.length = 0;
+ rep.authenticated = DRI2Authenticate(pDraw->pScreen, stuff->magic);
+ WriteToClient(client, sizeof(xDRI2AuthenticateReply), &rep);
+
+ return Success;
+}
+
+static void
+DRI2InvalidateBuffersEvent(DrawablePtr pDraw, void *priv)
+{
+ xDRI2InvalidateBuffers event;
+ ClientPtr client = priv;
+
+ event.type = DRI2EventBase + DRI2_InvalidateBuffers;
+ event.drawable = pDraw->id;
+
+ WriteEventsToClient(client, 1, (xEvent *)&event);
+}
+
+static int
+ProcDRI2CreateDrawable(ClientPtr client)
+{
+ REQUEST(xDRI2CreateDrawableReq);
+ DrawablePtr pDrawable;
+ int status;
+
+ REQUEST_SIZE_MATCH(xDRI2CreateDrawableReq);
+
+ if (!validDrawable(client, stuff->drawable, DixAddAccess,
+ &pDrawable, &status))
+ return status;
+
+ status = DRI2CreateDrawable(client, pDrawable, stuff->drawable,
+ DRI2InvalidateBuffersEvent, client);
+ if (status != Success)
+ return status;
+
+ return Success;
+}
+
+static int
+ProcDRI2DestroyDrawable(ClientPtr client)
+{
+ REQUEST(xDRI2DestroyDrawableReq);
+ DrawablePtr pDrawable;
+ int status;
+
+ REQUEST_SIZE_MATCH(xDRI2DestroyDrawableReq);
+ if (!validDrawable(client, stuff->drawable, DixRemoveAccess,
+ &pDrawable, &status))
+ return status;
+
+ return Success;
+}
+
+
+static int
+send_buffers_reply(ClientPtr client, DrawablePtr pDrawable,
+ DRI2BufferPtr *buffers, int count, int width, int height)
+{
+ xDRI2GetBuffersReply rep;
+ int skip = 0;
+ int i;
+
+ if (buffers == NULL)
+ return BadAlloc;
+
+ if (pDrawable->type == DRAWABLE_WINDOW) {
+ for (i = 0; i < count; i++) {
+ /* Do not send the real front buffer of a window to the client.
+ */
+ if (buffers[i]->attachment == DRI2BufferFrontLeft) {
+ skip++;
+ continue;
+ }
+ }
+ }
+
+ rep.type = X_Reply;
+ rep.length = (count - skip) * sizeof(xDRI2Buffer) / 4;
+ rep.sequenceNumber = client->sequence;
+ rep.width = width;
+ rep.height = height;
+ rep.count = count - skip;
+ WriteToClient(client, sizeof(xDRI2GetBuffersReply), &rep);
+
+ for (i = 0; i < count; i++) {
+ xDRI2Buffer buffer;
+
+ /* Do not send the real front buffer of a window to the client.
+ */
+ if ((pDrawable->type == DRAWABLE_WINDOW)
+ && (buffers[i]->attachment == DRI2BufferFrontLeft)) {
+ continue;
+ }
+
+ buffer.attachment = buffers[i]->attachment;
+ buffer.name = buffers[i]->name;
+ buffer.pitch = buffers[i]->pitch;
+ buffer.cpp = buffers[i]->cpp;
+ buffer.flags = buffers[i]->flags;
+ WriteToClient(client, sizeof(xDRI2Buffer), &buffer);
+ }
+ return Success;
+}
+
+
+static int
+ProcDRI2GetBuffers(ClientPtr client)
+{
+ REQUEST(xDRI2GetBuffersReq);
+ DrawablePtr pDrawable;
+ DRI2BufferPtr *buffers;
+ int status, width, height, count;
+ unsigned int *attachments;
+
+ REQUEST_FIXED_SIZE(xDRI2GetBuffersReq, stuff->count * 4);
+ if (!validDrawable(client, stuff->drawable, DixReadAccess | DixWriteAccess,
+ &pDrawable, &status))
+ return status;
+
+ if (DRI2ThrottleClient(client, pDrawable))
+ return Success;
+
+ attachments = (unsigned int *) &stuff[1];
+ buffers = DRI2GetBuffers(pDrawable, &width, &height,
+ attachments, stuff->count, &count);
+
+
+ return send_buffers_reply(client, pDrawable, buffers, count, width, height);
+
+}
+
+static int
+ProcDRI2GetBuffersWithFormat(ClientPtr client)
+{
+ REQUEST(xDRI2GetBuffersReq);
+ DrawablePtr pDrawable;
+ DRI2BufferPtr *buffers;
+ int status, width, height, count;
+ unsigned int *attachments;
+
+ REQUEST_FIXED_SIZE(xDRI2GetBuffersReq, stuff->count * (2 * 4));
+ if (!validDrawable(client, stuff->drawable, DixReadAccess | DixWriteAccess,
+ &pDrawable, &status))
+ return status;
+
+ if (DRI2ThrottleClient(client, pDrawable))
+ return Success;
+
+ attachments = (unsigned int *) &stuff[1];
+ buffers = DRI2GetBuffersWithFormat(pDrawable, &width, &height,
+ attachments, stuff->count, &count);
+
+ return send_buffers_reply(client, pDrawable, buffers, count, width, height);
+}
+
+static int
+ProcDRI2CopyRegion(ClientPtr client)
+{
+ REQUEST(xDRI2CopyRegionReq);
+ xDRI2CopyRegionReply rep;
+ DrawablePtr pDrawable;
+ int status;
+ RegionPtr pRegion;
+
+ REQUEST_SIZE_MATCH(xDRI2CopyRegionReq);
+
+ if (!validDrawable(client, stuff->drawable, DixWriteAccess,
+ &pDrawable, &status))
+ return status;
+
+ VERIFY_REGION(pRegion, stuff->region, client, DixReadAccess);
+
+ status = DRI2CopyRegion(pDrawable, pRegion, stuff->dest, stuff->src);
+ if (status != Success)
+ return status;
+
+ /* CopyRegion needs to be a round trip to make sure the X server
+ * queues the swap buffer rendering commands before the DRI client
+ * continues rendering. The reply has a bitmask to signal the
+ * presense of optional return values as well, but we're not using
+ * that yet.
+ */
+
+ rep.type = X_Reply;
+ rep.length = 0;
+ rep.sequenceNumber = client->sequence;
+
+ WriteToClient(client, sizeof(xDRI2CopyRegionReply), &rep);
+
+ return Success;
+}
+
+static void
+load_swap_reply(xDRI2SwapBuffersReply *rep, CARD64 sbc)
+{
+ rep->swap_hi = sbc >> 32;
+ rep->swap_lo = sbc & 0xffffffff;
+}
+
+static CARD64
+vals_to_card64(CARD32 lo, CARD32 hi)
+{
+ return (CARD64)hi << 32 | lo;
+}
+
+static void
+DRI2SwapEvent(ClientPtr client, void *data, int type, CARD64 ust, CARD64 msc,
+ CARD32 sbc)
+{
+ xDRI2BufferSwapComplete2 event;
+ DrawablePtr pDrawable = data;
+
+ event.type = DRI2EventBase + DRI2_BufferSwapComplete;
+ event.event_type = type;
+ event.drawable = pDrawable->id;
+ event.ust_hi = (CARD64)ust >> 32;
+ event.ust_lo = ust & 0xffffffff;
+ event.msc_hi = (CARD64)msc >> 32;
+ event.msc_lo = msc & 0xffffffff;
+ event.sbc = sbc;
+
+ WriteEventsToClient(client, 1, (xEvent *)&event);
+}
+
+static int
+ProcDRI2SwapBuffers(ClientPtr client)
+{
+ REQUEST(xDRI2SwapBuffersReq);
+ xDRI2SwapBuffersReply rep;
+ DrawablePtr pDrawable;
+ CARD64 target_msc, divisor, remainder, swap_target;
+ int status;
+
+ REQUEST_SIZE_MATCH(xDRI2SwapBuffersReq);
+
+ if (!validDrawable(client, stuff->drawable,
+ DixReadAccess | DixWriteAccess, &pDrawable, &status))
+ return status;
+
+ /*
+ * Ensures an out of control client can't exhaust our swap queue, and
+ * also orders swaps.
+ */
+ if (DRI2ThrottleClient(client, pDrawable))
+ return Success;
+
+ target_msc = vals_to_card64(stuff->target_msc_lo, stuff->target_msc_hi);
+ divisor = vals_to_card64(stuff->divisor_lo, stuff->divisor_hi);
+ remainder = vals_to_card64(stuff->remainder_lo, stuff->remainder_hi);
+
+ status = DRI2SwapBuffers(client, pDrawable, target_msc, divisor, remainder,
+ &swap_target, DRI2SwapEvent, pDrawable);
+ if (status != Success)
+ return BadDrawable;
+
+ rep.type = X_Reply;
+ rep.length = 0;
+ rep.sequenceNumber = client->sequence;
+ load_swap_reply(&rep, swap_target);
+
+ WriteToClient(client, sizeof(xDRI2SwapBuffersReply), &rep);
+
+ return Success;
+}
+
+static void
+load_msc_reply(xDRI2MSCReply *rep, CARD64 ust, CARD64 msc, CARD64 sbc)
+{
+ rep->ust_hi = ust >> 32;
+ rep->ust_lo = ust & 0xffffffff;
+ rep->msc_hi = msc >> 32;
+ rep->msc_lo = msc & 0xffffffff;
+ rep->sbc_hi = sbc >> 32;
+ rep->sbc_lo = sbc & 0xffffffff;
+}
+
+static int
+ProcDRI2GetMSC(ClientPtr client)
+{
+ REQUEST(xDRI2GetMSCReq);
+ xDRI2MSCReply rep;
+ DrawablePtr pDrawable;
+ CARD64 ust, msc, sbc;
+ int status;
+
+ REQUEST_SIZE_MATCH(xDRI2GetMSCReq);
+
+ if (!validDrawable(client, stuff->drawable, DixReadAccess, &pDrawable,
+ &status))
+ return status;
+
+ status = DRI2GetMSC(pDrawable, &ust, &msc, &sbc);
+ if (status != Success)
+ return status;
+
+ rep.type = X_Reply;
+ rep.length = 0;
+ rep.sequenceNumber = client->sequence;
+ load_msc_reply(&rep, ust, msc, sbc);
+
+ WriteToClient(client, sizeof(xDRI2MSCReply), &rep);
+
+ return Success;
+}
+
+static int
+ProcDRI2WaitMSC(ClientPtr client)
+{
+ REQUEST(xDRI2WaitMSCReq);
+ DrawablePtr pDrawable;
+ CARD64 target, divisor, remainder;
+ int status;
+
+ /* FIXME: in restart case, client may be gone at this point */
+
+ REQUEST_SIZE_MATCH(xDRI2WaitMSCReq);
+
+ if (!validDrawable(client, stuff->drawable, DixReadAccess, &pDrawable,
+ &status))
+ return status;
+
+ target = vals_to_card64(stuff->target_msc_lo, stuff->target_msc_hi);
+ divisor = vals_to_card64(stuff->divisor_lo, stuff->divisor_hi);
+ remainder = vals_to_card64(stuff->remainder_lo, stuff->remainder_hi);
+
+ status = DRI2WaitMSC(client, pDrawable, target, divisor, remainder);
+ if (status != Success)
+ return status;
+
+ return Success;
+}
+
+int
+ProcDRI2WaitMSCReply(ClientPtr client, CARD64 ust, CARD64 msc, CARD64 sbc)
+{
+ xDRI2MSCReply rep;
+
+ rep.type = X_Reply;
+ rep.length = 0;
+ rep.sequenceNumber = client->sequence;
+ load_msc_reply(&rep, ust, msc, sbc);
+
+ WriteToClient(client, sizeof(xDRI2MSCReply), &rep);
+
+ return Success;
+}
+
+static int
+ProcDRI2SwapInterval(ClientPtr client)
+{
+ REQUEST(xDRI2SwapIntervalReq);
+ DrawablePtr pDrawable;
+ int status;
+
+ /* FIXME: in restart case, client may be gone at this point */
+
+ REQUEST_SIZE_MATCH(xDRI2SwapIntervalReq);
+
+ if (!validDrawable(client, stuff->drawable, DixReadAccess | DixWriteAccess,
+ &pDrawable, &status))
+ return status;
+
+ DRI2SwapInterval(pDrawable, stuff->interval);
+
+ return Success;
+}
+
+static int
+ProcDRI2WaitSBC(ClientPtr client)
+{
+ REQUEST(xDRI2WaitSBCReq);
+ DrawablePtr pDrawable;
+ CARD64 target;
+ int status;
+
+ REQUEST_SIZE_MATCH(xDRI2WaitSBCReq);
+
+ if (!validDrawable(client, stuff->drawable, DixReadAccess, &pDrawable,
+ &status))
+ return status;
+
+ target = vals_to_card64(stuff->target_sbc_lo, stuff->target_sbc_hi);
+ status = DRI2WaitSBC(client, pDrawable, target);
+
+ return status;
+}
+
+static int
+ProcDRI2Dispatch (ClientPtr client)
+{
+ REQUEST(xReq);
+
+ switch (stuff->data) {
+ case X_DRI2QueryVersion:
+ return ProcDRI2QueryVersion(client);
+ }
+
+ if (!LocalClient(client))
+ return BadRequest;
+
+ switch (stuff->data) {
+ case X_DRI2Connect:
+ return ProcDRI2Connect(client);
+ case X_DRI2Authenticate:
+ return ProcDRI2Authenticate(client);
+ case X_DRI2CreateDrawable:
+ return ProcDRI2CreateDrawable(client);
+ case X_DRI2DestroyDrawable:
+ return ProcDRI2DestroyDrawable(client);
+ case X_DRI2GetBuffers:
+ return ProcDRI2GetBuffers(client);
+ case X_DRI2CopyRegion:
+ return ProcDRI2CopyRegion(client);
+ case X_DRI2GetBuffersWithFormat:
+ return ProcDRI2GetBuffersWithFormat(client);
+ case X_DRI2SwapBuffers:
+ return ProcDRI2SwapBuffers(client);
+ case X_DRI2GetMSC:
+ return ProcDRI2GetMSC(client);
+ case X_DRI2WaitMSC:
+ return ProcDRI2WaitMSC(client);
+ case X_DRI2WaitSBC:
+ return ProcDRI2WaitSBC(client);
+ case X_DRI2SwapInterval:
+ return ProcDRI2SwapInterval(client);
+ default:
+ return BadRequest;
+ }
+}
+
+static int
+SProcDRI2Connect(ClientPtr client)
+{
+ REQUEST(xDRI2ConnectReq);
+ xDRI2ConnectReply rep;
+ int n;
+
+ /* If the client is swapped, it's not local. Talk to the hand. */
+
+ swaps(&stuff->length, n);
+ if (sizeof(*stuff) / 4 != client->req_len)
+ return BadLength;
+
+ rep.sequenceNumber = client->sequence;
+ swaps(&rep.sequenceNumber, n);
+ rep.length = 0;
+ rep.driverNameLength = 0;
+ rep.deviceNameLength = 0;
+
+ return Success;
+}
+
+static int
+SProcDRI2Dispatch (ClientPtr client)
+{
+ REQUEST(xReq);
+
+ /*
+ * Only local clients are allowed DRI access, but remote clients
+ * still need these requests to find out cleanly.
+ */
+ switch (stuff->data)
+ {
+ case X_DRI2QueryVersion:
+ return ProcDRI2QueryVersion(client);
+ case X_DRI2Connect:
+ return SProcDRI2Connect(client);
+ default:
+ return BadRequest;
+ }
+}
+
+int DRI2EventBase;
+
+static void
+DRI2ExtensionInit(void)
+{
+ dri2Extension = AddExtension(DRI2_NAME,
+ DRI2NumberEvents,
+ DRI2NumberErrors,
+ ProcDRI2Dispatch,
+ SProcDRI2Dispatch,
+ NULL,
+ StandardMinorOpcode);
+
+ DRI2EventBase = dri2Extension->eventBase;
+}
+
+extern Bool noDRI2Extension;
+
+_X_HIDDEN ExtensionModule dri2ExtensionModule = {
+ DRI2ExtensionInit,
+ DRI2_NAME,
+ &noDRI2Extension,
+ NULL,
+ NULL
+};
diff --git a/xorg-server/hw/xfree86/loader/Makefile.am b/xorg-server/hw/xfree86/loader/Makefile.am
index 9cb27a2bd..07529b7b0 100644
--- a/xorg-server/hw/xfree86/loader/Makefile.am
+++ b/xorg-server/hw/xfree86/loader/Makefile.am
@@ -9,11 +9,7 @@ AM_CFLAGS = $(DIX_CFLAGS) $(XORG_CFLAGS)
EXTRA_DIST = \
loader.h \
- loaderProcs.h \
- sdksyms.sh
-
-nodist_libloader_la_SOURCES = \
- sdksyms.c
+ loaderProcs.h
libloader_la_SOURCES = \
loader.c \
@@ -23,11 +19,3 @@ libloader_la_SOURCES = \
os.c
libloader_la_LIBADD = $(DLOPEN_LIBS)
-
-CLEANFILES = sdksyms.c sdksyms.dep
-
-sdksyms.dep sdksyms.c: sdksyms.sh $(top_builddir)/include/do-not-use-config.h
- CPP='$(CPP)' AWK='$(AWK)' $(srcdir)/sdksyms.sh $(top_srcdir) $(AM_CFLAGS) $(CFLAGS) $(INCLUDES)
-
-SDKSYMS_DEP = sdksyms.dep
-include $(SDKSYMS_DEP)
diff --git a/xorg-server/hw/xfree86/os-support/Makefile.am b/xorg-server/hw/xfree86/os-support/Makefile.am
index 3af4328ff..348b7ffec 100644
--- a/xorg-server/hw/xfree86/os-support/Makefile.am
+++ b/xorg-server/hw/xfree86/os-support/Makefile.am
@@ -9,18 +9,13 @@ EXTRA_DIST = int10Defines.h xf86OSpriv.h
# as one library, otherwise libtool will actively defeat your attempts to
# list them multiple times on the link line.
noinst_LTLIBRARIES = libxorgos.la
-libxorgos_la_SOURCES = xorgos.c
+libxorgos_la_SOURCES =
libxorgos_la_LIBADD = @XORG_OS_SUBDIR@/lib@XORG_OS_SUBDIR@.la \
bus/libbus.la \
misc/libmisc.la
AM_CFLAGS = $(DIX_CFLAGS)
-xorgos.c:
- touch $@
-
-DISTCLEANFILES = xorgos.c
-
# FIXME: These don't seem to be used anywhere
EXTRA_DIST += \
shared/bios_devmem.c
diff --git a/xorg-server/hw/xfree86/os-support/shared/posix_tty.c b/xorg-server/hw/xfree86/os-support/shared/posix_tty.c
index 97860d0f2..fb8386022 100644
--- a/xorg-server/hw/xfree86/os-support/shared/posix_tty.c
+++ b/xorg-server/hw/xfree86/os-support/shared/posix_tty.c
@@ -1,655 +1,655 @@
-/*
- * Copyright 1993-2003 by The XFree86 Project, Inc.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice shall be included in
- * all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
- * THE XFREE86 PROJECT BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
- * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF
- * OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
- * SOFTWARE.
- *
- * Except as contained in this notice, the name of the XFree86 Project shall
- * not be used in advertising or otherwise to promote the sale, use or other
- * dealings in this Software without prior written authorization from the
- * XFree86 Project.
- */
-/*
- *
- * Copyright (c) 1997 Metro Link Incorporated
- *
- * Permission is hereby granted, free of charge, to any person obtaining a
- * copy of this software and associated documentation files (the "Software"),
- * to deal in the Software without restriction, including without limitation
- * the rights to use, copy, modify, merge, publish, distribute, sublicense,
- * and/or sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice shall be included in
- * all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
- * THE X CONSORTIUM BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
- * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF
- * OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
- * SOFTWARE.
- *
- * Except as contained in this notice, the name of the Metro Link shall not be
- * used in advertising or otherwise to promote the sale, use or other dealings
- * in this Software without prior written authorization from Metro Link.
- *
- */
-
-#ifdef HAVE_XORG_CONFIG_H
-#include <xorg-config.h>
-#endif
-
-#include <X11/X.h>
-#include "xf86.h"
-#include "xf86Priv.h"
-#include "xf86_OSlib.h"
-
-static int
-GetBaud (int baudrate)
-{
-#ifdef B300
- if (baudrate == 300)
- return B300;
-#endif
-#ifdef B1200
- if (baudrate == 1200)
- return B1200;
-#endif
-#ifdef B2400
- if (baudrate == 2400)
- return B2400;
-#endif
-#ifdef B4800
- if (baudrate == 4800)
- return B4800;
-#endif
-#ifdef B9600
- if (baudrate == 9600)
- return B9600;
-#endif
-#ifdef B19200
- if (baudrate == 19200)
- return B19200;
-#endif
-#ifdef B38400
- if (baudrate == 38400)
- return B38400;
-#endif
-#ifdef B57600
- if (baudrate == 57600)
- return B57600;
-#endif
-#ifdef B115200
- if (baudrate == 115200)
- return B115200;
-#endif
-#ifdef B230400
- if (baudrate == 230400)
- return B230400;
-#endif
-#ifdef B460800
- if (baudrate == 460800)
- return B460800;
-#endif
- return 0;
-}
-
-int
-xf86OpenSerial (pointer options)
-{
- struct termios t;
- int fd, i;
- char *dev;
-
- dev = xf86SetStrOption (options, "Device", NULL);
- if (!dev)
- {
- xf86Msg (X_ERROR, "xf86OpenSerial: No Device specified.\n");
- return -1;
- }
-
- SYSCALL (fd = open (dev, O_RDWR | O_NONBLOCK));
- if (fd == -1)
- {
- xf86Msg (X_ERROR,
- "xf86OpenSerial: Cannot open device %s\n\t%s.\n",
- dev, strerror (errno));
- free(dev);
- return -1;
- }
-
- if (!isatty (fd))
- {
- /* Allow non-tty devices to be opened. */
- free(dev);
- return fd;
- }
-
- /* set up default port parameters */
- SYSCALL (tcgetattr (fd, &t));
- t.c_iflag &= ~(IGNBRK|BRKINT|PARMRK|ISTRIP|INLCR\
- |IGNCR|ICRNL|IXON);
- t.c_oflag &= ~OPOST;
- t.c_lflag &= ~(ECHO|ECHONL|ICANON|ISIG|IEXTEN);
- t.c_cflag &= ~(CSIZE|PARENB);
- t.c_cflag |= CS8|CLOCAL;
-
- cfsetispeed (&t, B9600);
- cfsetospeed (&t, B9600);
- t.c_cc[VMIN] = 1;
- t.c_cc[VTIME] = 0;
-
- SYSCALL (tcsetattr (fd, TCSANOW, &t));
-
- if (xf86SetSerial (fd, options) == -1)
- {
- SYSCALL (close (fd));
- free(dev);
- return -1;
- }
-
- SYSCALL (i = fcntl (fd, F_GETFL, 0));
- if (i == -1)
- {
- SYSCALL (close (fd));
- free(dev);
- return -1;
- }
- i &= ~O_NONBLOCK;
- SYSCALL (i = fcntl (fd, F_SETFL, i));
- if (i == -1)
- {
- SYSCALL (close (fd));
- free(dev);
- return -1;
- }
- free(dev);
- return fd;
-}
-
-int
-xf86SetSerial (int fd, pointer options)
-{
- struct termios t;
- int val;
- const char *s;
- int baud, r;
-
- if (fd < 0)
- return -1;
-
- /* Don't try to set parameters for non-tty devices. */
- if (!isatty(fd))
- return 0;
-
- SYSCALL (tcgetattr (fd, &t));
-
- if ((val = xf86SetIntOption (options, "BaudRate", 0)))
- {
- if ((baud = GetBaud (val)))
- {
- cfsetispeed (&t, baud);
- cfsetospeed (&t, baud);
- }
- else
- {
- xf86Msg (X_ERROR,
- "Invalid Option BaudRate value: %d\n", val);
- return -1;
- }
- }
-
- if ((val = xf86SetIntOption (options, "StopBits", 0)))
- {
- switch (val)
- {
- case 1:
- t.c_cflag &= ~(CSTOPB);
- break;
- case 2:
- t.c_cflag |= CSTOPB;
- break;
- default:
- xf86Msg (X_ERROR,
- "Invalid Option StopBits value: %d\n", val);
- return -1;
- break;
- }
- }
-
- if ((val = xf86SetIntOption (options, "DataBits", 0)))
- {
- switch (val)
- {
- case 5:
- t.c_cflag &= ~(CSIZE);
- t.c_cflag |= CS5;
- break;
- case 6:
- t.c_cflag &= ~(CSIZE);
- t.c_cflag |= CS6;
- break;
- case 7:
- t.c_cflag &= ~(CSIZE);
- t.c_cflag |= CS7;
- break;
- case 8:
- t.c_cflag &= ~(CSIZE);
- t.c_cflag |= CS8;
- break;
- default:
- xf86Msg (X_ERROR,
- "Invalid Option DataBits value: %d\n", val);
- return -1;
- break;
- }
- }
-
- if ((s = xf86SetStrOption (options, "Parity", NULL)))
- {
- if (xf86NameCmp (s, "Odd") == 0)
- {
- t.c_cflag |= PARENB | PARODD;
- }
- else if (xf86NameCmp (s, "Even") == 0)
- {
- t.c_cflag |= PARENB;
- t.c_cflag &= ~(PARODD);
- }
- else if (xf86NameCmp (s, "None") == 0)
- {
- t.c_cflag &= ~(PARENB);
- }
- else
- {
- xf86Msg (X_ERROR, "Invalid Option Parity value: %s\n",
- s);
- return -1;
- }
- }
-
- if ((val = xf86SetIntOption (options, "Vmin", -1)) != -1)
- {
- t.c_cc[VMIN] = val;
- }
- if ((val = xf86SetIntOption (options, "Vtime", -1)) != -1)
- {
- t.c_cc[VTIME] = val;
- }
-
- if ((s = xf86SetStrOption (options, "FlowControl", NULL)))
- {
- xf86MarkOptionUsedByName (options, "FlowControl");
- if (xf86NameCmp (s, "Xoff") == 0)
- {
- t.c_iflag |= IXOFF;
- }
- else if (xf86NameCmp (s, "Xon") == 0)
- {
- t.c_iflag |= IXON;
- }
- else if (xf86NameCmp (s, "XonXoff") == 0)
- {
- t.c_iflag |= IXON|IXOFF;
- }
- else if (xf86NameCmp (s, "None") == 0)
- {
- t.c_iflag &= ~(IXON | IXOFF);
- }
- else
- {
- xf86Msg (X_ERROR,
- "Invalid Option FlowControl value: %s\n", s);
- return -1;
- }
- }
-
- if ((xf86SetBoolOption (options, "ClearDTR", FALSE)))
- {
-#ifdef CLEARDTR_SUPPORT
-# if defined(TIOCMBIC)
- val = TIOCM_DTR;
- SYSCALL (ioctl(fd, TIOCMBIC, &val));
-# else
- SYSCALL (ioctl(fd, TIOCCDTR, NULL));
-# endif
-#else
- xf86Msg (X_WARNING,
- "Option ClearDTR not supported on this OS\n");
- return -1;
-#endif
- xf86MarkOptionUsedByName (options, "ClearDTR");
- }
-
- if ((xf86SetBoolOption (options, "ClearRTS", FALSE)))
- {
- xf86Msg (X_WARNING,
- "Option ClearRTS not supported on this OS\n");
- return -1;
- xf86MarkOptionUsedByName (options, "ClearRTS");
- }
-
- SYSCALL (r = tcsetattr (fd, TCSANOW, &t));
- return r;
-}
-
-int
-xf86SetSerialSpeed (int fd, int speed)
-{
- struct termios t;
- int baud, r;
-
- if (fd < 0)
- return -1;
-
- /* Don't try to set parameters for non-tty devices. */
- if (!isatty(fd))
- return 0;
-
- SYSCALL (tcgetattr (fd, &t));
-
- if ((baud = GetBaud (speed)))
- {
- cfsetispeed (&t, baud);
- cfsetospeed (&t, baud);
- }
- else
- {
- xf86Msg (X_ERROR,
- "Invalid Option BaudRate value: %d\n", speed);
- return -1;
- }
-
- SYSCALL (r = tcsetattr (fd, TCSANOW, &t));
- return r;
-}
-
-int
-xf86ReadSerial (int fd, void *buf, int count)
-{
- int r;
- int i;
-
- SYSCALL (r = read (fd, buf, count));
- DebugF("ReadingSerial: 0x%x",
- (unsigned char)*(((unsigned char *)buf)));
- for (i = 1; i < r; i++)
- DebugF(", 0x%x",(unsigned char)*(((unsigned char *)buf) + i));
- DebugF("\n");
- return r;
-}
-
-int
-xf86WriteSerial (int fd, const void *buf, int count)
-{
- int r;
- int i;
-
- DebugF("WritingSerial: 0x%x",(unsigned char)*(((unsigned char *)buf)));
- for (i = 1; i < count; i++)
- ErrorF(", 0x%x",(unsigned char)*(((unsigned char *)buf) + i));
- DebugF("\n");
- SYSCALL (r = write (fd, buf, count));
- return r;
-}
-
-int
-xf86CloseSerial (int fd)
-{
- int r;
-
- SYSCALL (r = close (fd));
- return r;
-}
-
-int
-xf86WaitForInput (int fd, int timeout)
-{
- fd_set readfds;
- struct timeval to;
- int r;
-
- FD_ZERO(&readfds);
-
- if (fd >= 0) {
- FD_SET(fd, &readfds);
- }
-
- to.tv_sec = timeout / 1000000;
- to.tv_usec = timeout % 1000000;
-
- if (fd >= 0) {
- SYSCALL (r = select (FD_SETSIZE, &readfds, NULL, NULL, &to));
- }
- else {
- SYSCALL (r = select (FD_SETSIZE, NULL, NULL, NULL, &to));
- }
- xf86ErrorFVerb (9,"select returned %d\n", r);
- return r;
-}
-
-int
-xf86SerialSendBreak (int fd, int duration)
-{
- int r;
-
- SYSCALL (r = tcsendbreak (fd, duration));
- return r;
-
-}
-
-int
-xf86FlushInput(int fd)
-{
- fd_set fds;
- struct timeval timeout;
- char c[4];
-
- DebugF("FlushingSerial\n");
- if (tcflush(fd, TCIFLUSH) == 0)
- return 0;
-
- timeout.tv_sec = 0;
- timeout.tv_usec = 0;
- FD_ZERO(&fds);
- FD_SET(fd, &fds);
- while (select(FD_SETSIZE, &fds, NULL, NULL, &timeout) > 0) {
- if (read(fd, &c, sizeof(c)) < 1)
- return 0;
- FD_ZERO(&fds);
- FD_SET(fd, &fds);
- }
- return 0;
-}
-
-static struct states {
- int xf;
- int os;
-} modemStates[] = {
-#ifdef TIOCM_LE
- { XF86_M_LE, TIOCM_LE },
-#endif
-#ifdef TIOCM_DTR
- { XF86_M_DTR, TIOCM_DTR },
-#endif
-#ifdef TIOCM_RTS
- { XF86_M_RTS, TIOCM_RTS },
-#endif
-#ifdef TIOCM_ST
- { XF86_M_ST, TIOCM_ST },
-#endif
-#ifdef TIOCM_SR
- { XF86_M_SR, TIOCM_SR },
-#endif
-#ifdef TIOCM_CTS
- { XF86_M_CTS, TIOCM_CTS },
-#endif
-#ifdef TIOCM_CAR
- { XF86_M_CAR, TIOCM_CAR },
-#elif defined(TIOCM_CD)
- { XF86_M_CAR, TIOCM_CD },
-#endif
-#ifdef TIOCM_RNG
- { XF86_M_RNG, TIOCM_RNG },
-#elif defined(TIOCM_RI)
- { XF86_M_CAR, TIOCM_RI },
-#endif
-#ifdef TIOCM_DSR
- { XF86_M_DSR, TIOCM_DSR },
-#endif
-};
-
-static int numStates = sizeof(modemStates) / sizeof(modemStates[0]);
-
-static int
-xf2osState(int state)
-{
- int i;
- int ret = 0;
-
- for (i = 0; i < numStates; i++)
- if (state & modemStates[i].xf)
- ret |= modemStates[i].os;
- return ret;
-}
-
-static int
-os2xfState(int state)
-{
- int i;
- int ret = 0;
-
- for (i = 0; i < numStates; i++)
- if (state & modemStates[i].os)
- ret |= modemStates[i].xf;
- return ret;
-}
-
-static int
-getOsStateMask(void)
-{
- int i;
- int ret = 0;
- for (i = 0; i < numStates; i++)
- ret |= modemStates[i].os;
- return ret;
-}
-
-static int osStateMask = 0;
-
-int
-xf86SetSerialModemState(int fd, int state)
-{
- int ret;
- int s;
-
- if (fd < 0)
- return -1;
-
- /* Don't try to set parameters for non-tty devices. */
- if (!isatty(fd))
- return 0;
-
-#ifndef TIOCMGET
- return -1;
-#else
- if (!osStateMask)
- osStateMask = getOsStateMask();
-
- state = xf2osState(state);
- SYSCALL((ret = ioctl(fd, TIOCMGET, &s)));
- if (ret < 0)
- return -1;
- s &= ~osStateMask;
- s |= state;
- SYSCALL((ret = ioctl(fd, TIOCMSET, &s)));
- if (ret < 0)
- return -1;
- else
- return 0;
-#endif
-}
-
-int
-xf86GetSerialModemState(int fd)
-{
- int ret;
- int s;
-
- if (fd < 0)
- return -1;
-
- /* Don't try to set parameters for non-tty devices. */
- if (!isatty(fd))
- return 0;
-
-#ifndef TIOCMGET
- return -1;
-#else
- SYSCALL((ret = ioctl(fd, TIOCMGET, &s)));
- if (ret < 0)
- return -1;
- return os2xfState(s);
-#endif
-}
-
-int
-xf86SerialModemSetBits(int fd, int bits)
-{
- int ret;
- int s;
-
- if (fd < 0)
- return -1;
-
- /* Don't try to set parameters for non-tty devices. */
- if (!isatty(fd))
- return 0;
-
-#ifndef TIOCMGET
- return -1;
-#else
- s = xf2osState(bits);
- SYSCALL((ret = ioctl(fd, TIOCMBIS, &s)));
- return ret;
-#endif
-}
-
-int
-xf86SerialModemClearBits(int fd, int bits)
-{
- int ret;
- int s;
-
- if (fd < 0)
- return -1;
-
- /* Don't try to set parameters for non-tty devices. */
- if (!isatty(fd))
- return 0;
-
-#ifndef TIOCMGET
- return -1;
-#else
- s = xf2osState(bits);
- SYSCALL((ret = ioctl(fd, TIOCMBIC, &s)));
- return ret;
-#endif
-}
+/*
+ * Copyright 1993-2003 by The XFree86 Project, Inc.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
+ * THE XFREE86 PROJECT BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
+ * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF
+ * OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+ * SOFTWARE.
+ *
+ * Except as contained in this notice, the name of the XFree86 Project shall
+ * not be used in advertising or otherwise to promote the sale, use or other
+ * dealings in this Software without prior written authorization from the
+ * XFree86 Project.
+ */
+/*
+ *
+ * Copyright (c) 1997 Metro Link Incorporated
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
+ * THE X CONSORTIUM BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
+ * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF
+ * OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+ * SOFTWARE.
+ *
+ * Except as contained in this notice, the name of the Metro Link shall not be
+ * used in advertising or otherwise to promote the sale, use or other dealings
+ * in this Software without prior written authorization from Metro Link.
+ *
+ */
+
+#ifdef HAVE_XORG_CONFIG_H
+#include <xorg-config.h>
+#endif
+
+#include <X11/X.h>
+#include "xf86.h"
+#include "xf86Priv.h"
+#include "xf86_OSlib.h"
+
+static int
+GetBaud (int baudrate)
+{
+#ifdef B300
+ if (baudrate == 300)
+ return B300;
+#endif
+#ifdef B1200
+ if (baudrate == 1200)
+ return B1200;
+#endif
+#ifdef B2400
+ if (baudrate == 2400)
+ return B2400;
+#endif
+#ifdef B4800
+ if (baudrate == 4800)
+ return B4800;
+#endif
+#ifdef B9600
+ if (baudrate == 9600)
+ return B9600;
+#endif
+#ifdef B19200
+ if (baudrate == 19200)
+ return B19200;
+#endif
+#ifdef B38400
+ if (baudrate == 38400)
+ return B38400;
+#endif
+#ifdef B57600
+ if (baudrate == 57600)
+ return B57600;
+#endif
+#ifdef B115200
+ if (baudrate == 115200)
+ return B115200;
+#endif
+#ifdef B230400
+ if (baudrate == 230400)
+ return B230400;
+#endif
+#ifdef B460800
+ if (baudrate == 460800)
+ return B460800;
+#endif
+ return 0;
+}
+
+int
+xf86OpenSerial (pointer options)
+{
+ struct termios t;
+ int fd, i;
+ char *dev;
+
+ dev = xf86SetStrOption (options, "Device", NULL);
+ if (!dev)
+ {
+ xf86Msg (X_ERROR, "xf86OpenSerial: No Device specified.\n");
+ return -1;
+ }
+
+ SYSCALL (fd = open (dev, O_RDWR | O_NONBLOCK));
+ if (fd == -1)
+ {
+ xf86Msg (X_ERROR,
+ "xf86OpenSerial: Cannot open device %s\n\t%s.\n",
+ dev, strerror (errno));
+ free(dev);
+ return -1;
+ }
+
+ if (!isatty (fd))
+ {
+ /* Allow non-tty devices to be opened. */
+ free(dev);
+ return fd;
+ }
+
+ /* set up default port parameters */
+ SYSCALL (tcgetattr (fd, &t));
+ t.c_iflag &= ~(IGNBRK|BRKINT|PARMRK|ISTRIP|INLCR\
+ |IGNCR|ICRNL|IXON);
+ t.c_oflag &= ~OPOST;
+ t.c_lflag &= ~(ECHO|ECHONL|ICANON|ISIG|IEXTEN);
+ t.c_cflag &= ~(CSIZE|PARENB);
+ t.c_cflag |= CS8|CLOCAL;
+
+ cfsetispeed (&t, B9600);
+ cfsetospeed (&t, B9600);
+ t.c_cc[VMIN] = 1;
+ t.c_cc[VTIME] = 0;
+
+ SYSCALL (tcsetattr (fd, TCSANOW, &t));
+
+ if (xf86SetSerial (fd, options) == -1)
+ {
+ SYSCALL (close (fd));
+ free(dev);
+ return -1;
+ }
+
+ SYSCALL (i = fcntl (fd, F_GETFL, 0));
+ if (i == -1)
+ {
+ SYSCALL (close (fd));
+ free(dev);
+ return -1;
+ }
+ i &= ~O_NONBLOCK;
+ SYSCALL (i = fcntl (fd, F_SETFL, i));
+ if (i == -1)
+ {
+ SYSCALL (close (fd));
+ free(dev);
+ return -1;
+ }
+ free(dev);
+ return fd;
+}
+
+int
+xf86SetSerial (int fd, pointer options)
+{
+ struct termios t;
+ int val;
+ const char *s;
+ int baud, r;
+
+ if (fd < 0)
+ return -1;
+
+ /* Don't try to set parameters for non-tty devices. */
+ if (!isatty(fd))
+ return 0;
+
+ SYSCALL (tcgetattr (fd, &t));
+
+ if ((val = xf86SetIntOption (options, "BaudRate", 0)))
+ {
+ if ((baud = GetBaud (val)))
+ {
+ cfsetispeed (&t, baud);
+ cfsetospeed (&t, baud);
+ }
+ else
+ {
+ xf86Msg (X_ERROR,
+ "Invalid Option BaudRate value: %d\n", val);
+ return -1;
+ }
+ }
+
+ if ((val = xf86SetIntOption (options, "StopBits", 0)))
+ {
+ switch (val)
+ {
+ case 1:
+ t.c_cflag &= ~(CSTOPB);
+ break;
+ case 2:
+ t.c_cflag |= CSTOPB;
+ break;
+ default:
+ xf86Msg (X_ERROR,
+ "Invalid Option StopBits value: %d\n", val);
+ return -1;
+ break;
+ }
+ }
+
+ if ((val = xf86SetIntOption (options, "DataBits", 0)))
+ {
+ switch (val)
+ {
+ case 5:
+ t.c_cflag &= ~(CSIZE);
+ t.c_cflag |= CS5;
+ break;
+ case 6:
+ t.c_cflag &= ~(CSIZE);
+ t.c_cflag |= CS6;
+ break;
+ case 7:
+ t.c_cflag &= ~(CSIZE);
+ t.c_cflag |= CS7;
+ break;
+ case 8:
+ t.c_cflag &= ~(CSIZE);
+ t.c_cflag |= CS8;
+ break;
+ default:
+ xf86Msg (X_ERROR,
+ "Invalid Option DataBits value: %d\n", val);
+ return -1;
+ break;
+ }
+ }
+
+ if ((s = xf86SetStrOption (options, "Parity", NULL)))
+ {
+ if (xf86NameCmp (s, "Odd") == 0)
+ {
+ t.c_cflag |= PARENB | PARODD;
+ }
+ else if (xf86NameCmp (s, "Even") == 0)
+ {
+ t.c_cflag |= PARENB;
+ t.c_cflag &= ~(PARODD);
+ }
+ else if (xf86NameCmp (s, "None") == 0)
+ {
+ t.c_cflag &= ~(PARENB);
+ }
+ else
+ {
+ xf86Msg (X_ERROR, "Invalid Option Parity value: %s\n",
+ s);
+ return -1;
+ }
+ }
+
+ if ((val = xf86SetIntOption (options, "Vmin", -1)) != -1)
+ {
+ t.c_cc[VMIN] = val;
+ }
+ if ((val = xf86SetIntOption (options, "Vtime", -1)) != -1)
+ {
+ t.c_cc[VTIME] = val;
+ }
+
+ if ((s = xf86SetStrOption (options, "FlowControl", NULL)))
+ {
+ xf86MarkOptionUsedByName (options, "FlowControl");
+ if (xf86NameCmp (s, "Xoff") == 0)
+ {
+ t.c_iflag |= IXOFF;
+ }
+ else if (xf86NameCmp (s, "Xon") == 0)
+ {
+ t.c_iflag |= IXON;
+ }
+ else if (xf86NameCmp (s, "XonXoff") == 0)
+ {
+ t.c_iflag |= IXON|IXOFF;
+ }
+ else if (xf86NameCmp (s, "None") == 0)
+ {
+ t.c_iflag &= ~(IXON | IXOFF);
+ }
+ else
+ {
+ xf86Msg (X_ERROR,
+ "Invalid Option FlowControl value: %s\n", s);
+ return -1;
+ }
+ }
+
+ if ((xf86SetBoolOption (options, "ClearDTR", FALSE)))
+ {
+#ifdef CLEARDTR_SUPPORT
+# if defined(TIOCMBIC)
+ val = TIOCM_DTR;
+ SYSCALL (ioctl(fd, TIOCMBIC, &val));
+# else
+ SYSCALL (ioctl(fd, TIOCCDTR, NULL));
+# endif
+#else
+ xf86Msg (X_WARNING,
+ "Option ClearDTR not supported on this OS\n");
+ return -1;
+#endif
+ xf86MarkOptionUsedByName (options, "ClearDTR");
+ }
+
+ if ((xf86SetBoolOption (options, "ClearRTS", FALSE)))
+ {
+ xf86Msg (X_WARNING,
+ "Option ClearRTS not supported on this OS\n");
+ return -1;
+ xf86MarkOptionUsedByName (options, "ClearRTS");
+ }
+
+ SYSCALL (r = tcsetattr (fd, TCSANOW, &t));
+ return r;
+}
+
+int
+xf86SetSerialSpeed (int fd, int speed)
+{
+ struct termios t;
+ int baud, r;
+
+ if (fd < 0)
+ return -1;
+
+ /* Don't try to set parameters for non-tty devices. */
+ if (!isatty(fd))
+ return 0;
+
+ SYSCALL (tcgetattr (fd, &t));
+
+ if ((baud = GetBaud (speed)))
+ {
+ cfsetispeed (&t, baud);
+ cfsetospeed (&t, baud);
+ }
+ else
+ {
+ xf86Msg (X_ERROR,
+ "Invalid Option BaudRate value: %d\n", speed);
+ return -1;
+ }
+
+ SYSCALL (r = tcsetattr (fd, TCSANOW, &t));
+ return r;
+}
+
+int
+xf86ReadSerial (int fd, void *buf, int count)
+{
+ int r;
+ int i;
+
+ SYSCALL (r = read (fd, buf, count));
+ DebugF("ReadingSerial: 0x%x",
+ (unsigned char)*(((unsigned char *)buf)));
+ for (i = 1; i < r; i++)
+ DebugF(", 0x%x",(unsigned char)*(((unsigned char *)buf) + i));
+ DebugF("\n");
+ return r;
+}
+
+int
+xf86WriteSerial (int fd, const void *buf, int count)
+{
+ int r;
+ int i;
+
+ DebugF("WritingSerial: 0x%x",(unsigned char)*(((unsigned char *)buf)));
+ for (i = 1; i < count; i++)
+ DebugF(", 0x%x",(unsigned char)*(((unsigned char *)buf) + i));
+ DebugF("\n");
+ SYSCALL (r = write (fd, buf, count));
+ return r;
+}
+
+int
+xf86CloseSerial (int fd)
+{
+ int r;
+
+ SYSCALL (r = close (fd));
+ return r;
+}
+
+int
+xf86WaitForInput (int fd, int timeout)
+{
+ fd_set readfds;
+ struct timeval to;
+ int r;
+
+ FD_ZERO(&readfds);
+
+ if (fd >= 0) {
+ FD_SET(fd, &readfds);
+ }
+
+ to.tv_sec = timeout / 1000000;
+ to.tv_usec = timeout % 1000000;
+
+ if (fd >= 0) {
+ SYSCALL (r = select (FD_SETSIZE, &readfds, NULL, NULL, &to));
+ }
+ else {
+ SYSCALL (r = select (FD_SETSIZE, NULL, NULL, NULL, &to));
+ }
+ xf86ErrorFVerb (9,"select returned %d\n", r);
+ return r;
+}
+
+int
+xf86SerialSendBreak (int fd, int duration)
+{
+ int r;
+
+ SYSCALL (r = tcsendbreak (fd, duration));
+ return r;
+
+}
+
+int
+xf86FlushInput(int fd)
+{
+ fd_set fds;
+ struct timeval timeout;
+ char c[4];
+
+ DebugF("FlushingSerial\n");
+ if (tcflush(fd, TCIFLUSH) == 0)
+ return 0;
+
+ timeout.tv_sec = 0;
+ timeout.tv_usec = 0;
+ FD_ZERO(&fds);
+ FD_SET(fd, &fds);
+ while (select(FD_SETSIZE, &fds, NULL, NULL, &timeout) > 0) {
+ if (read(fd, &c, sizeof(c)) < 1)
+ return 0;
+ FD_ZERO(&fds);
+ FD_SET(fd, &fds);
+ }
+ return 0;
+}
+
+static struct states {
+ int xf;
+ int os;
+} modemStates[] = {
+#ifdef TIOCM_LE
+ { XF86_M_LE, TIOCM_LE },
+#endif
+#ifdef TIOCM_DTR
+ { XF86_M_DTR, TIOCM_DTR },
+#endif
+#ifdef TIOCM_RTS
+ { XF86_M_RTS, TIOCM_RTS },
+#endif
+#ifdef TIOCM_ST
+ { XF86_M_ST, TIOCM_ST },
+#endif
+#ifdef TIOCM_SR
+ { XF86_M_SR, TIOCM_SR },
+#endif
+#ifdef TIOCM_CTS
+ { XF86_M_CTS, TIOCM_CTS },
+#endif
+#ifdef TIOCM_CAR
+ { XF86_M_CAR, TIOCM_CAR },
+#elif defined(TIOCM_CD)
+ { XF86_M_CAR, TIOCM_CD },
+#endif
+#ifdef TIOCM_RNG
+ { XF86_M_RNG, TIOCM_RNG },
+#elif defined(TIOCM_RI)
+ { XF86_M_CAR, TIOCM_RI },
+#endif
+#ifdef TIOCM_DSR
+ { XF86_M_DSR, TIOCM_DSR },
+#endif
+};
+
+static int numStates = sizeof(modemStates) / sizeof(modemStates[0]);
+
+static int
+xf2osState(int state)
+{
+ int i;
+ int ret = 0;
+
+ for (i = 0; i < numStates; i++)
+ if (state & modemStates[i].xf)
+ ret |= modemStates[i].os;
+ return ret;
+}
+
+static int
+os2xfState(int state)
+{
+ int i;
+ int ret = 0;
+
+ for (i = 0; i < numStates; i++)
+ if (state & modemStates[i].os)
+ ret |= modemStates[i].xf;
+ return ret;
+}
+
+static int
+getOsStateMask(void)
+{
+ int i;
+ int ret = 0;
+ for (i = 0; i < numStates; i++)
+ ret |= modemStates[i].os;
+ return ret;
+}
+
+static int osStateMask = 0;
+
+int
+xf86SetSerialModemState(int fd, int state)
+{
+ int ret;
+ int s;
+
+ if (fd < 0)
+ return -1;
+
+ /* Don't try to set parameters for non-tty devices. */
+ if (!isatty(fd))
+ return 0;
+
+#ifndef TIOCMGET
+ return -1;
+#else
+ if (!osStateMask)
+ osStateMask = getOsStateMask();
+
+ state = xf2osState(state);
+ SYSCALL((ret = ioctl(fd, TIOCMGET, &s)));
+ if (ret < 0)
+ return -1;
+ s &= ~osStateMask;
+ s |= state;
+ SYSCALL((ret = ioctl(fd, TIOCMSET, &s)));
+ if (ret < 0)
+ return -1;
+ else
+ return 0;
+#endif
+}
+
+int
+xf86GetSerialModemState(int fd)
+{
+ int ret;
+ int s;
+
+ if (fd < 0)
+ return -1;
+
+ /* Don't try to set parameters for non-tty devices. */
+ if (!isatty(fd))
+ return 0;
+
+#ifndef TIOCMGET
+ return -1;
+#else
+ SYSCALL((ret = ioctl(fd, TIOCMGET, &s)));
+ if (ret < 0)
+ return -1;
+ return os2xfState(s);
+#endif
+}
+
+int
+xf86SerialModemSetBits(int fd, int bits)
+{
+ int ret;
+ int s;
+
+ if (fd < 0)
+ return -1;
+
+ /* Don't try to set parameters for non-tty devices. */
+ if (!isatty(fd))
+ return 0;
+
+#ifndef TIOCMGET
+ return -1;
+#else
+ s = xf2osState(bits);
+ SYSCALL((ret = ioctl(fd, TIOCMBIS, &s)));
+ return ret;
+#endif
+}
+
+int
+xf86SerialModemClearBits(int fd, int bits)
+{
+ int ret;
+ int s;
+
+ if (fd < 0)
+ return -1;
+
+ /* Don't try to set parameters for non-tty devices. */
+ if (!isatty(fd))
+ return 0;
+
+#ifndef TIOCMGET
+ return -1;
+#else
+ s = xf2osState(bits);
+ SYSCALL((ret = ioctl(fd, TIOCMBIC, &s)));
+ return ret;
+#endif
+}
diff --git a/xorg-server/hw/xfree86/loader/sdksyms.sh b/xorg-server/hw/xfree86/sdksyms.sh
index 6f5082ae5..6f5082ae5 100644
--- a/xorg-server/hw/xfree86/loader/sdksyms.sh
+++ b/xorg-server/hw/xfree86/sdksyms.sh
diff --git a/xorg-server/hw/xquartz/X11Application.m b/xorg-server/hw/xquartz/X11Application.m
index 9894b4ee6..d30ff3aa9 100644
--- a/xorg-server/hw/xquartz/X11Application.m
+++ b/xorg-server/hw/xquartz/X11Application.m
@@ -338,18 +338,21 @@ static void message_kit_thread (SEL selector, NSObject *arg) {
case NSAppKitDefined:
switch ([e subtype]) {
+ static BOOL x_was_active = NO;
+
case NSApplicationActivatedEventType:
for_x = NO;
- if ([self modalWindow] == nil) {
+ if ([e window] == nil && x_was_active) {
BOOL order_all_windows = YES, workspaces, ok;
for_appkit = NO;
-
- /* FIXME: hack to avoid having to pass the event to appkit,
- which would cause it to raise one of its windows. */
+
+ /* FIXME: This is a hack to avoid passing the event to AppKit which
+ * would result in it raising one of its windows.
+ */
_appFlags._active = YES;
-
- [self activateX:YES];
-
+
+ X11ApplicationSetFrontProcess();
+
/* Get the Spaces preference for SwitchOnActivate */
(void)CFPreferencesAppSynchronize(CFSTR("com.apple.dock"));
workspaces = CFPreferencesGetAppBooleanValue(CFSTR("workspaces"), CFSTR("com.apple.dock"), &ok);
@@ -370,8 +373,9 @@ static void message_kit_thread (SEL selector, NSObject *arg) {
* If there are no active windows, and there are minimized windows, we should
* be restoring one of them.
*/
- if ([e data2] & 0x10) // 0x10 is set when we use cmd-tab or the dock icon
+ if ([e data2] & 0x10) { // 0x10 (bfCPSOrderAllWindowsForward) is set when we use cmd-tab or the dock icon
DarwinSendDDXEvent(kXquartzBringAllToFront, 1, order_all_windows);
+ }
}
break;
@@ -381,7 +385,10 @@ static void message_kit_thread (SEL selector, NSObject *arg) {
case NSApplicationDeactivatedEventType:
for_x = NO;
- [self activateX:NO];
+
+ x_was_active = _x_active;
+ if(_x_active)
+ [self activateX:NO];
break;
}
break;
diff --git a/xorg-server/hw/xquartz/mach-startup/Makefile.am b/xorg-server/hw/xquartz/mach-startup/Makefile.am
index 1b194f3aa..388ecfa2a 100644
--- a/xorg-server/hw/xquartz/mach-startup/Makefile.am
+++ b/xorg-server/hw/xquartz/mach-startup/Makefile.am
@@ -22,7 +22,7 @@ X11_bin_LDADD = \
$(top_builddir)/dix/dixfonts.lo \
$(top_builddir)/miext/rootless/librootless.la \
$(top_builddir)/hw/xquartz/pbproxy/libxpbproxy.la \
- $(DARWIN_LIBS) $(MAIN_LIB) $(XSERVER_LIBS)
+ $(XQUARTZ_LIBS) $(XSERVER_LIBS)
X11_bin_LDFLAGS = \
$(XSERVER_SYS_LIBS) -lXplugin \
@@ -52,6 +52,8 @@ X11_bin_LDADD += \
$(top_builddir)/record/librecord.la
endif
+X11_bin_DEPENDENCIES = $(X11_bin_LDADD)
+
bin_PROGRAMS = Xquartz
dist_Xquartz_SOURCES = \
diff --git a/xorg-server/hw/xwin/windialogs.c b/xorg-server/hw/xwin/windialogs.c
index 346e7b4e0..0d5d7c641 100644
--- a/xorg-server/hw/xwin/windialogs.c
+++ b/xorg-server/hw/xwin/windialogs.c
@@ -115,7 +115,7 @@ winDrawURLWindow (LPARAM lParam)
/* Draw it */
SetBkMode (draw->hDC, OPAQUE);
SelectObject (draw->hDC, font);
- DrawText (draw->hDC, str, strlen (str),&rect,DT_CENTER | DT_VCENTER);
+ DrawText (draw->hDC, str, strlen (str),&rect,DT_LEFT | DT_VCENTER);
/* Delete the created font, replace it with stock font */
DeleteObject (SelectObject (draw->hDC, GetStockObject (ANSI_VAR_FONT)));
}
diff --git a/xorg-server/hw/xwin/winmultiwindowwindow.c b/xorg-server/hw/xwin/winmultiwindowwindow.c
index ceb8dff04..600c21ab3 100644
--- a/xorg-server/hw/xwin/winmultiwindowwindow.c
+++ b/xorg-server/hw/xwin/winmultiwindowwindow.c
@@ -433,8 +433,7 @@ winCreateWindowsWindow (WindowPtr pWin)
winPrivScreenPtr pScreenPriv = pWinPriv->pScreenPriv;
WinXSizeHints hints;
WindowPtr pDaddy;
- DWORD dwStyle;
- DWORD dwExStyle;
+ DWORD dwStyle, dwExStyle;
RECT rc;
winInitMultiWindowClass();
@@ -509,29 +508,35 @@ winCreateWindowsWindow (WindowPtr pWin)
}
}
- /* Create the window */
- /* Make it OVERLAPPED in create call since WS_POPUP doesn't support */
+ /* Make it WS_OVERLAPPED in create call since WS_POPUP doesn't support */
/* CW_USEDEFAULT, change back to popup after creation */
-
dwStyle = WS_OVERLAPPEDWINDOW | WS_CLIPCHILDREN | WS_CLIPSIBLINGS;
dwExStyle = WS_EX_TOOLWINDOW;
- rc.top = 0;
- rc.left = 0;
- rc.bottom = iHeight;
- rc.right = iWidth;
+
+ /*
+ Calculate the window coordinates containing the requested client area,
+ being careful to preseve CW_USEDEFAULT
+ */
+ rc.top = (iY != CW_USEDEFAULT) ? iY : 0;
+ rc.left = (iX != CW_USEDEFAULT) ? iX : 0;
+ rc.bottom = rc.top + iHeight;
+ rc.right = rc.left + iWidth;
AdjustWindowRectEx(&rc, dwStyle, FALSE, dwExStyle);
+ if (iY != CW_USEDEFAULT) iY = rc.top;
+ if (iX != CW_USEDEFAULT) iX = rc.left;
iHeight = rc.bottom - rc.top;
iWidth = rc.right - rc.left;
- winDebug("winCreateWindowsWindow - window size %dx%d\n", iWidth, iHeight);
+ winDebug("winCreateWindowsWindow - %dx%d @ %dx%d\n", iWidth, iHeight, iX, iY);
- hWnd = CreateWindowExA (dwExStyle, /* Extended styles */
+ /* Create the window */
+ hWnd = CreateWindowExA (dwExStyle, /* Extended styles */
WINDOW_CLASS_X, /* Class name */
WINDOW_TITLE_X, /* Window name */
dwStyle, /* Styles */
iX, /* Horizontal position */
iY, /* Vertical position */
- iWidth, /* Right edge */
+ iWidth, /* Right edge */
iHeight, /* Bottom edge */
hFore, /* Null or Parent window if transient*/
(HMENU) NULL, /* No menu */
@@ -549,14 +554,15 @@ winCreateWindowsWindow (WindowPtr pWin)
if (hIcon) SendMessage (hWnd, WM_SETICON, ICON_BIG, (LPARAM) hIcon);
if (hIconSmall) SendMessage (hWnd, WM_SETICON, ICON_SMALL, (LPARAM) hIconSmall);
- /* If we asked the native WM to place the window, synchronize the X window position */
- if (iX == CW_USEDEFAULT)
- winAdjustXWindow(pWin, hWnd);
-
/* Change style back to popup, already placed... */
SetWindowLongPtr(hWnd, GWL_STYLE, WS_POPUP | WS_CLIPCHILDREN | WS_CLIPSIBLINGS);
SetWindowPos (hWnd, 0, 0, 0, 0, 0,
SWP_FRAMECHANGED | SWP_NOZORDER | SWP_NOMOVE | SWP_NOSIZE | SWP_NOACTIVATE);
+
+ /* If we asked the native WM to place the window, synchronize the X window position */
+ if (iX == CW_USEDEFAULT)
+ winAdjustXWindow(pWin, hWnd);
+
/* Make sure it gets the proper system menu for a WS_POPUP, too */
GetSystemMenu (hWnd, TRUE);
diff --git a/xorg-server/hw/xwin/winmultiwindowwndproc.c b/xorg-server/hw/xwin/winmultiwindowwndproc.c
index 91a488913..1fb21bc51 100644
--- a/xorg-server/hw/xwin/winmultiwindowwndproc.c
+++ b/xorg-server/hw/xwin/winmultiwindowwndproc.c
@@ -1,1035 +1,1082 @@
-/*
- *Copyright (C) 1994-2000 The XFree86 Project, Inc. All Rights Reserved.
- *Copyright (C) Colin Harrison 2005-2008
- *
- *Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- *"Software"), to deal in the Software without restriction, including
- *without limitation the rights to use, copy, modify, merge, publish,
- *distribute, sublicense, and/or sell copies of the Software, and to
- *permit persons to whom the Software is furnished to do so, subject to
- *the following conditions:
- *
- *The above copyright notice and this permission notice shall be
- *included in all copies or substantial portions of the Software.
- *
- *THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- *EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- *MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- *NONINFRINGEMENT. IN NO EVENT SHALL THE XFREE86 PROJECT BE LIABLE FOR
- *ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF
- *CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- *WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- *Except as contained in this notice, the name of the XFree86 Project
- *shall not be used in advertising or otherwise to promote the sale, use
- *or other dealings in this Software without prior written authorization
- *from the XFree86 Project.
- *
- * Authors: Kensuke Matsuzaki
- * Earle F. Philhower, III
- * Harold L Hunt II
- * Colin Harrison
- */
-
-#ifdef HAVE_XWIN_CONFIG_H
-#include <xwin-config.h>
-#endif
-#include "win.h"
-#include "dixevents.h"
-#include "winmultiwindowclass.h"
-#include "winprefs.h"
-#include "winmsg.h"
-#include "inputstr.h"
-
-#ifdef XKB
-#ifndef XKB_IN_SERVER
-#define XKB_IN_SERVER
-#endif
-#include <xkbsrv.h>
-#endif
-
-extern void winUpdateWindowPosition (HWND hWnd, Bool reshape, HWND *zstyle);
-
-
-/*
- * Local globals
- */
-
-static UINT_PTR g_uipMousePollingTimerID = 0;
-
-
-/*
- * Constant defines
- */
-
-#define WIN_MULTIWINDOW_SHAPE YES
-
-
-/*
- * ConstrainSize - Taken from TWM sources - Respects hints for sizing
- */
-#define makemult(a,b) ((b==1) ? (a) : (((int)((a)/(b))) * (b)) )
-static void
-ConstrainSize (WinXSizeHints hints, int *widthp, int *heightp)
-{
- int minWidth, minHeight, maxWidth, maxHeight, xinc, yinc, delta;
- int baseWidth, baseHeight;
- int dwidth = *widthp, dheight = *heightp;
-
- if (hints.flags & PMinSize)
- {
- minWidth = hints.min_width;
- minHeight = hints.min_height;
- }
- else if (hints.flags & PBaseSize)
- {
- minWidth = hints.base_width;
- minHeight = hints.base_height;
- }
- else
- minWidth = minHeight = 1;
-
- if (hints.flags & PBaseSize)
- {
- baseWidth = hints.base_width;
- baseHeight = hints.base_height;
- }
- else if (hints.flags & PMinSize)
- {
- baseWidth = hints.min_width;
- baseHeight = hints.min_height;
- }
- else
- baseWidth = baseHeight = 0;
-
- if (hints.flags & PMaxSize)
- {
- maxWidth = hints.max_width;
- maxHeight = hints.max_height;
- }
- else
- {
- maxWidth = MAXINT;
- maxHeight = MAXINT;
- }
-
- if (hints.flags & PResizeInc)
- {
- xinc = hints.width_inc;
- yinc = hints.height_inc;
- }
- else
- xinc = yinc = 1;
-
- /*
- * First, clamp to min and max values
- */
- if (dwidth < minWidth)
- dwidth = minWidth;
- if (dheight < minHeight)
- dheight = minHeight;
-
- if (dwidth > maxWidth)
- dwidth = maxWidth;
- if (dheight > maxHeight)
- dheight = maxHeight;
-
- /*
- * Second, fit to base + N * inc
- */
- dwidth = ((dwidth - baseWidth) / xinc * xinc) + baseWidth;
- dheight = ((dheight - baseHeight) / yinc * yinc) + baseHeight;
-
- /*
- * Third, adjust for aspect ratio
- */
-
- /*
- * The math looks like this:
- *
- * minAspectX dwidth maxAspectX
- * ---------- <= ------- <= ----------
- * minAspectY dheight maxAspectY
- *
- * If that is multiplied out, then the width and height are
- * invalid in the following situations:
- *
- * minAspectX * dheight > minAspectY * dwidth
- * maxAspectX * dheight < maxAspectY * dwidth
- *
- */
-
- if (hints.flags & PAspect)
- {
- if (hints.min_aspect.x * dheight > hints.min_aspect.y * dwidth)
- {
- delta = makemult(hints.min_aspect.x * dheight / hints.min_aspect.y - dwidth, xinc);
- if (dwidth + delta <= maxWidth)
- dwidth += delta;
- else
- {
- delta = makemult(dheight - dwidth*hints.min_aspect.y/hints.min_aspect.x, yinc);
- if (dheight - delta >= minHeight)
- dheight -= delta;
- }
- }
-
- if (hints.max_aspect.x * dheight < hints.max_aspect.y * dwidth)
- {
- delta = makemult(dwidth * hints.max_aspect.y / hints.max_aspect.x - dheight, yinc);
- if (dheight + delta <= maxHeight)
- dheight += delta;
- else
- {
- delta = makemult(dwidth - hints.max_aspect.x*dheight/hints.max_aspect.y, xinc);
- if (dwidth - delta >= minWidth)
- dwidth -= delta;
- }
- }
- }
-
- /* Return computed values */
- *widthp = dwidth;
- *heightp = dheight;
-}
-#undef makemult
-
-
-
-/*
- * ValidateSizing - Ensures size request respects hints
- */
-static int
-ValidateSizing (HWND hwnd, WindowPtr pWin,
- WPARAM wParam, LPARAM lParam)
-{
- WinXSizeHints sizeHints;
- RECT *rect;
- int iWidth, iHeight;
- RECT rcClient, rcWindow;
- int iBorderWidthX, iBorderWidthY;
-
- /* Invalid input checking */
- if (pWin==NULL || lParam==0)
- return FALSE;
-
- /* No size hints, no checking */
- if (!winMultiWindowGetWMNormalHints (pWin, &sizeHints))
- return FALSE;
-
- /* Avoid divide-by-zero */
- if (sizeHints.flags & PResizeInc)
- {
- if (sizeHints.width_inc == 0) sizeHints.width_inc = 1;
- if (sizeHints.height_inc == 0) sizeHints.height_inc = 1;
- }
-
- rect = (RECT*)lParam;
-
- iWidth = rect->right - rect->left;
- iHeight = rect->bottom - rect->top;
-
- /* Now remove size of any borders and title bar */
- GetClientRect(hwnd, &rcClient);
- GetWindowRect(hwnd, &rcWindow);
- iBorderWidthX = (rcWindow.right - rcWindow.left) - (rcClient.right - rcClient.left);
- iBorderWidthY = (rcWindow.bottom - rcWindow.top) - (rcClient.bottom - rcClient.top);
- iWidth -= iBorderWidthX;
- iHeight -= iBorderWidthY;
-
- /* Constrain the size to legal values */
- ConstrainSize (sizeHints, &iWidth, &iHeight);
-
- /* Add back the size of borders and title bar */
- iWidth += iBorderWidthX;
- iHeight += iBorderWidthY;
-
- /* Adjust size according to where we're dragging from */
- switch(wParam) {
- case WMSZ_TOP:
- case WMSZ_TOPRIGHT:
- case WMSZ_BOTTOM:
- case WMSZ_BOTTOMRIGHT:
- case WMSZ_RIGHT:
- rect->right = rect->left + iWidth;
- break;
- default:
- rect->left = rect->right - iWidth;
- break;
- }
- switch(wParam) {
- case WMSZ_BOTTOM:
- case WMSZ_BOTTOMRIGHT:
- case WMSZ_BOTTOMLEFT:
- case WMSZ_RIGHT:
- case WMSZ_LEFT:
- rect->bottom = rect->top + iHeight;
- break;
- default:
- rect->top = rect->bottom - iHeight;
- break;
- }
- return TRUE;
-}
-
-extern Bool winInDestroyWindowsWindow;
-static Bool winInRaiseWindow = FALSE;
-static void winRaiseWindow(WindowPtr pWin)
-{
- if (!winInDestroyWindowsWindow && !winInRaiseWindow)
- {
- BOOL oldstate = winInRaiseWindow;
- XID vlist[1] = { 0 };
- winInRaiseWindow = TRUE;
- /* Call configure window directly to make sure it gets processed
- * in time
- */
- ConfigureWindow(pWin, CWStackMode, vlist, serverClient);
- winInRaiseWindow = oldstate;
- }
-}
-
-static
-void winStartMousePolling(winPrivScreenPtr s_pScreenPriv)
-{
- /*
- * Timer to poll mouse position. This is needed to make
- * programs like xeyes follow the mouse properly when the
- * mouse pointer is outside of any X window.
- */
- if (g_uipMousePollingTimerID == 0)
- g_uipMousePollingTimerID = SetTimer (s_pScreenPriv->hwndScreen,
- WIN_POLLING_MOUSE_TIMER_ID,
- MOUSE_POLLING_INTERVAL,
- NULL);
-}
-
-/*
- * winTopLevelWindowProc - Window procedure for all top-level Windows windows.
- */
-
-LRESULT CALLBACK
-winTopLevelWindowProc (HWND hwnd, UINT message,
- WPARAM wParam, LPARAM lParam)
-{
- POINT ptMouse;
- HDC hdcUpdate;
- PAINTSTRUCT ps;
- WindowPtr pWin = NULL;
- winPrivWinPtr pWinPriv = NULL;
- ScreenPtr s_pScreen = NULL;
- winPrivScreenPtr s_pScreenPriv = NULL;
- winScreenInfo *s_pScreenInfo = NULL;
- HWND hwndScreen = NULL;
- DrawablePtr pDraw = NULL;
- winWMMessageRec wmMsg;
- Bool fWMMsgInitialized = FALSE;
- static Bool s_fTracking = FALSE;
- Bool needRestack = FALSE;
- LRESULT ret;
-
- winDebugWin32Message("winTopLevelWindowProc", hwnd, message, wParam, lParam);
-
- /* Check if the Windows window property for our X window pointer is valid */
- if ((pWin = GetProp (hwnd, WIN_WINDOW_PROP)) != NULL)
- {
- /* Our X window pointer is valid */
-
- /* Get pointers to the drawable and the screen */
- pDraw = &pWin->drawable;
- s_pScreen = pWin->drawable.pScreen;
-
- /* Get a pointer to our window privates */
- pWinPriv = winGetWindowPriv(pWin);
-
- /* Get pointers to our screen privates and screen info */
- s_pScreenPriv = pWinPriv->pScreenPriv;
- s_pScreenInfo = s_pScreenPriv->pScreenInfo;
-
- /* Get the handle for our screen-sized window */
- hwndScreen = s_pScreenPriv->hwndScreen;
-
- /* */
- wmMsg.msg = 0;
- wmMsg.hwndWindow = hwnd;
- wmMsg.iWindow = (Window)GetProp (hwnd, WIN_WID_PROP);
-
- wmMsg.iX = pDraw->x;
- wmMsg.iY = pDraw->y;
- wmMsg.iWidth = pDraw->width;
- wmMsg.iHeight = pDraw->height;
-
- fWMMsgInitialized = TRUE;
-
- }
-
- /* Branch on message type */
- switch (message)
- {
- case WM_CREATE:
-
- /* */
- SetProp (hwnd,
- WIN_WINDOW_PROP,
- (HANDLE)((LPCREATESTRUCT) lParam)->lpCreateParams);
-
- /* */
- SetProp (hwnd,
- WIN_WID_PROP,
- (HANDLE)winGetWindowID (((LPCREATESTRUCT) lParam)->lpCreateParams));
-
- /*
- * Make X windows' Z orders sync with Windows windows because
- * there can be AlwaysOnTop windows overlapped on the window
- * currently being created.
- */
- winReorderWindowsMultiWindow ();
-
- /* Fix a 'round title bar corner background should be transparent not black' problem when first painted */
- {
- RECT rWindow;
- HRGN hRgnWindow;
- GetWindowRect(hwnd, &rWindow);
- hRgnWindow = CreateRectRgnIndirect(&rWindow);
- SetWindowRgn (hwnd, hRgnWindow, TRUE);
- }
-
- SetWindowLongPtr(hwnd, GWLP_USERDATA, (LONG_PTR)VCXSRV_SIGNATURE);
-
- return 0;
-
- case WM_INIT_SYS_MENU:
- /*
- * Add whatever the setup file wants to for this window
- */
- SetupSysMenu ((unsigned long)hwnd);
- return 0;
-
- case WM_SYSCOMMAND:
- /*
- * Any window menu items go through here
- */
- if (HandleCustomWM_COMMAND ((unsigned long)hwnd, LOWORD(wParam)))
- {
- /* Don't pass customized menus to DefWindowProc */
- return 0;
- }
- if (wParam == SC_RESTORE || wParam == SC_MAXIMIZE)
- {
- WINDOWPLACEMENT wndpl;
- wndpl.length = sizeof(wndpl);
- if (GetWindowPlacement(hwnd, &wndpl) && wndpl.showCmd == SW_SHOWMINIMIZED)
- needRestack = TRUE;
- }
- break;
-
- case WM_INITMENU:
- /* Checks/Unchecks any menu items before they are displayed */
- HandleCustomWM_INITMENU ((unsigned long)hwnd, wParam);
- break;
-
- case WM_ERASEBKGND:
- /*
- * Pretend that we did erase the background but we don't care,
- * since we repaint the entire region anyhow
- * This avoids some flickering when resizing.
- */
- return TRUE;
-
- case WM_PAINT:
- /* Only paint if our window handle is valid */
- if (hwndScreen == NULL)
- break;
-
- /* BeginPaint gives us an hdc that clips to the invalidated region */
- hdcUpdate = BeginPaint (hwnd, &ps);
- /* Avoid the BitBlt's if the PAINTSTRUCT is bogus */
- if (ps.rcPaint.right==0 && ps.rcPaint.bottom==0 && ps.rcPaint.left==0 && ps.rcPaint.top==0)
- {
- EndPaint (hwnd, &ps);
- return 0;
- }
-
- /* Try to copy from the shadow buffer */
- if (!BitBlt (hdcUpdate,
- ps.rcPaint.left, ps.rcPaint.top,
- ps.rcPaint.right - ps.rcPaint.left, ps.rcPaint.bottom - ps.rcPaint.top,
- s_pScreenPriv->hdcShadow,
- ps.rcPaint.left + pWin->drawable.x, ps.rcPaint.top + pWin->drawable.y,
- SRCCOPY))
- {
- LPVOID lpMsgBuf;
-
- /* Display a fancy error message */
- FormatMessage (FORMAT_MESSAGE_ALLOCATE_BUFFER |
- FORMAT_MESSAGE_FROM_SYSTEM |
- FORMAT_MESSAGE_IGNORE_INSERTS,
- NULL,
- GetLastError (),
- MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT),
- (LPTSTR) &lpMsgBuf,
- 0, NULL);
-
- ErrorF ("winTopLevelWindowProc - BitBlt failed: %s\n",
- (LPSTR)lpMsgBuf);
- LocalFree (lpMsgBuf);
- }
-
- /* EndPaint frees the DC */
- EndPaint (hwnd, &ps);
- return 0;
-
- case WM_MOUSEMOVE:
- /* Unpack the client area mouse coordinates */
- ptMouse.x = GET_X_LPARAM(lParam);
- ptMouse.y = GET_Y_LPARAM(lParam);
-
- /* Translate the client area mouse coordinates to screen coordinates */
- ClientToScreen (hwnd, &ptMouse);
-
- /* Screen Coords from (-X, -Y) -> Root Window (0, 0) */
- ptMouse.x -= GetSystemMetrics (SM_XVIRTUALSCREEN);
- ptMouse.y -= GetSystemMetrics (SM_YVIRTUALSCREEN);
-
- /* We can't do anything without privates */
- if (s_pScreenPriv == NULL || s_pScreenInfo->fIgnoreInput)
- break;
-
- /* Has the mouse pointer crossed screens? */
- if (s_pScreen != miPointerGetScreen(g_pwinPointer))
- miPointerSetScreen (g_pwinPointer, s_pScreenInfo->dwScreen,
- ptMouse.x - s_pScreenInfo->dwXOffset,
- ptMouse.y - s_pScreenInfo->dwYOffset);
-
- /* Are we tracking yet? */
- if (!s_fTracking)
- {
- TRACKMOUSEEVENT tme;
-
- /* Setup data structure */
- ZeroMemory (&tme, sizeof (tme));
- tme.cbSize = sizeof (tme);
- tme.dwFlags = TME_LEAVE;
- tme.hwndTrack = hwnd;
-
- /* Call the tracking function */
- if (!(*g_fpTrackMouseEvent) (&tme))
- ErrorF ("winTopLevelWindowProc - _TrackMouseEvent failed\n");
-
- /* Flag that we are tracking now */
- s_fTracking = TRUE;
- }
-
- /* Hide or show the Windows mouse cursor */
- if (g_fSoftwareCursor && g_fCursor)
- {
- /* Hide Windows cursor */
- g_fCursor = FALSE;
- ShowCursor (FALSE);
- }
-
- /* Kill the timer used to poll mouse events */
- if (g_uipMousePollingTimerID != 0)
- {
- KillTimer (s_pScreenPriv->hwndScreen, WIN_POLLING_MOUSE_TIMER_ID);
- g_uipMousePollingTimerID = 0;
- }
-
- /* Deliver absolute cursor position to X Server */
- winEnqueueMotion(ptMouse.x - s_pScreenInfo->dwXOffset,
- ptMouse.y - s_pScreenInfo->dwYOffset);
-
- return 0;
-
- case WM_NCMOUSEMOVE:
- /*
- * We break instead of returning 0 since we need to call
- * DefWindowProc to get the mouse cursor changes
- * and min/max/close button highlighting in Windows XP.
- * The Platform SDK says that you should return 0 if you
- * process this message, but it fails to mention that you
- * will give up any default functionality if you do return 0.
- */
-
- /* We can't do anything without privates */
- if (s_pScreenPriv == NULL || s_pScreenInfo->fIgnoreInput)
- break;
-
- /* Non-client mouse movement, show Windows cursor */
- if (g_fSoftwareCursor && !g_fCursor)
- {
- g_fCursor = TRUE;
- ShowCursor (TRUE);
- }
-
- winStartMousePolling(s_pScreenPriv);
-
- break;
-
- case WM_MOUSELEAVE:
- /* We can't do anything without privates */
- if (s_pScreenPriv == NULL || s_pScreenInfo->fIgnoreInput)
- break;
- /* Mouse has left our client area */
-
- /* Flag that we are no longer tracking */
- s_fTracking = FALSE;
-
- /* Show the mouse cursor, if necessary */
- if (g_fSoftwareCursor && !g_fCursor)
- {
- g_fCursor = TRUE;
- ShowCursor (TRUE);
- }
-
- winStartMousePolling(s_pScreenPriv);
-
- return 0;
-
- case WM_LBUTTONDBLCLK:
- case WM_LBUTTONDOWN:
- if (s_pScreenPriv == NULL || s_pScreenInfo->fIgnoreInput)
- break;
- g_fButton[0] = TRUE;
- SetCapture(hwnd);
- return winMouseButtonsHandle (s_pScreen, ButtonPress, Button1, wParam);
-
- case WM_LBUTTONUP:
- if (s_pScreenPriv == NULL || s_pScreenInfo->fIgnoreInput)
- break;
- g_fButton[0] = FALSE;
- ReleaseCapture();
- winStartMousePolling(s_pScreenPriv);
- return winMouseButtonsHandle (s_pScreen, ButtonRelease, Button1, wParam);
-
- case WM_MBUTTONDBLCLK:
- case WM_MBUTTONDOWN:
- if (s_pScreenPriv == NULL || s_pScreenInfo->fIgnoreInput)
- break;
- g_fButton[1] = TRUE;
- SetCapture(hwnd);
- return winMouseButtonsHandle (s_pScreen, ButtonPress, Button2, wParam);
-
- case WM_MBUTTONUP:
- if (s_pScreenPriv == NULL || s_pScreenInfo->fIgnoreInput)
- break;
- g_fButton[1] = FALSE;
- ReleaseCapture();
- winStartMousePolling(s_pScreenPriv);
- return winMouseButtonsHandle (s_pScreen, ButtonRelease, Button2, wParam);
-
- case WM_RBUTTONDBLCLK:
- case WM_RBUTTONDOWN:
- if (s_pScreenPriv == NULL || s_pScreenInfo->fIgnoreInput)
- break;
- g_fButton[2] = TRUE;
- SetCapture(hwnd);
- return winMouseButtonsHandle (s_pScreen, ButtonPress, Button3, wParam);
-
- case WM_RBUTTONUP:
- if (s_pScreenPriv == NULL || s_pScreenInfo->fIgnoreInput)
- break;
- g_fButton[2] = FALSE;
- ReleaseCapture();
- winStartMousePolling(s_pScreenPriv);
- return winMouseButtonsHandle (s_pScreen, ButtonRelease, Button3, wParam);
-
- case WM_XBUTTONDBLCLK:
- case WM_XBUTTONDOWN:
- if (s_pScreenPriv == NULL || s_pScreenInfo->fIgnoreInput)
- break;
- SetCapture(hwnd);
- return winMouseButtonsHandle (s_pScreen, ButtonPress, HIWORD(wParam) + 5, wParam);
-
- case WM_XBUTTONUP:
- if (s_pScreenPriv == NULL || s_pScreenInfo->fIgnoreInput)
- break;
- ReleaseCapture();
- winStartMousePolling(s_pScreenPriv);
- return winMouseButtonsHandle (s_pScreen, ButtonRelease, HIWORD(wParam) + 5, wParam);
-
- case WM_MOUSEWHEEL:
- if (SendMessage(hwnd, WM_NCHITTEST, 0, MAKELONG(GET_X_LPARAM(lParam), GET_Y_LPARAM(lParam))) == HTCLIENT)
- {
- /* Pass the message to the root window */
- SendMessage (hwndScreen, message, wParam, lParam);
- return 0;
- }
- else break;
-
- case WM_SETFOCUS:
- if (s_pScreenPriv == NULL || s_pScreenInfo->fIgnoreInput)
- break;
-
- {
- /* Get the parent window for transient handling */
- HWND hParent = GetParent(hwnd);
- if (hParent && IsIconic(hParent)) ShowWindow (hParent, SW_RESTORE);
- }
-
- winRestoreModeKeyStates ();
-
- /* Add the keyboard hook if possible */
- if (g_fKeyboardHookLL)
- g_fKeyboardHookLL = winInstallKeyboardHookLL ();
- return 0;
-
- case WM_KILLFOCUS:
- /* Pop any pressed keys since we are losing keyboard focus */
- winKeybdReleaseKeys ();
-
- /* Remove our keyboard hook if it is installed */
- winRemoveKeyboardHookLL ();
- if (!wParam)
- /* Revert the X focus as well, but only if the Windows focus is going to another window */
- DeleteWindowFromAnyEvents(pWin, FALSE);
- return 0;
-
- case WM_SYSDEADCHAR:
- case WM_DEADCHAR:
- /*
- * NOTE: We do nothing with WM_*CHAR messages,
- * nor does the root window, so we can just toss these messages.
- */
- return 0;
-
- case WM_SYSKEYDOWN:
- case WM_KEYDOWN:
-
- /*
- * Don't pass Alt-F4 key combo to root window,
- * let Windows translate to WM_CLOSE and close this top-level window.
- *
- * NOTE: We purposely don't check the fUseWinKillKey setting because
- * it should only apply to the key handling for the root window,
- * not for top-level window-manager windows.
- *
- * ALSO NOTE: We do pass Ctrl-Alt-Backspace to the root window
- * because that is a key combo that no X app should be expecting to
- * receive, since it has historically been used to shutdown the X server.
- * Passing Ctrl-Alt-Backspace to the root window preserves that
- * behavior, assuming that -unixkill has been passed as a parameter.
- */
- if (wParam == VK_F4 && (GetKeyState (VK_MENU) & 0x8000))
- break;
-
-#ifdef WINDBG
- if (wParam == VK_ESCAPE)
- {
- /* Place for debug: put any tests and dumps here */
- WINDOWPLACEMENT windPlace;
- RECT rc;
- LPRECT pRect;
-
- windPlace.length = sizeof (WINDOWPLACEMENT);
- GetWindowPlacement (hwnd, &windPlace);
- pRect = &windPlace.rcNormalPosition;
- winDebug ("\nCYGWINDOWING Dump:\n"
- "\tdrawable: (%hd, %hd) - %hdx%hd\n", pDraw->x,
- pDraw->y, pDraw->width, pDraw->height);
- winDebug ("\twindPlace: (%ld, %ld) - %ldx%ld\n", pRect->left,
- pRect->top, pRect->right - pRect->left,
- pRect->bottom - pRect->top);
- if (GetClientRect (hwnd, &rc))
- {
- pRect = &rc;
- winDebug ("\tClientRect: (%ld, %ld) - %ldx%ld\n", pRect->left,
- pRect->top, pRect->right - pRect->left,
- pRect->bottom - pRect->top);
- }
- if (GetWindowRect (hwnd, &rc))
- {
- pRect = &rc;
- winDebug ("\tWindowRect: (%ld, %ld) - %ldx%ld\n", pRect->left,
- pRect->top, pRect->right - pRect->left,
- pRect->bottom - pRect->top);
- }
- winDebug ("\n");
- }
-#endif
-
- /* Pass the message to the root window */
- return winWindowProc(hwndScreen, message, wParam, lParam);
-
- case WM_SYSKEYUP:
- case WM_KEYUP:
-
-
- /* Pass the message to the root window */
- return winWindowProc(hwndScreen, message, wParam, lParam);
-
- case WM_HOTKEY:
-
- /* Pass the message to the root window */
- SendMessage (hwndScreen, message, wParam, lParam);
- return 0;
-
- case WM_ACTIVATE:
-
- /* Pass the message to the root window */
- SendMessage (hwndScreen, message, wParam, lParam);
-
- if (LOWORD(wParam) != WA_INACTIVE)
- {
- /* Raise the window to the top in Z order */
- /* ago: Activate does not mean putting it to front! */
- /*
- wmMsg.msg = WM_WM_RAISE;
- if (fWMMsgInitialized)
- winSendMessageToWM (s_pScreenPriv->pWMInfo, &wmMsg);
- */
-
- /* Tell our Window Manager thread to activate the window */
- wmMsg.msg = WM_WM_ACTIVATE;
- if (fWMMsgInitialized && pWin->realized && !pWin->overrideRedirect /* for OOo menus */)
- winSendMessageToWM (s_pScreenPriv->pWMInfo, &wmMsg);
- }
- /* Prevent the mouse wheel from stalling when another window is minimized */
- if (HIWORD(wParam) == 0 && LOWORD(wParam) == WA_ACTIVE &&
- (HWND)lParam != NULL && (HWND)lParam != (HWND)GetParent(hwnd))
- SetFocus(hwnd);
- return 0;
-
- case WM_ACTIVATEAPP:
- /*
- * This message is also sent to the root window
- * so we do nothing for individual multiwindow windows
- */
- break;
-
- case WM_CLOSE:
- /* Branch on if the window was killed in X already */
- if (pWinPriv->fXKilled)
- {
- /* Window was killed, go ahead and destroy the window */
- DestroyWindow (hwnd);
- }
- else
- {
- /* Tell our Window Manager thread to kill the window */
- wmMsg.msg = WM_WM_KILL;
- if (fWMMsgInitialized)
- winSendMessageToWM (s_pScreenPriv->pWMInfo, &wmMsg);
- }
- return 0;
-
- case WM_DESTROY:
-
- /* Branch on if the window was killed in X already */
- if (pWinPriv && !pWinPriv->fXKilled)
- {
- winDebug ("winTopLevelWindowProc - WM_DESTROY - WM_WM_KILL\n");
-
- /* Tell our Window Manager thread to kill the window */
- wmMsg.msg = WM_WM_KILL;
- if (fWMMsgInitialized)
- winSendMessageToWM (s_pScreenPriv->pWMInfo, &wmMsg);
- }
-
- RemoveProp (hwnd, WIN_WINDOW_PROP);
- RemoveProp (hwnd, WIN_WID_PROP);
- RemoveProp (hwnd, WIN_NEEDMANAGE_PROP);
-
- break;
-
- case WM_MOVE:
- /* Adjust the X Window to the moved Windows window */
- winAdjustXWindow (pWin, hwnd);
- return 0;
-
- case WM_SHOWWINDOW:
- /* Bail out if the window is being hidden */
- if (!wParam)
- return 0;
-
- /* */
- if (!pWin->overrideRedirect)
- {
- /* Flag that this window needs to be made active when clicked */
- SetProp (hwnd, WIN_NEEDMANAGE_PROP, (HANDLE) 1);
-
- if (!(GetWindowLongPtr (hwnd, GWL_EXSTYLE) & WS_EX_APPWINDOW))
- {
- HWND zstyle = HWND_NOTOPMOST;
-
- /* Set the window extended style flags */
- SetWindowLongPtr (hwnd, GWL_EXSTYLE, WS_EX_APPWINDOW);
-
- /* Set the transient style flags */
- if (GetParent(hwnd)) SetWindowLongPtr (hwnd, GWL_STYLE,
- WS_POPUP | WS_OVERLAPPED | WS_SYSMENU | WS_CLIPCHILDREN | WS_CLIPSIBLINGS);
- /* Set the window standard style flags */
- else SetWindowLongPtr (hwnd, GWL_STYLE,
- (WS_POPUP | WS_OVERLAPPEDWINDOW | WS_CLIPCHILDREN | WS_CLIPSIBLINGS)
- & ~WS_CAPTION & ~WS_SIZEBOX);
-
- winUpdateWindowPosition (hwnd, FALSE, &zstyle);
- SetForegroundWindow (hwnd);
- }
- wmMsg.msg = WM_WM_MAP3;
- }
- else /* It is an overridden window so make it top of Z stack */
- {
- HWND forHwnd = GetForegroundWindow();
- winDebug ("overridden window is shown\n");
- if (forHwnd != NULL)
- {
- if (GetWindowLongPtr(forHwnd, GWLP_USERDATA) & (LONG_PTR)VCXSRV_SIGNATURE)
- {
- if (GetWindowLongPtr(forHwnd, GWL_EXSTYLE) & WS_EX_TOPMOST)
- SetWindowPos (hwnd, HWND_TOPMOST, 0, 0, 0, 0, SWP_NOMOVE | SWP_NOSIZE | SWP_NOACTIVATE);
- else
- SetWindowPos (hwnd, HWND_NOTOPMOST, 0, 0, 0, 0, SWP_NOMOVE | SWP_NOSIZE | SWP_NOACTIVATE);
- }
- }
- wmMsg.msg = WM_WM_MAP2;
- }
-
- /* Tell our Window Manager thread to map the window */
- if (fWMMsgInitialized)
- winSendMessageToWM (s_pScreenPriv->pWMInfo, &wmMsg);
-
- winStartMousePolling(s_pScreenPriv);
-
- return 0;
-
- case WM_SIZING:
- /* Need to legalize the size according to WM_NORMAL_HINTS */
- /* for applications like xterm */
- return ValidateSizing (hwnd, pWin, wParam, lParam);
-
- case WM_WINDOWPOSCHANGED:
- {
- LPWINDOWPOS pWinPos = (LPWINDOWPOS) lParam;
-
- if (!(pWinPos->flags & SWP_NOZORDER))
- {
-#if CYGWINDOWING_DEBUG
- winDebug ("\twindow z order was changed\n");
-#endif
- if (pWinPos->hwndInsertAfter == HWND_TOP
- ||pWinPos->hwndInsertAfter == HWND_TOPMOST
- ||pWinPos->hwndInsertAfter == HWND_NOTOPMOST)
- {
-#if CYGWINDOWING_DEBUG
- winDebug ("\traise to top\n");
-#endif
- /* Raise the window to the top in Z order */
- winRaiseWindow(pWin);
- }
- else if (pWinPos->hwndInsertAfter == HWND_BOTTOM)
- {
- }
- else
- {
- /* Check if this window is top of X windows. */
- HWND hWndAbove = NULL;
- DWORD dwCurrentProcessID = GetCurrentProcessId ();
- DWORD dwWindowProcessID = 0;
-
- for (hWndAbove = pWinPos->hwndInsertAfter;
- hWndAbove != NULL;
- hWndAbove = GetNextWindow (hWndAbove, GW_HWNDPREV))
- {
- /* Ignore other XWin process's window */
- GetWindowThreadProcessId (hWndAbove, &dwWindowProcessID);
-
- if ((dwWindowProcessID == dwCurrentProcessID)
- && GetProp (hWndAbove, WIN_WINDOW_PROP)
- && !IsWindowVisible (hWndAbove)
- && !IsIconic (hWndAbove) ) /* ignore minimized windows */
- break;
- }
- /* If this is top of X windows in Windows stack,
- raise it in X stack. */
- if (hWndAbove == NULL)
- {
-#if CYGWINDOWING_DEBUG
- winDebug ("\traise to top\n");
-#endif
- winRaiseWindow(pWin);
- }
- }
- }
- }
- /*
- * Pass the message to DefWindowProc to let the function
- * break down WM_WINDOWPOSCHANGED to WM_MOVE and WM_SIZE.
- */
- break;
-
- case WM_SIZE:
- /* see dix/window.c */
-#ifdef WINDBG
- {
- char buf[64];
- switch (wParam)
- {
- case SIZE_MINIMIZED:
- strcpy(buf, "SIZE_MINIMIZED");
- break;
- case SIZE_MAXIMIZED:
- strcpy(buf, "SIZE_MAXIMIZED");
- break;
- case SIZE_RESTORED:
- strcpy(buf, "SIZE_RESTORED");
- break;
- default:
- strcpy(buf, "UNKNOWN_FLAG");
- }
- winDebug ("winTopLevelWindowProc - WM_SIZE to %dx%d (%s) - %d ms\n",
- (int)LOWORD(lParam), (int)HIWORD(lParam), buf,
- (int)(GetTickCount ()));
- }
-#endif
- /* Adjust the X Window to the moved Windows window */
- winAdjustXWindow (pWin, hwnd);
- if (wParam == SIZE_MINIMIZED) winReorderWindowsMultiWindow();
- return 0; /* end of WM_SIZE handler */
-
- case WM_STYLECHANGED:
- /* when the style changes, adjust the window size so the client area remains the same */
- {
- LONG x,y;
- DrawablePtr pDraw = &pWin->drawable;
- x = pDraw->x - wBorderWidth(pWin);
- y = pDraw->y - wBorderWidth(pWin);
- winPositionWindowMultiWindow(pWin, x, y);
- }
- return 0;
-
- case WM_MOUSEACTIVATE:
-
- /* Check if this window needs to be made active when clicked */
- if (!GetProp (pWinPriv->hWnd, WIN_NEEDMANAGE_PROP))
- {
- winDebug ("winTopLevelWindowProc - WM_MOUSEACTIVATE - "
- "MA_NOACTIVATE\n");
-
- /* */
- return MA_NOACTIVATE;
- }
- break;
-
- case WM_SETCURSOR:
- if (LOWORD(lParam) == HTCLIENT)
- {
- if (!g_fSoftwareCursor) SetCursor (s_pScreenPriv->cursor.handle);
- return TRUE;
- }
- break;
-
- default:
- break;
- }
-
- ret = DefWindowProc (hwnd, message, wParam, lParam);
- /*
- * If the window was minized we get the stack change before the window is restored
- * and so it gets lost. Ensure there stacking order is correct.
- */
- if (needRestack)
- winReorderWindowsMultiWindow();
- return ret;
-}
+/*
+ *Copyright (C) 1994-2000 The XFree86 Project, Inc. All Rights Reserved.
+ *Copyright (C) Colin Harrison 2005-2008
+ *
+ *Permission is hereby granted, free of charge, to any person obtaining
+ * a copy of this software and associated documentation files (the
+ *"Software"), to deal in the Software without restriction, including
+ *without limitation the rights to use, copy, modify, merge, publish,
+ *distribute, sublicense, and/or sell copies of the Software, and to
+ *permit persons to whom the Software is furnished to do so, subject to
+ *the following conditions:
+ *
+ *The above copyright notice and this permission notice shall be
+ *included in all copies or substantial portions of the Software.
+ *
+ *THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ *EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ *MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ *NONINFRINGEMENT. IN NO EVENT SHALL THE XFREE86 PROJECT BE LIABLE FOR
+ *ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF
+ *CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+ *WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ *
+ *Except as contained in this notice, the name of the XFree86 Project
+ *shall not be used in advertising or otherwise to promote the sale, use
+ *or other dealings in this Software without prior written authorization
+ *from the XFree86 Project.
+ *
+ * Authors: Kensuke Matsuzaki
+ * Earle F. Philhower, III
+ * Harold L Hunt II
+ * Colin Harrison
+ */
+
+#ifdef HAVE_XWIN_CONFIG_H
+#include <xwin-config.h>
+#endif
+#include "win.h"
+#include "dixevents.h"
+#include "winmultiwindowclass.h"
+#include "winprefs.h"
+#include "winmsg.h"
+#include "inputstr.h"
+
+#ifdef XKB
+#ifndef XKB_IN_SERVER
+#define XKB_IN_SERVER
+#endif
+#include <xkbsrv.h>
+#endif
+
+extern void winUpdateWindowPosition (HWND hWnd, Bool reshape, HWND *zstyle);
+
+
+/*
+ * Local globals
+ */
+
+static UINT_PTR g_uipMousePollingTimerID = 0;
+
+
+/*
+ * Constant defines
+ */
+
+#define WIN_MULTIWINDOW_SHAPE YES
+
+
+/*
+ * ConstrainSize - Taken from TWM sources - Respects hints for sizing
+ */
+#define makemult(a,b) ((b==1) ? (a) : (((int)((a)/(b))) * (b)) )
+static void
+ConstrainSize (WinXSizeHints hints, int *widthp, int *heightp)
+{
+ int minWidth, minHeight, maxWidth, maxHeight, xinc, yinc, delta;
+ int baseWidth, baseHeight;
+ int dwidth = *widthp, dheight = *heightp;
+
+ if (hints.flags & PMinSize)
+ {
+ minWidth = hints.min_width;
+ minHeight = hints.min_height;
+ }
+ else if (hints.flags & PBaseSize)
+ {
+ minWidth = hints.base_width;
+ minHeight = hints.base_height;
+ }
+ else
+ minWidth = minHeight = 1;
+
+ if (hints.flags & PBaseSize)
+ {
+ baseWidth = hints.base_width;
+ baseHeight = hints.base_height;
+ }
+ else if (hints.flags & PMinSize)
+ {
+ baseWidth = hints.min_width;
+ baseHeight = hints.min_height;
+ }
+ else
+ baseWidth = baseHeight = 0;
+
+ if (hints.flags & PMaxSize)
+ {
+ maxWidth = hints.max_width;
+ maxHeight = hints.max_height;
+ }
+ else
+ {
+ maxWidth = MAXINT;
+ maxHeight = MAXINT;
+ }
+
+ if (hints.flags & PResizeInc)
+ {
+ xinc = hints.width_inc;
+ yinc = hints.height_inc;
+ }
+ else
+ xinc = yinc = 1;
+
+ /*
+ * First, clamp to min and max values
+ */
+ if (dwidth < minWidth)
+ dwidth = minWidth;
+ if (dheight < minHeight)
+ dheight = minHeight;
+
+ if (dwidth > maxWidth)
+ dwidth = maxWidth;
+ if (dheight > maxHeight)
+ dheight = maxHeight;
+
+ /*
+ * Second, fit to base + N * inc
+ */
+ dwidth = ((dwidth - baseWidth) / xinc * xinc) + baseWidth;
+ dheight = ((dheight - baseHeight) / yinc * yinc) + baseHeight;
+
+ /*
+ * Third, adjust for aspect ratio
+ */
+
+ /*
+ * The math looks like this:
+ *
+ * minAspectX dwidth maxAspectX
+ * ---------- <= ------- <= ----------
+ * minAspectY dheight maxAspectY
+ *
+ * If that is multiplied out, then the width and height are
+ * invalid in the following situations:
+ *
+ * minAspectX * dheight > minAspectY * dwidth
+ * maxAspectX * dheight < maxAspectY * dwidth
+ *
+ */
+
+ if (hints.flags & PAspect)
+ {
+ if (hints.min_aspect.x * dheight > hints.min_aspect.y * dwidth)
+ {
+ delta = makemult(hints.min_aspect.x * dheight / hints.min_aspect.y - dwidth, xinc);
+ if (dwidth + delta <= maxWidth)
+ dwidth += delta;
+ else
+ {
+ delta = makemult(dheight - dwidth*hints.min_aspect.y/hints.min_aspect.x, yinc);
+ if (dheight - delta >= minHeight)
+ dheight -= delta;
+ }
+ }
+
+ if (hints.max_aspect.x * dheight < hints.max_aspect.y * dwidth)
+ {
+ delta = makemult(dwidth * hints.max_aspect.y / hints.max_aspect.x - dheight, yinc);
+ if (dheight + delta <= maxHeight)
+ dheight += delta;
+ else
+ {
+ delta = makemult(dwidth - hints.max_aspect.x*dheight/hints.max_aspect.y, xinc);
+ if (dwidth - delta >= minWidth)
+ dwidth -= delta;
+ }
+ }
+ }
+
+ /* Return computed values */
+ *widthp = dwidth;
+ *heightp = dheight;
+}
+#undef makemult
+
+
+
+/*
+ * ValidateSizing - Ensures size request respects hints
+ */
+static int
+ValidateSizing (HWND hwnd, WindowPtr pWin,
+ WPARAM wParam, LPARAM lParam)
+{
+ WinXSizeHints sizeHints;
+ RECT *rect;
+ int iWidth, iHeight;
+ RECT rcClient, rcWindow;
+ int iBorderWidthX, iBorderWidthY;
+
+ /* Invalid input checking */
+ if (pWin==NULL || lParam==0)
+ return FALSE;
+
+ /* No size hints, no checking */
+ if (!winMultiWindowGetWMNormalHints (pWin, &sizeHints))
+ return FALSE;
+
+ /* Avoid divide-by-zero */
+ if (sizeHints.flags & PResizeInc)
+ {
+ if (sizeHints.width_inc == 0) sizeHints.width_inc = 1;
+ if (sizeHints.height_inc == 0) sizeHints.height_inc = 1;
+ }
+
+ rect = (RECT*)lParam;
+
+ iWidth = rect->right - rect->left;
+ iHeight = rect->bottom - rect->top;
+
+ /* Now remove size of any borders and title bar */
+ GetClientRect(hwnd, &rcClient);
+ GetWindowRect(hwnd, &rcWindow);
+ iBorderWidthX = (rcWindow.right - rcWindow.left) - (rcClient.right - rcClient.left);
+ iBorderWidthY = (rcWindow.bottom - rcWindow.top) - (rcClient.bottom - rcClient.top);
+ iWidth -= iBorderWidthX;
+ iHeight -= iBorderWidthY;
+
+ /* Constrain the size to legal values */
+ ConstrainSize (sizeHints, &iWidth, &iHeight);
+
+ /* Add back the size of borders and title bar */
+ iWidth += iBorderWidthX;
+ iHeight += iBorderWidthY;
+
+ /* Adjust size according to where we're dragging from */
+ switch(wParam) {
+ case WMSZ_TOP:
+ case WMSZ_TOPRIGHT:
+ case WMSZ_BOTTOM:
+ case WMSZ_BOTTOMRIGHT:
+ case WMSZ_RIGHT:
+ rect->right = rect->left + iWidth;
+ break;
+ default:
+ rect->left = rect->right - iWidth;
+ break;
+ }
+ switch(wParam) {
+ case WMSZ_BOTTOM:
+ case WMSZ_BOTTOMRIGHT:
+ case WMSZ_BOTTOMLEFT:
+ case WMSZ_RIGHT:
+ case WMSZ_LEFT:
+ rect->bottom = rect->top + iHeight;
+ break;
+ default:
+ rect->top = rect->bottom - iHeight;
+ break;
+ }
+ return TRUE;
+}
+
+extern Bool winInDestroyWindowsWindow;
+static Bool winInRaiseWindow = FALSE;
+static void winRaiseWindow(WindowPtr pWin)
+{
+ if (!winInDestroyWindowsWindow && !winInRaiseWindow)
+ {
+ BOOL oldstate = winInRaiseWindow;
+ XID vlist[1] = { 0 };
+ winInRaiseWindow = TRUE;
+ /* Call configure window directly to make sure it gets processed
+ * in time
+ */
+ ConfigureWindow(pWin, CWStackMode, vlist, serverClient);
+ winInRaiseWindow = oldstate;
+ }
+}
+
+static
+void winStartMousePolling(winPrivScreenPtr s_pScreenPriv)
+{
+ /*
+ * Timer to poll mouse position. This is needed to make
+ * programs like xeyes follow the mouse properly when the
+ * mouse pointer is outside of any X window.
+ */
+ if (g_uipMousePollingTimerID == 0)
+ g_uipMousePollingTimerID = SetTimer (s_pScreenPriv->hwndScreen,
+ WIN_POLLING_MOUSE_TIMER_ID,
+ MOUSE_POLLING_INTERVAL,
+ NULL);
+}
+
+/*
+ * winTopLevelWindowProc - Window procedure for all top-level Windows windows.
+ */
+
+LRESULT CALLBACK
+winTopLevelWindowProc (HWND hwnd, UINT message,
+ WPARAM wParam, LPARAM lParam)
+{
+ POINT ptMouse;
+ HDC hdcUpdate;
+ PAINTSTRUCT ps;
+ WindowPtr pWin = NULL;
+ winPrivWinPtr pWinPriv = NULL;
+ ScreenPtr s_pScreen = NULL;
+ winPrivScreenPtr s_pScreenPriv = NULL;
+ winScreenInfo *s_pScreenInfo = NULL;
+ HWND hwndScreen = NULL;
+ DrawablePtr pDraw = NULL;
+ winWMMessageRec wmMsg;
+ Bool fWMMsgInitialized = FALSE;
+ static Bool s_fTracking = FALSE;
+ Bool needRestack = FALSE;
+ LRESULT ret;
+
+ winDebugWin32Message("winTopLevelWindowProc", hwnd, message, wParam, lParam);
+
+ /* Check if the Windows window property for our X window pointer is valid */
+ if ((pWin = GetProp (hwnd, WIN_WINDOW_PROP)) != NULL)
+ {
+ /* Our X window pointer is valid */
+
+ /* Get pointers to the drawable and the screen */
+ pDraw = &pWin->drawable;
+ s_pScreen = pWin->drawable.pScreen;
+
+ /* Get a pointer to our window privates */
+ pWinPriv = winGetWindowPriv(pWin);
+
+ /* Get pointers to our screen privates and screen info */
+ s_pScreenPriv = pWinPriv->pScreenPriv;
+ s_pScreenInfo = s_pScreenPriv->pScreenInfo;
+
+ /* Get the handle for our screen-sized window */
+ hwndScreen = s_pScreenPriv->hwndScreen;
+
+ /* */
+ wmMsg.msg = 0;
+ wmMsg.hwndWindow = hwnd;
+ wmMsg.iWindow = (Window)GetProp (hwnd, WIN_WID_PROP);
+
+ wmMsg.iX = pDraw->x;
+ wmMsg.iY = pDraw->y;
+ wmMsg.iWidth = pDraw->width;
+ wmMsg.iHeight = pDraw->height;
+
+ fWMMsgInitialized = TRUE;
+
+ }
+
+ /* Branch on message type */
+ switch (message)
+ {
+ case WM_CREATE:
+
+ /* */
+ SetProp (hwnd,
+ WIN_WINDOW_PROP,
+ (HANDLE)((LPCREATESTRUCT) lParam)->lpCreateParams);
+
+ /* */
+ SetProp (hwnd,
+ WIN_WID_PROP,
+ (HANDLE)winGetWindowID (((LPCREATESTRUCT) lParam)->lpCreateParams));
+
+ /*
+ * Make X windows' Z orders sync with Windows windows because
+ * there can be AlwaysOnTop windows overlapped on the window
+ * currently being created.
+ */
+ winReorderWindowsMultiWindow ();
+
+ /* Fix a 'round title bar corner background should be transparent not black' problem when first painted */
+ {
+ RECT rWindow;
+ HRGN hRgnWindow;
+ GetWindowRect(hwnd, &rWindow);
+ hRgnWindow = CreateRectRgnIndirect(&rWindow);
+ SetWindowRgn (hwnd, hRgnWindow, TRUE);
+ }
+
+ SetWindowLongPtr(hwnd, GWLP_USERDATA, (LONG_PTR)VCXSRV_SIGNATURE);
+
+ return 0;
+
+ case WM_INIT_SYS_MENU:
+ /*
+ * Add whatever the setup file wants to for this window
+ */
+ SetupSysMenu ((unsigned long)hwnd);
+ return 0;
+
+ case WM_SYSCOMMAND:
+ /*
+ * Any window menu items go through here
+ */
+ if (HandleCustomWM_COMMAND ((unsigned long)hwnd, LOWORD(wParam)))
+ {
+ /* Don't pass customized menus to DefWindowProc */
+ return 0;
+ }
+ if (wParam == SC_RESTORE || wParam == SC_MAXIMIZE)
+ {
+ WINDOWPLACEMENT wndpl;
+ wndpl.length = sizeof(wndpl);
+ if (GetWindowPlacement(hwnd, &wndpl) && wndpl.showCmd == SW_SHOWMINIMIZED)
+ needRestack = TRUE;
+ }
+ break;
+
+ case WM_INITMENU:
+ /* Checks/Unchecks any menu items before they are displayed */
+ HandleCustomWM_INITMENU ((unsigned long)hwnd, wParam);
+ break;
+
+ case WM_ERASEBKGND:
+ /*
+ * Pretend that we did erase the background but we don't care,
+ * since we repaint the entire region anyhow
+ * This avoids some flickering when resizing.
+ */
+ return TRUE;
+
+ case WM_PAINT:
+ /* Only paint if our window handle is valid */
+ if (hwndScreen == NULL)
+ break;
+
+ /* BeginPaint gives us an hdc that clips to the invalidated region */
+ hdcUpdate = BeginPaint (hwnd, &ps);
+ /* Avoid the BitBlt's if the PAINTSTRUCT is bogus */
+ if (ps.rcPaint.right==0 && ps.rcPaint.bottom==0 && ps.rcPaint.left==0 && ps.rcPaint.top==0)
+ {
+ EndPaint (hwnd, &ps);
+ return 0;
+ }
+
+ /* Try to copy from the shadow buffer */
+ if (!BitBlt (hdcUpdate,
+ ps.rcPaint.left, ps.rcPaint.top,
+ ps.rcPaint.right - ps.rcPaint.left, ps.rcPaint.bottom - ps.rcPaint.top,
+ s_pScreenPriv->hdcShadow,
+ ps.rcPaint.left + pWin->drawable.x, ps.rcPaint.top + pWin->drawable.y,
+ SRCCOPY))
+ {
+ LPVOID lpMsgBuf;
+
+ /* Display a fancy error message */
+ FormatMessage (FORMAT_MESSAGE_ALLOCATE_BUFFER |
+ FORMAT_MESSAGE_FROM_SYSTEM |
+ FORMAT_MESSAGE_IGNORE_INSERTS,
+ NULL,
+ GetLastError (),
+ MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT),
+ (LPTSTR) &lpMsgBuf,
+ 0, NULL);
+
+ ErrorF ("winTopLevelWindowProc - BitBlt failed: %s\n",
+ (LPSTR)lpMsgBuf);
+ LocalFree (lpMsgBuf);
+ }
+
+ /* EndPaint frees the DC */
+ EndPaint (hwnd, &ps);
+ return 0;
+
+ case WM_MOUSEMOVE:
+ /* Unpack the client area mouse coordinates */
+ ptMouse.x = GET_X_LPARAM(lParam);
+ ptMouse.y = GET_Y_LPARAM(lParam);
+
+ /* Translate the client area mouse coordinates to screen coordinates */
+ ClientToScreen (hwnd, &ptMouse);
+
+ /* Screen Coords from (-X, -Y) -> Root Window (0, 0) */
+ ptMouse.x -= GetSystemMetrics (SM_XVIRTUALSCREEN);
+ ptMouse.y -= GetSystemMetrics (SM_YVIRTUALSCREEN);
+
+ /* We can't do anything without privates */
+ if (s_pScreenPriv == NULL || s_pScreenInfo->fIgnoreInput)
+ break;
+
+ /* Has the mouse pointer crossed screens? */
+ if (s_pScreen != miPointerGetScreen(g_pwinPointer))
+ miPointerSetScreen (g_pwinPointer, s_pScreenInfo->dwScreen,
+ ptMouse.x - s_pScreenInfo->dwXOffset,
+ ptMouse.y - s_pScreenInfo->dwYOffset);
+
+ /* Are we tracking yet? */
+ if (!s_fTracking)
+ {
+ TRACKMOUSEEVENT tme;
+
+ /* Setup data structure */
+ ZeroMemory (&tme, sizeof (tme));
+ tme.cbSize = sizeof (tme);
+ tme.dwFlags = TME_LEAVE;
+ tme.hwndTrack = hwnd;
+
+ /* Call the tracking function */
+ if (!(*g_fpTrackMouseEvent) (&tme))
+ ErrorF ("winTopLevelWindowProc - _TrackMouseEvent failed\n");
+
+ /* Flag that we are tracking now */
+ s_fTracking = TRUE;
+ }
+
+ /* Hide or show the Windows mouse cursor */
+ if (g_fSoftwareCursor && g_fCursor)
+ {
+ /* Hide Windows cursor */
+ g_fCursor = FALSE;
+ ShowCursor (FALSE);
+ }
+
+ /* Kill the timer used to poll mouse events */
+ if (g_uipMousePollingTimerID != 0)
+ {
+ KillTimer (s_pScreenPriv->hwndScreen, WIN_POLLING_MOUSE_TIMER_ID);
+ g_uipMousePollingTimerID = 0;
+ }
+
+ /* Deliver absolute cursor position to X Server */
+ winEnqueueMotion(ptMouse.x - s_pScreenInfo->dwXOffset,
+ ptMouse.y - s_pScreenInfo->dwYOffset);
+
+ return 0;
+
+ case WM_NCMOUSEMOVE:
+ /*
+ * We break instead of returning 0 since we need to call
+ * DefWindowProc to get the mouse cursor changes
+ * and min/max/close button highlighting in Windows XP.
+ * The Platform SDK says that you should return 0 if you
+ * process this message, but it fails to mention that you
+ * will give up any default functionality if you do return 0.
+ */
+
+ /* We can't do anything without privates */
+ if (s_pScreenPriv == NULL || s_pScreenInfo->fIgnoreInput)
+ break;
+
+ /* Non-client mouse movement, show Windows cursor */
+ if (g_fSoftwareCursor && !g_fCursor)
+ {
+ g_fCursor = TRUE;
+ ShowCursor (TRUE);
+ }
+
+ winStartMousePolling(s_pScreenPriv);
+
+ break;
+
+ case WM_MOUSELEAVE:
+ /* We can't do anything without privates */
+ if (s_pScreenPriv == NULL || s_pScreenInfo->fIgnoreInput)
+ break;
+ /* Mouse has left our client area */
+
+ /* Flag that we are no longer tracking */
+ s_fTracking = FALSE;
+
+ /* Show the mouse cursor, if necessary */
+ if (g_fSoftwareCursor && !g_fCursor)
+ {
+ g_fCursor = TRUE;
+ ShowCursor (TRUE);
+ }
+
+ winStartMousePolling(s_pScreenPriv);
+
+ return 0;
+
+ case WM_LBUTTONDBLCLK:
+ case WM_LBUTTONDOWN:
+ if (s_pScreenPriv == NULL || s_pScreenInfo->fIgnoreInput)
+ break;
+ g_fButton[0] = TRUE;
+ SetCapture(hwnd);
+ return winMouseButtonsHandle (s_pScreen, ButtonPress, Button1, wParam);
+
+ case WM_LBUTTONUP:
+ if (s_pScreenPriv == NULL || s_pScreenInfo->fIgnoreInput)
+ break;
+ g_fButton[0] = FALSE;
+ ReleaseCapture();
+ winStartMousePolling(s_pScreenPriv);
+ return winMouseButtonsHandle (s_pScreen, ButtonRelease, Button1, wParam);
+
+ case WM_MBUTTONDBLCLK:
+ case WM_MBUTTONDOWN:
+ if (s_pScreenPriv == NULL || s_pScreenInfo->fIgnoreInput)
+ break;
+ g_fButton[1] = TRUE;
+ SetCapture(hwnd);
+ return winMouseButtonsHandle (s_pScreen, ButtonPress, Button2, wParam);
+
+ case WM_MBUTTONUP:
+ if (s_pScreenPriv == NULL || s_pScreenInfo->fIgnoreInput)
+ break;
+ g_fButton[1] = FALSE;
+ ReleaseCapture();
+ winStartMousePolling(s_pScreenPriv);
+ return winMouseButtonsHandle (s_pScreen, ButtonRelease, Button2, wParam);
+
+ case WM_RBUTTONDBLCLK:
+ case WM_RBUTTONDOWN:
+ if (s_pScreenPriv == NULL || s_pScreenInfo->fIgnoreInput)
+ break;
+ g_fButton[2] = TRUE;
+ SetCapture(hwnd);
+ return winMouseButtonsHandle (s_pScreen, ButtonPress, Button3, wParam);
+
+ case WM_RBUTTONUP:
+ if (s_pScreenPriv == NULL || s_pScreenInfo->fIgnoreInput)
+ break;
+ g_fButton[2] = FALSE;
+ ReleaseCapture();
+ winStartMousePolling(s_pScreenPriv);
+ return winMouseButtonsHandle (s_pScreen, ButtonRelease, Button3, wParam);
+
+ case WM_XBUTTONDBLCLK:
+ case WM_XBUTTONDOWN:
+ if (s_pScreenPriv == NULL || s_pScreenInfo->fIgnoreInput)
+ break;
+ SetCapture(hwnd);
+ return winMouseButtonsHandle (s_pScreen, ButtonPress, HIWORD(wParam) + 5, wParam);
+
+ case WM_XBUTTONUP:
+ if (s_pScreenPriv == NULL || s_pScreenInfo->fIgnoreInput)
+ break;
+ ReleaseCapture();
+ winStartMousePolling(s_pScreenPriv);
+ return winMouseButtonsHandle (s_pScreen, ButtonRelease, HIWORD(wParam) + 5, wParam);
+
+ case WM_MOUSEWHEEL:
+ if (SendMessage(hwnd, WM_NCHITTEST, 0, MAKELONG(GET_X_LPARAM(lParam), GET_Y_LPARAM(lParam))) == HTCLIENT)
+ {
+ /* Pass the message to the root window */
+ SendMessage (hwndScreen, message, wParam, lParam);
+ return 0;
+ }
+ else break;
+
+ case WM_SETFOCUS:
+ if (s_pScreenPriv == NULL || s_pScreenInfo->fIgnoreInput)
+ break;
+
+ {
+ /* Get the parent window for transient handling */
+ HWND hParent = GetParent(hwnd);
+ if (hParent && IsIconic(hParent)) ShowWindow (hParent, SW_RESTORE);
+ }
+
+ winRestoreModeKeyStates ();
+
+ /* Add the keyboard hook if possible */
+ if (g_fKeyboardHookLL)
+ g_fKeyboardHookLL = winInstallKeyboardHookLL ();
+ return 0;
+
+ case WM_KILLFOCUS:
+ /* Pop any pressed keys since we are losing keyboard focus */
+ winKeybdReleaseKeys ();
+
+ /* Remove our keyboard hook if it is installed */
+ winRemoveKeyboardHookLL ();
+ if (!wParam)
+ /* Revert the X focus as well, but only if the Windows focus is going to another window */
+ DeleteWindowFromAnyEvents(pWin, FALSE);
+ return 0;
+
+ case WM_SYSDEADCHAR:
+ case WM_DEADCHAR:
+ /*
+ * NOTE: We do nothing with WM_*CHAR messages,
+ * nor does the root window, so we can just toss these messages.
+ */
+ return 0;
+
+ case WM_SYSKEYDOWN:
+ case WM_KEYDOWN:
+
+ /*
+ * Don't pass Alt-F4 key combo to root window,
+ * let Windows translate to WM_CLOSE and close this top-level window.
+ *
+ * NOTE: We purposely don't check the fUseWinKillKey setting because
+ * it should only apply to the key handling for the root window,
+ * not for top-level window-manager windows.
+ *
+ * ALSO NOTE: We do pass Ctrl-Alt-Backspace to the root window
+ * because that is a key combo that no X app should be expecting to
+ * receive, since it has historically been used to shutdown the X server.
+ * Passing Ctrl-Alt-Backspace to the root window preserves that
+ * behavior, assuming that -unixkill has been passed as a parameter.
+ */
+ if (wParam == VK_F4 && (GetKeyState (VK_MENU) & 0x8000))
+ break;
+
+#ifdef WINDBG
+ if (wParam == VK_ESCAPE)
+ {
+ /* Place for debug: put any tests and dumps here */
+ WINDOWPLACEMENT windPlace;
+ RECT rc;
+ LPRECT pRect;
+
+ windPlace.length = sizeof (WINDOWPLACEMENT);
+ GetWindowPlacement (hwnd, &windPlace);
+ pRect = &windPlace.rcNormalPosition;
+ winDebug ("\nCYGWINDOWING Dump:\n"
+ "\tdrawable: (%hd, %hd) - %hdx%hd\n", pDraw->x,
+ pDraw->y, pDraw->width, pDraw->height);
+ winDebug ("\twindPlace: (%ld, %ld) - %ldx%ld\n", pRect->left,
+ pRect->top, pRect->right - pRect->left,
+ pRect->bottom - pRect->top);
+ if (GetClientRect (hwnd, &rc))
+ {
+ pRect = &rc;
+ winDebug ("\tClientRect: (%ld, %ld) - %ldx%ld\n", pRect->left,
+ pRect->top, pRect->right - pRect->left,
+ pRect->bottom - pRect->top);
+ }
+ if (GetWindowRect (hwnd, &rc))
+ {
+ pRect = &rc;
+ winDebug ("\tWindowRect: (%ld, %ld) - %ldx%ld\n", pRect->left,
+ pRect->top, pRect->right - pRect->left,
+ pRect->bottom - pRect->top);
+ }
+ winDebug ("\n");
+ }
+#endif
+
+ /* Pass the message to the root window */
+ return winWindowProc(hwndScreen, message, wParam, lParam);
+
+ case WM_SYSKEYUP:
+ case WM_KEYUP:
+
+
+ /* Pass the message to the root window */
+ return winWindowProc(hwndScreen, message, wParam, lParam);
+
+ case WM_HOTKEY:
+
+ /* Pass the message to the root window */
+ SendMessage (hwndScreen, message, wParam, lParam);
+ return 0;
+
+ case WM_ACTIVATE:
+
+ /* Pass the message to the root window */
+ SendMessage (hwndScreen, message, wParam, lParam);
+
+ if (LOWORD(wParam) != WA_INACTIVE)
+ {
+ /* Raise the window to the top in Z order */
+ /* ago: Activate does not mean putting it to front! */
+ /*
+ wmMsg.msg = WM_WM_RAISE;
+ if (fWMMsgInitialized)
+ winSendMessageToWM (s_pScreenPriv->pWMInfo, &wmMsg);
+ */
+
+ /* Tell our Window Manager thread to activate the window */
+ wmMsg.msg = WM_WM_ACTIVATE;
+ if (fWMMsgInitialized && pWin->realized && !pWin->overrideRedirect /* for OOo menus */)
+ winSendMessageToWM (s_pScreenPriv->pWMInfo, &wmMsg);
+ }
+ /* Prevent the mouse wheel from stalling when another window is minimized */
+ if (HIWORD(wParam) == 0 && LOWORD(wParam) == WA_ACTIVE &&
+ (HWND)lParam != NULL && (HWND)lParam != (HWND)GetParent(hwnd))
+ SetFocus(hwnd);
+ return 0;
+
+ case WM_ACTIVATEAPP:
+ /*
+ * This message is also sent to the root window
+ * so we do nothing for individual multiwindow windows
+ */
+ break;
+
+ case WM_CLOSE:
+ /* Branch on if the window was killed in X already */
+ if (pWinPriv->fXKilled)
+ {
+ /* Window was killed, go ahead and destroy the window */
+ DestroyWindow (hwnd);
+ }
+ else
+ {
+ /* Tell our Window Manager thread to kill the window */
+ wmMsg.msg = WM_WM_KILL;
+ if (fWMMsgInitialized)
+ winSendMessageToWM (s_pScreenPriv->pWMInfo, &wmMsg);
+ }
+ return 0;
+
+ case WM_DESTROY:
+
+ /* Branch on if the window was killed in X already */
+ if (pWinPriv && !pWinPriv->fXKilled)
+ {
+ winDebug ("winTopLevelWindowProc - WM_DESTROY - WM_WM_KILL\n");
+
+ /* Tell our Window Manager thread to kill the window */
+ wmMsg.msg = WM_WM_KILL;
+ if (fWMMsgInitialized)
+ winSendMessageToWM (s_pScreenPriv->pWMInfo, &wmMsg);
+ }
+
+ RemoveProp (hwnd, WIN_WINDOW_PROP);
+ RemoveProp (hwnd, WIN_WID_PROP);
+ RemoveProp (hwnd, WIN_NEEDMANAGE_PROP);
+
+ break;
+
+ case WM_MOVE:
+ /* Adjust the X Window to the moved Windows window */
+ winAdjustXWindow (pWin, hwnd);
+ return 0;
+
+ case WM_SHOWWINDOW:
+ /* Bail out if the window is being hidden */
+ if (!wParam)
+ return 0;
+
+ /* */
+ if (!pWin->overrideRedirect)
+ {
+ /* Flag that this window needs to be made active when clicked */
+ SetProp (hwnd, WIN_NEEDMANAGE_PROP, (HANDLE) 1);
+
+ if (!(GetWindowLongPtr (hwnd, GWL_EXSTYLE) & WS_EX_APPWINDOW))
+ {
+ HWND zstyle = HWND_NOTOPMOST;
+
+ /* Set the window extended style flags */
+ SetWindowLongPtr (hwnd, GWL_EXSTYLE, WS_EX_APPWINDOW);
+
+ /* Set the transient style flags */
+ if (GetParent(hwnd)) SetWindowLongPtr (hwnd, GWL_STYLE,
+ WS_POPUP | WS_OVERLAPPED | WS_SYSMENU | WS_CLIPCHILDREN | WS_CLIPSIBLINGS);
+ /* Set the window standard style flags */
+ else SetWindowLongPtr (hwnd, GWL_STYLE,
+ (WS_POPUP | WS_OVERLAPPEDWINDOW | WS_CLIPCHILDREN | WS_CLIPSIBLINGS)
+ & ~WS_CAPTION & ~WS_SIZEBOX);
+
+ winUpdateWindowPosition (hwnd, FALSE, &zstyle);
+ SetForegroundWindow (hwnd);
+ }
+ wmMsg.msg = WM_WM_MAP3;
+ }
+ else /* It is an overridden window so make it top of Z stack */
+ {
+ HWND forHwnd = GetForegroundWindow();
+ winDebug ("overridden window is shown\n");
+ if (forHwnd != NULL)
+ {
+ if (GetWindowLongPtr(forHwnd, GWLP_USERDATA) & (LONG_PTR)VCXSRV_SIGNATURE)
+ {
+ if (GetWindowLongPtr(forHwnd, GWL_EXSTYLE) & WS_EX_TOPMOST)
+ SetWindowPos (hwnd, HWND_TOPMOST, 0, 0, 0, 0, SWP_NOMOVE | SWP_NOSIZE | SWP_NOACTIVATE);
+ else
+ SetWindowPos (hwnd, HWND_NOTOPMOST, 0, 0, 0, 0, SWP_NOMOVE | SWP_NOSIZE | SWP_NOACTIVATE);
+ }
+ }
+ wmMsg.msg = WM_WM_MAP2;
+ }
+
+ /* Tell our Window Manager thread to map the window */
+ if (fWMMsgInitialized)
+ winSendMessageToWM (s_pScreenPriv->pWMInfo, &wmMsg);
+
+ winStartMousePolling(s_pScreenPriv);
+
+ return 0;
+
+ case WM_SIZING:
+ /* Need to legalize the size according to WM_NORMAL_HINTS */
+ /* for applications like xterm */
+ return ValidateSizing (hwnd, pWin, wParam, lParam);
+
+ case WM_WINDOWPOSCHANGED:
+ {
+ LPWINDOWPOS pWinPos = (LPWINDOWPOS) lParam;
+
+ if (!(pWinPos->flags & SWP_NOZORDER))
+ {
+#if CYGWINDOWING_DEBUG
+ winDebug ("\twindow z order was changed\n");
+#endif
+ if (pWinPos->hwndInsertAfter == HWND_TOP
+ ||pWinPos->hwndInsertAfter == HWND_TOPMOST
+ ||pWinPos->hwndInsertAfter == HWND_NOTOPMOST)
+ {
+#if CYGWINDOWING_DEBUG
+ winDebug ("\traise to top\n");
+#endif
+ /* Raise the window to the top in Z order */
+ winRaiseWindow(pWin);
+ }
+ else if (pWinPos->hwndInsertAfter == HWND_BOTTOM)
+ {
+ }
+ else
+ {
+ /* Check if this window is top of X windows. */
+ HWND hWndAbove = NULL;
+ DWORD dwCurrentProcessID = GetCurrentProcessId ();
+ DWORD dwWindowProcessID = 0;
+
+ for (hWndAbove = pWinPos->hwndInsertAfter;
+ hWndAbove != NULL;
+ hWndAbove = GetNextWindow (hWndAbove, GW_HWNDPREV))
+ {
+ /* Ignore other XWin process's window */
+ GetWindowThreadProcessId (hWndAbove, &dwWindowProcessID);
+
+ if ((dwWindowProcessID == dwCurrentProcessID)
+ && GetProp (hWndAbove, WIN_WINDOW_PROP)
+ && !IsWindowVisible (hWndAbove)
+ && !IsIconic (hWndAbove) ) /* ignore minimized windows */
+ break;
+ }
+ /* If this is top of X windows in Windows stack,
+ raise it in X stack. */
+ if (hWndAbove == NULL)
+ {
+#if CYGWINDOWING_DEBUG
+ winDebug ("\traise to top\n");
+#endif
+ winRaiseWindow(pWin);
+ }
+ }
+ }
+ }
+ /*
+ * Pass the message to DefWindowProc to let the function
+ * break down WM_WINDOWPOSCHANGED to WM_MOVE and WM_SIZE.
+ */
+ break;
+
+ case WM_SIZE:
+ /* see dix/window.c */
+#ifdef WINDBG
+ {
+ char buf[64];
+ switch (wParam)
+ {
+ case SIZE_MINIMIZED:
+ strcpy(buf, "SIZE_MINIMIZED");
+ break;
+ case SIZE_MAXIMIZED:
+ strcpy(buf, "SIZE_MAXIMIZED");
+ break;
+ case SIZE_RESTORED:
+ strcpy(buf, "SIZE_RESTORED");
+ break;
+ default:
+ strcpy(buf, "UNKNOWN_FLAG");
+ }
+ winDebug ("winTopLevelWindowProc - WM_SIZE to %dx%d (%s) - %d ms\n",
+ (int)LOWORD(lParam), (int)HIWORD(lParam), buf,
+ (int)(GetTickCount ()));
+ }
+#endif
+ /* Adjust the X Window to the moved Windows window */
+ winAdjustXWindow (pWin, hwnd);
+ if (wParam == SIZE_MINIMIZED) winReorderWindowsMultiWindow();
+ return 0; /* end of WM_SIZE handler */
+
+ case WM_STYLECHANGING:
+ /*
+ When the style changes, adjust the Windows window size so the client area remains the same size,
+ and adjust the Windows window position so that the client area remains in the same place.
+ */
+ {
+ RECT newWinRect;
+ DWORD dwExStyle;
+ DWORD dwStyle;
+ DWORD newStyle = ((STYLESTRUCT *)lParam)->styleNew;
+ WINDOWINFO wi;
+
+ dwExStyle = GetWindowLongPtr (hwnd, GWL_EXSTYLE);
+ dwStyle = GetWindowLongPtr (hwnd, GWL_STYLE);
+
+ winDebug("winTopLevelWindowProc - WM_STYLECHANGING from %08x %08x\n", dwStyle, dwExStyle);
+
+ if (wParam == GWL_EXSTYLE)
+ dwExStyle = newStyle;
+
+ if (wParam == GWL_STYLE)
+ dwStyle = newStyle;
+
+ winDebug("winTopLevelWindowProc - WM_STYLECHANGING to %08x %08x\n", dwStyle, dwExStyle);
+
+ /* Get client rect in screen coordinates */
+ wi.cbSize = sizeof(WINDOWINFO);
+ GetWindowInfo(hwnd, &wi);
+
+ winDebug("winTopLevelWindowProc - WM_STYLECHANGING client area {%d, %d, %d, %d}, {%d x %d}\n", wi.rcClient.left, wi.rcClient.top, wi.rcClient.right, wi.rcClient.bottom, wi.rcClient.right - wi.rcClient.left, wi.rcClient.bottom - wi.rcClient.top);
+
+ newWinRect = wi.rcClient;
+ if (!AdjustWindowRectEx(&newWinRect, dwStyle, FALSE, dwExStyle))
+ winDebug("winTopLevelWindowProc - WM_STYLECHANGING AdjustWindowRectEx failed\n");
+
+ winDebug("winTopLevelWindowProc - WM_STYLECHANGING window area should be {%d, %d, %d, %d}, {%d x %d}\n", newWinRect.left, newWinRect.top, newWinRect.right, newWinRect.bottom, newWinRect.right - newWinRect.left, newWinRect.bottom - newWinRect.top);
+
+ /*
+ Style change hasn't happened yet, so we can't adjust the window size yet, as the winAdjustXWindow()
+ which WM_SIZE does will use the current (unchanged) style. Instead make a note to change it when
+ WM_STYLECHANGED is received...
+ */
+ pWinPriv->hDwp = BeginDeferWindowPos(1);
+ pWinPriv->hDwp = DeferWindowPos(pWinPriv->hDwp, hwnd, NULL, newWinRect.left, newWinRect.top, newWinRect.right - newWinRect.left, newWinRect.bottom - newWinRect.top, SWP_NOACTIVATE | SWP_NOZORDER);
+ }
+ return 0;
+
+ case WM_STYLECHANGED:
+ {
+ if (pWinPriv->hDwp)
+ {
+ EndDeferWindowPos(pWinPriv->hDwp);
+ pWinPriv->hDwp = NULL;
+ }
+ winDebug("winTopLevelWindowProc - WM_STYLECHANGED done\n");
+ }
+ return 0;
+
+ case WM_MOUSEACTIVATE:
+
+ /* Check if this window needs to be made active when clicked */
+ if (!GetProp (pWinPriv->hWnd, WIN_NEEDMANAGE_PROP))
+ {
+ winDebug ("winTopLevelWindowProc - WM_MOUSEACTIVATE - "
+ "MA_NOACTIVATE\n");
+
+ /* */
+ return MA_NOACTIVATE;
+ }
+ break;
+
+ case WM_SETCURSOR:
+ if (LOWORD(lParam) == HTCLIENT)
+ {
+ if (!g_fSoftwareCursor) SetCursor (s_pScreenPriv->cursor.handle);
+ return TRUE;
+ }
+ break;
+
+ default:
+ break;
+ }
+
+ ret = DefWindowProc (hwnd, message, wParam, lParam);
+ /*
+ * If the window was minized we get the stack change before the window is restored
+ * and so it gets lost. Ensure there stacking order is correct.
+ */
+ if (needRestack)
+ winReorderWindowsMultiWindow();
+ return ret;
+}
diff --git a/xorg-server/hw/xwin/winwindow.h b/xorg-server/hw/xwin/winwindow.h
index 8778fc696..5839a7a42 100644
--- a/xorg-server/hw/xwin/winwindow.h
+++ b/xorg-server/hw/xwin/winwindow.h
@@ -75,6 +75,7 @@ typedef struct
BOOL OpenGlWindow;
winPrivScreenPtr pScreenPriv;
Bool fXKilled;
+ HDWP hDwp;
/* Privates used by primary fb DirectDraw server */
LPDDSURFACEDESC pddsdPrimary;