Adding JMCR-Stable version
[Benchmarks_CSolver.git] / JMCR-Stable / real-world application / derby-10.3.2.1 / java / engine / org / apache / derby / impl / sql / execute / VTIResultSet.java
diff --git a/JMCR-Stable/real-world application/derby-10.3.2.1/java/engine/org/apache/derby/impl/sql/execute/VTIResultSet.java b/JMCR-Stable/real-world application/derby-10.3.2.1/java/engine/org/apache/derby/impl/sql/execute/VTIResultSet.java
new file mode 100644 (file)
index 0000000..d9c0eca
--- /dev/null
@@ -0,0 +1,612 @@
+/*\r
+\r
+   Derby - Class org.apache.derby.impl.sql.execute.VTIResultSet\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.sql.execute;\r
+\r
+import org.apache.derby.iapi.services.loader.ClassFactory;\r
+import org.apache.derby.iapi.services.loader.ClassInspector;\r
+\r
+import org.apache.derby.iapi.services.monitor.Monitor;\r
+\r
+import org.apache.derby.iapi.services.sanity.SanityManager;\r
+\r
+import org.apache.derby.iapi.services.stream.HeaderPrintWriter;\r
+import org.apache.derby.iapi.services.stream.InfoStreams;\r
+\r
+import org.apache.derby.iapi.sql.execute.CursorResultSet;\r
+import org.apache.derby.iapi.sql.execute.ExecRow;\r
+import org.apache.derby.iapi.sql.execute.NoPutResultSet;\r
+\r
+import org.apache.derby.iapi.sql.Activation;\r
+import org.apache.derby.iapi.sql.ResultDescription;\r
+import org.apache.derby.iapi.types.DataValueDescriptor;\r
+import org.apache.derby.iapi.sql.execute.ExecutionContext;\r
+\r
+import org.apache.derby.iapi.store.access.Qualifier;\r
+\r
+import org.apache.derby.iapi.error.StandardException;\r
+\r
+import org.apache.derby.iapi.services.loader.GeneratedMethod;\r
+\r
+import org.apache.derby.iapi.types.RowLocation;\r
+import org.apache.derby.iapi.reference.SQLState;\r
+\r
+import org.apache.derby.iapi.services.io.FormatableBitSet;\r
+import org.apache.derby.iapi.services.io.FormatableHashtable;\r
+\r
+import org.apache.derby.vti.DeferModification;\r
+import org.apache.derby.vti.IFastPath;\r
+import org.apache.derby.vti.VTIEnvironment;\r
+\r
+import java.sql.PreparedStatement;\r
+import java.sql.ResultSet;\r
+import java.sql.SQLException;\r
+import java.sql.ResultSetMetaData;\r
+\r
+\r
+/**\r
+ */\r
+class VTIResultSet extends NoPutResultSetImpl\r
+       implements CursorResultSet, VTIEnvironment {\r
+\r
+       /* Run time statistics variables */\r
+       public int rowsReturned;\r
+       public String javaClassName;\r
+\r
+    private boolean next;\r
+       private ClassInspector classInspector;\r
+    private GeneratedMethod row;\r
+    private GeneratedMethod constructor;\r
+       private PreparedStatement userPS;\r
+       private ResultSet userVTI;\r
+       private ExecRow allocatedRow;\r
+       private FormatableBitSet referencedColumns;\r
+       private boolean version2;\r
+       private boolean reuseablePs;\r
+       private boolean isTarget;\r
+       private FormatableHashtable compileTimeConstants;\r
+       private int ctcNumber;\r
+\r
+       private boolean pushedProjection;\r
+       private IFastPath       fastPath;\r
+\r
+       private Qualifier[][]   pushedQualifiers;\r
+\r
+       private boolean[] runtimeNullableColumn;\r
+\r
+       /**\r
+               Specified isolation level of SELECT (scan). If not set or\r
+               not application, it will be set to ExecutionContext.UNSPECIFIED_ISOLATION_LEVEL\r
+       */\r
+       private int scanIsolationLevel = ExecutionContext.UNSPECIFIED_ISOLATION_LEVEL;\r
+\r
+    //\r
+    // class interface\r
+    //\r
+    VTIResultSet(Activation activation, GeneratedMethod row, int resultSetNumber,\r
+                                GeneratedMethod constructor,\r
+                                String javaClassName,\r
+                                Qualifier[][] pushedQualifiers,\r
+                                int erdNumber,\r
+                                boolean version2, boolean reuseablePs,\r
+                                int ctcNumber,\r
+                                boolean isTarget,\r
+                                int scanIsolationLevel,\r
+                            double optimizerEstimatedRowCount,\r
+                                double optimizerEstimatedCost) \r
+               throws StandardException\r
+       {\r
+               super(activation, resultSetNumber, \r
+                         optimizerEstimatedRowCount, optimizerEstimatedCost);\r
+        this.row = row;\r
+               this.constructor = constructor;\r
+               this.javaClassName = javaClassName;\r
+               this.version2 = version2;\r
+               this.reuseablePs = reuseablePs;\r
+               this.isTarget = isTarget;\r
+               this.pushedQualifiers = pushedQualifiers;\r
+               this.scanIsolationLevel = scanIsolationLevel;\r
+\r
+               if (erdNumber != -1)\r
+               {\r
+                       this.referencedColumns = (FormatableBitSet)(activation.getPreparedStatement().\r
+                                                               getSavedObject(erdNumber));\r
+               }\r
+\r
+               this.ctcNumber = ctcNumber;\r
+               compileTimeConstants = (FormatableHashtable) (activation.getPreparedStatement().\r
+                                                               getSavedObject(ctcNumber));\r
+\r
+               constructorTime += getElapsedMillis(beginTime);\r
+    }\r
+\r
+       //\r
+       // ResultSet interface (leftover from NoPutResultSet)\r
+       //\r
+\r
+\r
+       /**\r
+     * Sets state to 'open'.\r
+        *\r
+        * @exception StandardException thrown if activation closed.\r
+     */\r
+       public void     openCore() throws StandardException \r
+       {\r
+               beginTime = getCurrentTimeMillis();\r
+               if (SanityManager.DEBUG)\r
+                   SanityManager.ASSERT( ! isOpen, "VTIResultSet already open");\r
+\r
+           isOpen = true;\r
+               numOpens++;\r
+\r
+               /* We need to Instantiate the user's ResultSet on the each open since\r
+                * there is no way to close and then reopen a java.sql.ResultSet.\r
+                * For Version 2 VTIs, we may be able to skip instantiated their\r
+                * PreparedStatement here.\r
+                */\r
+               try {\r
+                       if (version2)\r
+                       {\r
+                               userPS = (PreparedStatement) constructor.invoke(activation);\r
+\r
+                               if (userPS instanceof org.apache.derby.vti.Pushable) {\r
+                                       org.apache.derby.vti.Pushable p = (org.apache.derby.vti.Pushable) userPS;\r
+                                       if (referencedColumns != null) {\r
+                                               pushedProjection = p.pushProjection(this, getProjectedColList());\r
+                                       }\r
+                               }\r
+\r
+                               if (userPS instanceof org.apache.derby.vti.IQualifyable) {\r
+                                       org.apache.derby.vti.IQualifyable q = (org.apache.derby.vti.IQualifyable) userPS;\r
+\r
+                                       q.setQualifiers(this, pushedQualifiers);\r
+                               }\r
+                               fastPath = userPS instanceof IFastPath ? (IFastPath) userPS : null;\r
+\r
+                if( isTarget\r
+                    && userPS instanceof DeferModification\r
+                    && activation.getConstantAction() instanceof UpdatableVTIConstantAction)\r
+                {\r
+                    UpdatableVTIConstantAction constants = (UpdatableVTIConstantAction) activation.getConstantAction();\r
+                    ((DeferModification) userPS).modificationNotify( constants.statementType, constants.deferred);\r
+                }\r
+                \r
+                               if ((fastPath != null) && fastPath.executeAsFastPath())\r
+                                       ;\r
+                               else\r
+                                       userVTI = userPS.executeQuery();\r
+\r
+                               /* Save off the target VTI */\r
+                               if (isTarget)\r
+                               {\r
+                                       activation.setTargetVTI(userVTI);\r
+                               }\r
+\r
+                       }\r
+                       else\r
+                       {\r
+                               userVTI = (ResultSet) constructor.invoke(activation);\r
+                       }\r
+\r
+                       // Set up the nullablity of the runtime columns, may be delayed\r
+                       setNullableColumnList();\r
+               }\r
+               catch (Throwable t)\r
+               {\r
+                       throw StandardException.unexpectedUserException(t);\r
+               }\r
+\r
+\r
+               openTime += getElapsedMillis(beginTime);\r
+       }\r
+\r
+       private boolean[] setNullableColumnList() throws SQLException {\r
+\r
+               if (runtimeNullableColumn != null)\r
+                       return runtimeNullableColumn;\r
+\r
+               if (userVTI == null)\r
+                       return null;\r
+\r
+               ResultSetMetaData rsmd = userVTI.getMetaData();\r
+               boolean[] nullableColumn = new boolean[rsmd.getColumnCount() + 1];\r
+               for (int i = 1; i <  nullableColumn.length; i++) {\r
+                       nullableColumn[i] = rsmd.isNullable(i) != ResultSetMetaData.columnNoNulls;\r
+               }\r
+\r
+               return runtimeNullableColumn = nullableColumn;\r
+       }\r
+\r
+       /**\r
+        * If the VTI is a version2 vti that does not\r
+        * need to be instantiated multiple times then\r
+        * we simply close the current ResultSet and \r
+        * create a new one via a call to \r
+        * PreparedStatement.executeQuery().\r
+        *\r
+        * @see NoPutResultSet#openCore\r
+        * @exception StandardException thrown if cursor finished.\r
+        */\r
+       public void reopenCore() throws StandardException\r
+       {\r
+               if (reuseablePs)\r
+               {\r
+                       /* close the user ResultSet.\r
+                        */\r
+                       if (userVTI != null)\r
+                       {\r
+                               try\r
+                               {\r
+                                       userVTI.close();\r
+                                       userVTI = userPS.executeQuery();\r
+\r
+                                       /* Save off the target VTI */\r
+                                       if (isTarget)\r
+                                       {\r
+                                               activation.setTargetVTI(userVTI);\r
+                                       }\r
+                               } catch (SQLException se)\r
+                               {\r
+                                       throw StandardException.unexpectedUserException(se);\r
+                               }\r
+                       }\r
+               }\r
+               else\r
+               {\r
+                       close();\r
+                       openCore();     \r
+               }\r
+       }\r
+\r
+       /**\r
+     * If open and not returned yet, returns the row\r
+     * after plugging the parameters into the expressions.\r
+        *\r
+        * @exception StandardException thrown on failure.\r
+     */\r
+       public ExecRow  getNextRowCore() throws StandardException \r
+       {\r
+           ExecRow result = null;\r
+\r
+               beginTime = getCurrentTimeMillis();\r
+               \r
+               if ( isOpen ) \r
+               {\r
+                       try\r
+                       {\r
+                               if ((userVTI == null) && (fastPath != null)) {\r
+                                       result = getAllocatedRow();\r
+                                       int action = fastPath.nextRow(result.getRowArray());\r
+                                       if (action == IFastPath.GOT_ROW)\r
+                                               ;\r
+                                       else if (action == IFastPath.SCAN_COMPLETED)\r
+                                               result = null;\r
+                                       else if (action == IFastPath.NEED_RS) {\r
+                                               userVTI = userPS.executeQuery();\r
+                                       }\r
+                               }\r
+                               if ((userVTI != null))\r
+                {\r
+                    if( ! userVTI.next())\r
+                    {\r
+                        if( null != fastPath)\r
+                            fastPath.rowsDone();\r
+                        result = null;\r
+                    }\r
+                    else\r
+                    {\r
+                        // Get the cached row and fill it up\r
+                        result = getAllocatedRow();\r
+                        populateFromResultSet(result);\r
+                        if (fastPath != null)\r
+                            fastPath.currentRow(userVTI, result.getRowArray());\r
+                    }\r
+                               }\r
+                       }\r
+                       catch (Throwable t)\r
+                       {\r
+                               throw StandardException.unexpectedUserException(t);\r
+                       }\r
+\r
+               }\r
+\r
+               setCurrentRow(result);\r
+               if (result != null)\r
+               {\r
+                       rowsReturned++;\r
+                       rowsSeen++;\r
+               }\r
+\r
+               nextTime += getElapsedMillis(beginTime);\r
+           return result;\r
+       }\r
+\r
+       \r
+\r
+       /**\r
+     * @see org.apache.derby.iapi.sql.ResultSet#close\r
+        *\r
+        * @exception StandardException thrown on error\r
+        */\r
+       public void     close() throws StandardException\r
+       {\r
+               beginTime = getCurrentTimeMillis();\r
+               if (isOpen) {\r
+\r
+                       // we don't want to keep around a pointer to the\r
+                       // row ... so it can be thrown away.\r
+                       // REVISIT: does this need to be in a finally\r
+                       // block, to ensure that it is executed?\r
+               clearCurrentRow();\r
+               next = false;\r
+\r
+                       /* close the user ResultSet.  We have to eat any exception here\r
+                        * since our close() method cannot throw an exception.\r
+                        */\r
+                       if (userVTI != null)\r
+                       {\r
+                               try\r
+                               {\r
+                                       userVTI.close();\r
+                               } catch (SQLException se)\r
+                               {\r
+                                       throw StandardException.unexpectedUserException(se);\r
+                               }\r
+                               finally {\r
+                                       userVTI = null;\r
+                               }\r
+                       }\r
+                       if ((userPS != null) && !reuseablePs)\r
+                       {\r
+                               try\r
+                               {\r
+                                       userPS.close();\r
+                               } catch (SQLException se)\r
+                               {\r
+                                       throw StandardException.unexpectedUserException(se);\r
+                               }\r
+                               finally {\r
+                                       userPS = null;\r
+                               }\r
+                       }\r
+                       super.close();\r
+               }\r
+               else\r
+                       if (SanityManager.DEBUG)\r
+                               SanityManager.DEBUG("CloseRepeatInfo","Close of VTIResultSet repeated");\r
+\r
+               closeTime += getElapsedMillis(beginTime);\r
+       }\r
+\r
+       public void finish() throws StandardException {\r
+\r
+               // for a reusablePS it will be closed by the activation\r
+               // when it is closed.\r
+               if ((userPS != null) && !reuseablePs)\r
+               {\r
+                       try\r
+                       {\r
+                               userPS.close();\r
+                               userPS = null;\r
+                       } catch (SQLException se)\r
+                       {\r
+                               throw StandardException.unexpectedUserException(se);\r
+                       }\r
+               }\r
+\r
+               finishAndRTS();\r
+\r
+       }\r
+\r
+       /**\r
+        * Return the total amount of time spent in this ResultSet\r
+        *\r
+        * @param type  CURRENT_RESULTSET_ONLY - time spent only in this ResultSet\r
+        *                              ENTIRE_RESULTSET_TREE  - time spent in this ResultSet and below.\r
+        *\r
+        * @return long         The total amount of time spent (in milliseconds).\r
+        */\r
+       public long getTimeSpent(int type)\r
+       {\r
+               long totTime = constructorTime + openTime + nextTime + closeTime;\r
+               return totTime;\r
+       }\r
+\r
+       //\r
+       // CursorResultSet interface\r
+       //\r
+\r
+       /**\r
+        * This is not operating against a stored table,\r
+        * so it has no row location to report.\r
+        *\r
+        * @see CursorResultSet\r
+        *\r
+        * @return a null.\r
+        */\r
+       public RowLocation getRowLocation() {\r
+               if (SanityManager.DEBUG)\r
+                       SanityManager.THROWASSERT("RowResultSet used in positioned update/delete");\r
+               return null;\r
+       }\r
+\r
+       /**\r
+        * This is not used in positioned update and delete,\r
+        * so just return a null.\r
+        *\r
+        * @see CursorResultSet\r
+        *\r
+        * @return a null.\r
+        */\r
+       public ExecRow getCurrentRow() {\r
+               if (SanityManager.DEBUG)\r
+                       SanityManager.THROWASSERT("RowResultSet used in positioned update/delete");\r
+               return null;\r
+       }\r
+\r
+       // Class implementation\r
+\r
+       /**\r
+        * Return the GeneratedMethod for instantiating the VTI.\r
+        *\r
+        * @return The  GeneratedMethod for instantiating the VTI.\r
+        */\r
+       GeneratedMethod getVTIConstructor()\r
+       {\r
+               return constructor;\r
+       }\r
+\r
+       boolean isReuseablePs() {\r
+               return reuseablePs;\r
+       }\r
+\r
+\r
+       /**\r
+        * Cache the ExecRow for this result set.\r
+        *\r
+        * @return The cached ExecRow for this ResultSet\r
+        *\r
+        * @exception StandardException thrown on failure.\r
+        */\r
+       private ExecRow getAllocatedRow()\r
+               throws StandardException\r
+       {\r
+               if (allocatedRow == null)\r
+               {\r
+                       allocatedRow = (ExecRow) row.invoke(activation);\r
+               }\r
+\r
+               return allocatedRow;\r
+       }\r
+\r
+       private int[] getProjectedColList() {\r
+\r
+               FormatableBitSet refs = referencedColumns;\r
+               int size = refs.size();\r
+               int arrayLen = 0;\r
+               for (int i = 0; i < size; i++) {\r
+                       if (refs.isSet(i))\r
+                               arrayLen++;\r
+               }\r
+\r
+               int[] colList = new int[arrayLen];\r
+               int offset = 0;\r
+               for (int i = 0; i < size; i++) {\r
+                       if (refs.isSet(i))\r
+                               colList[offset++] = i + 1;\r
+               }\r
+\r
+               return colList;\r
+       }\r
+       /**\r
+        * @exception StandardException thrown on failure to open\r
+        */\r
+       public void populateFromResultSet(ExecRow row)\r
+               throws StandardException\r
+       {\r
+               try\r
+               {\r
+                       boolean[] nullableColumn = setNullableColumnList();\r
+                       DataValueDescriptor[] columns = row.getRowArray();\r
+                       // ExecRows are 0-based, ResultSets are 1-based\r
+                       int rsColNumber = 1;\r
+                       for (int index = 0; index < columns.length; index++)\r
+                       {\r
+                               // Skip over unreferenced columns\r
+                               if (referencedColumns != null && (! referencedColumns.get(index)))\r
+                               {\r
+                                       if (!pushedProjection)\r
+                                               rsColNumber++;\r
+\r
+                                       continue;\r
+                               }\r
+\r
+                               columns[index].setValueFromResultSet(\r
+                                                                       userVTI, rsColNumber, \r
+                                                                       /* last parameter is whether or\r
+                                                                        * not the column is nullable\r
+                                                                        */\r
+                                                                       nullableColumn[rsColNumber]);\r
+                               rsColNumber++;\r
+                       }\r
+\r
+               } catch (StandardException se) {\r
+                       throw se;\r
+               }\r
+               catch (Throwable t)\r
+               {\r
+                       throw StandardException.unexpectedUserException(t);\r
+               }\r
+       }\r
+\r
+       public final int getScanIsolationLevel() {\r
+               return scanIsolationLevel;\r
+       }\r
+\r
+       /*\r
+       ** VTIEnvironment\r
+       */\r
+       public final boolean isCompileTime() {\r
+               return false;\r
+       }\r
+\r
+       public final String getOriginalSQL() {\r
+               return activation.getPreparedStatement().getSource();\r
+       }\r
+\r
+       public final int getStatementIsolationLevel() {\r
+               return ExecutionContext.CS_TO_JDBC_ISOLATION_LEVEL_MAP[getScanIsolationLevel()];\r
+       }\r
+\r
+\r
+       public final void setSharedState(String key, java.io.Serializable value) {\r
+               if (key == null)\r
+                       return;\r
+\r
+               if (compileTimeConstants == null) {\r
+\r
+                       Object[] savedObjects = activation.getPreparedStatement().getSavedObjects();\r
+\r
+                       synchronized (savedObjects) {\r
+\r
+                               compileTimeConstants = (FormatableHashtable) savedObjects[ctcNumber];\r
+                               if (compileTimeConstants == null) {\r
+                                       compileTimeConstants = new FormatableHashtable();\r
+                                       savedObjects[ctcNumber] = compileTimeConstants;\r
+                               }\r
+                       }\r
+               }\r
+\r
+               if (value == null)\r
+                       compileTimeConstants.remove(key);\r
+               else\r
+                       compileTimeConstants.put(key, value);\r
+\r
+\r
+       }\r
+\r
+       public Object getSharedState(String key) {\r
+               if ((key == null) || (compileTimeConstants == null))\r
+                       return null;\r
+\r
+               return compileTimeConstants.get(key);\r
+       }\r
+}\r