Search in sources :

Example 6 with StorageException

use of io.atomix.storage.StorageException in project atomix by atomix.

the class FileChannelJournalSegmentWriter method truncate.

@Override
@SuppressWarnings("unchecked")
public void truncate(long index) {
    // If the index is greater than or equal to the last index, skip the truncate.
    if (index >= getLastIndex()) {
        return;
    }
    // Reset the last entry.
    lastEntry = null;
    try {
        // Truncate the index.
        this.index.truncate(index);
        if (index < segment.index()) {
            channel.position(JournalSegmentDescriptor.BYTES);
            channel.write(zero());
            channel.position(JournalSegmentDescriptor.BYTES);
        } else {
            // Reset the writer to the given index.
            reset(index);
            // Zero entries after the given index.
            long position = channel.position();
            channel.write(zero());
            channel.position(position);
        }
    } catch (IOException e) {
        throw new StorageException(e);
    }
}
Also used : IOException(java.io.IOException) StorageException(io.atomix.storage.StorageException)

Example 7 with StorageException

use of io.atomix.storage.StorageException in project atomix by atomix.

the class SegmentedJournal method loadSegment.

/**
 * Loads a segment.
 */
private JournalSegment<E> loadSegment(long segmentId) {
    File segmentFile = JournalSegmentFile.createSegmentFile(name, directory, segmentId);
    ByteBuffer buffer = ByteBuffer.allocate(JournalSegmentDescriptor.BYTES);
    try (FileChannel channel = openChannel(segmentFile)) {
        channel.read(buffer);
        buffer.flip();
        JournalSegmentDescriptor descriptor = new JournalSegmentDescriptor(buffer);
        JournalSegment<E> segment = newSegment(new JournalSegmentFile(segmentFile), descriptor);
        log.debug("Loaded disk segment: {} ({})", descriptor.id(), segmentFile.getName());
        return segment;
    } catch (IOException e) {
        throw new StorageException(e);
    }
}
Also used : FileChannel(java.nio.channels.FileChannel) IOException(java.io.IOException) RandomAccessFile(java.io.RandomAccessFile) File(java.io.File) ByteBuffer(java.nio.ByteBuffer) StorageException(io.atomix.storage.StorageException)

Example 8 with StorageException

use of io.atomix.storage.StorageException in project atomix by atomix.

the class SegmentedJournal method loadSegments.

/**
 * Loads all segments from disk.
 *
 * @return A collection of segments for the log.
 */
protected Collection<JournalSegment<E>> loadSegments() {
    // Ensure log directories are created.
    directory.mkdirs();
    TreeMap<Long, JournalSegment<E>> segments = new TreeMap<>();
    // Iterate through all files in the log directory.
    for (File file : directory.listFiles(File::isFile)) {
        // If the file looks like a segment file, attempt to load the segment.
        if (JournalSegmentFile.isSegmentFile(name, file)) {
            JournalSegmentFile segmentFile = new JournalSegmentFile(file);
            ByteBuffer buffer = ByteBuffer.allocate(JournalSegmentDescriptor.BYTES);
            try (FileChannel channel = openChannel(file)) {
                channel.read(buffer);
                buffer.flip();
            } catch (IOException e) {
                throw new StorageException(e);
            }
            JournalSegmentDescriptor descriptor = new JournalSegmentDescriptor(buffer);
            // Load the segment.
            JournalSegment<E> segment = loadSegment(descriptor.id());
            // Add the segment to the segments list.
            log.debug("Found segment: {} ({})", segment.descriptor().id(), segmentFile.file().getName());
            segments.put(segment.index(), segment);
        }
    }
    // Verify that all the segments in the log align with one another.
    JournalSegment<E> previousSegment = null;
    boolean corrupted = false;
    Iterator<Map.Entry<Long, JournalSegment<E>>> iterator = segments.entrySet().iterator();
    while (iterator.hasNext()) {
        JournalSegment<E> segment = iterator.next().getValue();
        if (previousSegment != null && previousSegment.lastIndex() != segment.index() - 1) {
            log.warn("Journal is inconsistent. {} is not aligned with prior segment {}", segment.file().file(), previousSegment.file().file());
            corrupted = true;
        }
        if (corrupted) {
            segment.close();
            segment.delete();
            iterator.remove();
        }
        previousSegment = segment;
    }
    return segments.values();
}
Also used : FileChannel(java.nio.channels.FileChannel) IOException(java.io.IOException) TreeMap(java.util.TreeMap) ByteBuffer(java.nio.ByteBuffer) RandomAccessFile(java.io.RandomAccessFile) File(java.io.File) StorageException(io.atomix.storage.StorageException)

Example 9 with StorageException

use of io.atomix.storage.StorageException in project atomix by atomix.

the class FileChannelJournalSegmentReader method readNext.

/**
 * Reads the next entry in the segment.
 */
@SuppressWarnings("unchecked")
private void readNext() {
    // Compute the index of the next entry in the segment.
    final long index = getNextIndex();
    try {
        // Read more bytes from the segment if necessary.
        if (memory.remaining() < maxEntrySize) {
            long position = channel.position() + memory.position();
            channel.position(position);
            memory.clear();
            channel.read(memory);
            channel.position(position);
            memory.flip();
        }
        // Mark the buffer so it can be reset if necessary.
        memory.mark();
        try {
            // Read the length of the entry.
            final int length = memory.getInt();
            // If the buffer length is zero then return.
            if (length <= 0 || length > maxEntrySize) {
                memory.reset().limit(memory.position());
                nextEntry = null;
                return;
            }
            // Read the checksum of the entry.
            long checksum = memory.getInt() & 0xFFFFFFFFL;
            // Compute the checksum for the entry bytes.
            final Checksum crc32 = new CRC32();
            crc32.update(memory.array(), memory.position(), length);
            // If the stored checksum equals the computed checksum, return the entry.
            if (checksum == crc32.getValue()) {
                int limit = memory.limit();
                memory.limit(memory.position() + length);
                E entry = namespace.deserialize(memory);
                memory.limit(limit);
                nextEntry = new Indexed<>(index, entry, length);
            } else {
                memory.reset().limit(memory.position());
                nextEntry = null;
            }
        } catch (BufferUnderflowException e) {
            memory.reset().limit(memory.position());
            nextEntry = null;
        }
    } catch (IOException e) {
        throw new StorageException(e);
    }
}
Also used : CRC32(java.util.zip.CRC32) Checksum(java.util.zip.Checksum) IOException(java.io.IOException) StorageException(io.atomix.storage.StorageException) BufferUnderflowException(java.nio.BufferUnderflowException)

Example 10 with StorageException

use of io.atomix.storage.StorageException in project atomix by atomix.

the class FileChannelJournalSegmentReader method reset.

@Override
public void reset() {
    try {
        channel.position(JournalSegmentDescriptor.BYTES);
    } catch (IOException e) {
        throw new StorageException(e);
    }
    memory.clear().limit(0);
    currentEntry = null;
    nextEntry = null;
    readNext();
}
Also used : IOException(java.io.IOException) StorageException(io.atomix.storage.StorageException)

Aggregations

StorageException (io.atomix.storage.StorageException)11 IOException (java.io.IOException)10 File (java.io.File)3 RandomAccessFile (java.io.RandomAccessFile)3 ByteBuffer (java.nio.ByteBuffer)3 FileChannel (java.nio.channels.FileChannel)3 CRC32 (java.util.zip.CRC32)3 Checksum (java.util.zip.Checksum)3 BufferUnderflowException (java.nio.BufferUnderflowException)2 KryoException (com.esotericsoftware.kryo.KryoException)1 BackupOperation (io.atomix.protocols.log.protocol.BackupOperation)1 LogEntry (io.atomix.protocols.log.protocol.LogEntry)1 Position (io.atomix.storage.journal.index.Position)1 BufferOverflowException (java.nio.BufferOverflowException)1 MappedByteBuffer (java.nio.MappedByteBuffer)1 TreeMap (java.util.TreeMap)1