I'm playing with generating dynamic proxies for properties.
A generated proxy is derived from a type that we want to proxy. When the proxy needs to access a (virtual) property on the type it's derived from, virtcall can't be used - it leads to infinite recursion. Thus we need to call OpCodes.Call. I noted that if I have:
public class MyParent
{
protected string _name;
protected string _color;
public virtual string Name
{
get { return _name; }
set { _name = value; }
}
public virtual string Color
{
get { return _color; }
set { _color = value; }
}
}
public class MyChild : MyParent
{
public override string Name {
get { return "42"; }
set { _name = value; }
}
}
When I emit OpCodes.Call
on the proxy object derived from MyChild
to call get_Color
it gets called correctly, even though technically this method is not implemented on MyChild
.
I was going to write some code that traverses the type hierarchy down to MyParent
where get_Color
implementation can be found and using that type method for OpCodes.Call
, but it appears this is not necessary:
var thisTypeMethod = property.GetGetMethod();
// I know that the next line technically is not correct because of non-virtual methods
// and also *new* overrides. Assume I'm doing it correctly, not by property.Name
// but by repeatedly calling MethodInfo.GetBaseDefinition()
var declaringTypeMethod = property.DeclaringType.GetProperty(property.Name).GetGetMethod();
and then
var proxyMethod = new DynamicMethod(thisTypeMethod.Name,thisTypeMethod.ReturnType, new Type[]{type},type,true);
var il = proxyMethod.GetILGenerator();
il.Emit(OpCodes.Ldarg_0);
il.Emit(OpCodes.Tailcall);
il.Emit(OpCodes.Call, thisTypeMethod);
il.Emit(OpCodes.Ret);
Is it safe NOT using declaringTypeMethod and using thisTypeMethod instead?
Aucun commentaire:
Enregistrer un commentaire