123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778 |
- //===--- TransARCAssign.cpp - Transformations to ARC mode -----------------===//
- //
- // The LLVM Compiler Infrastructure
- //
- // This file is distributed under the University of Illinois Open Source
- // License. See LICENSE.TXT for details.
- //
- //===----------------------------------------------------------------------===//
- //
- // makeAssignARCSafe:
- //
- // Add '__strong' where appropriate.
- //
- // for (id x in collection) {
- // x = 0;
- // }
- // ---->
- // for (__strong id x in collection) {
- // x = 0;
- // }
- //
- //===----------------------------------------------------------------------===//
- #include "Transforms.h"
- #include "Internals.h"
- #include "clang/AST/ASTContext.h"
- #include "clang/Sema/SemaDiagnostic.h"
- using namespace clang;
- using namespace arcmt;
- using namespace trans;
- namespace {
- class ARCAssignChecker : public RecursiveASTVisitor<ARCAssignChecker> {
- MigrationPass &Pass;
- llvm::DenseSet<VarDecl *> ModifiedVars;
- public:
- ARCAssignChecker(MigrationPass &pass) : Pass(pass) { }
- bool VisitBinaryOperator(BinaryOperator *Exp) {
- if (Exp->getType()->isDependentType())
- return true;
- Expr *E = Exp->getLHS();
- SourceLocation OrigLoc = E->getExprLoc();
- SourceLocation Loc = OrigLoc;
- DeclRefExpr *declRef = dyn_cast<DeclRefExpr>(E->IgnoreParenCasts());
- if (declRef && isa<VarDecl>(declRef->getDecl())) {
- ASTContext &Ctx = Pass.Ctx;
- Expr::isModifiableLvalueResult IsLV = E->isModifiableLvalue(Ctx, &Loc);
- if (IsLV != Expr::MLV_ConstQualified)
- return true;
- VarDecl *var = cast<VarDecl>(declRef->getDecl());
- if (var->isARCPseudoStrong()) {
- Transaction Trans(Pass.TA);
- if (Pass.TA.clearDiagnostic(diag::err_typecheck_arr_assign_enumeration,
- Exp->getOperatorLoc())) {
- if (!ModifiedVars.count(var)) {
- TypeLoc TLoc = var->getTypeSourceInfo()->getTypeLoc();
- Pass.TA.insert(TLoc.getBeginLoc(), "__strong ");
- ModifiedVars.insert(var);
- }
- }
- }
- }
-
- return true;
- }
- };
- } // anonymous namespace
- void trans::makeAssignARCSafe(MigrationPass &pass) {
- ARCAssignChecker assignCheck(pass);
- assignCheck.TraverseDecl(pass.Ctx.getTranslationUnitDecl());
- }
|