xref: /openbsd-src/usr.bin/make/memory.c (revision 77c73da267b2f50f6192758e2ab598a649226a74)
1*77c73da2Sespie /* $OpenBSD: memory.c,v 1.11 2014/05/18 08:08:50 espie Exp $ */
2f7923656Sespie 
3f7923656Sespie /*
4f7923656Sespie  * Copyright (c) 1988, 1989, 1990, 1993
5f7923656Sespie  *	The Regents of the University of California.  All rights reserved.
6f7923656Sespie  * Copyright (c) 1989 by Berkeley Softworks
7f7923656Sespie  * All rights reserved.
8f7923656Sespie  *
9f7923656Sespie  * This code is derived from software contributed to Berkeley by
10f7923656Sespie  * Adam de Boor.
11f7923656Sespie  *
12f7923656Sespie  * Redistribution and use in source and binary forms, with or without
13f7923656Sespie  * modification, are permitted provided that the following conditions
14f7923656Sespie  * are met:
15f7923656Sespie  * 1. Redistributions of source code must retain the above copyright
16f7923656Sespie  *    notice, this list of conditions and the following disclaimer.
17f7923656Sespie  * 2. Redistributions in binary form must reproduce the above copyright
18f7923656Sespie  *    notice, this list of conditions and the following disclaimer in the
19f7923656Sespie  *    documentation and/or other materials provided with the distribution.
20f75387cbSmillert  * 3. Neither the name of the University nor the names of its contributors
21f7923656Sespie  *    may be used to endorse or promote products derived from this software
22f7923656Sespie  *    without specific prior written permission.
23f7923656Sespie  *
24f7923656Sespie  * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
25f7923656Sespie  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
26f7923656Sespie  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
27f7923656Sespie  * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
28f7923656Sespie  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
29f7923656Sespie  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
30f7923656Sespie  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
31f7923656Sespie  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
32f7923656Sespie  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
33f7923656Sespie  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
34f7923656Sespie  * SUCH DAMAGE.
35f7923656Sespie  */
36f7923656Sespie 
37f7923656Sespie #include <sys/types.h>
38f7923656Sespie #include <sys/stat.h>
39f7923656Sespie #include <errno.h>
401f89b472Sespie #include <stddef.h>
411f89b472Sespie #include <stdint.h>
42f7923656Sespie #include <stdio.h>
43f7923656Sespie #include <stdlib.h>
44f7923656Sespie #include <string.h>
45f7923656Sespie #include <unistd.h>
46ff4f28c0Sespie #include <ohash.h>
47f7923656Sespie #include "defines.h"
48f7923656Sespie #include "memory.h"
49f7923656Sespie 
50f7923656Sespie static void enomem(size_t);
51f46d747cSespie static void enocmem(size_t, size_t);
52f7923656Sespie 
53f7923656Sespie /*
54f7923656Sespie  * emalloc --
55f7923656Sespie  *	malloc, but die on error.
56f7923656Sespie  */
57f7923656Sespie void *
emalloc(size_t size)58ad2b054bSespie emalloc(size_t size)
59f7923656Sespie {
60f7923656Sespie 	void *p;
61f7923656Sespie 
62ad2b054bSespie 	if ((p = malloc(size)) == NULL)
63ad2b054bSespie 		enomem(size);
64f7923656Sespie 	return p;
65f7923656Sespie }
66f7923656Sespie 
67f7923656Sespie /*
68f7923656Sespie  * estrdup --
69f7923656Sespie  *	strdup, but die on error.
70f7923656Sespie  */
71f7923656Sespie char *
estrdup(const char * str)72ad2b054bSespie estrdup(const char *str)
73f7923656Sespie {
74f7923656Sespie 	char *p;
75f7923656Sespie 	size_t size;
76f7923656Sespie 
77f7923656Sespie 	size = strlen(str) + 1;
78f7923656Sespie 
79f7923656Sespie 	p = emalloc(size);
80f7923656Sespie 	memcpy(p, str, size);
81f7923656Sespie 	return p;
82f7923656Sespie }
83f7923656Sespie 
84f7923656Sespie /*
85f7923656Sespie  * erealloc --
86f7923656Sespie  *	realloc, but die on error.
87f7923656Sespie  */
88f7923656Sespie void *
erealloc(void * ptr,size_t size)89ad2b054bSespie erealloc(void *ptr, size_t size)
90f7923656Sespie {
91f7923656Sespie 	if ((ptr = realloc(ptr, size)) == NULL)
92f7923656Sespie 		enomem(size);
93f7923656Sespie 	return ptr;
94f7923656Sespie }
95f7923656Sespie 
96f7923656Sespie void *
ereallocarray(void * ptr,size_t s1,size_t s2)97e2ff9f51Sespie ereallocarray(void *ptr, size_t s1, size_t s2)
98f46d747cSespie {
99e2ff9f51Sespie 	if ((ptr = reallocarray(ptr, s1, s2)) == NULL)
100f46d747cSespie 		enocmem(s1, s2);
101f46d747cSespie 	return ptr;
102f46d747cSespie }
103f46d747cSespie 
104f7923656Sespie /* Support routines for hash tables.  */
105f7923656Sespie void *
hash_calloc(size_t n,size_t s,void * u UNUSED)106e2ff9f51Sespie hash_calloc(size_t n, size_t s, void *u UNUSED)
107f7923656Sespie {
108*77c73da2Sespie 	void *p;
109*77c73da2Sespie 
110*77c73da2Sespie 	if ((p = calloc(n, s)) == NULL)
111*77c73da2Sespie 		enocmem(n, s);
112*77c73da2Sespie 	return p;
113f7923656Sespie }
114f7923656Sespie 
115f7923656Sespie void
hash_free(void * p,void * u UNUSED)116e2ff9f51Sespie hash_free(void *p, void *u UNUSED)
117f7923656Sespie {
118f7923656Sespie 	free(p);
119f7923656Sespie }
120f7923656Sespie 
121f7923656Sespie void *
element_alloc(size_t s,void * u UNUSED)122ad2b054bSespie element_alloc(size_t s, void *u UNUSED)
123f7923656Sespie {
124f7923656Sespie 	return emalloc(s);
125f7923656Sespie }
126f7923656Sespie 
127f7923656Sespie 
128f7923656Sespie 
129f7923656Sespie /*
130f7923656Sespie  * enomem --
131f7923656Sespie  *	die when out of memory.
132f7923656Sespie  */
133f7923656Sespie void
enomem(size_t size)134ad2b054bSespie enomem(size_t size)
135f7923656Sespie {
136f46d747cSespie 	fprintf(stderr, "make: %s (%zu)\n", strerror(errno), size);
137f7923656Sespie 	exit(2);
138f7923656Sespie }
139f7923656Sespie 
140f46d747cSespie void
enocmem(size_t sz1,size_t sz2)141f46d747cSespie enocmem(size_t sz1, size_t sz2)
142f46d747cSespie {
143f46d747cSespie 	fprintf(stderr, "make: %s (%zu * %zu)\n", strerror(errno), sz1, sz2);
144f46d747cSespie 	exit(2);
145f46d747cSespie }
146f7923656Sespie /*
147f7923656Sespie  * esetenv --
148f7923656Sespie  *	change environment, die on error.
149f7923656Sespie  */
150f7923656Sespie void
esetenv(const char * name,const char * value)151ad2b054bSespie esetenv(const char *name, const char *value)
152f7923656Sespie {
153f7923656Sespie 	if (setenv(name, value, 1) == 0)
154f7923656Sespie 	    return;
155f7923656Sespie 
156f7923656Sespie 	fprintf(stderr, "make: setenv failed (%s)\n", strerror(errno));
157f7923656Sespie 	exit(2);
158f7923656Sespie }
159f7923656Sespie 
160f7923656Sespie 
161f7923656Sespie /*
162f7923656Sespie  * enunlink --
163f7923656Sespie  *	Remove a file carefully, avoiding directories.
164f7923656Sespie  */
165f7923656Sespie int
eunlink(const char * file)166ad2b054bSespie eunlink(const char *file)
167f7923656Sespie {
168f7923656Sespie 	struct stat st;
169f7923656Sespie 
170f7923656Sespie 	if (lstat(file, &st) == -1)
171f7923656Sespie 		return -1;
172f7923656Sespie 
173f7923656Sespie 	if (S_ISDIR(st.st_mode)) {
174f7923656Sespie 		errno = EISDIR;
175f7923656Sespie 		return -1;
176f7923656Sespie 	}
177f7923656Sespie 	return unlink(file);
178f7923656Sespie }
179f7923656Sespie 
180ff4f28c0Sespie void
free_hash(struct ohash * h)181ff4f28c0Sespie free_hash(struct ohash *h)
182ff4f28c0Sespie {
183ff4f28c0Sespie 	void *e;
184ff4f28c0Sespie 	unsigned int i;
185ff4f28c0Sespie 
186ff4f28c0Sespie 	for (e = ohash_first(h, &i); e != NULL; e = ohash_next(h, &i))
187ff4f28c0Sespie 		free(e);
188ff4f28c0Sespie 	ohash_delete(h);
189ff4f28c0Sespie }
190ff4f28c0Sespie 
191