mirror of
https://github.com/kenzok8/small-package.git
synced 2026-02-04 22:09:05 +08:00
update 2023-01-26 15:46:00
This commit is contained in:
83
UnblockNeteaseMusic-Go/Makefile
Normal file
83
UnblockNeteaseMusic-Go/Makefile
Normal file
@@ -0,0 +1,83 @@
|
||||
# SPDX-Identifier-License: GPL-3.0-only
|
||||
#
|
||||
# Copyright (C) 2021 ImmortalWrt.org
|
||||
|
||||
include $(TOPDIR)/rules.mk
|
||||
|
||||
PKG_NAME:=UnblockNeteaseMusic-Go
|
||||
PKG_VERSION:=0.2.13
|
||||
PKG_RELEASE:=$(AUTORELEASE)
|
||||
|
||||
PKG_SOURCE:=$(PKG_NAME)-$(PKG_VERSION).tar.gz
|
||||
PKG_SOURCE_URL:=https://codeload.github.com/cnsilvan/UnblockNeteaseMusic/tar.gz/$(PKG_VERSION)?
|
||||
PKG_HASH:=92201b7f04ab1015c806c672b98a29b97d0f137d9b60e6d35d279c2064ed86a4
|
||||
|
||||
PKG_LICENSE:=GPL-3.0
|
||||
PKG_LICENSE_FILE:=LICENSE
|
||||
PKG_MAINTAINER:=Tianling Shen <cnsztl@immortalwrt.org>
|
||||
|
||||
PKG_CONFIG_DEPENDS:= \
|
||||
CONFIG_UNBLOCKNETEASEMUSIC_GO_COMPRESS_GOPROXY \
|
||||
CONFIG_UNBLOCKNETEASEMUSIC_GO_COMPRESS_UPX
|
||||
|
||||
PKG_BUILD_DIR:=$(BUILD_DIR)/$(firstword $(subst -, ,$(PKG_NAME)))-$(PKG_VERSION)
|
||||
PKG_BUILD_DEPENDS:=golang/host upx/host
|
||||
PKG_BUILD_PARALLEL:=1
|
||||
PKG_USE_MIPS16:=0
|
||||
|
||||
GO_PKG:=github.com/cnsilvan/UnblockNeteaseMusic
|
||||
GO_PKG_BUILD_PKG:=$$(GO_PKG)
|
||||
GO_PKG_LDFLAGS:=-s -w
|
||||
COMPILE_TIME:= $(shell TZ=UTC-8 date '+%Y-%m-%d %H:%M:%S')
|
||||
GO_PKG_LDFLAGS+= \
|
||||
-X '$(GO_PKG)/version.Version=$(PKG_VERSION)' \
|
||||
-X '$(GO_PKG)/version.BuildTime=$(COMPILE_TIME)' \
|
||||
-X '$(GO_PKG)/version.ExGoVersionInfo=$(GO_ARM) $(GO_MIPS)$(GO_MIPS64)'
|
||||
|
||||
include $(INCLUDE_DIR)/package.mk
|
||||
include $(TOPDIR)/feeds/packages/lang/golang/golang-package.mk
|
||||
|
||||
define Package/UnblockNeteaseMusic-Go/config
|
||||
config UNBLOCKNETEASEMUSIC_GO_COMPRESS_GOPROXY
|
||||
bool "Compiling with GOPROXY proxy"
|
||||
default n
|
||||
|
||||
config UNBLOCKNETEASEMUSIC_GO_COMPRESS_UPX
|
||||
bool "Compress executable files with UPX"
|
||||
depends on !mips64
|
||||
default n
|
||||
endef
|
||||
|
||||
ifeq ($(CONFIG_UNBLOCKNETEASEMUSIC_GO_COMPRESS_GOPROXY),y)
|
||||
export GO111MODULE=on
|
||||
export GOPROXY=https://goproxy.io
|
||||
endif
|
||||
|
||||
define Package/UnblockNeteaseMusic-Go
|
||||
SECTION:=multimedia
|
||||
CATEGORY:=Multimedia
|
||||
TITLE:=Revive Netease Cloud Music (Golang)
|
||||
URL:=https://github.com/cnsilvan/UnblockNeteaseMusic
|
||||
DEPENDS:=$(GO_ARCH_DEPENDS)
|
||||
endef
|
||||
|
||||
define Build/Compile
|
||||
$(call GoPackage/Build/Compile)
|
||||
ifeq ($(CONFIG_UNBLOCKNETEASEMUSIC_GO_COMPRESS_UPX),y)
|
||||
$(STAGING_DIR_HOST)/bin/upx --lzma --best $(GO_PKG_BUILD_BIN_DIR)/UnblockNeteaseMusic
|
||||
endif
|
||||
endef
|
||||
|
||||
define Package/UnblockNeteaseMusic-Go/install
|
||||
$(call GoPackage/Package/Install/Bin,$(PKG_INSTALL_DIR))
|
||||
|
||||
$(INSTALL_DIR) $(1)/usr/bin
|
||||
$(INSTALL_BIN) $(PKG_INSTALL_DIR)/usr/bin/UnblockNeteaseMusic $(1)/usr/bin/UnblockNeteaseMusic
|
||||
|
||||
$(INSTALL_DIR) $(1)/usr/share/UnblockNeteaseMusicGo
|
||||
$(CP) ./files/* $(1)/usr/share/UnblockNeteaseMusicGo/
|
||||
|
||||
endef
|
||||
|
||||
$(eval $(call GoBinPackage,UnblockNeteaseMusic-Go))
|
||||
$(eval $(call BuildPackage,UnblockNeteaseMusic-Go))
|
||||
14
UnblockNeteaseMusic-Go/files/ca.crt
Normal file
14
UnblockNeteaseMusic-Go/files/ca.crt
Normal file
@@ -0,0 +1,14 @@
|
||||
-----BEGIN CERTIFICATE-----
|
||||
MIICIjCCAaigAwIBAgIUTc9HQDej5hLCQ74u436a5yE4MDcwCgYIKoZIzj0EAwMw
|
||||
SDELMAkGA1UEBhMCQ04xJDAiBgNVBAMMG1VuYmxvY2tOZXRlYXNlTXVzaWMgUm9v
|
||||
dCBDQTETMBEGA1UECgwKMTcxNTE3MzMyOTAeFw0yMTA0MzAwNzIzMDJaFw0yNjA0
|
||||
MjkwNzIzMDJaMEgxCzAJBgNVBAYTAkNOMSQwIgYDVQQDDBtVbmJsb2NrTmV0ZWFz
|
||||
ZU11c2ljIFJvb3QgQ0ExEzARBgNVBAoMCjE3MTUxNzMzMjkwdjAQBgcqhkjOPQIB
|
||||
BgUrgQQAIgNiAASIyI7lYgGlq49qWtY1O2/XNDeowYf7W/Z+l7C14bphxAJ9jSDo
|
||||
tLwbFPWy5VPENc0rB0/yeHA2z7LU67POL2gGgp+17y7scLkkBk3Q7wRMETrtP44Z
|
||||
ITBstZ0wzVyyQEKjUzBRMB0GA1UdDgQWBBQ2F7+t8cPHJaWuCD8RHTSdLugKYzAf
|
||||
BgNVHSMEGDAWgBQ2F7+t8cPHJaWuCD8RHTSdLugKYzAPBgNVHRMBAf8EBTADAQH/
|
||||
MAoGCCqGSM49BAMDA2gAMGUCMQDqaRX2e01e0U+f0As/KUKDhmG5ElkK5CjYK9jk
|
||||
kXLNGFXJLGta6CDvjtMLBPc20qkCMBvDs+JnJKVBEJNZVsRBBs+v2YxNU/u2aYJa
|
||||
dMwXuFveSDWOS7mBeRztX/geEggiSw==
|
||||
-----END CERTIFICATE-----
|
||||
15
UnblockNeteaseMusic-Go/files/server.crt
Normal file
15
UnblockNeteaseMusic-Go/files/server.crt
Normal file
@@ -0,0 +1,15 @@
|
||||
-----BEGIN CERTIFICATE-----
|
||||
MIICRDCCAcqgAwIBAgIUeVqRrT2mHG5Mc8JD+ErphiAmlgkwCgYIKoZIzj0EAwMw
|
||||
SDELMAkGA1UEBhMCQ04xJDAiBgNVBAMMG1VuYmxvY2tOZXRlYXNlTXVzaWMgUm9v
|
||||
dCBDQTETMBEGA1UECgwKMTcxNTE3MzMyOTAeFw0yMTA0MzAwNzIzMDJaFw0yMjA0
|
||||
MzAwNzIzMDJaMHsxCzAJBgNVBAYTAkNOMREwDwYDVQQHDAhIYW5nemhvdTEsMCoG
|
||||
A1UECgwjTmV0RWFzZSAoSGFuZ3pob3UpIE5ldHdvcmsgQ28uLCBMdGQxETAPBgNV
|
||||
BAsMCElUIERlcHQuMRgwFgYDVQQDDA8qLm11c2ljLjE2My5jb20wdjAQBgcqhkjO
|
||||
PQIBBgUrgQQAIgNiAAQTPyU9RQ1pAFMLmozi+c4pEC1rrxAlPGwO9Em+qV+a5qLW
|
||||
gQjjsJeabMqJ/UQ7hDtdKVxWuXiAjMiDcXwL63I71MZKPTAEKXdCmNQwb4kXvRUn
|
||||
oOR4r7BMxEpGlf0CULWjQjBAMBMGA1UdJQQMMAoGCCsGAQUFBwMBMCkGA1UdEQQi
|
||||
MCCCDW11c2ljLjE2My5jb22CDyoubXVzaWMuMTYzLmNvbTAKBggqhkjOPQQDAwNo
|
||||
ADBlAjEAs5bdgnNP/DiK919RiWscC0kyuY0ugG1C8m8F2Yod4MI3oTyrkVcag21o
|
||||
NSzm802uAjBoPuKEbjjFP4ics0BQdICiVd6WCVAsE69FnlmqRteAJqxvdKGpVLi+
|
||||
Qi3arfomrrc=
|
||||
-----END CERTIFICATE-----
|
||||
9
UnblockNeteaseMusic-Go/files/server.key
Normal file
9
UnblockNeteaseMusic-Go/files/server.key
Normal file
@@ -0,0 +1,9 @@
|
||||
-----BEGIN EC PARAMETERS-----
|
||||
BgUrgQQAIg==
|
||||
-----END EC PARAMETERS-----
|
||||
-----BEGIN EC PRIVATE KEY-----
|
||||
MIGkAgEBBDBfW3twxGaQmMzP9p0/UU5EvHFVCbBw4piVFJ+pm/uFY6CKZkC5LGMa
|
||||
Uc9vn/KiewGgBwYFK4EEACKhZANiAAQTPyU9RQ1pAFMLmozi+c4pEC1rrxAlPGwO
|
||||
9Em+qV+a5qLWgQjjsJeabMqJ/UQ7hDtdKVxWuXiAjMiDcXwL63I71MZKPTAEKXdC
|
||||
mNQwb4kXvRUnoOR4r7BMxEpGlf0CULU=
|
||||
-----END EC PRIVATE KEY-----
|
||||
144
UnblockNeteaseMusic-Go/patches/01-fix-block-ad.patch
Normal file
144
UnblockNeteaseMusic-Go/patches/01-fix-block-ad.patch
Normal file
@@ -0,0 +1,144 @@
|
||||
From f4f5d11b578a1ab2c3d089bbe5453052b43892bb Mon Sep 17 00:00:00 2001
|
||||
From: tofuliang <tofuliang@gmail.com>
|
||||
Date: Mon, 24 Jan 2022 18:53:11 +0800
|
||||
Subject: [PATCH] fix block ad,add web traffic logs
|
||||
|
||||
---
|
||||
app.go | 1 +
|
||||
config/config.go | 1 +
|
||||
processor/processor.go | 55 +++++++++++++++++++++++++++++++++---------
|
||||
3 files changed, 45 insertions(+), 12 deletions(-)
|
||||
|
||||
diff --git a/app.go b/app.go
|
||||
index 73a6070..1018d75 100644
|
||||
--- a/app.go
|
||||
+++ b/app.go
|
||||
@@ -45,6 +45,7 @@ func main() {
|
||||
log.Println("EnableLocalVip=", *config.EnableLocalVip)
|
||||
log.Println("UnlockSoundEffects=", *config.UnlockSoundEffects)
|
||||
log.Println("QQCookieFile=", *config.QQCookieFile)
|
||||
+ log.Println("LogWebTraffic=", *config.LogWebTraffic)
|
||||
if host.InitHosts() == nil {
|
||||
//go func() {
|
||||
// // // terminal: $ go tool pprof -http=:8081 http://localhost:6060/debug/pprof/heap
|
||||
diff --git a/config/config.go b/config/config.go
|
||||
index 6c07873..a653cdf 100644
|
||||
--- a/config/config.go
|
||||
+++ b/config/config.go
|
||||
@@ -31,6 +31,7 @@ var (
|
||||
EnableLocalVip = flag.Bool("lv", false, "enable local vip")
|
||||
UnlockSoundEffects = flag.Bool("sef", false, "unlock SoundEffects")
|
||||
QQCookieFile = flag.String("qc", "./qq.cookie", "specify cookies file ,such as : \"qq.cookie\"")
|
||||
+ LogWebTraffic = flag.Bool("wl", false, "log request url and response")
|
||||
)
|
||||
|
||||
func ValidParams() bool {
|
||||
diff --git a/processor/processor.go b/processor/processor.go
|
||||
index 8d09dbf..d07b9d3 100644
|
||||
--- a/processor/processor.go
|
||||
+++ b/processor/processor.go
|
||||
@@ -6,14 +6,6 @@ import (
|
||||
"crypto/md5"
|
||||
"encoding/hex"
|
||||
"encoding/json"
|
||||
- "github.com/cnsilvan/UnblockNeteaseMusic/cache"
|
||||
- "github.com/cnsilvan/UnblockNeteaseMusic/common"
|
||||
- "github.com/cnsilvan/UnblockNeteaseMusic/config"
|
||||
- "github.com/cnsilvan/UnblockNeteaseMusic/network"
|
||||
- "github.com/cnsilvan/UnblockNeteaseMusic/processor/crypto"
|
||||
- "github.com/cnsilvan/UnblockNeteaseMusic/provider"
|
||||
- "github.com/cnsilvan/UnblockNeteaseMusic/utils"
|
||||
- "golang.org/x/text/width"
|
||||
"io"
|
||||
"io/ioutil"
|
||||
"log"
|
||||
@@ -22,6 +14,15 @@ import (
|
||||
"regexp"
|
||||
"strconv"
|
||||
"strings"
|
||||
+
|
||||
+ "github.com/cnsilvan/UnblockNeteaseMusic/cache"
|
||||
+ "github.com/cnsilvan/UnblockNeteaseMusic/common"
|
||||
+ "github.com/cnsilvan/UnblockNeteaseMusic/config"
|
||||
+ "github.com/cnsilvan/UnblockNeteaseMusic/network"
|
||||
+ "github.com/cnsilvan/UnblockNeteaseMusic/processor/crypto"
|
||||
+ "github.com/cnsilvan/UnblockNeteaseMusic/provider"
|
||||
+ "github.com/cnsilvan/UnblockNeteaseMusic/utils"
|
||||
+ "golang.org/x/text/width"
|
||||
)
|
||||
|
||||
var (
|
||||
@@ -188,6 +189,9 @@ func RequestAfter(request *http.Request, response *http.Response, netease *Netea
|
||||
if ok {
|
||||
code = codeN.String()
|
||||
}
|
||||
+
|
||||
+ logResponse(netease)
|
||||
+
|
||||
if strings.EqualFold(netease.Path, "/api/osx/version") {
|
||||
modified = disableUpdate(netease)
|
||||
} else if strings.Contains(netease.Path, "/usertool/sound/") {
|
||||
@@ -197,9 +201,24 @@ func RequestAfter(request *http.Request, response *http.Response, netease *Netea
|
||||
for key, resp := range netease.JsonBody {
|
||||
if strings.Contains(key, "/usertool/sound/") {
|
||||
modified = unblockSoundEffects(resp.(map[string]interface{}))
|
||||
- } else if *config.BlockAds && strings.Contains(netease.Path, "api/ad/") {
|
||||
+ } else if *config.BlockAds && strings.Contains(key, "api/ad/") {
|
||||
+ log.Println("block Ad has been triggered(" + key + ").")
|
||||
resp = &common.MapType{}
|
||||
modified = true
|
||||
+ } else if *config.BlockAds && strings.EqualFold(key, "/api/v2/banner/get") {
|
||||
+ newInfo := make(common.SliceType, 0)
|
||||
+ info := netease.JsonBody[key]
|
||||
+ for _, data := range info.(common.MapType)["banners"].(common.SliceType) {
|
||||
+ if banner, ok := data.(common.MapType); ok {
|
||||
+ if banner["adid"] == nil {
|
||||
+ newInfo = append(newInfo, banner)
|
||||
+ } else {
|
||||
+ log.Println("block banner Ad has been triggered.")
|
||||
+ modified = true
|
||||
+ }
|
||||
+ }
|
||||
+ }
|
||||
+ info.(common.MapType)["banners"] = newInfo
|
||||
}
|
||||
}
|
||||
} else if !netease.Web && (code == "401" || code == "512") && strings.Contains(netease.Path, "manipulate") {
|
||||
@@ -220,7 +239,9 @@ func RequestAfter(request *http.Request, response *http.Response, netease *Netea
|
||||
// log.Println("NeedRepackage")
|
||||
modifiedJson, _ := json.Marshal(netease.JsonBody)
|
||||
// log.Println(netease)
|
||||
- // log.Println(string(modifiedJson))
|
||||
+ if *config.LogWebTraffic {
|
||||
+ log.Println("modified =>\n" + string(modifiedJson))
|
||||
+ }
|
||||
if netease.Encrypted {
|
||||
modifiedJson = crypto.AesEncryptECB(modifiedJson, []byte(aeskey))
|
||||
}
|
||||
@@ -258,14 +279,24 @@ func disableUpdate(netease *Netease) bool {
|
||||
if len(value.(common.SliceType)) > 0 {
|
||||
modified = true
|
||||
jsonBody["updateFiles"] = make(common.SliceType, 0)
|
||||
+ log.Println("disable update has been triggered.")
|
||||
}
|
||||
default:
|
||||
}
|
||||
}
|
||||
- // modifiedJson, _ := json.Marshal(jsonBody)
|
||||
- // log.Println(string(modifiedJson))
|
||||
return modified
|
||||
}
|
||||
+
|
||||
+func logResponse(netease *Netease) {
|
||||
+ if *config.LogWebTraffic {
|
||||
+ reqUrl := netease.Path
|
||||
+ jsonBody := netease.JsonBody
|
||||
+ modifiedJson, _ := json.Marshal(jsonBody)
|
||||
+ sep := "===================================\n"
|
||||
+ log.Println(sep + reqUrl + " => \n" + string(modifiedJson) + "\n")
|
||||
+ }
|
||||
+}
|
||||
+
|
||||
func localVIP(netease *Netease) bool {
|
||||
if !*config.EnableLocalVip {
|
||||
return false
|
||||
@@ -0,0 +1,29 @@
|
||||
From 6c009953d357d1cc03478cf65fc05701fb1966d6 Mon Sep 17 00:00:00 2001
|
||||
From: ameansone <ameansone@outlook.com>
|
||||
Date: Sun, 5 Dec 2021 19:18:20 +0800
|
||||
Subject: [PATCH] fix(processor): avoid unnecessary decryption
|
||||
|
||||
---
|
||||
processor/processor.go | 8 ++++++--
|
||||
1 file changed, 6 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/processor/processor.go b/processor/processor.go
|
||||
index 8d09dbf..011571b 100644
|
||||
--- a/processor/processor.go
|
||||
+++ b/processor/processor.go
|
||||
@@ -177,9 +177,13 @@ func RequestAfter(request *http.Request, response *http.Response, netease *Netea
|
||||
if netease.Forward {
|
||||
aeskey = linuxApiKey
|
||||
}
|
||||
- decryptECBBytes, encrypted := crypto.AesDecryptECB(decryptECBBytes, []byte(aeskey))
|
||||
- netease.Encrypted = encrypted
|
||||
result := utils.ParseJson(decryptECBBytes)
|
||||
+ netease.Encrypted = false;
|
||||
+ if result == nil {
|
||||
+ decryptECBBytes, encrypted := crypto.AesDecryptECB(decryptECBBytes, []byte(aeskey))
|
||||
+ netease.Encrypted = encrypted
|
||||
+ result = utils.ParseJson(decryptECBBytes)
|
||||
+ }
|
||||
netease.JsonBody = result
|
||||
|
||||
modified := false
|
||||
52
UnblockNeteaseMusic/Makefile
Normal file
52
UnblockNeteaseMusic/Makefile
Normal file
@@ -0,0 +1,52 @@
|
||||
# SPDX-Identifier-License: GPL-3.0-only
|
||||
#
|
||||
# Copyright (C) 2021 ImmortalWrt.org
|
||||
|
||||
include $(TOPDIR)/rules.mk
|
||||
|
||||
PKG_NAME:=UnblockNeteaseMusic
|
||||
PKG_BASE_VERSION:=0.27.0
|
||||
PKG_RELEASE:=$(AUTORELEASE)
|
||||
|
||||
PKG_SOURCE_PROTO:=git
|
||||
PKG_SOURCE_URL:=https://github.com/UnblockNeteaseMusic/server.git
|
||||
PKG_SOURCE_DATE:=2022-10-09
|
||||
PKG_SOURCE_VERSION:=253dc89329ebd16ff22175d9d0ab9382ed8aaccc
|
||||
PKG_MIRROR_HASH:=c2ed5f269c1935575c57ed5489504ef37f453b2a512209bf0762a55fc3eb4b29
|
||||
|
||||
PKG_VERSION:=$(PKG_BASE_VERSION)-$(PKG_SOURCE_DATE)-$(call version_abbrev,$(PKG_SOURCE_VERSION))
|
||||
|
||||
PKG_LICENSE:=LGPL-3.0-only
|
||||
PKG_LICENSE_FILE:=LICENSE
|
||||
PKG_MAINTAINER:=Tianling Shen <cnsztl@immortalwrt.org>
|
||||
|
||||
include $(INCLUDE_DIR)/package.mk
|
||||
|
||||
define Package/UnblockNeteaseMusic
|
||||
SECTION:=multimedia
|
||||
CATEGORY:=Multimedia
|
||||
TITLE:=Revive Netease Cloud Music (NodeJS)
|
||||
URL:=https://github.com/nondanee/UnblockNeteaseMusic
|
||||
DEPENDS:=+node
|
||||
PKGARCH:=all
|
||||
endef
|
||||
|
||||
define Build/Prepare
|
||||
mkdir -p $(PKG_BUILD_DIR)
|
||||
xzcat $(DL_DIR)/$(PKG_SOURCE) | $(TAR) -C $(PKG_BUILD_DIR) $(TAR_OPTIONS)
|
||||
endef
|
||||
|
||||
define Build/Configure
|
||||
echo -e $(PKG_BASE_VERSION) > $(PKG_BUILD_DIR)/$(PKG_NAME)-$(PKG_VERSION)/core_ver
|
||||
echo -e $(PKG_SOURCE_VERSION) > $(PKG_BUILD_DIR)/$(PKG_NAME)-$(PKG_VERSION)/local_ver
|
||||
endef
|
||||
|
||||
define Build/Compile
|
||||
endef
|
||||
|
||||
define Package/UnblockNeteaseMusic/install
|
||||
$(INSTALL_DIR) $(1)/usr/share/UnblockNeteaseMusic
|
||||
$(CP) $(PKG_BUILD_DIR)/$(PKG_NAME)-$(PKG_VERSION)/* $(1)/usr/share/UnblockNeteaseMusic
|
||||
endef
|
||||
|
||||
$(eval $(call BuildPackage,UnblockNeteaseMusic))
|
||||
109
amule/Makefile
Normal file
109
amule/Makefile
Normal file
@@ -0,0 +1,109 @@
|
||||
#
|
||||
# Copyright (C) 2007-2009 OpenWrt.org
|
||||
#
|
||||
# This is free software, licensed under the GNU General Public License v2.
|
||||
# See /LICENSE for more information.
|
||||
#
|
||||
|
||||
include $(TOPDIR)/rules.mk
|
||||
|
||||
PKG_NAME:=aMule
|
||||
PKG_VERSION:=2.3.3
|
||||
PKG_RELEASE:=3
|
||||
PKG_REV=4b87b20
|
||||
|
||||
|
||||
PKG_SOURCE:=$(PKG_NAME)-$(PKG_VERSION)-r$(PKG_REV).tar.bz2
|
||||
PKG_SOURCE_SUBDIR:=$(PKG_NAME)-$(PKG_VERSION)
|
||||
PKG_SOURCE_PROTO:=git
|
||||
PKG_SOURCE_VERSION:=$(PKG_REV)
|
||||
PKG_SOURCE_URL:=https://github.com/amule-project/amule.git
|
||||
PKG_MIRROR_HASH:=102c4cb3dd2858db06fff19c5e2d0b65c6731b366f45df2adcd40fd0cd0fec47
|
||||
|
||||
PKG_BUILD_DIR:=$(BUILD_DIR)/$(PKG_NAME)-$(PKG_VERSION)
|
||||
PKG_BUILD_DEPENDS:=libgd libcryptopp
|
||||
|
||||
include $(INCLUDE_DIR)/package.mk
|
||||
include $(INCLUDE_DIR)/nls.mk
|
||||
|
||||
define Package/amule/config
|
||||
config AMULE_CRYPTOPP_STATIC_LINKING
|
||||
bool "Link libcryptopp statically"
|
||||
default n
|
||||
endef
|
||||
|
||||
define Package/amule
|
||||
SUBMENU:=P2P
|
||||
SECTION:=net
|
||||
CATEGORY:=Network
|
||||
TITLE:=A multi-platform eMule-like ed2k client
|
||||
URL:=http://www.amule.org/
|
||||
DEPENDS:=+libpng +libpthread +libncurses +libreadline +libwxbase +libupnp +libbfd \
|
||||
$(ICONV_DEPENDS) $(INTL_DEPENDS) +!AMULE_CRYPTOPP_STATIC_LINKING:libcryptopp
|
||||
endef
|
||||
|
||||
CONFIGURE_ARGS+= \
|
||||
--disable-static \
|
||||
--disable-rpath \
|
||||
--with-gnu-ld \
|
||||
--disable-ccache \
|
||||
--disable-optimize \
|
||||
--disable-profile \
|
||||
--disable-monolithic \
|
||||
--enable-amule-daemon \
|
||||
--enable-amulecmd \
|
||||
--enable-webserver \
|
||||
--disable-amule-gui \
|
||||
--disable-cas \
|
||||
--disable-wxcas \
|
||||
--disable-ed2k \
|
||||
--disable-alc \
|
||||
--disable-alcc \
|
||||
--disable-fileview \
|
||||
--disable-plasmamule \
|
||||
--without-wxdebug \
|
||||
--enable-dlp \
|
||||
--enable-upnp \
|
||||
--with-zlib="$(STAGING_DIR)/usr" \
|
||||
--with-gdlib-prefix="$(STAGING_DIR)/usr" \
|
||||
--with-libpng-prefix="$(STAGING_DIR)/usr" \
|
||||
--with-wx-prefix="$(STAGING_DIR)/usr" \
|
||||
--with-crypto-prefix="$(STAGING_DIR)/usr" \
|
||||
--with-libiconv-prefix="$(ICONV_PREFIX)" \
|
||||
--with-libintl-prefix="$(INTL_PREFIX)" \
|
||||
--with-libupnp-prefix="$(STAGING_DIR)/usr" \
|
||||
--without-x \
|
||||
--disable-debug
|
||||
|
||||
TARGET_LDFLAGS += $(if $(ICONV_FULL),-liconv)
|
||||
|
||||
define Build/Configure
|
||||
cd $(PKG_BUILD_DIR) && sh ./autogen.sh
|
||||
$(call Build/Configure/Default)
|
||||
endef
|
||||
|
||||
ifeq ($(CONFIG_AMULE_CRYPTOPP_STATIC_LINKING),y)
|
||||
SED_CMD:=sed
|
||||
else
|
||||
SED_CMD:=true
|
||||
endif
|
||||
|
||||
define Build/Compile
|
||||
$(SED_CMD) -i 's;^CRYPTOPP_LIBS.*;CRYPTOPP_LIBS \= "$(STAGING_DIR)/usr/lib/libcryptopp.a";g' \
|
||||
$(PKG_BUILD_DIR)/src/Makefile
|
||||
$(MAKE) -C $(PKG_BUILD_DIR) \
|
||||
HOSTCC="$(HOSTCC)" \
|
||||
DESTDIR="$(PKG_INSTALL_DIR)" \
|
||||
all
|
||||
endef
|
||||
|
||||
define Package/amule/install
|
||||
$(INSTALL_DIR) $(1)/usr/bin
|
||||
$(INSTALL_DIR) $(1)/usr/share/amule/webserver
|
||||
$(INSTALL_BIN) $(PKG_BUILD_DIR)/src/amule{cmd,d} $(1)/usr/bin/
|
||||
$(INSTALL_BIN) $(PKG_BUILD_DIR)/src/webserver/src/amuleweb $(1)/usr/bin/
|
||||
$(CP) $(PKG_BUILD_DIR)/src/webserver/default $(1)/usr/share/amule/webserver
|
||||
|
||||
endef
|
||||
|
||||
$(eval $(call BuildPackage,amule))
|
||||
25
amule/patches/0001-fix-API-mismatch-with-crypto-6.0.0.patch
Normal file
25
amule/patches/0001-fix-API-mismatch-with-crypto-6.0.0.patch
Normal file
@@ -0,0 +1,25 @@
|
||||
From 46ecaeadff4c07b8fd98cf41e27605895328ce0a Mon Sep 17 00:00:00 2001
|
||||
From: W_Y_CPP <383152993@qq.com>
|
||||
Date: Thu, 2 Dec 2021 00:46:12 -0800
|
||||
Subject: [PATCH] fix API mismatch with crypto++ 6.0.0
|
||||
|
||||
---
|
||||
src/ClientCreditsList.cpp | 2 +-
|
||||
1 file changed, 1 insertion(+), 1 deletion(-)
|
||||
|
||||
diff --git a/src/ClientCreditsList.cpp b/src/ClientCreditsList.cpp
|
||||
index d61e8d4..b02e162 100644
|
||||
--- a/src/ClientCreditsList.cpp
|
||||
+++ b/src/ClientCreditsList.cpp
|
||||
@@ -312,7 +312,7 @@ void CClientCreditsList::InitalizeCrypting()
|
||||
// calculate and store public key
|
||||
CryptoPP::RSASSA_PKCS1v15_SHA_Verifier pubkey(*static_cast<CryptoPP::RSASSA_PKCS1v15_SHA_Signer *>(m_pSignkey));
|
||||
CryptoPP::ArraySink asink(m_abyMyPublicKey, 80);
|
||||
- pubkey.DEREncode(asink);
|
||||
+ pubkey.GetMaterial().Save(asink);
|
||||
m_nMyPublicKeyLen = asink.TotalPutLength();
|
||||
asink.MessageEnd();
|
||||
} catch (const CryptoPP::Exception& e) {
|
||||
--
|
||||
2.17.1
|
||||
|
||||
2285
amule/patches/0002-fix-byte-type-error.patch
Normal file
2285
amule/patches/0002-fix-byte-type-error.patch
Normal file
File diff suppressed because it is too large
Load Diff
25
amule/patches/0003-fix-set_terminate.patch
Normal file
25
amule/patches/0003-fix-set_terminate.patch
Normal file
@@ -0,0 +1,25 @@
|
||||
From dcc605e06e106b05bc5e756eeeeb17abbc1a6e5c Mon Sep 17 00:00:00 2001
|
||||
From: W_Y_CPP <383152993@qq.com>
|
||||
Date: Wed, 1 Dec 2021 23:13:08 -0800
|
||||
Subject: [PATCH] fix set_terminate
|
||||
|
||||
---
|
||||
src/libs/common/MuleDebug.cpp | 2 +-
|
||||
1 file changed, 1 insertion(+), 1 deletion(-)
|
||||
|
||||
diff --git a/src/libs/common/MuleDebug.cpp b/src/libs/common/MuleDebug.cpp
|
||||
index 5d8d758..14206f9 100644
|
||||
--- a/src/libs/common/MuleDebug.cpp
|
||||
+++ b/src/libs/common/MuleDebug.cpp
|
||||
@@ -24,7 +24,7 @@
|
||||
//
|
||||
|
||||
#include <cstdlib> // Needed for std::abort()
|
||||
-
|
||||
+#include <exception>
|
||||
#ifdef HAVE_CONFIG_H
|
||||
# include "config.h" // Needed for HAVE_CXXABI and HAVE_EXECINFO
|
||||
#endif
|
||||
--
|
||||
2.17.1
|
||||
|
||||
1548
amule/patches/001-amule-dlp.patch
Normal file
1548
amule/patches/001-amule-dlp.patch
Normal file
File diff suppressed because it is too large
Load Diff
23
amule/patches/003_enable_upnp_cross_compile.patch
Normal file
23
amule/patches/003_enable_upnp_cross_compile.patch
Normal file
@@ -0,0 +1,23 @@
|
||||
diff -Naur a/m4/libupnp.m4 b/m4/libupnp.m4
|
||||
--- a/m4/libupnp.m4 2016-10-06 19:01:54.000000000 +0800
|
||||
+++ b/m4/libupnp.m4 2016-10-11 07:36:39.198318574 +0800
|
||||
@@ -52,7 +52,6 @@
|
||||
[export PKG_CONFIG_PATH=$withval/lib/pkgconfig])
|
||||
|
||||
dnl Check for libupnp >= MIN_LIBUPNP_VERSION
|
||||
- AS_IF([test $cross_compiling = no], [
|
||||
AC_MSG_CHECKING([for libupnp version >= MIN_LIBUPNP_VERSION])
|
||||
AS_IF([test -n "$PKG_CONFIG"], [
|
||||
AS_IF([$PKG_CONFIG libupnp --exists], [
|
||||
@@ -79,11 +78,6 @@
|
||||
])
|
||||
AC_MSG_RESULT([$result$resultstr])
|
||||
libupnp_error="libupnp >= MIN_LIBUPNP_VERSION not found$resultstr"
|
||||
- ], [
|
||||
-dnl Currently cross-compilation with libupnp is not supported.
|
||||
- result=no
|
||||
- libupnp_error="cross compiling"
|
||||
- ])
|
||||
|
||||
dnl Execute the right action.
|
||||
AS_IF([test ${result:-no} = yes], [$2], [$3])
|
||||
78
amule/patches/004_file_name_conversion.patch
Normal file
78
amule/patches/004_file_name_conversion.patch
Normal file
@@ -0,0 +1,78 @@
|
||||
diff --git a/src/amule.h b/src/amule.h
|
||||
index f25702f..240c02d 100644
|
||||
--- a/src/amule.h
|
||||
+++ b/src/amule.h
|
||||
@@ -553,6 +553,13 @@ class CamuleDaemonApp : public CamuleApp
|
||||
int OnExit();
|
||||
|
||||
virtual int InitGui(bool geometry_enable, wxString &geometry_string);
|
||||
+ // The GTK wxApps sets its file name conversion properly
|
||||
+ // in wxApp::Initialize(), while wxAppConsole::Initialize()
|
||||
+ // does not, leaving wxConvFile being set to wxConvLibc. File
|
||||
+ // name conversion should be set otherwise amuled will abort to
|
||||
+ // handle non-ASCII file names which monolithic amule can handle.
|
||||
+ // This function are overrided to perform this.
|
||||
+ virtual bool Initialize(int& argc_, wxChar **argv_);
|
||||
|
||||
#ifdef AMULED_APPTRAITS
|
||||
struct sigaction m_oldSignalChildAction;
|
||||
diff --git a/src/amuled.cpp b/src/amuled.cpp
|
||||
index 486da59..86e1ff8 100644
|
||||
--- a/src/amuled.cpp
|
||||
+++ b/src/amuled.cpp
|
||||
@@ -704,6 +704,41 @@ int CamuleDaemonApp::InitGui(bool ,wxString &)
|
||||
return 0;
|
||||
}
|
||||
|
||||
+bool CamuleDaemonApp::Initialize(int& argc_, wxChar **argv_)
|
||||
+{
|
||||
+ if ( !wxAppConsole::Initialize(argc_, argv_) ) {
|
||||
+ return false;
|
||||
+ }
|
||||
+
|
||||
+#ifdef __UNIX__
|
||||
+ wxString encName;
|
||||
+#if wxUSE_INTL
|
||||
+ // if a non default locale is set,
|
||||
+ // assume that the user wants his
|
||||
+ // filenames in this locale too
|
||||
+ encName = wxLocale::GetSystemEncodingName().Upper();
|
||||
+
|
||||
+ // But don't consider ASCII in this case.
|
||||
+ if ( !encName.empty() ) {
|
||||
+ if ( encName == wxT("US-ASCII") ) {
|
||||
+ // This means US-ASCII when returned
|
||||
+ // from GetEncodingFromName().
|
||||
+ encName.clear();
|
||||
+ }
|
||||
+ }
|
||||
+#endif // wxUSE_INTL
|
||||
+
|
||||
+ // in this case, UTF-8 is used by default.
|
||||
+ if ( encName.empty() ) {
|
||||
+ encName = wxT("UTF-8");
|
||||
+ }
|
||||
+
|
||||
+ static wxConvBrokenFileNames fileconv(encName);
|
||||
+ wxConvFileName = &fileconv;
|
||||
+#endif // __UNIX__
|
||||
+
|
||||
+ return true;
|
||||
+}
|
||||
|
||||
int CamuleDaemonApp::OnExit()
|
||||
{
|
||||
diff --git a/src/libs/common/Path.cpp b/src/libs/common/Path.cpp
|
||||
index 28152a2..5efefd0 100644
|
||||
--- a/src/libs/common/Path.cpp
|
||||
+++ b/src/libs/common/Path.cpp
|
||||
@@ -229,7 +229,8 @@ CPath::CPath(const wxString& filename)
|
||||
}
|
||||
|
||||
wxCharBuffer fn = filename2char(filename);
|
||||
- if (fn.data()) {
|
||||
+ // add fn.length() for wx 3.x
|
||||
+ if (fn.data()) {
|
||||
// Filename is valid in the current locale. This means that
|
||||
// it either originated from a (wx)system-call, or from a
|
||||
// user with a properly setup system.
|
||||
174
amule/patches/005_best_keyword_kad_search.patch
Normal file
174
amule/patches/005_best_keyword_kad_search.patch
Normal file
@@ -0,0 +1,174 @@
|
||||
diff --git a/src/SearchList.cpp b/src/SearchList.cpp
|
||||
index 32b28e9..342a18f 100644
|
||||
--- a/src/SearchList.cpp
|
||||
+++ b/src/SearchList.cpp
|
||||
@@ -75,7 +75,7 @@ void ParsedSearchExpression(const CSearchExpr* pexpr)
|
||||
int iOpNot = 0;
|
||||
|
||||
for (unsigned int i = 0; i < pexpr->m_aExpr.GetCount(); i++) {
|
||||
- wxString str(pexpr->m_aExpr[i]);
|
||||
+ const wxString& str = pexpr->m_aExpr[i];
|
||||
if (str == SEARCHOPTOK_AND) {
|
||||
iOpAnd++;
|
||||
} else if (str == SEARCHOPTOK_OR) {
|
||||
@@ -108,6 +108,25 @@ void ParsedSearchExpression(const CSearchExpr* pexpr)
|
||||
|
||||
// optimize search expression, if no OR nor NOT specified
|
||||
if (iOpAnd > 0 && iOpOr == 0 && iOpNot == 0) {
|
||||
+ // figure out if we can use a better keyword than the one the user selected
|
||||
+ // for example most user will search like this "The oxymoronaccelerator 2", which would ask the node which indexes "the"
|
||||
+ // This causes higher traffic for such nodes and makes them a viable target to attackers, while the kad result should be
|
||||
+ // the same or even better if we ask the node which indexes the rare keyword "oxymoronaccelerator", so we try to rearrange
|
||||
+ // keywords and generally assume that the longer keywords are rarer
|
||||
+ if (/*thePrefs::GetRearrangeKadSearchKeywords() &&*/ !s_strCurKadKeyword.IsEmpty()) {
|
||||
+ for (unsigned int i = 0; i < pexpr->m_aExpr.GetCount(); i++) {
|
||||
+ if (pexpr->m_aExpr[i] != SEARCHOPTOK_AND) {
|
||||
+ if (pexpr->m_aExpr[i] != s_strCurKadKeyword
|
||||
+ && pexpr->m_aExpr[i].find_first_of(Kademlia::CSearchManager::GetInvalidKeywordChars()) == wxString::npos
|
||||
+ && pexpr->m_aExpr[i].Find('"') != 0 // no quoted expressions as keyword
|
||||
+ && pexpr->m_aExpr[i].length() >= 3
|
||||
+ && s_strCurKadKeyword.length() < pexpr->m_aExpr[i].length())
|
||||
+ {
|
||||
+ s_strCurKadKeyword = pexpr->m_aExpr[i];
|
||||
+ }
|
||||
+ }
|
||||
+ }
|
||||
+ }
|
||||
wxString strAndTerms;
|
||||
for (unsigned int i = 0; i < pexpr->m_aExpr.GetCount(); i++) {
|
||||
if (pexpr->m_aExpr[i] != SEARCHOPTOK_AND) {
|
||||
@@ -285,7 +304,7 @@ void CSearchList::RemoveResults(long searchID)
|
||||
}
|
||||
|
||||
|
||||
-wxString CSearchList::StartNewSearch(uint32* searchID, SearchType type, const CSearchParams& params)
|
||||
+wxString CSearchList::StartNewSearch(uint32* searchID, SearchType type, CSearchParams& params)
|
||||
{
|
||||
// Check that we can actually perform the specified desired search.
|
||||
if ((type == KadSearch) && !Kademlia::CKademlia::IsRunning()) {
|
||||
@@ -306,6 +325,16 @@ wxString CSearchList::StartNewSearch(uint32* searchID, SearchType type, const CS
|
||||
m_resultType.Clear();
|
||||
}
|
||||
|
||||
+ if (type == KadSearch) {
|
||||
+ Kademlia::WordList words;
|
||||
+ Kademlia::CSearchManager::GetWords(params.searchString, &words);
|
||||
+ if (!words.empty()) {
|
||||
+ params.strKeyword = words.front();
|
||||
+ } else {
|
||||
+ return _("No keyword for Kad search - aborting");
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
bool supports64bit = type == KadSearch ? true : theApp->serverconnect->GetCurrentServer() != NULL && (theApp->serverconnect->GetCurrentServer()->GetTCPFlags() & SRV_TCPFLG_LARGEFILES);
|
||||
bool packetUsing64bit;
|
||||
|
||||
@@ -332,8 +361,7 @@ wxString CSearchList::StartNewSearch(uint32* searchID, SearchType type, const CS
|
||||
|
||||
// searchstring will get tokenized there
|
||||
// The tab must be created with the Kad search ID, so searchID is updated.
|
||||
- Kademlia::CSearch* search = Kademlia::CSearchManager::PrepareFindKeywords(
|
||||
- params.searchString, data->GetLength(), data->GetRawBuffer(), *searchID);
|
||||
+ Kademlia::CSearch* search = Kademlia::CSearchManager::PrepareFindKeywords(params.strKeyword, data->GetLength(), data->GetRawBuffer(), *searchID);
|
||||
|
||||
*searchID = search->GetSearchID();
|
||||
m_currentSearch = *searchID;
|
||||
@@ -632,7 +660,7 @@ void CSearchList::StopSearch(bool globalOnly)
|
||||
}
|
||||
|
||||
|
||||
-CSearchList::CMemFilePtr CSearchList::CreateSearchData(const CSearchParams& params, SearchType WXUNUSED(type), bool supports64bit, bool& packetUsing64bit)
|
||||
+CSearchList::CMemFilePtr CSearchList::CreateSearchData(CSearchParams& params, SearchType type, bool supports64bit, bool& packetUsing64bit)
|
||||
{
|
||||
// Count the number of used parameters
|
||||
unsigned int parametercount = 0;
|
||||
@@ -659,14 +687,16 @@ CSearchList::CMemFilePtr CSearchList::CreateSearchData(const CSearchParams& para
|
||||
_astrParserErrors.Empty();
|
||||
_SearchExpr.m_aExpr.Empty();
|
||||
|
||||
+ s_strCurKadKeyword.Clear();
|
||||
+ if (type == KadSearch) {
|
||||
+ wxASSERT( !params.strKeyword.IsEmpty() );
|
||||
+ s_strCurKadKeyword = params.strKeyword;
|
||||
+ }
|
||||
+
|
||||
LexInit(params.searchString);
|
||||
int iParseResult = yyparse();
|
||||
LexFree();
|
||||
|
||||
-#ifdef __DEBUG__
|
||||
- AddLogLineNS(CFormat(wxT("Search parsing result for \"%s\": %i"))
|
||||
- % params.searchString % iParseResult);
|
||||
-#endif
|
||||
if (_astrParserErrors.GetCount() > 0) {
|
||||
for (unsigned int i=0; i < _astrParserErrors.GetCount(); ++i) {
|
||||
AddLogLineNS(CFormat(wxT("Error %u: %s\n")) % i % _astrParserErrors[i]);
|
||||
@@ -681,21 +711,13 @@ CSearchList::CMemFilePtr CSearchList::CreateSearchData(const CSearchParams& para
|
||||
return CMemFilePtr(NULL);
|
||||
}
|
||||
|
||||
- #ifdef __DEBUG__
|
||||
- wxString mes(wxT("Search expression:"));
|
||||
- for (unsigned int i = 0; i < _SearchExpr.m_aExpr.GetCount(); i++) {
|
||||
- mes << wxT(" ") << _SearchExpr.m_aExpr[i];
|
||||
+ if (type == KadSearch && s_strCurKadKeyword != params.strKeyword) {
|
||||
+ AddDebugLogLineN(logSearch, CFormat(wxT("Keyword was rearranged, using '%s' instead of '%s'")) % s_strCurKadKeyword % params.strKeyword);
|
||||
+ params.strKeyword = s_strCurKadKeyword;
|
||||
}
|
||||
- AddLogLineNS(mes);
|
||||
- AddLogLineNS(CFormat(wxT("Expression count: %i")) % _SearchExpr.m_aExpr.GetCount());
|
||||
- #endif
|
||||
|
||||
parametercount += _SearchExpr.m_aExpr.GetCount();
|
||||
|
||||
- #ifdef __DEBUG__
|
||||
- AddLogLineNS(CFormat(wxT("Parameters: %i")) % parametercount);
|
||||
- #endif
|
||||
-
|
||||
/* Leave the unicode comment there, please... */
|
||||
CSearchExprTarget target(data.get(), true /*I assume everyone is unicoded */ ? utf8strRaw : utf8strNone, supports64bit, packetUsing64bit);
|
||||
|
||||
diff --git a/src/SearchList.h b/src/SearchList.h
|
||||
index 35b0fc6..6db7508 100644
|
||||
--- a/src/SearchList.h
|
||||
+++ b/src/SearchList.h
|
||||
@@ -64,6 +64,8 @@ class CSearchList : public wxEvtHandler
|
||||
|
||||
//! The actual string to search for.
|
||||
wxString searchString;
|
||||
+ //! The keyword selected for Kad search
|
||||
+ wxString strKeyword;
|
||||
//! The type of files to search for (may be empty), one of ED2KFTSTR_*
|
||||
wxString typeText;
|
||||
//! The filename extension. May be empty.
|
||||
@@ -90,7 +92,7 @@ class CSearchList : public wxEvtHandler
|
||||
* @param params The search parameters, see CSearchParams.
|
||||
* @return An empty string on success, otherwise an error-message.
|
||||
*/
|
||||
- wxString StartNewSearch(uint32* searchID, SearchType type, const CSearchParams& params);
|
||||
+ wxString StartNewSearch(uint32* searchID, SearchType type, CSearchParams& params);
|
||||
|
||||
/** Stops the current search (global or Kad), if any is in progress. */
|
||||
void StopSearch(bool globalOnly = false);
|
||||
@@ -189,7 +191,7 @@ class CSearchList : public wxEvtHandler
|
||||
typedef std::auto_ptr<CMemFile> CMemFilePtr;
|
||||
|
||||
/** Create a basic search-packet for the given search-type. */
|
||||
- CMemFilePtr CreateSearchData(const CSearchParams& params, SearchType type, bool supports64bit, bool& packetUsing64bit);
|
||||
+ CMemFilePtr CreateSearchData(CSearchParams& params, SearchType type, bool supports64bit, bool& packetUsing64bit);
|
||||
|
||||
|
||||
//! Timer used for global search intervals.
|
||||
diff --git a/src/kademlia/kademlia/SearchManager.cpp b/src/kademlia/kademlia/SearchManager.cpp
|
||||
index e7f25d4..f9ee924 100644
|
||||
--- a/src/kademlia/kademlia/SearchManager.cpp
|
||||
+++ b/src/kademlia/kademlia/SearchManager.cpp
|
||||
@@ -127,7 +127,7 @@ CSearch* CSearchManager::PrepareFindKeywords(const wxString& keyword, uint32_t s
|
||||
|
||||
wxString wstrKeyword = s->m_words.front();
|
||||
|
||||
- AddLogLineNS(CFormat(_("Keyword for search: %s")) % wstrKeyword);
|
||||
+ AddDebugLogLineN(logSearch, CFormat(wxT("Keyword for search: %s")) % wstrKeyword);
|
||||
|
||||
// Kry - I just decided to assume everyone is unicoded
|
||||
// GonoszTopi - seconded
|
||||
365
amule/patches/006_update-libupnp.patch
Normal file
365
amule/patches/006_update-libupnp.patch
Normal file
@@ -0,0 +1,365 @@
|
||||
diff -Naur a/m4/libupnp.m4 b/m4/libupnp.m4
|
||||
--- a/m4/libupnp.m4 2016-10-06 18:49:44.000000000 +0800
|
||||
+++ b/m4/libupnp.m4 2019-12-11 22:13:19.008225399 +0800
|
||||
@@ -45,11 +45,16 @@
|
||||
|
||||
dnl Test for --with-libupnp-prefix
|
||||
AC_ARG_WITH(
|
||||
- [libupnp-prefix],
|
||||
- [AS_HELP_STRING(
|
||||
+ [libupnp-prefix],[
|
||||
+ AS_HELP_STRING(
|
||||
[--with-libupnp-prefix=PREFIX],
|
||||
- [UPnP library location])],
|
||||
- [export PKG_CONFIG_PATH=$withval/lib/pkgconfig])
|
||||
+ [UPnP library location])],[
|
||||
+ AS_IF([test -d "$withval/lib64/pkgconfig"],[
|
||||
+ export PKG_CONFIG_PATH=$withval/lib64/pkgconfig
|
||||
+ ],[
|
||||
+ export PKG_CONFIG_PATH=$withval/lib/pkgconfig
|
||||
+ ])
|
||||
+ ])
|
||||
|
||||
dnl Check for libupnp >= MIN_LIBUPNP_VERSION
|
||||
AS_IF([test $cross_compiling = no], [
|
||||
diff -Naur a/src/UPnPBase.cpp b/src/UPnPBase.cpp
|
||||
--- a/src/UPnPBase.cpp 2016-10-06 18:49:44.000000000 +0800
|
||||
+++ b/src/UPnPBase.cpp 2019-12-11 22:15:04.536768532 +0800
|
||||
@@ -1127,7 +1127,11 @@
|
||||
|
||||
|
||||
// This function is static
|
||||
+#if UPNP_VERSION >= 10800
|
||||
+int CUPnPControlPoint::Callback(Upnp_EventType_e EventType, const void *Event, void * /*Cookie*/)
|
||||
+#else
|
||||
int CUPnPControlPoint::Callback(Upnp_EventType EventType, void *Event, void * /*Cookie*/)
|
||||
+#endif
|
||||
{
|
||||
std::ostringstream msg;
|
||||
std::ostringstream msg2;
|
||||
@@ -1149,24 +1153,47 @@
|
||||
msg2<< "UPNP_DISCOVERY_SEARCH_RESULT: ";
|
||||
// UPnP Discovery
|
||||
upnpDiscovery:
|
||||
+#if UPNP_VERSION >= 10800
|
||||
+ UpnpDiscovery *d_event = (UpnpDiscovery *)Event;
|
||||
+#else
|
||||
struct Upnp_Discovery *d_event = (struct Upnp_Discovery *)Event;
|
||||
+#endif
|
||||
IXML_Document *doc = NULL;
|
||||
+#if UPNP_VERSION >= 10800
|
||||
+ int errCode = UpnpDiscovery_get_ErrCode(d_event);
|
||||
+ if (errCode != UPNP_E_SUCCESS) {
|
||||
+ msg << UpnpGetErrorMessage(errCode) << ".";
|
||||
+#else
|
||||
int ret;
|
||||
if (d_event->ErrCode != UPNP_E_SUCCESS) {
|
||||
msg << UpnpGetErrorMessage(d_event->ErrCode) << ".";
|
||||
+#endif
|
||||
AddDebugLogLineC(logUPnP, msg);
|
||||
}
|
||||
// Get the XML tree device description in doc
|
||||
+#if UPNP_VERSION >= 10800
|
||||
+ const char *location = UpnpDiscovery_get_Location_cstr(d_event);
|
||||
+ int ret = UpnpDownloadXmlDoc(location, &doc);
|
||||
+#else
|
||||
ret = UpnpDownloadXmlDoc(d_event->Location, &doc);
|
||||
+#endif
|
||||
if (ret != UPNP_E_SUCCESS) {
|
||||
msg << "Error retrieving device description from " <<
|
||||
+#if UPNP_VERSION >= 10800
|
||||
+ location << ": " <<
|
||||
+#else
|
||||
d_event->Location << ": " <<
|
||||
+#endif
|
||||
UpnpGetErrorMessage(ret) <<
|
||||
"(" << ret << ").";
|
||||
AddDebugLogLineC(logUPnP, msg);
|
||||
} else {
|
||||
msg2 << "Retrieving device description from " <<
|
||||
+#if UPNP_VERSION >= 10800
|
||||
+ location << ".";
|
||||
+#else
|
||||
d_event->Location << ".";
|
||||
+#endif
|
||||
AddDebugLogLineN(logUPnP, msg2);
|
||||
}
|
||||
if (doc) {
|
||||
@@ -1194,8 +1221,14 @@
|
||||
AddDebugLogLineC(logUPnP, msg);
|
||||
}
|
||||
// Add the root device to our list
|
||||
+#if UPNP_VERSION >= 10800
|
||||
+ int expires = UpnpDiscovery_get_Expires(d_event);
|
||||
+ upnpCP->AddRootDevice(rootDevice, urlBase,
|
||||
+ location, expires);
|
||||
+#else
|
||||
upnpCP->AddRootDevice(rootDevice, urlBase,
|
||||
d_event->Location, d_event->Expires);
|
||||
+#endif
|
||||
}
|
||||
// Free the XML doc tree
|
||||
IXML::Document::Free(doc);
|
||||
@@ -1216,28 +1249,62 @@
|
||||
case UPNP_DISCOVERY_ADVERTISEMENT_BYEBYE: {
|
||||
//fprintf(stderr, "Callback: UPNP_DISCOVERY_ADVERTISEMENT_BYEBYE\n");
|
||||
// UPnP Device Removed
|
||||
+#if UPNP_VERSION >= 10800
|
||||
+ UpnpDiscovery *dab_event = (UpnpDiscovery *)Event;
|
||||
+ int errCode = UpnpDiscovery_get_ErrCode(dab_event);
|
||||
+ if (errCode != UPNP_E_SUCCESS) {
|
||||
+#else
|
||||
struct Upnp_Discovery *dab_event = (struct Upnp_Discovery *)Event;
|
||||
if (dab_event->ErrCode != UPNP_E_SUCCESS) {
|
||||
+#endif
|
||||
msg << "error(UPNP_DISCOVERY_ADVERTISEMENT_BYEBYE): " <<
|
||||
+#if UPNP_VERSION >= 10800
|
||||
+ UpnpGetErrorMessage(errCode) <<
|
||||
+#else
|
||||
UpnpGetErrorMessage(dab_event->ErrCode) <<
|
||||
+#endif
|
||||
".";
|
||||
AddDebugLogLineC(logUPnP, msg);
|
||||
}
|
||||
+#if UPNP_VERSION >= 10800
|
||||
+ std::string devType = UpnpDiscovery_get_DeviceType_cstr(dab_event);
|
||||
+#else
|
||||
std::string devType = dab_event->DeviceType;
|
||||
+#endif
|
||||
// Check for an InternetGatewayDevice and removes it from the list
|
||||
+
|
||||
std::transform(devType.begin(), devType.end(), devType.begin(), tolower);
|
||||
+
|
||||
if (stdStringIsEqualCI(devType, UPnP::Device::IGW)) {
|
||||
+#if UPNP_VERSION >= 10800
|
||||
+ const char *deviceID =
|
||||
+ UpnpDiscovery_get_DeviceID_cstr(dab_event);
|
||||
+ upnpCP->RemoveRootDevice(deviceID);
|
||||
+#else
|
||||
upnpCP->RemoveRootDevice(dab_event->DeviceId);
|
||||
+#endif
|
||||
}
|
||||
break;
|
||||
}
|
||||
case UPNP_EVENT_RECEIVED: {
|
||||
//fprintf(stderr, "Callback: UPNP_EVENT_RECEIVED\n");
|
||||
// Event reveived
|
||||
+#if UPNP_VERSION >= 10800
|
||||
+ UpnpEvent *e_event = (UpnpEvent *)Event;
|
||||
+ int eventKey = UpnpEvent_get_EventKey(e_event);
|
||||
+ IXML_Document *changedVariables =
|
||||
+ UpnpEvent_get_ChangedVariables(e_event);
|
||||
+ const std::string sid = UpnpEvent_get_SID_cstr(e_event);
|
||||
+#else
|
||||
struct Upnp_Event *e_event = (struct Upnp_Event *)Event;
|
||||
const std::string Sid = e_event->Sid;
|
||||
+#endif
|
||||
// Parses the event
|
||||
+#if UPNP_VERSION >= 10800
|
||||
+ upnpCP->OnEventReceived(sid, eventKey, changedVariables);
|
||||
+#else
|
||||
upnpCP->OnEventReceived(Sid, e_event->EventKey, e_event->ChangedVariables);
|
||||
+#endif
|
||||
break;
|
||||
}
|
||||
case UPNP_EVENT_SUBSCRIBE_COMPLETE:
|
||||
@@ -1252,24 +1319,42 @@
|
||||
//fprintf(stderr, "Callback: UPNP_EVENT_RENEWAL_COMPLETE\n");
|
||||
msg << "error(UPNP_EVENT_RENEWAL_COMPLETE): ";
|
||||
upnpEventRenewalComplete:
|
||||
+#if UPNP_VERSION >= 10800
|
||||
+ UpnpEventSubscribe *es_event = (UpnpEventSubscribe *)Event;
|
||||
+ int errCode = UpnpEventSubscribe_get_ErrCode(es_event);
|
||||
+ if (errCode != UPNP_E_SUCCESS) {
|
||||
+#else
|
||||
struct Upnp_Event_Subscribe *es_event =
|
||||
(struct Upnp_Event_Subscribe *)Event;
|
||||
if (es_event->ErrCode != UPNP_E_SUCCESS) {
|
||||
+#endif
|
||||
msg << "Error in Event Subscribe Callback";
|
||||
+#if UPNP_VERSION >= 10800
|
||||
+ UPnP::ProcessErrorMessage(msg.str(), errCode, NULL, NULL);
|
||||
+#else
|
||||
UPnP::ProcessErrorMessage(
|
||||
msg.str(), es_event->ErrCode, NULL, NULL);
|
||||
+#endif
|
||||
} else {
|
||||
#if 0
|
||||
+#if UPNP_VERSION >= 10800
|
||||
+
|
||||
+ const UpnpString *publisherUrl =
|
||||
+ UpnpEventSubscribe_get_PublisherUrl(es_event);
|
||||
+ const char *sid = UpnpEvent_get_SID_cstr(es_event);
|
||||
+ int timeOut = UpnpEvent_get_TimeOut(es_event);
|
||||
+ TvCtrlPointHandleSubscribeUpdate(
|
||||
+ publisherUrl, sid, timeOut);
|
||||
+#else
|
||||
TvCtrlPointHandleSubscribeUpdate(
|
||||
GET_UPNP_STRING(es_event->PublisherUrl),
|
||||
es_event->Sid,
|
||||
es_event->TimeOut );
|
||||
#endif
|
||||
+#endif
|
||||
}
|
||||
-
|
||||
break;
|
||||
}
|
||||
-
|
||||
case UPNP_EVENT_AUTORENEWAL_FAILED:
|
||||
//fprintf(stderr, "Callback: UPNP_EVENT_AUTORENEWAL_FAILED\n");
|
||||
msg << "error(UPNP_EVENT_AUTORENEWAL_FAILED): ";
|
||||
@@ -1280,29 +1365,56 @@
|
||||
msg << "error(UPNP_EVENT_SUBSCRIPTION_EXPIRED): ";
|
||||
msg2 << "UPNP_EVENT_SUBSCRIPTION_EXPIRED: ";
|
||||
upnpEventSubscriptionExpired:
|
||||
+#if UPNP_VERSION >= 10800
|
||||
+ UpnpEventSubscribe *es_event = (UpnpEventSubscribe *)Event;
|
||||
+#else
|
||||
struct Upnp_Event_Subscribe *es_event =
|
||||
(struct Upnp_Event_Subscribe *)Event;
|
||||
+#endif
|
||||
Upnp_SID newSID;
|
||||
memset(newSID, 0, sizeof(Upnp_SID));
|
||||
int TimeOut = 1801;
|
||||
+#if UPNP_VERSION >= 10800
|
||||
+ const char *publisherUrl =
|
||||
+ UpnpEventSubscribe_get_PublisherUrl_cstr(es_event);
|
||||
+#endif
|
||||
int ret = UpnpSubscribe(
|
||||
upnpCP->m_UPnPClientHandle,
|
||||
+#if UPNP_VERSION >= 10800
|
||||
+ publisherUrl,
|
||||
+#else
|
||||
GET_UPNP_STRING(es_event->PublisherUrl),
|
||||
+#endif
|
||||
&TimeOut,
|
||||
newSID);
|
||||
if (ret != UPNP_E_SUCCESS) {
|
||||
msg << "Error Subscribing to EventURL";
|
||||
+#if UPNP_VERSION >= 10800
|
||||
+ int errCode = UpnpEventSubscribe_get_ErrCode(es_event);
|
||||
+#endif
|
||||
UPnP::ProcessErrorMessage(
|
||||
+#if UPNP_VERSION >= 10800
|
||||
+ msg.str(), errCode, NULL, NULL);
|
||||
+#else
|
||||
msg.str(), es_event->ErrCode, NULL, NULL);
|
||||
+#endif
|
||||
} else {
|
||||
ServiceMap::iterator it =
|
||||
+#if UPNP_VERSION >= 10800
|
||||
+ upnpCP->m_ServiceMap.find(publisherUrl);
|
||||
+#else
|
||||
upnpCP->m_ServiceMap.find(GET_UPNP_STRING(es_event->PublisherUrl));
|
||||
+#endif
|
||||
if (it != upnpCP->m_ServiceMap.end()) {
|
||||
CUPnPService &service = *(it->second);
|
||||
service.SetTimeout(TimeOut);
|
||||
service.SetSID(newSID);
|
||||
msg2 << "Re-subscribed to EventURL '" <<
|
||||
+#if UPNP_VERSION >= 10800
|
||||
+ publisherUrl <<
|
||||
+#else
|
||||
GET_UPNP_STRING(es_event->PublisherUrl) <<
|
||||
+#endif
|
||||
"' with SID == '" <<
|
||||
newSID << "'.";
|
||||
AddDebugLogLineC(logUPnP, msg2);
|
||||
@@ -1321,17 +1433,34 @@
|
||||
case UPNP_CONTROL_ACTION_COMPLETE: {
|
||||
//fprintf(stderr, "Callback: UPNP_CONTROL_ACTION_COMPLETE\n");
|
||||
// This is here if we choose to do this asynchronously
|
||||
+#if UPNP_VERSION >= 10800
|
||||
+ UpnpActionComplete *a_event = (UpnpActionComplete *)Event;
|
||||
+ int errCode = UpnpActionComplete_get_ErrCode(a_event);
|
||||
+ IXML_Document *actionResult =
|
||||
+ UpnpActionComplete_get_ActionResult(a_event);
|
||||
+ if (errCode != UPNP_E_SUCCESS) {
|
||||
+#else
|
||||
struct Upnp_Action_Complete *a_event =
|
||||
(struct Upnp_Action_Complete *)Event;
|
||||
if (a_event->ErrCode != UPNP_E_SUCCESS) {
|
||||
+#endif
|
||||
UPnP::ProcessErrorMessage(
|
||||
"UpnpSendActionAsync",
|
||||
+#if UPNP_VERSION >= 10800
|
||||
+ errCode, NULL,
|
||||
+ actionResult);
|
||||
+#else
|
||||
a_event->ErrCode, NULL,
|
||||
a_event->ActionResult);
|
||||
+#endif
|
||||
} else {
|
||||
// Check the response document
|
||||
UPnP::ProcessActionResponse(
|
||||
+#if UPNP_VERSION >= 10800
|
||||
+ actionResult,
|
||||
+#else
|
||||
a_event->ActionResult,
|
||||
+#endif
|
||||
"<UpnpSendActionAsync>");
|
||||
}
|
||||
/* No need for any processing here, just print out results.
|
||||
@@ -1342,22 +1471,43 @@
|
||||
case UPNP_CONTROL_GET_VAR_COMPLETE: {
|
||||
//fprintf(stderr, "Callback: UPNP_CONTROL_GET_VAR_COMPLETE\n");
|
||||
msg << "error(UPNP_CONTROL_GET_VAR_COMPLETE): ";
|
||||
+#if UPNP_VERSION >= 10800
|
||||
+ UpnpStateVarComplete *sv_event = (UpnpStateVarComplete *)Event;
|
||||
+ int errCode = UpnpStateVarComplete_get_ErrCode(sv_event);
|
||||
+ if (errCode != UPNP_E_SUCCESS) {
|
||||
+#else
|
||||
struct Upnp_State_Var_Complete *sv_event =
|
||||
(struct Upnp_State_Var_Complete *)Event;
|
||||
if (sv_event->ErrCode != UPNP_E_SUCCESS) {
|
||||
+#endif
|
||||
msg << "m_UpnpGetServiceVarStatusAsync";
|
||||
UPnP::ProcessErrorMessage(
|
||||
+#if UPNP_VERSION >= 10800
|
||||
+ msg.str(), errCode, NULL, NULL);
|
||||
+#else
|
||||
msg.str(), sv_event->ErrCode, NULL, NULL);
|
||||
+#endif
|
||||
} else {
|
||||
#if 0
|
||||
// Warning: The use of UpnpGetServiceVarStatus and
|
||||
// UpnpGetServiceVarStatusAsync is deprecated by the
|
||||
// UPnP forum.
|
||||
+#if UPNP_VERSION >= 10800
|
||||
+ const char *ctrlUrl =
|
||||
+ UpnpStateVarComplete_get_CtrlUrl(sv_event);
|
||||
+ const char *stateVarName =
|
||||
+ UpnpStateVarComplete_get_StateVarName(sv_event);
|
||||
+ const DOMString currentVal =
|
||||
+ UpnpStateVarComplete_get_CurrentVal(sv_event);
|
||||
+ TvCtrlPointHandleGetVar(
|
||||
+ ctrlUrl, stateVarName, currentVal);
|
||||
+#else
|
||||
TvCtrlPointHandleGetVar(
|
||||
sv_event->CtrlUrl,
|
||||
sv_event->StateVarName,
|
||||
sv_event->CurrentVal );
|
||||
#endif
|
||||
+#endif
|
||||
}
|
||||
break;
|
||||
}
|
||||
diff -Naur a/src/UPnPBase.h b/src/UPnPBase.h
|
||||
--- a/src/UPnPBase.h 2016-10-06 18:49:44.000000000 +0800
|
||||
+++ b/src/UPnPBase.h 2019-12-11 22:16:28.165063153 +0800
|
||||
@@ -489,9 +489,15 @@
|
||||
|
||||
// Callback function
|
||||
static int Callback(
|
||||
+ #if UPNP_VERSION >= 10800
|
||||
+ Upnp_EventType_e EventType,
|
||||
+ const void *Event,
|
||||
+ void *Cookie);
|
||||
+ #else
|
||||
Upnp_EventType EventType,
|
||||
void* Event,
|
||||
void* Cookie);
|
||||
+ #endif
|
||||
|
||||
private:
|
||||
void OnEventReceived(
|
||||
19
amule/patches/007-binutils.patch
Normal file
19
amule/patches/007-binutils.patch
Normal file
@@ -0,0 +1,19 @@
|
||||
--- a/src/libs/common/MuleDebug.cpp 2016-10-06 18:49:44.000000000 +0800
|
||||
+++ b/src/libs/common/MuleDebug.cpp 2021-06-17 02:16:40.000000000 +0800
|
||||
@@ -268,14 +268,14 @@
|
||||
return;
|
||||
}
|
||||
|
||||
- bfd_vma vma = bfd_get_section_vma(abfd, section);
|
||||
+ bfd_vma vma = bfd_section_vma(section);
|
||||
|
||||
unsigned long address = (unsigned long)_address;
|
||||
if (address < vma) {
|
||||
return;
|
||||
}
|
||||
|
||||
- bfd_size_type size = bfd_section_size(abfd, section);
|
||||
+ bfd_size_type size = bfd_section_size(section);
|
||||
if (address > (vma + size)) {
|
||||
return;
|
||||
}
|
||||
16
amule/patches/008-upnp2.patch
Normal file
16
amule/patches/008-upnp2.patch
Normal file
@@ -0,0 +1,16 @@
|
||||
diff --git a/src/UPnPBase.cpp b/src/UPnPBase.cpp
|
||||
index 46ac7451e..dd244e5b0 100644
|
||||
--- a/src/UPnPBase.cpp
|
||||
+++ b/src/UPnPBase.cpp
|
||||
@@ -828,9 +828,9 @@
|
||||
int ret;
|
||||
char *ipAddress = NULL;
|
||||
unsigned short port = 0;
|
||||
- ret = UpnpInit(ipAddress, udpPort);
|
||||
+ ret = UpnpInit2(0, udpPort);
|
||||
if (ret != UPNP_E_SUCCESS) {
|
||||
- msg << "error(UpnpInit): Error code ";
|
||||
+ msg << "error(UpnpInit2): Error code ";
|
||||
goto error;
|
||||
}
|
||||
port = UpnpGetServerPort();
|
||||
55
baidupcs-web/Makefile
Normal file
55
baidupcs-web/Makefile
Normal file
@@ -0,0 +1,55 @@
|
||||
# SPDX-License-Identifier: GPL-3.0-only
|
||||
#
|
||||
# Copyright (C) 2022 ImmortalWrt.org
|
||||
|
||||
include $(TOPDIR)/rules.mk
|
||||
|
||||
PKG_NAME:=baidupcs-web
|
||||
PKG_VERSION:=3.7.4-nnew
|
||||
PKG_RELEASE:=$(AUTORELEASE)
|
||||
|
||||
PKG_SOURCE:=$(PKG_NAME)-$(PKG_VERSION).tar.gz
|
||||
PKG_SOURCE_URL:=https://codeload.github.com/Erope/BaiduPCS-Go/tar.gz/v$(PKG_VERSION)?
|
||||
PKG_HASH:=6efd1c5e4cf5cf876204bed246c70ea0212ad078d4eb7703d7f1179b39551d1d
|
||||
PKG_BUILD_DIR:=$(BUILD_DIR)/BaiduPCS-Go-$(PKG_VERSION)
|
||||
|
||||
PKG_LICENSE:=Apache-2.0
|
||||
PKG_LICENSE_FILES:=LICENSE
|
||||
|
||||
PKG_BUILD_DEPENDS:=golang/host go-rice/host
|
||||
PKG_BUILD_PARALLEL:=1
|
||||
PKG_USE_MIPS16:=0
|
||||
|
||||
GO_PKG:=github.com/Erope/BaiduPCS-Go
|
||||
GO_PKG_LDFLAGS_X:=main.Version=v$(PKG_VERSION)
|
||||
|
||||
include $(INCLUDE_DIR)/package.mk
|
||||
include $(TOPDIR)/feeds/packages/lang/golang/golang-package.mk
|
||||
|
||||
define Package/baidupcs-web
|
||||
SECTION:=net
|
||||
CATEGORY:=Network
|
||||
SUBMENU:=Download Manager
|
||||
TITLE:=A web controller for BaiduPCS-Go
|
||||
URL:=https://github.com/Erope/BaiduPCS-Go
|
||||
DEPENDS:=$(GO_ARCH_DEPENDS) +ca-bundle
|
||||
endef
|
||||
|
||||
define Build/Compile
|
||||
( \
|
||||
pushd "$(PKG_BUILD_DIR)/internal/pcsweb" ; \
|
||||
rice embed-go ; \
|
||||
popd ; \
|
||||
$(call GoPackage/Build/Compile) ; \
|
||||
)
|
||||
endef
|
||||
|
||||
define Package/baidupcs-web/install
|
||||
$(call GoPackage/Package/Install/Bin,$(PKG_INSTALL_DIR))
|
||||
|
||||
$(INSTALL_DIR) $(1)/usr/bin
|
||||
$(INSTALL_BIN) $(GO_PKG_BUILD_BIN_DIR)/BaiduPCS-Go $(1)/usr/bin/baidupcs-web
|
||||
endef
|
||||
|
||||
$(eval $(call GoBinPackage,baidupcs-web))
|
||||
$(eval $(call BuildPackage,baidupcs-web))
|
||||
61
dnsforwarder/Makefile
Normal file
61
dnsforwarder/Makefile
Normal file
@@ -0,0 +1,61 @@
|
||||
#
|
||||
# Copyright (C) 2021 ImmortalWrt
|
||||
# <https://immortalwrt.org>
|
||||
#
|
||||
# This is free software, licensed under the GNU General Public License v3.
|
||||
# See /LICENSE for more information.
|
||||
#
|
||||
|
||||
include $(TOPDIR)/rules.mk
|
||||
|
||||
PKG_NAME:=dnsforwarder
|
||||
PKG_VERSION:=6.1.15
|
||||
PKG_RELEASE:=11
|
||||
|
||||
PKG_SOURCE_PROTO:=git
|
||||
PKG_SOURCE_URL:=https://github.com/1715173329/dnsforwarder.git
|
||||
PKG_SOURCE_DATE:=2018-06-26
|
||||
PKG_SOURCE_VERSION:=587e61ae4d75dc976f538088b715a3c8ee26c144
|
||||
PKG_MIRROR_HASH:=7c141040ae384d254d90b3c3ee502d87330c9fdcd201ff29a669336a27b176d4
|
||||
|
||||
PKG_LICENSE:=GPL-3.0
|
||||
PKG_LICENSE_FILE:=LICENSE
|
||||
PKG_MAINTAINER:=Dennis <openwrt@tossp.com>
|
||||
|
||||
PKG_FIXUP:=autoreconf
|
||||
PKG_BUILD_PARALLEL:=1
|
||||
PKG_INSTALL:=1
|
||||
|
||||
include $(INCLUDE_DIR)/package.mk
|
||||
|
||||
define Package/dnsforwarder
|
||||
SECTION:=net
|
||||
CATEGORY:=Network
|
||||
TITLE:=A simple DNS forwarder
|
||||
URL:=https://github.com/holmium/dnsforwarder
|
||||
DEPENDS:=+coreutils +coreutils-base64 +dnsmasq-full +libpthread +wget-ssl
|
||||
endef
|
||||
|
||||
define Package/dnsforwarder/description
|
||||
Forwarding queries to customized domains (and their subdomains) to specified servers
|
||||
over a specified protocol (UDP or TCP). non-standard ports are supported.
|
||||
endef
|
||||
|
||||
CONFIGURE_ARGS+= --enable-downloader=wget
|
||||
|
||||
define Package/dnsforwarder/install
|
||||
$(INSTALL_DIR) $(1)/usr/bin
|
||||
$(INSTALL_BIN) $(PKG_INSTALL_DIR)/usr/bin/dnsforwarder $(1)/usr/bin/dnsforwarder
|
||||
|
||||
$(INSTALL_DIR) $(1)/etc/config
|
||||
$(INSTALL_CONF) files/etc/config/dnsforwarder $(1)/etc/config/dnsforwarder
|
||||
$(INSTALL_DIR) $(1)/etc/init.d
|
||||
$(INSTALL_BIN) files/etc/init.d/dnsforwarder $(1)/etc/init.d/dnsforwarder
|
||||
|
||||
$(INSTALL_DIR) $(1)/etc/dnsforwarder
|
||||
$(INSTALL_CONF) files/etc/dnsforwarder/gfw.txt $(1)/etc/dnsforwarder/gfw.txt
|
||||
$(INSTALL_DIR) $(1)/usr/share/dnsforwarder
|
||||
$(INSTALL_BIN) files/usr/share/dnsforwarder/gfwlist.sh $(1)/usr/share/dnsforwarder/gfwlist.sh
|
||||
endef
|
||||
|
||||
$(eval $(call BuildPackage,dnsforwarder))
|
||||
79
dnsforwarder/files/etc/config/dnsforwarder
Normal file
79
dnsforwarder/files/etc/config/dnsforwarder
Normal file
@@ -0,0 +1,79 @@
|
||||
|
||||
config arguments
|
||||
option enabled '0'
|
||||
option addr '127.0.0.1:5053'
|
||||
|
||||
config config
|
||||
option cache 'true'
|
||||
option cache_size '102400'
|
||||
option cache_ignore 'false'
|
||||
option gfw 'true'
|
||||
list block_ip '74.125.127.102'
|
||||
list block_ip '74.125.155.102'
|
||||
list block_ip '74.125.39.102'
|
||||
list block_ip '74.125.39.113'
|
||||
list block_ip '209.85.229.138'
|
||||
list block_ip '128.121.126.139'
|
||||
list block_ip '159.106.121.75'
|
||||
list block_ip '169.132.13.103'
|
||||
list block_ip '192.67.198.6'
|
||||
list block_ip '202.106.1.2'
|
||||
list block_ip '202.181.7.85'
|
||||
list block_ip '203.161.230.171'
|
||||
list block_ip '203.98.7.65'
|
||||
list block_ip '207.12.88.98'
|
||||
list block_ip '208.56.31.43'
|
||||
list block_ip '209.145.54.50'
|
||||
list block_ip '209.220.30.174'
|
||||
list block_ip '209.36.73.33'
|
||||
list block_ip '211.94.66.147'
|
||||
list block_ip '213.169.251.35'
|
||||
list block_ip '216.221.188.182'
|
||||
list block_ip '216.234.179.13'
|
||||
list block_ip '243.185.187.39'
|
||||
list block_ip '37.61.54.158'
|
||||
list block_ip '4.36.66.178'
|
||||
list block_ip '46.82.174.68'
|
||||
list block_ip '59.24.3.173'
|
||||
list block_ip '64.33.88.161'
|
||||
list block_ip '64.33.99.47'
|
||||
list block_ip '64.66.163.251'
|
||||
list block_ip '65.104.202.252'
|
||||
list block_ip '65.160.219.113'
|
||||
list block_ip '66.45.252.237'
|
||||
list block_ip '69.55.52.253'
|
||||
list block_ip '72.14.205.104'
|
||||
list block_ip '72.14.205.99'
|
||||
list block_ip '78.16.49.15'
|
||||
list block_ip '8.7.198.45'
|
||||
list block_ip '93.46.8.89'
|
||||
list block_ip '37.61.54.158'
|
||||
list block_ip '243.185.187.39'
|
||||
list block_ip '190.93.247.4'
|
||||
list block_ip '190.93.246.4'
|
||||
list block_ip '190.93.245.4'
|
||||
list block_ip '190.93.244.4'
|
||||
list block_ip '65.49.2.178'
|
||||
list block_ip '189.163.17.5'
|
||||
list block_ip '23.89.5.60'
|
||||
list block_ip '49.2.123.56'
|
||||
list block_ip '54.76.135.1'
|
||||
list block_ip '77.4.7.92'
|
||||
list block_ip '118.5.49.6'
|
||||
list block_ip '159.24.3.173'
|
||||
list block_ip '188.5.4.96'
|
||||
list block_ip '197.4.4.12'
|
||||
list block_ip '220.250.64.24'
|
||||
list block_ip '243.185.187.30'
|
||||
list block_ip '249.129.46.48'
|
||||
list block_ip '253.157.14.165'
|
||||
option block_ipv6 'false'
|
||||
list cache_control 'tossp.com $orig'
|
||||
list cache_control '* fixed 3600'
|
||||
option log 'false'
|
||||
list udp_group '9.9.9.9,119.29.29.29,223.5.5.5,114.114.114.114 * on'
|
||||
option block_negative_resp 'true'
|
||||
list udp_local '0.0.0.0:5053'
|
||||
list udp_local '[::0]:5053'
|
||||
option domain_statistic 'false'
|
||||
|
||||
5605
dnsforwarder/files/etc/dnsforwarder/gfw.txt
Normal file
5605
dnsforwarder/files/etc/dnsforwarder/gfw.txt
Normal file
File diff suppressed because it is too large
Load Diff
260
dnsforwarder/files/etc/init.d/dnsforwarder
Executable file
260
dnsforwarder/files/etc/init.d/dnsforwarder
Executable file
@@ -0,0 +1,260 @@
|
||||
#!/bin/sh /etc/rc.common
|
||||
|
||||
START=60
|
||||
|
||||
EXTRA_COMMANDS="makeconfig makegfwlist health"
|
||||
|
||||
CRON_FILE=/etc/crontabs/root
|
||||
PID_PATH=/var/run/dnsforwarder
|
||||
PID_FILE=${PID_PATH}/dns.pid
|
||||
DNSFORWARDER_CONF=/tmp/dnsforwarder.conf
|
||||
|
||||
add_cron()
|
||||
{
|
||||
sed -i '/dnsforwarder/d' $CRON_FILE
|
||||
echo '*/5 * * * * /etc/init.d/dnsforwarder health' >> $CRON_FILE
|
||||
echo '0 1 * * 0 /etc/init.d/dnsforwarder makegfwlist' >> $CRON_FILE
|
||||
crontab $CRON_FILE
|
||||
}
|
||||
|
||||
del_cron()
|
||||
{
|
||||
sed -i '/dnsforwarder/d' $CRON_FILE
|
||||
/etc/init.d/cron restart
|
||||
}
|
||||
|
||||
fixturboacc(){
|
||||
dns=$(uci get turboacc.config.dns_caching 2>/dev/null)
|
||||
if [ $dns -eq 1 ]; then
|
||||
uci set turboacc.config.dns_caching=0 && uci commit turboacc
|
||||
/etc/init.d/turboacc restart
|
||||
fi
|
||||
}
|
||||
|
||||
makelist() {
|
||||
[ -z "$2" ] && return
|
||||
local i
|
||||
local t="$1"; shift
|
||||
for i in "$@"
|
||||
do
|
||||
echo "$t $i"
|
||||
done
|
||||
}
|
||||
|
||||
health(){
|
||||
rm /var/log/dnsforwarder.log.* 2>/dev/null
|
||||
local pid=$(cat ${PID_FILE} 2>/dev/null)
|
||||
if [ -n "${pid}" -a -d /proc/$pid ]; then
|
||||
echo "[health] process exists ${pid}"
|
||||
else
|
||||
echo "[health] Dnsforwarder is not running ${pid}"
|
||||
start
|
||||
fi
|
||||
}
|
||||
|
||||
|
||||
makegfwlist(){
|
||||
local GFW_FILE='/etc/dnsforwarder/gfw.txt'
|
||||
local GFW_TMP_FILE='/tmp/dnsforwarder-gfw.old'
|
||||
local TSTIME=`date '+%Y-%m-%d %H:%M:%S'`
|
||||
touch ${GFW_TMP_FILE}
|
||||
cat /etc/config/gfw.list 2>/dev/null > /tmp/edf.ts
|
||||
cat /etc/dnsmasq.ssr/gfw_base.conf 2>/dev/null | awk -F '/' '{print $2}' | sed 's/^.//g' >> /tmp/edf.ts
|
||||
cat /etc/dnsmasq.ssr/gfw_list.conf 2>/dev/null | awk -F '/' '{print $2}' | sed 's/^.//g' >> /tmp/edf.ts
|
||||
sort /tmp/edf.ts | uniq > /tmp/edf.ts
|
||||
/usr/share/dnsforwarder/gfwlist.sh -i -l -o /tmp/dnsforwarder-gfw.tmp --extra-domain-file /tmp/edf.ts
|
||||
if [ $? != 0 ]; then
|
||||
echo 'Failed to fetch gfwlist'
|
||||
logger -t Failed to fetch gfwlist
|
||||
return 2
|
||||
fi
|
||||
local gfw=$(cat /tmp/dnsforwarder-gfw.tmp)
|
||||
echo "# GenerationAt TS_BUILD_TIME" > ${GFW_TMP_FILE}.new
|
||||
echo "protocol tcp" >> ${GFW_TMP_FILE}.new
|
||||
echo "server 8.8.8.8,8.8.4.4,1.1.1.1,1.0.0.1,208.67.222.222,208.67.220.220,209.244.0.3,209.244.0.4,8.26.56.26,8.20.247.20,156.154.70.1,156.154.71.1,199.85.126.10" >> ${GFW_TMP_FILE}.new
|
||||
echo -e 'proxy no\n\n\n' >> ${GFW_TMP_FILE}.new
|
||||
echo "${gfw}" >> ${GFW_TMP_FILE}.new
|
||||
if [ "`cat ${GFW_TMP_FILE}.new | md5sum`" == "`cat ${GFW_TMP_FILE} | md5sum`" ]; then
|
||||
printf "[\e[32m%s\e[0m]\n" "hold"
|
||||
else
|
||||
cp ${GFW_TMP_FILE}.new ${GFW_TMP_FILE}
|
||||
cp ${GFW_TMP_FILE} ${GFW_FILE}
|
||||
sed -i "s/TS_BUILD_TIME/${TSTIME}/g" ${GFW_FILE}
|
||||
printf "[\e[33m%s\e[0m]" "PID"
|
||||
restart
|
||||
fi
|
||||
}
|
||||
|
||||
makeconfig () {
|
||||
config_load dnsforwarder
|
||||
|
||||
local log=$(uci get dnsforwarder.@config[0].log 2>/dev/null)
|
||||
local log_size=$(uci get dnsforwarder.@config[0].log_size 2>/dev/null)
|
||||
|
||||
local gfw=$(uci get dnsforwarder.@config[0].gfw 2>/dev/null)
|
||||
|
||||
local udp_local=$(uci -d ',' get dnsforwarder.@config[0].udp_local 2>/dev/null)
|
||||
local udp_local_list=$(uci get dnsforwarder.@config[0].udp_local 2>/dev/null)
|
||||
local tcp_group=$(uci get dnsforwarder.@config[0].tcp_group 2>/dev/null)
|
||||
local udp_group=$(uci get dnsforwarder.@config[0].udp_group 2>/dev/null)
|
||||
local group_file=$(uci get dnsforwarder.@config[0].group_file 2>/dev/null)
|
||||
local block_ip=$(uci -d ',' get dnsforwarder.@config[0].block_ip 2>/dev/null)
|
||||
local ip_substituting=$(uci -d ',' get dnsforwarder.@config[0].ip_substituting 2>/dev/null)
|
||||
local block_negative_resp=$(uci get dnsforwarder.@config[0].block_negative_resp 2>/dev/null)
|
||||
local append_host=$(uci get dnsforwarder.@config[0].append_host 2>/dev/null)
|
||||
local block_ipv6=$(uci get dnsforwarder.@config[0].block_ipv6 2>/dev/null)
|
||||
|
||||
local cache=$(uci get dnsforwarder.@config[0].cache 2>/dev/null)
|
||||
local cache_size=$(uci get dnsforwarder.@config[0].cache_size 2>/dev/null)
|
||||
local cache_ignore=$(uci get dnsforwarder.@config[0].cache_ignore 2>/dev/null)
|
||||
local cache_control=$(uci get dnsforwarder.@config[0].cache_control 2>/dev/null)
|
||||
|
||||
local domain_statistic=$(uci get dnsforwarder.@config[0].domain_statistic 2>/dev/null)
|
||||
local udp_local_addr=$(uci get dnsforwarder.@arguments[0].addr 2>/dev/null)
|
||||
udp_local_addr=${udp_local_addr/:/#}
|
||||
|
||||
echo "LogOn ${log}" > $DNSFORWARDER_CONF
|
||||
if [ $log = "true" ]; then
|
||||
rm /var/log/dnsforwarder.log.* 2>/dev/null
|
||||
echo '' > /var/log/dnsforwarder.log
|
||||
echo "LogFileThresholdLength ${log_size}" >> $DNSFORWARDER_CONF
|
||||
echo "LogFileFolder /var/log" >> $DNSFORWARDER_CONF
|
||||
fi
|
||||
|
||||
[ -n "$udp_local" ] && echo "UDPLocal ${udp_local}" >> $DNSFORWARDER_CONF
|
||||
[ -n "$udp_local_addr" ] && eval "makelist 'server=' $udp_local_addr" > /tmp/dnsmasq.dnsforwarder.conf
|
||||
sed -i "s/ //g" /tmp/dnsmasq.dnsforwarder.conf
|
||||
|
||||
eval "makelist 'TCPGroup' $tcp_group" >> $DNSFORWARDER_CONF
|
||||
eval "makelist 'UDPGroup' $udp_group" >> $DNSFORWARDER_CONF
|
||||
eval "makelist 'GroupFile' $group_file" >> $DNSFORWARDER_CONF
|
||||
|
||||
if [ $gfw = "true" ]; then
|
||||
echo 'GroupFile /etc/dnsforwarder/gfw.txt' >> $DNSFORWARDER_CONF
|
||||
fi
|
||||
|
||||
echo "BlockIP ${block_ip}" >> $DNSFORWARDER_CONF
|
||||
eval "makelist 'IPSubstituting' $ip_substituting" >> $DNSFORWARDER_CONF
|
||||
echo "BlockNegativeResponse ${block_negative_resp}" >> $DNSFORWARDER_CONF
|
||||
eval "makelist 'AppendHosts' $append_host" >> $DNSFORWARDER_CONF
|
||||
echo "BlockIpv6WhenIpv4Exists ${block_ipv6}" >> $DNSFORWARDER_CONF
|
||||
|
||||
echo "UseCache ${cache}" >> $DNSFORWARDER_CONF
|
||||
if [ $cache = "true" ]; then
|
||||
echo "CacheSize ${cache_size}" >> $DNSFORWARDER_CONF
|
||||
echo "MemoryCache false" >> $DNSFORWARDER_CONF
|
||||
echo "CacheFile /tmp/dnsforwarder.cache" >> $DNSFORWARDER_CONF
|
||||
echo "IgnoreTTL ${cache_ignore}" >> $DNSFORWARDER_CONF
|
||||
eval "makelist 'CacheControl' $cache_control" >> $DNSFORWARDER_CONF
|
||||
echo "ReloadCache true" >> $DNSFORWARDER_CONF
|
||||
echo "OverwriteCache true" >> $DNSFORWARDER_CONF
|
||||
fi
|
||||
echo "DomainStatistic ${domain_statistic}" >> $DNSFORWARDER_CONF
|
||||
if [ $domain_statistic = "true" ]; then
|
||||
touch /tmp/dnsforwarder-statistic.html
|
||||
mkdir -p /root/.dnsforwarder
|
||||
rm /root/.dnsforwarder/statistic.html 2 > /dev/null
|
||||
ln -s /tmp/dnsforwarder-statistic.html /root/.dnsforwarder/statistic.html
|
||||
local domain_statistic_tag='<!-- TS DNSFORWARDER -->'
|
||||
echo "DomainStatisticTempletFile /tmp/dnsforwarder-statistic.html" >> $DNSFORWARDER_CONF
|
||||
echo "StatisticInsertionPosition ${domain_statistic_tag}" >> $DNSFORWARDER_CONF
|
||||
echo "StatisticUpdateInterval 60" >> $DNSFORWARDER_CONF
|
||||
echo "${domain_statistic_tag}" > /tmp/dnsforwarder-statistic.html
|
||||
fi
|
||||
}
|
||||
|
||||
start()
|
||||
{
|
||||
echo luci for dnsforwarder
|
||||
local vt_enabled=$(uci get dnsforwarder.@arguments[0].enabled 2>/dev/null)
|
||||
if [ $vt_enabled = 0 ]; then
|
||||
echo dnsforwarder is not enabled
|
||||
exit
|
||||
fi
|
||||
makeconfig
|
||||
fixturboacc
|
||||
dnsforwarder -f $DNSFORWARDER_CONF -d
|
||||
sleep 10
|
||||
mkdir -p ${PID_PATH}
|
||||
pid=$(ps | awk '$5 ~ /\[dnsforwarder\]/ {print $1}')
|
||||
echo "dnsforwarder running pid is ${pid}"
|
||||
logger -t The pid of dnsforwarder is ${PID_FILE} ${pid}
|
||||
echo ${pid} > ${PID_FILE}
|
||||
/etc/init.d/dnsforwarder enable
|
||||
local dnsmasq=$(uci get dnsforwarder.@arguments[0].dnsmasq 2>/dev/null)
|
||||
local addr=$(uci get dnsforwarder.@arguments[0].addr 2>/dev/null)
|
||||
[ -n "${addr}" ] && addr=${addr/:/#}
|
||||
|
||||
if [ "${dnsmasq}" = "1" ]; then
|
||||
uci delete dhcp.@dnsmasq[0].server 2>/dev/null
|
||||
# uci add_list dhcp.@dnsmasq[0].server=$addr
|
||||
uci delete dhcp.@dnsmasq[0].resolvfile 2>/dev/null
|
||||
uci set dhcp.@dnsmasq[0].noresolv=1
|
||||
uci set dhcp.@dnsmasq[0].serversfile=/tmp/dnsmasq.dnsforwarder.conf
|
||||
uci commit dhcp
|
||||
/etc/init.d/dnsmasq restart
|
||||
fi
|
||||
local dnsmasq_server_addr=$(uci get dhcp.@dnsmasq[0].server 2>/dev/null)
|
||||
if [ -n "${dnsmasq_server_addr}" ]; then
|
||||
uci set dhcp.@dnsmasq[0].noresolv=1
|
||||
uci commit dhcp
|
||||
/etc/init.d/dnsmasq restart
|
||||
fi
|
||||
add_cron
|
||||
}
|
||||
|
||||
stop()
|
||||
{
|
||||
del_cron
|
||||
logger -t stopping dnsforwarder
|
||||
local addr=$(uci get dnsforwarder.@arguments[0].addr 2>/dev/null)
|
||||
local dnsmasq=$(uci get dnsforwarder.@arguments[0].dnsmasq 2>/dev/null)
|
||||
addr=${addr/:/#}
|
||||
if [ "${dnsmasq}" = "1" ]; then
|
||||
uci del_list dhcp.@dnsmasq[0].server=$addr 2>/dev/null
|
||||
fi
|
||||
uci set dhcp.@dnsmasq[0].resolvfile=/tmp/resolv.conf.d/resolv.conf.auto 2>/dev/null
|
||||
uci delete dhcp.@dnsmasq[0].noresolv 2>/dev/null
|
||||
uci delete dhcp.@dnsmasq[0].serversfile 2>/dev/null
|
||||
uci commit dhcp
|
||||
/etc/init.d/dnsmasq restart
|
||||
[ -e ${PID_FILE} ] && {
|
||||
pid=$(cat ${PID_FILE})
|
||||
logger -t killing dnsforwarder pid ${pid}
|
||||
echo killing dnsforwarder pid ${pid}
|
||||
kill ${pid}
|
||||
rm -f ${PID_FILE}
|
||||
} || {
|
||||
logger -t Cannot find dnsforwarder pid file
|
||||
}
|
||||
}
|
||||
|
||||
restart()
|
||||
{
|
||||
pid=$(cat ${PID_FILE} 2>/dev/null)
|
||||
echo Dnsforwarder pid file is ${pid}
|
||||
[ -n "$pid" ] && {
|
||||
echo stopping pid ${pid}
|
||||
logger -t There is dnsforwarder pid ${pid}
|
||||
stop
|
||||
} || {
|
||||
logger -t Dnsforwarder is not running
|
||||
}
|
||||
sleep 7
|
||||
local vt_enabled=$(uci get dnsforwarder.@arguments[0].enabled 2>/dev/null)
|
||||
echo dnsforwarder status is ${vt_enabled}
|
||||
logger -t Dnsforwarder is initializing enabled is ${vt_enabled}
|
||||
if [ ${vt_enabled} = 1 ]; then
|
||||
[ -n "$pid" ] && {
|
||||
logger -t There is dnsforwarder pid ${pid}
|
||||
stop
|
||||
} || {
|
||||
logger -t Dnsforwarder is not running
|
||||
}
|
||||
|
||||
logger -t Restarting dnsforwarder
|
||||
start
|
||||
else
|
||||
/etc/init.d/dnsforwarder disable
|
||||
fi
|
||||
}
|
||||
313
dnsforwarder/files/usr/share/dnsforwarder/gfwlist.sh
Executable file
313
dnsforwarder/files/usr/share/dnsforwarder/gfwlist.sh
Executable file
@@ -0,0 +1,313 @@
|
||||
#/bin/sh
|
||||
|
||||
# Name: gfwlist2dnsmasq.sh
|
||||
# Desription: A shell script which convert gfwlist into dnsmasq rules.
|
||||
# Version: 0.8.0 (2017.12.25)
|
||||
# Author: Cokebar Chi
|
||||
# Website: https://github.com/cokebar
|
||||
|
||||
_green() {
|
||||
printf '\033[1;31;32m'
|
||||
printf -- "%b" "$1"
|
||||
printf '\033[0m'
|
||||
}
|
||||
|
||||
_red() {
|
||||
printf '\033[1;31;31m'
|
||||
printf -- "%b" "$1"
|
||||
printf '\033[0m'
|
||||
}
|
||||
|
||||
_yellow() {
|
||||
printf '\033[1;31;33m'
|
||||
printf -- "%b" "$1"
|
||||
printf '\033[0m'
|
||||
}
|
||||
|
||||
usage() {
|
||||
cat <<-EOF
|
||||
|
||||
Name: gfwlist2dnsmasq.sh
|
||||
Desription: A shell script which convert gfwlist into dnsmasq rules.
|
||||
Version: 0.8.0 (2017.12.25)
|
||||
Author: Cokebar Chi
|
||||
Website: https://github.com/cokebar
|
||||
|
||||
Usage: sh gfwlist2dnsmasq.sh [options] -o FILE
|
||||
Valid options are:
|
||||
-d, --dns <dns_ip>
|
||||
DNS IP address for the GfwList Domains (Default: 127.0.0.1)
|
||||
-p, --port <dns_port>
|
||||
DNS Port for the GfwList Domains (Default: 5353)
|
||||
-s, --ipset <ipset_name>
|
||||
Ipset name for the GfwList domains
|
||||
(If not given, ipset rules will not be generated.)
|
||||
-o, --output <FILE>
|
||||
/path/to/output_filename
|
||||
-i, --insecure
|
||||
Force bypass certificate validation (insecure)
|
||||
-l, --domain-list
|
||||
Convert Gfwlist into domain list instead of dnsmasq rules
|
||||
(If this option is set, DNS IP/Port & ipset are not needed)
|
||||
--exclude-domain-file <FILE>
|
||||
Delete specific domains in the result from a domain list text file
|
||||
Please put one domain per line
|
||||
--extra-domain-file <FILE>
|
||||
Include extra domains to the result from a domain list text file
|
||||
This file will be processed after the exclude-domain-file
|
||||
Please put one domain per line
|
||||
-h, --help
|
||||
Usage
|
||||
EOF
|
||||
exit $1
|
||||
}
|
||||
|
||||
clean_and_exit(){
|
||||
# Clean up temp files
|
||||
printf 'Cleaning up... '
|
||||
rm -rf $TMP_DIR
|
||||
_green 'Done\n\n'
|
||||
[ $1 -eq 0 ] && _green 'Job Finished.\n\n' || _red 'Exit with Error code '$1'.\n'
|
||||
exit $1
|
||||
}
|
||||
|
||||
check_depends(){
|
||||
which sed base64 curl >/dev/null
|
||||
if [ $? != 0 ]; then
|
||||
_red 'Error: Missing Dependency.\nPlease check whether you have the following binaries on you system:\nwhich, sed, base64, curl.\n'
|
||||
exit 3
|
||||
fi
|
||||
|
||||
SYS_KERNEL=`uname -s`
|
||||
if [ $SYS_KERNEL = "Darwin" -o $SYS_KERNEL = "FreeBSD" ]; then
|
||||
BASE64_DECODE='base64 -D'
|
||||
SED_ERES='sed -E'
|
||||
else
|
||||
BASE64_DECODE='base64 -d'
|
||||
SED_ERES='sed -r'
|
||||
fi
|
||||
}
|
||||
|
||||
get_args(){
|
||||
OUT_TYPE='DNSMASQ_RULES'
|
||||
DNS_IP='127.0.0.1'
|
||||
DNS_PORT='5353'
|
||||
IPSET_NAME=''
|
||||
FILE_FULLPATH=''
|
||||
CURL_EXTARG=''
|
||||
WITH_IPSET=0
|
||||
EXTRA_DOMAIN_FILE=''
|
||||
EXCLUDE_DOMAIN_FILE=''
|
||||
IPV4_PATTERN='^((2[0-4][0-9]|25[0-5]|[01]?[0-9][0-9]?)\.){3}(2[0-4][0-9]|25[0-5]|[01]?[0-9][0-9]?)$'
|
||||
IPV6_PATTERN='^((([0-9A-Fa-f]{1,4}:){7}([0-9A-Fa-f]{1,4}|:))|(([0-9A-Fa-f]{1,4}:){6}(:[0-9A-Fa-f]{1,4}|((25[0-5]|2[0-4][0-9]|1[0-9][0-9]|[1-9]?[0-9])(\.(25[0-5]|2[0-4][0-9]|1[0-9][0-9]|[1-9]?[0-9])){3})|:))|(([0-9A-Fa-f]{1,4}:){5}(((:[0-9A-Fa-f]{1,4}){1,2})|:((25[0-5]|2[0-4][0-9]|1[0-9][0-9]|[1-9]?[0-9])(\.(25[0-5]|2[0-4][0-9]|1[0-9][0-9]|[1-9]?[0-9])){3})|:))|(([0-9A-Fa-f]{1,4}:){4}(((:[0-9A-Fa-f]{1,4}){1,3})|((:[0-9A-Fa-f]{1,4})?:((25[0-5]|2[0-4][0-9]|1[0-9][0-9]|[1-9]?[0-9])(\.(25[0-5]|2[0-4][0-9]|1[0-9][0-9]|[1-9]?[0-9])){3}))|:))|(([0-9A-Fa-f]{1,4}:){3}(((:[0-9A-Fa-f]{1,4}){1,4})|((:[0-9A-Fa-f]{1,4}){0,2}:((25[0-5]|2[0-4][0-9]|1[0-9][0-9]|[1-9]?[0-9])(\.(25[0-5]|2[0-4][0-9]|1[0-9][0-9]|[1-9]?[0-9])){3}))|:))|(([0-9A-Fa-f]{1,4}:){2}(((:[0-9A-Fa-f]{1,4}){1,5})|((:[0-9A-Fa-f]{1,4}){0,3}:((25[0-5]|2[0-4][0-9]|1[0-9][0-9]|[1-9]?[0-9])(\.(25[0-5]|2[0-4][0-9]|1[0-9][0-9]|[1-9]?[0-9])){3}))|:))|(([0-9A-Fa-f]{1,4}:){1}(((:[0-9A-Fa-f]{1,4}){1,6})|((:[0-9A-Fa-f]{1,4}){0,4}:((25[0-5]|2[0-4][0-9]|1[0-9][0-9]|[1-9]?[0-9])(\.(25[0-5]|2[0-4][0-9]|1[0-9][0-9]|[1-9]?[0-9])){3}))|:))|(:(((:[0-9A-Fa-f]{1,4}){1,7})|((:[0-9A-Fa-f]{1,4}){0,5}:((25[0-5]|2[0-4][0-9]|1[0-9][0-9]|[1-9]?[0-9])(\.(25[0-5]|2[0-4][0-9]|1[0-9][0-9]|[1-9]?[0-9])){3}))|:)))(%.+)?$'
|
||||
|
||||
while [ ${#} -gt 0 ]; do
|
||||
case "${1}" in
|
||||
--help | -h)
|
||||
usage 0
|
||||
;;
|
||||
--domain-list | -l)
|
||||
OUT_TYPE='DOMAIN_LIST'
|
||||
;;
|
||||
--insecure | -i)
|
||||
CURL_EXTARG='--insecure'
|
||||
;;
|
||||
--dns | -d)
|
||||
DNS_IP="$2"
|
||||
shift
|
||||
;;
|
||||
--port | -p)
|
||||
DNS_PORT="$2"
|
||||
shift
|
||||
;;
|
||||
--ipset | -s)
|
||||
IPSET_NAME="$2"
|
||||
shift
|
||||
;;
|
||||
--output | -o)
|
||||
OUT_FILE="$2"
|
||||
shift
|
||||
;;
|
||||
--extra-domain-file)
|
||||
EXTRA_DOMAIN_FILE="$2"
|
||||
shift
|
||||
;;
|
||||
--exclude-domain-file)
|
||||
EXCLUDE_DOMAIN_FILE="$2"
|
||||
shift
|
||||
;;
|
||||
*)
|
||||
_red "Invalid argument: $1"
|
||||
usage 1
|
||||
;;
|
||||
esac
|
||||
shift 1
|
||||
done
|
||||
|
||||
# Check path & file name
|
||||
if [ -z $OUT_FILE ]; then
|
||||
_red 'Error: Please specify the path to the output file(using -o/--output argument).\n'
|
||||
exit 1
|
||||
else
|
||||
if [ -z ${OUT_FILE##*/} ]; then
|
||||
_red 'Error: '$OUT_FILE' is a path, not a file.\n'
|
||||
exit 1
|
||||
else
|
||||
if [ ${OUT_FILE}a != ${OUT_FILE%/*}a ] && [ ! -d ${OUT_FILE%/*} ]; then
|
||||
_red 'Error: Folder do not exist: '${OUT_FILE%/*}'\n'
|
||||
exit 1
|
||||
fi
|
||||
fi
|
||||
fi
|
||||
|
||||
if [ $OUT_TYPE = 'DNSMASQ_RULES' ]; then
|
||||
# Check DNS IP
|
||||
IPV4_TEST=$(echo $DNS_IP | grep -E $IPV4_PATTERN)
|
||||
IPV6_TEST=$(echo $DNS_IP | grep -E $IPV6_PATTERN)
|
||||
if [ "$IPV4_TEST" != "$DNS_IP" -a "$IPV6_TEST" != "$DNS_IP" ]; then
|
||||
_red 'Error: Please enter a valid DNS server IP address.\n'
|
||||
exit 1
|
||||
fi
|
||||
|
||||
# Check DNS port
|
||||
if [ $DNS_PORT -lt 1 -o $DNS_PORT -gt 65535 ]; then
|
||||
_red 'Error: Please enter a valid DNS server port.\n'
|
||||
exit 1
|
||||
fi
|
||||
|
||||
# Check ipset name
|
||||
if [ -z $IPSET_NAME ]; then
|
||||
WITH_IPSET=0
|
||||
else
|
||||
IPSET_TEST=$(echo $IPSET_NAME | grep -E '^\w+$')
|
||||
if [ "$IPSET_TEST" != "$IPSET_NAME" ]; then
|
||||
_red 'Error: Please enter a valid IP set name.\n'
|
||||
exit 1
|
||||
else
|
||||
WITH_IPSET=1
|
||||
fi
|
||||
fi
|
||||
fi
|
||||
|
||||
if [ ! -z $EXTRA_DOMAIN_FILE ] && [ ! -f $EXTRA_DOMAIN_FILE ]; then
|
||||
_yellow 'WARNING:\nExtra domain file does not exist, ignored.\n\n'
|
||||
EXTRA_DOMAIN_FILE=''
|
||||
fi
|
||||
|
||||
if [ ! -z $EXCLUDE_DOMAIN_FILE ] && [ ! -f $EXCLUDE_DOMAIN_FILE ]; then
|
||||
_yellow 'WARNING:\nExclude domain file does not exist, ignored.\n\n'
|
||||
EXCLUDE_DOMAIN_FILE=''
|
||||
fi
|
||||
}
|
||||
|
||||
|
||||
|
||||
process(){
|
||||
# Set Global Var
|
||||
BASE_URL='https://github.com/gfwlist/gfwlist/raw/master/gfwlist.txt'
|
||||
TMP_DIR=`mktemp -d /tmp/gfwlist2dnsmasq.XXXXXX`
|
||||
BASE64_FILE="$TMP_DIR/base64.txt"
|
||||
GFWLIST_FILE="$TMP_DIR/gfwlist.txt"
|
||||
DOMAIN_TEMP_FILE="$TMP_DIR/gfwlist2domain.tmp"
|
||||
DOMAIN_FILE="$TMP_DIR/gfwlist2domain.txt"
|
||||
CONF_TMP_FILE="$TMP_DIR/gfwlist.conf.tmp"
|
||||
OUT_TMP_FILE="$TMP_DIR/gfwlist.out.tmp"
|
||||
|
||||
# Fetch GfwList and decode it into plain text
|
||||
printf 'Fetching GfwList... '
|
||||
local tscurl='curl -L --connect-timeout 5 -m 300 --retry 3 --retry-delay 1'
|
||||
$tscurl $CURL_EXTARG -o$BASE64_FILE $BASE_URL \
|
||||
|| $tscurl $CURL_EXTARG -o$BASE64_FILE https://gitlab.com/gfwlist/gfwlist/raw/master/gfwlist.txt \
|
||||
|| $tscurl $CURL_EXTARG -o$BASE64_FILE https://git.tuxfamily.org/gfwlist/gfwlist.git/plain/gfwlist.txt \
|
||||
|| $tscurl $CURL_EXTARG -o$BASE64_FILE https://pagure.io/gfwlist/raw/master/f/gfwlist.txt \
|
||||
|| $tscurl $CURL_EXTARG -o$BASE64_FILE http://repo.or.cz/gfwlist.git/blob_plain/HEAD:/gfwlist.txt \
|
||||
|| $tscurl $CURL_EXTARG -o$BASE64_FILE https://bitbucket.org/gfwlist/gfwlist/raw/HEAD/gfwlist.txt \
|
||||
|| $tscurl $CURL_EXTARG -o$BASE64_FILE $BASE_URL
|
||||
if [ $? != 0 ]; then
|
||||
_red '\nFailed to fetch gfwlist.txt. Please check your Internet connection.\n'
|
||||
clean_and_exit 2
|
||||
fi
|
||||
$BASE64_DECODE $BASE64_FILE > $GFWLIST_FILE || ( _red 'Failed to decode gfwlist.txt. Quit.\n'; clean_and_exit 2 )
|
||||
_green 'Done.\n\n'
|
||||
|
||||
# Convert
|
||||
IGNORE_PATTERN='^\!|\[|^@@|(https?://){0,1}[0-9]+\.[0-9]+\.[0-9]+\.[0-9]+'
|
||||
HEAD_FILTER_PATTERN='s#^(\|\|?)?(https?://)?##g'
|
||||
TAIL_FILTER_PATTERN='s#/.*$|%2F.*$##g'
|
||||
DOMAIN_PATTERN='([a-zA-Z0-9][-a-zA-Z0-9]*(\.[a-zA-Z0-9][-a-zA-Z0-9]*)+)'
|
||||
HANDLE_WILDCARD_PATTERN='s#^(([a-zA-Z0-9]*\*[-a-zA-Z0-9]*)?(\.))?([a-zA-Z0-9][-a-zA-Z0-9]*(\.[a-zA-Z0-9][-a-zA-Z0-9]*)+)(\*)?#\4#g'
|
||||
|
||||
printf 'Converting GfwList to ' && _green $OUT_TYPE && printf ' ...\n'
|
||||
_yellow '\nWARNING:\nThe following lines in GfwList contain regex, and might be ignored:\n\n'
|
||||
cat $GFWLIST_FILE | grep -n '^/.*$'
|
||||
_yellow "\nThis script will try to convert some of the regex rules. But you should know this may not be a equivalent conversion.\nIf there's regex rules which this script do not deal with, you should add the domain manually to the list.\n\n"
|
||||
grep -vE $IGNORE_PATTERN $GFWLIST_FILE | $SED_ERES $HEAD_FILTER_PATTERN | $SED_ERES $TAIL_FILTER_PATTERN | grep -E $DOMAIN_PATTERN | $SED_ERES $HANDLE_WILDCARD_PATTERN > $DOMAIN_TEMP_FILE
|
||||
|
||||
printf 'google.com\ngoogle.ad\ngoogle.ae\ngoogle.com.af\ngoogle.com.ag\ngoogle.com.ai\ngoogle.al\ngoogle.am\ngoogle.co.ao\ngoogle.com.ar\ngoogle.as\ngoogle.at\ngoogle.com.au\ngoogle.az\ngoogle.ba\ngoogle.com.bd\ngoogle.be\ngoogle.bf\ngoogle.bg\ngoogle.com.bh\ngoogle.bi\ngoogle.bj\ngoogle.com.bn\ngoogle.com.bo\ngoogle.com.br\ngoogle.bs\ngoogle.bt\ngoogle.co.bw\ngoogle.by\ngoogle.com.bz\ngoogle.ca\ngoogle.cd\ngoogle.cf\ngoogle.cg\ngoogle.ch\ngoogle.ci\ngoogle.co.ck\ngoogle.cl\ngoogle.cm\ngoogle.cn\ngoogle.com.co\ngoogle.co.cr\ngoogle.com.cu\ngoogle.cv\ngoogle.com.cy\ngoogle.cz\ngoogle.de\ngoogle.dj\ngoogle.dk\ngoogle.dm\ngoogle.com.do\ngoogle.dz\ngoogle.com.ec\ngoogle.ee\ngoogle.com.eg\ngoogle.es\ngoogle.com.et\ngoogle.fi\ngoogle.com.fj\ngoogle.fm\ngoogle.fr\ngoogle.ga\ngoogle.ge\ngoogle.gg\ngoogle.com.gh\ngoogle.com.gi\ngoogle.gl\ngoogle.gm\ngoogle.gp\ngoogle.gr\ngoogle.com.gt\ngoogle.gy\ngoogle.com.hk\ngoogle.hn\ngoogle.hr\ngoogle.ht\ngoogle.hu\ngoogle.co.id\ngoogle.ie\ngoogle.co.il\ngoogle.im\ngoogle.co.in\ngoogle.iq\ngoogle.is\ngoogle.it\ngoogle.je\ngoogle.com.jm\ngoogle.jo\ngoogle.co.jp\ngoogle.co.ke\ngoogle.com.kh\ngoogle.ki\ngoogle.kg\ngoogle.co.kr\ngoogle.com.kw\ngoogle.kz\ngoogle.la\ngoogle.com.lb\ngoogle.li\ngoogle.lk\ngoogle.co.ls\ngoogle.lt\ngoogle.lu\ngoogle.lv\ngoogle.com.ly\ngoogle.co.ma\ngoogle.md\ngoogle.me\ngoogle.mg\ngoogle.mk\ngoogle.ml\ngoogle.com.mm\ngoogle.mn\ngoogle.ms\ngoogle.com.mt\ngoogle.mu\ngoogle.mv\ngoogle.mw\ngoogle.com.mx\ngoogle.com.my\ngoogle.co.mz\ngoogle.com.na\ngoogle.com.nf\ngoogle.com.ng\ngoogle.com.ni\ngoogle.ne\ngoogle.nl\ngoogle.no\ngoogle.com.np\ngoogle.nr\ngoogle.nu\ngoogle.co.nz\ngoogle.com.om\ngoogle.com.pa\ngoogle.com.pe\ngoogle.com.pg\ngoogle.com.ph\ngoogle.com.pk\ngoogle.pl\ngoogle.pn\ngoogle.com.pr\ngoogle.ps\ngoogle.pt\ngoogle.com.py\ngoogle.com.qa\ngoogle.ro\ngoogle.ru\ngoogle.rw\ngoogle.com.sa\ngoogle.com.sb\ngoogle.sc\ngoogle.se\ngoogle.com.sg\ngoogle.sh\ngoogle.si\ngoogle.sk\ngoogle.com.sl\ngoogle.sn\ngoogle.so\ngoogle.sm\ngoogle.sr\ngoogle.st\ngoogle.com.sv\ngoogle.td\ngoogle.tg\ngoogle.co.th\ngoogle.com.tj\ngoogle.tk\ngoogle.tl\ngoogle.tm\ngoogle.tn\ngoogle.to\ngoogle.com.tr\ngoogle.tt\ngoogle.com.tw\ngoogle.co.tz\ngoogle.com.ua\ngoogle.co.ug\ngoogle.co.uk\ngoogle.com.uy\ngoogle.co.uz\ngoogle.com.vc\ngoogle.co.ve\ngoogle.vg\ngoogle.co.vi\ngoogle.com.vn\ngoogle.vu\ngoogle.ws\ngoogle.rs\ngoogle.co.za\ngoogle.co.zm\ngoogle.co.zw\ngoogle.cat\n' >> $DOMAIN_TEMP_FILE
|
||||
printf 'Google search domains... ' && _green 'Added\n'
|
||||
|
||||
# Add blogspot domains
|
||||
printf 'blogspot.ca\nblogspot.co.uk\nblogspot.com\nblogspot.com.ar\nblogspot.com.au\nblogspot.com.br\nblogspot.com.by\nblogspot.com.co\nblogspot.com.cy\nblogspot.com.ee\nblogspot.com.eg\nblogspot.com.es\nblogspot.com.mt\nblogspot.com.ng\nblogspot.com.tr\nblogspot.com.uy\nblogspot.de\nblogspot.gr\nblogspot.in\nblogspot.mx\nblogspot.ch\nblogspot.fr\nblogspot.ie\nblogspot.it\nblogspot.pt\nblogspot.ro\nblogspot.sg\nblogspot.be\nblogspot.no\nblogspot.se\nblogspot.jp\nblogspot.in\nblogspot.ae\nblogspot.al\nblogspot.am\nblogspot.ba\nblogspot.bg\nblogspot.ch\nblogspot.cl\nblogspot.cz\nblogspot.dk\nblogspot.fi\nblogspot.gr\nblogspot.hk\nblogspot.hr\nblogspot.hu\nblogspot.ie\nblogspot.is\nblogspot.kr\nblogspot.li\nblogspot.lt\nblogspot.lu\nblogspot.md\nblogspot.mk\nblogspot.my\nblogspot.nl\nblogspot.no\nblogspot.pe\nblogspot.qa\nblogspot.ro\nblogspot.ru\nblogspot.se\nblogspot.sg\nblogspot.si\nblogspot.sk\nblogspot.sn\nblogspot.tw\nblogspot.ug\nblogspot.cat\n' >> $DOMAIN_TEMP_FILE
|
||||
printf 'Blogspot domains... ' && _green 'Added\n'
|
||||
|
||||
# Add twimg.edgesuite.net
|
||||
printf 'twimg.edgesuite.net\n' >> $DOMAIN_TEMP_FILE
|
||||
printf 'twimg.edgesuite.net... ' && _green 'Added\n'
|
||||
|
||||
# Delete exclude domains
|
||||
if [ ! -z $EXCLUDE_DOMAIN_FILE ]; then
|
||||
for line in $(cat $EXCLUDE_DOMAIN_FILE)
|
||||
do
|
||||
cat $DOMAIN_TEMP_FILE | grep -vF -f $EXCLUDE_DOMAIN_FILE > $DOMAIN_FILE
|
||||
done
|
||||
printf 'Domains in exclude domain file '$EXCLUDE_DOMAIN_FILE'... ' && _green 'Deleted\n'
|
||||
else
|
||||
cat $DOMAIN_TEMP_FILE > $DOMAIN_FILE
|
||||
fi
|
||||
|
||||
# Add extra domains
|
||||
if [ ! -z $EXTRA_DOMAIN_FILE ]; then
|
||||
cat $EXTRA_DOMAIN_FILE >> $DOMAIN_FILE
|
||||
printf 'Extra domain file '$EXTRA_DOMAIN_FILE'... ' && _green 'Added\n'
|
||||
fi
|
||||
|
||||
if [ $OUT_TYPE = 'DNSMASQ_RULES' ]; then
|
||||
# Convert domains into dnsmasq rules
|
||||
if [ $WITH_IPSET -eq 1 ]; then
|
||||
_green 'Ipset rules included.'
|
||||
sort -u $DOMAIN_FILE | $SED_ERES 's#(.+)#server=/\1/'$DNS_IP'\#'$DNS_PORT'\
|
||||
ipset=/\1/'$IPSET_NAME'#g' > $CONF_TMP_FILE
|
||||
else
|
||||
_green 'Ipset rules not included.'
|
||||
sort -u $DOMAIN_FILE | $SED_ERES 's#(.+)#server=/\1/'$DNS_IP'\#'$DNS_PORT'#g' > $CONF_TMP_FILE
|
||||
fi
|
||||
|
||||
# Generate output file
|
||||
echo '# dnsmasq rules generated by gfwlist' > $OUT_TMP_FILE
|
||||
echo "# Last Updated on $(date "+%Y-%m-%d %H:%M:%S")" >> $OUT_TMP_FILE
|
||||
echo '# ' >> $OUT_TMP_FILE
|
||||
cat $CONF_TMP_FILE >> $OUT_TMP_FILE
|
||||
cp $OUT_TMP_FILE $OUT_FILE
|
||||
else
|
||||
sort -u $DOMAIN_FILE > $OUT_TMP_FILE
|
||||
fi
|
||||
|
||||
cp $OUT_TMP_FILE $OUT_FILE
|
||||
printf '\nConverting GfwList to '$OUT_TYPE'... ' && _green 'Done\n\n'
|
||||
|
||||
# Clean up
|
||||
clean_and_exit 0
|
||||
}
|
||||
|
||||
main() {
|
||||
if [ -z "$1" ]; then
|
||||
usage 0
|
||||
else
|
||||
check_depends
|
||||
get_args "$@"
|
||||
_green '\nJob Started.\n\n'
|
||||
process
|
||||
fi
|
||||
}
|
||||
|
||||
main "$@"
|
||||
50
gmediarender/Makefile
Normal file
50
gmediarender/Makefile
Normal file
@@ -0,0 +1,50 @@
|
||||
#
|
||||
# Copyright (C) 2020 coolsnowwolf@gmail.com
|
||||
#
|
||||
# This is free software, licensed under the GNU General Public License v2.
|
||||
# See /LICENSE for more information.
|
||||
#
|
||||
|
||||
include $(TOPDIR)/rules.mk
|
||||
|
||||
PKG_NAME:=gmediarender
|
||||
PKG_VERSION:=2021-03-15
|
||||
PKG_RELEASE=$(PKG_SOURCE_VERSION)
|
||||
|
||||
PKG_SOURCE_PROTO:=git
|
||||
PKG_SOURCE_URL:=https://github.com/hzeller/gmrender-resurrect.git
|
||||
PKG_SOURCE_SUBDIR:=$(PKG_NAME)-$(PKG_VERSION)
|
||||
PKG_SOURCE_VERSION:=4ac7d8914dc089651ae9d6c421ecda8f4d0ab5e3
|
||||
PKG_SOURCE:=$(PKG_NAME)-$(PKG_VERSION)-$(PKG_SOURCE_VERSION).tar.gz
|
||||
PKG_MIRROR_HASH:=08e8e60b8734131acd5d667c40a9a7e9d8bc7e86f59b4972d177e653608a1215
|
||||
|
||||
PKG_FIXUP:=autoreconf
|
||||
PKG_INSTALL=1
|
||||
PKG_REMOVE_FILES:=autogen.sh aclocal.m4
|
||||
|
||||
include $(INCLUDE_DIR)/package.mk
|
||||
include $(INCLUDE_DIR)/nls.mk
|
||||
|
||||
define Package/gmediarender
|
||||
SECTION:=multimedia
|
||||
CATEGORY:=Multimedia
|
||||
DEPENDS:= +gstreamer1 +libgstreamer1 +gstreamer1-libs +glib2 +libupnp
|
||||
TITLE:=A Headless UPnP Renderer
|
||||
endef
|
||||
|
||||
define Package/gmediarender/description
|
||||
gmediarender implements the server component that provides UPnP
|
||||
controllers a means to render media content (audio, video and images)
|
||||
from a UPnP media server.
|
||||
endef
|
||||
|
||||
CONFIGURE_ARGS+= \
|
||||
CFLAGS="$(TARGET_CFLAGS) -std=gnu99" --with-build-cc="$(HOSTCC)" \
|
||||
--prefix="\usr"
|
||||
|
||||
define Package/gmediarender/install
|
||||
$(INSTALL_DIR) $(1)/usr/sbin
|
||||
$(INSTALL_BIN) $(PKG_INSTALL_DIR)/usr/bin/$(PKG_NAME) $(1)/usr/sbin/
|
||||
endef
|
||||
|
||||
$(eval $(call BuildPackage,gmediarender))
|
||||
55
go-aliyundrive-webdav/Makefile
Normal file
55
go-aliyundrive-webdav/Makefile
Normal file
@@ -0,0 +1,55 @@
|
||||
# SPDX-Identifier-License: GPL-3.0-only
|
||||
#
|
||||
# Copyright (C) 2021 ImmortalWrt.org
|
||||
|
||||
include $(TOPDIR)/rules.mk
|
||||
|
||||
PKG_NAME:=go-aliyundrive-webdav
|
||||
PKG_VERSION:=1.1.1
|
||||
PKG_RELEASE:=$(AUTORELEASE)
|
||||
|
||||
PKG_SOURCE:=$(PKG_NAME)-$(PKG_VERSION).tar.gz
|
||||
PKG_SOURCE_URL:=https://codeload.github.com/LinkLeong/go-aliyundrive-webdav/tar.gz/v$(PKG_VERSION)?
|
||||
PKG_HASH:=967472971586bc9c62d1579a780e52431eaf37e54f2fe1b180c9a52db2304874
|
||||
|
||||
PKG_LICENSE:=Apache-2.0
|
||||
PKG_LICENSE_FILE:=LICENSE
|
||||
PKG_MAINTAINER:=Tianling Shen <cnsztl@immortalwrt.org>
|
||||
|
||||
PKG_BUILD_DEPENDS:=golang/host
|
||||
PKG_BUILD_PARALLEL:=1
|
||||
PKG_USE_MIPS16:=0
|
||||
|
||||
GO_PKG:=go-aliyun-webdav
|
||||
GO_PKG_LDFLAGS_X:=main.Version=v$(PKG_VERSION)
|
||||
|
||||
include $(INCLUDE_DIR)/package.mk
|
||||
include $(TOPDIR)/feeds/packages/lang/golang/golang-package.mk
|
||||
|
||||
define Package/go-aliyundrive-webdav
|
||||
SECTION:=net
|
||||
CATEGORY:=Network
|
||||
SUBMENU:=File Transfer
|
||||
TITLE:=A WebDav server for AliyunDrive
|
||||
URL:=https://github.com/LinkLeong/go-aliyundrive-webdav
|
||||
DEPENDS:=$(GO_ARCH_DEPENDS)
|
||||
endef
|
||||
|
||||
|
||||
define Package/go-aliyundrive-webdav/conffiles
|
||||
/etc/config/go-aliyundrive-webdav
|
||||
endef
|
||||
|
||||
define Package/go-aliyundrive-webdav/install
|
||||
$(call GoPackage/Package/Install/Bin,$(PKG_INSTALL_DIR))
|
||||
$(INSTALL_DIR) $(1)/usr/bin/
|
||||
$(INSTALL_BIN) $(PKG_INSTALL_DIR)/usr/bin/go-aliyun-webdav $(1)/usr/bin/go-aliyundrive-webdav
|
||||
|
||||
$(INSTALL_DIR) $(1)/etc/config/
|
||||
$(INSTALL_CONF) $(CURDIR)/files/go-aliyundrive-webdav.config $(1)/etc/config/go-aliyundrive-webdav
|
||||
$(INSTALL_DIR) $(1)/etc/init.d/
|
||||
$(INSTALL_BIN) $(CURDIR)/files/go-aliyundrive-webdav.init $(1)/etc/init.d/go-aliyundrive-webdav
|
||||
endef
|
||||
|
||||
$(eval $(call GoBinPackage,go-aliyundrive-webdav))
|
||||
$(eval $(call BuildPackage,go-aliyundrive-webdav))
|
||||
23
go-aliyundrive-webdav/files/go-aliyundrive-webdav.config
Normal file
23
go-aliyundrive-webdav/files/go-aliyundrive-webdav.config
Normal file
@@ -0,0 +1,23 @@
|
||||
|
||||
|
||||
config go-aliyundrive-webdav 'config'
|
||||
option enabled '0'
|
||||
|
||||
# Listening port
|
||||
option port '8085'
|
||||
|
||||
# Refresh token
|
||||
option rt ''
|
||||
|
||||
# Mounting directory
|
||||
option path '/'
|
||||
|
||||
# Webdav auth username, default: admin
|
||||
option user 'admin'
|
||||
|
||||
# Webdav auth password, default: 123456
|
||||
option pwd '123456'
|
||||
|
||||
# Enable detailed logging
|
||||
option verbose '0'
|
||||
|
||||
50
go-aliyundrive-webdav/files/go-aliyundrive-webdav.init
Executable file
50
go-aliyundrive-webdav/files/go-aliyundrive-webdav.init
Executable file
@@ -0,0 +1,50 @@
|
||||
#!/bin/sh /etc/rc.common
|
||||
# Copyright (C) 2021 Tianling Shen <cnsztl@immortalwrt.org>
|
||||
|
||||
USE_PROCD=1
|
||||
START=99
|
||||
|
||||
CONF="go-aliyundrive-webdav"
|
||||
PROG="/usr/bin/go-aliyundrive-webdav"
|
||||
|
||||
start_service() {
|
||||
config_load "$CONF"
|
||||
|
||||
local enabled
|
||||
config_get_bool enabled "config" "enabled"
|
||||
[ "$enabled" -eq "1" ] || return 1
|
||||
|
||||
local port rt path user pwd verbose
|
||||
config_get port "config" "port"
|
||||
config_get rt "config" "rt"
|
||||
config_get path "config" "path"
|
||||
config_get user "config" "user"
|
||||
config_get pwd "config" "pwd"
|
||||
config_get_bool verbose "config" "verbose"
|
||||
|
||||
procd_open_instance "$CONF"
|
||||
|
||||
procd_set_param command "$PROG"
|
||||
|
||||
procd_append_param command "-rt" "$rt"
|
||||
procd_append_param command "-port" "$port"
|
||||
procd_append_param command "-path" "$path"
|
||||
procd_append_param command "-user" "$user"
|
||||
procd_append_param command "-pwd" "$pwd"
|
||||
[ "$verbose" -eq "0" ] || procd_append_param command "-v"
|
||||
|
||||
procd_set_param stdout 1
|
||||
procd_set_param stderr 1
|
||||
procd_set_param respawn
|
||||
|
||||
procd_close_instance
|
||||
}
|
||||
|
||||
reload_service() {
|
||||
stop
|
||||
start
|
||||
}
|
||||
|
||||
service_triggers() {
|
||||
procd_add_reload_trigger "go-aliyundrive-webdav"
|
||||
}
|
||||
24
luci-app-unblockneteasemusic/Makefile
Normal file
24
luci-app-unblockneteasemusic/Makefile
Normal file
@@ -0,0 +1,24 @@
|
||||
# SPDX-License-Identifier: GPL-3.0-only
|
||||
#
|
||||
# Copyright (C) 2019-2022 Tianling Shen <cnsztl@immortalwrt.org>
|
||||
|
||||
include $(TOPDIR)/rules.mk
|
||||
|
||||
LUCI_TITLE:=LuCI support for UnblockNeteaseMusic (JavaScript)
|
||||
LUCI_DEPENDS:=+dnsmasq-full +node \
|
||||
@(PACKAGE_libustream-mbedtls||PACKAGE_libustream-openssl||PACKAGE_libustream-wolfssl)
|
||||
LUCI_PKGARCH:=all
|
||||
|
||||
PKG_NAME:=luci-app-unblockneteasemusic
|
||||
PKG_VERSION:=3.1
|
||||
PKG_RELEASE:=4
|
||||
|
||||
PKG_MAINTAINER:=Tianling Shen <cnsztl@immortalwrt.org>
|
||||
|
||||
define Package/luci-app-unblockneteasemusic/conffiles
|
||||
/etc/config/unblockneteasemusic
|
||||
endef
|
||||
|
||||
include $(TOPDIR)/feeds/luci/luci.mk
|
||||
|
||||
# call BuildPackage - OpenWrt buildroot signature
|
||||
@@ -0,0 +1,358 @@
|
||||
/* SPDX-License-Identifier: GPL-3.0-only
|
||||
*
|
||||
* Copyright (C) 2022-2023 ImmortalWrt.org
|
||||
*/
|
||||
|
||||
'use strict';
|
||||
'require form';
|
||||
'require fs';
|
||||
'require network';
|
||||
'require poll';
|
||||
'require rpc';
|
||||
'require uci';
|
||||
'require ui';
|
||||
'require view';
|
||||
|
||||
var CBIStaticList = form.DynamicList.extend({
|
||||
__name__: 'CBI.StaticList',
|
||||
|
||||
renderWidget: function(/* ... */) {
|
||||
var dl = form.DynamicList.prototype.renderWidget.apply(this, arguments);
|
||||
dl.querySelector('.add-item ul > li[data-value="-"]').remove();
|
||||
return dl;
|
||||
}
|
||||
});
|
||||
|
||||
var callServiceList = rpc.declare({
|
||||
object: 'service',
|
||||
method: 'list',
|
||||
params: ['name'],
|
||||
expect: { '': {} }
|
||||
});
|
||||
|
||||
function getServiceStatus() {
|
||||
return L.resolveDefault(callServiceList('unblockneteasemusic'), {}).then(function (res) {
|
||||
var isRunning = false;
|
||||
try {
|
||||
isRunning = res['unblockneteasemusic']['instances']['unblockneteasemusic']['running'];
|
||||
} catch (e) { }
|
||||
return isRunning;
|
||||
});
|
||||
}
|
||||
|
||||
function renderStatus(isRunning) {
|
||||
var spanTemp = '<em><span style="color:%s"><strong>%s %s</strong></span></em>';
|
||||
var renderHTML;
|
||||
if (isRunning) {
|
||||
renderHTML = spanTemp.format('green', _('UnblockNeteaseMusic'), _('运行中'));
|
||||
} else {
|
||||
renderHTML = spanTemp.format('red', _('UnblockNeteaseMusic'), _('未运行'));
|
||||
}
|
||||
|
||||
return renderHTML;
|
||||
}
|
||||
|
||||
function uploadCertificate(type, filename, ev) {
|
||||
return ui.uploadFile('/usr/share/unblockneteasemusic/' + filename, ev.target)
|
||||
.then(L.bind(function(btn, res) {
|
||||
btn.firstChild.data = _('检查 %s 中...').format(type);
|
||||
|
||||
if (res.size <= 0) {
|
||||
ui.addNotification(null, E('p', _('上传的 %s 为空。').format(tyupe)));
|
||||
return fs.remove('/usr/share/unblockneteasemusic/' + filename);
|
||||
}
|
||||
|
||||
ui.addNotification(null, E('p', _('您的 %s 已成功上传。大小:%sB。').format(type, res.size)));
|
||||
}, this, ev.target))
|
||||
.catch(function(e) { ui.addNotification(null, E('p', e.message)) })
|
||||
.finally(L.bind(function(btn, input) {
|
||||
btn.firstChild.data = _('上传...');
|
||||
}, this, ev.target));
|
||||
}
|
||||
|
||||
return view.extend({
|
||||
load: function() {
|
||||
return Promise.all([
|
||||
uci.load('unblockneteasemusic'),
|
||||
network.getHostHints()
|
||||
]);
|
||||
},
|
||||
|
||||
render: function(data) {
|
||||
var m, s, o;
|
||||
|
||||
m = new form.Map('unblockneteasemusic', _('解除网易云音乐播放限制'),
|
||||
_('原理:采用 [Bilibili/JOOX/酷狗/酷我/咪咕/pyncmd/QQ/Youtube] 等音源,替换网易云音乐 无版权/收费 歌曲链接<br/>' +
|
||||
'具体使用方法参见:<a href="https://github.com/UnblockNeteaseMusic/luci-app-unblockneteasemusic" target="_blank">GitHub @UnblockNeteaseMusic/luci-app-unblockneteasemusic</a>'));
|
||||
|
||||
s = m.section(form.TypedSection);
|
||||
s.anonymous = true;
|
||||
s.render = function () {
|
||||
poll.add(function () {
|
||||
return L.resolveDefault(getServiceStatus()).then(function (res) {
|
||||
var view = document.getElementById('service_status');
|
||||
view.innerHTML = renderStatus(res);
|
||||
});
|
||||
});
|
||||
|
||||
return E('div', { class: 'cbi-section', id: 'status_bar' }, [
|
||||
E('p', { id: 'service_status' }, _('收集数据中...'))
|
||||
]);
|
||||
}
|
||||
|
||||
s = m.section(form.NamedSection, 'config', 'unblockneteasemusic');
|
||||
|
||||
o = s.option(form.Flag, 'enable', _('启用服务'));
|
||||
o.default = o.disabled;
|
||||
o.rmempty = false;
|
||||
|
||||
o = s.option(CBIStaticList, 'music_source', _('音源接口'),
|
||||
_('留空以使用默认音源。'));
|
||||
o.value('bilibili', _('Bilibili 音乐'));
|
||||
o.value('joox', _('JOOX 音乐'));
|
||||
o.value('kugou', _('酷狗音乐'));
|
||||
o.value('kuwo', _('酷我音乐'));
|
||||
o.value('migu', _('咪咕音乐'));
|
||||
o.value('pyncmd', _('网易云音乐(pyncmd)'));
|
||||
o.value('qq', _('QQ 音乐'));
|
||||
o.value('youtube', _('Youtube 音乐'));
|
||||
o.value('youtubedl', _('Youtube 音乐(youtube-dl)'));
|
||||
o.value('ytdlp', _('Youtube 音乐(yt-dlp)'));
|
||||
o.value('ytdownload', _('Youtube 音乐(ytdownload)'));
|
||||
|
||||
o = s.option(form.Value, 'joox_cookie', _('JOOX Cookie'),
|
||||
_('在 joox.com 获取,需要 wmid 和 session_key 值。'));
|
||||
o.placeholder = 'wmid=; session_key=';
|
||||
o.rmempty = false;
|
||||
o.depends({'music_source': 'joox', '!contains': true});
|
||||
|
||||
o = s.option(form.Value, 'migu_cookie', _('Migu Cookie'),
|
||||
_('通过抓包手机客户端请求获取,需要 aversionid 值。'));
|
||||
o.depends({'music_source': 'migu', '!contains': true});
|
||||
|
||||
o = s.option(form.Value, 'qq_cookie', _('QQ Cookie'),
|
||||
_('在 y.qq.com 获取,需要 uin 和 qm_keyst 值。'));
|
||||
o.placeholder = 'uin=; qm_keyst=';
|
||||
o.rmempty = false;
|
||||
o.depends({'music_source': 'qq', '!contains': true});
|
||||
|
||||
o = s.option(form.Value, 'youtube_key', _('Youtube API Key'),
|
||||
_('API Key 申请地址:https://developers.google.com/youtube/v3/getting-started#before-you-start'));
|
||||
o.depends({'music_source': 'youtube', '!contains': true});
|
||||
|
||||
o = s.option(form.Flag, 'follow_source_order', _('顺序查询'),
|
||||
_('默认为并行查询并返回第一个结果,开启后将严格按照配置音源的顺序进行查询。'))
|
||||
o.default = o.disabled;
|
||||
o.rmempty = false;
|
||||
|
||||
o = s.option(form.Flag, 'search_album', _('附加专辑名'),
|
||||
_('在其他音源搜索歌曲时携带专辑名称(默认搜索条件 <code>歌曲名 - 歌手</code>,启用后搜索条件 <code>歌曲名 - 歌手 专辑名</code>)。'));
|
||||
o.default = o.disabled;
|
||||
o.rmempty = false;
|
||||
|
||||
o = s.option(form.Flag, 'local_vip', _('启用本地 VIP'),
|
||||
_('启用后,可以使用去广告、个性换肤、鲸云音效等本地功能。'));
|
||||
o.default = o.disabled;
|
||||
o.rmempty = false;
|
||||
|
||||
o = s.option(form.Flag, 'enable_flac', _('启用无损音质'),
|
||||
_('目前仅支持酷狗、酷我、咪咕、pyncmd、QQ 音源。'));
|
||||
o.default = o.disabled;
|
||||
o.rmempty = false;
|
||||
|
||||
o = s.option(form.Flag, 'disable_upgrade_check', _('禁用更新检查'),
|
||||
_('禁止客户端检查更新,全平台支持。'));
|
||||
o.default = o.enabled;
|
||||
o.rmempty = false;
|
||||
|
||||
o = s.option(form.ListValue, 'replace_music_source', _('音源替换'),
|
||||
_('当音乐音质低于指定数值时,尝试强制使用其他平台的高音质版本进行替换。'));
|
||||
o.value('dont_replace', _('不强制替换音乐音源'));
|
||||
o.value('lower_than_192kbps', _('当音质低于 192 Kbps(中)时'));
|
||||
o.value('lower_than_320kbps', _('当音质低于 320 Kbps(高)时'));
|
||||
o.value('lower_than_999kbps', _('当音质低于 999 Kbps(无损)时'));
|
||||
o.value('replace_all', _('替换所有音乐音源'));
|
||||
o.default = 'dont_replace';
|
||||
o.rmempty = false;
|
||||
|
||||
o = s.option(form.Flag, 'auto_update', _('启用自动更新'),
|
||||
_('启用后,每天将定时自动检查最新版本并更新。'));
|
||||
o.default = o.disabled;
|
||||
o.rmempty = false;
|
||||
|
||||
o = s.option(form.ListValue, 'update_time', '检查更新时间',
|
||||
_('设定每天自动检查更新时间。'));
|
||||
for (var i = 0; i < 24; i++)
|
||||
o.value(i, i + ':00');
|
||||
o.default = '3';
|
||||
o.depends('auto_update', '1');
|
||||
|
||||
o = s.option(form.Button, '_download_cert', _('CA 根证书'),
|
||||
_('Linux / iOS / MacOSX 在信任根证书后方可正常使用。'));
|
||||
o.inputstyle = 'apply';
|
||||
o.inputtitle = _('下载 ca.crt');
|
||||
o.onclick = function() {
|
||||
return fs.read_direct('/usr/share/unblockneteasemusic/core/ca.crt', 'blob').then(function(blob) {
|
||||
var url = window.URL.createObjectURL(blob);
|
||||
var link = E('a', { 'style': 'display:none', 'href': url, 'download': 'ca.crt' });
|
||||
|
||||
document.body.appendChild(link);
|
||||
link.click();
|
||||
document.body.removeChild(link);
|
||||
window.URL.revokeObjectURL(url);
|
||||
}).catch(function(err) {
|
||||
ui.addNotification(null, E('p', [ _('下载文件失败:%s。').format(err.message) ]));
|
||||
});
|
||||
}
|
||||
|
||||
o = s.option(form.Flag, 'advanced_mode', _('启用进阶设置'),
|
||||
_('非必要不推荐使用。'));
|
||||
o.default = o.disabled,
|
||||
o.rmempty = false;
|
||||
|
||||
o = s.option(form.ListValue, 'log_level', _('日志等级'));
|
||||
o.value('debug', _('调试'));
|
||||
o.value('info', _('信息(默认)'));
|
||||
o.value('silent', _('静默'));
|
||||
o.default = 'info';
|
||||
o.rmempty = false;
|
||||
o.depends('advanced_mode', '1');
|
||||
|
||||
o = s.option(form.Value, 'http_port', _('HTTP 监听端口'));
|
||||
o.datatype = 'port';
|
||||
o.default = '5200';
|
||||
o.rmempty = false;
|
||||
o.depends('advanced_mode', '1');
|
||||
|
||||
o = s.option(form.Value, 'https_port', _('HTTPS 监听端口'));
|
||||
o.datatype = 'port';
|
||||
o.default = '5201';
|
||||
o.rmempty = false;
|
||||
o.depends('advanced_mode', '1');
|
||||
|
||||
o = s.option(form.Value, 'endpoint_url', _('EndPoint'),
|
||||
_('音源地址反代(包装)。'));
|
||||
o.default = 'https://music.163.com';
|
||||
o.rmempty = false;
|
||||
o.depends('advanced_mode', '1');
|
||||
|
||||
o = s.option(form.Value, 'cnrelay', _('UNM Bridge 服务器'),
|
||||
_('使用 UnblockNeteaseMusic 中继桥(bridge)以获取音源信息。'));
|
||||
o.placeholder = 'http(s)://host:port'
|
||||
o.depends('advanced_mode', '1');
|
||||
|
||||
o = s.option(form.ListValue, 'hijack_ways', _('劫持方法'));
|
||||
o.value('dont_hijack', _('不开启劫持'));
|
||||
o.value('use_ipset', _('使用 IPSet 劫持'));
|
||||
o.value('use_hosts', _('使用 Hosts 劫持'));
|
||||
o.default = 'dont_hijack';
|
||||
o.rmempty = false;
|
||||
o.depends('advanced_mode', '1');
|
||||
o.onchange = function(ev, section_id, value) {
|
||||
if (!section_id || !value)
|
||||
return null;
|
||||
|
||||
var ele_http_port = this.map.findElement('id', 'widget.cbid.unblockneteasemusic.%s.http_port'.format(section_id));
|
||||
var ele_https_port = this.map.findElement('id', 'widget.cbid.unblockneteasemusic.%s.https_port'.format(section_id));
|
||||
|
||||
if (value === 'use_hosts') {
|
||||
ele_http_port.value = '80';
|
||||
ele_http_port.disabled = true;
|
||||
|
||||
ele_https_port.value = '443';
|
||||
ele_https_port.disabled = true;
|
||||
} else if (ele_http_port.disabled || ele_https_port.disabled) {
|
||||
L.resolveDefault(this.map.data.loaded.unblockneteasemusic).then((res) => {
|
||||
ele_http_port.disabled = null;
|
||||
ele_http_port.value = res.config.http_port || '5200';
|
||||
|
||||
ele_https_port.disabled = null;
|
||||
ele_https_port.value = res.config.https_port || '5201';
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
o = s.option(form.Flag, 'keep_core_when_upgrade', _('升级时保留核心程序'));
|
||||
o.default = o.disabled;
|
||||
o.rmempty = false;
|
||||
o.depends('advanced_mode', '1');
|
||||
|
||||
o = s.option(form.Flag, 'pub_access', _('部署到公网'),
|
||||
_('默认仅放行局域网请求,如需提供公开访问请勾选此选项。'));
|
||||
o.default = o.disabled;
|
||||
o.rmempty = false;
|
||||
o.depends('advanced_mode', '1');
|
||||
|
||||
o = s.option(form.Flag, 'strict_mode', _('启用严格模式'),
|
||||
_('若将服务部署到公网,则强烈建议使用严格模式,此模式下仅放行网易云音乐所属域名的请求。<br/>注意:该模式下不能使用全局代理。'));
|
||||
o.default = o.disabled;
|
||||
o.rmempty = false;
|
||||
o.depends('advanced_mode', '1');
|
||||
|
||||
o = s.option(form.Value, 'netease_server_ip', _('网易云服务器 IP'));
|
||||
o.datatype = 'ipaddr';
|
||||
o.depends('advanced_mode', '1');
|
||||
|
||||
o = s.option(form.Value, 'proxy_server_ip', _('代理服务器地址'),
|
||||
_('使用代理服务器获取音乐信息。'));
|
||||
o.placeholder = 'http(s)://host:port';
|
||||
o.depends('advanced_mode', '1');
|
||||
|
||||
o = s.option(form.Value, 'self_issue_cert_crt', _('自签发证书公钥位置'));
|
||||
o.value('/usr/share/unblockneteasemusic/core/server.crt', _('内置公钥'));
|
||||
o.value('/usr/share/unblockneteasemusic/server.crt');
|
||||
o.default = '/usr/share/unblockneteasemusic/core/server.crt';
|
||||
o.datatype = 'file';
|
||||
o.depends('advanced_mode', '1');
|
||||
|
||||
o = s.option(form.Button, '_upload_cert', _('上传公钥'));
|
||||
o.inputstyle = 'action';
|
||||
o.inputtitle = _('上传...');
|
||||
o.depends('self_issue_cert_crt', '/usr/share/unblockneteasemusic/server.crt');
|
||||
o.onclick = L.bind(uploadCertificate, this, _('公钥'), 'server.crt');
|
||||
o.modalonly = true;
|
||||
|
||||
o = s.option(form.Value, 'self_issue_cert_key', _('自签发证书私钥位置'));
|
||||
o.value('/usr/share/unblockneteasemusic/core/server.key', _('内置私钥'));
|
||||
o.value('/usr/share/unblockneteasemusic/server.key');
|
||||
o.default = '/usr/share/unblockneteasemusic/core/server.key';
|
||||
o.datatype = 'file'
|
||||
o.depends('advanced_mode', '1');
|
||||
|
||||
o = s.option(form.Button, '_upload_key', _('上传私钥'));
|
||||
o.inputstyle = 'action';
|
||||
o.inputtitle = _('上传...');
|
||||
o.depends('self_issue_cert_key', '/usr/share/unblockneteasemusic/server.key');
|
||||
o.onclick = L.bind(uploadCertificate, this, _('私钥'), 'server.key');
|
||||
o.modalonly = true;
|
||||
|
||||
s = m.section(form.TableSection, 'acl_rule', _('例外客户端规则'),
|
||||
_('可以为局域网客户端分别设置不同的例外模式。'));
|
||||
s.addremove = true;
|
||||
s.anonymous = true;
|
||||
s.sortable = true;
|
||||
|
||||
o = s.option(form.Flag, 'enable', _('启用'));
|
||||
o.default = o.enabled;
|
||||
o.rmempty = false;
|
||||
|
||||
o = s.option(form.Value, 'ip_addr', _('IP 地址'));
|
||||
o.datatype = 'ip4addr';
|
||||
for (var i of Object.entries(data[1].hosts))
|
||||
for (var v in i[1].ipaddrs)
|
||||
if (i[1].ipaddrs[v]) {
|
||||
var ip_addr = i[1].ipaddrs[v], ip_host = i[1].name;
|
||||
o.value(ip_addr, ip_host ? String.format('%s (%s)', ip_host, ip_addr) : ip_addr)
|
||||
}
|
||||
o.rmempty = false;
|
||||
|
||||
o = s.option(form.ListValue, 'filter_mode', _('规则'));
|
||||
o.value('disable_all', _('不代理 HTTP 和 HTTPS'));
|
||||
o.value('disable_http', _('不代理 HTTP'));
|
||||
o.value('disable_https', _('不代理 HTTPS'));
|
||||
o.default = 'disable_all';
|
||||
o.rmempty = false;
|
||||
|
||||
return m.render();
|
||||
}
|
||||
});
|
||||
@@ -0,0 +1,224 @@
|
||||
/* SPDX-License-Identifier: GPL-3.0-only
|
||||
*
|
||||
* Copyright (C) 2022 ImmortalWrt.org
|
||||
*/
|
||||
|
||||
'use strict';
|
||||
'require dom';
|
||||
'require form';
|
||||
'require fs';
|
||||
'require poll';
|
||||
'require rpc';
|
||||
'require ui';
|
||||
'require view';
|
||||
|
||||
return view.extend({
|
||||
render: function() {
|
||||
var m, s, o;
|
||||
|
||||
var unm_helper = '/usr/share/unblockneteasemusic/update.sh';
|
||||
|
||||
m = new form.Map('unblockneteasemusic');
|
||||
|
||||
s = m.section(form.NamedSection, 'config', 'unblockneteasemusic', _('核心管理'));
|
||||
s.anonymous = true;
|
||||
|
||||
o = s.option(form.DummyValue, '_core_version', _('核心版本'));
|
||||
o.cfgvalue = function() {
|
||||
var _this = this;
|
||||
var spanTemp = '<div style="color:%s;margin-top:5px;"><strong>%s</strong></div>';
|
||||
|
||||
return fs.exec(unm_helper, [ 'check_version' ]).then(function(res) {
|
||||
if (res.code === 0)
|
||||
_this.default = String.format(spanTemp, 'green', res.stdout.trim());
|
||||
else if (res.code === 2)
|
||||
_this.default = String.format(spanTemp, 'red', _('未安装'));
|
||||
else {
|
||||
ui.addNotification(null, E('p', [ _('获取版本信息失败:%s。').format(res) ]));
|
||||
_this.default = String.format(spanTemp, 'red', _('未知错误'));
|
||||
}
|
||||
|
||||
return null;
|
||||
}).catch(function(err) {
|
||||
ui.addNotification(null, E('p', [ _('未知错误:%s。').format(err) ]));
|
||||
_this.default = String.format(spanTemp, 'red', _('未知错误'));
|
||||
|
||||
return null;
|
||||
});
|
||||
}
|
||||
o.rawhtml = true;
|
||||
|
||||
o = s.option(form.Button, '_remove_core', _('删除核心'),
|
||||
_('删除核心后,需手动点击下面的按钮重新下载,有助于解决版本冲突问题。'));
|
||||
o.inputstyle = 'remove';
|
||||
o.onclick = function() {
|
||||
var _this = this;
|
||||
|
||||
return fs.exec(unm_helper, [ 'remove_core' ]).then(function(res) {
|
||||
_this.description = '删除完毕。'
|
||||
return _this.map.reset();
|
||||
}).catch(function(err) {
|
||||
ui.addNotification(null, E('p', [ _('未知错误:%s。').format(err) ]));
|
||||
_this.description = '删除失败。'
|
||||
return _this.map.reset();
|
||||
});
|
||||
}
|
||||
|
||||
o = s.option(form.Button, '_update_core', _('更新核心'),
|
||||
_('更新完毕后会自动在后台重启插件,无需手动重启。'));
|
||||
o.inputstyle = 'action';
|
||||
o.onclick = function() {
|
||||
var _this = this;
|
||||
|
||||
return fs.exec(unm_helper, [ 'update_core' ]).then(function (res) {
|
||||
if (res.code === 0)
|
||||
_this.description = _('更新成功。');
|
||||
else if (res.code === 1)
|
||||
_this.description = _('更新失败。');
|
||||
else if (res.code === 2)
|
||||
_this.description = _('更新程序正在运行中。');
|
||||
else if (res.code === 3)
|
||||
_this.description = _('当前已是最新版本。');
|
||||
|
||||
return _this.map.reset();
|
||||
}).catch(function (err) {
|
||||
ui.addNotification(null, E('p', [ _('未知错误:%s。').format(err) ]));
|
||||
_this.description = _('更新失败。');
|
||||
return _this.map.reset();
|
||||
});
|
||||
}
|
||||
|
||||
o = s.option(form.Button, '_debug_log', _('调试报告'),
|
||||
_('若您遇到使用上的问题,请点此打印调试报告,并将其附在您的 issue 中。'));
|
||||
o.inputstyle = 'action';
|
||||
o.inputtitle = _('打印报告');
|
||||
o.onclick = function() {
|
||||
var log_modal = ui.showModal(_('打印调试报告'), [
|
||||
E('p', { 'class': 'spinning' },
|
||||
_('正在打印调试报告中...'))
|
||||
]);
|
||||
|
||||
return fs.exec_direct('/usr/bin/unm-debug', 'text').then(function (res) {
|
||||
log_modal.removeChild(log_modal.lastChild);
|
||||
|
||||
if (res) {
|
||||
log_modal.appendChild(E('p', _('提交 issue 时,您只需附上最后的链接,无需提供整个输出。')));
|
||||
log_modal.appendChild(E('textarea', {
|
||||
'id': 'content_debugLog',
|
||||
'class': 'cbi-input-textarea',
|
||||
'style': 'font-size:13px; resize: none',
|
||||
'readonly': 'readonly',
|
||||
'wrap': 'soft',
|
||||
'rows': '30'
|
||||
}, [ res.trim() ])
|
||||
);
|
||||
} else {
|
||||
log_modal.appendChild(E('p', _('错误')));
|
||||
log_modal.appendChild(E('pre', { 'class': 'errors' }, [ _('无法打印调试报告。') ]));
|
||||
}
|
||||
|
||||
var log_element = document.getElementById('content_debugLog') || null;
|
||||
if (log_element)
|
||||
log_element.scrollTop = log_element.scrollHeight;
|
||||
|
||||
log_modal.appendChild(E('div', { 'class': 'right' }, [
|
||||
log_element ? E('button', {
|
||||
'class': 'btn cbi-button-action',
|
||||
'click': ui.createHandlerFn(this, function() {
|
||||
var links = log_element.value.match(/https:\/\/(litter.catbox.moe|transfer.sh)\/.*.txt/g);
|
||||
|
||||
var textarea = document.createElement('textarea');
|
||||
document.body.appendChild(textarea);
|
||||
|
||||
textarea.style.position = 'absolute';
|
||||
textarea.style.clip = 'rect(0 0 0 0)';
|
||||
textarea.value = links ? links.join('\n'): log_element.value;
|
||||
textarea.select()
|
||||
|
||||
document.execCommand('copy', true);
|
||||
document.body.removeChild(textarea);
|
||||
})
|
||||
}, _('复制')) : '',
|
||||
E('button', {
|
||||
'class': 'btn',
|
||||
'click': ui.hideModal
|
||||
}, _('关闭'))
|
||||
]));
|
||||
|
||||
return null;
|
||||
}).catch(function (err) {
|
||||
ui.addNotification(null, E('p', _('无法打印调试报告:%s。').format(err)));
|
||||
ui.hideModal();
|
||||
|
||||
return null;
|
||||
});
|
||||
}
|
||||
|
||||
o = s.option(form.DummyValue, '_logview');
|
||||
o.render = function() {
|
||||
/* Thanks to luci-app-aria2 */
|
||||
var css = ' \
|
||||
#log_textarea { \
|
||||
padding: 10px; \
|
||||
text-align: left; \
|
||||
} \
|
||||
#log_textarea pre { \
|
||||
padding: .5rem; \
|
||||
word-break: break-all; \
|
||||
margin: 0; \
|
||||
} \
|
||||
.description { \
|
||||
background-color: #33ccff; \
|
||||
}';
|
||||
|
||||
var log_textarea = E('div', { 'id': 'log_textarea' },
|
||||
E('img', {
|
||||
'src': L.resource(['icons/loading.gif']),
|
||||
'alt': _('Loading'),
|
||||
'style': 'vertical-align:middle'
|
||||
}, _('Collecting data...'))
|
||||
);
|
||||
|
||||
poll.add(L.bind(function() {
|
||||
return fs.read('/tmp/unblockneteasemusic.log', 'text')
|
||||
.then(function(res) {
|
||||
var log = E('pre', { 'wrap': 'pre' }, [
|
||||
res.trim() || _('当前无日志。')
|
||||
]);
|
||||
|
||||
dom.content(log_textarea, log);
|
||||
}).catch(function(err) {
|
||||
if (err.toString().includes('NotFoundError'))
|
||||
var log = E('pre', { 'wrap': 'pre' }, [
|
||||
_('日志文件不存在。')
|
||||
]);
|
||||
else
|
||||
var log = E('pre', { 'wrap': 'pre' }, [
|
||||
_('未知错误:%s。').format(err)
|
||||
]);
|
||||
|
||||
dom.content(log_textarea, log);
|
||||
});
|
||||
}));
|
||||
|
||||
return E([
|
||||
E('style', [ css ]),
|
||||
E('div', {'class': 'cbi-map'}, [
|
||||
E('h3', {'name': 'content'}, _('运行日志')),
|
||||
E('div', {'class': 'cbi-section'}, [
|
||||
log_textarea,
|
||||
E('div', {'style': 'text-align:right'},
|
||||
E('small', {}, _('每 %s 秒刷新。').format(L.env.pollinterval))
|
||||
)
|
||||
])
|
||||
])
|
||||
]);
|
||||
}
|
||||
|
||||
return m.render();
|
||||
},
|
||||
|
||||
handleSaveApply: null,
|
||||
handleSave: null,
|
||||
handleReset: null
|
||||
});
|
||||
@@ -0,0 +1,12 @@
|
||||
|
||||
config unblockneteasemusic 'config'
|
||||
option enable '0'
|
||||
option music_source ''
|
||||
option follow_source_order '0'
|
||||
option local_vip '0'
|
||||
option enable_flac '0'
|
||||
option disable_upgrade_check '1'
|
||||
option replace_music_source 'dont_replace'
|
||||
option auto_update '1'
|
||||
option update_time '3'
|
||||
option advanced_mode '0'
|
||||
242
luci-app-unblockneteasemusic/root/etc/init.d/unblockneteasemusic
Executable file
242
luci-app-unblockneteasemusic/root/etc/init.d/unblockneteasemusic
Executable file
@@ -0,0 +1,242 @@
|
||||
#!/bin/sh /etc/rc.common
|
||||
# SPDX-License-Identifier: GPL-3.0-only
|
||||
#
|
||||
# Copyright (C) 2019-2023 Tianling Shen <cnsztl@immortalwrt.org>
|
||||
|
||||
USE_PROCD=1
|
||||
|
||||
START=99
|
||||
STOP=10
|
||||
|
||||
NAME="unblockneteasemusic"
|
||||
UPGRADE_CONF="/lib/upgrade/keep.d/$NAME"
|
||||
|
||||
RULES_UC="/usr/share/$NAME/rules/default.uc"
|
||||
RULES_NFT="/etc/nftables.d/90-$NAME-rules.nft"
|
||||
|
||||
is_enabled() {
|
||||
local enabled
|
||||
config_get_bool enabled "$1" "$2" "${3:-0}"
|
||||
if [ "$enabled" -eq "1" ]; then
|
||||
return 0
|
||||
else
|
||||
return 1
|
||||
fi
|
||||
}
|
||||
|
||||
append_param() {
|
||||
procd_append_param command "$1" $2
|
||||
}
|
||||
|
||||
append_param_arg() {
|
||||
local value
|
||||
config_get value "$1" "$2" $4
|
||||
[ -n "$value" ] && append_param "$3" "$value"
|
||||
}
|
||||
|
||||
append_param_env() {
|
||||
local value
|
||||
config_get value "$1" "$2" $4
|
||||
[ -n "$value" ] && procd_append_param env "$3"="$value"
|
||||
}
|
||||
|
||||
append_param_boolenv() {
|
||||
is_enabled "$1" "$2" "$4" && procd_append_param env "$3"="true"
|
||||
}
|
||||
|
||||
append_filter_client() {
|
||||
local cfg="$1"
|
||||
|
||||
is_enabled "$cfg" "enable" || return 1
|
||||
|
||||
local ip_addr filter_mode
|
||||
config_get ip_addr "$cfg" "ip_addr"
|
||||
config_get filter_mode "$cfg" "filter_mode"
|
||||
[ -n "$ip_addr" -a -n "$filter_mode" ] || return 1
|
||||
|
||||
case "${filter_mode}" in
|
||||
"disable_http")
|
||||
acl_http_addr="${acl_http_addr:+$acl_http_addr\n}${ip_addr}"
|
||||
;;
|
||||
"disable_https")
|
||||
acl_https_addr="${acl_https_addr:+$acl_https_addr\n}${ip_addr}"
|
||||
;;
|
||||
"disable_all")
|
||||
acl_http_addr="${acl_http_addr:+$acl_http_addr\n}${ip_addr}"
|
||||
acl_https_addr="${acl_https_addr:+$acl_https_addr\n}${ip_addr}"
|
||||
;;
|
||||
esac
|
||||
}
|
||||
|
||||
start_service() {
|
||||
config_load "$NAME"
|
||||
is_enabled "config" "enable" || return 1
|
||||
|
||||
local update_time
|
||||
config_get update_time "config" "update_time" "3"
|
||||
sed -i "/$NAME/d" /etc/crontabs/root
|
||||
is_enabled "config" "auto_update" && echo "0 ${update_time} * * * /usr/share/$NAME/update.sh update_core" >> "/etc/crontabs/root"
|
||||
echo "*/5 * * * * /usr/share/$NAME/log_check.sh" >> "/etc/crontabs/root"
|
||||
/etc/init.d/cron restart
|
||||
|
||||
[ ! -s "/usr/share/$NAME/core/app.js" ] && { rm -f "/usr/share/$NAME/local_ver"; sh "/usr/share/$NAME/update.sh" "update_core_non_restart"; }
|
||||
[ ! -s "/usr/share/$NAME/core/app.js" ] && { echo "Core Not Found, please download it before starting." >> "/tmp/$NAME.log"; exit 1; }
|
||||
|
||||
procd_open_instance "$NAME"
|
||||
procd_set_param command node "/usr/share/$NAME/core/app.js"
|
||||
append_param "-a" "0.0.0.0"
|
||||
|
||||
local http_port https_port hijack_ways
|
||||
config_get http_port "config" "http_port" "5200"
|
||||
config_get https_port "config" "https_port" "5201"
|
||||
config_get hijack_ways "config" "hijack_ways" "use_ipset"
|
||||
append_param "-p" "${http_port}":"${https_port}"
|
||||
|
||||
json_init
|
||||
if is_enabled "config" "pub_access"; then
|
||||
json_add_int o_pub_access "1"
|
||||
else
|
||||
json_add_int o_pub_access "0"
|
||||
fi
|
||||
json_add_int o_http_port "${http_port}"
|
||||
json_add_int o_https_port "${https_port}"
|
||||
json_add_string o_hijack_ways "${hijack_ways}"
|
||||
|
||||
append_param_arg "config" "music_source" "-o"
|
||||
append_param_arg "config" "cnrelay" "-c"
|
||||
append_param_arg "config" "endpoint_url" "-e" "https://music.163.com"
|
||||
append_param_arg "config" "netease_server_ip" "-f"
|
||||
append_param_arg "config" "proxy_server_ip" "-u"
|
||||
is_enabled "config" "strict_mode" && append_param "-s"
|
||||
|
||||
local log_level
|
||||
config_get log_level "config" "log_level" "info"
|
||||
procd_set_param env LOG_FILE="/tmp/$NAME.log"
|
||||
procd_append_param env LOG_LEVEL="$log_level"
|
||||
|
||||
append_param_env "config" "joox_cookie" "JOOX_COOKIE"
|
||||
append_param_env "config" "migu_cookie" "MIGU_COOKIE"
|
||||
append_param_env "config" "qq_cookie" "QQ_COOKIE"
|
||||
append_param_env "config" "youtube_key" "YOUTUBE_KEY"
|
||||
append_param_env "config" "self_issue_cert_crt" "SIGN_CERT" "/usr/share/$NAME/core/server.crt"
|
||||
append_param_env "config" "self_issue_cert_key" "SIGN_KEY" "/usr/share/$NAME/core/server.key"
|
||||
|
||||
append_param_boolenv "config" "follow_source_order" "FOLLOW_SOURCE_ORDER"
|
||||
append_param_boolenv "config" "search_album" "SEARCH_ALBUM"
|
||||
append_param_boolenv "config" "enable_flac" "ENABLE_FLAC"
|
||||
append_param_boolenv "config" "local_vip" "ENABLE_LOCAL_VIP"
|
||||
append_param_boolenv "config" "disable_upgrade_check" "DISABLE_UPGRADE_CHECK"
|
||||
case "$(config_get "config" "replace_music_source")" in
|
||||
"lower_than_192kbps") procd_append_param env MIN_BR="192000" ;;
|
||||
"lower_than_320kbps") procd_append_param env MIN_BR="320000" ;;
|
||||
"lower_than_999kbps") procd_append_param env MIN_BR="600000" ;;
|
||||
"replace_all") procd_append_param env MIN_BR="9999999" ;;
|
||||
esac
|
||||
|
||||
procd_set_param stdout 1
|
||||
procd_set_param stderr 1
|
||||
procd_set_param respawn
|
||||
|
||||
local lan_addr="$(uci -q get network.lan.ipaddr)"
|
||||
if [ "${hijack_ways}" = "use_ipset" ]; then
|
||||
mkdir -p "/tmp/dnsmasq.d"
|
||||
rm -f "/tmp/dnsmasq.d/dnsmasq-$NAME.conf"
|
||||
cat <<-EOF > "/tmp/dnsmasq.d/dnsmasq-$NAME.conf"
|
||||
dhcp-option=252,http://${lan_addr}:${http_port}/proxy.pac
|
||||
nftset=/.music.163.com/inet#fw4#neteasemusic
|
||||
nftset=/interface.music.163.com/inet#fw4#neteasemusic
|
||||
nftset=/interface3.music.163.com/inet#fw4#neteasemusic
|
||||
nftset=/apm.music.163.com/inet#fw4#neteasemusic
|
||||
nftset=/apm3.music.163.com/inet#fw4#neteasemusic
|
||||
nftset=/clientlog.music.163.com/inet#fw4#neteasemusic
|
||||
nftset=/clientlog3.music.163.com/inet#fw4#neteasemusic
|
||||
EOF
|
||||
/etc/init.d/dnsmasq reload
|
||||
|
||||
config_foreach append_filter_client "acl_rule"
|
||||
|
||||
local netease_music_ips="$(uclient-fetch -qO- "http://httpdns.n.netease.com/httpdns/v2/d?domain=music.163.com,interface.music.163.com,interface3.music.163.com,apm.music.163.com,apm3.music.163.com,clientlog.music.163.com,clientlog3.music.163.com" |jsonfilter -e '@.data.*.ip.*')"
|
||||
local netease_music_ips2="$(uclient-fetch -qO- "https://music.httpdns.c.163.com/d" --post-data="music.163.com,interface.music.163.com,interface3.music.163.com,apm.music.163.com,apm3.music.163.com,clientlog.music.163.com,clientlog3.music.163.com" |jsonfilter -e '@.dns.*["ips"].*')"
|
||||
local neteasemusic_addr="$(echo -e "${netease_music_ips}\n${netease_music_ips2}" | sort -u | awk '{print $1}')"
|
||||
|
||||
json_add_string o_acl_http_addr "$(echo -e "${acl_http_addr}" | sort -u | awk '{print $1}')"
|
||||
json_add_string o_acl_https_addr "$(echo -e "${acl_https_addr}" | sort -u | awk '{print $1}')"
|
||||
json_add_string o_neteasemusic_addr "$neteasemusic_addr"
|
||||
elif [ "${hijack_ways}" = "use_hosts" ]; then
|
||||
mkdir -p "/tmp/dnsmasq.d"
|
||||
rm -f "/tmp/dnsmasq.d/dnsmasq-$NAME.conf"
|
||||
cat <<-EOF > "/tmp/dnsmasq.d/dnsmasq-$NAME.conf"
|
||||
dhcp-option=252,http://${lan_addr}:${http_port}/proxy.pac
|
||||
address=/music.163.com/${lan_addr}
|
||||
address=/interface.music.163.com/${lan_addr}
|
||||
address=/interface3.music.163.com/${lan_addr}
|
||||
address=/apm.music.163.com/${lan_addr}
|
||||
address=/apm3.music.163.com/${lan_addr}
|
||||
address=/clientlog.music.163.com/${lan_addr}
|
||||
address=/clientlog3.music.163.com/${lan_addr}
|
||||
address=/music.httpdns.c.163.com/0.0.0.0
|
||||
EOF
|
||||
/etc/init.d/dnsmasq reload
|
||||
|
||||
ip route add "223.252.199.10" dev lo
|
||||
fi
|
||||
|
||||
local nft_tmp="/tmp/$NAME"
|
||||
json_dump -i > "$nft_tmp.json"
|
||||
if utpl -F "$nft_tmp.json" -S "$RULES_UC" > "$nft_tmp.nft" && ! cmp -s "$nft_tmp.nft" "$RULES_NFT"; then
|
||||
echo "table inet chk {include \"$nft_tmp.nft\";}" > "$nft_tmp.nft.chk"
|
||||
! nft -f "$nft_tmp.nft.chk" -c || { mv -f "$nft_tmp.nft" "$RULES_NFT"; fw4 reload; }
|
||||
fi
|
||||
rm -f "$nft_tmp.json" "$nft_tmp.nft" "$nft_tmp.nft.chk"
|
||||
|
||||
procd_close_instance
|
||||
}
|
||||
|
||||
stop_service() {
|
||||
config_load "$NAME"
|
||||
|
||||
sed -i "/$NAME/d" "/etc/crontabs/root"
|
||||
/etc/init.d/cron restart
|
||||
|
||||
rm -f "${UPGRADE_CONF}"
|
||||
is_enabled "config" "keep_core_when_upgrade" && {
|
||||
echo "/usr/share/$NAME/core/" >> "${UPGRADE_CONF}"
|
||||
echo "/usr/share/$NAME/local_ver" >> "${UPGRADE_CONF}"
|
||||
}
|
||||
|
||||
local self_issue_cert_crt self_issue_cert_key
|
||||
config_get "self_issue_cert_crt" "config" "self_issue_cert_crt"
|
||||
config_get "self_issue_cert_key" "config" "self_issue_cert_key"
|
||||
{ [ -f "${self_issue_cert_crt}" ] && [ -f "${self_issue_cert_key}" ]; } && {
|
||||
echo "${self_issue_cert_crt}" >> "${UPGRADE_CONF}"
|
||||
echo "${self_issue_cert_key}" >> "${UPGRADE_CONF}"
|
||||
}
|
||||
|
||||
local chain settable
|
||||
for chain in "netease_cloud_music_redir" "netease_cloud_music"; do
|
||||
nft flush chain inet fw4 "$chain" 2>"/dev/null"
|
||||
done
|
||||
for settable in "acl_neteasemusic_http" "acl_neteasemusic_https" "local_addr" "neteasemusic"; do
|
||||
nft flush set inet fw4 "$settable" 2>"/dev/null"
|
||||
done
|
||||
|
||||
rm -f "$RULES_NFT"
|
||||
fw4 reload
|
||||
|
||||
|
||||
rm -f "/tmp/dnsmasq.d/dnsmasq-$NAME.conf"
|
||||
/etc/init.d/dnsmasq reload
|
||||
|
||||
ip route del "223.252.199.10" 2>"/dev/null"
|
||||
|
||||
rm -f "/tmp/$NAME.log"
|
||||
}
|
||||
|
||||
reload_service() {
|
||||
stop
|
||||
start
|
||||
}
|
||||
|
||||
service_triggers() {
|
||||
procd_add_reload_trigger "$NAME"
|
||||
}
|
||||
@@ -0,0 +1,22 @@
|
||||
#!/bin/sh
|
||||
|
||||
if [ "$(uci -q get unblockneteasemusic.config.music_source)" = "default" ]; then
|
||||
uci -q delete "unblockneteasemusic.config.music_source"
|
||||
uci -q commit "unblockneteasemusic"
|
||||
fi
|
||||
|
||||
if [ "$(uci -q get unblockneteasemusic.config.hijack_ways)" = "use_hosts" ]; then
|
||||
[ "$(uci -q get "unblockneteasemusic.config.http_port")" = "80" ] || {
|
||||
uci -q set "unblockneteasemusic.config.http_port"="80"
|
||||
uci -q set "unblockneteasemusic.config.https_port"="443"
|
||||
uci -q commit "unblockneteasemusic"
|
||||
}
|
||||
fi
|
||||
|
||||
uci -q batch <<-EOF >"/dev/null"
|
||||
delete ucitrack.@unblockneteasemusic[-1]
|
||||
commit ucitrack
|
||||
EOF
|
||||
|
||||
rm -f /tmp/luci-indexcache
|
||||
exit 0
|
||||
16
luci-app-unblockneteasemusic/root/usr/bin/unm-debug
Executable file
16
luci-app-unblockneteasemusic/root/usr/bin/unm-debug
Executable file
@@ -0,0 +1,16 @@
|
||||
#!/bin/sh
|
||||
# Copyright (C) 2021-2022 Tianling Shen <cnsztl@immortalwrt.org>
|
||||
|
||||
command -v "curl" >"/dev/null" || { echo -e "curl is not found."; exit 1; }
|
||||
|
||||
mkdir -p "/tmp"
|
||||
/usr/share/unblockneteasemusic/debugging.sh 2>&1 | tee "/tmp/unm-debugging-output.txt"
|
||||
|
||||
catbox_link="$(curl -fsS -F "reqtype=fileupload" -F "time=72h" -F "fileToUpload=@/tmp/unm-debugging-output.txt" "https://litterbox.catbox.moe/resources/internals/api.php")"
|
||||
transfer_link="$(curl -fsS --upload-file "/tmp/unm-debugging-output.txt" "https://transfer.sh/unm-debugging-output.txt")"
|
||||
echo -e "\n"
|
||||
echo -e "Log is available at:"
|
||||
echo -e "$catbox_link"
|
||||
echo -e "$transfer_link"
|
||||
|
||||
rm -f "/tmp/unm-debugging-output.txt"
|
||||
@@ -0,0 +1,29 @@
|
||||
{
|
||||
"admin/services/unblockneteasemusic": {
|
||||
"title": "解除网易云音乐播放限制",
|
||||
"order": 50,
|
||||
"action": {
|
||||
"type": "firstchild"
|
||||
},
|
||||
"depends": {
|
||||
"acl": [ "luci-app-unblockneteasemusic" ],
|
||||
"uci": { "unblockneteasemusic": true }
|
||||
}
|
||||
},
|
||||
"admin/services/unblockneteasemusic/config": {
|
||||
"title": "基本设定",
|
||||
"order": 10,
|
||||
"action": {
|
||||
"type": "view",
|
||||
"path": "unblockneteasemusic/config"
|
||||
}
|
||||
},
|
||||
"admin/services/unblockneteasemusic/status": {
|
||||
"title": "状态信息",
|
||||
"order": 20,
|
||||
"action": {
|
||||
"type": "view",
|
||||
"path": "unblockneteasemusic/status"
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,25 @@
|
||||
{
|
||||
"luci-app-unblockneteasemusic": {
|
||||
"description": "Grant access to UnblockNeteaseMusic configuration",
|
||||
"read": {
|
||||
"file": {
|
||||
"/etc/init.d/unblockneteasemusic": [ "exec" ],
|
||||
"/tmp/unblockneteasemusic.log": [ "read" ],
|
||||
"/usr/bin/unm-debug": [ "exec" ],
|
||||
"/usr/share/unblockneteasemusic/update.sh": [ "exec" ],
|
||||
"/usr/share/unblockneteasemusic/core/ca.crt": [ "read" ]
|
||||
},
|
||||
"ubus": {
|
||||
"service": [ "list" ]
|
||||
},
|
||||
"uci": [ "unblockneteasemusic" ]
|
||||
},
|
||||
"write": {
|
||||
"file": {
|
||||
"/usr/share/unblockneteasemusic/server.crt": [ "write" ],
|
||||
"/usr/share/unblockneteasemusic/server.key": [ "write" ]
|
||||
},
|
||||
"uci": [ "unblockneteasemusic" ]
|
||||
}
|
||||
}
|
||||
}
|
||||
104
luci-app-unblockneteasemusic/root/usr/share/unblockneteasemusic/debugging.sh
Executable file
104
luci-app-unblockneteasemusic/root/usr/share/unblockneteasemusic/debugging.sh
Executable file
@@ -0,0 +1,104 @@
|
||||
#!/bin/sh
|
||||
# Copyright (C) 2021-2022 Tianling Shen <cnsztl@immortalwrt.org>
|
||||
|
||||
. /lib/functions.sh
|
||||
|
||||
NAME="unblockneteasemusic"
|
||||
|
||||
command -v "curl" >"/dev/null" || { echo -e "curl is not found."; exit 1; }
|
||||
|
||||
echo -e "Launching luci-app-unblockneteasmusic Debugging Tool..."
|
||||
echo -e "\n"
|
||||
|
||||
echo -e "OpenWrt info:"
|
||||
ubus call system board || cat "/etc/openwrt_release"
|
||||
echo -e "\n"
|
||||
|
||||
echo -e "uclient-fetch info:"
|
||||
opkg info uclient-fetch
|
||||
opkg info libustream-*
|
||||
uclient-fetch -O- 'https://api.github.com/repos/UnblockNeteaseMusic/server/commits?sha=enhanced&path=precompiled' | jsonfilter -e '@[0].sha' || echo -e "Failed to connect to GitHub with uclient-fetch."
|
||||
echo -e "\n"
|
||||
|
||||
echo -e "Node.js info:"
|
||||
opkg info node
|
||||
echo -e "Node.js is placed at $(command -v node || echo "Not Found")"
|
||||
echo -e "Node.js version: $(node -v 2>"/dev/null" || echo "Not Found")"
|
||||
echo -e "\n"
|
||||
|
||||
echo -e "luci-app-unblockneteasmusic info:"
|
||||
opkg info "luci-app-unblockneteasemusic"
|
||||
ls -lh "/etc/config/$NAME" "/etc/init.d/$NAME" "/usr/share/$NAME"
|
||||
cat "/etc/config/$NAME" | sed -e "s,joox_cookie .*,joox_cookie 'set',g" \
|
||||
-e "s,migu_cookie .*,migu_cookie 'set',g" \
|
||||
-e "s,qq_cookie .*,qq_cookie 'set',g" \
|
||||
-e "s,youtube_key .*,youtube_key 'set',g" \
|
||||
-e "s,proxy_server_ip .*,proxy_server_ip 'set',g"
|
||||
echo -e "\n"
|
||||
|
||||
echo -e "UnblockNeteaseMusic Node.js info:"
|
||||
echo -e "Git HEAD version: $(cat "/usr/share/$NAME/core_local_ver" 2>"/dev/null" || echo "Not Found")"
|
||||
echo -e "Core version: $(node "/usr/share/$NAME/core/app.js" -v 2>"/dev/null" || echo "Not Found")"
|
||||
ls -lh "/usr/share/$NAME/core" 2>"/dev/null"
|
||||
echo -e "\n"
|
||||
|
||||
echo -e "Netease networking info:"
|
||||
curl -fsv "http://music.163.com/song/media/outer/url?id=641644.mp3" 2>&1 | grep "Location" || echo -e "Cannot connect to NeteaseMusic."
|
||||
curl -sSL "http://httpdns.n.netease.com/httpdns/v2/d?domain=music.163.com" || echo -e "Cannot connect to Netease HTTPDNS."
|
||||
config_load "$NAME"
|
||||
config_get custom_proxy "config" "proxy_server_ip"
|
||||
[ -n "$custom_proxy" ] && { curl -sL -x "$custom_proxy" "http://music.163.com/song/media/outer/url?id=641644.mp3" 2>&1 | grep "Location" || echo -e "Cannot connect to NeteaseMusic via proxy."; }
|
||||
echo -e "\n"
|
||||
|
||||
echo -e "Port status:"
|
||||
config_get unm_port "config" "http_port" "5200"
|
||||
config_get unm_ports "config" "https_port" "5201"
|
||||
[ "$(config_get "config" "hijack_ways")" = "use_hosts" ] && { unm_port="80"; unm_ports="443"; }
|
||||
netstat -tlpen | grep "$unm_port" || echo -e "No instance found on port $unm_port."
|
||||
netstat -tlpen | grep "$unm_ports" || echo -e "No instance found on port $unm_ports."
|
||||
echo -e "\n"
|
||||
|
||||
echo -e "PROCD running info:"
|
||||
running_stat="$(ubus call service list '{"name": "unblockneteasemusic", "verbose": true}' | \
|
||||
sed -e 's,"JOOX_COOKIE".*","JOOX_COOKIE": "set",g' \
|
||||
-e 's,"MIGU_COOKIE".*","MIGU_COOKIE": "set",g' \
|
||||
-e 's,"QQ_COOKIE".*","QQ_COOKIE": "set",g' \
|
||||
-e 's,"YOUTUBE_KEY".*","YOUTUBE_KEY": "set",g')"
|
||||
[ "$(echo -e "$running_stat" | jsonfilter -e "@.$NAME.instances.$NAME.running")" == "true" ] || is_stopped=1
|
||||
echo -e "$running_stat"
|
||||
|
||||
echo -e "\n"
|
||||
|
||||
[ -n "$is_stopped" ] || {
|
||||
echo -e "Firewall info:"
|
||||
[ -e "/etc/nftables.d/90-$NAME-rules.nft" ] || echo -e 'netease_cloud_music nft rule file not found.'
|
||||
echo -e ""
|
||||
nft list set inet fw4 "acl_neteasemusic_http" 2>&1
|
||||
echo -e ""
|
||||
nft list set inet fw4 "acl_neteasemusic_https" 2>&1
|
||||
echo -e ""
|
||||
nft list set inet fw4 "local_addr" 2>&1
|
||||
echo -e ""
|
||||
nft list set inet fw4 "neteasemusic" 2>&1
|
||||
echo -e ""
|
||||
nft list chain inet fw4 "input_wan" | grep "unblockneteasemusic-http-" 2>"/dev/null" || echo -e 'Http Port pub access rule not found.'
|
||||
echo -e ""
|
||||
nft list chain inet fw4 "input_wan" | grep "unblockneteasemusic-https-" 2>"/dev/null" || echo -e 'Https Port pub access rule not found.'
|
||||
echo -e ""
|
||||
nft list chain inet fw4 "netease_cloud_music" 2>&1
|
||||
echo -e ""
|
||||
nft list chain inet fw4 "netease_cloud_music_redir" 2>&1
|
||||
echo -e ""
|
||||
cat "/tmp/dnsmasq.d/dnsmasq-$NAME.conf"
|
||||
echo -e "\n"
|
||||
|
||||
echo -e "Testing source replacing..."
|
||||
lan_ip="$(uci -q get "network.lan.ipaddr" || echo "127.0.0.1")"
|
||||
|
||||
curl -sSL -X "POST" "https://music.163.com/weapi/song/enhance/player/url/v1?csrf_token=" --data "params=bf3kf%2BOyalbxNS%2FeHAXquH8D2nt2YrhBzww4zy5rj2H%2BeAhdOIaGh4HHHzcoREFcu9Ve35LUgc%2BGE1YJD1HxrJ87ucm5zK%2FFn1lLvHFv1A8ZAuyU1afjG28s2Xja6zpfg00T0EcCeqkK61OpTfAaqw%3D%3D&encSecKey=6bab0dfa7ee3b292f9263a7af466636731cdbbd1d8747c9178c17477e70be899b7788c4a4e315c9fdb8c6e787603db6f9dff62c356f164d35b16b7f2d9ad5ede3cc7336130605521a8f916d308ce86b15c32b81c883ae2ba9c244444d91e1683be93fa0ea3e2a85207c9d693b86b5bb31adb002dd56c0bbcce9c73ec3bf5c105"
|
||||
echo -e ""
|
||||
curl -ksSL -X "POST" -x "http://$lan_ip:$unm_port" "https://music.163.com/weapi/song/enhance/player/url/v1?csrf_token=" --data "params=bf3kf%2BOyalbxNS%2FeHAXquH8D2nt2YrhBzww4zy5rj2H%2BeAhdOIaGh4HHHzcoREFcu9Ve35LUgc%2BGE1YJD1HxrJ87ucm5zK%2FFn1lLvHFv1A8ZAuyU1afjG28s2Xja6zpfg00T0EcCeqkK61OpTfAaqw%3D%3D&encSecKey=6bab0dfa7ee3b292f9263a7af466636731cdbbd1d8747c9178c17477e70be899b7788c4a4e315c9fdb8c6e787603db6f9dff62c356f164d35b16b7f2d9ad5ede3cc7336130605521a8f916d308ce86b15c32b81c883ae2ba9c244444d91e1683be93fa0ea3e2a85207c9d693b86b5bb31adb002dd56c0bbcce9c73ec3bf5c105"
|
||||
echo -e ""
|
||||
}
|
||||
|
||||
cat "/tmp/$NAME.log" 2>"/dev/null" || echo -e "Log is not avaiable."
|
||||
11
luci-app-unblockneteasemusic/root/usr/share/unblockneteasemusic/log_check.sh
Executable file
11
luci-app-unblockneteasemusic/root/usr/share/unblockneteasemusic/log_check.sh
Executable file
@@ -0,0 +1,11 @@
|
||||
#!/bin/sh
|
||||
# SPDX-License-Identifier: GPL-3.0-only
|
||||
# Copyright (C) 2019-2022 Tianling Shen <cnsztl@immortalwrt.org>
|
||||
|
||||
NAME="unblockneteasemusic"
|
||||
|
||||
log_max_size="4" #使用KB计算
|
||||
log_file="/tmp/$NAME.log"
|
||||
|
||||
log_size="$(expr $(ls -l "${log_file}" | awk -F ' ' '{print $5}') / "1024")"
|
||||
[ "${log_size}" -lt "${log_max_size}" ] || echo "" > "${log_file}"
|
||||
@@ -0,0 +1,30 @@
|
||||
{%
|
||||
|
||||
let http_port = o_http_port;
|
||||
let https_port = o_https_port;
|
||||
let pub_access = o_pub_access;
|
||||
let hijack_ways = o_hijack_ways;
|
||||
|
||||
%}
|
||||
|
||||
{% if (pub_access == 1): %}
|
||||
chain input_wan {
|
||||
tcp dport {{ http_port }} counter accept comment "!fw4: unblockneteasemusic-http-pub-access"
|
||||
tcp dport {{ https_port }} counter accept comment "!fw4: unblockneteasemusic-https-pub-access"
|
||||
}
|
||||
{% endif %}
|
||||
|
||||
{% if (hijack_ways == "use_ipset"): %}
|
||||
chain netease_cloud_music {
|
||||
type nat hook prerouting priority -1; policy accept;
|
||||
meta l4proto tcp ip daddr @neteasemusic jump netease_cloud_music_redir;
|
||||
}
|
||||
|
||||
chain netease_cloud_music_redir {
|
||||
ip daddr @local_addr return;
|
||||
ip saddr @acl_neteasemusic_http accept;
|
||||
ip saddr @acl_neteasemusic_https accept;
|
||||
tcp dport 80 counter redirect to :{{ http_port }};
|
||||
tcp dport 443 counter redirect to :{{ https_port }};
|
||||
}
|
||||
{% endif %}
|
||||
@@ -0,0 +1,9 @@
|
||||
{%
|
||||
|
||||
let hijack_ways = o_hijack_ways;
|
||||
if (hijack_ways == "use_ipset") {
|
||||
include("set.uc");
|
||||
}
|
||||
include("chain.uc");
|
||||
|
||||
%}
|
||||
@@ -0,0 +1,73 @@
|
||||
{%
|
||||
|
||||
let o_local_bypass = "
|
||||
0.0.0.0/8
|
||||
10.0.0.0/8
|
||||
100.64.0.0/10
|
||||
127.0.0.0/8
|
||||
169.254.0.0/16
|
||||
172.16.0.0/12
|
||||
192.0.0.0/24
|
||||
192.0.2.0/24
|
||||
192.31.196.0/24
|
||||
192.52.193.0/24
|
||||
192.88.99.0/24
|
||||
192.168.0.0/16
|
||||
192.175.48.0/24
|
||||
198.18.0.0/15
|
||||
198.51.100.0/24
|
||||
203.0.113.0/24
|
||||
224.0.0.0/4
|
||||
240.0.0.0/4
|
||||
";
|
||||
|
||||
let set_suffix = {
|
||||
"acl_neteasemusic_http": {
|
||||
str: o_acl_http_addr,
|
||||
},
|
||||
"acl_neteasemusic_https": {
|
||||
str: o_acl_https_addr,
|
||||
},
|
||||
"local_addr": {
|
||||
str: o_local_bypass,
|
||||
},
|
||||
"neteasemusic": {
|
||||
str: o_neteasemusic_addr,
|
||||
},
|
||||
};
|
||||
|
||||
function set_elements_parse(res, str) {
|
||||
for (let addr in split(str, /[ \t\n]/)) {
|
||||
addr = trim(addr);
|
||||
if (!addr) continue;
|
||||
push(res, addr);
|
||||
}
|
||||
}
|
||||
|
||||
function set_elements(suf) {
|
||||
let obj = set_suffix[suf];
|
||||
let res = [];
|
||||
let addr;
|
||||
|
||||
let str = obj["str"];
|
||||
if (str) {
|
||||
set_elements_parse(res, str);
|
||||
}
|
||||
|
||||
return res;
|
||||
}
|
||||
%}
|
||||
|
||||
{% for (let suf in set_suffix): %}
|
||||
set {{ suf }} {
|
||||
type ipv4_addr;
|
||||
flags interval;
|
||||
{% let elems = set_elements(suf); if (length(elems)): %}
|
||||
elements = {
|
||||
{% for (let i = 0; i < length(elems); i++): %}
|
||||
{{ elems[i] }}{% if (i < length(elems) - 1): %},{% endif %}{% print("\n") %}
|
||||
{% endfor %}
|
||||
}
|
||||
{% endif %}
|
||||
}
|
||||
{% endfor %}
|
||||
104
luci-app-unblockneteasemusic/root/usr/share/unblockneteasemusic/update.sh
Executable file
104
luci-app-unblockneteasemusic/root/usr/share/unblockneteasemusic/update.sh
Executable file
@@ -0,0 +1,104 @@
|
||||
#!/bin/sh
|
||||
# SPDX-License-Identifier: GPL-3.0-only
|
||||
# Copyright (C) 2019-2023 Tianling Shen <cnsztl@immortalwrt.org>
|
||||
|
||||
NAME="unblockneteasemusic"
|
||||
LOCK="/tmp/$NAME.update_core.lock"
|
||||
|
||||
check_core_if_already_running() {
|
||||
if [ -e "$LOCK" ]; then
|
||||
echo -e "\nA task is already running." >> "/tmp/$NAME.log"
|
||||
exit 2
|
||||
else
|
||||
touch "$LOCK"
|
||||
fi
|
||||
}
|
||||
|
||||
clean_log(){
|
||||
echo "" > "/tmp/$NAME.log"
|
||||
}
|
||||
|
||||
check_core_latest_version() {
|
||||
core_latest_ver="$(uclient-fetch -qO- 'https://api.github.com/repos/UnblockNeteaseMusic/server/commits?sha=enhanced&path=precompiled' | jsonfilter -e '@[0].sha')"
|
||||
[ -n "${core_latest_ver}" ] || { echo -e "\nFailed to check latest core version, please try again later." >> "/tmp/$NAME.log"; rm -f "$LOCK"; exit 1; }
|
||||
if [ ! -e "/usr/share/$NAME/core_local_ver" ]; then
|
||||
clean_log
|
||||
echo -e "Local version: NOT FOUND, latest version: ${core_latest_ver}." >> "/tmp/$NAME.log"
|
||||
update_core
|
||||
else
|
||||
if [ "$(cat /usr/share/$NAME/core_local_ver)" != "${core_latest_ver}" ]; then
|
||||
clean_log
|
||||
echo -e "Local version: $(cat /usr/share/$NAME/core_local_ver 2>"/dev/null"), latest version: ${core_latest_ver}." >> "/tmp/$NAME.log"
|
||||
update_core
|
||||
else
|
||||
echo -e "\nLocal version: $(cat /usr/share/$NAME/core_local_ver 2>"/dev/null"), latest version: ${core_latest_ver}." >> "/tmp/$NAME.log"
|
||||
echo -e "You're already using the latest version." >> "/tmp/$NAME.log"
|
||||
rm -f "$LOCK"
|
||||
exit 3
|
||||
fi
|
||||
fi
|
||||
}
|
||||
|
||||
update_core() {
|
||||
echo -e "Updating core..." >> "/tmp/$NAME.log"
|
||||
|
||||
mkdir -p "/usr/share/$NAME/core"
|
||||
rm -rf "/usr/share/$NAME/core"/*
|
||||
|
||||
for file in $(uclient-fetch -qO- "https://api.github.com/repos/UnblockNeteaseMusic/server/contents/precompiled" | jsonfilter -e '@[*].path')
|
||||
do
|
||||
uclient-fetch "https://fastly.jsdelivr.net/gh/UnblockNeteaseMusic/server@$core_latest_ver/$file" -qO "/usr/share/$NAME/core/${file##*/}"
|
||||
[ -s "/usr/share/$NAME/core/${file##*/}" ] || {
|
||||
echo -e "Failed to download ${file##*/}." >> "/tmp/$NAME.log"
|
||||
rm -f "$LOCK"
|
||||
exit 1
|
||||
}
|
||||
done
|
||||
|
||||
for cert in "ca.crt" "server.crt" "server.key"
|
||||
do
|
||||
uclient-fetch "https://fastly.jsdelivr.net/gh/UnblockNeteaseMusic/server@enhanced/${cert}" -qO "/usr/share/$NAME/core/${cert}"
|
||||
[ -s "/usr/share/$NAME/core/${cert}" ] || {
|
||||
echo -e "Failed to download ${cert}." >> "/tmp/$NAME.log"
|
||||
rm -f "$LOCK"
|
||||
exit 1
|
||||
}
|
||||
done
|
||||
|
||||
echo -e "${core_latest_ver}" > "/usr/share/$NAME/core_local_ver"
|
||||
[ -n "${non_restart}" ] || /etc/init.d/"$NAME" restart
|
||||
|
||||
echo -e "Succeeded in updating core." > "/tmp/$NAME.log"
|
||||
echo -e "Current core version: ${core_latest_ver}.\n" >> "/tmp/$NAME.log"
|
||||
rm -f "$LOCK"
|
||||
}
|
||||
|
||||
case "$1" in
|
||||
"check_version")
|
||||
if [ ! -e "/usr/share/$NAME/core_local_ver" ] || [ ! -e "/usr/share/$NAME/core/app.js" ]; then
|
||||
echo -e "Not installed."
|
||||
exit 2
|
||||
else
|
||||
version="$(node "/usr/share/$NAME/core/app.js" -v)"
|
||||
commit="$(cat "/usr/share/$NAME/core_local_ver" | head -c7)"
|
||||
echo "$version ($commit)"
|
||||
exit 0
|
||||
fi
|
||||
;;
|
||||
"update_core")
|
||||
check_core_if_already_running
|
||||
check_core_latest_version
|
||||
;;
|
||||
"update_core_non_restart")
|
||||
non_restart=1
|
||||
check_core_if_already_running
|
||||
check_core_latest_version
|
||||
;;
|
||||
"remove_core")
|
||||
/etc/init.d/"$NAME" stop
|
||||
rm -rf "/usr/share/$NAME/core" "/usr/share/$NAME/core_local_ver" "$LOCK"
|
||||
;;
|
||||
*)
|
||||
echo -e "Usage: $0/update.sh check_version | update_core | remove_core"
|
||||
;;
|
||||
esac
|
||||
80
miniupnpd/Makefile
Normal file
80
miniupnpd/Makefile
Normal file
@@ -0,0 +1,80 @@
|
||||
#
|
||||
# Copyright (C) 2006-2014 OpenWrt.org
|
||||
#
|
||||
# This is free software, licensed under the GNU General Public License v2.
|
||||
# See /LICENSE for more information.
|
||||
#
|
||||
|
||||
include $(TOPDIR)/rules.mk
|
||||
|
||||
PKG_NAME:=miniupnpd
|
||||
PKG_VERSION:=2.0.20170421
|
||||
PKG_RELEASE:=3
|
||||
|
||||
PKG_SOURCE_URL:=http://miniupnp.tuxfamily.org/files
|
||||
PKG_SOURCE:=$(PKG_NAME)-$(PKG_VERSION).tar.gz
|
||||
PKG_HASH:=9677aeccadf73b4bf8bb9d832c32b5da8266b4d58eed888f3fd43d7656405643
|
||||
|
||||
PKG_MAINTAINER:=Markus Stenberg <fingon@iki.fi>
|
||||
PKG_LICENSE:=BSD-3-Clause
|
||||
|
||||
include $(INCLUDE_DIR)/package.mk
|
||||
|
||||
define Package/miniupnpd
|
||||
SECTION:=net
|
||||
CATEGORY:=Network
|
||||
DEPENDS:=+iptables +libip4tc +libuuid
|
||||
TITLE:=Lightweight UPnP IGD, NAT-PMP & PCP daemon
|
||||
SUBMENU:=Firewall
|
||||
URL:=http://miniupnp.free.fr/
|
||||
endef
|
||||
|
||||
define Package/miniupnpd/config
|
||||
config MINIUPNPD_IGDv2
|
||||
bool
|
||||
default n
|
||||
prompt "Enable IGDv2"
|
||||
endef
|
||||
|
||||
define Package/miniupnpd/conffiles
|
||||
/etc/config/upnpd
|
||||
endef
|
||||
|
||||
define Package/miniupnpd/postinst
|
||||
#!/bin/sh
|
||||
|
||||
if [ -z "$$IPKG_INSTROOT" ]; then
|
||||
( . /etc/uci-defaults/99-miniupnpd )
|
||||
rm -f /etc/uci-defaults/99-miniupnpd
|
||||
fi
|
||||
|
||||
exit 0
|
||||
endef
|
||||
|
||||
define Build/Prepare
|
||||
$(call Build/Prepare/Default)
|
||||
echo "OpenWrt" | tr \(\)\ _ >$(PKG_BUILD_DIR)/os.openwrt
|
||||
endef
|
||||
|
||||
MAKE_FLAGS += \
|
||||
TARGET_OPENWRT=1 TEST=0 \
|
||||
LIBS="" \
|
||||
CC="$(TARGET_CC) -DIPTABLES_143 \
|
||||
-lip4tc -luuid" \
|
||||
CONFIG_OPTIONS="--portinuse --leasefile \
|
||||
$(if $(CONFIG_MINIUPNPD_IGDv2),--igd2)" \
|
||||
-f Makefile.linux \
|
||||
miniupnpd
|
||||
|
||||
|
||||
define Package/miniupnpd/install
|
||||
$(INSTALL_DIR) $(1)/usr/sbin $(1)/etc/init.d $(1)/etc/config $(1)/etc/uci-defaults $(1)/etc/hotplug.d/iface $(1)/usr/share/miniupnpd
|
||||
$(INSTALL_BIN) $(PKG_BUILD_DIR)/miniupnpd $(1)/usr/sbin/miniupnpd
|
||||
$(INSTALL_BIN) ./files/miniupnpd.init $(1)/etc/init.d/miniupnpd
|
||||
$(INSTALL_CONF) ./files/upnpd.config $(1)/etc/config/upnpd
|
||||
$(INSTALL_DATA) ./files/miniupnpd.hotplug $(1)/etc/hotplug.d/iface/50-miniupnpd
|
||||
$(INSTALL_DATA) ./files/miniupnpd.defaults $(1)/etc/uci-defaults/99-miniupnpd
|
||||
$(INSTALL_DATA) ./files/firewall.include $(1)/usr/share/miniupnpd/firewall.include
|
||||
endef
|
||||
|
||||
$(eval $(call BuildPackage,miniupnpd))
|
||||
57
miniupnpd/files/firewall.include
Normal file
57
miniupnpd/files/firewall.include
Normal file
@@ -0,0 +1,57 @@
|
||||
#!/bin/sh
|
||||
# miniupnpd integration for firewall3
|
||||
|
||||
IP6TABLES=/usr/sbin/ip6tables
|
||||
|
||||
iptables -t filter -N MINIUPNPD 2>/dev/null
|
||||
iptables -t nat -N MINIUPNPD 2>/dev/null
|
||||
iptables -t nat -N MINIUPNPD-POSTROUTING 2>/dev/null
|
||||
|
||||
[ -x $IP6TABLES ] && $IP6TABLES -t filter -N MINIUPNPD 2>/dev/null
|
||||
|
||||
. /lib/functions/network.sh
|
||||
|
||||
ADDED=0
|
||||
|
||||
add_extzone_rules() {
|
||||
local ext_zone=$1
|
||||
|
||||
[ -z "$ext_zone" ] && return
|
||||
|
||||
# IPv4 - due to NAT, need to add both to nat and filter table
|
||||
iptables -t filter -I zone_${ext_zone}_forward -j MINIUPNPD
|
||||
iptables -t nat -I zone_${ext_zone}_prerouting -j MINIUPNPD
|
||||
iptables -t nat -I zone_${ext_zone}_postrouting -j MINIUPNPD-POSTROUTING
|
||||
|
||||
# IPv6 if available - filter only
|
||||
[ -x $IP6TABLES ] && {
|
||||
$IP6TABLES -t filter -I zone_${ext_zone}_forward -j MINIUPNPD
|
||||
}
|
||||
ADDED=$(($ADDED + 1))
|
||||
}
|
||||
|
||||
# By default, user configuration is king.
|
||||
|
||||
for ext_iface in $(uci -q get upnpd.config.external_iface); do
|
||||
add_extzone_rules $(fw3 -q network "$ext_iface")
|
||||
done
|
||||
|
||||
add_extzone_rules $(uci -q get upnpd.config.external_zone)
|
||||
|
||||
[ ! $ADDED = 0 ] && exit 0
|
||||
|
||||
|
||||
# If really nothing is available, resort to network_find_wan{,6} and
|
||||
# assume external interfaces all have same firewall zone.
|
||||
|
||||
# (This heuristic may fail horribly, in case of e.g. multihoming, so
|
||||
# please set external_zone in that case!)
|
||||
|
||||
network_find_wan wan_iface
|
||||
network_find_wan6 wan6_iface
|
||||
|
||||
for ext_iface in $wan_iface $wan6_iface; do
|
||||
# fw3 -q network fails on sub-interfaces => map to device first
|
||||
network_get_device ext_device $ext_iface
|
||||
add_extzone_rules $(fw3 -q device "$ext_device")
|
||||
done
|
||||
13
miniupnpd/files/miniupnpd.defaults
Normal file
13
miniupnpd/files/miniupnpd.defaults
Normal file
@@ -0,0 +1,13 @@
|
||||
#!/bin/sh
|
||||
|
||||
uci -q batch <<-EOT
|
||||
delete firewall.miniupnpd
|
||||
set firewall.miniupnpd=include
|
||||
set firewall.miniupnpd.type=script
|
||||
set firewall.miniupnpd.path=/usr/share/miniupnpd/firewall.include
|
||||
set firewall.miniupnpd.family=any
|
||||
set firewall.miniupnpd.reload=1
|
||||
commit firewall
|
||||
EOT
|
||||
|
||||
exit 0
|
||||
39
miniupnpd/files/miniupnpd.hotplug
Normal file
39
miniupnpd/files/miniupnpd.hotplug
Normal file
@@ -0,0 +1,39 @@
|
||||
#!/bin/sh
|
||||
|
||||
/etc/init.d/miniupnpd enabled || exit 0
|
||||
|
||||
. /lib/functions/service.sh
|
||||
|
||||
# If miniupnpd is not running:
|
||||
# - check on _any_ event (even updates may contribute to network_find_wan*)
|
||||
|
||||
# If miniupnpd _is_ running:
|
||||
# - check only on ifup (otherwise lease updates etc would cause
|
||||
# miniupnpd state loss)
|
||||
|
||||
[ ! "$ACTION" = "ifup" ] && service_check /usr/sbin/miniupnpd && exit 0
|
||||
|
||||
tmpconf="/var/etc/miniupnpd.conf"
|
||||
extiface=$(uci get upnpd.config.external_iface)
|
||||
extzone=$(uci get upnpd.config.external_zone)
|
||||
|
||||
. /lib/functions/network.sh
|
||||
|
||||
for iface in $(uci get upnpd.config.internal_iface); do
|
||||
network_get_device device $iface
|
||||
[ "$DEVICE" = "$device" ] && /etc/init.d/miniupnpd restart && exit 0
|
||||
done
|
||||
|
||||
|
||||
if [ -z "$extiface" ] ; then
|
||||
# manual external zone (if dynamically find interfaces
|
||||
# belonging to it) overrides network_find_wan*
|
||||
if [ -n "$extzone" ] ; then
|
||||
ifname=$(fw3 -q zone $extzone | head -1)
|
||||
fi
|
||||
[ -n "$extiface" ] || network_find_wan extiface
|
||||
[ -n "$extiface" ] || network_find_wan6 extiface
|
||||
fi
|
||||
|
||||
[ -n "$ifname" ] || network_get_device ifname ${extiface}
|
||||
grep -q "ext_ifname=$ifname" $tmpconf || /etc/init.d/miniupnpd restart
|
||||
219
miniupnpd/files/miniupnpd.init
Normal file
219
miniupnpd/files/miniupnpd.init
Normal file
@@ -0,0 +1,219 @@
|
||||
#!/bin/sh /etc/rc.common
|
||||
# Copyright (C) 2006-2014 OpenWrt.org
|
||||
|
||||
START=94
|
||||
STOP=15
|
||||
|
||||
USE_PROCD=1
|
||||
PROG=/usr/sbin/miniupnpd
|
||||
|
||||
upnpd_get_port_range() {
|
||||
local _var="$1"; shift
|
||||
local _val
|
||||
|
||||
config_get _val "$@"
|
||||
|
||||
case "$_val" in
|
||||
[0-9]*[:-][0-9]*)
|
||||
export -n -- "${_var}_start=${_val%%[:-]*}"
|
||||
export -n -- "${_var}_end=${_val##*[:-]}"
|
||||
;;
|
||||
[0-9]*)
|
||||
export -n -- "${_var}_start=$_val"
|
||||
export -n -- "${_var}_end="
|
||||
;;
|
||||
esac
|
||||
}
|
||||
|
||||
conf_rule_add() {
|
||||
local cfg="$1"
|
||||
local tmpconf="$2"
|
||||
local action external_port_start external_port_end int_addr
|
||||
local internal_port_start internal_port_end
|
||||
|
||||
config_get action "$cfg" action "deny" # allow or deny
|
||||
upnpd_get_port_range "ext" "$cfg" ext_ports "0-65535" # external ports: x, x-y, x:y
|
||||
config_get int_addr "$cfg" int_addr "0.0.0.0/0" # ip or network and subnet mask (internal)
|
||||
upnpd_get_port_range "int" "$cfg" int_ports "0-65535" # internal ports: x, x-y, x:y or range
|
||||
|
||||
# Make a single IP IP/32 so that miniupnpd.conf can use it.
|
||||
case "$int_addr" in
|
||||
*/*) ;;
|
||||
*) int_addr="$int_addr/32" ;;
|
||||
esac
|
||||
|
||||
echo "${action} ${ext_start}${ext_end:+-}${ext_end} ${int_addr} ${int_start}${int_end:+-}${int_end}" >>$tmpconf
|
||||
}
|
||||
|
||||
upnpd_write_bool() {
|
||||
local opt="$1"
|
||||
local def="${2:-0}"
|
||||
local alt="$3"
|
||||
local val
|
||||
|
||||
config_get_bool val config "$opt" "$def"
|
||||
if [ "$val" -eq 0 ]; then
|
||||
echo "${alt:-$opt}=no" >> $tmpconf
|
||||
else
|
||||
echo "${alt:-$opt}=yes" >> $tmpconf
|
||||
fi
|
||||
}
|
||||
|
||||
boot() {
|
||||
return
|
||||
}
|
||||
|
||||
upnpd() {
|
||||
config_load "upnpd"
|
||||
local extiface intiface upload download logging secure enabled natpmp
|
||||
local extip port usesysuptime conffile serial_number model_number
|
||||
local uuid notify_interval presentation_url enable_upnp
|
||||
local upnp_lease_file clean_ruleset_threshold clean_ruleset_interval
|
||||
local ipv6_listening_ip enabled
|
||||
|
||||
config_get_bool enabled config enabled 1
|
||||
|
||||
[ "$enabled" -gt 0 ] || return 1
|
||||
|
||||
config_get extiface config external_iface
|
||||
config_get extzone config external_zone
|
||||
config_get intiface config internal_iface
|
||||
config_get extip config external_ip
|
||||
config_get port config port 5000
|
||||
config_get upload config upload
|
||||
config_get download config download
|
||||
config_get_bool logging config log_output 0
|
||||
config_get conffile config config_file
|
||||
config_get serial_number config serial_number
|
||||
config_get model_number config model_number
|
||||
config_get uuid config uuid
|
||||
config_get notify_interval config notify_interval
|
||||
config_get presentation_url config presentation_url
|
||||
config_get upnp_lease_file config upnp_lease_file
|
||||
config_get clean_ruleset_threshold config clean_ruleset_threshold
|
||||
config_get clean_ruleset_interval config clean_ruleset_interval
|
||||
config_get ipv6_listening_ip config ipv6_listening_ip
|
||||
|
||||
local args
|
||||
|
||||
. /lib/functions/network.sh
|
||||
|
||||
local ifname
|
||||
|
||||
# manual external interface overrides everything
|
||||
if [ -z "$extiface" ] ; then
|
||||
# manual external zone (if dynamically find interfaces
|
||||
# belonging to it) overrides network_find_wan*
|
||||
if [ -n "$extzone" ] ; then
|
||||
ifname=$(fw3 -q zone $extzone | head -1)
|
||||
fi
|
||||
[ -n "$extiface" ] || network_find_wan extiface
|
||||
[ -n "$extiface" ] || network_find_wan6 extiface
|
||||
fi
|
||||
|
||||
[ -n "$ifname" ] || network_get_device ifname ${extiface}
|
||||
|
||||
if [ -n "$conffile" ]; then
|
||||
args="-f $conffile"
|
||||
else
|
||||
local tmpconf="/var/etc/miniupnpd.conf"
|
||||
args="-f $tmpconf"
|
||||
mkdir -p /var/etc
|
||||
|
||||
echo "ext_ifname=$ifname" >$tmpconf
|
||||
|
||||
[ -n "$extip" ] && \
|
||||
echo "ext_ip=$extip" >>$tmpconf
|
||||
|
||||
local iface
|
||||
for iface in ${intiface:-lan}; do
|
||||
local device
|
||||
network_get_device device "$iface" && {
|
||||
echo "listening_ip=$device" >>$tmpconf
|
||||
}
|
||||
done
|
||||
|
||||
[ "$port" != "auto" ] && \
|
||||
echo "port=$port" >>$tmpconf
|
||||
|
||||
config_load "upnpd"
|
||||
upnpd_write_bool enable_natpmp 1
|
||||
upnpd_write_bool enable_upnp 1
|
||||
upnpd_write_bool secure_mode 1
|
||||
upnpd_write_bool pcp_allow_thirdparty 0
|
||||
upnpd_write_bool system_uptime 1
|
||||
|
||||
[ -n "$upnp_lease_file" ] && \
|
||||
echo "lease_file=$upnp_lease_file" >>$tmpconf
|
||||
|
||||
[ -n "$upload" -a -n "$download" ] && {
|
||||
echo "bitrate_down=$(($download * 1024 * 8))" >>$tmpconf
|
||||
echo "bitrate_up=$(($upload * 1024 * 8))" >>$tmpconf
|
||||
}
|
||||
|
||||
[ -n "${presentation_url}" ] && \
|
||||
echo "presentation_url=${presentation_url}" >>$tmpconf
|
||||
|
||||
[ -n "${notify_interval}" ] && \
|
||||
echo "notify_interval=${notify_interval}" >>$tmpconf
|
||||
|
||||
[ -n "${clean_ruleset_threshold}" ] && \
|
||||
echo "clean_ruleset_threshold=${clean_ruleset_threshold}" >>$tmpconf
|
||||
|
||||
[ -n "${clean_ruleset_interval}" ] && \
|
||||
echo "clean_ruleset_interval=${clean_ruleset_interval}" >>$tmpconf
|
||||
|
||||
[ -n "${ipv6_listening_ip}" ] && \
|
||||
echo "ipv6_listening_ip=${ipv6_listening_ip}" >>$tmpconf
|
||||
|
||||
[ -z "$uuid" ] && {
|
||||
uuid="$(cat /proc/sys/kernel/random/uuid)"
|
||||
uci set upnpd.config.uuid=$uuid
|
||||
uci commit upnpd
|
||||
}
|
||||
|
||||
[ "$uuid" = "nocli" ] || \
|
||||
echo "uuid=$uuid" >>$tmpconf
|
||||
|
||||
[ -n "${serial_number}" ] && \
|
||||
echo "serial=${serial_number}" >>$tmpconf
|
||||
|
||||
[ -n "${model_number}" ] && \
|
||||
echo "model_number=${model_number}" >>$tmpconf
|
||||
|
||||
config_foreach conf_rule_add perm_rule "$tmpconf"
|
||||
fi
|
||||
|
||||
|
||||
if [ -n "$ifname" ]; then
|
||||
# start firewall
|
||||
iptables -L MINIUPNPD >/dev/null 2>/dev/null || fw3 reload
|
||||
else
|
||||
logger -t "upnp daemon" "external interface not found, not starting"
|
||||
fi
|
||||
|
||||
procd_open_instance
|
||||
procd_set_param command "$PROG"
|
||||
procd_set_param respawn
|
||||
procd_append_param command -f "$tmpconf"
|
||||
[ "$log_output" = "1" ] && procd_append_param command -d
|
||||
procd_close_instance
|
||||
}
|
||||
|
||||
stop_service() {
|
||||
iptables -t nat -F MINIUPNPD 2>/dev/null
|
||||
iptables -t filter -F MINIUPNPD 2>/dev/null
|
||||
|
||||
[ -x /usr/sbin/ip6tables ] && {
|
||||
ip6tables -t filter -F MINIUPNPD 2>/dev/null
|
||||
}
|
||||
}
|
||||
|
||||
start_service() {
|
||||
config_load "upnpd"
|
||||
config_foreach upnpd "upnpd"
|
||||
}
|
||||
|
||||
service_triggers() {
|
||||
procd_add_reload_trigger "upnpd"
|
||||
}
|
||||
27
miniupnpd/files/upnpd.config
Normal file
27
miniupnpd/files/upnpd.config
Normal file
@@ -0,0 +1,27 @@
|
||||
config upnpd config
|
||||
option enabled 0
|
||||
option enable_natpmp 1
|
||||
option enable_upnp 1
|
||||
option secure_mode 1
|
||||
option log_output 0
|
||||
option download 1024
|
||||
option upload 512
|
||||
#by default, looked up dynamically from ubus
|
||||
#option external_iface wan
|
||||
option internal_iface lan
|
||||
option port 5000
|
||||
option upnp_lease_file /var/upnp.leases
|
||||
|
||||
config perm_rule
|
||||
option action allow
|
||||
option ext_ports 1024-65535
|
||||
option int_addr 0.0.0.0/0 # Does not override secure_mode
|
||||
option int_ports 1024-65535
|
||||
option comment "Allow high ports"
|
||||
|
||||
config perm_rule
|
||||
option action deny
|
||||
option ext_ports 0-65535
|
||||
option int_addr 0.0.0.0/0
|
||||
option int_ports 0-65535
|
||||
option comment "Default deny"
|
||||
25
miniupnpd/patches/100-no-daemon.patch
Normal file
25
miniupnpd/patches/100-no-daemon.patch
Normal file
@@ -0,0 +1,25 @@
|
||||
--- a/miniupnpd.c
|
||||
+++ b/miniupnpd.c
|
||||
@@ -1727,21 +1727,7 @@ init(int argc, char * * argv, struct runtime_vars * v)
|
||||
}
|
||||
}
|
||||
|
||||
- if(debug_flag)
|
||||
- {
|
||||
- pid = getpid();
|
||||
- }
|
||||
- else
|
||||
- {
|
||||
-#ifdef USE_DAEMON
|
||||
- if(daemon(0, 0)<0) {
|
||||
- perror("daemon()");
|
||||
- }
|
||||
- pid = getpid();
|
||||
-#else
|
||||
- pid = daemonize();
|
||||
-#endif
|
||||
- }
|
||||
+ pid = getpid();
|
||||
|
||||
openlog_option = LOG_PID|LOG_CONS;
|
||||
if(debug_flag)
|
||||
23
miniupnpd/patches/101-no-ssl-uuid.patch
Normal file
23
miniupnpd/patches/101-no-ssl-uuid.patch
Normal file
@@ -0,0 +1,23 @@
|
||||
We do not need to autodetect SSL/UUID; SSL we do not support, UUID we always do.
|
||||
|
||||
--- a/Makefile.linux
|
||||
+++ b/Makefile.linux
|
||||
@@ -153,14 +153,18 @@ LDLIBS += $(shell $(PKG_CONFIG) --static
|
||||
LDLIBS += $(shell $(PKG_CONFIG) --static --libs-only-l libnetfilter_conntrack)
|
||||
endif # ($(TEST),1)
|
||||
|
||||
+ifeq ($(TARGET_OPENWRT),)
|
||||
+# n/a - we don't enable https server for IGD v2 anyway in OpenWrt
|
||||
LDLIBS += $(shell $(PKG_CONFIG) --static --libs-only-l libssl)
|
||||
|
||||
+# n/a - we hardcodedly support libuuid
|
||||
TEST := $(shell $(PKG_CONFIG) --exists uuid && echo 1)
|
||||
ifeq ($(TEST),1)
|
||||
LDLIBS += $(shell $(PKG_CONFIG) --static --libs-only-l uuid)
|
||||
else
|
||||
$(info please install uuid-dev package / libuuid)
|
||||
endif # ($(TEST),1)
|
||||
+endif
|
||||
|
||||
TESTUPNPDESCGENOBJS = testupnpdescgen.o upnpdescgen.o
|
||||
|
||||
10
miniupnpd/patches/102-ipv6-ext-port.patch
Normal file
10
miniupnpd/patches/102-ipv6-ext-port.patch
Normal file
@@ -0,0 +1,10 @@
|
||||
--- a/pcpserver.c
|
||||
+++ b/pcpserver.c
|
||||
@@ -982,6 +982,7 @@ static int CreatePCPMap_NAT(pcp_info_t *
|
||||
timestamp);
|
||||
if (r < 0)
|
||||
return PCP_ERR_NO_RESOURCES;
|
||||
+ pcp_msg_info->ext_port = pcp_msg_info->int_port;
|
||||
return PCP_SUCCESS;
|
||||
}
|
||||
|
||||
27
miniupnpd/patches/103-no-ipv6-autodetection.patch
Normal file
27
miniupnpd/patches/103-no-ipv6-autodetection.patch
Normal file
@@ -0,0 +1,27 @@
|
||||
The miniupnpd makefile tries to autodetect iptables capabilities.
|
||||
This will incorrectly detect capabilities such as ipv6 support even though it is disabled for the target build.
|
||||
|
||||
As the OpenWRT buildsystem already passes the right compile flags, we can skip the autodetection.
|
||||
|
||||
|
||||
--- a/netfilter/Makefile
|
||||
+++ b/netfilter/Makefile
|
||||
@@ -38,8 +38,6 @@ endif
|
||||
endif
|
||||
endif
|
||||
|
||||
-LIBS += /lib/libip4tc.so /lib/libip6tc.so
|
||||
-
|
||||
all: iptcrdr.o testiptcrdr iptpinhole.o \
|
||||
testiptcrdr_peer testiptcrdr_dscp test_nfct_get
|
||||
# testiptpinhole
|
||||
--- a/Makefile.linux
|
||||
+++ b/Makefile.linux
|
||||
@@ -73,7 +73,6 @@ CPPFLAGS += -DIPTABLES_143
|
||||
endif
|
||||
|
||||
CFLAGS += $(shell $(PKG_CONFIG) --cflags libiptc)
|
||||
-LDLIBS += $(shell $(PKG_CONFIG) --static --libs-only-l libiptc)
|
||||
LDFLAGS += $(shell $(PKG_CONFIG) --libs-only-L libiptc)
|
||||
LDFLAGS += $(shell $(PKG_CONFIG) --libs-only-other libiptc)
|
||||
else
|
||||
20
miniupnpd/patches/104-always-libuuid.patch
Normal file
20
miniupnpd/patches/104-always-libuuid.patch
Normal file
@@ -0,0 +1,20 @@
|
||||
As it turns out, the 'magic' libuuid/bsd uuid check just checks
|
||||
outside buildtree altogether for the uuid_generate. So we just
|
||||
hardcode it.
|
||||
|
||||
--- a/genconfig.sh
|
||||
+++ b/genconfig.sh
|
||||
@@ -367,12 +367,7 @@ case $FW in
|
||||
esac
|
||||
|
||||
# UUID API
|
||||
-if grep uuid_create /usr/include/uuid.h > /dev/null 2>&1 ; then
|
||||
- echo "#define BSD_UUID" >> ${CONFIGFILE}
|
||||
-fi
|
||||
-if grep uuid_generate /usr/include/uuid/uuid.h > /dev/null 2>&1 ; then
|
||||
- echo "#define LIB_UUID" >> ${CONFIGFILE}
|
||||
-fi
|
||||
+echo "#define LIB_UUID" >> ${CONFIGFILE}
|
||||
|
||||
# set V6SOCKETS_ARE_V6ONLY to 0 if it was not set above
|
||||
if [ -z "$V6SOCKETS_ARE_V6ONLY" ] ; then
|
||||
90
miniupnpd/patches/105-build-with-kernel-5.4.patch
Normal file
90
miniupnpd/patches/105-build-with-kernel-5.4.patch
Normal file
@@ -0,0 +1,90 @@
|
||||
--- a/netfilter/iptcrdr.c
|
||||
+++ b/netfilter/iptcrdr.c
|
||||
@@ -1116,9 +1116,13 @@ addnatrule(int proto, unsigned short epo
|
||||
} else {
|
||||
match = get_udp_match(eport, 0);
|
||||
}
|
||||
- e->nfcache = NFC_IP_DST_PT;
|
||||
+#ifdef NFC_UNKNOWN
|
||||
+ e->nfcache = NFC_UNKNOWN;
|
||||
+#endif
|
||||
target = get_dnat_target(iaddr, iport);
|
||||
- e->nfcache |= NFC_UNKNOWN;
|
||||
+#ifdef NFC_IP_DST_PT
|
||||
+ e->nfcache |= NFC_IP_DST_PT;
|
||||
+#endif
|
||||
tmp = realloc(e, sizeof(struct ipt_entry)
|
||||
+ match->u.match_size
|
||||
+ target->u.target_size);
|
||||
@@ -1186,9 +1190,13 @@ addmasqueraderule(int proto,
|
||||
} else {
|
||||
match = get_udp_match(0, iport);
|
||||
}
|
||||
- e->nfcache = NFC_IP_DST_PT;
|
||||
+#ifdef NFC_UNKNOWN
|
||||
+ e->nfcache = NFC_UNKNOWN;
|
||||
+#endif
|
||||
target = get_masquerade_target(eport);
|
||||
- e->nfcache |= NFC_UNKNOWN;
|
||||
+#ifdef NFC_IP_DST_PT
|
||||
+ e->nfcache |= NFC_IP_DST_PT;
|
||||
+#endif
|
||||
tmp = realloc(e, sizeof(struct ipt_entry)
|
||||
+ match->u.match_size
|
||||
+ target->u.target_size);
|
||||
@@ -1266,9 +1274,16 @@ addpeernatrule(int proto,
|
||||
} else {
|
||||
match = get_udp_match(rport, iport);
|
||||
}
|
||||
- e->nfcache = NFC_IP_DST_PT | NFC_IP_SRC_PT;
|
||||
+#ifdef NFC_UNKNOWN
|
||||
+ e->nfcache = NFC_UNKNOWN;
|
||||
+#endif
|
||||
target = get_snat_target(eaddr, eport);
|
||||
- e->nfcache |= NFC_UNKNOWN;
|
||||
+#ifdef NFC_IP_DST_PT
|
||||
+ e->nfcache |= NFC_IP_DST_PT;
|
||||
+#endif
|
||||
+#ifdef NFC_IP_SRC_PT
|
||||
+ e->nfcache |= NFC_IP_SRC_PT;
|
||||
+#endif
|
||||
tmp = realloc(e, sizeof(struct ipt_entry)
|
||||
+ match->u.match_size
|
||||
+ target->u.target_size);
|
||||
@@ -1337,9 +1352,16 @@ addpeerdscprule(int proto, unsigned char
|
||||
} else {
|
||||
match = get_udp_match(rport, iport);
|
||||
}
|
||||
- e->nfcache = NFC_IP_DST_PT | NFC_IP_SRC_PT;
|
||||
+#ifdef NFC_UNKNOWN
|
||||
+ e->nfcache = NFC_UNKNOWN;
|
||||
+#endif
|
||||
target = get_dscp_target(dscp);
|
||||
- e->nfcache |= NFC_UNKNOWN;
|
||||
+#ifdef NFC_IP_DST_PT
|
||||
+ e->nfcache |= NFC_IP_DST_PT;
|
||||
+#endif
|
||||
+#ifdef NFC_IP_SRC_PT
|
||||
+ e->nfcache |= NFC_IP_SRC_PT;
|
||||
+#endif
|
||||
tmp = realloc(e, sizeof(struct ipt_entry)
|
||||
+ match->u.match_size
|
||||
+ target->u.target_size);
|
||||
@@ -1420,11 +1442,15 @@ add_filter_rule(int proto, const char *
|
||||
} else {
|
||||
match = get_udp_match(iport,0);
|
||||
}
|
||||
- e->nfcache = NFC_IP_DST_PT;
|
||||
e->ip.dst.s_addr = inet_addr(iaddr);
|
||||
e->ip.dmsk.s_addr = INADDR_NONE;
|
||||
+#ifdef NFC_UNKNOWN
|
||||
+ e->nfcache = NFC_UNKNOWN;
|
||||
+#endif
|
||||
target = get_accept_target();
|
||||
- e->nfcache |= NFC_UNKNOWN;
|
||||
+#ifdef NFC_IP_DST_PT
|
||||
+ e->nfcache |= NFC_IP_DST_PT;
|
||||
+#endif
|
||||
tmp = realloc(e, sizeof(struct ipt_entry)
|
||||
+ match->u.match_size
|
||||
+ target->u.target_size);
|
||||
13
miniupnpd/patches/106-spam-syslog-ignoring.patch
Normal file
13
miniupnpd/patches/106-spam-syslog-ignoring.patch
Normal file
@@ -0,0 +1,13 @@
|
||||
--- a/minissdp.c 2017-04-21 19:24:23.000000000 +0800
|
||||
+++ b/minissdp.c 2021-06-22 07:01:24.000000000 +0800
|
||||
@@ -865,8 +865,8 @@
|
||||
lan_addr = get_lan_for_peer(sender);
|
||||
if(lan_addr == NULL)
|
||||
{
|
||||
- syslog(LOG_WARNING, "SSDP packet sender %s not from a LAN, ignoring",
|
||||
- sender_str);
|
||||
+ /* syslog(LOG_WARNING, "SSDP packet sender %s not from a LAN, ignoring",
|
||||
+ sender_str); */
|
||||
return;
|
||||
}
|
||||
|
||||
51
msd_lite/Makefile
Normal file
51
msd_lite/Makefile
Normal file
@@ -0,0 +1,51 @@
|
||||
#
|
||||
# Copyright (C) 2006-2016 OpenWrt.org
|
||||
#
|
||||
# This is free software, licensed under the GNU General Public License v2.
|
||||
# See /LICENSE for more information.
|
||||
#
|
||||
|
||||
include $(TOPDIR)/rules.mk
|
||||
|
||||
PKG_NAME:=msd_lite
|
||||
PKG_VERSION:=1.10
|
||||
PKG_RELEASE:=1
|
||||
|
||||
PKG_SOURCE_PROTO:=git
|
||||
PKG_SOURCE_DATE:=2022-04-17
|
||||
PKG_SOURCE_URL:=https://github.com/rozhuk-im/msd_lite.git
|
||||
PKG_SOURCE_VERSION:=e254782c0f2199f5351cc7dae1d0be3ebaa5a7f0
|
||||
PKG_MIRROR_HASH:=dc6d9d4e3cc498238460a0599008713d97882020fe514f46156c0fec8d87fdc6
|
||||
|
||||
PKG_LICENSE:=BSD-2-Clause
|
||||
PKG_LICENSE_FILES:=LICENSE
|
||||
|
||||
include $(INCLUDE_DIR)/package.mk
|
||||
include $(INCLUDE_DIR)/cmake.mk
|
||||
|
||||
define Package/msd_lite
|
||||
SECTION:=net
|
||||
CATEGORY:=Network
|
||||
TITLE:=Multi Stream daemon Lite
|
||||
URL:=https://github.com/rozhuk-im/msd_litea
|
||||
DEPENDS:= +libpthread
|
||||
endef
|
||||
|
||||
define Package/msd_lite/description
|
||||
Program for IP TV streaming on the network via HTTP
|
||||
endef
|
||||
|
||||
define Package/msd_lite/conffiles
|
||||
/etc/msd_lite/msd_lite.conf
|
||||
endef
|
||||
|
||||
CMAKE_OPTIONS += \
|
||||
-DCONFDIR=/etc/msd_lite
|
||||
|
||||
define Package/msd_lite/install
|
||||
$(INSTALL_DIR) $(1)/etc/msd_lite $(1)/usr/bin
|
||||
$(INSTALL_CONF) $(PKG_BUILD_DIR)/conf/msd_lite.conf $(1)/etc/msd_lite/
|
||||
$(INSTALL_BIN) $(PKG_INSTALL_DIR)/usr/bin/msd_lite $(1)/usr/bin/
|
||||
endef
|
||||
|
||||
$(eval $(call BuildPackage,msd_lite))
|
||||
11
msd_lite/patches/001-ignore-install.patch
Normal file
11
msd_lite/patches/001-ignore-install.patch
Normal file
@@ -0,0 +1,11 @@
|
||||
--- a/CMakeLists.txt
|
||||
+++ b/CMakeLists.txt
|
||||
@@ -234,7 +234,7 @@
|
||||
##################### INSTALLATION #####################################
|
||||
|
||||
# Configs
|
||||
-install(CODE "FILE(MAKE_DIRECTORY ${CONFDIR})")
|
||||
+#install(CODE "FILE(MAKE_DIRECTORY ${CONFDIR})")
|
||||
|
||||
install_if_not_exists(conf/msd_lite.conf ${CONFDIR} "msd_lite.conf" ".sample")
|
||||
|
||||
68
mwan3/Makefile
Normal file
68
mwan3/Makefile
Normal file
@@ -0,0 +1,68 @@
|
||||
#
|
||||
# Copyright (C) 2006-2014 OpenWrt.org
|
||||
#
|
||||
# This is free software, licensed under the GNU General Public License v2.
|
||||
# See /LICENSE for more information.
|
||||
#
|
||||
|
||||
include $(TOPDIR)/rules.mk
|
||||
|
||||
PKG_NAME:=mwan3
|
||||
PKG_VERSION:=2.8.8
|
||||
PKG_RELEASE:=2
|
||||
PKG_MAINTAINER:=Florian Eckert <fe@dev.tdt.de>
|
||||
PKG_LICENSE:=GPL-2.0
|
||||
|
||||
include $(INCLUDE_DIR)/package.mk
|
||||
|
||||
define Package/mwan3
|
||||
SECTION:=net
|
||||
CATEGORY:=Network
|
||||
SUBMENU:=Routing and Redirection
|
||||
DEPENDS:= \
|
||||
+ip \
|
||||
+ipset \
|
||||
+iptables \
|
||||
+iptables-mod-conntrack-extra \
|
||||
+iptables-mod-ipopt \
|
||||
+jshn
|
||||
TITLE:=Multiwan hotplug script with connection tracking support
|
||||
MAINTAINER:=Florian Eckert <fe@dev.tdt.de>
|
||||
PKGARCH:=all
|
||||
endef
|
||||
|
||||
define Package/mwan3/description
|
||||
Hotplug script which makes configuration of multiple WAN interfaces simple
|
||||
and manageable. With loadbalancing/failover support for up to 250 wan
|
||||
interfaces, connection tracking and an easy to manage traffic ruleset.
|
||||
endef
|
||||
|
||||
define Package/mwan3/conffiles
|
||||
/etc/config/mwan3
|
||||
/etc/mwan3.user
|
||||
endef
|
||||
|
||||
define Build/Compile
|
||||
endef
|
||||
|
||||
define Package/mwan3/postinst
|
||||
#!/bin/sh
|
||||
if [ -z "$${IPKG_INSTROOT}" ]; then
|
||||
/etc/init.d/rpcd restart
|
||||
fi
|
||||
exit 0
|
||||
endef
|
||||
|
||||
define Package/mwan3/postrm
|
||||
#!/bin/sh
|
||||
if [ -z "$${IPKG_INSTROOT}" ]; then
|
||||
/etc/init.d/rpcd restart
|
||||
fi
|
||||
exit 0
|
||||
endef
|
||||
|
||||
define Package/mwan3/install
|
||||
$(CP) ./files/* $(1)
|
||||
endef
|
||||
|
||||
$(eval $(call BuildPackage,mwan3))
|
||||
23
mwan3/files/etc/config/mwan3
Normal file
23
mwan3/files/etc/config/mwan3
Normal file
@@ -0,0 +1,23 @@
|
||||
|
||||
config globals 'globals'
|
||||
option mmx_mask '0x3F00'
|
||||
option rtmon_interval '5'
|
||||
|
||||
config member 'wan_m1_w3'
|
||||
option interface 'wan'
|
||||
option metric '1'
|
||||
option weight '3'
|
||||
|
||||
config policy 'balanced'
|
||||
option last_resort 'default'
|
||||
list use_member 'wan_m1_w3'
|
||||
|
||||
config rule 'https'
|
||||
option sticky '1'
|
||||
option dest_port '443'
|
||||
option proto 'tcp'
|
||||
option use_policy 'balanced'
|
||||
|
||||
config rule 'default_rule'
|
||||
option dest_ip '0.0.0.0/0'
|
||||
option use_policy 'balanced'
|
||||
94
mwan3/files/etc/hotplug.d/iface/15-mwan3
Normal file
94
mwan3/files/etc/hotplug.d/iface/15-mwan3
Normal file
@@ -0,0 +1,94 @@
|
||||
#!/bin/sh
|
||||
|
||||
. /lib/functions.sh
|
||||
. /lib/functions/network.sh
|
||||
. /lib/mwan3/mwan3.sh
|
||||
. /usr/share/libubox/jshn.sh
|
||||
|
||||
[ "$ACTION" == "ifup" -o "$ACTION" == "ifdown" ] || exit 1
|
||||
[ -n "$INTERFACE" ] || exit 2
|
||||
|
||||
if [ "$ACTION" == "ifup" ]; then
|
||||
[ -n "$DEVICE" ] || exit 3
|
||||
fi
|
||||
|
||||
config_load mwan3
|
||||
config_get_bool enabled globals 'enabled' '0'
|
||||
[ ${enabled} -gt 0 ] || exit 0
|
||||
|
||||
mwan3_lock "$ACTION" "$INTERFACE"
|
||||
mwan3_init
|
||||
mwan3_set_connected_iptables
|
||||
mwan3_set_custom_ipset
|
||||
mwan3_unlock "$ACTION" "$INTERFACE"
|
||||
|
||||
config_get enabled $INTERFACE enabled 0
|
||||
config_get initial_state $INTERFACE initial_state "online"
|
||||
[ "$enabled" == "1" ] || exit 0
|
||||
|
||||
if [ "$ACTION" == "ifup" ]; then
|
||||
config_get family $INTERFACE family ipv4
|
||||
if [ "$family" = "ipv4" ]; then
|
||||
ubus call network.interface.${INTERFACE}_4 status &>/dev/null
|
||||
if [ "$?" -eq "0" ]; then
|
||||
network_get_ipaddr src_ip ${INTERFACE}_4
|
||||
else
|
||||
network_get_ipaddr src_ip ${INTERFACE}
|
||||
fi
|
||||
[ -n "$src_ip" ] || src_ip="0.0.0.0"
|
||||
elif [ "$family" = "ipv6" ]; then
|
||||
ubus call network.interface.${INTERFACE}_6 status &>/dev/null
|
||||
if [ "$?" -eq "0" ]; then
|
||||
network_get_ipaddr6 src_ip ${INTERFACE}_6
|
||||
else
|
||||
network_get_ipaddr6 src_ip ${INTERFACE}
|
||||
fi
|
||||
[ -n "$src_ip" ] || src_ip="::"
|
||||
fi
|
||||
fi
|
||||
|
||||
if [ "$initial_state" = "offline" ]; then
|
||||
json_load "$(ubus call mwan3 status '{"section":"interfaces"}')"
|
||||
json_select "interfaces"
|
||||
json_select "${INTERFACE}"
|
||||
json_get_var running running
|
||||
json_get_var status status
|
||||
else
|
||||
status=online
|
||||
running=1
|
||||
fi
|
||||
|
||||
mwan3_lock "$ACTION" "$INTERFACE"
|
||||
$LOG notice "Execute "$ACTION" event on interface $INTERFACE (${DEVICE:-unknown})"
|
||||
|
||||
case "$ACTION" in
|
||||
ifup)
|
||||
mwan3_set_general_rules
|
||||
mwan3_set_general_iptables
|
||||
mwan3_create_iface_iptables $INTERFACE $DEVICE
|
||||
mwan3_create_iface_rules $INTERFACE $DEVICE
|
||||
mwan3_create_iface_route $INTERFACE $DEVICE
|
||||
if [ ${running} -eq 1 -a "${status}" = "online" ]; then
|
||||
$LOG notice "Starting tracker on interface $INTERFACE (${DEVICE:-unknown})"
|
||||
mwan3_set_iface_hotplug_state $INTERFACE "online"
|
||||
mwan3_track $INTERFACE $DEVICE "online" "$src_ip"
|
||||
else
|
||||
$LOG notice "Starting tracker on interface $INTERFACE (${DEVICE:-unknown})"
|
||||
mwan3_set_iface_hotplug_state $INTERFACE "offline"
|
||||
mwan3_track $INTERFACE $DEVICE "offline" "$src_ip"
|
||||
fi
|
||||
mwan3_set_policies_iptables
|
||||
mwan3_set_user_rules
|
||||
;;
|
||||
ifdown)
|
||||
mwan3_set_iface_hotplug_state $INTERFACE "offline"
|
||||
mwan3_delete_iface_ipset_entries $INTERFACE
|
||||
mwan3_track_signal $INTERFACE $DEVICE
|
||||
mwan3_set_policies_iptables
|
||||
mwan3_set_user_rules
|
||||
;;
|
||||
esac
|
||||
|
||||
mwan3_unlock "$ACTION" "$INTERFACE"
|
||||
|
||||
exit 0
|
||||
22
mwan3/files/etc/hotplug.d/iface/16-mwan3
Normal file
22
mwan3/files/etc/hotplug.d/iface/16-mwan3
Normal file
@@ -0,0 +1,22 @@
|
||||
#!/bin/sh
|
||||
|
||||
. /lib/functions.sh
|
||||
. /lib/functions/network.sh
|
||||
. /lib/mwan3/mwan3.sh
|
||||
|
||||
config_load mwan3
|
||||
config_get_bool enabled globals 'enabled' '0'
|
||||
[ ${enabled} -gt 0 ] || exit 0
|
||||
|
||||
if [ "$ACTION" == "ifup" ]; then
|
||||
mwan3_lock "$ACTION" "mwan3rtmon"
|
||||
mwan3_rtmon
|
||||
mwan3_unlock "$ACTION" "mwan3rtmon"
|
||||
fi
|
||||
|
||||
config_get enabled $INTERFACE enabled 0
|
||||
[ "${enabled}" = "0" ] || {
|
||||
mwan3_flush_conntrack "$INTERFACE" "$ACTION"
|
||||
}
|
||||
|
||||
exit 0
|
||||
16
mwan3/files/etc/hotplug.d/iface/16-mwan3-user
Normal file
16
mwan3/files/etc/hotplug.d/iface/16-mwan3-user
Normal file
@@ -0,0 +1,16 @@
|
||||
#!/bin/sh
|
||||
|
||||
[ -f "/etc/mwan3.user" ] && {
|
||||
. /lib/functions.sh
|
||||
|
||||
config_load mwan3
|
||||
config_get_bool enabled globals 'enabled' '0'
|
||||
[ ${enabled} -gt 0 ] || exit 0
|
||||
|
||||
config_get enabled "$INTERFACE" enabled 0
|
||||
[ "${enabled}" = "1" ] || exit 0
|
||||
env -i ACTION="$ACTION" INTERFACE="$INTERFACE" DEVICE="$DEVICE" \
|
||||
/bin/sh /etc/mwan3.user
|
||||
}
|
||||
|
||||
exit 0
|
||||
28
mwan3/files/etc/init.d/mwan3
Executable file
28
mwan3/files/etc/init.d/mwan3
Executable file
@@ -0,0 +1,28 @@
|
||||
#!/bin/sh /etc/rc.common
|
||||
|
||||
START=19
|
||||
USE_PROCD=1
|
||||
|
||||
boot() {
|
||||
. /lib/config/uci.sh
|
||||
uci_toggle_state mwan3 globals enabled "1"
|
||||
mwan3_boot=1
|
||||
rc_procd start_service
|
||||
}
|
||||
|
||||
reload_service() {
|
||||
/usr/sbin/mwan3 restart
|
||||
}
|
||||
|
||||
start_service() {
|
||||
[ -n "${mwan3_boot}" ] && return 0
|
||||
/usr/sbin/mwan3 start
|
||||
}
|
||||
|
||||
stop_service() {
|
||||
/usr/sbin/mwan3 stop
|
||||
}
|
||||
|
||||
service_triggers() {
|
||||
procd_add_reload_trigger 'mwan3'
|
||||
}
|
||||
16
mwan3/files/etc/mwan3.user
Normal file
16
mwan3/files/etc/mwan3.user
Normal file
@@ -0,0 +1,16 @@
|
||||
#!/bin/sh
|
||||
#
|
||||
# This file is interpreted as shell script.
|
||||
# Put your custom mwan3 action here, they will
|
||||
# be executed with each netifd hotplug interface event
|
||||
# on interfaces for which mwan3 is enabled.
|
||||
#
|
||||
# There are three main environment variables that are passed to this script.
|
||||
#
|
||||
# $ACTION
|
||||
# <ifup> Is called by netifd and mwan3track
|
||||
# <ifdown> Is called by netifd and mwan3track
|
||||
# <connected> Is only called by mwan3track if tracking was successful
|
||||
# <disconnected> Is only called by mwan3track if tracking has failed
|
||||
# $INTERFACE Name of the interface which went up or down (e.g. "wan" or "wwan")
|
||||
# $DEVICE Physical device name which interface went up or down (e.g. "eth0" or "wwan0")
|
||||
26
mwan3/files/etc/uci-defaults/mwan3-migrate-flush_conntrack
Normal file
26
mwan3/files/etc/uci-defaults/mwan3-migrate-flush_conntrack
Normal file
@@ -0,0 +1,26 @@
|
||||
#!/bin/sh
|
||||
|
||||
. /lib/functions.sh
|
||||
|
||||
mwan3_migrate_flush_conntrack() {
|
||||
local iface="$1"
|
||||
|
||||
config_get value "${iface}" flush_conntrack
|
||||
case $value in
|
||||
always)
|
||||
uci_remove mwan3 "$iface" flush_conntrack
|
||||
uci_add_list mwan3 "$iface" flush_conntrack ifup
|
||||
uci_add_list mwan3 "$iface" flush_conntrack ifdown
|
||||
;;
|
||||
never)
|
||||
uci_remove mwan3 "$iface" flush_conntrack
|
||||
;;
|
||||
esac
|
||||
|
||||
uci_commit mwan3
|
||||
}
|
||||
|
||||
config_load mwan3
|
||||
config_foreach mwan3_migrate_flush_conntrack interface
|
||||
|
||||
exit 0
|
||||
6
mwan3/files/lib/mwan3/common.sh
Normal file
6
mwan3/files/lib/mwan3/common.sh
Normal file
@@ -0,0 +1,6 @@
|
||||
#!/bin/sh
|
||||
|
||||
get_uptime() {
|
||||
local uptime=$(cat /proc/uptime)
|
||||
echo "${uptime%%.*}"
|
||||
}
|
||||
1207
mwan3/files/lib/mwan3/mwan3.sh
Normal file
1207
mwan3/files/lib/mwan3/mwan3.sh
Normal file
File diff suppressed because it is too large
Load Diff
230
mwan3/files/usr/libexec/rpcd/mwan3
Executable file
230
mwan3/files/usr/libexec/rpcd/mwan3
Executable file
@@ -0,0 +1,230 @@
|
||||
#!/bin/sh
|
||||
|
||||
. /lib/functions.sh
|
||||
. /lib/functions/network.sh
|
||||
. /usr/share/libubox/jshn.sh
|
||||
. /lib/mwan3/common.sh
|
||||
|
||||
MWAN3TRACK_STATUS_DIR="/var/run/mwan3track"
|
||||
|
||||
IPS="ipset"
|
||||
IPT4="iptables -t mangle -w"
|
||||
IPT6="ip6tables -t mangle -w"
|
||||
|
||||
report_connected_v4() {
|
||||
local address
|
||||
|
||||
if [ -n "$($IPT4 -S mwan3_connected 2> /dev/null)" ]; then
|
||||
for address in $($IPS -o save list mwan3_connected_v4 | grep add | cut -d " " -f 3); do
|
||||
json_add_string "" "${address}"
|
||||
done
|
||||
fi
|
||||
}
|
||||
|
||||
report_connected_v6() {
|
||||
local address
|
||||
|
||||
if [ -n "$($IPT6 -S mwan3_connected 2> /dev/null)" ]; then
|
||||
for address in $($IPS -o save list mwan3_connected_v6 | grep add | cut -d " " -f 3); do
|
||||
json_add_string "" "${address}"
|
||||
done
|
||||
fi
|
||||
}
|
||||
|
||||
report_policies() {
|
||||
local ipt="$1"
|
||||
local policy="$2"
|
||||
|
||||
local percent total_weight weight iface
|
||||
|
||||
total_weight=$($ipt -S $policy | grep -v '.*--comment "out .*" .*$' | cut -s -d'"' -f2 | head -1 | awk '{print $3}')
|
||||
|
||||
for iface in $($ipt -S $policy | grep -v '.*--comment "out .*" .*$' | cut -s -d'"' -f2 | awk '{print $1}'); do
|
||||
weight=$($ipt -S $policy | grep -v '.*--comment "out .*" .*$' | cut -s -d'"' -f2 | awk '$1 == "'$iface'"' | awk '{print $2}')
|
||||
percent=$(($weight*100/$total_weight))
|
||||
json_add_object
|
||||
json_add_string interface "$iface"
|
||||
json_add_int percent "$percent"
|
||||
json_close_object
|
||||
done
|
||||
}
|
||||
|
||||
report_policies_v4() {
|
||||
local policy
|
||||
|
||||
for policy in $($IPT4 -S | awk '{print $2}' | grep mwan3_policy_ | sort -u); do
|
||||
json_add_array "${policy##*mwan3_policy_}"
|
||||
report_policies "$IPT4" "$policy"
|
||||
json_close_array
|
||||
done
|
||||
}
|
||||
|
||||
report_policies_v6() {
|
||||
local policy
|
||||
|
||||
for policy in $($IPT6 -S | awk '{print $2}' | grep mwan3_policy_ | sort -u); do
|
||||
json_add_array "${policy##*mwan3_policy_}"
|
||||
report_policies "$IPT6" "$policy"
|
||||
json_close_array
|
||||
done
|
||||
}
|
||||
|
||||
get_mwan3_status() {
|
||||
local iface="${1}"
|
||||
local iface_select="${2}"
|
||||
local running="0"
|
||||
local age=0
|
||||
local online=0
|
||||
local offline=0
|
||||
local up="0"
|
||||
local enabled pid device time_p time_n time_u time_d status
|
||||
|
||||
network_get_device device $1
|
||||
|
||||
if [ "${iface}" = "${iface_select}" ] || [ "${iface_select}" = "" ]; then
|
||||
pid="$(pgrep -f "mwan3track $iface $device")"
|
||||
if [ "${pid}" != "" ]; then
|
||||
running="1"
|
||||
fi
|
||||
|
||||
time_p="$(cat "$MWAN3TRACK_STATUS_DIR/${iface}/TIME")"
|
||||
[ -z "${time_p}" ] || {
|
||||
time_n="$(get_uptime)"
|
||||
let age=time_n-time_p
|
||||
}
|
||||
|
||||
time_u="$(cat "$MWAN3TRACK_STATUS_DIR/${iface}/ONLINE")"
|
||||
[ -z "${time_u}" ] || [ "${time_u}" = "0" ] || {
|
||||
time_n="$(get_uptime)"
|
||||
let online=time_n-time_u
|
||||
}
|
||||
|
||||
time_d="$(cat "$MWAN3TRACK_STATUS_DIR/${iface}/OFFLINE")"
|
||||
[ -z "${time_d}" ] || [ "${time_d}" = "0" ] || {
|
||||
time_n="$(get_uptime)"
|
||||
let offline=time_n-time_d
|
||||
}
|
||||
|
||||
local uptime="0"
|
||||
|
||||
config_get enabled "$iface" enabled 0
|
||||
network_get_uptime uptime "$iface"
|
||||
network_is_up "$iface" && up="1"
|
||||
|
||||
if [ -f "$MWAN3TRACK_STATUS_DIR/${iface}/STATUS" ]; then
|
||||
status="$(cat "$MWAN3TRACK_STATUS_DIR/${iface}/STATUS")"
|
||||
else
|
||||
status="unknown"
|
||||
fi
|
||||
|
||||
json_add_object "${iface}"
|
||||
json_add_int age "$age"
|
||||
json_add_int online "${online}"
|
||||
json_add_int offline "${offline}"
|
||||
json_add_int uptime "${uptime}"
|
||||
json_add_int "score" "$(cat "$MWAN3TRACK_STATUS_DIR/${iface}/SCORE")"
|
||||
json_add_int "lost" "$(cat "$MWAN3TRACK_STATUS_DIR/${iface}/LOST")"
|
||||
json_add_int "turn" "$(cat "$MWAN3TRACK_STATUS_DIR/${iface}/TURN")"
|
||||
json_add_string "status" "${status}"
|
||||
json_add_boolean "enabled" "${enabled}"
|
||||
json_add_boolean "running" "${running}"
|
||||
json_add_boolean "up" "${up}"
|
||||
json_add_array "track_ip"
|
||||
for file in $MWAN3TRACK_STATUS_DIR/${iface}/*; do
|
||||
track="${file#*/TRACK_}"
|
||||
if [ "${track}" != "${file}" ]; then
|
||||
json_add_object
|
||||
json_add_string ip "${track}"
|
||||
json_add_string status "$(cat "${file}")"
|
||||
json_add_int latency "$(cat "$MWAN3TRACK_STATUS_DIR/${iface}/LATENCY_${track}")"
|
||||
json_add_int packetloss "$(cat "$MWAN3TRACK_STATUS_DIR/${iface}/LOSS_${track}")"
|
||||
json_close_object
|
||||
fi
|
||||
done
|
||||
json_close_array
|
||||
json_close_object
|
||||
fi
|
||||
}
|
||||
|
||||
main () {
|
||||
|
||||
case "$1" in
|
||||
list)
|
||||
json_init
|
||||
json_add_object "status"
|
||||
json_add_string "section" "x"
|
||||
json_add_string "interface" "x"
|
||||
json_add_string "policies" "x"
|
||||
json_close_object
|
||||
json_dump
|
||||
;;
|
||||
call)
|
||||
case "$2" in
|
||||
status)
|
||||
local section iface
|
||||
read input;
|
||||
json_load "$input"
|
||||
json_get_var section section
|
||||
json_get_var iface interface
|
||||
|
||||
config_load mwan3
|
||||
json_init
|
||||
case "$section" in
|
||||
interfaces)
|
||||
json_add_object interfaces
|
||||
config_foreach get_mwan3_status interface "${iface}"
|
||||
json_close_object
|
||||
;;
|
||||
connected)
|
||||
json_add_object connected
|
||||
json_add_array ipv4
|
||||
report_connected_v4
|
||||
json_close_array
|
||||
json_add_array ipv6
|
||||
report_connected_v6
|
||||
json_close_array
|
||||
json_close_object
|
||||
;;
|
||||
policies)
|
||||
json_add_object policies
|
||||
json_add_object ipv4
|
||||
report_policies_v4
|
||||
json_close_object
|
||||
json_add_object ipv6
|
||||
report_policies_v6
|
||||
json_close_object
|
||||
json_close_object
|
||||
;;
|
||||
*)
|
||||
# interfaces
|
||||
json_add_object interfaces
|
||||
config_foreach get_mwan3_status interface
|
||||
json_close_object
|
||||
# connected
|
||||
json_add_object connected
|
||||
json_add_array ipv4
|
||||
report_connected_v4
|
||||
json_close_array
|
||||
json_add_array ipv6
|
||||
report_connected_v6
|
||||
json_close_array
|
||||
json_close_object
|
||||
# policies
|
||||
json_add_object policies
|
||||
json_add_object ipv4
|
||||
report_policies_v4
|
||||
json_close_object
|
||||
json_add_object ipv6
|
||||
report_policies_v6
|
||||
json_close_object
|
||||
json_close_object
|
||||
;;
|
||||
esac
|
||||
json_dump
|
||||
;;
|
||||
esac
|
||||
;;
|
||||
esac
|
||||
}
|
||||
|
||||
main "$@"
|
||||
213
mwan3/files/usr/sbin/mwan3
Executable file
213
mwan3/files/usr/sbin/mwan3
Executable file
@@ -0,0 +1,213 @@
|
||||
#!/bin/sh
|
||||
|
||||
. /lib/functions.sh
|
||||
. /usr/share/libubox/jshn.sh
|
||||
. /lib/functions/network.sh
|
||||
. /lib/mwan3/mwan3.sh
|
||||
|
||||
help()
|
||||
{
|
||||
cat <<EOF
|
||||
Syntax: mwan3 [command]
|
||||
|
||||
Available commands:
|
||||
start Load iptables rules, ip rules and ip routes
|
||||
stop Unload iptables rules, ip rules and ip routes
|
||||
restart Reload iptables rules, ip rules and ip routes
|
||||
ifup <iface> Load rules and routes for specific interface
|
||||
ifdown <iface> Unload rules and routes for specific interface
|
||||
interfaces Show interfaces status
|
||||
policies Show currently active policy
|
||||
connected Show directly connected networks
|
||||
rules Show active rules
|
||||
status Show all status
|
||||
|
||||
EOF
|
||||
}
|
||||
|
||||
ifdown()
|
||||
{
|
||||
if [ -z "$1" ]; then
|
||||
echo "Error: Expecting interface. Usage: mwan3 ifdown <interface>" && exit 0
|
||||
fi
|
||||
|
||||
if [ -n "$2" ]; then
|
||||
echo "Error: Too many arguments. Usage: mwan3 ifdown <interface>" && exit 0
|
||||
fi
|
||||
|
||||
ACTION=ifdown INTERFACE=$1 /sbin/hotplug-call iface
|
||||
|
||||
kill $(pgrep -f "mwan3track $1 $2") &> /dev/null
|
||||
mwan3_track_clean $1
|
||||
}
|
||||
|
||||
ifup()
|
||||
{
|
||||
local device enabled up l3_device status
|
||||
|
||||
config_load mwan3
|
||||
config_get_bool enabled globals 'enabled' 0
|
||||
[ ${enabled} -gt 0 ] || {
|
||||
echo "The service mwan3 is global disabled."
|
||||
echo "Please execute \"/etc/init.d/mwan3 start\" first."
|
||||
exit 1
|
||||
}
|
||||
|
||||
if [ -z "$1" ]; then
|
||||
echo "Expecting interface. Usage: mwan3 ifup <interface>" && exit 0
|
||||
fi
|
||||
|
||||
if [ -n "$2" ]; then
|
||||
echo "Too many arguments. Usage: mwan3 ifup <interface>" && exit 0
|
||||
fi
|
||||
|
||||
status=$(ubus -S call network.interface.$1 status)
|
||||
[ -n "$status" ] && {
|
||||
json_load "$status"
|
||||
json_get_vars up l3_device
|
||||
}
|
||||
|
||||
config_get enabled "$1" enabled 0
|
||||
|
||||
if [ "$up" = "1" ] \
|
||||
&& [ -n "$l3_device" ] \
|
||||
&& [ "$enabled" = "1" ]; then
|
||||
ACTION=ifup INTERFACE=$1 DEVICE=$l3_device /sbin/hotplug-call iface
|
||||
fi
|
||||
}
|
||||
|
||||
interfaces()
|
||||
{
|
||||
config_load mwan3
|
||||
|
||||
echo "Interface status:"
|
||||
config_foreach mwan3_report_iface_status interface
|
||||
echo -e
|
||||
}
|
||||
|
||||
policies()
|
||||
{
|
||||
echo "Current ipv4 policies:"
|
||||
mwan3_report_policies_v4
|
||||
echo -e
|
||||
echo "Current ipv6 policies:"
|
||||
mwan3_report_policies_v6
|
||||
echo -e
|
||||
}
|
||||
|
||||
connected()
|
||||
{
|
||||
echo "Directly connected ipv4 networks:"
|
||||
mwan3_report_connected_v4
|
||||
echo -e
|
||||
echo "Directly connected ipv6 networks:"
|
||||
mwan3_report_connected_v6
|
||||
echo -e
|
||||
}
|
||||
|
||||
rules()
|
||||
{
|
||||
echo "Active ipv4 user rules:"
|
||||
mwan3_report_rules_v4
|
||||
echo -e
|
||||
echo "Active ipv6 user rules:"
|
||||
mwan3_report_rules_v6
|
||||
echo -e
|
||||
}
|
||||
|
||||
status()
|
||||
{
|
||||
interfaces
|
||||
policies
|
||||
connected
|
||||
rules
|
||||
}
|
||||
|
||||
start()
|
||||
{
|
||||
local enabled
|
||||
|
||||
uci_toggle_state mwan3 globals enabled "1"
|
||||
|
||||
config_load mwan3
|
||||
config_foreach ifup interface
|
||||
}
|
||||
|
||||
stop()
|
||||
{
|
||||
local ipset route rule table IP IPT pid
|
||||
|
||||
mwan3_lock "command" "mwan3"
|
||||
|
||||
for pid in $(pgrep -f "mwan3rtmon"); do
|
||||
kill -TERM "$pid" > /dev/null 2>&1
|
||||
sleep 1
|
||||
kill -KILL "$pid" > /dev/null 2>&1
|
||||
done
|
||||
|
||||
for pid in $(pgrep -f "mwan3track"); do
|
||||
kill -TERM "$pid" > /dev/null 2>&1
|
||||
sleep 1
|
||||
kill -KILL "$pid" > /dev/null 2>&1
|
||||
done
|
||||
|
||||
config_load mwan3
|
||||
config_foreach mwan3_track_clean interface
|
||||
|
||||
for IP in "$IP4" "$IP6"; do
|
||||
|
||||
for route in $(seq 1 $MWAN3_INTERFACE_MAX); do
|
||||
$IP route flush table $route &> /dev/null
|
||||
done
|
||||
|
||||
for rule in $($IP rule list | egrep '^[1-2][0-9]{3}\:' | cut -d ':' -f 1); do
|
||||
$IP rule del pref $rule &> /dev/null
|
||||
done
|
||||
done
|
||||
|
||||
for IPT in "$IPT4" "$IPT6"; do
|
||||
|
||||
$IPT -D PREROUTING -j mwan3_hook &> /dev/null
|
||||
$IPT -D OUTPUT -j mwan3_hook &> /dev/null
|
||||
|
||||
for table in $($IPT -S | awk '{print $2}' | grep mwan3 | sort -u); do
|
||||
$IPT -F $table &> /dev/null
|
||||
done
|
||||
|
||||
for table in $($IPT -S | awk '{print $2}' | grep mwan3 | sort -u); do
|
||||
$IPT -X $table &> /dev/null
|
||||
done
|
||||
done
|
||||
|
||||
for ipset in $($IPS -n list | grep mwan3_); do
|
||||
$IPS -q destroy $ipset
|
||||
done
|
||||
|
||||
for ipset in $($IPS -n list | grep mwan3 | grep -E '_v4|_v6'); do
|
||||
$IPS -q destroy $ipset
|
||||
done
|
||||
|
||||
mwan3_unlock "command" "mwan3"
|
||||
|
||||
mwan3_lock_clean
|
||||
rm -rf $MWAN3_STATUS_DIR $MWAN3TRACK_STATUS_DIR
|
||||
|
||||
uci_toggle_state mwan3 globals enabled "0"
|
||||
}
|
||||
|
||||
restart() {
|
||||
stop
|
||||
start
|
||||
}
|
||||
|
||||
case "$1" in
|
||||
ifup|ifdown|interfaces|policies|connected|rules|status|start|stop|restart)
|
||||
mwan3_init
|
||||
$*
|
||||
;;
|
||||
*)
|
||||
help
|
||||
;;
|
||||
esac
|
||||
|
||||
exit 0
|
||||
38
mwan3/files/usr/sbin/mwan3rtmon
Executable file
38
mwan3/files/usr/sbin/mwan3rtmon
Executable file
@@ -0,0 +1,38 @@
|
||||
#!/bin/sh
|
||||
|
||||
. /lib/functions.sh
|
||||
. /lib/mwan3/mwan3.sh
|
||||
|
||||
LOG="logger -t $(basename "$0")[$$] -p"
|
||||
|
||||
clean_up() {
|
||||
$LOG notice "Stopping mwan3rtmon..."
|
||||
exit 0
|
||||
}
|
||||
|
||||
rtchange() {
|
||||
$LOG info "Detect rtchange event."
|
||||
}
|
||||
|
||||
main() {
|
||||
local rtmon_interval
|
||||
trap clean_up TERM
|
||||
trap rtchange USR1
|
||||
|
||||
config_load mwan3
|
||||
config_get rtmon_interval globals rtmon_interval '5'
|
||||
|
||||
sleep 3
|
||||
while true; do
|
||||
mwan3_lock "service" "mwan3rtmon"
|
||||
mwan3_rtmon_ipv4 || mwan3_rtmon_ipv6
|
||||
ret=$?
|
||||
mwan3_unlock "service" "mwan3rtmon"
|
||||
[ "$ret" = "0" ] || break
|
||||
[ "$rtmon_interval" = "0" ] && break
|
||||
sleep "$rtmon_interval" &
|
||||
wait
|
||||
done
|
||||
}
|
||||
|
||||
main "$@"
|
||||
293
mwan3/files/usr/sbin/mwan3track
Executable file
293
mwan3/files/usr/sbin/mwan3track
Executable file
@@ -0,0 +1,293 @@
|
||||
#!/bin/sh
|
||||
|
||||
. /lib/functions.sh
|
||||
. /lib/mwan3/common.sh
|
||||
|
||||
LOG="logger -t $(basename "$0")[$$] -p"
|
||||
INTERFACE=""
|
||||
DEVICE=""
|
||||
PING="/bin/ping"
|
||||
|
||||
IFDOWN_EVENT=0
|
||||
|
||||
clean_up() {
|
||||
$LOG notice "Stopping mwan3track for interface \"${INTERFACE}\""
|
||||
exit 0
|
||||
}
|
||||
|
||||
if_down() {
|
||||
$LOG info "Detect ifdown event on interface ${INTERFACE} (${DEVICE})"
|
||||
IFDOWN_EVENT=1
|
||||
}
|
||||
|
||||
validate_track_method() {
|
||||
case "$1" in
|
||||
ping)
|
||||
which ping 1>/dev/null 2>&1 || {
|
||||
$LOG warn "Missing ping. Please install iputils-ping package or enable ping util and recompile busybox."
|
||||
return 1
|
||||
}
|
||||
;;
|
||||
arping)
|
||||
which arping 1>/dev/null 2>&1 || {
|
||||
$LOG warn "Missing arping. Please install iputils-arping package."
|
||||
return 1
|
||||
}
|
||||
;;
|
||||
httping)
|
||||
which httping 1>/dev/null 2>&1 || {
|
||||
$LOG warn "Missing httping. Please install httping package."
|
||||
return 1
|
||||
}
|
||||
[ -n "$2" -a "$2" != "0.0.0.0" -a "$2" != "::" ] || {
|
||||
$LOG warn "Cannot determine source IP for the interface which is required by httping."
|
||||
return 1
|
||||
}
|
||||
;;
|
||||
nping-*)
|
||||
which nping 1>/dev/null 2>&1 || {
|
||||
$LOG warn "Missing nping. Please install nping package."
|
||||
return 1
|
||||
}
|
||||
;;
|
||||
*)
|
||||
$LOG warn "Unsupported tracking method: $track_method"
|
||||
return 2
|
||||
;;
|
||||
esac
|
||||
}
|
||||
|
||||
main() {
|
||||
local reliability count timeout interval failure_interval
|
||||
local recovery_interval down up size
|
||||
local keep_failure_interval check_quality failure_latency
|
||||
local recovery_latency failure_loss recovery_loss
|
||||
local max_ttl httping_ssl
|
||||
|
||||
[ -z "$5" ] && echo "Error: should not be started manually" && exit 0
|
||||
|
||||
INTERFACE=$1
|
||||
DEVICE=$2
|
||||
STATUS=$3
|
||||
SRC_IP=$4
|
||||
mkdir -p /var/run/mwan3track/$1
|
||||
trap clean_up TERM
|
||||
trap if_down USR1
|
||||
|
||||
config_load mwan3
|
||||
config_get track_method $1 track_method ping
|
||||
config_get_bool httping_ssl $1 httping_ssl 0
|
||||
validate_track_method $track_method $SRC_IP || {
|
||||
track_method=ping
|
||||
if validate_track_method $track_method; then
|
||||
$LOG warn "Using ping to track interface $INTERFACE avaliability"
|
||||
else
|
||||
$LOG err "No track method avaliable"
|
||||
exit 1
|
||||
fi
|
||||
}
|
||||
config_get reliability $1 reliability 1
|
||||
config_get count $1 count 1
|
||||
config_get timeout $1 timeout 4
|
||||
config_get interval $1 interval 10
|
||||
config_get down $1 down 5
|
||||
config_get up $1 up 5
|
||||
config_get size $1 size 56
|
||||
config_get max_ttl $1 max_ttl 60
|
||||
config_get failure_interval $1 failure_interval $interval
|
||||
config_get_bool keep_failure_interval $1 keep_failure_interval 0
|
||||
config_get recovery_interval $1 recovery_interval $interval
|
||||
config_get_bool check_quality $1 check_quality 0
|
||||
config_get failure_latency $1 failure_latency 1000
|
||||
config_get recovery_latency $1 recovery_latency 500
|
||||
config_get failure_loss $1 failure_loss 40
|
||||
config_get recovery_loss $1 recovery_loss 10
|
||||
|
||||
local score=$(($down+$up))
|
||||
local track_ips=$(echo $* | cut -d ' ' -f 5-99)
|
||||
local host_up_count=0
|
||||
local lost=0
|
||||
local sleep_time=0
|
||||
local turn=0
|
||||
local result
|
||||
local ping_protocol=4
|
||||
local ping_result
|
||||
local ping_result_raw
|
||||
local ping_status
|
||||
local loss=0
|
||||
local latency=0
|
||||
|
||||
if [ "$STATUS" = "offline" ]; then
|
||||
echo "offline" > /var/run/mwan3track/$1/STATUS
|
||||
echo "0" > /var/run/mwan3track/$1/ONLINE
|
||||
echo "$(get_uptime)" > /var/run/mwan3track/$1/OFFLINE
|
||||
score=0
|
||||
else
|
||||
echo "online" > /var/run/mwan3track/$1/STATUS
|
||||
echo "0" > /var/run/mwan3track/$1/OFFLINE
|
||||
echo "$(get_uptime)" > /var/run/mwan3track/$1/ONLINE
|
||||
env -i ACTION="connected" INTERFACE="$1" DEVICE="$2" /sbin/hotplug-call iface
|
||||
fi
|
||||
while true; do
|
||||
|
||||
sleep_time=$interval
|
||||
|
||||
for track_ip in $track_ips; do
|
||||
if [ $host_up_count -lt $reliability ]; then
|
||||
case "$track_method" in
|
||||
ping)
|
||||
# pinging IPv6 hosts with an interface is troublesome
|
||||
# https://bugs.openwrt.org/index.php?do=details&task_id=2897
|
||||
# so get the IP address of the interface and use that instead
|
||||
if echo $track_ip | grep -q ':'; then
|
||||
ADDR=$(ip -6 addr ls dev "$DEVICE" | sed -ne '/\/128/d' -e 's/ *inet6 \([^ \/]*\).* scope global.*/\1/p' | head -n1)
|
||||
[ -z "$ADDR" ] && ADDR=$(ip -6 addr ls dev "$DEVICE" | sed -ne 's/ *inet6 \([^ \/]*\).* scope global.*/\1/p')
|
||||
ping_protocol=6
|
||||
fi
|
||||
if [ $check_quality -eq 0 ]; then
|
||||
$PING -$ping_protocol -I ${ADDR:-$DEVICE} -c $count -W $timeout -s $size -t $max_ttl -q $track_ip &> /dev/null
|
||||
result=$?
|
||||
else
|
||||
ping_result_raw="$($PING -$ping_protocol -I ${ADDR:-$DEVICE} -c $count -W $timeout -s $size -t $max_ttl -q $track_ip 2>/dev/null)"
|
||||
ping_status=$?
|
||||
ping_result=$(echo "$ping_result_raw" | tail -n2)
|
||||
loss="$(echo "$ping_result" | grep "packet loss" | cut -d "," -f3 | awk '{print $1}' | sed -e 's/%//')"
|
||||
if [ "$ping_status" -ne 0 ] || [ "$loss" -eq 100 ]; then
|
||||
latency=999999
|
||||
loss=100
|
||||
else
|
||||
latency="$(echo "$ping_result" | grep -E 'rtt|round-trip' | cut -d "=" -f2 | cut -d "/" -f2 | cut -d "." -f1)"
|
||||
fi
|
||||
fi
|
||||
;;
|
||||
arping)
|
||||
arping -I $DEVICE -c $count -w $timeout -q $track_ip &> /dev/null
|
||||
result=$?
|
||||
;;
|
||||
httping)
|
||||
if [ "$httping_ssl" -eq 1 ]; then
|
||||
httping -y $SRC_IP -c $count -t $timeout -q "https://$track_ip" &> /dev/null
|
||||
else
|
||||
httping -y $SRC_IP -c $count -t $timeout -q "http://$track_ip" &> /dev/null
|
||||
fi
|
||||
result=$?
|
||||
;;
|
||||
nping-tcp)
|
||||
result=$(nping -e $DEVICE -c $count $track_ip --tcp | grep Lost | awk '{print $12}')
|
||||
;;
|
||||
nping-udp)
|
||||
result=$(nping -e $DEVICE -c $count $track_ip --udp | grep Lost | awk '{print $12}')
|
||||
;;
|
||||
nping-icmp)
|
||||
result=$(nping -e $DEVICE -c $count $track_ip --icmp | grep Lost | awk '{print $12}')
|
||||
;;
|
||||
nping-arp)
|
||||
result=$(nping -e $DEVICE -c $count $track_ip --arp | grep Lost | awk '{print $12}')
|
||||
;;
|
||||
esac
|
||||
if [ $check_quality -eq 0 ]; then
|
||||
if [ $result -eq 0 ]; then
|
||||
let host_up_count++
|
||||
echo "up" > /var/run/mwan3track/$1/TRACK_${track_ip}
|
||||
if [ $score -le $up ]; then
|
||||
$LOG info "Check ($track_method) success for target \"$track_ip\" on interface $1 ($2)"
|
||||
fi
|
||||
else
|
||||
let lost++
|
||||
echo "down" > /var/run/mwan3track/$1/TRACK_${track_ip}
|
||||
if [ $score -gt $up ]; then
|
||||
$LOG info "Check ($track_method) failed for target \"$track_ip\" on interface $1 ($2)"
|
||||
fi
|
||||
fi
|
||||
else
|
||||
if [ "$loss" -ge "$failure_loss" -o "$latency" -ge "$failure_latency" ]; then
|
||||
let lost++
|
||||
echo "down" > /var/run/mwan3track/$1/TRACK_${track_ip}
|
||||
echo "$latency" > /var/run/mwan3track/$1/LATENCY_${track_ip}
|
||||
echo "$loss" > /var/run/mwan3track/$1/LOSS_${track_ip}
|
||||
|
||||
if [ $score -gt $up ]; then
|
||||
$LOG info "Check (${track_method}: latency=${latency}ms loss=${loss}%) failed for target \"$track_ip\" on interface $1 ($2)"
|
||||
fi
|
||||
elif [ "$loss" -le "$recovery_loss" -a "$latency" -le "$recovery_latency" ]; then
|
||||
let host_up_count++
|
||||
echo "up" > /var/run/mwan3track/$1/TRACK_${track_ip}
|
||||
echo "$latency" > /var/run/mwan3track/$1/LATENCY_${track_ip}
|
||||
echo "$loss" > /var/run/mwan3track/$1/LOSS_${track_ip}
|
||||
|
||||
if [ $score -le $up ]; then
|
||||
$LOG info "Check (${track_method}: latency=${latency}ms loss=${loss}%) success for target \"$track_ip\" on interface $1 ($2)"
|
||||
fi
|
||||
else
|
||||
echo "skipped" > /var/run/mwan3track/$1/TRACK_${track_ip}
|
||||
fi
|
||||
fi
|
||||
else
|
||||
echo "skipped" > /var/run/mwan3track/$1/TRACK_${track_ip}
|
||||
fi
|
||||
done
|
||||
|
||||
if [ $host_up_count -lt $reliability ]; then
|
||||
let score--
|
||||
|
||||
if [ $score -lt $up ]; then
|
||||
score=0
|
||||
[ ${keep_failure_interval} -eq 1 ] && {
|
||||
sleep_time=$failure_interval
|
||||
}
|
||||
else
|
||||
sleep_time=$failure_interval
|
||||
fi
|
||||
|
||||
if [ $score -eq $up ]; then
|
||||
echo "offline" > /var/run/mwan3track/$1/STATUS
|
||||
env -i ACTION=ifdown INTERFACE=$1 DEVICE=$2 /sbin/hotplug-call iface
|
||||
score=0
|
||||
fi
|
||||
else
|
||||
if [ $score -lt $(($down+$up)) ] && [ $lost -gt 0 ]; then
|
||||
$LOG info "Lost $(($lost*$count)) ping(s) on interface $1 ($2)"
|
||||
fi
|
||||
|
||||
let score++
|
||||
lost=0
|
||||
|
||||
if [ $score -gt $up ]; then
|
||||
echo "online" > /var/run/mwan3track/$1/STATUS
|
||||
score=$(($down+$up))
|
||||
elif [ $score -le $up ]; then
|
||||
sleep_time=$recovery_interval
|
||||
fi
|
||||
|
||||
if [ $score -eq $up ]; then
|
||||
$LOG notice "Interface $1 ($2) is online"
|
||||
echo "online" > /var/run/mwan3track/$1/STATUS
|
||||
env -i ACTION=ifup INTERFACE=$1 DEVICE=$2 /sbin/hotplug-call iface
|
||||
exit 0
|
||||
fi
|
||||
fi
|
||||
|
||||
let turn++
|
||||
mkdir -p "/var/run/mwan3track/${1}"
|
||||
echo "${lost}" > /var/run/mwan3track/$1/LOST
|
||||
echo "${score}" > /var/run/mwan3track/$1/SCORE
|
||||
echo "${turn}" > /var/run/mwan3track/$1/TURN
|
||||
echo "$(get_uptime)" > /var/run/mwan3track/$1/TIME
|
||||
|
||||
host_up_count=0
|
||||
sleep "${sleep_time}" &
|
||||
wait
|
||||
|
||||
if [ "${IFDOWN_EVENT}" -eq 1 ]; then
|
||||
echo "offline" > /var/run/mwan3track/$1/STATUS
|
||||
echo "$(get_uptime)" > /var/run/mwan3track/$1/OFFLINE
|
||||
echo "0" > /var/run/mwan3track/$1/ONLINE
|
||||
$LOG notice "Interface $1 ($2) is offline"
|
||||
env -i ACTION="disconnected" INTERFACE="$1" DEVICE="$2" /sbin/hotplug-call iface
|
||||
score=0
|
||||
IFDOWN_EVENT=0
|
||||
fi
|
||||
done
|
||||
}
|
||||
|
||||
main "$@"
|
||||
89
nps/Makefile
Normal file
89
nps/Makefile
Normal file
@@ -0,0 +1,89 @@
|
||||
# SPDX-License-Identifier: GPL-3.0-only
|
||||
#
|
||||
# Copyright (C) 2021 ImmortalWrt.org
|
||||
|
||||
include $(TOPDIR)/rules.mk
|
||||
|
||||
PKG_NAME:=nps
|
||||
PKG_VERSION:=0.26.10
|
||||
PKG_RELEASE:=$(AUTORELEASE)
|
||||
|
||||
PKG_SOURCE:=$(PKG_NAME)-$(PKG_VERSION).tar.gz
|
||||
PKG_SOURCE_URL:=https://codeload.github.com/ehang-io/nps/tar.gz/v$(PKG_VERSION)?
|
||||
PKG_HASH:=1b2fe9d251f55105d65027a1cee464f65d2f6ab3bd4a20e4655e5135db68aee7
|
||||
|
||||
PKG_LICENSE:=Apache-2.0
|
||||
PKG_LICENSE_FILE:=LICENSE
|
||||
PKG_MAINTAINTER:=Tianling Shen <cnsztl@immortalwrt.org>
|
||||
|
||||
PKG_CONFIG_DEPENDS:= \
|
||||
CONFIG_NPC_COMPRESS_UPX \
|
||||
CONFIG_NPS_COMPRESS_UPX
|
||||
|
||||
PKG_BUILD_DEPENDS:=golang/host upx/host
|
||||
PKG_BUILD_PARALLEL:=1
|
||||
PKG_USE_MIPS16:=0
|
||||
|
||||
GO_PKG:=ehang.io/nps
|
||||
GO_PKG_BUILD_PKG:=ehang.io/nps/cmd/...
|
||||
GO_PKG_LDFLAGS:=-s -w
|
||||
|
||||
include $(INCLUDE_DIR)/package.mk
|
||||
include $(TOPDIR)/feeds/packages/lang/golang/golang-package.mk
|
||||
|
||||
define Package/nps/template
|
||||
SECTION:=net
|
||||
CATEGORY:=Network
|
||||
TITLE:=A intranet penetration proxy server ($(1))
|
||||
DEPENDS:=$(GO_ARCH_DEPENDS) +ca-bundle
|
||||
URL:=https://ehang-io.github.io/nps
|
||||
endef
|
||||
|
||||
Package/npc = $(call Package/nps/template,client)
|
||||
Package/nps = $(call Package/nps/template,server)
|
||||
|
||||
define Package/nps/description/template
|
||||
NPS is a lightweight, high-performance, powerful intranet penetration proxy server,
|
||||
with a powerful web management terminal.
|
||||
endef
|
||||
|
||||
Package/npc/description = $(Package/nps/description/template)
|
||||
Package/nps/description = $(Package/nps/description/template)
|
||||
|
||||
define Package/npc/config
|
||||
config NPC_COMPRESS_UPX
|
||||
bool "Compress executable files with UPX"
|
||||
depends on !mips64
|
||||
default n
|
||||
endef
|
||||
|
||||
define Package/nps/config
|
||||
config NPS_COMPRESS_UPX
|
||||
bool "Compress executable files with UPX"
|
||||
depends on !mips64
|
||||
default n
|
||||
endef
|
||||
|
||||
define Build/Compile
|
||||
$(call GoPackage/Build/Compile)
|
||||
ifeq ($(CONFIG_NPC_COMPRESS_UPX),y)
|
||||
$(STAGING_DIR_HOST)/bin/upx --lzma --best $(GO_PKG_BUILD_BIN_DIR)/npc
|
||||
endif
|
||||
ifeq ($(CONFIG_NPS_COMPRESS_UPX),y)
|
||||
$(STAGING_DIR_HOST)/bin/upx --lzma --best $(GO_PKG_BUILD_BIN_DIR)/nps
|
||||
endif
|
||||
endef
|
||||
|
||||
define Package/nps/install/template
|
||||
$(call GoPackage/Package/Install/Bin,$(PKG_INSTALL_DIR))
|
||||
$(INSTALL_DIR) $(1)/usr/bin
|
||||
$(INSTALL_BIN) $(PKG_INSTALL_DIR)/usr/bin/$(2) $(1)/usr/bin/$(2)
|
||||
endef
|
||||
|
||||
Package/npc/install = $(call Package/nps/install/template,$(1),npc)
|
||||
Package/nps/install = $(call Package/nps/install/template,$(1),nps)
|
||||
|
||||
$(eval $(call GoBinPackage,npc))
|
||||
$(eval $(call GoBinPackage,nps))
|
||||
$(eval $(call BuildPackage,npc))
|
||||
$(eval $(call BuildPackage,nps))
|
||||
4
nps/patches/100-remove-useless-sdk-in-npc.patch
Normal file
4
nps/patches/100-remove-useless-sdk-in-npc.patch
Normal file
@@ -0,0 +1,4 @@
|
||||
diff --git a/cmd/npc/sdk.go b/cmd/npc/sdk.go.bak
|
||||
similarity index 100%
|
||||
rename from cmd/npc/sdk.go
|
||||
rename to cmd/npc/sdk.go.bak
|
||||
66
qBittorrent-static/Makefile
Normal file
66
qBittorrent-static/Makefile
Normal file
@@ -0,0 +1,66 @@
|
||||
#
|
||||
# Copyright (C) 2017-2020
|
||||
#
|
||||
# This is free software, licensed under the GNU General Public License v2.
|
||||
#
|
||||
|
||||
include $(TOPDIR)/rules.mk
|
||||
|
||||
PKG_NAME:=qBittorrent-static
|
||||
PKG_VERSION:=4.4.5_v2.0.7
|
||||
PKG_RELEASE=1
|
||||
|
||||
STRIP:=true
|
||||
|
||||
ifeq ($(ARCH),x86_64)
|
||||
PKG_ARCH:=x86_64
|
||||
endif
|
||||
|
||||
ifeq ($(ARCH),arm64)
|
||||
PKG_ARCH:=aarch64
|
||||
endif
|
||||
|
||||
ifeq ($(ARCH),aarch64)
|
||||
PKG_ARCH:=aarch64
|
||||
endif
|
||||
|
||||
ifeq ($(ARCH),arm)
|
||||
PKG_ARCH:=armv7
|
||||
endif
|
||||
|
||||
include $(INCLUDE_DIR)/package.mk
|
||||
|
||||
define Package/qBittorrent-static
|
||||
SECTION:=net
|
||||
CATEGORY:=Network
|
||||
DEPENDS:=@(arm||aarch64||x86_64)
|
||||
SUBMENU:=BitTorrent
|
||||
TITLE:=bittorrent client programmed in C++ / Qt
|
||||
URL:=https://www.qbittorrent.org/
|
||||
endef
|
||||
|
||||
define Package/qBittorrent-static/description
|
||||
qBittorrent is a bittorrent client programmed in C++ / Qt that uses
|
||||
libtorrent (sometimes called libtorrent-rasterbar) by Arvid Norberg.
|
||||
It aims to be a good alternative to all other bittorrent clients out
|
||||
there. qBittorrent is fast, stable and provides unicode support as
|
||||
well as many features.
|
||||
endef
|
||||
|
||||
define Download/qbittorrent
|
||||
URL:=https://github.com/userdocs/qbittorrent-nox-static/releases/download/release-$(PKG_VERSION)
|
||||
URL_FILE:=$(PKG_ARCH)-qbittorrent-nox
|
||||
FILE:=qbittorrent-nox
|
||||
HASH:=skip
|
||||
endef
|
||||
|
||||
define Build/Compile
|
||||
endef
|
||||
|
||||
define Package/qBittorrent-static/install
|
||||
$(INSTALL_DIR) $(1)/usr/bin
|
||||
$(INSTALL_BIN) $(DL_DIR)/qbittorrent-nox $(1)/usr/bin
|
||||
endef
|
||||
|
||||
$(eval $(call Download,qbittorrent))
|
||||
$(eval $(call BuildPackage,qBittorrent-static))
|
||||
95
qBittorrent/Makefile
Normal file
95
qBittorrent/Makefile
Normal file
@@ -0,0 +1,95 @@
|
||||
#
|
||||
# Copyright (C) 2017-2020
|
||||
#
|
||||
# This is free software, licensed under the GNU General Public License v2.
|
||||
#
|
||||
|
||||
include $(TOPDIR)/rules.mk
|
||||
|
||||
PKG_NAME:=qbittorrent
|
||||
PKG_VERSION:=4.4.5
|
||||
PKG_RELEASE=1
|
||||
|
||||
PKG_SOURCE:=qBittorrent-release-$(PKG_VERSION).tar.gz
|
||||
PKG_SOURCE_URL:=https://codeload.github.com/qbittorrent/qBittorrent/tar.gz/release-$(PKG_VERSION)?
|
||||
PKG_HASH:=70c2128b44fe4df4dfc8afc765a304d70cf1b042b5214bcc855d8b3bbc9ccf36
|
||||
|
||||
PKG_BUILD_DIR:=$(BUILD_DIR)/qBittorrent-release-$(PKG_VERSION)
|
||||
|
||||
PKG_LICENSE:=GPL-2.0+
|
||||
PKG_LICENSE_FILES:=COPYING
|
||||
PKG_CPE_ID:=cpe:/a:qbittorrent:qbittorrent
|
||||
|
||||
PKG_BUILD_DEPENDS:=qttools
|
||||
|
||||
PKG_BUILD_PARALLEL:=1
|
||||
PKG_INSTALL:=1
|
||||
PKG_USE_MIPS16:=0
|
||||
|
||||
include $(INCLUDE_DIR)/package.mk
|
||||
include $(INCLUDE_DIR)/cmake.mk
|
||||
|
||||
define Package/qbittorrent
|
||||
SECTION:=net
|
||||
CATEGORY:=Network
|
||||
SUBMENU:=BitTorrent
|
||||
DEPENDS:=+libgcc +libstdcpp \
|
||||
+rblibtorrent \
|
||||
+libopenssl \
|
||||
+qt5-core \
|
||||
+qt5-network \
|
||||
+qt5-sql \
|
||||
+qt5-xml \
|
||||
+zlib
|
||||
TITLE:=bittorrent client programmed in C++ / Qt
|
||||
URL:=https://www.qbittorrent.org/
|
||||
PROVIDES:=qBittorrent
|
||||
endef
|
||||
|
||||
define Package/qbittorrent/description
|
||||
qBittorrent is a bittorrent client programmed in C++ / Qt that uses
|
||||
libtorrent (sometimes called libtorrent-rasterbar) by Arvid Norberg.
|
||||
It aims to be a good alternative to all other bittorrent clients out
|
||||
there. qBittorrent is fast, stable and provides unicode support as
|
||||
well as many features.
|
||||
endef
|
||||
|
||||
CMAKE_OPTIONS += \
|
||||
-DCMAKE_BUILD_TYPE=Release \
|
||||
-DQT6=OFF \
|
||||
-DSTACKTRACE=OFF \
|
||||
-DWEBUI=ON \
|
||||
-DGUI=OFF \
|
||||
-DVERBOSE_CONFIGURE=ON
|
||||
|
||||
# The pcre2 is compiled with support for mips16
|
||||
ifdef CONFIG_USE_MIPS16
|
||||
TARGET_CFLAGS += -minterlink-mips16
|
||||
endif
|
||||
|
||||
# Support the glibc
|
||||
ifdef CONFIG_USE_GLIBC
|
||||
TARGET_LDFLAGS += -ldl -lrt -lpthread
|
||||
endif
|
||||
|
||||
TARGET_CFLAGS += -std=c++17 -ffunction-sections -fdata-sections -flto
|
||||
TARGET_LDFLAGS += -Wl,--gc-sections,--as-needed -flto
|
||||
|
||||
# The pentium-mmx with lto will build failed on qt6
|
||||
ifeq ($(ARCH),i386)
|
||||
ifneq ($(findstring pentium-mmx,$(CONFIG_CPU_TYPE)),)
|
||||
TARGET_CFLAGS := $(filter-out -flto,$(TARGET_CFLAGS))
|
||||
TARGET_LDFLAGS := $(filter-out -flto,$(TARGET_LDFLAGS))
|
||||
endif
|
||||
endif
|
||||
|
||||
define Package/qbittorrent/conffiles
|
||||
/etc/config/qbittorrent
|
||||
endef
|
||||
|
||||
define Package/qbittorrent/install
|
||||
$(INSTALL_DIR) $(1)/usr/bin
|
||||
$(INSTALL_BIN) $(PKG_INSTALL_DIR)/usr/bin/qbittorrent-nox $(1)/usr/bin
|
||||
endef
|
||||
|
||||
$(eval $(call BuildPackage,qbittorrent))
|
||||
200
qtbase/Makefile
Normal file
200
qtbase/Makefile
Normal file
@@ -0,0 +1,200 @@
|
||||
#
|
||||
# Copyright (C) 2020 Openwrt.org
|
||||
#
|
||||
# This is free software, licensed under the Apache License, Version 2.0 .
|
||||
#
|
||||
|
||||
include $(TOPDIR)/rules.mk
|
||||
|
||||
PKG_NAME:=qtbase
|
||||
PKG_BASE:=5.15
|
||||
PKG_BUGFIX:=6
|
||||
PKG_VERSION:=$(PKG_BASE).$(PKG_BUGFIX)
|
||||
PKG_RELEASE:=1
|
||||
|
||||
PKG_SOURCE:=$(PKG_NAME)-everywhere-opensource-src-$(PKG_VERSION).tar.xz
|
||||
PKG_SOURCE_URL:= \
|
||||
http://master.qt.io/archive/qt/$(PKG_BASE)/$(PKG_VERSION)/submodules \
|
||||
http://mirrors.tuna.tsinghua.edu.cn/qt/archive/qt/$(PKG_BASE)/$(PKG_VERSION)/submodules \
|
||||
http://qt.mirror.constant.com/archive/qt/$(PKG_BASE)/$(PKG_VERSION)/submodules
|
||||
PKG_HASH:=396bc6b0d773ac6a7c691a4c3d901999f571e3e7033d7fd6f65e4ef2b6eb7340
|
||||
|
||||
PKG_BUILD_DIR:=$(BUILD_DIR)/$(PKG_NAME)-everywhere-src-$(PKG_VERSION)
|
||||
|
||||
PKG_BUILD_PARALLEL:=1
|
||||
PKG_USE_MIPS16:=0
|
||||
PKG_CPE_ID:=cpe:/a:qt:qt
|
||||
|
||||
include $(INCLUDE_DIR)/package.mk
|
||||
|
||||
define Package/qtbase/Default
|
||||
SECTION:=libs
|
||||
CATEGORY:=Libraries
|
||||
SUBMENU:=Qt5
|
||||
TITLE:=qtbase
|
||||
URL:=http://qt-project.org
|
||||
DEPENDS:=+libgcc +libstdcpp @!LINUX_2_6_36
|
||||
endef
|
||||
|
||||
define Package/qtbase/description
|
||||
This package provides the Qt5 libraries.
|
||||
|
||||
Qt is a cross-platform application development framework for desktop, embedded and mobile.
|
||||
Supported Platforms include Linux, OS X, Windows, VxWorks, QNX, Android, iOS, BlackBerry,
|
||||
Sailfish OS and others.
|
||||
|
||||
Qt is not a programming language on its own. It is a framework written in C++.
|
||||
|
||||
This package provides the following run-time libraries:
|
||||
- core
|
||||
- network
|
||||
- xml
|
||||
endef
|
||||
|
||||
define Package/qtbase
|
||||
$(call Package/qtbase/Default)
|
||||
TITLE+=all libs
|
||||
DEPENDS+=$(QTBASE_DEPENDS)
|
||||
endef
|
||||
|
||||
define Package/qtbase/install
|
||||
true
|
||||
endef
|
||||
|
||||
define Package/qtbase/config
|
||||
config QT5_INCLUDE_ATOMIC
|
||||
bool "Depends on libatomic"
|
||||
default y if !(arm_v7 || ARCH_64BIT || TARGET_x86)
|
||||
default n
|
||||
help
|
||||
Check this options to add the libatomic to the dependences.
|
||||
- You'd better to confirm whether your compiler need the external libatomic.
|
||||
Otherwise, it is not recommended to modify this option mannually.
|
||||
|
||||
menu "Select Qtbase Libraries"
|
||||
comment "Qtbase Libraries"
|
||||
|
||||
$(foreach lib,$(QTBASE_LIBS),
|
||||
config PACKAGE_qt5-$(lib)
|
||||
prompt "Qtbase $(lib) library."
|
||||
default m if ALL
|
||||
)
|
||||
endmenu
|
||||
endef
|
||||
|
||||
PKG_CONFIG_DEPENDS = CONFIG_QT5_INCLUDE_ATOMIC
|
||||
|
||||
EXTRA_CFLAGS += $(FPIC) -ffunction-sections -fdata-sections -flto
|
||||
EXTRA_LDFLAGS += -Wl,--gc-sections,--as-needed
|
||||
|
||||
CONFIGURE_ARGS = \
|
||||
-sysroot $(STAGING_DIR) \
|
||||
-hostprefix $(STAGING_DIR_HOSTPKG) \
|
||||
-extprefix $(STAGING_DIR)/usr \
|
||||
-prefix /usr \
|
||||
-archdatadir /usr/share/Qt \
|
||||
-datadir /usr/share/Qt \
|
||||
-device linux-generic-g++ \
|
||||
-device-option CROSS_COMPILE="$(TARGET_CROSS)" \
|
||||
-device-option COMPILER_FLAGS="$(TARGET_CFLAGS) $(EXTRA_CFLAGS) $(TARGET_CPPFLAGS) $(EXTRA_CPPFLAGS)" \
|
||||
-device-option LINKER_FLAGS="$(TARGET_LDFLAGS) $(EXTRA_LDFLAGS)" \
|
||||
-confirm-license \
|
||||
-opensource \
|
||||
-release \
|
||||
-shared \
|
||||
-strip \
|
||||
-no-rpath \
|
||||
-no-use-gold-linker \
|
||||
-ltcg \
|
||||
-mimetype-database \
|
||||
-openssl-linked \
|
||||
-qt-doubleconversion \
|
||||
-system-pcre \
|
||||
-system-zlib \
|
||||
$(if $(findstring i386,$(ARCH)),-no-sse2 -no-sse4.1) \
|
||||
-no-angle \
|
||||
-no-cups \
|
||||
-no-dbus \
|
||||
-no-directfb \
|
||||
-no-dtls\
|
||||
-no-egl \
|
||||
-no-eglfs \
|
||||
-no-freetype \
|
||||
-no-gbm \
|
||||
-no-glib \
|
||||
-no-gtk \
|
||||
-no-gui \
|
||||
-no-harfbuzz \
|
||||
-no-iconv \
|
||||
-no-icu \
|
||||
-no-kms \
|
||||
-no-libjpeg \
|
||||
-no-libmd4c \
|
||||
-no-libpng \
|
||||
-no-libudev \
|
||||
-no-mtdev \
|
||||
-no-opengl \
|
||||
-no-opengles3 \
|
||||
-no-openvg \
|
||||
-no-pch \
|
||||
-no-slog2 \
|
||||
-sql-sqlite \
|
||||
-no-trace \
|
||||
-no-tslib \
|
||||
-no-vulkan \
|
||||
-no-widgets \
|
||||
-no-xcb \
|
||||
-no-xkbcommon \
|
||||
-no-zstd \
|
||||
-no-compile-examples \
|
||||
-no-feature-concurrent \
|
||||
-no-feature-gssapi \
|
||||
-no-feature-testlib \
|
||||
-make libs \
|
||||
-nomake examples \
|
||||
-nomake tests \
|
||||
-nomake tools \
|
||||
-v
|
||||
|
||||
|
||||
define Build/Compile
|
||||
+$(MAKE) $(PKG_JOBS) -C $(PKG_BUILD_DIR)
|
||||
endef
|
||||
|
||||
define Build/InstallDev
|
||||
$(MAKE) -C $(PKG_BUILD_DIR) install
|
||||
endef
|
||||
|
||||
define Package/qtbase/Default/install
|
||||
$(INSTALL_DIR) $(1)/usr/lib
|
||||
$(CP) $(PKG_BUILD_DIR)/lib/libQt5$(shell echo $(2) | sed -e 's/\b[[:alpha:]]/\u&/g').so* $(1)/usr/lib
|
||||
endef
|
||||
|
||||
define DefineQtbaseLibrary
|
||||
QTBASE_DEPENDS+=+qt5-$(1)
|
||||
|
||||
QTBASE_LIBS+=$(1)
|
||||
|
||||
define Package/qt5-$(1)
|
||||
$(call Package/qtbase/Default)
|
||||
TITLE+=$(1)
|
||||
DEPENDS+=$(foreach lib,$(2),+qt5-$(lib)) $(3)
|
||||
HIDDEN:=1
|
||||
endef
|
||||
|
||||
define Package/qt5-$(1)/description
|
||||
This package contains the qt5 $(1) library.
|
||||
endef
|
||||
|
||||
define Package/qt5-$(1)/install
|
||||
$(call Package/qtbase/Default/install,$$(1),$(1))
|
||||
endef
|
||||
endef
|
||||
|
||||
$(eval $(call DefineQtbaseLibrary,core,,+QT5_INCLUDE_ATOMIC:libatomic +libpcre2-16 +zlib))
|
||||
$(eval $(call DefineQtbaseLibrary,network,core,+libopenssl +zlib))
|
||||
$(eval $(call DefineQtbaseLibrary,xml,core,))
|
||||
$(eval $(call DefineQtbaseLibrary,sql,core))
|
||||
|
||||
$(foreach lib,$(QTBASE_LIBS),$(eval $(call BuildPackage,qt5-$(lib))))
|
||||
$(eval $(call BuildPackage,qtbase))
|
||||
50
qttools/Makefile
Normal file
50
qttools/Makefile
Normal file
@@ -0,0 +1,50 @@
|
||||
#
|
||||
# Copyright (C) 2019 Openwrt.org
|
||||
#
|
||||
# This is free software, licensed under the Apache License, Version 2.0 .
|
||||
#
|
||||
|
||||
include $(TOPDIR)/rules.mk
|
||||
|
||||
PKG_NAME:=qttools
|
||||
PKG_BASE:=5.15
|
||||
PKG_BUGFIX:=6
|
||||
PKG_VERSION:=$(PKG_BASE).$(PKG_BUGFIX)
|
||||
PKG_RELEASE:=1
|
||||
|
||||
PKG_SOURCE:=$(PKG_NAME)-everywhere-opensource-src-$(PKG_VERSION).tar.xz
|
||||
PKG_SOURCE_URL:= \
|
||||
http://master.qt.io/archive/qt/$(PKG_BASE)/$(PKG_VERSION)/submodules \
|
||||
http://mirrors.tuna.tsinghua.edu.cn/qt/archive/qt/$(PKG_BASE)/$(PKG_VERSION)/submodules \
|
||||
http://qt.mirror.constant.com/archive/qt/$(PKG_BASE)/$(PKG_VERSION)/submodules
|
||||
PKG_HASH:=2c1486ab7e6dad76fb34642cd4f91d533e5dfeec0ee527129c2c2ed4ab283c3b
|
||||
|
||||
PKG_BUILD_DIR:=$(BUILD_DIR)/$(PKG_NAME)-everywhere-src-$(PKG_VERSION)
|
||||
|
||||
PKG_BUILD_PARALLEL:=1
|
||||
PKG_BUILD_DEPENDS:=qtbase
|
||||
|
||||
include $(INCLUDE_DIR)/package.mk
|
||||
|
||||
define Package/qttools
|
||||
SECTION:=libs
|
||||
CATEGORY:=Libraries
|
||||
SUBMENU:=Qt5
|
||||
TITLE:=qttools
|
||||
URL:=http://qt-project.org
|
||||
BUILDONLY:=1
|
||||
endef
|
||||
|
||||
define Build/Configure
|
||||
cd $(PKG_BUILD_DIR) && qmake -o Makefile qttools.pro
|
||||
endef
|
||||
|
||||
define Build/Compile
|
||||
+$(MAKE) $(PKG_JOBS) -C $(PKG_BUILD_DIR)
|
||||
endef
|
||||
|
||||
define Build/InstallDev
|
||||
$(MAKE) -C $(PKG_BUILD_DIR) install
|
||||
endef
|
||||
|
||||
$(eval $(call BuildPackage,qttools))
|
||||
62
rblibtorrent/Makefile
Normal file
62
rblibtorrent/Makefile
Normal file
@@ -0,0 +1,62 @@
|
||||
include $(TOPDIR)/rules.mk
|
||||
|
||||
PKG_NAME:=rblibtorrent
|
||||
PKG_VERSION:=1.2.17
|
||||
PKG_RELEASE=1
|
||||
|
||||
PKG_SOURCE_PROTO:=git
|
||||
PKG_SOURCE_URL:=https://github.com/arvidn/libtorrent.git
|
||||
PKG_SOURCE_SUBDIR:=$(PKG_NAME)-$(PKG_VERSION)
|
||||
PKG_SOURCE_VERSION:=2d34455ad2b828d3da23634f7de93fafded5442d
|
||||
PKG_SOURCE:=$(PKG_NAME)-$(PKG_VERSION).tar.gz
|
||||
PKG_MIRROR_HASH:=3fa86163d370584f747d34737a556a5426fd5eb4ce1ba1dc594dce3357594d90
|
||||
|
||||
PKG_LICENSE:=BSD
|
||||
PKG_LICENSE_FILES:=COPYING
|
||||
|
||||
PKG_USE_MIPS16:=0
|
||||
PKG_BUILD_PARALLEL:=1
|
||||
|
||||
include $(INCLUDE_DIR)/package.mk
|
||||
include $(INCLUDE_DIR)/cmake.mk
|
||||
|
||||
define Package/rblibtorrent
|
||||
SECTION:=libs
|
||||
CATEGORY:=Libraries
|
||||
TITLE:=Rasterbar BitTorrent library
|
||||
URL:=https://www.libtorrent.org/
|
||||
DEPENDS:=+libgcc +libstdcpp +libopenssl +boost +boost-system +boost-chrono +boost-random +libatomic
|
||||
MAINTAINER:=Arvid Norberg <arvid@libtorrent.org>
|
||||
endef
|
||||
|
||||
define Package/rblibtorrent/description
|
||||
Rasterbar libtorrent is a C++ library that aims to be a good alternative to
|
||||
all the other bittorrent implementations around. It is a library and not a
|
||||
full featured client, although it comes with a working example client.
|
||||
endef
|
||||
|
||||
TARGET_CFLAGS += $(if $(CONFIG_SOFT_FLOAT),-DBOOST_NO_FENV_H) -fPIC -ffunction-sections -fdata-sections -flto
|
||||
EXTRA_CXXFLAGS += $(if $(CONFIG_GCC_VERSION_4_8),-std=gnu++11,-std=gnu++17)
|
||||
TARGET_LDFLAGS += -lstdc++ -Wl,--gc-sections,--as-needed -flto
|
||||
|
||||
CMAKE_OPTIONS += \
|
||||
-DCMAKE_BUILD_TYPE=Release \
|
||||
-DCMAKE_CXX_STANDARD=17 \
|
||||
-DBUILD_SHARED_LIBS=ON \
|
||||
-Ddeprecated-functions=ON \
|
||||
-Dencryption=ON \
|
||||
-Diconv=ON \
|
||||
-Dstatic_runtime=ON \
|
||||
-Dlogging=OFF
|
||||
|
||||
define Build/InstallDev
|
||||
$(INSTALL_DIR) $(1)
|
||||
$(CP) $(PKG_INSTALL_DIR)/* $(1)
|
||||
endef
|
||||
|
||||
define Package/rblibtorrent/install
|
||||
$(INSTALL_DIR) $(1)/usr/lib
|
||||
$(CP) $(PKG_INSTALL_DIR)/usr/lib/*.so* $(1)/usr/lib
|
||||
endef
|
||||
|
||||
$(eval $(call BuildPackage,rblibtorrent))
|
||||
45
tcpping/Makefile
Normal file
45
tcpping/Makefile
Normal file
@@ -0,0 +1,45 @@
|
||||
# SPDX-License-Identifier: GPL-3.0-only
|
||||
#
|
||||
# Copyright (C) 2021 ImmortalWrt.org
|
||||
|
||||
include $(TOPDIR)/rules.mk
|
||||
|
||||
PKG_NAME:=tcpping
|
||||
PKG_VERSION:=0.2
|
||||
PKG_RELEASE=2
|
||||
|
||||
PKG_SOURCE_PROTO:=git
|
||||
PKG_SOURCE_URL:=https://github.com/coolsnowwolf/tcping
|
||||
PKG_SOURCE_DATE:=2020-09-19
|
||||
PKG_SOURCE_VERSION:=d890cc1bd8e3951390ceeff1ccb092a5d802850c
|
||||
PKG_MIRROR_HASH:=018554a80e8a9d8fedd39821f35aa02c7c763fd42213761fba9b21c2533e1ab8
|
||||
|
||||
PKG_BUILD_PARALLEL:=1
|
||||
|
||||
include $(INCLUDE_DIR)/package.mk
|
||||
|
||||
define Package/tcpping
|
||||
SECTION:=net
|
||||
CATEGORY:=Network
|
||||
DEPENDS:=+libnet-1.2.x +libpcap
|
||||
TITLE:=TCP Ping Tool
|
||||
endef
|
||||
|
||||
define Package/tcpping/description
|
||||
Ping look-alike that uses TCP SYN packets to
|
||||
get around firewalls and ICMP blackholes.
|
||||
endef
|
||||
|
||||
define Build/Compile
|
||||
+$(MAKE) $(PKG_JOBS) -C $(PKG_BUILD_DIR) \
|
||||
$(TARGET_CONFIGURE_OPTS) \
|
||||
CFLAGS="$(TARGET_CFLAGS) -I$(STAGING_DIR)/usr/lib/libnet-1.2.x/include -L$(STAGING_DIR)/usr/lib/libnet-1.2.x/lib" \
|
||||
INSTALL_PROG=":"
|
||||
endef
|
||||
|
||||
define Package/tcpping/install
|
||||
$(INSTALL_DIR) $(1)/usr/bin
|
||||
$(INSTALL_BIN) $(PKG_BUILD_DIR)/tcpping $(1)/usr/bin/tcpping
|
||||
endef
|
||||
|
||||
$(eval $(call BuildPackage,tcpping))
|
||||
85
uugamebooster/Makefile
Normal file
85
uugamebooster/Makefile
Normal file
@@ -0,0 +1,85 @@
|
||||
#
|
||||
# Copyright (C) 2021 KFERMercer <KFER.Mercer@gmail.com>
|
||||
#
|
||||
# This is free software, licensed under the GNU General Public License v3.
|
||||
#
|
||||
|
||||
#
|
||||
# to get the latest version & md5 checksum:
|
||||
# curl -L -s -k -H "Accept:text/plain" "http://router.uu.163.com/api/plugin?type=openwrt-$(UU_ARCH)"
|
||||
#
|
||||
|
||||
include $(TOPDIR)/rules.mk
|
||||
|
||||
PKG_NAME:=uugamebooster
|
||||
PKG_VERSION:=v3.6.2
|
||||
PKG_RELEASE:=1
|
||||
|
||||
include $(INCLUDE_DIR)/package.mk
|
||||
|
||||
define Package/uugamebooster
|
||||
SECTION:=net
|
||||
CATEGORY:=Network
|
||||
DEPENDS:=@(aarch64||arm||mipsel||x86_64) +kmod-tun
|
||||
TITLE:=NetEase UU Game Booster
|
||||
URL:=https://uu.163.com
|
||||
endef
|
||||
|
||||
define Package/uugamebooster/description
|
||||
NetEase's UU Game Booster Accelerates Triple-A Gameplay and Market
|
||||
endef
|
||||
|
||||
ifeq ($(ARCH),arm)
|
||||
UU_ARCH:=arm
|
||||
PKG_MD5SUM:=ee720928879208091c509c685f21db05
|
||||
endif
|
||||
|
||||
ifeq ($(ARCH),aarch64)
|
||||
UU_ARCH:=aarch64
|
||||
PKG_MD5SUM:=279ec2a24f2765669aee8f57cb47e30d
|
||||
endif
|
||||
|
||||
ifeq ($(ARCH),mipsel)
|
||||
UU_ARCH:=mipsel
|
||||
PKG_MD5SUM:=d2176e47a783e0be9bbecbceb606470b
|
||||
endif
|
||||
|
||||
ifeq ($(ARCH),x86_64)
|
||||
UU_ARCH:=x86_64
|
||||
PKG_MD5SUM:=3656d9cedbe369be7adc059248a9d4bd
|
||||
endif
|
||||
|
||||
PKG_SOURCE_URL:=https://uu.gdl.netease.com/uuplugin/openwrt-$(UU_ARCH)/$(PKG_VERSION)/uu.tar.gz?
|
||||
PKG_SOURCE:=$(PKG_NAME)-$(UU_ARCH)-$(PKG_VERSION).tar.gz
|
||||
|
||||
STRIP:=true
|
||||
|
||||
UNTAR_DIR:=$(BUILD_DIR)/$(PKG_NAME)-$(PKG_VERSION)/$(PKG_NAME)-$(UU_ARCH)-bin
|
||||
|
||||
define Build/Prepare
|
||||
mkdir -vp $(UNTAR_DIR)
|
||||
tar -zxvf $(DL_DIR)/$(PKG_SOURCE) -C $(UNTAR_DIR)
|
||||
endef
|
||||
|
||||
define Build/Compile
|
||||
endef
|
||||
|
||||
define Package/uugamebooster/conffiles
|
||||
/root/.uuplugin_uuid
|
||||
endef
|
||||
|
||||
define Package/uugamebooster/install
|
||||
# $(INSTALL_DIR) $(1)/etc/init.d
|
||||
# $(INSTALL_BIN) ./files/uugamebooster.init $(1)/etc/init.d/uuplugin
|
||||
|
||||
$(INSTALL_DIR) $(1)/usr/share/uugamebooster
|
||||
$(INSTALL_BIN) $(UNTAR_DIR)/uuplugin $(1)/usr/share/uugamebooster/uuplugin
|
||||
$(INSTALL_CONF) $(UNTAR_DIR)/uu.conf $(1)/usr/share/uugamebooster/uu.conf
|
||||
|
||||
# not finish yet:
|
||||
# $(INSTALL_DIR) $(1)/usr/bin
|
||||
# $(INSTALL_BIN) ./files/uugamebooster-update $(1)/usr/bin/uugamebooster
|
||||
# $(LN) $(1)/usr/bin/uugamebooster/uugamebooster-update $(1)/usr/bin/uugamebooster-update
|
||||
endef
|
||||
|
||||
$(eval $(call BuildPackage,uugamebooster))
|
||||
18
uugamebooster/files/uugamebooster-update
Executable file
18
uugamebooster/files/uugamebooster-update
Executable file
@@ -0,0 +1,18 @@
|
||||
#!/bin/sh
|
||||
|
||||
# Return: 0 means update flag is set.
|
||||
check_update() {
|
||||
if [ -f "/usr/bin/uugamebooster/uu.update" ];then
|
||||
return 0
|
||||
else
|
||||
return 1
|
||||
fi
|
||||
}
|
||||
|
||||
check_update
|
||||
if [ "$?" != "0" ];then
|
||||
exit 0
|
||||
return
|
||||
fi
|
||||
|
||||
exit 0
|
||||
@@ -1,68 +1,58 @@
|
||||
# SPDX-Identifier-License: GPL-3.0-only
|
||||
#
|
||||
# Copyright (C) 2015-2016 OpenWrt.org
|
||||
#
|
||||
# This is free software, licensed under the GNU General Public License v3.
|
||||
#
|
||||
# Copyright (C) 2021 ImmortalWrt.org
|
||||
|
||||
include $(TOPDIR)/rules.mk
|
||||
|
||||
ifeq ($(ARCH),x86_64)
|
||||
PKG_ARCH_VERYSYNC:=amd64
|
||||
endif
|
||||
ifeq ($(ARCH),mipsel)
|
||||
PKG_ARCH_VERYSYNC:=mipsle
|
||||
endif
|
||||
ifeq ($(ARCH),mips)
|
||||
PKG_ARCH_VERYSYNC:=mips
|
||||
endif
|
||||
ifeq ($(ARCH),i386)
|
||||
PKG_ARCH_VERYSYNC:=386
|
||||
endif
|
||||
ifeq ($(ARCH),arm)
|
||||
PKG_ARCH_VERYSYNC:=arm
|
||||
endif
|
||||
ifeq ($(ARCH),aarch64)
|
||||
PKG_ARCH_VERYSYNC:=arm64
|
||||
endif
|
||||
ifeq ($(ARCH),powerpc64)
|
||||
PKG_ARCH_VERYSYNC:=ppc64
|
||||
PKG_ARCH_VERYSYNC:=arm64
|
||||
PKG_HASH_VERYSYNC:=113b1098434c9657e51d95a86f70436ff55db291cca1094bc65e911642424367
|
||||
else ifeq ($(ARCH),arm)
|
||||
PKG_ARCH_VERYSYNC:=arm
|
||||
PKG_HASH_VERYSYNC:=6eb2a8e41dcdaacfecc20c13ef6b7805176dad6a410d38bf65a962bc0f7f8554
|
||||
else ifeq ($(ARCH),i386)
|
||||
PKG_ARCH_VERYSYNC:=386
|
||||
PKG_HASH_VERYSYNC:=d84b71cc7ef0db95bf0f6dc3d38884b3856cc36ae1ac1f430c35cdd033cc7c16
|
||||
else ifeq ($(ARCH),mips)
|
||||
PKG_ARCH_VERYSYNC:=mips
|
||||
PKG_HASH_VERYSYNC:=54d8fe303e3b51ae5078fe74e69ab64d102334e55ee257d9eec7aef13a21d911
|
||||
else ifeq ($(ARCH),mipsel)
|
||||
PKG_ARCH_VERYSYNC:=mipsle
|
||||
PKG_HASH_VERYSYNC:=7edc4eae4a1941d8a52fce2506d599af6f207498a3d8cabe819f023d0df15e2f
|
||||
else ifeq ($(ARCH),powerpc64)
|
||||
PKG_ARCH_VERYSYNC:=ppc64
|
||||
PKG_HASH_VERYSYNC:=c89e670b31123b240fc5e4be15cb7e836e8584b5a955efea5fca5b4f9d009ea1
|
||||
else ifeq ($(ARCH),x86_64)
|
||||
PKG_ARCH_VERYSYNC:=amd64
|
||||
PKG_HASH_VERYSYNC:=6214cd485bfc40a8c53a3c53e900a0fa2e629d5137345f3ad2195bd9e0f47fba
|
||||
endif
|
||||
|
||||
PKG_NAME:=verysync
|
||||
PKG_VERSION:=v2.13.2
|
||||
PKG_RELEASE:=1
|
||||
PKG_BUILD_DIR:=$(BUILD_DIR)/$(PKG_NAME)-$(PKG_VERSION)
|
||||
PKG_SOURCE:=$(PKG_NAME)-linux-$(PKG_ARCH_VERYSYNC)-$(PKG_VERSION).tar.gz
|
||||
PKG_SOURCE_URL:=http://dl.verysync.com/releases/$(PKG_VERSION)/
|
||||
PKG_HASH:=skip
|
||||
PKG_VERSION:=2.14.0
|
||||
PKG_RELEASE:=$(AUTORELEASE)
|
||||
|
||||
PKG_SOURCE:=$(PKG_NAME)-linux-$(PKG_ARCH_VERYSYNC)-v$(PKG_VERSION).tar.gz
|
||||
PKG_SOURCE_URL:=http://dl.verysync.com/releases/v$(PKG_VERSION)/ \
|
||||
http://dl-cn.verysync.com/releases/v$(PKG_VERSION)/
|
||||
PKG_HASH:=$(PKG_HASH_VERYSYNC)
|
||||
PKG_BUILD_DIR:=$(BUILD_DIR)/$(PKG_NAME)-linux-$(PKG_ARCH_VERYSYNC)-v$(PKG_VERSION)
|
||||
|
||||
include $(INCLUDE_DIR)/package.mk
|
||||
|
||||
define Package/$(PKG_NAME)
|
||||
SECTION:=net
|
||||
CATEGORY:=Network
|
||||
TITLE:=A efficient data transmission tool
|
||||
DEPENDS:=
|
||||
URL:=http://www.verysync.com
|
||||
endef
|
||||
|
||||
define Package/$(PKG_NAME)/description
|
||||
Verysync is a efficient data transmission tool.
|
||||
endef
|
||||
|
||||
define Build/Prepare
|
||||
tar -xzvf $(DL_DIR)/$(PKG_SOURCE) -C $(PKG_BUILD_DIR)
|
||||
endef
|
||||
|
||||
define Build/Configure
|
||||
define Package/verysync
|
||||
SECTION:=net
|
||||
CATEGORY:=Network
|
||||
TITLE:=A efficient data transmission tool
|
||||
URL:=http://www.verysync.com
|
||||
DEPENDS:=@(aarch64||arm||i386||mips||mipsel||powerpc64||x86_64)
|
||||
endef
|
||||
|
||||
define Build/Compile
|
||||
endef
|
||||
|
||||
define Package/$(PKG_NAME)/install
|
||||
define Package/verysync/install
|
||||
$(INSTALL_DIR) $(1)/usr/bin
|
||||
$(INSTALL_BIN) $(PKG_BUILD_DIR)/$(PKG_NAME)-linux-$(PKG_ARCH_VERYSYNC)-$(PKG_VERSION)/verysync $(1)/usr/bin/verysync
|
||||
$(INSTALL_BIN) $(PKG_BUILD_DIR)/verysync $(1)/usr/bin/verysync
|
||||
endef
|
||||
|
||||
$(eval $(call BuildPackage,$(PKG_NAME)))
|
||||
$(eval $(call BuildPackage,verysync))
|
||||
|
||||
Reference in New Issue
Block a user