GetField(“m_cultureTableRecord”, … ) on DateTimeFormatInfo type returns Nothing


With the previous versions of framework we are using the following code to set the PersianCalendar as the default calendar for the culture:

        Dim ci As New CultureInfo("fa-IR")
        Dim dtfi As DateTimeFormatInfo = ci.DateTimeFormat
        dtfi.AbbreviatedDayNames = New String() {"?", "?", "?", "?", "?", "?", "?"}
        dtfi.DayNames = New String() {"??????", "??????", "?? ????", "????????", "???????", "????", "????"}
        dtfi.AbbreviatedMonthNames = New String() {"???????", "????????", "?????", "???", "?????", "??????", "???", "????", "???", "??", "????", "?????", ""}
        dtfi.MonthNames = New String() {"???????", "????????", "?????", "???", "?????", "??????", "???", "????", "???", "??", "????", "?????", ""}
        dtfi.AMDesignator = "?.?"
        dtfi.PMDesignator = "?.?"
        dtfi.ShortDatePattern = "yyyy/MM/dd"
        dtfi.FirstDayOfWeek = DayOfWeek.Saturday
        Dim PersianCal As New PersianCalendar
        GetType(DateTimeFormatInfo).GetField("calendar", (BindingFlags.NonPublic Or (BindingFlags.Public Or BindingFlags.Instance))).SetValue(dtfi, PersianCal)
        Dim obj As Object = GetType(DateTimeFormatInfo).GetField("m_cultureTableRecord", (BindingFlags.NonPublic Or (BindingFlags.Public Or BindingFlags.Instance))).GetValue(dtfi)
        obj.GetType.GetMethod("UseCurrentCalendar", (BindingFlags.NonPublic Or BindingFlags.Instance)).Invoke(obj, New Object() {PersianCal.GetType.GetProperty("ID", (BindingFlags.NonPublic Or BindingFlags.Instance)).GetValue(PersianCal, Nothing)})
        GetType(CultureInfo).GetField("calendar", (BindingFlags.NonPublic Or (BindingFlags.Public Or BindingFlags.Instance))).SetValue(ci, PersianCal)
        Thread.CurrentThread.CurrentCulture = ci
        Thread.CurrentThread.CurrentUICulture = ci
        CultureInfo.CurrentCulture.DateTimeFormat = dtfi
        CultureInfo.CurrentUICulture.DateTimeFormat = dtfi

But in the version 4 of the framework, the above code does not work. because the following line returns Nothing:

        Dim obj As Object = GetType(DateTimeFormatInfo).GetField("m_cultureTableRecord", (BindingFlags.NonPublic Or (BindingFlags.Public Or BindingFlags.Instance)))

What are the changes needed to get the code working?


m_cultureTableRecord and calendar are both private fields. They are part of internal implementation of the DateTimeFormatInfo type  and therefore are subject to change without any notice.Your application should never use them, it is not supported scenario. If your application is using them, it is a bug in your code and source of potential instability (it is not guaranteed to work at all).In other words, such changes in .NET Fx 4.0 are by design. Use only public APIs to achieve what you need: of private field calendar, can you set public property Calendar?Also check out CultureInfo.Calendar and CultureInfo.UseUserOverride.-Karel/

Thank you for your reply. I know that they are internal fields. But for whatever reason, though it’s possible (the above code works perfectly on the previous versions without any problem) the PersianCalendar was not in the OptionalCalendars of the fa-IR culture info! and still the same in .Net 4! Is it possible with the public APIs to achieve that?!! Regards, Parham.

Instead of private field calendar, can you set public property Calendar ? Also check out CultureInfo.Calendar and CultureInfo.UseUserOverride . -KarelPersianCalendar Class : Your application should not use a PersianCalendar object as the default calendar for a culture. The default calendar is specified by the CultureInfo..::. Calendar property and must be one of the calendars returned by the CultureInfo..::. OptionalCalendars property. Currently, the PersianCalendar class is not an optional calendar for any culture supported by the CultureInfo class and consequently cannot be a default calendar