]> granicus.if.org Git - clang/commitdiff
Allow cpu-dispatch forward declarations.
authorErich Keane <erich.keane@intel.com>
Wed, 28 Nov 2018 21:54:04 +0000 (21:54 +0000)
committerErich Keane <erich.keane@intel.com>
Wed, 28 Nov 2018 21:54:04 +0000 (21:54 +0000)
As a followup to r347805, allow forward declarations of cpu-dispatch and
cpu-specific for the same reasons.

Change-Id: Ic1bde9be369b1f8f1d47d58e6fbdc2f9dfcdd785

git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@347812 91177308-0d34-0410-b5e6-96231b3b80d8

lib/Sema/SemaDecl.cpp
test/CodeGen/attr-cpuspecific.c
test/Sema/attr-cpuspecific.c

index 8ccd9ae322b7eaee25983b37332889e0f19a9cca..5b2d2899f81103fb6aa530352b794803a8a9cefc 100644 (file)
@@ -9822,6 +9822,15 @@ static bool CheckMultiVersionAdditionalDecl(
     return true;
   }
 
+  // Permit forward declarations in the case where these two are compatible.
+  if (!OldFD->isMultiVersion()) {
+    OldFD->setIsMultiVersion();
+    NewFD->setIsMultiVersion();
+    Redeclaration = true;
+    OldDecl = OldFD;
+    return false;
+  }
+
   NewFD->setIsMultiVersion();
   Redeclaration = false;
   MergeTypeWithPrevious = false;
@@ -9896,14 +9905,6 @@ static bool CheckMultiVersionFunction(Sema &S, FunctionDecl *NewFD,
     return CheckTargetCausesMultiVersioning(S, OldFD, NewFD, NewTA,
                                             Redeclaration, OldDecl,
                                             MergeTypeWithPrevious, Previous);
-  // Previous declarations lack CPUDispatch/CPUSpecific.
-  if (!OldFD->isMultiVersion()) {
-    S.Diag(OldFD->getLocation(), diag::err_multiversion_required_in_redecl)
-        << 1;
-    S.Diag(NewFD->getLocation(), diag::note_multiversioning_caused_here);
-    NewFD->setInvalidDecl();
-    return true;
-  }
 
   // At this point, we have a multiversion function decl (in OldFD) AND an
   // appropriate attribute in the current function decl.  Resolve that these are
index 57a0ebebf2568e9cb1a01a85cc075140718d12b3..d6c99648cb7d8a1312b1618434d4de80095f2a1b 100644 (file)
@@ -23,7 +23,10 @@ void NotCalled(void){}
 // LINUX: define void @NotCalled.S() #[[S]]
 // WINDOWS: define dso_local void @NotCalled.S() #[[S:[0-9]+]]
 
-// Done before any of the implementations.
+// Done before any of the implementations.  Also has an undecorated forward
+// declaration.
+void TwoVersions(void);
+
 ATTR(cpu_dispatch(ivybridge, knl))
 void TwoVersions(void);
 // LINUX: define void ()* @TwoVersions.resolver()
index 91063c1c5b8aab98c5cd7007945503fbf8742421..4d21a8c894d26876ab4119a036d09905fe3142cd 100644 (file)
@@ -37,10 +37,8 @@ int __attribute__((cpu_dispatch(atom))) redecl2(void) { }
 // expected-note@-2 {{previous definition is here}}
 int __attribute__((cpu_dispatch(atom))) redecl2(void) { }
 
-int redecl3(void);
-// expected-error@-1 {{function declaration is missing 'cpu_specific' or 'cpu_dispatch' attribute in a multiversioned function}}
-// expected-note@+1 {{function multiversioning caused by this declaration}}
-int __attribute__((cpu_dispatch(atom))) redecl3(void) {}
+int allow_fwd_decl(void);
+int __attribute__((cpu_dispatch(atom))) allow_fwd_decl(void) {}
 
 int __attribute__((cpu_specific(atom))) redecl4(void);
 // expected-error@+1 {{function declaration is missing 'cpu_specific' or 'cpu_dispatch' attribute in a multiversioned function}}