diff options
author | Douglas Gregor <dgregor@apple.com> | 2011-04-28 00:56:09 +0000 |
---|---|---|
committer | Douglas Gregor <dgregor@apple.com> | 2011-04-28 00:56:09 +0000 |
commit | 1d684c253f0eee3df231076f59b99ccaf8329fe4 (patch) | |
tree | 611d1c7752c22f22c2e136ff25b914661a82d6da /clang/lib | |
parent | 22e6c10256f4f496bdecbd66d7e477dcd25bf6ad (diff) | |
download | bcm5719-llvm-1d684c253f0eee3df231076f59b99ccaf8329fe4.tar.gz bcm5719-llvm-1d684c253f0eee3df231076f59b99ccaf8329fe4.zip |
More cleanup of template argument deduction and its handling of
non-CVR qualifiers. We can now properly match address-space--qualified
references during template argument deduction.
llvm-svn: 130365
Diffstat (limited to 'clang/lib')
-rw-r--r-- | clang/lib/AST/DeclCXX.cpp | 4 | ||||
-rw-r--r-- | clang/lib/Sema/SemaTemplateDeduction.cpp | 45 |
2 files changed, 43 insertions, 6 deletions
diff --git a/clang/lib/AST/DeclCXX.cpp b/clang/lib/AST/DeclCXX.cpp index 7ab60303ad3..566e2b936c9 100644 --- a/clang/lib/AST/DeclCXX.cpp +++ b/clang/lib/AST/DeclCXX.cpp @@ -270,11 +270,11 @@ GetBestOverloadCandidateSimple( unsigned Best = 0, N = Cands.size(); for (unsigned I = 1; I != N; ++I) - if (Cands[Best].second.isSupersetOf(Cands[I].second)) + if (Cands[Best].second.compatiblyIncludes(Cands[I].second)) Best = I; for (unsigned I = 1; I != N; ++I) - if (Cands[Best].second.isSupersetOf(Cands[I].second)) + if (Cands[Best].second.compatiblyIncludes(Cands[I].second)) return 0; return Cands[Best].first; diff --git a/clang/lib/Sema/SemaTemplateDeduction.cpp b/clang/lib/Sema/SemaTemplateDeduction.cpp index b395fcd33d5..73d523f8bb1 100644 --- a/clang/lib/Sema/SemaTemplateDeduction.cpp +++ b/clang/lib/Sema/SemaTemplateDeduction.cpp @@ -800,6 +800,32 @@ DeduceTemplateArguments(Sema &S, return Sema::TDK_Success; } +/// \brief Determine whether the parameter has qualifiers that are either +/// inconsistent with or a superset of the argument's qualifiers. +static bool hasInconsistentOrSupersetQualifiersOf(QualType ParamType, + QualType ArgType) { + Qualifiers ParamQs = ParamType.getQualifiers(); + Qualifiers ArgQs = ArgType.getQualifiers(); + + if (ParamQs == ArgQs) + return false; + + // Mismatched (but not missing) Objective-C GC attributes. + if (ParamQs.getObjCGCAttr() != ArgQs.getObjCGCAttr() && + ParamQs.hasObjCGCAttr()) + return true; + + // Mismatched (but not missing) address spaces. + if (ParamQs.getAddressSpace() != ArgQs.getAddressSpace() && + ParamQs.hasAddressSpace()) + return true; + + // CVR qualifier superset. + return (ParamQs.getCVRQualifiers() != ArgQs.getCVRQualifiers()) && + ((ParamQs.getCVRQualifiers() | ArgQs.getCVRQualifiers()) + == ParamQs.getCVRQualifiers()); +} + /// \brief Deduce the template arguments by comparing the parameter type and /// the argument type (C++ [temp.deduct.type]). /// @@ -960,7 +986,8 @@ DeduceTemplateArguments(Sema &S, // The argument type can not be less qualified than the parameter // type. - if (Param.isMoreQualifiedThan(Arg) && !(TDF & TDF_IgnoreQualifiers)) { + if (!(TDF & TDF_IgnoreQualifiers) && + hasInconsistentOrSupersetQualifiersOf(Param, Arg)) { Info.Param = cast<TemplateTypeParmDecl>(TemplateParams->getParam(Index)); Info.FirstArg = TemplateArgument(Param); Info.SecondArg = TemplateArgument(Arg); @@ -971,8 +998,18 @@ DeduceTemplateArguments(Sema &S, assert(Arg != S.Context.OverloadTy && "Unresolved overloaded function"); QualType DeducedType = Arg; - // local manipulation is okay because it's canonical - DeducedType.removeLocalCVRQualifiers(Param.getCVRQualifiers()); + // Remove any qualifiers on the parameter from the deduced type. + // We checked the qualifiers for consistency above. + Qualifiers DeducedQs = DeducedType.getQualifiers(); + Qualifiers ParamQs = Param.getQualifiers(); + DeducedQs.removeCVRQualifiers(ParamQs.getCVRQualifiers()); + if (ParamQs.hasObjCGCAttr()) + DeducedQs.removeObjCGCAttr(); + if (ParamQs.hasAddressSpace()) + DeducedQs.removeAddressSpace(); + DeducedType = S.Context.getQualifiedType(DeducedType.getUnqualifiedType(), + DeducedQs); + if (RecanonicalizeArg) DeducedType = S.Context.getCanonicalType(DeducedType); @@ -1005,7 +1042,7 @@ DeduceTemplateArguments(Sema &S, // Check the cv-qualifiers on the parameter and argument types. if (!(TDF & TDF_IgnoreQualifiers)) { if (TDF & TDF_ParamWithReferenceType) { - if (Param.isMoreQualifiedThan(Arg)) + if (hasInconsistentOrSupersetQualifiersOf(Param, Arg)) return Sema::TDK_NonDeducedMismatch; } else if (!IsPossiblyOpaquelyQualifiedType(Param)) { if (Param.getCVRQualifiers() != Arg.getCVRQualifiers()) |