Merged from emacs@sv.gnu.org
[bpt/emacs.git] / src / xdisp.c
index 9481bbb..aea7ab5 100644 (file)
@@ -1,7 +1,7 @@
 /* Display generation from window structure and buffer text.
    Copyright (C) 1985, 1986, 1987, 1988, 1993, 1994, 1995,
                  1997, 1998, 1999, 2000, 2001, 2002, 2003,
-                 2004, 2005, 2006 Free Software Foundation, Inc.
+                 2004, 2005, 2006, 2007 Free Software Foundation, Inc.
 
 This file is part of GNU Emacs.
 
@@ -256,9 +256,9 @@ Lisp_Object list_of_error;
 Lisp_Object Vfontification_functions;
 Lisp_Object Qfontification_functions;
 
-/* Non-zero means automatically select any window when the mouse
+/* Non-nil means automatically select any window when the mouse
    cursor moves into it.  */
-int mouse_autoselect_window;
+Lisp_Object Vmouse_autoselect_window;
 
 /* Non-zero means draw tool bar buttons raised when the mouse moves
    over them.  */
@@ -283,10 +283,12 @@ Lisp_Object Vtool_bar_button_margin;
 
 EMACS_INT tool_bar_button_relief;
 
-/* Non-zero means automatically resize tool-bars so that all tool-bar
-   items are visible, and no blank lines remain.  */
+/* Non-nil means automatically resize tool-bars so that all tool-bar
+   items are visible, and no blank lines remain.
 
-int auto_resize_tool_bars_p;
+   If value is `grow-only', only make tool-bar bigger.  */
+
+Lisp_Object Vauto_resize_tool_bars;
 
 /* Non-zero means draw block and hollow cursor as wide as the glyph
    under it.  For example, if a block cursor is over a tab, it will be
@@ -578,21 +580,12 @@ Lisp_Object Vmessage_log_max;
 
 static Lisp_Object Vmessages_buffer_name;
 
-/* Index 0 is the buffer that holds the current (desired) echo area message,
-   or nil if none is desired right now.
-
-   Index 1 is the buffer that holds the previously displayed echo area message,
-   or nil to indicate no message.  This is normally what's on the screen now.
-
-   These two can point to the same buffer.  That happens when the last
-   message output by the user (or made by echoing) has been displayed.  */
+/* Current, index 0, and last displayed echo area message.  Either
+   buffers from echo_buffers, or nil to indicate no message.  */
 
 Lisp_Object echo_area_buffer[2];
 
-/* Permanent pointers to the two buffers that are used for echo area
-   purposes.  Once the two buffers are made, and their pointers are
-   placed here, these two slots remain unchanged unless those buffers
-   need to be created afresh.  */
+/* The buffers referenced from echo_area_buffer.  */
 
 static Lisp_Object echo_buffer[2];
 
@@ -615,6 +608,11 @@ int message_buf_print;
 Lisp_Object Qinhibit_menubar_update;
 int inhibit_menubar_update;
 
+/* When evaluating expressions from menu bar items (enable conditions,
+   for instance), this is the frame they are being processed for.  */
+
+Lisp_Object Vmenu_updating_frame;
+
 /* Maximum height for resizing mini-windows.  Either a float
    specifying a fraction of the available height, or an integer
    specifying a number of lines.  */
@@ -710,6 +708,10 @@ Lisp_Object Vresize_mini_windows;
 
 struct buffer *displayed_buffer;
 
+/* Space between overline and text. */
+
+EMACS_INT overline_margin;
+
 /* Value returned from text property handlers (see below).  */
 
 enum prop_handled
@@ -802,10 +804,6 @@ static int clear_face_cache_count;
 static int clear_image_cache_count;
 #endif
 
-/* Record the previous terminal frame we displayed.  */
-
-static struct frame *previous_terminal_frame;
-
 /* Non-zero while redisplay_internal is in progress.  */
 
 int redisplaying_p;
@@ -900,7 +898,7 @@ static void redisplay_window P_ ((Lisp_Object, int));
 static Lisp_Object redisplay_window_error ();
 static Lisp_Object redisplay_window_0 P_ ((Lisp_Object));
 static Lisp_Object redisplay_window_1 P_ ((Lisp_Object));
-static void update_menu_bar P_ ((struct frame *, int));
+static int update_menu_bar P_ ((struct frame *, int, int));
 static int try_window_reusing_current_matrix P_ ((struct window *));
 static int try_window_id P_ ((struct window *));
 static int display_line P_ ((struct it *));
@@ -916,6 +914,7 @@ static int display_string P_ ((unsigned char *, Lisp_Object, Lisp_Object,
 static void compute_line_metrics P_ ((struct it *));
 static void run_redisplay_end_trigger_hook P_ ((struct it *));
 static int get_overlay_strings P_ ((struct it *, int));
+static int get_overlay_strings_1 P_ ((struct it *, int, int));
 static void next_overlay_string P_ ((struct it *));
 static void reseat P_ ((struct it *, struct text_pos, int));
 static void reseat_1 P_ ((struct it *, struct text_pos, int));
@@ -1265,15 +1264,15 @@ line_bottom_y (it)
 
 
 /* Return 1 if position CHARPOS is visible in window W.
+   CHARPOS < 0 means return info about WINDOW_END position.
    If visible, set *X and *Y to pixel coordinates of top left corner.
    Set *RTOP and *RBOT to pixel height of an invisible area of glyph at POS.
-   EXACT_MODE_LINE_HEIGHTS_P non-zero means compute exact mode-line
-   and header-lines heights.  */
+   Set *ROWH and *VPOS to row's visible height and VPOS (row number).  */
 
 int
-pos_visible_p (w, charpos, x, y, rtop, rbot, exact_mode_line_heights_p)
+pos_visible_p (w, charpos, x, y, rtop, rbot, rowh, vpos)
      struct window *w;
-     int charpos, *x, *y, *rtop, *rbot, exact_mode_line_heights_p;
+     int charpos, *x, *y, *rtop, *rbot, *rowh, *vpos;
 {
   struct it it;
   struct text_pos top;
@@ -1291,26 +1290,23 @@ pos_visible_p (w, charpos, x, y, rtop, rbot, exact_mode_line_heights_p)
 
   SET_TEXT_POS_FROM_MARKER (top, w->start);
 
-  /* Compute exact mode line heights, if requested.  */
-  if (exact_mode_line_heights_p)
-    {
-      if (WINDOW_WANTS_MODELINE_P (w))
-       current_mode_line_height
-         = display_mode_line (w, CURRENT_MODE_LINE_FACE_ID (w),
-                              current_buffer->mode_line_format);
+  /* Compute exact mode line heights.  */
+  if (WINDOW_WANTS_MODELINE_P (w))
+    current_mode_line_height
+      = display_mode_line (w, CURRENT_MODE_LINE_FACE_ID (w),
+                          current_buffer->mode_line_format);
 
-      if (WINDOW_WANTS_HEADER_LINE_P (w))
-       current_header_line_height
-         = display_mode_line (w, HEADER_LINE_FACE_ID,
+  if (WINDOW_WANTS_HEADER_LINE_P (w))
+    current_header_line_height
+      = display_mode_line (w, HEADER_LINE_FACE_ID,
                               current_buffer->header_line_format);
-    }
 
   start_display (&it, w, top);
-  move_it_to (&it, charpos, -1, it.last_visible_y, -1,
-             MOVE_TO_POS | MOVE_TO_Y);
+  move_it_to (&it, charpos, -1, it.last_visible_y-1, -1,
+             (charpos >= 0 ? MOVE_TO_POS : 0) | MOVE_TO_Y);
 
   /* Note that we may overshoot because of invisible text.  */
-  if (IT_CHARPOS (it) >= charpos)
+  if (charpos >= 0 && IT_CHARPOS (it) >= charpos)
     {
       int top_x = it.current_x;
       int top_y = it.current_y;
@@ -1327,6 +1323,9 @@ pos_visible_p (w, charpos, x, y, rtop, rbot, exact_mode_line_heights_p)
          *y = max (top_y + max (0, it.max_ascent - it.ascent), window_top_y);
          *rtop = max (0, window_top_y - top_y);
          *rbot = max (0, bottom_y - it.last_visible_y);
+         *rowh = max (0, (min (bottom_y, it.last_visible_y)
+                          - max (top_y, window_top_y)));
+         *vpos = it.vpos;
        }
     }
   else
@@ -1336,7 +1335,8 @@ pos_visible_p (w, charpos, x, y, rtop, rbot, exact_mode_line_heights_p)
       it2 = it;
       if (IT_CHARPOS (it) < ZV && FETCH_BYTE (IT_BYTEPOS (it)) != '\n')
        move_it_by_lines (&it, 1, 0);
-      if (charpos < IT_CHARPOS (it))
+      if (charpos < IT_CHARPOS (it)
+         || (it.what == IT_EOB && charpos == IT_CHARPOS (it)))
        {
          visible_p = 1;
          move_it_to (&it2, charpos, -1, -1, -1, MOVE_TO_POS);
@@ -1345,6 +1345,11 @@ pos_visible_p (w, charpos, x, y, rtop, rbot, exact_mode_line_heights_p)
          *rtop = max (0, -it2.current_y);
          *rbot = max (0, ((it2.current_y + it2.max_ascent + it2.max_descent)
                           - it.last_visible_y));
+         *rowh = max (0, (min (it2.current_y + it2.max_ascent + it2.max_descent,
+                               it.last_visible_y)
+                          - max (it2.current_y,
+                                 WINDOW_HEADER_LINE_HEIGHT (w))));
+         *vpos = it2.vpos;
        }
     }
 
@@ -1356,6 +1361,15 @@ pos_visible_p (w, charpos, x, y, rtop, rbot, exact_mode_line_heights_p)
   if (visible_p && XFASTINT (w->hscroll) > 0)
     *x -= XFASTINT (w->hscroll) * WINDOW_FRAME_COLUMN_WIDTH (w);
 
+#if 0
+  /* Debugging code.  */
+  if (visible_p)
+    fprintf (stderr, "+pv pt=%d vs=%d --> x=%d y=%d rt=%d rb=%d rh=%d vp=%d\n",
+            charpos, w->vscroll, *x, *y, *rtop, *rbot, *rowh, *vpos);
+  else
+    fprintf (stderr, "-pv pt=%d vs=%d\n", charpos, w->vscroll);
+#endif
+
   return visible_p;
 }
 
@@ -1910,7 +1924,7 @@ get_glyph_string_clip_rects (s, rects, n)
     }
 
   if ((s->for_overlaps & OVERLAPS_BOTH) == 0
-      || (s->for_overlaps & OVERLAPS_BOTH) == OVERLAPS_BOTH && n == 1)
+      || ((s->for_overlaps & OVERLAPS_BOTH) == OVERLAPS_BOTH && n == 1))
     {
 #ifdef CONVERT_FROM_XRECT
       CONVERT_FROM_XRECT (r, *rects);
@@ -1936,23 +1950,27 @@ get_glyph_string_clip_rects (s, rects, n)
        {
          rs[i] = r;
          if (r.y + r.height > row_y)
-           if (r.y < row_y)
-             rs[i].height = row_y - r.y;
-           else
-             rs[i].height = 0;
+           {
+             if (r.y < row_y)
+               rs[i].height = row_y - r.y;
+             else
+               rs[i].height = 0;
+           }
          i++;
        }
       if (s->for_overlaps & OVERLAPS_SUCC)
        {
          rs[i] = r;
          if (r.y < row_y + s->row->visible_height)
-           if (r.y + r.height > row_y + s->row->visible_height)
-             {
-               rs[i].y = row_y + s->row->visible_height;
-               rs[i].height = r.y + r.height - rs[i].y;
-             }
-           else
-             rs[i].height = 0;
+           {
+             if (r.y + r.height > row_y + s->row->visible_height)
+               {
+                 rs[i].y = row_y + s->row->visible_height;
+                 rs[i].height = r.y + r.height - rs[i].y;
+               }
+             else
+               rs[i].height = 0;
+           }
          i++;
        }
 
@@ -1982,15 +2000,15 @@ get_glyph_string_clip_rect (s, nr)
    Set w->phys_cursor_width to width of phys cursor.
 */
 
-int
-get_phys_cursor_geometry (w, row, glyph, heightp)
+void
+get_phys_cursor_geometry (w, row, glyph, xp, yp, heightp)
      struct window *w;
      struct glyph_row *row;
      struct glyph *glyph;
-     int *heightp;
+     int *xp, *yp, *heightp;
 {
   struct frame *f = XFRAME (WINDOW_FRAME (w));
-  int y, wd, h, h0, y0;
+  int x, y, wd, h, h0, y0;
 
   /* Compute the width of the rectangle to draw.  If on a stretch
      glyph, and `x-stretch-block-cursor' is nil, don't draw a
@@ -2000,6 +2018,14 @@ get_phys_cursor_geometry (w, row, glyph, heightp)
 #ifdef HAVE_NTGUI
   wd++; /* Why? */
 #endif
+
+  x = w->phys_cursor.x;
+  if (x < 0)
+    {
+      wd += x;
+      x = 0;
+    }
+
   if (glyph->type == STRETCH_GLYPH
       && !x_stretch_cursor_p)
     wd = min (FRAME_COLUMN_WIDTH (f), wd);
@@ -2029,8 +2055,9 @@ get_phys_cursor_geometry (w, row, glyph, heightp)
        }
     }
 
+  *xp = WINDOW_TEXT_TO_FRAME_PIXEL_X (w, x);
+  *yp = WINDOW_TO_FRAME_PIXEL_Y (w, y);
   *heightp = h;
-  return WINDOW_TO_FRAME_PIXEL_Y (w, y);
 }
 
 /*
@@ -2053,8 +2080,9 @@ remember_mouse_glyph (f, gx, gy, rect)
   /* Try to determine frame pixel position and size of the glyph under
      frame pixel coordinates X/Y on frame F.  */
 
-  window = window_from_coordinates (f, gx, gy, &part, &x, &y, 0);
-  if (NILP (window))
+  if (!f->glyphs_initialized_p
+      || (window = window_from_coordinates (f, gx, gy, &part, &x, &y, 0),
+         NILP (window)))
     {
       width = FRAME_SMALLEST_CHAR_WIDTH (f);
       height = FRAME_SMALLEST_FONT_HEIGHT (f);
@@ -2467,7 +2495,7 @@ init_iterator (it, w, charpos, bytepos, row, base_face_id)
   XSETWINDOW (it->window, w);
   it->w = w;
   it->f = XFRAME (w->frame);
-
+  
   /* Extra space between lines (on window systems only).  */
   if (base_face_id == DEFAULT_FACE_ID
       && FRAME_WINDOW_P (it->f))
@@ -2484,9 +2512,9 @@ init_iterator (it, w, charpos, bytepos, row, base_face_id)
 
   /* If realized faces have been removed, e.g. because of face
      attribute changes of named faces, recompute them.  When running
-     in batch mode, the face cache of Vterminal_frame is null.  If
+     in batch mode, the face cache of the initial frame is null.  If
      we happen to get called, make a dummy face cache.  */
-  if (noninteractive && FRAME_FACE_CACHE (it->f) == NULL)
+  if (FRAME_FACE_CACHE (it->f) == NULL)
     init_frame_faces (it->f);
   if (FRAME_FACE_CACHE (it->f)->used == 0)
     recompute_basic_faces (it->f);
@@ -2896,8 +2924,8 @@ init_from_display_pos (it, w, pos)
         also ``processed'' overlay strings at ZV.  */
       while (it->sp)
        pop_it (it);
-      it->current.overlay_string_index = -1;
-      it->method = GET_FROM_BUFFER;
+      xassert (it->current.overlay_string_index == -1);
+      xassert (it->method == GET_FROM_BUFFER);
       if (CHARPOS (pos->pos) == ZV)
        it->overlay_strings_at_end_processed_p = 1;
     }
@@ -3008,7 +3036,19 @@ handle_stop (it)
          if (handled == HANDLED_RECOMPUTE_PROPS)
            break;
          else if (handled == HANDLED_RETURN)
-           return;
+           {
+             /* We still want to show before and after strings from
+                overlays even if the actual buffer text is replaced.  */
+             if (!handle_overlay_change_p || it->sp > 1)
+               return;
+             if (!get_overlay_strings_1 (it, 0, 0))
+               return;
+             it->ignore_overlay_strings_at_pos_p = 1;
+             it->string_from_display_prop_p = 0;
+             handle_overlay_change_p = 0;
+             handled = HANDLED_RECOMPUTE_PROPS;
+             break;
+           }
          else if (handled == HANDLED_OVERLAY_STRING_CONSUMED)
            handle_overlay_change_p = 0;
        }
@@ -3197,7 +3237,9 @@ handle_fontified_prop (it)
       && !NILP (Vrun_hooks)
       && (pos = make_number (IT_CHARPOS (*it)),
          prop = Fget_char_property (pos, Qfontified, Qnil),
-         NILP (prop)))
+         /* Ignore the special cased nil value always present at EOB since
+            no amount of fontifying will be able to change it.  */
+         NILP (prop) && IT_CHARPOS (*it) < Z))
     {
       int count = SPECPDL_INDEX ();
       Lisp_Object val;
@@ -3854,7 +3896,7 @@ handle_single_display_spec (it, spec, object, position,
 {
   Lisp_Object form;
   Lisp_Object location, value;
-  struct text_pos start_pos;
+  struct text_pos start_pos, save_pos;
   int valid_p;
 
   /* If SPEC is a list of the form `(when FORM . VALUE)', evaluate FORM.
@@ -3897,7 +3939,7 @@ handle_single_display_spec (it, spec, object, position,
       && EQ (XCAR (spec), Qheight)
       && CONSP (XCDR (spec)))
     {
-      if (FRAME_TERMCAP_P (it->f) || FRAME_MSDOS_P (it->f))
+      if (!FRAME_WINDOW_P (it->f))
        return 0;
 
       it->font_height = XCAR (XCDR (spec));
@@ -3963,7 +4005,7 @@ handle_single_display_spec (it, spec, object, position,
       && EQ (XCAR (spec), Qspace_width)
       && CONSP (XCDR (spec)))
     {
-      if (FRAME_TERMCAP_P (it->f) || FRAME_MSDOS_P (it->f))
+      if (!FRAME_WINDOW_P (it->f))
        return 0;
 
       value = XCAR (XCDR (spec));
@@ -3979,7 +4021,7 @@ handle_single_display_spec (it, spec, object, position,
     {
       Lisp_Object tem;
 
-      if (FRAME_TERMCAP_P (it->f) || FRAME_MSDOS_P (it->f))
+      if (!FRAME_WINDOW_P (it->f))
        return 0;
 
       if (tem = XCDR (spec), CONSP (tem))
@@ -4005,7 +4047,7 @@ handle_single_display_spec (it, spec, object, position,
       && EQ (XCAR (spec), Qraise)
       && CONSP (XCDR (spec)))
     {
-      if (FRAME_TERMCAP_P (it->f) || FRAME_MSDOS_P (it->f))
+      if (!FRAME_WINDOW_P (it->f))
        return 0;
 
 #ifdef HAVE_WINDOW_SYSTEM
@@ -4046,7 +4088,7 @@ handle_single_display_spec (it, spec, object, position,
       int face_id = DEFAULT_FACE_ID;
       int fringe_bitmap;
 
-      if (FRAME_TERMCAP_P (it->f) || FRAME_MSDOS_P (it->f))
+      if (!FRAME_WINDOW_P (it->f))
        /* If we return here, POSITION has been advanced
           across the text with this property.  */
        return 0;
@@ -4071,7 +4113,10 @@ handle_single_display_spec (it, spec, object, position,
       /* Save current settings of IT so that we can restore them
         when we are finished with the glyph property value.  */
 
+      save_pos = it->position;
+      it->position = *position;
       push_it (it);
+      it->position = save_pos;
 
       it->area = TEXT_AREA;
       it->what = IT_IMAGE;
@@ -4092,7 +4137,7 @@ handle_single_display_spec (it, spec, object, position,
          it->left_user_fringe_face_id = face_id;
        }
       else
-       {
+        {
          it->right_user_fringe_bitmap = fringe_bitmap;
          it->right_user_fringe_face_id = face_id;
        }
@@ -4137,15 +4182,18 @@ handle_single_display_spec (it, spec, object, position,
 
   valid_p = (STRINGP (value)
 #ifdef HAVE_WINDOW_SYSTEM
-            || (!FRAME_TERMCAP_P (it->f) && valid_image_p (value))
+             || (FRAME_WINDOW_P (it->f) && valid_image_p (value))
 #endif /* not HAVE_WINDOW_SYSTEM */
-            || (CONSP (value) && EQ (XCAR (value), Qspace)));
+             || (CONSP (value) && EQ (XCAR (value), Qspace)));
 
   if (valid_p && !display_replaced_before_p)
     {
       /* Save current settings of IT so that we can restore them
         when we are finished with the glyph property value.  */
+      save_pos = it->position;
+      it->position = *position;
       push_it (it);
+      it->position = save_pos;
 
       if (NILP (location))
        it->area = TEXT_AREA;
@@ -4206,7 +4254,7 @@ handle_single_display_spec (it, spec, object, position,
 }
 
 
-/* Check if SPEC is a display specification value whose text should be
+/* Check if SPEC is a display sub-property value whose text should be
    treated as intangible.  */
 
 static int
@@ -4443,6 +4491,28 @@ handle_composition_prop (it)
 
       if (id >= 0)
        {
+         struct composition *cmp = composition_table[id];
+
+         if (cmp->glyph_len == 0)
+           {
+             /* No glyph.  */
+             if (STRINGP (it->string))
+               {
+                 IT_STRING_CHARPOS (*it) = end;
+                 IT_STRING_BYTEPOS (*it) = string_char_to_byte (it->string,
+                                                                end);
+               }
+             else
+               {
+                 IT_CHARPOS (*it) = end;
+                 IT_BYTEPOS (*it) = CHAR_TO_BYTE (end);
+               }
+             return HANDLED_RECOMPUTE_PROPS;
+           }
+
+         it->stop_charpos = end;
+         push_it (it);
+
          it->method = GET_FROM_COMPOSITION;
          it->cmp_id = id;
          it->cmp_len = COMPOSITION_LENGTH (prop);
@@ -4452,7 +4522,6 @@ handle_composition_prop (it)
          it->len = (STRINGP (it->string)
                     ? string_char_to_byte (it->string, end)
                     : CHAR_TO_BYTE (end)) - pos_byte;
-         it->stop_charpos = end;
          handled = HANDLED_RETURN;
        }
     }
@@ -4512,13 +4581,14 @@ next_overlay_string (it)
       int display_ellipsis_p = it->stack[it->sp - 1].display_ellipsis_p;
 
       pop_it (it);
-      xassert (it->stop_charpos >= BEGV
-              && it->stop_charpos <= it->end_charpos);
-      it->string = Qnil;
+      xassert (it->sp > 0
+              || it->method == GET_FROM_COMPOSITION
+              || (NILP (it->string)
+                  && it->method == GET_FROM_BUFFER
+                  && it->stop_charpos >= BEGV
+                  && it->stop_charpos <= it->end_charpos));
       it->current.overlay_string_index = -1;
-      SET_TEXT_POS (it->current.string_pos, -1, -1);
       it->n_overlay_strings = 0;
-      it->method = GET_FROM_BUFFER;
 
       /* If we're at the end of the buffer, record that we have
         processed the overlay strings there already, so that
@@ -4774,7 +4844,7 @@ load_overlay_strings (it, charpos)
    least one overlay string was found.  */
 
 static int
-get_overlay_strings (it, charpos)
+get_overlay_strings_1 (it, charpos, compute_stop_p)
      struct it *it;
      int charpos;
 {
@@ -4796,12 +4866,13 @@ get_overlay_strings (it, charpos)
       /* Make sure we know settings in current_buffer, so that we can
         restore meaningful values when we're done with the overlay
         strings.  */
-      compute_stop_pos (it);
+      if (compute_stop_p)
+       compute_stop_pos (it);
       xassert (it->face_id >= 0);
 
       /* Save IT's settings.  They are restored after all overlay
         strings have been processed.  */
-      xassert (it->sp == 0);
+      xassert (!compute_stop_p || it->sp == 0);
       push_it (it);
 
       /* Set up IT to deliver display elements from the first overlay
@@ -4813,13 +4884,22 @@ get_overlay_strings (it, charpos)
       it->end_charpos = SCHARS (it->string);
       it->multibyte_p = STRING_MULTIBYTE (it->string);
       it->method = GET_FROM_STRING;
+      return 1;
     }
-  else
-    {
-      it->string = Qnil;
-      it->current.overlay_string_index = -1;
-      it->method = GET_FROM_BUFFER;
-    }
+
+  it->current.overlay_string_index = -1;
+  return 0;
+}
+
+static int
+get_overlay_strings (it, charpos)
+     struct it *it;
+     int charpos;
+{
+  it->string = Qnil;
+  it->method = GET_FROM_BUFFER;
+
+  (void) get_overlay_strings_1 (it, charpos, 1);
 
   CHECK_IT (it);
 
@@ -4844,19 +4924,38 @@ push_it (it)
 {
   struct iterator_stack_entry *p;
 
-  xassert (it->sp < 2);
+  xassert (it->sp < IT_STACK_SIZE);
   p = it->stack + it->sp;
 
   p->stop_charpos = it->stop_charpos;
   xassert (it->face_id >= 0);
   p->face_id = it->face_id;
   p->string = it->string;
-  p->pos = it->current;
+  p->method = it->method;
+  switch (p->method)
+    {
+    case GET_FROM_IMAGE:
+      p->u.image.object = it->object;
+      p->u.image.image_id = it->image_id;
+      p->u.image.slice = it->slice;
+      break;
+    case GET_FROM_COMPOSITION:
+      p->u.comp.object = it->object;
+      p->u.comp.c = it->c;
+      p->u.comp.len = it->len;
+      p->u.comp.cmp_id = it->cmp_id;
+      p->u.comp.cmp_len = it->cmp_len;
+      break;
+    case GET_FROM_STRETCH:
+      p->u.stretch.object = it->object;
+      break;
+    }
+  p->position = it->position;
+  p->current = it->current;
   p->end_charpos = it->end_charpos;
   p->string_nchars = it->string_nchars;
   p->area = it->area;
   p->multibyte_p = it->multibyte_p;
-  p->slice = it->slice;
   p->space_width = it->space_width;
   p->font_height = it->font_height;
   p->voffset = it->voffset;
@@ -4883,13 +4982,40 @@ pop_it (it)
   p = it->stack + it->sp;
   it->stop_charpos = p->stop_charpos;
   it->face_id = p->face_id;
+  it->current = p->current;
+  it->position = p->position;
   it->string = p->string;
-  it->current = p->pos;
+  if (NILP (it->string))
+    SET_TEXT_POS (it->current.string_pos, -1, -1);
+  it->method = p->method;
+  switch (it->method)
+    {
+    case GET_FROM_IMAGE:
+      it->image_id = p->u.image.image_id;
+      it->object = p->u.image.object;
+      it->slice = p->u.image.slice;
+      break;
+    case GET_FROM_COMPOSITION:
+      it->object = p->u.comp.object;
+      it->c = p->u.comp.c;
+      it->len = p->u.comp.len;
+      it->cmp_id = p->u.comp.cmp_id;
+      it->cmp_len = p->u.comp.cmp_len;
+      break;
+    case GET_FROM_STRETCH:
+      it->object = p->u.comp.object;
+      break;
+    case GET_FROM_BUFFER:
+      it->object = it->w->buffer;
+      break;
+    case GET_FROM_STRING:
+      it->object = it->string;
+      break;
+    }
   it->end_charpos = p->end_charpos;
   it->string_nchars = p->string_nchars;
   it->area = p->area;
   it->multibyte_p = p->multibyte_p;
-  it->slice = p->slice;
   it->space_width = p->space_width;
   it->font_height = p->font_height;
   it->voffset = p->voffset;
@@ -5021,6 +5147,7 @@ back_to_previous_visible_line_start (it)
   while (IT_CHARPOS (*it) > BEGV)
     {
       back_to_previous_line_start (it);
+
       if (IT_CHARPOS (*it) <= BEGV)
        break;
 
@@ -5040,37 +5167,47 @@ back_to_previous_visible_line_start (it)
          continue;
       }
 
-      /* If newline has a display property that replaces the newline with something
-        else (image or text), find start of overlay or interval and continue search
-        from that point.  */
-      if (IT_CHARPOS (*it) > BEGV)
-       {
-         struct it it2 = *it;
-         int pos;
-         int beg, end;
-         Lisp_Object val, overlay;
-
-         pos = --IT_CHARPOS (it2);
-         --IT_BYTEPOS (it2);
-         it2.sp = 0;
-         if (handle_display_prop (&it2) == HANDLED_RETURN
-             && !NILP (val = get_char_property_and_overlay
-                       (make_number (pos), Qdisplay, Qnil, &overlay))
-             && (OVERLAYP (overlay)
-                 ? (beg = OVERLAY_POSITION (OVERLAY_START (overlay)))
-                 : get_property_and_range (pos, Qdisplay, &val, &beg, &end, Qnil)))
-           {
-             if (beg < BEGV)
-               beg = BEGV;
-             IT_CHARPOS (*it) = beg;
-             IT_BYTEPOS (*it) = buf_charpos_to_bytepos (current_buffer, beg);
-             continue;
-           }
-       }
+      if (IT_CHARPOS (*it) <= BEGV)
+       break;
 
-      break;
+      {
+       struct it it2;
+       int pos;
+       int beg, end;
+       Lisp_Object val, overlay;
+
+       /* If newline is part of a composition, continue from start of composition */
+       if (find_composition (IT_CHARPOS (*it), -1, &beg, &end, &val, Qnil)
+           && beg < IT_CHARPOS (*it))
+         goto replaced;
+
+       /* If newline is replaced by a display property, find start of overlay
+          or interval and continue search from that point.  */
+       it2 = *it;
+       pos = --IT_CHARPOS (it2);
+       --IT_BYTEPOS (it2);
+       it2.sp = 0;
+       if (handle_display_prop (&it2) == HANDLED_RETURN
+           && !NILP (val = get_char_property_and_overlay
+                     (make_number (pos), Qdisplay, Qnil, &overlay))
+           && (OVERLAYP (overlay)
+               ? (beg = OVERLAY_POSITION (OVERLAY_START (overlay)))
+               : get_property_and_range (pos, Qdisplay, &val, &beg, &end, Qnil)))
+         goto replaced;
+
+       /* Newline is not replaced by anything -- so we are done.  */
+       break;
+
+      replaced:
+       if (beg < BEGV)
+         beg = BEGV;
+       IT_CHARPOS (*it) = beg;
+       IT_BYTEPOS (*it) = buf_charpos_to_bytepos (current_buffer, beg);
+      }
     }
 
+  it->continuation_lines_width = 0;
+
   xassert (IT_CHARPOS (*it) >= BEGV);
   xassert (IT_CHARPOS (*it) == BEGV
           || FETCH_BYTE (IT_BYTEPOS (*it) - 1) == '\n');
@@ -5193,7 +5330,6 @@ reseat_1 (it, pos, set_stop_p)
   xassert (CHARPOS (pos) >= BEGV && CHARPOS (pos) <= ZV);
 
   it->current.pos = it->position = pos;
-  XSETBUFFER (it->object, current_buffer);
   it->end_charpos = ZV;
   it->dpvec = NULL;
   it->current.dpvec_index = -1;
@@ -5202,15 +5338,11 @@ reseat_1 (it, pos, set_stop_p)
   IT_STRING_BYTEPOS (*it) = -1;
   it->string = Qnil;
   it->method = GET_FROM_BUFFER;
-  /* RMS: I added this to fix a bug in move_it_vertically_backward
-     where it->area continued to relate to the starting point
-     for the backward motion.  Bug report from
-     Nick Roberts <nick@nick.uklinux.net> on 19 May 2003.
-     However, I am not sure whether reseat still does the right thing
-     in general after this change.  */
+  it->object = it->w->buffer;
   it->area = TEXT_AREA;
   it->multibyte_p = !NILP (current_buffer->enable_multibyte_characters);
   it->sp = 0;
+  it->string_from_display_prop_p = 0;
   it->face_before_selective_p = 0;
 
   if (set_stop_p)
@@ -5689,18 +5821,18 @@ set_iterator_to_next (it, reseat_p)
 
     case GET_FROM_COMPOSITION:
       xassert (it->cmp_id >= 0 && it->cmp_id < n_compositions);
-      if (STRINGP (it->string))
+      xassert (it->sp > 0);
+      pop_it (it);
+      if (it->method == GET_FROM_STRING)
        {
          IT_STRING_BYTEPOS (*it) += it->len;
          IT_STRING_CHARPOS (*it) += it->cmp_len;
-         it->method = GET_FROM_STRING;
          goto consider_string_end;
        }
-      else
+      else if (it->method == GET_FROM_BUFFER)
        {
          IT_BYTEPOS (*it) += it->len;
          IT_CHARPOS (*it) += it->cmp_len;
-         it->method = GET_FROM_BUFFER;
        }
       break;
 
@@ -5730,7 +5862,10 @@ set_iterator_to_next (it, reseat_p)
          else if (STRINGP (it->string))
            it->method = GET_FROM_STRING;
          else
-           it->method = GET_FROM_BUFFER;
+           {
+             it->method = GET_FROM_BUFFER;
+             it->object = it->w->buffer;
+           }
 
          it->dpvec = NULL;
          it->current.dpvec_index = -1;
@@ -5778,9 +5913,8 @@ set_iterator_to_next (it, reseat_p)
              && it->sp > 0)
            {
              pop_it (it);
-             if (STRINGP (it->string))
+             if (it->method == GET_FROM_STRING)
                goto consider_string_end;
-             it->method = GET_FROM_BUFFER;
            }
        }
       break;
@@ -5792,13 +5926,8 @@ set_iterator_to_next (it, reseat_p)
          if the `display' property takes up the whole string.  */
       xassert (it->sp > 0);
       pop_it (it);
-      it->image_id = 0;
-      if (STRINGP (it->string))
-       {
-         it->method = GET_FROM_STRING;
-         goto consider_string_end;
-       }
-      it->method = GET_FROM_BUFFER;
+      if (it->method == GET_FROM_STRING)
+       goto consider_string_end;
       break;
 
     default:
@@ -5943,9 +6072,7 @@ next_element_from_string (it)
        }
     }
 
-  /* Record what we have and where it came from.  Note that we store a
-     buffer position in IT->position although it could arguably be a
-     string position.  */
+  /* Record what we have and where it came from.  */
   it->what = IT_CHARACTER;
   it->object = it->string;
   it->position = position;
@@ -6021,6 +6148,7 @@ next_element_from_ellipsis (it)
         setting face_before_selective_p.  */
       it->saved_face_id = it->face_id;
       it->method = GET_FROM_BUFFER;
+      it->object = it->w->buffer;
       reseat_at_next_visible_line_start (it, 1);
       it->face_before_selective_p = 1;
     }
@@ -6207,6 +6335,10 @@ next_element_from_composition (it)
   it->position = (STRINGP (it->string)
                  ? it->current.string_pos
                  : it->current.pos);
+  if (STRINGP (it->string))
+    it->object = it->string;
+  else
+    it->object = it->w->buffer;
   return 1;
 }
 
@@ -6655,6 +6787,10 @@ move_it_to (it, to_charpos, to_x, to_y, to_vpos, op)
          if (reached)
            break;
        }
+      else if (BUFFERP (it->object)
+              && it->method == GET_FROM_BUFFER
+              && IT_CHARPOS (*it) >= to_charpos)
+       skip = MOVE_POS_MATCH_OR_ZV;
       else
        skip = move_it_in_display_line_to (it, to_charpos, -1, MOVE_TO_POS);
 
@@ -6681,7 +6817,12 @@ move_it_to (it, to_charpos, to_x, to_y, to_vpos, op)
          break;
 
        case MOVE_LINE_CONTINUED:
-         it->continuation_lines_width += it->current_x;
+         /* For continued lines ending in a tab, some of the glyphs
+            associated with the tab are displayed on the current
+            line.  Since it->current_x does not include these glyphs,
+            we use it->last_visible_x instead.  */
+         it->continuation_lines_width +=
+           (it->c == '\t') ? it->last_visible_x : it->current_x;
          break;
 
        default:
@@ -7370,8 +7511,8 @@ message2_nolog (m, nbytes, multibyte)
       do_pending_window_change (0);
       echo_area_display (1);
       do_pending_window_change (0);
-      if (frame_up_to_date_hook != 0 && ! gc_in_progress)
-       (*frame_up_to_date_hook) (f);
+      if (FRAME_TERMINAL (f)->frame_up_to_date_hook != 0 && ! gc_in_progress)
+       (*FRAME_TERMINAL (f)->frame_up_to_date_hook) (f);
     }
 }
 
@@ -7474,8 +7615,8 @@ message3_nolog (m, nbytes, multibyte)
       do_pending_window_change (0);
       echo_area_display (1);
       do_pending_window_change (0);
-      if (frame_up_to_date_hook != 0 && ! gc_in_progress)
-       (*frame_up_to_date_hook) (f);
+      if (FRAME_TERMINAL (f)->frame_up_to_date_hook != 0 && ! gc_in_progress)
+       (*FRAME_TERMINAL (f)->frame_up_to_date_hook) (f);
     }
 }
 
@@ -7713,6 +7854,10 @@ ensure_echo_area_buffers ()
    WHICH > 0 means use echo_area_buffer[1].  If that is nil, choose a
    suitable buffer from echo_buffer[] and clear it.
 
+   If WHICH < 0, set echo_area_buffer[1] to echo_area_buffer[0], so
+   that the current message becomes the last displayed one, make
+   choose a suitable buffer for echo_area_buffer[0], and clear it.
+
    Value is what FN returns.  */
 
 static int
@@ -7737,6 +7882,17 @@ with_echo_area_buffer (w, which, fn, a1, a2, a3, a4)
     this_one = 0, the_other = 1;
   else if (which > 0)
     this_one = 1, the_other = 0;
+  else
+    {
+      this_one = 0, the_other = 1;
+      clear_buffer_p = 1;
+
+      /* We need a fresh one in case the current echo buffer equals
+        the one containing the last displayed echo area message.  */
+      if (!NILP (echo_area_buffer[this_one])
+         && EQ (echo_area_buffer[this_one], echo_area_buffer[the_other]))
+       echo_area_buffer[this_one] = Qnil;
+    }
 
   /* Choose a suitable buffer from echo_buffer[] is we don't
      have one.  */
@@ -8374,7 +8530,7 @@ set_message (s, string, nbytes, multibyte_p)
     = ((s && multibyte_p)
        || (STRINGP (string) && STRING_MULTIBYTE (string)));
 
-  with_echo_area_buffer (0, 0, set_message_1,
+  with_echo_area_buffer (0, -1, set_message_1,
                         (EMACS_INT) s, string, nbytes, multibyte_p);
   message_buf_print = 0;
   help_echo_showing_p = 0;
@@ -8404,7 +8560,6 @@ set_message_1 (a1, a2, nbytes, multibyte_p)
 
   /* Insert new message at BEG.  */
   TEMP_SET_PT_BOTH (BEG, BEG_BYTE);
-  Ferase_buffer ();
 
   if (STRINGP (string))
     {
@@ -8500,11 +8655,11 @@ clear_garbaged_frames ()
     {
       Lisp_Object tail, frame;
       int changed_count = 0;
-
+      
       FOR_EACH_FRAME (tail, frame)
        {
          struct frame *f = XFRAME (frame);
-
+         
          if (FRAME_VISIBLE_P (f) && FRAME_GARBAGED_P (f))
            {
              if (f->resized_p)
@@ -8518,7 +8673,7 @@ clear_garbaged_frames ()
              f->resized_p = 0;
            }
        }
-
+      
       frame_garbaged = 0;
       if (changed_count)
        ++windows_or_buffers_changed;
@@ -8551,11 +8706,10 @@ echo_area_display (update_frame_p)
 /* The terminal frame is used as the first Emacs frame on the Mac OS.  */
 #ifndef MAC_OS8
 #ifdef HAVE_WINDOW_SYSTEM
-  /* When Emacs starts, selected_frame may be a visible terminal
-     frame, even if we run under a window system.  If we let this
-     through, a message would be displayed on the terminal.  */
-  if (EQ (selected_frame, Vterminal_frame)
-      && !NILP (Vwindow_system))
+  /* When Emacs starts, selected_frame may be the initial terminal
+     frame.  If we let this through, a message would be displayed on
+     the terminal.  */
+  if (FRAME_INITIAL_P (XFRAME (selected_frame)))
     return 0;
 #endif /* HAVE_WINDOW_SYSTEM */
 #endif
@@ -8606,7 +8760,7 @@ echo_area_display (update_frame_p)
                 Can do with a display update of the echo area,
                 unless we displayed some mode lines.  */
              update_single_window (w, 1);
-             rif->flush_display (f);
+             FRAME_RIF (f)->flush_display (f);
            }
          else
            update_frame (f, 1, 1);
@@ -8621,8 +8775,10 @@ echo_area_display (update_frame_p)
   else if (!EQ (mini_window, selected_window))
     windows_or_buffers_changed++;
 
-  /* The current message is now also the last one displayed.  */
+  /* Last displayed message is now the current message.  */
   echo_area_buffer[1] = echo_area_buffer[0];
+  /* Inform read_char that we're not echoing.  */
+  echo_message_buffer = Qnil;
 
   /* Prevent redisplay optimization in redisplay_internal by resetting
      this_line_start_pos.  This is done because the mini-buffer now
@@ -8916,6 +9072,9 @@ prepare_menu_bars ()
     {
       Lisp_Object tail, frame;
       int count = SPECPDL_INDEX ();
+      /* 1 means that update_menu_bar has run its hooks
+        so any further calls to update_menu_bar shouldn't do so again.  */
+      int menu_bar_hooks_run = 0;
 
       record_unwind_save_match_data ();
 
@@ -8947,9 +9106,12 @@ prepare_menu_bars ()
            }
 
          GCPRO1 (tail);
-         update_menu_bar (f, 0);
+         menu_bar_hooks_run = update_menu_bar (f, 0, menu_bar_hooks_run);
 #ifdef HAVE_WINDOW_SYSTEM
          update_tool_bar (f, 0);
+#ifdef MAC_OS
+         mac_update_title_bar (f, 0);
+#endif
 #endif
          UNGCPRO;
        }
@@ -8959,9 +9121,12 @@ prepare_menu_bars ()
   else
     {
       struct frame *sf = SELECTED_FRAME ();
-      update_menu_bar (sf, 1);
+      update_menu_bar (sf, 1, 0);
 #ifdef HAVE_WINDOW_SYSTEM
       update_tool_bar (sf, 1);
+#ifdef MAC_OS
+      mac_update_title_bar (sf, 1);
+#endif
 #endif
     }
 
@@ -8977,12 +9142,18 @@ prepare_menu_bars ()
    before we start to fill in any display lines, because it can call
    eval.
 
-   If SAVE_MATCH_DATA is non-zero, we must save and restore it here.  */
+   If SAVE_MATCH_DATA is non-zero, we must save and restore it here.
 
-static void
-update_menu_bar (f, save_match_data)
+   If HOOKS_RUN is 1, that means a previous call to update_menu_bar
+   already ran the menu bar hooks for this redisplay, so there
+   is no need to run them again.  The return value is the
+   updated value of this flag, to pass to the next call.  */
+
+static int
+update_menu_bar (f, save_match_data, hooks_run)
      struct frame *f;
      int save_match_data;
+     int hooks_run;
 {
   Lisp_Object window;
   register struct window *w;
@@ -8991,7 +9162,7 @@ update_menu_bar (f, save_match_data)
      happen when, for instance, an activate-menubar-hook causes a
      redisplay.  */
   if (inhibit_menubar_update)
-    return;
+    return hooks_run;
 
   window = FRAME_SELECTED_WINDOW (f);
   w = XWINDOW (window);
@@ -9047,15 +9218,22 @@ update_menu_bar (f, save_match_data)
              specbind (Qoverriding_local_map, Qnil);
            }
 
-         /* Run the Lucid hook.  */
-         safe_run_hooks (Qactivate_menubar_hook);
+         if (!hooks_run)
+           {
+             /* Run the Lucid hook.  */
+             safe_run_hooks (Qactivate_menubar_hook);
+
+             /* If it has changed current-menubar from previous value,
+                really recompute the menu-bar from the value.  */
+             if (! NILP (Vlucid_menu_bar_dirty_flag))
+               call0 (Qrecompute_lucid_menubar);
 
-         /* If it has changed current-menubar from previous value,
-            really recompute the menu-bar from the value.  */
-         if (! NILP (Vlucid_menu_bar_dirty_flag))
-           call0 (Qrecompute_lucid_menubar);
+             safe_run_hooks (Qmenu_bar_update_hook);
 
-         safe_run_hooks (Qmenu_bar_update_hook);
+             hooks_run = 1;
+           }
+
+         XSETFRAME (Vmenu_updating_frame, f);
          FRAME_MENU_BAR_ITEMS (f) = menu_bar_items (FRAME_MENU_BAR_ITEMS (f));
 
          /* Redisplay the menu bar in case we changed it.  */
@@ -9084,6 +9262,8 @@ update_menu_bar (f, save_match_data)
          set_buffer_internal_1 (prev);
        }
     }
+
+  return hooks_run;
 }
 
 
@@ -9152,8 +9332,8 @@ x_cursor_to (vpos, hpos, y, x)
     {
       BLOCK_INPUT;
       display_and_set_cursor (w, 1, hpos, vpos, x, y);
-      if (rif->flush_display_optional)
-       rif->flush_display_optional (SELECTED_FRAME ());
+      if (FRAME_RIF (SELECTED_FRAME ())->flush_display_optional)
+       FRAME_RIF (SELECTED_FRAME ())->flush_display_optional (SELECTED_FRAME ());
       UNBLOCK_INPUT;
     }
 }
@@ -9248,7 +9428,8 @@ update_tool_bar (f, save_match_data)
                                          &new_n_tool_bar);
 
          /* Redisplay the tool-bar if we changed it.  */
-         if (NILP (Fequal (new_tool_bar, f->tool_bar_items)))
+         if (new_n_tool_bar != f->n_tool_bar_items
+             || NILP (Fequal (new_tool_bar, f->tool_bar_items)))
             {
               /* Redisplay that happens asynchronously due to an expose event
                  may access f->tool_bar_items.  Make sure we update both
@@ -9463,7 +9644,8 @@ display_tool_bar_line (it, height)
 
   while (it->current_x < max_x)
     {
-      int x_before, x, n_glyphs_before, i, nglyphs;
+      int x, n_glyphs_before, i, nglyphs;
+      struct it it_before;
 
       /* Get the next display element.  */
       if (!get_next_display_element (it))
@@ -9475,22 +9657,29 @@ display_tool_bar_line (it, height)
        }
 
       /* Produce glyphs.  */
-      x_before = it->current_x;
-      n_glyphs_before = it->glyph_row->used[TEXT_AREA];
+      n_glyphs_before = row->used[TEXT_AREA];
+      it_before = *it;
+
       PRODUCE_GLYPHS (it);
 
-      nglyphs = it->glyph_row->used[TEXT_AREA] - n_glyphs_before;
+      nglyphs = row->used[TEXT_AREA] - n_glyphs_before;
       i = 0;
-      x = x_before;
+      x = it_before.current_x;
       while (i < nglyphs)
        {
          struct glyph *glyph = row->glyphs[TEXT_AREA] + n_glyphs_before + i;
 
          if (x + glyph->pixel_width > max_x)
            {
-             /* Glyph doesn't fit on line.  */
-             it->glyph_row->used[TEXT_AREA] = n_glyphs_before + i;
-             it->current_x = x;
+             /* Glyph doesn't fit on line.  Backtrack.  */
+             row->used[TEXT_AREA] = n_glyphs_before;
+             *it = it_before;
+             /* If this is the only glyph on this line, it will never fit on the
+                toolbar, so skip it.   But ensure there is at least one glyph,
+                so we don't accidentally disable the tool-bar.  */
+             if (n_glyphs_before == 0
+                 && (it->vpos > 0 || IT_STRING_CHARPOS (*it) < it->end_charpos-1))
+               break;
              goto out;
            }
 
@@ -9509,9 +9698,16 @@ display_tool_bar_line (it, height)
  out:;
 
   row->displays_text_p = row->used[TEXT_AREA] != 0;
-  /* Use default face for the border below the tool bar.  */
-  if (!row->displays_text_p)
+
+  /* Use default face for the border below the tool bar.
+
+     FIXME: When auto-resize-tool-bars is grow-only, there is
+     no additional border below the possibly empty tool-bar lines.
+     So to make the extra empty lines look "normal", we have to
+     use the tool-bar face for the border too.  */
+  if (!row->displays_text_p && !EQ (Vauto_resize_tool_bars, Qgrow_only))
     it->face_id = DEFAULT_FACE_ID;
+
   extend_face_to_end_of_line (it);
   last = row->glyphs[TEXT_AREA] + row->used[TEXT_AREA] - 1;
   last->right_box_line_p = 1;
@@ -9521,6 +9717,8 @@ display_tool_bar_line (it, height)
   /* Make line the desired height and center it vertically.  */
   if ((height -= it->max_ascent + it->max_descent) > 0)
     {
+      /* Don't add more than one line height.  */
+      height %= FRAME_LINE_HEIGHT (it->f);
       it->max_ascent += height / 2;
       it->max_descent += (height + 1) / 2;
     }
@@ -9531,6 +9729,7 @@ display_tool_bar_line (it, height)
   if (!row->displays_text_p)
     {
       row->height = row->phys_height = it->last_visible_y - row->y;
+      row->visible_height = row->height;
       row->ascent = row->phys_ascent = 0;
       row->extra_line_spacing = 0;
     }
@@ -9547,6 +9746,11 @@ display_tool_bar_line (it, height)
 }
 
 
+/* Max tool-bar height.  */
+
+#define MAX_FRAME_TOOL_BAR_HEIGHT(f) \
+  ((FRAME_LINE_HEIGHT (f) * FRAME_LINES (f)))
+
 /* Value is the number of screen lines needed to make all tool-bar
    items of frame F visible.  The number of actual rows needed is
    returned in *N_ROWS if non-NULL.  */
@@ -9558,20 +9762,25 @@ tool_bar_lines_needed (f, n_rows)
 {
   struct window *w = XWINDOW (f->tool_bar_window);
   struct it it;
+  /* tool_bar_lines_needed is called from redisplay_tool_bar after building
+     the desired matrix, so use (unused) mode-line row as temporary row to
+     avoid destroying the first tool-bar row.  */
+  struct glyph_row *temp_row = MATRIX_MODE_LINE_ROW (w->desired_matrix);
 
   /* Initialize an iterator for iteration over
      F->desired_tool_bar_string in the tool-bar window of frame F.  */
-  init_iterator (&it, w, -1, -1, w->desired_matrix->rows, TOOL_BAR_FACE_ID);
+  init_iterator (&it, w, -1, -1, temp_row, TOOL_BAR_FACE_ID);
   it.first_visible_x = 0;
   it.last_visible_x = FRAME_TOTAL_COLS (f) * FRAME_COLUMN_WIDTH (f);
   reseat_to_string (&it, NULL, f->desired_tool_bar_string, 0, 0, 0, -1);
 
   while (!ITERATOR_AT_END_P (&it))
     {
-      it.glyph_row = w->desired_matrix->rows;
-      clear_glyph_row (it.glyph_row);
+      clear_glyph_row (temp_row);
+      it.glyph_row = temp_row;
       display_tool_bar_line (&it, -1);
     }
+  clear_glyph_row (temp_row);
 
   /* f->n_tool_bar_rows == 0 means "unknown"; -1 means no tool-bar.  */
   if (n_rows)
@@ -9623,7 +9832,6 @@ redisplay_tool_bar (f)
   struct window *w;
   struct it it;
   struct glyph_row *row;
-  int change_height_p = 0;
 
 #ifdef USE_GTK
   if (FRAME_EXTERNAL_TOOL_BAR (f))
@@ -9651,7 +9859,29 @@ redisplay_tool_bar (f)
   reseat_to_string (&it, NULL, f->desired_tool_bar_string, 0, 0, 0, -1);
 
   if (f->n_tool_bar_rows == 0)
-    (void)tool_bar_lines_needed (f, &f->n_tool_bar_rows);
+    {
+      int nlines;
+
+      if ((nlines = tool_bar_lines_needed (f, &f->n_tool_bar_rows),
+          nlines != WINDOW_TOTAL_LINES (w)))
+       {
+         extern Lisp_Object Qtool_bar_lines;
+         Lisp_Object frame;
+         int old_height = WINDOW_TOTAL_LINES (w);
+
+         XSETFRAME (frame, f);
+         Fmodify_frame_parameters (frame,
+                                   Fcons (Fcons (Qtool_bar_lines,
+                                                 make_number (nlines)),
+                                          Qnil));
+         if (WINDOW_TOTAL_LINES (w) != old_height)
+           {
+             clear_glyph_matrix (w->desired_matrix);
+             fonts_changed_p = 1;
+             return 1;
+           }
+       }
+    }
 
   /* Display as many lines as needed to display all tool-bar items.  */
 
@@ -9671,7 +9901,7 @@ redisplay_tool_bar (f)
        border = 0;
 
       rows = f->n_tool_bar_rows;
-      height = (it.last_visible_y - border) / rows;
+      height = max (1, (it.last_visible_y - border) / rows);
       extra = it.last_visible_y - border - height * rows;
 
       while (it.current_y < it.last_visible_y)
@@ -9696,19 +9926,22 @@ redisplay_tool_bar (f)
   w->desired_matrix->no_scrolling_p = 1;
   w->must_be_updated_p = 1;
 
-  if (auto_resize_tool_bars_p)
+  if (!NILP (Vauto_resize_tool_bars))
     {
-      int nlines;
+      int max_tool_bar_height = MAX_FRAME_TOOL_BAR_HEIGHT (f);
+      int change_height_p = 0;
 
       /* If we couldn't display everything, change the tool-bar's
-        height.  */
-      if (IT_STRING_CHARPOS (it) < it.end_charpos)
+        height if there is room for more.  */
+      if (IT_STRING_CHARPOS (it) < it.end_charpos
+         && it.current_y < max_tool_bar_height)
        change_height_p = 1;
 
+      row = it.glyph_row - 1;
+
       /* If there are blank lines at the end, except for a partially
         visible blank line at the end that is smaller than
         FRAME_LINE_HEIGHT, change the tool-bar's height.  */
-      row = it.glyph_row - 1;
       if (!row->displays_text_p
          && row->height >= FRAME_LINE_HEIGHT (f))
        change_height_p = 1;
@@ -9716,31 +9949,46 @@ redisplay_tool_bar (f)
       /* If row displays tool-bar items, but is partially visible,
         change the tool-bar's height.  */
       if (row->displays_text_p
-         && MATRIX_ROW_BOTTOM_Y (row) > it.last_visible_y)
+         && MATRIX_ROW_BOTTOM_Y (row) > it.last_visible_y
+         && MATRIX_ROW_BOTTOM_Y (row) < max_tool_bar_height)
        change_height_p = 1;
 
       /* Resize windows as needed by changing the `tool-bar-lines'
         frame parameter.  */
-      if (change_height_p
-         && (nlines = tool_bar_lines_needed (f, &f->n_tool_bar_rows),
-             nlines != WINDOW_TOTAL_LINES (w)))
+      if (change_height_p)
        {
          extern Lisp_Object Qtool_bar_lines;
          Lisp_Object frame;
          int old_height = WINDOW_TOTAL_LINES (w);
+         int nrows;
+         int nlines = tool_bar_lines_needed (f, &nrows);
 
-         XSETFRAME (frame, f);
-         clear_glyph_matrix (w->desired_matrix);
-         Fmodify_frame_parameters (frame,
-                                   Fcons (Fcons (Qtool_bar_lines,
-                                                 make_number (nlines)),
-                                          Qnil));
-         if (WINDOW_TOTAL_LINES (w) != old_height)
-           fonts_changed_p = 1;
+         change_height_p = ((EQ (Vauto_resize_tool_bars, Qgrow_only)
+                             && !f->minimize_tool_bar_window_p)
+                            ? (nlines > old_height)
+                            : (nlines != old_height));
+         f->minimize_tool_bar_window_p = 0;
+
+         if (change_height_p)
+           {
+             XSETFRAME (frame, f);
+             Fmodify_frame_parameters (frame,
+                                       Fcons (Fcons (Qtool_bar_lines,
+                                                     make_number (nlines)),
+                                              Qnil));
+             if (WINDOW_TOTAL_LINES (w) != old_height)
+               {
+                 clear_glyph_matrix (w->desired_matrix);
+                 f->n_tool_bar_rows = nrows;
+                 fonts_changed_p = 1;
+                 return 1;
+               }
+           }
        }
     }
 
-  return change_height_p;
+  f->minimize_tool_bar_window_p = 0;
+  return 0;
 }
 
 
@@ -10537,6 +10785,8 @@ select_frame_for_redisplay (frame)
   Lisp_Object tail, sym, val;
   Lisp_Object old = selected_frame;
 
+  xassert (FRAMEP (frame) && FRAME_LIVE_P (XFRAME (frame)));
+
   selected_frame = frame;
 
   for (tail = XFRAME (frame)->param_alist; CONSP (tail); tail = XCDR (tail))
@@ -10585,13 +10835,13 @@ redisplay_internal (preserve_echo_area)
      int preserve_echo_area;
 {
   struct window *w = XWINDOW (selected_window);
-  struct frame *f = XFRAME (w->frame);
+  struct frame *f;
   int pause;
   int must_finish = 0;
   struct text_pos tlbufpos, tlendpos;
   int number_of_visible_frames;
   int count;
-  struct frame *sf = SELECTED_FRAME ();
+  struct frame *sf;
   int polling_stopped_here = 0;
 
   /* Non-zero means redisplay has to consider all windows on all
@@ -10604,8 +10854,16 @@ redisplay_internal (preserve_echo_area)
      initialized, or redisplay is explicitly turned off by setting
      Vinhibit_redisplay.  */
   if (noninteractive
-      || !NILP (Vinhibit_redisplay)
-      || !f->glyphs_initialized_p)
+      || !NILP (Vinhibit_redisplay))
+    return;
+
+  /* Don't examine these until after testing Vinhibit_redisplay.
+     When Emacs is shutting down, perhaps because its connection to
+     X has dropped, we should not look at them at all.  */
+  f = XFRAME (w->frame);
+  sf = SELECTED_FRAME ();
+
+  if (!f->glyphs_initialized_p)
     return;
 
   /* The flag redisplay_performed_directly_p is set by
@@ -10618,7 +10876,7 @@ redisplay_internal (preserve_echo_area)
        return;
     }
 
-#if defined (USE_X_TOOLKIT) || defined (USE_GTK)
+#if defined (USE_X_TOOLKIT) || defined (USE_GTK) || defined (MAC_OS)
   if (popup_activated ())
     return;
 #endif
@@ -10666,17 +10924,16 @@ redisplay_internal (preserve_echo_area)
   if (face_change_count)
     ++windows_or_buffers_changed;
 
-  if (! FRAME_WINDOW_P (sf)
-      && previous_terminal_frame != sf)
+  if (FRAME_TERMCAP_P (sf)
+      && FRAME_TTY (sf)->previous_frame != sf)
     {
-      /* Since frames on an ASCII terminal share the same display
-        area, displaying a different frame means redisplay the whole
-        thing.  */
+      /* Since frames on a single ASCII terminal share the same
+        display area, displaying a different frame means redisplay
+        the whole thing.  */
       windows_or_buffers_changed++;
       SET_FRAME_GARBAGED (sf);
-      XSETFRAME (Vterminal_frame, sf);
+      FRAME_TTY (sf)->previous_frame = sf;
     }
-  previous_terminal_frame = sf;
 
   /* Set the visible flags for all frames.  Do this before checking
      for resized or garbaged frames; they want to know if their frames
@@ -10698,6 +10955,7 @@ redisplay_internal (preserve_echo_area)
       }
   }
 
+  
   /* Notice any pending interrupt request to change frame size.  */
   do_pending_window_change (1);
 
@@ -11053,7 +11311,7 @@ redisplay_internal (preserve_echo_area)
        {
          struct frame *f = XFRAME (frame);
 
-         if (FRAME_WINDOW_P (f) || f == sf)
+         if (FRAME_WINDOW_P (f) || FRAME_TERMCAP_P (f) || f == sf)
            {
              if (! EQ (frame, selected_frame))
                /* Select the frame, for the sake of frame-local
@@ -11062,16 +11320,16 @@ redisplay_internal (preserve_echo_area)
 
              /* Mark all the scroll bars to be removed; we'll redeem
                 the ones we want when we redisplay their windows.  */
-             if (condemn_scroll_bars_hook)
-               condemn_scroll_bars_hook (f);
+             if (FRAME_TERMINAL (f)->condemn_scroll_bars_hook)
+               FRAME_TERMINAL (f)->condemn_scroll_bars_hook (f);
 
              if (FRAME_VISIBLE_P (f) && !FRAME_OBSCURED_P (f))
                redisplay_windows (FRAME_ROOT_WINDOW (f));
 
              /* Any scroll bars which redisplay_windows should have
                 nuked should now go away.  */
-             if (judge_scroll_bars_hook)
-               judge_scroll_bars_hook (f);
+             if (FRAME_TERMINAL (f)->judge_scroll_bars_hook)
+               FRAME_TERMINAL (f)->judge_scroll_bars_hook (f);
 
              /* If fonts changed, display again.  */
              /* ??? rms: I suspect it is a mistake to jump all the way
@@ -11118,12 +11376,12 @@ redisplay_internal (preserve_echo_area)
          FOR_EACH_FRAME (tail, frame)
            {
              struct frame *f = XFRAME (frame);
-             if (f->updated_p)
-               {
-                 mark_window_display_accurate (f->root_window, 1);
-                 if (frame_up_to_date_hook)
-                   frame_up_to_date_hook (f);
-               }
+              if (f->updated_p)
+                {
+                  mark_window_display_accurate (f->root_window, 1);
+                  if (FRAME_TERMINAL (f)->frame_up_to_date_hook)
+                    FRAME_TERMINAL (f)->frame_up_to_date_hook (f);
+                }
            }
        }
     }
@@ -11208,8 +11466,8 @@ redisplay_internal (preserve_echo_area)
          /* Say overlay arrows are up to date.  */
          update_overlay_arrows (1);
 
-         if (frame_up_to_date_hook != 0)
-           frame_up_to_date_hook (sf);
+         if (FRAME_TERMINAL (sf)->frame_up_to_date_hook != 0)
+           FRAME_TERMINAL (sf)->frame_up_to_date_hook (sf);
        }
 
       update_mode_lines = 0;
@@ -11319,8 +11577,9 @@ redisplay_preserve_echo_area (from_where)
   else
     redisplay_internal (1);
 
-  if (rif != NULL && rif->flush_display_optional)
-    rif->flush_display_optional (NULL);
+  if (FRAME_RIF (SELECTED_FRAME ()) != NULL
+      && FRAME_RIF (SELECTED_FRAME ())->flush_display_optional)
+    FRAME_RIF (SELECTED_FRAME ())->flush_display_optional (NULL);
 }
 
 
@@ -11328,7 +11587,8 @@ redisplay_preserve_echo_area (from_where)
    redisplay_internal.  Reset redisplaying_p to the value it had
    before redisplay_internal was called, and clear
    prevent_freeing_realized_faces_p.  It also selects the previously
-   selected frame.  */
+   selected frame, unless it has been deleted (by an X connection
+   failure during redisplay, for example).  */
 
 static Lisp_Object
 unwind_redisplay (val)
@@ -11339,7 +11599,8 @@ unwind_redisplay (val)
   old_redisplaying_p = XCAR (val);
   redisplaying_p = XFASTINT (old_redisplaying_p);
   old_frame = XCDR (val);
-  if (! EQ (old_frame, selected_frame))
+  if (! EQ (old_frame, selected_frame)
+      && FRAME_LIVE_P (XFRAME (old_frame)))
     select_frame_for_redisplay (old_frame);
   return Qnil;
 }
@@ -11555,9 +11816,11 @@ redisplay_window_1 (window)
 
 /* Set cursor position of W.  PT is assumed to be displayed in ROW.
    DELTA is the number of bytes by which positions recorded in ROW
-   differ from current buffer positions.  */
+   differ from current buffer positions.
 
-void
+   Return 0 if cursor is not on this row.  1 otherwise.  */
+
+int
 set_cursor_from_row (w, row, matrix, delta, delta_bytes, dy, dvpos)
      struct window *w;
      struct glyph_row *row;
@@ -11604,7 +11867,7 @@ set_cursor_from_row (w, row, matrix, delta, delta_bytes, dy, dvpos)
          x += glyph->pixel_width;
          ++glyph;
          if (cursor_from_overlay_pos
-             && last_pos > cursor_from_overlay_pos)
+             && last_pos >= cursor_from_overlay_pos)
            {
              cursor_from_overlay_pos = 0;
              cursor = 0;
@@ -11612,16 +11875,21 @@ set_cursor_from_row (w, row, matrix, delta, delta_bytes, dy, dvpos)
        }
       else
        {
-         string_before_pos = last_pos;
-         string_start = glyph;
-         string_start_x = x;
+         if (string_start == NULL)
+           {
+             string_before_pos = last_pos;
+             string_start = glyph;
+             string_start_x = x;
+           }
          /* Skip all glyphs from string.  */
          do
            {
+             Lisp_Object cprop;
              int pos;
              if ((cursor == NULL || glyph > cursor)
-                 && !NILP (Fget_char_property (make_number ((glyph)->charpos),
-                                               Qcursor, (glyph)->object))
+                 && (cprop = Fget_char_property (make_number ((glyph)->charpos),
+                                                 Qcursor, (glyph)->object),
+                     !NILP (cprop))
                  && (pos = string_buffer_position (w, glyph->object,
                                                    string_before_pos),
                      (pos == 0   /* From overlay */
@@ -11632,14 +11900,15 @@ set_cursor_from_row (w, row, matrix, delta, delta_bytes, dy, dvpos)
                     Add 1 to last_pos so that if point corresponds to the
                     glyph right after the overlay, we still use a 'cursor'
                     property found in that overlay.  */
-                 cursor_from_overlay_pos = pos == 0 ? last_pos+1 : 0;
+                 cursor_from_overlay_pos = (pos ? 0 : last_pos
+                                            + (INTEGERP (cprop) ? XINT (cprop) : 0));
                  cursor = glyph;
                  cursor_x = x;
                }
              x += glyph->pixel_width;
              ++glyph;
            }
-         while (glyph < end && STRINGP (glyph->object));
+         while (glyph < end && EQ (glyph->object, string_start->object));
        }
     }
 
@@ -11669,25 +11938,25 @@ set_cursor_from_row (w, row, matrix, delta, delta_bytes, dy, dvpos)
         glyph on point by scanning from string_start again.  */
       Lisp_Object limit;
       Lisp_Object string;
+      struct glyph *stop = glyph;
       int pos;
 
       limit = make_number (pt_old + 1);
-      end = glyph;
       glyph = string_start;
       x = string_start_x;
       string = glyph->object;
       pos = string_buffer_position (w, string, string_before_pos);
       /* If STRING is from overlay, LAST_POS == 0.  We skip such glyphs
         because we always put cursor after overlay strings.  */
-      while (pos == 0 && glyph < end)
+      while (pos == 0 && glyph < stop)
        {
          string = glyph->object;
-         SKIP_GLYPHS (glyph, end, x, EQ (glyph->object, string));
-         if (glyph < end)
+         SKIP_GLYPHS (glyph, stop, x, EQ (glyph->object, string));
+         if (glyph < stop)
            pos = string_buffer_position (w, glyph->object, string_before_pos);
        }
 
-      while (glyph < end)
+      while (glyph < stop)
        {
          pos = XINT (Fnext_single_char_property_change
                      (make_number (pos), Qdisplay, Qnil, limit));
@@ -11695,15 +11964,20 @@ set_cursor_from_row (w, row, matrix, delta, delta_bytes, dy, dvpos)
            break;
          /* Skip glyphs from the same string.  */
          string = glyph->object;
-         SKIP_GLYPHS (glyph, end, x, EQ (glyph->object, string));
+         SKIP_GLYPHS (glyph, stop, x, EQ (glyph->object, string));
          /* Skip glyphs from an overlay.  */
-         while (glyph < end
+         while (glyph < stop
                 && ! string_buffer_position (w, glyph->object, pos))
            {
              string = glyph->object;
-             SKIP_GLYPHS (glyph, end, x, EQ (glyph->object, string));
+             SKIP_GLYPHS (glyph, stop, x, EQ (glyph->object, string));
            }
        }
+
+      /* If we reached the end of the line, and end was from a string,
+        cursor is not on this line.  */
+      if (glyph == end && row->continued_p)
+       return 0;
     }
 
   w->cursor.hpos = glyph - row->glyphs[TEXT_AREA];
@@ -11737,6 +12011,8 @@ set_cursor_from_row (w, row, matrix, delta, delta_bytes, dy, dvpos)
       else
        CHARPOS (this_line_start_pos) = 0;
     }
+
+  return 1;
 }
 
 
@@ -11811,7 +12087,8 @@ cursor_row_fully_visible_p (w, force_p, current_matrix_p)
   window_height = window_box_height (w);
   if (row->height >= window_height)
     {
-      if (!force_p || MINI_WINDOW_P (w) || w->vscroll)
+      if (!force_p || MINI_WINDOW_P (w)
+         || w->vscroll || w->cursor.vpos == 0)
        return 1;
     }
   return 0;
@@ -12420,8 +12697,18 @@ try_cursor_movement (window, startp, scroll_step)
            rc = CURSOR_MOVEMENT_MUST_SCROLL;
          else
            {
-             set_cursor_from_row (w, row, w->current_matrix, 0, 0, 0, 0);
-             rc = CURSOR_MOVEMENT_SUCCESS;
+             do
+               {
+                 if (set_cursor_from_row (w, row, w->current_matrix, 0, 0, 0, 0))
+                   {
+                     rc = CURSOR_MOVEMENT_SUCCESS;
+                     break;
+                   }
+                 ++row;
+               }
+             while (MATRIX_ROW_BOTTOM_Y (row) < last_y
+                    && MATRIX_ROW_START_CHARPOS (row) == PT
+                    && cursor_row_p (w, row));
            }
        }
     }
@@ -12462,7 +12749,9 @@ set_vertical_scroll_bar (w)
     start = end = whole = 0;
 
   /* Indicate what this scroll bar ought to be displaying now.  */
-  set_vertical_scroll_bar_hook (w, end - start, whole, start);
+  if (FRAME_TERMINAL (XFRAME (w->frame))->set_vertical_scroll_bar_hook)
+    (*FRAME_TERMINAL (XFRAME (w->frame))->set_vertical_scroll_bar_hook)
+      (w, end - start, whole, start);
 }
 
 
@@ -12682,8 +12971,6 @@ redisplay_window (window, just_this_one_p)
       /* IT may overshoot PT if text at PT is invisible.  */
       else if (IT_CHARPOS (it) > PT && CHARPOS (startp) <= PT)
        w->force_start = Qt;
-
-
     }
 
   /* Handle case where place to start displaying has been specified,
@@ -12853,6 +13140,43 @@ redisplay_window (window, just_this_one_p)
               || (XFASTINT (w->last_modified) >= MODIFF
                   && XFASTINT (w->last_overlay_modified) >= OVERLAY_MODIFF)))
     {
+
+      /* If first window line is a continuation line, and window start
+        is inside the modified region, but the first change is before
+        current window start, we must select a new window start.
+
+        However, if this is the result of a down-mouse event (e.g. by
+        extending the mouse-drag-overlay), we don't want to select a
+        new window start, since that would change the position under
+        the mouse, resulting in an unwanted mouse-movement rather
+        than a simple mouse-click.  */
+      if (NILP (w->start_at_line_beg)
+         && NILP (do_mouse_tracking)
+         && CHARPOS (startp) > BEGV)
+       {
+         /* Make sure beg_unchanged and end_unchanged are up to date.
+            Do it only if buffer has really changed.  This may or may
+            not have been done by try_window_id (see which) already. */
+         if (MODIFF > SAVE_MODIFF
+             /* This seems to happen sometimes after saving a buffer.  */
+             || BEG_UNCHANGED + END_UNCHANGED > Z_BYTE)
+           {
+             if (GPT - BEG < BEG_UNCHANGED)
+               BEG_UNCHANGED = GPT - BEG;
+             if (Z - GPT < END_UNCHANGED)
+               END_UNCHANGED = Z - GPT;
+           }
+
+         if (CHARPOS (startp) > BEG + BEG_UNCHANGED
+             && CHARPOS (startp) <= Z - END_UNCHANGED)
+           {
+             /* There doesn't seems to be a simple way to find a new
+                window start that is near the old window start, so
+                we just recenter.  */
+             goto recenter;
+           }
+       }
+
 #if GLYPH_DEBUG
       debug_method_add (w, "same window start");
 #endif
@@ -13154,17 +13478,22 @@ redisplay_window (window, just_this_one_p)
         display_menu_bar (w);
 
 #ifdef HAVE_WINDOW_SYSTEM
+      if (FRAME_WINDOW_P (f))
+        {
 #ifdef USE_GTK
-      redisplay_tool_bar_p = FRAME_EXTERNAL_TOOL_BAR (f);
+          redisplay_tool_bar_p = FRAME_EXTERNAL_TOOL_BAR (f);
 #else
-      redisplay_tool_bar_p = WINDOWP (f->tool_bar_window)
-        && (FRAME_TOOL_BAR_LINES (f) > 0
-            || auto_resize_tool_bars_p);
-
+          redisplay_tool_bar_p = WINDOWP (f->tool_bar_window)
+            && (FRAME_TOOL_BAR_LINES (f) > 0
+                || !NILP (Vauto_resize_tool_bars));
 #endif
 
-      if (redisplay_tool_bar_p)
-        redisplay_tool_bar (f);
+          if (redisplay_tool_bar_p && redisplay_tool_bar (f))
+           {
+             extern int ignore_mouse_drag_p;
+             ignore_mouse_drag_p = 1;
+           }
+        }
 #endif
     }
 
@@ -13198,7 +13527,8 @@ redisplay_window (window, just_this_one_p)
 
       /* Note that we actually used the scroll bar attached to this
         window, so it shouldn't be deleted at the end of redisplay.  */
-      redeem_scroll_bar_hook (w);
+      if (FRAME_TERMINAL (f)->redeem_scroll_bar_hook)
+        (*FRAME_TERMINAL (f)->redeem_scroll_bar_hook) (w);
     }
 
   /* Restore current_buffer and value of point in it.  */
@@ -13227,6 +13557,7 @@ try_window (window, pos, check_margins)
   struct window *w = XWINDOW (window);
   struct it it;
   struct glyph_row *last_text_row = NULL;
+  struct frame *f = XFRAME (w->frame);
 
   /* Make POS the new window start.  */
   set_marker_both (w->start, Qnil, CHARPOS (pos), BYTEPOS (pos));
@@ -13257,7 +13588,8 @@ try_window (window, pos, check_margins)
       this_scroll_margin = min (this_scroll_margin, WINDOW_TOTAL_LINES (w) / 4);
       this_scroll_margin *= FRAME_LINE_HEIGHT (it.f);
 
-      if ((w->cursor.y < this_scroll_margin
+      if ((w->cursor.y >= 0    /* not vscrolled */
+          && w->cursor.y < this_scroll_margin
           && CHARPOS (pos) > BEGV
           && IT_CHARPOS (it) < ZV)
          /* rms: considering make_cursor_line_fully_visible_p here
@@ -13462,10 +13794,10 @@ try_window_reusing_current_matrix (w)
          if (run.height > 0 && run.current_y != run.desired_y)
            {
              update_begin (f);
-             rif->update_window_begin_hook (w);
-             rif->clear_window_mouse_face (w);
-             rif->scroll_run_hook (w, &run);
-             rif->update_window_end_hook (w, 0, 0);
+             FRAME_RIF (f)->update_window_begin_hook (w);
+             FRAME_RIF (f)->clear_window_mouse_face (w);
+             FRAME_RIF (f)->scroll_run_hook (w, &run);
+             FRAME_RIF (f)->update_window_end_hook (w, 0, 0);
              update_end (f);
            }
 
@@ -13634,10 +13966,10 @@ try_window_reusing_current_matrix (w)
       if (run.height)
        {
          update_begin (f);
-         rif->update_window_begin_hook (w);
-         rif->clear_window_mouse_face (w);
-         rif->scroll_run_hook (w, &run);
-         rif->update_window_end_hook (w, 0, 0);
+         FRAME_RIF (f)->update_window_begin_hook (w);
+         FRAME_RIF (f)->clear_window_mouse_face (w);
+         FRAME_RIF (f)->scroll_run_hook (w, &run);
+         FRAME_RIF (f)->update_window_end_hook (w, 0, 0);
          update_end (f);
        }
 
@@ -14087,7 +14419,7 @@ try_window_id (w)
 
   /* Window must either use window-based redisplay or be full width.  */
   if (!FRAME_WINDOW_P (f)
-      && (!line_ins_del_ok
+      && (!FRAME_LINE_INS_DEL_OK (f)
          || !WINDOW_FULL_WIDTH_P (w)))
     GIVE_UP (4);
 
@@ -14496,10 +14828,10 @@ try_window_id (w)
 
       if (FRAME_WINDOW_P (f))
        {
-         rif->update_window_begin_hook (w);
-         rif->clear_window_mouse_face (w);
-         rif->scroll_run_hook (w, &run);
-         rif->update_window_end_hook (w, 0, 0);
+         FRAME_RIF (f)->update_window_begin_hook (w);
+         FRAME_RIF (f)->clear_window_mouse_face (w);
+         FRAME_RIF (f)->scroll_run_hook (w, &run);
+         FRAME_RIF (f)->update_window_end_hook (w, 0, 0);
        }
       else
        {
@@ -14517,36 +14849,36 @@ try_window_id (w)
            {
              /* Scroll last_unchanged_at_beg_row to the end of the
                 window down dvpos lines.  */
-             set_terminal_window (end);
+             set_terminal_window (f, end);
 
              /* On dumb terminals delete dvpos lines at the end
                 before inserting dvpos empty lines.  */
-             if (!scroll_region_ok)
-               ins_del_lines (end - dvpos, -dvpos);
+             if (!FRAME_SCROLL_REGION_OK (f))
+               ins_del_lines (f, end - dvpos, -dvpos);
 
              /* Insert dvpos empty lines in front of
                  last_unchanged_at_beg_row.  */
-             ins_del_lines (from, dvpos);
+             ins_del_lines (f, from, dvpos);
            }
          else if (dvpos < 0)
            {
              /* Scroll up last_unchanged_at_beg_vpos to the end of
                 the window to last_unchanged_at_beg_vpos - |dvpos|.  */
-             set_terminal_window (end);
+             set_terminal_window (f, end);
 
              /* Delete dvpos lines in front of
                 last_unchanged_at_beg_vpos.  ins_del_lines will set
                 the cursor to the given vpos and emit |dvpos| delete
                 line sequences.  */
-             ins_del_lines (from + dvpos, dvpos);
+             ins_del_lines (f, from + dvpos, dvpos);
 
              /* On a dumb terminal insert dvpos empty lines at the
                  end.  */
-             if (!scroll_region_ok)
-               ins_del_lines (end + dvpos, -dvpos);
+             if (!FRAME_SCROLL_REGION_OK (f))
+               ins_del_lines (f, end + dvpos, -dvpos);
            }
 
-         set_terminal_window (0);
+         set_terminal_window (f, 0);
        }
 
       update_end (f);
@@ -14578,7 +14910,7 @@ try_window_id (w)
     sync_frame_with_window_matrix_rows (w);
 
   /* Adjust buffer positions in reused rows.  */
-  if (delta)
+  if (delta || delta_bytes)
     increment_matrix_positions (current_matrix,
                                first_unchanged_at_end_vpos + dvpos,
                                bottom_vpos, delta, delta_bytes);
@@ -14846,6 +15178,25 @@ dump_glyph (row, glyph, area)
               glyph->left_box_line_p,
               glyph->right_box_line_p);
     }
+  else if (glyph->type == COMPOSITE_GLYPH)
+    {
+      fprintf (stderr,
+              "  %5d %4c %6d %c %3d 0x%05x %c %4d %1.1d%1.1d\n",
+              glyph - row->glyphs[TEXT_AREA],
+              '+',
+              glyph->charpos,
+              (BUFFERP (glyph->object)
+               ? 'B'
+               : (STRINGP (glyph->object)
+                  ? 'S'
+                  : '-')),
+              glyph->pixel_width,
+              glyph->u.cmp_id,
+              '.',
+              glyph->face_id,
+              glyph->left_box_line_p,
+              glyph->right_box_line_p);
+    }
 }
 
 
@@ -14861,7 +15212,7 @@ dump_glyph_row (row, vpos, glyphs)
 {
   if (glyphs != 1)
     {
-      fprintf (stderr, "Row Start   End Used oEI><\\CTZFesm     X    Y    W    H    V    A    P\n");
+      fprintf (stderr, "Row Start   End Used oE><\\CTZFesm     X    Y    W    H    V    A    P\n");
       fprintf (stderr, "======================================================================\n");
 
       fprintf (stderr, "%3d %5d %5d %4d %1.1d%1.1d%1.1d%1.1d\
@@ -16289,6 +16640,9 @@ display_mode_line (w, face_id, format)
   int count = SPECPDL_INDEX ();
 
   init_iterator (&it, w, -1, -1, NULL, face_id);
+  /* Don't extend on a previously drawn mode-line.
+     This may happen if called from pos_visible_p.  */
+  it.glyph_row->enabled_p = 0;
   prepare_desired_row (it.glyph_row);
 
   it.glyph_row->mode_line_p = 1;
@@ -16305,9 +16659,10 @@ display_mode_line (w, face_id, format)
   /* Temporarily make frame's keyboard the current kboard so that
      kboard-local variables in the mode_line_format will get the right
      values.  */
-  push_frame_kboard (it.f);
+  push_kboard (FRAME_KBOARD (it.f));
+  record_unwind_save_match_data ();
   display_mode_element (&it, 0, 0, 0, format, Qnil, 0);
-  pop_frame_kboard ();
+  pop_kboard ();
 
   unbind_to (count, Qnil);
 
@@ -16946,9 +17301,9 @@ for details) to use.
 
 Optional second arg FACE specifies the face property to put
 on all characters for which no face is specified.
-t means whatever face the window's mode line currently uses
+The value t means whatever face the window's mode line currently uses
 \(either `mode-line' or `mode-line-inactive', depending).
-nil means the default is no face property.
+A value of nil means the default is no face property.
 If FACE is an integer, the value string has no text properties.
 
 Optional third and fourth args WINDOW and BUFFER specify the window
@@ -17022,9 +17377,9 @@ are the selected window and the window's buffer).  */)
        = (NILP (face) ? Qnil : Fcons (Qface, Fcons (face, Qnil)));
     }
 
-  push_frame_kboard (it.f);
+  push_kboard (FRAME_KBOARD (it.f));
   display_mode_element (&it, 0, 0, 0, format, Qnil, 0);
-  pop_frame_kboard ();
+  pop_kboard ();
 
   if (no_props)
     {
@@ -17077,7 +17432,7 @@ pint2str (buf, width, d)
 
 /* Write a null-terminated, right justified decimal and "human
    readable" representation of the nonnegative integer D to BUF using
-   a minimal field width WIDTH.         D should be smaller than 999.5e24. */
+   a minimal field width WIDTH.  D should be smaller than 999.5e24. */
 
 static const char power_letter[] =
   {
@@ -17377,12 +17732,20 @@ decode_mode_spec (w, c, field_width, precision, multibyte)
       break;
 
     case 'c':
-      {
-       int col = (int) current_column (); /* iftc */
-       w->column_number_displayed = make_number (col);
-       pint2str (decode_mode_spec_buf, field_width, col);
-       return decode_mode_spec_buf;
-      }
+      /* %c and %l are ignored in `frame-title-format'.
+         (In redisplay_internal, the frame title is drawn _before_ the
+         windows are updated, so the stuff which depends on actual
+         window contents (such as %l) may fail to render properly, or
+         even crash emacs.)  */
+      if (mode_line_target == MODE_LINE_TITLE)
+       return "";
+      else
+       {
+         int col = (int) current_column (); /* iftc */
+         w->column_number_displayed = make_number (col);
+         pint2str (decode_mode_spec_buf, field_width, col);
+         return decode_mode_spec_buf;
+       }
 
     case 'e':
 #ifndef SYSTEM_MALLOC
@@ -17424,11 +17787,16 @@ decode_mode_spec (w, c, field_width, precision, multibyte)
 
     case 'l':
       {
-       int startpos = XMARKER (w->start)->charpos;
-       int startpos_byte = marker_byte_position (w->start);
-       int line, linepos, linepos_byte, topline;
-       int nlines, junk;
-       int height = WINDOW_TOTAL_LINES (w);
+       int startpos, startpos_byte, line, linepos, linepos_byte;
+       int topline, nlines, junk, height;
+
+       /* %c and %l are ignored in `frame-title-format'.  */
+       if (mode_line_target == MODE_LINE_TITLE)
+         return "";
+
+       startpos = XMARKER (w->start)->charpos;
+       startpos_byte = marker_byte_position (w->start);
+       height = WINDOW_TOTAL_LINES (w);
 
        /* If we decided that this buffer isn't suitable for line numbers,
           don't forget that too fast.  */
@@ -17635,8 +18003,8 @@ decode_mode_spec (w, c, field_width, precision, multibyte)
          {
            /* No need to mention EOL here--the terminal never needs
               to do EOL conversion.  */
-           p = decode_mode_spec_coding (keyboard_coding.symbol, p, 0);
-           p = decode_mode_spec_coding (terminal_coding.symbol, p, 0);
+           p = decode_mode_spec_coding (FRAME_KEYBOARD_CODING (f)->symbol, p, 0);
+           p = decode_mode_spec_coding (FRAME_TERMINAL_CODING (f)->symbol, p, 0);
          }
        p = decode_mode_spec_coding (b->buffer_file_coding_system,
                                     p, eol_flag);
@@ -18128,6 +18496,8 @@ calc_pixel_width_or_height (res, it, prop, font, width_p, align_to)
   if (NILP (prop))
     return OK_PIXELS (0);
 
+  xassert (FRAME_LIVE_P (it->f));
+
   if (SYMBOLP (prop))
     {
       if (SCHARS (SYMBOL_NAME (prop)) == 2)
@@ -18244,7 +18614,8 @@ calc_pixel_width_or_height (res, it, prop, font, width_p, align_to)
       if (SYMBOLP (car))
        {
 #ifdef HAVE_WINDOW_SYSTEM
-         if (valid_image_p (prop))
+         if (FRAME_WINDOW_P (it->f)
+             && valid_image_p (prop))
            {
              int id = lookup_image (it->f, prop);
              struct image *img = IMAGE_FROM_ID (it->f, id);
@@ -18461,8 +18832,7 @@ get_glyph_face_and_encoding (f, glyph, char2b, two_byte_p)
         sure to use a face suitable for unibyte.  */
       STORE_XCHAR2B (char2b, 0, glyph->u.ch);
     }
-  else if (glyph->u.ch < 128
-          && glyph->face_id < BASIC_FACE_ID_SENTINEL)
+  else if (glyph->u.ch < 128)
     {
       /* Case of ASCII in a face known to fit ASCII.  */
       STORE_XCHAR2B (char2b, 0, glyph->u.ch);
@@ -18486,7 +18856,7 @@ get_glyph_face_and_encoding (f, glyph, char2b, two_byte_p)
            = FONT_INFO_FROM_ID (f, face->font_info_id);
          if (font_info)
            glyph->font_type
-             = rif->encode_char (glyph->u.ch, char2b, font_info, two_byte_p);
+             = FRAME_RIF (f)->encode_char (glyph->u.ch, char2b, font_info, two_byte_p);
        }
     }
 
@@ -18673,6 +19043,7 @@ fill_stretch_glyph_string (s, row, area, start, end)
   s->font = s->face->font;
   s->font_info = FONT_INFO_FROM_ID (s->f, s->face->font_info_id);
   s->width = glyph->pixel_width;
+  s->nchars = 1;
   voffset = glyph->voffset;
 
   for (++glyph;
@@ -18718,7 +19089,7 @@ x_get_glyph_overhangs (glyph, f, left, right)
       font = face->font;
       font_info = FONT_INFO_FROM_ID (f, face->font_info_id);
       if (font  /* ++KFS: Should this be font_info ?  */
-         && (pcm = rif->per_char_metric (font, &char2b, glyph->font_type)))
+         && (pcm = FRAME_RIF (f)->per_char_metric (font, &char2b, glyph->font_type)))
        {
          if (pcm->rbearing > pcm->width)
            *right = pcm->rbearing - pcm->width;
@@ -18863,7 +19234,7 @@ get_char_face_and_encoding (f, c, face_id, char2b, multibyte_p, display_p)
       face_id = FACE_FOR_CHAR (f, face, c);
       face = FACE_FROM_ID (f, face_id);
     }
-  else if (c < 128 && face_id < BASIC_FACE_ID_SENTINEL)
+  else if (c < 128)
     {
       /* Case of ASCII in a face known to fit ASCII.  */
       STORE_XCHAR2B (char2b, 0, c);
@@ -18886,7 +19257,7 @@ get_char_face_and_encoding (f, c, face_id, char2b, multibyte_p, display_p)
          struct font_info *font_info
            = FONT_INFO_FROM_ID (f, face->font_info_id);
          if (font_info)
-           rif->encode_char (c, char2b, font_info, 0);
+           FRAME_RIF (f)->encode_char (c, char2b, font_info, 0);
        }
     }
 
@@ -18949,8 +19320,8 @@ compute_overhangs_and_x (s, x, backward_p)
     {
       while (s)
        {
-         if (rif->compute_glyph_string_overhangs)
-           rif->compute_glyph_string_overhangs (s);
+         if (FRAME_RIF (s->f)->compute_glyph_string_overhangs)
+           FRAME_RIF (s->f)->compute_glyph_string_overhangs (s);
          x -= s->width;
          s->x = x;
          s = s->prev;
@@ -18960,8 +19331,8 @@ compute_overhangs_and_x (s, x, backward_p)
     {
       while (s)
        {
-         if (rif->compute_glyph_string_overhangs)
-           rif->compute_glyph_string_overhangs (s);
+         if (FRAME_RIF (s->f)->compute_glyph_string_overhangs)
+           FRAME_RIF (s->f)->compute_glyph_string_overhangs (s);
          s->x = x;
          x += s->width;
          s = s->next;
@@ -19249,9 +19620,9 @@ draw_glyphs (w, x, row, area, start, end, hl, overlaps)
       struct glyph_string *h, *t;
 
       /* Compute overhangs for all glyph strings.  */
-      if (rif->compute_glyph_string_overhangs)
+      if (FRAME_RIF (f)->compute_glyph_string_overhangs)
        for (s = head; s; s = s->next)
-         rif->compute_glyph_string_overhangs (s);
+         FRAME_RIF (f)->compute_glyph_string_overhangs (s);
 
       /* Prepend glyph strings for glyphs in front of the first glyph
         string that are overwritten because of the first glyph
@@ -19329,7 +19700,7 @@ draw_glyphs (w, x, row, area, start, end, hl, overlaps)
 
   /* Draw all strings.  */
   for (s = head; s; s = s->next)
-    rif->draw_glyph_string (s);
+    FRAME_RIF (f)->draw_glyph_string (s);
 
   if (area == TEXT_AREA
       && !row->full_width_p
@@ -19487,7 +19858,7 @@ produce_image_glyph (it)
 {
   struct image *img;
   struct face *face;
-  int glyph_ascent;
+  int glyph_ascent, crop;
   struct glyph_slice slice;
 
   xassert (it->what == IT_IMAGE);
@@ -19595,6 +19966,15 @@ produce_image_glyph (it)
 
   take_vertical_position_into_account (it);
 
+  /* Automatically crop wide image glyphs at right edge so we can
+     draw the cursor on same display row.  */
+  if ((crop = it->pixel_width - (it->last_visible_x - it->current_x), crop > 0)
+      && (it->hpos == 0 || it->pixel_width > it->last_visible_x / 4))
+    {
+      it->pixel_width -= crop;
+      slice.width -= crop;
+    }
+
   if (it->glyph_row)
     {
       struct glyph *glyph;
@@ -19818,20 +20198,6 @@ produce_stretch_glyph (it)
   it->descent = it->phys_descent = height - it->ascent;
   it->nglyphs = width > 0 && height > 0 ? 1 : 0;
 
-  if (width > 0 && height > 0 && face->box != FACE_NO_BOX)
-    {
-      if (face->box_line_width > 0)
-       {
-         it->ascent += face->box_line_width;
-         it->descent += face->box_line_width;
-       }
-
-      if (it->start_of_box_run_p)
-       it->pixel_width += abs (face->box_line_width);
-      if (it->end_of_box_run_p)
-       it->pixel_width += abs (face->box_line_width);
-    }
-
   take_vertical_position_into_account (it);
 }
 
@@ -20029,20 +20395,20 @@ x_produce_glyphs (it)
 
          it->nglyphs = 1;
 
-         pcm = rif->per_char_metric (font, &char2b,
-                                     FONT_TYPE_FOR_UNIBYTE (font, it->char_to_display));
-
-         if (it->override_ascent >= 0)
-           {
-             it->ascent = it->override_ascent;
-             it->descent = it->override_descent;
-             boff = it->override_boff;
-           }
-         else
-           {
-             it->ascent = FONT_BASE (font) + boff;
-             it->descent = FONT_DESCENT (font) - boff;
-           }
+          pcm = FRAME_RIF (it->f)->per_char_metric
+            (font, &char2b, FONT_TYPE_FOR_UNIBYTE (font, it->char_to_display));
+
+         if (it->override_ascent >= 0)
+           {
+             it->ascent = it->override_ascent;
+             it->descent = it->override_descent;
+             boff = it->override_boff;
+           }
+         else
+           {
+             it->ascent = FONT_BASE (font) + boff;
+             it->descent = FONT_DESCENT (font) - boff;
+           }
 
          if (pcm)
            {
@@ -20105,7 +20471,7 @@ x_produce_glyphs (it)
          /* If face has an overline, add the height of the overline
             (1 pixel) and a 1 pixel margin to the character height.  */
          if (face->overline_p)
-           it->ascent += 2;
+           it->ascent += overline_margin;
 
          if (it->constrain_row_ascent_descent_p)
            {
@@ -20260,8 +20626,8 @@ x_produce_glyphs (it)
             from the charset width; this is what old redisplay code
             did.  */
 
-         pcm = rif->per_char_metric (font, &char2b,
-                                     FONT_TYPE_FOR_MULTIBYTE (font, it->c));
+         pcm = FRAME_RIF (it->f)->per_char_metric (font, &char2b,
+                                                    FONT_TYPE_FOR_MULTIBYTE (font, it->c));
 
          if (font_not_found_p || !pcm)
            {
@@ -20307,7 +20673,7 @@ x_produce_glyphs (it)
          /* If face has an overline, add the height of the overline
             (1 pixel) and a 1 pixel margin to the character height.  */
          if (face->overline_p)
-           it->ascent += 2;
+           it->ascent += overline_margin;
 
          take_vertical_position_into_account (it);
 
@@ -20392,8 +20758,8 @@ x_produce_glyphs (it)
 
          /* Initialize the bounding box.  */
          if (font_info
-             && (pcm = rif->per_char_metric (font, &char2b,
-                                             FONT_TYPE_FOR_MULTIBYTE (font, it->c))))
+             && (pcm = FRAME_RIF (it->f)->per_char_metric (font, &char2b,
+                                                            FONT_TYPE_FOR_MULTIBYTE (font, it->c))))
            {
              width = pcm->width;
              ascent = pcm->ascent;
@@ -20451,8 +20817,8 @@ x_produce_glyphs (it)
                }
 
              if (font_info
-                 && (pcm = rif->per_char_metric (font, &char2b,
-                                                 FONT_TYPE_FOR_MULTIBYTE (font, ch))))
+                 && (pcm = FRAME_RIF (it->f)->per_char_metric (font, &char2b,
+                                                                FONT_TYPE_FOR_MULTIBYTE (font, ch))))
                {
                  width = pcm->width;
                  ascent = pcm->ascent;
@@ -20582,7 +20948,7 @@ x_produce_glyphs (it)
       /* If face has an overline, add the height of the overline
         (1 pixel) and a 1 pixel margin to the character height.  */
       if (face->overline_p)
-       it->ascent += 2;
+       it->ascent += overline_margin;
 
       take_vertical_position_into_account (it);
 
@@ -20692,8 +21058,8 @@ x_insert_glyphs (start, len)
   frame_x = window_box_left (w, updated_area) + output_cursor.x;
   frame_y = WINDOW_TO_FRAME_PIXEL_Y (w, output_cursor.y);
 
-  rif->shift_glyphs_for_insert (f, frame_x, frame_y, shifted_region_width,
-                               line_height, shift_by_width);
+  FRAME_RIF (f)->shift_glyphs_for_insert (f, frame_x, frame_y, shifted_region_width,
+                                          line_height, shift_by_width);
 
   /* Write the glyphs.  */
   hpos = start - row->glyphs[updated_area];
@@ -20775,8 +21141,8 @@ x_clear_end_of_line (to_x)
   if (to_x > from_x && to_y > from_y)
     {
       BLOCK_INPUT;
-      rif->clear_frame_area (f, from_x, from_y,
-                            to_x - from_x, to_y - from_y);
+      FRAME_RIF (f)->clear_frame_area (f, from_x, from_y,
+                                       to_x - from_x, to_y - from_y);
       UNBLOCK_INPUT;
     }
 }
@@ -20957,10 +21323,35 @@ get_window_cursor_type (w, glyph, width, active_cursor)
   /* Use normal cursor if not blinked off.  */
   if (!w->cursor_off_p)
     {
-      if (glyph != NULL && glyph->type == IMAGE_GLYPH) {
-       if (cursor_type == FILLED_BOX_CURSOR)
-         cursor_type = HOLLOW_BOX_CURSOR;
+#ifdef HAVE_WINDOW_SYSTEM
+      if (glyph != NULL && glyph->type == IMAGE_GLYPH)
+       {
+         if (cursor_type == FILLED_BOX_CURSOR)
+           {
+             /* Using a block cursor on large images can be very annoying.
+                So use a hollow cursor for "large" images.
+                If image is not transparent (no mask), also use hollow cursor.  */
+             struct image *img = IMAGE_FROM_ID (f, glyph->u.img_id);
+             if (img != NULL && IMAGEP (img->spec))
+               {
+                 /* Arbitrarily, interpret "Large" as >32x32 and >NxN
+                    where N = size of default frame font size.
+                    This should cover most of the "tiny" icons people may use.  */
+                 if (!img->mask
+                     || img->width > max (32, WINDOW_FRAME_COLUMN_WIDTH (w))
+                     || img->height > max (32, WINDOW_FRAME_LINE_HEIGHT (w)))
+                   cursor_type = HOLLOW_BOX_CURSOR;
+               }
+           }
+         else if (cursor_type != NO_CURSOR)
+           {
+             /* Display current only supports BOX and HOLLOW cursors for images.
+                So for now, unconditionally use a HOLLOW cursor when cursor is
+                not a solid box cursor.  */
+             cursor_type = HOLLOW_BOX_CURSOR;
+           }
       }
+#endif
       return cursor_type;
     }
 
@@ -21246,7 +21637,7 @@ erase_phys_cursor (w)
   /* Maybe clear the display under the cursor.  */
   if (w->phys_cursor_type == HOLLOW_BOX_CURSOR)
     {
-      int x, y;
+      int x, y, left_x;
       int header_line_height = WINDOW_HEADER_LINE_HEIGHT (w);
       int width;
 
@@ -21254,12 +21645,17 @@ erase_phys_cursor (w)
       if (cursor_glyph == NULL)
        goto mark_cursor_off;
 
-      x = WINDOW_TEXT_TO_FRAME_PIXEL_X (w, w->phys_cursor.x);
+      width = cursor_glyph->pixel_width;
+      left_x = window_box_left_offset (w, TEXT_AREA);
+      x = w->phys_cursor.x;
+      if (x < left_x)
+       width -= left_x - x;
+      width = min (width, window_box_width (w, TEXT_AREA) - x);
       y = WINDOW_TO_FRAME_PIXEL_Y (w, max (header_line_height, cursor_row->y));
-      width = min (cursor_glyph->pixel_width,
-                  window_box_width (w, TEXT_AREA) - w->phys_cursor.x);
+      x = WINDOW_TEXT_TO_FRAME_PIXEL_X (w, max (x, left_x));
 
-      rif->clear_frame_area (f, x, y, width, cursor_row->visible_height);
+      if (width > 0)
+       FRAME_RIF (f)->clear_frame_area (f, x, y, width, cursor_row->visible_height);
     }
 
   /* Erase the cursor by redrawing the character underneath it.  */
@@ -21356,9 +21752,9 @@ display_and_set_cursor (w, on, hpos, vpos, x, y)
       w->phys_cursor.vpos = vpos;
     }
 
-  rif->draw_window_cursor (w, glyph_row, x, y,
-                          new_cursor_type, new_cursor_width,
-                          on, active_cursor);
+  FRAME_RIF (f)->draw_window_cursor (w, glyph_row, x, y,
+                                     new_cursor_type, new_cursor_width,
+                                     on, active_cursor);
 }
 
 
@@ -21506,12 +21902,12 @@ show_mouse_face (dpyinfo, draw)
     }
 
   /* Change the mouse cursor.  */
-  if (draw == DRAW_NORMAL_TEXT)
-    rif->define_frame_cursor (f, FRAME_X_OUTPUT (f)->text_cursor);
+  if (draw == DRAW_NORMAL_TEXT && !EQ (dpyinfo->mouse_face_window, f->tool_bar_window))
+    FRAME_RIF (f)->define_frame_cursor (f, FRAME_X_OUTPUT (f)->text_cursor);
   else if (draw == DRAW_MOUSE_FACE)
-    rif->define_frame_cursor (f, FRAME_X_OUTPUT (f)->hand_cursor);
+    FRAME_RIF (f)->define_frame_cursor (f, FRAME_X_OUTPUT (f)->hand_cursor);
   else
-    rif->define_frame_cursor (f, FRAME_X_OUTPUT (f)->nontext_cursor);
+    FRAME_RIF (f)->define_frame_cursor (f, FRAME_X_OUTPUT (f)->nontext_cursor);
 }
 
 /* EXPORT:
@@ -21950,7 +22346,6 @@ on_hot_spot_p (hot_spot, x, y)
          return inside;
        }
     }
-  /* If we don't understand the format, pretend we're not in the hot-spot.  */
   return 0;
 }
 
@@ -22030,7 +22425,7 @@ define_frame_cursor1 (f, cursor, pointer)
     }
 
   if (cursor != No_Cursor)
-    rif->define_frame_cursor (f, cursor);
+    FRAME_RIF (f)->define_frame_cursor (f, cursor);
 }
 
 /* Take proper action when mouse has moved to the mode or header line
@@ -22291,7 +22686,7 @@ note_mouse_highlight (f, x, y)
   struct buffer *b;
 
   /* When a menu is active, don't highlight because this looks odd.  */
-#if defined (USE_X_TOOLKIT) || defined (USE_GTK) || defined (HAVE_NTGUI)
+#if defined (USE_X_TOOLKIT) || defined (USE_GTK) || defined (MAC_OS)
   if (popup_activated ())
     return;
 #endif
@@ -22351,7 +22746,10 @@ note_mouse_highlight (f, x, y)
     }
 
   if (part == ON_VERTICAL_BORDER)
-    cursor = FRAME_X_OUTPUT (f)->horizontal_drag_cursor;
+    {
+      cursor = FRAME_X_OUTPUT (f)->horizontal_drag_cursor;
+      help_echo_string = build_string ("drag-mouse-1: resize");
+    }
   else if (part == ON_LEFT_FRINGE || part == ON_RIGHT_FRINGE
           || part == ON_SCROLL_BAR)
     cursor = FRAME_X_OUTPUT (f)->nontext_cursor;
@@ -22990,8 +23388,8 @@ phys_cursor_in_rect_p (w, r)
         I assume the effect is the same -- and this is portable.  */
       return x_intersect_rectangles (&cr, r, &result);
     }
-  else
-    return 0;
+  /* If we don't understand the format, pretend we're not in the hot-spot.  */
+  return 0;
 }
 
 
@@ -23003,6 +23401,8 @@ void
 x_draw_vertical_border (w)
      struct window *w;
 {
+  struct frame *f = XFRAME (WINDOW_FRAME (w));
+  
   /* We could do better, if we knew what type of scroll-bar the adjacent
      windows (on either side) have...  But we don't :-(
      However, I think this works ok.  ++KFS 2003-04-25 */
@@ -23023,9 +23423,9 @@ x_draw_vertical_border (w)
       y1 -= 1;
 
       if (WINDOW_LEFT_FRINGE_WIDTH (w) == 0)
-       x1 -= 1;
+        x1 -= 1;
 
-      rif->draw_vertical_window_border (w, x1, y0, y1);
+      FRAME_RIF (f)->draw_vertical_window_border (w, x1, y0, y1);
     }
   else if (!WINDOW_LEFTMOST_P (w)
           && !WINDOW_HAS_VERTICAL_SCROLL_BAR_ON_LEFT (w))
@@ -23036,9 +23436,9 @@ x_draw_vertical_border (w)
       y1 -= 1;
 
       if (WINDOW_LEFT_FRINGE_WIDTH (w) == 0)
-       x0 -= 1;
+        x0 -= 1;
 
-      rif->draw_vertical_window_border (w, x0, y0, y1);
+      FRAME_RIF (f)->draw_vertical_window_border (w, x0, y0, y1);
     }
 }
 
@@ -23624,7 +24024,7 @@ Value is a number or a cons (WIDTH-DPI . HEIGHT-DPI).  */);
   truncate_partial_width_windows = 1;
 
   DEFVAR_BOOL ("mode-line-inverse-video", &mode_line_inverse_video,
-    doc: /* nil means display the mode-line/header-line/menu-bar in the default face.
+    doc: /* When nil, display the mode-line/header-line/menu-bar in the default face.
 Any other value means to use the appropriate face, `mode-line',
 `header-line', or `menu' respectively.  */);
   mode_line_inverse_video = 1;
@@ -23655,9 +24055,10 @@ This variable is not guaranteed to be accurate except while processing
   DEFVAR_LISP ("frame-title-format", &Vframe_title_format,
     doc: /* Template for displaying the title bar of visible frames.
 \(Assuming the window manager supports this feature.)
-This variable has the same structure as `mode-line-format' (which see),
-and is used only on frames for which no explicit name has been set
-\(see `modify-frame-parameters').  */);
+
+This variable has the same structure as `mode-line-format', except that
+the %c and %l constructs are ignored.  It is used only on frames for
+which no explicit name has been set \(see `modify-frame-parameters').  */);
 
   DEFVAR_LISP ("icon-title-format", &Vicon_title_format,
     doc: /* Template for displaying the title bar of an iconified frame.
@@ -23703,16 +24104,30 @@ Each function is called with two arguments, the window and the end trigger value
 See `set-window-redisplay-end-trigger'.  */);
   Vredisplay_end_trigger_functions = Qnil;
 
-  DEFVAR_BOOL ("mouse-autoselect-window", &mouse_autoselect_window,
-    doc: /* *Non-nil means autoselect window with mouse pointer.  */);
-  mouse_autoselect_window = 0;
-
-  DEFVAR_BOOL ("auto-resize-tool-bars", &auto_resize_tool_bars_p,
+  DEFVAR_LISP ("mouse-autoselect-window", &Vmouse_autoselect_window,
+     doc: /* *Non-nil means autoselect window with mouse pointer.
+If nil, do not autoselect windows.
+A positive number means delay autoselection by that many seconds: a
+window is autoselected only after the mouse has remained in that
+window for the duration of the delay.
+A negative number has a similar effect, but causes windows to be
+autoselected only after the mouse has stopped moving.  \(Because of
+the way Emacs compares mouse events, you will occasionally wait twice
+that time before the window gets selected.\)
+Any other value means to autoselect window instantaneously when the
+mouse pointer enters it.
+
+Autoselection selects the minibuffer only if it is active, and never
+unselects the minibuffer if it is active.  */);
+  Vmouse_autoselect_window = Qnil;
+
+  DEFVAR_LISP ("auto-resize-tool-bars", &Vauto_resize_tool_bars,
     doc: /* *Non-nil means automatically resize tool-bars.
-This increases a tool-bar's height if not all tool-bar items are visible.
-It decreases a tool-bar's height when it would display blank lines
-otherwise.  */);
-  auto_resize_tool_bars_p = 1;
+This dynamically changes the tool-bar's height to the minimum height
+that is needed to make all tool-bar items visible.
+If value is `grow-only', the tool-bar's height is only increased
+automatically; to decreace the tool-bar height, use \\[recenter].  */);
+  Vauto_resize_tool_bars = Qt;
 
   DEFVAR_BOOL ("auto-raise-tool-bar-buttons", &auto_raise_tool_bar_buttons_p,
     doc: /* *Non-nil means raise tool-bar buttons when the mouse moves over them.  */);
@@ -23797,7 +24212,7 @@ before automatic hscrolling will horizontally scroll the window.  */);
 
   DEFVAR_LISP ("hscroll-step", &Vhscroll_step,
     doc: /* *How many columns to scroll the window when point gets too close to the edge.
-When point is less than `automatic-hscroll-margin' columns from the window
+When point is less than `hscroll-margin' columns from the window
 edge, automatic hscrolling will scroll the window by the amount of columns
 determined by this variable.  If its value is a positive integer, scroll that
 many columns.  If it's a positive floating-point number, it specifies the
@@ -23825,6 +24240,11 @@ This is used to update submenus such as Buffers,
 whose contents depend on various data.  */);
   Vmenu_bar_update_hook = Qnil;
 
+  DEFVAR_LISP ("menu-updating-frame", &Vmenu_updating_frame,
+              doc: /* Frame for which we are updating a menu.
+The enable predicate for a menu binding should check this variable.  */);
+  Vmenu_updating_frame = Qnil;
+
   DEFVAR_BOOL ("inhibit-menubar-update", &inhibit_menubar_update,
     doc: /* Non-nil means don't update menu bars.  Internal use only.  */);
   inhibit_menubar_update = 0;
@@ -23850,6 +24270,12 @@ whose contents depend on various data.  */);
               doc: /* Inhibit try_cursor_movement display optimization.  */);
   inhibit_try_cursor_movement = 0;
 #endif /* GLYPH_DEBUG */
+
+  DEFVAR_INT ("overline-margin", &overline_margin,
+              doc: /* *Space between overline and text, in pixels.
+The default value is 2: the height of the overline (1 pixel) plus 1 pixel
+margin to the caracter height.  */);
+  overline_margin = 2;
 }