Imported Upstream version 0.19.7
[platform/upstream/gettext.git] / gnulib-local / lib / xmalloc.c
1 /* xmalloc.c -- malloc with out of memory checking
2    Copyright (C) 1990-1996, 2000-2003, 2005-2007, 2012, 2015 Free
3    Software Foundation, Inc.
4
5    This program is free software: you can redistribute it and/or modify
6    it under the terms of the GNU General Public License as published by
7    the Free Software Foundation; either version 3 of the License, or
8    (at your option) any later version.
9
10    This program is distributed in the hope that it will be useful,
11    but WITHOUT ANY WARRANTY; without even the implied warranty of
12    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13    GNU General Public License for more details.
14
15    You should have received a copy of the GNU General Public License
16    along with this program.  If not, see <http://www.gnu.org/licenses/>.  */
17
18 #include <config.h>
19
20 /* Specification.  */
21 #include "xalloc.h"
22
23 #include <stdlib.h>
24
25 #include "error.h"
26 #include "gettext.h"
27
28 #define _(str) gettext (str)
29
30
31 /* Exit value when the requested amount of memory is not available.
32    The caller may set it to some other value.  */
33 int xmalloc_exit_failure = EXIT_FAILURE;
34
35 void
36 xalloc_die ()
37 {
38   error (xmalloc_exit_failure, 0, _("memory exhausted"));
39   /* _Noreturn cannot be given to error, since it may return if
40      its first argument is 0.  To help compilers understand the
41      xalloc_die does terminate, call exit. */
42   exit (EXIT_FAILURE);
43 }
44
45 static void *
46 fixup_null_alloc (size_t n)
47 {
48   void *p;
49
50   p = NULL;
51   if (n == 0)
52     p = malloc ((size_t) 1);
53   if (p == NULL)
54     xalloc_die ();
55   return p;
56 }
57
58 /* Allocate N bytes of memory dynamically, with error checking.  */
59
60 void *
61 xmalloc (size_t n)
62 {
63   void *p;
64
65   p = malloc (n);
66   if (p == NULL)
67     p = fixup_null_alloc (n);
68   return p;
69 }
70
71 /* Allocate memory for NMEMB elements of SIZE bytes, with error checking.
72    SIZE must be > 0.  */
73
74 void *
75 xnmalloc (size_t nmemb, size_t size)
76 {
77   size_t n;
78   void *p;
79
80   if (xalloc_oversized (nmemb, size))
81     xalloc_die ();
82   n = nmemb * size;
83   p = malloc (n);
84   if (p == NULL)
85     p = fixup_null_alloc (n);
86   return p;
87 }
88
89 /* Allocate SIZE bytes of memory dynamically, with error checking,
90    and zero it.  */
91
92 void *
93 xzalloc (size_t size)
94 {
95   void *p;
96
97   p = xmalloc (size);
98   memset (p, 0, size);
99   return p;
100 }
101
102 /* Allocate memory for N elements of S bytes, with error checking,
103    and zero it.  */
104
105 void *
106 xcalloc (size_t n, size_t s)
107 {
108   void *p;
109
110   p = calloc (n, s);
111   if (p == NULL)
112     p = fixup_null_alloc (n);
113   return p;
114 }
115
116 /* Change the size of an allocated block of memory P to N bytes,
117    with error checking.
118    If P is NULL, run xmalloc.  */
119
120 void *
121 xrealloc (void *p, size_t n)
122 {
123   if (p == NULL)
124     return xmalloc (n);
125   p = realloc (p, n);
126   if (p == NULL)
127     p = fixup_null_alloc (n);
128   return p;
129 }