use of org.apache.derby.iapi.store.raw.data.RawContainerHandle in project derby by apache.
the class BaseDataFileFactory method dropContainer.
/**
* Drop a container.
*
* <P><B>Synchronisation</B>
* <P>
* This call will mark the container as dropped and then obtain an CX lock
* (table level exclusive lock) on the container. Once a container has
* been marked as dropped it cannot be retrieved by an openContainer()
* call unless explicitly with droppedOK.
* <P>
* Once the exclusive lock has been obtained the container is removed
* and all its pages deallocated. The container will be fully removed
* at the commit time of the transaction.
*
* @exception StandardException Standard Derby error policy
*/
public void dropContainer(RawTransaction t, ContainerKey ckey) throws StandardException {
boolean tmpContainer = (ckey.getSegmentId() == ContainerHandle.TEMPORARY_SEGMENT);
LockingPolicy cl = null;
if (!tmpContainer) {
if (isReadOnly()) {
throw StandardException.newException(SQLState.DATA_CONTAINER_READ_ONLY);
}
cl = t.newLockingPolicy(LockingPolicy.MODE_CONTAINER, TransactionController.ISOLATION_SERIALIZABLE, true);
if (SanityManager.DEBUG)
SanityManager.ASSERT(cl != null);
}
// close all open containers and 'onCommit' objects of this container
t.notifyObservers(ckey);
RawContainerHandle containerHdl = (RawContainerHandle) t.openContainer(ckey, cl, ContainerHandle.MODE_FORUPDATE);
// happening thru some means other than the lock we are getting here.
try {
if (containerHdl == null || containerHdl.getContainerStatus() != RawContainerHandle.NORMAL) {
// If we are a temp container, don't worry about it.
if (tmpContainer) {
if (containerHdl != null)
containerHdl.removeContainer((LogInstant) null);
return;
} else {
throw StandardException.newException(SQLState.DATA_CONTAINER_VANISHED, ckey);
}
}
// Container exist, is updatable and we got the lock.
if (tmpContainer) {
containerHdl.dropContainer((LogInstant) null, true);
containerHdl.removeContainer((LogInstant) null);
} else {
ContainerOperation lop = new ContainerOperation(containerHdl, ContainerOperation.DROP);
// mark the container as pre-dirtied so that if a checkpoint
// happens after the log record is sent to the log stream, the
// cache cleaning will wait for this change.
containerHdl.preDirty(true);
try {
t.logAndDo(lop);
} finally {
// in case logAndDo fail, make sure the container is not
// stuck in preDirty state.
containerHdl.preDirty(false);
}
// remember this as a post commit work item
Serviceable p = new ReclaimSpace(ReclaimSpace.CONTAINER, ckey, this, true);
if (SanityManager.DEBUG) {
if (SanityManager.DEBUG_ON(DaemonService.DaemonTrace)) {
SanityManager.DEBUG(DaemonService.DaemonTrace, "Add post commit work " + p);
}
}
t.addPostCommitWork(p);
}
} finally {
if (containerHdl != null)
containerHdl.close();
}
}
use of org.apache.derby.iapi.store.raw.data.RawContainerHandle in project derby by apache.
the class T_Recovery method R301.
/*
* test recovery of 301
*/
protected void R301() throws T_Fail, StandardException {
long cid1 = find(key(301, 1));
if (cid1 < 0) {
REPORT("R301 not run");
return;
}
long cid2 = find(key(301, 2));
Transaction t = t_util.t_startTransaction();
try {
LockingPolicy nolock = t.newLockingPolicy(LockingPolicy.MODE_NONE, 0, false);
ContainerKey id1 = new ContainerKey(0, cid1);
ContainerHandle c = t.openContainer(id1, ContainerHandle.MODE_READONLY);
if (c != null)
throw T_Fail.testFailMsg("expect container to be dropped");
RawContainerHandle stub = ((RawTransaction) t).openDroppedContainer(id1, nolock);
/*Not true always after fix for p4#25641(fix for bug:4580)
Checkpoint calls cleans up the stubs that not necessary
for recovery.
if (stub == null)
throw T_Fail.testFailMsg("drop container should still be there");
*/
if (stub != null)
if (stub.getContainerStatus() != RawContainerHandle.COMMITTED_DROP)
throw T_Fail.testFailMsg("expect container to be committed dropped");
ContainerKey id2 = new ContainerKey(0, cid2);
c = t.openContainer(id2, ContainerHandle.MODE_READONLY);
if (c != null)
throw T_Fail.testFailMsg("expect container to be dropped");
stub = ((RawTransaction) t).openDroppedContainer(id2, nolock);
/*Not true always after fix for p4#25641(fix for bug:4580)
Checkpoint calls cleans up the stubs that not necessary
for recovery.
if (stub == null)
throw T_Fail.testFailMsg("drop container should still be there");
*/
if (stub != null)
if (stub.getContainerStatus() != RawContainerHandle.COMMITTED_DROP)
throw T_Fail.testFailMsg("expect container to be committed dropped");
} finally {
t_util.t_commit(t);
t.close();
}
PASS("R301 : cid1 " + cid1 + " cid2 " + cid2);
}
use of org.apache.derby.iapi.store.raw.data.RawContainerHandle in project derby by apache.
the class ReclaimSpaceHelper method reclaimContainer.
private static int reclaimContainer(BaseDataFileFactory dataFactory, RawTransaction tran, ReclaimSpace work) throws StandardException {
// when we want to reclaim the whole container, gets an exclusive
// XLock on the container, wait for the lock.
LockingPolicy container_xlock = tran.newLockingPolicy(LockingPolicy.MODE_CONTAINER, TransactionController.ISOLATION_SERIALIZABLE, true);
if (SanityManager.DEBUG)
SanityManager.ASSERT(container_xlock != null);
// Try to just get the container thru the transaction.
// Need to do this to transition the transaction to active state.
RawContainerHandle containerHdl = tran.openDroppedContainer(work.getContainerId(), container_xlock);
// deleted, done work
if (containerHdl == null || containerHdl.getContainerStatus() == RawContainerHandle.NORMAL || containerHdl.getContainerStatus() == RawContainerHandle.COMMITTED_DROP) {
if (containerHdl != null)
containerHdl.close();
// release xlock, if any
tran.abort();
if (SanityManager.DEBUG) {
if (SanityManager.DEBUG_ON(DaemonService.DaemonTrace)) {
SanityManager.DEBUG(DaemonService.DaemonTrace, " aborted " + work);
}
}
} else {
// we got an xlock on a dropped container. Must be committed.
// Get rid of the container now.
ContainerOperation lop = new ContainerOperation(containerHdl, ContainerOperation.REMOVE);
// mark the container as pre-dirtied so that if a checkpoint
// happens after the log record is sent to the log stream, the
// cache cleaning will wait for this change.
containerHdl.preDirty(true);
try {
tran.logAndDo(lop);
} finally {
// in case logAndDo fail, make sure the container is not
// stuck in preDirty state.
containerHdl.preDirty(false);
}
containerHdl.close();
tran.commit();
if (SanityManager.DEBUG) {
if (SanityManager.DEBUG_ON(DaemonService.DaemonTrace)) {
SanityManager.DEBUG(DaemonService.DaemonTrace, " committed " + work);
}
}
}
return Serviceable.DONE;
}
use of org.apache.derby.iapi.store.raw.data.RawContainerHandle in project derby by apache.
the class EncryptOrDecryptData method encryptOrDecryptContainer.
/**
* Encrypts or decrypts the specified container.
*
* @param t transaction that used to perform the cryptographic operation
* @param ckey the key of the container that is being encrypted/decrypted
* @param doEncrypt tells whether to encrypt or decrypt
* @exception StandardException Standard Derby error policy
*/
private void encryptOrDecryptContainer(RawTransaction t, ContainerKey ckey, boolean doEncrypt) throws StandardException {
LockingPolicy cl = t.newLockingPolicy(LockingPolicy.MODE_CONTAINER, TransactionController.ISOLATION_SERIALIZABLE, true);
if (SanityManager.DEBUG)
SanityManager.ASSERT(cl != null);
RawContainerHandle containerHdl = (RawContainerHandle) t.openContainer(ckey, cl, ContainerHandle.MODE_FORUPDATE);
if (SanityManager.DEBUG)
SanityManager.ASSERT(containerHdl != null);
EncryptContainerOperation lop = new EncryptContainerOperation(containerHdl);
t.logAndDo(lop);
// flush the log to reduce the window between where
// the encrypted container is created & synced and the
// log record for it makes it to disk. if we fail during
// encryption of the container, log record will make sure
// container is restored to the original state and
// any temporary files are cleaned up.
dataFactory.flush(t.getLastLogInstant());
// encrypt the container.
String newFilePath = getFilePath(ckey, false);
StorageFile newFile = storageFactory.newStorageFile(newFilePath);
containerHdl.encryptOrDecryptContainer(newFilePath, doEncrypt);
containerHdl.close();
// discard pages in the cache related to this container.
if (!dataFactory.getPageCache().discard(ckey)) {
if (SanityManager.DEBUG)
SanityManager.THROWASSERT("unable to discard pages releated to " + "container " + ckey + " from the page cache");
}
// get rid of the container entry from conatainer cache
if (!dataFactory.getContainerCache().discard(ckey)) {
if (SanityManager.DEBUG)
SanityManager.THROWASSERT("unable to discard a container " + ckey + " from the container cache");
}
StorageFile currentFile = dataFactory.getContainerPath(ckey, false);
StorageFile oldFile = getFile(ckey, true);
if (!privRename(currentFile, oldFile)) {
throw StandardException.newException(SQLState.RAWSTORE_ERROR_RENAMING_FILE, currentFile, oldFile);
}
// now replace current container file with the new file.
if (!privRename(newFile, currentFile)) {
throw StandardException.newException(SQLState.RAWSTORE_ERROR_RENAMING_FILE, newFile, currentFile);
}
}
use of org.apache.derby.iapi.store.raw.data.RawContainerHandle in project derby by apache.
the class LockCount method openDroppedContainer.
/**
* Open a container that may already have been dropped.
*
* @exception StandardException Standard Derby exception policy
* @see RawTransaction#openDroppedContainer
*/
public RawContainerHandle openDroppedContainer(ContainerKey containerId, LockingPolicy locking) throws StandardException {
setActiveState();
if (locking == null)
locking = xactFactory.getLockingPolicy(LockingPolicy.MODE_NONE, TransactionController.ISOLATION_NOLOCK, false);
RawContainerHandle hdl = null;
// first try to open it for update, if that fail, open it for read
try {
hdl = dataFactory.openDroppedContainer(this, containerId, locking, ContainerHandle.MODE_FORUPDATE);
} catch (StandardException se) {
// if this also fail, throw exception
hdl = dataFactory.openDroppedContainer(this, containerId, locking, ContainerHandle.MODE_READONLY);
}
return hdl;
}
Aggregations