<div dir="ltr">Hi Erik,<div><br></div><div>with this change clangs warns on this program:</div><div><br></div><div><div>$ cat <a href="http://test.mm">test.mm</a></div><div>#import <Cocoa/Cocoa.h></div><div>@interface AXPlatformNodeCocoa : NSObject<br></div><div>@end</div><div>@implementation AXPlatformNodeCocoa<br></div><div>- (NSArray*)accessibilityAttributeNames {</div><div> NSArray* const kTextfieldAttributes = @[</div><div> NSAccessibilityPlaceholderValueAttribute,</div><div> ];</div><div> return kTextfieldAttributes;</div><div>}</div><div>@end</div><div><br></div><div>$ bin/clang -c <a href="http://test.mm">test.mm</a> -isysroot $(xcrun -show-sdk-path) -Wpartial-availability -mmacosx-version-min=10.7</div><div>test.mm:9:5: warning: 'NSAccessibilityPlaceholderValueAttribute' is partial: introduced in macOS 10.6 [-Wpartial-availability]</div><div> NSAccessibilityPlaceholderValueAttribute,</div><div> ^</div><div>/Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX10.11.sdk/System/Library/Frameworks/AppKit.framework/Headers/NSAccessibilityConstants.h:85:31: note: </div><div> 'NSAccessibilityPlaceholderValueAttribute' has been explicitly marked partial here</div></div><div><br></div><div>Given that I'm building with -mmacosx-version-min=10.7 it seems strange to warn about something introduced in 10.6. This is probably not doing what it should?</div><div><br></div><div>Thanks,</div><div>Nico</div><div><br></div></div><div class="gmail_extra"><br><div class="gmail_quote">On Fri, Jul 29, 2016 at 1:37 PM, Erik Pilkington via cfe-commits <span dir="ltr"><<a href="mailto:cfe-commits@lists.llvm.org" target="_blank">cfe-commits@lists.llvm.org</a>></span> wrote:<br><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">Author: epilk<br>
Date: Fri Jul 29 12:37:38 2016<br>
New Revision: 277175<br>
<br>
URL: <a href="http://llvm.org/viewvc/llvm-project?rev=277175&view=rev" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project?rev=277175&view=rev</a><br>
Log:<br>
Reapply r277058: "[ObjC] Consider availability of context when emitting availability warnings"<br>
<br>
Modified:<br>
cfe/trunk/include/clang/AST/DeclBase.h<br>
cfe/trunk/include/clang/Sema/Sema.h<br>
cfe/trunk/lib/AST/DeclBase.cpp<br>
cfe/trunk/lib/Sema/SemaDeclAttr.cpp<br>
cfe/trunk/lib/Sema/SemaExpr.cpp<br>
cfe/trunk/test/SemaObjC/attr-availability.m<br>
<br>
Modified: cfe/trunk/include/clang/AST/DeclBase.h<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/AST/DeclBase.h?rev=277175&r1=277174&r2=277175&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/AST/DeclBase.h?rev=277175&r1=277174&r2=277175&view=diff</a><br>
==============================================================================<br>
--- cfe/trunk/include/clang/AST/DeclBase.h (original)<br>
+++ cfe/trunk/include/clang/AST/DeclBase.h Fri Jul 29 12:37:38 2016<br>
@@ -17,6 +17,7 @@<br>
#include "clang/AST/AttrIterator.h"<br>
#include "clang/AST/DeclarationName.h"<br>
#include "clang/Basic/Specifiers.h"<br>
+#include "clang/Basic/VersionTuple.h"<br>
#include "llvm/ADT/PointerUnion.h"<br>
#include "llvm/ADT/iterator.h"<br>
#include "llvm/ADT/iterator_range.h"<br>
@@ -603,7 +604,12 @@ public:<br>
/// AR_Available, will be set to a (possibly empty) message<br>
/// describing why the declaration has not been introduced, is<br>
/// deprecated, or is unavailable.<br>
- AvailabilityResult getAvailability(std::string *Message = nullptr) const;<br>
+ ///<br>
+ /// \param EnclosingVersion The version to compare with. If empty, assume the<br>
+ /// deployment target version.<br>
+ AvailabilityResult<br>
+ getAvailability(std::string *Message = nullptr,<br>
+ VersionTuple EnclosingVersion = VersionTuple()) const;<br>
<br>
/// \brief Determine whether this declaration is marked 'deprecated'.<br>
///<br>
<br>
Modified: cfe/trunk/include/clang/Sema/Sema.h<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Sema/Sema.h?rev=277175&r1=277174&r2=277175&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Sema/Sema.h?rev=277175&r1=277174&r2=277175&view=diff</a><br>
==============================================================================<br>
--- cfe/trunk/include/clang/Sema/Sema.h (original)<br>
+++ cfe/trunk/include/clang/Sema/Sema.h Fri Jul 29 12:37:38 2016<br>
@@ -9596,7 +9596,12 @@ public:<br>
}<br>
<br>
AvailabilityResult getCurContextAvailability() const;<br>
-<br>
+<br>
+ /// \brief Get the verison that this context implies.<br>
+ /// For instance, a method in an interface that is annotated with an<br>
+ /// availability attribuite effectively has the availability of the interface.<br>
+ VersionTuple getVersionForDecl(const Decl *Ctx) const;<br>
+<br>
const DeclContext *getCurObjCLexicalContext() const {<br>
const DeclContext *DC = getCurLexicalContext();<br>
// A category implicitly has the attribute of the interface.<br>
<br>
Modified: cfe/trunk/lib/AST/DeclBase.cpp<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/DeclBase.cpp?rev=277175&r1=277174&r2=277175&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/DeclBase.cpp?rev=277175&r1=277174&r2=277175&view=diff</a><br>
==============================================================================<br>
--- cfe/trunk/lib/AST/DeclBase.cpp (original)<br>
+++ cfe/trunk/lib/AST/DeclBase.cpp Fri Jul 29 12:37:38 2016<br>
@@ -400,11 +400,12 @@ const Attr *Decl::getDefiningAttr() cons<br>
/// diagnostics.<br>
static AvailabilityResult CheckAvailability(ASTContext &Context,<br>
const AvailabilityAttr *A,<br>
- std::string *Message) {<br>
- VersionTuple TargetMinVersion =<br>
- Context.getTargetInfo().getPlatformMinVersion();<br>
+ std::string *Message,<br>
+ VersionTuple EnclosingVersion) {<br>
+ if (EnclosingVersion.empty())<br>
+ EnclosingVersion = Context.getTargetInfo().getPlatformMinVersion();<br>
<br>
- if (TargetMinVersion.empty())<br>
+ if (EnclosingVersion.empty())<br>
return AR_Available;<br>
<br>
// Check if this is an App Extension "platform", and if so chop off<br>
@@ -449,7 +450,7 @@ static AvailabilityResult CheckAvailabil<br>
<br>
// Make sure that this declaration has already been introduced.<br>
if (!A->getIntroduced().empty() &&<br>
- TargetMinVersion < A->getIntroduced()) {<br>
+ EnclosingVersion < A->getIntroduced()) {<br>
if (Message) {<br>
Message->clear();<br>
llvm::raw_string_ostream Out(*Message);<br>
@@ -463,7 +464,7 @@ static AvailabilityResult CheckAvailabil<br>
}<br>
<br>
// Make sure that this declaration hasn't been obsoleted.<br>
- if (!A->getObsoleted().empty() && TargetMinVersion >= A->getObsoleted()) {<br>
+ if (!A->getObsoleted().empty() && EnclosingVersion >= A->getObsoleted()) {<br>
if (Message) {<br>
Message->clear();<br>
llvm::raw_string_ostream Out(*Message);<br>
@@ -477,7 +478,7 @@ static AvailabilityResult CheckAvailabil<br>
}<br>
<br>
// Make sure that this declaration hasn't been deprecated.<br>
- if (!A->getDeprecated().empty() && TargetMinVersion >= A->getDeprecated()) {<br>
+ if (!A->getDeprecated().empty() && EnclosingVersion >= A->getDeprecated()) {<br>
if (Message) {<br>
Message->clear();<br>
llvm::raw_string_ostream Out(*Message);<br>
@@ -493,9 +494,10 @@ static AvailabilityResult CheckAvailabil<br>
return AR_Available;<br>
}<br>
<br>
-AvailabilityResult Decl::getAvailability(std::string *Message) const {<br>
+AvailabilityResult Decl::getAvailability(std::string *Message,<br>
+ VersionTuple EnclosingVersion) const {<br>
if (auto *FTD = dyn_cast<FunctionTemplateDecl>(this))<br>
- return FTD->getTemplatedDecl()->getAvailability(Message);<br>
+ return FTD->getTemplatedDecl()->getAvailability(Message, EnclosingVersion);<br>
<br>
AvailabilityResult Result = AR_Available;<br>
std::string ResultMessage;<br>
@@ -520,7 +522,7 @@ AvailabilityResult Decl::getAvailability<br>
<br>
if (const auto *Availability = dyn_cast<AvailabilityAttr>(A)) {<br>
AvailabilityResult AR = CheckAvailability(getASTContext(), Availability,<br>
- Message);<br>
+ Message, EnclosingVersion);<br>
<br>
if (AR == AR_Unavailable)<br>
return AR_Unavailable;<br>
@@ -579,8 +581,8 @@ bool Decl::isWeakImported() const {<br>
return true;<br>
<br>
if (const auto *Availability = dyn_cast<AvailabilityAttr>(A)) {<br>
- if (CheckAvailability(getASTContext(), Availability,<br>
- nullptr) == AR_NotYetIntroduced)<br>
+ if (CheckAvailability(getASTContext(), Availability, nullptr,<br>
+ VersionTuple()) == AR_NotYetIntroduced)<br>
return true;<br>
}<br>
}<br>
<br>
Modified: cfe/trunk/lib/Sema/SemaDeclAttr.cpp<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaDeclAttr.cpp?rev=277175&r1=277174&r2=277175&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaDeclAttr.cpp?rev=277175&r1=277174&r2=277175&view=diff</a><br>
==============================================================================<br>
--- cfe/trunk/lib/Sema/SemaDeclAttr.cpp (original)<br>
+++ cfe/trunk/lib/Sema/SemaDeclAttr.cpp Fri Jul 29 12:37:38 2016<br>
@@ -6484,3 +6484,26 @@ void Sema::EmitAvailabilityWarning(Avail<br>
DoEmitAvailabilityWarning(*this, AD, Ctx, D, Message, Loc, UnknownObjCClass,<br>
ObjCProperty, ObjCPropertyAccess);<br>
}<br>
+<br>
+VersionTuple Sema::getVersionForDecl(const Decl *D) const {<br>
+ assert(D && "Expected a declaration here!");<br>
+<br>
+ VersionTuple DeclVersion;<br>
+ if (const auto *AA = getAttrForPlatform(getASTContext(), D))<br>
+ DeclVersion = AA->getIntroduced();<br>
+<br>
+ const ObjCInterfaceDecl *Interface = nullptr;<br>
+<br>
+ if (const auto *MD = dyn_cast<ObjCMethodDecl>(D))<br>
+ Interface = MD->getClassInterface();<br>
+ else if (const auto *ID = dyn_cast<ObjCImplementationDecl>(D))<br>
+ Interface = ID->getClassInterface();<br>
+<br>
+ if (Interface) {<br>
+ if (const auto *AA = getAttrForPlatform(getASTContext(), Interface))<br>
+ if (AA->getIntroduced() > DeclVersion)<br>
+ DeclVersion = AA->getIntroduced();<br>
+ }<br>
+<br>
+ return DeclVersion;<br>
+}<br>
<br>
Modified: cfe/trunk/lib/Sema/SemaExpr.cpp<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaExpr.cpp?rev=277175&r1=277174&r2=277175&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaExpr.cpp?rev=277175&r1=277174&r2=277175&view=diff</a><br>
==============================================================================<br>
--- cfe/trunk/lib/Sema/SemaExpr.cpp (original)<br>
+++ cfe/trunk/lib/Sema/SemaExpr.cpp Fri Jul 29 12:37:38 2016<br>
@@ -107,9 +107,14 @@ static AvailabilityResult<br>
DiagnoseAvailabilityOfDecl(Sema &S, NamedDecl *D, SourceLocation Loc,<br>
const ObjCInterfaceDecl *UnknownObjCClass,<br>
bool ObjCPropertyAccess) {<br>
- // See if this declaration is unavailable or deprecated.<br>
+ VersionTuple ContextVersion;<br>
+ if (const DeclContext *DC = S.getCurObjCLexicalContext())<br>
+ ContextVersion = S.getVersionForDecl(cast<Decl>(DC));<br>
+<br>
+ // See if this declaration is unavailable, deprecated, or partial in the<br>
+ // current context.<br>
std::string Message;<br>
- AvailabilityResult Result = D->getAvailability(&Message);<br>
+ AvailabilityResult Result = D->getAvailability(&Message, ContextVersion);<br>
<br>
// For typedefs, if the typedef declaration appears available look<br>
// to the underlying type to see if it is more restrictive.<br>
@@ -117,7 +122,7 @@ DiagnoseAvailabilityOfDecl(Sema &S, Name<br>
if (Result == AR_Available) {<br>
if (const TagType *TT = TD->getUnderlyingType()->getAs<TagType>()) {<br>
D = TT->getDecl();<br>
- Result = D->getAvailability(&Message);<br>
+ Result = D->getAvailability(&Message, ContextVersion);<br>
continue;<br>
}<br>
}<br>
@@ -128,7 +133,7 @@ DiagnoseAvailabilityOfDecl(Sema &S, Name<br>
if (ObjCInterfaceDecl *IDecl = dyn_cast<ObjCInterfaceDecl>(D)) {<br>
if (IDecl->getDefinition()) {<br>
D = IDecl->getDefinition();<br>
- Result = D->getAvailability(&Message);<br>
+ Result = D->getAvailability(&Message, ContextVersion);<br>
}<br>
}<br>
<br>
@@ -136,7 +141,7 @@ DiagnoseAvailabilityOfDecl(Sema &S, Name<br>
if (Result == AR_Available) {<br>
const DeclContext *DC = ECD->getDeclContext();<br>
if (const EnumDecl *TheEnumDecl = dyn_cast<EnumDecl>(DC))<br>
- Result = TheEnumDecl->getAvailability(&Message);<br>
+ Result = TheEnumDecl->getAvailability(&Message, ContextVersion);<br>
}<br>
<br>
const ObjCPropertyDecl *ObjCPDecl = nullptr;<br>
@@ -144,7 +149,8 @@ DiagnoseAvailabilityOfDecl(Sema &S, Name<br>
Result == AR_NotYetIntroduced) {<br>
if (const ObjCMethodDecl *MD = dyn_cast<ObjCMethodDecl>(D)) {<br>
if (const ObjCPropertyDecl *PD = MD->findPropertyDecl()) {<br>
- AvailabilityResult PDeclResult = PD->getAvailability(nullptr);<br>
+ AvailabilityResult PDeclResult =<br>
+ PD->getAvailability(nullptr, ContextVersion);<br>
if (PDeclResult == Result)<br>
ObjCPDecl = PD;<br>
}<br>
@@ -198,7 +204,7 @@ DiagnoseAvailabilityOfDecl(Sema &S, Name<br>
break;<br>
<br>
}<br>
- return Result;<br>
+ return Result;<br>
}<br>
<br>
/// \brief Emit a note explaining that this function is deleted.<br>
<br>
Modified: cfe/trunk/test/SemaObjC/attr-availability.m<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/cfe/trunk/test/SemaObjC/attr-availability.m?rev=277175&r1=277174&r2=277175&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/cfe/trunk/test/SemaObjC/attr-availability.m?rev=277175&r1=277174&r2=277175&view=diff</a><br>
==============================================================================<br>
--- cfe/trunk/test/SemaObjC/attr-availability.m (original)<br>
+++ cfe/trunk/test/SemaObjC/attr-availability.m Fri Jul 29 12:37:38 2016<br>
@@ -294,3 +294,34 @@ __attribute__((objc_root_class))<br>
[obj method]; // expected-error{{'method' is unavailable}}<br>
}<br>
@end<br>
+<br>
+#if defined(WARN_PARTIAL)<br>
+<br>
+int fn_10_7() __attribute__((availability(macosx, introduced=10.7))); // expected-note{{marked partial here}}<br>
+int fn_10_8() __attribute__((availability(macosx, introduced=10.8))) { // expected-note{{marked partial here}}<br>
+ return fn_10_7();<br>
+}<br>
+<br>
+__attribute__((objc_root_class))<br>
+@interface LookupAvailabilityBase<br>
+-(void) method1;<br>
+@end<br>
+<br>
+@implementation LookupAvailabilityBase<br>
+-(void)method1 { fn_10_7(); } // expected-warning{{partial}} expected-note{{explicitly redeclare}}<br>
+@end<br>
+<br>
+__attribute__((availability(macosx, introduced=10.7)))<br>
+@interface LookupAvailability : LookupAvailabilityBase<br>
+- (void)method2;<br>
+- (void)method3;<br>
+- (void)method4 __attribute__((availability(macosx, introduced=10.8)));<br>
+@end<br>
+<br>
+@implementation LookupAvailability<br>
+-(void)method2 { fn_10_7(); }<br>
+-(void)method3 { fn_10_8(); } // expected-warning{{partial}} expected-note{{explicitly redeclare}}<br>
+-(void)method4 { fn_10_8(); }<br>
+@end<br>
+<br>
+#endif<br>
<br>
<br>
_______________________________________________<br>
cfe-commits mailing list<br>
<a href="mailto:cfe-commits@lists.llvm.org">cfe-commits@lists.llvm.org</a><br>
<a href="http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits" rel="noreferrer" target="_blank">http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits</a><br>
</blockquote></div><br></div>