default ValidOffsetAndEpoch validateOffsetAndEpoch(long offset, int epoch) {
        if (startOffset() == 0 && offset == 0) {
            return ValidOffsetAndEpoch.valid(new OffsetAndEpoch(0, 0));
        }

        Optional<OffsetAndEpoch> earliestSnapshotId = earliestSnapshotId();
        if (earliestSnapshotId.isPresent() &&
            ((offset < startOffset()) ||
             (offset == startOffset() && epoch != earliestSnapshotId.get().epoch()) ||
             (epoch < earliestSnapshotId.get().epoch()))
        ) {
            /* Send a snapshot if the leader has a snapshot at the log start offset and
             * 1. the fetch offset is less than the log start offset or
             * 2. the fetch offset is equal to the log start offset and last fetch epoch doesn't match
             *    the oldest snapshot or
             * 3. last fetch epoch is less than the oldest snapshot's epoch
             */
            OffsetAndEpoch latestSnapshotId = latestSnapshotId().orElseThrow(() -> new IllegalStateException(
                String.format(
                    "Log start offset (%d) is greater than zero but latest snapshot was not found",
                    startOffset()
                )
            ));

            return ValidOffsetAndEpoch.snapshot(latestSnapshotId);
        } else {
            OffsetAndEpoch endOffsetAndEpoch = endOffsetForEpoch(epoch);

            if (endOffsetAndEpoch.epoch() != epoch || endOffsetAndEpoch.offset() < offset) {
                return ValidOffsetAndEpoch.diverging(endOffsetAndEpoch);
            } else {
                return ValidOffsetAndEpoch.valid(new OffsetAndEpoch(offset, epoch));
            }
        }
    }
Validate the given offset and epoch against the log and oldest snapshot.

Returns the largest valid offset and epoch given `offset` and `epoch` as the upper bound.
This can result in three possible values returned:

1. ValidOffsetAndEpoch.valid if the given offset and epoch is valid in the log.

2. ValidOffsetAndEpoch.diverging if the given offset and epoch is not valid; and the
largest valid offset and epoch is in the log.

3. ValidOffsetAndEpoch.snapshot if the given offset and epoch is not valid; and the largest
valid offset and epoch is less than the oldest snapshot.

@param offset the offset to validate
@param epoch the epoch of the record at offset - 1
@return the largest valid offset and epoch
raft/src/main/java/org/apache/kafka/raft/ReplicatedLog.java