⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 b2irowlocking3.java

📁 derby database source code.good for you.
💻 JAVA
📖 第 1 页 / 共 3 页
字号:
/*   Derby - Class org.apache.derby.impl.store.access.btree.index.B2IRowLocking3   Copyright 1998, 2004 The Apache Software Foundation or its licensors, as applicable.   Licensed under the Apache License, Version 2.0 (the "License");   you may not use this file except in compliance with the License.   You may obtain a copy of the License at      http://www.apache.org/licenses/LICENSE-2.0   Unless required by applicable law or agreed to in writing, software   distributed under the License is distributed on an "AS IS" BASIS,   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.   See the License for the specific language governing permissions and   limitations under the License. */package org.apache.derby.impl.store.access.btree.index;import org.apache.derby.iapi.services.sanity.SanityManager;import org.apache.derby.iapi.error.StandardException; import org.apache.derby.iapi.store.access.conglomerate.TransactionManager;import org.apache.derby.iapi.store.access.ConglomerateController;import org.apache.derby.iapi.store.access.RowUtil;import org.apache.derby.iapi.store.access.TransactionController;import org.apache.derby.iapi.store.raw.FetchDescriptor;import org.apache.derby.iapi.store.raw.LockingPolicy;import org.apache.derby.iapi.store.raw.Page;import org.apache.derby.iapi.store.raw.RecordHandle;import org.apache.derby.iapi.store.raw.Transaction;import org.apache.derby.iapi.types.DataValueDescriptor;import org.apache.derby.iapi.types.RowLocation;import org.apache.derby.impl.store.access.btree.BTree;import org.apache.derby.impl.store.access.btree.BTreeLockingPolicy;import org.apache.derby.impl.store.access.btree.ControlRow;import org.apache.derby.impl.store.access.btree.LeafControlRow;import org.apache.derby.impl.store.access.btree.OpenBTree;import org.apache.derby.impl.store.access.btree.BTreeRowPosition;import org.apache.derby.impl.store.access.btree.WaitError;/**Implements the jdbc serializable isolation level using row locks.<p>Holds read and write locks until end of transaction.Obtains previous key locks to protect from phantom reads.**/class B2IRowLocking3 implements BTreeLockingPolicy{    /**************************************************************************     * Private/Protected fields of This class:     **************************************************************************     */    /**     * The container id of the base container for this index.  Used to build     * record handles to make lock calls on.     **/    protected ConglomerateController        base_cc;    /**     * The OpenBtree to use if we have to lock anything in the btree vs.     * base row locking.     **/    protected OpenBTree                     open_btree;    /**     * The locking policy to use to get and release the scan locks.  We could     * cache this somewhere better.     **/    private LockingPolicy                   scan_locking_policy;    /**     * The transaction to associate lock requests with.     **/    private Transaction                     rawtran;    /**************************************************************************     * Constructors for This class:     **************************************************************************     */    B2IRowLocking3(    Transaction             rawtran,    int                     lock_level,    LockingPolicy           locking_policy,    ConglomerateController  base_cc,    OpenBTree               open_btree)    {        this.rawtran             = rawtran;        this.base_cc             = base_cc;        this.open_btree          = open_btree;        this.scan_locking_policy =             rawtran.newLockingPolicy(                LockingPolicy.MODE_RECORD,                 TransactionController.ISOLATION_READ_COMMITTED, true);    }    /**************************************************************************     * Private methods of This class:     **************************************************************************     */    private boolean _lockScan(    RecordHandle    rh,    boolean         forUpdate,    boolean         wait)		throws StandardException    {        boolean ret_val = true;        // only get the scan lock if we are record locking.                if (!forUpdate)        {            ret_val =                 scan_locking_policy.lockRecordForRead(                    rawtran, open_btree.getContainerHandle(),                     rh, wait, false);        }        else        {            ret_val =                 scan_locking_policy.lockRecordForWrite(                    rawtran, rh, false, wait);        }        return(ret_val);    }    /**     * Lock key previous to first key in btree.     * <p>     * In the previous key locking protocol repeatable read and phantom      * protection is guaranteed by locking a range of keys in the btree.     * The range is defined by the key previous to the first key you look     * at and all subsequent keys you look at.  The first key in the index     * is a special case, as there are no keys previous to it.  In that     * case a special key is declared the "previous key" to the first key     * in the btree and is locked instead.     * <p>     * In this implementation that first key is defined to be in the base     * container, page ContainerHandle.FIRST_PAGE_NUMBER, record id      * PREVIOUS_KEY_HANDLE.     * <p>     * Note that the previous key is the same for all indexes on a given     * conglomerate.  It seemed better for all locks on a base table to have     * the same containerid, rather than having some locks generated from      * a btree have a containerid from base table and some having a containerid     * from the btree.  If this turns out to be a problem we could either     * have 2 different containerid's, be more creative with the record id, or     * even add more to the lock key.     *     * @param aux_leaf          If non-null, this leaf is unlatched if the      *                          routine has to wait on the lock.     * @param lock_operation    Whether to lock exclusive or share.     * @param lock_duration     For what duration should the lock be held,     *                          if INSTANT_DURATION, then the routine will     *                          guarantee that lock was acquired while holding     *                          the latch, but then immediately release the     *                          lock.  If COMMIT_DURATION or MANUAL_DURATION     *                          then the lock be held when routine returns     *                          successfully.     *	 * @exception  StandardException  Standard exception policy.     **/    private boolean lockPreviousToFirstKey(    LeafControlRow          current_leaf,    LeafControlRow          aux_leaf,    int                     lock_operation,    int                     lock_duration)		throws StandardException    {        // This is first row in table, lock the special key that         // represents the key previous to the first key of the table.        // First try to get the lock NOWAIT, while latch is held.        boolean ret_status =             base_cc.lockRow(                BTree.ROOTPAGEID,                 RecordHandle.PREVIOUS_KEY_HANDLE,                 lock_operation,                false /* NOWAIT */,                 lock_duration);        if (!ret_status)        {            current_leaf.release();            current_leaf = null;            if (aux_leaf != null)            {                aux_leaf.release();                aux_leaf = null;            }            // Couldn't get the lock NOWAIT, release latch and wait for lock.            base_cc.lockRow(                BTree.ROOTPAGEID,                 RecordHandle.PREVIOUS_KEY_HANDLE,                 lock_operation,                true /* WAIT */,                 lock_duration);        }        return(ret_status);    }    /**     * Lock a btree row (row is at given slot in page).     * <p>     * Lock the row at the given slot in the page.  Meant to be used if caller      * only has the slot on the page to be locked, and has not read the row     * yet.  This routine fetches the row location field from the page, and then     * locks that rowlocation in the base container.     * <p>     * Lock a btree row, enforcing the standard lock/latch protocol.       * On return the row is locked.  Return status indicates if the lock     * was waited for, which will mean a latch was dropped while waiting.     * In general a false status means that the caller will either have      * to research the tree unless some protocol has been implemented that     * insures that the row will not have moved while the latch was dropped.     * <p>     * This routine request a row lock NOWAIT on the in-memory row      * "current_row.".  If the lock is granted the routine will return true.     * If the lock cannot be granted NOWAIT, then the routine will release     * the latch on "current_leaf" and "aux_leaf" (if aux_leaf is non-null),     * and then it will request a WAIT lock on the row.       * <p>     *     * @param btree             The conglomerate we are locking.     * @param current_leaf      Latched current leaf where "current" key is.     * @param aux_leaf          If non-null, this leaf is unlatched if the      *                          routine has to wait on the lock.     * @param current_slot      Slot of row to lock.     * @param lock_fetch_desc   Descriptor for fetching just the RowLocation,     *                          used for locking.     * @param check_changed_rowloc     *                          whether to check for the changed rowloc or not.     * @param lock_operation    Whether lock is for key prev to insert or not.     * @param lock_duration     For what duration should the lock be held,     *                          if INSTANT_DURATION, then the routine will     *                          guarantee that lock was acquired while holding     *                          the latch, but then immediately release the     *                          lock.  If COMMIT_DURATION or MANUAL_DURATION     *                          then the lock be held when routine returns     *                          successfully.     *	 * @exception  StandardException  Standard exception policy.     **/    private boolean lockRowOnPage(    BTree                   btree,    LeafControlRow          current_leaf,    LeafControlRow          aux_leaf,    int                     current_slot,    boolean                 check_changed_rowloc,    FetchDescriptor         lock_fetch_desc,    DataValueDescriptor[]   lock_template,    RowLocation             lock_row_loc,    int                     lock_operation,    int                     lock_duration)		throws StandardException    {        if (SanityManager.DEBUG)        {            SanityManager.ASSERT(current_leaf != null);            if (current_slot <= 0 ||                 current_slot >= current_leaf.getPage().recordCount())            {                SanityManager.THROWASSERT(                    "current_slot = " + current_slot +                    "; current_leaf.getPage().recordCount() = " +                        current_leaf.getPage().recordCount());            }            if (!(btree instanceof B2I))            {                SanityManager.THROWASSERT(                    "btree not instance of B2I, it is " +                    btree.getClass().getName());            }            SanityManager.ASSERT(lock_template != null, "template is null");            // For now the RowLocation is expected to be the object located in            // the last column of the lock_template, this may change if we            // ever support rows with RowLocations somewhere else.            SanityManager.ASSERT(                lock_row_loc == lock_template[lock_template.length - 1],                 "row_loc is not the object in last column of lock_template.");        }        // Fetch the row location to lock.        RecordHandle rec_handle =             current_leaf.getPage().fetchFromSlot(                (RecordHandle) null, current_slot,                 lock_template, lock_fetch_desc, true);        // First try to get the lock NOWAIT, while latch is held.        boolean ret_status =            base_cc.lockRow(                lock_row_loc,                 lock_operation,                false /* NOWAIT */, lock_duration);        if (!ret_status)        {            // Could not get the lock NOWAIT, release latch and wait for lock.            if (current_leaf != null)            {                current_leaf.release();                current_leaf = null;            }            if (aux_leaf != null)            {                aux_leaf.release();                aux_leaf = null;            }            base_cc.lockRow(                lock_row_loc,                 lock_operation,                true /* WAIT */, lock_duration);        }        return(ret_status);    }    private boolean searchLeftAndLockPreviousKey(    B2I                     b2i,    LeafControlRow          current_leaf,    int                     current_slot,    FetchDescriptor         lock_fetch_desc,    DataValueDescriptor[]   lock_template,    RowLocation             lock_row_loc,    OpenBTree               open_btree,    int                     lock_operation,    int                     lock_duration)

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -