Index: include/clang/StaticAnalyzer/Core/PathSensitive/SValBuilder.h =================================================================== --- include/clang/StaticAnalyzer/Core/PathSensitive/SValBuilder.h +++ include/clang/StaticAnalyzer/Core/PathSensitive/SValBuilder.h @@ -86,7 +86,7 @@ ProgramStateManager &stateMgr) : Context(context), BasicVals(context, alloc), SymMgr(context, BasicVals, alloc), MemMgr(context, alloc), - StateMgr(stateMgr), ArrayIndexTy(context.LongLongTy), + StateMgr(stateMgr), ArrayIndexTy(context.getSignedSizeType()), ArrayIndexWidth(context.getTypeSize(ArrayIndexTy)) {} virtual ~SValBuilder() = default; Index: lib/StaticAnalyzer/Core/ProgramState.cpp =================================================================== --- lib/StaticAnalyzer/Core/ProgramState.cpp +++ lib/StaticAnalyzer/Core/ProgramState.cpp @@ -336,9 +336,8 @@ // Get the offset: the minimum value of the array index type. BasicValueFactory &BVF = svalBuilder.getBasicValueFactory(); - // FIXME: This should be using ValueManager::ArrayindexTy...somehow. if (indexTy.isNull()) - indexTy = Ctx.IntTy; + indexTy = svalBuilder.getArrayIndexType(); nonloc::ConcreteInt Min(BVF.getMinValue(indexTy)); // Adjust the index. Index: lib/StaticAnalyzer/Core/RegionStore.cpp =================================================================== --- lib/StaticAnalyzer/Core/RegionStore.cpp +++ lib/StaticAnalyzer/Core/RegionStore.cpp @@ -1341,7 +1341,8 @@ // If a variable is reinterpreted as a type that doesn't fit into a larger // type evenly, round it down. // This is a signed value, since it's used in arithmetic with signed indices. - return svalBuilder.makeIntVal(RegionSize / EleSize, false); + return svalBuilder.makeIntVal(RegionSize / EleSize, + svalBuilder.getArrayIndexType()); } //===----------------------------------------------------------------------===// Index: test/Analysis/index-type.c =================================================================== --- test/Analysis/index-type.c +++ test/Analysis/index-type.c @@ -6,15 +6,34 @@ #ifdef M32 -#define X86_ARRAY_SIZE (UINT_MAX/2 + 4) +#define X86_ARRAY_SIZE (UINT_MAX/4 + 4) void testIndexTooBig() { char arr[X86_ARRAY_SIZE]; - char *ptr = arr + UINT_MAX/2; + char *ptr = arr + UINT_MAX/4; ptr += 2; // index shouldn't overflow *ptr = 42; // no-warning } +#define SIZE 4294967296 + +static unsigned size; +static void * addr; +static unsigned buf[SIZE]; + +void testOutOfBounds() { + // not out of bounds + buf[SIZE-1] = 1; // no-warning +} + +void testOutOfBoundsCopy1() { + memcpy(buf, addr, size); // no-warning +} + +void testOutOfBoundsCopy2() { + memcpy(addr, buf, size); // no-warning +} + #else // 64-bit tests #define ARRAY_SIZE 0x100000000