diff options
| author | Po Lu | 2022-07-02 21:55:22 +0800 |
|---|---|---|
| committer | Po Lu | 2022-07-02 21:56:59 +0800 |
| commit | b25ca542983dc885d69d263cb9719f7f3db416fa (patch) | |
| tree | f96df4aecc6e9adf2df0f17d5262c121cffce4b6 /src | |
| parent | 59d109b73c48ca41d240f1fbe10f7349e9df4e31 (diff) | |
| download | emacs-b25ca542983dc885d69d263cb9719f7f3db416fa.tar.gz emacs-b25ca542983dc885d69d263cb9719f7f3db416fa.zip | |
Fix error handling for XCB Xlib
* src/xterm.c (xm_send_drop_message)
(xm_send_top_level_enter_message, xm_send_drag_motion_message)
(xm_send_top_level_leave_message, x_dnd_compute_toplevels)
(x_dnd_send_enter, x_dnd_send_position, x_dnd_send_leave)
(x_dnd_send_drop, handle_one_xevent, x_catch_errors_with_handler)
(x_request_can_fail, x_clean_failable_requests)
(x_ignore_errors_for_next_request, x_stop_ignoring_errors)
(x_uncatch_errors, x_check_errors, x_had_errors_p, x_error_handler)
(frame_set_mouse_pixel_position, x_focus_frame): Record serial
sequences instead of simply the next request when ignoring a
single request. Use XNextRequest instead of NextRequest, since
the latter is unreliable when using Xlib built with XCB.
* src/xterm.h (struct x_failable_request): New struct..
(struct x_display_info): Make failable request variables the
right type.
Diffstat (limited to 'src')
| -rw-r--r-- | src/xterm.c | 99 | ||||
| -rw-r--r-- | src/xterm.h | 18 |
2 files changed, 84 insertions, 33 deletions
diff --git a/src/xterm.c b/src/xterm.c index 0c695324f3b..7ab22f256f6 100644 --- a/src/xterm.c +++ b/src/xterm.c | |||
| @@ -1117,6 +1117,7 @@ static void x_scroll_bar_end_update (struct x_display_info *, struct scroll_bar | |||
| 1117 | static int x_filter_event (struct x_display_info *, XEvent *); | 1117 | static int x_filter_event (struct x_display_info *, XEvent *); |
| 1118 | #endif | 1118 | #endif |
| 1119 | static void x_ignore_errors_for_next_request (struct x_display_info *); | 1119 | static void x_ignore_errors_for_next_request (struct x_display_info *); |
| 1120 | static void x_stop_ignoring_errors (struct x_display_info *); | ||
| 1120 | static void x_clean_failable_requests (struct x_display_info *); | 1121 | static void x_clean_failable_requests (struct x_display_info *); |
| 1121 | 1122 | ||
| 1122 | static struct frame *x_tooltip_window_to_frame (struct x_display_info *, | 1123 | static struct frame *x_tooltip_window_to_frame (struct x_display_info *, |
| @@ -2444,6 +2445,7 @@ xm_send_drop_message (struct x_display_info *dpyinfo, Window source, | |||
| 2444 | 2445 | ||
| 2445 | x_ignore_errors_for_next_request (dpyinfo); | 2446 | x_ignore_errors_for_next_request (dpyinfo); |
| 2446 | XSendEvent (dpyinfo->display, target, False, NoEventMask, &msg); | 2447 | XSendEvent (dpyinfo->display, target, False, NoEventMask, &msg); |
| 2448 | x_stop_ignoring_errors (dpyinfo); | ||
| 2447 | } | 2449 | } |
| 2448 | 2450 | ||
| 2449 | static void | 2451 | static void |
| @@ -2470,6 +2472,7 @@ xm_send_top_level_enter_message (struct x_display_info *dpyinfo, Window source, | |||
| 2470 | 2472 | ||
| 2471 | x_ignore_errors_for_next_request (dpyinfo); | 2473 | x_ignore_errors_for_next_request (dpyinfo); |
| 2472 | XSendEvent (dpyinfo->display, target, False, NoEventMask, &msg); | 2474 | XSendEvent (dpyinfo->display, target, False, NoEventMask, &msg); |
| 2475 | x_stop_ignoring_errors (dpyinfo); | ||
| 2473 | } | 2476 | } |
| 2474 | 2477 | ||
| 2475 | static void | 2478 | static void |
| @@ -2500,6 +2503,7 @@ xm_send_drag_motion_message (struct x_display_info *dpyinfo, Window source, | |||
| 2500 | 2503 | ||
| 2501 | x_ignore_errors_for_next_request (dpyinfo); | 2504 | x_ignore_errors_for_next_request (dpyinfo); |
| 2502 | XSendEvent (dpyinfo->display, target, False, NoEventMask, &msg); | 2505 | XSendEvent (dpyinfo->display, target, False, NoEventMask, &msg); |
| 2506 | x_stop_ignoring_errors (dpyinfo); | ||
| 2503 | } | 2507 | } |
| 2504 | 2508 | ||
| 2505 | static void | 2509 | static void |
| @@ -2558,6 +2562,7 @@ xm_send_top_level_leave_message (struct x_display_info *dpyinfo, Window source, | |||
| 2558 | 2562 | ||
| 2559 | x_ignore_errors_for_next_request (dpyinfo); | 2563 | x_ignore_errors_for_next_request (dpyinfo); |
| 2560 | XSendEvent (dpyinfo->display, target, False, NoEventMask, &msg); | 2564 | XSendEvent (dpyinfo->display, target, False, NoEventMask, &msg); |
| 2565 | x_stop_ignoring_errors (dpyinfo); | ||
| 2561 | } | 2566 | } |
| 2562 | 2567 | ||
| 2563 | static int | 2568 | static int |
| @@ -3211,6 +3216,7 @@ x_dnd_compute_toplevels (struct x_display_info *dpyinfo) | |||
| 3211 | XShapeSelectInput (dpyinfo->display, | 3216 | XShapeSelectInput (dpyinfo->display, |
| 3212 | toplevels[i], | 3217 | toplevels[i], |
| 3213 | ShapeNotifyMask); | 3218 | ShapeNotifyMask); |
| 3219 | x_stop_ignoring_errors (dpyinfo); | ||
| 3214 | 3220 | ||
| 3215 | #ifndef HAVE_XCB_SHAPE | 3221 | #ifndef HAVE_XCB_SHAPE |
| 3216 | x_catch_errors (dpyinfo->display); | 3222 | x_catch_errors (dpyinfo->display); |
| @@ -4397,6 +4403,7 @@ x_dnd_send_enter (struct frame *f, Window target, int supported) | |||
| 4397 | 4403 | ||
| 4398 | x_ignore_errors_for_next_request (dpyinfo); | 4404 | x_ignore_errors_for_next_request (dpyinfo); |
| 4399 | XSendEvent (FRAME_X_DISPLAY (f), target, False, NoEventMask, &msg); | 4405 | XSendEvent (FRAME_X_DISPLAY (f), target, False, NoEventMask, &msg); |
| 4406 | x_stop_ignoring_errors (dpyinfo); | ||
| 4400 | } | 4407 | } |
| 4401 | 4408 | ||
| 4402 | static void | 4409 | static void |
| @@ -4459,6 +4466,7 @@ x_dnd_send_position (struct frame *f, Window target, int supported, | |||
| 4459 | { | 4466 | { |
| 4460 | x_ignore_errors_for_next_request (dpyinfo); | 4467 | x_ignore_errors_for_next_request (dpyinfo); |
| 4461 | XSendEvent (FRAME_X_DISPLAY (f), target, False, NoEventMask, &msg); | 4468 | XSendEvent (FRAME_X_DISPLAY (f), target, False, NoEventMask, &msg); |
| 4469 | x_stop_ignoring_errors (dpyinfo); | ||
| 4462 | 4470 | ||
| 4463 | x_dnd_waiting_for_status_window = target; | 4471 | x_dnd_waiting_for_status_window = target; |
| 4464 | } | 4472 | } |
| @@ -4484,6 +4492,7 @@ x_dnd_send_leave (struct frame *f, Window target) | |||
| 4484 | 4492 | ||
| 4485 | x_ignore_errors_for_next_request (dpyinfo); | 4493 | x_ignore_errors_for_next_request (dpyinfo); |
| 4486 | XSendEvent (FRAME_X_DISPLAY (f), target, False, NoEventMask, &msg); | 4494 | XSendEvent (FRAME_X_DISPLAY (f), target, False, NoEventMask, &msg); |
| 4495 | x_stop_ignoring_errors (dpyinfo); | ||
| 4487 | } | 4496 | } |
| 4488 | 4497 | ||
| 4489 | static bool | 4498 | static bool |
| @@ -4516,6 +4525,7 @@ x_dnd_send_drop (struct frame *f, Window target, Time timestamp, | |||
| 4516 | 4525 | ||
| 4517 | x_ignore_errors_for_next_request (dpyinfo); | 4526 | x_ignore_errors_for_next_request (dpyinfo); |
| 4518 | XSendEvent (FRAME_X_DISPLAY (f), target, False, NoEventMask, &msg); | 4527 | XSendEvent (FRAME_X_DISPLAY (f), target, False, NoEventMask, &msg); |
| 4528 | x_stop_ignoring_errors (dpyinfo); | ||
| 4519 | return true; | 4529 | return true; |
| 4520 | } | 4530 | } |
| 4521 | 4531 | ||
| @@ -16454,6 +16464,7 @@ handle_one_xevent (struct x_display_info *dpyinfo, | |||
| 16454 | XSendEvent (dpyinfo->display, target, | 16464 | XSendEvent (dpyinfo->display, target, |
| 16455 | False, NoEventMask, | 16465 | False, NoEventMask, |
| 16456 | &x_dnd_pending_send_position); | 16466 | &x_dnd_pending_send_position); |
| 16467 | x_stop_ignoring_errors (dpyinfo); | ||
| 16457 | x_dnd_pending_send_position.type = 0; | 16468 | x_dnd_pending_send_position.type = 0; |
| 16458 | 16469 | ||
| 16459 | /* Since we sent another XdndPosition message, we | 16470 | /* Since we sent another XdndPosition message, we |
| @@ -22991,7 +23002,8 @@ x_error_catcher (Display *display, XErrorEvent *event, | |||
| 22991 | There is no need to use this mechanism for ignoring errors from | 23002 | There is no need to use this mechanism for ignoring errors from |
| 22992 | single asynchronous requests, such as sending a ClientMessage to a | 23003 | single asynchronous requests, such as sending a ClientMessage to a |
| 22993 | window that might no longer exist. Use | 23004 | window that might no longer exist. Use |
| 22994 | x_ignore_errors_for_next_request instead. */ | 23005 | x_ignore_errors_for_next_request (paired with |
| 23006 | x_stop_ignoring_errors) instead. */ | ||
| 22995 | 23007 | ||
| 22996 | void | 23008 | void |
| 22997 | x_catch_errors_with_handler (Display *dpy, x_special_error_handler handler, | 23009 | x_catch_errors_with_handler (Display *dpy, x_special_error_handler handler, |
| @@ -23004,7 +23016,7 @@ x_catch_errors_with_handler (Display *dpy, x_special_error_handler handler, | |||
| 23004 | data->handler = handler; | 23016 | data->handler = handler; |
| 23005 | data->handler_data = handler_data; | 23017 | data->handler_data = handler_data; |
| 23006 | data->prev = x_error_message; | 23018 | data->prev = x_error_message; |
| 23007 | data->first_request = NextRequest (dpy); | 23019 | data->first_request = XNextRequest (dpy); |
| 23008 | x_error_message = data; | 23020 | x_error_message = data; |
| 23009 | 23021 | ||
| 23010 | ++x_error_message_count; | 23022 | ++x_error_message_count; |
| @@ -23018,17 +23030,21 @@ x_catch_errors (Display *dpy) | |||
| 23018 | 23030 | ||
| 23019 | /* Return if errors for REQUEST should be ignored even if there is no | 23031 | /* Return if errors for REQUEST should be ignored even if there is no |
| 23020 | error handler applied. */ | 23032 | error handler applied. */ |
| 23021 | static unsigned long * | 23033 | static struct x_failable_request * |
| 23022 | x_request_can_fail (struct x_display_info *dpyinfo, | 23034 | x_request_can_fail (struct x_display_info *dpyinfo, |
| 23023 | unsigned long request) | 23035 | unsigned long request) |
| 23024 | { | 23036 | { |
| 23025 | unsigned long *failable_requests; | 23037 | struct x_failable_request *failable_requests; |
| 23026 | 23038 | ||
| 23027 | for (failable_requests = dpyinfo->failable_requests; | 23039 | for (failable_requests = dpyinfo->failable_requests; |
| 23028 | failable_requests < dpyinfo->next_failable_request; | 23040 | failable_requests < dpyinfo->next_failable_request; |
| 23029 | failable_requests++) | 23041 | failable_requests++) |
| 23030 | { | 23042 | { |
| 23031 | if (*failable_requests == request) | 23043 | if (X_COMPARE_SERIALS (request, >=, |
| 23044 | failable_requests->start) | ||
| 23045 | && (!failable_requests->end | ||
| 23046 | || X_COMPARE_SERIALS (request, <=, | ||
| 23047 | failable_requests->end))) | ||
| 23032 | return failable_requests; | 23048 | return failable_requests; |
| 23033 | } | 23049 | } |
| 23034 | 23050 | ||
| @@ -23040,13 +23056,17 @@ x_request_can_fail (struct x_display_info *dpyinfo, | |||
| 23040 | static void | 23056 | static void |
| 23041 | x_clean_failable_requests (struct x_display_info *dpyinfo) | 23057 | x_clean_failable_requests (struct x_display_info *dpyinfo) |
| 23042 | { | 23058 | { |
| 23043 | unsigned long *first, *last; | 23059 | struct x_failable_request *first, *last; |
| 23044 | 23060 | ||
| 23045 | last = dpyinfo->next_failable_request; | 23061 | last = dpyinfo->next_failable_request; |
| 23046 | 23062 | ||
| 23047 | for (first = dpyinfo->failable_requests; first < last; first++) | 23063 | for (first = dpyinfo->failable_requests; first < last; first++) |
| 23048 | { | 23064 | { |
| 23049 | if (*first > LastKnownRequestProcessed (dpyinfo->display)) | 23065 | if (X_COMPARE_SERIALS (first->start, >, |
| 23066 | LastKnownRequestProcessed (dpyinfo->display)) | ||
| 23067 | || !first->end | ||
| 23068 | || X_COMPARE_SERIALS (first->end, >, | ||
| 23069 | LastKnownRequestProcessed (dpyinfo->display))) | ||
| 23050 | break; | 23070 | break; |
| 23051 | } | 23071 | } |
| 23052 | 23072 | ||
| @@ -23061,7 +23081,14 @@ x_clean_failable_requests (struct x_display_info *dpyinfo) | |||
| 23061 | static void | 23081 | static void |
| 23062 | x_ignore_errors_for_next_request (struct x_display_info *dpyinfo) | 23082 | x_ignore_errors_for_next_request (struct x_display_info *dpyinfo) |
| 23063 | { | 23083 | { |
| 23064 | unsigned long *request, *max; | 23084 | struct x_failable_request *request, *max; |
| 23085 | |||
| 23086 | if ((dpyinfo->next_failable_request | ||
| 23087 | != dpyinfo->failable_requests) | ||
| 23088 | && (dpyinfo->next_failable_request - 1)->end == 0) | ||
| 23089 | /* A new sequence should never be started before an old one | ||
| 23090 | finishes. Use `x_catch_errors' to nest error handlers. */ | ||
| 23091 | emacs_abort (); | ||
| 23065 | 23092 | ||
| 23066 | request = dpyinfo->next_failable_request; | 23093 | request = dpyinfo->next_failable_request; |
| 23067 | max = dpyinfo->failable_requests + N_FAILABLE_REQUESTS; | 23094 | max = dpyinfo->failable_requests + N_FAILABLE_REQUESTS; |
| @@ -23071,7 +23098,7 @@ x_ignore_errors_for_next_request (struct x_display_info *dpyinfo) | |||
| 23071 | /* There is no point in making this extra sync if all requests | 23098 | /* There is no point in making this extra sync if all requests |
| 23072 | are known to have been fully processed. */ | 23099 | are known to have been fully processed. */ |
| 23073 | if ((LastKnownRequestProcessed (dpyinfo->display) | 23100 | if ((LastKnownRequestProcessed (dpyinfo->display) |
| 23074 | != NextRequest (dpyinfo->display) - 1)) | 23101 | != XNextRequest (dpyinfo->display) - 1)) |
| 23075 | XSync (dpyinfo->display, False); | 23102 | XSync (dpyinfo->display, False); |
| 23076 | 23103 | ||
| 23077 | x_clean_failable_requests (dpyinfo); | 23104 | x_clean_failable_requests (dpyinfo); |
| @@ -23083,10 +23110,21 @@ x_ignore_errors_for_next_request (struct x_display_info *dpyinfo) | |||
| 23083 | function. */ | 23110 | function. */ |
| 23084 | emacs_abort (); | 23111 | emacs_abort (); |
| 23085 | 23112 | ||
| 23086 | *request = NextRequest (dpyinfo->display); | 23113 | request->start = XNextRequest (dpyinfo->display); |
| 23114 | request->end = 0; | ||
| 23115 | |||
| 23087 | dpyinfo->next_failable_request++; | 23116 | dpyinfo->next_failable_request++; |
| 23088 | } | 23117 | } |
| 23089 | 23118 | ||
| 23119 | static void | ||
| 23120 | x_stop_ignoring_errors (struct x_display_info *dpyinfo) | ||
| 23121 | { | ||
| 23122 | struct x_failable_request *range; | ||
| 23123 | |||
| 23124 | range = dpyinfo->next_failable_request - 1; | ||
| 23125 | range->end = XNextRequest (dpyinfo->display) - 1; | ||
| 23126 | } | ||
| 23127 | |||
| 23090 | /* Undo the last x_catch_errors call. | 23128 | /* Undo the last x_catch_errors call. |
| 23091 | DPY should be the display that was passed to x_catch_errors. | 23129 | DPY should be the display that was passed to x_catch_errors. |
| 23092 | 23130 | ||
| @@ -23134,10 +23172,10 @@ x_uncatch_errors (void) | |||
| 23134 | /* There is no point in making this extra sync if all requests | 23172 | /* There is no point in making this extra sync if all requests |
| 23135 | are known to have been fully processed. */ | 23173 | are known to have been fully processed. */ |
| 23136 | && (LastKnownRequestProcessed (x_error_message->dpy) | 23174 | && (LastKnownRequestProcessed (x_error_message->dpy) |
| 23137 | != NextRequest (x_error_message->dpy) - 1) | 23175 | != XNextRequest (x_error_message->dpy) - 1) |
| 23138 | /* Likewise if no request was made since the trap was | 23176 | /* Likewise if no request was made since the trap was |
| 23139 | installed. */ | 23177 | installed. */ |
| 23140 | && (NextRequest (x_error_message->dpy) | 23178 | && (XNextRequest (x_error_message->dpy) |
| 23141 | > x_error_message->first_request)) | 23179 | > x_error_message->first_request)) |
| 23142 | { | 23180 | { |
| 23143 | XSync (x_error_message->dpy, False); | 23181 | XSync (x_error_message->dpy, False); |
| @@ -23171,8 +23209,8 @@ x_check_errors (Display *dpy, const char *format) | |||
| 23171 | /* There is no point in making this extra sync if all requests | 23209 | /* There is no point in making this extra sync if all requests |
| 23172 | are known to have been fully processed. */ | 23210 | are known to have been fully processed. */ |
| 23173 | if ((LastKnownRequestProcessed (dpy) | 23211 | if ((LastKnownRequestProcessed (dpy) |
| 23174 | != NextRequest (dpy) - 1) | 23212 | != XNextRequest (dpy) - 1) |
| 23175 | && (NextRequest (dpy) | 23213 | && (XNextRequest (dpy) |
| 23176 | > x_error_message->first_request)) | 23214 | > x_error_message->first_request)) |
| 23177 | XSync (dpy, False); | 23215 | XSync (dpy, False); |
| 23178 | 23216 | ||
| @@ -23206,8 +23244,8 @@ x_had_errors_p (Display *dpy) | |||
| 23206 | 23244 | ||
| 23207 | /* Make sure to catch any errors incurred so far. */ | 23245 | /* Make sure to catch any errors incurred so far. */ |
| 23208 | if ((LastKnownRequestProcessed (dpy) | 23246 | if ((LastKnownRequestProcessed (dpy) |
| 23209 | != NextRequest (dpy) - 1) | 23247 | != XNextRequest (dpy) - 1) |
| 23210 | && (NextRequest (dpy) | 23248 | && (XNextRequest (dpy) |
| 23211 | > x_error_message->first_request)) | 23249 | > x_error_message->first_request)) |
| 23212 | XSync (dpy, False); | 23250 | XSync (dpy, False); |
| 23213 | 23251 | ||
| @@ -23471,7 +23509,7 @@ x_error_handler (Display *display, XErrorEvent *event) | |||
| 23471 | { | 23509 | { |
| 23472 | struct x_error_message_stack *stack; | 23510 | struct x_error_message_stack *stack; |
| 23473 | struct x_display_info *dpyinfo; | 23511 | struct x_display_info *dpyinfo; |
| 23474 | unsigned long *fail, *last; | 23512 | struct x_failable_request *fail, *last; |
| 23475 | 23513 | ||
| 23476 | #if defined USE_GTK && defined HAVE_GTK3 | 23514 | #if defined USE_GTK && defined HAVE_GTK3 |
| 23477 | if ((event->error_code == BadMatch | 23515 | if ((event->error_code == BadMatch |
| @@ -23488,13 +23526,17 @@ x_error_handler (Display *display, XErrorEvent *event) | |||
| 23488 | 23526 | ||
| 23489 | if (fail) | 23527 | if (fail) |
| 23490 | { | 23528 | { |
| 23491 | /* Now that this request has been handled, remove it from | 23529 | /* Now that this request sequence has been fully handled, |
| 23492 | the list of requests that can fail. */ | 23530 | remove it from the list of requests that can fail. */ |
| 23493 | last = dpyinfo->next_failable_request; | 23531 | |
| 23494 | memmove (&dpyinfo->failable_requests, fail, | 23532 | if (event->serial == fail->end) |
| 23495 | sizeof *fail * (last - fail)); | 23533 | { |
| 23496 | dpyinfo->next_failable_request = (dpyinfo->failable_requests | 23534 | last = dpyinfo->next_failable_request; |
| 23497 | + (last - fail)); | 23535 | memmove (&dpyinfo->failable_requests, fail, |
| 23536 | sizeof *fail * (last - fail)); | ||
| 23537 | dpyinfo->next_failable_request = (dpyinfo->failable_requests | ||
| 23538 | + (last - fail)); | ||
| 23539 | } | ||
| 23498 | 23540 | ||
| 23499 | return 0; | 23541 | return 0; |
| 23500 | } | 23542 | } |
| @@ -24882,11 +24924,9 @@ frame_set_mouse_pixel_position (struct frame *f, int pix_x, int pix_y) | |||
| 24882 | &deviceid)) | 24924 | &deviceid)) |
| 24883 | { | 24925 | { |
| 24884 | x_ignore_errors_for_next_request (FRAME_DISPLAY_INFO (f)); | 24926 | x_ignore_errors_for_next_request (FRAME_DISPLAY_INFO (f)); |
| 24885 | 24927 | XIWarpPointer (FRAME_X_DISPLAY (f), deviceid, None, | |
| 24886 | XIWarpPointer (FRAME_X_DISPLAY (f), | 24928 | FRAME_X_WINDOW (f), 0, 0, 0, 0, pix_x, pix_y); |
| 24887 | deviceid, None, | 24929 | x_stop_ignoring_errors (FRAME_DISPLAY_INFO (f)); |
| 24888 | FRAME_X_WINDOW (f), | ||
| 24889 | 0, 0, 0, 0, pix_x, pix_y); | ||
| 24890 | } | 24930 | } |
| 24891 | } | 24931 | } |
| 24892 | else | 24932 | else |
| @@ -25025,6 +25065,7 @@ x_focus_frame (struct frame *f, bool noactivate) | |||
| 25025 | x_ignore_errors_for_next_request (dpyinfo); | 25065 | x_ignore_errors_for_next_request (dpyinfo); |
| 25026 | XSetInputFocus (FRAME_X_DISPLAY (f), FRAME_OUTER_WINDOW (f), | 25066 | XSetInputFocus (FRAME_X_DISPLAY (f), FRAME_OUTER_WINDOW (f), |
| 25027 | RevertToParent, CurrentTime); | 25067 | RevertToParent, CurrentTime); |
| 25068 | x_stop_ignoring_errors (dpyinfo); | ||
| 25028 | 25069 | ||
| 25029 | if (!noactivate) | 25070 | if (!noactivate) |
| 25030 | x_ewmh_activate_frame (f); | 25071 | x_ewmh_activate_frame (f); |
diff --git a/src/xterm.h b/src/xterm.h index eee76724268..7c09073d765 100644 --- a/src/xterm.h +++ b/src/xterm.h | |||
| @@ -261,6 +261,16 @@ struct xi_device_t | |||
| 261 | Status x_parse_color (struct frame *f, const char *color_name, | 261 | Status x_parse_color (struct frame *f, const char *color_name, |
| 262 | XColor *color); | 262 | XColor *color); |
| 263 | 263 | ||
| 264 | struct x_failable_request | ||
| 265 | { | ||
| 266 | /* The first request making up this sequence. */ | ||
| 267 | unsigned long start; | ||
| 268 | |||
| 269 | /* If this is zero, then the request has not yet been made. | ||
| 270 | Otherwise, this is the request that ends this sequence. */ | ||
| 271 | unsigned long end; | ||
| 272 | }; | ||
| 273 | |||
| 264 | 274 | ||
| 265 | /* For each X display, we have a structure that records | 275 | /* For each X display, we have a structure that records |
| 266 | information about it. */ | 276 | information about it. */ |
| @@ -746,12 +756,12 @@ struct x_display_info | |||
| 746 | int screen_mm_width; | 756 | int screen_mm_width; |
| 747 | int screen_mm_height; | 757 | int screen_mm_height; |
| 748 | 758 | ||
| 749 | /* Circular buffer of request serials to ignore inside an error | 759 | /* Circular buffer of request serial ranges to ignore inside an |
| 750 | handler in increasing order. */ | 760 | error handler in increasing order. */ |
| 751 | unsigned long failable_requests[N_FAILABLE_REQUESTS]; | 761 | struct x_failable_request failable_requests[N_FAILABLE_REQUESTS]; |
| 752 | 762 | ||
| 753 | /* Pointer to the next request in `failable_requests'. */ | 763 | /* Pointer to the next request in `failable_requests'. */ |
| 754 | unsigned long *next_failable_request; | 764 | struct x_failable_request *next_failable_request; |
| 755 | }; | 765 | }; |
| 756 | 766 | ||
| 757 | #ifdef HAVE_X_I18N | 767 | #ifdef HAVE_X_I18N |