• Mike Gabriel's avatar
    nx-X11 vs. X.Org 6.9 patches for further studying / documentation · 1e5ee575
    Mike Gabriel authored
      NoMachine kept all original X.Org 6.9 files in the nx-X11 source
      tree. These files have been removed in Feb 2015 during a major
      code cleanup.
    
      For later studying we provide all diffs of the changes that
      NoMachine employed on the original X.Org X11 code tree in the
      doc/nx-X11_vs_XOrg69_patches folder.
    1e5ee575
NXproperty.c.NX.patch 9.31 KB
--- ./nx-X11/programs/Xserver/hw/nxagent/X/NXproperty.c.X.original	2015-02-13 14:03:44.744441510 +0100
+++ ./nx-X11/programs/Xserver/hw/nxagent/X/NXproperty.c	2015-02-10 19:13:13.772687085 +0100
@@ -1,3 +1,20 @@
+/**************************************************************************/
+/*                                                                        */
+/* Copyright (c) 2001, 2011 NoMachine, http://www.nomachine.com/.         */
+/*                                                                        */
+/* NXAGENT, NX protocol compression and NX extensions to this software    */
+/* are copyright of NoMachine. Redistribution and use of the present      */
+/* software is allowed according to terms specified in the file LICENSE   */
+/* which comes in the source distribution.                                */
+/*                                                                        */
+/* Check http://www.nomachine.com/licensing.html for applicability.       */
+/*                                                                        */
+/* NX and NoMachine are trademarks of Medialogic S.p.A.                   */
+/*                                                                        */
+/* All rights reserved.                                                   */
+/*                                                                        */
+/**************************************************************************/
+
 /* $XFree86: xc/programs/Xserver/dix/property.c,v 3.12 2002/02/19 11:09:22 alanh Exp $ */
 /***********************************************************
 
@@ -58,7 +75,7 @@
 #include "windowstr.h"
 #include "propertyst.h"
 #include "dixstruct.h"
-#include "dispatch.h"
+#include "../../dix/dispatch.h"
 #include "swaprep.h"
 #ifdef XCSECURITY
 #define _SECURITY_SERVER
@@ -69,6 +86,11 @@
 #include "lbxtags.h"
 #endif
 
+#include "Options.h"
+#include "Rootless.h"
+#include "Client.h"
+#include "Windows.h"
+
 #if defined(LBX) || defined(LBX_COMPAT)
 #if 0 /* no header in X11 environment, not used in X11 environment */
 int fWriteToClient(ClientPtr client, int len, char *buf)
@@ -78,6 +100,17 @@
 #endif
 #endif
 
+extern Atom clientCutProperty;
+
+#ifdef NXAGENT_SERVER
+typedef struct
+{
+  CARD32 state;
+  Window icon;
+}
+nxagentWMStateRec;
+#endif
+
 /*****************************************************************
  * Property Stuff
  *
@@ -234,6 +267,15 @@
     totalSize = len * sizeInBytes;
     REQUEST_FIXED_SIZE(xChangePropertyReq, totalSize);
 
+#ifdef NXAGENT_CLIPBOARD
+    {
+       extern WindowPtr nxagentGetClipboardWindow(Atom, WindowPtr);
+
+       pWin = nxagentGetClipboardWindow(stuff->property, NULL);
+    }
+
+    if (pWin == NULL)
+#endif
     pWin = (WindowPtr)SecurityLookupWindow(stuff->window, client,
 					   SecurityWriteAccess);
     if (!pWin)
@@ -261,6 +303,18 @@
     }
 #endif
 
+#ifdef NXAGENT_ARTSD
+    {
+    /* Do not process MCOPGLOBALS property changes,
+      they are already set reflecting the server side settings.
+      Just return success.
+    */
+      extern Atom mcop_local_atom;
+      if (stuff->property == mcop_local_atom)
+        return client->noClientException;
+    }
+#endif
+
 #ifdef LBX
     err = LbxChangeWindowProperty(client, pWin, stuff->property, stuff->type,
 	 (int)format, (int)mode, len, TRUE, (pointer)&stuff[1], TRUE, NULL);
@@ -271,7 +325,23 @@
     if (err != Success)
 	return err;
     else
-	return client->noClientException;
+    {
+      if (nxagentOption(Rootless) == 1)
+      {
+        nxagentExportProperty(pWin, stuff->property, stuff->type, (int) format,
+                                  (int) mode, len, (pointer) &stuff[1]);
+      }
+
+      nxagentGuessClientHint(client, stuff->property, (char *) &stuff[1]);
+
+      nxagentGuessShadowHint(client, stuff->property);
+
+      #ifdef NX_DEBUG_INPUT
+      nxagentGuessDumpInputInfo(client, stuff->property, (char *) &stuff[1]);
+      #endif
+
+      return client->noClientException;
+    }
 }
 
 int
@@ -289,10 +359,23 @@
     int sizeInBytes;
     int totalSize;
     pointer data;
+    int copySize;
 
     sizeInBytes = format>>3;
     totalSize = len * sizeInBytes;
 
+    copySize = nxagentOption(CopyBufferSize);
+
+    if (copySize != COPY_UNLIMITED && property == clientCutProperty)
+    {
+      if (totalSize > copySize)
+      {
+        totalSize = copySize;
+        totalSize = totalSize - (totalSize % sizeInBytes);
+        len = totalSize / sizeInBytes;
+      }
+    }
+
     /* first see if property already exists */
 
     pProp = wUserProps (pWin);
@@ -491,6 +574,11 @@
 int
 ProcGetProperty(ClientPtr client)
 {
+    #ifdef NXAGENT_SERVER
+    nxagentWMStateRec wmState;
+    nxagentWMStateRec *wmsP = &wmState;
+    #endif
+
     PropertyPtr pProp, prevProp;
     unsigned long n, len, ind;
     WindowPtr pWin;
@@ -498,6 +586,7 @@
     REQUEST(xGetPropertyReq);
 
     REQUEST_SIZE_MATCH(xGetPropertyReq);
+
     if (stuff->delete)
 	UpdateCurrentTime();
     pWin = (WindowPtr)SecurityLookupWindow(stuff->window, client,
@@ -533,6 +622,59 @@
 
     reply.type = X_Reply;
     reply.sequenceNumber = client->sequence;
+
+    #ifdef NXAGENT_SERVER
+
+    /*
+     * Creating a reply for WM_STATE property if it doesn't exist.
+     * This is intended to allow drag & drop work in JAva 1.6 when
+     * the agent is connected to NXWin in multiwindow mode.
+     */
+
+    if (nxagentOption(Rootless) &&
+            nxagentWindowTopLevel(pWin) &&
+                (!pProp) &&
+                    strcmp(NameForAtom(stuff->property), "WM_STATE") == 0)
+    {
+      wmState.state = 1;
+      wmState.icon = None;
+
+      if (ChangeWindowProperty(pWin, stuff->property, stuff->property, 32, 0, 2, &wmState, 1) == Success)
+      {
+        nxagentExportProperty(pWin, stuff->property, stuff->property, 32, 0, 2, &wmState);
+      }
+
+      n = 8;
+      ind = stuff->longOffset << 2;        
+
+      if (n < ind)
+      {
+        client->errorValue = stuff->longOffset;
+        return BadValue;
+      }
+
+      len = min(n - ind, 4 * stuff->longLength);
+
+      reply.bytesAfter = n - (ind + len);
+      reply.length = (len + 3) >> 2;
+
+      reply.format = 32;
+      reply.nItems = len / 4;
+      reply.propertyType = stuff->property;
+
+      WriteReplyToClient(client, sizeof(xGenericReply), &reply);
+
+      if (len)
+      {
+        client->pSwapReplyFunc = (ReplySwapPtr)CopySwap32Write;
+
+        WriteSwappedDataToClient(client, len, (char *)wmsP + ind);
+      }
+
+      return(client->noClientException);
+    }
+    #endif
+
     if (!pProp) 
 	return NullPropertyReply(client, None, 0, &reply);
 
@@ -643,6 +785,126 @@
     return(client->noClientException);
 }
 
+#ifdef NXAGENT_CLIPBOARD
+/* GetWindowProperty clipboard use only */
+int
+GetWindowProperty(pWin, property, longOffset, longLength, delete,
+            type, actualType, format, nItems, bytesAfter, propData )
+    WindowPtr	        pWin;
+    Atom		property;
+    long			longOffset;
+    long			longLength;
+    Bool			delete;
+    Atom		type;
+    Atom		*actualType;
+    int			*format;
+    unsigned long	*nItems;
+    unsigned long	*bytesAfter;
+    unsigned char	**propData;
+{
+    PropertyPtr pProp, prevProp;
+    unsigned long n, len, ind;
+
+    if (!pWin)
+	return BadWindow;
+
+
+    if (!ValidAtom(property))
+    {
+	return(BadAtom);
+    }
+    if ((type != AnyPropertyType) && !ValidAtom(type))
+    {
+	return(BadAtom);
+    }
+
+    pProp = wUserProps (pWin);
+    prevProp = (PropertyPtr)NULL;
+
+    while (pProp)
+    {
+	if (pProp->propertyName == property)
+	    break;
+	prevProp = pProp;
+	pProp = pProp->next;
+    }
+
+
+    if (!pProp)
+	return (BadAtom);
+
+    /* If the request type and actual type don't match. Return the
+    property information, but not the data. */
+
+    if (((type != pProp->type) &&
+	 (type != AnyPropertyType))
+       )
+    {
+	*bytesAfter = pProp->size;
+	*format = pProp->format;
+	*nItems = 0;
+	*actualType = pProp->type;
+	return(Success);
+    }
+
+/*
+ *  Return type, format, value to client
+ */
+    n = (pProp->format/8) * pProp->size; /* size (bytes) of prop */
+    ind = longOffset << 2;
+
+   /* If longOffset is invalid such that it causes "len" to
+	    be negative, it's a value error. */
+
+    if (n < ind)
+    {
+	return BadValue;
+    }
+
+    len = min(n - ind, 4 * longLength);
+
+    *bytesAfter = n - (ind + len);
+    *format = pProp->format;
+    *nItems = len / (pProp->format / 8 );
+    *actualType = pProp->type;
+
+    if (delete && (*bytesAfter == 0))
+    { /* send the event */
+	xEvent event;
+
+	event.u.u.type = PropertyNotify;
+	event.u.property.window = pWin->drawable.id;
+	event.u.property.state = PropertyDelete;
+	event.u.property.atom = pProp->propertyName;
+	event.u.property.time = currentTime.milliseconds;
+	DeliverEvents(pWin, &event, 1, (WindowPtr)NULL);
+    }
+
+    if (len)
+    {
+	 *propData = (unsigned char *)(pProp->data) + ind;
+    }
+
+    if (delete && (*bytesAfter == 0))
+    { /* delete the Property */
+#ifdef LBX
+	if (pProp->tag_id)
+	    TagDeleteTag(pProp->tag_id);
+#endif
+	if (prevProp == (PropertyPtr)NULL) /* takes care of head */
+	{
+	    if (!(pWin->optional->userProps = pProp->next))
+		CheckWindowOptionalNeed (pWin);
+	}
+	else
+	    prevProp->next = pProp->next;
+	xfree(pProp->data);
+	xfree(pProp);
+    }
+    return(Success);
+}
+#endif
+
 int
 ProcListProperties(ClientPtr client)
 {
@@ -727,3 +989,4 @@
     else
 	return(result);
 }
+