private object EvaluateRecursive(IConfigurationSectionHandler factory, object config, string [] keys, int iKey, XmlTextReader reader)
        {
            string name = keys[iKey];

            TraceVerbose("  EvaluateRecursive " + iKey + " " + name);

            int depth = reader.Depth;

            while (reader.Read() && reader.NodeType != XmlNodeType.Element)
            {
                ;
            }

            while (reader.Depth == depth + 1)
            {
                TraceVerbose("  EvaluateRecursive " + iKey + " " + name + " Name:" + reader.Name);
                if (reader.Name == name)
                {
                    if (iKey < keys.Length - 1)
                    {
                        config = EvaluateRecursive(factory, config, keys, iKey + 1, reader);
                    }
                    else
                    {
                        TraceVerbose("  EvaluateRecursive " + iKey + " calling Create()");
                        Debug.Assert(iKey == keys.Length - 1);

                        PermissionSet permissionSet = CreatePermissionSetFromLocation(_filename);
                        permissionSet.PermitOnly();
                        try {
                            //
                            // Call configuration section handler
                            //
                            // - try-catch is necessary to insulate config system from exceptions in user config handlers.
                            //   - bubble ConfigurationExceptions & XmlException
                            //   - wrap all others in ConfigurationException
                            //
                            int line = reader.LineNumber;
                            try {
                                ConfigXmlDocument doc     = new ConfigXmlDocument();
                                XmlNode           section = doc.ReadConfigNode(_filename, reader);
                                config = factory.Create(config, null, section);
                            }
                            catch (ConfigurationException) {
                                throw;
                            }
                            catch (XmlException) {
                                throw;
                            }
                            catch (Exception ex) {
                                throw new ConfigurationException(
                                          SR.GetString(SR.Exception_in_config_section_handler),
                                          ex, _filename, line);
                            }
                        }
                        finally {
                            CodeAccessPermission.RevertPermitOnly();
                        }
                    }
                    continue;
                }
                StrictSkipToNextElement(reader);
            }
            return(config);
        }