System.Diagnostics.PerformanceCounterLib.GetStringTable C# (CSharp) Method

GetStringTable() private method

private GetStringTable ( bool isHelp ) : string>.Dictionary
isHelp bool
return string>.Dictionary
        private Dictionary<int, string> GetStringTable(bool isHelp)
        {
            Dictionary<int, string> stringTable;
            RegistryKey libraryKey;

            libraryKey = Registry.PerformanceData;

            try
            {
                string[] names = null;
                int waitRetries = 14;   //((2^13)-1)*10ms == approximately 1.4mins
                int waitSleep = 0;

                // In some stress situations, querying counter values from 
                // HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Perflib\009 
                // often returns null/empty data back. We should build fault-tolerance logic to 
                // make it more reliable because getting null back once doesn't necessarily mean 
                // that the data is corrupted, most of the time we would get the data just fine 
                // in subsequent tries.
                while (waitRetries > 0)
                {
                    try
                    {
                        if (!isHelp)
                            names = (string[])libraryKey.GetValue("Counter " + _perfLcid);
                        else
                            names = (string[])libraryKey.GetValue("Explain " + _perfLcid);

                        if ((names == null) || (names.Length == 0))
                        {
                            --waitRetries;
                            if (waitSleep == 0)
                                waitSleep = 10;
                            else
                            {
                                System.Threading.Thread.Sleep(waitSleep);
                                waitSleep *= 2;
                            }
                        }
                        else
                            break;
                    }
                    catch (IOException)
                    {
                        // RegistryKey throws if it can't find the value.  We want to return an empty table
                        // and throw a different exception higher up the stack. 
                        names = null;
                        break;
                    }
                    catch (InvalidCastException)
                    {
                        // Unable to cast object of type 'System.Byte[]' to type 'System.String[]'.
                        // this happens when the registry data store is corrupt and the type is not even REG_MULTI_SZ
                        names = null;
                        break;
                    }
                }

                if (names == null)
                    stringTable = new Dictionary<int, string>();
                else
                {
                    stringTable = new Dictionary<int, string>(names.Length / 2);

                    for (int index = 0; index < (names.Length / 2); ++index)
                    {
                        string nameString = names[(index * 2) + 1];
                        if (nameString == null)
                            nameString = String.Empty;

                        int key;
                        if (!Int32.TryParse(names[index * 2], NumberStyles.Integer, CultureInfo.InvariantCulture, out key))
                        {
                            if (isHelp)
                            {
                                // Category Help Table
                                throw new InvalidOperationException(SR.Format(SR.CategoryHelpCorrupt, names[index * 2]));
                            }
                            else
                            {
                                // Counter Name Table 
                                throw new InvalidOperationException(SR.Format(SR.CounterNameCorrupt, names[index * 2]));
                            }
                        }

                        stringTable[key] = nameString;
                    }
                }
            }
            finally
            {
                libraryKey.Dispose();
            }

            return stringTable;
        }