Search in sources :

Example 6 with BytesAndBits

use of org.apache.geode.internal.cache.persistence.BytesAndBits in project geode by apache.

the class Oplog method basicGet.

/**
   * Extracts the Value byte array & UserBit from the OpLog
   * 
   * @param offsetInOplog The starting position from which to read the data in the opLog
   * @param bitOnly boolean indicating whether the value needs to be extracted along with the
   *        UserBit or not.
   * @param valueLength The length of the byte array which represents the value
   * @param userBits The userBits of the value.
   * @return BytesAndBits object which wraps the extracted value & user bit
   */
private BytesAndBits basicGet(DiskRegionView dr, long offsetInOplog, boolean bitOnly, int valueLength, byte userBits) {
    BytesAndBits bb = null;
    if (EntryBits.isAnyInvalid(userBits) || EntryBits.isTombstone(userBits) || bitOnly || valueLength == 0) {
        if (EntryBits.isInvalid(userBits)) {
            bb = new BytesAndBits(DiskEntry.INVALID_BYTES, userBits);
        } else if (EntryBits.isTombstone(userBits)) {
            bb = new BytesAndBits(DiskEntry.TOMBSTONE_BYTES, userBits);
        } else {
            bb = new BytesAndBits(DiskEntry.LOCAL_INVALID_BYTES, userBits);
        }
    } else {
        if (offsetInOplog == -1)
            return null;
        try {
            for (; ; ) {
                dr.getCancelCriterion().checkCancelInProgress(null);
                boolean interrupted = Thread.interrupted();
                try {
                    bb = attemptGet(dr, offsetInOplog, bitOnly, valueLength, userBits);
                    break;
                } catch (InterruptedIOException ignore) {
                // bug 39756
                // ignore, we'll clear and retry.
                } finally {
                    if (interrupted) {
                        Thread.currentThread().interrupt();
                    }
                }
            }
        // for
        } catch (IOException ex) {
            getParent().getCancelCriterion().checkCancelInProgress(ex);
            throw new DiskAccessException(LocalizedStrings.Oplog_FAILED_READING_FROM_0_OPLOGID_1_OFFSET_BEING_READ_2_CURRENT_OPLOG_SIZE_3_ACTUAL_FILE_SIZE_4_IS_ASYNCH_MODE_5_IS_ASYNCH_WRITER_ALIVE_6.toLocalizedString(this.diskFile.getPath(), this.oplogId, offsetInOplog, this.crf.currSize, this.crf.bytesFlushed, !dr.isSync(), Boolean.FALSE), ex, dr.getName());
        } catch (IllegalStateException ex) {
            checkClosed();
            throw ex;
        }
    }
    return bb;
}
Also used : InterruptedIOException(java.io.InterruptedIOException) DiskAccessException(org.apache.geode.cache.DiskAccessException) InterruptedIOException(java.io.InterruptedIOException) IOException(java.io.IOException) BytesAndBits(org.apache.geode.internal.cache.persistence.BytesAndBits)

Example 7 with BytesAndBits

use of org.apache.geode.internal.cache.persistence.BytesAndBits in project geode by apache.

the class OverflowOplog method getBytesAndBits.

/**
   * Returns the unserialized bytes and bits for the given Entry. If Oplog is destroyed while
   * querying, then the DiskRegion is queried again to obatin the value This method should never get
   * invoked for an entry which has been destroyed
   * 
   * @since GemFire 3.2.1
   * @param id The DiskId for the entry @param offset The offset in this OpLog where the entry is
   *        present. @param faultingIn @param bitOnly boolean indicating whether to extract just the
   *        UserBit or UserBit with value @return BytesAndBits object wrapping the value & user bit
   */
public BytesAndBits getBytesAndBits(DiskRegionView dr, DiskId id, boolean faultingIn, boolean bitOnly) {
    OverflowOplog retryOplog = null;
    long offset = 0;
    synchronized (id) {
        int opId = (int) id.getOplogId();
        if (opId != getOplogId()) {
            // the oplog changed on us so we need to do a recursive
            // call after unsyncing
            retryOplog = this.getOplogSet().getChild(opId);
        } else {
            // fetch this while synced so it will be consistent with oplogId
            offset = id.getOffsetInOplog();
        }
    }
    if (retryOplog != null) {
        return retryOplog.getBytesAndBits(dr, id, faultingIn, bitOnly);
    }
    BytesAndBits bb = null;
    long start = this.stats.startRead();
    // the data is present in the current oplog file.
    if (offset == -1) {
        // Since it is given that a get operation has alreadty
        // taken a
        // lock on an entry , no put operation could have modified the
        // oplog ID
        // there fore synchronization is not needed
        // synchronized (id) {
        offset = id.getOffsetInOplog();
    }
    // is still open) we can retrieve the value from this oplog.
    try {
        bb = basicGet(dr, offset, bitOnly, id.getValueLength(), id.getUserBits());
    } catch (DiskAccessException dae) {
        logger.error(LocalizedMessage.create(LocalizedStrings.Oplog_OPLOGBASICGET_ERROR_IN_READING_THE_DATA_FROM_DISK_FOR_DISK_ID_HAVING_DATA_AS_0, id), dae);
        throw dae;
    }
    if (bb == null) {
        throw new EntryDestroyedException(LocalizedStrings.Oplog_NO_VALUE_WAS_FOUND_FOR_ENTRY_WITH_DISK_ID_0_ON_A_REGION_WITH_SYNCHRONOUS_WRITING_SET_TO_1.toLocalizedString(new Object[] { id, dr.isSync() }));
    }
    if (bitOnly) {
        dr.endRead(start, this.stats.endRead(start, 1), 1);
    } else {
        dr.endRead(start, this.stats.endRead(start, bb.getBytes().length), bb.getBytes().length);
    }
    return bb;
}
Also used : EntryDestroyedException(org.apache.geode.cache.EntryDestroyedException) DiskAccessException(org.apache.geode.cache.DiskAccessException) BytesAndBits(org.apache.geode.internal.cache.persistence.BytesAndBits)

Example 8 with BytesAndBits

use of org.apache.geode.internal.cache.persistence.BytesAndBits in project geode by apache.

the class Oplog method getBytesAndBits.

/**
   * Returns the unserialized bytes and bits for the given Entry. If Oplog is destroyed while
   * querying, then the DiskRegion is queried again to obatin the value This method should never get
   * invoked for an entry which has been destroyed
   * 
   * @since GemFire 3.2.1
   * @param id The DiskId for the entry @param offset The offset in this OpLog where the entry is
   *        present. @param faultingIn @param bitOnly boolean indicating whether to extract just the
   *        UserBit or UserBit with value @return BytesAndBits object wrapping the value & user bit
   */
public BytesAndBits getBytesAndBits(DiskRegionView dr, DiskId id, boolean faultingIn, boolean bitOnly) {
    Oplog retryOplog = null;
    long offset = 0;
    synchronized (id) {
        long opId = id.getOplogId();
        if (opId != getOplogId()) {
            // the oplog changed on us so we need to do a recursive
            // call after unsyncing
            retryOplog = getOplogSet().getChild(opId);
        } else {
            // fetch this while synced so it will be consistent with oplogId
            offset = id.getOffsetInOplog();
        }
    }
    if (retryOplog != null) {
        return retryOplog.getBytesAndBits(dr, id, faultingIn, bitOnly);
    }
    BytesAndBits bb = null;
    long start = this.stats.startRead();
    // the data is present in the current oplog file.
    if (offset == -1) {
        // Since it is given that a get operation has alreadty
        // taken a
        // lock on an entry , no put operation could have modified the
        // oplog ID
        // there fore synchronization is not needed
        offset = id.getOffsetInOplog();
    }
    // is still open) we can retrieve the value from this oplog.
    try {
        bb = basicGet(dr, offset, bitOnly, id.getValueLength(), id.getUserBits());
    } catch (DiskAccessException dae) {
        logger.error(LocalizedMessage.create(LocalizedStrings.Oplog_OPLOGBASICGET_ERROR_IN_READING_THE_DATA_FROM_DISK_FOR_DISK_ID_HAVING_DATA_AS_0, id), dae);
        throw dae;
    }
    if (bb == null) {
        throw new EntryDestroyedException(LocalizedStrings.Oplog_NO_VALUE_WAS_FOUND_FOR_ENTRY_WITH_DISK_ID_0_ON_A_REGION_WITH_SYNCHRONOUS_WRITING_SET_TO_1.toLocalizedString(new Object[] { id, dr.isSync() }));
    }
    if (bitOnly) {
        dr.endRead(start, this.stats.endRead(start, 1), 1);
    } else {
        dr.endRead(start, this.stats.endRead(start, bb.getBytes().length), bb.getBytes().length);
    }
    return bb;
}
Also used : EntryDestroyedException(org.apache.geode.cache.EntryDestroyedException) DiskAccessException(org.apache.geode.cache.DiskAccessException) StoredObject(org.apache.geode.internal.offheap.StoredObject) BytesAndBits(org.apache.geode.internal.cache.persistence.BytesAndBits)

Example 9 with BytesAndBits

use of org.apache.geode.internal.cache.persistence.BytesAndBits in project geode by apache.

the class Oplog method attemptGet.

private BytesAndBits attemptGet(DiskRegionView dr, long offsetInOplog, boolean bitOnly, int valueLength, byte userBits) throws IOException {
    boolean didReopen = false;
    boolean accessedInactive = false;
    try {
        synchronized (this.lock) /* crf */
        {
            // if (this.closed || this.deleted.get()) {
            // throw new DiskAccessException("attempting get on "
            // + (this.deleted.get() ? "destroyed" : "closed")
            // + " oplog #" + getOplogId(), this.owner);
            // }
            this.beingRead = true;
            if (/*
             * !getParent().isSync() since compactor groups writes &&
             */
            (offsetInOplog + valueLength) > this.crf.bytesFlushed && !this.closed) {
                // fix for bug 41205
                flushAllNoSync(true);
            }
            try {
                UninterruptibleRandomAccessFile myRAF = null;
                if (this.crf.RAFClosed) {
                    myRAF = new UninterruptibleRandomAccessFile(this.crf.f, "r");
                    this.stats.incOpenOplogs();
                    if (this.okToReopen) {
                        this.crf.RAFClosed = false;
                        this.okToReopen = false;
                        this.crf.raf = myRAF;
                        didReopen = true;
                    }
                } else {
                    myRAF = this.crf.raf;
                    accessedInactive = true;
                }
                BytesAndBits bb = null;
                try {
                    final long writePosition = (this.doneAppending) ? this.crf.bytesFlushed : myRAF.getFilePointer();
                    if ((offsetInOplog + valueLength) > writePosition) {
                        throw new DiskAccessException(LocalizedStrings.Oplog_TRIED_TO_SEEK_TO_0_BUT_THE_FILE_LENGTH_IS_1_OPLOG_FILE_OBJECT_USED_FOR_READING_2.toLocalizedString(offsetInOplog + valueLength, writePosition, this.crf.raf), dr.getName());
                    } else if (offsetInOplog < 0) {
                        throw new DiskAccessException(LocalizedStrings.Oplog_CANNOT_FIND_RECORD_0_WHEN_READING_FROM_1.toLocalizedString(offsetInOplog, this.diskFile.getPath()), dr.getName());
                    }
                    try {
                        myRAF.seek(offsetInOplog);
                        this.stats.incOplogSeeks();
                        byte[] valueBytes = new byte[valueLength];
                        myRAF.readFully(valueBytes);
                        this.stats.incOplogReads();
                        bb = new BytesAndBits(valueBytes, userBits);
                        // also set the product version for an older product
                        final Version version = getProductVersionIfOld();
                        if (version != null) {
                            bb.setVersion(version);
                        }
                    } finally {
                        // disk io
                        if (!this.doneAppending) {
                            // by seeking back to writePosition
                            myRAF.seek(writePosition);
                            this.stats.incOplogSeeks();
                        }
                    }
                    return bb;
                } finally {
                    if (myRAF != this.crf.raf) {
                        try {
                            myRAF.close();
                        } catch (IOException ignore) {
                        }
                    }
                }
            } finally {
                this.beingRead = false;
            // if (this.closed || this.deleted.get()) {
            // throw new DiskAccessException("attempting get on "
            // + (this.deleted.get() ? "destroyed" : "closed")
            // + " oplog #" + getOplogId(), this.owner);
            // }
            }
        }
    // sync
    } finally {
        if (accessedInactive) {
            getOplogSet().inactiveAccessed(this);
        } else if (didReopen) {
            getOplogSet().inactiveReopened(this);
        }
    }
}
Also used : UninterruptibleRandomAccessFile(org.apache.geode.internal.cache.persistence.UninterruptibleRandomAccessFile) Version(org.apache.geode.internal.Version) DiskAccessException(org.apache.geode.cache.DiskAccessException) InterruptedIOException(java.io.InterruptedIOException) IOException(java.io.IOException) BytesAndBits(org.apache.geode.internal.cache.persistence.BytesAndBits)

Aggregations

BytesAndBits (org.apache.geode.internal.cache.persistence.BytesAndBits)9 DiskAccessException (org.apache.geode.cache.DiskAccessException)5 IOException (java.io.IOException)3 InterruptedIOException (java.io.InterruptedIOException)3 EntryDestroyedException (org.apache.geode.cache.EntryDestroyedException)2 RandomAccessFile (java.io.RandomAccessFile)1 ByteBuffer (java.nio.ByteBuffer)1 RegionDestroyedException (org.apache.geode.cache.RegionDestroyedException)1 Version (org.apache.geode.internal.Version)1 UninterruptibleRandomAccessFile (org.apache.geode.internal.cache.persistence.UninterruptibleRandomAccessFile)1 StoredObject (org.apache.geode.internal.offheap.StoredObject)1