X-Git-Url: https://code.delx.au/gnu-emacs/blobdiff_plain/60e992936ae72fa3f32c8549f74dde22fa0e4e37..80d0edae927b550944eb54eb49a70cb7f5353b68:/src/dispnew.c diff --git a/src/dispnew.c b/src/dispnew.c index 0314e34ecb..15190abfb7 100644 --- a/src/dispnew.c +++ b/src/dispnew.c @@ -1,6 +1,7 @@ /* Updating of data structures for redisplay. - Copyright (C) 1985,86,87,88,93,94,95,97,98,1999,2000,01,02,2003 - Free Software Foundation, Inc. + Copyright (C) 1985, 1986, 1987, 1988, 1993, 1994, 1995, + 1997, 1998, 1999, 2000, 2001, 2002, 2003, + 2004, 2005 Free Software Foundation, Inc. This file is part of GNU Emacs. @@ -16,8 +17,8 @@ GNU General Public License for more details. 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, Inc., 59 Temple Place - Suite 330, -Boston, MA 02111-1307, USA. */ +the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, +Boston, MA 02110-1301, USA. */ #include #include @@ -1184,6 +1185,9 @@ increment_row_positions (row, delta, delta_bytes) MATRIX_ROW_END_CHARPOS (row) += delta; MATRIX_ROW_END_BYTEPOS (row) += delta_bytes; + if (!row->enabled_p) + return; + /* Increment positions in glyphs. */ for (area = 0; area < LAST_AREA; ++area) for (i = 0; i < row->used[area]; ++i) @@ -1516,7 +1520,10 @@ row_equal_p (w, a, b, mouse_face_p) if (a->fill_line_p != b->fill_line_p || a->cursor_in_fringe_p != b->cursor_in_fringe_p || a->left_fringe_bitmap != b->left_fringe_bitmap + || a->left_fringe_face_id != b->left_fringe_face_id || a->right_fringe_bitmap != b->right_fringe_bitmap + || a->right_fringe_face_id != b->right_fringe_face_id + || a->overlay_arrow_bitmap != b->overlay_arrow_bitmap || a->exact_window_width_line_p != b->exact_window_width_line_p || a->overlapped_p != b->overlapped_p || (MATRIX_ROW_CONTINUATION_LINE_P (a) @@ -1908,10 +1915,10 @@ allocate_matrices_for_frame_redisplay (window, x, y, dim_only_p, || dim.width != w->desired_matrix->matrix_w || dim.height != w->desired_matrix->matrix_h || (margin_glyphs_to_reserve (w, dim.width, - w->right_margin_cols) + w->left_margin_cols) != w->desired_matrix->left_margin_glyphs) || (margin_glyphs_to_reserve (w, dim.width, - w->left_margin_cols) + w->right_margin_cols) != w->desired_matrix->right_margin_glyphs)) *window_change_flags |= CHANGED_LEAF_MATRIX; @@ -1979,7 +1986,7 @@ required_matrix_height (w) int ch_height = FRAME_SMALLEST_FONT_HEIGHT (f); int window_pixel_height = window_box_height (w) + abs (w->vscroll); return (((window_pixel_height + ch_height - 1) - / ch_height) + / ch_height) * w->nrows_scale_factor /* One partially visible line at the top and bottom of the window. */ + 2 @@ -2007,7 +2014,7 @@ required_matrix_width (w) /* Compute number of glyphs needed in a glyph row. */ return (((window_pixel_width + ch_width - 1) - / ch_width) + / ch_width) * w->ncols_scale_factor /* 2 partially visible columns in the text area. */ + 2 /* One partially visible column at the right @@ -2716,9 +2723,15 @@ build_frame_matrix_from_leaf_window (frame_matrix, w) if (!WINDOW_RIGHTMOST_P (w)) { struct Lisp_Char_Table *dp = window_display_table (w); - right_border_glyph = (dp && INTEGERP (DISP_BORDER_GLYPH (dp)) - ? XINT (DISP_BORDER_GLYPH (dp)) - : '|'); + + right_border_glyph + = ((dp && INTEGERP (DISP_BORDER_GLYPH (dp))) + ? spec_glyph_lookup_face (w, XINT (DISP_BORDER_GLYPH (dp))) + : '|'); + + if (FAST_GLYPH_FACE (right_border_glyph) <= 0) + right_border_glyph + = FAST_MAKE_GLYPH (right_border_glyph, VERTICAL_BORDER_FACE_ID); } } else @@ -2774,6 +2787,7 @@ build_frame_matrix_from_leaf_window (frame_matrix, w) SET_CHAR_GLYPH_FROM_GLYPH (*border, right_border_glyph); } +#if GLYPH_DEBUG /* Window row window_y must be a slice of frame row frame_y. */ xassert (glyph_row_slice_p (window_row, frame_row)); @@ -2781,7 +2795,6 @@ build_frame_matrix_from_leaf_window (frame_matrix, w) /* If rows are in sync, we don't have to copy glyphs because frame and window share glyphs. */ -#if GLYPH_DEBUG strcpy (w->current_matrix->method, w->desired_matrix->method); add_window_display_history (w, w->current_matrix->method, 0); #endif @@ -2799,6 +2812,27 @@ build_frame_matrix_from_leaf_window (frame_matrix, w) } } +/* Given a user-specified glyph, possibly including a Lisp-level face + ID, return a glyph that has a realized face ID. + This is used for glyphs displayed specially and not part of the text; + for instance, vertical separators, truncation markers, etc. */ + +GLYPH +spec_glyph_lookup_face (w, glyph) + struct window *w; + GLYPH glyph; +{ + int lface_id = FAST_GLYPH_FACE (glyph); + /* Convert the glyph's specified face to a realized (cache) face. */ + if (lface_id > 0) + { + int face_id = merge_faces (XFRAME (w->frame), + Qt, lface_id, DEFAULT_FACE_ID); + glyph + = FAST_MAKE_GLYPH (FAST_GLYPH_CHAR (glyph), face_id); + } + return glyph; +} /* Add spaces to a glyph row ROW in a window matrix. @@ -3161,15 +3195,21 @@ mirror_line_dance (w, unchanged_at_top, nlines, copy_from, retained_p) struct glyph_matrix *m2; int m2_from; - w2 = frame_row_to_window (root, frame_to); - m2 = w2->current_matrix; - m2_from = frame_from - m2->matrix_y; - copy_row_except_pointers (m->rows + window_to, - m2->rows + m2_from); - - /* If frame line is empty, window line is empty, too. */ - if (!retained_p[copy_from[i]]) - m->rows[window_to].enabled_p = 0; + w2 = frame_row_to_window (root, frame_from); + /* ttn@surf.glug.org: when enabling menu bar using `emacs + -nw', FROM_FRAME sometimes has no associated window. + This check avoids a segfault if W2 is null. */ + if (w2) + { + m2 = w2->current_matrix; + m2_from = frame_from - m2->matrix_y; + copy_row_except_pointers (m->rows + window_to, + m2->rows + m2_from); + + /* If frame line is empty, window line is empty, too. */ + if (!retained_p[copy_from[i]]) + m->rows[window_to].enabled_p = 0; + } sync_p = 1; } else if (from_inside_window_p) @@ -3655,7 +3695,9 @@ direct_output_for_insert (g) cursor_to (y, x); } +#ifdef HAVE_WINDOW_SYSTEM update_window_fringes (w, 0); +#endif if (rif) rif->update_window_end_hook (w, 1, 0); @@ -3824,10 +3866,15 @@ update_frame (f, force_p, inhibit_hairy_id_p) paused_p = update_window_tree (root_window, force_p); update_end (f); -#if 0 /* This flush is a performance bottleneck under X, - and it doesn't seem to be necessary anyway. */ - rif->flush_display (f); -#endif + /* This flush is a performance bottleneck under X, + and it doesn't seem to be necessary anyway (in general). + It is necessary when resizing the window with the mouse, or + at least the fringes are not redrawn in a timely manner. ++kfs */ + if (f->force_flush_display_p) + { + rif->flush_display (f); + f->force_flush_display_p = 0; + } } else { @@ -4055,17 +4102,17 @@ update_window (w, force_p) extern Lisp_Object do_mouse_tracking; #if GLYPH_DEBUG struct frame *f = XFRAME (WINDOW_FRAME (w)); -#endif /* Check that W's frame doesn't have glyph matrices. */ xassert (FRAME_WINDOW_P (f)); xassert (updating_frame != NULL); +#endif /* Check pending input the first time so that we can quickly return. */ if (redisplay_dont_pause) force_p = 1; else - detect_input_pending (); + detect_input_pending_ignore_squeezables (); /* If forced to complete the update, or if no input is pending, do the update. */ @@ -4120,19 +4167,11 @@ update_window (w, force_p) goto set_cursor; } else if (rc > 0) - /* We've scrolled the display. */ - force_p = 1; - changed_p = 1; - } - - /* Update the header line after scrolling because a new header - line would otherwise overwrite lines at the top of the window - that can be scrolled. */ - if (header_line_row && header_line_row->enabled_p) - { - header_line_row->y = 0; - update_window_line (w, 0, &mouse_face_overwritten_p); - changed_p = 1; + { + /* We've scrolled the display. */ + force_p = 1; + changed_p = 1; + } } /* Update the rest of the lines. */ @@ -4147,7 +4186,7 @@ update_window (w, force_p) scrolling large windows with repeated scroll-up commands will too quickly pause redisplay. */ if (!force_p && ++n_updated % preempt_count == 0) - detect_input_pending (); + detect_input_pending_ignore_squeezables (); changed_p |= update_window_line (w, vpos, &mouse_face_overwritten_p); @@ -4171,6 +4210,16 @@ update_window (w, force_p) set_cursor: + /* Update the header line after scrolling because a new header + line would otherwise overwrite lines at the top of the window + that can be scrolled. */ + if (header_line_row && header_line_row->enabled_p) + { + header_line_row->y = 0; + update_window_line (w, 0, &mouse_face_overwritten_p); + changed_p = 1; + } + /* Fix the appearance of overlapping/overlapped rows. */ if (!paused_p && !w->pseudo_window_p) { @@ -4194,7 +4243,9 @@ update_window (w, force_p) strcpy (w->current_matrix->method, w->desired_matrix->method); #endif +#ifdef HAVE_WINDOW_SYSTEM update_window_fringes (w, 0); +#endif /* End the update of window W. Don't set the cursor if we paused updating the display because in this case, @@ -4515,6 +4566,7 @@ update_window_line (w, vpos, mouse_face_overwritten_p) || desired_row->y != current_row->y || desired_row->visible_height != current_row->visible_height || desired_row->cursor_in_fringe_p != current_row->cursor_in_fringe_p + || desired_row->overlay_arrow_bitmap != current_row->overlay_arrow_bitmap || current_row->redraw_fringe_bitmaps_p || desired_row->mode_line_p != current_row->mode_line_p || desired_row->exact_window_width_line_p != current_row->exact_window_width_line_p @@ -5021,7 +5073,10 @@ scrolling_window (w, header_line_p) to_overlapped_p = to->overlapped_p; if (!from->mode_line_p && !w->pseudo_window_p && (to->left_fringe_bitmap != from->left_fringe_bitmap - || to->right_fringe_bitmap != from->right_fringe_bitmap)) + || to->right_fringe_bitmap != from->right_fringe_bitmap + || to->left_fringe_face_id != from->left_fringe_face_id + || to->right_fringe_face_id != from->right_fringe_face_id + || to->overlay_arrow_bitmap != from->overlay_arrow_bitmap)) from->redraw_fringe_bitmaps_p = 1; assign_row (to, from); to->enabled_p = 1, from->enabled_p = 0; @@ -5033,8 +5088,8 @@ scrolling_window (w, header_line_p) for (i = 0; i < row_entry_idx; ++i) row_table[row_entry_pool[i].bucket] = NULL; - /* Value is non-zero to indicate that we scrolled the display. */ - return 1; + /* Value is > 0 to indicate that we scrolled the display. */ + return nruns; } @@ -5075,7 +5130,7 @@ update_frame_1 (f, force_p, inhibit_id_p) if (redisplay_dont_pause) force_p = 1; - else if (!force_p && detect_input_pending ()) + else if (!force_p && detect_input_pending_ignore_squeezables ()) { pause = 1; goto do_pause; @@ -5131,7 +5186,7 @@ update_frame_1 (f, force_p, inhibit_id_p) } if ((i - 1) % preempt_count == 0) - detect_input_pending (); + detect_input_pending_ignore_squeezables (); update_frame_line (f, i); } @@ -5712,6 +5767,9 @@ buffer_posn_from_coords (w, x, y, pos, object, dx, dy, width, height) struct text_pos startp; Lisp_Object string; struct glyph_row *row; +#ifdef HAVE_WINDOW_SYSTEM + struct image *img = 0; +#endif int x0, x1; current_buffer = XBUFFER (w->buffer); @@ -5737,25 +5795,35 @@ buffer_posn_from_coords (w, x, y, pos, object, dx, dy, width, height) #ifdef HAVE_WINDOW_SYSTEM if (it.what == IT_IMAGE) { - struct image *img; if ((img = IMAGE_FROM_ID (it.f, it.image_id)) != NULL && !NILP (img->spec)) *object = img->spec; } #endif - row = MATRIX_ROW (w->current_matrix, it.vpos); - if (row->enabled_p) + if (it.vpos < w->current_matrix->nrows + && (row = MATRIX_ROW (w->current_matrix, it.vpos), + row->enabled_p)) { if (it.hpos < row->used[TEXT_AREA]) { struct glyph *glyph = row->glyphs[TEXT_AREA] + it.hpos; - *width = glyph->pixel_width; - *height = glyph->ascent + glyph->descent; #ifdef HAVE_WINDOW_SYSTEM - if (glyph->type == IMAGE_GLYPH) - *dy -= row->ascent - glyph->ascent; + if (img) + { + *dy -= row->ascent - glyph->ascent; + *dx += glyph->slice.x; + *dy += glyph->slice.y; + /* Image slices positions are still relative to the entire image */ + *width = img->width; + *height = img->height; + } + else #endif + { + *width = glyph->pixel_width; + *height = glyph->ascent + glyph->descent; + } } else { @@ -5812,7 +5880,7 @@ mode_line_string (w, part, x, y, charpos, object, dx, dy, width, height) it's the one we were looking for. */ glyph = row->glyphs[TEXT_AREA]; end = glyph + row->used[TEXT_AREA]; - for (x0 = *x; glyph < end && x0 > glyph->pixel_width; ++glyph) + for (x0 = *x; glyph < end && x0 >= glyph->pixel_width; ++glyph) x0 -= glyph->pixel_width; *x = glyph - row->glyphs[TEXT_AREA]; if (glyph < end) @@ -5893,18 +5961,18 @@ marginal_area_string (w, part, x, y, charpos, object, dx, dy, width, height) it's the one we were looking for. */ if (area == RIGHT_MARGIN_AREA) x0 = ((WINDOW_HAS_FRINGES_OUTSIDE_MARGINS (w) - ? WINDOW_LEFT_FRINGE_WIDTH (w) + ? WINDOW_LEFT_FRINGE_WIDTH (w) : WINDOW_TOTAL_FRINGE_WIDTH (w)) + window_box_width (w, LEFT_MARGIN_AREA) + window_box_width (w, TEXT_AREA)); else x0 = (WINDOW_HAS_FRINGES_OUTSIDE_MARGINS (w) - ? WINDOW_LEFT_FRINGE_WIDTH (w) + ? WINDOW_LEFT_FRINGE_WIDTH (w) : 0); glyph = row->glyphs[area]; end = glyph + row->used[area]; - for (x0 = *x - x0; glyph < end && x0 > glyph->pixel_width; ++glyph) + for (x0 = *x - x0; glyph < end && x0 >= glyph->pixel_width; ++glyph) x0 -= glyph->pixel_width; *x = glyph - row->glyphs[area]; if (glyph < end) @@ -5921,6 +5989,8 @@ marginal_area_string (w, part, x, y, charpos, object, dx, dy, width, height) if (img != NULL) *object = img->spec; y0 -= row->ascent - glyph->ascent; + x0 += glyph->slice.x; + y0 += glyph->slice.y; } #endif } @@ -5962,6 +6032,9 @@ window_change_signal (signalnum) /* If we don't have an argument, */ #endif int old_errno = errno; + signal (SIGWINCH, window_change_signal); + SIGNAL_THREAD_CHECK (signalnum); + get_frame_size (&width, &height); /* The frame size change obviously applies to a termcap-controlled @@ -5984,7 +6057,6 @@ window_change_signal (signalnum) /* If we don't have an argument, */ } } - signal (SIGWINCH, window_change_signal); errno = old_errno; } #endif /* SIGWINCH */ @@ -6281,7 +6353,7 @@ Emacs was built without floating point support. #ifndef EMACS_HAS_USECS if (sec == 0 && usec != 0) - error ("millisecond `sleep-for' not supported on %s", SYSTEM_TYPE); + error ("Millisecond `sleep-for' not supported on %s", SYSTEM_TYPE); #endif /* Assure that 0 <= usec < 1000000. */ @@ -6299,52 +6371,13 @@ Emacs was built without floating point support. if (sec < 0 || (sec == 0 && usec == 0)) return Qnil; - { - Lisp_Object zero; - - XSETFASTINT (zero, 0); - wait_reading_process_input (sec, usec, zero, 0); - } - - /* We should always have wait_reading_process_input; we have a dummy - implementation for systems which don't support subprocesses. */ -#if 0 - /* No wait_reading_process_input */ - immediate_quit = 1; - QUIT; - -#ifdef VMS - sys_sleep (sec); -#else /* not VMS */ -/* The reason this is done this way - (rather than defined (H_S) && defined (H_T)) - is because the VMS preprocessor doesn't grok `defined'. */ -#ifdef HAVE_SELECT - EMACS_GET_TIME (end_time); - EMACS_SET_SECS_USECS (timeout, sec, usec); - EMACS_ADD_TIME (end_time, end_time, timeout); - - while (1) - { - EMACS_GET_TIME (timeout); - EMACS_SUB_TIME (timeout, end_time, timeout); - if (EMACS_TIME_NEG_P (timeout) - || !select (1, 0, 0, 0, &timeout)) - break; - } -#else /* not HAVE_SELECT */ - sleep (sec); -#endif /* HAVE_SELECT */ -#endif /* not VMS */ - - immediate_quit = 0; -#endif /* no subprocesses */ + wait_reading_process_output (sec, usec, 0, 0, Qnil, NULL, 0); return Qnil; } -/* This is just like wait_reading_process_input, except that +/* This is just like wait_reading_process_output, except that it does the redisplay. It's also much like Fsit_for, except that it can be used for @@ -6354,11 +6387,9 @@ Lisp_Object sit_for (sec, usec, reading, display, initial_display) int sec, usec, reading, display, initial_display; { - Lisp_Object read_kbd; - swallow_events (display); - if (detect_input_pending_run_timers (display) || !NILP (Vexecuting_macro)) + if (detect_input_pending_run_timers (display) || !NILP (Vexecuting_kbd_macro)) return Qnil; if (initial_display) @@ -6371,8 +6402,8 @@ sit_for (sec, usec, reading, display, initial_display) gobble_input (0); #endif - XSETINT (read_kbd, reading ? -1 : 1); - wait_reading_process_input (sec, usec, read_kbd, display); + wait_reading_process_output (sec, usec, reading ? -1 : 1, display, + Qnil, NULL, 0); return detect_input_pending () ? Qnil : Qt; } @@ -6422,7 +6453,7 @@ usage: (sit-for SECONDS &optional NODISP OLD-NODISP) */) #ifndef EMACS_HAS_USECS if (usec != 0 && sec == 0) - error ("millisecond `sit-for' not supported on %s", SYSTEM_TYPE); + error ("Millisecond `sit-for' not supported on %s", SYSTEM_TYPE); #endif return sit_for (sec, usec, 0, NILP (nodisp), NILP (nodisp)); @@ -6436,68 +6467,106 @@ usage: (sit-for SECONDS &optional NODISP OLD-NODISP) */) /* A vector of size >= 2 * NFRAMES + 3 * NBUFFERS + 1, containing the session's frames, frame names, buffers, buffer-read-only flags, and - buffer-modified-flags, and a trailing sentinel (so we don't need to - add length checks). */ + buffer-modified-flags. */ static Lisp_Object frame_and_buffer_state; DEFUN ("frame-or-buffer-changed-p", Fframe_or_buffer_changed_p, - Sframe_or_buffer_changed_p, 0, 0, 0, + Sframe_or_buffer_changed_p, 0, 1, 0, doc: /* Return non-nil if the frame and buffer state appears to have changed. -The state variable is an internal vector containing all frames and buffers, +VARIABLE is a variable name whose value is either nil or a state vector +that will be updated to contain all frames and buffers, aside from buffers whose names start with space, -along with the buffers' read-only and modified flags, which allows a fast -check to see whether the menu bars might need to be recomputed. +along with the buffers' read-only and modified flags. This allows a fast +check to see whether buffer menus might need to be recomputed. If this function returns non-nil, it updates the internal vector to reflect -the current state. */) - () +the current state. + +If VARIABLE is nil, an internal variable is used. Users should not +pass nil for VARIABLE. */) + (variable) + Lisp_Object variable; { - Lisp_Object tail, frame, buf; - Lisp_Object *vecp; + Lisp_Object state, tail, frame, buf; + Lisp_Object *vecp, *end; int n; - vecp = XVECTOR (frame_and_buffer_state)->contents; + if (! NILP (variable)) + { + CHECK_SYMBOL (variable); + state = Fsymbol_value (variable); + if (! VECTORP (state)) + goto changed; + } + else + state = frame_and_buffer_state; + + vecp = XVECTOR (state)->contents; + end = vecp + XVECTOR (state)->size; + FOR_EACH_FRAME (tail, frame) { + if (vecp == end) + goto changed; if (!EQ (*vecp++, frame)) goto changed; + if (vecp == end) + goto changed; if (!EQ (*vecp++, XFRAME (frame)->name)) goto changed; } - /* Check that the buffer info matches. - No need to test for the end of the vector - because the last element of the vector is lambda - and that will always cause a mismatch. */ + /* Check that the buffer info matches. */ for (tail = Vbuffer_alist; CONSP (tail); tail = XCDR (tail)) { buf = XCDR (XCAR (tail)); /* Ignore buffers that aren't included in buffer lists. */ if (SREF (XBUFFER (buf)->name, 0) == ' ') continue; + if (vecp == end) + goto changed; if (!EQ (*vecp++, buf)) goto changed; + if (vecp == end) + goto changed; if (!EQ (*vecp++, XBUFFER (buf)->read_only)) goto changed; + if (vecp == end) + goto changed; if (!EQ (*vecp++, Fbuffer_modified_p (buf))) goto changed; } + if (vecp == end) + goto changed; /* Detect deletion of a buffer at the end of the list. */ if (EQ (*vecp, Qlambda)) return Qnil; + + /* Come here if we decide the data has changed. */ changed: - /* Start with 1 so there is room for at least one lambda at the end. */ + /* Count the size we will need. + Start with 1 so there is room for at least one lambda at the end. */ n = 1; FOR_EACH_FRAME (tail, frame) n += 2; for (tail = Vbuffer_alist; CONSP (tail); tail = XCDR (tail)) n += 3; - /* Reallocate the vector if it's grown, or if it's shrunk a lot. */ - if (n > XVECTOR (frame_and_buffer_state)->size - || n + 20 < XVECTOR (frame_and_buffer_state)->size / 2) + /* Reallocate the vector if data has grown to need it, + or if it has shrunk a lot. */ + if (! VECTORP (state) + || n > XVECTOR (state)->size + || n + 20 < XVECTOR (state)->size / 2) /* Add 20 extra so we grow it less often. */ - frame_and_buffer_state = Fmake_vector (make_number (n + 20), Qlambda); - vecp = XVECTOR (frame_and_buffer_state)->contents; + { + state = Fmake_vector (make_number (n + 20), Qlambda); + if (! NILP (variable)) + Fset (variable, state); + else + frame_and_buffer_state = state; + } + + /* Record the new data in the (possibly reallocated) vector. */ + vecp = XVECTOR (state)->contents; FOR_EACH_FRAME (tail, frame) { *vecp++ = frame; @@ -6515,12 +6584,12 @@ the current state. */) } /* Fill up the vector with lambdas (always at least one). */ *vecp++ = Qlambda; - while (vecp - XVECTOR (frame_and_buffer_state)->contents - < XVECTOR (frame_and_buffer_state)->size) + while (vecp - XVECTOR (state)->contents + < XVECTOR (state)->size) *vecp++ = Qlambda; /* Make sure we didn't overflow the vector. */ - if (vecp - XVECTOR (frame_and_buffer_state)->contents - > XVECTOR (frame_and_buffer_state)->size) + if (vecp - XVECTOR (state)->contents + > XVECTOR (state)->size) abort (); return Qt; }