]> code.delx.au - gnu-emacs/blobdiff - src/casefiddle.c
Don't call xfree from the watcher thread. Do it only in remove_watch.
[gnu-emacs] / src / casefiddle.c
index 43ecd38dc7d9b022162acb3444c1a5923256bd94..e365462757696146917a623d4b878d7656b7f194 100644 (file)
@@ -1,6 +1,6 @@
 /* GNU Emacs case conversion functions.
 
-Copyright (C) 1985, 1994, 1997-1999, 2001-2011 Free Software Foundation, Inc.
+Copyright (C) 1985, 1994, 1997-1999, 2001-2012 Free Software Foundation, Inc.
 
 This file is part of GNU Emacs.
 
@@ -19,10 +19,10 @@ along with GNU Emacs.  If not, see <http://www.gnu.org/licenses/>.  */
 
 
 #include <config.h>
-#include <setjmp.h>
+
 #include "lisp.h"
-#include "buffer.h"
 #include "character.h"
+#include "buffer.h"
 #include "commands.h"
 #include "syntax.h"
 #include "composite.h"
@@ -35,8 +35,8 @@ Lisp_Object Qidentity;
 static Lisp_Object
 casify_object (enum case_action flag, Lisp_Object obj)
 {
-  register int c, c1;
-  register int inword = flag == CASE_DOWN;
+  int c, c1;
+  bool inword = flag == CASE_DOWN;
 
   /* If the case table is flagged as modified, rescan it.  */
   if (NILP (XCHAR_TABLE (BVAR (current_buffer, downcase_table))->extras[1]))
@@ -47,12 +47,13 @@ casify_object (enum case_action flag, Lisp_Object obj)
       int flagbits = (CHAR_ALT | CHAR_SUPER | CHAR_HYPER
                      | CHAR_SHIFT | CHAR_CTL | CHAR_META);
       int flags = XINT (obj) & flagbits;
-      int multibyte = ! NILP (BVAR (current_buffer, enable_multibyte_characters));
+      bool multibyte = ! NILP (BVAR (current_buffer,
+                                    enable_multibyte_characters));
 
       /* If the character has higher bits set
         above the flags, return it unchanged.
         It is not a real character.  */
-      if ((unsigned) XFASTINT (obj) > (unsigned) flagbits)
+      if (UNSIGNED_CMP (XFASTINT (obj), >, flagbits))
        return obj;
 
       c1 = XFASTINT (obj) & ~flagbits;
@@ -82,8 +83,8 @@ casify_object (enum case_action flag, Lisp_Object obj)
     wrong_type_argument (Qchar_or_string_p, obj);
   else if (!STRING_MULTIBYTE (obj))
     {
-      EMACS_INT i;
-      EMACS_INT size = SCHARS (obj);
+      ptrdiff_t i;
+      ptrdiff_t size = SCHARS (obj);
 
       obj = Fcopy_sequence (obj);
       for (i = 0; i < size; i++)
@@ -111,26 +112,19 @@ casify_object (enum case_action flag, Lisp_Object obj)
     }
   else
     {
-      EMACS_INT i, i_byte, size = SCHARS (obj);
+      ptrdiff_t i, i_byte, size = SCHARS (obj);
       int len;
       USE_SAFE_ALLOCA;
-      unsigned char *dst, *o;
-      /* Over-allocate by 12%: this is a minor overhead, but should be
-        sufficient in 99.999% of the cases to avoid a reallocation.  */
-      EMACS_INT o_size = SBYTES (obj) + SBYTES (obj) / 8 + MAX_MULTIBYTE_LENGTH;
-      SAFE_ALLOCA (dst, void *, o_size);
-      o = dst;
+      ptrdiff_t o_size = (size < STRING_BYTES_BOUND / MAX_MULTIBYTE_LENGTH
+                         ? size * MAX_MULTIBYTE_LENGTH
+                         : STRING_BYTES_BOUND);
+      unsigned char *dst = SAFE_ALLOCA (o_size);
+      unsigned char *o = dst;
 
       for (i = i_byte = 0; i < size; i++, i_byte += len)
        {
-         if ((o - dst) + MAX_MULTIBYTE_LENGTH > o_size)
-           { /* Not enough space for the next char: grow the destination.  */
-             unsigned char *old_dst = dst;
-             o_size += o_size; /* Probably overkill, but extremely rare.  */
-             SAFE_ALLOCA (dst, void *, o_size);
-             memcpy (dst, old_dst, o - old_dst);
-             o = dst + (o - old_dst);
-           }
+         if (o_size - (o - dst) < MAX_MULTIBYTE_LENGTH)
+           string_overflow ();
          c = STRING_CHAR_AND_LENGTH (SDATA (obj) + i_byte, len);
          if (inword && flag != CASE_CAPITALIZE_UP)
            c = downcase (c);
@@ -196,17 +190,17 @@ The argument object is not altered--the value is a copy.  */)
 static void
 casify_region (enum case_action flag, Lisp_Object b, Lisp_Object e)
 {
-  register int c;
-  register int inword = flag == CASE_DOWN;
-  register int multibyte = !NILP (BVAR (current_buffer, enable_multibyte_characters));
-  EMACS_INT start, end;
-  EMACS_INT start_byte, end_byte;
+  int c;
+  bool inword = flag == CASE_DOWN;
+  bool multibyte = !NILP (BVAR (current_buffer, enable_multibyte_characters));
+  ptrdiff_t start, end;
+  ptrdiff_t start_byte;
 
   /* Position of first and last changes.  */
-  EMACS_INT first = -1, last IF_LINT (= 0);
+  ptrdiff_t first = -1, last IF_LINT (= 0);
 
-  EMACS_INT opoint = PT;
-  EMACS_INT opoint_byte = PT_BYTE;
+  ptrdiff_t opoint = PT;
+  ptrdiff_t opoint_byte = PT_BYTE;
 
   if (EQ (b, e))
     /* Not modifying because nothing marked */
@@ -222,9 +216,8 @@ casify_region (enum case_action flag, Lisp_Object b, Lisp_Object e)
   modify_region (current_buffer, start, end, 0);
   record_change (start, end - start);
   start_byte = CHAR_TO_BYTE (start);
-  end_byte = CHAR_TO_BYTE (end);
 
-  SETUP_BUFFER_SYNTAX_TABLE(); /* For syntax_prefix_flag_p.  */
+  SETUP_BUFFER_SYNTAX_TABLE ();        /* For syntax_prefix_flag_p.  */
 
   while (start < end)
     {
@@ -352,10 +345,10 @@ character positions to operate on.  */)
 }
 \f
 static Lisp_Object
-operate_on_word (Lisp_Object arg, EMACS_INT *newpoint)
+operate_on_word (Lisp_Object arg, ptrdiff_t *newpoint)
 {
   Lisp_Object val;
-  EMACS_INT farend;
+  ptrdiff_t farend;
   EMACS_INT iarg;
 
   CHECK_NUMBER (arg);
@@ -377,7 +370,7 @@ See also `capitalize-word'.  */)
   (Lisp_Object arg)
 {
   Lisp_Object beg, end;
-  EMACS_INT newpoint;
+  ptrdiff_t newpoint;
   XSETFASTINT (beg, PT);
   end = operate_on_word (arg, &newpoint);
   casify_region (CASE_UP, beg, end);
@@ -391,7 +384,7 @@ With negative argument, convert previous words but do not move.  */)
   (Lisp_Object arg)
 {
   Lisp_Object beg, end;
-  EMACS_INT newpoint;
+  ptrdiff_t newpoint;
   XSETFASTINT (beg, PT);
   end = operate_on_word (arg, &newpoint);
   casify_region (CASE_DOWN, beg, end);
@@ -407,7 +400,7 @@ With negative argument, capitalize previous words but do not move.  */)
   (Lisp_Object arg)
 {
   Lisp_Object beg, end;
-  EMACS_INT newpoint;
+  ptrdiff_t newpoint;
   XSETFASTINT (beg, PT);
   end = operate_on_word (arg, &newpoint);
   casify_region (CASE_CAPITALIZE, beg, end);
@@ -418,8 +411,7 @@ With negative argument, capitalize previous words but do not move.  */)
 void
 syms_of_casefiddle (void)
 {
-  Qidentity = intern_c_string ("identity");
-  staticpro (&Qidentity);
+  DEFSYM (Qidentity, "identity");
   defsubr (&Supcase);
   defsubr (&Sdowncase);
   defsubr (&Scapitalize);
@@ -436,9 +428,9 @@ syms_of_casefiddle (void)
 void
 keys_of_casefiddle (void)
 {
-  initial_define_key (control_x_map, Ctl('U'), "upcase-region");
+  initial_define_key (control_x_map, Ctl ('U'), "upcase-region");
   Fput (intern ("upcase-region"), Qdisabled, Qt);
-  initial_define_key (control_x_map, Ctl('L'), "downcase-region");
+  initial_define_key (control_x_map, Ctl ('L'), "downcase-region");
   Fput (intern ("downcase-region"), Qdisabled, Qt);
 
   initial_define_key (meta_map, 'u', "upcase-word");