List:Commits« Previous MessageNext Message »
From:pharvey Date:August 18 2006 6:03am
Subject:Connector/ODBC 5 commit: r492 - in trunk: MYODBCDriver/MYODBCDriverLib MYSQLPlus/MYSQLPlusLib MYSQLPlus/include
View as plain text  
Modified:
   trunk/MYODBCDriver/MYODBCDriverLib/SQLGetFunctions.cpp
   trunk/MYSQLPlus/MYSQLPlusLib/MResult.cpp
   trunk/MYSQLPlus/MYSQLPlusLib/MResult.h
   trunk/MYSQLPlus/MYSQLPlusLib/MResultPlus.cpp
   trunk/MYSQLPlus/MYSQLPlusLib/MResultPlus.h
   trunk/MYSQLPlus/MYSQLPlusLib/MResultRes.cpp
   trunk/MYSQLPlus/MYSQLPlusLib/MResultRes.h
   trunk/MYSQLPlus/MYSQLPlusLib/MResultStmt.cpp
   trunk/MYSQLPlus/MYSQLPlusLib/MResultStmt.h
   trunk/MYSQLPlus/MYSQLPlusLib/MStatement.cpp
   trunk/MYSQLPlus/include/MStatement.h
Log:
- more work to implement block cursors
- implemented SQLBulkOperations with min functionality as per C/ODBC v3

Modified: trunk/MYODBCDriver/MYODBCDriverLib/SQLGetFunctions.cpp
===================================================================
--- trunk/MYODBCDriver/MYODBCDriverLib/SQLGetFunctions.cpp	2006-08-17 06:02:08 UTC (rev
491)
+++ trunk/MYODBCDriver/MYODBCDriverLib/SQLGetFunctions.cpp	2006-08-18 06:03:26 UTC (rev
492)
@@ -96,7 +96,7 @@
     SQL_API_SQLTABLES,
 /*  SQL_API_SQLTRANSACT,            Dep */
 /*  SQL_API_SQLALLOCHANDLESTD       Std */
-/*  SQL_API_SQLBULKOPERATIONS,          */
+    SQL_API_SQLBULKOPERATIONS,
     SQL_API_SQLBINDPARAMETER,
     SQL_API_SQLBROWSECONNECT,
 /*  SQL_API_SQLCOLATTRIBUTES,       Dep */
@@ -113,7 +113,7 @@
     SQL_API_SQLPRIMARYKEYS,
     SQL_API_SQLPROCEDURECOLUMNS,
     SQL_API_SQLPROCEDURES,
-/*  SQL_API_SQLSETPOS,                  */
+    SQL_API_SQLSETPOS,
 /*  SQL_API_SQLSETSCROLLOPTIONS,    Dep */
     SQL_API_SQLTABLEPRIVILEGES
 };

Modified: trunk/MYSQLPlus/MYSQLPlusLib/MResult.cpp
===================================================================
--- trunk/MYSQLPlus/MYSQLPlusLib/MResult.cpp	2006-08-17 06:02:08 UTC (rev 491)
+++ trunk/MYSQLPlus/MYSQLPlusLib/MResult.cpp	2006-08-18 06:03:26 UTC (rev 492)
@@ -83,26 +83,13 @@
 }
 
 /*! 
-    \internal
-    \brief  Allocates, initializes and returns a new MYODBC_RES_HANDLE. 
+    \brief  Base class for resultset abstraction.
 
-            The current position will be EOR.
-            
-    \param  hDia        Diagnostic handle to use for errors and warnings.
-                        This is likely to just be the diagnostic handle
-                        associated with an ODBC statement.
-    \param  pDesIRD     Descriptor describing the result set. This is
-                        likely to be the IRD of a statement.                            
-    \param  pMySQL      The current MySQL (connection) handle. This should
-                        be null if nMethod is MYODBC_RES_METHOD_INTERNAL.
-    \param  phRes       Pointer to a place where we can store the new handle.
+            Resultsets are derived from this abstract base class. 
 
-    \return SQLRETURN
-
-    \retval SQL_SUCCESS
-    \retval SQL_ERROR  
-
-    \sa     MYODBCResFree
+    \sa MResultPlus
+        MResultRes
+        MResultStmt
 */
 MResult::MResult( MStatement *pStatement )
     : QObject( pStatement )
@@ -114,7 +101,6 @@
     nState          = STATE_UNINITIALIZED;
     bBuffered       = true;
     nRow            = 0;
-    nPos            = 1;
     nRowsAffected   = 0;
     /*!
         \internal
@@ -138,38 +124,6 @@
     MYODBCDbgReturn2();
 }
 
-/*! 
-    \brief  Sets the cursor position in a rowset (a subset of the resultset).
-
-            Allows an application to refresh data in the rowset or to update or 
-            delete data in the resultset.
-            
-    \param  nRowNumber  1-based position in rowset to perform operation. 0 = all rows in
rowset.
-    \param  nOperation  Operation;
-                            - SQL_POSITION
-                            - SQL_REFRESH
-                            - SQL_UPDATE
-                            - SQL_DELETE
-    \param  nLockType   How to lock the row(s) after operation;
-                            - SQL_LOCK_NO_CHANGE
-                            - SQL_LOCK_EXCLUSIVE
-                            - SQL_LOCK_UNLOCK 
-    \return SQLRETURN
-
-    \retval SQL_SUCCESS
-    \retval SQL_SUCCESS_WITH_INFO
-    \retval SQL_ERROR  
-
-    \sa     doFetch
-            doFetchScroll
-            doBulkOperations
-*/
-SQLRETURN MResult::setPos( SQLUSMALLINT nRowNumber, SQLUSMALLINT nOperation, SQLUSMALLINT
nLockType )
-{
-    MYODBCDbgEnter();
-    MYODBCDbgReturn( SQL_ERROR );
-}
-
 MResult::STATE MResult::getState()
 {
     MYODBCDbgEnter();
@@ -432,103 +386,6 @@
     MYODBCDbgReturn3( "%d", bBuffered );
 }
 
-/*!
-    \brief  Fetchs the next row/rowset from the resultset.
-
-*/
-SQLRETURN MResult::doFetch()
-{
-    MYODBCDbgEnter();
-
-    MYODBCDbgReturn( doFetchScroll( SQL_FETCH_NEXT, 0 ) );
-}
-
-/*!
-    \brief  Fetchs the desired row/rowset from the resultset.
-
-*/
-SQLRETURN MResult::doFetchScroll( SQLSMALLINT nFetchOrientation, SQLINTEGER nFetchOffset
)
-{
-    MYODBCDbgEnter();
-
-    switch ( nFetchOrientation )
-    {
-        case SQL_FETCH_NEXT:
-            /*!
-                \internal ODBC RULE
-
-                Return the next rowset. This is equivalent to calling SQLFetch.
SQLFetchScroll ignores the value 
-                of FetchOffset.
-            */
-            MYODBCDbgReturn( getResult()->doNext() );
-
-        case SQL_FETCH_PRIOR:
-            /*!
-                \internal ODBC RULE
-
-                Return the prior rowset. SQLFetchScroll ignores the value of FetchOffset.
-            */
-            MYODBCDbgReturn( getResult()->doPrev() );
-
-        case SQL_FETCH_RELATIVE:
-            /*!
-                \internal ODBC RULE
-
-                Return the rowset FetchOffset from the start of the current rowset.
-            */
-            {
-            }
-            break;
-
-        case SQL_FETCH_ABSOLUTE:
-            /*!
-                \internal ODBC RULE
-
-                Return the rowset starting at row FetchOffset.
-            */
-            {
-            }
-            break;
-
-        case SQL_FETCH_FIRST:
-            /*!
-                \internal ODBC RULE
-
-                Return the first rowset in the result set. SQLFetchScroll ignores the
value of FetchOffset.
-            */
-            MYODBCDbgReturn( getResult()->doFirst() );
-
-        case SQL_FETCH_LAST:
-            /*!
-                \internal ODBC RULE
-
-                Return the last complete rowset in the result set. SQLFetchScroll ignores
the value of FetchOffset.
-            */
-            MYODBCDbgReturn( getResult()->doLast() );
-
-        case SQL_FETCH_BOOKMARK:
-            /*!
-                \internal ODBC RULE
-
-                Return the rowset FetchOffset rows from the bookmark specified by the
SQL_ATTR_FETCH_BOOKMARK_PTR 
-                statement attribute.
-            */
-            {
-            }
-            break;
-
-        default:
-            /*!
-                \internal ODBC RULE (DM)
-
-                The value specified for the argument FetchOrientation was invalid.
-            */
-            MYODBCDbgReturn( getDiagnostic()->doAppend( MDiagnostic::DIA_HY106 ) );
-    }
-
-    MYODBCDbgReturn( getDiagnostic()->doAppend( MDiagnostic::DIA_HY000, 0, tr(
QString( "Control reached unexpected place %1:%2" ).arg( __FILE__ ).arg( __LINE__ ) ) )
);
-}
-
 BOOLEAN MResult::isValidColumn( uint nColumn )
 {
     BOOLEAN b;

Modified: trunk/MYSQLPlus/MYSQLPlusLib/MResult.h
===================================================================
--- trunk/MYSQLPlus/MYSQLPlusLib/MResult.h	2006-08-17 06:02:08 UTC (rev 491)
+++ trunk/MYSQLPlus/MYSQLPlusLib/MResult.h	2006-08-18 06:03:26 UTC (rev 492)
@@ -84,12 +84,14 @@
             Notice that we have to support row and set based interaction. The most common

             interaction is for the app to request a result-set (set based operation) 
             using SQLExecute() but then to operate on the result-set using row based
-            interactions using SQLFetch(). Such things as Block cursors and column binds 
-            across rows effect a kind of set based interaction upon the result-set.
+            interactions - this is what we support here. This does not support such
things
+            as block cursors. Block cursor support is layered upon our functionality here
- find 
+            that in MStatement.
 
     \sa     MResultPlus
             MResultRes
             MResultStmt
+            MStatement
 */
 class MResult : public QObject
 {
@@ -107,7 +109,6 @@
     virtual ~MResult();
 
     /* setters */
-    virtual SQLRETURN setPos( SQLUSMALLINT nRowNumber, SQLUSMALLINT nOperation,
SQLUSMALLINT nLockType );
     virtual SQLRETURN setData( uint nColumn, const QVariant &variantData ) = 0;
     virtual SQLRETURN setRow( qulonglong nRow ) = 0;
 
@@ -124,10 +125,17 @@
     /* doers */
     virtual SQLRETURN doPrepare( MCommand *pCommand ) = 0;
     virtual SQLRETURN doExecute() = 0;
+    virtual SQLRETURN doAppend() = 0;
+    virtual SQLRETURN doClear() = 0;
+    virtual SQLRETURN doDelete() = 0;
+    virtual SQLRETURN doFirst() = 0;
+    virtual SQLRETURN doInsert() = 0;
+    virtual SQLRETURN doLast() = 0;
+    virtual SQLRETURN doNext() = 0;
+    virtual SQLRETURN doPrev() = 0;
+    virtual SQLRETURN doSkip( qlonglong nRows ) = 0;
+    virtual SQLRETURN doCommit() = 0;
 
-    virtual SQLRETURN doFetch();
-    virtual SQLRETURN doFetchScroll( SQLSMALLINT nFetchOrientation, SQLINTEGER
nFetchOffset );
-
     /* isers */
     virtual BOOLEAN isValidColumn( uint nColumn );
     virtual BOOLEAN isValidRow() = 0;
@@ -140,6 +148,7 @@
 protected:
     MResultGetData  resultGetData;      /*!< to support getData()       */
     MResultPutData  resultPutData;      /*!< to support doPutData()     */
+    qulonglong      nRow;           /*!< Current row number (SQL_ATTR_ROW_NUMBER).    
                                                                 */
 
     /* setters */
     BOOLEAN setState( STATE nState );
@@ -155,6 +164,7 @@
     MDescriptor *   getAppRowDesc();
     MDescriptor *   getImpParamDesc();
     MDescriptor *   getImpRowDesc();
+    qulonglong      getRow() { return nRow; }
 
     /* support for getData: this is called when target C type is SQL_C_DEFAULT  (derive
type from IRD)  */
     SQLRETURN       setGetDataDefault();
@@ -258,25 +268,12 @@
     /*@}*/
 
     /* doers */
-    virtual SQLRETURN doAppend() = 0;
-    virtual SQLRETURN doClear() = 0;
-    virtual SQLRETURN doDelete() = 0;
-    virtual SQLRETURN doFirst() = 0;
-    virtual SQLRETURN doInsert() = 0;
-    virtual SQLRETURN doLast() = 0;
-    virtual SQLRETURN doNext() = 0;
-    virtual SQLRETURN doPrev() = 0;
-    virtual SQLRETURN doSkip( qlonglong nRows ) = 0;
-    virtual SQLRETURN doCommit() = 0;
-
     virtual SQLRETURN doStateRollBack( STATE nState ) = 0;
     SQLRETURN doLoadMetaDataField( unsigned int nField, MYSQL_FIELD *pField,
MDescriptorIRD *pDescriptor );
 
 private:
     STATE           nState;         /*!< our state                                    
                                                                 */
     BOOLEAN         bBuffered;      /*!< true causes entire resultset to get pulled to
client at execute (enabling other features) (default=true)       */
-    qulonglong      nRow;           /*!< Current row number (1st row of rowset) where
0=eof/bof. We need to keep track of this due to lack of functionality in client.  */
-    SQLUSMALLINT    nPos;           /*!< Pos/row in rowset which is current (1 to
rowset size). Affects getData() etc. See also; setPos().              */
     qulonglong      nRowsAffected;  /*!< number of rows affected by a non-SELECT
statement (catalog and SHOW statements count as SELECT in this case)   */
 };
 

Modified: trunk/MYSQLPlus/MYSQLPlusLib/MResultPlus.cpp
===================================================================
--- trunk/MYSQLPlus/MYSQLPlusLib/MResultPlus.cpp	2006-08-17 06:02:08 UTC (rev 491)
+++ trunk/MYSQLPlus/MYSQLPlusLib/MResultPlus.cpp	2006-08-18 06:03:26 UTC (rev 492)
@@ -1433,7 +1433,6 @@
         case STATE_EXECUTED:
             listResults.clear();
             nRow = 0;
-            nPos = 1;
             setRowsAffected( 0 );
 //            getImpParamDesc()->doClear();
             getImpRowDesc()->doClear();

Modified: trunk/MYSQLPlus/MYSQLPlusLib/MResultPlus.h
===================================================================
--- trunk/MYSQLPlus/MYSQLPlusLib/MResultPlus.h	2006-08-17 06:02:08 UTC (rev 491)
+++ trunk/MYSQLPlus/MYSQLPlusLib/MResultPlus.h	2006-08-18 06:03:26 UTC (rev 492)
@@ -59,6 +59,16 @@
     /* doers */
     SQLRETURN doPrepare( MCommand *pCommand );
     SQLRETURN doExecute();
+    SQLRETURN doAppend();
+    SQLRETURN doClear();
+    SQLRETURN doDelete();
+    SQLRETURN doFirst();
+    SQLRETURN doInsert();
+    SQLRETURN doLast();
+    SQLRETURN doNext();
+    SQLRETURN doPrev();
+    SQLRETURN doSkip( qlonglong nRows );
+    SQLRETURN doCommit();
 
     SQLRETURN doColumns( const QString &stringCatalogFilter, const QString
&stringSchemaFilter, const QString &stringTableFilter, const QString
&stringColumnFilter );
     SQLRETURN doForeignKeys( const QString &stringPKCatalog, const QString
&stringPKSchema, const QString &stringPKTable, const QString
&stringFKCatalog, const QString &stringFKSchema, const QString &stringFKTable
);
@@ -78,17 +88,6 @@
 
 protected:
     /* doers */
-    SQLRETURN doAppend();
-    SQLRETURN doClear();
-    SQLRETURN doDelete();
-    SQLRETURN doFirst();
-    SQLRETURN doInsert();
-    SQLRETURN doLast();
-    SQLRETURN doNext();
-    SQLRETURN doPrev();
-    SQLRETURN doSkip( qlonglong nRows );
-    SQLRETURN doCommit();
-
     SQLRETURN doStateRollBack( STATE nState );
 
     SQLRETURN doAppendVarChar();

Modified: trunk/MYSQLPlus/MYSQLPlusLib/MResultRes.cpp
===================================================================
--- trunk/MYSQLPlus/MYSQLPlusLib/MResultRes.cpp	2006-08-17 06:02:08 UTC (rev 491)
+++ trunk/MYSQLPlus/MYSQLPlusLib/MResultRes.cpp	2006-08-18 06:03:26 UTC (rev 492)
@@ -1034,7 +1034,6 @@
                 mysql_free_result( pRes );
             pRes = NULL;
             nRow = 0;
-            nPos = 1;
             setRowsAffected( 0 );
             resultGetData.doClear();
             resultPutData.doClear();

Modified: trunk/MYSQLPlus/MYSQLPlusLib/MResultRes.h
===================================================================
--- trunk/MYSQLPlus/MYSQLPlusLib/MResultRes.h	2006-08-17 06:02:08 UTC (rev 491)
+++ trunk/MYSQLPlus/MYSQLPlusLib/MResultRes.h	2006-08-18 06:03:26 UTC (rev 492)
@@ -34,14 +34,6 @@
 
     SQLRETURN doPrepare( MCommand *pCommand );
     SQLRETURN doExecute();
-
-    BOOLEAN isValidRow();
-    BOOLEAN isValidRow( qulonglong nRow );
-    BOOLEAN isDirty();
-
-protected:
-
-    /* doers */
     SQLRETURN doAppend();
     SQLRETURN doClear();
     SQLRETURN doDelete();
@@ -53,6 +45,13 @@
     SQLRETURN doSkip( qlonglong nRows );
     SQLRETURN doCommit();
 
+    BOOLEAN isValidRow();
+    BOOLEAN isValidRow( qulonglong nRow );
+    BOOLEAN isDirty();
+
+protected:
+
+    /* doers */
     SQLRETURN doStateRollBack( STATE nState );
 
 private:

Modified: trunk/MYSQLPlus/MYSQLPlusLib/MResultStmt.cpp
===================================================================
--- trunk/MYSQLPlus/MYSQLPlusLib/MResultStmt.cpp	2006-08-17 06:02:08 UTC (rev 491)
+++ trunk/MYSQLPlus/MYSQLPlusLib/MResultStmt.cpp	2006-08-18 06:03:26 UTC (rev 492)
@@ -1039,7 +1039,6 @@
             if ( !mysql_stmt_reset( pstm ) )
                 MYODBCDbgReturn( getDiagnostic()->doAppend( MDiagnostic::DIA_HY000,
mysql_stmt_errno( pstm ), mysql_stmt_error( pstm ) ) );
             nRow = 0;
-            nPos = 1;
             setRowsAffected( 0 );
             resultGetData.doClear();
             setState( STATE_PREPARED );

Modified: trunk/MYSQLPlus/MYSQLPlusLib/MResultStmt.h
===================================================================
--- trunk/MYSQLPlus/MYSQLPlusLib/MResultStmt.h	2006-08-17 06:02:08 UTC (rev 491)
+++ trunk/MYSQLPlus/MYSQLPlusLib/MResultStmt.h	2006-08-18 06:03:26 UTC (rev 492)
@@ -64,14 +64,6 @@
 
     SQLRETURN doPrepare( MCommand *pCommand );
     SQLRETURN doExecute();
-
-    BOOLEAN isValidRow();
-    BOOLEAN isValidRow( qulonglong nRow );
-    BOOLEAN isDirty();
-
-protected:
-
-    /* doers */
     SQLRETURN doAppend();
     SQLRETURN doClear();
     SQLRETURN doDelete();
@@ -83,6 +75,13 @@
     SQLRETURN doSkip( qlonglong nRows );
     SQLRETURN doCommit();
 
+    BOOLEAN isValidRow();
+    BOOLEAN isValidRow( qulonglong nRow );
+    BOOLEAN isDirty();
+
+protected:
+
+    /* doers */
     SQLRETURN doStateRollBack( STATE nState );
 
 private:

Modified: trunk/MYSQLPlus/MYSQLPlusLib/MStatement.cpp
===================================================================
--- trunk/MYSQLPlus/MYSQLPlusLib/MStatement.cpp	2006-08-17 06:02:08 UTC (rev 491)
+++ trunk/MYSQLPlus/MYSQLPlusLib/MStatement.cpp	2006-08-18 06:03:26 UTC (rev 492)
@@ -6,13 +6,20 @@
             This is the constructor for MStatement. It must have a viable MConnection to
be used
             as a parent object.
 
-            MStatement may have the following child objects;
+            Cursor
 
-                    - MDiagnostic (1)
-                    - MDescriptor (4)
-                    - MCommands (0-1)
-                    - MResult (0-1)
+                A resultset maintains a very basic cursor which operates on a row. Here,
a statement 
+                expands on the resultset cursor to implement block cursors as needed. 
 
+            Object Hierarchy
+
+                MStatement may have the following child objects;
+    
+                        - MDiagnostic (1)
+                        - MDescriptor (4)
+                        - MCommands (0-1)
+                        - MResult (0-1)
+
     \note
 
             Indicate our className without using Q_OBJECT/className(). We can do this
@@ -38,6 +45,7 @@
     pAppParamDesc       = pAppParamDescOrig = new MDescriptorAPD( this );
     pAppRowDesc         = pAppRowDescOrig   = new MDescriptorARD( this );
     bImplicitPrepare    = false;
+    nPos                = 1;
     nAsyncEnable        = SQL_ASYNC_ENABLE_DEFAULT;
     nConcurrency        = SQL_CONCUR_DEFAULT;
     nCursorScrollable   = SQL_NONSCROLLABLE;
@@ -191,6 +199,32 @@
     MYODBCDbgReturn( SQL_SUCCESS );
 }
 
+/*! 
+    \brief  Sets the cursor position in a rowset (a subset of the resultset).
+
+            Allows an application to refresh data in the rowset or to update or 
+            delete data in the resultset.
+            
+    \param  nRowNumber  1-based position in rowset to perform operation. 0 = all rows in
rowset.
+    \param  nOperation  Operation;
+                            - SQL_POSITION
+                            - SQL_REFRESH
+                            - SQL_UPDATE
+                            - SQL_DELETE
+    \param  nLockType   How to lock the row(s) after operation;
+                            - SQL_LOCK_NO_CHANGE
+                            - SQL_LOCK_EXCLUSIVE
+                            - SQL_LOCK_UNLOCK 
+    \return SQLRETURN
+
+    \retval SQL_SUCCESS
+    \retval SQL_SUCCESS_WITH_INFO
+    \retval SQL_ERROR  
+
+    \sa     doFetch
+            doFetchScroll
+            doBulkOperations
+*/
 SQLRETURN MStatement::setPos( SQLUSMALLINT nRowNumber, SQLUSMALLINT nOperation,
SQLUSMALLINT nLockType )
 {
     MYODBCDbgEnter();
@@ -202,7 +236,71 @@
     */
     pDiagnostic->doClear();
 
-    MYODBCDbgReturn( SQL_ERROR );
+    /*!
+        \internal ODBC RULE (DM)
+
+        The specified StatementHandle was not in an executed state. The function 
+        was called without first calling SQLExecDirect, SQLExecute, or a catalog 
+        function.     
+    */
+    if ( !isExecuted() )
+        MYODBCDbgReturn( getDiagnostic()->doAppend( MDiagnostic::DIA_HY010 ) );
+
+    /*!
+        \internal ODBC RULE (DM)
+
+        An asynchronously executing function (not this one) was called 
+        for the StatementHandle and was still executing when this function 
+        was called.
+    */
+    if ( isAsyncInProgress() )
+        MYODBCDbgReturn( getDiagnostic()->doAppend( MDiagnostic::DIA_HY010 ) );
+
+    /*!
+        \internal ODBC RULE (DM)
+
+        SQLExecute, SQLExecDirect, SQLBulkOperations, or SQLSetPos was 
+        called for the StatementHandle and returned SQL_NEED_DATA. This 
+        function was called before data was sent for all data-at-execution 
+        parameters or columns.
+    */
+    if ( isDataNeeded() )
+        MYODBCDbgReturn( getDiagnostic()->doAppend( MDiagnostic::DIA_HY010 ) );
+
++++++++++
+
+    switch ( nOperation )
+    {
+        case SQL_POSITION:
+            MYODBCDbgReturn( setPos( nRowNumber ) );
+
+        case SQL_REFRESH:
+        case SQL_UPDATE:
+        case SQL_DELETE:
+
+        case SQL_ADD:
+            /*!
+                \internal ODBC RULE
+
+                SQL_ADD value for the Operation argument has been deprecated for ODBC
3.x. ODBC 3.x 
+                drivers will need to support SQL_ADD for backward compatibility. This
functionality 
+                has been replaced by a call to SQLBulkOperations with an Operation of
SQL_ADD. When 
+                an ODBC 3.x application works with an ODBC 2.x driver, the Driver Manager
maps a call 
+                to SQLBulkOperations with an Operation of SQL_ADD to SQLSetPos with an
Operation of 
+                SQL_ADD.
+
+                \internal MYODBC RULE
+
+                We do not support this backward compatibility. Any applications linking
directly to
+                the driver should be ODBC v3 applications.
+            */
+            MYODBCDbgReturn( getDiagnostic()->doAppend( MDiagnostic::DIA_HYC00 ) );
+
+        default:
+            MYODBCDbgReturn( getDiagnostic()->doAppend( MDiagnostic::DIA_HY092 ) );
+    }
+
+    MYODBCDbgReturn( getDiagnostic()->doAppend( MDiagnostic::DIA_HY000, 0, tr(
"Control reached unexpected location in setPos()." ) ) );
 }
 
 SQLRETURN MStatement::setStmtAttr( SQLINTEGER nAttribute, SQLPOINTER pValue, SQLINTEGER
nStringLength )
@@ -1568,7 +1666,47 @@
     */
     pDiagnostic->doClear();
 
-    MYODBCDbgReturn( SQL_ERROR );
+    /*!
+        \internal ODBC RULE (DM)
+
+        The specified StatementHandle was not in an executed state. The function 
+        was called without first calling SQLExecDirect, SQLExecute, or a catalog 
+        function.     
+    */
+    if ( !isExecuted() )
+        MYODBCDbgReturn( getDiagnostic()->doAppend( MDiagnostic::DIA_HY010 ) );
+
+    /*!
+        \internal ODBC RULE (DM)
+
+        An asynchronously executing function (not this one) was called 
+        for the StatementHandle and was still executing when this function 
+        was called.
+    */
+    if ( isAsyncInProgress() )
+        MYODBCDbgReturn( getDiagnostic()->doAppend( MDiagnostic::DIA_HY010 ) );
+
+    /*!
+        \internal ODBC RULE (DM)
+
+        SQLExecute, SQLExecDirect, SQLBulkOperations, or SQLSetPos was 
+        called for the StatementHandle and returned SQL_NEED_DATA. This 
+        function was called before data was sent for all data-at-execution 
+        parameters or columns.
+    */
+    if ( isDataNeeded() )
+        MYODBCDbgReturn( getDiagnostic()->doAppend( MDiagnostic::DIA_HY010 ) );
+
+    /*!
+        \internal
+        \todo
+
+        This is what C/ODBC v3 does - we need to implement more here.
+    */
+    if ( nOperation == SQL_ADD )
+        MYODBCDbgReturn( setPos( 0, SQL_ADD, SQL_LOCK_NO_CHANGE );
+
+    MYODBCDbgReturn( getDiagnostic()->doAppend( MDiagnostic::DIA_IM001 ) );
 }
 
 /*!
@@ -2585,55 +2723,7 @@
 {
     MYODBCDbgEnter();
 
-    /*!
-        \internal ODBC RULE
-
-        We clear diagnostic each time an ODBC API call is made (with exceptions).
-    */
-    pDiagnostic->doClear();
-
-    /*!
-        \internal ODBC RULE (DM)
-
-        The specified StatementHandle was not in an executed state. 
-        The function was called without first calling SQLExecDirect, 
-        SQLExecute or a catalog function.
-    */
-    if ( !isExecuted() )
-        MYODBCDbgReturn( getDiagnostic()->doAppend( MDiagnostic::DIA_HY010 ) );
-
-    /*!
-        \internal ODBC RULE (DM)
-
-        An asynchronously executing function (not this one) was called 
-        for the StatementHandle and was still executing when this function 
-        was called.
-    */
-    if ( isAsyncInProgress() )
-        MYODBCDbgReturn( getDiagnostic()->doAppend( MDiagnostic::DIA_HY010 ) );
-
-    /*!
-        \internal ODBC RULE (DM)
-
-        SQLExecute, SQLExecDirect, SQLBulkOperations, or SQLSetPos was called for the
StatementHandle and 
-        returned SQL_NEED_DATA. This function was called before data was sent for all
data-at-execution 
-        parameters or columns.
-    */
-    if ( isDataNeeded() )
-        MYODBCDbgReturn( getDiagnostic()->doAppend( MDiagnostic::DIA_HY010 ) );
-
-    /*!
-        \internal ODBC RULE (DM)
-
-        The StatementHandle was in an executed state, but no result 
-        set was associated with the StatementHandle.
-    */
-    if ( getState() == STATE_S4 )
-        MYODBCDbgReturn( getDiagnostic()->doAppend( MDiagnostic::DIA_24000 ) );
-
-    setState( STATE_S6 );
-
-    MYODBCDbgReturn( getResult()->doFetch() );
+    MYODBCDbgReturn( doFetchScroll( SQL_FETCH_NEXT, 0 ) );
 }
 
 SQLRETURN MStatement::doFetchScroll( SQLSMALLINT nFetchOrientation, SQLINTEGER
nFetchOffset )
@@ -2713,7 +2803,7 @@
         but the value specified with the SQL_ATTR_KEYSET_SIZE statement attribute was
greater than 0 and 
         less than the value specified with the SQL_ATTR_ROW_ARRAY_SIZE statement
attribute.
     */
-    if ( getCursorType() == SQL_CURSOR_KEYSET_DRIVEN && ( getKeysetSize() > 0
&& getKeysetSize() < getRowArraySize() )
+    if ( getCursorType() == SQL_CURSOR_KEYSET_DRIVEN && getKeysetSize() > 0
&& getKeysetSize() < getRowArraySize() )
         MYODBCDbgReturn( getDiagnostic()->doAppend( MDiagnostic::DIA_HY107 ) );
 
     /*!
@@ -2737,7 +2827,82 @@
 
     setState( STATE_S6 );
 
-    MYODBCDbgReturn( getResult()->doFetchScroll( nFetchOrientation, nFetchOffset ) );
+    switch ( nFetchOrientation )
+    {
+        case SQL_FETCH_NEXT:
+            /*!
+                \internal ODBC RULE
+
+                Return the next rowset. This is equivalent to calling SQLFetch.
SQLFetchScroll ignores the value 
+                of FetchOffset.
+            */
+            MYODBCDbgReturn( getResult()->doNext() );
+
+        case SQL_FETCH_PRIOR:
+            /*!
+                \internal ODBC RULE
+
+                Return the prior rowset. SQLFetchScroll ignores the value of FetchOffset.
+            */
+            MYODBCDbgReturn( getResult()->doPrev() );
+
+        case SQL_FETCH_RELATIVE:
+            /*!
+                \internal ODBC RULE
+
+                Return the rowset FetchOffset from the start of the current rowset.
+            */
+            {
+            }
+            break;
+
+        case SQL_FETCH_ABSOLUTE:
+            /*!
+                \internal ODBC RULE
+
+                Return the rowset starting at row FetchOffset.
+            */
+            {
+            }
+            break;
+
+        case SQL_FETCH_FIRST:
+            /*!
+                \internal ODBC RULE
+
+                Return the first rowset in the result set. SQLFetchScroll ignores the
value of FetchOffset.
+            */
+            MYODBCDbgReturn( getResult()->doFirst() );
+
+        case SQL_FETCH_LAST:
+            /*!
+                \internal ODBC RULE
+
+                Return the last complete rowset in the result set. SQLFetchScroll ignores
the value of FetchOffset.
+            */
+            MYODBCDbgReturn( getResult()->doLast() );
+
+        case SQL_FETCH_BOOKMARK:
+            /*!
+                \internal ODBC RULE
+
+                Return the rowset FetchOffset rows from the bookmark specified by the
SQL_ATTR_FETCH_BOOKMARK_PTR 
+                statement attribute.
+            */
+            {
+            }
+            break;
+
+        default:
+            /*!
+                \internal ODBC RULE (DM)
+
+                The value specified for the argument FetchOrientation was invalid.
+            */
+            MYODBCDbgReturn( getDiagnostic()->doAppend( MDiagnostic::DIA_HY106 ) );
+    }
+
+    MYODBCDbgReturn( getDiagnostic()->doAppend( MDiagnostic::DIA_HY000, 0, QString(
"Control reached unexpected place %1:%2" ).arg( __FILE__ ).arg( __LINE__ ) ) );
 }
 
 SQLRETURN MStatement::doForeignKeys( SQLWCHAR *psPKCatalog, SQLSMALLINT nLength1,
SQLWCHAR *psPKSchema, SQLSMALLINT nLength2, SQLWCHAR *psPKTable, SQLSMALLINT nLength3,
SQLWCHAR *psFKCatalog, SQLSMALLINT nLength4, SQLWCHAR *psFKSchema, SQLSMALLINT nLength5,
SQLWCHAR *psFKTable, SQLSMALLINT nLength6 )
@@ -5725,6 +5890,13 @@
     MYODBCDbgReturn3( "%s", stringCursorName );
 }
 
+SQLUSMALLINT MStatement::getPos()
+{
+    MYODBCDbgEnter();
+
+    MYODBCDbgReturn3( "%d", nPos );
+}
+
 MDescriptor *MStatement::getAppParamDesc()
 {
     MYODBCDbgEnter();
@@ -6009,6 +6181,7 @@
             setState( STATE_S0 );
             break;
 
+            /* unwind prepare... */
         case STATE_S2:
         case STATE_S3:
             {
@@ -6030,6 +6203,7 @@
             }
             break;
 
+            /* unwind execute... */
         case STATE_S4:
         case STATE_S5:
         case STATE_S6:
@@ -6064,6 +6238,7 @@
                     if ( pCommands->getCommand()->isResultSetPossible() )
                         nState = STATE_S3; // we will have a resultset
                 }
+                nPos = 1;
                 setState( nState );
             }
             break;

Modified: trunk/MYSQLPlus/include/MStatement.h
===================================================================
--- trunk/MYSQLPlus/include/MStatement.h	2006-08-17 06:02:08 UTC (rev 491)
+++ trunk/MYSQLPlus/include/MStatement.h	2006-08-18 06:03:26 UTC (rev 492)
@@ -132,10 +132,11 @@
     MConnection *   getConnection();                
     MCommands *     getCommands();
     MDiagnostic *   getDiagnostic();
-
     MDescriptor*    getAppParamDescOrig();          /*!< Original app param desc.     
                                     */ 
     MDescriptor*    getAppRowDescOrig();            /*!< Original app row desc.       
                                     */ 
     QString         getCursorName();                /*!< cursor name; 0-1 per
statement and connection unique               */
+    SQLUSMALLINT    getPos();                       /*!< Pos in rowset.               
                                     */
+
     MDescriptor*    getAppParamDesc();              /*!< SQL_ATTR_APP_PARAM_DESC      
                                     */
     MDescriptor*    getAppRowDesc();                /*!< SQL_ATTR_APP_ROW_DESC        
                                     */
     SQLUINTEGER     getAsyncEnable();               /*!< SQL_ATTR_ASYNC_ENABLE        
                                     */
@@ -185,6 +186,7 @@
     MDescriptor *   pAppRowDescOrig;        /*!< Original app row desc.               
                         */
     QString         stringCursorName;       /*!< cursor name - used by pos
update/delete (WHERE CURRENT OF name)*/
     BOOLEAN         bImplicitPrepare;       /*!< true if prepare done implicitly ie
doExecDirect or doTables etc*/
+    SQLUSMALLINT    nPos;                   /*!< current row within
row-set/block-cursor                        */
     MDescriptor *   pAppParamDesc;          /*!< SQL_ATTR_APP_PARAM_DESC              
                         */
     MDescriptor *   pAppRowDesc;            /*!< SQL_ATTR_APP_ROW_DESC                
                         */
     SQLUINTEGER     nAsyncEnable;           /*!< SQL_ATTR_ASYNC_ENABLE                
                         */

Thread
Connector/ODBC 5 commit: r492 - in trunk: MYODBCDriver/MYODBCDriverLib MYSQLPlus/MYSQLPlusLib MYSQLPlus/includepharvey18 Aug