27 #include "llvm/ADT/DenseMap.h" 28 #include "llvm/ADT/DenseSet.h" 30 using namespace clang;
60 assert(resultClass &&
"unexpected object type!");
65 if (receiverTypeIfCall.
isNull() &&
75 if (receiverTypeIfCall.
isNull())
82 if (!receiverClass)
return false;
85 assert(receiverClass &&
"method not associated with a class!");
101 UnavailableAttr::IR_ARCInitReturnsUnrelated, loc));
106 Diag(loc, diag::err_arc_init_method_unrelated_result_type);
115 if (OldD->
hasAttr<NoEscapeAttr>() && !NewD->
hasAttr<NoEscapeAttr>()) {
116 S.
Diag(NewD->
getLocation(), diag::warn_overriding_method_missing_noescape);
152 CurrentClass = Cat->getClassInterface();
153 else if (
ObjCImplDecl *Impl = dyn_cast<ObjCImplDecl>(DC))
154 CurrentClass = Impl->getClassInterface();
156 = dyn_cast<ObjCCategoryImplDecl>(DC))
157 CurrentClass = CatImpl->getClassInterface();
162 diag::warn_related_result_type_compatibility_class)
168 diag::warn_related_result_type_compatibility_protocol)
175 diag::note_related_result_type_family)
180 diag::note_related_result_type_overridden);
183 if ((NewMethod->
hasAttr<NSReturnsRetainedAttr>() !=
184 Overridden->
hasAttr<NSReturnsRetainedAttr>())) {
187 ? diag::err_nsreturns_retained_attribute_mismatch
188 : diag::warn_nsreturns_retained_attribute_mismatch)
192 if ((NewMethod->
hasAttr<NSReturnsNotRetainedAttr>() !=
193 Overridden->
hasAttr<NSReturnsNotRetainedAttr>())) {
196 ? diag::err_nsreturns_retained_attribute_mismatch
197 : diag::warn_nsreturns_retained_attribute_mismatch)
206 ni != ne && oi != oe; ++ni, ++oi) {
209 if (newDecl->
hasAttr<NSConsumedAttr>() !=
210 oldDecl->
hasAttr<NSConsumedAttr>()) {
213 ? diag::err_nsconsumed_attribute_mismatch
214 : diag::warn_nsconsumed_attribute_mismatch);
262 if (method->
hasAttr<NSReturnsRetainedAttr>())
270 if (method->
hasAttr<NSReturnsRetainedAttr>() ||
271 method->
hasAttr<NSReturnsNotRetainedAttr>() ||
272 method->
hasAttr<NSReturnsAutoreleasedAttr>())
285 bool IsCategory =
false;
286 StringRef RealizedPlatform;
288 nullptr, VersionTuple(),
291 if (isa<ObjCMethodDecl>(ND)) {
294 if (RealizedPlatform.empty())
298 if (RealizedPlatform.endswith(
"_app_extension"))
300 S.
Diag(ImplLoc, diag::warn_unavailable_def);
305 if (
const auto *CD = dyn_cast<ObjCCategoryDecl>(ND)) {
306 if (!CD->getClassInterface()->isDeprecated())
308 ND = CD->getClassInterface();
313 S.
Diag(ImplLoc, diag::warn_deprecated_def)
314 << (isa<ObjCMethodDecl>(ND)
316 : isa<ObjCCategoryDecl>(ND) || IsCategory ? 2
318 if (isa<ObjCMethodDecl>(ND))
323 << (isa<ObjCCategoryDecl>(ND) ?
"category" :
"class");
376 diag::err_func_def_incomplete_result))
398 if (!Param->isInvalidDecl() &&
401 Diag(Param->getLocation(), diag::warn_arc_strong_pointer_objc_pointer) <<
404 if (Param->getIdentifier())
447 ImplDeclOfMethodDecl = OID->getImplementation();
448 else if (
ObjCCategoryDecl *CD = dyn_cast<ObjCCategoryDecl>(ContDeclOfMethodDecl)) {
449 if (CD->IsClassExtension()) {
451 ImplDeclOfMethodDecl = OID->getImplementation();
453 ImplDeclOfMethodDecl = CD->getImplementation();
457 if (!ImplDeclOfMethodDecl || ImplDeclOfMethodDecl != ImplDeclOfMethodDef)
465 IC->getSuperClass() !=
nullptr;
466 }
else if (IC->hasDesignatedInitializers()) {
492 (SuperMethod && SuperMethod->
hasAttr<ObjCRequiresSuperAttr>());
505 ObjCInterfaceValidatorCCC() : CurrentIDecl(
nullptr) {}
507 : CurrentIDecl(IDecl) {}
509 bool ValidateCandidate(
const TypoCorrection &candidate)
override {
514 std::unique_ptr<CorrectionCandidateCallback> clone()
override {
515 return std::make_unique<ObjCInterfaceValidatorCCC>(*this);
527 unsigned NumProtoRefs,
532 for (
unsigned i = 0; i < NumProtoRefs; ++i) {
557 ObjCInterfaceValidatorCCC CCC(IDecl);
562 << SuperName << ClassName);
568 Diag(SuperLoc, diag::err_recursive_superclass)
569 << SuperName << ClassName <<
SourceRange(AtInterfaceLoc, ClassLoc);
573 dyn_cast_or_null<ObjCInterfaceDecl>(PrevDecl);
577 if (SuperClassDecl) {
582 if (PrevDecl && !SuperClassDecl) {
586 dyn_cast_or_null<TypedefNameDecl>(PrevDecl)) {
587 QualType T = TDecl->getUnderlyingType();
607 if (!SuperClassDecl) {
608 Diag(SuperLoc, diag::err_redefinition_different_kind) << SuperName;
613 if (!dyn_cast_or_null<TypedefNameDecl>(PrevDecl)) {
615 Diag(SuperLoc, diag::err_undef_superclass)
616 << SuperName << ClassName <<
SourceRange(AtInterfaceLoc, ClassLoc);
619 diag::err_forward_superclass,
622 SourceRange(AtInterfaceLoc, ClassLoc))) {
623 SuperClassDecl =
nullptr;
628 if (SuperClassType.isNull()) {
629 assert(!SuperClassDecl &&
"Failed to set SuperClassType?");
635 if (!SuperTypeArgs.empty()) {
643 SuperTypeArgsRange.
getEnd(),
655 if (!SuperClassTInfo) {
675 if (parsedTypeBound) {
686 diag::err_objc_type_param_bound_missing_pointer)
687 << typeBound << paramName
706 diag::err_objc_type_param_bound_nonobject)
707 << typeBound << paramName;
710 typeBoundInfo =
nullptr;
719 bool diagnosed =
false;
723 rangeToRemove = attr.getLocalSourceRange();
724 if (attr.getTypePtr()->getImmediateNullability()) {
725 Diag(attr.getBeginLoc(),
726 diag::err_objc_type_param_bound_explicit_nullability)
727 << paramName << typeBound
737 diag::err_objc_type_param_bound_qualified)
738 << paramName << typeBound
748 if (!quals.
empty()) {
758 if (!typeBoundInfo) {
765 index, paramLoc, paramName, colonLoc,
776 reinterpret_cast<ObjCTypeParamDecl * const *>(typeParamsIn.data()),
777 typeParamsIn.size());
783 llvm::SmallDenseMap<IdentifierInfo *, ObjCTypeParamDecl *> knownParams;
784 for (
auto typeParam : typeParams) {
785 auto known = knownParams.find(typeParam->getIdentifier());
786 if (known != knownParams.end()) {
787 Diag(typeParam->getLocation(), diag::err_objc_type_param_redecl)
788 << typeParam->getIdentifier()
791 typeParam->setInvalidDecl();
793 knownParams.insert(std::make_pair(typeParam->getIdentifier(), typeParam));
805 for (
auto typeParam : *typeParamList) {
806 if (!typeParam->isInvalidDecl()) {
832 if (prevTypeParams->
size() != newTypeParams->
size()) {
834 if (newTypeParams->
size() > prevTypeParams->
size()) {
840 S.
Diag(diagLoc, diag::err_objc_type_param_arity_mismatch)
841 <<
static_cast<unsigned>(newContext)
842 << (newTypeParams->
size() > prevTypeParams->
size())
843 << prevTypeParams->
size()
844 << newTypeParams->
size();
850 for (
unsigned i = 0, n = prevTypeParams->
size(); i != n; ++i) {
857 newContext != TypeParamListContext::Definition) {
876 auto diag = S.
Diag(diagLoc,
877 diag::err_objc_type_param_variance_conflict)
878 <<
static_cast<unsigned>(newTypeParam->
getVariance())
880 <<
static_cast<unsigned>(prevTypeParam->
getVariance())
889 StringRef newVarianceStr
896 (newVarianceStr +
" ").str());
923 S.
Diag(newBoundRange.
getBegin(), diag::err_objc_type_param_bound_conflict)
948 if (newContext == TypeParamListContext::ForwardDeclaration ||
949 newContext == TypeParamListContext::Definition) {
957 diag::err_objc_type_param_bound_missing)
960 << (newContext == TypeParamListContext::ForwardDeclaration)
980 Decl *
const *ProtoRefs,
unsigned NumProtoRefs,
983 assert(ClassName &&
"Missing class identifier");
990 if (PrevDecl && !isa<ObjCInterfaceDecl>(PrevDecl)) {
991 Diag(ClassLoc, diag::err_redefinition_different_kind) << ClassName;
998 if (PrevIDecl && PrevIDecl->getIdentifier() != ClassName) {
1011 ClassName = PrevIDecl->getIdentifier();
1018 if (typeParamList) {
1022 TypeParamListContext::Definition)) {
1023 typeParamList =
nullptr;
1026 Diag(ClassLoc, diag::err_objc_parameterized_forward_class_first)
1028 Diag(prevTypeParamList->getLAngleLoc(), diag::note_previous_decl)
1033 for (
auto typeParam : *prevTypeParamList) {
1034 clonedTypeParams.push_back(
1038 typeParam->getVariance(),
1040 typeParam->getIndex(),
1042 typeParam->getIdentifier(),
1057 typeParamList, PrevIDecl, ClassLoc);
1061 Diag(AtInterfaceLoc, diag::err_duplicate_class_def)
1062 << PrevIDecl->getDeclName();
1063 Diag(Def->getLocation(), diag::note_previous_definition);
1082 ClassName, ClassLoc,
1083 SuperName, SuperLoc, SuperTypeArgs,
1084 SuperTypeArgsRange);
1092 NumProtoRefs, ProtoLocs);
1116 if (
const TypedefNameDecl *TDecl = dyn_cast_or_null<TypedefNameDecl>(IDecl)) {
1117 QualType T = TDecl->getUnderlyingType();
1120 ProtocolRefs.append(OPT->qual_begin(), OPT->qual_end());
1125 ProtocolLocs.append(OPT->getNumProtocols(), SuperLoc);
1142 Diag(AliasLocation, diag::err_conflicting_aliasing_type) << AliasName;
1151 dyn_cast_or_null<TypedefNameDecl>(CDeclU)) {
1152 QualType T = TDecl->getUnderlyingType();
1155 ClassName = IDecl->getIdentifier();
1164 Diag(ClassLocation, diag::warn_undef_interface) << ClassName;
1187 E = PList.
end(); I != E; ++I) {
1190 if (PDecl->getIdentifier() == PName) {
1191 Diag(Ploc, diag::err_protocol_has_circular_dependency);
1192 Diag(PrevLoc, diag::note_previous_definition);
1196 if (!PDecl->hasDefinition())
1200 PDecl->getLocation(), PDecl->getReferencedProtocols()))
1214 assert(ProtocolName &&
"Missing protocol identifier");
1220 Diag(ProtocolLoc, diag::warn_duplicate_protocol_def) << ProtocolName;
1221 Diag(Def->getLocation(), diag::note_previous_definition);
1228 ProtocolLoc, AtProtoInterfaceLoc,
1235 PDecl->startDefinition();
1243 ProtocolName, ProtocolLoc, PrevDecl->
getLocation(), PList);
1248 ProtocolLoc, AtProtoInterfaceLoc,
1252 PDecl->startDefinition();
1262 if (!err && NumProtoRefs ) {
1265 NumProtoRefs, ProtoLocs);
1277 UndefinedProtocol = PDecl;
1283 UndefinedProtocol = PI;
1309 Diag(Pair.second, diag::err_undeclared_protocol) << Pair.first;
1318 if (!ForObjCContainer) {
1327 if (WarnOnDeclarations &&
1329 Diag(Pair.second, diag::warn_undef_protocolref) << Pair.first;
1330 Diag(UndefinedProtocol->
getLocation(), diag::note_protocol_decl_undefined)
1331 << UndefinedProtocol;
1333 Protocols.push_back(PDecl);
1340 class ObjCTypeArgOrProtocolValidatorCCC final
1345 ObjCTypeArgOrProtocolValidatorCCC(
ASTContext &context,
1347 :
Context(context), LookupKind(lookupKind) { }
1349 bool ValidateCandidate(
const TypoCorrection &candidate)
override {
1363 if (isa<RecordDecl>(typeDecl) && !Context.getLangOpts().CPlusPlus)
1368 auto type = Context.getTypeDeclType(typeDecl);
1369 if (
type->isObjCObjectPointerType() ||
1370 type->isBlockPointerType() ||
1371 type->isDependentType() ||
1372 type->isObjCObjectType())
1389 std::unique_ptr<CorrectionCandidateCallback> clone()
override {
1390 return std::make_unique<ObjCTypeArgOrProtocolValidatorCCC>(*this);
1399 bool SelectProtocolFirst) {
1400 Diag(TypeArgLoc, diag::err_objc_type_args_and_protocols)
1401 << SelectProtocolFirst << TypeArgId << ProtocolId
1418 bool warnOnIncompleteProtocols) {
1421 unsigned numProtocolsResolved = 0;
1422 auto resolvedAsProtocols = [&] {
1423 assert(numProtocolsResolved == identifiers.size() &&
"Unresolved protocols");
1430 bool allAreTypeNames =
false;
1434 baseClass = objcObjectType->getInterface();
1436 if (
auto typeParams = baseClass->getTypeParamList()) {
1437 if (typeParams->size() == numProtocolsResolved) {
1439 allAreTypeNames =
true;
1446 for (
unsigned i = 0, n = protocols.size(); i != n; ++i) {
1451 if (!warnOnIncompleteProtocols) {
1463 if (warnOnIncompleteProtocols &&
1465 Diag(identifierLocs[i], diag::warn_undef_protocolref)
1474 if (allAreTypeNames) {
1477 if (isa<ObjCInterfaceDecl>(
decl)) {
1479 firstClassNameLoc = identifierLocs[i];
1480 }
else if (!isa<TypeDecl>(
decl)) {
1482 allAreTypeNames =
false;
1485 allAreTypeNames =
false;
1494 if (allAreTypeNames && firstClassNameLoc.
isValid()) {
1495 llvm::SmallPtrSet<ObjCProtocolDecl*, 8> knownProtocols;
1497 bool allProtocolsDeclared =
true;
1498 for (
auto proto : protocols) {
1499 if (knownProtocols.count(static_cast<ObjCProtocolDecl *>(proto)) == 0) {
1500 allProtocolsDeclared =
false;
1505 if (allProtocolsDeclared) {
1506 Diag(firstClassNameLoc, diag::warn_objc_redundant_qualified_class_type)
1507 << baseClass->getDeclName() <<
SourceRange(lAngleLoc, rAngleLoc)
1513 protocolLAngleLoc = lAngleLoc;
1514 protocolRAngleLoc = rAngleLoc;
1515 assert(protocols.size() == identifierLocs.size());
1519 for (
unsigned i = 0, n = identifiers.size(); i != n; ++i) {
1521 protocols.push_back(proto);
1523 ++numProtocolsResolved;
1527 if (numProtocolsResolved == identifiers.size())
1528 return resolvedAsProtocols();
1534 typedef llvm::PointerUnion<TypeDecl *, ObjCInterfaceDecl *> TypeOrClassDecl;
1536 unsigned numTypeDeclsResolved = 0;
1537 for (
unsigned i = 0, n = identifiers.size(); i != n; ++i) {
1541 typeDecls.push_back(TypeOrClassDecl());
1545 if (
auto typeDecl = dyn_cast<TypeDecl>(decl)) {
1546 typeDecls.push_back(typeDecl);
1547 ++numTypeDeclsResolved;
1551 if (
auto objcClass = dyn_cast<ObjCInterfaceDecl>(decl)) {
1552 typeDecls.push_back(objcClass);
1553 ++numTypeDeclsResolved;
1557 typeDecls.push_back(TypeOrClassDecl());
1564 auto resolveTypeReference = [&](TypeOrClassDecl typeDecl,
SourceLocation loc)
1568 const char* prevSpec;
1571 if (
auto *actualTypeDecl = typeDecl.dyn_cast<
TypeDecl *>())
1599 Diag(loc, diag::err_objc_type_arg_missing_star)
1610 auto resolvedAsTypeDecls = [&] {
1614 assert(numTypeDeclsResolved == identifiers.size() &&
"Unresolved type decl");
1616 for (
unsigned i = 0, n = identifiers.size(); i != n; ++i) {
1618 TypeResult type = resolveTypeReference(typeDecls[i], identifierLocs[i]);
1624 typeArgs.push_back(type.
get());
1627 typeArgsLAngleLoc = lAngleLoc;
1628 typeArgsRAngleLoc = rAngleLoc;
1633 if (numTypeDeclsResolved == identifiers.size())
1634 return resolvedAsTypeDecls();
1640 for (
unsigned i = 0, n = identifiers.size(); i != n; ++i) {
1643 if (protocols[i] || typeDecls[i]) {
1649 if (protocols[i] && typeDecls[i])
1672 identifiers[i], identifierLocs[i],
1673 protocols[i] !=
nullptr);
1681 ObjCTypeArgOrProtocolValidatorCCC CCC(
Context, lookupKind);
1689 PDiag(diag::err_undeclared_protocol_suggest)
1692 protocols[i] = proto;
1693 ++numProtocolsResolved;
1700 PDiag(diag::err_unknown_typename_suggest)
1703 typeDecls[i] = typeDecl;
1704 ++numTypeDeclsResolved;
1711 PDiag(diag::err_unknown_type_or_class_name_suggest)
1712 << identifiers[i] <<
true);
1714 typeDecls[i] = objcClass;
1715 ++numTypeDeclsResolved;
1721 Diag(identifierLocs[i],
1722 (lookupKind ==
LookupAnyName ? diag::err_objc_type_arg_missing
1724 : diag::err_unknown_typename))
1733 if (numProtocolsResolved == identifiers.size())
1734 return resolvedAsProtocols();
1737 assert(numTypeDeclsResolved == identifiers.size() &&
"Not all types?");
1738 return resolvedAsTypeDecls();
1749 llvm::DenseMap<Selector, const ObjCMethodDecl*> MethodMap;
1750 for (
auto *MD : ID->
methods())
1751 MethodMap[MD->getSelector()] = MD;
1753 if (MethodMap.empty())
1755 for (
const auto *Method : CAT->
methods()) {
1756 const ObjCMethodDecl *&PrevMethod = MethodMap[Method->getSelector()];
1760 Diag(Method->getLocation(), diag::err_duplicate_method_decl)
1761 << Method->getDeclName();
1779 IdentPair.second, AtProtocolLoc,
1791 DeclsInGroup.push_back(PDecl);
1801 Decl *
const *ProtoRefs,
unsigned NumProtoRefs,
1811 diag::err_category_forward_interface,
1812 CategoryName ==
nullptr)) {
1817 ClassLoc, CategoryLoc, CategoryName,
1818 IDecl, typeParamList);
1823 Diag(ClassLoc, diag::err_undef_interface) << ClassName;
1828 Diag(ClassLoc, diag::err_class_extension_after_impl) << ClassName;
1830 diag::note_implementation_declared);
1838 Diag(CategoryLoc, diag::warn_dup_category_def)
1839 << ClassName << CategoryName;
1840 Diag(
Previous->getLocation(), diag::note_previous_definition);
1845 if (typeParamList) {
1850 : TypeParamListContext::Extension))
1851 typeParamList =
nullptr;
1854 diag::err_objc_parameterized_category_nonclass)
1855 << (CategoryName !=
nullptr)
1859 typeParamList =
nullptr;
1864 ClassLoc, CategoryLoc, CategoryName, IDecl,
1877 NumProtoRefs, ProtoLocs);
1915 ClassLoc, AtCatImplLoc, CatLoc);
1918 Diag(ClassLoc, diag::err_undef_interface) << ClassName;
1921 diag::err_undef_interface)) {
1933 if (IDecl && IDecl->
hasAttr<ObjCRuntimeVisibleAttr>()) {
1934 Diag(ClassLoc, diag::err_objc_runtime_visible_category)
1941 Diag(ClassLoc, diag::err_dup_implementation_category) << ClassName
1944 diag::note_previous_definition);
1970 if (PrevDecl && !isa<ObjCInterfaceDecl>(PrevDecl)) {
1971 Diag(ClassLoc, diag::err_redefinition_different_kind) << ClassName;
1973 }
else if ((IDecl = dyn_cast_or_null<ObjCInterfaceDecl>(PrevDecl))) {
1977 diag::warn_undef_interface);
1981 ObjCInterfaceValidatorCCC CCC{};
1990 PDiag(diag::warn_undef_interface_suggest) << ClassName,
1993 Diag(ClassLoc, diag::warn_undef_interface) << ClassName;
1999 if (SuperClassname) {
2003 if (PrevDecl && !isa<ObjCInterfaceDecl>(PrevDecl)) {
2004 Diag(SuperClassLoc, diag::err_redefinition_different_kind)
2008 SDecl = dyn_cast_or_null<ObjCInterfaceDecl>(PrevDecl);
2012 Diag(SuperClassLoc, diag::err_undef_superclass)
2013 << SuperClassname << ClassName;
2017 Diag(SuperClassLoc, diag::err_conflicting_super_class)
2056 ClassLoc, AtClassImplLoc, SuperClassLoc);
2067 Diag(ClassLoc, diag::err_dup_implementation_class) << ClassName;
2069 diag::note_previous_definition);
2083 Diag(ClassLoc, diag::err_objc_runtime_visible_subclass)
2094 DeclsInGroup.reserve(Decls.size() + 1);
2096 for (
unsigned i = 0, e = Decls.size(); i != e; ++i) {
2097 Decl *Dcl = Decls[i];
2102 DeclsInGroup.push_back(Dcl);
2105 DeclsInGroup.push_back(ObjCImpDecl);
2113 assert(ImpDecl &&
"missing implementation decl");
2123 for (
unsigned i = 0, e = numIvars; i != e; ++i) {
2135 assert(ivars &&
"missing @implementation ivars");
2139 for (
unsigned i = 0; i < numIvars; i++) {
2144 Diag(ClsIvar->getLocation(), diag::note_previous_definition);
2152 Diag(ClsExtIvar->getLocation(), diag::note_previous_definition);
2169 for (; numIvars > 0 && IVI != IVE; ++IVI) {
2172 assert (ImplIvar &&
"missing implementation ivar");
2173 assert (ClsIvar &&
"missing class ivar");
2185 diag::err_conflicting_ivar_bitwidth)
2188 diag::note_previous_definition);
2200 Diag(ivars[j]->getLocation(), diag::err_inconsistent_ivar_count);
2201 else if (IVI != IVE)
2202 Diag(IVI->getLocation(), diag::err_inconsistent_ivar_count);
2207 bool &IncompleteImpl,
2229 S.
Diag(MethodLoc, diag::note_method_declared_at) << method;
2305 (y & ~
Decl::OBJC_TQ_CSNullability);
2311 bool IsProtocolMethodDecl,
2312 bool IsOverridingMode,
2314 if (IsProtocolMethodDecl &&
2320 ? diag::warn_conflicting_overriding_ret_type_modifiers
2321 : diag::warn_conflicting_ret_type_modifiers))
2330 if (Warn && IsOverridingMode &&
2335 auto nullabilityMethodImpl =
2337 auto nullabilityMethodDecl =
2340 diag::warn_conflicting_nullability_attr_overriding_ret_types)
2342 nullabilityMethodImpl,
2346 nullabilityMethodDecl,
2359 IsOverridingMode ? diag::warn_conflicting_overriding_ret_types
2360 : diag::warn_conflicting_ret_types;
2376 IsOverridingMode ? diag::warn_non_covariant_overriding_ret_types
2377 : diag::warn_non_covariant_ret_types;
2386 ? diag::note_previous_declaration
2387 : diag::note_previous_definition)
2397 bool IsProtocolMethodDecl,
2398 bool IsOverridingMode,
2400 if (IsProtocolMethodDecl &&
2404 if (IsOverridingMode)
2406 diag::warn_conflicting_overriding_param_modifiers)
2410 diag::warn_conflicting_param_modifiers)
2422 if (Warn && IsOverridingMode &&
2426 diag::warn_conflicting_nullability_attr_overriding_param_types)
2443 IsOverridingMode ? diag::warn_conflicting_overriding_param_types
2444 : diag::warn_conflicting_param_types;
2460 IsOverridingMode ? diag::warn_non_contravariant_overriding_param_types
2461 : diag::warn_non_contravariant_param_types;
2467 << MethodImpl->
getDeclName() << IfaceTy << ImplTy;
2469 (IsOverridingMode ? diag::note_previous_declaration
2470 : diag::note_previous_definition))
2481 if (implFamily == declFamily)
return false;
2493 unsigned errorID = diag::err_arc_lost_method_convention;
2494 unsigned noteID = diag::note_arc_lost_method_convention;
2497 family = implFamily;
2498 errorID = diag::err_arc_gained_method_convention;
2499 noteID = diag::note_arc_gained_method_convention;
2503 enum FamilySelector {
2504 F_alloc, F_copy, F_mutableCopy = F_copy, F_init, F_new
2506 FamilySelector familySelector = FamilySelector();
2509 case OMF_None: llvm_unreachable(
"logic error, no method convention");
2523 case OMF_init: familySelector = F_init;
break;
2524 case OMF_alloc: familySelector = F_alloc;
break;
2525 case OMF_copy: familySelector = F_copy;
break;
2527 case OMF_new: familySelector = F_new;
break;
2530 enum ReasonSelector { R_NonObjectReturn, R_UnrelatedReturn };
2531 ReasonSelector reasonSelector;
2536 reasonSelector = R_UnrelatedReturn;
2538 reasonSelector = R_NonObjectReturn;
2541 S.
Diag(impl->
getLocation(), errorID) <<
int(familySelector) << int(reasonSelector);
2542 S.
Diag(decl->
getLocation(), noteID) <<
int(familySelector) << int(reasonSelector);
2549 bool IsProtocolMethodDecl) {
2555 IsProtocolMethodDecl,
false,
2561 IM != EM && IF != EF; ++IM, ++IF) {
2563 IsProtocolMethodDecl,
false,
true);
2568 diag::warn_conflicting_variadic);
2575 bool IsProtocolMethodDecl) {
2578 IsProtocolMethodDecl,
true,
2584 IM != EM && IF != EF; ++IM, ++IF) {
2586 IsProtocolMethodDecl,
true,
true);
2591 diag::warn_conflicting_overriding_variadic);
2600 bool IsProtocolMethodDecl) {
2608 if (MethodDecl->
hasAttr<UnavailableAttr>() ||
2609 MethodDecl->
hasAttr<DeprecatedAttr>())
2613 IsProtocolMethodDecl,
false,
false);
2618 IM != EM && IF != EF; ++IM, ++IF) {
2621 IsProtocolMethodDecl,
false,
false);
2633 diag::warn_category_method_impl_match);
2650 if (PDecl->
hasAttr<ObjCExplicitProtocolImplAttr>())
2652 for (
const auto *PI : PDecl->
protocols())
2675 bool& IncompleteImpl,
2683 assert (IDecl &&
"CheckProtocolMethodDefs - IDecl is null");
2699 if (PDecl->
hasAttr<ObjCExplicitProtocolImplAttr>()) {
2700 if (!ProtocolsExplictImpl) {
2705 ProtocolsExplictImpl->end())
2723 if (InsMap.count(fISelector))
2743 !method->isPropertyAccessor() &&
2744 !InsMap.count(method->getSelector()) &&
2760 IDecl->lookupMethod(method->getSelector(),
2764 if (C || MethodInClass->isPropertyAccessor())
2766 unsigned DIAG = diag::warn_unimplemented_protocol_method;
2776 !ClsMap.count(method->getSelector()) &&
2783 if (C && IDecl->lookupMethod(method->getSelector(),
2789 unsigned DIAG = diag::warn_unimplemented_protocol_method;
2798 CDecl, ProtocolsExplictImpl);
2810 bool &IncompleteImpl,
2811 bool ImmediateClass,
2812 bool WarnCategoryMethodImpl) {
2816 if (!InsMapSeen.insert(I->getSelector()).second)
2818 if (!I->isPropertyAccessor() &&
2819 !InsMap.count(I->getSelector())) {
2822 diag::warn_undef_method_impl);
2828 "Expected to find the method through lookup as well");
2830 if (ImpMethodDecl) {
2834 if (!WarnCategoryMethodImpl)
2836 isa<ObjCProtocolDecl>(CDecl));
2837 else if (!I->isPropertyAccessor())
2846 if (!ClsMapSeen.insert(I->getSelector()).second)
2848 if (!I->isPropertyAccessor() &&
2849 !ClsMap.count(I->getSelector())) {
2852 diag::warn_undef_method_impl);
2857 "Expected to find the method through lookup as well");
2859 if (ImpMethodDecl) {
2863 if (!WarnCategoryMethodImpl)
2865 isa<ObjCProtocolDecl>(CDecl));
2866 else if (!I->isPropertyAccessor())
2875 for (
auto *PI : PD->protocols())
2877 IMPDecl, PI, IncompleteImpl,
false,
2878 WarnCategoryMethodImpl);
2885 if (!WarnCategoryMethodImpl) {
2886 for (
auto *Cat : I->visible_categories())
2888 IMPDecl, Cat, IncompleteImpl,
2889 ImmediateClass && Cat->IsClassExtension(),
2890 WarnCategoryMethodImpl);
2893 for (
auto *Ext : I->visible_extensions())
2895 IMPDecl, Ext, IncompleteImpl,
false,
2896 WarnCategoryMethodImpl);
2900 for (
auto *PI : I->all_referenced_protocols())
2902 IMPDecl, PI, IncompleteImpl,
false,
2903 WarnCategoryMethodImpl);
2907 if (!WarnCategoryMethodImpl && I->getSuperClass())
2910 I->getSuperClass(), IncompleteImpl,
false);
2941 if (SuperIDecl && SuperIDecl->
lookupMethod(Sel,
false))
2945 if (InsMap.empty() && ClsMap.empty())
2949 bool IncompleteImpl =
false;
2952 IncompleteImpl,
false,
2958 bool IncompleteImpl) {
2963 InsMap.insert(I->getSelector());
2971 const auto *
P = PImpl->getPropertyDecl();
2974 InsMap.insert(
P->getGetterName());
2975 if (!
P->getSetterName().isNull())
2976 InsMap.insert(
P->getSetterName());
2983 bool SynthesizeProperties =
LangOpts.ObjCDefaultSynthProperties &&
2985 !IDecl->isObjCRequiresPropertyDefs();
2994 ClsMap.insert(I->getSelector());
3001 IncompleteImpl,
true);
3006 dyn_cast<ObjCCategoryImplDecl>(IMPDecl))
3017 for (
auto *PI : I->all_referenced_protocols())
3019 InsMap, ClsMap, I, ExplicitImplProtocols);
3023 if (!
C->IsClassExtension()) {
3024 for (
auto *
P :
C->protocols())
3026 IncompleteImpl, InsMap, ClsMap, CDecl,
3027 ExplicitImplProtocols);
3032 llvm_unreachable(
"invalid ObjCContainerDecl type.");
3042 for (
unsigned i = 0; i != NumElts; ++i) {
3047 if (PrevDecl && !isa<ObjCInterfaceDecl>(PrevDecl)) {
3057 Diag(AtClassLoc, diag::err_redefinition_different_kind) << IdentList[i];
3065 Diag(AtClassLoc, diag::warn_forward_class_redefinition)
3075 = dyn_cast_or_null<ObjCInterfaceDecl>(PrevDecl);
3097 if (PrevIDecl && TypeParams) {
3101 *
this, PrevTypeParams, TypeParams,
3102 TypeParamListContext::ForwardDeclaration)) {
3103 TypeParams =
nullptr;
3107 Diag(IdentLocs[i], diag::err_objc_parameterized_forward_class)
3110 Diag(Def->getLocation(), diag::note_defined_here)
3113 TypeParams =
nullptr;
3119 ClassName, TypeParams, PrevIDecl,
3125 DeclsInGroup.push_back(IDecl);
3133 const Type *left,
const Type *right);
3142 if (left == right)
return true;
3165 if (isa<VectorType>(left))
return isa<VectorType>(right);
3166 if (isa<VectorType>(right))
return false;
3189 return (leftSK == rightSK);
3195 assert(lt && rt && lt != rt);
3197 if (!isa<RecordType>(lt) || !isa<RecordType>(rt))
return false;
3198 RecordDecl *left = cast<RecordType>(lt)->getDecl();
3199 RecordDecl *right = cast<RecordType>(rt)->getDecl();
3205 if ((isa<CXXRecordDecl>(left) && !cast<CXXRecordDecl>(left)->isPOD()) ||
3206 (isa<CXXRecordDecl>(right) && !cast<CXXRecordDecl>(right)->isPOD()))
3221 for (; li != le && ri != re; ++li, ++ri) {
3222 if (!
matchTypes(Context, strategy, li->getType(), ri->getType()))
3225 return (li == le && ri == re);
3246 (left->
hasAttr<NSReturnsRetainedAttr>()
3247 != right->
hasAttr<NSReturnsRetainedAttr>() ||
3248 left->
hasAttr<NSConsumesSelfAttr>()
3249 != right->
hasAttr<NSConsumesSelfAttr>()))
3256 for (; li != le && ri != re; ++li, ++ri) {
3257 assert(ri != right->
param_end() &&
"Param mismatch");
3260 if (!
matchTypes(Context, strategy, lparm->getType(), rparm->getType()))
3264 lparm->hasAttr<NSConsumedAttr>() != rparm->hasAttr<NSConsumedAttr>())
3273 auto *MethodInListProtocol =
3277 if ((MethodProtocol && !MethodInListProtocol) ||
3278 (!MethodProtocol && MethodInListProtocol))
3281 if (MethodProtocol && MethodInListProtocol)
3287 return MethodInterface == MethodInListInterface;
3296 if (!CD->IsClassExtension() && List->
getBits() < 2)
3310 for (; List; Previous = List, List = List->
getNext()) {
3327 if (!SameDeclaration ||
3333 List->setHasMoreThanOneDecl(
true);
3339 ListWithSameDeclaration = List;
3342 !ListWithSameDeclaration &&
3344 ListWithSameDeclaration = List;
3358 List->setHasMoreThanOneDecl(
true);
3365 List->setMethod(Method);
3371 List->setMethod(Method);
3382 if (ListWithSameDeclaration) {
3385 ListWithSameDeclaration->
setMethod(Method);
3386 ListWithSameDeclaration->
setNext(List);
3396 assert(ExternalSource &&
"We need an external AST source");
3397 ExternalSource->ReadMethodPool(Sel);
3401 if (!ExternalSource)
3403 ExternalSource->updateOutOfDateSelector(Sel);
3406 void Sema::AddMethodToGlobalPool(
ObjCMethodDecl *Method,
bool impl,
3422 ObjCMethodList &Entry = instance ? Pos->second.first : Pos->second.second;
3459 assert(BoundInterface &&
"unexpected object type!");
3464 if (MethodProtocol) {
3474 return MethodInterface == BoundInterface ||
3475 MethodInterface->isSuperClassOf(BoundInterface) ||
3476 BoundInterface->isSuperClassOf(MethodInterface);
3478 llvm_unreachable(
"unknown method context");
3485 bool InstanceFirst,
bool CheckTheOther,
3490 GlobalMethodPool::iterator Pos =
MethodPool.find(Sel);
3498 if (M->getMethod() && !M->getMethod()->isHidden()) {
3500 Methods.push_back(M->getMethod());
3504 if (!Methods.empty())
3505 return Methods.size() > 1;
3514 if (M->getMethod() && !M->getMethod()->isHidden()) {
3516 Methods.push_back(M->getMethod());
3519 return Methods.size() > 1;
3527 FilteredMethods.push_back(BestMethod);
3529 for (
auto *M : Methods)
3530 if (M != BestMethod && !M->
hasAttr<UnavailableAttr>())
3531 FilteredMethods.push_back(M);
3533 if (FilteredMethods.size() > 1)
3537 GlobalMethodPool::iterator Pos =
MethodPool.find(Sel);
3548 bool receiverIdOrClass,
3553 GlobalMethodPool::iterator Pos =
MethodPool.find(Sel);
3558 ObjCMethodList &MethList = instance ? Pos->second.first : Pos->second.second;
3561 if (M->getMethod() && !M->getMethod()->isHidden())
3562 return M->getMethod();
3569 bool receiverIdOrClass) {
3571 bool issueDiagnostic =
false, issueError =
false;
3575 bool strictSelectorMatch =
3576 receiverIdOrClass &&
3578 if (strictSelectorMatch) {
3579 for (
unsigned I = 1, N = Methods.size(); I != N; ++I) {
3581 issueDiagnostic =
true;
3590 if (!strictSelectorMatch ||
3591 (issueDiagnostic &&
getLangOpts().ObjCAutoRefCount))
3592 for (
unsigned I = 1, N = Methods.size(); I != N; ++I) {
3596 issueDiagnostic =
true;
3603 if (issueDiagnostic) {
3605 Diag(R.
getBegin(), diag::err_arc_multiple_method_decl) << Sel << R;
3606 else if (strictSelectorMatch)
3607 Diag(R.
getBegin(), diag::warn_strict_multiple_method_decl) << Sel << R;
3609 Diag(R.
getBegin(), diag::warn_multiple_method_decl) << Sel << R;
3611 Diag(Methods[0]->getBeginLoc(),
3612 issueError ? diag::note_possibility : diag::note_using)
3613 << Methods[0]->getSourceRange();
3614 for (
unsigned I = 1, N = Methods.size(); I != N; ++I) {
3615 Diag(Methods[I]->getBeginLoc(), diag::note_also_found)
3616 << Methods[I]->getSourceRange();
3622 GlobalMethodPool::iterator Pos =
MethodPool.find(Sel);
3628 Method = Method->getNext())
3629 if (Method->getMethod() &&
3632 return Method->getMethod();
3635 Method = Method->getNext())
3636 if (Method->getMethod() &&
3639 return Method->getMethod();
3647 const unsigned MaxEditDistance = 1;
3648 unsigned BestEditDistance = MaxEditDistance + 1;
3651 unsigned MinPossibleEditDistance =
abs((
int)MethodName.size() - (int)Typo.size());
3652 if (MinPossibleEditDistance > 0 &&
3653 Typo.size() / MinPossibleEditDistance < 1)
3655 unsigned EditDistance = Typo.edit_distance(MethodName,
true, MaxEditDistance);
3656 if (EditDistance > MaxEditDistance)
3658 if (EditDistance == BestEditDistance)
3659 BestMethod.push_back(Method);
3660 else if (EditDistance < BestEditDistance) {
3662 BestMethod.push_back(Method);
3681 bool ObjectIsId =
true, ObjectIsClass =
true;
3683 ObjectIsId = ObjectIsClass =
false;
3688 ObjectType =
QualType(ObjCPtr->getInterfaceType(), 0);
3689 ObjectIsId = ObjectIsClass =
false;
3692 ObjectIsClass =
false;
3698 for (GlobalMethodPool::iterator b =
MethodPool.begin(),
3702 if (M->getMethod() &&
3703 (M->getMethod()->getSelector().getNumArgs() == NumArgs) &&
3704 (M->getMethod()->getSelector() != Sel)) {
3706 Methods.push_back(M->getMethod());
3707 else if (!ObjectIsClass &&
3710 Methods.push_back(M->getMethod());
3714 if (M->getMethod() &&
3715 (M->getMethod()->getSelector().getNumArgs() == NumArgs) &&
3716 (M->getMethod()->getSelector() != Sel)) {
3718 Methods.push_back(M->getMethod());
3719 else if (!ObjectIsId &&
3722 Methods.push_back(M->getMethod());
3727 for (
unsigned i = 0, e = Methods.size(); i < e; i++) {
3731 return (SelectedMethods.size() == 1) ? SelectedMethods[0] :
nullptr;
3741 for (
auto *Ivar : ID->
ivars()) {
3742 if (Ivar->isInvalidDecl())
3747 Diag(Ivar->getLocation(), diag::err_duplicate_member) << II;
3749 Ivar->setInvalidDecl();
3761 if (ivar->isInvalidDecl())
continue;
3764 S.
Diag(ivar->getLocation(), diag::err_arc_weak_disabled);
3766 S.
Diag(ivar->getLocation(), diag::err_arc_weak_no_runtime);
3780 if (ivar->isInvalidDecl())
3786 S.
Diag(ivar->getLocation(), diag::err_flexible_array_arc_retainable);
3787 ivar->setInvalidDecl();
3794 case Decl::ObjCInterface:
3796 case Decl::ObjCProtocol:
3798 case Decl::ObjCCategory:
3799 if (cast<ObjCCategoryDecl>(
CurContext)->IsClassExtension())
3802 case Decl::ObjCImplementation:
3804 case Decl::ObjCCategoryImpl:
3816 return (RecordTy && RecordTy->getDecl()->hasFlexibleArrayMember());
3823 if ((IntfDecl = dyn_cast<ObjCInterfaceDecl>(OCD))) {
3824 Ivars = IntfDecl->
ivars();
3825 }
else if (
auto *ImplDecl = dyn_cast<ObjCImplementationDecl>(OCD)) {
3826 IntfDecl = ImplDecl->getClassInterface();
3827 Ivars = ImplDecl->
ivars();
3828 }
else if (
auto *CategoryDecl = dyn_cast<ObjCCategoryDecl>(OCD)) {
3829 if (CategoryDecl->IsClassExtension()) {
3830 IntfDecl = CategoryDecl->getClassInterface();
3831 Ivars = CategoryDecl->
ivars();
3836 if (!isa<ObjCInterfaceDecl>(OCD)) {
3837 for (
auto ivar : Ivars) {
3839 S.
Diag(ivar->getLocation(), diag::warn_variable_sized_ivar_visibility)
3840 << ivar->getDeclName() << ivar->getType();
3852 if (ivar->isInvalidDecl() || !ivar->getNextIvar())
3855 bool IsInvalidIvar =
false;
3857 S.
Diag(ivar->getLocation(), diag::err_flexible_array_not_at_end)
3858 << ivar->getDeclName() << IvarTy
3860 IsInvalidIvar =
true;
3862 if (RecordTy->getDecl()->hasFlexibleArrayMember()) {
3863 S.
Diag(ivar->getLocation(),
3864 diag::err_objc_variable_sized_type_not_at_end)
3865 << ivar->getDeclName() << IvarTy;
3866 IsInvalidIvar =
true;
3869 if (IsInvalidIvar) {
3870 S.
Diag(ivar->getNextIvar()->getLocation(),
3871 diag::note_next_ivar_declaration)
3872 << ivar->getNextIvar()->getSynthesize();
3873 ivar->setInvalidDecl();
3881 (Ivars.begin() == Ivars.end()) ?
nullptr : *Ivars.begin();
3884 while (SuperClass && SuperClass->
ivar_empty())
3888 std::advance(IvarIter, SuperClass->
ivar_size() - 1);
3892 diag::warn_superclass_variable_sized_type_not_at_end)
3893 << FirstIvar->
getDeclName() << LastIvar->getDeclName()
3894 << LastIvar->getType() << SuperClass->
getDeclName();
3895 S.
Diag(LastIvar->getLocation(), diag::note_entity_declared_at)
3896 << LastIvar->getDeclName();
3908 assert(AtEnd.
isValid() &&
"Invalid location for '@end'");
3910 auto *OCD = cast<ObjCContainerDecl>(
CurContext);
3911 Decl *ClassDecl = OCD;
3913 bool isInterfaceDeclKind =
3914 isa<ObjCInterfaceDecl>(ClassDecl) || isa<ObjCCategoryDecl>(ClassDecl)
3915 || isa<ObjCProtocolDecl>(ClassDecl);
3916 bool checkIdenticalMethods = isa<ObjCImplementationDecl>(ClassDecl);
3922 if (
auto *OID = dyn_cast<ObjCImplementationDecl>(
CurContext)) {
3923 for (
auto PropImpl : OID->property_impls()) {
3924 if (
auto *Getter = PropImpl->getGetterMethodDecl())
3925 if (Getter->isSynthesizedAccessorStub()) {
3926 OID->makeDeclVisibleInContext(Getter);
3927 OID->addDecl(Getter);
3929 if (
auto *Setter = PropImpl->getSetterMethodDecl())
3930 if (Setter->isSynthesizedAccessorStub()) {
3931 OID->makeDeclVisibleInContext(Setter);
3932 OID->addDecl(Setter);
3938 llvm::DenseMap<Selector, const ObjCMethodDecl*> InsMap;
3939 llvm::DenseMap<Selector, const ObjCMethodDecl*> ClsMap;
3941 for (
unsigned i = 0, e = allMethods.size(); i != e; i++ ) {
3943 cast_or_null<ObjCMethodDecl>(allMethods[i]);
3945 if (!Method)
continue;
3951 if ((isInterfaceDeclKind && PrevMethod && !match)
3952 || (checkIdenticalMethods && match)) {
3975 if ((isInterfaceDeclKind && PrevMethod && !match)
3976 || (checkIdenticalMethods && match)) {
3995 if (isa<ObjCInterfaceDecl>(ClassDecl)) {
4002 if (
C->IsClassExtension()) {
4008 if (CDecl->getIdentifier())
4012 for (
auto *I : CDecl->properties())
4014 CDecl->setAtEndRange(AtEnd);
4017 IC->setAtEndRange(AtEnd);
4024 for (
const auto *Ext : IDecl->visible_extensions()) {
4025 for (
const auto *
Property : Ext->instance_properties()) {
4028 = IC->FindPropertyImplDecl(
Property->getIdentifier(),
4030 if (PIDecl->getPropertyImplementation()
4034 for (
const auto *Ext : IDecl->visible_extensions()) {
4036 Ext->getInstanceMethod(
Property->getGetterName()))
4037 GetterMethod->setPropertyAccessor(
true);
4040 = Ext->getInstanceMethod(
Property->getSetterName()))
4041 SetterMethod->setPropertyAccessor(
true);
4049 if (IDecl->hasDesignatedInitializers())
4054 bool HasRootClassAttr = IDecl->hasAttr<ObjCRootClassAttr>();
4055 if (IDecl->getSuperClass() ==
nullptr) {
4058 if (!HasRootClassAttr) {
4061 Diag(DeclLoc, diag::warn_objc_root_class_missing)
4062 << IDecl->getIdentifier();
4069 if (NSObjectDecl && NSObjectDecl->getDefinition()) {
4070 Diag(SuperClassLoc, diag::note_objc_needs_superclass)
4073 Diag(SuperClassLoc, diag::note_objc_needs_superclass);
4076 }
else if (HasRootClassAttr) {
4078 Diag(IDecl->getLocation(), diag::err_objc_root_class_subclass);
4086 if (IDecl->hasAttr<ObjCSubclassingRestrictedAttr>() &&
4087 Super->hasAttr<ObjCSubclassingRestrictedAttr>()) {
4088 Diag(IC->getLocation(), diag::err_restricted_superclass_mismatch);
4089 Diag(Super->getLocation(), diag::note_class_declared);
4093 if (IDecl->hasAttr<ObjCClassStubAttr>())
4094 Diag(IC->getLocation(), diag::err_implementation_of_class_stub);
4097 while (IDecl->getSuperClass()) {
4099 IDecl = IDecl->getSuperClass();
4105 dyn_cast<ObjCCategoryImplDecl>(ClassDecl)) {
4106 CatImplClass->setAtEndRange(AtEnd);
4112 = IDecl->FindCategoryDeclaration(CatImplClass->getIdentifier())) {
4116 }
else if (
const auto *IntfDecl = dyn_cast<ObjCInterfaceDecl>(ClassDecl)) {
4118 if (!IntfDecl->hasAttr<ObjCSubclassingRestrictedAttr>() &&
4119 Super->hasAttr<ObjCSubclassingRestrictedAttr>()) {
4120 Diag(IntfDecl->getLocation(), diag::err_restricted_superclass_mismatch);
4121 Diag(Super->getLocation(), diag::note_class_declared);
4125 if (IntfDecl->hasAttr<ObjCClassStubAttr>() &&
4126 !IntfDecl->hasAttr<ObjCSubclassingRestrictedAttr>())
4127 Diag(IntfDecl->getLocation(), diag::err_class_stub_subclassing_mismatch);
4130 if (isInterfaceDeclKind) {
4132 for (
unsigned i = 0, e = allTUVars.size(); i != e; i++) {
4135 if (
VarDecl *VDecl = dyn_cast<VarDecl>(*I)) {
4136 if (!VDecl->hasExternalStorage())
4137 Diag(VDecl->getLocation(), diag::err_objc_var_decl_inclass);
4143 for (
unsigned i = 0, e = allTUVars.size(); i != e; i++) {
4146 (*I)->setTopLevelDeclInObjCContainer();
4175 if (ResultObjectType->isObjCIdType() ||
4176 ResultObjectType->isObjCQualifiedIdType())
4181 = ResultObjectType->getInterfaceDecl()) {
4187 if (ResultClass->isSuperClassOf(CurrentClass))
4203 class OverrideSearch {
4215 Sema::GlobalMethodPool::iterator it = S.
MethodPool.find(selector);
4235 dyn_cast<ObjCCategoryDecl>(container)) {
4236 searchFromContainer(container);
4238 searchFromContainer(Interface);
4240 searchFromContainer(container);
4245 iterator begin()
const {
return Overridden.begin(); }
4246 iterator end()
const {
return Overridden.end(); }
4253 #define OBJCCONTAINER(type, base) \ 4255 searchFrom(cast<type##Decl>(container)); \ 4257 #define ABSTRACT_DECL(expansion) 4258 #define DECL(type, base) \ 4260 #include "clang/AST/DeclNodes.inc" 4261 llvm_unreachable(
"not an ObjC container!");
4321 for (
const auto *Proto : protocols)
4333 Overridden.insert(meth);
4343 searchFromContainer(container);
4350 if (
const auto *attr = overridden->
getAttr<ObjCDirectAttr>()) {
4352 Diag(attr->getLocation(), diag::note_previous_declaration);
4353 }
else if (
const auto *attr = method->
getAttr<ObjCDirectAttr>()) {
4354 Diag(attr->getLocation(), diag::err_objc_direct_on_override)
4366 OverrideSearch overrides(*
this, ObjCMethod);
4372 bool hasOverriddenMethodsInBaseOrProtocol =
false;
4374 if (!hasOverriddenMethodsInBaseOrProtocol) {
4375 if (isa<ObjCProtocolDecl>(overridden->getDeclContext()) ||
4376 CurrentClass != overridden->getClassInterface() ||
4377 overridden->isOverriding()) {
4379 hasOverriddenMethodsInBaseOrProtocol =
true;
4388 GlobalMethodPool::iterator It =
4393 unsigned CategCount = List.
getBits();
4394 if (CategCount > 0) {
4397 if (CategCount > 1 ||
4398 !isa<ObjCCategoryImplDecl>(overridden->getDeclContext())) {
4399 OverrideSearch overrides(*
this, overridden);
4401 if (isa<ObjCProtocolDecl>(SuperOverridden->getDeclContext()) ||
4402 CurrentClass != SuperOverridden->getClassInterface()) {
4404 hasOverriddenMethodsInBaseOrProtocol =
true;
4405 overridden->setOverriding(
true);
4422 if (ObjCMethod->
isImplicit() && overridden->isImplicit())
4429 isa<ObjCProtocolDecl>(overridden->getDeclContext()));
4431 if (CurrentClass && overridden->
getDeclContext() != CurrentClass &&
4432 isa<ObjCInterfaceDecl>(overridden->getDeclContext()) &&
4437 PrevE = overridden->param_end();
4438 for (; ParamI != E && PrevI != PrevE; ++ParamI, ++PrevI) {
4439 assert(PrevI != overridden->param_end() &&
"Param mismatch");
4445 Diag((*ParamI)->getLocation(), diag::ext_typecheck_base_super)
4447 Diag(overridden->getLocation(), diag::note_previous_declaration);
4454 ObjCMethod->
setOverriding(hasOverriddenMethodsInBaseOrProtocol);
4464 bool prevUsesCSKeyword) {
4470 if (nullability.hasValue() == prevNullability.hasValue()) {
4476 if (*nullability == *prevNullability)
4480 S.
Diag(loc, diag::err_nullability_conflicting)
4503 if (prevMethod->
hasAttr<ObjCRequiresSuperAttr>() &&
4504 !method->
hasAttr<ObjCRequiresSuperAttr>()) {
4507 ObjCRequiresSuperAttr::CreateImplicit(S.
Context,
4524 unsigned numPrevParams = prevMethod->
param_size();
4525 for (
unsigned i = 0, n =
std::min(numParams, numPrevParams); i != n; ++i) {
4545 llvm::Triple::x86 &&
4546 "x86-specific check invoked for a different target");
4550 if (
P->getType()->isVectorType()) {
4551 Loc =
P->getBeginLoc();
4556 if (Loc.isInvalid()) {
4567 VersionTuple AcceptedInVersion;
4568 if (Triple.getOS() == llvm::Triple::IOS)
4569 AcceptedInVersion = VersionTuple(9);
4570 else if (Triple.isMacOSX())
4571 AcceptedInVersion = VersionTuple(10, 11);
4577 SemaRef.
Diag(Loc, diag::err_objc_method_unsupported_param_ret_type)
4580 << (Triple.isMacOSX() ?
"macOS 10.11" :
"iOS 9");
4592 bool isVariadic,
bool MethodDefinition) {
4595 Diag(MethodLoc, diag::err_missing_method_context);
4602 bool HasRelatedResultType =
false;
4610 QualType bareResultType = resultDeclType;
4615 Diag(MethodLoc, diag::warn_missing_method_return_type)
4620 Context, MethodLoc, EndLoc, Sel, resultDeclType, ReturnTInfo,
CurContext,
4621 MethodType == tok::minus, isVariadic,
4626 HasRelatedResultType);
4630 for (
unsigned i = 0, e = Sel.
getNumArgs(); i != e; ++i) {
4634 if (!ArgInfo[i].
Type) {
4641 LookupResult R(*
this, ArgInfo[i].Name, ArgInfo[i].NameLoc,
4647 Diag(ArgInfo[i].NameLoc,
4648 (MethodDefinition ? diag::warn_method_param_redefinition
4649 : diag::warn_method_param_declaration))
4652 diag::note_previous_declaration);
4661 ArgInfo[i].NameLoc, ArgInfo[i].Name,
4673 if (Param->
hasAttr<BlocksAttr>()) {
4680 Params.push_back(Param);
4683 for (
unsigned i = 0, e = CNumArgs; i != e; ++i) {
4686 if (ArgType.isNull())
4693 Params.push_back(Param);
4696 ObjCMethod->setMethodParams(Context, Params, SelectorLocs);
4697 ObjCMethod->setObjCDeclQualifier(
4705 if (
ObjCImplDecl *ImpDecl = dyn_cast<ObjCImplDecl>(ClassDecl)) {
4706 if (MethodType == tok::minus) {
4707 PrevMethod = ImpDecl->getInstanceMethod(Sel);
4708 ImpDecl->addInstanceMethod(ObjCMethod);
4710 PrevMethod = ImpDecl->getClassMethod(Sel);
4711 ImpDecl->addClassMethod(ObjCMethod);
4720 if (
auto *Setter = PropertyImpl->getSetterMethodDecl())
4721 if (Setter->getSelector() == Sel &&
4722 Setter->isInstanceMethod() == ObjCMethod->isInstanceMethod()) {
4723 assert(Setter->isSynthesizedAccessorStub() &&
"autosynth stub expected");
4724 PropertyImpl->setSetterMethodDecl(ObjCMethod);
4726 if (
auto *Getter = PropertyImpl->getGetterMethodDecl())
4727 if (Getter->getSelector() == Sel &&
4728 Getter->isInstanceMethod() == ObjCMethod->isInstanceMethod()) {
4729 assert(Getter->isSynthesizedAccessorStub() &&
"autosynth stub expected");
4730 PropertyImpl->setGetterMethodDecl(ObjCMethod);
4741 if (!ObjCMethod->isDirectMethod()) {
4743 if (
const auto *attr = CanonicalMD->
getAttr<ObjCDirectAttr>()) {
4745 ObjCDirectAttr::CreateImplicit(Context, attr->getLocation()));
4752 if (
auto *IMD = IDecl->lookupMethod(ObjCMethod->getSelector(),
4753 ObjCMethod->isInstanceMethod())) {
4772 if (IDecl == IMD->getClassInterface()) {
4773 auto diagContainerMismatch = [&] {
4774 int decl = 0, impl = 0;
4776 if (
auto *Cat = dyn_cast<ObjCCategoryDecl>(IMD->getDeclContext()))
4777 decl = Cat->IsClassExtension() ? 1 : 2;
4779 if (isa<ObjCCategoryImplDecl>(ImpDecl))
4780 impl = 1 + (decl != 0);
4782 Diag(ObjCMethod->getLocation(),
4783 diag::err_objc_direct_impl_decl_mismatch)
4785 Diag(IMD->getLocation(), diag::note_previous_declaration);
4788 if (
const auto *attr = ObjCMethod->getAttr<ObjCDirectAttr>()) {
4789 if (ObjCMethod->getCanonicalDecl() != IMD) {
4790 diagContainerMismatch();
4791 }
else if (!IMD->isDirectMethod()) {
4792 Diag(attr->getLocation(), diag::err_objc_direct_missing_on_decl);
4793 Diag(IMD->getLocation(), diag::note_previous_declaration);
4795 }
else if (
const auto *attr = IMD->getAttr<ObjCDirectAttr>()) {
4796 if (ObjCMethod->getCanonicalDecl() != IMD) {
4797 diagContainerMismatch();
4799 ObjCMethod->addAttr(
4800 ObjCDirectAttr::CreateImplicit(Context, attr->getLocation()));
4806 if (isa<ObjCCategoryImplDecl>(ImpDecl) && IMD->isOverriding() &&
4807 ObjCMethod->getSelector().getMethodFamily() ==
OMF_dealloc) {
4808 Diag(ObjCMethod->getLocation(), diag::warn_dealloc_in_category)
4809 << ObjCMethod->getDeclName();
4811 }
else if (ImpDecl->hasAttr<ObjCDirectMembersAttr>()) {
4812 ObjCMethod->addAttr(
4813 ObjCDirectAttr::CreateImplicit(Context, ObjCMethod->getLocation()));
4819 for (
auto *
C : IDecl->visible_categories())
4820 for (
auto &
P :
C->protocols())
4821 if (
auto *IMD =
P->lookupMethod(ObjCMethod->getSelector(),
4822 ObjCMethod->isInstanceMethod())) {
4823 assert(ObjCMethod->parameters().size() ==
4824 IMD->parameters().size() &&
4825 "Methods have different number of parameters");
4826 auto OI = IMD->param_begin(), OE = IMD->param_end();
4827 auto NI = ObjCMethod->param_begin();
4828 for (; OI != OE; ++OI, ++NI)
4833 if (!isa<ObjCProtocolDecl>(ClassDecl)) {
4834 if (!ObjCMethod->isDirectMethod() &&
4835 ClassDecl->
hasAttr<ObjCDirectMembersAttr>()) {
4836 ObjCMethod->addAttr(
4837 ObjCDirectAttr::CreateImplicit(Context, ObjCMethod->getLocation()));
4848 IDecl = cast<ObjCCategoryDecl>(ClassDecl)->getClassInterface();
4851 if (
auto *IMD = IDecl->
lookupMethod(ObjCMethod->getSelector(),
4852 ObjCMethod->isInstanceMethod(),
4855 if (isa<ObjCProtocolDecl>(IMD->getDeclContext())) {
4859 }
else if (ObjCMethod->isDirectMethod() || IMD->isDirectMethod()) {
4860 Diag(ObjCMethod->getLocation(),
4861 diag::err_objc_direct_duplicate_decl)
4862 << ObjCMethod->isDirectMethod() << IMD->isDirectMethod()
4863 << ObjCMethod->getDeclName();
4864 Diag(IMD->getLocation(), diag::note_previous_declaration);
4869 cast<DeclContext>(ClassDecl)->addDecl(ObjCMethod);
4874 Diag(ObjCMethod->getLocation(), diag::err_duplicate_method_decl)
4875 << ObjCMethod->getDeclName();
4877 ObjCMethod->setInvalidDecl();
4885 if (!CurrentClass) {
4887 CurrentClass = Cat->getClassInterface();
4888 else if (
ObjCImplDecl *Impl = dyn_cast<ObjCImplDecl>(ClassDecl))
4889 CurrentClass = Impl->getClassInterface();
4891 = dyn_cast<ObjCCategoryImplDecl>(ClassDecl))
4892 CurrentClass = CatImpl->getClassInterface();
4900 bool ARCError =
false;
4906 !ObjCMethod->hasRelatedResultType() &&
4907 LangOpts.ObjCInferRelatedResultType) {
4908 bool InferRelatedResultType =
false;
4909 switch (ObjCMethod->getMethodFamily()) {
4923 InferRelatedResultType = ObjCMethod->isClassMethod();
4930 InferRelatedResultType = ObjCMethod->isInstanceMethod();
4934 if (InferRelatedResultType &&
4935 !ObjCMethod->getReturnType()->isObjCIndependentClassType())
4936 ObjCMethod->setRelatedResultType();
4939 if (MethodDefinition &&
4945 if (
const auto *attr = ObjCMethod->getAttr<AvailabilityAttr>()) {
4946 if (ObjCMethod->isClassMethod() &&
4947 ObjCMethod->getSelector().getAsString() ==
"load") {
4948 Diag(attr->getLocation(), diag::warn_availability_on_static_initializer)
4950 ObjCMethod->dropAttr<AvailabilityAttr>();
4955 ObjCMethod->createImplicitParams(Context, ObjCMethod->getClassInterface());
4973 Diag(D->
getLocation(), diag::err_objc_decls_may_only_appear_in_global_scope);
4987 Diag(DeclStart, diag::err_undef_interface) << ClassName;
4991 Diag(DeclStart, diag::err_atdef_nonfragile_interface);
4999 for (
unsigned i = 0; i < Ivars.size(); i++) {
5007 Decls.push_back(FD);
5012 D != Decls.end(); ++D) {
5016 else if (
RecordDecl *Record = dyn_cast<RecordDecl>(TagD))
5017 Record->addDecl(FD);
5032 Diag(IdLoc, diag::err_arg_with_address_space);
5044 Diag(IdLoc, diag::err_illegal_qualifiers_on_catch_parm);
5049 Diag(IdLoc, diag::err_catch_param_not_objc_type);
5052 Diag(IdLoc, diag::err_catch_param_not_objc_type);
5085 diag::err_invalid_thread)
5119 if (New->
hasAttr<BlocksAttr>())
5132 Ivars.push_back(Iv);
5138 if (ExternalSource) {
5140 ExternalSource->ReadReferencedSelectors(Sels);
5141 for (
unsigned I = 0, N = Sels.size(); I != N; ++I)
5152 Selector Sel = SelectorAndLocation.first;
5155 Diag(Loc, diag::warn_unimplemented_selector) << Sel;
5178 IV->getIdentifier());
5187 class UnusedBackingIvarChecker :
5194 bool InvokedSelfMethod;
5198 : S(S), Method(Method), IvarD(IvarD),
5199 AccessedIvar(
false), InvokedSelfMethod(
false) {
5205 AccessedIvar =
true;
5214 InvokedSelfMethod =
true;
5227 unsigned DIAG = diag::warn_unused_property_backing_ivar;
5237 if (CurMethod->isSynthesizedAccessorStub())
5240 UnusedBackingIvarChecker Checker(*
this, CurMethod, IV);
5241 Checker.TraverseStmt(CurMethod->getBody());
5242 if (Checker.AccessedIvar)
5249 if (!IV->
isReferenced() || !Checker.InvokedSelfMethod) {
5250 Diag(Loc, DIAG) << IV;
Decl * ActOnAtEnd(Scope *S, SourceRange AtEnd, ArrayRef< Decl *> allMethods=None, ArrayRef< DeclGroupPtrTy > allTUVars=None)
const ObjCInterfaceType * getInterfaceType() const
If this pointer points to an Objective C @interface type, gets the type for that interface.
const internal::VariadicAllOfMatcher< Type > type
Matches Types in the clang AST.
Defines the clang::ASTContext interface.
bool hasDefinition() const
Determine whether this class has been defined.
static bool tryMatchRecordTypes(ASTContext &Context, Sema::MethodMatchStrategy strategy, const Type *left, const Type *right)
ObjCIvarDecl * GetIvarBackingPropertyAccessor(const ObjCMethodDecl *Method, const ObjCPropertyDecl *&PDecl) const
GetIvarBackingPropertyAccessor - If method is a property setter/getter and it property has a backing ...
void DiagnoseClassExtensionDupMethods(ObjCCategoryDecl *CAT, ObjCInterfaceDecl *ID)
DiagnoseClassExtensionDupMethods - Check for duplicate declaration of a class method in its extension...
bool isClassMethod() const
Decl * ActOnStartCategoryInterface(SourceLocation AtInterfaceLoc, IdentifierInfo *ClassName, SourceLocation ClassLoc, ObjCTypeParamList *typeParamList, IdentifierInfo *CategoryName, SourceLocation CategoryLoc, Decl *const *ProtoRefs, unsigned NumProtoRefs, const SourceLocation *ProtoLocs, SourceLocation EndProtoLoc, const ParsedAttributesView &AttrList)
void setImplicit(bool I=true)
ParsedType CreateParsedType(QualType T, TypeSourceInfo *TInfo)
Package the given type and TSI into a ParsedType.
bool isSelfExpr(Expr *RExpr)
Private Helper predicate to check for 'self'.
The receiver is an object instance.
void setEndOfDefinitionLoc(SourceLocation LE)
VersionTuple getPlatformMinVersion() const
Retrieve the minimum desired version of the platform, to which the program should be compiled...
ExternalSemaSource * getExternalSource() const
bool isObjCQualifiedIdType() const
True if this is equivalent to 'id.
Smart pointer class that efficiently represents Objective-C method names.
QualType getObjCIdType() const
Represents the Objective-CC id type.
QualType getAdjustedParameterType(QualType T) const
Perform adjustment on the parameter type of a function.
void PushExpressionEvaluationContext(ExpressionEvaluationContext NewContext, Decl *LambdaContextDecl=nullptr, ExpressionEvaluationContextRecord::ExpressionKind Type=ExpressionEvaluationContextRecord::EK_Other)
PointerType - C99 6.7.5.1 - Pointer Declarators.
A (possibly-)qualified type.
Simple class containing the result of Sema::CorrectTypo.
void setStarLoc(SourceLocation Loc)
unsigned param_size() const
ObjCInterfaceDecl * getClassInterface()
all_protocol_range all_referenced_protocols() const
ObjCInterfaceDecl * getClassInterface()
void startDefinition()
Starts the definition of this Objective-C class, taking it from a forward declaration (@class) to a d...
bool AreMultipleMethodsInGlobalPool(Selector Sel, ObjCMethodDecl *BestMethod, SourceRange R, bool receiverIdOrClass, SmallVectorImpl< ObjCMethodDecl *> &Methods)
ObjCDeclQualifier getObjCDeclQualifier() const
static QualType getObjectType(APValue::LValueBase B)
Retrieves the "underlying object type" of the given expression, as used by __builtin_object_size.
llvm::DenseSet< IdentifierInfo * > ProtocolNameSet
FIXME: Type hierarchies in Objective-C can be deep.
Ordinary name lookup, which finds ordinary names (functions, variables, typedefs, etc...
bool LookupName(LookupResult &R, Scope *S, bool AllowBuiltinCreation=false)
Perform unqualified name lookup starting from a given scope.
Look up the name of an Objective-C protocol.
const ObjCProtocolList & getReferencedProtocols() const
Expr * getBitWidth() const
QualType getPointeeType() const
If this is a pointer, ObjC object pointer, or block pointer, this returns the respective pointee...
const llvm::Triple & getTriple() const
Returns the target triple of the primary target.
ObjCMethodDecl * LookupMethodInObjectType(Selector Sel, QualType Ty, bool IsInstance)
LookupMethodInType - Look up a method in an ObjCObjectType.
static bool CheckMethodOverrideParam(Sema &S, ObjCMethodDecl *MethodImpl, ObjCMethodDecl *MethodDecl, ParmVarDecl *ImplVar, ParmVarDecl *IfaceVar, bool IsProtocolMethodDecl, bool IsOverridingMode, bool Warn)
Defines the SourceManager interface.
void ActOnDocumentableDecl(Decl *D)
Should be called on all declarations that might have attached documentation comments.
bool isRecordType() const
SemaDiagnosticBuilder Diag(SourceLocation Loc, unsigned DiagID)
Emit a diagnostic.
Decl - This represents one declaration (or definition), e.g.
void DiagnoseMissingDesignatedInitOverrides(const ObjCImplementationDecl *ImplD, const ObjCInterfaceDecl *IFD)
__DEVICE__ long long abs(long long __n)
void ProcessDeclAttributeList(Scope *S, Decl *D, const ParsedAttributesView &AL, bool IncludeCXX11Attributes=true)
Captures information about "declaration specifiers" specific to Objective-C.
ObjCTypeParamList * actOnObjCTypeParamList(Scope *S, SourceLocation lAngleLoc, ArrayRef< Decl *> typeParams, SourceLocation rAngleLoc)
void DiagnoseFunctionSpecifiers(const DeclSpec &DS)
Diagnose function specifiers on a declaration of an identifier that does not identify a function...
Scope * TUScope
Translation Unit Scope - useful to Objective-C actions that need to lookup file scope declarations in...
static ObjCMethodDecl * Create(ASTContext &C, SourceLocation beginLoc, SourceLocation endLoc, Selector SelInfo, QualType T, TypeSourceInfo *ReturnTInfo, DeclContext *contextDecl, bool isInstance=true, bool isVariadic=false, bool isPropertyAccessor=false, bool isSynthesizedAccessorStub=false, bool isImplicitlyDeclared=false, bool isDefined=false, ImplementationControl impControl=None, bool HasRelatedResultType=false)
static ObjCProtocolDecl * Create(ASTContext &C, DeclContext *DC, IdentifierInfo *Id, SourceLocation nameLoc, SourceLocation atStartLoc, ObjCProtocolDecl *PrevDecl)
static bool NestedProtocolHasNoDefinition(ObjCProtocolDecl *PDecl, ObjCProtocolDecl *&UndefinedProtocol)
known_categories_range known_categories() const
ObjCTypeParamList * getTypeParamList() const
Retrieve the type parameters of this class.
bool CheckForwardProtocolDeclarationForCircularDependency(IdentifierInfo *PName, SourceLocation &PLoc, SourceLocation PrevLoc, const ObjCList< ObjCProtocolDecl > &PList)
The base class of the type hierarchy.
void AddFactoryMethodToGlobalPool(ObjCMethodDecl *Method, bool impl=false)
AddFactoryMethodToGlobalPool - Same as above, but for factory methods.
The parameter is covariant, e.g., X<T> is a subtype of X<U> when the type parameter is covariant and ...
CanQual< T > getUnqualifiedType() const
Retrieve the unqualified form of this type.
bool isCompilingModule() const
Are we compiling a module interface (.cppm or module map)?
bool isObjCContainer() const
SourceLocation getLocForEndOfToken(SourceLocation Loc, unsigned Offset=0)
Calls Lexer::getLocForEndOfToken()
const ObjCObjectPointerType * getAsObjCInterfacePointerType() const
static const char * getSpecifierName(DeclSpec::TST T, const PrintingPolicy &Policy)
Turn a type-specifier-type into a string like "_Bool" or "union".
SourceLocation getEndLoc() const LLVM_READONLY
const TargetInfo & getTargetInfo() const
A container of type source information.
void ProcessPropertyDecl(ObjCPropertyDecl *property)
Process the specified property declaration and create decls for the setters and getters as needed...
ObjCMethodDecl * getMethod() const
TSCS getThreadStorageClassSpec() const
void ActOnTypedefedProtocols(SmallVectorImpl< Decl *> &ProtocolRefs, SmallVectorImpl< SourceLocation > &ProtocolLocs, IdentifierInfo *SuperName, SourceLocation SuperLoc)
ActOnTypedefedProtocols - this action finds protocol list as part of the typedef'ed use for a qualifi...
param_const_iterator param_end() const
SourceLocation getEndLoc() const
Get the end source location.
void createImplicitParams(ASTContext &Context, const ObjCInterfaceDecl *ID)
createImplicitParams - Used to lazily create the self and cmd implict parameters. ...
Represents a variable declaration or definition.
void setImplementation(ObjCCategoryImplDecl *ImplD)
PartialDiagnostic PDiag(unsigned DiagID=0)
Build a partial diagnostic.
Information about one declarator, including the parsed type information and the identifier.
DiagnosticsEngine & Diags
const T * getAs() const
Member-template getAs<specific type>'.
ObjCCategoryImplDecl * getImplementation() const
static void WarnUndefinedMethod(Sema &S, SourceLocation ImpLoc, ObjCMethodDecl *method, bool &IncompleteImpl, unsigned DiagID, NamedDecl *NeededFor=nullptr)
ObjCMethodDecl - Represents an instance or class method declaration.
DeclClass * getCorrectionDeclAs() const
bool isInvalidDecl() const
classmeth_range class_methods() const
llvm::MapVector< Selector, SourceLocation > ReferencedSelectors
Method selectors used in a @selector expression.
protocol_range protocols() const
static const NamedDecl * getDefinition(const Decl *D)
Represents a parameter to a function.
The collection of all-type qualifiers we support.
const ObjCInterfaceDecl * getSuperClass() const
IdentifierInfo * getIdentifier() const
Get the identifier that names this declaration, if there is one.
Base wrapper for a particular "section" of type source info.
Represents a struct/union/class.
SourceLocation getVarianceLoc() const
Retrieve the location of the variance keyword.
DeclarationName getDeclName() const
Get the actual, stored name of the declaration, which may be a special name.
One of these records is kept for each identifier that is lexed.
std::unique_ptr< NSAPI > NSAPIObj
Caches identifiers/selectors for NSFoundation APIs.
static void checkObjCMethodX86VectorTypes(Sema &SemaRef, const ObjCMethodDecl *Method)
Verify that the method parameters/return value have types that are supported by the x86 target...
const ObjCProtocolList & getReferencedProtocols() const
Represents a class type in Objective C.
Holds long-lived AST nodes (such as types and decls) that can be referred to throughout the semantic ...
ObjCMethodDecl * getClassMethod(Selector Sel, bool AllowHidden=false) const
const ParmVarDecl *const * param_const_iterator
bool isObjCLifetimeType() const
Returns true if objects of this type have lifetime semantics under ARC.
ObjCMethodFamily
A family of Objective-C methods.
The parameter is contravariant, e.g., X<T> is a subtype of X<U> when the type parameter is covariant ...
Base class for callback objects used by Sema::CorrectTypo to check the validity of a potential typo c...
void set(T *const *InList, unsigned Elts, ASTContext &Ctx)
TypeSourceInfo * getTypeSourceInfo(ASTContext &Context, QualType T)
Creates a TypeSourceInfo for the given type.
SourceLocation getBeginLoc() const LLVM_READONLY
bool isObjCIdType() const
Represents a member of a struct/union/class.
SourceRange getReturnTypeSourceRange() const
instmeth_range instance_methods() const
void setSuperClass(TypeSourceInfo *superClass)
method_range methods() const
SourceRange getSourceRange() const
bool ObjCQualifiedIdTypesAreCompatible(const ObjCObjectPointerType *LHS, const ObjCObjectPointerType *RHS, bool ForCompare)
ObjCQualifiedIdTypesAreCompatible - We know that one of lhs/rhs is an ObjCQualifiedIDType.
DeclGroupPtrTy ActOnForwardClassDeclaration(SourceLocation Loc, IdentifierInfo **IdentList, SourceLocation *IdentLocs, ArrayRef< ObjCTypeParamList *> TypeParamLists, unsigned NumElts)
void ClearStorageClassSpecs()
void setReturnType(QualType T)
static DeclaratorChunk getPointer(unsigned TypeQuals, SourceLocation Loc, SourceLocation ConstQualLoc, SourceLocation VolatileQualLoc, SourceLocation RestrictQualLoc, SourceLocation AtomicQualLoc, SourceLocation UnalignedQualLoc)
Return a DeclaratorChunk for a pointer.
static bool checkTypeParamListConsistency(Sema &S, ObjCTypeParamList *prevTypeParams, ObjCTypeParamList *newTypeParams, TypeParamListContext newContext)
Check consistency between two Objective-C type parameter lists, e.g., between a category/extension an...
bool isObjCQualifiedClassType() const
static bool FilterMethodsByTypeBound(ObjCMethodDecl *Method, const ObjCObjectType *TypeBound)
Return true if the given method is wthin the type bound.
void CheckExtraCXXDefaultArguments(Declarator &D)
CheckExtraCXXDefaultArguments - Check for any extra default arguments in the declarator, which is not a function declaration or definition and therefore is not permitted to have default arguments.
llvm::BumpPtrAllocator BumpAlloc
Qualifiers getLocalQualifiers() const
Retrieve the set of qualifiers local to this particular QualType instance, not including any qualifie...
bool isInvalidType() const
bool isUnarySelector() const
bool isDeprecated(std::string *Message=nullptr) const
Determine whether this declaration is marked 'deprecated'.
ObjCMethodFamily getMethodFamily() const
Determines the family of this method.
void MatchAllMethodDeclarations(const SelectorSet &InsMap, const SelectorSet &ClsMap, SelectorSet &InsMapSeen, SelectorSet &ClsMapSeen, ObjCImplDecl *IMPDecl, ObjCContainerDecl *IDecl, bool &IncompleteImpl, bool ImmediateClass, bool WarnCategoryMethodImpl=false)
MatchAllMethodDeclarations - Check methods declaraed in interface or or protocol against those declar...
bool checkInitMethod(ObjCMethodDecl *method, QualType receiverTypeIfCall)
Check whether the given method, which must be in the 'init' family, is a valid member of that family...
bool isDirectMethod() const
True if the method is tagged as objc_direct.
void setMethod(ObjCMethodDecl *M)
bool isBitField() const
Determines whether this field is a bitfield.
bool isNonFragile() const
Does this runtime follow the set of implied behaviors for a "non-fragile" ABI?
Represents the results of name lookup.
ObjCMethodDecl * LookupImplementedMethodInGlobalPool(Selector Sel)
LookupImplementedMethodInGlobalPool - Returns the method which has an implementation.
bool isNeXTFamily() const
Is this runtime basically of the NeXT family of runtimes?
void mergeDeclAttributes(NamedDecl *New, Decl *Old, AvailabilityMergeKind AMK=AMK_Redeclaration)
mergeDeclAttributes - Copy attributes from the Old decl to the New one.
static ObjCInterfaceDecl * Create(const ASTContext &C, DeclContext *DC, SourceLocation atLoc, IdentifierInfo *Id, ObjCTypeParamList *typeParamList, ObjCInterfaceDecl *PrevDecl, SourceLocation ClassLoc=SourceLocation(), bool isInternal=false)
ObjCContainerDecl - Represents a container for method declarations.
ObjCMethodDecl * getCurMethodDecl()
getCurMethodDecl - If inside of a method body, this returns a pointer to the method decl for the meth...
bool isReferenced() const
Whether any declaration of this entity was referenced.
static ObjCCategoryDecl * Create(ASTContext &C, DeclContext *DC, SourceLocation AtLoc, SourceLocation ClassNameLoc, SourceLocation CategoryNameLoc, IdentifierInfo *Id, ObjCInterfaceDecl *IDecl, ObjCTypeParamList *typeParamList, SourceLocation IvarLBraceLoc=SourceLocation(), SourceLocation IvarRBraceLoc=SourceLocation())
SCS
storage-class-specifier
void CollectIvarsToConstructOrDestruct(ObjCInterfaceDecl *OI, SmallVectorImpl< ObjCIvarDecl *> &Ivars)
CollectIvarsToConstructOrDestruct - Collect those ivars which require initialization.
DeclGroupPtrTy BuildDeclaratorGroup(MutableArrayRef< Decl *> Group)
BuildDeclaratorGroup - convert a list of declarations into a declaration group, performing any necess...
Decl * ActOnObjCContainerStartDefinition(Decl *IDecl)
void RemoveDecl(NamedDecl *D)
RemoveDecl - Unlink the decl from its shadowed decl chain.
void ActOnDefs(Scope *S, Decl *TagD, SourceLocation DeclStart, IdentifierInfo *ClassName, SmallVectorImpl< Decl *> &Decls)
Called whenever @defs(ClassName) is encountered in the source.
SourceLocation getBeginLoc() const LLVM_READONLY
const clang::PrintingPolicy & getPrintingPolicy() const
Selector GetNullarySelector(StringRef name, ASTContext &Ctx)
Utility function for constructing a nullary selector.
GlobalMethodPool MethodPool
Method Pool - allows efficient lookup when typechecking messages to "id".
Represents a declaration of a type.
static ObjCAtDefsFieldDecl * Create(ASTContext &C, DeclContext *DC, SourceLocation StartLoc, SourceLocation IdLoc, IdentifierInfo *Id, QualType T, Expr *BW)
void setExceptionVariable(bool EV)
void FindProtocolDeclaration(bool WarnOnDeclarations, bool ForObjCContainer, ArrayRef< IdentifierLocPair > ProtocolId, SmallVectorImpl< Decl *> &Protocols)
FindProtocolDeclaration - This routine looks up protocols and issues an error if they are not declare...
ObjCProtocolDecl * getDefinition()
Retrieve the definition of this protocol, if any.
Scope - A scope is a transient data structure that is used while parsing the program.
const ObjCMethodDecl * SelectorsForTypoCorrection(Selector Sel, QualType ObjectType=QualType())
static bool CheckMethodOverrideReturn(Sema &S, ObjCMethodDecl *MethodImpl, ObjCMethodDecl *MethodDecl, bool IsProtocolMethodDecl, bool IsOverridingMode, bool Warn)
field_iterator field_begin() const
unsigned getBitWidthValue(const ASTContext &Ctx) const
bool declaresSameEntity(const Decl *D1, const Decl *D2)
Determine whether two declarations declare the same entity.
void setAsRedeclaration(const ObjCMethodDecl *PrevMethod)
Represents an Objective-C protocol declaration.
static VarDecl * Create(ASTContext &C, DeclContext *DC, SourceLocation StartLoc, SourceLocation IdLoc, IdentifierInfo *Id, QualType T, TypeSourceInfo *TInfo, StorageClass S)
const LangOptions & getLangOpts() const
const CXXScopeSpec & getCXXScopeSpec() const
getCXXScopeSpec - Return the C++ scope specifier (global scope or nested-name-specifier) that is part...
bool isScalarType() const
void setProtocolList(ObjCProtocolDecl *const *List, unsigned Num, const SourceLocation *Locs, ASTContext &C)
setProtocolList - Set the list of protocols that this interface implements.
Decl * ActOnObjCExceptionDecl(Scope *S, Declarator &D)
bool hasExplicitBound() const
Whether this type parameter has an explicitly-written type bound, e.g., "T : NSView".
SmallVector< BoundNodes, 1 > match(MatcherT Matcher, const NodeT &Node, ASTContext &Context)
Returns the results of matching Matcher on Node.
A class that does preorder or postorder depth-first traversal on the entire Clang AST and visits each...
Represents an ObjC class declaration.
QualType getReturnType() const
ObjCInterfaceDecl * getInterface() const
Gets the interface declaration for this object type, if the base type really is an interface...
const T * getTypePtr() const
Retrieve the underlying type pointer, which refers to a canonical type.
IdentifierInfo * getIdentifier() const
const LangOptions & LangOpts
ObjCMethodDecl * getCanonicalDecl() override
Retrieves the "canonical" declaration of the given declaration.
This object can be modified without requiring retains or releases.
void AtomicPropertySetterGetterRules(ObjCImplDecl *IMPDecl, ObjCInterfaceDecl *IDecl)
AtomicPropertySetterGetterRules - This routine enforces the rule (via warning) when atomic property h...
TyLocType push(QualType T)
Pushes space for a new TypeLoc of the given type.
void AddInstanceMethodToGlobalPool(ObjCMethodDecl *Method, bool impl=false)
AddInstanceMethodToGlobalPool - All instance methods in a translation unit are added to a global pool...
void CheckObjCMethodOverrides(ObjCMethodDecl *ObjCMethod, ObjCInterfaceDecl *CurrentClass, ResultTypeCompatibilityKind RTC)
AvailabilityResult
Captures the result of checking the availability of a declaration.
static Decl::ObjCDeclQualifier CvtQTToAstBitMask(ObjCDeclSpec::ObjCDeclQualifier PQTVal)
CvtQTToAstBitMask - utility routine to produce an AST bitmask for objective-c's type qualifier from t...
ObjCPropertyImplDecl - Represents implementation declaration of a property in a class or category imp...
TypeResult actOnObjCTypeArgsAndProtocolQualifiers(Scope *S, SourceLocation Loc, ParsedType BaseType, SourceLocation TypeArgsLAngleLoc, ArrayRef< ParsedType > TypeArgs, SourceLocation TypeArgsRAngleLoc, SourceLocation ProtocolLAngleLoc, ArrayRef< Decl *> Protocols, ArrayRef< SourceLocation > ProtocolLocs, SourceLocation ProtocolRAngleLoc)
Build a specialized and/or protocol-qualified Objective-C type.
static bool isAcceptableMethodMismatch(ObjCMethodDecl *chosen, ObjCMethodDecl *other)
Determines if this is an "acceptable" loose mismatch in the global method pool.
DeclSpec & getMutableDeclSpec()
getMutableDeclSpec - Return a non-const version of the DeclSpec.
Sema - This implements semantic analysis and AST building for C.
visible_extensions_range visible_extensions() const
AvailabilityResult getAvailability(std::string *Message=nullptr, VersionTuple EnclosingVersion=VersionTuple(), StringRef *RealizedPlatform=nullptr) const
Determine the availability of the given declaration.
ResultTypeCompatibilityKind
Describes the compatibility of a result type with its method.
llvm::SmallPtrSet< Selector, 8 > SelectorSet
bool inferObjCARCLifetime(ValueDecl *decl)
void SetRangeStart(SourceLocation Loc)
void AddAnyMethodToGlobalPool(Decl *D)
AddAnyMethodToGlobalPool - Add any method, instance or factory to global pool.
bool hasQualifiers() const
Determine whether this type has any qualifiers.
DeclGroupPtrTy ActOnForwardProtocolDeclaration(SourceLocation AtProtoclLoc, ArrayRef< IdentifierLocPair > IdentList, const ParsedAttributesView &attrList)
ActOnForwardProtocolDeclaration - Handle @protocol foo;.
SourceRange getRange() const
void ActOnSuperClassOfClassInterface(Scope *S, SourceLocation AtInterfaceLoc, ObjCInterfaceDecl *IDecl, IdentifierInfo *ClassName, SourceLocation ClassLoc, IdentifierInfo *SuperName, SourceLocation SuperLoc, ArrayRef< ParsedType > SuperTypeArgs, SourceRange SuperTypeArgsRange)
DeclGroupPtrTy ActOnFinishObjCImplementation(Decl *ObjCImpDecl, ArrayRef< Decl *> Decls)
TypeSourceInfo * getTrivialTypeSourceInfo(QualType T, SourceLocation Loc=SourceLocation()) const
Allocate a TypeSourceInfo where all locations have been initialized to a given location, which defaults to the empty location.
void ReadMethodPool(Selector Sel)
Read the contents of the method pool for a given selector from external storage.
bool AnyObjCImplementation()
Return true if there is at least one @implementation in the TU.
unsigned ivar_size() const
TypeSourceInfo * getTypeSourceInfo() const
bool hasDefinition() const
Determine whether this protocol has a definition.
void DeepCollectObjCIvars(const ObjCInterfaceDecl *OI, bool leafClass, SmallVectorImpl< const ObjCIvarDecl *> &Ivars) const
DeepCollectObjCIvars - This routine first collects all declared, but not synthesized, ivars in super class and then collects all ivars, including those synthesized for current class.
SourceLocation getBeginLoc() const
Get the begin source location.
Type source information for an attributed type.
LookupNameKind
Describes the kind of name lookup to perform.
ObjCMethodList * getNext() const
bool isDeclScope(Decl *D)
isDeclScope - Return true if this is the scope that the specified decl is declared in...
ivar_iterator ivar_begin() const
bool isInSystemHeader(SourceLocation Loc) const
Returns if a SourceLocation is in a system header.
static Kind getNullabilityAttrKind(NullabilityKind kind)
Retrieve the attribute kind corresponding to the given nullability kind.
This file defines the classes used to store parsed information about declaration-specifiers and decla...
const T * castAs() const
Member-template castAs<specific type>.
TypeResult ActOnTypeName(Scope *S, Declarator &D)
T getAs() const
Convert to the specified TypeLoc type, returning a null TypeLoc if this TypeLoc is not of the desired...
bool hasRelatedResultType() const
Determine whether this method has a result type that is related to the message receiver's type...
static void DiagnoseObjCImplementedDeprecations(Sema &S, const NamedDecl *ND, SourceLocation ImplLoc)
const internal::VariadicAllOfMatcher< Decl > decl
Matches declarations.
void setInvalidDecl(bool Invalid=true)
setInvalidDecl - Indicates the Decl had a semantic error.
bool isThisDeclarationADefinition() const
Determine whether this particular declaration is also the definition.
SourceLocation getThreadStorageClassSpecLoc() const
bool isImplicit() const
isImplicit - Indicates whether the declaration was implicitly generated by the implementation.
void setAtEndRange(SourceRange atEnd)
void ActOnStartOfObjCMethodDef(Scope *S, Decl *D)
ActOnStartOfObjCMethodDef - This routine sets up parameters; invisible and user declared, in the method definition's AST.
void setRelatedResultType(bool RRT=true)
Note whether this method has a related result type.
field_iterator field_end() const
static ObjCTypeParamDecl * Create(ASTContext &ctx, DeclContext *dc, ObjCTypeParamVariance variance, SourceLocation varianceLoc, unsigned index, SourceLocation nameLoc, IdentifierInfo *name, SourceLocation colonLoc, TypeSourceInfo *boundInfo)
bool isFileContext() const
StringRef getNameForSlot(unsigned argIndex) const
Retrieve the name at a given position in the selector.
bool isObjCClassType() const
DeclContext * getDeclContext()
bool isObjCIdType() const
True if this is equivalent to the 'id' type, i.e.
ObjCInterfaceDecl * getSuperClass() const
static ObjCTypeParamList * create(ASTContext &ctx, SourceLocation lAngleLoc, ArrayRef< ObjCTypeParamDecl *> typeParams, SourceLocation rAngleLoc)
Create a new Objective-C type parameter list.
void ProcessDeclAttributes(Scope *S, Decl *D, const Declarator &PD)
ScalarTypeKind getScalarTypeKind() const
Given that this is a scalar type, classify it.
void setDefined(bool isDefined)
bool RequireCompleteType(SourceLocation Loc, QualType T, TypeDiagnoser &Diagnoser)
Ensure that the type T is a complete type.
SourceLocation getStorageClassSpecLoc() const
ParmVarDecl *const * param_iterator
void setImplementation(ObjCImplementationDecl *ImplD)
static Optional< NullabilityKind > stripOuterNullability(QualType &T)
Strip off the top-level nullability annotation on the given type, if it's there.
void mergeClassExtensionProtocolList(ObjCProtocolDecl *const *List, unsigned Num, ASTContext &C)
mergeClassExtensionProtocolList - Merge class extension's protocol list into the protocol list for th...
ObjCIvarDecl * lookupInstanceVariable(IdentifierInfo *IVarName, ObjCInterfaceDecl *&ClassDeclared)
static void DiagnoseWeakIvars(Sema &S, ObjCImplementationDecl *ID)
Diagnose attempts to define ARC-__weak ivars when __weak is disabled.
bool isSingleResult() const
Determines if this names a single result which is not an unresolved value using decl.
clang::ObjCRuntime ObjCRuntime
propimpl_range property_impls() const
bool hasSameNullabilityTypeQualifier(QualType SubT, QualType SuperT, bool IsParam) const
An expression that sends a message to the given Objective-C object or class.
static void DiagnoseVariableSizedIvars(Sema &S, ObjCContainerDecl *OCD)
void WarnConflictingTypedMethods(ObjCMethodDecl *Method, ObjCMethodDecl *MethodDecl, bool IsProtocolMethodDecl)
QualType getObjCInterfaceType(const ObjCInterfaceDecl *Decl, ObjCInterfaceDecl *PrevDecl=nullptr) const
getObjCInterfaceType - Return the unique reference to the type for the specified ObjC interface decl...
SourceLocation getEnd() const
bool isInstanceMethod() const
ReceiverKind getReceiverKind() const
Determine the kind of receiver that this message is being sent to.
void DiagnoseTypeArgsAndProtocols(IdentifierInfo *ProtocolId, SourceLocation ProtocolLoc, IdentifierInfo *TypeArgId, SourceLocation TypeArgLoc, bool SelectProtocolFirst=false)
unsigned getNumArgs() const
void addMethodToGlobalList(ObjCMethodList *List, ObjCMethodDecl *Method)
Add the given method to the list of globally-known methods.
void PushOnScopeChains(NamedDecl *D, Scope *S, bool AddToContext=true)
Add this decl to the scope shadowed decl chains.
void CollectInheritedProtocols(const Decl *CDecl, llvm::SmallPtrSet< ObjCProtocolDecl *, 8 > &Protocols)
CollectInheritedProtocols - Collect all protocols in current class and those inherited by it...
Selector getSelector() const
QualType getTypeDeclType(const TypeDecl *Decl, const TypeDecl *PrevDecl=nullptr) const
Return the unique reference to the type for the specified type declaration.
NamedDecl * LookupSingleName(Scope *S, DeclarationName Name, SourceLocation Loc, LookupNameKind NameKind, RedeclarationKind Redecl=NotForRedeclaration)
Look up a name, looking for a single declaration.
bool isNull() const
Return true if this QualType doesn't point to a type yet.
ImplicitParamDecl * getSelfDecl() const
void removeCVRQualifiers(unsigned mask)
ObjCTypeParamVariance
Describes the variance of a given generic parameter.
ObjCKeywordKind
Provides a namespace for Objective-C keywords which start with an '@'.
void setDeclContext(DeclContext *DC)
setDeclContext - Set both the semantic and lexical DeclContext to DC.
QualType getAttributedType(attr::Kind attrKind, QualType modifiedType, QualType equivalentType)
bool isSynthesizedAccessorStub() const
ObjCDeclQualifier
ObjCDeclQualifier - Qualifier used on types in method declarations.
void DiagnoseDuplicateIvars(ObjCInterfaceDecl *ID, ObjCInterfaceDecl *SID)
DiagnoseDuplicateIvars - Check for duplicate ivars in the entire class at the start of @implementatio...
static ObjCCompatibleAliasDecl * Create(ASTContext &C, DeclContext *DC, SourceLocation L, IdentifierInfo *Id, ObjCInterfaceDecl *aliasedClass)
Decl::Kind getDeclKind() const
void makeDeclVisibleInContext(NamedDecl *D)
Makes a declaration visible within this context.
std::string getAsString() const
Derive the full selector name (e.g.
SelectorTable & Selectors
ActionResult - This structure is used while parsing/acting on expressions, stmts, etc...
static void findProtocolsWithExplicitImpls(const ObjCProtocolDecl *PDecl, ProtocolNameSet &PNS)
static bool IsVariableSizedType(QualType T)
SCS getStorageClassSpec() const
ASTContext & getASTContext() const
StringRef getPlatformName() const
Retrieve the name of the platform as it is used in the availability attribute.
Encodes a location in the source.
IdentifierInfo & get(StringRef Name)
Return the identifier token info for the specified named identifier.
void setTopLevelDeclInObjCContainer(bool V=true)
bool CheckParmsForFunctionDef(ArrayRef< ParmVarDecl *> Parameters, bool CheckParameterNames)
Helpers for dealing with blocks and functions.
ivar_iterator ivar_end() const
void CheckImplementationIvars(ObjCImplementationDecl *ImpDecl, ObjCIvarDecl **Fields, unsigned nIvars, SourceLocation Loc)
CheckImplementationIvars - This routine checks if the instance variables listed in the implelementati...
LangAS getAddressSpace() const
Return the address space of this type.
Interfaces are the core concept in Objective-C for object oriented design.
std::pair< NullabilityKind, bool > DiagNullabilityKind
A nullability kind paired with a bit indicating whether it used a context-sensitive keyword...
static bool diagnoseNoescape(const ParmVarDecl *NewD, const ParmVarDecl *OldD, Sema &S)
Issue a warning if the parameter of the overridden method is non-escaping but the parameter of the ov...
static void mergeInterfaceMethodToImpl(Sema &S, ObjCMethodDecl *method, ObjCMethodDecl *prevMethod)
Merge information from the declaration of a method in the @interface (or a category/extension) into t...
The nullability qualifier is set when the nullability of the result or parameter was expressed via a ...
Decl * ActOnStartClassImplementation(SourceLocation AtClassImplLoc, IdentifierInfo *ClassName, SourceLocation ClassLoc, IdentifierInfo *SuperClassname, SourceLocation SuperClassLoc, const ParsedAttributesView &AttrList)
static bool objcModifiersConflict(Decl::ObjCDeclQualifier x, Decl::ObjCDeclQualifier y)
Determine whether two set of Objective-C declaration qualifiers conflict.
ObjCCategoryDecl * getCategoryDecl() const
bool ObjCWarnForNoDesignatedInitChain
This starts true for a method marked as designated initializer and will be set to false if there is a...
void CheckObjCMethodOverride(ObjCMethodDecl *NewMethod, const ObjCMethodDecl *Overridden)
Check whether the given new method is a valid override of the given overridden method, and set any properties that should be inherited.
QualType getBaseElementType(const ArrayType *VAT) const
Return the innermost element type of an array type.
static QualType mergeTypeNullabilityForRedecl(Sema &S, SourceLocation loc, QualType type, bool usesCSKeyword, SourceLocation prevLoc, QualType prevType, bool prevUsesCSKeyword)
Merge type nullability from for a redeclaration of the same entity, producing the updated type of the...
std::unique_ptr< ProtocolNameSet > LazyProtocolNameSet
void DiagnoseUseOfUnimplementedSelectors()
void setProtocolList(ObjCProtocolDecl *const *List, unsigned Num, const SourceLocation *Locs, ASTContext &C)
setProtocolList - Set the list of protocols that this interface implements.
static bool isObjCTypeSubstitutable(ASTContext &Context, const ObjCObjectPointerType *A, const ObjCObjectPointerType *B, bool rejectId)
Determines if type B can be substituted for type A.
ObjCInterfaceDecl * lookupInheritedClass(const IdentifierInfo *ICName)
lookupInheritedClass - This method returns ObjCInterfaceDecl * of the super class whose name is passe...
ObjCCategoryDecl - Represents a category declaration.
TokenKind
Provides a simple uniform namespace for tokens from all C languages.
void setOverriding(bool IsOver)
TypoCorrection CorrectTypo(const DeclarationNameInfo &Typo, Sema::LookupNameKind LookupKind, Scope *S, CXXScopeSpec *SS, CorrectionCandidateCallback &CCC, CorrectTypoKind Mode, DeclContext *MemberContext=nullptr, bool EnteringContext=false, const ObjCObjectPointerType *OPT=nullptr, bool RecordFailure=true)
Try to "correct" a typo in the source code by finding visible declarations whose names are similar to...
Look up any declaration with any name.
Decl * ActOnStartClassInterface(Scope *S, SourceLocation AtInterfaceLoc, IdentifierInfo *ClassName, SourceLocation ClassLoc, ObjCTypeParamList *typeParamList, IdentifierInfo *SuperName, SourceLocation SuperLoc, ArrayRef< ParsedType > SuperTypeArgs, SourceRange SuperTypeArgsRange, Decl *const *ProtoRefs, unsigned NumProtoRefs, const SourceLocation *ProtoLocs, SourceLocation EndProtoLoc, const ParsedAttributesView &AttrList)
bool isObjCObjectPointerType() const
void DiagnoseUnimplementedProperties(Scope *S, ObjCImplDecl *IMPDecl, ObjCContainerDecl *CDecl, bool SynthesizeProperties)
DiagnoseUnimplementedProperties - This routine warns on those properties which must be implemented by...
Represents one property declaration in an Objective-C interface.
void setProtocolList(ObjCProtocolDecl *const *List, unsigned Num, const SourceLocation *Locs, ASTContext &C)
setProtocolList - Set the list of protocols that this interface implements.
ObjCProtocolDecl * LookupProtocol(IdentifierInfo *II, SourceLocation IdLoc, RedeclarationKind Redecl=NotForRedeclaration)
Find the protocol with the given name, if any.
bool DiagnoseUseOfDecl(NamedDecl *D, ArrayRef< SourceLocation > Locs, const ObjCInterfaceDecl *UnknownObjCClass=nullptr, bool ObjCPropertyAccess=false, bool AvoidPartialAvailabilityChecks=false, ObjCInterfaceDecl *ClassReciever=nullptr)
Determine whether the use of this declaration is valid, and emit any corresponding diagnostics...
void updateOutOfDateSelector(Selector Sel)
bool isSuperClassOf(const ObjCInterfaceDecl *I) const
isSuperClassOf - Return true if this class is the specified class or is a super class of the specifie...
bool ObjCIsDesignatedInit
True when this is a method marked as a designated initializer.
bool ObjCShouldCallSuper
A flag that is set when parsing a method that must call super's implementation, such as -dealloc...
ObjCDeclQualifier getObjCDeclQualifier() const
TypeLoc findExplicitQualifierLoc() const
Find a type with the location of an explicit type qualifier.
bool isImplicitInterfaceDecl() const
isImplicitInterfaceDecl - check that this is an implicitly declared ObjCInterfaceDecl node...
void popObjCTypeParamList(Scope *S, ObjCTypeParamList *typeParamList)
bool isVectorType() const
SourceLocation getInlineSpecLoc() const
static bool HelperIsMethodInObjCType(Sema &S, Selector Sel, QualType ObjectType)
ObjCImplementationDecl * getImplementation() const
bool hasSameUnqualifiedType(QualType T1, QualType T2) const
Determine whether the given types are equivalent after cvr-qualifiers have been removed.
std::string getAsString() const
bool isDesignatedInitializerForTheInterface(const ObjCMethodDecl **InitMethod=nullptr) const
Returns true if the method selector resolves to a designated initializer in the class's interface...
ObjCTypeParamDecl * back() const
QualType getObjCInstanceType()
Retrieve the Objective-C "instancetype" type, if already known; otherwise, returns a NULL type;...
void DiagnoseOwningPropertyGetterSynthesis(const ObjCImplementationDecl *D)
static bool checkMethodFamilyMismatch(Sema &S, ObjCMethodDecl *impl, ObjCMethodDecl *decl)
In ARC, check whether the conventional meanings of the two methods match.
ObjCDeclQualifier getObjCDeclQualifier() const
Expr * getInstanceReceiver()
Returns the object expression (receiver) for an instance message, or null for a message that is not a...
SourceRange getSourceRange() const LLVM_READONLY
Get the source range that spans this declarator.
ObjCIvarDecl * getNextIvar()
void diagnoseTypo(const TypoCorrection &Correction, const PartialDiagnostic &TypoDiag, bool ErrorRecovery=true)
Base class for declarations which introduce a typedef-name.
void WarnExactTypedMethods(ObjCMethodDecl *Method, ObjCMethodDecl *MethodDecl, bool IsProtocolMethodDecl)
WarnExactTypedMethods - This routine issues a warning if method implementation declaration matches ex...
bool CollectMultipleMethodsInGlobalPool(Selector Sel, SmallVectorImpl< ObjCMethodDecl *> &Methods, bool InstanceFirst, bool CheckTheOther, const ObjCObjectType *TypeBound=nullptr)
We first select the type of the method: Instance or Factory, then collect all methods with that type...
const ObjCInterfaceDecl * getClassInterface() const
Dataflow Directional Tag Classes.
llvm::iterator_range< specific_decl_iterator< ObjCIvarDecl > > ivar_range
bool isValid() const
Return true if this is a valid SourceLocation object.
std::pair< IdentifierInfo *, SourceLocation > IdentifierLocPair
A simple pair of identifier info and location.
void DiagnoseUnusedBackingIvarInAccessor(Scope *S, const ObjCImplementationDecl *ImplD)
DiagnoseUnusedBackingIvarInAccessor - Issue an 'unused' warning if ivar which backs the property is n...
void diagnoseNullResettableSynthesizedSetters(const ObjCImplDecl *impDecl)
Diagnose any null-resettable synthesized setters.
DeclContext - This is used only as base class of specific decl types that can act as declaration cont...
Decl * ActOnMethodDeclaration(Scope *S, SourceLocation BeginLoc, SourceLocation EndLoc, tok::TokenKind MethodType, ObjCDeclSpec &ReturnQT, ParsedType ReturnType, ArrayRef< SourceLocation > SelectorLocs, Selector Sel, ObjCArgInfo *ArgInfo, DeclaratorChunk::ParamInfo *CParamInfo, unsigned CNumArgs, const ParsedAttributesView &AttrList, tok::ObjCKeywordKind MethodImplKind, bool isVariadic, bool MethodDefinition)
bool CheckFunctionReturnType(QualType T, SourceLocation Loc)
llvm::SmallVector< std::pair< SourceLocation, const BlockDecl * >, 1 > ImplicitlyRetainedSelfLocs
List of SourceLocations where 'self' is implicitly retained inside a block.
void CheckConflictingOverridingMethod(ObjCMethodDecl *Method, ObjCMethodDecl *Overridden, bool IsProtocolMethodDecl)
bool ObjCIsSecondaryInit
True when this is an initializer method not marked as a designated initializer within a class that ha...
QualType getUnderlyingType() const
const ObjCProtocolList & getReferencedProtocols() const
TypeParamListContext
The context in which an Objective-C type parameter list occurs, for use in diagnostics.
static FixItHint CreateRemoval(CharSourceRange RemoveRange)
Create a code modification hint that removes the given source range.
ObjCInterfaceDecl * getDefinition()
Retrieve the definition of this class, or NULL if this class has been forward-declared (with @class) ...
bool CheckARCMethodDecl(ObjCMethodDecl *method)
Check a method declaration for compatibility with the Objective-C ARC conventions.
Represents the declaration of an Objective-C type parameter.
NamedDecl * getFoundDecl() const
Fetch the unique decl found by this lookup.
static std::string getAsString(SplitQualType split, const PrintingPolicy &Policy)
static void CheckProtocolMethodDefs(Sema &S, SourceLocation ImpLoc, ObjCProtocolDecl *PDecl, bool &IncompleteImpl, const Sema::SelectorSet &InsMap, const Sema::SelectorSet &ClsMap, ObjCContainerDecl *CDecl, LazyProtocolNameSet &ProtocolsExplictImpl)
CheckProtocolMethodDefs - This routine checks unimplemented methods Declared in protocol, and those referenced by it.
void PushDeclContext(Scope *S, DeclContext *DC)
Set the current declaration context until it gets popped.
static ObjCImplementationDecl * Create(ASTContext &C, DeclContext *DC, ObjCInterfaceDecl *classInterface, ObjCInterfaceDecl *superDecl, SourceLocation nameLoc, SourceLocation atStartLoc, SourceLocation superLoc=SourceLocation(), SourceLocation IvarLBraceLoc=SourceLocation(), SourceLocation IvarRBraceLoc=SourceLocation())
bool ObjCWarnForNoInitDelegation
This starts true for a secondary initializer method and will be set to false if there is an invocatio...
ObjCIvarDecl * getIvarDecl(IdentifierInfo *Id) const
getIvarDecl - This method looks up an ivar in this ContextDecl.
static bool matchTypes(ASTContext &Context, Sema::MethodMatchStrategy strategy, QualType leftQT, QualType rightQT)
bool hasObjCLifetime() const
IdentifierResolver IdResolver
DeclarationNameInfo - A collector data type for bundling together a DeclarationName and the correspnd...
ParmVarDecl * CheckParameter(DeclContext *DC, SourceLocation StartLoc, SourceLocation NameLoc, IdentifierInfo *Name, QualType T, TypeSourceInfo *TSInfo, StorageClass SC)
bool isHidden() const
Determine whether this declaration might be hidden from name lookup.
specific_decl_iterator - Iterates over a subrange of declarations stored in a DeclContext, providing only those that are of type SpecificDecl (or a class derived from it).
void AddPragmaAttributes(Scope *S, Decl *D)
Adds the attributes that have been specified using the '#pragma clang attribute push' directives to t...
Represents a pointer to an Objective C object.
static bool HasExplicitOwnershipAttr(Sema &S, ParmVarDecl *Param)
HasExplicitOwnershipAttr - returns true when pointer to ObjC pointer has explicit ownership attribute...
SourceRange getSourceRange() const LLVM_READONLY
Get the full source range.
ObjCImplementationDecl - Represents a class definition - this is where method definitions are specifi...
bool isIncompleteArrayType() const
A helper class that allows the use of isa/cast/dyncast to detect TagType objects of structs/unions/cl...
void setNext(ObjCMethodList *L)
static bool isMethodContextSameForKindofLookup(ObjCMethodDecl *Method, ObjCMethodDecl *MethodInList)
bool isIntegerType() const
isIntegerType() does not include complex integers (a GCC extension).
void AddDecl(NamedDecl *D)
AddDecl - Link the decl to its shadowed decl chain.
SourceLocation getSelectorLoc(unsigned Index) const
void ImplMethodsVsClassMethods(Scope *S, ObjCImplDecl *IMPDecl, ObjCContainerDecl *IDecl, bool IncompleteImpl=false)
ImplMethodsVsClassMethods - This is main routine to warn if any method remains unimplemented in the c...
Selector getSelector(unsigned NumArgs, IdentifierInfo **IIV)
Can create any sort of selector.
bool isObjCQualifiedIdType() const
TypeSourceInfo * getTypeSourceInfo() const
DeclContext * getCurLexicalContext() const
static const TST TST_typename
param_const_iterator param_begin() const
Base for LValueReferenceType and RValueReferenceType.
VarDecl * BuildObjCExceptionDecl(TypeSourceInfo *TInfo, QualType ExceptionType, SourceLocation StartLoc, SourceLocation IdLoc, IdentifierInfo *Id, bool Invalid=false)
Build a type-check a new Objective-C exception variable declaration.
DeclContext * getRedeclContext()
getRedeclContext - Retrieve the context in which an entity conflicts with other entities of the same ...
bool hasSameType(QualType T1, QualType T2) const
Determine whether the given types T1 and T2 are equivalent.
virtual void HandleTopLevelDeclInObjCContainer(DeclGroupRef D)
Handle the specified top-level declaration that occurred inside and ObjC container.
Simple template class for restricting typo correction candidates to ones having a single Decl* of the...
SmallVector< ExpressionEvaluationContextRecord, 8 > ExprEvalContexts
A stack of expression evaluation contexts.
void CheckObjCMethodDirectOverrides(ObjCMethodDecl *method, ObjCMethodDecl *overridden)
A list of Objective-C protocols, along with the source locations at which they were referenced...
Wraps an ObjCPointerType with source location information.
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.
void addDecl(Decl *D)
Add the declaration D into this context.
bool canAssignObjCInterfaces(const ObjCObjectPointerType *LHSOPT, const ObjCObjectPointerType *RHSOPT)
canAssignObjCInterfaces - Return true if the two interface types are compatible for assignment from R...
ObjCMethodDecl * lookupMethod(Selector Sel, bool isInstance, bool shallowCategoryLookup=false, bool followSuper=true, const ObjCCategoryDecl *C=nullptr) const
lookupMethod - This method returns an instance/class method by looking in the class, its categories, and its super classes (using a linear search).
Optional< NullabilityKind > getNullability(const ASTContext &context) const
Determine the nullability of the given type.
void AddTypeInfo(const DeclaratorChunk &TI, ParsedAttributes &&attrs, SourceLocation EndLoc)
AddTypeInfo - Add a chunk to this declarator.
static void DiagnoseRetainableFlexibleArrayMember(Sema &S, ObjCInterfaceDecl *ID)
Diagnose attempts to use flexible array member with retainable object type.
static Sema::ResultTypeCompatibilityKind CheckRelatedResultTypeCompatibility(Sema &S, ObjCMethodDecl *Method, ObjCInterfaceDecl *CurrentClass)
Check whether the declared result type of the given Objective-C method declaration is compatible with...
static QualType GetTypeFromParser(ParsedType Ty, TypeSourceInfo **TInfo=nullptr)
ObjCIvarRefExpr - A reference to an ObjC instance variable.
SourceManager & getSourceManager()
void setObjCMethodScopeInfo(unsigned parameterIndex)
bool isObjCObjectType() const
bool isIncompleteType(NamedDecl **Def=nullptr) const
Types are partitioned into 3 broad categories (C99 6.2.5p1): object types, function types...
bool SetTypeSpecType(TST T, SourceLocation Loc, const char *&PrevSpec, unsigned &DiagID, const PrintingPolicy &Policy)
bool hasMoreThanOneDecl() const
bool IsClassExtension() const
ImplementationControl getImplementationControl() const
RedeclarationKind forRedeclarationInCurContext()
SourceLocation getIdentifierLoc() const
CanQualType getCanonicalType(QualType T) const
Return the canonical (structural) type corresponding to the specified potentially non-canonical type ...
ObjCInterfaceDecl * getObjCInterfaceDecl(IdentifierInfo *&Id, SourceLocation IdLoc, bool TypoCorrection=false)
Look for an Objective-C class in the translation unit.
bool isSet() const
Deprecated.
TypeLoc getTypeLoc() const
Return the TypeLoc wrapper for the type source info.
Reading or writing from this object requires a barrier call.
No particular method family.
const ObjCPropertyDecl * findPropertyDecl(bool CheckOverrides=true) const
Returns the property associated with this method's selector.
bool typesAreCompatible(QualType T1, QualType T2, bool CompareUnqualified=false)
Compatibility predicates used to check assignment expressions.
ThreadStorageClassSpecifier
Thread storage-class-specifier.
Decl * ActOnStartProtocolInterface(SourceLocation AtProtoInterfaceLoc, IdentifierInfo *ProtocolName, SourceLocation ProtocolLoc, Decl *const *ProtoRefNames, unsigned NumProtoRefs, const SourceLocation *ProtoLocs, SourceLocation EndProtoLoc, const ParsedAttributesView &AttrList)
Captures information about "declaration specifiers".
QualType getUnqualifiedType() const
Retrieve the unqualified variant of the given type, removing as little sugar as possible.
A factory, from which one makes pools, from which one creates individual attributes which are dealloc...
static void HelperSelectorsForTypoCorrection(SmallVectorImpl< const ObjCMethodDecl *> &BestMethod, StringRef Typo, const ObjCMethodDecl *Method)
TypeInfo getTypeInfo(const Type *T) const
Get the size and alignment of the specified complete type in bits.
ObjCDeclQualifier
ObjCDeclQualifier - 'Qualifiers' written next to the return and parameter types in method declaration...
sema::FunctionScopeInfo * getCurFunction() const
void actOnObjCTypeArgsOrProtocolQualifiers(Scope *S, ParsedType baseType, SourceLocation lAngleLoc, ArrayRef< IdentifierInfo *> identifiers, ArrayRef< SourceLocation > identifierLocs, SourceLocation rAngleLoc, SourceLocation &typeArgsLAngleLoc, SmallVectorImpl< ParsedType > &typeArgs, SourceLocation &typeArgsRAngleLoc, SourceLocation &protocolLAngleLoc, SmallVectorImpl< Decl *> &protocols, SourceLocation &protocolRAngleLoc, bool warnOnIncompleteProtocols)
Given a list of identifiers (and their locations), resolve the names to either Objective-C protocol q...
bool MatchTwoMethodDeclarations(const ObjCMethodDecl *Method, const ObjCMethodDecl *PrevMethod, MethodMatchStrategy strategy=MMS_strict)
MatchTwoMethodDeclarations - Checks if two methods' type match and returns true, or false...
Qualifiers getQualifiers() const
Retrieve the set of qualifiers applied to this type.
ObjCIvarDecl - Represents an ObjC instance variable.
ObjCIvarDecl * getPropertyIvarDecl() const
bool CheckObjCDeclScope(Decl *D)
Checks that the Objective-C declaration is declared in the global scope.
const DeclSpec & getDeclSpec() const
getDeclSpec - Return the declaration-specifier that this declarator was declared with.
Decl * ActOnStartCategoryImplementation(SourceLocation AtCatImplLoc, IdentifierInfo *ClassName, SourceLocation ClassLoc, IdentifierInfo *CatName, SourceLocation CatLoc, const ParsedAttributesView &AttrList)
ActOnStartCategoryImplementation - Perform semantic checks on the category implementation declaration...
DeclContext * CurContext
CurContext - This is the current declaration context of parsing.
Stores a list of Objective-C type parameters for a parameterized class or a category/extension thereo...
ImplicitParamDecl * getCmdDecl() const
static FixItHint CreateReplacement(CharSourceRange RemoveRange, StringRef Code)
Create a code modification hint that replaces the given source range with the given code string...
SourceManager & getSourceManager() const
__DEVICE__ int min(int __a, int __b)
SourceLocation getBeginLoc() const LLVM_READONLY
bool isInlineSpecified() const
a linked list of methods with the same selector name but different signatures.
std::pair< ObjCMethodList, ObjCMethodList > GlobalMethods
#define DIAG(ENUM, FLAGS, DEFAULT_MAPPING, DESC, GROUP, SFINAE, NOWERROR, SHOWINSYSHEADER, CATEGORY)
bool isDependentType() const
Whether this type is a dependent type, meaning that its definition somehow depends on a template para...
bool isIgnored(unsigned DiagID, SourceLocation Loc) const
Determine whether the diagnostic is known to be ignored.
ObjCTypeParamVariance getVariance() const
Determine the variance of this type parameter.
void ActOnObjCContainerFinishDefinition()
void setObjCDeclQualifier(ObjCDeclQualifier QTVal)
ParamInfo - An array of paraminfo objects is allocated whenever a function declarator is parsed...
A trivial tuple used to represent a source range.
bool hasUnrecoverableErrorOccurred() const
ObjCMethodDecl * getMethod(Selector Sel, bool isInstance, bool AllowHidden=false) const
void setLexicalDeclContext(DeclContext *DC)
static SourceRange getTypeRange(TypeSourceInfo *TSI)
This represents a decl that may have a name.
ObjCIvarDecl * all_declared_ivar_begin()
all_declared_ivar_begin - return first ivar declared in this class, its extensions and its implementa...
QualType getObjCObjectPointerType(QualType OIT) const
Return a ObjCObjectPointerType type for the given ObjCObjectType.
static ObjCCategoryImplDecl * Create(ASTContext &C, DeclContext *DC, IdentifierInfo *Id, ObjCInterfaceDecl *classInterface, SourceLocation nameLoc, SourceLocation atStartLoc, SourceLocation CategoryNameLoc)
void setVariance(ObjCTypeParamVariance variance)
Set the variance of this type parameter.
void setTypeSourceInfo(TypeSourceInfo *newType)
void DiagnoseMultipleMethodInGlobalPool(SmallVectorImpl< ObjCMethodDecl *> &Methods, Selector Sel, SourceRange R, bool receiverIdOrClass)
ObjCMethodDecl * getInstanceMethod(Selector Sel, bool AllowHidden=false) const
bool isPropertyAccessor() const
DeclResult actOnObjCTypeParam(Scope *S, ObjCTypeParamVariance variance, SourceLocation varianceLoc, unsigned index, IdentifierInfo *paramName, SourceLocation paramLoc, SourceLocation colonLoc, ParsedType typeBound)
SourceLocation getLAngleLoc() const
static void diagnoseUseOfProtocols(Sema &TheSema, ObjCContainerDecl *CD, ObjCProtocolDecl *const *ProtoRefs, unsigned NumProtoRefs, const SourceLocation *ProtoLocs)
void SetRangeEnd(SourceLocation Loc)
void mergeObjCMethodDecls(ObjCMethodDecl *New, ObjCMethodDecl *Old)
ObjCContainerKind getObjCContainerKind() const
void pushFullCopy(TypeLoc L)
Pushes a copy of the given TypeLoc onto this builder.
void setType(QualType newType)
SourceLocation getBegin() const
const LangOptions & getLangOpts() const
unsigned size() const
Determine the number of type parameters in this list.
void CheckCategoryVsClassMethodMatches(ObjCCategoryImplDecl *CatIMP)
CheckCategoryVsClassMethodMatches - Checks that methods implemented in category matches with those im...
void SetIvarInitializers(ObjCImplementationDecl *ObjCImplementation)
SetIvarInitializers - This routine builds initialization ASTs for the Objective-C implementation whos...
ObjCCategoryImplDecl - An object of this class encapsulates a category @implementation declaration...
The parameter is invariant: must match exactly.
void PushFunctionScope()
Enter a new function scope.
Decl * ActOnCompatibilityAlias(SourceLocation AtCompatibilityAliasLoc, IdentifierInfo *AliasName, SourceLocation AliasLocation, IdentifierInfo *ClassName, SourceLocation ClassLocation)
ActOnCompatibilityAlias - this action is called after complete parsing of a @compatibility_alias decl...
SourceLocation getLocation() const
TypeSourceInfo * GetTypeForDeclarator(Declarator &D, Scope *S)
GetTypeForDeclarator - Convert the type for the specified declarator to Type instances.
QualType getType() const
Return the type wrapped by this type source info.
ArrayRef< ParmVarDecl * > parameters() const
ObjCCompatibleAliasDecl - Represents alias of a class.
Helper class that creates diagnostics with optional template instantiation stacks.
bool isUnavailable(std::string *Message=nullptr) const
Determine whether this declaration is marked 'unavailable'.
Qualifiers::ObjCLifetime getObjCLifetime() const
Returns lifetime attribute of this type.
ObjCCategoryDecl * FindCategoryDeclaration(IdentifierInfo *CategoryId) const
FindCategoryDeclaration - Finds category declaration in the list of categories for this class and ret...