diff options
Diffstat (limited to 'lib/Sema/SemaInit.h')
-rw-r--r-- | lib/Sema/SemaInit.h | 60 |
1 files changed, 50 insertions, 10 deletions
diff --git a/lib/Sema/SemaInit.h b/lib/Sema/SemaInit.h index 7c6327f..5f2592f 100644 --- a/lib/Sema/SemaInit.h +++ b/lib/Sema/SemaInit.h @@ -92,11 +92,12 @@ private: unsigned Location; /// \brief When Kind == EK_Base, the base specifier that provides the - /// base class. - CXXBaseSpecifier *Base; + /// base class. The lower bit specifies whether the base is an inherited + /// virtual base. + uintptr_t Base; - /// \brief When Kind = EK_ArrayElement or EK_VectorElement, the - /// index of the array or vector element being initialized. + /// \brief When Kind == EK_ArrayElement or EK_VectorElement, the + /// index of the array or vector element being initialized. unsigned Index; }; @@ -141,7 +142,12 @@ public: /// \brief Create the initialization entity for a parameter that is /// only known by its type. static InitializedEntity InitializeParameter(QualType Type) { - return InitializedEntity(EK_Parameter, SourceLocation(), Type); + InitializedEntity Entity; + Entity.Kind = EK_Parameter; + Entity.Type = Type; + Entity.Parent = 0; + Entity.VariableOrMember = 0; + return Entity; } /// \brief Create the initialization entity for the result of a function. @@ -168,7 +174,8 @@ public: /// \brief Create the initialization entity for a base class subobject. static InitializedEntity InitializeBase(ASTContext &Context, - CXXBaseSpecifier *Base); + CXXBaseSpecifier *Base, + bool IsInheritedVirtualBase); /// \brief Create the initialization entity for a member subobject. static InitializedEntity InitializeMember(FieldDecl *Member, @@ -204,7 +211,13 @@ public: /// \brief Retrieve the base specifier. CXXBaseSpecifier *getBaseSpecifier() const { assert(getKind() == EK_Base && "Not a base specifier"); - return Base; + return reinterpret_cast<CXXBaseSpecifier *>(Base & ~0x1); + } + + /// \brief Return whether the base is an inherited virtual base. + bool isInheritedVirtualBase() const { + assert(getKind() == EK_Base && "Not a base specifier"); + return Base & 0x1; } /// \brief Determine the location of the 'return' keyword when initializing @@ -416,6 +429,10 @@ public: SK_BindReference, /// \brief Reference binding to a temporary. SK_BindReferenceToTemporary, + /// \brief An optional copy of a temporary object to another + /// temporary object, which is permitted (but not required) by + /// C++98/03 but not C++0x. + SK_ExtraneousCopyToTemporary, /// \brief Perform a user-defined conversion, either via a conversion /// function or via a constructor. SK_UserConversion, @@ -525,7 +542,11 @@ private: /// \brief The candidate set created when initialization failed. OverloadCandidateSet FailedCandidateSet; - + + /// \brief Prints a follow-up note that highlights the location of + /// the initialized entity, if it's remote. + void PrintInitLocationNote(Sema &S, const InitializedEntity &Entity); + public: /// \brief Try to perform initialization of the given entity, creating a /// record of the steps required to perform the initialization. @@ -606,6 +627,10 @@ public: /// \brief Determine whether this initialization failed due to an ambiguity. bool isAmbiguous() const; + /// \brief Determine whether this initialization is direct call to a + /// constructor. + bool isConstructorInitialization() const; + /// \brief Add a new step in the initialization that resolves the address /// of an overloaded function to a specific function declaration. /// @@ -625,11 +650,26 @@ public: /// \brief Add a new step binding a reference to an object. /// - /// \param BindingTemporary true if we are binding a reference to a temporary + /// \param BindingTemporary True if we are binding a reference to a temporary /// object (thereby extending its lifetime); false if we are binding to an /// lvalue or an lvalue treated as an rvalue. + /// + /// \param UnnecessaryCopy True if we should check for a copy + /// constructor for a completely unnecessary but void AddReferenceBindingStep(QualType T, bool BindingTemporary); - + + /// \brief Add a new step that makes an extraneous copy of the input + /// to a temporary of the same class type. + /// + /// This extraneous copy only occurs during reference binding in + /// C++98/03, where we are permitted (but not required) to introduce + /// an extra copy. At a bare minimum, we must check that we could + /// call the copy constructor, and produce a diagnostic if the copy + /// constructor is inaccessible or no copy constructor matches. + // + /// \param T The type of the temporary being created. + void AddExtraneousCopyToTemporary(QualType T); + /// \brief Add a new step invoking a conversion function, which is either /// a constructor or a conversion function. void AddUserConversionStep(FunctionDecl *Function, |