diff --git a/clang/include/clang/Basic/DiagnosticSemaKinds.td b/clang/include/clang/Basic/DiagnosticSemaKinds.td index 7c2918d17f76..77f1b9b0d707 100644 --- a/clang/include/clang/Basic/DiagnosticSemaKinds.td +++ b/clang/include/clang/Basic/DiagnosticSemaKinds.td @@ -5896,7 +5896,7 @@ def note_deleted_special_member_class_subobject : Note< def note_deleted_default_ctor_uninit_field : Note< "%select{default constructor of|constructor inherited by}0 " "%1 is implicitly deleted because field %2 of " - "%select{reference|const-qualified}4 type %3 would not be initialized">; + "%select{reference|const-qualified|reducer}4 type %3 would not be initialized">; def note_deleted_default_ctor_all_const : Note< "%select{default constructor of|constructor inherited by}0 " "%1 is implicitly deleted because all " diff --git a/clang/lib/AST/DeclCXX.cpp b/clang/lib/AST/DeclCXX.cpp index 137c36101244..44b70b24cacb 100644 --- a/clang/lib/AST/DeclCXX.cpp +++ b/clang/lib/AST/DeclCXX.cpp @@ -1088,8 +1088,8 @@ void CXXRecordDecl::addedMember(Decl *D) { // suppress hyperobject registration. data().Aggregate = false; data().HasIrrelevantDestructor = false; - data().HasTrivialSpecialMembers &= ~SMF_Destructor; - data().HasTrivialSpecialMembersForCall &= ~SMF_Destructor; + data().HasTrivialSpecialMembers &= ~SMF_All; + data().HasTrivialSpecialMembersForCall &= ~SMF_All; } if (!Field->hasInClassInitializer() && !Field->isMutable()) { diff --git a/clang/lib/Sema/SemaDeclCXX.cpp b/clang/lib/Sema/SemaDeclCXX.cpp index e8cf41007cc4..a655248511ec 100644 --- a/clang/lib/Sema/SemaDeclCXX.cpp +++ b/clang/lib/Sema/SemaDeclCXX.cpp @@ -9595,6 +9595,12 @@ bool SpecialMemberDeletionInfo::shouldDeleteForField(FieldDecl *FD) { << !!ICI << MD->getParent() << FD << FieldType << /*Reference*/0; return true; } + if (FieldType->isHyperobjectType() && !FD->hasInClassInitializer()) { + if (Diagnose) + S.Diag(FD->getLocation(), diag::note_deleted_default_ctor_uninit_field) + << !!ICI << MD->getParent() << FD << FieldType << /*Reducer*/2; + return true; + } // C++11 [class.ctor]p5 (modified by DR2394): any non-variant non-static // data member of const-qualified type (or array thereof) with no // brace-or-equal-initializer is not const-default-constructible. diff --git a/clang/test/Cilk/hyper-errors.cpp b/clang/test/Cilk/hyper-errors.cpp index 664df5983143..e5a45d155d18 100644 --- a/clang/test/Cilk/hyper-errors.cpp +++ b/clang/test/Cilk/hyper-errors.cpp @@ -1,5 +1,5 @@ // RUN: %clang_cc1 %s -x c++ -fopencilk -verify -fsyntax-only -struct C { int _Hyperobject c; }; +struct C { int _Hyperobject c = 0; }; struct C _Hyperobject c; // expected-error{{type 'struct C', which contains a hyperobject, may not be a hyperobject}} long _Hyperobject d; // expected-note{{previous definition}} void f() { diff --git a/clang/test/Cilk/hyper-init-error.cpp b/clang/test/Cilk/hyper-init-error.cpp index 38c608c85bf5..bc54fb0fa29d 100644 --- a/clang/test/Cilk/hyper-init-error.cpp +++ b/clang/test/Cilk/hyper-init-error.cpp @@ -1,14 +1,22 @@ // RUN: %clang_cc1 %s -fopencilk -verify -fsyntax-only extern void id(void *), reduce(void *, void *); -struct one_hyperobject { +struct uninit_hyperobject { // expected-note@-1{{implicit copy}} // expected-note@-2{{implicit move}} // expected-note@-3{{implicit default}} int _Hyperobject(id, reduce) field; + // expected-note@-1{{would not be initialized}} }; // braced initializer lists do not work -one_hyperobject h1 = {-1}; +uninit_hyperobject h1 = {-1}; // expected-error@-1{{no matching constructor for initialization}} -one_hyperobject h2; +uninit_hyperobject h2; +// expected-error@-1{{implicitly-deleted default constructor}} + +struct init_hyperobject { + int _Hyperobject(id, reduce) field = 0; +}; + +init_hyperobject h3; diff --git a/clang/test/Cilk/hyper-register.cpp b/clang/test/Cilk/hyper-register.cpp index cedddc1e6843..a39e6050b08c 100644 --- a/clang/test/Cilk/hyper-register.cpp +++ b/clang/test/Cilk/hyper-register.cpp @@ -3,7 +3,7 @@ struct S { static void identity(void *); static void reduce(void *, void *); - int _Hyperobject(identity, reduce) member; + int _Hyperobject(identity, reduce) member = 0; S(); ~S(); }; diff --git a/clang/test/Cilk/hyper-template-errors.cpp b/clang/test/Cilk/hyper-template-errors.cpp index 300dc90acf6e..b456d8f8434a 100644 --- a/clang/test/Cilk/hyper-template-errors.cpp +++ b/clang/test/Cilk/hyper-template-errors.cpp @@ -7,7 +7,8 @@ struct reducer // expected-error@-1{{type 'long _Hyperobject', which contains a hyperobject, may not be a hyperobject}} // expected-error@-2{{type 'reducer', which contains a hyperobject, may not be a hyperobject}} // expected-error@-3{{type 'wrap', which contains a hyperobject, may not be a hyperobject}} - int _Hyperobject value2; + int _Hyperobject value2 = 0; + reducer(); }; reducer r_hl; // expected-note{{in instantiation}}