diff --git a/v2rayN/v2rayN/Global.cs b/v2rayN/v2rayN/Global.cs index f64cef38..6ba5b6e0 100644 --- a/v2rayN/v2rayN/Global.cs +++ b/v2rayN/v2rayN/Global.cs @@ -110,28 +110,32 @@ namespace v2rayN /// - /// vmess + /// Vmess /// public const string vmessProtocol = "vmess://"; /// - /// shadowsocks + /// Shadowsocks /// public const string ssProtocol = "ss://"; /// - /// socks + /// ShadowsocksR + /// + public const string ssrProtocol = "ssr://"; + /// + /// Socks proxy /// public const string socksProtocol = "socks://"; /// - /// http + /// HTTP /// public const string httpProtocol = "http://"; /// - /// https + /// HTTPS /// public const string httpsProtocol = "https://"; /// - /// pac + /// PAC /// public const string pacFILE = "pac.txt"; @@ -164,6 +168,7 @@ namespace v2rayN public const string IEProxyExceptions = "localhost;127.*;10.*;172.16.*;172.17.*;172.18.*;172.19.*;172.20.*;172.21.*;172.22.*;172.23.*;172.24.*;172.25.*;172.26.*;172.27.*;172.28.*;172.29.*;172.30.*;172.31.*;192.168.*"; + public const string ssProtocols_via_v2ray = "aes-256-cfb;aes-128-cfb;chacha20;chacha20-ietf;aes-256-gcm;aes-128-gcm;chacha20-poly1305;chacha20-ietf-poly1305"; #endregion #region 全局变量 diff --git a/v2rayN/v2rayN/Handler/V2rayConfigHandler.cs b/v2rayN/v2rayN/Handler/V2rayConfigHandler.cs index 8c3a81f3..80f73ee3 100644 --- a/v2rayN/v2rayN/Handler/V2rayConfigHandler.cs +++ b/v2rayN/v2rayN/Handler/V2rayConfigHandler.cs @@ -3,6 +3,7 @@ using System.Collections.Generic; using System.IO; using System.Linq; using System.Net; +using System.Text.RegularExpressions; using v2rayN.Base; using v2rayN.Mode; @@ -1215,7 +1216,7 @@ namespace v2rayN.Handler msg = UIRes.I18N("ConfigurationFormatIncorrect"); vmessItem.configType = (int)EConfigType.Shadowsocks; - result = result.Substring(Global.ssProtocol.Length); + result = result.Substring(Global.ssProtocol.Length); // strip //remark int indexRemark = result.IndexOf("#"); if (indexRemark > 0) @@ -1255,6 +1256,61 @@ namespace v2rayN.Handler vmessItem.security = arr21[0]; vmessItem.id = arr21[1]; } + else if (result.StartsWith(Global.ssrProtocol)) + { + vmessItem.configType = (int)EConfigType.Shadowsocks; + if (result.Length <= Global.ssrProtocol.Length) + { + return null; + } + result = result.Substring(Global.ssrProtocol.Length); + + //part decode + // thanks to https://html50.github.io/ssr2jsonBat/ + result = result.Replace("-", "+").Replace("_", "/"); // TODO: review ss:// works. + string text = Utils.Base64Decode(result); + try + { + string[] arr = text.Split(':'); + + string ip = arr[0]; + string port = arr[1]; + string protocol = arr[2]; + string method = arr[3]; + string obfs = arr[4]; + string[] base64two = arr[5].Split(new string[] { "/?"}, StringSplitOptions.RemoveEmptyEntries); + string password = Utils.Base64Decode(base64two[0]); + string remark = ""; + + string arr2 = base64two[1]; + string _remark = Regex.Match(arr2, "remarks=([^&]*)").Groups[1].Value; + _remark = _remark.Replace("-", "+").Replace("_", "/"); // necessary + remark = Utils.Base64Decode(_remark); + + if (method == "chacha20-ietf") { method = "chacha20-ietf-poly1305"; } // ssr alia + string[] v2ray_supported = Global.ssProtocols_via_v2ray.Split(';'); + if (!v2ray_supported.Contains(method.ToLower()) || + protocol != "origin" || + obfs != "plain") + { + // TODO: Counters and then report to user + msg = UIRes.I18N("IncorrectconfigurationSSR"); + return null; // skip + } + + vmessItem.address = ip; + vmessItem.port = Convert.ToInt32(port); + vmessItem.security = method; + vmessItem.id = password; + vmessItem.remarks = remark; + } + catch + { + System.Diagnostics.Debug.Fail(text); + msg = UIRes.I18N("IncorrectconfigurationSSRError"); + return null; + } + } else if (result.StartsWith(Global.socksProtocol)) { msg = UIRes.I18N("ConfigurationFormatIncorrect"); diff --git a/v2rayN/v2rayN/Resx/ResUI.Designer.cs b/v2rayN/v2rayN/Resx/ResUI.Designer.cs index e80f0555..bc480b11 100644 --- a/v2rayN/v2rayN/Resx/ResUI.Designer.cs +++ b/v2rayN/v2rayN/Resx/ResUI.Designer.cs @@ -19,7 +19,7 @@ namespace v2rayN.Resx { // 类通过类似于 ResGen 或 Visual Studio 的工具自动生成的。 // 若要添加或移除成员,请编辑 .ResX 文件,然后重新运行 ResGen // (以 /str 作为命令选项),或重新生成 VS 项目。 - [global::System.CodeDom.Compiler.GeneratedCodeAttribute("System.Resources.Tools.StronglyTypedResourceBuilder", "15.0.0.0")] + [global::System.CodeDom.Compiler.GeneratedCodeAttribute("System.Resources.Tools.StronglyTypedResourceBuilder", "16.0.0.0")] [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] [global::System.Runtime.CompilerServices.CompilerGeneratedAttribute()] internal class ResUI { @@ -249,6 +249,24 @@ namespace v2rayN.Resx { } } + /// + /// 查找类似 is not supported. 的本地化字符串。 + /// + internal static string IncorrectconfigurationSSR { + get { + return ResourceManager.GetString("IncorrectconfigurationSSR", resourceCulture); + } + } + + /// + /// 查找类似 An error occurred. 的本地化字符串。 + /// + internal static string IncorrectconfigurationSSRError { + get { + return ResourceManager.GetString("IncorrectconfigurationSSRError", resourceCulture); + } + } + /// /// 查找类似 is not the correct server configuration file, please check 的本地化字符串。 /// diff --git a/v2rayN/v2rayN/Resx/ResUI.resx b/v2rayN/v2rayN/Resx/ResUI.resx index 74280a36..084e0701 100644 --- a/v2rayN/v2rayN/Resx/ResUI.resx +++ b/v2rayN/v2rayN/Resx/ResUI.resx @@ -222,6 +222,12 @@ is not the correct configuration, please check + + is not supported. + + + An error occurred. + is not the correct server configuration file, please check diff --git a/v2rayN/v2rayN/Resx/ResUI.zh-Hans.resx b/v2rayN/v2rayN/Resx/ResUI.zh-Hans.resx index cf7cab26..9eac4c3a 100644 --- a/v2rayN/v2rayN/Resx/ResUI.zh-Hans.resx +++ b/v2rayN/v2rayN/Resx/ResUI.zh-Hans.resx @@ -222,6 +222,12 @@ 不是正确的配置,请检查 + + 不受支持或识别失败。 + + + 发生内部错误。 + 不是正确的服务端配置文件,请检查