AvaloniaUI/Avalonia · error · InvalidOperationException
Collection was modified during enumeration.
Error message
Collection was modified during enumeration.
What it means
InvalidOperationException thrown by the PooledStack<T> enumerator's MoveNext when the stack's version stamp differs from the one captured at enumerator creation (`_version != _stack._version`). PooledStack bumps _version on every Push/Pop/Clear/return, so any structural change during enumeration invalidates the enumerator and this guard aborts iteration rather than yielding stale or corrupt data.
Source
Thrown at src/Avalonia.Base/Collections/Pooled/PooledStack.cs:647
internal Enumerator(PooledStack<T> stack)
{
_stack = stack;
_version = stack._version;
_index = -2;
_currentElement = default;
}
public void Dispose()
{
_index = -1;
}
public bool MoveNext()
{
bool retval;
if (_version != _stack._version)
throw new InvalidOperationException("Collection was modified during enumeration.");
if (_index == -2)
{ // First call to enumerator.
_index = _stack._size - 1;
retval = (_index >= 0);
if (retval)
_currentElement = _stack._array[_index];
return retval;
}
if (_index == -1)
{ // End of enumeration.
return false;
}
retval = (--_index >= 0);
if (retval)
_currentElement = _stack._array[_index];
else
_currentElement = default;View on GitHub (pinned to 11c5427268)
Solutions
- Take a snapshot before iterating: `foreach (var x in stack.ToArray())`.
- Do not mutate the stack inside the loop; collect changes and apply them after the enumeration completes.
- Use a lock or copy for concurrent access.
Example fix
// before
foreach (var item in stack)
stack.Pop(); // mutates during enumeration
// after
foreach (var item in stack.ToArray())
stack.Pop(); Defensive patterns
Strategy: validation
Validate before calling
foreach (var item in stack.ToArray()) // iterate a snapshot
Process(item); // safe to Push/Pop here Prevention
- Never Push/Pop/Clear inside a foreach over the same stack.
- Snapshot with ToArray() before mutating loops.
- Serialize concurrent access with a lock or copy.
When it happens
Trigger: Calling Push/Pop/Clear/Trim on a PooledStack while a `foreach` or manual MoveNext loop over that same stack is in progress; modifying the stack from inside the loop body.
Common situations: Removing/adding items inside a foreach; reentrancy where an event handler mutates the stack during enumeration; iterating a stack that another thread mutates.
Related errors
- Enumeration was not started. | Enumeration has ended.
- Stack was empty.
- Collection was modified during enumeration.
- Invalid enumerator state: enumeration cannot proceed.
- Destination too short.
AI-assisted analysis of AvaloniaUI/Avalonia@11c5427268 (2026-08-13).
Data as JSON: /api/errors/a61608da461f4688.
Report an issue: GitHub.