/// Like ValueIsPHI but also check if the PHI has no source
  /// operands, i.e., it was just added.
  static SILArgument *ValueIsNewPHI(SILValue Val, SILSSAUpdater *Updater) {
    SILArgument *PHI = ValueIsPHI(Val, Updater);
    if (PHI) {
      auto *PhiBB = PHI->getParent();
      size_t PhiIdx = PHI->getIndex();

      // If all predecessor edges are 'not set' this is a new phi.
      for (auto *PredBB : PhiBB->getPreds()) {
        OperandValueArrayRef Edges =
            getEdgeValuesForTerminator(PredBB->getTerminator(), PhiBB);

        assert(PhiIdx < Edges.size() && "Not enough edges!");

        SILValue V = Edges[PhiIdx];
        // Check for the 'not set' sentinel.
        if (V.getDef() != Updater->PHISentinel.get())
          return nullptr;
      }
      return PHI;
    }
    return nullptr;
  }
Example #2
0
Effects *FunctionEffects::getEffectsOn(SILValue Addr) {
  SILValue BaseAddr = skipValueProjections(skipAddrProjections(Addr));
  switch (BaseAddr->getKind()) {
    case swift::ValueKind::SILArgument: {
      // Can we associate the address to a function parameter?
      SILArgument *Arg = cast<SILArgument>(BaseAddr);
      if (Arg->isFunctionArg()) {
        return &ParamEffects[Arg->getIndex()];
      }
      break;
    }
    case ValueKind::AllocStackInst:
    case ValueKind::AllocRefInst:
    case ValueKind::AllocRefDynamicInst:
    case ValueKind::AllocBoxInst:
      // Effects on locally allocated storage.
      return &LocalEffects;
    default:
      break;
  }
  // Everything else.
  return &GlobalEffects;
}