1/* memory allocation routines with error checking.
2   Copyright 1989, 90, 91, 92, 93, 94 Free Software Foundation, Inc.
3
4This file is part of the libiberty library.
5Libiberty is free software; you can redistribute it and/or
6modify it under the terms of the GNU Library General Public
7License as published by the Free Software Foundation; either
8version 2 of the License, or (at your option) any later version.
9
10Libiberty is distributed in the hope that it will be useful,
11but WITHOUT ANY WARRANTY; without even the implied warranty of
12MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
13Library General Public License for more details.
14
15You should have received a copy of the GNU Library General Public
16License along with libiberty; see the file COPYING.LIB.  If
17not, write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
18Boston, MA 02111-1307, USA.  */
19
20#include "ansidecl.h"
21#include "libiberty.h"
22
23#include <stdio.h>
24
25#ifdef __STDC__
26#include <stddef.h>
27#else
28#define size_t unsigned long
29#define ptrdiff_t long
30#endif
31
32#if VMS
33#include <stdlib.h>
34#include <unixlib.h>
35#else
36/* For systems with larger pointers than ints, these must be declared.  */
37PTR malloc PARAMS ((size_t));
38PTR realloc PARAMS ((PTR, size_t));
39PTR calloc PARAMS ((size_t, size_t));
40PTR sbrk PARAMS ((ptrdiff_t));
41#endif
42
43/* The program name if set.  */
44static const char *name = "";
45
46#ifdef HAVE_SBRK
47/* The initial sbrk, set when the program name is set. Not used for win32
48   ports other than cygwin32.  */
49static char *first_break = NULL;
50#endif /* HAVE_SBRK */
51
52void
53xmalloc_set_program_name (s)
54     const char *s;
55{
56  name = s;
57#ifdef HAVE_SBRK
58  /* Win32 ports other than cygwin32 don't have brk() */
59  if (first_break == NULL)
60    first_break = (char *) sbrk (0);
61#endif /* HAVE_SBRK */
62}
63
64PTR
65xmalloc (size)
66    size_t size;
67{
68  PTR newmem;
69
70  if (size == 0)
71    size = 1;
72  newmem = malloc (size);
73  if (!newmem)
74    {
75#ifdef HAVE_SBRK
76      extern char **environ;
77      size_t allocated;
78
79      if (first_break != NULL)
80	allocated = (char *) sbrk (0) - first_break;
81      else
82	allocated = (char *) sbrk (0) - (char *) &environ;
83      fprintf (stderr,
84	       "\n%s%sCan not allocate %lu bytes after allocating %lu bytes\n",
85	       name, *name ? ": " : "",
86	       (unsigned long) size, (unsigned long) allocated);
87#else /* HAVE_SBRK */
88      fprintf (stderr,
89              "\n%s%sCan not allocate %lu bytes\n",
90              name, *name ? ": " : "",
91              (unsigned long) size);
92#endif /* HAVE_SBRK */
93      xexit (1);
94    }
95  return (newmem);
96}
97
98PTR
99xcalloc (nelem, elsize)
100  size_t nelem, elsize;
101{
102  PTR newmem;
103
104  if (nelem == 0 || elsize == 0)
105    nelem = elsize = 1;
106
107  newmem = calloc (nelem, elsize);
108  if (!newmem)
109    {
110#ifdef HAVE_SBRK
111      extern char **environ;
112      size_t allocated;
113
114      if (first_break != NULL)
115	allocated = (char *) sbrk (0) - first_break;
116      else
117	allocated = (char *) sbrk (0) - (char *) &environ;
118      fprintf (stderr,
119	       "\n%s%sCan not allocate %lu bytes after allocating %lu bytes\n",
120	       name, *name ? ": " : "",
121	       (unsigned long) (nelem * elsize), (unsigned long) allocated);
122#else /* HAVE_SBRK */
123      fprintf (stderr,
124              "\n%s%sCan not allocate %lu bytes\n",
125              name, *name ? ": " : "",
126              (unsigned long) (nelem * elsize));
127#endif /* HAVE_SBRK */
128      xexit (1);
129    }
130  return (newmem);
131}
132
133PTR
134xrealloc (oldmem, size)
135    PTR oldmem;
136    size_t size;
137{
138  PTR newmem;
139
140  if (size == 0)
141    size = 1;
142  if (!oldmem)
143    newmem = malloc (size);
144  else
145    newmem = realloc (oldmem, size);
146  if (!newmem)
147    {
148#ifdef HAVE_SBRK
149      extern char **environ;
150      size_t allocated;
151
152      if (first_break != NULL)
153	allocated = (char *) sbrk (0) - first_break;
154      else
155	allocated = (char *) sbrk (0) - (char *) &environ;
156      fprintf (stderr,
157	       "\n%s%sCan not reallocate %lu bytes after allocating %lu bytes\n",
158	       name, *name ? ": " : "",
159	       (unsigned long) size, (unsigned long) allocated);
160#else /* HAVE_SBRK */
161      fprintf (stderr,
162              "\n%s%sCan not reallocate %lu bytes\n",
163              name, *name ? ": " : "",
164              (unsigned long) size);
165#endif /* HAVE_SBRK */
166      xexit (1);
167    }
168  return (newmem);
169}
170