[PATCH] D43576: Solution to fix PR27066 - Redefinition with same mangled name as another definition (dllexport and uuid)

2018-05-14 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 146642.

https://reviews.llvm.org/D43576

Files:
  include/clang/AST/Decl.h
  include/clang/AST/RecursiveASTVisitor.h
  include/clang/Basic/Attr.td
  include/clang/Basic/DeclNodes.td
  include/clang/Sema/AttributeList.h
  include/clang/Sema/Sema.h
  lib/AST/Decl.cpp
  lib/AST/DeclBase.cpp
  lib/AST/DeclCXX.cpp
  lib/CodeGen/CGDecl.cpp
  lib/Parse/ParseDecl.cpp
  lib/Sema/SemaDecl.cpp
  lib/Sema/SemaDeclAttr.cpp
  lib/Sema/SemaExprCXX.cpp
  lib/Sema/SemaTemplateInstantiateDecl.cpp
  lib/Serialization/ASTCommon.cpp
  test/SemaCXX/ms-uuid-1.cpp
  utils/TableGen/ClangAttrEmitter.cpp

Index: utils/TableGen/ClangAttrEmitter.cpp
===
--- utils/TableGen/ClangAttrEmitter.cpp
+++ utils/TableGen/ClangAttrEmitter.cpp
@@ -322,12 +322,15 @@
 OS << "\" << get" << getUpperName() << "().getAsString() << \"";
   else if (type == "ParamIdx")
 OS << "\" << get" << getUpperName() << "().getSourceIndex() << \"";
-  else
+  else if (type == "DeclSpecUuidDecl *") {
+OS << "\" << get" << getUpperName() << "() << \"";
+	} else
 OS << "\" << get" << getUpperName() << "() << \"";
 }
 
 void writeDump(raw_ostream &OS) const override {
-  if (type == "FunctionDecl *" || type == "NamedDecl *") {
+  if (type == "FunctionDecl *" || type == "NamedDecl *" ||
+	  (type == "DeclSpecUuidDecl *")) {
 OS << "OS << \" \";\n";
 OS << "dumpBareDeclRef(SA->get" << getUpperName() << "());\n"; 
   } else if (type == "IdentifierInfo *") {
@@ -1280,6 +1283,8 @@
 Ptr = llvm::make_unique(Arg, Attr, "ParamIdx");
   else if (ArgName == "VersionArgument")
 Ptr = llvm::make_unique(Arg, Attr);
+  else if (ArgName == "DeclSpecUuidDeclArgument")
+Ptr = llvm::make_unique(Arg, Attr, "DeclSpecUuidDecl *");
 
   if (!Ptr) {
 // Search in reverse order so that the most-derived type is handled first.
Index: test/SemaCXX/ms-uuid-1.cpp
===
--- /dev/null
+++ test/SemaCXX/ms-uuid-1.cpp
@@ -0,0 +1,31 @@
+// RUN: %clang_cc1 -fms-extensions -fms-compatibility -std=c++14 -emit-obj -fdiagnostics-show-option %s
+// expected-no-diagnostics
+typedef struct _GUID {
+  int i;
+} IID;
+template 
+class A {};
+
+struct
+__declspec(uuid("{DDB47A6A-0F23-11D5-9109-00E0296B75D3}"))
+S1 {};
+
+struct
+__declspec(uuid("{DDB47A6A-0F23-11D5-9109-00E0296B75D3}"))
+S2 {};
+
+struct __declspec(dllexport)
+C1 : public A<&__uuidof(S1)> {};
+
+struct __declspec(dllexport)
+C2 : public A<&__uuidof(S2)> {};
+int printf(const char *, ...);
+int main() {
+
+  if (&__uuidof(S1) == &__uuidof(S2))
+printf("OK\n");
+  else
+printf("ERROR\n");
+
+  return 0;
+}
Index: lib/Serialization/ASTCommon.cpp
===
--- lib/Serialization/ASTCommon.cpp
+++ lib/Serialization/ASTCommon.cpp
@@ -272,6 +272,7 @@
   case Decl::ObjCProtocol:
   case Decl::ObjCInterface:
   case Decl::Empty:
+  case Decl::DeclSpecUuid:
 return true;
 
   // Never redeclarable.
Index: lib/Sema/SemaTemplateInstantiateDecl.cpp
===
--- lib/Sema/SemaTemplateInstantiateDecl.cpp
+++ lib/Sema/SemaTemplateInstantiateDecl.cpp
@@ -535,6 +535,15 @@
   return Inst;
 }
 
+Decl *
+TemplateDeclInstantiator::VisitDeclSpecUuidDecl(DeclSpecUuidDecl *D) {
+  DeclSpecUuidDecl *Inst = DeclSpecUuidDecl::Create(SemaRef.Context, Owner,
+D->getLocation(),
+D->getStrUuid());
+  Owner->addDecl(Inst);
+  return Inst;
+}
+
 Decl *TemplateDeclInstantiator::InstantiateTypedefNameDecl(TypedefNameDecl *D,
bool IsTypeAlias) {
   bool Invalid = false;
Index: lib/Sema/SemaExprCXX.cpp
===
--- lib/Sema/SemaExprCXX.cpp
+++ lib/Sema/SemaExprCXX.cpp
@@ -566,20 +566,66 @@
   }
 }
 
+/// Find the uuid of a type.
+static void
+FindStrUuid(Sema &SemaRef, QualType QT,
+	llvm::SmallVector &StrUuid) {
+  const Type *Ty = QT.getTypePtr();
+  if (QT->isPointerType() || QT->isReferenceType())
+Ty = QT->getPointeeType().getTypePtr();
+  else if (QT->isArrayType())
+Ty = Ty->getBaseElementTypeUnsafe();
+
+  const auto *TD = Ty->getAsTagDecl();
+  if (!TD) {
+return;
+  }
+  const Decl* dd =
+TD->getPreviousDecl() ? TD->getPreviousDecl() :
+TD->getMostRecentDecl();
+  auto str = SemaRef.DeclSpecToStrUuid.find(dd);
+  if (str != SemaRef.DeclSpecToStrUuid.end()) {
+StrUuid.push_back(str->second);
+return;
+  }
+
+  if (const auto *CTSD = dyn_cast(TD)) {
+const TemplateArgumentList &TAL = CTSD->getTemplateArgs();
+for (const TemplateArgument &TA : TAL.asArray()) {
+  if (TA.get

[PATCH] D43576: Solution to fix PR27066 - Redefinition with same mangled name as another definition (dllexport and uuid)

2018-02-22 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 135502.

https://reviews.llvm.org/D43576

Files:
  test/CodeGenCXX/instantiate-uuid.cpp
  test/Sema/member-reference-dll.cpp


Index: test/Sema/member-reference-dll.cpp
===
--- test/Sema/member-reference-dll.cpp
+++ /dev/null
@@ -1,24 +0,0 @@
-// RUN: %clang_cc1 -triple x86_64-windows-msvc -fsyntax-only -verify 
-fms-extensions -fms-compatibility %s
-// expected-no-diagnostics
-
-namespace test1 {
-class __declspec(dllimport) Edge;
-
-template 
-class __declspec(dllimport) Range {
-  void insert(T *obj) { obj->loc(); }
-};
-
-template void Range::insert(Edge *);
-} // namespace test1
-
-namespace test2 {
-class __declspec(dllexport) Edge;
-
-template 
-class __declspec(dllimport) Range {
-  void insert(T *obj) { obj->loc(); }
-};
-
-template void Range::insert(Edge *);
-} // namespace test2
Index: test/CodeGenCXX/instantiate-uuid.cpp
===
--- /dev/null
+++ test/CodeGenCXX/instantiate-uuid.cpp
@@ -0,0 +1,29 @@
+// RUN: %clang_cc1 -triple x86_64-pc-windows-msvc -std=c++14 -fms-extensions 
-fms-compatibility -emit-llvm -o - %s | Filecheck %s
+
+// expected-no-diagnostics
+
+// M32-DAG: 
$"\01??4?$A@$E?_GUID_ddb47a6a_0f23_11d5_9109_00e0296b75d3@@3U__s_GUID@@B@@QEAAAEAV0@AEBV0@@Z"
 = comdat any
+
+typedef struct _GUID {
+  int i;
+} IID;
+template 
+class A {};
+
+struct
+__declspec(uuid("{DDB47A6A-0F23-11D5-9109-00E0296B75D3}"))
+S1 {};
+
+struct
+__declspec(uuid("{DDB47A6A-0F23-11D5-9109-00E0296B75D3}"))
+S2 {};
+
+struct __declspec(dllexport)
+C1 : public A<&__uuidof(S1)> {};
+
+struct __declspec(dllexport)
+C2 : public A<&__uuidof(S2)> {};
+
+// CHECK-LABEL: define weak_odr dllexport dereferenceable(1) %class.A* 
@"\01??4?$A@$E?_GUID_ddb47a6a_0f23_11d5_9109_00e0296b75d3@@3U__s_GUID@@B@@QEAAAEAV0@AEBV0@@Z"
+
+


Index: test/Sema/member-reference-dll.cpp
===
--- test/Sema/member-reference-dll.cpp
+++ /dev/null
@@ -1,24 +0,0 @@
-// RUN: %clang_cc1 -triple x86_64-windows-msvc -fsyntax-only -verify -fms-extensions -fms-compatibility %s
-// expected-no-diagnostics
-
-namespace test1 {
-class __declspec(dllimport) Edge;
-
-template 
-class __declspec(dllimport) Range {
-  void insert(T *obj) { obj->loc(); }
-};
-
-template void Range::insert(Edge *);
-} // namespace test1
-
-namespace test2 {
-class __declspec(dllexport) Edge;
-
-template 
-class __declspec(dllimport) Range {
-  void insert(T *obj) { obj->loc(); }
-};
-
-template void Range::insert(Edge *);
-} // namespace test2
Index: test/CodeGenCXX/instantiate-uuid.cpp
===
--- /dev/null
+++ test/CodeGenCXX/instantiate-uuid.cpp
@@ -0,0 +1,29 @@
+// RUN: %clang_cc1 -triple x86_64-pc-windows-msvc -std=c++14 -fms-extensions -fms-compatibility -emit-llvm -o - %s | Filecheck %s
+
+// expected-no-diagnostics
+
+// M32-DAG: $"\01??4?$A@$E?_GUID_ddb47a6a_0f23_11d5_9109_00e0296b75d3@@3U__s_GUID@@B@@QEAAAEAV0@AEBV0@@Z" = comdat any
+
+typedef struct _GUID {
+  int i;
+} IID;
+template 
+class A {};
+
+struct
+__declspec(uuid("{DDB47A6A-0F23-11D5-9109-00E0296B75D3}"))
+S1 {};
+
+struct
+__declspec(uuid("{DDB47A6A-0F23-11D5-9109-00E0296B75D3}"))
+S2 {};
+
+struct __declspec(dllexport)
+C1 : public A<&__uuidof(S1)> {};
+
+struct __declspec(dllexport)
+C2 : public A<&__uuidof(S2)> {};
+
+// CHECK-LABEL: define weak_odr dllexport dereferenceable(1) %class.A* @"\01??4?$A@$E?_GUID_ddb47a6a_0f23_11d5_9109_00e0296b75d3@@3U__s_GUID@@B@@QEAAAEAV0@AEBV0@@Z"
+
+
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D43576: Solution to fix PR27066 - Redefinition with same mangled name as another definition (dllexport and uuid)

2018-02-22 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added a comment.

Adding test case.


https://reviews.llvm.org/D43576



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D43576: Solution to fix PR27066 - Redefinition with same mangled name as another definition (dllexport and uuid)

2018-02-22 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added a comment.

In https://reviews.llvm.org/D43576#1016295, @majnemer wrote:

> We should really, really avoid making this sort of change without first 
> trying to desugar uuidof into a reference to a variable. That would solve a 
> ton of problems, problems like this one.


Not sure I fully understand what you are proposing?

Are you proposing that generated symbols like this:
??4?$A@$E?_GUID_ddb47a6a_0f23_11d5_9109_00e0296b75d3@@3U__s_GUID@@B@@QEAAAEAV0@AEBV0@@Z
 
Be de-sugared? Wouldn't that be different that what MS is doing? 
Can you please give me more details about what you are thinking of?
Thanks.


https://reviews.llvm.org/D43576



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D43576: Solution to fix PR27066 - Redefinition with same mangled name as another definition (dllexport and uuid)

2018-02-26 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added a comment.

In https://reviews.llvm.org/D43576#1016588, @rsmith wrote:

> In https://reviews.llvm.org/D43576#1016561, @majnemer wrote:
>
> > Here's my thinking: the `__uuidof` expression literally declares a variable 
> > called `_GUID_ddb47a6a_0f23_11d5_9109_00e0296b75d3` of type `__s_GUID` 
> > which is why it behaves the way it does: https://godbolt.org/g/74FY7U
>
>
> This is an implementation detail leaking, though. no? Note that that is a 
> reserved name.
>
> > I don't think it is reasonable to invent new semantics which are different 
> > from the MSVC ones because we find the MSVC ones inelegant.
>
> I mostly agree, but my point is that this is *not* the MSVC semantics, it's 
> merely an implementation detail that non-conforming code happens to be able 
> to observe. Suppose that `type_info` objects were similarly accessible in 
> MSVC by guessing their mangled names. Would you be arguing that we should 
> inject variables for those too? (And note that it is *nearly* true that 
> `type_info` objects work that way: https://godbolt.org/g/zByFFg -- but the 
> parser gets confused somehow when you reference them.) The only difference I 
> can see between these cases is that the reserved name used for the GUID case 
> happens to not contain any ?s and @s, so happens to be utterable as an 
> identifier.
>
> We should not attempt to be compatible with the cases where MSVC's 
> implementation details happen to leak into user-visible semantics.
>
> > What is the relative upside to a new kind of Decl? Better AST fidelity?
>
> Yes, exactly. The same reason we don't desguar other things any more than we 
> have to.


Before I start implementing this I want to make sure that we are on the same 
page on this.
From your comments it looks like we do not want to create global variables for 
the uuid globals. I tend to agree with that. I do like the idea of creating a 
new Decl type for the uuid declspec. But I want to make sure that I understand 
what you are referring to.
Currently this declaration:
struct
__declspec(uuid("{DDB47A6A-0F23-11D5-9109-00E0296B75D3}"))
S1;

a CXXRecordDecl type is generated with attributes (the uuid being an 
attribute). Are you proposing that instead a new type is generated for S1 say 
something like CXXUuidRecord? And create also a new TagType that corresponds to 
this new Decl?


https://reviews.llvm.org/D43576



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D44505: [MS] Always use base dtors in place of complete/vbase dtors when possible

2018-03-16 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added a comment.

LGTM 2. It fixes PR32990.


https://reviews.llvm.org/D44505



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D45978: dllexport const variables must have external linkage.

2019-01-26 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam marked an inline comment as done.
zahiraam added a comment.

Aaron,

Please advise. 
Thanks.




Comment at: test/Sema/dllexport.c:70
+// const variables
+__declspec(dllexport) int const x = 3;
 

aaron.ballman wrote:
> Can you think of any redeclaration scenarios we should also test? e.g., weird 
> cases like this:
> ```
> extern int const x;
> __declspec(dllexport) int const x = 3;
> ```
> which brings up an interesting question -- does MSVC truly treat it as though 
> it were extern, or just only-kinda-sorta treat it like it was extern? e.g., 
> can you do this:
> ```
> __declspec(dllexport) const int j;
> ```
> Regardless, having some codegen tests demonstrating that the variable has the 
> correct semantics that we're emulating would be nice.
With MSVC:

ksh-3.2$ cat t2.cpp
__declspec(dllexport) const int j;
ksh-3.2$

ksh-3.2$ cl -c t2.cpp
Microsoft (R) C/C++ Optimizing Compiler Version 19.00.24210 for x64
Copyright (C) Microsoft Corporation.  All rights reserved.

t2.cpp
t2.cpp(1): error C2734: 'j': 'const' object must be initialized if not 'extern'

ksh-3.2$ cat t3.cpp
__declspec(dllexport) int const x = 3;
int main ()
{
  int y = x + 10;

  return y;
}

ksh-3.2$ cl -c t3.cpp
Microsoft (R) C/C++ Optimizing Compiler Version 19.00.24210 for x64
Copyright (C) Microsoft Corporation.  All rights reserved.

t3.cpp
ksh-3.2$ dumpbin /symbols t3.obj | grep External
**008  SECT3  notype ()External | main**
ksh-3.2$
ksh-3.2$ cat t4.cpp
extern int const x = 3;
int main ()
{
  int y = x + 10;

  return y;
}

ksh-3.2$ cl -c t4.cpp
Microsoft (R) C/C++ Optimizing Compiler Version 19.00.24210 for x64
Copyright (C) Microsoft Corporation.  All rights reserved.

t4.cpp
ksh-3.2$ dumpbin /symbols t4.obj | grep External
**008  SECT3  notype   External | ?x@@3HB (int const x)
00B  SECT4  notype ()External | main**
ksh-3.2$

So we see that with dllexport, the ony symbol marked with "External" is main. 
With "extern" both main and x are marked as External.

With clang without the patch:
ksh-3.2$ clang -c t2.cpp
t2.cpp:1:33: error: default initialization of an object of const type 'const 
int'
__declspec(dllexport) const int j;
^
  = 0
t2.cpp:1:33: error: 'j' must have external linkage when declared 'dllexport'
2 errors generated.
ksh-3.2$
ksh-3.2$ clang -c t3.cpp
t3.cpp:1:33: error: 'x' must have external linkage when declared 'dllexport'
__declspec(dllexport) int const x = 3;
^
1 error generated.
ksh-3.2$ clang -c t4.cpp
ksh-3.2$ dumpbin /symbols t4.o | grep External
**00F  SECT1  notype ()External | main
010  SECT5  notype   External | ?x@@3HB (int const x)**
ksh-3.2$

Clang with patch above at the right place (I am thinking in  
Sema::AddInitializerToDecl):

ksh-3.2$ clang -c t3.cpp
ksh-3.2$ dumpbin /symbols t3.o | grep External
**00E  SECT1  notype ()External | main
00F  SECT5  notype   External | ?x@@3HB (int const x)**
ksh-3.2$
ksh-3.2$ clang -c t4.cpp
ksh-3.2$ dumpbin /symbols t4.o | grep External
00C  SECT1  notype ()External | main
00D  SECT5  notype   External | ?x@@3HB (int const x)
ksh-3.2$

Both MSVC and clang have the same behavior with t2.cpp.
With the patch clang will have the same beahvior than MSVC when extern and 
dllexport are used. That's not  quite what MSVC's behavior is!
What are your thoughts?
Thanks.




CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D45978/new/

https://reviews.llvm.org/D45978



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D45978: dllexport const variables must have external linkage.

2019-03-07 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 189659.
zahiraam marked 3 inline comments as done.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D45978/new/

https://reviews.llvm.org/D45978

Files:
  lib/Sema/SemaDecl.cpp
  test/CodeGen/dllexport-1.c
  test/Sema/dllexport-1.cpp
  test/Sema/dllexport-2.cpp
  test/SemaCXX/dllexport.cpp
  test/SemaCXX/dllimport.cpp

Index: test/SemaCXX/dllimport.cpp
===
--- test/SemaCXX/dllimport.cpp
+++ test/SemaCXX/dllimport.cpp
@@ -121,7 +121,12 @@
 // External linkage is required.
 __declspec(dllimport) static int StaticGlobal; // expected-error{{'StaticGlobal' must have external linkage when declared 'dllimport'}}
 __declspec(dllimport) Internal InternalTypeGlobal; // expected-error{{'InternalTypeGlobal' must have external linkage when declared 'dllimport'}}
-namespace{ __declspec(dllimport) int InternalGlobal; } // expected-error{{'(anonymous namespace)::InternalGlobal' must have external linkage when declared 'dllimport'}}
+#ifdef MS
+// expected-nodiagnostics
+#else
+// expected-error@+1{{'(anonymous namespace)::InternalGlobal' must have external linkage when declared 'dllimport'}}
+namespace{ __declspec(dllimport) int InternalGlobal; }
+#endif
 namespace ns { __declspec(dllimport) int ExternalGlobal; }
 
 __declspec(dllimport) auto InternalAutoTypeGlobal = Internal(); // expected-error{{'InternalAutoTypeGlobal' must have external linkage when declared 'dllimport'}}
@@ -213,7 +218,12 @@
 // External linkage is required.
 template __declspec(dllimport) static int StaticVarTmpl; // expected-error{{'StaticVarTmpl' must have external linkage when declared 'dllimport'}}
 template __declspec(dllimport) Internal InternalTypeVarTmpl; // expected-error{{'InternalTypeVarTmpl' must have external linkage when declared 'dllimport'}}
-namespace{ template __declspec(dllimport) int InternalVarTmpl; } // expected-error{{'(anonymous namespace)::InternalVarTmpl' must have external linkage when declared 'dllimport'}}
+#ifdef MS
+// expected-nodiagnostics
+#else
+// expected-error@+2{{'(anonymous namespace)::InternalVarTmpl' must have external linkage when declared 'dllimport'}}
+#endif
+namespace{ template __declspec(dllimport) int InternalVarTmpl; }
 namespace ns { template __declspec(dllimport) int ExternalVarTmpl; }
 
 template __declspec(dllimport) auto InternalAutoTypeVarTmpl = Internal(); // expected-error{{definition of dllimport data}} // expected-error{{'InternalAutoTypeVarTmpl' must have external linkage when declared 'dllimport'}}
Index: test/SemaCXX/dllexport.cpp
===
--- test/SemaCXX/dllexport.cpp
+++ test/SemaCXX/dllexport.cpp
@@ -69,7 +69,12 @@
 // External linkage is required.
 __declspec(dllexport) static int StaticGlobal; // expected-error{{'StaticGlobal' must have external linkage when declared 'dllexport'}}
 __declspec(dllexport) Internal InternalTypeGlobal; // expected-error{{'InternalTypeGlobal' must have external linkage when declared 'dllexport'}}
-namespace{ __declspec(dllexport) int InternalGlobal; } // expected-error{{'(anonymous namespace)::InternalGlobal' must have external linkage when declared 'dllexport'}}
+#ifdef MS
+// expected-nodiagnostics
+#else
+// expected-error@+1{{anonymous namespace)::InternalGlobal' must have external linkage when declared 'dllexport'}}
+namespace{ __declspec(dllexport) int InternalGlobal; }
+#endif
 namespace ns { __declspec(dllexport) int ExternalGlobal; }
 
 __declspec(dllexport) auto InternalAutoTypeGlobal = Internal(); // expected-error{{'InternalAutoTypeGlobal' must have external linkage when declared 'dllexport'}}
@@ -124,7 +129,12 @@
 // External linkage is required.
 template __declspec(dllexport) static int StaticVarTmpl; // expected-error{{'StaticVarTmpl' must have external linkage when declared 'dllexport'}}
 template __declspec(dllexport) Internal InternalTypeVarTmpl; // expected-error{{'InternalTypeVarTmpl' must have external linkage when declared 'dllexport'}}
-namespace{ template __declspec(dllexport) int InternalVarTmpl; } // expected-error{{'(anonymous namespace)::InternalVarTmpl' must have external linkage when declared 'dllexport'}}
+#ifdef MS
+// expected-nodiagnostics
+#else
+// expected-error@+1{{anonymous namespace)::InternalVarTmpl' must have external linkage when declared 'dllexport'}}
+namespace{ template __declspec(dllexport) int InternalVarTmpl; }
+#endif
 namespace ns { template __declspec(dllexport) int ExternalVarTmpl = 1; }
 
 template __declspec(dllexport) auto InternalAutoTypeVarTmpl = Internal(); // expected-error{{'InternalAutoTypeVarTmpl' must have external linkage when declared 'dllexport'}}
Index: test/Sema/dllexport-2.cpp
===
--- /dev/null
+++ test/Sema/dllexport-2.cpp
@@ -0,0 +1,32 @@
+// RUN: %clang_cc1 -triple x86_64-pc-linux-gnu -fsyntax-only -fms-extensions -verify 

[PATCH] D45978: dllexport const variables must have external linkage.

2019-03-08 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added inline comments.



Comment at: lib/Sema/SemaDecl.cpp:5975-5977
+if ((!ND.isExternallyVisible() &&
+  (!isAnonymousNS || !(VD && VD->hasInit( ||
+  (VD && VD->isStaticLocal())) {

aaron.ballman wrote:
> This used to unconditionally warn, but now has predicates -- should this 
> still warn when not in MSVC mode?
Please see new version of code.


CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D45978/new/

https://reviews.llvm.org/D45978



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D45978: dllexport const variables must have external linkage.

2019-03-08 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 189843.
zahiraam marked 10 inline comments as done.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D45978/new/

https://reviews.llvm.org/D45978

Files:
  lib/Sema/SemaDecl.cpp
  test/CodeGen/dllexport-1.c
  test/Sema/dllexport-1.cpp
  test/Sema/dllexport-2.cpp
  test/SemaCXX/dllexport.cpp
  test/SemaCXX/dllimport.cpp

Index: test/SemaCXX/dllimport.cpp
===
--- test/SemaCXX/dllimport.cpp
+++ test/SemaCXX/dllimport.cpp
@@ -121,7 +121,9 @@
 // External linkage is required.
 __declspec(dllimport) static int StaticGlobal; // expected-error{{'StaticGlobal' must have external linkage when declared 'dllimport'}}
 __declspec(dllimport) Internal InternalTypeGlobal; // expected-error{{'InternalTypeGlobal' must have external linkage when declared 'dllimport'}}
+#ifndef MS
 namespace{ __declspec(dllimport) int InternalGlobal; } // expected-error{{'(anonymous namespace)::InternalGlobal' must have external linkage when declared 'dllimport'}}
+#endif
 namespace ns { __declspec(dllimport) int ExternalGlobal; }
 
 __declspec(dllimport) auto InternalAutoTypeGlobal = Internal(); // expected-error{{'InternalAutoTypeGlobal' must have external linkage when declared 'dllimport'}}
@@ -213,7 +215,9 @@
 // External linkage is required.
 template __declspec(dllimport) static int StaticVarTmpl; // expected-error{{'StaticVarTmpl' must have external linkage when declared 'dllimport'}}
 template __declspec(dllimport) Internal InternalTypeVarTmpl; // expected-error{{'InternalTypeVarTmpl' must have external linkage when declared 'dllimport'}}
+#ifndef MS
 namespace{ template __declspec(dllimport) int InternalVarTmpl; } // expected-error{{'(anonymous namespace)::InternalVarTmpl' must have external linkage when declared 'dllimport'}}
+#endif
 namespace ns { template __declspec(dllimport) int ExternalVarTmpl; }
 
 template __declspec(dllimport) auto InternalAutoTypeVarTmpl = Internal(); // expected-error{{definition of dllimport data}} // expected-error{{'InternalAutoTypeVarTmpl' must have external linkage when declared 'dllimport'}}
Index: test/SemaCXX/dllexport.cpp
===
--- test/SemaCXX/dllexport.cpp
+++ test/SemaCXX/dllexport.cpp
@@ -69,7 +69,9 @@
 // External linkage is required.
 __declspec(dllexport) static int StaticGlobal; // expected-error{{'StaticGlobal' must have external linkage when declared 'dllexport'}}
 __declspec(dllexport) Internal InternalTypeGlobal; // expected-error{{'InternalTypeGlobal' must have external linkage when declared 'dllexport'}}
+#ifndef MS
 namespace{ __declspec(dllexport) int InternalGlobal; } // expected-error{{'(anonymous namespace)::InternalGlobal' must have external linkage when declared 'dllexport'}}
+#endif
 namespace ns { __declspec(dllexport) int ExternalGlobal; }
 
 __declspec(dllexport) auto InternalAutoTypeGlobal = Internal(); // expected-error{{'InternalAutoTypeGlobal' must have external linkage when declared 'dllexport'}}
@@ -124,7 +126,9 @@
 // External linkage is required.
 template __declspec(dllexport) static int StaticVarTmpl; // expected-error{{'StaticVarTmpl' must have external linkage when declared 'dllexport'}}
 template __declspec(dllexport) Internal InternalTypeVarTmpl; // expected-error{{'InternalTypeVarTmpl' must have external linkage when declared 'dllexport'}}
+#ifndef MS
 namespace{ template __declspec(dllexport) int InternalVarTmpl; } // expected-error{{'(anonymous namespace)::InternalVarTmpl' must have external linkage when declared 'dllexport'}}
+#endif
 namespace ns { template __declspec(dllexport) int ExternalVarTmpl = 1; }
 
 template __declspec(dllexport) auto InternalAutoTypeVarTmpl = Internal(); // expected-error{{'InternalAutoTypeVarTmpl' must have external linkage when declared 'dllexport'}}
Index: test/Sema/dllexport-2.cpp
===
--- /dev/null
+++ test/Sema/dllexport-2.cpp
@@ -0,0 +1,30 @@
+// RUN: %clang_cc1 -triple x86_64-pc-linux-gnu -fsyntax-only -fms-extensions -verify %s
+// RUN: %clang_cc1 -triple x86_64-pc-windows-msvc -fsyntax-only -fms-extensions -verify %s -DMSVC
+
+// Export const variable.
+
+#ifdef MSVC
+// expected-error@+6 {{default initialization of an object of const type 'const int'}}
+// expected-error@+5 {{'j' must have external linkage when declared 'dllexport'}}
+#else
+// expected-warning@+3 {{__declspec attribute 'dllexport' is not supported}}
+// expected-error@+2 {{default initialization of an object of const type}}
+#endif
+__declspec(dllexport) int const j;
+
+// With typedef
+typedef const int CInt;
+
+#ifdef MSVC
+// expected-error@+6 {{default initialization of an object of const type 'CInt' (aka 'const int')}}
+// expected-error@+5 {{'j2' must have external linkage when declared 'dllexport'}}
+#else
+// expected-warning@+3 {{__declspec attribute 'dllexport' is not supported}}
+// expected-e

[PATCH] D45978: dllexport const variables must have external linkage.

2019-03-11 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam marked 6 inline comments as done.
zahiraam added inline comments.



Comment at: test/SemaCXX/dllexport.cpp:72-74
+#ifndef MS
 namespace{ __declspec(dllexport) int InternalGlobal; } // 
expected-error{{'(anonymous namespace)::InternalGlobal' must have external 
linkage when declared 'dllexport'}}
+#endif

aaron.ballman wrote:
> I don't have a copy of mingw handy -- can you test that this behavior matches 
> the behavior when targeting mingw32 with GCC? Might also be a good idea to 
> test cygwin as a target as well. I would have thought that they would behave 
> the same as MSVC, but I can't easily test it myself.
Tested it with a set of combinations. The test is passing... 


CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D45978/new/

https://reviews.llvm.org/D45978



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D45978: dllexport const variables must have external linkage.

2019-03-11 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 190124.
zahiraam marked an inline comment as done.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D45978/new/

https://reviews.llvm.org/D45978

Files:
  lib/Sema/SemaDecl.cpp
  test/CodeGen/dllexport-1.c
  test/Sema/dllexport-1.cpp
  test/Sema/dllexport-2.cpp
  test/SemaCXX/dllexport.cpp
  test/SemaCXX/dllimport.cpp

Index: test/SemaCXX/dllimport.cpp
===
--- test/SemaCXX/dllimport.cpp
+++ test/SemaCXX/dllimport.cpp
@@ -121,7 +121,9 @@
 // External linkage is required.
 __declspec(dllimport) static int StaticGlobal; // expected-error{{'StaticGlobal' must have external linkage when declared 'dllimport'}}
 __declspec(dllimport) Internal InternalTypeGlobal; // expected-error{{'InternalTypeGlobal' must have external linkage when declared 'dllimport'}}
+#ifndef MS
 namespace{ __declspec(dllimport) int InternalGlobal; } // expected-error{{'(anonymous namespace)::InternalGlobal' must have external linkage when declared 'dllimport'}}
+#endif
 namespace ns { __declspec(dllimport) int ExternalGlobal; }
 
 __declspec(dllimport) auto InternalAutoTypeGlobal = Internal(); // expected-error{{'InternalAutoTypeGlobal' must have external linkage when declared 'dllimport'}}
@@ -213,7 +215,9 @@
 // External linkage is required.
 template __declspec(dllimport) static int StaticVarTmpl; // expected-error{{'StaticVarTmpl' must have external linkage when declared 'dllimport'}}
 template __declspec(dllimport) Internal InternalTypeVarTmpl; // expected-error{{'InternalTypeVarTmpl' must have external linkage when declared 'dllimport'}}
+#ifndef MS
 namespace{ template __declspec(dllimport) int InternalVarTmpl; } // expected-error{{'(anonymous namespace)::InternalVarTmpl' must have external linkage when declared 'dllimport'}}
+#endif
 namespace ns { template __declspec(dllimport) int ExternalVarTmpl; }
 
 template __declspec(dllimport) auto InternalAutoTypeVarTmpl = Internal(); // expected-error{{definition of dllimport data}} // expected-error{{'InternalAutoTypeVarTmpl' must have external linkage when declared 'dllimport'}}
Index: test/SemaCXX/dllexport.cpp
===
--- test/SemaCXX/dllexport.cpp
+++ test/SemaCXX/dllexport.cpp
@@ -69,7 +69,9 @@
 // External linkage is required.
 __declspec(dllexport) static int StaticGlobal; // expected-error{{'StaticGlobal' must have external linkage when declared 'dllexport'}}
 __declspec(dllexport) Internal InternalTypeGlobal; // expected-error{{'InternalTypeGlobal' must have external linkage when declared 'dllexport'}}
+#ifndef MS
 namespace{ __declspec(dllexport) int InternalGlobal; } // expected-error{{'(anonymous namespace)::InternalGlobal' must have external linkage when declared 'dllexport'}}
+#endif
 namespace ns { __declspec(dllexport) int ExternalGlobal; }
 
 __declspec(dllexport) auto InternalAutoTypeGlobal = Internal(); // expected-error{{'InternalAutoTypeGlobal' must have external linkage when declared 'dllexport'}}
@@ -124,7 +126,9 @@
 // External linkage is required.
 template __declspec(dllexport) static int StaticVarTmpl; // expected-error{{'StaticVarTmpl' must have external linkage when declared 'dllexport'}}
 template __declspec(dllexport) Internal InternalTypeVarTmpl; // expected-error{{'InternalTypeVarTmpl' must have external linkage when declared 'dllexport'}}
+#ifndef MS
 namespace{ template __declspec(dllexport) int InternalVarTmpl; } // expected-error{{'(anonymous namespace)::InternalVarTmpl' must have external linkage when declared 'dllexport'}}
+#endif
 namespace ns { template __declspec(dllexport) int ExternalVarTmpl = 1; }
 
 template __declspec(dllexport) auto InternalAutoTypeVarTmpl = Internal(); // expected-error{{'InternalAutoTypeVarTmpl' must have external linkage when declared 'dllexport'}}
Index: test/Sema/dllexport-2.cpp
===
--- /dev/null
+++ test/Sema/dllexport-2.cpp
@@ -0,0 +1,26 @@
+// RUN: %clang_cc1 -triple x86_64-pc-linux-gnu -fsyntax-only -fms-extensions -verify %s
+// RUN: %clang_cc1 -triple x86_64-pc-windows-msvc -fsyntax-only -fms-extensions -verify %s -DMSVC
+
+// Export const variable.
+
+#ifdef MSVC
+// expected-error@+4 {{'j' must have external linkage when declared 'dllexport'}}
+#else
+// expected-warning@+2 {{__declspec attribute 'dllexport' is not supported}}
+#endif
+__declspec(dllexport) int const j; // expected-error {{default initialization of an object of const type 'const int'}}
+
+// With typedef
+typedef const int CInt;
+
+#ifdef MSVC
+// expected-error@+4 {{'j2' must have external linkage when declared 'dllexport'}}
+#else
+// expected-warning@+2 {{__declspec attribute 'dllexport' is not supported}}
+#endif
+__declspec(dllexport) CInt j2; //expected-error {{default initialization of an object of const type 'CInt'}}
+
+#ifndef MSVC
+// expected-warning@+2 {{__declspec attribute 'dllexport' is 

[PATCH] D45978: dllexport const variables must have external linkage.

2019-03-18 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added a comment.

In D45978#1431057 , @aaron.ballman 
wrote:

> LGTM!


Would you mind committing the changes please? Thanks.


CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D45978/new/

https://reviews.llvm.org/D45978



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D43576: Solution to fix PR27066 - Redefinition with same mangled name as another definition (dllexport and uuid)

2019-03-19 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added a comment.

It would be nice to have a review for this year old (updated) patch. Thanks.


CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D43576/new/

https://reviews.llvm.org/D43576



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D43576: Solution to fix PR27066 - Redefinition with same mangled name as another definition (dllexport and uuid)

2019-03-19 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 191371.
Herald added a subscriber: jdoerfert.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D43576/new/

https://reviews.llvm.org/D43576

Files:
  include/clang/AST/Decl.h
  include/clang/AST/RecursiveASTVisitor.h
  include/clang/Basic/Attr.td
  include/clang/Basic/DeclNodes.td
  include/clang/Sema/ParsedAttr.h
  include/clang/Sema/Sema.h
  lib/AST/Decl.cpp
  lib/AST/DeclBase.cpp
  lib/AST/DeclCXX.cpp
  lib/CodeGen/CGDecl.cpp
  lib/Parse/ParseDecl.cpp
  lib/Sema/SemaDecl.cpp
  lib/Sema/SemaDeclAttr.cpp
  lib/Sema/SemaExprCXX.cpp
  lib/Sema/SemaTemplateInstantiateDecl.cpp
  lib/Serialization/ASTCommon.cpp
  test/Parser/MicrosoftExtensions.cpp
  test/Parser/ms-square-bracket-attributes.mm
  test/Sema/ms-uuid-1.cpp
  utils/TableGen/ClangAttrEmitter.cpp

Index: utils/TableGen/ClangAttrEmitter.cpp
===
--- utils/TableGen/ClangAttrEmitter.cpp
+++ utils/TableGen/ClangAttrEmitter.cpp
@@ -321,12 +321,15 @@
 OS << "\" << get" << getUpperName() << "().getAsString() << \"";
   else if (type == "ParamIdx")
 OS << "\" << get" << getUpperName() << "().getSourceIndex() << \"";
-  else
+  else if (type == "DeclSpecUuidDecl *") {
+OS << "\" << get" << getUpperName() << "() << \"";
+  } else
 OS << "\" << get" << getUpperName() << "() << \"";
 }
 
 void writeDump(raw_ostream &OS) const override {
-  if (type == "FunctionDecl *" || type == "NamedDecl *") {
+  if (type == "FunctionDecl *" || type == "NamedDecl *" ||
+	  (type == "DeclSpecUuidDecl *")) {
 OS << "OS << \" \";\n";
 OS << "dumpBareDeclRef(SA->get" << getUpperName() << "());\n"; 
   } else if (type == "IdentifierInfo *") {
@@ -1296,6 +1299,8 @@
 Ptr = llvm::make_unique(Arg, Attr);
   else if (ArgName == "VersionArgument")
 Ptr = llvm::make_unique(Arg, Attr);
+  else if (ArgName == "DeclSpecUuidDeclArgument")
+Ptr = llvm::make_unique(Arg, Attr, "DeclSpecUuidDecl *");
 
   if (!Ptr) {
 // Search in reverse order so that the most-derived type is handled first.
Index: test/Sema/ms-uuid-1.cpp
===
--- /dev/null
+++ test/Sema/ms-uuid-1.cpp
@@ -0,0 +1,31 @@
+// RUN: %clang_cc1 -fms-extensions -fms-compatibility -std=c++14 -emit-obj -fdiagnostics-show-option %s
+// expected-no-diagnostics
+typedef struct _GUID {
+  int i;
+} IID;
+template 
+class A {};
+
+struct
+__declspec(uuid("{DDB47A6A-0F23-11D5-9109-00E0296B75D3}"))
+S1 {};
+
+struct
+__declspec(uuid("{DDB47A6A-0F23-11D5-9109-00E0296B75D3}"))
+S2 {};
+
+struct __declspec(dllexport)
+C1 : public A<&__uuidof(S1)> {};
+
+struct __declspec(dllexport)
+C2 : public A<&__uuidof(S2)> {};
+int printf(const char *, ...);
+int main() {
+
+  if (&__uuidof(S1) == &__uuidof(S2))
+printf("OK\n");
+  else
+printf("ERROR\n");
+
+  return 0;
+}
Index: test/Parser/ms-square-bracket-attributes.mm
===
--- test/Parser/ms-square-bracket-attributes.mm
+++ test/Parser/ms-square-bracket-attributes.mm
@@ -19,7 +19,7 @@
 // uuids must be ascii string literals.
 // expected-error@+1 {{uuid attribute contains a malformed GUID}}
 [uuid(u8"00A0---C000-0049")] struct struct_with_uuid_u8;
-// expected-error@+1 {{uuid attribute contains a malformed GUID}}
+// expected-error@+1 {{attribute requires a string}}
 [uuid(L"00A0---C000-0049")] struct struct_with_uuid_L;
 
 // cl.exe doesn't allow raw string literals in []-style attributes, but does
Index: test/Parser/MicrosoftExtensions.cpp
===
--- test/Parser/MicrosoftExtensions.cpp
+++ test/Parser/MicrosoftExtensions.cpp
@@ -76,7 +76,7 @@
struct_with_uuid var_with_uuid[1];
struct_without_uuid var_without_uuid[1];
 
-   __uuidof(struct_with_uuid);
+   __uuidof(struct_with_uuid); // expected-error {{non-type template argument of type 'const _GUID' is not a constant expression}}
__uuidof(struct_with_uuid2);
__uuidof(struct_with_uuid3);
__uuidof(struct_without_uuid); // expected-error {{cannot call operator __uuidof on a type with no GUID}}
@@ -137,7 +137,7 @@
 
 COM_CLASS_TEMPLATE_REF good_template_arg;
 
-COM_CLASS_TEMPLATE bad_template_arg; // expected-error {{non-type template argument of type 'const _GUID' is not a constant expression}}
+COM_CLASS_TEMPLATE bad_template_arg;
 
 namespace PR16911 {
 struct __declspec(uuid("{12345678-1234-1234-1234-1234567890aB}")) uuid;
Index: lib/Serialization/ASTCommon.cpp
===
--- lib/Serialization/ASTCommon.cpp
+++ lib/Serialization/ASTCommon.cpp
@@ -348,6 +348,7 @@
   case Decl::ObjCProtocol:
   case Decl::ObjCInterface:
   case Decl::Empty:
+  case Decl::DeclSpecUuid:
 return true;
 
   // Never redecla

[PATCH] D43576: Solution to fix PR27066 - Redefinition with same mangled name as another definition (dllexport and uuid)

2019-04-02 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 193258.
zahiraam marked 15 inline comments as done.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D43576/new/

https://reviews.llvm.org/D43576

Files:
  include/clang/AST/Decl.h
  include/clang/AST/RecursiveASTVisitor.h
  include/clang/Basic/Attr.td
  include/clang/Basic/DeclNodes.td
  include/clang/Sema/ParsedAttr.h
  include/clang/Sema/Sema.h
  lib/AST/Decl.cpp
  lib/AST/DeclBase.cpp
  lib/AST/DeclCXX.cpp
  lib/CodeGen/CGDecl.cpp
  lib/Parse/ParseDeclCXX.cpp
  lib/Sema/SemaDecl.cpp
  lib/Sema/SemaDeclAttr.cpp
  lib/Sema/SemaExprCXX.cpp
  lib/Sema/SemaTemplateInstantiateDecl.cpp
  lib/Serialization/ASTCommon.cpp
  test/Parser/MicrosoftExtensions.cpp
  test/Sema/ms-uuid-1.cpp
  test/Sema/ms-uuid-2.cpp
  utils/TableGen/ClangAttrEmitter.cpp

Index: utils/TableGen/ClangAttrEmitter.cpp
===
--- utils/TableGen/ClangAttrEmitter.cpp
+++ utils/TableGen/ClangAttrEmitter.cpp
@@ -321,12 +321,15 @@
 OS << "\" << get" << getUpperName() << "().getAsString() << \"";
   else if (type == "ParamIdx")
 OS << "\" << get" << getUpperName() << "().getSourceIndex() << \"";
-  else
+  else if (type == "DeclSpecUuidDecl *") {
+OS << "\" << get" << getUpperName() << "() << \"";
+  } else
 OS << "\" << get" << getUpperName() << "() << \"";
 }
 
 void writeDump(raw_ostream &OS) const override {
-  if (type == "FunctionDecl *" || type == "NamedDecl *") {
+  if (type == "FunctionDecl *" || type == "NamedDecl *" ||
+  type == "DeclSpecUuidDecl *") {
 OS << "OS << \" \";\n";
 OS << "dumpBareDeclRef(SA->get" << getUpperName() << "());\n"; 
   } else if (type == "IdentifierInfo *") {
@@ -1296,6 +1299,8 @@
 Ptr = llvm::make_unique(Arg, Attr);
   else if (ArgName == "VersionArgument")
 Ptr = llvm::make_unique(Arg, Attr);
+  else if (ArgName == "DeclSpecUuidDeclArgument")
+Ptr = llvm::make_unique(Arg, Attr, "DeclSpecUuidDecl *");
 
   if (!Ptr) {
 // Search in reverse order so that the most-derived type is handled first.
Index: test/Sema/ms-uuid-2.cpp
===
--- /dev/null
+++ test/Sema/ms-uuid-2.cpp
@@ -0,0 +1,18 @@
+// RUN: %clang_cc1 -fsyntax-only -verify -fms-extensions -fms-compatibility -std=c++14  %s
+
+
+typedef struct _GUID
+{
+unsigned long  Data1;
+unsigned short Data2;
+unsigned short Data3;
+unsigned char  Data4[8];
+} GUID;
+
+// expected-error@+5 {{C++ requires a type specifier for all declarations}}
+// expected-error@+4 {{invalid digit 'a' in decimal constant}}
+// expected-error@+3 {{use of undeclared identifier 'def0'}}
+// expected-error@+2 {{invalid digit 'a' in decimal constant}}
+// expected-error@+1 {{expected ';' after top level declarator}}
+uuid(12345678-9abc-def0-1234-56789abcdef0) struct S2;
+
Index: test/Sema/ms-uuid-1.cpp
===
--- /dev/null
+++ test/Sema/ms-uuid-1.cpp
@@ -0,0 +1,31 @@
+// RUN: %clang_cc1 -fsyntax-only -verify -fms-extensions -fms-compatibility -std=c++14 %s
+// expected-no-diagnostics
+typedef struct _GUID {
+  int i;
+} IID;
+template 
+class A {};
+
+struct
+__declspec(uuid("{DDB47A6A-0F23-11D5-9109-00E0296B75D3}"))
+S1 {};
+
+struct
+__declspec(uuid("{DDB47A6A-0F23-11D5-9109-00E0296B75D3}"))
+S2 {};
+
+struct __declspec(dllexport)
+C1 : public A<&__uuidof(S1)> {};
+
+struct __declspec(dllexport)
+C2 : public A<&__uuidof(S2)> {};
+int printf(const char *, ...);
+int main() {
+
+  if (&__uuidof(S1) == &__uuidof(S2))
+printf("OK\n");
+  else
+printf("ERROR\n");
+
+  return 0;
+}
Index: test/Parser/MicrosoftExtensions.cpp
===
--- test/Parser/MicrosoftExtensions.cpp
+++ test/Parser/MicrosoftExtensions.cpp
@@ -76,7 +76,7 @@
struct_with_uuid var_with_uuid[1];
struct_without_uuid var_without_uuid[1];
 
-   __uuidof(struct_with_uuid);
+   __uuidof(struct_with_uuid); // expected-error {{non-type template argument of type 'const _GUID' is not a constant expression}}
__uuidof(struct_with_uuid2);
__uuidof(struct_with_uuid3);
__uuidof(struct_without_uuid); // expected-error {{cannot call operator __uuidof on a type with no GUID}}
@@ -137,7 +137,7 @@
 
 COM_CLASS_TEMPLATE_REF good_template_arg;
 
-COM_CLASS_TEMPLATE bad_template_arg; // expected-error {{non-type template argument of type 'const _GUID' is not a constant expression}}
+COM_CLASS_TEMPLATE bad_template_arg;
 
 namespace PR16911 {
 struct __declspec(uuid("{12345678-1234-1234-1234-1234567890aB}")) uuid;
Index: lib/Serialization/ASTCommon.cpp
===
--- lib/Serialization/ASTCommon.cpp
+++ lib/Serialization/ASTCommon.cpp
@@ -348,6 +348,7 @@
   case Decl::ObjCProtocol:
   case Decl::ObjCInterface:
   case Decl:

[PATCH] D43576: Solution to fix PR27066 - Redefinition with same mangled name as another definition (dllexport and uuid)

2019-04-02 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added a comment.

There are still a few things I haven't addressed yet. Mostly because not sure 
there is another solution like getting rid of the map from StringRef to expr. 
The other issue is not adding new kind to ParsedAttr. There may be another way 
of doing it, but didn't look at it yet.
Meanwhile can you please let me know if you are happy with the current status 
of the implementation.




Comment at: lib/Parse/ParseDecl.cpp:594
+  bool Invalid = false;
+  StringRef UuidStr = PP.getSpelling(Tok, UuidBuffer, &Invalid);
+

rsmith wrote:
> How does this handle the case where multiple tokens must be concatenated to 
> form a uuid? Eg, `uuid(12345678-9abc-def0-1234-56789abcdef0)`
ksh-3.2$ cat m3.cpp
struct __declspec (uuid(12345678-9abc-def0-1234-56789abcdef0)) s;
ksh-3.2$ clang -c m3.cpp
m3.cpp:1:35: error: invalid digit 'a' in decimal constant
struct __declspec (uuid(12345678-9abc-def0-1234-56789abcdef0)) s;
  ^
m3.cpp:1:39: error: use of undeclared identifier 'def0'
struct __declspec (uuid(12345678-9abc-def0-1234-56789abcdef0)) s;
  ^
m3.cpp:1:54: error: invalid digit 'a' in decimal constant
struct __declspec (uuid(12345678-9abc-def0-1234-56789abcdef0)) s;
 ^
3 errors generated.
ksh-3.2$



CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D43576/new/

https://reviews.llvm.org/D43576



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D45978: dllexport const variables must have external linkage.

2019-02-03 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added a comment.

In D45978#1379901 , @rnk wrote:

> I'm still not sure this is the best place to make this change, but the 
> functionality is important. There are still unaddressed comments (no need to 
> check MSVCCompatibility, formatting), and I think once those are fixed we can 
> land this.


Since it needs to fail for this:

__declspec(dllexport) const int j;

and pass for this:

__declspec(dllexport) int const x = 3;

I am proposing to add this code in Sema::AddInitializerToDecl(Decl *RealDecl, 
Expr *Init, bool DirectInit).


CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D45978/new/

https://reviews.llvm.org/D45978



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D45978: dllexport const variables must have external linkage.

2019-02-06 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 185541.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D45978/new/

https://reviews.llvm.org/D45978

Files:
  lib/Sema/SemaDecl.cpp
  test/Sema/dllexport-1.cpp
  test/Sema/dllexport-2.cpp


Index: test/Sema/dllexport-2.cpp
===
--- /dev/null
+++ test/Sema/dllexport-2.cpp
@@ -0,0 +1,6 @@
+// RUN: %clang_cc1 -triple i686-win32 -fsyntax-only -fms-extensions -verify %s
+// RUN: %clang_cc1 -triple x86_64-win32   -fsyntax-only -fms-extensions 
-verify -std=c++11 %s
+
+// Export const variable.
+
+__declspec(dllexport) int const j; // expected-error {{default initialization 
of an object of const type 'const int'}} // expected-error {{'j' must have 
external linkage when declared 'dllexport'}}
Index: test/Sema/dllexport-1.cpp
===
--- /dev/null
+++ test/Sema/dllexport-1.cpp
@@ -0,0 +1,9 @@
+// RUN: %clang_cc1 -triple i686-win32 -fsyntax-only -fms-extensions -verify %s
+// RUN: %clang_cc1 -triple x86_64-win32   -fsyntax-only -fms-extensions 
-verify -std=c++11 %s
+
+// CHECK: @"?x@@3HB" = dso_local dllexport constant i32 3, align 4
+
+// Export const variable initialization.
+
+// expected-no-diagnostics
+__declspec(dllexport) int const x = 3;
Index: lib/Sema/SemaDecl.cpp
===
--- lib/Sema/SemaDecl.cpp
+++ lib/Sema/SemaDecl.cpp
@@ -11367,6 +11367,16 @@
 !isTemplateInstantiation(VDecl->getTemplateSpecializationKind()))
   Diag(VDecl->getLocation(), diag::warn_extern_init);
 
+// In Microsoft C++ mode, a const variable defined in namespace scope has
+// external linkage by default if the variable is declared with
+// __declspec(dllexport).
+if (Context.getTargetInfo().getCXXABI().isMicrosoft() &&
+getLangOpts().CPlusPlus &&
+VDecl->getType().isLocalConstQualified() &&
+VDecl->hasAttr() &&
+VDecl->getDefinition())
+  VDecl->setStorageClass(SC_Extern);
+
 // C99 6.7.8p4. All file scoped initializers need to be constant.
 if (!getLangOpts().CPlusPlus && !VDecl->isInvalidDecl())
   CheckForConstantInitializer(Init, DclT);


Index: test/Sema/dllexport-2.cpp
===
--- /dev/null
+++ test/Sema/dllexport-2.cpp
@@ -0,0 +1,6 @@
+// RUN: %clang_cc1 -triple i686-win32 -fsyntax-only -fms-extensions -verify %s
+// RUN: %clang_cc1 -triple x86_64-win32   -fsyntax-only -fms-extensions -verify -std=c++11 %s
+
+// Export const variable.
+
+__declspec(dllexport) int const j; // expected-error {{default initialization of an object of const type 'const int'}} // expected-error {{'j' must have external linkage when declared 'dllexport'}}
Index: test/Sema/dllexport-1.cpp
===
--- /dev/null
+++ test/Sema/dllexport-1.cpp
@@ -0,0 +1,9 @@
+// RUN: %clang_cc1 -triple i686-win32 -fsyntax-only -fms-extensions -verify %s
+// RUN: %clang_cc1 -triple x86_64-win32   -fsyntax-only -fms-extensions -verify -std=c++11 %s
+
+// CHECK: @"?x@@3HB" = dso_local dllexport constant i32 3, align 4
+
+// Export const variable initialization.
+
+// expected-no-diagnostics
+__declspec(dllexport) int const x = 3;
Index: lib/Sema/SemaDecl.cpp
===
--- lib/Sema/SemaDecl.cpp
+++ lib/Sema/SemaDecl.cpp
@@ -11367,6 +11367,16 @@
 !isTemplateInstantiation(VDecl->getTemplateSpecializationKind()))
   Diag(VDecl->getLocation(), diag::warn_extern_init);
 
+// In Microsoft C++ mode, a const variable defined in namespace scope has
+// external linkage by default if the variable is declared with
+// __declspec(dllexport).
+if (Context.getTargetInfo().getCXXABI().isMicrosoft() &&
+getLangOpts().CPlusPlus &&
+VDecl->getType().isLocalConstQualified() &&
+VDecl->hasAttr() &&
+VDecl->getDefinition())
+  VDecl->setStorageClass(SC_Extern);
+
 // C99 6.7.8p4. All file scoped initializers need to be constant.
 if (!getLangOpts().CPlusPlus && !VDecl->isInvalidDecl())
   CheckForConstantInitializer(Init, DclT);
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D45978: dllexport const variables must have external linkage.

2019-02-06 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added a comment.



> That seems like a reasonable place to try, to me.

Ok. Let's see if this does the trick. Thanks.


CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D45978/new/

https://reviews.llvm.org/D45978



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D45978: dllexport const variables must have external linkage.

2019-02-08 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added a comment.

In D45978#1387385 , @aaron.ballman 
wrote:

> Can you add tests for C mode as well, as it seems the behavior differs there.


Aaron,

Let me know if that is enough. Thanks.


CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D45978/new/

https://reviews.llvm.org/D45978



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D45978: dllexport const variables must have external linkage.

2019-02-08 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 185920.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D45978/new/

https://reviews.llvm.org/D45978

Files:
  test/Sema/dllexport-1.cpp
  test/Sema/dllexport-2.cpp
  test/Sema/dllexport.c


Index: test/Sema/dllexport.c
===
--- test/Sema/dllexport.c
+++ test/Sema/dllexport.c
@@ -162,3 +162,16 @@
 
 void __declspec(dllexport) precedenceRedecl2();
 void __declspec(dllimport) precedenceRedecl2() {} // 
expected-warning{{'dllimport' attribute ignored}}
+
+// Export const variable.
+
+// CHECK: @y = common dso_local dllexport global i32 0, align 4
+
+__declspec(dllexport) int const x = 3;
+__declspec(dllexport) const int y;
+extern int const z = 4; // expected-warning{{'extern' variable has an 
initializer}}
+
+int main() {
+  int a = x + y + z;
+  return a;
+}
Index: test/Sema/dllexport-2.cpp
===
--- test/Sema/dllexport-2.cpp
+++ test/Sema/dllexport-2.cpp
@@ -1,5 +1,5 @@
 // RUN: %clang_cc1 -triple i686-win32 -fsyntax-only -fms-extensions -verify %s
-// RUN: %clang_cc1 -triple x86_64-win32   -fsyntax-only -fms-extensions 
-verify -std=c++11 %s
+// RUN: %clang_cc1 -triple x86_64-win32 -fsyntax-only -fms-extensions -verify 
-std=c++11 %s
 
 // Export const variable.
 
Index: test/Sema/dllexport-1.cpp
===
--- test/Sema/dllexport-1.cpp
+++ test/Sema/dllexport-1.cpp
@@ -1,5 +1,5 @@
 // RUN: %clang_cc1 -triple i686-win32 -fsyntax-only -fms-extensions -verify %s
-// RUN: %clang_cc1 -triple x86_64-win32   -fsyntax-only -fms-extensions 
-verify -std=c++11 %s
+// RUN: %clang_cc1 -triple x86_64-win32 -fsyntax-only -fms-extensions -verify 
-std=c++11 %s
 
 // CHECK: @"?x@@3HB" = dso_local dllexport constant i32 3, align 4
 


Index: test/Sema/dllexport.c
===
--- test/Sema/dllexport.c
+++ test/Sema/dllexport.c
@@ -162,3 +162,16 @@
 
 void __declspec(dllexport) precedenceRedecl2();
 void __declspec(dllimport) precedenceRedecl2() {} // expected-warning{{'dllimport' attribute ignored}}
+
+// Export const variable.
+
+// CHECK: @y = common dso_local dllexport global i32 0, align 4
+
+__declspec(dllexport) int const x = 3;
+__declspec(dllexport) const int y;
+extern int const z = 4; // expected-warning{{'extern' variable has an initializer}}
+
+int main() {
+  int a = x + y + z;
+  return a;
+}
Index: test/Sema/dllexport-2.cpp
===
--- test/Sema/dllexport-2.cpp
+++ test/Sema/dllexport-2.cpp
@@ -1,5 +1,5 @@
 // RUN: %clang_cc1 -triple i686-win32 -fsyntax-only -fms-extensions -verify %s
-// RUN: %clang_cc1 -triple x86_64-win32   -fsyntax-only -fms-extensions -verify -std=c++11 %s
+// RUN: %clang_cc1 -triple x86_64-win32 -fsyntax-only -fms-extensions -verify -std=c++11 %s
 
 // Export const variable.
 
Index: test/Sema/dllexport-1.cpp
===
--- test/Sema/dllexport-1.cpp
+++ test/Sema/dllexport-1.cpp
@@ -1,5 +1,5 @@
 // RUN: %clang_cc1 -triple i686-win32 -fsyntax-only -fms-extensions -verify %s
-// RUN: %clang_cc1 -triple x86_64-win32   -fsyntax-only -fms-extensions -verify -std=c++11 %s
+// RUN: %clang_cc1 -triple x86_64-win32 -fsyntax-only -fms-extensions -verify -std=c++11 %s
 
 // CHECK: @"?x@@3HB" = dso_local dllexport constant i32 3, align 4
 
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D45978: dllexport const variables must have external linkage.

2019-02-11 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added a comment.

In D45978#1392855 , @aaron.ballman 
wrote:

> It looks like the patch got mucked up somehow, I only see three testing files 
> in the patch now?


Oops! Sorry about that.


CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D45978/new/

https://reviews.llvm.org/D45978



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D45978: dllexport const variables must have external linkage.

2019-02-11 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 186275.
Herald added a subscriber: mstorsjo.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D45978/new/

https://reviews.llvm.org/D45978

Files:
  lib/Sema/SemaDecl.cpp
  test/Sema/dllexport-1.c
  test/Sema/dllexport-1.cpp
  test/Sema/dllexport-2.cpp


Index: test/Sema/dllexport-2.cpp
===
--- /dev/null
+++ test/Sema/dllexport-2.cpp
@@ -0,0 +1,6 @@
+// RUN: %clang_cc1 -triple i686-win32 -fsyntax-only -fms-extensions -verify %s
+// RUN: %clang_cc1 -triple x86_64-win32 -fsyntax-only -fms-extensions -verify 
-std=c++11 %s
+
+// Export const variable.
+
+__declspec(dllexport) int const j; // expected-error {{default initialization 
of an object of const type 'const int'}} // expected-error {{'j' must have 
external linkage when declared 'dllexport'}}
Index: test/Sema/dllexport-1.cpp
===
--- /dev/null
+++ test/Sema/dllexport-1.cpp
@@ -0,0 +1,9 @@
+// RUN: %clang_cc1 -triple i686-win32 -fsyntax-only -fms-extensions -verify %s
+// RUN: %clang_cc1 -triple x86_64-win32 -fsyntax-only -fms-extensions -verify 
-std=c++11 %s
+
+// CHECK: @"?x@@3HB" = dso_local dllexport constant i32 3, align 4
+
+// Export const variable initialization.
+
+// expected-no-diagnostics
+__declspec(dllexport) int const x = 3;
Index: test/Sema/dllexport-1.c
===
--- /dev/null
+++ test/Sema/dllexport-1.c
@@ -0,0 +1,17 @@
+// RUN: %clang_cc1 -triple i686-win32 -emit-llvm -fms-extensions -std=c99 < 
%s| FileCheck %s
+// RUN: %clang_cc1 -triple x86_64-win32 -emit-llvm -fms-extensions -std=c11 < 
%s | FileCheck %s
+// RUN: %clang_cc1 -triple i686-mingw32 -emit-llvm -fms-extensions -std=c11 < 
%s | FileCheck %s
+// RUN: %clang_cc1 -triple x86_64-mingw32 -emit-llvm -fms-extensions -std=c11 
< %s | FileCheck %s
+
+// Export const variable.
+
+// CHECK: @y = common dso_local dllexport global i32 0, align 4
+
+__declspec(dllexport) int const x = 3;
+__declspec(dllexport) const int y;
+extern int const z = 4; // expected-warning{{'extern' variable has an 
initializer}}
+
+int main() {
+  int a = x + y + z;
+  return a;
+}
Index: lib/Sema/SemaDecl.cpp
===
--- lib/Sema/SemaDecl.cpp
+++ lib/Sema/SemaDecl.cpp
@@ -11367,6 +11367,16 @@
 !isTemplateInstantiation(VDecl->getTemplateSpecializationKind()))
   Diag(VDecl->getLocation(), diag::warn_extern_init);
 
+// In Microsoft C++ mode, a const variable defined in namespace scope has
+// external linkage by default if the variable is declared with
+// __declspec(dllexport).
+if (Context.getTargetInfo().getCXXABI().isMicrosoft() &&
+getLangOpts().CPlusPlus &&
+VDecl->getType().isLocalConstQualified() &&
+VDecl->hasAttr() &&
+VDecl->getDefinition())
+  VDecl->setStorageClass(SC_Extern);
+
 // C99 6.7.8p4. All file scoped initializers need to be constant.
 if (!getLangOpts().CPlusPlus && !VDecl->isInvalidDecl())
   CheckForConstantInitializer(Init, DclT);


Index: test/Sema/dllexport-2.cpp
===
--- /dev/null
+++ test/Sema/dllexport-2.cpp
@@ -0,0 +1,6 @@
+// RUN: %clang_cc1 -triple i686-win32 -fsyntax-only -fms-extensions -verify %s
+// RUN: %clang_cc1 -triple x86_64-win32 -fsyntax-only -fms-extensions -verify -std=c++11 %s
+
+// Export const variable.
+
+__declspec(dllexport) int const j; // expected-error {{default initialization of an object of const type 'const int'}} // expected-error {{'j' must have external linkage when declared 'dllexport'}}
Index: test/Sema/dllexport-1.cpp
===
--- /dev/null
+++ test/Sema/dllexport-1.cpp
@@ -0,0 +1,9 @@
+// RUN: %clang_cc1 -triple i686-win32 -fsyntax-only -fms-extensions -verify %s
+// RUN: %clang_cc1 -triple x86_64-win32 -fsyntax-only -fms-extensions -verify -std=c++11 %s
+
+// CHECK: @"?x@@3HB" = dso_local dllexport constant i32 3, align 4
+
+// Export const variable initialization.
+
+// expected-no-diagnostics
+__declspec(dllexport) int const x = 3;
Index: test/Sema/dllexport-1.c
===
--- /dev/null
+++ test/Sema/dllexport-1.c
@@ -0,0 +1,17 @@
+// RUN: %clang_cc1 -triple i686-win32 -emit-llvm -fms-extensions -std=c99 < %s| FileCheck %s
+// RUN: %clang_cc1 -triple x86_64-win32 -emit-llvm -fms-extensions -std=c11 < %s | FileCheck %s
+// RUN: %clang_cc1 -triple i686-mingw32 -emit-llvm -fms-extensions -std=c11 < %s | FileCheck %s
+// RUN: %clang_cc1 -triple x86_64-mingw32 -emit-llvm -fms-extensions -std=c11 < %s | FileCheck %s
+
+// Export const variable.
+
+// CHECK: @y = common dso_local dllexport global i32 0, align 4
+
+__declspec(dllexport) int const x = 3;
+__declspec(dllexport) const int y;
+extern int const z =

[PATCH] D45978: dllexport const variables must have external linkage.

2019-02-12 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added a subscriber: z.
zahiraam added inline comments.



Comment at: test/Sema/dllexport-1.c:8
+
+// CHECK: @y = common dso_local dllexport global i32 0, align 4
+

aaron.ballman wrote:
> Are x and z also exported as expected?
Only x and y are exported.


**@x = dso_local dllexport constant i32 3, align 4**
@z = dso_local constant i32 4, align 4
**@y = common dso_local dllexport global i32 0, align 4**

But then if I take this simple case:
extern int const z = 4;

int main() {
  int a = z + 2;
  return a;
}
ksh-3.2$ clang -c test3.c
test3.c:1:18: warning: 'extern' variable has an initializer 
[-Wextern-initializer]
extern int const z = 4;
 ^
1 warning generated.
ksh-3.2$ dumpbin /symbols test3.o | grep External
00F  SECT1  notype ()External | main
**010  SECT5  notype   External | z**
ksh-3.2$
When emitting the IR, z is declared as a local constant (not exported):
@z = dso_local constant i32 4, align 4




CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D45978/new/

https://reviews.llvm.org/D45978



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D45978: dllexport const variables must have external linkage.

2019-02-12 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 186460.
zahiraam marked 3 inline comments as done.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D45978/new/

https://reviews.llvm.org/D45978

Files:
  lib/Sema/SemaDecl.cpp
  test/CodeGen/dllexport.c
  test/Sema/dllexport-1.cpp
  test/Sema/dllexport-2.cpp


Index: test/Sema/dllexport-2.cpp
===
--- /dev/null
+++ test/Sema/dllexport-2.cpp
@@ -0,0 +1,6 @@
+// RUN: %clang_cc1 -triple i686-win32 -fsyntax-only -fms-extensions -verify %s
+// RUN: %clang_cc1 -triple x86_64-win32 -fsyntax-only -fms-extensions -verify 
-std=c++11 %s
+
+// Export const variable.
+
+__declspec(dllexport) int const j; // expected-error {{default initialization 
of an object of const type 'const int'}} // expected-error {{'j' must have 
external linkage when declared 'dllexport'}}
Index: test/Sema/dllexport-1.cpp
===
--- /dev/null
+++ test/Sema/dllexport-1.cpp
@@ -0,0 +1,9 @@
+// RUN: %clang_cc1 -triple i686-win32 -fsyntax-only -fms-extensions -verify %s
+// RUN: %clang_cc1 -triple x86_64-win32 -fsyntax-only -fms-extensions -verify 
-std=c++11 %s
+
+// CHECK: @"?x@@3HB" = dso_local dllexport constant i32 3, align 4
+
+// Export const variable initialization.
+
+// expected-no-diagnostics
+__declspec(dllexport) int const x = 3;
Index: test/CodeGen/dllexport.c
===
--- test/CodeGen/dllexport.c
+++ test/CodeGen/dllexport.c
@@ -113,3 +113,29 @@
 // CHECK-DAG: define dso_local dllexport void @precedenceRedecl2()
 void __declspec(dllexport) precedenceRedecl2(void);
 void __declspec(dllimport) precedenceRedecl2(void) {}
+
+// Export const variable.
+
+// CHECK-DAG: @x = dso_local dllexport constant i32 3, align 4
+// CHECK-DAG: @z = dso_local constant i32 4, align 4
+// CHECK-DAG: @y = common dso_local dllexport global i32 0, align 4
+
+__declspec(dllexport) int const x = 3;
+__declspec(dllexport) const int y;
+extern int const z = 4; // expected-warning{{'extern' variable has an 
initializer}}
+
+int main() {
+  int a = x + y + z;
+  return a;
+}
+
+// CHECK-DAG: @a = dso_local dllexport constant i32 3, align 4
+// CHECK-DAG: @b = dso_local constant i32 4, align 4
+
+__declspec(dllexport) int const a = 3;
+extern int const b = 4; // expected-warning{{'extern' variable has an 
initializer}}
+
+int foo() {
+  int c = a + b;
+  return c;
+}
Index: lib/Sema/SemaDecl.cpp
===
--- lib/Sema/SemaDecl.cpp
+++ lib/Sema/SemaDecl.cpp
@@ -11367,6 +11367,16 @@
 !isTemplateInstantiation(VDecl->getTemplateSpecializationKind()))
   Diag(VDecl->getLocation(), diag::warn_extern_init);
 
+// In Microsoft C++ mode, a const variable defined in namespace scope has
+// external linkage by default if the variable is declared with
+// __declspec(dllexport).
+if (Context.getTargetInfo().getCXXABI().isMicrosoft() &&
+getLangOpts().CPlusPlus &&
+VDecl->getType().isLocalConstQualified() &&
+VDecl->hasAttr() &&
+VDecl->getDefinition())
+  VDecl->setStorageClass(SC_Extern);
+
 // C99 6.7.8p4. All file scoped initializers need to be constant.
 if (!getLangOpts().CPlusPlus && !VDecl->isInvalidDecl())
   CheckForConstantInitializer(Init, DclT);


Index: test/Sema/dllexport-2.cpp
===
--- /dev/null
+++ test/Sema/dllexport-2.cpp
@@ -0,0 +1,6 @@
+// RUN: %clang_cc1 -triple i686-win32 -fsyntax-only -fms-extensions -verify %s
+// RUN: %clang_cc1 -triple x86_64-win32 -fsyntax-only -fms-extensions -verify -std=c++11 %s
+
+// Export const variable.
+
+__declspec(dllexport) int const j; // expected-error {{default initialization of an object of const type 'const int'}} // expected-error {{'j' must have external linkage when declared 'dllexport'}}
Index: test/Sema/dllexport-1.cpp
===
--- /dev/null
+++ test/Sema/dllexport-1.cpp
@@ -0,0 +1,9 @@
+// RUN: %clang_cc1 -triple i686-win32 -fsyntax-only -fms-extensions -verify %s
+// RUN: %clang_cc1 -triple x86_64-win32 -fsyntax-only -fms-extensions -verify -std=c++11 %s
+
+// CHECK: @"?x@@3HB" = dso_local dllexport constant i32 3, align 4
+
+// Export const variable initialization.
+
+// expected-no-diagnostics
+__declspec(dllexport) int const x = 3;
Index: test/CodeGen/dllexport.c
===
--- test/CodeGen/dllexport.c
+++ test/CodeGen/dllexport.c
@@ -113,3 +113,29 @@
 // CHECK-DAG: define dso_local dllexport void @precedenceRedecl2()
 void __declspec(dllexport) precedenceRedecl2(void);
 void __declspec(dllimport) precedenceRedecl2(void) {}
+
+// Export const variable.
+
+// CHECK-DAG: @x = dso_local dllexport constant i32 3, align 4
+// CHECK-DAG: @z = dso_local constant i32 4, align 4
+// 

[PATCH] D45978: dllexport const variables must have external linkage.

2019-02-13 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 186641.
zahiraam marked 5 inline comments as done.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D45978/new/

https://reviews.llvm.org/D45978

Files:
  lib/Sema/SemaDecl.cpp
  test/CodeGen/dllexport-1.c
  test/Sema/dllexport-1.cpp
  test/Sema/dllexport-2.cpp


Index: test/Sema/dllexport-2.cpp
===
--- /dev/null
+++ test/Sema/dllexport-2.cpp
@@ -0,0 +1,5 @@
+// RUN: %clang_cc1 -fsyntax-only -fms-extensions -verify %s
+
+// Export const variable.
+
+__declspec(dllexport) int const j; // expected-error {{default initialization 
of an object of const type 'const int'}} // expected-error {{'j' must have 
external linkage when declared 'dllexport'}}
Index: test/Sema/dllexport-1.cpp
===
--- /dev/null
+++ test/Sema/dllexport-1.cpp
@@ -0,0 +1,6 @@
+// RUN: %clang_cc1 -fsyntax-only -fms-extensions -verify %s
+
+// Export const variable initialization.
+
+// expected-no-diagnostics
+__declspec(dllexport) int const x = 3;
Index: test/CodeGen/dllexport-1.c
===
--- /dev/null
+++ test/CodeGen/dllexport-1.c
@@ -0,0 +1,17 @@
+// RUN: %clang_cc1 -emit-llvm -fms-extensions -o - %s | FileCheck %s
+
+
+// Export const variable.
+
+// CHECK: @x = dso_local dllexport constant i32 3, align 4
+// CHECK: @z = dso_local constant i32 4, align 4
+// CHECK: @y = common dso_local dllexport global i32 0, align 4
+
+__declspec(dllexport) int const x = 3;
+__declspec(dllexport) const int y;
+extern int const z = 4; // expected-warning{{'extern' variable has an 
initializer}}
+
+int main() {
+  int a = x + y + z;
+  return a;
+}
Index: lib/Sema/SemaDecl.cpp
===
--- lib/Sema/SemaDecl.cpp
+++ lib/Sema/SemaDecl.cpp
@@ -11367,6 +11367,16 @@
 !isTemplateInstantiation(VDecl->getTemplateSpecializationKind()))
   Diag(VDecl->getLocation(), diag::warn_extern_init);
 
+// In Microsoft C++ mode, a const variable defined in namespace scope has
+// external linkage by default if the variable is declared with
+// __declspec(dllexport).
+if (Context.getTargetInfo().getCXXABI().isMicrosoft() &&
+getLangOpts().CPlusPlus &&
+VDecl->getType().isLocalConstQualified() &&
+VDecl->hasAttr() &&
+VDecl->getDefinition())
+  VDecl->setStorageClass(SC_Extern);
+
 // C99 6.7.8p4. All file scoped initializers need to be constant.
 if (!getLangOpts().CPlusPlus && !VDecl->isInvalidDecl())
   CheckForConstantInitializer(Init, DclT);


Index: test/Sema/dllexport-2.cpp
===
--- /dev/null
+++ test/Sema/dllexport-2.cpp
@@ -0,0 +1,5 @@
+// RUN: %clang_cc1 -fsyntax-only -fms-extensions -verify %s
+
+// Export const variable.
+
+__declspec(dllexport) int const j; // expected-error {{default initialization of an object of const type 'const int'}} // expected-error {{'j' must have external linkage when declared 'dllexport'}}
Index: test/Sema/dllexport-1.cpp
===
--- /dev/null
+++ test/Sema/dllexport-1.cpp
@@ -0,0 +1,6 @@
+// RUN: %clang_cc1 -fsyntax-only -fms-extensions -verify %s
+
+// Export const variable initialization.
+
+// expected-no-diagnostics
+__declspec(dllexport) int const x = 3;
Index: test/CodeGen/dllexport-1.c
===
--- /dev/null
+++ test/CodeGen/dllexport-1.c
@@ -0,0 +1,17 @@
+// RUN: %clang_cc1 -emit-llvm -fms-extensions -o - %s | FileCheck %s
+
+
+// Export const variable.
+
+// CHECK: @x = dso_local dllexport constant i32 3, align 4
+// CHECK: @z = dso_local constant i32 4, align 4
+// CHECK: @y = common dso_local dllexport global i32 0, align 4
+
+__declspec(dllexport) int const x = 3;
+__declspec(dllexport) const int y;
+extern int const z = 4; // expected-warning{{'extern' variable has an initializer}}
+
+int main() {
+  int a = x + y + z;
+  return a;
+}
Index: lib/Sema/SemaDecl.cpp
===
--- lib/Sema/SemaDecl.cpp
+++ lib/Sema/SemaDecl.cpp
@@ -11367,6 +11367,16 @@
 !isTemplateInstantiation(VDecl->getTemplateSpecializationKind()))
   Diag(VDecl->getLocation(), diag::warn_extern_init);
 
+// In Microsoft C++ mode, a const variable defined in namespace scope has
+// external linkage by default if the variable is declared with
+// __declspec(dllexport).
+if (Context.getTargetInfo().getCXXABI().isMicrosoft() &&
+getLangOpts().CPlusPlus &&
+VDecl->getType().isLocalConstQualified() &&
+VDecl->hasAttr() &&
+VDecl->getDefinition())
+  VDecl->setStorageClass(SC_Extern);
+
 // C99 6.7.8p4. All file scoped initializers need to be constant.
 if (!getLangOpts().CPlusPlus && !VDecl->isI

[PATCH] D45978: dllexport const variables must have external linkage.

2019-02-13 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added a comment.




CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D45978/new/

https://reviews.llvm.org/D45978



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D45978: dllexport const variables must have external linkage.

2019-02-14 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam marked an inline comment as done.
zahiraam added inline comments.



Comment at: lib/Sema/SemaDecl.cpp:11370
 
+// In Microsoft C++ mode, a const variable defined in namespace scope has
+// external linkage by default if the variable is declared with

aaron.ballman wrote:
> thakis wrote:
> > Even in unnamed namespaces?
> That would definitely be good to test.
It looks like not. 

ksh-3.2$ cat test4.cpp
namespace {
__declspec(dllexport) int const x = 3;
}

int main ()
{
  int y = x + 10;

  return y;
}

ksh-3.2$ cl -c test4.cpp
Microsoft (R) C/C++ Optimizing Compiler Version 19.00.24210 for x64
Copyright (C) Microsoft Corporation.  All rights reserved.

test4.cpp
ksh-3.2$ dumpbin /symbols test4.obj | grep External
**008  SECT3  notype ()External | main**
ksh-3.2$

ksh-3.2$ clang -c test4.cpp
test4.cpp:2:33: error: '(anonymous namespace)::x' must have external linkage 
when declared 'dllexport'
__declspec(dllexport) int const x = 3;
^
1 error generated.
ksh-3.2$

So the diag shouldn't go off when the variable is in an anonymous namespace? Do 
you agree?



CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D45978/new/

https://reviews.llvm.org/D45978



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D45978: dllexport const variables must have external linkage.

2019-02-23 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added a comment.

Let's see if I have included every thing mentioned. Thanks.


CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D45978/new/

https://reviews.llvm.org/D45978



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D45978: dllexport const variables must have external linkage.

2019-02-23 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 188047.
zahiraam marked 2 inline comments as done.
Herald added subscribers: jdoerfert, jfb, mgrang, srhines.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D45978/new/

https://reviews.llvm.org/D45978

Files:
  lib/Sema/SemaDecl.cpp
  mypatch.patch
  test/CodeGen/dllexport-1.c
  test/Sema/dllexport-1.cpp
  test/Sema/dllexport-2.cpp



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D37308: Interface class with uuid base record

2017-08-30 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam created this revision.

Added support for interface inheriting from a uuid base record.


https://reviews.llvm.org/D37308

Files:
  lib/Sema/SemaDeclCXX.cpp
  test/SemaCXX/ms-uuid.cpp


Index: test/SemaCXX/ms-uuid.cpp
===
--- test/SemaCXX/ms-uuid.cpp
+++ test/SemaCXX/ms-uuid.cpp
@@ -93,3 +93,15 @@
 [uuid("00A0---C000-0049"),
  uuid("00A0---C000-0049")] class C10;
 }
+
+struct __declspec(uuid("---C000-0046")) IUnknown {};
+__interface ISfFileIOPropertyPage : public IUnknown {};
+
+class __declspec(uuid("---C000-0046")) IUnknown1 {};
+__interface __declspec(dllimport) ISfFileIOPropertyPage1 : public IUnknown1 
{}; // expected-error{{interface type cannot inherit from}}
+
+struct __declspec(uuid("---C000-0046")) IUnknown2 {};
+__interface __declspec(dllimport) ISfFileIOPropertyPage2 : public IUnknown2 
{}; // expected-error{{interface type cannot inherit from}}
+
+struct __declspec(dllexport) IUnknown3{};
+__interface foo : public IUnknown3{}; // expected-error{{interface type cannot 
inherit from}}
Index: lib/Sema/SemaDeclCXX.cpp
===
--- lib/Sema/SemaDeclCXX.cpp
+++ lib/Sema/SemaDeclCXX.cpp
@@ -2398,6 +2398,13 @@
   }
 }
 
+
+/// \brief Tests if the __interface base is public.
+static bool IsBasePublicInterface(const CXXRecordDecl *RD,
+  AccessSpecifier spec) {
+  return RD->isInterface() && spec == AS_public;
+}
+
 /// \brief Performs the actual work of attaching the given base class
 /// specifiers to a C++ class.
 bool Sema::AttachBaseSpecifiers(CXXRecordDecl *Class,
@@ -2450,10 +2457,13 @@
   if (const RecordType *Record = NewBaseType->getAs()) {
 const CXXRecordDecl *RD = cast(Record->getDecl());
 if (Class->isInterface() &&
-  (!RD->isInterface() ||
-   KnownBase->getAccessSpecifier() != AS_public)) {
-  // The Microsoft extension __interface does not permit bases that
-  // are not themselves public interfaces.
+!IsBasePublicInterface(RD, KnownBase->getAccessSpecifier()) &&
+// The Microsoft extension __interface does not permit bases that
+// are not themselves public interfaces.
+// An interface can inherit from a base, as long as it has
+// uuid attributes.
+(!RD->getAttr() ||
+Class->hasAttrs())) {
   Diag(KnownBase->getLocStart(), diag::err_invalid_base_in_interface)
 << getRecordDiagFromTagKind(RD->getTagKind()) << RD->getName()
 << RD->getSourceRange();


Index: test/SemaCXX/ms-uuid.cpp
===
--- test/SemaCXX/ms-uuid.cpp
+++ test/SemaCXX/ms-uuid.cpp
@@ -93,3 +93,15 @@
 [uuid("00A0---C000-0049"),
  uuid("00A0---C000-0049")] class C10;
 }
+
+struct __declspec(uuid("---C000-0046")) IUnknown {};
+__interface ISfFileIOPropertyPage : public IUnknown {};
+
+class __declspec(uuid("---C000-0046")) IUnknown1 {};
+__interface __declspec(dllimport) ISfFileIOPropertyPage1 : public IUnknown1 {}; // expected-error{{interface type cannot inherit from}}
+
+struct __declspec(uuid("---C000-0046")) IUnknown2 {};
+__interface __declspec(dllimport) ISfFileIOPropertyPage2 : public IUnknown2 {}; // expected-error{{interface type cannot inherit from}}
+
+struct __declspec(dllexport) IUnknown3{};
+__interface foo : public IUnknown3{}; // expected-error{{interface type cannot inherit from}}
Index: lib/Sema/SemaDeclCXX.cpp
===
--- lib/Sema/SemaDeclCXX.cpp
+++ lib/Sema/SemaDeclCXX.cpp
@@ -2398,6 +2398,13 @@
   }
 }
 
+
+/// \brief Tests if the __interface base is public.
+static bool IsBasePublicInterface(const CXXRecordDecl *RD,
+  AccessSpecifier spec) {
+  return RD->isInterface() && spec == AS_public;
+}
+
 /// \brief Performs the actual work of attaching the given base class
 /// specifiers to a C++ class.
 bool Sema::AttachBaseSpecifiers(CXXRecordDecl *Class,
@@ -2450,10 +2457,13 @@
   if (const RecordType *Record = NewBaseType->getAs()) {
 const CXXRecordDecl *RD = cast(Record->getDecl());
 if (Class->isInterface() &&
-  (!RD->isInterface() ||
-   KnownBase->getAccessSpecifier() != AS_public)) {
-  // The Microsoft extension __interface does not permit bases that
-  // are not themselves public interfaces.
+!IsBasePublicInterface(RD, KnownBase->getAccessSpecifier()) &&
+// The Microsoft extension __interface does not permit bases that
+// are not themselves public interfaces.
+// An interface can

[PATCH] D37308: Interface class with uuid base record

2017-08-31 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 113387.
zahiraam added a comment.

Removed the helper function.

If RD (base class) has uuid attribute, we want to ensure that the interface 
doesn't have attributes. Otherwise cases like:

class __declspec(uuid("---C000-0046")) IUnknown1 {};
__interface __declspec(dllimport) ISfFileIOPropertyPage1 : public IUnknown1 {};

will compile.


https://reviews.llvm.org/D37308

Files:
  lib/Sema/SemaDeclCXX.cpp


Index: lib/Sema/SemaDeclCXX.cpp
===
--- lib/Sema/SemaDeclCXX.cpp
+++ lib/Sema/SemaDeclCXX.cpp
@@ -2398,13 +2398,6 @@
   }
 }
 
-
-/// \brief Tests if the __interface base is public.
-static bool IsBasePublicInterface(const CXXRecordDecl *RD,
-  AccessSpecifier spec) {
-  return RD->isInterface() && spec == AS_public;
-}
-
 /// \brief Performs the actual work of attaching the given base class
 /// specifiers to a C++ class.
 bool Sema::AttachBaseSpecifiers(CXXRecordDecl *Class,
@@ -2457,13 +2450,13 @@
   if (const RecordType *Record = NewBaseType->getAs()) {
 const CXXRecordDecl *RD = cast(Record->getDecl());
 if (Class->isInterface() &&
-!IsBasePublicInterface(RD, KnownBase->getAccessSpecifier()) &&
+!(RD->isInterface() &&
+  KnownBase->getAccessSpecifier() == AS_public) &&
 // The Microsoft extension __interface does not permit bases that
 // are not themselves public interfaces.
 // An interface can inherit from a base, as long as it has
 // uuid attributes.
-(!RD->getAttr() ||
-Class->hasAttrs())) {
+(!RD->getAttr() || Class->hasAttrs())) {
   Diag(KnownBase->getLocStart(), diag::err_invalid_base_in_interface)
 << getRecordDiagFromTagKind(RD->getTagKind()) << RD->getName()
 << RD->getSourceRange();


Index: lib/Sema/SemaDeclCXX.cpp
===
--- lib/Sema/SemaDeclCXX.cpp
+++ lib/Sema/SemaDeclCXX.cpp
@@ -2398,13 +2398,6 @@
   }
 }
 
-
-/// \brief Tests if the __interface base is public.
-static bool IsBasePublicInterface(const CXXRecordDecl *RD,
-  AccessSpecifier spec) {
-  return RD->isInterface() && spec == AS_public;
-}
-
 /// \brief Performs the actual work of attaching the given base class
 /// specifiers to a C++ class.
 bool Sema::AttachBaseSpecifiers(CXXRecordDecl *Class,
@@ -2457,13 +2450,13 @@
   if (const RecordType *Record = NewBaseType->getAs()) {
 const CXXRecordDecl *RD = cast(Record->getDecl());
 if (Class->isInterface() &&
-!IsBasePublicInterface(RD, KnownBase->getAccessSpecifier()) &&
+!(RD->isInterface() &&
+  KnownBase->getAccessSpecifier() == AS_public) &&
 // The Microsoft extension __interface does not permit bases that
 // are not themselves public interfaces.
 // An interface can inherit from a base, as long as it has
 // uuid attributes.
-(!RD->getAttr() ||
-	 Class->hasAttrs())) {
+(!RD->getAttr() || Class->hasAttrs())) {
   Diag(KnownBase->getLocStart(), diag::err_invalid_base_in_interface)
 << getRecordDiagFromTagKind(RD->getTagKind()) << RD->getName()
 << RD->getSourceRange();
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D37308: Interface class with uuid base record

2017-08-31 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added a comment.

The test case you gave doesn't compile. It returns the diagnostic. CL has the 
same behavior. I don't think it is because of the dllimport.


https://reviews.llvm.org/D37308



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D37308: Interface class with uuid base record

2017-08-31 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added a comment.

That's both of the code snip-its are supposed to fail (take the diagnostic). If 
I remove the ClasshasAttrs() condition, from line #2459, these snip-its will 
pass. I was trying to explain the need for that part of the condition.


https://reviews.llvm.org/D37308



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D37308: Interface class with uuid base record

2017-08-31 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added a comment.

Aaron,

Yes I want to this to succeed:

struct __declspec(uuid("---C000-0046")) IUnknown {};
__interface ISfFileIOPropertyPage : public IUnknown {};

But I also want this to succeed:

struct __declspec(uuid("---C000-0046")) IUnknown {};
struct IPropertyPage : public IUnknown {};
__interface ISfFileIOPropertyPage : public IPropertyPage {};

And I can't figure out how these 2 can be differentiated. I think the 
conditions that I have currently are differently too. This later case doesn't 
succeed with the current code. 
And I want this to fail:

class __declspec(uuid("---C000-0046")) IUnknown1 {};
__interface __declspec(dllimport) ISfFileIOPropertyPage1 : public IUnknown1 {};

This currently does with the current code.

I guess I need to work on it a bit more.


https://reviews.llvm.org/D37308



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D37308: Interface class with uuid base record

2017-09-07 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 114201.
zahiraam added a comment.

Just upload a new patch. Please review.


https://reviews.llvm.org/D37308

Files:
  lib/Sema/SemaDeclCXX.cpp
  test/SemaCXX/ms-uuid.cpp


Index: test/SemaCXX/ms-uuid.cpp
===
--- test/SemaCXX/ms-uuid.cpp
+++ test/SemaCXX/ms-uuid.cpp
@@ -93,3 +93,28 @@
 [uuid("00A0---C000-0049"),
  uuid("00A0---C000-0049")] class C10;
 }
+
+struct __declspec(uuid("---C000-0046")) IUnknown {};
+__interface ISfFileIOPropertyPage : public IUnknown {};
+
+struct __declspec(uuid("---C000-0045")) IUnknown1 {};
+__interface ISfFileIOPropertyPage1 : public IUnknown1 {};  // expected-error 
{{interface type cannot inherit from}}
+
+struct __declspec(uuid("---C000-0046")) IUnknown2 {};
+struct IPropertyPage2 : public IUnknown2 {};
+__interface ISfFileIOPropertyPage2 : public IPropertyPage2 {}; // 
expected-error {{interface type cannot inherit from}}
+
+struct IPropertyPage3 : public IUnknown {};
+__interface ISfFileIOPropertyPage3 : public IPropertyPage3 {};
+
+
+__interface __declspec(dllimport) ISfFileIOPropertyPage33 : public IUnknown {};
+
+struct __declspec(uuid("---C000-0046")) IUnknown4 {};
+__interface ISfFileIOPropertyPage4 : public IUnknown4 {}; // expected-error 
{{interface type cannot inherit from}}
+
+class __declspec(uuid("---C000-0046")) IUnknown5 {};
+__interface ISfFileIOPropertyPage5 : public IUnknown5 {}; // expected-error 
{{interface type cannot inherit from}}
+
+struct __declspec(dllexport) IUnknown6{};
+__interface foo : public IUnknown6{}; // expected-error {{interface type 
cannot inherit from}}
Index: lib/Sema/SemaDeclCXX.cpp
===
--- lib/Sema/SemaDeclCXX.cpp
+++ lib/Sema/SemaDeclCXX.cpp
@@ -2373,6 +2373,32 @@
   return true;
 }
 
+/// \brief Tests if the __interface base is public.
+static bool IsBasePublicInterface(const CXXRecordDecl *RD,
+  AccessSpecifier spec) {
+  return RD->isInterface() && spec == AS_public;
+}
+
+/// \brief Test is base RD is an uuid Unknown type.
+static bool IsUnknownType(const CXXRecordDecl *RD) {
+  return RD->isStruct() && RD->hasAttr() &&
+ RD->getName() == "IUnknown" &&
+ (RD->getAttr())->getGuid() ==
+ "---C000-0046" &&
+ RD->isEmpty();
+}
+
+static bool IsInheritatedBaseUuid(const CXXRecordDecl *RD) {
+  for (unsigned int n = 0; n < RD->getNumBases(); n++) {
+const CXXRecordDecl *Base =
+RD->bases_begin()->getType()->getAsCXXRecordDecl();
+
+return (Base && Base->getName() == "IUnknown" &&
+!strcmp(Base->getAttr()->getSpelling(),"uuid"));
+  }
+  return false;
+}
+
 /// Use small set to collect indirect bases.  As this is only used
 /// locally, there's no need to abstract the small size parameter.
 typedef llvm::SmallPtrSet IndirectBaseSet;
@@ -2450,8 +2476,8 @@
   if (const RecordType *Record = NewBaseType->getAs()) {
 const CXXRecordDecl *RD = cast(Record->getDecl());
 if (Class->isInterface() &&
-  (!RD->isInterface() ||
-   KnownBase->getAccessSpecifier() != AS_public)) {
+!IsBasePublicInterface(RD, KnownBase->getAccessSpecifier()) &&
+!IsUnknownType(RD) && !IsInheritatedBaseUuid(RD)) {
   // The Microsoft extension __interface does not permit bases that
   // are not themselves public interfaces.
   Diag(KnownBase->getLocStart(), diag::err_invalid_base_in_interface)


Index: test/SemaCXX/ms-uuid.cpp
===
--- test/SemaCXX/ms-uuid.cpp
+++ test/SemaCXX/ms-uuid.cpp
@@ -93,3 +93,28 @@
 [uuid("00A0---C000-0049"),
  uuid("00A0---C000-0049")] class C10;
 }
+
+struct __declspec(uuid("---C000-0046")) IUnknown {};
+__interface ISfFileIOPropertyPage : public IUnknown {};
+
+struct __declspec(uuid("---C000-0045")) IUnknown1 {};
+__interface ISfFileIOPropertyPage1 : public IUnknown1 {};  // expected-error {{interface type cannot inherit from}}
+
+struct __declspec(uuid("---C000-0046")) IUnknown2 {};
+struct IPropertyPage2 : public IUnknown2 {};
+__interface ISfFileIOPropertyPage2 : public IPropertyPage2 {}; // expected-error {{interface type cannot inherit from}}
+
+struct IPropertyPage3 : public IUnknown {};
+__interface ISfFileIOPropertyPage3 : public IPropertyPage3 {};
+
+
+__interface __declspec(dllimport) ISfFileIOPropertyPage33 : public IUnknown {};
+
+struct __declspec(uuid("---C000-0046")) IUnknown4 {};
+__interface ISfFileIOPropertyPage4 : public IUnknown4 {}; // expected-error {{interface type cannot inherit from

[PATCH] D37308: Interface class with uuid base record

2017-09-08 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 114428.
zahiraam added a comment.

Responding to Erich 's and Aaron's reviews. Thanks.


https://reviews.llvm.org/D37308

Files:
  lib/Sema/SemaDeclCXX.cpp
  test/SemaCXX/ms-uuid.cpp


Index: test/SemaCXX/ms-uuid.cpp
===
--- test/SemaCXX/ms-uuid.cpp
+++ test/SemaCXX/ms-uuid.cpp
@@ -93,3 +93,27 @@
 [uuid("00A0---C000-0049"),
  uuid("00A0---C000-0049")] class C10;
 }
+
+struct __declspec(uuid("---C000-0046")) IUnknown {};
+__interface ISfFileIOPropertyPage : public IUnknown {};
+
+struct __declspec(uuid("---C000-0045")) IUnknown1 {};
+__interface ISfFileIOPropertyPage1 : public IUnknown1 {};  // expected-error 
{{interface type cannot inherit from}}
+
+struct __declspec(uuid("---C000-0046")) IUnknown2 {};
+struct IPropertyPage2 : public IUnknown2 {};
+__interface ISfFileIOPropertyPage2 : public IPropertyPage2 {}; // 
expected-error {{interface type cannot inherit from}}
+
+struct IPropertyPage3 : public IUnknown {};
+__interface ISfFileIOPropertyPage3 : public IPropertyPage3 {};
+
+__interface __declspec(dllimport) ISfFileIOPropertyPage33 : public IUnknown {};
+
+struct __declspec(uuid("---C000-0046")) IUnknown4 {};
+__interface ISfFileIOPropertyPage4 : public IUnknown4 {}; // expected-error 
{{interface type cannot inherit from}}
+
+class __declspec(uuid("---C000-0046")) IUnknown5 {};
+__interface ISfFileIOPropertyPage5 : public IUnknown5 {}; // expected-error 
{{interface type cannot inherit from}}
+
+struct __declspec(dllexport) IUnknown6{};
+__interface foo : public IUnknown6{}; // expected-error {{interface type 
cannot inherit from}}
Index: lib/Sema/SemaDeclCXX.cpp
===
--- lib/Sema/SemaDeclCXX.cpp
+++ lib/Sema/SemaDeclCXX.cpp
@@ -2373,6 +2373,35 @@
   return true;
 }
 
+/// \brief Tests if the __interface base is public.
+static bool IsRecordPublicInterface(const CXXRecordDecl *RD,
+  AccessSpecifier spec) {
+  return RD->isInterface() && spec == AS_public;
+}
+
+/// \brief Test if record is an uuid Unknown.
+/// This is an MS SDK specific type that has a special
+/// behavior in the CL compiler.
+static bool IsUnknownType(const CXXRecordDecl *RD) {
+  auto *Uuid = RD->getAttr();
+  
+  return RD->isStruct() && RD->getName() == "IUnknown" && RD->isEmpty() &&
+ Uuid && Uuid->getGuid() =="---C000-0046";
+}
+
+/// \brief Test if record and records in inheritance tree is a an Unknown.
+static bool IsOrInheritsFromUnknown(const CXXRecordDecl *RD) {
+  if (RD->getNumBases()) {
+const CXXRecordDecl *Base =
+  RD->bases_begin()->getType()->getAsCXXRecordDecl();
+
+return Base && IsUnknownType(Base) && !IsUnknownType(RD) &&
+   IsOrInheritsFromUnknown(Base);
+  } else {
+return IsUnknownType(RD);
+  }
+}
+
 /// Use small set to collect indirect bases.  As this is only used
 /// locally, there's no need to abstract the small size parameter.
 typedef llvm::SmallPtrSet IndirectBaseSet;
@@ -2450,8 +2479,8 @@
   if (const RecordType *Record = NewBaseType->getAs()) {
 const CXXRecordDecl *RD = cast(Record->getDecl());
 if (Class->isInterface() &&
-  (!RD->isInterface() ||
-   KnownBase->getAccessSpecifier() != AS_public)) {
+!IsRecordPublicInterface(RD, KnownBase->getAccessSpecifier()) &&
+!IsOrInheritsFromUnknown(RD)) {
   // The Microsoft extension __interface does not permit bases that
   // are not themselves public interfaces.
   Diag(KnownBase->getLocStart(), diag::err_invalid_base_in_interface)


Index: test/SemaCXX/ms-uuid.cpp
===
--- test/SemaCXX/ms-uuid.cpp
+++ test/SemaCXX/ms-uuid.cpp
@@ -93,3 +93,27 @@
 [uuid("00A0---C000-0049"),
  uuid("00A0---C000-0049")] class C10;
 }
+
+struct __declspec(uuid("---C000-0046")) IUnknown {};
+__interface ISfFileIOPropertyPage : public IUnknown {};
+
+struct __declspec(uuid("---C000-0045")) IUnknown1 {};
+__interface ISfFileIOPropertyPage1 : public IUnknown1 {};  // expected-error {{interface type cannot inherit from}}
+
+struct __declspec(uuid("---C000-0046")) IUnknown2 {};
+struct IPropertyPage2 : public IUnknown2 {};
+__interface ISfFileIOPropertyPage2 : public IPropertyPage2 {}; // expected-error {{interface type cannot inherit from}}
+
+struct IPropertyPage3 : public IUnknown {};
+__interface ISfFileIOPropertyPage3 : public IPropertyPage3 {};
+
+__interface __declspec(dllimport) ISfFileIOPropertyPage33 : public IUnknown {};
+
+struct __declspec(uuid("---C000-0046")) IUnknow

[PATCH] D37308: Interface class with uuid base record

2017-09-09 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 114497.
zahiraam added a comment.

Erich,

Addressed your comments.
Thanks.


https://reviews.llvm.org/D37308

Files:
  lib/Sema/SemaDeclCXX.cpp
  test/SemaCXX/ms-uuid.cpp


Index: test/SemaCXX/ms-uuid.cpp
===
--- test/SemaCXX/ms-uuid.cpp
+++ test/SemaCXX/ms-uuid.cpp
@@ -93,3 +93,32 @@
 [uuid("00A0---C000-0049"),
  uuid("00A0---C000-0049")] class C10;
 }
+
+struct __declspec(uuid("---C000-0046")) IUnknown {};
+struct IPropertyPageBase : public IUnknown {};
+struct IPropertyPage : public IPropertyPageBase {};
+__interface ISfFileIOPropertyPage : public IPropertyPage {};
+
+
+__interface ISfFileIOPropertyPage1 : public IUnknown {};
+
+struct __declspec(uuid("---C000-0045")) IUnknown1 {};
+__interface ISfFileIOPropertyPage2 : public IUnknown1 {};  // expected-error 
{{interface type cannot inherit from}}
+
+struct __declspec(uuid("---C000-0046")) IUnknown2 {};
+struct IPropertyPage2 : public IUnknown2 {};
+__interface ISfFileIOPropertyPage3 : public IPropertyPage2 {}; // 
expected-error {{interface type cannot inherit from}}
+
+struct IPropertyPage3 : public IUnknown {};
+__interface ISfFileIOPropertyPage4 : public IPropertyPage3 {};
+
+__interface __declspec(dllimport) ISfFileIOPropertyPage33 : public IUnknown {};
+
+struct __declspec(uuid("---C000-0046")) IUnknown4 {};
+__interface ISfFileIOPropertyPage5 : public IUnknown4 {}; // expected-error 
{{interface type cannot inherit from}}
+
+class __declspec(uuid("---C000-0046")) IUnknown5 {};
+__interface ISfFileIOPropertyPage6 : public IUnknown5 {}; // expected-error 
{{interface type cannot inherit from}}
+
+struct __declspec(dllexport) IUnknown6{};
+__interface foo : public IUnknown6{}; // expected-error {{interface type 
cannot inherit from}}
Index: lib/Sema/SemaDeclCXX.cpp
===
--- lib/Sema/SemaDeclCXX.cpp
+++ lib/Sema/SemaDeclCXX.cpp
@@ -2373,6 +2373,33 @@
   return true;
 }
 
+/// \brief Tests if the __interface base is public.
+static bool IsDeclPublicInterface(const CXXRecordDecl *RD,
+  AccessSpecifier spec) {
+  return RD->isInterface() && spec == AS_public;
+}
+
+/// \brief Test if record is an uuid Unknown.
+/// This is an MS SDK specific type that has a special
+/// behavior in the CL compiler.
+static bool IsIUnknownType(const CXXRecordDecl *RD) {
+  auto *Uuid = RD->getAttr();
+
+  return RD->isStruct() && RD->getName() == "IUnknown" && RD->isEmpty() &&
+ Uuid && Uuid->getGuid() =="---C000-0046" &&
+ dyn_cast(RD->getDeclContext());
+}
+
+/// \brief Test if RD or its inhetited bases is an IUnknow type.
+static bool IsOrInheritsFromIUnknown(const CXXRecordDecl *RD) {
+  const CXXRecordDecl *Base =
+  RD->getNumBases() ? RD->bases_begin()->getType()->getAsCXXRecordDecl()
+: nullptr;
+
+  return IsIUnknownType(RD) ||
+ Base &&  (IsIUnknownType(Base) || IsOrInheritsFromIUnknown(Base));
+}
+
 /// Use small set to collect indirect bases.  As this is only used
 /// locally, there's no need to abstract the small size parameter.
 typedef llvm::SmallPtrSet IndirectBaseSet;
@@ -2450,10 +2477,10 @@
   if (const RecordType *Record = NewBaseType->getAs()) {
 const CXXRecordDecl *RD = cast(Record->getDecl());
 if (Class->isInterface() &&
-  (!RD->isInterface() ||
-   KnownBase->getAccessSpecifier() != AS_public)) {
-  // The Microsoft extension __interface does not permit bases that
-  // are not themselves public interfaces.
+// The Microsoft extension __interface does not permit bases that
+// are not themselves public interfaces.
+!IsDeclPublicInterface(RD, KnownBase->getAccessSpecifier()) &&
+!IsOrInheritsFromIUnknown(RD)) {
   Diag(KnownBase->getLocStart(), diag::err_invalid_base_in_interface)
 << getRecordDiagFromTagKind(RD->getTagKind()) << RD->getName()
 << RD->getSourceRange();


Index: test/SemaCXX/ms-uuid.cpp
===
--- test/SemaCXX/ms-uuid.cpp
+++ test/SemaCXX/ms-uuid.cpp
@@ -93,3 +93,32 @@
 [uuid("00A0---C000-0049"),
  uuid("00A0---C000-0049")] class C10;
 }
+
+struct __declspec(uuid("---C000-0046")) IUnknown {};
+struct IPropertyPageBase : public IUnknown {};
+struct IPropertyPage : public IPropertyPageBase {};
+__interface ISfFileIOPropertyPage : public IPropertyPage {};
+
+
+__interface ISfFileIOPropertyPage1 : public IUnknown {};
+
+struct __declspec(uuid("---C000-0045")) IUnknown1 {};
+__interface ISfFileIOPropertyPage2 : public IUnkn

[PATCH] D37308: Interface class with uuid base record

2017-09-12 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 114935.
zahiraam added a comment.

Erich, Aaron,
Please review at your convenience. 
Thanks.


https://reviews.llvm.org/D37308

Files:
  lib/Sema/SemaDeclCXX.cpp
  test/SemaCXX/ms-uuid.cpp


Index: test/SemaCXX/ms-uuid.cpp
===
--- test/SemaCXX/ms-uuid.cpp
+++ test/SemaCXX/ms-uuid.cpp
@@ -93,3 +93,32 @@
 [uuid("00A0---C000-0049"),
  uuid("00A0---C000-0049")] class C10;
 }
+
+struct __declspec(uuid("---C000-0046")) IUnknown {};
+struct IPropertyPageBase : public IUnknown {};
+struct IPropertyPage : public IPropertyPageBase {};
+__interface ISfFileIOPropertyPage : public IPropertyPage {};
+
+
+__interface ISfFileIOPropertyPage1 : public IUnknown {};
+
+struct __declspec(uuid("---C000-0045")) IUnknown1 {};
+__interface ISfFileIOPropertyPage2 : public IUnknown1 {};  // expected-error 
{{interface type cannot inherit from}}
+
+struct __declspec(uuid("---C000-0046")) IUnknown2 {};
+struct IPropertyPage2 : public IUnknown2 {};
+__interface ISfFileIOPropertyPage3 : public IPropertyPage2 {}; // 
expected-error {{interface type cannot inherit from}}
+
+struct IPropertyPage3 : public IUnknown {};
+__interface ISfFileIOPropertyPage4 : public IPropertyPage3 {};
+
+__interface __declspec(dllimport) ISfFileIOPropertyPage33 : public IUnknown {};
+
+struct __declspec(uuid("---C000-0046")) IUnknown4 {};
+__interface ISfFileIOPropertyPage5 : public IUnknown4 {}; // expected-error 
{{interface type cannot inherit from}}
+
+class __declspec(uuid("---C000-0046")) IUnknown5 {};
+__interface ISfFileIOPropertyPage6 : public IUnknown5 {}; // expected-error 
{{interface type cannot inherit from}}
+
+struct __declspec(dllexport) IUnknown6{};
+__interface foo : public IUnknown6{}; // expected-error {{interface type 
cannot inherit from}}
Index: lib/Sema/SemaDeclCXX.cpp
===
--- lib/Sema/SemaDeclCXX.cpp
+++ lib/Sema/SemaDeclCXX.cpp
@@ -2373,6 +2373,33 @@
   return true;
 }
 
+/// \brief Tests if RD is a public interface.
+static bool IsDeclPublicInterface(const CXXRecordDecl *RD,
+  AccessSpecifier spec) {
+  return RD->isInterface() && spec == AS_public;
+}
+
+/// \brief Test if record is a uuid for IUnknown.
+/// This is an MS SDK specific type that has a special
+/// behavior in the CL compiler.
+static bool IsIUnknownType(const CXXRecordDecl *RD) {
+  const auto *Uuid = RD->getAttr();
+
+  return Uuid && Uuid->getGuid() =="---C000-0046" &&
+ RD->isStruct() && RD->getName() == "IUnknown" && RD->isEmpty() &&
+ RD->getDeclContext()->isTranslationUnit();
+}
+
+/// \brief Test if RD or its inherited bases is an IUnknow type.
+static bool IsOrInheritsFromIUnknown(const CXXRecordDecl *RD) {
+  bool result = IsIUnknownType(RD);
+  for (const auto *I = RD->bases_begin(), *E = RD->bases_end(); I != E; ++I) {
+const CXXRecordDecl *BB = I->getType()->getAsCXXRecordDecl();
+return result || IsOrInheritsFromIUnknown(BB);
+  }
+  return result;
+}
+
 /// Use small set to collect indirect bases.  As this is only used
 /// locally, there's no need to abstract the small size parameter.
 typedef llvm::SmallPtrSet IndirectBaseSet;
@@ -2450,10 +2477,10 @@
   if (const RecordType *Record = NewBaseType->getAs()) {
 const CXXRecordDecl *RD = cast(Record->getDecl());
 if (Class->isInterface() &&
-  (!RD->isInterface() ||
-   KnownBase->getAccessSpecifier() != AS_public)) {
-  // The Microsoft extension __interface does not permit bases that
-  // are not themselves public interfaces.
+// The Microsoft extension __interface does not permit bases that
+// are not themselves public interfaces.
+!IsDeclPublicInterface(RD, KnownBase->getAccessSpecifier()) &&
+!IsOrInheritsFromIUnknown(RD)) {
   Diag(KnownBase->getLocStart(), diag::err_invalid_base_in_interface)
 << getRecordDiagFromTagKind(RD->getTagKind()) << RD->getName()
 << RD->getSourceRange();


Index: test/SemaCXX/ms-uuid.cpp
===
--- test/SemaCXX/ms-uuid.cpp
+++ test/SemaCXX/ms-uuid.cpp
@@ -93,3 +93,32 @@
 [uuid("00A0---C000-0049"),
  uuid("00A0---C000-0049")] class C10;
 }
+
+struct __declspec(uuid("---C000-0046")) IUnknown {};
+struct IPropertyPageBase : public IUnknown {};
+struct IPropertyPage : public IPropertyPageBase {};
+__interface ISfFileIOPropertyPage : public IPropertyPage {};
+
+
+__interface ISfFileIOPropertyPage1 : public IUnknown {};
+
+struct __declspec(uuid("---C000-0045")) IUnknown1 {};
+__interface IS

[PATCH] D37308: Interface class with uuid base record

2017-09-13 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 115125.
zahiraam added a comment.

Hi have made all the changes requested.


https://reviews.llvm.org/D37308

Files:
  lib/Sema/SemaDeclCXX.cpp


Index: lib/Sema/SemaDeclCXX.cpp
===
--- lib/Sema/SemaDeclCXX.cpp
+++ lib/Sema/SemaDeclCXX.cpp
@@ -2373,6 +2373,40 @@
   return true;
 }
 
+/// \brief Tests if RD is a public interface.
+static bool IsDeclPublicInterface(const CXXRecordDecl *RD,
+  AccessSpecifier spec) {
+  return RD->isInterface() && spec == AS_public;
+}
+
+/// \brief Test if record is a uuid for IUnknown.
+/// This is an MS SDK specific type that has a special
+/// behavior in the CL compiler.
+static bool IsIUnknownType(const CXXRecordDecl *RD) {
+  const auto *Uuid = RD->getAttr();
+
+  return Uuid && RD->isStruct()  && RD->isEmpty() &&
+ RD->getDeclContext()->isTranslationUnit() &&
+ RD->getName() == "IUnknown" &&
+ Uuid->getGuid() =="---C000-0046";
+}
+
+/// \brief Test if RD or its inherited bases is an IUnknown type.
+static bool IsOrInheritsFromIUnknown(const CXXRecordDecl *RD) {
+  bool IsUnknown = IsIUnknownType(RD);
+  for (CXXRecordDecl::base_class_const_iterator Base = RD->bases_begin(),
+BaseEnd = RD->bases_end();
+   Base != BaseEnd; ++Base) {
+   CXXRecordDecl *BaseChild = Base->getType()->getAsCXXRecordDecl();
+   
+   return IsUnknown ||
+  IsOrInheritsFromIUnknown(BaseChild) ||
+  (RD->getNumBases() > 1) &&
+  IsOrInheritsFromIUnknown((CXXRecordDecl*) 
BaseChild->getNextDeclInContext());
+  }
+  return IsUnknown;
+}
+
 /// Use small set to collect indirect bases.  As this is only used
 /// locally, there's no need to abstract the small size parameter.
 typedef llvm::SmallPtrSet IndirectBaseSet;
@@ -2450,10 +2484,10 @@
   if (const RecordType *Record = NewBaseType->getAs()) {
 const CXXRecordDecl *RD = cast(Record->getDecl());
 if (Class->isInterface() &&
-  (!RD->isInterface() ||
-   KnownBase->getAccessSpecifier() != AS_public)) {
-  // The Microsoft extension __interface does not permit bases that
-  // are not themselves public interfaces.
+// The Microsoft extension __interface does not permit bases that
+// are not themselves public interfaces.
+!IsDeclPublicInterface(RD, KnownBase->getAccessSpecifier()) &&
+!IsOrInheritsFromIUnknown(RD)) {
   Diag(KnownBase->getLocStart(), diag::err_invalid_base_in_interface)
 << getRecordDiagFromTagKind(RD->getTagKind()) << RD->getName()
 << RD->getSourceRange();


Index: lib/Sema/SemaDeclCXX.cpp
===
--- lib/Sema/SemaDeclCXX.cpp
+++ lib/Sema/SemaDeclCXX.cpp
@@ -2373,6 +2373,40 @@
   return true;
 }
 
+/// \brief Tests if RD is a public interface.
+static bool IsDeclPublicInterface(const CXXRecordDecl *RD,
+  AccessSpecifier spec) {
+  return RD->isInterface() && spec == AS_public;
+}
+
+/// \brief Test if record is a uuid for IUnknown.
+/// This is an MS SDK specific type that has a special
+/// behavior in the CL compiler.
+static bool IsIUnknownType(const CXXRecordDecl *RD) {
+  const auto *Uuid = RD->getAttr();
+
+  return Uuid && RD->isStruct()  && RD->isEmpty() &&
+ RD->getDeclContext()->isTranslationUnit() &&
+ RD->getName() == "IUnknown" &&
+ Uuid->getGuid() =="---C000-0046";
+}
+
+/// \brief Test if RD or its inherited bases is an IUnknown type.
+static bool IsOrInheritsFromIUnknown(const CXXRecordDecl *RD) {
+  bool IsUnknown = IsIUnknownType(RD);
+  for (CXXRecordDecl::base_class_const_iterator Base = RD->bases_begin(),
+BaseEnd = RD->bases_end();
+   Base != BaseEnd; ++Base) {
+   CXXRecordDecl *BaseChild = Base->getType()->getAsCXXRecordDecl();
+   
+   return IsUnknown ||
+  IsOrInheritsFromIUnknown(BaseChild) ||
+  (RD->getNumBases() > 1) &&
+  IsOrInheritsFromIUnknown((CXXRecordDecl*) BaseChild->getNextDeclInContext());
+  }
+  return IsUnknown;
+}
+
 /// Use small set to collect indirect bases.  As this is only used
 /// locally, there's no need to abstract the small size parameter.
 typedef llvm::SmallPtrSet IndirectBaseSet;
@@ -2450,10 +2484,10 @@
   if (const RecordType *Record = NewBaseType->getAs()) {
 const CXXRecordDecl *RD = cast(Record->getDecl());
 if (Class->isInterface() &&
-  (!RD->isInterface() ||
-   KnownBase->getAccessSpecifier() != AS_public)) {
-  // The Microsoft extension __interface does not permit bases that
-  // are not themselves public interfaces.
+// The Microsoft extension __interface does not permit bases that
+ 

[PATCH] D37308: Interface class with uuid base record

2017-09-13 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added a comment.

Erich,

The IsOrInheritsFromIUnknown function is needed. 
Wh




Comment at: lib/Sema/SemaDeclCXX.cpp:2377
+/// \brief Tests if the __interface base is public.
+static bool IsBasePublicInterface(const CXXRecordDecl *RD,
+  AccessSpecifier spec) {

erichkeane wrote:
> This function isn't testing the 'base', it is testing the actual record decl.
RD is the base of the interface. But I can rename it to IsRDPublicInterface.


https://reviews.llvm.org/D37308



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D37308: Interface class with uuid base record

2017-09-13 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added a comment.

MSVC and xmain compile this:
struct __declspec(uuid("---C000-0046")) IUnknown {};
struct PageBase : public IUnknown {};
struct Page3 : public PageBase {};
struct Page4 : public PageBase {};
__interface PropertyPage : public Page4 {};

But MSVC doesn't compile this:

struct __declspec(uuid("---C000-0046")) IUnknown {};
struct PageBase : public IUnknown {};
struct Page3 : public PageBase {};
struct Page4 : public PageBase {};
struct Page5 : public Page3, Page4{};
__interface PropertyPage : public Page5 {};

So a base of RD that has siblings and inherits from a Unknown is not permitted. 
Which means that if the number is siblings are greater than one, we should 
fail. I guess the current function doesn't take that into account.


https://reviews.llvm.org/D37308



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D43576: Solution to fix PR27066 - Redefinition with same mangled name as another definition (dllexport and uuid)

2019-05-30 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added a comment.

A review please :-) Thanks.


CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D43576/new/

https://reviews.llvm.org/D43576



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D43576: Solution to fix PR27066 - Redefinition with same mangled name as another definition (dllexport and uuid)

2019-07-03 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added inline comments.



Comment at: include/clang/AST/Decl.h:4303
+
+   StringLiteral *getSTLUuid() { return STLUuid; }
+};

rsmith wrote:
> What does "STL" mean here?
Renamed it.



Comment at: lib/CodeGen/CodeGenModule.cpp:1071-1073
+  const auto ExistingRecord = Manglings.find(MangledName);
+  if (ExistingRecord != std::end(Manglings))
+Manglings.remove(&(*ExistingRecord));

rsmith wrote:
> Was this supposed to be included in this patch? It looks like this is 
> papering over a bug elsewhere.
This is the code that actually fixes the bug. The rest of the patch is to 
represent uuid in the AST.



Comment at: lib/CodeGen/CodeGenModule.cpp:1071-1073
+  const auto ExistingRecord = Manglings.find(MangledName);
+  if (ExistingRecord != std::end(Manglings))
+Manglings.remove(&(*ExistingRecord));

zahiraam wrote:
> rsmith wrote:
> > Was this supposed to be included in this patch? It looks like this is 
> > papering over a bug elsewhere.
> This is the code that actually fixes the bug. The rest of the patch is to 
> represent uuid in the AST.
Removed.


CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D43576/new/

https://reviews.llvm.org/D43576



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D43576: Solution to fix PR27066 - Redefinition with same mangled name as another definition (dllexport and uuid)

2019-07-03 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 207882.
zahiraam marked 14 inline comments as done.
zahiraam added a comment.

Thanks for the review.
I  think and hope that I have responded to every issue you raised. Let me know 
if there are still pending issues.
Happy 4th!


CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D43576/new/

https://reviews.llvm.org/D43576

Files:
  clang/include/clang/AST/Decl.h
  clang/include/clang/AST/RecursiveASTVisitor.h
  clang/include/clang/Basic/Attr.td
  clang/include/clang/Basic/DeclNodes.td
  clang/include/clang/Sema/Sema.h
  clang/lib/AST/Decl.cpp
  clang/lib/AST/DeclBase.cpp
  clang/lib/AST/DeclCXX.cpp
  clang/lib/CodeGen/CGDecl.cpp
  clang/lib/Sema/SemaDecl.cpp
  clang/lib/Sema/SemaDeclAttr.cpp
  clang/lib/Sema/SemaExprCXX.cpp
  clang/lib/Sema/SemaTemplateInstantiateDecl.cpp
  clang/test/Sema/ms-uuid-1.cpp
  clang/test/Sema/ms-uuid-2.cpp
  clang/utils/TableGen/ClangAttrEmitter.cpp

Index: clang/utils/TableGen/ClangAttrEmitter.cpp
===
--- clang/utils/TableGen/ClangAttrEmitter.cpp
+++ clang/utils/TableGen/ClangAttrEmitter.cpp
@@ -321,12 +321,15 @@
 OS << "\" << get" << getUpperName() << "().getAsString() << \"";
   else if (type == "ParamIdx")
 OS << "\" << get" << getUpperName() << "().getSourceIndex() << \"";
-  else
+  else if (type == "DeclSpecUuidDecl *") {
+OS << "\" << get" << getUpperName() << "() << \"";
+  } else
 OS << "\" << get" << getUpperName() << "() << \"";
 }
 
 void writeDump(raw_ostream &OS) const override {
-  if (type == "FunctionDecl *" || type == "NamedDecl *") {
+  if (type == "FunctionDecl *" || type == "NamedDecl *" ||
+  type == "DeclSpecUuidDecl *") {
 OS << "OS << \" \";\n";
 OS << "dumpBareDeclRef(SA->get" << getUpperName() << "());\n"; 
   } else if (type == "IdentifierInfo *") {
@@ -1296,6 +1299,8 @@
 Ptr = llvm::make_unique(Arg, Attr);
   else if (ArgName == "VersionArgument")
 Ptr = llvm::make_unique(Arg, Attr);
+  else if (ArgName == "DeclSpecUuidDeclArgument")
+Ptr = llvm::make_unique(Arg, Attr, "DeclSpecUuidDecl *");
 
   if (!Ptr) {
 // Search in reverse order so that the most-derived type is handled first.
Index: clang/test/Sema/ms-uuid-2.cpp
===
--- /dev/null
+++ clang/test/Sema/ms-uuid-2.cpp
@@ -0,0 +1,17 @@
+// RUN: %clang_cc1 -fsyntax-only -verify -fms-extensions -fms-compatibility -std=c++14  %s
+
+
+typedef struct _GUID
+{
+unsigned long  Data1;
+unsigned short Data2;
+unsigned short Data3;
+unsigned char  Data4[8];
+} GUID;
+
+// expected-error@+5 {{C++ requires a type specifier for all declarations}}
+// expected-error@+4 {{invalid digit 'a' in decimal constant}}
+// expected-error@+3 {{use of undeclared identifier 'def0'}}
+// expected-error@+2 {{invalid digit 'a' in decimal constant}}
+// expected-error@+1 {{expected ';' after top level declarator}}
+uuid(12345678-9abc-def0-1234-56789abcdef0) struct S2;
Index: clang/test/Sema/ms-uuid-1.cpp
===
--- /dev/null
+++ clang/test/Sema/ms-uuid-1.cpp
@@ -0,0 +1,31 @@
+// RUN: %clang_cc1 -fsyntax-only -verify -fms-extensions -fms-compatibility -std=c++14 %s
+// expected-no-diagnostics
+typedef struct _GUID {
+  int i;
+} IID;
+template 
+class A {};
+
+struct
+__declspec(uuid("{DDB47A6A-0F23-11D5-9109-00E0296B75D3}"))
+S1 {};
+
+struct
+__declspec(uuid("{DDB47A6A-0F23-11D5-9109-00E0296B75D3}"))
+S2 {};
+
+struct __declspec(dllexport)
+C1 : public A<&__uuidof(S1)> {};
+
+struct __declspec(dllexport)
+C2 : public A<&__uuidof(S2)> {};
+int printf(const char *, ...);
+int main() {
+
+  if (&__uuidof(S1) == &__uuidof(S2))
+printf("OK\n");
+  else
+printf("ERROR\n");
+
+  return 0;
+}
Index: clang/lib/Sema/SemaTemplateInstantiateDecl.cpp
===
--- clang/lib/Sema/SemaTemplateInstantiateDecl.cpp
+++ clang/lib/Sema/SemaTemplateInstantiateDecl.cpp
@@ -641,6 +641,11 @@
   return Inst;
 }
 
+Decl *
+TemplateDeclInstantiator::VisitDeclSpecUuidDecl(DeclSpecUuidDecl *D) {
+   llvm_unreachable("DeclSpecUuidDecl cannot be instantiated");
+}
+
 Decl *TemplateDeclInstantiator::InstantiateTypedefNameDecl(TypedefNameDecl *D,
bool IsTypeAlias) {
   bool Invalid = false;
Index: clang/lib/Sema/SemaExprCXX.cpp
===
--- clang/lib/Sema/SemaExprCXX.cpp
+++ clang/lib/Sema/SemaExprCXX.cpp
@@ -628,7 +628,7 @@
   return ExprError(Diag(TypeidLoc, diag::err_uuidof_without_guid));
 if (UuidAttrs.size() > 1)
   return ExprError(Diag(TypeidLoc, diag::err_uuidof_with_multiple_guids));
-UuidStr = UuidAttrs.back()->getGuid();
+UuidStr = UuidAttrs.back()->getDecl

[PATCH] D43576: Solution to fix PR27066 - Redefinition with same mangled name as another definition (dllexport and uuid)

2019-05-20 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam marked 12 inline comments as done.
zahiraam added a comment.

@rsmith I think I have made all the changes you have pointed out to. But please 
note that this new patch only impements an explicit AST representation of uuid  
in template arguments. It **does not** fix the bug for which this review was 
opened for. 
I will take care of the bug in time. But before doing that I want to make sure 
that the changes required to give an explicit AST for uuid is correct.

Thanks for taking the time to review. And sorry my response is slow to come. 
This work is done in my "spare" time.




Comment at: lib/Sema/SemaExprCXX.cpp:675-678
+  if (expr.isUnset()) {
+uuid_expr =
+new (Context) CXXUuidofExpr(TypeInfoType.withConst(), Operand, UuidStr,
+SourceRange(TypeidLoc, RParenLoc));

rsmith wrote:
> We should store a pointer to the UUID declaration on a non-dependent 
> `CXXUuidofExpr`.
Not sure what that means.



Comment at: lib/Sema/SemaExprCXX.cpp:675-678
+  if (expr.isUnset()) {
+uuid_expr =
+new (Context) CXXUuidofExpr(TypeInfoType.withConst(), Operand, UuidStr,
+SourceRange(TypeidLoc, RParenLoc));

zahiraam wrote:
> rsmith wrote:
> > We should store a pointer to the UUID declaration on a non-dependent 
> > `CXXUuidofExpr`.
> Not sure what that means.
However the test case is still failing. Still need to find a solution for the 
fail.



Comment at: lib/Sema/SemaExprCXX.cpp:619
+ /// Finds the __declSpec uuid Decl off a type.
+ static void FindADeclOffAType(Sema &SemaRef,
+   QualType QT,

rsmith wrote:
> Do we need both this and getUuidAttrOfType?
No.


CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D43576/new/

https://reviews.llvm.org/D43576



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D43576: Solution to fix PR27066 - Redefinition with same mangled name as another definition (dllexport and uuid)

2019-05-20 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 200258.
zahiraam marked 2 inline comments as done.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D43576/new/

https://reviews.llvm.org/D43576

Files:
  include/clang/AST/Decl.h
  include/clang/AST/RecursiveASTVisitor.h
  include/clang/Basic/Attr.td
  include/clang/Basic/DeclNodes.td
  include/clang/Sema/ParsedAttr.h
  include/clang/Sema/Sema.h
  lib/AST/Decl.cpp
  lib/AST/DeclBase.cpp
  lib/AST/DeclCXX.cpp
  lib/CodeGen/CGDecl.cpp
  lib/CodeGen/CodeGenModule.cpp
  lib/Sema/SemaDecl.cpp
  lib/Sema/SemaDeclAttr.cpp
  lib/Sema/SemaExprCXX.cpp
  lib/Sema/SemaTemplateInstantiateDecl.cpp
  lib/Serialization/ASTCommon.cpp
  test/Sema/ms-uuid-1.cpp
  test/Sema/ms-uuid-2.cpp
  utils/TableGen/ClangAttrEmitter.cpp

Index: utils/TableGen/ClangAttrEmitter.cpp
===
--- utils/TableGen/ClangAttrEmitter.cpp
+++ utils/TableGen/ClangAttrEmitter.cpp
@@ -321,12 +321,15 @@
 OS << "\" << get" << getUpperName() << "().getAsString() << \"";
   else if (type == "ParamIdx")
 OS << "\" << get" << getUpperName() << "().getSourceIndex() << \"";
-  else
+  else if (type == "DeclSpecUuidDecl *") {
+OS << "\" << get" << getUpperName() << "() << \"";
+  } else
 OS << "\" << get" << getUpperName() << "() << \"";
 }
 
 void writeDump(raw_ostream &OS) const override {
-  if (type == "FunctionDecl *" || type == "NamedDecl *") {
+  if (type == "FunctionDecl *" || type == "NamedDecl *" ||
+  type == "DeclSpecUuidDecl *") {
 OS << "OS << \" \";\n";
 OS << "dumpBareDeclRef(SA->get" << getUpperName() << "());\n"; 
   } else if (type == "IdentifierInfo *") {
@@ -1296,6 +1299,9 @@
 Ptr = llvm::make_unique(Arg, Attr);
   else if (ArgName == "VersionArgument")
 Ptr = llvm::make_unique(Arg, Attr);
+  else if (ArgName == "DeclSpecUuidDeclArgument")
+Ptr = llvm::make_unique(Arg, Attr, "DeclSpecUuidDecl *");
+
 
   if (!Ptr) {
 // Search in reverse order so that the most-derived type is handled first.
Index: test/Sema/ms-uuid-2.cpp
===
--- /dev/null
+++ test/Sema/ms-uuid-2.cpp
@@ -0,0 +1,18 @@
+// RUN: %clang_cc1 -fsyntax-only -verify -fms-extensions -fms-compatibility -std=c++14  %s
+
+
+typedef struct _GUID
+{
+unsigned long  Data1;
+unsigned short Data2;
+unsigned short Data3;
+unsigned char  Data4[8];
+} GUID;
+
+// expected-error@+5 {{C++ requires a type specifier for all declarations}}
+// expected-error@+4 {{invalid digit 'a' in decimal constant}}
+// expected-error@+3 {{use of undeclared identifier 'def0'}}
+// expected-error@+2 {{invalid digit 'a' in decimal constant}}
+// expected-error@+1 {{expected ';' after top level declarator}}
+uuid(12345678-9abc-def0-1234-56789abcdef0) struct S2;
+
Index: test/Sema/ms-uuid-1.cpp
===
--- /dev/null
+++ test/Sema/ms-uuid-1.cpp
@@ -0,0 +1,31 @@
+// RUN: %clang_cc1 -fsyntax-only -verify -fms-extensions -fms-compatibility -std=c++14 %s
+// expected-no-diagnostics
+typedef struct _GUID {
+  int i;
+} IID;
+template 
+class A {};
+
+struct
+__declspec(uuid("{DDB47A6A-0F23-11D5-9109-00E0296B75D3}"))
+S1 {};
+
+struct
+__declspec(uuid("{DDB47A6A-0F23-11D5-9109-00E0296B75D3}"))
+S2 {};
+
+struct __declspec(dllexport)
+C1 : public A<&__uuidof(S1)> {};
+
+struct __declspec(dllexport)
+C2 : public A<&__uuidof(S2)> {};
+int printf(const char *, ...);
+int main() {
+
+  if (&__uuidof(S1) == &__uuidof(S2))
+printf("OK\n");
+  else
+printf("ERROR\n");
+
+  return 0;
+}
Index: lib/Serialization/ASTCommon.cpp
===
--- lib/Serialization/ASTCommon.cpp
+++ lib/Serialization/ASTCommon.cpp
@@ -348,6 +348,7 @@
   case Decl::ObjCProtocol:
   case Decl::ObjCInterface:
   case Decl::Empty:
+  case Decl::DeclSpecUuid:
 return true;
 
   // Never redeclarable.
Index: lib/Sema/SemaTemplateInstantiateDecl.cpp
===
--- lib/Sema/SemaTemplateInstantiateDecl.cpp
+++ lib/Sema/SemaTemplateInstantiateDecl.cpp
@@ -630,6 +630,11 @@
   return Inst;
 }
 
+ Decl *
+ TemplateDeclInstantiator::VisitDeclSpecUuidDecl(DeclSpecUuidDecl *D) {
+   llvm_unreachable("DeclSpecUuidDecl cannot be instantiated");
+}
+
 Decl *TemplateDeclInstantiator::InstantiateTypedefNameDecl(TypedefNameDecl *D,
bool IsTypeAlias) {
   bool Invalid = false;
Index: lib/Sema/SemaExprCXX.cpp
===
--- lib/Sema/SemaExprCXX.cpp
+++ lib/Sema/SemaExprCXX.cpp
@@ -628,11 +628,12 @@
   return ExprError(Diag(TypeidLoc, diag::err_uuidof_without_guid));
 if (UuidAttrs.size() > 1)
   return ExprError(Diag(TypeidLoc, diag::err_uuidof_

[PATCH] D43576: Solution to fix PR27066 - Redefinition with same mangled name as another definition (dllexport and uuid)

2019-05-21 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added a comment.

And this patch actually fixes the bug. Thanks.


CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D43576/new/

https://reviews.llvm.org/D43576



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D43576: Solution to fix PR27066 - Redefinition with same mangled name as another definition (dllexport and uuid)

2019-05-21 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 200484.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D43576/new/

https://reviews.llvm.org/D43576

Files:
  include/clang/AST/Decl.h
  include/clang/AST/RecursiveASTVisitor.h
  include/clang/Basic/Attr.td
  include/clang/Basic/DeclNodes.td
  include/clang/Sema/ParsedAttr.h
  include/clang/Sema/Sema.h
  lib/AST/Decl.cpp
  lib/AST/DeclBase.cpp
  lib/AST/DeclCXX.cpp
  lib/CodeGen/CGDecl.cpp
  lib/CodeGen/CodeGenModule.cpp
  lib/Sema/SemaDecl.cpp
  lib/Sema/SemaDeclAttr.cpp
  lib/Sema/SemaExprCXX.cpp
  lib/Sema/SemaTemplateInstantiateDecl.cpp
  lib/Serialization/ASTCommon.cpp
  test/Sema/ms-uuid-1.cpp
  test/Sema/ms-uuid-2.cpp
  utils/TableGen/ClangAttrEmitter.cpp

Index: utils/TableGen/ClangAttrEmitter.cpp
===
--- utils/TableGen/ClangAttrEmitter.cpp
+++ utils/TableGen/ClangAttrEmitter.cpp
@@ -321,12 +321,15 @@
 OS << "\" << get" << getUpperName() << "().getAsString() << \"";
   else if (type == "ParamIdx")
 OS << "\" << get" << getUpperName() << "().getSourceIndex() << \"";
-  else
+  else if (type == "DeclSpecUuidDecl *") {
+OS << "\" << get" << getUpperName() << "() << \"";
+  } else
 OS << "\" << get" << getUpperName() << "() << \"";
 }
 
 void writeDump(raw_ostream &OS) const override {
-  if (type == "FunctionDecl *" || type == "NamedDecl *") {
+  if (type == "FunctionDecl *" || type == "NamedDecl *" ||
+  type == "DeclSpecUuidDecl *") {
 OS << "OS << \" \";\n";
 OS << "dumpBareDeclRef(SA->get" << getUpperName() << "());\n"; 
   } else if (type == "IdentifierInfo *") {
@@ -1296,6 +1299,9 @@
 Ptr = llvm::make_unique(Arg, Attr);
   else if (ArgName == "VersionArgument")
 Ptr = llvm::make_unique(Arg, Attr);
+  else if (ArgName == "DeclSpecUuidDeclArgument")
+Ptr = llvm::make_unique(Arg, Attr, "DeclSpecUuidDecl *");
+
 
   if (!Ptr) {
 // Search in reverse order so that the most-derived type is handled first.
Index: test/Sema/ms-uuid-2.cpp
===
--- /dev/null
+++ test/Sema/ms-uuid-2.cpp
@@ -0,0 +1,18 @@
+// RUN: %clang_cc1 -fsyntax-only -verify -fms-extensions -fms-compatibility -std=c++14  %s
+
+
+typedef struct _GUID
+{
+unsigned long  Data1;
+unsigned short Data2;
+unsigned short Data3;
+unsigned char  Data4[8];
+} GUID;
+
+// expected-error@+5 {{C++ requires a type specifier for all declarations}}
+// expected-error@+4 {{invalid digit 'a' in decimal constant}}
+// expected-error@+3 {{use of undeclared identifier 'def0'}}
+// expected-error@+2 {{invalid digit 'a' in decimal constant}}
+// expected-error@+1 {{expected ';' after top level declarator}}
+uuid(12345678-9abc-def0-1234-56789abcdef0) struct S2;
+
Index: test/Sema/ms-uuid-1.cpp
===
--- /dev/null
+++ test/Sema/ms-uuid-1.cpp
@@ -0,0 +1,31 @@
+// RUN: %clang_cc1 -fsyntax-only -verify -fms-extensions -fms-compatibility -std=c++14 %s
+// expected-no-diagnostics
+typedef struct _GUID {
+  int i;
+} IID;
+template 
+class A {};
+
+struct
+__declspec(uuid("{DDB47A6A-0F23-11D5-9109-00E0296B75D3}"))
+S1 {};
+
+struct
+__declspec(uuid("{DDB47A6A-0F23-11D5-9109-00E0296B75D3}"))
+S2 {};
+
+struct __declspec(dllexport)
+C1 : public A<&__uuidof(S1)> {};
+
+struct __declspec(dllexport)
+C2 : public A<&__uuidof(S2)> {};
+int printf(const char *, ...);
+int main() {
+
+  if (&__uuidof(S1) == &__uuidof(S2))
+printf("OK\n");
+  else
+printf("ERROR\n");
+
+  return 0;
+}
Index: lib/Serialization/ASTCommon.cpp
===
--- lib/Serialization/ASTCommon.cpp
+++ lib/Serialization/ASTCommon.cpp
@@ -348,6 +348,7 @@
   case Decl::ObjCProtocol:
   case Decl::ObjCInterface:
   case Decl::Empty:
+  case Decl::DeclSpecUuid:
 return true;
 
   // Never redeclarable.
Index: lib/Sema/SemaTemplateInstantiateDecl.cpp
===
--- lib/Sema/SemaTemplateInstantiateDecl.cpp
+++ lib/Sema/SemaTemplateInstantiateDecl.cpp
@@ -630,6 +630,11 @@
   return Inst;
 }
 
+ Decl *
+ TemplateDeclInstantiator::VisitDeclSpecUuidDecl(DeclSpecUuidDecl *D) {
+   llvm_unreachable("DeclSpecUuidDecl cannot be instantiated");
+}
+
 Decl *TemplateDeclInstantiator::InstantiateTypedefNameDecl(TypedefNameDecl *D,
bool IsTypeAlias) {
   bool Invalid = false;
Index: lib/Sema/SemaExprCXX.cpp
===
--- lib/Sema/SemaExprCXX.cpp
+++ lib/Sema/SemaExprCXX.cpp
@@ -628,11 +628,12 @@
   return ExprError(Diag(TypeidLoc, diag::err_uuidof_without_guid));
 if (UuidAttrs.size() > 1)
   return ExprError(Diag(TypeidLoc, diag::err_uuidof_with_multiple_guids));
-UuidStr = UuidA

[PATCH] D43576: Solution to fix PR27066 - Redefinition with same mangled name as another definition (dllexport and uuid)

2018-04-14 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added a comment.

In https://reviews.llvm.org/D43576#1016295, @majnemer wrote:

> We should really, really avoid making this sort of change without first 
> trying to desugar uuidof into a reference to a variable. That would solve a 
> ton of problems, problems like this one.


Not sure I fully understand what you are proposing?

Are you proposing that generated symbols like this:
??4?$A@$E?_GUID_ddb47a6a_0f23_11d5_9109_00e0296b75d3@@3U__s_GUID@@B@@QEAAAEAV0@AEBV0@@Z
 
Be de-sugared? Wouldn't that be different that what MS is doing? 
Can you please give me more details about what you are thinking of?
Thanks.

In https://reviews.llvm.org/D43576#1019943, @rsmith wrote:

> In https://reviews.llvm.org/D43576#1019703, @zahiraam wrote:
>
> > Currently this declaration:
> > struct
> >  __declspec(uuid("{DDB47A6A-0F23-11D5-9109-00E0296B75D3}"))
> >  S1;
> >
> > a CXXRecordDecl type is generated with attributes (the uuid being an 
> > attribute). Are you proposing that instead a new type is generated for S1 
> > say something like CXXUuidRecord? And create also a new TagType that 
> > corresponds to this new Decl?
>
>
> No. Concretely, I'd suggest we create a new `UuidDecl` object representing 
> the `_GUID` object. An instance of `UuidDecl` would be created and owned by 
> the `uuid` attribute, and `__uuidof(X)` would denote the `UuidDecl` owned by 
> the `uuid` attribute on the `CXXRecordDecl`. We'd also need some way to form 
> redeclaration chains for `UuidDecl`s (which means we'll need a map from UUID 
> to `UuidDecl` somewhere, perhaps on the `ASTContext`).




In https://reviews.llvm.org/D43576#1019943, @rsmith wrote:

> In https://reviews.llvm.org/D43576#1019703, @zahiraam wrote:
>
> > Currently this declaration:
> > struct
> >  __declspec(uuid("{DDB47A6A-0F23-11D5-9109-00E0296B75D3}"))
> >  S1;
> >
> > a CXXRecordDecl type is generated with attributes (the uuid being an 
> > attribute). Are you proposing that instead a new type is generated for S1 
> > say something like CXXUuidRecord? And create also a new TagType that 
> > corresponds to this new Decl?
>
>
> No. Concretely, I'd suggest we create a new `UuidDecl` object representing 
> the `_GUID` object. An instance of `UuidDecl` would be created and owned by 
> the `uuid` attribute, and `__uuidof(X)` would denote the `UuidDecl` owned by 
> the `uuid` attribute on the `CXXRecordDecl`. We'd also need some way to form 
> redeclaration chains for `UuidDecl`s (which means we'll need a map from UUID 
> to `UuidDecl` somewhere, perhaps on the `ASTContext`).


As per Richard comment. I have added a UuidDecl owned by the uuid attribute. 
This patch concerns only this change. It is not a patch to fix the bug yet. I 
want to make sure that we are in agreement with my changes first. Then I will 
change the code that deal with ParseCXUuid. 
Comments are welcome. 
Thanks.


https://reviews.llvm.org/D43576



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D43576: Solution to fix PR27066 - Redefinition with same mangled name as another definition (dllexport and uuid)

2018-04-14 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 142516.

https://reviews.llvm.org/D43576

Files:
  include/clang/AST/Decl.h
  include/clang/AST/RecursiveASTVisitor.h
  include/clang/Basic/Attr.td
  include/clang/Basic/DeclNodes.td
  include/clang/Sema/AttributeList.h
  include/clang/Sema/Sema.h
  lib/AST/Decl.cpp
  lib/AST/DeclBase.cpp
  lib/AST/DeclCXX.cpp
  lib/Parse/ParseDecl.cpp
  lib/Sema/SemaDecl.cpp
  lib/Sema/SemaDeclAttr.cpp
  lib/Sema/SemaExprCXX.cpp
  lib/Sema/SemaTemplateInstantiateDecl.cpp
  utils/TableGen/ClangAttrEmitter.cpp

Index: utils/TableGen/ClangAttrEmitter.cpp
===
--- utils/TableGen/ClangAttrEmitter.cpp
+++ utils/TableGen/ClangAttrEmitter.cpp
@@ -322,12 +322,15 @@
 OS << "\" << get" << getUpperName() << "().getAsString() << \"";
   else if (type == "ParamIdx")
 OS << "\" << get" << getUpperName() << "().getSourceIndex() << \"";
-  else
+  else if (type == "DeclSpecUuidDecl *") {
+OS << "\" << get" << getUpperName() << "() << \"";
+	} else
 OS << "\" << get" << getUpperName() << "() << \"";
 }
 
 void writeDump(raw_ostream &OS) const override {
-  if (type == "FunctionDecl *" || type == "NamedDecl *") {
+  if (type == "FunctionDecl *" || type == "NamedDecl *" ||
+	  (type == "DeclSpecUuidDecl *")) {
 OS << "OS << \" \";\n";
 OS << "dumpBareDeclRef(SA->get" << getUpperName() << "());\n"; 
   } else if (type == "IdentifierInfo *") {
@@ -1280,6 +1283,8 @@
 Ptr = llvm::make_unique(Arg, Attr, "ParamIdx");
   else if (ArgName == "VersionArgument")
 Ptr = llvm::make_unique(Arg, Attr);
+  else if (ArgName == "DeclSpecUuidDeclArgument")
+Ptr = llvm::make_unique(Arg, Attr, "DeclSpecUuidDecl *");
 
   if (!Ptr) {
 // Search in reverse order so that the most-derived type is handled first.
Index: lib/Sema/SemaTemplateInstantiateDecl.cpp
===
--- lib/Sema/SemaTemplateInstantiateDecl.cpp
+++ lib/Sema/SemaTemplateInstantiateDecl.cpp
@@ -535,6 +535,15 @@
   return Inst;
 }
 
+Decl *
+TemplateDeclInstantiator::VisitDeclSpecUuidDecl(DeclSpecUuidDecl *D) {
+  DeclSpecUuidDecl *Inst = DeclSpecUuidDecl::Create(SemaRef.Context, Owner,
+D->getLocation(),
+D->getStrUuid());
+  Owner->addDecl(Inst);
+  return Inst;
+}
+
 Decl *TemplateDeclInstantiator::InstantiateTypedefNameDecl(TypedefNameDecl *D,
bool IsTypeAlias) {
   bool Invalid = false;
Index: lib/Sema/SemaExprCXX.cpp
===
--- lib/Sema/SemaExprCXX.cpp
+++ lib/Sema/SemaExprCXX.cpp
@@ -573,7 +573,7 @@
   return ExprError(Diag(TypeidLoc, diag::err_uuidof_without_guid));
 if (UuidAttrs.size() > 1)
   return ExprError(Diag(TypeidLoc, diag::err_uuidof_with_multiple_guids));
-UuidStr = UuidAttrs.back()->getGuid();
+UuidStr = UuidAttrs.back()->getDeclSpecUuidDecl()->getStrUuid();
   }
 
   return new (Context) CXXUuidofExpr(TypeInfoType.withConst(), Operand, UuidStr,
@@ -596,7 +596,8 @@
 return ExprError(Diag(TypeidLoc, diag::err_uuidof_without_guid));
   if (UuidAttrs.size() > 1)
 return ExprError(Diag(TypeidLoc, diag::err_uuidof_with_multiple_guids));
-  UuidStr = UuidAttrs.back()->getGuid();
+  UuidStr = UuidAttrs.back()->getDeclSpecUuidDecl()->getStrUuid();
+
 }
   }
 
Index: lib/Sema/SemaDeclAttr.cpp
===
--- lib/Sema/SemaDeclAttr.cpp
+++ lib/Sema/SemaDeclAttr.cpp
@@ -4930,14 +4930,10 @@
 //===--===//
 
 UuidAttr *Sema::mergeUuidAttr(Decl *D, SourceRange Range,
-  unsigned AttrSpellingListIndex, StringRef Uuid) {
-  if (const auto *UA = D->getAttr()) {
-if (UA->getGuid().equals_lower(Uuid))
-  return nullptr;
-Diag(UA->getLocation(), diag::err_mismatched_uuid);
-Diag(Range.getBegin(), diag::note_previous_uuid);
-D->dropAttr();
-  }
+  unsigned AttrSpellingListIndex,
+  DeclSpecUuidDecl *Uuid) {
+  if (D->getAttr())
+return nullptr;
 
   return ::new (Context) UuidAttr(Range, Context, Uuid, AttrSpellingListIndex);
 }
@@ -4949,9 +4945,9 @@
 return;
   }
 
-  StringRef StrRef;
-  SourceLocation LiteralLoc;
-  if (!S.checkStringLiteralArgumentAttr(AL, 0, StrRef, &LiteralLoc))
+  StringRef  StrRef = AL.getUuidDecl()->getStrUuid();
+  SourceLocation LiteralLoc = AL.getLoc();
+  if (StrRef.empty())
 return;
 
   // GUID format is "----" or
@@ -4987,7 +4983,9 @@
 S.Diag(AL.getLoc(), diag::warn_atl_uuid_deprecated);
 
   UuidAttr *UA = S.mergeUuidAttr(D, AL.getRange(),
-   

[PATCH] D43576: Solution to fix PR27066 - Redefinition with same mangled name as another definition (dllexport and uuid)

2018-04-15 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam marked 4 inline comments as done.
zahiraam added inline comments.



Comment at: lib/Parse/ParseDecl.cpp:572
+DeclSpecUuidDecl *ArgDecl =
+  DeclSpecUuidDecl::Create(Actions.getASTContext(),
+   Actions.getFunctionLevelDeclContext(),

rsmith wrote:
> What should happen if multiple declarations (of distinct entities) use the 
> same `__declspec(uuid(...))` attribute? Should you get a redefinition error 
> for the attribute or should they all share the same UUID entity? Either way, 
> we'll want to do some (minimal) UUID lookup and build a redeclaration chain 
> for `DeclSpecUuidDecl`s.
If we want to align with MS, we don't want  to signal an error. So may be I 
should have a map that assigns to each StrUuid a list of DeclSpecUuid?
So for this code:
struct
__declspec(uuid("{DDB47A6A-0F23-11D5-9109-00E0296B75D3}"))
S1 {};

struct
__declspec(uuid("{DDB47A6A-0F23-11D5-9109-00E0296B75D3}"))
S2 {};

I will have a map from DDB47A6A-0F23-11D5-9109-00E0296B75D3 to {S1, S2}. Do you 
agree?




Comment at: lib/Sema/SemaDeclAttr.cpp:4937-4938
-  return nullptr;
-Diag(UA->getLocation(), diag::err_mismatched_uuid);
-Diag(Range.getBegin(), diag::note_previous_uuid);
-D->dropAttr();

rsmith wrote:
> Do we still diagnose UUID mismatches somewhere else?
Not as far as I know. I guess I should put this diag somewhere?


https://reviews.llvm.org/D43576



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D43576: Solution to fix PR27066 - Redefinition with same mangled name as another definition (dllexport and uuid)

2018-04-20 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam marked 3 inline comments as done.
zahiraam added inline comments.



Comment at: lib/Sema/SemaDeclAttr.cpp:4937-4938
-  return nullptr;
-Diag(UA->getLocation(), diag::err_mismatched_uuid);
-Diag(Range.getBegin(), diag::note_previous_uuid);
-D->dropAttr();

zahiraam wrote:
> rsmith wrote:
> > Do we still diagnose UUID mismatches somewhere else?
> Not as far as I know. I guess I should put this diag somewhere?
Fixed the initial code.


https://reviews.llvm.org/D43576



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D43576: Solution to fix PR27066 - Redefinition with same mangled name as another definition (dllexport and uuid)

2018-04-20 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 143321.

https://reviews.llvm.org/D43576

Files:
  include/clang/AST/Decl.h
  include/clang/Basic/Attr.td
  include/clang/Sema/AttributeList.h
  include/clang/Sema/Sema.h
  lib/AST/Decl.cpp
  lib/AST/DeclCXX.cpp
  lib/CodeGen/CGDecl.cpp
  lib/CodeGen/CodeGenModule.cpp
  lib/Parse/ParseDecl.cpp
  lib/Sema/SemaDeclAttr.cpp
  lib/Serialization/ASTCommon.cpp
  utils/TableGen/ClangAttrEmitter.cpp

Index: utils/TableGen/ClangAttrEmitter.cpp
===
--- utils/TableGen/ClangAttrEmitter.cpp
+++ utils/TableGen/ClangAttrEmitter.cpp
@@ -330,7 +330,7 @@
 
 void writeDump(raw_ostream &OS) const override {
   if (type == "FunctionDecl *" || type == "NamedDecl *" ||
-	  (type == "DeclSpecUuidDecl *")) {
+  type == "DeclSpecUuidDecl *") {
 OS << "OS << \" \";\n";
 OS << "dumpBareDeclRef(SA->get" << getUpperName() << "());\n"; 
   } else if (type == "IdentifierInfo *") {
Index: lib/Serialization/ASTCommon.cpp
===
--- lib/Serialization/ASTCommon.cpp
+++ lib/Serialization/ASTCommon.cpp
@@ -269,6 +269,7 @@
   case Decl::ObjCProtocol:
   case Decl::ObjCInterface:
   case Decl::Empty:
+  case Decl::DeclSpecUuid:
 return true;
 
   // Never redeclarable.
Index: lib/Sema/SemaDeclAttr.cpp
===
--- lib/Sema/SemaDeclAttr.cpp
+++ lib/Sema/SemaDeclAttr.cpp
@@ -4932,8 +4932,13 @@
 UuidAttr *Sema::mergeUuidAttr(Decl *D, SourceRange Range,
   unsigned AttrSpellingListIndex,
   DeclSpecUuidDecl *Uuid) {
-  if (D->getAttr())
-return nullptr;
+  if (const auto *UA = D->getAttr()) {
+if (UA->getDeclSpecUuidDecl()->getStrUuid().equals_lower(Uuid->getStrUuid()))
+  return nullptr;
+Diag(UA->getLocation(), diag::err_mismatched_uuid);
+Diag(Range.getBegin(), diag::note_previous_uuid);
+D->dropAttr();
+  }
 
   return ::new (Context) UuidAttr(Range, Context, Uuid, AttrSpellingListIndex);
 }
@@ -4945,7 +4950,7 @@
 return;
   }
 
-  StringRef  StrRef = AL.getUuidDecl()->getStrUuid();
+  StringRef  StrRef = AL.getUuidStr();
   SourceLocation LiteralLoc = AL.getLoc();
   if (StrRef.empty())
 return;
@@ -4982,12 +4987,28 @@
   if (AL.isMicrosoftAttribute()) // Check for [uuid(...)] spelling.
 S.Diag(AL.getLoc(), diag::warn_atl_uuid_deprecated);
 
+  DeclSpecUuidDecl *ArgDecl, *PreviousArgDecl;
+  ArgDecl = DeclSpecUuidDecl::Create(S.getASTContext(),
+ S.getFunctionLevelDeclContext(),
+ SourceLocation(),
+ StrRef);
+
+  // Do a lookup of the declspec.
+  auto DSU = S.UuidDeclSpecMap.find(StrRef);
+  if (DSU != S.UuidDeclSpecMap.end()) {
+PreviousArgDecl  = DSU->second;
+PreviousArgDecl->setNext(ArgDecl);
+ArgDecl->setPrevious(PreviousArgDecl);
+  }
+  S.UuidDeclSpecMap[StrRef] = ArgDecl;
+
   UuidAttr *UA = S.mergeUuidAttr(D, AL.getRange(),
  AL.getAttributeSpellingListIndex(),
- AL.getUuidDecl());
+ ArgDecl);
 
   if (UA)
 D->addAttr(UA);
+
 }
 
 static void handleMSInheritanceAttr(Sema &S, Decl *D, const AttributeList &AL) {
Index: lib/Parse/ParseDecl.cpp
===
--- lib/Parse/ParseDecl.cpp
+++ lib/Parse/ParseDecl.cpp
@@ -560,26 +560,20 @@
 // Parse the uuid attribute and create a UuidDecl.
 ConsumeParen();
 assert(Tok.is(tok::string_literal) && "uuid not followed by string literal '('");
-int sz = Tok.getLength();
 SmallString<8> UuidBuffer;
 bool Invalid = false;
 StringRef UuidStr = PP.getSpelling(Tok, UuidBuffer, &Invalid);
 
 // Clean up the string from the "\" at begining and at end.
 StringRef UuidStr1 = UuidStr.ltrim('\"');
 StringRef TrimmedUuidStr = UuidStr1.rtrim('\"');
-DeclSpecUuidDecl *ArgDecl =
-  DeclSpecUuidDecl::Create(Actions.getASTContext(),
-   Actions.getFunctionLevelDeclContext(),
-   SourceLocation(),
-   TrimmedUuidStr);
 
 // Advance to next token. Should be a r-paren.
 PP.Lex(Tok);
 SourceLocation RParen = Tok.getLocation();
 SourceRange attrRange = SourceRange(AttrNameLoc, RParen);
 if (!ExpectAndConsume(tok::r_paren))
-  Attrs.addNew(AttrName, attrRange, nullptr, AttrNameLoc, ArgDecl, AttributeList::AS_Declspec);
+  Attrs.addNew(AttrName, attrRange, nullptr, AttrNameLoc, TrimmedUuidStr, AttributeList::AS_Declspec);
 return true;
   }
   unsigned NumArgs =
@@ -936,7 +930,6 @@
   enum { Introduced, Deprecated, Obsoleted, Unknown };
   AvailabilityChange Changes[Unknown];
   ExprResult MessageExpr, ReplacementExpr;
-  Decl *DeclSpecUuidDecl = nullptr;
 
   // Opening '('.
   BalancedDelimiterTracker T(*this, tok::l_paren);
Index: lib/CodeGen/CodeGenModule.cpp
=

[PATCH] D43576: Solution to fix PR27066 - Redefinition with same mangled name as another definition (dllexport and uuid)

2018-04-20 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added a comment.

Richard,
Please let me know if I have answered to all the issues you raised. Thanks.


https://reviews.llvm.org/D43576



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D84780: Setting the /bigobj option globally for Windows debug build. https://bugs.llvm.org/show_bug.cgi?id=46733

2020-07-28 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam created this revision.
Herald added subscribers: llvm-commits, lldb-commits, cfe-commits, 
AlexeySotkin, msifontes, jurahul, Kayjukh, grosul1, bader, Joonsoo, liufengdb, 
aartbik, lucyrfox, mgester, arpith-jacob, antiagainst, shauheen, jpienaar, 
rriddle, mehdi_amini, hiraditya, mgorny.
Herald added a reviewer: mravishankar.
Herald added a reviewer: antiagainst.
Herald added projects: clang, LLDB, MLIR, LLVM.
zahiraam requested review of this revision.
Herald added a reviewer: jdoerfert.
Herald added subscribers: sstefan1, stephenneuendorffer, nicolasvasilache, 
ormris.

Change-Id: Ie69e3b62ac4e7bd266ed48a76f4cbe9ec8a899d1


Repository:
  rG LLVM Github Monorepo

https://reviews.llvm.org/D84780

Files:
  clang/lib/ASTMatchers/Dynamic/CMakeLists.txt
  clang/lib/CodeGen/CMakeLists.txt
  clang/lib/Sema/CMakeLists.txt
  clang/unittests/AST/CMakeLists.txt
  clang/unittests/ASTMatchers/CMakeLists.txt
  clang/unittests/Tooling/CMakeLists.txt
  lldb/source/API/CMakeLists.txt
  llvm/cmake/modules/HandleLLVMOptions.cmake
  llvm/lib/Passes/CMakeLists.txt
  mlir/lib/Dialect/SPIRV/CMakeLists.txt

Index: mlir/lib/Dialect/SPIRV/CMakeLists.txt
===
--- mlir/lib/Dialect/SPIRV/CMakeLists.txt
+++ mlir/lib/Dialect/SPIRV/CMakeLists.txt
@@ -1,6 +1,3 @@
-if (MSVC)
-  set_source_files_properties(SPIRVDialect.cpp PROPERTIES COMPILE_FLAGS /bigobj)
-endif()
 
 set(LLVM_TARGET_DEFINITIONS SPIRVCanonicalization.td)
 mlir_tablegen(SPIRVCanonicalization.inc -gen-rewriters)
Index: llvm/lib/Passes/CMakeLists.txt
===
--- llvm/lib/Passes/CMakeLists.txt
+++ llvm/lib/Passes/CMakeLists.txt
@@ -1,7 +1,3 @@
-if (MSVC)
-  set_source_files_properties(PassBuilder.cpp PROPERTIES COMPILE_FLAGS /bigobj)
-endif()
-
 add_llvm_component_library(LLVMPasses
   PassBuilder.cpp
   PassPlugin.cpp
Index: llvm/cmake/modules/HandleLLVMOptions.cmake
===
--- llvm/cmake/modules/HandleLLVMOptions.cmake
+++ llvm/cmake/modules/HandleLLVMOptions.cmake
@@ -468,6 +468,10 @@
   endif()
 endif()
   endif()
+  # By default MSVC has a 2^16 limit on the number of sections in an object file,
+  # but in many objects files need more than that. This flag is to increase the
+  # number of sections.
+  append("/bigobj" CMAKE_CXX_FLAGS)
 endif( MSVC )
 
 # Warnings-as-errors handling for GCC-compatible compilers:
Index: lldb/source/API/CMakeLists.txt
===
--- lldb/source/API/CMakeLists.txt
+++ lldb/source/API/CMakeLists.txt
@@ -126,9 +126,6 @@
   set_property(TARGET liblldb APPEND PROPERTY BUILD_RPATH   "${PYTHON_RPATH}")
 endif()
 
-if (MSVC)
-  set_source_files_properties(SBReproducer.cpp PROPERTIES COMPILE_FLAGS /bigobj)
-endif()
 
 if(lldb_python_wrapper)
   add_dependencies(liblldb swig_wrapper)
Index: clang/unittests/Tooling/CMakeLists.txt
===
--- clang/unittests/Tooling/CMakeLists.txt
+++ clang/unittests/Tooling/CMakeLists.txt
@@ -4,14 +4,6 @@
   Support
   )
 
-# By default MSVC has a 2^16 limit on the number of sections in an object file,
-# and this needs more than that.
-if (MSVC)
-  set_source_files_properties(RecursiveASTVisitorTest.cpp PROPERTIES COMPILE_FLAGS /bigobj)
-  set_source_files_properties(RecursiveASTVisitorTestExprVisitor.cpp PROPERTIES COMPILE_FLAGS /bigobj)
-  set_source_files_properties(RecursiveASTVisitorTests/Callbacks.cpp PROPERTIES COMPILE_FLAGS /bigobj)
-  set_source_files_properties(SourceCodeTest.cpp PROPERTIES COMPILE_FLAGS /bigobj)
-endif()
 
 add_clang_unittest(ToolingTests
   ASTSelectionTest.cpp
Index: clang/unittests/ASTMatchers/CMakeLists.txt
===
--- clang/unittests/ASTMatchers/CMakeLists.txt
+++ clang/unittests/ASTMatchers/CMakeLists.txt
@@ -3,15 +3,6 @@
   Support
   )
 
-# By default MSVC has a 2^16 limit on the number of sections in an object file,
-# and this needs more than that.
-if (MSVC)
-  set_source_files_properties(InternalASTMatchersTest.cpp PROPERTIES COMPILE_FLAGS /bigobj)
-  set_source_files_properties(NodeMatchersTest.cpp PROPERTIES COMPILE_FLAGS /bigobj)
-  set_source_files_properties(NarrowingMatchersTest.cpp PROPERTIES COMPILE_FLAGS /bigobj)
-  set_source_files_properties(ASTTraversalMatchersTest.cpp PROPERTIES COMPILE_FLAGS /bigobj)
-endif()
-
 add_clang_unittest(ASTMatchersTests
   ASTMatchersInternalTest.cpp
   ASTMatchersNodeTest.cpp
Index: clang/unittests/AST/CMakeLists.txt
===
--- clang/unittests/AST/CMakeLists.txt
+++ clang/unittests/AST/CMakeLists.txt
@@ -3,9 +3,6 @@
   Support
   )
 
-if (MSVC)
-  set_source_files_properties(ASTImporterTest.cpp PROPERTIES COMPILE_FLAGS /bigobj)
-endif()
 
 add_clang_unittest(ASTTests
   ASTContextParentMapTest.cpp
Index: cl

[PATCH] D40621: MS ABI: Treat explicit instantiation definitions of dllimport function templates as explicit instantiation decls (PR35435)

2017-11-30 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added a comment.

Looks good to me 2.


Repository:
  rL LLVM

https://reviews.llvm.org/D40621



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D123630: [WIP] Remove connection between 'ffast-math' and 'ffp-contract'.

2022-08-29 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 456337.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D123630/new/

https://reviews.llvm.org/D123630

Files:
  clang/docs/UsersManual.rst
  clang/lib/Driver/ToolChains/Clang.cpp
  clang/test/CodeGen/ffp-contract-option.c
  clang/test/Driver/fp-contract.c

Index: clang/test/Driver/fp-contract.c
===
--- /dev/null
+++ clang/test/Driver/fp-contract.c
@@ -0,0 +1,114 @@
+// Test that -ffp-contract is set to the right value when combined with
+// the options -ffast-math and -fno-fast-math.
+
+// RUN: %clang -### -ffast-math -c %s 2>&1  \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+// CHECK-FPC-FAST: "-ffp-contract=fast"
+
+// RUN: %clang -### -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=on -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+// CHECK-FPC-ON:   "-ffp-contract=on"
+
+// RUN: %clang -### -ffast-math -ffp-contract=off -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+// CHECK-FPC-OFF:  "-ffp-contract=off"
+
+// RUN: %clang -### -ffast-math -ffp-contract=fast -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=fast -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+// RUN: %clang -### -ffp-contract=on -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+// RUN: %clang -### -ffp-contract=off -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=fast -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+// RUN: %clang -### -ffp-contract=on -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+// RUN: %clang -### -ffp-contract=off -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+
+// RUN: %clang -### -ffast-math -ffp-contract=fast -ffp-contract=on -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=on -ffp-contract=off -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=on -ffp-contract=fast -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=off -ffp-contract=on -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=off -ffp-contract=fast \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=on -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=off -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=fast -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffast-math -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -fno-fast-math -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -fno-fast-math -ffp-contract=on -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -fno-fast-math -ffp-contract=off -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clang -### -fno-fast-math -ffp-contract=fast -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=fast -fno-fast-math -ffp-contract=on \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffp-contract=fast -fno-fast-math -ffp-contract=off \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clang -### -ffp-contract=off -fno-fast-math -ffp-contract=fast \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=off -fno-fast-math -ffp-contract=on \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffp-contract=on -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=off -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=fast -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=on -ffast-math -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffp-contract=off -ffast-math -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clang -### -ffp-contract=fast -ffast-math -fno-

[PATCH] D123630: Remove connection between 'ffast-math' and 'ffp-contract'.

2022-09-01 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 457358.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D123630/new/

https://reviews.llvm.org/D123630

Files:
  clang/docs/UsersManual.rst
  clang/lib/Driver/ToolChains/Clang.cpp
  clang/test/CodeGen/ffp-contract-option.c
  clang/test/Driver/fp-contract.c

Index: clang/test/Driver/fp-contract.c
===
--- /dev/null
+++ clang/test/Driver/fp-contract.c
@@ -0,0 +1,114 @@
+// Test that -ffp-contract is set to the right value when combined with
+// the options -ffast-math and -fno-fast-math.
+
+// RUN: %clang -### -ffast-math -c %s 2>&1  \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+// CHECK-FPC-FAST: "-ffp-contract=fast"
+
+// RUN: %clang -### -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=on -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+// CHECK-FPC-ON:   "-ffp-contract=on"
+
+// RUN: %clang -### -ffast-math -ffp-contract=off -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+// CHECK-FPC-OFF:  "-ffp-contract=off"
+
+// RUN: %clang -### -ffast-math -ffp-contract=fast -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=fast -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+// RUN: %clang -### -ffp-contract=on -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+// RUN: %clang -### -ffp-contract=off -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=fast -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+// RUN: %clang -### -ffp-contract=on -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+// RUN: %clang -### -ffp-contract=off -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+
+// RUN: %clang -### -ffast-math -ffp-contract=fast -ffp-contract=on -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=on -ffp-contract=off -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=on -ffp-contract=fast -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=off -ffp-contract=on -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=off -ffp-contract=fast \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=on -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=off -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=fast -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffast-math -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -fno-fast-math -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -fno-fast-math -ffp-contract=on -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -fno-fast-math -ffp-contract=off -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clang -### -fno-fast-math -ffp-contract=fast -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=fast -fno-fast-math -ffp-contract=on \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffp-contract=fast -fno-fast-math -ffp-contract=off \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clang -### -ffp-contract=off -fno-fast-math -ffp-contract=fast \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=off -fno-fast-math -ffp-contract=on \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffp-contract=on -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=off -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=fast -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=on -ffast-math -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffp-contract=off -ffast-math -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clang -### -ffp-contract=fast -ffast-math -fno-

[PATCH] D123630: Remove connection between 'ffast-math' and 'ffp-contract'.

2022-09-07 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added a comment.

@fhahn @aaron.ballman would you mind taking time for a review for this patch? 
Thanks.


CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D123630/new/

https://reviews.llvm.org/D123630

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D123630: Remove connection between 'ffast-math' and 'ffp-contract'.

2022-09-07 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 458506.
zahiraam marked 4 inline comments as done.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D123630/new/

https://reviews.llvm.org/D123630

Files:
  clang/docs/UsersManual.rst
  clang/lib/Driver/ToolChains/Clang.cpp
  clang/test/CodeGen/ffp-contract-option.c
  clang/test/Driver/fp-contract.c

Index: clang/test/Driver/fp-contract.c
===
--- /dev/null
+++ clang/test/Driver/fp-contract.c
@@ -0,0 +1,114 @@
+// Test that -ffp-contract is set to the right value when combined with
+// the options -ffast-math and -fno-fast-math.
+
+// RUN: %clang -### -ffast-math -c %s 2>&1  \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+// CHECK-FPC-FAST: "-ffp-contract=fast"
+
+// RUN: %clang -### -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=on -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+// CHECK-FPC-ON:   "-ffp-contract=on"
+
+// RUN: %clang -### -ffast-math -ffp-contract=off -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+// CHECK-FPC-OFF:  "-ffp-contract=off"
+
+// RUN: %clang -### -ffast-math -ffp-contract=fast -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=fast -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+// RUN: %clang -### -ffp-contract=on -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+// RUN: %clang -### -ffp-contract=off -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=fast -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+// RUN: %clang -### -ffp-contract=on -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+// RUN: %clang -### -ffp-contract=off -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+
+// RUN: %clang -### -ffast-math -ffp-contract=fast -ffp-contract=on -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=on -ffp-contract=off -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=on -ffp-contract=fast -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=off -ffp-contract=on -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=off -ffp-contract=fast \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=on -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=off -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=fast -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffast-math -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -fno-fast-math -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -fno-fast-math -ffp-contract=on -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -fno-fast-math -ffp-contract=off -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clang -### -fno-fast-math -ffp-contract=fast -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=fast -fno-fast-math -ffp-contract=on \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffp-contract=fast -fno-fast-math -ffp-contract=off \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clang -### -ffp-contract=off -fno-fast-math -ffp-contract=fast \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=off -fno-fast-math -ffp-contract=on \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffp-contract=on -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=off -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=fast -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=on -ffast-math -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffp-contract=off -ffast-math -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clan

[PATCH] D123630: Remove connection between 'ffast-math' and 'ffp-contract'.

2022-09-07 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added a comment.

Thanks @aaron.ballman!


CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D123630/new/

https://reviews.llvm.org/D123630

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D123630: Remove connection between 'ffast-math' and 'ffp-contract'.

2022-09-09 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 459028.
zahiraam marked an inline comment as done.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D123630/new/

https://reviews.llvm.org/D123630

Files:
  clang/docs/UsersManual.rst
  clang/lib/Driver/ToolChains/Clang.cpp
  clang/test/CodeGen/ffp-contract-option.c
  clang/test/Driver/fp-contract.c

Index: clang/test/Driver/fp-contract.c
===
--- /dev/null
+++ clang/test/Driver/fp-contract.c
@@ -0,0 +1,114 @@
+// Test that -ffp-contract is set to the right value when combined with
+// the options -ffast-math and -fno-fast-math.
+
+// RUN: %clang -### -ffast-math -c %s 2>&1  \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+// CHECK-FPC-FAST: "-ffp-contract=fast"
+
+// RUN: %clang -### -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=on -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+// CHECK-FPC-ON:   "-ffp-contract=on"
+
+// RUN: %clang -### -ffast-math -ffp-contract=off -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+// CHECK-FPC-OFF:  "-ffp-contract=off"
+
+// RUN: %clang -### -ffast-math -ffp-contract=fast -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=fast -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+// RUN: %clang -### -ffp-contract=on -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+// RUN: %clang -### -ffp-contract=off -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=fast -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+// RUN: %clang -### -ffp-contract=on -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+// RUN: %clang -### -ffp-contract=off -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+
+// RUN: %clang -### -ffast-math -ffp-contract=fast -ffp-contract=on -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=on -ffp-contract=off -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=on -ffp-contract=fast -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=off -ffp-contract=on -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=off -ffp-contract=fast \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=on -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=off -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=fast -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffast-math -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -fno-fast-math -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -fno-fast-math -ffp-contract=on -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -fno-fast-math -ffp-contract=off -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clang -### -fno-fast-math -ffp-contract=fast -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=fast -fno-fast-math -ffp-contract=on \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffp-contract=fast -fno-fast-math -ffp-contract=off \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clang -### -ffp-contract=off -fno-fast-math -ffp-contract=fast \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=off -fno-fast-math -ffp-contract=on \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffp-contract=on -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=off -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=fast -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=on -ffast-math -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffp-contract=off -ffast-math -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clan

[PATCH] D123630: Remove connection between 'ffast-math' and 'ffp-contract'.

2022-09-13 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 459893.
zahiraam marked 2 inline comments as done.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D123630/new/

https://reviews.llvm.org/D123630

Files:
  clang/docs/UsersManual.rst
  clang/lib/Driver/ToolChains/Clang.cpp
  clang/test/CodeGen/ffp-contract-option.c
  clang/test/Driver/fp-contract.c

Index: clang/test/Driver/fp-contract.c
===
--- /dev/null
+++ clang/test/Driver/fp-contract.c
@@ -0,0 +1,114 @@
+// Test that -ffp-contract is set to the right value when combined with
+// the options -ffast-math and -fno-fast-math.
+
+// RUN: %clang -### -ffast-math -c %s 2>&1  \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+// CHECK-FPC-FAST: "-ffp-contract=fast"
+
+// RUN: %clang -### -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=on -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+// CHECK-FPC-ON:   "-ffp-contract=on"
+
+// RUN: %clang -### -ffast-math -ffp-contract=off -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+// CHECK-FPC-OFF:  "-ffp-contract=off"
+
+// RUN: %clang -### -ffast-math -ffp-contract=fast -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=fast -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+// RUN: %clang -### -ffp-contract=on -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+// RUN: %clang -### -ffp-contract=off -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=fast -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+// RUN: %clang -### -ffp-contract=on -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+// RUN: %clang -### -ffp-contract=off -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+
+// RUN: %clang -### -ffast-math -ffp-contract=fast -ffp-contract=on -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=on -ffp-contract=off -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=on -ffp-contract=fast -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=off -ffp-contract=on -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=off -ffp-contract=fast \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=on -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=off -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=fast -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffast-math -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -fno-fast-math -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -fno-fast-math -ffp-contract=on -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -fno-fast-math -ffp-contract=off -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clang -### -fno-fast-math -ffp-contract=fast -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=fast -fno-fast-math -ffp-contract=on \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffp-contract=fast -fno-fast-math -ffp-contract=off \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clang -### -ffp-contract=off -fno-fast-math -ffp-contract=fast \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=off -fno-fast-math -ffp-contract=on \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffp-contract=on -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=off -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=fast -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=on -ffast-math -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffp-contract=off -ffast-math -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clan

[PATCH] D123630: Remove connection between 'ffast-math' and 'ffp-contract'.

2022-09-13 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added inline comments.



Comment at: clang/docs/UsersManual.rst:1453-1455
+   Note: ``DenormalFPMath`` and ``DenormalFP32Math`` are set by default to IEEE
+   (no flush) for ``-fno-fast-math``, ``-fno-unsafe-math-optimizations``, and
+   any setting of ``fp-model``. Clang does enable flush-to-zero when

jcranmer-intel wrote:
> You can replace this text with saying that `-fno-fast-math` implies 
> `-fdenormal-fp-math=ieee`. No need to directly mention `DenormalFPMath`; 
> instead relate it to the other command line flags that are documented.
Not sure that's the change you are proposing?


CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D123630/new/

https://reviews.llvm.org/D123630

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D123630: Remove connection between 'ffast-math' and 'ffp-contract'.

2022-09-14 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 460178.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D123630/new/

https://reviews.llvm.org/D123630

Files:
  clang/docs/UsersManual.rst
  clang/lib/Driver/ToolChains/Clang.cpp
  clang/test/CodeGen/ffp-contract-option.c
  clang/test/Driver/fp-contract.c

Index: clang/test/Driver/fp-contract.c
===
--- /dev/null
+++ clang/test/Driver/fp-contract.c
@@ -0,0 +1,114 @@
+// Test that -ffp-contract is set to the right value when combined with
+// the options -ffast-math and -fno-fast-math.
+
+// RUN: %clang -### -ffast-math -c %s 2>&1  \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+// CHECK-FPC-FAST: "-ffp-contract=fast"
+
+// RUN: %clang -### -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=on -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+// CHECK-FPC-ON:   "-ffp-contract=on"
+
+// RUN: %clang -### -ffast-math -ffp-contract=off -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+// CHECK-FPC-OFF:  "-ffp-contract=off"
+
+// RUN: %clang -### -ffast-math -ffp-contract=fast -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=fast -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+// RUN: %clang -### -ffp-contract=on -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+// RUN: %clang -### -ffp-contract=off -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=fast -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+// RUN: %clang -### -ffp-contract=on -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+// RUN: %clang -### -ffp-contract=off -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+
+// RUN: %clang -### -ffast-math -ffp-contract=fast -ffp-contract=on -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=on -ffp-contract=off -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=on -ffp-contract=fast -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=off -ffp-contract=on -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=off -ffp-contract=fast \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=on -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=off -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=fast -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffast-math -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -fno-fast-math -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -fno-fast-math -ffp-contract=on -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -fno-fast-math -ffp-contract=off -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clang -### -fno-fast-math -ffp-contract=fast -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=fast -fno-fast-math -ffp-contract=on \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffp-contract=fast -fno-fast-math -ffp-contract=off \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clang -### -ffp-contract=off -fno-fast-math -ffp-contract=fast \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=off -fno-fast-math -ffp-contract=on \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffp-contract=on -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=off -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=fast -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=on -ffast-math -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffp-contract=off -ffast-math -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clang -### -ffp-contract=fast -ffast-math -fno-

[PATCH] D123630: Remove connection between 'ffast-math' and 'ffp-contract'.

2022-09-15 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 460389.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D123630/new/

https://reviews.llvm.org/D123630

Files:
  clang/docs/UsersManual.rst
  clang/lib/Driver/ToolChains/Clang.cpp
  clang/test/CodeGen/ffp-contract-option.c
  clang/test/Driver/fp-contract.c

Index: clang/test/Driver/fp-contract.c
===
--- /dev/null
+++ clang/test/Driver/fp-contract.c
@@ -0,0 +1,114 @@
+// Test that -ffp-contract is set to the right value when combined with
+// the options -ffast-math and -fno-fast-math.
+
+// RUN: %clang -### -ffast-math -c %s 2>&1  \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+// CHECK-FPC-FAST: "-ffp-contract=fast"
+
+// RUN: %clang -### -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=on -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+// CHECK-FPC-ON:   "-ffp-contract=on"
+
+// RUN: %clang -### -ffast-math -ffp-contract=off -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+// CHECK-FPC-OFF:  "-ffp-contract=off"
+
+// RUN: %clang -### -ffast-math -ffp-contract=fast -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=fast -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+// RUN: %clang -### -ffp-contract=on -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+// RUN: %clang -### -ffp-contract=off -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=fast -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+// RUN: %clang -### -ffp-contract=on -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+// RUN: %clang -### -ffp-contract=off -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+
+// RUN: %clang -### -ffast-math -ffp-contract=fast -ffp-contract=on -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=on -ffp-contract=off -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=on -ffp-contract=fast -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=off -ffp-contract=on -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=off -ffp-contract=fast \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=on -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=off -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=fast -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffast-math -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -fno-fast-math -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -fno-fast-math -ffp-contract=on -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -fno-fast-math -ffp-contract=off -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clang -### -fno-fast-math -ffp-contract=fast -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=fast -fno-fast-math -ffp-contract=on \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffp-contract=fast -fno-fast-math -ffp-contract=off \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clang -### -ffp-contract=off -fno-fast-math -ffp-contract=fast \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=off -fno-fast-math -ffp-contract=on \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffp-contract=on -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=off -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=fast -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=on -ffast-math -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffp-contract=off -ffast-math -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clang -### -ffp-contract=fast -ffast-math -fno-

[PATCH] D123630: Remove connection between 'ffast-math' and 'ffp-contract'.

2022-09-15 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 460470.
zahiraam marked 3 inline comments as done.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D123630/new/

https://reviews.llvm.org/D123630

Files:
  clang/docs/UsersManual.rst
  clang/lib/Driver/ToolChains/Clang.cpp
  clang/test/CodeGen/ffp-contract-option.c
  clang/test/Driver/fp-contract.c

Index: clang/test/Driver/fp-contract.c
===
--- /dev/null
+++ clang/test/Driver/fp-contract.c
@@ -0,0 +1,114 @@
+// Test that -ffp-contract is set to the right value when combined with
+// the options -ffast-math and -fno-fast-math.
+
+// RUN: %clang -### -ffast-math -c %s 2>&1  \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+// CHECK-FPC-FAST: "-ffp-contract=fast"
+
+// RUN: %clang -### -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=on -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+// CHECK-FPC-ON:   "-ffp-contract=on"
+
+// RUN: %clang -### -ffast-math -ffp-contract=off -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+// CHECK-FPC-OFF:  "-ffp-contract=off"
+
+// RUN: %clang -### -ffast-math -ffp-contract=fast -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=fast -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+// RUN: %clang -### -ffp-contract=on -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+// RUN: %clang -### -ffp-contract=off -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=fast -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+// RUN: %clang -### -ffp-contract=on -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+// RUN: %clang -### -ffp-contract=off -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+
+// RUN: %clang -### -ffast-math -ffp-contract=fast -ffp-contract=on -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=on -ffp-contract=off -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=on -ffp-contract=fast -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=off -ffp-contract=on -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=off -ffp-contract=fast \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=on -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=off -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clang -### -ffast-math -ffp-contract=fast -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffast-math -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -fno-fast-math -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -fno-fast-math -ffp-contract=on -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -fno-fast-math -ffp-contract=off -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clang -### -fno-fast-math -ffp-contract=fast -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=fast -fno-fast-math -ffp-contract=on \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffp-contract=fast -fno-fast-math -ffp-contract=off \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clang -### -ffp-contract=off -fno-fast-math -ffp-contract=fast \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=off -fno-fast-math -ffp-contract=on \
+// RUN: -c %s 2>&1 | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffp-contract=on -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=off -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=fast -ffast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-FAST %s
+
+// RUN: %clang -### -ffp-contract=on -ffast-math -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-ON %s
+
+// RUN: %clang -### -ffp-contract=off -ffast-math -fno-fast-math -c %s 2>&1 \
+// RUN:   | FileCheck --check-prefix=CHECK-FPC-OFF %s
+
+// RUN: %clan

[PATCH] D149573: [Clang][C++23] Implement core language changes from P1467R9 extended floating-point types and standard names

2023-11-20 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added a comment.

Just starting to look at this. Don't we need a RN for this?


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D149573/new/

https://reviews.llvm.org/D149573

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D128571: [X86] Support `_Float16` on SSE2 and up

2022-06-27 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam accepted this revision.
zahiraam added a comment.

LGTM.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D128571/new/

https://reviews.llvm.org/D128571

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D113107: Support of expression granularity for _Float16.

2022-06-28 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam marked an inline comment as done.
zahiraam added a comment.

In D113107#3606106 , @rjmccall wrote:

> In D113107#3606094 , @zahiraam 
> wrote:
>
>> In D113107#3605797 , @rjmccall 
>> wrote:
>>
>>> I think on balance the right thing to do is probably to add an alternative 
>>> to `-fexcess-precision`, like `-fexcess-precision=none`.  We can default to 
>>> `-fexcess-precision=standard` and treat `-fexcess-precision=fast` as an 
>>> alias for `standard` for now.
>>
>> In 
>> https://gcc.gnu.org/onlinedocs/gcc-4.8.2/gcc/Optimize-Options.html#index-ffloat-store-900
>>  ,  it looks like when compiling C, the default is 
>> -fexcess-precision=standard which would align with this implementation and 
>> our default too. So I think we could use the same name for the option. 
>> -fexcess-precision=none corresponds to the current behavior.
>> -fexcess-precision=standard = -fexcess-precision=fast corresponds to this 
>> implementation.
>> Agreed?
>
> Since you're not landing this option right now anyway, do you mind broaching 
> this with the GCC folks, just to be good neighbors?  You can just say that 
> (1) Clang is looking for a way to request operation-by-operation lowering, 
> (2) it feels like `-fexcess-precision` is the right option to add that to, 
> (3) we don't want to tread on toes by adding an alternative to "their" option 
> without talking to them first, and (4) what do they think about "none"?

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=106117


CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D113107/new/

https://reviews.llvm.org/D113107

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D128814: [Clang][Preprocessor] Fix inconsistent `FLT_EVAL_METHOD` when compiling vs preprocessing

2022-06-29 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added a comment.

Took the time to test the change on a few "crooked" tests I had used for the 
original patch. It works! LGTM.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D128814/new/

https://reviews.llvm.org/D128814

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D113107: Support of expression granularity for _Float16.

2022-06-29 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added a comment.

In D113107#3615372 , @zahiraam wrote:

> In D113107#3606106 , @rjmccall 
> wrote:
>
>> In D113107#3606094 , @zahiraam 
>> wrote:
>>
>>> In D113107#3605797 , @rjmccall 
>>> wrote:
>>>
 I think on balance the right thing to do is probably to add an alternative 
 to `-fexcess-precision`, like `-fexcess-precision=none`.  We can default 
 to `-fexcess-precision=standard` and treat `-fexcess-precision=fast` as an 
 alias for `standard` for now.
>>>
>>> In 
>>> https://gcc.gnu.org/onlinedocs/gcc-4.8.2/gcc/Optimize-Options.html#index-ffloat-store-900
>>>  ,  it looks like when compiling C, the default is 
>>> -fexcess-precision=standard which would align with this implementation and 
>>> our default too. So I think we could use the same name for the option. 
>>> -fexcess-precision=none corresponds to the current behavior.
>>> -fexcess-precision=standard = -fexcess-precision=fast corresponds to this 
>>> implementation.
>>> Agreed?
>>
>> Since you're not landing this option right now anyway, do you mind broaching 
>> this with the GCC folks, just to be good neighbors?  You can just say that 
>> (1) Clang is looking for a way to request operation-by-operation lowering, 
>> (2) it feels like `-fexcess-precision` is the right option to add that to, 
>> (3) we don't want to tread on toes by adding an alternative to "their" 
>> option without talking to them first, and (4) what do they think about 
>> "none"?
>
> https://gcc.gnu.org/bugzilla/show_bug.cgi?id=106117

In GCC using no -fexcess-precision is the same than using 
-fexcess-precision=standard. The patch we are proposing here is implementing 
this part.  So for  a + b + c, we are generating (_Float16) [((float a) + 
(float b)) + (float c)]
In GCC using -fexcess-precision=16 is generating yet another flavor of the 
operation-by-operation emulation. For the same addition than above, gcc is 
generating (_Float16) [(float) (_Float16) ((float a) + (float b)) + (float c)]. 
That's different than our current implementation.
See https://godbolt.org/z/aM8fzTsj1
Am I understanding correctly? @pengfei you are interested in the 
-fexcess-precision=16 part of this right? @rjmccall what do yo think?


CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D113107/new/

https://reviews.llvm.org/D113107

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D113107: Support of expression granularity for _Float16.

2022-06-29 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 441167.
zahiraam marked 2 inline comments as done.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D113107/new/

https://reviews.llvm.org/D113107

Files:
  clang/docs/LanguageExtensions.rst
  clang/docs/ReleaseNotes.rst
  clang/include/clang/Basic/TargetInfo.h
  clang/lib/Basic/Targets/X86.cpp
  clang/lib/Basic/Targets/X86.h
  clang/lib/CodeGen/CGExprComplex.cpp
  clang/lib/CodeGen/CGExprScalar.cpp
  clang/lib/CodeGen/CodeGenFunction.h
  clang/test/CodeGen/X86/Float16-arithmetic.c
  clang/test/CodeGen/X86/Float16-complex.c
  clang/test/Sema/Float16.c
  clang/test/SemaCXX/Float16.cpp

Index: clang/test/SemaCXX/Float16.cpp
===
--- clang/test/SemaCXX/Float16.cpp
+++ clang/test/SemaCXX/Float16.cpp
@@ -1,20 +1,10 @@
-// RUN: %clang_cc1 -fsyntax-only -verify -triple i686-linux-pc %s
-// RUN: %clang_cc1 -fsyntax-only -verify -triple i686-linux-pc -target-feature +sse2 %s -DHAVE
-// RUN: %clang_cc1 -fsyntax-only -verify -triple x86_64-linux-pc %s -DHAVE
-// RUN: %clang_cc1 -fsyntax-only -verify -triple spir-unknown-unknown %s -DHAVE
-// RUN: %clang_cc1 -fsyntax-only -verify -triple armv7a-linux-gnu %s -DHAVE
-// RUN: %clang_cc1 -fsyntax-only -verify -triple aarch64-linux-gnu %s -DHAVE
+// RUN: %clang_cc1 -fsyntax-only -verify -triple x86_64-linux-pc %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple spir-unknown-unknown %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple armv7a-linux-gnu %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple aarch64-linux-gnu %s
 
-#ifdef HAVE
 // expected-no-diagnostics
-#endif // HAVE
 
-#ifndef HAVE
-// expected-error@+2{{_Float16 is not supported on this target}}
-#endif // !HAVE
 _Float16 f;
 
-#ifndef HAVE
-// expected-error@+2{{invalid suffix 'F16' on floating constant}}
-#endif // !HAVE
 const auto g = 1.1F16;
Index: clang/test/Sema/Float16.c
===
--- clang/test/Sema/Float16.c
+++ clang/test/Sema/Float16.c
@@ -1,19 +1,23 @@
+<<< HEAD
 // RUN: %clang_cc1 -fsyntax-only -verify -triple i686-linux-pc %s
 // RUN: %clang_cc1 -fsyntax-only -verify -triple i686-linux-pc -target-feature +sse2 %s -DHAVE
 // RUN: %clang_cc1 -fsyntax-only -verify -triple x86_64-linux-pc %s -DHAVE
 // RUN: %clang_cc1 -fsyntax-only -verify -triple spir-unknown-unknown %s -DHAVE
 // RUN: %clang_cc1 -fsyntax-only -verify -triple armv7a-linux-gnu %s -DHAVE
 // RUN: %clang_cc1 -fsyntax-only -verify -triple aarch64-linux-gnu %s -DHAVE
+===
+// RUN: %clang_cc1 -fsyntax-only -verify -triple x86_64-linux-pc %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple x86_64-linux-pc -target-feature +avx512fp16 %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple spir-unknown-unknown %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple armv7a-linux-gnu %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple aarch64-linux-gnu %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple x86_64-linux-pc -target-feature +avx512fp16 %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple spir-unknown-unknown %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple armv7a-linux-gnu %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple aarch64-linux-gnu %s
 
-#ifndef HAVE
-// expected-error@+2{{_Float16 is not supported on this target}}
-#endif // HAVE
-_Float16 f;
-
-#ifdef HAVE
 _Complex _Float16 a;
 void builtin_complex(void) {
   _Float16 a = 0;
   (void)__builtin_complex(a, a); // expected-error {{'_Complex _Float16' is invalid}}
 }
-#endif
Index: clang/test/CodeGen/X86/Float16-complex.c
===
--- clang/test/CodeGen/X86/Float16-complex.c
+++ clang/test/CodeGen/X86/Float16-complex.c
@@ -1,134 +1,407 @@
-// RUN: %clang_cc1 %s -O0 -emit-llvm -triple x86_64-unknown-unknown -target-feature +avx512fp16 -o - | FileCheck %s --check-prefix=X86
-// RUN: %clang_cc1 %s -O0 -emit-llvm -triple x86_64-unknown-unknown -o - | FileCheck %s --check-prefix=X86
+// RUN: %clang_cc1 %s -O0 -emit-llvm -triple x86_64-unknown-unknown -target-feature +avx512fp16 -o - | FileCheck %s --check-prefixes=CHECK,AVX
+// RUN: %clang_cc1 %s -O0 -emit-llvm -triple x86_64-unknown-unknown -o - | FileCheck %s --check-prefixes=CHECK,X86
 
 _Float16 _Complex add_half_rr(_Float16 a, _Float16 b) {
-  // X86-LABEL: @add_half_rr(
-  // X86: fadd
-  // X86-NOT: fadd
-  // X86: ret
+  // CHECK-LABEL: @add_half_rr(
+  // CHECK: [[A:%.*]] = alloca half
+  // CHECK-NEXT: [[B:%.*]] = alloca half
+  // CHECK: [[A_LOAD:%.*]] = load half, ptr [[A]]
+
+  // AVX-NEXT: [[B_LOAD:%.*]] = load half, ptr [[B]]
+  // AVX-NEXT: [[AB_ADD:%.*]] = fadd half [[A_LOAD]], [[B_LOAD]]
+  // AVX: store half [[AB_ADD]], {{.*}}
+
+  // X86-NEXT: [[A_EXT:%.*]] = fpext half [[A_LOAD]] to float
+  // X86-NEXT: [[B_LOAD:%.*]] = load half, ptr [[B]]
+  // X86-NEXT: [[B_EXT:%.*]] = fpext half [[B_LOAD]] to float
+  // X86-NEXT: [[AB_ADD:%.*]] = fadd float [[A_EXT]], [[B_EXT]]
+  // 

[PATCH] D113107: Support of expression granularity for _Float16.

2022-06-29 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added a comment.

Fixed LIT tests. Fixed EmitPromoted for the Complex emitter (not 100% sure 
about it?). Added compound operator scalar emulation.


CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D113107/new/

https://reviews.llvm.org/D113107

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D113107: Support of expression granularity for _Float16.

2022-06-29 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 441169.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D113107/new/

https://reviews.llvm.org/D113107

Files:
  clang/docs/LanguageExtensions.rst
  clang/docs/ReleaseNotes.rst
  clang/include/clang/Basic/TargetInfo.h
  clang/lib/Basic/Targets/X86.cpp
  clang/lib/Basic/Targets/X86.h
  clang/lib/CodeGen/CGExprComplex.cpp
  clang/lib/CodeGen/CGExprScalar.cpp
  clang/lib/CodeGen/CodeGenFunction.h
  clang/test/CodeGen/X86/Float16-arithmetic.c
  clang/test/CodeGen/X86/Float16-complex.c
  clang/test/Sema/Float16.c
  clang/test/SemaCXX/Float16.cpp

Index: clang/test/SemaCXX/Float16.cpp
===
--- clang/test/SemaCXX/Float16.cpp
+++ clang/test/SemaCXX/Float16.cpp
@@ -1,20 +1,10 @@
-// RUN: %clang_cc1 -fsyntax-only -verify -triple i686-linux-pc %s
-// RUN: %clang_cc1 -fsyntax-only -verify -triple i686-linux-pc -target-feature +sse2 %s -DHAVE
-// RUN: %clang_cc1 -fsyntax-only -verify -triple x86_64-linux-pc %s -DHAVE
-// RUN: %clang_cc1 -fsyntax-only -verify -triple spir-unknown-unknown %s -DHAVE
-// RUN: %clang_cc1 -fsyntax-only -verify -triple armv7a-linux-gnu %s -DHAVE
-// RUN: %clang_cc1 -fsyntax-only -verify -triple aarch64-linux-gnu %s -DHAVE
+// RUN: %clang_cc1 -fsyntax-only -verify -triple x86_64-linux-pc %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple spir-unknown-unknown %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple armv7a-linux-gnu %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple aarch64-linux-gnu %s
 
-#ifdef HAVE
 // expected-no-diagnostics
-#endif // HAVE
 
-#ifndef HAVE
-// expected-error@+2{{_Float16 is not supported on this target}}
-#endif // !HAVE
 _Float16 f;
 
-#ifndef HAVE
-// expected-error@+2{{invalid suffix 'F16' on floating constant}}
-#endif // !HAVE
 const auto g = 1.1F16;
Index: clang/test/Sema/Float16.c
===
--- clang/test/Sema/Float16.c
+++ clang/test/Sema/Float16.c
@@ -1,19 +1,15 @@
-// RUN: %clang_cc1 -fsyntax-only -verify -triple i686-linux-pc %s
-// RUN: %clang_cc1 -fsyntax-only -verify -triple i686-linux-pc -target-feature +sse2 %s -DHAVE
-// RUN: %clang_cc1 -fsyntax-only -verify -triple x86_64-linux-pc %s -DHAVE
-// RUN: %clang_cc1 -fsyntax-only -verify -triple spir-unknown-unknown %s -DHAVE
-// RUN: %clang_cc1 -fsyntax-only -verify -triple armv7a-linux-gnu %s -DHAVE
-// RUN: %clang_cc1 -fsyntax-only -verify -triple aarch64-linux-gnu %s -DHAVE
+// RUN: %clang_cc1 -fsyntax-only -verify -triple x86_64-linux-pc %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple x86_64-linux-pc -target-feature +avx512fp16 %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple spir-unknown-unknown %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple armv7a-linux-gnu %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple aarch64-linux-gnu %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple x86_64-linux-pc -target-feature +avx512fp16 %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple spir-unknown-unknown %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple armv7a-linux-gnu %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple aarch64-linux-gnu %s
 
-#ifndef HAVE
-// expected-error@+2{{_Float16 is not supported on this target}}
-#endif // HAVE
-_Float16 f;
-
-#ifdef HAVE
 _Complex _Float16 a;
 void builtin_complex(void) {
   _Float16 a = 0;
   (void)__builtin_complex(a, a); // expected-error {{'_Complex _Float16' is invalid}}
 }
-#endif
Index: clang/test/CodeGen/X86/Float16-complex.c
===
--- clang/test/CodeGen/X86/Float16-complex.c
+++ clang/test/CodeGen/X86/Float16-complex.c
@@ -1,134 +1,407 @@
-// RUN: %clang_cc1 %s -O0 -emit-llvm -triple x86_64-unknown-unknown -target-feature +avx512fp16 -o - | FileCheck %s --check-prefix=X86
-// RUN: %clang_cc1 %s -O0 -emit-llvm -triple x86_64-unknown-unknown -o - | FileCheck %s --check-prefix=X86
+// RUN: %clang_cc1 %s -O0 -emit-llvm -triple x86_64-unknown-unknown -target-feature +avx512fp16 -o - | FileCheck %s --check-prefixes=CHECK,AVX
+// RUN: %clang_cc1 %s -O0 -emit-llvm -triple x86_64-unknown-unknown -o - | FileCheck %s --check-prefixes=CHECK,X86
 
 _Float16 _Complex add_half_rr(_Float16 a, _Float16 b) {
-  // X86-LABEL: @add_half_rr(
-  // X86: fadd
-  // X86-NOT: fadd
-  // X86: ret
+  // CHECK-LABEL: @add_half_rr(
+  // CHECK: [[A:%.*]] = alloca half
+  // CHECK-NEXT: [[B:%.*]] = alloca half
+  // CHECK: [[A_LOAD:%.*]] = load half, ptr [[A]]
+
+  // AVX-NEXT: [[B_LOAD:%.*]] = load half, ptr [[B]]
+  // AVX-NEXT: [[AB_ADD:%.*]] = fadd half [[A_LOAD]], [[B_LOAD]]
+  // AVX: store half [[AB_ADD]], {{.*}}
+
+  // X86-NEXT: [[A_EXT:%.*]] = fpext half [[A_LOAD]] to float
+  // X86-NEXT: [[B_LOAD:%.*]] = load half, ptr [[B]]
+  // X86-NEXT: [[B_EXT:%.*]] = fpext half [[B_LOAD]] to float
+  // X86-NEXT: [[AB_ADD:%.*]] = fadd float [[A_EXT]], [[B_EXT]]
+  // X86-NEXT: [[AB_ADD_TRUNC:%.*]] = fptrunc float [[AB_ADD]] to half

[PATCH] D113107: Support of expression granularity for _Float16.

2022-07-01 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 441702.
zahiraam marked 7 inline comments as done.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D113107/new/

https://reviews.llvm.org/D113107

Files:
  clang/docs/LanguageExtensions.rst
  clang/docs/ReleaseNotes.rst
  clang/include/clang/Basic/TargetInfo.h
  clang/lib/Basic/Targets/X86.cpp
  clang/lib/Basic/Targets/X86.h
  clang/lib/CodeGen/CGExprComplex.cpp
  clang/lib/CodeGen/CGExprScalar.cpp
  clang/lib/CodeGen/CodeGenFunction.h
  clang/test/CodeGen/X86/Float16-arithmetic.c
  clang/test/CodeGen/X86/Float16-complex.c
  clang/test/Sema/Float16.c
  clang/test/SemaCXX/Float16.cpp

Index: clang/test/SemaCXX/Float16.cpp
===
--- clang/test/SemaCXX/Float16.cpp
+++ clang/test/SemaCXX/Float16.cpp
@@ -1,20 +1,10 @@
-// RUN: %clang_cc1 -fsyntax-only -verify -triple i686-linux-pc %s
-// RUN: %clang_cc1 -fsyntax-only -verify -triple i686-linux-pc -target-feature +sse2 %s -DHAVE
-// RUN: %clang_cc1 -fsyntax-only -verify -triple x86_64-linux-pc %s -DHAVE
-// RUN: %clang_cc1 -fsyntax-only -verify -triple spir-unknown-unknown %s -DHAVE
-// RUN: %clang_cc1 -fsyntax-only -verify -triple armv7a-linux-gnu %s -DHAVE
-// RUN: %clang_cc1 -fsyntax-only -verify -triple aarch64-linux-gnu %s -DHAVE
+// RUN: %clang_cc1 -fsyntax-only -verify -triple x86_64-linux-pc %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple spir-unknown-unknown %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple armv7a-linux-gnu %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple aarch64-linux-gnu %s
 
-#ifdef HAVE
 // expected-no-diagnostics
-#endif // HAVE
 
-#ifndef HAVE
-// expected-error@+2{{_Float16 is not supported on this target}}
-#endif // !HAVE
 _Float16 f;
 
-#ifndef HAVE
-// expected-error@+2{{invalid suffix 'F16' on floating constant}}
-#endif // !HAVE
 const auto g = 1.1F16;
Index: clang/test/Sema/Float16.c
===
--- clang/test/Sema/Float16.c
+++ clang/test/Sema/Float16.c
@@ -1,19 +1,15 @@
-// RUN: %clang_cc1 -fsyntax-only -verify -triple i686-linux-pc %s
-// RUN: %clang_cc1 -fsyntax-only -verify -triple i686-linux-pc -target-feature +sse2 %s -DHAVE
-// RUN: %clang_cc1 -fsyntax-only -verify -triple x86_64-linux-pc %s -DHAVE
-// RUN: %clang_cc1 -fsyntax-only -verify -triple spir-unknown-unknown %s -DHAVE
-// RUN: %clang_cc1 -fsyntax-only -verify -triple armv7a-linux-gnu %s -DHAVE
-// RUN: %clang_cc1 -fsyntax-only -verify -triple aarch64-linux-gnu %s -DHAVE
+// RUN: %clang_cc1 -fsyntax-only -verify -triple x86_64-linux-pc %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple x86_64-linux-pc -target-feature +avx512fp16 %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple spir-unknown-unknown %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple armv7a-linux-gnu %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple aarch64-linux-gnu %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple x86_64-linux-pc -target-feature +avx512fp16 %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple spir-unknown-unknown %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple armv7a-linux-gnu %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple aarch64-linux-gnu %s
 
-#ifndef HAVE
-// expected-error@+2{{_Float16 is not supported on this target}}
-#endif // HAVE
-_Float16 f;
-
-#ifdef HAVE
 _Complex _Float16 a;
 void builtin_complex(void) {
   _Float16 a = 0;
   (void)__builtin_complex(a, a); // expected-error {{'_Complex _Float16' is invalid}}
 }
-#endif
Index: clang/test/CodeGen/X86/Float16-complex.c
===
--- clang/test/CodeGen/X86/Float16-complex.c
+++ clang/test/CodeGen/X86/Float16-complex.c
@@ -1,134 +1,422 @@
-// RUN: %clang_cc1 %s -O0 -emit-llvm -triple x86_64-unknown-unknown -target-feature +avx512fp16 -o - | FileCheck %s --check-prefix=X86
-// RUN: %clang_cc1 %s -O0 -emit-llvm -triple x86_64-unknown-unknown -o - | FileCheck %s --check-prefix=X86
+// RUN: %clang_cc1 %s -O0 -emit-llvm -triple x86_64-unknown-unknown -target-feature +avx512fp16 -o - | FileCheck %s --check-prefixes=CHECK,AVX
+// RUN: %clang_cc1 %s -O0 -emit-llvm -triple x86_64-unknown-unknown -o - | FileCheck %s --check-prefixes=CHECK,X86
 
 _Float16 _Complex add_half_rr(_Float16 a, _Float16 b) {
-  // X86-LABEL: @add_half_rr(
-  // X86: fadd
-  // X86-NOT: fadd
-  // X86: ret
+  // CHECK-LABEL: @add_half_rr(
+  // CHECK: [[A:%.*]] = alloca half
+  // CHECK-NEXT: [[B:%.*]] = alloca half
+  // CHECK: [[A_LOAD:%.*]] = load half, ptr [[A]]
+
+  // AVX-NEXT: [[B_LOAD:%.*]] = load half, ptr [[B]]
+  // AVX-NEXT: [[AB_ADD:%.*]] = fadd half [[A_LOAD]], [[B_LOAD]]
+  // AVX: store half [[AB_ADD]], {{.*}}
+
+  // X86-NEXT: [[A_EXT:%.*]] = fpext half [[A_LOAD]] to float
+  // X86-NEXT: [[B_LOAD:%.*]] = load half, ptr [[B]]
+  // X86-NEXT: [[B_EXT:%.*]] = fpext half [[B_LOAD]] to float
+  // X86-NEXT: [[AB_ADD:%.*]] = fadd float [[A_EXT]], [[B_EXT]]
+  // X86-NEXT: [[AB_ADD_TRUN

[PATCH] D113107: Support of expression granularity for _Float16.

2022-07-01 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added a comment.

Refactored the code as requested and fixed the compound operator promotion for 
scalar.
The operators that are left to complete are compound operators for complex type 
and ternary operator for scalar and complex types.
Then we need to add the option -fexcess-precision. I am not sure for now where 
and what values the _FLT_EVAL_METHOD should have when excess  precision is 
enabled/disabled.


CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D113107/new/

https://reviews.llvm.org/D113107

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D122155: Add warning when eval-method is set in the presence of value unsafe floating-point calculations.

2022-03-23 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam marked 2 inline comments as done.
zahiraam added inline comments.



Comment at: clang/include/clang/Basic/DiagnosticFrontendKinds.td:50-53
+def warn_eval_method_setting_via_option_in_value_unsafe_context : Warning<
+"setting the eval method via '-ffp-eval-method' has not effect when 
numeric "
+"results of floating-point calculations aren't value-safe.">,
+InGroup;

aaron.ballman wrote:
> andrew.w.kaylor wrote:
> > zahiraam wrote:
> > > aaron.ballman wrote:
> > > > Unless you have a strong reason for this to be a warning, this seems 
> > > > like a situation we should diagnose as an error with a much clearer 
> > > > message.
> > > May  be @andrew.w.kaylor would weigh in on this?
> > I was going to say that for the command line option we could just issue a 
> > warning saying that the later option overrides the earlier, but it's a bit 
> > complicated to sort out what that would mean if the eval method follows a 
> > fast-math option and it might not always be what the user intended. So, I 
> > guess I'd agree that it should be an error.
> > 
> > For the case with pragmas, the model I'd follow is the mixing of #pragma 
> > float_control(except, on) with a fast-math mode or #pragma 
> > float_control(precise, off) with a non-ignore exception mode. In both those 
> > cases we issue an error.
> > For the case with pragmas, the model I'd follow is the mixing of #pragma 
> > float_control(except, on) with a fast-math mode or #pragma 
> > float_control(precise, off) with a non-ignore exception mode. In both those 
> > cases we issue an error.
> 
> Good catch, I think that's a good approach as well.
I think i  will have the issue with the order of appearance of the options on 
the command line. 
// RUN: -freciprocal-math -mreassociate   -ffp-eval-method=source 
and
// RUN: -mreassociate -ffp-eval-method=source 

will depend on which order I will test for 
LangOpts.ApproxFunc/AllowFPReasson/AllowRecip being used or not?

The run lines above might give the same diagnostic. Unless I do something 
really complicated to check the order of the options on the command line?


CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D122155/new/

https://reviews.llvm.org/D122155

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D122155: Add warning when eval-method is set in the presence of value unsafe floating-point calculations.

2022-03-25 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 418210.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D122155/new/

https://reviews.llvm.org/D122155

Files:
  clang/include/clang/Basic/DiagnosticFrontendKinds.td
  clang/include/clang/Basic/DiagnosticSemaKinds.td
  clang/lib/Frontend/CompilerInvocation.cpp
  clang/lib/Sema/SemaAttr.cpp
  clang/test/Sema/eval-method-with-unsafe-math.c

Index: clang/test/Sema/eval-method-with-unsafe-math.c
===
--- /dev/null
+++ clang/test/Sema/eval-method-with-unsafe-math.c
@@ -0,0 +1,82 @@
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu  \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=WARN-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu  -freciprocal-math \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=WARN-RECPR,WARN-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu  -mreassociate \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=WARN-REC,WARN-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu  -fapprox-func \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=WARN-FUNC,WARN-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -freciprocal-math -mreassociate -verify \
+// RUN: %s 2>&1 | FileCheck %s --check-prefixes=WARN-REC,WARN-RECPR,WARN-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -freciprocal-math -mreassociate -fapprox-func \
+// RUN: -verify %s 2>&1 \
+// RUN: | FileCheck %s --check-prefixes=WARN-FUNC,WARN-REC,WARN-RECPR,WARN-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -fapprox-func -ffp-eval-method=source \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-FUNC
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -mreassociate -ffp-eval-method=source \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-ASSOC
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -freciprocal-math -ffp-eval-method=source \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-RECPR
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -freciprocal-math -mreassociate \
+// RUN: -ffp-eval-method=source \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-ASSOC,CHECK-RECPR
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -freciprocal-math -mreassociate -fapprox-func \
+// RUN: -ffp-eval-method=source -verify %s 2>&1 \
+// RUN: | FileCheck %s --check-prefixes=CHECK-ASSOC,CHECK-RECPR,CHECK-FUNC
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -ffp-eval-method=source \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=WARN-FUNC-OPT,WARN-PRGM
+
+// CHECK-FUNC: (frontend): 'fapprox-func' produces inaccurate arithmetic results. It is illegal when 'ffp-eval-method' is set.
+// CHECK-ASSOC: (frontend): 'mreassociate' produces inaccurate arithmetic results. It is illegal when 'ffp-eval-method' is set.
+// CHECK-RECPR: (frontend): 'freciprocal' produces inaccurate arithmetic results. It is illegal when 'ffp-eval-method' is set.
+
+// expected-no-diagnostics
+
+float f1(float a, float b, float c) {
+  a = b + c;
+  return a * b + c;
+}
+
+float f2(float a, float b, float c) {
+  // WARN-FUNC-OPT: eval method setting via 'option ffp-eval-method' cannot be used with 'pragma_clang_fp_eval_reassociate'
+#pragma clang fp reassociate (on)
+  return (a + b) + c;
+}
+
+float f3(float a, float b, float c) {
+#pragma clang fp reassociate (off)
+  return (a - b) - c;
+}
+
+float f4(float a, float b, float c) {
+#pragma clang fp eval_method (double)
+  // WARN-FUNC: '#pragma clang fp eval_method' cannot be used with 'fapprox_func'
+  // WARN-REC: '#pragma clang fp eval_method' cannot be used with 'mreassociate'
+  // WARN-RECPR: '#pragma clang fp eval_method' cannot be used with 'freciprocal'
+  // WARN-PRGM: eval method setting via '#pragma clang fp eval_method' cannot be used with 'pragma_clang_fp_eval_reassociate'
+#pragma clang fp reassociate (on)
+  return (a * c) - (b * c);
+}
Index: clang/lib/Sema/SemaAttr.cpp
===
--- clang/lib/Sema/SemaAttr.cpp
+++ clang/lib/Sema/SemaAttr.cpp
@@ -486,6 +486,15 @@
 NewFPFeatures.setFPEvalMethodOverride(LangOptions::FEM_Extended);
 break;
   }
+  if (getLangOpts().ApproxFunc)
+Diag(Loc, diag::warn_pragma_clang_fp_eval_method_used_with_fapprox_func)
+<< "#pragma clang fp eval_method";
+  if (getLangOpts().AllowFPReassoc)
+Diag(Lo

[PATCH] D122155: Add warning when eval-method is set in the presence of value unsafe floating-point calculations.

2022-03-28 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 418597.
zahiraam marked 5 inline comments as done.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D122155/new/

https://reviews.llvm.org/D122155

Files:
  clang/include/clang/Basic/DiagnosticFrontendKinds.td
  clang/include/clang/Basic/DiagnosticSemaKinds.td
  clang/lib/Frontend/CompilerInvocation.cpp
  clang/lib/Sema/SemaAttr.cpp
  clang/test/Sema/eval-method-with-unsafe-math.c

Index: clang/test/Sema/eval-method-with-unsafe-math.c
===
--- /dev/null
+++ clang/test/Sema/eval-method-with-unsafe-math.c
@@ -0,0 +1,82 @@
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu  \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu  -freciprocal-math \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-RECPR,CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu  -mreassociate \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-ASSOC,CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu  -fapprox-func \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-FUNC,CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -freciprocal-math -mreassociate -verify \
+// RUN: %s 2>&1 | FileCheck %s --check-prefixes=CHECK-ASSOC,CHECK-RECPR,CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -freciprocal-math -mreassociate -fapprox-func \
+// RUN: -verify %s 2>&1 \
+// RUN: | FileCheck %s --check-prefixes=CHECK-FUNC,CHECK-ASSOC,CHECK-RECPR,CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -fapprox-func -ffp-eval-method=source \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-FE-FUNC
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -mreassociate -ffp-eval-method=source \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-FE-ASSOC
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -freciprocal-math -ffp-eval-method=source \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-FE-RECPR
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -freciprocal-math -mreassociate \
+// RUN: -ffp-eval-method=source \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-FE-ASSOC,CHECK-FE-RECPR
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -freciprocal-math -mreassociate -fapprox-func \
+// RUN: -ffp-eval-method=source -verify %s 2>&1 \
+// RUN: | FileCheck %s --check-prefixes=CHECK-FE-ASSOC,CHECK-FE-RECPR,CHECK-FE-FUNC
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -ffp-eval-method=source \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-FFP-OPT,CHECK-PRGM
+
+// CHECK-FE-FUNC: (frontend): option 'ffp-eval-method' cannot be used with option 'fapprox-func'.
+// CHECK-FE-ASSOC: (frontend): option 'ffp-eval-method' cannot be used with option 'mreassociate'.
+// CHECK-FE-RECPR: (frontend): option 'ffp-eval-method' cannot be used with option 'freciprocal'.
+
+// expected-no-diagnostics
+
+float f1(float a, float b, float c) {
+  a = b + c;
+  return a * b + c;
+}
+
+float f2(float a, float b, float c) {
+  // CHECK-FFP-OPT: option 'ffp-eval-method' cannot be used when '#pragma clang fp reassociate' is enabled.
+#pragma clang fp reassociate(on)
+  return (a + b) + c;
+}
+
+float f3(float a, float b, float c) {
+#pragma clang fp reassociate(off)
+  return (a - b) - c;
+}
+
+float f4(float a, float b, float c) {
+#pragma clang fp eval_method (double)
+  // CHECK-FUNC: '#pragma clang fp eval_method' cannot be used when option 'fapprox_func' is enabled.
+  // CHECK-ASSOC: '#pragma clang fp eval_method' cannot be used when option 'mreassociate' is enabled.
+  // CHECK-RECPR: '#pragma clang fp eval_method' cannot be used when option 'freciprocal' is enabled.
+  // CHECK-PRGM: '#pragma clang fp eval_method' cannot be used when '#pragma clang fp reassociate' is enabled.
+#pragma clang fp reassociate(on)
+  return (a * c) - (b * c);
+}
Index: clang/lib/Sema/SemaAttr.cpp
===
--- clang/lib/Sema/SemaAttr.cpp
+++ clang/lib/Sema/SemaAttr.cpp
@@ -486,6 +486,12 @@
 NewFPFeatures.setFPEvalMethodOverride(LangOptions::FEM_Extended);
 break;
   }
+  if (getLangOpts().ApproxFunc)
+Diag(Loc, diag::err_setting_eval_method_used_in_unsafe_context) << 0 << 0;
+  if (getLangOpts().AllowFPReassoc)
+Diag(Loc, diag::err_

[PATCH] D122155: Add warning when eval-method is set in the presence of value unsafe floating-point calculations.

2022-03-29 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 418936.
zahiraam marked 3 inline comments as done.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D122155/new/

https://reviews.llvm.org/D122155

Files:
  clang/include/clang/Basic/DiagnosticFrontendKinds.td
  clang/include/clang/Basic/DiagnosticSemaKinds.td
  clang/lib/Frontend/CompilerInvocation.cpp
  clang/lib/Sema/SemaAttr.cpp
  clang/test/Driver/eval-method-with-unsafe-math.c
  clang/test/Sema/eval-method-with-unsafe-math.c

Index: clang/test/Sema/eval-method-with-unsafe-math.c
===
--- /dev/null
+++ clang/test/Sema/eval-method-with-unsafe-math.c
@@ -0,0 +1,56 @@
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu  \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu  -freciprocal-math \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-RECPR,CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu  -mreassociate \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-ASSOC,CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu  -fapprox-func \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-FUNC,CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -freciprocal-math -mreassociate -verify \
+// RUN: %s 2>&1 | FileCheck %s --check-prefixes=CHECK-ASSOC,CHECK-RECPR,CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -freciprocal-math -mreassociate -fapprox-func \
+// RUN: -verify %s 2>&1 \
+// RUN: | FileCheck %s --check-prefixes=CHECK-FUNC,CHECK-ASSOC,CHECK-RECPR,CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -ffp-eval-method=source \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-FFP-OPT,CHECK-PRGM
+
+// expected-no-diagnostics
+
+float f1(float a, float b, float c) {
+  a = b + c;
+  return a * b + c;
+}
+
+float f2(float a, float b, float c) {
+  // CHECK-FFP-OPT: option 'ffp-eval-method' cannot be used with '#pragma clang fp reassociate'.
+#pragma clang fp reassociate(on)
+  return (a + b) + c;
+}
+
+float f3(float a, float b, float c) {
+#pragma clang fp reassociate(off)
+  return (a - b) - c;
+}
+
+float f4(float a, float b, float c) {
+#pragma clang fp eval_method(double)
+  // CHECK-FUNC: '#pragma clang fp eval_method' cannot be used with option 'fapprox-func'.
+  // CHECK-ASSOC: '#pragma clang fp eval_method' cannot be used with option 'mreassociate'.
+  // CHECK-RECPR: '#pragma clang fp eval_method' cannot be used with option 'freciprocal'.
+  // CHECK-PRGM: '#pragma clang fp eval_method' cannot be used with '#pragma clang fp reassociate'.
+#pragma clang fp reassociate(on)
+  return (a * c) - (b * c);
+}
Index: clang/test/Driver/eval-method-with-unsafe-math.c
===
--- /dev/null
+++ clang/test/Driver/eval-method-with-unsafe-math.c
@@ -0,0 +1,29 @@
+// RUN: not %clang -Xclang -fexperimental-strict-floating-point \
+// RUN: -Xclang -triple -Xclang x86_64-linux-gnu -fapprox-func \
+// RUN: -Xclang -verify -ffp-eval-method=source %s 2>&1  \
+// RUN: | FileCheck %s --check-prefixes=CHECK-FUNC
+
+// RUN: not %clang -Xclang -fexperimental-strict-floating-point \
+// RUN: -Xclang -triple -Xclang x86_64-linux-gnu -Xclang -mreassociate \
+// RUN: -ffp-eval-method=source -Xclang -verify %s 2>&1 \
+// RUN: | FileCheck %s --check-prefixes=CHECK-ASSOC
+
+// RUN: not %clang -Xclang -fexperimental-strict-floating-point \
+// RUN: -Xclang -triple -Xclang x86_64-linux-gnu -Xclang -freciprocal-math \
+// RUN: -ffp-eval-method=source -Xclang -verify %s 2>&1 \
+// RUN: | FileCheck %s --check-prefixes=CHECK-RECPR
+
+// RUN: not %clang -Xclang -fexperimental-strict-floating-point \
+// RUN: -Xclang -triple -Xclang x86_64-linux-gnu -Xclang -freciprocal-math \
+// RUN: -Xclang -mreassociate -ffp-eval-method=source -Xclang -verify %s 2>&1 \
+// RUN: | FileCheck %s --check-prefixes=CHECK-ASSOC,CHECK-RECPR
+
+// RUN: not %clang -Xclang -fexperimental-strict-floating-point \
+// RUN: -Xclang -triple -Xclang x86_64-linux-gnu -Xclang -freciprocal-math \
+// RUN: -Xclang -mreassociate -fapprox-func -ffp-eval-method=source \
+// RUN: -Xclang -verify %s 2>&1 \
+// RUN: | FileCheck %s --check-prefixes=CHECK-ASSOC,CHECK-RECPR,CHECK-FUNC
+
+// CHECK-FUNC: (frontend): option 'ffp-eval-method' cannot be used with option 'fapprox-func'.
+// CHECK-ASSOC: (frontend): option 'ffp-eval-method' cannot be used with option 'mreassociate'.
+// CHECK-RECPR: (frontend): option 'ffp-eval-method' cannot be used with option 'freciprocal'.
Index: clang/lib/Sema/SemaAttr.cpp
===

[PATCH] D122155: Add warning when eval-method is set in the presence of value unsafe floating-point calculations.

2022-04-01 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 419746.
Herald added a subscriber: pengfei.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D122155/new/

https://reviews.llvm.org/D122155

Files:
  clang/include/clang/Basic/DiagnosticFrontendKinds.td
  clang/include/clang/Basic/DiagnosticSemaKinds.td
  clang/lib/Sema/SemaAttr.cpp
  clang/test/CodeGen/X86/32bit-behavior.c
  clang/test/Driver/eval-method-with-unsafe-math.c
  clang/test/Sema/eval-method-with-unsafe-math.c

Index: clang/test/Sema/eval-method-with-unsafe-math.c
===
--- /dev/null
+++ clang/test/Sema/eval-method-with-unsafe-math.c
@@ -0,0 +1,56 @@
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu  \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu  -freciprocal-math \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-RECPR,CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu  -mreassociate \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-ASSOC,CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu  -fapprox-func \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-FUNC,CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -freciprocal-math -mreassociate -verify \
+// RUN: %s 2>&1 | FileCheck %s --check-prefixes=CHECK-ASSOC,CHECK-RECPR,CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -freciprocal-math -mreassociate -fapprox-func \
+// RUN: -verify %s 2>&1 \
+// RUN: | FileCheck %s --check-prefixes=CHECK-FUNC,CHECK-ASSOC,CHECK-RECPR,CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -ffp-eval-method=source \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-FFP-OPT,CHECK-PRGM
+
+// expected-no-diagnostics
+
+float f1(float a, float b, float c) {
+  a = b + c;
+  return a * b + c;
+}
+
+float f2(float a, float b, float c) {
+  // CHECK-FFP-OPT: option 'ffp-eval-method' cannot be used with '#pragma clang fp reassociate'.
+#pragma clang fp reassociate(on)
+  return (a + b) + c;
+}
+
+float f3(float a, float b, float c) {
+#pragma clang fp reassociate(off)
+  return (a - b) - c;
+}
+
+float f4(float a, float b, float c) {
+#pragma clang fp eval_method(double)
+  // CHECK-FUNC: '#pragma clang fp eval_method' cannot be used with option 'fapprox-func'.
+  // CHECK-ASSOC: '#pragma clang fp eval_method' cannot be used with option 'mreassociate'.
+  // CHECK-RECPR: '#pragma clang fp eval_method' cannot be used with option 'freciprocal'.
+  // CHECK-PRGM: '#pragma clang fp eval_method' cannot be used with '#pragma clang fp reassociate'.
+#pragma clang fp reassociate(on)
+  return (a * c) - (b * c);
+}
Index: clang/test/Driver/eval-method-with-unsafe-math.c
===
--- /dev/null
+++ clang/test/Driver/eval-method-with-unsafe-math.c
@@ -0,0 +1,29 @@
+// RUN: not %clang -Xclang -fexperimental-strict-floating-point \
+// RUN: -Xclang -triple -Xclang x86_64-linux-gnu -fapprox-func \
+// RUN: -Xclang -verify -ffp-eval-method=source %s 2>&1  \
+// RUN: | FileCheck %s --check-prefixes=CHECK-FUNC
+
+// RUN: not %clang -Xclang -fexperimental-strict-floating-point \
+// RUN: -Xclang -triple -Xclang x86_64-linux-gnu -Xclang -mreassociate \
+// RUN: -ffp-eval-method=source -Xclang -verify %s 2>&1 \
+// RUN: | FileCheck %s --check-prefixes=CHECK-ASSOC
+
+// RUN: not %clang -Xclang -fexperimental-strict-floating-point \
+// RUN: -Xclang -triple -Xclang x86_64-linux-gnu -Xclang -freciprocal-math \
+// RUN: -ffp-eval-method=source -Xclang -verify %s 2>&1 \
+// RUN: | FileCheck %s --check-prefixes=CHECK-RECPR
+
+// RUN: not %clang -Xclang -fexperimental-strict-floating-point \
+// RUN: -Xclang -triple -Xclang x86_64-linux-gnu -Xclang -freciprocal-math \
+// RUN: -Xclang -mreassociate -ffp-eval-method=source -Xclang -verify %s 2>&1 \
+// RUN: | FileCheck %s --check-prefixes=CHECK-ASSOC,CHECK-RECPR
+
+// RUN: not %clang -Xclang -fexperimental-strict-floating-point \
+// RUN: -Xclang -triple -Xclang x86_64-linux-gnu -Xclang -freciprocal-math \
+// RUN: -Xclang -mreassociate -fapprox-func -ffp-eval-method=source \
+// RUN: -Xclang -verify %s 2>&1 \
+// RUN: | FileCheck %s --check-prefixes=CHECK-ASSOC,CHECK-RECPR,CHECK-FUNC
+
+// CHECK-FUNC: (frontend): option 'ffp-eval-method' cannot be used with option 'fapprox-func'.
+// CHECK-ASSOC: (frontend): option 'ffp-eval-method' cannot be used with option 'mreassociate'.
+// CHECK-RECPR: (frontend): option 'ffp-eval-method' cannot be used with option 'freciprocal'.
Index: clang/test/CodeGen/X86/32bit-behavior.c

[PATCH] D122155: Add warning when eval-method is set in the presence of value unsafe floating-point calculations.

2022-04-01 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 419763.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D122155/new/

https://reviews.llvm.org/D122155

Files:
  clang/include/clang/Basic/DiagnosticFrontendKinds.td
  clang/include/clang/Basic/DiagnosticSemaKinds.td
  clang/lib/Sema/SemaAttr.cpp
  clang/test/CodeGen/X86/32bit-behavior.c
  clang/test/Driver/eval-method-with-unsafe-math.c
  clang/test/Sema/eval-method-with-unsafe-math.c

Index: clang/test/Sema/eval-method-with-unsafe-math.c
===
--- /dev/null
+++ clang/test/Sema/eval-method-with-unsafe-math.c
@@ -0,0 +1,56 @@
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu  \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu  -freciprocal-math \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-RECPR,CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu  -mreassociate \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-ASSOC,CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu  -fapprox-func \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-FUNC,CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -freciprocal-math -mreassociate -verify \
+// RUN: %s 2>&1 | FileCheck %s --check-prefixes=CHECK-ASSOC,CHECK-RECPR,CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -freciprocal-math -mreassociate -fapprox-func \
+// RUN: -verify %s 2>&1 \
+// RUN: | FileCheck %s --check-prefixes=CHECK-FUNC,CHECK-ASSOC,CHECK-RECPR,CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -ffp-eval-method=source \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-FFP-OPT,CHECK-PRGM
+
+// expected-no-diagnostics
+
+float f1(float a, float b, float c) {
+  a = b + c;
+  return a * b + c;
+}
+
+float f2(float a, float b, float c) {
+  // CHECK-FFP-OPT: option 'ffp-eval-method' cannot be used with '#pragma clang fp reassociate'.
+#pragma clang fp reassociate(on)
+  return (a + b) + c;
+}
+
+float f3(float a, float b, float c) {
+#pragma clang fp reassociate(off)
+  return (a - b) - c;
+}
+
+float f4(float a, float b, float c) {
+#pragma clang fp eval_method(double)
+  // CHECK-FUNC: '#pragma clang fp eval_method' cannot be used with option 'fapprox-func'.
+  // CHECK-ASSOC: '#pragma clang fp eval_method' cannot be used with option 'mreassociate'.
+  // CHECK-RECPR: '#pragma clang fp eval_method' cannot be used with option 'freciprocal'.
+  // CHECK-PRGM: '#pragma clang fp eval_method' cannot be used with '#pragma clang fp reassociate'.
+#pragma clang fp reassociate(on)
+  return (a * c) - (b * c);
+}
Index: clang/test/Driver/eval-method-with-unsafe-math.c
===
--- /dev/null
+++ clang/test/Driver/eval-method-with-unsafe-math.c
@@ -0,0 +1,29 @@
+// RUN: not %clang -Xclang -fexperimental-strict-floating-point \
+// RUN: -Xclang -triple -Xclang x86_64-linux-gnu -fapprox-func \
+// RUN: -Xclang -verify -ffp-eval-method=source %s 2>&1  \
+// RUN: | FileCheck %s --check-prefixes=CHECK-FUNC
+
+// RUN: not %clang -Xclang -fexperimental-strict-floating-point \
+// RUN: -Xclang -triple -Xclang x86_64-linux-gnu -Xclang -mreassociate \
+// RUN: -ffp-eval-method=source -Xclang -verify %s 2>&1 \
+// RUN: | FileCheck %s --check-prefixes=CHECK-ASSOC
+
+// RUN: not %clang -Xclang -fexperimental-strict-floating-point \
+// RUN: -Xclang -triple -Xclang x86_64-linux-gnu -Xclang -freciprocal-math \
+// RUN: -ffp-eval-method=source -Xclang -verify %s 2>&1 \
+// RUN: | FileCheck %s --check-prefixes=CHECK-RECPR
+
+// RUN: not %clang -Xclang -fexperimental-strict-floating-point \
+// RUN: -Xclang -triple -Xclang x86_64-linux-gnu -Xclang -freciprocal-math \
+// RUN: -Xclang -mreassociate -ffp-eval-method=source -Xclang -verify %s 2>&1 \
+// RUN: | FileCheck %s --check-prefixes=CHECK-ASSOC,CHECK-RECPR
+
+// RUN: not %clang -Xclang -fexperimental-strict-floating-point \
+// RUN: -Xclang -triple -Xclang x86_64-linux-gnu -Xclang -freciprocal-math \
+// RUN: -Xclang -mreassociate -fapprox-func -ffp-eval-method=source \
+// RUN: -Xclang -verify %s 2>&1 \
+// RUN: | FileCheck %s --check-prefixes=CHECK-ASSOC,CHECK-RECPR,CHECK-FUNC
+
+// CHECK-FUNC: (frontend): option 'ffp-eval-method' cannot be used with option 'fapprox-func'.
+// CHECK-ASSOC: (frontend): option 'ffp-eval-method' cannot be used with option 'mreassociate'.
+// CHECK-RECPR: (frontend): option 'ffp-eval-method' cannot be used with option 'freciprocal'.
Index: clang/test/CodeGen/X86/32bit-behavior.c

[PATCH] D122155: Add warning when eval-method is set in the presence of value unsafe floating-point calculations.

2022-04-03 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 420035.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D122155/new/

https://reviews.llvm.org/D122155

Files:
  clang/include/clang/Basic/DiagnosticFrontendKinds.td
  clang/include/clang/Basic/DiagnosticSemaKinds.td
  clang/lib/Frontend/CompilerInvocation.cpp
  clang/lib/Sema/SemaAttr.cpp
  clang/test/Driver/eval-method-with-unsafe-math.c
  clang/test/Sema/eval-method-with-unsafe-math.c

Index: clang/test/Sema/eval-method-with-unsafe-math.c
===
--- /dev/null
+++ clang/test/Sema/eval-method-with-unsafe-math.c
@@ -0,0 +1,56 @@
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu  \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu  -freciprocal-math \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-RECPR,CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu  -mreassociate \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-ASSOC,CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu  -fapprox-func \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-FUNC,CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -freciprocal-math -mreassociate -verify \
+// RUN: %s 2>&1 | FileCheck %s --check-prefixes=CHECK-ASSOC,CHECK-RECPR,CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -freciprocal-math -mreassociate -fapprox-func \
+// RUN: -verify %s 2>&1 \
+// RUN: | FileCheck %s --check-prefixes=CHECK-FUNC,CHECK-ASSOC,CHECK-RECPR,CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -ffp-eval-method=source \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-FFP-OPT,CHECK-PRGM
+
+// expected-no-diagnostics
+
+float f1(float a, float b, float c) {
+  a = b + c;
+  return a * b + c;
+}
+
+float f2(float a, float b, float c) {
+  // CHECK-FFP-OPT: option 'ffp-eval-method' cannot be used with '#pragma clang fp reassociate'
+#pragma clang fp reassociate(on)
+  return (a + b) + c;
+}
+
+float f3(float a, float b, float c) {
+#pragma clang fp reassociate(off)
+  return (a - b) - c;
+}
+
+float f4(float a, float b, float c) {
+#pragma clang fp eval_method(double)
+  // CHECK-FUNC: '#pragma clang fp eval_method' cannot be used with option 'fapprox-func'
+  // CHECK-ASSOC: '#pragma clang fp eval_method' cannot be used with option 'mreassociate'
+  // CHECK-RECPR: '#pragma clang fp eval_method' cannot be used with option 'freciprocal'
+  // CHECK-PRGM: '#pragma clang fp eval_method' cannot be used with '#pragma clang fp reassociate'
+#pragma clang fp reassociate(on)
+  return (a * c) - (b * c);
+}
Index: clang/test/Driver/eval-method-with-unsafe-math.c
===
--- /dev/null
+++ clang/test/Driver/eval-method-with-unsafe-math.c
@@ -0,0 +1,29 @@
+// RUN: not %clang -Xclang -fexperimental-strict-floating-point \
+// RUN: -Xclang -triple -Xclang x86_64-linux-gnu -fapprox-func \
+// RUN: -Xclang -verify -ffp-eval-method=source %s 2>&1  \
+// RUN: | FileCheck %s --check-prefixes=CHECK-FUNC
+
+// RUN: not %clang -Xclang -fexperimental-strict-floating-point \
+// RUN: -Xclang -triple -Xclang x86_64-linux-gnu -Xclang -mreassociate \
+// RUN: -ffp-eval-method=source -Xclang -verify %s 2>&1 \
+// RUN: | FileCheck %s --check-prefixes=CHECK-ASSOC
+
+// RUN: not %clang -Xclang -fexperimental-strict-floating-point \
+// RUN: -Xclang -triple -Xclang x86_64-linux-gnu -Xclang -freciprocal-math \
+// RUN: -ffp-eval-method=source -Xclang -verify %s 2>&1 \
+// RUN: | FileCheck %s --check-prefixes=CHECK-RECPR
+
+// RUN: not %clang -Xclang -fexperimental-strict-floating-point \
+// RUN: -Xclang -triple -Xclang x86_64-linux-gnu -Xclang -freciprocal-math \
+// RUN: -Xclang -mreassociate -ffp-eval-method=source -Xclang -verify %s 2>&1 \
+// RUN: | FileCheck %s --check-prefixes=CHECK-ASSOC,CHECK-RECPR
+
+// RUN: not %clang -Xclang -fexperimental-strict-floating-point \
+// RUN: -Xclang -triple -Xclang x86_64-linux-gnu -Xclang -freciprocal-math \
+// RUN: -Xclang -mreassociate -fapprox-func -ffp-eval-method=source \
+// RUN: -Xclang -verify %s 2>&1 \
+// RUN: | FileCheck %s --check-prefixes=CHECK-ASSOC,CHECK-RECPR,CHECK-FUNC
+
+// CHECK-FUNC: (frontend): option 'ffp-eval-method' cannot be used with option 'fapprox-func'
+// CHECK-ASSOC: (frontend): option 'ffp-eval-method' cannot be used with option 'mreassociate'
+// CHECK-RECPR: (frontend): option 'ffp-eval-method' cannot be used with option 'freciprocal'
Index: clang/lib/Sema/SemaAttr.cpp
==

[PATCH] D122992: Remove wrong warning. Fix for https://github.com/llvm/llvm-project/issues/54625

2022-04-03 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam created this revision.
zahiraam added reviewers: andrew.w.kaylor, aaron.ballman, efriedma.
Herald added a project: All.
zahiraam requested review of this revision.
Herald added a subscriber: MaskRay.
Herald added a project: clang.

When driver's floating-point options change, the user is made aware via a 
diagnostic. In the case of combining a fast math option with a non-fast option 
there should be no diagnostic. This patch removes the wrong diagnostic.
This is a fix for https://github.com/llvm/llvm-project/issues/54625.


Repository:
  rG LLVM Github Monorepo

https://reviews.llvm.org/D122992

Files:
  clang/lib/Driver/ToolChains/Clang.cpp
  clang/test/Driver/fp-model.c


Index: clang/test/Driver/fp-model.c
===
--- clang/test/Driver/fp-model.c
+++ clang/test/Driver/fp-model.c
@@ -3,6 +3,8 @@
 //
 // REQUIRES: clang-driver
 
+// expected-no-diagnostics
+
 // RUN: %clang -### -ffp-model=fast -ffp-contract=off -c %s 2>&1 \
 // RUN:   | FileCheck --check-prefix=WARN %s
 // WARN: warning: overriding '-ffp-model=fast' option with '-ffp-contract=off' 
[-Woverriding-t-option]
@@ -19,6 +21,13 @@
 // RUN:   | FileCheck --check-prefix=WARN3 %s
 // WARN3: warning: overriding '-ffp-model=strict' option with '-ffast-math' 
[-Woverriding-t-option]
 
+// RUN: %clang -c -ffast-math -fno-fast-math -Xclang -verify %s 2>&1
+// RUN: %clang -c -fno-fast-math -ffast-math -Xclang -verify %s 2>&1
+// RUN: %clang -c -ffast-math -ffp-contract=on -Xclang -verify %s 2>&1
+// RUN: %clang -c -ffp-contract=on -ffast-math -Xclang -verify %s 2>&1
+// RUN: %clang -c -ffp-contract=on -ffp-model=fast -Xclang -verify %s 2>&1
+// RUN: %clang -c -ffp-model=fast -ffp-contract=on -Xclang -verify %s 2>&1
+
 // RUN: %clang -### -ffp-model=strict -ffinite-math-only -c %s 2>&1 \
 // RUN:   | FileCheck --check-prefix=WARN4 %s
 // WARN4: warning: overriding '-ffp-model=strict' option with 
'-ffinite-math-only' [-Woverriding-t-option]
@@ -63,6 +72,9 @@
 // RUN:   | FileCheck --check-prefix=WARNf %s
 // WARNf: warning: overriding '-ffp-model=strict' option with '-Ofast' 
[-Woverriding-t-option]
 
+// RUN: %clang -c -Ofast -fno-fast-math -Xclang -verify %s 2>&1
+// RUN: %clang -c -fno-fast-math -Ofast  -Xclang -verify %s 2>&1
+
 // RUN: %clang -### -ffp-model=strict 
-fdenormal-fp-math=preserve-sign,preserve-sign -c %s 2>&1 \
 // RUN:   | FileCheck --check-prefix=WARN10 %s
 // WARN10: warning: overriding '-ffp-model=strict' option with 
'-fdenormal-fp-math=preserve-sign,preserve-sign' [-Woverriding-t-option]
@@ -102,6 +114,9 @@
 // CHECK-FPM-PRECISE: "-ffp-contract=on"
 // CHECK-FPM-PRECISE: "-fno-rounding-math"
 
+// RUN: %clang -c -ffp-model=precise -ffp-contract=fast -Xclang -verify %s 2>&1
+// RUN: %clang -c -ffp-contract=fast -ffp-model=precise -Xclang -verify %s 2>&1
+
 // RUN: %clang -### -nostdinc -ffp-model=strict -c %s 2>&1 \
 // RUN:   | FileCheck --check-prefix=CHECK-FPM-STRICT %s
 // CHECK-FPM-STRICT: "-cc1"
Index: clang/lib/Driver/ToolChains/Clang.cpp
===
--- clang/lib/Driver/ToolChains/Clang.cpp
+++ clang/lib/Driver/ToolChains/Clang.cpp
@@ -3006,9 +3006,6 @@
   !JA.isOffloading(Action::OFK_HIP))
 if (FPContract == "fast") {
   FPContract = "on";
-  D.Diag(clang::diag::warn_drv_overriding_flag_option)
-  << "-ffp-contract=fast"
-  << "-ffp-contract=on";
 }
   break;
 }


Index: clang/test/Driver/fp-model.c
===
--- clang/test/Driver/fp-model.c
+++ clang/test/Driver/fp-model.c
@@ -3,6 +3,8 @@
 //
 // REQUIRES: clang-driver
 
+// expected-no-diagnostics
+
 // RUN: %clang -### -ffp-model=fast -ffp-contract=off -c %s 2>&1 \
 // RUN:   | FileCheck --check-prefix=WARN %s
 // WARN: warning: overriding '-ffp-model=fast' option with '-ffp-contract=off' [-Woverriding-t-option]
@@ -19,6 +21,13 @@
 // RUN:   | FileCheck --check-prefix=WARN3 %s
 // WARN3: warning: overriding '-ffp-model=strict' option with '-ffast-math' [-Woverriding-t-option]
 
+// RUN: %clang -c -ffast-math -fno-fast-math -Xclang -verify %s 2>&1
+// RUN: %clang -c -fno-fast-math -ffast-math -Xclang -verify %s 2>&1
+// RUN: %clang -c -ffast-math -ffp-contract=on -Xclang -verify %s 2>&1
+// RUN: %clang -c -ffp-contract=on -ffast-math -Xclang -verify %s 2>&1
+// RUN: %clang -c -ffp-contract=on -ffp-model=fast -Xclang -verify %s 2>&1
+// RUN: %clang -c -ffp-model=fast -ffp-contract=on -Xclang -verify %s 2>&1
+
 // RUN: %clang -### -ffp-model=strict -ffinite-math-only -c %s 2>&1 \
 // RUN:   | FileCheck --check-prefix=WARN4 %s
 // WARN4: warning: overriding '-ffp-model=strict' option with '-ffinite-math-only' [-Woverriding-t-option]
@@ -63,6 +72,9 @@
 // RUN:   | FileCheck --check-prefix=WARNf %s
 // WARNf: warning: overriding '-ffp-model=strict' option with '-Ofast' [-Woverriding-t-option]
 
+// RUN: %clang -c -Ofast -fno

[PATCH] D122155: Add warning when eval-method is set in the presence of value unsafe floating-point calculations.

2022-04-04 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 420168.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D122155/new/

https://reviews.llvm.org/D122155

Files:
  clang/include/clang/Basic/DiagnosticFrontendKinds.td
  clang/include/clang/Basic/DiagnosticSemaKinds.td
  clang/lib/Frontend/CompilerInvocation.cpp
  clang/lib/Sema/SemaAttr.cpp
  clang/test/CodeGen/X86/32bit-behavior.c
  clang/test/Driver/eval-method-with-unsafe-math.c
  clang/test/Sema/eval-method-with-unsafe-math.c

Index: clang/test/Sema/eval-method-with-unsafe-math.c
===
--- /dev/null
+++ clang/test/Sema/eval-method-with-unsafe-math.c
@@ -0,0 +1,56 @@
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu  \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu  -freciprocal-math \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-RECPR,CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu  -mreassociate \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-ASSOC,CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu  -fapprox-func \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-FUNC,CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -freciprocal-math -mreassociate -verify \
+// RUN: %s 2>&1 | FileCheck %s --check-prefixes=CHECK-ASSOC,CHECK-RECPR,CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -freciprocal-math -mreassociate -fapprox-func \
+// RUN: -verify %s 2>&1 \
+// RUN: | FileCheck %s --check-prefixes=CHECK-FUNC,CHECK-ASSOC,CHECK-RECPR,CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -ffp-eval-method=source \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-FFP-OPT,CHECK-PRGM
+
+// expected-no-diagnostics
+
+float f1(float a, float b, float c) {
+  a = b + c;
+  return a * b + c;
+}
+
+float f2(float a, float b, float c) {
+  // CHECK-FFP-OPT: option 'ffp-eval-method' cannot be used with '#pragma clang fp reassociate'
+#pragma clang fp reassociate(on)
+  return (a + b) + c;
+}
+
+float f3(float a, float b, float c) {
+#pragma clang fp reassociate(off)
+  return (a - b) - c;
+}
+
+float f4(float a, float b, float c) {
+#pragma clang fp eval_method(double)
+  // CHECK-FUNC: '#pragma clang fp eval_method' cannot be used with option 'fapprox-func'
+  // CHECK-ASSOC: '#pragma clang fp eval_method' cannot be used with option 'mreassociate'
+  // CHECK-RECPR: '#pragma clang fp eval_method' cannot be used with option 'freciprocal'
+  // CHECK-PRGM: '#pragma clang fp eval_method' cannot be used with '#pragma clang fp reassociate'
+#pragma clang fp reassociate(on)
+  return (a * c) - (b * c);
+}
Index: clang/test/Driver/eval-method-with-unsafe-math.c
===
--- /dev/null
+++ clang/test/Driver/eval-method-with-unsafe-math.c
@@ -0,0 +1,29 @@
+// RUN: not %clang -Xclang -fexperimental-strict-floating-point \
+// RUN: -Xclang -triple -Xclang x86_64-linux-gnu -fapprox-func \
+// RUN: -Xclang -verify -ffp-eval-method=source %s 2>&1  \
+// RUN: | FileCheck %s --check-prefixes=CHECK-FUNC
+
+// RUN: not %clang -Xclang -fexperimental-strict-floating-point \
+// RUN: -Xclang -triple -Xclang x86_64-linux-gnu -Xclang -mreassociate \
+// RUN: -ffp-eval-method=source -Xclang -verify %s 2>&1 \
+// RUN: | FileCheck %s --check-prefixes=CHECK-ASSOC
+
+// RUN: not %clang -Xclang -fexperimental-strict-floating-point \
+// RUN: -Xclang -triple -Xclang x86_64-linux-gnu -Xclang -freciprocal-math \
+// RUN: -ffp-eval-method=source -Xclang -verify %s 2>&1 \
+// RUN: | FileCheck %s --check-prefixes=CHECK-RECPR
+
+// RUN: not %clang -Xclang -fexperimental-strict-floating-point \
+// RUN: -Xclang -triple -Xclang x86_64-linux-gnu -Xclang -freciprocal-math \
+// RUN: -Xclang -mreassociate -ffp-eval-method=source -Xclang -verify %s 2>&1 \
+// RUN: | FileCheck %s --check-prefixes=CHECK-ASSOC,CHECK-RECPR
+
+// RUN: not %clang -Xclang -fexperimental-strict-floating-point \
+// RUN: -Xclang -triple -Xclang x86_64-linux-gnu -Xclang -freciprocal-math \
+// RUN: -Xclang -mreassociate -fapprox-func -ffp-eval-method=source \
+// RUN: -Xclang -verify %s 2>&1 \
+// RUN: | FileCheck %s --check-prefixes=CHECK-ASSOC,CHECK-RECPR,CHECK-FUNC
+
+// CHECK-FUNC: (frontend): option 'ffp-eval-method' cannot be used with option 'fapprox-func'
+// CHECK-ASSOC: (frontend): option 'ffp-eval-method' cannot be used with option 'mreassociate'
+// CHECK-RECPR: (frontend): option 'ffp-eval-method' cannot be used with option 'freciprocal'
Index: clang/test/CodeGen/X86/32bit-behavior.c

[PATCH] D122155: Add warning when eval-method is set in the presence of value unsafe floating-point calculations.

2022-04-05 Thread Zahira Ammarguellat via Phabricator via cfe-commits
This revision was automatically updated to reflect the committed changes.
Closed by commit rG4d165ad7d9b3: In fast-math mode, when unsafe math 
optimizations are enabled, the (authored by zahiraam).

Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D122155/new/

https://reviews.llvm.org/D122155

Files:
  clang/include/clang/Basic/DiagnosticFrontendKinds.td
  clang/include/clang/Basic/DiagnosticSemaKinds.td
  clang/lib/Frontend/CompilerInvocation.cpp
  clang/lib/Sema/SemaAttr.cpp
  clang/test/CodeGen/X86/32bit-behavior.c
  clang/test/Driver/eval-method-with-unsafe-math.c
  clang/test/Sema/eval-method-with-unsafe-math.c

Index: clang/test/Sema/eval-method-with-unsafe-math.c
===
--- /dev/null
+++ clang/test/Sema/eval-method-with-unsafe-math.c
@@ -0,0 +1,56 @@
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu  \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu  -freciprocal-math \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-RECPR,CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu  -mreassociate \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-ASSOC,CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu  -fapprox-func \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-FUNC,CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -freciprocal-math -mreassociate -verify \
+// RUN: %s 2>&1 | FileCheck %s --check-prefixes=CHECK-ASSOC,CHECK-RECPR,CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -freciprocal-math -mreassociate -fapprox-func \
+// RUN: -verify %s 2>&1 \
+// RUN: | FileCheck %s --check-prefixes=CHECK-FUNC,CHECK-ASSOC,CHECK-RECPR,CHECK-PRGM
+
+// RUN: not %clang_cc1 -fexperimental-strict-floating-point \
+// RUN: -triple x86_64-linux-gnu -ffp-eval-method=source \
+// RUN: -verify %s 2>&1 | FileCheck %s --check-prefixes=CHECK-FFP-OPT,CHECK-PRGM
+
+// expected-no-diagnostics
+
+float f1(float a, float b, float c) {
+  a = b + c;
+  return a * b + c;
+}
+
+float f2(float a, float b, float c) {
+  // CHECK-FFP-OPT: option 'ffp-eval-method' cannot be used with '#pragma clang fp reassociate'
+#pragma clang fp reassociate(on)
+  return (a + b) + c;
+}
+
+float f3(float a, float b, float c) {
+#pragma clang fp reassociate(off)
+  return (a - b) - c;
+}
+
+float f4(float a, float b, float c) {
+#pragma clang fp eval_method(double)
+  // CHECK-FUNC: '#pragma clang fp eval_method' cannot be used with option 'fapprox-func'
+  // CHECK-ASSOC: '#pragma clang fp eval_method' cannot be used with option 'mreassociate'
+  // CHECK-RECPR: '#pragma clang fp eval_method' cannot be used with option 'freciprocal'
+  // CHECK-PRGM: '#pragma clang fp eval_method' cannot be used with '#pragma clang fp reassociate'
+#pragma clang fp reassociate(on)
+  return (a * c) - (b * c);
+}
Index: clang/test/Driver/eval-method-with-unsafe-math.c
===
--- /dev/null
+++ clang/test/Driver/eval-method-with-unsafe-math.c
@@ -0,0 +1,29 @@
+// RUN: not %clang -Xclang -fexperimental-strict-floating-point \
+// RUN: -Xclang -triple -Xclang x86_64-linux-gnu -fapprox-func \
+// RUN: -Xclang -verify -ffp-eval-method=source %s 2>&1  \
+// RUN: | FileCheck %s --check-prefixes=CHECK-FUNC
+
+// RUN: not %clang -Xclang -fexperimental-strict-floating-point \
+// RUN: -Xclang -triple -Xclang x86_64-linux-gnu -Xclang -mreassociate \
+// RUN: -ffp-eval-method=source -Xclang -verify %s 2>&1 \
+// RUN: | FileCheck %s --check-prefixes=CHECK-ASSOC
+
+// RUN: not %clang -Xclang -fexperimental-strict-floating-point \
+// RUN: -Xclang -triple -Xclang x86_64-linux-gnu -Xclang -freciprocal-math \
+// RUN: -ffp-eval-method=source -Xclang -verify %s 2>&1 \
+// RUN: | FileCheck %s --check-prefixes=CHECK-RECPR
+
+// RUN: not %clang -Xclang -fexperimental-strict-floating-point \
+// RUN: -Xclang -triple -Xclang x86_64-linux-gnu -Xclang -freciprocal-math \
+// RUN: -Xclang -mreassociate -ffp-eval-method=source -Xclang -verify %s 2>&1 \
+// RUN: | FileCheck %s --check-prefixes=CHECK-ASSOC,CHECK-RECPR
+
+// RUN: not %clang -Xclang -fexperimental-strict-floating-point \
+// RUN: -Xclang -triple -Xclang x86_64-linux-gnu -Xclang -freciprocal-math \
+// RUN: -Xclang -mreassociate -fapprox-func -ffp-eval-method=source \
+// RUN: -Xclang -verify %s 2>&1 \
+// RUN: | FileCheck %s --check-prefixes=CHECK-ASSOC,CHECK-RECPR,CHECK-FUNC
+
+// CHECK-FUNC: (frontend): option 'ffp-eval-method' cannot be used with option 'fapprox-func'
+// CHECK-ASSOC: (frontend): option 'ffp-eval-method' canno

[PATCH] D113107: Support of expression granularity for _Float16.

2022-08-09 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 451261.
zahiraam marked 7 inline comments as done.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D113107/new/

https://reviews.llvm.org/D113107

Files:
  clang/docs/LanguageExtensions.rst
  clang/include/clang/Basic/TargetInfo.h
  clang/lib/Basic/Targets/X86.cpp
  clang/lib/Basic/Targets/X86.h
  clang/lib/CodeGen/CGExprComplex.cpp
  clang/lib/CodeGen/CGExprScalar.cpp
  clang/lib/CodeGen/CodeGenFunction.h
  clang/test/CodeGen/X86/Float16-arithmetic.c
  clang/test/CodeGen/X86/Float16-complex.c
  clang/test/Sema/Float16.c
  clang/test/SemaCXX/Float16.cpp

Index: clang/test/SemaCXX/Float16.cpp
===
--- clang/test/SemaCXX/Float16.cpp
+++ clang/test/SemaCXX/Float16.cpp
@@ -1,20 +1,10 @@
-// RUN: %clang_cc1 -fsyntax-only -verify -triple i686-linux-pc %s
-// RUN: %clang_cc1 -fsyntax-only -verify -triple i686-linux-pc -target-feature +sse2 %s -DHAVE
-// RUN: %clang_cc1 -fsyntax-only -verify -triple x86_64-linux-pc %s -DHAVE
-// RUN: %clang_cc1 -fsyntax-only -verify -triple spir-unknown-unknown %s -DHAVE
-// RUN: %clang_cc1 -fsyntax-only -verify -triple armv7a-linux-gnu %s -DHAVE
-// RUN: %clang_cc1 -fsyntax-only -verify -triple aarch64-linux-gnu %s -DHAVE
+// RUN: %clang_cc1 -fsyntax-only -verify -triple x86_64-linux-pc %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple spir-unknown-unknown %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple armv7a-linux-gnu %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple aarch64-linux-gnu %s
 
-#ifdef HAVE
 // expected-no-diagnostics
-#endif // HAVE
 
-#ifndef HAVE
-// expected-error@+2{{_Float16 is not supported on this target}}
-#endif // !HAVE
 _Float16 f;
 
-#ifndef HAVE
-// expected-error@+2{{invalid suffix 'F16' on floating constant}}
-#endif // !HAVE
 const auto g = 1.1F16;
Index: clang/test/Sema/Float16.c
===
--- clang/test/Sema/Float16.c
+++ clang/test/Sema/Float16.c
@@ -1,19 +1,15 @@
-// RUN: %clang_cc1 -fsyntax-only -verify -triple i686-linux-pc %s
-// RUN: %clang_cc1 -fsyntax-only -verify -triple i686-linux-pc -target-feature +sse2 %s -DHAVE
-// RUN: %clang_cc1 -fsyntax-only -verify -triple x86_64-linux-pc %s -DHAVE
-// RUN: %clang_cc1 -fsyntax-only -verify -triple spir-unknown-unknown %s -DHAVE
-// RUN: %clang_cc1 -fsyntax-only -verify -triple armv7a-linux-gnu %s -DHAVE
-// RUN: %clang_cc1 -fsyntax-only -verify -triple aarch64-linux-gnu %s -DHAVE
+// RUN: %clang_cc1 -fsyntax-only -verify -triple x86_64-linux-pc %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple x86_64-linux-pc -target-feature +avx512fp16 %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple spir-unknown-unknown %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple armv7a-linux-gnu %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple aarch64-linux-gnu %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple x86_64-linux-pc -target-feature +avx512fp16 %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple spir-unknown-unknown %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple armv7a-linux-gnu %s
+// RUN: %clang_cc1 -fsyntax-only -verify -triple aarch64-linux-gnu %s
 
-#ifndef HAVE
-// expected-error@+2{{_Float16 is not supported on this target}}
-#endif // HAVE
-_Float16 f;
-
-#ifdef HAVE
 _Complex _Float16 a;
 void builtin_complex(void) {
   _Float16 a = 0;
   (void)__builtin_complex(a, a); // expected-error {{'_Complex _Float16' is invalid}}
 }
-#endif
Index: clang/test/CodeGen/X86/Float16-complex.c
===
--- clang/test/CodeGen/X86/Float16-complex.c
+++ clang/test/CodeGen/X86/Float16-complex.c
@@ -1,134 +1,995 @@
-// RUN: %clang_cc1 %s -O0 -emit-llvm -triple x86_64-unknown-unknown -target-feature +avx512fp16 -o - | FileCheck %s --check-prefix=X86
-// RUN: %clang_cc1 %s -O0 -emit-llvm -triple x86_64-unknown-unknown -o - | FileCheck %s --check-prefix=X86
+// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py
+// RUN: %clang_cc1 %s -O0 -emit-llvm -triple x86_64-unknown-unknown -target-feature +avx512fp16 -o - | FileCheck %s --check-prefixes=AVX
+// RUN: %clang_cc1 %s -O0 -emit-llvm -triple x86_64-unknown-unknown -o - | FileCheck %s --check-prefixes=X86
 
+// AVX-LABEL: @add_half_rr(
+// AVX-NEXT:  entry:
+// AVX-NEXT:[[RETVAL:%.*]] = alloca { half, half }, align 2
+// AVX-NEXT:[[A_ADDR:%.*]] = alloca half, align 2
+// AVX-NEXT:[[B_ADDR:%.*]] = alloca half, align 2
+// AVX-NEXT:store half [[A:%.*]], ptr [[A_ADDR]], align 2
+// AVX-NEXT:store half [[B:%.*]], ptr [[B_ADDR]], align 2
+// AVX-NEXT:[[TMP0:%.*]] = load half, ptr [[A_ADDR]], align 2
+// AVX-NEXT:[[TMP1:%.*]] = load half, ptr [[B_ADDR]], align 2
+// AVX-NEXT:[[ADD:%.*]] = fadd half [[TMP0]], [[TMP1]]
+// AVX-NEXT:[[RETVAL_REALP:%.*]] = getelementptr inbounds { half, half }, ptr [[RETVAL]], i32 0, i32 0
+// AVX-NEXT:[[RETVAL_IMAGP:%.*]] = getelement

[PATCH] D113107: Support of expression granularity for _Float16.

2022-08-09 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added inline comments.



Comment at: clang/test/CodeGen/X86/Float16-arithmetic.c:5-14
+  // CHECK-LABEL: @add1
+  // CHECK: [[A:%.*]] = alloca half
+  // CHECK-NEXT: [[B:%.*]] = alloca half
+  // CHECK: [[A_LOAD:%.*]] = load half, ptr [[A]]
+  // CHECK-NEXT: [[A_EXT:%.*]] = fpext half [[A_LOAD]] to float
+  // CHECK-NEXT: [[B_LOAD:%.*]] = load half, ptr [[B]]
+  // CHECK-NEXT: [[B_EXT:%.*]] = fpext half [[B_LOAD]] to float

pengfei wrote:
> Are these code generated manually? It can be updated by command 
> `llvm/utils/update_cc_test_checks.py 
> clang/test/CodeGen/X86/Float16-arithmetic.c`.
@pengfei Thanks. I didn't know about the script.


CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D113107/new/

https://reviews.llvm.org/D113107

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D113107: Support of expression granularity for _Float16.

2022-08-09 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added a comment.

@pengfei , @rjmccall  Thanks for the reviews. Sorry the updated patch took so 
long, I was on my sabbatical and returned back this week.
I think I have responded to all the raised issues. Let me know if there is more 
to be done on this patch.
Again thanks for the reviews.


CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D113107/new/

https://reviews.llvm.org/D113107

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D121122: Set FLT_EVAL_METHOD to -1 when fast-math is enabled.

2022-03-08 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 413936.
zahiraam marked 3 inline comments as done.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D121122/new/

https://reviews.llvm.org/D121122

Files:
  clang/lib/Lex/PPMacroExpansion.cpp
  clang/lib/Sema/Sema.cpp
  clang/lib/Sema/SemaAttr.cpp
  clang/test/CodeGen/eval-method-fast-math.c

Index: clang/test/CodeGen/eval-method-fast-math.c
===
--- /dev/null
+++ clang/test/CodeGen/eval-method-fast-math.c
@@ -0,0 +1,87 @@
+// RUN: %clang_cc1 -fexperimental-strict-floating-point  \
+// RUN: -triple x86_64-linux-gnu -emit-llvm -o - %s  \
+// RUN: | FileCheck %s -check-prefixes=CHECK
+
+// RUN: %clang_cc1 -triple i386--linux -emit-llvm -o - %s \
+// RUN: | FileCheck %s -check-prefixes=CHECK-EXT
+
+// RUN: %clang_cc1 -fexperimental-strict-floating-point  \
+// RUN: -mreassociate -freciprocal-math -ffp-contract=fast \
+// RUN: -ffast-math -triple x86_64-linux-gnu \
+// RUN: -emit-llvm -o - %s \
+// RUN: | FileCheck %s -check-prefixes=CHECK-FAST
+
+// RUN: %clang_cc1 -triple i386--linux -mreassociate -freciprocal-math \
+// RUN: -ffp-contract=fast -ffast-math -emit-llvm -o - %s \
+// RUN: | FileCheck %s -check-prefixes=CHECK-FAST
+
+float res;
+int add(float a, float b, float c) {
+  // CHECK: fadd float
+  // CHECK: load float, float*
+  // CHECK: fadd float
+  // CHECK: store float
+  // CHECK-FAST: fadd fast float
+  // CHECK-FAST: load float, float*
+  // CHECK-FAST: fadd fast float
+  // CHECK: ret i32 0
+  // CHECK-EXT: ret i32 2
+  // CHECK-FAST: ret i32 -1
+  res = a + b + c;
+  return __FLT_EVAL_METHOD__;
+}
+
+int add_precise(float a, float b, float c) {
+#pragma float_control(precise, on)
+  // CHECK: fadd float
+  // CHECK: load float, float*
+  // CHECK: fadd float
+  // CHECK: store float
+  // CHECK: ret i32 0
+  // CHECK-FAST: ret i32 -1
+  res = a + b + c;
+  return __FLT_EVAL_METHOD__;
+}
+
+#pragma float_control(push)
+#pragma float_control(precise, on)
+int add_precise_1(float a, float b, float c) {
+  // CHECK: fadd float
+  // CHECK: load float, float*
+  // CHECK: fadd float
+  // CHECK: store float
+  // CHECK: ret i32 0
+  // CHECK-FAST: ret i32 -1
+  res = a + b + c;
+  return __FLT_EVAL_METHOD__;
+}
+#pragma float_control(pop)
+
+int add_not_precise(float a, float b, float c) {
+  // Fast-math is enabled with this pragma.
+#pragma float_control(precise, off)
+  // CHECK-FAST: fadd fast float
+  // CHECK-FAST: load float, float*
+  // CHECK-FAST: fadd fast float
+  // CHECK-FAST: ret i32 -1
+  res = a + b + c;
+  return __FLT_EVAL_METHOD__;
+}
+
+#pragma float_control(push)
+// Fast-math is enabled with this pragma.
+#pragma float_control(precise, off)
+int add_not_precise_1(float a, float b, float c) {
+  // CHECK-FAST: fadd fast float
+  // CHECK-FAST: load float, float*
+  // CHECK-FAST: fadd fast float
+  // CHECK-FAST: ret i32 -1
+  res = a + b + c;
+  return __FLT_EVAL_METHOD__;
+}
+#pragma float_control(pop)
+
+int getFPEvalMethod() {
+  // CHECK: ret i32 0
+  return __FLT_EVAL_METHOD__;
+}
Index: clang/lib/Sema/SemaAttr.cpp
===
--- clang/lib/Sema/SemaAttr.cpp
+++ clang/lib/Sema/SemaAttr.cpp
@@ -517,6 +517,9 @@
 else
   NewFPFeatures.setFPPreciseEnabled(false);
 FpPragmaStack.Act(Loc, Action, StringRef(), NewFPFeatures);
+// Fast-math is enabled.
+PP.setCurrentFPEvalMethod(
+Loc, LangOptions::FPEvalMethodKind::FEM_Indeterminable);
 break;
   case PFC_Except:
 if (!isPreciseFPEnabled())
@@ -540,6 +543,8 @@
 }
 FpPragmaStack.Act(Loc, Action, StringRef(), NewFPFeatures);
 NewFPFeatures = FpPragmaStack.CurrentValue;
+PP.setCurrentFPEvalMethod(SourceLocation(),
+  CurFPFeatures.getFPEvalMethod());
 break;
   }
   CurFPFeatures = NewFPFeatures.applyOverrides(getLangOpts());
Index: clang/lib/Sema/Sema.cpp
===
--- clang/lib/Sema/Sema.cpp
+++ clang/lib/Sema/Sema.cpp
@@ -254,6 +254,10 @@
 PP.setCurrentFPEvalMethod(SourceLocation(),
   getLangOpts().getFPEvalMethod());
   CurFPFeatures.setFPEvalMethod(PP.getCurrentFPEvalMethod());
+  // Fast-math is enabled.
+  if (getLangOpts().AllowFPReassoc || getLangOpts().AllowRecip)
+PP.setCurrentFPEvalMethod(SourceLocation(),
+  LangOptions::FEM_Indeterminable);
 }
 
 // Anchor Sema's type info to this TU.
Index: clang/lib/Lex/PPMacroExpansion.cpp
===
--- clang/lib/Lex/PPMacroExpansion.cpp
+++ clang/lib/Lex/PPMacroExpansion.cpp
@@ -1577,14 +1577,35 @@
 Tok.setKind(tok::string_literal);
   } else if (II == Ident__FLT_EVAL_METHOD__) {
 // __FLT_EVAL_METHOD__ is set to the default value.
-OS << getTUFPEvalMethod();
-// __FLT_EVAL_METHOD__ expands to a simple numeric value.
-Tok.setKind(tok::num

[PATCH] D121122: Set FLT_EVAL_METHOD to -1 when fast-math is enabled.

2022-03-08 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added inline comments.



Comment at: clang/lib/Lex/PPMacroExpansion.cpp:1600
+} else {
+  OS << getTUFPEvalMethod();
+  // __FLT_EVAL_METHOD__ expands to a simple numeric value.

andrew.w.kaylor wrote:
> It looks like you've got tabs in the code here.
No. I think that just means that the block of code was shifted  by a few spaces 
because it's in a condition now.



Comment at: clang/lib/Sema/SemaAttr.cpp:521
+// Fast-math is enabled.
+PP.setCurrentFPEvalMethod(
+Loc, LangOptions::FPEvalMethodKind::FEM_Indeterminable);

andrew.w.kaylor wrote:
> Why don't you need the reverse of this in the Precise and Pop cases? Also, 
> why is it necessary to call getCurrentFPEvalMethod() immediately after 
> setting it?
The call to getCurrentFPEvalMethod() was just left over debugging. Removed it.


CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D121122/new/

https://reviews.llvm.org/D121122

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D121122: Set FLT_EVAL_METHOD to -1 when fast-math is enabled.

2022-03-09 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 414216.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D121122/new/

https://reviews.llvm.org/D121122

Files:
  clang/lib/Lex/PPMacroExpansion.cpp
  clang/lib/Sema/Sema.cpp
  clang/lib/Sema/SemaAttr.cpp
  clang/test/CodeGen/eval-method-fast-math.c

Index: clang/test/CodeGen/eval-method-fast-math.c
===
--- /dev/null
+++ clang/test/CodeGen/eval-method-fast-math.c
@@ -0,0 +1,87 @@
+// RUN: %clang_cc1 -fexperimental-strict-floating-point  \
+// RUN: -triple x86_64-linux-gnu -emit-llvm -o - %s  \
+// RUN: | FileCheck %s -check-prefixes=CHECK
+
+// RUN: %clang_cc1 -triple i386--linux -emit-llvm -o - %s \
+// RUN: | FileCheck %s -check-prefixes=CHECK-EXT
+
+// RUN: %clang_cc1 -fexperimental-strict-floating-point  \
+// RUN: -mreassociate -freciprocal-math -ffp-contract=fast \
+// RUN: -ffast-math -triple x86_64-linux-gnu \
+// RUN: -emit-llvm -o - %s \
+// RUN: | FileCheck %s -check-prefixes=CHECK-FAST
+
+// RUN: %clang_cc1 -triple i386--linux -mreassociate -freciprocal-math \
+// RUN: -ffp-contract=fast -ffast-math -emit-llvm -o - %s \
+// RUN: | FileCheck %s -check-prefixes=CHECK-FAST
+
+float res;
+int add(float a, float b, float c) {
+  // CHECK: fadd float
+  // CHECK: load float, float*
+  // CHECK: fadd float
+  // CHECK: store float
+  // CHECK-FAST: fadd fast float
+  // CHECK-FAST: load float, float*
+  // CHECK-FAST: fadd fast float
+  // CHECK: ret i32 0
+  // CHECK-EXT: ret i32 2
+  // CHECK-FAST: ret i32 -1
+  res = a + b + c;
+  return __FLT_EVAL_METHOD__;
+}
+
+int add_precise(float a, float b, float c) {
+#pragma float_control(precise, on)
+  // CHECK: fadd float
+  // CHECK: load float, float*
+  // CHECK: fadd float
+  // CHECK: store float
+  // CHECK: ret i32 0
+  // CHECK-FAST: ret i32 -1
+  res = a + b + c;
+  return __FLT_EVAL_METHOD__;
+}
+
+#pragma float_control(push)
+#pragma float_control(precise, on)
+int add_precise_1(float a, float b, float c) {
+  // CHECK: fadd float
+  // CHECK: load float, float*
+  // CHECK: fadd float
+  // CHECK: store float
+  // CHECK: ret i32 0
+  // CHECK-FAST: ret i32 -1
+  res = a + b + c;
+  return __FLT_EVAL_METHOD__;
+}
+#pragma float_control(pop)
+
+int add_not_precise(float a, float b, float c) {
+  // Fast-math is enabled with this pragma.
+#pragma float_control(precise, off)
+  // CHECK-FAST: fadd fast float
+  // CHECK-FAST: load float, float*
+  // CHECK-FAST: fadd fast float
+  // CHECK-FAST: ret i32 -1
+  res = a + b + c;
+  return __FLT_EVAL_METHOD__;
+}
+
+#pragma float_control(push)
+// Fast-math is enabled with this pragma.
+#pragma float_control(precise, off)
+int add_not_precise_1(float a, float b, float c) {
+  // CHECK-FAST: fadd fast float
+  // CHECK-FAST: load float, float*
+  // CHECK-FAST: fadd fast float
+  // CHECK-FAST: ret i32 -1
+  res = a + b + c;
+  return __FLT_EVAL_METHOD__;
+}
+#pragma float_control(pop)
+
+int getFPEvalMethod() {
+  // CHECK: ret i32 0
+  return __FLT_EVAL_METHOD__;
+}
Index: clang/lib/Sema/SemaAttr.cpp
===
--- clang/lib/Sema/SemaAttr.cpp
+++ clang/lib/Sema/SemaAttr.cpp
@@ -517,6 +517,9 @@
 else
   NewFPFeatures.setFPPreciseEnabled(false);
 FpPragmaStack.Act(Loc, Action, StringRef(), NewFPFeatures);
+// Fast-math is enabled.
+PP.setCurrentFPEvalMethod(
+Loc, LangOptions::FPEvalMethodKind::FEM_Indeterminable);
 break;
   case PFC_Except:
 if (!isPreciseFPEnabled())
@@ -540,6 +543,12 @@
 }
 FpPragmaStack.Act(Loc, Action, StringRef(), NewFPFeatures);
 NewFPFeatures = FpPragmaStack.CurrentValue;
+if (CurFPFeatures.getAllowFPReassociate() ||
+CurFPFeatures.getAllowReciprocal())
+  // Since we are popping the pragma, we don't want to be passing
+  // a location here.
+  PP.setCurrentFPEvalMethod(SourceLocation(),
+CurFPFeatures.getFPEvalMethod());
 break;
   }
   CurFPFeatures = NewFPFeatures.applyOverrides(getLangOpts());
Index: clang/lib/Sema/Sema.cpp
===
--- clang/lib/Sema/Sema.cpp
+++ clang/lib/Sema/Sema.cpp
@@ -254,6 +254,10 @@
 PP.setCurrentFPEvalMethod(SourceLocation(),
   getLangOpts().getFPEvalMethod());
   CurFPFeatures.setFPEvalMethod(PP.getCurrentFPEvalMethod());
+  // Fast-math is enabled.
+  if (getLangOpts().AllowFPReassoc || getLangOpts().AllowRecip)
+PP.setCurrentFPEvalMethod(SourceLocation(),
+  LangOptions::FEM_Indeterminable);
 }
 
 // Anchor Sema's type info to this TU.
Index: clang/lib/Lex/PPMacroExpansion.cpp
===
--- clang/lib/Lex/PPMacroExpansion.cpp
+++ clang/lib/Lex/PPMacroExpansion.cpp
@@ -1577,14 +1577,35 @@
 Tok.setKind(tok::string_literal);
   } else if (II == Ident__FLT_EVAL_METHOD__) {
 // __FLT_EVAL_MET

[PATCH] D121380: Pragma `clang fp eval_method` needs to take as input a supported value.

2022-03-10 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam created this revision.
zahiraam added reviewers: aaron.ballman, andrew.w.kaylor.
Herald added a project: All.
zahiraam requested review of this revision.
Herald added a project: clang.

Diagnose when `#pragma clang fp eval_method` doesn't have a supported value. 
Currently the compiler is crashing.


Repository:
  rG LLVM Github Monorepo

https://reviews.llvm.org/D121380

Files:
  clang/include/clang/Basic/DiagnosticParseKinds.td
  clang/test/Sema/fp-eval-pragma.cpp


Index: clang/test/Sema/fp-eval-pragma.cpp
===
--- clang/test/Sema/fp-eval-pragma.cpp
+++ clang/test/Sema/fp-eval-pragma.cpp
@@ -27,6 +27,16 @@
   return 0;
 }
 
+void apply_pragma_with_wrong_value() {
+ // expected-error@+1{{unexpected argument 'value' to '#pragma clang fp 
eval_method'; expected 'source' or 'double' or 'extended'}}
+#pragma clang fp eval_method(value)
+}
+
+int foo3() {
+  apply_pragma_with_wrong_value();
+  return 0;
+}
+
 void foo() {
   auto a = __FLT_EVAL_METHOD__;
   {
Index: clang/include/clang/Basic/DiagnosticParseKinds.td
===
--- clang/include/clang/Basic/DiagnosticParseKinds.td
+++ clang/include/clang/Basic/DiagnosticParseKinds.td
@@ -1489,7 +1489,8 @@
   "%select{"
   "'fast' or 'on' or 'off'|"
   "'on' or 'off'|"
-  "'ignore', 'maytrap' or 'strict'}2">;
+  "'ignore', 'maytrap' or 'strict'|"
+  "'source' or 'double' or 'extended'}2">;
 
 def err_pragma_invalid_keyword : Error<
   "invalid argument; expected 'enable'%select{|, 'full'}0%select{|, 
'assume_safety'}1 or 'disable'">;


Index: clang/test/Sema/fp-eval-pragma.cpp
===
--- clang/test/Sema/fp-eval-pragma.cpp
+++ clang/test/Sema/fp-eval-pragma.cpp
@@ -27,6 +27,16 @@
   return 0;
 }
 
+void apply_pragma_with_wrong_value() {
+ // expected-error@+1{{unexpected argument 'value' to '#pragma clang fp eval_method'; expected 'source' or 'double' or 'extended'}}
+#pragma clang fp eval_method(value)
+}
+
+int foo3() {
+  apply_pragma_with_wrong_value();
+  return 0;
+}
+
 void foo() {
   auto a = __FLT_EVAL_METHOD__;
   {
Index: clang/include/clang/Basic/DiagnosticParseKinds.td
===
--- clang/include/clang/Basic/DiagnosticParseKinds.td
+++ clang/include/clang/Basic/DiagnosticParseKinds.td
@@ -1489,7 +1489,8 @@
   "%select{"
   "'fast' or 'on' or 'off'|"
   "'on' or 'off'|"
-  "'ignore', 'maytrap' or 'strict'}2">;
+  "'ignore', 'maytrap' or 'strict'|"
+  "'source' or 'double' or 'extended'}2">;
 
 def err_pragma_invalid_keyword : Error<
   "invalid argument; expected 'enable'%select{|, 'full'}0%select{|, 'assume_safety'}1 or 'disable'">;
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D121380: Pragma `clang fp eval_method` needs to take as input a supported value.

2022-03-10 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 414416.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D121380/new/

https://reviews.llvm.org/D121380

Files:
  clang/include/clang/Basic/DiagnosticParseKinds.td
  clang/test/Sema/fp-eval-pragma.cpp


Index: clang/test/Sema/fp-eval-pragma.cpp
===
--- clang/test/Sema/fp-eval-pragma.cpp
+++ clang/test/Sema/fp-eval-pragma.cpp
@@ -27,6 +27,16 @@
   return 0;
 }
 
+void apply_pragma_with_wrong_value() {
+ // expected-error@+1{{unexpected argument 'value' to '#pragma clang fp 
eval_method'; expected 'source' or 'double' or 'extended'}}
+#pragma clang fp eval_method(value)
+}
+
+int foo3() {
+  apply_pragma_with_wrong_value();
+  return 0;
+}
+
 void foo() {
   auto a = __FLT_EVAL_METHOD__;
   {
Index: clang/include/clang/Basic/DiagnosticParseKinds.td
===
--- clang/include/clang/Basic/DiagnosticParseKinds.td
+++ clang/include/clang/Basic/DiagnosticParseKinds.td
@@ -1489,7 +1489,8 @@
   "%select{"
   "'fast' or 'on' or 'off'|"
   "'on' or 'off'|"
-  "'ignore', 'maytrap' or 'strict'}2">;
+  "'ignore', 'maytrap' or 'strict'|"
+  "'source', 'double' or 'extended'}2">;
 
 def err_pragma_invalid_keyword : Error<
   "invalid argument; expected 'enable'%select{|, 'full'}0%select{|, 
'assume_safety'}1 or 'disable'">;


Index: clang/test/Sema/fp-eval-pragma.cpp
===
--- clang/test/Sema/fp-eval-pragma.cpp
+++ clang/test/Sema/fp-eval-pragma.cpp
@@ -27,6 +27,16 @@
   return 0;
 }
 
+void apply_pragma_with_wrong_value() {
+ // expected-error@+1{{unexpected argument 'value' to '#pragma clang fp eval_method'; expected 'source' or 'double' or 'extended'}}
+#pragma clang fp eval_method(value)
+}
+
+int foo3() {
+  apply_pragma_with_wrong_value();
+  return 0;
+}
+
 void foo() {
   auto a = __FLT_EVAL_METHOD__;
   {
Index: clang/include/clang/Basic/DiagnosticParseKinds.td
===
--- clang/include/clang/Basic/DiagnosticParseKinds.td
+++ clang/include/clang/Basic/DiagnosticParseKinds.td
@@ -1489,7 +1489,8 @@
   "%select{"
   "'fast' or 'on' or 'off'|"
   "'on' or 'off'|"
-  "'ignore', 'maytrap' or 'strict'}2">;
+  "'ignore', 'maytrap' or 'strict'|"
+  "'source', 'double' or 'extended'}2">;
 
 def err_pragma_invalid_keyword : Error<
   "invalid argument; expected 'enable'%select{|, 'full'}0%select{|, 'assume_safety'}1 or 'disable'">;
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D121380: Pragma `clang fp eval_method` needs to take as input a supported value.

2022-03-10 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 414424.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D121380/new/

https://reviews.llvm.org/D121380

Files:
  clang/include/clang/Basic/DiagnosticParseKinds.td
  clang/test/Sema/fp-eval-pragma.cpp


Index: clang/test/Sema/fp-eval-pragma.cpp
===
--- clang/test/Sema/fp-eval-pragma.cpp
+++ clang/test/Sema/fp-eval-pragma.cpp
@@ -27,6 +27,16 @@
   return 0;
 }
 
+void apply_pragma_with_wrong_value() {
+  // expected-error@+1{{unexpected argument 'value' to '#pragma clang fp 
eval_method'; expected 'source' or 'double' or 'extended'}}
+#pragma clang fp eval_method(value)
+}
+
+int foo3() {
+  apply_pragma_with_wrong_value();
+  return 0;
+}
+
 void foo() {
   auto a = __FLT_EVAL_METHOD__;
   {
Index: clang/include/clang/Basic/DiagnosticParseKinds.td
===
--- clang/include/clang/Basic/DiagnosticParseKinds.td
+++ clang/include/clang/Basic/DiagnosticParseKinds.td
@@ -1489,7 +1489,8 @@
   "%select{"
   "'fast' or 'on' or 'off'|"
   "'on' or 'off'|"
-  "'ignore', 'maytrap' or 'strict'}2">;
+  "'ignore', 'maytrap' or 'strict'|"
+  "'source', 'double' or 'extended'}2">;
 
 def err_pragma_invalid_keyword : Error<
   "invalid argument; expected 'enable'%select{|, 'full'}0%select{|, 
'assume_safety'}1 or 'disable'">;


Index: clang/test/Sema/fp-eval-pragma.cpp
===
--- clang/test/Sema/fp-eval-pragma.cpp
+++ clang/test/Sema/fp-eval-pragma.cpp
@@ -27,6 +27,16 @@
   return 0;
 }
 
+void apply_pragma_with_wrong_value() {
+  // expected-error@+1{{unexpected argument 'value' to '#pragma clang fp eval_method'; expected 'source' or 'double' or 'extended'}}
+#pragma clang fp eval_method(value)
+}
+
+int foo3() {
+  apply_pragma_with_wrong_value();
+  return 0;
+}
+
 void foo() {
   auto a = __FLT_EVAL_METHOD__;
   {
Index: clang/include/clang/Basic/DiagnosticParseKinds.td
===
--- clang/include/clang/Basic/DiagnosticParseKinds.td
+++ clang/include/clang/Basic/DiagnosticParseKinds.td
@@ -1489,7 +1489,8 @@
   "%select{"
   "'fast' or 'on' or 'off'|"
   "'on' or 'off'|"
-  "'ignore', 'maytrap' or 'strict'}2">;
+  "'ignore', 'maytrap' or 'strict'|"
+  "'source', 'double' or 'extended'}2">;
 
 def err_pragma_invalid_keyword : Error<
   "invalid argument; expected 'enable'%select{|, 'full'}0%select{|, 'assume_safety'}1 or 'disable'">;
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D121122: Set FLT_EVAL_METHOD to -1 when fast-math is enabled.

2022-03-10 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam added inline comments.



Comment at: clang/lib/Sema/Sema.cpp:258
+  // Fast-math is enabled.
+  if (getLangOpts().AllowFPReassoc || getLangOpts().AllowRecip)
+PP.setCurrentFPEvalMethod(SourceLocation(),

aaron.ballman wrote:
> Shouldn't this be looking at `getLangOpts().FastMath`?
when the -ffast-math is enabled on the command line, it triggers all these math 
driver options:

"-menable-no-infs" "-menable-no-nans" "-fapprox-func" "-menable-unsafe-fp-math" 
"-fno-signed-zeros" "-mreassociate" "-freciprocal-math" "-ffp-contract=fast"  
"-ffast-math" "-ffinite-math-only"

That's a bit restrictive. We want the eval-method set to -1 when either reassoc 
or allowrecip are enabled.




CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D121122/new/

https://reviews.llvm.org/D121122

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[PATCH] D121122: Set FLT_EVAL_METHOD to -1 when fast-math is enabled.

2022-03-10 Thread Zahira Ammarguellat via Phabricator via cfe-commits
zahiraam updated this revision to Diff 414460.
zahiraam marked an inline comment as done.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D121122/new/

https://reviews.llvm.org/D121122

Files:
  clang/lib/Lex/PPMacroExpansion.cpp
  clang/lib/Sema/Sema.cpp
  clang/lib/Sema/SemaAttr.cpp
  clang/test/CodeGen/eval-method-fast-math.c

Index: clang/test/CodeGen/eval-method-fast-math.c
===
--- /dev/null
+++ clang/test/CodeGen/eval-method-fast-math.c
@@ -0,0 +1,87 @@
+// RUN: %clang_cc1 -fexperimental-strict-floating-point  \
+// RUN: -triple x86_64-linux-gnu -emit-llvm -o - %s  \
+// RUN: | FileCheck %s -check-prefixes=CHECK
+
+// RUN: %clang_cc1 -triple i386--linux -emit-llvm -o - %s \
+// RUN: | FileCheck %s -check-prefixes=CHECK-EXT
+
+// RUN: %clang_cc1 -fexperimental-strict-floating-point  \
+// RUN: -mreassociate -freciprocal-math -ffp-contract=fast \
+// RUN: -ffast-math -triple x86_64-linux-gnu \
+// RUN: -emit-llvm -o - %s \
+// RUN: | FileCheck %s -check-prefixes=CHECK-FAST
+
+// RUN: %clang_cc1 -triple i386--linux -mreassociate -freciprocal-math \
+// RUN: -ffp-contract=fast -ffast-math -emit-llvm -o - %s \
+// RUN: | FileCheck %s -check-prefixes=CHECK-FAST
+
+float res;
+int add(float a, float b, float c) {
+  // CHECK: fadd float
+  // CHECK: load float, float*
+  // CHECK: fadd float
+  // CHECK: store float
+  // CHECK-FAST: fadd fast float
+  // CHECK-FAST: load float, float*
+  // CHECK-FAST: fadd fast float
+  // CHECK: ret i32 0
+  // CHECK-EXT: ret i32 2
+  // CHECK-FAST: ret i32 -1
+  res = a + b + c;
+  return __FLT_EVAL_METHOD__;
+}
+
+int add_precise(float a, float b, float c) {
+#pragma float_control(precise, on)
+  // CHECK: fadd float
+  // CHECK: load float, float*
+  // CHECK: fadd float
+  // CHECK: store float
+  // CHECK: ret i32 0
+  // CHECK-FAST: ret i32 -1
+  res = a + b + c;
+  return __FLT_EVAL_METHOD__;
+}
+
+#pragma float_control(push)
+#pragma float_control(precise, on)
+int add_precise_1(float a, float b, float c) {
+  // CHECK: fadd float
+  // CHECK: load float, float*
+  // CHECK: fadd float
+  // CHECK: store float
+  // CHECK: ret i32 0
+  // CHECK-FAST: ret i32 -1
+  res = a + b + c;
+  return __FLT_EVAL_METHOD__;
+}
+#pragma float_control(pop)
+
+int add_not_precise(float a, float b, float c) {
+  // Fast-math is enabled with this pragma.
+#pragma float_control(precise, off)
+  // CHECK-FAST: fadd fast float
+  // CHECK-FAST: load float, float*
+  // CHECK-FAST: fadd fast float
+  // CHECK-FAST: ret i32 -1
+  res = a + b + c;
+  return __FLT_EVAL_METHOD__;
+}
+
+#pragma float_control(push)
+// Fast-math is enabled with this pragma.
+#pragma float_control(precise, off)
+int add_not_precise_1(float a, float b, float c) {
+  // CHECK-FAST: fadd fast float
+  // CHECK-FAST: load float, float*
+  // CHECK-FAST: fadd fast float
+  // CHECK-FAST: ret i32 -1
+  res = a + b + c;
+  return __FLT_EVAL_METHOD__;
+}
+#pragma float_control(pop)
+
+int getFPEvalMethod() {
+  // CHECK: ret i32 0
+  return __FLT_EVAL_METHOD__;
+}
Index: clang/lib/Sema/SemaAttr.cpp
===
--- clang/lib/Sema/SemaAttr.cpp
+++ clang/lib/Sema/SemaAttr.cpp
@@ -517,6 +517,9 @@
 else
   NewFPFeatures.setFPPreciseEnabled(false);
 FpPragmaStack.Act(Loc, Action, StringRef(), NewFPFeatures);
+// `AllowFPReassoc` or `AllowReciprocal` option is enabled.
+PP.setCurrentFPEvalMethod(
+Loc, LangOptions::FPEvalMethodKind::FEM_Indeterminable);
 break;
   case PFC_Except:
 if (!isPreciseFPEnabled())
@@ -540,6 +543,12 @@
 }
 FpPragmaStack.Act(Loc, Action, StringRef(), NewFPFeatures);
 NewFPFeatures = FpPragmaStack.CurrentValue;
+if (CurFPFeatures.getAllowFPReassociate() ||
+CurFPFeatures.getAllowReciprocal())
+  // Since we are popping the pragma, we don't want to be passing
+  // a location here.
+  PP.setCurrentFPEvalMethod(SourceLocation(),
+CurFPFeatures.getFPEvalMethod());
 break;
   }
   CurFPFeatures = NewFPFeatures.applyOverrides(getLangOpts());
Index: clang/lib/Sema/Sema.cpp
===
--- clang/lib/Sema/Sema.cpp
+++ clang/lib/Sema/Sema.cpp
@@ -254,6 +254,12 @@
 PP.setCurrentFPEvalMethod(SourceLocation(),
   getLangOpts().getFPEvalMethod());
   CurFPFeatures.setFPEvalMethod(PP.getCurrentFPEvalMethod());
+  // When `-ffast-math` option is enabled, it triggers several driver math
+  // options to be enabled. Among these, only one the following two modes
+  // affect the eval-method:  reciprocal or reassociate.
+  if (getLangOpts().AllowFPReassoc || getLangOpts().AllowRecip)
+PP.setCurrentFPEvalMethod(SourceLocation(),
+  LangOptions::FEM_Indeterminable);
 }
 
 // Anchor Sema's type info to this TU.
Index: clang/lib/Lex/PPMacroExpansion.cpp

  1   2   3   4   5   6   >