annotate src/flac-1.2.1/include/share/alloc.h @ 89:8a15ff55d9af

Add bzip2, zlib, liblo, portaudio sources
author Chris Cannam <cannam@all-day-breakfast.com>
date Wed, 20 Mar 2013 13:59:52 +0000
parents 98c1576536ae
children
rev   line source
cannam@86 1 /* alloc - Convenience routines for safely allocating memory
cannam@86 2 * Copyright (C) 2007 Josh Coalson
cannam@86 3 *
cannam@86 4 * This library is free software; you can redistribute it and/or
cannam@86 5 * modify it under the terms of the GNU Lesser General Public
cannam@86 6 * License as published by the Free Software Foundation; either
cannam@86 7 * version 2.1 of the License, or (at your option) any later version.
cannam@86 8 *
cannam@86 9 * This library is distributed in the hope that it will be useful,
cannam@86 10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
cannam@86 11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
cannam@86 12 * Lesser General Public License for more details.
cannam@86 13 *
cannam@86 14 * You should have received a copy of the GNU Lesser General Public
cannam@86 15 * License along with this library; if not, write to the Free Software
cannam@86 16 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
cannam@86 17 */
cannam@86 18
cannam@86 19 #ifndef FLAC__SHARE__ALLOC_H
cannam@86 20 #define FLAC__SHARE__ALLOC_H
cannam@86 21
cannam@86 22 #if HAVE_CONFIG_H
cannam@86 23 # include <config.h>
cannam@86 24 #endif
cannam@86 25
cannam@86 26 /* WATCHOUT: for c++ you may have to #define __STDC_LIMIT_MACROS 1 real early
cannam@86 27 * before #including this file, otherwise SIZE_MAX might not be defined
cannam@86 28 */
cannam@86 29
cannam@86 30 #include <limits.h> /* for SIZE_MAX */
cannam@89 31 #if !defined _MSC_VER && !defined __EMX__
cannam@86 32 #include <stdint.h> /* for SIZE_MAX in case limits.h didn't get it */
cannam@86 33 #endif
cannam@86 34 #include <stdlib.h> /* for size_t, malloc(), etc */
cannam@86 35
cannam@86 36 #ifndef SIZE_MAX
cannam@86 37 # ifndef SIZE_T_MAX
cannam@86 38 # ifdef _MSC_VER
cannam@86 39 # define SIZE_T_MAX UINT_MAX
cannam@86 40 # else
cannam@86 41 # error
cannam@86 42 # endif
cannam@86 43 # endif
cannam@86 44 # define SIZE_MAX SIZE_T_MAX
cannam@86 45 #endif
cannam@86 46
cannam@86 47 #ifndef FLaC__INLINE
cannam@86 48 #define FLaC__INLINE
cannam@86 49 #endif
cannam@86 50
cannam@86 51 /* avoid malloc()ing 0 bytes, see:
cannam@86 52 * https://www.securecoding.cert.org/confluence/display/seccode/MEM04-A.+Do+not+make+assumptions+about+the+result+of+allocating+0+bytes?focusedCommentId=5407003
cannam@86 53 */
cannam@86 54 static FLaC__INLINE void *safe_malloc_(size_t size)
cannam@86 55 {
cannam@86 56 /* malloc(0) is undefined; FLAC src convention is to always allocate */
cannam@86 57 if(!size)
cannam@86 58 size++;
cannam@86 59 return malloc(size);
cannam@86 60 }
cannam@86 61
cannam@86 62 static FLaC__INLINE void *safe_calloc_(size_t nmemb, size_t size)
cannam@86 63 {
cannam@86 64 if(!nmemb || !size)
cannam@86 65 return malloc(1); /* malloc(0) is undefined; FLAC src convention is to always allocate */
cannam@86 66 return calloc(nmemb, size);
cannam@86 67 }
cannam@86 68
cannam@86 69 /*@@@@ there's probably a better way to prevent overflows when allocating untrusted sums but this works for now */
cannam@86 70
cannam@86 71 static FLaC__INLINE void *safe_malloc_add_2op_(size_t size1, size_t size2)
cannam@86 72 {
cannam@86 73 size2 += size1;
cannam@86 74 if(size2 < size1)
cannam@86 75 return 0;
cannam@86 76 return safe_malloc_(size2);
cannam@86 77 }
cannam@86 78
cannam@86 79 static FLaC__INLINE void *safe_malloc_add_3op_(size_t size1, size_t size2, size_t size3)
cannam@86 80 {
cannam@86 81 size2 += size1;
cannam@86 82 if(size2 < size1)
cannam@86 83 return 0;
cannam@86 84 size3 += size2;
cannam@86 85 if(size3 < size2)
cannam@86 86 return 0;
cannam@86 87 return safe_malloc_(size3);
cannam@86 88 }
cannam@86 89
cannam@86 90 static FLaC__INLINE void *safe_malloc_add_4op_(size_t size1, size_t size2, size_t size3, size_t size4)
cannam@86 91 {
cannam@86 92 size2 += size1;
cannam@86 93 if(size2 < size1)
cannam@86 94 return 0;
cannam@86 95 size3 += size2;
cannam@86 96 if(size3 < size2)
cannam@86 97 return 0;
cannam@86 98 size4 += size3;
cannam@86 99 if(size4 < size3)
cannam@86 100 return 0;
cannam@86 101 return safe_malloc_(size4);
cannam@86 102 }
cannam@86 103
cannam@86 104 static FLaC__INLINE void *safe_malloc_mul_2op_(size_t size1, size_t size2)
cannam@86 105 #if 0
cannam@86 106 needs support for cases where sizeof(size_t) != 4
cannam@86 107 {
cannam@86 108 /* could be faster #ifdef'ing off SIZEOF_SIZE_T */
cannam@86 109 if(sizeof(size_t) == 4) {
cannam@86 110 if ((double)size1 * (double)size2 < 4294967296.0)
cannam@86 111 return malloc(size1*size2);
cannam@86 112 }
cannam@86 113 return 0;
cannam@86 114 }
cannam@86 115 #else
cannam@86 116 /* better? */
cannam@86 117 {
cannam@86 118 if(!size1 || !size2)
cannam@86 119 return malloc(1); /* malloc(0) is undefined; FLAC src convention is to always allocate */
cannam@86 120 if(size1 > SIZE_MAX / size2)
cannam@86 121 return 0;
cannam@86 122 return malloc(size1*size2);
cannam@86 123 }
cannam@86 124 #endif
cannam@86 125
cannam@86 126 static FLaC__INLINE void *safe_malloc_mul_3op_(size_t size1, size_t size2, size_t size3)
cannam@86 127 {
cannam@86 128 if(!size1 || !size2 || !size3)
cannam@86 129 return malloc(1); /* malloc(0) is undefined; FLAC src convention is to always allocate */
cannam@86 130 if(size1 > SIZE_MAX / size2)
cannam@86 131 return 0;
cannam@86 132 size1 *= size2;
cannam@86 133 if(size1 > SIZE_MAX / size3)
cannam@86 134 return 0;
cannam@86 135 return malloc(size1*size3);
cannam@86 136 }
cannam@86 137
cannam@86 138 /* size1*size2 + size3 */
cannam@86 139 static FLaC__INLINE void *safe_malloc_mul2add_(size_t size1, size_t size2, size_t size3)
cannam@86 140 {
cannam@86 141 if(!size1 || !size2)
cannam@86 142 return safe_malloc_(size3);
cannam@86 143 if(size1 > SIZE_MAX / size2)
cannam@86 144 return 0;
cannam@86 145 return safe_malloc_add_2op_(size1*size2, size3);
cannam@86 146 }
cannam@86 147
cannam@86 148 /* size1 * (size2 + size3) */
cannam@86 149 static FLaC__INLINE void *safe_malloc_muladd2_(size_t size1, size_t size2, size_t size3)
cannam@86 150 {
cannam@86 151 if(!size1 || (!size2 && !size3))
cannam@86 152 return malloc(1); /* malloc(0) is undefined; FLAC src convention is to always allocate */
cannam@86 153 size2 += size3;
cannam@86 154 if(size2 < size3)
cannam@86 155 return 0;
cannam@86 156 return safe_malloc_mul_2op_(size1, size2);
cannam@86 157 }
cannam@86 158
cannam@86 159 static FLaC__INLINE void *safe_realloc_add_2op_(void *ptr, size_t size1, size_t size2)
cannam@86 160 {
cannam@86 161 size2 += size1;
cannam@86 162 if(size2 < size1)
cannam@86 163 return 0;
cannam@86 164 return realloc(ptr, size2);
cannam@86 165 }
cannam@86 166
cannam@86 167 static FLaC__INLINE void *safe_realloc_add_3op_(void *ptr, size_t size1, size_t size2, size_t size3)
cannam@86 168 {
cannam@86 169 size2 += size1;
cannam@86 170 if(size2 < size1)
cannam@86 171 return 0;
cannam@86 172 size3 += size2;
cannam@86 173 if(size3 < size2)
cannam@86 174 return 0;
cannam@86 175 return realloc(ptr, size3);
cannam@86 176 }
cannam@86 177
cannam@86 178 static FLaC__INLINE void *safe_realloc_add_4op_(void *ptr, size_t size1, size_t size2, size_t size3, size_t size4)
cannam@86 179 {
cannam@86 180 size2 += size1;
cannam@86 181 if(size2 < size1)
cannam@86 182 return 0;
cannam@86 183 size3 += size2;
cannam@86 184 if(size3 < size2)
cannam@86 185 return 0;
cannam@86 186 size4 += size3;
cannam@86 187 if(size4 < size3)
cannam@86 188 return 0;
cannam@86 189 return realloc(ptr, size4);
cannam@86 190 }
cannam@86 191
cannam@86 192 static FLaC__INLINE void *safe_realloc_mul_2op_(void *ptr, size_t size1, size_t size2)
cannam@86 193 {
cannam@86 194 if(!size1 || !size2)
cannam@86 195 return realloc(ptr, 0); /* preserve POSIX realloc(ptr, 0) semantics */
cannam@86 196 if(size1 > SIZE_MAX / size2)
cannam@86 197 return 0;
cannam@86 198 return realloc(ptr, size1*size2);
cannam@86 199 }
cannam@86 200
cannam@86 201 /* size1 * (size2 + size3) */
cannam@86 202 static FLaC__INLINE void *safe_realloc_muladd2_(void *ptr, size_t size1, size_t size2, size_t size3)
cannam@86 203 {
cannam@86 204 if(!size1 || (!size2 && !size3))
cannam@86 205 return realloc(ptr, 0); /* preserve POSIX realloc(ptr, 0) semantics */
cannam@86 206 size2 += size3;
cannam@86 207 if(size2 < size3)
cannam@86 208 return 0;
cannam@86 209 return safe_realloc_mul_2op_(ptr, size1, size2);
cannam@86 210 }
cannam@86 211
cannam@86 212 #endif