78 Commits

Author SHA1 Message Date
tyk
e970703a11 更新 simpleupdates/scripts/update_tailscale.sh 2025-09-17 22:22:42 +08:00
tyk
6b1d2dcca0 更新 simpleupdates/scripts/update_sshd.sh 2025-09-17 22:22:24 +08:00
tyk
de3c77ded7 更新 simpleupdates/scripts/update_simplefirewall.sh 2025-09-17 22:22:06 +08:00
tyk
b79f0435b7 更新 simpleupdates/scripts/update_simpleadmin.sh 2025-09-17 22:21:50 +08:00
tyk
fedca206e8 更新 simpleupdates/scripts/update_socat-at-bridge.sh 2025-09-17 22:21:22 +08:00
tyk
36915e3e8f 更新 README.md 2025-09-17 21:57:31 +08:00
tyk
1d57cbbca8 更新 RMxxx_rgmii_toolkit.sh 2025-09-17 21:56:43 +08:00
tyk
c413a02fc7 更新 RMxxx_rgmii_toolkit.sh 2025-09-17 21:49:01 +08:00
Cameron Thompson
909918c538 Merge pull request #170 from iamromulan/development-SDXLEMUR
Merge new PR's for SDXLEMUR
2025-05-31 20:19:31 -04:00
Cameron Thompson
47aaea465b Prep for SDXLEMUR main branch 2025-05-31 20:18:31 -04:00
Cameron Thompson
a48cb19db8 Merge pull request #168 from clndwhr/bug/fix-sms-phone-number
[BUG FIX] Fix Parsing for the phone number on received SMS
2025-05-31 20:11:12 -04:00
Cameron Thompson
630b897cd5 Merge pull request #167 from 1alessandro1/patch-2
Update year, maybe other branches need this too
2025-05-31 20:10:18 -04:00
Christopher Landwehr
2bc2ae3844 had to adjust for SMS Short codes in New Zealand where the minimum can be 3 digits (12 length hex string) 2025-05-22 14:05:18 -04:00
Christopher Landwehr
5ea71c3ccb Change the conditional to check on the hexString length and what it starts with vs just with what it starts with as a HEX string > 17 should indidcate the string is actual Hexadecimal and likely UTF-16BE, or starting with 003/002B and length >15 2025-05-22 13:55:50 -04:00
1alessandro1
179c9fa702 Update year 2025-05-22 00:55:41 +02:00
Cameron Thompson
6dd3eb8ea2 Update README.md 2025-05-16 23:43:09 -04:00
Cameron Thompson
5030f2c0bd Update deployment
- Updated simpleadmin content deployment script to obtain content from latest PR's #163 and #165

- Updated all deployment scripts to reflect a gitroot branch of development-SDXLEMUR

- Removed an unused deployment script that is no longer needed.
2025-05-16 23:40:53 -04:00
Cameron Thompson
94053b777e Merge pull request #165 from clndwhr/bug/fix-PCI-and-EARFCN-on-Homepage
[BUG FIX] PCI and EARFCN for NSA on Simple Admin Home Page
2025-05-16 23:12:02 -04:00
Cameron Thompson
b4cd059b76 Revert more overhaul stuff 2025-05-16 23:10:20 -04:00
Cameron Thompson
696cbf3054 Revert "Progress..."
This reverts commit ec07fb07ac.
2025-05-16 23:09:39 -04:00
Cameron Thompson
6e9acd8c87 Merge pull request #163 from clndwhr/bug/fix-bandwidth-reporting-and-adjust-tac
[BUG FIX] Bandwidth reporting and TAC Adjustment
2025-05-16 23:08:01 -04:00
Cameron Thompson
23038054bd Revert more overhaul stuff 2025-05-16 23:07:00 -04:00
Cameron Thompson
90d53cfe1d Revert "Progress..."
This reverts commit ec07fb07ac.
2025-05-16 23:03:40 -04:00
Cameron Thompson
2ef3ea4cb7 Revert "Merge branch 'SDXLEMUR' into development-SDXLEMUR"
This reverts commit 8c80eb7c0f, reversing
changes made to 8d7b02ca92.
2025-05-16 22:54:55 -04:00
Cameron Thompson
8c80eb7c0f Merge branch 'SDXLEMUR' into development-SDXLEMUR 2025-05-16 22:53:11 -04:00
Christopher Landwehr
72845b4360 migrate and cleanup code for SA codebase and structures 2025-05-16 11:36:33 -04:00
Christopher Landwehr
6c7ed50953 adjusting the logic for PCI on NSA(ENDC), and fixing the index for EARCN PCC on NSA(ENDC) 2025-05-16 10:48:57 -04:00
Christopher Landwehr
5996be64f4 updated NR_BANDWIDTH_LOOKUP to th eaccurate reference 2025-05-12 22:31:03 -04:00
Christopher Landwehr
2cbe8b76ab code reduction 2025-05-12 22:30:41 -04:00
Christopher Landwehr
f021311c93 Tac formatting 2025-05-12 22:30:31 -04:00
Christopher Landwehr
71f7dacf72 offline fonts and font-awesome icons 2025-05-12 22:01:54 -04:00
Christopher Landwehr
517f41c590 adjusting the reported Bandwidth mapping, utilzed the same functionality as QuecManager, updated TAC to show Base10 and Base16 value 2025-05-12 21:27:36 -04:00
Christopher Landwehr
69800c0608 Merge branch 'development-SDXLEMUR' of https://github.com/clndwhr/quectel-rgmii-toolkit into development-SDXLEMUR
# Conflicts:
#	README.md
2025-05-12 21:25:51 -04:00
Cameron Thompson
8d7b02ca92 Update README.md 2025-05-12 21:11:49 -04:00
Cameron Thompson
7ee03707e3 Update README.md 2025-05-12 21:10:57 -04:00
Cameron Thompson
4a76a5d032 Merge pull request #117 from 1alessandro1/SDXLEMUR
Convert eNB to decimal
2025-04-02 22:41:51 -04:00
Cameron Thompson
6c3cf93ffd Merge pull request #116 from 1alessandro1/patch-1
Fix typo
2025-01-28 20:43:14 -05:00
1alessandro1
924e06a153 Convert eNB to decimal 2025-01-27 23:52:38 +01:00
1alessandro1
a6fbc35f18 Fix typo 2025-01-27 23:33:16 +01:00
Cameron Thompson
ec07fb07ac Progress... 2024-12-20 16:31:13 -05:00
Cameron Thompson
d52f2c1b0f Begin rework process of opkg/opt 2024-12-09 18:48:33 +00:00
Cameron Thompson
370eb276a0 Update update_tailscale.sh 2024-11-22 19:35:29 -05:00
Cameron Thompson
550552d1a1 Update start_menu.sh 2024-11-20 22:27:53 -05:00
Cameron Thompson
b2758616cc Fix wrong link 2024-11-13 03:05:13 +00:00
Cameron Thompson
6f72fb4568 Update for new gitroot 2024-11-06 00:32:24 -05:00
Cameron Thompson
3235bd2c46 Update update_tailscale.sh 2024-11-01 00:17:38 -04:00
Cameron Thompson
d48f2f9c59 Update RMxxx_rgmii_toolkit.sh 2024-10-30 23:39:11 +00:00
Cameron Thompson
4b9785ceff Update RMxxx_rgmii_toolkit.sh 2024-10-30 19:18:59 -04:00
Cameron Thompson
64ff33c056 Update at-list.md
Add disable automapn command
2024-09-25 00:30:41 -04:00
Cameron Thompson
fffa77f106 Update at-list.md
Add more details
2024-09-25 00:20:25 -04:00
Cameron Thompson
0673ed1020 github directories can be downloaded 2024-09-16 23:56:57 -04:00
Cameron Thompson
acddaf7b08 Update download 2024-09-07 14:51:52 -04:00
Cameron Thompson
3117d70408 Update download
-Po not supported by busybox grep
2024-09-07 14:39:24 -04:00
Cameron Thompson
0e93104d53 Update at-list.md 2024-09-07 14:02:39 -04:00
Cameron Thompson
b4646a6875 draft 2024-09-04 23:34:36 -04:00
Cameron Thompson
96158cf859 edits 2024-08-25 23:16:44 -04:00
Cameron Thompson
2b961a40ef edits 2024-08-25 23:10:36 -04:00
Cameron Thompson
780e3b4cc8 Update download 2024-08-25 22:37:25 -04:00
Cameron Thompson
c32e90a436 Update download 2024-08-25 22:33:39 -04:00
Cameron Thompson
c3931dd009 Add more diagnostics 2024-08-25 22:24:52 -04:00
Cameron Thompson
643412f4ae Add diagnostic echos 2024-08-25 22:09:03 -04:00
Cameron Thompson
00ca424ae6 Update download 2024-08-25 00:22:17 -04:00
Cameron Thompson
949863c70e Create download
Create a download command that uses curl and falls back to wget. Should be able to download entire directories recursively from github as well.
2024-08-24 23:25:22 -04:00
Cameron Thompson
44f3a7aeed Update update_tailscale.sh
Updated to install latest 1.70.0
2024-07-23 01:24:39 -04:00
Cameron Thompson
ca190cebd1 Revert Changes 2024-07-14 12:23:25 -04:00
Cameron Thompson
435c472b16 Revert changes 2024-07-14 02:51:54 -04:00
Cameron Thompson
9c2870eb61 Update update_simpleadmin.sh 2024-07-14 01:49:15 -04:00
Cameron Thompson
a061212ff4 fix syntax 2024-07-14 01:57:04 -04:00
Cameron Thompson
91d1ade6a4 Fix syntax 2024-07-14 01:56:40 -04:00
Cameron Thompson
f872efca51 Merge pull request #69 from dr-dolomite/feature-watchcat
User AT command implementation
2024-07-14 01:55:20 -04:00
Cameron Thompson
1cd14a2225 Add ARCH check 2024-07-14 01:16:49 -04:00
Cameron Thompson
5fffcfd80d Update tailscale to 1.68.2 2024-07-14 00:45:01 -04:00
Cameron Thompson
f7780a589e Update get_atcommand
Uses atcmd11 now instead of microcom
2024-07-14 00:32:59 -04:00
Cameron Thompson
f2592a3dbb Merge branch 'development' of https://github.com/iamromulan/quectel-rgmii-toolkit into development 2024-07-13 23:23:26 -04:00
Cameron Thompson
865adc2fcd Add atcmd11
Separate commands for separate AT streams
2024-07-13 23:23:20 -04:00
Cameron Thompson
3f32d4001b Merge pull request #68 from dr-dolomite/feature-watchcat
Hot fix and band locking improvement and 502 support
2024-07-13 22:52:15 -04:00
Cameron Thompson
41b2c6a4f9 Update screenshots 2024-07-13 22:38:12 -04:00
Cameron Thompson
b8cd5b3a2a Merge pull request #67 from dr-dolomite/feature-watchcat
Added Various Changes and Fixes for Simple Network
2024-07-13 21:01:37 -04:00
844 changed files with 18075 additions and 112688 deletions

3
.gitignore vendored
View File

@@ -1,3 +0,0 @@
# Windows Zone.Identifier files (created when downloading files from internet)
*:Zone.Identifier
*Zone.Identifier

1
.obsidian/app.json vendored
View File

@@ -1 +0,0 @@
{}

View File

@@ -1 +0,0 @@
{}

View File

@@ -1,31 +0,0 @@
{
"file-explorer": true,
"global-search": true,
"switcher": true,
"graph": true,
"backlink": true,
"canvas": true,
"outgoing-link": true,
"tag-pane": true,
"properties": false,
"page-preview": true,
"daily-notes": true,
"templates": true,
"note-composer": true,
"command-palette": true,
"slash-command": false,
"editor-status": true,
"bookmarks": true,
"markdown-importer": false,
"zk-prefixer": false,
"random-note": false,
"outline": true,
"word-count": true,
"slides": false,
"audio-recorder": false,
"workspaces": false,
"file-recovery": true,
"publish": false,
"sync": true,
"webviewer": false
}

View File

@@ -1,173 +0,0 @@
{
"main": {
"id": "cfbe859ecf56fae0",
"type": "split",
"children": [
{
"id": "b83a784c3a7d92c5",
"type": "tabs",
"children": [
{
"id": "f1014514d48382b8",
"type": "leaf",
"state": {
"type": "markdown",
"state": {
"file": "README.md",
"mode": "source",
"source": false
},
"icon": "lucide-file",
"title": "README"
}
}
]
}
],
"direction": "vertical"
},
"left": {
"id": "d0cb12d3f48108e9",
"type": "split",
"children": [
{
"id": "a8a7e64788ca4c59",
"type": "tabs",
"children": [
{
"id": "7d7f951eade08e15",
"type": "leaf",
"state": {
"type": "file-explorer",
"state": {
"sortOrder": "alphabetical",
"autoReveal": false
},
"icon": "lucide-folder-closed",
"title": "Files"
}
},
{
"id": "7febcdc7d3c2deea",
"type": "leaf",
"state": {
"type": "search",
"state": {
"query": "",
"matchingCase": false,
"explainSearch": false,
"collapseAll": false,
"extraContext": false,
"sortOrder": "alphabetical"
},
"icon": "lucide-search",
"title": "Search"
}
},
{
"id": "12bb71ef9436a043",
"type": "leaf",
"state": {
"type": "bookmarks",
"state": {},
"icon": "lucide-bookmark",
"title": "Bookmarks"
}
}
]
}
],
"direction": "horizontal",
"width": 300
},
"right": {
"id": "3bcff15aa34346c5",
"type": "split",
"children": [
{
"id": "249aae86eddbae79",
"type": "tabs",
"children": [
{
"id": "60b3bb238ff8dd44",
"type": "leaf",
"state": {
"type": "backlink",
"state": {
"file": "README.md",
"collapseAll": false,
"extraContext": false,
"sortOrder": "alphabetical",
"showSearch": false,
"searchQuery": "",
"backlinkCollapsed": false,
"unlinkedCollapsed": true
},
"icon": "links-coming-in",
"title": "Backlinks for README"
}
},
{
"id": "168425d9c5df2b15",
"type": "leaf",
"state": {
"type": "outgoing-link",
"state": {
"file": "README.md",
"linksCollapsed": false,
"unlinkedCollapsed": true
},
"icon": "links-going-out",
"title": "Outgoing links from README"
}
},
{
"id": "cb0c34fa52269a79",
"type": "leaf",
"state": {
"type": "tag",
"state": {
"sortOrder": "frequency",
"useHierarchy": true,
"showSearch": false,
"searchQuery": ""
},
"icon": "lucide-tags",
"title": "Tags"
}
},
{
"id": "edfdf272173ebc96",
"type": "leaf",
"state": {
"type": "outline",
"state": {
"file": "README.md",
"followCursor": false,
"showSearch": false,
"searchQuery": ""
},
"icon": "lucide-list",
"title": "Outline of README"
}
}
]
}
],
"direction": "horizontal",
"width": 300,
"collapsed": true
},
"left-ribbon": {
"hiddenItems": {
"switcher:Open quick switcher": false,
"graph:Open graph view": false,
"canvas:Create new canvas": false,
"daily-notes:Open today's daily note": false,
"templates:Insert template": false,
"command-palette:Open command palette": false
}
},
"active": "f1014514d48382b8",
"lastOpenFiles": []
}

249
README.md
View File

@@ -1,61 +1,44 @@
Current Branch: **development-SDXPINN**
# RGMII Toolkit
Software deployment Toolkit for Quectel RM5xxx series 5G modems utilizing an m.2 to RJ45 adapter (RGMII)
>:checkered_flag: Hint: Start by checking out the ipk-source directory, each package is broken down into its contents. Inside, root represents the structure copied starting at / and control includes metadata and scripts to be ran before and after installation. The build-ipk.sh will produce an ipk based on the control and root directories next to it.
Current Branch: **SDXLEMUR**
# SDXPINN OpenWRT Repository
Please PR to [development-SDXLEMUR](https://github.com/iamromulan/quectel-rgmii-toolkit/tree/development-SDXLEMUR) instead of the main one :)
This branch of the repository serves as both an opkg source and feed for the custom packages I make available for Quectel cellular modules with the SDXPINN system. This source is preloaded into my custom firmware for the RM551E-GL found here: https://mega.nz/file/GUkk0RpD#7JsFymzKBBKplxLs5tqc5-m7rBmrB2QPfTfMtf1ZQ4g
Flash with QFlash, QFIL, or qfirehose. At first boot a script will automaticly set the module to PCIe RC mode and USB ECM mode then reboot so wait for that reboot after flash to proceed. From there either by Ethernet or USB ECM visit http://192.168.224.1/ or ssh root@192.168.224.1 Password: iamromulan
> :warning: Custom firmware is only available for the RM551E-GL for now. An RM550V-GLAA firmware will be available soon.
[![IndoorBuild](https://img.youtube.com/vi/SdNEyDfTIKk/0.jpg)](https://www.youtube.com/watch?v=SdNEyDfTIKk)
[Watch on YouTube](https://www.youtube.com/watch?v=SdNEyDfTIKk)
Fork development, and PR development to development :)
#### [JUMP TO HOW TO USE](#how-to-use)
**Currently:** This will allow you to install or if already installed, update, remove, or modify:
- Simple Admin: A simple web interface for managing your Quectel m.2 modem through it's gateway address
- It will install socat-at-bridge: sets up ttyOUT and ttyOUT2 for AT commands. You'll be able to use the `atcmd` command as well for an interactive at command session from adb, ssh, or ttyd
- It will install simplefirewall: A simple firewall that blocks definable incoming ports and a TTL mangle option/modifier. As of now only the TTL is controllable through Simple Admin. You can edit port block options and TTL from the 3rd option in the toolkit
- Tailscale: A magic VPN for accessing Simple Admin, SSH, and ttyd on the go. The Toolkit installs the Tailscale client directly to the modem and allows you to login and configure other settings. Head over to tailscale.com to sign up for a free account and learn more.
- Schedule a Daily Reboot at a specified time
- A fix for certain modems that don't start in CFUN=1 mode
- Entware/OPKG: A package installer/manager/repo
- Run `opkg help` to see how to use it
- These packages are installable: https://bin.entware.net/armv7sf-k3.2/Packages.html
- TTYd: A shell session right from your browser
- Currently this uses port 443 but SSL/TLS is not in use (http only for now)
- Entware/OPKG is required so it will install it if it isn't installed
- This will replace the stock Quectel login and passwd binaries with ones from entware
# :warning: Known issues with Packages
Currently there is know vulnerability with QuecManager that allows cgi scripts to be executed unauthenticated. It is not recommended to expose uhttpd to the public internet, and to only used in a controlled, trusted local environment for now. Please see [Issue #175](https://github.com/iamromulan/quectel-rgmii-toolkit/issues/175) for more info.
# RC PCIe Toolkit
If you prefer starting from factory firmware you may use the toolkit script here to deploy my repo and other fixes via adb. It has been a while since I last visited this deployment script so open an issue if you see something wrong. See the wiki for info on adb.
**My goal** is for this to also include any new useful scripts or software for this modem and others that support RGMII mode.
## Screenshots
Software deployment Toolkit for Quectel RM5xxx series 5G modems utilizing an m.2 to RJ45 adapter (RC PCIe)
![Toolkit](https://github.com/iamromulan/quectel-rgmii-configuration-notes/blob/main/images/dev_toolkit.png?raw=true)
![Home](https://github.com/iamromulan/quectel-rgmii-configuration-notes/blob/main/images/dev_home.png?raw=true)
![Simple Network](https://github.com/iamromulan/quectel-rgmii-configuration-notes/blob/main/images/dev_simplenetwork.png?raw=true)
![Simple Scan](https://github.com/iamromulan/quectel-rgmii-configuration-notes/blob/main/images/dev_simplescan.png?raw=true)
![Simple Settings](https://github.com/iamromulan/quectel-rgmii-configuration-notes/blob/main/images/dev_simplesettings.png?raw=true)
![SMS](https://github.com/iamromulan/quectel-rgmii-configuration-notes/blob/main/images/dev_sms.png?raw=true)
![Console](https://github.com/iamromulan/quectel-rgmii-configuration-notes/blob/main/images/dev_console.png?raw=true)
![Device Info](https://github.com/iamromulan/quectel-rgmii-configuration-notes/blob/main/images/dev_deviceinfo.png?raw=true)
# The below commands will download the toolkit for RM55x modems/SDXPINN platform
# Current state:
The toolkit will do the following:
1. AT Commands
- Needs tested.
2. Install sdxpinn-mount-fix/run me after a flash!
- Installs sdxpinn-mount-fix so you can have a usable filesystem.
- You won't get far without this installed
3. TTL Setup
- Will allow you to set a TTL value
4. Install Basic Packages/enable luci/add iamromulan's feed to opkg
- Adds this repo as a source for opkg/software to get packages
- Installs the public key for this repo
- Installs a few basic packages: atinout luci-app-atinout-mod sdxpinn-console-menu shadow-login luci-app-ttyd mc mc-skins
- Starts and enables the SSH server and uhttpd web server (Luci)
5. Set root password
- Runs the passwd utility so you can set your password for root
6. Tailscale Management
- Will let you install tailscale
- Installs my updated ipks
- Will let you configure tailscale
- No web server yet
7. Install Speedtest.net CLI app (speedtest command)
- Will install the speedtest command (speedtest.net test)
- After install type speedtest to use it
# Devleopment Branch: the below commands will download the beta/work in progress toolkit
## How to Use
**To run the Toolkit:**
@@ -65,116 +48,95 @@ The toolkit will do the following:
- Run `adb shell ping 8.8.8.8` to make sure the shell can access the internet. If you get an error, make sure the modem is connected to a cellular network and make sure `AT+QMAPWAC=1` as covered in the troubleshooting section: [I Can't get internet access from the Ethernet port (Common)](https://github.com/iamromulan/quectel-rgmii-configuration-notes/tree/main?tab=readme-ov-file#i-cant-get-internet-access-from-the-ethernet-port-common)
- If you don't get an error you should be getting replies back endlessly, press `CTRL-C` to stop it.
- Simply Copy/Paste this into your Command Prompt/Shell
```bash
adb shell "cd /tmp && wget -O RMxxx_rgmii_toolkit.sh http://git.ievo.top/tyk/quectel-rgmii-toolkit/raw/branch/SDXLEMUR/RMxxx_rgmii_toolkit.sh && chmod +x RMxxx_rgmii_toolkit.sh && ./RMxxx_rgmii_toolkit.sh" && cd /
```
**Or, if you want to stay in the modems shell when you are done**
```
adb root
adb shell
```
Then run
```
cd /tmp && wget -O rcPCIe_SDXPINN_toolkit.sh https://raw.githubusercontent.com/iamromulan/quectel-rgmii-toolkit/SDXPINN/rcPCIe_SDXPINN_toolkit.sh && chmod +x rcPCIe_SDXPINN_toolkit.sh && ./rcPCIe_SDXPINN_toolkit.sh && cd /
cd /tmp && wget -O RMxxx_rgmii_toolkit.sh http://git.ievo.top/tyk/quectel-rgmii-toolkit/raw/branch/SDXLEMUR/RMxxx_rgmii_toolkit.sh && chmod +x RMxxx_rgmii_toolkit.sh && ./RMxxx_rgmii_toolkit.sh && cd /
```
**You should see:**
![Toolkit](https://github.com/iamromulan/quectel-rgmii-configuration-notes/blob/main/images/iamromulantoolkit.png?raw=true)
## Tailscale Installation and Config
> :warning: Your modem must already be connected to the internet for this to install
### Installation:
Open up the toolkit main menu and **press 4** to enter the Tailscale menu
![Toolkit](https://github.com/iamromulan/quectel-rgmii-configuration-notes/blob/main/images/tailscalemenu.png?raw=true)
**Press 1, wait for it to install. This is a very large file for the system so give it some time.**
**Once done and it says Tailscale installed successfully press 2/enter to configure it.**
![Toolkit](https://github.com/iamromulan/quectel-rgmii-configuration-notes/blob/main/images/tailscaleconfig.png?raw=true)
If you want to, enable the Tailscale Web UI on port 8088 for configuration from the browser later by **pressing 1/enter**.
To do it in the toolkit:
First time connecting you'll be given a link to login with
- Press 3 to just connect only.
- Press 4 to connect and enable SSH access (remote command line) over tailscale.
- Press 5 to reconnect with SSH off while connected with SSH on
- Press 6 to disconnect
- Press 7 to Logout
That's it! From another device running tailscale you should be able to access your modem through the IP assigned to it by your tailnet. To access SSH from another device on the tailnet, open a terminal/command prompt and type
tailscale ssh root@(IP or Hostname)
IP or Hostname being the IP or hostname assigned to it in your tailnet
- Note that your SSH client must be able to give you a link to sign in with upon connecting. That's how the session is authorized. Works fine in Windows CMD or on Android use JuiceSSH.
## Advanced/Beta
### Entware/OPKG installation
# Useful AT Commands
It isn't perfect yet so it goes here under Advanced/Beta for now.
Here's what you gotta know about going into it:
You can send more than one command at once by sperating them with ``;`` and not including the AT part. ``AT+QENG="servingcell";+QCAINFO`` for example to see the info from both ``AT+QENG="servingcell"`` and ``AT+QCAINFO``
- After installing, the `opkg` command will work
- You can run `opkg list` to see a list of installable packages, or head over to https://bin.entware.net/armv7sf-k3.2/Packages.html
- Everything opkg does is installed to /opt
- `/opt` is actually located at `/usrdata/opt` to save space but is
mounted at `/opt`
- Anything `opkg` installs will not be available in the system path by
default but you can get around this either:
#### Temporarily:
Run this at the start of each adb shell or SSH shell session
## PCIe RC Ethernet mode setup
export PATH=/opt/bin:/opt/sbin:$PATH
For use with a board like the [Rework.Network PoE 2.5gig RJ45 sled](https://rework.network/collections/lte-home-gateway/products/5g2phy)
#### Permanently:
Symbolic linking each binary installed by the package to `/bin` and `/sbin` from `/opt/bin` and `/opt/sbin`
For example, if you were to install zerotier:
### For x70 modems (RM550/551)
opkg install zerotier
ln -sf /opt/bin/zerotier-one /bin
ln -sf /opt/bin/zerotier-cli /bin
ln -sf /opt/bin/zerotier-idtool /bin
For BETA versions of firmware: the adb value 2 trick still works so one and done:
``AT+QCFG="pcie/mode",1;+QCFG="usbnet",1;+QCFG="usbcfg",0x2C7C,0x0122,1,1,1,1,1,2,0;+CFUN=1,1``
OR if you are running the latest non-beta firmware
``AT+QCFG="pcie/mode",1;+QCFG="usbnet",1``
Then unlock ADB:
Ask the modem for its adb code by sending: ``AT+QADBKEY?``
It'll respond with something like ``+QADBKEY: 29229988``
Take that number and paste it in this generator: https://onecompiler.com/python/3znepjcsq (hint: where it says STDIN)
You should get something like
``AT+QADBKEY="mrX4zOPwdSIEjfM"``
Send that command to the modem and adb will be able to be turned on with the next command
Now you can turn it on with the usbcfg command ``AT+QCFG="usbcfg"``
***Be super careful, this controls what ports are on/off over USB.***
Run it and you will get the current settings. Something like this:
``+QCFG: "usbcfg",0x2C7C,0x0122,1,1,1,1,1,0,0``
Send ``AT+QCFG="usbcfg",0x2C7C,0x0122,1,1,1,1,1,1,0`` to enable adb
Now you can reboot: ``AT+CFUN=1,1``
This will do the following:
- Enable PCIe RC mode (Driver selection is automatic now)
- Set to ECM mode via USB and AP mode connection behavior
- Force Enables ADB Access
- Reboots after all the above
Tip: APN automatic selection will somtimes choose the wrong APN. You may need to set your APN after powering up with the SIM inserted.
## The List
- ``AT+CFUN=1,1`` (reboot)
- ``AT+CFUN=0;CFUN=1`` (Disconnect then reconnect)(tip: run this after chnaging APN and you don't have to reboot)
- ``AT+QMAPWAC? ``(get current status of auto connect, 0=disabled 1=enabled)
- ``AT+QMAPWAC=1`` (enable auto connect internet for ethernet)
- ``AT+QMAPWAC=0`` (disable auto connect for ethernet; use when you want internet over USB to work; IPPT must be disabled)
- ``AT+QUIMSLOT?`` (get active sim slot; 1=Slot 1; 2=Slot 2)
- ``AT+QUIMSLOT=1`` (switch to sim slot 1)
- ``AT+QUIMSLOT=2`` (switch to sim slot 2)
- ``AT+CGDCONT?`` (Get active APN profle st 1 through 8)
- ``AT+QMBNCFG="AutoSel",0;+QMBNCFG="Deactivate"`` (Disable Automatic APN selection)(You will need to set your APN when you switch SIMs or Slots)(Can also set APN after you switch the run ``AT+CFUN=0;CFUN=1``
- ``AT+CGDCONT=1,"IPV4V6","APNHERE"`` (Sets APN profile 1 to APNHERE using both IPV4 and IPV6)
- ``AT+GSN`` (Show current IMEI)
- ``AT+EGMR=0,7`` (Show current IMEI)
- ``AT+EGMR=1,7,"IMEIGOESHERE"`` (sets/repairs IMEI)
- ``AT+QCFG="usbcfg",0x2C7C,0x0801,1,1,1,1,1,2,0`` (enables adb bypasses adb key)
- ``AT+QENG="servingcell"`` (shows anchor band and network connection status)
- ``AT+QCAINFO`` (Show all connected bands/CA info)
- ``AT+QNWPREFCFG="mode_pref"`` (Check what the current network search mode is set to)
- ``AT+QNWPREFCFG="mode_pref",AUTO`` (Set network search mode to automatic)
- ``AT+QNWPREFCFG="mode_pref",NR5G:LTE`` (Set network search mode to 5GNR and 4GLTE only)
- ``AT+QNWPREFCFG="mode_pref",NR5G`` (Set network search mode to 5GNR only)
- ``AT+QNWPREFCFG="mode_pref",LTE`` (Set network search mode to 4GLTE only)
- ``AT+QNWPREFCFG="nr5g_disable_mode"`` (Check to see if SA or NSA NR5G is disabled)
- ``AT+QNWPREFCFG="nr5g_disable_mode",0`` (Enable Both SA and NSA 5GNR)
- ``AT+QNWPREFCFG="nr5g_disable_mode",1`` (Disable SA 5GNR only)
- ``AT+QNWPREFCFG="nr5g_disable_mode",2`` (Disable NSA 5GNR only)
- ``AT+QNWPREFCFG="nr5g_band"`` (Get current SA 5GNR bandlock settings)
- ``AT+QNWPREFCFG="nsa_nr5g_band"`` (Get current NSA 5GNR bandlock settings)
- ``AT+QNWPREFCFG="nr5g_band",1:2:3:4:5:6`` (Example: Lock to SA 5G/NR bands n1,n2,n3,n4,n5, and n6)
- ``AT+QNWPREFCFG="nsa_nr5g_band",1:2:3:4:5:6`` (Example: Lock to SA 5G/NR bands n1,n2,n3,n4,n5, and n6)
- ``AT+QNWPREFCFG="lte_band"`` (Get current 4GLTE bandlock settings)
- ``AT+QNWPREFCFG="lte_band",1:2:3:4:5:6`` (Example: Lock to 4G/LTE bands 1,2,3,4,5, and 6)
- ``AT+QMAP="WWAN"`` (Show currently assigned IPv4 and IPv6 from the provider)
- ``AT+QMAP="LANIP"`` (Show current DHCP range and Gateway address for VLAN0)
- ``AT+QMAP="LANIP",IP_start_range,IP_end_range,Gateway_IP `` (Set IPv4 Start/End range and Gateway IP of DHCP for VLAN0)
- ``AT+QMAP="DHCPV4DNS","disable"`` (disable the onboard DNS proxy; recommended for IPPT)
- ``AT+QMAP="MPDN_rule",0,1,0,1,1,"FF:FF:FF:FF:FF:FF"``
(:warning: On the RM551E-GL you must specify the ethernet devices MAC address instead of FF:FF:FF...)
- ``AT+QMAP="MPDN_rule",0`` (turn off IPPT/clear MPDN rule 0; Remember to run AT+QMAPWAC=1 and reboot after)
Now you can run those 3 binaries from the shell anytime since they are linked in a place already part of the system path.
I plan to create a watchdog service for /opt/bin and /opt/sbin that will automaticly link new packages to /bin or /sbin later on in order to combat this.
### TTYd installation
It isn't perfect yet so it goes here under Advanced/Beta for now.
Here's what you gotta know about going into it:
- This listens on port 443 for http requests (no SSL/TLS yet)
- This will automaticly install entware and patch the login and passwd binaries with ones from entware
- It will ask you to set a password for the `root` user account
- TTYd doesn't seem to be too mobile friendly for now but I optimized it the best i could for now so it is at least usable through a smartphone browser. Hopefully the startup script can be improved even more later.
## Acknowledgements
### GitHub Users/Individuals:
@@ -186,12 +148,15 @@ Thank You to:
[rbflurry](https://github.com/rbflurry/) for inital Simple Admin fixes
[dr-dolomite](https://github.com/dr-dolomite) for simpleadmin 2.0 and QuecManager!
[dr-dolomite](https://github.com/dr-dolomite) for some major stat page improvements and this repos first approved external PR!
[tarunVreddy](https://github.com/tarunVreddy) for helping with the SA band aggregation parse
### Existing projects:
Simpleadmin heavily uses the AT Command Parsing Scripts (Basically a copy with new changes and tweaks) of Dairyman's Rooter Source https://github.com/ofmodemsandmen/ROOterSource2203
Tailscale was obtained through Tailscale's static build page. Since these modems have a 32-bit ARM processor on-board I used the arm package. https://pkgs.tailscale.com/stable/#static
Entware/opkg was obtained through [Entware's wiki](https://github.com/Entware/Entware/wiki/Alternative-install-vs-standard) and the installer heavily modified by [iamromulan](https://github.com/iamromulan) for use with Quectel modems
TTYd was obtained from the [TTYd Project](https://github.com/tsl0922/ttyd)

945
RMxxx_rgmii_toolkit.sh Normal file
View File

@@ -0,0 +1,945 @@
#!/bin/sh
# Define toolkit paths
export PATH=/bin:/sbin:/usr/bin:/usr/sbin:/opt/bin:/opt/sbin:/usrdata/root/bin
GITUSER="tyk"
REPONAME="quectel-rgmii-toolkit"
GITTREE="SDXLEMUR"
GITMAINTREE="SDXLEMUR"
GITDEVTREE="development-SDXLEMUR"
GITROOT="http://git.ievo.top/tyk/quectel-rgmii-toolkit/raw/branch/SDXLEMUR"
GITROOTMAIN="http://git.ievo.top/$GITUSER/$REPONAME/$GITMAINTREE"
GITROOTDEV="http://git.ievo.top/$GITUSER/$REPONAME/$GITDEVTREE"
TMP_DIR="/tmp"
USRDATA_DIR="/usrdata"
SOCAT_AT_DIR="/usrdata/socat-at-bridge"
SOCAT_AT_SYSD_DIR="/usrdata/socat-at-bridge/systemd_units"
SIMPLE_ADMIN_DIR="/usrdata/simpleadmin"
SIMPLE_FIREWALL_DIR="/usrdata/simplefirewall"
SIMPLE_FIREWALL_SCRIPT="$SIMPLE_FIREWALL_DIR/simplefirewall.sh"
SIMPLE_FIREWALL_SYSTEMD_DIR="$SIMPLE_FIREWALL_DIR/systemd"
TAILSCALE_DIR="/usrdata/tailscale"
TAILSCALE_SYSD_DIR="/usrdata/tailscale/systemd"
# AT Command Script Variables and Functions
DEVICE_FILE="/dev/smd7"
TIMEOUT=4 # Set a timeout for the response
# Function to remount file system as read-write
remount_rw() {
mount -o remount,rw /
}
# Function to remount file system as read-only
remount_ro() {
mount -o remount,ro /
}
# Basic AT commands without socat bridge for fast responce commands only
start_listening() {
cat "$DEVICE_FILE" > /tmp/device_readout &
CAT_PID=$!
}
send_at_command() {
echo -e "\e[1;31mThis only works for basic quick responding commands!\e[0m" # Red
echo -e "\e[1;36mType 'install' to simply type atcmd in shell from now on\e[0m"
echo -e "\e[1;36mThe installed version is much better than this portable version\e[0m"
echo -e "\e[1;32mEnter AT command (or type 'exit' to quit): \e[0m"
read at_command
if [ "$at_command" = "exit" ]; then
return 1
fi
if [ "$at_command" = "install" ]; then
install_update_at_socat
echo -e "\e[1;32mInstalled. Type atcmd from adb shell or ssh to start an AT Command session\e[0m"
return 1
fi
echo -e "${at_command}\r" > "$DEVICE_FILE"
}
wait_for_response() {
local start_time=$(date +%s)
local current_time
local elapsed_time
echo -e "\e[1;32mCommand sent, waiting for response...\e[0m"
while true; do
if grep -qe "OK" -e "ERROR" /tmp/device_readout; then
echo -e "\e[1;32mResponse received:\e[0m"
cat /tmp/device_readout
return 0
fi
current_time=$(date +%s)
elapsed_time=$((current_time - start_time))
if [ "$elapsed_time" -ge "$TIMEOUT" ]; then
echo -e "\e[1;31mError: Response timed out.\e[0m" # Red
echo -e "\e[1;32mIf the responce takes longer than a second or 2 to respond this will not work\e[0m" # Green
echo -e "\e[1;36mType install to install the better version of this that will work.\e[0m" # Cyan
return 1
fi
sleep 1
done
}
cleanup() {
kill "$CAT_PID"
wait "$CAT_PID" 2>/dev/null
rm -f /tmp/device_readout
}
send_at_commands() {
if [ -c "$DEVICE_FILE" ]; then
while true; do
start_listening
send_at_command
if [ $? -eq 1 ]; then
cleanup
break
fi
wait_for_response
cleanup
done
else
echo -e "\e[1;31mError: Device $DEVICE_FILE does not exist!\e[0m"
fi
}
# Check for existing Entware/opkg installation, install if not installed
ensure_entware_installed() {
remount_rw
if [ ! -f "/opt/bin/opkg" ]; then
echo -e "\e[1;32mInstalling Entware/OPKG\e[0m"
cd /tmp && wget -O installentware.sh "$GITROOT/installentware.sh" && chmod +x installentware.sh && ./installentware.sh
if [ "$?" -ne 0 ]; then
echo -e "\e[1;31mEntware/OPKG installation failed. Please check your internet connection or the repository URL.\e[0m"
exit 1
fi
cd /
else
echo -e "\e[1;32mEntware/OPKG is already installed.\e[0m"
if [ "$(readlink /bin/login)" != "/opt/bin/login" ]; then
opkg update && opkg install shadow-login shadow-passwd shadow-useradd
if [ "$?" -ne 0 ]; then
echo -e "\e[1;31mPackage installation failed. Please check your internet connection and try again.\e[0m"
exit 1
fi
# Replace the login and passwd binaries and set home for root to a writable directory
rm /opt/etc/shadow
rm /opt/etc/passwd
cp /etc/shadow /opt/etc/
cp /etc/passwd /opt/etc
mkdir -p /usrdata/root/bin
touch /usrdata/root/.profile
echo "# Set PATH for all shells" > /usrdata/root/.profile
echo "export PATH=/bin:/usr/sbin:/usr/bin:/sbin:/opt/sbin:/opt/bin:/usrdata/root/bin" >> /usrdata/root/.profile
chmod +x /usrdata/root/.profile
sed -i '1s|/home/root:/bin/sh|/usrdata/root:/bin/bash|' /opt/etc/passwd
rm /bin/login /usr/bin/passwd
ln -sf /opt/bin/login /bin
ln -sf /opt/bin/passwd /usr/bin/
ln -sf /opt/bin/useradd /usr/bin/
echo -e "\e[1;31mPlease set the root password.\e[0m"
/opt/bin/passwd
# Install basic and useful utilities
opkg install mc htop dfc lsof
ln -sf /opt/bin/mc /bin
ln -sf /opt/bin/htop /bin
ln -sf /opt/bin/dfc /bin
ln -sf /opt/bin/lsof /bin
fi
if [ ! -f "/usrdata/root/.profile" ]; then
opkg update && opkg install shadow-useradd
mkdir -p /usrdata/root/bin
touch /usrdata/root/.profile
echo "# Set PATH for all shells" > /usrdata/root/.profile
echo "export PATH=/bin:/usr/sbin:/usr/bin:/sbin:/opt/sbin:/opt/bin:/usrdata/root/bin" >> /usrdata/root/.profile
chmod +x /usrdata/root/.profile
sed -i '1s|/home/root:/bin/sh|/usrdata/root:/bin/bash|' /opt/etc/passwd
fi
fi
if [ ! -f "/opt/sbin/useradd" ]; then
echo "useradd does not exist. Installing shadow-useradd..."
opkg install shadow-useradd
else
echo "useradd already exists. Continuing..."
fi
if [ ! -f "/usr/bin/curl" ] && [ ! -f "/opt/bin/curl" ]; then
echo "curl does not exist. Installing curl..."
opkg update && opkg install curl
if [ "$?" -ne 0 ]; then
echo -e "\e[1;31mFailed to install curl. Please check your internet connection and try again.\e[0m"
exit 1
fi
else
echo "curl already exists. Continuing..."
fi
}
#Uninstall Entware if the Users chooses
uninstall_entware() {
echo -e '\033[31mInfo: Starting Entware/OPKG uninstallation...\033[0m'
# Stop services
systemctl stop rc.unslung.service
/opt/etc/init.d/rc.unslung stop
rm /lib/systemd/system/multi-user.target.wants/rc.unslung.service
rm /lib/systemd/system/rc.unslung.service
systemctl stop opt.mount
rm /lib/systemd/system/multi-user.target.wants/start-opt-mount.service
rm /lib/systemd/system/opt.mount
rm /lib/systemd/system/start-opt-mount.service
# Unmount /opt if mounted
mountpoint -q /opt && umount /opt
# Remove Entware installation directory
rm -rf /usrdata/opt
rm -rf /opt
# Reload systemctl daemon
systemctl daemon-reload
# Optionally, clean up any modifications to /etc/profile or other system files
# Restore original link to login binary compiled by Quectel
rm /bin/login
ln /bin/login.shadow /bin/login
echo -e '\033[32mInfo: Entware/OPKG has been uninstalled successfully.\033[0m'
}
# function to configure the fetures of simplefirewall
configure_simple_firewall() {
if [ ! -f "$SIMPLE_FIREWALL_SCRIPT" ]; then
echo -e "\033[0;31mSimplefirewall is not installed, would you like to install it?\033[0m"
echo -e "\033[0;32m1) Yes\033[0m"
echo -e "\033[0;31m2) No\033[0m"
read -p "Enter your choice (1-2): " install_choice
case $install_choice in
1)
install_simple_firewall
;;
2)
return
;;
*)
echo -e "\033[0;31mInvalid choice. Please select either 1 or 2.\033[0m"
;;
esac
fi
echo -e "\e[1;32mConfigure Simple Firewall:\e[0m"
echo -e "\e[38;5;208m1) Configure incoming port block\e[0m"
echo -e "\e[38;5;27m2) Configure TTL\e[0m"
read -p "Enter your choice (1-2): " menu_choice
case $menu_choice in
1)
# Original ports configuration code with exit option
current_ports_line=$(grep '^PORTS=' "$SIMPLE_FIREWALL_SCRIPT")
ports=$(echo "$current_ports_line" | cut -d'=' -f2 | tr -d '()' | tr ' ' '\n' | grep -o '[0-9]\+')
echo -e "\e[1;32mCurrent configured ports:\e[0m"
echo "$ports" | awk '{print NR") "$0}'
while true; do
echo -e "\e[1;32mEnter a port number to add/remove, or type 'done' or 'exit' to finish:\e[0m"
read port
if [ "$port" = "done" ] || [ "$port" = "exit" ]; then
if [ "$port" = "exit" ]; then
echo -e "\e[1;31mExiting without making changes...\e[0m"
return
fi
break
elif ! echo "$port" | grep -qE '^[0-9]+$'; then
echo -e "\e[1;31mInvalid input: Please enter a numeric value.\e[0m"
elif echo "$ports" | grep -q "^$port\$"; then
ports=$(echo "$ports" | grep -v "^$port\$")
echo -e "\e[1;32mPort $port removed.\e[0m"
else
ports=$(echo "$ports"; echo "$port" | grep -o '[0-9]\+')
echo -e "\e[1;32mPort $port added.\e[0m"
fi
done
if [ "$port" != "exit" ]; then
new_ports_line="PORTS=($(echo "$ports" | tr '\n' ' '))"
sed -i "s/$current_ports_line/$new_ports_line/" "$SIMPLE_FIREWALL_SCRIPT"
fi
;;
2)
# TTL configuration code
ttl_value=$(cat /usrdata/simplefirewall/ttlvalue)
if [ "$ttl_value" -eq 0 ]; then
echo -e "\e[1;31mTTL is not set.\e[0m"
else
echo -e "\e[1;32mTTL value is set to $ttl_value.\e[0m"
fi
echo -e "\e[1;31mType 'exit' to cancel.\e[0m"
read -p "What do you want the TTL value to be: " new_ttl_value
if [ "$new_ttl_value" = "exit" ]; then
echo -e "\e[1;31mExiting TTL configuration...\e[0m"
return
elif ! echo "$new_ttl_value" | grep -qE '^[0-9]+$'; then
echo -e "\e[1;31mInvalid input: Please enter a numeric value.\e[0m"
return
else
/usrdata/simplefirewall/ttl-override stop
echo "$new_ttl_value" > /usrdata/simplefirewall/ttlvalue
/usrdata/simplefirewall/ttl-override start
echo -e "\033[0;32mTTL value updated to $new_ttl_value.\033[0m"
fi
;;
*)
echo -e "\e[1;31mInvalid choice. Please select either 1 or 2.\e[0m"
;;
esac
systemctl restart simplefirewall
echo -e "\e[1;32mFirewall configuration updated.\e[0m"
}
set_simpleadmin_passwd(){
ensure_entware_installed
opkg update
opkg install libaprutil
wget -O /usrdata/root/bin/htpasswd $GITROOT/simpleadmin/htpasswd && chmod +x /usrdata/root/bin/htpasswd
wget -O /usrdata/root/bin/simplepasswd $GITROOT/simpleadmin/simplepasswd && chmod +x /usrdata/root/bin/simplepasswd
echo -e "\e[1;32mTo change your simpleadmin (admin) password in the future...\e[0m"
echo -e "\e[1;32mIn the console type simplepasswd and press enter\e[0m"
/usrdata/root/bin/simplepasswd
}
set_root_passwd() {
echo -e "\e[1;31mPlease set the root/console password.\e[0m"
/opt/bin/passwd
}
# Function to install/update Simple Admin
install_simple_admin() {
echo -e "\e[1;32mInstalling Simpleadmin 2.0\e[0m"
ensure_entware_installed
echo -e "\e[1;31m2) Installing Simpleadmin 2.0\e[0m"
mkdir /usrdata/simpleupdates > /dev/null 2>&1
mkdir /usrdata/simpleupdates/scripts > /dev/null 2>&1
wget -O /usrdata/simpleupdates/scripts/update_socat-at-bridge.sh $GITROOT/simpleupdates/scripts/update_socat-at-bridge.sh && chmod +x /usrdata/simpleupdates/scripts/update_socat-at-bridge.sh
echo -e "\e[1;32mInstalling/updating dependency: socat-at-bridge\e[0m"
echo -e "\e[1;32mPlease Wait....\e[0m"
/usrdata/simpleupdates/scripts/update_socat-at-bridge.sh
echo -e "\e[1;32m Dependency: socat-at-bridge has been updated/installed.\e[0m"
sleep 1
wget -O /usrdata/simpleupdates/scripts/update_simplefirewall.sh $GITROOT/simpleupdates/scripts/update_simplefirewall.sh && chmod +x /usrdata/simpleupdates/scripts/update_simplefirewall.sh
echo -e "\e[1;32mInstalling/updating dependency: simplefirewall\e[0m"
echo -e "\e[1;32mPlease Wait....\e[0m"
/usrdata/simpleupdates/scripts/update_simplefirewall.sh
echo -e "\e[1;32m Dependency: simplefirewall has been updated/installed.\e[0m"
sleep 1
set_simpleadmin_passwd
wget -O /usrdata/simpleupdates/scripts/update_simpleadmin.sh $GITROOT/simpleupdates/scripts/update_simpleadmin.sh && chmod +x /usrdata/simpleupdates/scripts/update_simpleadmin.sh
echo -e "\e[1;32mInstalling/updating: Simpleadmin content\e[0m"
echo -e "\e[1;32mPlease Wait....\e[0m"
/usrdata/simpleupdates/scripts/update_simpleadmin.sh
echo -e "\e[1;32mSimpleadmin content has been updated/installed.\e[0m"
sleep 1
break
}
# Function to Uninstall Simpleadmin and dependencies
uninstall_simpleadmin_components() {
echo -e "\e[1;32mStarting the uninstallation process for Simpleadmin components.\e[0m"
echo -e "\e[1;32mNote: Uninstalling certain components may affect the functionality of others.\e[0m"
remount_rw
# Uninstall Simple Firewall
echo -e "\e[1;32mDo you want to uninstall Simplefirewall?\e[0m"
echo -e "\e[1;31mIf you do, the TTL part of simpleadmin will no longer work.\e[0m"
echo -e "\e[1;32m1) Yes\e[0m"
echo -e "\e[1;31m2) No\e[0m"
read -p "Enter your choice (1 or 2): " choice_simplefirewall
if [ "$choice_simplefirewall" -eq 1 ]; then
echo "Uninstalling Simplefirewall..."
systemctl stop simplefirewall
systemctl stop ttl-override
rm -f /lib/systemd/system/simplefirewall.service
rm -f /lib/systemd/system/ttl-override.service
systemctl daemon-reload
rm -rf "$SIMPLE_FIREWALL_DIR"
echo "Simplefirewall uninstalled."
fi
# Uninstall socat-at-bridge
echo -e "\e[1;32mDo you want to uninstall socat-at-bridge?\e[0m"
echo -e "\e[1;31mIf you do, AT commands and the stat page will no longer work. atcmd won't either.\e[0m"
echo -e "\e[1;32m1) Yes\e[0m"
echo -e "\e[1;31m2) No\e[0m"
read -p "Enter your choice (1 or 2): " choice_socat_at_bridge
if [ "$choice_socat_at_bridge" -eq 1 ]; then
echo -e "\033[0;32mRemoving installed AT Socat Bridge services...\033[0m"
systemctl stop at-telnet-daemon > /dev/null 2>&1
systemctl disable at-telnet-daemon > /dev/null 2>&1
systemctl stop socat-smd11 > /dev/null 2>&1
systemctl stop socat-smd11-to-ttyIN > /dev/null 2>&1
systemctl stop socat-smd11-from-ttyIN > /dev/null 2>&1
systemctl stop socat-smd7 > /dev/null 2>&1
systemctl stop socat-smd7-to-ttyIN2 > /dev/null 2>&1
systemctl stop socat-smd7-to-ttyIN > /dev/null 2>&1
systemctl stop socat-smd7-from-ttyIN2 > /dev/null 2>&1
systemctl stop socat-smd7-from-ttyIN > /dev/null 2>&1
rm /lib/systemd/system/at-telnet-daemon.service > /dev/null 2>&1
rm /lib/systemd/system/socat-smd11.service > /dev/null 2>&1
rm /lib/systemd/system/socat-smd11-to-ttyIN.service > /dev/null 2>&1
rm /lib/systemd/system/socat-smd11-from-ttyIN.service > /dev/null 2>&1
rm /lib/systemd/system/socat-smd7.service > /dev/null 2>&1
rm /lib/systemd/system/socat-smd7-to-ttyIN2.service > /dev/null 2>&1
rm /lib/systemd/system/socat-smd7-to-ttyIN.service > /dev/null 2>&1
rm /lib/systemd/system/socat-smd7-from-ttyIN.service > /dev/null 2>&1
rm /lib/systemd/system/socat-smd7-from-ttyIN2.service > /dev/null 2>&1
systemctl daemon-reload > /dev/null 2>&1
rm -rf "$SOCAT_AT_DIR" > /dev/null 2>&1
rm -rf "$SOCAT_AT_DIR" > /dev/null 2>&1
rm -rf "/usrdata/micropython" > /dev/null 2>&1
rm -rf "/usrdata/at-telnet" > /dev/null 2>&1
echo -e "\033[0;32mAT Socat Bridge services removed!...\033[0m"
fi
# Uninstall ttyd
echo -e "\e[1;32mDo you want to uninstall ttyd (simpleadmin console)?\e[0m"
echo -e "\e[1;31mWarning: Do not uninstall if you are currently using ttyd to do this!!!\e[0m"
echo -e "\e[1;32m1) Yes\e[0m"
echo -e "\e[1;31m2) No\e[0m"
read -p "Enter your choice (1 or 2): " choice_simpleadmin
if [ "$choice_simpleadmin" -eq 1 ]; then
echo -e "\e[1;34mUninstalling ttyd...\e[0m"
systemctl stop ttyd
rm -rf /usrdata/ttyd
rm /lib/systemd/system/ttyd.service
rm /lib/systemd/system/multi-user.target.wants/ttyd.service
rm /bin/ttyd
echo -e "\e[1;32mttyd has been uninstalled.\e[0m"
fi
echo "Uninstalling the rest of Simpleadmin..."
# Check if Lighttpd service is installed and remove it if present
if [ -f "/lib/systemd/system/lighttpd.service" ]; then
echo "Lighttpd detected, uninstalling Lighttpd and its modules..."
systemctl stop lighttpd
opkg --force-remove --force-removal-of-dependent-packages remove lighttpd-mod-authn_file lighttpd-mod-auth lighttpd-mod-cgi lighttpd-mod-openssl lighttpd-mod-proxy lighttpd
rm -rf $LIGHTTPD_DIR
fi
systemctl stop simpleadmin_generate_status
systemctl stop simpleadmin_httpd
rm -f /lib/systemd/system/simpleadmin_httpd.service
rm -f /lib/systemd/system/simpleadmin_generate_status.service
systemctl daemon-reload
rm -rf "$SIMPLE_ADMIN_DIR"
echo "The rest of Simpleadmin and Lighttpd (if present) uninstalled."
remount_ro
echo "Uninstallation process completed."
}
# Function for Tailscale Submenu
tailscale_menu() {
while true; do
echo -e "\e[1;32mTailscale Menu\e[0m"
echo -e "\e[1;32m1) Install/Update Tailscale\e[0m"
echo -e "\e[1;36m2) Configure Tailscale\e[0m"
echo -e "\e[1;31m3) Return to Main Menu\e[0m"
read -p "Enter your choice: " tailscale_choice
case $tailscale_choice in
1) install_update_tailscale;;
2) configure_tailscale;;
3) break;;
*) echo "Invalid option";;
esac
done
}
# Function to install, update, or remove Tailscale
install_update_tailscale() {
echo -e "\e[1;31m2) Installing tailscale from the $GITTREE branch\e[0m"
ensure_entware_installed
mkdir /usrdata/simpleupdates > /dev/null 2>&1
mkdir /usrdata/simpleupdates/scripts > /dev/null 2>&1
wget -O /usrdata/simpleupdates/scripts/update_tailscale.sh $GITROOT/simpleupdates/scripts/update_tailscale.sh && chmod +x /usrdata/simpleupdates/scripts/update_tailscale.sh
echo -e "\e[1;32mInstalling/updating: Tailscale\e[0m"
echo -e "\e[1;32mPlease Wait....\e[0m"
remount_rw
/usrdata/simpleupdates/scripts/update_tailscale.sh
echo -e "\e[1;32m Tailscale has been updated/installed.\e[0m"
}
# Function to Configure Tailscale
configure_tailscale() {
while true; do
echo "Configure Tailscale"
echo -e "\e[38;5;40m1) Enable Tailscale Web UI at http://192.168.225.1:8088 (Gateway on port 8088)\e[0m" # Green
echo -e "\e[38;5;196m2) Disable Tailscale Web UI\e[0m" # Red
echo -e "\e[38;5;27m3) Connect to Tailnet\e[0m" # Brown
echo -e "\e[38;5;87m4) Connect to Tailnet with SSH ON\e[0m" # Light cyan
echo -e "\e[38;5;105m5) Reconnect to Tailnet with SSH OFF\e[0m" # Light magenta
echo -e "\e[38;5;172m6) Disconnect from Tailnet (reconnects at reboot)\e[0m" # Light yellow
echo -e "\e[1;31m7) Logout from tailscale account\e[0m"
echo -e "\e[38;5;27m8) Return to Tailscale Menu\e[0m"
read -p "Enter your choice: " config_choice
case $config_choice in
1)
remount_rw
cd /lib/systemd/system/
wget -O tailscale-webui.service $GITROOT/tailscale/systemd/tailscale-webui.service
wget -O tailscale-webui-trigger.service $GITROOT/tailscale/systemd/tailscale-webui-trigger.service
ln -sf /lib/systemd/system/tailscale-webui-trigger.service /lib/systemd/system/multi-user.target.wants/
systemctl daemon-reload
echo "Tailscale Web UI Enabled"
echo "Starting Web UI..."
systemctl start tailscale-webui
echo "Web UI started!"
remount_ro
;;
2)
remount_rw
systemctl stop tailscale-webui
systemctl disable tailscale-webui-trigger
rm /lib/systemd/system/multi-user.target.wants/tailscale-webui.service
rm /lib/systemd/system/multi-user.target.wants/tailscale-webui-trigger.service
rm /lib/systemd/system/tailscale-webui.service
rm /lib/systemd/system/tailscale-webui-trigger.service
systemctl daemon-reload
echo "Tailscale Web UI Stopped and Disabled"
remount_ro
;;
3) $TAILSCALE_DIR/tailscale up --accept-dns=false --reset;;
4) $TAILSCALE_DIR/tailscale up --ssh --accept-dns=false --reset;;
5) $TAILSCALE_DIR/tailscale up --accept-dns=false --reset;;
6) $TAILSCALE_DIR/tailscale down;;
7) $TAILSCALE_DIR/tailscale logout;;
8) break;;
*) echo "Invalid option";;
esac
done
}
# Function to manage Daily Reboot Timer
manage_reboot_timer() {
# Remount root filesystem as read-write
mount -o remount,rw /
# Check if the rebootmodem service, timer, or trigger already exists
if [ -f /lib/systemd/system/rebootmodem.service ] || [ -f /lib/systemd/system/rebootmodem.timer ] || [ -f /lib/systemd/system/rebootmodem-trigger.service ]; then
echo -e "\e[1;32mThe rebootmodem service/timer/trigger is already installed.\e[0m"
echo -e "\e[1;32m1) Change\e[0m" # Green
echo -e "\e[1;31m2) Remove\e[0m" # Red
read -p "Enter your choice (1 for Change, 2 for Remove): " reboot_choice
case $reboot_choice in
2)
# Stop and disable timer and trigger service by removing symlinks
systemctl stop rebootmodem.timer
systemctl stop rebootmodem-trigger.service
# Remove symbolic links and files
rm -f /lib/systemd/system/multi-user.target.wants/rebootmodem-trigger.service
rm -f /lib/systemd/system/rebootmodem.service
rm -f /lib/systemd/system/rebootmodem.timer
rm -f /lib/systemd/system/rebootmodem-trigger.service
rm -f "$USRDATA_DIR/reboot_modem.sh"
# Reload systemd to apply changes
systemctl daemon-reload
echo -e "\e[1;32mRebootmodem service, timer, trigger, and script removed successfully.\e[0m"
;;
1)
printf "Enter the new time for daily reboot (24-hour format in Coordinated Universal Time, HH:MM): "
read new_time
# Validate the new time format using grep
if ! echo "$new_time" | grep -qE '^([01]?[0-9]|2[0-3]):[0-5][0-9]$'; then
echo "Invalid time format. Exiting."
exit 1
else
# Remove old symlinks and script
rm -f /lib/systemd/system/multi-user.target.wants/rebootmodem-trigger.service
rm -f "$USRDATA_DIR/reboot_modem.sh"
# Set the user time to the new time and recreate the service, timer, trigger, and script
user_time=$new_time
create_service_and_timer
fi
;;
*)
echo -e "\e[1;31mInvalid choice. Exiting.\e[0m"
exit 1
;;
esac
else
printf "Enter the time for daily reboot (24-hour format in UTC, HH:MM): "
read user_time
# Validate the time format using grep
if ! echo "$user_time" | grep -qE '^([01]?[0-9]|2[0-3]):[0-5][0-9]$'; then
echo "Invalid time format. Exiting."
exit 1
else
create_service_and_timer
fi
fi
# Remount root filesystem as read-only
mount -o remount,ro /
}
# Function to create systemd service and timer files with the user-specified time for the reboot timer
create_service_and_timer() {
remount_rw
# Define the path for the modem reboot script
MODEM_REBOOT_SCRIPT="$USRDATA_DIR/reboot_modem.sh"
# Create the modem reboot script
echo "#!/bin/sh
/bin/echo -e 'AT+CFUN=1,1 \r' > /dev/smd7" > "$MODEM_REBOOT_SCRIPT"
# Make the script executable
chmod +x "$MODEM_REBOOT_SCRIPT"
# Create the systemd service file for reboot
echo "[Unit]
Description=Reboot Modem Daily
[Service]
Type=oneshot
ExecStart=/bin/sh /usrdata/reboot_modem.sh
Restart=no
RemainAfterExit=no" > /lib/systemd/system/rebootmodem.service
# Create the systemd timer file with the user-specified time
echo "[Unit]
Description=Starts rebootmodem.service daily at the specified time
[Timer]
OnCalendar=*-*-* $user_time:00
Persistent=false" > /lib/systemd/system/rebootmodem.timer
# Create a trigger service that starts the timer at boot
echo "[Unit]
Description=Trigger the rebootmodem timer at boot
[Service]
Type=oneshot
ExecStart=/bin/systemctl start rebootmodem.timer
RemainAfterExit=yes" > /lib/systemd/system/rebootmodem-trigger.service
# Create symbolic links for the trigger service in the wanted directory
ln -sf /lib/systemd/system/rebootmodem-trigger.service /lib/systemd/system/multi-user.target.wants/
# Reload systemd to recognize the new timer and trigger service
systemctl daemon-reload
sleep 2s
# Start the trigger service, which will start the timer
systemctl start rebootmodem-trigger.service
remount_ro
# Confirmation
echo -e "\e[1;32mRebootmodem-trigger service created and started successfully.\e[0m"
echo -e "\e[1;32mReboot schedule set successfully. The modem will reboot daily at $user_time UTC.\e[0m"
}
manage_cfun_fix() {
cfun_service_path="/lib/systemd/system/cfunfix.service"
cfun_fix_script="/usrdata/cfun_fix.sh"
mount -o remount,rw /
if [ -f "$cfun_service_path" ]; then
echo -e "\e[1;32mThe CFUN fix is already installed. Do you want to remove it?\e[0m" # Green
echo -e "\e[1;32m1) Yes\e[0m" # Green
echo -e "\e[1;31m2) No\e[0m" # Red
read -p "Enter your choice: " choice
if [ "$choice" = "1" ]; then
echo "Removing CFUN fix..."
systemctl stop cfunfix.service
rm -f /lib/systemd/system/multi-user.target.wants/cfunfix.service
rm -f "$cfun_service_path"
rm -f "$cfun_fix_script"
systemctl daemon-reload
echo "CFUN fix has been removed."
else
echo "Returning to main menu..."
fi
else
echo -e "\e[1;32mInstalling CFUN fix...\e[0m"
# Create the CFUN fix script
echo "#!/bin/sh
/bin/echo -e 'AT+CFUN=1 \r' > /dev/smd7" > "$cfun_fix_script"
chmod +x "$cfun_fix_script"
# Create the systemd service file to execute the CFUN fix script at boot
echo "[Unit]
Description=CFUN Fix Service
After=network.target
[Service]
Type=oneshot
ExecStart=$cfun_fix_script
RemainAfterExit=yes
[Install]
WantedBy=multi-user.target" > "$cfun_service_path"
ln -sf "$cfun_service_path" "/lib/systemd/system/multi-user.target.wants/"
systemctl daemon-reload
mount -o remount,ro /
echo -e "\e[1;32mCFUN fix has been installed and will execute at every boot.\e[0m"
fi
}
install_sshd() {
if [ -d "/usrdata/sshd" ]; then
echo -e "\e[1;31mSSHD is currently installed.\e[0m"
echo -e "Do you want to update or uninstall?"
echo -e "1.) Update"
echo -e "2.) Uninstall"
read -p "Select an option (1 or 2): " sshd_choice
case $sshd_choice in
1)
echo -e "\e[1;31m2) Installing sshd from the $GITTREE branch\e[0m"
;;
2)
echo -e "\e[1;31mUninstalling SSHD...\e[0m"
systemctl stop sshd
rm /lib/systemd/system/sshd.service
opkg remove openssh-server-pam
echo -e "\e[1;32mSSHD has been uninstalled successfully.\e[0m"
return 0
;;
*)
echo -e "\e[1;31mInvalid option. Please select 1 or 2.\e[0m"
return 1
;;
esac
fi
# Proceed with installation or updating if not uninstalling
ensure_entware_installed
mkdir /usrdata/simpleupdates > /dev/null 2>&1
mkdir /usrdata/simpleupdates/scripts > /dev/null 2>&1
wget -O /usrdata/simpleupdates/scripts/update_sshd.sh $GITROOT/simpleupdates/scripts/update_sshd.sh && chmod +x /usrdata/simpleupdates/scripts/update_sshd.sh
echo -e "\e[1;32mInstalling/updating: SSHd\e[0m"
echo -e "\e[1;32mPlease Wait....\e[0m"
/usrdata/simpleupdates/scripts/update_sshd.sh
echo -e "\e[1;32m SSHd has been updated/installed.\e[0m"
}
# Main menu
ARCH=$(uname -a)
if echo "$ARCH" | grep -q "aarch64"; then
cd /tmp && wget -O RM55x_rcPCIe_toolkit.sh http://git.ievo.top/iamromulan/quectel-rgmii-toolkit/SDXPINN/RM55x_rcPCIe_toolkit.sh && chmod +x RM55x_rcPCIe_toolkit.sh && ./RM55x_rcPCIe_toolkit.sh && cd /
exit 0
elif echo "$ARCH" | grep -q "armv7l"; then
# Continue if architecture is armv7l
echo "Architecture is armv7l, continuing..."
else
uname -a
echo "Unsupported architecture."
exit 1
fi
while true; do
echo " .%+: "
echo " .*@@@-. "
echo " :@@@@- "
echo " @@@@#. "
echo " -@@@@#. "
echo " :. %@@@@: -# "
echo " .+- #@@@@%.+@- "
echo " .#- . +@@@@# #@- "
echo " -@*@*@% @@@@@::@@= "
echo ".+%@@@@@@@@@%=. =@@@@# #@@- .. "
echo " .@@@@@: :@@@@@ =@@@..%= "
echo " -::@-.+. @@@@@.=@@@- =@- "
echo " .@- .@@@@@:.@@@* @@. "
echo " .%- -@@@@@:=@@@@ @@# "
echo " .#- .%@@@@@@#. +@@@@@.#@@@@ @@@."
echo " .*- .@@@@@@@@@@=. @@@@@@ @@@@@ @@@:"
echo " :. .%@@@@@@@@@@@%. .@@@@@+:@@@@@ @@@-"
echo " -@@@@@@@@@@@@@@@..@@@@@@.-@@@@@ .@@@-"
echo " -@@@@@@@@@@%. .@@@@@@. @@@@@+ =@@@="
echo " =@@@@@@@@* .@@@@@@. @@@@@@..@@@@-"
echo " #@@@@@@@@-*@@@@@%..@@@@@@+ #@@@@-"
echo " @@@@@@:.-@@@@@@. @@@@@@= %@@@@@."
echo " .@@@@. *@@@@@@- .+@@@@@@-.@@@@@@+ "
echo " %@@. =@@@@@*. +@@@@@@%.-@@@@@@% "
echo " .@@ .@@@@@= :@@@@@@@@..@@@@@@@= "
echo " =@.+@@@@@. -@@@@@@@*.:@@@@@@@*. "
echo " %.*@@@@= .@@@@@@@-.:@@@@@@@+. "
echo " ..@@@@= .@@@@@@: #@@@@@@@: "
echo " .@@@@ +@@@@..%@@@@@+. "
echo " .@@@. @@@@.:@@@@+. "
echo " @@@. @@@. @@@* .@. "
echo " :@@@ %@@..@@#. *@ "
echo " -*: .@@* :@@. @@. -..@@ "
echo " =@@@@@@.*@- :@% @* =@:=@# "
echo " .@@@-+@@@@:%@..%- ...@%:@@: "
echo " .@@. @@-%@: .%@@*@@%. "
echo " :@@ :+ *@ *@@#*@@@. "
echo " =@@@.@@@@ "
echo " .*@@@:=@@@@: "
echo " .@@@@:.@@@@@: "
echo " .@@@@#.-@@@@@. "
echo " #@@@@: =@@@@@- "
echo " .@@@@@..@@@@@@* "
echo " -@@@@@. @@@@@@#. "
echo " -@@@@@ @@@@@@% "
echo " @@@@@. #@@@@@@. "
echo " :@@@@# =@@@@@@% "
echo " @@@@@: @@@@@@@: "
echo " *@@@@ @@@@@@@. "
echo " .@@@@ @@@@@@@ "
echo " #@@@. @@@@@@* "
echo " @@@# @@@@@@@ "
echo " .@@+=@@@@@@. "
echo " *@@@@@@ "
echo " :@@@@@= "
echo " .@@@@@@. "
echo " :@@@@@*. "
echo " .=@@@@@- "
echo " :+##+. "
echo -e "\e[92m"
echo "Welcome to iamromulan's RGMII Toolkit script for Quectel RMxxx Series modems!"
echo "Visit https://github.com/iamromulan for more!"
echo -e "\e[0m"
echo "Select an option:"
echo -e "\e[0m"
echo -e "\e[96m1) Send AT Commands\e[0m" # Cyan
echo -e "\e[93m2) Install Simple Admin\e[0m" # Yellow
echo -e "\e[95m3) Set Simpleadmin (admin) password\e[0m" # Light Purple
echo -e "\e[94m4) Set Console/ttyd (root) password\e[0m" # Light Blue
echo -e "\e[91m5) Uninstall Simple Admin\e[0m" # Light Red
echo -e "\e[95m6) Simple Firewall Management\e[0m" # Light Purple
echo -e "\e[94m7) Tailscale Management\e[0m" # Light Blue
echo -e "\e[92m8) Install/Change or remove Daily Reboot Timer\e[0m" # Light Green
echo -e "\e[96m9) Install/Uninstall CFUN 0 Fix\e[0m" # Cyan (repeated color for additional options)
echo -e "\e[91m10) Uninstall Entware/OPKG\e[0m" # Light Red
echo -e "\e[92m11) Install Speedtest.net CLI app (speedtest command)\e[0m" # Light Green
echo -e "\e[92m12) Install Fast.com CLI app (fast command)(tops out at 40Mbps)\e[0m" # Light Green
echo -e "\e[92m13) Install OpenSSH Server\e[0m" # Light Green
echo -e "\e[93m14) Exit\e[0m" # Yellow (repeated color for exit option)
read -p "Enter your choice: " choice
case $choice in
1)
send_at_commands
;;
2)
install_simple_admin
;;
3) set_simpleadmin_passwd
;;
4)
set_root_passwd
;;
5)
uninstall_simpleadmin_components
;;
6)
configure_simple_firewall
;;
7)
tailscale_menu
;;
8)
manage_reboot_timer
;;
9)
manage_cfun_fix
;;
10)
echo -e "\033[31mAre you sure you want to uninstall entware?\033[0m"
echo -e "\033[31m1) Yes\033[0m"
echo -e "\033[31m2) No\033[0m"
read -p "Select an option (1 or 2): " user_choice
case $user_choice in
1)
# If yes, uninstall existing entware
echo -e "\033[31mUninstalling existing entware...\033[0m"
uninstall_entware # Assuming uninstall_entware is a defined function or command
echo -e "\033[31mEntware has been uninstalled.\033[0m"
;;
2)
# If no, exit the script
echo -e "\033[31mUninstallation cancelled.\033[0m"
exit # Use 'exit' to terminate the script outside a loop
;;
*)
# Handle invalid input
echo -e "\033[31mInvalid option. Please select 1 or 2.\033[0m"
;;
esac
;;
11)
ensure_entware_installed
echo -e "\e[1;32mInstalling Speedtest.net CLI (speedtest command)\e[0m"
remount_rw
mkdir /usrdata/root
mkdir /usrdata/root/bin
cd /usrdata/root/bin
wget https://install.speedtest.net/app/cli/ookla-speedtest-1.2.0-linux-armhf.tgz
tar -xzf ookla-speedtest-1.2.0-linux-armhf.tgz
rm ookla-speedtest-1.2.0-linux-armhf.tgz
rm speedtest.md
cd /
ln -sf /usrdata/root/bin/speedtest /bin
remount_ro
echo -e "\e[1;32mSpeedtest CLI (speedtest command) installed!!\e[0m"
echo -e "\e[1;32mTry running the command 'speedtest'\e[0m"
echo -e "\e[1;32mNote that it will not work unless you login to the root account first\e[0m"
echo -e "\e[1;32mNormaly only an issue in adb, ttyd and ssh you are forced to login\e[0m"
echo -e "\e[1;32mIf in adb just type login and then try to run the speedtest command\e[0m"
;;
12)
echo -e "\e[1;32mInstalling fast.com CLI (fast command)\e[0m"
remount_rw
mkdir /usrdata/root
mkdir /usrdata/root/bin
cd /usrdata/root/bin
wget -O fast https://github.com/ddo/fast/releases/download/v0.0.4/fast_linux_arm && chmod +x fast
cd /
ln -sf /usrdata/root/bin/fast /bin
remount_ro
echo -e "\e[1;32mFast.com CLI (speedtest command) installed!!\e[0m"
echo -e "\e[1;32mTry running the command 'fast'\e[0m"
echo -e "\e[1;32mThe fast.com test tops out at 40Mbps on the modem\e[0m"
;;
13)
install_sshd
;;
14)
echo -e "\e[1;32mGoodbye!\e[0m"
break
;;
*)
echo -e "\e[1;31mInvalid option\e[0m"
;;
esac
done

109
at-list.md Normal file
View File

@@ -0,0 +1,109 @@
# Useful AT Commands
You can send more than one command at once by sperating them with ``;`` and not including the AT part. ``AT+QENG="servingcell";+QCAINFO`` for example to see the info from both ``AT+QENG="servingcell"`` and ``AT+QCAINFO``
## PCIe RC Ethernet mode setup
### For RM500-RM521 modems
``AT+QETH="eth_driver","r8125",1;+QCFG="pcie/mode",1;+QCFG="usbnet",1;+QMAP="MPDN_rule",0,1,0,1,1,"FF:FF:FF:FF:FF:FF";+QMAP="DHCPV4DNS","disable";+QCFG="usbcfg",0x2C7C,0x0801,1,1,1,1,1,2,0;+CFUN=1,1``
This will do the following:
- Set the 2.5Gig Ethernet driver as active
- Enable PCIe RC mode
- Set to ECM mode via USB and AP mode connection behavior
- Enable IPPT
- Enable DNS IPPT (disables onboard proxy)
- Force Enables ADB Access
- Reboots after all the above
### For x70 modems (RM550/551)
For BETA versions of firmware: the adb value 2 trick still works so one and done:
``AT+QCFG="pcie/mode",1;+QCFG="usbnet",1;+QCFG="usbcfg",0x2C7C,0x0122,1,1,1,1,1,2,0;+CFUN=1,1``
OR if you are running the latest non-beta firmware
``AT+QCFG="pcie/mode",1;+QCFG="usbnet",1``
Then unlock ADB:
Ask the modem for its adb code by sending: ``AT+QADBKEY?``
It'll respond with something like ``+QADBKEY: 29229988``
Take that number and paste it in this generator: https://onecompiler.com/python/3znepjcsq (hint: where it says STDIN)
You should get something like
``AT+QADBKEY="mrX4zOPwdSIEjfM"``
Send that command to the modem and adb will be able to be turned on with the next command
Now you can turn it on with the usbcfg command ``AT+QCFG="usbcfg"``
***Be super careful, this controls what ports are on/off over USB.***
Run it and you will get the current settings. Something like this:
``+QCFG: "usbcfg",0x2C7C,0x0122,1,1,1,1,1,0,0``
Send ``AT+QCFG="usbcfg",0x2C7C,0x0122,1,1,1,1,1,1,0`` to enable adb
Now you can reboot: ``AT+CFUN=1,1``
This will do the following:
- Enable PCIe RC mode (Driver selection is automatic now)
- Set to ECM mode via USB and AP mode connection behavior
- Force Enables ADB Access
- Reboots after all the above
Tip: APN automatic selection will somtimes choose the wrong APN. You may need to set your APN after powering up with the SIM inserted.
## The List
- ``AT+CFUN=1,1`` (reboot)
- ``AT+CFUN=0;CFUN=1`` (Disconnect then reconnect)(tip: run this after chnaging APN and you don't have to reboot)
- ``AT+QMAPWAC? ``(get current status of auto connect, 0=disabled 1=enabled)
- ``AT+QMAPWAC=1`` (enable auto connect internet for ethernet)
- ``AT+QMAPWAC=0`` (disable auto connect for ethernet; use when you want internet over USB to work; IPPT must be disabled)
- ``AT+QUIMSLOT?`` (get active sim slot; 1=Slot 1; 2=Slot 2)
- ``AT+QUIMSLOT=1`` (switch to sim slot 1)
- ``AT+QUIMSLOT=2`` (switch to sim slot 2)
- ``AT+CGDCONT?`` (Get active APN profle st 1 through 8)
- ``AT+QMBNCFG="AutoSel",0;+QMBNCFG="Deactivate"`` (Disable Automatic APN selection)(You will need to set your APN when you switch SIMs or Slots)(Can also set APN after you switch the run ``AT+CFUN=0;CFUN=1``
- ``AT+CGDCONT=1,"IPV4V6","APNHERE"`` (Sets APN profile 1 to APNHERE using both IPV4 and IPV6)
- ``AT+GSN`` (Show current IMEI)
- ``AT+EGMR=0,7`` (Show current IMEI)
- ``AT+EGMR=1,7,"IMEIGOESHERE"`` (sets/repairs IMEI)
- ``AT+QCFG="usbcfg",0x2C7C,0x0801,1,1,1,1,1,2,0`` (enables adb bypasses adb key)
- ``AT+QENG="servingcell"`` (shows anchor band and network connection status)
- ``AT+QCAINFO`` (Show all connected bands/CA info)
- ``AT+QNWPREFCFG="mode_pref"`` (Check what the current network search mode is set to)
- ``AT+QNWPREFCFG="mode_pref",AUTO`` (Set network search mode to automatic)
- ``AT+QNWPREFCFG="mode_pref",NR5G:LTE`` (Set network search mode to 5GNR and 4GLTE only)
- ``AT+QNWPREFCFG="mode_pref",NR5G`` (Set network search mode to 5GNR only)
- ``AT+QNWPREFCFG="mode_pref",LTE`` (Set network search mode to 4GLTE only)
- ``AT+QNWPREFCFG="nr5g_disable_mode"`` (Check to see if SA or NSA NR5G is disabled)
- ``AT+QNWPREFCFG="nr5g_disable_mode",0`` (Enable Both SA and NSA 5GNR)
- ``AT+QNWPREFCFG="nr5g_disable_mode",1`` (Disable SA 5GNR only)
- ``AT+QNWPREFCFG="nr5g_disable_mode",2`` (Disable NSA 5GNR only)
- ``AT+QNWPREFCFG="nr5g_band"`` (Get current SA 5GNR bandlock settings)
- ``AT+QNWPREFCFG="nsa_nr5g_band"`` (Get current NSA 5GNR bandlock settings)
- ``AT+QNWPREFCFG="nr5g_band",1:2:3:4:5:6`` (Example: Lock to SA 5G/NR bands n1,n2,n3,n4,n5, and n6)
- ``AT+QNWPREFCFG="nsa_nr5g_band",1:2:3:4:5:6`` (Example: Lock to SA 5G/NR bands n1,n2,n3,n4,n5, and n6)
- ``AT+QNWPREFCFG="lte_band"`` (Get current 4GLTE bandlock settings)
- ``AT+QNWPREFCFG="lte_band",1:2:3:4:5:6`` (Example: Lock to 4G/LTE bands 1,2,3,4,5, and 6)
- ``AT+QMAP="WWAN"`` (Show currently assigned IPv4 and IPv6 from the provider)
- ``AT+QMAP="LANIP"`` (Show current DHCP range and Gateway address for VLAN0)
- ``AT+QMAP="LANIP",IP_start_range,IP_end_range,Gateway_IP `` (Set IPv4 Start/End range and Gateway IP of DHCP for VLAN0)
- ``AT+QMAP="DHCPV4DNS","disable"`` (disable the onboard DNS proxy; recommended for IPPT)
- ``AT+QMAP="MPDN_rule",0,1,0,1,1,"FF:FF:FF:FF:FF:FF"`` (Turn on IP Passthrough for Ethernet)
(:warning: On the RM551E-GL you must specify the ethernet devices MAC address instead of FF:FF:FF...)
- ``AT+QMAP="MPDN_rule",0`` (turn off IPPT/clear MPDN rule 0; Remember to run AT+QMAPWAC=1 and reboot after)

View File

@@ -1,6 +0,0 @@
Package: sdxpinn-firstboot
Version: 1.0
Architecture: sdxpinn
Maintainer: Cameron Thompson iamromulan@github.com
Source: github.com/iamromulan
Description: A first boot init after a flash or factory reset

View File

@@ -1,5 +0,0 @@
#!/bin/ash
service first-boot enable
exit 0

View File

@@ -1,74 +0,0 @@
#!/bin/sh
# Script for building OpenWRT .ipk packages using tar by iamromulan
# Works with SDXPPINN OpenWRT - iamromulan
# This script accepts an optional path to the directory containing the `CONTROL` and `root` directories.
# Usage: ./build-ipk.sh [path]
# If no path is provided, the script will look in the current directory for `CONTROL` and `root` directories.
# This will spit out an ipk in the current directory
# Check if the script is run as root. If not, rerun with sudo.
if [ "$(id -u)" -ne 0 ]; then
echo "Script is not running as root. Re-executing with sudo..."
exec sudo "$0" "$@"
fi
# Set the default build path to the current directory
build_path="."
# Check if a path is provided as the first argument
if [ "$1" ]; then
build_path="$1"
fi
# Check if the required directories are present in the specified path
if [ ! -d "${build_path}/CONTROL" ] || [ ! -d "${build_path}/root" ]; then
echo "Error: CONTROL and root directories must be present in the specified path (${build_path})."
exit 1
fi
# Extract values from the CONTROL/control file in the specified path
pkgname=$(grep -i '^Package:' "${build_path}/CONTROL/control" | awk '{print $2}')
version=$(grep -i '^Version:' "${build_path}/CONTROL/control" | awk '{print $2}')
architecture=$(grep -i '^Architecture:' "${build_path}/CONTROL/control" | awk '{print $2}')
# Check if values are extracted correctly
if [ -z "$pkgname" ] || [ -z "$version" ] || [ -z "$architecture" ]; then
echo "Error: Failed to extract Package, Version, or Architecture from ${build_path}/CONTROL/control."
exit 1
fi
# Set the final IPK name based on the extracted values
ipkname="${pkgname}_${version}_${architecture}.ipk"
# Ensure all CONTROL scripts are executable
echo "Setting permissions for CONTROL scripts..."
chmod +x "${build_path}/CONTROL"/*
# Set ownership for CONTROL and root files
echo "Setting ownership for all package files..."
chown -R root:root "${build_path}/CONTROL"/*
chown -R root:root "${build_path}/root"/*
# Create control.tar.gz from the CONTROL directory
echo "Creating control.tar.gz..."
tar -czvf control.tar.gz -C "${build_path}/CONTROL" .
# Create data.tar.gz from the root directory
echo "Creating data.tar.gz..."
tar -czvf data.tar.gz -C "${build_path}/root" .
# Create debian-binary file (must contain exactly "2.0" without a newline)
echo -n "2.0" > debian-binary
chown -R root:root debian-binary
# Combine the components into the final .ipk file using tar
echo "Packaging ${ipkname}..."
tar -czvf "$ipkname" debian-binary control.tar.gz data.tar.gz
# Clean up intermediate files
echo "Cleaning up temporary files..."
rm -f control.tar.gz data.tar.gz debian-binary
echo "IPK package ${ipkname} created successfully using tar."

View File

@@ -1,31 +0,0 @@
#!/bin/sh /etc/rc.common
START=99
STOP=15
USE_PROCD=1
start_service() {
# Create log file
touch /usrdata/first-boot.log
# Redirect all output to log file
exec >>/usrdata/first-boot.log 2>&1
echo "Starting first boot script: $(date)"
echo "Remounting the real rootfs as rw"
mount -o remount,rw /real_rootfs
echo "Sending AT Commands"
atcmd 'AT+QCFG="usbnet",1'
atcmd 'AT+QCFG="pcie/mode",1'
echo "Disabling first-boot service"
service first-boot disable
echo "Restarting modem"
atcmd 'AT+CFUN=1,1'
echo "Removing first-boot service"
rm /real_rootfs/etc/init.d/first-boot
echo "First boot script completed: $(date)"
}

View File

@@ -1,6 +0,0 @@
Package: sdxpinn-patch
Version: 2.5
Architecture: all
Maintainer: Cameron Thompson iamromulan@github.com
Source: github.com/iamromulan
Description: A general first system patch for SDXPINN OpenWRT

View File

@@ -1,5 +0,0 @@
#!/bin/ash
echo "Complete"
exit 0

View File

@@ -1,211 +0,0 @@
#!/bin/ash
clean_distfeeds() {
# Define the list of items to comment out
items_to_comment=$(cat <<EOF
src/gz openwrt_core https://downloads.openwrt.org/releases/22.03.5/targets/sdx75/generic/packages
src/gz openwrt_qtiagm https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qtiagm
src/gz openwrt_qtiargs https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qtiargs
src/gz openwrt_qtiaudio https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qtiaudio
src/gz openwrt_qtiaudioprop https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qtiaudioprop
src/gz openwrt_qtibsp https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qtibsp
src/gz openwrt_qtibspprop https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qtibspprop
src/gz openwrt_qtibt https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qtibt
src/gz openwrt_qtibtprop https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qtibtprop
src/gz openwrt_qticore https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qticore
src/gz openwrt_qticoreinternal https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qticoreinternal
src/gz openwrt_qticoreprop https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qticoreprop
src/gz openwrt_qtictainternal https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qtictainternal
src/gz openwrt_qtidata https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qtidata
src/gz openwrt_qtidatainternal https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qtidatainternal
src/gz openwrt_qtidataprop https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qtidataprop
src/gz openwrt_qtiipq https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qtiipq
src/gz openwrt_qtiipqezmesh https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qtiipqezmesh
src/gz openwrt_qtiipqprop https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qtiipqprop
src/gz openwrt_qtilocation https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qtilocation
src/gz openwrt_qtilocationinternal https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qtilocationinternal
src/gz openwrt_qtilocationprop https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qtilocationprop
src/gz openwrt_qtimsdcprop https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qtimsdcprop
src/gz openwrt_qtinternal https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qtinternal
src/gz openwrt_qtipal https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qtipal
src/gz openwrt_qtiperfprop https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qtiperfprop
src/gz openwrt_qtippatprop https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qtippatprop
src/gz openwrt_qtiquectel https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qtiquectel
src/gz openwrt_qtiquectelprop https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qtiquectelprop
src/gz openwrt_qtirilprop https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qtirilprop
src/gz openwrt_qtisecurity https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qtisecurity
src/gz openwrt_qtisecurityinternal https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qtisecurityinternal
src/gz openwrt_qtisecurityprop https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qtisecurityprop
src/gz openwrt_qtisensorsinternal https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qtisensorsinternal
src/gz openwrt_qtisensorsprop https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qtisensorsprop
src/gz openwrt_qtissdk https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qtissdk
src/gz openwrt_qtissmgr https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qtissmgr
src/gz openwrt_qtissmgrprop https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qtissmgrprop
src/gz openwrt_qtiwlan https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qtiwlan
src/gz openwrt_qtiwlanprop https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/qtiwlanprop
EOF
)
# Define the list of items to ensure are uncommented
items_to_keep=$(cat <<EOF
src/gz openwrt_base https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/base
src/gz openwrt_luci https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/luci
src/gz openwrt_packages https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/packages
src/gz openwrt_routing https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/routing
src/gz openwrt_telephony https://downloads.openwrt.org/releases/22.03.5/packages/aarch64_cortex-a53/telephony/
EOF
)
# Input file to process
INPUT_FILE="/etc/opkg/distfeeds.conf"
# Backup the original file
cp "$INPUT_FILE" "${INPUT_FILE}.bak"
# Create a temporary file for the modified content
TEMP_FILE="${INPUT_FILE}.tmp"
: > "$TEMP_FILE" # Clear/create the temp file
# Process each line in the input file
while IFS= read -r line || [ -n "$line" ]; do
# Skip empty lines
[ -z "$line" ] && continue
# Skip malformed lines
echo "$line" | grep -qE '^(#[[:space:]]*)?src/gz ' || continue
# Remove any existing comment marks for comparison
clean_line=$(echo "$line" | sed 's/^#[[:space:]]*//')
# Check if line should be commented
if echo "$items_to_comment" | grep -Fxq "$clean_line"; then
echo "# $clean_line" >> "$TEMP_FILE"
continue
fi
# Check if line should be kept uncommented
if echo "$items_to_keep" | grep -Fxq "$clean_line"; then
echo "$clean_line" >> "$TEMP_FILE"
continue
fi
# Preserve other lines as-is
echo "$line" >> "$TEMP_FILE"
done < "$INPUT_FILE"
# Add any missing items_to_keep entries
echo "$items_to_keep" | while IFS= read -r keep_item; do
[ -z "$keep_item" ] && continue
if ! grep -Fxq "$keep_item" "$TEMP_FILE"; then
echo "$keep_item" >> "$TEMP_FILE"
fi
done
# Replace the original file with the modified one
mv "$TEMP_FILE" "$INPUT_FILE"
echo "Processed '$INPUT_FILE'. Backup saved as '${INPUT_FILE}.bak'."
}
repo_iamromulanSDXPINN_check() {
# Define the repository and key details
STABLE_REPO_LINE="src/gz iamromulan-SDXPINN-repo https://raw.githubusercontent.com/iamromulan/quectel-rgmii-toolkit/SDXPINN/opkg-feed"
DEV_REPO_LINE="src/gz iamromulan-SDXPINN-repo https://raw.githubusercontent.com/iamromulan/quectel-rgmii-toolkit/development-SDXPINN/opkg-feed"
FEEDS_FILE="/etc/opkg/customfeeds.conf"
PUBLIC_KEY_URL="https://raw.githubusercontent.com/iamromulan/quectel-rgmii-toolkit/SDXPINN/opkg-feed/iamromulan-SDXPINN-repo.key"
TMP_KEY="/tmp/iamromulan-SDXPINN-repo.key"
KEYS_DIR="/etc/opkg/keys"
# Remove duplicate and development repo lines
if grep -q "iamromulan-SDXPINN-repo" "$FEEDS_FILE"; then
echo "Cleaning up duplicate or development repo entries in $FEEDS_FILE."
sed -i "/iamromulan-SDXPINN-repo/d" "$FEEDS_FILE"
fi
# Add the stable repository to customfeeds.conf
echo "Adding stable repository to $FEEDS_FILE."
echo "$STABLE_REPO_LINE" >> "$FEEDS_FILE" || {
echo "Error: Could not add repository to $FEEDS_FILE."
return 1
}
# Download the key temporarily for verification
curl -fsSL "$PUBLIC_KEY_URL" -o "$TMP_KEY" || {
echo "Error: Failed to download public key from $PUBLIC_KEY_URL."
return 1
}
# Check if the key already exists in /etc/opkg/keys/
local key_installed=0
for key in "$KEYS_DIR"/*; do
if cmp -s "$TMP_KEY" "$key"; then
echo "Public key already installed: $(basename "$key")."
key_installed=1
break
fi
done
# If the key is not installed, add it
if [ "$key_installed" -eq 0 ]; then
echo "Installing public key..."
opkg-key add "$TMP_KEY" || {
echo "Error: Failed to add public key."
rm -f "$TMP_KEY"
return 1
}
echo "Public key installed successfully."
fi
# Clean up temporary key file
rm -f "$TMP_KEY"
return 0
}
noprerm_mount_fix() {
if [ -f /real_rootfs/usr/lib/opkg/info/sdxpinn-mount-fix.prerm ]; then
mount -o remount,rw /real_rootfs
sleep 1
rm /real_rootfs/usr/lib/opkg/info/sdxpinn-mount-fix.prerm
sleep 1
mount -o remount,ro /real_rootfs
fi
if [ -f /usr/lib/opkg/info/sdxpinn-mount-fix.prerm ]; then
rm /usr/lib/opkg/info/sdxpinn-mount-fix.prerm
fi
}
opkg_arch_patch() {
if [ ! -f /etc/opkg/arch.conf ]; then
cat > /etc/opkg/arch.conf << 'EOF'
arch all 1
arch noarch 1
arch sdxpinn 2
arch aarch64_cortex-a53 10
arch aarch64_generic 20
EOF
else
for arch in "all 1" "noarch 1" "sdxpinn 2" "aarch64_cortex-a53 10" "aarch64_generic 20"; do
if ! grep -q "^arch $arch$" /etc/opkg/arch.conf; then
echo "arch $arch" >> /etc/opkg/arch.conf
fi
done
fi
}
# Begin Patch Process
echo -e "\e[92mBegining sdxpinn-patch process...\e[0m"
echo -e "\e[92mEnsuring distfeeds is clean of any non-working sources and has stock OpenWRT ones...\e[0m"
clean_distfeeds
echo -e "\e[92mEnsuring iamromulan's SDXPINN repo is listed in customfeeds and public key is installed...\e[0m"
repo_iamromulanSDXPINN_check
echo -e "\e[92miamromulan's SDXPINN repo source and key is installed.\e[0m"
echo -e "\e[92mEnsuring mount-fix does not have a prerm\e[0m"
noprerm_mount_fix
echo -e "\e[92mEnsuring opkg reconizes needed archs\e[0m"
opkg_arch_patch
echo -e "\e[92msdxpinn-patch process complete.\e[0m"
exit 0

View File

@@ -1,5 +0,0 @@
#!/bin/ash
echo -e "\e[38;5;196mINFO: This package can not be removed by opkg\e[0m"
echo -e "\e[38;5;40mINFO: This package can be upgraded...\e[0m"
exit 0

View File

@@ -1,74 +0,0 @@
#!/bin/sh
# Script for building OpenWRT .ipk packages using tar by iamromulan
# Works with SDXPPINN OpenWRT - iamromulan
# This script accepts an optional path to the directory containing the `CONTROL` and `root` directories.
# Usage: ./build-ipk.sh [path]
# If no path is provided, the script will look in the current directory for `CONTROL` and `root` directories.
# This will spit out an ipk in the current directory
# Check if the script is run as root. If not, rerun with sudo.
if [ "$(id -u)" -ne 0 ]; then
echo "Script is not running as root. Re-executing with sudo..."
exec sudo "$0" "$@"
fi
# Set the default build path to the current directory
build_path="."
# Check if a path is provided as the first argument
if [ "$1" ]; then
build_path="$1"
fi
# Check if the required directories are present in the specified path
if [ ! -d "${build_path}/CONTROL" ] || [ ! -d "${build_path}/root" ]; then
echo "Error: CONTROL and root directories must be present in the specified path (${build_path})."
exit 1
fi
# Extract values from the CONTROL/control file in the specified path
pkgname=$(grep -i '^Package:' "${build_path}/CONTROL/control" | awk '{print $2}')
version=$(grep -i '^Version:' "${build_path}/CONTROL/control" | awk '{print $2}')
architecture=$(grep -i '^Architecture:' "${build_path}/CONTROL/control" | awk '{print $2}')
# Check if values are extracted correctly
if [ -z "$pkgname" ] || [ -z "$version" ] || [ -z "$architecture" ]; then
echo "Error: Failed to extract Package, Version, or Architecture from ${build_path}/CONTROL/control."
exit 1
fi
# Set the final IPK name based on the extracted values
ipkname="${pkgname}_${version}_${architecture}.ipk"
# Ensure all CONTROL scripts are executable
echo "Setting permissions for CONTROL scripts..."
chmod +x "${build_path}/CONTROL"/*
# Set ownership for CONTROL and root files
echo "Setting ownership for all package files..."
chown -R root:root "${build_path}/CONTROL"/*
chown -R root:root "${build_path}/root"/*
# Create control.tar.gz from the CONTROL directory
echo "Creating control.tar.gz..."
tar -czvf control.tar.gz -C "${build_path}/CONTROL" .
# Create data.tar.gz from the root directory
echo "Creating data.tar.gz..."
tar -czvf data.tar.gz -C "${build_path}/root" .
# Create debian-binary file (must contain exactly "2.0" without a newline)
echo -n "2.0" > debian-binary
chown -R root:root debian-binary
# Combine the components into the final .ipk file using tar
echo "Packaging ${ipkname}..."
tar -czvf "$ipkname" debian-binary control.tar.gz data.tar.gz
# Clean up intermediate files
echo "Cleaning up temporary files..."
rm -f control.tar.gz data.tar.gz debian-binary
echo "IPK package ${ipkname} created successfully using tar."

View File

@@ -1,6 +0,0 @@
Package: sdxpinn-firstboot
Version: 1.0
Architecture: sdxpinn
Maintainer: Cameron Thompson iamromulan@github.com
Source: github.com/iamromulan
Description: A first boot init after a flash or factory reset

View File

@@ -1,5 +0,0 @@
#!/bin/ash
service first-boot enable
exit 0

View File

@@ -1,74 +0,0 @@
#!/bin/sh
# Script for building OpenWRT .ipk packages using tar by iamromulan
# Works with SDXPPINN OpenWRT - iamromulan
# This script accepts an optional path to the directory containing the `CONTROL` and `root` directories.
# Usage: ./build-ipk.sh [path]
# If no path is provided, the script will look in the current directory for `CONTROL` and `root` directories.
# This will spit out an ipk in the current directory
# Check if the script is run as root. If not, rerun with sudo.
if [ "$(id -u)" -ne 0 ]; then
echo "Script is not running as root. Re-executing with sudo..."
exec sudo "$0" "$@"
fi
# Set the default build path to the current directory
build_path="."
# Check if a path is provided as the first argument
if [ "$1" ]; then
build_path="$1"
fi
# Check if the required directories are present in the specified path
if [ ! -d "${build_path}/CONTROL" ] || [ ! -d "${build_path}/root" ]; then
echo "Error: CONTROL and root directories must be present in the specified path (${build_path})."
exit 1
fi
# Extract values from the CONTROL/control file in the specified path
pkgname=$(grep -i '^Package:' "${build_path}/CONTROL/control" | awk '{print $2}')
version=$(grep -i '^Version:' "${build_path}/CONTROL/control" | awk '{print $2}')
architecture=$(grep -i '^Architecture:' "${build_path}/CONTROL/control" | awk '{print $2}')
# Check if values are extracted correctly
if [ -z "$pkgname" ] || [ -z "$version" ] || [ -z "$architecture" ]; then
echo "Error: Failed to extract Package, Version, or Architecture from ${build_path}/CONTROL/control."
exit 1
fi
# Set the final IPK name based on the extracted values
ipkname="${pkgname}_${version}_${architecture}.ipk"
# Ensure all CONTROL scripts are executable
echo "Setting permissions for CONTROL scripts..."
chmod +x "${build_path}/CONTROL"/*
# Set ownership for CONTROL and root files
echo "Setting ownership for all package files..."
chown -R root:root "${build_path}/CONTROL"/*
chown -R root:root "${build_path}/root"/*
# Create control.tar.gz from the CONTROL directory
echo "Creating control.tar.gz..."
tar -czvf control.tar.gz -C "${build_path}/CONTROL" .
# Create data.tar.gz from the root directory
echo "Creating data.tar.gz..."
tar -czvf data.tar.gz -C "${build_path}/root" .
# Create debian-binary file (must contain exactly "2.0" without a newline)
echo -n "2.0" > debian-binary
chown -R root:root debian-binary
# Combine the components into the final .ipk file using tar
echo "Packaging ${ipkname}..."
tar -czvf "$ipkname" debian-binary control.tar.gz data.tar.gz
# Clean up intermediate files
echo "Cleaning up temporary files..."
rm -f control.tar.gz data.tar.gz debian-binary
echo "IPK package ${ipkname} created successfully using tar."

View File

@@ -1,31 +0,0 @@
#!/bin/sh /etc/rc.common
START=99
STOP=15
USE_PROCD=1
start_service() {
# Create log file
touch /usrdata/first-boot.log
# Redirect all output to log file
exec >>/usrdata/first-boot.log 2>&1
echo "Starting first boot script: $(date)"
echo "Remounting the real rootfs as rw"
mount -o remount,rw /real_rootfs
echo "Sending AT Commands"
atcmd 'AT+QCFG="usbnet",1'
atcmd 'AT+QCFG="pcie/mode",1'
echo "Disabling first-boot service"
service first-boot disable
echo "Restarting modem"
atcmd 'AT+CFUN=1,1'
echo "Removing first-boot service"
rm /real_rootfs/etc/init.d/first-boot
echo "First boot script completed: $(date)"
}

View File

@@ -1,6 +0,0 @@
Package: sdxpinn-patch
Version: 2.5
Architecture: all
Maintainer: Cameron Thompson iamromulan@github.com
Source: github.com/iamromulan
Description: A general first system patch for SDXPINN OpenWRT

View File

@@ -1,5 +0,0 @@
#!/bin/ash
echo "Complete"
exit 0

View File

@@ -1,213 +0,0 @@
#!/bin/ash
clean_distfeeds() {
# Define the list of items to comment out
items_to_comment=$(cat <<EOF
src/gz openwrt_core https://downloads.openwrt.org/releases/23.05.4/targets/sdx75/generic/packages
src/gz openwrt_qtiagm https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtiagm
src/gz openwrt_qtiargs https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtiargs
src/gz openwrt_qtiaudio https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtiaudio
src/gz openwrt_qtiaudioprop https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtiaudioprop
src/gz openwrt_qtibsp https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtibsp
src/gz openwrt_qtibspprop https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtibspprop
src/gz openwrt_qtibt https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtibt
src/gz openwrt_qtibtprop https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtibtprop
src/gz openwrt_qticore https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qticore
src/gz openwrt_qticoreinternal https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qticoreinternal
src/gz openwrt_qticoreprop https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qticoreprop
src/gz openwrt_qtictainternal https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtictainternal
src/gz openwrt_qtidata https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtidata
src/gz openwrt_qtidatainternal https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtidatainternal
src/gz openwrt_qtidataprop https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtidataprop
src/gz openwrt_qtiemergencyalertprop https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtiemergencyalertprop
src/gz openwrt_qtigplv2 https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtigplv2
src/gz openwrt_qtiipq https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtiipq
src/gz openwrt_qtiipqezmesh https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtiipqezmesh
src/gz openwrt_qtiipqprop https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtiipqprop
src/gz openwrt_qtilocation https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtilocation
src/gz openwrt_qtilocationinternal https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtilocationinternal
src/gz openwrt_qtilocationprop https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtilocationprop
src/gz openwrt_qtimsdcprop https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtimsdcprop
src/gz openwrt_qtinternal https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtinternal
src/gz openwrt_qtipal https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtipal
src/gz openwrt_qtiperfprop https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtiperfprop
src/gz openwrt_qtippatprop https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtippatprop
src/gz openwrt_qtiquectel https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtiquectel
src/gz openwrt_qtiquectelprop https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtiquectelprop
src/gz openwrt_qtirilprop https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtirilprop
src/gz openwrt_qtisecurity https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtisecurity
src/gz openwrt_qtisecurityinternal https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtisecurityinternal
src/gz openwrt_qtisecurityprop https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtisecurityprop
src/gz openwrt_qtisensorsinternal https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtisensorsinternal
src/gz openwrt_qtisensorsprop https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtisensorsprop
src/gz openwrt_qtissdk https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtissdk
src/gz openwrt_qtissmgr https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtissmgr
src/gz openwrt_qtissmgrprop https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtissmgrprop
src/gz openwrt_qtiwlan https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtiwlan
src/gz openwrt_qtiwlanprop https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/qtiwlanprop
EOF
)
# Define the list of items to ensure are uncommented
items_to_keep=$(cat <<EOF
src/gz openwrt_base https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/base
src/gz openwrt_luci https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/luci
src/gz openwrt_packages https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/packages
src/gz openwrt_routing https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/routing
src/gz openwrt_routing https://downloads.openwrt.org/releases/23.05.4/packages/aarch64_cortex-a53/telephony
EOF
)
# Input file to process
INPUT_FILE="/etc/opkg/distfeeds.conf"
# Backup the original file
cp "$INPUT_FILE" "${INPUT_FILE}.bak"
# Create a temporary file for the modified content
TEMP_FILE="${INPUT_FILE}.tmp"
: > "$TEMP_FILE" # Clear/create the temp file
# Process each line in the input file
while IFS= read -r line || [ -n "$line" ]; do
# Skip empty lines
[ -z "$line" ] && continue
# Skip malformed lines
echo "$line" | grep -qE '^(#[[:space:]]*)?src/gz ' || continue
# Remove any existing comment marks for comparison
clean_line=$(echo "$line" | sed 's/^#[[:space:]]*//')
# Check if line should be commented
if echo "$items_to_comment" | grep -Fxq "$clean_line"; then
echo "# $clean_line" >> "$TEMP_FILE"
continue
fi
# Check if line should be kept uncommented
if echo "$items_to_keep" | grep -Fxq "$clean_line"; then
echo "$clean_line" >> "$TEMP_FILE"
continue
fi
# Preserve other lines as-is
echo "$line" >> "$TEMP_FILE"
done < "$INPUT_FILE"
# Add any missing items_to_keep entries
echo "$items_to_keep" | while IFS= read -r keep_item; do
[ -z "$keep_item" ] && continue
if ! grep -Fxq "$keep_item" "$TEMP_FILE"; then
echo "$keep_item" >> "$TEMP_FILE"
fi
done
# Replace the original file with the modified one
mv "$TEMP_FILE" "$INPUT_FILE"
echo "Processed '$INPUT_FILE'. Backup saved as '${INPUT_FILE}.bak'."
}
repo_iamromulanSDXPINN_check() {
# Define the repository and key details
STABLE_REPO_LINE="src/gz iamromulan-SDXPINN-repo https://raw.githubusercontent.com/iamromulan/quectel-rgmii-toolkit/SDXPINN/opkg-feed"
DEV_REPO_LINE="src/gz iamromulan-SDXPINN-repo https://raw.githubusercontent.com/iamromulan/quectel-rgmii-toolkit/development-SDXPINN/opkg-feed"
FEEDS_FILE="/etc/opkg/customfeeds.conf"
PUBLIC_KEY_URL="https://raw.githubusercontent.com/iamromulan/quectel-rgmii-toolkit/SDXPINN/opkg-feed/iamromulan-SDXPINN-repo.key"
TMP_KEY="/tmp/iamromulan-SDXPINN-repo.key"
KEYS_DIR="/etc/opkg/keys"
# Remove duplicate and development repo lines
if grep -q "iamromulan-SDXPINN-repo" "$FEEDS_FILE"; then
echo "Cleaning up duplicate or development repo entries in $FEEDS_FILE."
sed -i "/iamromulan-SDXPINN-repo/d" "$FEEDS_FILE"
fi
# Add the stable repository to customfeeds.conf
echo "Adding stable repository to $FEEDS_FILE."
echo "$STABLE_REPO_LINE" >> "$FEEDS_FILE" || {
echo "Error: Could not add repository to $FEEDS_FILE."
return 1
}
# Download the key temporarily for verification
curl -fsSL "$PUBLIC_KEY_URL" -o "$TMP_KEY" || {
echo "Error: Failed to download public key from $PUBLIC_KEY_URL."
return 1
}
# Check if the key already exists in /etc/opkg/keys/
local key_installed=0
for key in "$KEYS_DIR"/*; do
if cmp -s "$TMP_KEY" "$key"; then
echo "Public key already installed: $(basename "$key")."
key_installed=1
break
fi
done
# If the key is not installed, add it
if [ "$key_installed" -eq 0 ]; then
echo "Installing public key..."
opkg-key add "$TMP_KEY" || {
echo "Error: Failed to add public key."
rm -f "$TMP_KEY"
return 1
}
echo "Public key installed successfully."
fi
# Clean up temporary key file
rm -f "$TMP_KEY"
return 0
}
noprerm_mount_fix() {
if [ -f /real_rootfs/usr/lib/opkg/info/sdxpinn-mount-fix.prerm ]; then
mount -o remount,rw /real_rootfs
sleep 1
rm /real_rootfs/usr/lib/opkg/info/sdxpinn-mount-fix.prerm
sleep 1
mount -o remount,ro /real_rootfs
fi
if [ -f /usr/lib/opkg/info/sdxpinn-mount-fix.prerm ]; then
rm /usr/lib/opkg/info/sdxpinn-mount-fix.prerm
fi
}
opkg_arch_patch() {
if [ ! -f /etc/opkg/arch.conf ]; then
cat > /etc/opkg/arch.conf << 'EOF'
arch all 1
arch noarch 1
arch sdxpinn 2
arch aarch64_cortex-a53 10
arch aarch64_generic 20
EOF
else
for arch in "all 1" "noarch 1" "sdxpinn 2" "aarch64_cortex-a53 10" "aarch64_generic 20"; do
if ! grep -q "^arch $arch$" /etc/opkg/arch.conf; then
echo "arch $arch" >> /etc/opkg/arch.conf
fi
done
fi
}
# Begin Patch Process
echo -e "\e[92mBegining sdxpinn-patch process...\e[0m"
echo -e "\e[92mEnsuring distfeeds is clean of any non-working sources and has stock OpenWRT ones...\e[0m"
clean_distfeeds
echo -e "\e[92mEnsuring iamromulan's SDXPINN repo is listed in customfeeds and public key is installed...\e[0m"
repo_iamromulanSDXPINN_check
echo -e "\e[92miamromulan's SDXPINN repo source and key is installed.\e[0m"
echo -e "\e[92mEnsuring mount-fix does not have a prerm\e[0m"
noprerm_mount_fix
echo -e "\e[92mEnsuring opkg reconizes needed archs\e[0m"
opkg_arch_patch
echo -e "\e[92msdxpinn-patch process complete.\e[0m"
exit 0

View File

@@ -1,5 +0,0 @@
#!/bin/ash
echo -e "\e[38;5;196mINFO: This package can not be removed by opkg\e[0m"
echo -e "\e[38;5;40mINFO: This package can be upgraded...\e[0m"
exit 0

View File

@@ -1,74 +0,0 @@
#!/bin/sh
# Script for building OpenWRT .ipk packages using tar by iamromulan
# Works with SDXPPINN OpenWRT - iamromulan
# This script accepts an optional path to the directory containing the `CONTROL` and `root` directories.
# Usage: ./build-ipk.sh [path]
# If no path is provided, the script will look in the current directory for `CONTROL` and `root` directories.
# This will spit out an ipk in the current directory
# Check if the script is run as root. If not, rerun with sudo.
if [ "$(id -u)" -ne 0 ]; then
echo "Script is not running as root. Re-executing with sudo..."
exec sudo "$0" "$@"
fi
# Set the default build path to the current directory
build_path="."
# Check if a path is provided as the first argument
if [ "$1" ]; then
build_path="$1"
fi
# Check if the required directories are present in the specified path
if [ ! -d "${build_path}/CONTROL" ] || [ ! -d "${build_path}/root" ]; then
echo "Error: CONTROL and root directories must be present in the specified path (${build_path})."
exit 1
fi
# Extract values from the CONTROL/control file in the specified path
pkgname=$(grep -i '^Package:' "${build_path}/CONTROL/control" | awk '{print $2}')
version=$(grep -i '^Version:' "${build_path}/CONTROL/control" | awk '{print $2}')
architecture=$(grep -i '^Architecture:' "${build_path}/CONTROL/control" | awk '{print $2}')
# Check if values are extracted correctly
if [ -z "$pkgname" ] || [ -z "$version" ] || [ -z "$architecture" ]; then
echo "Error: Failed to extract Package, Version, or Architecture from ${build_path}/CONTROL/control."
exit 1
fi
# Set the final IPK name based on the extracted values
ipkname="${pkgname}_${version}_${architecture}.ipk"
# Ensure all CONTROL scripts are executable
echo "Setting permissions for CONTROL scripts..."
chmod +x "${build_path}/CONTROL"/*
# Set ownership for CONTROL and root files
echo "Setting ownership for all package files..."
chown -R root:root "${build_path}/CONTROL"/*
chown -R root:root "${build_path}/root"/*
# Create control.tar.gz from the CONTROL directory
echo "Creating control.tar.gz..."
tar -czvf control.tar.gz -C "${build_path}/CONTROL" .
# Create data.tar.gz from the root directory
echo "Creating data.tar.gz..."
tar -czvf data.tar.gz -C "${build_path}/root" .
# Create debian-binary file (must contain exactly "2.0" without a newline)
echo -n "2.0" > debian-binary
chown -R root:root debian-binary
# Combine the components into the final .ipk file using tar
echo "Packaging ${ipkname}..."
tar -czvf "$ipkname" debian-binary control.tar.gz data.tar.gz
# Clean up intermediate files
echo "Cleaning up temporary files..."
rm -f control.tar.gz data.tar.gz debian-binary
echo "IPK package ${ipkname} created successfully using tar."

View File

@@ -1,10 +0,0 @@
# For preping a firmware before capture of the mtd block
This directory is for custom firmware development. It contains special versions of ipks intended to be installed as apart of a custom firmware.
This is mostly here to help me simplify the firmware creation process
R01 is for R01 firmware on OpenWRT 22.03.5
R02 is for R02 firmware on OpenWRT 23.05.4
~iamromulan

View File

@@ -1,16 +1,15 @@
#!/bin/sh
# Disabled for now
# Determine the absolute path of the script
SCRIPT_PATH=$(realpath "$0")
#download() {
# if [ "$1" = "github" ]; then
# download_github_directory "$2" "$3"
# else
# download_file "$1" "$2"
# fi
#}
download() {
if [ "$1" = "github" ]; then
download_github_directory "$2" "$3"
else
download_file "$1" "$2"
fi
}
download_file() {
url="$1"
@@ -107,10 +106,9 @@ download_github_directory() {
}'
}
#if [ "$#" -eq 0 ]; then
# echo "Usage: download <type> <url> [output_directory]"
if [ "$#" -eq 0 ]; then
echo "Usage: download <type> <url> [output_directory]"
exit 1
#else
else
download "$@"
#fi
exit 0
fi

167
installentware.sh Normal file
View File

@@ -0,0 +1,167 @@
#!/bin/sh
# Modified by iamromulan to set up a proper entware environment for Quectel RM5xx series m.2 modems
TYPE='generic'
#|---------|-----------------|
#| TARGET | Quectel Modem |
#| ARCH | armv7sf-k3.2 |
#| LOADER | ld-linux.so.3 |
#| GLIBC | 2.27 |
#|---------|-----------------|
unset LD_LIBRARY_PATH
unset LD_PRELOAD
ARCH=armv7sf-k3.2
LOADER=ld-linux.so.3
GLIBC=2.27
PRE_OPKG_PATH=$(which opkg)
# Remount filesystem as read-write
mount -o remount,rw /
create_opt_mount() {
# Bind /usrdata/opt to /opt
echo -e '\033[32mInfo: Setting up /opt mount to /usrdata/opt...\033[0m'
cat <<EOF > /lib/systemd/system/opt.mount
[Unit]
Description=Bind /usrdata/opt to /opt
[Mount]
What=/usrdata/opt
Where=/opt
Type=none
Options=bind
[Install]
WantedBy=multi-user.target
EOF
systemctl daemon-reload
systemctl start opt.mount
# Additional systemd service to ensure opt.mount starts at boot
echo -e '\033[32mInfo: Creating service to start opt.mount at boot...\033[0m'
cat <<EOF > /lib/systemd/system/start-opt-mount.service
[Unit]
Description=Ensure opt.mount is started at boot
After=network.target
[Service]
Type=oneshot
ExecStart=/bin/systemctl start opt.mount
[Install]
WantedBy=multi-user.target
EOF
systemctl daemon-reload
ln -s /lib/systemd/system/start-opt-mount.service /lib/systemd/system/multi-user.target.wants/start-opt-mount.service
}
if [ -n "$PRE_OPKG_PATH" ]; then
# Automatically rename the existing opkg binary
mv "$PRE_OPKG_PATH" "${PRE_OPKG_PATH}_old"
echo -e "\033[32mFactory/Already existing opkg has been renamed to opkg_old.\033[0m"
else
echo "Info: no existing opkg binary detected, proceeding with installation"
fi
echo -e '\033[32mInfo: Creating /opt mount pointed to /usrdata/opt ...\033[0m'
create_opt_mount
echo -e '\033[32mInfo: Proceeding with main installation ...\033[0m'
# no need to create many folders. entware-opt package creates most
for folder in bin etc lib/opkg tmp var/lock
do
if [ -d "/opt/$folder" ]; then
echo -e '\033[31mWarning: Folder /opt/$folder exists!\033[0m'
echo -e '\033[31mWarning: If something goes wrong please clean /opt folder and try again.\033[0m'
else
mkdir -p /opt/$folder
fi
done
echo -e '\033[32mInfo: Opkg package manager deployment...\033[0m'
URL=http://bin.entware.net/${ARCH}/installer
wget $URL/opkg -O /opt/bin/opkg
chmod 755 /opt/bin/opkg
wget $URL/opkg.conf -O /opt/etc/opkg.conf
echo -e '\033[32mInfo: Basic packages installation...\033[0m'
/opt/bin/opkg update
/opt/bin/opkg install entware-opt
# Fix for multiuser environment
chmod 777 /opt/tmp
for file in passwd group shells shadow gshadow; do
if [ $TYPE = 'generic' ]; then
if [ -f /etc/$file ]; then
ln -sf /etc/$file /opt/etc/$file
else
[ -f /opt/etc/$file.1 ] && cp /opt/etc/$file.1 /opt/etc/$file
fi
else
if [ -f /opt/etc/$file.1 ]; then
cp /opt/etc/$file.1 /opt/etc/$file
fi
fi
done
[ -f /etc/localtime ] && ln -sf /etc/localtime /opt/etc/localtime
# Create and enable rc.unslung service
echo -e '\033[32mInfo: Creating rc.unslung (Entware init.d service)...\033[0m'
cat <<EOF > /lib/systemd/system/rc.unslung.service
[Unit]
Description=Start Entware services
[Service]
Type=oneshot
# Add a delay to give /opt time to mount
ExecStartPre=/bin/sleep 5
ExecStart=/opt/etc/init.d/rc.unslung start
RemainAfterExit=yes
[Install]
WantedBy=multi-user.target
EOF
systemctl daemon-reload
ln -s /lib/systemd/system/rc.unslung.service /lib/systemd/system/multi-user.target.wants/rc.unslung.service
systemctl start rc.unslung.service
echo -e '\033[32mInfo: Congratulations!\033[0m'
echo -e '\033[32mInfo: If there are no errors above then Entware was successfully initialized.\033[0m'
echo -e '\033[32mInfo: Add /opt/bin & /opt/sbin to $PATH variable\033[0m'
ln -sf /opt/bin/opkg /bin
echo -e '\033[32mInfo: Patching Quectel Login Binary\033[0m'
opkg update && opkg install shadow-login shadow-passwd shadow-useradd
if [ "$?" -ne 0 ]; then
echo -e "\e[1;31mPackage installation failed. Please check your internet connection and try again.\e[0m"
exit 1
fi
# Replace the login and passwd binaries and set home for root to a writable directory
rm /opt/etc/shadow
rm /opt/etc/passwd
cp /etc/shadow /opt/etc/
cp /etc/passwd /opt/etc
mkdir /usrdata/root
mkdir /usrdata/root/bin
touch /usrdata/root/.profile
echo "# Set PATH for all shells" > /usrdata/root/.profile
echo "export PATH=/bin:/usr/sbin:/usr/bin:/sbin:/opt/sbin:/opt/bin:/usrdata/root/bin" >> /usrdata/root/.profile
chmod +x /usrdata/root/.profile
sed -i '1s|/home/root:/bin/sh|/usrdata/root:/bin/bash|' /opt/etc/passwd
rm /bin/login /usr/bin/passwd
ln -sf /opt/bin/login /bin
ln -sf /opt/bin/passwd /usr/bin/
ln -sf /opt/bin/useradd /usr/bin/
echo -e "\e[1;31mPlease set the root password.\e[0m"
/usr/bin/passwd
# Install basic and useful utilites
opkg install mc htop dfc lsof
ln -sf /opt/bin/mc /bin
ln -sf /opt/bin/htop /bin
ln -sf /opt/bin/dfc /bin
ln -sf /opt/bin/lsof /bin
# Remount filesystem as read-only
mount -o remount,ro /

View File

@@ -1,13 +0,0 @@
Package: atinout
Version: 0.9.1
Depends: libc
Source: feeds/kiddin9/atinout
SourceName: atinout
License: GPLv2
LicenseFiles: LICENSE
Section: net
SourceDateEpoch: 1691250335
Maintainer: Adrian Guenter <a@gntr.me>
Architecture: aarch64_cortex-a53
Installed-Size: 3571
Description: Atinout is a program that will execute AT commands in sequence and capture the response from the modem.

View File

@@ -1,5 +0,0 @@
#!/bin/sh
[ "${IPKG_NO_SCRIPT}" = "1" ] && exit 0
[ -s ${IPKG_INSTROOT}/lib/functions.sh ] || exit 0
. ${IPKG_INSTROOT}/lib/functions.sh
default_postinst $0 $@

View File

@@ -1,4 +0,0 @@
#!/bin/sh
[ -s ${IPKG_INSTROOT}/lib/functions.sh ] || exit 0
. ${IPKG_INSTROOT}/lib/functions.sh
default_prerm $0 $@

View File

@@ -1,74 +0,0 @@
#!/bin/sh
# Script for building OpenWRT .ipk packages using tar by iamromulan
# Works with SDXPPINN OpenWRT - iamromulan
# This script accepts an optional path to the directory containing the `CONTROL` and `root` directories.
# Usage: ./build-ipk.sh [path]
# If no path is provided, the script will look in the current directory for `CONTROL` and `root` directories.
# This will spit out an ipk in the current directory
# Check if the script is run as root. If not, rerun with sudo.
if [ "$(id -u)" -ne 0 ]; then
echo "Script is not running as root. Re-executing with sudo..."
exec sudo "$0" "$@"
fi
# Set the default build path to the current directory
build_path="."
# Check if a path is provided as the first argument
if [ "$1" ]; then
build_path="$1"
fi
# Check if the required directories are present in the specified path
if [ ! -d "${build_path}/CONTROL" ] || [ ! -d "${build_path}/root" ]; then
echo "Error: CONTROL and root directories must be present in the specified path (${build_path})."
exit 1
fi
# Extract values from the CONTROL/control file in the specified path
pkgname=$(grep -i '^Package:' "${build_path}/CONTROL/control" | awk '{print $2}')
version=$(grep -i '^Version:' "${build_path}/CONTROL/control" | awk '{print $2}')
architecture=$(grep -i '^Architecture:' "${build_path}/CONTROL/control" | awk '{print $2}')
# Check if values are extracted correctly
if [ -z "$pkgname" ] || [ -z "$version" ] || [ -z "$architecture" ]; then
echo "Error: Failed to extract Package, Version, or Architecture from ${build_path}/CONTROL/control."
exit 1
fi
# Set the final IPK name based on the extracted values
ipkname="${pkgname}_${version}_${architecture}.ipk"
# Ensure all CONTROL scripts are executable
echo "Setting permissions for CONTROL scripts..."
chmod +x "${build_path}/CONTROL"/*
# Set ownership for CONTROL and root files
echo "Setting ownership for all package files..."
chown -R root:root "${build_path}/CONTROL"/*
chown -R root:root "${build_path}/root"/*
# Create control.tar.gz from the CONTROL directory
echo "Creating control.tar.gz..."
tar -czvf control.tar.gz -C "${build_path}/CONTROL" .
# Create data.tar.gz from the root directory
echo "Creating data.tar.gz..."
tar -czvf data.tar.gz -C "${build_path}/root" .
# Create debian-binary file (must contain exactly "2.0" without a newline)
echo -n "2.0" > debian-binary
chown -R root:root debian-binary
# Combine the components into the final .ipk file using tar
echo "Packaging ${ipkname}..."
tar -czvf "$ipkname" debian-binary control.tar.gz data.tar.gz
# Clean up intermediate files
echo "Cleaning up temporary files..."
rm -f control.tar.gz data.tar.gz debian-binary
echo "IPK package ${ipkname} created successfully using tar."

View File

@@ -1,2 +0,0 @@
/etc/config/
/etc/atinout/

View File

@@ -1,7 +0,0 @@
Package: kmod-wireguard
Depends: sdxpinn-patch
Version: 1
Architecture: sdxpinn
Maintainer: Cameron Thompson iamromulan@github.com
Source: github.com/iamromulan
Description: Wireguard is compiled into the kernel

View File

@@ -1,5 +0,0 @@
#!/bin/ash
echo "kmod-wireguard registration Complete"
exit 0

View File

@@ -1,74 +0,0 @@
#!/bin/sh
# Script for building OpenWRT .ipk packages using tar by iamromulan
# Works with SDXPPINN OpenWRT - iamromulan
# This script accepts an optional path to the directory containing the `CONTROL` and `root` directories.
# Usage: ./build-ipk.sh [path]
# If no path is provided, the script will look in the current directory for `CONTROL` and `root` directories.
# This will spit out an ipk in the current directory
# Check if the script is run as root. If not, rerun with sudo.
if [ "$(id -u)" -ne 0 ]; then
echo "Script is not running as root. Re-executing with sudo..."
exec sudo "$0" "$@"
fi
# Set the default build path to the current directory
build_path="."
# Check if a path is provided as the first argument
if [ "$1" ]; then
build_path="$1"
fi
# Check if the required directories are present in the specified path
if [ ! -d "${build_path}/CONTROL" ] || [ ! -d "${build_path}/root" ]; then
echo "Error: CONTROL and root directories must be present in the specified path (${build_path})."
exit 1
fi
# Extract values from the CONTROL/control file in the specified path
pkgname=$(grep -i '^Package:' "${build_path}/CONTROL/control" | awk '{print $2}')
version=$(grep -i '^Version:' "${build_path}/CONTROL/control" | awk '{print $2}')
architecture=$(grep -i '^Architecture:' "${build_path}/CONTROL/control" | awk '{print $2}')
# Check if values are extracted correctly
if [ -z "$pkgname" ] || [ -z "$version" ] || [ -z "$architecture" ]; then
echo "Error: Failed to extract Package, Version, or Architecture from ${build_path}/CONTROL/control."
exit 1
fi
# Set the final IPK name based on the extracted values
ipkname="${pkgname}_${version}_${architecture}.ipk"
# Ensure all CONTROL scripts are executable
echo "Setting permissions for CONTROL scripts..."
chmod +x "${build_path}/CONTROL"/*
# Set ownership for CONTROL and root files
echo "Setting ownership for all package files..."
chown -R root:root "${build_path}/CONTROL"/*
chown -R root:root "${build_path}/root"/*
# Create control.tar.gz from the CONTROL directory
echo "Creating control.tar.gz..."
tar -czvf control.tar.gz -C "${build_path}/CONTROL" .
# Create data.tar.gz from the root directory
echo "Creating data.tar.gz..."
tar -czvf data.tar.gz -C "${build_path}/root" .
# Create debian-binary file (must contain exactly "2.0" without a newline)
echo -n "2.0" > debian-binary
chown -R root:root debian-binary
# Combine the components into the final .ipk file using tar
echo "Packaging ${ipkname}..."
tar -czvf "$ipkname" debian-binary control.tar.gz data.tar.gz
# Clean up intermediate files
echo "Cleaning up temporary files..."
rm -f control.tar.gz data.tar.gz debian-binary
echo "IPK package ${ipkname} created successfully using tar."

View File

@@ -1,14 +0,0 @@
Package: libucode20230711
Version: 2024.07.22~b610860d-r3
Depends: libc, libjson-c5
Provides: libucode
Source: https://dl.openwrt.ai/packages-24.10/aarch64_cortex-a53/base/libucode20230711_2025.02.10~a8a11aea-r1_aarch64_cortex-a53.ipk
SourceName: ucode
License: ISC
Section: libs
SourceDateEpoch: 1729600843
ABIVersion: 20230711
Maintainer: Jo-Philipp Wich <jo@mein.io>
Architecture: aarch64_cortex-a53
Installed-Size: 204800
Description: The libucode package provides the shared runtime library for the ucode interpreter.

View File

@@ -1,5 +0,0 @@
#!/bin/sh
[ "${IPKG_NO_SCRIPT}" = "1" ] && exit 0
[ -s ${IPKG_INSTROOT}/lib/functions.sh ] || exit 0
. ${IPKG_INSTROOT}/lib/functions.sh
default_postinst $0 $@

View File

@@ -1,4 +0,0 @@
#!/bin/sh
[ -s ${IPKG_INSTROOT}/lib/functions.sh ] || exit 0
. ${IPKG_INSTROOT}/lib/functions.sh
default_prerm $0 $@

View File

@@ -1,74 +0,0 @@
#!/bin/sh
# Script for building OpenWRT .ipk packages using tar by iamromulan
# Works with SDXPPINN OpenWRT - iamromulan
# This script accepts an optional path to the directory containing the `CONTROL` and `root` directories.
# Usage: ./build-ipk.sh [path]
# If no path is provided, the script will look in the current directory for `CONTROL` and `root` directories.
# This will spit out an ipk in the current directory
# Check if the script is run as root. If not, rerun with sudo.
if [ "$(id -u)" -ne 0 ]; then
echo "Script is not running as root. Re-executing with sudo..."
exec sudo "$0" "$@"
fi
# Set the default build path to the current directory
build_path="."
# Check if a path is provided as the first argument
if [ "$1" ]; then
build_path="$1"
fi
# Check if the required directories are present in the specified path
if [ ! -d "${build_path}/CONTROL" ] || [ ! -d "${build_path}/root" ]; then
echo "Error: CONTROL and root directories must be present in the specified path (${build_path})."
exit 1
fi
# Extract values from the CONTROL/control file in the specified path
pkgname=$(grep -i '^Package:' "${build_path}/CONTROL/control" | awk '{print $2}')
version=$(grep -i '^Version:' "${build_path}/CONTROL/control" | awk '{print $2}')
architecture=$(grep -i '^Architecture:' "${build_path}/CONTROL/control" | awk '{print $2}')
# Check if values are extracted correctly
if [ -z "$pkgname" ] || [ -z "$version" ] || [ -z "$architecture" ]; then
echo "Error: Failed to extract Package, Version, or Architecture from ${build_path}/CONTROL/control."
exit 1
fi
# Set the final IPK name based on the extracted values
ipkname="${pkgname}_${version}_${architecture}.ipk"
# Ensure all CONTROL scripts are executable
echo "Setting permissions for CONTROL scripts..."
chmod +x "${build_path}/CONTROL"/*
# Set ownership for CONTROL and root files
echo "Setting ownership for all package files..."
chown -R root:root "${build_path}/CONTROL"/*
chown -R root:root "${build_path}/root"/*
# Create control.tar.gz from the CONTROL directory
echo "Creating control.tar.gz..."
tar -czvf control.tar.gz -C "${build_path}/CONTROL" .
# Create data.tar.gz from the root directory
echo "Creating data.tar.gz..."
tar -czvf data.tar.gz -C "${build_path}/root" .
# Create debian-binary file (must contain exactly "2.0" without a newline)
echo -n "2.0" > debian-binary
chown -R root:root debian-binary
# Combine the components into the final .ipk file using tar
echo "Packaging ${ipkname}..."
tar -czvf "$ipkname" debian-binary control.tar.gz data.tar.gz
# Clean up intermediate files
echo "Cleaning up temporary files..."
rm -f control.tar.gz data.tar.gz debian-binary
echo "IPK package ${ipkname} created successfully using tar."

View File

@@ -1 +0,0 @@
/etc/config/argon

View File

@@ -1,12 +0,0 @@
Package: luci-app-argon-config
Version: 0.9-1
Depends: libc, luci-compat, luci-lib-ipkg
Recommends: luci-theme-argon
Source: github.com/jerrykuku/luci-app-argon-config/releases/tag/v0.9
SourceName: luci-app-argon-config
Section: luci
SourceDateEpoch: 1650782942
Maintainer: github.com/jerrykuku
Architecture: all
Installed-Size: 3586
Description: LuCI page for Argon Config

View File

@@ -1,5 +0,0 @@
#!/bin/sh
[ "${IPKG_NO_SCRIPT}" = "1" ] && exit 0
[ -s ${IPKG_INSTROOT}/lib/functions.sh ] || exit 0
. ${IPKG_INSTROOT}/lib/functions.sh
default_postinst $0 $@

View File

@@ -1,7 +0,0 @@
[ -n "${IPKG_INSTROOT}" ] || {
(. /etc/uci-defaults/luci-argon-config) && rm -f /etc/uci-defaults/luci-argon-config
rm -f /tmp/luci-indexcache
rm -rf /tmp/luci-modulecache/
killall -HUP rpcd 2>/dev/null
exit 0
}

View File

@@ -1,4 +0,0 @@
#!/bin/sh
[ -s ${IPKG_INSTROOT}/lib/functions.sh ] || exit 0
. ${IPKG_INSTROOT}/lib/functions.sh
default_prerm $0 $@

View File

@@ -1,74 +0,0 @@
#!/bin/sh
# Script for building OpenWRT .ipk packages using tar by iamromulan
# Works with SDXPPINN OpenWRT - iamromulan
# This script accepts an optional path to the directory containing the `CONTROL` and `root` directories.
# Usage: ./build-ipk.sh [path]
# If no path is provided, the script will look in the current directory for `CONTROL` and `root` directories.
# This will spit out an ipk in the current directory
# Check if the script is run as root. If not, rerun with sudo.
if [ "$(id -u)" -ne 0 ]; then
echo "Script is not running as root. Re-executing with sudo..."
exec sudo "$0" "$@"
fi
# Set the default build path to the current directory
build_path="."
# Check if a path is provided as the first argument
if [ "$1" ]; then
build_path="$1"
fi
# Check if the required directories are present in the specified path
if [ ! -d "${build_path}/CONTROL" ] || [ ! -d "${build_path}/root" ]; then
echo "Error: CONTROL and root directories must be present in the specified path (${build_path})."
exit 1
fi
# Extract values from the CONTROL/control file in the specified path
pkgname=$(grep -i '^Package:' "${build_path}/CONTROL/control" | awk '{print $2}')
version=$(grep -i '^Version:' "${build_path}/CONTROL/control" | awk '{print $2}')
architecture=$(grep -i '^Architecture:' "${build_path}/CONTROL/control" | awk '{print $2}')
# Check if values are extracted correctly
if [ -z "$pkgname" ] || [ -z "$version" ] || [ -z "$architecture" ]; then
echo "Error: Failed to extract Package, Version, or Architecture from ${build_path}/CONTROL/control."
exit 1
fi
# Set the final IPK name based on the extracted values
ipkname="${pkgname}_${version}_${architecture}.ipk"
# Ensure all CONTROL scripts are executable
echo "Setting permissions for CONTROL scripts..."
chmod +x "${build_path}/CONTROL"/*
# Set ownership for CONTROL and root files
echo "Setting ownership for all package files..."
chown -R root:root "${build_path}/CONTROL"/*
chown -R root:root "${build_path}/root"/*
# Create control.tar.gz from the CONTROL directory
echo "Creating control.tar.gz..."
tar -czvf control.tar.gz -C "${build_path}/CONTROL" .
# Create data.tar.gz from the root directory
echo "Creating data.tar.gz..."
tar -czvf data.tar.gz -C "${build_path}/root" .
# Create debian-binary file (must contain exactly "2.0" without a newline)
echo -n "2.0" > debian-binary
chown -R root:root debian-binary
# Combine the components into the final .ipk file using tar
echo "Packaging ${ipkname}..."
tar -czvf "$ipkname" debian-binary control.tar.gz data.tar.gz
# Clean up intermediate files
echo "Cleaning up temporary files..."
rm -f control.tar.gz data.tar.gz debian-binary
echo "IPK package ${ipkname} created successfully using tar."

View File

@@ -1,9 +0,0 @@
config global
option primary '#5e72e4'
option dark_primary '#483d8b'
option blur '10'
option blur_dark '10'
option transparency '0.5'
option transparency_dark '0.5'
option mode 'normal'
option bing_background '0'

View File

@@ -1,6 +0,0 @@
#!/bin/sh
sed -i 's/cbi.submit\"] = true/cbi.submit\"] = \"1\"/g' /usr/lib/lua/luci/dispatcher.lua
rm -f /tmp/luci-indexcache
exit 0

View File

@@ -1,10 +0,0 @@
module("luci.controller.argon-config", package.seeall)
function index()
if not nixio.fs.access('/www/luci-static/argon/css/cascade.css') then
return
end
local page = entry({"admin", "system", "argon-config"}, form("argon-config"), _("Argon Config"), 90)
page.acl_depends = { "luci-app-argon-config" }
end

View File

@@ -1,217 +0,0 @@
local nxfs = require 'nixio.fs'
local wa = require 'luci.tools.webadmin'
local opkg = require 'luci.model.ipkg'
local sys = require 'luci.sys'
local http = require 'luci.http'
local nutil = require 'nixio.util'
local name = 'argon'
local uci = require 'luci.model.uci'.cursor()
local fstat = nxfs.statvfs(opkg.overlay_root())
local space_total = fstat and fstat.blocks or 0
local space_free = fstat and fstat.bfree or 0
local space_used = space_total - space_free
local free_byte = space_free * fstat.frsize
local primary, dark_primary, blur_radius, blur_radius_dark, blur_opacity, mode
if nxfs.access('/etc/config/argon') then
primary = uci:get_first('argon', 'global', 'primary')
dark_primary = uci:get_first('argon', 'global', 'dark_primary')
blur_radius = uci:get_first('argon', 'global', 'blur')
blur_radius_dark = uci:get_first('argon', 'global', 'blur_dark')
blur_opacity = uci:get_first('argon', 'global', 'transparency')
blur_opacity_dark = uci:get_first('argon', 'global', 'transparency_dark')
mode = uci:get_first('argon', 'global', 'mode')
bing_background = uci:get_first('argon', 'global', 'bing_background')
end
function glob(...)
local iter, code, msg = nxfs.glob(...)
if iter then
return nutil.consume(iter)
else
return nil, code, msg
end
end
local transparency_sets = {
0,
0.1,
0.2,
0.3,
0.4,
0.5,
0.6,
0.7,
0.8,
0.9,
1
}
-- [[ 模糊设置 ]]--
br = SimpleForm('config', translate('Argon Config'), translate('Here you can set the blur and transparency of the login page of argon theme, and manage the background pictures and videos.[Chrome is recommended]'))
br.reset = false
br.submit = false
s = br:section(SimpleSection)
o = s:option(ListValue, 'bing_background', translate('Wallpaper Source'))
o:value('0', translate('Built-in'))
o:value('1', translate('Bing Wallpapers'))
o.default = bing_background
o.rmempty = false
o = s:option(ListValue, 'mode', translate('Theme mode'))
o:value('normal', translate('Follow System'))
o:value('light', translate('Force Light'))
o:value('dark', translate('Force Dark'))
o.default = mode
o.rmempty = false
o.description = translate('You can choose Theme color mode here')
o = s:option(Value, 'primary', translate('[Light mode] Primary Color'), translate('A HEX Color ; ( Default: #5e72e4 )'))
o.default = primary
o.datatype = ufloat
o.rmempty = false
o = s:option(ListValue, 'transparency', translate('[Light mode] Transparency'), translate('0 transparent - 1 opaque ; ( Suggest: transparent: 0 or translucent preset: 0.5 )'))
for _, v in ipairs(transparency_sets) do
o:value(v)
end
o.default = blur_opacity
o.datatype = ufloat
o.rmempty = false
o = s:option(Value, 'blur', translate('[Light mode] Frosted Glass Radius'), translate('Larger value will more blurred ; ( Suggest: clear: 1 or blur preset: 10 )'))
o.default = blur_radius
o.datatype = ufloat
o.rmempty = false
o = s:option(Value, 'dark_primary', translate('[Dark mode] Primary Color'), translate('A HEX Color ; ( Default: #483d8b )'))
o.default = dark_primary
o.datatype = ufloat
o.rmempty = false
o = s:option(ListValue, 'transparency_dark', translate('[Dark mode] Transparency'), translate('0 transparent - 1 opaque ; ( Suggest: Black translucent preset: 0.5 )'))
for _, v in ipairs(transparency_sets) do
o:value(v)
end
o.default = blur_opacity_dark
o.datatype = ufloat
o.rmempty = false
o = s:option(Value, 'blur_dark', translate('[Dark mode] Frosted Glass Radius'), translate('Larger value will more blurred ; ( Suggest: clear: 1 or blur preset: 10 )'))
o.default = blur_radius_dark
o.datatype = ufloat
o.rmempty = false
o = s:option(Button, 'save', translate('Save Changes'))
o.inputstyle = 'reload'
function br.handle(self, state, data)
if (state == FORM_VALID and data.blur ~= nil and data.blur_dark ~= nil and data.transparency ~= nil and data.transparency_dark ~= nil and data.mode ~= nil) then
nxfs.writefile('/tmp/aaa', data)
for key, value in pairs(data) do
uci:set('argon','@global[0]',key,value)
end
uci:commit('argon')
end
return true
end
ful = SimpleForm('upload', translate('Upload (Free: ') .. wa.byte_format(free_byte) .. ')', translate("You can upload files such as jpg,png,gif,mp4,webm files, To change the login page background."))
ful.reset = false
ful.submit = false
sul = ful:section(SimpleSection, '', translate("Upload file to '/www/luci-static/argon/background/'"))
fu = sul:option(FileUpload, '')
fu.template = 'argon-config/other_upload'
um = sul:option(DummyValue, '', nil)
um.template = 'argon-config/other_dvalue'
local dir, fd
dir = '/www/luci-static/argon/background/'
nxfs.mkdir(dir)
http.setfilehandler(
function(meta, chunk, eof)
if not fd then
if not meta then
return
end
if meta and chunk then
fd = nixio.open(dir .. meta.file, 'w')
end
if not fd then
um.value = translate('Create upload file error.')
return
end
end
if chunk and fd then
fd:write(chunk)
end
if eof and fd then
fd:close()
fd = nil
um.value = translate('File saved to') .. ' "/www/luci-static/argon/background/' .. meta.file .. '"'
end
end
)
if http.formvalue('upload') then
local f = http.formvalue('ulfile')
if #f <= 0 then
um.value = translate('No specify upload file.')
end
end
local function getSizeStr(size)
local i = 0
local byteUnits = {' kB', ' MB', ' GB', ' TB'}
repeat
size = size / 1024
i = i + 1
until (size <= 1024)
return string.format('%.1f', size) .. byteUnits[i]
end
local inits, attr = {}
for i, f in ipairs(glob(dir .. '*')) do
attr = nxfs.stat(f)
if attr then
inits[i] = {}
inits[i].name = nxfs.basename(f)
inits[i].mtime = os.date('%Y-%m-%d %H:%M:%S', attr.mtime)
inits[i].modestr = attr.modestr
inits[i].size = getSizeStr(attr.size)
inits[i].remove = 0
inits[i].install = false
end
end
form = SimpleForm('filelist', translate('Background file list'), nil)
form.reset = false
form.submit = false
tb = form:section(Table, inits)
nm = tb:option(DummyValue, 'name', translate('File name'))
mt = tb:option(DummyValue, 'mtime', translate('Modify time'))
sz = tb:option(DummyValue, 'size', translate('Size'))
btnrm = tb:option(Button, 'remove', translate('Remove'))
btnrm.render = function(self, section, scope)
self.inputstyle = 'remove'
Button.render(self, section, scope)
end
btnrm.write = function(self, section)
local v = nxfs.unlink(dir .. nxfs.basename(inits[section].name))
if v then
table.remove(inits, section)
end
return v
end
return br, ful, form

View File

@@ -1,7 +0,0 @@
<%+cbi/valueheader%>
<% if self:cfgvalue(section) ~= false then %>
<input class="cbi-button cbi-input-<%=self.inputstyle or "button" %>" style="display: <%= display %>" type="submit"<%= attr("name", cbid) .. attr("id", cbid) .. attr("value", self.inputtitle or self.title)%> />
<% else %>
-
<% end %>
<%+cbi/valuefooter%>

View File

@@ -1,8 +0,0 @@
<%+cbi/valueheader%>
<span style="color: red">
<%
local val = self:cfgvalue(section) or self.default or ""
write(pcdata(val))
%>
</span>
<%+cbi/valuefooter%>

View File

@@ -1,5 +0,0 @@
<%+cbi/valueheader%>
<label class="cbi-value" style="display:inline-block; width: 130px" for="ulfile"><%:Choose local file:%></label>
<input class="cbi-input-file" style="width: 400px" type="file" id="ulfile" name="ulfile" accept="image/png, image/jpeg, image/gif, video/mp4, video/webm"/>
<input type="submit" class="btn cbi-button cbi-input-apply" name="upload" value="<%:Upload%>" />
<%+cbi/valuefooter%>

View File

@@ -1,11 +0,0 @@
{
"luci-app-argon-config": {
"description": "Grant UCI access for luci-app-argon-config",
"read": {
"uci": [ "argon" ]
},
"write": {
"uci": [ "argon" ]
}
}
}

View File

@@ -1 +0,0 @@
/etc/config/atcommands.user

View File

@@ -1,12 +0,0 @@
Package: luci-app-atinout-mod
Version: 1.3.4-20250119
Depends: libc, atinout, luci-compat
Source: package/luci-app-atinout-mod
SourceName: luci-app-atinout-mod
License: GPLv3
Section: luci
SourceDateEpoch: 1636930326
Maintainer: OpenWrt LuCI community
Architecture: all
Installed-Size: 3790
Description: Web UI for atinout modded by iamromulan preset for use on SDXPINN

View File

@@ -1,5 +0,0 @@
#!/bin/sh
[ "${IPKG_NO_SCRIPT}" = "1" ] && exit 0
[ -s ${IPKG_INSTROOT}/lib/functions.sh ] || exit 0
. ${IPKG_INSTROOT}/lib/functions.sh
default_postinst $0 $@

View File

@@ -1,7 +0,0 @@
#!/bin/sh
chmod +x /sbin/set_at_port.sh
chmod +x /usr/bin/luci-app-atinout
rm -rf /tmp/luci-indexcache
rm -rf /tmp/luci-modulecache/
/sbin/set_at_port.sh
exit 0

View File

@@ -1,4 +0,0 @@
#!/bin/sh
[ -s ${IPKG_INSTROOT}/lib/functions.sh ] || exit 0
. ${IPKG_INSTROOT}/lib/functions.sh
default_prerm $0 $@

View File

@@ -1,74 +0,0 @@
#!/bin/sh
# Script for building OpenWRT .ipk packages using tar by iamromulan
# Works with SDXPPINN OpenWRT - iamromulan
# This script accepts an optional path to the directory containing the `CONTROL` and `root` directories.
# Usage: ./build-ipk.sh [path]
# If no path is provided, the script will look in the current directory for `CONTROL` and `root` directories.
# This will spit out an ipk in the current directory
# Check if the script is run as root. If not, rerun with sudo.
if [ "$(id -u)" -ne 0 ]; then
echo "Script is not running as root. Re-executing with sudo..."
exec sudo "$0" "$@"
fi
# Set the default build path to the current directory
build_path="."
# Check if a path is provided as the first argument
if [ "$1" ]; then
build_path="$1"
fi
# Check if the required directories are present in the specified path
if [ ! -d "${build_path}/CONTROL" ] || [ ! -d "${build_path}/root" ]; then
echo "Error: CONTROL and root directories must be present in the specified path (${build_path})."
exit 1
fi
# Extract values from the CONTROL/control file in the specified path
pkgname=$(grep -i '^Package:' "${build_path}/CONTROL/control" | awk '{print $2}')
version=$(grep -i '^Version:' "${build_path}/CONTROL/control" | awk '{print $2}')
architecture=$(grep -i '^Architecture:' "${build_path}/CONTROL/control" | awk '{print $2}')
# Check if values are extracted correctly
if [ -z "$pkgname" ] || [ -z "$version" ] || [ -z "$architecture" ]; then
echo "Error: Failed to extract Package, Version, or Architecture from ${build_path}/CONTROL/control."
exit 1
fi
# Set the final IPK name based on the extracted values
ipkname="${pkgname}_${version}_${architecture}.ipk"
# Ensure all CONTROL scripts are executable
echo "Setting permissions for CONTROL scripts..."
chmod +x "${build_path}/CONTROL"/*
# Set ownership for CONTROL and root files
echo "Setting ownership for all package files..."
chown -R root:root "${build_path}/CONTROL"/*
chown -R root:root "${build_path}/root"/*
# Create control.tar.gz from the CONTROL directory
echo "Creating control.tar.gz..."
tar -czvf control.tar.gz -C "${build_path}/CONTROL" .
# Create data.tar.gz from the root directory
echo "Creating data.tar.gz..."
tar -czvf data.tar.gz -C "${build_path}/root" .
# Create debian-binary file (must contain exactly "2.0" without a newline)
echo -n "2.0" > debian-binary
chown -R root:root debian-binary
# Combine the components into the final .ipk file using tar
echo "Packaging ${ipkname}..."
tar -czvf "$ipkname" debian-binary control.tar.gz data.tar.gz
# Clean up intermediate files
echo "Cleaning up temporary files..."
rm -f control.tar.gz data.tar.gz debian-binary
echo "IPK package ${ipkname} created successfully using tar."

View File

@@ -1,30 +0,0 @@
Reboot;AT+CFUN=1,1
Disconnect;AT+CFUN=0
Connect;AT+CFUN=1
Signal Info;AT+QENG="servingcell"
CA Info;AT+QCAINFO
Get current SIM Slot;AT+QUIMSLOT?
Switch to SIM Slot 1;AT+QUIMSLOT=1
Switch to SIM Slot 2;AT+QUIMSLOT=2
Get current APN List;AT+CGDCONT?
Set APN to NRBROADBAND;AT+CGDCONT=1,"IPV4V6","NRBROADBAND"
Show Current IMEI;AT+EGMR=0,7
Show Current Network Mode;AT+QNWPREFCFG="mode_pref"
Set Network Mode to AUTO;AT+QNWPREFCFG="mode_pref",AUTO
Set Network Mode to 5G NR/4G LTE Only;AT+QNWPREFCFG="mode_pref",NR5G:LTE
Set Network Mode to 5G NR Only;AT+QNWPREFCFG="mode_pref",NR5G
Set Network Mode to 4G LTE Only;AT+QNWPREFCFG="mode_pref",LTE
Check to see if SA or NSA is disabled;AT+QNWPREFCFG="nr5g_disable_mode"
Enable Both SA and NSA;AT+QNWPREFCFG="nr5g_disable_mode",0
Disable SA Only;AT+QNWPREFCFG="nr5g_disable_mode",1
Disable NSA Only;AT+QNWPREFCFG="nr5g_disable_mode",2
Get Currently Enabled 5G/NR SA Bands;AT+QNWPREFCFG="nr5g_band"
Get Currently Enabled 5G/NR NSA Bands;AT+QNWPREFCFG="nsa_nr5g_band"
Get Currently Enabled 4G/LTE Bands;AT+QNWPREFCFG="lte_band"
View assigned IPv4/IPv6 addresses from the provider;AT+QMAP="WWAN"
Enable IPPT paste in MAC for FF:FF:FF...;AT+QMAP="MPDN_rule",0,1,0,1,1,"FF:FF:FF:FF:FF:FF"
Disable IPPT;AT+QMAP="MPDN_rule",0
Set IPv4 DMZ....replace iphere;AT+QMAP="DMZ",1,4,iphere
Set IPv6 DMZ....replace iphere;AT+QMAP="DMZ",1,6,iphere
Disable IPv4 DMZ;AT+QMAP="DMZ",0,4
Disable IPv6 DMZ;AT+QMAP="DMZ",0,6

View File

@@ -1,4 +0,0 @@
config atinout 'general'
option atcport '/dev/smd7'

View File

@@ -1,21 +0,0 @@
#!/bin/sh
# Copyright 2020-2021 Rafał Wabik (IceG) - From eko.one.pl forum
# Licensed to the GNU General Public License v3.0.
work=false
for port in /dev/ttyUSB*
do
[[ -e $port ]] || continue
gcom -d $port info &> /tmp/testusb
testUSB=`cat /tmp/testusb | grep "Error\|Can't"`
if [ -z "$testUSB" ]; then
work=$port
break
fi
done
rm -rf /tmp/testusb
if [ $work != false ]; then
uci set atinout.@atinout[0].atcport=$work
uci commit atinout
fi

View File

@@ -1,21 +0,0 @@
#!/bin/sh
# Copyright 2020-2021 Rafał Wabik (IceG) - From eko.one.pl forum
# Licensed to the GNU General Public License v3.0.
work=false
for port in /dev/ttyUSB*
do
[[ -e $port ]] || continue
gcom -d $port info &> /tmp/testusb
testUSB=`cat /tmp/testusb | grep "Error\|Can't"`
if [ -z "$testUSB" ]; then
work=$port
break
fi
done
rm -rf /tmp/testusb
if [ $work != false ]; then
uci set atinout.@atinout[0].atcport=$work
uci commit atinout
fi

View File

@@ -1,8 +0,0 @@
#!/bin/sh
ARGS=$1
DEVPORT=$(uci -q get atinout.general.atcport)
if [ "$DEVPORT" ]; then
echo "${ARGS}" | /usr/bin/atinout - ${DEVPORT} -
fi

View File

@@ -1,49 +0,0 @@
local e=require"luci.util"
local e=require"nixio.fs"
local e=require"luci.sys"
local e=require"luci.http"
local e=require"luci.dispatcher"
local e=require"luci.http"
local t=require"luci.sys"
local t=require"luci.model.uci".cursor()
module("luci.controller.modem.atc",package.seeall)
function index()
entry({"admin","modem"},firstchild(),"Modem",30).dependent=false
entry({"admin","modem","atc"},alias("admin","modem","atc","atcommand"),translate("AT Commands"),10).acl_depends={"luci-app-atinout-mod"}
entry({"admin","modem","atc","atcommand"},template("modem/atcommand"),translate("AT Commands"),10)
entry({"admin","modem","atc","atconfig"},cbi("modem/atconfig"),translate("Configuration"),20)
entry({"admin","modem","webcmd"},call("webcmd"))
entry({"admin","modem","atc","user_atc"},call("useratc"),nil).leaf=true
end
function webcmd()
local t=e.formvalue("cmd")
if t then
local t=io.popen("/usr/bin/luci-app-atinout "..t:gsub("[$]","\\\$"):gsub("\"","\\\"").." 2>&1")
local a=t:read("*a")
t:close()
e.write(tostring(a))
else
e.write_json(e.formvalue())
end
end
function uussd(t)
local e=nixio.fs.access("/etc/config/atcommands.user")and
io.popen("cat /etc/config/atcommands.user")
if e then
for a in e:lines()do
local e=a
if e then
t[#t+1]={
usd=e
}
end
end
e:close()
end
end
function useratc()
local e={}
uussd(e)
luci.http.prepare_content("application/json")
luci.http.write_json(e)
end

View File

@@ -1,35 +0,0 @@
local e=require"luci.util"
local o=require"nixio.fs"
local e=require"luci.sys"
local e=require"luci.http"
local e=require"luci.dispatcher"
local e=require"luci.http"
local e=require"luci.sys"
local e=require"luci.model.uci".cursor()
local n="/etc/config/atcommands.user"
local t
local e
local i
local a=nixio.fs.glob("/dev/tty[A-Z][A-Z]*")
t=Map("atinout",translate("Atinout Configuration"),
translate("Configuration panel for atinout."))
e=t:section(NamedSection,'general',"atinout",""..translate("AT Commands Terminal Settings"))
e.anonymous=true
i=e:option(Value,"atcport",translate("AT Command Sending Port"))
if a then
local e
for e in a do
i:value(e,e)
end
end
local e=e:option(TextValue,"user_atcommands",translate("User AT Commands"),translate("Each line must have the following format: 'AT Command name;AT Command'. Save to file '/etc/config/atcommands.user'."))
e.rows=20
e.rmempty=false
function e.cfgvalue(e,e)
return o.readfile(n)
end
function e.write(t,t,e)
e=e:gsub("\r\n","\n")
o.writefile(n,e)
end
return t

View File

@@ -1,133 +0,0 @@
<%+header%>
<!--
This module gives some convinience to access the shell via web, in
case that you don't have a uart console or telnet/ssh connection.
Hua Shao <nossiac@163.com>
-->
<h2><%:AT Commands%></h2>
<label><%:Web UI for sending AT Commands.%></label>
<p></p>
<h4><%:Sending commands to modem%></h4>
<div class="table" width="100%">
<div class="tr">
<div class="td left" width="23%"><%:User AT Commands%>:</div>
<div class="td left" style="width:55%;">
<select name="ussd" id="pl" onclick="copyFunction()">
</select>
</div>
<div class="td left" style="width:55%;"></div>
</div>
<div class="tr">
<div class="td left" style="width:23%;"><%:Command to send%>:</div>
<div class="td left" ><input type="text" id="code" required size="20" ></div>
</div>
</div>
<div class="table" width="100%">
<div class="td left" style="width:23%;"><%:Reply%>:
<p>
<pre id="result" style="visibility: hidden; width:77%;"></pre></div>
<div class="tr cbi-rowstyle-2">
<div class="td right"><div style="float: left;"><div class="ifacebadge"><a href="https://eko.one.pl">e1</a></div></div><input type="button" style="margin-right: 23%"; id="sendcmd" class="btn cbi-button cbi-button-neutral" value="<%:Send Command%>" /></div>
</div>
</div>
<script type="text/javascript">
window.onload = function readUSER() {
XHR.get('<%=luci.dispatcher.build_url("admin", "modem", "atc", "user_atc")%>', null,
function(x, json)
{
select = document.getElementById('pl');
var count = Object.keys(json).length;
for(var d=0;d<=count;d++)
{
var opt = document.createElement('option');
var s = json[d].usd;
var fields = s.split(/;/);
var name = fields[0];
var code = fields[1];
opt.text = name;
opt.value = code.trim();
opt.innerHTML = name;
select.appendChild(opt);
}
}
);
}
function copyFunction() {
var node = document.getElementById('result');
node.style.visibility = 'hidden';
var x = document.getElementById("pl").value;
document.getElementById("code").value = x;
document.getElementById("result").innerHTML = "";
}
function postcmd(cmd) {
(new XHR()).post("<%=luci.dispatcher.build_url("admin", "modem", "webcmd")%>", {"cmd":cmd}, function(x) {
console.log(x.response)
console.log(x)
var aStr = x.response;
var myre = /(^[ \t]*\n)/gm;
var bStr = aStr.replace(myre,"");
document.getElementById("result").innerHTML = bStr;
});
return false;
}
document.addEventListener('DOMContentLoaded', function (ev) {var button = document.getElementById("sendcmd");
button.addEventListener("click", function () {
var s = document.getElementById("code").value;
if ( s.length == 0 )
{
document.getElementById("result").innerHTML = "";
alert("<%:Please enter a AT Command%>");
return false;
}
var cmd = document.getElementById("code");
postcmd(cmd.value);
cmd.value = "";
var node = document.getElementById('result');
if (node.style.visibility=='visible') {
node.style.visibility = 'hidden';
}
else
node.style.visibility = 'visible'
return true;
});
}, true);
</script>
<%+footer%>

View File

@@ -1,17 +0,0 @@
{
"luci-app-atinout-mod": {
"description": "Grant UCI and file access for luci-app-atinout-mod",
"read": {
"uci": [ "atinout" ]
},
"write": {
"uci": [ "atinout" ]
}
}
}

View File

@@ -1 +0,0 @@
/etc/config/wireguard

View File

@@ -1,11 +0,0 @@
Package: luci-app-go-wireguard
Version: 4.500-2
Depends: libc, wireguard-tools, kmod-wireguard, luci-proto-wireguard, udptunnel, eoip
Source: package/rooter/0optionalapps/ext-wireguard
SourceName: ext-wireguard
Section: utils
SourceDateEpoch: 1716401566
Maintainer: Created by DM/makefile by Cobia@whirlpool
Architecture: all
Installed-Size: 23912
Description: Install scripts for Wireguard

View File

@@ -1,3 +0,0 @@
#!/bin/sh
ln -sf /usr/bin/udptunnel /sbin/udptunnel
exit 0

View File

@@ -1,74 +0,0 @@
#!/bin/sh
# Script for building OpenWRT .ipk packages using tar by iamromulan
# Works with SDXPPINN OpenWRT - iamromulan
# This script accepts an optional path to the directory containing the `CONTROL` and `root` directories.
# Usage: ./build-ipk.sh [path]
# If no path is provided, the script will look in the current directory for `CONTROL` and `root` directories.
# This will spit out an ipk in the current directory
# Check if the script is run as root. If not, rerun with sudo.
if [ "$(id -u)" -ne 0 ]; then
echo "Script is not running as root. Re-executing with sudo..."
exec sudo "$0" "$@"
fi
# Set the default build path to the current directory
build_path="."
# Check if a path is provided as the first argument
if [ "$1" ]; then
build_path="$1"
fi
# Check if the required directories are present in the specified path
if [ ! -d "${build_path}/CONTROL" ] || [ ! -d "${build_path}/root" ]; then
echo "Error: CONTROL and root directories must be present in the specified path (${build_path})."
exit 1
fi
# Extract values from the CONTROL/control file in the specified path
pkgname=$(grep -i '^Package:' "${build_path}/CONTROL/control" | awk '{print $2}')
version=$(grep -i '^Version:' "${build_path}/CONTROL/control" | awk '{print $2}')
architecture=$(grep -i '^Architecture:' "${build_path}/CONTROL/control" | awk '{print $2}')
# Check if values are extracted correctly
if [ -z "$pkgname" ] || [ -z "$version" ] || [ -z "$architecture" ]; then
echo "Error: Failed to extract Package, Version, or Architecture from ${build_path}/CONTROL/control."
exit 1
fi
# Set the final IPK name based on the extracted values
ipkname="${pkgname}_${version}_${architecture}.ipk"
# Ensure all CONTROL scripts are executable
echo "Setting permissions for CONTROL scripts..."
chmod +x "${build_path}/CONTROL"/*
# Set ownership for CONTROL and root files
echo "Setting ownership for all package files..."
chown -R root:root "${build_path}/CONTROL"/*
chown -R root:root "${build_path}/root"/*
# Create control.tar.gz from the CONTROL directory
echo "Creating control.tar.gz..."
tar -czvf control.tar.gz -C "${build_path}/CONTROL" .
# Create data.tar.gz from the root directory
echo "Creating data.tar.gz..."
tar -czvf data.tar.gz -C "${build_path}/root" .
# Create debian-binary file (must contain exactly "2.0" without a newline)
echo -n "2.0" > debian-binary
chown -R root:root debian-binary
# Combine the components into the final .ipk file using tar
echo "Packaging ${ipkname}..."
tar -czvf "$ipkname" debian-binary control.tar.gz data.tar.gz
# Clean up intermediate files
echo "Cleaning up temporary files..."
rm -f control.tar.gz data.tar.gz debian-binary
echo "IPK package ${ipkname} created successfully using tar."

View File

@@ -1,5 +0,0 @@
config settings 'settings'
option enabled '0'
option client '0'
option server '0'

View File

@@ -1,36 +0,0 @@
config wireguard_recipe b_client
option _description "Wireguard Client"
option _role "client"
option client "1"
option port "51280"
option auto '0'
option addresses ''
option dns ''
option privatekey ''
option name ''
option keepalive '25'
option publickey ''
option presharedkey ''
option ips ''
option ra_ips '1'
option endpoint_host ''
option sport '51280'
option active '0'
option udptunnel '0'
option mtu '1280'
config wireguard_recipe b_server
option _description "Wireguard Server"
option _role "server"
option client "0"
option port "51280"
option auto '0'
option addresses ''
option publickey ''
option privatekey ''
option usepre '0'
option presharedkey ''
option active '0'
option udptunnel '0'
option udpport '54321'
option mtu '1280'

View File

@@ -1,92 +0,0 @@
#!/bin/sh /etc/rc.common
. /lib/functions.sh
# Copyright (C) 2006 OpenWrt.org
START=99
log() {
logger -t "WireGuard Init.d : " "$@"
}
chk_zone() {
local config=$1
config_get src $config src
config_get dest $config dest
if [ $src = "lan" -a $dest = "wg" ]; then
uci set firewall."$config".dest="wan"
uci commit firewall
fi
}
check_config () {
log "Check Client Interfaces"
uci delete network.wg0
uci delete network.wg1
uci commit network
uci set network.wg0=interface
uci set network.wg0.proto="wireguard"
uci set network.wg0.auto="0"
uci set network.wg0.private_key=""
uci set network.wg0.listen_port=""
uci add_list network.wg0.addresses=""
uci set network.wg1=interface
uci set network.wg1.proto="wireguard"
uci set network.wg1.auto="0"
uci set network.wg1.private_key=""
uci set network.wg1.listen_port=""
uci add_list network.wg1.addresses=""
uci commit network
uci delete firewall.wgzone
uci delete firewall.wgwforward
uci delete firewall.wwgforward
uci delete firewall.lwgforward
uci delete firewall.wglforward
uci commit firewall
uci set firewall.wgzone=zone
uci set firewall.wgzone.name="wg"
uci set firewall.wgzone.forward="ACCEPT"
uci set firewall.wgzone.output="ACCEPT"
uci set firewall.wgzone.network="wg0 wg1"
uci set firewall.wgzone.input="ACCEPT"
uci set firewall.wgzone.masq="1"
uci set firewall.wgzone.mtu_fix="1"
uci commit firewall
config_load firewall
config_foreach chk_zone forwarding
/etc/init.d/firewall restart
}
chk_start() {
local config=$1
config_get auto $config auto
uci set wireguard."$config".active="0"
uci commit wireguard
if [ $auto = '1' ]; then
/usr/lib/wireguard/startvpn.sh $config
else
/usr/lib/wireguard/stopvpn.sh $config
fi
}
start() {
uci set wireguard.settings.client="0"
uci set wireguard.settings.server="0"
uci commit wireguard
if [ ! -e /etc/openvpn ]; then
mkdir /etc/openvpn
fi
check_config
config_load wireguard
config_foreach chk_start wireguard
if [ -e /etc/crontabs/root ]; then
sed -i '/wireguard_watchdog/d' /etc/crontabs/root
fi
echo '* * * * * /usr/bin/wireguard_watchdog' >> /etc/crontabs/root
/etc/init.d/cron restart
}

View File

@@ -1,111 +0,0 @@
-- Copyright 2016-2017 Dan Luedtke <mail@danrl.com>
-- Licensed to the public under the Apache License 2.0.
module("luci.controller.wireguard", package.seeall)
I18N = require "luci.i18n"
translate = I18N.translate
function index()
local multilock = luci.model.uci.cursor():get("custom", "multiuser", "multi") or "0"
local rootlock = luci.model.uci.cursor():get("custom", "multiuser", "root") or "0"
if (multilock == "0") or (multilock == "1" and rootlock == "1") then
entry({"admin", "vpn", "wireguard"}, cbi("wireguard"), _("Wireguard"), 63)
entry( {"admin", "vpn", "wireguard", "client"}, cbi("wireguard-client"), nil ).leaf = true
entry( {"admin", "vpn", "wireguard", "server"}, cbi("wireguard-server"), nil ).leaf = true
end
entry( {"admin", "vpn", "wireguard", "wupload"}, call("conf_upload"))
entry( {"admin", "vpn", "generateconf"}, call("conf_gen"))
entry( {"admin", "vpn", "textconf"}, call("text_gen"))
entry( {"admin", "vpn", "wirestatus"}, call("wirestatus"))
end
function conf_upload()
local fs = require("nixio.fs")
local http = require("luci.http")
local util = require("luci.util")
local uci = require("luci.model.uci").cursor()
local upload = http.formvalue("ovpn_file")
local name = http.formvalue("instance_name2")
local file = "/etc/openvpn/" ..name.. ".conf"
if name and upload then
local fp
http.setfilehandler(
function(meta, chunk, eof)
local data = util.trim(chunk:gsub("\r\n", "\n")) .. "\n"
data = util.trim(data:gsub("[\128-\255]", ""))
if not fp and meta and meta.name == "ovpn_file" then
fp = io.open(file, "w")
end
if fp and data then
fp:write(data)
end
if fp and eof then
fp:close()
end
end
)
if fs.access(file) then
os.execute("/usr/lib/wireguard/conf.sh " .. name .. " " .. file)
end
end
http.redirect(luci.dispatcher.build_url('admin/vpn/wireguard'))
end
function conf_gen()
os.execute("/usr/lib/wireguard/create.sh")
end
function text_gen()
local set = luci.http.formvalue("set")
os.execute("/usr/lib/wireguard/text.sh " .. "\"" .. set .. "\"")
end
function wirestatus()
local data = { }
local last_device = ""
local wg_dump = io.popen("wg show all dump")
if wg_dump then
local line
for line in wg_dump:lines() do
local line = string.split(line, "\t")
if not (last_device == line[1]) then
last_device = line[1]
data[line[1]] = {
name = line[1],
public_key = line[3],
listen_port = line[4],
fwmark = line[5],
peers = { }
}
else
local peer = {
public_key = line[2],
endpoint = line[4],
allowed_ips = { },
latest_handshake = line[6],
transfer_rx = line[7],
transfer_tx = line[8],
persistent_keepalive = line[9]
}
if not (line[4] == '(none)') then
for ipkey, ipvalue in pairs(string.split(line[5], ",")) do
if #ipvalue > 0 then
table.insert(peer['allowed_ips'], ipvalue)
end
end
end
table.insert(data[line[1]].peers, peer)
end
end
end
luci.http.prepare_content("application/json")
luci.http.write_json(data)
end

View File

@@ -1,104 +0,0 @@
require("luci.ip")
require("luci.model.uci")
--luci.sys.call("/usr/lib/wireguard/keygen.sh " .. arg[1])
local m = Map("wireguard", translate("Wireguard Client"), translate("Set up a Wireguard Client"))
e = m:section(NamedSection, "settings", "")
m.on_init = function(self)
--luci.sys.call("/usr/lib/wireguard/keygen.sh " .. arg[1])
end
btn = e:option(Button, "_btn", translate(" "))
btn.inputtitle = translate("Back to Main Page")
btn.inputstyle = "apply"
btn.redirect = luci.dispatcher.build_url(
"admin", "vpn", "wireguard"
)
function btn.write(self, section, value)
luci.http.redirect( self.redirect )
end
local s = m:section( NamedSection, arg[1], "wireguard", translate("Client") )
ip = s:option(Value, "addresses", translate("IP Addresses :"), translate("Comma separated list of IP Addresses that server will accept from this client"));
ip.rmempty = true;
ip.optional=false;
ip.default="10.14.0.2/24";
port = s:option(Value, "port", translate("Listen Port :"), translate("Client Listen Port"));
port.rmempty = true;
port.optional=false;
port.default="51820";
ul = s:option(ListValue, "udptunnel", translate("Enable UDP over TCP :"));
ul:value("0", translate("No"))
ul:value("1", translate("Yes"))
ul.default=0
dns = s:option(Value, "dns", translate("DNS Servers :"), translate("Comma separated list of DNS Servers."));
dns.rmempty = true;
dns.optional=false;
mtu = s:option(Value, "mtu", translate("MTU :"), translate("Maximum MTU"));
mtu.rmempty = true;
mtu.optional=false;
mtu.datatype = 'range(1280,1420)';
mtu.default="1280";
pka = s:option(Value, "persistent_keepalive", translate("Persistent Keep Alive :"), translate("Seconds between keep alive messages"));
pka.rmempty = true;
pka.optional=false;
pka.datatype = 'range(1,100)';
pka.default="25";
pkey = s:option(Value, "privatekey", translate("Private Key :"), translate("Private Key supplied by the Server"));
pkey.rmempty = true;
pkey.optional=false;
il = s:option(ListValue, "wginter", translate("Interface to Use :"));
il:value("0", translate("WG0"))
il:value("1", translate("WG1"))
il.default="0"
bl = s:option(ListValue, "auto", translate("Start on Boot :"));
bl:value("0", translate("No"))
bl:value("1", translate("Yes"))
bl.default="0"
xbl = s:option(ListValue, "forward", translate("All Traffic Through Tunnel :"));
xbl:value("0", translate("No"))
xbl:value("1", translate("Yes"))
xbl.default="1"
s = m:section( NamedSection, arg[1], "wireguard", translate("Server") )
name = s:option( Value, "name", translate("Server Name :"), translate("Optional Server name"))
pukey = s:option(Value, "publickey", translate("Public Key :"), translate("Public Key of the Server"));
pukey.rmempty = true;
pukey.optional=false;
prkey = s:option(Value, "presharedkey", translate("Presharedkey :"), translate("PreShared Key from the Server"));
prkey.rmempty = true;
prkey.optional=false;
host = s:option(Value, "endpoint_host", translate("Server Address :"), translate("URL or IP Address of Server"));
host.rmempty = true;
host.optional=false;
host.default="";
sport = s:option(Value, "sport", translate("Listen Port :"), translate("Server Listen Port"));
sport.rmempty = true;
sport.optional=false;
sport.default="51820";
sip = s:option(Value, "ips", translate("Allowed IP Addresses :"), translate("Comma separated list of IP Addresses that server will accept"));
sip.rmempty = true;
sip.optional=false;
sip.default="10.14.0.0/24";
return m

View File

@@ -1,130 +0,0 @@
require("luci.ip")
require("luci.model.uci")
--luci.sys.call("/usr/lib/wireguard/keygen.sh " .. arg[1])
local m = Map("wireguard", translate("Wireguard Server"), translate("Set up a Wireguard Server"))
e = m:section(NamedSection, "settings", "")
m.on_init = function(self)
luci.sys.call("/usr/lib/wireguard/keygen.sh " .. arg[1])
end
m.on_after_save = function(self)
luci.sys.call("/usr/lib/wireguard/keygen.sh " .. arg[1] .. "&")
end
btn = e:option(Button, "_btn", translate(" "))
btn.inputtitle = translate("Back to Main Page")
btn.inputstyle = "apply"
btn.redirect = luci.dispatcher.build_url(
"admin", "vpn", "wireguard"
)
function btn.write(self, section, value)
luci.http.redirect( self.redirect )
end
local s = m:section( NamedSection, arg[1], "wireguard", translate("Server") )
ip = s:option(Value, "addresses", translate("Internal IP Address :"));
ip.rmempty = true;
ip.optional=false;
ip.default="10.14.0.1/32";
ip.datatype = "ipaddr"
host = s:option(Value, "endpoint_host", translate("Server Address :"), translate("URL or IP Address of Server"));
host.rmempty = true;
host.optional=false;
host.default="example.wireguard.org";
port = s:option(Value, "port", translate("Port :"), translate("Server Listen Port. Default is 51280"));
port.rmempty = true;
port.optional=false;
port.default="51280";
ul = s:option(ListValue, "udptunnel", "Enable UDP over TCP :");
ul:value("0", translate("No"))
ul:value("1", translate("Yes"))
ul.default=0
uport = s:option(Value, "udpport", translate("UDP over TCP Port :"), translate("Server Local TCP Port. Default is 54321"));
uport.rmempty = true;
uport.optional=false;
uport.default="54321";
uport:depends("udptunnel", "1")
pkey = s:option(DummyValue, "privatekey", translate("Private Key :"));
pkey.optional=false;
pukey = s:option(DummyValue, "publickey", translate("Public Key :"), translate("Server Public key sent to Clients"));
pukey.optional=false;
pl = s:option(ListValue, "usepre", "Use PreSharedKey :");
pl:value("0", translate("No"))
pl:value("1", translate("Yes"))
pl.default=0
prkey = s:option(DummyValue, "presharedkey", translate("PreShared Key :"), translate("PreShared Key sent to Client"));
prkey.optional=false;
prkey:depends("usepre", "1")
bl = s:option(ListValue, "auto", translate("Start on Boot :"));
bl:value("0", translate("No"))
bl:value("1", translate("Yes"))
bl.default="0"
xbl = s:option(ListValue, "forward", translate("All Traffic Through Tunnel :"));
xbl:value("0", translate("No"))
xbl:value("1", translate("Yes"))
xbl.default="1"
b3 = s:option(DummyValue, "blank", " ");
sx = s:option(Value, "_dmy1", translate(" "))
sx.template = "wireguard/conf"
ss = m:section(TypedSection, "custom" .. arg[1], translate("Clients"), translate("Clients of this server"))
ss.anonymous = true
ss.addremove = true
name = ss:option(Value, "name", translate("Client Name"))
name.optional=false;
cport = ss:option(Value, "endpoint_port", translate("Listen Port :"), translate("Port sent to Client. Default is 51280"));
cport.rmempty = true;
cport.optional=false;
cport.default="";
aip = ss:option(Value, "address", translate("Assigned IP Address :"), translate("IP Address assigned to Client"));
aip.rmempty = true;
aip.optional=false;
aip.default="10.14.0.2/32";
dns = ss:option(Value, "dns", translate("DNS Servers :"), translate("Comma separated list of DNS Servers sent to Client"));
dns.rmempty = true;
dns.optional=false;
dns.default="";
mtu = ss:option(Value, "mtu", translate("MTU :"), translate("Maximum MTU"));
mtu.rmempty = true;
mtu.optional=false;
mtu.datatype = 'range(1280,1420)';
mtu.default="1280";
aip = ss:option(Value, "allowed_ips", translate("Allowed IP Address :"), translate("Comma separated list of IP Addresses allowed from Client"));
aip.rmempty = true;
aip.optional=false;
aip.default="0.0.0.0/0,::/0";
pukey = ss:option(DummyValue, "publickey", translate("Public Key :"), translate("Client Public Key"));
pukey.optional=false;
pikey = ss:option(DummyValue, "privatekey", translate("Private Key :"), translate("Private Key sent to Client"));
pikey.optional=false;
b3 = ss:option(DummyValue, "blank", " ");
return m

View File

@@ -1,182 +0,0 @@
local fs = require "nixio.fs"
local sys = require "luci.sys"
local uci = require "luci.model.uci".cursor()
local testfullps = sys.exec("ps --help 2>&1 | grep BusyBox") --check which ps do we have
local psstring = (string.len(testfullps)>0) and "ps w" or "ps axfw" --set command we use to get pid
local m = Map("wireguard", translate("Wireguard"), translate("Set up a Wireguard VPN Tunnel on your Router"))
local s = m:section( TypedSection, "wireguard", translate("Instances"), translate("Below is a list of configured Wireguard Instances and their current state") )
s.template = "cbi/tblsection"
s.template_addremove = "wireguard/cbi-select-input-add"
s.addremove = true
s.add_select_options = { }
local cfg = s:option(DummyValue, "config")
function cfg.cfgvalue(self, section)
local file_cfg = self.map:get(section, "client")
if file_cfg == "1" then
s.extedit = luci.dispatcher.build_url("admin", "vpn", "wireguard", "client", "%s")
else
s.extedit = luci.dispatcher.build_url("admin", "vpn", "wireguard", "server", "%s")
end
end
uci:load("wireguard_recipes")
uci:foreach( "wireguard_recipes", "wireguard_recipe",
function(section)
s.add_select_options[section['.name']] =
section['_description'] or section['.name']
end
)
function s.parse(self, section)
local recipe = luci.http.formvalue(
luci.cbi.CREATE_PREFIX .. self.config .. "." ..
self.sectiontype .. ".select"
)
if recipe and not s.add_select_options[recipe] then
self.invalid_cts = true
else
TypedSection.parse( self, section )
end
end
function s.create(self, name)
local recipe = luci.http.formvalue(
luci.cbi.CREATE_PREFIX .. self.config .. "." ..
self.sectiontype .. ".select"
)
local name = luci.http.formvalue(
luci.cbi.CREATE_PREFIX .. self.config .. "." ..
self.sectiontype .. ".text"
)
if #name > 3 and not name:match("[^a-zA-Z0-9_]") then
local s = uci:section("wireguard", "wireguard", name)
if s then
local options = uci:get_all("wireguard_recipes", recipe)
for k, v in pairs(options) do
if k ~= "_role" and k ~= "_description" then
if type(v) == "boolean" then
v = v and "1" or "0"
end
uci:set("wireguard", name, k, v)
end
end
uci:save("wireguard")
uci:commit("wireguard")
if extedit then
luci.http.redirect( self.extedit:format(name) )
end
end
elseif #name > 0 then
self.invalid_cts = true
end
return 0
end
function s.remove(self, name)
local cfg_file = "/etc/openvpn/" ..name.. ".conf"
local auth_file = "/etc/openvpn/" ..name.. ".auth"
if fs.access(cfg_file) then
fs.unlink(cfg_file)
end
if fs.access(auth_file) then
fs.unlink(auth_file)
end
uci:delete("wireguard", name)
uci:save("wireguard")
uci:commit("wireguard")
end
local port = s:option( DummyValue, "client", translate("Type") )
function port.cfgvalue(self, section)
local val = AbstractValue.cfgvalue(self, section)
if val == nil then
val = 0
end
if val == "1" then
return "Client"
else
return "Server"
end
end
local addr = s:option( DummyValue, "addresses", translate("IP Addresses") )
function addr.cfgvalue(self, section)
local val = AbstractValue.cfgvalue(self, section)
return val or "----"
end
local auto = s:option( DummyValue, "udptunnel", translate("UDP over TCP") )
function auto.cfgvalue(self, section)
local val = AbstractValue.cfgvalue(self, section)
if val == nil then
val = 0
end
if val == "1" then
return "Yes"
else
return "No"
end
end
local auto = s:option( DummyValue, "auto", translate("Start on Boot") )
function auto.cfgvalue(self, section)
local val = AbstractValue.cfgvalue(self, section)
if val == nil then
val = 0
end
if val == "1" then
return "Yes"
else
return "No"
end
end
local active = s:option( DummyValue, "active", translate("Started") )
function active.cfgvalue(self, section)
local val = AbstractValue.cfgvalue(self, section)
if val == nil then
val = 0
end
if val == "1" then
return "Yes"
else
return "No"
end
end
local updown = s:option( Button, "_updown", translate("Start/Stop") )
updown._state = false
updown.redirect = luci.dispatcher.build_url(
"admin", "vpn", "wireguard"
)
function updown.cbid(self, section)
local file_cfg = self.map:get(section, "active")
if file_cfg == "1" then
pid = 1
else
pid = nil
end
self._state = pid ~= nil
self.option = self._state and "stop" or "start"
return AbstractValue.cbid(self, section)
end
function updown.cfgvalue(self, section)
self.title = self._state and "stop" or "start"
self.inputstyle = self._state and "reset" or "reload"
end
function updown.write(self, section, value)
if self.option == "stop" then
sys.call("/usr/lib/wireguard/stopvpn.sh %s" % section)
else
sys.call("/usr/lib/wireguard/startvpn.sh %s" % section)
end
luci.http.redirect( self.redirect )
end
m:section(SimpleSection).template = "wireguard/wireguard"
return m

View File

@@ -1,111 +0,0 @@
<script type="text/javascript">
//<![CDATA[
function vpn_add()
{
var vpn_name = div_add.querySelector("#instance_name1").value.replace(/[^\x00-\x7F]|[\s\.!@#$%^&*()\-+=\[\]{};':"\\|,<>\/?]/g,'');
var vpn_template = div_add.querySelector("#instance_template").value;
var form = document.getElementsByName('cbi')[0];
if (!vpn_name || !vpn_name.length)
{
return info_message(vpn_output, "<%=pcdata(translate("The 'Name' field must not be empty!"))%>", 2000);
}
document.getElementById("instance_name1").value = vpn_name;
if (document.getElementById("cbi-wireguard-" + vpn_name) != null)
{
return info_message(vpn_output, "<%=pcdata(translate("Instance with that name already exists!"))%>", 2000);
}
if (!vpn_template || !vpn_template.length)
{
return info_message(vpn_output, "<%=pcdata(translate("Please select a valid VPN template!"))%>", 2000);
}
if (form)
{
form.submit();
}
}
function vpn_upload()
{
var vpn_name = div_upload.querySelector("#instance_name2").value.replace(/[^\x00-\x7F]|[\s\.!@#$%^&*()\-+=\[\]{};':"\\|,<>\/?]/g,'');
var vpn_file = document.getElementById("ovpn_file").value;
var form = document.getElementsByName('cbi')[0];
if (!vpn_name || !vpn_name.length)
{
return info_message(vpn_output, "<%=pcdata(translate("The 'Name' field must not be empty!"))%>", 2000);
}
document.getElementById("instance_name2").value = vpn_name;
if (document.getElementById("cbi-wireguard-" + vpn_name) != null)
{
return info_message(vpn_output, "<%=pcdata(translate("Instance with that name already exists!"))%>", 2000);
}
if (!vpn_file || !vpn_file.length)
{
return info_message(vpn_output, "<%=pcdata(translate("Please select a valid CONF config file to upload!"))%>", 2000);
}
if (form)
{
form.enctype = 'multipart/form-data';
form.action = '<%=url('admin/vpn/wireguard/wupload')%>';
form.submit();
}
}
function info_message(output, msg, timeout)
{
timeout = timeout || 0;
output.innerHTML = '<em>' + msg + '</em>';
if (timeout > 0)
{
setTimeout(function(){ output.innerHTML=""}, timeout);
}
}
//]]>
</script>
<%+wireguard/ovpn_css%>
<div class="cbi-section-node">
<div class="table cbi-section-table">
<h4><%:Template based configuration%></h4>
<div class="tr cbi-section-table-row" id="div_add">
<div class="td left">
<input type="text" maxlength="20" placeholder="Instance name" name="cbi.cts.<%=self.config%>.<%=self.sectiontype%>.text" id="instance_name1" />
</div>
<div class="td left">
<select id="instance_template" name="cbi.cts.<%=self.config%>.<%=self.sectiontype%>.select">
<option value="" selected="selected" disabled="disabled"><%:Select template ...%></option>
<%- for k, v in luci.util.kspairs(self.add_select_options) do %>
<option value="<%=k%>"><%=luci.xml.pcdata(v)%></option>
<% end -%>
</select>
</div>
<div class="td left">
<input class="cbi-button cbi-button-add" type="submit" onclick="vpn_add(); return false;" value="<%:Add%>" title="<%:Add template based configuration%>" /><br />
</div>
</div>
<h4><%:Conf configuration file upload%></h4>
<div class="tr cbi-section-table-row" id="div_upload">
<div class="td left">
<input type="text" maxlength="20" placeholder="Instance name" name="instance_name2" id="instance_name2" />
</div>
<div class="td left">
<input type="file" name="ovpn_file" id="ovpn_file" accept="application/x-wireguard-profile,.conf" />
</div>
<div class="td left">
<input class="cbi-button cbi-button-add" type="submit" onclick="vpn_upload(); return false;" value="<%:Upload%>" title="<%:Upload conf file%>" />
</div>
</div>
</div>
<div class="vpn-output">
<span id="vpn_output"></span>
</div>
</div>

View File

@@ -1,27 +0,0 @@
<script type="text/javascript" src="<%=resource%>/xhr.js"></script>
<script type="text/javascript">//<![CDATA[
function generateconf()
{
XHR.get('<%=luci.dispatcher.build_url("admin", "vpn", "generateconf")%>',
null,
function(x, rv)
{
window.open('http://'+window.location.hostname+'/package/wgconf.tar.gz', '_self')
}
);
}
//]]></script>
<fieldset class="cbi-section" id="cbi-family">
<table width="550" border="0">
<tr>
<td width="20%">&nbsp;</td>
<td width="17%"><input type="button" type="submit" id="generate" class="cbi-button cbi-button-apply" value="<%:Generate Conf Files%>" onclick="return generateconf()" /></td>
<td width="17%">&nbsp;</td>
<td width="46%">&nbsp;</td>
</tr>
</table>
</fieldset>

View File

@@ -1,38 +0,0 @@
<style type="text/css">
h4
{
white-space: nowrap;
border-bottom: 0px;
margin: 10px 5px 5px 5px;
}
.tr
{
border: 0px;
text-align: left;
}
.vpn-output
{
box-shadow: none;
margin: 10px 5px 5px 5px;
color: #a22;
}
textarea
{
border: 1px solid #cccccc;
padding: 5px;
font-size: 12px;
font-family: monospace;
resize: none;
white-space: pre;
overflow-wrap: normal;
overflow-x: scroll;
}
a
{
line-height: 1.5;
}
hr
{
margin: 0.5em 0;
}
</style>

View File

@@ -1,30 +0,0 @@
<%#
Copyright 2008 Steven Barth <steven@midlink.org>
Copyright 2008 Jo-Philipp Wich <jow@openwrt.org>
Licensed to the public under the Apache License 2.0.
-%>
<%+openvpn/ovpn_css%>
<div class="cbi-section">
<h3>
<a href="<%=url('admin/vpn/wireguard')%>"><%:Overview%></a> &#187;
<%=luci.i18n.translatef("Instance \"%s\"", self.instance)%>
</h3>
<% if self.mode == "basic" then %>
<a href="<%=url('admin/vpn/wireguard/advanced', self.instance, "Service")%>"><%:Switch to advanced configuration%> &#187;</a><p/>
<hr />
<% elseif self.mode == "advanced" then %>
<a href="<%=url('admin/vpn/wireguard/basic', self.instance)%>"><%:Switch to basic configuration%> &#187;</a><p/>
<hr />
<%:Configuration category%>:
<% for i, c in ipairs(self.categories) do %>
<% if c == self.category then %>
<strong><%=translate(c)%></strong>
<% else %>
<a href="<%=luci.dispatcher.build_url("admin", "vpn", "wireguard", "advanced", self.instance, c)%>"><%=translate(c)%></a>
<% end %>
<% if next(self.categories, i) then %>|<% end %>
<% end %>
<% end %>
</div>

View File

@@ -1,61 +0,0 @@
<%
%>
<script type="text/javascript" src="<%=resource%>/xhr.js"></script>
<script type="text/javascript">//<![CDATA[
function uploadc(btn)
{
var conf = document.getElementById("conf").value;
if ( conf == "" )
{
alert("<%:You must enter a Conf file!!%>");
return false;
}
var iname = document.getElementById("iname").value;
if ( iname == "" )
{
alert("<%:You must enter an Instance name!!%>");
return false;
}
var boot = document.getElementById('boot').checked;
bootn = "0";
if ( boot == true )
{
bootn= "1";
}
confile = bootn + "?" + iname + "?" + conf +"\n?";
XHR.get('<%=luci.dispatcher.build_url("admin", "vpn", "textconf")%>',
{ set: confile },
function(x, rv)
{
window.location.reload(false);
}
);
}
//]]></script>
<fieldset class="cbi-section" id="cbi-family">
<legend><%:Paste Configuration File Here%></legend>
<table id="ctxt" width="700" border="0" style="display:table;">
<tr>
<td width="50%">
<textarea name="conf" id="conf" rows="10" style="width: 600px;" maxlength="1000"></textarea>
</td>
</tr>
</table>
<table id="btxt" width="700" border="0" style="display:table;">
<tr>
<td width="10%"><input type="button" id="apply1" class="cbi-button cbi-button-apply" value="<%:Upload Conf File%>" onclick="return uploadc(this)" /></td>
<td width="10%"><div align="right"><strong><%:Instance Name : %></strong></div></td>
<td width="12%"><input type="text" name="iname" id="iname" class="cbi-input-text" style="width: 150px;" maxlength="100" value="SardisTel"></input></td>
<td width="10%"><div align="right"><strong><%:Start on Boot : %></strong></div></td>
<td width="8%">
<input type="checkbox" id="boot" checked />
</td>
<td width="50%">&nbsp;</td>
</tr>
</table>
</fieldset>

View File

@@ -1,228 +0,0 @@
<%#
Copyright 2016-2017 Dan Luedtke <mail@danrl.com>
Licensed to the public under the Apache License 2.0.
-%>
<%
-%>
<script type="text/javascript">//<![CDATA[
function bytes_to_str(bytes) {
bytes = parseFloat(bytes);
if (bytes < 1) { return "0 B"; }
var sizes = ['B', 'KiB', 'MiB', 'GiB', 'TiB', 'PiB'];
var i = parseInt(Math.floor(Math.log(bytes) / Math.log(1024)));
return Math.round(bytes / Math.pow(1024, i), 2) + ' ' + sizes[i];
};
function timestamp_to_str(timestamp) {
if (timestamp < 1) {
return '<%:Never%>';
}
var now = new Date();
var seconds = (now.getTime() / 1000) - timestamp;
var ago = "";
if (seconds < 60) {
ago = parseInt(seconds) + '<%:s ago%>';
} else if (seconds < 3600) {
ago = parseInt(seconds / 60) + '<%:m ago%>';
} else if (seconds < 86401) {
ago = parseInt(seconds / 3600) + '<%:h ago%>';
} else {
ago = '<%:over a day ago%>';
}
var t = new Date(timestamp * 1000);
return t.toUTCString() + ' (' + ago + ')';
}
XHR.poll(5, '<%=luci.dispatcher.build_url("admin", "vpn", "wirestatus")%>', null,
function(x, data) {
both = {};
bothbp={};
iii = 1;
for (var key in data) {
if (!data.hasOwnProperty(key)) { continue; }
var ifname = key;
var iface = data[key];
var s = "";
if (iface.public_key == '(none)') {
s += '<em><%:Interface does not have a public key!%></em>';
} else {
s += String.format(
'<strong><%:Public Key%>: </strong>%s',
iface.public_key
);
}
if (iface.listen_port > 0) {
s += String.format(
'<br /><strong><%:Listen Port%>: </strong>%s',
iface.listen_port
);
}
if (iface.fwmark != 'off') {
s += String.format(
'<br /><strong><%:Firewall Mark%>: </strong>%s',
iface.fwmark
);
}
if ( iii == 1 )
{
document.getElementById("iinfo").innerHTML = s;
document.getElementById("leg").innerHTML = ifname;
}
else
{
document.getElementById("iinfo1").innerHTML = s;
document.getElementById("leg1").innerHTML = ifname;
}
for (var i = 0, ilen = iface.peers.length; i < ilen; i++) {
var peer = iface.peers[i];
var s = String.format(
'<strong><%:Public Key%>: </strong>%s',
peer.public_key
);
if (peer.endpoint != '(none)') {
s += String.format(
'<br /><strong><%:Endpoint%>: </strong>%s',
peer.endpoint
);
}
if (peer.allowed_ips.length > 0) {
s += '<br /><strong><%:Allowed IPs%>:</strong>';
for (var k = 0, klen = peer.allowed_ips.length; k < klen; k++) {
s += '<br />&nbsp;&nbsp;&bull;&nbsp;' + peer.allowed_ips[k];
}
}
if (peer.persistent_keepalive != 'off') {
s += String.format(
'<br /><strong><%:Persistent Keepalive%>: </strong>%ss',
peer.persistent_keepalive
);
}
var icon = '<img src="<%=resource%>/icons/wireguard_disabled.png" />';
var now = new Date();
if (((now.getTime() / 1000) - peer.latest_handshake) < 140) {
icon = '<img src="<%=resource%>/icons/wireguard.png" />';
}
s += String.format(
'<br /><strong><%:Latest Handshake%>: </strong>%s',
timestamp_to_str(peer.latest_handshake)
);
s += String.format(
'<br /><strong><%:Data Received%>: </strong>%s' +
'<br /><strong><%:Data Transmitted%>: </strong>%s',
bytes_to_str(peer.transfer_rx),
bytes_to_str(peer.transfer_tx)
);
if ( iii == 1 )
{
document.getElementById("config").innerHTML = icon;
document.getElementById("info").innerHTML = s;
}
else
{
document.getElementById("config1").innerHTML = icon;
document.getElementById("info1").innerHTML = s;
}
}
iii = iii + 1;
}
});
//]]></script>
<h2><%:WireGuard Status%></h2>
<fieldset class="cbi-section">
<div>
<table width="900" border="0">
<tr>
<td width="50px" style="vertical-align:center;font-size : 25px">
<div><%:Interface %></div>
</td>
<td width="100px" id="leg" style="width:100px; text-align:left; padding:3px;font-size : 25px">&nbsp;</td>
<td width="650px">&nbsp;</td>
</tr>
</table>
<table width="900" border="0">
<tr>
<td width="20px">&nbsp;</td>
<td width="150px" style="vertical-align:center;font-size : 20px">
<div><%:Configuration%></div>
</td>
<td width="100px" id="config" style="width:16px; text-align:center; padding:3px">&nbsp;</td>
<td width="50px">&nbsp;</td>
<td width="580px">
<div id="info" style="vertical-align:middle; padding: 3px">
<em><%:Collecting data...%></em>
</div>
</td>
</tr>
<tr>
<td>&nbsp;</td>
<td style="vertical-align:center;font-size : 20px">
<div><%:Peer%></div>
</td>
<td>&nbsp;</td>
<td>&nbsp;</td>
<td>
<div id="iinfo" style="vertical-align:middle; padding: 3px">
<em><%:Collecting data...%></em>
</div>
</td>
</tr>
</table>
<table width="900" border="0" id="second1">
<tr>
<td width="50px" style="vertical-align:center;font-size : 25px">
<div><%:Interface %></div>
</td>
<td width="100px" id="leg1" style="width:100px; text-align:left; padding:3px;font-size : 25px">&nbsp;</td>
<td width="650px">&nbsp;</td>
</tr>
</table>
<table width="900" border="0" id="second">
<tr>
<td width="20px">&nbsp;</td>
<td width="150px" style="vertical-align:center;font-size : 20px">
<div><%:Configuration%></div>
</td>
<td width="100px" id="config1" style="width:16px; text-align:center; padding:3px">&nbsp;</td>
<td width="50px">&nbsp;</td>
<td width="580px">
<div id="info1" style="vertical-align:middle; padding: 3px">
<em><%:Collecting data...%></em>
</div>
</td>
</tr>
<tr>
<td>&nbsp;</td>
<td style="vertical-align:center;font-size : 20px">
<div><%:Peer%></div>
</td>
<td>&nbsp;</td>
<td>&nbsp;</td>
<td>
<div id="iinfo1" style="vertical-align:middle; padding: 3px">
<em><%:Collecting data...%></em>
</div>
</td>
</tr>
</table>
<!--
<table id="cmdtxt" width="700" border="0" style="display:table;">
<tr>
<td width="100%">
<textarea readonly="readonly" name="attxt" id="attxt" rows="6" style="width: 600px;" maxlength="160"></textarea>
</td>
</tr>
</table> -->
</div>
</fieldset>

View File

@@ -1,134 +0,0 @@
#!/bin/sh
log() {
modlog "Wireguard Conf" "$@"
}
name=$1
file=$2
auto=$3
if [ -z $auto ]; then
auto="0"
fi
extract() {
line=$1
PD=$(echo "$line" | grep "#")
if [ ! -z "$PD" ]; then
return
fi
PRK=$(echo "$line" | grep "PrivateKey" | tr " " ",")
if [ ! -z "$PRK" ]; then
PrivateKey=$(echo $PRK | cut -d, -f3)
fi
PRK=$(echo "$line" | grep "PublicKey" | tr " " ",")
if [ ! -z "$PRK" ]; then
PublicKey=$(echo $PRK | cut -d, -f3)
fi
PRK=$(echo "$line" | grep "PresharedKey" | tr " " ",")
if [ ! -z "$PRK" ]; then
PreSharedKey=$(echo $PRK | cut -d, -f3)
fi
INTER=$(echo "$line" | grep "WGinterface" | tr " " ",")
if [ ! -z "$INTER" ]; then
wginter=$(echo $INTER | cut -d, -f3)
if [ "$wginter" -gt 1 ]; then
wginter="1"
fi
fi
PRK=$(echo "$line" | grep "Address" | tr " " "#")
if [ ! -z "$PRK" ]; then
if [ -z $Address ]; then
Address=$(echo $PRK | cut -d# -f3)
else
Address=$Address","$(echo $PRK | cut -d# -f3)
fi
fi
PRK=$(echo "$line" | grep "dns" | tr " " "#")
if [ ! -z "$PRK" ]; then
dns=$(echo $PRK | cut -d# -f3)
fi
PRK=$(echo "$line" | grep "DNS" | tr " " "#")
if [ ! -z "$PRK" ]; then
dns=$(echo $PRK | cut -d# -f3)
fi
PRK=$(echo "$line" | grep "ListenPort" | tr " " ",")
if [ ! -z "$PRK" ]; then
listenport=$(echo $PRK | cut -d, -f3)
fi
PRK=$(echo "$line" | grep "AllowedIPs" | tr " " "#")
if [ ! -z "$PRK" ]; then
if [ -z $allowedips ]; then
allowedips=$(echo $PRK | cut -d# -f3)
else
allowedips=$allowedips","$(echo $PRK | cut -d# -f3)
fi
fi
PRK=$(echo "$line" | grep "Endpoint" | tr " " ",")
if [ ! -z "$PRK" ]; then
endpoint=$(echo $PRK | cut -d, -f3)
fi
MTU=$(echo "$line" | grep "MTU" | tr " " ",")
if [ ! -z "$MTU" ]; then
mtu=$(echo $MTU | cut -d, -f3)
fi
}
listenport="51280"
dns=""
sed -i -e "s!PrivateKey= !PrivateKey=!g" $file
sed -i -e "s!PrivateKey=!PrivateKey = !g" $file
sed -i -e "s!PublicKey= !PublicKey=!g" $file
sed -i -e "s!PublicKey=!PublicKey = !g" $file
sed -i -e "s!PresharedKey= !PresharedKey=!g" $file
sed -i -e "s!PresharedKey=!PresharedKey = !g" $file
sed -i -e "s!Address= !Address=!g" $file
sed -i -e "s!Address=!Address = !g" $file
sed -i -e "s!WGinterface=!WGinterface = !g" $file
sed -i -e "s!WGinterface= !WGinterface = !g" $file
sed -i -e "s!dns= !dns=!g" $file
sed -i -e "s!dns=!dns = !g" $file
sed -i -e "s!DNS= !DNS=!g" $file
sed -i -e "s!DNS=!DNS = !g" $file
sed -i -e "s!ListenPort= !ListenPort=!g" $file
sed -i -e "s!ListenPort=!ListenPort = !g" $file
sed -i -e "s!AllowedIPs= !AllowedIPs=!g" $file
sed -i -e "s!AllowedIPs=!AllowedIPs = !g" $file
sed -i -e "s!Endpoint= !Endpoint=!g" $file
sed -i -e "s!Endpoint=!Endpoint = !g" $file
sed -i -e "s!MTU= !MTU=!g" $file
sed -i -e "s!MTU=!MTU = !g" $file
while IFS= read -r linex
do
extract "$linex"
done < $file
extract "$linex"
PRK=$(echo "$endpoint" | tr ":" ",")
endpoint=$(echo $PRK | cut -d, -f1)
sport=$(echo $PRK | cut -d, -f2)
if [ -z "$wginter" ]; then
wginter="0"
fi
uci delete wireguard.$name
uci set wireguard.$name=wireguard
uci set wireguard.$name.auto=$auto
uci set wireguard.$name.client="1"
uci set wireguard.$name.active="0"
uci set wireguard.$name.privatekey="$PrivateKey"
uci set wireguard.$name.presharedkey="$PreSharedKey"
uci set wireguard.$name.port="$listenport"
uci set wireguard.$name.addresses="$Address"
uci set wireguard.$name.dns="$dns"
uci set wireguard.$name.wginter="$wginter"
uci set wireguard.$name.publickey="$PublicKey"
uci set wireguard.$name.endpoint_host="$endpoint"
uci set wireguard.$name.ips="$allowedips"
uci set wireguard.$name.name="$name"
uci set wireguard.$name.sport="$sport"
uci set wireguard.$name.mtu="$mtu"
uci set wireguard.$name.persistent_keepalive='25'
uci commit wireguard
rm -f $file

View File

@@ -1,81 +0,0 @@
#!/bin/sh
. /lib/functions.sh
log() {
logger -t "Wireguard Conf" "$@"
}
WG=$(cat /tmp/wginst)
do_create() {
local config=$1
config_get name $config name
if [ -z $name ]; then
name=$config
fi
echo "----Start Conf File for "$name" ----" >> ${PKI_DIR}/package/wg.conf
echo "[Interface]" >> ${PKI_DIR}/package/wg.conf
config_get privatekey $config privatekey
echo "PrivateKey = "$privatekey >> ${PKI_DIR}/package/wg.conf
config_get address $config address
echo "Address = "$address >> ${PKI_DIR}/package/wg.conf
config_get endpoint_port $config endpoint_port
if [ ! -z $endpoint_port ]; then
echo "ListenPort = "$endpoint_port >> ${PKI_DIR}/package/wg.conf
fi
config_get dns $config dns
if [ ! -z $dns ]; then
echo "DNS = "$dns >> ${PKI_DIR}/package/wg.conf
fi
config_get mtu $config mtu
if [ ! -z $mtu ]; then
echo "MTU = "$mtu >> ${PKI_DIR}/package/wg.conf
fi
config_get wginter $config wginter
if [ -z"$wginter"]; then
wginter=0
fi
#echo "PrivateKey = "$wginter >> ${PKI_DIR}/package/wg.conf
echo " " >> ${PKI_DIR}/package/wg.conf
echo "[Peer]" >> ${PKI_DIR}/package/wg.conf
PUB=$(uci get wireguard."$WG".publickey)
echo "PublicKey = "$PUB >> ${PKI_DIR}/package/wg.conf
USE=$(uci get wireguard."$WG".usepre)
if [ $USE = "1" ]; then
PRE=$(uci get wireguard."$WG".presharedkey)
echo "PresharedKey = "$PRE >> ${PKI_DIR}/package/wg.conf
fi
HOST=$(uci get wireguard."$WG".endpoint_host)
PORT=$(uci get wireguard."$WG".port)
if [ ! -z $PORT ]; then
HOST=$HOST":"$PORT
fi
echo "Endpoint = "$HOST >> ${PKI_DIR}/package/wg.conf
config_get allowed_ips $config allowed_ips
echo "AllowedIPs = "$allowed_ips >> ${PKI_DIR}/package/wg.conf
echo "----EndConf File for "$name" ----" >> ${PKI_DIR}/package/wg.conf
echo " " >> ${PKI_DIR}/package/wg.conf
}
#PKI_DIR="/tmp/wireguard"
PKI_DIR="/www"
#rm -rfv "$PKI_DIR"
#mkdir -p ${PKI_DIR}
#chmod -R 0777 ${PKI_DIR}
cd ${PKI_DIR}
mkdir -p package
cd ..
chmod -R 0777 ${PKI_DIR}/package
#rm -rfv "/www/package"
#ln -s ${PKI_DIR}/package /www/package
rm -f ${PKI_DIR}/package/wg.conf
config_load wireguard
config_foreach do_create custom$WG
cd ${PKI_DIR}/package
tar -czf wgconf.tar.gz wg.conf

View File

@@ -1,68 +0,0 @@
#!/bin/sh
. /lib/functions.sh
log() {
modlog "Wireguard KeyGen" "$@"
}
WG=$1
ww=$(echo "$WG" | grep "https")
if [ ! -z "$ww" ]; then
exit 0
fi
echo "$WG" > /tmp/wginst
sleep 5
EXST=$(uci get wireguard."$WG")
if [ -z $EXST ]; then
uci set wireguard."$WG"="wireguard"
uci commit wireguard
fi
PRIV=$(uci get wireguard."$WG".privatekey)
if [ -z $PRIV ]; then
umask u=rw,g=,o=
wg genkey | tee /tmp/wgserver.key | wg pubkey > /tmp/wgclient.pub
wg genpsk > /tmp/wg.psk
WG_KEY="$(cat /tmp/wgserver.key)" # private key
WG_PSK="$(cat /tmp/wg.psk)" # shared key
WG_PUB="$(cat /tmp/wgclient.pub)" # public key to be used on other end
rm -f /tmp/wgserver.key
rm -f /tmp/wg.psk
rm -f /tmp/wgclient.pub
uci set wireguard."$WG".privatekey=$WG_KEY
uci set wireguard."$WG".publickey=$WG_PUB
uci set wireguard."$WG".presharedkey=$WG_PSK
uci commit wireguard
fi
do_custom() {
local config=$1
config_get privatekey $config privatekey
if [ -z "$privatekey" ]; then
umask u=rw,g=,o=
wg genkey | tee /tmp/wgserver.key | wg pubkey > /tmp/wgclient.pub
wg genpsk > /tmp/wg.psk
WG_KEY="$(cat /tmp/wgserver.key)" # private key
WG_PSK="$(cat /tmp/wg.psk)" # shared key
WG_PUB="$(cat /tmp/wgclient.pub)" # public key to be used on other end
rm -f /tmp/wgserver.key
rm -f /tmp/wg.psk
rm -f /tmp/wgclient.pub
log "$WG_KEY"
uci set wireguard."$config".privatekey=$WG_KEY
uci set wireguard."$config".publickey=$WG_PUB
uci set wireguard."$config".presharedkey=$WG_PSK
uci set wireguard."$config".persistent_keepalive='25'
uci set wireguard."$config".route_allowed_ips='1'
fi
}
config_load wireguard
config_foreach do_custom custom$WG
uci commit wireguard

View File

@@ -1,328 +0,0 @@
#!/bin/sh
. /lib/functions.sh
log() {
logger -t "Wireguard Start" "$@"
}
WG=$1
chk_zone() {
local config=$1
config_get src $config src
config_get dest $config dest
if [ $src = "lan" -a $dest = "wan" ]; then
uci set firewall."$config".dest="wg"
uci commit firewall
fi
}
do_dns() {
cdns=$1
local ifce=$2
ldns=$(uci -q get network.wg$ifce.dns)
ex=$(echo "$ldns" | grep "$cdns")
if [ -z $ex ]; then
log "Add DNS $cdns to WG$ifce"
uci add_list network.wg$ifce.dns="$cdns"
uci commit network
/etc/init.d/network reload
fi
}
do_port() {
PORT=$1
udp=$2
# look for rule for this port
INB="inbound"$PORT$udp
RULE=$(uci -q get firewall.$INB)
if [ -z $RULE ]; then
uci set firewall.$INB=rule
uci set firewall.$INB.name=$INB
uci set firewall.$INB.target=ACCEPT
uci set firewall.$INB.src=*
uci set firewall.$INB.proto=$udp
uci set firewall.$INB.dest_port=$PORT
uci commit firewall
/etc/init.d/firewall reload
fi
}
do_delete() {
local config=$1
uci delete network.$1
}
create_speer() {
local config=$1
uci set network.$config="wireguard_wg1"
config_get persistent_keepalive $config persistent_keepalive
uci set network.$config.persistent_keepalive="$persistent_keepalive"
config_get route_allowed_ips $config route_allowed_ips
uci set network.$config.route_allowed_ips="$route_allowed_ips"
config_get publickey $config publickey
uci set network.$config.public_key="$publickey"
usepre=$(uci -q get wireguard.$WG.usepre)
log "$usepre"
if [ $usepre = "1" ]; then
presharedkey=$(uci -q get wireguard.$WG.presharedkey)
log "$presharedkey"
uci set network.$config.preshared_key="$presharedkey"
fi
config_get allowed_ips $config allowed_ips
allowed_ips=$allowed_ips","
ips=$(echo $allowed_ips | cut -d, -f1)
i=1
while [ ! -z $ips ]
do
uci add_list network.$config.allowed_ips="$ips"
i=$((i+1))
ips=$(echo $allowed_ips | cut -d, -f$i)
done
}
create_cpeer() {
local config=$1
local ifce=$2
uci set network.$config="wireguard_wg$ifce"
publickey=$(uci -q get wireguard."$config".publickey)
uci set network.$config.public_key="$publickey"
presharedkey=$(uci -q get wireguard."$WG".presharedkey)
if [ ! -z $presharedkey ]; then
uci set network.$config.preshared_key="$presharedkey"
fi
persistent_keepalive=$(uci -q get wireguard."$config".persistent_keepalive)
if [ -z $persistent_keepalive ]; then
persistent_keepalive=25
fi
uci set network.$config.persistent_keepalive="$persistent_keepalive"
route_allowed_ips=1
uci set network.$config.route_allowed_ips="$route_allowed_ips"
if [ $UDP = 1 ]; then
endpoint_host="127.0.0.1"
uci set network.$config.endpoint_host="$endpoint_host"
sport=$(uci -q get wireguard."$config".port)
if [ -z $sport ]; then
sport="54321"
fi
uci set network.$config.endpoint_port="$sport"
else
endpoint_host=$(uci -q get wireguard."$config".endpoint_host)
uci set network.$config.endpoint_host="$endpoint_host"
sport=$(uci -q get wireguard."$config".sport)
if [ -z $sport ]; then
sport="51280"
fi
uci set network.$config.endpoint_port="$sport"
fi
ips=$(uci -q get wireguard."$config".ips)","
cips=$(echo $ips | cut -d, -f1)
i=1
while [ ! -z $cips ]
do
uci add_list network.$config.allowed_ips="$cips"
i=$((i+1))
cips=$(echo $ips | cut -d, -f$i)
done
}
handle_server() {
config_foreach do_delete wireguard_wg1
uci delete network.wg1
uci set network.wg1="interface"
uci set network.wg1.proto="wireguard"
auto=$(uci -q get wireguard."$WG".auto)
if [ -z $auto ]; then
auto="0"
fi
uci set network.wg1.auto="$auto"
port=$(uci -q get wireguard."$WG".port)
if [ -z $port ]; then
port="51280"
fi
uci set network.wg1.listen_port="$port"
do_port $port udp
privatekey=$(uci -q get wireguard."$WG".privatekey)
uci set network.wg1.private_key="$privatekey"
ips=$(uci -q get wireguard."$WG".addresses)","
cips=$(echo $ips | cut -d, -f1)
i=1
while [ ! -z $cips ]
do
uci add_list network.wg1.addresses="$cips"
i=$((i+1))
cips=$(echo $ips | cut -d, -f"$i")
if [ -z $cips ]; then
break
fi
done
config_load wireguard
config_foreach create_speer custom$WG
uci commit network
}
handle_client() {
ifce=$1
config_foreach do_delete wireguard_wg$ifce
uci delete network.wg$ifce
uci set network.wg$ifce="interface"
uci set network.wg$ifce.proto="wireguard"
uci set network.wg$ifce.metric="1"
auto=$(uci -q get wireguard."$WG".auto)
if [ -z $auto ]; then
auto="0"
fi
uci set network.wg$ifce.auto="$auto"
mtu=$(uci -q get wireguard."$WG".mtu)
if [ ! -z $mtu ]; then
uci set network.wg$ifce.mtu="$mtu"
fi
dns=$(uci -q get wireguard."$WG".dns)
if [ ! -z $dns ]; then
do_dns $dns $ifce
fi
port=$(uci -q get wireguard."$WG".port)
if [ -z $port ]; then
port="51280"
fi
uci set network.wg$ifce.listen_port="$port"
do_port $port udp
privatekey=$(uci -q get wireguard."$WG".privatekey)
uci set network.wg$ifce.private_key="$privatekey"
ips=$(uci -q get wireguard."$WG".addresses)","
cips=$(echo $ips | cut -d, -f1)
i=1
while [ ! -z "$cips" ]
do
uci add_list network.wg$ifce.addresses="$cips"
i=$((i+1))
cips=$(echo "$ips" | cut -d, -f"$i")
if [ -z "$cips" ]; then
break
fi
done
uci add_list network.wg$ifce.addresses="::/0"
create_cpeer $WG $ifce
uci commit network
}
udp_server() {
local config=$1
udpport=$(uci -q get wireguard."$WG".udpport)
if [ -z $udpport ]; then
udpport="54321"
fi
port=$(uci -q get wireguard."$WG".port)
if [ -z $port ]; then
port="54321"
fi
do_port $udpport tcp
udptunnel -s -v "0.0.0.0:"$udpport "127.0.0.1:"$port &
#log "udptunnel -s -v 0.0.0.0:$udpport 127.0.0.1:$port"
}
udp_client() {
local config=$1
port=$(uci -q get wireguard."$WG".port)
if [ -z $port ]; then
port="54321"
fi
endpoint_host=$(uci -q get wireguard.$WG.endpoint_host)
sport=$(uci -q get wireguard.$WG.sport)
if [ -z $sport ]; then
sport="51280"
fi
udptunnel "127.0.0.1:"$port $endpoint_host":"$sport &
#log "udptunnel 127.0.0.1:$port $endpoint_host:$sport"
}
forward=$(uci -q get wireguard."$WG".forward)
if [ "$forward" != "0" ]; then
config_load firewall
config_foreach chk_zone forwarding
else
uci set firewall.wgwforward=forwarding
uci set firewall.wgwforward.dest="wan"
uci set firewall.wgwforward.src="wg"
uci set firewall.wwgforward=forwarding
uci set firewall.wwgforward.dest="wg"
uci set firewall.wwgforward.src="wan"
uci set firewall.lwgforward=forwarding
uci set firewall.lwgforward.dest="wg"
uci set firewall.lwgforward.src="lan"
uci set firewall.wglforward=forwarding
uci set firewall.wglforward.dest="lan"
uci set firewall.wglforward.src="wg"
uci commit firewall
fi
/etc/init.d/firewall restart
config_load network
SERVE=$(uci -q get wireguard."$WG".client)
if [ $SERVE = "0" ]; then
running=$(uci -q get wireguard.settings.server)
if [ $running = 1 ]; then
exit 0
fi
UDP=$(uci -q get wireguard."$WG".udptunnel)
if [ $UDP = 1 ]; then
udp_server $WG
fi
handle_server
uci commit network
ifup wg1
sleep 2
uci set wireguard.settings.server="1"
else
running=$(uci -q get wireguard.settings.client)
log "Client running $running"
INTER=$(uci -q get wireguard."$WG".wginter)
if [ -z "$INTER" ]; then
INTER=0
fi
UDP=$(uci -q get wireguard."$WG".udptunnel)
if [ $UDP = 1 ]; then
udp_client $WG
fi
handle_client $INTER
uci commit network
log "Start Interface"
ifup wg$INTER
sleep 2
uci set wireguard.settings.client="1"
if [ -e /usr/lib/wireguard/wiremwan3.sh ]; then
/usr/lib/wireguard/wiremwan3.sh start
fi
fi
uci set wireguard."$WG".active="1"
uci commit wireguard
service firewall reload

View File

@@ -1,75 +0,0 @@
#!/bin/sh
. /lib/functions.sh
log() {
logger -t "Wireguard Stop" "$@"
}
chk_zone() {
local config=$1
config_get src $config src
config_get dest $config dest
if [ $src = "lan" -a $dest = "wg" ]; then
uci set firewall."$config".dest="wan"
uci commit firewall
fi
}
WG=$1
forward=$(uci -q get wireguard."$WG".forward)
if [ "$forward" != "0" ]; then
config_load firewall
config_foreach chk_zone forwarding
else
uci delete firewall.wgwforward
uci delete firewall.wwgforward
uci delete firewall.lwgforward
uci delete firewall.wglforward
uci commit firewall
fi
/etc/init.d/firewall restart
SERVE=$(uci get wireguard."$WG".client)
if [ $SERVE = "0" ]; then
ifdown wg1
uci set wireguard.settings.server="0"
uci delete network.wg1
uci set network.wg1=interface
uci set network.wg1.proto="wireguard"
uci set network.wg1.auto="0"
uci set network.wg1.private_key=""
uci set network.wg1.listen_port=""
uci add_list network.wg1.addresses=""
uci commit network
else
INTER=$(uci -q get wireguard."$WG".wginter)
if [ -z "$INTER" ]; then
INTER=0
fi
ifdown wg$INTER
uci set wireguard.settings.client="0"
uci delete network.wg$INTER
uci set network.wg$INTER=interface
uci set network.wg$INTER.proto="wireguard"
uci set network.wg$INTER.auto="0"
uci set network.wg$INTER.private_key=""
uci set network.wg$INTER.listen_port=""
uci add_list network.wg$INTER.addresses=""
uci commit network
if [ -e /usr/lib/wireguard/wiremwan3.sh ]; then
/usr/lib/wireguard/wiremwan3.sh stop
fi
ifup wan
fi
UDP=$(uci get wireguard."$WG".udptunnel)
if [ $UDP = 1 ]; then
PID=$(ps |grep "udptunnel" | grep -v grep |head -n 1 | awk '{print $1}')
kill -9 $PID
fi
uci set wireguard."$WG".active="0"
uci commit wireguard
/etc/init.d/wireguard stop

Some files were not shown because too many files have changed in this diff Show More