Exemplo n.º 1
0
bool trans::hasSideEffects(Expr *E, ASTContext &Ctx) {
  if (!E || !E->HasSideEffects(Ctx))
    return false;

  E = E->IgnoreParenCasts();
  ObjCMessageExpr *ME = dyn_cast<ObjCMessageExpr>(E);
  if (!ME)
    return true;
  switch (ME->getMethodFamily()) {
  case OMF_autorelease:
  case OMF_dealloc:
  case OMF_release:
  case OMF_retain:
    switch (ME->getReceiverKind()) {
    case ObjCMessageExpr::SuperInstance:
      return false;
    case ObjCMessageExpr::Instance:
      return hasSideEffects(ME->getInstanceReceiver(), Ctx);
    default:
      break;
    }
    break;
  default:
    break;
  }

  return true;
}
  // match expr against [_x delegate] or [self.x delegate]
  static bool matchObjCMessageExprForInterestingDelegate(const ObjCMessageExpr &expr,
                                                         const ObjCImplFacts &facts,
                                                         const ObjCIvarDecl **foundIvar,
                                                         const ObjCPropertyDecl **foundProperty) {
    // want an instance message to a non-null receiver
    const Expr *receiver = expr.getInstanceReceiver();
    if (!receiver) {
      return false;
    }
    const ObjCIvarDecl *ivarDecl = matchIvarLValueExpression(*receiver);
    if (!ivarDecl) {
      return false;
    }
    if (facts._ivarFactsMap.find(ivarDecl) == facts._ivarFactsMap.end()) {
      // not an interesting ivar (no entry)
      return false;
    }

    // is this a getter to an assign property?
    const ObjCPropertyDecl *propDecl = matchObjCMessageWithPropertyGetter(expr);
    if (propDecl) {
      if (propDecl->getSetterKind() != ObjCPropertyDecl::Assign) {
        return false;
      }
      // here we go!
      *foundIvar = ivarDecl;
      *foundProperty = propDecl;
      return true;
    }
    return false;
  }