From 9f27c4bcf977dd055f75706c112c46e180ea427e Mon Sep 17 00:00:00 2001 From: ChsBuffer <33744752+chsbuffer@users.noreply.github.com> Date: Sat, 11 Jul 2020 19:30:35 +0800 Subject: [PATCH] =?UTF-8?q?=E5=9F=BA=E6=9C=AC=E5=AE=8C=E6=88=90=E9=87=8D?= =?UTF-8?q?=E6=9E=84=20Controller?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- Netch/Controllers/DNSController.cs | 35 +-- .../{ => EncryptedProxy}/SSController.cs | 33 +-- .../{ => EncryptedProxy}/SSRController.cs | 23 +- .../{ => EncryptedProxy}/TrojanController.cs | 20 +- .../{ => EncryptedProxy}/VMessController.cs | 18 +- Netch/Controllers/Interface/Controller.cs | 93 ++++-- Netch/Controllers/Interface/EncryptedProxy.cs | 18 ++ Netch/Controllers/Interface/ModeController.cs | 15 + Netch/Controllers/Interface/ServerClient.cs | 32 --- Netch/Controllers/MainController.cs | 123 +++----- .../Controllers/{ => Mode}/HTTPController.cs | 27 +- Netch/Controllers/Mode/NFController.cs | 269 ++++++++++++++++++ .../{ => Mode}/TUNTAPController.cs | 205 +++++++++---- Netch/Controllers/NFController.cs | 269 ------------------ Netch/Controllers/NTTController.cs | 22 +- Netch/Controllers/PrivoxyController.cs | 49 ++-- Netch/Forms/MainForm.Control.cs | 6 +- Netch/Forms/MainForm.MenuStrip.cs | 58 +--- Netch/Forms/MainForm.Profile.cs | 2 +- Netch/Forms/MainForm.cs | 55 ++-- Netch/Override/ToolStripProfessionalRender.cs | 2 +- Netch/Utils/Bandwidth.cs | 33 +-- Netch/Utils/Configuration.cs | 106 ------- Netch/Utils/Firewall.cs | 28 +- Netch/Utils/Logging.cs | 11 +- Netch/Utils/ShareLink.cs | 26 +- Netch/Win32Native.cs | 2 +- 27 files changed, 806 insertions(+), 774 deletions(-) rename Netch/Controllers/{ => EncryptedProxy}/SSController.cs (74%) rename Netch/Controllers/{ => EncryptedProxy}/SSRController.cs (85%) rename Netch/Controllers/{ => EncryptedProxy}/TrojanController.cs (82%) rename Netch/Controllers/{ => EncryptedProxy}/VMessController.cs (95%) create mode 100644 Netch/Controllers/Interface/EncryptedProxy.cs create mode 100644 Netch/Controllers/Interface/ModeController.cs delete mode 100644 Netch/Controllers/Interface/ServerClient.cs rename Netch/Controllers/{ => Mode}/HTTPController.cs (85%) create mode 100644 Netch/Controllers/Mode/NFController.cs rename Netch/Controllers/{ => Mode}/TUNTAPController.cs (67%) delete mode 100644 Netch/Controllers/NFController.cs diff --git a/Netch/Controllers/DNSController.cs b/Netch/Controllers/DNSController.cs index 5b3363c8..29a573ed 100644 --- a/Netch/Controllers/DNSController.cs +++ b/Netch/Controllers/DNSController.cs @@ -1,6 +1,5 @@ using System; using System.Diagnostics; -using Netch.Forms; using Netch.Utils; namespace Netch.Controllers @@ -9,9 +8,10 @@ namespace Netch.Controllers { public DNSController() { - MainName = "unbound"; + AkaName = "dns Service"; + MainFile = "unbound"; ExtFiles = new[] {"unbound-service.conf", "forward-zone.conf"}; - ready = BeforeStartProgress(); + InitCheck(); } /// @@ -20,33 +20,36 @@ namespace Netch.Controllers /// public bool Start() { - MainForm.Instance.StatusText(i18N.Translate("Starting dns Service")); + if (!Ready) return false; + + Instance = GetProcess("bin\\unbound.exe"); + Instance.StartInfo.Arguments = "-c unbound-service.conf -v"; + + Instance.OutputDataReceived += OnOutputDataReceived; + Instance.ErrorDataReceived += OnOutputDataReceived; + try { - Instance = MainController.GetProcess("bin\\unbound.exe"); - - Instance.StartInfo.Arguments = "-c unbound-service.conf -v"; - - Instance.OutputDataReceived += OnOutputDataReceived; - Instance.ErrorDataReceived += OnOutputDataReceived; - Instance.Start(); Instance.BeginOutputReadLine(); Instance.BeginErrorReadLine(); - Logging.Info("dns-unbound 启动完毕"); return true; } - catch (Exception) + catch (Exception e) { - Logging.Info("dns-unbound 进程出错"); - Stop(); + Logging.Error("dns-unbound 进程出错:\n" + e); return false; } } - public void OnOutputDataReceived(object sender, DataReceivedEventArgs e) + private void OnOutputDataReceived(object sender, DataReceivedEventArgs e) { WriteLog(e); } + + public override void Stop() + { + StopInstance(); + } } } \ No newline at end of file diff --git a/Netch/Controllers/SSController.cs b/Netch/Controllers/EncryptedProxy/SSController.cs similarity index 74% rename from Netch/Controllers/SSController.cs rename to Netch/Controllers/EncryptedProxy/SSController.cs index bb04cdf4..00bea7d7 100644 --- a/Netch/Controllers/SSController.cs +++ b/Netch/Controllers/EncryptedProxy/SSController.cs @@ -6,12 +6,12 @@ using Netch.Utils; namespace Netch.Controllers { - public class SSController : ServerClient + public class SSController : EncryptedProxy { public SSController() { - MainName = "Shadowsocks"; - ready = BeforeStartProgress(); + MainFile = "Shadowsocks"; + InitCheck(); } public override bool Start(Server server, Mode mode) @@ -27,7 +27,7 @@ namespace Netch.Controllers if (!NativeMethods.Shadowsocks.Info(client, remote, passwd, method)) { State = State.Stopped; - Logging.Info("DLL SS INFO 设置失败!"); + Logging.Error("DLL SS INFO 设置失败!"); return false; } @@ -36,7 +36,7 @@ namespace Netch.Controllers if (!NativeMethods.Shadowsocks.Start()) { State = State.Stopped; - Logging.Info("DLL SS 启动失败!"); + Logging.Error("DLL SS 启动失败!"); return false; } @@ -45,18 +45,13 @@ namespace Netch.Controllers return true; } - Instance = MainController.GetProcess("bin\\Shadowsocks.exe"); - - #region Instance.Arguments + if (!Ready) return false; + Instance = GetProcess("bin\\Shadowsocks.exe"); + Instance.StartInfo.Arguments = $"-s {server.Hostname} -p {server.Port} -b {Global.Settings.LocalAddress} -l {Global.Settings.Socks5LocalPort} -m {server.EncryptMethod} -k \"{server.Password}\" -u"; if (!string.IsNullOrWhiteSpace(server.Plugin) && !string.IsNullOrWhiteSpace(server.PluginOption)) - Instance.StartInfo.Arguments = $"-s {server.Hostname} -p {server.Port} -b {Global.Settings.LocalAddress} -l {Global.Settings.Socks5LocalPort} -m {server.EncryptMethod} -k \"{server.Password}\" -u --plugin {server.Plugin} --plugin-opts \"{server.PluginOption}\""; - else - Instance.StartInfo.Arguments = $"-s {server.Hostname} -p {server.Port} -b {Global.Settings.LocalAddress} -l {Global.Settings.Socks5LocalPort} -m {server.EncryptMethod} -k \"{server.Password}\" -u"; + Instance.StartInfo.Arguments += $" --plugin {server.Plugin} --plugin-opts \"{server.PluginOption}\""; if (mode.BypassChina) Instance.StartInfo.Arguments += " --acl default.acl"; - - #endregion - Instance.OutputDataReceived += OnOutputDataReceived; Instance.ErrorDataReceived += OnOutputDataReceived; @@ -64,6 +59,7 @@ namespace Netch.Controllers Instance.Start(); Instance.BeginOutputReadLine(); Instance.BeginErrorReadLine(); + for (var i = 0; i < 1000; i++) { Thread.Sleep(10); @@ -72,14 +68,14 @@ namespace Netch.Controllers if (State == State.Stopped) { - Logging.Info("SS 进程启动失败"); + Logging.Error("SS 进程启动失败"); Stop(); return false; } } - Logging.Info("SS 进程启动超时"); + Logging.Error("SS 进程启动超时"); Stop(); return false; } @@ -87,10 +83,11 @@ namespace Netch.Controllers /// /// SSController 停止 /// - public new void Stop() + public override void Stop() { - base.Stop(); if (Global.Settings.BootShadowsocksFromDLL) NativeMethods.Shadowsocks.Stop(); + else + StopInstance(); } public override void OnOutputDataReceived(object sender, DataReceivedEventArgs e) diff --git a/Netch/Controllers/SSRController.cs b/Netch/Controllers/EncryptedProxy/SSRController.cs similarity index 85% rename from Netch/Controllers/SSRController.cs rename to Netch/Controllers/EncryptedProxy/SSRController.cs index 9df0d015..d11975e0 100644 --- a/Netch/Controllers/SSRController.cs +++ b/Netch/Controllers/EncryptedProxy/SSRController.cs @@ -5,23 +5,23 @@ using Netch.Utils; namespace Netch.Controllers { - public class SSRController : ServerClient + public class SSRController : EncryptedProxy { public SSRController() { - MainName = "ShadowsocksR"; - ready = BeforeStartProgress(); + MainFile = "ShadowsocksR"; + InitCheck(); } public override bool Start(Server server, Mode mode) { - Instance = MainController.GetProcess("bin\\ShadowsocksR.exe"); + if (!Ready) return false; + + Instance = GetProcess("bin\\ShadowsocksR.exe"); Instance.StartInfo.FileName = "bin\\ShadowsocksR.exe"; Instance.OutputDataReceived += OnOutputDataReceived; Instance.ErrorDataReceived += OnOutputDataReceived; - #region Instance.Arguments - Instance.StartInfo.Arguments = $"-s {server.Hostname} -p {server.Port} -k \"{server.Password}\" -m {server.EncryptMethod} -t 120"; if (!string.IsNullOrEmpty(server.Protocol)) @@ -42,8 +42,6 @@ namespace Netch.Controllers if (mode.BypassChina) Instance.StartInfo.Arguments += " --acl default.acl"; - #endregion - State = State.Starting; Instance.Start(); Instance.BeginOutputReadLine(); @@ -57,14 +55,14 @@ namespace Netch.Controllers if (State == State.Stopped) { - Logging.Info("SSR 进程启动失败"); + Logging.Error("SSR 进程启动失败"); Stop(); return false; } } - Logging.Info("SSR 进程启动超时"); + Logging.Error("SSR 进程启动超时"); Stop(); return false; } @@ -81,5 +79,10 @@ namespace Netch.Controllers else if (e.Data.Contains("Invalid config path") || e.Data.Contains("usage")) State = State.Stopped; } } + + public override void Stop() + { + StopInstance(); + } } } \ No newline at end of file diff --git a/Netch/Controllers/TrojanController.cs b/Netch/Controllers/EncryptedProxy/TrojanController.cs similarity index 82% rename from Netch/Controllers/TrojanController.cs rename to Netch/Controllers/EncryptedProxy/TrojanController.cs index 25ad80de..090609b1 100644 --- a/Netch/Controllers/TrojanController.cs +++ b/Netch/Controllers/EncryptedProxy/TrojanController.cs @@ -2,24 +2,23 @@ using System.Diagnostics; using System.IO; using System.Threading; -using Netch.Forms; using Netch.Models; using Netch.Utils; using Newtonsoft.Json; namespace Netch.Controllers { - public class TrojanController : ServerClient + public class TrojanController : EncryptedProxy { public TrojanController() { - MainName = "Trojan"; - ready = BeforeStartProgress(); + MainFile = "Trojan"; + InitCheck(); } public override bool Start(Server server, Mode mode) { - MainForm.Instance.StatusText(i18N.Translate("Starting Trojan")); + if (!Ready) return false; File.WriteAllText("data\\last.json", JsonConvert.SerializeObject(new Trojan { @@ -33,7 +32,7 @@ namespace Netch.Controllers } })); - Instance = MainController.GetProcess("bin\\Trojan.exe"); + Instance = GetProcess("bin\\Trojan.exe"); Instance.StartInfo.Arguments = "-c ..\\data\\last.json"; Instance.OutputDataReceived += OnOutputDataReceived; Instance.ErrorDataReceived += OnOutputDataReceived; @@ -50,14 +49,14 @@ namespace Netch.Controllers if (State == State.Stopped) { - Logging.Info("Trojan 进程启动失败"); + Logging.Error("Trojan 进程启动失败"); Stop(); return false; } } - Logging.Info("Trojan 进程启动超时"); + Logging.Error("Trojan 进程启动超时"); Stop(); return false; } @@ -74,5 +73,10 @@ namespace Netch.Controllers else if (e.Data.Contains("exiting")) State = State.Stopped; } } + + public override void Stop() + { + StopInstance(); + } } } \ No newline at end of file diff --git a/Netch/Controllers/VMessController.cs b/Netch/Controllers/EncryptedProxy/VMessController.cs similarity index 95% rename from Netch/Controllers/VMessController.cs rename to Netch/Controllers/EncryptedProxy/VMessController.cs index 5c782145..944ad063 100644 --- a/Netch/Controllers/VMessController.cs +++ b/Netch/Controllers/EncryptedProxy/VMessController.cs @@ -9,16 +9,17 @@ using VMess = Netch.Models.Information.VMess; namespace Netch.Controllers { - public class VMessController : ServerClient + public class VMessController : EncryptedProxy { public VMessController() { - MainName = "v2ray"; - ready = BeforeStartProgress(); + MainFile = "v2ray"; + InitCheck(); } public override bool Start(Server server, Mode mode) { + if (!Ready) return false; File.WriteAllText("data\\last.json", JsonConvert.SerializeObject(new VMess.Config { inbounds = new List @@ -167,7 +168,7 @@ namespace Netch.Controllers } })); - Instance = MainController.GetProcess("bin\\v2ray.exe"); + Instance = GetProcess("bin\\v2ray.exe"); Instance.StartInfo.Arguments = "-config ..\\data\\last.json"; Instance.OutputDataReceived += OnOutputDataReceived; @@ -190,14 +191,14 @@ namespace Netch.Controllers if (State == State.Stopped) { - Logging.Info("V2Ray 进程启动失败"); + Logging.Error("V2Ray 进程启动失败"); Stop(); return false; } } - Logging.Info("V2Ray 进程启动超时"); + Logging.Error("V2Ray 进程启动超时"); Stop(); return false; } @@ -214,5 +215,10 @@ namespace Netch.Controllers else if (e.Data.Contains("config file not readable") || e.Data.Contains("failed to")) State = State.Stopped; } } + + public override void Stop() + { + StopInstance(); + } } } \ No newline at end of file diff --git a/Netch/Controllers/Interface/Controller.cs b/Netch/Controllers/Interface/Controller.cs index e5a5ce2f..76ca45e9 100644 --- a/Netch/Controllers/Interface/Controller.cs +++ b/Netch/Controllers/Interface/Controller.cs @@ -6,8 +6,18 @@ using Netch.Utils; namespace Netch.Controllers { - public class Controller + public abstract class Controller { + /// + /// 控制器名 + /// + /// 未赋值会在 赋值为 + /// + public string AkaName; + + /// + /// 其他需要文件 + /// protected string[] ExtFiles; /// @@ -16,21 +26,26 @@ namespace Netch.Controllers public Process Instance; /// - /// 程序名 + /// 主程序名(不含扩展名) /// - public string MainName; + public string MainFile; - public bool ready; + /// + /// 运行检查, 由 赋值 + /// + public bool Ready; /// /// 当前状态 /// protected State State = State.Waiting; + public abstract void Stop(); + /// /// 停止 /// - public void Stop() + protected void StopInstance() { try { @@ -40,7 +55,7 @@ namespace Netch.Controllers } catch (Exception e) { - Logging.Info(e.ToString()); + Logging.Error($"停止 {MainFile}.exe 错误:\n" + e); } } @@ -49,53 +64,87 @@ namespace Netch.Controllers /// 杀残留进程,清除日志,检查文件 /// /// - protected bool BeforeStartProgress() + protected void InitCheck() { + if (string.IsNullOrEmpty(AkaName)) AkaName = MainFile; + var result = false; // 杀残留 - MainController.KillProcessByName(MainName); + MainController.KillProcessByName(MainFile); // 清日志 try { - if (File.Exists($"logging\\{MainName}.log")) File.Delete($"logging\\{MainName}.log"); + if (File.Exists($"logging\\{AkaName}.log")) File.Delete($"logging\\{AkaName}.log"); } catch (Exception) { - // ignore + // ignored } // 检查文件 - if (!File.Exists($"bin\\{MainName}.exe")) Logging.Info($"bin\\{MainName}.exe 文件不存在"); + var mainResult = true; + var extResult = true; + if (!string.IsNullOrEmpty(MainFile) && !File.Exists($"bin\\{MainFile}.exe")) + { + mainResult = false; + Logging.Error($"主程序 bin\\{MainFile}.exe 不存在"); + } if (ExtFiles == null) - result = true; + extResult = true; else foreach (var f in ExtFiles) if (!File.Exists($"bin\\{f}")) - Logging.Info($"bin\\{f}.exe 文件不存在"); + { + extResult = false; + Logging.Error($"附加文件 bin\\{f} 不存在"); + } - if (!ready) Logging.Info(MainName + "未能就绪"); - return result; + result = extResult && mainResult; + if (!result) + Logging.Error(AkaName + " 未就绪"); + Ready = result; } /// /// 写日志 /// - /// - /// e是否为空 - public bool WriteLog(DataReceivedEventArgs e) + /// + /// 是否为空 + protected bool WriteLog(DataReceivedEventArgs std) { - if (string.IsNullOrWhiteSpace(e.Data)) return false; + if (string.IsNullOrWhiteSpace(std.Data)) return false; try + { - File.AppendAllText($"logging\\{MainName}.log", $@"{e.Data}{Global.EOF}"); + File.AppendAllText($"logging\\{AkaName}.log", $@"{std.Data}{Global.EOF}"); } - catch (Exception exception) + catch (Exception e) { - Logging.Info($"写入{MainName}日志失败" + exception); + Logging.Error($"写入{AkaName}日志错误:\n" + e); } return true; } + + public static Process GetProcess(string path = null, bool redirectStd = true) + { + var p = new Process + { + StartInfo = + { + Arguments = "", + WorkingDirectory = $"{Global.NetchDir}\\bin", + CreateNoWindow = true, + RedirectStandardError = redirectStd, + RedirectStandardInput = redirectStd, + RedirectStandardOutput = redirectStd, + UseShellExecute = false + }, + EnableRaisingEvents = true + }; + if (path != null) p.StartInfo.FileName = Path.GetFullPath(path); + return p; + } } } \ No newline at end of file diff --git a/Netch/Controllers/Interface/EncryptedProxy.cs b/Netch/Controllers/Interface/EncryptedProxy.cs new file mode 100644 index 00000000..e036c346 --- /dev/null +++ b/Netch/Controllers/Interface/EncryptedProxy.cs @@ -0,0 +1,18 @@ +using System.Diagnostics; +using Netch.Models; + +namespace Netch.Controllers +{ + public abstract class EncryptedProxy : Controller + { + /// + /// 启动 + /// + /// 服务器 + /// 模式 + /// 是否启动成功 + public abstract bool Start(Server server, Mode mode); + + public abstract void OnOutputDataReceived(object sender, DataReceivedEventArgs e); + } +} \ No newline at end of file diff --git a/Netch/Controllers/Interface/ModeController.cs b/Netch/Controllers/Interface/ModeController.cs new file mode 100644 index 00000000..696320af --- /dev/null +++ b/Netch/Controllers/Interface/ModeController.cs @@ -0,0 +1,15 @@ +using Netch.Models; + +namespace Netch.Controllers +{ + public abstract class ModeController : Controller + { + /// + /// 启动 + /// + /// 服务器 + /// 模式 + /// 是否成功 + public abstract bool Start(Server server, Mode mode); + } +} \ No newline at end of file diff --git a/Netch/Controllers/Interface/ServerClient.cs b/Netch/Controllers/Interface/ServerClient.cs deleted file mode 100644 index 40db32f0..00000000 --- a/Netch/Controllers/Interface/ServerClient.cs +++ /dev/null @@ -1,32 +0,0 @@ -using System.Diagnostics; -using Netch.Models; - -namespace Netch.Controllers -{ - public abstract class ServerClient : Controller - { - /// - /// 启动 - /// - /// 服务器 - /// 模式 - /// 是否启动成功 - public abstract bool Start(Server server, Mode mode); - - /// - /// ServerClient 停止 - /// - /// 注意 对象类型 以调用子类 Stop() 方法 - /// - public new void Stop() - { - base.Stop(); - - // SSController Stop() - // 不能自动转换对象类型的兼容代码 :( - if (Global.Settings.BootShadowsocksFromDLL) NativeMethods.Shadowsocks.Stop(); - } - - public abstract void OnOutputDataReceived(object sender, DataReceivedEventArgs e); - } -} \ No newline at end of file diff --git a/Netch/Controllers/MainController.cs b/Netch/Controllers/MainController.cs index 6ce17c77..2216f09d 100644 --- a/Netch/Controllers/MainController.cs +++ b/Netch/Controllers/MainController.cs @@ -1,7 +1,6 @@ using System; using System.ComponentModel; using System.Diagnostics; -using System.IO; using System.Runtime.InteropServices; using System.Threading.Tasks; using Netch.Forms; @@ -12,29 +11,15 @@ namespace Netch.Controllers { public class MainController { - /// - /// HTTP 控制器 - /// - public HTTPController pHTTPController; + public EncryptedProxy pEncryptedProxyController; - /// - /// NF 控制器 - /// - public NFController pNFController; + public ModeController pModeController; /// /// NTT 控制器 /// public NTTController pNTTController; - public ServerClient pServerClientController; - - - /// - /// TUN/TAP 控制器 - /// - public TUNTAPController pTUNTAPController; - [DllImport("dnsapi", EntryPoint = "DnsFlushResolverCache")] public static extern uint FlushDNSResolverCache(); @@ -46,6 +31,7 @@ namespace Netch.Controllers /// 是否启动成功 public bool Start(Server server, Mode mode) { + pNTTController ??= new NTTController(); FlushDNSResolverCache(); var result = false; @@ -58,61 +44,60 @@ namespace Netch.Controllers switch (server.Type) { case "SS": - pServerClientController = new SSController(); + pEncryptedProxyController = new SSController(); break; case "SSR": - pServerClientController = new SSRController(); + pEncryptedProxyController = new SSRController(); break; case "VMess": - pServerClientController = new VMessController(); + pEncryptedProxyController = new VMessController(); break; case "Trojan": - pServerClientController = new TrojanController(); + pEncryptedProxyController = new TrojanController(); break; } - MainForm.Instance.StatusText(i18N.Translate("Starting ", pServerClientController.MainName)); - if (pServerClientController.ready) result = pServerClientController.Start(server, mode); + MainForm.Instance.StatusText(i18N.Translate("Starting ", pEncryptedProxyController.AkaName)); + if (pEncryptedProxyController.Ready) result = pEncryptedProxyController.Start(server, mode); } - if (result) // If server runs,then run mode + if (result) + { + // 加密代理已启动 switch (mode.Type) { case 0: // 进程代理模式 - pNFController ??= new NFController(); - pNTTController ??= new NTTController(); - if (pNFController.ready) result = pNFController.Start(server, mode, false); - - if (!result && pNFController.ready) - { - MainForm.Instance.StatusText(i18N.Translate("Restarting Redirector")); - Logging.Info("正常启动失败后尝试停止驱动服务再重新启动"); - //正常启动失败后尝试停止驱动服务再重新启动 - result = pNFController.Start(server, mode, true); - } - - if (result) - Task.Run(() => pNTTController.Start()); + pModeController = new NFController(); break; case 1: // TUN/TAP 黑名单代理模式 case 2: // TUN/TAP 白名单代理模式 - pTUNTAPController ??= new TUNTAPController(); - pNTTController ??= new NTTController(); - result = pTUNTAPController.Start(server, mode); + pModeController = new TUNTAPController(); + break; + case 3: + case 5: + pModeController = new HTTPController(); + break; + case 4: // Socks5 代理模式,不需要启动额外的Server + result = true; + break; + } + + if (pModeController != null && pModeController.Ready) + { + MainForm.Instance.StatusText(i18N.Translate("Starting ", pModeController.AkaName)); + result = pModeController.Start(server, mode); + } + + switch (mode.Type) + { + case 0: + case 1: + case 2: if (result) Task.Run(() => pNTTController.Start()); break; - case 3: // HTTP 系统代理和 Socks5 和 HTTP 代理模式 - case 5: - pHTTPController ??= new HTTPController(); - result = pHTTPController.Start(server, mode); - break; - case 4: // Socks5 代理模式,不需要启动额外的Server - break; - default: - result = false; - break; } + } if (!result) Stop(); @@ -124,36 +109,8 @@ namespace Netch.Controllers /// public void Stop() { - pServerClientController?.Stop(); - - if (pNFController != null) - pNFController.Stop(); - else if (pTUNTAPController != null) - pTUNTAPController.Stop(); - else - pHTTPController?.Stop(); - - pNTTController?.Stop(); - } - - public static Process GetProcess(string path = null) - { - var p = new Process - { - StartInfo = - { - Arguments = "", - WorkingDirectory = $"{Global.NetchDir}\\bin", - CreateNoWindow = true, - RedirectStandardError = true, - RedirectStandardInput = true, - RedirectStandardOutput = true, - UseShellExecute = false - }, - EnableRaisingEvents = true - }; - if (path != null) p.StartInfo.FileName = Path.GetFullPath(path); - return p; + pEncryptedProxyController?.Stop(); + pModeController?.Stop(); } public static void KillProcessByName(string name) @@ -166,11 +123,11 @@ namespace Netch.Controllers } catch (Win32Exception e) { - Logging.Info($"结束进程 {name} 错误: " + e.Message); + Logging.Error($"结束进程 {name} 错误:\n" + e); } catch (Exception) { - // ignore + // ignored } } } diff --git a/Netch/Controllers/HTTPController.cs b/Netch/Controllers/Mode/HTTPController.cs similarity index 85% rename from Netch/Controllers/HTTPController.cs rename to Netch/Controllers/Mode/HTTPController.cs index 9a92feff..df320b9b 100644 --- a/Netch/Controllers/HTTPController.cs +++ b/Netch/Controllers/Mode/HTTPController.cs @@ -7,7 +7,7 @@ using Netch.Utils; namespace Netch.Controllers { - public class HTTPController + public class HTTPController : ModeController { /// /// 实例 @@ -17,14 +17,22 @@ namespace Netch.Controllers private string prevBypass, prevHTTP, prevPAC; private bool prevEnabled; + public HTTPController() + { + AkaName = "HTTP"; + Ready = true; + } + /// /// 启动 /// /// 服务器 /// 模式 /// 是否启动成功 - public bool Start(Server server, Mode mode) + public override bool Start(Server server, Mode mode) { + if (!Ready) return false; + RecordPrevious(); try { @@ -45,7 +53,7 @@ namespace Netch.Controllers { if (MessageBoxX.Show(i18N.Translate("Failed to set the system proxy, it may be caused by the lack of dependent programs. Do you want to jump to Netch's official website to download dependent programs?"), confirm: true) == DialogResult.OK) Process.Start("https://netch.org/#/?id=%e4%be%9d%e8%b5%96"); - Logging.Info("设置系统代理失败" + e); + Logging.Error("设置系统代理失败" + e); return false; } @@ -72,18 +80,11 @@ namespace Netch.Controllers /// /// 停止 /// - public void Stop() + public override void Stop() { try { - try - { - pPrivoxyController.Stop(); - } - catch (Exception e) - { - Logging.Info(e.ToString()); - } + pPrivoxyController.Stop(); NativeMethods.SetGlobal(prevHTTP, prevBypass); if (prevPAC != "") @@ -94,7 +95,7 @@ namespace Netch.Controllers } catch (Exception e) { - Logging.Info(e.ToString()); + Logging.Error("停止HTTP控制器错误:\n" + e); } } } diff --git a/Netch/Controllers/Mode/NFController.cs b/Netch/Controllers/Mode/NFController.cs new file mode 100644 index 00000000..afeff92c --- /dev/null +++ b/Netch/Controllers/Mode/NFController.cs @@ -0,0 +1,269 @@ +using System; +using System.Diagnostics; +using System.IO; +using System.ServiceProcess; +using System.Threading; +using System.Threading.Tasks; +using Netch.Forms; +using Netch.Models; +using Netch.Utils; +using nfapinet; + +namespace Netch.Controllers +{ + public class NFController : ModeController + { + /// + /// 流量变动处理器 + /// + /// 上传 + /// 下载 + public delegate void BandwidthUpdateHandler(long upload, long download); + + private readonly string _binDriverPath; + + private readonly string _driverPath = $"{Environment.SystemDirectory}\\drivers\\netfilter2.sys"; + private readonly ServiceController _service = new ServiceController("netfilter2"); + private string _systemDriverVersion; + + public NFController() + { + MainFile = "Redirector"; + InitCheck(); + + // 驱动版本 + _systemDriverVersion = FileVersionInfo.GetVersionInfo(_driverPath).FileVersion; + // 生成系统版本 + var winNTver = $"{Environment.OSVersion.Version.Major.ToString()}.{Environment.OSVersion.Version.Minor.ToString()}"; + var driverName = ""; + switch (winNTver) + { + case "10.0": + driverName = "Win-10.sys"; + break; + case "6.3": + case "6.2": + driverName = "Win-8.sys"; + break; + case "6.1": + case "6.0": + driverName = "Win-7.sys"; + break; + default: + Logging.Error($"不支持的系统版本:{winNTver}"); + Ready = false; + return; + } + + _binDriverPath = "bin\\" + driverName; + } + + /// + /// 流量变动事件 + /// + public event BandwidthUpdateHandler OnBandwidthUpdated; + + public override bool Start(Server server, Mode mode) + { + if (!CheckDriverReady()) + { + if (File.Exists(_driverPath)) + UninstallDriver(); + if (!InstallDriver()) + return false; + } + + var processList = ""; + foreach (var proc in mode.Rule) + processList += proc + ","; + processList += "NTT.exe"; + + Instance = GetProcess("bin\\Redirector.exe"); + if (server.Type != "Socks5") + { + Instance.StartInfo.Arguments += $"-r 127.0.0.1:{Global.Settings.Socks5LocalPort} -p \"{processList}\""; + } + + else + { + var result = DNS.Lookup(server.Hostname); + if (result == null) + { + Logging.Info("无法解析服务器 IP 地址"); + return false; + } + + Instance.StartInfo.Arguments += $"-r {result}:{server.Port} -p \"{processList}\""; + if (!string.IsNullOrWhiteSpace(server.Username) && !string.IsNullOrWhiteSpace(server.Password)) Instance.StartInfo.Arguments += $" -username \"{server.Username}\" -password \"{server.Password}\""; + } + + Instance.StartInfo.Arguments += $" -t {Global.Settings.RedirectorTCPPort}"; + Instance.OutputDataReceived += OnOutputDataReceived; + Instance.ErrorDataReceived += OnOutputDataReceived; + + for (var i = 0; i < 2; i++) + { + State = State.Starting; + Instance.Start(); + Instance.BeginOutputReadLine(); + Instance.BeginErrorReadLine(); + + for (var j = 0; j < 40; j++) + { + Thread.Sleep(250); + + if (State == State.Started) return true; + } + + Logging.Error("NF 进程启动超时"); + Stop(); + if (!RestartService()) return false; + } + + return false; + } + + private bool RestartService() + { + try + { + switch (_service.Status) + { + // 启动驱动服务 + case ServiceControllerStatus.Running: + // 防止其他程序占用 重置 NF 百万连接数限制 + _service.Stop(); + _service.WaitForStatus(ServiceControllerStatus.Stopped); + MainForm.Instance.StatusText(i18N.Translate("Starting netfilter2 Service")); + _service.Start(); + break; + case ServiceControllerStatus.Stopped: + MainForm.Instance.StatusText(i18N.Translate("Starting netfilter2 Service")); + _service.Start(); + break; + } + } + catch (Exception e) + { + Logging.Error("启动驱动服务失败:\n" + e); + + var result = NFAPI.nf_registerDriver("netfilter2"); + if (result != NF_STATUS.NF_STATUS_SUCCESS) + { + Logging.Error($"注册驱动失败,返回值:{result}"); + return false; + } + + Logging.Info("注册驱动成功"); + } + + return true; + } + + private bool CheckDriverReady() + { + // 检查驱动是否存在 + if (!File.Exists(_driverPath)) return false; + + // 检查驱动版本号 + var binVersion = FileVersionInfo.GetVersionInfo(_binDriverPath).FileVersion; + return _systemDriverVersion.Equals(binVersion); + } + + public bool UninstallDriver() + { + try + { + var service = new ServiceController("netfilter2"); + if (service.Status == ServiceControllerStatus.Running) + { + service.Stop(); + service.WaitForStatus(ServiceControllerStatus.Stopped); + } + } + catch (Exception) + { + // ignored + } + + if (!File.Exists(_driverPath)) return true; + try + { + NFAPI.nf_unRegisterDriver("netfilter2"); + + File.Delete(_driverPath); + _systemDriverVersion = ""; + return true; + } + catch (Exception ex) + { + throw ex; + } + } + + public bool InstallDriver() + { + if (!Ready) return false; + Logging.Info("安装驱动中"); + try + { + File.Copy(_binDriverPath, _driverPath); + } + catch (Exception e) + { + Logging.Error("驱动复制失败\n" + e); + return false; + } + + MainForm.Instance.StatusText(i18N.Translate("Register driver")); + // 注册驱动文件 + var result = NFAPI.nf_registerDriver("netfilter2"); + if (result == NF_STATUS.NF_STATUS_SUCCESS) + { + _systemDriverVersion = FileVersionInfo.GetVersionInfo(_driverPath).FileVersion; + Logging.Info($"驱动安装成功,当前驱动版本:{_systemDriverVersion}"); + } + else + { + Logging.Error($"注册驱动失败,返回值:{result}"); + return false; + } + + return true; + } + + private void OnOutputDataReceived(object sender, DataReceivedEventArgs e) + { + if (!WriteLog(e)) return; + if (State == State.Starting) + { + if (Instance.HasExited) + State = State.Stopped; + else if (e.Data.Contains("Started")) + State = State.Started; + else if (e.Data.Contains("Failed") || e.Data.Contains("Unable")) State = State.Stopped; + } + else if (State == State.Started) + { + if (e.Data.StartsWith("[APP][Bandwidth]")) + { + var splited = e.Data.Replace("[APP][Bandwidth]", "").Trim().Split(','); + if (splited.Length == 2) + { + var uploadSplited = splited[0].Split(':'); + var downloadSplited = splited[1].Split(':'); + + if (uploadSplited.Length == 2 && downloadSplited.Length == 2) + if (long.TryParse(uploadSplited[1], out var upload) && long.TryParse(downloadSplited[1], out var download)) + Task.Run(() => OnBandwidthUpdated(upload, download)); + } + } + } + } + + public override void Stop() + { + StopInstance(); + } + } +} \ No newline at end of file diff --git a/Netch/Controllers/TUNTAPController.cs b/Netch/Controllers/Mode/TUNTAPController.cs similarity index 67% rename from Netch/Controllers/TUNTAPController.cs rename to Netch/Controllers/Mode/TUNTAPController.cs index ea759620..479756bc 100644 --- a/Netch/Controllers/TUNTAPController.cs +++ b/Netch/Controllers/Mode/TUNTAPController.cs @@ -1,9 +1,13 @@ -using System.Collections.Generic; +using System; +using System.Collections.Generic; using System.Diagnostics; using System.IO; using System.Net; +using System.Net.NetworkInformation; +using System.Net.Sockets; using System.Text; using System.Threading; +using System.Windows.Forms; using Netch.Forms; using Netch.Models; using Netch.Properties; @@ -11,32 +15,28 @@ using Netch.Utils; namespace Netch.Controllers { - public class TUNTAPController : Controller + public class TUNTAPController : ModeController { // ByPassLan IP - private readonly List BypassLanIPs = new List {"10.0.0.0/8", "172.16.0.0/16", "192.168.0.0/16"}; + private readonly List _bypassLanIPs = new List {"10.0.0.0/8", "172.16.0.0/16", "192.168.0.0/16"}; + + private Mode _savedMode = new Mode(); + private Server _savedServer = new Server(); + + /// + /// 服务器 IP 地址 + /// + private IPAddress[] _serverAddresses = new IPAddress[0]; /// /// 本地 DNS 服务控制器 /// public DNSController pDNSController = new DNSController(); - public Mode SavedMode = new Mode(); - - /// - /// 保存传入的规则 - /// - public Server SavedServer = new Server(); - - /// - /// 服务器 IP 地址 - /// - public IPAddress[] ServerAddresses = new IPAddress[0]; - public TUNTAPController() { - MainName = "tun2socks"; - ready = BeforeStartProgress(); + MainFile = "tun2socks"; + InitCheck(); } /// @@ -45,16 +45,16 @@ namespace Netch.Controllers public bool Configure() { // 查询服务器 IP 地址 - var destination = Dns.GetHostAddressesAsync(SavedServer.Hostname); + var destination = Dns.GetHostAddressesAsync(_savedServer.Hostname); if (destination.Wait(1000)) { if (destination.Result.Length == 0) return false; - ServerAddresses = destination.Result; + _serverAddresses = destination.Result; } // 搜索出口 - return Configuration.SearchOutbounds(); + return SearchOutbounds(); } /// @@ -65,12 +65,12 @@ namespace Netch.Controllers MainForm.Instance.StatusText(i18N.Translate("SetupBypass")); Logging.Info("设置绕行规则 → 设置让服务器 IP 走直连"); // 让服务器 IP 走直连 - foreach (var address in ServerAddresses) + foreach (var address in _serverAddresses) if (!IPAddress.IsLoopback(address)) NativeMethods.CreateRoute(address.ToString(), 32, Global.Adapter.Gateway.ToString(), Global.Adapter.Index); // 处理模式的绕过中国 - if (SavedMode.BypassChina) + if (_savedMode.BypassChina) { Logging.Info("设置绕行规则 → 处理模式的绕过中国"); using (var sr = new StringReader(Encoding.UTF8.GetString(Resources.CNIP))) @@ -98,7 +98,7 @@ namespace Netch.Controllers Logging.Info("设置绕行规则 → 处理绕过局域网 IP"); // 处理绕过局域网 IP - foreach (var ip in BypassLanIPs) + foreach (var ip in _bypassLanIPs) { var info = ip.Split('/'); var address = IPAddress.Parse(info[0]); @@ -106,7 +106,7 @@ namespace Netch.Controllers if (!IPAddress.IsLoopback(address)) NativeMethods.CreateRoute(address.ToString(), int.Parse(info[1]), Global.Adapter.Gateway.ToString(), Global.Adapter.Index); } - if (SavedMode.Type == 2) // 处理仅规则内走直连 + if (_savedMode.Type == 2) // 处理仅规则内走直连 { Logging.Info("设置绕行规则 → 处理仅规则内走直连"); // 将 TUN/TAP 网卡权重放到最高 @@ -129,14 +129,14 @@ namespace Netch.Controllers { State = State.Stopped; - foreach (var address in ServerAddresses) NativeMethods.DeleteRoute(address.ToString(), 32, Global.Adapter.Gateway.ToString(), Global.Adapter.Index); + foreach (var address in _serverAddresses) NativeMethods.DeleteRoute(address.ToString(), 32, Global.Adapter.Gateway.ToString(), Global.Adapter.Index); return false; } Logging.Info("设置绕行规则 → 创建规则路由"); // 创建规则路由 - foreach (var ip in SavedMode.Rule) + foreach (var ip in _savedMode.Rule) { var info = ip.Split('/'); @@ -145,10 +145,10 @@ namespace Netch.Controllers NativeMethods.CreateRoute(info[0], prefix, Global.Adapter.Gateway.ToString(), Global.Adapter.Index); } } - else if (SavedMode.Type == 1) // 处理仅规则内走代理 + else if (_savedMode.Type == 1) // 处理仅规则内走代理 { Logging.Info("设置绕行规则->处理仅规则内走代理"); - foreach (var ip in SavedMode.Rule) + foreach (var ip in _savedMode.Rule) { var info = ip.Split('/'); @@ -211,11 +211,11 @@ namespace Netch.Controllers /// public bool ClearBypass() { - if (SavedMode.Type == 2) + if (_savedMode.Type == 2) { NativeMethods.DeleteRoute("0.0.0.0", 0, Global.Settings.TUNTAP.Gateway, Global.TUNTAP.Index, 10); - foreach (var ip in SavedMode.Rule) + foreach (var ip in _savedMode.Rule) { var info = ip.Split('/'); @@ -224,9 +224,9 @@ namespace Netch.Controllers NativeMethods.DeleteRoute(info[0], prefix, Global.Adapter.Gateway.ToString(), Global.Adapter.Index); } } - else if (SavedMode.Type == 1) + else if (_savedMode.Type == 1) { - foreach (var ip in SavedMode.Rule) + foreach (var ip in _savedMode.Rule) { var info = ip.Split('/'); @@ -278,7 +278,7 @@ namespace Netch.Controllers if (!IPAddress.IsLoopback(address)) NativeMethods.DeleteRoute(address.ToString(), int.Parse(info[1]), Global.Adapter.Gateway.ToString(), Global.Adapter.Index); } - foreach (var ip in BypassLanIPs) + foreach (var ip in _bypassLanIPs) { var info = ip.Split('/'); var address = IPAddress.Parse(info[0]); @@ -286,7 +286,7 @@ namespace Netch.Controllers if (!IPAddress.IsLoopback(address)) NativeMethods.DeleteRoute(address.ToString(), int.Parse(info[1]), Global.Adapter.Gateway.ToString(), Global.Adapter.Index); } - if (SavedMode.BypassChina) + if (_savedMode.BypassChina) using (var sr = new StringReader(Encoding.UTF8.GetString(Resources.CNIP))) { string text; @@ -299,24 +299,21 @@ namespace Netch.Controllers } } - foreach (var address in ServerAddresses) + foreach (var address in _serverAddresses) if (!IPAddress.IsLoopback(address)) NativeMethods.DeleteRoute(address.ToString(), 32, Global.Adapter.Gateway.ToString(), Global.Adapter.Index); return true; } - /// - /// 启动 - /// - /// 配置 - /// 是否成功 - public bool Start(Server server, Mode mode) + public override bool Start(Server server, Mode mode) { + if (!Ready) return false; + MainForm.Instance.StatusText(i18N.Translate("Starting Tap")); - SavedMode = mode; - SavedServer = server; + _savedMode = mode; + _savedServer = server; if (!Configure()) return false; @@ -324,7 +321,7 @@ namespace Netch.Controllers SetupBypass(); Logging.Info("设置绕行规则完毕"); - Instance = MainController.GetProcess("bin\\tun2socks.exe"); + Instance = GetProcess("bin\\tun2socks.exe"); var adapterName = TUNTAP.GetName(Global.TUNTAP.ComponentID); Logging.Info($"tun2sock使用适配器:{adapterName}"); @@ -353,15 +350,13 @@ namespace Netch.Controllers if (Global.Settings.TUNTAP.UseFakeDNS) dns += " -fakeDns"; if (server.Type == "Socks5") - Instance.StartInfo.Arguments = string.Format("-proxyServer {0}:{1} -tunAddr {2} -tunMask {3} -tunGw {4} -tunDns {5} -tunName \"{6}\"", server.Hostname, server.Port, Global.Settings.TUNTAP.Address, Global.Settings.TUNTAP.Netmask, Global.Settings.TUNTAP.Gateway, dns, adapterName); + Instance.StartInfo.Arguments = $"-proxyServer {server.Hostname}:{server.Port} -tunAddr {Global.Settings.TUNTAP.Address} -tunMask {Global.Settings.TUNTAP.Netmask} -tunGw {Global.Settings.TUNTAP.Gateway} -tunDns {dns} -tunName \"{adapterName}\""; else - Instance.StartInfo.Arguments = string.Format("-proxyServer 127.0.0.1:{0} -tunAddr {1} -tunMask {2} -tunGw {3} -tunDns {4} -tunName \"{5}\"", Global.Settings.Socks5LocalPort, Global.Settings.TUNTAP.Address, Global.Settings.TUNTAP.Netmask, Global.Settings.TUNTAP.Gateway, dns, adapterName); + Instance.StartInfo.Arguments = $"-proxyServer 127.0.0.1:{Global.Settings.Socks5LocalPort} -tunAddr {Global.Settings.TUNTAP.Address} -tunMask {Global.Settings.TUNTAP.Netmask} -tunGw {Global.Settings.TUNTAP.Gateway} -tunDns {dns} -tunName \"{adapterName}\""; Instance.ErrorDataReceived += OnOutputDataReceived; Instance.OutputDataReceived += OnOutputDataReceived; - Logging.Info(Instance.StartInfo.Arguments); - State = State.Starting; Instance.Start(); Instance.BeginErrorReadLine(); @@ -387,14 +382,14 @@ namespace Netch.Controllers /// /// TUN/TAP停止 /// - public new void Stop() + public override void Stop() { - base.Stop(); + StopInstance(); ClearBypass(); pDNSController.Stop(); } - public void OnOutputDataReceived(object sender, DataReceivedEventArgs e) + private void OnOutputDataReceived(object sender, DataReceivedEventArgs e) { if (!WriteLog(e)) return; if (State == State.Starting) @@ -404,5 +399,113 @@ namespace Netch.Controllers else if (e.Data.Contains("failed") || e.Data.Contains("invalid vconfig file")) State = State.Stopped; } } + + /// + /// 搜索出口 + /// + public static bool SearchOutbounds() + { + Logging.Info("正在搜索出口中"); + + if (Win32Native.GetBestRoute(BitConverter.ToUInt32(IPAddress.Parse("114.114.114.114").GetAddressBytes(), 0), 0, out var pRoute) == 0) + { + Global.Adapter.Index = pRoute.dwForwardIfIndex; + Global.Adapter.Gateway = new IPAddress(pRoute.dwForwardNextHop); + Logging.Info($"当前 网关 地址:{Global.Adapter.Gateway}"); + } + else + { + Logging.Error("GetBestRoute 搜索失败"); + return false; + } + + Logging.Info($"搜索适配器index:{Global.Adapter.Index}"); + var AddressGot = false; + foreach (var adapter in NetworkInterface.GetAllNetworkInterfaces()) + try + { + var adapterProperties = adapter.GetIPProperties(); + var p = adapterProperties.GetIPv4Properties(); + Logging.Info($"检测适配器:{adapter.Name} {adapter.Id} {adapter.Description}, index: {p.Index}"); + + // 通过索引查找对应适配器的 IPv4 地址 + if (p.Index == Global.Adapter.Index) + { + var AdapterIPs = ""; + + foreach (var ip in adapterProperties.UnicastAddresses) + { + if (ip.Address.AddressFamily == AddressFamily.InterNetwork) + { + AddressGot = true; + Global.Adapter.Address = ip.Address; + Logging.Info($"当前出口 IPv4 地址:{Global.Adapter.Address}"); + break; + } + + AdapterIPs = $"{ip.Address} | "; + } + + if (!AddressGot) + { + if (AdapterIPs.Length > 3) + { + AdapterIPs = AdapterIPs.Substring(0, AdapterIPs.Length - 3); + Logging.Info($"所有出口地址:{AdapterIPs}"); + } + + Logging.Error("出口无 IPv4 地址,当前只支持 IPv4 地址"); + return false; + } + + break; + } + } + catch (Exception) + { + // ignored + } + + if (!AddressGot) + { + Logging.Error("无法找到当前使用适配器"); + return false; + } + + // 搜索 TUN/TAP 适配器的索引 + Global.TUNTAP.ComponentID = TUNTAP.GetComponentID(); + if (string.IsNullOrEmpty(Global.TUNTAP.ComponentID)) + { + Logging.Error("未找到可用 TUN/TAP 适配器"); + if (MessageBoxX.Show(i18N.Translate("TUN/TAP driver is not detected. Is it installed now?"), confirm: true) == DialogResult.OK) + { + Configuration.addtap(); + //给点时间,不然立马安装完毕就查找适配器可能会导致找不到适配器ID + Thread.Sleep(1000); + Global.TUNTAP.ComponentID = TUNTAP.GetComponentID(); + } + else + { + return false; + } + + //MessageBoxX.Show(i18N.Translate("Please install TAP-Windows and create an TUN/TAP adapter manually")); + // return false; + } + + foreach (var adapter in NetworkInterface.GetAllNetworkInterfaces()) + if (adapter.Id == Global.TUNTAP.ComponentID) + { + Global.TUNTAP.Adapter = adapter; + Global.TUNTAP.Index = adapter.GetIPProperties().GetIPv4Properties().Index; + + Logging.Info($"找到适配器TUN/TAP:{adapter.Id}"); + + return true; + } + + Logging.Error("无法找到出口"); + return false; + } } } \ No newline at end of file diff --git a/Netch/Controllers/NFController.cs b/Netch/Controllers/NFController.cs deleted file mode 100644 index a67f766e..00000000 --- a/Netch/Controllers/NFController.cs +++ /dev/null @@ -1,269 +0,0 @@ -using System; -using System.Diagnostics; -using System.IO; -using System.ServiceProcess; -using System.Threading; -using System.Threading.Tasks; -using Netch.Forms; -using Netch.Models; -using Netch.Utils; -using nfapinet; - -namespace Netch.Controllers -{ - public class NFController : Controller - { - /// - /// 流量变动处理器 - /// - /// 上传 - /// 下载 - public delegate void BandwidthUpdateHandler(long upload, long download); - - /// 驱动文件路径 - private readonly string _driverPath = $"{Environment.SystemDirectory}\\drivers\\netfilter2.sys"; - - public NFController() - { - MainName = "Redirector"; - ready = BeforeStartProgress(); - } - - /// - /// 流量变动事件 - /// - public event BandwidthUpdateHandler OnBandwidthUpdated; - - /// - /// 启动 - /// - /// 服务器 - /// 模式 - /// 先停止驱动服务再重新启动 - /// 是否成功 - public bool Start(Server server, Mode mode, bool StopServiceAndRestart) - { - if (!StopServiceAndRestart) - MainForm.Instance.StatusText(i18N.Translate("Starting Redirector")); - - // 检查驱动是否存在 - if (File.Exists(_driverPath)) - { - // 生成系统版本 - var version = $"{Environment.OSVersion.Version.Major.ToString()}.{Environment.OSVersion.Version.Minor.ToString()}"; - var driverName = ""; - - switch (version) - { - case "10.0": - driverName = "Win-10.sys"; - break; - case "6.3": - case "6.2": - driverName = "Win-8.sys"; - break; - case "6.1": - case "6.0": - driverName = "Win-7.sys"; - break; - default: - Logging.Info($"不支持的系统版本:{version}"); - return false; - } - - // 检查驱动版本号 - var SystemfileVerInfo = FileVersionInfo.GetVersionInfo(_driverPath); - var BinFileVerInfo = FileVersionInfo.GetVersionInfo(string.Format("bin\\{0}", driverName)); - - if (!SystemfileVerInfo.FileVersion.Equals(BinFileVerInfo.FileVersion)) - { - Logging.Info("开始更新驱动"); - // 需要更新驱动 - try - { - var service = new ServiceController("netfilter2"); - if (service.Status == ServiceControllerStatus.Running) - { - service.Stop(); - service.WaitForStatus(ServiceControllerStatus.Stopped); - } - - NFAPI.nf_unRegisterDriver("netfilter2"); - - //删除老驱动 - File.Delete(_driverPath); - if (!InstallDriver()) - return false; - - Logging.Info($"驱动更新完毕,当前驱动版本:{BinFileVerInfo.FileVersion}"); - } - catch (Exception) - { - Logging.Info("更新驱动出错"); - } - } - } - else - { - if (!InstallDriver()) return false; - } - - try - { - // 启动驱动服务 - var service = new ServiceController("netfilter2"); - if (service.Status == ServiceControllerStatus.Running && StopServiceAndRestart) - { - // 防止其他程序占用 重置 NF 百万连接数限制 - service.Stop(); - service.WaitForStatus(ServiceControllerStatus.Stopped); - MainForm.Instance.StatusText(i18N.Translate("Starting netfilter2 Service")); - service.Start(); - } - else if (service.Status == ServiceControllerStatus.Stopped) - { - MainForm.Instance.StatusText(i18N.Translate("Starting netfilter2 Service")); - service.Start(); - } - } - catch (Exception e) - { - Logging.Info(e.ToString()); - - var result = NFAPI.nf_registerDriver("netfilter2"); - if (result != NF_STATUS.NF_STATUS_SUCCESS) - { - Logging.Info($"注册驱动失败,返回值:{result}"); - return false; - } - } - - var processes = ""; - foreach (var proc in mode.Rule) - { - processes += proc; - processes += ","; - } - - processes += "NTT.exe"; - - Instance = MainController.GetProcess("bin\\Redirector.exe"); - - if (server.Type != "Socks5") - { - Instance.StartInfo.Arguments += $"-r 127.0.0.1:{Global.Settings.Socks5LocalPort} -p \"{processes}\""; - } - else - { - var result = DNS.Lookup(server.Hostname); - if (result == null) - { - Logging.Info("无法解析服务器 IP 地址"); - return false; - } - - Instance.StartInfo.Arguments += $"-r {result}:{server.Port} -p \"{processes}\""; - if (!string.IsNullOrWhiteSpace(server.Username) && !string.IsNullOrWhiteSpace(server.Password)) Instance.StartInfo.Arguments += $" -username \"{server.Username}\" -password \"{server.Password}\""; - } - - Instance.StartInfo.Arguments += $" -t {Global.Settings.RedirectorTCPPort}"; - Logging.Info(Instance.StartInfo.Arguments); - Instance.OutputDataReceived += OnOutputDataReceived; - Instance.ErrorDataReceived += OnOutputDataReceived; - - State = State.Starting; - Instance.Start(); - Instance.BeginOutputReadLine(); - Instance.BeginErrorReadLine(); - - for (var i = 0; i < 10; i++) - { - Thread.Sleep(1000); - - if (State == State.Started) return true; - } - - Logging.Info("NF 进程启动超时"); - Stop(); - return false; - } - - public bool InstallDriver() - { - Logging.Info("安装驱动中"); - // 生成系统版本 - var version = $"{Environment.OSVersion.Version.Major.ToString()}.{Environment.OSVersion.Version.Minor.ToString()}"; - - // 检查系统版本并复制对应驱动 - try - { - switch (version) - { - case "10.0": - File.Copy("bin\\Win-10.sys", _driverPath); - Logging.Info("已复制 Win10 驱动"); - break; - case "6.3": - case "6.2": - File.Copy("bin\\Win-8.sys", _driverPath); - Logging.Info("已复制 Win8 驱动"); - break; - case "6.1": - case "6.0": - File.Copy("bin\\Win-7.sys", _driverPath); - Logging.Info("已复制 Win7 驱动"); - break; - default: - Logging.Info($"不支持的系统版本:{version}"); - return false; - } - } - catch (Exception e) - { - Logging.Info("复制驱动文件失败"); - Logging.Info(e.ToString()); - return false; - } - - MainForm.Instance.StatusText(i18N.Translate("Register driver")); - // 注册驱动文件 - var result = NFAPI.nf_registerDriver("netfilter2"); - if (result != NF_STATUS.NF_STATUS_SUCCESS) - { - Logging.Info($"注册驱动失败,返回值:{result}"); - return false; - } - - return true; - } - - public void OnOutputDataReceived(object sender, DataReceivedEventArgs e) - { - if (!WriteLog(e)) return; - if (State == State.Starting) - { - if (Instance.HasExited) - State = State.Stopped; - else if (e.Data.Contains("Started")) - State = State.Started; - else if (e.Data.Contains("Failed") || e.Data.Contains("Unable")) State = State.Stopped; - } - else if (State == State.Started) - { - if (e.Data.StartsWith("[APP][Bandwidth]")) - { - var splited = e.Data.Replace("[APP][Bandwidth]", "").Trim().Split(','); - if (splited.Length == 2) - { - var uploadSplited = splited[0].Split(':'); - var downloadSplited = splited[1].Split(':'); - - if (uploadSplited.Length == 2 && downloadSplited.Length == 2) - if (long.TryParse(uploadSplited[1], out var upload) && long.TryParse(downloadSplited[1], out var download)) - Task.Run(() => OnBandwidthUpdated(upload, download)); - } - } - } - } - } -} \ No newline at end of file diff --git a/Netch/Controllers/NTTController.cs b/Netch/Controllers/NTTController.cs index 7e9fc39f..80b9c442 100644 --- a/Netch/Controllers/NTTController.cs +++ b/Netch/Controllers/NTTController.cs @@ -12,21 +12,22 @@ namespace Netch.Controllers { public NTTController() { - MainName = "NTT"; - ready = BeforeStartProgress(); + MainFile = "NTT"; + InitCheck(); } /// - /// 启动NatTypeTester + /// 启动 NatTypeTester /// /// public (bool, string, string, string) Start() { + if (!Ready) return (false, null, null, null); Thread.Sleep(1000); MainForm.Instance.NatTypeStatusText(i18N.Translate("Starting NatTester")); try { - Instance = MainController.GetProcess("bin\\NTT.exe"); + Instance = GetProcess("bin\\NTT.exe"); Instance.StartInfo.Arguments = $" {Global.Settings.STUN_Server} {Global.Settings.STUN_Server_Port}"; @@ -39,7 +40,7 @@ namespace Netch.Controllers Instance.BeginErrorReadLine(); Instance.WaitForExit(); - var result = File.ReadAllText($"logging\\{MainName}.log").Split('#'); + var result = File.ReadAllText($"logging\\{MainFile}.log").Split('#'); var natType = result[0]; var localEnd = result[1]; var publicEnd = result[2]; @@ -49,15 +50,22 @@ namespace Netch.Controllers } catch (Exception) { - Logging.Info("NTT 进程出错"); + Logging.Error("NTT 进程出错"); Stop(); return (false, null, null, null); } } - public void OnOutputDataReceived(object sender, DataReceivedEventArgs e) + private void OnOutputDataReceived(object sender, DataReceivedEventArgs e) { WriteLog(e); } + + /// + /// 无用 + /// + public override void Stop() + { + } } } \ No newline at end of file diff --git a/Netch/Controllers/PrivoxyController.cs b/Netch/Controllers/PrivoxyController.cs index 9e9fbc38..e11b2af5 100644 --- a/Netch/Controllers/PrivoxyController.cs +++ b/Netch/Controllers/PrivoxyController.cs @@ -1,4 +1,5 @@ -using System.Diagnostics; +using System; +using System.Diagnostics; using System.IO; using Netch.Models; @@ -8,34 +9,44 @@ namespace Netch.Controllers { public PrivoxyController() { - MainName = "Privoxy"; + MainFile = "Privoxy"; ExtFiles = new[] {"default.conf"}; - ready = BeforeStartProgress(); + InitCheck(); } public bool Start(Server server, Mode mode) { - if (server.Type != "Socks5") - File.WriteAllText("data\\privoxy.conf", File.ReadAllText("bin\\default.conf").Replace("_BIND_PORT_", Global.Settings.HTTPLocalPort.ToString()).Replace("_DEST_PORT_", Global.Settings.Socks5LocalPort.ToString()).Replace("0.0.0.0", Global.Settings.LocalAddress)); - else - File.WriteAllText("data\\privoxy.conf", File.ReadAllText("bin\\default.conf").Replace("_BIND_PORT_", Global.Settings.HTTPLocalPort.ToString()).Replace("_DEST_PORT_", server.Port.ToString()).Replace("s 0.0.0.0", $"s {Global.Settings.LocalAddress}").Replace("/ 127.0.0.1", $"/ {server.Hostname}")); + if (!Ready) return false; + var isSocks5 = server.Type == "Socks5"; + var socks5Port = isSocks5 ? server.Port : Global.Settings.Socks5LocalPort; + var text = File.ReadAllText("bin\\default.conf") + .Replace("_BIND_PORT_", Global.Settings.HTTPLocalPort.ToString()) + .Replace("_DEST_PORT_", socks5Port.ToString()) + .Replace("0.0.0.0", Global.Settings.LocalAddress); + if (isSocks5) + text = text.Replace("/ 127.0.0.1", $"/ {server.Hostname}"); + File.WriteAllText("data\\privoxy.conf", text); - Instance = new Process + Instance = GetProcess("bin\\Privoxy.exe", false); + Instance.StartInfo.Arguments = "..\\data\\privoxy.conf"; + Instance.StartInfo.WindowStyle = ProcessWindowStyle.Hidden; + Instance.StartInfo.UseShellExecute = true; + try { - StartInfo = - { - FileName = $"{Global.NetchDir}\\bin\\Privoxy.exe", - Arguments = "..\\data\\privoxy.conf", - WorkingDirectory = $"{Global.NetchDir}\\bin", - WindowStyle = ProcessWindowStyle.Hidden, - UseShellExecute = true, - CreateNoWindow = true - } - }; - Instance.Start(); + Instance.Start(); + } + catch (Exception) + { + return false; + } return true; } + + public override void Stop() + { + StopInstance(); + } } } \ No newline at end of file diff --git a/Netch/Forms/MainForm.Control.cs b/Netch/Forms/MainForm.Control.cs index 22f55017..a36e6d0d 100644 --- a/Netch/Forms/MainForm.Control.cs +++ b/Netch/Forms/MainForm.Control.cs @@ -36,7 +36,7 @@ namespace Netch.Forms //MenuStrip.Enabled = ConfigurationGroupBox.Enabled = ControlButton.Enabled = SettingsButton.Enabled = false; UpdateStatus(State.Starting); - + Firewall.AddNetchFwRules(); Task.Run(() => @@ -44,7 +44,7 @@ namespace Netch.Forms var server = ServerComboBox.SelectedItem as Models.Server; var mode = ModeComboBox.SelectedItem as Models.Mode; - MainController = new MainController(); + MainController ??= new MainController(); var startResult = MainController.Start(server, mode); @@ -94,7 +94,7 @@ namespace Netch.Forms if (server.Type == "Socks5") { // 不可控Socks5 - if (mode.Type == 3 && mode.Type == 5) + if (mode.Type == 3 || mode.Type == 5) { // 可控HTTP text.Append( diff --git a/Netch/Forms/MainForm.MenuStrip.cs b/Netch/Forms/MainForm.MenuStrip.cs index 945c5e02..f0364bad 100644 --- a/Netch/Forms/MainForm.MenuStrip.cs +++ b/Netch/Forms/MainForm.MenuStrip.cs @@ -1,5 +1,4 @@ using System; -using System.IO; using System.Linq; using System.Net; using System.ServiceProcess; @@ -18,7 +17,9 @@ using WebClient = Netch.Override.WebClient; namespace Netch.Forms { partial class Dummy - {} + { + } + partial class MainForm { #region MenuStrip @@ -160,7 +161,7 @@ namespace Netch.Forms } catch (Exception) { - // 跳过 + // ignored } Global.Settings.Server = Global.Settings.Server.Where(server => server.Group != item.Remark).ToList(); @@ -261,39 +262,18 @@ namespace Netch.Forms Task.Run(() => { - var driver = $"{Environment.SystemDirectory}\\drivers\\netfilter2.sys"; - if (File.Exists(driver)) + try { - try + if (new NFController().UninstallDriver()) { - var service = new ServiceController("netfilter2"); - if (service.Status == ServiceControllerStatus.Running) - { - service.Stop(); - service.WaitForStatus(ServiceControllerStatus.Stopped); - } - } - catch (Exception) - { - // 跳过 - } - - try - { - NFAPI.nf_unRegisterDriver("netfilter2"); - - File.Delete(driver); - MessageBoxX.Show(i18N.Translate("Service has been uninstalled"), owner: this); } - catch (Exception ex) - { - MessageBoxX.Show(i18N.Translate("Error") + i18N.Translate(": ") + ex, info: false, owner: this); - } } - else + catch (Exception e) { - MessageBoxX.Show(i18N.Translate("Service has been uninstalled"), owner: this); + MessageBox.Show(i18N.Translate("Error", e.Message)); + Console.WriteLine(e); + throw; } Enabled = true; @@ -398,8 +378,8 @@ namespace Netch.Forms } catch (Exception e) { - Logging.Info("使用代理更新 ACL 失败!" + e.Message); - MessageBoxX.Show(i18N.Translate("ACL update failed") + "\n" + e.Message); + Logging.Error("使用代理更新 ACL 失败!" + e); + MessageBoxX.Show(i18N.Translate("ACL update failed") + "\n" + e); } finally { @@ -414,17 +394,7 @@ namespace Netch.Forms private void exitToolStripMenuItem_Click(object sender, EventArgs e) { - if (State != State.Waiting && State != State.Stopped) - { - ControlButton_Click(sender, e); - } - SaveConfigs(); - - UpdateStatus(State.Terminating); - NotifyIcon.Visible = false; - Close(); - Dispose(); - Environment.Exit(Environment.ExitCode); + Exit(true); } private void RelyToolStripMenuItem_Click(object sender, EventArgs e) @@ -461,7 +431,7 @@ namespace Netch.Forms } else { - Logging.Info("ACL 更新失败!" + args.Error); + Logging.Error("ACL 更新失败!" + args.Error); MessageBoxX.Show(i18N.Translate("ACL update failed") + "\n" + args.Error); } } diff --git a/Netch/Forms/MainForm.Profile.cs b/Netch/Forms/MainForm.Profile.cs index ac1067b2..0866986b 100644 --- a/Netch/Forms/MainForm.Profile.cs +++ b/Netch/Forms/MainForm.Profile.cs @@ -13,7 +13,7 @@ namespace Netch.Forms partial class MainForm { - // init at MainFrom_Load() + /// init at private int _sizeHeight; private int _controlHeight; private int _profileBoxHeight; diff --git a/Netch/Forms/MainForm.cs b/Netch/Forms/MainForm.cs index bdf84468..f1000e4f 100644 --- a/Netch/Forms/MainForm.cs +++ b/Netch/Forms/MainForm.cs @@ -148,7 +148,7 @@ namespace Netch.Forms // 如果勾选了关闭时退出,自动点击退出按钮 else { - ExitToolStripButton.PerformClick(); + Exit(true); } } } @@ -414,35 +414,52 @@ namespace Netch.Forms Activate(); } - private void ExitToolStripButton_Click(object sender, EventArgs e) + private void Exit(bool forceExit = false) { // 已启动 if (State != State.Waiting && State != State.Stopped) { - // 未开启自动停止 - if (!Global.Settings.StopWhenExited) + if (forceExit) + ControlFun(); + else { - MessageBoxX.Show(i18N.Translate("Please press Stop button first")); + if (!Global.Settings.StopWhenExited) + { + // 未开启自动停止 + MessageBoxX.Show(i18N.Translate("Please press Stop button first")); - Visible = true; - ShowInTaskbar = true; // 显示在系统任务栏 - WindowState = FormWindowState.Normal; // 还原窗体 - NotifyIcon.Visible = true; // 托盘图标隐藏 + Visible = true; + ShowInTaskbar = true; // 显示在系统任务栏 + WindowState = FormWindowState.Normal; // 还原窗体 + NotifyIcon.Visible = true; // 托盘图标隐藏 - return; + return; + } } - // 自动停止 - - ControlButton_Click(sender, e); } - SaveConfigs(); - - UpdateStatus(State.Terminating); NotifyIcon.Visible = false; - Close(); - Dispose(); - Environment.Exit(Environment.ExitCode); + Hide(); + + Task.Run(() => + { + for (var i = 0; i < 16; i++) + { + if (State == State.Waiting || State == State.Stopped) + break; + Thread.Sleep(250); + } + + SaveConfigs(); + UpdateStatus(State.Terminating); + Dispose(); + Environment.Exit(Environment.ExitCode); + }); + } + + private void ExitToolStripButton_Click(object sender, EventArgs e) + { + Exit(); } private void NotifyIcon_MouseDoubleClick(object sender, MouseEventArgs e) diff --git a/Netch/Override/ToolStripProfessionalRender.cs b/Netch/Override/ToolStripProfessionalRender.cs index e88bcd78..138fb9f4 100644 --- a/Netch/Override/ToolStripProfessionalRender.cs +++ b/Netch/Override/ToolStripProfessionalRender.cs @@ -4,7 +4,7 @@ { protected override void OnRenderToolStripBorder(System.Windows.Forms.ToolStripRenderEventArgs e) { - // 跳过 + // ignored } } } diff --git a/Netch/Utils/Bandwidth.cs b/Netch/Utils/Bandwidth.cs index bb2e273e..22538a2b 100644 --- a/Netch/Utils/Bandwidth.cs +++ b/Netch/Utils/Bandwidth.cs @@ -15,13 +15,13 @@ namespace Netch.Utils public static int received; /// - /// 计算流量 - /// - /// 流量 - /// 带单位的流量字符串 - public static string Compute(long bandwidth) + /// 计算流量 + /// + /// 流量 + /// 带单位的流量字符串 + public static string Compute(long bandwidth) { - string[] units = { "KB", "MB", "GB", "TB", "PB" }; + string[] units = {"KB", "MB", "GB", "TB", "PB"}; double result = bandwidth; var i = -1; @@ -50,27 +50,24 @@ namespace Netch.Utils //var processList = Process.GetProcessesByName(ProcessName).Select(p => p.Id).ToHashSet(); var processList = new List(); - if (server.Type.Equals("Socks5") && mainController.pHTTPController != null) + if (server.Type.Equals("Socks5") && mainController.pModeController.AkaName == "HTTP") { - processList.Add(mainController.pHTTPController.pPrivoxyController.Instance.Id); + processList.Add(((HTTPController) mainController.pModeController).pPrivoxyController.Instance.Id); } else if (server.Type.Equals("SS") && Global.Settings.BootShadowsocksFromDLL) { processList.Add(Process.GetCurrentProcess().Id); } - else if (mainController.pServerClientController != null) + else if (mainController.pEncryptedProxyController != null) { // mainController.pServerClientController.Instance - processList.Add(mainController.pServerClientController.Instance.Id); + processList.Add(mainController.pEncryptedProxyController.Instance.Id); } - else if (mainController.pTUNTAPController != null) + else if (mainController.pModeController != null) { - processList.Add(mainController.pTUNTAPController.Instance.Id); - } - else if (mainController.pNFController != null) - { - processList.Add(mainController.pNFController.Instance.Id); + processList.Add(mainController.pModeController.Instance.Id); } + Logging.Info("启动流量统计 PID:" + string.Join(",", processList.ToArray())); Task.Run(() => @@ -109,6 +106,7 @@ namespace Netch.Utils MainForm.Instance.OnBandwidthUpdated(0); received = 0; } + while (MainForm.Instance.State != State.Stopped) { Task.Delay(1000).Wait(); @@ -117,7 +115,6 @@ namespace Netch.Utils MainForm.Instance.OnBandwidthUpdated(Convert.ToInt64(received)); } } - } } -} +} \ No newline at end of file diff --git a/Netch/Utils/Configuration.cs b/Netch/Utils/Configuration.cs index 229ad5f6..c692470d 100644 --- a/Netch/Utils/Configuration.cs +++ b/Netch/Utils/Configuration.cs @@ -89,112 +89,6 @@ namespace Netch.Utils File.WriteAllText(SETTINGS_JSON, JsonConvert.SerializeObject(Global.Settings, Formatting.Indented)); } - /// - /// 搜索出口 - /// - public static bool SearchOutbounds() - { - Logging.Info("正在搜索出口中"); - - if (Win32Native.GetBestRoute(BitConverter.ToUInt32(IPAddress.Parse("114.114.114.114").GetAddressBytes(), 0), 0, out var pRoute) == 0) - { - Global.Adapter.Index = pRoute.dwForwardIfIndex; - Global.Adapter.Gateway = new IPAddress(pRoute.dwForwardNextHop); - Logging.Info($"当前 网关 地址:{Global.Adapter.Gateway}"); - } - else - { - Logging.Info("GetBestRoute 搜索失败"); - return false; - } - - Logging.Info($"搜索适配器index:{Global.Adapter.Index}"); - var AddressGot = false; - foreach (var adapter in NetworkInterface.GetAllNetworkInterfaces()) - { - try - { - var adapterProperties = adapter.GetIPProperties(); - var p = adapterProperties.GetIPv4Properties(); - Logging.Info($"检测适配器:{adapter.Name} {adapter.Id} {adapter.Description}, index: {p.Index}"); - - // 通过索引查找对应适配器的 IPv4 地址 - if (p.Index == Global.Adapter.Index) - { - var AdapterIPs = ""; - - foreach (var ip in adapterProperties.UnicastAddresses) - { - if (ip.Address.AddressFamily == AddressFamily.InterNetwork) - { - AddressGot = true; - Global.Adapter.Address = ip.Address; - Logging.Info($"当前出口 IPv4 地址:{Global.Adapter.Address}"); - break; - } - AdapterIPs = $"{ip.Address} | "; - } - - if (!AddressGot) - { - if (AdapterIPs.Length > 3) - { - AdapterIPs = AdapterIPs.Substring(0, AdapterIPs.Length - 3); - Logging.Info($"所有出口地址:{AdapterIPs}"); - } - Logging.Info("出口无 IPv4 地址,当前只支持 IPv4 地址"); - return false; - } - break; - } - - } - catch (Exception) - { } - } - - if (!AddressGot) - { - Logging.Info("无法找到当前使用适配器"); - return false; - } - - // 搜索 TUN/TAP 适配器的索引 - Global.TUNTAP.ComponentID = TUNTAP.GetComponentID(); - if (string.IsNullOrEmpty(Global.TUNTAP.ComponentID)) - { - Logging.Info("未找到可用 TUN/TAP 适配器"); - if (MessageBoxX.Show(i18N.Translate("TUN/TAP driver is not detected. Is it installed now?"),confirm:true) == DialogResult.OK) - { - addtap(); - //给点时间,不然立马安装完毕就查找适配器可能会导致找不到适配器ID - Thread.Sleep(1000); - Global.TUNTAP.ComponentID = TUNTAP.GetComponentID(); - } - else - { - return false; - } - //MessageBoxX.Show(i18N.Translate("Please install TAP-Windows and create an TUN/TAP adapter manually")); - // return false; - } - - foreach (var adapter in NetworkInterface.GetAllNetworkInterfaces()) - { - if (adapter.Id == Global.TUNTAP.ComponentID) - { - Global.TUNTAP.Adapter = adapter; - Global.TUNTAP.Index = adapter.GetIPProperties().GetIPv4Properties().Index; - - Logging.Info($"找到适配器:{adapter.Id}"); - - return true; - } - } - - Logging.Info("无法找到出口"); - return false; - } /// /// 安装tap网卡 /// diff --git a/Netch/Utils/Firewall.cs b/Netch/Utils/Firewall.cs index e61f1359..7c25dbd3 100644 --- a/Netch/Utils/Firewall.cs +++ b/Netch/Utils/Firewall.cs @@ -1,9 +1,5 @@ using System; -using System.Collections; -using System.Collections.Generic; -using System.Diagnostics; using System.IO; -using System.Linq; using NetFwTypeLib; namespace Netch.Utils @@ -24,8 +20,8 @@ namespace Netch.Utils "Netch.exe" }; - private const string _netch = "Netch"; - private const string _netchAutoRule = "NetchAutoRule"; + private const string Netch = "Netch"; + private const string NetchAutoRule = "NetchAutoRule"; /// /// 添加防火墙规则 (非 Netch 自带程序) @@ -33,7 +29,7 @@ namespace Netch.Utils /// public static void AddFwRule(string exeFullPath) { - AddFwRule(_netchAutoRule, exeFullPath); + AddFwRule(NetchAutoRule, exeFullPath); } /// @@ -41,7 +37,7 @@ namespace Netch.Utils /// public static void RemoveFwRules() { - RemoveFwRules(_netchAutoRule); + RemoveFwRules(NetchAutoRule); } /// @@ -49,7 +45,7 @@ namespace Netch.Utils /// public static void AddNetchFwRules() { - if (GetFwRulePath(_netch).StartsWith(Global.NetchDir) && GetFwRulesNumber(_netch) >= ProgramPath.Length) return; + if (GetFwRulePath(Netch).StartsWith(Global.NetchDir) && GetFwRulesNumber(Netch) >= ProgramPath.Length) return; RemoveNetchFwRules(); foreach (var p in ProgramPath) { @@ -64,9 +60,9 @@ namespace Netch.Utils /// /// 清除防火墙规则 (Netch 自带程序) /// - public static void RemoveNetchFwRules() + private static void RemoveNetchFwRules() { - RemoveFwRules(_netch); + RemoveFwRules(Netch); } #region 封装 @@ -111,7 +107,7 @@ namespace Netch.Utils var rule = (INetFwRule2)FwPolicy.Rules.Item(ruleName); return rule.ApplicationName; } - catch (Exception e) + catch (Exception) { return ""; } @@ -120,7 +116,13 @@ namespace Netch.Utils private static int GetFwRulesNumber(string ruleName) { // https://stackoverflow.com/a/53601691 - return FwPolicy.Rules.Cast().Count(rule => rule.Name == ruleName); + var i = 0; + foreach (INetFwRule2 rule in FwPolicy.Rules) + { + if (rule.Name == ruleName) + i++; + } + return i; } #endregion diff --git a/Netch/Utils/Logging.cs b/Netch/Utils/Logging.cs index eeba7723..fb5f340d 100644 --- a/Netch/Utils/Logging.cs +++ b/Netch/Utils/Logging.cs @@ -12,7 +12,16 @@ namespace Netch.Utils /// 内容 public static void Info(string text) { - File.AppendAllText("logging\\application.log", $@"[{DateTime.Now}] {text}{Global.EOF}"); + File.AppendAllText("logging\\application.log", $@"[{DateTime.Now}][INFO] {text}{Global.EOF}"); + } + + /// + /// 错误 + /// + /// 内容 + public static void Error(string text) + { + File.AppendAllText("logging\\application.log", $@"[{DateTime.Now}][ERROR] {text}{Global.EOF}"); } } } diff --git a/Netch/Utils/ShareLink.cs b/Netch/Utils/ShareLink.cs index fab0f872..8db51bfb 100644 --- a/Netch/Utils/ShareLink.cs +++ b/Netch/Utils/ShareLink.cs @@ -123,7 +123,7 @@ namespace Netch.Utils } catch (Exception e) { - Logging.Info(e.ToString()); + Logging.Error(e.ToString()); return null; } @@ -256,7 +256,7 @@ namespace Netch.Utils if (!Global.EncryptMethods.SS.Contains(data.EncryptMethod)) { - Logging.Info(string.Format("不支持的 SS 加密方式:{0}", data.EncryptMethod)); + Logging.Error($"不支持的 SS 加密方式:{data.EncryptMethod}"); return null; } @@ -313,14 +313,14 @@ namespace Netch.Utils data.TransferProtocol = vmess.net; if (!Global.TransferProtocols.Contains(data.TransferProtocol)) { - Logging.Info(string.Format("不支持的 VMess 传输协议:{0}", data.TransferProtocol)); + Logging.Error($"不支持的 VMess 传输协议:{data.TransferProtocol}"); return null; } data.FakeType = vmess.type; if (data.FakeType.Length != 0 && !Global.FakeTypes.Contains(data.FakeType)) { - Logging.Info(string.Format("不支持的 VMess 伪装类型:{0}", data.FakeType)); + Logging.Error($"不支持的 VMess 伪装类型:{data.FakeType}"); return null; } @@ -337,7 +337,7 @@ namespace Netch.Utils { if (!Global.EncryptMethods.VMessQUIC.Contains(vmess.host)) { - Logging.Info(string.Format("不支持的 VMess QUIC 加密方式:{0}", vmess.host)); + Logging.Error($"不支持的 VMess QUIC 加密方式:{vmess.host}"); return null; } @@ -393,43 +393,43 @@ namespace Netch.Utils case "SS": if (!Global.EncryptMethods.SS.Contains(NetchLink.EncryptMethod)) { - Logging.Info($"不支持的 SS 加密方式:{NetchLink.EncryptMethod}"); + Logging.Error($"不支持的 SS 加密方式:{NetchLink.EncryptMethod}"); return null; } break; case "SSR": if (!Global.EncryptMethods.SSR.Contains(NetchLink.EncryptMethod)) { - Logging.Info($"不支持的 SSR 加密方式:{NetchLink.EncryptMethod}"); + Logging.Error($"不支持的 SSR 加密方式:{NetchLink.EncryptMethod}"); return null; } if (!Global.Protocols.Contains(NetchLink.Protocol)) { - Logging.Info($"不支持的 SSR 协议:{NetchLink.Protocol}"); + Logging.Error($"不支持的 SSR 协议:{NetchLink.Protocol}"); return null; } if (!Global.OBFSs.Contains(NetchLink.OBFS)) { - Logging.Info($"不支持的 SSR 混淆:{NetchLink.OBFS}"); + Logging.Error($"不支持的 SSR 混淆:{NetchLink.OBFS}"); return null; } break; case "VMess": if (!Global.TransferProtocols.Contains(NetchLink.TransferProtocol)) { - Logging.Info($"不支持的 VMess 传输协议:{NetchLink.TransferProtocol}"); + Logging.Error($"不支持的 VMess 传输协议:{NetchLink.TransferProtocol}"); return null; } if (!Global.FakeTypes.Contains(NetchLink.FakeType)) { - Logging.Info($"不支持的 VMess 伪装类型:{NetchLink.FakeType}"); + Logging.Error($"不支持的 VMess 伪装类型:{NetchLink.FakeType}"); return null; } if (NetchLink.TransferProtocol == "quic") { if (!Global.EncryptMethods.VMessQUIC.Contains(NetchLink.QUICSecure)) { - Logging.Info($"不支持的 VMess QUIC 加密方式:{NetchLink.QUICSecure}"); + Logging.Error($"不支持的 VMess QUIC 加密方式:{NetchLink.QUICSecure}"); return null; } } @@ -492,7 +492,7 @@ namespace Netch.Utils } catch (Exception e) { - Logging.Info(e.ToString()); + Logging.Error(e.ToString()); return null; } diff --git a/Netch/Win32Native.cs b/Netch/Win32Native.cs index 3cd02fa7..46dbd8f5 100644 --- a/Netch/Win32Native.cs +++ b/Netch/Win32Native.cs @@ -281,7 +281,7 @@ namespace Netch } catch (Exception) { - // 跳过 + // ignored } finally {