emacs-diffs
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[Emacs-diffs] trunk r116643: Fix crashes in lisp_align_free in a build w


From: Eli Zaretskii
Subject: [Emacs-diffs] trunk r116643: Fix crashes in lisp_align_free in a build with GC_MCHECK.
Date: Mon, 03 Mar 2014 16:47:43 +0000
User-agent: Bazaar (2.6b2)

------------------------------------------------------------
revno: 116643
revision-id: address@hidden
parent: address@hidden
fixes bug: http://debbugs.gnu.org/16901
committer: Eli Zaretskii <address@hidden>
branch nick: trunk
timestamp: Mon 2014-03-03 18:46:36 +0200
message:
  Fix crashes in lisp_align_free in a build with GC_MCHECK.
  
   src/gmalloc.c (aligned_alloc): Fix adjustment of size of the
   allocated buffer due to alignment.
   (freehook): If the block to be freed was allocated by
   'aligned_alloc', find its real pointer before calling 'free'.
   (mabort) [emacs]: Call 'emacs_abort', not 'abort', to provide a
   backtrace.
modified:
  src/ChangeLog                  changelog-20091113204419-o5vbwnq5f7feedwu-1438
  src/gmalloc.c                  gmalloc.c-20091113204419-o5vbwnq5f7feedwu-1085
=== modified file 'src/ChangeLog'
--- a/src/ChangeLog     2014-03-03 08:27:58 +0000
+++ b/src/ChangeLog     2014-03-03 16:46:36 +0000
@@ -1,3 +1,13 @@
+2014-03-03  Eli Zaretskii  <address@hidden>
+
+       * gmalloc.c (aligned_alloc): Fix adjustment of size of the
+       allocated buffer due to alignment.
+       (freehook): If the block to be freed was allocated by
+       'aligned_alloc', find its real pointer before calling 'free'.
+       (Bug#16901)
+       (mabort) [emacs]: Call 'emacs_abort', not 'abort', to provide a
+       backtrace.
+
 2014-03-03  Dmitry Antipov  <address@hidden>
 
        * font.c (toplevel): Adjust comment about font cache layout.

=== modified file 'src/gmalloc.c'
--- a/src/gmalloc.c     2014-01-01 07:43:34 +0000
+++ b/src/gmalloc.c     2014-03-03 16:46:36 +0000
@@ -68,6 +68,10 @@
 extern void malloc_enable_thread (void);
 #endif
 
+#ifdef emacs
+extern void emacs_abort (void);
+#endif
+
 /* The allocator divides the heap into blocks of fixed size; large
    requests receive one or more whole blocks, and small requests
    receive a fragment of a block.  Fragment sizes are powers of two,
@@ -1595,7 +1599,7 @@
     {
       /* Reallocate the block with only as much excess as it needs.  */
       free (result);
-      result = malloc (adj + size);
+      result = malloc (size + alignment - adj);
       if (result == NULL)      /* Impossible unless interrupted.  */
        return NULL;
 
@@ -1605,7 +1609,7 @@
         different block with weaker alignment.  If so, this block is too
         short to contain SIZE after alignment correction.  So we must
         try again and get another block, slightly larger.  */
-    } while (adj > lastadj);
+    } while (adj < lastadj);
 
   if (adj != 0)
     {
@@ -1787,6 +1791,22 @@
 
   if (ptr)
     {
+      struct alignlist *l;
+
+      /* If the block was allocated by aligned_alloc, its real pointer
+        to free is recorded in _aligned_blocks; find that.  */
+      PROTECT_MALLOC_STATE (0);
+      LOCK_ALIGNED_BLOCKS ();
+      for (l = _aligned_blocks; l != NULL; l = l->next)
+       if (l->aligned == ptr)
+         {
+           l->aligned = NULL;  /* Mark the slot in the list as free.  */
+           ptr = l->exact;
+           break;
+         }
+      UNLOCK_ALIGNED_BLOCKS ();
+      PROTECT_MALLOC_STATE (1);
+
       hdr = ((struct hdr *) ptr) - 1;
       checkhdr (hdr);
       hdr->magic = MAGICFREE;
@@ -1878,7 +1898,11 @@
 #else
   fprintf (stderr, "mcheck: %s\n", msg);
   fflush (stderr);
+# ifdef emacs
+  emacs_abort ();
+# else
   abort ();
+# endif
 #endif
 }
 


reply via email to

[Prev in Thread] Current Thread [Next in Thread]