Code:
/ 4.0 / 4.0 / DEVDIV_TFS / Dev10 / Releases / RTMRel / ndp / cdf / src / WF / RunTime / System / Activities / Statements / InteropEnvironment.cs / 1305376 / InteropEnvironment.cs
//---------------------------------------------------------------- // Copyright (c) Microsoft Corporation. All rights reserved. //--------------------------------------------------------------- namespace System.Activities.Statements { using System.Activities; using System.Activities.Tracking; using System.Collections.Generic; using System.Collections.ObjectModel; using System.Diagnostics; using System.Reflection; using System.Runtime.Serialization; using System.Transactions; using System.Workflow.Runtime; using System.Workflow.Runtime.Tracking; using System.Runtime; using System.Globalization; class InteropEnvironment : IDisposable, IServiceProvider { static readonly ReadOnlyCollectionemptyList = new ReadOnlyCollection (new IComparable[] { }); static MethodInfo getServiceMethod = typeof(NativeActivityContext).GetMethod("GetExtension"); NativeActivityContext nativeActivityContext; BookmarkCallback bookmarkCallback; bool disposed; bool completed; bool canceled; InteropExecutor executor; IEnumerable initialBookmarks; Exception uncaughtException; Transaction transaction; public InteropEnvironment(InteropExecutor interopExecutor, NativeActivityContext nativeActivityContext, BookmarkCallback bookmarkCallback, Interop activity, Transaction transaction) { //setup environment; this.executor = interopExecutor; this.nativeActivityContext = nativeActivityContext; this.Activity = activity; this.executor.ServiceProvider = this; this.bookmarkCallback = bookmarkCallback; this.transaction = transaction; OnEnter(); } public Interop Activity { get; set; } void IDisposable.Dispose() { if (!this.disposed) { OnExit(); this.disposed = true; } } public void Execute(System.Workflow.ComponentModel.Activity definition, NativeActivityContext context) { Debug.Assert(!disposed, "Cannot access disposed object"); try { this.executor.Initialize(definition, this.Activity.GetInputArgumentValues(context), this.Activity.HasNameCollision); ProcessExecutionStatus(this.executor.Execute()); } catch (Exception e) { this.uncaughtException = e; throw; } } public void Cancel() { Debug.Assert(!disposed, "Cannot access disposed object"); try { ProcessExecutionStatus(this.executor.Cancel()); this.canceled = true; } catch (Exception e) { this.uncaughtException = e; throw; } } public void EnqueueEvent(IComparable queueName, object item) { Debug.Assert(!disposed, "Cannot access disposed object"); try { ProcessExecutionStatus(this.executor.EnqueueEvent(queueName, item)); } catch (Exception e) { this.uncaughtException = e; throw; } } public void TrackActivityStatusChange(System.Workflow.ComponentModel.Activity activity, int eventCounter) { this.nativeActivityContext.Track( new InteropTrackingRecord(this.Activity.DisplayName, new ActivityTrackingRecord( activity.GetType(), activity.QualifiedName, activity.ContextGuid, activity.Parent == null ? Guid.Empty : activity.Parent.ContextGuid, activity.ExecutionStatus, DateTime.UtcNow, eventCounter, null ) ) ); } public void TrackData(System.Workflow.ComponentModel.Activity activity, int eventCounter, string key, object data) { this.nativeActivityContext.Track( new InteropTrackingRecord(this.Activity.DisplayName, new UserTrackingRecord( activity.GetType(), activity.QualifiedName, activity.ContextGuid, activity.Parent == null ? Guid.Empty : activity.Parent.ContextGuid, DateTime.UtcNow, eventCounter, key, data ) ) ); } public void Resume() { Debug.Assert(!disposed, "Cannot access disposed object"); try { ProcessExecutionStatus(this.executor.Resume()); } catch (Exception e) { this.uncaughtException = e; throw; } } // object IServiceProvider.GetService(Type serviceType) { Debug.Assert(!disposed, "Cannot access disposed object"); MethodInfo genericMethodInfo = getServiceMethod.MakeGenericMethod(serviceType); return genericMethodInfo.Invoke(this.nativeActivityContext, null); } public void Persist() { this.Activity.Persist(this.nativeActivityContext); } public void CreateTransaction(TransactionOptions transactionOptions) { this.Activity.CreateTransaction(this.nativeActivityContext, transactionOptions); } public void CommitTransaction() { this.Activity.CommitTransaction(this.nativeActivityContext); } public void AddResourceManager(VolatileResourceManager resourceManager) { this.Activity.AddResourceManager(this.nativeActivityContext,resourceManager); } //Called everytime on enter of interopenvironment. void OnEnter() { //Capture Current state of Queues in InteropEnvironment. this.initialBookmarks = this.executor.Queues; // This method sets up the ambient transaction for the current thread. // Since the runtime can execute us on different threads, // we have to set up the transaction scope everytime we enter the interop environment and clear it when we leave the environment. this.executor.SetAmbientTransactionAndServiceEnvironment(this.transaction); } //Called everytime we leave InteropEnvironment. void OnExit() { if (this.uncaughtException != null) { if (WorkflowExecutor.IsIrrecoverableException(this.uncaughtException)) { return; } } // This method clears the ambient transaction for the current thread. // Since the runtime can execute us on different threads, // we have to set up the transaction scope everytime we enter the interop environment and clear it when we leave the environment. this.executor.ClearAmbientTransactionAndServiceEnvironment(); //Capture Current state of Queues in InteropEnvironment. IEnumerable currentBookmarks = this.executor.Queues; //Set outparameters when completed or faulted. if (this.completed || this.uncaughtException != null) { this.Activity.OnClose(this.nativeActivityContext, this.uncaughtException); this.Activity.SetOutputArgumentValues( this.executor.Outputs, this.nativeActivityContext); this.nativeActivityContext.RemoveAllBookmarks(); this.executor.BookmarkQueueMap.Clear(); if (this.canceled) { this.nativeActivityContext.MarkCanceled(); } } else { //Find Differentials IList deletedBookmarks = new List (); foreach (IComparable value in this.initialBookmarks) { deletedBookmarks.Add(value); } IList newBookmarks = null; foreach (IComparable value in currentBookmarks) { if (!deletedBookmarks.Remove(value)) { if (newBookmarks == null) { newBookmarks = new List (); } newBookmarks.Add(value); } } if (newBookmarks != null) { // Create new Queues as Bookmark. foreach (IComparable bookmark in newBookmarks) { // Bookmark v2Bookmark = this.nativeActivityContext.CreateBookmark(bookmark.ToString(), this.bookmarkCallback, BookmarkOptions.MultipleResume); this.executor.BookmarkQueueMap.Add(v2Bookmark, bookmark); } } // Delete removed queues. foreach (IComparable bookmark in deletedBookmarks) { this.nativeActivityContext.RemoveBookmark(bookmark.ToString()); List bookmarksToRemove = new List (); foreach (KeyValuePair entry in this.executor.BookmarkQueueMap) { if (entry.Value == bookmark) { bookmarksToRemove.Add(entry.Key); } } foreach (Bookmark bookmarkToRemove in bookmarksToRemove) { this.executor.BookmarkQueueMap.Remove(bookmarkToRemove); } } } } void ProcessExecutionStatus(System.Workflow.ComponentModel.ActivityExecutionStatus executionStatus) { this.completed = (executionStatus == System.Workflow.ComponentModel.ActivityExecutionStatus.Closed); } public static class ParameterHelper { static readonly Type activityType = typeof(System.Workflow.ComponentModel.Activity); static readonly Type compositeActivityType = typeof(System.Workflow.ComponentModel.CompositeActivity); static readonly Type dependencyObjectType = typeof(System.Workflow.ComponentModel.DependencyObject); static readonly Type activityConditionType = typeof(System.Workflow.ComponentModel.ActivityCondition); // Interop Property Names internal const string interopPropertyActivityType = "ActivityType"; internal const string interopPropertyActivityProperties = "ActivityProperties"; internal const string interopPropertyActivityMetaProperties = "ActivityMetaProperties"; // Allowed Meta-Properties internal const string activityNameMetaProperty = "Name"; //Check property names for any Property/PropertyOut pairs that would conflict with our naming scheme public static bool HasPropertyNameCollision(IList properties) { bool hasNameCollision = false; HashSet propertyNames = new HashSet (); foreach (PropertyInfo propertyInfo in properties) { propertyNames.Add(propertyInfo.Name); } if (propertyNames.Contains(interopPropertyActivityType) || propertyNames.Contains(interopPropertyActivityProperties) || propertyNames.Contains(interopPropertyActivityMetaProperties)) { hasNameCollision = true; } else { foreach (PropertyInfo propertyInfo in properties) { if (propertyNames.Contains(propertyInfo.Name + Interop.OutArgumentSuffix)) { hasNameCollision = true; break; } } } return hasNameCollision; } public static bool IsBindable(PropertyInfo propertyInfo) { bool isMetaProperty; if (!IsBindableOrMetaProperty(propertyInfo, out isMetaProperty)) { return false; } return !isMetaProperty; } public static bool IsBindableOrMetaProperty(PropertyInfo propertyInfo, out bool isMetaProperty) { isMetaProperty = false; // Validate the declaring type: CompositeActivity and DependencyObject if (propertyInfo.DeclaringType.Equals(compositeActivityType) || propertyInfo.DeclaringType.Equals(dependencyObjectType)) { return false; } // Validate the declaring type: Activity // We allow certain meta-properties on System.Workflow.ComponentModel.Activity to be visible if (propertyInfo.DeclaringType.Equals(activityType) && !String.Equals(propertyInfo.Name, activityNameMetaProperty, StringComparison.Ordinal)) { return false; } //Validate the data type if (activityConditionType.IsAssignableFrom(propertyInfo.PropertyType)) { return false; } //Validate whether there is DP(Meta) backup string dependencyPropertyName = propertyInfo.Name; System.Workflow.ComponentModel.DependencyProperty dependencyProperty = System.Workflow.ComponentModel.DependencyProperty.FromName(dependencyPropertyName, propertyInfo.DeclaringType); if (dependencyProperty != null && dependencyProperty.DefaultMetadata.IsMetaProperty) { isMetaProperty = true; } return true; } } } } // File provided for Reference Use Only by Microsoft Corporation (c) 2007. //---------------------------------------------------------------- // Copyright (c) Microsoft Corporation. All rights reserved. //--------------------------------------------------------------- namespace System.Activities.Statements { using System.Activities; using System.Activities.Tracking; using System.Collections.Generic; using System.Collections.ObjectModel; using System.Diagnostics; using System.Reflection; using System.Runtime.Serialization; using System.Transactions; using System.Workflow.Runtime; using System.Workflow.Runtime.Tracking; using System.Runtime; using System.Globalization; class InteropEnvironment : IDisposable, IServiceProvider { static readonly ReadOnlyCollection emptyList = new ReadOnlyCollection (new IComparable[] { }); static MethodInfo getServiceMethod = typeof(NativeActivityContext).GetMethod("GetExtension"); NativeActivityContext nativeActivityContext; BookmarkCallback bookmarkCallback; bool disposed; bool completed; bool canceled; InteropExecutor executor; IEnumerable initialBookmarks; Exception uncaughtException; Transaction transaction; public InteropEnvironment(InteropExecutor interopExecutor, NativeActivityContext nativeActivityContext, BookmarkCallback bookmarkCallback, Interop activity, Transaction transaction) { //setup environment; this.executor = interopExecutor; this.nativeActivityContext = nativeActivityContext; this.Activity = activity; this.executor.ServiceProvider = this; this.bookmarkCallback = bookmarkCallback; this.transaction = transaction; OnEnter(); } public Interop Activity { get; set; } void IDisposable.Dispose() { if (!this.disposed) { OnExit(); this.disposed = true; } } public void Execute(System.Workflow.ComponentModel.Activity definition, NativeActivityContext context) { Debug.Assert(!disposed, "Cannot access disposed object"); try { this.executor.Initialize(definition, this.Activity.GetInputArgumentValues(context), this.Activity.HasNameCollision); ProcessExecutionStatus(this.executor.Execute()); } catch (Exception e) { this.uncaughtException = e; throw; } } public void Cancel() { Debug.Assert(!disposed, "Cannot access disposed object"); try { ProcessExecutionStatus(this.executor.Cancel()); this.canceled = true; } catch (Exception e) { this.uncaughtException = e; throw; } } public void EnqueueEvent(IComparable queueName, object item) { Debug.Assert(!disposed, "Cannot access disposed object"); try { ProcessExecutionStatus(this.executor.EnqueueEvent(queueName, item)); } catch (Exception e) { this.uncaughtException = e; throw; } } public void TrackActivityStatusChange(System.Workflow.ComponentModel.Activity activity, int eventCounter) { this.nativeActivityContext.Track( new InteropTrackingRecord(this.Activity.DisplayName, new ActivityTrackingRecord( activity.GetType(), activity.QualifiedName, activity.ContextGuid, activity.Parent == null ? Guid.Empty : activity.Parent.ContextGuid, activity.ExecutionStatus, DateTime.UtcNow, eventCounter, null ) ) ); } public void TrackData(System.Workflow.ComponentModel.Activity activity, int eventCounter, string key, object data) { this.nativeActivityContext.Track( new InteropTrackingRecord(this.Activity.DisplayName, new UserTrackingRecord( activity.GetType(), activity.QualifiedName, activity.ContextGuid, activity.Parent == null ? Guid.Empty : activity.Parent.ContextGuid, DateTime.UtcNow, eventCounter, key, data ) ) ); } public void Resume() { Debug.Assert(!disposed, "Cannot access disposed object"); try { ProcessExecutionStatus(this.executor.Resume()); } catch (Exception e) { this.uncaughtException = e; throw; } } // object IServiceProvider.GetService(Type serviceType) { Debug.Assert(!disposed, "Cannot access disposed object"); MethodInfo genericMethodInfo = getServiceMethod.MakeGenericMethod(serviceType); return genericMethodInfo.Invoke(this.nativeActivityContext, null); } public void Persist() { this.Activity.Persist(this.nativeActivityContext); } public void CreateTransaction(TransactionOptions transactionOptions) { this.Activity.CreateTransaction(this.nativeActivityContext, transactionOptions); } public void CommitTransaction() { this.Activity.CommitTransaction(this.nativeActivityContext); } public void AddResourceManager(VolatileResourceManager resourceManager) { this.Activity.AddResourceManager(this.nativeActivityContext,resourceManager); } //Called everytime on enter of interopenvironment. void OnEnter() { //Capture Current state of Queues in InteropEnvironment. this.initialBookmarks = this.executor.Queues; // This method sets up the ambient transaction for the current thread. // Since the runtime can execute us on different threads, // we have to set up the transaction scope everytime we enter the interop environment and clear it when we leave the environment. this.executor.SetAmbientTransactionAndServiceEnvironment(this.transaction); } //Called everytime we leave InteropEnvironment. void OnExit() { if (this.uncaughtException != null) { if (WorkflowExecutor.IsIrrecoverableException(this.uncaughtException)) { return; } } // This method clears the ambient transaction for the current thread. // Since the runtime can execute us on different threads, // we have to set up the transaction scope everytime we enter the interop environment and clear it when we leave the environment. this.executor.ClearAmbientTransactionAndServiceEnvironment(); //Capture Current state of Queues in InteropEnvironment. IEnumerable currentBookmarks = this.executor.Queues; //Set outparameters when completed or faulted. if (this.completed || this.uncaughtException != null) { this.Activity.OnClose(this.nativeActivityContext, this.uncaughtException); this.Activity.SetOutputArgumentValues( this.executor.Outputs, this.nativeActivityContext); this.nativeActivityContext.RemoveAllBookmarks(); this.executor.BookmarkQueueMap.Clear(); if (this.canceled) { this.nativeActivityContext.MarkCanceled(); } } else { //Find Differentials IList deletedBookmarks = new List (); foreach (IComparable value in this.initialBookmarks) { deletedBookmarks.Add(value); } IList newBookmarks = null; foreach (IComparable value in currentBookmarks) { if (!deletedBookmarks.Remove(value)) { if (newBookmarks == null) { newBookmarks = new List (); } newBookmarks.Add(value); } } if (newBookmarks != null) { // Create new Queues as Bookmark. foreach (IComparable bookmark in newBookmarks) { // Bookmark v2Bookmark = this.nativeActivityContext.CreateBookmark(bookmark.ToString(), this.bookmarkCallback, BookmarkOptions.MultipleResume); this.executor.BookmarkQueueMap.Add(v2Bookmark, bookmark); } } // Delete removed queues. foreach (IComparable bookmark in deletedBookmarks) { this.nativeActivityContext.RemoveBookmark(bookmark.ToString()); List bookmarksToRemove = new List (); foreach (KeyValuePair entry in this.executor.BookmarkQueueMap) { if (entry.Value == bookmark) { bookmarksToRemove.Add(entry.Key); } } foreach (Bookmark bookmarkToRemove in bookmarksToRemove) { this.executor.BookmarkQueueMap.Remove(bookmarkToRemove); } } } } void ProcessExecutionStatus(System.Workflow.ComponentModel.ActivityExecutionStatus executionStatus) { this.completed = (executionStatus == System.Workflow.ComponentModel.ActivityExecutionStatus.Closed); } public static class ParameterHelper { static readonly Type activityType = typeof(System.Workflow.ComponentModel.Activity); static readonly Type compositeActivityType = typeof(System.Workflow.ComponentModel.CompositeActivity); static readonly Type dependencyObjectType = typeof(System.Workflow.ComponentModel.DependencyObject); static readonly Type activityConditionType = typeof(System.Workflow.ComponentModel.ActivityCondition); // Interop Property Names internal const string interopPropertyActivityType = "ActivityType"; internal const string interopPropertyActivityProperties = "ActivityProperties"; internal const string interopPropertyActivityMetaProperties = "ActivityMetaProperties"; // Allowed Meta-Properties internal const string activityNameMetaProperty = "Name"; //Check property names for any Property/PropertyOut pairs that would conflict with our naming scheme public static bool HasPropertyNameCollision(IList properties) { bool hasNameCollision = false; HashSet propertyNames = new HashSet (); foreach (PropertyInfo propertyInfo in properties) { propertyNames.Add(propertyInfo.Name); } if (propertyNames.Contains(interopPropertyActivityType) || propertyNames.Contains(interopPropertyActivityProperties) || propertyNames.Contains(interopPropertyActivityMetaProperties)) { hasNameCollision = true; } else { foreach (PropertyInfo propertyInfo in properties) { if (propertyNames.Contains(propertyInfo.Name + Interop.OutArgumentSuffix)) { hasNameCollision = true; break; } } } return hasNameCollision; } public static bool IsBindable(PropertyInfo propertyInfo) { bool isMetaProperty; if (!IsBindableOrMetaProperty(propertyInfo, out isMetaProperty)) { return false; } return !isMetaProperty; } public static bool IsBindableOrMetaProperty(PropertyInfo propertyInfo, out bool isMetaProperty) { isMetaProperty = false; // Validate the declaring type: CompositeActivity and DependencyObject if (propertyInfo.DeclaringType.Equals(compositeActivityType) || propertyInfo.DeclaringType.Equals(dependencyObjectType)) { return false; } // Validate the declaring type: Activity // We allow certain meta-properties on System.Workflow.ComponentModel.Activity to be visible if (propertyInfo.DeclaringType.Equals(activityType) && !String.Equals(propertyInfo.Name, activityNameMetaProperty, StringComparison.Ordinal)) { return false; } //Validate the data type if (activityConditionType.IsAssignableFrom(propertyInfo.PropertyType)) { return false; } //Validate whether there is DP(Meta) backup string dependencyPropertyName = propertyInfo.Name; System.Workflow.ComponentModel.DependencyProperty dependencyProperty = System.Workflow.ComponentModel.DependencyProperty.FromName(dependencyPropertyName, propertyInfo.DeclaringType); if (dependencyProperty != null && dependencyProperty.DefaultMetadata.IsMetaProperty) { isMetaProperty = true; } return true; } } } } // File provided for Reference Use Only by Microsoft Corporation (c) 2007.
Link Menu

This book is available now!
Buy at Amazon US or
Buy at Amazon UK
- ComponentSerializationService.cs
- TypedLocationWrapper.cs
- TableRowCollection.cs
- ValidationHelpers.cs
- PerformanceCounterPermission.cs
- CommonBehaviorsSection.cs
- PromptBuilder.cs
- InfoCardRSAPKCS1SignatureDeformatter.cs
- WebBrowser.cs
- FlowDocumentScrollViewer.cs
- NetMsmqBindingCollectionElement.cs
- DropDownList.cs
- Brush.cs
- MouseGestureValueSerializer.cs
- ListControl.cs
- ProgressChangedEventArgs.cs
- SizeAnimationUsingKeyFrames.cs
- Logging.cs
- DataSourceCollectionBase.cs
- Propagator.cs
- WizardSideBarListControlItem.cs
- TrailingSpaceComparer.cs
- StatusBarDesigner.cs
- SQLInt32.cs
- AuthorizationRuleCollection.cs
- DecimalKeyFrameCollection.cs
- GrammarBuilderPhrase.cs
- CodeTypeParameterCollection.cs
- UrlPropertyAttribute.cs
- HierarchicalDataBoundControl.cs
- Privilege.cs
- Avt.cs
- ActiveXHost.cs
- AsymmetricSecurityBindingElement.cs
- MergeFilterQuery.cs
- ValidationPropertyAttribute.cs
- WebPartDisplayModeCancelEventArgs.cs
- RoleBoolean.cs
- RelationshipWrapper.cs
- OletxDependentTransaction.cs
- GZipDecoder.cs
- DataGridColumnHeadersPresenterAutomationPeer.cs
- EncoderReplacementFallback.cs
- ProfileService.cs
- DelegateSerializationHolder.cs
- ItemMap.cs
- OdbcDataAdapter.cs
- SqlParameter.cs
- HtmlWindow.cs
- DbConnectionStringCommon.cs
- FormsAuthenticationTicket.cs
- WmlLiteralTextAdapter.cs
- HtmlTableCellCollection.cs
- Style.cs
- OperatorExpressions.cs
- XslCompiledTransform.cs
- DataGridViewComboBoxColumnDesigner.cs
- WebSysDefaultValueAttribute.cs
- InputEventArgs.cs
- UIPermission.cs
- RuntimeHelpers.cs
- StaticResourceExtension.cs
- BinaryMessageEncodingBindingElement.cs
- BaseCodePageEncoding.cs
- OpCellTreeNode.cs
- EpmTargetPathSegment.cs
- TextureBrush.cs
- ZipArchive.cs
- SBCSCodePageEncoding.cs
- ChtmlFormAdapter.cs
- NativeMethodsOther.cs
- DataObjectEventArgs.cs
- TextDecorationCollection.cs
- UriSection.cs
- ProjectionCamera.cs
- WindowsRegion.cs
- ApplicationHost.cs
- LexicalChunk.cs
- MsmqIntegrationSecurity.cs
- Pens.cs
- SizeFConverter.cs
- DispatchChannelSink.cs
- DESCryptoServiceProvider.cs
- NamespaceTable.cs
- BinaryWriter.cs
- CannotUnloadAppDomainException.cs
- HtmlLink.cs
- WebPartChrome.cs
- VirtualPathProvider.cs
- WebSysDescriptionAttribute.cs
- SafeNativeMethodsOther.cs
- WebPartHeaderCloseVerb.cs
- XmlSchemaSimpleType.cs
- PersonalizationDictionary.cs
- DocumentXmlWriter.cs
- SslStream.cs
- FamilyTypeface.cs
- SafeMILHandle.cs
- WindowsRichEdit.cs
- ReflectionUtil.cs