ClientConfigurationSystem
using System.Configuration.Internal;
using System.Threading;
namespace System.Configuration
{
internal sealed class ClientConfigurationSystem : IInternalConfigSystem
{
private const string SystemDiagnosticsConfigKey = "system.diagnostics";
private const string SystemNetGroupKey = "system.net/";
private readonly IInternalConfigHost _configHost;
private readonly IInternalConfigRoot _configRoot;
private readonly bool _isAppConfigHttp;
private IInternalConfigRecord _completeConfigRecord;
private Exception _initError;
private bool _isInitInProgress;
private bool _isMachineConfigInited;
private bool _isUserConfigInited;
private IInternalConfigRecord _machineConfigRecord;
bool IInternalConfigSystem.SupportsUserConfig {
get {
return true;
}
}
internal ClientConfigurationSystem()
{
IConfigSystem configSystem = new ConfigSystem();
configSystem.Init(typeof(ClientConfigurationHost), null, null);
_configHost = configSystem.Host;
_configRoot = configSystem.Root;
_configRoot.ConfigRemoved += OnConfigRemoved;
_isAppConfigHttp = ((IInternalConfigHostPaths)_configHost).IsAppConfigHttp;
}
object IInternalConfigSystem.GetSection(string sectionName)
{
PrepareClientConfigSystem(sectionName);
IInternalConfigRecord internalConfigRecord = null;
if (DoesSectionOnlyUseMachineConfig(sectionName)) {
if (_isMachineConfigInited)
internalConfigRecord = _machineConfigRecord;
} else if (_isUserConfigInited) {
internalConfigRecord = _completeConfigRecord;
}
return internalConfigRecord?.GetSection(sectionName);
}
void IInternalConfigSystem.RefreshConfig(string sectionName)
{
PrepareClientConfigSystem(sectionName);
if (_isMachineConfigInited)
_machineConfigRecord.RefreshSection(sectionName);
}
private bool IsSectionUsedInInit(string configKey)
{
if (!(configKey == "system.diagnostics")) {
if (_isAppConfigHttp)
return configKey.StartsWith("system.net/", StringComparison.Ordinal);
return false;
}
return true;
}
private bool DoesSectionOnlyUseMachineConfig(string configKey)
{
if (_isAppConfigHttp)
return configKey.StartsWith("system.net/", StringComparison.Ordinal);
return false;
}
private void EnsureInit(string configKey)
{
bool flag = false;
lock (this) {
if (!_isUserConfigInited) {
if (!_isInitInProgress) {
_isInitInProgress = true;
flag = true;
} else if (!IsSectionUsedInInit(configKey)) {
Monitor.Wait(this);
}
}
}
if (flag)
try {
try {
_machineConfigRecord = _configRoot.GetConfigRecord("MACHINE");
_machineConfigRecord.ThrowIfInitErrors();
_isMachineConfigInited = true;
IInternalConfigHostPaths internalConfigHostPaths = (IInternalConfigHostPaths)_configHost;
internalConfigHostPaths.RefreshConfigPaths();
string configPath = (!internalConfigHostPaths.HasLocalConfig) ? (internalConfigHostPaths.HasRoamingConfig ? "MACHINE/EXE/ROAMING_USER" : "MACHINE/EXE") : "MACHINE/EXE/ROAMING_USER/LOCAL_USER";
_completeConfigRecord = _configRoot.GetConfigRecord(configPath);
_completeConfigRecord.ThrowIfInitErrors();
_isUserConfigInited = true;
} catch (Exception inner) {
_initError = new ConfigurationErrorsException(System.SR.Config_client_config_init_error, inner);
throw _initError;
}
} catch {
ConfigurationManager.SetInitError(_initError);
_isMachineConfigInited = true;
_isUserConfigInited = true;
throw;
} finally {
lock (this) {
try {
ConfigurationManager.CompleteConfigInit();
_isInitInProgress = false;
} finally {
Monitor.PulseAll(this);
}
}
}
}
private void PrepareClientConfigSystem(string sectionName)
{
if (!_isUserConfigInited)
EnsureInit(sectionName);
if (_initError != null)
throw _initError;
}
private void OnConfigRemoved(object sender, InternalConfigEventArgs e)
{
try {
IInternalConfigRecord internalConfigRecord = _completeConfigRecord = _configRoot.GetConfigRecord(_completeConfigRecord.ConfigPath);
_completeConfigRecord.ThrowIfInitErrors();
} catch (Exception inner) {
_initError = new ConfigurationErrorsException(System.SR.Config_client_config_init_error, inner);
ConfigurationManager.SetInitError(_initError);
throw _initError;
}
}
}
}