Exception.GetBaseException() returning exception with not null InnerException

According to MSDN GetBaseException should behave like

public Exception GetBaseException()
{ 
    Exception result = this; 
    while (result.InnerException != null) 
        result = result.InnerException; 
    return result; 
}

And states

For all exceptions in a chain of exceptions, the GetBaseException method must return the same object (the base exception).

Which begs the question, why is this method virtual? It would seem that any override could only match the implementation or violate the contract.

According to MSDN AggregateException.GetBaseException

Returns the AggregateException that is the root cause of this exception.

By the OP's statement (and inspection of the source), "Returns the AggregateException" can be violated because the result is not always an AggregateException.

Frankly, I find the whole statement to be a non-sequitur as I would consider the 'first' NON-AggregateException to be "the root cause of this exception" insofar as one can identify a singular ("the") root cause. Since "regular" exceptions just get wrapped in AggregateExceptions as one moves toward the root of a parallel processing 'fan out'.

My best interpretation is that AggregateException.GetBaseException is intended to "unwrap" pointlessly non-parallel nested AggregateExceptions until reaching a level where 'fan out' actually occurs.

The bug here (LATER FIXED) would appear to be what happens when there IS no 'fan out', i.e. an AggregateException with just one (non-Aggregate) InnerException(s). In that case it returns that (non-Aggregate) Exception. .... which has a different GetBaseException implementation/interpretation.

EDIT 2020: At some point in the intervening years AggregateException.GetBaseException's implementation was fixed to match the above interpretation. @Jan-Slodicka's answer indicates it was fixed at least in Mono as far back as 2016.


It seemed that the problem wasn't linked with SignalR. It has to do with AggregateExceptions.

I was looking at the MSDN page of AggregateException.GetBaseException Method and I found this:

Returns the AggregateException that is the root cause of this exception

So I guess that the documentation of Exception.GetBaseException Method is valid only if the method is not overridden.