update 2025-05-04 16:26:33
This commit is contained in:
parent
e7078b8470
commit
c0c4f3d4a6
|
@ -232,6 +232,13 @@ o:value("1:65535", translate("All"))
|
|||
o.validate = port_validate
|
||||
o:depends({ _hide_node_option = "1", ['!reverse'] = true })
|
||||
|
||||
o = s:option(DummyValue, "tips", " ")
|
||||
o.rawhtml = true
|
||||
o.cfgvalue = function(t, n)
|
||||
return string.format('<font color="red">%s</font>',
|
||||
translate("The port settings support single ports and ranges.<br>Separate multiple ports with commas (,).<br>Example: 21,80,443,1000:2000."))
|
||||
end
|
||||
|
||||
o = s:option(ListValue, "direct_dns_query_strategy", translate("Direct Query Strategy"))
|
||||
o.default = "UseIP"
|
||||
o:value("UseIP")
|
||||
|
|
|
@ -114,6 +114,8 @@ o.cfgvalue = function(t, n)
|
|||
protocol = "HY"
|
||||
elseif protocol == "hysteria2" then
|
||||
protocol = "HY2"
|
||||
elseif protocol == "anytls" then
|
||||
protocol = "AnyTLS"
|
||||
else
|
||||
protocol = protocol:gsub("^%l",string.upper)
|
||||
end
|
||||
|
|
|
@ -95,6 +95,13 @@ o.default = "1:65535"
|
|||
o:value("1:65535", translate("All"))
|
||||
o.validate = port_validate
|
||||
|
||||
o = s:option(DummyValue, "tips", " ")
|
||||
o.rawhtml = true
|
||||
o.cfgvalue = function(t, n)
|
||||
return string.format('<font color="red">%s</font>',
|
||||
translate("The port settings support single ports and ranges.<br>Separate multiple ports with commas (,).<br>Example: 21,80,443,1000:2000."))
|
||||
end
|
||||
|
||||
---- Use nftables
|
||||
o = s:option(ListValue, "use_nft", translate("Firewall tools"))
|
||||
o.default = "0"
|
||||
|
|
|
@ -8,6 +8,9 @@ if not singbox_bin then
|
|||
return
|
||||
end
|
||||
|
||||
local local_version = api.get_app_version("sing-box")
|
||||
local version_ge_1_12_0 = api.compare_versions(local_version:match("[^v]+"), ">=", "1.12.0")
|
||||
|
||||
local singbox_tags = luci.sys.exec(singbox_bin .. " version | grep 'Tags:' | awk '{print $2}'")
|
||||
|
||||
local appname = api.appname
|
||||
|
@ -59,6 +62,9 @@ end
|
|||
if singbox_tags:find("with_quic") then
|
||||
o:value("hysteria2", "Hysteria2")
|
||||
end
|
||||
if version_ge_1_12_0 then
|
||||
o:value("anytls", "AnyTLS")
|
||||
end
|
||||
o:value("_urltest", translate("URLTest"))
|
||||
o:value("_shunt", translate("Shunt"))
|
||||
o:value("_iface", translate("Custom Interface"))
|
||||
|
@ -254,6 +260,7 @@ o:depends({ [_n("protocol")] = "shadowsocks" })
|
|||
o:depends({ [_n("protocol")] = "shadowsocksr" })
|
||||
o:depends({ [_n("protocol")] = "trojan" })
|
||||
o:depends({ [_n("protocol")] = "tuic" })
|
||||
o:depends({ [_n("protocol")] = "anytls" })
|
||||
|
||||
o = s:option(ListValue, _n("security"), translate("Encrypt Method"))
|
||||
for a, t in ipairs(security_list) do o:value(t) end
|
||||
|
@ -434,6 +441,7 @@ o:depends({ [_n("protocol")] = "vless" })
|
|||
o:depends({ [_n("protocol")] = "http" })
|
||||
o:depends({ [_n("protocol")] = "trojan" })
|
||||
o:depends({ [_n("protocol")] = "shadowsocks" })
|
||||
o:depends({ [_n("protocol")] = "anytls" })
|
||||
|
||||
o = s:option(ListValue, _n("alpn"), translate("alpn"))
|
||||
o.default = "default"
|
||||
|
@ -527,6 +535,7 @@ if singbox_tags:find("with_utls") then
|
|||
o:depends({ [_n("protocol")] = "shadowsocks", [_n("utls")] = true })
|
||||
o:depends({ [_n("protocol")] = "socks", [_n("utls")] = true })
|
||||
o:depends({ [_n("protocol")] = "trojan", [_n("utls")] = true })
|
||||
o:depends({ [_n("protocol")] = "anytls", [_n("utls")] = true })
|
||||
|
||||
o = s:option(Value, _n("reality_publicKey"), translate("Public Key"))
|
||||
o:depends({ [_n("utls")] = true, [_n("reality")] = true })
|
||||
|
@ -752,6 +761,7 @@ o:depends({ [_n("protocol")] = "hysteria" })
|
|||
o:depends({ [_n("protocol")] = "vless" })
|
||||
o:depends({ [_n("protocol")] = "tuic" })
|
||||
o:depends({ [_n("protocol")] = "hysteria2" })
|
||||
o:depends({ [_n("protocol")] = "anytls" })
|
||||
|
||||
o = s:option(ListValue, _n("chain_proxy"), translate("Chain Proxy"))
|
||||
o:value("", translate("Close(Not use)"))
|
||||
|
|
|
@ -8,6 +8,11 @@ if not singbox_bin then
|
|||
return
|
||||
end
|
||||
|
||||
local local_version = api.get_app_version("sing-box")
|
||||
local version_ge_1_12_0 = api.compare_versions(local_version:match("[^v]+"), ">=", "1.12.0")
|
||||
|
||||
local fs = api.fs
|
||||
|
||||
local singbox_tags = luci.sys.exec(singbox_bin .. " version | grep 'Tags:' | awk '{print $2}'")
|
||||
|
||||
local type_name = "sing-box"
|
||||
|
@ -48,6 +53,9 @@ end
|
|||
if singbox_tags:find("with_quic") then
|
||||
o:value("hysteria2", "Hysteria2")
|
||||
end
|
||||
if version_ge_1_12_0 then
|
||||
o:value("anytls", "AnyTLS")
|
||||
end
|
||||
o:value("direct", "Direct")
|
||||
|
||||
o = s:option(Value, _n("port"), translate("Listen Port"))
|
||||
|
@ -71,6 +79,7 @@ o:depends({ [_n("protocol")] = "http" })
|
|||
o = s:option(Value, _n("username"), translate("Username"))
|
||||
o:depends({ [_n("auth")] = true })
|
||||
o:depends({ [_n("protocol")] = "naive" })
|
||||
o:depends({ [_n("protocol")] = "anytls" })
|
||||
|
||||
o = s:option(Value, _n("password"), translate("Password"))
|
||||
o.password = true
|
||||
|
@ -78,6 +87,7 @@ o:depends({ [_n("auth")] = true })
|
|||
o:depends({ [_n("protocol")] = "shadowsocks" })
|
||||
o:depends({ [_n("protocol")] = "naive" })
|
||||
o:depends({ [_n("protocol")] = "tuic" })
|
||||
o:depends({ [_n("protocol")] = "anytls" })
|
||||
|
||||
if singbox_tags:find("with_quic") then
|
||||
o = s:option(Value, _n("hysteria_up_mbps"), translate("Max upload Mbps"))
|
||||
|
@ -221,6 +231,7 @@ o:depends({ [_n("protocol")] = "http" })
|
|||
o:depends({ [_n("protocol")] = "vmess" })
|
||||
o:depends({ [_n("protocol")] = "vless" })
|
||||
o:depends({ [_n("protocol")] = "trojan" })
|
||||
o:depends({ [_n("protocol")] = "anytls" })
|
||||
|
||||
if singbox_tags:find("with_reality_server") then
|
||||
-- [[ REALITY部分 ]] --
|
||||
|
@ -230,6 +241,7 @@ if singbox_tags:find("with_reality_server") then
|
|||
o:depends({ [_n("protocol")] = "vmess", [_n("tls")] = true })
|
||||
o:depends({ [_n("protocol")] = "vless", [_n("tls")] = true })
|
||||
o:depends({ [_n("protocol")] = "trojan", [_n("tls")] = true })
|
||||
o:depends({ [_n("protocol")] = "anytls", [_n("tls")] = true })
|
||||
|
||||
o = s:option(Value, _n("reality_private_key"), translate("Private Key"))
|
||||
o:depends({ [_n("reality")] = true })
|
||||
|
|
|
@ -471,6 +471,8 @@ function get_valid_nodes()
|
|||
protocol = "HY"
|
||||
elseif protocol == "hysteria2" then
|
||||
protocol = "HY2"
|
||||
elseif protocol == "anytls" then
|
||||
protocol = "AnyTLS"
|
||||
else
|
||||
protocol = protocol:gsub("^%l",string.upper)
|
||||
end
|
||||
|
@ -504,9 +506,22 @@ function get_node_remarks(n)
|
|||
protocol = "VMess"
|
||||
elseif protocol == "vless" then
|
||||
protocol = "VLESS"
|
||||
elseif protocol == "shadowsocks" then
|
||||
protocol = "SS"
|
||||
elseif protocol == "shadowsocksr" then
|
||||
protocol = "SSR"
|
||||
elseif protocol == "wireguard" then
|
||||
protocol = "WG"
|
||||
elseif protocol == "hysteria" then
|
||||
protocol = "HY"
|
||||
elseif protocol == "hysteria2" then
|
||||
protocol = "HY2"
|
||||
elseif protocol == "anytls" then
|
||||
protocol = "AnyTLS"
|
||||
else
|
||||
protocol = protocol:gsub("^%l",string.upper)
|
||||
end
|
||||
if type2 == "sing-box" then type2 = "Sing-Box" end
|
||||
type2 = type2 .. " " .. protocol
|
||||
end
|
||||
remarks = "%s:[%s]" % {type2, n.remarks}
|
||||
|
@ -849,7 +864,8 @@ local default_file_tree = {
|
|||
armv5 = "arm.*5",
|
||||
armv6 = "arm.*6[^4]*",
|
||||
armv7 = "arm.*7",
|
||||
armv8 = "arm64"
|
||||
armv8 = "arm64",
|
||||
riscv64 = "riscv64"
|
||||
}
|
||||
|
||||
function get_api_json(url)
|
||||
|
|
|
@ -382,6 +382,13 @@ function gen_outbound(flag, node, tag, proxy_table)
|
|||
}
|
||||
end
|
||||
|
||||
if node.protocol == "anytls" then
|
||||
protocol_table = {
|
||||
password = (node.password and node.password ~= "") and node.password or "",
|
||||
tls = tls
|
||||
}
|
||||
end
|
||||
|
||||
if protocol_table then
|
||||
for key, value in pairs(protocol_table) do
|
||||
result[key] = value
|
||||
|
@ -667,6 +674,18 @@ function gen_config_server(node)
|
|||
}
|
||||
end
|
||||
|
||||
if node.protocol == "anytls" then
|
||||
protocol_table = {
|
||||
users = {
|
||||
{
|
||||
name = (node.username and node.username ~= "") and node.username or "sekai",
|
||||
password = node.password
|
||||
}
|
||||
},
|
||||
tls = tls,
|
||||
}
|
||||
end
|
||||
|
||||
if node.protocol == "direct" then
|
||||
protocol_table = {
|
||||
network = (node.d_protocol ~= "TCP,UDP") and node.d_protocol or nil,
|
||||
|
|
|
@ -28,7 +28,7 @@ local api = require "luci.passwall2.api"
|
|||
line-height: 1.2rem;
|
||||
}
|
||||
</style>
|
||||
<div class="cbi-section cbi-tblsection dns-con">
|
||||
<div class="dns-con">
|
||||
<div id="faq_dns">
|
||||
<ul>
|
||||
<b class="faq-title"><%:DNS related issues:%></b>
|
||||
|
|
|
@ -4,9 +4,20 @@ local api = require "luci.passwall2.api"
|
|||
|
||||
<script type="text/javascript">
|
||||
//<![CDATA[
|
||||
function getXHR() {
|
||||
if (typeof XHR === 'object' && typeof XHR.create === 'function') {
|
||||
return XHR.create();
|
||||
} else if (typeof XHR === 'function') {
|
||||
return new XHR();
|
||||
} else {
|
||||
throw new Error("XHR is not supported in this environment.");
|
||||
}
|
||||
}
|
||||
|
||||
function ajax_add_node(link) {
|
||||
var xhr = getXHR();
|
||||
if (link) {
|
||||
XHR.get('<%=api.url("link_add_node")%>', {
|
||||
xhr.post('<%=api.url("link_add_node")%>', {
|
||||
'link': link
|
||||
},
|
||||
function(x, data) {
|
||||
|
|
|
@ -538,6 +538,41 @@ local hysteria2_type = map:get("@global_subscribe[0]", "hysteria2_type") or "sin
|
|||
params += opt.query("congestion_control", dom_prefix + "tuic_congestion_control");
|
||||
params += opt.query("allowinsecure", dom_prefix + "tls_allowInsecure");
|
||||
|
||||
params += "#" + encodeURI(v_alias.value);
|
||||
if (params[0] == "&") {
|
||||
params = params.substring(1);
|
||||
}
|
||||
url += params;
|
||||
} else if (v_type === "sing-box" && opt.get(dom_prefix + "protocol").value === "anytls") {
|
||||
protocol = "anytls";
|
||||
var v_password = opt.get(dom_prefix + "password");
|
||||
var v_port = opt.get(dom_prefix + "port");
|
||||
url = encodeURIComponent(v_password.value) +
|
||||
"@" + _address +
|
||||
":" + v_port.value + "?";
|
||||
|
||||
var params = "";
|
||||
if (opt.get(dom_prefix + "tls").checked) {
|
||||
var v_security = "tls";
|
||||
if (opt.get(dom_prefix + "fingerprint") && opt.get(dom_prefix + "fingerprint").value != "") {
|
||||
let v_fp = opt.get(dom_prefix + "fingerprint").value;
|
||||
params += "&fp=" + v_fp;
|
||||
}
|
||||
if (opt.get(dom_prefix + "reality") && opt.get(dom_prefix + "reality").checked) {
|
||||
v_security = "reality";
|
||||
if (opt.get(dom_prefix + "fingerprint") && opt.get(dom_prefix + "fingerprint").value != "") {
|
||||
let v_fp = opt.get(dom_prefix + "fingerprint").value;
|
||||
params += "&fp=" + v_fp;
|
||||
}
|
||||
params += opt.query("pbk", dom_prefix + "reality_publicKey");
|
||||
params += opt.query("sid", dom_prefix + "reality_shortId");
|
||||
}
|
||||
params += "&security=" + v_security;
|
||||
params += opt.query("alpn", dom_prefix + "alpn");
|
||||
params += opt.query("sni", dom_prefix + "tls_serverName");
|
||||
params += opt.query("allowinsecure", dom_prefix + "tls_allowInsecure");
|
||||
}
|
||||
|
||||
params += "#" + encodeURI(v_alias.value);
|
||||
if (params[0] == "&") {
|
||||
params = params.substring(1);
|
||||
|
@ -639,10 +674,28 @@ local hysteria2_type = map:get("@global_subscribe[0]", "hysteria2_type") or "sin
|
|||
}
|
||||
try {
|
||||
obj.dispatchEvent(event);
|
||||
} catch (err) {
|
||||
}
|
||||
} catch (err) {}
|
||||
} else {
|
||||
//alert('<%:Faltal on set option, please help in debug: %>' + opt + ' = ' + val);
|
||||
// 处理 DynamicList
|
||||
var fullName = this.base + '.' + opt;
|
||||
var lists = document.querySelectorAll('.cbi-dynlist');
|
||||
for (var i = 0; i < lists.length; i++) {
|
||||
var parent = lists[i].closest('.cbi-value');
|
||||
if (!parent) continue;
|
||||
// 尝试从 label 的 for 属性中提取 fullName
|
||||
var label = parent.querySelector('label.cbi-value-title');
|
||||
var labelFor = label?.getAttribute('for');
|
||||
if (labelFor === fullName) {
|
||||
var input = lists[i].querySelector('input[type="text"]');
|
||||
var addBtn = lists[i].querySelector('.cbi-button-add');
|
||||
if (input && addBtn) {
|
||||
input.value = val;
|
||||
addBtn.click();
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
setlist: function (opt, vlist) {
|
||||
|
@ -764,6 +817,9 @@ local hysteria2_type = map:get("@global_subscribe[0]", "hysteria2_type") or "sin
|
|||
dom_prefix = "xray_"
|
||||
opt.set('type', "Xray");
|
||||
opt.set(dom_prefix + 'protocol', "shadowsocks");
|
||||
} else if (ss_type == "shadowsocks-rust") {
|
||||
dom_prefix = "ssrust_"
|
||||
opt.set('type', "SS-Rust");
|
||||
} else {
|
||||
if (["2022-blake3-aes-128-gcm", "2022-blake3-aes-256-gcm", "2022-blake3-chacha20-poly1305"].includes(method)) {
|
||||
dom_prefix = "ssrust_"
|
||||
|
@ -782,10 +838,27 @@ local hysteria2_type = map:get("@global_subscribe[0]", "hysteria2_type") or "sin
|
|||
opt.set(dom_prefix + 'password', password || "");
|
||||
opt.set(dom_prefix + 'method', method || "");
|
||||
opt.set(dom_prefix + 'ss_method', method || "");
|
||||
opt.set(dom_prefix + 'plugin', plugin || "none");
|
||||
if (plugin && plugin != "none") {
|
||||
opt.set(dom_prefix + 'plugin_opts', pluginOpts || "");
|
||||
plugin = (plugin === "simple-obfs") ? "obfs-local" : plugin;
|
||||
opt.set(dom_prefix + 'plugin_enabled', true);
|
||||
opt.set(dom_prefix + 'plugin', plugin || "none");
|
||||
opt.set(dom_prefix + 'plugin_opts', pluginOpts || "");
|
||||
//obfs-local插件转换成xray支持的格式
|
||||
if (plugin == "obfs-local" && dom_prefix == "xray_") {
|
||||
var obfs = pluginOpts.match(/obfs=([^;]+)/);
|
||||
var obfs_host = pluginOpts.match(/obfs-host=([^;]+)/);
|
||||
obfs = obfs ? obfs[1] : "";
|
||||
obfs_host = obfs_host ? obfs_host[1] : "";
|
||||
if (obfs === "http") {
|
||||
opt.set(dom_prefix + 'transport', "raw");
|
||||
opt.set(dom_prefix + 'tcp_guise', "http");
|
||||
opt.set(dom_prefix + 'tcp_guise_http_host', obfs_host || '');
|
||||
} else if (obfs === "tls") {
|
||||
opt.set(dom_prefix + 'tls', true);
|
||||
opt.set(dom_prefix + 'tls_serverName', obfs_host || '');
|
||||
opt.set(dom_prefix + 'tls_allowInsecure', true);
|
||||
}
|
||||
}
|
||||
}
|
||||
if (param !== undefined) {
|
||||
opt.set('remarks', decodeURIComponent(param));
|
||||
|
@ -800,7 +873,7 @@ local hysteria2_type = map:get("@global_subscribe[0]", "hysteria2_type") or "sin
|
|||
opt.set(dom_prefix + 'alpn', queryParam.alpn || 'default');
|
||||
opt.set(dom_prefix + 'tls_serverName', queryParam.sni || '');
|
||||
opt.set(dom_prefix + 'tls_allowInsecure', true);
|
||||
if (queryParam.allowinsecure === '0') {
|
||||
if (queryParam.allowinsecure === '0' || queryParam.insecure === '0') {
|
||||
opt.set(dom_prefix + 'tls_allowInsecure', false);
|
||||
}
|
||||
if (queryParam.fp && queryParam.fp.trim() != "") {
|
||||
|
@ -1032,8 +1105,9 @@ local hysteria2_type = map:get("@global_subscribe[0]", "hysteria2_type") or "sin
|
|||
tls_serverName = tls_serverName || "";
|
||||
opt.set(dom_prefix + 'tls_serverName', tls_serverName);
|
||||
}
|
||||
if (queryParam.allowinsecure === '1') {
|
||||
opt.set(dom_prefix + 'tls_allowInsecure', true);
|
||||
if (queryParam.allowinsecure === '0' || queryParam.insecure === '0') {
|
||||
opt.set(dom_prefix + 'tls_allowInsecure', false);
|
||||
}
|
||||
|
||||
opt.set(dom_prefix + 'mux', queryParam.mux === '1');
|
||||
|
@ -1170,7 +1244,7 @@ local hysteria2_type = map:get("@global_subscribe[0]", "hysteria2_type") or "sin
|
|||
opt.set(dom_prefix + 'alpn', queryParam.alpn || 'default');
|
||||
opt.set(dom_prefix + 'tls_serverName', queryParam.sni || '');
|
||||
opt.set(dom_prefix + 'tls_allowInsecure', true);
|
||||
if (queryParam.allowinsecure === '0') {
|
||||
if (queryParam.allowinsecure === '0' || queryParam.insecure === '0') {
|
||||
opt.set(dom_prefix + 'tls_allowInsecure', false);
|
||||
}
|
||||
if (queryParam.fp && queryParam.fp.trim() != "") {
|
||||
|
@ -1357,13 +1431,73 @@ local hysteria2_type = map:get("@global_subscribe[0]", "hysteria2_type") or "sin
|
|||
opt.set(dom_prefix + 'tuic_alpn', queryParam.alpn || 'default');
|
||||
opt.set(dom_prefix + 'tls_serverName', queryParam.sni || '');
|
||||
opt.set(dom_prefix + 'tls_allowInsecure', true);
|
||||
if (queryParam.allowinsecure === '0') {
|
||||
if (queryParam.allowinsecure === '0' || queryParam.insecure === '0') {
|
||||
opt.set(dom_prefix + 'tls_allowInsecure', false);
|
||||
}
|
||||
if (hash) {
|
||||
opt.set('remarks', decodeURIComponent(hash.substr(1)));
|
||||
}
|
||||
}
|
||||
if (ssu[0] === "anytls") {
|
||||
if (has_singbox) {
|
||||
dom_prefix = "singbox_"
|
||||
opt.set('type', "sing-box");
|
||||
}
|
||||
opt.set(dom_prefix + 'protocol', "anytls");
|
||||
var m = parseNodeUrl(ssrurl);
|
||||
var password = m.passwd;
|
||||
if (password === "") {
|
||||
s.innerHTML = "<font color='red'><%:Invalid Share URL Format%></font>";
|
||||
return false;
|
||||
}
|
||||
opt.set(dom_prefix + 'password', password);
|
||||
opt.set(dom_prefix + 'address', m.hostname);
|
||||
opt.set(dom_prefix + 'port', m.port || "443");
|
||||
var queryParam = {};
|
||||
if (m.search.length > 1) {
|
||||
var query = m.search.replace('/?', '?').split('?')
|
||||
var queryParams = query[1];
|
||||
var queryArray = queryParams.split('&');
|
||||
var params;
|
||||
for (i = 0; i < queryArray.length; i++) {
|
||||
params = queryArray[i].split('=');
|
||||
queryParam[decodeURIComponent(params[0])] = decodeURIComponent(params[1] || '');
|
||||
}
|
||||
}
|
||||
if (queryParam.security) {
|
||||
if (queryParam.security == "tls") {
|
||||
opt.set(dom_prefix + 'tls', true);
|
||||
opt.set(dom_prefix + 'reality', false);
|
||||
opt.set(dom_prefix + 'flow', queryParam.flow || '');
|
||||
opt.set(dom_prefix + 'alpn', queryParam.alpn || 'default');
|
||||
opt.set(dom_prefix + 'tls_serverName', queryParam.sni || '');
|
||||
opt.set(dom_prefix + 'tls_allowInsecure', true);
|
||||
if (queryParam.allowinsecure === '0' || queryParam.insecure === '0') {
|
||||
opt.set(dom_prefix + 'tls_allowInsecure', false);
|
||||
}
|
||||
if (queryParam.fp && queryParam.fp.trim() != "") {
|
||||
opt.set(dom_prefix + 'utls', true);
|
||||
opt.set(dom_prefix + 'fingerprint', queryParam.fp);
|
||||
}
|
||||
}
|
||||
if (queryParam.security == "reality") {
|
||||
opt.set(dom_prefix + 'tls', true);
|
||||
opt.set(dom_prefix + 'reality', true);
|
||||
opt.set(dom_prefix + 'flow', queryParam.flow || '');
|
||||
opt.set(dom_prefix + 'alpn', queryParam.alpn || 'default');
|
||||
opt.set(dom_prefix + 'tls_serverName', queryParam.sni || '');
|
||||
if (queryParam.fp && queryParam.fp.trim() != "") {
|
||||
opt.set(dom_prefix + 'utls', true);
|
||||
opt.set(dom_prefix + 'fingerprint', queryParam.fp);
|
||||
}
|
||||
opt.set(dom_prefix + 'reality_publicKey', queryParam.pbk || '');
|
||||
opt.set(dom_prefix + 'reality_shortId', queryParam.sid || '');
|
||||
}
|
||||
}
|
||||
if (m.hash) {
|
||||
opt.set('remarks', decodeURIComponent(m.hash.substr(1)));
|
||||
}
|
||||
}
|
||||
if (dom_prefix && dom_prefix != null) {
|
||||
if (opt.get(dom_prefix + 'port').value) {
|
||||
opt.get(dom_prefix + 'port').focus();
|
||||
|
|
|
@ -610,6 +610,9 @@ msgstr "填写你不希望被代理转发的端口,优先级最高。"
|
|||
msgid "If you don't want to let the device in the list to go proxy, please choose all."
|
||||
msgstr "如果您不想让列表中的设备走代理,请选择全部。"
|
||||
|
||||
msgid "The port settings support single ports and ranges.<br>Separate multiple ports with commas (,).<br>Example: 21,80,443,1000:2000."
|
||||
msgstr "以上端口设置支持单端口和端口范围。<br>多个端口用英文逗号(,)隔开。<br>例:21,80,443,1000:2000。"
|
||||
|
||||
msgid "TCP Proxy Drop Ports"
|
||||
msgstr "TCP转发屏蔽端口"
|
||||
|
||||
|
|
|
@ -46,6 +46,43 @@ comment() {
|
|||
echo "-m comment --comment '$name'"
|
||||
}
|
||||
|
||||
#解决端口超过15个ipt无效,支持单端口、端口范围
|
||||
add_port_rules() {
|
||||
local ipt_cmd="$1"
|
||||
local port_list="$2"
|
||||
local target="$3"
|
||||
echo "$port_list" | grep -vq '[0-9]' && return
|
||||
port_list=$(echo "$port_list" | tr -d ' ' | sed 's/-/:/g' | tr ',' '\n' | awk '!a[$0]++' | grep -v '^$')
|
||||
[ -z "$port_list" ] && return
|
||||
if echo "$port_list" | grep -q '^1:65535$'; then
|
||||
eval "$ipt_cmd $target"
|
||||
return
|
||||
fi
|
||||
local multiport_ports=""
|
||||
local range_ports=""
|
||||
local count=0
|
||||
local port
|
||||
for port in $port_list; do
|
||||
if echo "$port" | grep -q ':'; then
|
||||
range_ports="$range_ports $port"
|
||||
else
|
||||
multiport_ports="$multiport_ports,$port"
|
||||
count=$((count + 1))
|
||||
if [ "$count" -eq 15 ]; then
|
||||
eval "$ipt_cmd -m multiport --dport ${multiport_ports#,} $target"
|
||||
multiport_ports=""
|
||||
count=0
|
||||
fi
|
||||
fi
|
||||
done
|
||||
if [ -n "$multiport_ports" ]; then
|
||||
eval "$ipt_cmd -m multiport --dport ${multiport_ports#,} $target"
|
||||
fi
|
||||
for port in $range_ports; do
|
||||
eval "$ipt_cmd --dport $port $target"
|
||||
done
|
||||
}
|
||||
|
||||
destroy_ipset() {
|
||||
for i in "$@"; do
|
||||
ipset -q -F $i
|
||||
|
@ -265,6 +302,7 @@ add_shunt_t_rule() {
|
|||
local shunt_args=${1}
|
||||
local t_args=${2}
|
||||
local t_jump_args=${3}
|
||||
local t_ports_args=${4}
|
||||
[ -n "${shunt_args}" ] && {
|
||||
for j in ${shunt_args}; do
|
||||
local _set_name=$(echo ${j} | awk -F ':' '{print $1}')
|
||||
|
@ -272,7 +310,11 @@ add_shunt_t_rule() {
|
|||
[ -n "${_set_name}" ] && [ -n "${_outbound}" ] && {
|
||||
local _t_arg="${t_jump_args}"
|
||||
[ "${_outbound}" = "direct" ] && _t_arg="-j RETURN"
|
||||
if [ -z "${t_ports_args}" ] || [ "${t_ports_args}" == "1:65535" ]; then
|
||||
${t_args} $(dst ${_set_name}) ${_t_arg}
|
||||
else
|
||||
add_port_rules "${t_args} $(dst ${_set_name})" "${t_ports_args}" "${_t_arg}"
|
||||
fi
|
||||
}
|
||||
done
|
||||
}
|
||||
|
@ -375,8 +417,8 @@ load_acl() {
|
|||
|
||||
[ "$tcp_no_redir_ports" != "disable" ] && {
|
||||
if [ "$tcp_no_redir_ports" != "1:65535" ]; then
|
||||
$ip6t_m -A PSW2 $(comment "$remarks") ${_ipt_source} -p tcp -m multiport --dport $tcp_no_redir_ports -j RETURN 2>/dev/null
|
||||
$ipt_tmp -A PSW2 $(comment "$remarks") ${_ipt_source} -p tcp -m multiport --dport $tcp_no_redir_ports -j RETURN
|
||||
add_port_rules "$ip6t_m -A PSW2 $(comment "$remarks") ${_ipt_source} -p tcp" $tcp_no_redir_ports "-j RETURN" 2>/dev/null
|
||||
add_port_rules "$ipt_tmp -A PSW2 $(comment "$remarks") ${_ipt_source} -p tcp" $tcp_no_redir_ports "-j RETURN"
|
||||
echolog " - ${msg}不代理 TCP 端口[${tcp_no_redir_ports}]"
|
||||
else
|
||||
#结束时会return,无需加多余的规则。
|
||||
|
@ -387,8 +429,8 @@ load_acl() {
|
|||
|
||||
[ "$udp_no_redir_ports" != "disable" ] && {
|
||||
if [ "$udp_no_redir_ports" != "1:65535" ]; then
|
||||
$ip6t_m -A PSW2 $(comment "$remarks") ${_ipt_source} -p udp -m multiport --dport $udp_no_redir_ports -j RETURN 2>/dev/null
|
||||
$ipt_m -A PSW2 $(comment "$remarks") ${_ipt_source} -p udp -m multiport --dport $udp_no_redir_ports -j RETURN
|
||||
add_port_rules "$ip6t_m -A PSW2 $(comment "$remarks") ${_ipt_source} -p udp" $udp_no_redir_ports "-j RETURN" 2>/dev/null
|
||||
add_port_rules "$ipt_m -A PSW2 $(comment "$remarks") ${_ipt_source} -p udp" $udp_no_redir_ports "-j RETURN"
|
||||
echolog " - ${msg}不代理 UDP 端口[${udp_no_redir_ports}]"
|
||||
else
|
||||
#结束时会return,无需加多余的规则。
|
||||
|
@ -433,14 +475,14 @@ load_acl() {
|
|||
}
|
||||
|
||||
$ipt_tmp -A PSW2 $(comment "$remarks") -p tcp ${_ipt_source} -d $FAKE_IP ${ipt_j}
|
||||
add_shunt_t_rule "${shunt_list4}" "$ipt_tmp -A PSW2 $(comment "$remarks") -p tcp ${_ipt_source} $(factor $tcp_redir_ports "-m multiport --dport")" "${ipt_j}"
|
||||
$ipt_tmp -A PSW2 $(comment "$remarks") -p tcp ${_ipt_source} $(factor $tcp_redir_ports "-m multiport --dport") ${ipt_j}
|
||||
add_shunt_t_rule "${shunt_list4}" "$ipt_tmp -A PSW2 $(comment "$remarks") -p tcp ${_ipt_source}" "${ipt_j}" $tcp_redir_ports
|
||||
add_port_rules "$ipt_tmp -A PSW2 $(comment "$remarks") -p tcp ${_ipt_source}" $tcp_redir_ports "${ipt_j}"
|
||||
[ -n "${is_tproxy}" ] && $ipt_m -A PSW2 $(comment "$remarks") -p tcp ${_ipt_source} $(REDIRECT $redir_port TPROXY)
|
||||
|
||||
[ "$PROXY_IPV6" == "1" ] && {
|
||||
$ip6t_m -A PSW2 $(comment "$remarks") -p tcp ${_ipt_source} -d $FAKE_IP_6 -j PSW2_RULE 2>/dev/null
|
||||
add_shunt_t_rule "${shunt_list6}" "$ip6t_m -A PSW2 $(comment "$remarks") -p tcp ${_ipt_source} $(factor $tcp_redir_ports "-m multiport --dport")" "${ipt_j}" 2>/dev/null
|
||||
$ip6t_m -A PSW2 $(comment "$remarks") -p tcp ${_ipt_source} $(factor $tcp_redir_ports "-m multiport --dport") -j PSW2_RULE 2>/dev/null
|
||||
add_shunt_t_rule "${shunt_list6}" "$ip6t_m -A PSW2 $(comment "$remarks") -p tcp ${_ipt_source}" "${ipt_j}" $tcp_redir_ports 2>/dev/null
|
||||
add_port_rules "$ip6t_m -A PSW2 $(comment "$remarks") -p tcp ${_ipt_source}" $tcp_redir_ports "-j PSW2_RULE" 2>/dev/null
|
||||
$ip6t_m -A PSW2 $(comment "$remarks") -p tcp ${_ipt_source} $(REDIRECT $redir_port TPROXY) 2>/dev/null
|
||||
}
|
||||
echolog " - ${msg2}"
|
||||
|
@ -452,14 +494,14 @@ load_acl() {
|
|||
msg2="${msg}使用 UDP 节点[$node_remark](TPROXY:${redir_port})"
|
||||
|
||||
$ipt_m -A PSW2 $(comment "$remarks") -p udp ${_ipt_source} -d $FAKE_IP -j PSW2_RULE
|
||||
add_shunt_t_rule "${shunt_list4}" "$ipt_m -A PSW2 $(comment "$remarks") -p udp ${_ipt_source} $(factor $udp_redir_ports "-m multiport --dport")" "-j PSW2_RULE"
|
||||
$ipt_m -A PSW2 $(comment "$remarks") -p udp ${_ipt_source} $(factor $udp_redir_ports "-m multiport --dport") -j PSW2_RULE
|
||||
add_shunt_t_rule "${shunt_list4}" "$ipt_m -A PSW2 $(comment "$remarks") -p udp ${_ipt_source}" "-j PSW2_RULE" $udp_redir_ports
|
||||
add_port_rules "$ipt_m -A PSW2 $(comment "$remarks") -p udp ${_ipt_source}" $udp_redir_ports "-j PSW2_RULE"
|
||||
$ipt_m -A PSW2 $(comment "$remarks") -p udp ${_ipt_source} $(REDIRECT $redir_port TPROXY)
|
||||
|
||||
[ "$PROXY_IPV6" == "1" ] && {
|
||||
$ip6t_m -A PSW2 $(comment "$remarks") -p udp ${_ipt_source} -d $FAKE_IP_6 -j PSW2_RULE 2>/dev/null
|
||||
add_shunt_t_rule "${shunt_list6}" "$ip6t_m -A PSW2 $(comment "$remarks") -p udp ${_ipt_source} $(factor $udp_redir_ports "-m multiport --dport")" "-j PSW2_RULE" 2>/dev/null
|
||||
$ip6t_m -A PSW2 $(comment "$remarks") -p udp ${_ipt_source} $(factor $udp_redir_ports "-m multiport --dport") -j PSW2_RULE 2>/dev/null
|
||||
add_shunt_t_rule "${shunt_list6}" "$ip6t_m -A PSW2 $(comment "$remarks") -p udp ${_ipt_source}" "-j PSW2_RULE" $udp_redir_ports 2>/dev/null
|
||||
add_port_rules "$ip6t_m -A PSW2 $(comment "$remarks") -p udp ${_ipt_source}" $udp_redir_ports "-j PSW2_RULE" 2>/dev/null
|
||||
$ip6t_m -A PSW2 $(comment "$remarks") -p udp ${_ipt_source} $(REDIRECT $redir_port TPROXY) 2>/dev/null
|
||||
}
|
||||
echolog " - ${msg2}"
|
||||
|
@ -480,8 +522,8 @@ load_acl() {
|
|||
[ -n "${is_tproxy}" ] && ipt_tmp=$ipt_m
|
||||
|
||||
[ "$TCP_NO_REDIR_PORTS" != "disable" ] && {
|
||||
$ip6t_m -A PSW2 $(comment "默认") -p tcp -m multiport --dport $TCP_NO_REDIR_PORTS -j RETURN
|
||||
$ipt_tmp -A PSW2 $(comment "默认") -p tcp -m multiport --dport $TCP_NO_REDIR_PORTS -j RETURN
|
||||
add_port_rules "$ip6t_m -A PSW2 $(comment "默认") -p tcp" $TCP_NO_REDIR_PORTS "-j RETURN"
|
||||
add_port_rules "$ipt_tmp -A PSW2 $(comment "默认") -p tcp" $TCP_NO_REDIR_PORTS "-j RETURN"
|
||||
if [ "$TCP_NO_REDIR_PORTS" != "1:65535" ]; then
|
||||
echolog " - ${msg}不代理 TCP 端口[${TCP_NO_REDIR_PORTS}]"
|
||||
else
|
||||
|
@ -491,8 +533,8 @@ load_acl() {
|
|||
}
|
||||
|
||||
[ "$UDP_NO_REDIR_PORTS" != "disable" ] && {
|
||||
$ip6t_m -A PSW2 $(comment "默认") -p udp -m multiport --dport $UDP_NO_REDIR_PORTS -j RETURN
|
||||
$ipt_m -A PSW2 $(comment "默认") -p udp -m multiport --dport $UDP_NO_REDIR_PORTS -j RETURN
|
||||
add_port_rules "$ip6t_m -A PSW2 $(comment "默认") -p udp" $UDP_NO_REDIR_PORTS "-j RETURN"
|
||||
add_port_rules "$ipt_tmp -A PSW2 $(comment "默认") -p udp" $UDP_NO_REDIR_PORTS "-j RETURN"
|
||||
if [ "$UDP_NO_REDIR_PORTS" != "1:65535" ]; then
|
||||
echolog " - ${msg}不代理 UDP 端口[${UDP_NO_REDIR_PORTS}]"
|
||||
else
|
||||
|
@ -533,14 +575,14 @@ load_acl() {
|
|||
}
|
||||
|
||||
$ipt_tmp -A PSW2 $(comment "默认") -p tcp -d $FAKE_IP ${ipt_j}
|
||||
add_shunt_t_rule "${SHUNT_LIST4}" "$ipt_tmp -A PSW2 $(comment "默认") -p tcp $(factor $TCP_REDIR_PORTS "-m multiport --dport")" "${ipt_j}"
|
||||
$ipt_tmp -A PSW2 $(comment "默认") -p tcp $(factor $TCP_REDIR_PORTS "-m multiport --dport") ${ipt_j}
|
||||
add_shunt_t_rule "${SHUNT_LIST4}" "$ipt_tmp -A PSW2 $(comment "默认") -p tcp" "${ipt_j}" $TCP_REDIR_PORTS
|
||||
add_port_rules "$ipt_tmp -A PSW2 $(comment "默认") -p tcp" $TCP_REDIR_PORTS "${ipt_j}"
|
||||
[ -n "${is_tproxy}" ] && $ipt_m -A PSW2 $(comment "默认") -p tcp $(REDIRECT $REDIR_PORT TPROXY)
|
||||
|
||||
[ "$PROXY_IPV6" == "1" ] && {
|
||||
$ip6t_m -A PSW2 $(comment "默认") -p tcp -d $FAKE_IP_6 -j PSW2_RULE
|
||||
add_shunt_t_rule "${SHUNT_LIST6}" "$ip6t_m -A PSW2 $(comment "默认") -p tcp $(factor $TCP_REDIR_PORTS "-m multiport --dport")" "-j PSW2_RULE"
|
||||
$ip6t_m -A PSW2 $(comment "默认") -p tcp $(factor $TCP_REDIR_PORTS "-m multiport --dport") -j PSW2_RULE
|
||||
add_shunt_t_rule "${SHUNT_LIST6}" "$ip6t_m -A PSW2 $(comment "默认") -p tcp" "-j PSW2_RULE" $TCP_REDIR_PORTS
|
||||
add_port_rules "$ip6t_m -A PSW2 $(comment "默认") -p tcp" $TCP_REDIR_PORTS "-j PSW2_RULE"
|
||||
$ip6t_m -A PSW2 $(comment "默认") -p tcp $(REDIRECT $REDIR_PORT TPROXY)
|
||||
}
|
||||
|
||||
|
@ -551,14 +593,14 @@ load_acl() {
|
|||
msg2="${msg}使用 UDP 节点[$(config_n_get $NODE remarks)](TPROXY:${REDIR_PORT})"
|
||||
|
||||
$ipt_m -A PSW2 $(comment "默认") -p udp -d $FAKE_IP -j PSW2_RULE
|
||||
add_shunt_t_rule "${SHUNT_LIST4}" "$ipt_m -A PSW2 $(comment "默认") -p udp $(factor $UDP_REDIR_PORTS "-m multiport --dport")" "-j PSW2_RULE"
|
||||
$ipt_m -A PSW2 $(comment "默认") -p udp $(factor $UDP_REDIR_PORTS "-m multiport --dport") -j PSW2_RULE
|
||||
add_shunt_t_rule "${SHUNT_LIST4}" "$ipt_m -A PSW2 $(comment "默认") -p udp" "-j PSW2_RULE" $UDP_REDIR_PORTS
|
||||
add_port_rules "$ipt_m -A PSW2 $(comment "默认") -p udp" $UDP_REDIR_PORTS "-j PSW2_RULE"
|
||||
$ipt_m -A PSW2 $(comment "默认") -p udp $(REDIRECT $REDIR_PORT TPROXY)
|
||||
|
||||
[ "$PROXY_IPV6" == "1" ] && {
|
||||
$ip6t_m -A PSW2 $(comment "默认") -p udp -d $FAKE_IP_6 -j PSW2_RULE
|
||||
add_shunt_t_rule "${SHUNT_LIST6}" "$ip6t_m -A PSW2 $(comment "默认") -p udp $(factor $UDP_REDIR_PORTS "-m multiport --dport")" "-j PSW2_RULE"
|
||||
$ip6t_m -A PSW2 $(comment "默认") -p udp $(factor $UDP_REDIR_PORTS "-m multiport --dport") -j PSW2_RULE
|
||||
add_shunt_t_rule "${SHUNT_LIST6}" "$ip6t_m -A PSW2 $(comment "默认") -p udp" "-j PSW2_RULE" $UDP_REDIR_PORTS
|
||||
add_port_rules "$ip6t_m -A PSW2 $(comment "默认") -p udp" $UDP_REDIR_PORTS "-j PSW2_RULE"
|
||||
$ip6t_m -A PSW2 $(comment "默认") -p udp $(REDIRECT $REDIR_PORT TPROXY)
|
||||
}
|
||||
|
||||
|
@ -825,8 +867,8 @@ add_firewall_rule() {
|
|||
|
||||
msg="【路由器本机】,"
|
||||
[ "$TCP_NO_REDIR_PORTS" != "disable" ] && {
|
||||
$ipt_tmp -A PSW2_OUTPUT -p tcp -m multiport --dport $TCP_NO_REDIR_PORTS -j RETURN
|
||||
$ip6t_m -A PSW2_OUTPUT -p tcp -m multiport --dport $TCP_NO_REDIR_PORTS -j RETURN
|
||||
add_port_rules "$ipt_tmp -A PSW2_OUTPUT -p tcp" $TCP_NO_REDIR_PORTS "-j RETURN"
|
||||
add_port_rules "$ip6t_m -A PSW2_OUTPUT -p tcp" $TCP_NO_REDIR_PORTS "-j RETURN"
|
||||
if [ "$TCP_NO_REDIR_PORTS" != "1:65535" ]; then
|
||||
echolog " - ${msg}不代理 TCP 端口[${TCP_NO_REDIR_PORTS}]"
|
||||
else
|
||||
|
@ -836,8 +878,8 @@ add_firewall_rule() {
|
|||
}
|
||||
|
||||
[ "$UDP_NO_REDIR_PORTS" != "disable" ] && {
|
||||
$ipt_m -A PSW2_OUTPUT -p udp -m multiport --dport $UDP_NO_REDIR_PORTS -j RETURN
|
||||
$ip6t_m -A PSW2_OUTPUT -p udp -m multiport --dport $UDP_NO_REDIR_PORTS -j RETURN
|
||||
add_port_rules "$ipt_m -A PSW2_OUTPUT -p udp" $UDP_NO_REDIR_PORTS "-j RETURN"
|
||||
add_port_rules "$ip6t_m -A PSW2_OUTPUT -p udp" $UDP_NO_REDIR_PORTS "-j RETURN"
|
||||
if [ "$UDP_NO_REDIR_PORTS" != "1:65535" ]; then
|
||||
echolog " - ${msg}不代理 UDP 端口[${UDP_NO_REDIR_PORTS}]"
|
||||
else
|
||||
|
@ -878,8 +920,8 @@ add_firewall_rule() {
|
|||
fi
|
||||
|
||||
$ipt_tmp -A PSW2_OUTPUT -p tcp -d $FAKE_IP ${ipt_j}
|
||||
add_shunt_t_rule "${SHUNT_LIST4}" "$ipt_tmp -A PSW2_OUTPUT -p tcp $(factor $TCP_REDIR_PORTS "-m multiport --dport")" "${ipt_j}"
|
||||
$ipt_tmp -A PSW2_OUTPUT -p tcp $(factor $TCP_REDIR_PORTS "-m multiport --dport") ${ipt_j}
|
||||
add_shunt_t_rule "${SHUNT_LIST4}" "$ipt_tmp -A PSW2_OUTPUT -p tcp" "${ipt_j}" $TCP_REDIR_PORTS
|
||||
add_port_rules "$ipt_tmp -A PSW2_OUTPUT -p tcp" $TCP_REDIR_PORTS "${ipt_j}"
|
||||
[ -z "${is_tproxy}" ] && $ipt_n -A OUTPUT -p tcp -j PSW2_OUTPUT
|
||||
[ -n "${is_tproxy}" ] && {
|
||||
$ipt_m -A PSW2 $(comment "本机") -p tcp -i lo $(REDIRECT $REDIR_PORT TPROXY)
|
||||
|
@ -889,8 +931,8 @@ add_firewall_rule() {
|
|||
|
||||
[ "$PROXY_IPV6" == "1" ] && {
|
||||
$ip6t_m -A PSW2_OUTPUT -p tcp -d $FAKE_IP_6 -j PSW2_RULE
|
||||
add_shunt_t_rule "${SHUNT_LIST6}" "$ip6t_m -A PSW2_OUTPUT -p tcp $(factor $TCP_REDIR_PORTS "-m multiport --dport")" "-j PSW2_RULE"
|
||||
$ip6t_m -A PSW2_OUTPUT -p tcp $(factor $TCP_REDIR_PORTS "-m multiport --dport") -j PSW2_RULE
|
||||
add_shunt_t_rule "${SHUNT_LIST6}" "$ip6t_m -A PSW2_OUTPUT -p tcp" "-j PSW2_RULE" $TCP_REDIR_PORTS
|
||||
add_port_rules "$ip6t_m -A PSW2_OUTPUT -p tcp" $TCP_REDIR_PORTS "-j PSW2_RULE"
|
||||
$ip6t_m -A PSW2 $(comment "本机") -p tcp -i lo $(REDIRECT $REDIR_PORT TPROXY)
|
||||
$ip6t_m -A PSW2 $(comment "本机") -p tcp -i lo -j RETURN
|
||||
insert_rule_before "$ip6t_m" "OUTPUT" "mwan3" "$(comment mangle-OUTPUT-PSW2) -p tcp -j PSW2_OUTPUT"
|
||||
|
@ -907,16 +949,16 @@ add_firewall_rule() {
|
|||
# 加载路由器自身代理 UDP
|
||||
if [ -n "$NODE" ] && [ "$UDP_LOCALHOST_PROXY" = "1" ]; then
|
||||
$ipt_m -A PSW2_OUTPUT -p udp -d $FAKE_IP -j PSW2_RULE
|
||||
add_shunt_t_rule "${SHUNT_LIST4}" "$ipt_m -A PSW2_OUTPUT -p udp $(factor $UDP_REDIR_PORTS "-m multiport --dport")" "-j PSW2_RULE"
|
||||
$ipt_m -A PSW2_OUTPUT -p udp $(factor $UDP_REDIR_PORTS "-m multiport --dport") -j PSW2_RULE
|
||||
add_shunt_t_rule "${SHUNT_LIST4}" "$ipt_m -A PSW2_OUTPUT -p udp" "-j PSW2_RULE" $UDP_REDIR_PORTS
|
||||
add_port_rules "$ipt_m -A PSW2_OUTPUT -p udp" $UDP_REDIR_PORTS "-j PSW2_RULE"
|
||||
$ipt_m -A PSW2 $(comment "本机") -p udp -i lo $(REDIRECT $REDIR_PORT TPROXY)
|
||||
$ipt_m -A PSW2 $(comment "本机") -p udp -i lo -j RETURN
|
||||
insert_rule_before "$ipt_m" "OUTPUT" "mwan3" "$(comment mangle-OUTPUT-PSW2) -p udp -j PSW2_OUTPUT"
|
||||
|
||||
[ "$PROXY_IPV6" == "1" ] && {
|
||||
$ip6t_m -A PSW2_OUTPUT -p udp -d $FAKE_IP_6 -j PSW2_RULE
|
||||
add_shunt_t_rule "${SHUNT_LIST6}" "$ip6t_m -A PSW2_OUTPUT -p udp $(factor $UDP_REDIR_PORTS "-m multiport --dport")" "-j PSW2_RULE"
|
||||
$ip6t_m -A PSW2_OUTPUT -p udp $(factor $UDP_REDIR_PORTS "-m multiport --dport") -j PSW2_RULE
|
||||
add_shunt_t_rule "${SHUNT_LIST6}" "$ip6t_m -A PSW2_OUTPUT -p udp" "-j PSW2_RULE" $UDP_REDIR_PORTS
|
||||
add_port_rules "$ip6t_m -A PSW2_OUTPUT -p udp" $UDP_REDIR_PORTS "-j PSW2_RULE"
|
||||
$ip6t_m -A PSW2 $(comment "本机") -p udp -i lo $(REDIRECT $REDIR_PORT TPROXY)
|
||||
$ip6t_m -A PSW2 $(comment "本机") -p udp -i lo -j RETURN
|
||||
insert_rule_before "$ip6t_m" "OUTPUT" "mwan3" "$(comment mangle-OUTPUT-PSW2) -p udp -j PSW2_OUTPUT"
|
||||
|
|
|
@ -20,15 +20,26 @@ FAKE_IP="198.18.0.0/16"
|
|||
FAKE_IP_6="fc00::/18"
|
||||
|
||||
factor() {
|
||||
if [ -z "$1" ] || [ -z "$2" ]; then
|
||||
echo ""
|
||||
elif [ "$1" == "1:65535" ]; then
|
||||
local ports="$1"
|
||||
if [ -z "$1" ] || [ -z "$2" ] || [ "$ports" = "1:65535" ]; then
|
||||
echo ""
|
||||
# acl mac address
|
||||
elif [ -n "$(echo $1 | grep -E '([A-Fa-f0-9]{2}:){5}[A-Fa-f0-9]{2}')" ]; then
|
||||
elif echo "$1" | grep -qE '([A-Fa-f0-9]{2}:){5}[A-Fa-f0-9]{2}'; then
|
||||
echo "$2 {$1}"
|
||||
else
|
||||
echo "$2 {$(echo $1 | sed 's/:/-/g')}"
|
||||
ports=$(echo "$ports" | tr -d ' ' | sed 's/:/-/g' | tr ',' '\n' | awk '!a[$0]++' | grep -v '^$')
|
||||
[ -z "$ports" ] && { echo ""; return; }
|
||||
if echo "$ports" | grep -q '^1-65535$'; then
|
||||
echo ""
|
||||
return
|
||||
fi
|
||||
local port
|
||||
local port_list=""
|
||||
for port in $ports; do
|
||||
port_list="${port_list},$port"
|
||||
done
|
||||
port_list="${port_list#,}"
|
||||
echo "$2 {$port_list}"
|
||||
fi
|
||||
}
|
||||
|
||||
|
|
|
@ -543,8 +543,8 @@ local function processData(szType, content, add_mode, add_from)
|
|||
info.type = "none"
|
||||
end
|
||||
result.tcp_guise = info.type
|
||||
result.tcp_guise_http_host = info.host
|
||||
result.tcp_guise_http_path = info.path
|
||||
result.tcp_guise_http_host = (info.host and info.host ~= "") and { info.host } or nil
|
||||
result.tcp_guise_http_path = (info.path and info.path ~= "") and { info.path } or nil
|
||||
end
|
||||
if info.net == 'kcp' or info.net == 'mkcp' then
|
||||
info.net = "mkcp"
|
||||
|
@ -586,7 +586,12 @@ local function processData(szType, content, add_mode, add_from)
|
|||
if info.tls == "tls" or info.tls == "1" then
|
||||
result.tls = "1"
|
||||
result.tls_serverName = (info.sni and info.sni ~= "") and info.sni or info.host
|
||||
info.allowinsecure = info.allowinsecure or info.insecure
|
||||
if info.allowinsecure and (info.allowinsecure == "1" or info.allowinsecure == "0") then
|
||||
result.tls_allowInsecure = info.allowinsecure
|
||||
else
|
||||
result.tls_allowInsecure = allowInsecure_default and "1" or "0"
|
||||
end
|
||||
else
|
||||
result.tls = "0"
|
||||
end
|
||||
|
@ -692,8 +697,27 @@ local function processData(szType, content, add_mode, add_from)
|
|||
|
||||
if result.plugin then
|
||||
if result.type == 'Xray' then
|
||||
--不支持插件
|
||||
result.error_msg = "Xray不支持插件."
|
||||
-- obfs-local插件转换成xray支持的格式
|
||||
if result.plugin ~= "obfs-local" then
|
||||
result.error_msg = "Xray不支持 " .. result.plugin .. " 插件."
|
||||
else
|
||||
local obfs = result.plugin_opts:match("obfs=([^;]+)") or ""
|
||||
local obfs_host = result.plugin_opts:match("obfs%-host=([^;]+)") or ""
|
||||
if obfs == "" or obfs_host == "" then
|
||||
result.error_msg = "SS " .. result.plugin .. " 插件选项不完整."
|
||||
end
|
||||
if obfs == "http" then
|
||||
result.transport = "raw"
|
||||
result.tcp_guise = "http"
|
||||
result.tcp_guise_http_host = (obfs_host and obfs_host ~= "") and { obfs_host } or nil
|
||||
elseif obfs == "tls" then
|
||||
result.tls = "1"
|
||||
result.tls_serverName = obfs_host
|
||||
result.tls_allowInsecure = "1"
|
||||
end
|
||||
result.plugin = nil
|
||||
result.plugin_opts = nil
|
||||
end
|
||||
end
|
||||
if result.type == "sing-box" then
|
||||
result.plugin_enabled = "1"
|
||||
|
@ -761,8 +785,8 @@ local function processData(szType, content, add_mode, add_from)
|
|||
end
|
||||
if params.type == 'raw' or params.type == 'tcp' then
|
||||
result.tcp_guise = params.headerType or "none"
|
||||
result.tcp_guise_http_host = params.host
|
||||
result.tcp_guise_http_path = params.path
|
||||
result.tcp_guise_http_host = (params.host and params.host ~= "") and { params.host } or nil
|
||||
result.tcp_guise_http_path = (params.path and params.path ~= "") and { params.path } or nil
|
||||
end
|
||||
if params.type == 'kcp' or params.type == 'mkcp' then
|
||||
result.transport = "mkcp"
|
||||
|
@ -790,7 +814,10 @@ local function processData(szType, content, add_mode, add_from)
|
|||
result.tls = "1"
|
||||
result.tls_serverName = (params.sni and params.sni ~= "") and params.sni or params.host
|
||||
result.alpn = params.alpn
|
||||
result.fingerprint = (params.fp and params.fp ~= "") and params.fp or "chrome"
|
||||
if params.fp and params.fp ~= "" then
|
||||
result.utls = "1"
|
||||
result.fingerprint = params.fp
|
||||
end
|
||||
if params.security == "reality" then
|
||||
result.reality = "1"
|
||||
result.reality_publicKey = params.pbk or nil
|
||||
|
@ -798,7 +825,12 @@ local function processData(szType, content, add_mode, add_from)
|
|||
result.reality_spiderX = params.spx or nil
|
||||
end
|
||||
end
|
||||
params.allowinsecure = params.allowinsecure or params.insecure
|
||||
if params.allowinsecure and (params.allowinsecure == "1" or params.allowinsecure == "0") then
|
||||
result.tls_allowInsecure = params.allowinsecure
|
||||
else
|
||||
result.tls_allowInsecure = allowInsecure_default and "1" or "0"
|
||||
end
|
||||
else
|
||||
result.error_msg = "请更换Xray或Sing-Box来支持SS更多的传输方式."
|
||||
end
|
||||
|
@ -860,6 +892,7 @@ local function processData(szType, content, add_mode, add_from)
|
|||
result.tls = '1'
|
||||
result.tls_serverName = peer and peer or sni
|
||||
|
||||
params.allowinsecure = params.allowinsecure or params.insecure
|
||||
if params.allowinsecure then
|
||||
if params.allowinsecure == "1" or params.allowinsecure == "0" then
|
||||
result.tls_allowInsecure = params.allowinsecure
|
||||
|
@ -917,8 +950,8 @@ local function processData(szType, content, add_mode, add_from)
|
|||
end
|
||||
if params.type == 'raw' or params.type == 'tcp' then
|
||||
result.tcp_guise = params.headerType or "none"
|
||||
result.tcp_guise_http_host = params.host
|
||||
result.tcp_guise_http_path = params.path
|
||||
result.tcp_guise_http_host = (params.host and params.host ~= "") and { params.host } or nil
|
||||
result.tcp_guise_http_path = (params.path and params.path ~= "") and { params.path } or nil
|
||||
end
|
||||
if params.type == 'kcp' or params.type == 'mkcp' then
|
||||
result.transport = "mkcp"
|
||||
|
@ -1062,8 +1095,8 @@ local function processData(szType, content, add_mode, add_from)
|
|||
end
|
||||
if params.type == 'raw' or params.type == 'tcp' then
|
||||
result.tcp_guise = params.headerType or "none"
|
||||
result.tcp_guise_http_host = params.host
|
||||
result.tcp_guise_http_path = params.path
|
||||
result.tcp_guise_http_host = (params.host and params.host ~= "") and { params.host } or nil
|
||||
result.tcp_guise_http_path = (params.path and params.path ~= "") and { params.path } or nil
|
||||
end
|
||||
if params.type == 'kcp' or params.type == 'mkcp' then
|
||||
result.transport = "mkcp"
|
||||
|
@ -1114,7 +1147,10 @@ local function processData(szType, content, add_mode, add_from)
|
|||
result.tls = "1"
|
||||
result.tls_serverName = (params.sni and params.sni ~= "") and params.sni or params.host
|
||||
result.alpn = params.alpn
|
||||
result.fingerprint = (params.fp and params.fp ~= "") and params.fp or "chrome"
|
||||
if params.fp and params.fp ~= "" then
|
||||
result.utls = "1"
|
||||
result.fingerprint = params.fp
|
||||
end
|
||||
if params.security == "reality" then
|
||||
result.reality = "1"
|
||||
result.reality_publicKey = params.pbk or nil
|
||||
|
@ -1124,7 +1160,13 @@ local function processData(szType, content, add_mode, add_from)
|
|||
end
|
||||
|
||||
result.port = port
|
||||
|
||||
params.allowinsecure = params.allowinsecure or params.insecure
|
||||
if params.allowinsecure and (params.allowinsecure == "1" or params.allowinsecure == "0") then
|
||||
result.tls_allowInsecure = params.allowinsecure
|
||||
else
|
||||
result.tls_allowInsecure = allowInsecure_default and "1" or "0"
|
||||
end
|
||||
|
||||
if result.type == "sing-box" and (result.transport == "mkcp" or result.transport == "xhttp" or result.transport == "splithttp") then
|
||||
log("跳过节点:" .. result.remarks ..",因Sing-Box不支持" .. szType .. "协议的" .. result.transport .. "传输方式,需更换Xray。")
|
||||
|
@ -1167,8 +1209,12 @@ local function processData(szType, content, add_mode, add_from)
|
|||
result.hysteria_auth_type = "string"
|
||||
result.hysteria_auth_password = params.auth
|
||||
result.tls_serverName = params.peer
|
||||
if params.insecure and params.insecure == "1" then
|
||||
result.tls_allowInsecure = "1"
|
||||
params.allowinsecure = params.allowinsecure or params.insecure
|
||||
if params.allowinsecure and (params.allowinsecure == "1" or params.allowinsecure == "0") then
|
||||
result.tls_allowInsecure = params.allowinsecure
|
||||
--log(result.remarks ..' 使用节点AllowInsecure设定: '.. result.tls_allowInsecure)
|
||||
else
|
||||
result.tls_allowInsecure = allowInsecure_default and "1" or "0"
|
||||
end
|
||||
result.hysteria_alpn = params.alpn
|
||||
result.hysteria_up_mbps = params.upmbps
|
||||
|
@ -1215,8 +1261,9 @@ local function processData(szType, content, add_mode, add_from)
|
|||
result.address = host_port
|
||||
end
|
||||
result.tls_serverName = params.sni
|
||||
if params.insecure and (params.insecure == "1" or params.insecure == "0") then
|
||||
result.tls_allowInsecure = params.insecure
|
||||
params.allowinsecure = params.allowinsecure or params.insecure
|
||||
if params.allowinsecure and (params.allowinsecure == "1" or params.allowinsecure == "0") then
|
||||
result.tls_allowInsecure = params.allowinsecure
|
||||
--log(result.remarks ..' 使用节点AllowInsecure设定: '.. result.tls_allowInsecure)
|
||||
else
|
||||
result.tls_allowInsecure = allowInsecure_default and "1" or "0"
|
||||
|
@ -1278,6 +1325,7 @@ local function processData(szType, content, add_mode, add_from)
|
|||
result.tls_serverName = params.sni
|
||||
result.tuic_alpn = params.alpn or "default"
|
||||
result.tuic_congestion_control = params.congestion_control or "cubic"
|
||||
params.allowinsecure = params.allowinsecure or params.insecure
|
||||
if params.allowinsecure then
|
||||
if params.allowinsecure == "1" or params.allowinsecure == "0" then
|
||||
result.tls_allowInsecure = params.allowinsecure
|
||||
|
@ -1290,6 +1338,70 @@ local function processData(szType, content, add_mode, add_from)
|
|||
end
|
||||
result.type = 'sing-box'
|
||||
result.protocol = "tuic"
|
||||
elseif szType == "anytls" then
|
||||
result.type = 'sing-box'
|
||||
result.protocol = "anytls"
|
||||
local alias = ""
|
||||
if content:find("#") then
|
||||
local idx_sp = content:find("#")
|
||||
alias = content:sub(idx_sp + 1, -1)
|
||||
content = content:sub(0, idx_sp - 1)
|
||||
end
|
||||
result.remarks = UrlDecode(alias)
|
||||
if content:find("@") then
|
||||
local Info = split(content, "@")
|
||||
result.password = UrlDecode(Info[1])
|
||||
local port = "443"
|
||||
Info[2] = (Info[2] or ""):gsub("/%?", "?")
|
||||
local query = split(Info[2], "?")
|
||||
local host_port = query[1]
|
||||
local params = {}
|
||||
for _, v in pairs(split(query[2], '&')) do
|
||||
local t = split(v, '=')
|
||||
params[t[1]] = UrlDecode(t[2])
|
||||
end
|
||||
-- [2001:4860:4860::8888]:443
|
||||
-- 8.8.8.8:443
|
||||
if host_port:find(":") then
|
||||
local sp = split(host_port, ":")
|
||||
port = sp[#sp]
|
||||
if api.is_ipv6addrport(host_port) then
|
||||
result.address = api.get_ipv6_only(host_port)
|
||||
else
|
||||
result.address = sp[1]
|
||||
end
|
||||
else
|
||||
result.address = host_port
|
||||
end
|
||||
result.tls = "0"
|
||||
if params.security == "tls" or params.security == "reality" then
|
||||
result.tls = "1"
|
||||
result.tls_serverName = (params.sni and params.sni ~= "") and params.sni or params.host
|
||||
result.alpn = params.alpn
|
||||
if params.fp and params.fp ~= "" then
|
||||
result.utls = "1"
|
||||
result.fingerprint = params.fp
|
||||
end
|
||||
if params.security == "reality" then
|
||||
result.reality = "1"
|
||||
result.reality_publicKey = params.pbk or nil
|
||||
result.reality_shortId = params.sid or nil
|
||||
end
|
||||
end
|
||||
result.port = port
|
||||
params.allowinsecure = params.allowinsecure or params.insecure
|
||||
if params.allowinsecure and (params.allowinsecure == "1" or params.allowinsecure == "0") then
|
||||
result.tls_allowInsecure = params.allowinsecure
|
||||
else
|
||||
result.tls_allowInsecure = allowInsecure_default and "1" or "0"
|
||||
end
|
||||
local singbox_version = api.get_app_version("sing-box")
|
||||
local version_ge_1_12 = api.compare_versions(singbox_version:match("[^v]+"), ">=", "1.12.0")
|
||||
if not has_singbox or not version_ge_1_12 then
|
||||
log("跳过节点:" .. result.remarks ..",因" .. szType .. "类型的节点需要 Sing-Box 1.12 以上版本支持。")
|
||||
return nil
|
||||
end
|
||||
end
|
||||
else
|
||||
log('暂时不支持' .. szType .. "类型的节点订阅,跳过此节点。")
|
||||
return nil
|
||||
|
@ -1512,6 +1624,9 @@ local function update_node(manual)
|
|||
for _, vv in ipairs(list) do
|
||||
local cfgid = uci:section(appname, "nodes", api.gen_short_uuid())
|
||||
for kkk, vvv in pairs(vv) do
|
||||
if type(vvv) == "table" and next(vvv) ~= nil then
|
||||
uci:set_list(appname, cfgid, kkk, vvv)
|
||||
else
|
||||
uci:set(appname, cfgid, kkk, vvv)
|
||||
-- sing-box 域名解析策略
|
||||
if kkk == "type" and vvv == "sing-box" then
|
||||
|
@ -1520,6 +1635,7 @@ local function update_node(manual)
|
|||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
-- 更新机场信息
|
||||
for cfgid, info in pairs(subscribe_info) do
|
||||
for key, value in pairs(info) do
|
||||
|
|
Loading…
Reference in New Issue