--- /dev/null
+/*\r
+\r
+ Derby - Class org.apache.derby.impl.store.raw.data.ContainerBasicOperation\r
+\r
+ Licensed to the Apache Software Foundation (ASF) under one or more\r
+ contributor license agreements. See the NOTICE file distributed with\r
+ this work for additional information regarding copyright ownership.\r
+ The ASF licenses this file to you under the Apache License, Version 2.0\r
+ (the "License"); you may not use this file except in compliance with\r
+ the License. You may obtain a copy of the License at\r
+\r
+ http://www.apache.org/licenses/LICENSE-2.0\r
+\r
+ Unless required by applicable law or agreed to in writing, software\r
+ distributed under the License is distributed on an "AS IS" BASIS,\r
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\r
+ See the License for the specific language governing permissions and\r
+ limitations under the License.\r
+\r
+ */\r
+\r
+package org.apache.derby.impl.store.raw.data;\r
+\r
+import org.apache.derby.iapi.reference.SQLState;\r
+\r
+import org.apache.derby.iapi.store.raw.ContainerKey;\r
+\r
+import org.apache.derby.iapi.store.raw.ContainerHandle;\r
+import org.apache.derby.iapi.store.raw.Loggable;\r
+import org.apache.derby.iapi.store.raw.LockingPolicy;\r
+import org.apache.derby.iapi.store.raw.Transaction;\r
+\r
+import org.apache.derby.iapi.store.raw.xact.RawTransaction;\r
+import org.apache.derby.iapi.store.raw.data.RawContainerHandle;\r
+\r
+import org.apache.derby.iapi.error.StandardException;\r
+import org.apache.derby.iapi.services.sanity.SanityManager;\r
+\r
+import org.apache.derby.iapi.services.io.CompressedNumber;\r
+import org.apache.derby.iapi.util.ByteArray;\r
+\r
+import java.io.OutputStream;\r
+import java.io.ObjectInput;\r
+import java.io.ObjectOutput;\r
+import java.io.IOException;\r
+\r
+/** \r
+A Container Operation change the state of the container.\r
+A ContainerBasicOperation is the base class for all container operations.\r
+*/\r
+\r
+public abstract class ContainerBasicOperation implements Loggable\r
+{\r
+ /* page info this operation changed */\r
+ private long containerVersion;\r
+ protected ContainerKey containerId;\r
+\r
+ transient protected RawContainerHandle containerHdl = null;\r
+ transient private boolean foundHere = false;\r
+\r
+ protected ContainerBasicOperation(RawContainerHandle hdl) throws StandardException\r
+ {\r
+ containerHdl = hdl;\r
+ containerId = hdl.getId();\r
+ containerVersion = hdl.getContainerVersion();\r
+ }\r
+\r
+ /*\r
+ * Formatable methods\r
+ */\r
+\r
+ // no-arg constructor, required by Formatable\r
+ public ContainerBasicOperation() { super(); }\r
+\r
+ public void writeExternal(ObjectOutput out) throws IOException\r
+ {\r
+ containerId.writeExternal(out);\r
+ CompressedNumber.writeLong(out, containerVersion);\r
+ }\r
+\r
+ public void readExternal(ObjectInput in) \r
+ throws IOException, ClassNotFoundException \r
+ {\r
+ containerId = ContainerKey.read(in);\r
+ containerVersion = CompressedNumber.readLong(in);\r
+ }\r
+\r
+\r
+ /**\r
+ Loggable methods\r
+ */\r
+\r
+ /**\r
+ the default for prepared log is always null for all the operations\r
+ that don't have optionalData. If an operation has optional data,\r
+ the operation need to prepare the optional data for this method.\r
+\r
+ Space Operation has no optional data to write out\r
+ */\r
+ public ByteArray getPreparedLog()\r
+ {\r
+ return (ByteArray) null;\r
+ }\r
+\r
+ public void releaseResource(Transaction tran)\r
+ {\r
+ if (!foundHere)\r
+ return;\r
+\r
+ if (containerHdl != null)\r
+ {\r
+ containerHdl.close();\r
+ containerHdl = null;\r
+ }\r
+\r
+ foundHere = false;\r
+ }\r
+\r
+ /**\r
+ A space operation is a RAWSTORE log record\r
+ */\r
+ public int group()\r
+ {\r
+ return Loggable.RAWSTORE;\r
+ }\r
+\r
+ /**\r
+ Methods specific to this class\r
+ */\r
+\r
+ /**\r
+ Open the container with this segmentId and containerId.\r
+ This method should only be called if the container has already been\r
+ created.\r
+\r
+ @exception StandardException the container cannot be found or cannot be\r
+ opened.\r
+ */\r
+ protected RawContainerHandle findContainer(Transaction tran)\r
+ throws StandardException\r
+ {\r
+ releaseResource(tran);\r
+\r
+ RawTransaction rtran = (RawTransaction)tran;\r
+ containerHdl = rtran.openDroppedContainer(\r
+ containerId, (LockingPolicy) null);\r
+\r
+ //If we are in roll forward recovery, missing container will be\r
+ //recreated becuase we might have hit a log record which has a \r
+ //reused the container id that was dropped earlier.\r
+ if (rtran.inRollForwardRecovery())\r
+ {\r
+ if (containerHdl == null)\r
+ {\r
+ if (SanityManager.DEBUG) \r
+ {\r
+ if(SanityManager.DEBUG_ON("LoadTran"))\r
+ {\r
+ SanityManager.DEBUG_PRINT(\r
+ "Trace", \r
+ "cannot find container " + containerId + \r
+ ", now attempt last ditch effort");\r
+ }\r
+ }\r
+ \r
+\r
+ containerHdl = findContainerForRedoRecovery(rtran);\r
+\r
+ if (SanityManager.DEBUG) \r
+ {\r
+ if(SanityManager.DEBUG_ON("LoadTran"))\r
+ {\r
+ SanityManager.DEBUG_PRINT("Trace",\r
+ " findContainerForRedoRecovery, got container=" + \r
+ (containerHdl != null));\r
+ }\r
+ }\r
+\r
+ }\r
+ } \r
+ \r
+ if (containerHdl == null)\r
+ {\r
+ throw StandardException.newException(\r
+ SQLState.DATA_CONTAINER_VANISHED, containerId);\r
+ }\r
+\r
+ foundHere = true;\r
+ return containerHdl;\r
+ }\r
+\r
+ /**\r
+ Subclass (e.g., ContainerOperation) that wishes to do something abou\r
+ missing container in load tran should override this method to return\r
+ the recreated container\r
+\r
+ @exception StandardException Standard Derby error policy\r
+ */\r
+ protected RawContainerHandle findContainerForRedoRecovery(\r
+ RawTransaction tran) \r
+ throws StandardException \r
+ {\r
+ return null;\r
+ }\r
+ \r
+\r
+ /**\r
+ @exception StandardException Standard Derby error policy\r
+ */\r
+ public boolean needsRedo(Transaction xact)\r
+ throws StandardException\r
+ {\r
+ findContainer(xact);\r
+\r
+ long cVersion = containerHdl.getContainerVersion();\r
+\r
+ if (cVersion == containerVersion)\r
+ return true;\r
+\r
+ releaseResource(xact);\r
+\r
+ if (cVersion > containerVersion)\r
+ return false;\r
+ else\r
+ {\r
+ // RESOLVE - correct error handling\r
+ if (SanityManager.DEBUG)\r
+ {\r
+ SanityManager.THROWASSERT("log corrupted, missing log record: "+\r
+ "log container version = " +\r
+ containerVersion + \r
+ " container header version " + cVersion);\r
+ }\r
+ return false;\r
+ }\r
+ }\r
+\r
+\r
+ public String toString()\r
+ {\r
+ if (SanityManager.DEBUG)\r
+ {\r
+ return "Space Operation: " + containerId ;\r
+ }\r
+ else\r
+ return null;\r
+ }\r
+\r
+}\r
+\r
+\r