Index: include/clang/StaticAnalyzer/Core/PathSensitive/MemRegion.h =================================================================== --- include/clang/StaticAnalyzer/Core/PathSensitive/MemRegion.h +++ include/clang/StaticAnalyzer/Core/PathSensitive/MemRegion.h @@ -962,7 +962,10 @@ CXXThisRegion(const PointerType *thisPointerTy, const StackArgumentsSpaceRegion *sReg) : TypedValueRegion(sReg, CXXThisRegionKind), - ThisPointerTy(thisPointerTy) {} + ThisPointerTy(thisPointerTy) { + assert(ThisPointerTy->getPointeeType()->getAsCXXRecordDecl() && + "Invalid region type!"); + } static void ProfileRegion(llvm::FoldingSetNodeID &ID, const PointerType *PT, @@ -1076,6 +1079,8 @@ assert((!Idx.getAs() || Idx.castAs().getValue().isSigned()) && "The index must be signed"); + assert(!elementType.isNull() && !elementType->isVoidType() && + "Invalid region type!"); } static void ProfileRegion(llvm::FoldingSetNodeID& ID, QualType elementType, Index: lib/StaticAnalyzer/Core/ExprEngine.cpp =================================================================== --- lib/StaticAnalyzer/Core/ExprEngine.cpp +++ lib/StaticAnalyzer/Core/ExprEngine.cpp @@ -2209,9 +2209,17 @@ ProgramStateRef state = Node->getState(); if (IsGLValueLike) { - SVal V = state->getLValue(A->getType(), - state->getSVal(Idx, LCtx), - state->getSVal(Base, LCtx)); + QualType T = A->getType(); + + // One of the forbidden LValue types! We still need to have sensible + // symbolic locations to represent this stuff. Note that arithmetic on + // void pointers is a GCC extension. + if (T->isVoidType()) + T = getContext().CharTy; + + SVal V = state->getLValue(T, + state->getSVal(Idx, LCtx), + state->getSVal(Base, LCtx)); Bldr.generateNode(A, Node, state->BindExpr(A, LCtx, V), nullptr, ProgramPoint::PostLValueKind); } else if (IsVectorType) { Index: lib/StaticAnalyzer/Core/SimpleSValBuilder.cpp =================================================================== --- lib/StaticAnalyzer/Core/SimpleSValBuilder.cpp +++ lib/StaticAnalyzer/Core/SimpleSValBuilder.cpp @@ -988,6 +988,12 @@ elementType = resultTy->getPointeeType(); } + // Represent arithmetic on void pointers as arithmetic on char pointers. + // It is fine when a TypedValueRegion of char value type represents + // a void pointer. Note that arithmetic on void pointers is a GCC extension. + if (elementType->isVoidType()) + elementType = getContext().CharTy; + if (Optional indexV = index.getAs()) { return loc::MemRegionVal(MemMgr.getElementRegion(elementType, *indexV, superR, getContext()));