Index: unix/tkUnixSend.c
==================================================================
--- unix/tkUnixSend.c
+++ unix/tkUnixSend.c
@@ -259,14 +259,17 @@
     NameRegistry *regPtr;
     int result, actualFormat;
     unsigned long bytesAfter;
     Atom actualType;
     char **propertyPtr;
+    Tk_ErrorHandler handler;
 
     if (dispPtr->commTkwin == NULL) {
 	SendInit(interp, dispPtr);
     }
+
+    handler = Tk_CreateErrorHandler(dispPtr->display, -1, -1, -1, NULL, NULL);
 
     regPtr = ckalloc(sizeof(NameRegistry));
     regPtr->dispPtr = dispPtr;
     regPtr->locked = 0;
     regPtr->modified = 0;
@@ -304,11 +307,14 @@
 	    regPtr->property = NULL;
 	}
 	XDeleteProperty(dispPtr->display,
 		RootWindow(dispPtr->display, 0),
 		dispPtr->registryProperty);
+	XSync(dispPtr->display, False);
     }
+
+    Tk_DeleteErrorHandler(handler);
 
     /*
      * Xlib placed an extra null byte after the end of the property, just to
      * make sure that it is always NULL-terminated. Be sure to include this
      * byte in our count if it's needed to ensure null termination (note: as
@@ -512,10 +518,15 @@
 static void
 RegClose(
     NameRegistry *regPtr)	/* Pointer to a registry opened with a
 				 * previous call to RegOpen. */
 {
+    Tk_ErrorHandler handler;
+
+    handler = Tk_CreateErrorHandler(regPtr->dispPtr->display, -1, -1, -1,
+		    NULL, NULL);
+
     if (regPtr->modified) {
 	if (!regPtr->locked && !localData.sendDebug) {
 	    Tcl_Panic("The name registry was modified without being locked!");
 	}
 	XChangeProperty(regPtr->dispPtr->display,
@@ -537,10 +548,12 @@
      * ungrab command is still sitting in our output buffer, we could
      * deadlock.
      */
 
     XFlush(regPtr->dispPtr->display);
+
+    Tk_DeleteErrorHandler(handler);
 
     if (regPtr->property != NULL) {
 	if (regPtr->allocedByX) {
 	    XFree(regPtr->property);
 	} else {
@@ -1093,10 +1106,35 @@
     Tcl_DStringAppend(&request, Tcl_GetString(objv[firstArg]), -1);
     for (i = firstArg+1; i < objc; i++) {
 	Tcl_DStringAppend(&request, " ", 1);
 	Tcl_DStringAppend(&request, Tcl_GetString(objv[i]), -1);
     }
+
+    if (!async) {
+	/*
+	 * Register the fact that we're waiting for a command to complete
+	 * (this is needed by SendEventProc and by AppendErrorProc to pass
+	 * back the command's results). Set up a timeout handler so that
+	 * we can check during long sends to make sure that the destination
+	 * application is still alive.
+	 *
+	 * We prepare the pending struct here in order to catch potential
+	 * early X errors from AppendPropCarefully() due to XSync().
+	 */
+
+	pending.serial = localData.sendSerial;
+	pending.dispPtr = dispPtr;
+	pending.target = destName;
+	pending.commWindow = commWindow;
+	pending.interp = interp;
+	pending.result = NULL;
+	pending.errorInfo = NULL;
+	pending.errorCode = NULL;
+	pending.gotResponse = 0;
+	pending.nextPtr = tsdPtr->pendingCommands;
+	tsdPtr->pendingCommands = &pending;
+    }
     (void) AppendPropCarefully(dispPtr->display, commWindow,
 	    dispPtr->commProperty, Tcl_DStringValue(&request),
 	    Tcl_DStringLength(&request) + 1, (async ? NULL : &pending));
     Tcl_DStringFree(&request);
     if (async) {
@@ -1106,30 +1144,10 @@
 	 */
 
 	return TCL_OK;
     }
 
-    /*
-     * Register the fact that we're waiting for a command to complete (this is
-     * needed by SendEventProc and by AppendErrorProc to pass back the
-     * command's results). Set up a timeout handler so that we can check
-     * during long sends to make sure that the destination application is
-     * still alive.
-     */
-
-    pending.serial = localData.sendSerial;
-    pending.dispPtr = dispPtr;
-    pending.target = destName;
-    pending.commWindow = commWindow;
-    pending.interp = interp;
-    pending.result = NULL;
-    pending.errorInfo = NULL;
-    pending.errorCode = NULL;
-    pending.gotResponse = 0;
-    pending.nextPtr = tsdPtr->pendingCommands;
-    tsdPtr->pendingCommands = &pending;
-
     /*
      * Enter a loop processing X events until the result comes in or the
      * target is declared to be dead. While waiting for a result, look only at
      * send-related events so that the send is synchronous with respect to
      * other events in the application.
@@ -1957,15 +1975,15 @@
 	Tcl_WrongNumArgs(interp, 1, objv,
 		"option ?arg ...?");
 	return TCL_ERROR;
     }
 
-	if (Tcl_GetIndexFromObjStruct(interp, objv[1], testsendOptions,
+    if (Tcl_GetIndexFromObjStruct(interp, objv[1], testsendOptions,
 		sizeof(char *), "option", 0, &index) != TCL_OK) {
-	    return TCL_ERROR;
-	}
-	if (index == TESTSEND_BOGUS) {
+	return TCL_ERROR;
+    }
+    if (index == TESTSEND_BOGUS) {
 	XChangeProperty(winPtr->dispPtr->display,
 		RootWindow(winPtr->dispPtr->display, 0),
 		winPtr->dispPtr->registryProperty, XA_INTEGER, 32,
 		PropModeReplace,
 		(unsigned char *) "This is bogus information", 6);

