public void Close() { // this method will actually close the internal connection and dipose it, this // should only be called by a non-pooled sqlconnection, or by the object pooler // when it deems an object should be destroyed // it's possible to have a connection finalizer, internal connection finalizer, // and the object pool destructor calling this method at the same time, so // we need to provide some synchronization if (_fConnectionOpen) { if (Interlocked.CompareExchange(ref _lock, 1, 0) == 0) { if (_fConnectionOpen) { if (_fIsPooled) { // PerfCounters - on close of pooled connection, decrement count SQL.DecrementPooledConnectionCount(); } try { try { _parser.Disconnect(); // UNDONE: GC.SuppressFinalize causes a permission demand? //GC.SuppressFinalize(_parser); } finally { // _connectionWeakRef= // close will always close, even if exception is thrown // remember to null out any object references _connectionWeakRef = null; _connectionOptions = null; _parser = null; _loginAck = null; _fConnectionOpen = false; // mark internal connection as closed _fUsableState = false; // mark internal connection as unusable _pool = null; _dtcAddress = null; _transactionGuid = Guid.Empty; _transactionExport = null; // always release the lock //Interlocked.CompareExchange(ref _lock, 0, 1); _lock = 0; } } catch { // MDAC 80973 throw; } } else { // release lock in case where connection already closed //Interlocked.CompareExchange(ref _lock, 0, 1); _lock = 0; } } } }
private void EnlistNonNullDistributedTransaction(ITransaction transaction) { //if (AdapterSwitches.SqlPooling.TraceVerbose) // Debug.WriteLine("SqlInternalConnection.EnlistDistributedTransaction(): Enlisting connection in distributed transaction..."); if (null == _dtcAddress) { _dtcAddress = _parser.GetDTCAddress(_connectionOptions.ConnectTimeout); } Debug.Assert(_dtcAddress != null, "SqlInternalConnection.EnlistDistributedTransaction(): dtcAddress null, error #1"); byte[] cookie = null; int length = 0; UnsafeNativeMethods.ITransactionExport transactionExport = null; if (null != _transactionExport) { transactionExport = _transactionExport.GetITransactionExport(); } // if the call for the cookie fails, re-obtain the DTCAddress and recall the function if (!Transaction.GetTransactionCookie(_dtcAddress, transaction, ref transactionExport, ref cookie, ref length)) { _dtcAddress = _parser.GetDTCAddress(_connectionOptions.ConnectTimeout); Debug.Assert(_dtcAddress != null, "SqlInternalConnection.Activate(): dtcAddress null, error #2"); if (!Transaction.GetTransactionCookie(_dtcAddress, transaction, ref transactionExport, ref cookie, ref length)) { throw SQL.TransactionEnlistmentError(); } } if (null != transactionExport) { _transactionExport = new TransactionExportWrapper(transactionExport); } else { _transactionExport = null; } // send cookie to server to finish enlistment _parser.PropagateDistributedTransaction(cookie, length, _connectionOptions.ConnectTimeout); }