172961230a5890071bcca436eb5630172ce84ec41Andreas Huber/* 272961230a5890071bcca436eb5630172ce84ec41Andreas Huber * Copyright (C) 2010 The Android Open Source Project 372961230a5890071bcca436eb5630172ce84ec41Andreas Huber * 472961230a5890071bcca436eb5630172ce84ec41Andreas Huber * Licensed under the Apache License, Version 2.0 (the "License"); 572961230a5890071bcca436eb5630172ce84ec41Andreas Huber * you may not use this file except in compliance with the License. 672961230a5890071bcca436eb5630172ce84ec41Andreas Huber * You may obtain a copy of the License at 772961230a5890071bcca436eb5630172ce84ec41Andreas Huber * 872961230a5890071bcca436eb5630172ce84ec41Andreas Huber * http://www.apache.org/licenses/LICENSE-2.0 972961230a5890071bcca436eb5630172ce84ec41Andreas Huber * 1072961230a5890071bcca436eb5630172ce84ec41Andreas Huber * Unless required by applicable law or agreed to in writing, software 1172961230a5890071bcca436eb5630172ce84ec41Andreas Huber * distributed under the License is distributed on an "AS IS" BASIS, 1272961230a5890071bcca436eb5630172ce84ec41Andreas Huber * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 1372961230a5890071bcca436eb5630172ce84ec41Andreas Huber * See the License for the specific language governing permissions and 1472961230a5890071bcca436eb5630172ce84ec41Andreas Huber * limitations under the License. 1572961230a5890071bcca436eb5630172ce84ec41Andreas Huber */ 1672961230a5890071bcca436eb5630172ce84ec41Andreas Huber 1772961230a5890071bcca436eb5630172ce84ec41Andreas Huber#ifndef A_BASE_H_ 1872961230a5890071bcca436eb5630172ce84ec41Andreas Huber 1972961230a5890071bcca436eb5630172ce84ec41Andreas Huber#define A_BASE_H_ 2072961230a5890071bcca436eb5630172ce84ec41Andreas Huber 21ec8930f218fa0c1acde631543b40b5a0b28bfe1fGlenn Kasten#ifndef ARRAY_SIZE 22a9522673f3076ea937eb2912945d7ed646ca05dfLajos Molnar#define ARRAY_SIZE(a) (sizeof(a) / sizeof(*(a))) 23ec8930f218fa0c1acde631543b40b5a0b28bfe1fGlenn Kasten#endif 24a9522673f3076ea937eb2912945d7ed646ca05dfLajos Molnar 2572961230a5890071bcca436eb5630172ce84ec41Andreas Huber#define DISALLOW_EVIL_CONSTRUCTORS(name) \ 2672961230a5890071bcca436eb5630172ce84ec41Andreas Huber name(const name &); \ 2772961230a5890071bcca436eb5630172ce84ec41Andreas Huber name &operator=(const name &) 2872961230a5890071bcca436eb5630172ce84ec41Andreas Huber 29d00b7d1fb949e226b189e7d0047d78531b3264daAndy Hung/* Returns true if the size parameter is safe for new array allocation (32-bit) 30d00b7d1fb949e226b189e7d0047d78531b3264daAndy Hung * 31d00b7d1fb949e226b189e7d0047d78531b3264daAndy Hung * Example usage: 32d00b7d1fb949e226b189e7d0047d78531b3264daAndy Hung * 33d00b7d1fb949e226b189e7d0047d78531b3264daAndy Hung * if (!isSafeArraySize<uint32_t>(arraySize)) { 34d00b7d1fb949e226b189e7d0047d78531b3264daAndy Hung * return BAD_VALUE; 35d00b7d1fb949e226b189e7d0047d78531b3264daAndy Hung * } 36d00b7d1fb949e226b189e7d0047d78531b3264daAndy Hung * ... 37d00b7d1fb949e226b189e7d0047d78531b3264daAndy Hung * uint32_t *myArray = new uint32_t[arraySize]; 38d00b7d1fb949e226b189e7d0047d78531b3264daAndy Hung * 39d00b7d1fb949e226b189e7d0047d78531b3264daAndy Hung * There is a bug in gcc versions earlier than 4.8 where the new[] array allocation 40d00b7d1fb949e226b189e7d0047d78531b3264daAndy Hung * will overflow in the internal 32 bit heap allocation, resulting in an 41d00b7d1fb949e226b189e7d0047d78531b3264daAndy Hung * underallocated array. This is a security issue that allows potential overwriting 42d00b7d1fb949e226b189e7d0047d78531b3264daAndy Hung * of other heap data. 43d00b7d1fb949e226b189e7d0047d78531b3264daAndy Hung * 44d00b7d1fb949e226b189e7d0047d78531b3264daAndy Hung * An alternative to checking is to create a safe new array template function which 45d00b7d1fb949e226b189e7d0047d78531b3264daAndy Hung * either throws a std::bad_alloc exception or returns NULL/nullptr_t; NULL considered 46d00b7d1fb949e226b189e7d0047d78531b3264daAndy Hung * safe since normal access of NULL throws an exception. 47d00b7d1fb949e226b189e7d0047d78531b3264daAndy Hung * 48d00b7d1fb949e226b189e7d0047d78531b3264daAndy Hung * https://securityblog.redhat.com/2012/10/31/array-allocation-in-cxx/ 49d00b7d1fb949e226b189e7d0047d78531b3264daAndy Hung */ 50d00b7d1fb949e226b189e7d0047d78531b3264daAndy Hungtemplate <typename T, typename S> 51d00b7d1fb949e226b189e7d0047d78531b3264daAndy Hungbool isSafeArraySize(S size) { 52d00b7d1fb949e226b189e7d0047d78531b3264daAndy Hung return size >= 0 // in case S is signed, ignored if not. 53d00b7d1fb949e226b189e7d0047d78531b3264daAndy Hung && size <= 0xffffffff / sizeof(T); // max-unsigned-32-bit-int / element-size. 54d00b7d1fb949e226b189e7d0047d78531b3264daAndy Hung} 55d00b7d1fb949e226b189e7d0047d78531b3264daAndy Hung 5672961230a5890071bcca436eb5630172ce84ec41Andreas Huber#endif // A_BASE_H_ 57