changeset 17643:eaa841a1f670

xalloc: allow x2nrealloc (P, PN, S) where P && !*PN * lib/xalloc.h (x2nrealloc): Extend slightly, to allow the current size to be zero even when the pointer is nonnull. This accommodates the use case where P is malloc (0) and *PN is 0 on a host where malloc (0) yields nonnull.
author Paul Eggert <eggert@cs.ucla.edu>
date Sat, 12 Apr 2014 10:45:47 -0700
parents 8af917141d49
children bfa6d7414863
files ChangeLog lib/xalloc.h
diffstat 2 files changed, 14 insertions(+), 7 deletions(-) [+]
line wrap: on
line diff
--- a/ChangeLog	Wed Apr 09 10:20:08 2014 -0600
+++ b/ChangeLog	Sat Apr 12 10:45:47 2014 -0700
@@ -1,3 +1,11 @@
+2014-04-12  Paul Eggert  <eggert@cs.ucla.edu>
+
+	xalloc: allow x2nrealloc (P, PN, S) where P && !*PN
+	* lib/xalloc.h (x2nrealloc): Extend slightly, to allow the current
+	size to be zero even when the pointer is nonnull.  This
+	accommodates the use case where P is malloc (0) and *PN is 0 on a
+	host where malloc (0) yields nonnull.
+
 2014-04-09  Eric Blake  <eblake@redhat.com>
 
 	fts: avoid unnecessary strlen calls
--- a/lib/xalloc.h	Wed Apr 09 10:20:08 2014 -0600
+++ b/lib/xalloc.h	Sat Apr 12 10:45:47 2014 -0700
@@ -122,10 +122,9 @@
 
 /* If P is null, allocate a block of at least *PN such objects;
    otherwise, reallocate P so that it contains more than *PN objects
-   each of S bytes.  *PN must be nonzero unless P is null, and S must
-   be nonzero.  Set *PN to the new number of objects, and return the
-   pointer to the new block.  *PN is never set to zero, and the
-   returned pointer is never null.
+   each of S bytes.  S must be nonzero.  Set *PN to the new number of
+   objects, and return the pointer to the new block.  *PN is never set
+   to zero, and the returned pointer is never null.
 
    Repeated reallocations are guaranteed to make progress, either by
    allocating an initial block with a nonzero size, or by allocating a
@@ -196,13 +195,13 @@
     }
   else
     {
-      /* Set N = ceil (1.5 * N) so that progress is made if N == 1.
+      /* Set N = floor (1.5 * N) + 1 so that progress is made even if N == 0.
          Check for overflow, so that N * S stays in size_t range.
-         The check is slightly conservative, but an exact check isn't
+         The check may be slightly conservative, but an exact check isn't
          worth the trouble.  */
       if ((size_t) -1 / 3 * 2 / s <= n)
         xalloc_die ();
-      n += (n + 1) / 2;
+      n += n / 2 + 1;
     }
 
   *pn = n;