Skip to content

Crash in MS.Internal.Data.AccessorTable.CleanupOperation #11665

@IngeborgAtRS

Description

@IngeborgAtRS

Description

I had an unexpected crash in my application (see crash log below). It's large, with many WPF views - this may have contributed to triggering this crash. The application had been running for over 4 hours when the crash occurred.

Reproduction Steps

I was not able to reproduce. It may be related to how long the application has been executing (over 4 hours).

Expected behavior

No crash :).

Actual behavior

The crash log is as follows:

System.InvalidOperationException: Collection was modified; enumeration operation may not execute.
   at System.Collections.Generic.Dictionary`2.Enumerator.MoveNext()
   at MS.Internal.Data.AccessorTable.CleanupOperation(Object arg)
   at System.Windows.Threading.ExceptionWrapper.InternalRealCall(Delegate callback, Object args, Int32 numArgs)
   at System.Windows.Threading.ExceptionWrapper.TryCatchWhen(Object source, Delegate callback, Object args, Int32 numArgs, Delegate catchHandler)
   at System.Windows.Threading.DispatcherOperation.InvokeImpl()
   at MS.Internal.CulturePreservingExecutionContext.CallbackWrapper(Object obj)
   at System.Threading.ExecutionContext.RunInternal(ExecutionContext executionContext, ContextCallback callback, Object state)
--- End of stack trace from previous location ---
   at System.Threading.ExecutionContext.RunInternal(ExecutionContext executionContext, ContextCallback callback, Object state)
   at MS.Internal.CulturePreservingExecutionContext.Run(CulturePreservingExecutionContext executionContext, ContextCallback callback, Object state)
   at System.Windows.Threading.DispatcherOperation.Invoke()
   at System.Windows.Threading.Dispatcher.ProcessQueue()
   at System.Windows.Threading.Dispatcher.WndProcHook(IntPtr hwnd, Int32 msg, IntPtr wParam, IntPtr lParam, Boolean& handled)
   at MS.Win32.HwndWrapper.WndProc(IntPtr hwnd, Int32 msg, IntPtr wParam, IntPtr lParam, Boolean& handled)
   at System.Windows.Threading.ExceptionWrapper.InternalRealCall(Delegate callback, Object args, Int32 numArgs)
   at System.Windows.Threading.ExceptionWrapper.TryCatchWhen(Object source, Delegate callback, Object args, Int32 numArgs, Delegate catchHandler)
   at System.Windows.Threading.Dispatcher.LegacyInvokeImpl(DispatcherPriority priority, TimeSpan timeout, Delegate method, Object args, Int32 numArgs)
   at MS.Win32.HwndSubclass.SubclassWndProc(IntPtr hwnd, Int32 msg, IntPtr wParam, IntPtr lParam)
   at MS.Win32.UnsafeNativeMethods.DispatchMessage(MSG& msg)
   at System.Windows.Threading.Dispatcher.PushFrameImpl(DispatcherFrame frame)
   at System.Threading.ExecutionContext.RunInternal(ExecutionContext executionContext, ContextCallback callback, Object state)
--- End of stack trace from previous location ---
   at System.Threading.ExecutionContext.RunInternal(ExecutionContext executionContext, ContextCallback callback, Object state)

Regression?

Uncertain since repro steps are unknown. We recently moved our application from .Net framework 4.8 to .Net 8, could be related.

Known Workarounds

None

Impact

Uncertain. I have so far only seen this once.

Configuration

.Net 8, Windows 11, x64. I doubt that it's specific to the configuration.

Other information

I find this code suspicious:

             // Remove entries that are sufficiently old
            foreach (KeyValuePair<AccessorTableKey, AccessorInfo> entry in _table)
            {
                int age = _generation - entry.Value.Generation;
                if (age >= AgeLimit)
                {
                    _table.Remove(entry.Key);
                }
            }

Removing an entry from something you're enumerating always looks suspicious, but maybe the dictionary enumerator can handle it.
Otherwise, is it possible that _table could be updated from multiple threads by the DataBinding engine?

Metadata

Metadata

Assignees

No one assigned

    Labels

    InvestigateRequires further investigation by the WPF team.

    Type

    No type
    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions