31#include "llvm/ADT/SmallVector.h"
32#include "llvm/ADT/StringExtras.h"
62 struct CastOperation {
63 CastOperation(Sema &S, QualType destType,
ExprResult src)
64 :
Self(S), SrcExpr(src), DestType(destType),
67 Kind(CK_Dependent), IsARCUnbridgedCast(
false) {
81 !DestType->isArrayType() && !DestType.getPointerAuth()) {
82 DestType = DestType.getAtomicUnqualifiedType();
85 if (
const BuiltinType *placeholder =
87 PlaceholderKind = placeholder->getKind();
101 bool IsARCUnbridgedCast;
104 SourceLocation Locations[3];
106 OpRangeType(SourceLocation Begin, SourceLocation LParen,
107 SourceLocation RParen)
108 : Locations{Begin, LParen, RParen} {}
110 OpRangeType() =
default;
112 SourceLocation getBegin()
const {
return Locations[0]; }
114 SourceLocation getLParenLoc()
const {
return Locations[1]; }
116 SourceLocation getRParenLoc()
const {
return Locations[2]; }
118 friend const StreamingDiagnostic &
119 operator<<(
const StreamingDiagnostic &DB, OpRangeType Op) {
120 return DB << SourceRange(Op);
123 SourceRange getParenRange()
const {
124 return SourceRange(getLParenLoc(), getRParenLoc());
127 operator SourceRange()
const {
128 return SourceRange(getBegin(), getRParenLoc());
133 SourceRange DestRange;
136 void CheckConstCast();
137 void CheckReinterpretCast();
138 void CheckStaticCast();
139 void CheckDynamicCast();
140 void CheckCXXCStyleCast(
bool FunctionalCast,
bool ListInitialization);
142 void CheckCStyleCast();
143 void CheckBuiltinBitCast();
144 void CheckAddrspaceCast();
146 void updatePartOfExplicitCastFlags(
CastExpr *CE) {
150 for (;
auto *ICE = dyn_cast<ImplicitCastExpr>(CE->
getSubExpr()); CE = ICE)
151 ICE->setIsPartOfExplicitCast(
true);
159 if (IsARCUnbridgedCast) {
161 Self.Context, Self.Context.ARCUnbridgedCastTy, CK_Dependent,
163 Self.CurFPFeatureOverrides());
165 updatePartOfExplicitCastFlags(
castExpr);
175 if (PlaceholderKind != K)
return false;
181 bool isPlaceholder()
const {
182 return PlaceholderKind != 0;
185 return PlaceholderKind == K;
189 void checkAddressSpaceCast(QualType SrcType, QualType DestType);
191 void checkCastAlign() {
192 Self.CheckCastAlign(SrcExpr.get(), DestType, OpRange);
196 bool IsReinterpretCast =
false) {
197 assert(Self.getLangOpts().allowsNonTrivialObjCLifetimeQualifiers());
199 Expr *src = SrcExpr.
get();
200 if (Self.ObjC().CheckObjCConversion(
201 OpRange, DestType, src, CCK,
true,
false, BO_PtrMemD,
203 IsARCUnbridgedCast =
true;
207 void checkQualifiedDestType() {
209 if (DestType.getPointerAuth()) {
210 Self.Diag(DestRange.getBegin(), diag::err_ptrauth_qualifier_cast)
211 << DestType << DestRange;
216 void checkNonOverloadPlaceholders() {
217 if (!isPlaceholder() || isPlaceholder(BuiltinType::Overload))
220 SrcExpr = Self.CheckPlaceholderExpr(SrcExpr.get());
221 if (SrcExpr.isInvalid())
229 if (
const auto *PtrType = dyn_cast<PointerType>(FromType)) {
230 if (PtrType->getPointeeType()->hasAttr(attr::NoDeref)) {
231 if (
const auto *DestType = dyn_cast<PointerType>(ToType)) {
232 if (!DestType->getPointeeType()->hasAttr(attr::NoDeref)) {
233 S.
Diag(OpLoc, diag::warn_noderef_to_dereferenceable_pointer);
240 struct CheckNoDerefRAII {
241 CheckNoDerefRAII(CastOperation &Op) : Op(Op) {}
242 ~CheckNoDerefRAII() {
243 if (!Op.SrcExpr.isInvalid())
244 CheckNoDeref(Op.Self, Op.SrcExpr.get()->getType(), Op.ResultType,
245 Op.OpRange.getBegin());
273 bool CStyle, CastOperation::OpRangeType OpRange,
278 bool CStyle, CastOperation::OpRangeType OpRange,
282 CastOperation::OpRangeType OpRange,
284 QualType OrigDestType,
unsigned &msg,
289 CastOperation::OpRangeType OpRange,
unsigned &msg,
295 CastOperation::OpRangeType OpRange,
297 bool ListInitialization);
300 CastOperation::OpRangeType OpRange,
303 bool ListInitialization);
309 CastOperation::OpRangeType OpRange,
349 CastOperation Op(*
this, DestType, E);
351 CastOperation::OpRangeType(OpLoc,
Parens.getBegin(),
Parens.getEnd());
352 Op.DestRange = AngleBrackets;
354 Op.checkQualifiedDestType();
357 default: llvm_unreachable(
"Unknown C++ cast!");
359 case tok::kw_addrspace_cast:
360 if (!TypeDependent) {
361 Op.CheckAddrspaceCast();
366 Context, Op.ResultType, Op.ValueKind, Op.Kind, Op.SrcExpr.
get(),
367 DestTInfo, OpLoc,
Parens.getEnd(), AngleBrackets));
369 case tok::kw_const_cast:
370 if (!TypeDependent) {
377 Op.ValueKind, Op.SrcExpr.
get(), DestTInfo,
381 case tok::kw_dynamic_cast: {
384 return ExprError(
Diag(OpLoc, diag::err_openclcxx_not_supported)
388 if (!TypeDependent) {
389 Op.CheckDynamicCast();
394 Op.ValueKind, Op.Kind, Op.SrcExpr.
get(),
395 &Op.BasePath, DestTInfo,
399 case tok::kw_reinterpret_cast: {
400 if (!TypeDependent) {
401 Op.CheckReinterpretCast();
407 Op.ValueKind, Op.Kind, Op.SrcExpr.
get(),
408 nullptr, DestTInfo, OpLoc,
412 case tok::kw_static_cast: {
413 if (!TypeDependent) {
414 Op.CheckStaticCast();
421 Context, Op.ResultType, Op.ValueKind, Op.Kind, Op.SrcExpr.
get(),
423 Parens.getEnd(), AngleBrackets));
443 if (Operand->hasPlaceholderType()) {
450 CastOperation Op(*
this, TSI->
getType(), Operand);
451 Op.OpRange = CastOperation::OpRangeType(KWLoc, KWLoc, RParenLoc);
456 Op.CheckBuiltinBitCast();
463 Op.SrcExpr.
get(), TSI, KWLoc, RParenLoc);
464 return Op.complete(BCE);
470 CastOperation::OpRangeType range,
472 bool listInitialization) {
495 range.getBegin(), range, listInitialization)
498 range.getBegin(), range.getParenRange(), listInitialization)
509 default:
return false;
541 case OR_Success: llvm_unreachable(
"successful failed overload");
543 if (candidates.
empty())
544 msg = diag::err_ovl_no_conversion_in_cast;
546 msg = diag::err_ovl_no_viable_conversion_in_cast;
551 msg = diag::err_ovl_ambiguous_conversion_in_cast;
559 assert(Res ==
OR_Deleted &&
"Inconsistent overload resolution");
564 S.
PDiag(diag::err_ovl_deleted_conversion_in_cast)
565 << CT << srcType << destType << (Msg !=
nullptr)
566 << (Msg ? Msg->
getString() : StringRef())
575 S.
PDiag(msg) << CT << srcType << destType << range
577 S, howManyCandidates, src);
584 CastOperation::OpRangeType opRange,
Expr *src,
585 QualType destType,
bool listInitialization) {
586 if (msg == diag::err_bad_cxx_cast_generic &&
591 S.
Diag(opRange.getBegin(), msg) << castType
595 int DifferentPtrness = 0;
598 From = Ptr->getPointeeType();
603 To = Ptr->getPointeeType();
606 if (!DifferentPtrness) {
609 DeclFrom && DeclTo) {
610 if (!DeclFrom->isCompleteDefinition())
611 S.
Diag(DeclFrom->getLocation(), diag::note_type_incomplete) << DeclFrom;
612 if (!DeclTo->isCompleteDefinition())
613 S.
Diag(DeclTo->getLocation(), diag::note_type_incomplete) << DeclTo;
621enum CastAwayConstnessKind {
628 CACK_SimilarKind = 2,
647static CastAwayConstnessKind
649 enum {
None, Ptr, MemPtr, BlockPtr,
Array };
651 if (
T->isAnyPointerType())
return Ptr;
652 if (
T->isMemberPointerType())
return MemPtr;
653 if (
T->isBlockPointerType())
return BlockPtr;
656 if (
T->isConstantArrayType() ||
T->isIncompleteArrayType())
return Array;
661 if (
auto *AT = Context.getAsArrayType(
T))
662 return AT->getElementType();
663 return T->getPointeeType();
666 CastAwayConstnessKind Kind;
674 Kind = CastAwayConstnessKind::CACK_Similar;
675 }
else if (Context.UnwrapSimilarTypes(T1, T2)) {
676 Kind = CastAwayConstnessKind::CACK_Similar;
679 int T1Class = Classify(T1);
681 return CastAwayConstnessKind::CACK_None;
683 int T2Class = Classify(T2);
685 return CastAwayConstnessKind::CACK_None;
689 Kind = T1Class == T2Class ? CastAwayConstnessKind::CACK_SimilarKind
690 : CastAwayConstnessKind::CACK_Incoherent;
698 Context.UnwrapSimilarArrayTypes(T1, T2);
700 if (Classify(T1) !=
Array)
703 auto T2Class = Classify(T2);
707 if (T2Class !=
Array)
708 Kind = CastAwayConstnessKind::CACK_Incoherent;
709 else if (Kind != CastAwayConstnessKind::CACK_Incoherent)
710 Kind = CastAwayConstnessKind::CACK_SimilarKind;
725static CastAwayConstnessKind
727 bool CheckCVR,
bool CheckObjCLifetime,
728 QualType *TheOffendingSrcType =
nullptr,
729 QualType *TheOffendingDestType =
nullptr,
733 if (!CheckCVR && CheckObjCLifetime && !
Self.Context.getLangOpts().ObjC)
734 return CastAwayConstnessKind::CACK_None;
739 "Source type is not pointer or pointer to member.");
742 "Destination type is not pointer or pointer to member.");
745 QualType UnwrappedSrcType =
Self.Context.getCanonicalType(SrcType),
746 UnwrappedDestType =
Self.Context.getCanonicalType(DestType);
751 QualType PrevUnwrappedSrcType = UnwrappedSrcType;
752 QualType PrevUnwrappedDestType = UnwrappedDestType;
753 auto WorstKind = CastAwayConstnessKind::CACK_Similar;
754 bool AllConstSoFar =
true;
756 Self.Context, UnwrappedSrcType, UnwrappedDestType)) {
759 if (Kind > WorstKind)
764 Self.Context.getUnqualifiedArrayType(UnwrappedSrcType, SrcQuals);
765 Self.Context.getUnqualifiedArrayType(UnwrappedDestType, DestQuals);
771 UnwrappedDestType->isObjCObjectType())
780 if (SrcCvrQuals != DestCvrQuals) {
781 if (CastAwayQualifiers)
782 *CastAwayQualifiers = SrcCvrQuals - DestCvrQuals;
785 if (!DestCvrQuals.compatiblyIncludes(SrcCvrQuals,
786 Self.getASTContext())) {
787 if (TheOffendingSrcType)
788 *TheOffendingSrcType = PrevUnwrappedSrcType;
789 if (TheOffendingDestType)
790 *TheOffendingDestType = PrevUnwrappedDestType;
801 if (CheckObjCLifetime &&
807 if (AllConstSoFar && !DestQuals.
hasConst()) {
808 AllConstSoFar =
false;
809 if (TheOffendingSrcType)
810 *TheOffendingSrcType = PrevUnwrappedSrcType;
811 if (TheOffendingDestType)
812 *TheOffendingDestType = PrevUnwrappedDestType;
815 PrevUnwrappedSrcType = UnwrappedSrcType;
816 PrevUnwrappedDestType = UnwrappedDestType;
819 return CastAwayConstnessKind::CACK_None;
825 case CastAwayConstnessKind::CACK_None:
826 llvm_unreachable(
"did not cast away constness");
828 case CastAwayConstnessKind::CACK_Similar:
830 case CastAwayConstnessKind::CACK_SimilarKind:
831 DiagID = diag::err_bad_cxx_cast_qualifiers_away;
834 case CastAwayConstnessKind::CACK_Incoherent:
835 DiagID = diag::ext_bad_cxx_cast_qualifiers_away_incoherent;
839 llvm_unreachable(
"unexpected cast away constness kind");
845void CastOperation::CheckDynamicCast() {
846 CheckNoDerefRAII NoderefCheck(*
this);
849 SrcExpr =
Self.DefaultFunctionArrayLvalueConversion(SrcExpr.get());
850 else if (isPlaceholder())
851 SrcExpr =
Self.CheckPlaceholderExpr(SrcExpr.get());
852 if (SrcExpr.isInvalid())
855 QualType OrigSrcType = SrcExpr.get()->getType();
856 QualType DestType =
Self.Context.getCanonicalType(this->DestType);
869 Self.Diag(OpRange.getBegin(), diag::err_bad_dynamic_cast_not_ref_or_ptr)
870 << this->DestType << DestRange;
875 const auto *DestRecord = DestPointee->
getAsCanonical<RecordType>();
877 assert(DestPointer &&
"Reference to void is not possible");
878 }
else if (DestRecord) {
879 if (
Self.RequireCompleteType(OpRange.getBegin(), DestPointee,
880 diag::err_bad_cast_incomplete,
886 Self.Diag(OpRange.getBegin(), diag::err_bad_dynamic_cast_not_class)
896 QualType SrcType =
Self.Context.getCanonicalType(OrigSrcType);
902 Self.Diag(OpRange.getBegin(), diag::err_bad_dynamic_cast_not_ptr)
903 << OrigSrcType << this->DestType << SrcExpr.get()->getSourceRange();
907 }
else if (DestReference->isLValueReferenceType()) {
908 if (!SrcExpr.get()->isLValue()) {
909 Self.Diag(OpRange.getBegin(), diag::err_bad_cxx_cast_rvalue)
910 <<
CT_Dynamic << OrigSrcType << this->DestType << OpRange;
912 SrcPointee = SrcType;
916 if (SrcExpr.get()->isPRValue())
917 SrcExpr =
Self.CreateMaterializeTemporaryExpr(
918 SrcType, SrcExpr.get(),
false);
919 SrcPointee = SrcType;
924 if (
Self.RequireCompleteType(OpRange.getBegin(), SrcPointee,
925 diag::err_bad_cast_incomplete,
931 Self.Diag(OpRange.getBegin(), diag::err_bad_dynamic_cast_not_class)
937 assert((DestPointer || DestReference) &&
938 "Bad destination non-ptr/ref slipped through.");
939 assert((DestRecord || DestPointee->
isVoidType()) &&
940 "Bad destination pointee slipped through.");
941 assert(SrcRecord &&
"Bad source pointee slipped through.");
945 Self.Diag(OpRange.getBegin(), diag::err_bad_cxx_cast_qualifiers_away)
946 <<
CT_Dynamic << OrigSrcType << this->DestType << OpRange;
953 if (DestRecord == SrcRecord) {
961 Self.IsDerivedFrom(OpRange.getBegin(), SrcPointee, DestPointee)) {
962 if (
Self.CheckDerivedToBaseConversion(SrcPointee, DestPointee,
963 OpRange.getBegin(), OpRange,
969 Kind = CK_DerivedToBase;
975 assert(SrcDecl &&
"Definition missing");
977 Self.Diag(OpRange.getBegin(), diag::err_bad_dynamic_cast_not_polymorphic)
986 Self.Diag(OpRange.getBegin(), diag::err_no_dynamic_cast_with_fno_rtti);
994 Self.CUDA().checkRTTIUse(OpRange.getBegin(),
"dynamic_cast");
997 if (!
Self.getLangOpts().RTTIData) {
999 Self.getASTContext().getTargetInfo().getCXXABI().isMicrosoft();
1000 bool isClangCL =
Self.getDiagnostics().getDiagnosticOptions().getFormat() ==
1002 if (MicrosoftABI || !DestPointee->
isVoidType())
1003 Self.Diag(OpRange.getBegin(),
1004 diag::warn_no_dynamic_cast_with_rtti_disabled)
1011 auto *DestDecl = DestRecord->getAsCXXRecordDecl();
1012 if (DestDecl->isEffectivelyFinal())
1013 Self.MarkVTableUsed(OpRange.getBegin(), DestDecl);
1025void CastOperation::CheckConstCast() {
1026 CheckNoDerefRAII NoderefCheck(*
this);
1029 SrcExpr =
Self.DefaultFunctionArrayLvalueConversion(SrcExpr.get());
1030 else if (isPlaceholder())
1031 SrcExpr =
Self.CheckPlaceholderExpr(SrcExpr.get());
1032 if (SrcExpr.isInvalid())
1035 unsigned msg = diag::err_bad_cxx_cast_generic;
1039 << SrcExpr.get()->getType() << DestType << OpRange;
1045void CastOperation::CheckAddrspaceCast() {
1046 unsigned msg = diag::err_bad_cxx_cast_generic;
1050 Self.Diag(OpRange.getBegin(), msg)
1051 <<
CT_Addrspace << SrcExpr.get()->getType() << DestType << OpRange;
1061 CastOperation::OpRangeType OpRange) {
1088 ReinterpretKind = ReinterpretUpcast;
1090 ReinterpretKind = ReinterpretDowncast;
1095 bool NonZeroOffset =
false;
1097 E = BasePaths.
end();
1101 bool IsVirtual =
false;
1102 for (CXXBasePath::const_iterator IElem = Path.begin(), EElem = Path.end();
1103 IElem != EElem; ++IElem) {
1104 IsVirtual = IElem->Base->isVirtual();
1107 const CXXRecordDecl *BaseRD = IElem->Base->getType()->getAsCXXRecordDecl();
1108 assert(BaseRD &&
"Base type should be a valid unqualified class type");
1113 if (Class->isInvalidDecl() || !ClassDefinition ||
1114 !ClassDefinition->isCompleteDefinition())
1118 Self.Context.getASTRecordLayout(Class);
1123 if (Offset.isZero())
1127 NonZeroOffset =
true;
1132 (void) NonZeroOffset;
1134 "Should have returned if has non-virtual base with zero offset");
1137 ReinterpretKind == ReinterpretUpcast? DestType : SrcType;
1139 ReinterpretKind == ReinterpretUpcast? SrcType : DestType;
1142 Self.Diag(BeginLoc, diag::warn_reinterpret_different_from_static)
1143 << DerivedType << BaseType << !
VirtualBase <<
int(ReinterpretKind)
1145 Self.Diag(BeginLoc, diag::note_reinterpret_updowncast_use_static)
1146 <<
int(ReinterpretKind)
1158 if (Context.getTypeSizeInChars(SrcType) ==
1159 Context.getTypeSizeInChars(DestType))
1162 return Context.hasSameUnqualifiedType(SrcType, DestType);
1167 unsigned int DiagID = 0;
1168 const unsigned int DiagList[] = {diag::warn_cast_function_type_strict,
1169 diag::warn_cast_function_type};
1194 assert(SrcFTy && DstFTy);
1196 if (
Self.Context.hasSameType(SrcFTy, DstFTy))
1200 if (DiagID == diag::warn_cast_function_type_strict)
1204 if (!
T->getReturnType()->isVoidType())
1207 return !PT->isVariadic() && PT->getNumParams() == 0;
1220 if (!
T->getReturnType()->isIntegerType())
1223 return !PT->isVariadic() && PT->getNumParams() == 0;
1228 if (IsVoidVoid(SrcFTy) || IsVoidVoid(DstFTy))
1234 if (
Self.getASTContext().getTargetInfo().getTriple().isOSWindows() &&
1254 unsigned NumParams = SrcFPTy->getNumParams();
1255 unsigned DstNumParams = DstFPTy->getNumParams();
1256 if (NumParams > DstNumParams) {
1257 if (!DstFPTy->isVariadic())
1259 NumParams = DstNumParams;
1260 }
else if (NumParams < DstNumParams) {
1261 if (!SrcFPTy->isVariadic())
1265 for (
unsigned i = 0; i < NumParams; ++i)
1267 DstFPTy->getParamType(i),
Self.Context))
1278void CastOperation::CheckReinterpretCast() {
1279 if (ValueKind ==
VK_PRValue && !isPlaceholder(BuiltinType::Overload))
1280 SrcExpr =
Self.DefaultFunctionArrayLvalueConversion(SrcExpr.get());
1282 checkNonOverloadPlaceholders();
1283 if (SrcExpr.isInvalid())
1286 unsigned msg = diag::err_bad_cxx_cast_generic;
1289 false, OpRange, msg, Kind);
1291 if (SrcExpr.isInvalid())
1293 if (SrcExpr.get()->getType() ==
Self.Context.OverloadTy) {
1295 Self.Diag(OpRange.getBegin(), diag::err_bad_reinterpret_cast_overload)
1297 << DestType << OpRange;
1298 Self.NoteAllOverloadCandidates(SrcExpr.get());
1307 if (
Self.getLangOpts().allowsNonTrivialObjCLifetimeQualifiers())
1313 Self.Diag(OpRange.getBegin(), DiagID)
1314 << SrcExpr.get()->getType() << DestType << OpRange;
1324void CastOperation::CheckStaticCast() {
1325 CheckNoDerefRAII NoderefCheck(*
this);
1327 if (isPlaceholder()) {
1328 checkNonOverloadPlaceholders();
1329 if (SrcExpr.isInvalid())
1339 if (claimPlaceholder(BuiltinType::Overload)) {
1340 Self.ResolveAndFixSingleFunctionTemplateSpecialization(SrcExpr,
1343 OpRange, DestType, diag::err_bad_static_cast_overload);
1344 if (SrcExpr.isInvalid())
1348 SrcExpr =
Self.IgnoredValueConversions(SrcExpr.get());
1353 !isPlaceholder(BuiltinType::Overload)) {
1354 SrcExpr =
Self.DefaultFunctionArrayLvalueConversion(SrcExpr.get());
1355 if (SrcExpr.isInvalid())
1359 unsigned msg = diag::err_bad_cxx_cast_generic;
1362 OpRange, msg, Kind, BasePath,
false);
1364 if (SrcExpr.isInvalid())
1366 if (SrcExpr.get()->getType() ==
Self.Context.OverloadTy) {
1368 Self.Diag(OpRange.getBegin(), diag::err_bad_static_cast_overload)
1369 << oe->
getName() << DestType << OpRange
1371 Self.NoteAllOverloadCandidates(SrcExpr.get());
1379 if (Kind == CK_BitCast)
1381 if (
Self.getLangOpts().allowsNonTrivialObjCLifetimeQualifiers())
1396 DestPtrType->getPointeeType().getAddressSpace();
1404 CastOperation::OpRangeType OpRange,
1407 bool ListInitialization) {
1433 OpRange, msg, Kind, BasePath);
1441 Kind, BasePath, msg);
1448 Kind, ListInitialization);
1469 if (
const EnumType *
Enum = dyn_cast<EnumType>(SrcType)) {
1470 if (
Enum->getDecl()->isScoped()) {
1472 Kind = CK_IntegralToBoolean;
1475 Kind = CK_IntegralCast;
1478 Kind = CK_IntegralToFloating;
1493 if (
Self.RequireCompleteType(OpRange.getBegin(), DestType,
1494 diag::err_bad_cast_incomplete)) {
1504 bool DestIsFixedBoolean =
1505 ED->
isFixed() && ED->getIntegerType()->isBooleanType();
1507 Kind = DestIsFixedBoolean ? CK_IntegralToBoolean : CK_IntegralCast;
1514 Kind = DestIsFixedBoolean ? CK_FloatingToBoolean : CK_FloatingToIntegral;
1530 OpRange, msg, Kind, BasePath);
1553 if (DestPointeeQuals != SrcPointeeQuals &&
1555 Self.getASTContext())) {
1556 msg = diag::err_bad_cxx_cast_qualifiers_away;
1561 ? CK_AddressSpaceConversion
1568 if (!CStyle &&
Self.getLangOpts().MSVCCompat &&
1570 Self.Diag(OpRange.getBegin(), diag::ext_ms_cast_fn_obj) << OpRange;
1578 Kind = CK_CPointerToObjCPointerCast;
1583 Kind = CK_AnyPointerToBlockPointerCast;
1597 Self.ObjC().CheckTollFreeBridgeStaticCast(DestType, SrcExpr.
get(), Kind))
1604 if (SrcPointer->getPointeeType()->isRecordType() &&
1606 msg = diag::err_bad_cxx_cast_unrelated_class;
1609 if (
Self.CheckMatrixCast(OpRange, DestType, SrcType, Kind)) {
1616 if (SrcType ==
Self.Context.AMDGPUFeaturePredicateTy &&
1617 DestType ==
Self.Context.getLogicalOperationType()) {
1618 SrcExpr =
Self.AMDGPU().ExpandAMDGPUPredicateBuiltIn(SrcExpr.
get());
1645 QualType ToType = R->getPointeeType();
1653 SrcExpr->
getBeginLoc(), ToType, FromType, &RefConv);
1660 msg = SrcExpr->
isLValue() ? diag::err_bad_lvalue_to_rvalue_cast
1661 : diag::err_bad_rvalue_to_rvalue_cast;
1665 if (RefConv & Sema::ReferenceConversions::DerivedToBase) {
1666 Kind = CK_DerivedToBase;
1667 if (
Self.CheckDerivedToBaseConversion(FromType, ToType,
1669 &BasePath, CStyle)) {
1682 CastOperation::OpRangeType OpRange,
1695 if (!DestReference) {
1699 if (!RValueRef && !SrcExpr->
isLValue()) {
1701 msg = diag::err_bad_cxx_cast_rvalue;
1711 Self.Context.getCanonicalType(SrcExpr->
getType()),
1712 Self.Context.getCanonicalType(DestPointee), CStyle,
1713 OpRange, SrcExpr->
getType(), DestType, msg, Kind,
1720 CastOperation::OpRangeType OpRange,
1738 msg = diag::err_bad_static_cast_pointer_nonpointer;
1745 CStyle, OpRange, SrcType, DestType, msg, Kind,
1754 CastOperation::OpRangeType OpRange,
1759 if (!
Self.isCompleteType(OpRange.getBegin(), SrcType) ||
1760 !
Self.isCompleteType(OpRange.getBegin(), DestType))
1764 if (!DestType->
getAs<RecordType>() || !SrcType->
getAs<RecordType>()) {
1770 if (!
Self.IsDerivedFrom(OpRange.getBegin(), DestType, SrcType, Paths)) {
1795 msg = diag::err_bad_cxx_cast_qualifiers_away;
1807 Self.IsDerivedFrom(OpRange.getBegin(), DestType, SrcType, Paths);
1809 std::string PathDisplayStr;
1810 std::set<unsigned> DisplayedPaths;
1812 if (DisplayedPaths.insert(Path.back().SubobjectNumber).second) {
1815 PathDisplayStr +=
"\n ";
1817 PathDisplayStr += PE.Base->getType().getAsString() +
" -> ";
1822 Self.Diag(OpRange.getBegin(), diag::err_ambiguous_base_to_derived_cast)
1825 << PathDisplayStr << OpRange;
1832 Self.Diag(OpRange.getBegin(), diag::err_static_downcast_via_virtual)
1833 << OrigSrcType << OrigDestType <<
VirtualBase << OpRange;
1839 switch (
Self.CheckBaseClassAccess(OpRange.getBegin(),
1842 diag::err_downcast_from_inaccessible_base)) {
1854 Self.BuildBasePathArray(Paths, BasePath);
1855 Kind = CK_BaseToDerived;
1869 CastOperation::OpRangeType OpRange,
1876 bool WasOverloadedFunction =
false;
1880 =
Self.ResolveAddressOfOverloadedFunction(SrcExpr.
get(), DestType,
false,
1883 SrcType =
Self.Context.getMemberPointerType(
1884 Fn->getType(), std::nullopt, M->
getParent());
1885 WasOverloadedFunction =
true;
1889 switch (
Self.CheckMemberPointerConversion(
1890 SrcType, DestMemPtr, Kind, BasePath, OpRange.getBegin(), OpRange, CStyle,
1893 if (Kind == CK_NullToMemberPointer) {
1894 msg = diag::err_bad_static_cast_member_pointer_nonmp;
1908 if (WasOverloadedFunction) {
1920 SrcExpr =
Self.FixOverloadedFunctionReference(SrcExpr, FoundOverload, Fn);
1937 CastOperation::OpRangeType OpRange,
1939 bool ListInitialization) {
1941 if (
Self.RequireCompleteType(OpRange.getBegin(), DestType,
1942 diag::err_bad_cast_incomplete) ||
1943 Self.RequireNonAbstractType(OpRange.getBegin(), DestType,
1944 diag::err_allocation_of_abstract_type)) {
1957 OpRange.getBegin(), OpRange.getParenRange(), ListInitialization)
1959 Expr *SrcExprRaw = SrcExpr.
get();
1976 if (
Result.isInvalid()) {
1982 Kind = CK_ConstructorConversion;
1995 DestType =
Self.Context.getCanonicalType(DestType);
1997 bool NeedToMaterializeTemporary =
false;
2015 msg = diag::err_bad_cxx_cast_rvalue;
2023 msg = diag::err_bad_cxx_cast_rvalue;
2029 NeedToMaterializeTemporary =
true;
2038 msg = diag::err_bad_cxx_cast_bitfield;
2042 DestType =
Self.Context.getPointerType(DestTypeTmp->getPointeeType());
2043 SrcType =
Self.Context.getPointerType(SrcType);
2058 msg = diag::err_bad_const_cast_dest;
2067 msg = diag::err_bad_const_cast_dest;
2077 if (!
Self.Context.hasCvrSimilarType(SrcType, DestType))
2080 if (NeedToMaterializeTemporary)
2083 SrcExpr =
Self.CreateMaterializeTemporaryExpr(SrcExpr.
get()->
getType(),
2098 unsigned DiagID = IsDereference ?
2099 diag::warn_pointer_indirection_from_incompatible_type :
2100 diag::warn_undefined_reinterpret_cast;
2102 if (
Diags.isIgnored(DiagID, Range.getBegin()))
2106 if (IsDereference) {
2121 if (
Context.hasSameUnqualifiedType(DestTy, SrcTy)) {
2146 Diag(Range.getBegin(), DiagID) << SrcType << DestType << Range;
2152 if (
Self.Context.hasSameType(SrcType, DestType))
2155 if (SrcPtrTy->isObjCSelType()) {
2161 diag::warn_cast_pointer_from_sel)
2170 CastOperation::OpRangeType OpRange) {
2174 if (
Self.Context.hasSameType(SrcType, DstType) ||
2177 const auto *SrcFTy =
2179 const auto *DstFTy =
2189 if (
auto *UO = dyn_cast<UnaryOperator>(Src))
2190 if (UO->getOpcode() == UO_AddrOf)
2192 auto *DRE = dyn_cast<DeclRefExpr>(Src);
2195 auto *FD = dyn_cast<FunctionDecl>(DRE->getDecl());
2203 CallingConv DefaultCC =
Self.getASTContext().getDefaultCallingConvention(
2204 FD->isVariadic(), FD->isCXXInstanceMember());
2205 if (DstCC == DefaultCC || SrcCC != DefaultCC)
2211 Self.Diag(OpRange.getBegin(), diag::warn_cast_calling_conv)
2212 << SrcCCName << DstCCName << OpRange;
2217 if (
Self.Diags.isIgnored(diag::warn_cast_calling_conv, OpRange.getBegin()))
2224 SourceLocation NameLoc = FD->getFirstDecl()->getNameInfo().getLoc();
2228 llvm::raw_svector_ostream OS(CCAttrText);
2229 if (
Self.getLangOpts().MicrosoftExt) {
2231 OS <<
"__" << DstCCName;
2238 OS <<
"__attribute__((" << DstCCName <<
"))";
2239 AttrTokens.push_back(tok::kw___attribute);
2240 AttrTokens.push_back(tok::l_paren);
2241 AttrTokens.push_back(tok::l_paren);
2246 AttrTokens.push_back(tok::r_paren);
2247 AttrTokens.push_back(tok::r_paren);
2250 if (!AttrSpelling.empty())
2251 CCAttrText = AttrSpelling;
2253 Self.Diag(NameLoc, diag::note_change_calling_conv_fixit)
2269 &&
Self.Context.getTypeSize(DestType) >
2270 Self.Context.getTypeSize(SrcType)) {
2277 diag::warn_int_to_void_pointer_cast
2278 : diag::warn_int_to_pointer_cast;
2294 if (
Self.ResolveAndFixSingleFunctionTemplateSpecialization(
2305 if (!
Self.resolveAndFixAddressOfSingleOverloadCandidate(
2308 return Result.isUsable();
2313 CastOperation::OpRangeType OpRange,
2315 bool IsLValueCast =
false;
2317 DestType =
Self.Context.getCanonicalType(DestType);
2322 if (SrcType ==
Self.Context.OverloadTy) {
2327 assert(FixedExpr.
isUsable() &&
"Invalid result fixing overloaded expr");
2328 SrcExpr = FixedExpr;
2336 msg = diag::err_bad_cxx_cast_rvalue;
2341 Self.CheckCompatibleReinterpretCast(SrcType, DestType,
2349 const char *inappropriate =
nullptr;
2354 msg = diag::err_bad_cxx_cast_bitfield;
2359 inappropriate =
"matrix element";
2362 case OK_ObjCSubscript: inappropriate =
"container subscripting expression";
2365 if (inappropriate) {
2366 Self.Diag(OpRange.getBegin(), diag::err_bad_reinterpret_cast_reference)
2367 << inappropriate << DestType
2374 DestType =
Self.Context.getPointerType(DestTypeTmp->getPointeeType());
2375 SrcType =
Self.Context.getPointerType(SrcType);
2377 IsLValueCast =
true;
2381 SrcType =
Self.Context.getCanonicalType(SrcType);
2385 if (DestMemPtr && SrcMemPtr) {
2391 SrcMemPtr->isMemberFunctionPointer())
2394 if (
Self.Context.getTargetInfo().getCXXABI().isMicrosoft()) {
2397 (void)
Self.isCompleteType(OpRange.getBegin(), SrcType);
2398 (void)
Self.isCompleteType(OpRange.getBegin(), DestType);
2402 if (
Self.Context.getTypeSize(DestMemPtr) !=
2403 Self.Context.getTypeSize(SrcMemPtr)) {
2404 msg = diag::err_bad_cxx_cast_member_pointer_size;
2418 assert(!IsLValueCast);
2419 Kind = CK_ReinterpretMemberPointer;
2429 if (
Self.Context.getTypeSize(SrcType) >
2430 Self.Context.getTypeSize(DestType)) {
2431 msg = diag::err_bad_reinterpret_cast_small_int;
2434 Kind = CK_PointerToIntegral;
2442 if (srcIsVector || destIsVector) {
2444 if (
Self.isValidSveBitcast(SrcType, DestType)) {
2450 if (
Self.RISCV().isValidRVVBitcast(SrcType, DestType)) {
2464 if (
Self.areLaxCompatibleVectorTypes(SrcType, DestType)) {
2469 if (
Self.LangOpts.OpenCL && !CStyle) {
2472 if (
Self.areVectorTypesSameSize(SrcType, DestType)) {
2481 msg = diag::err_bad_cxx_cast_vector_to_scalar_different_size;
2482 else if (!srcIsVector)
2483 msg = diag::err_bad_cxx_cast_scalar_to_vector_different_size;
2485 msg = diag::err_bad_cxx_cast_vector_to_vector_different_size;
2490 if (SrcType == DestType) {
2514 if (!destIsPtr && !srcIsPtr) {
2521 assert(srcIsPtr &&
"One type must be a pointer");
2525 if ((
Self.Context.getTypeSize(SrcType) >
2526 Self.Context.getTypeSize(DestType))) {
2527 bool MicrosoftException =
2529 if (MicrosoftException) {
2531 ? diag::warn_void_pointer_to_int_cast
2532 : diag::warn_pointer_to_int_cast;
2533 Self.Diag(OpRange.getBegin(),
Diag) << SrcType << DestType << OpRange;
2535 msg = diag::err_bad_reinterpret_cast_small_int;
2539 Kind = CK_PointerToIntegral;
2544 assert(destIsPtr &&
"One type must be a pointer");
2550 Kind = CK_IntegralToPointer;
2554 if (!destIsPtr || !srcIsPtr) {
2574 Kind = CK_AddressSpaceConversion;
2581 }
else if (IsLValueCast) {
2582 Kind = CK_LValueBitCast;
2584 Kind =
Self.ObjC().PrepareCastToObjCObjectPointer(SrcExpr);
2587 Kind = CK_AnyPointerToBlockPointerCast;
2598 return SuccessResult;
2612 return SuccessResult;
2621 Self.DiagCompat(OpRange.getBegin(), diag_compat::cast_fn_obj) << OpRange;
2622 return SuccessResult;
2627 Self.DiagCompat(OpRange.getBegin(), diag_compat::cast_fn_obj) << OpRange;
2628 return SuccessResult;
2640 Self.Diag(OpRange.getBegin(),
2641 diag::warn_bad_cxx_cast_nested_pointer_addr_space)
2654 return SuccessResult;
2660 if (!
Self.getLangOpts().OpenCL && !
Self.getLangOpts().SYCLIsDevice)
2677 auto SrcPointeeType = SrcPtrType->getPointeeType();
2678 auto DestPointeeType = DestPtrType->getPointeeType();
2679 if (!DestPointeeType.isAddressSpaceOverlapping(SrcPointeeType,
2680 Self.getASTContext())) {
2681 msg = diag::err_bad_cxx_cast_addr_space_mismatch;
2684 auto SrcPointeeTypeWithoutAS =
2685 Self.Context.removeAddrSpaceQualType(SrcPointeeType.getCanonicalType());
2686 auto DestPointeeTypeWithoutAS =
2687 Self.Context.removeAddrSpaceQualType(DestPointeeType.getCanonicalType());
2688 if (
Self.Context.hasSameType(SrcPointeeTypeWithoutAS,
2689 DestPointeeTypeWithoutAS)) {
2690 Kind = SrcPointeeType.getAddressSpace() == DestPointeeType.getAddressSpace()
2692 : CK_AddressSpaceConversion;
2699void CastOperation::checkAddressSpaceCast(
QualType SrcType,
QualType DestType) {
2711 if (
Self.getLangOpts().OpenCL) {
2712 const Type *DestPtr, *SrcPtr;
2713 bool Nested =
false;
2714 unsigned DiagID = diag::err_typecheck_incompatible_address_space;
2715 DestPtr =
Self.getASTContext().getCanonicalType(DestType.
getTypePtr()),
2716 SrcPtr =
Self.getASTContext().getCanonicalType(SrcType.
getTypePtr());
2726 Self.getASTContext())) {
2727 Self.Diag(OpRange.getBegin(), DiagID)
2729 << SrcExpr.get()->getSourceRange();
2738 DiagID = diag::ext_nested_pointer_qualifier_mismatch;
2744 bool SrcCompatXL = this->
getLangOpts().getAltivecSrcCompat() ==
2758 bool SrcCompatGCC = this->
getLangOpts().getAltivecSrcCompat() ==
2760 if (this->
getLangOpts().AltiVec && SrcCompatGCC) {
2762 diag::err_invalid_conversion_between_vector_and_integer)
2763 << VecTy << SrcTy << R;
2769void CastOperation::CheckCXXCStyleCast(
bool FunctionalStyle,
2770 bool ListInitialization) {
2771 assert(
Self.getLangOpts().CPlusPlus);
2774 if (isPlaceholder()) {
2776 if (claimPlaceholder(BuiltinType::UnknownAny)) {
2777 SrcExpr =
Self.checkUnknownAnyCast(DestRange, DestType,
2778 SrcExpr.get(), Kind,
2779 ValueKind, BasePath);
2783 checkNonOverloadPlaceholders();
2784 if (SrcExpr.isInvalid())
2794 if (claimPlaceholder(BuiltinType::Overload)) {
2795 Self.ResolveAndFixSingleFunctionTemplateSpecialization(
2797 true, DestRange, DestType,
2798 diag::err_bad_cstyle_cast_overload);
2799 if (SrcExpr.isInvalid())
2803 SrcExpr =
Self.IgnoredValueConversions(SrcExpr.get());
2808 if (DestType->
isDependentType() || SrcExpr.get()->isTypeDependent() ||
2809 SrcExpr.get()->isValueDependent()) {
2810 assert(Kind == CK_Dependent);
2817 if (
Self.getLangOpts().HLSL) {
2818 if (CheckHLSLCStyleCast(CCK))
2823 !isPlaceholder(BuiltinType::Overload)) {
2824 SrcExpr =
Self.DefaultFunctionArrayLvalueConversion(SrcExpr.get());
2825 if (SrcExpr.isInvalid())
2831 if (
Self.CheckAltivecInitFromScalar(OpRange, DestType,
2832 SrcExpr.get()->getType())) {
2836 if (
Self.ShouldSplatAltivecScalarInCast(vecTy) &&
2837 (SrcExpr.get()->getType()->isIntegerType() ||
2838 SrcExpr.get()->getType()->isFloatingType())) {
2839 Kind = CK_VectorSplat;
2840 SrcExpr =
Self.prepareVectorSplat(DestType, SrcExpr.get());
2846 QualType SrcType = SrcExpr.get()->getType();
2848 Self.Diag(OpRange.getBegin(), diag::err_wasm_cast_table)
2849 << 1 << SrcExpr.get()->getSourceRange();
2866 unsigned msg = diag::err_bad_cxx_cast_generic;
2869 if (SrcExpr.isInvalid())
2877 if (SrcExpr.isInvalid())
2884 BasePath, ListInitialization);
2885 if (SrcExpr.isInvalid())
2891 OpRange, msg, Kind);
2892 if (SrcExpr.isInvalid())
2898 if (
Self.getLangOpts().allowsNonTrivialObjCLifetimeQualifiers() &&
2900 checkObjCConversion(CCK);
2903 if (SrcExpr.get()->getType() ==
Self.Context.OverloadTy) {
2914 Self.Diag(OpRange.getBegin(), diag::err_bad_cstyle_cast_overload)
2915 << OE->
getName() << DestType << OpRange
2917 Self.NoteAllOverloadCandidates(SrcExpr.get());
2921 OpRange, SrcExpr.get(), DestType, ListInitialization);
2926 if (Kind == CK_BitCast)
2930 Self.Diag(OpRange.getBegin(), DiagID)
2931 << SrcExpr.get()->getType() << DestType << OpRange;
2942 assert(
Self.getLangOpts().HLSL &&
"Must be HLSL!");
2943 QualType SrcTy = SrcExpr.get()->getType();
2947 if (
Self.HLSL().CanPerformElementwiseCast(SrcExpr.get(), DestType)) {
2949 SrcExpr =
Self.ImpCastExprToType(
2950 SrcExpr.get(),
Self.Context.getArrayParameterType(SrcTy),
2951 CK_HLSLArrayRValue,
VK_PRValue,
nullptr, CCK);
2953 SrcExpr =
Self.DefaultLvalueConversion(SrcExpr.get());
2954 Kind = CK_HLSLElementwiseCast;
2961 if (
Self.HLSL().CanPerformAggregateSplatCast(SrcExpr.get(), DestType)) {
2962 SrcExpr =
Self.DefaultLvalueConversion(SrcExpr.get());
2967 SrcExpr =
Self.ImpCastExprToType(
2969 SrcExpr.get()->getValueKind(),
nullptr, CCK);
2971 else if (MT && MT->getNumElementsFlattened() == 1)
2972 SrcExpr =
Self.ImpCastExprToType(
2973 SrcExpr.get(), MT->getElementType(), CK_HLSLMatrixTruncation,
2974 SrcExpr.get()->getValueKind(),
nullptr, CCK);
2979 SrcExpr =
Self.ImpCastExprToType(
2980 SrcExpr.get(), DVT->getElementType(),
2981 Self.PrepareScalarCast(SrcExpr, DVT->getElementType()),
2982 SrcExpr.get()->getValueKind(),
nullptr, CCK);
2987 SrcExpr =
Self.ImpCastExprToType(
2988 SrcExpr.get(), DMT->getElementType(),
2989 Self.PrepareScalarCast(SrcExpr, DMT->getElementType()),
2990 SrcExpr.get()->getValueKind(),
nullptr, CCK);
2992 Kind = CK_HLSLAggregateSplatCast;
2998 if (
Self.HLSL().CanPerformPackedTypeCast(SrcExpr.get(), DestType)) {
3000 Self.ImpCastExprToType(SrcExpr.get(), DestType, CK_IntegralCast,
3001 SrcExpr.get()->getValueKind(),
nullptr, CCK);
3002 Kind = CK_IntegralCast;
3009 Self.Diag(OpRange.getBegin(), diag::err_bad_cxx_cast_generic)
3010 << 4 << SrcTy << DestType;
3022 if (
Self.Diags.isIgnored(diag::warn_bad_function_cast,
3051 diag::warn_bad_function_cast)
3056void CastOperation::CheckCStyleCast() {
3057 assert(!
Self.getLangOpts().CPlusPlus);
3060 if (claimPlaceholder(BuiltinType::UnknownAny)) {
3061 SrcExpr =
Self.checkUnknownAnyCast(DestRange, DestType,
3062 SrcExpr.get(), Kind,
3063 ValueKind, BasePath);
3071 SrcExpr =
Self.IgnoredValueConversions(SrcExpr.get());
3072 if (SrcExpr.isInvalid())
3081 if (
Self.getASTContext().isDependenceAllowed() &&
3083 SrcExpr.get()->isValueDependent())) {
3084 assert((DestType->
containsErrors() || SrcExpr.get()->containsErrors() ||
3085 SrcExpr.get()->containsErrors()) &&
3086 "should only occur in error-recovery path.");
3087 assert(Kind == CK_Dependent);
3092 if (SrcExpr.get()->getType() ==
Self.Context.OverloadTy) {
3095 SrcExpr.get(), DestType,
true, DAP))
3096 SrcExpr =
Self.FixOverloadedFunctionReference(SrcExpr.get(), DAP, FD);
3099 assert(SrcExpr.isUsable());
3101 SrcExpr =
Self.DefaultFunctionArrayLvalueConversion(SrcExpr.get());
3102 if (SrcExpr.isInvalid())
3104 QualType SrcType = SrcExpr.get()->getType();
3107 Self.Diag(OpRange.getBegin(), diag::err_wasm_cast_table)
3108 << 1 << SrcExpr.get()->getSourceRange();
3115 checkAddressSpaceCast(SrcType, DestType);
3116 if (SrcExpr.isInvalid())
3119 if (
Self.RequireCompleteType(OpRange.getBegin(), DestType,
3120 diag::err_typecheck_cast_to_incomplete)) {
3127 Self.Context.hasSameUnqualifiedType(DestType, SrcType)) {
3134 Self.isValidSveBitcast(SrcType, DestType)) {
3141 Self.RISCV().isValidRVVBitcast(SrcType, DestType)) {
3148 if (
const RecordType *DestRecordTy =
3150 if (
Self.Context.hasSameUnqualifiedType(DestType, SrcType)) {
3152 Self.Diag(OpRange.getBegin(), diag::ext_typecheck_cast_nonscalar)
3153 << DestType << SrcExpr.get()->getSourceRange();
3162 Self.Diag(OpRange.getBegin(), diag::ext_typecheck_cast_to_union)
3163 << SrcExpr.get()->getSourceRange();
3167 Self.Diag(OpRange.getBegin(), diag::err_typecheck_cast_to_union_no_type)
3168 << SrcType << SrcExpr.get()->getSourceRange();
3175 if (
Self.getLangOpts().OpenCL && DestType->
isEventT()) {
3177 if (SrcExpr.get()->EvaluateAsInt(
Result,
Self.Context)) {
3178 llvm::APSInt CastInt =
Result.Val.getInt();
3180 Kind = CK_ZeroToOCLOpaqueType;
3183 Self.Diag(OpRange.getBegin(),
3184 diag::err_opencl_cast_non_zero_to_event_t)
3185 <<
toString(CastInt, 10) << SrcExpr.get()->getSourceRange();
3192 Self.Diag(OpRange.getBegin(), diag::err_typecheck_cond_expect_scalar)
3193 << DestType << SrcExpr.get()->getSourceRange();
3203 Self.Diag(SrcExpr.get()->getExprLoc(),
3204 diag::err_typecheck_expect_scalar_operand)
3205 << SrcType << SrcExpr.get()->getSourceRange();
3220 Self.Diag(SrcExpr.get()->getExprLoc(), diag::err_nullptr_cast)
3227 Self.Context, DestType, CK_PointerToBoolean, SrcExpr.get(),
nullptr,
3236 Self.CurFPFeatureOverrides());
3241 if (!SrcExpr.get()->isNullPointerConstant(
Self.Context,
3243 Self.Diag(SrcExpr.get()->getExprLoc(), diag::err_nullptr_cast)
3252 Self.CurFPFeatureOverrides());
3256 SrcExpr =
Self.CheckExtVectorCast(OpRange, DestType, SrcExpr.get(), Kind);
3261 if (
Self.CheckMatrixCast(OpRange, DestType, SrcType, Kind))
3267 if (
Self.CheckAltivecInitFromScalar(OpRange, DestType, SrcType)) {
3271 if (
Self.ShouldSplatAltivecScalarInCast(DestVecTy) &&
3273 Kind = CK_VectorSplat;
3274 SrcExpr =
Self.prepareVectorSplat(DestType, SrcExpr.get());
3275 }
else if (
Self.CheckVectorCast(OpRange, DestType, SrcType, Kind)) {
3282 if (
Self.CheckVectorCast(OpRange, SrcType, DestType, Kind))
3293 Self.Diag(SrcExpr.get()->getExprLoc(), diag::err_cast_selector_expr);
3302 Self.Diag(SrcExpr.get()->getExprLoc(),
3303 diag::err_cast_pointer_from_non_pointer_int)
3304 << SrcType << SrcExpr.get()->getSourceRange();
3313 Self.Diag(SrcExpr.get()->getBeginLoc(),
3314 diag::err_cast_pointer_to_non_pointer_int)
3315 << DestType << SrcExpr.get()->getSourceRange();
3320 if ((
Self.Context.getTypeSize(SrcType) >
3321 Self.Context.getTypeSize(DestType)) &&
3331 : diag::warn_void_pointer_to_int_cast;
3333 Diag = diag::warn_pointer_to_enum_cast;
3335 Diag = diag::warn_pointer_to_int_cast;
3336 Self.Diag(OpRange.getBegin(),
Diag) << SrcType << DestType << OpRange;
3340 if (
Self.getLangOpts().OpenCL && !
Self.getOpenCLOptions().isAvailableOption(
3341 "cl_khr_fp16",
Self.getLangOpts())) {
3343 Self.Diag(SrcExpr.get()->getBeginLoc(), diag::err_opencl_cast_to_half)
3344 << DestType << SrcExpr.get()->getSourceRange();
3351 if (
Self.getLangOpts().allowsNonTrivialObjCLifetimeQualifiers()) {
3353 if (SrcExpr.isInvalid())
3357 if (
Self.getLangOpts().ObjCAutoRefCount && CastPtr) {
3360 Qualifiers ExprQuals = ExprPtr->getPointeeType().getQualifiers();
3362 ExprPtr->getPointeeType()->isObjCLifetimeType() &&
3364 Self.Diag(SrcExpr.get()->getBeginLoc(),
3365 diag::err_typecheck_incompatible_ownership)
3367 << SrcExpr.get()->getSourceRange();
3371 }
else if (!
Self.ObjC().CheckObjCARCUnavailableWeakConversion(DestType,
3373 Self.Diag(SrcExpr.get()->getBeginLoc(),
3374 diag::err_arc_convesion_of_weak_unavailable)
3375 << 1 << SrcType << DestType << SrcExpr.get()->getSourceRange();
3382 Self.Diag(OpRange.getBegin(), DiagID) << SrcType << DestType << OpRange;
3391 if (SrcRD && DestRD && SrcRD->
hasAttr<RandomizeLayoutAttr>() &&
3394 Self.Diag(OpRange.getBegin(), diag::err_cast_from_randomized_struct)
3395 << SrcType << DestType;
3404 Kind =
Self.PrepareScalarCast(SrcExpr, DestType);
3405 if (SrcExpr.isInvalid())
3408 if (Kind == CK_BitCast)
3412void CastOperation::CheckBuiltinBitCast() {
3413 QualType SrcType = SrcExpr.get()->getType();
3415 if (
Self.RequireCompleteType(OpRange.getBegin(), DestType,
3416 diag::err_typecheck_cast_to_incomplete) ||
3417 Self.RequireCompleteType(OpRange.getBegin(), SrcType,
3418 diag::err_incomplete_type)) {
3423 if (SrcExpr.get()->isPRValue())
3424 SrcExpr =
Self.CreateMaterializeTemporaryExpr(SrcType, SrcExpr.get(),
3427 CharUnits DestSize =
Self.Context.getTypeSizeInChars(DestType);
3428 CharUnits SourceSize =
Self.Context.getTypeSizeInChars(SrcType);
3429 if (DestSize != SourceSize) {
3430 Self.Diag(OpRange.getBegin(), diag::err_bit_cast_type_size_mismatch)
3438 Self.Diag(OpRange.getBegin(), diag::err_bit_cast_non_trivially_copyable)
3445 Self.Diag(OpRange.getBegin(), diag::err_bit_cast_non_trivially_copyable)
3451 Kind = CK_LValueToRValueBitCast;
3466 QualType TheOffendingSrcType, TheOffendingDestType;
3469 &TheOffendingSrcType, &TheOffendingDestType,
3470 &CastAwayQualifiers) !=
3471 CastAwayConstnessKind::CACK_Similar)
3475 int qualifiers = -1;
3478 }
else if (CastAwayQualifiers.
hasConst()) {
3484 if (qualifiers == -1)
3486 << SrcType << DestType;
3489 << TheOffendingSrcType << TheOffendingDestType << qualifiers;
3501 Op.CheckCXXCStyleCast(
false,
3504 Op.CheckCStyleCast();
3513 Op.checkQualifiedDestType();
3516 Context, Op.ResultType, Op.ValueKind, Op.Kind, Op.SrcExpr.
get(),
3525 assert(LPLoc.
isValid() &&
"List-initialization shouldn't get here.");
3529 CastOperation::OpRangeType(Op.DestRange.
getBegin(), LPLoc, RPLoc);
3531 Op.CheckCXXCStyleCast(
true,
false);
3535 Op.checkQualifiedDestType();
3541 Context, Op.ResultType, Op.ValueKind, CastTypeInfo, Op.Kind,
Defines the clang::ASTContext interface.
Defines the clang::Expr interface and subclasses for C++ expressions.
Result
Implement __builtin_bit_cast and related operations.
static DiagnosticBuilder Diag(DiagnosticsEngine *Diags, const LangOptions &Features, FullSourceLoc TokLoc, const char *TokBegin, const char *TokRangeBegin, const char *TokRangeEnd, unsigned DiagID)
Produce a diagnostic highlighting some portion of a literal.
Implements a partial diagnostic that can be emitted anwyhere in a DiagnosticBuilder stream.
Defines the clang::Preprocessor interface.
static std::string toString(const clang::SanitizerSet &Sanitizers)
Produce a string containing comma-separated names of sanitizers in Sanitizers set.
This file declares semantic analysis functions specific to AMDGPU.
This file declares semantic analysis for CUDA constructs.
static TryCastResult TryStaticDowncast(Sema &Self, CanQualType SrcType, CanQualType DestType, bool CStyle, CastOperation::OpRangeType OpRange, QualType OrigSrcType, QualType OrigDestType, unsigned &msg, CastKind &Kind, CXXCastPath &BasePath)
TryStaticDowncast - Common functionality of TryStaticReferenceDowncast and TryStaticPointerDowncast.
static CastAwayConstnessKind CastsAwayConstness(Sema &Self, QualType SrcType, QualType DestType, bool CheckCVR, bool CheckObjCLifetime, QualType *TheOffendingSrcType=nullptr, QualType *TheOffendingDestType=nullptr, Qualifiers *CastAwayQualifiers=nullptr)
Check if the pointer conversion from SrcType to DestType casts away constness as defined in C++ [expr...
static TryCastResult TryStaticPointerDowncast(Sema &Self, QualType SrcType, QualType DestType, bool CStyle, CastOperation::OpRangeType OpRange, unsigned &msg, CastKind &Kind, CXXCastPath &BasePath)
Tests whether a conversion according to C++ 5.2.9p8 is valid.
static TryCastResult getCastAwayConstnessCastKind(CastAwayConstnessKind CACK, unsigned &DiagID)
static bool IsAddressSpaceConversion(QualType SrcType, QualType DestType)
@ CT_Reinterpret
reinterpret_cast
@ CT_Functional
Type(expr)
@ CT_Addrspace
addrspace_cast
static TryCastResult TryConstCast(Sema &Self, ExprResult &SrcExpr, QualType DestType, bool CStyle, unsigned &msg)
TryConstCast - See if a const_cast from source to destination is allowed, and perform it if it is.
static TryCastResult TryReinterpretCast(Sema &Self, ExprResult &SrcExpr, QualType DestType, bool CStyle, CastOperation::OpRangeType OpRange, unsigned &msg, CastKind &Kind)
static bool isValidCast(TryCastResult TCR)
static TryCastResult TryStaticReferenceDowncast(Sema &Self, Expr *SrcExpr, QualType DestType, bool CStyle, CastOperation::OpRangeType OpRange, unsigned &msg, CastKind &Kind, CXXCastPath &BasePath)
Tests whether a conversion according to C++ 5.2.9p5 is valid.
static bool argTypeIsABIEquivalent(QualType SrcType, QualType DestType, ASTContext &Context)
static unsigned int checkCastFunctionType(Sema &Self, const ExprResult &SrcExpr, QualType DestType)
static TryCastResult TryLValueToRValueCast(Sema &Self, Expr *SrcExpr, QualType DestType, bool CStyle, SourceRange OpRange, CastKind &Kind, CXXCastPath &BasePath, unsigned &msg)
Tests whether a conversion according to N2844 is valid.
@ TC_Success
The cast method is appropriate and successful.
@ TC_Extension
The cast method is appropriate and accepted as a language extension.
@ TC_Failed
The cast method is appropriate, but failed.
@ TC_NotApplicable
The cast method is not applicable.
static void DiagnoseReinterpretUpDownCast(Sema &Self, const Expr *SrcExpr, QualType DestType, CastOperation::OpRangeType OpRange)
Check that a reinterpret_cast<DestType>(SrcExpr) is not used as upcast or downcast between respective...
static void DiagnoseCastQual(Sema &Self, const ExprResult &SrcExpr, QualType DestType)
DiagnoseCastQual - Warn whenever casts discards a qualifiers, be it either const, volatile or both.
static TryCastResult TryStaticMemberPointerUpcast(Sema &Self, ExprResult &SrcExpr, QualType SrcType, QualType DestType, bool CStyle, CastOperation::OpRangeType OpRange, unsigned &msg, CastKind &Kind, CXXCastPath &BasePath)
TryStaticMemberPointerUpcast - Tests whether a conversion according to C++ 5.2.9p9 is valid:
static void DiagnoseCallingConvCast(Sema &Self, const ExprResult &SrcExpr, QualType DstType, CastOperation::OpRangeType OpRange)
Diagnose casts that change the calling convention of a pointer to a function defined in the current T...
static TryCastResult TryStaticCast(Sema &Self, ExprResult &SrcExpr, QualType DestType, CheckedConversionKind CCK, CastOperation::OpRangeType OpRange, unsigned &msg, CastKind &Kind, CXXCastPath &BasePath, bool ListInitialization)
TryStaticCast - Check if a static cast can be performed, and do so if possible.
static void DiagnoseCastOfObjCSEL(Sema &Self, const ExprResult &SrcExpr, QualType DestType)
static void DiagnoseBadFunctionCast(Sema &Self, const ExprResult &SrcExpr, QualType DestType)
DiagnoseBadFunctionCast - Warn whenever a function call is cast to a non-matching type.
static TryCastResult TryStaticImplicitCast(Sema &Self, ExprResult &SrcExpr, QualType DestType, CheckedConversionKind CCK, CastOperation::OpRangeType OpRange, unsigned &msg, CastKind &Kind, bool ListInitialization)
TryStaticImplicitCast - Tests whether a conversion according to C++ 5.2.9p2 is valid:
static bool fixOverloadedReinterpretCastExpr(Sema &Self, QualType DestType, ExprResult &Result)
static bool tryDiagnoseOverloadedCast(Sema &S, CastType CT, CastOperation::OpRangeType range, Expr *src, QualType destType, bool listInitialization)
Try to diagnose a failed overloaded cast.
static void diagnoseBadCast(Sema &S, unsigned msg, CastType castType, CastOperation::OpRangeType opRange, Expr *src, QualType destType, bool listInitialization)
Diagnose a failed cast.
static CastAwayConstnessKind unwrapCastAwayConstnessLevel(ASTContext &Context, QualType &T1, QualType &T2)
Unwrap one level of types for CastsAwayConstness.
static void checkIntToPointerCast(bool CStyle, const SourceRange &OpRange, const Expr *SrcExpr, QualType DestType, Sema &Self)
static TryCastResult TryAddressSpaceCast(Sema &Self, ExprResult &SrcExpr, QualType DestType, bool CStyle, unsigned &msg, CastKind &Kind)
This file declares semantic analysis for HLSL constructs.
This file declares semantic analysis for Objective-C.
This file declares semantic analysis functions specific to RISC-V.
static QualType getPointeeType(const MemRegion *R)
TextDiagnosticBuffer::DiagList DiagList
Holds long-lived AST nodes (such as types and decls) that can be referred to throughout the semantic ...
const LangOptions & getLangOpts() const
ASTRecordLayout - This class contains layout information for one RecordDecl, which is a struct/union/...
CharUnits getBaseClassOffset(const CXXRecordDecl *Base) const
getBaseClassOffset - Get the offset, in chars, for the given base class.
Represents a C++2a __builtin_bit_cast(T, v) expression.
static CStyleCastExpr * Create(const ASTContext &Context, QualType T, ExprValueKind VK, CastKind K, Expr *Op, const CXXCastPath *BasePath, FPOptionsOverride FPO, TypeSourceInfo *WrittenTy, SourceLocation L, SourceLocation R)
static CXXAddrspaceCastExpr * Create(const ASTContext &Context, QualType T, ExprValueKind VK, CastKind Kind, Expr *Op, TypeSourceInfo *WrittenTy, SourceLocation L, SourceLocation RParenLoc, SourceRange AngleBrackets)
Represents a path from a specific derived class (which is not represented as part of the path) to a p...
BasePaths - Represents the set of paths from a derived class to one of its (direct or indirect) bases...
const RecordType * getDetectedVirtual() const
The virtual base discovered on the path (if we are merely detecting virtuals).
bool isRecordingPaths() const
Whether we are recording paths.
void setRecordingPaths(bool RP)
Specify whether we should be recording paths or not.
void clear()
Clear the base-paths results.
std::list< CXXBasePath >::const_iterator const_paths_iterator
bool isAmbiguous(CanQualType BaseType) const
Determine whether the path from the most-derived type to the given base type is ambiguous (i....
static CXXConstCastExpr * Create(const ASTContext &Context, QualType T, ExprValueKind VK, Expr *Op, TypeSourceInfo *WrittenTy, SourceLocation L, SourceLocation RParenLoc, SourceRange AngleBrackets)
static CXXDynamicCastExpr * Create(const ASTContext &Context, QualType T, ExprValueKind VK, CastKind Kind, Expr *Op, const CXXCastPath *Path, TypeSourceInfo *Written, SourceLocation L, SourceLocation RParenLoc, SourceRange AngleBrackets)
static CXXFunctionalCastExpr * Create(const ASTContext &Context, QualType T, ExprValueKind VK, TypeSourceInfo *Written, CastKind Kind, Expr *Op, const CXXCastPath *Path, FPOptionsOverride FPO, SourceLocation LPLoc, SourceLocation RPLoc)
Represents a static or instance method of a struct/union/class.
const CXXRecordDecl * getParent() const
Return the parent of this method declaration, which is the class in which this method is defined.
Represents a C++ struct/union/class.
CXXRecordDecl * getDefinition() const
bool isDerivedFrom(const CXXRecordDecl *Base) const
Determine whether this class is derived from the class Base.
static CXXReinterpretCastExpr * Create(const ASTContext &Context, QualType T, ExprValueKind VK, CastKind Kind, Expr *Op, const CXXCastPath *Path, TypeSourceInfo *WrittenTy, SourceLocation L, SourceLocation RParenLoc, SourceRange AngleBrackets)
static CXXStaticCastExpr * Create(const ASTContext &Context, QualType T, ExprValueKind VK, CastKind K, Expr *Op, const CXXCastPath *Path, TypeSourceInfo *Written, FPOptionsOverride FPO, SourceLocation L, SourceLocation RParenLoc, SourceRange AngleBrackets)
bool isAtLeastAsQualifiedAs(CanQual< T > Other, const ASTContext &Ctx) const
Determines whether this canonical type is at least as qualified as the Other canonical type.
CanQual< T > getUnqualifiedType() const
Retrieve the unqualified form of this type.
CanProxy< U > getAs() const
Retrieve a canonical type pointer with a different static type, upcasting or downcasting as needed.
CastExpr - Base class for type casts, including both implicit casts (ImplicitCastExpr) and explicit c...
static const FieldDecl * getTargetFieldForToUnionCast(QualType unionType, QualType opType)
This is an opaque type for sizes expressed in character units.
QuantityType getQuantity() const
Get the raw integer representation of this quantity.
static CharUnits Zero()
Construct a CharUnits quantity of zero.
Represents a concrete matrix type with constant number of rows and columns.
A POD class for pairing a NamedDecl* with an access specifier.
bool isInvalidDecl() const
Information about one declarator, including the parsed type information and the identifier.
bool isInvalidType() const
bool isFixed() const
Returns true if this is an Objective-C, C++11, or Microsoft-style enumeration with a fixed underlying...
This represents one expression.
bool isIntegerConstantExpr(const ASTContext &Ctx) const
bool isTypeDependent() const
Determines whether the type of this expression depends on.
Expr * IgnoreParenImpCasts() LLVM_READONLY
Skip past any parentheses and implicit casts which might surround this expression until reaching a fi...
bool isLValue() const
isLValue - True if this expression is an "l-value" according to the rules of the current language.
@ NPC_NeverValueDependent
Specifies that the expression should never be value-dependent.
ExprObjectKind getObjectKind() const
getObjectKind - The object kind that this expression produces.
SourceLocation getExprLoc() const LLVM_READONLY
getExprLoc - Return the preferred location for the arrow when diagnosing a problem with a generic exp...
bool refersToBitField() const
Returns true if this expression is a gl-value that potentially refers to a bit-field.
static ExprValueKind getValueKindForType(QualType T)
getValueKindForType - Given a formal return or parameter type, give its value kind.
static FixItHint CreateReplacement(CharSourceRange RemoveRange, StringRef Code)
Create a code modification hint that replaces the given source range with the given code string.
static FixItHint CreateInsertion(SourceLocation InsertionLoc, StringRef Code, bool BeforePreviousInsertions=false)
Create a code modification hint that inserts the given code string at a specific location.
Represents a function declaration or definition.
Represents a prototype with parameter type info, e.g.
FunctionType - C99 6.7.5.3 - Function Declarators.
static StringRef getNameForCallConv(CallingConv CC)
CallingConv getCallConv() const
QualType getReturnType() const
One of these records is kept for each identifier that is lexed.
tok::TokenKind getTokenID() const
If this is a source-language token (e.g.
bool isKeyword(const LangOptions &LangOpts) const
Return true if this token is a keyword in the specified language.
static ImplicitCastExpr * Create(const ASTContext &Context, QualType T, CastKind Kind, Expr *Operand, const CXXCastPath *BasePath, ExprValueKind Cat, FPOptionsOverride FPO)
Describes the kind of initialization being performed, along with location information for tokens rela...
static InitializationKind CreateCast(SourceRange TypeRange)
Create a direct initialization due to a cast that isn't a C-style or functional cast.
static InitializationKind CreateFunctionalCast(SourceLocation StartLoc, SourceRange ParenRange, bool InitList)
Create a direct initialization for a functional cast.
static InitializationKind CreateCStyleCast(SourceLocation StartLoc, SourceRange TypeRange, bool InitList)
Create a direct initialization for a C-style cast.
Describes the sequence of initializations required to initialize a given object or reference with a s...
ExprResult Perform(Sema &S, const InitializedEntity &Entity, const InitializationKind &Kind, MultiExprArg Args, QualType *ResultType=nullptr)
Perform the actual initialization of the given entity based on the computed initialization sequence.
FailureKind getFailureKind() const
Determine why initialization failed.
OverloadingResult getFailedOverloadResult() const
Get the overloading result, for when the initialization sequence failed due to a bad overload.
bool Failed() const
Determine whether the initialization sequence is invalid.
@ FK_UserConversionOverloadFailed
Overloading for a user-defined conversion failed.
@ FK_ConstructorOverloadFailed
Overloading for initialization by constructor failed.
@ FK_ParenthesizedListInitFailed
Parenthesized list initialization failed at some point.
bool isConstructorInitialization() const
Determine whether this initialization is direct call to a constructor.
OverloadCandidateSet & getFailedCandidateSet()
Retrieve a reference to the candidate set when overload resolution fails.
Describes an entity that is being initialized.
static InitializedEntity InitializeTemporary(QualType Type)
Create the initialization entity for a temporary.
Represents a matrix type, as defined in the Matrix Types clang extensions.
A pointer to member type per C++ 8.3.3 - Pointers to members.
bool isMemberFunctionPointer() const
Returns true if the member type (i.e.
SourceRange getSourceRange() const LLVM_READONLY
Retrieve the source range covering the entirety of this nested-name-specifier.
OverloadCandidateSet - A set of overload candidates, used in C++ overload resolution (C++ 13....
SmallVectorImpl< OverloadCandidate >::iterator iterator
void NoteCandidates(PartialDiagnosticAt PA, Sema &S, OverloadCandidateDisplayKind OCD, ArrayRef< Expr * > Args, StringRef Opc="", SourceLocation Loc=SourceLocation(), llvm::function_ref< bool(OverloadCandidate &)> Filter=[](OverloadCandidate &) { return true;})
When overload resolution fails, prints diagnostic messages containing the candidates in the candidate...
OverloadingResult BestViableFunction(Sema &S, SourceLocation Loc, OverloadCandidateSet::iterator &Best)
Find the best viable function on this overload set, if it exists.
A reference to an overloaded function set, either an UnresolvedLookupExpr or an UnresolvedMemberExpr.
static FindResult find(Expr *E)
Finds the overloaded expression in the given expression E of OverloadTy.
NestedNameSpecifierLoc getQualifierLoc() const
Fetches the nested-name qualifier with source-location information, if one was given.
DeclarationName getName() const
Gets the name looked up.
PointerType - C99 6.7.5.1 - Pointer Declarators.
QualType getPointeeType() const
Engages in a tight little dance with the lexer to efficiently preprocess tokens.
IdentifierInfo * getIdentifierInfo(StringRef Name) const
Return information about the specified preprocessor identifier token.
StringRef getLastMacroWithSpelling(SourceLocation Loc, ArrayRef< TokenValue > Tokens) const
Return the name of the macro defined before Loc that has spelling Tokens.
A (possibly-)qualified type.
bool isTriviallyCopyableType(const ASTContext &Context) const
Return true if this is a trivially copyable type (C++0x [basic.types]p9)
QualType getNonLValueExprType(const ASTContext &Context) const
Determine the type of a (typically non-lvalue) expression with the specified result type.
bool isAddressSpaceOverlapping(QualType T, const ASTContext &Ctx) const
Returns true if address space qualifiers overlap with T address space qualifiers.
bool isNull() const
Return true if this QualType doesn't point to a type yet.
const Type * getTypePtr() const
Retrieves a pointer to the underlying (unqualified) type.
LangAS getAddressSpace() const
Return the address space of this type.
Qualifiers getQualifiers() const
Retrieve the set of qualifiers applied to this type.
QualType getNonReferenceType() const
If Type is a reference type (e.g., const int&), returns the type that the reference refers to ("const...
QualType getCanonicalType() const
QualType getUnqualifiedType() const
Retrieve the unqualified variant of the given type, removing as little sugar as possible.
QualType withCVRQualifiers(unsigned CVR) const
unsigned getCVRQualifiers() const
Retrieve the set of CVR (const-volatile-restrict) qualifiers applied to this type.
static std::string getAsString(SplitQualType split, const PrintingPolicy &Policy)
bool isAtLeastAsQualifiedAs(QualType Other, const ASTContext &Ctx) const
Determine whether this type is at least as qualified as the other given type, requiring exact equalit...
The collection of all-type qualifiers we support.
unsigned getCVRQualifiers() const
void removeObjCLifetime()
bool compatiblyIncludes(Qualifiers other, const ASTContext &Ctx) const
Determines if these qualifiers compatibly include another set.
static bool isAddressSpaceSupersetOf(LangAS A, LangAS B, const ASTContext &Ctx)
Returns true if address space A is equal to or a superset of B.
static Qualifiers fromCVRMask(unsigned CVR)
bool compatiblyIncludesObjCLifetime(Qualifiers other) const
Determines if these qualifiers compatibly include another set of qualifiers from the narrow perspecti...
An rvalue reference type, per C++11 [dcl.ref].
Represents a struct/union/class.
RecordDecl * getDefinition() const
Returns the RecordDecl that actually defines this struct/union/class.
Base for LValueReferenceType and RValueReferenceType.
QualType getPointeeType() const
PartialDiagnostic PDiag(unsigned DiagID=0)
Build a partial diagnostic.
SemaDiagnosticBuilder Diag(SourceLocation Loc, unsigned DiagID)
Emit a diagnostic.
Sema - This implements semantic analysis and AST building for C.
ReferenceCompareResult
ReferenceCompareResult - Expresses the result of comparing two types (cv1 T1 and cv2 T2) to determine...
@ Ref_Incompatible
Ref_Incompatible - The two types are incompatible, so direct reference binding is not possible.
@ Ref_Compatible
Ref_Compatible - The two types are reference-compatible.
ExprResult BuildCXXFunctionalCastExpr(TypeSourceInfo *TInfo, QualType Type, SourceLocation LParenLoc, Expr *CastExpr, SourceLocation RParenLoc)
ExprResult BuildBuiltinBitCastExpr(SourceLocation KWLoc, TypeSourceInfo *TSI, Expr *Operand, SourceLocation RParenLoc)
FPOptionsOverride CurFPFeatureOverrides()
bool ShouldSplatAltivecScalarInCast(const VectorType *VecTy)
ExprResult ActOnBuiltinBitCastExpr(SourceLocation KWLoc, Declarator &Dcl, ExprResult Operand, SourceLocation RParenLoc)
const LangOptions & getLangOpts() const
void CheckExtraCXXDefaultArguments(Declarator &D)
CheckExtraCXXDefaultArguments - Check for any extra default arguments in the declarator,...
ExprResult BuildCStyleCastExpr(SourceLocation LParenLoc, TypeSourceInfo *Ty, SourceLocation RParenLoc, Expr *Op)
ReferenceConversionsScope::ReferenceConversions ReferenceConversions
ExprResult ActOnCXXNamedCast(SourceLocation OpLoc, tok::TokenKind Kind, SourceLocation LAngleBracketLoc, Declarator &D, SourceLocation RAngleBracketLoc, SourceLocation LParenLoc, Expr *E, SourceLocation RParenLoc)
ActOnCXXNamedCast - Parse {dynamic,static,reinterpret,const,addrspace}_cast's.
ExprResult CheckPlaceholderExpr(Expr *E)
Check for operands with placeholder types and complain if found.
void DiscardMisalignedMemberAddress(const Type *T, Expr *E)
This function checks if the expression is in the sef of potentially misaligned members and it is conv...
void CheckCompatibleReinterpretCast(QualType SrcType, QualType DestType, bool IsDereference, SourceRange Range)
TypeSourceInfo * GetTypeForDeclaratorCast(Declarator &D, QualType FromTy)
DiagnosticsEngine & Diags
ExprResult BuildCXXNamedCast(SourceLocation OpLoc, tok::TokenKind Kind, TypeSourceInfo *Ty, Expr *E, SourceRange AngleBrackets, SourceRange Parens)
bool CheckAltivecInitFromScalar(SourceRange R, QualType VecTy, QualType SrcTy)
Encodes a location in the source.
bool isValid() const
Return true if this is a valid SourceLocation object.
A trivial tuple used to represent a source range.
SourceLocation getBegin() const
SourceLocation getEndLoc() const LLVM_READONLY
SourceRange getSourceRange() const LLVM_READONLY
SourceLocation tokens are not useful in isolation - they are low level value objects created/interpre...
SourceLocation getBeginLoc() const LLVM_READONLY
StringLiteral - This represents a string literal expression, e.g.
StringRef getString() const
bool isCompleteDefinition() const
Return true if this decl has its body fully specified.
Stores token information for comparing actual tokens with predefined values.
Base wrapper for a particular "section" of type source info.
SourceRange getSourceRange() const LLVM_READONLY
Get the full source range.
SourceLocation getEndLoc() const
Get the end source location.
SourceLocation getBeginLoc() const
Get the begin source location.
A container of type source information.
TypeLoc getTypeLoc() const
Return the TypeLoc wrapper for the type source info.
QualType getType() const
Return the type wrapped by this type source info.
The base class of the type hierarchy.
bool isIncompleteOrObjectType() const
Return true if this is an incomplete or object type, in other words, not a function type.
bool isBlockPointerType() const
bool isBooleanType() const
bool isFunctionReferenceType() const
bool isPlaceholderType() const
Test for a type which does not represent an actual type-system type but is instead used as a placehol...
bool isSignedIntegerType() const
Return true if this is an integer type that is signed, according to C99 6.2.5p4 [char,...
bool isComplexType() const
isComplexType() does not include complex integers (a GCC extension).
bool isRValueReferenceType() const
CXXRecordDecl * getAsCXXRecordDecl() const
Retrieves the CXXRecordDecl that this type refers to, either because the type is a RecordType or beca...
bool isConstantArrayType() const
RecordDecl * getAsRecordDecl() const
Retrieves the RecordDecl this type refers to.
bool isVoidPointerType() const
bool isFunctionPointerType() const
bool isArithmeticType() const
bool isPointerType() const
bool isIntegerType() const
isIntegerType() does not include complex integers (a GCC extension).
const T * castAs() const
Member-template castAs<specific type>.
bool isReferenceType() const
bool isEnumeralType() const
bool isScalarType() const
const CXXRecordDecl * getPointeeCXXRecordDecl() const
If this is a pointer or reference to a RecordType, return the CXXRecordDecl that the type refers to.
bool isSizelessBuiltinType() const
bool isIntegralType(const ASTContext &Ctx) const
Determine whether this type is an integral type.
QualType getPointeeType() const
If this is a pointer, ObjC object pointer, or block pointer, this returns the respective pointee.
bool isIntegralOrEnumerationType() const
Determine whether this type is an integral or enumeration type.
bool isExtVectorType() const
bool isAnyCharacterType() const
Determine whether this type is any of the built-in character types.
bool isLValueReferenceType() const
bool isDependentType() const
Whether this type is a dependent type, meaning that its definition somehow depends on a template para...
bool isFixedPointType() const
Return true if this is a fixed point type according to ISO/IEC JTC1 SC22 WG14 N1169.
const BuiltinType * getAsPlaceholderType() const
bool isWebAssemblyTableType() const
Returns true if this is a WebAssembly table type: either an array of reference types,...
bool containsErrors() const
Whether this type is an error type.
bool isMemberPointerType() const
bool isMatrixType() const
EnumDecl * castAsEnumDecl() const
bool isComplexIntegerType() const
bool isObjCObjectType() const
bool isObjCLifetimeType() const
Returns true if objects of this type have lifetime semantics under ARC.
bool isFunctionType() const
bool isObjCObjectPointerType() const
bool isMemberFunctionPointerType() const
bool isVectorType() const
bool isRealFloatingType() const
Floating point categories.
const T * getAsCanonical() const
If this type is canonically the specified type, return its canonical type cast to that specified type...
bool isFloatingType() const
bool isUnsignedIntegerType() const
Return true if this is an integer type that is unsigned, according to C99 6.2.5p6 [which returns true...
bool isAnyPointerType() const
const T * getAs() const
Member-template getAs<specific type>'.
bool isNullPtrType() const
bool isRecordType() const
bool isFunctionNoProtoType() const
Represents a GCC generic vector type.
unsigned getNumElements() const
VectorKind getVectorKind() const
QualType getElementType() const
Defines the clang::TargetInfo interface.
const internal::VariadicDynCastAllOfMatcher< Stmt, CastExpr > castExpr
Matches any cast nodes of Clang's AST.
TokenKind
Provides a simple uniform namespace for tokens from all C languages.
Top level wrappers for InstallAPI frontend operations.
CanQual< Type > CanQualType
Represents a canonical, potentially-qualified type.
bool isa(CodeGen::Address addr)
OverloadingResult
OverloadingResult - Capture the result of performing overload resolution.
@ OR_Deleted
Succeeded, but refers to a deleted function.
@ OR_Success
Overload resolution succeeded.
@ OR_Ambiguous
Ambiguous candidates found.
@ OR_No_Viable_Function
No viable function found.
OverloadCandidateDisplayKind
@ OCD_AmbiguousCandidates
Requests that only tied-for-best candidates be shown.
@ OCD_ViableCandidates
Requests that only viable candidates be shown.
@ OCD_AllCandidates
Requests that all candidates be shown.
@ OK_VectorComponent
A vector component is an element or range of elements of a vector.
@ OK_ObjCProperty
An Objective-C property is a logical field of an Objective-C object which is read and written via Obj...
@ OK_ObjCSubscript
An Objective-C array/dictionary subscripting which reads an object or writes at the subscripted array...
@ OK_Ordinary
An ordinary object is located at an address in memory.
@ OK_BitField
A bitfield object is a bitfield on a C or C++ record.
@ OK_MatrixComponent
A matrix component is a single element or range of elements of a matrix.
@ Self
'self' clause, allowed on Compute and Combined Constructs, plus 'update'.
@ Result
The result type of a method or function.
const FunctionProtoType * T
CastKind
CastKind - The kind of operation required for a conversion.
std::pair< SourceLocation, PartialDiagnostic > PartialDiagnosticAt
A partial diagnostic along with the source location where this diagnostic occurs.
ExprValueKind
The categorization of expression values, currently following the C++11 scheme.
@ VK_PRValue
A pr-value expression (in the C++11 taxonomy) produces a temporary value.
SmallVector< CXXBaseSpecifier *, 4 > CXXCastPath
A simple array of base specifiers.
const StreamingDiagnostic & operator<<(const StreamingDiagnostic &DB, const ConceptReference *C)
Insertion operator for diagnostics.
CallingConv
CallingConv - Specifies the calling convention that a function uses.
@ AltiVecBool
is AltiVec 'vector bool ...'
@ AltiVecVector
is AltiVec vector
@ AltiVecPixel
is AltiVec 'vector Pixel'
U cast(CodeGen::Address addr)
@ Enum
The "enum" keyword introduces the elaborated-type-specifier.
ActionResult< Expr * > ExprResult
@ Parens
New-expression has a C++98 paren-delimited initializer.
CheckedConversionKind
The kind of conversion being performed.
@ CStyleCast
A C-style cast.
@ OtherCast
A cast other than a C-style cast.
@ FunctionalCast
A functional-style cast.
Represents an element in a path from a derived class to a base class.
EvalResult is a struct with detailed info about an evaluated expression.
OverloadExpr * Expression