private void processUse(
      RegisterSpec def, SsaInsn use, EscapeSet escSet, ArrayList<RegisterSpec> regWorklist) {
    int useOpcode = use.getOpcode().getOpcode();
    switch (useOpcode) {
      case RegOps.MOVE:
        // Follow uses of the move by adding it to the worklist
        escSet.regSet.set(use.getResult().getReg());
        regWorklist.add(use.getResult());
        break;
      case RegOps.IF_EQ:
      case RegOps.IF_NE:
      case RegOps.CHECK_CAST:
        // Compared objects can't be replaced, so promote if necessary
        if (escSet.escape.compareTo(EscapeState.METHOD) < 0) {
          escSet.escape = EscapeState.METHOD;
        }
        break;
      case RegOps.APUT:
        // For array puts, check for a constant array index
        RegisterSpec putIndex = use.getSources().get(2);
        if (!putIndex.getTypeBearer().isConstant()) {
          // If not constant, array can't be replaced
          escSet.replaceableArray = false;
        }
        // Intentional fallthrough
      case RegOps.PUT_FIELD:
        // Skip non-object puts
        RegisterSpec putValue = use.getSources().get(0);
        if (putValue.getTypeBearer().getBasicType() != Type.BT_OBJECT) {
          break;
        }
        escSet.replaceableArray = false;

        // Raise 1st object's escape state to 2nd if 2nd is higher
        RegisterSpecList sources = use.getSources();
        if (sources.get(0).getReg() == def.getReg()) {
          int setIndex = findSetIndex(sources.get(1));
          if (setIndex != latticeValues.size()) {
            EscapeSet parentSet = latticeValues.get(setIndex);
            addEdge(parentSet, escSet);
            if (escSet.escape.compareTo(parentSet.escape) < 0) {
              escSet.escape = parentSet.escape;
            }
          }
        } else {
          int setIndex = findSetIndex(sources.get(0));
          if (setIndex != latticeValues.size()) {
            EscapeSet childSet = latticeValues.get(setIndex);
            addEdge(escSet, childSet);
            if (childSet.escape.compareTo(escSet.escape) < 0) {
              childSet.escape = escSet.escape;
            }
          }
        }
        break;
      case RegOps.AGET:
        // For array gets, check for a constant array index
        RegisterSpec getIndex = use.getSources().get(1);
        if (!getIndex.getTypeBearer().isConstant()) {
          // If not constant, array can't be replaced
          escSet.replaceableArray = false;
        }
        break;
      case RegOps.PUT_STATIC:
        // Static puts cause an object to escape globally
        escSet.escape = EscapeState.GLOBAL;
        break;
      case RegOps.INVOKE_STATIC:
      case RegOps.INVOKE_VIRTUAL:
      case RegOps.INVOKE_SUPER:
      case RegOps.INVOKE_DIRECT:
      case RegOps.INVOKE_INTERFACE:
      case RegOps.RETURN:
      case RegOps.THROW:
        // These operations cause an object to escape interprocedurally
        escSet.escape = EscapeState.INTER;
        break;
      default:
        break;
    }
  }
Handles non-phi uses of new objects. Checks to see how instruction is used and updates the
escape state accordingly.

@param def {@code non-null;} register holding definition of new object
@param use {@code non-null;} use of object being processed
@param escSet {@code non-null;} EscapeSet for the object
@param regWorklist {@code non-null;} worklist of instructions left to process for this object
android/android_framework/dex-maker/src/main/java/com/android/dx/ssa/EscapeAnalysis.java