示例#1
0
        internal SqlTransaction(SqlInternalConnection internalConnection, SqlConnection con,
                                IsolationLevel iso, SqlInternalTransaction internalTransaction)
        {
            SqlConnection.VerifyExecutePermission();

            _isolationLevel = iso;
            _connection     = con;

            if (internalTransaction == null)
            {
                _internalTransaction = new SqlInternalTransaction(internalConnection, TransactionType.LocalFromAPI, this);
            }
            else
            {
                Debug.Assert(internalConnection.CurrentTransaction == internalTransaction, "Unexpected Parser.CurrentTransaction state!");
                _internalTransaction = internalTransaction;
                _internalTransaction.InitParent(this);
            }
        }
示例#2
0
        override public void EnlistTransaction(SysTx.Transaction transaction)
        {
            SqlConnection.VerifyExecutePermission();

            ValidateConnectionForExecute(null);

            // If a connection has a local transaction outstanding and you try
            // to enlist in a DTC transaction, SQL Server will rollback the
            // local transaction and then do the enlist (7.0 and 2000).  So, if
            // the user tries to do this, throw.
            if (HasLocalTransaction)
            {
                throw ADP.LocalTransactionPresent();
            }

            if (null != transaction && transaction.Equals(EnlistedTransaction))
            {
                // No-op if this is the current transaction
                return;
            }

            // If a connection is already enlisted in a DTC transaction and you
            // try to enlist in another one, in 7.0 the existing DTC transaction
            // would roll back and then the connection would enlist in the new
            // one. In SQL 2000 & 2005, when you enlist in a DTC transaction
            // while the connection is already enlisted in a DTC transaction,
            // the connection simply switches enlistments.  Regardless, simply
            // enlist in the user specified distributed transaction.  This
            // behavior matches OLEDB and ODBC.

            TdsParser bestEffortCleanupTarget = null;

            RuntimeHelpers.PrepareConstrainedRegions();
            try
            {
#if DEBUG
                TdsParser.ReliabilitySection tdsReliabilitySection = new TdsParser.ReliabilitySection();

                RuntimeHelpers.PrepareConstrainedRegions();
                try
                {
                    tdsReliabilitySection.Start();
#else
                {
#endif //DEBUG
                    bestEffortCleanupTarget = SqlInternalConnection.GetBestEffortCleanupTarget(Connection);
                    Enlist(transaction);
                }
#if DEBUG
                finally
                {
                    tdsReliabilitySection.Stop();
                }
#endif //DEBUG
            }
            catch (System.OutOfMemoryException e)
            {
                Connection.Abort(e);
                throw;
            }
            catch (System.StackOverflowException e)
            {
                Connection.Abort(e);
                throw;
            }
            catch (System.Threading.ThreadAbortException e)
            {
                Connection.Abort(e);
                SqlInternalConnection.BestEffortCleanup(bestEffortCleanupTarget);
                throw;
            }
        }