virtualCERCall MDA
Nota
Este artigo é específico do .NET Framework. Ele não se aplica a implementações mais recentes do .NET, incluindo o .NET 6 e versões posteriores.
O virtualCERCall
assistente de depuração gerenciado (MDA) é ativado como um aviso indicando que um site de chamada dentro de um gráfico de chamada de região de execução restrita (CER) se refere a um destino virtual, ou seja, uma chamada virtual para um método virtual não final ou uma chamada usando uma interface. O Common Language Runtime (CLR) não pode prever o método de destino dessas chamadas apenas a partir da linguagem intermediária e da análise de metadados. Como resultado, a árvore de chamada não pode ser preparada como parte do gráfico CER e o thread aborta nessa subárvore não pode ser bloqueado automaticamente. Este MDA alerta para casos em que uma RCE pode precisar ser estendida usando chamadas explícitas para o PrepareMethod método assim que as informações adicionais necessárias para calcular o destino da chamada forem conhecidas em tempo de execução.
Sintomas
CERs que não são executadas quando um thread é anulado ou um domínio de aplicativo é descarregado.
Motivo
Um CER contém uma chamada para um método virtual que não pode ser preparado automaticamente.
Resolução
Chame PrepareMethod para o método virtual.
Efeito no tempo de execução
Este MDA não tem efeito sobre o CLR.
Saída
Method 'MethodWithCer', while executing within a constrained execution region, makes a call
at IL offset 0x0024 to 'VirtualMethod', which is virtual and cannot be prepared automatically
at compile time. The caller must ensure this method is prepared explicitly at
runtime before entering the constrained execution region.
method name="VirtualMethod"
declaringType name="VirtualCERCall+MyClass"
declaringModule name="mda"
callsite name="MethodWithCer" offset="0x0024"
Configuração
<mdaConfig>
<assistants>
<VirtualCERCall />
</assistants>
</mdaConfig>
Exemplo
class MyClass
{
[ReliabilityContract(Consistency.MayCorruptProcess, CER.None)]
virtual void VirtualMethod()
{
...
}
}
class MyDerivedClass : MyClass
{
[ReliabilityContract(Consistency.MayCorruptProcess, CER.None)]
override void VirtualMethod()
{
...
}
}
void MethodWithCer(MyClass object)
{
RuntimeHelpers.PrepareConstrainedRegions();
try
{
...
}
finally
{
// Start of the CER.
// Cannot tell at analysis time whether object is a MyClass
// or a MyDerivedClass, so we do not know which version of
// VirtualMethod we are going to call.
object.VirtualMethod();
}
}