14585130bSYuri Pankov /*
24585130bSYuri Pankov  * Copyright (c) 2008 Otto Moerbeek <otto@drijf.net>
34585130bSYuri Pankov  *
44585130bSYuri Pankov  * Permission to use, copy, modify, and distribute this software for any
54585130bSYuri Pankov  * purpose with or without fee is hereby granted, provided that the above
64585130bSYuri Pankov  * copyright notice and this permission notice appear in all copies.
74585130bSYuri Pankov  *
84585130bSYuri Pankov  * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
94585130bSYuri Pankov  * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
104585130bSYuri Pankov  * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
114585130bSYuri Pankov  * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
124585130bSYuri Pankov  * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
134585130bSYuri Pankov  * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
144585130bSYuri Pankov  * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
154585130bSYuri Pankov  */
164585130bSYuri Pankov 
174585130bSYuri Pankov #include <sys/types.h>
184585130bSYuri Pankov #include <errno.h>
194585130bSYuri Pankov #include <stdint.h>
204585130bSYuri Pankov #include <stdlib.h>
214585130bSYuri Pankov 
224585130bSYuri Pankov /*
234585130bSYuri Pankov  * This is sqrt(SIZE_MAX+1), as s1*s2 <= SIZE_MAX
244585130bSYuri Pankov  * if both s1 < MUL_NO_OVERFLOW and s2 < MUL_NO_OVERFLOW
254585130bSYuri Pankov  */
264585130bSYuri Pankov #define	MUL_NO_OVERFLOW	((size_t)1 << (sizeof (size_t) * 4))
274585130bSYuri Pankov 
284585130bSYuri Pankov void *
reallocarray(void * ptr,size_t nelem,size_t elsize)29*f1cdbd37SYuri Pankov reallocarray(void *ptr, size_t nelem, size_t elsize)
304585130bSYuri Pankov {
31*f1cdbd37SYuri Pankov 	if ((nelem >= MUL_NO_OVERFLOW || elsize >= MUL_NO_OVERFLOW) &&
32*f1cdbd37SYuri Pankov 	    nelem > 0 && SIZE_MAX / nelem < elsize) {
334585130bSYuri Pankov 		errno = ENOMEM;
344585130bSYuri Pankov 		return (NULL);
354585130bSYuri Pankov 	}
36*f1cdbd37SYuri Pankov 	return (realloc(ptr, elsize * nelem));
374585130bSYuri Pankov }
38