3

32 スレッドで並列 foreach ループを実行しようとしています。

この foreach ループは次を呼び出しています。

WorkflowInvoker.Invoke(new MyWorkflow(), myInputDictionary)

並列 foreach ループは、約 65000 項目のリストで構成されています。

ある時点で、約 6000 ~ 6700 項目で、WorkflowInvoker.Invoke(new MyWorkflow(), myInputDictionary) の呼び出しにより、次のメッセージとともに AccessViolationException がスローされます。 ."

WorkflowInvoker のインスタンスを作成し、MyWorkflow のインスタンスを新しく作成した WorkflowInvoker に直接渡し、クラスで Invoke メソッドを呼び出すなど、さまざまなことを試しました。また、WorkflowInvoker.Invoke を静的メソッドとして呼び出すだけですが、違いはありません。アプリケーションは毎回同じ時点でクラッシュします。スレッドがあるため、問題の原因を正確にデバッグして特定することは困難です。

もちろん、通常の foreach ループで呼び出しを行っている場合、問題は発生しません。

最初は、仮想マシンのメモリが不足しているのではないかと考えました。これは、アプリケーションが使用可能なすべてのメモリを消費し始め、合計メモリの 85% (4GB) の制限に達し、その後クラッシュしたように見えたためです。そのため、メモリ サイズを 1GB に変更して、ループの早い段階で例外を誘発できるかどうかを確認しましたが、代わりに Windows がガベージ コレクションを開始したため、最終的には 6000 ~ 6700 アイテム付近の同じポイントで例外が発生しました。

私の次の動きはどうあるべきかについての提案は、大歓迎です;-)

-- 編集 - 完全なスタック トレースを追加 --

at System.Reflection.Emit.ModuleBuilder.nCreateISymWriterForDynamicModule(Module module, String filename)
at System.Reflection.Emit.AssemblyBuilder.DefineDynamicModuleInternalNoLock(String name, Boolean emitSymbolInfo, StackCrawlMark& stackMark)
at System.Reflection.Emit.AssemblyBuilder.DefineDynamicModuleInternal(String name, Boolean emitSymbolInfo, StackCrawlMark& stackMark)
at System.Reflection.Emit.AssemblyBuilder.DefineDynamicModule(String name, Boolean emitSymbolInfo)
at System.Activities.Debugger.StateManager.InitDynamicModule(String asmName)
at System.Activities.Debugger.StateManager..ctor(Properties properties, Boolean debugStartedAtRoot)
at System.Activities.Debugger.DebugManager..ctor(Activity root, String moduleNamePrefix, String typeNamePrefix, String auxiliaryThreadName, Boolean breakOnStartup, WorkflowInstance host, Boolean debugStartedAtRoot)
at System.Activities.Debugger.DebugController.EnsureActivityInstrumented(ActivityInstance instance, Boolean primeCurrentInstance)
at System.Activities.Debugger.DebugController.ActivityStarted(ActivityInstance activityInstance)
at System.Activities.Runtime.ActivityExecutor.ExecuteActivityWorkItem.ExecuteBody(ActivityExecutor executor, BookmarkManager bookmarkManager, Location resultLocation)
at System.Activities.Runtime.ActivityExecutor.ExecuteRootWorkItem.Execute(ActivityExecutor executor, BookmarkManager bookmarkManager)
at System.Activities.Runtime.ActivityExecutor.OnExecuteWorkItem(WorkItem workItem)
at System.Activities.Runtime.Scheduler.Callbacks.ExecuteWorkItem(WorkItem workItem)
at System.Activities.Runtime.Scheduler.OnScheduledWork(Object state)
at System.Runtime.Fx.SendOrPostThunk.UnhandledExceptionFrame(Object state)
at System.Activities.WorkflowApplication.PumpBasedSynchronizationContext.WorkItem.Invoke()
at System.Activities.WorkflowApplication.PumpBasedSynchronizationContext.DoPump()
at System.Activities.WorkflowApplication.Invoke(Activity activity, IDictionary`2 inputs, WorkflowInstanceExtensionManager extensions, TimeSpan timeout)
at System.Activities.WorkflowInvoker.Invoke(Activity workflow, IDictionary`2 inputs, TimeSpan timeout, WorkflowInstanceExtensionManager extensions)
at System.Activities.WorkflowInvoker.Invoke(IDictionary`2 inputs)

-- 余分な編集 - 問題のメソッドを追加 - ビジネスロジック名を削除するために少し難読化 --

public MyOutputData InvokeMyWorkflow(MyInputData input) 
{
      IDictionary<string, object> wfInput = new Dictionary<string, object>
       {
        { "ArgData", input }
       };
  MyWorkflow myWorkflow = new MyWorkflow();
  try
  {
       WorkflowInvoker invoker = new WorkflowInvoker(myWorkflow);
       IDictionary<string, object> output = invoker.Invoke(wfInput);
       return output["ArgData"] == null ? null : (MyOutputData)output["ArgData"];
  }
  catch (Exception ace)
  {
           Log.Error(ace.StackTrace);
       return null;
  }
 }
4

0 に答える 0