changeset 108657:7e4a23f2f3ea

Completed initial debugging and testing of reimplemented cursor motion. .gdbinit (prowlims): Display row->minpos and row->maxpos. Display truncated_on_left_p and truncated_on_right_p flags. Formatting fixes. (pmtxrows): Display the ordinal number of each row. Don't display rows beyond the last one. xdisp.c (RECORD_MAX_MIN_POS): New macro. (display_line): Use it to record the minimum and maximum buffer positions for glyphs in the row being assembled. If word wrap is in effect, restore minimum and maximum positions seen up to the wrap point, when iterator returns to it. (find_row_edges): Fix logic; eol_pos should be tested before the rest. (try_window_reusing_current_matrix): Give up if in bidi-reordered row and cursor not already at point. Restore original pre-bidi code for unidirectional buffers. bidi.c (bidi_cache_shrink, bidi_cache_iterator_state): Fix reallocation of the cache. (Bug#6210) (bidi_cache_iterator_state): Don't zero out new_paragraph (it is not copied by bidi_copy_it).
author Eli Zaretskii <eliz@gnu.org>
date Wed, 19 May 2010 23:24:21 +0300
parents 0b28d05fa415
children 76010a03e524
files src/.gdbinit src/ChangeLog src/bidi.c src/xdisp.c
diffstat 4 files changed, 100 insertions(+), 97 deletions(-) [+]
line wrap: on
line diff
--- a/src/.gdbinit	Tue May 18 18:22:15 2010 +0300
+++ b/src/.gdbinit	Wed May 19 23:24:21 2010 +0300
@@ -616,7 +616,7 @@
 end
 
 define prowlims
-  printf "start=%d,end=%d,reversed=%d,cont=%d,at_zv=%d\n", $arg0->start.pos.charpos, $arg0->end.pos.charpos, $arg0->reversed_p, $arg0->continued_p, $arg0->ends_at_zv_p
+  printf "edges=(%d,%d),r2l=%d,cont=%d,trunc=(%d,%d),at_zv=%d\n", $arg0->minpos.charpos, $arg0->maxpos.charpos, $arg0->reversed_p, $arg0->continued_p, $arg0->truncated_on_left_p, $arg0->truncated_on_right_p, $arg0->ends_at_zv_p
 end
 document prowlims
 Print important attributes of a glyph_row structure.
@@ -626,10 +626,13 @@
 define pmtxrows
   set $mtx = $arg0
   set $gl = $mtx->rows
-  set $glend = $mtx->rows + $mtx->nrows
+  set $glend = $mtx->rows + $mtx->nrows - 1
+  set $i = 0
   while ($gl < $glend)
+    printf "%d: ", $i
     prowlims $gl
     set $gl = $gl + 1
+    set $i = $i + 1
   end
 end
 document pmtxrows
--- a/src/ChangeLog	Tue May 18 18:22:15 2010 +0300
+++ b/src/ChangeLog	Wed May 19 23:24:21 2010 +0300
@@ -1,3 +1,27 @@
+2010-05-19  Eli Zaretskii  <eliz@gnu.org>
+
+	* .gdbinit (prowlims): Display row->minpos and row->maxpos.
+	Display truncated_on_left_p and truncated_on_right_p flags.
+	Formatting fixes.
+	(pmtxrows): Display the ordinal number of each row.  Don't display
+	rows beyond the last one.
+
+	* xdisp.c (RECORD_MAX_MIN_POS): New macro.
+	(display_line): Use it to record the minimum and maximum buffer
+	positions for glyphs in the row being assembled.  If word wrap is
+	in effect, restore minimum and maximum positions seen up to the
+	wrap point, when iterator returns to it.
+	(find_row_edges): Fix logic; eol_pos should be tested before the
+	rest.
+	(try_window_reusing_current_matrix): Give up if in bidi-reordered
+	row and cursor not already at point.  Restore original pre-bidi
+	code for unidirectional buffers.
+
+	* bidi.c (bidi_cache_shrink, bidi_cache_iterator_state): Fix
+	reallocation of the cache.  (Bug#6210)
+	(bidi_cache_iterator_state): Don't zero out new_paragraph (it is
+	not copied by bidi_copy_it).
+
 2010-05-18  Eli Zaretskii  <eliz@gnu.org>
 
 	* dispextern.h (struct glyph_row): New members minpos and maxpos.
--- a/src/bidi.c	Tue May 18 18:22:15 2010 +0300
+++ b/src/bidi.c	Wed May 19 23:24:21 2010 +0300
@@ -543,6 +543,7 @@
 #define BIDI_CACHE_CHUNK 200
 static struct bidi_it *bidi_cache;
 static size_t bidi_cache_size = 0;
+static size_t elsz = sizeof (struct bidi_it);
 static int bidi_cache_idx;	/* next unused cache slot */
 static int bidi_cache_last_idx;	/* slot of last cache hit */
 
@@ -558,8 +559,9 @@
 {
   if (bidi_cache_size > BIDI_CACHE_CHUNK)
     {
-      bidi_cache_size = BIDI_CACHE_CHUNK * sizeof (struct bidi_it);
-      bidi_cache = (struct bidi_it *) xrealloc (bidi_cache, bidi_cache_size);
+      bidi_cache_size = BIDI_CACHE_CHUNK;
+      bidi_cache =
+	(struct bidi_it *) xrealloc (bidi_cache, bidi_cache_size * elsz);
     }
   bidi_cache_reset ();
 }
@@ -688,9 +690,9 @@
       /* Enlarge the cache as needed.  */
       if (idx >= bidi_cache_size)
 	{
-	  bidi_cache_size += BIDI_CACHE_CHUNK * sizeof (struct bidi_it);
+	  bidi_cache_size += BIDI_CACHE_CHUNK;
 	  bidi_cache =
-	    (struct bidi_it *) xrealloc (bidi_cache, bidi_cache_size);
+	    (struct bidi_it *) xrealloc (bidi_cache, bidi_cache_size * elsz);
 	}
       /* Character positions should correspond to cache positions 1:1.
 	 If we are outside the range of cached positions, the cache is
@@ -705,7 +707,6 @@
       bidi_copy_it (&bidi_cache[idx], bidi_it);
       if (!resolved)
 	bidi_cache[idx].resolved_level = -1;
-      bidi_cache[idx].new_paragraph = 0;
     }
   else
     {
--- a/src/xdisp.c	Tue May 18 18:22:15 2010 +0300
+++ b/src/xdisp.c	Wed May 19 23:24:21 2010 +0300
@@ -15293,39 +15293,26 @@
 	    {
 	      struct glyph *glyph = row->glyphs[TEXT_AREA] + w->cursor.hpos;
 	      struct glyph *end = glyph + row->used[TEXT_AREA];
-	      struct glyph *orig_glyph = glyph;
-	      struct cursor_pos orig_cursor = w->cursor;
-
-	      for (; glyph < end
-		     && (!BUFFERP (glyph->object)
-			 || glyph->charpos != PT);
-		   glyph++)
-		{
-		  w->cursor.hpos++;
-		  w->cursor.x += glyph->pixel_width;
-		}
-	      /* With bidi reordering, charpos changes non-linearly
-		 with hpos, so the right glyph could be to the
-		 left.  */
-	      if (!NILP (XBUFFER (w->buffer)->bidi_display_reordering)
-		  && (!BUFFERP (glyph->object) || glyph->charpos != PT))
-		{
-		  struct glyph *start_glyph = row->glyphs[TEXT_AREA];
-
-		  glyph = orig_glyph - 1;
-		  orig_cursor.hpos--;
-		  orig_cursor.x -= glyph->pixel_width;
-		  for (; glyph >= start_glyph
-			 && (!BUFFERP (glyph->object)
-			     || glyph->charpos != PT);
-		       glyph--)
-		    {
-		      w->cursor.hpos--;
-		      w->cursor.x -= glyph->pixel_width;
-		    }
-		  if (BUFFERP (glyph->object) && glyph->charpos == PT)
-		    w->cursor = orig_cursor;
-		}
+
+	      /* Can't use this optimization with bidi-reordered glyph
+		 rows, unless cursor is already at point. */
+	      if (!NILP (XBUFFER (w->buffer)->bidi_display_reordering))
+		{
+		  if (!(w->cursor.hpos >= 0
+			&& w->cursor.hpos < row->used[TEXT_AREA]
+			&& BUFFERP (glyph->object)
+			&& glyph->charpos == PT))
+		    return 0;
+		}
+	      else
+		for (; glyph < end
+		       && (!BUFFERP (glyph->object)
+			   || glyph->charpos < PT);
+		     glyph++)
+		  {
+		    w->cursor.hpos++;
+		    w->cursor.x += glyph->pixel_width;
+		  }
 	    }
 	}
 
@@ -17530,14 +17517,7 @@
   /* ROW->minpos is the value of min_pos, the minimal buffer position
      we have in ROW.  */
   if (min_pos <= ZV)
-    {
-      SET_TEXT_POS (row->minpos, min_pos, min_bpos);
-      if (max_pos == 0)
-	{
-	  max_pos = min_pos;
-	  max_bpos = min_bpos;
-	}
-    }
+    SET_TEXT_POS (row->minpos, min_pos, min_bpos);
   else
     {
       /* We didn't find _any_ valid buffer positions in any of the
@@ -17554,12 +17534,11 @@
   /* Here are the various use-cases for ending the row, and the
      corresponding values for ROW->maxpos:
 
-     Empty line                               min_pos + 1
      Line ends in a newline from buffer       eol_pos + 1
      Line is continued from buffer            max_pos + 1
      Line ends in a newline from string       max_pos
      Line is continued from string            max_pos
-     Line is entirely from a string           min_pos
+     Line is entirely from a string           min_pos == max_pos
      Line that ends at ZV                     ZV
 
      If you discover other use-cases, please add them here as
@@ -17568,16 +17547,7 @@
     row->maxpos = it->current.pos;
   else if (row->used[TEXT_AREA])
     {
-      if (max_pos == min_pos)
-	{
-	  if (it->method == GET_FROM_BUFFER)
-	    /* Empty line, which stands for a newline.  */
-	    SET_TEXT_POS (row->maxpos, min_pos + 1, min_bpos + 1);
-	  else
-	    /* A line that is entirely from a string.  */
-	    row->maxpos = row->minpos;
-	}
-      else if (CHARPOS (it->eol_pos) > 0)
+      if (CHARPOS (it->eol_pos) > 0)
 	SET_TEXT_POS (row->maxpos,
 		      CHARPOS (it->eol_pos) + 1, BYTEPOS (it->eol_pos) + 1);
       else if (row->continued_p)
@@ -17592,6 +17562,9 @@
 	}
       else if (row->ends_in_newline_from_string_p)
 	SET_TEXT_POS (row->maxpos, max_pos, max_bpos);
+      else if (max_pos == min_pos && it->method != GET_FROM_BUFFER)
+	/* A line that is entirely from a string/image/stretch...  */
+	row->maxpos = row->minpos;
       else
 	abort ();
     }
@@ -17616,6 +17589,8 @@
   int wrap_row_used = -1, wrap_row_ascent, wrap_row_height;
   int wrap_row_phys_ascent, wrap_row_phys_height;
   int wrap_row_extra_line_spacing;
+  EMACS_INT wrap_row_min_pos, wrap_row_min_bpos;
+  EMACS_INT wrap_row_max_pos, wrap_row_max_bpos;
   int cvpos;
   EMACS_INT min_pos = ZV + 1, min_bpos, max_pos = 0, max_bpos;
 
@@ -17674,6 +17649,23 @@
   row->phys_height = it->max_phys_ascent + it->max_phys_descent;
   row->extra_line_spacing = it->max_extra_line_spacing;
 
+/* Utility macro to record max and min buffer positions seen until now.  */
+#define RECORD_MAX_MIN_POS(IT)					\
+  do								\
+    {								\
+      if (IT_CHARPOS (*(IT)) < min_pos)				\
+	{							\
+	  min_pos = IT_CHARPOS (*(IT));				\
+	  min_bpos = IT_BYTEPOS (*(IT));			\
+	}							\
+      if (IT_CHARPOS (*(IT)) > max_pos)				\
+	{							\
+	  max_pos = IT_CHARPOS (*(IT));				\
+	  max_bpos = IT_BYTEPOS (*(IT));			\
+	}							\
+    }								\
+  while (0)
+
   /* Loop generating characters.  The loop is left with IT on the next
      character to display.  */
   while (1)
@@ -17743,6 +17735,10 @@
 		  wrap_row_phys_ascent = row->phys_ascent;
 		  wrap_row_phys_height = row->phys_height;
 		  wrap_row_extra_line_spacing = row->extra_line_spacing;
+		  wrap_row_min_pos = min_pos;
+		  wrap_row_min_bpos = min_bpos;
+		  wrap_row_max_pos = max_pos;
+		  wrap_row_max_bpos = max_bpos;
 		  may_wrap = 0;
 		}
 	    }
@@ -17793,6 +17789,10 @@
 					 it->max_extra_line_spacing);
 	  if (it->current_x - it->pixel_width < it->first_visible_x)
 	    row->x = x - it->first_visible_x;
+	  /* Record the maximum and minimum buffer positions seen so
+	     far in glyphs that will be displayed by this row.  */
+	  if (it->bidi_p)
+	    RECORD_MAX_MIN_POS (it);
 	}
       else
 	{
@@ -17826,6 +17826,11 @@
 		      it->current_x = new_x;
 		      it->continuation_lines_width += new_x;
 		      ++it->hpos;
+		      /* Record the maximum and minimum buffer
+			 positions seen so far in glyphs that will be
+			 displayed by this row.  */
+		      if (it->bidi_p)
+			RECORD_MAX_MIN_POS (it);
 		      if (i == nglyphs - 1)
 			{
 			  /* If line-wrap is on, check if a previous
@@ -17857,27 +17862,6 @@
 				}
 			    }
 			}
-
-		      /* Record the maximum and minimum buffer
-			 positions seen so far in glyphs that will be
-			 displayed by this row.  */
-		      if (it->bidi_p)
-			{
-			  if (BUFFERP (glyph->object)
-			      || INTEGERP (glyph->object))
-			    {
-			      if (IT_CHARPOS (*it) < min_pos)
-				{
-				  min_pos = IT_CHARPOS (*it);
-				  min_bpos = IT_BYTEPOS (*it);
-				}
-			      if (IT_CHARPOS (*it) > max_pos)
-				{
-				  max_pos = IT_CHARPOS (*it);
-				  max_bpos = IT_BYTEPOS (*it);
-				}
-			    }
-			}
 		    }
 		  else if (CHAR_GLYPH_PADDING_P (*glyph)
 			   && !FRAME_WINDOW_P (it->f))
@@ -17921,6 +17905,10 @@
 		      row->phys_ascent = wrap_row_phys_ascent;
 		      row->phys_height = wrap_row_phys_height;
 		      row->extra_line_spacing = wrap_row_extra_line_spacing;
+		      min_pos = wrap_row_min_pos;
+		      min_bpos = wrap_row_min_bpos;
+		      max_pos = wrap_row_max_pos;
+		      max_bpos = wrap_row_max_bpos;
 		      row->continued_p = 1;
 		      row->ends_at_zv_p = 0;
 		      row->exact_window_width_line_p = 0;
@@ -17987,22 +17975,7 @@
 		     seen so far in glyphs that will be displayed by
 		     this row.  */
 		  if (it->bidi_p)
-		    {
-		      if (BUFFERP (glyph->object)
-			  || INTEGERP (glyph->object))
-			{
-			  if (IT_CHARPOS (*it) < min_pos)
-			    {
-			      min_pos = IT_CHARPOS (*it);
-			      min_bpos = IT_BYTEPOS (*it);
-			    }
-			  if (IT_CHARPOS (*it) > max_pos)
-			    {
-			      max_pos = IT_CHARPOS (*it);
-			      max_bpos = IT_BYTEPOS (*it);
-			    }
-			}
-		    }
+		    RECORD_MAX_MIN_POS (it);
 
 		  if (x < it->first_visible_x)
 		    /* Glyph is partially visible, i.e. row starts at
@@ -18261,6 +18234,8 @@
     it->glyph_row->reversed_p = row->reversed_p;
   it->start = row->end;
   return row->displays_text_p;
+
+#undef RECORD_MAX_MIN_POS
 }
 
 DEFUN ("current-bidi-paragraph-direction", Fcurrent_bidi_paragraph_direction,