SemaAccess.cpp 65 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330133113321333133413351336133713381339134013411342134313441345134613471348134913501351135213531354135513561357135813591360136113621363136413651366136713681369137013711372137313741375137613771378137913801381138213831384138513861387138813891390139113921393139413951396139713981399140014011402140314041405140614071408140914101411141214131414141514161417141814191420142114221423142414251426142714281429143014311432143314341435143614371438143914401441144214431444144514461447144814491450145114521453145414551456145714581459146014611462146314641465146614671468146914701471147214731474147514761477147814791480148114821483148414851486148714881489149014911492149314941495149614971498149915001501150215031504150515061507150815091510151115121513151415151516151715181519152015211522152315241525152615271528152915301531153215331534153515361537153815391540154115421543154415451546154715481549155015511552155315541555155615571558155915601561156215631564156515661567156815691570157115721573157415751576157715781579158015811582158315841585158615871588158915901591159215931594159515961597159815991600160116021603160416051606160716081609161016111612161316141615161616171618161916201621162216231624162516261627162816291630163116321633163416351636163716381639164016411642164316441645164616471648164916501651165216531654165516561657165816591660166116621663166416651666166716681669167016711672167316741675167616771678167916801681168216831684168516861687168816891690169116921693169416951696169716981699170017011702170317041705170617071708170917101711171217131714171517161717171817191720172117221723172417251726172717281729173017311732173317341735173617371738173917401741174217431744174517461747174817491750175117521753175417551756175717581759176017611762176317641765176617671768176917701771177217731774177517761777177817791780178117821783178417851786178717881789179017911792179317941795179617971798179918001801180218031804180518061807180818091810181118121813181418151816181718181819182018211822182318241825182618271828182918301831183218331834
  1. //===---- SemaAccess.cpp - C++ Access Control -------------------*- C++ -*-===//
  2. //
  3. // The LLVM Compiler Infrastructure
  4. //
  5. // This file is distributed under the University of Illinois Open Source
  6. // License. See LICENSE.TXT for details.
  7. //
  8. //===----------------------------------------------------------------------===//
  9. //
  10. // This file provides Sema routines for C++ access control semantics.
  11. //
  12. //===----------------------------------------------------------------------===//
  13. #include "clang/Sema/SemaInternal.h"
  14. #include "clang/Sema/DelayedDiagnostic.h"
  15. #include "clang/Sema/Initialization.h"
  16. #include "clang/Sema/Lookup.h"
  17. #include "clang/AST/ASTContext.h"
  18. #include "clang/AST/CXXInheritance.h"
  19. #include "clang/AST/DeclCXX.h"
  20. #include "clang/AST/DeclFriend.h"
  21. #include "clang/AST/DeclObjC.h"
  22. #include "clang/AST/DependentDiagnostic.h"
  23. #include "clang/AST/ExprCXX.h"
  24. using namespace clang;
  25. using namespace sema;
  26. /// A copy of Sema's enum without AR_delayed.
  27. enum AccessResult {
  28. AR_accessible,
  29. AR_inaccessible,
  30. AR_dependent
  31. };
  32. /// SetMemberAccessSpecifier - Set the access specifier of a member.
  33. /// Returns true on error (when the previous member decl access specifier
  34. /// is different from the new member decl access specifier).
  35. bool Sema::SetMemberAccessSpecifier(NamedDecl *MemberDecl,
  36. NamedDecl *PrevMemberDecl,
  37. AccessSpecifier LexicalAS) {
  38. if (!PrevMemberDecl) {
  39. // Use the lexical access specifier.
  40. MemberDecl->setAccess(LexicalAS);
  41. return false;
  42. }
  43. // C++ [class.access.spec]p3: When a member is redeclared its access
  44. // specifier must be same as its initial declaration.
  45. if (LexicalAS != AS_none && LexicalAS != PrevMemberDecl->getAccess()) {
  46. Diag(MemberDecl->getLocation(),
  47. diag::err_class_redeclared_with_different_access)
  48. << MemberDecl << LexicalAS;
  49. Diag(PrevMemberDecl->getLocation(), diag::note_previous_access_declaration)
  50. << PrevMemberDecl << PrevMemberDecl->getAccess();
  51. MemberDecl->setAccess(LexicalAS);
  52. return true;
  53. }
  54. MemberDecl->setAccess(PrevMemberDecl->getAccess());
  55. return false;
  56. }
  57. static CXXRecordDecl *FindDeclaringClass(NamedDecl *D) {
  58. DeclContext *DC = D->getDeclContext();
  59. // This can only happen at top: enum decls only "publish" their
  60. // immediate members.
  61. if (isa<EnumDecl>(DC))
  62. DC = cast<EnumDecl>(DC)->getDeclContext();
  63. CXXRecordDecl *DeclaringClass = cast<CXXRecordDecl>(DC);
  64. while (DeclaringClass->isAnonymousStructOrUnion())
  65. DeclaringClass = cast<CXXRecordDecl>(DeclaringClass->getDeclContext());
  66. return DeclaringClass;
  67. }
  68. namespace {
  69. struct EffectiveContext {
  70. EffectiveContext() : Inner(0), Dependent(false) {}
  71. explicit EffectiveContext(DeclContext *DC)
  72. : Inner(DC),
  73. Dependent(DC->isDependentContext()) {
  74. // C++ [class.access.nest]p1:
  75. // A nested class is a member and as such has the same access
  76. // rights as any other member.
  77. // C++ [class.access]p2:
  78. // A member of a class can also access all the names to which
  79. // the class has access. A local class of a member function
  80. // may access the same names that the member function itself
  81. // may access.
  82. // This almost implies that the privileges of nesting are transitive.
  83. // Technically it says nothing about the local classes of non-member
  84. // functions (which can gain privileges through friendship), but we
  85. // take that as an oversight.
  86. while (true) {
  87. if (isa<CXXRecordDecl>(DC)) {
  88. CXXRecordDecl *Record = cast<CXXRecordDecl>(DC)->getCanonicalDecl();
  89. Records.push_back(Record);
  90. DC = Record->getDeclContext();
  91. } else if (isa<FunctionDecl>(DC)) {
  92. FunctionDecl *Function = cast<FunctionDecl>(DC)->getCanonicalDecl();
  93. Functions.push_back(Function);
  94. if (Function->getFriendObjectKind())
  95. DC = Function->getLexicalDeclContext();
  96. else
  97. DC = Function->getDeclContext();
  98. } else if (DC->isFileContext()) {
  99. break;
  100. } else {
  101. DC = DC->getParent();
  102. }
  103. }
  104. }
  105. bool isDependent() const { return Dependent; }
  106. bool includesClass(const CXXRecordDecl *R) const {
  107. R = R->getCanonicalDecl();
  108. return std::find(Records.begin(), Records.end(), R)
  109. != Records.end();
  110. }
  111. /// Retrieves the innermost "useful" context. Can be null if we're
  112. /// doing access-control without privileges.
  113. DeclContext *getInnerContext() const {
  114. return Inner;
  115. }
  116. typedef SmallVectorImpl<CXXRecordDecl*>::const_iterator record_iterator;
  117. DeclContext *Inner;
  118. SmallVector<FunctionDecl*, 4> Functions;
  119. SmallVector<CXXRecordDecl*, 4> Records;
  120. bool Dependent;
  121. };
  122. /// Like sema::AccessedEntity, but kindly lets us scribble all over
  123. /// it.
  124. struct AccessTarget : public AccessedEntity {
  125. AccessTarget(const AccessedEntity &Entity)
  126. : AccessedEntity(Entity) {
  127. initialize();
  128. }
  129. AccessTarget(ASTContext &Context,
  130. MemberNonce _,
  131. CXXRecordDecl *NamingClass,
  132. DeclAccessPair FoundDecl,
  133. QualType BaseObjectType)
  134. : AccessedEntity(Context.getDiagAllocator(), Member, NamingClass,
  135. FoundDecl, BaseObjectType) {
  136. initialize();
  137. }
  138. AccessTarget(ASTContext &Context,
  139. BaseNonce _,
  140. CXXRecordDecl *BaseClass,
  141. CXXRecordDecl *DerivedClass,
  142. AccessSpecifier Access)
  143. : AccessedEntity(Context.getDiagAllocator(), Base, BaseClass, DerivedClass,
  144. Access) {
  145. initialize();
  146. }
  147. bool isInstanceMember() const {
  148. return (isMemberAccess() && getTargetDecl()->isCXXInstanceMember());
  149. }
  150. bool hasInstanceContext() const {
  151. return HasInstanceContext;
  152. }
  153. class SavedInstanceContext {
  154. public:
  155. ~SavedInstanceContext() {
  156. Target.HasInstanceContext = Has;
  157. }
  158. private:
  159. friend struct AccessTarget;
  160. explicit SavedInstanceContext(AccessTarget &Target)
  161. : Target(Target), Has(Target.HasInstanceContext) {}
  162. AccessTarget &Target;
  163. bool Has;
  164. };
  165. SavedInstanceContext saveInstanceContext() {
  166. return SavedInstanceContext(*this);
  167. }
  168. void suppressInstanceContext() {
  169. HasInstanceContext = false;
  170. }
  171. const CXXRecordDecl *resolveInstanceContext(Sema &S) const {
  172. assert(HasInstanceContext);
  173. if (CalculatedInstanceContext)
  174. return InstanceContext;
  175. CalculatedInstanceContext = true;
  176. DeclContext *IC = S.computeDeclContext(getBaseObjectType());
  177. InstanceContext = (IC ? cast<CXXRecordDecl>(IC)->getCanonicalDecl() : 0);
  178. return InstanceContext;
  179. }
  180. const CXXRecordDecl *getDeclaringClass() const {
  181. return DeclaringClass;
  182. }
  183. private:
  184. void initialize() {
  185. HasInstanceContext = (isMemberAccess() &&
  186. !getBaseObjectType().isNull() &&
  187. getTargetDecl()->isCXXInstanceMember());
  188. CalculatedInstanceContext = false;
  189. InstanceContext = 0;
  190. if (isMemberAccess())
  191. DeclaringClass = FindDeclaringClass(getTargetDecl());
  192. else
  193. DeclaringClass = getBaseClass();
  194. DeclaringClass = DeclaringClass->getCanonicalDecl();
  195. }
  196. bool HasInstanceContext : 1;
  197. mutable bool CalculatedInstanceContext : 1;
  198. mutable const CXXRecordDecl *InstanceContext;
  199. const CXXRecordDecl *DeclaringClass;
  200. };
  201. }
  202. /// Checks whether one class might instantiate to the other.
  203. static bool MightInstantiateTo(const CXXRecordDecl *From,
  204. const CXXRecordDecl *To) {
  205. // Declaration names are always preserved by instantiation.
  206. if (From->getDeclName() != To->getDeclName())
  207. return false;
  208. const DeclContext *FromDC = From->getDeclContext()->getPrimaryContext();
  209. const DeclContext *ToDC = To->getDeclContext()->getPrimaryContext();
  210. if (FromDC == ToDC) return true;
  211. if (FromDC->isFileContext() || ToDC->isFileContext()) return false;
  212. // Be conservative.
  213. return true;
  214. }
  215. /// Checks whether one class is derived from another, inclusively.
  216. /// Properly indicates when it couldn't be determined due to
  217. /// dependence.
  218. ///
  219. /// This should probably be donated to AST or at least Sema.
  220. static AccessResult IsDerivedFromInclusive(const CXXRecordDecl *Derived,
  221. const CXXRecordDecl *Target) {
  222. assert(Derived->getCanonicalDecl() == Derived);
  223. assert(Target->getCanonicalDecl() == Target);
  224. if (Derived == Target) return AR_accessible;
  225. bool CheckDependent = Derived->isDependentContext();
  226. if (CheckDependent && MightInstantiateTo(Derived, Target))
  227. return AR_dependent;
  228. AccessResult OnFailure = AR_inaccessible;
  229. SmallVector<const CXXRecordDecl*, 8> Queue; // actually a stack
  230. while (true) {
  231. if (Derived->isDependentContext() && !Derived->hasDefinition())
  232. return AR_dependent;
  233. for (CXXRecordDecl::base_class_const_iterator
  234. I = Derived->bases_begin(), E = Derived->bases_end(); I != E; ++I) {
  235. const CXXRecordDecl *RD;
  236. QualType T = I->getType();
  237. if (const RecordType *RT = T->getAs<RecordType>()) {
  238. RD = cast<CXXRecordDecl>(RT->getDecl());
  239. } else if (const InjectedClassNameType *IT
  240. = T->getAs<InjectedClassNameType>()) {
  241. RD = IT->getDecl();
  242. } else {
  243. assert(T->isDependentType() && "non-dependent base wasn't a record?");
  244. OnFailure = AR_dependent;
  245. continue;
  246. }
  247. RD = RD->getCanonicalDecl();
  248. if (RD == Target) return AR_accessible;
  249. if (CheckDependent && MightInstantiateTo(RD, Target))
  250. OnFailure = AR_dependent;
  251. Queue.push_back(RD);
  252. }
  253. if (Queue.empty()) break;
  254. Derived = Queue.back();
  255. Queue.pop_back();
  256. }
  257. return OnFailure;
  258. }
  259. static bool MightInstantiateTo(Sema &S, DeclContext *Context,
  260. DeclContext *Friend) {
  261. if (Friend == Context)
  262. return true;
  263. assert(!Friend->isDependentContext() &&
  264. "can't handle friends with dependent contexts here");
  265. if (!Context->isDependentContext())
  266. return false;
  267. if (Friend->isFileContext())
  268. return false;
  269. // TODO: this is very conservative
  270. return true;
  271. }
  272. // Asks whether the type in 'context' can ever instantiate to the type
  273. // in 'friend'.
  274. static bool MightInstantiateTo(Sema &S, CanQualType Context, CanQualType Friend) {
  275. if (Friend == Context)
  276. return true;
  277. if (!Friend->isDependentType() && !Context->isDependentType())
  278. return false;
  279. // TODO: this is very conservative.
  280. return true;
  281. }
  282. static bool MightInstantiateTo(Sema &S,
  283. FunctionDecl *Context,
  284. FunctionDecl *Friend) {
  285. if (Context->getDeclName() != Friend->getDeclName())
  286. return false;
  287. if (!MightInstantiateTo(S,
  288. Context->getDeclContext(),
  289. Friend->getDeclContext()))
  290. return false;
  291. CanQual<FunctionProtoType> FriendTy
  292. = S.Context.getCanonicalType(Friend->getType())
  293. ->getAs<FunctionProtoType>();
  294. CanQual<FunctionProtoType> ContextTy
  295. = S.Context.getCanonicalType(Context->getType())
  296. ->getAs<FunctionProtoType>();
  297. // There isn't any way that I know of to add qualifiers
  298. // during instantiation.
  299. if (FriendTy.getQualifiers() != ContextTy.getQualifiers())
  300. return false;
  301. if (FriendTy->getNumArgs() != ContextTy->getNumArgs())
  302. return false;
  303. if (!MightInstantiateTo(S,
  304. ContextTy->getResultType(),
  305. FriendTy->getResultType()))
  306. return false;
  307. for (unsigned I = 0, E = FriendTy->getNumArgs(); I != E; ++I)
  308. if (!MightInstantiateTo(S,
  309. ContextTy->getArgType(I),
  310. FriendTy->getArgType(I)))
  311. return false;
  312. return true;
  313. }
  314. static bool MightInstantiateTo(Sema &S,
  315. FunctionTemplateDecl *Context,
  316. FunctionTemplateDecl *Friend) {
  317. return MightInstantiateTo(S,
  318. Context->getTemplatedDecl(),
  319. Friend->getTemplatedDecl());
  320. }
  321. static AccessResult MatchesFriend(Sema &S,
  322. const EffectiveContext &EC,
  323. const CXXRecordDecl *Friend) {
  324. if (EC.includesClass(Friend))
  325. return AR_accessible;
  326. if (EC.isDependent()) {
  327. CanQualType FriendTy
  328. = S.Context.getCanonicalType(S.Context.getTypeDeclType(Friend));
  329. for (EffectiveContext::record_iterator
  330. I = EC.Records.begin(), E = EC.Records.end(); I != E; ++I) {
  331. CanQualType ContextTy
  332. = S.Context.getCanonicalType(S.Context.getTypeDeclType(*I));
  333. if (MightInstantiateTo(S, ContextTy, FriendTy))
  334. return AR_dependent;
  335. }
  336. }
  337. return AR_inaccessible;
  338. }
  339. static AccessResult MatchesFriend(Sema &S,
  340. const EffectiveContext &EC,
  341. CanQualType Friend) {
  342. if (const RecordType *RT = Friend->getAs<RecordType>())
  343. return MatchesFriend(S, EC, cast<CXXRecordDecl>(RT->getDecl()));
  344. // TODO: we can do better than this
  345. if (Friend->isDependentType())
  346. return AR_dependent;
  347. return AR_inaccessible;
  348. }
  349. /// Determines whether the given friend class template matches
  350. /// anything in the effective context.
  351. static AccessResult MatchesFriend(Sema &S,
  352. const EffectiveContext &EC,
  353. ClassTemplateDecl *Friend) {
  354. AccessResult OnFailure = AR_inaccessible;
  355. // Check whether the friend is the template of a class in the
  356. // context chain.
  357. for (SmallVectorImpl<CXXRecordDecl*>::const_iterator
  358. I = EC.Records.begin(), E = EC.Records.end(); I != E; ++I) {
  359. CXXRecordDecl *Record = *I;
  360. // Figure out whether the current class has a template:
  361. ClassTemplateDecl *CTD;
  362. // A specialization of the template...
  363. if (isa<ClassTemplateSpecializationDecl>(Record)) {
  364. CTD = cast<ClassTemplateSpecializationDecl>(Record)
  365. ->getSpecializedTemplate();
  366. // ... or the template pattern itself.
  367. } else {
  368. CTD = Record->getDescribedClassTemplate();
  369. if (!CTD) continue;
  370. }
  371. // It's a match.
  372. if (Friend == CTD->getCanonicalDecl())
  373. return AR_accessible;
  374. // If the context isn't dependent, it can't be a dependent match.
  375. if (!EC.isDependent())
  376. continue;
  377. // If the template names don't match, it can't be a dependent
  378. // match.
  379. if (CTD->getDeclName() != Friend->getDeclName())
  380. continue;
  381. // If the class's context can't instantiate to the friend's
  382. // context, it can't be a dependent match.
  383. if (!MightInstantiateTo(S, CTD->getDeclContext(),
  384. Friend->getDeclContext()))
  385. continue;
  386. // Otherwise, it's a dependent match.
  387. OnFailure = AR_dependent;
  388. }
  389. return OnFailure;
  390. }
  391. /// Determines whether the given friend function matches anything in
  392. /// the effective context.
  393. static AccessResult MatchesFriend(Sema &S,
  394. const EffectiveContext &EC,
  395. FunctionDecl *Friend) {
  396. AccessResult OnFailure = AR_inaccessible;
  397. for (SmallVectorImpl<FunctionDecl*>::const_iterator
  398. I = EC.Functions.begin(), E = EC.Functions.end(); I != E; ++I) {
  399. if (Friend == *I)
  400. return AR_accessible;
  401. if (EC.isDependent() && MightInstantiateTo(S, *I, Friend))
  402. OnFailure = AR_dependent;
  403. }
  404. return OnFailure;
  405. }
  406. /// Determines whether the given friend function template matches
  407. /// anything in the effective context.
  408. static AccessResult MatchesFriend(Sema &S,
  409. const EffectiveContext &EC,
  410. FunctionTemplateDecl *Friend) {
  411. if (EC.Functions.empty()) return AR_inaccessible;
  412. AccessResult OnFailure = AR_inaccessible;
  413. for (SmallVectorImpl<FunctionDecl*>::const_iterator
  414. I = EC.Functions.begin(), E = EC.Functions.end(); I != E; ++I) {
  415. FunctionTemplateDecl *FTD = (*I)->getPrimaryTemplate();
  416. if (!FTD)
  417. FTD = (*I)->getDescribedFunctionTemplate();
  418. if (!FTD)
  419. continue;
  420. FTD = FTD->getCanonicalDecl();
  421. if (Friend == FTD)
  422. return AR_accessible;
  423. if (EC.isDependent() && MightInstantiateTo(S, FTD, Friend))
  424. OnFailure = AR_dependent;
  425. }
  426. return OnFailure;
  427. }
  428. /// Determines whether the given friend declaration matches anything
  429. /// in the effective context.
  430. static AccessResult MatchesFriend(Sema &S,
  431. const EffectiveContext &EC,
  432. FriendDecl *FriendD) {
  433. // Whitelist accesses if there's an invalid or unsupported friend
  434. // declaration.
  435. if (FriendD->isInvalidDecl() || FriendD->isUnsupportedFriend())
  436. return AR_accessible;
  437. if (TypeSourceInfo *T = FriendD->getFriendType())
  438. return MatchesFriend(S, EC, T->getType()->getCanonicalTypeUnqualified());
  439. NamedDecl *Friend
  440. = cast<NamedDecl>(FriendD->getFriendDecl()->getCanonicalDecl());
  441. // FIXME: declarations with dependent or templated scope.
  442. if (isa<ClassTemplateDecl>(Friend))
  443. return MatchesFriend(S, EC, cast<ClassTemplateDecl>(Friend));
  444. if (isa<FunctionTemplateDecl>(Friend))
  445. return MatchesFriend(S, EC, cast<FunctionTemplateDecl>(Friend));
  446. if (isa<CXXRecordDecl>(Friend))
  447. return MatchesFriend(S, EC, cast<CXXRecordDecl>(Friend));
  448. assert(isa<FunctionDecl>(Friend) && "unknown friend decl kind");
  449. return MatchesFriend(S, EC, cast<FunctionDecl>(Friend));
  450. }
  451. static AccessResult GetFriendKind(Sema &S,
  452. const EffectiveContext &EC,
  453. const CXXRecordDecl *Class) {
  454. AccessResult OnFailure = AR_inaccessible;
  455. // Okay, check friends.
  456. for (CXXRecordDecl::friend_iterator I = Class->friend_begin(),
  457. E = Class->friend_end(); I != E; ++I) {
  458. FriendDecl *Friend = *I;
  459. switch (MatchesFriend(S, EC, Friend)) {
  460. case AR_accessible:
  461. return AR_accessible;
  462. case AR_inaccessible:
  463. continue;
  464. case AR_dependent:
  465. OnFailure = AR_dependent;
  466. break;
  467. }
  468. }
  469. // That's it, give up.
  470. return OnFailure;
  471. }
  472. namespace {
  473. /// A helper class for checking for a friend which will grant access
  474. /// to a protected instance member.
  475. struct ProtectedFriendContext {
  476. Sema &S;
  477. const EffectiveContext &EC;
  478. const CXXRecordDecl *NamingClass;
  479. bool CheckDependent;
  480. bool EverDependent;
  481. /// The path down to the current base class.
  482. SmallVector<const CXXRecordDecl*, 20> CurPath;
  483. ProtectedFriendContext(Sema &S, const EffectiveContext &EC,
  484. const CXXRecordDecl *InstanceContext,
  485. const CXXRecordDecl *NamingClass)
  486. : S(S), EC(EC), NamingClass(NamingClass),
  487. CheckDependent(InstanceContext->isDependentContext() ||
  488. NamingClass->isDependentContext()),
  489. EverDependent(false) {}
  490. /// Check classes in the current path for friendship, starting at
  491. /// the given index.
  492. bool checkFriendshipAlongPath(unsigned I) {
  493. assert(I < CurPath.size());
  494. for (unsigned E = CurPath.size(); I != E; ++I) {
  495. switch (GetFriendKind(S, EC, CurPath[I])) {
  496. case AR_accessible: return true;
  497. case AR_inaccessible: continue;
  498. case AR_dependent: EverDependent = true; continue;
  499. }
  500. }
  501. return false;
  502. }
  503. /// Perform a search starting at the given class.
  504. ///
  505. /// PrivateDepth is the index of the last (least derived) class
  506. /// along the current path such that a notional public member of
  507. /// the final class in the path would have access in that class.
  508. bool findFriendship(const CXXRecordDecl *Cur, unsigned PrivateDepth) {
  509. // If we ever reach the naming class, check the current path for
  510. // friendship. We can also stop recursing because we obviously
  511. // won't find the naming class there again.
  512. if (Cur == NamingClass)
  513. return checkFriendshipAlongPath(PrivateDepth);
  514. if (CheckDependent && MightInstantiateTo(Cur, NamingClass))
  515. EverDependent = true;
  516. // Recurse into the base classes.
  517. for (CXXRecordDecl::base_class_const_iterator
  518. I = Cur->bases_begin(), E = Cur->bases_end(); I != E; ++I) {
  519. // If this is private inheritance, then a public member of the
  520. // base will not have any access in classes derived from Cur.
  521. unsigned BasePrivateDepth = PrivateDepth;
  522. if (I->getAccessSpecifier() == AS_private)
  523. BasePrivateDepth = CurPath.size() - 1;
  524. const CXXRecordDecl *RD;
  525. QualType T = I->getType();
  526. if (const RecordType *RT = T->getAs<RecordType>()) {
  527. RD = cast<CXXRecordDecl>(RT->getDecl());
  528. } else if (const InjectedClassNameType *IT
  529. = T->getAs<InjectedClassNameType>()) {
  530. RD = IT->getDecl();
  531. } else {
  532. assert(T->isDependentType() && "non-dependent base wasn't a record?");
  533. EverDependent = true;
  534. continue;
  535. }
  536. // Recurse. We don't need to clean up if this returns true.
  537. CurPath.push_back(RD);
  538. if (findFriendship(RD->getCanonicalDecl(), BasePrivateDepth))
  539. return true;
  540. CurPath.pop_back();
  541. }
  542. return false;
  543. }
  544. bool findFriendship(const CXXRecordDecl *Cur) {
  545. assert(CurPath.empty());
  546. CurPath.push_back(Cur);
  547. return findFriendship(Cur, 0);
  548. }
  549. };
  550. }
  551. /// Search for a class P that EC is a friend of, under the constraint
  552. /// InstanceContext <= P
  553. /// if InstanceContext exists, or else
  554. /// NamingClass <= P
  555. /// and with the additional restriction that a protected member of
  556. /// NamingClass would have some natural access in P, which implicitly
  557. /// imposes the constraint that P <= NamingClass.
  558. ///
  559. /// This isn't quite the condition laid out in the standard.
  560. /// Instead of saying that a notional protected member of NamingClass
  561. /// would have to have some natural access in P, it says the actual
  562. /// target has to have some natural access in P, which opens up the
  563. /// possibility that the target (which is not necessarily a member
  564. /// of NamingClass) might be more accessible along some path not
  565. /// passing through it. That's really a bad idea, though, because it
  566. /// introduces two problems:
  567. /// - Most importantly, it breaks encapsulation because you can
  568. /// access a forbidden base class's members by directly subclassing
  569. /// it elsewhere.
  570. /// - It also makes access substantially harder to compute because it
  571. /// breaks the hill-climbing algorithm: knowing that the target is
  572. /// accessible in some base class would no longer let you change
  573. /// the question solely to whether the base class is accessible,
  574. /// because the original target might have been more accessible
  575. /// because of crazy subclassing.
  576. /// So we don't implement that.
  577. static AccessResult GetProtectedFriendKind(Sema &S, const EffectiveContext &EC,
  578. const CXXRecordDecl *InstanceContext,
  579. const CXXRecordDecl *NamingClass) {
  580. assert(InstanceContext == 0 ||
  581. InstanceContext->getCanonicalDecl() == InstanceContext);
  582. assert(NamingClass->getCanonicalDecl() == NamingClass);
  583. // If we don't have an instance context, our constraints give us
  584. // that NamingClass <= P <= NamingClass, i.e. P == NamingClass.
  585. // This is just the usual friendship check.
  586. if (!InstanceContext) return GetFriendKind(S, EC, NamingClass);
  587. ProtectedFriendContext PRC(S, EC, InstanceContext, NamingClass);
  588. if (PRC.findFriendship(InstanceContext)) return AR_accessible;
  589. if (PRC.EverDependent) return AR_dependent;
  590. return AR_inaccessible;
  591. }
  592. static AccessResult HasAccess(Sema &S,
  593. const EffectiveContext &EC,
  594. const CXXRecordDecl *NamingClass,
  595. AccessSpecifier Access,
  596. const AccessTarget &Target) {
  597. assert(NamingClass->getCanonicalDecl() == NamingClass &&
  598. "declaration should be canonicalized before being passed here");
  599. if (Access == AS_public) return AR_accessible;
  600. assert(Access == AS_private || Access == AS_protected);
  601. AccessResult OnFailure = AR_inaccessible;
  602. for (EffectiveContext::record_iterator
  603. I = EC.Records.begin(), E = EC.Records.end(); I != E; ++I) {
  604. // All the declarations in EC have been canonicalized, so pointer
  605. // equality from this point on will work fine.
  606. const CXXRecordDecl *ECRecord = *I;
  607. // [B2] and [M2]
  608. if (Access == AS_private) {
  609. if (ECRecord == NamingClass)
  610. return AR_accessible;
  611. if (EC.isDependent() && MightInstantiateTo(ECRecord, NamingClass))
  612. OnFailure = AR_dependent;
  613. // [B3] and [M3]
  614. } else {
  615. assert(Access == AS_protected);
  616. switch (IsDerivedFromInclusive(ECRecord, NamingClass)) {
  617. case AR_accessible: break;
  618. case AR_inaccessible: continue;
  619. case AR_dependent: OnFailure = AR_dependent; continue;
  620. }
  621. // C++ [class.protected]p1:
  622. // An additional access check beyond those described earlier in
  623. // [class.access] is applied when a non-static data member or
  624. // non-static member function is a protected member of its naming
  625. // class. As described earlier, access to a protected member is
  626. // granted because the reference occurs in a friend or member of
  627. // some class C. If the access is to form a pointer to member,
  628. // the nested-name-specifier shall name C or a class derived from
  629. // C. All other accesses involve a (possibly implicit) object
  630. // expression. In this case, the class of the object expression
  631. // shall be C or a class derived from C.
  632. //
  633. // We interpret this as a restriction on [M3].
  634. // In this part of the code, 'C' is just our context class ECRecord.
  635. // These rules are different if we don't have an instance context.
  636. if (!Target.hasInstanceContext()) {
  637. // If it's not an instance member, these restrictions don't apply.
  638. if (!Target.isInstanceMember()) return AR_accessible;
  639. // If it's an instance member, use the pointer-to-member rule
  640. // that the naming class has to be derived from the effective
  641. // context.
  642. // Emulate a MSVC bug where the creation of pointer-to-member
  643. // to protected member of base class is allowed but only from
  644. // static member functions.
  645. if (S.getLangOpts().MicrosoftMode && !EC.Functions.empty())
  646. if (CXXMethodDecl* MD = dyn_cast<CXXMethodDecl>(EC.Functions.front()))
  647. if (MD->isStatic()) return AR_accessible;
  648. // Despite the standard's confident wording, there is a case
  649. // where you can have an instance member that's neither in a
  650. // pointer-to-member expression nor in a member access: when
  651. // it names a field in an unevaluated context that can't be an
  652. // implicit member. Pending clarification, we just apply the
  653. // same naming-class restriction here.
  654. // FIXME: we're probably not correctly adding the
  655. // protected-member restriction when we retroactively convert
  656. // an expression to being evaluated.
  657. // We know that ECRecord derives from NamingClass. The
  658. // restriction says to check whether NamingClass derives from
  659. // ECRecord, but that's not really necessary: two distinct
  660. // classes can't be recursively derived from each other. So
  661. // along this path, we just need to check whether the classes
  662. // are equal.
  663. if (NamingClass == ECRecord) return AR_accessible;
  664. // Otherwise, this context class tells us nothing; on to the next.
  665. continue;
  666. }
  667. assert(Target.isInstanceMember());
  668. const CXXRecordDecl *InstanceContext = Target.resolveInstanceContext(S);
  669. if (!InstanceContext) {
  670. OnFailure = AR_dependent;
  671. continue;
  672. }
  673. switch (IsDerivedFromInclusive(InstanceContext, ECRecord)) {
  674. case AR_accessible: return AR_accessible;
  675. case AR_inaccessible: continue;
  676. case AR_dependent: OnFailure = AR_dependent; continue;
  677. }
  678. }
  679. }
  680. // [M3] and [B3] say that, if the target is protected in N, we grant
  681. // access if the access occurs in a friend or member of some class P
  682. // that's a subclass of N and where the target has some natural
  683. // access in P. The 'member' aspect is easy to handle because P
  684. // would necessarily be one of the effective-context records, and we
  685. // address that above. The 'friend' aspect is completely ridiculous
  686. // to implement because there are no restrictions at all on P
  687. // *unless* the [class.protected] restriction applies. If it does,
  688. // however, we should ignore whether the naming class is a friend,
  689. // and instead rely on whether any potential P is a friend.
  690. if (Access == AS_protected && Target.isInstanceMember()) {
  691. // Compute the instance context if possible.
  692. const CXXRecordDecl *InstanceContext = 0;
  693. if (Target.hasInstanceContext()) {
  694. InstanceContext = Target.resolveInstanceContext(S);
  695. if (!InstanceContext) return AR_dependent;
  696. }
  697. switch (GetProtectedFriendKind(S, EC, InstanceContext, NamingClass)) {
  698. case AR_accessible: return AR_accessible;
  699. case AR_inaccessible: return OnFailure;
  700. case AR_dependent: return AR_dependent;
  701. }
  702. llvm_unreachable("impossible friendship kind");
  703. }
  704. switch (GetFriendKind(S, EC, NamingClass)) {
  705. case AR_accessible: return AR_accessible;
  706. case AR_inaccessible: return OnFailure;
  707. case AR_dependent: return AR_dependent;
  708. }
  709. // Silence bogus warnings
  710. llvm_unreachable("impossible friendship kind");
  711. }
  712. /// Finds the best path from the naming class to the declaring class,
  713. /// taking friend declarations into account.
  714. ///
  715. /// C++0x [class.access.base]p5:
  716. /// A member m is accessible at the point R when named in class N if
  717. /// [M1] m as a member of N is public, or
  718. /// [M2] m as a member of N is private, and R occurs in a member or
  719. /// friend of class N, or
  720. /// [M3] m as a member of N is protected, and R occurs in a member or
  721. /// friend of class N, or in a member or friend of a class P
  722. /// derived from N, where m as a member of P is public, private,
  723. /// or protected, or
  724. /// [M4] there exists a base class B of N that is accessible at R, and
  725. /// m is accessible at R when named in class B.
  726. ///
  727. /// C++0x [class.access.base]p4:
  728. /// A base class B of N is accessible at R, if
  729. /// [B1] an invented public member of B would be a public member of N, or
  730. /// [B2] R occurs in a member or friend of class N, and an invented public
  731. /// member of B would be a private or protected member of N, or
  732. /// [B3] R occurs in a member or friend of a class P derived from N, and an
  733. /// invented public member of B would be a private or protected member
  734. /// of P, or
  735. /// [B4] there exists a class S such that B is a base class of S accessible
  736. /// at R and S is a base class of N accessible at R.
  737. ///
  738. /// Along a single inheritance path we can restate both of these
  739. /// iteratively:
  740. ///
  741. /// First, we note that M1-4 are equivalent to B1-4 if the member is
  742. /// treated as a notional base of its declaring class with inheritance
  743. /// access equivalent to the member's access. Therefore we need only
  744. /// ask whether a class B is accessible from a class N in context R.
  745. ///
  746. /// Let B_1 .. B_n be the inheritance path in question (i.e. where
  747. /// B_1 = N, B_n = B, and for all i, B_{i+1} is a direct base class of
  748. /// B_i). For i in 1..n, we will calculate ACAB(i), the access to the
  749. /// closest accessible base in the path:
  750. /// Access(a, b) = (* access on the base specifier from a to b *)
  751. /// Merge(a, forbidden) = forbidden
  752. /// Merge(a, private) = forbidden
  753. /// Merge(a, b) = min(a,b)
  754. /// Accessible(c, forbidden) = false
  755. /// Accessible(c, private) = (R is c) || IsFriend(c, R)
  756. /// Accessible(c, protected) = (R derived from c) || IsFriend(c, R)
  757. /// Accessible(c, public) = true
  758. /// ACAB(n) = public
  759. /// ACAB(i) =
  760. /// let AccessToBase = Merge(Access(B_i, B_{i+1}), ACAB(i+1)) in
  761. /// if Accessible(B_i, AccessToBase) then public else AccessToBase
  762. ///
  763. /// B is an accessible base of N at R iff ACAB(1) = public.
  764. ///
  765. /// \param FinalAccess the access of the "final step", or AS_public if
  766. /// there is no final step.
  767. /// \return null if friendship is dependent
  768. static CXXBasePath *FindBestPath(Sema &S,
  769. const EffectiveContext &EC,
  770. AccessTarget &Target,
  771. AccessSpecifier FinalAccess,
  772. CXXBasePaths &Paths) {
  773. // Derive the paths to the desired base.
  774. const CXXRecordDecl *Derived = Target.getNamingClass();
  775. const CXXRecordDecl *Base = Target.getDeclaringClass();
  776. // FIXME: fail correctly when there are dependent paths.
  777. bool isDerived = Derived->isDerivedFrom(const_cast<CXXRecordDecl*>(Base),
  778. Paths);
  779. assert(isDerived && "derived class not actually derived from base");
  780. (void) isDerived;
  781. CXXBasePath *BestPath = 0;
  782. assert(FinalAccess != AS_none && "forbidden access after declaring class");
  783. bool AnyDependent = false;
  784. // Derive the friend-modified access along each path.
  785. for (CXXBasePaths::paths_iterator PI = Paths.begin(), PE = Paths.end();
  786. PI != PE; ++PI) {
  787. AccessTarget::SavedInstanceContext _ = Target.saveInstanceContext();
  788. // Walk through the path backwards.
  789. AccessSpecifier PathAccess = FinalAccess;
  790. CXXBasePath::iterator I = PI->end(), E = PI->begin();
  791. while (I != E) {
  792. --I;
  793. assert(PathAccess != AS_none);
  794. // If the declaration is a private member of a base class, there
  795. // is no level of friendship in derived classes that can make it
  796. // accessible.
  797. if (PathAccess == AS_private) {
  798. PathAccess = AS_none;
  799. break;
  800. }
  801. const CXXRecordDecl *NC = I->Class->getCanonicalDecl();
  802. AccessSpecifier BaseAccess = I->Base->getAccessSpecifier();
  803. PathAccess = std::max(PathAccess, BaseAccess);
  804. switch (HasAccess(S, EC, NC, PathAccess, Target)) {
  805. case AR_inaccessible: break;
  806. case AR_accessible:
  807. PathAccess = AS_public;
  808. // Future tests are not against members and so do not have
  809. // instance context.
  810. Target.suppressInstanceContext();
  811. break;
  812. case AR_dependent:
  813. AnyDependent = true;
  814. goto Next;
  815. }
  816. }
  817. // Note that we modify the path's Access field to the
  818. // friend-modified access.
  819. if (BestPath == 0 || PathAccess < BestPath->Access) {
  820. BestPath = &*PI;
  821. BestPath->Access = PathAccess;
  822. // Short-circuit if we found a public path.
  823. if (BestPath->Access == AS_public)
  824. return BestPath;
  825. }
  826. Next: ;
  827. }
  828. assert((!BestPath || BestPath->Access != AS_public) &&
  829. "fell out of loop with public path");
  830. // We didn't find a public path, but at least one path was subject
  831. // to dependent friendship, so delay the check.
  832. if (AnyDependent)
  833. return 0;
  834. return BestPath;
  835. }
  836. /// Given that an entity has protected natural access, check whether
  837. /// access might be denied because of the protected member access
  838. /// restriction.
  839. ///
  840. /// \return true if a note was emitted
  841. static bool TryDiagnoseProtectedAccess(Sema &S, const EffectiveContext &EC,
  842. AccessTarget &Target) {
  843. // Only applies to instance accesses.
  844. if (!Target.isInstanceMember())
  845. return false;
  846. assert(Target.isMemberAccess());
  847. const CXXRecordDecl *NamingClass = Target.getNamingClass();
  848. NamingClass = NamingClass->getCanonicalDecl();
  849. for (EffectiveContext::record_iterator
  850. I = EC.Records.begin(), E = EC.Records.end(); I != E; ++I) {
  851. const CXXRecordDecl *ECRecord = *I;
  852. switch (IsDerivedFromInclusive(ECRecord, NamingClass)) {
  853. case AR_accessible: break;
  854. case AR_inaccessible: continue;
  855. case AR_dependent: continue;
  856. }
  857. // The effective context is a subclass of the declaring class.
  858. // Check whether the [class.protected] restriction is limiting
  859. // access.
  860. // To get this exactly right, this might need to be checked more
  861. // holistically; it's not necessarily the case that gaining
  862. // access here would grant us access overall.
  863. NamedDecl *D = Target.getTargetDecl();
  864. // If we don't have an instance context, [class.protected] says the
  865. // naming class has to equal the context class.
  866. if (!Target.hasInstanceContext()) {
  867. // If it does, the restriction doesn't apply.
  868. if (NamingClass == ECRecord) continue;
  869. // TODO: it would be great to have a fixit here, since this is
  870. // such an obvious error.
  871. S.Diag(D->getLocation(), diag::note_access_protected_restricted_noobject)
  872. << S.Context.getTypeDeclType(ECRecord);
  873. return true;
  874. }
  875. const CXXRecordDecl *InstanceContext = Target.resolveInstanceContext(S);
  876. assert(InstanceContext && "diagnosing dependent access");
  877. switch (IsDerivedFromInclusive(InstanceContext, ECRecord)) {
  878. case AR_accessible: continue;
  879. case AR_dependent: continue;
  880. case AR_inaccessible:
  881. break;
  882. }
  883. // Okay, the restriction seems to be what's limiting us.
  884. // Use a special diagnostic for constructors and destructors.
  885. if (isa<CXXConstructorDecl>(D) || isa<CXXDestructorDecl>(D) ||
  886. (isa<FunctionTemplateDecl>(D) &&
  887. isa<CXXConstructorDecl>(
  888. cast<FunctionTemplateDecl>(D)->getTemplatedDecl()))) {
  889. S.Diag(D->getLocation(), diag::note_access_protected_restricted_ctordtor)
  890. << isa<CXXDestructorDecl>(D);
  891. return true;
  892. }
  893. // Otherwise, use the generic diagnostic.
  894. S.Diag(D->getLocation(), diag::note_access_protected_restricted_object)
  895. << S.Context.getTypeDeclType(ECRecord);
  896. return true;
  897. }
  898. return false;
  899. }
  900. /// Diagnose the path which caused the given declaration or base class
  901. /// to become inaccessible.
  902. static void DiagnoseAccessPath(Sema &S,
  903. const EffectiveContext &EC,
  904. AccessTarget &Entity) {
  905. AccessSpecifier Access = Entity.getAccess();
  906. NamedDecl *D = (Entity.isMemberAccess() ? Entity.getTargetDecl() : 0);
  907. const CXXRecordDecl *DeclaringClass = Entity.getDeclaringClass();
  908. // Easy case: the decl's natural access determined its path access.
  909. // We have to check against AS_private here in case Access is AS_none,
  910. // indicating a non-public member of a private base class.
  911. if (D && (Access == D->getAccess() || D->getAccess() == AS_private)) {
  912. switch (HasAccess(S, EC, DeclaringClass, D->getAccess(), Entity)) {
  913. case AR_inaccessible: {
  914. if (Access == AS_protected &&
  915. TryDiagnoseProtectedAccess(S, EC, Entity))
  916. return;
  917. // Find an original declaration.
  918. while (D->isOutOfLine()) {
  919. NamedDecl *PrevDecl = 0;
  920. if (VarDecl *VD = dyn_cast<VarDecl>(D))
  921. PrevDecl = VD->getPreviousDecl();
  922. else if (FunctionDecl *FD = dyn_cast<FunctionDecl>(D))
  923. PrevDecl = FD->getPreviousDecl();
  924. else if (TypedefNameDecl *TND = dyn_cast<TypedefNameDecl>(D))
  925. PrevDecl = TND->getPreviousDecl();
  926. else if (TagDecl *TD = dyn_cast<TagDecl>(D)) {
  927. if (isa<RecordDecl>(D) && cast<RecordDecl>(D)->isInjectedClassName())
  928. break;
  929. PrevDecl = TD->getPreviousDecl();
  930. }
  931. if (!PrevDecl) break;
  932. D = PrevDecl;
  933. }
  934. CXXRecordDecl *DeclaringClass = FindDeclaringClass(D);
  935. Decl *ImmediateChild;
  936. if (D->getDeclContext() == DeclaringClass)
  937. ImmediateChild = D;
  938. else {
  939. DeclContext *DC = D->getDeclContext();
  940. while (DC->getParent() != DeclaringClass)
  941. DC = DC->getParent();
  942. ImmediateChild = cast<Decl>(DC);
  943. }
  944. // Check whether there's an AccessSpecDecl preceding this in the
  945. // chain of the DeclContext.
  946. bool Implicit = true;
  947. for (CXXRecordDecl::decl_iterator
  948. I = DeclaringClass->decls_begin(), E = DeclaringClass->decls_end();
  949. I != E; ++I) {
  950. if (*I == ImmediateChild) break;
  951. if (isa<AccessSpecDecl>(*I)) {
  952. Implicit = false;
  953. break;
  954. }
  955. }
  956. S.Diag(D->getLocation(), diag::note_access_natural)
  957. << (unsigned) (Access == AS_protected)
  958. << Implicit;
  959. return;
  960. }
  961. case AR_accessible: break;
  962. case AR_dependent:
  963. llvm_unreachable("can't diagnose dependent access failures");
  964. }
  965. }
  966. CXXBasePaths Paths;
  967. CXXBasePath &Path = *FindBestPath(S, EC, Entity, AS_public, Paths);
  968. CXXBasePath::iterator I = Path.end(), E = Path.begin();
  969. while (I != E) {
  970. --I;
  971. const CXXBaseSpecifier *BS = I->Base;
  972. AccessSpecifier BaseAccess = BS->getAccessSpecifier();
  973. // If this is public inheritance, or the derived class is a friend,
  974. // skip this step.
  975. if (BaseAccess == AS_public)
  976. continue;
  977. switch (GetFriendKind(S, EC, I->Class)) {
  978. case AR_accessible: continue;
  979. case AR_inaccessible: break;
  980. case AR_dependent:
  981. llvm_unreachable("can't diagnose dependent access failures");
  982. }
  983. // Check whether this base specifier is the tighest point
  984. // constraining access. We have to check against AS_private for
  985. // the same reasons as above.
  986. if (BaseAccess == AS_private || BaseAccess >= Access) {
  987. // We're constrained by inheritance, but we want to say
  988. // "declared private here" if we're diagnosing a hierarchy
  989. // conversion and this is the final step.
  990. unsigned diagnostic;
  991. if (D) diagnostic = diag::note_access_constrained_by_path;
  992. else if (I + 1 == Path.end()) diagnostic = diag::note_access_natural;
  993. else diagnostic = diag::note_access_constrained_by_path;
  994. S.Diag(BS->getSourceRange().getBegin(), diagnostic)
  995. << BS->getSourceRange()
  996. << (BaseAccess == AS_protected)
  997. << (BS->getAccessSpecifierAsWritten() == AS_none);
  998. if (D)
  999. S.Diag(D->getLocation(), diag::note_field_decl);
  1000. return;
  1001. }
  1002. }
  1003. llvm_unreachable("access not apparently constrained by path");
  1004. }
  1005. static void DiagnoseBadAccess(Sema &S, SourceLocation Loc,
  1006. const EffectiveContext &EC,
  1007. AccessTarget &Entity) {
  1008. const CXXRecordDecl *NamingClass = Entity.getNamingClass();
  1009. const CXXRecordDecl *DeclaringClass = Entity.getDeclaringClass();
  1010. NamedDecl *D = (Entity.isMemberAccess() ? Entity.getTargetDecl() : 0);
  1011. S.Diag(Loc, Entity.getDiag())
  1012. << (Entity.getAccess() == AS_protected)
  1013. << (D ? D->getDeclName() : DeclarationName())
  1014. << S.Context.getTypeDeclType(NamingClass)
  1015. << S.Context.getTypeDeclType(DeclaringClass);
  1016. DiagnoseAccessPath(S, EC, Entity);
  1017. }
  1018. /// MSVC has a bug where if during an using declaration name lookup,
  1019. /// the declaration found is unaccessible (private) and that declaration
  1020. /// was bring into scope via another using declaration whose target
  1021. /// declaration is accessible (public) then no error is generated.
  1022. /// Example:
  1023. /// class A {
  1024. /// public:
  1025. /// int f();
  1026. /// };
  1027. /// class B : public A {
  1028. /// private:
  1029. /// using A::f;
  1030. /// };
  1031. /// class C : public B {
  1032. /// private:
  1033. /// using B::f;
  1034. /// };
  1035. ///
  1036. /// Here, B::f is private so this should fail in Standard C++, but
  1037. /// because B::f refers to A::f which is public MSVC accepts it.
  1038. static bool IsMicrosoftUsingDeclarationAccessBug(Sema& S,
  1039. SourceLocation AccessLoc,
  1040. AccessTarget &Entity) {
  1041. if (UsingShadowDecl *Shadow =
  1042. dyn_cast<UsingShadowDecl>(Entity.getTargetDecl())) {
  1043. const NamedDecl *OrigDecl = Entity.getTargetDecl()->getUnderlyingDecl();
  1044. if (Entity.getTargetDecl()->getAccess() == AS_private &&
  1045. (OrigDecl->getAccess() == AS_public ||
  1046. OrigDecl->getAccess() == AS_protected)) {
  1047. S.Diag(AccessLoc, diag::ext_ms_using_declaration_inaccessible)
  1048. << Shadow->getUsingDecl()->getQualifiedNameAsString()
  1049. << OrigDecl->getQualifiedNameAsString();
  1050. return true;
  1051. }
  1052. }
  1053. return false;
  1054. }
  1055. /// Determines whether the accessed entity is accessible. Public members
  1056. /// have been weeded out by this point.
  1057. static AccessResult IsAccessible(Sema &S,
  1058. const EffectiveContext &EC,
  1059. AccessTarget &Entity) {
  1060. // Determine the actual naming class.
  1061. CXXRecordDecl *NamingClass = Entity.getNamingClass();
  1062. while (NamingClass->isAnonymousStructOrUnion())
  1063. NamingClass = cast<CXXRecordDecl>(NamingClass->getParent());
  1064. NamingClass = NamingClass->getCanonicalDecl();
  1065. AccessSpecifier UnprivilegedAccess = Entity.getAccess();
  1066. assert(UnprivilegedAccess != AS_public && "public access not weeded out");
  1067. // Before we try to recalculate access paths, try to white-list
  1068. // accesses which just trade in on the final step, i.e. accesses
  1069. // which don't require [M4] or [B4]. These are by far the most
  1070. // common forms of privileged access.
  1071. if (UnprivilegedAccess != AS_none) {
  1072. switch (HasAccess(S, EC, NamingClass, UnprivilegedAccess, Entity)) {
  1073. case AR_dependent:
  1074. // This is actually an interesting policy decision. We don't
  1075. // *have* to delay immediately here: we can do the full access
  1076. // calculation in the hope that friendship on some intermediate
  1077. // class will make the declaration accessible non-dependently.
  1078. // But that's not cheap, and odds are very good (note: assertion
  1079. // made without data) that the friend declaration will determine
  1080. // access.
  1081. return AR_dependent;
  1082. case AR_accessible: return AR_accessible;
  1083. case AR_inaccessible: break;
  1084. }
  1085. }
  1086. AccessTarget::SavedInstanceContext _ = Entity.saveInstanceContext();
  1087. // We lower member accesses to base accesses by pretending that the
  1088. // member is a base class of its declaring class.
  1089. AccessSpecifier FinalAccess;
  1090. if (Entity.isMemberAccess()) {
  1091. // Determine if the declaration is accessible from EC when named
  1092. // in its declaring class.
  1093. NamedDecl *Target = Entity.getTargetDecl();
  1094. const CXXRecordDecl *DeclaringClass = Entity.getDeclaringClass();
  1095. FinalAccess = Target->getAccess();
  1096. switch (HasAccess(S, EC, DeclaringClass, FinalAccess, Entity)) {
  1097. case AR_accessible:
  1098. FinalAccess = AS_public;
  1099. break;
  1100. case AR_inaccessible: break;
  1101. case AR_dependent: return AR_dependent; // see above
  1102. }
  1103. if (DeclaringClass == NamingClass)
  1104. return (FinalAccess == AS_public ? AR_accessible : AR_inaccessible);
  1105. Entity.suppressInstanceContext();
  1106. } else {
  1107. FinalAccess = AS_public;
  1108. }
  1109. assert(Entity.getDeclaringClass() != NamingClass);
  1110. // Append the declaration's access if applicable.
  1111. CXXBasePaths Paths;
  1112. CXXBasePath *Path = FindBestPath(S, EC, Entity, FinalAccess, Paths);
  1113. if (!Path)
  1114. return AR_dependent;
  1115. assert(Path->Access <= UnprivilegedAccess &&
  1116. "access along best path worse than direct?");
  1117. if (Path->Access == AS_public)
  1118. return AR_accessible;
  1119. return AR_inaccessible;
  1120. }
  1121. static void DelayDependentAccess(Sema &S,
  1122. const EffectiveContext &EC,
  1123. SourceLocation Loc,
  1124. const AccessTarget &Entity) {
  1125. assert(EC.isDependent() && "delaying non-dependent access");
  1126. DeclContext *DC = EC.getInnerContext();
  1127. assert(DC->isDependentContext() && "delaying non-dependent access");
  1128. DependentDiagnostic::Create(S.Context, DC, DependentDiagnostic::Access,
  1129. Loc,
  1130. Entity.isMemberAccess(),
  1131. Entity.getAccess(),
  1132. Entity.getTargetDecl(),
  1133. Entity.getNamingClass(),
  1134. Entity.getBaseObjectType(),
  1135. Entity.getDiag());
  1136. }
  1137. /// Checks access to an entity from the given effective context.
  1138. static AccessResult CheckEffectiveAccess(Sema &S,
  1139. const EffectiveContext &EC,
  1140. SourceLocation Loc,
  1141. AccessTarget &Entity) {
  1142. assert(Entity.getAccess() != AS_public && "called for public access!");
  1143. if (S.getLangOpts().MicrosoftMode &&
  1144. IsMicrosoftUsingDeclarationAccessBug(S, Loc, Entity))
  1145. return AR_accessible;
  1146. switch (IsAccessible(S, EC, Entity)) {
  1147. case AR_dependent:
  1148. DelayDependentAccess(S, EC, Loc, Entity);
  1149. return AR_dependent;
  1150. case AR_inaccessible:
  1151. if (!Entity.isQuiet())
  1152. DiagnoseBadAccess(S, Loc, EC, Entity);
  1153. return AR_inaccessible;
  1154. case AR_accessible:
  1155. return AR_accessible;
  1156. }
  1157. // silence unnecessary warning
  1158. llvm_unreachable("invalid access result");
  1159. }
  1160. static Sema::AccessResult CheckAccess(Sema &S, SourceLocation Loc,
  1161. AccessTarget &Entity) {
  1162. // If the access path is public, it's accessible everywhere.
  1163. if (Entity.getAccess() == AS_public)
  1164. return Sema::AR_accessible;
  1165. // If we're currently parsing a declaration, we may need to delay
  1166. // access control checking, because our effective context might be
  1167. // different based on what the declaration comes out as.
  1168. //
  1169. // For example, we might be parsing a declaration with a scope
  1170. // specifier, like this:
  1171. // A::private_type A::foo() { ... }
  1172. //
  1173. // Or we might be parsing something that will turn out to be a friend:
  1174. // void foo(A::private_type);
  1175. // void B::foo(A::private_type);
  1176. if (S.DelayedDiagnostics.shouldDelayDiagnostics()) {
  1177. S.DelayedDiagnostics.add(DelayedDiagnostic::makeAccess(Loc, Entity));
  1178. return Sema::AR_delayed;
  1179. }
  1180. EffectiveContext EC(S.CurContext);
  1181. switch (CheckEffectiveAccess(S, EC, Loc, Entity)) {
  1182. case AR_accessible: return Sema::AR_accessible;
  1183. case AR_inaccessible: return Sema::AR_inaccessible;
  1184. case AR_dependent: return Sema::AR_dependent;
  1185. }
  1186. llvm_unreachable("falling off end");
  1187. }
  1188. void Sema::HandleDelayedAccessCheck(DelayedDiagnostic &DD, Decl *decl) {
  1189. // Access control for names used in the declarations of functions
  1190. // and function templates should normally be evaluated in the context
  1191. // of the declaration, just in case it's a friend of something.
  1192. // However, this does not apply to local extern declarations.
  1193. DeclContext *DC = decl->getDeclContext();
  1194. if (FunctionDecl *fn = dyn_cast<FunctionDecl>(decl)) {
  1195. if (!DC->isFunctionOrMethod()) DC = fn;
  1196. } else if (FunctionTemplateDecl *fnt = dyn_cast<FunctionTemplateDecl>(decl)) {
  1197. // Never a local declaration.
  1198. DC = fnt->getTemplatedDecl();
  1199. }
  1200. EffectiveContext EC(DC);
  1201. AccessTarget Target(DD.getAccessData());
  1202. if (CheckEffectiveAccess(*this, EC, DD.Loc, Target) == ::AR_inaccessible)
  1203. DD.Triggered = true;
  1204. }
  1205. void Sema::HandleDependentAccessCheck(const DependentDiagnostic &DD,
  1206. const MultiLevelTemplateArgumentList &TemplateArgs) {
  1207. SourceLocation Loc = DD.getAccessLoc();
  1208. AccessSpecifier Access = DD.getAccess();
  1209. Decl *NamingD = FindInstantiatedDecl(Loc, DD.getAccessNamingClass(),
  1210. TemplateArgs);
  1211. if (!NamingD) return;
  1212. Decl *TargetD = FindInstantiatedDecl(Loc, DD.getAccessTarget(),
  1213. TemplateArgs);
  1214. if (!TargetD) return;
  1215. if (DD.isAccessToMember()) {
  1216. CXXRecordDecl *NamingClass = cast<CXXRecordDecl>(NamingD);
  1217. NamedDecl *TargetDecl = cast<NamedDecl>(TargetD);
  1218. QualType BaseObjectType = DD.getAccessBaseObjectType();
  1219. if (!BaseObjectType.isNull()) {
  1220. BaseObjectType = SubstType(BaseObjectType, TemplateArgs, Loc,
  1221. DeclarationName());
  1222. if (BaseObjectType.isNull()) return;
  1223. }
  1224. AccessTarget Entity(Context,
  1225. AccessTarget::Member,
  1226. NamingClass,
  1227. DeclAccessPair::make(TargetDecl, Access),
  1228. BaseObjectType);
  1229. Entity.setDiag(DD.getDiagnostic());
  1230. CheckAccess(*this, Loc, Entity);
  1231. } else {
  1232. AccessTarget Entity(Context,
  1233. AccessTarget::Base,
  1234. cast<CXXRecordDecl>(TargetD),
  1235. cast<CXXRecordDecl>(NamingD),
  1236. Access);
  1237. Entity.setDiag(DD.getDiagnostic());
  1238. CheckAccess(*this, Loc, Entity);
  1239. }
  1240. }
  1241. Sema::AccessResult Sema::CheckUnresolvedLookupAccess(UnresolvedLookupExpr *E,
  1242. DeclAccessPair Found) {
  1243. if (!getLangOpts().AccessControl ||
  1244. !E->getNamingClass() ||
  1245. Found.getAccess() == AS_public)
  1246. return AR_accessible;
  1247. AccessTarget Entity(Context, AccessTarget::Member, E->getNamingClass(),
  1248. Found, QualType());
  1249. Entity.setDiag(diag::err_access) << E->getSourceRange();
  1250. return CheckAccess(*this, E->getNameLoc(), Entity);
  1251. }
  1252. /// Perform access-control checking on a previously-unresolved member
  1253. /// access which has now been resolved to a member.
  1254. Sema::AccessResult Sema::CheckUnresolvedMemberAccess(UnresolvedMemberExpr *E,
  1255. DeclAccessPair Found) {
  1256. if (!getLangOpts().AccessControl ||
  1257. Found.getAccess() == AS_public)
  1258. return AR_accessible;
  1259. QualType BaseType = E->getBaseType();
  1260. if (E->isArrow())
  1261. BaseType = BaseType->getAs<PointerType>()->getPointeeType();
  1262. AccessTarget Entity(Context, AccessTarget::Member, E->getNamingClass(),
  1263. Found, BaseType);
  1264. Entity.setDiag(diag::err_access) << E->getSourceRange();
  1265. return CheckAccess(*this, E->getMemberLoc(), Entity);
  1266. }
  1267. /// Is the given special member function accessible for the purposes of
  1268. /// deciding whether to define a special member function as deleted?
  1269. bool Sema::isSpecialMemberAccessibleForDeletion(CXXMethodDecl *decl,
  1270. AccessSpecifier access,
  1271. QualType objectType) {
  1272. // Fast path.
  1273. if (access == AS_public || !getLangOpts().AccessControl) return true;
  1274. AccessTarget entity(Context, AccessTarget::Member, decl->getParent(),
  1275. DeclAccessPair::make(decl, access), objectType);
  1276. // Suppress diagnostics.
  1277. entity.setDiag(PDiag());
  1278. switch (CheckAccess(*this, SourceLocation(), entity)) {
  1279. case AR_accessible: return true;
  1280. case AR_inaccessible: return false;
  1281. case AR_dependent: llvm_unreachable("dependent for =delete computation");
  1282. case AR_delayed: llvm_unreachable("cannot delay =delete computation");
  1283. }
  1284. llvm_unreachable("bad access result");
  1285. }
  1286. Sema::AccessResult Sema::CheckDestructorAccess(SourceLocation Loc,
  1287. CXXDestructorDecl *Dtor,
  1288. const PartialDiagnostic &PDiag,
  1289. QualType ObjectTy) {
  1290. if (!getLangOpts().AccessControl)
  1291. return AR_accessible;
  1292. // There's never a path involved when checking implicit destructor access.
  1293. AccessSpecifier Access = Dtor->getAccess();
  1294. if (Access == AS_public)
  1295. return AR_accessible;
  1296. CXXRecordDecl *NamingClass = Dtor->getParent();
  1297. if (ObjectTy.isNull()) ObjectTy = Context.getTypeDeclType(NamingClass);
  1298. AccessTarget Entity(Context, AccessTarget::Member, NamingClass,
  1299. DeclAccessPair::make(Dtor, Access),
  1300. ObjectTy);
  1301. Entity.setDiag(PDiag); // TODO: avoid copy
  1302. return CheckAccess(*this, Loc, Entity);
  1303. }
  1304. /// Checks access to a constructor.
  1305. Sema::AccessResult Sema::CheckConstructorAccess(SourceLocation UseLoc,
  1306. CXXConstructorDecl *Constructor,
  1307. const InitializedEntity &Entity,
  1308. AccessSpecifier Access,
  1309. bool IsCopyBindingRefToTemp) {
  1310. if (!getLangOpts().AccessControl || Access == AS_public)
  1311. return AR_accessible;
  1312. PartialDiagnostic PD(PDiag());
  1313. switch (Entity.getKind()) {
  1314. default:
  1315. PD = PDiag(IsCopyBindingRefToTemp
  1316. ? diag::ext_rvalue_to_reference_access_ctor
  1317. : diag::err_access_ctor);
  1318. break;
  1319. case InitializedEntity::EK_Base:
  1320. PD = PDiag(diag::err_access_base_ctor);
  1321. PD << Entity.isInheritedVirtualBase()
  1322. << Entity.getBaseSpecifier()->getType() << getSpecialMember(Constructor);
  1323. break;
  1324. case InitializedEntity::EK_Member: {
  1325. const FieldDecl *Field = cast<FieldDecl>(Entity.getDecl());
  1326. PD = PDiag(diag::err_access_field_ctor);
  1327. PD << Field->getType() << getSpecialMember(Constructor);
  1328. break;
  1329. }
  1330. case InitializedEntity::EK_LambdaCapture: {
  1331. const VarDecl *Var = Entity.getCapturedVar();
  1332. PD = PDiag(diag::err_access_lambda_capture);
  1333. PD << Var->getName() << Entity.getType() << getSpecialMember(Constructor);
  1334. break;
  1335. }
  1336. }
  1337. return CheckConstructorAccess(UseLoc, Constructor, Entity, Access, PD);
  1338. }
  1339. /// Checks access to a constructor.
  1340. Sema::AccessResult Sema::CheckConstructorAccess(SourceLocation UseLoc,
  1341. CXXConstructorDecl *Constructor,
  1342. const InitializedEntity &Entity,
  1343. AccessSpecifier Access,
  1344. const PartialDiagnostic &PD) {
  1345. if (!getLangOpts().AccessControl ||
  1346. Access == AS_public)
  1347. return AR_accessible;
  1348. CXXRecordDecl *NamingClass = Constructor->getParent();
  1349. // Initializing a base sub-object is an instance method call on an
  1350. // object of the derived class. Otherwise, we have an instance method
  1351. // call on an object of the constructed type.
  1352. CXXRecordDecl *ObjectClass;
  1353. if (Entity.getKind() == InitializedEntity::EK_Base) {
  1354. ObjectClass = cast<CXXConstructorDecl>(CurContext)->getParent();
  1355. } else {
  1356. ObjectClass = NamingClass;
  1357. }
  1358. AccessTarget AccessEntity(Context, AccessTarget::Member, NamingClass,
  1359. DeclAccessPair::make(Constructor, Access),
  1360. Context.getTypeDeclType(ObjectClass));
  1361. AccessEntity.setDiag(PD);
  1362. return CheckAccess(*this, UseLoc, AccessEntity);
  1363. }
  1364. /// Checks direct (i.e. non-inherited) access to an arbitrary class
  1365. /// member.
  1366. Sema::AccessResult Sema::CheckDirectMemberAccess(SourceLocation UseLoc,
  1367. NamedDecl *Target,
  1368. const PartialDiagnostic &Diag) {
  1369. AccessSpecifier Access = Target->getAccess();
  1370. if (!getLangOpts().AccessControl ||
  1371. Access == AS_public)
  1372. return AR_accessible;
  1373. CXXRecordDecl *NamingClass = cast<CXXRecordDecl>(Target->getDeclContext());
  1374. AccessTarget Entity(Context, AccessTarget::Member, NamingClass,
  1375. DeclAccessPair::make(Target, Access),
  1376. QualType());
  1377. Entity.setDiag(Diag);
  1378. return CheckAccess(*this, UseLoc, Entity);
  1379. }
  1380. /// Checks access to an overloaded operator new or delete.
  1381. Sema::AccessResult Sema::CheckAllocationAccess(SourceLocation OpLoc,
  1382. SourceRange PlacementRange,
  1383. CXXRecordDecl *NamingClass,
  1384. DeclAccessPair Found,
  1385. bool Diagnose) {
  1386. if (!getLangOpts().AccessControl ||
  1387. !NamingClass ||
  1388. Found.getAccess() == AS_public)
  1389. return AR_accessible;
  1390. AccessTarget Entity(Context, AccessTarget::Member, NamingClass, Found,
  1391. QualType());
  1392. if (Diagnose)
  1393. Entity.setDiag(diag::err_access)
  1394. << PlacementRange;
  1395. return CheckAccess(*this, OpLoc, Entity);
  1396. }
  1397. /// Checks access to an overloaded member operator, including
  1398. /// conversion operators.
  1399. Sema::AccessResult Sema::CheckMemberOperatorAccess(SourceLocation OpLoc,
  1400. Expr *ObjectExpr,
  1401. Expr *ArgExpr,
  1402. DeclAccessPair Found) {
  1403. if (!getLangOpts().AccessControl ||
  1404. Found.getAccess() == AS_public)
  1405. return AR_accessible;
  1406. const RecordType *RT = ObjectExpr->getType()->castAs<RecordType>();
  1407. CXXRecordDecl *NamingClass = cast<CXXRecordDecl>(RT->getDecl());
  1408. AccessTarget Entity(Context, AccessTarget::Member, NamingClass, Found,
  1409. ObjectExpr->getType());
  1410. Entity.setDiag(diag::err_access)
  1411. << ObjectExpr->getSourceRange()
  1412. << (ArgExpr ? ArgExpr->getSourceRange() : SourceRange());
  1413. return CheckAccess(*this, OpLoc, Entity);
  1414. }
  1415. Sema::AccessResult Sema::CheckAddressOfMemberAccess(Expr *OvlExpr,
  1416. DeclAccessPair Found) {
  1417. if (!getLangOpts().AccessControl ||
  1418. Found.getAccess() == AS_none ||
  1419. Found.getAccess() == AS_public)
  1420. return AR_accessible;
  1421. OverloadExpr *Ovl = OverloadExpr::find(OvlExpr).Expression;
  1422. CXXRecordDecl *NamingClass = Ovl->getNamingClass();
  1423. AccessTarget Entity(Context, AccessTarget::Member, NamingClass, Found,
  1424. /*no instance context*/ QualType());
  1425. Entity.setDiag(diag::err_access)
  1426. << Ovl->getSourceRange();
  1427. return CheckAccess(*this, Ovl->getNameLoc(), Entity);
  1428. }
  1429. /// Checks access for a hierarchy conversion.
  1430. ///
  1431. /// \param ForceCheck true if this check should be performed even if access
  1432. /// control is disabled; some things rely on this for semantics
  1433. /// \param ForceUnprivileged true if this check should proceed as if the
  1434. /// context had no special privileges
  1435. Sema::AccessResult Sema::CheckBaseClassAccess(SourceLocation AccessLoc,
  1436. QualType Base,
  1437. QualType Derived,
  1438. const CXXBasePath &Path,
  1439. unsigned DiagID,
  1440. bool ForceCheck,
  1441. bool ForceUnprivileged) {
  1442. if (!ForceCheck && !getLangOpts().AccessControl)
  1443. return AR_accessible;
  1444. if (Path.Access == AS_public)
  1445. return AR_accessible;
  1446. CXXRecordDecl *BaseD, *DerivedD;
  1447. BaseD = cast<CXXRecordDecl>(Base->getAs<RecordType>()->getDecl());
  1448. DerivedD = cast<CXXRecordDecl>(Derived->getAs<RecordType>()->getDecl());
  1449. AccessTarget Entity(Context, AccessTarget::Base, BaseD, DerivedD,
  1450. Path.Access);
  1451. if (DiagID)
  1452. Entity.setDiag(DiagID) << Derived << Base;
  1453. if (ForceUnprivileged) {
  1454. switch (CheckEffectiveAccess(*this, EffectiveContext(),
  1455. AccessLoc, Entity)) {
  1456. case ::AR_accessible: return Sema::AR_accessible;
  1457. case ::AR_inaccessible: return Sema::AR_inaccessible;
  1458. case ::AR_dependent: return Sema::AR_dependent;
  1459. }
  1460. llvm_unreachable("unexpected result from CheckEffectiveAccess");
  1461. }
  1462. return CheckAccess(*this, AccessLoc, Entity);
  1463. }
  1464. /// Checks access to all the declarations in the given result set.
  1465. void Sema::CheckLookupAccess(const LookupResult &R) {
  1466. assert(getLangOpts().AccessControl
  1467. && "performing access check without access control");
  1468. assert(R.getNamingClass() && "performing access check without naming class");
  1469. for (LookupResult::iterator I = R.begin(), E = R.end(); I != E; ++I) {
  1470. if (I.getAccess() != AS_public) {
  1471. AccessTarget Entity(Context, AccessedEntity::Member,
  1472. R.getNamingClass(), I.getPair(),
  1473. R.getBaseObjectType());
  1474. Entity.setDiag(diag::err_access);
  1475. CheckAccess(*this, R.getNameLoc(), Entity);
  1476. }
  1477. }
  1478. }
  1479. /// Checks access to Decl from the given class. The check will take access
  1480. /// specifiers into account, but no member access expressions and such.
  1481. ///
  1482. /// \param Decl the declaration to check if it can be accessed
  1483. /// \param Class the class/context from which to start the search
  1484. /// \return true if the Decl is accessible from the Class, false otherwise.
  1485. bool Sema::IsSimplyAccessible(NamedDecl *Decl, DeclContext *Ctx) {
  1486. if (CXXRecordDecl *Class = dyn_cast<CXXRecordDecl>(Ctx)) {
  1487. if (!Decl->isCXXClassMember())
  1488. return true;
  1489. QualType qType = Class->getTypeForDecl()->getCanonicalTypeInternal();
  1490. AccessTarget Entity(Context, AccessedEntity::Member, Class,
  1491. DeclAccessPair::make(Decl, Decl->getAccess()),
  1492. qType);
  1493. if (Entity.getAccess() == AS_public)
  1494. return true;
  1495. EffectiveContext EC(CurContext);
  1496. return ::IsAccessible(*this, EC, Entity) != ::AR_inaccessible;
  1497. }
  1498. if (ObjCIvarDecl *Ivar = dyn_cast<ObjCIvarDecl>(Decl)) {
  1499. // @public and @package ivars are always accessible.
  1500. if (Ivar->getCanonicalAccessControl() == ObjCIvarDecl::Public ||
  1501. Ivar->getCanonicalAccessControl() == ObjCIvarDecl::Package)
  1502. return true;
  1503. // If we are inside a class or category implementation, determine the
  1504. // interface we're in.
  1505. ObjCInterfaceDecl *ClassOfMethodDecl = 0;
  1506. if (ObjCMethodDecl *MD = getCurMethodDecl())
  1507. ClassOfMethodDecl = MD->getClassInterface();
  1508. else if (FunctionDecl *FD = getCurFunctionDecl()) {
  1509. if (ObjCImplDecl *Impl
  1510. = dyn_cast<ObjCImplDecl>(FD->getLexicalDeclContext())) {
  1511. if (ObjCImplementationDecl *IMPD
  1512. = dyn_cast<ObjCImplementationDecl>(Impl))
  1513. ClassOfMethodDecl = IMPD->getClassInterface();
  1514. else if (ObjCCategoryImplDecl* CatImplClass
  1515. = dyn_cast<ObjCCategoryImplDecl>(Impl))
  1516. ClassOfMethodDecl = CatImplClass->getClassInterface();
  1517. }
  1518. }
  1519. // If we're not in an interface, this ivar is inaccessible.
  1520. if (!ClassOfMethodDecl)
  1521. return false;
  1522. // If we're inside the same interface that owns the ivar, we're fine.
  1523. if (declaresSameEntity(ClassOfMethodDecl, Ivar->getContainingInterface()))
  1524. return true;
  1525. // If the ivar is private, it's inaccessible.
  1526. if (Ivar->getCanonicalAccessControl() == ObjCIvarDecl::Private)
  1527. return false;
  1528. return Ivar->getContainingInterface()->isSuperClassOf(ClassOfMethodDecl);
  1529. }
  1530. return true;
  1531. }