]> code.delx.au - gnu-emacs/blobdiff - src/scroll.c
Merge from emacs-24
[gnu-emacs] / src / scroll.c
index 71ce43b2e483ee70b0511e4bb39ceb0ca946b23d..7cb683c4577c059c1a8a6cf3fe03c21db73ad117 100644 (file)
@@ -1,7 +1,7 @@
 /* Calculate what line insertion or deletion to do, and do it
 
-Copyright (C) 1985-1986, 1990, 1993-1994, 2001-2012
-  Free Software Foundation, Inc.
+Copyright (C) 1985-1986, 1990, 1993-1994, 2001-2014 Free Software
+Foundation, Inc.
 
 This file is part of GNU Emacs.
 
@@ -86,11 +86,11 @@ static void do_scrolling (struct frame *,
    new contents appears.  */
 
 static void
-calculate_scrolling (FRAME_PTR frame,
+calculate_scrolling (struct frame *frame,
                     /* matrix is of size window_size + 1 on each side.  */
                     struct matrix_elt *matrix,
                     int window_size, int lines_below,
-                    int *draw_cost, int *old_hash, int *new_hash,
+                    int *draw_cost, unsigned *old_hash, unsigned *new_hash,
                     int free_at_end)
 {
   register int i, j;
@@ -245,19 +245,20 @@ do_scrolling (struct frame *frame, struct glyph_matrix *current_matrix,
 {
   struct matrix_elt *p;
   int i, j, k;
+  USE_SAFE_ALLOCA;
 
-  /* Set to 1 if we have set a terminal window with
-     set_terminal_window.  It's unsigned to work around GCC bug 48228.  */
-  unsigned int terminal_window_p = 0;
+  /* True if we have set a terminal window with set_terminal_window.  */
+  bool terminal_window_p = 0;
 
   /* A queue for line insertions to be done.  */
   struct queue { int count, pos; };
-  struct queue *queue_start
-    = alloca (current_matrix->nrows * sizeof *queue_start);
+  struct queue *queue_start;
+  SAFE_NALLOCA (queue_start, 1, current_matrix->nrows);
   struct queue *queue = queue_start;
 
-  char *retained_p = alloca (window_size * sizeof *retained_p);
-  int *copy_from = alloca (window_size * sizeof *copy_from);
+  char *retained_p = SAFE_ALLOCA (window_size);
+  int *copy_from;
+  SAFE_NALLOCA (copy_from, 1, window_size);
 
   /* Zero means line is empty.  */
   memset (retained_p, 0, window_size * sizeof (char));
@@ -379,6 +380,7 @@ do_scrolling (struct frame *frame, struct glyph_matrix *current_matrix,
 
   if (terminal_window_p)
     set_terminal_window (frame, 0);
+  SAFE_FREE ();
 }
 
 \f
@@ -423,12 +425,12 @@ do_scrolling (struct frame *frame, struct glyph_matrix *current_matrix,
    is the equivalent of draw_cost for the old line contents */
 
 static void
-calculate_direct_scrolling (FRAME_PTR frame,
+calculate_direct_scrolling (struct frame *frame,
                            /* matrix is of size window_size + 1 on each side.  */
                            struct matrix_elt *matrix,
                            int window_size, int lines_below,
                            int *draw_cost, int *old_draw_cost,
-                           int *old_hash, int *new_hash,
+                           unsigned *old_hash, unsigned *new_hash,
                            int free_at_end)
 {
   register int i, j;
@@ -650,32 +652,32 @@ do_direct_scrolling (struct frame *frame, struct glyph_matrix *current_matrix,
 {
   struct matrix_elt *p;
   int i, j;
+  USE_SAFE_ALLOCA;
 
   /* A queue of deletions and insertions to be performed.  */
   struct alt_queue { int count, pos, window; };
-  struct alt_queue *queue_start = (struct alt_queue *)
-    alloca (window_size * sizeof *queue_start);
+  struct alt_queue *queue_start;
+  SAFE_NALLOCA (queue_start, 1, window_size);
   struct alt_queue *queue = queue_start;
 
-  /* Set to 1 if a terminal window has been set with
-     set_terminal_window: */
-  int terminal_window_p = 0;
+  /* True if a terminal window has been set with set_terminal_window.  */
+  bool terminal_window_p = 0;
 
-  /* A nonzero value of write_follows indicates that a write has been
-     selected, allowing either an insert or a delete to be selected
-     next.  When write_follows is zero, a delete cannot be selected
+  /* If true, a write has been selected, allowing either an insert or a
+     delete to be selected next.  If false, a delete cannot be selected
      unless j < i, and an insert cannot be selected unless i < j.
      This corresponds to a similar restriction (with the ordering
      reversed) in calculate_direct_scrolling, which is intended to
      ensure that lines marked as inserted will be blank. */
-  int write_follows_p = 1;
+  bool write_follows_p = 1;
 
   /* For each row in the new matrix what row of the old matrix it is.  */
-  int *copy_from = alloca (window_size * sizeof *copy_from);
+  int *copy_from;
+  SAFE_NALLOCA (copy_from, 1, window_size);
 
   /* Non-zero for each row in the new matrix that is retained from the
      old matrix.  Lines not retained are empty.  */
-  char *retained_p = alloca (window_size * sizeof *retained_p);
+  char *retained_p = SAFE_ALLOCA (window_size);
 
   memset (retained_p, 0, window_size * sizeof (char));
 
@@ -791,18 +793,19 @@ do_direct_scrolling (struct frame *frame, struct glyph_matrix *current_matrix,
 
   if (terminal_window_p)
     set_terminal_window (frame, 0);
+  SAFE_FREE ();
 }
 
 
 \f
 void
-scrolling_1 (FRAME_PTR frame, int window_size, int unchanged_at_top,
+scrolling_1 (struct frame *frame, int window_size, int unchanged_at_top,
             int unchanged_at_bottom, int *draw_cost, int *old_draw_cost,
-            int *old_hash, int *new_hash, int free_at_end)
+            unsigned *old_hash, unsigned *new_hash, int free_at_end)
 {
+  USE_SAFE_ALLOCA;
   struct matrix_elt *matrix;
-  matrix = ((struct matrix_elt *)
-           alloca ((window_size + 1) * (window_size + 1) * sizeof *matrix));
+  SAFE_NALLOCA (matrix, window_size + 1, window_size + 1);
 
   if (FRAME_SCROLL_REGION_OK (frame))
     {
@@ -822,6 +825,8 @@ scrolling_1 (FRAME_PTR frame, int window_size, int unchanged_at_top,
                     frame->current_matrix, matrix, window_size,
                    unchanged_at_top);
     }
+
+  SAFE_FREE ();
 }
 
 
@@ -834,12 +839,14 @@ scrolling_1 (FRAME_PTR frame, int window_size, int unchanged_at_top,
 
 int
 scrolling_max_lines_saved (int start, int end,
-                           int *oldhash, int *newhash,
+                           unsigned *oldhash, unsigned *newhash,
                            int *cost)
 {
-  struct { int hash; int count; } lines[01000];
-  register int i, h;
-  register int matchcount = 0;
+  enum { LOG2_NLINES = 9 };
+  enum { NLINES = 1 << LOG2_NLINES };
+  struct { unsigned hash; int count; } lines[NLINES];
+  int i, h;
+  int matchcount = 0;
   int avg_length = 0;
   int threshold;
 
@@ -860,7 +867,7 @@ scrolling_max_lines_saved (int start, int end,
     {
       if (cost[i] > threshold)
        {
-         h = newhash[i] & 0777;
+         h = newhash[i] & (NLINES - 1);
          lines[h].hash = newhash[i];
          lines[h].count++;
        }
@@ -870,7 +877,7 @@ scrolling_max_lines_saved (int start, int end,
      matches between old lines and new.  */
   for (i = start; i < end; i++)
     {
-      h = oldhash[i] & 0777;
+      h = oldhash[i] & (NLINES - 1);
       if (oldhash[i] == lines[h].hash)
        {
          matchcount++;
@@ -886,7 +893,7 @@ scrolling_max_lines_saved (int start, int end,
    overhead and multiply factor values */
 
 static void
-line_ins_del (FRAME_PTR frame, int ov1, int pf1, int ovn, int pfn,
+line_ins_del (struct frame *frame, int ov1, int pf1, int ovn, int pfn,
               register int *ov, register int *mf)
 {
   register int i;
@@ -904,7 +911,7 @@ line_ins_del (FRAME_PTR frame, int ov1, int pf1, int ovn, int pfn,
 }
 
 static void
-ins_del_costs (FRAME_PTR frame,
+ins_del_costs (struct frame *frame,
               const char *one_line_string, const char *multi_string,
               const char *setup_string, const char *cleanup_string,
               int *costvec, int *ncostvec,
@@ -960,7 +967,7 @@ ins_del_costs (FRAME_PTR frame,
  */
 
 void
-do_line_insertion_deletion_costs (FRAME_PTR frame,
+do_line_insertion_deletion_costs (struct frame *frame,
                                  const char *ins_line_string,
                                  const char *multi_ins_string,
                                  const char *del_line_string,