本文整理汇总了C++中QualType::isIntegralOrEnumerationType方法的典型用法代码示例。如果您正苦于以下问题:C++ QualType::isIntegralOrEnumerationType方法的具体用法?C++ QualType::isIntegralOrEnumerationType怎么用?C++ QualType::isIntegralOrEnumerationType使用的例子?那么, 这里精选的方法代码示例或许可以为您提供帮助。您也可以进一步了解该方法所在类QualType
的用法示例。
在下文中一共展示了QualType::isIntegralOrEnumerationType方法的13个代码示例,这些例子默认根据受欢迎程度排序。您可以为喜欢或者感觉有用的代码点赞,您的评价将有助于系统推荐出更棒的C++代码示例。
示例1: evalCastFromLoc
SVal SimpleSValBuilder::evalCastFromLoc(Loc val, QualType castTy) {
// Casts from pointers -> pointers, just return the lval.
//
// Casts from pointers -> references, just return the lval. These
// can be introduced by the frontend for corner cases, e.g
// casting from va_list* to __builtin_va_list&.
//
if (Loc::isLocType(castTy) || castTy->isReferenceType())
return val;
// FIXME: Handle transparent unions where a value can be "transparently"
// lifted into a union type.
if (castTy->isUnionType())
return UnknownVal();
if (castTy->isIntegralOrEnumerationType()) {
unsigned BitWidth = Context.getTypeSize(castTy);
if (!val.getAs<loc::ConcreteInt>())
return makeLocAsInteger(val, BitWidth);
llvm::APSInt i = val.castAs<loc::ConcreteInt>().getValue();
BasicVals.getAPSIntType(castTy).apply(i);
return makeIntVal(i);
}
// All other cases: return 'UnknownVal'. This includes casting pointers
// to floats, which is probably badness it itself, but this is a good
// intermediate solution until we do something better.
return UnknownVal();
}
示例2: evalCastFromLoc
SVal SimpleSValBuilder::evalCastFromLoc(Loc val, QualType castTy) {
// Casts from pointers -> pointers, just return the lval.
//
// Casts from pointers -> references, just return the lval. These
// can be introduced by the frontend for corner cases, e.g
// casting from va_list* to __builtin_va_list&.
//
if (Loc::isLocType(castTy) || castTy->isReferenceType())
return val;
// FIXME: Handle transparent unions where a value can be "transparently"
// lifted into a union type.
if (castTy->isUnionType())
return UnknownVal();
// Casting a Loc to a bool will almost always be true,
// unless this is a weak function or a symbolic region.
if (castTy->isBooleanType()) {
switch (val.getSubKind()) {
case loc::MemRegionValKind: {
const MemRegion *R = val.castAs<loc::MemRegionVal>().getRegion();
if (const FunctionCodeRegion *FTR = dyn_cast<FunctionCodeRegion>(R))
if (const FunctionDecl *FD = dyn_cast<FunctionDecl>(FTR->getDecl()))
if (FD->isWeak())
// FIXME: Currently we are using an extent symbol here,
// because there are no generic region address metadata
// symbols to use, only content metadata.
return nonloc::SymbolVal(SymMgr.getExtentSymbol(FTR));
if (const SymbolicRegion *SymR = R->getSymbolicBase())
return nonloc::SymbolVal(SymR->getSymbol());
// FALL-THROUGH
LLVM_FALLTHROUGH;
}
case loc::GotoLabelKind:
// Labels and non-symbolic memory regions are always true.
return makeTruthVal(true, castTy);
}
}
if (castTy->isIntegralOrEnumerationType()) {
unsigned BitWidth = Context.getTypeSize(castTy);
if (!val.getAs<loc::ConcreteInt>())
return makeLocAsInteger(val, BitWidth);
llvm::APSInt i = val.castAs<loc::ConcreteInt>().getValue();
BasicVals.getAPSIntType(castTy).apply(i);
return makeIntVal(i);
}
// All other cases: return 'UnknownVal'. This includes casting pointers
// to floats, which is probably badness it itself, but this is a good
// intermediate solution until we do something better.
return UnknownVal();
}
示例3: makeZeroVal
DefinedOrUnknownSVal SValBuilder::makeZeroVal(QualType type) {
if (Loc::isLocType(type))
return makeNull();
if (type->isIntegralOrEnumerationType())
return makeIntVal(0, type);
// FIXME: Handle floats.
// FIXME: Handle structs.
return UnknownVal();
}
示例4: conjureOffsetSymbolOnLocation
/// \brief Optionally conjure and return a symbol for offset when processing
/// an expression \p Expression.
/// If \p Other is a location, conjure a symbol for \p Symbol
/// (offset) if it is unknown so that memory arithmetic always
/// results in an ElementRegion.
/// \p Count The number of times the current basic block was visited.
static SVal conjureOffsetSymbolOnLocation(
SVal Symbol, SVal Other, Expr* Expression, SValBuilder &svalBuilder,
unsigned Count, const LocationContext *LCtx) {
QualType Ty = Expression->getType();
if (Other.getAs<Loc>() &&
Ty->isIntegralOrEnumerationType() &&
Symbol.isUnknown()) {
return svalBuilder.conjureSymbolVal(Expression, LCtx, Ty, Count);
}
return Symbol;
}
示例5: canSymbolicate
bool SymbolManager::canSymbolicate(QualType T) {
T = T.getCanonicalType();
if (Loc::isLocType(T))
return true;
if (T->isIntegralOrEnumerationType())
return true;
if (T->isRecordType() && !T->isUnionType())
return true;
return false;
}
示例6: makeZeroVal
DefinedOrUnknownSVal SValBuilder::makeZeroVal(QualType type) {
if (Loc::isLocType(type))
return makeNull();
if (type->isIntegralOrEnumerationType())
return makeIntVal(0, type);
if (type->isArrayType() || type->isRecordType() || type->isVectorType() ||
type->isAnyComplexType())
return makeCompoundVal(type, BasicVals.getEmptySValList());
// FIXME: Handle floats.
return UnknownVal();
}
示例7: getSValAsScalarOrLoc
SVal ProgramState::getSValAsScalarOrLoc(const MemRegion *R) const {
// We only want to do fetches from regions that we can actually bind
// values. For example, SymbolicRegions of type 'id<...>' cannot
// have direct bindings (but their can be bindings on their subregions).
if (!R->isBoundable())
return UnknownVal();
if (const TypedValueRegion *TR = dyn_cast<TypedValueRegion>(R)) {
QualType T = TR->getValueType();
if (Loc::isLocType(T) || T->isIntegralOrEnumerationType())
return getSVal(R);
}
return UnknownVal();
}
示例8: assumeSymNE
ProgramStateRef
SimpleConstraintManager::assumeAuxForSymbol(ProgramStateRef State,
SymbolRef Sym, bool Assumption) {
BasicValueFactory &BVF = getBasicVals();
QualType T = Sym->getType();
// None of the constraint solvers currently support non-integer types.
if (!T->isIntegralOrEnumerationType())
return State;
const llvm::APSInt &zero = BVF.getValue(0, T);
if (Assumption)
return assumeSymNE(State, Sym, zero, zero);
else
return assumeSymEQ(State, Sym, zero, zero);
}
示例9: assumeSymNE
ProgramStateRef
RangedConstraintManager::assumeSymUnsupported(ProgramStateRef State,
SymbolRef Sym, bool Assumption) {
BasicValueFactory &BVF = getBasicVals();
QualType T = Sym->getType();
// Non-integer types are not supported.
if (!T->isIntegralOrEnumerationType())
return State;
// Reverse the operation and add directly to state.
const llvm::APSInt &Zero = BVF.getValue(0, T);
if (Assumption)
return assumeSymNE(State, Sym, Zero, Zero);
else
return assumeSymEQ(State, Sym, Zero, Zero);
}
示例10: checkPreStmt
void CFNumberCreateChecker::checkPreStmt(const CallExpr *CE,
CheckerContext &C) const {
ProgramStateRef state = C.getState();
const FunctionDecl *FD = C.getCalleeDecl(CE);
if (!FD)
return;
ASTContext &Ctx = C.getASTContext();
if (!II)
II = &Ctx.Idents.get("CFNumberCreate");
if (FD->getIdentifier() != II || CE->getNumArgs() != 3)
return;
// Get the value of the "theType" argument.
const LocationContext *LCtx = C.getLocationContext();
SVal TheTypeVal = state->getSVal(CE->getArg(1), LCtx);
// FIXME: We really should allow ranges of valid theType values, and
// bifurcate the state appropriately.
Optional<nonloc::ConcreteInt> V = TheTypeVal.getAs<nonloc::ConcreteInt>();
if (!V)
return;
uint64_t NumberKind = V->getValue().getLimitedValue();
Optional<uint64_t> OptTargetSize = GetCFNumberSize(Ctx, NumberKind);
// FIXME: In some cases we can emit an error.
if (!OptTargetSize)
return;
uint64_t TargetSize = *OptTargetSize;
// Look at the value of the integer being passed by reference. Essentially
// we want to catch cases where the value passed in is not equal to the
// size of the type being created.
SVal TheValueExpr = state->getSVal(CE->getArg(2), LCtx);
// FIXME: Eventually we should handle arbitrary locations. We can do this
// by having an enhanced memory model that does low-level typing.
Optional<loc::MemRegionVal> LV = TheValueExpr.getAs<loc::MemRegionVal>();
if (!LV)
return;
const TypedValueRegion* R = dyn_cast<TypedValueRegion>(LV->stripCasts());
if (!R)
return;
QualType T = Ctx.getCanonicalType(R->getValueType());
// FIXME: If the pointee isn't an integer type, should we flag a warning?
// People can do weird stuff with pointers.
if (!T->isIntegralOrEnumerationType())
return;
uint64_t SourceSize = Ctx.getTypeSize(T);
// CHECK: is SourceSize == TargetSize
if (SourceSize == TargetSize)
return;
// Generate an error. Only generate a sink error node
// if 'SourceSize < TargetSize'; otherwise generate a non-fatal error node.
//
// FIXME: We can actually create an abstract "CFNumber" object that has
// the bits initialized to the provided values.
//
ExplodedNode *N = SourceSize < TargetSize ? C.generateErrorNode()
: C.generateNonFatalErrorNode();
if (N) {
SmallString<128> sbuf;
llvm::raw_svector_ostream os(sbuf);
os << (SourceSize == 8 ? "An " : "A ")
<< SourceSize << " bit integer is used to initialize a CFNumber "
"object that represents "
<< (TargetSize == 8 ? "an " : "a ")
<< TargetSize << " bit integer. ";
if (SourceSize < TargetSize)
os << (TargetSize - SourceSize)
<< " bits of the CFNumber value will be garbage." ;
else
os << (SourceSize - TargetSize)
<< " bits of the input integer will be lost.";
if (!BT)
BT.reset(new APIMisuse(this, "Bad use of CFNumberCreate"));
auto report = llvm::make_unique<BugReport>(*BT, os.str(), N);
report->addRange(CE->getArg(2)->getSourceRange());
C.emitReport(std::move(report));
}
}
示例11: evalCast
// FIXME: should rewrite according to the cast kind.
SVal SValBuilder::evalCast(SVal val, QualType castTy, QualType originalTy) {
castTy = Context.getCanonicalType(castTy);
originalTy = Context.getCanonicalType(originalTy);
if (val.isUnknownOrUndef() || castTy == originalTy)
return val;
if (castTy->isBooleanType()) {
if (val.isUnknownOrUndef())
return val;
if (val.isConstant())
return makeTruthVal(!val.isZeroConstant(), castTy);
if (!Loc::isLocType(originalTy) &&
!originalTy->isIntegralOrEnumerationType() &&
!originalTy->isMemberPointerType())
return UnknownVal();
if (SymbolRef Sym = val.getAsSymbol(true)) {
BasicValueFactory &BVF = getBasicValueFactory();
// FIXME: If we had a state here, we could see if the symbol is known to
// be zero, but we don't.
return makeNonLoc(Sym, BO_NE, BVF.getValue(0, Sym->getType()), castTy);
}
// Loc values are not always true, they could be weakly linked functions.
if (Optional<Loc> L = val.getAs<Loc>())
return evalCastFromLoc(*L, castTy);
Loc L = val.castAs<nonloc::LocAsInteger>().getLoc();
return evalCastFromLoc(L, castTy);
}
// For const casts, casts to void, just propagate the value.
if (!castTy->isVariableArrayType() && !originalTy->isVariableArrayType())
if (shouldBeModeledWithNoOp(Context, Context.getPointerType(castTy),
Context.getPointerType(originalTy)))
return val;
// Check for casts from pointers to integers.
if (castTy->isIntegralOrEnumerationType() && Loc::isLocType(originalTy))
return evalCastFromLoc(val.castAs<Loc>(), castTy);
// Check for casts from integers to pointers.
if (Loc::isLocType(castTy) && originalTy->isIntegralOrEnumerationType()) {
if (Optional<nonloc::LocAsInteger> LV = val.getAs<nonloc::LocAsInteger>()) {
if (const MemRegion *R = LV->getLoc().getAsRegion()) {
StoreManager &storeMgr = StateMgr.getStoreManager();
R = storeMgr.castRegion(R, castTy);
return R ? SVal(loc::MemRegionVal(R)) : UnknownVal();
}
return LV->getLoc();
}
return dispatchCast(val, castTy);
}
// Just pass through function and block pointers.
if (originalTy->isBlockPointerType() || originalTy->isFunctionPointerType()) {
assert(Loc::isLocType(castTy));
return val;
}
// Check for casts from array type to another type.
if (const ArrayType *arrayT =
dyn_cast<ArrayType>(originalTy.getCanonicalType())) {
// We will always decay to a pointer.
QualType elemTy = arrayT->getElementType();
val = StateMgr.ArrayToPointer(val.castAs<Loc>(), elemTy);
// Are we casting from an array to a pointer? If so just pass on
// the decayed value.
if (castTy->isPointerType() || castTy->isReferenceType())
return val;
// Are we casting from an array to an integer? If so, cast the decayed
// pointer value to an integer.
assert(castTy->isIntegralOrEnumerationType());
// FIXME: Keep these here for now in case we decide soon that we
// need the original decayed type.
// QualType elemTy = cast<ArrayType>(originalTy)->getElementType();
// QualType pointerTy = C.getPointerType(elemTy);
return evalCastFromLoc(val.castAs<Loc>(), castTy);
}
// Check for casts from a region to a specific type.
if (const MemRegion *R = val.getAsRegion()) {
// Handle other casts of locations to integers.
if (castTy->isIntegralOrEnumerationType())
return evalCastFromLoc(loc::MemRegionVal(R), castTy);
// FIXME: We should handle the case where we strip off view layers to get
// to a desugared type.
if (!Loc::isLocType(castTy)) {
// FIXME: There can be gross cases where one casts the result of a function
// (that returns a pointer) to some other value that happens to fit
// within that pointer value. We currently have no good way to
// model such operations. When this happens, the underlying operation
// is that the caller is reasoning about bits. Conceptually we are
// layering a "view" of a location on top of those bits. Perhaps
// we need to be more lazy about mutual possible views, even on an
// SVal? This may be necessary for bit-level reasoning as well.
return UnknownVal();
//.........这里部分代码省略.........
示例12: SynthesizeSVRInit
//.........这里部分代码省略.........
// 2) object types :
// check existance of copy constructor before call
if (!availableCopyConstructor(desugaredTy, m_Sema))
return E;
// call new (setValueWithAlloc(gCling, &SVR, ETy)) (E)
Call = m_Sema->ActOnCallExpr(/*Scope*/0, m_UnresolvedWithAlloc,
locStart, CallArgs, locEnd);
Expr* placement = Call.take();
if (const ConstantArrayType* constArray
= dyn_cast<ConstantArrayType>(desugaredTy.getTypePtr())) {
CallArgs.clear();
CallArgs.push_back(E);
CallArgs.push_back(placement);
uint64_t arrSize
= m_Context->getConstantArrayElementCount(constArray);
Expr* arrSizeExpr
= utils::Synthesize::IntegerLiteralExpr(*m_Context, arrSize);
CallArgs.push_back(arrSizeExpr);
// 2.1) arrays:
// call copyArray(T* src, void* placement, int size)
Call = m_Sema->ActOnCallExpr(/*Scope*/0, m_UnresolvedCopyArray,
locStart, CallArgs, locEnd);
}
else {
TypeSourceInfo* ETSI
= m_Context->getTrivialTypeSourceInfo(ETy, noLoc);
Call = m_Sema->BuildCXXNew(E->getSourceRange(),
/*useGlobal ::*/true,
/*placementLParen*/ noLoc,
MultiExprArg(placement),
/*placementRParen*/ noLoc,
/*TypeIdParens*/ SourceRange(),
/*allocType*/ ETSI->getType(),
/*allocTypeInfo*/ETSI,
/*arraySize*/0,
/*directInitRange*/E->getSourceRange(),
/*initializer*/E,
/*mayContainAuto*/false
);
}
}
else if (desugaredTy->isIntegralOrEnumerationType()
|| desugaredTy->isReferenceType()
|| desugaredTy->isPointerType()
|| desugaredTy->isFloatingType()) {
if (desugaredTy->isIntegralOrEnumerationType()) {
// 1) enum, integral, float, double, referece, pointer types :
// call to cling::internal::setValueNoAlloc(...);
// If the type is enum or integral we need to force-cast it into
// uint64 in order to pick up the correct overload.
if (desugaredTy->isIntegralOrEnumerationType()) {
QualType UInt64Ty = m_Context->UnsignedLongLongTy;
TypeSourceInfo* TSI
= m_Context->getTrivialTypeSourceInfo(UInt64Ty, noLoc);
Expr* castedE
= m_Sema->BuildCStyleCastExpr(noLoc, TSI, noLoc, E).take();
CallArgs.push_back(castedE);
}
}
else if (desugaredTy->isReferenceType()) {
// we need to get the address of the references
Expr* AddrOfE = m_Sema->BuildUnaryOp(/*Scope*/0, noLoc, UO_AddrOf,
E).take();
CallArgs.push_back(AddrOfE);
}
else if (desugaredTy->isPointerType()) {
// function pointers need explicit void* cast.
QualType VoidPtrTy = m_Context->VoidPtrTy;
TypeSourceInfo* TSI
= m_Context->getTrivialTypeSourceInfo(VoidPtrTy, noLoc);
Expr* castedE
= m_Sema->BuildCStyleCastExpr(noLoc, TSI, noLoc, E).take();
CallArgs.push_back(castedE);
}
else if (desugaredTy->isFloatingType()) {
// floats and double will fall naturally in the correct
// case, because of the overload resolution.
CallArgs.push_back(E);
}
Call = m_Sema->ActOnCallExpr(/*Scope*/0, m_UnresolvedNoAlloc,
locStart, CallArgs, locEnd);
}
else
assert(0 && "Unhandled code path?");
assert(!Call.isInvalid() && "Invalid Call");
// Extend the scope of the temporary cleaner if applicable.
if (Cleanups) {
Cleanups->setSubExpr(Call.take());
Cleanups->setValueKind(Call.take()->getValueKind());
Cleanups->setType(Call.take()->getType());
return Cleanups;
}
return Call.take();
}
示例13: checkPreStmt
void CFNumberChecker::checkPreStmt(const CallExpr *CE,
CheckerContext &C) const {
ProgramStateRef state = C.getState();
const FunctionDecl *FD = C.getCalleeDecl(CE);
if (!FD)
return;
ASTContext &Ctx = C.getASTContext();
if (!ICreate) {
ICreate = &Ctx.Idents.get("CFNumberCreate");
IGetValue = &Ctx.Idents.get("CFNumberGetValue");
}
if (!(FD->getIdentifier() == ICreate || FD->getIdentifier() == IGetValue) ||
CE->getNumArgs() != 3)
return;
// Get the value of the "theType" argument.
SVal TheTypeVal = C.getSVal(CE->getArg(1));
// FIXME: We really should allow ranges of valid theType values, and
// bifurcate the state appropriately.
Optional<nonloc::ConcreteInt> V = TheTypeVal.getAs<nonloc::ConcreteInt>();
if (!V)
return;
uint64_t NumberKind = V->getValue().getLimitedValue();
Optional<uint64_t> OptCFNumberSize = GetCFNumberSize(Ctx, NumberKind);
// FIXME: In some cases we can emit an error.
if (!OptCFNumberSize)
return;
uint64_t CFNumberSize = *OptCFNumberSize;
// Look at the value of the integer being passed by reference. Essentially
// we want to catch cases where the value passed in is not equal to the
// size of the type being created.
SVal TheValueExpr = C.getSVal(CE->getArg(2));
// FIXME: Eventually we should handle arbitrary locations. We can do this
// by having an enhanced memory model that does low-level typing.
Optional<loc::MemRegionVal> LV = TheValueExpr.getAs<loc::MemRegionVal>();
if (!LV)
return;
const TypedValueRegion* R = dyn_cast<TypedValueRegion>(LV->stripCasts());
if (!R)
return;
QualType T = Ctx.getCanonicalType(R->getValueType());
// FIXME: If the pointee isn't an integer type, should we flag a warning?
// People can do weird stuff with pointers.
if (!T->isIntegralOrEnumerationType())
return;
uint64_t PrimitiveTypeSize = Ctx.getTypeSize(T);
if (PrimitiveTypeSize == CFNumberSize)
return;
// FIXME: We can actually create an abstract "CFNumber" object that has
// the bits initialized to the provided values.
ExplodedNode *N = C.generateNonFatalErrorNode();
if (N) {
SmallString<128> sbuf;
llvm::raw_svector_ostream os(sbuf);
bool isCreate = (FD->getIdentifier() == ICreate);
if (isCreate) {
os << (PrimitiveTypeSize == 8 ? "An " : "A ")
<< PrimitiveTypeSize << "-bit integer is used to initialize a "
<< "CFNumber object that represents "
<< (CFNumberSize == 8 ? "an " : "a ")
<< CFNumberSize << "-bit integer; ";
} else {
os << "A CFNumber object that represents "
<< (CFNumberSize == 8 ? "an " : "a ")
<< CFNumberSize << "-bit integer is used to initialize "
<< (PrimitiveTypeSize == 8 ? "an " : "a ")
<< PrimitiveTypeSize << "-bit integer; ";
}
if (PrimitiveTypeSize < CFNumberSize)
os << (CFNumberSize - PrimitiveTypeSize)
<< " bits of the CFNumber value will "
<< (isCreate ? "be garbage." : "overwrite adjacent storage.");
else
os << (PrimitiveTypeSize - CFNumberSize)
<< " bits of the integer value will be "
<< (isCreate ? "lost." : "garbage.");
if (!BT)
BT.reset(new APIMisuse(this, "Bad use of CFNumber APIs"));
auto report = llvm::make_unique<BugReport>(*BT, os.str(), N);
report->addRange(CE->getArg(2)->getSourceRange());
C.emitReport(std::move(report));
}
//.........这里部分代码省略.........