final V replaceNode(long key, V value, Object cv) {
    int hash = spread(key);
      for (Node<V>[] tab = table;;) {
          Node<V> f; int n, i, fh;
          if (tab == null || (n = tab.length) == 0 ||
              (f = tabAt(tab, i = (n - 1) & hash)) == null)
              break;
          else if ((fh = f.hash) == MOVED)
              tab = helpTransfer(tab, f);
          else {
              V oldVal = null;
              boolean validated = false;
              synchronized (f) {
                  if (tabAt(tab, i) == f) {
                      if (fh >= 0) {
                          validated = true;
                          for (Node<V> e = f, pred = null;;) {
                              if (e.key == key) {
                                  V ev = e.val;
                                  if (cv == null || cv == ev ||
                                      (ev != null && cv.equals(ev))) {
                                      oldVal = ev;
                                      if (value != null)
                                          e.val = value;
                                      else if (pred != null)
                                          pred.next = e.next;
                                      else
                                          setTabAt(tab, i, e.next);
                                  }
                                  break;
                              }
                              pred = e;
                              if ((e = e.next) == null)
                                  break;
                          }
                      }
                      else if (f instanceof TreeBin) {
                          validated = true;
                          TreeBin<V> t = (TreeBin<V>)f;
                          TreeNode<V> r, p;
                          if ((r = t.root) != null &&
                              (p = r.findTreeNode(hash, key)) != null) {
                              V pv = p.val;
                              if (cv == null || cv == pv ||
                                  (pv != null && cv.equals(pv))) {
                                  oldVal = pv;
                                  if (value != null)
                                      p.val = value;
                                  else if (t.removeTreeNode(p))
                                      setTabAt(tab, i, untreeify(t.first));
                              }
                          }
                      }
                      else if (f instanceof ReservationNode)
                          throw new IllegalStateException("Recursive update");
                  }
              }
              if (validated) {
                  if (oldVal != null) {
                      if (value == null)
                          addCount(-1L, -1);
                      return oldVal;
                  }
                  break;
              }
          }
      }
      return null;
  }
final V replaceNode(long key, V value, Object cv)