1 //===--- SemaExprMember.cpp - Semantic Analysis for Expressions -----------===// 2 // 3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4 // See https://llvm.org/LICENSE.txt for license information. 5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6 // 7 //===----------------------------------------------------------------------===// 8 // 9 // This file implements semantic analysis member access expressions. 10 // 11 //===----------------------------------------------------------------------===// 12 #include "clang/AST/DeclCXX.h" 13 #include "clang/AST/DeclObjC.h" 14 #include "clang/AST/DeclTemplate.h" 15 #include "clang/AST/ExprCXX.h" 16 #include "clang/AST/ExprObjC.h" 17 #include "clang/Lex/Preprocessor.h" 18 #include "clang/Sema/Lookup.h" 19 #include "clang/Sema/Overload.h" 20 #include "clang/Sema/Scope.h" 21 #include "clang/Sema/ScopeInfo.h" 22 #include "clang/Sema/SemaObjC.h" 23 #include "clang/Sema/SemaOpenMP.h" 24 25 using namespace clang; 26 using namespace sema; 27 28 typedef llvm::SmallPtrSet<const CXXRecordDecl*, 4> BaseSet; 29 30 /// Determines if the given class is provably not derived from all of 31 /// the prospective base classes. 32 static bool isProvablyNotDerivedFrom(Sema &SemaRef, CXXRecordDecl *Record, 33 const BaseSet &Bases) { 34 auto BaseIsNotInSet = [&Bases](const CXXRecordDecl *Base) { 35 return !Bases.count(Base->getCanonicalDecl()); 36 }; 37 return BaseIsNotInSet(Record) && Record->forallBases(BaseIsNotInSet); 38 } 39 40 enum IMAKind { 41 /// The reference is definitely not an instance member access. 42 IMA_Static, 43 44 /// The reference may be an implicit instance member access. 45 IMA_Mixed, 46 47 /// The reference may be to an instance member, but it might be invalid if 48 /// so, because the context is not an instance method. 49 IMA_Mixed_StaticOrExplicitContext, 50 51 /// The reference may be to an instance member, but it is invalid if 52 /// so, because the context is from an unrelated class. 53 IMA_Mixed_Unrelated, 54 55 /// The reference is definitely an implicit instance member access. 56 IMA_Instance, 57 58 /// The reference may be to an unresolved using declaration. 59 IMA_Unresolved, 60 61 /// The reference is a contextually-permitted abstract member reference. 62 IMA_Abstract, 63 64 /// Whether the context is static is dependent on the enclosing template (i.e. 65 /// in a dependent class scope explicit specialization). 66 IMA_Dependent, 67 68 /// The reference may be to an unresolved using declaration and the 69 /// context is not an instance method. 70 IMA_Unresolved_StaticOrExplicitContext, 71 72 // The reference refers to a field which is not a member of the containing 73 // class, which is allowed because we're in C++11 mode and the context is 74 // unevaluated. 75 IMA_Field_Uneval_Context, 76 77 /// All possible referrents are instance members and the current 78 /// context is not an instance method. 79 IMA_Error_StaticOrExplicitContext, 80 81 /// All possible referrents are instance members of an unrelated 82 /// class. 83 IMA_Error_Unrelated 84 }; 85 86 /// The given lookup names class member(s) and is not being used for 87 /// an address-of-member expression. Classify the type of access 88 /// according to whether it's possible that this reference names an 89 /// instance member. This is best-effort in dependent contexts; it is okay to 90 /// conservatively answer "yes", in which case some errors will simply 91 /// not be caught until template-instantiation. 92 static IMAKind ClassifyImplicitMemberAccess(Sema &SemaRef, 93 const LookupResult &R) { 94 assert(!R.empty() && (*R.begin())->isCXXClassMember()); 95 96 DeclContext *DC = SemaRef.getFunctionLevelDeclContext(); 97 98 bool couldInstantiateToStatic = false; 99 bool isStaticOrExplicitContext = SemaRef.CXXThisTypeOverride.isNull(); 100 101 if (auto *MD = dyn_cast<CXXMethodDecl>(DC)) { 102 if (MD->isImplicitObjectMemberFunction()) { 103 isStaticOrExplicitContext = false; 104 // A dependent class scope function template explicit specialization 105 // that is neither declared 'static' nor with an explicit object 106 // parameter could instantiate to a static or non-static member function. 107 couldInstantiateToStatic = MD->getDependentSpecializationInfo(); 108 } 109 } 110 111 if (R.isUnresolvableResult()) { 112 if (couldInstantiateToStatic) 113 return IMA_Dependent; 114 return isStaticOrExplicitContext ? IMA_Unresolved_StaticOrExplicitContext 115 : IMA_Unresolved; 116 } 117 118 // Collect all the declaring classes of instance members we find. 119 bool hasNonInstance = false; 120 bool isField = false; 121 BaseSet Classes; 122 for (NamedDecl *D : R) { 123 // Look through any using decls. 124 D = D->getUnderlyingDecl(); 125 126 if (D->isCXXInstanceMember()) { 127 isField |= isa<FieldDecl>(D) || isa<MSPropertyDecl>(D) || 128 isa<IndirectFieldDecl>(D); 129 130 CXXRecordDecl *R = cast<CXXRecordDecl>(D->getDeclContext()); 131 Classes.insert(R->getCanonicalDecl()); 132 } else 133 hasNonInstance = true; 134 } 135 136 // If we didn't find any instance members, it can't be an implicit 137 // member reference. 138 if (Classes.empty()) 139 return IMA_Static; 140 141 if (couldInstantiateToStatic) 142 return IMA_Dependent; 143 144 // C++11 [expr.prim.general]p12: 145 // An id-expression that denotes a non-static data member or non-static 146 // member function of a class can only be used: 147 // (...) 148 // - if that id-expression denotes a non-static data member and it 149 // appears in an unevaluated operand. 150 // 151 // This rule is specific to C++11. However, we also permit this form 152 // in unevaluated inline assembly operands, like the operand to a SIZE. 153 IMAKind AbstractInstanceResult = IMA_Static; // happens to be 'false' 154 assert(!AbstractInstanceResult); 155 switch (SemaRef.ExprEvalContexts.back().Context) { 156 case Sema::ExpressionEvaluationContext::Unevaluated: 157 case Sema::ExpressionEvaluationContext::UnevaluatedList: 158 if (isField && SemaRef.getLangOpts().CPlusPlus11) 159 AbstractInstanceResult = IMA_Field_Uneval_Context; 160 break; 161 162 case Sema::ExpressionEvaluationContext::UnevaluatedAbstract: 163 AbstractInstanceResult = IMA_Abstract; 164 break; 165 166 case Sema::ExpressionEvaluationContext::DiscardedStatement: 167 case Sema::ExpressionEvaluationContext::ConstantEvaluated: 168 case Sema::ExpressionEvaluationContext::ImmediateFunctionContext: 169 case Sema::ExpressionEvaluationContext::PotentiallyEvaluated: 170 case Sema::ExpressionEvaluationContext::PotentiallyEvaluatedIfUsed: 171 break; 172 } 173 174 // If the current context is not an instance method, it can't be 175 // an implicit member reference. 176 if (isStaticOrExplicitContext) { 177 if (hasNonInstance) 178 return IMA_Mixed_StaticOrExplicitContext; 179 180 return AbstractInstanceResult ? AbstractInstanceResult 181 : IMA_Error_StaticOrExplicitContext; 182 } 183 184 CXXRecordDecl *contextClass; 185 if (auto *MD = dyn_cast<CXXMethodDecl>(DC)) 186 contextClass = MD->getParent()->getCanonicalDecl(); 187 else if (auto *RD = dyn_cast<CXXRecordDecl>(DC)) 188 contextClass = RD; 189 else 190 return AbstractInstanceResult ? AbstractInstanceResult 191 : IMA_Error_StaticOrExplicitContext; 192 193 // [class.mfct.non-static]p3: 194 // ...is used in the body of a non-static member function of class X, 195 // if name lookup (3.4.1) resolves the name in the id-expression to a 196 // non-static non-type member of some class C [...] 197 // ...if C is not X or a base class of X, the class member access expression 198 // is ill-formed. 199 if (R.getNamingClass() && 200 contextClass->getCanonicalDecl() != 201 R.getNamingClass()->getCanonicalDecl()) { 202 // If the naming class is not the current context, this was a qualified 203 // member name lookup, and it's sufficient to check that we have the naming 204 // class as a base class. 205 Classes.clear(); 206 Classes.insert(R.getNamingClass()->getCanonicalDecl()); 207 } 208 209 // If we can prove that the current context is unrelated to all the 210 // declaring classes, it can't be an implicit member reference (in 211 // which case it's an error if any of those members are selected). 212 if (isProvablyNotDerivedFrom(SemaRef, contextClass, Classes)) 213 return hasNonInstance ? IMA_Mixed_Unrelated : 214 AbstractInstanceResult ? AbstractInstanceResult : 215 IMA_Error_Unrelated; 216 217 return (hasNonInstance ? IMA_Mixed : IMA_Instance); 218 } 219 220 /// Diagnose a reference to a field with no object available. 221 static void diagnoseInstanceReference(Sema &SemaRef, 222 const CXXScopeSpec &SS, 223 NamedDecl *Rep, 224 const DeclarationNameInfo &nameInfo) { 225 SourceLocation Loc = nameInfo.getLoc(); 226 SourceRange Range(Loc); 227 if (SS.isSet()) Range.setBegin(SS.getRange().getBegin()); 228 229 // Look through using shadow decls and aliases. 230 Rep = Rep->getUnderlyingDecl(); 231 232 DeclContext *FunctionLevelDC = SemaRef.getFunctionLevelDeclContext(); 233 CXXMethodDecl *Method = dyn_cast<CXXMethodDecl>(FunctionLevelDC); 234 CXXRecordDecl *ContextClass = Method ? Method->getParent() : nullptr; 235 CXXRecordDecl *RepClass = dyn_cast<CXXRecordDecl>(Rep->getDeclContext()); 236 237 bool InStaticMethod = Method && Method->isStatic(); 238 bool InExplicitObjectMethod = 239 Method && Method->isExplicitObjectMemberFunction(); 240 bool IsField = isa<FieldDecl>(Rep) || isa<IndirectFieldDecl>(Rep); 241 242 std::string Replacement; 243 if (InExplicitObjectMethod) { 244 DeclarationName N = Method->getParamDecl(0)->getDeclName(); 245 if (!N.isEmpty()) { 246 Replacement.append(N.getAsString()); 247 Replacement.append("."); 248 } 249 } 250 if (IsField && InStaticMethod) 251 // "invalid use of member 'x' in static member function" 252 SemaRef.Diag(Loc, diag::err_invalid_member_use_in_method) 253 << Range << nameInfo.getName() << /*static*/ 0; 254 else if (IsField && InExplicitObjectMethod) { 255 auto Diag = SemaRef.Diag(Loc, diag::err_invalid_member_use_in_method) 256 << Range << nameInfo.getName() << /*explicit*/ 1; 257 if (!Replacement.empty()) 258 Diag << FixItHint::CreateInsertion(Loc, Replacement); 259 } else if (ContextClass && RepClass && SS.isEmpty() && 260 !InExplicitObjectMethod && !InStaticMethod && 261 !RepClass->Equals(ContextClass) && 262 RepClass->Encloses(ContextClass)) 263 // Unqualified lookup in a non-static member function found a member of an 264 // enclosing class. 265 SemaRef.Diag(Loc, diag::err_nested_non_static_member_use) 266 << IsField << RepClass << nameInfo.getName() << ContextClass << Range; 267 else if (IsField) 268 SemaRef.Diag(Loc, diag::err_invalid_non_static_member_use) 269 << nameInfo.getName() << Range; 270 else if (!InExplicitObjectMethod) 271 SemaRef.Diag(Loc, diag::err_member_call_without_object) 272 << Range << /*static*/ 0; 273 else { 274 if (const auto *Tpl = dyn_cast<FunctionTemplateDecl>(Rep)) 275 Rep = Tpl->getTemplatedDecl(); 276 const auto *Callee = cast<CXXMethodDecl>(Rep); 277 auto Diag = SemaRef.Diag(Loc, diag::err_member_call_without_object) 278 << Range << Callee->isExplicitObjectMemberFunction(); 279 if (!Replacement.empty()) 280 Diag << FixItHint::CreateInsertion(Loc, Replacement); 281 } 282 } 283 284 bool Sema::isPotentialImplicitMemberAccess(const CXXScopeSpec &SS, 285 LookupResult &R, 286 bool IsAddressOfOperand) { 287 if (!getLangOpts().CPlusPlus) 288 return false; 289 else if (R.empty() || !R.begin()->isCXXClassMember()) 290 return false; 291 else if (!IsAddressOfOperand) 292 return true; 293 else if (!SS.isEmpty()) 294 return false; 295 else if (R.isOverloadedResult()) 296 return false; 297 else if (R.isUnresolvableResult()) 298 return true; 299 else 300 return isa<FieldDecl, IndirectFieldDecl, MSPropertyDecl>(R.getFoundDecl()); 301 } 302 303 ExprResult Sema::BuildPossibleImplicitMemberExpr( 304 const CXXScopeSpec &SS, SourceLocation TemplateKWLoc, LookupResult &R, 305 const TemplateArgumentListInfo *TemplateArgs, const Scope *S) { 306 switch (IMAKind Classification = ClassifyImplicitMemberAccess(*this, R)) { 307 case IMA_Instance: 308 case IMA_Mixed: 309 case IMA_Mixed_Unrelated: 310 case IMA_Unresolved: 311 return BuildImplicitMemberExpr( 312 SS, TemplateKWLoc, R, TemplateArgs, 313 /*IsKnownInstance=*/Classification == IMA_Instance, S); 314 case IMA_Field_Uneval_Context: 315 Diag(R.getNameLoc(), diag::warn_cxx98_compat_non_static_member_use) 316 << R.getLookupNameInfo().getName(); 317 [[fallthrough]]; 318 case IMA_Static: 319 case IMA_Abstract: 320 case IMA_Mixed_StaticOrExplicitContext: 321 case IMA_Unresolved_StaticOrExplicitContext: 322 if (TemplateArgs || TemplateKWLoc.isValid()) 323 return BuildTemplateIdExpr(SS, TemplateKWLoc, R, /*RequiresADL=*/false, 324 TemplateArgs); 325 return BuildDeclarationNameExpr(SS, R, /*NeedsADL=*/false, 326 /*AcceptInvalidDecl=*/false); 327 case IMA_Dependent: 328 R.suppressDiagnostics(); 329 return UnresolvedLookupExpr::Create( 330 Context, R.getNamingClass(), SS.getWithLocInContext(Context), 331 TemplateKWLoc, R.getLookupNameInfo(), /*RequiresADL=*/false, 332 TemplateArgs, R.begin(), R.end(), /*KnownDependent=*/true, 333 /*KnownInstantiationDependent=*/true); 334 335 case IMA_Error_StaticOrExplicitContext: 336 case IMA_Error_Unrelated: 337 diagnoseInstanceReference(*this, SS, R.getRepresentativeDecl(), 338 R.getLookupNameInfo()); 339 return ExprError(); 340 } 341 342 llvm_unreachable("unexpected instance member access kind"); 343 } 344 345 /// Determine whether input char is from rgba component set. 346 static bool 347 IsRGBA(char c) { 348 switch (c) { 349 case 'r': 350 case 'g': 351 case 'b': 352 case 'a': 353 return true; 354 default: 355 return false; 356 } 357 } 358 359 // OpenCL v1.1, s6.1.7 360 // The component swizzle length must be in accordance with the acceptable 361 // vector sizes. 362 static bool IsValidOpenCLComponentSwizzleLength(unsigned len) 363 { 364 return (len >= 1 && len <= 4) || len == 8 || len == 16; 365 } 366 367 /// Check an ext-vector component access expression. 368 /// 369 /// VK should be set in advance to the value kind of the base 370 /// expression. 371 static QualType 372 CheckExtVectorComponent(Sema &S, QualType baseType, ExprValueKind &VK, 373 SourceLocation OpLoc, const IdentifierInfo *CompName, 374 SourceLocation CompLoc) { 375 // FIXME: Share logic with ExtVectorElementExpr::containsDuplicateElements, 376 // see FIXME there. 377 // 378 // FIXME: This logic can be greatly simplified by splitting it along 379 // halving/not halving and reworking the component checking. 380 const ExtVectorType *vecType = baseType->castAs<ExtVectorType>(); 381 382 // The vector accessor can't exceed the number of elements. 383 const char *compStr = CompName->getNameStart(); 384 385 // This flag determines whether or not the component is one of the four 386 // special names that indicate a subset of exactly half the elements are 387 // to be selected. 388 bool HalvingSwizzle = false; 389 390 // This flag determines whether or not CompName has an 's' char prefix, 391 // indicating that it is a string of hex values to be used as vector indices. 392 bool HexSwizzle = (*compStr == 's' || *compStr == 'S') && compStr[1]; 393 394 bool HasRepeated = false; 395 bool HasIndex[16] = {}; 396 397 int Idx; 398 399 // Check that we've found one of the special components, or that the component 400 // names must come from the same set. 401 if (!strcmp(compStr, "hi") || !strcmp(compStr, "lo") || 402 !strcmp(compStr, "even") || !strcmp(compStr, "odd")) { 403 HalvingSwizzle = true; 404 } else if (!HexSwizzle && 405 (Idx = vecType->getPointAccessorIdx(*compStr)) != -1) { 406 bool HasRGBA = IsRGBA(*compStr); 407 do { 408 // Ensure that xyzw and rgba components don't intermingle. 409 if (HasRGBA != IsRGBA(*compStr)) 410 break; 411 if (HasIndex[Idx]) HasRepeated = true; 412 HasIndex[Idx] = true; 413 compStr++; 414 } while (*compStr && (Idx = vecType->getPointAccessorIdx(*compStr)) != -1); 415 416 // Emit a warning if an rgba selector is used earlier than OpenCL C 3.0. 417 if (HasRGBA || (*compStr && IsRGBA(*compStr))) { 418 if (S.getLangOpts().OpenCL && 419 S.getLangOpts().getOpenCLCompatibleVersion() < 300) { 420 const char *DiagBegin = HasRGBA ? CompName->getNameStart() : compStr; 421 S.Diag(OpLoc, diag::ext_opencl_ext_vector_type_rgba_selector) 422 << StringRef(DiagBegin, 1) << SourceRange(CompLoc); 423 } 424 } 425 } else { 426 if (HexSwizzle) compStr++; 427 while ((Idx = vecType->getNumericAccessorIdx(*compStr)) != -1) { 428 if (HasIndex[Idx]) HasRepeated = true; 429 HasIndex[Idx] = true; 430 compStr++; 431 } 432 } 433 434 if (!HalvingSwizzle && *compStr) { 435 // We didn't get to the end of the string. This means the component names 436 // didn't come from the same set *or* we encountered an illegal name. 437 size_t Offset = compStr - CompName->getNameStart() + 1; 438 char Fmt[3] = {'\'', *compStr, '\''}; 439 S.Diag(OpLoc.getLocWithOffset(Offset), 440 diag::err_ext_vector_component_name_illegal) 441 << StringRef(Fmt, 3) << SourceRange(CompLoc); 442 return QualType(); 443 } 444 445 // Ensure no component accessor exceeds the width of the vector type it 446 // operates on. 447 if (!HalvingSwizzle) { 448 compStr = CompName->getNameStart(); 449 450 if (HexSwizzle) 451 compStr++; 452 453 while (*compStr) { 454 if (!vecType->isAccessorWithinNumElements(*compStr++, HexSwizzle)) { 455 S.Diag(OpLoc, diag::err_ext_vector_component_exceeds_length) 456 << baseType << SourceRange(CompLoc); 457 return QualType(); 458 } 459 } 460 } 461 462 // OpenCL mode requires swizzle length to be in accordance with accepted 463 // sizes. Clang however supports arbitrary lengths for other languages. 464 if (S.getLangOpts().OpenCL && !HalvingSwizzle) { 465 unsigned SwizzleLength = CompName->getLength(); 466 467 if (HexSwizzle) 468 SwizzleLength--; 469 470 if (IsValidOpenCLComponentSwizzleLength(SwizzleLength) == false) { 471 S.Diag(OpLoc, diag::err_opencl_ext_vector_component_invalid_length) 472 << SwizzleLength << SourceRange(CompLoc); 473 return QualType(); 474 } 475 } 476 477 // The component accessor looks fine - now we need to compute the actual type. 478 // The vector type is implied by the component accessor. For example, 479 // vec4.b is a float, vec4.xy is a vec2, vec4.rgb is a vec3, etc. 480 // vec4.s0 is a float, vec4.s23 is a vec3, etc. 481 // vec4.hi, vec4.lo, vec4.e, and vec4.o all return vec2. 482 unsigned CompSize = HalvingSwizzle ? (vecType->getNumElements() + 1) / 2 483 : CompName->getLength(); 484 if (HexSwizzle) 485 CompSize--; 486 487 if (CompSize == 1) 488 return vecType->getElementType(); 489 490 if (HasRepeated) 491 VK = VK_PRValue; 492 493 QualType VT = S.Context.getExtVectorType(vecType->getElementType(), CompSize); 494 // Now look up the TypeDefDecl from the vector type. Without this, 495 // diagostics look bad. We want extended vector types to appear built-in. 496 for (Sema::ExtVectorDeclsType::iterator 497 I = S.ExtVectorDecls.begin(S.getExternalSource()), 498 E = S.ExtVectorDecls.end(); 499 I != E; ++I) { 500 if ((*I)->getUnderlyingType() == VT) 501 return S.Context.getTypedefType(*I); 502 } 503 504 return VT; // should never get here (a typedef type should always be found). 505 } 506 507 static Decl *FindGetterSetterNameDeclFromProtocolList(const ObjCProtocolDecl*PDecl, 508 IdentifierInfo *Member, 509 const Selector &Sel, 510 ASTContext &Context) { 511 if (Member) 512 if (ObjCPropertyDecl *PD = PDecl->FindPropertyDeclaration( 513 Member, ObjCPropertyQueryKind::OBJC_PR_query_instance)) 514 return PD; 515 if (ObjCMethodDecl *OMD = PDecl->getInstanceMethod(Sel)) 516 return OMD; 517 518 for (const auto *I : PDecl->protocols()) { 519 if (Decl *D = FindGetterSetterNameDeclFromProtocolList(I, Member, Sel, 520 Context)) 521 return D; 522 } 523 return nullptr; 524 } 525 526 static Decl *FindGetterSetterNameDecl(const ObjCObjectPointerType *QIdTy, 527 IdentifierInfo *Member, 528 const Selector &Sel, 529 ASTContext &Context) { 530 // Check protocols on qualified interfaces. 531 Decl *GDecl = nullptr; 532 for (const auto *I : QIdTy->quals()) { 533 if (Member) 534 if (ObjCPropertyDecl *PD = I->FindPropertyDeclaration( 535 Member, ObjCPropertyQueryKind::OBJC_PR_query_instance)) { 536 GDecl = PD; 537 break; 538 } 539 // Also must look for a getter or setter name which uses property syntax. 540 if (ObjCMethodDecl *OMD = I->getInstanceMethod(Sel)) { 541 GDecl = OMD; 542 break; 543 } 544 } 545 if (!GDecl) { 546 for (const auto *I : QIdTy->quals()) { 547 // Search in the protocol-qualifier list of current protocol. 548 GDecl = FindGetterSetterNameDeclFromProtocolList(I, Member, Sel, Context); 549 if (GDecl) 550 return GDecl; 551 } 552 } 553 return GDecl; 554 } 555 556 ExprResult 557 Sema::ActOnDependentMemberExpr(Expr *BaseExpr, QualType BaseType, 558 bool IsArrow, SourceLocation OpLoc, 559 const CXXScopeSpec &SS, 560 SourceLocation TemplateKWLoc, 561 NamedDecl *FirstQualifierInScope, 562 const DeclarationNameInfo &NameInfo, 563 const TemplateArgumentListInfo *TemplateArgs) { 564 // Even in dependent contexts, try to diagnose base expressions with 565 // obviously wrong types, e.g.: 566 // 567 // T* t; 568 // t.f; 569 // 570 // In Obj-C++, however, the above expression is valid, since it could be 571 // accessing the 'f' property if T is an Obj-C interface. The extra check 572 // allows this, while still reporting an error if T is a struct pointer. 573 if (!IsArrow) { 574 const PointerType *PT = BaseType->getAs<PointerType>(); 575 if (PT && (!getLangOpts().ObjC || 576 PT->getPointeeType()->isRecordType())) { 577 assert(BaseExpr && "cannot happen with implicit member accesses"); 578 Diag(OpLoc, diag::err_typecheck_member_reference_struct_union) 579 << BaseType << BaseExpr->getSourceRange() << NameInfo.getSourceRange(); 580 return ExprError(); 581 } 582 } 583 584 assert(BaseType->isDependentType() || NameInfo.getName().isDependentName() || 585 isDependentScopeSpecifier(SS) || 586 (TemplateArgs && llvm::any_of(TemplateArgs->arguments(), 587 [](const TemplateArgumentLoc &Arg) { 588 return Arg.getArgument().isDependent(); 589 }))); 590 591 // Get the type being accessed in BaseType. If this is an arrow, the BaseExpr 592 // must have pointer type, and the accessed type is the pointee. 593 return CXXDependentScopeMemberExpr::Create( 594 Context, BaseExpr, BaseType, IsArrow, OpLoc, 595 SS.getWithLocInContext(Context), TemplateKWLoc, FirstQualifierInScope, 596 NameInfo, TemplateArgs); 597 } 598 599 /// We know that the given qualified member reference points only to 600 /// declarations which do not belong to the static type of the base 601 /// expression. Diagnose the problem. 602 static void DiagnoseQualifiedMemberReference(Sema &SemaRef, 603 Expr *BaseExpr, 604 QualType BaseType, 605 const CXXScopeSpec &SS, 606 NamedDecl *rep, 607 const DeclarationNameInfo &nameInfo) { 608 // If this is an implicit member access, use a different set of 609 // diagnostics. 610 if (!BaseExpr) 611 return diagnoseInstanceReference(SemaRef, SS, rep, nameInfo); 612 613 SemaRef.Diag(nameInfo.getLoc(), diag::err_qualified_member_of_unrelated) 614 << SS.getRange() << rep << BaseType; 615 } 616 617 bool Sema::CheckQualifiedMemberReference(Expr *BaseExpr, 618 QualType BaseType, 619 const CXXScopeSpec &SS, 620 const LookupResult &R) { 621 CXXRecordDecl *BaseRecord = 622 cast_or_null<CXXRecordDecl>(computeDeclContext(BaseType)); 623 if (!BaseRecord) { 624 // We can't check this yet because the base type is still 625 // dependent. 626 assert(BaseType->isDependentType()); 627 return false; 628 } 629 630 for (LookupResult::iterator I = R.begin(), E = R.end(); I != E; ++I) { 631 // If this is an implicit member reference and we find a 632 // non-instance member, it's not an error. 633 if (!BaseExpr && !(*I)->isCXXInstanceMember()) 634 return false; 635 636 // Note that we use the DC of the decl, not the underlying decl. 637 DeclContext *DC = (*I)->getDeclContext()->getNonTransparentContext(); 638 if (!DC->isRecord()) 639 continue; 640 641 CXXRecordDecl *MemberRecord = cast<CXXRecordDecl>(DC)->getCanonicalDecl(); 642 if (BaseRecord->getCanonicalDecl() == MemberRecord || 643 !BaseRecord->isProvablyNotDerivedFrom(MemberRecord)) 644 return false; 645 } 646 647 DiagnoseQualifiedMemberReference(*this, BaseExpr, BaseType, SS, 648 R.getRepresentativeDecl(), 649 R.getLookupNameInfo()); 650 return true; 651 } 652 653 namespace { 654 655 // Callback to only accept typo corrections that are either a ValueDecl or a 656 // FunctionTemplateDecl and are declared in the current record or, for a C++ 657 // classes, one of its base classes. 658 class RecordMemberExprValidatorCCC final : public CorrectionCandidateCallback { 659 public: 660 explicit RecordMemberExprValidatorCCC(QualType RTy) 661 : Record(RTy->getAsRecordDecl()) { 662 // Don't add bare keywords to the consumer since they will always fail 663 // validation by virtue of not being associated with any decls. 664 WantTypeSpecifiers = false; 665 WantExpressionKeywords = false; 666 WantCXXNamedCasts = false; 667 WantFunctionLikeCasts = false; 668 WantRemainingKeywords = false; 669 } 670 671 bool ValidateCandidate(const TypoCorrection &candidate) override { 672 NamedDecl *ND = candidate.getCorrectionDecl(); 673 // Don't accept candidates that cannot be member functions, constants, 674 // variables, or templates. 675 if (!ND || !(isa<ValueDecl>(ND) || isa<FunctionTemplateDecl>(ND))) 676 return false; 677 678 // Accept candidates that occur in the current record. 679 if (Record->containsDecl(ND)) 680 return true; 681 682 if (const auto *RD = dyn_cast<CXXRecordDecl>(Record)) { 683 // Accept candidates that occur in any of the current class' base classes. 684 for (const auto &BS : RD->bases()) { 685 if (const auto *BSTy = BS.getType()->getAs<RecordType>()) { 686 if (BSTy->getDecl()->containsDecl(ND)) 687 return true; 688 } 689 } 690 } 691 692 return false; 693 } 694 695 std::unique_ptr<CorrectionCandidateCallback> clone() override { 696 return std::make_unique<RecordMemberExprValidatorCCC>(*this); 697 } 698 699 private: 700 const RecordDecl *const Record; 701 }; 702 703 } 704 705 static bool LookupMemberExprInRecord(Sema &SemaRef, LookupResult &R, 706 Expr *BaseExpr, QualType RTy, 707 SourceLocation OpLoc, bool IsArrow, 708 CXXScopeSpec &SS, bool HasTemplateArgs, 709 SourceLocation TemplateKWLoc, 710 TypoExpr *&TE) { 711 SourceRange BaseRange = BaseExpr ? BaseExpr->getSourceRange() : SourceRange(); 712 if (!RTy->isDependentType() && 713 !SemaRef.isThisOutsideMemberFunctionBody(RTy) && 714 SemaRef.RequireCompleteType( 715 OpLoc, RTy, diag::err_typecheck_incomplete_tag, BaseRange)) 716 return true; 717 718 // LookupTemplateName/LookupParsedName don't expect these both to exist 719 // simultaneously. 720 QualType ObjectType = SS.isSet() ? QualType() : RTy; 721 if (HasTemplateArgs || TemplateKWLoc.isValid()) 722 return SemaRef.LookupTemplateName(R, 723 /*S=*/nullptr, SS, ObjectType, 724 /*EnteringContext=*/false, TemplateKWLoc); 725 726 SemaRef.LookupParsedName(R, /*S=*/nullptr, &SS, ObjectType); 727 728 if (!R.empty() || R.wasNotFoundInCurrentInstantiation()) 729 return false; 730 731 DeclarationName Typo = R.getLookupName(); 732 SourceLocation TypoLoc = R.getNameLoc(); 733 // Recompute the lookup context. 734 DeclContext *DC = SS.isSet() ? SemaRef.computeDeclContext(SS) 735 : SemaRef.computeDeclContext(RTy); 736 737 struct QueryState { 738 Sema &SemaRef; 739 DeclarationNameInfo NameInfo; 740 Sema::LookupNameKind LookupKind; 741 RedeclarationKind Redecl; 742 }; 743 QueryState Q = {R.getSema(), R.getLookupNameInfo(), R.getLookupKind(), 744 R.redeclarationKind()}; 745 RecordMemberExprValidatorCCC CCC(RTy); 746 TE = SemaRef.CorrectTypoDelayed( 747 R.getLookupNameInfo(), R.getLookupKind(), nullptr, &SS, CCC, 748 [=, &SemaRef](const TypoCorrection &TC) { 749 if (TC) { 750 assert(!TC.isKeyword() && 751 "Got a keyword as a correction for a member!"); 752 bool DroppedSpecifier = 753 TC.WillReplaceSpecifier() && 754 Typo.getAsString() == TC.getAsString(SemaRef.getLangOpts()); 755 SemaRef.diagnoseTypo(TC, SemaRef.PDiag(diag::err_no_member_suggest) 756 << Typo << DC << DroppedSpecifier 757 << SS.getRange()); 758 } else { 759 SemaRef.Diag(TypoLoc, diag::err_no_member) 760 << Typo << DC << (SS.isSet() ? SS.getRange() : BaseRange); 761 } 762 }, 763 [=](Sema &SemaRef, TypoExpr *TE, TypoCorrection TC) mutable { 764 LookupResult R(Q.SemaRef, Q.NameInfo, Q.LookupKind, Q.Redecl); 765 R.clear(); // Ensure there's no decls lingering in the shared state. 766 R.suppressDiagnostics(); 767 R.setLookupName(TC.getCorrection()); 768 for (NamedDecl *ND : TC) 769 R.addDecl(ND); 770 R.resolveKind(); 771 return SemaRef.BuildMemberReferenceExpr( 772 BaseExpr, BaseExpr->getType(), OpLoc, IsArrow, SS, SourceLocation(), 773 nullptr, R, nullptr, nullptr); 774 }, 775 Sema::CTK_ErrorRecovery, DC); 776 777 return false; 778 } 779 780 static ExprResult LookupMemberExpr(Sema &S, LookupResult &R, 781 ExprResult &BaseExpr, bool &IsArrow, 782 SourceLocation OpLoc, CXXScopeSpec &SS, 783 Decl *ObjCImpDecl, bool HasTemplateArgs, 784 SourceLocation TemplateKWLoc); 785 786 ExprResult Sema::BuildMemberReferenceExpr( 787 Expr *Base, QualType BaseType, SourceLocation OpLoc, bool IsArrow, 788 CXXScopeSpec &SS, SourceLocation TemplateKWLoc, 789 NamedDecl *FirstQualifierInScope, const DeclarationNameInfo &NameInfo, 790 const TemplateArgumentListInfo *TemplateArgs, const Scope *S, 791 ActOnMemberAccessExtraArgs *ExtraArgs) { 792 LookupResult R(*this, NameInfo, LookupMemberName); 793 794 // Implicit member accesses. 795 if (!Base) { 796 TypoExpr *TE = nullptr; 797 QualType RecordTy = BaseType; 798 if (IsArrow) RecordTy = RecordTy->castAs<PointerType>()->getPointeeType(); 799 if (LookupMemberExprInRecord(*this, R, nullptr, RecordTy, OpLoc, IsArrow, 800 SS, TemplateArgs != nullptr, TemplateKWLoc, 801 TE)) 802 return ExprError(); 803 if (TE) 804 return TE; 805 806 // Explicit member accesses. 807 } else { 808 ExprResult BaseResult = Base; 809 ExprResult Result = 810 LookupMemberExpr(*this, R, BaseResult, IsArrow, OpLoc, SS, 811 ExtraArgs ? ExtraArgs->ObjCImpDecl : nullptr, 812 TemplateArgs != nullptr, TemplateKWLoc); 813 814 if (BaseResult.isInvalid()) 815 return ExprError(); 816 Base = BaseResult.get(); 817 818 if (Result.isInvalid()) 819 return ExprError(); 820 821 if (Result.get()) 822 return Result; 823 824 // LookupMemberExpr can modify Base, and thus change BaseType 825 BaseType = Base->getType(); 826 } 827 828 // BuildMemberReferenceExpr expects the nested-name-specifier, if any, to be 829 // valid. 830 if (SS.isInvalid()) 831 return ExprError(); 832 833 return BuildMemberReferenceExpr(Base, BaseType, 834 OpLoc, IsArrow, SS, TemplateKWLoc, 835 FirstQualifierInScope, R, TemplateArgs, S, 836 false, ExtraArgs); 837 } 838 839 ExprResult 840 Sema::BuildAnonymousStructUnionMemberReference(const CXXScopeSpec &SS, 841 SourceLocation loc, 842 IndirectFieldDecl *indirectField, 843 DeclAccessPair foundDecl, 844 Expr *baseObjectExpr, 845 SourceLocation opLoc) { 846 // First, build the expression that refers to the base object. 847 848 // Case 1: the base of the indirect field is not a field. 849 VarDecl *baseVariable = indirectField->getVarDecl(); 850 CXXScopeSpec EmptySS; 851 if (baseVariable) { 852 assert(baseVariable->getType()->isRecordType()); 853 854 // In principle we could have a member access expression that 855 // accesses an anonymous struct/union that's a static member of 856 // the base object's class. However, under the current standard, 857 // static data members cannot be anonymous structs or unions. 858 // Supporting this is as easy as building a MemberExpr here. 859 assert(!baseObjectExpr && "anonymous struct/union is static data member?"); 860 861 DeclarationNameInfo baseNameInfo(DeclarationName(), loc); 862 863 ExprResult result 864 = BuildDeclarationNameExpr(EmptySS, baseNameInfo, baseVariable); 865 if (result.isInvalid()) return ExprError(); 866 867 baseObjectExpr = result.get(); 868 } 869 870 assert((baseVariable || baseObjectExpr) && 871 "referencing anonymous struct/union without a base variable or " 872 "expression"); 873 874 // Build the implicit member references to the field of the 875 // anonymous struct/union. 876 Expr *result = baseObjectExpr; 877 IndirectFieldDecl::chain_iterator 878 FI = indirectField->chain_begin(), FEnd = indirectField->chain_end(); 879 880 // Case 2: the base of the indirect field is a field and the user 881 // wrote a member expression. 882 if (!baseVariable) { 883 FieldDecl *field = cast<FieldDecl>(*FI); 884 885 bool baseObjectIsPointer = baseObjectExpr->getType()->isPointerType(); 886 887 // Make a nameInfo that properly uses the anonymous name. 888 DeclarationNameInfo memberNameInfo(field->getDeclName(), loc); 889 890 // Build the first member access in the chain with full information. 891 result = 892 BuildFieldReferenceExpr(result, baseObjectIsPointer, SourceLocation(), 893 SS, field, foundDecl, memberNameInfo) 894 .get(); 895 if (!result) 896 return ExprError(); 897 } 898 899 // In all cases, we should now skip the first declaration in the chain. 900 ++FI; 901 902 while (FI != FEnd) { 903 FieldDecl *field = cast<FieldDecl>(*FI++); 904 905 // FIXME: these are somewhat meaningless 906 DeclarationNameInfo memberNameInfo(field->getDeclName(), loc); 907 DeclAccessPair fakeFoundDecl = 908 DeclAccessPair::make(field, field->getAccess()); 909 910 result = 911 BuildFieldReferenceExpr(result, /*isarrow*/ false, SourceLocation(), 912 (FI == FEnd ? SS : EmptySS), field, 913 fakeFoundDecl, memberNameInfo) 914 .get(); 915 } 916 917 return result; 918 } 919 920 static ExprResult 921 BuildMSPropertyRefExpr(Sema &S, Expr *BaseExpr, bool IsArrow, 922 const CXXScopeSpec &SS, 923 MSPropertyDecl *PD, 924 const DeclarationNameInfo &NameInfo) { 925 // Property names are always simple identifiers and therefore never 926 // require any interesting additional storage. 927 return new (S.Context) MSPropertyRefExpr(BaseExpr, PD, IsArrow, 928 S.Context.PseudoObjectTy, VK_LValue, 929 SS.getWithLocInContext(S.Context), 930 NameInfo.getLoc()); 931 } 932 933 MemberExpr *Sema::BuildMemberExpr( 934 Expr *Base, bool IsArrow, SourceLocation OpLoc, NestedNameSpecifierLoc NNS, 935 SourceLocation TemplateKWLoc, ValueDecl *Member, DeclAccessPair FoundDecl, 936 bool HadMultipleCandidates, const DeclarationNameInfo &MemberNameInfo, 937 QualType Ty, ExprValueKind VK, ExprObjectKind OK, 938 const TemplateArgumentListInfo *TemplateArgs) { 939 assert((!IsArrow || Base->isPRValue()) && 940 "-> base must be a pointer prvalue"); 941 MemberExpr *E = 942 MemberExpr::Create(Context, Base, IsArrow, OpLoc, NNS, TemplateKWLoc, 943 Member, FoundDecl, MemberNameInfo, TemplateArgs, Ty, 944 VK, OK, getNonOdrUseReasonInCurrentContext(Member)); 945 E->setHadMultipleCandidates(HadMultipleCandidates); 946 MarkMemberReferenced(E); 947 948 // C++ [except.spec]p17: 949 // An exception-specification is considered to be needed when: 950 // - in an expression the function is the unique lookup result or the 951 // selected member of a set of overloaded functions 952 if (auto *FPT = Ty->getAs<FunctionProtoType>()) { 953 if (isUnresolvedExceptionSpec(FPT->getExceptionSpecType())) { 954 if (auto *NewFPT = ResolveExceptionSpec(MemberNameInfo.getLoc(), FPT)) 955 E->setType(Context.getQualifiedType(NewFPT, Ty.getQualifiers())); 956 } 957 } 958 959 return E; 960 } 961 962 /// Determine if the given scope is within a function-try-block handler. 963 static bool IsInFnTryBlockHandler(const Scope *S) { 964 // Walk the scope stack until finding a FnTryCatchScope, or leave the 965 // function scope. If a FnTryCatchScope is found, check whether the TryScope 966 // flag is set. If it is not, it's a function-try-block handler. 967 for (; S != S->getFnParent(); S = S->getParent()) { 968 if (S->isFnTryCatchScope()) 969 return (S->getFlags() & Scope::TryScope) != Scope::TryScope; 970 } 971 return false; 972 } 973 974 ExprResult 975 Sema::BuildMemberReferenceExpr(Expr *BaseExpr, QualType BaseExprType, 976 SourceLocation OpLoc, bool IsArrow, 977 const CXXScopeSpec &SS, 978 SourceLocation TemplateKWLoc, 979 NamedDecl *FirstQualifierInScope, 980 LookupResult &R, 981 const TemplateArgumentListInfo *TemplateArgs, 982 const Scope *S, 983 bool SuppressQualifierCheck, 984 ActOnMemberAccessExtraArgs *ExtraArgs) { 985 assert(!SS.isInvalid() && "nested-name-specifier cannot be invalid"); 986 // If the member wasn't found in the current instantiation, or if the 987 // arrow operator was used with a dependent non-pointer object expression, 988 // build a CXXDependentScopeMemberExpr. 989 if (R.wasNotFoundInCurrentInstantiation() || 990 (R.getLookupName().getCXXOverloadedOperator() == OO_Equal && 991 (SS.isSet() ? SS.getScopeRep()->isDependent() 992 : BaseExprType->isDependentType()))) 993 return ActOnDependentMemberExpr(BaseExpr, BaseExprType, IsArrow, OpLoc, SS, 994 TemplateKWLoc, FirstQualifierInScope, 995 R.getLookupNameInfo(), TemplateArgs); 996 997 QualType BaseType = BaseExprType; 998 if (IsArrow) { 999 assert(BaseType->isPointerType()); 1000 BaseType = BaseType->castAs<PointerType>()->getPointeeType(); 1001 } 1002 R.setBaseObjectType(BaseType); 1003 1004 assert((SS.isEmpty() 1005 ? !BaseType->isDependentType() || computeDeclContext(BaseType) 1006 : !isDependentScopeSpecifier(SS) || computeDeclContext(SS)) && 1007 "dependent lookup context that isn't the current instantiation?"); 1008 1009 const DeclarationNameInfo &MemberNameInfo = R.getLookupNameInfo(); 1010 DeclarationName MemberName = MemberNameInfo.getName(); 1011 SourceLocation MemberLoc = MemberNameInfo.getLoc(); 1012 1013 if (R.isAmbiguous()) 1014 return ExprError(); 1015 1016 // [except.handle]p10: Referring to any non-static member or base class of an 1017 // object in the handler for a function-try-block of a constructor or 1018 // destructor for that object results in undefined behavior. 1019 const auto *FD = getCurFunctionDecl(); 1020 if (S && BaseExpr && FD && 1021 (isa<CXXDestructorDecl>(FD) || isa<CXXConstructorDecl>(FD)) && 1022 isa<CXXThisExpr>(BaseExpr->IgnoreImpCasts()) && 1023 IsInFnTryBlockHandler(S)) 1024 Diag(MemberLoc, diag::warn_cdtor_function_try_handler_mem_expr) 1025 << isa<CXXDestructorDecl>(FD); 1026 1027 if (R.empty()) { 1028 ExprResult RetryExpr = ExprError(); 1029 if (ExtraArgs && !IsArrow && BaseExpr && !BaseExpr->isTypeDependent()) { 1030 SFINAETrap Trap(*this, true); 1031 ParsedType ObjectType; 1032 bool MayBePseudoDestructor = false; 1033 RetryExpr = ActOnStartCXXMemberReference(getCurScope(), BaseExpr, OpLoc, 1034 tok::arrow, ObjectType, 1035 MayBePseudoDestructor); 1036 if (RetryExpr.isUsable() && !Trap.hasErrorOccurred()) { 1037 CXXScopeSpec TempSS(SS); 1038 RetryExpr = ActOnMemberAccessExpr( 1039 ExtraArgs->S, RetryExpr.get(), OpLoc, tok::arrow, TempSS, 1040 TemplateKWLoc, ExtraArgs->Id, ExtraArgs->ObjCImpDecl); 1041 } 1042 if (Trap.hasErrorOccurred()) 1043 RetryExpr = ExprError(); 1044 } 1045 1046 // Rederive where we looked up. 1047 DeclContext *DC = 1048 (SS.isSet() ? computeDeclContext(SS) : computeDeclContext(BaseType)); 1049 assert(DC); 1050 1051 if (RetryExpr.isUsable()) 1052 Diag(OpLoc, diag::err_no_member_overloaded_arrow) 1053 << MemberName << DC << FixItHint::CreateReplacement(OpLoc, "->"); 1054 else 1055 Diag(R.getNameLoc(), diag::err_no_member) 1056 << MemberName << DC 1057 << (SS.isSet() 1058 ? SS.getRange() 1059 : (BaseExpr ? BaseExpr->getSourceRange() : SourceRange())); 1060 return RetryExpr; 1061 } 1062 1063 // Diagnose lookups that find only declarations from a non-base 1064 // type. This is possible for either qualified lookups (which may 1065 // have been qualified with an unrelated type) or implicit member 1066 // expressions (which were found with unqualified lookup and thus 1067 // may have come from an enclosing scope). Note that it's okay for 1068 // lookup to find declarations from a non-base type as long as those 1069 // aren't the ones picked by overload resolution. 1070 if ((SS.isSet() || !BaseExpr || 1071 (isa<CXXThisExpr>(BaseExpr) && 1072 cast<CXXThisExpr>(BaseExpr)->isImplicit())) && 1073 !SuppressQualifierCheck && 1074 CheckQualifiedMemberReference(BaseExpr, BaseType, SS, R)) 1075 return ExprError(); 1076 1077 // Construct an unresolved result if we in fact got an unresolved 1078 // result. 1079 if (R.isOverloadedResult() || R.isUnresolvableResult()) { 1080 // Suppress any lookup-related diagnostics; we'll do these when we 1081 // pick a member. 1082 R.suppressDiagnostics(); 1083 1084 UnresolvedMemberExpr *MemExpr 1085 = UnresolvedMemberExpr::Create(Context, R.isUnresolvableResult(), 1086 BaseExpr, BaseExprType, 1087 IsArrow, OpLoc, 1088 SS.getWithLocInContext(Context), 1089 TemplateKWLoc, MemberNameInfo, 1090 TemplateArgs, R.begin(), R.end()); 1091 1092 return MemExpr; 1093 } 1094 1095 assert(R.isSingleResult()); 1096 DeclAccessPair FoundDecl = R.begin().getPair(); 1097 NamedDecl *MemberDecl = R.getFoundDecl(); 1098 1099 // FIXME: diagnose the presence of template arguments now. 1100 1101 // If the decl being referenced had an error, return an error for this 1102 // sub-expr without emitting another error, in order to avoid cascading 1103 // error cases. 1104 if (MemberDecl->isInvalidDecl()) 1105 return ExprError(); 1106 1107 // Handle the implicit-member-access case. 1108 if (!BaseExpr) { 1109 // If this is not an instance member, convert to a non-member access. 1110 if (!MemberDecl->isCXXInstanceMember()) { 1111 // We might have a variable template specialization (or maybe one day a 1112 // member concept-id). 1113 if (TemplateArgs || TemplateKWLoc.isValid()) 1114 return BuildTemplateIdExpr(SS, TemplateKWLoc, R, /*ADL*/false, TemplateArgs); 1115 1116 return BuildDeclarationNameExpr(SS, R.getLookupNameInfo(), MemberDecl, 1117 FoundDecl, TemplateArgs); 1118 } 1119 SourceLocation Loc = R.getNameLoc(); 1120 if (SS.getRange().isValid()) 1121 Loc = SS.getRange().getBegin(); 1122 BaseExpr = BuildCXXThisExpr(Loc, BaseExprType, /*IsImplicit=*/true); 1123 } 1124 1125 // C++17 [expr.ref]p2, per CWG2813: 1126 // For the first option (dot), if the id-expression names a static member or 1127 // an enumerator, the first expression is a discarded-value expression; if 1128 // the id-expression names a non-static data member, the first expression 1129 // shall be a glvalue. 1130 auto ConvertBaseExprToDiscardedValue = [&] { 1131 assert(getLangOpts().CPlusPlus && 1132 "Static member / member enumerator outside of C++"); 1133 if (IsArrow) 1134 return false; 1135 ExprResult Converted = IgnoredValueConversions(BaseExpr); 1136 if (Converted.isInvalid()) 1137 return true; 1138 BaseExpr = Converted.get(); 1139 DiagnoseDiscardedExprMarkedNodiscard(BaseExpr); 1140 return false; 1141 }; 1142 auto ConvertBaseExprToGLValue = [&] { 1143 if (IsArrow || !BaseExpr->isPRValue()) 1144 return false; 1145 ExprResult Converted = TemporaryMaterializationConversion(BaseExpr); 1146 if (Converted.isInvalid()) 1147 return true; 1148 BaseExpr = Converted.get(); 1149 return false; 1150 }; 1151 1152 // Check the use of this member. 1153 if (DiagnoseUseOfDecl(MemberDecl, MemberLoc)) 1154 return ExprError(); 1155 1156 if (FieldDecl *FD = dyn_cast<FieldDecl>(MemberDecl)) { 1157 if (ConvertBaseExprToGLValue()) 1158 return ExprError(); 1159 return BuildFieldReferenceExpr(BaseExpr, IsArrow, OpLoc, SS, FD, FoundDecl, 1160 MemberNameInfo); 1161 } 1162 1163 if (MSPropertyDecl *PD = dyn_cast<MSPropertyDecl>(MemberDecl)) { 1164 // No temporaries are materialized for property references yet. 1165 // They might be materialized when this is transformed into a member call. 1166 // Note that this is slightly different behaviour from MSVC which doesn't 1167 // implement CWG2813 yet: MSVC might materialize an extra temporary if the 1168 // getter or setter function is an explicit object member function. 1169 return BuildMSPropertyRefExpr(*this, BaseExpr, IsArrow, SS, PD, 1170 MemberNameInfo); 1171 } 1172 1173 if (IndirectFieldDecl *FD = dyn_cast<IndirectFieldDecl>(MemberDecl)) { 1174 if (ConvertBaseExprToGLValue()) 1175 return ExprError(); 1176 // We may have found a field within an anonymous union or struct 1177 // (C++ [class.union]). 1178 return BuildAnonymousStructUnionMemberReference(SS, MemberLoc, FD, 1179 FoundDecl, BaseExpr, 1180 OpLoc); 1181 } 1182 1183 // Static data member 1184 if (VarDecl *Var = dyn_cast<VarDecl>(MemberDecl)) { 1185 if (ConvertBaseExprToDiscardedValue()) 1186 return ExprError(); 1187 return BuildMemberExpr(BaseExpr, IsArrow, OpLoc, 1188 SS.getWithLocInContext(Context), TemplateKWLoc, Var, 1189 FoundDecl, /*HadMultipleCandidates=*/false, 1190 MemberNameInfo, Var->getType().getNonReferenceType(), 1191 VK_LValue, OK_Ordinary); 1192 } 1193 1194 if (CXXMethodDecl *MemberFn = dyn_cast<CXXMethodDecl>(MemberDecl)) { 1195 ExprValueKind valueKind; 1196 QualType type; 1197 if (MemberFn->isInstance()) { 1198 valueKind = VK_PRValue; 1199 type = Context.BoundMemberTy; 1200 if (MemberFn->isImplicitObjectMemberFunction() && 1201 ConvertBaseExprToGLValue()) 1202 return ExprError(); 1203 } else { 1204 // Static member function 1205 if (ConvertBaseExprToDiscardedValue()) 1206 return ExprError(); 1207 valueKind = VK_LValue; 1208 type = MemberFn->getType(); 1209 } 1210 1211 return BuildMemberExpr(BaseExpr, IsArrow, OpLoc, 1212 SS.getWithLocInContext(Context), TemplateKWLoc, 1213 MemberFn, FoundDecl, /*HadMultipleCandidates=*/false, 1214 MemberNameInfo, type, valueKind, OK_Ordinary); 1215 } 1216 assert(!isa<FunctionDecl>(MemberDecl) && "member function not C++ method?"); 1217 1218 if (EnumConstantDecl *Enum = dyn_cast<EnumConstantDecl>(MemberDecl)) { 1219 if (ConvertBaseExprToDiscardedValue()) 1220 return ExprError(); 1221 return BuildMemberExpr( 1222 BaseExpr, IsArrow, OpLoc, SS.getWithLocInContext(Context), 1223 TemplateKWLoc, Enum, FoundDecl, /*HadMultipleCandidates=*/false, 1224 MemberNameInfo, Enum->getType(), VK_PRValue, OK_Ordinary); 1225 } 1226 1227 if (VarTemplateDecl *VarTempl = dyn_cast<VarTemplateDecl>(MemberDecl)) { 1228 if (ConvertBaseExprToDiscardedValue()) 1229 return ExprError(); 1230 if (!TemplateArgs) { 1231 diagnoseMissingTemplateArguments( 1232 SS, /*TemplateKeyword=*/TemplateKWLoc.isValid(), VarTempl, MemberLoc); 1233 return ExprError(); 1234 } 1235 1236 DeclResult VDecl = CheckVarTemplateId(VarTempl, TemplateKWLoc, 1237 MemberNameInfo.getLoc(), *TemplateArgs); 1238 if (VDecl.isInvalid()) 1239 return ExprError(); 1240 1241 // Non-dependent member, but dependent template arguments. 1242 if (!VDecl.get()) 1243 return ActOnDependentMemberExpr( 1244 BaseExpr, BaseExpr->getType(), IsArrow, OpLoc, SS, TemplateKWLoc, 1245 FirstQualifierInScope, MemberNameInfo, TemplateArgs); 1246 1247 VarDecl *Var = cast<VarDecl>(VDecl.get()); 1248 if (!Var->getTemplateSpecializationKind()) 1249 Var->setTemplateSpecializationKind(TSK_ImplicitInstantiation, MemberLoc); 1250 1251 return BuildMemberExpr(BaseExpr, IsArrow, OpLoc, 1252 SS.getWithLocInContext(Context), TemplateKWLoc, Var, 1253 FoundDecl, /*HadMultipleCandidates=*/false, 1254 MemberNameInfo, Var->getType().getNonReferenceType(), 1255 VK_LValue, OK_Ordinary, TemplateArgs); 1256 } 1257 1258 // We found something that we didn't expect. Complain. 1259 if (isa<TypeDecl>(MemberDecl)) 1260 Diag(MemberLoc, diag::err_typecheck_member_reference_type) 1261 << MemberName << BaseType << int(IsArrow); 1262 else 1263 Diag(MemberLoc, diag::err_typecheck_member_reference_unknown) 1264 << MemberName << BaseType << int(IsArrow); 1265 1266 Diag(MemberDecl->getLocation(), diag::note_member_declared_here) 1267 << MemberName; 1268 R.suppressDiagnostics(); 1269 return ExprError(); 1270 } 1271 1272 /// Given that normal member access failed on the given expression, 1273 /// and given that the expression's type involves builtin-id or 1274 /// builtin-Class, decide whether substituting in the redefinition 1275 /// types would be profitable. The redefinition type is whatever 1276 /// this translation unit tried to typedef to id/Class; we store 1277 /// it to the side and then re-use it in places like this. 1278 static bool ShouldTryAgainWithRedefinitionType(Sema &S, ExprResult &base) { 1279 const ObjCObjectPointerType *opty 1280 = base.get()->getType()->getAs<ObjCObjectPointerType>(); 1281 if (!opty) return false; 1282 1283 const ObjCObjectType *ty = opty->getObjectType(); 1284 1285 QualType redef; 1286 if (ty->isObjCId()) { 1287 redef = S.Context.getObjCIdRedefinitionType(); 1288 } else if (ty->isObjCClass()) { 1289 redef = S.Context.getObjCClassRedefinitionType(); 1290 } else { 1291 return false; 1292 } 1293 1294 // Do the substitution as long as the redefinition type isn't just a 1295 // possibly-qualified pointer to builtin-id or builtin-Class again. 1296 opty = redef->getAs<ObjCObjectPointerType>(); 1297 if (opty && !opty->getObjectType()->getInterface()) 1298 return false; 1299 1300 base = S.ImpCastExprToType(base.get(), redef, CK_BitCast); 1301 return true; 1302 } 1303 1304 static bool isRecordType(QualType T) { 1305 return T->isRecordType(); 1306 } 1307 static bool isPointerToRecordType(QualType T) { 1308 if (const PointerType *PT = T->getAs<PointerType>()) 1309 return PT->getPointeeType()->isRecordType(); 1310 return false; 1311 } 1312 1313 ExprResult 1314 Sema::PerformMemberExprBaseConversion(Expr *Base, bool IsArrow) { 1315 if (IsArrow && !Base->getType()->isFunctionType()) 1316 return DefaultFunctionArrayLvalueConversion(Base); 1317 1318 return CheckPlaceholderExpr(Base); 1319 } 1320 1321 /// Look up the given member of the given non-type-dependent 1322 /// expression. This can return in one of two ways: 1323 /// * If it returns a sentinel null-but-valid result, the caller will 1324 /// assume that lookup was performed and the results written into 1325 /// the provided structure. It will take over from there. 1326 /// * Otherwise, the returned expression will be produced in place of 1327 /// an ordinary member expression. 1328 /// 1329 /// The ObjCImpDecl bit is a gross hack that will need to be properly 1330 /// fixed for ObjC++. 1331 static ExprResult LookupMemberExpr(Sema &S, LookupResult &R, 1332 ExprResult &BaseExpr, bool &IsArrow, 1333 SourceLocation OpLoc, CXXScopeSpec &SS, 1334 Decl *ObjCImpDecl, bool HasTemplateArgs, 1335 SourceLocation TemplateKWLoc) { 1336 assert(BaseExpr.get() && "no base expression"); 1337 1338 // Perform default conversions. 1339 BaseExpr = S.PerformMemberExprBaseConversion(BaseExpr.get(), IsArrow); 1340 if (BaseExpr.isInvalid()) 1341 return ExprError(); 1342 1343 QualType BaseType = BaseExpr.get()->getType(); 1344 1345 DeclarationName MemberName = R.getLookupName(); 1346 SourceLocation MemberLoc = R.getNameLoc(); 1347 1348 // For later type-checking purposes, turn arrow accesses into dot 1349 // accesses. The only access type we support that doesn't follow 1350 // the C equivalence "a->b === (*a).b" is ObjC property accesses, 1351 // and those never use arrows, so this is unaffected. 1352 if (IsArrow) { 1353 if (const PointerType *Ptr = BaseType->getAs<PointerType>()) 1354 BaseType = Ptr->getPointeeType(); 1355 else if (const ObjCObjectPointerType *Ptr = 1356 BaseType->getAs<ObjCObjectPointerType>()) 1357 BaseType = Ptr->getPointeeType(); 1358 else if (BaseType->isFunctionType()) 1359 goto fail; 1360 else if (BaseType->isDependentType()) 1361 BaseType = S.Context.DependentTy; 1362 else if (BaseType->isRecordType()) { 1363 // Recover from arrow accesses to records, e.g.: 1364 // struct MyRecord foo; 1365 // foo->bar 1366 // This is actually well-formed in C++ if MyRecord has an 1367 // overloaded operator->, but that should have been dealt with 1368 // by now--or a diagnostic message already issued if a problem 1369 // was encountered while looking for the overloaded operator->. 1370 if (!S.getLangOpts().CPlusPlus) { 1371 S.Diag(OpLoc, diag::err_typecheck_member_reference_suggestion) 1372 << BaseType << int(IsArrow) << BaseExpr.get()->getSourceRange() 1373 << FixItHint::CreateReplacement(OpLoc, "."); 1374 } 1375 IsArrow = false; 1376 } else { 1377 S.Diag(MemberLoc, diag::err_typecheck_member_reference_arrow) 1378 << BaseType << BaseExpr.get()->getSourceRange(); 1379 return ExprError(); 1380 } 1381 } 1382 1383 // If the base type is an atomic type, this access is undefined behavior per 1384 // C11 6.5.2.3p5. Instead of giving a typecheck error, we'll warn the user 1385 // about the UB and recover by converting the atomic lvalue into a non-atomic 1386 // lvalue. Because this is inherently unsafe as an atomic operation, the 1387 // warning defaults to an error. 1388 if (const auto *ATy = BaseType->getAs<AtomicType>()) { 1389 S.DiagRuntimeBehavior(OpLoc, nullptr, 1390 S.PDiag(diag::warn_atomic_member_access)); 1391 BaseType = ATy->getValueType().getUnqualifiedType(); 1392 BaseExpr = ImplicitCastExpr::Create( 1393 S.Context, IsArrow ? S.Context.getPointerType(BaseType) : BaseType, 1394 CK_AtomicToNonAtomic, BaseExpr.get(), nullptr, 1395 BaseExpr.get()->getValueKind(), FPOptionsOverride()); 1396 } 1397 1398 // Handle field access to simple records. 1399 if (BaseType->getAsRecordDecl()) { 1400 TypoExpr *TE = nullptr; 1401 if (LookupMemberExprInRecord(S, R, BaseExpr.get(), BaseType, OpLoc, IsArrow, 1402 SS, HasTemplateArgs, TemplateKWLoc, TE)) 1403 return ExprError(); 1404 1405 // Returning valid-but-null is how we indicate to the caller that 1406 // the lookup result was filled in. If typo correction was attempted and 1407 // failed, the lookup result will have been cleared--that combined with the 1408 // valid-but-null ExprResult will trigger the appropriate diagnostics. 1409 return ExprResult(TE); 1410 } else if (BaseType->isDependentType()) { 1411 R.setNotFoundInCurrentInstantiation(); 1412 return ExprEmpty(); 1413 } 1414 1415 // Handle ivar access to Objective-C objects. 1416 if (const ObjCObjectType *OTy = BaseType->getAs<ObjCObjectType>()) { 1417 if (!SS.isEmpty() && !SS.isInvalid()) { 1418 S.Diag(SS.getRange().getBegin(), diag::err_qualified_objc_access) 1419 << 1 << SS.getScopeRep() 1420 << FixItHint::CreateRemoval(SS.getRange()); 1421 SS.clear(); 1422 } 1423 1424 IdentifierInfo *Member = MemberName.getAsIdentifierInfo(); 1425 1426 // There are three cases for the base type: 1427 // - builtin id (qualified or unqualified) 1428 // - builtin Class (qualified or unqualified) 1429 // - an interface 1430 ObjCInterfaceDecl *IDecl = OTy->getInterface(); 1431 if (!IDecl) { 1432 if (S.getLangOpts().ObjCAutoRefCount && 1433 (OTy->isObjCId() || OTy->isObjCClass())) 1434 goto fail; 1435 // There's an implicit 'isa' ivar on all objects. 1436 // But we only actually find it this way on objects of type 'id', 1437 // apparently. 1438 if (OTy->isObjCId() && Member->isStr("isa")) 1439 return new (S.Context) ObjCIsaExpr(BaseExpr.get(), IsArrow, MemberLoc, 1440 OpLoc, S.Context.getObjCClassType()); 1441 if (ShouldTryAgainWithRedefinitionType(S, BaseExpr)) 1442 return LookupMemberExpr(S, R, BaseExpr, IsArrow, OpLoc, SS, 1443 ObjCImpDecl, HasTemplateArgs, TemplateKWLoc); 1444 goto fail; 1445 } 1446 1447 if (S.RequireCompleteType(OpLoc, BaseType, 1448 diag::err_typecheck_incomplete_tag, 1449 BaseExpr.get())) 1450 return ExprError(); 1451 1452 ObjCInterfaceDecl *ClassDeclared = nullptr; 1453 ObjCIvarDecl *IV = IDecl->lookupInstanceVariable(Member, ClassDeclared); 1454 1455 if (!IV) { 1456 // Attempt to correct for typos in ivar names. 1457 DeclFilterCCC<ObjCIvarDecl> Validator{}; 1458 Validator.IsObjCIvarLookup = IsArrow; 1459 if (TypoCorrection Corrected = S.CorrectTypo( 1460 R.getLookupNameInfo(), Sema::LookupMemberName, nullptr, nullptr, 1461 Validator, Sema::CTK_ErrorRecovery, IDecl)) { 1462 IV = Corrected.getCorrectionDeclAs<ObjCIvarDecl>(); 1463 S.diagnoseTypo( 1464 Corrected, 1465 S.PDiag(diag::err_typecheck_member_reference_ivar_suggest) 1466 << IDecl->getDeclName() << MemberName); 1467 1468 // Figure out the class that declares the ivar. 1469 assert(!ClassDeclared); 1470 1471 Decl *D = cast<Decl>(IV->getDeclContext()); 1472 if (auto *Category = dyn_cast<ObjCCategoryDecl>(D)) 1473 D = Category->getClassInterface(); 1474 1475 if (auto *Implementation = dyn_cast<ObjCImplementationDecl>(D)) 1476 ClassDeclared = Implementation->getClassInterface(); 1477 else if (auto *Interface = dyn_cast<ObjCInterfaceDecl>(D)) 1478 ClassDeclared = Interface; 1479 1480 assert(ClassDeclared && "cannot query interface"); 1481 } else { 1482 if (IsArrow && 1483 IDecl->FindPropertyDeclaration( 1484 Member, ObjCPropertyQueryKind::OBJC_PR_query_instance)) { 1485 S.Diag(MemberLoc, diag::err_property_found_suggest) 1486 << Member << BaseExpr.get()->getType() 1487 << FixItHint::CreateReplacement(OpLoc, "."); 1488 return ExprError(); 1489 } 1490 1491 S.Diag(MemberLoc, diag::err_typecheck_member_reference_ivar) 1492 << IDecl->getDeclName() << MemberName 1493 << BaseExpr.get()->getSourceRange(); 1494 return ExprError(); 1495 } 1496 } 1497 1498 assert(ClassDeclared); 1499 1500 // If the decl being referenced had an error, return an error for this 1501 // sub-expr without emitting another error, in order to avoid cascading 1502 // error cases. 1503 if (IV->isInvalidDecl()) 1504 return ExprError(); 1505 1506 // Check whether we can reference this field. 1507 if (S.DiagnoseUseOfDecl(IV, MemberLoc)) 1508 return ExprError(); 1509 if (IV->getAccessControl() != ObjCIvarDecl::Public && 1510 IV->getAccessControl() != ObjCIvarDecl::Package) { 1511 ObjCInterfaceDecl *ClassOfMethodDecl = nullptr; 1512 if (ObjCMethodDecl *MD = S.getCurMethodDecl()) 1513 ClassOfMethodDecl = MD->getClassInterface(); 1514 else if (ObjCImpDecl && S.getCurFunctionDecl()) { 1515 // Case of a c-function declared inside an objc implementation. 1516 // FIXME: For a c-style function nested inside an objc implementation 1517 // class, there is no implementation context available, so we pass 1518 // down the context as argument to this routine. Ideally, this context 1519 // need be passed down in the AST node and somehow calculated from the 1520 // AST for a function decl. 1521 if (ObjCImplementationDecl *IMPD = 1522 dyn_cast<ObjCImplementationDecl>(ObjCImpDecl)) 1523 ClassOfMethodDecl = IMPD->getClassInterface(); 1524 else if (ObjCCategoryImplDecl* CatImplClass = 1525 dyn_cast<ObjCCategoryImplDecl>(ObjCImpDecl)) 1526 ClassOfMethodDecl = CatImplClass->getClassInterface(); 1527 } 1528 if (!S.getLangOpts().DebuggerSupport) { 1529 if (IV->getAccessControl() == ObjCIvarDecl::Private) { 1530 if (!declaresSameEntity(ClassDeclared, IDecl) || 1531 !declaresSameEntity(ClassOfMethodDecl, ClassDeclared)) 1532 S.Diag(MemberLoc, diag::err_private_ivar_access) 1533 << IV->getDeclName(); 1534 } else if (!IDecl->isSuperClassOf(ClassOfMethodDecl)) 1535 // @protected 1536 S.Diag(MemberLoc, diag::err_protected_ivar_access) 1537 << IV->getDeclName(); 1538 } 1539 } 1540 bool warn = true; 1541 if (S.getLangOpts().ObjCWeak) { 1542 Expr *BaseExp = BaseExpr.get()->IgnoreParenImpCasts(); 1543 if (UnaryOperator *UO = dyn_cast<UnaryOperator>(BaseExp)) 1544 if (UO->getOpcode() == UO_Deref) 1545 BaseExp = UO->getSubExpr()->IgnoreParenCasts(); 1546 1547 if (DeclRefExpr *DE = dyn_cast<DeclRefExpr>(BaseExp)) 1548 if (DE->getType().getObjCLifetime() == Qualifiers::OCL_Weak) { 1549 S.Diag(DE->getLocation(), diag::err_arc_weak_ivar_access); 1550 warn = false; 1551 } 1552 } 1553 if (warn) { 1554 if (ObjCMethodDecl *MD = S.getCurMethodDecl()) { 1555 ObjCMethodFamily MF = MD->getMethodFamily(); 1556 warn = (MF != OMF_init && MF != OMF_dealloc && MF != OMF_finalize && 1557 !S.ObjC().IvarBacksCurrentMethodAccessor(IDecl, MD, IV)); 1558 } 1559 if (warn) 1560 S.Diag(MemberLoc, diag::warn_direct_ivar_access) << IV->getDeclName(); 1561 } 1562 1563 ObjCIvarRefExpr *Result = new (S.Context) ObjCIvarRefExpr( 1564 IV, IV->getUsageType(BaseType), MemberLoc, OpLoc, BaseExpr.get(), 1565 IsArrow); 1566 1567 if (IV->getType().getObjCLifetime() == Qualifiers::OCL_Weak) { 1568 if (!S.isUnevaluatedContext() && 1569 !S.Diags.isIgnored(diag::warn_arc_repeated_use_of_weak, MemberLoc)) 1570 S.getCurFunction()->recordUseOfWeak(Result); 1571 } 1572 1573 return Result; 1574 } 1575 1576 // Objective-C property access. 1577 const ObjCObjectPointerType *OPT; 1578 if (!IsArrow && (OPT = BaseType->getAs<ObjCObjectPointerType>())) { 1579 if (!SS.isEmpty() && !SS.isInvalid()) { 1580 S.Diag(SS.getRange().getBegin(), diag::err_qualified_objc_access) 1581 << 0 << SS.getScopeRep() << FixItHint::CreateRemoval(SS.getRange()); 1582 SS.clear(); 1583 } 1584 1585 // This actually uses the base as an r-value. 1586 BaseExpr = S.DefaultLvalueConversion(BaseExpr.get()); 1587 if (BaseExpr.isInvalid()) 1588 return ExprError(); 1589 1590 assert(S.Context.hasSameUnqualifiedType(BaseType, 1591 BaseExpr.get()->getType())); 1592 1593 IdentifierInfo *Member = MemberName.getAsIdentifierInfo(); 1594 1595 const ObjCObjectType *OT = OPT->getObjectType(); 1596 1597 // id, with and without qualifiers. 1598 if (OT->isObjCId()) { 1599 // Check protocols on qualified interfaces. 1600 Selector Sel = S.PP.getSelectorTable().getNullarySelector(Member); 1601 if (Decl *PMDecl = 1602 FindGetterSetterNameDecl(OPT, Member, Sel, S.Context)) { 1603 if (ObjCPropertyDecl *PD = dyn_cast<ObjCPropertyDecl>(PMDecl)) { 1604 // Check the use of this declaration 1605 if (S.DiagnoseUseOfDecl(PD, MemberLoc)) 1606 return ExprError(); 1607 1608 return new (S.Context) 1609 ObjCPropertyRefExpr(PD, S.Context.PseudoObjectTy, VK_LValue, 1610 OK_ObjCProperty, MemberLoc, BaseExpr.get()); 1611 } 1612 1613 if (ObjCMethodDecl *OMD = dyn_cast<ObjCMethodDecl>(PMDecl)) { 1614 Selector SetterSel = 1615 SelectorTable::constructSetterSelector(S.PP.getIdentifierTable(), 1616 S.PP.getSelectorTable(), 1617 Member); 1618 ObjCMethodDecl *SMD = nullptr; 1619 if (Decl *SDecl = FindGetterSetterNameDecl(OPT, 1620 /*Property id*/ nullptr, 1621 SetterSel, S.Context)) 1622 SMD = dyn_cast<ObjCMethodDecl>(SDecl); 1623 1624 return new (S.Context) 1625 ObjCPropertyRefExpr(OMD, SMD, S.Context.PseudoObjectTy, VK_LValue, 1626 OK_ObjCProperty, MemberLoc, BaseExpr.get()); 1627 } 1628 } 1629 // Use of id.member can only be for a property reference. Do not 1630 // use the 'id' redefinition in this case. 1631 if (IsArrow && ShouldTryAgainWithRedefinitionType(S, BaseExpr)) 1632 return LookupMemberExpr(S, R, BaseExpr, IsArrow, OpLoc, SS, 1633 ObjCImpDecl, HasTemplateArgs, TemplateKWLoc); 1634 1635 return ExprError(S.Diag(MemberLoc, diag::err_property_not_found) 1636 << MemberName << BaseType); 1637 } 1638 1639 // 'Class', unqualified only. 1640 if (OT->isObjCClass()) { 1641 // Only works in a method declaration (??!). 1642 ObjCMethodDecl *MD = S.getCurMethodDecl(); 1643 if (!MD) { 1644 if (ShouldTryAgainWithRedefinitionType(S, BaseExpr)) 1645 return LookupMemberExpr(S, R, BaseExpr, IsArrow, OpLoc, SS, 1646 ObjCImpDecl, HasTemplateArgs, TemplateKWLoc); 1647 1648 goto fail; 1649 } 1650 1651 // Also must look for a getter name which uses property syntax. 1652 Selector Sel = S.PP.getSelectorTable().getNullarySelector(Member); 1653 ObjCInterfaceDecl *IFace = MD->getClassInterface(); 1654 if (!IFace) 1655 goto fail; 1656 1657 ObjCMethodDecl *Getter; 1658 if ((Getter = IFace->lookupClassMethod(Sel))) { 1659 // Check the use of this method. 1660 if (S.DiagnoseUseOfDecl(Getter, MemberLoc)) 1661 return ExprError(); 1662 } else 1663 Getter = IFace->lookupPrivateMethod(Sel, false); 1664 // If we found a getter then this may be a valid dot-reference, we 1665 // will look for the matching setter, in case it is needed. 1666 Selector SetterSel = 1667 SelectorTable::constructSetterSelector(S.PP.getIdentifierTable(), 1668 S.PP.getSelectorTable(), 1669 Member); 1670 ObjCMethodDecl *Setter = IFace->lookupClassMethod(SetterSel); 1671 if (!Setter) { 1672 // If this reference is in an @implementation, also check for 'private' 1673 // methods. 1674 Setter = IFace->lookupPrivateMethod(SetterSel, false); 1675 } 1676 1677 if (Setter && S.DiagnoseUseOfDecl(Setter, MemberLoc)) 1678 return ExprError(); 1679 1680 if (Getter || Setter) { 1681 return new (S.Context) ObjCPropertyRefExpr( 1682 Getter, Setter, S.Context.PseudoObjectTy, VK_LValue, 1683 OK_ObjCProperty, MemberLoc, BaseExpr.get()); 1684 } 1685 1686 if (ShouldTryAgainWithRedefinitionType(S, BaseExpr)) 1687 return LookupMemberExpr(S, R, BaseExpr, IsArrow, OpLoc, SS, 1688 ObjCImpDecl, HasTemplateArgs, TemplateKWLoc); 1689 1690 return ExprError(S.Diag(MemberLoc, diag::err_property_not_found) 1691 << MemberName << BaseType); 1692 } 1693 1694 // Normal property access. 1695 return S.ObjC().HandleExprPropertyRefExpr( 1696 OPT, BaseExpr.get(), OpLoc, MemberName, MemberLoc, SourceLocation(), 1697 QualType(), false); 1698 } 1699 1700 if (BaseType->isExtVectorBoolType()) { 1701 // We disallow element access for ext_vector_type bool. There is no way to 1702 // materialize a reference to a vector element as a pointer (each element is 1703 // one bit in the vector). 1704 S.Diag(R.getNameLoc(), diag::err_ext_vector_component_name_illegal) 1705 << MemberName 1706 << (BaseExpr.get() ? BaseExpr.get()->getSourceRange() : SourceRange()); 1707 return ExprError(); 1708 } 1709 1710 // Handle 'field access' to vectors, such as 'V.xx'. 1711 if (BaseType->isExtVectorType()) { 1712 // FIXME: this expr should store IsArrow. 1713 IdentifierInfo *Member = MemberName.getAsIdentifierInfo(); 1714 ExprValueKind VK = (IsArrow ? VK_LValue : BaseExpr.get()->getValueKind()); 1715 QualType ret = CheckExtVectorComponent(S, BaseType, VK, OpLoc, 1716 Member, MemberLoc); 1717 if (ret.isNull()) 1718 return ExprError(); 1719 Qualifiers BaseQ = 1720 S.Context.getCanonicalType(BaseExpr.get()->getType()).getQualifiers(); 1721 ret = S.Context.getQualifiedType(ret, BaseQ); 1722 1723 return new (S.Context) 1724 ExtVectorElementExpr(ret, VK, BaseExpr.get(), *Member, MemberLoc); 1725 } 1726 1727 // Adjust builtin-sel to the appropriate redefinition type if that's 1728 // not just a pointer to builtin-sel again. 1729 if (IsArrow && BaseType->isSpecificBuiltinType(BuiltinType::ObjCSel) && 1730 !S.Context.getObjCSelRedefinitionType()->isObjCSelType()) { 1731 BaseExpr = S.ImpCastExprToType( 1732 BaseExpr.get(), S.Context.getObjCSelRedefinitionType(), CK_BitCast); 1733 return LookupMemberExpr(S, R, BaseExpr, IsArrow, OpLoc, SS, 1734 ObjCImpDecl, HasTemplateArgs, TemplateKWLoc); 1735 } 1736 1737 // Failure cases. 1738 fail: 1739 1740 // Recover from dot accesses to pointers, e.g.: 1741 // type *foo; 1742 // foo.bar 1743 // This is actually well-formed in two cases: 1744 // - 'type' is an Objective C type 1745 // - 'bar' is a pseudo-destructor name which happens to refer to 1746 // the appropriate pointer type 1747 if (const PointerType *Ptr = BaseType->getAs<PointerType>()) { 1748 if (!IsArrow && Ptr->getPointeeType()->isRecordType() && 1749 MemberName.getNameKind() != DeclarationName::CXXDestructorName) { 1750 S.Diag(OpLoc, diag::err_typecheck_member_reference_suggestion) 1751 << BaseType << int(IsArrow) << BaseExpr.get()->getSourceRange() 1752 << FixItHint::CreateReplacement(OpLoc, "->"); 1753 1754 if (S.isSFINAEContext()) 1755 return ExprError(); 1756 1757 // Recurse as an -> access. 1758 IsArrow = true; 1759 return LookupMemberExpr(S, R, BaseExpr, IsArrow, OpLoc, SS, 1760 ObjCImpDecl, HasTemplateArgs, TemplateKWLoc); 1761 } 1762 } 1763 1764 // If the user is trying to apply -> or . to a function name, it's probably 1765 // because they forgot parentheses to call that function. 1766 if (S.tryToRecoverWithCall( 1767 BaseExpr, S.PDiag(diag::err_member_reference_needs_call), 1768 /*complain*/ false, 1769 IsArrow ? &isPointerToRecordType : &isRecordType)) { 1770 if (BaseExpr.isInvalid()) 1771 return ExprError(); 1772 BaseExpr = S.DefaultFunctionArrayConversion(BaseExpr.get()); 1773 return LookupMemberExpr(S, R, BaseExpr, IsArrow, OpLoc, SS, 1774 ObjCImpDecl, HasTemplateArgs, TemplateKWLoc); 1775 } 1776 1777 // HLSL supports implicit conversion of scalar types to single element vector 1778 // rvalues in member expressions. 1779 if (S.getLangOpts().HLSL && BaseType->isScalarType()) { 1780 QualType VectorTy = S.Context.getExtVectorType(BaseType, 1); 1781 BaseExpr = S.ImpCastExprToType(BaseExpr.get(), VectorTy, CK_VectorSplat, 1782 BaseExpr.get()->getValueKind()); 1783 return LookupMemberExpr(S, R, BaseExpr, IsArrow, OpLoc, SS, ObjCImpDecl, 1784 HasTemplateArgs, TemplateKWLoc); 1785 } 1786 1787 S.Diag(OpLoc, diag::err_typecheck_member_reference_struct_union) 1788 << BaseType << BaseExpr.get()->getSourceRange() << MemberLoc; 1789 1790 return ExprError(); 1791 } 1792 1793 ExprResult Sema::ActOnMemberAccessExpr(Scope *S, Expr *Base, 1794 SourceLocation OpLoc, 1795 tok::TokenKind OpKind, CXXScopeSpec &SS, 1796 SourceLocation TemplateKWLoc, 1797 UnqualifiedId &Id, Decl *ObjCImpDecl) { 1798 // Warn about the explicit constructor calls Microsoft extension. 1799 if (getLangOpts().MicrosoftExt && 1800 Id.getKind() == UnqualifiedIdKind::IK_ConstructorName) 1801 Diag(Id.getSourceRange().getBegin(), 1802 diag::ext_ms_explicit_constructor_call); 1803 1804 TemplateArgumentListInfo TemplateArgsBuffer; 1805 1806 // Decompose the name into its component parts. 1807 DeclarationNameInfo NameInfo; 1808 const TemplateArgumentListInfo *TemplateArgs; 1809 DecomposeUnqualifiedId(Id, TemplateArgsBuffer, 1810 NameInfo, TemplateArgs); 1811 1812 bool IsArrow = (OpKind == tok::arrow); 1813 1814 if (getLangOpts().HLSL && IsArrow) 1815 return ExprError(Diag(OpLoc, diag::err_hlsl_operator_unsupported) << 2); 1816 1817 NamedDecl *FirstQualifierInScope 1818 = (!SS.isSet() ? nullptr : FindFirstQualifierInScope(S, SS.getScopeRep())); 1819 1820 // This is a postfix expression, so get rid of ParenListExprs. 1821 ExprResult Result = MaybeConvertParenListExprToParenExpr(S, Base); 1822 if (Result.isInvalid()) return ExprError(); 1823 Base = Result.get(); 1824 1825 ActOnMemberAccessExtraArgs ExtraArgs = {S, Id, ObjCImpDecl}; 1826 ExprResult Res = BuildMemberReferenceExpr( 1827 Base, Base->getType(), OpLoc, IsArrow, SS, TemplateKWLoc, 1828 FirstQualifierInScope, NameInfo, TemplateArgs, S, &ExtraArgs); 1829 1830 if (!Res.isInvalid() && isa<MemberExpr>(Res.get())) 1831 CheckMemberAccessOfNoDeref(cast<MemberExpr>(Res.get())); 1832 1833 return Res; 1834 } 1835 1836 void Sema::CheckMemberAccessOfNoDeref(const MemberExpr *E) { 1837 if (isUnevaluatedContext()) 1838 return; 1839 1840 QualType ResultTy = E->getType(); 1841 1842 // Member accesses have four cases: 1843 // 1: non-array member via "->": dereferences 1844 // 2: non-array member via ".": nothing interesting happens 1845 // 3: array member access via "->": nothing interesting happens 1846 // (this returns an array lvalue and does not actually dereference memory) 1847 // 4: array member access via ".": *adds* a layer of indirection 1848 if (ResultTy->isArrayType()) { 1849 if (!E->isArrow()) { 1850 // This might be something like: 1851 // (*structPtr).arrayMember 1852 // which behaves roughly like: 1853 // &(*structPtr).pointerMember 1854 // in that the apparent dereference in the base expression does not 1855 // actually happen. 1856 CheckAddressOfNoDeref(E->getBase()); 1857 } 1858 } else if (E->isArrow()) { 1859 if (const auto *Ptr = dyn_cast<PointerType>( 1860 E->getBase()->getType().getDesugaredType(Context))) { 1861 if (Ptr->getPointeeType()->hasAttr(attr::NoDeref)) 1862 ExprEvalContexts.back().PossibleDerefs.insert(E); 1863 } 1864 } 1865 } 1866 1867 ExprResult 1868 Sema::BuildFieldReferenceExpr(Expr *BaseExpr, bool IsArrow, 1869 SourceLocation OpLoc, const CXXScopeSpec &SS, 1870 FieldDecl *Field, DeclAccessPair FoundDecl, 1871 const DeclarationNameInfo &MemberNameInfo) { 1872 // x.a is an l-value if 'a' has a reference type. Otherwise: 1873 // x.a is an l-value/x-value/pr-value if the base is (and note 1874 // that *x is always an l-value), except that if the base isn't 1875 // an ordinary object then we must have an rvalue. 1876 ExprValueKind VK = VK_LValue; 1877 ExprObjectKind OK = OK_Ordinary; 1878 if (!IsArrow) { 1879 if (BaseExpr->getObjectKind() == OK_Ordinary) 1880 VK = BaseExpr->getValueKind(); 1881 else 1882 VK = VK_PRValue; 1883 } 1884 if (VK != VK_PRValue && Field->isBitField()) 1885 OK = OK_BitField; 1886 1887 // Figure out the type of the member; see C99 6.5.2.3p3, C++ [expr.ref] 1888 QualType MemberType = Field->getType(); 1889 if (const ReferenceType *Ref = MemberType->getAs<ReferenceType>()) { 1890 MemberType = Ref->getPointeeType(); 1891 VK = VK_LValue; 1892 } else { 1893 QualType BaseType = BaseExpr->getType(); 1894 if (IsArrow) BaseType = BaseType->castAs<PointerType>()->getPointeeType(); 1895 1896 Qualifiers BaseQuals = BaseType.getQualifiers(); 1897 1898 // GC attributes are never picked up by members. 1899 BaseQuals.removeObjCGCAttr(); 1900 1901 // CVR attributes from the base are picked up by members, 1902 // except that 'mutable' members don't pick up 'const'. 1903 if (Field->isMutable()) BaseQuals.removeConst(); 1904 1905 Qualifiers MemberQuals = 1906 Context.getCanonicalType(MemberType).getQualifiers(); 1907 1908 assert(!MemberQuals.hasAddressSpace()); 1909 1910 Qualifiers Combined = BaseQuals + MemberQuals; 1911 if (Combined != MemberQuals) 1912 MemberType = Context.getQualifiedType(MemberType, Combined); 1913 1914 // Pick up NoDeref from the base in case we end up using AddrOf on the 1915 // result. E.g. the expression 1916 // &someNoDerefPtr->pointerMember 1917 // should be a noderef pointer again. 1918 if (BaseType->hasAttr(attr::NoDeref)) 1919 MemberType = 1920 Context.getAttributedType(attr::NoDeref, MemberType, MemberType); 1921 } 1922 1923 auto isDefaultedSpecialMember = [this](const DeclContext *Ctx) { 1924 auto *Method = dyn_cast<CXXMethodDecl>(CurContext); 1925 if (!Method || !Method->isDefaulted()) 1926 return false; 1927 1928 return getDefaultedFunctionKind(Method).isSpecialMember(); 1929 }; 1930 1931 // Implicit special members should not mark fields as used. 1932 if (!isDefaultedSpecialMember(CurContext)) 1933 UnusedPrivateFields.remove(Field); 1934 1935 ExprResult Base = PerformObjectMemberConversion(BaseExpr, SS.getScopeRep(), 1936 FoundDecl, Field); 1937 if (Base.isInvalid()) 1938 return ExprError(); 1939 1940 // Build a reference to a private copy for non-static data members in 1941 // non-static member functions, privatized by OpenMP constructs. 1942 if (getLangOpts().OpenMP && IsArrow && 1943 !CurContext->isDependentContext() && 1944 isa<CXXThisExpr>(Base.get()->IgnoreParenImpCasts())) { 1945 if (auto *PrivateCopy = OpenMP().isOpenMPCapturedDecl(Field)) { 1946 return OpenMP().getOpenMPCapturedExpr(PrivateCopy, VK, OK, 1947 MemberNameInfo.getLoc()); 1948 } 1949 } 1950 1951 return BuildMemberExpr( 1952 Base.get(), IsArrow, OpLoc, SS.getWithLocInContext(Context), 1953 /*TemplateKWLoc=*/SourceLocation(), Field, FoundDecl, 1954 /*HadMultipleCandidates=*/false, MemberNameInfo, MemberType, VK, OK); 1955 } 1956 1957 ExprResult 1958 Sema::BuildImplicitMemberExpr(const CXXScopeSpec &SS, 1959 SourceLocation TemplateKWLoc, 1960 LookupResult &R, 1961 const TemplateArgumentListInfo *TemplateArgs, 1962 bool IsKnownInstance, const Scope *S) { 1963 assert(!R.empty() && !R.isAmbiguous()); 1964 1965 SourceLocation loc = R.getNameLoc(); 1966 1967 // If this is known to be an instance access, go ahead and build an 1968 // implicit 'this' expression now. 1969 QualType ThisTy = getCurrentThisType(); 1970 assert(!ThisTy.isNull() && "didn't correctly pre-flight capture of 'this'"); 1971 1972 Expr *baseExpr = nullptr; // null signifies implicit access 1973 if (IsKnownInstance) { 1974 SourceLocation Loc = R.getNameLoc(); 1975 if (SS.getRange().isValid()) 1976 Loc = SS.getRange().getBegin(); 1977 baseExpr = BuildCXXThisExpr(loc, ThisTy, /*IsImplicit=*/true); 1978 } 1979 1980 return BuildMemberReferenceExpr( 1981 baseExpr, ThisTy, 1982 /*OpLoc=*/SourceLocation(), 1983 /*IsArrow=*/!getLangOpts().HLSL, SS, TemplateKWLoc, 1984 /*FirstQualifierInScope=*/nullptr, R, TemplateArgs, S); 1985 } 1986