diff --git a/clang/include/clang/Analysis/RetainSummaryManager.h b/clang/include/clang/Analysis/RetainSummaryManager.h index 6773ea48ef51..1174c4270868 100644 --- a/clang/include/clang/Analysis/RetainSummaryManager.h +++ b/clang/include/clang/Analysis/RetainSummaryManager.h @@ -1,762 +1,767 @@ //=== RetainSummaryManager.h - Summaries for reference counting ---*- C++ -*--// // // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. // See https://llvm.org/LICENSE.txt for license information. // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception // //===----------------------------------------------------------------------===// // // This file defines summaries implementation for retain counting, which // implements a reference count checker for Core Foundation and Cocoa // on (Mac OS X). // //===----------------------------------------------------------------------===// #ifndef LLVM_CLANG_ANALYSIS_RETAINSUMMARY_MANAGER_H #define LLVM_CLANG_ANALYSIS_RETAINSUMMARY_MANAGER_H #include "llvm/ADT/DenseMap.h" #include "llvm/ADT/FoldingSet.h" #include "llvm/ADT/ImmutableMap.h" #include "clang/AST/Attr.h" #include "clang/AST/DeclCXX.h" #include "clang/AST/DeclObjC.h" #include "clang/AST/ParentMap.h" #include "clang/Analysis/AnyCall.h" #include "clang/Analysis/SelectorExtras.h" #include "llvm/ADT/STLExtras.h" using namespace clang; namespace clang { namespace ento { /// Determines the object kind of a tracked object. enum class ObjKind { /// Indicates that the tracked object is a CF object. CF, /// Indicates that the tracked object is an Objective-C object. ObjC, /// Indicates that the tracked object could be a CF or Objective-C object. AnyObj, /// Indicates that the tracked object is a generalized object. Generalized, /// Indicates that the tracking object is a descendant of a /// referenced-counted OSObject, used in the Darwin kernel. OS }; enum ArgEffectKind { /// There is no effect. DoNothing, /// The argument is treated as if an -autorelease message had been sent to /// the referenced object. Autorelease, /// The argument is treated as if the referenced object was deallocated. Dealloc, /// The argument has its reference count decreased by 1. DecRef, /// The argument has its reference count decreased by 1 to model /// a transferred bridge cast under ARC. DecRefBridgedTransferred, /// The argument has its reference count increased by 1. IncRef, /// The argument is a pointer to a retain-counted object; on exit, the new /// value of the pointer is a +0 value. UnretainedOutParameter, /// The argument is a pointer to a retain-counted object; on exit, the new /// value of the pointer is a +1 value. RetainedOutParameter, /// The argument is a pointer to a retain-counted object; on exit, the new /// value of the pointer is a +1 value iff the return code is zero. RetainedOutParameterOnZero, /// The argument is a pointer to a retain-counted object; on exit, the new /// value of the pointer is a +1 value iff the return code is non-zero. RetainedOutParameterOnNonZero, /// The argument is treated as potentially escaping, meaning that /// even when its reference count hits 0 it should be treated as still /// possibly being alive as someone else *may* be holding onto the object. MayEscape, /// All typestate tracking of the object ceases. This is usually employed /// when the effect of the call is completely unknown. StopTracking, /// All typestate tracking of the object ceases. Unlike StopTracking, /// this is also enforced when the method body is inlined. /// /// In some cases, we obtain a better summary for this checker /// by looking at the call site than by inlining the function. /// Signifies that we should stop tracking the symbol even if /// the function is inlined. StopTrackingHard, /// Performs the combined functionality of DecRef and StopTrackingHard. /// /// The models the effect that the called function decrements the reference /// count of the argument and all typestate tracking on that argument /// should cease. DecRefAndStopTrackingHard, }; /// An ArgEffect summarizes the retain count behavior on an argument or receiver /// to a function or method. class ArgEffect { ArgEffectKind K; ObjKind O; public: explicit ArgEffect(ArgEffectKind K = DoNothing, ObjKind O = ObjKind::AnyObj) : K(K), O(O) {} ArgEffectKind getKind() const { return K; } ObjKind getObjKind() const { return O; } ArgEffect withKind(ArgEffectKind NewK) { return ArgEffect(NewK, O); } bool operator==(const ArgEffect &Other) const { return K == Other.K && O == Other.O; } }; /// RetEffect summarizes a call's retain/release behavior with respect /// to its return value. class RetEffect { public: enum Kind { /// Indicates that no retain count information is tracked for /// the return value. NoRet, /// Indicates that the returned value is an owned (+1) symbol. OwnedSymbol, /// Indicates that the returned value is an object with retain count /// semantics but that it is not owned (+0). This is the default /// for getters, etc. NotOwnedSymbol, /// Indicates that the return value is an owned object when the /// receiver is also a tracked object. OwnedWhenTrackedReceiver, // Treat this function as returning a non-tracked symbol even if // the function has been inlined. This is used where the call // site summary is more precise than the summary indirectly produced // by inlining the function NoRetHard }; private: Kind K; ObjKind O; RetEffect(Kind k, ObjKind o = ObjKind::AnyObj) : K(k), O(o) {} public: Kind getKind() const { return K; } ObjKind getObjKind() const { return O; } bool isOwned() const { return K == OwnedSymbol || K == OwnedWhenTrackedReceiver; } bool notOwned() const { return K == NotOwnedSymbol; } bool operator==(const RetEffect &Other) const { return K == Other.K && O == Other.O; } static RetEffect MakeOwnedWhenTrackedReceiver() { return RetEffect(OwnedWhenTrackedReceiver, ObjKind::ObjC); } static RetEffect MakeOwned(ObjKind o) { return RetEffect(OwnedSymbol, o); } static RetEffect MakeNotOwned(ObjKind o) { return RetEffect(NotOwnedSymbol, o); } static RetEffect MakeNoRet() { return RetEffect(NoRet); } static RetEffect MakeNoRetHard() { return RetEffect(NoRetHard); } }; /// A key identifying a summary. class ObjCSummaryKey { IdentifierInfo* II; Selector S; public: ObjCSummaryKey(IdentifierInfo* ii, Selector s) : II(ii), S(s) {} ObjCSummaryKey(const ObjCInterfaceDecl *d, Selector s) : II(d ? d->getIdentifier() : nullptr), S(s) {} ObjCSummaryKey(Selector s) : II(nullptr), S(s) {} IdentifierInfo *getIdentifier() const { return II; } Selector getSelector() const { return S; } }; } // end namespace ento } // end namespace clang using namespace ento; namespace llvm { //===----------------------------------------------------------------------===// // Adapters for FoldingSet. //===----------------------------------------------------------------------===// template <> struct FoldingSetTrait { static inline void Profile(const ArgEffect X, FoldingSetNodeID &ID) { ID.AddInteger((unsigned) X.getKind()); ID.AddInteger((unsigned) X.getObjKind()); } }; template <> struct FoldingSetTrait { static inline void Profile(const RetEffect &X, FoldingSetNodeID &ID) { ID.AddInteger((unsigned) X.getKind()); ID.AddInteger((unsigned) X.getObjKind()); } }; template <> struct DenseMapInfo { static inline ObjCSummaryKey getEmptyKey() { return ObjCSummaryKey(DenseMapInfo::getEmptyKey(), DenseMapInfo::getEmptyKey()); } static inline ObjCSummaryKey getTombstoneKey() { return ObjCSummaryKey(DenseMapInfo::getTombstoneKey(), DenseMapInfo::getTombstoneKey()); } static unsigned getHashValue(const ObjCSummaryKey &V) { typedef std::pair PairTy; return DenseMapInfo::getHashValue(PairTy(V.getIdentifier(), V.getSelector())); } static bool isEqual(const ObjCSummaryKey& LHS, const ObjCSummaryKey& RHS) { return LHS.getIdentifier() == RHS.getIdentifier() && LHS.getSelector() == RHS.getSelector(); } }; } // end llvm namespace namespace clang { namespace ento { /// ArgEffects summarizes the effects of a function/method call on all of /// its arguments. typedef llvm::ImmutableMap ArgEffects; /// Summary for a function with respect to ownership changes. class RetainSummary { /// Args - a map of (index, ArgEffect) pairs, where index /// specifies the argument (starting from 0). This can be sparsely /// populated; arguments with no entry in Args use 'DefaultArgEffect'. ArgEffects Args; /// DefaultArgEffect - The default ArgEffect to apply to arguments that /// do not have an entry in Args. ArgEffect DefaultArgEffect; /// Receiver - If this summary applies to an Objective-C message expression, /// this is the effect applied to the state of the receiver. ArgEffect Receiver; /// Effect on "this" pointer - applicable only to C++ method calls. ArgEffect This; /// Ret - The effect on the return value. Used to indicate if the /// function/method call returns a new tracked symbol. RetEffect Ret; public: RetainSummary(ArgEffects A, RetEffect R, ArgEffect defaultEff, ArgEffect ReceiverEff, ArgEffect ThisEff) : Args(A), DefaultArgEffect(defaultEff), Receiver(ReceiverEff), This(ThisEff), Ret(R) {} /// getArg - Return the argument effect on the argument specified by /// idx (starting from 0). ArgEffect getArg(unsigned idx) const { if (const ArgEffect *AE = Args.lookup(idx)) return *AE; return DefaultArgEffect; } void addArg(ArgEffects::Factory &af, unsigned idx, ArgEffect e) { Args = af.add(Args, idx, e); } /// setDefaultArgEffect - Set the default argument effect. void setDefaultArgEffect(ArgEffect E) { DefaultArgEffect = E; } /// getRetEffect - Returns the effect on the return value of the call. RetEffect getRetEffect() const { return Ret; } /// setRetEffect - Set the effect of the return value of the call. void setRetEffect(RetEffect E) { Ret = E; } /// Sets the effect on the receiver of the message. void setReceiverEffect(ArgEffect e) { Receiver = e; } /// getReceiverEffect - Returns the effect on the receiver of the call. /// This is only meaningful if the summary applies to an ObjCMessageExpr*. ArgEffect getReceiverEffect() const { return Receiver; } /// \return the effect on the "this" receiver of the method call. /// This is only meaningful if the summary applies to CXXMethodDecl*. ArgEffect getThisEffect() const { return This; } + ArgEffect getDefaultEffect() const { return DefaultArgEffect; } + /// Set the effect of the method on "this". void setThisEffect(ArgEffect e) { This = e; } bool isNoop() const { return Ret == RetEffect::MakeNoRet() && Receiver.getKind() == DoNothing && DefaultArgEffect.getKind() == MayEscape && This.getKind() == DoNothing && Args.isEmpty(); } /// Test if two retain summaries are identical. Note that merely equivalent /// summaries are not necessarily identical (for example, if an explicit /// argument effect matches the default effect). bool operator==(const RetainSummary &Other) const { return Args == Other.Args && DefaultArgEffect == Other.DefaultArgEffect && Receiver == Other.Receiver && This == Other.This && Ret == Other.Ret; } /// Profile this summary for inclusion in a FoldingSet. void Profile(llvm::FoldingSetNodeID& ID) const { ID.Add(Args); ID.Add(DefaultArgEffect); ID.Add(Receiver); ID.Add(This); ID.Add(Ret); } /// A retain summary is simple if it has no ArgEffects other than the default. bool isSimple() const { return Args.isEmpty(); } ArgEffects getArgEffects() const { return Args; } private: ArgEffect getDefaultArgEffect() const { return DefaultArgEffect; } friend class RetainSummaryManager; }; class ObjCSummaryCache { typedef llvm::DenseMap MapTy; MapTy M; public: ObjCSummaryCache() {} const RetainSummary * find(const ObjCInterfaceDecl *D, Selector S) { // Do a lookup with the (D,S) pair. If we find a match return // the iterator. ObjCSummaryKey K(D, S); MapTy::iterator I = M.find(K); if (I != M.end()) return I->second; if (!D) return nullptr; // Walk the super chain. If we find a hit with a parent, we'll end // up returning that summary. We actually allow that key (null,S), as // we cache summaries for the null ObjCInterfaceDecl* to allow us to // generate initial summaries without having to worry about NSObject // being declared. // FIXME: We may change this at some point. for (ObjCInterfaceDecl *C=D->getSuperClass() ;; C=C->getSuperClass()) { if ((I = M.find(ObjCSummaryKey(C, S))) != M.end()) break; if (!C) return nullptr; } // Cache the summary with original key to make the next lookup faster // and return the iterator. const RetainSummary *Summ = I->second; M[K] = Summ; return Summ; } const RetainSummary *find(IdentifierInfo* II, Selector S) { // FIXME: Class method lookup. Right now we don't have a good way // of going between IdentifierInfo* and the class hierarchy. MapTy::iterator I = M.find(ObjCSummaryKey(II, S)); if (I == M.end()) I = M.find(ObjCSummaryKey(S)); return I == M.end() ? nullptr : I->second; } const RetainSummary *& operator[](ObjCSummaryKey K) { return M[K]; } const RetainSummary *& operator[](Selector S) { return M[ ObjCSummaryKey(S) ]; } }; class RetainSummaryTemplate; class RetainSummaryManager { typedef llvm::DenseMap FuncSummariesTy; typedef ObjCSummaryCache ObjCMethodSummariesTy; typedef llvm::FoldingSetNodeWrapper CachedSummaryNode; /// Ctx - The ASTContext object for the analyzed ASTs. ASTContext &Ctx; /// Records whether or not the analyzed code runs in ARC mode. const bool ARCEnabled; /// Track Objective-C and CoreFoundation objects. const bool TrackObjCAndCFObjects; /// Track sublcasses of OSObject. const bool TrackOSObjects; /// FuncSummaries - A map from FunctionDecls to summaries. FuncSummariesTy FuncSummaries; /// ObjCClassMethodSummaries - A map from selectors (for instance methods) /// to summaries. ObjCMethodSummariesTy ObjCClassMethodSummaries; /// ObjCMethodSummaries - A map from selectors to summaries. ObjCMethodSummariesTy ObjCMethodSummaries; /// BPAlloc - A BumpPtrAllocator used for allocating summaries, ArgEffects, /// and all other data used by the checker. llvm::BumpPtrAllocator BPAlloc; /// AF - A factory for ArgEffects objects. ArgEffects::Factory AF; /// ObjCAllocRetE - Default return effect for methods returning Objective-C /// objects. RetEffect ObjCAllocRetE; /// ObjCInitRetE - Default return effect for init methods returning /// Objective-C objects. RetEffect ObjCInitRetE; /// SimpleSummaries - Used for uniquing summaries that don't have special /// effects. llvm::FoldingSet SimpleSummaries; /// Create an OS object at +1. const RetainSummary *getOSSummaryCreateRule(const FunctionDecl *FD); /// Get an OS object at +0. const RetainSummary *getOSSummaryGetRule(const FunctionDecl *FD); /// Increment the reference count on OS object. const RetainSummary *getOSSummaryRetainRule(const FunctionDecl *FD); /// Decrement the reference count on OS object. const RetainSummary *getOSSummaryReleaseRule(const FunctionDecl *FD); /// Free the OS object. const RetainSummary *getOSSummaryFreeRule(const FunctionDecl *FD); const RetainSummary *getUnarySummary(const FunctionType* FT, ArgEffectKind AE); const RetainSummary *getCFSummaryCreateRule(const FunctionDecl *FD); const RetainSummary *getCFSummaryGetRule(const FunctionDecl *FD); const RetainSummary *getCFCreateGetRuleSummary(const FunctionDecl *FD); const RetainSummary *getPersistentSummary(const RetainSummary &OldSumm); const RetainSummary * getPersistentSummary(RetEffect RetEff, ArgEffects ScratchArgs, ArgEffect ReceiverEff = ArgEffect(DoNothing), ArgEffect DefaultEff = ArgEffect(MayEscape), ArgEffect ThisEff = ArgEffect(DoNothing)) { RetainSummary Summ(ScratchArgs, RetEff, DefaultEff, ReceiverEff, ThisEff); return getPersistentSummary(Summ); } const RetainSummary *getDoNothingSummary() { return getPersistentSummary(RetEffect::MakeNoRet(), ArgEffects(AF.getEmptyMap()), ArgEffect(DoNothing), ArgEffect(DoNothing)); } const RetainSummary *getDefaultSummary() { return getPersistentSummary(RetEffect::MakeNoRet(), ArgEffects(AF.getEmptyMap()), ArgEffect(DoNothing), ArgEffect(MayEscape)); } const RetainSummary *getPersistentStopSummary() { return getPersistentSummary( RetEffect::MakeNoRet(), ArgEffects(AF.getEmptyMap()), ArgEffect(StopTracking), ArgEffect(StopTracking)); } void InitializeClassMethodSummaries(); void InitializeMethodSummaries(); void addNSObjectClsMethSummary(Selector S, const RetainSummary *Summ) { ObjCClassMethodSummaries[S] = Summ; } void addNSObjectMethSummary(Selector S, const RetainSummary *Summ) { ObjCMethodSummaries[S] = Summ; } void addClassMethSummary(const char* Cls, const char* name, const RetainSummary *Summ, bool isNullary = true) { IdentifierInfo* ClsII = &Ctx.Idents.get(Cls); Selector S = isNullary ? GetNullarySelector(name, Ctx) : GetUnarySelector(name, Ctx); ObjCClassMethodSummaries[ObjCSummaryKey(ClsII, S)] = Summ; } void addInstMethSummary(const char* Cls, const char* nullaryName, const RetainSummary *Summ) { IdentifierInfo* ClsII = &Ctx.Idents.get(Cls); Selector S = GetNullarySelector(nullaryName, Ctx); ObjCMethodSummaries[ObjCSummaryKey(ClsII, S)] = Summ; } template void addMethodSummary(IdentifierInfo *ClsII, ObjCMethodSummariesTy &Summaries, const RetainSummary *Summ, Keywords *... Kws) { Selector S = getKeywordSelector(Ctx, Kws...); Summaries[ObjCSummaryKey(ClsII, S)] = Summ; } template void addInstMethSummary(const char *Cls, const RetainSummary *Summ, Keywords *... Kws) { addMethodSummary(&Ctx.Idents.get(Cls), ObjCMethodSummaries, Summ, Kws...); } template void addClsMethSummary(const char *Cls, const RetainSummary *Summ, Keywords *... Kws) { addMethodSummary(&Ctx.Idents.get(Cls), ObjCClassMethodSummaries, Summ, Kws...); } template void addClsMethSummary(IdentifierInfo *II, const RetainSummary *Summ, Keywords *... Kws) { addMethodSummary(II, ObjCClassMethodSummaries, Summ, Kws...); } const RetainSummary * generateSummary(const FunctionDecl *FD, bool &AllowAnnotations); /// Return a summary for OSObject, or nullptr if not found. const RetainSummary *getSummaryForOSObject(const FunctionDecl *FD, StringRef FName, QualType RetTy); /// Return a summary for Objective-C or CF object, or nullptr if not found. const RetainSummary *getSummaryForObjCOrCFObject( const FunctionDecl *FD, StringRef FName, QualType RetTy, const FunctionType *FT, bool &AllowAnnotations); /// Apply the annotation of {@code pd} in function {@code FD} /// to the resulting summary stored in out-parameter {@code Template}. /// \return whether an annotation was applied. bool applyParamAnnotationEffect(const ParmVarDecl *pd, unsigned parm_idx, const NamedDecl *FD, RetainSummaryTemplate &Template); public: RetainSummaryManager(ASTContext &ctx, bool trackObjCAndCFObjects, bool trackOSObjects) : Ctx(ctx), ARCEnabled((bool)Ctx.getLangOpts().ObjCAutoRefCount), TrackObjCAndCFObjects(trackObjCAndCFObjects), TrackOSObjects(trackOSObjects), AF(BPAlloc), ObjCAllocRetE(ARCEnabled ? RetEffect::MakeNotOwned(ObjKind::ObjC) : RetEffect::MakeOwned(ObjKind::ObjC)), ObjCInitRetE(ARCEnabled ? RetEffect::MakeNotOwned(ObjKind::ObjC) : RetEffect::MakeOwnedWhenTrackedReceiver()) { InitializeClassMethodSummaries(); InitializeMethodSummaries(); } enum class BehaviorSummary { // Function does not return. NoOp, // Function returns the first argument. Identity, // Function returns "this" argument. IdentityThis, // Function either returns zero, or the input parameter. IdentityOrZero }; Optional canEval(const CallExpr *CE, const FunctionDecl *FD, bool &hasTrustedImplementationAnnotation); /// \return Whether the type corresponds to a known smart pointer /// implementation (that is, everything about it is inlineable). static bool isKnownSmartPointer(QualType QT); bool isTrustedReferenceCountImplementation(const FunctionDecl *FD); const RetainSummary *getSummary(AnyCall C, bool HasNonZeroCallbackArg=false, bool IsReceiverUnconsumedSelf=false, QualType ReceiverType={}); RetEffect getObjAllocRetEffect() const { return ObjCAllocRetE; } private: /// getMethodSummary - This version of getMethodSummary is used to query /// the summary for the current method being analyzed. const RetainSummary *getMethodSummary(const ObjCMethodDecl *MD); const RetainSummary *getFunctionSummary(const FunctionDecl *FD); const RetainSummary *getMethodSummary(Selector S, const ObjCInterfaceDecl *ID, const ObjCMethodDecl *MD, QualType RetTy, ObjCMethodSummariesTy &CachedSummaries); const RetainSummary * getInstanceMethodSummary(const ObjCMessageExpr *ME, QualType ReceiverType); const RetainSummary *getClassMethodSummary(const ObjCMessageExpr *ME); const RetainSummary *getStandardMethodSummary(const ObjCMethodDecl *MD, Selector S, QualType RetTy); /// Determine if there is a special return effect for this function or method. Optional getRetEffectFromAnnotations(QualType RetTy, const Decl *D); void updateSummaryFromAnnotations(const RetainSummary *&Summ, const ObjCMethodDecl *MD); void updateSummaryFromAnnotations(const RetainSummary *&Summ, const FunctionDecl *FD); const RetainSummary *updateSummaryForNonZeroCallbackArg(const RetainSummary *S, AnyCall &C); /// Special case '[super init];' and '[self init];' /// /// Even though calling '[super init]' without assigning the result to self /// and checking if the parent returns 'nil' is a bad pattern, it is common. /// Additionally, our Self Init checker already warns about it. To avoid /// overwhelming the user with messages from both checkers, we model the case /// of '[super init]' in cases when it is not consumed by another expression /// as if the call preserves the value of 'self'; essentially, assuming it can /// never fail and return 'nil'. /// Note, we don't want to just stop tracking the value since we want the /// RetainCount checker to report leaks and use-after-free if SelfInit checker /// is turned off. void updateSummaryForReceiverUnconsumedSelf(const RetainSummary *&S); + /// Set argument types for arguments which are not doing anything. + void updateSummaryForArgumentTypes(const AnyCall &C, const RetainSummary *&RS); + /// Determine whether a declaration {@code D} of correspondent type (return /// type for functions/methods) {@code QT} has any of the given attributes, /// provided they pass necessary validation checks AND tracking the given /// attribute is enabled. /// Returns the object kind corresponding to the present attribute, or None, /// if none of the specified attributes are present. /// Crashes if passed an attribute which is not explicitly handled. template Optional hasAnyEnabledAttrOf(const Decl *D, QualType QT); template Optional hasAnyEnabledAttrOf(const Decl *D, QualType QT); friend class RetainSummaryTemplate; }; // Used to avoid allocating long-term (BPAlloc'd) memory for default retain // summaries. If a function or method looks like it has a default summary, but // it has annotations, the annotations are added to the stack-based template // and then copied into managed memory. class RetainSummaryTemplate { RetainSummaryManager &Manager; const RetainSummary *&RealSummary; RetainSummary ScratchSummary; bool Accessed; public: RetainSummaryTemplate(const RetainSummary *&real, RetainSummaryManager &mgr) : Manager(mgr), RealSummary(real), ScratchSummary(*real), Accessed(false) {} ~RetainSummaryTemplate() { if (Accessed) RealSummary = Manager.getPersistentSummary(ScratchSummary); } RetainSummary &operator*() { Accessed = true; return ScratchSummary; } RetainSummary *operator->() { Accessed = true; return &ScratchSummary; } }; } // end namespace ento } // end namespace clang #endif diff --git a/clang/lib/Analysis/RetainSummaryManager.cpp b/clang/lib/Analysis/RetainSummaryManager.cpp index 9a514efb7c30..c3611711974a 100644 --- a/clang/lib/Analysis/RetainSummaryManager.cpp +++ b/clang/lib/Analysis/RetainSummaryManager.cpp @@ -1,1229 +1,1272 @@ //== RetainSummaryManager.cpp - Summaries for reference counting --*- C++ -*--// // // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. // See https://llvm.org/LICENSE.txt for license information. // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception // //===----------------------------------------------------------------------===// // // This file defines summaries implementation for retain counting, which // implements a reference count checker for Core Foundation, Cocoa // and OSObject (on Mac OS X). // //===----------------------------------------------------------------------===// #include "clang/Analysis/DomainSpecific/CocoaConventions.h" #include "clang/Analysis/RetainSummaryManager.h" #include "clang/AST/Attr.h" #include "clang/AST/DeclCXX.h" #include "clang/AST/DeclObjC.h" #include "clang/AST/ParentMap.h" #include "clang/ASTMatchers/ASTMatchFinder.h" using namespace clang; using namespace ento; template constexpr static bool isOneOf() { return false; } /// Helper function to check whether the class is one of the /// rest of varargs. template constexpr static bool isOneOf() { return std::is_same::value || isOneOf(); } namespace { /// Fake attribute class for RC* attributes. struct GeneralizedReturnsRetainedAttr { static bool classof(const Attr *A) { if (auto AA = dyn_cast(A)) return AA->getAnnotation() == "rc_ownership_returns_retained"; return false; } }; struct GeneralizedReturnsNotRetainedAttr { static bool classof(const Attr *A) { if (auto AA = dyn_cast(A)) return AA->getAnnotation() == "rc_ownership_returns_not_retained"; return false; } }; struct GeneralizedConsumedAttr { static bool classof(const Attr *A) { if (auto AA = dyn_cast(A)) return AA->getAnnotation() == "rc_ownership_consumed"; return false; } }; } template Optional RetainSummaryManager::hasAnyEnabledAttrOf(const Decl *D, QualType QT) { ObjKind K; if (isOneOf()) { if (!TrackObjCAndCFObjects) return None; K = ObjKind::CF; } else if (isOneOf()) { if (!TrackObjCAndCFObjects) return None; if (isOneOf() && !cocoa::isCocoaObjectRef(QT)) return None; K = ObjKind::ObjC; } else if (isOneOf()) { if (!TrackOSObjects) return None; K = ObjKind::OS; } else if (isOneOf()) { K = ObjKind::Generalized; } else { llvm_unreachable("Unexpected attribute"); } if (D->hasAttr()) return K; return None; } template Optional RetainSummaryManager::hasAnyEnabledAttrOf(const Decl *D, QualType QT) { if (auto Out = hasAnyEnabledAttrOf(D, QT)) return Out; return hasAnyEnabledAttrOf(D, QT); } const RetainSummary * RetainSummaryManager::getPersistentSummary(const RetainSummary &OldSumm) { // Unique "simple" summaries -- those without ArgEffects. if (OldSumm.isSimple()) { ::llvm::FoldingSetNodeID ID; OldSumm.Profile(ID); void *Pos; CachedSummaryNode *N = SimpleSummaries.FindNodeOrInsertPos(ID, Pos); if (!N) { N = (CachedSummaryNode *) BPAlloc.Allocate(); new (N) CachedSummaryNode(OldSumm); SimpleSummaries.InsertNode(N, Pos); } return &N->getValue(); } RetainSummary *Summ = (RetainSummary *) BPAlloc.Allocate(); new (Summ) RetainSummary(OldSumm); return Summ; } static bool isSubclass(const Decl *D, StringRef ClassName) { using namespace ast_matchers; DeclarationMatcher SubclassM = cxxRecordDecl(isSameOrDerivedFrom(ClassName)); return !(match(SubclassM, *D, D->getASTContext()).empty()); } static bool isOSObjectSubclass(const Decl *D) { - return isSubclass(D, "OSMetaClassBase"); + return D && isSubclass(D, "OSMetaClassBase"); } static bool isOSObjectDynamicCast(StringRef S) { return S == "safeMetaCast"; } static bool isOSObjectThisCast(StringRef S) { return S == "metaCast"; } + +static bool isOSObjectPtr(QualType QT) { + return isOSObjectSubclass(QT->getPointeeCXXRecordDecl()); +} + +static bool isISLObjectRef(QualType Ty) { + return StringRef(Ty.getAsString()).startswith("isl_"); +} + static bool isOSIteratorSubclass(const Decl *D) { return isSubclass(D, "OSIterator"); } static bool hasRCAnnotation(const Decl *D, StringRef rcAnnotation) { for (const auto *Ann : D->specific_attrs()) { if (Ann->getAnnotation() == rcAnnotation) return true; } return false; } static bool isRetain(const FunctionDecl *FD, StringRef FName) { return FName.startswith_lower("retain") || FName.endswith_lower("retain"); } static bool isRelease(const FunctionDecl *FD, StringRef FName) { return FName.startswith_lower("release") || FName.endswith_lower("release"); } static bool isAutorelease(const FunctionDecl *FD, StringRef FName) { return FName.startswith_lower("autorelease") || FName.endswith_lower("autorelease"); } static bool isMakeCollectable(StringRef FName) { return FName.contains_lower("MakeCollectable"); } /// A function is OSObject related if it is declared on a subclass /// of OSObject, or any of the parameters is a subclass of an OSObject. static bool isOSObjectRelated(const CXXMethodDecl *MD) { if (isOSObjectSubclass(MD->getParent())) return true; for (ParmVarDecl *Param : MD->parameters()) { QualType PT = Param->getType()->getPointeeType(); if (!PT.isNull()) if (CXXRecordDecl *RD = PT->getAsCXXRecordDecl()) if (isOSObjectSubclass(RD)) return true; } return false; } bool RetainSummaryManager::isKnownSmartPointer(QualType QT) { QT = QT.getCanonicalType(); const auto *RD = QT->getAsCXXRecordDecl(); if (!RD) return false; const IdentifierInfo *II = RD->getIdentifier(); if (II && II->getName() == "smart_ptr") if (const auto *ND = dyn_cast(RD->getDeclContext())) if (ND->getNameAsString() == "os") return true; return false; } const RetainSummary * RetainSummaryManager::getSummaryForOSObject(const FunctionDecl *FD, StringRef FName, QualType RetTy) { if (RetTy->isPointerType()) { const CXXRecordDecl *PD = RetTy->getPointeeType()->getAsCXXRecordDecl(); if (PD && isOSObjectSubclass(PD)) { if (const IdentifierInfo *II = FD->getIdentifier()) { StringRef FuncName = II->getName(); if (isOSObjectDynamicCast(FuncName) || isOSObjectThisCast(FuncName)) return getDefaultSummary(); // All objects returned with functions *not* starting with // get, or iterators, are returned at +1. if ((!FuncName.startswith("get") && !FuncName.startswith("Get")) || isOSIteratorSubclass(PD)) { return getOSSummaryCreateRule(FD); } else { return getOSSummaryGetRule(FD); } } } } if (const auto *MD = dyn_cast(FD)) { const CXXRecordDecl *Parent = MD->getParent(); if (TrackOSObjects && Parent && isOSObjectSubclass(Parent)) { if (FName == "release" || FName == "taggedRelease") return getOSSummaryReleaseRule(FD); if (FName == "retain" || FName == "taggedRetain") return getOSSummaryRetainRule(FD); if (FName == "free") return getOSSummaryFreeRule(FD); if (MD->getOverloadedOperator() == OO_New) return getOSSummaryCreateRule(MD); } } return nullptr; } const RetainSummary *RetainSummaryManager::getSummaryForObjCOrCFObject( const FunctionDecl *FD, StringRef FName, QualType RetTy, const FunctionType *FT, bool &AllowAnnotations) { ArgEffects ScratchArgs(AF.getEmptyMap()); std::string RetTyName = RetTy.getAsString(); if (FName == "pthread_create" || FName == "pthread_setspecific") { // Part of: and . // This will be addressed better with IPA. return getPersistentStopSummary(); } else if(FName == "NSMakeCollectable") { // Handle: id NSMakeCollectable(CFTypeRef) AllowAnnotations = false; return RetTy->isObjCIdType() ? getUnarySummary(FT, DoNothing) : getPersistentStopSummary(); } else if (FName == "CMBufferQueueDequeueAndRetain" || FName == "CMBufferQueueDequeueIfDataReadyAndRetain") { // Part of: . return getPersistentSummary(RetEffect::MakeOwned(ObjKind::CF), ScratchArgs, ArgEffect(DoNothing), ArgEffect(DoNothing)); } else if (FName == "CFPlugInInstanceCreate") { return getPersistentSummary(RetEffect::MakeNoRet(), ScratchArgs); } else if (FName == "IORegistryEntrySearchCFProperty" || (RetTyName == "CFMutableDictionaryRef" && (FName == "IOBSDNameMatching" || FName == "IOServiceMatching" || FName == "IOServiceNameMatching" || FName == "IORegistryEntryIDMatching" || FName == "IOOpenFirmwarePathMatching"))) { // Part of . (IOKit) // This should be addressed using a API table. return getPersistentSummary(RetEffect::MakeOwned(ObjKind::CF), ScratchArgs, ArgEffect(DoNothing), ArgEffect(DoNothing)); } else if (FName == "IOServiceGetMatchingService" || FName == "IOServiceGetMatchingServices") { // FIXES: // This should be addressed using a API table. This strcmp is also // a little gross, but there is no need to super optimize here. ScratchArgs = AF.add(ScratchArgs, 1, ArgEffect(DecRef, ObjKind::CF)); return getPersistentSummary(RetEffect::MakeNoRet(), ScratchArgs, ArgEffect(DoNothing), ArgEffect(DoNothing)); } else if (FName == "IOServiceAddNotification" || FName == "IOServiceAddMatchingNotification") { // Part of . (IOKit) // This should be addressed using a API table. ScratchArgs = AF.add(ScratchArgs, 2, ArgEffect(DecRef, ObjKind::CF)); return getPersistentSummary(RetEffect::MakeNoRet(), ScratchArgs, ArgEffect(DoNothing), ArgEffect(DoNothing)); } else if (FName == "CVPixelBufferCreateWithBytes") { // FIXES: // Eventually this can be improved by recognizing that the pixel // buffer passed to CVPixelBufferCreateWithBytes is released via // a callback and doing full IPA to make sure this is done correctly. // FIXME: This function has an out parameter that returns an // allocated object. ScratchArgs = AF.add(ScratchArgs, 7, ArgEffect(StopTracking)); return getPersistentSummary(RetEffect::MakeNoRet(), ScratchArgs, ArgEffect(DoNothing), ArgEffect(DoNothing)); } else if (FName == "CGBitmapContextCreateWithData") { // FIXES: // Eventually this can be improved by recognizing that 'releaseInfo' // passed to CGBitmapContextCreateWithData is released via // a callback and doing full IPA to make sure this is done correctly. ScratchArgs = AF.add(ScratchArgs, 8, ArgEffect(ArgEffect(StopTracking))); return getPersistentSummary(RetEffect::MakeOwned(ObjKind::CF), ScratchArgs, ArgEffect(DoNothing), ArgEffect(DoNothing)); } else if (FName == "CVPixelBufferCreateWithPlanarBytes") { // FIXES: // Eventually this can be improved by recognizing that the pixel // buffer passed to CVPixelBufferCreateWithPlanarBytes is released // via a callback and doing full IPA to make sure this is done // correctly. ScratchArgs = AF.add(ScratchArgs, 12, ArgEffect(StopTracking)); return getPersistentSummary(RetEffect::MakeNoRet(), ScratchArgs, ArgEffect(DoNothing), ArgEffect(DoNothing)); } else if (FName == "VTCompressionSessionEncodeFrame") { // The context argument passed to VTCompressionSessionEncodeFrame() // is passed to the callback specified when creating the session // (e.g. with VTCompressionSessionCreate()) which can release it. // To account for this possibility, conservatively stop tracking // the context. ScratchArgs = AF.add(ScratchArgs, 5, ArgEffect(StopTracking)); return getPersistentSummary(RetEffect::MakeNoRet(), ScratchArgs, ArgEffect(DoNothing), ArgEffect(DoNothing)); } else if (FName == "dispatch_set_context" || FName == "xpc_connection_set_context") { // - The analyzer currently doesn't have // a good way to reason about the finalizer function for libdispatch. // If we pass a context object that is memory managed, stop tracking it. // - Same problem, but for XPC. // FIXME: this hack should possibly go away once we can handle // libdispatch and XPC finalizers. ScratchArgs = AF.add(ScratchArgs, 1, ArgEffect(StopTracking)); return getPersistentSummary(RetEffect::MakeNoRet(), ScratchArgs, ArgEffect(DoNothing), ArgEffect(DoNothing)); } else if (FName.startswith("NSLog")) { return getDoNothingSummary(); } else if (FName.startswith("NS") && (FName.find("Insert") != StringRef::npos)) { // Whitelist NSXXInsertXX, for example NSMapInsertIfAbsent, since they can // be deallocated by NSMapRemove. (radar://11152419) ScratchArgs = AF.add(ScratchArgs, 1, ArgEffect(StopTracking)); ScratchArgs = AF.add(ScratchArgs, 2, ArgEffect(StopTracking)); return getPersistentSummary(RetEffect::MakeNoRet(), ScratchArgs, ArgEffect(DoNothing), ArgEffect(DoNothing)); } if (RetTy->isPointerType()) { // For CoreFoundation ('CF') types. if (cocoa::isRefType(RetTy, "CF", FName)) { if (isRetain(FD, FName)) { // CFRetain isn't supposed to be annotated. However, this may as // well be a user-made "safe" CFRetain function that is incorrectly // annotated as cf_returns_retained due to lack of better options. // We want to ignore such annotation. AllowAnnotations = false; return getUnarySummary(FT, IncRef); } else if (isAutorelease(FD, FName)) { // The headers use cf_consumed, but we can fully model CFAutorelease // ourselves. AllowAnnotations = false; return getUnarySummary(FT, Autorelease); } else if (isMakeCollectable(FName)) { AllowAnnotations = false; return getUnarySummary(FT, DoNothing); } else { return getCFCreateGetRuleSummary(FD); } } // For CoreGraphics ('CG') and CoreVideo ('CV') types. if (cocoa::isRefType(RetTy, "CG", FName) || cocoa::isRefType(RetTy, "CV", FName)) { if (isRetain(FD, FName)) return getUnarySummary(FT, IncRef); else return getCFCreateGetRuleSummary(FD); } // For all other CF-style types, use the Create/Get // rule for summaries but don't support Retain functions // with framework-specific prefixes. if (coreFoundation::isCFObjectRef(RetTy)) { return getCFCreateGetRuleSummary(FD); } if (FD->hasAttr()) { return getCFCreateGetRuleSummary(FD); } } // Check for release functions, the only kind of functions that we care // about that don't return a pointer type. if (FName.startswith("CG") || FName.startswith("CF")) { // Test for 'CGCF'. FName = FName.substr(FName.startswith("CGCF") ? 4 : 2); if (isRelease(FD, FName)) return getUnarySummary(FT, DecRef); else { assert(ScratchArgs.isEmpty()); // Remaining CoreFoundation and CoreGraphics functions. // We use to assume that they all strictly followed the ownership idiom // and that ownership cannot be transferred. While this is technically // correct, many methods allow a tracked object to escape. For example: // // CFMutableDictionaryRef x = CFDictionaryCreateMutable(...); // CFDictionaryAddValue(y, key, x); // CFRelease(x); // ... it is okay to use 'x' since 'y' has a reference to it // // We handle this and similar cases with the follow heuristic. If the // function name contains "InsertValue", "SetValue", "AddValue", // "AppendValue", or "SetAttribute", then we assume that arguments may // "escape." This means that something else holds on to the object, // allowing it be used even after its local retain count drops to 0. ArgEffectKind E = (StrInStrNoCase(FName, "InsertValue") != StringRef::npos || StrInStrNoCase(FName, "AddValue") != StringRef::npos || StrInStrNoCase(FName, "SetValue") != StringRef::npos || StrInStrNoCase(FName, "AppendValue") != StringRef::npos || StrInStrNoCase(FName, "SetAttribute") != StringRef::npos) ? MayEscape : DoNothing; return getPersistentSummary(RetEffect::MakeNoRet(), ScratchArgs, ArgEffect(DoNothing), ArgEffect(E, ObjKind::CF)); } } return nullptr; } const RetainSummary * RetainSummaryManager::generateSummary(const FunctionDecl *FD, bool &AllowAnnotations) { // We generate "stop" summaries for implicitly defined functions. if (FD->isImplicit()) return getPersistentStopSummary(); const IdentifierInfo *II = FD->getIdentifier(); StringRef FName = II ? II->getName() : ""; // Strip away preceding '_'. Doing this here will effect all the checks // down below. FName = FName.substr(FName.find_first_not_of('_')); // Inspect the result type. Strip away any typedefs. const auto *FT = FD->getType()->getAs(); QualType RetTy = FT->getReturnType(); if (TrackOSObjects) if (const RetainSummary *S = getSummaryForOSObject(FD, FName, RetTy)) return S; if (TrackObjCAndCFObjects) if (const RetainSummary *S = getSummaryForObjCOrCFObject(FD, FName, RetTy, FT, AllowAnnotations)) return S; if (const auto *MD = dyn_cast(FD)) if (!(TrackOSObjects && isOSObjectRelated(MD))) return getPersistentSummary(RetEffect::MakeNoRet(), ArgEffects(AF.getEmptyMap()), ArgEffect(DoNothing), ArgEffect(StopTracking), ArgEffect(DoNothing)); return getDefaultSummary(); } const RetainSummary * RetainSummaryManager::getFunctionSummary(const FunctionDecl *FD) { // If we don't know what function we're calling, use our default summary. if (!FD) return getDefaultSummary(); // Look up a summary in our cache of FunctionDecls -> Summaries. FuncSummariesTy::iterator I = FuncSummaries.find(FD); if (I != FuncSummaries.end()) return I->second; // No summary? Generate one. bool AllowAnnotations = true; const RetainSummary *S = generateSummary(FD, AllowAnnotations); // Annotations override defaults. if (AllowAnnotations) updateSummaryFromAnnotations(S, FD); FuncSummaries[FD] = S; return S; } //===----------------------------------------------------------------------===// // Summary creation for functions (largely uses of Core Foundation). //===----------------------------------------------------------------------===// static ArgEffect getStopTrackingHardEquivalent(ArgEffect E) { switch (E.getKind()) { case DoNothing: case Autorelease: case DecRefBridgedTransferred: case IncRef: case UnretainedOutParameter: case RetainedOutParameter: case RetainedOutParameterOnZero: case RetainedOutParameterOnNonZero: case MayEscape: case StopTracking: case StopTrackingHard: return E.withKind(StopTrackingHard); case DecRef: case DecRefAndStopTrackingHard: return E.withKind(DecRefAndStopTrackingHard); case Dealloc: return E.withKind(Dealloc); } llvm_unreachable("Unknown ArgEffect kind"); } const RetainSummary * RetainSummaryManager::updateSummaryForNonZeroCallbackArg(const RetainSummary *S, AnyCall &C) { ArgEffect RecEffect = getStopTrackingHardEquivalent(S->getReceiverEffect()); ArgEffect DefEffect = getStopTrackingHardEquivalent(S->getDefaultArgEffect()); ArgEffects ScratchArgs(AF.getEmptyMap()); ArgEffects CustomArgEffects = S->getArgEffects(); for (ArgEffects::iterator I = CustomArgEffects.begin(), E = CustomArgEffects.end(); I != E; ++I) { ArgEffect Translated = getStopTrackingHardEquivalent(I->second); if (Translated.getKind() != DefEffect.getKind()) ScratchArgs = AF.add(ScratchArgs, I->first, Translated); } RetEffect RE = RetEffect::MakeNoRetHard(); // Special cases where the callback argument CANNOT free the return value. // This can generally only happen if we know that the callback will only be // called when the return value is already being deallocated. if (const IdentifierInfo *Name = C.getIdentifier()) { // When the CGBitmapContext is deallocated, the callback here will free // the associated data buffer. // The callback in dispatch_data_create frees the buffer, but not // the data object. if (Name->isStr("CGBitmapContextCreateWithData") || Name->isStr("dispatch_data_create")) RE = S->getRetEffect(); } return getPersistentSummary(RE, ScratchArgs, RecEffect, DefEffect); } void RetainSummaryManager::updateSummaryForReceiverUnconsumedSelf( const RetainSummary *&S) { RetainSummaryTemplate Template(S, *this); Template->setReceiverEffect(ArgEffect(DoNothing)); Template->setRetEffect(RetEffect::MakeNoRet()); } + +void RetainSummaryManager::updateSummaryForArgumentTypes( + const AnyCall &C, const RetainSummary *&RS) { + RetainSummaryTemplate Template(RS, *this); + + unsigned parm_idx = 0; + for (auto pi = C.param_begin(), pe = C.param_end(); pi != pe; + ++pi, ++parm_idx) { + QualType QT = (*pi)->getType(); + + // Skip already created values. + if (RS->getArgEffects().contains(parm_idx)) + continue; + + ObjKind K = ObjKind::AnyObj; + + if (isISLObjectRef(QT)) { + K = ObjKind::Generalized; + } else if (isOSObjectPtr(QT)) { + K = ObjKind::OS; + } else if (cocoa::isCocoaObjectRef(QT)) { + K = ObjKind::ObjC; + } else if (coreFoundation::isCFObjectRef(QT)) { + K = ObjKind::CF; + } + + if (K != ObjKind::AnyObj) + Template->addArg(AF, parm_idx, + ArgEffect(RS->getDefaultArgEffect().getKind(), K)); + } +} + const RetainSummary * RetainSummaryManager::getSummary(AnyCall C, bool HasNonZeroCallbackArg, bool IsReceiverUnconsumedSelf, QualType ReceiverType) { const RetainSummary *Summ; switch (C.getKind()) { case AnyCall::Function: case AnyCall::Constructor: case AnyCall::Allocator: case AnyCall::Deallocator: Summ = getFunctionSummary(cast_or_null(C.getDecl())); break; case AnyCall::Block: case AnyCall::Destructor: // FIXME: These calls are currently unsupported. return getPersistentStopSummary(); case AnyCall::ObjCMethod: { const auto *ME = cast_or_null(C.getExpr()); if (!ME) { return getMethodSummary(cast(C.getDecl())); } else if (ME->isInstanceMessage()) { Summ = getInstanceMethodSummary(ME, ReceiverType); } else { Summ = getClassMethodSummary(ME); } break; } } if (HasNonZeroCallbackArg) Summ = updateSummaryForNonZeroCallbackArg(Summ, C); if (IsReceiverUnconsumedSelf) updateSummaryForReceiverUnconsumedSelf(Summ); + updateSummaryForArgumentTypes(C, Summ); + assert(Summ && "Unknown call type?"); return Summ; } const RetainSummary * RetainSummaryManager::getCFCreateGetRuleSummary(const FunctionDecl *FD) { if (coreFoundation::followsCreateRule(FD)) return getCFSummaryCreateRule(FD); return getCFSummaryGetRule(FD); } bool RetainSummaryManager::isTrustedReferenceCountImplementation( const FunctionDecl *FD) { return hasRCAnnotation(FD, "rc_ownership_trusted_implementation"); } Optional RetainSummaryManager::canEval(const CallExpr *CE, const FunctionDecl *FD, bool &hasTrustedImplementationAnnotation) { IdentifierInfo *II = FD->getIdentifier(); if (!II) return None; StringRef FName = II->getName(); FName = FName.substr(FName.find_first_not_of('_')); QualType ResultTy = CE->getCallReturnType(Ctx); if (ResultTy->isObjCIdType()) { if (II->isStr("NSMakeCollectable")) return BehaviorSummary::Identity; } else if (ResultTy->isPointerType()) { // Handle: (CF|CG|CV)Retain // CFAutorelease // It's okay to be a little sloppy here. if (FName == "CMBufferQueueDequeueAndRetain" || FName == "CMBufferQueueDequeueIfDataReadyAndRetain") { // Part of: . // These are not retain. They just return something and retain it. return None; } if (cocoa::isRefType(ResultTy, "CF", FName) || cocoa::isRefType(ResultTy, "CG", FName) || cocoa::isRefType(ResultTy, "CV", FName)) if (isRetain(FD, FName) || isAutorelease(FD, FName) || isMakeCollectable(FName)) return BehaviorSummary::Identity; // safeMetaCast is called by OSDynamicCast. // We assume that OSDynamicCast is either an identity (cast is OK, // the input was non-zero), // or that it returns zero (when the cast failed, or the input // was zero). if (TrackOSObjects) { if (isOSObjectDynamicCast(FName) && FD->param_size() >= 1) { return BehaviorSummary::IdentityOrZero; } else if (isOSObjectThisCast(FName) && isa(FD) && !cast(FD)->isStatic()) { return BehaviorSummary::IdentityThis; } } const FunctionDecl* FDD = FD->getDefinition(); if (FDD && isTrustedReferenceCountImplementation(FDD)) { hasTrustedImplementationAnnotation = true; return BehaviorSummary::Identity; } } if (const auto *MD = dyn_cast(FD)) { const CXXRecordDecl *Parent = MD->getParent(); if (TrackOSObjects && Parent && isOSObjectSubclass(Parent)) if (FName == "release" || FName == "retain") return BehaviorSummary::NoOp; } return None; } const RetainSummary * RetainSummaryManager::getUnarySummary(const FunctionType* FT, ArgEffectKind AE) { // Unary functions have no arg effects by definition. ArgEffects ScratchArgs(AF.getEmptyMap()); // Sanity check that this is *really* a unary function. This can // happen if people do weird things. const FunctionProtoType* FTP = dyn_cast(FT); if (!FTP || FTP->getNumParams() != 1) return getPersistentStopSummary(); ArgEffect Effect(AE, ObjKind::CF); ScratchArgs = AF.add(ScratchArgs, 0, Effect); return getPersistentSummary(RetEffect::MakeNoRet(), ScratchArgs, ArgEffect(DoNothing), ArgEffect(DoNothing)); } const RetainSummary * RetainSummaryManager::getOSSummaryRetainRule(const FunctionDecl *FD) { return getPersistentSummary(RetEffect::MakeNoRet(), AF.getEmptyMap(), /*ReceiverEff=*/ArgEffect(DoNothing), /*DefaultEff=*/ArgEffect(DoNothing), /*ThisEff=*/ArgEffect(IncRef, ObjKind::OS)); } const RetainSummary * RetainSummaryManager::getOSSummaryReleaseRule(const FunctionDecl *FD) { return getPersistentSummary(RetEffect::MakeNoRet(), AF.getEmptyMap(), /*ReceiverEff=*/ArgEffect(DoNothing), /*DefaultEff=*/ArgEffect(DoNothing), /*ThisEff=*/ArgEffect(DecRef, ObjKind::OS)); } const RetainSummary * RetainSummaryManager::getOSSummaryFreeRule(const FunctionDecl *FD) { return getPersistentSummary(RetEffect::MakeNoRet(), AF.getEmptyMap(), /*ReceiverEff=*/ArgEffect(DoNothing), /*DefaultEff=*/ArgEffect(DoNothing), /*ThisEff=*/ArgEffect(Dealloc, ObjKind::OS)); } const RetainSummary * RetainSummaryManager::getOSSummaryCreateRule(const FunctionDecl *FD) { return getPersistentSummary(RetEffect::MakeOwned(ObjKind::OS), AF.getEmptyMap()); } const RetainSummary * RetainSummaryManager::getOSSummaryGetRule(const FunctionDecl *FD) { return getPersistentSummary(RetEffect::MakeNotOwned(ObjKind::OS), AF.getEmptyMap()); } const RetainSummary * RetainSummaryManager::getCFSummaryCreateRule(const FunctionDecl *FD) { return getPersistentSummary(RetEffect::MakeOwned(ObjKind::CF), ArgEffects(AF.getEmptyMap())); } const RetainSummary * RetainSummaryManager::getCFSummaryGetRule(const FunctionDecl *FD) { return getPersistentSummary(RetEffect::MakeNotOwned(ObjKind::CF), ArgEffects(AF.getEmptyMap()), ArgEffect(DoNothing), ArgEffect(DoNothing)); } //===----------------------------------------------------------------------===// // Summary creation for Selectors. //===----------------------------------------------------------------------===// Optional RetainSummaryManager::getRetEffectFromAnnotations(QualType RetTy, const Decl *D) { if (hasAnyEnabledAttrOf(D, RetTy)) return ObjCAllocRetE; if (auto K = hasAnyEnabledAttrOf(D, RetTy)) return RetEffect::MakeOwned(*K); if (auto K = hasAnyEnabledAttrOf< CFReturnsNotRetainedAttr, OSReturnsNotRetainedAttr, GeneralizedReturnsNotRetainedAttr, NSReturnsNotRetainedAttr, NSReturnsAutoreleasedAttr>(D, RetTy)) return RetEffect::MakeNotOwned(*K); if (const auto *MD = dyn_cast(D)) for (const auto *PD : MD->overridden_methods()) if (auto RE = getRetEffectFromAnnotations(RetTy, PD)) return RE; return None; } /// \return Whether the chain of typedefs starting from {@code QT} /// has a typedef with a given name {@code Name}. static bool hasTypedefNamed(QualType QT, StringRef Name) { while (auto *T = dyn_cast(QT)) { const auto &Context = T->getDecl()->getASTContext(); if (T->getDecl()->getIdentifier() == &Context.Idents.get(Name)) return true; QT = T->getDecl()->getUnderlyingType(); } return false; } static QualType getCallableReturnType(const NamedDecl *ND) { if (const auto *FD = dyn_cast(ND)) { return FD->getReturnType(); } else if (const auto *MD = dyn_cast(ND)) { return MD->getReturnType(); } else { llvm_unreachable("Unexpected decl"); } } bool RetainSummaryManager::applyParamAnnotationEffect( const ParmVarDecl *pd, unsigned parm_idx, const NamedDecl *FD, RetainSummaryTemplate &Template) { QualType QT = pd->getType(); if (auto K = hasAnyEnabledAttrOf(pd, QT)) { Template->addArg(AF, parm_idx, ArgEffect(DecRef, *K)); return true; } else if (auto K = hasAnyEnabledAttrOf< CFReturnsRetainedAttr, OSReturnsRetainedAttr, OSReturnsRetainedOnNonZeroAttr, OSReturnsRetainedOnZeroAttr, GeneralizedReturnsRetainedAttr>(pd, QT)) { // For OSObjects, we try to guess whether the object is created based // on the return value. if (K == ObjKind::OS) { QualType QT = getCallableReturnType(FD); bool HasRetainedOnZero = pd->hasAttr(); bool HasRetainedOnNonZero = pd->hasAttr(); // The usual convention is to create an object on non-zero return, but // it's reverted if the typedef chain has a typedef kern_return_t, // because kReturnSuccess constant is defined as zero. // The convention can be overwritten by custom attributes. bool SuccessOnZero = HasRetainedOnZero || (hasTypedefNamed(QT, "kern_return_t") && !HasRetainedOnNonZero); bool ShouldSplit = !QT.isNull() && !QT->isVoidType(); ArgEffectKind AK = RetainedOutParameter; if (ShouldSplit && SuccessOnZero) { AK = RetainedOutParameterOnZero; } else if (ShouldSplit && (!SuccessOnZero || HasRetainedOnNonZero)) { AK = RetainedOutParameterOnNonZero; } Template->addArg(AF, parm_idx, ArgEffect(AK, ObjKind::OS)); } // For others: // Do nothing. Retained out parameters will either point to a +1 reference // or NULL, but the way you check for failure differs depending on the // API. Consequently, we don't have a good way to track them yet. return true; } else if (auto K = hasAnyEnabledAttrOf( pd, QT)) { Template->addArg(AF, parm_idx, ArgEffect(UnretainedOutParameter, *K)); return true; } if (const auto *MD = dyn_cast(FD)) { for (const auto *OD : MD->overridden_methods()) { const ParmVarDecl *OP = OD->parameters()[parm_idx]; if (applyParamAnnotationEffect(OP, parm_idx, OD, Template)) return true; } } return false; } void RetainSummaryManager::updateSummaryFromAnnotations(const RetainSummary *&Summ, const FunctionDecl *FD) { if (!FD) return; assert(Summ && "Must have a summary to add annotations to."); RetainSummaryTemplate Template(Summ, *this); // Effects on the parameters. unsigned parm_idx = 0; for (auto pi = FD->param_begin(), pe = FD->param_end(); pi != pe; ++pi, ++parm_idx) applyParamAnnotationEffect(*pi, parm_idx, FD, Template); QualType RetTy = FD->getReturnType(); if (Optional RetE = getRetEffectFromAnnotations(RetTy, FD)) Template->setRetEffect(*RetE); if (hasAnyEnabledAttrOf(FD, RetTy)) Template->setThisEffect(ArgEffect(DecRef, ObjKind::OS)); } void RetainSummaryManager::updateSummaryFromAnnotations(const RetainSummary *&Summ, const ObjCMethodDecl *MD) { if (!MD) return; assert(Summ && "Must have a valid summary to add annotations to"); RetainSummaryTemplate Template(Summ, *this); // Effects on the receiver. if (hasAnyEnabledAttrOf(MD, MD->getReturnType())) Template->setReceiverEffect(ArgEffect(DecRef, ObjKind::ObjC)); // Effects on the parameters. unsigned parm_idx = 0; for (auto pi = MD->param_begin(), pe = MD->param_end(); pi != pe; ++pi, ++parm_idx) applyParamAnnotationEffect(*pi, parm_idx, MD, Template); QualType RetTy = MD->getReturnType(); if (Optional RetE = getRetEffectFromAnnotations(RetTy, MD)) Template->setRetEffect(*RetE); } const RetainSummary * RetainSummaryManager::getStandardMethodSummary(const ObjCMethodDecl *MD, Selector S, QualType RetTy) { // Any special effects? ArgEffect ReceiverEff = ArgEffect(DoNothing, ObjKind::ObjC); RetEffect ResultEff = RetEffect::MakeNoRet(); // Check the method family, and apply any default annotations. switch (MD ? MD->getMethodFamily() : S.getMethodFamily()) { case OMF_None: case OMF_initialize: case OMF_performSelector: // Assume all Objective-C methods follow Cocoa Memory Management rules. // FIXME: Does the non-threaded performSelector family really belong here? // The selector could be, say, @selector(copy). if (cocoa::isCocoaObjectRef(RetTy)) ResultEff = RetEffect::MakeNotOwned(ObjKind::ObjC); else if (coreFoundation::isCFObjectRef(RetTy)) { // ObjCMethodDecl currently doesn't consider CF objects as valid return // values for alloc, new, copy, or mutableCopy, so we have to // double-check with the selector. This is ugly, but there aren't that // many Objective-C methods that return CF objects, right? if (MD) { switch (S.getMethodFamily()) { case OMF_alloc: case OMF_new: case OMF_copy: case OMF_mutableCopy: ResultEff = RetEffect::MakeOwned(ObjKind::CF); break; default: ResultEff = RetEffect::MakeNotOwned(ObjKind::CF); break; } } else { ResultEff = RetEffect::MakeNotOwned(ObjKind::CF); } } break; case OMF_init: ResultEff = ObjCInitRetE; ReceiverEff = ArgEffect(DecRef, ObjKind::ObjC); break; case OMF_alloc: case OMF_new: case OMF_copy: case OMF_mutableCopy: if (cocoa::isCocoaObjectRef(RetTy)) ResultEff = ObjCAllocRetE; else if (coreFoundation::isCFObjectRef(RetTy)) ResultEff = RetEffect::MakeOwned(ObjKind::CF); break; case OMF_autorelease: ReceiverEff = ArgEffect(Autorelease, ObjKind::ObjC); break; case OMF_retain: ReceiverEff = ArgEffect(IncRef, ObjKind::ObjC); break; case OMF_release: ReceiverEff = ArgEffect(DecRef, ObjKind::ObjC); break; case OMF_dealloc: ReceiverEff = ArgEffect(Dealloc, ObjKind::ObjC); break; case OMF_self: // -self is handled specially by the ExprEngine to propagate the receiver. break; case OMF_retainCount: case OMF_finalize: // These methods don't return objects. break; } // If one of the arguments in the selector has the keyword 'delegate' we // should stop tracking the reference count for the receiver. This is // because the reference count is quite possibly handled by a delegate // method. if (S.isKeywordSelector()) { for (unsigned i = 0, e = S.getNumArgs(); i != e; ++i) { StringRef Slot = S.getNameForSlot(i); if (Slot.substr(Slot.size() - 8).equals_lower("delegate")) { if (ResultEff == ObjCInitRetE) ResultEff = RetEffect::MakeNoRetHard(); else ReceiverEff = ArgEffect(StopTrackingHard, ObjKind::ObjC); } } } if (ReceiverEff.getKind() == DoNothing && ResultEff.getKind() == RetEffect::NoRet) return getDefaultSummary(); return getPersistentSummary(ResultEff, ArgEffects(AF.getEmptyMap()), ArgEffect(ReceiverEff), ArgEffect(MayEscape)); } const RetainSummary * RetainSummaryManager::getClassMethodSummary(const ObjCMessageExpr *ME) { assert(!ME->isInstanceMessage()); const ObjCInterfaceDecl *Class = ME->getReceiverInterface(); return getMethodSummary(ME->getSelector(), Class, ME->getMethodDecl(), ME->getType(), ObjCClassMethodSummaries); } const RetainSummary *RetainSummaryManager::getInstanceMethodSummary( const ObjCMessageExpr *ME, QualType ReceiverType) { const ObjCInterfaceDecl *ReceiverClass = nullptr; // We do better tracking of the type of the object than the core ExprEngine. // See if we have its type in our private state. if (!ReceiverType.isNull()) if (const auto *PT = ReceiverType->getAs()) ReceiverClass = PT->getInterfaceDecl(); // If we don't know what kind of object this is, fall back to its static type. if (!ReceiverClass) ReceiverClass = ME->getReceiverInterface(); // FIXME: The receiver could be a reference to a class, meaning that // we should use the class method. // id x = [NSObject class]; // [x performSelector:... withObject:... afterDelay:...]; Selector S = ME->getSelector(); const ObjCMethodDecl *Method = ME->getMethodDecl(); if (!Method && ReceiverClass) Method = ReceiverClass->getInstanceMethod(S); return getMethodSummary(S, ReceiverClass, Method, ME->getType(), ObjCMethodSummaries); } const RetainSummary * RetainSummaryManager::getMethodSummary(Selector S, const ObjCInterfaceDecl *ID, const ObjCMethodDecl *MD, QualType RetTy, ObjCMethodSummariesTy &CachedSummaries) { // Objective-C method summaries are only applicable to ObjC and CF objects. if (!TrackObjCAndCFObjects) return getDefaultSummary(); // Look up a summary in our summary cache. const RetainSummary *Summ = CachedSummaries.find(ID, S); if (!Summ) { Summ = getStandardMethodSummary(MD, S, RetTy); // Annotations override defaults. updateSummaryFromAnnotations(Summ, MD); // Memoize the summary. CachedSummaries[ObjCSummaryKey(ID, S)] = Summ; } return Summ; } void RetainSummaryManager::InitializeClassMethodSummaries() { ArgEffects ScratchArgs = AF.getEmptyMap(); // Create the [NSAssertionHandler currentHander] summary. addClassMethSummary("NSAssertionHandler", "currentHandler", getPersistentSummary(RetEffect::MakeNotOwned(ObjKind::ObjC), ScratchArgs)); // Create the [NSAutoreleasePool addObject:] summary. ScratchArgs = AF.add(ScratchArgs, 0, ArgEffect(Autorelease)); addClassMethSummary("NSAutoreleasePool", "addObject", getPersistentSummary(RetEffect::MakeNoRet(), ScratchArgs, ArgEffect(DoNothing), ArgEffect(Autorelease))); } void RetainSummaryManager::InitializeMethodSummaries() { ArgEffects ScratchArgs = AF.getEmptyMap(); // Create the "init" selector. It just acts as a pass-through for the // receiver. const RetainSummary *InitSumm = getPersistentSummary( ObjCInitRetE, ScratchArgs, ArgEffect(DecRef, ObjKind::ObjC)); addNSObjectMethSummary(GetNullarySelector("init", Ctx), InitSumm); // awakeAfterUsingCoder: behaves basically like an 'init' method. It // claims the receiver and returns a retained object. addNSObjectMethSummary(GetUnarySelector("awakeAfterUsingCoder", Ctx), InitSumm); // The next methods are allocators. const RetainSummary *AllocSumm = getPersistentSummary(ObjCAllocRetE, ScratchArgs); const RetainSummary *CFAllocSumm = getPersistentSummary(RetEffect::MakeOwned(ObjKind::CF), ScratchArgs); // Create the "retain" selector. RetEffect NoRet = RetEffect::MakeNoRet(); const RetainSummary *Summ = getPersistentSummary( NoRet, ScratchArgs, ArgEffect(IncRef, ObjKind::ObjC)); addNSObjectMethSummary(GetNullarySelector("retain", Ctx), Summ); // Create the "release" selector. Summ = getPersistentSummary(NoRet, ScratchArgs, ArgEffect(DecRef, ObjKind::ObjC)); addNSObjectMethSummary(GetNullarySelector("release", Ctx), Summ); // Create the -dealloc summary. Summ = getPersistentSummary(NoRet, ScratchArgs, ArgEffect(Dealloc, ObjKind::ObjC)); addNSObjectMethSummary(GetNullarySelector("dealloc", Ctx), Summ); // Create the "autorelease" selector. Summ = getPersistentSummary(NoRet, ScratchArgs, ArgEffect(Autorelease, ObjKind::ObjC)); addNSObjectMethSummary(GetNullarySelector("autorelease", Ctx), Summ); // For NSWindow, allocated objects are (initially) self-owned. // FIXME: For now we opt for false negatives with NSWindow, as these objects // self-own themselves. However, they only do this once they are displayed. // Thus, we need to track an NSWindow's display status. // This is tracked in . // See also http://llvm.org/bugs/show_bug.cgi?id=3714. const RetainSummary *NoTrackYet = getPersistentSummary(RetEffect::MakeNoRet(), ScratchArgs, ArgEffect(StopTracking), ArgEffect(StopTracking)); addClassMethSummary("NSWindow", "alloc", NoTrackYet); // For NSPanel (which subclasses NSWindow), allocated objects are not // self-owned. // FIXME: For now we don't track NSPanels. object for the same reason // as for NSWindow objects. addClassMethSummary("NSPanel", "alloc", NoTrackYet); // For NSNull, objects returned by +null are singletons that ignore // retain/release semantics. Just don't track them. // addClassMethSummary("NSNull", "null", NoTrackYet); // Don't track allocated autorelease pools, as it is okay to prematurely // exit a method. addClassMethSummary("NSAutoreleasePool", "alloc", NoTrackYet); addClassMethSummary("NSAutoreleasePool", "allocWithZone", NoTrackYet, false); addClassMethSummary("NSAutoreleasePool", "new", NoTrackYet); // Create summaries QCRenderer/QCView -createSnapShotImageOfType: addInstMethSummary("QCRenderer", AllocSumm, "createSnapshotImageOfType"); addInstMethSummary("QCView", AllocSumm, "createSnapshotImageOfType"); // Create summaries for CIContext, 'createCGImage' and // 'createCGLayerWithSize'. These objects are CF objects, and are not // automatically garbage collected. addInstMethSummary("CIContext", CFAllocSumm, "createCGImage", "fromRect"); addInstMethSummary("CIContext", CFAllocSumm, "createCGImage", "fromRect", "format", "colorSpace"); addInstMethSummary("CIContext", CFAllocSumm, "createCGLayerWithSize", "info"); } const RetainSummary * RetainSummaryManager::getMethodSummary(const ObjCMethodDecl *MD) { const ObjCInterfaceDecl *ID = MD->getClassInterface(); Selector S = MD->getSelector(); QualType ResultTy = MD->getReturnType(); ObjCMethodSummariesTy *CachedSummaries; if (MD->isInstanceMethod()) CachedSummaries = &ObjCMethodSummaries; else CachedSummaries = &ObjCClassMethodSummaries; return getMethodSummary(S, ID, MD, ResultTy, *CachedSummaries); } diff --git a/clang/lib/StaticAnalyzer/Checkers/RetainCountChecker/RetainCountChecker.cpp b/clang/lib/StaticAnalyzer/Checkers/RetainCountChecker/RetainCountChecker.cpp index b55ea2a116e8..18de1de78459 100644 --- a/clang/lib/StaticAnalyzer/Checkers/RetainCountChecker/RetainCountChecker.cpp +++ b/clang/lib/StaticAnalyzer/Checkers/RetainCountChecker/RetainCountChecker.cpp @@ -1,1494 +1,1499 @@ //==-- RetainCountChecker.cpp - Checks for leaks and other issues -*- C++ -*--// // // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. // See https://llvm.org/LICENSE.txt for license information. // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception // //===----------------------------------------------------------------------===// // // This file defines the methods for RetainCountChecker, which implements // a reference count checker for Core Foundation and Cocoa on (Mac OS X). // //===----------------------------------------------------------------------===// #include "RetainCountChecker.h" #include "clang/StaticAnalyzer/Core/PathSensitive/CallEvent.h" using namespace clang; using namespace ento; using namespace retaincountchecker; using llvm::StrInStrNoCase; REGISTER_MAP_WITH_PROGRAMSTATE(RefBindings, SymbolRef, RefVal) namespace clang { namespace ento { namespace retaincountchecker { const RefVal *getRefBinding(ProgramStateRef State, SymbolRef Sym) { return State->get(Sym); } } // end namespace retaincountchecker } // end namespace ento } // end namespace clang static ProgramStateRef setRefBinding(ProgramStateRef State, SymbolRef Sym, RefVal Val) { assert(Sym != nullptr); return State->set(Sym, Val); } static ProgramStateRef removeRefBinding(ProgramStateRef State, SymbolRef Sym) { return State->remove(Sym); } void RefVal::print(raw_ostream &Out) const { if (!T.isNull()) Out << "Tracked " << T.getAsString() << " | "; switch (getKind()) { default: llvm_unreachable("Invalid RefVal kind"); case Owned: { Out << "Owned"; unsigned cnt = getCount(); if (cnt) Out << " (+ " << cnt << ")"; break; } case NotOwned: { Out << "NotOwned"; unsigned cnt = getCount(); if (cnt) Out << " (+ " << cnt << ")"; break; } case ReturnedOwned: { Out << "ReturnedOwned"; unsigned cnt = getCount(); if (cnt) Out << " (+ " << cnt << ")"; break; } case ReturnedNotOwned: { Out << "ReturnedNotOwned"; unsigned cnt = getCount(); if (cnt) Out << " (+ " << cnt << ")"; break; } case Released: Out << "Released"; break; case ErrorDeallocNotOwned: Out << "-dealloc (not-owned)"; break; case ErrorLeak: Out << "Leaked"; break; case ErrorLeakReturned: Out << "Leaked (Bad naming)"; break; case ErrorUseAfterRelease: Out << "Use-After-Release [ERROR]"; break; case ErrorReleaseNotOwned: Out << "Release of Not-Owned [ERROR]"; break; case RefVal::ErrorOverAutorelease: Out << "Over-autoreleased"; break; case RefVal::ErrorReturnedNotOwned: Out << "Non-owned object returned instead of owned"; break; } switch (getIvarAccessHistory()) { case IvarAccessHistory::None: break; case IvarAccessHistory::AccessedDirectly: Out << " [direct ivar access]"; break; case IvarAccessHistory::ReleasedAfterDirectAccess: Out << " [released after direct ivar access]"; } if (ACnt) { Out << " [autorelease -" << ACnt << ']'; } } namespace { class StopTrackingCallback final : public SymbolVisitor { ProgramStateRef state; public: StopTrackingCallback(ProgramStateRef st) : state(std::move(st)) {} ProgramStateRef getState() const { return state; } bool VisitSymbol(SymbolRef sym) override { state = removeRefBinding(state, sym); return true; } }; } // end anonymous namespace //===----------------------------------------------------------------------===// // Handle statements that may have an effect on refcounts. //===----------------------------------------------------------------------===// void RetainCountChecker::checkPostStmt(const BlockExpr *BE, CheckerContext &C) const { // Scan the BlockDecRefExprs for any object the retain count checker // may be tracking. if (!BE->getBlockDecl()->hasCaptures()) return; ProgramStateRef state = C.getState(); auto *R = cast(C.getSVal(BE).getAsRegion()); BlockDataRegion::referenced_vars_iterator I = R->referenced_vars_begin(), E = R->referenced_vars_end(); if (I == E) return; // FIXME: For now we invalidate the tracking of all symbols passed to blocks // via captured variables, even though captured variables result in a copy // and in implicit increment/decrement of a retain count. SmallVector Regions; const LocationContext *LC = C.getLocationContext(); MemRegionManager &MemMgr = C.getSValBuilder().getRegionManager(); for ( ; I != E; ++I) { const VarRegion *VR = I.getCapturedRegion(); if (VR->getSuperRegion() == R) { VR = MemMgr.getVarRegion(VR->getDecl(), LC); } Regions.push_back(VR); } state = state->scanReachableSymbols(Regions).getState(); C.addTransition(state); } void RetainCountChecker::checkPostStmt(const CastExpr *CE, CheckerContext &C) const { const ObjCBridgedCastExpr *BE = dyn_cast(CE); if (!BE) return; ArgEffect AE = ArgEffect(IncRef, ObjKind::ObjC); switch (BE->getBridgeKind()) { case OBC_Bridge: // Do nothing. return; case OBC_BridgeRetained: AE = AE.withKind(IncRef); break; case OBC_BridgeTransfer: AE = AE.withKind(DecRefBridgedTransferred); break; } ProgramStateRef state = C.getState(); SymbolRef Sym = C.getSVal(CE).getAsLocSymbol(); if (!Sym) return; const RefVal* T = getRefBinding(state, Sym); if (!T) return; RefVal::Kind hasErr = (RefVal::Kind) 0; state = updateSymbol(state, Sym, *T, AE, hasErr, C); if (hasErr) { // FIXME: If we get an error during a bridge cast, should we report it? return; } C.addTransition(state); } void RetainCountChecker::processObjCLiterals(CheckerContext &C, const Expr *Ex) const { ProgramStateRef state = C.getState(); const ExplodedNode *pred = C.getPredecessor(); for (const Stmt *Child : Ex->children()) { SVal V = pred->getSVal(Child); if (SymbolRef sym = V.getAsSymbol()) if (const RefVal* T = getRefBinding(state, sym)) { RefVal::Kind hasErr = (RefVal::Kind) 0; state = updateSymbol(state, sym, *T, ArgEffect(MayEscape, ObjKind::ObjC), hasErr, C); if (hasErr) { processNonLeakError(state, Child->getSourceRange(), hasErr, sym, C); return; } } } // Return the object as autoreleased. // RetEffect RE = RetEffect::MakeNotOwned(ObjKind::ObjC); if (SymbolRef sym = state->getSVal(Ex, pred->getLocationContext()).getAsSymbol()) { QualType ResultTy = Ex->getType(); state = setRefBinding(state, sym, RefVal::makeNotOwned(ObjKind::ObjC, ResultTy)); } C.addTransition(state); } void RetainCountChecker::checkPostStmt(const ObjCArrayLiteral *AL, CheckerContext &C) const { // Apply the 'MayEscape' to all values. processObjCLiterals(C, AL); } void RetainCountChecker::checkPostStmt(const ObjCDictionaryLiteral *DL, CheckerContext &C) const { // Apply the 'MayEscape' to all keys and values. processObjCLiterals(C, DL); } void RetainCountChecker::checkPostStmt(const ObjCBoxedExpr *Ex, CheckerContext &C) const { const ExplodedNode *Pred = C.getPredecessor(); ProgramStateRef State = Pred->getState(); if (SymbolRef Sym = Pred->getSVal(Ex).getAsSymbol()) { QualType ResultTy = Ex->getType(); State = setRefBinding(State, Sym, RefVal::makeNotOwned(ObjKind::ObjC, ResultTy)); } C.addTransition(State); } void RetainCountChecker::checkPostStmt(const ObjCIvarRefExpr *IRE, CheckerContext &C) const { Optional IVarLoc = C.getSVal(IRE).getAs(); if (!IVarLoc) return; ProgramStateRef State = C.getState(); SymbolRef Sym = State->getSVal(*IVarLoc).getAsSymbol(); if (!Sym || !dyn_cast_or_null(Sym->getOriginRegion())) return; // Accessing an ivar directly is unusual. If we've done that, be more // forgiving about what the surrounding code is allowed to do. QualType Ty = Sym->getType(); ObjKind Kind; if (Ty->isObjCRetainableType()) Kind = ObjKind::ObjC; else if (coreFoundation::isCFObjectRef(Ty)) Kind = ObjKind::CF; else return; // If the value is already known to be nil, don't bother tracking it. ConstraintManager &CMgr = State->getConstraintManager(); if (CMgr.isNull(State, Sym).isConstrainedTrue()) return; if (const RefVal *RV = getRefBinding(State, Sym)) { // If we've seen this symbol before, or we're only seeing it now because // of something the analyzer has synthesized, don't do anything. if (RV->getIvarAccessHistory() != RefVal::IvarAccessHistory::None || isSynthesizedAccessor(C.getStackFrame())) { return; } // Note that this value has been loaded from an ivar. C.addTransition(setRefBinding(State, Sym, RV->withIvarAccess())); return; } RefVal PlusZero = RefVal::makeNotOwned(Kind, Ty); // In a synthesized accessor, the effective retain count is +0. if (isSynthesizedAccessor(C.getStackFrame())) { C.addTransition(setRefBinding(State, Sym, PlusZero)); return; } State = setRefBinding(State, Sym, PlusZero.withIvarAccess()); C.addTransition(State); } static bool isReceiverUnconsumedSelf(const CallEvent &Call) { if (const auto *MC = dyn_cast(&Call)) { // Check if the message is not consumed, we know it will not be used in // an assignment, ex: "self = [super init]". return MC->getMethodFamily() == OMF_init && MC->isReceiverSelfOrSuper() && !Call.getLocationContext() ->getAnalysisDeclContext() ->getParentMap() .isConsumedExpr(Call.getOriginExpr()); } return false; } const static RetainSummary *getSummary(RetainSummaryManager &Summaries, const CallEvent &Call, QualType ReceiverType) { const Expr *CE = Call.getOriginExpr(); AnyCall C = CE ? *AnyCall::forExpr(CE) : AnyCall(cast(Call.getDecl())); return Summaries.getSummary(C, Call.hasNonZeroCallbackArg(), isReceiverUnconsumedSelf(Call), ReceiverType); } void RetainCountChecker::checkPostCall(const CallEvent &Call, CheckerContext &C) const { RetainSummaryManager &Summaries = getSummaryManager(C); // Leave null if no receiver. QualType ReceiverType; if (const auto *MC = dyn_cast(&Call)) { if (MC->isInstanceMessage()) { SVal ReceiverV = MC->getReceiverSVal(); if (SymbolRef Sym = ReceiverV.getAsLocSymbol()) if (const RefVal *T = getRefBinding(C.getState(), Sym)) ReceiverType = T->getType(); } } const RetainSummary *Summ = getSummary(Summaries, Call, ReceiverType); if (C.wasInlined) { processSummaryOfInlined(*Summ, Call, C); return; } checkSummary(*Summ, Call, C); } /// GetReturnType - Used to get the return type of a message expression or /// function call with the intention of affixing that type to a tracked symbol. /// While the return type can be queried directly from RetEx, when /// invoking class methods we augment to the return type to be that of /// a pointer to the class (as opposed it just being id). // FIXME: We may be able to do this with related result types instead. // This function is probably overestimating. static QualType GetReturnType(const Expr *RetE, ASTContext &Ctx) { QualType RetTy = RetE->getType(); // If RetE is not a message expression just return its type. // If RetE is a message expression, return its types if it is something /// more specific than id. if (const ObjCMessageExpr *ME = dyn_cast(RetE)) if (const ObjCObjectPointerType *PT = RetTy->getAs()) if (PT->isObjCQualifiedIdType() || PT->isObjCIdType() || PT->isObjCClassType()) { // At this point we know the return type of the message expression is // id, id<...>, or Class. If we have an ObjCInterfaceDecl, we know this // is a call to a class method whose type we can resolve. In such // cases, promote the return type to XXX* (where XXX is the class). const ObjCInterfaceDecl *D = ME->getReceiverInterface(); return !D ? RetTy : Ctx.getObjCObjectPointerType(Ctx.getObjCInterfaceType(D)); } return RetTy; } static Optional refValFromRetEffect(RetEffect RE, QualType ResultTy) { if (RE.isOwned()) { return RefVal::makeOwned(RE.getObjKind(), ResultTy); } else if (RE.notOwned()) { return RefVal::makeNotOwned(RE.getObjKind(), ResultTy); } return None; } static bool isPointerToObject(QualType QT) { QualType PT = QT->getPointeeType(); if (!PT.isNull()) if (PT->getAsCXXRecordDecl()) return true; return false; } /// Whether the tracked value should be escaped on a given call. /// OSObjects are escaped when passed to void * / etc. static bool shouldEscapeOSArgumentOnCall(const CallEvent &CE, unsigned ArgIdx, const RefVal *TrackedValue) { if (TrackedValue->getObjKind() != ObjKind::OS) return false; if (ArgIdx >= CE.parameters().size()) return false; return !isPointerToObject(CE.parameters()[ArgIdx]->getType()); } // We don't always get the exact modeling of the function with regards to the // retain count checker even when the function is inlined. For example, we need // to stop tracking the symbols which were marked with StopTrackingHard. void RetainCountChecker::processSummaryOfInlined(const RetainSummary &Summ, const CallEvent &CallOrMsg, CheckerContext &C) const { ProgramStateRef state = C.getState(); // Evaluate the effect of the arguments. for (unsigned idx = 0, e = CallOrMsg.getNumArgs(); idx != e; ++idx) { SVal V = CallOrMsg.getArgSVal(idx); if (SymbolRef Sym = V.getAsLocSymbol()) { bool ShouldRemoveBinding = Summ.getArg(idx).getKind() == StopTrackingHard; if (const RefVal *T = getRefBinding(state, Sym)) if (shouldEscapeOSArgumentOnCall(CallOrMsg, idx, T)) ShouldRemoveBinding = true; if (ShouldRemoveBinding) state = removeRefBinding(state, Sym); } } // Evaluate the effect on the message receiver. if (const auto *MsgInvocation = dyn_cast(&CallOrMsg)) { if (SymbolRef Sym = MsgInvocation->getReceiverSVal().getAsLocSymbol()) { if (Summ.getReceiverEffect().getKind() == StopTrackingHard) { state = removeRefBinding(state, Sym); } } } // Consult the summary for the return value. RetEffect RE = Summ.getRetEffect(); if (SymbolRef Sym = CallOrMsg.getReturnValue().getAsSymbol()) { if (RE.getKind() == RetEffect::NoRetHard) state = removeRefBinding(state, Sym); } C.addTransition(state); } static bool isSmartPtrField(const MemRegion *MR) { const auto *TR = dyn_cast( cast(MR)->getSuperRegion()); return TR && RetainSummaryManager::isKnownSmartPointer(TR->getValueType()); } /// A value escapes in these possible cases: /// /// - binding to something that is not a memory region. /// - binding to a memregion that does not have stack storage /// - binding to a variable that has a destructor attached using CleanupAttr /// /// We do not currently model what happens when a symbol is /// assigned to a struct field, unless it is a known smart pointer /// implementation, about which we know that it is inlined. /// FIXME: This could definitely be improved upon. static bool shouldEscapeRegion(const MemRegion *R) { if (isSmartPtrField(R)) return false; const auto *VR = dyn_cast(R); if (!R->hasStackStorage() || !VR) return true; const VarDecl *VD = VR->getDecl(); if (!VD->hasAttr()) return false; // CleanupAttr attaches destructors, which cause escaping. return true; } static SmallVector updateOutParameters(ProgramStateRef State, const RetainSummary &Summ, const CallEvent &CE) { SVal L = CE.getReturnValue(); // Splitting is required to support out parameters, // as out parameters might be created only on the "success" branch. // We want to avoid eagerly splitting unless out parameters are actually // needed. bool SplitNecessary = false; for (auto &P : Summ.getArgEffects()) if (P.second.getKind() == RetainedOutParameterOnNonZero || P.second.getKind() == RetainedOutParameterOnZero) SplitNecessary = true; ProgramStateRef AssumeNonZeroReturn = State; ProgramStateRef AssumeZeroReturn = State; if (SplitNecessary) { if (auto DL = L.getAs()) { AssumeNonZeroReturn = AssumeNonZeroReturn->assume(*DL, true); AssumeZeroReturn = AssumeZeroReturn->assume(*DL, false); } } for (unsigned idx = 0, e = CE.getNumArgs(); idx != e; ++idx) { SVal ArgVal = CE.getArgSVal(idx); ArgEffect AE = Summ.getArg(idx); auto *ArgRegion = dyn_cast_or_null(ArgVal.getAsRegion()); if (!ArgRegion) continue; QualType PointeeTy = ArgRegion->getValueType(); SVal PointeeVal = State->getSVal(ArgRegion); SymbolRef Pointee = PointeeVal.getAsLocSymbol(); if (!Pointee) continue; if (shouldEscapeRegion(ArgRegion)) continue; auto makeNotOwnedParameter = [&](ProgramStateRef St) { return setRefBinding(St, Pointee, RefVal::makeNotOwned(AE.getObjKind(), PointeeTy)); }; auto makeOwnedParameter = [&](ProgramStateRef St) { return setRefBinding(St, Pointee, RefVal::makeOwned(ObjKind::OS, PointeeTy)); }; switch (AE.getKind()) { case UnretainedOutParameter: AssumeNonZeroReturn = makeNotOwnedParameter(AssumeNonZeroReturn); AssumeZeroReturn = makeNotOwnedParameter(AssumeZeroReturn); break; case RetainedOutParameter: AssumeNonZeroReturn = makeOwnedParameter(AssumeNonZeroReturn); AssumeZeroReturn = makeOwnedParameter(AssumeZeroReturn); break; case RetainedOutParameterOnNonZero: AssumeNonZeroReturn = makeOwnedParameter(AssumeNonZeroReturn); break; case RetainedOutParameterOnZero: AssumeZeroReturn = makeOwnedParameter(AssumeZeroReturn); break; default: break; } } if (SplitNecessary) { return {AssumeNonZeroReturn, AssumeZeroReturn}; } else { assert(AssumeZeroReturn == AssumeNonZeroReturn); return {AssumeZeroReturn}; } } void RetainCountChecker::checkSummary(const RetainSummary &Summ, const CallEvent &CallOrMsg, CheckerContext &C) const { ProgramStateRef state = C.getState(); // Evaluate the effect of the arguments. RefVal::Kind hasErr = (RefVal::Kind) 0; SourceRange ErrorRange; SymbolRef ErrorSym = nullptr; // Helper tag for providing diagnostics: indicate whether dealloc was sent // at this location. bool DeallocSent = false; for (unsigned idx = 0, e = CallOrMsg.getNumArgs(); idx != e; ++idx) { SVal V = CallOrMsg.getArgSVal(idx); ArgEffect Effect = Summ.getArg(idx); if (SymbolRef Sym = V.getAsLocSymbol()) { if (const RefVal *T = getRefBinding(state, Sym)) { if (shouldEscapeOSArgumentOnCall(CallOrMsg, idx, T)) Effect = ArgEffect(StopTrackingHard, ObjKind::OS); state = updateSymbol(state, Sym, *T, Effect, hasErr, C); if (hasErr) { ErrorRange = CallOrMsg.getArgSourceRange(idx); ErrorSym = Sym; break; } else if (Effect.getKind() == Dealloc) { DeallocSent = true; } } } } // Evaluate the effect on the message receiver / `this` argument. bool ReceiverIsTracked = false; if (!hasErr) { if (const auto *MsgInvocation = dyn_cast(&CallOrMsg)) { if (SymbolRef Sym = MsgInvocation->getReceiverSVal().getAsLocSymbol()) { if (const RefVal *T = getRefBinding(state, Sym)) { ReceiverIsTracked = true; state = updateSymbol(state, Sym, *T, Summ.getReceiverEffect(), hasErr, C); if (hasErr) { ErrorRange = MsgInvocation->getOriginExpr()->getReceiverRange(); ErrorSym = Sym; } else if (Summ.getReceiverEffect().getKind() == Dealloc) { DeallocSent = true; } } } } else if (const auto *MCall = dyn_cast(&CallOrMsg)) { if (SymbolRef Sym = MCall->getCXXThisVal().getAsLocSymbol()) { if (const RefVal *T = getRefBinding(state, Sym)) { state = updateSymbol(state, Sym, *T, Summ.getThisEffect(), hasErr, C); if (hasErr) { ErrorRange = MCall->getOriginExpr()->getSourceRange(); ErrorSym = Sym; } } } } } // Process any errors. if (hasErr) { processNonLeakError(state, ErrorRange, hasErr, ErrorSym, C); return; } // Consult the summary for the return value. RetEffect RE = Summ.getRetEffect(); if (RE.getKind() == RetEffect::OwnedWhenTrackedReceiver) { if (ReceiverIsTracked) RE = getSummaryManager(C).getObjAllocRetEffect(); else RE = RetEffect::MakeNoRet(); } if (SymbolRef Sym = CallOrMsg.getReturnValue().getAsSymbol()) { QualType ResultTy = CallOrMsg.getResultType(); if (RE.notOwned()) { const Expr *Ex = CallOrMsg.getOriginExpr(); assert(Ex); ResultTy = GetReturnType(Ex, C.getASTContext()); } if (Optional updatedRefVal = refValFromRetEffect(RE, ResultTy)) state = setRefBinding(state, Sym, *updatedRefVal); } SmallVector Out = updateOutParameters(state, Summ, CallOrMsg); for (ProgramStateRef St : Out) { if (DeallocSent) { C.addTransition(St, C.getPredecessor(), &DeallocSentTag); } else { C.addTransition(St); } } } ProgramStateRef RetainCountChecker::updateSymbol(ProgramStateRef state, SymbolRef sym, RefVal V, ArgEffect AE, RefVal::Kind &hasErr, CheckerContext &C) const { bool IgnoreRetainMsg = (bool)C.getASTContext().getLangOpts().ObjCAutoRefCount; if (AE.getObjKind() == ObjKind::ObjC && IgnoreRetainMsg) { switch (AE.getKind()) { default: break; case IncRef: AE = AE.withKind(DoNothing); break; case DecRef: AE = AE.withKind(DoNothing); break; case DecRefAndStopTrackingHard: AE = AE.withKind(StopTracking); break; } } // Handle all use-after-releases. if (V.getKind() == RefVal::Released) { V = V ^ RefVal::ErrorUseAfterRelease; hasErr = V.getKind(); return setRefBinding(state, sym, V); } switch (AE.getKind()) { case UnretainedOutParameter: case RetainedOutParameter: case RetainedOutParameterOnZero: case RetainedOutParameterOnNonZero: llvm_unreachable("Applies to pointer-to-pointer parameters, which should " "not have ref state."); case Dealloc: // NB. we only need to add a note in a non-error case. switch (V.getKind()) { default: llvm_unreachable("Invalid RefVal state for an explicit dealloc."); case RefVal::Owned: // The object immediately transitions to the released state. V = V ^ RefVal::Released; V.clearCounts(); return setRefBinding(state, sym, V); case RefVal::NotOwned: V = V ^ RefVal::ErrorDeallocNotOwned; hasErr = V.getKind(); break; } break; case MayEscape: if (V.getKind() == RefVal::Owned) { V = V ^ RefVal::NotOwned; break; } LLVM_FALLTHROUGH; case DoNothing: return state; case Autorelease: // Update the autorelease counts. V = V.autorelease(); break; case StopTracking: case StopTrackingHard: return removeRefBinding(state, sym); case IncRef: switch (V.getKind()) { default: llvm_unreachable("Invalid RefVal state for a retain."); case RefVal::Owned: case RefVal::NotOwned: V = V + 1; break; } break; case DecRef: case DecRefBridgedTransferred: case DecRefAndStopTrackingHard: switch (V.getKind()) { default: // case 'RefVal::Released' handled above. llvm_unreachable("Invalid RefVal state for a release."); case RefVal::Owned: assert(V.getCount() > 0); if (V.getCount() == 1) { if (AE.getKind() == DecRefBridgedTransferred || V.getIvarAccessHistory() == RefVal::IvarAccessHistory::AccessedDirectly) V = V ^ RefVal::NotOwned; else V = V ^ RefVal::Released; } else if (AE.getKind() == DecRefAndStopTrackingHard) { return removeRefBinding(state, sym); } V = V - 1; break; case RefVal::NotOwned: if (V.getCount() > 0) { if (AE.getKind() == DecRefAndStopTrackingHard) return removeRefBinding(state, sym); V = V - 1; } else if (V.getIvarAccessHistory() == RefVal::IvarAccessHistory::AccessedDirectly) { // Assume that the instance variable was holding on the object at // +1, and we just didn't know. if (AE.getKind() == DecRefAndStopTrackingHard) return removeRefBinding(state, sym); V = V.releaseViaIvar() ^ RefVal::Released; } else { V = V ^ RefVal::ErrorReleaseNotOwned; hasErr = V.getKind(); } break; } break; } return setRefBinding(state, sym, V); } const RefCountBug & RetainCountChecker::errorKindToBugKind(RefVal::Kind ErrorKind, SymbolRef Sym) const { switch (ErrorKind) { case RefVal::ErrorUseAfterRelease: return useAfterRelease; case RefVal::ErrorReleaseNotOwned: return releaseNotOwned; case RefVal::ErrorDeallocNotOwned: if (Sym->getType()->getPointeeCXXRecordDecl()) return freeNotOwned; return deallocNotOwned; default: llvm_unreachable("Unhandled error."); } } void RetainCountChecker::processNonLeakError(ProgramStateRef St, SourceRange ErrorRange, RefVal::Kind ErrorKind, SymbolRef Sym, CheckerContext &C) const { // HACK: Ignore retain-count issues on values accessed through ivars, // because of cases like this: // [_contentView retain]; // [_contentView removeFromSuperview]; // [self addSubview:_contentView]; // invalidates 'self' // [_contentView release]; if (const RefVal *RV = getRefBinding(St, Sym)) if (RV->getIvarAccessHistory() != RefVal::IvarAccessHistory::None) return; ExplodedNode *N = C.generateErrorNode(St); if (!N) return; auto report = llvm::make_unique( errorKindToBugKind(ErrorKind, Sym), C.getASTContext().getLangOpts(), N, Sym); report->addRange(ErrorRange); C.emitReport(std::move(report)); } //===----------------------------------------------------------------------===// // Handle the return values of retain-count-related functions. //===----------------------------------------------------------------------===// bool RetainCountChecker::evalCall(const CallExpr *CE, CheckerContext &C) const { ProgramStateRef state = C.getState(); const FunctionDecl *FD = C.getCalleeDecl(CE); if (!FD) return false; RetainSummaryManager &SmrMgr = getSummaryManager(C); QualType ResultTy = CE->getCallReturnType(C.getASTContext()); // See if the function has 'rc_ownership_trusted_implementation' // annotate attribute. If it does, we will not inline it. bool hasTrustedImplementationAnnotation = false; const LocationContext *LCtx = C.getLocationContext(); using BehaviorSummary = RetainSummaryManager::BehaviorSummary; Optional BSmr = SmrMgr.canEval(CE, FD, hasTrustedImplementationAnnotation); // See if it's one of the specific functions we know how to eval. if (!BSmr) return false; // Bind the return value. if (BSmr == BehaviorSummary::Identity || BSmr == BehaviorSummary::IdentityOrZero || BSmr == BehaviorSummary::IdentityThis) { const Expr *BindReturnTo = (BSmr == BehaviorSummary::IdentityThis) ? cast(CE)->getImplicitObjectArgument() : CE->getArg(0); SVal RetVal = state->getSVal(BindReturnTo, LCtx); // If the receiver is unknown or the function has // 'rc_ownership_trusted_implementation' annotate attribute, conjure a // return value. // FIXME: this branch is very strange. if (RetVal.isUnknown() || (hasTrustedImplementationAnnotation && !ResultTy.isNull())) { SValBuilder &SVB = C.getSValBuilder(); RetVal = SVB.conjureSymbolVal(nullptr, CE, LCtx, ResultTy, C.blockCount()); } // Bind the value. state = state->BindExpr(CE, LCtx, RetVal, /*Invalidate=*/false); if (BSmr == BehaviorSummary::IdentityOrZero) { // Add a branch where the output is zero. ProgramStateRef NullOutputState = C.getState(); // Assume that output is zero on the other branch. NullOutputState = NullOutputState->BindExpr( CE, LCtx, C.getSValBuilder().makeNull(), /*Invalidate=*/false); C.addTransition(NullOutputState, &CastFailTag); // And on the original branch assume that both input and // output are non-zero. if (auto L = RetVal.getAs()) state = state->assume(*L, /*Assumption=*/true); } } C.addTransition(state); return true; } ExplodedNode * RetainCountChecker::processReturn(const ReturnStmt *S, CheckerContext &C) const { ExplodedNode *Pred = C.getPredecessor(); // Only adjust the reference count if this is the top-level call frame, // and not the result of inlining. In the future, we should do // better checking even for inlined calls, and see if they match // with their expected semantics (e.g., the method should return a retained // object, etc.). if (!C.inTopFrame()) return Pred; if (!S) return Pred; const Expr *RetE = S->getRetValue(); if (!RetE) return Pred; ProgramStateRef state = C.getState(); SymbolRef Sym = state->getSValAsScalarOrLoc(RetE, C.getLocationContext()).getAsLocSymbol(); if (!Sym) return Pred; // Get the reference count binding (if any). const RefVal *T = getRefBinding(state, Sym); if (!T) return Pred; // Change the reference count. RefVal X = *T; switch (X.getKind()) { case RefVal::Owned: { unsigned cnt = X.getCount(); assert(cnt > 0); X.setCount(cnt - 1); X = X ^ RefVal::ReturnedOwned; break; } case RefVal::NotOwned: { unsigned cnt = X.getCount(); if (cnt) { X.setCount(cnt - 1); X = X ^ RefVal::ReturnedOwned; } else { X = X ^ RefVal::ReturnedNotOwned; } break; } default: return Pred; } // Update the binding. state = setRefBinding(state, Sym, X); Pred = C.addTransition(state); // At this point we have updated the state properly. // Everything after this is merely checking to see if the return value has // been over- or under-retained. // Did we cache out? if (!Pred) return nullptr; // Update the autorelease counts. static CheckerProgramPointTag AutoreleaseTag(this, "Autorelease"); state = handleAutoreleaseCounts(state, Pred, &AutoreleaseTag, C, Sym, X, S); // Have we generated a sink node? if (!state) return nullptr; // Get the updated binding. T = getRefBinding(state, Sym); assert(T); X = *T; // Consult the summary of the enclosing method. RetainSummaryManager &Summaries = getSummaryManager(C); const Decl *CD = &Pred->getCodeDecl(); RetEffect RE = RetEffect::MakeNoRet(); // FIXME: What is the convention for blocks? Is there one? if (const ObjCMethodDecl *MD = dyn_cast(CD)) { const RetainSummary *Summ = Summaries.getSummary(AnyCall(MD)); RE = Summ->getRetEffect(); } else if (const FunctionDecl *FD = dyn_cast(CD)) { if (!isa(FD)) { const RetainSummary *Summ = Summaries.getSummary(AnyCall(FD)); RE = Summ->getRetEffect(); } } return checkReturnWithRetEffect(S, C, Pred, RE, X, Sym, state); } ExplodedNode * RetainCountChecker::checkReturnWithRetEffect(const ReturnStmt *S, CheckerContext &C, ExplodedNode *Pred, RetEffect RE, RefVal X, SymbolRef Sym, ProgramStateRef state) const { // HACK: Ignore retain-count issues on values accessed through ivars, // because of cases like this: // [_contentView retain]; // [_contentView removeFromSuperview]; // [self addSubview:_contentView]; // invalidates 'self' // [_contentView release]; if (X.getIvarAccessHistory() != RefVal::IvarAccessHistory::None) return Pred; // Any leaks or other errors? if (X.isReturnedOwned() && X.getCount() == 0) { if (RE.getKind() != RetEffect::NoRet) { if (!RE.isOwned()) { // The returning type is a CF, we expect the enclosing method should // return ownership. X = X ^ RefVal::ErrorLeakReturned; // Generate an error node. state = setRefBinding(state, Sym, X); static CheckerProgramPointTag ReturnOwnLeakTag(this, "ReturnsOwnLeak"); ExplodedNode *N = C.addTransition(state, Pred, &ReturnOwnLeakTag); if (N) { const LangOptions &LOpts = C.getASTContext().getLangOpts(); auto R = llvm::make_unique(leakAtReturn, LOpts, N, Sym, C); C.emitReport(std::move(R)); } return N; } } } else if (X.isReturnedNotOwned()) { if (RE.isOwned()) { if (X.getIvarAccessHistory() == RefVal::IvarAccessHistory::AccessedDirectly) { // Assume the method was trying to transfer a +1 reference from a // strong ivar to the caller. state = setRefBinding(state, Sym, X.releaseViaIvar() ^ RefVal::ReturnedOwned); } else { // Trying to return a not owned object to a caller expecting an // owned object. state = setRefBinding(state, Sym, X ^ RefVal::ErrorReturnedNotOwned); static CheckerProgramPointTag ReturnNotOwnedTag(this, "ReturnNotOwnedForOwned"); ExplodedNode *N = C.addTransition(state, Pred, &ReturnNotOwnedTag); if (N) { auto R = llvm::make_unique( returnNotOwnedForOwned, C.getASTContext().getLangOpts(), N, Sym); C.emitReport(std::move(R)); } return N; } } } return Pred; } //===----------------------------------------------------------------------===// // Check various ways a symbol can be invalidated. //===----------------------------------------------------------------------===// void RetainCountChecker::checkBind(SVal loc, SVal val, const Stmt *S, CheckerContext &C) const { ProgramStateRef state = C.getState(); const MemRegion *MR = loc.getAsRegion(); // Find all symbols referenced by 'val' that we are tracking // and stop tracking them. if (MR && shouldEscapeRegion(MR)) { state = state->scanReachableSymbols(val).getState(); C.addTransition(state); } } ProgramStateRef RetainCountChecker::evalAssume(ProgramStateRef state, SVal Cond, bool Assumption) const { // FIXME: We may add to the interface of evalAssume the list of symbols // whose assumptions have changed. For now we just iterate through the // bindings and check if any of the tracked symbols are NULL. This isn't // too bad since the number of symbols we will track in practice are // probably small and evalAssume is only called at branches and a few // other places. RefBindingsTy B = state->get(); if (B.isEmpty()) return state; bool changed = false; RefBindingsTy::Factory &RefBFactory = state->get_context(); ConstraintManager &CMgr = state->getConstraintManager(); for (auto &I : B) { // Check if the symbol is null stop tracking the symbol. ConditionTruthVal AllocFailed = CMgr.isNull(state, I.first); if (AllocFailed.isConstrainedTrue()) { changed = true; B = RefBFactory.remove(B, I.first); } } if (changed) state = state->set(B); return state; } ProgramStateRef RetainCountChecker::checkRegionChanges( ProgramStateRef state, const InvalidatedSymbols *invalidated, ArrayRef ExplicitRegions, ArrayRef Regions, const LocationContext *LCtx, const CallEvent *Call) const { if (!invalidated) return state; llvm::SmallPtrSet WhitelistedSymbols; for (const MemRegion *I : ExplicitRegions) if (const SymbolicRegion *SR = I->StripCasts()->getAs()) WhitelistedSymbols.insert(SR->getSymbol()); for (SymbolRef sym : *invalidated) { if (WhitelistedSymbols.count(sym)) continue; // Remove any existing reference-count binding. state = removeRefBinding(state, sym); } return state; } ProgramStateRef RetainCountChecker::handleAutoreleaseCounts(ProgramStateRef state, ExplodedNode *Pred, const ProgramPointTag *Tag, CheckerContext &Ctx, SymbolRef Sym, RefVal V, const ReturnStmt *S) const { unsigned ACnt = V.getAutoreleaseCount(); // No autorelease counts? Nothing to be done. if (!ACnt) return state; unsigned Cnt = V.getCount(); // FIXME: Handle sending 'autorelease' to already released object. if (V.getKind() == RefVal::ReturnedOwned) ++Cnt; // If we would over-release here, but we know the value came from an ivar, // assume it was a strong ivar that's just been relinquished. if (ACnt > Cnt && V.getIvarAccessHistory() == RefVal::IvarAccessHistory::AccessedDirectly) { V = V.releaseViaIvar(); --ACnt; } if (ACnt <= Cnt) { if (ACnt == Cnt) { V.clearCounts(); if (V.getKind() == RefVal::ReturnedOwned) { V = V ^ RefVal::ReturnedNotOwned; } else { V = V ^ RefVal::NotOwned; } } else { V.setCount(V.getCount() - ACnt); V.setAutoreleaseCount(0); } return setRefBinding(state, Sym, V); } // HACK: Ignore retain-count issues on values accessed through ivars, // because of cases like this: // [_contentView retain]; // [_contentView removeFromSuperview]; // [self addSubview:_contentView]; // invalidates 'self' // [_contentView release]; if (V.getIvarAccessHistory() != RefVal::IvarAccessHistory::None) return state; // Woah! More autorelease counts then retain counts left. // Emit hard error. V = V ^ RefVal::ErrorOverAutorelease; state = setRefBinding(state, Sym, V); ExplodedNode *N = Ctx.generateSink(state, Pred, Tag); if (N) { SmallString<128> sbuf; llvm::raw_svector_ostream os(sbuf); os << "Object was autoreleased "; if (V.getAutoreleaseCount() > 1) os << V.getAutoreleaseCount() << " times but the object "; else os << "but "; os << "has a +" << V.getCount() << " retain count"; const LangOptions &LOpts = Ctx.getASTContext().getLangOpts(); auto R = llvm::make_unique(overAutorelease, LOpts, N, Sym, os.str()); Ctx.emitReport(std::move(R)); } return nullptr; } ProgramStateRef RetainCountChecker::handleSymbolDeath(ProgramStateRef state, SymbolRef sid, RefVal V, SmallVectorImpl &Leaked) const { bool hasLeak; // HACK: Ignore retain-count issues on values accessed through ivars, // because of cases like this: // [_contentView retain]; // [_contentView removeFromSuperview]; // [self addSubview:_contentView]; // invalidates 'self' // [_contentView release]; if (V.getIvarAccessHistory() != RefVal::IvarAccessHistory::None) hasLeak = false; else if (V.isOwned()) hasLeak = true; else if (V.isNotOwned() || V.isReturnedOwned()) hasLeak = (V.getCount() > 0); else hasLeak = false; if (!hasLeak) return removeRefBinding(state, sid); Leaked.push_back(sid); return setRefBinding(state, sid, V ^ RefVal::ErrorLeak); } ExplodedNode * RetainCountChecker::processLeaks(ProgramStateRef state, SmallVectorImpl &Leaked, CheckerContext &Ctx, ExplodedNode *Pred) const { // Generate an intermediate node representing the leak point. ExplodedNode *N = Ctx.addTransition(state, Pred); const LangOptions &LOpts = Ctx.getASTContext().getLangOpts(); if (N) { for (SymbolRef L : Leaked) { const RefCountBug &BT = Pred ? leakWithinFunction : leakAtReturn; Ctx.emitReport(llvm::make_unique(BT, LOpts, N, L, Ctx)); } } return N; } -static bool isISLObjectRef(QualType Ty) { - return StringRef(Ty.getAsString()).startswith("isl_"); -} - void RetainCountChecker::checkBeginFunction(CheckerContext &Ctx) const { if (!Ctx.inTopFrame()) return; RetainSummaryManager &SmrMgr = getSummaryManager(Ctx); const LocationContext *LCtx = Ctx.getLocationContext(); const FunctionDecl *FD = dyn_cast(LCtx->getDecl()); if (!FD || SmrMgr.isTrustedReferenceCountImplementation(FD)) return; ProgramStateRef state = Ctx.getState(); const RetainSummary *FunctionSummary = SmrMgr.getSummary(AnyCall(FD)); ArgEffects CalleeSideArgEffects = FunctionSummary->getArgEffects(); for (unsigned idx = 0, e = FD->getNumParams(); idx != e; ++idx) { const ParmVarDecl *Param = FD->getParamDecl(idx); SymbolRef Sym = state->getSVal(state->getRegion(Param, LCtx)).getAsSymbol(); QualType Ty = Param->getType(); const ArgEffect *AE = CalleeSideArgEffects.lookup(idx); - if (AE && AE->getKind() == DecRef && isISLObjectRef(Ty)) { - state = setRefBinding( - state, Sym, RefVal::makeOwned(ObjKind::Generalized, Ty)); - } else if (isISLObjectRef(Ty)) { - state = setRefBinding( - state, Sym, - RefVal::makeNotOwned(ObjKind::Generalized, Ty)); + if (AE) { + ObjKind K = AE->getObjKind(); + if (K == ObjKind::Generalized || K == ObjKind::OS || + (TrackNSCFStartParam && (K == ObjKind::ObjC || K == ObjKind::CF))) { + RefVal NewVal = AE->getKind() == DecRef ? RefVal::makeOwned(K, Ty) + : RefVal::makeNotOwned(K, Ty); + state = setRefBinding(state, Sym, NewVal); + } } } Ctx.addTransition(state); } void RetainCountChecker::checkEndFunction(const ReturnStmt *RS, CheckerContext &Ctx) const { ExplodedNode *Pred = processReturn(RS, Ctx); // Created state cached out. if (!Pred) { return; } ProgramStateRef state = Pred->getState(); RefBindingsTy B = state->get(); // Don't process anything within synthesized bodies. const LocationContext *LCtx = Pred->getLocationContext(); if (LCtx->getAnalysisDeclContext()->isBodyAutosynthesized()) { assert(!LCtx->inTopFrame()); return; } for (auto &I : B) { state = handleAutoreleaseCounts(state, Pred, /*Tag=*/nullptr, Ctx, I.first, I.second); if (!state) return; } // If the current LocationContext has a parent, don't check for leaks. // We will do that later. // FIXME: we should instead check for imbalances of the retain/releases, // and suggest annotations. if (LCtx->getParent()) return; B = state->get(); SmallVector Leaked; for (auto &I : B) state = handleSymbolDeath(state, I.first, I.second, Leaked); processLeaks(state, Leaked, Ctx, Pred); } void RetainCountChecker::checkDeadSymbols(SymbolReaper &SymReaper, CheckerContext &C) const { ExplodedNode *Pred = C.getPredecessor(); ProgramStateRef state = C.getState(); SmallVector Leaked; // Update counts from autorelease pools for (const auto &I: state->get()) { SymbolRef Sym = I.first; if (SymReaper.isDead(Sym)) { static CheckerProgramPointTag Tag(this, "DeadSymbolAutorelease"); const RefVal &V = I.second; state = handleAutoreleaseCounts(state, Pred, &Tag, C, Sym, V); if (!state) return; // Fetch the new reference count from the state, and use it to handle // this symbol. state = handleSymbolDeath(state, Sym, *getRefBinding(state, Sym), Leaked); } } if (Leaked.empty()) { C.addTransition(state); return; } Pred = processLeaks(state, Leaked, C, Pred); // Did we cache out? if (!Pred) return; // Now generate a new node that nukes the old bindings. // The only bindings left at this point are the leaked symbols. RefBindingsTy::Factory &F = state->get_context(); RefBindingsTy B = state->get(); for (SymbolRef L : Leaked) B = F.remove(B, L); state = state->set(B); C.addTransition(state, Pred); } void RetainCountChecker::printState(raw_ostream &Out, ProgramStateRef State, const char *NL, const char *Sep) const { RefBindingsTy B = State->get(); if (B.isEmpty()) return; Out << Sep << NL; for (auto &I : B) { Out << I.first << " : "; I.second.print(Out); Out << NL; } } //===----------------------------------------------------------------------===// // Checker registration. //===----------------------------------------------------------------------===// void ento::registerRetainCountBase(CheckerManager &Mgr) { Mgr.registerChecker(); } bool ento::shouldRegisterRetainCountBase(const LangOptions &LO) { return true; } +// FIXME: remove this, hack for backwards compatibility: +// it should be possible to enable the NS/CF retain count checker as +// osx.cocoa.RetainCount, and it should be possible to disable +// osx.OSObjectRetainCount using osx.cocoa.RetainCount:CheckOSObject=false. +static bool getOption(AnalyzerOptions &Options, + StringRef Postfix, + StringRef Value) { + auto I = Options.Config.find( + (StringRef("osx.cocoa.RetainCount:") + Postfix).str()); + if (I != Options.Config.end()) + return I->getValue() == Value; + return false; +} + void ento::registerRetainCountChecker(CheckerManager &Mgr) { auto *Chk = Mgr.getChecker(); Chk->TrackObjCAndCFObjects = true; + Chk->TrackNSCFStartParam = getOption(Mgr.getAnalyzerOptions(), + "TrackNSCFStartParam", + "true"); } bool ento::shouldRegisterRetainCountChecker(const LangOptions &LO) { return true; } -// FIXME: remove this, hack for backwards compatibility: -// it should be possible to enable the NS/CF retain count checker as -// osx.cocoa.RetainCount, and it should be possible to disable -// osx.OSObjectRetainCount using osx.cocoa.RetainCount:CheckOSObject=false. -static bool hasPrevCheckOSObjectOptionDisabled(AnalyzerOptions &Options) { - auto I = Options.Config.find("osx.cocoa.RetainCount:CheckOSObject"); - if (I != Options.Config.end()) - return I->getValue() == "false"; - return false; -} - void ento::registerOSObjectRetainCountChecker(CheckerManager &Mgr) { auto *Chk = Mgr.getChecker(); - if (!hasPrevCheckOSObjectOptionDisabled(Mgr.getAnalyzerOptions())) + if (!getOption(Mgr.getAnalyzerOptions(), + "CheckOSObject", + "false")) Chk->TrackOSObjects = true; } bool ento::shouldRegisterOSObjectRetainCountChecker(const LangOptions &LO) { return true; } diff --git a/clang/lib/StaticAnalyzer/Checkers/RetainCountChecker/RetainCountChecker.h b/clang/lib/StaticAnalyzer/Checkers/RetainCountChecker/RetainCountChecker.h index 775cd21851d0..506ece1e5785 100644 --- a/clang/lib/StaticAnalyzer/Checkers/RetainCountChecker/RetainCountChecker.h +++ b/clang/lib/StaticAnalyzer/Checkers/RetainCountChecker/RetainCountChecker.h @@ -1,395 +1,398 @@ //==--- RetainCountChecker.h - Checks for leaks and other issues -*- C++ -*--// // // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. // See https://llvm.org/LICENSE.txt for license information. // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception // //===----------------------------------------------------------------------===// // // This file defines the methods for RetainCountChecker, which implements // a reference count checker for Core Foundation and Cocoa on (Mac OS X). // //===----------------------------------------------------------------------===// #ifndef LLVM_CLANG_LIB_STATICANALYZER_CHECKERS_RETAINCOUNTCHECKER_H #define LLVM_CLANG_LIB_STATICANALYZER_CHECKERS_RETAINCOUNTCHECKER_H #include "clang/StaticAnalyzer/Checkers/BuiltinCheckerRegistration.h" #include "RetainCountDiagnostics.h" #include "clang/AST/Attr.h" #include "clang/AST/DeclCXX.h" #include "clang/AST/DeclObjC.h" #include "clang/AST/ParentMap.h" #include "clang/Analysis/DomainSpecific/CocoaConventions.h" #include "clang/Analysis/RetainSummaryManager.h" #include "clang/Basic/LangOptions.h" #include "clang/Basic/SourceManager.h" #include "clang/Analysis/SelectorExtras.h" #include "clang/StaticAnalyzer/Core/BugReporter/BugType.h" #include "clang/StaticAnalyzer/Core/BugReporter/PathDiagnostic.h" #include "clang/StaticAnalyzer/Core/Checker.h" #include "clang/StaticAnalyzer/Core/CheckerManager.h" #include "clang/StaticAnalyzer/Core/PathSensitive/CallEvent.h" #include "clang/StaticAnalyzer/Core/PathSensitive/CheckerContext.h" #include "clang/StaticAnalyzer/Core/PathSensitive/ProgramStateTrait.h" #include "clang/StaticAnalyzer/Core/PathSensitive/SymbolManager.h" #include "llvm/ADT/DenseMap.h" #include "llvm/ADT/FoldingSet.h" #include "llvm/ADT/ImmutableList.h" #include "llvm/ADT/ImmutableMap.h" #include "llvm/ADT/STLExtras.h" #include "llvm/ADT/SmallString.h" #include "llvm/ADT/StringExtras.h" #include #include namespace clang { namespace ento { namespace retaincountchecker { /// Metadata on reference. class RefVal { public: enum Kind { Owned = 0, // Owning reference. NotOwned, // Reference is not owned by still valid (not freed). Released, // Object has been released. ReturnedOwned, // Returned object passes ownership to caller. ReturnedNotOwned, // Return object does not pass ownership to caller. ERROR_START, ErrorDeallocNotOwned, // -dealloc called on non-owned object. ErrorUseAfterRelease, // Object used after released. ErrorReleaseNotOwned, // Release of an object that was not owned. ERROR_LEAK_START, ErrorLeak, // A memory leak due to excessive reference counts. ErrorLeakReturned, // A memory leak due to the returning method not having // the correct naming conventions. ErrorOverAutorelease, ErrorReturnedNotOwned }; /// Tracks how an object referenced by an ivar has been used. /// /// This accounts for us not knowing if an arbitrary ivar is supposed to be /// stored at +0 or +1. enum class IvarAccessHistory { None, AccessedDirectly, ReleasedAfterDirectAccess }; private: /// The number of outstanding retains. unsigned Cnt; /// The number of outstanding autoreleases. unsigned ACnt; /// The (static) type of the object at the time we started tracking it. QualType T; /// The current state of the object. /// /// See the RefVal::Kind enum for possible values. unsigned RawKind : 5; /// The kind of object being tracked (CF or ObjC or OSObject), if known. /// /// See the ObjKind enum for possible values. unsigned RawObjectKind : 3; /// True if the current state and/or retain count may turn out to not be the /// best possible approximation of the reference counting state. /// /// If true, the checker may decide to throw away ("override") this state /// in favor of something else when it sees the object being used in new ways. /// /// This setting should not be propagated to state derived from this state. /// Once we start deriving new states, it would be inconsistent to override /// them. unsigned RawIvarAccessHistory : 2; RefVal(Kind k, ObjKind o, unsigned cnt, unsigned acnt, QualType t, IvarAccessHistory IvarAccess) : Cnt(cnt), ACnt(acnt), T(t), RawKind(static_cast(k)), RawObjectKind(static_cast(o)), RawIvarAccessHistory(static_cast(IvarAccess)) { assert(getKind() == k && "not enough bits for the kind"); assert(getObjKind() == o && "not enough bits for the object kind"); assert(getIvarAccessHistory() == IvarAccess && "not enough bits"); } public: Kind getKind() const { return static_cast(RawKind); } ObjKind getObjKind() const { return static_cast(RawObjectKind); } unsigned getCount() const { return Cnt; } unsigned getAutoreleaseCount() const { return ACnt; } unsigned getCombinedCounts() const { return Cnt + ACnt; } void clearCounts() { Cnt = 0; ACnt = 0; } void setCount(unsigned i) { Cnt = i; } void setAutoreleaseCount(unsigned i) { ACnt = i; } QualType getType() const { return T; } /// Returns what the analyzer knows about direct accesses to a particular /// instance variable. /// /// If the object with this refcount wasn't originally from an Objective-C /// ivar region, this should always return IvarAccessHistory::None. IvarAccessHistory getIvarAccessHistory() const { return static_cast(RawIvarAccessHistory); } bool isOwned() const { return getKind() == Owned; } bool isNotOwned() const { return getKind() == NotOwned; } bool isReturnedOwned() const { return getKind() == ReturnedOwned; } bool isReturnedNotOwned() const { return getKind() == ReturnedNotOwned; } /// Create a state for an object whose lifetime is the responsibility of the /// current function, at least partially. /// /// Most commonly, this is an owned object with a retain count of +1. static RefVal makeOwned(ObjKind o, QualType t) { return RefVal(Owned, o, /*Count=*/1, 0, t, IvarAccessHistory::None); } /// Create a state for an object whose lifetime is not the responsibility of /// the current function. /// /// Most commonly, this is an unowned object with a retain count of +0. static RefVal makeNotOwned(ObjKind o, QualType t) { return RefVal(NotOwned, o, /*Count=*/0, 0, t, IvarAccessHistory::None); } RefVal operator-(size_t i) const { return RefVal(getKind(), getObjKind(), getCount() - i, getAutoreleaseCount(), getType(), getIvarAccessHistory()); } RefVal operator+(size_t i) const { return RefVal(getKind(), getObjKind(), getCount() + i, getAutoreleaseCount(), getType(), getIvarAccessHistory()); } RefVal operator^(Kind k) const { return RefVal(k, getObjKind(), getCount(), getAutoreleaseCount(), getType(), getIvarAccessHistory()); } RefVal autorelease() const { return RefVal(getKind(), getObjKind(), getCount(), getAutoreleaseCount()+1, getType(), getIvarAccessHistory()); } RefVal withIvarAccess() const { assert(getIvarAccessHistory() == IvarAccessHistory::None); return RefVal(getKind(), getObjKind(), getCount(), getAutoreleaseCount(), getType(), IvarAccessHistory::AccessedDirectly); } RefVal releaseViaIvar() const { assert(getIvarAccessHistory() == IvarAccessHistory::AccessedDirectly); return RefVal(getKind(), getObjKind(), getCount(), getAutoreleaseCount(), getType(), IvarAccessHistory::ReleasedAfterDirectAccess); } // Comparison, profiling, and pretty-printing. bool hasSameState(const RefVal &X) const { return getKind() == X.getKind() && Cnt == X.Cnt && ACnt == X.ACnt && getIvarAccessHistory() == X.getIvarAccessHistory(); } bool operator==(const RefVal& X) const { return T == X.T && hasSameState(X) && getObjKind() == X.getObjKind(); } void Profile(llvm::FoldingSetNodeID& ID) const { ID.Add(T); ID.AddInteger(RawKind); ID.AddInteger(Cnt); ID.AddInteger(ACnt); ID.AddInteger(RawObjectKind); ID.AddInteger(RawIvarAccessHistory); } void print(raw_ostream &Out) const; }; class RetainCountChecker : public Checker< check::Bind, check::DeadSymbols, check::BeginFunction, check::EndFunction, check::PostStmt, check::PostStmt, check::PostStmt, check::PostStmt, check::PostStmt, check::PostStmt, check::PostCall, check::RegionChanges, eval::Assume, eval::Call > { RefCountBug useAfterRelease{this, RefCountBug::UseAfterRelease}; RefCountBug releaseNotOwned{this, RefCountBug::ReleaseNotOwned}; RefCountBug deallocNotOwned{this, RefCountBug::DeallocNotOwned}; RefCountBug freeNotOwned{this, RefCountBug::FreeNotOwned}; RefCountBug overAutorelease{this, RefCountBug::OverAutorelease}; RefCountBug returnNotOwnedForOwned{this, RefCountBug::ReturnNotOwnedForOwned}; RefCountBug leakWithinFunction{this, RefCountBug::LeakWithinFunction}; RefCountBug leakAtReturn{this, RefCountBug::LeakAtReturn}; CheckerProgramPointTag DeallocSentTag{this, "DeallocSent"}; CheckerProgramPointTag CastFailTag{this, "DynamicCastFail"}; mutable std::unique_ptr Summaries; public: /// Track Objective-C and CoreFoundation objects. bool TrackObjCAndCFObjects = false; /// Track sublcasses of OSObject. bool TrackOSObjects = false; + /// Track initial parameters (for the entry point) for NS/CF objects. + bool TrackNSCFStartParam = false; + RetainCountChecker() {}; RetainSummaryManager &getSummaryManager(ASTContext &Ctx) const { if (!Summaries) Summaries.reset( new RetainSummaryManager(Ctx, TrackObjCAndCFObjects, TrackOSObjects)); return *Summaries; } RetainSummaryManager &getSummaryManager(CheckerContext &C) const { return getSummaryManager(C.getASTContext()); } void printState(raw_ostream &Out, ProgramStateRef State, const char *NL, const char *Sep) const override; void checkBind(SVal loc, SVal val, const Stmt *S, CheckerContext &C) const; void checkPostStmt(const BlockExpr *BE, CheckerContext &C) const; void checkPostStmt(const CastExpr *CE, CheckerContext &C) const; void checkPostStmt(const ObjCArrayLiteral *AL, CheckerContext &C) const; void checkPostStmt(const ObjCDictionaryLiteral *DL, CheckerContext &C) const; void checkPostStmt(const ObjCBoxedExpr *BE, CheckerContext &C) const; void checkPostStmt(const ObjCIvarRefExpr *IRE, CheckerContext &C) const; void checkPostCall(const CallEvent &Call, CheckerContext &C) const; void checkSummary(const RetainSummary &Summ, const CallEvent &Call, CheckerContext &C) const; void processSummaryOfInlined(const RetainSummary &Summ, const CallEvent &Call, CheckerContext &C) const; bool evalCall(const CallExpr *CE, CheckerContext &C) const; ProgramStateRef evalAssume(ProgramStateRef state, SVal Cond, bool Assumption) const; ProgramStateRef checkRegionChanges(ProgramStateRef state, const InvalidatedSymbols *invalidated, ArrayRef ExplicitRegions, ArrayRef Regions, const LocationContext* LCtx, const CallEvent *Call) const; ExplodedNode* checkReturnWithRetEffect(const ReturnStmt *S, CheckerContext &C, ExplodedNode *Pred, RetEffect RE, RefVal X, SymbolRef Sym, ProgramStateRef state) const; void checkDeadSymbols(SymbolReaper &SymReaper, CheckerContext &C) const; void checkBeginFunction(CheckerContext &C) const; void checkEndFunction(const ReturnStmt *RS, CheckerContext &C) const; ProgramStateRef updateSymbol(ProgramStateRef state, SymbolRef sym, RefVal V, ArgEffect E, RefVal::Kind &hasErr, CheckerContext &C) const; const RefCountBug &errorKindToBugKind(RefVal::Kind ErrorKind, SymbolRef Sym) const; void processNonLeakError(ProgramStateRef St, SourceRange ErrorRange, RefVal::Kind ErrorKind, SymbolRef Sym, CheckerContext &C) const; void processObjCLiterals(CheckerContext &C, const Expr *Ex) const; ProgramStateRef handleSymbolDeath(ProgramStateRef state, SymbolRef sid, RefVal V, SmallVectorImpl &Leaked) const; ProgramStateRef handleAutoreleaseCounts(ProgramStateRef state, ExplodedNode *Pred, const ProgramPointTag *Tag, CheckerContext &Ctx, SymbolRef Sym, RefVal V, const ReturnStmt *S=nullptr) const; ExplodedNode *processLeaks(ProgramStateRef state, SmallVectorImpl &Leaked, CheckerContext &Ctx, ExplodedNode *Pred = nullptr) const; const CheckerProgramPointTag &getDeallocSentTag() const { return DeallocSentTag; } const CheckerProgramPointTag &getCastFailTag() const { return CastFailTag; } private: /// Perform the necessary checks and state adjustments at the end of the /// function. /// \p S Return statement, may be null. ExplodedNode * processReturn(const ReturnStmt *S, CheckerContext &C) const; }; //===----------------------------------------------------------------------===// // RefBindings - State used to track object reference counts. //===----------------------------------------------------------------------===// const RefVal *getRefBinding(ProgramStateRef State, SymbolRef Sym); /// Returns true if this stack frame is for an Objective-C method that is a /// property getter or setter whose body has been synthesized by the analyzer. inline bool isSynthesizedAccessor(const StackFrameContext *SFC) { auto Method = dyn_cast_or_null(SFC->getDecl()); if (!Method || !Method->isPropertyAccessor()) return false; return SFC->getAnalysisDeclContext()->isBodyAutosynthesized(); } } // end namespace retaincountchecker } // end namespace ento } // end namespace clang #endif diff --git a/clang/lib/StaticAnalyzer/Checkers/RetainCountChecker/RetainCountDiagnostics.cpp b/clang/lib/StaticAnalyzer/Checkers/RetainCountChecker/RetainCountDiagnostics.cpp index dcb5ca855581..8e13ee35f3c4 100644 --- a/clang/lib/StaticAnalyzer/Checkers/RetainCountChecker/RetainCountDiagnostics.cpp +++ b/clang/lib/StaticAnalyzer/Checkers/RetainCountChecker/RetainCountDiagnostics.cpp @@ -1,880 +1,924 @@ // RetainCountDiagnostics.cpp - Checks for leaks and other issues -*- C++ -*--// // // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. // See https://llvm.org/LICENSE.txt for license information. // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception // //===----------------------------------------------------------------------===// // // This file defines diagnostics for RetainCountChecker, which implements // a reference count checker for Core Foundation and Cocoa on (Mac OS X). // //===----------------------------------------------------------------------===// #include "RetainCountDiagnostics.h" #include "RetainCountChecker.h" using namespace clang; using namespace ento; using namespace retaincountchecker; StringRef RefCountBug::bugTypeToName(RefCountBug::RefCountBugType BT) { switch (BT) { case UseAfterRelease: return "Use-after-release"; case ReleaseNotOwned: return "Bad release"; case DeallocNotOwned: return "-dealloc sent to non-exclusively owned object"; case FreeNotOwned: return "freeing non-exclusively owned object"; case OverAutorelease: return "Object autoreleased too many times"; case ReturnNotOwnedForOwned: return "Method should return an owned object"; case LeakWithinFunction: return "Leak"; case LeakAtReturn: return "Leak of returned object"; } llvm_unreachable("Unknown RefCountBugType"); } StringRef RefCountBug::getDescription() const { switch (BT) { case UseAfterRelease: return "Reference-counted object is used after it is released"; case ReleaseNotOwned: return "Incorrect decrement of the reference count of an object that is " "not owned at this point by the caller"; case DeallocNotOwned: return "-dealloc sent to object that may be referenced elsewhere"; case FreeNotOwned: return "'free' called on an object that may be referenced elsewhere"; case OverAutorelease: return "Object autoreleased too many times"; case ReturnNotOwnedForOwned: return "Object with a +0 retain count returned to caller where a +1 " "(owning) retain count is expected"; case LeakWithinFunction: case LeakAtReturn: return ""; } llvm_unreachable("Unknown RefCountBugType"); } RefCountBug::RefCountBug(const CheckerBase *Checker, RefCountBugType BT) : BugType(Checker, bugTypeToName(BT), categories::MemoryRefCount, /*SupressOnSink=*/BT == LeakWithinFunction || BT == LeakAtReturn), BT(BT), Checker(Checker) {} static bool isNumericLiteralExpression(const Expr *E) { // FIXME: This set of cases was copied from SemaExprObjC. return isa(E) || isa(E) || isa(E) || isa(E) || isa(E); } /// If type represents a pointer to CXXRecordDecl, /// and is not a typedef, return the decl name. /// Otherwise, return the serialization of type. static std::string getPrettyTypeName(QualType QT) { QualType PT = QT->getPointeeType(); if (!PT.isNull() && !QT->getAs()) if (const auto *RD = PT->getAsCXXRecordDecl()) return RD->getName(); return QT.getAsString(); } /// Write information about the type state change to {@code os}, /// return whether the note should be generated. static bool shouldGenerateNote(llvm::raw_string_ostream &os, const RefVal *PrevT, const RefVal &CurrV, bool DeallocSent) { // Get the previous type state. RefVal PrevV = *PrevT; // Specially handle -dealloc. if (DeallocSent) { // Determine if the object's reference count was pushed to zero. assert(!PrevV.hasSameState(CurrV) && "The state should have changed."); // We may not have transitioned to 'release' if we hit an error. // This case is handled elsewhere. if (CurrV.getKind() == RefVal::Released) { assert(CurrV.getCombinedCounts() == 0); os << "Object released by directly sending the '-dealloc' message"; return true; } } // Determine if the typestate has changed. if (!PrevV.hasSameState(CurrV)) switch (CurrV.getKind()) { case RefVal::Owned: case RefVal::NotOwned: if (PrevV.getCount() == CurrV.getCount()) { // Did an autorelease message get sent? if (PrevV.getAutoreleaseCount() == CurrV.getAutoreleaseCount()) return false; assert(PrevV.getAutoreleaseCount() < CurrV.getAutoreleaseCount()); os << "Object autoreleased"; return true; } if (PrevV.getCount() > CurrV.getCount()) os << "Reference count decremented."; else os << "Reference count incremented."; if (unsigned Count = CurrV.getCount()) os << " The object now has a +" << Count << " retain count."; return true; case RefVal::Released: if (CurrV.getIvarAccessHistory() == RefVal::IvarAccessHistory::ReleasedAfterDirectAccess && CurrV.getIvarAccessHistory() != PrevV.getIvarAccessHistory()) { os << "Strong instance variable relinquished. "; } os << "Object released."; return true; case RefVal::ReturnedOwned: // Autoreleases can be applied after marking a node ReturnedOwned. if (CurrV.getAutoreleaseCount()) return false; os << "Object returned to caller as an owning reference (single " "retain count transferred to caller)"; return true; case RefVal::ReturnedNotOwned: os << "Object returned to caller with a +0 retain count"; return true; default: return false; } return true; } /// Finds argument index of the out paramter in the call {@code S} /// corresponding to the symbol {@code Sym}. /// If none found, returns None. static Optional findArgIdxOfSymbol(ProgramStateRef CurrSt, const LocationContext *LCtx, SymbolRef &Sym, Optional> CE) { if (!CE) return None; for (unsigned Idx = 0; Idx < (*CE)->getNumArgs(); Idx++) if (const MemRegion *MR = (*CE)->getArgSVal(Idx).getAsRegion()) if (const auto *TR = dyn_cast(MR)) if (CurrSt->getSVal(MR, TR->getValueType()).getAsSymExpr() == Sym) return Idx; return None; } Optional findMetaClassAlloc(const Expr *Callee) { if (const auto *ME = dyn_cast(Callee)) { if (ME->getMemberDecl()->getNameAsString() != "alloc") return None; const Expr *This = ME->getBase()->IgnoreParenImpCasts(); if (const auto *DRE = dyn_cast(This)) { const ValueDecl *VD = DRE->getDecl(); if (VD->getNameAsString() != "metaClass") return None; if (const auto *RD = dyn_cast(VD->getDeclContext())) return RD->getNameAsString(); } } return None; } std::string findAllocatedObjectName(const Stmt *S, QualType QT) { if (const auto *CE = dyn_cast(S)) if (auto Out = findMetaClassAlloc(CE->getCallee())) return *Out; return getPrettyTypeName(QT); } static void generateDiagnosticsForCallLike(ProgramStateRef CurrSt, const LocationContext *LCtx, const RefVal &CurrV, SymbolRef &Sym, const Stmt *S, llvm::raw_string_ostream &os) { CallEventManager &Mgr = CurrSt->getStateManager().getCallEventManager(); if (const CallExpr *CE = dyn_cast(S)) { // Get the name of the callee (if it is available) // from the tracked SVal. SVal X = CurrSt->getSValAsScalarOrLoc(CE->getCallee(), LCtx); const FunctionDecl *FD = X.getAsFunctionDecl(); // If failed, try to get it from AST. if (!FD) FD = dyn_cast(CE->getCalleeDecl()); if (const auto *MD = dyn_cast(CE->getCalleeDecl())) { os << "Call to method '" << MD->getQualifiedNameAsString() << '\''; } else if (FD) { os << "Call to function '" << FD->getQualifiedNameAsString() << '\''; } else { os << "function call"; } } else if (isa(S)) { os << "Operator 'new'"; } else { assert(isa(S)); CallEventRef Call = Mgr.getObjCMethodCall(cast(S), CurrSt, LCtx); switch (Call->getMessageKind()) { case OCM_Message: os << "Method"; break; case OCM_PropertyAccess: os << "Property"; break; case OCM_Subscript: os << "Subscript"; break; } } Optional> CE = Mgr.getCall(S, CurrSt, LCtx); auto Idx = findArgIdxOfSymbol(CurrSt, LCtx, Sym, CE); // If index is not found, we assume that the symbol was returned. if (!Idx) { os << " returns "; } else { os << " writes "; } if (CurrV.getObjKind() == ObjKind::CF) { os << "a Core Foundation object of type '" << Sym->getType().getAsString() << "' with a "; } else if (CurrV.getObjKind() == ObjKind::OS) { os << "an OSObject of type '" << findAllocatedObjectName(S, Sym->getType()) << "' with a "; } else if (CurrV.getObjKind() == ObjKind::Generalized) { os << "an object of type '" << Sym->getType().getAsString() << "' with a "; } else { assert(CurrV.getObjKind() == ObjKind::ObjC); QualType T = Sym->getType(); if (!isa(T)) { os << "an Objective-C object with a "; } else { const ObjCObjectPointerType *PT = cast(T); os << "an instance of " << PT->getPointeeType().getAsString() << " with a "; } } if (CurrV.isOwned()) { os << "+1 retain count"; } else { assert(CurrV.isNotOwned()); os << "+0 retain count"; } if (Idx) { os << " into an out parameter '"; const ParmVarDecl *PVD = (*CE)->parameters()[*Idx]; PVD->getNameForDiagnostic(os, PVD->getASTContext().getPrintingPolicy(), /*Qualified=*/false); os << "'"; QualType RT = (*CE)->getResultType(); if (!RT.isNull() && !RT->isVoidType()) { SVal RV = (*CE)->getReturnValue(); if (CurrSt->isNull(RV).isConstrainedTrue()) { os << " (assuming the call returns zero)"; } else if (CurrSt->isNonNull(RV).isConstrainedTrue()) { os << " (assuming the call returns non-zero)"; } } } } namespace clang { namespace ento { namespace retaincountchecker { class RefCountReportVisitor : public BugReporterVisitor { protected: SymbolRef Sym; public: RefCountReportVisitor(SymbolRef sym) : Sym(sym) {} void Profile(llvm::FoldingSetNodeID &ID) const override { static int x = 0; ID.AddPointer(&x); ID.AddPointer(Sym); } std::shared_ptr VisitNode(const ExplodedNode *N, BugReporterContext &BRC, BugReport &BR) override; std::shared_ptr getEndPath(BugReporterContext &BRC, const ExplodedNode *N, BugReport &BR) override; }; class RefLeakReportVisitor : public RefCountReportVisitor { public: RefLeakReportVisitor(SymbolRef sym) : RefCountReportVisitor(sym) {} std::shared_ptr getEndPath(BugReporterContext &BRC, const ExplodedNode *N, BugReport &BR) override; }; } // end namespace retaincountchecker } // end namespace ento } // end namespace clang /// Find the first node with the parent stack frame. static const ExplodedNode *getCalleeNode(const ExplodedNode *Pred) { const StackFrameContext *SC = Pred->getStackFrame(); if (SC->inTopFrame()) return nullptr; const StackFrameContext *PC = SC->getParent()->getStackFrame(); if (!PC) return nullptr; const ExplodedNode *N = Pred; while (N && N->getStackFrame() != PC) { N = N->getFirstPred(); } return N; } /// Insert a diagnostic piece at function exit /// if a function parameter is annotated as "os_consumed", /// but it does not actually consume the reference. static std::shared_ptr annotateConsumedSummaryMismatch(const ExplodedNode *N, CallExitBegin &CallExitLoc, const SourceManager &SM, CallEventManager &CEMgr) { const ExplodedNode *CN = getCalleeNode(N); if (!CN) return nullptr; CallEventRef<> Call = CEMgr.getCaller(N->getStackFrame(), N->getState()); std::string sbuf; llvm::raw_string_ostream os(sbuf); ArrayRef Parameters = Call->parameters(); for (unsigned I=0; I < Call->getNumArgs() && I < Parameters.size(); ++I) { const ParmVarDecl *PVD = Parameters[I]; if (!PVD->hasAttr()) continue; if (SymbolRef SR = Call->getArgSVal(I).getAsLocSymbol()) { const RefVal *CountBeforeCall = getRefBinding(CN->getState(), SR); const RefVal *CountAtExit = getRefBinding(N->getState(), SR); if (!CountBeforeCall || !CountAtExit) continue; unsigned CountBefore = CountBeforeCall->getCount(); unsigned CountAfter = CountAtExit->getCount(); bool AsExpected = CountBefore > 0 && CountAfter == CountBefore - 1; if (!AsExpected) { os << "Parameter '"; PVD->getNameForDiagnostic(os, PVD->getASTContext().getPrintingPolicy(), /*Qualified=*/false); os << "' is marked as consuming, but the function did not consume " << "the reference\n"; } } } if (os.str().empty()) return nullptr; PathDiagnosticLocation L = PathDiagnosticLocation::create(CallExitLoc, SM); return std::make_shared(L, os.str()); } +/// Annotate the parameter at the analysis entry point. +static std::shared_ptr +annotateStartParameter(const ExplodedNode *N, SymbolRef Sym, + const SourceManager &SM) { + auto PP = N->getLocationAs(); + if (!PP) + return nullptr; + + const CFGBlock *Src = PP->getSrc(); + const RefVal *CurrT = getRefBinding(N->getState(), Sym); + + if (&Src->getParent()->getEntry() != Src || !CurrT || + getRefBinding(N->getFirstPred()->getState(), Sym)) + return nullptr; + + const auto *VR = cast(cast(Sym)->getRegion()); + const auto *PVD = cast(VR->getDecl()); + PathDiagnosticLocation L = PathDiagnosticLocation(PVD, SM); + + std::string s; + llvm::raw_string_ostream os(s); + os << "Parameter '" << PVD->getNameAsString() + << "' starts at +"; + if (CurrT->getCount() == 1) { + os << "1, as it is marked as consuming"; + } else { + assert(CurrT->getCount() == 0); + os << "0"; + } + return std::make_shared(L, os.str()); +} + std::shared_ptr RefCountReportVisitor::VisitNode(const ExplodedNode *N, BugReporterContext &BRC, BugReport &BR) { const auto &BT = static_cast(BR.getBugType()); const auto *Checker = static_cast(BT.getChecker()); bool IsFreeUnowned = BT.getBugType() == RefCountBug::FreeNotOwned || BT.getBugType() == RefCountBug::DeallocNotOwned; const SourceManager &SM = BRC.getSourceManager(); CallEventManager &CEMgr = BRC.getStateManager().getCallEventManager(); if (auto CE = N->getLocationAs()) if (auto PD = annotateConsumedSummaryMismatch(N, *CE, SM, CEMgr)) return PD; + if (auto PD = annotateStartParameter(N, Sym, SM)) + return PD; + // FIXME: We will eventually need to handle non-statement-based events // (__attribute__((cleanup))). if (!N->getLocation().getAs()) return nullptr; // Check if the type state has changed. const ExplodedNode *PrevNode = N->getFirstPred(); ProgramStateRef PrevSt = PrevNode->getState(); ProgramStateRef CurrSt = N->getState(); const LocationContext *LCtx = N->getLocationContext(); const RefVal* CurrT = getRefBinding(CurrSt, Sym); if (!CurrT) return nullptr; const RefVal &CurrV = *CurrT; const RefVal *PrevT = getRefBinding(PrevSt, Sym); // Create a string buffer to constain all the useful things we want // to tell the user. std::string sbuf; llvm::raw_string_ostream os(sbuf); if (PrevT && IsFreeUnowned && CurrV.isNotOwned() && PrevT->isOwned()) { os << "Object is now not exclusively owned"; auto Pos = PathDiagnosticLocation::create(N->getLocation(), SM); return std::make_shared(Pos, os.str()); } // This is the allocation site since the previous node had no bindings // for this symbol. if (!PrevT) { const Stmt *S = N->getLocation().castAs().getStmt(); if (isa(S) && isSynthesizedAccessor(LCtx->getStackFrame())) { S = LCtx->getStackFrame()->getCallSite(); } if (isa(S)) { os << "NSArray literal is an object with a +0 retain count"; } else if (isa(S)) { os << "NSDictionary literal is an object with a +0 retain count"; } else if (const ObjCBoxedExpr *BL = dyn_cast(S)) { if (isNumericLiteralExpression(BL->getSubExpr())) os << "NSNumber literal is an object with a +0 retain count"; else { const ObjCInterfaceDecl *BoxClass = nullptr; if (const ObjCMethodDecl *Method = BL->getBoxingMethod()) BoxClass = Method->getClassInterface(); // We should always be able to find the boxing class interface, // but consider this future-proofing. if (BoxClass) { os << *BoxClass << " b"; } else { os << "B"; } os << "oxed expression produces an object with a +0 retain count"; } } else if (isa(S)) { os << "Object loaded from instance variable"; } else { generateDiagnosticsForCallLike(CurrSt, LCtx, CurrV, Sym, S, os); } PathDiagnosticLocation Pos(S, SM, N->getLocationContext()); return std::make_shared(Pos, os.str()); } // Gather up the effects that were performed on the object at this // program point bool DeallocSent = false; const ProgramPointTag *Tag = N->getLocation().getTag(); if (Tag == &Checker->getCastFailTag()) { os << "Assuming dynamic cast returns null due to type mismatch"; } if (Tag == &Checker->getDeallocSentTag()) { // We only have summaries attached to nodes after evaluating CallExpr and // ObjCMessageExprs. const Stmt *S = N->getLocation().castAs().getStmt(); if (const CallExpr *CE = dyn_cast(S)) { // Iterate through the parameter expressions and see if the symbol // was ever passed as an argument. unsigned i = 0; for (auto AI=CE->arg_begin(), AE=CE->arg_end(); AI!=AE; ++AI, ++i) { // Retrieve the value of the argument. Is it the symbol // we are interested in? if (CurrSt->getSValAsScalarOrLoc(*AI, LCtx).getAsLocSymbol() != Sym) continue; // We have an argument. Get the effect! DeallocSent = true; } } else if (const ObjCMessageExpr *ME = dyn_cast(S)) { if (const Expr *receiver = ME->getInstanceReceiver()) { if (CurrSt->getSValAsScalarOrLoc(receiver, LCtx) .getAsLocSymbol() == Sym) { // The symbol we are tracking is the receiver. DeallocSent = true; } } } } if (!shouldGenerateNote(os, PrevT, CurrV, DeallocSent)) return nullptr; if (os.str().empty()) return nullptr; // We have nothing to say! const Stmt *S = N->getLocation().castAs().getStmt(); PathDiagnosticLocation Pos(S, BRC.getSourceManager(), N->getLocationContext()); auto P = std::make_shared(Pos, os.str()); // Add the range by scanning the children of the statement for any bindings // to Sym. for (const Stmt *Child : S->children()) if (const Expr *Exp = dyn_cast_or_null(Child)) if (CurrSt->getSValAsScalarOrLoc(Exp, LCtx).getAsLocSymbol() == Sym) { P->addRange(Exp->getSourceRange()); break; } return std::move(P); } static Optional describeRegion(const MemRegion *MR) { if (const auto *VR = dyn_cast_or_null(MR)) return std::string(VR->getDecl()->getName()); // Once we support more storage locations for bindings, // this would need to be improved. return None; } namespace { // Find the first node in the current function context that referred to the // tracked symbol and the memory location that value was stored to. Note, the // value is only reported if the allocation occurred in the same function as // the leak. The function can also return a location context, which should be // treated as interesting. struct AllocationInfo { const ExplodedNode* N; const MemRegion *R; const LocationContext *InterestingMethodContext; AllocationInfo(const ExplodedNode *InN, const MemRegion *InR, const LocationContext *InInterestingMethodContext) : N(InN), R(InR), InterestingMethodContext(InInterestingMethodContext) {} }; } // end anonymous namespace static AllocationInfo GetAllocationSite(ProgramStateManager &StateMgr, const ExplodedNode *N, SymbolRef Sym) { const ExplodedNode *AllocationNode = N; const ExplodedNode *AllocationNodeInCurrentOrParentContext = N; const MemRegion *FirstBinding = nullptr; const LocationContext *LeakContext = N->getLocationContext(); // The location context of the init method called on the leaked object, if // available. const LocationContext *InitMethodContext = nullptr; while (N) { ProgramStateRef St = N->getState(); const LocationContext *NContext = N->getLocationContext(); if (!getRefBinding(St, Sym)) break; StoreManager::FindUniqueBinding FB(Sym); StateMgr.iterBindings(St, FB); if (FB) { const MemRegion *R = FB.getRegion(); // Do not show local variables belonging to a function other than // where the error is reported. if (auto MR = dyn_cast(R->getMemorySpace())) if (MR->getStackFrame() == LeakContext->getStackFrame()) FirstBinding = R; } // AllocationNode is the last node in which the symbol was tracked. AllocationNode = N; // AllocationNodeInCurrentContext, is the last node in the current or // parent context in which the symbol was tracked. // // Note that the allocation site might be in the parent context. For example, // the case where an allocation happens in a block that captures a reference // to it and that reference is overwritten/dropped by another call to // the block. if (NContext == LeakContext || NContext->isParentOf(LeakContext)) AllocationNodeInCurrentOrParentContext = N; // Find the last init that was called on the given symbol and store the // init method's location context. if (!InitMethodContext) if (auto CEP = N->getLocation().getAs()) { const Stmt *CE = CEP->getCallExpr(); if (const auto *ME = dyn_cast_or_null(CE)) { const Stmt *RecExpr = ME->getInstanceReceiver(); if (RecExpr) { SVal RecV = St->getSVal(RecExpr, NContext); if (ME->getMethodFamily() == OMF_init && RecV.getAsSymbol() == Sym) InitMethodContext = CEP->getCalleeContext(); } } } N = N->getFirstPred(); } // If we are reporting a leak of the object that was allocated with alloc, // mark its init method as interesting. const LocationContext *InterestingMethodContext = nullptr; if (InitMethodContext) { const ProgramPoint AllocPP = AllocationNode->getLocation(); if (Optional SP = AllocPP.getAs()) if (const ObjCMessageExpr *ME = SP->getStmtAs()) if (ME->getMethodFamily() == OMF_alloc) InterestingMethodContext = InitMethodContext; } // If allocation happened in a function different from the leak node context, // do not report the binding. assert(N && "Could not find allocation node"); if (AllocationNodeInCurrentOrParentContext && AllocationNodeInCurrentOrParentContext->getLocationContext() != - LeakContext) + LeakContext) FirstBinding = nullptr; return AllocationInfo(AllocationNodeInCurrentOrParentContext, FirstBinding, InterestingMethodContext); } std::shared_ptr RefCountReportVisitor::getEndPath(BugReporterContext &BRC, const ExplodedNode *EndN, BugReport &BR) { BR.markInteresting(Sym); return BugReporterVisitor::getDefaultEndPath(BRC, EndN, BR); } std::shared_ptr RefLeakReportVisitor::getEndPath(BugReporterContext &BRC, const ExplodedNode *EndN, BugReport &BR) { // Tell the BugReporterContext to report cases when the tracked symbol is // assigned to different variables, etc. BR.markInteresting(Sym); // We are reporting a leak. Walk up the graph to get to the first node where // the symbol appeared, and also get the first VarDecl that tracked object // is stored to. AllocationInfo AllocI = GetAllocationSite(BRC.getStateManager(), EndN, Sym); const MemRegion* FirstBinding = AllocI.R; BR.markInteresting(AllocI.InterestingMethodContext); SourceManager& SM = BRC.getSourceManager(); // Compute an actual location for the leak. Sometimes a leak doesn't // occur at an actual statement (e.g., transition between blocks; end // of function) so we need to walk the graph and compute a real location. const ExplodedNode *LeakN = EndN; PathDiagnosticLocation L = PathDiagnosticLocation::createEndOfPath(LeakN, SM); std::string sbuf; llvm::raw_string_ostream os(sbuf); os << "Object leaked: "; Optional RegionDescription = describeRegion(FirstBinding); if (RegionDescription) { os << "object allocated and stored into '" << *RegionDescription << '\''; } else { os << "allocated object of type '" << getPrettyTypeName(Sym->getType()) << "'"; } // Get the retain count. const RefVal* RV = getRefBinding(EndN->getState(), Sym); assert(RV); if (RV->getKind() == RefVal::ErrorLeakReturned) { // FIXME: Per comments in rdar://6320065, "create" only applies to CF // objects. Only "copy", "alloc", "retain" and "new" transfer ownership // to the caller for NS objects. const Decl *D = &EndN->getCodeDecl(); os << (isa(D) ? " is returned from a method " : " is returned from a function "); if (D->hasAttr()) { os << "that is annotated as CF_RETURNS_NOT_RETAINED"; } else if (D->hasAttr()) { os << "that is annotated as NS_RETURNS_NOT_RETAINED"; } else if (D->hasAttr()) { os << "that is annotated as OS_RETURNS_NOT_RETAINED"; } else { if (const ObjCMethodDecl *MD = dyn_cast(D)) { if (BRC.getASTContext().getLangOpts().ObjCAutoRefCount) { os << "managed by Automatic Reference Counting"; } else { os << "whose name ('" << MD->getSelector().getAsString() << "') does not start with " "'copy', 'mutableCopy', 'alloc' or 'new'." " This violates the naming convention rules" " given in the Memory Management Guide for Cocoa"; } } else { const FunctionDecl *FD = cast(D); - os << "whose name ('" << *FD - << "') does not contain 'Copy' or 'Create'. This violates the naming" - " convention rules given in the Memory Management Guide for Core" - " Foundation"; + ObjKind K = RV->getObjKind(); + if (K == ObjKind::ObjC || K == ObjKind::CF) { + os << "whose name ('" << *FD + << "') does not contain 'Copy' or 'Create'. This violates the " + "naming" + " convention rules given in the Memory Management Guide for " + "Core" + " Foundation"; + } else if (RV->getObjKind() == ObjKind::OS) { + std::string FuncName = FD->getNameAsString(); + os << "whose name ('" << FuncName + << "') starts with '" << StringRef(FuncName).substr(0, 3) << "'"; + } } } } else { os << " is not referenced later in this execution path and has a retain " "count of +" << RV->getCount(); } return std::make_shared(L, os.str()); } RefCountReport::RefCountReport(const RefCountBug &D, const LangOptions &LOpts, ExplodedNode *n, SymbolRef sym, bool isLeak) : BugReport(D, D.getDescription(), n), Sym(sym), isLeak(isLeak) { if (!isLeak) addVisitor(llvm::make_unique(sym)); } RefCountReport::RefCountReport(const RefCountBug &D, const LangOptions &LOpts, ExplodedNode *n, SymbolRef sym, StringRef endText) : BugReport(D, D.getDescription(), endText, n) { addVisitor(llvm::make_unique(sym)); } void RefLeakReport::deriveParamLocation(CheckerContext &Ctx, SymbolRef sym) { const SourceManager& SMgr = Ctx.getSourceManager(); if (!sym->getOriginRegion()) return; auto *Region = dyn_cast(sym->getOriginRegion()); if (Region) { const Decl *PDecl = Region->getDecl(); if (PDecl && isa(PDecl)) { PathDiagnosticLocation ParamLocation = PathDiagnosticLocation::create(PDecl, SMgr); Location = ParamLocation; UniqueingLocation = ParamLocation; UniqueingDecl = Ctx.getLocationContext()->getDecl(); } } } void RefLeakReport::deriveAllocLocation(CheckerContext &Ctx, SymbolRef sym) { // Most bug reports are cached at the location where they occurred. // With leaks, we want to unique them by the location where they were // allocated, and only report a single path. To do this, we need to find // the allocation site of a piece of tracked memory, which we do via a // call to GetAllocationSite. This will walk the ExplodedGraph backwards. // Note that this is *not* the trimmed graph; we are guaranteed, however, // that all ancestor nodes that represent the allocation site have the // same SourceLocation. const ExplodedNode *AllocNode = nullptr; const SourceManager& SMgr = Ctx.getSourceManager(); AllocationInfo AllocI = GetAllocationSite(Ctx.getStateManager(), getErrorNode(), sym); AllocNode = AllocI.N; AllocBinding = AllocI.R; markInteresting(AllocI.InterestingMethodContext); // Get the SourceLocation for the allocation site. // FIXME: This will crash the analyzer if an allocation comes from an // implicit call (ex: a destructor call). // (Currently there are no such allocations in Cocoa, though.) AllocStmt = PathDiagnosticLocation::getStmt(AllocNode); if (!AllocStmt) { AllocBinding = nullptr; return; } PathDiagnosticLocation AllocLocation = PathDiagnosticLocation::createBegin(AllocStmt, SMgr, AllocNode->getLocationContext()); Location = AllocLocation; // Set uniqieing info, which will be used for unique the bug reports. The // leaks should be uniqued on the allocation site. UniqueingLocation = AllocLocation; UniqueingDecl = AllocNode->getLocationContext()->getDecl(); } void RefLeakReport::createDescription(CheckerContext &Ctx) { assert(Location.isValid() && UniqueingDecl && UniqueingLocation.isValid()); Description.clear(); llvm::raw_string_ostream os(Description); os << "Potential leak of an object"; Optional RegionDescription = describeRegion(AllocBinding); if (RegionDescription) { os << " stored into '" << *RegionDescription << '\''; } else { // If we can't figure out the name, just supply the type information. os << " of type '" << getPrettyTypeName(Sym->getType()) << "'"; } } RefLeakReport::RefLeakReport(const RefCountBug &D, const LangOptions &LOpts, ExplodedNode *n, SymbolRef sym, CheckerContext &Ctx) : RefCountReport(D, LOpts, n, sym, /*isLeak=*/true) { deriveAllocLocation(Ctx, sym); if (!AllocBinding) deriveParamLocation(Ctx, sym); createDescription(Ctx); addVisitor(llvm::make_unique(sym)); } diff --git a/clang/test/Analysis/Inputs/expected-plists/retain-release.m.objc.plist b/clang/test/Analysis/Inputs/expected-plists/retain-release.m.objc.plist index def9a4a3cc93..00c651f1fdd1 100644 --- a/clang/test/Analysis/Inputs/expected-plists/retain-release.m.objc.plist +++ b/clang/test/Analysis/Inputs/expected-plists/retain-release.m.objc.plist @@ -1,26111 +1,26111 @@ clang_version diagnostics path kindcontrol edges start - line348 + line355 col3 file0 - line348 + line355 col16 file0 end - line349 + line356 col3 file0 - line349 + line356 col11 file0 kindevent location - line349 + line356 col20 file0 ranges - line349 + line356 col20 file0 - line349 + line356 col37 file0 depth0 extended_message Call to function 'CFDateCreate' returns a Core Foundation object of type 'CFDateRef' with a +1 retain count message Call to function 'CFDateCreate' returns a Core Foundation object of type 'CFDateRef' with a +1 retain count kindcontrol edges start - line349 + line356 col3 file0 - line349 + line356 col11 file0 end - line350 + line357 col3 file0 - line350 + line357 col10 file0 kindevent location - line350 + line357 col3 file0 ranges - line350 + line357 col3 file0 - line350 + line357 col16 file0 - line350 + line357 col12 file0 - line350 + line357 col15 file0 depth0 extended_message Reference count incremented. The object now has a +2 retain count message Reference count incremented. The object now has a +2 retain count kindcontrol edges start - line350 + line357 col3 file0 - line350 + line357 col10 file0 end - line351 + line358 col3 file0 - line351 + line358 col11 file0 kindevent location - line351 + line358 col3 file0 ranges - line351 + line358 col3 file0 - line351 + line358 col17 file0 - line351 + line358 col13 file0 - line351 + line358 col16 file0 depth0 extended_message Reference count decremented. The object now has a +1 retain count message Reference count decremented. The object now has a +1 retain count kindcontrol edges start - line351 + line358 col3 file0 - line351 + line358 col11 file0 end - line353 + line360 col3 file0 - line353 + line360 col11 file0 kindevent location - line353 + line360 col3 file0 ranges - line353 + line360 col3 file0 - line353 + line360 col17 file0 - line353 + line360 col13 file0 - line353 + line360 col16 file0 depth0 extended_message Object released message Object released kindcontrol edges start - line353 + line360 col3 file0 - line353 + line360 col11 file0 end - line354 + line361 col3 file0 - line354 + line361 col3 file0 kindcontrol edges start - line354 + line361 col3 file0 - line354 + line361 col3 file0 end - line354 + line361 col7 file0 - line354 + line361 col27 file0 kindevent location - line354 + line361 col7 file0 ranges - line354 + line361 col29 file0 - line354 + line361 col32 file0 depth0 extended_message Reference-counted object is used after it is released message Reference-counted object is used after it is released descriptionReference-counted object is used after it is released categoryMemory (Core Foundation/Objective-C/OSObject) typeUse-after-release check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context1089a297e77ff0c9d2d55cfb3aae26d3 issue_context_kindfunction issue_contextf1 issue_hash_function_offset7 location - line354 + line361 col7 file0 ExecutedLines 0 - 347 - 348 - 349 - 350 - 351 - 352 - 353 354 + 355 + 356 + 357 + 358 + 359 + 360 + 361 path kindcontrol edges start - line359 + line366 col3 file0 - line359 + line366 col16 file0 end - line360 + line367 col3 file0 - line360 + line367 col11 file0 kindevent location - line360 + line367 col20 file0 ranges - line360 + line367 col20 file0 - line360 + line367 col37 file0 depth0 extended_message Call to function 'CFDateCreate' returns a Core Foundation object of type 'CFDateRef' with a +1 retain count message Call to function 'CFDateCreate' returns a Core Foundation object of type 'CFDateRef' with a +1 retain count kindcontrol edges start - line360 + line367 col3 file0 - line360 + line367 col11 file0 end - line361 + line368 col3 file0 - line361 + line368 col3 file0 kindevent location - line361 + line368 col3 file0 ranges - line361 + line368 col3 file0 - line361 + line368 col27 file0 - line361 + line368 col4 file0 - line361 + line368 col19 file0 depth0 extended_message Reference count incremented. The object now has a +2 retain count message Reference count incremented. The object now has a +2 retain count kindcontrol edges start - line361 + line368 col3 file0 - line361 + line368 col3 file0 end - line362 + line369 col3 file0 - line362 + line369 col11 file0 kindevent location - line362 + line369 col3 file0 ranges - line362 + line369 col3 file0 - line362 + line369 col17 file0 - line362 + line369 col13 file0 - line362 + line369 col16 file0 depth0 extended_message Reference count decremented. The object now has a +1 retain count message Reference count decremented. The object now has a +1 retain count kindcontrol edges start - line362 + line369 col3 file0 - line362 + line369 col11 file0 end - line364 + line371 col3 file0 - line364 + line371 col3 file0 kindevent location - line364 + line371 col3 file0 ranges - line364 + line371 col3 file0 - line364 + line371 col28 file0 - line364 + line371 col4 file0 - line364 + line371 col19 file0 depth0 extended_message Object released message Object released kindcontrol edges start - line364 + line371 col3 file0 - line364 + line371 col3 file0 end - line365 + line372 col3 file0 - line365 + line372 col3 file0 kindcontrol edges start - line365 + line372 col3 file0 - line365 + line372 col3 file0 end - line365 + line372 col7 file0 - line365 + line372 col27 file0 kindevent location - line365 + line372 col7 file0 ranges - line365 + line372 col29 file0 - line365 + line372 col32 file0 depth0 extended_message Reference-counted object is used after it is released message Reference-counted object is used after it is released descriptionReference-counted object is used after it is released categoryMemory (Core Foundation/Objective-C/OSObject) typeUse-after-release check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_contextbb12c99d56657635b20d4a0801590eed issue_context_kindfunction issue_contextf2 issue_hash_function_offset7 location - line365 + line372 col7 file0 ExecutedLines 0 - 358 - 359 - 360 - 361 - 362 - 363 - 364 365 + 366 + 367 + 368 + 369 + 370 + 371 + 372 path kindcontrol edges start - line395 + line402 col3 file0 - line395 + line402 col16 file0 end - line396 + line403 col3 file0 - line396 + line403 col11 file0 kindevent location - line396 + line403 col20 file0 ranges - line396 + line403 col20 file0 - line396 + line403 col37 file0 depth0 extended_message Call to function 'CFDateCreate' returns a Core Foundation object of type 'CFDateRef' with a +1 retain count message Call to function 'CFDateCreate' returns a Core Foundation object of type 'CFDateRef' with a +1 retain count kindcontrol edges start - line396 + line403 col3 file0 - line396 + line403 col11 file0 end - line398 + line405 col3 file0 - line398 + line405 col4 file0 kindcontrol edges start - line398 + line405 col3 file0 - line398 + line405 col4 file0 end - line398 + line405 col7 file0 - line398 + line405 col7 file0 kindevent location - line398 + line405 col7 file0 ranges - line398 + line405 col7 file0 - line398 + line405 col7 file0 depth0 extended_message Assuming 'x' is 0 message Assuming 'x' is 0 kindcontrol edges start - line398 + line405 col7 file0 - line398 + line405 col7 file0 end - line401 + line408 col3 file0 - line401 + line408 col8 file0 kindcontrol edges start - line401 + line408 col3 file0 - line401 + line408 col8 file0 end - line401 + line408 col10 file0 - line401 + line408 col10 file0 kindevent location - line401 + line408 col10 file0 ranges - line401 + line408 col10 file0 - line401 + line408 col10 file0 depth0 extended_message Object leaked: object allocated and stored into 'date' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'date' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'date' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context0e9bb151f425535a0ec1b0bf0574dd7d issue_context_kindfunction issue_contextf5 issue_hash_function_offset2 location - line401 + line408 col10 file0 ExecutedLines 0 - 394 - 395 - 396 - 398 401 + 402 + 403 + 405 + 408 path kindevent location - line407 + line414 col20 file0 ranges - line407 + line414 col20 file0 - line407 + line414 col62 file0 depth0 extended_message Call to function 'CFDateCreate' returns a Core Foundation object of type 'CFDateRef' with a +1 retain count message Call to function 'CFDateCreate' returns a Core Foundation object of type 'CFDateRef' with a +1 retain count kindcontrol edges start - line407 + line414 col3 file0 - line407 + line414 col11 file0 end - line408 + line415 col3 file0 - line408 + line415 col10 file0 kindevent location - line408 + line415 col3 file0 ranges - line408 + line415 col3 file0 - line408 + line415 col16 file0 - line408 + line415 col12 file0 - line408 + line415 col15 file0 depth0 extended_message Reference count incremented. The object now has a +2 retain count message Reference count incremented. The object now has a +2 retain count kindcontrol edges start - line408 + line415 col3 file0 - line408 + line415 col10 file0 end - line409 + line416 col3 file0 - line409 + line416 col8 file0 kindevent location - line409 + line416 col3 file0 ranges - line409 + line416 col3 file0 - line409 + line416 col13 file0 depth0 extended_message Object leaked: object allocated and stored into 'date' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'date' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'date' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_contextad4b758c93bbe7feeee349a526293527 issue_context_kindfunction issue_contextf6 issue_hash_function_offset1 location - line409 + line416 col3 file0 ExecutedLines 0 - 406 - 407 - 408 - 409 + 413 + 414 + 415 + 416 path kindevent location - line415 + line422 col20 file0 ranges - line415 + line422 col20 file0 - line415 + line422 col62 file0 depth0 extended_message Call to function 'CFDateCreate' returns a Core Foundation object of type 'CFDateRef' with a +1 retain count message Call to function 'CFDateCreate' returns a Core Foundation object of type 'CFDateRef' with a +1 retain count kindcontrol edges start - line415 + line422 col3 file0 - line415 + line422 col11 file0 end - line416 + line423 col3 file0 - line416 + line423 col10 file0 kindevent location - line416 + line423 col3 file0 ranges - line416 + line423 col3 file0 - line416 + line423 col16 file0 - line416 + line423 col12 file0 - line416 + line423 col15 file0 depth0 extended_message Reference count incremented. The object now has a +2 retain count message Reference count incremented. The object now has a +2 retain count kindcontrol edges start - line416 + line423 col3 file0 - line416 + line423 col10 file0 end - line418 + line425 col3 file0 - line418 + line425 col8 file0 kindevent location - line418 + line425 col3 file0 ranges - line418 + line425 col3 file0 - line418 + line425 col13 file0 depth0 extended_message Object leaked: object allocated and stored into 'date' is not referenced later in this execution path and has a retain count of +2 message Object leaked: object allocated and stored into 'date' is not referenced later in this execution path and has a retain count of +2 descriptionPotential leak of an object stored into 'date' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context2a319c210c1c5b4274e3f28931ead03b issue_context_kindfunction issue_contextf7 issue_hash_function_offset1 location - line418 + line425 col3 file0 ExecutedLines 0 - 414 - 415 - 416 - 417 - 418 + 421 + 422 + 423 + 424 + 425 path kindcontrol edges start - line415 + line422 col3 file0 - line415 + line422 col11 file0 end - line417 + line424 col3 file0 - line417 + line424 col6 file0 kindevent location - line417 + line424 col10 file0 ranges - line417 + line424 col10 file0 - line417 + line424 col52 file0 depth0 extended_message Call to function 'CFDateCreate' returns a Core Foundation object of type 'CFDateRef' with a +1 retain count message Call to function 'CFDateCreate' returns a Core Foundation object of type 'CFDateRef' with a +1 retain count kindcontrol edges start - line417 + line424 col3 file0 - line417 + line424 col6 file0 end - line418 + line425 col3 file0 - line418 + line425 col8 file0 kindevent location - line418 + line425 col3 file0 ranges - line418 + line425 col3 file0 - line418 + line425 col13 file0 depth0 extended_message Object leaked: object allocated and stored into 'date' is returned from a function whose name ('f7') does not contain 'Copy' or 'Create'. This violates the naming convention rules given in the Memory Management Guide for Core Foundation message Object leaked: object allocated and stored into 'date' is returned from a function whose name ('f7') does not contain 'Copy' or 'Create'. This violates the naming convention rules given in the Memory Management Guide for Core Foundation descriptionPotential leak of an object stored into 'date' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak of returned object check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context2c347e0a0af508867a6d854a3fc8f690 issue_context_kindfunction issue_contextf7 issue_hash_function_offset3 location - line418 + line425 col3 file0 ExecutedLines 0 - 414 - 415 - 416 - 417 - 418 + 421 + 422 + 423 + 424 + 425 path kindevent location - line426 + line433 col20 file0 ranges - line426 + line433 col20 file0 - line426 + line433 col33 file0 depth0 extended_message Call to function 'MyDateCreate' returns a Core Foundation object of type 'CFDateRef' with a +1 retain count message Call to function 'MyDateCreate' returns a Core Foundation object of type 'CFDateRef' with a +1 retain count kindcontrol edges start - line426 + line433 col3 file0 - line426 + line433 col11 file0 end - line427 + line434 col3 file0 - line427 + line434 col10 file0 kindevent location - line427 + line434 col3 file0 ranges - line427 + line434 col3 file0 - line427 + line434 col16 file0 - line427 + line434 col12 file0 - line427 + line434 col15 file0 depth0 extended_message Reference count incremented. The object now has a +2 retain count message Reference count incremented. The object now has a +2 retain count kindcontrol edges start - line427 + line434 col3 file0 - line427 + line434 col10 file0 end - line428 + line435 col3 file0 - line428 + line435 col8 file0 kindevent location - line428 + line435 col3 file0 ranges - line428 + line435 col3 file0 - line428 + line435 col13 file0 depth0 extended_message Object leaked: object allocated and stored into 'date' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'date' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'date' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context0be746eb38e868156f7f57ea95735f4e issue_context_kindfunction issue_contextf8 issue_hash_function_offset1 location - line428 + line435 col3 file0 ExecutedLines 0 - 425 - 426 - 427 - 428 + 432 + 433 + 434 + 435 path kindcontrol edges start - line432 + line439 col3 file0 - line432 + line439 col11 file0 end - line433 + line440 col3 file0 - line433 + line440 col5 file0 kindevent location - line433 + line440 col3 file0 ranges - line433 + line440 col3 file0 - line433 + line440 col8 file0 depth0 extended_message 'p' initialized to a null pointer value message 'p' initialized to a null pointer value kindcontrol edges start - line433 + line440 col3 file0 - line433 + line440 col5 file0 end - line435 + line442 col3 file0 - line435 + line442 col4 file0 kindcontrol edges start - line435 + line442 col3 file0 - line435 + line442 col4 file0 end - line435 + line442 col7 file0 - line435 + line442 col7 file0 kindevent location - line435 + line442 col7 file0 ranges - line435 + line442 col7 file0 - line435 + line442 col11 file0 depth0 extended_message Assuming 'date' is null message Assuming 'date' is null kindcontrol edges start - line435 + line442 col7 file0 - line435 + line442 col7 file0 end - line435 + line442 col14 file0 - line435 + line442 col14 file0 kindcontrol edges start - line435 + line442 col14 file0 - line435 + line442 col14 file0 end - line435 + line442 col17 file0 - line435 + line442 col17 file0 kindevent location - line435 + line442 col17 file0 ranges - line435 + line442 col15 file0 - line435 + line442 col15 file0 depth0 extended_message Dereference of null pointer (loaded from variable 'p') message Dereference of null pointer (loaded from variable 'p') descriptionDereference of null pointer (loaded from variable 'p') categoryLogic error typeDereference of null pointer check_namecore.NullDereference issue_hash_content_of_line_in_context4af5d8d1438976cc7fa006af5f843b13 issue_context_kindfunction issue_contextf9 issue_hash_function_offset4 location - line435 + line442 col17 file0 ExecutedLines 0 - 431 - 432 - 433 - 435 + 438 + 439 + 440 + 442 path kindevent location - line444 + line451 col20 file0 ranges - line444 + line451 col20 file0 - line444 + line451 col75 file0 depth0 extended_message Call to function 'DADiskCreateFromBSDName' returns a Core Foundation object of type 'DADiskRef' with a +1 retain count message Call to function 'DADiskCreateFromBSDName' returns a Core Foundation object of type 'DADiskRef' with a +1 retain count kindcontrol edges start - line444 + line451 col3 file0 - line444 + line451 col11 file0 end - line445 + line452 col3 file0 - line445 + line452 col4 file0 kindcontrol edges start - line445 + line452 col3 file0 - line445 + line452 col4 file0 end - line445 + line452 col7 file0 - line445 + line452 col10 file0 kindevent location - line445 + line452 col7 file0 ranges - line445 + line452 col7 file0 - line445 + line452 col10 file0 depth0 extended_message Assuming 'disk' is non-null message Assuming 'disk' is non-null kindcontrol edges start - line445 + line452 col7 file0 - line445 + line452 col10 file0 end - line445 + line452 col13 file0 - line445 + line452 col17 file0 kindcontrol edges start - line445 + line452 col13 file0 - line445 + line452 col17 file0 end - line447 + line454 col3 file0 - line447 + line454 col6 file0 kindcontrol edges start - line447 + line454 col3 file0 - line447 + line454 col6 file0 end - line448 + line455 col3 file0 - line448 + line455 col4 file0 kindcontrol edges start - line448 + line455 col3 file0 - line448 + line455 col4 file0 end - line448 + line455 col7 file0 - line448 + line455 col10 file0 kindevent location - line448 + line455 col7 file0 ranges - line448 + line455 col7 file0 - line448 + line455 col10 file0 depth0 extended_message Assuming 'disk' is null message Assuming 'disk' is null kindcontrol edges start - line448 + line455 col7 file0 - line448 + line455 col10 file0 end - line450 + line457 col3 file0 - line450 + line457 col17 file0 kindcontrol edges start - line450 + line457 col3 file0 - line450 + line457 col17 file0 end - line450 + line457 col26 file0 - line450 + line457 col46 file0 kindevent location - line450 + line457 col26 file0 ranges - line450 + line457 col26 file0 - line450 + line457 col46 file0 depth0 extended_message Object leaked: object allocated and stored into 'disk' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'disk' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'disk' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context3e83186b5b944ef7a3ec026d469d5ad7 issue_context_kindfunction issue_contextf10 issue_hash_function_offset1 location - line450 + line457 col26 file0 ExecutedLines 0 - 443 - 444 - 445 - 447 - 448 450 + 451 + 452 + 454 + 455 + 457 path kindcontrol edges start - line444 + line451 col3 file0 - line444 + line451 col11 file0 end - line445 + line452 col3 file0 - line445 + line452 col4 file0 kindcontrol edges start - line445 + line452 col3 file0 - line445 + line452 col4 file0 end - line445 + line452 col7 file0 - line445 + line452 col10 file0 kindevent location - line445 + line452 col7 file0 ranges - line445 + line452 col7 file0 - line445 + line452 col10 file0 depth0 extended_message Assuming 'disk' is null message Assuming 'disk' is null kindcontrol edges start - line445 + line452 col7 file0 - line445 + line452 col10 file0 end - line447 + line454 col3 file0 - line447 + line454 col6 file0 kindcontrol edges start - line447 + line454 col3 file0 - line447 + line454 col6 file0 end - line448 + line455 col3 file0 - line448 + line455 col4 file0 kindcontrol edges start - line448 + line455 col3 file0 - line448 + line455 col4 file0 end - line448 + line455 col7 file0 - line448 + line455 col10 file0 kindevent location - line448 + line455 col7 file0 ranges - line448 + line455 col7 file0 - line448 + line455 col10 file0 depth0 extended_message Assuming 'disk' is null message Assuming 'disk' is null kindcontrol edges start - line448 + line455 col7 file0 - line448 + line455 col10 file0 end - line450 + line457 col3 file0 - line450 + line457 col17 file0 kindevent location - line450 + line457 col26 file0 ranges - line450 + line457 col26 file0 - line450 + line457 col49 file0 depth0 extended_message Call to function 'DADiskCopyDescription' returns a Core Foundation object of type 'CFDictionaryRef' with a +1 retain count message Call to function 'DADiskCopyDescription' returns a Core Foundation object of type 'CFDictionaryRef' with a +1 retain count kindcontrol edges start - line450 + line457 col3 file0 - line450 + line457 col17 file0 end - line451 + line458 col3 file0 - line451 + line458 col4 file0 kindcontrol edges start - line451 + line458 col3 file0 - line451 + line458 col4 file0 end - line451 + line458 col7 file0 - line451 + line458 col10 file0 kindevent location - line451 + line458 col7 file0 ranges - line451 + line458 col7 file0 - line451 + line458 col10 file0 depth0 extended_message Assuming 'dict' is non-null message Assuming 'dict' is non-null kindcontrol edges start - line451 + line458 col7 file0 - line451 + line458 col10 file0 end - line451 + line458 col13 file0 - line451 + line458 col17 file0 kindevent location - line451 + line458 col13 file0 ranges - line451 + line458 col13 file0 - line451 + line458 col17 file0 depth0 extended_message Object leaked: object allocated and stored into 'dict' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'dict' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'dict' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_contextffc6479dc21fc10cdb83b4392685ed36 issue_context_kindfunction issue_contextf10 issue_hash_function_offset7 location - line451 + line458 col13 file0 ExecutedLines 0 - 443 - 444 - 445 - 447 - 448 450 451 + 452 + 454 + 455 + 457 + 458 path kindcontrol edges start - line444 + line451 col3 file0 - line444 + line451 col11 file0 end - line445 + line452 col3 file0 - line445 + line452 col4 file0 kindcontrol edges start - line445 + line452 col3 file0 - line445 + line452 col4 file0 end - line445 + line452 col7 file0 - line445 + line452 col10 file0 kindevent location - line445 + line452 col7 file0 ranges - line445 + line452 col7 file0 - line445 + line452 col10 file0 depth0 extended_message Assuming 'disk' is null message Assuming 'disk' is null kindcontrol edges start - line445 + line452 col7 file0 - line445 + line452 col10 file0 end - line447 + line454 col3 file0 - line447 + line454 col6 file0 kindcontrol edges start - line447 + line454 col3 file0 - line447 + line454 col6 file0 end - line448 + line455 col3 file0 - line448 + line455 col4 file0 kindcontrol edges start - line448 + line455 col3 file0 - line448 + line455 col4 file0 end - line448 + line455 col7 file0 - line448 + line455 col10 file0 kindevent location - line448 + line455 col7 file0 ranges - line448 + line455 col7 file0 - line448 + line455 col10 file0 depth0 extended_message Assuming 'disk' is null message Assuming 'disk' is null kindcontrol edges start - line448 + line455 col7 file0 - line448 + line455 col10 file0 end - line450 + line457 col3 file0 - line450 + line457 col17 file0 kindcontrol edges start - line450 + line457 col3 file0 - line450 + line457 col17 file0 end - line451 + line458 col3 file0 - line451 + line458 col4 file0 kindcontrol edges start - line451 + line458 col3 file0 - line451 + line458 col4 file0 end - line451 + line458 col7 file0 - line451 + line458 col10 file0 kindevent location - line451 + line458 col7 file0 ranges - line451 + line458 col7 file0 - line451 + line458 col10 file0 depth0 extended_message Assuming 'dict' is null message Assuming 'dict' is null kindcontrol edges start - line451 + line458 col7 file0 - line451 + line458 col10 file0 end - line453 + line460 col3 file0 - line453 + line460 col6 file0 kindevent location - line453 + line460 col10 file0 ranges - line453 + line460 col10 file0 - line453 + line460 col31 file0 depth0 extended_message Call to function 'DADiskCopyWholeDisk' returns a Core Foundation object of type 'DADiskRef' with a +1 retain count message Call to function 'DADiskCopyWholeDisk' returns a Core Foundation object of type 'DADiskRef' with a +1 retain count kindcontrol edges start - line453 + line460 col3 file0 - line453 + line460 col6 file0 end - line454 + line461 col3 file0 - line454 + line461 col4 file0 kindcontrol edges start - line454 + line461 col3 file0 - line454 + line461 col4 file0 end - line454 + line461 col7 file0 - line454 + line461 col10 file0 kindevent location - line454 + line461 col7 file0 ranges - line454 + line461 col7 file0 - line454 + line461 col10 file0 depth0 extended_message Assuming 'disk' is non-null message Assuming 'disk' is non-null kindcontrol edges start - line454 + line461 col7 file0 - line454 + line461 col10 file0 end - line454 + line461 col13 file0 - line454 + line461 col17 file0 kindevent location - line454 + line461 col13 file0 ranges - line454 + line461 col13 file0 - line454 + line461 col17 file0 depth0 extended_message Object leaked: object allocated and stored into 'disk' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'disk' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'disk' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context1c06fc99a1d078653ae8e4fe308e09cd issue_context_kindfunction issue_contextf10 issue_hash_function_offset10 location - line454 + line461 col13 file0 ExecutedLines 0 - 443 - 444 - 445 - 447 - 448 450 451 - 453 + 452 454 + 455 + 457 + 458 + 460 + 461 path kindcontrol edges start - line444 + line451 col3 file0 - line444 + line451 col11 file0 end - line445 + line452 col3 file0 - line445 + line452 col4 file0 kindcontrol edges start - line445 + line452 col3 file0 - line445 + line452 col4 file0 end - line445 + line452 col7 file0 - line445 + line452 col10 file0 kindevent location - line445 + line452 col7 file0 ranges - line445 + line452 col7 file0 - line445 + line452 col10 file0 depth0 extended_message Assuming 'disk' is null message Assuming 'disk' is null kindcontrol edges start - line445 + line452 col7 file0 - line445 + line452 col10 file0 end - line447 + line454 col3 file0 - line447 + line454 col6 file0 kindevent location - line447 + line454 col10 file0 ranges - line447 + line454 col10 file0 - line447 + line454 col63 file0 depth0 extended_message Call to function 'DADiskCreateFromIOMedia' returns a Core Foundation object of type 'DADiskRef' with a +1 retain count message Call to function 'DADiskCreateFromIOMedia' returns a Core Foundation object of type 'DADiskRef' with a +1 retain count kindcontrol edges start - line447 + line454 col3 file0 - line447 + line454 col6 file0 end - line448 + line455 col3 file0 - line448 + line455 col4 file0 kindcontrol edges start - line448 + line455 col3 file0 - line448 + line455 col4 file0 end - line448 + line455 col7 file0 - line448 + line455 col10 file0 kindevent location - line448 + line455 col7 file0 ranges - line448 + line455 col7 file0 - line448 + line455 col10 file0 depth0 extended_message Assuming 'disk' is non-null message Assuming 'disk' is non-null kindcontrol edges start - line448 + line455 col7 file0 - line448 + line455 col10 file0 end - line448 + line455 col13 file0 - line448 + line455 col17 file0 kindcontrol edges start - line448 + line455 col13 file0 - line448 + line455 col17 file0 end - line450 + line457 col3 file0 - line450 + line457 col17 file0 kindcontrol edges start - line450 + line457 col3 file0 - line450 + line457 col17 file0 end - line451 + line458 col3 file0 - line451 + line458 col4 file0 kindcontrol edges start - line451 + line458 col3 file0 - line451 + line458 col4 file0 end - line451 + line458 col7 file0 - line451 + line458 col10 file0 kindevent location - line451 + line458 col7 file0 ranges - line451 + line458 col7 file0 - line451 + line458 col10 file0 depth0 extended_message Assuming 'dict' is null message Assuming 'dict' is null kindcontrol edges start - line451 + line458 col7 file0 - line451 + line458 col10 file0 end - line453 + line460 col3 file0 - line453 + line460 col6 file0 kindcontrol edges start - line453 + line460 col3 file0 - line453 + line460 col6 file0 end - line454 + line461 col3 file0 - line454 + line461 col4 file0 kindcontrol edges start - line454 + line461 col3 file0 - line454 + line461 col4 file0 end - line454 + line461 col7 file0 - line454 + line461 col10 file0 kindevent location - line454 + line461 col7 file0 ranges - line454 + line461 col7 file0 - line454 + line461 col10 file0 depth0 extended_message Assuming 'disk' is null message Assuming 'disk' is null kindcontrol edges start - line454 + line461 col7 file0 - line454 + line461 col10 file0 end - line456 + line463 col3 file0 - line456 + line463 col16 file0 kindcontrol edges start - line456 + line463 col3 file0 - line456 + line463 col16 file0 end - line456 + line463 col30 file0 - line456 + line463 col46 file0 kindevent location - line456 + line463 col30 file0 ranges - line456 + line463 col30 file0 - line456 + line463 col46 file0 depth0 extended_message Object leaked: object allocated and stored into 'disk' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'disk' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'disk' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context460f099c6ae21a4b3ae818c9f65df2b0 issue_context_kindfunction issue_contextf10 issue_hash_function_offset4 location - line456 + line463 col30 file0 ExecutedLines 0 - 443 - 444 - 445 - 447 - 448 450 451 - 453 + 452 454 - 456 + 455 + 457 + 458 + 460 + 461 + 463 path kindcontrol edges start - line444 + line451 col3 file0 - line444 + line451 col11 file0 end - line445 + line452 col3 file0 - line445 + line452 col4 file0 kindcontrol edges start - line445 + line452 col3 file0 - line445 + line452 col4 file0 end - line445 + line452 col7 file0 - line445 + line452 col10 file0 kindevent location - line445 + line452 col7 file0 ranges - line445 + line452 col7 file0 - line445 + line452 col10 file0 depth0 extended_message Assuming 'disk' is null message Assuming 'disk' is null kindcontrol edges start - line445 + line452 col7 file0 - line445 + line452 col10 file0 end - line447 + line454 col3 file0 - line447 + line454 col6 file0 kindcontrol edges start - line447 + line454 col3 file0 - line447 + line454 col6 file0 end - line448 + line455 col3 file0 - line448 + line455 col4 file0 kindcontrol edges start - line448 + line455 col3 file0 - line448 + line455 col4 file0 end - line448 + line455 col7 file0 - line448 + line455 col10 file0 kindevent location - line448 + line455 col7 file0 ranges - line448 + line455 col7 file0 - line448 + line455 col10 file0 depth0 extended_message Assuming 'disk' is null message Assuming 'disk' is null kindcontrol edges start - line448 + line455 col7 file0 - line448 + line455 col10 file0 end - line450 + line457 col3 file0 - line450 + line457 col17 file0 kindcontrol edges start - line450 + line457 col3 file0 - line450 + line457 col17 file0 end - line451 + line458 col3 file0 - line451 + line458 col4 file0 kindcontrol edges start - line451 + line458 col3 file0 - line451 + line458 col4 file0 end - line451 + line458 col7 file0 - line451 + line458 col10 file0 kindevent location - line451 + line458 col7 file0 ranges - line451 + line458 col7 file0 - line451 + line458 col10 file0 depth0 extended_message Assuming 'dict' is null message Assuming 'dict' is null kindcontrol edges start - line451 + line458 col7 file0 - line451 + line458 col10 file0 end - line453 + line460 col3 file0 - line453 + line460 col6 file0 kindcontrol edges start - line453 + line460 col3 file0 - line453 + line460 col6 file0 end - line454 + line461 col3 file0 - line454 + line461 col4 file0 kindcontrol edges start - line454 + line461 col3 file0 - line454 + line461 col4 file0 end - line454 + line461 col7 file0 - line454 + line461 col10 file0 kindevent location - line454 + line461 col7 file0 ranges - line454 + line461 col7 file0 - line454 + line461 col10 file0 depth0 extended_message Assuming 'disk' is null message Assuming 'disk' is null kindcontrol edges start - line454 + line461 col7 file0 - line454 + line461 col10 file0 end - line456 + line463 col3 file0 - line456 + line463 col16 file0 kindcontrol edges start - line456 + line463 col3 file0 - line456 + line463 col16 file0 end - line456 + line463 col30 file0 - line456 + line463 col46 file0 kindevent location - line456 + line463 col30 file0 ranges - line456 + line463 col30 file0 - line457 + line464 col68 file0 depth0 extended_message Call to function 'DADissenterCreate' returns a Core Foundation object of type 'DADissenterRef' with a +1 retain count message Call to function 'DADissenterCreate' returns a Core Foundation object of type 'DADissenterRef' with a +1 retain count kindcontrol edges start - line456 + line463 col30 file0 - line456 + line463 col46 file0 end - line456 + line463 col3 file0 - line456 + line463 col16 file0 kindcontrol edges start - line456 + line463 col3 file0 - line456 + line463 col16 file0 end - line458 + line465 col3 file0 - line458 + line465 col4 file0 kindcontrol edges start - line458 + line465 col3 file0 - line458 + line465 col4 file0 end - line458 + line465 col7 file0 - line458 + line465 col15 file0 kindevent location - line458 + line465 col7 file0 ranges - line458 + line465 col7 file0 - line458 + line465 col15 file0 depth0 extended_message Assuming 'dissenter' is non-null message Assuming 'dissenter' is non-null kindcontrol edges start - line458 + line465 col7 file0 - line458 + line465 col15 file0 end - line458 + line465 col18 file0 - line458 + line465 col22 file0 kindevent location - line458 + line465 col18 file0 ranges - line458 + line465 col18 file0 - line458 + line465 col22 file0 depth0 extended_message Object leaked: object allocated and stored into 'dissenter' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'dissenter' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'dissenter' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context65004e269b1b5cb5d9b5c6f7a02926e3 issue_context_kindfunction issue_contextf10 issue_hash_function_offset13 location - line458 + line465 col18 file0 ExecutedLines 0 - 443 - 444 - 445 - 447 - 448 450 451 - 453 + 452 454 - 456 + 455 457 458 + 460 + 461 + 463 + 464 + 465 path kindcontrol edges start - line444 + line451 col3 file0 - line444 + line451 col11 file0 end - line445 + line452 col3 file0 - line445 + line452 col4 file0 kindcontrol edges start - line445 + line452 col3 file0 - line445 + line452 col4 file0 end - line445 + line452 col7 file0 - line445 + line452 col10 file0 kindevent location - line445 + line452 col7 file0 ranges - line445 + line452 col7 file0 - line445 + line452 col10 file0 depth0 extended_message Assuming 'disk' is null message Assuming 'disk' is null kindcontrol edges start - line445 + line452 col7 file0 - line445 + line452 col10 file0 end - line447 + line454 col3 file0 - line447 + line454 col6 file0 kindcontrol edges start - line447 + line454 col3 file0 - line447 + line454 col6 file0 end - line448 + line455 col3 file0 - line448 + line455 col4 file0 kindcontrol edges start - line448 + line455 col3 file0 - line448 + line455 col4 file0 end - line448 + line455 col7 file0 - line448 + line455 col10 file0 kindevent location - line448 + line455 col7 file0 ranges - line448 + line455 col7 file0 - line448 + line455 col10 file0 depth0 extended_message Assuming 'disk' is null message Assuming 'disk' is null kindcontrol edges start - line448 + line455 col7 file0 - line448 + line455 col10 file0 end - line450 + line457 col3 file0 - line450 + line457 col17 file0 kindcontrol edges start - line450 + line457 col3 file0 - line450 + line457 col17 file0 end - line451 + line458 col3 file0 - line451 + line458 col4 file0 kindcontrol edges start - line451 + line458 col3 file0 - line451 + line458 col4 file0 end - line451 + line458 col7 file0 - line451 + line458 col10 file0 kindevent location - line451 + line458 col7 file0 ranges - line451 + line458 col7 file0 - line451 + line458 col10 file0 depth0 extended_message Assuming 'dict' is null message Assuming 'dict' is null kindcontrol edges start - line451 + line458 col7 file0 - line451 + line458 col10 file0 end - line453 + line460 col3 file0 - line453 + line460 col6 file0 kindcontrol edges start - line453 + line460 col3 file0 - line453 + line460 col6 file0 end - line454 + line461 col3 file0 - line454 + line461 col4 file0 kindcontrol edges start - line454 + line461 col3 file0 - line454 + line461 col4 file0 end - line454 + line461 col7 file0 - line454 + line461 col10 file0 kindevent location - line454 + line461 col7 file0 ranges - line454 + line461 col7 file0 - line454 + line461 col10 file0 depth0 extended_message Assuming 'disk' is null message Assuming 'disk' is null kindcontrol edges start - line454 + line461 col7 file0 - line454 + line461 col10 file0 end - line456 + line463 col3 file0 - line456 + line463 col16 file0 kindcontrol edges start - line456 + line463 col3 file0 - line456 + line463 col16 file0 end - line458 + line465 col3 file0 - line458 + line465 col4 file0 kindcontrol edges start - line458 + line465 col3 file0 - line458 + line465 col4 file0 end - line458 + line465 col7 file0 - line458 + line465 col15 file0 kindevent location - line458 + line465 col7 file0 ranges - line458 + line465 col7 file0 - line458 + line465 col15 file0 depth0 extended_message Assuming 'dissenter' is null message Assuming 'dissenter' is null kindcontrol edges start - line458 + line465 col7 file0 - line458 + line465 col15 file0 end - line460 + line467 col3 file0 - line460 + line467 col14 file0 kindevent location - line460 + line467 col26 file0 ranges - line460 + line467 col26 file0 - line460 + line467 col61 file0 depth0 extended_message Call to function 'DASessionCreate' returns a Core Foundation object of type 'DASessionRef' with a +1 retain count message Call to function 'DASessionCreate' returns a Core Foundation object of type 'DASessionRef' with a +1 retain count kindcontrol edges start - line460 + line467 col3 file0 - line460 + line467 col14 file0 end - line461 + line468 col3 file0 - line461 + line468 col4 file0 kindcontrol edges start - line461 + line468 col3 file0 - line461 + line468 col4 file0 end - line461 + line468 col7 file0 - line461 + line468 col13 file0 kindevent location - line461 + line468 col7 file0 ranges - line461 + line468 col7 file0 - line461 + line468 col13 file0 depth0 extended_message Assuming 'session' is non-null message Assuming 'session' is non-null kindcontrol edges start - line461 + line468 col7 file0 - line461 + line468 col13 file0 end - line461 + line468 col16 file0 - line461 + line468 col20 file0 kindevent location - line461 + line468 col16 file0 ranges - line461 + line468 col16 file0 - line461 + line468 col20 file0 depth0 extended_message Object leaked: object allocated and stored into 'session' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'session' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'session' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_contexte9c1be038ef498b7985f5b1ddcb5444f issue_context_kindfunction issue_contextf10 issue_hash_function_offset17 location - line461 + line468 col16 file0 ExecutedLines 0 - 443 - 444 - 445 - 447 - 448 450 451 - 453 + 452 454 - 456 + 455 457 458 460 461 + 463 + 464 + 465 + 467 + 468 path kindevent location - line478 + line485 col16 file0 ranges - line478 + line485 col16 file0 - line478 + line485 col31 file0 depth0 extended_message Call to function 'CMCreateFooRef' returns a Core Foundation object of type 'CMFooRef' with a +1 retain count message Call to function 'CMCreateFooRef' returns a Core Foundation object of type 'CMFooRef' with a +1 retain count kindcontrol edges start - line478 + line485 col3 file0 - line478 + line485 col10 file0 end - line479 + line486 col1 file0 - line479 + line486 col1 file0 kindevent location - line479 + line486 col1 file0 depth0 extended_message Object leaked: object allocated and stored into 'f' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'f' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'f' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context9c7c3b2bf298c7d046fd6fc7f6fe688e issue_context_kindfunction issue_contexttestLeakCoreMediaReferenceType issue_hash_function_offset1 location - line479 + line486 col1 file0 ExecutedLines 0 - 477 - 478 - 479 + 484 + 485 + 486 path kindevent location - line482 + line489 col16 file0 ranges - line482 + line489 col16 file0 - line482 + line489 col28 file0 depth0 extended_message Call to function 'CMGetFooRef' returns a Core Foundation object of type 'CMFooRef' with a +0 retain count message Call to function 'CMGetFooRef' returns a Core Foundation object of type 'CMFooRef' with a +0 retain count kindcontrol edges start - line482 + line489 col3 file0 - line482 + line489 col10 file0 end - line483 + line490 col3 file0 - line483 + line490 col11 file0 kindevent location - line483 + line490 col3 file0 ranges - line483 + line490 col13 file0 - line483 + line490 col13 file0 depth0 extended_message Incorrect decrement of the reference count of an object that is not owned at this point by the caller message Incorrect decrement of the reference count of an object that is not owned at this point by the caller descriptionIncorrect decrement of the reference count of an object that is not owned at this point by the caller categoryMemory (Core Foundation/Objective-C/OSObject) typeBad release check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context69932084739a429d667d8de6de42af0b issue_context_kindfunction issue_contexttestOverReleaseMediaReferenceType issue_hash_function_offset2 location - line483 + line490 col3 file0 ExecutedLines 0 - 481 - 482 - 483 + 488 + 489 + 490 path kindcontrol edges start - line516 + line523 col3 file0 - line516 + line523 col13 file0 end - line520 + line527 col3 file0 - line520 + line527 col21 file0 kindevent location - line520 + line527 col23 file0 ranges - line520 + line527 col23 file0 - line520 + line527 col57 file0 depth0 extended_message Assuming 'buffer' is not equal to 'queue' message Assuming 'buffer' is not equal to 'queue' kindevent location - line520 + line527 col3 file0 ranges - line520 + line527 col3 file0 - line520 + line527 col58 file0 depth0 extended_message FALSE message FALSE descriptionFALSE categorydebug typeChecking analyzer assumptions check_namedebug.ExprInspection issue_hash_content_of_line_in_context78b71dc497a2059b950406cb2a1cfd01 issue_context_kindfunction issue_contexttestCMBufferQueueDequeueAndRetain issue_hash_function_offset5 location - line520 + line527 col3 file0 ExecutedLines 0 - 515 - 516 - 520 + 522 + 523 + 527 path kindcontrol edges start - line516 + line523 col3 file0 - line516 + line523 col13 file0 end - line520 + line527 col3 file0 - line520 + line527 col21 file0 kindevent location - line520 + line527 col23 file0 ranges - line520 + line527 col23 file0 - line520 + line527 col57 file0 depth0 extended_message Assuming 'buffer' is equal to 'queue' message Assuming 'buffer' is equal to 'queue' kindevent location - line520 + line527 col3 file0 ranges - line520 + line527 col3 file0 - line520 + line527 col58 file0 depth0 extended_message TRUE message TRUE descriptionTRUE categorydebug typeChecking analyzer assumptions check_namedebug.ExprInspection issue_hash_content_of_line_in_context78b71dc497a2059b950406cb2a1cfd01 issue_context_kindfunction issue_contexttestCMBufferQueueDequeueAndRetain issue_hash_function_offset5 location - line520 + line527 col3 file0 ExecutedLines 0 - 515 - 516 - 520 + 522 + 523 + 527 path kindevent location - line516 + line523 col24 file0 ranges - line516 + line523 col24 file0 - line516 + line523 col59 file0 depth0 extended_message Call to function 'CMBufferQueueDequeueAndRetain' returns a Core Foundation object of type 'CMBufferRef' with a +1 retain count message Call to function 'CMBufferQueueDequeueAndRetain' returns a Core Foundation object of type 'CMBufferRef' with a +1 retain count kindcontrol edges start - line516 + line523 col3 file0 - line516 + line523 col13 file0 end - line520 + line527 col3 file0 - line520 + line527 col21 file0 kindevent location - line520 + line527 col23 file0 ranges - line520 + line527 col23 file0 - line520 + line527 col57 file0 depth0 extended_message Assuming 'buffer' is not equal to 'queue' message Assuming 'buffer' is not equal to 'queue' kindevent location - line520 + line527 col3 file0 ranges - line520 + line527 col3 file0 - line520 + line527 col58 file0 depth0 extended_message Object leaked: object allocated and stored into 'buffer' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'buffer' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'buffer' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context0f30258c45ed9ecd8646db90eaf20c4a issue_context_kindfunction issue_contexttestCMBufferQueueDequeueAndRetain issue_hash_function_offset1 location - line520 + line527 col3 file0 ExecutedLines 0 - 515 - 516 - 520 + 522 + 523 + 527 path kindcontrol edges start - line527 + line534 col3 file0 - line527 + line534 col19 file0 end - line540 + line547 col3 file0 - line540 + line547 col4 file0 kindevent location - line540 + line547 col22 file0 ranges - line540 + line547 col22 file0 - line540 + line547 col49 file0 depth0 extended_message Call to function 'CFArrayGetValueAtIndex' returns a Core Foundation object of type 'const void *' with a +0 retain count message Call to function 'CFArrayGetValueAtIndex' returns a Core Foundation object of type 'const void *' with a +0 retain count kindcontrol edges start - line540 + line547 col3 file0 - line540 + line547 col4 file0 end - line546 + line553 col3 file0 - line546 + line553 col11 file0 kindevent location - line546 + line553 col3 file0 ranges - line546 + line553 col13 file0 - line546 + line553 col14 file0 depth0 extended_message Incorrect decrement of the reference count of an object that is not owned at this point by the caller message Incorrect decrement of the reference count of an object that is not owned at this point by the caller descriptionIncorrect decrement of the reference count of an object that is not owned at this point by the caller categoryMemory (Core Foundation/Objective-C/OSObject) typeBad release check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context13e672795c0e57433c642c84f26f6c9b issue_context_kindfunction issue_contextf11 issue_hash_function_offset21 location - line546 + line553 col3 file0 ExecutedLines 0 - 525 - 527 - 530 - 531 + 532 534 537 - 540 - 543 - 546 + 538 + 541 + 544 + 547 + 550 + 553 path kindevent location - line554 + line561 col17 file0 ranges - line554 + line561 col17 file0 - line554 + line561 col29 file0 depth0 extended_message Call to function 'MyCreateFun' returns a Core Foundation object of type 'CFTypeRef' with a +1 retain count message Call to function 'MyCreateFun' returns a Core Foundation object of type 'CFTypeRef' with a +1 retain count kindcontrol edges start - line554 + line561 col3 file0 - line554 + line561 col11 file0 end - line555 + line562 col1 file0 - line555 + line562 col1 file0 kindevent location - line555 + line562 col1 file0 depth0 extended_message Object leaked: object allocated and stored into 'o' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'o' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'o' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_contexteeff9e133573bdbc1aeb633284cbdb2b issue_context_kindfunction issue_contextf12 issue_hash_function_offset1 location - line555 + line562 col1 file0 ExecutedLines 0 - 553 - 554 - 555 + 560 + 561 + 562 path kindevent location - line563 + line570 col25 file0 ranges - line563 + line570 col25 file0 - line563 + line570 col75 file0 depth0 extended_message Call to function 'CFArrayCreateMutable' returns a Core Foundation object of type 'CFMutableArrayRef' with a +1 retain count message Call to function 'CFArrayCreateMutable' returns a Core Foundation object of type 'CFMutableArrayRef' with a +1 retain count kindcontrol edges start - line563 + line570 col3 file0 - line563 + line570 col19 file0 end - line564 + line571 col3 file0 - line564 + line571 col3 file0 kindevent location - line564 + line571 col3 file0 ranges - line564 + line571 col3 file0 - line564 + line571 col22 file0 - line564 + line571 col4 file0 - line564 + line571 col9 file0 depth0 extended_message Object autoreleased message Object autoreleased kindcontrol edges start - line564 + line571 col3 file0 - line564 + line571 col3 file0 end - line565 + line572 col3 file0 - line565 + line572 col3 file0 kindevent location - line565 + line572 col3 file0 ranges - line565 + line572 col3 file0 - line565 + line572 col22 file0 - line565 + line572 col4 file0 - line565 + line572 col9 file0 depth0 extended_message Object autoreleased message Object autoreleased kindcontrol edges start - line565 + line572 col3 file0 - line565 + line572 col3 file0 end - line566 + line573 col1 file0 - line566 + line573 col1 file0 kindevent location - line566 + line573 col1 file0 depth0 extended_message Object was autoreleased 2 times but the object has a +1 retain count message Object was autoreleased 2 times but the object has a +1 retain count descriptionObject autoreleased too many times categoryMemory (Core Foundation/Objective-C/OSObject) typeObject autoreleased too many times check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context620a4245edc8df18036da34702ca01c8 issue_context_kindfunction issue_contextf13_autorelease_b issue_hash_function_offset4 location - line566 + line573 col1 file0 ExecutedLines 0 - 562 - 563 - 564 - 565 - 566 + 569 + 570 + 571 + 572 + 573 path kindevent location - line569 + line576 col25 file0 ranges - line569 + line576 col25 file0 - line569 + line576 col75 file0 depth0 extended_message Call to function 'CFArrayCreateMutable' returns a Core Foundation object of type 'CFMutableArrayRef' with a +1 retain count message Call to function 'CFArrayCreateMutable' returns a Core Foundation object of type 'CFMutableArrayRef' with a +1 retain count kindcontrol edges start - line569 + line576 col3 file0 - line569 + line576 col19 file0 end - line570 + line577 col3 file0 - line570 + line577 col3 file0 kindevent location - line570 + line577 col3 file0 ranges - line570 + line577 col3 file0 - line570 + line577 col22 file0 - line570 + line577 col4 file0 - line570 + line577 col9 file0 depth0 extended_message Object autoreleased message Object autoreleased kindcontrol edges start - line570 + line577 col3 file0 - line570 + line577 col3 file0 end - line571 + line578 col3 file0 - line571 + line578 col3 file0 kindevent location - line571 + line578 col3 file0 ranges - line571 + line578 col3 file0 - line571 + line578 col22 file0 - line571 + line578 col4 file0 - line571 + line578 col9 file0 depth0 extended_message Object autoreleased message Object autoreleased kindcontrol edges start - line571 + line578 col3 file0 - line571 + line578 col3 file0 end - line572 + line579 col3 file0 - line572 + line579 col8 file0 kindevent location - line572 + line579 col3 file0 ranges - line572 + line579 col3 file0 - line572 + line579 col10 file0 depth0 extended_message Object was autoreleased 2 times but the object has a +0 retain count message Object was autoreleased 2 times but the object has a +0 retain count descriptionObject autoreleased too many times categoryMemory (Core Foundation/Objective-C/OSObject) typeObject autoreleased too many times check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context1a87a5f904c165069a731b0325d45edf issue_context_kindfunction issue_contextf13_autorelease_c issue_hash_function_offset4 location - line572 + line579 col3 file0 ExecutedLines 0 - 568 - 569 - 570 - 571 - 572 + 575 + 576 + 577 + 578 + 579 path kindevent location - line576 + line583 col25 file0 ranges - line576 + line583 col25 file0 - line576 + line583 col75 file0 depth0 extended_message Call to function 'CFArrayCreateMutable' returns a Core Foundation object of type 'CFMutableArrayRef' with a +1 retain count message Call to function 'CFArrayCreateMutable' returns a Core Foundation object of type 'CFMutableArrayRef' with a +1 retain count kindcontrol edges start - line576 + line583 col3 file0 - line576 + line583 col19 file0 end - line577 + line584 col3 file0 - line577 + line584 col3 file0 kindevent location - line577 + line584 col3 file0 ranges - line577 + line584 col3 file0 - line577 + line584 col22 file0 - line577 + line584 col4 file0 - line577 + line584 col9 file0 depth0 extended_message Object autoreleased message Object autoreleased kindcontrol edges start - line577 + line584 col3 file0 - line577 + line584 col3 file0 end - line578 + line585 col3 file0 - line578 + line585 col3 file0 kindevent location - line578 + line585 col3 file0 ranges - line578 + line585 col3 file0 - line578 + line585 col22 file0 - line578 + line585 col4 file0 - line578 + line585 col9 file0 depth0 extended_message Object autoreleased message Object autoreleased kindcontrol edges start - line578 + line585 col3 file0 - line578 + line585 col3 file0 end - line579 + line586 col3 file0 - line579 + line586 col19 file0 kindcontrol edges start - line579 + line586 col3 file0 - line579 + line586 col19 file0 end - line579 + line586 col25 file0 - line579 + line586 col44 file0 kindevent location - line579 + line586 col25 file0 ranges - line579 + line586 col25 file0 - line579 + line586 col75 file0 depth0 extended_message Object was autoreleased 2 times but the object has a +1 retain count message Object was autoreleased 2 times but the object has a +1 retain count descriptionObject autoreleased too many times categoryMemory (Core Foundation/Objective-C/OSObject) typeObject autoreleased too many times check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context6ed645efdfe968f31d4356610bb6dd02 issue_context_kindfunction issue_contextf13_autorelease_d issue_hash_function_offset4 location - line579 + line586 col25 file0 ExecutedLines 0 - 575 - 576 - 577 - 578 - 579 + 582 + 583 + 584 + 585 + 586 path kindevent location - line587 + line594 col3 file0 ranges - line587 + line594 col3 file0 - line587 + line594 col53 file0 depth0 extended_message Call to function 'CFArrayCreateMutable' returns a Core Foundation object of type 'CFMutableArrayRef' with a +1 retain count message Call to function 'CFArrayCreateMutable' returns a Core Foundation object of type 'CFMutableArrayRef' with a +1 retain count kindcontrol edges start - line587 + line594 col3 file0 - line587 + line594 col22 file0 end - line588 + line595 col1 file0 - line588 + line595 col1 file0 kindevent location - line588 + line595 col1 file0 depth0 extended_message Object leaked: allocated object of type 'CFMutableArrayRef' is not referenced later in this execution path and has a retain count of +1 message Object leaked: allocated object of type 'CFMutableArrayRef' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object of type 'CFMutableArrayRef' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context5295be41524e9e28f4b1a608006801fe issue_context_kindfunction issue_contextf14_leakimmediately issue_hash_function_offset1 location - line588 + line595 col1 file0 ExecutedLines 0 - 586 - 587 - 588 + 593 + 594 + 595 path kindcontrol edges start - line602 + line609 col3 file0 - line602 + line609 col4 file0 end - line602 + line609 col7 file0 - line602 + line609 col7 file0 kindevent location - line602 + line609 col7 file0 ranges - line602 + line609 col7 file0 - line602 + line609 col7 file0 depth0 extended_message Assuming 'p' is null message Assuming 'p' is null kindcontrol edges start - line602 + line609 col7 file0 - line602 + line609 col7 file0 end - line605 + line612 col3 file0 - line605 + line612 col8 file0 kindcontrol edges start - line605 + line612 col3 file0 - line605 + line612 col8 file0 end - line605 + line612 col11 file0 - line605 + line612 col11 file0 kindcontrol edges start - line605 + line612 col11 file0 - line605 + line612 col11 file0 end - line607 + line614 col5 file0 - line607 + line614 col13 file0 kindevent location - line607 + line614 col5 file0 ranges - line607 + line614 col15 file0 - line607 + line614 col15 file0 depth0 extended_message Null pointer argument in call to CFRelease message Null pointer argument in call to CFRelease descriptionNull pointer argument in call to CFRelease categoryAPI Misuse (Apple) typenull passed to CF memory management function check_nameosx.coreFoundation.CFRetainRelease issue_hash_content_of_line_in_contexte7e2ba205af363f2c4cec7d01dcb6d6c issue_context_kindfunction issue_contextf16 issue_hash_function_offset6 location - line607 + line614 col5 file0 ExecutedLines 0 - 601 - 602 - 605 - 606 - 607 + 608 + 609 + 612 + 613 + 614 path kindcontrol edges start - line602 + line609 col3 file0 - line602 + line609 col4 file0 end - line602 + line609 col7 file0 - line602 + line609 col7 file0 kindevent location - line602 + line609 col7 file0 ranges - line602 + line609 col7 file0 - line602 + line609 col7 file0 depth0 extended_message Assuming 'p' is null message Assuming 'p' is null kindcontrol edges start - line602 + line609 col7 file0 - line602 + line609 col7 file0 end - line605 + line612 col3 file0 - line605 + line612 col8 file0 kindcontrol edges start - line605 + line612 col3 file0 - line605 + line612 col8 file0 end - line605 + line612 col11 file0 - line605 + line612 col11 file0 kindcontrol edges start - line605 + line612 col11 file0 - line605 + line612 col11 file0 end - line610 + line617 col5 file0 - line610 + line617 col12 file0 kindevent location - line610 + line617 col5 file0 ranges - line610 + line617 col14 file0 - line610 + line617 col14 file0 depth0 extended_message Null pointer argument in call to CFRetain message Null pointer argument in call to CFRetain descriptionNull pointer argument in call to CFRetain categoryAPI Misuse (Apple) typenull passed to CF memory management function check_nameosx.coreFoundation.CFRetainRelease issue_hash_content_of_line_in_context64f4a3367d5d8e832ca8a23ca4d72717 issue_context_kindfunction issue_contextf16 issue_hash_function_offset9 location - line610 + line617 col5 file0 ExecutedLines 0 - 601 - 602 - 605 + 608 609 - 610 + 612 + 616 + 617 path kindcontrol edges start - line602 + line609 col3 file0 - line602 + line609 col4 file0 end - line602 + line609 col7 file0 - line602 + line609 col7 file0 kindevent location - line602 + line609 col7 file0 ranges - line602 + line609 col7 file0 - line602 + line609 col7 file0 depth0 extended_message Assuming 'p' is null message Assuming 'p' is null kindcontrol edges start - line602 + line609 col7 file0 - line602 + line609 col7 file0 end - line605 + line612 col3 file0 - line605 + line612 col8 file0 kindcontrol edges start - line605 + line612 col3 file0 - line605 + line612 col8 file0 end - line605 + line612 col11 file0 - line605 + line612 col11 file0 kindcontrol edges start - line605 + line612 col11 file0 - line605 + line612 col11 file0 end - line613 + line620 col5 file0 - line613 + line620 col21 file0 kindevent location - line613 + line620 col5 file0 ranges - line613 + line620 col23 file0 - line613 + line620 col23 file0 depth0 extended_message Null pointer argument in call to CFMakeCollectable message Null pointer argument in call to CFMakeCollectable descriptionNull pointer argument in call to CFMakeCollectable categoryAPI Misuse (Apple) typenull passed to CF memory management function check_nameosx.coreFoundation.CFRetainRelease issue_hash_content_of_line_in_context61123dbb677396de5abbdd778c399140 issue_context_kindfunction issue_contextf16 issue_hash_function_offset12 location - line613 + line620 col5 file0 ExecutedLines 0 - 601 - 602 - 605 + 608 + 609 612 - 613 + 619 + 620 path kindcontrol edges start - line602 + line609 col3 file0 - line602 + line609 col4 file0 end - line602 + line609 col7 file0 - line602 + line609 col7 file0 kindevent location - line602 + line609 col7 file0 ranges - line602 + line609 col7 file0 - line602 + line609 col7 file0 depth0 extended_message Assuming 'p' is null message Assuming 'p' is null kindcontrol edges start - line602 + line609 col7 file0 - line602 + line609 col7 file0 end - line605 + line612 col3 file0 - line605 + line612 col8 file0 kindcontrol edges start - line605 + line612 col3 file0 - line605 + line612 col8 file0 end - line605 + line612 col11 file0 - line605 + line612 col11 file0 kindcontrol edges start - line605 + line612 col11 file0 - line605 + line612 col11 file0 end - line616 + line623 col5 file0 - line616 + line623 col17 file0 kindevent location - line616 + line623 col5 file0 ranges - line616 + line623 col19 file0 - line616 + line623 col19 file0 depth0 extended_message Null pointer argument in call to CFAutorelease message Null pointer argument in call to CFAutorelease descriptionNull pointer argument in call to CFAutorelease categoryAPI Misuse (Apple) typenull passed to CF memory management function check_nameosx.coreFoundation.CFRetainRelease issue_hash_content_of_line_in_context965bca78fe04bfa55b6ea428da3c20e3 issue_context_kindfunction issue_contextf16 issue_hash_function_offset15 location - line616 + line623 col5 file0 ExecutedLines 0 - 601 - 602 - 605 - 615 - 616 + 608 + 609 + 612 + 622 + 623 path kindevent location - line656 + line672 col10 file0 ranges - line656 + line672 col10 file0 - line656 + line672 col32 file0 depth0 extended_message Call to function 'isl_basic_map_cow' returns an object of type 'isl_basic_map *' with a +1 retain count message Call to function 'isl_basic_map_cow' returns an object of type 'isl_basic_map *' with a +1 retain count kindcontrol edges start - line656 + line672 col3 file0 - line656 + line672 col6 file0 end - line657 + line673 col1 file0 - line657 + line673 col1 file0 kindevent location - line657 + line673 col1 file0 depth0 extended_message Object leaked: object allocated and stored into 'bmap' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'bmap' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'bmap' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context2e5affde083280f6d31ed412ac8c2396 issue_context_kindfunction issue_contextf18 issue_hash_function_offset2 location - line657 + line673 col1 file0 ExecutedLines 0 - 654 - 656 - 657 + 670 + 672 + 673 path kindevent location - line682 + line698 col17 file0 ranges - line682 + line698 col17 file0 - line682 + line698 col55 file0 depth0 extended_message Method returns an Objective-C object with a +0 retain count message Method returns an Objective-C object with a +0 retain count kindcontrol edges start - line682 + line698 col3 file0 - line682 + line698 col10 file0 end - line683 + line699 col3 file0 - line683 + line699 col8 file0 kindevent location - line683 + line699 col3 file0 ranges - line683 + line699 col3 file0 - line683 + line699 col10 file0 depth0 extended_message Object with a +0 retain count returned to caller where a +1 (owning) retain count is expected message Object with a +0 retain count returned to caller where a +1 (owning) retain count is expected descriptionObject with a +0 retain count returned to caller where a +1 (owning) retain count is expected categoryMemory (Core Foundation/Objective-C/OSObject) typeMethod should return an owned object check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_contextfdd0cb02c08c718da2686b6e0f04aad7 issue_context_kindObjective-C method issue_contextnewString issue_hash_function_offset2 location - line683 + line699 col3 file0 ExecutedLines 0 - 681 - 682 - 683 + 697 + 698 + 699 path kindevent location - line696 + line712 col20 file0 ranges - line696 + line712 col20 file0 - line696 + line712 col63 file0 depth0 extended_message Method returns an instance of NSString with a +1 retain count message Method returns an instance of NSString with a +1 retain count kindcontrol edges start - line696 + line712 col3 file0 - line696 + line712 col10 file0 end - line703 + line719 col3 file0 - line703 + line719 col4 file0 kindcontrol edges start - line703 + line719 col3 file0 - line703 + line719 col4 file0 end - line703 + line719 col6 file0 - line703 + line719 col6 file0 kindevent location - line703 + line719 col6 file0 ranges - line703 + line719 col6 file0 - line703 + line719 col10 file0 depth0 extended_message Assuming 'name' is nil message Assuming 'name' is nil kindcontrol edges start - line703 + line719 col6 file0 - line703 + line719 col6 file0 end - line704 + line720 col5 file0 - line704 + line720 col10 file0 kindevent location - line704 + line720 col5 file0 ranges - line704 + line720 col5 file0 - line704 + line720 col10 file0 depth0 extended_message Object leaked: object allocated and stored into 'kind' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'kind' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'kind' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context03f39b74e1ccafa9c613ba4bb71de560 issue_context_kindfunction issue_contextrdar_6659160 issue_hash_function_offset5 location - line704 + line720 col5 file0 ExecutedLines 0 - 690 - 691 - 696 - 702 - 703 - 704 + 706 + 707 + 712 + 718 + 719 + 720 path kindcontrol edges start - line696 + line712 col3 file0 - line696 + line712 col10 file0 end - line703 + line719 col3 file0 - line703 + line719 col4 file0 kindcontrol edges start - line703 + line719 col3 file0 - line703 + line719 col4 file0 end - line703 + line719 col6 file0 - line703 + line719 col6 file0 kindevent location - line703 + line719 col6 file0 ranges - line703 + line719 col6 file0 - line703 + line719 col10 file0 depth0 extended_message Assuming 'name' is non-nil message Assuming 'name' is non-nil kindcontrol edges start - line703 + line719 col6 file0 - line703 + line719 col6 file0 end - line706 + line722 col3 file0 - line706 + line722 col7 file0 kindevent location - line706 + line722 col3 file0 ranges - line706 + line722 col3 file0 - line706 + line722 col19 file0 depth0 extended_message 'kindC' initialized to a null pointer value message 'kindC' initialized to a null pointer value kindcontrol edges start - line706 + line722 col3 file0 - line706 + line722 col7 file0 end - line714 + line730 col3 file0 - line714 + line730 col4 file0 kindcontrol edges start - line714 + line730 col3 file0 - line714 + line730 col4 file0 end - line714 + line730 col6 file0 - line714 + line730 col9 file0 kindevent location - line714 + line730 col6 file0 ranges - line714 + line730 col6 file0 - line714 + line730 col9 file0 depth0 extended_message Assuming 'kind' is nil message Assuming 'kind' is nil kindcontrol edges start - line714 + line730 col6 file0 - line714 + line730 col9 file0 end - line716 + line732 col3 file0 - line716 + line732 col4 file0 kindcontrol edges start - line716 + line732 col3 file0 - line716 + line732 col4 file0 end - line717 + line733 col5 file0 - line717 + line733 col9 file0 kindcontrol edges start - line717 + line733 col5 file0 - line717 + line733 col9 file0 end - line718 + line734 col3 file0 - line718 + line734 col4 file0 kindcontrol edges start - line718 + line734 col3 file0 - line718 + line734 col4 file0 end - line718 + line734 col13 file0 - line718 + line734 col17 file0 kindevent location - line718 + line734 col13 file0 ranges - line718 + line734 col13 file0 - line718 + line734 col17 file0 depth0 extended_message Array access (from variable 'kindC') results in a null pointer dereference message Array access (from variable 'kindC') results in a null pointer dereference descriptionArray access (from variable 'kindC') results in a null pointer dereference categoryLogic error typeDereference of null pointer check_namecore.NullDereference issue_hash_content_of_line_in_context2824c4e1d4ab13c3ae5a0ebb2aa4ed89 issue_context_kindfunction issue_contextrdar_6659160 issue_hash_function_offset27 location - line718 + line734 col13 file0 ExecutedLines 0 - 690 - 691 - 696 - 702 - 703 706 707 - 714 - 716 - 717 + 712 718 + 719 + 722 + 723 + 730 + 732 + 733 + 734 path kindcontrol edges start - line696 + line712 col3 file0 - line696 + line712 col10 file0 end - line702 + line718 col3 file0 - line702 + line718 col10 file0 kindevent location - line702 + line718 col20 file0 ranges - line702 + line718 col20 file0 - line702 + line718 col57 file0 depth0 extended_message Method returns an Objective-C object with a +0 retain count message Method returns an Objective-C object with a +0 retain count kindcontrol edges start - line702 + line718 col3 file0 - line702 + line718 col10 file0 end - line703 + line719 col3 file0 - line703 + line719 col4 file0 kindcontrol edges start - line703 + line719 col3 file0 - line703 + line719 col4 file0 end - line703 + line719 col6 file0 - line703 + line719 col6 file0 kindevent location - line703 + line719 col6 file0 ranges - line703 + line719 col6 file0 - line703 + line719 col10 file0 depth0 extended_message Assuming 'name' is non-nil message Assuming 'name' is non-nil kindcontrol edges start - line703 + line719 col6 file0 - line703 + line719 col6 file0 end - line706 + line722 col3 file0 - line706 + line722 col7 file0 kindcontrol edges start - line706 + line722 col3 file0 - line706 + line722 col7 file0 end - line714 + line730 col3 file0 - line714 + line730 col4 file0 kindcontrol edges start - line714 + line730 col3 file0 - line714 + line730 col4 file0 end - line714 + line730 col6 file0 - line714 + line730 col9 file0 kindevent location - line714 + line730 col6 file0 ranges - line714 + line730 col6 file0 - line714 + line730 col9 file0 depth0 extended_message Assuming 'kind' is non-nil message Assuming 'kind' is non-nil kindcontrol edges start - line714 + line730 col6 file0 - line714 + line730 col9 file0 end - line715 + line731 col5 file0 - line715 + line731 col9 file0 kindcontrol edges start - line715 + line731 col5 file0 - line715 + line731 col9 file0 end - line716 + line732 col3 file0 - line716 + line732 col4 file0 kindcontrol edges start - line716 + line732 col3 file0 - line716 + line732 col4 file0 end - line717 + line733 col5 file0 - line717 + line733 col9 file0 kindcontrol edges start - line717 + line733 col5 file0 - line717 + line733 col9 file0 end - line718 + line734 col3 file0 - line718 + line734 col4 file0 kindcontrol edges start - line718 + line734 col3 file0 - line718 + line734 col4 file0 end - line718 + line734 col6 file0 - line718 + line734 col6 file0 kindevent location - line718 + line734 col6 file0 ranges - line718 + line734 col6 file0 - line718 + line734 col21 file0 depth0 extended_message Assuming the condition is false message Assuming the condition is false kindcontrol edges start - line718 + line734 col6 file0 - line718 + line734 col6 file0 end - line720 + line736 col3 file0 - line720 + line736 col4 file0 kindcontrol edges start - line720 + line736 col3 file0 - line720 + line736 col4 file0 end - line720 + line736 col6 file0 - line720 + line736 col6 file0 kindevent location - line720 + line736 col6 file0 ranges - line720 + line736 col6 file0 - line720 + line736 col21 file0 depth0 extended_message Assuming the condition is false message Assuming the condition is false kindcontrol edges start - line720 + line736 col6 file0 - line720 + line736 col6 file0 end - line723 + line739 col3 file0 - line723 + line739 col3 file0 kindcontrol edges start - line723 + line739 col3 file0 - line723 + line739 col3 file0 end - line724 + line740 col3 file0 - line724 + line740 col3 file0 kindevent location - line724 + line740 col3 file0 ranges - line724 + line740 col4 file0 - line724 + line740 col7 file0 depth0 extended_message Incorrect decrement of the reference count of an object that is not owned at this point by the caller message Incorrect decrement of the reference count of an object that is not owned at this point by the caller descriptionIncorrect decrement of the reference count of an object that is not owned at this point by the caller categoryMemory (Core Foundation/Objective-C/OSObject) typeBad release check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_contextc8a4713a734a4f6e747423ef88af6bf8 issue_context_kindfunction issue_contextrdar_6659160 issue_hash_function_offset33 location - line724 + line740 col3 file0 ExecutedLines 0 - 690 - 691 - 696 - 702 - 703 706 707 - 714 - 715 - 716 - 717 + 712 718 - 720 + 719 + 722 723 - 724 + 730 + 731 + 732 + 733 + 734 + 736 + 739 + 740 path kindevent location - line746 + line762 col12 file0 ranges - line746 + line762 col12 file0 - line746 + line762 col34 file0 depth0 extended_message Method returns an instance of NSString with a +1 retain count message Method returns an instance of NSString with a +1 retain count kindcontrol edges start - line746 + line762 col3 file0 - line746 + line762 col4 file0 end - line747 + line763 col3 file0 - line747 + line763 col3 file0 kindevent location - line747 + line763 col3 file0 ranges - line747 + line763 col3 file0 - line747 + line763 col15 file0 - line747 + line763 col4 file0 - line747 + line763 col6 file0 depth0 extended_message Object released by directly sending the '-dealloc' message message Object released by directly sending the '-dealloc' message kindcontrol edges start - line747 + line763 col3 file0 - line747 + line763 col3 file0 end - line748 + line764 col3 file0 - line748 + line764 col3 file0 kindevent location - line748 + line764 col3 file0 ranges - line748 + line764 col4 file0 - line748 + line764 col6 file0 depth0 extended_message Reference-counted object is used after it is released message Reference-counted object is used after it is released descriptionReference-counted object is used after it is released categoryMemory (Core Foundation/Objective-C/OSObject) typeUse-after-release check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context83c7891609f8efb616060d0c6ae6bb43 issue_context_kindfunction issue_contextpr3820_ReleaseAfterDealloc issue_hash_function_offset3 location - line748 + line764 col3 file0 ExecutedLines 0 - 744 - 745 - 746 - 747 - 748 + 760 + 761 + 762 + 763 + 764 path kindcontrol edges start - line754 + line770 col3 file0 - line754 + line770 col7 file0 end - line755 + line771 col3 file0 - line755 + line771 col4 file0 kindevent location - line755 + line771 col12 file0 ranges - line755 + line771 col12 file0 - line755 + line771 col34 file0 depth0 extended_message Method returns an instance of NSString with a +1 retain count message Method returns an instance of NSString with a +1 retain count kindcontrol edges start - line755 + line771 col3 file0 - line755 + line771 col4 file0 end - line756 + line772 col3 file0 - line756 + line772 col3 file0 kindevent location - line756 + line772 col3 file0 ranges - line756 + line772 col3 file0 - line756 + line772 col15 file0 - line756 + line772 col4 file0 - line756 + line772 col6 file0 depth0 extended_message Object released message Object released kindcontrol edges start - line756 + line772 col3 file0 - line756 + line772 col3 file0 end - line757 + line773 col3 file0 - line757 + line773 col3 file0 kindevent location - line757 + line773 col3 file0 ranges - line757 + line773 col4 file0 - line757 + line773 col6 file0 depth0 extended_message Reference-counted object is used after it is released message Reference-counted object is used after it is released descriptionReference-counted object is used after it is released categoryMemory (Core Foundation/Objective-C/OSObject) typeUse-after-release check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context9fe338c720f25b3b1d5a68930d3ae4b8 issue_context_kindfunction issue_contextpr3820_DeallocAfterRelease issue_hash_function_offset4 location - line757 + line773 col3 file0 ExecutedLines 0 - 752 - 753 - 754 - 755 - 756 - 757 + 768 + 769 + 770 + 771 + 772 + 773 path kindcontrol edges start - line809 + line825 col2 file0 - line809 + line825 col20 file0 end - line809 + line825 col31 file0 - line809 + line825 col31 file0 kindevent location - line809 + line825 col31 file0 ranges - line809 + line825 col31 file0 - line809 + line825 col76 file0 depth0 extended_message Method returns an Objective-C object with a +0 retain count message Method returns an Objective-C object with a +0 retain count kindevent location - line809 + line825 col30 file0 ranges - line809 + line825 col30 file0 - line809 + line825 col84 file0 - line809 + line825 col31 file0 - line809 + line825 col76 file0 depth0 extended_message Reference count incremented. The object now has a +1 retain count message Reference count incremented. The object now has a +1 retain count kindcontrol edges start - line809 + line825 col30 file0 - line809 + line825 col30 file0 end - line809 + line825 col2 file0 - line809 + line825 col20 file0 kindcontrol edges start - line809 + line825 col2 file0 - line809 + line825 col20 file0 end - line813 + line829 col2 file0 - line813 + line829 col6 file0 kindcontrol edges start - line813 + line829 col2 file0 - line813 + line829 col6 file0 end - line814 + line830 col1 file0 - line814 + line830 col1 file0 kindevent location - line814 + line830 col1 file0 depth0 extended_message Object leaked: object allocated and stored into 'dict' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'dict' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'dict' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_contextdf3400f53fc437aede21f685ca1955d4 issue_context_kindObjective-C method issue_contextapplicationDidFinishLaunching: issue_hash_function_offset1 location - line814 + line830 col1 file0 ExecutedLines 0 - 808 - 809 - 811 - 813 - 814 + 824 + 825 + 827 + 829 + 830 path kindcontrol edges start - line821 + line837 col2 file0 - line821 + line837 col20 file0 end - line821 + line837 col31 file0 - line821 + line837 col31 file0 kindevent location - line821 + line837 col31 file0 ranges - line821 + line837 col31 file0 - line821 + line837 col76 file0 depth0 extended_message Method returns an Objective-C object with a +0 retain count message Method returns an Objective-C object with a +0 retain count kindevent location - line821 + line837 col30 file0 ranges - line821 + line837 col30 file0 - line821 + line837 col84 file0 - line821 + line837 col31 file0 - line821 + line837 col76 file0 depth0 extended_message Reference count incremented. The object now has a +1 retain count message Reference count incremented. The object now has a +1 retain count kindcontrol edges start - line821 + line837 col30 file0 - line821 + line837 col30 file0 end - line821 + line837 col2 file0 - line821 + line837 col20 file0 kindcontrol edges start - line821 + line837 col2 file0 - line821 + line837 col20 file0 end - line822 + line838 col2 file0 - line822 + line838 col3 file0 kindcontrol edges start - line822 + line838 col2 file0 - line822 + line838 col3 file0 end - line822 + line838 col6 file0 - line822 + line838 col11 file0 kindevent location - line822 + line838 col6 file0 ranges - line822 + line838 col6 file0 - line822 + line838 col11 file0 depth0 extended_message Assuming the condition is false message Assuming the condition is false kindcontrol edges start - line822 + line838 col6 file0 - line822 + line838 col11 file0 end - line824 + line840 col1 file0 - line824 + line840 col1 file0 kindevent location - line824 + line840 col1 file0 depth0 extended_message Object leaked: object allocated and stored into 'dict' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'dict' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'dict' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context5104ca579763af0f8c66da3fdc42b95f issue_context_kindObjective-C method issue_contextradar10102244 issue_hash_function_offset1 location - line824 + line840 col1 file0 ExecutedLines 0 - 820 - 821 - 822 - 824 + 836 + 837 + 838 + 840 path kindcontrol edges start - line832 + line848 col3 file0 - line832 + line848 col19 file0 end - line833 + line849 col3 file0 - line833 + line849 col9 file0 kindevent location - line833 + line849 col20 file0 ranges - line833 + line849 col20 file0 - line833 + line849 col34 file0 depth0 extended_message Method returns an Objective-C object with a +0 retain count message Method returns an Objective-C object with a +0 retain count kindcontrol edges start - line833 + line849 col3 file0 - line833 + line849 col9 file0 end - line834 + line850 col3 file0 - line834 + line850 col3 file0 kindevent location - line834 + line850 col3 file0 ranges - line834 + line850 col4 file0 - line834 + line850 col8 file0 depth0 extended_message Incorrect decrement of the reference count of an object that is not owned at this point by the caller message Incorrect decrement of the reference count of an object that is not owned at this point by the caller descriptionIncorrect decrement of the reference count of an object that is not owned at this point by the caller categoryMemory (Core Foundation/Objective-C/OSObject) typeBad release check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_contexta4a85a3991cb3888217d5c62346107dc issue_context_kindfunction issue_contextrdar_6257780_Case1 issue_hash_function_offset3 location - line834 + line850 col3 file0 ExecutedLines 0 - 831 - 832 - 833 - 834 + 847 + 848 + 849 + 850 path kindcontrol edges start - line909 + line925 col3 file0 - line909 + line925 col3 file0 end - line910 + line926 col3 file0 - line910 + line926 col3 file0 kindevent location - line910 + line926 col3 file0 ranges - line910 + line926 col3 file0 - line910 + line926 col36 file0 depth0 extended_message Method returns an instance of RDar6320065Subclass with a +1 retain count message Method returns an instance of RDar6320065Subclass with a +1 retain count kindcontrol edges start - line910 + line926 col3 file0 - line910 + line926 col3 file0 end - line911 + line927 col3 file0 - line911 + line927 col8 file0 kindevent location - line911 + line927 col3 file0 ranges - line911 + line927 col3 file0 - line911 + line927 col13 file0 depth0 extended_message Object leaked: allocated object of type 'RDar6320065Subclass *' is not referenced later in this execution path and has a retain count of +1 message Object leaked: allocated object of type 'RDar6320065Subclass *' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object of type 'RDar6320065Subclass *' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context75b7ad344b1d4665d918188bd10429df issue_context_kindObjective-C method issue_context_initReturningNewClassBad issue_hash_function_offset2 location - line911 + line927 col3 file0 ExecutedLines 0 - 908 - 909 - 910 - 911 + 924 + 925 + 926 + 927 path kindcontrol edges start - line914 + line930 col3 file0 - line914 + line930 col3 file0 end - line915 + line931 col3 file0 - line915 + line931 col6 file0 kindevent location - line915 + line931 col10 file0 ranges - line915 + line931 col10 file0 - line915 + line931 col43 file0 depth0 extended_message Method returns an instance of RDar6320065Subclass with a +1 retain count message Method returns an instance of RDar6320065Subclass with a +1 retain count kindcontrol edges start - line915 + line931 col3 file0 - line915 + line931 col6 file0 end - line916 + line932 col3 file0 - line916 + line932 col8 file0 kindevent location - line916 + line932 col10 file0 ranges - line916 + line932 col10 file0 - line916 + line932 col27 file0 - line916 + line932 col11 file0 - line916 + line932 col14 file0 depth0 extended_message Object autoreleased message Object autoreleased kindevent location - line916 + line932 col3 file0 ranges - line916 + line932 col3 file0 - line916 + line932 col27 file0 depth0 extended_message Object with a +0 retain count returned to caller where a +1 (owning) retain count is expected message Object with a +0 retain count returned to caller where a +1 (owning) retain count is expected descriptionObject with a +0 retain count returned to caller where a +1 (owning) retain count is expected categoryMemory (Core Foundation/Objective-C/OSObject) typeMethod should return an owned object check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context791e285d27d610c4c016065dd5addd37 issue_context_kindObjective-C method issue_contextinitReturningNewClassBad2 issue_hash_function_offset3 location - line916 + line932 col3 file0 ExecutedLines 0 - 913 - 914 - 915 - 916 + 929 + 930 + 931 + 932 path kindevent location - line954 + line970 col37 file0 ranges - line954 + line970 col37 file0 - line954 + line970 col59 file0 depth0 extended_message Method returns an instance of NSString with a +1 retain count message Method returns an instance of NSString with a +1 retain count kindevent location - line954 + line970 col30 file0 ranges - line954 + line970 col30 file0 - line954 + line970 col59 file0 depth0 extended_message Object leaked: allocated object of type 'NSString *' is returned from a method whose name ('NoCopyString') does not start with 'copy', 'mutableCopy', 'alloc' or 'new'. This violates the naming convention rules given in the Memory Management Guide for Cocoa message Object leaked: allocated object of type 'NSString *' is returned from a method whose name ('NoCopyString') does not start with 'copy', 'mutableCopy', 'alloc' or 'new'. This violates the naming convention rules given in the Memory Management Guide for Cocoa descriptionPotential leak of an object of type 'NSString *' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak of returned object check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context58cf9e4228ab9cbe375ddf37d04d45f1 issue_context_kindObjective-C method issue_contextNoCopyString issue_hash_function_offset0 location - line954 + line970 col30 file0 ExecutedLines 0 - 954 + 970 path kindevent location - line955 + line971 col37 file0 ranges - line955 + line971 col37 file0 - line955 + line971 col59 file0 depth0 extended_message Method returns an instance of NSString with a +1 retain count message Method returns an instance of NSString with a +1 retain count kindevent location - line955 + line971 col30 file0 ranges - line955 + line971 col30 file0 - line955 + line971 col59 file0 depth0 extended_message Object leaked: allocated object of type 'NSString *' is returned from a method whose name ('noCopyString') does not start with 'copy', 'mutableCopy', 'alloc' or 'new'. This violates the naming convention rules given in the Memory Management Guide for Cocoa message Object leaked: allocated object of type 'NSString *' is returned from a method whose name ('noCopyString') does not start with 'copy', 'mutableCopy', 'alloc' or 'new'. This violates the naming convention rules given in the Memory Management Guide for Cocoa descriptionPotential leak of an object of type 'NSString *' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak of returned object check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_contexte1b0176b31382e7e75129dd78883c91b issue_context_kindObjective-C method issue_contextnoCopyString issue_hash_function_offset0 location - line955 + line971 col30 file0 ExecutedLines 0 - 955 + 971 path kindevent location - line959 + line975 col3 file0 ranges - line959 + line975 col3 file0 - line959 + line975 col18 file0 depth0 extended_message Calling 'NoCopyString' message Calling 'NoCopyString' kindevent location - line954 + line970 col1 file0 depth1 extended_message Entered call from 'test_RDar6859457' message Entered call from 'test_RDar6859457' kindcontrol edges start - line954 + line970 col1 file0 - line954 + line970 col1 file0 end - line954 + line970 col30 file0 - line954 + line970 col35 file0 kindevent location - line954 + line970 col37 file0 ranges - line954 + line970 col37 file0 - line954 + line970 col59 file0 depth1 extended_message Method returns an instance of NSString with a +1 retain count message Method returns an instance of NSString with a +1 retain count kindevent location - line959 + line975 col3 file0 ranges - line959 + line975 col3 file0 - line959 + line975 col18 file0 depth0 extended_message Returning from 'NoCopyString' message Returning from 'NoCopyString' kindcontrol edges start - line959 + line975 col3 file0 - line959 + line975 col3 file0 end - line960 + line976 col3 file0 - line960 + line976 col3 file0 kindevent location - line960 + line976 col3 file0 ranges - line960 + line976 col3 file0 - line960 + line976 col18 file0 depth0 extended_message Object leaked: allocated object of type 'NSString *' is not referenced later in this execution path and has a retain count of +1 message Object leaked: allocated object of type 'NSString *' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object of type 'NSString *' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context5ff4d17e82026ccd84121b0a361fc135 issue_context_kindfunction issue_contexttest_RDar6859457 issue_hash_function_offset1 location - line960 + line976 col3 file0 ExecutedLines 0 - 954 - 958 - 959 - 960 + 970 + 974 + 975 + 976 path kindcontrol edges start - line959 + line975 col3 file0 - line959 + line975 col3 file0 end - line960 + line976 col3 file0 - line960 + line976 col3 file0 kindevent location - line960 + line976 col3 file0 ranges - line960 + line976 col3 file0 - line960 + line976 col18 file0 depth0 extended_message Calling 'noCopyString' message Calling 'noCopyString' kindevent location - line955 + line971 col1 file0 depth1 extended_message Entered call from 'test_RDar6859457' message Entered call from 'test_RDar6859457' kindcontrol edges start - line955 + line971 col1 file0 - line955 + line971 col1 file0 end - line955 + line971 col30 file0 - line955 + line971 col35 file0 kindevent location - line955 + line971 col37 file0 ranges - line955 + line971 col37 file0 - line955 + line971 col59 file0 depth1 extended_message Method returns an instance of NSString with a +1 retain count message Method returns an instance of NSString with a +1 retain count kindevent location - line960 + line976 col3 file0 ranges - line960 + line976 col3 file0 - line960 + line976 col18 file0 depth0 extended_message Returning from 'noCopyString' message Returning from 'noCopyString' kindcontrol edges start - line960 + line976 col3 file0 - line960 + line976 col3 file0 end - line961 + line977 col3 file0 - line961 + line977 col3 file0 kindevent location - line961 + line977 col3 file0 ranges - line961 + line977 col3 file0 - line961 + line977 col54 file0 depth0 extended_message Object leaked: allocated object of type 'NSString *' is not referenced later in this execution path and has a retain count of +1 message Object leaked: allocated object of type 'NSString *' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object of type 'NSString *' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context964683651b544d6c1cce0c4ae6961936 issue_context_kindfunction issue_contexttest_RDar6859457 issue_hash_function_offset2 location - line961 + line977 col3 file0 ExecutedLines 0 - 954 - 955 - 958 - 959 - 960 - 961 + 970 + 971 + 974 + 975 + 976 + 977 path kindevent location - line994 + line1010 col10 file0 ranges - line994 + line1010 col10 file0 - line994 + line1010 col32 file0 depth0 extended_message Method returns an instance of NSString with a +1 retain count message Method returns an instance of NSString with a +1 retain count kindevent location - line994 + line1010 col3 file0 ranges - line994 + line1010 col3 file0 - line994 + line1010 col32 file0 depth0 extended_message Object leaked: allocated object of type 'NSString *' is returned from a method whose name (':') does not start with 'copy', 'mutableCopy', 'alloc' or 'new'. This violates the naming convention rules given in the Memory Management Guide for Cocoa message Object leaked: allocated object of type 'NSString *' is returned from a method whose name (':') does not start with 'copy', 'mutableCopy', 'alloc' or 'new'. This violates the naming convention rules given in the Memory Management Guide for Cocoa descriptionPotential leak of an object of type 'NSString *' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak of returned object check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_contextca046c4c96c27a0e8c84dd707563bba9 issue_context_kindObjective-C method issue_context: issue_hash_function_offset1 location - line994 + line1010 col3 file0 ExecutedLines 0 - 993 - 994 + 1009 + 1010 path kindevent location - line1024 + line1040 col3 file0 ranges - line1024 + line1040 col3 file0 - line1024 + line1040 col38 file0 depth0 extended_message Method returns an Objective-C object with a +1 retain count message Method returns an Objective-C object with a +1 retain count kindcontrol edges start - line1024 + line1040 col3 file0 - line1024 + line1040 col3 file0 end - line1025 + line1041 col3 file0 - line1025 + line1041 col3 file0 kindevent location - line1025 + line1041 col3 file0 ranges - line1025 + line1041 col3 file0 - line1025 + line1041 col42 file0 depth0 extended_message Object leaked: allocated object of type 'id' is not referenced later in this execution path and has a retain count of +1 message Object leaked: allocated object of type 'id' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object of type 'id' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context12515c1f2d3343496d32a54ef376347d issue_context_kindfunction issue_contextrdar6902710 issue_hash_function_offset1 location - line1025 + line1041 col3 file0 ExecutedLines 0 - 1021 - 1022 - 1023 - 1024 - 1025 + 1037 + 1038 + 1039 + 1040 + 1041 path kindcontrol edges start - line1024 + line1040 col3 file0 - line1024 + line1040 col3 file0 end - line1025 + line1041 col3 file0 - line1025 + line1041 col3 file0 kindevent location - line1025 + line1041 col3 file0 ranges - line1025 + line1041 col3 file0 - line1025 + line1041 col42 file0 depth0 extended_message Method returns an Objective-C object with a +1 retain count message Method returns an Objective-C object with a +1 retain count kindcontrol edges start - line1025 + line1041 col3 file0 - line1025 + line1041 col3 file0 end - line1026 + line1042 col3 file0 - line1026 + line1042 col3 file0 kindevent location - line1026 + line1042 col3 file0 ranges - line1026 + line1042 col3 file0 - line1026 + line1042 col43 file0 depth0 extended_message Object leaked: allocated object of type 'id' is not referenced later in this execution path and has a retain count of +1 message Object leaked: allocated object of type 'id' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object of type 'id' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_contexte10d7d441805b9f66c118bfeccf32f29 issue_context_kindfunction issue_contextrdar6902710 issue_hash_function_offset2 location - line1026 + line1042 col3 file0 ExecutedLines 0 - 1021 - 1022 - 1023 - 1024 - 1025 - 1026 + 1037 + 1038 + 1039 + 1040 + 1041 + 1042 path kindcontrol edges start - line1024 + line1040 col3 file0 - line1024 + line1040 col3 file0 end - line1026 + line1042 col3 file0 - line1026 + line1042 col3 file0 kindevent location - line1026 + line1042 col3 file0 ranges - line1026 + line1042 col3 file0 - line1026 + line1042 col43 file0 depth0 extended_message Method returns a Core Foundation object of type 'CGImageRef' with a +1 retain count message Method returns a Core Foundation object of type 'CGImageRef' with a +1 retain count kindcontrol edges start - line1026 + line1042 col3 file0 - line1026 + line1042 col3 file0 end - line1027 + line1043 col3 file0 - line1027 + line1043 col3 file0 kindevent location - line1027 + line1043 col3 file0 ranges - line1027 + line1043 col3 file0 - line1027 + line1043 col69 file0 depth0 extended_message Object leaked: allocated object of type 'CGImageRef' is not referenced later in this execution path and has a retain count of +1 message Object leaked: allocated object of type 'CGImageRef' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object of type 'CGImageRef' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context3ae54947ad02e14773ac126982de301d issue_context_kindfunction issue_contextrdar6902710 issue_hash_function_offset3 location - line1027 + line1043 col3 file0 ExecutedLines 0 - 1021 - 1022 - 1023 - 1024 - 1025 - 1026 - 1027 + 1037 + 1038 + 1039 + 1040 + 1041 + 1042 + 1043 path kindcontrol edges start - line1024 + line1040 col3 file0 - line1024 + line1040 col3 file0 end - line1027 + line1043 col3 file0 - line1027 + line1043 col3 file0 kindevent location - line1027 + line1043 col3 file0 ranges - line1027 + line1043 col3 file0 - line1027 + line1043 col69 file0 depth0 extended_message Method returns a Core Foundation object of type 'CGImageRef' with a +1 retain count message Method returns a Core Foundation object of type 'CGImageRef' with a +1 retain count kindcontrol edges start - line1027 + line1043 col3 file0 - line1027 + line1043 col3 file0 end - line1028 + line1044 col1 file0 - line1028 + line1044 col1 file0 kindevent location - line1028 + line1044 col1 file0 depth0 extended_message Object leaked: allocated object of type 'CGImageRef' is not referenced later in this execution path and has a retain count of +1 message Object leaked: allocated object of type 'CGImageRef' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object of type 'CGImageRef' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context6dba0d2672617f7eb2c512129fb17bb3 issue_context_kindfunction issue_contextrdar6902710 issue_hash_function_offset4 location - line1028 + line1044 col1 file0 ExecutedLines 0 - 1021 - 1022 - 1023 - 1024 - 1025 - 1026 - 1027 - 1028 + 1037 + 1038 + 1039 + 1040 + 1041 + 1042 + 1043 + 1044 path kindevent location - line1036 + line1052 col3 file0 ranges - line1036 + line1052 col3 file0 - line1036 + line1052 col45 file0 depth0 extended_message Method returns a Core Foundation object of type 'CGLayerRef' with a +1 retain count message Method returns a Core Foundation object of type 'CGLayerRef' with a +1 retain count kindcontrol edges start - line1036 + line1052 col3 file0 - line1036 + line1052 col3 file0 end - line1037 + line1053 col1 file0 - line1037 + line1053 col1 file0 kindevent location - line1037 + line1053 col1 file0 depth0 extended_message Object leaked: allocated object of type 'CGLayerRef' is not referenced later in this execution path and has a retain count of +1 message Object leaked: allocated object of type 'CGLayerRef' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object of type 'CGLayerRef' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_contextb065641c4257dac33ff15b08859d09e2 issue_context_kindfunction issue_contextrdar6945561 issue_hash_function_offset1 location - line1037 + line1053 col1 file0 ExecutedLines 0 - 1035 - 1036 - 1037 + 1051 + 1052 + 1053 path kindevent location - line1045 + line1061 col3 file0 ranges - line1045 + line1061 col3 file0 - line1045 + line1061 col49 file0 depth0 extended_message Call to function 'IOBSDNameMatching' returns a Core Foundation object of type 'CFMutableDictionaryRef' with a +1 retain count message Call to function 'IOBSDNameMatching' returns a Core Foundation object of type 'CFMutableDictionaryRef' with a +1 retain count kindcontrol edges start - line1045 + line1061 col3 file0 - line1045 + line1061 col19 file0 end - line1046 + line1062 col1 file0 - line1046 + line1062 col1 file0 kindevent location - line1046 + line1062 col1 file0 depth0 extended_message Object leaked: allocated object of type 'CFMutableDictionaryRef' is not referenced later in this execution path and has a retain count of +1 message Object leaked: allocated object of type 'CFMutableDictionaryRef' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object of type 'CFMutableDictionaryRef' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context7cbb4f547b5c1fb1a456ecc47f27d853 issue_context_kindfunction issue_contextIOBSDNameMatching_wrapper issue_hash_function_offset1 location - line1046 + line1062 col1 file0 ExecutedLines 0 - 1044 - 1045 - 1046 + 1060 + 1061 + 1062 path kindevent location - line1049 + line1065 col3 file0 ranges - line1049 + line1065 col3 file0 - line1049 + line1065 col25 file0 depth0 extended_message Call to function 'IOServiceMatching' returns a Core Foundation object of type 'CFMutableDictionaryRef' with a +1 retain count message Call to function 'IOServiceMatching' returns a Core Foundation object of type 'CFMutableDictionaryRef' with a +1 retain count kindcontrol edges start - line1049 + line1065 col3 file0 - line1049 + line1065 col19 file0 end - line1050 + line1066 col1 file0 - line1050 + line1066 col1 file0 kindevent location - line1050 + line1066 col1 file0 depth0 extended_message Object leaked: allocated object of type 'CFMutableDictionaryRef' is not referenced later in this execution path and has a retain count of +1 message Object leaked: allocated object of type 'CFMutableDictionaryRef' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object of type 'CFMutableDictionaryRef' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context0b329ce97e1baf94f89590888a4af794 issue_context_kindfunction issue_contextIOServiceMatching_wrapper issue_hash_function_offset1 location - line1050 + line1066 col1 file0 ExecutedLines 0 - 1048 - 1049 - 1050 + 1064 + 1065 + 1066 path kindevent location - line1053 + line1069 col3 file0 ranges - line1053 + line1069 col3 file0 - line1053 + line1069 col29 file0 depth0 extended_message Call to function 'IOServiceNameMatching' returns a Core Foundation object of type 'CFMutableDictionaryRef' with a +1 retain count message Call to function 'IOServiceNameMatching' returns a Core Foundation object of type 'CFMutableDictionaryRef' with a +1 retain count kindcontrol edges start - line1053 + line1069 col3 file0 - line1053 + line1069 col23 file0 end - line1054 + line1070 col1 file0 - line1054 + line1070 col1 file0 kindevent location - line1054 + line1070 col1 file0 depth0 extended_message Object leaked: allocated object of type 'CFMutableDictionaryRef' is not referenced later in this execution path and has a retain count of +1 message Object leaked: allocated object of type 'CFMutableDictionaryRef' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object of type 'CFMutableDictionaryRef' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_contexte207241fbe4666cffeeca3f47966425f issue_context_kindfunction issue_contextIOServiceNameMatching_wrapper issue_hash_function_offset1 location - line1054 + line1070 col1 file0 ExecutedLines 0 - 1052 - 1053 - 1054 + 1068 + 1069 + 1070 path kindevent location - line1061 + line1077 col30 file0 ranges - line1061 + line1077 col30 file0 - line1061 + line1077 col41 file0 depth0 extended_message Call to function 'CreateDict' returns a Core Foundation object of type 'CFDictionaryRef' with a +1 retain count message Call to function 'CreateDict' returns a Core Foundation object of type 'CFDictionaryRef' with a +1 retain count kindcontrol edges start - line1061 + line1077 col3 file0 - line1061 + line1077 col17 file0 end - line1062 + line1078 col3 file0 - line1062 + line1078 col11 file0 kindevent location - line1062 + line1078 col3 file0 ranges - line1062 + line1078 col3 file0 - line1062 + line1078 col21 file0 - line1062 + line1078 col13 file0 - line1062 + line1078 col20 file0 depth0 extended_message Object released message Object released kindcontrol edges start - line1062 + line1078 col3 file0 - line1062 + line1078 col11 file0 end - line1063 + line1079 col3 file0 - line1063 + line1079 col26 file0 kindevent location - line1063 + line1079 col3 file0 ranges - line1063 + line1079 col58 file0 - line1063 + line1079 col65 file0 depth0 extended_message Reference-counted object is used after it is released message Reference-counted object is used after it is released descriptionReference-counted object is used after it is released categoryMemory (Core Foundation/Objective-C/OSObject) typeUse-after-release check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_contextae61d11111bc6c9f049a5ca8935b7bae issue_context_kindfunction issue_contextIOServiceAddNotification_wrapper issue_hash_function_offset4 location - line1063 + line1079 col3 file0 ExecutedLines 0 - 1058 - 1059 - 1061 - 1062 - 1063 - 1064 + 1074 + 1075 + 1077 + 1078 + 1079 + 1080 path kindevent location - line1068 + line1084 col3 file0 ranges - line1068 + line1084 col3 file0 - line1068 + line1084 col36 file0 depth0 extended_message Call to function 'IORegistryEntryIDMatching' returns a Core Foundation object of type 'CFMutableDictionaryRef' with a +1 retain count message Call to function 'IORegistryEntryIDMatching' returns a Core Foundation object of type 'CFMutableDictionaryRef' with a +1 retain count kindcontrol edges start - line1068 + line1084 col3 file0 - line1068 + line1084 col27 file0 end - line1069 + line1085 col1 file0 - line1069 + line1085 col1 file0 kindevent location - line1069 + line1085 col1 file0 depth0 extended_message Object leaked: allocated object of type 'CFMutableDictionaryRef' is not referenced later in this execution path and has a retain count of +1 message Object leaked: allocated object of type 'CFMutableDictionaryRef' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object of type 'CFMutableDictionaryRef' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context62fc802833a96d44d2fa008826c46c64 issue_context_kindfunction issue_contextIORegistryEntryIDMatching_wrapper issue_hash_function_offset1 location - line1069 + line1085 col1 file0 ExecutedLines 0 - 1067 - 1068 - 1069 + 1083 + 1084 + 1085 path kindevent location - line1073 + line1089 col3 file0 ranges - line1073 + line1089 col3 file0 - line1073 + line1089 col55 file0 depth0 extended_message Call to function 'IOOpenFirmwarePathMatching' returns a Core Foundation object of type 'CFMutableDictionaryRef' with a +1 retain count message Call to function 'IOOpenFirmwarePathMatching' returns a Core Foundation object of type 'CFMutableDictionaryRef' with a +1 retain count kindcontrol edges start - line1073 + line1089 col3 file0 - line1073 + line1089 col28 file0 end - line1074 + line1090 col1 file0 - line1074 + line1090 col1 file0 kindevent location - line1074 + line1090 col1 file0 depth0 extended_message Object leaked: allocated object of type 'CFMutableDictionaryRef' is not referenced later in this execution path and has a retain count of +1 message Object leaked: allocated object of type 'CFMutableDictionaryRef' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object of type 'CFMutableDictionaryRef' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context644a1e5f3d844a5d9b140de26e6e5645 issue_context_kindfunction issue_contextIOOpenFirmwarePathMatching_wrapper issue_hash_function_offset1 location - line1074 + line1090 col1 file0 ExecutedLines 0 - 1071 - 1072 - 1073 - 1074 + 1087 + 1088 + 1089 + 1090 path kindevent location - line1077 + line1093 col30 file0 ranges - line1077 + line1093 col30 file0 - line1077 + line1093 col41 file0 depth0 extended_message Call to function 'CreateDict' returns a Core Foundation object of type 'CFDictionaryRef' with a +1 retain count message Call to function 'CreateDict' returns a Core Foundation object of type 'CFDictionaryRef' with a +1 retain count kindcontrol edges start - line1077 + line1093 col3 file0 - line1077 + line1093 col17 file0 end - line1078 + line1094 col3 file0 - line1078 + line1094 col29 file0 kindevent location - line1078 + line1094 col3 file0 ranges - line1078 + line1094 col3 file0 - line1078 + line1094 col51 file0 - line1078 + line1094 col43 file0 - line1078 + line1094 col50 file0 depth0 extended_message Object released message Object released kindcontrol edges start - line1078 + line1094 col3 file0 - line1078 + line1094 col29 file0 end - line1079 + line1095 col3 file0 - line1079 + line1095 col11 file0 kindevent location - line1079 + line1095 col3 file0 ranges - line1079 + line1095 col13 file0 - line1079 + line1095 col20 file0 depth0 extended_message Reference-counted object is used after it is released message Reference-counted object is used after it is released descriptionReference-counted object is used after it is released categoryMemory (Core Foundation/Objective-C/OSObject) typeUse-after-release check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context904a99d378144e5aa011649cec493695 issue_context_kindfunction issue_contextIOServiceGetMatchingService_wrapper issue_hash_function_offset3 location - line1079 + line1095 col3 file0 ExecutedLines 0 - 1076 - 1077 - 1078 - 1079 + 1092 + 1093 + 1094 + 1095 path kindevent location - line1083 + line1099 col30 file0 ranges - line1083 + line1099 col30 file0 - line1083 + line1099 col41 file0 depth0 extended_message Call to function 'CreateDict' returns a Core Foundation object of type 'CFDictionaryRef' with a +1 retain count message Call to function 'CreateDict' returns a Core Foundation object of type 'CFDictionaryRef' with a +1 retain count kindcontrol edges start - line1083 + line1099 col3 file0 - line1083 + line1099 col17 file0 end - line1084 + line1100 col3 file0 - line1084 + line1100 col30 file0 kindevent location - line1084 + line1100 col3 file0 ranges - line1084 + line1100 col3 file0 - line1084 + line1100 col62 file0 - line1084 + line1100 col44 file0 - line1084 + line1100 col51 file0 depth0 extended_message Object released message Object released kindcontrol edges start - line1084 + line1100 col3 file0 - line1084 + line1100 col30 file0 end - line1085 + line1101 col3 file0 - line1085 + line1101 col11 file0 kindevent location - line1085 + line1101 col3 file0 ranges - line1085 + line1101 col13 file0 - line1085 + line1101 col20 file0 depth0 extended_message Reference-counted object is used after it is released message Reference-counted object is used after it is released descriptionReference-counted object is used after it is released categoryMemory (Core Foundation/Objective-C/OSObject) typeUse-after-release check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context23c94c459003beb49ea078f75a86ccc5 issue_context_kindfunction issue_contextIOServiceGetMatchingServices_wrapper issue_hash_function_offset3 location - line1085 + line1101 col3 file0 ExecutedLines 0 - 1082 - 1083 - 1084 - 1085 + 1098 + 1099 + 1100 + 1101 path kindevent location - line1091 + line1107 col30 file0 ranges - line1091 + line1107 col30 file0 - line1091 + line1107 col41 file0 depth0 extended_message Call to function 'CreateDict' returns a Core Foundation object of type 'CFDictionaryRef' with a +1 retain count message Call to function 'CreateDict' returns a Core Foundation object of type 'CFDictionaryRef' with a +1 retain count kindcontrol edges start - line1091 + line1107 col3 file0 - line1091 + line1107 col17 file0 end - line1092 + line1108 col3 file0 - line1092 + line1108 col34 file0 kindevent location - line1092 + line1108 col3 file0 ranges - line1092 + line1108 col3 file0 - line1092 + line1108 col106 file0 - line1092 + line1108 col66 file0 - line1092 + line1108 col73 file0 depth0 extended_message Object released message Object released kindcontrol edges start - line1092 + line1108 col3 file0 - line1092 + line1108 col34 file0 end - line1093 + line1109 col3 file0 - line1093 + line1109 col11 file0 kindevent location - line1093 + line1109 col3 file0 ranges - line1093 + line1109 col13 file0 - line1093 + line1109 col20 file0 depth0 extended_message Reference-counted object is used after it is released message Reference-counted object is used after it is released descriptionReference-counted object is used after it is released categoryMemory (Core Foundation/Objective-C/OSObject) typeUse-after-release check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context06e6fa1f7f96818fbd619dfe8b210b0d issue_context_kindfunction issue_contextIOServiceAddMatchingNotification_wrapper issue_hash_function_offset4 location - line1093 + line1109 col3 file0 ExecutedLines 0 - 1088 - 1089 - 1091 - 1092 - 1093 + 1104 + 1105 + 1107 + 1108 + 1109 path kindcontrol edges start - line1131 + line1147 col3 file0 - line1131 + line1147 col23 file0 end - line1134 + line1150 col3 file0 - line1134 + line1150 col10 file0 kindevent location - line1134 + line1150 col22 file0 ranges - line1134 + line1150 col22 file0 - line1134 + line1150 col53 file0 depth0 extended_message Method returns an instance of NSNumber with a +1 retain count message Method returns an instance of NSNumber with a +1 retain count kindcontrol edges start - line1134 + line1150 col3 file0 - line1134 + line1150 col10 file0 end - line1136 + line1152 col3 file0 - line1136 + line1152 col3 file0 kindevent location - line1136 + line1152 col3 file0 ranges - line1136 + line1152 col3 file0 - line1136 + line1152 col18 file0 - line1136 + line1152 col4 file0 - line1136 + line1152 col9 file0 depth0 extended_message Reference count decremented message Reference count decremented kindcontrol edges start - line1136 + line1152 col3 file0 - line1136 + line1152 col3 file0 end - line1137 + line1153 col3 file0 - line1137 + line1153 col3 file0 kindevent location - line1137 + line1153 col3 file0 ranges - line1137 + line1153 col3 file0 - line1137 + line1153 col17 file0 - line1137 + line1153 col4 file0 - line1137 + line1153 col9 file0 depth0 extended_message Reference count incremented. The object now has a +1 retain count message Reference count incremented. The object now has a +1 retain count kindcontrol edges start - line1137 + line1153 col3 file0 - line1137 + line1153 col3 file0 end - line1138 + line1154 col3 file0 - line1138 + line1154 col11 file0 kindevent location - line1138 + line1154 col3 file0 ranges - line1138 + line1154 col3 file0 - line1138 + line1154 col23 file0 depth0 extended_message Object leaked: object allocated and stored into 'number' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'number' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'number' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context1692047c1a2ab283584ae01c84e3ae35 issue_context_kindfunction issue_contextrdar_7152619 issue_hash_function_offset4 location - line1138 + line1154 col3 file0 ExecutedLines 0 - 67 - 68 - 69 - 70 - 71 - 1130 - 1131 - 1132 - 1133 - 1134 - 1135 - 1136 - 1137 - 1138 + 74 + 75 + 76 + 77 + 78 + 1146 + 1147 + 1148 + 1149 + 1150 + 1151 + 1152 + 1153 + 1154 path kindcontrol edges start - line1147 + line1163 col3 file0 - line1147 + line1163 col8 file0 end - line1158 + line1174 col3 file0 - line1158 + line1174 col15 file0 kindcontrol edges start - line1158 + line1174 col3 file0 - line1158 + line1174 col15 file0 end - line1159 + line1175 col41 file0 - line1159 + line1175 col67 file0 kindevent location - line1159 + line1175 col41 file0 ranges - line1159 + line1175 col41 file0 - line1159 + line1175 col69 file0 depth0 extended_message Call to function 'CGColorSpaceCreateDeviceRGB' returns a Core Foundation object of type 'CGColorSpaceRef' with a +1 retain count message Call to function 'CGColorSpaceCreateDeviceRGB' returns a Core Foundation object of type 'CGColorSpaceRef' with a +1 retain count kindcontrol edges start - line1159 + line1175 col41 file0 - line1159 + line1175 col67 file0 end - line1158 + line1174 col3 file0 - line1158 + line1174 col15 file0 kindevent location - line1158 + line1174 col3 file0 ranges - line1158 + line1174 col3 file0 - line1158 + line1174 col26 file0 depth0 extended_message Object leaked: allocated object of type 'CGColorSpaceRef' is not referenced later in this execution path and has a retain count of +1 message Object leaked: allocated object of type 'CGColorSpaceRef' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object of type 'CGColorSpaceRef' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context17e5c3184216ca3aef86288dc1f41d8d issue_context_kindfunction issue_contextrdar_7184450 issue_hash_function_offset13 location - line1158 + line1174 col3 file0 ExecutedLines 0 - 1145 - 1146 - 1147 - 1148 - 1149 - 1150 - 1151 - 1152 - 1153 - 1154 - 1155 - 1158 - 1159 - 1160 + 1161 + 1162 + 1163 + 1164 + 1165 + 1166 + 1167 + 1168 + 1169 + 1170 + 1171 + 1174 + 1175 + 1176 path kindcontrol edges start - line1169 + line1185 col3 file0 - line1169 + line1185 col8 file0 end - line1180 + line1196 col3 file0 - line1180 + line1196 col15 file0 kindcontrol edges start - line1180 + line1196 col3 file0 - line1180 + line1196 col15 file0 end - line1181 + line1197 col40 file0 - line1181 + line1197 col66 file0 kindevent location - line1181 + line1197 col40 file0 ranges - line1181 + line1197 col40 file0 - line1181 + line1197 col68 file0 depth0 extended_message Call to function 'CGColorSpaceCreateDeviceRGB' returns a Core Foundation object of type 'CGColorSpaceRef' with a +1 retain count message Call to function 'CGColorSpaceCreateDeviceRGB' returns a Core Foundation object of type 'CGColorSpaceRef' with a +1 retain count kindcontrol edges start - line1181 + line1197 col40 file0 - line1181 + line1197 col66 file0 end - line1180 + line1196 col3 file0 - line1180 + line1196 col15 file0 kindevent location - line1180 + line1196 col3 file0 ranges - line1180 + line1196 col3 file0 - line1180 + line1196 col26 file0 depth0 extended_message Object leaked: allocated object of type 'CGColorSpaceRef' is not referenced later in this execution path and has a retain count of +1 message Object leaked: allocated object of type 'CGColorSpaceRef' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object of type 'CGColorSpaceRef' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_contextc2225660bdec84d2ae183eda303a1abb issue_context_kindfunction issue_contextrdar_7184450_pos issue_hash_function_offset13 location - line1180 + line1196 col3 file0 ExecutedLines 0 - 1167 - 1168 - 1169 - 1170 - 1171 - 1172 - 1173 - 1174 - 1175 - 1176 - 1177 - 1180 - 1181 + 1183 + 1184 + 1185 + 1186 + 1187 + 1188 + 1189 + 1190 + 1191 + 1192 + 1193 + 1196 + 1197 path kindcontrol edges start - line1169 + line1185 col3 file0 - line1169 + line1185 col8 file0 end - line1180 + line1196 col3 file0 - line1180 + line1196 col15 file0 kindcontrol edges start - line1180 + line1196 col3 file0 - line1180 + line1196 col15 file0 end - line1181 + line1197 col4 file0 - line1181 + line1197 col38 file0 kindevent location - line1181 + line1197 col4 file0 ranges - line1181 + line1197 col4 file0 - line1181 + line1197 col107 file0 depth0 extended_message Call to function 'CGGradientCreateWithColorComponents' returns a Core Foundation object of type 'CGGradientRef' with a +1 retain count message Call to function 'CGGradientCreateWithColorComponents' returns a Core Foundation object of type 'CGGradientRef' with a +1 retain count kindcontrol edges start - line1181 + line1197 col4 file0 - line1181 + line1197 col38 file0 end - line1183 + line1199 col3 file0 - line1183 + line1199 col29 file0 kindcontrol edges start - line1183 + line1199 col3 file0 - line1183 + line1199 col29 file0 end - line1185 + line1201 col1 file0 - line1185 + line1201 col1 file0 kindevent location - line1185 + line1201 col1 file0 depth0 extended_message Object leaked: object allocated and stored into 'myGradient' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'myGradient' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'myGradient' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context6415d6b7dd7d48a2ef27f4c4d0168c64 issue_context_kindfunction issue_contextrdar_7184450_pos issue_hash_function_offset13 location - line1185 + line1201 col1 file0 ExecutedLines 0 - 1167 - 1168 - 1169 - 1170 - 1171 - 1172 - 1173 - 1174 - 1175 - 1176 - 1177 - 1180 - 1181 1183 1184 1185 + 1186 + 1187 + 1188 + 1189 + 1190 + 1191 + 1192 + 1193 + 1196 + 1197 + 1199 + 1200 + 1201 path kindevent location - line1219 + line1235 col22 file0 ranges - line1219 + line1235 col22 file0 - line1219 + line1235 col53 file0 depth0 extended_message Method returns an instance of NSNumber with a +1 retain count message Method returns an instance of NSNumber with a +1 retain count kindcontrol edges start - line1219 + line1235 col3 file0 - line1219 + line1235 col10 file0 end - line1220 + line1236 col1 file0 - line1220 + line1236 col1 file0 kindevent location - line1220 + line1236 col1 file0 depth0 extended_message Object leaked: object allocated and stored into 'number' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'number' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'number' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context08a69979bb4fa932512da1327fbf3b23 issue_context_kindfunction issue_contextrdar_7299394_positive issue_hash_function_offset1 location - line1220 + line1236 col1 file0 ExecutedLines 0 - 1218 - 1219 - 1220 + 1234 + 1235 + 1236 path kindcontrol edges start - line1454 + line1470 col5 file0 - line1454 + line1470 col12 file0 end - line1456 + line1472 col3 file0 - line1456 + line1472 col31 file0 kindevent location - line1456 + line1472 col3 file0 ranges - line1456 + line1472 col3 file0 - line1457 + line1473 col60 file0 depth0 extended_message Call to function 'CGBitmapContextCreateWithData' returns a Core Foundation object of type 'CGContextRef' with a +1 retain count message Call to function 'CGBitmapContextCreateWithData' returns a Core Foundation object of type 'CGContextRef' with a +1 retain count kindcontrol edges start - line1456 + line1472 col3 file0 - line1456 + line1472 col31 file0 end - line1458 + line1474 col1 file0 - line1458 + line1474 col1 file0 kindevent location - line1458 + line1474 col1 file0 depth0 extended_message Object leaked: allocated object of type 'CGContextRef' is not referenced later in this execution path and has a retain count of +1 message Object leaked: allocated object of type 'CGContextRef' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object of type 'CGContextRef' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context32b76a1b35c681cad8093c7e79e36388 issue_context_kindfunction issue_contextrdar_7358899 issue_hash_function_offset7 location - line1458 + line1474 col1 file0 ExecutedLines 0 - 1446 - 1447 - 1448 - 1449 - 1454 - 1456 - 1457 - 1458 + 1462 + 1463 + 1464 + 1465 + 1470 + 1472 + 1473 + 1474 path kindevent location - line1474 + line1490 col10 file0 ranges - line1474 + line1490 col10 file0 - line1474 + line1490 col22 file0 depth0 extended_message Method returns an Objective-C object with a +1 retain count message Method returns an Objective-C object with a +1 retain count kindcontrol edges start - line1474 + line1490 col3 file0 - line1474 + line1490 col4 file0 end - line1475 + line1491 col1 file0 - line1475 + line1491 col1 file0 kindevent location - line1475 + line1491 col1 file0 depth0 extended_message Object leaked: object allocated and stored into 'y' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'y' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'y' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context7e6172f0b4b6af27712153519e1934e1 issue_context_kindfunction issue_contextrdar7265711_a issue_hash_function_offset1 location - line1475 + line1491 col1 file0 ExecutedLines 0 - 1473 - 1474 - 1475 + 1489 + 1490 + 1491 path kindcontrol edges start - line1494 + line1510 col3 file0 - line1494 + line1510 col10 file0 end - line1495 + line1511 col3 file0 - line1495 + line1511 col10 file0 kindevent location - line1495 + line1511 col22 file0 ranges - line1495 + line1511 col22 file0 - line1495 + line1511 col53 file0 depth0 extended_message Method returns an instance of NSNumber with a +1 retain count message Method returns an instance of NSNumber with a +1 retain count kindcontrol edges start - line1495 + line1511 col3 file0 - line1495 + line1511 col10 file0 end - line1496 + line1512 col1 file0 - line1496 + line1512 col1 file0 kindevent location - line1496 + line1512 col1 file0 depth0 extended_message Object leaked: object allocated and stored into 'number' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'number' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'number' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context5eb97f906bb3af4befe63c891484f791 issue_context_kindfunction issue_contextrdar7306898 issue_hash_function_offset4 location - line1496 + line1512 col1 file0 ExecutedLines 0 - 1491 - 1494 - 1495 - 1496 + 1507 + 1510 + 1511 + 1512 path kindevent location - line1505 + line1521 col3 file0 ranges - line1505 + line1521 col3 file0 - line1505 + line1521 col23 file0 depth0 extended_message The 'release' message should be sent to instances of class 'RDar7252064' and not the class directly message The 'release' message should be sent to instances of class 'RDar7252064' and not the class directly descriptionThe 'release' message should be sent to instances of class 'RDar7252064' and not the class directly categoryAPI Misuse (Apple) typemessage incorrectly sent to class instead of class instance check_nameosx.cocoa.ClassRelease issue_hash_content_of_line_in_contextbdc4aaf3d712232f4ae72dce230189f9 issue_context_kindfunction issue_contextrdar7252064 issue_hash_function_offset1 location - line1505 + line1521 col3 file0 ExecutedLines 0 - 1504 - 1505 + 1520 + 1521 path kindcontrol edges start - line1505 + line1521 col3 file0 - line1505 + line1521 col3 file0 end - line1506 + line1522 col3 file0 - line1506 + line1522 col3 file0 kindevent location - line1506 + line1522 col3 file0 ranges - line1506 + line1522 col3 file0 - line1506 + line1522 col22 file0 depth0 extended_message The 'retain' message should be sent to instances of class 'RDar7252064' and not the class directly message The 'retain' message should be sent to instances of class 'RDar7252064' and not the class directly descriptionThe 'retain' message should be sent to instances of class 'RDar7252064' and not the class directly categoryAPI Misuse (Apple) typemessage incorrectly sent to class instead of class instance check_nameosx.cocoa.ClassRelease issue_hash_content_of_line_in_contextb767178ef573c7bd520dc62faabc32fc issue_context_kindfunction issue_contextrdar7252064 issue_hash_function_offset2 location - line1506 + line1522 col3 file0 ExecutedLines 0 - 1504 - 1505 - 1506 + 1520 + 1521 + 1522 path kindcontrol edges start - line1505 + line1521 col3 file0 - line1505 + line1521 col3 file0 end - line1507 + line1523 col3 file0 - line1507 + line1523 col3 file0 kindevent location - line1507 + line1523 col3 file0 ranges - line1507 + line1523 col3 file0 - line1507 + line1523 col27 file0 depth0 extended_message The 'autorelease' message should be sent to instances of class 'RDar7252064' and not the class directly message The 'autorelease' message should be sent to instances of class 'RDar7252064' and not the class directly descriptionThe 'autorelease' message should be sent to instances of class 'RDar7252064' and not the class directly categoryAPI Misuse (Apple) typemessage incorrectly sent to class instead of class instance check_nameosx.cocoa.ClassRelease issue_hash_content_of_line_in_context3dbe304966f8bffa6bdefc5f3ada7df6 issue_context_kindfunction issue_contextrdar7252064 issue_hash_function_offset3 location - line1507 + line1523 col3 file0 ExecutedLines 0 - 1504 - 1505 - 1506 - 1507 + 1520 + 1521 + 1522 + 1523 path kindcontrol edges start - line1505 + line1521 col3 file0 - line1505 + line1521 col3 file0 end - line1508 + line1524 col3 file0 - line1508 + line1524 col3 file0 kindevent location - line1508 + line1524 col3 file0 ranges - line1508 + line1524 col3 file0 - line1508 + line1524 col27 file0 depth0 extended_message The 'drain' message should be sent to instances of class 'NSAutoreleasePool' and not the class directly message The 'drain' message should be sent to instances of class 'NSAutoreleasePool' and not the class directly descriptionThe 'drain' message should be sent to instances of class 'NSAutoreleasePool' and not the class directly categoryAPI Misuse (Apple) typemessage incorrectly sent to class instead of class instance check_nameosx.cocoa.ClassRelease issue_hash_content_of_line_in_contextc519bce30f1da4bb6e3ecc46453d6958 issue_context_kindfunction issue_contextrdar7252064 issue_hash_function_offset4 location - line1508 + line1524 col3 file0 ExecutedLines 0 - 1504 - 1505 - 1506 - 1507 - 1508 + 1520 + 1521 + 1522 + 1523 + 1524 path kindevent location - line1535 + line1551 col19 file0 ranges - line1535 + line1551 col19 file0 - line1535 + line1551 col42 file0 depth0 extended_message Method returns an instance of NSString with a +1 retain count message Method returns an instance of NSString with a +1 retain count kindcontrol edges start - line1535 + line1551 col3 file0 - line1535 + line1551 col10 file0 end - line1536 + line1552 col1 file0 - line1536 + line1552 col1 file0 kindevent location - line1536 + line1552 col1 file0 depth0 extended_message Object leaked: object allocated and stored into 'str' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'str' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'str' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context6b9b51ce7b68ca0ba6a85e8924601a96 issue_context_kindfunction issue_contexttest_attr_1 issue_hash_function_offset1 location - line1536 + line1552 col1 file0 ExecutedLines 0 - 1534 - 1535 - 1536 + 1550 + 1551 + 1552 path kindevent location - line1539 + line1555 col19 file0 ranges - line1539 + line1555 col19 file0 - line1539 + line1555 col44 file0 depth0 extended_message Method returns a Core Foundation object of type 'NSString *' with a +1 retain count message Method returns a Core Foundation object of type 'NSString *' with a +1 retain count kindcontrol edges start - line1539 + line1555 col3 file0 - line1539 + line1555 col10 file0 end - line1540 + line1556 col1 file0 - line1540 + line1556 col1 file0 kindevent location - line1540 + line1556 col1 file0 depth0 extended_message Object leaked: object allocated and stored into 'str' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'str' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'str' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_contexteb040d5ec198d092ec9894af4dce6af8 issue_context_kindfunction issue_contexttest_attr_1b issue_hash_function_offset1 location - line1540 + line1556 col1 file0 ExecutedLines 0 - 1538 - 1539 - 1540 + 1554 + 1555 + 1556 path kindcontrol edges start - line1543 + line1559 col3 file0 - line1543 + line1559 col10 file0 end - line1544 + line1560 col3 file0 - line1544 + line1560 col10 file0 kindevent location - line1544 + line1560 col20 file0 ranges - line1544 + line1560 col20 file0 - line1544 + line1560 col38 file0 depth0 extended_message Method returns an instance of NSString with a +1 retain count message Method returns an instance of NSString with a +1 retain count kindcontrol edges start - line1544 + line1560 col3 file0 - line1544 + line1560 col10 file0 end - line1545 + line1561 col3 file0 - line1545 + line1561 col10 file0 kindcontrol edges start - line1545 + line1561 col3 file0 - line1545 + line1561 col10 file0 end - line1545 + line1561 col20 file0 - line1545 + line1561 col20 file0 kindevent location - line1545 + line1561 col20 file0 ranges - line1545 + line1561 col20 file0 - line1545 + line1561 col37 file0 depth0 extended_message Object leaked: object allocated and stored into 'str2' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'str2' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'str2' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context21b45a41bb0c3c70a0efe89359ff3385 issue_context_kindfunction issue_contexttest_attr1c issue_hash_function_offset2 location - line1545 + line1561 col20 file0 ExecutedLines 0 - 1542 - 1543 - 1544 - 1545 + 1558 + 1559 + 1560 + 1561 path kindcontrol edges start - line1543 + line1559 col3 file0 - line1543 + line1559 col10 file0 end - line1546 + line1562 col3 file0 - line1546 + line1562 col10 file0 kindcontrol edges start - line1546 + line1562 col3 file0 - line1546 + line1562 col10 file0 end - line1546 + line1562 col21 file0 - line1546 + line1562 col21 file0 kindevent location - line1546 + line1562 col21 file0 ranges - line1546 + line1562 col21 file0 - line1546 + line1562 col38 file0 depth0 extended_message Method returns an instance of NSString with a +0 retain count message Method returns an instance of NSString with a +0 retain count kindevent location - line1546 + line1562 col20 file0 ranges - line1546 + line1562 col20 file0 - line1546 + line1562 col46 file0 - line1546 + line1562 col21 file0 - line1546 + line1562 col38 file0 depth0 extended_message Reference count incremented. The object now has a +1 retain count message Reference count incremented. The object now has a +1 retain count kindcontrol edges start - line1546 + line1562 col20 file0 - line1546 + line1562 col20 file0 end - line1546 + line1562 col3 file0 - line1546 + line1562 col10 file0 kindcontrol edges start - line1546 + line1562 col3 file0 - line1546 + line1562 col10 file0 end - line1547 + line1563 col1 file0 - line1547 + line1563 col1 file0 kindevent location - line1547 + line1563 col1 file0 depth0 extended_message Object leaked: object allocated and stored into 'str4' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'str4' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'str4' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context60396abae77bacd747ea9081b63a32db issue_context_kindfunction issue_contexttest_attr1c issue_hash_function_offset4 location - line1547 + line1563 col1 file0 ExecutedLines 0 - 1542 - 1543 - 1544 - 1545 - 1546 - 1547 + 1558 + 1559 + 1560 + 1561 + 1562 + 1563 path kindevent location - line1550 + line1566 col26 file0 ranges - line1550 + line1566 col26 file0 - line1550 + line1566 col50 file0 depth0 extended_message Method returns an instance of TestOwnershipAttr with a +1 retain count message Method returns an instance of TestOwnershipAttr with a +1 retain count kindcontrol edges start - line1550 + line1566 col3 file0 - line1550 + line1566 col19 file0 end - line1551 + line1567 col1 file0 - line1551 + line1567 col1 file0 kindevent location - line1551 + line1567 col1 file0 depth0 extended_message Object leaked: object allocated and stored into 'x' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'x' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'x' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_contexte258a710e07550a3dc5f47361a7380e1 issue_context_kindfunction issue_contexttestattr2_a issue_hash_function_offset1 location - line1551 + line1567 col1 file0 ExecutedLines 0 - 1549 - 1550 - 1551 + 1565 + 1566 + 1567 path kindevent location - line1554 + line1570 col26 file0 ranges - line1554 + line1570 col26 file0 - line1554 + line1570 col63 file0 depth0 extended_message Method returns an Objective-C object with a +1 retain count message Method returns an Objective-C object with a +1 retain count kindcontrol edges start - line1554 + line1570 col3 file0 - line1554 + line1570 col19 file0 end - line1555 + line1571 col1 file0 - line1555 + line1571 col1 file0 kindevent location - line1555 + line1571 col1 file0 depth0 extended_message Object leaked: object allocated and stored into 'x' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'x' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'x' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_contextdc245145c78c3421392a20775cdd6f23 issue_context_kindfunction issue_contexttestattr2_b issue_hash_function_offset1 location - line1555 + line1571 col1 file0 ExecutedLines 0 - 1553 - 1554 - 1555 + 1569 + 1570 + 1571 path kindevent location - line1558 + line1574 col26 file0 ranges - line1558 + line1574 col26 file0 - line1558 + line1574 col63 file0 depth0 extended_message Method returns an Objective-C object with a +1 retain count message Method returns an Objective-C object with a +1 retain count kindcontrol edges start - line1558 + line1574 col3 file0 - line1558 + line1574 col19 file0 end - line1559 + line1575 col3 file0 - line1559 + line1575 col3 file0 kindcontrol edges start - line1559 + line1575 col3 file0 - line1559 + line1575 col3 file0 end - line1560 + line1576 col1 file0 - line1560 + line1576 col1 file0 kindevent location - line1560 + line1576 col1 file0 depth0 extended_message Object leaked: object allocated and stored into 'x' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'x' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'x' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context77b970319b12b0c189e46ad65fa848c7 issue_context_kindfunction issue_contexttestattr2_b_11358224_self_assign_looses_the_leak issue_hash_function_offset1 location - line1560 + line1576 col1 file0 ExecutedLines 0 - 1557 - 1558 - 1559 - 1560 + 1573 + 1574 + 1575 + 1576 path kindevent location - line1590 + line1606 col10 file0 ranges - line1590 + line1606 col10 file0 - line1590 + line1606 col25 file0 depth0 extended_message Method returns an instance of NSString with a +1 retain count message Method returns an instance of NSString with a +1 retain count kindevent location - line1590 + line1606 col3 file0 ranges - line1590 + line1606 col3 file0 - line1590 + line1606 col25 file0 depth0 extended_message Object leaked: allocated object of type 'NSString *' is returned from a method that is annotated as NS_RETURNS_NOT_RETAINED message Object leaked: allocated object of type 'NSString *' is returned from a method that is annotated as NS_RETURNS_NOT_RETAINED descriptionPotential leak of an object of type 'NSString *' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak of returned object check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context4a8d774d2b821ce1601df7edabf66097 issue_context_kindObjective-C method issue_contextnewString issue_hash_function_offset1 location - line1590 + line1606 col3 file0 ExecutedLines 0 - 1589 - 1590 + 1605 + 1606 path kindcontrol edges start - line1623 + line1639 col3 file0 - line1623 + line1639 col8 file0 end - line1623 + line1639 col26 file0 - line1623 + line1639 col26 file0 kindevent location - line1623 + line1639 col26 file0 ranges - line1623 + line1639 col26 file0 - line1623 + line1639 col53 file0 depth0 extended_message Calling 'returnsCFRetainedAsCF' message Calling 'returnsCFRetainedAsCF' kindevent location - line1614 + line1630 col1 file0 depth1 extended_message Entered call from 'newCFRetainedAsCFNoAttr' message Entered call from 'newCFRetainedAsCFNoAttr' kindcontrol edges start - line1614 + line1630 col1 file0 - line1614 + line1630 col1 file0 end - line1615 + line1631 col3 file0 - line1615 + line1631 col8 file0 kindcontrol edges start - line1615 + line1631 col3 file0 - line1615 + line1631 col8 file0 end - line1615 + line1631 col10 file0 - line1615 + line1631 col30 file0 kindevent location - line1615 + line1631 col10 file0 ranges - line1615 + line1631 col10 file0 - line1615 + line1631 col32 file0 depth1 extended_message Calling 'returnsRetainedCFDate' message Calling 'returnsRetainedCFDate' kindevent location - line1604 + line1620 col1 file0 depth2 extended_message Entered call from 'returnsCFRetainedAsCF' message Entered call from 'returnsCFRetainedAsCF' kindcontrol edges start - line1604 + line1620 col1 file0 - line1604 + line1620 col19 file0 end - line1606 + line1622 col3 file0 - line1606 + line1622 col8 file0 kindevent location - line1606 + line1622 col10 file0 ranges - line1606 + line1622 col10 file0 - line1606 + line1622 col52 file0 depth2 extended_message Call to function 'CFDateCreate' returns a Core Foundation object of type 'CFDateRef' with a +1 retain count message Call to function 'CFDateCreate' returns a Core Foundation object of type 'CFDateRef' with a +1 retain count kindevent location - line1615 + line1631 col10 file0 ranges - line1615 + line1631 col10 file0 - line1615 + line1631 col32 file0 depth1 extended_message Returning from 'returnsRetainedCFDate' message Returning from 'returnsRetainedCFDate' kindcontrol edges start - line1615 + line1631 col10 file0 - line1615 + line1631 col30 file0 end - line1615 + line1631 col3 file0 - line1615 + line1631 col8 file0 kindevent location - line1623 + line1639 col26 file0 ranges - line1623 + line1639 col26 file0 - line1623 + line1639 col53 file0 depth0 extended_message Returning from 'returnsCFRetainedAsCF' message Returning from 'returnsCFRetainedAsCF' kindcontrol edges start - line1623 + line1639 col26 file0 - line1623 + line1639 col26 file0 end - line1623 + line1639 col21 file0 - line1623 + line1639 col21 file0 kindevent location - line1623 + line1639 col21 file0 ranges - line1623 + line1639 col21 file0 - line1623 + line1639 col66 file0 - line1623 + line1639 col22 file0 - line1623 + line1639 col53 file0 depth0 extended_message Object autoreleased message Object autoreleased kindcontrol edges start - line1623 + line1639 col21 file0 - line1623 + line1639 col21 file0 end - line1623 + line1639 col3 file0 - line1623 + line1639 col8 file0 kindevent location - line1623 + line1639 col3 file0 ranges - line1623 + line1639 col3 file0 - line1623 + line1639 col66 file0 depth0 extended_message Object with a +0 retain count returned to caller where a +1 (owning) retain count is expected message Object with a +0 retain count returned to caller where a +1 (owning) retain count is expected descriptionObject with a +0 retain count returned to caller where a +1 (owning) retain count is expected categoryMemory (Core Foundation/Objective-C/OSObject) typeMethod should return an owned object check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context2a609b8807dab6d3cb1a1db524094f2f issue_context_kindObjective-C method issue_contextnewCFRetainedAsCFNoAttr issue_hash_function_offset1 location - line1623 + line1639 col3 file0 ExecutedLines 0 - 1604 - 1605 - 1606 - 1614 - 1615 + 1620 + 1621 1622 - 1623 + 1630 + 1631 + 1638 + 1639 path kindcontrol edges start - line1627 + line1643 col3 file0 - line1627 + line1643 col8 file0 end - line1627 + line1643 col20 file0 - line1627 + line1643 col40 file0 kindevent location - line1627 + line1643 col20 file0 ranges - line1627 + line1643 col20 file0 - line1627 + line1643 col42 file0 depth0 extended_message Calling 'returnsRetainedCFDate' message Calling 'returnsRetainedCFDate' kindevent location - line1604 + line1620 col1 file0 depth1 extended_message Entered call from 'alsoReturnsRetained' message Entered call from 'alsoReturnsRetained' kindcontrol edges start - line1604 + line1620 col1 file0 - line1604 + line1620 col19 file0 end - line1606 + line1622 col3 file0 - line1606 + line1622 col8 file0 kindevent location - line1606 + line1622 col10 file0 ranges - line1606 + line1622 col10 file0 - line1606 + line1622 col52 file0 depth1 extended_message Call to function 'CFDateCreate' returns a Core Foundation object of type 'CFDateRef' with a +1 retain count message Call to function 'CFDateCreate' returns a Core Foundation object of type 'CFDateRef' with a +1 retain count kindevent location - line1627 + line1643 col20 file0 ranges - line1627 + line1643 col20 file0 - line1627 + line1643 col42 file0 depth0 extended_message Returning from 'returnsRetainedCFDate' message Returning from 'returnsRetainedCFDate' kindcontrol edges start - line1627 + line1643 col20 file0 - line1627 + line1643 col40 file0 end - line1627 + line1643 col3 file0 - line1627 + line1643 col8 file0 kindevent location - line1627 + line1643 col3 file0 ranges - line1627 + line1643 col3 file0 - line1627 + line1643 col42 file0 depth0 extended_message Object leaked: allocated object of type 'CFDateRef' is returned from a method whose name ('alsoReturnsRetained') does not start with 'copy', 'mutableCopy', 'alloc' or 'new'. This violates the naming convention rules given in the Memory Management Guide for Cocoa message Object leaked: allocated object of type 'CFDateRef' is returned from a method whose name ('alsoReturnsRetained') does not start with 'copy', 'mutableCopy', 'alloc' or 'new'. This violates the naming convention rules given in the Memory Management Guide for Cocoa descriptionPotential leak of an object of type 'CFDateRef' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak of returned object check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context944f189da47b1406f9cca6f17ad9f77c issue_context_kindObjective-C method issue_contextalsoReturnsRetained issue_hash_function_offset1 location - line1627 + line1643 col3 file0 ExecutedLines 0 - 1604 - 1605 - 1606 - 1626 - 1627 + 1620 + 1621 + 1622 + 1642 + 1643 path kindcontrol edges start - line1631 + line1647 col3 file0 - line1631 + line1647 col8 file0 end - line1631 + line1647 col10 file0 - line1631 + line1647 col30 file0 kindevent location - line1631 + line1647 col10 file0 ranges - line1631 + line1647 col10 file0 - line1631 + line1647 col32 file0 depth0 extended_message Calling 'returnsRetainedCFDate' message Calling 'returnsRetainedCFDate' kindevent location - line1604 + line1620 col1 file0 depth1 extended_message Entered call from 'alsoReturnsRetainedAsCF' message Entered call from 'alsoReturnsRetainedAsCF' kindcontrol edges start - line1604 + line1620 col1 file0 - line1604 + line1620 col19 file0 end - line1606 + line1622 col3 file0 - line1606 + line1622 col8 file0 kindevent location - line1606 + line1622 col10 file0 ranges - line1606 + line1622 col10 file0 - line1606 + line1622 col52 file0 depth1 extended_message Call to function 'CFDateCreate' returns a Core Foundation object of type 'CFDateRef' with a +1 retain count message Call to function 'CFDateCreate' returns a Core Foundation object of type 'CFDateRef' with a +1 retain count kindevent location - line1631 + line1647 col10 file0 ranges - line1631 + line1647 col10 file0 - line1631 + line1647 col32 file0 depth0 extended_message Returning from 'returnsRetainedCFDate' message Returning from 'returnsRetainedCFDate' kindcontrol edges start - line1631 + line1647 col10 file0 - line1631 + line1647 col30 file0 end - line1631 + line1647 col3 file0 - line1631 + line1647 col8 file0 kindevent location - line1631 + line1647 col3 file0 ranges - line1631 + line1647 col3 file0 - line1631 + line1647 col32 file0 depth0 extended_message Object leaked: allocated object of type 'CFDateRef' is returned from a method whose name ('alsoReturnsRetainedAsCF') does not start with 'copy', 'mutableCopy', 'alloc' or 'new'. This violates the naming convention rules given in the Memory Management Guide for Cocoa message Object leaked: allocated object of type 'CFDateRef' is returned from a method whose name ('alsoReturnsRetainedAsCF') does not start with 'copy', 'mutableCopy', 'alloc' or 'new'. This violates the naming convention rules given in the Memory Management Guide for Cocoa descriptionPotential leak of an object of type 'CFDateRef' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak of returned object check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context30ebf65449c31336f8a97555d79f1943 issue_context_kindObjective-C method issue_contextalsoReturnsRetainedAsCF issue_hash_function_offset1 location - line1631 + line1647 col3 file0 ExecutedLines 0 - 1604 - 1605 - 1606 - 1630 - 1631 + 1620 + 1621 + 1622 + 1646 + 1647 path kindcontrol edges start - line1651 + line1667 col3 file0 - line1651 + line1667 col8 file0 end - line1652 + line1668 col3 file0 - line1652 + line1668 col13 file0 kindevent location - line1652 + line1668 col23 file0 ranges - line1652 + line1668 col23 file0 - line1652 + line1668 col82 file0 depth0 extended_message Call to function 'CFNumberCreate' returns a Core Foundation object of type 'CFNumberRef' with a +1 retain count message Call to function 'CFNumberCreate' returns a Core Foundation object of type 'CFNumberRef' with a +1 retain count kindcontrol edges start - line1652 + line1668 col3 file0 - line1652 + line1668 col13 file0 end - line1653 + line1669 col1 file0 - line1653 + line1669 col1 file0 kindevent location - line1653 + line1669 col1 file0 depth0 extended_message Object leaked: object allocated and stored into 'value' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'value' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'value' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context2ab1a2345ddfa1fd48777c7c179d4e33 issue_context_kindfunction issue_contexttest_panic_negative issue_hash_function_offset2 location - line1653 + line1669 col1 file0 ExecutedLines 0 - 1650 - 1651 - 1652 - 1653 + 1666 + 1667 + 1668 + 1669 path kindcontrol edges start - line1662 + line1678 col3 file0 - line1662 + line1678 col8 file0 end - line1663 + line1679 col3 file0 - line1663 + line1679 col13 file0 kindevent location - line1663 + line1679 col23 file0 ranges - line1663 + line1679 col23 file0 - line1663 + line1679 col82 file0 depth0 extended_message Call to function 'CFNumberCreate' returns a Core Foundation object of type 'CFNumberRef' with a +1 retain count message Call to function 'CFNumberCreate' returns a Core Foundation object of type 'CFNumberRef' with a +1 retain count kindcontrol edges start - line1663 + line1679 col3 file0 - line1663 + line1679 col13 file0 end - line1664 + line1680 col3 file0 - line1664 + line1680 col4 file0 kindcontrol edges start - line1664 + line1680 col3 file0 - line1664 + line1680 col4 file0 end - line1664 + line1680 col7 file0 - line1664 + line1680 col7 file0 kindevent location - line1664 + line1680 col7 file0 ranges - line1664 + line1680 col7 file0 - line1664 + line1680 col7 file0 depth0 extended_message Assuming 'x' is 0 message Assuming 'x' is 0 kindcontrol edges start - line1664 + line1680 col7 file0 - line1664 + line1680 col7 file0 end - line1666 + line1682 col1 file0 - line1666 + line1682 col1 file0 kindevent location - line1666 + line1682 col1 file0 depth0 extended_message Object leaked: object allocated and stored into 'value' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'value' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'value' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_contextf96bb4f5c1af6cf932d7ab58b678c235 issue_context_kindfunction issue_contexttest_panic_neg_2 issue_hash_function_offset2 location - line1666 + line1682 col1 file0 ExecutedLines 0 - 1661 - 1662 - 1663 - 1664 - 1666 + 1677 + 1678 + 1679 + 1680 + 1682 path kindevent location - line1686 + line1702 col22 file0 ranges - line1686 + line1702 col22 file0 - line1686 + line1702 col53 file0 depth0 extended_message Method returns an instance of NSNumber with a +1 retain count message Method returns an instance of NSNumber with a +1 retain count kindcontrol edges start - line1686 + line1702 col3 file0 - line1686 + line1702 col10 file0 end - line1687 + line1703 col3 file0 - line1687 + line1703 col3 file0 kindevent location - line1687 + line1703 col3 file0 ranges - line1687 + line1703 col3 file0 - line1687 + line1703 col7 file0 depth0 extended_message Object leaked: object allocated and stored into 'number' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'number' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'number' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context14182fb28ed03595f896c2f8536ac111 issue_context_kindfunction issue_contexttest_blocks_1_pos issue_hash_function_offset1 location - line1687 + line1703 col3 file0 ExecutedLines 0 - 1685 - 1686 - 1687 + 1701 + 1702 + 1703 path kindevent location - line1707 + line1723 col22 file0 ranges - line1707 + line1723 col22 file0 - line1707 + line1723 col53 file0 depth0 extended_message Method returns an instance of NSNumber with a +1 retain count message Method returns an instance of NSNumber with a +1 retain count kindcontrol edges start - line1707 + line1723 col3 file0 - line1707 + line1723 col10 file0 end - line1708 + line1724 col3 file0 - line1708 + line1724 col3 file0 kindevent location - line1708 + line1724 col3 file0 ranges - line1708 + line1724 col3 file0 - line1708 + line1724 col39 file0 depth0 extended_message Calling anonymous block message Calling anonymous block kindevent location - line1708 + line1724 col3 file0 depth1 extended_message Entered call from 'test_blocks_1_indirect_retain_via_call' message Entered call from 'test_blocks_1_indirect_retain_via_call' kindcontrol edges start - line1708 + line1724 col3 file0 - line1708 + line1724 col3 file0 end - line1708 + line1724 col19 file0 - line1708 + line1724 col19 file0 kindevent location - line1708 + line1724 col19 file0 ranges - line1708 + line1724 col19 file0 - line1708 + line1724 col28 file0 - line1708 + line1724 col20 file0 - line1708 + line1724 col20 file0 depth1 extended_message Reference count incremented. The object now has a +2 retain count message Reference count incremented. The object now has a +2 retain count kindevent location - line1708 + line1724 col3 file0 ranges - line1708 + line1724 col3 file0 - line1708 + line1724 col39 file0 depth0 extended_message Returning to caller message Returning to caller kindcontrol edges start - line1708 + line1724 col3 file0 - line1708 + line1724 col3 file0 end - line1709 + line1725 col1 file0 - line1709 + line1725 col1 file0 kindevent location - line1709 + line1725 col1 file0 depth0 extended_message Object leaked: object allocated and stored into 'number' is not referenced later in this execution path and has a retain count of +2 message Object leaked: object allocated and stored into 'number' is not referenced later in this execution path and has a retain count of +2 descriptionPotential leak of an object stored into 'number' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_contextdbf800f836ff675d2f779f7417877c1b issue_context_kindfunction issue_contexttest_blocks_1_indirect_retain_via_call issue_hash_function_offset1 location - line1709 + line1725 col1 file0 ExecutedLines 0 - 1706 - 1707 - 1708 - 1709 + 1722 + 1723 + 1724 + 1725 path kindcontrol edges start - line1759 + line1775 col5 file0 - line1759 + line1775 col14 file0 end - line1762 + line1778 col5 file0 - line1762 + line1778 col9 file0 kindcontrol edges start - line1762 + line1778 col5 file0 - line1762 + line1778 col9 file0 end - line1762 + line1778 col12 file0 - line1762 + line1778 col24 file0 kindevent location - line1762 + line1778 col12 file0 ranges - line1762 + line1778 col12 file0 - line1762 + line1778 col38 file0 depth0 extended_message Assuming 'error_to_dump' is not equal to null message Assuming 'error_to_dump' is not equal to null kindevent location - line1762 + line1778 col12 file0 ranges - line1762 + line1778 col12 file0 - line1762 + line1778 col38 file0 depth0 extended_message Entering loop body message Entering loop body kindcontrol edges start - line1762 + line1778 col12 file0 - line1762 + line1778 col24 file0 end - line1763 + line1779 col9 file0 - line1763 + line1779 col23 file0 kindcontrol edges start - line1763 + line1779 col9 file0 - line1763 + line1779 col23 file0 end - line1765 + line1781 col9 file0 - line1765 + line1781 col12 file0 kindevent location - line1765 + line1781 col16 file0 ranges - line1765 + line1781 col16 file0 - line1765 + line1781 col49 file0 depth0 extended_message Call to function 'CFErrorCopyUserInfo' returns a Core Foundation object of type 'CFDictionaryRef' with a +1 retain count message Call to function 'CFErrorCopyUserInfo' returns a Core Foundation object of type 'CFDictionaryRef' with a +1 retain count kindcontrol edges start - line1765 + line1781 col9 file0 - line1765 + line1781 col12 file0 end - line1767 + line1783 col9 file0 - line1767 + line1783 col10 file0 kindcontrol edges start - line1767 + line1783 col9 file0 - line1767 + line1783 col10 file0 end - line1767 + line1783 col13 file0 - line1767 + line1783 col16 file0 kindevent location - line1767 + line1783 col13 file0 ranges - line1767 + line1783 col13 file0 - line1767 + line1783 col30 file0 depth0 extended_message Assuming 'info' is not equal to null message Assuming 'info' is not equal to null kindcontrol edges start - line1767 + line1783 col13 file0 - line1767 + line1783 col16 file0 end - line1770 + line1786 col23 file0 - line1770 + line1786 col23 file0 kindevent location - line1770 + line1786 col23 file0 depth0 extended_message Object leaked: object allocated and stored into 'info' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'info' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'info' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context64424de797303506a3dfdb52fa765645 issue_context_kindfunction issue_contextrdar_8724287 issue_hash_function_offset7 location - line1770 + line1786 col23 file0 ExecutedLines 0 - 1757 - 1758 - 1759 - 1761 - 1762 - 1763 - 1765 - 1767 - 1770 + 1773 + 1774 + 1775 + 1777 + 1778 + 1779 + 1781 + 1783 + 1786 path kindevent location - line1815 + line1831 col10 file0 ranges - line1815 + line1831 col10 file0 - line1815 + line1831 col60 file0 depth0 extended_message Call to function 'CFArrayCreateMutable' returns a Core Foundation object of type 'CFMutableArrayRef' with a +1 retain count message Call to function 'CFArrayCreateMutable' returns a Core Foundation object of type 'CFMutableArrayRef' with a +1 retain count kindevent location - line1815 + line1831 col3 file0 ranges - line1815 + line1831 col3 file0 - line1815 + line1831 col60 file0 depth0 extended_message Object leaked: allocated object of type 'CFMutableArrayRef' is returned from a function whose name ('camelcase_createno') does not contain 'Copy' or 'Create'. This violates the naming convention rules given in the Memory Management Guide for Core Foundation message Object leaked: allocated object of type 'CFMutableArrayRef' is returned from a function whose name ('camelcase_createno') does not contain 'Copy' or 'Create'. This violates the naming convention rules given in the Memory Management Guide for Core Foundation descriptionPotential leak of an object of type 'CFMutableArrayRef' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak of returned object check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context7b7fc0c36e58713202141cb584150903 issue_context_kindfunction issue_contextcamelcase_createno issue_hash_function_offset1 location - line1815 + line1831 col3 file0 ExecutedLines 0 - 1814 - 1815 + 1830 + 1831 path kindevent location - line1823 + line1839 col10 file0 ranges - line1823 + line1839 col10 file0 - line1823 + line1839 col60 file0 depth0 extended_message Call to function 'CFArrayCreateMutable' returns a Core Foundation object of type 'CFMutableArrayRef' with a +1 retain count message Call to function 'CFArrayCreateMutable' returns a Core Foundation object of type 'CFMutableArrayRef' with a +1 retain count kindevent location - line1823 + line1839 col3 file0 ranges - line1823 + line1839 col3 file0 - line1823 + line1839 col60 file0 depth0 extended_message Object leaked: allocated object of type 'CFMutableArrayRef' is returned from a function whose name ('camelcase_copying') does not contain 'Copy' or 'Create'. This violates the naming convention rules given in the Memory Management Guide for Core Foundation message Object leaked: allocated object of type 'CFMutableArrayRef' is returned from a function whose name ('camelcase_copying') does not contain 'Copy' or 'Create'. This violates the naming convention rules given in the Memory Management Guide for Core Foundation descriptionPotential leak of an object of type 'CFMutableArrayRef' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak of returned object check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context32912dd9518de1b3f4cc8ba38368f7e6 issue_context_kindfunction issue_contextcamelcase_copying issue_hash_function_offset1 location - line1823 + line1839 col3 file0 ExecutedLines 0 - 1822 - 1823 + 1838 + 1839 path kindevent location - line1844 + line1860 col10 file0 ranges - line1844 + line1860 col10 file0 - line1844 + line1860 col60 file0 depth0 extended_message Call to function 'CFArrayCreateMutable' returns a Core Foundation object of type 'CFMutableArrayRef' with a +1 retain count message Call to function 'CFArrayCreateMutable' returns a Core Foundation object of type 'CFMutableArrayRef' with a +1 retain count kindevent location - line1844 + line1860 col3 file0 ranges - line1844 + line1860 col3 file0 - line1844 + line1860 col60 file0 depth0 extended_message Object leaked: allocated object of type 'CFMutableArrayRef' is returned from a function whose name ('camel_creat') does not contain 'Copy' or 'Create'. This violates the naming convention rules given in the Memory Management Guide for Core Foundation message Object leaked: allocated object of type 'CFMutableArrayRef' is returned from a function whose name ('camel_creat') does not contain 'Copy' or 'Create'. This violates the naming convention rules given in the Memory Management Guide for Core Foundation descriptionPotential leak of an object of type 'CFMutableArrayRef' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak of returned object check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context1dccc42846a9ef9bf1a1830e277d5b78 issue_context_kindfunction issue_contextcamel_creat issue_hash_function_offset1 location - line1844 + line1860 col3 file0 ExecutedLines 0 - 1843 - 1844 + 1859 + 1860 path kindevent location - line1856 + line1872 col10 file0 ranges - line1856 + line1872 col10 file0 - line1856 + line1872 col60 file0 depth0 extended_message Call to function 'CFArrayCreateMutable' returns a Core Foundation object of type 'CFMutableArrayRef' with a +1 retain count message Call to function 'CFArrayCreateMutable' returns a Core Foundation object of type 'CFMutableArrayRef' with a +1 retain count kindevent location - line1856 + line1872 col3 file0 ranges - line1856 + line1872 col3 file0 - line1856 + line1872 col60 file0 depth0 extended_message Object leaked: allocated object of type 'CFMutableArrayRef' is returned from a function whose name ('camel_copymachine') does not contain 'Copy' or 'Create'. This violates the naming convention rules given in the Memory Management Guide for Core Foundation message Object leaked: allocated object of type 'CFMutableArrayRef' is returned from a function whose name ('camel_copymachine') does not contain 'Copy' or 'Create'. This violates the naming convention rules given in the Memory Management Guide for Core Foundation descriptionPotential leak of an object of type 'CFMutableArrayRef' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak of returned object check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context2a0ba33097f6e9362a79689e2ac0cf4a issue_context_kindfunction issue_contextcamel_copymachine issue_hash_function_offset1 location - line1856 + line1872 col3 file0 ExecutedLines 0 - 1855 - 1856 + 1871 + 1872 path kindcontrol edges start - line1876 + line1892 col3 file0 - line1876 + line1892 col16 file0 end - line1877 + line1893 col3 file0 - line1877 + line1893 col11 file0 kindevent location - line1877 + line1893 col24 file0 ranges - line1877 + line1893 col24 file0 - line1877 + line1893 col41 file0 depth0 extended_message Call to function 'CFDateCreate' returns a Core Foundation object of type 'CFDateRef' with a +1 retain count message Call to function 'CFDateCreate' returns a Core Foundation object of type 'CFDateRef' with a +1 retain count kindcontrol edges start - line1877 + line1893 col3 file0 - line1877 + line1893 col11 file0 end - line1878 + line1894 col1 file0 - line1878 + line1894 col1 file0 kindevent location - line1878 + line1894 col1 file0 depth0 extended_message Object leaked: object allocated and stored into 'vals' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'vals' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'vals' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context43f6c1be372d09a4a4cffaefa69d0148 issue_context_kindfunction issue_contextrdar6582778 issue_hash_function_offset2 location - line1878 + line1894 col1 file0 ExecutedLines 0 - 1875 - 1876 - 1877 - 1878 + 1891 + 1892 + 1893 + 1894 path kindcontrol edges start - line1902 + line1918 col3 file0 - line1902 + line1918 col16 file0 end - line1904 + line1920 col3 file0 - line1904 + line1920 col10 file0 kindevent location - line1904 + line1920 col22 file0 ranges - line1904 + line1920 col22 file0 - line1904 + line1920 col64 file0 depth0 extended_message Method returns an instance of NSString with a +1 retain count message Method returns an instance of NSString with a +1 retain count kindcontrol edges start - line1904 + line1920 col3 file0 - line1904 + line1920 col10 file0 end - line1905 + line1921 col3 file0 - line1905 + line1921 col3 file0 kindevent location - line1905 + line1921 col3 file0 ranges - line1905 + line1921 col3 file0 - line1905 + line1921 col18 file0 - line1905 + line1921 col4 file0 - line1905 + line1921 col9 file0 depth0 extended_message Object released message Object released kindcontrol edges start - line1905 + line1921 col3 file0 - line1905 + line1921 col3 file0 end - line1907 + line1923 col3 file0 - line1907 + line1923 col10 file0 kindcontrol edges start - line1907 + line1923 col3 file0 - line1907 + line1923 col10 file0 end - line1907 + line1923 col27 file0 - line1907 + line1923 col27 file0 kindevent location - line1907 + line1923 col27 file0 ranges - line1907 + line1923 col28 file0 - line1907 + line1923 col33 file0 depth0 extended_message Reference-counted object is used after it is released message Reference-counted object is used after it is released descriptionReference-counted object is used after it is released categoryMemory (Core Foundation/Objective-C/OSObject) typeUse-after-release check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_contextebe7e868c0075bfa7480e3359e4fbce8 issue_context_kindfunction issue_contextrdar10232019_positive issue_hash_function_offset6 location - line1907 + line1923 col27 file0 ExecutedLines 0 - 1901 - 1902 - 1904 - 1905 - 1907 + 1917 + 1918 + 1920 + 1921 + 1923 path kindcontrol edges start - line2034 + line2050 col9 file0 - line2034 + line2050 col16 file0 end - line2035 + line2051 col9 file0 - line2035 + line2051 col15 file0 kindevent location - line2035 + line2051 col22 file0 ranges - line2035 + line2051 col22 file0 - line2035 + line2051 col66 file0 depth0 extended_message Method returns an instance of NSArray with a +1 retain count message Method returns an instance of NSArray with a +1 retain count kindcontrol edges start - line2035 + line2051 col9 file0 - line2035 + line2051 col15 file0 end - line2038 + line2054 col9 file0 - line2038 + line2054 col9 file0 kindevent location - line2038 + line2054 col9 file0 ranges - line2038 + line2054 col9 file0 - line2038 + line2054 col23 file0 depth0 extended_message Object leaked: object allocated and stored into 'a' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'a' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'a' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context507c3679ae27249e01844b7555843688 issue_context_kindfunction issue_contexttest_objc_arrays issue_hash_function_offset3 location - line2038 + line2054 col9 file0 ExecutedLines 0 - 2032 - 2034 - 2035 - 2036 - 2037 - 2038 + 2048 + 2050 + 2051 + 2052 + 2053 + 2054 path kindcontrol edges start - line2034 + line2050 col9 file0 - line2034 + line2050 col16 file0 end - line2038 + line2054 col9 file0 - line2038 + line2054 col9 file0 kindcontrol edges start - line2038 + line2054 col9 file0 - line2038 + line2054 col9 file0 end - line2042 + line2058 col9 file0 - line2042 + line2058 col16 file0 kindcontrol edges start - line2042 + line2058 col9 file0 - line2042 + line2058 col16 file0 end - line2044 + line2060 col9 file0 - line2044 + line2060 col15 file0 kindevent location - line2044 + line2060 col23 file0 ranges - line2044 + line2060 col23 file0 - line2044 + line2060 col56 file0 depth0 extended_message Method returns an instance of NSArray with a +1 retain count message Method returns an instance of NSArray with a +1 retain count kindcontrol edges start - line2044 + line2060 col9 file0 - line2044 + line2060 col15 file0 end - line2047 + line2063 col9 file0 - line2047 + line2063 col9 file0 kindevent location - line2047 + line2063 col9 file0 ranges - line2047 + line2063 col9 file0 - line2047 + line2063 col23 file0 depth0 extended_message Object leaked: object allocated and stored into 'a2' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'a2' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'a2' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context821f8268a0b7d3f90e4dd88fa1edf39b issue_context_kindfunction issue_contexttest_objc_arrays issue_hash_function_offset12 location - line2047 + line2063 col9 file0 ExecutedLines 0 - 2032 - 2034 - 2035 - 2036 - 2037 - 2038 - 2042 - 2043 - 2044 - 2045 - 2046 - 2047 + 2048 + 2050 + 2051 + 2052 + 2053 + 2054 + 2058 + 2059 + 2060 + 2061 + 2062 + 2063 path kindcontrol edges start - line2034 + line2050 col9 file0 - line2034 + line2050 col16 file0 end - line2038 + line2054 col9 file0 - line2038 + line2054 col9 file0 kindcontrol edges start - line2038 + line2054 col9 file0 - line2038 + line2054 col9 file0 end - line2042 + line2058 col9 file0 - line2042 + line2058 col16 file0 kindcontrol edges start - line2042 + line2058 col9 file0 - line2042 + line2058 col16 file0 end - line2047 + line2063 col9 file0 - line2047 + line2063 col9 file0 kindcontrol edges start - line2047 + line2063 col9 file0 - line2047 + line2063 col9 file0 end - line2051 + line2067 col9 file0 - line2051 + line2067 col16 file0 kindcontrol edges start - line2051 + line2067 col9 file0 - line2051 + line2067 col16 file0 end - line2052 + line2068 col9 file0 - line2052 + line2068 col15 file0 kindcontrol edges start - line2052 + line2068 col9 file0 - line2052 + line2068 col15 file0 end - line2052 + line2068 col24 file0 - line2052 + line2068 col24 file0 kindevent location - line2052 + line2068 col24 file0 ranges - line2052 + line2068 col24 file0 - line2052 + line2068 col27 file0 depth0 extended_message NSArray literal is an object with a +0 retain count message NSArray literal is an object with a +0 retain count kindevent location - line2052 + line2068 col23 file0 ranges - line2052 + line2068 col23 file0 - line2052 + line2068 col35 file0 - line2052 + line2068 col24 file0 - line2052 + line2068 col27 file0 depth0 extended_message Reference count incremented. The object now has a +1 retain count message Reference count incremented. The object now has a +1 retain count kindcontrol edges start - line2052 + line2068 col23 file0 - line2052 + line2068 col23 file0 end - line2052 + line2068 col9 file0 - line2052 + line2068 col15 file0 kindcontrol edges start - line2052 + line2068 col9 file0 - line2052 + line2068 col15 file0 end - line2055 + line2071 col9 file0 - line2055 + line2071 col9 file0 kindevent location - line2055 + line2071 col9 file0 ranges - line2055 + line2071 col9 file0 - line2055 + line2071 col23 file0 depth0 extended_message Object leaked: object allocated and stored into 'a3' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'a3' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'a3' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context37b00e6e0e6b792ea3294a9ffd6f4886 issue_context_kindfunction issue_contexttest_objc_arrays issue_hash_function_offset20 location - line2055 + line2071 col9 file0 ExecutedLines 0 - 2032 - 2034 - 2035 - 2036 - 2037 - 2038 - 2042 - 2043 - 2044 - 2045 - 2046 - 2047 + 2048 + 2050 2051 2052 2053 2054 - 2055 + 2058 + 2059 + 2060 + 2061 + 2062 + 2063 + 2067 + 2068 + 2069 + 2070 + 2071 path kindcontrol edges start - line2034 + line2050 col9 file0 - line2034 + line2050 col16 file0 end - line2038 + line2054 col9 file0 - line2038 + line2054 col9 file0 kindcontrol edges start - line2038 + line2054 col9 file0 - line2038 + line2054 col9 file0 end - line2042 + line2058 col9 file0 - line2042 + line2058 col16 file0 kindcontrol edges start - line2042 + line2058 col9 file0 - line2042 + line2058 col16 file0 end - line2047 + line2063 col9 file0 - line2047 + line2063 col9 file0 kindcontrol edges start - line2047 + line2063 col9 file0 - line2047 + line2063 col9 file0 end - line2051 + line2067 col9 file0 - line2051 + line2067 col16 file0 kindcontrol edges start - line2051 + line2067 col9 file0 - line2051 + line2067 col16 file0 end - line2055 + line2071 col9 file0 - line2055 + line2071 col9 file0 kindcontrol edges start - line2055 + line2071 col9 file0 - line2055 + line2071 col9 file0 end - line2059 + line2075 col9 file0 - line2059 + line2075 col16 file0 kindcontrol edges start - line2059 + line2075 col9 file0 - line2059 + line2075 col16 file0 end - line2060 + line2076 col9 file0 - line2060 + line2076 col15 file0 kindevent location - line2060 + line2076 col22 file0 ranges - line2060 + line2076 col22 file0 - line2060 + line2076 col57 file0 depth0 extended_message Method returns an instance of NSArray with a +1 retain count message Method returns an instance of NSArray with a +1 retain count kindcontrol edges start - line2060 + line2076 col9 file0 - line2060 + line2076 col15 file0 end - line2064 + line2080 col9 file0 - line2064 + line2080 col9 file0 kindevent location - line2064 + line2080 col9 file0 ranges - line2064 + line2080 col9 file0 - line2064 + line2080 col23 file0 depth0 extended_message Object leaked: object allocated and stored into 'a' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'a' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'a' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context62fc5b80705a03ab1d8b50bdcfbfb179 issue_context_kindfunction issue_contexttest_objc_arrays issue_hash_function_offset28 location - line2064 + line2080 col9 file0 ExecutedLines 0 - 2032 - 2034 - 2035 - 2036 - 2037 - 2038 - 2042 - 2043 - 2044 - 2045 - 2046 - 2047 + 2048 + 2050 2051 2052 2053 2054 - 2055 + 2058 2059 2060 2061 + 2062 2063 - 2064 + 2067 + 2068 + 2069 + 2070 + 2071 + 2075 + 2076 + 2077 + 2079 + 2080 path kindcontrol edges start - line2034 + line2050 col9 file0 - line2034 + line2050 col16 file0 end - line2038 + line2054 col9 file0 - line2038 + line2054 col9 file0 kindcontrol edges start - line2038 + line2054 col9 file0 - line2038 + line2054 col9 file0 end - line2042 + line2058 col9 file0 - line2042 + line2058 col16 file0 kindcontrol edges start - line2042 + line2058 col9 file0 - line2042 + line2058 col16 file0 end - line2047 + line2063 col9 file0 - line2047 + line2063 col9 file0 kindcontrol edges start - line2047 + line2063 col9 file0 - line2047 + line2063 col9 file0 end - line2051 + line2067 col9 file0 - line2051 + line2067 col16 file0 kindcontrol edges start - line2051 + line2067 col9 file0 - line2051 + line2067 col16 file0 end - line2055 + line2071 col9 file0 - line2055 + line2071 col9 file0 kindcontrol edges start - line2055 + line2071 col9 file0 - line2055 + line2071 col9 file0 end - line2059 + line2075 col9 file0 - line2059 + line2075 col16 file0 kindcontrol edges start - line2059 + line2075 col9 file0 - line2059 + line2075 col16 file0 end - line2064 + line2080 col9 file0 - line2064 + line2080 col9 file0 kindcontrol edges start - line2064 + line2080 col9 file0 - line2064 + line2080 col9 file0 end - line2068 + line2084 col9 file0 - line2068 + line2084 col15 file0 kindcontrol edges start - line2068 + line2084 col9 file0 - line2068 + line2084 col15 file0 end - line2069 + line2085 col9 file0 - line2069 + line2085 col20 file0 kindcontrol edges start - line2069 + line2085 col9 file0 - line2069 + line2085 col20 file0 end - line2069 + line2085 col28 file0 - line2069 + line2085 col28 file0 kindevent location - line2069 + line2085 col28 file0 ranges - line2069 + line2085 col28 file0 - line2069 + line2085 col35 file0 depth0 extended_message NSDictionary literal is an object with a +0 retain count message NSDictionary literal is an object with a +0 retain count kindevent location - line2069 + line2085 col27 file0 ranges - line2069 + line2085 col27 file0 - line2069 + line2085 col43 file0 - line2069 + line2085 col28 file0 - line2069 + line2085 col35 file0 depth0 extended_message Reference count incremented. The object now has a +1 retain count message Reference count incremented. The object now has a +1 retain count kindcontrol edges start - line2069 + line2085 col27 file0 - line2069 + line2085 col27 file0 end - line2069 + line2085 col9 file0 - line2069 + line2085 col20 file0 kindcontrol edges start - line2069 + line2085 col9 file0 - line2069 + line2085 col20 file0 end - line2073 + line2089 col9 file0 - line2073 + line2089 col9 file0 kindevent location - line2073 + line2089 col9 file0 ranges - line2073 + line2089 col9 file0 - line2073 + line2089 col23 file0 depth0 extended_message Object leaked: object allocated and stored into 'a' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'a' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'a' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_context3eee239ca30a84ef6ecc5d154ae8df28 issue_context_kindfunction issue_contexttest_objc_arrays issue_hash_function_offset37 location - line2073 + line2089 col9 file0 ExecutedLines 0 - 2032 - 2034 - 2035 - 2036 - 2037 - 2038 - 2042 - 2043 - 2044 - 2045 - 2046 - 2047 + 2048 + 2050 2051 2052 2053 2054 - 2055 + 2058 2059 2060 2061 + 2062 2063 - 2064 + 2067 2068 2069 2070 - 2072 - 2073 + 2071 + 2075 + 2076 + 2077 + 2079 + 2080 + 2084 + 2085 + 2086 + 2088 + 2089 path kindcontrol edges start - line2078 + line2094 col3 file0 - line2078 + line2094 col4 file0 end - line2078 + line2094 col15 file0 - line2078 + line2094 col15 file0 kindevent location - line2078 + line2094 col15 file0 ranges - line2078 + line2094 col15 file0 - line2078 + line2094 col16 file0 depth0 extended_message NSNumber literal is an object with a +0 retain count message NSNumber literal is an object with a +0 retain count kindevent location - line2078 + line2094 col14 file0 ranges - line2078 + line2094 col14 file0 - line2078 + line2094 col24 file0 - line2078 + line2094 col15 file0 - line2078 + line2094 col16 file0 depth0 extended_message Reference count incremented. The object now has a +1 retain count message Reference count incremented. The object now has a +1 retain count kindcontrol edges start - line2078 + line2094 col14 file0 - line2078 + line2094 col14 file0 end - line2078 + line2094 col3 file0 - line2078 + line2094 col4 file0 kindcontrol edges start - line2078 + line2094 col3 file0 - line2078 + line2094 col4 file0 end - line2079 + line2095 col3 file0 - line2079 + line2095 col3 file0 kindcontrol edges start - line2079 + line2095 col3 file0 - line2079 + line2095 col3 file0 end - line2080 + line2096 col1 file0 - line2080 + line2096 col1 file0 kindevent location - line2080 + line2096 col1 file0 depth0 extended_message Object leaked: object allocated and stored into 'value' is not referenced later in this execution path and has a retain count of +1 message Object leaked: object allocated and stored into 'value' is not referenced later in this execution path and has a retain count of +1 descriptionPotential leak of an object stored into 'value' categoryMemory (Core Foundation/Objective-C/OSObject) typeLeak check_nameosx.cocoa.RetainCountBase issue_hash_content_of_line_in_contextcb86fdadd2217db6b784b37dc29eba34 issue_context_kindfunction issue_contexttest_objc_integer_literals issue_hash_function_offset1 location - line2080 + line2096 col1 file0 ExecutedLines 0 - 2077 - 2078 - 2079 - 2080 + 2093 + 2094 + 2095 + 2096 path kindcontrol edges start - line2083 + line2099 col3 file0 - line2083 + line2099 col4 file0 end - line2083 + line2099 col15 file0 - line2083 + line2099 col15 file0 kindevent location - line2083 + line2099 col15 file0 ranges - line2083 + line2099 col15 file0 - line2083 + line2099 col18 file0 depth0 extended_message NSNumber boxed expression produces an object with a +0 retain count message NSNumber boxed expression produces an object with a +0 retain count kindevent location - line2083 + line2099 col14 file0 ranges - line2083 + line2099 col14 file0 - line2083 + line2099 col26 file0 - line2083 + line2099 col15 file0 - line2083 + line2099 col18 file0 depth0 extended_message Reference count incremented. The object now has a +1 retain count message Reference count incremented. The object now has a +1 retain count kindcontrol edges start - line2083 + line2099 col14 file0 - line2083 + line2099 col14 file0 end - line2083 + line2099 col3 file0 - line2083 + line2099 col4 file0 kindcontrol edges start - line2083 + line2099 col3 file0 - line2083 + line2099 col4 file0 end - line2087 + line2103 col3 file0 - line2087 + line2103 col3 file0 kindevent location - line2087 + line2103 col3 file0 ranges - line2087 + line2103 col3 file0 - line2087 + line2103 col21 file0 depth0 extended_message Object leaked: object allocated and stored into 'value' is not referenced later in t