diff options
author | Richard M. Stallman <rms@gnu.org> | 1995-02-02 18:49:38 +0000 |
---|---|---|
committer | Richard M. Stallman <rms@gnu.org> | 1995-02-02 18:49:38 +0000 |
commit | 95a8a747e4be74008041681e61757f2d37ce6caf (patch) | |
tree | 0ee72b8ef9f5a1e4b456022969d97f09a2e37c85 /src/xselect.c | |
parent | e9f0bf5568595cebbb07d6396148c7eb2b5b4ee1 (diff) | |
download | emacs-95a8a747e4be74008041681e61757f2d37ce6caf.tar.gz |
(wait_for_property_change): Avoid unlikely timing error.
(x_get_foreign_selection): Pass display to
x_start_queueing_selection_events and x_stop_queueing_selection_events.
(x_reply_selection_request): Call x_start_queueing_selection_events
and x_stop_queueing_selection_events. Handle X protocol errors.
Diffstat (limited to 'src/xselect.c')
-rw-r--r-- | src/xselect.c | 39 |
1 files changed, 22 insertions, 17 deletions
diff --git a/src/xselect.c b/src/xselect.c index 90ccdbbfde4..5e7432e9e47 100644 --- a/src/xselect.c +++ b/src/xselect.c @@ -17,18 +17,11 @@ You should have received a copy of the GNU General Public License along with GNU Emacs; see the file COPYING. If not, write to the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */ -/* x_handle_selection_notify -x_reply_selection_request */ - /* Rewritten by jwz */ #include <config.h> #include "lisp.h" -#if 0 -#include <stdio.h> /* termhooks.h needs this */ -#include "termhooks.h" -#endif #include "xterm.h" /* for all of the X includes */ #include "dispextern.h" /* frame.h seems to want this */ #include "frame.h" /* Need this to get the X window of selected_frame */ @@ -500,6 +493,8 @@ x_reply_selection_request (event, format, data, size, type) reply.property = reply.target; /* #### XChangeProperty can generate BadAlloc, and we must handle it! */ + BLOCK_INPUT; + x_catch_errors (display); /* Store the data on the requested property. If the selection is large, only store the first N bytes of it. @@ -511,20 +506,18 @@ x_reply_selection_request (event, format, data, size, type) #if 0 fprintf (stderr,"\nStoring all %d\n", bytes_remaining); #endif - BLOCK_INPUT; XChangeProperty (display, window, reply.property, type, format, PropModeReplace, data, size); /* At this point, the selection was successfully stored; ack it. */ XSendEvent (display, window, False, 0L, (XEvent *) &reply); - XFlush (display); - UNBLOCK_INPUT; } else { /* Send an INCR selection. */ struct prop_location *wait_object; + int had_errors; - BLOCK_INPUT; + x_start_queuing_selection_requests (display); if (x_window_to_frame (window)) /* #### debug */ error ("attempt to transfer an INCR to ourself!"); @@ -541,11 +534,14 @@ x_reply_selection_request (event, format, data, size, type) /* Tell 'em the INCR data is there... */ (void) XSendEvent (display, window, False, 0L, (XEvent *) &reply); XFlush (display); + + had_errors = x_had_errors_p (display); UNBLOCK_INPUT; /* First, wait for the requestor to ack by deleting the property. This can run random lisp code (process handlers) or signal. */ - wait_for_property_change (wait_object); + if (! had_errors) + wait_for_property_change (wait_object); while (bytes_remaining) { @@ -567,8 +563,12 @@ x_reply_selection_request (event, format, data, size, type) bytes_remaining -= i; data += i; XFlush (display); + had_errors = x_had_errors_p (display); UNBLOCK_INPUT; + if (had_errors) + break; + /* Now wait for the requestor to ack this chunk by deleting the property. This can run random lisp code or signal. */ @@ -585,9 +585,12 @@ x_reply_selection_request (event, format, data, size, type) XChangeProperty (display, window, reply.property, type, format, PropModeReplace, data, 0); - XFlush (display); - UNBLOCK_INPUT; + x_stop_queuing_selection_requests (display); } + + XFlush (display); + x_uncatch_errors (display); + UNBLOCK_INPUT; } /* Handle a SelectionRequest event EVENT. @@ -912,9 +915,11 @@ wait_for_property_change (location) XCONS (property_change_reply)->car = Qnil; + property_change_reply_object = location; + /* If the event we are waiting for arrives beyond here, it will set + property_change_reply, because property_change_reply_object says so. */ if (! location->arrived) { - property_change_reply_object = location; secs = x_selection_timeout / 1000; usecs = (x_selection_timeout % 1000) * 1000; wait_reading_process_input (secs, usecs, property_change_reply, 0); @@ -1062,7 +1067,7 @@ x_get_foreign_selection (selection_symbol, target_type) reading_selection_window = requestor_window; reading_which_selection = selection_atom; XCONS (reading_selection_reply)->car = Qnil; - x_start_queuing_selection_requests (selected_frame); + x_start_queuing_selection_requests (display); UNBLOCK_INPUT; /* This allows quits. Also, don't wait forever. */ @@ -1073,7 +1078,7 @@ x_get_foreign_selection (selection_symbol, target_type) BLOCK_INPUT; x_check_errors (display, "Cannot get selection: %s"); x_uncatch_errors (display); - x_stop_queuing_selection_requests (selected_frame); + x_stop_queuing_selection_requests (display); UNBLOCK_INPUT; if (NILP (XCONS (reading_selection_reply)->car)) |