]> granicus.if.org Git - clang/commitdiff
Delay linkage checks when validating the weakref attribute.
authorRafael Espindola <rafael.espindola@gmail.com>
Wed, 16 Jan 2013 23:49:06 +0000 (23:49 +0000)
committerRafael Espindola <rafael.espindola@gmail.com>
Wed, 16 Jan 2013 23:49:06 +0000 (23:49 +0000)
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@172678 91177308-0d34-0410-b5e6-96231b3b80d8

lib/Sema/SemaDecl.cpp
lib/Sema/SemaDeclAttr.cpp
test/SemaCXX/attr-weakref.cpp

index 0316654660683acdbc5e3cdb1775e857e4fe9d10..b85e94bce8fd7cd9d7735aa8ffe7f01b4c79e4da 100644 (file)
@@ -4314,10 +4314,17 @@ bool Sema::inferObjCARCLifetime(ValueDecl *decl) {
 
 static void checkAttributesAfterMerging(Sema &S, NamedDecl &ND) {
   // 'weak' only applies to declarations with external linkage.
-  WeakAttr *WA = ND.getAttr<WeakAttr>();
-  if (WA && ND.getLinkage() != ExternalLinkage) {
-    S.Diag(WA->getLocation(), diag::err_attribute_weak_static);
-    ND.dropAttr<WeakAttr>();
+  if (WeakAttr *Attr = ND.getAttr<WeakAttr>()) {
+    if (ND.getLinkage() != ExternalLinkage) {
+      S.Diag(Attr->getLocation(), diag::err_attribute_weak_static);
+      ND.dropAttr<WeakAttr>();
+    }
+  }
+  if (WeakRefAttr *Attr = ND.getAttr<WeakRefAttr>()) {
+    if (ND.getLinkage() == ExternalLinkage) {
+      S.Diag(Attr->getLocation(), diag::err_attribute_weakref_not_static);
+      ND.dropAttr<WeakRefAttr>();
+    }
   }
 }
 
index 5f9516f70ee16f3ec38cee0895fada2dc059e09d..acd075ee7fb329efcd7855ee494200c7ac9392d5 100644 (file)
@@ -1420,11 +1420,6 @@ static void handleWeakRefAttr(Sema &S, Decl *D, const AttributeList &Attr) {
   // This looks like a bug in gcc. We reject that for now. We should revisit
   // it if this behaviour is actually used.
 
-  if (nd->getLinkage() == ExternalLinkage) {
-    S.Diag(Attr.getLoc(), diag::err_attribute_weakref_not_static);
-    return;
-  }
-
   // GCC rejects
   // static ((alias ("y"), weakref)).
   // Should we? How to check that weakref is before or after alias?
@@ -4583,7 +4578,8 @@ void Sema::ProcessDeclAttributeList(Scope *S, Decl *D,
   // but that looks really pointless. We reject it.
   if (Inheritable && D->hasAttr<WeakRefAttr>() && !D->hasAttr<AliasAttr>()) {
     Diag(AttrList->getLoc(), diag::err_attribute_weakref_without_alias) <<
-    dyn_cast<NamedDecl>(D)->getNameAsString();
+    cast<NamedDecl>(D)->getNameAsString();
+    D->dropAttr<WeakRefAttr>();
     return;
   }
 }
index a34579198fef5021b641a37c8662a661476aaf8d..f3d7a6241c91d6fcf2eab6c3e394f88f8719d918 100644 (file)
@@ -28,4 +28,7 @@ int a7() __attribute__((weakref ("f1"))); // expected-error {{weakref declaratio
 int a8 __attribute__((weakref ("v1"))); // expected-error {{weakref declaration must have internal linkage}}
 
 // gcc accepts this
-int a9 __attribute__((weakref)); // expected-error {{weakref declaration must have internal linkage}}
+int a9 __attribute__((weakref));  // expected-error {{weakref declaration of 'a9' must also have an alias attribute}}
+
+static int a10();
+int a10() __attribute__((weakref ("foo")));