internal OletxCommittableTransaction CreateTransaction( TransactionOptions properties ) { OletxCommittableTransaction tx = null; RealOletxTransaction realTransaction = null; ITransactionShim transactionShim = null; Guid txIdentifier = Guid.Empty; OutcomeEnlistment outcomeEnlistment = null; // Demand the distributed transation permission to create one of // these. DistributedTransactionPermission txPerm = new DistributedTransactionPermission(PermissionState.Unrestricted); txPerm.Demand(); TransactionManager.ValidateIsolationLevel(properties.IsolationLevel); // Never create a transaction with an IsolationLevel of Unspecified. if (IsolationLevel.Unspecified == properties.IsolationLevel) { properties.IsolationLevel = configuredTransactionOptions.IsolationLevel; } properties.Timeout = TransactionManager.ValidateTimeout(properties.Timeout); this.dtcTransactionManagerLock.AcquireReaderLock(-1); try { // OletxTransactionIsolationLevel oletxIsoLevel = OletxTransactionManager.ConvertIsolationLevel(properties.IsolationLevel); UInt32 oletxTimeout = DtcTransactionManager.AdjustTimeout(properties.Timeout); outcomeEnlistment = new OutcomeEnlistment(); IntPtr outcomeEnlistmentHandle = IntPtr.Zero; RuntimeHelpers.PrepareConstrainedRegions(); try { outcomeEnlistmentHandle = HandleTable.AllocHandle(outcomeEnlistment); dtcTransactionManager.ProxyShimFactory.BeginTransaction( oletxTimeout, oletxIsoLevel, outcomeEnlistmentHandle, out txIdentifier, out transactionShim ); } catch (COMException ex) { OletxTransactionManager.ProxyException(ex); throw; } finally { if (transactionShim == null && outcomeEnlistmentHandle != IntPtr.Zero) { HandleTable.FreeHandle(outcomeEnlistmentHandle); } } realTransaction = new RealOletxTransaction( this, transactionShim, outcomeEnlistment, txIdentifier, oletxIsoLevel, true ); tx = new OletxCommittableTransaction(realTransaction); if (DiagnosticTrace.Information) { TransactionCreatedTraceRecord.Trace(SR.GetString(SR.TraceSourceOletx), tx.TransactionTraceId ); } } finally { this.dtcTransactionManagerLock.ReleaseReaderLock(); } return(tx); }
internal static void DemandTransactionPermissions(ServiceEndpoint endpoint, string operationName) { bool transactionFlow = false; bool flowOptionAllowed = false; if (endpoint.Binding is NetMsmqBinding) { NetMsmqBinding msmqBinding = endpoint.Binding as NetMsmqBinding; if (msmqBinding.Durable) { transactionFlow = true; if (Transaction.Current != null) { flowOptionAllowed = true; } } } if (endpoint.Binding is NetTcpBinding) { NetTcpBinding tcpBinding = endpoint.Binding as NetTcpBinding; transactionFlow = tcpBinding.TransactionFlow; } if (endpoint.Binding is NetNamedPipeBinding) { NetNamedPipeBinding ipcBinding = endpoint.Binding as NetNamedPipeBinding; transactionFlow = ipcBinding.TransactionFlow; } if (endpoint.Binding is WSHttpBinding) { WSHttpBinding wsBinding = endpoint.Binding as WSHttpBinding; transactionFlow = wsBinding.TransactionFlow; } if (endpoint.Binding is WSDualHttpBinding) { WSDualHttpBinding wsDualBinding = endpoint.Binding as WSDualHttpBinding; transactionFlow = wsDualBinding.TransactionFlow; } if (transactionFlow) { if (Transaction.Current != null) { //If operationName is null, then at least one operation needs to allow flow foreach (OperationDescription operation in endpoint.Contract.Operations) { string name = operationName ?? operation.Name; if (name != operation.Name) { continue; } foreach (IOperationBehavior behavior in operation.Behaviors) { if (behavior is TransactionFlowAttribute) { TransactionFlowAttribute attribute = behavior as TransactionFlowAttribute; if (attribute.Transactions != TransactionFlowOption.NotAllowed) { flowOptionAllowed = true; break; } } } if (flowOptionAllowed) { break; } } if (flowOptionAllowed) { IPermission distributedTransactionPermission = new DistributedTransactionPermission(PermissionState.Unrestricted); distributedTransactionPermission.Demand(); } } } }
internal OletxCommittableTransaction CreateTransaction( TransactionOptions properties ) { OletxCommittableTransaction tx = null; RealOletxTransaction realTransaction = null; ITransactionShim transactionShim = null; Guid txIdentifier = Guid.Empty; OutcomeEnlistment outcomeEnlistment = null; // Demand the distributed transation permission to create one of // these. DistributedTransactionPermission txPerm = new DistributedTransactionPermission( PermissionState.Unrestricted ); txPerm.Demand(); TransactionManager.ValidateIsolationLevel( properties.IsolationLevel ); // Never create a transaction with an IsolationLevel of Unspecified. if ( IsolationLevel.Unspecified == properties.IsolationLevel ) { properties.IsolationLevel = configuredTransactionOptions.IsolationLevel; } properties.Timeout = TransactionManager.ValidateTimeout( properties.Timeout ); this.dtcTransactionManagerLock.AcquireReaderLock( -1 ); try { // OletxTransactionIsolationLevel oletxIsoLevel = OletxTransactionManager.ConvertIsolationLevel( properties.IsolationLevel ); UInt32 oletxTimeout = DtcTransactionManager.AdjustTimeout( properties.Timeout ); outcomeEnlistment = new OutcomeEnlistment(); IntPtr outcomeEnlistmentHandle = IntPtr.Zero; RuntimeHelpers.PrepareConstrainedRegions(); try { outcomeEnlistmentHandle = HandleTable.AllocHandle( outcomeEnlistment ); dtcTransactionManager.ProxyShimFactory.BeginTransaction( oletxTimeout, oletxIsoLevel, outcomeEnlistmentHandle, out txIdentifier, out transactionShim ); } catch ( COMException ex ) { OletxTransactionManager.ProxyException( ex ); throw; } finally { if ( transactionShim == null && outcomeEnlistmentHandle != IntPtr.Zero ) { HandleTable.FreeHandle( outcomeEnlistmentHandle ); } } realTransaction = new RealOletxTransaction( this, transactionShim, outcomeEnlistment, txIdentifier, oletxIsoLevel, true ); tx = new OletxCommittableTransaction( realTransaction ); if ( DiagnosticTrace.Information ) { TransactionCreatedTraceRecord.Trace( SR.GetString( SR.TraceSourceOletx ), tx.TransactionTraceId ); } } finally { this.dtcTransactionManagerLock.ReleaseReaderLock(); } return tx; }