private ProxyInfo GetProxyInfoFromRegistry(RegistryKey reg)
        {
            var pi = new ProxyInfo(null, reg.GetValue(regAutoConfigUrl) as string, reg.GetValue(regProxyEnable) as int?, reg.GetValue(regProxyServer) as string,
                                   reg.GetValue(regProxyOverride) as string);

            return(pi);
        }
        /// <summary>
        /// Remove the HTTP and/or HTTPS proxy setting from current machine
        /// </summary>
        internal void RemoveProxy(ProxyProtocolType protocolType, bool saveOriginalConfig = true)
        {
            var reg = Registry.CurrentUser.OpenSubKey(regKeyInternetSettings, true);

            if (reg != null)
            {
                if (saveOriginalConfig)
                {
                    SaveOriginalProxyConfiguration(reg);
                }

                if (reg.GetValue(regProxyServer) != null)
                {
                    string exisitingContent = reg.GetValue(regProxyServer) as string;

                    var existingSystemProxyValues = ProxyInfo.GetSystemProxyValues(exisitingContent);
                    existingSystemProxyValues.RemoveAll(x => (protocolType & x.ProtocolType) != 0);

                    if (existingSystemProxyValues.Count != 0)
                    {
                        reg.SetValue(regProxyEnable, 1);
                        reg.SetValue(regProxyServer, string.Join(";", existingSystemProxyValues.Select(x => x.ToString()).ToArray()));
                    }
                    else
                    {
                        reg.SetValue(regProxyEnable, 0);
                        reg.SetValue(regProxyServer, string.Empty);
                    }
                }

                Refresh();
            }
        }
        /// <summary>
        ///     Set the HTTP and/or HTTPS proxy server for current machine
        /// </summary>
        /// <param name="hostname"></param>
        /// <param name="port"></param>
        /// <param name="protocolType"></param>
        internal void SetProxy(string hostname, int port, ProxyProtocolType protocolType)
        {
            using (var reg = openInternetSettingsKey())
            {
                if (reg == null)
                {
                    return;
                }

                saveOriginalProxyConfiguration(reg);
                prepareRegistry(reg);

                string?existingContent           = reg.GetValue(regProxyServer) as string;
                var    existingSystemProxyValues = ProxyInfo.GetSystemProxyValues(existingContent);
                existingSystemProxyValues.RemoveAll(x => (protocolType & x.ProtocolType) != 0);
                if ((protocolType & ProxyProtocolType.Http) != 0)
                {
                    existingSystemProxyValues.Add(new HttpSystemProxyValue(hostname, port, ProxyProtocolType.Http));
                }

                if ((protocolType & ProxyProtocolType.Https) != 0)
                {
                    existingSystemProxyValues.Add(new HttpSystemProxyValue(hostname, port, ProxyProtocolType.Https));
                }

                reg.DeleteValue(regAutoConfigUrl, false);
                reg.SetValue(regProxyEnable, 1);
                reg.SetValue(regProxyServer,
                             string.Join(";", existingSystemProxyValues.Select(x => x.ToString()).ToArray()));

                refresh();
            }
        }
        private void SaveOriginalProxyConfiguration(RegistryKey reg)
        {
            if (originalValues != null)
            {
                return;
            }

            originalValues = GetProxyInfoFromRegistry(reg);
        }
        internal void RestoreOriginalSettings()
        {
            if (originalValues == null)
            {
                return;
            }

            var reg = Registry.CurrentUser.OpenSubKey(regKeyInternetSettings, true);

            if (reg != null)
            {
                var ov = originalValues;
                if (ov.AutoConfigUrl != null)
                {
                    reg.SetValue(regAutoConfigUrl, ov.AutoConfigUrl);
                }
                else
                {
                    reg.DeleteValue(regAutoConfigUrl, false);
                }

                if (ov.ProxyEnable.HasValue)
                {
                    reg.SetValue(regProxyEnable, ov.ProxyEnable.Value);
                }
                else
                {
                    reg.DeleteValue(regProxyEnable, false);
                }

                if (ov.ProxyServer != null)
                {
                    reg.SetValue(regProxyServer, ov.ProxyServer);
                }
                else
                {
                    reg.DeleteValue(regProxyServer, false);
                }

                if (ov.ProxyOverride != null)
                {
                    reg.SetValue(regProxyOverride, ov.ProxyOverride);
                }
                else
                {
                    reg.DeleteValue(regProxyOverride, false);
                }

                originalValues = null;
                Refresh();
            }
        }
        /// <summary>
        ///     Set the HTTP and/or HTTPS proxy server for current machine
        /// </summary>
        /// <param name="hostname"></param>
        /// <param name="port"></param>
        /// <param name="protocolType"></param>
        public void SetProxy(string hostname, int port, ProxyProtocolType protocolType)
        {
            var reg = Registry.CurrentUser.OpenSubKey(regKeyInternetSettings, true);

            if (reg != null)
            {
                saveOriginalProxyConfiguration(reg);
                prepareRegistry(reg);

                string exisitingContent          = reg.GetValue(regProxyServer) as string;
                var    existingSystemProxyValues = ProxyInfo.GetSystemProxyValues(exisitingContent);
                existingSystemProxyValues.RemoveAll(x => (protocolType & x.ProtocolType) != 0);
                if ((protocolType & ProxyProtocolType.Http) != 0)
                {
                    existingSystemProxyValues.Add(new HttpSystemProxyValue
                    {
                        HostName     = hostname,
                        ProtocolType = ProxyProtocolType.Http,
                        Port         = port
                    });
                }

                if ((protocolType & ProxyProtocolType.Https) != 0)
                {
                    existingSystemProxyValues.Add(new HttpSystemProxyValue
                    {
                        HostName     = hostname,
                        ProtocolType = ProxyProtocolType.Https,
                        Port         = port
                    });
                }

                reg.DeleteValue(regAutoConfigUrl, false);
                reg.SetValue(regProxyEnable, 1);
                reg.SetValue(regProxyServer,
                             string.Join(";", existingSystemProxyValues.Select(x => x.ToString()).ToArray()));

                refresh();
            }
        }
        internal void RestoreOriginalSettings()
        {
            if (originalValues == null)
            {
                return;
            }

            using (var reg = Registry.CurrentUser.OpenSubKey(regKeyInternetSettings, true))
            {
                if (reg == null)
                {
                    return;
                }

                var ov = originalValues;
                if (ov.AutoConfigUrl != null)
                {
                    reg.SetValue(regAutoConfigUrl, ov.AutoConfigUrl);
                }
                else
                {
                    reg.DeleteValue(regAutoConfigUrl, false);
                }

                if (ov.ProxyEnable.HasValue)
                {
                    reg.SetValue(regProxyEnable, ov.ProxyEnable.Value);
                }
                else
                {
                    reg.DeleteValue(regProxyEnable, false);
                }

                if (ov.ProxyServer != null)
                {
                    reg.SetValue(regProxyServer, ov.ProxyServer);
                }
                else
                {
                    reg.DeleteValue(regProxyServer, false);
                }

                if (ov.ProxyOverride != null)
                {
                    reg.SetValue(regProxyOverride, ov.ProxyOverride);
                }
                else
                {
                    reg.DeleteValue(regProxyOverride, false);
                }

                // This should not be needed, but sometimes the values are not stored into the registry
                // at system shutdown without flushing.
                reg.Flush();

                originalValues = null;

                const int SM_SHUTTINGDOWN = 0x2000;
                Version   windows7Version = new Version(6, 1);
                if (Environment.OSVersion.Version > windows7Version ||
                    NativeMethods.GetSystemMetrics(SM_SHUTTINGDOWN) == 0)
                {
                    // Do not call refresh() in Windows 7 or earlier at system shutdown.
                    // SetInternetOption in the refresh method re-enables ProxyEnable registry value
                    // in Windows 7 or earlier at system shutdown.
                    refresh();
                }
            }
        }