[Mono-dev] Mono's reflection implementation

Robert Jordan robertj at gmx.net
Thu Sep 10 08:10:09 EDT 2009


Hi,

This is not a bug. BindingFlags.NonPublic does not return inherited
non-public class members.

It seems that MS.NET's internal delegate implementation is different
from Mono's. Maybe they are explicitly defining these fields in
inherited delegates.

Robert

Kris Mok wrote:
> Hi all,
> 
> I was trying out some tricks and needed reflection to pull them off. But 
> when I tried to retrieve private instance fields of an object, I found a 
> difference in behavior on Type.GetFields between Microsoft's CLR and Mono. I 
> tried this on Ubuntu 9.04 with Mono 2.0.1 from apt-get, and Mono 2.4.3.2 
> from source tarball.
> 
> Here's a repro:
> 
> using System;
> using System.Reflection;
> 
> static class Program {
>     static void PrintNonPublicInstanceFields(Type type) {
>         Console.WriteLine("non-public instance fields of {0}", type);
>         var mInfos = type.GetFields(BindingFlags.NonPublic | 
> BindingFlags.Instance);
>         if (0 == mInfos.Length) Console.WriteLine("mInfos is empty");
>         foreach (var mi in mInfos) {
>             Console.WriteLine(mi);
>         }
>     }
> 
>     static void Main(string[] args) {
>         // Mono 2.0.1 doesn't handle GetFields correctly:
>         // it only searches declared ones, not inherited ones
>         // Mono 2.4.3.2 behaves the same...
>         PrintNonPublicInstanceFields(typeof(Func<int, int>));
>         Console.WriteLine();
>         PrintNonPublicInstanceFields(typeof(Delegate));
>     }
> }
> 
> On Mono, the program's output is:
> non-public instance fields of System.Func`2[System.Int32,System.Int32]
> mInfos is empty
> 
> non-public instance fields of System.Delegate
> System.IntPtr method_ptr
> System.IntPtr invoke_impl
> System.Object m_target
> System.IntPtr method
> System.IntPtr delegate_trampoline
> System.IntPtr method_code
> System.Reflection.MethodInfo method_info
> System.Reflection.MethodInfo original_method_info
> System.DelegateData data
> 
> where as on Microsoft's CLR, the output is:
> non-public instance fields of System.Func`2[System.Int32,System.Int32]
> System.Object _target
> System.Reflection.MethodBase _methodBase
> IntPtr _methodPtr
> IntPtr _methodPtrAux
> 
> non-public instance fields of System.Delegate
> System.Object _target
> System.Reflection.MethodBase _methodBase
> IntPtr _methodPtr
> IntPtr _methodPtrAux
> 
> I know the difference in actual private fields is due to different internal 
> implementations, what I'm trying to say is that Mono's Type.GetFields 
> doesn't return inherited fields.
> 
> According to Mono's documentation, here:
> http://go-mono.org/docs/monodoc.ashx?link=M%3aSystem.Type.GetFields(System.Reflection.BindingFlags)
> it says: System.Reflection.BindingFlags.DeclaredOnly to search only the 
> fields declared in the type, not fields that were simply inherited.
> I thought this should imply Type.GetFields will return inherited fields if I 
> don't call it with BindingFlags.DeclaredOnly. Is the current behavior 
> by-design or a bug? 



More information about the Mono-devel-list mailing list