private void switchOpLog(DiskRegionView dr, int lengthOfOperationCausingSwitch,
      DiskEntry entryCausingSwitch) {
    String drName;
    if (dr != null) {
      drName = dr.getName();
    } else {
      drName = getParent().getName();
    }
    flushAll(); // needed in case of async
    lengthOfOperationCausingSwitch += 20; // for worstcase overhead of writing
                                          // first record

    // if length of operation is greater than max Dir Size than an exception is
    // thrown

    if (logger.isDebugEnabled()) {
      logger.debug("Oplog::switchOpLog: Entry causing Oplog switch has diskID={}",
          (entryCausingSwitch != null ? entryCausingSwitch.getDiskId() : "Entry is null"));
    }
    if (lengthOfOperationCausingSwitch > getParent().getMaxDirSize()) {
      throw new DiskAccessException(
          String.format(
              "Operation size cannot exceed the maximum directory size. Switching problem for entry having DiskID=%s",
              (entryCausingSwitch != null
                  ? entryCausingSwitch.getDiskId().toString() : "\"null Entry\"")),
          drName);
    }
    if (LocalRegion.ISSUE_CALLBACKS_TO_CACHE_OBSERVER) {
      CacheObserverHolder.getInstance().beforeSwitchingOplog();
    }

    if (logger.isDebugEnabled()) {
      logger.debug(
          "Oplog::switchOpLog: About to add the Oplog = {} for compaction. Entry causing the switch is having DiskID = {}",
          oplogId,
          (entryCausingSwitch != null ? entryCausingSwitch.getDiskId() : "null Entry"));
    }
    if (needsCompaction()) {
      addToBeCompacted();
    } else {
      getOplogSet().addInactive(this);
    }

    try {
      DirectoryHolder nextDirHolder =
          getOplogSet().getNextDir(lengthOfOperationCausingSwitch, true);
      Oplog newOplog = new Oplog(oplogId + 1, nextDirHolder, this);
      newOplog.firstRecord = true;
      getOplogSet().setChild(newOplog);

      finishedAppending();

      // Defer the unpreblow and close of the RAF. We saw pauses in testing from
      // unpreblow of the drf, maybe because it is freeing pages that were
      // preallocated. Close can pause if another thread is calling force on the
      // file channel - see 50254. These operations should be safe to defer,
      // a concurrent read will synchronize on the oplog and use or reopen the
      // RAF
      // as needed.
      getParent().executeDelayedExpensiveWrite(() -> {
        // need to truncate crf and drf if their actual size is less than
        // their pregrow size
        unpreblow(crf, getMaxCrfSize());
        unpreblow(drf, getMaxDrfSize());
        // Close the crf using closeRAF. We will reopen the crf if we
        // need it to fault in or to read values during compaction.
        closeRAF();
        // I think at this point the drf no longer needs to be open
        synchronized (lock/* drf */) {
          if (!drf.RAFClosed) {
            try {
              drf.channel.close();
            } catch (IOException ignore) {
            }
            try {
              drf.raf.close();
            } catch (IOException ignore) {
            }
            drf.RAFClosed = true;
          }
        }

      });

      // offline compaction will not execute create Krf in the task, becasue
      // this.totalLiveCount.get() == 0
      if (getParent().isOfflineCompacting()) {
        krfClose();
      } else {
        createKrfAsync();
      }
    } catch (DiskAccessException dae) {
      // Remove the Oplog which was added in the DiskStoreImpl
      // for compaction as compaction cannot be done.
      // However, it is also possible that compactor
      // may have done the compaction of the Oplog but the switching thread
      // encountered timeout exception.
      // So the code below may or may not actually
      // ensure that the Oplog has been compacted or not.
      getOplogSet().removeOplog(oplogId);
      throw dae;
    }
  }
This function is used to switch from one op Log to another , when the size of the current oplog
has reached the maximum permissible. It is always called from synch block with lock object
being the OpLog File object We will reuse the ByteBuffer Pool. We should add the current Oplog
for compaction first & then try to get next directory holder as in case there is only a single
directory with space being full, compaction has to happen before it can be given a new
directory. If the operation causing the switching is on an Entry which already is referencing
the oplog to be compacted, then the compactor thread will skip compaction that entry & the
switching thread will roll the entry explicitly.

@param lengthOfOperationCausingSwitch length of the operation causing the switch
@param entryCausingSwitch DiskEntry object operation on which caused the switching of Oplog.
       This can be null if the switching has been invoked by the forceRolling which does not
       need an operation on entry to cause the switch
geode-core/src/main/java/org/apache/geode/internal/cache/Oplog.java