diff options
author | Faisal Vali <faisalv@yahoo.com> | 2013-09-29 17:08:32 +0000 |
---|---|---|
committer | Faisal Vali <faisalv@yahoo.com> | 2013-09-29 17:08:32 +0000 |
commit | 850da1a3a24085ed65a52197d05b271b085796a9 (patch) | |
tree | e4dcaa926099f22cab746cbc19ac35630c0da23e /clang/lib/Sema/SemaTemplateDeduction.cpp | |
parent | 6e16d54266e8f440f3cdadf814744efdac88efa8 (diff) | |
download | bcm5719-llvm-850da1a3a24085ed65a52197d05b271b085796a9.tar.gz bcm5719-llvm-850da1a3a24085ed65a52197d05b271b085796a9.zip |
Fix windows newlines :(
llvm-svn: 191641
Diffstat (limited to 'clang/lib/Sema/SemaTemplateDeduction.cpp')
-rw-r--r-- | clang/lib/Sema/SemaTemplateDeduction.cpp | 266 |
1 files changed, 133 insertions, 133 deletions
diff --git a/clang/lib/Sema/SemaTemplateDeduction.cpp b/clang/lib/Sema/SemaTemplateDeduction.cpp index 4c73fddbb53..ea06b0bb75d 100644 --- a/clang/lib/Sema/SemaTemplateDeduction.cpp +++ b/clang/lib/Sema/SemaTemplateDeduction.cpp @@ -3607,10 +3607,10 @@ Sema::DeduceTemplateArguments(FunctionTemplateDecl *FunctionTemplate, return TDK_Success; } -/// \brief Given a function declaration (e.g. a generic lambda conversion
-/// function) that contains an 'auto' in its result type, substitute it
-/// with the same Deduced type that the TypeToReplaceAutoWith was deduced
-/// with.
+/// \brief Given a function declaration (e.g. a generic lambda conversion +/// function) that contains an 'auto' in its result type, substitute it +/// with the same Deduced type that the TypeToReplaceAutoWith was deduced +/// with. static inline void ReplaceAutoWithinFunctionReturnType(FunctionDecl *F, QualType TypeToReplaceAutoWith, Sema &S) { @@ -3618,9 +3618,9 @@ ReplaceAutoWithinFunctionReturnType(FunctionDecl *F, TypeToReplaceAutoWith = TypeToReplaceAutoWith-> getContainedAutoType()->getDeducedType(); - QualType AutoResultType = F->getResultType();
- assert(AutoResultType->getContainedAutoType());
- QualType DeducedResultType = S.SubstAutoType(AutoResultType,
+ QualType AutoResultType = F->getResultType(); + assert(AutoResultType->getContainedAutoType()); + QualType DeducedResultType = S.SubstAutoType(AutoResultType, TypeToReplaceAutoWith); S.Context.adjustDeducedFunctionResultType(F, DeducedResultType); } @@ -3721,101 +3721,101 @@ Sema::DeduceTemplateArguments(FunctionTemplateDecl *ConversionTemplate, = DeduceTemplateArgumentsByTypeMatch(*this, TemplateParams, P, A, Info, Deduced, TDF)) return Result; -
- // Create an Instantiation Scope for finalizing the operator.
- LocalInstantiationScope InstScope(*this);
-
- CXXMethodDecl *LambdaCallOpSpec = 0;
+ + // Create an Instantiation Scope for finalizing the operator. + LocalInstantiationScope InstScope(*this); + + CXXMethodDecl *LambdaCallOpSpec = 0; bool GenericLambdaCallOperatorHasDeducedReturnType = false; -
- // Having successfully deduced and matched the type of the conversion
- // function against the destination type, if the destination type
- // is a ptr-to-function and the source type is a generic lambda conversion
- // to ptr-to-function, we know that the parameters of the destination
- // ptr-to-function have matched successfully against those of our
- // lambda's conversion function.
- // For instance:
- // int (*fp)(int) = [](auto a) { return a; };
- // [template<class T> operator id<auto(*)(T)>() const]
- // If it is indeed the conversion operator of a generic lambda then if
- // not already done, create the corresponding specializations of the call
- // operator and the static-invoker; and if the return type is auto,
- // deduce the return type, and then check and see if it matches the ToType.
-
- const bool IsGenericLambdaConversionOperator =
- isLambdaConversionOperator(Conv);
- if (IsGenericLambdaConversionOperator) {
- const Type *FromTypePtr = P.getTypePtr();
- const Type *ToTypePtr = A.getTypePtr();
-
- assert(P->isPointerType());
- FromTypePtr = P->getPointeeType().getTypePtr();
- assert(A->isPointerType());
- ToTypePtr = A->getPointeeType().getTypePtr();
-
- CXXRecordDecl *LambdaClass = Conv->getParent();
- assert(LambdaClass && LambdaClass->isGenericLambda());
-
- const FunctionType *ToFunType = ToTypePtr->getAs<FunctionType>();
-
- // The specialization of the Generic Lambda Call Op, instantiated
- // using the deduced parameters from the conversion function
- // i.e.
- // auto L = [](auto a) { return f(a); };
- // int (*fp)(int) = L;
- //
-
- CXXMethodDecl *CallOp = LambdaClass->getLambdaCallOperator();
- QualType CallOpResultType = CallOp->getResultType();
- GenericLambdaCallOperatorHasDeducedReturnType =
- CallOpResultType->getContainedAutoType();
- FunctionTemplateDecl *CallOpTemplate =
- CallOp->getDescribedFunctionTemplate();
-
- TemplateDeductionInfo OpInfo(Info.getLocation());
- FunctionDecl *CallOpSpec = 0;
- // Use the deduced arguments so far, to specialize our generic
- // lambda's call operator.
- if (TemplateDeductionResult Result
- = FinishTemplateArgumentDeduction(CallOpTemplate, Deduced,
- 0, CallOpSpec, OpInfo))
- return Result;
-
- bool HadToDeduceReturnTypeDuringCurrentCall = false;
- // If we need to deduce the return type, do so (instantiates the callop).
- if (GenericLambdaCallOperatorHasDeducedReturnType &&
- CallOpSpec->getResultType()->isUndeducedType()) {
- HadToDeduceReturnTypeDuringCurrentCall = true;
- DeduceReturnType(CallOpSpec, CallOpSpec->getPointOfInstantiation(),
- /*Diagnose*/ true);
- }
-
- LambdaCallOpSpec = cast<CXXMethodDecl>(CallOpSpec);
-
- // Check to see if the return type of the destination ptr-to-function
- // matches the return type of the call operator.
- if (!Context.hasSameType(LambdaCallOpSpec->getResultType(),
- ToFunType->getResultType()))
- return TDK_NonDeducedMismatch;
- // Since we have succeeded in matching the source and destination
- // ptr-to-functions (now including return type), and have successfully
- // specialized our corresponding call operator, we are ready to
- // specialize the static invoker with the deduced arguments of our
- // ptr-to-function.
- FunctionDecl *InvokerSpecialization = 0;
- FunctionTemplateDecl *InvokerTemplate = LambdaClass->
- getLambdaStaticInvoker()->getDescribedFunctionTemplate();
-
- TemplateDeductionResult Result
- = FinishTemplateArgumentDeduction(InvokerTemplate, Deduced, 0,
- InvokerSpecialization, Info);
- assert(Result == TDK_Success);
- // Set the result type to match the corresponding call operator
- // specialization's result type.
- if (GenericLambdaCallOperatorHasDeducedReturnType &&
- InvokerSpecialization->getResultType()->isUndeducedType())
- ReplaceAutoWithinFunctionReturnType(InvokerSpecialization,
- LambdaCallOpSpec->getResultType(), *this);
+ + // Having successfully deduced and matched the type of the conversion + // function against the destination type, if the destination type + // is a ptr-to-function and the source type is a generic lambda conversion + // to ptr-to-function, we know that the parameters of the destination + // ptr-to-function have matched successfully against those of our + // lambda's conversion function. + // For instance: + // int (*fp)(int) = [](auto a) { return a; }; + // [template<class T> operator id<auto(*)(T)>() const] + // If it is indeed the conversion operator of a generic lambda then if + // not already done, create the corresponding specializations of the call + // operator and the static-invoker; and if the return type is auto, + // deduce the return type, and then check and see if it matches the ToType. + + const bool IsGenericLambdaConversionOperator = + isLambdaConversionOperator(Conv); + if (IsGenericLambdaConversionOperator) { + const Type *FromTypePtr = P.getTypePtr(); + const Type *ToTypePtr = A.getTypePtr(); + + assert(P->isPointerType()); + FromTypePtr = P->getPointeeType().getTypePtr(); + assert(A->isPointerType()); + ToTypePtr = A->getPointeeType().getTypePtr(); + + CXXRecordDecl *LambdaClass = Conv->getParent(); + assert(LambdaClass && LambdaClass->isGenericLambda()); + + const FunctionType *ToFunType = ToTypePtr->getAs<FunctionType>(); + + // The specialization of the Generic Lambda Call Op, instantiated + // using the deduced parameters from the conversion function + // i.e. + // auto L = [](auto a) { return f(a); }; + // int (*fp)(int) = L; + // + + CXXMethodDecl *CallOp = LambdaClass->getLambdaCallOperator(); + QualType CallOpResultType = CallOp->getResultType(); + GenericLambdaCallOperatorHasDeducedReturnType = + CallOpResultType->getContainedAutoType(); + FunctionTemplateDecl *CallOpTemplate = + CallOp->getDescribedFunctionTemplate(); + + TemplateDeductionInfo OpInfo(Info.getLocation()); + FunctionDecl *CallOpSpec = 0; + // Use the deduced arguments so far, to specialize our generic + // lambda's call operator. + if (TemplateDeductionResult Result + = FinishTemplateArgumentDeduction(CallOpTemplate, Deduced, + 0, CallOpSpec, OpInfo)) + return Result; + + bool HadToDeduceReturnTypeDuringCurrentCall = false; + // If we need to deduce the return type, do so (instantiates the callop). + if (GenericLambdaCallOperatorHasDeducedReturnType && + CallOpSpec->getResultType()->isUndeducedType()) { + HadToDeduceReturnTypeDuringCurrentCall = true; + DeduceReturnType(CallOpSpec, CallOpSpec->getPointOfInstantiation(), + /*Diagnose*/ true); + } + + LambdaCallOpSpec = cast<CXXMethodDecl>(CallOpSpec); + + // Check to see if the return type of the destination ptr-to-function + // matches the return type of the call operator. + if (!Context.hasSameType(LambdaCallOpSpec->getResultType(), + ToFunType->getResultType())) + return TDK_NonDeducedMismatch; + // Since we have succeeded in matching the source and destination + // ptr-to-functions (now including return type), and have successfully + // specialized our corresponding call operator, we are ready to + // specialize the static invoker with the deduced arguments of our + // ptr-to-function. + FunctionDecl *InvokerSpecialization = 0; + FunctionTemplateDecl *InvokerTemplate = LambdaClass-> + getLambdaStaticInvoker()->getDescribedFunctionTemplate(); + + TemplateDeductionResult Result + = FinishTemplateArgumentDeduction(InvokerTemplate, Deduced, 0, + InvokerSpecialization, Info); + assert(Result == TDK_Success); + // Set the result type to match the corresponding call operator + // specialization's result type. + if (GenericLambdaCallOperatorHasDeducedReturnType && + InvokerSpecialization->getResultType()->isUndeducedType()) + ReplaceAutoWithinFunctionReturnType(InvokerSpecialization, + LambdaCallOpSpec->getResultType(), *this); // Ensure that static invoker doesn't have a const qualifier. // FIXME: When creating the InvokerTemplate in SemaLambda.cpp @@ -3826,41 +3826,41 @@ Sema::DeduceTemplateArguments(FunctionTemplateDecl *ConversionTemplate, FunctionProtoType::ExtProtoInfo EPI = InvokerFPT->getExtProtoInfo(); EPI.TypeQuals = 0; InvokerSpecialization->setType(Context.getFunctionType( - InvokerFPT->getResultType(), InvokerFPT->getArgTypes(),EPI));
-
- // Since the original conversion operator's parameters are the same
- // entities as the lambda's call operator's, we introduce a mapping
- // from the generic to the specialized parameters of the call operators.
- // This only needs to be done in the absence of return type deduction,
- // since deducing the return type entails instantiation which adds
- // the parameter mapping to the CurrentInstantiationScope.
- // This is necessary when transforming nested lambdas that do not
- // capture.
- // FIXME: This will be fixed once nested lambdas and capturing
- // is implemented since it does require handling parameter
- // packs correctly which might require careful calls to
- // SemaTemplateInstantiate::addInstantiatedParametersToScope.
+ InvokerFPT->getResultType(), InvokerFPT->getArgTypes(),EPI)); + + // Since the original conversion operator's parameters are the same + // entities as the lambda's call operator's, we introduce a mapping + // from the generic to the specialized parameters of the call operators. + // This only needs to be done in the absence of return type deduction, + // since deducing the return type entails instantiation which adds + // the parameter mapping to the CurrentInstantiationScope. + // This is necessary when transforming nested lambdas that do not + // capture. + // FIXME: This will be fixed once nested lambdas and capturing + // is implemented since it does require handling parameter + // packs correctly which might require careful calls to + // SemaTemplateInstantiate::addInstantiatedParametersToScope. // if (!HadToDeduceReturnTypeDuringCurrentCall) { ... } } -
-
+ + // Finish template argument deduction. - FunctionDecl *ConversionSpec = 0;
- TemplateDeductionResult Result
- = FinishTemplateArgumentDeduction(ConversionTemplate, Deduced, 0,
- ConversionSpec, Info);
- Specialization = cast_or_null<CXXConversionDecl>(ConversionSpec);
- if (Result == TDK_Success && GenericLambdaCallOperatorHasDeducedReturnType) {
- // Set the return type of the conversion specialization, since even
- // though we have ensured that the return types are compatible, if
- // there is an auto in the return type of this conversion function,
- // replace it permanently with the return type of the deduced lambda
- // so we don't try and deduce against it.
- assert(LambdaCallOpSpec);
- if (ConversionSpec->getResultType()->isUndeducedType())
- ReplaceAutoWithinFunctionReturnType(ConversionSpec,
- LambdaCallOpSpec->getResultType(),
- *this);
+ FunctionDecl *ConversionSpec = 0; + TemplateDeductionResult Result + = FinishTemplateArgumentDeduction(ConversionTemplate, Deduced, 0, + ConversionSpec, Info); + Specialization = cast_or_null<CXXConversionDecl>(ConversionSpec); + if (Result == TDK_Success && GenericLambdaCallOperatorHasDeducedReturnType) { + // Set the return type of the conversion specialization, since even + // though we have ensured that the return types are compatible, if + // there is an auto in the return type of this conversion function, + // replace it permanently with the return type of the deduced lambda + // so we don't try and deduce against it. + assert(LambdaCallOpSpec); + if (ConversionSpec->getResultType()->isUndeducedType()) + ReplaceAutoWithinFunctionReturnType(ConversionSpec, + LambdaCallOpSpec->getResultType(), + *this); } return Result; } |