llvm::BumpPtrAllocator *Allocator;
};
-
} // end namespace til
} // end namespace threadSafety
} // end namespace clang
-
inline void *operator new(size_t Sz,
clang::threadSafety::til::MemRegionRef &R) {
return R.allocate(Sz);
}
-
namespace clang {
namespace threadSafety {
namespace til {
-
// A simple fixed size array class that does not manage its own memory,
// suitable for use with bump pointer allocation.
template <class T> class SimpleArray {
Data = A.allocateT<T>(Ncp);
Capacity = Ncp;
memcpy(Data, Odata, sizeof(T) * Size);
- return;
}
// Reserve space for at least N more items.
size_t Capacity;
};
-
} // end namespace til
-
// A copy on write vector.
// The vector can be in one of three states:
// * invalid -- no operations are permitted.
VectorData *Data;
};
-
inline std::ostream& operator<<(std::ostream& ss, const StringRef str) {
return ss.write(str.data(), str.size());
}
-
} // end namespace threadSafety
} // end namespace clang
-#endif // LLVM_CLANG_THREAD_SAFETY_UTIL_H
+#endif // LLVM_CLANG_THREAD_SAFETY_UTIL_H
}
};
-}
+} // end anonymous namespace
ObjCMigrateAction::ObjCMigrateAction(
std::unique_ptr<FrontendAction> WrappedAction,
}
return true;
}
-
class ObjCMigrator : public RecursiveASTVisitor<ObjCMigrator> {
ObjCMigrateASTConsumer &Consumer;
return true;
}
};
-}
+} // end anonymous namespace
void ObjCMigrateASTConsumer::migrateDecl(Decl *D) {
if (!D)
versionsMatch(Deprecated1, Deprecated2) &&
versionsMatch(Obsoleted1, Obsoleted2) &&
IsUnavailable1 == IsUnavailable2);
-
}
static bool MatchTwoAttributeLists(const AttrVec &Attrs1, const AttrVec &Attrs2,
}
}
-
ObjCMigrateASTConsumer::CF_BRIDGING_KIND
ObjCMigrateASTConsumer::migrateAddFunctionAnnotation(
ASTContext &Ctx,
return;
}
}
- return;
}
namespace {
return true;
}
};
-} // anonymous namespace
+} // end anonymous namespace
static bool hasSuperInitCall(const ObjCMethodDecl *MD) {
return !SuperInitChecker().TraverseStmt(MD->getBody());
}
};
-}
+} // end anonymous namespace
void ObjCMigrateASTConsumer::HandleTranslationUnit(ASTContext &Ctx) {
EditEntry() : File(), Offset(), RemoveLen() {}
};
-}
+} // end anonymous namespace
namespace llvm {
template<> struct DenseMapInfo<EditEntry> {
LHS.Text == RHS.Text;
}
};
-}
+} // end namespace llvm
namespace {
class RemapFileParser {
Entries.push_back(Entry);
}
};
-}
+} // end anonymous namespace
static bool reportDiag(const Twine &Err, DiagnosticsEngine &Diag) {
Diag.Report(Diag.getCustomDiagID(DiagnosticsEngine::Error, "%0"))
// This file implements a diagnostic formatting hook for AST elements.
//
//===----------------------------------------------------------------------===//
+
#include "clang/AST/ASTDiagnostic.h"
#include "clang/AST/ASTContext.h"
#include "clang/AST/ASTLambda.h"
NeedQuotes = false;
break;
}
-
}
if (NeedQuotes) {
Unbold();
OS << "]";
}
- return;
}
/// PrintExpr - Prints out the expr template arguments, highlighting argument
Unbold();
OS << ']';
}
-
}
/// PrintValueDeclAndInteger - Uses the print functions for ValueDecl and
return true;
}
}; // end class TemplateDiff
-} // end namespace
+} // end anonymous namespace
/// FormatTemplateTypeDiff - A helper static function to start the template
/// diff and return the properly formatted string. Returns true if the diff
+//===--- CommentLexer.cpp -------------------------------------------------===//
+//
+// The LLVM Compiler Infrastructure
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
#include "clang/AST/CommentLexer.h"
#include "clang/AST/CommentCommandTraits.h"
#include "clang/AST/CommentDiagnostic.h"
#include "clang/AST/CommentHTMLTags.inc"
#include "clang/AST/CommentHTMLNamedCharacterReferences.inc"
-} // unnamed namespace
+} // end anonymous namespace
StringRef Lexer::resolveHTMLNamedCharacterReference(StringRef Name) const {
// Fast path, first check a few most widely used named character references.
llvm_unreachable("buffer end hit before '*/' was seen");
}
-} // unnamed namespace
+} // end anonymous namespace
void Lexer::formTokenWithChars(Token &Result, const char *TokEnd,
tok::TokenKind Kind) {
setupAndLexHTMLEndTag(T);
else
formTextToken(T, TokenPtr);
-
return;
}
}
formTokenWithChars(T, TokenPtr, tok::text);
T.setText(Resolved);
- return;
}
void Lexer::setupAndLexHTMLStartTag(Token &T) {
} // end namespace comments
} // end namespace clang
-
namespace {
#include "clang/AST/CommentHTMLTagsProperties.inc"
-} // unnamed namespace
+} // end anonymous namespace
Sema::Sema(llvm::BumpPtrAllocator &Allocator, const SourceManager &SourceMgr,
DiagnosticsEngine &Diags, CommandTraits &Traits,
<< CorrectedName
<< FixItHint::CreateReplacement(ArgRange, CorrectedName);
}
-
- return;
}
void Sema::actOnTParamCommandFinish(TParamCommandComment *Command,
BestIndex = CurrIndex;
}
}
-} // unnamed namespace
+} // end anonymous namespace
unsigned Sema::correctTypoInParmVarReference(
StringRef Typo,
}
return false;
}
-} // unnamed namespace
+} // end anonymous namespace
bool Sema::resolveTParamReference(
StringRef Name,
Corrector);
}
}
-} // unnamed namespace
+} // end anonymous namespace
StringRef Sema::correctTypoInTParamReference(
StringRef Typo,
} // end namespace comments
} // end namespace clang
-
CodeGenFunction &CGF;
SanitizerSet OldSanOpts;
};
-}
+} // end anonymous namespace
namespace {
class FieldMemcpyizer {
const CXXRecordDecl *ClassDecl;
private:
-
void emitMemcpyIR(Address DestPtr, Address SrcPtr, CharUnits Size) {
llvm::PointerType *DPT = DestPtr.getType();
llvm::Type *DBP =
}
void addInitialField(FieldDecl *F) {
- FirstField = F;
- LastField = F;
- FirstFieldOffset = RecLayout.getFieldOffset(F->getFieldIndex());
- LastFieldOffset = FirstFieldOffset;
- LastAddedFieldIndex = F->getFieldIndex();
- return;
- }
+ FirstField = F;
+ LastField = F;
+ FirstFieldOffset = RecLayout.getFieldOffset(F->getFieldIndex());
+ LastFieldOffset = FirstFieldOffset;
+ LastAddedFieldIndex = F->getFieldIndex();
+ }
void addNextField(FieldDecl *F) {
// For the most part, the following invariant will hold:
class ConstructorMemcpyizer : public FieldMemcpyizer {
private:
-
/// Get source argument for copy constructor. Returns null if not a copy
/// constructor.
static const VarDecl *getTrivialCopySource(CodeGenFunction &CGF,
class AssignmentMemcpyizer : public FieldMemcpyizer {
private:
-
// Returns the memcpyable field copied by the given statement, if one
// exists. Otherwise returns null.
FieldDecl *getMemcpyableField(Stmt *S) {
SmallVector<Stmt*, 16> AggregatedStmts;
public:
-
AssignmentMemcpyizer(CodeGenFunction &CGF, const CXXMethodDecl *AD,
FunctionArgList &Args)
: FieldMemcpyizer(CGF, AD->getParent(), Args[Args.size() - 1]),
struct CallDtorDeleteConditional final : EHScopeStack::Cleanup {
llvm::Value *ShouldDeleteCondition;
+
public:
CallDtorDeleteConditional(llvm::Value *ShouldDeleteCondition)
: ShouldDeleteCondition(ShouldDeleteCondition) {
/*Delegating=*/false, Addr);
}
};
-}
+} // end anonymous namespace
void CodeGenFunction::PushDestructorCleanup(const CXXDestructorDecl *D,
Address Addr) {
#include "llvm/IR/GlobalVariable.h"
#include "llvm/IR/Intrinsics.h"
#include "llvm/IR/Type.h"
+
using namespace clang;
using namespace CodeGen;
-
void CodeGenFunction::EmitDecl(const Decl &D) {
switch (D.getKind()) {
case Decl::BuiltinTemplate:
CGF.EmitLifetimeEnd(Size, Addr);
}
};
-}
+} // end anonymous namespace
/// EmitAutoVarWithLifetime - Does the setup required for an automatic
/// variable with lifetime.
}
init = castExpr->getSubExpr();
- continue;
}
return false;
}
}
}
-
/// shouldUseMemSetPlusStoresToInitialize - Decide whether we should use memset
/// plus some stores to initialize a local variable instead of using a memcpy
/// from a constant global. It is beneficial to use memset if the global is all
return false;
}
+
void CodeGenFunction::EmitAutoVarInit(const AutoVarEmission &emission) {
assert(emission.Variable && "emission was not valid!");
ElementType, ElementAlign, Destroyer);
}
};
-}
+} // end anonymous namespace
/// pushIrregularPartialArrayCleanup - Push an EH cleanup to destroy
/// already-constructed elements of the given array. The cleanup
CGF.EmitARCRelease(Param, Precise);
}
};
-}
+} // end anonymous namespace
/// Emit an alloca (or GlobalValue depending on target)
/// for the specified parameter and set up LocalDeclMap.
#include "llvm/Support/Compiler.h"
#include <cstdarg>
-
using namespace clang;
using namespace CodeGen;
-
namespace {
/// Class that lazily initialises the runtime function. Avoids inserting the
/// types and the function declaration into a module if they're not used, and
/// runtime provides some LLVM passes that can use this to do things like
/// automatic IMP caching and speculative inlining.
unsigned msgSendMDKind;
+
/// Helper function that generates a constant string and returns a pointer to
/// the start of the string. The result of this function can be used anywhere
/// where the C code specifies const char*.
return llvm::ConstantExpr::getGetElementPtr(Array.getElementType(),
Array.getPointer(), Zeros);
}
+
/// Emits a linkonce_odr string, whose name is the prefix followed by the
/// string value. This allows the linker to combine the strings between
/// different modules. Used for EH typeinfo names, selector strings, and a
return llvm::ConstantExpr::getGetElementPtr(ConstStr->getValueType(),
ConstStr, Zeros);
}
+
/// Generates a global structure, initialized by the elements in the vector.
/// The element types must match the types of the structure elements in the
/// first argument.
GV->setAlignment(Align.getQuantity());
return GV;
}
+
/// Generates a global array. The vector must contain the same number of
/// elements that the array type declares, of the type specified as the array
/// element type.
GV->setAlignment(Align.getQuantity());
return GV;
}
+
/// Generates a global array, inferring the array type from the specified
/// element type and the size of the initialiser.
llvm::GlobalVariable *MakeGlobalArray(llvm::Type *Ty,
llvm::ArrayType *ArrayTy = llvm::ArrayType::get(Ty, V.size());
return MakeGlobal(ArrayTy, V, Align, Name, linkage);
}
+
/// Returns a property name and encoding string.
llvm::Constant *MakePropertyEncodingString(const ObjCPropertyDecl *PD,
const Decl *Container) {
}
return MakeConstantString(PD->getNameAsString());
}
+
/// Push the property attributes into two structure fields.
void PushPropertyAttributes(std::vector<llvm::Constant*> &Fields,
ObjCPropertyDecl *property, bool isSynthesized=true, bool
Fields.push_back(llvm::ConstantInt::get(Int8Ty, 0));
Fields.push_back(llvm::ConstantInt::get(Int8Ty, 0));
}
+
/// Ensures that the value has the required type, by inserting a bitcast if
/// required. This function lets us avoid inserting bitcasts that are
/// redundant.
if (V.getType() == Ty) return V;
return B.CreateBitCast(V, Ty);
}
+
// Some zeros used for GEPs in lots of places.
llvm::Constant *Zeros[2];
/// Null pointer value. Mainly used as a terminator in various arrays.
llvm::Constant *NULLPtr;
/// LLVM context.
llvm::LLVMContext &VMContext;
+
private:
/// Placeholder for the class. Lots of things refer to the class before we've
/// actually emitted it. We use this alias as a placeholder, and then replace
LazyRuntimeFunction SyncExitFn;
private:
-
/// Function called if fast enumeration detects that the collection is
/// modified during the update.
LazyRuntimeFunction EnumerationMutationFn;
/// Objective-C 1 property structures when targeting the GCC runtime or it
/// will abort.
const int ProtocolVersion;
-private:
+
/// Generates an instance variable list structure. This is a structure
/// containing a size and an array of structures containing instance variable
/// metadata. This is used purely for introspection in the fragile ABI. In
llvm::Constant *GenerateIvarList(ArrayRef<llvm::Constant *> IvarNames,
ArrayRef<llvm::Constant *> IvarTypes,
ArrayRef<llvm::Constant *> IvarOffsets);
+
/// Generates a method list structure. This is a structure containing a size
/// and an array of structures containing method metadata.
///
ArrayRef<Selector> MethodSels,
ArrayRef<llvm::Constant *> MethodTypes,
bool isClassMethodList);
+
/// Emits an empty protocol. This is used for \@protocol() where no protocol
/// is found. The runtime will (hopefully) fix up the pointer to refer to the
/// real protocol.
llvm::Constant *GenerateEmptyProtocol(const std::string &ProtocolName);
+
/// Generates a list of property metadata structures. This follows the same
/// pattern as method and instance variable metadata lists.
llvm::Constant *GeneratePropertyList(const ObjCImplementationDecl *OID,
SmallVectorImpl<Selector> &InstanceMethodSels,
SmallVectorImpl<llvm::Constant*> &InstanceMethodTypes);
+
/// Generates a list of referenced protocols. Classes, categories, and
/// protocols all use this structure.
llvm::Constant *GenerateProtocolList(ArrayRef<std::string> Protocols);
+
/// To ensure that all protocols are seen by the runtime, we add a category on
/// a class defined in the runtime, declaring no methods, but adopting the
/// protocols. This is a horribly ugly hack, but it allows us to collect all
/// of the protocols without changing the ABI.
void GenerateProtocolHolderCategory();
+
/// Generates a class structure.
llvm::Constant *GenerateClassStructure(
llvm::Constant *MetaClass,
llvm::Constant *StrongIvarBitmap,
llvm::Constant *WeakIvarBitmap,
bool isMeta=false);
+
/// Generates a method list. This is used by protocols to define the required
/// and optional methods.
llvm::Constant *GenerateProtocolMethodList(
ArrayRef<llvm::Constant *> MethodNames,
ArrayRef<llvm::Constant *> MethodTypes);
+
/// Returns a selector with the specified type encoding. An empty string is
/// used to return an untyped selector (with the types field set to NULL).
llvm::Value *GetSelector(CodeGenFunction &CGF, Selector Sel,
const std::string &TypeEncoding);
+
/// Returns the variable used to store the offset of an instance variable.
llvm::GlobalVariable *ObjCIvarOffsetVariable(const ObjCInterfaceDecl *ID,
const ObjCIvarDecl *Ivar);
/// Emits a reference to a class. This allows the linker to object if there
/// is no class of the matching name.
+
protected:
void EmitClassRef(const std::string &className);
+
/// Emits a pointer to the named class
virtual llvm::Value *GetClassNamed(CodeGenFunction &CGF,
const std::string &Name, bool isWeak);
+
/// Looks up the method for sending a message to the specified object. This
/// mechanism differs between the GCC and GNU runtimes, so this method must be
/// overridden in subclasses.
llvm::Value *cmd,
llvm::MDNode *node,
MessageSendInfo &MSI) = 0;
+
/// Looks up the method for sending a message to a superclass. This
/// mechanism differs between the GCC and GNU runtimes, so this method must
/// be overridden in subclasses.
Address ObjCSuper,
llvm::Value *cmd,
MessageSendInfo &MSI) = 0;
+
/// Libobjc2 uses a bitfield representation where small(ish) bitfields are
/// stored in a 64-bit value with the low bit set to 1 and the remaining 63
/// bits set to their values, LSB first, while larger ones are stored in a
/// a bitfield with the 64th bit set will be (int64_t)&{ 2, [0, 1<<31] },
/// while a bitfield / with the 63rd bit set will be 1<<64.
llvm::Constant *MakeBitField(ArrayRef<bool> bits);
+
public:
CGObjCGNU(CodeGenModule &cgm, unsigned runtimeABIVersion,
unsigned protocolClassVersion);
return nullptr;
}
};
+
/// Class representing the legacy GCC Objective-C ABI. This is the default when
/// -fobjc-nonfragile-abi is not specified.
///
/// structure describing the receiver and the class, and a selector as
/// arguments. Returns the IMP for the corresponding method.
LazyRuntimeFunction MsgLookupSuperFn;
+
protected:
llvm::Value *LookupIMP(CodeGenFunction &CGF, llvm::Value *&Receiver,
llvm::Value *cmd, llvm::MDNode *node,
imp->setMetadata(msgSendMDKind, node);
return imp.getInstruction();
}
+
llvm::Value *LookupIMPSuper(CodeGenFunction &CGF, Address ObjCSuper,
llvm::Value *cmd, MessageSendInfo &MSI) override {
- CGBuilderTy &Builder = CGF.Builder;
- llvm::Value *lookupArgs[] = {EnforceType(Builder, ObjCSuper,
- PtrToObjCSuperTy).getPointer(), cmd};
- return CGF.EmitNounwindRuntimeCall(MsgLookupSuperFn, lookupArgs);
- }
- public:
- CGObjCGCC(CodeGenModule &Mod) : CGObjCGNU(Mod, 8, 2) {
- // IMP objc_msg_lookup(id, SEL);
- MsgLookupFn.init(&CGM, "objc_msg_lookup", IMPTy, IdTy, SelectorTy,
- nullptr);
- // IMP objc_msg_lookup_super(struct objc_super*, SEL);
- MsgLookupSuperFn.init(&CGM, "objc_msg_lookup_super", IMPTy,
- PtrToObjCSuperTy, SelectorTy, nullptr);
- }
+ CGBuilderTy &Builder = CGF.Builder;
+ llvm::Value *lookupArgs[] = {EnforceType(Builder, ObjCSuper,
+ PtrToObjCSuperTy).getPointer(), cmd};
+ return CGF.EmitNounwindRuntimeCall(MsgLookupSuperFn, lookupArgs);
+ }
+
+public:
+ CGObjCGCC(CodeGenModule &Mod) : CGObjCGNU(Mod, 8, 2) {
+ // IMP objc_msg_lookup(id, SEL);
+ MsgLookupFn.init(&CGM, "objc_msg_lookup", IMPTy, IdTy, SelectorTy,
+ nullptr);
+ // IMP objc_msg_lookup_super(struct objc_super*, SEL);
+ MsgLookupSuperFn.init(&CGM, "objc_msg_lookup_super", IMPTy,
+ PtrToObjCSuperTy, SelectorTy, nullptr);
+ }
};
+
/// Class used when targeting the new GNUstep runtime ABI.
class CGObjCGNUstep : public CGObjCGNU {
/// The slot lookup function. Returns a pointer to a cacheable structure
/// Type of an slot structure pointer. This is returned by the various
/// lookup functions.
llvm::Type *SlotTy;
+
public:
llvm::Constant *GetEHType(QualType T) override;
+
protected:
llvm::Value *LookupIMP(CodeGenFunction &CGF, llvm::Value *&Receiver,
llvm::Value *cmd, llvm::MDNode *node,
Receiver = Builder.CreateLoad(ReceiverPtr, true);
return imp;
}
+
llvm::Value *LookupIMPSuper(CodeGenFunction &CGF, Address ObjCSuper,
llvm::Value *cmd,
MessageSendInfo &MSI) override {
return Builder.CreateAlignedLoad(Builder.CreateStructGEP(nullptr, slot, 4),
CGF.getPointerAlign());
}
+
public:
CGObjCGNUstep(CodeGenModule &Mod) : CGObjCGNU(Mod, 9, 3) {
const ObjCRuntime &R = CGM.getLangOpts().ObjCRuntime;
CxxAtomicObjectGetFn.init(&CGM, "objc_getCppObjectAtomic", VoidTy, PtrTy,
PtrTy, PtrTy, nullptr);
}
+
llvm::Constant *GetCppAtomicObjectGetFunction() override {
// The optimised functions were added in version 1.7 of the GNUstep
// runtime.
VersionTuple(1, 7));
return CxxAtomicObjectGetFn;
}
+
llvm::Constant *GetCppAtomicObjectSetFunction() override {
// The optimised functions were added in version 1.7 of the GNUstep
// runtime.
VersionTuple(1, 7));
return CxxAtomicObjectSetFn;
}
+
llvm::Constant *GetOptimizedPropertySetFunction(bool atomic,
bool copy) override {
// The optimised property functions omit the GC check, and so are not
};
} // end anonymous namespace
-
/// Emits a reference to a dummy variable which is emitted with each class.
/// This ensures that a linker error will be generated when trying to link
/// together modules where a referenced class is not defined.
const ObjCInterfaceDecl *OID) {
return GetClassNamed(CGF, OID->getNameAsString(), OID->isWeakImported());
}
+
llvm::Value *CGObjCGNU::EmitNSAutoreleasePoolClassRef(CodeGenFunction &CGF) {
return GetClassNamed(CGF, "NSAutoreleasePool", false);
}
llvm::Value *CGObjCGNU::GetSelector(CodeGenFunction &CGF, Selector Sel,
const std::string &TypeEncoding) {
-
SmallVectorImpl<TypedSelector> &Types = SelectorTable[Sel];
llvm::GlobalAlias *SelValue = nullptr;
}
llvm::Value *cmd = GetSelector(CGF, Sel);
-
-
CallArgList ActualArgs;
ActualArgs.add(RValue::get(EnforceType(Builder, Receiver, IdTy)), ASTIdTy);
MakeGlobalArray(PtrToIntTy, IvarOffsetValues, CGM.getPointerAlign(),
".ivar.offsets");
-
// Collect information about instance methods
SmallVector<Selector, 16> InstanceMethodSels;
SmallVector<llvm::Constant*, 16> InstanceMethodTypes;
llvm::Constant *Properties = GeneratePropertyList(OID, InstanceMethodSels,
InstanceMethodTypes);
-
// Collect information about class methods
SmallVector<Selector, 16> ClassMethodSels;
SmallVector<llvm::Constant*, 16> ClassMethodTypes;
Classes.push_back(ClassStruct);
}
-
llvm::Function *CGObjCGNU::ModuleInitFunction() {
// Only emit an ObjC load function if no Objective-C stuff has been called
if (Classes.empty() && Categories.empty() && ConstantStrings.empty() &&
llvm::Constant *CGObjCGNU::GetGetStructFunction() {
return GetStructPropertyFn;
}
+
llvm::Constant *CGObjCGNU::GetSetStructFunction() {
return SetStructPropertyFn;
}
+
llvm::Constant *CGObjCGNU::GetCppAtomicObjectGetFunction() {
return nullptr;
}
+
llvm::Constant *CGObjCGNU::GetCppAtomicObjectSetFunction() {
return nullptr;
}
// In Objective-C++ mode, we actually emit something equivalent to the C++
// exception handler.
EmitTryCatchStmt(CGF, S, EnterCatchFn, ExitCatchFn, ExceptionReThrowFn);
- return ;
}
void CGObjCGNU::EmitThrowStmt(CodeGenFunction &CGF,
return CGM.CreateRuntimeFunction(
llvm::FunctionType::get(CGM.Int32Ty, params, false),
"objc_exception_match");
-
}
/// SetJmpFn - LLVM _setjmp function.
/// modern abi
class ObjCNonFragileABITypesHelper : public ObjCCommonTypesHelper {
public:
-
// MethodListnfABITy - LLVM for struct _method_list_t
llvm::StructType *MethodListnfABITy;
llvm::Constant *GetSetStructFunction() override {
return ObjCTypes.getCopyStructFn();
}
+
llvm::Constant *GetGetStructFunction() override {
return ObjCTypes.getCopyStructFn();
}
+
llvm::Constant *GetCppAtomicObjectSetFunction() override {
return ObjCTypes.getCppAtomicObjectFunction();
}
+
llvm::Constant *GetCppAtomicObjectGetFunction() override {
return ObjCTypes.getCppAtomicObjectFunction();
}
bool IsDisordered = false;
llvm::SmallVector<IvarInfo, 8> IvarsInfo;
+
public:
IvarLayoutBuilder(CodeGenModule &CGM, CharUnits instanceBegin,
CharUnits instanceEnd, bool forStrongLayout)
printf("\n");
}
};
-}
+} // end anonymous namespace
llvm::Constant *CGObjCCommonMac::BuildGCBlockLayout(CodeGenModule &CGM,
const CGBlockInfo &blockInfo) {
}
}
-
/// getBlockCaptureLifetime - This routine returns life time of the captured
/// block variable for the purpose of block layout meta-data generation. FQT is
/// the type of the variable captured in the block.
return getBitmapBlockLayout(false);
}
-
llvm::Constant *CGObjCCommonMac::BuildByrefLayout(CodeGen::CodeGenModule &CGM,
QualType T) {
assert(CGM.getLangOpts().getGC() == LangOptions::NonGC);
llvm::Constant *CGObjCMac::GetGetStructFunction() {
return ObjCTypes.getCopyStructFn();
}
+
llvm::Constant *CGObjCMac::GetSetStructFunction() {
return ObjCTypes.getCopyStructFn();
}
llvm::Constant *CGObjCMac::GetCppAtomicObjectGetFunction() {
return ObjCTypes.getCppAtomicObjectFunction();
}
+
llvm::Constant *CGObjCMac::GetCppAtomicObjectSetFunction() {
return ObjCTypes.getCppAtomicObjectFunction();
}
void emitWriteHazard();
void emitHazardsInNewBlocks();
};
-}
+} // end anonymous namespace
/// Create the fragile-ABI read and write hazards based on the current
/// state of the function, which is presumed to be immediately prior
llvm::Value *args[] = { src, dst.getPointer() };
CGF.EmitNounwindRuntimeCall(ObjCTypes.getGcAssignWeakFn(),
args, "weakassign");
- return;
}
/// EmitObjCGlobalAssign - Code gen for assigning to a __strong object.
else
CGF.EmitNounwindRuntimeCall(ObjCTypes.getGcAssignThreadLocalFn(),
args, "threadlocalassign");
- return;
}
/// EmitObjCIvarAssign - Code gen for assigning to a __strong object.
dst = CGF.Builder.CreateBitCast(dst, ObjCTypes.PtrObjectPtrTy);
llvm::Value *args[] = { src, dst.getPointer(), ivarOffset };
CGF.EmitNounwindRuntimeCall(ObjCTypes.getGcAssignIvarFn(), args);
- return;
}
/// EmitObjCStrongCastAssign - Code gen for assigning to a __strong cast object.
llvm::Value *args[] = { src, dst.getPointer() };
CGF.EmitNounwindRuntimeCall(ObjCTypes.getGcAssignStrongCastFn(),
args, "strongassign");
- return;
}
void CGObjCMac::EmitGCMemmoveCollectable(CodeGen::CodeGenFunction &CGF,
// struct _objc_cache *
CacheTy = llvm::StructType::create(VMContext, "struct._objc_cache");
CachePtrTy = llvm::PointerType::getUnqual(CacheTy);
-
}
ObjCTypesHelper::ObjCTypesHelper(CodeGen::CodeGenModule &cgm)
llvm::StructType::create("struct._objc_exception_data",
llvm::ArrayType::get(CGM.Int32Ty,SetJmpBufferSize),
StackPtrTy, nullptr);
-
}
ObjCNonFragileABITypesHelper::ObjCNonFragileABITypesHelper(CodeGen::CodeGenModule &cgm)
ThreadIDVar(ThreadIDVar) {
assert(ThreadIDVar != nullptr && "No ThreadID in OpenMP region.");
}
+
/// \brief Get a variable or parameter for storing global thread id
/// inside OpenMP construct.
const VarDecl *getThreadIDVariable() const override { return ThreadIDVar; }
ThreadIDVar(ThreadIDVar) {
assert(ThreadIDVar != nullptr && "No ThreadID in OpenMP region.");
}
+
/// \brief Get a variable or parameter for storing global thread id
/// inside OpenMP construct.
const VarDecl *getThreadIDVariable() const override { return ThreadIDVar; }
: CGOpenMPRegionInfo(InlinedRegion, CodeGen, Kind, HasCancel),
OldCSI(OldCSI),
OuterRegionInfo(dyn_cast_or_null<CGOpenMPRegionInfo>(OldCSI)) {}
+
// \brief Retrieve the value of the context parameter.
llvm::Value *getContextValue() const override {
if (OuterRegionInfo)
return OuterRegionInfo->getContextValue();
llvm_unreachable("No context value for inlined OpenMP region");
}
+
void setContextValue(llvm::Value *V) override {
if (OuterRegionInfo) {
OuterRegionInfo->setContextValue(V);
}
llvm_unreachable("No context value for inlined OpenMP region");
}
+
/// \brief Lookup the captured field decl for a variable.
const FieldDecl *lookup(const VarDecl *VD) const override {
if (OuterRegionInfo)
// captured variables, we can use the original one.
return nullptr;
}
+
FieldDecl *getThisFieldDecl() const override {
if (OuterRegionInfo)
return OuterRegionInfo->getThisFieldDecl();
return nullptr;
}
+
/// \brief Get a variable or parameter for storing global thread id
/// inside OpenMP construct.
const VarDecl *getThreadIDVariable() const override {
CGF.CapturedStmtInfo = new CGOpenMPInlinedRegionInfo(
CGF.CapturedStmtInfo, CodeGen, Kind, HasCancel);
}
+
~InlinedOpenMPRegionRAII() {
// Restore original CapturedStmtInfo only if we're done with code emission.
auto *OldCSI =
assert(CleanupArgs.size() == N);
std::copy(CleanupArgs.begin(), CleanupArgs.end(), std::begin(Args));
}
+
void Emit(CodeGenFunction &CGF, Flags /*flags*/) override {
if (!CGF.HaveInsertPoint())
return;
// We can't have any padding between symbols, so we need to have 1-byte
// alignment.
Entry->setAlignment(1);
- return;
}
void CGOpenMPRuntime::createOffloadEntriesAndInfoMetadata() {
CancelSections = 3,
CancelTaskgroup = 4
};
-}
+} // anonymous namespace
static RTCancelKind getCancellationKind(OpenMPDirectiveKind CancelRegion) {
RTCancelKind CancelKind = CancelNoreq;
FileID = ID.getFile();
LineNum = PLoc.getLine();
ColumnNum = PLoc.getColumn();
- return;
}
void CGOpenMPRuntime::emitTargetOutlinedFunction(
const OMPExecutableDirective &D, StringRef ParentName,
llvm::Function *&OutlinedFn, llvm::Constant *&OutlinedFnID,
bool IsOffloadEntry) {
-
assert(!ParentName.empty() && "Invalid target region parent name!");
const CapturedStmt &CS = *cast<CapturedStmt>(D.getAssociatedStmt());
// Register the information for the entry associated with this target region.
OffloadEntriesInfoManager.registerTargetRegionEntryInfo(
DeviceID, FileID, ParentName, Line, Column, OutlinedFn, OutlinedFnID);
- return;
}
void CGOpenMPRuntime::emitTargetCall(CodeGenFunction &CGF,
MapTypesArray = MapTypesArrayGbl;
for (unsigned i = 0; i < PointerNumVal; ++i) {
-
llvm::Value *BPVal = BasePointers[i];
if (BPVal->getType()->isPointerTy())
BPVal = CGF.Builder.CreateBitCast(BPVal, CGM.VoidPtrTy);
CGF.EmitBranch(OffloadContBlock);
CGF.EmitBlock(OffloadContBlock, /*IsFinished=*/true);
- return;
}
void CGOpenMPRuntime::scanForTargetRegionsFunctions(const Stmt *S,
// Keep looking for target regions recursively.
for (auto *II : S->children())
scanForTargetRegionsFunctions(II, ParentName);
-
- return;
}
bool CGOpenMPRuntime::emitTargetFunctions(GlobalDecl GD) {
SmallVector<DeclRefExpr *, 32> BlockDeclRefs;
-
// Block related declarations.
SmallVector<ValueDecl *, 8> BlockByCopyDecls;
llvm::SmallPtrSet<ValueDecl *, 8> BlockByCopyDeclsPtrSet;
public:
llvm::DenseMap<ObjCMethodDecl*, std::string> MethodInternalNames;
+
// Top Level Driver code.
bool HandleTopLevelDecl(DeclGroupRef D) override {
for (DeclGroupRef::iterator I = D.begin(), E = D.end(); I != E; ++I) {
RewriteObjCQualifiedInterfaceTypes(TD);
}
}
- return;
}
void HandleTopLevelSingleDecl(Decl *D);
}
return false;
}
+
bool PointerTypeTakesAnyBlockArguments(QualType QT);
bool PointerTypeTakesAnyObjCQualifiedType(QualType QT);
void GetExtentOfArgList(const char *Name, const char *&LParen,
/*Pascal=*/false, StrType, SourceLocation());
}
};
-
-}
+} // end anonymous namespace
void RewriteModernObjC::RewriteBlocksInFunctionProtoType(QualType funcType,
NamedDecl *D) {
else
WriteInternalIvarName(ClassDecl, D, IvarOffsetName);
-
std::string S = "(*(";
QualType IvarT = D->getType();
if (D->isBitField())
void RewriteModernObjC::RewriteForwardClassEpilogue(ObjCInterfaceDecl *ClassDecl,
const std::string &typedefString) {
- SourceLocation startLoc = ClassDecl->getLocStart();
- const char *startBuf = SM->getCharacterData(startLoc);
- const char *semiPtr = strchr(startBuf, ';');
- // Replace the @class with typedefs corresponding to the classes.
- ReplaceText(startLoc, semiPtr-startBuf+1, typedefString);
+ SourceLocation startLoc = ClassDecl->getLocStart();
+ const char *startBuf = SM->getCharacterData(startLoc);
+ const char *semiPtr = strchr(startBuf, ';');
+ // Replace the @class with typedefs corresponding to the classes.
+ ReplaceText(startLoc, semiPtr-startBuf+1, typedefString);
}
void RewriteModernObjC::RewriteForwardClassDecl(DeclGroupRef D) {
}
}
}
+
void RewriteModernObjC::RewriteImplementationDecl(Decl *OID) {
ObjCImplementationDecl *IMD = dyn_cast<ObjCImplementationDecl>(OID);
ObjCCategoryImplDecl *CID = dyn_cast<ObjCCategoryImplDecl>(OID);
Diags.Report(Context->getFullLoc(S->getLocStart()),
TryFinallyContainsReturnDiag);
}
- return;
}
Stmt *RewriteModernObjC::RewriteObjCAutoreleasePoolStmt(ObjCAutoreleasePoolStmt *S) {
Context->UnsignedIntTy, SourceLocation());
MsgExprs.push_back(cnt);
-
SmallVector<QualType, 4> ArgTypes;
ArgTypes.push_back(Context->getObjCClassType());
ArgTypes.push_back(Context->getObjCSelType());
CK_BitCast,
DictLiteralKeyME);
-
-
// Synthesize a call to objc_msgSend().
SmallVector<Expr*, 32> MsgExprs;
SmallVector<Expr*, 4> ClsExprs;
Context->UnsignedIntTy, SourceLocation());
MsgExprs.push_back(cnt);
-
SmallVector<QualType, 8> ArgTypes;
ArgTypes.push_back(Context->getObjCClassType());
ArgTypes.push_back(Context->getObjCSelType());
str += "\t memset((void*)&s, 0, sizeof(s));\n";
str += "\t else\n";
-
str += "\t s = (("; str += castType.getAsString(Context->getPrintingPolicy());
str += ")(void *)objc_msgSend_stret)(receiver, sel";
for (unsigned i = 2; i < ArgTypes.size(); i++) {
}
str += ");\n";
-
str += "\t}\n";
str += "\t"; str += returnType.getAsString(Context->getPrintingPolicy());
str += " s;\n";
ProtocolExprDecls.insert(Exp->getProtocol()->getCanonicalDecl());
// delete Exp; leak for now, see RewritePropertyOrImplicitSetter() usage for more info.
return castExpr;
-
}
bool RewriteModernObjC::BufferContainsPPDirectives(const char *startBuf,
TagLocation = ED->getLocation();
return Context->getSourceManager().isBeforeInTranslationUnit(
IDecl->getLocation(), TagLocation);
-
}
return false;
}
if (IsNamedDefinition)
GlobalDefinedTags.insert(TD);
}
-
}
unsigned RewriteModernObjC::ObjCIvarBitfieldGroupNo(ObjCIvarDecl *IV) {
Result += "__GRBF_";
unsigned GroupNo = ObjCIvarBitfieldGroupNo(IV);
Result += utostr(GroupNo);
- return;
}
/// ObjCIvarBitfieldGroupType - Names struct type for ivar bitfield group.
Result += "__T_";
unsigned GroupNo = ObjCIvarBitfieldGroupNo(IV);
Result += utostr(GroupNo);
- return;
}
/// ObjCIvarBitfieldGroupOffset - Names symbol for ivar bitfield group field offset.
// Meta Data Emission
//===----------------------------------------------------------------------===//
-
/// RewriteImplementations - This routine rewrites all method implementations
/// and emits meta-data.
HasLocalVariableExternalStorage(DRE->getDecl()))
// FIXME: Handle enums.
BlockDeclRefs.push_back(DRE);
-
- return;
}
void RewriteModernObjC::GetInnerBlockDeclRefExprs(Stmt *S,
ImportedLocalExternalDecls.insert(Var);
}
}
-
- return;
}
/// convertObjCTypeToCStyleType - This routine converts such objc types
break;
}
}
- return;
}
void RewriteModernObjC::RewriteImplicitCastObjCExpr(CastExpr *IC) {
Str += TypeString;
Str += ")";
InsertText(IC->getSubExpr()->getLocStart(), Str);
-
- return;
}
void RewriteModernObjC::RewriteBlockPointerFunctionArgs(FunctionDecl *FD) {
break;
}
}
- return;
}
bool RewriteModernObjC::PointerTypeTakesAnyBlockArguments(QualType QT) {
OrigLength++;
}
ReplaceText(Start, OrigLength, buf);
-
- return;
}
-
/// SynthesizeByrefCopyDestroyHelper - This routine synthesizes:
/// void __Block_byref_id_object_copy(struct Block_byref_id_object *dst,
/// struct Block_byref_id_object *src) {
InsertText(separatorLoc, lastDecl ? "}" : "};\n");
}
- return;
}
void RewriteModernObjC::CollectBlockDeclRefInfo(BlockExpr *Exp) {
Stmt *RewriteModernObjC::SynthBlockInitExpr(BlockExpr *Exp,
const SmallVectorImpl<DeclRefExpr *> &InnerBlockDeclRefs) {
-
const BlockDecl *block = Exp->getBlockDecl();
Blocks.push_back(Exp);
CollectBlockDeclRefInfo(Exp);
// Add inner imported variables now used in current block.
- int countOfInnerDecls = 0;
+ int countOfInnerDecls = 0;
if (!InnerBlockDeclRefs.empty()) {
for (unsigned i = 0; i < InnerBlockDeclRefs.size(); i++) {
DeclRefExpr *Exp = InnerBlockDeclRefs[i];
// Mark this protocol as having been generated.
if (!ObjCSynthesizedProtocols.insert(PDecl->getCanonicalDecl()).second)
llvm_unreachable("protocol already synthesized");
-
}
void RewriteModernObjC::RewriteObjCProtocolListMetaData(
/* Container */IDecl,
"_OBJC_$_PROP_LIST_",
CDecl->getNameAsString());
-
// Data for initializing _class_ro_t metaclass meta-data
uint32_t flags = CLS_META;
std::string InstanceSize;
std::string InstanceStart;
-
bool classIsHidden = CDecl->getVisibility() == HiddenVisibility;
if (classIsHidden)
flags |= OBJC2_CLS_HIDDEN;
if (ImplementationIsNonLazy(IDecl))
DefinedNonLazyClasses.push_back(CDecl);
-
}
void RewriteModernObjC::RewriteClassSetupInitHook(std::string &Result) {
// Determine if this category is also "non-lazy".
if (ImplementationIsNonLazy(IDecl))
DefinedNonLazyCategories.push_back(CDecl);
-
}
void RewriteModernObjC::RewriteCategorySetupInitHook(std::string &Result) {
return Replacement;
}
-#endif
+#endif // CLANG_ENABLE_OBJC_REWRITER
namespace {
class RewriteObjC : public ASTConsumer {
protected:
-
enum {
BLOCK_FIELD_IS_OBJECT = 3, /* id, NSObject, __attribute__((NSObject)),
block, ... */
: R(R), SavedValue(R.DisableReplaceStmt) {
R.DisableReplaceStmt = true;
}
+
~DisableReplaceStmtScope() {
R.DisableReplaceStmt = SavedValue;
}
};
+
void InitializeCommon(ASTContext &context);
public:
-
// Top Level Driver code.
bool HandleTopLevelDecl(DeclGroupRef D) override {
for (DeclGroupRef::iterator I = D.begin(), E = D.end(); I != E; ++I) {
}
return true;
}
+
void HandleTopLevelSingleDecl(Decl *D);
void HandleDeclInMainFile(Decl *D);
RewriteObjC(std::string inFile, raw_ostream *OS,
class RewriteObjCFragileABI : public RewriteObjC {
public:
-
RewriteObjCFragileABI(std::string inFile, raw_ostream *OS,
DiagnosticsEngine &D, const LangOptions &LOpts,
bool silenceMacroWarn) : RewriteObjC(inFile, OS,
std::string &Result) override;
Stmt *RewriteObjCIvarRefExpr(ObjCIvarRefExpr *IV) override;
};
-}
+} // end anonymous namespace
void RewriteObjC::RewriteBlocksInFunctionProtoType(QualType funcType,
NamedDecl *D) {
}
}
}
+
void RewriteObjC::RewriteImplementationDecl(Decl *OID) {
ObjCImplementationDecl *IMD = dyn_cast<ObjCImplementationDecl>(OID);
ObjCCategoryImplDecl *CID = dyn_cast<ObjCCategoryImplDecl>(OID);
Diags.Report(Context->getFullLoc(S->getLocStart()),
TryFinallyContainsReturnDiag);
}
- return;
}
void RewriteObjC::HasReturnStmts(Stmt *S, bool &hasReturns)
if (SubStmt)
HasReturnStmts(SubStmt, hasReturns);
- if (isa<ReturnStmt>(S))
- hasReturns = true;
- return;
+ if (isa<ReturnStmt>(S))
+ hasReturns = true;
}
void RewriteObjC::RewriteTryReturnStmts(Stmt *S) {
- // Perform a bottom up traversal of all children.
- for (Stmt *SubStmt : S->children())
- if (SubStmt) {
- RewriteTryReturnStmts(SubStmt);
- }
- if (isa<ReturnStmt>(S)) {
- SourceLocation startLoc = S->getLocStart();
- const char *startBuf = SM->getCharacterData(startLoc);
-
- const char *semiBuf = strchr(startBuf, ';');
- assert((*semiBuf == ';') && "RewriteTryReturnStmts: can't find ';'");
- SourceLocation onePastSemiLoc = startLoc.getLocWithOffset(semiBuf-startBuf+1);
+ // Perform a bottom up traversal of all children.
+ for (Stmt *SubStmt : S->children())
+ if (SubStmt) {
+ RewriteTryReturnStmts(SubStmt);
+ }
+ if (isa<ReturnStmt>(S)) {
+ SourceLocation startLoc = S->getLocStart();
+ const char *startBuf = SM->getCharacterData(startLoc);
+ const char *semiBuf = strchr(startBuf, ';');
+ assert((*semiBuf == ';') && "RewriteTryReturnStmts: can't find ';'");
+ SourceLocation onePastSemiLoc = startLoc.getLocWithOffset(semiBuf-startBuf+1);
- std::string buf;
- buf = "{ objc_exception_try_exit(&_stack); return";
+ std::string buf;
+ buf = "{ objc_exception_try_exit(&_stack); return";
- ReplaceText(startLoc, 6, buf);
- InsertText(onePastSemiLoc, "}");
- }
- return;
+ ReplaceText(startLoc, 6, buf);
+ InsertText(onePastSemiLoc, "}");
+ }
}
void RewriteObjC::RewriteSyncReturnStmts(Stmt *S, std::string syncExitBuf) {
ReplaceText(startLoc, 6, buf);
InsertText(onePastSemiLoc, "}");
}
- return;
}
Stmt *RewriteObjC::RewriteObjCTryStmt(ObjCAtTryStmt *S) {
}
}
-
void RewriteObjC::RewriteBlockLiteralFunctionDecl(FunctionDecl *FD) {
SourceLocation FunLocStart = FD->getTypeSpecStartLoc();
const FunctionType *funcType = FD->getType()->getAs<FunctionType>();
CallExpr *STCE = new (Context) CallExpr(
*Context, PE, MsgExprs, FT->getReturnType(), VK_RValue, SourceLocation());
return STCE;
-
}
-
Stmt *RewriteObjC::SynthMessageExpr(ObjCMessageExpr *Exp,
SourceLocation StartLoc,
SourceLocation EndLoc) {
ProtocolExprDecls.insert(Exp->getProtocol()->getCanonicalDecl());
// delete Exp; leak for now, see RewritePropertyOrImplicitSetter() usage for more info.
return castExpr;
-
}
bool RewriteObjC::BufferContainsPPDirectives(const char *startBuf,
// Meta Data Emission
//===----------------------------------------------------------------------===//
-
/// RewriteImplementations - This routine rewrites all method implementations
/// and emits meta-data.
HasLocalVariableExternalStorage(DRE->getDecl()))
// FIXME: Handle enums.
BlockDeclRefs.push_back(DRE);
-
- return;
}
void RewriteObjC::GetInnerBlockDeclRefExprs(Stmt *S,
ImportedLocalExternalDecls.insert(Var);
}
}
-
- return;
}
/// convertFunctionTypeOfBlocks - This routine converts a function type
break;
}
}
- return;
}
void RewriteObjC::RewriteBlockPointerFunctionArgs(FunctionDecl *FD) {
break;
}
}
- return;
}
bool RewriteObjC::PointerTypeTakesAnyBlockArguments(QualType QT) {
OrigLength++;
}
ReplaceText(Start, OrigLength, buf);
-
- return;
}
-
/// SynthesizeByrefCopyDestroyHelper - This routine synthesizes:
/// void __Block_byref_id_object_copy(struct Block_byref_id_object *dst,
/// struct Block_byref_id_object *src) {
InsertText(semiLoc, "}");
}
- return;
}
void RewriteObjC::CollectBlockDeclRefInfo(BlockExpr *Exp) {
Exp = new (Context) UnaryOperator(Exp, UO_AddrOf, QT, VK_RValue,
OK_Ordinary, SourceLocation());
}
-
}
InitExprs.push_back(Exp);
}
// Mark this protocol as having been generated.
if (!ObjCSynthesizedProtocols.insert(PDecl->getCanonicalDecl()).second)
llvm_unreachable("protocol already synthesized");
-
}
void RewriteObjCFragileABI::RewriteObjCProtocolListMetaData(
return Replacement;
}
-#endif
+#endif // CLANG_ENABLE_OBJC_REWRITER
void checkPostStmt(const ObjCArrayLiteral *AL,
CheckerContext &C) const;
};
-}
+} // end anonymous namespace
void NilArgChecker::warnIfNilExpr(const Expr *E,
const char *Msg,
if (ExplodedNode *N = C.generateErrorNode()) {
generateBugReport(N, Msg, E->getSourceRange(), E, C);
}
-
}
}
class CFRetainReleaseChecker : public Checker< check::PreStmt<CallExpr> > {
mutable std::unique_ptr<APIMisuse> BT;
mutable IdentifierInfo *Retain, *Release, *MakeCollectable, *Autorelease;
+
public:
CFRetainReleaseChecker()
: Retain(nullptr), Release(nullptr), MakeCollectable(nullptr),
};
} // end anonymous namespace
-
void CFRetainReleaseChecker::checkPreStmt(const CallExpr *CE,
CheckerContext &C) const {
// If the CallExpr doesn't have exactly 1 argument just give up checking.
public:
void checkPreObjCMessage(const ObjCMethodCall &msg, CheckerContext &C) const;
};
-}
+} // end anonymous namespace
void ClassReleaseChecker::checkPreObjCMessage(const ObjCMethodCall &msg,
CheckerContext &C) const {
-
if (!BT) {
BT.reset(new APIMisuse(
this, "message incorrectly sent to class instead of class instance"));
public:
void checkPreObjCMessage(const ObjCMethodCall &msg, CheckerContext &C) const;
};
-}
+} // end anonymous namespace
/// isVariadicMessage - Returns whether the given message is a variadic message,
/// where all arguments must be Objective-C types.
const CallEvent *Call,
PointerEscapeKind Kind) const;
};
-}
+} // end anonymous namespace
static bool isKnownNonNilCollectionType(QualType T) {
const ObjCObjectPointerType *PT = T->getAs<ObjCObjectPointerType>();
return assumeCollectionNonEmpty(C, State, CollectionS, Assumption);
}
-
/// If the fist block edge is a back edge, we are reentering the loop.
static bool alreadyExecutedAtLeastOneLoopIteration(const ExplodedNode *N,
const ObjCForCollectionStmt *FCS) {
C.addTransition(State);
}
- return;
}
static SymbolRef getMethodReceiverIfKnownImmutable(const CallEvent *Call) {
void checkPostObjCMessage(const ObjCMethodCall &M, CheckerContext &C) const;
};
-}
+} // end anonymous namespace
ProgramStateRef
ObjCNonNilReturnValueChecker::assumeExprIsNonNull(const Expr *NonNullExpr,
-//= CheckerDocumentation.cpp - Documentation checker ---------------*- C++ -*-//
+//===- CheckerDocumentation.cpp - Documentation checker ---------*- C++ -*-===//
//
// The LLVM Compiler Infrastructure
//
check::Event<ImplicitNullDerefEvent>,
check::ASTDecl<FunctionDecl> > {
public:
-
/// \brief Pre-visit the Statement.
///
/// The method will be called before the analyzer core processes the
/// check::Bind
void checkBind(SVal Loc, SVal Val, const Stmt *S, CheckerContext &) const {}
-
/// \brief Called whenever a symbol becomes dead.
///
/// This callback should be used by the checkers to aggressively clean
AnalysisManager &Mgr,
BugReporter &BR) const {}
-
/// \brief Evaluates function call.
///
/// The analysis core threats all function calls in the same way. However, some
void checkASTDecl(const FunctionDecl *D,
AnalysisManager &Mgr,
BugReporter &BR) const {}
-
};
void CheckerDocumentation::checkPostStmt(const DeclStmt *DS,
CheckerContext &C) const {
- return;
}
} // end namespace ento
-//===- Chrootchecker.cpp -------- Basic security checks ----------*- C++ -*-==//
+//===- Chrootchecker.cpp -------- Basic security checks ---------*- C++ -*-===//
//
// The LLVM Compiler Infrastructure
//
#include "clang/StaticAnalyzer/Core/PathSensitive/ProgramStateTrait.h"
#include "clang/StaticAnalyzer/Core/PathSensitive/SymbolManager.h"
#include "llvm/ADT/ImmutableMap.h"
+
using namespace clang;
using namespace ento;
C.emitReport(llvm::make_unique<BugReport>(
*BT_BreakJail, BT_BreakJail->getDescription(), N));
}
-
- return;
}
void ento::registerChrootChecker(CheckerManager &mgr) {
-//== DynamicTypePropagation.cpp -------------------------------- -*- C++ -*--=//
+//===- DynamicTypePropagation.cpp ------------------------------*- C++ -*--===//
//
// The LLVM Compiler Infrastructure
//
const ObjCObjectPointerType *To, ExplodedNode *N,
SymbolRef Sym, CheckerContext &C,
const Stmt *ReportedNode = nullptr) const;
+
public:
void checkPreCall(const CallEvent &Call, CheckerContext &C) const;
void checkPostCall(const CallEvent &Call, CheckerContext &C) const;
/// This value is set to true, when the Generics checker is turned on.
DefaultBool CheckGenerics;
};
-}
+} // end anonymous namespace
void DynamicTypePropagation::checkDeadSymbols(SymbolReaper &SR,
CheckerContext &C) const {
ProgramStateRef State = C.getState();
State = setDynamicTypeInfo(State, Region, Ty, /*CanBeSubclass=*/false);
C.addTransition(State);
- return;
}
void DynamicTypePropagation::checkPreCall(const CallEvent &Call,
// class. This method is provided by the runtime and available on all classes.
if (MessageExpr->getReceiverKind() == ObjCMessageExpr::Class &&
Sel.getAsString() == "class") {
-
QualType ReceiverType = MessageExpr->getClassReceiver();
const auto *ReceiverClassType = ReceiverType->getAs<ObjCObjectType>();
QualType ReceiverClassPointerType =
-//=- IvarInvalidationChecker.cpp - -*- C++ -------------------------------*-==//
+//===- IvarInvalidationChecker.cpp ------------------------------*- C++ -*-===//
//
// The LLVM Compiler Infrastructure
//
using namespace ento;
namespace {
-
struct ChecksFilter {
/// Check for missing invalidation method declarations.
DefaultBool check_MissingInvalidationMethod;
};
class IvarInvalidationCheckerImpl {
-
typedef llvm::SmallSetVector<const ObjCMethodDecl*, 2> MethodSet;
typedef llvm::DenseMap<const ObjCMethodDecl*,
const ObjCIvarDecl*> MethToIvarMapTy;
typedef llvm::DenseMap<const ObjCIvarDecl*,
const ObjCPropertyDecl*> IvarToPropMapTy;
-
struct InvalidationInfo {
/// Has the ivar been invalidated?
bool IsInvalidated;
void VisitObjCMessageExpr(const ObjCMessageExpr *ME);
void VisitChildren(const Stmt *S) {
- for (const Stmt *Child : S->children()) {
+ for (const auto *Child : S->children()) {
if (Child)
this->Visit(Child);
if (CalledAnotherInvalidationMethod)
const IvarToPropMapTy &IvarToPopertyMap,
const ObjCInterfaceDecl *InterfaceD,
bool MissingDeclaration) const;
+
void reportIvarNeedsInvalidation(const ObjCIvarDecl *IvarD,
const IvarToPropMapTy &IvarToPopertyMap,
const ObjCMethodDecl *MethodD) const;
}
return;
}
-
- return;
}
bool IvarInvalidationCheckerImpl::trackIvar(const ObjCIvarDecl *Iv,
VisitStmt(ME);
}
-}
+} // end anonymous namespace
// Register the checkers.
namespace {
-
class IvarInvalidationChecker :
public Checker<check::ASTDecl<ObjCImplementationDecl> > {
public:
Walker.visit(D);
}
};
-}
+} // end anonymous namespace
#define REGISTER_CHECKER(name) \
void ento::register##name(CheckerManager &mgr) { \
REGISTER_CHECKER(InstanceVariableInvalidation)
REGISTER_CHECKER(MissingInvalidationMethod)
-
C.addTransition(
State->set<ArraySizeMap>(ArraySym, SizeV.castAs<DefinedSVal>()));
- return;
}
void ObjCContainersChecker::checkPostStmt(const CallExpr *CE,
const InvalidatedSymbols &Escaped,
const CallEvent *Call,
PointerEscapeKind Kind) const {
- for (InvalidatedSymbols::const_iterator I = Escaped.begin(),
- E = Escaped.end();
- I != E; ++I) {
- SymbolRef Sym = *I;
+ for (const auto &Sym : Escaped) {
// When a symbol for a mutable array escapes, we can't reason precisely
// about its size any more -- so remove it from the map.
// Note that we aren't notified here when a CFMutableArrayRef escapes as a
}
return State;
}
+
/// Register checker.
void ento::registerObjCContainersChecker(CheckerManager &mgr) {
mgr.registerChecker<ObjCContainersChecker>();
report->addRange(SizeE->getSourceRange());
bugreporter::trackNullOrUndefValue(N, SizeE, *report);
C.emitReport(std::move(report));
- return;
}
void VLASizeChecker::checkPreStmt(const DeclStmt *DS, CheckerContext &C) const {
}
LCtx = LCtx->getParent();
}
-
}
// The GDM component containing the dynamic dispatch bifurcation info. When
DynamicDispatchModeInlined = 1,
DynamicDispatchModeConservative
};
-}
+} // end anonymous namespace
+
REGISTER_TRAIT_WITH_PROGRAMSTATE(DynamicDispatchBifurcationMap,
CLANG_ENTO_PROGRAMSTATE_MAP(const MemRegion *,
unsigned))
currBldrCtx->getBlock(),
currStmtIdx);
-
CallEnter Loc(CallE, CalleeSFC, CurLC);
// Construct a new state which contains the mapping from actual to
if (!Opts.mayInlineCXXSharedPtrDtor())
if (isCXXSharedPtrDtor(FD))
return false;
-
}
}
conservativeEvalCall(Call, Bldr, Pred, NoIState);
NumOfDynamicDispatchPathSplits++;
- return;
}
-
void ExprEngine::VisitReturnStmt(const ReturnStmt *RS, ExplodedNode *Pred,
ExplodedNodeSet &Dst) {
-
ExplodedNodeSet dstPreVisit;
getCheckerManager().runCheckersForPreStmt(dstPreVisit, Pred, RS, *this);
template <typename RegionTy, typename A1>
RegionTy* MemRegionManager::getRegion(const A1 a1) {
-
const typename MemRegionManagerTrait<RegionTy>::SuperRegionTy *superRegion =
MemRegionManagerTrait<RegionTy>::getSuperRegion(*this, a1);
template <typename RegionTy, typename A1, typename A2>
RegionTy* MemRegionManager::getRegion(const A1 a1, const A2 a2) {
-
const typename MemRegionManagerTrait<RegionTy>::SuperRegionTy *superRegion =
MemRegionManagerTrait<RegionTy>::getSuperRegion(*this, a1, a2);
template <typename RegionTy, typename A1, typename A2>
RegionTy* MemRegionManager::getSubRegion(const A1 a1, const A2 a2,
const MemRegion *superRegion) {
-
llvm::FoldingSetNodeID ID;
RegionTy::ProfileRegion(ID, a1, a2, superRegion);
void *InsertPos;
template <typename RegionTy, typename A1, typename A2, typename A3>
RegionTy* MemRegionManager::getSubRegion(const A1 a1, const A2 a2, const A3 a3,
const MemRegion *superRegion) {
-
llvm::FoldingSetNodeID ID;
RegionTy::ProfileRegion(ID, a1, a2, a3, superRegion);
void *InsertPos;
os << "'";
printPrettyAsExpr(os);
os << "'";
- return;
}
void MemRegion::printPrettyAsExpr(raw_ostream &os) const {
llvm_unreachable("This region cannot be printed pretty.");
- return;
}
bool VarRegion::canPrintPrettyAsExpr() const {
} else {
os << "field " << "\'" << getDecl()->getName() << "'";
}
- return;
}
bool CXXBaseObjectRegion::canPrintPrettyAsExpr() const {
const CompoundLiteralRegion*
MemRegionManager::getCompoundLiteralRegion(const CompoundLiteralExpr *CL,
const LocationContext *LC) {
-
const MemRegion *sReg = nullptr;
if (CL->isFileScope())
MemRegionManager::getElementRegion(QualType elementType, NonLoc Idx,
const MemRegion* superRegion,
ASTContext &Ctx){
-
QualType T = Ctx.getCanonicalType(elementType).getUnqualifiedType();
llvm::FoldingSetNodeID ID;
PathDiagnosticControlFlowPiece::~PathDiagnosticControlFlowPiece() {}
PathDiagnosticMacroPiece::~PathDiagnosticMacroPiece() {}
-
void PathPieces::flattenTo(PathPieces &Primary, PathPieces &Current,
bool ShouldFlattenMacros) const {
for (PathPieces::const_iterator I = begin(), E = end(); I != E; ++I) {
}
}
-
PathDiagnostic::~PathDiagnostic() {}
PathDiagnostic::PathDiagnostic(StringRef CheckName, const Decl *declWithIssue,
}
static Optional<bool> comparePath(const PathPieces &X, const PathPieces &Y);
+
static Optional<bool>
compareControlFlow(const PathDiagnosticControlFlowPiece &X,
const PathDiagnosticControlFlowPiece &Y) {
// S might be a temporary statement that does not have a location in the
// source code, so find an enclosing statement and use its location.
if (!L.isValid()) {
-
AnalysisDeclContext *ADC;
if (LAC.is<const LocationContext*>())
ADC = LAC.get<const LocationContext*>()->getAnalysisDeclContext();
llvm_unreachable("Unknown CFGElement kind");
}
-
PathDiagnosticLocation
- PathDiagnosticLocation::createBegin(const Decl *D,
- const SourceManager &SM) {
+PathDiagnosticLocation::createBegin(const Decl *D,
+ const SourceManager &SM) {
return PathDiagnosticLocation(D->getLocStart(), SM, SingleLocK);
}
PathDiagnosticLocation
- PathDiagnosticLocation::createBegin(const Stmt *S,
- const SourceManager &SM,
- LocationOrAnalysisDeclContext LAC) {
+PathDiagnosticLocation::createBegin(const Stmt *S,
+ const SourceManager &SM,
+ LocationOrAnalysisDeclContext LAC) {
return PathDiagnosticLocation(getValidSourceLocation(S, LAC),
SM, SingleLocK);
}
-
PathDiagnosticLocation
PathDiagnosticLocation::createEnd(const Stmt *S,
const SourceManager &SM,
}
PathDiagnosticLocation
- PathDiagnosticLocation::createOperatorLoc(const BinaryOperator *BO,
- const SourceManager &SM) {
+PathDiagnosticLocation::createOperatorLoc(const BinaryOperator *BO,
+ const SourceManager &SM) {
return PathDiagnosticLocation(BO->getOperatorLoc(), SM, SingleLocK);
}
PathDiagnosticLocation
- PathDiagnosticLocation::createConditionalColonLoc(
+PathDiagnosticLocation::createConditionalColonLoc(
const ConditionalOperator *CO,
const SourceManager &SM) {
return PathDiagnosticLocation(CO->getColonLoc(), SM, SingleLocK);
PathDiagnosticLocation
- PathDiagnosticLocation::createMemberLoc(const MemberExpr *ME,
- const SourceManager &SM) {
+PathDiagnosticLocation::createMemberLoc(const MemberExpr *ME,
+ const SourceManager &SM) {
return PathDiagnosticLocation(ME->getMemberLoc(), SM, SingleLocK);
}
PathDiagnosticLocation
- PathDiagnosticLocation::createBeginBrace(const CompoundStmt *CS,
- const SourceManager &SM) {
+PathDiagnosticLocation::createBeginBrace(const CompoundStmt *CS,
+ const SourceManager &SM) {
SourceLocation L = CS->getLBracLoc();
return PathDiagnosticLocation(L, SM, SingleLocK);
}
PathDiagnosticLocation
- PathDiagnosticLocation::createEndBrace(const CompoundStmt *CS,
- const SourceManager &SM) {
+PathDiagnosticLocation::createEndBrace(const CompoundStmt *CS,
+ const SourceManager &SM) {
SourceLocation L = CS->getRBracLoc();
return PathDiagnosticLocation(L, SM, SingleLocK);
}
PathDiagnosticLocation
- PathDiagnosticLocation::createDeclBegin(const LocationContext *LC,
- const SourceManager &SM) {
+PathDiagnosticLocation::createDeclBegin(const LocationContext *LC,
+ const SourceManager &SM) {
// FIXME: Should handle CXXTryStmt if analyser starts supporting C++.
if (const CompoundStmt *CS =
dyn_cast_or_null<CompoundStmt>(LC->getDecl()->getBody()))
}
PathDiagnosticLocation
- PathDiagnosticLocation::createDeclEnd(const LocationContext *LC,
- const SourceManager &SM) {
+PathDiagnosticLocation::createDeclEnd(const LocationContext *LC,
+ const SourceManager &SM) {
SourceLocation L = LC->getDecl()->getBodyRBrace();
return PathDiagnosticLocation(L, SM, SingleLocK);
}
PathDiagnosticLocation
- PathDiagnosticLocation::create(const ProgramPoint& P,
- const SourceManager &SMng) {
-
+PathDiagnosticLocation::create(const ProgramPoint& P,
+ const SourceManager &SMng) {
const Stmt* S = nullptr;
if (Optional<BlockEdge> BE = P.getAs<BlockEdge>()) {
const CFGBlock *BSrc = BE->getSrc();
ID.AddInteger(Range.getBegin().getRawEncoding());
ID.AddInteger(Range.getEnd().getRawEncoding());
ID.AddInteger(Loc.getRawEncoding());
- return;
}
void PathDiagnosticPiece::Profile(llvm::FoldingSetNodeID &ID) const {
*column = 0;
if (offset)
*offset = 0;
- return;
}
static void createNullLocation(CXString *filename, unsigned *line,
*column = 0;
if (offset)
*offset = 0;
- return;
}
extern "C" {
unsigned *line,
unsigned *column,
unsigned *offset) {
-
if (!isASTUnitSourceLocation(location)) {
CXLoadedDiagnostic::decodeLocation(location, file, line, column, offset);
return;
CXString *filename,
unsigned *line,
unsigned *column) {
-
if (!isASTUnitSourceLocation(location)) {
// Other SourceLocation implementations do not support presumed locations
// at this time.
unsigned *line,
unsigned *column,
unsigned *offset) {
-
if (!isASTUnitSourceLocation(location)) {
CXLoadedDiagnostic::decodeLocation(location, file, line,
column, offset);
unsigned *line,
unsigned *column,
unsigned *offset) {
-
if (!isASTUnitSourceLocation(location)) {
CXLoadedDiagnostic::decodeLocation(location, file, line,
column, offset);