Author: gert
Date: 2007-10-19 12:04:39 -0400 (Fri, 19 Oct 2007)
New Revision: 87835

Modified:
   trunk/mcs/class/System.Data/System.Data.Common/ChangeLog
   trunk/mcs/class/System.Data/System.Data.Common/DbTransaction.cs
   trunk/mcs/class/System.Data/System.Data.Common/ExceptionHelper.cs
   trunk/mcs/class/System.Data/System.Data.Odbc/ChangeLog
   trunk/mcs/class/System.Data/System.Data.Odbc/OdbcTransaction.cs
   trunk/mcs/class/System.Data/System.Data.OleDb/ChangeLog
   trunk/mcs/class/System.Data/System.Data.OleDb/OleDbTransaction.cs
   trunk/mcs/class/System.Data/System.Data.SqlClient/ChangeLog
   trunk/mcs/class/System.Data/System.Data.SqlClient/SqlTransaction.cs
Log:
* DbTransaction.cs: Do not perform a rollback in Dispose (bool).
Leaves it up to deriving classes to override Dispose (bool) and
perform a rollback if necessary. Fixes bug #325397. Code formatting.
* ExceptionHelper.cs: Added TransactionNotUsable method that constructs
an InvalidOperationException to be thrown by IDbTransaction
implementations when the transaction is no longer open.
* OdbcTransaction.cs: Keep state of the transaction, and update it
when performing commit or rollback. In Dispose (bool), only perform
a rollback if transaction was not committed or rollback before.
In Commit and Rollback, throw an InvalidOperationException if
transaction is no longer open.
* SqlTransaction.cs: Avoid unnecessary initialization. Remove
isRolledBack since its essentially the same as isOpen. Use
ExceptionHelper.TransactionNotUsable instead of duplicating code.
On 2.0 profile, ignore call to Rollback when transaction was already
disposed.
* OleDbTransaction.cs: Keep track of whether transaction is open and
whether it's disposed. In Commit an Rollback, throw an IOE if the
transaction is no longer open. In Dispose (bool), perform a rollback
if the transaction is still open.


Modified: trunk/mcs/class/System.Data/System.Data.Common/ChangeLog
===================================================================
--- trunk/mcs/class/System.Data/System.Data.Common/ChangeLog    2007-10-19 
15:59:13 UTC (rev 87834)
+++ trunk/mcs/class/System.Data/System.Data.Common/ChangeLog    2007-10-19 
16:04:39 UTC (rev 87835)
@@ -1,3 +1,12 @@
+2007-10-19  Gert Driesen  <[EMAIL PROTECTED]>
+
+       * DbTransaction.cs: Do not perform a rollback in Dispose (bool).
+       Leaves it up to deriving classes to override Dispose (bool) and
+       perform a rollback if necessary. Fixes bug #325397. Code formatting.
+       * ExceptionHelper.cs: Added TransactionNotUsable method that constructs
+       an InvalidOperationException to be thrown by IDbTransaction
+       implementations when the transaction is no longer open.
+
 2007-09-27  Nagappan A <[EMAIL PROTECTED]> 
 
        * DbDataAdapter.cs: Added MonoTODO in appropriate place.

Modified: trunk/mcs/class/System.Data/System.Data.Common/DbTransaction.cs
===================================================================
--- trunk/mcs/class/System.Data/System.Data.Common/DbTransaction.cs     
2007-10-19 15:59:13 UTC (rev 87834)
+++ trunk/mcs/class/System.Data/System.Data.Common/DbTransaction.cs     
2007-10-19 16:04:39 UTC (rev 87835)
@@ -6,8 +6,6 @@
 //
 // Copyright (C) Tim Coleman, 2003
 //
-
-//
 // Copyright (C) 2004 Novell, Inc (http://www.novell.com)
 //
 // Permission is hereby granted, free of charge, to any person obtaining
@@ -32,7 +30,8 @@
 
 #if NET_2_0 || TARGET_JVM
 
-namespace System.Data.Common {
+namespace System.Data.Common
+{
        public abstract class DbTransaction : MarshalByRefObject, 
IDbTransaction, IDisposable
        {
                #region Constructors
@@ -49,19 +48,24 @@
                        get { return DbConnection; }
                }
 
-               protected abstract DbConnection DbConnection { get; }
+               protected abstract DbConnection DbConnection {
+                       get;
+               }
 
                IDbConnection IDbTransaction.Connection {
                        get { return (IDbConnection) Connection; }
                }
 
-               public abstract IsolationLevel IsolationLevel { get; }
+               public abstract IsolationLevel IsolationLevel {
+                       get;
+               }
 
                #endregion // Properties
 
                #region Methods
 
                public abstract void Commit ();
+
                public abstract void Rollback ();
 
                public void Dispose ()
@@ -71,8 +75,6 @@
 
                protected virtual void Dispose (bool disposing)
                {
-                       if (disposing)
-                               Rollback();
                }
 
                #endregion // Methods

Modified: trunk/mcs/class/System.Data/System.Data.Common/ExceptionHelper.cs
===================================================================
--- trunk/mcs/class/System.Data/System.Data.Common/ExceptionHelper.cs   
2007-10-19 15:59:13 UTC (rev 87834)
+++ trunk/mcs/class/System.Data/System.Data.Common/ExceptionHelper.cs   
2007-10-19 16:04:39 UTC (rev 87835)
@@ -6,11 +6,12 @@
 //
 
 using System;
+using System.Globalization;
 
 namespace System.Data.Common
 {
        internal sealed class ExceptionHelper
-       {       
+       {
                internal static ArgumentException InvalidSizeValue (int value)
                {
                        string [] args = new string [] {value.ToString ()};
@@ -23,7 +24,7 @@
                }
 
                internal static ArgumentOutOfRangeException 
InvalidDataRowVersion (DataRowVersion value)
-               {                       
+               {
                        object [] args = new object [] { "DataRowVersion", 
value.ToString () } ;
                        return new ArgumentOutOfRangeException  
(GetExceptionMessage ("{0}: Invalid DataRow Version enumeration value: 
{1}",args));
                }
@@ -90,6 +91,14 @@
                        return new InvalidOperationException  
(GetExceptionMessage ("Execute requires the command to have a transaction 
object when the connection assigned to the command is in a pending local 
transaction.  The Transaction property of the command has not been 
initialized."));
                }
 
+               internal static InvalidOperationException TransactionNotUsable 
(Type type)
+               {
+                       return new InvalidOperationException (string.Format (
+                               CultureInfo.InvariantCulture,
+                               "This {0} has completed; it is no longer 
usable.",
+                               type.Name));
+               }
+
                internal static InvalidOperationException 
ParametersNotInitialized (int parameterPosition,string parameterName,string 
parameterType)
                {
                        object [] args = new object [] { parameterPosition, 
parameterName, parameterType };
@@ -198,15 +207,14 @@
                {
                        if ((args == null) || (args.Length == 0)) {
                                return exceptionMessage;
-                       }
-                       else {
+                       } else {
                                return String.Format (exceptionMessage,args);
                        }
                }
 
                internal static string GetExceptionMessage (string 
exceptionMessage)
                {
-                       return GetExceptionMessage (exceptionMessage,null);
+                       return GetExceptionMessage (exceptionMessage, null);
                }
        }
 }


Property changes on: 
trunk/mcs/class/System.Data/System.Data.Common/ExceptionHelper.cs
___________________________________________________________________
Name: svn:eol-style
   + CRLF

Modified: trunk/mcs/class/System.Data/System.Data.Odbc/ChangeLog
===================================================================
--- trunk/mcs/class/System.Data/System.Data.Odbc/ChangeLog      2007-10-19 
15:59:13 UTC (rev 87834)
+++ trunk/mcs/class/System.Data/System.Data.Odbc/ChangeLog      2007-10-19 
16:04:39 UTC (rev 87835)
@@ -1,5 +1,13 @@
 2007-10-19  Gert Driesen  <[EMAIL PROTECTED]>
 
+       * OdbcTransaction.cs: Keep state of the transaction, and update it
+       when performing commit or rollback. In Dispose (bool), only perform
+       a rollback if transaction was not committed or rollback before.
+       In Commit and Rollback, throw an InvalidOperationException if
+       transaction is no longer open.
+
+2007-10-19  Gert Driesen  <[EMAIL PROTECTED]>
+
        * OdbcTransaction.cs: Use OdbcIsolationLevel enum value instead of
        magic numbers. For Snapshot isolation level, the attribute
        SQL_COPT_SS_TXN_ISOLATION must be used instead. When isolation level

Modified: trunk/mcs/class/System.Data/System.Data.Odbc/OdbcTransaction.cs
===================================================================
--- trunk/mcs/class/System.Data/System.Data.Odbc/OdbcTransaction.cs     
2007-10-19 15:59:13 UTC (rev 87834)
+++ trunk/mcs/class/System.Data/System.Data.Odbc/OdbcTransaction.cs     
2007-10-19 16:04:39 UTC (rev 87835)
@@ -29,12 +29,9 @@
 //
 using System;
 using System.Data;
+using System.Data.Common;
 using System.Globalization;
 
-#if NET_2_0
-using System.Data.Common;
-#endif
-
 namespace System.Data.Odbc
 {
 #if NET_2_0
@@ -46,6 +43,7 @@
                private bool disposed;
                private OdbcConnection connection;
                private IsolationLevel isolationlevel;
+               private bool isOpen;
 
                internal OdbcTransaction (OdbcConnection conn, IsolationLevel 
isolationlevel)
                {
@@ -122,6 +120,7 @@
                        }
                        this.isolationlevel = isolationlevel;
                        connection = conn;
+                       isOpen = true;
                }
 
                // Set Auto-commit (102) connection attribute
@@ -188,7 +187,7 @@
                void Dispose (bool disposing)
                {
                        if (!disposed) {
-                               if (disposing)
+                               if (disposing && isOpen)
                                        Rollback ();
                                disposed = true;
                        }
@@ -210,12 +209,16 @@
 #endif //NET_2_0
                void Commit ()
                {
+                       if (!isOpen)
+                               throw ExceptionHelper.TransactionNotUsable 
(GetType ());
+
                        if (connection.transaction == this) {
                                OdbcReturn ret = libodbc.SQLEndTran ((short) 
OdbcHandleType.Dbc, connection.hDbc, 0);
                                if (ret != OdbcReturn.Success && ret != 
OdbcReturn.SuccessWithInfo)
                                        throw new OdbcException (new OdbcError 
("SQLEndTran", OdbcHandleType.Dbc, connection.hDbc));
                                SetAutoCommit (connection, true); // restore 
default auto-commit
                                connection.transaction = null;
+                               isOpen = false;
                        } else
                                throw new InvalidOperationException ();
                }
@@ -226,12 +229,16 @@
 #endif //NET_2_0
                void Rollback()
                {
+                       if (!isOpen)
+                               throw ExceptionHelper.TransactionNotUsable 
(GetType ());
+
                        if (connection.transaction == this) {
                                OdbcReturn ret = libodbc.SQLEndTran ((short) 
OdbcHandleType.Dbc, connection.hDbc, 1);
                                if (ret!=OdbcReturn.Success && ret != 
OdbcReturn.SuccessWithInfo)
                                        throw new OdbcException (new OdbcError 
("SQLEndTran", OdbcHandleType.Dbc, connection.hDbc));
                                SetAutoCommit (connection, true);    // restore 
default auto-commit
                                connection.transaction = null;
+                               isOpen = false;
                        } else
                                throw new InvalidOperationException ();
                }

Modified: trunk/mcs/class/System.Data/System.Data.OleDb/ChangeLog
===================================================================
--- trunk/mcs/class/System.Data/System.Data.OleDb/ChangeLog     2007-10-19 
15:59:13 UTC (rev 87834)
+++ trunk/mcs/class/System.Data/System.Data.OleDb/ChangeLog     2007-10-19 
16:04:39 UTC (rev 87835)
@@ -1,3 +1,10 @@
+2007-10-19  Gert Driesen  <[EMAIL PROTECTED]>
+
+       * OleDbTransaction.cs: Keep track of whether transaction is open and
+       whether it's disposed. In Commit an Rollback, throw an IOE if the
+       transaction is no longer open. In Dispose (bool), perform a rollback
+       if the transaction is still open.
+
 2007-10-19  Nagappan <[EMAIL PROTECTED]> 
 
        * OleDbCommandBuilder.cs: Implemented ApplyParameterInfo, Dispose,

Modified: trunk/mcs/class/System.Data/System.Data.OleDb/OleDbTransaction.cs
===================================================================
--- trunk/mcs/class/System.Data/System.Data.OleDb/OleDbTransaction.cs   
2007-10-19 15:59:13 UTC (rev 87834)
+++ trunk/mcs/class/System.Data/System.Data.OleDb/OleDbTransaction.cs   
2007-10-19 16:04:39 UTC (rev 87835)
@@ -41,9 +41,11 @@
        {
                #region Fields
 
+               bool disposed;
                OleDbConnection connection;
                IntPtr gdaTransaction;
                int depth;
+               bool isOpen;
 
                #endregion // Fields
 
@@ -85,6 +87,7 @@
                        }
                        
                        libgda.gda_connection_begin_transaction 
(connection.GdaConnection, gdaTransaction);
+                       isOpen = true;
                }
 
                internal OleDbTransaction (OleDbConnection connection, 
IsolationLevel isolevel) 
@@ -155,9 +158,13 @@
 #endif
                void Commit ()
                {
+                       if (!isOpen)
+                               throw ExceptionHelper.TransactionNotUsable 
(GetType ());
+
                        if (!libgda.gda_connection_commit_transaction 
(connection.GdaConnection,
-                                                                               
                                        gdaTransaction))
+                               gdaTransaction))
                                throw new InvalidOperationException ();
+                       isOpen = false;
                }
 
 #if ONLY_1_1
@@ -169,16 +176,25 @@
 #endif
 
 #if NET_2_0
-               protected override void Dispose (bool disposing)
+               protected override
+#endif
+               void Dispose (bool disposing)
                {
+                       if (!disposed) {
+                               if (disposing && isOpen)
+                                       Rollback ();
+                               disposed = true;
+                       }
+
+#if NET_2_0
                        base.Dispose (disposing);
+#endif
                }
-#else
+
                void IDisposable.Dispose ()
                {
-                       GC.SuppressFinalize (this);
+                       Dispose (true);
                }
-#endif
 
                public
 #if NET_2_0
@@ -186,9 +202,13 @@
 #endif
                void Rollback ()
                {
+                       if (!isOpen)
+                               throw ExceptionHelper.TransactionNotUsable 
(GetType ());
+
                        if (!libgda.gda_connection_rollback_transaction 
(connection.GdaConnection,
-                                                                               
                                                gdaTransaction))
+                               gdaTransaction))
                                throw new InvalidOperationException ();
+                       isOpen = false;
                }
 
                #endregion // Methods

Modified: trunk/mcs/class/System.Data/System.Data.SqlClient/ChangeLog
===================================================================
--- trunk/mcs/class/System.Data/System.Data.SqlClient/ChangeLog 2007-10-19 
15:59:13 UTC (rev 87834)
+++ trunk/mcs/class/System.Data/System.Data.SqlClient/ChangeLog 2007-10-19 
16:04:39 UTC (rev 87835)
@@ -1,3 +1,11 @@
+2007-10-19  Gert Driesen  <[EMAIL PROTECTED]>
+
+       * SqlTransaction.cs: Avoid unnecessary initialization. Remove 
+       isRolledBack since its essentially the same as isOpen. Use
+       ExceptionHelper.TransactionNotUsable instead of duplicating code.
+       On 2.0 profile, ignore call to Rollback when transaction was already
+       disposed.
+
 2007-10-18  Gert Driesen  <[EMAIL PROTECTED]>
 
        * SqlConnection.cs: Avoid unnecessary initialization. Use string.Empty

Modified: trunk/mcs/class/System.Data/System.Data.SqlClient/SqlTransaction.cs
===================================================================
--- trunk/mcs/class/System.Data/System.Data.SqlClient/SqlTransaction.cs 
2007-10-19 15:59:13 UTC (rev 87834)
+++ trunk/mcs/class/System.Data/System.Data.SqlClient/SqlTransaction.cs 
2007-10-19 16:04:39 UTC (rev 87835)
@@ -44,11 +44,10 @@
        {
                #region Fields
 
-               bool disposed = false;
+               bool disposed;
                SqlConnection connection;
                IsolationLevel isolationLevel;
                bool isOpen;
-               bool isRolledBack = false;
 
                #endregion
 
@@ -59,7 +58,6 @@
                        this.connection = connection;
                        this.isolationLevel = isolevel;
                        isOpen = true;
-                       isRolledBack = false;
                }
 
                #endregion // Constructors
@@ -101,7 +99,8 @@
                void Commit ()
                {
                        if (!isOpen)
-                               throw new InvalidOperationException ("The 
Transaction was not open.");
+                               throw ExceptionHelper.TransactionNotUsable 
(GetType ());
+
                        connection.Tds.Execute ("COMMIT TRANSACTION");
                        connection.Transaction = null;
                        isOpen = false;
@@ -112,7 +111,7 @@
 #endif
                void Dispose (bool disposing)
                {
-                       if (!disposed)  {
+                       if (!disposed) {
                                if (disposing) {
                                        if (isOpen) // in case it is called in 
the dispose of the class, then the isOpen is already false 
                                                Rollback ();
@@ -133,29 +132,32 @@
 #if NET_2_0
                override
 #endif // NET_2_0
-        void Rollback ()
+               void Rollback ()
                {
                        Rollback (String.Empty);
                }
 
                public void Rollback (string transactionName)
                {
-                       if (!isRolledBack) {
-                               if (!isOpen)
-                                       throw new InvalidOperationException 
("The Transaction was not open.");
-                               connection.Tds.Execute (String.Format ("IF 
@@TRANCOUNT > 0 ROLLBACK TRANSACTION {0}",
-                                                                      
transactionName));
-                               isRolledBack = true;
-                               isOpen = false;
-                               connection.Transaction = null;
-                               connection = null;
-                       }
+#if NET_2_0
+                       if (disposed)
+                               return;
+#endif
+
+                       if (!isOpen)
+                               throw ExceptionHelper.TransactionNotUsable 
(GetType ());
+
+                       connection.Tds.Execute (String.Format ("IF @@TRANCOUNT 
> 0 ROLLBACK TRANSACTION {0}",
+                                                               
transactionName));
+                       isOpen = false;
+                       connection.Transaction = null;
+                       connection = null;
                }
 
                public void Save (string savePointName)
                {
                        if (!isOpen)
-                               throw new InvalidOperationException ("The 
Transaction was not open.");
+                               throw ExceptionHelper.TransactionNotUsable 
(GetType ());
                        connection.Tds.Execute (String.Format ("SAVE 
TRANSACTION {0}", savePointName));
                }
 

_______________________________________________
Mono-patches maillist  -  [email protected]
http://lists.ximian.com/mailman/listinfo/mono-patches

Reply via email to