diff options
author | Douglas Gregor <dgregor@apple.com> | 2010-04-16 22:09:46 +0000 |
---|---|---|
committer | Douglas Gregor <dgregor@apple.com> | 2010-04-16 22:09:46 +0000 |
commit | d6e44a3c4193bd422bfa78c8086fb16bb2168e34 (patch) | |
tree | cb04261ecfa3a4512613d65fd851aae18dbad935 /lib/Sema/SemaDeclCXX.cpp | |
parent | e74ef1289d5fff0a6ea573198bf354fa8cd84d51 (diff) |
Collapse the three separate initialization paths in
TryStaticImplicitCast (for references, class types, and everything
else, respectively) into a single invocation of
InitializationSequence.
One of the paths (for class types) was the only client of
Sema::TryInitializationByConstructor, which I have eliminated. This
also simplified the interface for much of the cast-checking logic,
eliminating yet more code.
I've kept the representation of C++ functional casts with <> 1
arguments the same, despite the fact that I hate it. That fix will
come soon. To satisfy my paranoia, I've bootstrapped + tested Clang
with these changes.
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@101549 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/Sema/SemaDeclCXX.cpp')
-rw-r--r-- | lib/Sema/SemaDeclCXX.cpp | 107 |
1 files changed, 0 insertions, 107 deletions
diff --git a/lib/Sema/SemaDeclCXX.cpp b/lib/Sema/SemaDeclCXX.cpp index 8318b316d8..4ce428465a 100644 --- a/lib/Sema/SemaDeclCXX.cpp +++ b/lib/Sema/SemaDeclCXX.cpp @@ -4271,113 +4271,6 @@ void Sema::AddCXXDirectInitializerToDecl(DeclPtrTy Dcl, FinalizeVarWithDestructor(VDecl, Record); } -/// \brief Add the applicable constructor candidates for an initialization -/// by constructor. -static void AddConstructorInitializationCandidates(Sema &SemaRef, - QualType ClassType, - Expr **Args, - unsigned NumArgs, - InitializationKind Kind, - OverloadCandidateSet &CandidateSet) { - // C++ [dcl.init]p14: - // If the initialization is direct-initialization, or if it is - // copy-initialization where the cv-unqualified version of the - // source type is the same class as, or a derived class of, the - // class of the destination, constructors are considered. The - // applicable constructors are enumerated (13.3.1.3), and the - // best one is chosen through overload resolution (13.3). The - // constructor so selected is called to initialize the object, - // with the initializer expression(s) as its argument(s). If no - // constructor applies, or the overload resolution is ambiguous, - // the initialization is ill-formed. - const RecordType *ClassRec = ClassType->getAs<RecordType>(); - assert(ClassRec && "Can only initialize a class type here"); - - // FIXME: When we decide not to synthesize the implicitly-declared - // constructors, we'll need to make them appear here. - - const CXXRecordDecl *ClassDecl = cast<CXXRecordDecl>(ClassRec->getDecl()); - DeclarationName ConstructorName - = SemaRef.Context.DeclarationNames.getCXXConstructorName( - SemaRef.Context.getCanonicalType(ClassType).getUnqualifiedType()); - DeclContext::lookup_const_iterator Con, ConEnd; - for (llvm::tie(Con, ConEnd) = ClassDecl->lookup(ConstructorName); - Con != ConEnd; ++Con) { - DeclAccessPair FoundDecl = DeclAccessPair::make(*Con, (*Con)->getAccess()); - - // Find the constructor (which may be a template). - CXXConstructorDecl *Constructor = 0; - FunctionTemplateDecl *ConstructorTmpl= dyn_cast<FunctionTemplateDecl>(*Con); - if (ConstructorTmpl) - Constructor - = cast<CXXConstructorDecl>(ConstructorTmpl->getTemplatedDecl()); - else - Constructor = cast<CXXConstructorDecl>(*Con); - - if ((Kind.getKind() == InitializationKind::IK_Direct) || - (Kind.getKind() == InitializationKind::IK_Value) || - (Kind.getKind() == InitializationKind::IK_Copy && - Constructor->isConvertingConstructor(/*AllowExplicit=*/false)) || - ((Kind.getKind() == InitializationKind::IK_Default) && - Constructor->isDefaultConstructor())) { - if (ConstructorTmpl) - SemaRef.AddTemplateOverloadCandidate(ConstructorTmpl, FoundDecl, - /*ExplicitArgs*/ 0, - Args, NumArgs, CandidateSet); - else - SemaRef.AddOverloadCandidate(Constructor, FoundDecl, - Args, NumArgs, CandidateSet); - } - } -} - -/// \brief Attempt to perform initialization by constructor -/// (C++ [dcl.init]p14), which may occur as part of direct-initialization or -/// copy-initialization. -/// -/// This routine determines whether initialization by constructor is possible, -/// but it does not emit any diagnostics in the case where the initialization -/// is ill-formed. -/// -/// \param ClassType the type of the object being initialized, which must have -/// class type. -/// -/// \param Args the arguments provided to initialize the object -/// -/// \param NumArgs the number of arguments provided to initialize the object -/// -/// \param Kind the type of initialization being performed -/// -/// \returns the constructor used to initialize the object, if successful. -/// Otherwise, emits a diagnostic and returns NULL. -CXXConstructorDecl * -Sema::TryInitializationByConstructor(QualType ClassType, - Expr **Args, unsigned NumArgs, - SourceLocation Loc, - InitializationKind Kind) { - // Build the overload candidate set - OverloadCandidateSet CandidateSet(Loc); - AddConstructorInitializationCandidates(*this, ClassType, Args, NumArgs, Kind, - CandidateSet); - - // Determine whether we found a constructor we can use. - OverloadCandidateSet::iterator Best; - switch (BestViableFunction(CandidateSet, Loc, Best)) { - case OR_Success: - case OR_Deleted: - // We found a constructor. Return it. - return cast<CXXConstructorDecl>(Best->Function); - - case OR_No_Viable_Function: - case OR_Ambiguous: - // Overload resolution failed. Return nothing. - return 0; - } - - // Silence GCC warning - return 0; -} - /// \brief Given a constructor and the set of arguments provided for the /// constructor, convert the arguments and add any required default arguments /// to form a proper call to this constructor. |