Esempio n. 1
0
        /*=================================GetCompareInfo==========================
         **Action: Get the CompareInfo constructed from the data table in the specified assembly for the specified culture.
         **       The purpose of this method is to provide versioning for CompareInfo tables.
         **       If you pass Assembly which contains different sorting table, you will sort your strings using the data
         **       in the assembly.
         **Returns: The CompareInfo for the specified culture.
         **Arguments:
         **   culture     the ID of the culture
         **   assembly   the assembly which contains the sorting table.
         **Exceptions:
         **  ArugmentNullException when the assembly is null
         **  ArgumentException if culture is invalid.
         **============================================================================*/

        /* Note: The design goal here is that we can still provide version even when the underlying algorithm for CompareInfo
         *   is totally changed in the future.
         *   In the case that the algorithm for CompareInfo is changed, we can use this method to
         *   provide the old algorithm for the old tables.  The idea is to change the implementation for GetCompareInfo()
         *   to something like:
         *     1. Check the ID of the assembly.
         *     2. If the assembly needs old code, create an instance of the old CompareInfo class. The name of CompareInfo
         *        will be like CompareInfoVersion1 and extends from CompareInfo.
         *     3. Otherwise, create an instance of the current CompareInfo.
         *   The CompareInfo ctor always provides the implementation for the current data table.
         */

        /// <include file='doc\CompareInfo.uex' path='docs/doc[@for="CompareInfo.GetCompareInfo"]/*' />
        public static CompareInfo GetCompareInfo(int culture, Assembly assembly)
        {
            // Parameter checking.
            if (assembly == null)
            {
                throw new ArgumentNullException("assembly");
            }
            if (assembly != typeof(Object).Module.Assembly)
            {
                throw new ArgumentException(Environment.GetResourceString("Argument_OnlyMscorlib"));
            }

            // culture is verified to see if it is valid when CompareInfo is constructed.

            GlobalizationAssembly ga = GlobalizationAssembly.GetGlobalizationAssembly(assembly);
            Object compInfo          = ga.compareInfoCache[culture];

            if (compInfo == null)
            {
                lock (typeof(GlobalizationAssembly)) {
                    //
                    // Re-check again to make sure that no one has created the CompareInfo for the culture yet before the current
                    // thread enters this sync block.
                    //
                    if ((compInfo = ga.compareInfoCache[culture]) == null)
                    {
                        compInfo = new CompareInfo(ga, culture);
                        ga.compareInfoCache[culture] = compInfo;
                    }
                }
            }

            return((CompareInfo)compInfo);
        }
Esempio n. 2
0
        internal static unsafe void *GetNativeTextInfo(int cultureID)
        {
            // First, assume this culture does not has exceptions. I.e. we should use the default casingg table.
            // So we assign the native NativeTextInfo for the default casing table to it.
            void *pNativeTextInfo = m_pDefaultCasingTable;

            // Now, go thru the exception table to see if it has exception or not.
            for (int i = 0; i < m_exceptionCount; i++)
            {
                if (m_exceptionTable[i].langID == cultureID)
                {
                    // This culture has exceptions.
                    if (m_exceptionNativeTextInfo[i] == 0)
                    {
                        lock (InternalSyncObject) {
                            // Read the exception casing file.
                            if (m_pExceptionFile == null)
                            {
                                m_pExceptionFile = GlobalizationAssembly.GetGlobalizationResourceBytePtr(typeof(TextInfo).Assembly, CASING_EXCEPTIONS_FILE_NAME);
                            }
                            long tempPtr = (long)(InternalAllocateCasingTable(m_pExceptionFile, m_exceptionTable[i].exceptIndex));
                            System.Threading.Thread.MemoryBarrier();
                            m_exceptionNativeTextInfo[i] = tempPtr;
                        }
                    }
                    pNativeTextInfo = (void *)m_exceptionNativeTextInfo[i];
                    break;
                }
            }
            return(pNativeTextInfo);
        }
Esempio n. 3
0
        ////////////////////////////////////////////////////////////////////////
        //
        //  Actions:
        //      This is the static ctor for TextInfo.  It does the following items:
        //      * Get the total count of cultures with exceptions.
        //      * Set up an exception index table so that we can check if a culture has exception.  If yes, which sub-table
        //        in the exception table file we should use for this culture.
        //      * Set up a cache for NativeTextInfo that we create for cultures with exceptions.
        //
        ////////////////////////////////////////////////////////////////////////

        static unsafe TextInfo()
        {
            //with AppDomains active, the static initializer is no longer good enough to ensure that only one
            //thread is ever in AllocateDefaultCasingTable at a given time.
            //We use InterlockedExchangePointer in the native side to ensure that only one instance of native CasingTable instance
            //is created per process.

            //We check if the table is already allocated in native, so we only need to synchronize
            //access in managed.
            byte *temp = GlobalizationAssembly.GetGlobalizationResourceBytePtr(typeof(TextInfo).Assembly, CASING_FILE_NAME);

            System.Threading.Thread.MemoryBarrier();
            m_pDataTable = temp;

            TextInfoDataHeader *pHeader = (TextInfoDataHeader *)m_pDataTable;

            m_exceptionCount = pHeader->exceptionCount;
            // Setup exception tables
            m_exceptionTable          = (ExceptionTableItem *)&(pHeader->exceptionLangId);
            m_exceptionNativeTextInfo = new long[m_exceptionCount];

            // Create the native NativeTextInfo for the default linguistic casing table.
            m_pDefaultCasingTable = AllocateDefaultCasingTable(m_pDataTable);

            BCLDebug.Assert(m_pDataTable != null, "Error in reading the table.");
            BCLDebug.Assert(m_pDefaultCasingTable != null, "m_pDefaultCasingTable != null");
        }
Esempio n. 4
0
        internal unsafe void InitializeBaseInfoTablePointers(String fileName, bool fromAssembly)
        {
            if (fromAssembly)
            {
                m_pDataFileStart = GlobalizationAssembly.GetGlobalizationResourceBytePtr(typeof(BaseInfoTable).Assembly, fileName);
            }
            else
            {
                this.memoryMapFile = new MemoryMapFile(fileName);

                if (this.memoryMapFile.FileSize == 0)
                {
                    m_valid = false;
                    return;
                }

                this.m_pDataFileStart = this.memoryMapFile.GetBytePtr();
            }
            EndianessHeader *pEndianHeader = (EndianessHeader *)m_pDataFileStart;

            // Set up pointer to the CultureTableHeader

#if BIGENDIAN
            BCLDebug.Assert(pEndianHeader->beOffset != 0, "Big-Endian data is expected.");
            m_pCultureHeader = (CultureTableHeader *)(m_pDataFileStart + pEndianHeader->beOffset);
#else
            BCLDebug.Assert(pEndianHeader->leOffset != 0, "Little-Endian data is expected.");
            m_pCultureHeader = (CultureTableHeader *)(m_pDataFileStart + pEndianHeader->leOffset);
#endif

            // Set up misc pointers and variables.
            // Different data items for calendar and culture, so they each have their own setting thingy.
            SetDataItemPointers();
        }
Esempio n. 5
0
        private static CompareInfo GetCompareInfoWithPrefixedLcid(int cultureKey, Assembly assembly, int prefix)
        {
            if (assembly == null)
            {
                throw new ArgumentNullException("assembly");
            }
            int cultureId = cultureKey & ~prefix;

            if (System.Globalization.CultureTableRecord.IsCustomCultureId(cultureId))
            {
                throw new ArgumentException(Environment.GetResourceString("Argument_CustomCultureCannotBePassedByNumber", new object[] { "culture" }));
            }
            if (assembly != typeof(object).Module.Assembly)
            {
                throw new ArgumentException(Environment.GetResourceString("Argument_OnlyMscorlib"));
            }
            GlobalizationAssembly globalizationAssembly = GlobalizationAssembly.GetGlobalizationAssembly(assembly);
            object obj2 = globalizationAssembly.compareInfoCache[cultureKey];

            if (obj2 == null)
            {
                lock (InternalSyncObject)
                {
                    obj2 = globalizationAssembly.compareInfoCache[cultureKey];
                    if (obj2 == null)
                    {
                        obj2 = new CompareInfo(globalizationAssembly, cultureId);
                        Thread.MemoryBarrier();
                        globalizationAssembly.compareInfoCache[cultureKey] = obj2;
                    }
                }
            }
            return((CompareInfo)obj2);
        }
Esempio n. 6
0
 static GlobalizationAssembly() {
     lock (typeof(GlobalizationAssembly)) {
         if (m_defaultInstance==null) {
             // Initialize the default GlobalizationAseembly for the default assembly.
             m_defaultInstance = GetGlobalizationAssembly(Assembly.GetAssembly(typeof(GlobalizationAssembly)));
         }
     }
 }       
 static GlobalizationAssembly()
 {
     lock (typeof(GlobalizationAssembly)) {
         if (m_defaultInstance == null)
         {
             // Initialize the default GlobalizationAseembly for the default assembly.
             m_defaultInstance = GetGlobalizationAssembly(Assembly.GetAssembly(typeof(GlobalizationAssembly)));
         }
     }
 }
        internal static GlobalizationAssembly GetGlobalizationAssembly(Assembly assembly)
        {
            GlobalizationAssembly assembly2 = (GlobalizationAssembly)m_assemblyHash[assembly];

            if (assembly2 == null)
            {
                RuntimeHelpers.TryCode code = new RuntimeHelpers.TryCode(GlobalizationAssembly.CreateGlobalizationAssembly);
                RuntimeHelpers.ExecuteCodeWithLock(typeof(CultureTableRecord), code, assembly);
                assembly2 = (GlobalizationAssembly)m_assemblyHash[assembly];
            }
            return(assembly2);
        }
        private unsafe static bool InitTable()
        {
            byte *globalizationResourceBytePtr = GlobalizationAssembly.GetGlobalizationResourceBytePtr(typeof(CharUnicodeInfo).Assembly, "charinfo.nlp");

            CharUnicodeInfo.UnicodeDataHeader *ptr = (CharUnicodeInfo.UnicodeDataHeader *)globalizationResourceBytePtr;
            CharUnicodeInfo.s_pCategoryLevel1Index = (ushort *)(globalizationResourceBytePtr + ptr->OffsetToCategoriesIndex);
            CharUnicodeInfo.s_pCategoriesValue     = globalizationResourceBytePtr + ptr->OffsetToCategoriesValue;
            CharUnicodeInfo.s_pNumericLevel1Index  = (ushort *)(globalizationResourceBytePtr + ptr->OffsetToNumbericIndex);
            CharUnicodeInfo.s_pNumericValues       = globalizationResourceBytePtr + ptr->OffsetToNumbericValue;
            CharUnicodeInfo.s_pDigitValues         = (CharUnicodeInfo.DigitValues *)(globalizationResourceBytePtr + ptr->OffsetToDigitValue);
            return(true);
        }
Esempio n. 10
0
 internal unsafe CompareInfo(GlobalizationAssembly ga, int culture)
 {
     if (culture < 0)
     {
         throw new ArgumentOutOfRangeException("culture", Environment.GetResourceString("ArgumentOutOfRange_NeedPosNum"));
     }
     this.m_sortingLCID = this.GetSortingLCID(culture);
     if (!this.IsSynthetic)
     {
         this.m_pSortingTable = InitializeCompareInfo(GlobalizationAssembly.DefaultInstance.pNativeGlobalizationAssembly, this.m_sortingLCID);
     }
     this.culture = culture;
 }
Esempio n. 11
0
 private static void CreateGlobalizationAssembly(object assem)
 {
     Assembly assembly2 = (Assembly) assem;
     GlobalizationAssembly assembly = (GlobalizationAssembly) m_assemblyHash[assembly2];
     if (assembly == null)
     {
         assembly = new GlobalizationAssembly {
             pNativeGlobalizationAssembly = nativeCreateGlobalizationAssembly(assembly2)
         };
         Thread.MemoryBarrier();
         m_assemblyHash[assembly2] = assembly;
     }
 }
Esempio n. 12
0
 internal unsafe CompareInfo(GlobalizationAssembly ga, int culture)
 {
     if (culture < 0)
     {
         throw new ArgumentOutOfRangeException("culture", Environment.GetResourceString("ArgumentOutOfRange_NeedPosNum"));
     }
     this.m_sortingLCID = this.GetSortingLCID(culture);
     if (!this.IsSynthetic)
     {
         this.m_pSortingTable = InitializeCompareInfo(GlobalizationAssembly.DefaultInstance.pNativeGlobalizationAssembly, this.m_sortingLCID);
     }
     this.culture = culture;
 }
Esempio n. 13
0
        internal int culture;               // the culture ID used to create this instance.


        ////////////////////////////////////////////////////////////////////////
        //
        //  CompareInfo Constructor
        //
        //
        ////////////////////////////////////////////////////////////////////////


        // Constructs an instance that most closely corresponds to the NLS locale
        // identifier.
        internal unsafe CompareInfo(GlobalizationAssembly ga, int culture)
        {
            if (culture < 0)
            {
                throw new ArgumentOutOfRangeException("culture", Environment.GetResourceString("ArgumentOutOfRange_NeedPosNum"));
            }

            // NOTENOTE YSLin: In the future, move all the culture validation to the native code InitializeCompareInfo, since we make three
            // native calls below, which are expansive.

            //
            // Verify that this is a valid culture.
            //
            int dataItem = CultureTable.GetDataItemFromCultureID(CultureInfo.GetLangID(culture));

            if (dataItem == -1)
            {
                throw new ArgumentException(
                          String.Format(Environment.GetResourceString("Argument_CultureNotSupported"), culture), "culture");
            }

            // We do the following because the native C++ SortingTable is based on the
            // WIN32 LCID.  It doesn't work for neutral cultures liek 0x0009.  So we convert culture
            // to a Win32 LCID here.

            // Note that we have to get Sort ID from culture.  This will affect the result of string comparison.
            this.win32LCID = CultureTable.GetDefaultInt32Value(dataItem, CultureTable.WIN32LANGID);

            int sortID = CultureInfo.GetSortID(culture);

            if (sortID != 0)
            {
                // Need to verify if the Sort ID is valid.
                if (!CultureTable.IsValidSortID(dataItem, sortID))
                {
                    throw new ArgumentException(
                              String.Format(Environment.GetResourceString("Argument_CultureNotSupported"), culture), "culture");
                }
                // This is an alterinative sort LCID.  Hey man, don't forget to take your SORTID with you.
                win32LCID |= sortID << 16;
            }

            // TODO: InitializeCompareInfo should use ga instead of getting the default instance.

            // Call to the native side to create/get the corresponding native C++ SortingTable for this culture.
            // The returned value is a 32-bit pointer to the native C++ SortingTable instance.
            // We cache this pointer so that we can call methods of the SortingTable directly.
            pSortingTable = InitializeCompareInfo(GlobalizationAssembly.m_defaultInstance.pNativeGlobalizationAssembly, win32LCID);
            // Since win32LCID can be different from the passed-in culture in the case of neutral cultures, store the culture ID in a different place.
            this.culture = culture;
        }
Esempio n. 14
0
        private static void CreateGlobalizationAssembly(object assem)
        {
            Assembly assembly2             = (Assembly)assem;
            GlobalizationAssembly assembly = (GlobalizationAssembly)m_assemblyHash[assembly2];

            if (assembly == null)
            {
                assembly = new GlobalizationAssembly {
                    pNativeGlobalizationAssembly = nativeCreateGlobalizationAssembly(assembly2)
                };
                Thread.MemoryBarrier();
                m_assemblyHash[assembly2] = assembly;
            }
        }
Esempio n. 15
0
        private unsafe static void CreateGlobalizationAssembly(object assem)
        {
            GlobalizationAssembly ga;
            Assembly assembly = (Assembly)assem;

            if ((ga = (GlobalizationAssembly)m_assemblyHash[assembly]) == null)
            {
                // This assembly is not used before, create a corresponding native NativeGlobalizationAssembly object for it.
                ga = new GlobalizationAssembly();
                ga.pNativeGlobalizationAssembly = nativeCreateGlobalizationAssembly(assembly);
                System.Threading.Thread.MemoryBarrier();
                m_assemblyHash[assembly] = ga;
            }
        }
Esempio n. 16
0
        //We need to allocate the underlying table that provides us with the information that we
        //use.  We allocate this once in the class initializer and then we don't need to worry
        //about it again.
        //
        unsafe static CharUnicodeInfo()
        {
            m_pDataTable = GlobalizationAssembly.GetGlobalizationResourceBytePtr(typeof(CharUnicodeInfo).Assembly, UNICODE_INFO_FILE_NAME);
            UnicodeDataHeader *mainHeader = (UnicodeDataHeader *)m_pDataTable;

            // Set up the native pointer to different part of the tables.
            m_pCategoryLevel1Index = (ushort *)(m_pDataTable + mainHeader->OffsetToCategoriesIndex);
            m_pCategoriesValue     = (byte *)(m_pDataTable + mainHeader->OffsetToCategoriesValue);
            m_pNumericLevel1Index  = (ushort *)(m_pDataTable + mainHeader->OffsetToNumbericIndex);
            m_pNumericValues       = (byte *)(m_pDataTable + mainHeader->OffsetToNumbericValue);
            m_pDigitValues         = (DigitValues *)(m_pDataTable + mainHeader->OffsetToDigitValue);

            // Go to native side to make sure the native CharacterInfoTable pointer in the native side is initialized.
            nativeInitTable(m_pDataTable);
        }
Esempio n. 17
0
        unsafe static bool InitTable()
        {
            // Go to native side and get pointer to the native table
            byte *pDataTable = GlobalizationAssembly.GetGlobalizationResourceBytePtr(typeof(CharUnicodeInfo).Assembly, UNICODE_INFO_FILE_NAME);

            UnicodeDataHeader *mainHeader = (UnicodeDataHeader *)pDataTable;

            // Set up the native pointer to different part of the tables.
            s_pCategoryLevel1Index = (ushort *)(pDataTable + EndianSwap(mainHeader->OffsetToCategoriesIndex));
            s_pCategoriesValue     = (byte *)(pDataTable + EndianSwap(mainHeader->OffsetToCategoriesValue));
            s_pNumericLevel1Index  = (ushort *)(pDataTable + EndianSwap(mainHeader->OffsetToNumbericIndex));
            s_pNumericValues       = (byte *)(pDataTable + EndianSwap(mainHeader->OffsetToNumbericValue));
            s_pDigitValues         = (DigitValues *)(pDataTable + EndianSwap(mainHeader->OffsetToDigitValue));

            return(true);
        }
        /*=================================GetGlobalizationAssembly==========================
         **Action: Return the GlobalizationAssembly instance for the specified assembly.
         **  Every assembly should have one and only one instance of GlobalizationAssembly.
         **Returns: An instance of GlobalizationAssembly.
         **Arguments:
         **Exceptions:
         **============================================================================*/
        unsafe internal static GlobalizationAssembly GetGlobalizationAssembly(Assembly assembly)
        {
            GlobalizationAssembly ga;

            if ((ga = (GlobalizationAssembly)m_assemblyHash[assembly]) == null)
            {
                lock (typeof(GlobalizationAssembly)) {
                    if ((ga = (GlobalizationAssembly)m_assemblyHash[assembly]) == null)
                    {
                        // This assembly is not used before, create a corresponding native NativeGlobalizationAssembly object for it.
                        ga = new GlobalizationAssembly();
                        ga.pNativeGlobalizationAssembly = nativeCreateGlobalizationAssembly(assembly);
                        m_assemblyHash[assembly]        = ga;
                    }
                }
            }
            return(ga);
        }
Esempio n. 19
0
        internal unsafe void InitializeBaseInfoTablePointers(string fileName, bool fromAssembly)
        {
            if (fromAssembly)
            {
                this.m_pDataFileStart = GlobalizationAssembly.GetGlobalizationResourceBytePtr(typeof(BaseInfoTable).Assembly, fileName);
            }
            else
            {
                this.memoryMapFile = new AgileSafeNativeMemoryHandle(fileName);
                if (this.memoryMapFile.FileSize == 0L)
                {
                    this.m_valid = false;
                    return;
                }
                this.m_pDataFileStart = this.memoryMapFile.GetBytePtr();
            }
            EndianessHeader *pDataFileStart = (EndianessHeader *)this.m_pDataFileStart;

            this.m_pCultureHeader = (CultureTableHeader *)(this.m_pDataFileStart + pDataFileStart->leOffset);
            this.SetDataItemPointers();
        }
Esempio n. 20
0
 /*=================================GetGlobalizationAssembly==========================
 **Action: Return the GlobalizationAssembly instance for the specified assembly.
 **  Every assembly should have one and only one instance of GlobalizationAssembly.
 **Returns: An instance of GlobalizationAssembly.
 **Arguments:
 **Exceptions:
 ============================================================================*/
 unsafe internal static GlobalizationAssembly GetGlobalizationAssembly(Assembly assembly) {
     GlobalizationAssembly ga;
     
     if ((ga = (GlobalizationAssembly)m_assemblyHash[assembly]) == null) {            
         lock (typeof(GlobalizationAssembly)) {
             if ((ga = (GlobalizationAssembly)m_assemblyHash[assembly]) == null) {
                 // This assembly is not used before, create a corresponding native NativeGlobalizationAssembly object for it.
                 ga = new GlobalizationAssembly();
                 ga.pNativeGlobalizationAssembly = nativeCreateGlobalizationAssembly(assembly);
                 m_assemblyHash[assembly] = ga;
             }
         }
     }
     return (ga);
 }
Esempio n. 21
0
        internal int culture;               // the culture ID used to create this instance.
        
    
        ////////////////////////////////////////////////////////////////////////
        //
        //  CompareInfo Constructor
        //
        //
        ////////////////////////////////////////////////////////////////////////


        // Constructs an instance that most closely corresponds to the NLS locale 
        // identifier.  
        internal unsafe CompareInfo(GlobalizationAssembly ga, int culture) {
            if (culture < 0) {
                throw new ArgumentOutOfRangeException("culture", Environment.GetResourceString("ArgumentOutOfRange_NeedPosNum"));
            }

            
            //
            // Verify that this is a valid culture.
            //
            int dataItem = CultureTable.GetDataItemFromCultureID(CultureInfo.GetLangID(culture));
            if (dataItem == -1) {
                throw new ArgumentException(
                    String.Format(Environment.GetResourceString("Argument_CultureNotSupported"), culture), "culture");            
            }

            // We do the following because the native C++ SortingTable is based on the 
            // WIN32 LCID.  It doesn't work for neutral cultures liek 0x0009.  So we convert culture
            // to a Win32 LCID here.

            // Note that we have to get Sort ID from culture.  This will affect the result of string comparison.
            this.win32LCID = CultureTable.GetDefaultInt32Value(dataItem, CultureTable.WIN32LANGID);

            int sortID = CultureInfo.GetSortID(culture);
            if (sortID != 0) {
                // Need to verify if the Sort ID is valid.
                if (!CultureTable.IsValidSortID(dataItem, sortID)) {
                    throw new ArgumentException(
                        String.Format(Environment.GetResourceString("Argument_CultureNotSupported"), culture), "culture");            
                }
                // This is an alterinative sort LCID.  Hey man, don't forget to take your SORTID with you.
                win32LCID |= sortID << 16;
            }


            // Call to the native side to create/get the corresponding native C++ SortingTable for this culture.
            // The returned value is a 32-bit pointer to the native C++ SortingTable instance.  
            // We cache this pointer so that we can call methods of the SortingTable directly.
            pSortingTable = InitializeCompareInfo(GlobalizationAssembly.m_defaultInstance.pNativeGlobalizationAssembly, win32LCID);
            // Since win32LCID can be different from the passed-in culture in the case of neutral cultures, store the culture ID in a different place.
            this.culture = culture;

        }    
Esempio n. 22
0
        private static unsafe bool InitTable()
        {
            byte *globalizationResourceBytePtr;

            CharUnicodeInfo.UnicodeDataHeader *unicodeDataHeaderPtr = (CharUnicodeInfo.UnicodeDataHeader *)(globalizationResourceBytePtr = GlobalizationAssembly.GetGlobalizationResourceBytePtr(typeof(CharUnicodeInfo).Assembly, "charinfo.nlp"));
            IntPtr num1 = (IntPtr)unicodeDataHeaderPtr->OffsetToCategoriesIndex;

            CharUnicodeInfo.s_pCategoryLevel1Index = (ushort *)(globalizationResourceBytePtr + num1.ToInt64());
            IntPtr num2 = (IntPtr)unicodeDataHeaderPtr->OffsetToCategoriesValue;

            CharUnicodeInfo.s_pCategoriesValue = globalizationResourceBytePtr + num2.ToInt64();
            IntPtr num3 = (IntPtr)unicodeDataHeaderPtr->OffsetToNumbericIndex;

            CharUnicodeInfo.s_pNumericLevel1Index = (ushort *)(globalizationResourceBytePtr + num3.ToInt64());
            IntPtr num4 = (IntPtr)unicodeDataHeaderPtr->OffsetToNumbericValue;

            CharUnicodeInfo.s_pNumericValues = globalizationResourceBytePtr + num4.ToInt64();
            IntPtr num5 = (IntPtr)unicodeDataHeaderPtr->OffsetToDigitValue;

            CharUnicodeInfo.s_pDigitValues = (CharUnicodeInfo.DigitValues *)(globalizationResourceBytePtr + num5.ToInt64());
            return(true);
        }
 private unsafe static void CreateGlobalizationAssembly(object assem)
 {
     GlobalizationAssembly ga;
     Assembly assembly = (Assembly) assem;
     if ((ga = (GlobalizationAssembly)m_assemblyHash[assembly]) == null) 
     {
         // This assembly is not used before, create a corresponding native NativeGlobalizationAssembly object for it.
         ga = new GlobalizationAssembly();
         ga.pNativeGlobalizationAssembly = nativeCreateGlobalizationAssembly(assembly);
         System.Threading.Thread.MemoryBarrier();
         m_assemblyHash[assembly] = ga;
     }
 }
        private String m_name = null;                          // The name of the culture of this instance
        

        
        ////////////////////////////////////////////////////////////////////////
        //
        //  CompareInfo Constructor
        //
        //
        ////////////////////////////////////////////////////////////////////////


        // Constructs an instance that most closely corresponds to the NLS locale 
        // identifier.  
        internal unsafe CompareInfo(GlobalizationAssembly ga, int culture) {
            if (culture < 0) {
                throw new ArgumentOutOfRangeException("culture", Environment.GetResourceString("ArgumentOutOfRange_NeedPosNum"));
            }
            // Get the Win32 LCID used to create NativeCompareInfo, which only takes Win32 LCID.
            this.m_sortingLCID = GetSortingLCID(culture);

            // If version support is enabled, InitializeCompareInfo should use ga instead of getting the default 
            // instance.

            // Call to the native side to create/get the corresponding native C++ SortingTable for this culture.
            // The returned value is a 32-bit pointer to the native C++ SortingTable instance.  
            // We cache this pointer so that we can call methods of the SortingTable directly.
            if (!IsSynthetic)
            {
                m_pSortingTable = InitializeCompareInfo(GlobalizationAssembly.DefaultInstance.pNativeGlobalizationAssembly, this.m_sortingLCID);
            }
            // Since this.m_sortingLCID can be different from the passed-in culture in the case of neutral cultures, store the culture ID in a different place.
            this.culture = culture;

        }