Merge source of CTCGFW

This commit is contained in:
CN_SZTL 2019-12-15 11:07:11 +08:00
parent 0f39011c13
commit 6eaee82a10
No known key found for this signature in database
GPG Key ID: 6850B6345C862176
34 changed files with 6731 additions and 364 deletions

View File

@ -11,14 +11,14 @@
include $(TOPDIR)/rules.mk
PKG_NAME:=UnblockNeteaseMusic
PKG_VERSION:=0.20.4
PKG_VERSION:=0.22.1
PKG_RELEASE:=1
PKG_LICENSE:=MIT
PKG_SOURCE_PROTO:=git
PKG_SOURCE_URL:=https://github.com/nondanee/UnblockNeteaseMusic.git
PKG_SOURCE_VERSION:=023a97f0e62d322a8d64c59ef3942da7c8a1b546
PKG_SOURCE_VERSION:=c727245b8de201b91ae859c6ae1412c77ef25cf0
PKG_SOURCE_SUBDIR:=$(PKG_NAME)
PKG_SOURCE:=$(PKG_SOURCE_SUBDIR)-$(PKG_VERSION).tar.gz

View File

@ -1,16 +1,15 @@
# Copyright (C) 2019 Openwrt.org
#
# This is a free software, use it under Apache Licene 2.0 & GNU General Public License v3.0.
# This is free software, licensed under the Apache License, Version 2.0 .
#
include $(TOPDIR)/rules.mk
LUCI_TITLE:=qbittorrent-nox for LuCI
LUCI_DEPENDS:=+qBittorrent
LUCI_TITLE:=LuCI support for qBittorrent
LUCI_DEPENDS:=+qBittorrent +python
LUCI_PKGARCH:=all
PKG_NAME:=luci-app-qbittorrent
PKG_VERSION=1.0
PKG_RELEASE:=4
PKG_RELEASE:=18
include $(TOPDIR)/feeds/luci/luci.mk

View File

@ -1,4 +1,16 @@
module("luci.controller.qbittorrent",package.seeall)
function index()
entry({"admin","nas","qbittorrent"},cbi("qbittorrent"),_("qbittorrent"))
if not nixio.fs.access("/etc/config/qbittorrent")then
return
end
entry({"admin","nas","qBittorrent"},cbi("qbittorrent"),_("qBittorrent"))
entry({"admin","nas","qBittorrent","status"},call("act_status")).leaf=true
end
function act_status()
local e={}
e.running=luci.sys.call("pgrep qbittorrent-nox >/dev/null")==0
luci.http.prepare_content("application/json")
luci.http.write_json(e)
end

View File

@ -1,44 +1,371 @@
require("luci.sys")
local e=require"luci.model.uci".cursor()
local o=e:get_first("qbittorrent","Preferences","port")or 8080
local o=luci.sys.exec("uci get qbittorrent.main.Port | xargs echo -n") or 8080
local a=(luci.sys.call("pidof qbittorrent-nox > /dev/null")==0)
local t=""
local e=""
if a then
t="&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<input class=\"cbi-button cbi-button-apply\" type=\"submit\" value=\" "..translate("Open Web Interface").." \" onclick=\"window.open('http://'+window.location.hostname+':"..o.."')\"/>"
end
if a then
e="<b><font color=\"green\">"..translate("Running").."</font></b>"
else
e="<b><font color=\"red\">"..translate("Not running").."</font></b>"
t="<br /><br /><input class=\"cbi-button cbi-button-apply\" type=\"button\" value=\" "..translate("Open Web Interface").." \" onclick=\"window.open('http://'+window.location.hostname+':"..o.."')\"/>"
end
m = Map("qbittorrent", translate("qbittorrent"), translate("A BT/PT downloader base on Qt")..t
.."<br/><br/>"..translate("qbittorrent Run Status").." : "..e.."<br/>")
s_basic = m:section(TypedSection, "basic", translate("Basic Settings"))
s_basic.anonymous = true
enable = s_basic:option(Flag, "enable", translate("Enable"))
profile_dir = s_basic:option(Value,"profile_dir",translate("profile_dir"),translate("Store configuration files in the Path"))
profile_dir.default = "/tmp"
program_dir = s_basic:option(Value,"program_dir",translate("program_dir"),translate("Store Program files in the Path"))
program_dir.default = "/usr/bin"
library_dir = s_basic:option(Value,"library_dir",translate("library_dir"),translate("Store Library in the Path"))
library_dir.default = "/usr/lib"
s_download = m:section(TypedSection, "Preferences", translate("Download Settings"))
s_download.anonymous = true
download_dir = s_download:option(Value,"download_dir",translate("download_dir"),translate("Store download files in the Path"))
download_dir.default = "/tmp/download"
s_webui = m:section(TypedSection, "Preferences", translate("WEBUI Settings"))
s_webui.anonymous = true
port = s_webui:option(Value,"port",translate("port"),translate("WEBUI listening port"))
port.default = "8080"
local apply = luci.http.formvalue("cbi.apply")
if apply then
io.popen("/etc/init.d/qbittorrent restart")
function titlesplit(Value)
return "<p style=\"font-size:20px;font-weight:bold;color: DodgerBlue\">" .. translate(Value) .. "</p>"
end
m = Map("qbittorrent", translate("qBittorrent"), translate("qBittorrent is a cross-platform free and open-source BitTorrent client")..t)
s = m:section(NamedSection, "main", "qbittorrent")
s:tab("basic", translate("Basic Settings"))
o = s:taboption("basic", Flag, "enabled", translate("Enabled"))
o.default = "1"
o = s:taboption("basic", ListValue, "user", translate("Run daemon as user"))
local u
for u in luci.util.execi("cat /etc/passwd | cut -d ':' -f1") do
o:value(u)
end
o = s:taboption("basic", Value, "profile", translate("Store configuration files in the Path"))
o.default = '/tmp'
o = s:taboption("basic", Value, "SavePath", translate("Store download files in the Path"))
o.placeholder = "/tmp/download"
o = s:taboption("basic", Value, "Port", translate("WEBUI listening port"))
o.datatype = "port"
o.placeholder = "8080"
o = s:taboption("basic", Flag, "UseRandomPort", translate("Use Random Port"), translate("Randomly assigns a different port every time qBittorrent starts up"))
o.enabled = "true"
o.disabled = "false"
o.default = o.enabled
o = s:taboption("basic", Value, "PortRangeMin", translate("Connection Port"), translate("Incoming connection port"))
o:depends("UseRandomPort", false)
o.datatype = "range(1024,65535)"
s:tab("connection", translate("Connection Settings"))
o = s:taboption("connection", Flag, "UPnP", translate("Use UPnP for Connections"), translate("Use UPnP/ NAT-PMP port forwarding from my router. Refer to the "
.. "<a href='https://en.wikipedia.org/wiki/Port_forwarding' target='_blank'>wiki</a>."))
o.enabled = "true"
o.disabled = "false"
o.default = o.enabled
o = s:taboption("connection", Value, "GlobalDLLimit", translate("Global Download Speed"), translate("Global Download Speed Limit(KiB/s)."))
o.datatype = "float"
o.placeholder = "0"
o = s:taboption("connection", Value, "GlobalUPLimit", translate("Global Upload Speed"), translate("Global Upload Speed Limit(KiB/s)."))
o.datatype = "float"
o.placeholder = "0"
o = s:taboption("connection", Value, "GlobalDLLimitAlt", translate("Alternative Download Speed"), translate("Alternative Download Speed Limit(KiB/s)."))
o.datatype = "float"
o.placeholder = "10"
o = s:taboption("connection", Value, "GlobalUPLimitAlt", translate("Alternative Upload Speed"), translate("Alternative Upload Speed Limit(KiB/s)."))
o.datatype = "float"
o.placeholder = "10"
o = s:taboption("connection", ListValue, "BTProtocol", translate("Enabled protocol"), translate("The protocol that was enabled."))
o:value("Both", translate("TCP and UTP"))
o:value("TCP", translate("TCP"))
o:value("UTP", translate("UTP"))
o.default = "Both"
o = s:taboption("connection", Value, "InetAddress", translate("Inet Address"), translate("The address that respond to the trackers."))
s:tab("downloads", translate("Download Settings"))
o = s:taboption("downloads", Flag, "CreateTorrentSubfolder", translate("Create Subfolder"), translate("Create subfolder for torrents with multiple files."))
o.enabled = "true"
o.disabled = "false"
o.default = o.enabled
o = s:taboption("downloads", Flag, "StartInPause", translate("Start In Pause"), translate("Do not start the download automatically."))
o.enabled = "true"
o.disabled = "false"
o.default = o.disabled
o = s:taboption("downloads", Flag, "AutoDeleteAddedTorrentFile", translate("Auto Delete Torrent File"), translate("The .torrent files will be deleted afterwards."))
o.enabled = "IfAdded"
o.disabled = "Never"
o.default = o.disabled
o = s:taboption("downloads", Flag, "PreAllocation", translate("Pre Allocation"), translate("Pre-allocate disk space for all files."))
o.enabled = "true"
o.disabled = "false"
o.default = o.disabled
o = s:taboption("downloads", Flag, "UseIncompleteExtension", translate("Use Incomplete Extension"), translate("The incomplete task will be added the extension of !qB."))
o.enabled = "true"
o.disabled = "false"
o.default = o.disabled
o = s:taboption("downloads", Flag, "TempPathEnabled", translate("Temp Path Enabled"))
o.enabled = "true"
o.disabled = "false"
o.default = o.enabled
o = s:taboption("downloads", Value, "TempPath", translate("Temp Path"), translate("The absolute and relative path can be set."))
o:depends("TempPathEnabled", "true")
o.placeholder = "temp/"
o = s:taboption("downloads", Value, "DiskWriteCacheSize", translate("Disk Cache Size (MiB)"), translate("The value -1 is auto and 0 is disable. In default, it is set to 64MiB."))
o.datatype = "integer"
o.placeholder = "64"
o = s:taboption("downloads", Value, "DiskWriteCacheTTL", translate("Disk Cache TTL (s)"), translate("In default, it is set to 60s."))
o.datatype = "integer"
o.placeholder = "60"
o = s:taboption("downloads", DummyValue, "Saving Management", titlesplit("Saving Management"))
o = s:taboption("downloads", ListValue, "DisableAutoTMMByDefault", translate("Default Torrent Management Mode"))
o:value("true", translate("Manual"))
o:value("false", translate("Automaic"))
o.default = "true"
o = s:taboption("downloads", ListValue, "CategoryChanged", translate("Torrent Category Changed"), translate("Choose the action when torrent category changed."))
o:value("true", translate("Switch torrent to Manual Mode"))
o:value("false", translate("Relocate torrent"))
o.default = "false"
o = s:taboption("downloads", ListValue, "DefaultSavePathChanged", translate("Default Save Path Changed"), translate("Choose the action when default save path changed."))
o:value("true", translate("Switch affected torrent to Manual Mode"))
o:value("false", translate("Relocate affected torrent"))
o.default = "true"
o = s:taboption("downloads", ListValue, "CategorySavePathChanged", translate("Category Save Path Changed"), translate("Choose the action when category save path changed."))
o:value("true", translate("Switch affected torrent to Manual Mode"))
o:value("false", translate("Relocate affected torrent"))
o.default = "true"
o = s:taboption("downloads", Value, "TorrentExportDir", translate("Torrent Export Dir"), translate("The .torrent files will be copied to the target directory."))
o = s:taboption("downloads", Value, "FinishedTorrentExportDir", translate("Finished Torrent Export Dir"), translate("The .torrent files for finished downloads will be copied to the target directory."))
s:tab("bittorrent", translate("Bittorrent Settings"))
o = s:taboption("bittorrent", Flag, "DHT", translate("Enable DHT"), translate("Enable DHT (decentralized network) to find more peers"))
o.enabled = "true"
o.disabled = "false"
o.default = o.enabled
o = s:taboption("bittorrent", Flag, "PeX", translate("Enable PeX"), translate("Enable Peer Exchange (PeX) to find more peers"))
o.enabled = "true"
o.disabled = "false"
o.default = o.enabled
o = s:taboption("bittorrent", Flag, "LSD", translate("Enable LSD"), translate("Enable Local Peer Discovery to find more peers"))
o.enabled = "true"
o.disabled = "false"
o.default = o.disabled
o = s:taboption("bittorrent", Flag, "uTP_rate_limited", translate("uTP Rate Limit"), translate("Apply rate limit to μTP protocol."))
o.enabled = "true"
o.disabled = "false"
o.default = o.enabled
o = s:taboption("bittorrent", ListValue, "Encryption", translate("Encryption Mode"), translate("Enable DHT (decentralized network) to find more peers"))
o:value("0", translate("Prefer Encryption"))
o:value("1", translate("Require Encryption"))
o:value("2", translate("Disable Encryption"))
o.default = "0"
o = s:taboption("bittorrent", Value, "MaxConnecs", translate("Max Connections"), translate("The max number of connections."))
o.datatype = "integer"
o.placeholder = "500"
o = s:taboption("bittorrent", Value, "MaxConnecsPerTorrent", translate("Max Connections Per Torrent"), translate("The max number of connections per torrent."))
o.datatype = "integer"
o.placeholder = "100"
o = s:taboption("bittorrent", Value, "MaxUploads", translate("Max Uploads"), translate("The max number of connected peers."))
o.datatype = "integer"
o.placeholder = "8"
o = s:taboption("bittorrent", Value, "MaxUploadsPerTorrent", translate("Max Uploads Per Torrent"), translate("The max number of connected peers per torrent."))
o.datatype = "integer"
o.placeholder = "4"
o = s:taboption("bittorrent", Value, "MaxRatio", translate("Max Ratio"), translate("The max ratio for seeding. -1 is to disable the seeding."))
o.datatype = "float"
o.placeholder = "-1"
o = s:taboption("bittorrent", ListValue, "MaxRatioAction", translate("Max Ratio Action"), translate("The action when reach the max seeding ratio."))
o:value("0", translate("Pause them"))
o:value("1", translate("Remove them"))
o.defaule = "0"
o = s:taboption("bittorrent", Value, "GlobalMaxSeedingMinutes", translate("Max Seeding Minutes"), translate("Units: minutes"))
o.datatype = "integer"
o = s:taboption("bittorrent", DummyValue, "Queueing Setting", titlesplit("Queueing Setting"))
o = s:taboption("bittorrent", Flag, "QueueingEnabled", translate("Enable Torrent Queueing"))
o.enabled = "true"
o.disabled = "false"
o.default = o.enabled
o = s:taboption("bittorrent", Value, "MaxActiveDownloads", translate("Maximum Active Downloads"))
o.datatype = "integer"
o.placeholder = "3"
o = s:taboption("bittorrent", Value, "MaxActiveUploads", translate("Max Active Uploads"))
o.datatype = "integer"
o.placeholder = "3"
o = s:taboption("bittorrent", Value, "MaxActiveTorrents", translate("Max Active Torrents"))
o.datatype = "integer"
o.placeholder = "5"
o = s:taboption("bittorrent", Flag, "IgnoreSlowTorrents", translate("Ignore Slow Torrents"), translate("Do not count slow torrents in these limits."))
o.enabled = "true"
o.disabled = "false"
o.default = o.disabled
o = s:taboption("bittorrent", Value, "SlowTorrentsDownloadRate", translate("Download rate threshold"), translate("Units: KiB/s"))
o.datatype = "integer"
o.placeholder = "2"
o = s:taboption("bittorrent", Value, "SlowTorrentsUploadRate", translate("Upload rate threshold"), translate("Units: KiB/s"))
o.datatype = "integer"
o.placeholder = "2"
o = s:taboption("bittorrent", Value, "SlowTorrentsInactivityTimer", translate("Torrent inactivity timer"), translate("Units: seconds"))
o.datatype = "integer"
o.placeholder = "60"
s:tab("webgui", translate("WebUI Settings"))
o = s:taboption("webgui", Flag, "UseUPnP", translate("Use UPnP for WebUI"), translate("Using the UPnP / NAT-PMP port of the router for connecting to WebUI."))
o.enabled = "true"
o.disabled = "false"
o.default = o.disabled
o = s:taboption("webgui", Value, "Username", translate("Username"), translate("The login name for WebUI."))
o.placeholder = "admin"
o = s:taboption("webgui", Value, "Password", translate("Password"), translate("The login password for WebUI."))
o.password = true
o = s:taboption("webgui", Value, "Locale", translate("Locale Language"))
o:value("en", translate("English"))
o:value("zh", translate("Chinese"))
o.default = "en"
o = s:taboption("webgui", Flag, "CSRFProtection", translate("CSRF Protection"), translate("Enable Cross-Site Request Forgery (CSRF) protection."))
o.enabled = "true"
o.disabled = "false"
o.default = o.enabled
o = s:taboption("webgui", Flag, "ClickjackingProtection", translate("Clickjacking Protection"), translate("Enable clickjacking protection."))
o.enabled = "true"
o.disabled = "false"
o.default = o.enabled
o = s:taboption("webgui", Flag, "HostHeaderValidation", translate("Host Header Validation"), translate("Validate the host header."))
o.enabled = "true"
o.disabled = "false"
o.default = o.enabled
o = s:taboption("webgui", Flag, "LocalHostAuth", translate("Local Host Authentication"), translate("Force authentication for clients on localhost."))
o.enabled = "true"
o.disabled = "false"
o.default = o.enabled
o = s:taboption("webgui", Flag, "AuthSubnetWhitelistEnabled", translate("Enable Subnet Whitelist"))
o.enabled = "true"
o.disabled = "false"
o.default = o.disabled
o = s:taboption("webgui", DynamicList, "AuthSubnetWhitelist", translate("Subnet Whitelist"))
o:depends("AuthSubnetWhitelistEnabled", "true")
s:tab("advanced", translate("Advance Settings"))
o = s:taboption("advanced", Flag, "AnonymousMode", translate("Anonymous Mode"), translate("When enabled, qBittorrent will take certain measures to try"
.. " to mask its identity. Refer to the <a href='https://github.com/qbittorrent/qBittorrent/wiki/Anonymous-Mode' target='_blank'>wiki</a>"))
o.enabled = "true"
o.disabled = "false"
o.default = o.enabled
o = s:taboption("advanced", Flag, "SuperSeeding", translate("Super Seeding"), translate("The super seeding mode."))
o.enabled = "true"
o.disabled = "false"
o.default = o.disabled
o = s:taboption("advanced", Value, "configuration", translate("Profile Folder Suffix"), translate("Suffix for profile folder"))
o = s:taboption("advanced", Flag, "IncludeOverhead", translate("Limit Overhead Usage"), translate("The overhead usage is been limitted."))
o.enabled = "true"
o.disabled = "false"
o.default = o.disabled
o = s:taboption("advanced", Flag, "IgnoreLimitsLAN", translate("Ignore LAN Limit"), translate("Ignore the speed limit to LAN."))
o.enabled = "true"
o.disabled = "false"
o.default = o.enabled
o = s:taboption("advanced", Flag, "osCache", translate("Use os Cache"))
o.enabled = "true"
o.disabled = "false"
o.default = o.enabled
o = s:taboption("advanced", Value, "OutgoingPortsMax", translate("Max Outgoing Port"), translate("The max outgoing port."))
o.datatype = "port"
o = s:taboption("advanced", Value, "OutgoingPortsMin", translate("Min Outgoing Port"), translate("The min outgoing port."))
o.datatype = "port"
o = s:taboption("advanced", ListValue, "SeedChokingAlgorithm", translate("Choking Algorithm"), translate("The strategy of choking algorithm."))
o:value("RoundRobin", translate("Round Robin"))
o:value("FastestUpload", translate("Fastest Upload"))
o:value("AntiLeech", translate("Anti-Leech"))
o.default = "FastestUpload"
o = s:taboption("advanced", Flag, "AnnounceToAllTrackers", translate("Announce To All Trackers"))
o.enabled = "true"
o.disabled = "false"
o.default = o.disabled
o = s:taboption("advanced", Flag, "AnnounceToAllTiers", translate("Announce To All Tiers"))
o.enabled = "true"
o.disabled = "false"
o.default = o.enabled
o = s:taboption("advanced", Flag, "Enabled", translate("Enable Log"), translate("Enable logger to log file."))
o.enabled = "true"
o.disabled = "false"
o.default = o.enabled
o = s:taboption("advanced", Value, "Path", translate("Log Path"), translate("The path for qbittorrent log."))
o:depends("Enabled", "true")
o = s:taboption("advanced", Flag, "Backup", translate("Enable Backup"), translate("Backup log file when oversize the given size."))
o:depends("Enabled", "true")
o.enabled = "true"
o.disabled = "false"
o.default = o.enabled
o = s:taboption("advanced", Flag, "DeleteOld", translate("Delete Old Backup"), translate("Delete the old log file."))
o:depends("Enabled", "true")
o.enabled = "true"
o.disabled = "false"
o.default = o.enabled
o = s:taboption("advanced", Value, "MaxSizeBytes", translate("Log Max Size"), translate("The max size for qbittorrent log (Unit: Bytes)."))
o:depends("Enabled", "true")
o.placeholder = "66560"
o = s:taboption("advanced", Value, "SaveTime", translate("Log Saving Period"), translate("The log file will be deteted after given time. 1d -- 1 day, 1m -- 1 month, 1y -- 1 year"))
o:depends("Enabled", "true")
o.datatype = "string"
return m

View File

@ -0,0 +1,22 @@
<script type="text/javascript">//<![CDATA[
XHR.poll(3, '<%=url([[admin]], [[nas]], [[qBittorrent]], [[status]])%>', null,
function(x, data) {
var tb = document.getElementById('qBittorrent_status');
if (data && tb) {
if (data.running) {
var links = '<em><b><font color=green>qBittorrent <%:RUNNING%></font></b></em>';
tb.innerHTML = links;
} else {
tb.innerHTML = '<em><b><font color=red>qBittorrent <%:NOT RUNNING%></font></b></em>';
}
}
}
);
//]]>
</script>
<style>.mar-10 {margin-left: 50px; margin-right: 10px;}</style>
<fieldset class="cbi-section">
<p id="qBittorrent_status">
<em><%:Collecting data...%></em>
</p>
</fieldset>

View File

@ -1,5 +1,5 @@
msgid "qbittorrent"
msgstr "BT下载器-qb"
msgstr "qbittorrent"
msgid "Running"
msgstr "运行中"
@ -16,8 +16,8 @@ msgstr "基本设置"
msgid "Enable"
msgstr "启用"
msgid "A BT/PT downloader base on Qt"
msgstr "一个基于QT的BT/PT下载器"
msgid "qBittorrent is a cross-platform free and open-source BitTorrent client"
msgstr "qBittorrent是一个基于 QT 的跨平台的开源 BitTorrent 客户端"
msgid "profile_dir"
msgstr "配置文件目录"
@ -50,4 +50,525 @@ msgid "WEBUI Settings"
msgstr "WEBUI设置"
msgid "WEBUI listening port"
msgstr "WEBUI监听端口"
msgstr "WebUI 监听端口"
msgid "Use Random Port"
msgstr "随机传入连接端口"
msgid "Randomly assigns a different port every time qBittorrent starts up"
msgstr "在每次启动时使用不同的传入连接端口"
msgid "Connection Port"
msgstr "用于传入连接的端口"
msgid "Incoming connection port"
msgstr "推荐在防火墙 -> 流量规则 中,打开这个端口获得更好的下载速度( TCP+UDP "
msgid "Bittorrent Settings"
msgstr "Bittorrent 设置"
msgid "WebUI Settings"
msgstr "WebUI 设置"
msgid "Advance Settings"
msgstr "高级设置"
msgid "Run daemon as user"
msgstr "用户组"
msgid "Parent Path for Profile Folder"
msgstr "配置保存路径"
msgid "The path for storing profile folder using by command: <b>--profile [PATH]</b>."
msgstr "配置文件的保存路径,默认的配置文件夹在/tmp下。例如<code>/etc/config</code>"
msgid "Profile Folder Suffix"
msgstr "配置目录后缀"
msgid "Suffix for profile folder, for example, <b>qBittorrent_[NAME]</b>."
msgstr "配置文件文件夹的后缀。例如: <b>qBittorrent_[NAME]</b>"
msgid "Locale Language"
msgstr "WebUI语言"
msgid "English"
msgstr "英文"
msgid "Chinese"
msgstr "中文"
msgid "Enable Log"
msgstr "启用日志"
msgid "Enable logger to log file."
msgstr "qBittorrent的启动和运行信息文档。"
msgid "Log Path"
msgstr "日志文件"
msgid "The path for qbittorrent log."
msgstr "日志文件自定义保存路径默认都在配置文件夹的data下。"
msgid "Enable Backup"
msgstr "启用备份"
msgid "Backup log file when oversize the given size."
msgstr "备份日志文件。"
msgid "Delete Old Backup"
msgstr "删除备份"
msgid "Delete the old log file."
msgstr "符合下列设定后将删除旧的日志文件。"
msgid "Log Max Size"
msgstr "日志保存大小"
msgid "Log Saving Period"
msgstr "日志保存期限"
msgid "The max size for qbittorrent log (Unit: Bytes)."
msgstr "设定日志文件的大小(单位:字节)"
msgid "The log file will be deteted after given time. 1d -- 1 day, 1m -- 1 month, 1y -- 1 year"
msgstr "设定日志文件的时间1d-1天,1m-1个月,1y-1年"
msgid "Connection Settings"
msgstr "连接设置"
msgid "Use UPnP for Connections"
msgstr "端口自动转发"
msgid "Use UPnP/ NAT-PMP port forwarding from my router."
msgstr "使用路由器的UPnP/NAT-PMP端口自动转发。"
msgid "Use Random Port"
msgstr "启用随机端口"
msgid "Use different port on each startup voids the first"
msgstr "在每次启动时使用随机的端口。"
msgid "Connection Port"
msgstr "自定义端口"
msgid "Generate Randomly"
msgstr "默认端口8999"
msgid "Global Download Speed"
msgstr "全局下载速度限制"
msgid "Global Download Speed Limit(KiB/s)."
msgstr "全局下载速度限制(KiB/s)0为无限制。"
msgid "Global Upload Speed"
msgstr "全局上传速度限制"
msgid "Alternative Download Speed"
msgstr "备用下载速度限制"
msgid "Alternative Upload Speed"
msgstr "备用上传速度限制"
msgid "Global Upload Speed Limit(KiB/s)."
msgstr "全局上传速度限制(KiB/s)0为无限制。"
msgid "Alternative Download Speed Limit(KiB/s)."
msgstr "备用下载速度限制(KiB/s)0为无限制。"
msgid "Alternative Upload Speed Limit(KiB/s)."
msgstr "备用上传速度限制(KiB/s)0为无限制。"
msgid "Enabled protocol"
msgstr "启用的协议"
msgid "The protocol that was enabled."
msgstr "当前已启用的协议。"
msgid "TCP and UTP"
msgstr "TCP和UTP"
msgid "Inet Address"
msgstr "输入地址"
msgid "The address that respond to the trackers."
msgstr "响应跟踪器的地址。"
msgid "When adding seeds"
msgstr "当添加种子时"
msgid "Downloads Settings"
msgstr "下载设置"
msgid "Create Subfolder"
msgstr "创建目录"
msgid "Create subfolder for torrents with multiple files."
msgstr "为含多个文件的种子创建子文件夹。"
msgid "Start In Pause"
msgstr "开始暂停"
msgid "Do not start the download automatically."
msgstr "在下载任务添加后暂停。"
msgid "Auto Delete Torrent File"
msgstr "删除种子"
msgid "The .torrent files will be deleted afterwards."
msgstr "下载完成后自动删除这个种子文件。"
msgid "Pre Allocation"
msgstr "磁盘预分配"
msgid "Pre-allocate disk space for all files."
msgstr "为刚添加的文件预先分配磁盘空间。"
msgid "Use Incomplete Extension"
msgstr "使用扩展名"
msgid "The incomplete task will be added the extension of !qB."
msgstr "为不完整的文件添加后缀名<code>!qB</code>"
msgid "Save Path"
msgstr "文件保存路径"
msgid "The path to save the download file. For example:<code>/mnt/sda1/download</code>"
msgstr "下载文件的保存路径。例如:<code>/mnt/sda1/download</code>"
msgid "Temp Path Enabled"
msgstr "启用临时目录"
msgid "Temp Path"
msgstr "临时路径"
msgid "The absolute and relative path can be set."
msgstr "可以设置绝对和相对路径。"
msgid "Disk Cache Size (MiB)"
msgstr "磁盘缓存"
msgid "The value -1 is auto and 0 is disable. In default, it is set to 64MiB."
msgstr "数值1是自动的0是禁用的。默认设置为64MiB。"
msgid "Disk Cache TTL (s)"
msgstr "磁盘缓存TTL"
msgid "In default, it is set to 60s."
msgstr "默认设置为60秒。"
msgid "Saving Management"
msgstr "保存管理"
msgid "Default Torrent Management Mode"
msgstr "默认种子管理模式"
msgid "Manual"
msgstr "手动"
msgid "Automaic"
msgstr "自动"
msgid "Torrent Category Changed"
msgstr "当种子分类修改时"
msgid "Choose the action when torrent category changed."
msgstr "选择种子类别更改时的操作。"
msgid "Switch torrent to Manual Mode"
msgstr "将种子切换到手动模式"
msgid "Relocate torrent"
msgstr "重新定位种子"
msgid "Default Save Path Changed"
msgstr "当默认保存路径修改时"
msgid "Choose the action when default save path changed."
msgstr "选择默认保存路径更改时的操作。"
msgid "Switch affected torrent to Manual Mode"
msgstr "将受影响的种子切换到手动模式"
msgid "Relocate affected torrent"
msgstr "重新定位种子"
msgid "Category Save Path Changed"
msgstr "当分类保存路径修改时"
msgid "Choose the action when category save path changed."
msgstr "选择分类保存路径更改时的操作。"
msgid "Torrent Export Dir"
msgstr "种子导出目录"
msgid "The .torrent files will be copied to the target directory."
msgstr "种子文件将被复制到目标目录。例如:<code>/etc/config</code>"
msgid "Finished Torrent Export Dir"
msgstr "复制种子文件"
msgid "The .torrent files for finished downloads will be copied to the target directory."
msgstr "将已下载完成的种子文件复制到目标目录。例如:<code>/etc/config</code>"
msgid "Bittorrent Settings"
msgstr "BT设置""
msgid "Enable DHT"
msgstr "启用DHT"
msgid "Enable DHT (decentralized network) to find more peers"
msgstr "启用DHT(去中心化网络) 以找到更多用户。"
msgid "Enable PeX"
msgstr "启用PeX"
msgid "Enable Peer Exchange (PeX) to find more peers"
msgstr "启用用户交换(PeX)以找到更多用户。"
msgid "Enable LSD"
msgstr "启用LSD"
msgid "Enable Local Peer Discovery to find more peers"
msgstr "启用本地用户发现以找到更多用户。"
msgid "uTP Rate Limit"
msgstr "uTP速度限制"
msgid "Apply rate limit to µTP protocol."
msgstr "针对µTP协议进行速度限制。"
msgid "Encryption Mode"
msgstr "加密模式"
msgid "Enable DHT (decentralized network) to find more peers"
msgstr "使DHT分散网络能够找到更多的对等点。"
msgid "Prefer Encryption"
msgstr "偏好加密"
msgid "Require Encryption"
msgstr "强制加密"
msgid "Disable Encryption"
msgstr "禁用加密"
msgid "Max Connections"
msgstr "连接数限制"
msgid "The max number of connections."
msgstr "全局最大连接数。"
msgid "Max Connections Per Torrent"
msgstr "种子连接数限制"
msgid "The max number of connections per torrent."
msgstr "每个种子的最大连接数。"
msgid "Max Uploads"
msgstr "最大上传数"
msgid "The max number of connected peers."
msgstr "全局最大上传线程数。"
msgid "Max Uploads Per Torrent"
msgstr "种子上传限制"
msgid "The max number of connected peers per torrent."
msgstr "每个种子上传线程最大值。"
msgid "Share rate limit"
msgstr "分享率限制"
msgid "Max Ratio"
msgstr "最大的分享率"
msgid "The max ratio for seeding. -1 is to disable the seeding."
msgstr "分享的最大比例设定。-1是禁用做种。"
msgid "Max Seeding Minutes"
msgstr "最大做种时间"
msgid "Units: minutes"
msgstr "做种最大比例设定。单位:分钟"
msgid "Max Ratio Action"
msgstr "达到后"
msgid "The action when reach the max seeding ratio."
msgstr "达到设定分享率和时间后的动作。"
msgid "Pause them"
msgstr "暂停"
msgid "Remove them"
msgstr "删除"
msgid "Queueing Setting"
msgstr "种子排队设置"
msgid "Enable Torrent Queueing"
msgstr "启用种子排队"
msgid "Maximum Active Downloads"
msgstr "最大活动的下载数"
msgid "Max Active Uploads"
msgstr "最大活动的上传数"
msgid "Max Active Torrents"
msgstr "最大活动的种子数"
msgid "Ignore Slow Torrents"
msgstr "忽略慢速的种子"
msgid "Do not count slow torrents in these limits."
msgstr "慢速的种子不包在括限制内。"
msgid "Download rate threshold"
msgstr "下载速度阈值"
msgid "Upload rate threshold"
msgstr "上传速度阈值"
msgid "Units: KiB/s"
msgstr "单位KiB/s"
msgid "Torrent inactivity timer"
msgstr "种子不活动时间"
msgid "Units: seconds"
msgstr "时间单位:分钟"
msgid "WebUI Settings"
msgstr "WebUI设置"
msgid "Username"
msgstr ""
msgid "Password"
msgstr ""
msgid "Use UPnP for WebUI"
msgstr "WebUI端口转发"
msgid "Using the UPnP / NAT-PMP port of the router for connecting to WebUI."
msgstr "使用路由器的UPnP/NAT-PMP端口转发到WebUI。"
msgid "The login name for WebUI."
msgstr "WebUI的登录用户名设置。"
msgid "The login password for WebUI."
msgstr "WebUI用户的登录密码设置。"
msgid "The listening port for WebUI."
msgstr "WebUI的登录端口设置。默认端口8080"
msgid "CSRF Protection"
msgstr "CSRF保护"
msgid "Enable Cross-Site Request Forgery (CSRF) protection."
msgstr "启用跨站点请求伪造(CSRF)保护。"
msgid "Clickjacking Protection"
msgstr "劫持保护"
msgid "Enable clickjacking protection."
msgstr "启用点击劫持保护。"
msgid "Host Header Validation"
msgstr "主机标头验证"
msgid "Validate the host header."
msgstr "启用主机标头验证."
msgid "Local Host Authentication"
msgstr "本地主机认证"
msgid "Force authentication for clients on localhost."
msgstr "强制对本地主机上的客户端进行身份验证。"
msgid "Enable Subnet Whitelist"
msgstr "使子网白名单"
msgid "Subnet Whitelist"
msgstr "输入IP地址"
msgid "Skip authentication for clients in the IP subnet white list."
msgstr "对IP子网白名单中的客户端跳过身份验证."
msgid "Advance Settings"
msgstr "高级设置"
msgid "Anonymous Mode"
msgstr "匿名模式"
msgid "When enabled, qBittorrent will take certain measures to try"
msgstr "启用后qBittorrent将采取某些措施隐藏其身份。"
msgid "Super Seeding"
msgstr "超级种子"
msgid "The super seeding mode."
msgstr "超级种子模式。"
msgid "Limit Overhead Usage"
msgstr "开销限制"
msgid "The overhead usage is been limitted."
msgstr "对传送总开销进行速度限制。"
msgid "Ignore LAN Limit"
msgstr "LAN限制"
msgid "Ignore the speed limit to LAN."
msgstr "忽略对LAN的速度限制。"
msgid "Use os Cache"
msgstr "使用OS操作系统缓存管理"
msgid "Max Outgoing Port"
msgstr "端口设置"
msgid The max outgoing port.""
msgstr "最大输出端口。"
msgid "Min Outgoing Port"
msgstr "端口设置"
msgid "The min outgoing port."
msgstr "最小输出端口。"
msgid "Choking Algorithm"
msgstr "数据传输算法"
msgid "The strategy of choking algorithm."
msgstr "数据传输算法的策略。"
msgid "Round Robin"
msgstr "负载均衡"
msgid "Fastest Upload"
msgstr "最快上传"
msgid "Anti-Leech"
msgstr "反吸血"
msgid "Announce To All Trackers"
msgstr "对所有Trackers宣告"
msgid "Announce To All Tiers"
msgstr "对所有Tiers宣告"
msgid "configuration file"
msgstr "配置文件"
msgid "Operation log"
msgstr "运行日志"
msgid "This page is the log document content of qbittorrent."
msgstr "本页是qBittorrent的日志文档内容。"
msgid "This page is the content of the configuration document under /etc/config/qbittorrent."
msgstr "本页是/etc/config/qbittorrent下的配置文档内容。"

View File

@ -1,3 +1,19 @@
config basic
config Preferences
config qbittorrent 'main'
option user 'root'
option Locale 'zh'
option BTProtocol 'Both'
option DisableAutoTMMByDefault 'true'
option CategoryChanged 'false'
option DefaultSavePathChanged 'true'
option CategorySavePathChanged 'true'
option Encryption '0'
option MaxRatioAction '0'
option CSRFProtection 'false'
option SeedChokingAlgorithm 'FastestUpload'
option Enabled 'false'
option Port '8080'
option profile '/opt'
option enabled '0'

View File

@ -1,67 +1,264 @@
#!/bin/sh /etc/rc.common
# Licensed to the public under the Apache License 2.0.
# ubus call service list
START=99
config_qbittorrent()
{
local download_dir
local port
config_get download_dir $1 download_dir
config_get port $1 port
if [ -f $2/qBittorrent/config/qBittorrent.conf ]; then
sed -i 's/WebUI\\Port=[0-9]*/WebUI\\Port='"$port"'/g' $2/qBittorrent/config/qBittorrent.conf
sed -i 's/Downloads\\SavePath=[a-z,/]*//g' $2/qBittorrent/config/qBittorrent.conf
echo "Downloads\SavePath=$down" >> $2/qBittorrent/config/qBittorrent.conf
else
cat>$2/qBittorrent/config/qBittorrent.conf<<EOF
[AutoRun]
enabled=false
program=
USE_PROCD=1
NAME=qbittorrent
args=/usr/bin/qbittorrent-nox
QBT_PID_FILE=/var/run/qbittorrent.pid
QBT_INI_FILE=/tmp/qBittorrent/config/qBittorrent.conf
QBT_INSTANCE=""
_info() {
logger -p daemon.info -t "$NAME" "$*"
}
_err() {
logger -p daemon.err -t "$NAME" "$*"
}
validate_QBT () {
uci_validate_section "$NAME" vlmcsd "$1" \
'enabled:bool:1' \
'user:string:root' \
'profile:string:/tmp' \
'configuration:string' \
'DHT:or("true","false"):true' \
'Encryption:or("0","1","2"):0' \
'LSD:or("true","false"):true' \
'MaxConnecs:integer' \
'MaxConnecsPerTorrent:integer' \
'MaxRatio:float' \
'MaxRatioAction:or("0","1")' \
'MaxUploads:integer' \
'MaxUploadsPerTorrent:integer' \
'PeX:or("true","false"):true' \
'uTP_rate_limited:or("true","false"):true' \
'PortRangeMin:port' \
'InetAddress:string' \
'UPnP:or("true","false"):true' \
'GlobalDLLimit:float' \
'GlobalDLLimitAlt:float' \
'GlobalUPLimit:float' \
'GlobalUPLimitAlt:float' \
'DiskWriteCacheSize:integer' \
'DiskWriteCacheTTL:integer' \
'FinishedTorrentExportDir:string' \
'PreAllocation:or("true","false"):false' \
'SavePath:string:/tmp/download' \
'StartInPause:or("true","false"):false' \
'TempPathEnabled:or("true","false"):true' \
'TempPath:string:temp/' \
'UseIncompleteExtension:or("true","false"):false' \
'TorrentExportDir:string' \
'Locale:string:en' \
'UseRandomPort:or("true","false"):true' \
'IgnoreSlowTorrents:or("true","false")' \
'MaxActiveDownloads:integer' \
'MaxActiveTorrents:integer' \
'MaxActiveUploads:integer' \
'QueueingEnabled:or("true","false")' \
'AuthSubnetWhitelist:string' \
'AuthSubnetWhitelistEnabled:or("true","false"):false' \
'ClickjackingProtection:or("true","false"):true' \
'CSRFProtection:or("true","false"):true' \
'HostHeaderValidation:or("true","false"):true' \
'LocalHostAuth:or("true","false"):true' \
'Password:string' \
'Port:port:8080' \
'Username:string' \
'UseUPnP:or("true","false"):true' \
'AnonymousMode:or("true","false"):true' \
'AnnounceToAllTrackers:or("true","false")' \
'IgnoreLimitsLAN:or("true","false"):true' \
'IncludeOverhead:or("true","false"):false' \
'osCache:or("true","false")' \
'OutgoingPortsMax:port' \
'OutgoingPortsMin:port' \
'AnnounceToAllTiers:or("true","false")' \
'BTProtocol:or("Both","TCP","UTP")' \
'CreateTorrentSubfolder:or("true","false"):true' \
'DisableAutoTMMByDefault:or("true","false"):true' \
'SuperSeeding:or("true","false"):false' \
'GlobalMaxSeedingMinutes:integer' \
'SeedChokingAlgorithm:or("RoundRobin","FastestUpload","AntiLeech")' \
'SlowTorrentsDownloadRate:integer' \
'SlowTorrentsInactivityTimer:integer' \
'SlowTorrentsUploadRate:integer' \
'CategoryChanged:or("true","false"):false' \
'CategorySavePathChanged:or("true","false"):true' \
'DefaultSavePathChanged:or("true","false"):true' \
'AutoDeleteAddedTorrentFile:or("Never","IfAdded"):Never' \
'Enabled:or("true","false")' \
'Path:string' \
'Backup:or("true","false")' \
'DeleteOld:or("true","false")' \
'MaxSizeBytes:integer' \
'SaveTime:string'
}
sed_options () {
local Anchor=$1
local category=$( echo $2 | sed 's/\s/\\\\/g' )
shift
shift
if [ $( sed -n '/^\['"$Anchor"'\]/p' $QBT_INI_FILE | wc -l ) -lt 1 ]; then
sed -i '$a\\n\['"$Anchor"'\]' "$QBT_INI_FILE"
fi
local o; local v; local ol
for o in "$@"; do
v=$( echo "$(eval echo "\$$o")" | sed 's/[\/\.]/\\&/g' )
[ -n "$category" ] && ol="$category\\\\$o" || ol="$o"
[ -n "$v" ] && {
if [ $( sed -n '/^'"$ol"'=/p' $QBT_INI_FILE | wc -l ) -lt 1 ]; then
sed -i '/'"$Anchor"'/a'"$ol"'='"$v" "$QBT_INI_FILE"
else
sed -i 's/'"$ol"'=.*/'"$ol"'='"$v"'/g' "$QBT_INI_FILE"
fi
} || {
sed -i '/'"$ol"'=.*/d' "$QBT_INI_FILE"
}
done
}
config_QBT () {
local Password_ha1="";local Age="";local AgeType=""
[ -n "$Password" ] && \
Password_ha1="@ByteArray($(echo -n $Password|md5sum|grep -oE '[a-z0-9]{32}'))"
[ -n "$SaveTime" ] && {
[ -n "$(echo $SaveTime | sed 's/[0-9dmyDMY]//g')" ] && { _err "Error save time setted."; return 1; }
Age="$(echo $SaveTime | sed 's/[dmyDMY]//g')"
AgeType="$(echo $SaveTime | sed 's/[0-9]//g' | sed 's/[dD]/0/g' | sed 's/[mM]/1/g' | sed 's/[yY]/2/g')"
}
[ -f "$QBT_INI_FILE" ] || {
cat>"$QBT_INI_FILE"<<EOF
[LegalNotice]
Accepted=true
[Network]
Cookies=@Invalid()
[Preferences]
Downloads\SavePath=$download_dir
General\Locale=zh
WebUI\Port=$port
EOF
fi
}
run_qbittorrent()
{
local enable
config_get_bool enable $1 enable
if [ $enable ]; then
local profile_dir
config_get profile_dir $1 profile_dir
config_foreach config_qbittorrent 'Preferences' $profile_dir
if [ "$profile_dir" != "" ]; then
config_get library_dir $1 library_dir
config_get program_dir $1 program_dir
export PATH=$PATH:$program_dir
export LD_LIBRARY_PATH=$library_dir
qbittorrent-nox -d --profile=$profile_dir
else
echo "no profile_dir,stop!"
fi
}
sed_options "Core" "" \
"AutoDeleteAddedTorrentFile"
sed_options "BitTorrent" "Session DisableAutoTMMTriggers" \
"CategoryChanged" "CategorySavePathChanged" "DefaultSavePathChanged"
sed_options "BitTorrent" "Session" \
"AnnounceToAllTiers" "BTProtocol" "CreateTorrentSubfolder" "DisableAutoTMMByDefault" "GlobalMaxSeedingMinutes" \
"SeedChokingAlgorithm" "SlowTorrentsDownloadRate" "SlowTorrentsInactivityTimer" "SlowTorrentsUploadRate"
sed_options "Preferences" "WebUI" \
"AuthSubnetWhitelistEnabled" "AuthSubnetWhitelist" "CSRFProtection" \
"ClickjackingProtection" "HostHeaderValidation" "LocalHostAuth" \
"Password_ha1" "Port" "Username" "UseUPnP"
sed_options "Preferences" "Queueing" \
"IgnoreSlowTorrents" "MaxActiveDownloads" "MaxActiveTorrents" "MaxActiveUploads" \
"QueueingEnabled"
sed_options "Preferences" "General" \
"Locale" "UseRandomPort"
sed_options "Preferences" "Downloads" \
"DiskWriteCacheSize" "DiskWriteCacheTTL" "FinishedTorrentExportDir" "PreAllocation" \
"SavePath" "StartInPause" "TempPathEnabled" "TempPath" "TorrentExportDir" \
"UseIncompleteExtension"
sed_options "Preferences" "Connection" \
"GlobalDLLimit" "GlobalDLLimitAlt" "GlobalUPLimit" "GlobalUPLimitAlt" \
"PortRangeMin" "InetAddress" "UPnP"
sed_options "Preferences" "Bittorrent" \
"DHT" "Encryption" "LSD" "MaxConnecs" "MaxConnecsPerTorrent" "MaxRatio" \
"MaxRatioAction" "MaxUploads" "MaxUploadsPerTorrent" "PeX" "uTP_rate_limited"
sed_options "Preferences" "Advanced" \
"AnnounceToAllTrackers" "AnonymousMode" "IgnoreLimitsLAN" "IncludeOverhead" "osCache" "OutgoingPortsMax" \
"OutgoingPortsMin" "SuperSeeding"
sed_options "Application" "FileLogger" \
"Enabled" "Path" "Backup" "DeleteOld" "MaxSizeBytes" "Age" "AgeType"
fi
}
start()
{
local profile_path
config_load 'qbittorrent'
config_foreach run_qbittorrent 'basic'
init_QBT(){
local section="$1"
QBT_INSTANCE="${NAME}.${section}"
validate_QBT "$section" || { _err "Validation failed."; return 1; }
[ x"$enabled" = x0 ] && {
_info "Instance \"${section}\" disabled.";
procd_kill "$NAME" "$QBT_INSTANCE" >/dev/null 2>&1;
return 1;
}
local confdir="qBittorrent"
[ -n "$configuration" ] && {
confdir="qBittorrent_$configuration"
}
[ -d "$profile/$confdir/config" ] || {
mkdir -m 0755 -p "$profile/$confdir/config"
}
[ "$user" != "root" ] && {
[ -d "$confdir" ] && {
local groupnow="$(ls -l $profile | grep $confdir | awk '{print $3})"
local usernow="$(ls -l $profile | grep $confdir | awk '{print $4})"
[ "$usernow" != "$user" ] && { _err "Permission denied!"; return 1; }
} || {
chmod -R g+w "$profile/$confdir"
chown -R "$user":"$user" "$profile/$confdir"
}
}
[ "$AuthSubnetWhitelistEnabled" = true ] && {
AuthSubnetWhitelist="$( echo $AuthSubnetWhitelist | sed 's/ /,/g')"
} || {
AuthSubnetWhitelist="@Invalid()"
}
QBT_INI_FILE="$profile/$confdir/config/qBittorrent.conf"
config_QBT
procd_open_instance $QBT_INSTANCE
procd_set_param command $args
procd_append_param command --profile="$profile"
[ -n "$configuration" ] && {
procd_append_param command --configuration="$configuration"
}
procd_set_param respawn
procd_set_param user $user
procd_set_param file $QBT_INI_FILE
procd_set_param pidfile $QBT_PID_FILE
procd_close_instance
}
stop()
service_triggers()
{
killall qbittorrent-nox
return 0
procd_add_reload_trigger "$NAME"
}
start_service() {
config_load "$NAME"
config_foreach init_QBT "$NAME"
}
reload_service() {
restart
}
restart() {
stop
sleep 2
start
}

View File

@ -0,0 +1,21 @@
#!/bin/sh
uci -q batch <<-EOF >/dev/null
delete ucitrack.@qbittorrent[-1]
add ucitrack qbittorrent
set ucitrack.@qbittorrent[-1].init=qbittorrent
commit ucitrack
EOF
if [ ."$(uci -q get qbittorrent.main)" != ."qbittorrent" ]; then
uci -q batch <<-EOF >/dev/null
add qbittorrent qbittorrent
rename qbittorrent.@qbittorrent[-1]="main"
set qbittorrent.main.enabled=0
set qbittorrent.main.profile="/tmp"
commit qbittorrent
EOF
fi
rm -f /tmp/luci-indexcache
exit 0

View File

@ -2,10 +2,11 @@ include $(TOPDIR)/rules.mk
PKG_NAME:=luci-app-ssr-plus
PKG_VERSION:=1
PKG_RELEASE:=125
PKG_RELEASE:=131
PKG_CONFIG_DEPENDS:= CONFIG_PACKAGE_$(PKG_NAME)_INCLUDE_Shadowsocks \
CONFIG_PACKAGE_$(PKG_NAME)_INCLUDE_V2ray \
CONFIG_PACKAGE_$(PKG_NAME)_INCLUDE_Trojan \
CONFIG_PACKAGE_$(PKG_NAME)_INCLUDE_Kcptun \
CONFIG_PACKAGE_$(PKG_NAME)_INCLUDE_ShadowsocksR_Server \
CONFIG_PACKAGE_$(PKG_NAME)_INCLUDE_ShadowsocksR_Socks
@ -21,6 +22,10 @@ config PACKAGE_$(PKG_NAME)_INCLUDE_V2ray
bool "Include V2ray"
default y if x86_64
config PACKAGE_$(PKG_NAME)_INCLUDE_Trojan
bool "Include Trojan"
default y if x86_64
config PACKAGE_$(PKG_NAME)_INCLUDE_Kcptun
bool "Include Kcptun"
default n
@ -43,6 +48,8 @@ define Package/luci-app-ssr-plus
DEPENDS:=+shadowsocksr-libev-alt +ipset +ip-full +iptables-mod-tproxy +dnsmasq-full +coreutils +coreutils-base64 +bash +pdnsd-alt +wget \
+PACKAGE_$(PKG_NAME)_INCLUDE_Shadowsocks:shadowsocks-libev-ss-redir \
+PACKAGE_$(PKG_NAME)_INCLUDE_V2ray:v2ray \
+PACKAGE_$(PKG_NAME)_INCLUDE_Trojan:trojan \
+PACKAGE_$(PKG_NAME)_INCLUDE_Trojan:ipt2socks \
+PACKAGE_$(PKG_NAME)_INCLUDE_Kcptun:openwrt-kcptun-client \
+PACKAGE_$(PKG_NAME)_INCLUDE_ShadowsocksR_Server:shadowsocksr-libev-server \
+PACKAGE_$(PKG_NAME)_INCLUDE_ShadowsocksR_Socks:shadowsocksr-libev-ssr-local

View File

@ -114,7 +114,7 @@ s = m:section(NamedSection, sid, "servers")
s.anonymous = true
s.addremove = false
o = s:option(DummyValue,"ssr_url","SS/SSR/V2RAY URL")
o = s:option(DummyValue,"ssr_url","SS/SSR/V2RAY/TROJAN URL")
o.rawhtml = true
o.template = "shadowsocksr/ssrurl"
o.value =sid
@ -127,6 +127,9 @@ end
if nixio.fs.access("/usr/bin/v2ray/v2ray") then
o:value("v2ray", translate("V2Ray"))
end
if nixio.fs.access("/usr/sbin/trojan") then
o:value("trojan", translate("Trojan"))
end
o.description = translate("Using incorrect encryption mothod may causes service fail to start")
o = s:option(Value, "alias", translate("Alias(optional)"))
@ -149,6 +152,7 @@ o.password = true
o.rmempty = true
o:depends("type", "ssr")
o:depends("type", "ss")
o:depends("type", "trojan")
o = s:option(ListValue, "encrypt_method", translate("Encrypt Method"))
for _, v in ipairs(encrypt_methods) do o:value(v) end
@ -327,18 +331,26 @@ o.rmempty = true
o = s:option(Flag, "insecure", translate("allowInsecure"))
o.rmempty = true
o:depends("type", "v2ray")
o:depends("type", "trojan")
-- [[ TLS ]]--
o = s:option(Flag, "tls", translate("TLS"))
o.rmempty = true
o.default = "0"
o:depends("type", "v2ray")
o:depends("type", "trojan")
o = s:option(Value, "tls_host", translate("TLS Host"))
o:depends("tls", "1")
o.rmempty = true
o:depends("type", "trojan")
-- [[ Mux ]]--
o = s:option(Flag, "mux", translate("Mux"))
o.rmempty = true
o.default = "0"
o:depends("type", "v2ray")
o:depends("type", "trojan")
o = s:option(Value, "concurrency", translate("Concurrency"))
o.datatype = "uinteger"

View File

@ -2,7 +2,8 @@ local fs = require "nixio.fs"
local conffile = "/tmp/ssrpro.log"
f = SimpleForm("logview")
f.reset = false
f.submit = false
t = f:field(TextValue, "conf")
t.rmempty = true
t.rows = 20
@ -12,4 +13,4 @@ function t.cfgvalue()
end
t.readonly="readonly"
return f
return f

View File

@ -88,7 +88,7 @@
var s = document.getElementById(urlname + '-status');
if (!s)
return false;
var ssrurl = prompt("在这里黏贴配置链接 ssr:// | ss:// | vmess://", "");
var ssrurl = prompt("在这里黏贴配置链接 ssr:// | ss:// | vmess:// | trojan://", "");
if (ssrurl == null || ssrurl == "") {
s.innerHTML = "<font color='red'>用户取消</font>";
return false;
@ -97,7 +97,7 @@
//var ssu = ssrurl.match(/ssr:\/\/([A-Za-z0-9_-]+)/i);
var ssu = ssrurl.split('://');
console.log(ssu.length);
if ((ssu[0] != "ssr" && ssu[0] != "ss" && ssu[0] != "vmess") || ssu[1] == "") {
if ((ssu[0] != "ssr" && ssu[0] != "ss" && ssu[0] != "vmess" && ssu[0] != "trojan") || ssu[1] == "") {
s.innerHTML = "<font color='red'>无效格式</font>";
return false;
}
@ -170,6 +170,29 @@
s.innerHTML = "<font color='green'>导入Shadowsocks配置信息成功</font>";
return false;
} else if (ssu[0] == "trojan") {
var ploc = ssu[1].indexOf("#");
if (ploc > 0) {
url0 = ssu[1].substr(0, ploc);
param = ssu[1].substr(ploc + 1);
} else {
url0 = ssu[1]
}
var sstr = b64decsafe(url0);
document.getElementById('cbid.shadowsocksr.' + sid + '.type').value = "trojan";
document.getElementById('cbid.shadowsocksr.' + sid + '.type').dispatchEvent(event);
var team = sstr.split('@');
console.log(param);
var part1 = team[0].split(':');
var part2 = team[1].split(':');
document.getElementById('cbid.shadowsocksr.' + sid + '.server').value = part2[0];
document.getElementById('cbid.shadowsocksr.' + sid + '.server_port').value = part2[1];
document.getElementById('cbid.shadowsocksr.' + sid + '.password').value = part1[1];
if (param != undefined) {
document.getElementById('cbid.shadowsocksr.' + sid + '.alias').value = decodeURI(param);
}
s.innerHTML = "<font color='green'>导入Trojan配置信息成功</font>";
return false;
} else if (ssu[0] == "vmess") {
var sstr = b64DecodeUnicode(ssu[1]);
var ploc = sstr.indexOf("/?");

View File

@ -378,7 +378,7 @@ msgid "GFW List"
msgstr "GFW列表"
msgid "ShadowSocksR Plus+ Settings"
msgstr "ShadowSocksR Plus+ 设置支持SS/SSR/V2RAY"
msgstr "ShadowSocksR Plus+ 设置支持SS/SSR/V2RAY/TROJAN"
msgid "Main Server"
msgstr "主服务器"
@ -516,10 +516,10 @@ msgid "Ping Latency"
msgstr "Ping延迟"
msgid "Bypass Domain List"
msgstr "域名白名单"
msgstr "不走代理的域名"
msgid "Black Domain List"
msgstr "域名黑名单"
msgstr "强制走代理的域名"
msgid "Update Subscribe List"
msgstr "更新订阅URL列表"

View File

@ -43,11 +43,10 @@ uci_get_by_type() {
add_cron()
{
sed -i '/ssrplus.log/d' $CRON_FILE
echo '0 1 * * * echo "" > /tmp/ssrplus.log' >> $CRON_FILE
[ -n "$(grep -w "/usr/share/shadowsocksr/subscribe.sh" $CRON_FILE)" ] && sed -i '/\/usr\/share\/shadowsocksr\/subscribe.sh/d' $CRON_FILE
sed -i '/shadowsocksr/d' $CRON_FILE
sed -i '/ssrplus.log/d' $CRON_FILE && echo '0 1 * * * echo "" > /tmp/ssrplus.log' >> $CRON_FILE
[ $(uci_get_by_type server_subscribe auto_update 0) -eq 1 ] && echo "0 $(uci_get_by_type server_subscribe auto_update_time) * * * /usr/share/shadowsocksr/subscribe.sh" >> $CRON_FILE
[ -z "$(grep -w "/usr/share/shadowsocksr/update.sh" $CRON_FILE)" ] && echo "0 5 * * * /usr/share/shadowsocksr/update.sh" >> $CRON_FILE
[ $(uci_get_by_type server_subscribe auto_update 0) -eq 1 ] && echo "0 5 * * * /usr/share/shadowsocksr/update.sh" >> $CRON_FILE
crontab $CRON_FILE
}
@ -67,7 +66,7 @@ gen_config_file() {
elif [ "$host" != "${host#*:[0-9a-fA-F]}" ] ;then
hostip=${host}
else
hostip=`nslookup ${host} | grep 'Address 1' | sed 's/Address 1: //g'`
hostip=`ping ${host} -s 1 -c 1 | grep PING | cut -d'(' -f 2 | cut -d')' -f1`
if echo $hostip|grep -E "^[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}$">/dev/null; then
hostip=${hostip}
else
@ -125,6 +124,9 @@ EOF
elif [ "$stype" == "v2ray" ] ;then
lua /usr/share/shadowsocksr/genv2config.lua $GLOBAL_SERVER tcp $(uci_get_by_name $1 local_port) > /var/etc/v2-ssr-retcp.json
sed -i 's/\\//g' /var/etc/v2-ssr-retcp.json
elif [ "$stype" == "trojan" ] ;then
lua /usr/share/shadowsocksr/gentrojanconfig.lua $GLOBAL_SERVER nat $(uci_get_by_name $1 local_port) > /var/etc/trojan-ssr-retcp.json
sed -i 's/\\//g' /var/etc/trojan-ssr-retcp.json
fi
}
@ -143,7 +145,7 @@ start_rules() {
elif [ "$server" != "${server#*:[0-9a-fA-F]}" ] ;then
server=${server}
else
server=`nslookup ${server} | grep 'Address 1' | sed 's/Address 1: //g'`
server=`ping ${server} -s 1 -c 1 | grep PING | cut -d'(' -f 2 | cut -d')' -f1`
if echo $server|grep -E "^[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}$">/dev/null; then
echo $server >/etc/ssr_ip
else
@ -265,7 +267,7 @@ server {
}
EOF
/usr/sbin/pdnsd -c /var/etc/pdnsd.conf &
/usr/sbin/pdnsd -c /var/etc/pdnsd.conf -d
}
@ -301,6 +303,8 @@ start_redir() {
sscmd="/usr/bin/ssr-redir"
elif [ "$stype" == "v2ray" ] ;then
sscmd="/usr/bin/v2ray/v2ray"
elif [ "$stype" == "trojan" ] ;then
sscmd="/usr/sbin/trojan"
fi
local utype=$(uci_get_by_name $UDP_RELAY_SERVER type)
@ -310,6 +314,8 @@ start_redir() {
ucmd="/usr/bin/ssr-redir"
elif [ "$utype" == "v2ray" ] ;then
ucmd="/usr/bin/v2ray/v2ray"
elif [ "$utype" == "trojan" ] ;then
ucmd="/usr/sbin/trojan"
fi
if [ "$(uci_get_by_type global threads 0)" = "0" ] ;then
@ -330,6 +336,9 @@ start_redir() {
elif [ "$stype" == "v2ray" ] ;then
$sscmd -config /var/etc/v2-ssr-retcp.json >/dev/null 2>&1 &
echo "$(date "+%Y-%m-%d %H:%M:%S") $($sscmd -version | head -1) Started!" >> /tmp/ssrplus.log
elif [ "$stype" == "trojan" ] ;then
$sscmd --config /var/etc/trojan-ssr-retcp.json >/dev/null 2>&1 &
echo "$(date "+%Y-%m-%d %H:%M:%S") $($sscmd --version 2>&1 | head -1) Started!" >> /tmp/ssrplus.log
fi
if [ -n "$UDP_RELAY_SERVER" ] ;then
@ -346,7 +355,12 @@ start_redir() {
elif [ "$utype" == "v2ray" ] ; then
lua /usr/share/shadowsocksr/genv2config.lua $UDP_RELAY_SERVER udp $(uci_get_by_name $UDP_RELAY_SERVER local_port) > /var/etc/v2-ssr-reudp.json
sed -i 's/\\//g' /var/etc/v2-ssr-reudp.json
$ucmd -config /var/etc/v2-ssr-reudp.json >/dev/null 2>&1 &
$ucmd -config /var/etc/v2-ssr-reudp.json >/dev/null 2>&1 &
elif [ "$stype" == "trojan" ] ;then
lua /usr/share/shadowsocksr/gentrojanconfig.lua $GLOBAL_SERVER client 10801 > /var/etc/trojan-ssr-reudp.json
sed -i 's/\\//g' /var/etc/trojan-ssr-reudp.json
$ucmd --config /var/etc/trojan-ssr-reudp.json >/dev/null 2>&1 &
ipt2socks -U -4 -b 0.0.0.0 -s 127.0.0.1 -p 10801 -l $(uci_get_by_name $UDP_RELAY_SERVER local_port) >/dev/null 2>&1 &
fi
fi
@ -537,10 +551,16 @@ stop() {
killall -q -9 ss-redir
killall -q -9 ssr-redir
killall -q -9 v2ray
killall -q -9 trojan
killall -q -9 ipt2socks
killall -q -9 ssr-server
killall -q -9 kcptun-client
killall -q -9 ssr-local
killall -q -9 pdnsd
if [ -f /var/run/pdnsd.pid ] ;then
kill $(cat /var/run/pdnsd.pid) >/dev/null 2>&1
else
kill -9 $(busybox ps -w | grep pdnsd | grep -v grep | awk '{print $1}') >/dev/null 2>&1
fi
if [ -f "/tmp/dnsmasq.d/dnsmasq-ssr.conf" ]; then
rm -f /tmp/dnsmasq.d/dnsmasq-ssr.conf

View File

@ -0,0 +1,38 @@
local ucursor = require "luci.model.uci".cursor()
local json = require "luci.jsonc"
local server_section = arg[1]
local proto = arg[2]
local local_port = arg[3]
local server = ucursor:get_all("shadowsocksr", server_section)
local trojan = {
log_level = 3,
run_type = proto,
local_addr = "0.0.0.0",
local_port = tonumber(local_port),
remote_addr = server.server,
remote_port = tonumber(server.server_port),
udp_timeout = 60,
-- 传入连接
password = {server.password},
-- 传出连接
ssl = {
verify = false,
verify_hostname = (server.tls == "1") and false or true,
cert = "",
ciper = "ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-CHACHA20-POLY1305:ECDHE-RSA-CHACHA20-POLY1305:ECDHE-RSA-AES128-SHA:ECDHE-RSA-AES256-SHA:RSA-AES128-GCM-SHA256:RSA-AES256-GCM-SHA384:RSA-AES128-SHA:RSA-AES256-SHA:RSA-3DES-EDE-SHA",
sni = server.tls_host,
alpn = {"h2", "http/1.1"},
curve = "",
reuse_session = true,
session_ticket = false,
},
tcp = {
no_delay = true,
keep_alive = true,
fast_open = (server.fast_open == "1") and true or false,
fast_open_qlen = 20
}
}
print(json.stringify(trojan, 1))

View File

@ -11,7 +11,7 @@ include $(TOPDIR)/rules.mk
PKG_NAME:=luci-app-unblockmusic
PKG_VERSION:=2.2.0
PKG_RELEASE:=9
PKG_RELEASE:=11
PKG_LICENSE:=Apache-2.0

View File

@ -25,7 +25,7 @@ add_rule()
$ipt_n -A cloud_music -d 192.168.0.0/16 -j RETURN
$ipt_n -A cloud_music -d 224.0.0.0/4 -j RETURN
$ipt_n -A cloud_music -d 240.0.0.0/4 -j RETURN
$ipt_n -A cloud_music -p tcp -j REDIRECT --to-ports 5202
$ipt_n -A cloud_music -p tcp -j REDIRECT --to-ports 5200
$ipt_n -I PREROUTING -p tcp --dport 80 -m set --match-set music dst -j cloud_music
}
@ -41,7 +41,7 @@ del_rule(){
set_firewall(){
rm -f /tmp/dnsmasq.d/dnsmasq-163.conf
mkdir -p /tmp/dnsmasq.d
echo "dhcp-option=252,http://$ROUTE_IP:5200/proxy.pac" > /tmp/dnsmasq.d/dnsmasq-163.conf
echo "dhcp-option=252,http://$ROUTE_IP:5201/proxy.pac" > /tmp/dnsmasq.d/dnsmasq-163.conf
echo "ipset=/music.163.com/music" >> /tmp/dnsmasq.d/dnsmasq-163.conf
echo "ipset=/interface.music.163.com/music" >> /tmp/dnsmasq.d/dnsmasq-163.conf
/etc/init.d/dnsmasq restart >/dev/null 2>&1
@ -82,11 +82,11 @@ start()
fi
if [ $TYPE = "default" ]; then
node /usr/share/UnblockNeteaseMusic/app.js $endponintset -p 5200:5201 >/tmp/unblockmusic.log 2>&1 &
node /usr/share/UnblockNeteaseMusic/app.js -p 5202 >>/tmp/unblockmusic.log 2>&1 &
node /usr/share/UnblockNeteaseMusic/app.js $endponintset -p 5201:5202 >/tmp/unblockmusic.log 2>&1 &
node /usr/share/UnblockNeteaseMusic/app.js -p 5200 >>/tmp/unblockmusic.log 2>&1 &
else
node /usr/share/UnblockNeteaseMusic/app.js $endponintset -p 5200:5201 -o $TYPE >/tmp/unblockmusic.log 2>&1 &
node /usr/share/UnblockNeteaseMusic/app.js -p 5202 -o $TYPE >>/tmp/unblockmusic.log 2>&1 &
node /usr/share/UnblockNeteaseMusic/app.js $endponintset -p 5201:5202 -o $TYPE >/tmp/unblockmusic.log 2>&1 &
node /usr/share/UnblockNeteaseMusic/app.js -p 5200 -o $TYPE >>/tmp/unblockmusic.log 2>&1 &
fi
set_firewall

View File

@ -0,0 +1,3 @@
/usr/share/UnblockNeteaseMusic/ca.crt
/usr/share/UnblockNeteaseMusic/server.crt
/usr/share/UnblockNeteaseMusic/server.key

View File

@ -1,11 +1,11 @@
#!/bin/bash
log_max_size="10" #使用KB计算
log_max_size="100" #使用KB计算
log_file="/tmp/unblockmusic.log"
while true
do
sleep 10s
sleep 30s
icount=`busybox ps -w | grep app.js |grep -v grep| wc -l`
if [ $icount -ne 2 ] ;then
/etc/init.d/unblockmusic restart

View File

@ -10,7 +10,7 @@ function clean_log(){
}
function check_latest_version(){
latest_ver="$(wget -O- https://github.com/nondanee/UnblockNeteaseMusic/commits/master |tr -d '\n' |grep -Eo 'commit\/[0-9a-z]+' |sed -n 1p |sed 's#commit/##g')"
latest_ver="$(wget-ssl --no-check-certificate -O- https://github.com/nondanee/UnblockNeteaseMusic/commits/master |tr -d '\n' |grep -Eo 'commit\/[0-9a-z]+' |sed -n 1p |sed 's#commit/##g')"
[ -z "${latest_ver}" ] && echo -e "\nFailed to check latest version, please try again later." >>/tmp/unblockmusic_update.log && exit 1
if [ ! -e "/usr/share/UnblockNeteaseMusic/local_ver" ]; then
clean_log

View File

@ -1,14 +1,14 @@
include $(TOPDIR)/rules.mk
PKG_NAME:=qBittorrent
PKG_VERSION:=4.1.8
PKG_RELEASE=1
PKG_NAME:=qbittorrent
PKG_VERSION:=4.1.9
PKG_RELEASE=5
PKG_SOURCE_PROTO:=git
PKG_SOURCE_URL:=https://github.com/qbittorrent/qBittorrent.git
PKG_SOURCE_SUBDIR:=$(PKG_NAME)-$(PKG_VERSION)
PKG_SOURCE_VERSION:=0de5cbaa4becf4eb89245324cb76c9a7c9412a33
PKG_SOURCE:=$(PKG_NAME)-$(PKG_VERSION).tar.gz
PKG_SOURCE:=$(PKG_NAME)-release-$(PKG_VERSION).tar.gz
PKG_SOURCE_URL:=https://codeload.github.com/qbittorrent/qBittorrent/tar.gz/release-$(PKG_VERSION)?
PKG_HASH:=620127f73f88ed3f2b2e4195cbc641f7c27f967d3b045e45f7916c0995fd61fe
PKG_BUILD_DIR:=$(BUILD_DIR)/qBittorrent-release-$(PKG_VERSION)
PKG_LICENSE:=GPL-2.0+
PKG_LICENSE_FILES:=COPYING
@ -36,17 +36,19 @@ there. qBittorrent is fast, stable and provides unicode support as
well as many features.
endef
CONFIGURE_VARS += \
QT_QMAKE="$(TOOLCHAIN_DIR)/bin" \
PKG_CONFIG_PATH="$(TOOLCHAIN_DIR)/lib/pkgconfig"
CONFIGURE_ARGS += \
--disable-gui \
--enable-stacktrace=no \
--with-boost=$(STAGING_DIR)/usr
MAKE_VARS += \
INSTALL_ROOT="$(PKG_INSTALL_DIR)"
define Build/Prepare
$(call Build/Prepare/Default)
$(SED) '/<context>/{:a;N;/<\/context>/!ba;/\/gui\//d}' `ls $(PKG_BUILD_DIR)/src/lang/qbittorrent_*.ts`
endef
define Package/qBittorrent/install
$(INSTALL_DIR) $(1)/usr/man/man1
$(INSTALL_BIN) $(PKG_INSTALL_DIR)/usr/man/man1/qbittorrent-nox.1 $(1)/usr/man/man1/qbittorrent-nox.1

View File

@ -0,0 +1,126 @@
--- a/src/icons/icons.qrc
+++ b/src/icons/icons.qrc
@@ -250,38 +250,16 @@
<file>flags/zm.svg</file>
<file>flags/zw.svg</file>
<file>L.gif</file>
- <file>loading.png</file>
<file>qbt-theme/application-exit.svg</file>
- <file>qbt-theme/application-rss+xml.svg</file>
- <file>qbt-theme/application-x-mswinurl.svg</file>
<file>qbt-theme/checked.svg</file>
<file>qbt-theme/configure.svg</file>
- <file>qbt-theme/dialog-cancel.svg</file>
- <file>qbt-theme/dialog-information.svg</file>
- <file>qbt-theme/dialog-warning.svg</file>
<file>qbt-theme/document-edit-verify.svg</file>
<file>qbt-theme/document-edit.svg</file>
- <file>qbt-theme/document-encrypt.svg</file>
- <file>qbt-theme/document-import.svg</file>
- <file>qbt-theme/document-new.svg</file>
- <file>qbt-theme/document-properties.svg</file>
- <file>qbt-theme/document-save.svg</file>
- <file>qbt-theme/download.svg</file>
- <file>qbt-theme/edit-clear-history.svg</file>
<file>qbt-theme/edit-clear.svg</file>
<file>qbt-theme/edit-copy.svg</file>
- <file>qbt-theme/edit-cut.svg</file>
<file>qbt-theme/edit-delete.svg</file>
- <file>qbt-theme/edit-find-user.svg</file>
<file>qbt-theme/edit-find.svg</file>
- <file>qbt-theme/edit-paste.svg</file>
<file>qbt-theme/edit-rename.svg</file>
- <file>qbt-theme/folder-documents.svg</file>
- <file>qbt-theme/folder-download.svg</file>
- <file>qbt-theme/folder-new.svg</file>
- <file>qbt-theme/folder-remote.svg</file>
- <file>qbt-theme/gear.svg</file>
- <file>qbt-theme/gear32.svg</file>
<file>qbt-theme/go-bottom.svg</file>
<file>qbt-theme/go-down.svg</file>
<file>qbt-theme/go-top.svg</file>
@@ -295,43 +273,15 @@
<file>qbt-theme/kt-set-max-upload-speed.png</file>
<file>qbt-theme/list-add.svg</file>
<file>qbt-theme/list-remove.svg</file>
- <file>qbt-theme/mail-folder-inbox.svg</file>
- <file>qbt-theme/mail-mark-read.svg</file>
<file>qbt-theme/media-playback-pause.svg</file>
<file>qbt-theme/media-playback-start.svg</file>
<file>qbt-theme/media-seek-forward.svg</file>
- <file>qbt-theme/network-server.svg</file>
- <file>qbt-theme/network-wired.svg</file>
- <file>qbt-theme/object-locked.svg</file>
- <file>qbt-theme/office-chart-line.svg</file>
- <file>qbt-theme/preferences-desktop.svg</file>
- <file>qbt-theme/preferences-other.svg</file>
- <file>qbt-theme/preferences-system-network.svg</file>
- <file>qbt-theme/preferences-web-browser-cookies.svg</file>
- <file>qbt-theme/rss-config.png</file>
<file>qbt-theme/security-high.svg</file>
<file>qbt-theme/security-low.svg</file>
- <file>qbt-theme/services.svg</file>
- <file>qbt-theme/speedometer.svg</file>
<file>qbt-theme/system-log-out.svg</file>
- <file>qbt-theme/tab-close.svg</file>
- <file>qbt-theme/task-attention.svg</file>
- <file>qbt-theme/task-complete.png</file>
- <file>qbt-theme/task-ongoing.png</file>
- <file>qbt-theme/task-reject.png</file>
- <file>qbt-theme/text-plain.svg</file>
- <file>qbt-theme/tools-report-bug.svg</file>
- <file>qbt-theme/unavailable.svg</file>
- <file>qbt-theme/user-group-delete.svg</file>
- <file>qbt-theme/user-group-new.svg</file>
- <file>qbt-theme/view-calendar-journal.svg</file>
<file>qbt-theme/view-categories.svg</file>
- <file>qbt-theme/view-filter.svg</file>
- <file>qbt-theme/view-preview.svg</file>
- <file>qbt-theme/view-refresh.svg</file>
<file>qbt-theme/view-statistics.svg</file>
<file>qbt-theme/wallet-open.svg</file>
- <file>qbt-theme/webui.svg</file>
<file>skin/arrow-right.gif</file>
<file>skin/bg-dropdown.gif</file>
<file>skin/bg-handle-horizontal.gif</file>
@@ -342,7 +292,6 @@
<file>skin/completed.svg</file>
<file>skin/connected.svg</file>
<file>skin/disconnected.svg</file>
- <file>skin/dock-tabs.gif</file>
<file>skin/download.svg</file>
<file>skin/downloading.svg</file>
<file>skin/error.svg</file>
@@ -353,14 +302,11 @@
<file>skin/handle-icon-horizontal.gif</file>
<file>skin/handle-icon.gif</file>
<file>skin/knob.gif</file>
- <file>skin/logo-blank.gif</file>
<file>skin/logo.gif</file>
<file>skin/logo2.gif</file>
<file>skin/mascot.png</file>
<file>skin/paused.svg</file>
<file>skin/qbittorrent-tray.svg</file>
- <file>skin/qbittorrent-tray-dark.svg</file>
- <file>skin/qbittorrent-tray-light.svg</file>
<file>skin/qbittorrent32.png</file>
<file>skin/queued.svg</file>
<file>skin/ratio.svg</file>
@@ -370,17 +316,12 @@
<file>skin/spacer.gif</file>
<file>skin/spinner-placeholder.gif</file>
<file>skin/spinner.gif</file>
- <file>skin/splash.png</file>
<file>skin/stalledDL.svg</file>
<file>skin/stalledUP.svg</file>
<file>skin/tabs.gif</file>
<file>skin/toolbox-divider.gif</file>
- <file>skin/toolbox-divider2.gif</file>
<file>skin/uploading.svg</file>
<file>slow.png</file>
<file>slow_off.png</file>
- <file>sphere.png</file>
- <file>sphere2.png</file>
- <file>url.png</file>
</qresource>
</RCC>

View File

@ -0,0 +1,807 @@
--- a/src/base/bittorrent/peerinfo.cpp
+++ b/src/base/bittorrent/peerinfo.cpp
@@ -186,11 +186,26 @@ PeerAddress PeerInfo::address() const
m_nativeInfo.ip.port());
}
+int PeerInfo::port() const
+{
+ return m_nativeInfo.ip.port();
+}
+
QString PeerInfo::client() const
{
return QString::fromStdString(m_nativeInfo.client);
}
+QString PeerInfo::pid() const
+{
+ return QString::fromStdString(m_nativeInfo.pid.to_string());
+}
+
+QString PeerInfo::pidtoclient() const
+{
+ return QString::fromStdString(libt::identify_client(m_nativeInfo.pid));
+}
+
qreal PeerInfo::progress() const
{
return m_nativeInfo.progress;
--- a/src/base/bittorrent/peerinfo.h
+++ b/src/base/bittorrent/peerinfo.h
@@ -34,6 +34,7 @@
#include <QHostAddress>
#include <libtorrent/peer_info.hpp>
+#include <libtorrent/identify_client.hpp>
namespace BitTorrent
{
@@ -85,7 +86,10 @@ namespace BitTorrent
bool isPlaintextEncrypted() const;
PeerAddress address() const;
+ int port() const;
QString client() const;
+ QString pid() const;
+ QString pidtoclient() const;
qreal progress() const;
int payloadUpSpeed() const;
int payloadDownSpeed() const;
--- a/src/base/bittorrent/session.cpp
+++ b/src/base/bittorrent/session.cpp
@@ -69,6 +69,7 @@
#endif
#include "base/algorithm.h"
+#include "base/bittorrent/peerinfo.h"
#include "base/exceptions.h"
#include "base/global.h"
#include "base/logger.h"
@@ -335,6 +336,8 @@ Session::Session(QObject *parent)
, m_isAltGlobalSpeedLimitEnabled(BITTORRENT_SESSION_KEY("UseAlternativeGlobalSpeedLimit"), false)
, m_isBandwidthSchedulerEnabled(BITTORRENT_SESSION_KEY("BandwidthSchedulerEnabled"), false)
, m_saveResumeDataInterval(BITTORRENT_SESSION_KEY("SaveResumeDataInterval"), 60)
+ , m_autoBanUnknownPeer(BITTORRENT_SESSION_KEY("AutoBanUnknownPeer"), true)
+ , m_showTrackerAuthWindow(BITTORRENT_SESSION_KEY("ShowTrackerAuthWindow"), true)
, m_port(BITTORRENT_SESSION_KEY("Port"), 8999)
, m_useRandomPort(BITTORRENT_SESSION_KEY("UseRandomPort"), false)
, m_networkInterface(BITTORRENT_SESSION_KEY("Interface"))
@@ -502,6 +505,7 @@ Session::Session(QObject *parent)
libt::ip_filter filter;
processBannedIPs(filter);
m_nativeSession->set_ip_filter(filter);
+ loadOfflineFilter();
}
m_categories = map_cast(m_storedCategories);
@@ -518,6 +522,17 @@ Session::Session(QObject *parent)
connect(m_refreshTimer, &QTimer::timeout, this, &Session::refresh);
m_refreshTimer->start();
+ // Unban Timer
+ m_unbanTimer = new QTimer(this);
+ m_unbanTimer->setInterval(500);
+ connect(m_unbanTimer, &QTimer::timeout, this, &Session::processUnbanRequest);
+
+ // Ban Timer
+ m_banTimer = new QTimer(this);
+ m_banTimer->setInterval(500);
+ connect(m_banTimer, &QTimer::timeout, this, &Session::autoBanBadClient);
+ m_banTimer->start();
+
m_statistics = new Statistics(this);
updateSeedingLimitTimer();
@@ -1077,6 +1092,7 @@ void Session::configure()
enableIPFilter();
else
disableIPFilter();
+ loadOfflineFilter();
m_IPFilteringChanged = false;
}
@@ -1905,6 +1921,95 @@ void Session::banIP(const QString &ip)
}
}
+bool Session::checkAccessFlags(const QString &ip)
+{
+ libt::ip_filter filter = m_nativeSession->get_ip_filter();
+ boost::system::error_code ec;
+ libt::address addr = libt::address::from_string(ip.toLatin1().constData(), ec);
+ Q_ASSERT(!ec);
+ if (ec) return false;
+ return filter.access(addr);
+}
+
+void Session::tempblockIP(const QString &ip)
+{
+ libt::ip_filter filter = m_nativeSession->get_ip_filter();
+ boost::system::error_code ec;
+ libt::address addr = libt::address::from_string(ip.toLatin1().constData(), ec);
+ Q_ASSERT(!ec);
+ if (ec) return;
+ filter.add_rule(addr, addr, libt::ip_filter::blocked);
+ m_nativeSession->set_ip_filter(filter);
+ insertQueue(ip);
+}
+
+void Session::removeBlockedIP(const QString &ip)
+{
+ libt::ip_filter filter = m_nativeSession->get_ip_filter();
+ boost::system::error_code ec;
+ libt::address addr = libt::address::from_string(ip.toLatin1().constData(), ec);
+ Q_ASSERT(!ec);
+ if (ec) return;
+ filter.add_rule(addr, addr, 0);
+ m_nativeSession->set_ip_filter(filter);
+}
+
+void Session::eraseIPFilter()
+{
+ q_bannedIPs.clear();
+ q_unbanTime.clear();
+ if (isIPFilteringEnabled()) {
+ enableIPFilter();
+ } else {
+ disableIPFilter();
+ loadOfflineFilter();
+ }
+}
+
+void Session::autoBanBadClient()
+{
+ const BitTorrent::SessionStatus tStatus = BitTorrent::Session::instance()->status();
+ if (tStatus.peersCount > 0) {
+ bool m_AutoBan = BitTorrent::Session::instance()->isAutoBanUnknownPeerEnabled();
+ foreach (BitTorrent::TorrentHandle *const torrent, BitTorrent::Session::instance()->torrents()) {
+ QList<BitTorrent::PeerInfo> peers = torrent->peers();
+ foreach (const BitTorrent::PeerInfo &peer, peers) {
+ BitTorrent::PeerAddress addr = peer.address();
+ if (addr.ip.isNull()) continue;
+ QString ip = addr.ip.toString();
+ int port = peer.port();
+ QString client = peer.client();
+ QString ptoc = peer.pidtoclient();
+ QString pid = peer.pid().left(8);
+ QString country = peer.country();
+
+ QRegExp IDFilter("-(XL|SD|XF|QD|BN|DL)(\\d+)-");
+ QRegExp UAFilter("\\d+.\\d+.\\d+.\\d+");
+ if (IDFilter.exactMatch(pid) || UAFilter.exactMatch(client)) {
+ qDebug("Auto Banning bad Peer %s...", ip.toLocal8Bit().data());
+ Logger::instance()->addMessage(tr("Auto banning bad Peer '%1'...'%2'...'%3'...'%4'").arg(ip).arg(pid).arg(ptoc).arg(country));
+ tempblockIP(ip);
+ continue;
+ }
+
+ if(m_AutoBan) {
+ if (client.contains("Unknown") && country == "CN") {
+ qDebug("Auto Banning Unknown Peer %s...", ip.toLocal8Bit().data());
+ Logger::instance()->addMessage(tr("Auto banning Unknown Peer '%1'...'%2'...'%3'...'%4'").arg(ip).arg(pid).arg(ptoc).arg(country));
+ tempblockIP(ip);
+ continue;
+ }
+ if (port >= 65000 && country == "CN" && client.contains("Transmission")) {
+ qDebug("Auto Banning Offline Downloader %s...", ip.toLocal8Bit().data());
+ Logger::instance()->addMessage(tr("Auto banning Offline Downloader '%1:%2'...'%3'...'%4'...'%5'").arg(ip).arg(port).arg(pid).arg(ptoc).arg(country));
+ tempblockIP(ip);
+ }
+ }
+ }
+ }
+ }
+}
+
// Delete a torrent from the session, given its hash
// deleteLocalFiles = true means that the torrent will be removed from the hard-drive too
bool Session::deleteTorrent(const QString &hash, bool deleteLocalFiles)
@@ -2787,6 +2892,30 @@ void Session::setSaveResumeDataInterval(
}
}
+bool Session::isAutoBanUnknownPeerEnabled() const
+{
+ return m_autoBanUnknownPeer;
+}
+
+void Session::setAutoBanUnknownPeer(bool value)
+{
+ if (value != isAutoBanUnknownPeerEnabled()) {
+ m_autoBanUnknownPeer = value;
+ }
+}
+
+bool Session::isShowTrackerAuthWindow() const
+{
+ return m_showTrackerAuthWindow;
+}
+
+void Session::setShowTrackerAuthWindow(bool value)
+{
+ if (value != isShowTrackerAuthWindow()) {
+ m_showTrackerAuthWindow = value;
+ }
+}
+
int Session::port() const
{
static int randomPort = Utils::Random::rand(1024, 65535);
@@ -3877,6 +4006,220 @@ void Session::disableIPFilter()
m_nativeSession->set_ip_filter(filter);
}
+// Insert banned IP to Queue
+void Session::insertQueue(QString ip)
+{
+ q_bannedIPs.enqueue(ip);
+ q_unbanTime.enqueue(QDateTime::currentMSecsSinceEpoch() + 60 * 60 * 1000);
+
+ if (!m_unbanTimer->isActive()) {
+ m_unbanTimer->start();
+ }
+}
+
+// Process Unban Queue
+void Session::processUnbanRequest()
+{
+ if (q_bannedIPs.isEmpty() && q_unbanTime.isEmpty()) {
+ m_unbanTimer->stop();
+ }
+ else if (m_isActive) {
+ return;
+ }
+ else {
+ m_isActive = true;
+ int64_t currentTime = QDateTime::currentMSecsSinceEpoch();
+ int64_t nextTime = q_unbanTime.dequeue();
+ int delayTime = int(nextTime - currentTime);
+ QString nextIP = q_bannedIPs.dequeue();
+ if (delayTime < 0) {
+ QTimer::singleShot(0, [=] { BitTorrent::Session::instance()->removeBlockedIP(nextIP); m_isActive = false; });
+ }
+ else {
+ QTimer::singleShot(delayTime, [=] { BitTorrent::Session::instance()->removeBlockedIP(nextIP); m_isActive = false; });
+ }
+ }
+}
+
+// Handle ipfilter.dat
+int trim(char* const data, int start, int end)
+{
+ if (start >= end) return start;
+ int newStart = start;
+
+ for (int i = start; i <= end; ++i) {
+ if (isspace(data[i]) != 0) {
+ data[i] = '\0';
+ }
+ else {
+ newStart = i;
+ break;
+ }
+ }
+
+ for (int i = end; i >= start; --i) {
+ if (isspace(data[i]) != 0)
+ data[i] = '\0';
+ else
+ break;
+ }
+
+ return newStart;
+}
+
+int findAndNullDelimiter(char *const data, char delimiter, int start, int end)
+{
+ for (int i = start; i <= end; ++i) {
+ if (data[i] == delimiter) {
+ data[i] = '\0';
+ return i;
+ }
+ }
+
+ return -1;
+}
+
+int Session::parseOfflineFilterFile(QString ipDat, libt::ip_filter &filter)
+{
+ int ruleCount = 0;
+ QFile file(ipDat);
+ if (!file.exists()) return ruleCount;
+
+ if (!file.open(QIODevice::ReadOnly | QIODevice::Text)) {
+ LogMsg(tr("I/O Error: Could not open IP filter file in read mode."), Log::CRITICAL);
+ return ruleCount;
+ }
+
+ std::vector<char> buffer(2 * 1024 * 1024, 0); // seems a bit faster than QVector
+ qint64 bytesRead = 0;
+ int offset = 0;
+ int start = 0;
+ int endOfLine = -1;
+ int nbLine = 0;
+
+ while (true) {
+ bytesRead = file.read(buffer.data() + offset, 2 * 1024 * 1024 - offset - 1);
+ if (bytesRead < 0)
+ break;
+ int dataSize = bytesRead + offset;
+ if (bytesRead == 0 && dataSize == 0)
+ break;
+
+ for (start = 0; start < dataSize; ++start) {
+ endOfLine = -1;
+ // The file might have ended without the last line having a newline
+ if (!(bytesRead == 0 && dataSize > 0)) {
+ for (int i = start; i < dataSize; ++i) {
+ if (buffer[i] == '\n') {
+ endOfLine = i;
+ // We need to NULL the newline in case the line has only an IP range.
+ // In that case the parser won't work for the end IP, because it ends
+ // with the newline and not with a number.
+ buffer[i] = '\0';
+ break;
+ }
+ }
+ }
+ else {
+ endOfLine = dataSize;
+ buffer[dataSize] = '\0';
+ }
+
+ if (endOfLine == -1) {
+ // read the next chunk from file
+ // but first move(copy) the leftover data to the front of the buffer
+ offset = dataSize - start;
+ memmove(buffer.data(), buffer.data() + start, offset);
+ break;
+ }
+ else {
+ ++nbLine;
+ }
+
+ if ((buffer[start] == '#')
+ || ((buffer[start] == '/') && ((start + 1 < dataSize) && (buffer[start + 1] == '/')))) {
+ start = endOfLine;
+ continue;
+ }
+
+ // Each line should follow this format:
+ // 001.009.096.105 - 001.009.096.105 , 000 , Some organization
+ // The 3rd entry is access level and if above 127 the IP range isn't blocked.
+ int firstComma = findAndNullDelimiter(buffer.data(), ',', start, endOfLine);
+ if (firstComma != -1)
+ findAndNullDelimiter(buffer.data(), ',', firstComma + 1, endOfLine);
+
+ // Check if there is an access value (apparently not mandatory)
+ if (firstComma != -1) {
+ // There is possibly one
+ const long int nbAccess = strtol(buffer.data() + firstComma + 1, nullptr, 10);
+ // Ignoring this rule because access value is too high
+ if (nbAccess > 127L) {
+ start = endOfLine;
+ continue;
+ }
+ }
+
+ // IP Range should be split by a dash
+ int endOfIPRange = ((firstComma == -1) ? (endOfLine - 1) : (firstComma - 1));
+ int delimIP = findAndNullDelimiter(buffer.data(), '-', start, endOfIPRange);
+ if (delimIP == -1) {
+ start = endOfLine;
+ continue;
+ }
+
+ boost::system::error_code ec;
+ int newStart = trim(buffer.data(), start, delimIP - 1);
+ libt::address startAddr = libt::address::from_string(buffer.data() + newStart, ec);
+ Q_ASSERT(!ec);
+ if (ec) {
+ start = endOfLine;
+ continue;
+ }
+
+ newStart = trim(buffer.data(), delimIP + 1, endOfIPRange);
+ libt::address endAddr = libt::address::from_string(buffer.data() + newStart, ec);
+ Q_ASSERT(!ec);
+ if (ec) {
+ start = endOfLine;
+ continue;
+ }
+
+ if ((startAddr.is_v4() != endAddr.is_v4())
+ || (startAddr.is_v6() != endAddr.is_v6())) {
+ start = endOfLine;
+ continue;
+ }
+
+ start = endOfLine;
+
+ filter.add_rule(startAddr, endAddr, libt::ip_filter::blocked);
+ ++ruleCount;
+ }
+
+ if (start >= dataSize)
+ offset = 0;
+ }
+
+ return ruleCount;
+}
+
+void Session::loadOfflineFilter() {
+ int Count = 0;
+ libt::ip_filter offlineFilter = m_nativeSession->get_ip_filter();
+
+#if defined(Q_OS_WIN)
+ Count = parseOfflineFilterFile("./ipfilter.dat", offlineFilter);
+#endif
+
+#if (defined(Q_OS_UNIX) && !defined(Q_OS_MAC))
+ Count = parseOfflineFilterFile(QDir::home().absoluteFilePath(".config")+"/qBittorrent/ipfilter.dat", offlineFilter);
+#endif
+
+ m_nativeSession->set_ip_filter(offlineFilter);
+ Logger::instance()->addMessage(tr("Successfully parsed the offline downloader IP filter: %1 rules were applied.", "%1 is a number").arg(Count));
+}
+
void Session::recursiveTorrentDownload(const InfoHash &hash)
{
TorrentHandle *const torrent = m_torrents.value(hash);
@@ -4063,6 +4406,7 @@ void Session::handleIPFilterParsed(int r
}
Logger::instance()->addMessage(tr("Successfully parsed the provided IP filter: %1 rules were applied.", "%1 is a number").arg(ruleCount));
emit IPFilterParsed(false, ruleCount);
+ loadOfflineFilter();
}
void Session::handleIPFilterError()
--- a/src/base/bittorrent/session.h
+++ b/src/base/bittorrent/session.h
@@ -40,8 +40,10 @@
#include <QMap>
#include <QNetworkConfigurationManager>
#include <QPointer>
+#include <QQueue>
#include <QSet>
#include <QStringList>
+#include <QTimer>
#include <QVector>
#include <QWaitCondition>
@@ -341,6 +343,10 @@ namespace BitTorrent
uint saveResumeDataInterval() const;
void setSaveResumeDataInterval(uint value);
+ bool isAutoBanUnknownPeerEnabled() const;
+ void setAutoBanUnknownPeer(bool value);
+ bool isShowTrackerAuthWindow() const;
+ void setShowTrackerAuthWindow(bool value);
int port() const;
void setPort(int port);
bool useRandomPort() const;
@@ -467,6 +473,19 @@ namespace BitTorrent
void setMaxRatioAction(MaxRatioAction act);
void banIP(const QString &ip);
+ bool checkAccessFlags(const QString &ip);
+ void tempblockIP(const QString &ip);
+ void removeBlockedIP(const QString &ip);
+ void eraseIPFilter();
+ void autoBanBadClient();
+
+ // Unban Timer
+ bool m_isActive = false;
+ QQueue<QString> q_bannedIPs;
+ QQueue<int64_t> q_unbanTime;
+ QTimer *m_unbanTimer;
+ QTimer *m_banTimer;
+ void insertQueue(QString ip);
bool isKnownTorrent(const InfoHash &hash) const;
bool addTorrent(QString source, const AddTorrentParams &params = AddTorrentParams());
@@ -546,6 +565,9 @@ namespace BitTorrent
void tagAdded(const QString &tag);
void tagRemoved(const QString &tag);
+ public slots:
+ void processUnbanRequest();
+
private slots:
void configureDeferred();
void readAlerts();
@@ -601,6 +623,8 @@ namespace BitTorrent
void populateAdditionalTrackers();
void enableIPFilter();
void disableIPFilter();
+ int parseOfflineFilterFile(QString ipDat, libtorrent::ip_filter &filter);
+ void loadOfflineFilter();
bool addTorrent_impl(CreateTorrentParams params, const MagnetUri &magnetUri,
TorrentInfo torrentInfo = TorrentInfo(),
@@ -713,6 +737,8 @@ namespace BitTorrent
CachedSettingValue<bool> m_isAltGlobalSpeedLimitEnabled;
CachedSettingValue<bool> m_isBandwidthSchedulerEnabled;
CachedSettingValue<uint> m_saveResumeDataInterval;
+ CachedSettingValue<bool> m_autoBanUnknownPeer;
+ CachedSettingValue<bool> m_showTrackerAuthWindow;
CachedSettingValue<int> m_port;
CachedSettingValue<bool> m_useRandomPort;
CachedSettingValue<QString> m_networkInterface;
--- a/src/base/bittorrent/torrenthandle.cpp
+++ b/src/base/bittorrent/torrenthandle.cpp
@@ -1561,7 +1561,8 @@ void TorrentHandle::handleTrackerErrorAl
m_trackerInfos[trackerUrl].lastMessage = message;
if (p->status_code == 401)
- m_session->handleTorrentTrackerAuthenticationRequired(this, trackerUrl);
+ if (Preferences::instance()->getShowTrackerAuthWindow())
+ m_session->handleTorrentTrackerAuthenticationRequired(this, trackerUrl);
m_session->handleTorrentTrackerError(this, trackerUrl);
}
--- a/src/base/preferences.cpp
+++ b/src/base/preferences.cpp
@@ -1090,6 +1090,26 @@ void Preferences::setTrayIconStyle(TrayI
}
#endif
+bool Preferences::getAutoBanUnknownPeer() const
+{
+ return value("Preferences/Advanced/AutoBanUnknownPeer", false).toBool();
+}
+
+void Preferences::setAutoBanUnknownPeer(const bool checked)
+{
+ setValue("Preferences/Advanced/AutoBanUnknownPeer", checked);
+}
+
+bool Preferences::getShowTrackerAuthWindow() const
+{
+ return value("Preferences/Advanced/ShowTrackerAuthWindow", true).toBool();
+}
+
+void Preferences::setShowTrackerAuthWindow(const bool checked)
+{
+ setValue("Preferences/Advanced/ShowTrackerAuthWindow", checked);
+}
+
// Stuff that don't appear in the Options GUI but are saved
// in the same file.
--- a/src/base/preferences.h
+++ b/src/base/preferences.h
@@ -300,6 +300,10 @@ public:
TrayIcon::Style trayIconStyle() const;
void setTrayIconStyle(TrayIcon::Style style);
#endif // Q_OS_MAC
+ bool getAutoBanUnknownPeer() const;
+ void setAutoBanUnknownPeer(const bool checked);
+ bool getShowTrackerAuthWindow() const;
+ void setShowTrackerAuthWindow(const bool checked);
// Stuff that don't appear in the Options GUI but are saved
// in the same file.
--- a/src/base/settingsstorage.cpp
+++ b/src/base/settingsstorage.cpp
@@ -91,6 +91,8 @@ namespace
{"BitTorrent/Session/InterfaceName", "Preferences/Connection/InterfaceName"},
{"BitTorrent/Session/InterfaceAddress", "Preferences/Connection/InterfaceAddress"},
{"BitTorrent/Session/SaveResumeDataInterval", "Preferences/Downloads/SaveResumeDataInterval"},
+ {"BitTorrent/Session/AutoBanUnknownPeer", "Preferences/Advanced/AutoBanUnknownPeer"},
+ {"BitTorrent/Session/ShowTrackerAuthWindow", "Preferences/Advanced/ShowTrackerAuthWindow"},
{"BitTorrent/Session/Encryption", "Preferences/Bittorrent/Encryption"},
{"BitTorrent/Session/ForceProxy", "Preferences/Connection/ProxyForce"},
{"BitTorrent/Session/ProxyPeerConnections", "Preferences/Connection/ProxyPeerConnections"},
--- a/src/gui/advancedsettings.cpp
+++ b/src/gui/advancedsettings.cpp
@@ -60,6 +60,8 @@ enum AdvSettingsRows
NETWORK_LISTEN_IPV6,
// behavior
SAVE_RESUME_DATA_INTERVAL,
+ CONFIRM_AUTO_BAN,
+ SHOW_TRACKER_AUTH_WINDOW,
CONFIRM_RECHECK_TORRENT,
RECHECK_COMPLETED,
#if defined(Q_OS_WIN) || defined(Q_OS_MAC)
@@ -215,6 +217,10 @@ void AdvancedSettings::saveAdvancedSetti
// Announce IP
QHostAddress addr(lineEditAnnounceIP.text().trimmed());
session->setAnnounceIP(addr.isNull() ? "" : addr.toString());
+ // Auto ban Unknown Peer
+ session->setAutoBanUnknownPeer(cb_auto_ban_unknown_peer.isChecked());
+ // Show Tracker Authenticaion Window
+ session->setShowTrackerAuthWindow(cb_show_tracker_auth_window.isChecked());
// Program notification
MainWindow *const mainWindow = static_cast<Application*>(QCoreApplication::instance())->mainWindow();
@@ -465,6 +471,12 @@ void AdvancedSettings::loadAdvancedSetti
// Announce IP
lineEditAnnounceIP.setText(session->announceIP());
addRow(ANNOUNCE_IP, tr("IP Address to report to trackers (requires restart)"), &lineEditAnnounceIP);
+ // Auto Ban Unknown Peer from China
+ cb_auto_ban_unknown_peer.setChecked(session->isAutoBanUnknownPeerEnabled());
+ addRow(CONFIRM_AUTO_BAN, tr("Auto Ban Unknown Peer from China"), &cb_auto_ban_unknown_peer);
+ // Show Tracker Authenticaion Window
+ cb_show_tracker_auth_window.setChecked(session->isShowTrackerAuthWindow());
+ addRow(SHOW_TRACKER_AUTH_WINDOW, tr("Show Tracker Authenticaion Window"), &cb_show_tracker_auth_window);
// Program notifications
const MainWindow *const mainWindow = static_cast<Application*>(QCoreApplication::instance())->mainWindow();
--- a/src/gui/advancedsettings.h
+++ b/src/gui/advancedsettings.h
@@ -65,7 +65,8 @@ private:
QCheckBox checkBoxOsCache, checkBoxRecheckCompleted, checkBoxResolveCountries, checkBoxResolveHosts, checkBoxSuperSeeding,
checkBoxProgramNotifications, checkBoxTorrentAddedNotifications, checkBoxTrackerFavicon, checkBoxTrackerStatus,
checkBoxConfirmTorrentRecheck, checkBoxConfirmRemoveAllTags, checkBoxListenIPv6, checkBoxAnnounceAllTrackers, checkBoxAnnounceAllTiers,
- checkBoxGuidedReadCache, checkBoxMultiConnectionsPerIp, checkBoxSuggestMode, checkBoxCoalesceRW, checkBoxSpeedWidgetEnabled;
+ checkBoxGuidedReadCache, checkBoxMultiConnectionsPerIp, checkBoxSuggestMode, checkBoxCoalesceRW, checkBoxSpeedWidgetEnabled,
+ cb_auto_ban_unknown_peer, cb_show_tracker_auth_window;
QComboBox comboBoxInterface, comboBoxInterfaceAddress, comboBoxUtpMixedMode, comboBoxChokingAlgorithm, comboBoxSeedChokingAlgorithm;
QLineEdit lineEditAnnounceIP;
--- a/src/gui/mainwindow.cpp
+++ b/src/gui/mainwindow.cpp
@@ -73,6 +73,7 @@
#include "addnewtorrentdialog.h"
#include "application.h"
#include "autoexpandabledialog.h"
+#include "base/bittorrent/peerinfo.h"
#include "cookiesdialog.h"
#include "downloadfromurldialog.h"
#include "executionlogwidget.h"
--- a/src/gui/properties/peerlistdelegate.h
+++ b/src/gui/properties/peerlistdelegate.h
@@ -49,6 +49,7 @@ public:
CONNECTION,
FLAGS,
CLIENT,
+ PEERID,
PROGRESS,
DOWN_SPEED,
UP_SPEED,
--- a/src/gui/properties/peerlistwidget.cpp
+++ b/src/gui/properties/peerlistwidget.cpp
@@ -75,6 +75,7 @@ PeerListWidget::PeerListWidget(Propertie
m_listModel->setHeaderData(PeerListDelegate::FLAGS, Qt::Horizontal, tr("Flags"));
m_listModel->setHeaderData(PeerListDelegate::CONNECTION, Qt::Horizontal, tr("Connection"));
m_listModel->setHeaderData(PeerListDelegate::CLIENT, Qt::Horizontal, tr("Client", "i.e.: Client application"));
+ m_listModel->setHeaderData(PeerListDelegate::PEERID, Qt::Horizontal, tr("Peer ID", "i.e.: Client Peer ID"));
m_listModel->setHeaderData(PeerListDelegate::PROGRESS, Qt::Horizontal, tr("Progress", "i.e: % downloaded"));
m_listModel->setHeaderData(PeerListDelegate::DOWN_SPEED, Qt::Horizontal, tr("Down Speed", "i.e: Download speed"));
m_listModel->setHeaderData(PeerListDelegate::UP_SPEED, Qt::Horizontal, tr("Up Speed", "i.e: Upload speed"));
@@ -288,8 +289,13 @@ void PeerListWidget::banSelectedPeers()
for (const QModelIndex &index : selectedIndexes) {
int row = m_proxyModel->mapToSource(index).row();
QString ip = m_listModel->data(m_listModel->index(row, PeerListDelegate::IP_HIDDEN)).toString();
+ QString client = m_listModel->data(m_listModel->index(row, PeerListDelegate::CLIENT)).toString();
+ QString peerid = m_listModel->data(m_listModel->index(row, PeerListDelegate::PEERID)).toString();
+ QHostAddress host;
+ host.setAddress(ip);
+ const QString countryName = Net::GeoIPManager::CountryName(Net::GeoIPManager::instance()->lookup(host));
qDebug("Banning peer %s...", ip.toLocal8Bit().data());
- Logger::instance()->addMessage(tr("Manually banning peer '%1'...").arg(ip));
+ Logger::instance()->addMessage(tr("Manually banning peer '%1'...'%2'...'%3'...'%4'").arg(ip).arg(peerid).arg(client).arg(countryName));
BitTorrent::Session::instance()->banIP(ip);
}
// Refresh list
@@ -398,6 +404,7 @@ QStandardItem *PeerListWidget::addPeer(c
m_listModel->setData(m_listModel->index(row, PeerListDelegate::FLAGS), peer.flags());
m_listModel->setData(m_listModel->index(row, PeerListDelegate::FLAGS), peer.flagsDescription(), Qt::ToolTipRole);
m_listModel->setData(m_listModel->index(row, PeerListDelegate::CLIENT), peer.client().toHtmlEscaped());
+ m_listModel->setData(m_listModel->index(row, PeerListDelegate::PEERID), peer.pid().left(8).toHtmlEscaped());
m_listModel->setData(m_listModel->index(row, PeerListDelegate::PROGRESS), peer.progress());
m_listModel->setData(m_listModel->index(row, PeerListDelegate::DOWN_SPEED), peer.payloadDownSpeed());
m_listModel->setData(m_listModel->index(row, PeerListDelegate::UP_SPEED), peer.payloadUpSpeed());
@@ -429,6 +436,7 @@ void PeerListWidget::updatePeer(const QS
m_listModel->setData(m_listModel->index(row, PeerListDelegate::FLAGS), peer.flags());
m_listModel->setData(m_listModel->index(row, PeerListDelegate::FLAGS), peer.flagsDescription(), Qt::ToolTipRole);
m_listModel->setData(m_listModel->index(row, PeerListDelegate::CLIENT), peer.client().toHtmlEscaped());
+ m_listModel->setData(m_listModel->index(row, PeerListDelegate::PEERID), peer.pid().left(8).toHtmlEscaped());
m_listModel->setData(m_listModel->index(row, PeerListDelegate::PROGRESS), peer.progress());
m_listModel->setData(m_listModel->index(row, PeerListDelegate::DOWN_SPEED), peer.payloadDownSpeed());
m_listModel->setData(m_listModel->index(row, PeerListDelegate::UP_SPEED), peer.payloadUpSpeed());
--- a/src/webui/api/appcontroller.cpp
+++ b/src/webui/api/appcontroller.cpp
@@ -153,6 +153,7 @@ void AppController::preferencesAction()
data["ip_filter_path"] = Utils::Fs::toNativePath(session->IPFilterFile());
data["ip_filter_trackers"] = session->isTrackerFilteringEnabled();
data["banned_IPs"] = session->bannedIPs().join("\n");
+ data["auto_ban_unknown_peer"] = session->isAutoBanUnknownPeerEnabled();
// Speed
// Global Rate Limits
@@ -401,6 +402,8 @@ void AppController::setPreferencesAction
session->setTrackerFilteringEnabled(m["ip_filter_trackers"].toBool());
if (m.contains("banned_IPs"))
session->setBannedIPs(m["banned_IPs"].toString().split('\n'));
+ if (m.contains("auto_ban_unknown_peer"))
+ session->setAutoBanUnknownPeer(m["auto_ban_unknown_peer"].toBool());
// Speed
// Global Rate Limits
--- a/src/webui/api/transfercontroller.cpp
+++ b/src/webui/api/transfercontroller.cpp
@@ -30,6 +30,7 @@
#include <QJsonObject>
+#include "base/logger.h"
#include "base/bittorrent/session.h"
const char KEY_TRANSFER_DLSPEED[] = "dl_info_speed";
@@ -111,3 +112,37 @@ void TransferController::speedLimitsMode
{
setResult(QString::number(BitTorrent::Session::instance()->isAltGlobalSpeedLimitEnabled()));
}
+
+void TransferController::tempblockPeerAction()
+{
+ checkParams({"ip"});
+ QString ip = params()["ip"];
+ boost::system::error_code ec;
+ boost::asio::ip::address addr = boost::asio::ip::address::from_string(ip.toStdString(), ec);
+ bool isBanned = BitTorrent::Session::instance()->checkAccessFlags(QString::fromStdString(addr.to_string()));
+
+ if (ip.isEmpty()) {
+ setResult(QLatin1String("IP field should not be empty."));
+ return;
+ }
+
+ if (ec) {
+ setResult(QLatin1String("The given IP address is not valid."));
+ return;
+ }
+
+ if (isBanned) {
+ setResult(QLatin1String("The given IP address already exists."));
+ return;
+ }
+
+ BitTorrent::Session::instance()->tempblockIP(ip);
+ Logger::instance()->addMessage(tr("Peer '%1' banned via Web API.").arg(ip));
+ setResult(QLatin1String("Done."));
+}
+
+void TransferController::resetIPFilterAction()
+{
+ BitTorrent::Session::instance()->eraseIPFilter();
+ setResult(QLatin1String("Erased."));
+}
--- a/src/webui/api/transfercontroller.h
+++ b/src/webui/api/transfercontroller.h
@@ -46,4 +46,6 @@ private slots:
void downloadLimitAction();
void setUploadLimitAction();
void setDownloadLimitAction();
+ void tempblockPeerAction();
+ void resetIPFilterAction();
};
--- a/src/webui/www/private/preferences_content.html
+++ b/src/webui/www/private/preferences_content.html
@@ -377,6 +377,8 @@
<textarea id="banned_IPs_textarea" rows="5" cols="70"></textarea>
</fieldset>
</div>
+ <input type="checkbox" id="auto_ban_unknown_peer_checkbox" />
+ <label for="auto_ban_unknown_peer_checkbox">QBT_TR(Auto Ban Unknown Client From China)QBT_TR[CONTEXT=OptionsDialog]</label>
</fieldset>
</div>
@@ -1252,6 +1254,7 @@
$('ipfilter_text').setProperty('value', pref.ip_filter_path);
$('ipfilter_trackers_checkbox').setProperty('checked', pref.ip_filter_trackers);
$('banned_IPs_textarea').setProperty('value', pref.banned_IPs);
+ $('auto_ban_unknown_peer_checkbox').setProperty('checked', pref.auto_ban_unknown_peer);
updateFilterSettings();
// Speed tab
@@ -1502,6 +1505,7 @@
settings.set('ip_filter_path', $('ipfilter_text').getProperty('value'));
settings.set('ip_filter_trackers', $('ipfilter_trackers_checkbox').getProperty('checked'));
settings.set('banned_IPs', $('banned_IPs_textarea').getProperty('value'));
+ settings.set('auto_ban_unknown_peer', $('auto_ban_unknown_peer_checkbox').getProperty('checked'));
// Speed tab
// Global Rate Limits

View File

@ -1,136 +1,177 @@
#
# Copyright (C) 2013 Riccardo Ferrazzo <f.riccardo87@gmail.com>
# Copyright (C) 2017 Paweł Knioła <pawel.kn@gmail.com>
# Copyright (C) 2017-2019 Entware
#
# This is free software, licensed under the GNU General Public License v2.
# See /LICENSE for more information.
#
# ported to Entware from
# https://github.com/KryptonLee/qBittorrent-openwrt-package and
# https://github.com/pawelkn/qt5-openwrt-package
include $(TOPDIR)/rules.mk
PKG_NAME:=qt5
PKG_VERSION:=5.13
PKG_VERSION:=5.9.8
PKG_RELEASE:=1
PKG_MD5SUM:=d66b1da335d0c25325fdf493e9044c38
PKG_SOURCE:=qt-everywhere-src-$(PKG_VERSION).$(PKG_RELEASE).tar.xz
PKG_SOURCE_URL:=http://download.qt-project.org/archive/qt/$(PKG_VERSION)/$(PKG_VERSION).$(PKG_RELEASE)/single
PKG_BUILD_DIR=$(BUILD_DIR)/qt-everywhere-src-$(PKG_VERSION).$(PKG_RELEASE)
PKG_SOURCE:=qt-everywhere-opensource-src-$(PKG_VERSION).tar.xz
PKG_SOURCE_URL:=http://download.qt-project.org/archive/qt/5.9/$(PKG_VERSION)/single
PKG_HASH:=86aca7dc37f161fc730a9d4f6bddf684962ca560327682e282ff61bf8b859c36
PKG_BUILD_PARALLEL:=1
PKG_USE_MIPS16:=0
PKG_BUILD_DIR=$(BUILD_DIR)/qt-everywhere-opensource-src-$(PKG_VERSION)
include $(INCLUDE_DIR)/package.mk
ifndef CONFIG_USE_GLIBC
# not using sstrip here as this fucks up the .so's somehow
STRIP:=/bin/true
RSTRIP:= \
NM="$(TOOLCHAIN_DIR)/bin/$(TARGET_CROSS)nm" \
STRIP="$(STRIP)" \
STRIP_KMOD="$(STRIP)" \
$(SCRIPT_DIR)/rstrip.sh
NM="$(TOOLCHAIN_DIR)/bin/$(TARGET_CROSS)nm" \
STRIP="$(STRIP)" \
STRIP_KMOD="$(STRIP)" \
$(SCRIPT_DIR)/rstrip.sh
endif
define Package/qt5/Default
SECTION:=libs
CATEGORY:=Libraries
SUBMENU:=Qt5
TITLE:=qt5
URL:=http://qt-project.org
DEPENDS:=+libatomic +libstdcpp +libopenssl +zlib +icu @!LINUX_2_6
SECTION:=libs
CATEGORY:=Libraries
SUBMENU:=Qt5
TITLE:=qt5
URL:=http://qt-project.org
DEPENDS:=+librt +libstdcpp +libpthread @!LINUX_2_6_36
endef
define Package/qt5-core
$(call Package/qt5/Default)
TITLE+=core
endef
define Package/qt5-concurrent
$(call Package/qt5/Default)
TITLE+=concurrent
DEPENDS+=+qt5-core
$(call Package/qt5/Default)
TITLE+=core
DEPENDS+=+libatomic +zlib +libpcre2-16 +libdouble-conversion
endef
define Package/qt5-network
$(call Package/qt5/Default)
TITLE+=network
DEPENDS+=+qt5-core
endef
define Package/qt5-widgets
$(call Package/qt5/Default)
TITLE+=widgets
DEPENDS+=+qt5-core +qt5-network
endef
define Package/qt5-sql
$(call Package/qt5/Default)
TITLE+=sql
DEPENDS+=+qt5-core +libmariadbclient
$(call Package/qt5/Default)
TITLE+=network
DEPENDS+=+qt5-core +libopenssl
endef
define Package/qt5-xml
$(call Package/qt5/Default)
TITLE+=xml
DEPENDS+=+qt5-core
$(call Package/qt5/Default)
TITLE+=xml
DEPENDS+=+qt5-core
endef
define Package/qt5-serialport
$(call Package/qt5/Default)
TITLE+=serialport
DEPENDS+=+qt5-core
endef
define Package/qt5-xmlpatterns
$(call Package/qt5/Default)
TITLE+=xmlpatterns
DEPENDS+=+qt5-core +qt5-network
endef
define Package/qt5-test
$(call Package/qt5/Default)
TITLE+=test
DEPENDS+=+qt5-core
endef
CONFIGURE_ARGS = \
-prefix /usr \
-sysroot $(STAGING_DIR) \
-plugindir /usr/lib/Qt/plugins \
-R /usr/lib \
-I $(STAGING_DIR)/usr/include \
-L $(STAGING_DIR)/usr/lib \
-xplatform linux-openwrt-g++ \
-release \
-shared \
-opensource \
-confirm-license \
-no-use-gold-linker \
-strip \
-ltcg \
-optimized-qmake \
-system-doubleconversion \
-no-glib \
-no-icu \
-system-pcre \
-system-zlib \
-no-slog2 \
-openssl-linked \
-no-cups \
-no-freetype \
-no-harfbuzz \
-no-gtk \
-no-opengl \
-no-opengles3 \
-no-angle \
-no-openvg \
-no-directfb \
-no-eglfs \
-no-egl \
-no-iconv \
-no-gbm \
-no-kms \
-no-xcb \
-no-pch \
-no-libudev \
-no-mtdev \
-no-tslib \
-no-xkbcommon-evdev \
-no-libpng \
-no-libjpeg \
-no-sql-db2 \
-no-sql-ibase \
-no-sql-mysql \
-no-sql-oci \
-no-sql-odbc \
-no-sql-psql \
-no-sql-sqlite \
-no-sql-sqlite2 \
-no-sqlite \
-no-sql-tds \
-no-gui \
-no-widgets \
-no-dbus \
-no-qml-debug \
-make libs \
-nomake examples \
-nomake tests \
-nomake tools \
-no-compile-examples \
-skip qt3d \
-skip qtactiveqt \
-skip qtandroidextras \
-skip qtcanvas3d \
-skip qtcharts \
-skip qtconnectivity \
-skip qtdatavis3d \
-skip qtdeclarative \
-skip qtdoc \
-skip qtgamepad \
-skip qtgraphicaleffects \
-skip qtimageformats \
-skip qtlocation \
-skip qtmacextras \
-skip qtmultimedia \
-skip qtnetworkauth \
-skip qtpurchasing \
-skip qtquickcontrols \
-skip qtquickcontrols2 \
-skip qtremoteobjects \
-skip qtscript \
-skip qtscxml \
-skip qtsensors \
-skip qtserialbus \
-skip qtserialport \
-skip qtspeech \
-skip qtsvg \
-skip qttranslations \
-skip qtvirtualkeyboard \
-skip qtwayland \
-skip qtwebchannel \
-skip qtwebengine \
-skip qtwebsockets \
-skip qtwebview \
-skip qtwinextras \
-skip qtx11extras \
-skip qtxmlpatterns \
-v
define Build/Configure
$(INSTALL_DIR) $(PKG_BUILD_DIR)/qtbase/mkspecs/linux-openwrt-g++
$(CP) ./files/qplatformdefs.h $(PKG_BUILD_DIR)/qtbase/mkspecs/linux-openwrt-g++/qplatformdefs.h
$(CP) ./files/qmake.conf $(PKG_BUILD_DIR)/qtbase/mkspecs/linux-openwrt-g++/qmake.conf
$(SED) 's@$$$$(TARGET_CROSS)@$(TARGET_CROSS)@g' $(PKG_BUILD_DIR)/qtbase/mkspecs/linux-openwrt-g++/qmake.conf
( cd $(PKG_BUILD_DIR) ; \
./configure \
-prefix $(TOOLCHAIN_DIR) \
-xplatform linux-openwrt-g++ \
-opensource \
-confirm-license \
-no-iconv \
-no-pch \
-no-rpath \
-no-strip \
-no-cups \
-no-dbus \
-no-eglfs \
-no-kms \
-no-opengl \
-no-directfb \
-no-xcb \
-openssl-runtime \
-qt-zlib \
-qt-pcre \
-qt-freetype \
-make libs \
-nomake examples \
-nomake tools \
-nomake tests \
-skip qtdeclarative \
-skip qtmultimedia \
-skip activeqt \
-skip qtdoc \
-skip qtconnectivity \
-skip wayland \
-skip qtscript \
-v \
)
$(SED) 's@$$$$(TARGET_CFLAGS)@$(TARGET_CFLAGS)@g' $(PKG_BUILD_DIR)/qtbase/mkspecs/linux-openwrt-g++/qmake.conf
$(SED) 's@$$$$(TARGET_CXXFLAGS)@$(TARGET_CXXFLAGS)@g' $(PKG_BUILD_DIR)/qtbase/mkspecs/linux-openwrt-g++/qmake.conf
$(SED) 's@$$$$(TARGET_LDFLAGS)@$(TARGET_LDFLAGS)@g' $(PKG_BUILD_DIR)/qtbase/mkspecs/linux-openwrt-g++/qmake.conf
$(call Build/Configure/Default)
endef
define Build/Compile
@ -139,95 +180,25 @@ endef
define Build/InstallDev
$(MAKE) -C $(PKG_BUILD_DIR) install
$(CP) $(PKG_BUILD_DIR)/qtbase/bin/qmake $(TOOLCHAIN_DIR)/bin/
$(CP) $(PKG_BUILD_DIR)/qtbase/bin/qt.conf $(TOOLCHAIN_DIR)/bin/
$(INSTALL_CONF) $(PKG_BUILD_DIR)/qtbase/bin/qt.conf $(STAGING_DIR)/usr/bin
$(RM) $(STAGING_DIR)/usr/bin/qt{attributionsscanner,paths,plugininfo}
endef
define Package/qt5-core/install
$(INSTALL_DIR) $(1)/usr/lib/
$(CP) $(PKG_BUILD_DIR)/qtbase/lib/libQt5Core.so* $(1)/usr/lib/
$(CP) $(PKG_BUILD_DIR)/qtbase/lib/libQt5Core.prl $(1)/usr/lib/
$(CP) $(PKG_BUILD_DIR)/qtbase/lib/libQt5Core.la $(1)/usr/lib/
endef
define Package/qt5-concurrent/install
$(INSTALL_DIR) $(1)/usr/lib/
$(CP) $(PKG_BUILD_DIR)/qtbase/lib/libQt5Concurrent.so* $(1)/usr/lib/
$(CP) $(PKG_BUILD_DIR)/qtbase/lib/libQt5Concurrent.prl $(1)/usr/lib/
$(CP) $(PKG_BUILD_DIR)/qtbase/lib/libQt5Concurrent.la $(1)/usr/lib/
$(INSTALL_DIR) $(1)/usr/lib
$(CP) $(PKG_BUILD_DIR)/qtbase/lib/libQt5Core.so* $(1)/usr/lib
endef
define Package/qt5-network/install
$(INSTALL_DIR) $(1)/usr/lib/
$(CP) $(PKG_BUILD_DIR)/qtbase/lib/libQt5Network.so* $(1)/usr/lib/
$(CP) $(PKG_BUILD_DIR)/qtbase/lib/libQt5Network.prl $(1)/usr/lib/
$(CP) $(PKG_BUILD_DIR)/qtbase/lib/libQt5Network.la $(1)/usr/lib/
endef
define Package/qt5-widgets/install
$(INSTALL_DIR) $(1)/usr/lib/
$(INSTALL_DIR) $(1)/usr/lib/Qt/plugins/generic/
$(INSTALL_DIR) $(1)/usr/lib/Qt/plugins/platforms/
$(INSTALL_DIR) $(1)/usr/lib/Qt/plugins/imageformats/
$(INSTALL_DIR) $(1)/usr/lib/fonts/
$(CP) $(PKG_BUILD_DIR)/qtbase/lib/libQt5Gui.so* $(1)/usr/lib/
$(CP) $(PKG_BUILD_DIR)/qtbase/lib/libQt5Gui.prl $(1)/usr/lib/
$(CP) $(PKG_BUILD_DIR)/qtbase/lib/libQt5Gui.la $(1)/usr/lib/
$(CP) $(PKG_BUILD_DIR)/qtsvg/lib/libQt5Svg.so* $(1)/usr/lib/
$(CP) $(PKG_BUILD_DIR)/qtsvg/lib/libQt5Svg.prl $(1)/usr/lib/
$(CP) $(PKG_BUILD_DIR)/qtsvg/lib/libQt5Svg.la $(1)/usr/lib/
$(CP) $(PKG_BUILD_DIR)/qtbase/lib/libQt5Widgets.so* $(1)/usr/lib/
$(CP) $(PKG_BUILD_DIR)/qtbase/lib/libQt5Widgets.prl $(1)/usr/lib/
$(CP) $(PKG_BUILD_DIR)/qtbase/lib/libQt5Widgets.la $(1)/usr/lib/
$(CP) $(PKG_BUILD_DIR)/qtbase/plugins/generic/*.so $(1)/usr/lib/Qt/plugins/generic/
$(CP) $(PKG_BUILD_DIR)/qtbase/plugins/platforms/*.so $(1)/usr/lib/Qt/plugins/platforms/
$(CP) $(PKG_BUILD_DIR)/qtbase/plugins/imageformats/*.so $(1)/usr/lib/Qt/plugins/imageformats/
$(CP) $(PKG_BUILD_DIR)/qtbase/lib/fonts/* $(1)/usr/lib/fonts/
endef
define Package/qt5-sql/install
$(INSTALL_DIR) $(1)/usr/lib/
$(INSTALL_DIR) $(1)/usr/lib/Qt/plugins/sqldrivers/
$(CP) $(PKG_BUILD_DIR)/qtbase/lib/libQt5Sql.so* $(1)/usr/lib/
$(CP) $(PKG_BUILD_DIR)/qtbase/lib/libQt5Sql.prl $(1)/usr/lib/
$(CP) $(PKG_BUILD_DIR)/qtbase/lib/libQt5Sql.la $(1)/usr/lib/
$(CP) $(PKG_BUILD_DIR)/qtbase/plugins/sqldrivers/*.so $(1)/usr/lib/Qt/plugins/sqldrivers/
$(INSTALL_DIR) $(1)/usr/lib
$(CP) $(PKG_BUILD_DIR)/qtbase/lib/libQt5Network.so* $(1)/usr/lib
endef
define Package/qt5-xml/install
$(INSTALL_DIR) $(1)/usr/lib/
$(CP) $(PKG_BUILD_DIR)/qtbase/lib/libQt5Xml.so* $(1)/usr/lib/
$(CP) $(PKG_BUILD_DIR)/qtbase/lib/libQt5Xml.prl $(1)/usr/lib/
$(CP) $(PKG_BUILD_DIR)/qtbase/lib/libQt5Xml.la $(1)/usr/lib/
$(INSTALL_DIR) $(1)/usr/lib
$(CP) $(PKG_BUILD_DIR)/qtbase/lib/libQt5Xml.so* $(1)/usr/lib
endef
define Package/qt5-serialport/install
$(INSTALL_DIR) $(1)/usr/lib/
$(CP) $(PKG_BUILD_DIR)/qtserialport/lib/libQt5SerialPort.so* $(1)/usr/lib/
$(CP) $(PKG_BUILD_DIR)/qtserialport/lib/libQt5SerialPort.prl $(1)/usr/lib/
$(CP) $(PKG_BUILD_DIR)/qtserialport/lib/libQt5SerialPort.la $(1)/usr/lib/
endef
define Package/qt5-xmlpatterns/install
$(INSTALL_DIR) $(1)/usr/lib/
$(CP) $(PKG_BUILD_DIR)/qtxmlpatterns/lib/libQt5XmlPatterns.so* $(1)/usr/lib/
$(CP) $(PKG_BUILD_DIR)/qtxmlpatterns/lib/libQt5XmlPatterns.prl $(1)/usr/lib/
$(CP) $(PKG_BUILD_DIR)/qtxmlpatterns/lib/libQt5XmlPatterns.la $(1)/usr/lib/
endef
define Package/qt5-test/install
$(INSTALL_DIR) $(1)/usr/lib/
$(CP) $(PKG_BUILD_DIR)/qtbase/lib/libQt5Test.so* $(1)/usr/lib/
$(CP) $(PKG_BUILD_DIR)/qtbase/lib/libQt5Test.prl $(1)/usr/lib/
$(CP) $(PKG_BUILD_DIR)/qtbase/lib/libQt5Test.la $(1)/usr/lib/
endef
$(eval $(call BuildPackage,qt5-core))
$(eval $(call BuildPackage,qt5-concurrent))
$(eval $(call BuildPackage,qt5-core,+zlib,+libpcre2-16,+libdouble-conversion))
$(eval $(call BuildPackage,qt5-network))
$(eval $(call BuildPackage,qt5-widgets))
$(eval $(call BuildPackage,qt5-sql))
$(eval $(call BuildPackage,qt5-xml))
$(eval $(call BuildPackage,qt5-serialport))
$(eval $(call BuildPackage,qt5-xmlpatterns))
$(eval $(call BuildPackage,qt5-test))

View File

@ -1,40 +0,0 @@
/****************************************************************************
**
** Copyright (C) 2016 The Qt Company Ltd.
** Contact: https://www.qt.io/licensing/
**
** This file is part of the qmake spec of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:LGPL$
** Commercial License Usage
** Licensees holding valid commercial Qt licenses may use this file in
** accordance with the commercial license agreement provided with the
** Software or, alternatively, in accordance with the terms contained in
** a written agreement between you and The Qt Company. For licensing terms
** and conditions see https://www.qt.io/terms-conditions. For further
** information use the contact form at https://www.qt.io/contact-us.
**
** GNU Lesser General Public License Usage
** Alternatively, this file may be used under the terms of the GNU Lesser
** General Public License version 3 as published by the Free Software
** Foundation and appearing in the file LICENSE.LGPL3 included in the
** packaging of this file. Please review the following information to
** ensure the GNU Lesser General Public License version 3 requirements
** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
**
** GNU General Public License Usage
** Alternatively, this file may be used under the terms of the GNU
** General Public License version 2.0 or (at your option) the GNU General
** Public license version 3 or any later version approved by the KDE Free
** Qt Foundation. The licenses are as published by the Free Software
** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
** included in the packaging of this file. Please review the following
** information to ensure the GNU General Public License requirements will
** be met: https://www.gnu.org/licenses/gpl-2.0.html and
** https://www.gnu.org/licenses/gpl-3.0.html.
**
** $QT_END_LICENSE$
**
****************************************************************************/
#include "../linux-g++/qplatformdefs.h"

View File

@ -0,0 +1,74 @@
--- a/qtserialbus/src/plugins/canbus/socketcan/socketcanbackend.cpp
+++ b/qtserialbus/src/plugins/canbus/socketcan/socketcanbackend.cpp
@@ -33,7 +33,6 @@
** $QT_END_LICENSE$
**
****************************************************************************/
-
#include "socketcanbackend.h"
#include <QtCore/qdatastream.h>
@@ -50,29 +49,7 @@
#include <sys/ioctl.h>
#include <sys/time.h>
-#ifndef CANFD_MTU
-// CAN FD support was added by Linux kernel 3.6
-// For prior kernels we redefine the missing defines here
-// they are taken from linux/can/raw.h & linux/can.h
-
-enum {
- CAN_RAW_FD_FRAMES = 5
-};
-
-#define CAN_MAX_DLEN 8
-#define CANFD_MAX_DLEN 64
-struct canfd_frame {
- canid_t can_id; /* 32 bit CAN_ID + EFF/RTR/ERR flags */
- __u8 len; /* frame payload length in byte */
- __u8 flags; /* additional flags for CAN FD */
- __u8 __res0; /* reserved / padding */
- __u8 __res1; /* reserved / padding */
- __u8 data[CANFD_MAX_DLEN] __attribute__((aligned(8)));
-};
-#define CAN_MTU (sizeof(struct can_frame))
-#define CANFD_MTU (sizeof(struct canfd_frame))
-#endif
#ifndef CANFD_BRS
# define CANFD_BRS 0x01 /* bit rate switch (second bitrate for payload data) */
--- a/qtserialbus/src/plugins/canbus/socketcan/socketcanbackend.h
+++ b/qtserialbus/src/plugins/canbus/socketcan/socketcanbackend.h
@@ -45,6 +45,31 @@
#include <QtCore/qstring.h>
#include <QtCore/qvariant.h>
+#ifndef CANFD_MTU
+// CAN FD support was added by Linux kernel 3.6
+// For prior kernels we redefine the missing defines here
+// they are taken from linux/can/raw.h & linux/can.h
+
+enum {
+ CAN_RAW_FD_FRAMES = 5
+};
+
+#define CAN_MAX_DLEN 8
+#define CANFD_MAX_DLEN 64
+struct canfd_frame {
+ canid_t can_id; /* 32 bit CAN_ID + EFF/RTR/ERR flags */
+ __u8 len; /* frame payload length in byte */
+ __u8 flags; /* additional flags for CAN FD */
+ __u8 __res0; /* reserved / padding */
+ __u8 __res1; /* reserved / padding */
+ __u8 data[CANFD_MAX_DLEN] __attribute__((aligned(8)));
+};
+#define CAN_MTU (sizeof(struct can_frame))
+#define CANFD_MTU (sizeof(struct canfd_frame))
+
+#endif
+
+
QT_BEGIN_NAMESPACE
class SocketCanBackend : public QCanBusDevice

View File

@ -0,0 +1,91 @@
This patch disables prinstsupport, sql, concurrent, testlib base libs compilation
--- a/qtbase/src/src.pro
+++ b/qtbase/src/src.pro
@@ -66,22 +66,10 @@ src_dbus.target = sub-dbus
src_dbus.depends = src_corelib
force_dbus_bootstrap: src_dbus.depends += src_tools_bootstrap_dbus # avoid syncqt race
-src_concurrent.subdir = $$PWD/concurrent
-src_concurrent.target = sub-concurrent
-src_concurrent.depends = src_corelib
-
-src_sql.subdir = $$PWD/sql
-src_sql.target = sub-sql
-src_sql.depends = src_corelib
-
src_network.subdir = $$PWD/network
src_network.target = sub-network
src_network.depends = src_corelib
-src_testlib.subdir = $$PWD/testlib
-src_testlib.target = sub-testlib
-src_testlib.depends = src_corelib # testlib links only to corelib, but see below for the headers
-
src_3rdparty_pcre2.subdir = $$PWD/3rdparty/pcre2
src_3rdparty_pcre2.target = sub-3rdparty-pcre2
@@ -125,13 +113,6 @@ src_openglextensions.subdir = $$PWD/open
src_openglextensions.target = sub-openglextensions
src_openglextensions.depends = src_gui
-src_printsupport.subdir = $$PWD/printsupport
-src_printsupport.target = sub-printsupport
-src_printsupport.depends = src_corelib src_gui src_widgets src_tools_uic
-
-src_plugins.subdir = $$PWD/plugins
-src_plugins.target = sub-plugins
-
src_android.subdir = $$PWD/android
# this order is important
@@ -152,14 +133,8 @@ TOOLS = src_tools_moc src_tools_rcc src_
win32:SUBDIRS += src_winmain
qtConfig(network) {
SUBDIRS += src_network
- src_plugins.depends += src_network
-}
-qtConfig(sql) {
- SUBDIRS += src_sql
- src_plugins.depends += src_sql
}
qtConfig(xml): SUBDIRS += src_xml
-qtConfig(testlib): SUBDIRS += src_testlib
qtConfig(dbus) {
force_dbus_bootstrap|qtConfig(private_tests): \
SUBDIRS += src_tools_bootstrap_dbus
@@ -167,9 +142,7 @@ qtConfig(dbus) {
TOOLS += src_tools_qdbusxml2cpp src_tools_qdbuscpp2xml
qtConfig(accessibility-atspi-bridge): \
src_platformsupport.depends += src_dbus src_tools_qdbusxml2cpp
- src_plugins.depends += src_dbus src_tools_qdbusxml2cpp src_tools_qdbuscpp2xml
}
-qtConfig(concurrent): SUBDIRS += src_concurrent
qtConfig(gui) {
qtConfig(harfbuzz):!qtConfig(system-harfbuzz) {
SUBDIRS += src_3rdparty_harfbuzzng
@@ -190,24 +163,17 @@ qtConfig(gui) {
}
SUBDIRS += src_gui src_platformsupport src_platformheaders
qtConfig(opengl): SUBDIRS += src_openglextensions
- src_plugins.depends += src_gui src_platformsupport src_platformheaders
- src_testlib.depends += src_gui # if QtGui is enabled, QtTest requires QtGui's headers
qtConfig(widgets) {
SUBDIRS += src_tools_uic src_widgets
!android-embedded: SUBDIRS += src_printsupport
TOOLS += src_tools_uic
- src_plugins.depends += src_widgets
- !android-embedded: src_plugins.depends += src_printsupport
- src_testlib.depends += src_widgets # if QtWidgets is enabled, QtTest requires QtWidgets's headers
qtConfig(opengl) {
SUBDIRS += src_opengl
- src_plugins.depends += src_opengl
}
}
}
-SUBDIRS += src_plugins
-nacl: SUBDIRS -= src_network src_testlib
+nacl: SUBDIRS -= src_network
android:!android-embedded: SUBDIRS += src_android src_3rdparty_gradle

File diff suppressed because it is too large Load Diff

View File

@ -14,20 +14,18 @@ include(../common/g++-unix.conf)
QMAKE_CC = $(TARGET_CROSS)gcc
QMAKE_CXX = $(TARGET_CROSS)g++
QMAKE_CFLAGS += $$(TARGET_CFLAGS)
QMAKE_CXXFLAGS += $$(TARGET_CXXFLAGS)
QMAKE_LFLAGS += $$(TARGET_LDFLAGS)
QMAKE_CFLAGS += $(TARGET_CFLAGS)
QMAKE_CXXFLAGS += $(TARGET_CXXFLAGS)
QMAKE_LFLAGS += $(TARGET_LDFLAGS)
QMAKE_LINK_C = $$QMAKE_CC
QMAKE_LINK_C_SHLIB = $$QMAKE_CC
QMAKE_LINK = $$QMAKE_CXX
QMAKE_LINK_SHLIB = $$QMAKE_CXX
QMAKE_LINK_C = $(TARGET_CROSS)gcc
QMAKE_LINK_C_SHLIB = $(TARGET_CROSS)gcc
QMAKE_LINK = $(TARGET_CROSS)g++
QMAKE_LINK_SHLIB = $(TARGET_CROSS)g++
# modifications to linux.conf
QMAKE_AR = $(TARGET_CROSS)ar cqs
QMAKE_OBJCOPY = $(TARGET_CROSS)objcopy
QMAKE_NM = $(TARGET_CROSS)nm -P
QMAKE_STRIP = $(TARGET_CROSS)strip
load(qt_config)

View File

@ -0,0 +1,9 @@
#include "../linux-g++/qplatformdefs.h"
#undef QT_SOCKLEN_T
#if defined(__GLIBC__) && (__GLIBC__ < 2)
#define QT_SOCKLEN_T int
#else
#define QT_SOCKLEN_T socklen_t
#endif

View File

@ -0,0 +1,48 @@
#
# Copyright (C) 2014 OpenWrt-dist
#
# This is free software, licensed under the GNU General Public License v2.
# See /LICENSE for more information.
#
include $(TOPDIR)/rules.mk
PKG_NAME:=ipt2socks
PKG_VERSION:=1.0.1
PKG_RELEASE:=2
PKG_SOURCE_PROTO:=git
PKG_SOURCE_URL:=https://github.com/zfl9/ipt2socks.git
PKG_SOURCE_VERSION:=b9bd7d888f2f95a6d7306030c8a5e252732dc451
PKG_SOURCE_SUBDIR:=$(PKG_NAME)-$(PKG_VERSION)-$(PKG_SOURCE_VERSION)
PKG_SOURCE:=$(PKG_NAME)-$(PKG_VERSION)-$(PKG_SOURCE_VERSION).tar.gz
PKG_BUILD_DIR:=$(BUILD_DIR)/$(PKG_NAME)/$(PKG_NAME)-$(PKG_VERSION)-$(PKG_SOURCE_VERSION)
include $(INCLUDE_DIR)/package.mk
define Package/ipt2socks
SECTION:=net
CATEGORY:=Network
TITLE:=Utility for converting iptables (REDIRECT/TPROXY) to SOCKS5
URL:=https://github.com/zfl9/ipt2socks
DEPENDS:=+libuv
endef
define Package/ipt2socks/description
Utility for converting iptables (REDIRECT/TPROXY) to SOCKS5.
endef
define Package/ipt2socks/conffiles
/etc/config/ipt2socks
endef
#MAKE_FLAGS += INCLUDES="-I$(STAGING_DIR)/usr/include"
#MAKE_FLAGS += LDFLAGS="-L$(STAGING_DIR)/usr/lib"
MAKE_FLAGS += LIBS="-l:libuv_a.a"
define Package/ipt2socks/install
$(INSTALL_DIR) $(1)/usr/bin
$(INSTALL_BIN) $(PKG_BUILD_DIR)/ipt2socks $(1)/usr/bin
endef
$(eval $(call BuildPackage,ipt2socks))

View File

@ -0,0 +1,66 @@
#
# Copyright (C) 2018-2019 wongsyrone
#
# This is free software, licensed under the GNU General Public License v3.
# See /LICENSE for more information.
#
include $(TOPDIR)/rules.mk
PKG_NAME:=trojan
PKG_VERSION:=1.13.0
PKG_RELEASE:=2
PKG_SOURCE_PROTO:=git
PKG_SOURCE_URL:=https://github.com/trojan-gfw/trojan.git
PKG_SOURCE_SUBDIR:=$(PKG_NAME)-$(PKG_VERSION)
PKG_SOURCE_VERSION:=98533aa1003979862763f4225266de78581e40bc
PKG_SOURCE:=$(PKG_NAME)-$(PKG_VERSION)-$(PKG_SOURCE_VERSION).tar.gz
CMAKE_INSTALL:=1
PKG_BUILD_PARALLEL:=0
PKG_BUILD_DEPENDS:=openssl
PKG_LICENSE:=GPL-3.0
PKG_MAINTAINER:=GreaterFire
include $(INCLUDE_DIR)/package.mk
include $(INCLUDE_DIR)/cmake.mk
TARGET_CXXFLAGS += -Wall -Wextra
TARGET_CXXFLAGS += $(FPIC)
# LTO
TARGET_CXXFLAGS += -flto
TARGET_LDFLAGS += -flto
# CXX standard
TARGET_CXXFLAGS += -std=c++11
TARGET_CXXFLAGS := $(filter-out -O%,$(TARGET_CXXFLAGS)) -O3
TARGET_CXXFLAGS += -ffunction-sections -fdata-sections
TARGET_LDFLAGS += -Wl,--gc-sections
CMAKE_OPTIONS += \
-DENABLE_MYSQL=OFF \
-DENABLE_SSL_KEYLOG=ON \
-DENABLE_NAT=ON \
-DFORCE_TCP_FASTOPEN=OFF \
-DSYSTEMD_SERVICE=OFF \
-DOPENSSL_USE_STATIC_LIBS=FALSE \
-DBoost_DEBUG=OFF \
-DBoost_NO_BOOST_CMAKE=ON
define Package/trojan
SECTION:=net
CATEGORY:=Network
TITLE:=An unidentifiable mechanism that helps you bypass GFW
URL:=https://github.com/trojan-gfw/trojan
DEPENDS:=+libpthread +libstdcpp +libopenssl \
+boost +boost-system +boost-program_options +boost-date_time
endef
define Package/trojan/install
$(INSTALL_DIR) $(1)/usr/sbin
$(INSTALL_BIN) $(PKG_INSTALL_DIR)/usr/bin/trojan $(1)/usr/sbin/trojan
endef
$(eval $(call BuildPackage,trojan))

View File

@ -0,0 +1,11 @@
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -43,7 +43,7 @@ if(MSVC)
add_definitions(-DBOOST_DATE_TIME_NO_LIB)
endif()
-find_package(OpenSSL 1.0.2 REQUIRED)
+find_package(OpenSSL 1.1.1 REQUIRED)
include_directories(${OPENSSL_INCLUDE_DIR})
target_link_libraries(trojan ${OPENSSL_LIBRARIES})
if(OPENSSL_VERSION VERSION_GREATER_EQUAL 1.1.1)