Compare commits

...

152 Commits

Author SHA1 Message Date
elseif
8f15749897 Update README.md
Signed-off-by: elseif <elseif@live.cn>
2025-07-29 11:52:44 +08:00
elseif
9712d7d464 Update CODE_OF_CONDUCT.md
Signed-off-by: elseif <elseif@live.cn>
2025-07-28 20:59:12 +08:00
elseif
7bebf605a0 Update LICENSE
Signed-off-by: elseif <elseif@live.cn>
2025-07-28 20:58:30 +08:00
elseif
f018e0de99 Update LICENSE
Signed-off-by: elseif <elseif@live.cn>
2025-07-28 20:58:05 +08:00
elseif
7ef69a1e31 Update README_PT.md
Signed-off-by: elseif <elseif@live.cn>
2025-07-28 20:56:07 +08:00
elseif
1ba7057fc7 Update README_EN.md
Signed-off-by: elseif <elseif@live.cn>
2025-07-28 20:55:53 +08:00
elseif
8a52ef8df4 Update README.md
Signed-off-by: elseif <elseif@live.cn>
2025-07-28 20:55:38 +08:00
elseif
7292ad7a80 Update README_PT.md
Signed-off-by: elseif <elseif@live.cn>
2025-07-28 20:47:06 +08:00
elseif
88de7162b7 Update README_EN.md
Signed-off-by: elseif <elseif@live.cn>
2025-07-28 20:46:51 +08:00
elseif
f3497a9a4b Update README.md
Signed-off-by: elseif <elseif@live.cn>
2025-07-28 20:46:34 +08:00
elseif
702efdb828 Update CODE_OF_CONDUCT.md
Signed-off-by: elseif <elseif@live.cn>
2025-07-28 20:43:37 +08:00
elseif
a2038ece24 Update CODE_OF_CONDUCT.md
Signed-off-by: elseif <elseif@live.cn>
2025-07-28 20:40:04 +08:00
elseif
0b3fd16ba7 Update LICENSE
Signed-off-by: elseif <elseif@live.cn>
2025-07-28 20:35:14 +08:00
elseif
8367df6ef0 Update mikrotik_patch_7.yml
Signed-off-by: elseif <elseif@live.cn>
2025-07-17 22:07:56 +08:00
zyb
2b9db1436c modified: patch.py 2025-07-13 14:27:34 +08:00
zyb
6dccdda7bb modified: .github/workflows/mikrotik_patch_7.yml 2025-07-11 21:10:15 +08:00
zyb
1d0b4f9563 modified: .github/workflows/mikrotik_patch_7.yml 2025-07-11 20:48:53 +08:00
zyb
ce13b4b959 modified: .github/workflows/mikrotik_patch_7.yml 2025-07-11 20:42:06 +08:00
zyb
3f98072f2d modified: .github/workflows/mikrotik_patch_7.yml 2025-07-11 20:38:55 +08:00
zyb
ceb85aaf72 modified: .github/workflows/mikrotik_patch_7.yml
modified:   busybox/busybox_aarch64
	new file:   busybox/busybox_arm
	modified:   busybox/busybox_x86
	modified:   keygen/keygen_aarch64
	new file:   keygen/keygen_arm
	modified:   patch.py
2025-07-11 20:36:23 +08:00
elseif
ad132d5a8d Update mikrotik_patch_7.yml
Signed-off-by: elseif <elseif@live.cn>
2025-07-10 18:49:16 +08:00
elseif
0e6364e06a Update mikrotik_patch_7.yml
Signed-off-by: elseif <elseif@live.cn>
2025-07-10 18:46:53 +08:00
elseif
c7f31476e7 Update chr.sh
Signed-off-by: elseif <elseif@live.cn>
2025-07-08 00:58:38 +08:00
elseif
674370280d Update chr.sh
Signed-off-by: elseif <elseif@live.cn>
2025-07-06 01:30:56 +08:00
elseif
9a7ea04b45 Update mikrotik_patch_7.yml
Signed-off-by: elseif <elseif@live.cn>
2025-07-05 14:40:35 +08:00
elseif
4965f266db Create CODE_OF_CONDUCT.md
Signed-off-by: elseif <elseif@live.cn>
2025-07-05 06:07:33 +08:00
elseif
6c33b4c2c9 Update README.md
Signed-off-by: elseif <elseif@live.cn>
2025-07-04 00:26:48 +08:00
zyb
5729c4746a modified: README.md
modified:   README_EN.md
	modified:   README_PT.md
2025-06-29 01:36:00 +08:00
elseif
0e89b026b8 Create LICENSE
Signed-off-by: elseif <elseif@live.cn>
2025-06-23 12:41:14 +08:00
zyb
88925b0057 modified: .github/workflows/mikrotik_patch_7.yml 2025-06-23 12:37:27 +08:00
zyb
18f7b4cf36 modified: .github/workflows/mikrotik_patch_7.yml 2025-06-21 14:49:16 +08:00
zyb
77b0644c95 modified: .github/workflows/mikrotik_patch_7.yml 2025-06-21 14:32:03 +08:00
zyb
e72436306b modified: .github/workflows/mikrotik_patch_7.yml 2025-06-21 10:37:46 +08:00
zyb
d32177f1e7 modified: .github/workflows/mikrotik_patch_6.yml 2025-06-21 09:49:51 +08:00
zyb
2ad3d69a4d modified: .github/workflows/mikrotik_patch_7.yml 2025-06-21 09:47:49 +08:00
zyb
70819de5a4 modified: .github/workflows/mikrotik_patch_7.yml 2025-06-19 14:31:23 +08:00
zyb
f22db63a10 modified: npk.py 2025-06-19 13:48:23 +08:00
zyb
178ffcbadb modified: .github/workflows/mikrotik_patch_7.yml
modified:   patch.py
2025-06-19 13:45:31 +08:00
zyb
70bca68232 modified: npk.py
modified:   patch.py
2025-06-19 13:38:45 +08:00
zyb
4cdd6d5619 modified: patch.py 2025-06-19 13:31:48 +08:00
zyb
af97ad2a07 modified: .github/workflows/mikrotik_patch_7.yml
modified:   patch.py
2025-06-19 13:28:29 +08:00
zyb
fd50885bf4 modified: patch.py 2025-06-19 13:23:52 +08:00
zyb
2551551828 modified: .github/workflows/mikrotik_patch_7.yml
modified:   patch.py
2025-06-19 13:21:08 +08:00
zyb
d8f092eb80 modified: patch.py 2025-06-19 13:16:46 +08:00
zyb
fe68e753c6 modified: patch.py 2025-06-19 13:15:26 +08:00
zyb
9ca203dcad modified: .github/workflows/mikrotik_patch_7.yml 2025-06-19 13:11:50 +08:00
zyb
939e01725c modified: .github/workflows/mikrotik_patch_7.yml 2025-06-19 13:07:24 +08:00
zyb
1935f35864 modified: .github/workflows/mikrotik_patch_7.yml
modified:   npk.py
2025-06-19 12:48:56 +08:00
zyb
676f0e0f82 modified: .github/workflows/mikrotik_patch_7.yml 2025-06-19 12:43:23 +08:00
zyb
b50ba21932 modified: .github/workflows/mikrotik_patch_7.yml 2025-06-19 12:34:03 +08:00
zyb
78f63469c9 modified: .github/workflows/mikrotik_patch_7.yml 2025-06-19 12:30:13 +08:00
zyb
511392906b modified: .github/workflows/mikrotik_patch_7.yml 2025-06-19 12:22:59 +08:00
elseif
2d2ca3e493 Merge pull request #118 from PauloNRocha/main
Add Portuguese translation of README
2025-06-19 12:12:44 +08:00
zyb
3f988f27ed modified: .github/workflows/mikrotik_patch_7.yml
deleted:    .github/workflows/self_hosted_patch.yml
	modified:   .gitignore
2025-06-19 12:09:51 +08:00
elseif
8a2b8f629c Update self_hosted_patch.yml
Signed-off-by: elseif <elseif@live.cn>
2025-06-19 10:26:00 +08:00
elseif
2ce0f85f8a Update self_hosted_patch.yml
Signed-off-by: elseif <elseif@live.cn>
2025-06-19 10:17:52 +08:00
elseif
a07fe281f1 Update self_hosted_patch.yml
Signed-off-by: elseif <elseif@live.cn>
2025-06-19 10:07:34 +08:00
elseif
70321348ad Update self_hosted_patch.yml
Signed-off-by: elseif <elseif@live.cn>
2025-06-19 10:04:58 +08:00
Paulo Rocha
6b1d9a4a62 minor spelling corrections 2025-06-18 23:04:09 -03:00
elseif
9f5f72bb03 Update self_hosted_patch.yml
Signed-off-by: elseif <elseif@live.cn>
2025-06-19 10:00:30 +08:00
Paulo Rocha
173dfd69e3 Add Portuguese translation of README
Added README_PT.md with full Brazilian Portuguese translation of the original README. Helpful for Portuguese-speaking users.
2025-06-18 22:57:15 -03:00
elseif
f0698d8814 Update self_hosted_patch.yml
Signed-off-by: elseif <elseif@live.cn>
2025-06-19 09:50:58 +08:00
elseif
db75ad1711 Update self_hosted_patch.yml
Signed-off-by: elseif <elseif@live.cn>
2025-06-19 09:47:03 +08:00
elseif
f54f9f15b6 Update chr.sh
Signed-off-by: elseif <elseif@live.cn>
2025-06-19 09:13:42 +08:00
elseif
17b37b7124 Delete mbr.bin
Signed-off-by: elseif <elseif@live.cn>
2025-06-19 09:09:13 +08:00
elseif
48ce77cf80 Update self_hosted_patch.yml
Signed-off-by: elseif <elseif@live.cn>
2025-06-18 19:32:27 +08:00
elseif
202dab0201 Update self_hosted_patch.yml
Signed-off-by: elseif <elseif@live.cn>
2025-06-18 19:23:34 +08:00
elseif
ef13a0cf68 Update self_hosted_patch.yml
Signed-off-by: elseif <elseif@live.cn>
2025-06-18 19:22:07 +08:00
elseif
cc05886c0a Update self_hosted_patch.yml
Signed-off-by: elseif <elseif@live.cn>
2025-06-18 19:16:56 +08:00
elseif
018f060462 Update self_hosted_patch.yml
Signed-off-by: elseif <elseif@live.cn>
2025-06-18 18:52:44 +08:00
elseif
fcd6926272 Update self_hosted_patch.yml
Signed-off-by: elseif <elseif@live.cn>
2025-06-18 18:37:08 +08:00
elseif
6cd71c9efe Update patch.py
Signed-off-by: elseif <elseif@live.cn>
2025-06-18 18:33:59 +08:00
elseif
a350e2badd Update patch.py
Signed-off-by: elseif <elseif@live.cn>
2025-06-18 18:24:26 +08:00
elseif
9bad9f06f1 Update self_hosted_patch.yml
Signed-off-by: elseif <elseif@live.cn>
2025-06-18 18:15:06 +08:00
elseif
a5db54eca5 Update patch.py
Signed-off-by: elseif <elseif@live.cn>
2025-06-18 18:11:41 +08:00
elseif
dedfe06698 Update self_hosted_patch.yml
Signed-off-by: elseif <elseif@live.cn>
2025-06-18 14:55:56 +08:00
elseif
cdae26e673 Update self_hosted_patch.yml
Signed-off-by: elseif <elseif@live.cn>
2025-06-18 14:46:50 +08:00
elseif
33cd5313f0 Update self_hosted_patch.yml
Signed-off-by: elseif <elseif@live.cn>
2025-06-18 14:41:27 +08:00
elseif
2b0548ba76 Update self_hosted_patch.yml
Signed-off-by: elseif <elseif@live.cn>
2025-06-18 14:33:59 +08:00
elseif
4a9d5672c1 Update self_hosted_patch.yml
Signed-off-by: elseif <elseif@live.cn>
2025-06-18 14:22:06 +08:00
elseif
23dd4c7f43 Update self_hosted_patch.yml
Signed-off-by: elseif <elseif@live.cn>
2025-06-18 14:10:48 +08:00
elseif
80bda12745 Update self_hosted_patch.yml
Signed-off-by: elseif <elseif@live.cn>
2025-06-18 14:01:56 +08:00
elseif
954fcfdbe3 Update self_hosted_patch.yml
Signed-off-by: elseif <elseif@live.cn>
2025-06-18 13:53:19 +08:00
elseif
78516e3695 Update self_hosted_patch.yml
Signed-off-by: elseif <elseif@live.cn>
2025-06-18 13:29:47 +08:00
elseif
e43686eca2 Update self_hosted_patch.yml
Signed-off-by: elseif <elseif@live.cn>
2025-06-18 13:25:01 +08:00
elseif
3f3bd3978b self_hosted_patch.yml
Signed-off-by: elseif <elseif@live.cn>
2025-06-18 13:04:42 +08:00
elseif
d6c9e7c528 Update mikrotik_patch_6.yml
Signed-off-by: elseif <elseif@live.cn>
2025-06-17 15:54:00 +08:00
elseif
476691ac29 Add files via upload
Signed-off-by: elseif <elseif@live.cn>
2025-06-17 15:20:57 +08:00
elseif
8e3ff90b2d Add files via upload
Signed-off-by: elseif <elseif@live.cn>
2025-06-17 15:20:15 +08:00
elseif
50a2f3f03b Update patch.py
Signed-off-by: elseif <elseif@live.cn>
2025-06-14 20:19:25 +08:00
elseif
317904dfbf Update mikrotik_patch_7.yml
Signed-off-by: elseif <elseif@live.cn>
2025-06-14 19:48:15 +08:00
elseif
6e0c8a52bd Update mikrotik_patch_6.yml
Signed-off-by: elseif <elseif@live.cn>
2025-06-12 00:29:26 +08:00
elseif
2fe1832095 Update mikrotik_patch_6.yml
Signed-off-by: elseif <elseif@live.cn>
2025-06-12 00:17:39 +08:00
elseif
7a15204f3a Update mikrotik_patch_6.yml
Signed-off-by: elseif <elseif@live.cn>
2025-06-12 00:15:02 +08:00
elseif
6e0c64cd73 Update mikrotik_patch_6.yml
Signed-off-by: elseif <elseif@live.cn>
2025-06-12 00:10:46 +08:00
elseif
f4a4187e23 Update patch.py
Signed-off-by: elseif <elseif@live.cn>
2025-03-04 11:23:03 +08:00
elseif
66323bbfea Update mikrotik_patch_6.yml
Signed-off-by: elseif <elseif@live.cn>
2025-02-25 13:14:44 +08:00
elseif
7f2ec84067 Update mikrotik_patch_6.yml
Signed-off-by: elseif <elseif@live.cn>
2025-02-25 13:13:36 +08:00
elseif
5589babdcc Update patch.py
Signed-off-by: elseif <elseif@live.cn>
2025-02-25 13:09:00 +08:00
elseif
18bae23bf3 Update mikrotik_patch_6.yml
Signed-off-by: elseif <elseif@live.cn>
2025-02-25 12:47:17 +08:00
elseif
3d52d65eb5 Update patch.py
Signed-off-by: elseif <elseif@live.cn>
2025-02-25 12:39:41 +08:00
elseif
a951a224b0 Update mikrotik_patch_6.yml
Signed-off-by: elseif <elseif@live.cn>
2025-02-25 12:37:48 +08:00
elseif
343fe653ee Update mikrotik_patch_7.yml
Signed-off-by: elseif <elseif@live.cn>
2025-02-24 14:37:08 +08:00
elseif
bfb4e91be7 Update mikrotik_patch_7.yml
Signed-off-by: elseif <elseif@live.cn>
2025-02-24 14:19:57 +08:00
elseif
898d1c1789 Update patch.py
Signed-off-by: elseif <elseif@live.cn>
2025-02-22 15:34:42 +08:00
elseif
e4167afbec Update mikrotik_patch_7.yml
Signed-off-by: elseif <elseif@live.cn>
2025-02-22 15:33:07 +08:00
elseif
aeaf99729f Update mikrotik_patch_7.yml
Signed-off-by: elseif <elseif@live.cn>
2025-02-22 15:27:06 +08:00
elseif
d125a063ce Update mikrotik_patch_7.yml
Signed-off-by: elseif <elseif@live.cn>
2025-02-22 15:22:40 +08:00
elseif
ce926f7cc9 Update mikrotik_patch_7.yml
Signed-off-by: elseif <elseif@live.cn>
2025-02-19 17:45:20 +08:00
elseif
aea2da2a36 Update mikrotik_patch_7.yml
Signed-off-by: elseif <elseif@live.cn>
2025-02-19 17:31:26 +08:00
elseif
c869dca3c1 Update mikrotik_patch_7.yml
Signed-off-by: elseif <elseif@live.cn>
2025-02-19 17:23:14 +08:00
elseif
cbe8254d84 Update mikrotik_patch_7.yml
Signed-off-by: elseif <elseif@live.cn>
2025-02-19 17:18:39 +08:00
elseif
331df17ee7 Update mikrotik_patch_7.yml
Signed-off-by: elseif <elseif@live.cn>
2025-02-19 17:12:01 +08:00
elseif
35852182b2 Update mikrotik_patch_7.yml
Signed-off-by: elseif <elseif@live.cn>
2025-02-19 16:30:46 +08:00
elseif
e0d1eb1a98 Update mikrotik_patch_7.yml
Signed-off-by: elseif <elseif@live.cn>
2025-02-19 16:26:17 +08:00
elseif
0717a39c02 Update mikrotik_patch_7.yml
Signed-off-by: elseif <elseif@live.cn>
2025-02-19 16:24:30 +08:00
elseif
4993be82a6 Update mikrotik_patch_7.yml
Signed-off-by: elseif <elseif@live.cn>
2025-02-19 16:22:42 +08:00
elseif
0dbed4777f Update mikrotik_patch_7.yml
Signed-off-by: elseif <elseif@live.cn>
2025-02-19 16:17:23 +08:00
elseif
3b529862d1 Update README.md
Signed-off-by: elseif <elseif@live.cn>
2025-02-19 15:43:29 +08:00
elseif
6da98653fc Update README_EN.md
Signed-off-by: elseif <elseif@live.cn>
2025-02-19 15:43:02 +08:00
elseif
27e023fb28 Update README_EN.md
Signed-off-by: elseif <elseif@live.cn>
2025-02-19 15:42:28 +08:00
elseif
df6b25a30e Update README.md
Signed-off-by: elseif <elseif@live.cn>
2025-02-19 15:42:06 +08:00
elseif
60294067c7 Merge pull request #80 from emam06/patch-3
Update
2025-02-19 15:41:19 +08:00
elseif
d309253b06 Update mikrotik_patch_7.yml
Signed-off-by: elseif <elseif@live.cn>
2025-02-19 11:12:54 +08:00
elseif
b3579cb363 Update mikrotik_patch_7.yml
Signed-off-by: elseif <elseif@live.cn>
2025-02-19 11:09:18 +08:00
elseif
0f2c5e6081 Update patch.py
Signed-off-by: elseif <elseif@live.cn>
2025-02-18 20:50:25 +08:00
elseif
8f59465bf0 Update patch.py
Signed-off-by: elseif <elseif@live.cn>
2025-02-18 20:43:39 +08:00
elseif
736af6817b Update patch.py
Signed-off-by: elseif <elseif@live.cn>
2025-02-18 20:33:03 +08:00
elseif
10a56eb673 Update patch.py
Signed-off-by: elseif <elseif@live.cn>
2025-02-18 20:31:07 +08:00
elseif
6518dda504 Update mikrotik_patch_7.yml
Signed-off-by: elseif <elseif@live.cn>
2025-02-18 15:42:28 +08:00
elseif
74e812fa2b Update mikrotik_patch_7.yml
Signed-off-by: elseif <elseif@live.cn>
2025-02-18 15:40:17 +08:00
elseif
810909828a Update mikrotik_patch_7.yml
Signed-off-by: elseif <elseif@live.cn>
2025-02-18 15:16:22 +08:00
elseif
49f4ad0a59 Update mikrotik_patch_7.yml
Signed-off-by: elseif <elseif@live.cn>
2025-02-18 15:02:01 +08:00
elseif
ece607c8f7 Update mikrotik_patch_7.yml
Signed-off-by: elseif <elseif@live.cn>
2025-02-18 15:01:10 +08:00
elseif
1426fc061a Update mikrotik_patch_7.yml
Signed-off-by: elseif <elseif@live.cn>
2025-02-17 12:44:05 +08:00
elseif
7579dadaea Update patch.py
Signed-off-by: elseif <elseif@live.cn>
2025-02-17 12:29:48 +08:00
elseif
6b6669fb23 Update mikrotik_patch_7.yml
Signed-off-by: elseif <elseif@live.cn>
2025-02-17 12:27:07 +08:00
elseif
5f603dcebc Update patch.py
Signed-off-by: elseif <elseif@live.cn>
2025-02-11 17:47:22 +08:00
elseif
e1994f69d6 Update mikrotik_patch_6.yml
Signed-off-by: elseif <elseif@live.cn>
2025-02-07 13:43:33 +08:00
elseif
39af3326bd Update patch.py
Signed-off-by: elseif <elseif@live.cn>
2025-02-07 03:39:14 +08:00
elseif
c657f2e736 Update patch.py
Signed-off-by: elseif <elseif@live.cn>
2025-02-07 03:08:29 +08:00
elseif
a8dd672a66 Update patch.py
Signed-off-by: elseif <elseif@live.cn>
2025-02-07 00:51:42 +08:00
elseif
cf01bbda4d Update mikrotik_patch_7.yml
Signed-off-by: elseif <elseif@live.cn>
2025-02-07 00:43:57 +08:00
elseif
1c9207d498 Update patch.py
Signed-off-by: elseif <elseif@live.cn>
2025-02-07 00:40:47 +08:00
elseif
f1ed27cb52 Update patch.py
Signed-off-by: elseif <elseif@live.cn>
2025-02-05 23:32:42 +08:00
elseif
8d38a80dd8 Update mikrotik_patch_7.yml
Signed-off-by: elseif <elseif@live.cn>
2025-02-05 23:30:14 +08:00
elseif
f4af3671be Update patch.py
Signed-off-by: elseif <elseif@live.cn>
2025-02-05 23:19:28 +08:00
elseif
2f0f0b1abb Update patch.py
Signed-off-by: elseif <elseif@live.cn>
2025-02-05 23:01:27 +08:00
elseif
ea10a1a4c7 Update patch.py
Signed-off-by: elseif <elseif@live.cn>
2025-02-05 22:47:38 +08:00
emam06
bd03ecb963 Update
Signed-off-by: emam06 <egr7yco@gmail.com>
2025-01-27 15:17:41 +02:00
elseif
5b909283a0 Update mikrotik_patch_7.yml
Signed-off-by: elseif <elseif@live.cn>
2025-01-25 21:35:52 +08:00
elseif
289ea3a34f Update mikrotik_patch_7.yml
Signed-off-by: elseif <elseif@live.cn>
2025-01-25 03:15:17 +08:00
18 changed files with 605 additions and 234 deletions

View File

@@ -3,10 +3,28 @@ name: Patch Mikrotik RouterOS 6.x
on:
# push:
# branches: [ "main" ]
schedule:
- cron: "0 0 * * *"
# schedule:
# - cron: "0 0 * * *"
workflow_dispatch:
inputs:
channel:
description: 'Channel (stable, long-term)'
required: true
default: 'stable'
type: choice
options:
- stable
- long-term
version:
description: "Version ('', 6.49.17, 6.49.18,...)"
required: false
default: ''
type: string
buildtime:
description: "Build Time"
required: false
default: ''
type: string
permissions:
contents: write
@@ -36,14 +54,20 @@ jobs:
steps:
- name: Set build time
id: set_buildtime
run: echo "BUILD_TIME=$(date +'%s')" >> $GITHUB_OUTPUT
run: |
_BUILD_TIME=${{ github.event.inputs.buildtime }}
if [ -z "$_BUILD_TIME" ]; then
echo "BUILD_TIME=$(date +'%s')" >> $GITHUB_OUTPUT
else
echo "BUILD_TIME=$_BUILD_TIME" >> $GITHUB_OUTPUT
fi
Patch_RouterOS:
needs: Set_BuildTime
runs-on: ubuntu-22.04
strategy:
matrix:
channel: [long-term,stable]
channel: ${{ fromJSON(format('["{0}"]', github.event.inputs.channel || 'stable')) }}
env:
TZ: 'Asia/Shanghai'
LATEST_VERSION: ""
@@ -60,7 +84,10 @@ jobs:
id: get_latest
run: |
echo $(uname -a)
LATEST_VERSION=$(wget -nv -O - https://upgrade.mikrotik.com/routeros/NEWEST6.${{ matrix.channel }} | cut -d ' ' -f1)
LATEST_VERSION=${{ github.event.inputs.version }}
if [ -z "$_LATEST_VERSION" ]; then
LATEST_VERSION=$(wget -nv -O - https://${{ env.MIKRO_UPGRADE_URL }}/routeros/NEWEST6.${{ matrix.channel }} | cut -d ' ' -f1)
fi
echo Latest Version:$LATEST_VERSION
if [ "${{ github.event_name }}" == "schedule" ]; then
_LATEST_VERSION=$(wget -nv -O - https://${{ env.CUSTOM_UPGRADE_URL }}/routeros/NEWEST6.${{ matrix.channel }} | cut -d ' ' -f1)
@@ -77,8 +104,48 @@ jobs:
cat CHANGELOG
echo "LATEST_VERSION=${LATEST_VERSION}" >> $GITHUB_ENV
echo "BUILD_TIME=${BUILD_TIME}" >> $GITHUB_ENV
has_patched_npk=false
if wget -nv --spider https://${{ env.CUSTOM_UPGRADE_URL }}/routeros/$LATEST_VERSION/routeros-x86-$LATEST_VERSION.npk; then
echo "RouterOS NPK file exists, attempting to download..."
if wget -nv -O routeros-x86-$LATEST_VERSION.npk https://${{ env.CUSTOM_UPGRADE_URL }}/routeros/$LATEST_VERSION/routeros-x86-$LATEST_VERSION.npk; then
echo "RouterOS NPK file downloaded successfully."
if wget -nv --spider https://${{ env.CUSTOM_UPGRADE_URL }}/routeros/$LATEST_VERSION/system-$LATEST_VERSION.npk; then
echo "System NPK file exists, attempting to download..."
if wget -nv -O system-$LATEST_VERSION.npk https://${{ env.CUSTOM_UPGRADE_URL }}/routeros/$LATEST_VERSION/system-$LATEST_VERSION.npk; then
has_patched_npk=true
fi
fi
fi
fi
echo "has_patched_npk=$has_patched_npk" >> $GITHUB_OUTPUT
- name: Cache Squashfs
if: steps.get_latest.outputs.has_new_version == 'true'
id: cache-squashfs
uses: actions/cache@v4
with:
path: |
option.sfs
key: busybox-squashfs
- name: Create Squashfs for option
if: steps.get_latest.outputs.has_new_version == 'true' && steps.cache-squashfs.outputs.cache-hit != 'true'
run: |
sudo mkdir -p ./option-root/bin/
sudo cp busybox/busybox_x86 ./option-root/bin/busybox
sudo chmod +x ./option-root/bin/busybox
sudo cp keygen/keygen_x86 ./option-root/bin/keygen
sudo chmod +x ./option-root/bin/keygen
sudo chmod +x ./busybox/busybox_x86
COMMANDS=$(./busybox/busybox_x86 --list)
for cmd in $COMMANDS; do
sudo ln -sf /pckg/option/bin/busybox ./option-root/bin/$cmd
done
sudo mksquashfs option-root option.sfs -quiet -comp xz -no-xattrs -b 256k
sudo rm -rf option-root
- name: Cache mikrotik-${{ env.LATEST_VERSION }}.iso
if: steps.get_latest.outputs.has_new_version == 'true'
id: cache-mikrotik
@@ -105,14 +172,20 @@ jobs:
sudo rsync -a ./iso/ ./new_iso/
sudo umount ./iso
sudo rm -rf ./iso
sudo mv ./new_iso/system-$LATEST_VERSION.npk ./
sudo -E python3 patch.py npk system-$LATEST_VERSION.npk
if [ "${{ steps.get_latest.outputs.has_patched_npk }}" == "false" ]; then
sudo mv ./new_iso/system-$LATEST_VERSION.npk ./
sudo -E python3 patch.py npk system-$LATEST_VERSION.npk
else
sudo -E python3 npk.py sign system-$LATEST_VERSION.npk system-$LATEST_VERSION.npk
fi
sudo -E python3 patch.py kernel ./new_iso/isolinux/initrd.rgz
NPK_FILES=$(find ./new_iso/*.npk)
for file in $NPK_FILES; do
sudo -E python3 npk.py sign $file $file
done
sudo cp system-$LATEST_VERSION.npk ./new_iso/
#sudo -E python3 npk.py create ./new_iso/gps-$LATEST_VERSION.npk ./option-$LATEST_VERSION.npk option ./option.sfs -desc="busybox"
#sudo cp option-$LATEST_VERSION.npk ./new_iso/
sudo mkisofs -o mikrotik-$LATEST_VERSION.iso \
-V "MikroTik $LATEST_VERSION" \
-sysid "" -preparer "MiKroTiK" \
@@ -129,13 +202,9 @@ jobs:
sudo mkdir ./all_packages
sudo cp ./new_iso/*.npk ./all_packages/
sudo rm -rf ./new_iso
cd ./all_packages
sudo zip ../all_packages-x86-$LATEST_VERSION.zip *.npk
cd ..
- name: Create install-image-${{ env.LATEST_VERSION }}.img
if: steps.get_latest.outputs.has_new_version == 'true'
if: steps.get_latest.outputs.has_new_version == 'true' && steps.get_latest.outputs.has_patched_npk == 'true'
run: |
sudo modprobe nbd
sudo apt-get update
@@ -184,19 +253,27 @@ jobs:
- name: Create chr-${{ env.LATEST_VERSION }}.img
if: steps.get_latest.outputs.has_new_version == 'true'
run: |
sudo modprobe nbd
sudo apt-get install -y qemu-utils extlinux > /dev/null
sudo mkdir ./chr
sudo cp chr.img chr-$LATEST_VERSION.img
sudo qemu-nbd -c /dev/nbd0 -f raw chr-$LATEST_VERSION.img
sudo -E python3 patch.py block /dev/nbd0p1 boot/initrd.rgz
sudo mount /dev/nbd0p1 ./chr
sudo cp ./all_packages/dude-$LATEST_VERSION.npk ./chr/var/pdb/dude/image
sudo -E python3 patch.py npk ./chr/var/pdb/routeros-x86/image
sudo cp ./chr/var/pdb/routeros-x86/image ./all_packages/routeros-x86-$LATEST_VERSION.npk
sudo cp ./all_packages/routeros-x86-$LATEST_VERSION.npk routeros-x86-$LATEST_VERSION.npk
if [ "${{ steps.get_latest.outputs.has_patched_npk }}" == "false" ]; then
sudo -E python3 patch.py npk ./chr/var/pdb/routeros-x86/image
sudo cp ./chr/var/pdb/routeros-x86/image ./all_packages/routeros-x86-$LATEST_VERSION.npk
else
sudo -E python3 npk.py sign routeros-x86-$LATEST_VERSION.npk routeros-x86-$LATEST_VERSION.npk
sudo cp -f routeros-x86-$LATEST_VERSION.npk ./chr/var/pdb/routeros-x86/image
sudo cp routeros-x86-$LATEST_VERSION.npk ./all_packages/routeros-x86-$LATEST_VERSION.npk
fi
#sudo mkdir -p ./chr/var/pdb/option
#sudo cp ./all_packages/option-$LATEST_VERSION.npk ./chr/var/pdb/option/image
sudo umount ./chr
sudo qemu-nbd -d /dev/nbd0
sudo rm -rf ./chr
sudo qemu-img convert -f raw -O qcow2 chr-$LATEST_VERSION.img chr-$LATEST_VERSION.qcow2
sudo qemu-img convert -f raw -O vmdk chr-$LATEST_VERSION.img chr-$LATEST_VERSION.vmdk
sudo qemu-img convert -f raw -O vpc chr-$LATEST_VERSION.img chr-$LATEST_VERSION.vhd
@@ -210,21 +287,28 @@ jobs:
sudo zip chr-$LATEST_VERSION.vdi.zip chr-$LATEST_VERSION.vdi
sudo zip chr-$LATEST_VERSION.img.zip chr-$LATEST_VERSION.img
sudo rm chr-$LATEST_VERSION$ARCH.qcow2
sudo rm chr-$LATEST_VERSION$ARCH.vmdk
sudo rm chr-$LATEST_VERSION$ARCH.vhd
sudo rm chr-$LATEST_VERSION$ARCH.vhdx
sudo rm chr-$LATEST_VERSION$ARCH.vdi
sudo rm chr-$LATEST_VERSION$ARCH.img
sudo rm chr-$LATEST_VERSION.qcow2
sudo rm chr-$LATEST_VERSION.vmdk
sudo rm chr-$LATEST_VERSION.vhd
sudo rm chr-$LATEST_VERSION.vhdx
sudo rm chr-$LATEST_VERSION.vdi
sudo rm chr-$LATEST_VERSION.img
cd ./all_packages
sudo zip ../all_packages-x86-$LATEST_VERSION.zip *.npk
cd ..
- name: Upload Files
if: steps.get_latest.outputs.has_new_version == 'true'
run: |
sudo mkdir -p ./publish/$LATEST_VERSION
echo $LATEST_VERSION $BUILD_TIME | sudo tee ./publish/NEWEST6.${{ matrix.channel }}
sudo cp CHANGELOG ./publish/$LATEST_VERSION/
sudo cp ./all_packages/*.npk ./publish/$LATEST_VERSION/
if [ "${{ steps.get_latest.outputs.has_patched_npk }}" == "false" ]; then
OUTDIR="$LATEST_VERSION-UNDONE"
else
OUTDIR="$LATEST_VERSION"
fi
sudo mkdir -p ./publish/$OUTDIR
sudo cp CHANGELOG ./publish/$OUTDIR/
sudo cp ./all_packages/*.npk ./publish/$OUTDIR/
sudo chown -R root:root ./publish/
sudo apt-get install -y lftp ssh sshpass > /dev/null 2>&1
sudo -E lftp -u ${{ secrets.SSH_USERNAME }},'${{ secrets.SSH_PASSWORD }}' sftp://${{ secrets.SSH_SERVER }}:${{ secrets.SSH_PORT }} <<EOF
@@ -232,7 +316,8 @@ jobs:
mirror --reverse --verbose --only-newer ./publish ${{ secrets.SSH_DIRECTORY }}
bye
EOF
sshpass -p "${{ secrets.SSH_PASSWORD }}" ssh -o StrictHostKeyChecking=no -p ${{ secrets.SSH_PORT }} ${{ secrets.SSH_USERNAME }}@${{ secrets.SSH_SERVER }} "chown -R 32768:32768 /rw/disk/${{ secrets.SSH_DIRECTORY }}/"
sshpass -p "${{ secrets.SSH_PASSWORD }}" ssh -o StrictHostKeyChecking=no -p ${{ secrets.SSH_PORT }} ${{ secrets.SSH_USERNAME }}@${{ secrets.SSH_SERVER }} "echo $LATEST_VERSION $BUILD_TIME | tee /rw/disk/${{ secrets.SSH_DIRECTORY }}/NEWEST6.${{ matrix.channel }}; chown -R 32768:32768 /rw/disk/${{ secrets.SSH_DIRECTORY }}/"
- name: Clear Cloudflare cache
if: steps.get_latest.outputs.has_new_version == 'true'
run: |
@@ -242,23 +327,23 @@ jobs:
--data '{"purge_everything": true}'
- name: Delete Release tag ${{ env.LATEST_VERSION }}
if: steps.get_latest.outputs.has_new_version == 'true'
if: steps.get_latest.outputs.has_new_version == 'true' && steps.get_latest.outputs.has_patched_npk == 'true'
run: |
HEADER="Authorization: token ${{ secrets.GITHUB_TOKEN }}"
RELEASE_INFO=$(curl -s -H $HEADER https://api.github.com/repos/${{ github.repository }}/releases/tags/$LATEST_VERSION$ARCH)
RELEASE_INFO=$(curl -s -H $HEADER https://api.github.com/repos/${{ github.repository }}/releases/tags/$LATEST_VERSION)
RELEASE_ID=$(echo $RELEASE_INFO | jq -r '.id')
echo "Release ID: $RELEASE_ID"
if [ "$RELEASE_ID" != "null" ]; then
curl -X DELETE -H "$HEADER" https://api.github.com/repos/${{ github.repository }}/git/refs/tags/$LATEST_VERSION$ARCH
echo "Tag $LATEST_VERSION$ARCH deleted successfully."
curl -X DELETE -H "$HEADER" https://api.github.com/repos/${{ github.repository }}/git/refs/tags/$LATEST_VERSION
echo "Tag $LATEST_VERSION deleted successfully."
curl -X DELETE -H "$HEADER" https://api.github.com/repos/${{ github.repository }}/releases/$RELEASE_ID
echo "Release with tag $LATEST_VERSION$ARCH deleted successfully."
echo "Release with tag $LATEST_VERSION deleted successfully."
else
echo "Release not found for tag: $LATEST_VERSION)"
fi
- name: Create Release tag ${{ env.LATEST_VERSION }}
if: steps.get_latest.outputs.has_new_version == 'true'
if: steps.get_latest.outputs.has_new_version == 'true' && steps.get_latest.outputs.has_patched_npk == 'true'
uses: softprops/action-gh-release@v2
with:
name: "RouterOS ${{ env.LATEST_VERSION }}"

View File

@@ -3,8 +3,41 @@ on:
# push:
# branches: [ "main" ]
schedule:
- cron: "0 0 * * *"
- cron: "0 0 * * *" # At UTC 00:00 on every day
workflow_dispatch:
inputs:
arch:
description: 'Architecture (x86, arm64, arm)'
required: true
default: 'x86'
type: choice
options:
- x86
- arm64
- arm
channel:
description: 'Channel (stable, testing)'
required: true
default: 'stable'
type: choice
options:
- stable
- testing
version:
description: "Specify version (e.g., 7.19.2), empty for latest"
required: false
default: ''
type: string
buildtime:
description: "Custom build time, leave empty for now"
required: false
default: ''
type: string
release:
description: "Release to GitHub & Upload "
required: false
default: false
type: boolean
permissions:
contents: write
@@ -28,26 +61,51 @@ env:
CUSTOM_CLOUD_URL: ${{ secrets.CUSTOM_CLOUD_URL }}
jobs:
Set_BuildTime:
Set_Variables:
runs-on: ubuntu-22.04
outputs:
BUILD_TIME: ${{ steps.set_buildtime.outputs.BUILD_TIME }}
BUILD_TIME: ${{ steps.set_vars.outputs.BUILD_TIME }}
RELEASE: ${{ steps.set_vars.outputs.RELEASE }}
MATRIX_JSON: ${{ steps.set_vars.outputs.MATRIX_JSON }}
steps:
- name: Set build time
id: set_buildtime
run: echo "BUILD_TIME=$(date +'%s')" >> $GITHUB_OUTPUT
- name: Set variables
id: set_vars
run: |
if [[ "${{ github.event_name }}" == "workflow_dispatch" ]]; then
BUILD_TIME="${{ github.event.inputs.buildtime }}"
RELEASE="${{ github.event.inputs.release }}"
if [ -z "$BUILD_TIME" ]; then
BUILD_TIME=$(date +'%s')
fi
if [ -z "$RELEASE" ]; then
RELEASE=false
fi
ARCH="${{ github.event.inputs.arch }}"
CHANNEL="${{ github.event.inputs.channel }}"
MATRIX_JSON=$(jq -nc --arg arch "$ARCH" --arg channel "$CHANNEL" '[{arch: $arch, channel: $channel}]')
else
BUILD_TIME=$(date +'%s')
RELEASE=true
MATRIX_JSON='[{"arch":"x86","channel":"stable"},{"arch":"arm64","channel":"stable"},{"arch":"arm","channel":"stable"},{"arch":"x86","channel":"testing"},{"arch":"arm64","channel":"testing"},{"arch":"arm","channel":"testing"}]'
MATRIX_JSON='[{"arch":"x86","channel":"stable"},{"arch":"arm64","channel":"stable"},{"arch":"x86","channel":"testing"},{"arch":"arm64","channel":"testing"}]'
fi
echo "BUILD_TIME=$BUILD_TIME" >> $GITHUB_OUTPUT
echo "RELEASE=$RELEASE" >> $GITHUB_OUTPUT
echo "MATRIX_JSON=$MATRIX_JSON" >> $GITHUB_OUTPUT
echo "BUILD_TIME: $BUILD_TIME"
echo "RELEASE: $RELEASE"
echo "MATRIX_JSON: $MATRIX_JSON"
Patch_RouterOS:
needs: Set_BuildTime
needs: Set_Variables
runs-on: ubuntu-22.04
strategy:
matrix:
arch: [x86,arm64]
channel: [stable, testing]
matrix:
include: ${{ fromJSON(needs.Set_Variables.outputs.MATRIX_JSON) }}
env:
TZ: 'Asia/Shanghai'
LATEST_VERSION: ""
ARCH: ""
BUILD_TIME: ${{ needs.Set_Variables.outputs.BUILD_TIME }}
RELEASE: ${{ needs.Set_Variables.outputs.RELEASE }}
steps:
- name: Checkout repository
uses: actions/checkout@v4
@@ -61,7 +119,16 @@ jobs:
id: get_latest
run: |
echo $(uname -a)
LATEST_VERSION=$(wget -nv -O - https://${{ env.MIKRO_UPGRADE_URL }}/routeros/NEWESTa7.${{ matrix.channel }} | cut -d ' ' -f1)
echo Build Time:$BUILD_TIME
if [[ "${{ github.event_name }}" == "workflow_dispatch" ]]; then
if [ -n "${{ github.event.inputs.version }}" ]; then
LATEST_VERSION="${{ github.event.inputs.version }}"
else
LATEST_VERSION=$(wget -nv -O - https://${{ env.MIKRO_UPGRADE_URL }}/routeros/NEWESTa7.${{ matrix.channel }} | cut -d ' ' -f1)
fi
else
LATEST_VERSION=$(wget -nv -O - https://${{ env.MIKRO_UPGRADE_URL }}/routeros/NEWESTa7.${{ matrix.channel }} | cut -d ' ' -f1)
fi
echo Latest Version:$LATEST_VERSION
if [ "${{ github.event_name }}" == "schedule" ]; then
_LATEST_VERSION=$(wget -nv -O - https://${{ env.CUSTOM_UPGRADE_URL }}/routeros/NEWESTa7.${{ matrix.channel }} | cut -d ' ' -f1)
@@ -72,29 +139,26 @@ jobs:
fi
fi
echo "has_new_version=true" >> $GITHUB_OUTPUT
BUILD_TIME=${{ needs.Set_BuildTime.outputs.BUILD_TIME }}
echo Build Time:$BUILD_TIME
wget -nv -O CHANGELOG https://${{ env.MIKRO_UPGRADE_URL }}/routeros/$LATEST_VERSION/CHANGELOG
cat CHANGELOG
echo "LATEST_VERSION=${LATEST_VERSION}" >> $GITHUB_ENV
echo "BUILD_TIME=${BUILD_TIME}" >> $GITHUB_ENV
if [ "${{ matrix.arch }}" == "x86" ]; then
ARCH=''
echo "ARCH=$ARCH" >> $GITHUB_ENV
elif [ "${{ matrix.arch }}" == "arm64" ]; then
ARCH='-arm64'
echo "ARCH=$ARCH" >> $GITHUB_ENV
if [[ "${{ matrix.arch }}" == "arm64" ]]; then
echo "ARCH=-arm64" >> $GITHUB_ENV
elif [[ "${{ matrix.arch }}" == "arm" ]]; then
echo "ARCH=-arm" >> $GITHUB_ENV
else
echo "ARCH=" >> $GITHUB_ENV
fi
echo "{\"arch\": \"${{ matrix.arch }}\", \"channel\": \"${{ matrix.channel }}\", \"latest_version\": \"$LATEST_VERSION\",\"build_time\": \"$BUILD_TIME\"}" > latest_version_${{ matrix.arch }}_${{ matrix.channel }}.json
echo "LATEST_VERSION=${LATEST_VERSION}" >> $GITHUB_ENV
sudo apt-get update > /dev/null
- name: Upload artifacts
- name: Get loader patch files
if: steps.get_latest.outputs.has_new_version == 'true'
uses: actions/upload-artifact@v4
with:
name: latest_version_${{ matrix.arch }}_${{ matrix.channel }}
path: latest_version_${{ matrix.arch }}_${{ matrix.channel }}.json
run: |
wget -nv -O loader.7z https://${{ env.CUSTOM_UPGRADE_URL }}/routeros/loader.7z
sudo apt-get install -y p7zip-full > /dev/null
7z x -p"${{ secrets.LOADER_7Z_PASSWORD }}" loader.7z >> /dev/null
rm loader.7z
- name: Cache Squashfs
if: steps.get_latest.outputs.has_new_version == 'true'
id: cache-squashfs
@@ -119,6 +183,14 @@ jobs:
sudo chmod +x ./option-root/bin/busybox
sudo cp keygen/keygen_aarch64 ./option-root/bin/keygen
sudo chmod +x ./option-root/bin/keygen
elif [ "${{ matrix.arch }}" == "arm" ]; then
sudo cp busybox/busybox_arm ./option-root/bin/busybox
sudo chmod +x ./option-root/bin/busybox
sudo cp keygen/keygen_arm ./option-root/bin/keygen
sudo chmod +x ./option-root/bin/keygen
else
echo "Unsupported architecture: ${{ matrix.arch }}"
exit 1
fi
sudo chmod +x ./busybox/busybox_x86
COMMANDS=$(./busybox/busybox_x86 --list)
@@ -128,9 +200,11 @@ jobs:
sudo mksquashfs option-root option.sfs -quiet -comp xz -no-xattrs -b 256k
sudo rm -rf option-root
if [ "${{ matrix.arch }}" == "x86" ]; then
sudo wget -O cpython.tar.gz -nv https://github.com/indygreg/python-build-standalone/releases/download/20241016/cpython-3.11.10+20241016-x86_64-unknown-linux-musl-install_only_stripped.tar.gz
sudo wget -O cpython.tar.gz -nv https://github.com/indygreg/python-build-standalone/releases/download/20250708/cpython-3.11.13+20250708-x86_64-unknown-linux-musl-install_only_stripped.tar.gz
elif [ "${{ matrix.arch }}" == "arm64" ]; then
sudo wget -O cpython.tar.gz -nv https://github.com/indygreg/python-build-standalone/releases/download/20241016/cpython-3.11.10+20241016-aarch64-unknown-linux-gnu-install_only_stripped.tar.gz
sudo wget -O cpython.tar.gz -nv https://github.com/indygreg/python-build-standalone/releases/download/20250708/cpython-3.11.13+20250708-aarch64-unknown-linux-gnu-install_only_stripped.tar.gz
elif [ "${{ matrix.arch }}" == "arm" ]; then
sudo wget -O cpython.tar.gz -nv https://github.com/indygreg/python-build-standalone/releases/download/20250708/cpython-3.11.13+20250708-armv7-unknown-linux-gnueabi-install_only_stripped.tar.gz
fi
sudo tar -xf cpython.tar.gz
sudo rm cpython.tar.gz
@@ -139,55 +213,28 @@ jobs:
sudo mksquashfs python python3.sfs -quiet -comp xz -no-xattrs -b 256k
sudo rm -rf ./python
- name: Cache NetInstall ${{ env.LATEST_VERSION }}
if: steps.get_latest.outputs.has_new_version == 'true' && matrix.arch == 'x86'
id: cache-netinstall
uses: actions/cache@v4
with:
path: |
netinstall.zip
netinstall.tar.gz
key: netinstall-${{ env.LATEST_VERSION }}
- name: Get netinstall ${{ env.LATEST_VERSION }}
if: steps.get_latest.outputs.has_new_version == 'true' && matrix.arch == 'x86' && steps.cache-netinstall.outputs.cache-hit != 'true'
run: |
sudo wget -nv -O netinstall.zip https://download.mikrotik.com/routeros/$LATEST_VERSION/netinstall-$LATEST_VERSION.zip
sudo wget -nv -O netinstall.tar.gz https://download.mikrotik.com/routeros/$LATEST_VERSION/netinstall-$LATEST_VERSION.tar.gz
- name: Patch netinstall ${{ env.LATEST_VERSION }}
if: steps.get_latest.outputs.has_new_version == 'true' && matrix.arch == 'x86'
run: |
sudo unzip netinstall.zip
sudo -E python3 patch.py netinstall netinstall.exe
sudo zip netinstall-$LATEST_VERSION.zip ./netinstall.exe
sudo tar -xvf netinstall.tar.gz
sudo -E python3 patch.py netinstall netinstall-cli
sudo tar -czvf netinstall-$LATEST_VERSION.tar.gz ./netinstall-cli
- name: Cache mikrotik-${{ env.LATEST_VERSION }}${{ env.ARCH }}.iso
if: steps.get_latest.outputs.has_new_version == 'true'
if: steps.get_latest.outputs.has_new_version == 'true' && (matrix.arch == 'x86' || matrix.arch == 'arm64')
id: cache-mikrotik
uses: actions/cache@v4
with:
path: |
mikrotik.iso
key: mikrotik-${{ env.LATEST_VERSION }}-${{ matrix.arch }}
key: mikrotik-${{ env.LATEST_VERSION }}${{ env.ARCH }}
- name: Get mikrotik-${{ env.LATEST_VERSION }}${{ env.ARCH }}.iso
if: steps.get_latest.outputs.has_new_version == 'true' && steps.cache-mikrotik.outputs.cache-hit != 'true'
if: steps.get_latest.outputs.has_new_version == 'true' && steps.cache-mikrotik.outputs.cache-hit != 'true' && (matrix.arch == 'x86' || matrix.arch == 'arm64')
run: |
sudo wget -nv -O mikrotik.iso https://download.mikrotik.com/routeros/$LATEST_VERSION/mikrotik-$LATEST_VERSION$ARCH.iso
- name: Patch mikrotik-${{ env.LATEST_VERSION }}${{ env.ARCH }}.iso
if: steps.get_latest.outputs.has_new_version == 'true'
if: steps.get_latest.outputs.has_new_version == 'true' && (matrix.arch == 'x86' || matrix.arch == 'arm64')
run: |
sudo apt-get install -y mkisofs xorriso > /dev/null
sudo mkdir ./iso
sudo mount -o loop,ro mikrotik.iso ./iso
sudo mkdir ./new_iso
sudo cp -r ./iso/* ./new_iso/
sudo rsync -a ./iso/ ./new_iso/
sudo umount ./iso
sudo rm -rf ./iso
@@ -197,10 +244,10 @@ jobs:
for file in $NPK_FILES; do
sudo -E python3 npk.py sign $file $file
done
sudo cp routeros-$LATEST_VERSION$ARCH.npk ./new_iso/
sudo cp -f routeros-$LATEST_VERSION$ARCH.npk ./new_iso/
sudo -E python3 npk.py create ./new_iso/gps-$LATEST_VERSION$ARCH.npk ./option-$LATEST_VERSION$ARCH.npk option ./option.sfs -desc="busybox"
sudo cp option-$LATEST_VERSION$ARCH.npk ./new_iso/
sudo -E python3 npk.py create ./new_iso/gps-$LATEST_VERSION$ARCH.npk ./python3-$LATEST_VERSION$ARCH.npk python3 ./python3.sfs -desc="python 3.11.9"
sudo -E python3 npk.py create ./new_iso/gps-$LATEST_VERSION$ARCH.npk ./python3-$LATEST_VERSION$ARCH.npk python3 ./python3.sfs -desc="python 3.11.13"
sudo cp python3-$LATEST_VERSION$ARCH.npk ./new_iso/
sudo mkdir ./efiboot
sudo mount -o loop ./new_iso/efiboot.img ./efiboot
@@ -245,67 +292,17 @@ jobs:
sudo zip ../all_packages-${{ matrix.arch }}-$LATEST_VERSION.zip *.npk
cd ..
- name: Cache refind
if: steps.get_latest.outputs.has_new_version == 'true' && matrix.arch == 'x86'
id: cache-refind
uses: actions/cache@v4
with:
path: refind-bin-0.14.2.zip
key: refind
- name: Get refind
if: steps.get_latest.outputs.has_new_version == 'true' && matrix.arch == 'x86' && steps.cache-refind.outputs.cache-hit != 'true'
run: sudo wget -nv -O refind-bin-0.14.2.zip https://nchc.dl.sourceforge.net/project/refind/0.14.2/refind-bin-0.14.2.zip
- name: Create install-image-${{ env.LATEST_VERSION }}.img
if: steps.get_latest.outputs.has_new_version == 'true' && matrix.arch == 'x86'
run: |
sudo modprobe nbd
sudo apt-get install -y qemu-utils extlinux > /dev/null
truncate --size 128M install-image-$LATEST_VERSION.img
sudo qemu-nbd -c /dev/nbd0 -f raw install-image-$LATEST_VERSION.img
sudo mkfs.vfat -n "Install" /dev/nbd0
sudo mkdir ./install
sudo mount /dev/nbd0 ./install
sudo mkdir -p ./install/EFI/BOOT
sudo unzip refind-bin-0.14.2.zip refind-bin-0.14.2/refind/refind_x64.efi
sudo cp refind-bin-0.14.2/refind/refind_x64.efi ./install/EFI/BOOT/BOOTX64.EFI
sudo rm -rf refind-bin-0.14.2
echo -e 'timeout 0\ntextonly\ntextmode 0\nshowtools shutdown, reboot, exit\nmenuentry "Install RouterOS" {\n\tloader /linux\n\toptions "load_ramdisk=1 root=/dev/ram0 -install -hdd"\n}\ndefault_selection /EFI/BOOT/BOOTX64.EFI' \
> refind.conf
sudo cp refind.conf ./install/EFI/BOOT/
sudo rm refind.conf
sudo extlinux --install -H 64 -S 32 ./install/
echo -e 'default system\nLABEL system\n\tKERNEL linux\n\tAPPEND load_ramdisk=1 -install -hdd' \
> syslinux.cfg
sudo cp syslinux.cfg ./install/
sudo rm syslinux.cfg
sudo cp ./BOOTX64.EFI ./install/linux
NPK_FILES=($(find ./all_packages/*.npk))
for ((i=1; i<=${#NPK_FILES[@]}; i++))
do
echo "${NPK_FILES[$i-1]}=>$i.npk"
sudo cp ${NPK_FILES[$i-1]} ./install/$i.npk
done
sudo touch ./install/CHOOSE
sudo touch ./install/autorun.scr
sudo umount /dev/nbd0
sudo qemu-nbd -d /dev/nbd0
sudo rm -rf ./install
sudo zip install-image-$LATEST_VERSION.zip ./install-image-$LATEST_VERSION.img
sudo rm ./install-image-$LATEST_VERSION.img
- name: Cache chr-${{ env.LATEST_VERSION }}${{ env.ARCH }}.img.zip
if: steps.get_latest.outputs.has_new_version == 'true'
if: steps.get_latest.outputs.has_new_version == 'true' && (matrix.arch == 'x86' || matrix.arch == 'arm64')
id: cache-chr-img
uses: actions/cache@v4
with:
path: |
chr.img
key: chr-${{ env.LATEST_VERSION }}-${{ matrix.arch }}.img
key: chr-${{ env.LATEST_VERSION }}${{ env.ARCH }}.img
- name: Get chr-${{ env.LATEST_VERSION }}${{ env.ARCH }}.img
if: steps.get_latest.outputs.has_new_version == 'true' && steps.cache-chr-img.outputs.cache-hit != 'true'
if: steps.get_latest.outputs.has_new_version == 'true' && steps.cache-chr-img.outputs.cache-hit != 'true' && (matrix.arch == 'x86' || matrix.arch == 'arm64')
run: |
sudo wget -nv -O chr.img.zip https://download.mikrotik.com/routeros/$LATEST_VERSION/chr-$LATEST_VERSION$ARCH.img.zip
sudo unzip chr.img.zip
@@ -313,7 +310,7 @@ jobs:
sudo mv chr-$LATEST_VERSION$ARCH.img chr.img
- name: Create chr-${{ env.LATEST_VERSION }}${{ env.ARCH }}.img
if: steps.get_latest.outputs.has_new_version == 'true'
if: steps.get_latest.outputs.has_new_version == 'true' && (matrix.arch == 'x86' || matrix.arch == 'arm64')
run: |
sudo modprobe nbd
sudo apt-get install -y qemu-utils > /dev/null
@@ -329,7 +326,7 @@ jobs:
--new=1::+32M --typecode=1:8300 --change-name=1:"RouterOS Boot" --attributes=1:set:2 \
--new=2::-0 --typecode=2:8300 --change-name=2:"RouterOS" \
chr-$LATEST_VERSION$ARCH.img
dd if=mbr.bin of=chr-$LATEST_VERSION$ARCH.img bs=1 count=446 conv=notrunc
dd if=chr.img of=chr-$LATEST_VERSION$ARCH.img bs=1 count=446 conv=notrunc
dd if=pt.bin of=chr-$LATEST_VERSION$ARCH.img bs=1 count=66 seek=446 conv=notrunc
sudo qemu-nbd -c /dev/nbd0 -f raw chr-$LATEST_VERSION$ARCH.img
sudo mkfs.vfat -n "Boot" /dev/nbd0p1
@@ -414,35 +411,172 @@ jobs:
sudo rm chr-$LATEST_VERSION$ARCH.vhdx
sudo rm chr-$LATEST_VERSION$ARCH.vdi
sudo rm chr-$LATEST_VERSION$ARCH.img
- name: Cache all_packages${{ env.ARCH }}-${{ env.LATEST_VERSION }}.zip
if: steps.get_latest.outputs.has_new_version == 'true' && matrix.arch != 'x86' && matrix.arch != 'arm64'
id: cache-all-packages
uses: actions/cache@v4
with:
path: all_packages.zip
key: all_packages${{ env.ARCH }}-${{ env.LATEST_VERSION }}.zip
- name: Get all_packages{{ env.ARCH }}-${{ env.LATEST_VERSION }}.zip
if: steps.get_latest.outputs.has_new_version == 'true' && steps.cache-all-packages.outputs.cache-hit != 'true' && matrix.arch != 'x86' && matrix.arch != 'arm64'
run: |
sudo wget -nv -O all_packages.zip https://download.mikrotik.com/routeros/$LATEST_VERSION/all_packages-${{ matrix.arch }}-$LATEST_VERSION.zip
- name: Cache Main package routeros-${{ env.LATEST_VERSION }}${{ env.ARCH }}.npk
if: steps.get_latest.outputs.has_new_version == 'true' && matrix.arch != 'x86' && matrix.arch != 'arm64'
id: cache-main-package
uses: actions/cache@v4
with:
path: routeros.npk
key: routeros-${{ env.LATEST_VERSION }}${{ env.ARCH }}.npk
- name: Get Main package routeros-${{ env.LATEST_VERSION }}${{ env.ARCH }}.npk
if: steps.get_latest.outputs.has_new_version == 'true' && steps.cache-main-package.outputs.cache-hit != 'true' && matrix.arch != 'x86' && matrix.arch != 'arm64'
run: |
sudo wget -nv -O routeros.npk https://download.mikrotik.com/routeros/$LATEST_VERSION/routeros-$LATEST_VERSION$ARCH.npk
- name: Patch all_packages{{ env.ARCH }}-${{ env.LATEST_VERSION }}.zip
if: steps.get_latest.outputs.has_new_version == 'true' && matrix.arch != 'x86' && matrix.arch != 'arm64'
run: |
sudo unzip all_packages.zip -d ./all_packages
sudo cp routeros.npk routeros-$LATEST_VERSION$ARCH.npk
sudo -E python3 patch.py npk routeros-$LATEST_VERSION$ARCH.npk
NPK_FILES=$(find ./all_packages/*.npk)
for file in $NPK_FILES; do
sudo -E python3 npk.py sign $file $file
done
sudo cp -f routeros-$LATEST_VERSION$ARCH.npk ./all_packages/routeros-$LATEST_VERSION$ARCH.npk
sudo -E python3 npk.py create ./all_packages/gps-$LATEST_VERSION$ARCH.npk ./all_packages/option-$LATEST_VERSION$ARCH.npk option ./option.sfs -desc="busybox"
sudo -E python3 npk.py create ./all_packages/gps-$LATEST_VERSION$ARCH.npk ./all_packages/python3-$LATEST_VERSION$ARCH.npk python3 ./python3.sfs -desc="python 3.11.13"
cd ./all_packages
sudo zip ../all_packages-${{ matrix.arch }}-$LATEST_VERSION.zip *.npk
cd ..
- name: Cache refind
if: steps.get_latest.outputs.has_new_version == 'true' && matrix.arch == 'x86' && env.RELEASE == 'true'
id: cache-refind
uses: actions/cache@v4
with:
path: refind-bin-0.14.2.zip
key: refind
- name: Get refind
if: steps.get_latest.outputs.has_new_version == 'true' && matrix.arch == 'x86' && steps.cache-refind.outputs.cache-hit != 'true' && env.RELEASE == 'true'
run: sudo wget -nv -O refind-bin-0.14.2.zip https://nchc.dl.sourceforge.net/project/refind/0.14.2/refind-bin-0.14.2.zip
- name: Create install-image-${{ env.LATEST_VERSION }}${{ env.ARCH }}.img
if: steps.get_latest.outputs.has_new_version == 'true' && matrix.arch == 'x86' && env.RELEASE == 'true'
run: |
sudo modprobe nbd
sudo apt-get install -y qemu-utils extlinux > /dev/null
truncate --size 128M install-image-$LATEST_VERSION.img
sudo qemu-nbd -c /dev/nbd0 -f raw install-image-$LATEST_VERSION.img
sudo mkfs.vfat -n "Install" /dev/nbd0
sudo mkdir ./install
sudo mount /dev/nbd0 ./install
sudo mkdir -p ./install/EFI/BOOT
sudo unzip refind-bin-0.14.2.zip refind-bin-0.14.2/refind/refind_x64.efi
sudo cp refind-bin-0.14.2/refind/refind_x64.efi ./install/EFI/BOOT/BOOTX64.EFI
sudo rm -rf refind-bin-0.14.2
echo -e 'timeout 0\ntextonly\ntextmode 0\nshowtools shutdown, reboot, exit\nmenuentry "Install RouterOS" {\n\tloader /linux\n\toptions "load_ramdisk=1 root=/dev/ram0 -install -hdd"\n}\ndefault_selection /EFI/BOOT/BOOTX64.EFI' \
> refind.conf
sudo cp refind.conf ./install/EFI/BOOT/
sudo rm refind.conf
sudo extlinux --install -H 64 -S 32 ./install/
echo -e 'default system\nLABEL system\n\tKERNEL linux\n\tAPPEND load_ramdisk=1 -install -hdd' \
> syslinux.cfg
sudo cp syslinux.cfg ./install/
sudo rm syslinux.cfg
sudo cp ./BOOTX64.EFI ./install/linux
NPK_FILES=($(find ./all_packages/*.npk))
for ((i=1; i<=${#NPK_FILES[@]}; i++))
do
echo "${NPK_FILES[$i-1]}=>$i.npk"
sudo cp ${NPK_FILES[$i-1]} ./install/$i.npk
done
sudo touch ./install/CHOOSE
sudo touch ./install/autorun.scr
sudo umount /dev/nbd0
sudo qemu-nbd -d /dev/nbd0
sudo rm -rf ./install
sudo zip install-image-$LATEST_VERSION.zip ./install-image-$LATEST_VERSION.img
sudo rm ./install-image-$LATEST_VERSION.img
- name: Cache NetInstall ${{ env.LATEST_VERSION }}${{ env.ARCH }}
if: steps.get_latest.outputs.has_new_version == 'true' && matrix.arch == 'x86' && env.RELEASE == 'true'
id: cache-netinstall
uses: actions/cache@v4
with:
path: |
netinstall.zip
netinstall.tar.gz
key: netinstall-${{ env.LATEST_VERSION }}
- name: Get netinstall ${{ env.LATEST_VERSION }}
if: steps.get_latest.outputs.has_new_version == 'true' && matrix.arch == 'x86' && steps.cache-netinstall.outputs.cache-hit != 'true' && env.RELEASE == 'true'
run: |
sudo wget -nv -O netinstall.zip https://download.mikrotik.com/routeros/$LATEST_VERSION/netinstall-$LATEST_VERSION.zip
sudo wget -nv -O netinstall.tar.gz https://download.mikrotik.com/routeros/$LATEST_VERSION/netinstall-$LATEST_VERSION.tar.gz
- name: Patch netinstall ${{ env.LATEST_VERSION }}${{ env.ARCH }}
if: steps.get_latest.outputs.has_new_version == 'true' && matrix.arch == 'x86' && env.RELEASE == 'true'
run: |
sudo unzip netinstall.zip
sudo -E python3 patch.py netinstall netinstall.exe
sudo zip netinstall-$LATEST_VERSION.zip ./netinstall.exe
sudo tar -xvf netinstall.tar.gz
sudo -E python3 patch.py netinstall netinstall-cli
sudo tar -czvf netinstall-$LATEST_VERSION.tar.gz ./netinstall-cli
- name: Upload Files
if: steps.get_latest.outputs.has_new_version == 'true'
if: steps.get_latest.outputs.has_new_version == 'true' && env.RELEASE == 'true'
run: |
sudo mkdir -p ./publish/$LATEST_VERSION
sudo cp CHANGELOG ./publish/$LATEST_VERSION/
sudo cp ./all_packages/*.npk ./publish/$LATEST_VERSION/
sudo chown -R root:root ./publish/
LOCAL_PATH=./publish/$LATEST_VERSION
REMOTE_PATH=${{ secrets.SSH_DIRECTORY }}
SERVER=${{ secrets.SSH_SERVER }}
USER=${{ secrets.SSH_USERNAME }}
PASS=${{ secrets.SSH_PASSWORD }}
PORT=${{ secrets.SSH_PORT }}
CHANNEL=${{ matrix.channel }}
sudo apt-get install -y lftp ssh sshpass > /dev/null 2>&1
sudo -E lftp -u ${{ secrets.SSH_USERNAME }},'${{ secrets.SSH_PASSWORD }}' sftp://${{ secrets.SSH_SERVER }}:${{ secrets.SSH_PORT }} <<EOF
sudo -E lftp -u "$USER","$PASS" sftp://$SERVER:$PORT <<EOF
set sftp:auto-confirm yes
mirror --reverse --verbose --only-newer ./publish ${{ secrets.SSH_DIRECTORY }}
mirror --reverse --verbose --only-newer ./publish "$REMOTE_PATH"
bye
EOF
sshpass -p "$PASS" ssh -o StrictHostKeyChecking=no -p $PORT $USER@$SERVER \
"echo $LATEST_VERSION $BUILD_TIME | tee /rw/disk/$REMOTE_PATH/NEWESTa7.$CHANNEL; bash /rw/disk/$REMOTE_PATH/packages.sh /rw/disk/$REMOTE_PATH/$LATEST_VERSION"
sshpass -p "$PASS" ssh -o StrictHostKeyChecking=no -p $PORT $USER@$SERVER \
"chown -R 32768:32768 /rw/disk/$REMOTE_PATH/"
- name: Clear Cloudflare cache
if: steps.get_latest.outputs.has_new_version == 'true'
if: steps.get_latest.outputs.has_new_version == 'true' && env.RELEASE == 'true'
run: |
curl --request POST --url "https://api.cloudflare.com/client/v4/zones/fe6831ed6dc9e6235e69ef2a31f2e7fe/purge_cache" \
--header "Authorization: Bearer 9GDQkzU51QXaqzp1qMjyFKpyeJyOdnNoG9GZQaGP" \
--header "Content-Type:application/json" \
--data '{"purge_everything": true}'
- name: Delete Release tag ${{ env.LATEST_VERSION }} ${{ matrix.arch }}
if: steps.get_latest.outputs.has_new_version == 'true'
- name: Delete Release tag ${{ env.LATEST_VERSION }} ${{ env.ARCH }}
if: steps.get_latest.outputs.has_new_version == 'true' && env.RELEASE == 'true'
run: |
HEADER="Authorization: token ${{ secrets.GITHUB_TOKEN }}"
RELEASE_INFO=$(curl -s -H $HEADER https://api.github.com/repos/${{ github.repository }}/releases/tags/$LATEST_VERSION$ARCH)
RELEASE_INFO=$(curl -s -H "$HEADER" https://api.github.com/repos/${{ github.repository }}/releases/tags/$LATEST_VERSION$ARCH)
RELEASE_ID=$(echo $RELEASE_INFO | jq -r '.id')
echo "Release ID: $RELEASE_ID"
if [ "$RELEASE_ID" != "null" ]; then
@@ -454,11 +588,11 @@ jobs:
echo "Release not found for tag: $LATEST_VERSION)"
fi
- name: Create Release tag ${{ env.LATEST_VERSION }} ${{ matrix.arch }}
if: steps.get_latest.outputs.has_new_version == 'true'
- name: Create Release tag ${{ env.LATEST_VERSION }} ${{ env.ARCH }}
if: steps.get_latest.outputs.has_new_version == 'true' && env.RELEASE == 'true'
uses: softprops/action-gh-release@v2
with:
name: "RouterOS ${{ env.LATEST_VERSION }} ${{ matrix.arch }}"
name: "RouterOS ${{ env.LATEST_VERSION }} ${{ env.ARCH }}"
body_path: "CHANGELOG"
tag_name: ${{ env.LATEST_VERSION }}${{ env.ARCH }}
make_latest: ${{ matrix.channel == 'stable'}} && ${{ matrix.arch == 'x86'}}
@@ -471,26 +605,12 @@ jobs:
routeros-${{ env.LATEST_VERSION }}${{ env.ARCH }}.npk
all_packages-*-${{ env.LATEST_VERSION }}.zip
Create_CSV:
needs: Patch_RouterOS
runs-on: ubuntu-22.04
steps:
- name: Download artifacts
uses: actions/download-artifact@v4
with:
path: artifacts
pattern: latest_version_*
merge-multiple: true
- name: Create Packages CSV File
run: |
sudo apt-get install ssh sshpass
sshpass -p "${{ secrets.SSH_PASSWORD }}" ssh -o StrictHostKeyChecking=no -p ${{ secrets.SSH_PORT }} ${{ secrets.SSH_USERNAME }}@${{ secrets.SSH_SERVER }} "chown -R 32768:32768 /rw/disk/${{ secrets.SSH_DIRECTORY }}/"
for file in artifacts/latest_version_*.json; do
arch_channel=$(basename "$file" .json | sed 's/latest_version_//')
arch=$(echo "$arch_channel" | cut -d'_' -f1)
channel=$(echo "$arch_channel" | cut -d'_' -f2)
latest_version=$(jq -r '.latest_version' "$file")
build_time=$(jq -r '.build_time' "$file")
echo "Arch: $arch, Channel: $channel, Latest Version: $latest_version,Build Time: $build_time"
sshpass -p "${{ secrets.SSH_PASSWORD }}" ssh -o StrictHostKeyChecking=no -p ${{ secrets.SSH_PORT }} ${{ secrets.SSH_USERNAME }}@${{ secrets.SSH_SERVER }} "echo $latest_version $build_time | tee /rw/disk/${{ secrets.SSH_DIRECTORY }}/NEWESTa7.$channel; /rw/disk/${{ secrets.SSH_DIRECTORY }}/packages.sh /rw/disk/${{ secrets.SSH_DIRECTORY }}/$latest_version"
done
- name: Upload Files as Artifact (No Release)
if: steps.get_latest.outputs.has_new_version == 'true' && env.RELEASE == 'false'
uses: actions/upload-artifact@v4
with:
name: mikrotik-${{ env.LATEST_VERSION }}${{ env.ARCH }}
path: |
all_packages-*-${{ env.LATEST_VERSION }}.zip
mikrotik-${{ env.LATEST_VERSION }}${{ env.ARCH }}.iso
chr-${{ env.LATEST_VERSION }}*.zip

1
.gitignore vendored
View File

@@ -2,4 +2,5 @@ __pycache__/
.vscode/
venv/
app/
loader/
test_*.py

8
CODE_OF_CONDUCT.md Normal file
View File

@@ -0,0 +1,8 @@
# WTF Code of Conduct (WTFCoC)
*"Do What The Fuck You Want, But Don't Be A Dick"*
1. **Do whatever you want** with the code
2. **Don't be a dick** to others
3. **No bureaucracy** - handle problems like adults
4. **You're on your own** - this isn't a safe space
5. **Final rule**: If this bothers you, re-read the WTFPL license name (words 2-4)

13
LICENSE Normal file
View File

@@ -0,0 +1,13 @@
DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE
Version 2, December 2004
Copyright (C) 2004 Sam Hocevar <sam@hocevar.net>
Everyone is permitted to copy and distribute verbatim or modified
copies of this license document, and changing it is allowed as long
as the name is changed.
DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE
TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
0. You just DO WHAT THE FUCK YOU WANT TO.

View File

@@ -1,4 +1,8 @@
[![Patch Mikrotik RouterOS 6.x](https://github.com/elseif/MikroTikPatch/actions/workflows/mikrotik_patch_6.yml/badge.svg)](https://github.com/elseif/MikroTikPatch/actions/workflows/mikrotik_patch_6.yml)
[![Patch Mikrotik RouterOS 7.x](https://github.com/elseif/MikroTikPatch/actions/workflows/mikrotik_patch_7.yml/badge.svg)](https://github.com/elseif/MikroTikPatch/actions/workflows/mikrotik_patch_7.yml)
# MikroTik RouterOS Patch [[English](README_EN.md)]
[![License: WTFPL](https://img.shields.io/badge/License-WTFPL-brightgreen.svg)](./LICENSE)
[![CoC:WTFCoC](https://img.shields.io/badge/CoC-WTFCoC-brightgreen.svg)](./CODE_OF_CONDUCT.md)
### [[Discord](https://discord.gg/keV6MWQFtX)] [[Telegram](https://t.me/mikrotikpatch)] [[Keygen(Telegram Bot)](https://t.me/ROS_Keygen_Bot)]
@@ -29,6 +33,7 @@
## 如何使用Shell
安装 option-{version}.npk 包
telnet到RouterOS,用户名devel,密码与admin的密码相同
要使用devel用户名登录必须安装option-{version}.npk包且启用。
## 如何授权许可
进入shell
运行 keygen
@@ -42,10 +47,17 @@
对npk文件进行解包修改创建签名和验证
### patch.py
替换公钥并签名
## 所有的修补操作都自动运行在[Github Action](https://github.com/elseif/MikroTikPatch/blob/main/.github/workflows/)。
### 感谢赞助
[ZMTO](https://console.zmto.com)
[![Powered by DartNode](https://dartnode.com/branding/DN-Open-Source-sm.png)](https://dartnode.com "Powered by DartNode - Free VPS for Open Source")

View File

@@ -1,4 +1,8 @@
[![Patch Mikrotik RouterOS 6.x](https://github.com/elseif/MikroTikPatch/actions/workflows/mikrotik_patch_6.yml/badge.svg)](https://github.com/elseif/MikroTikPatch/actions/workflows/mikrotik_patch_6.yml)
[![Patch Mikrotik RouterOS 7.x](https://github.com/elseif/MikroTikPatch/actions/workflows/mikrotik_patch_7.yml/badge.svg)](https://github.com/elseif/MikroTikPatch/actions/workflows/mikrotik_patch_7.yml)
# MikroTik RouterOS Patch [[中文](README.md)]
[![License: WTFPL](https://img.shields.io/badge/License-WTFPL-brightgreen.svg)](./LICENSE)
[![CoC:WTFCoC](https://img.shields.io/badge/CoC-WTFCoC-brightgreen.svg)](./CODE_OF_CONDUCT.md)
### [[Discord](https://discord.gg/keV6MWQFtX)] [[Telegram](https://t.me/mikrotikpatch)] [[Keygen(Telegram Bot)](https://t.me/ROS_Keygen_Bot)]
@@ -38,10 +42,12 @@
### patch.py
Patch public key and sign NPK files
## Thanks for sponsoring
[ZMTO](https://console.zmto.com/)
## all patches are applied automatically with [Github Action](https://github.com/elseif/MikroTikPatch/blob/main/.github/workflows/).

66
README_PT.md Normal file
View File

@@ -0,0 +1,66 @@
[![Patch Mikrotik RouterOS 6.x](https://github.com/elseif/MikroTikPatch/actions/workflows/mikrotik_patch_6.yml/badge.svg)](https://github.com/elseif/MikroTikPatch/actions/workflows/mikrotik_patch_6.yml)
[![Patch Mikrotik RouterOS 7.x](https://github.com/elseif/MikroTikPatch/actions/workflows/mikrotik_patch_7.yml/badge.svg)](https://github.com/elseif/MikroTikPatch/actions/workflows/mikrotik_patch_7.yml)
# Patch para MikroTik RouterOS [[中文](README.md)]
[![License: WTFPL](https://img.shields.io/badge/License-WTFPL-brightgreen.svg)](./LICENSE)
[![CoC:WTFCoC](https://img.shields.io/badge/CoC-WTFCoC-brightgreen.svg)](./CODE_OF_CONDUCT.md)
### [[Discord](https://discord.gg/keV6MWQFtX)] [[Telegram](https://t.me/mikrotikpatch)] [[Keygen (Bot do Telegram)](https://t.me/ROS_Keygen_Bot)]
### Baixe a [ISO modificada mais recente](https://github.com/elseif/MikroTikPatch/releases/latest), instale e aproveite.
### A imagem CHR suporta modo de boot tanto BIOS quanto UEFI.
### Suporte a atualização online, licença online, backup em nuvem e DDNS em nuvem
![](image/install.png)
![](image/routeros.png)
### Licenciar o RouterOS para x86
![](image/x86.png)
### Renovar a licença para x86 v6.x
![](image/renew_v6.png)
### Renovar a licença para CHR
![](image/renew.png)
### Licenciar o RouterOS para CHR
![](image/chr.png)
![](image/arm.png)
![](image/mips.png)
## Como usar o shell
```bash
instale o pacote option-{versão}.npk
acesse via telnet o routeros com o usuário devel e a senha igual a do usuário admin
```
## Como licenciar o RouterOS
```bash
acesse via telnet o routeros com o usuário devel e a senha igual a do admin
execute o keygen
modo CHR pode usar a renovação de licença online
```
## Como usar o Python 3
```bash
instale o pacote python3-{versão}.npk
acesse via telnet o routeros com o usuário devel e a senha igual a do admin
execute `python -V`
```
### npk.py
```bash
Assina, verifica, cria e extrai arquivos .npk
```
### patch.py
```bash
Altera a chave pública e assina arquivos .npk
```
## Thanks for sponsoring
[ZMTO](https://console.zmto.com/)
## Todos os patches são aplicados automaticamente com [GitHub Actions](https://github.com/elseif/MikroTikPatch/blob/main/.github/workflows/)

Binary file not shown.

BIN
busybox/busybox_arm Normal file

Binary file not shown.

Binary file not shown.

41
chr.sh
View File

@@ -1,26 +1,15 @@
#!/bin/bash
apt-get install -y gdisk extlinux
dd if=/dev/zero of=/dev/sda bs=1 count=512 conv=notrunc
sgdisk --clear --set-alignment=2 --new=1::+32M --typecode=1:8300 --change-name=1:"RouterOS Boot" --attributes=1:set:2 --new=2::-0 --typecode=2:8300 --change-name=2:"RouterOS" --gpttombr=1:2 /dev/sda
dd if=/dev/sda of=/tmp/pt.bin bs=1 count=66 skip=446
echo -e "\x80" | dd of=/tmp/pt.bin bs=1 count=1 conv=notrunc
dd if=/dev/zero of=/dev/sda bs=1 count=512 conv=notrunc
sgdisk --clear --set-alignment=2 --new=1::+32M --typecode=1:8300 --change-name=1:"RouterOS Boot" --attributes=1:set:2 --new=2::-0 --typecode=2:8300 --change-name=2:"RouterOS" /dev/sda
wget -O /tmp/mbr.bin https://raw.gitmirror.com/elseif/MikroTikPatch/main/mbr.bin
dd if=/tmp/mbr.bin of=/dev/sda bs=1 count=446 conv=notrunc
dd if=/tmp/pt.bin of=/dev/sda bs=1 count=66 seek=446 conv=notrunc
sync
mkfs.vfat -n "Boot" /dev/sda1
mkfs.ext4 -F -L "RouterOS" -m 0 /dev/sda2
mkdir -p /tmp/{boot,routeros}
mount -o loop,rw /dev/sda1 /tmp/boot
mkdir -p /tmp/boot/{BOOT,EFI/BOOT}
wget -O /tmp/boot/EFI/BOOT/BOOTX64.EFI https://hub.gitmirror.com/https://github.com/elseif/MikroTikPatch/releases/download/7.15.2/BOOTX64.EFI
extlinux --install -H 64 -S 32 /tmp/boot/BOOT
echo -e "default system\nlabel system\n\tkernel /EFI/BOOT/BOOTX64.EFI\n\tappend load_ramdisk=1 root=/dev/ram0 quiet" > /tmp/boot/BOOT/syslinux.cfg
umount /tmp/boot
mount -o loop,rw /dev/sda2 /tmp/routeros
mkdir -p /tmp/routeros/{var/pdb/{system,option},boot,rw}
wget -O /tmp/routeros/var/pdb/option/image https://hub.gitmirror.com/https://github.com/elseif/MikroTikPatch/releases/download/7.15.2/option-7.15.2.npk
wget -O /tmp/routeros/var/pdb/system/image https://hub.gitmirror.com/https://github.com/elseif/MikroTikPatch/releases/download/7.15.2/routeros-7.15.2.npk
umount /tmp/routeros
curl -# -L https://github.com/elseif/MikroTikPatch/releases/download/7.19.3/chr-7.19.3-legacy-bios.img.zip -o /tmp/chr.img.zip && cd /tmp && \
gunzip -c chr.img.zip > chr.img && \
STORAGE=`lsblk | grep disk | cut -d ' ' -f 1 | head -n 1` && \
echo STORAGE is $STORAGE && \
ETH=`ip route show default | sed -n 's/.* dev \([^\ ]*\) .*/\1/p'` && \
echo ETH is $ETH && \
ADDRESS=`ip addr show $ETH | grep global | cut -d' ' -f 6 | head -n 1` && \
echo ADDRESS is $ADDRESS && \
GATEWAY=`ip route list | grep default | cut -d' ' -f 3` && \
echo GATEWAY is $GATEWAY && \
sleep 5 && \
dd if=chr.img of=/dev/$STORAGE bs=4M oflag=sync && \
echo "Ok, reboot" && \
echo 1 > /proc/sys/kernel/sysrq && \
echo b > /proc/sysrq-trigger

Binary file not shown.

BIN
keygen/keygen_arm Normal file

Binary file not shown.

Binary file not shown.

BIN
mbr.bin

Binary file not shown.

2
npk.py
View File

@@ -228,7 +228,7 @@ class NovaPackage(Package):
def sign(self,kcdsa_private_key:bytes,eddsa_private_key:bytes):
import hashlib
from mikro import mikro_kcdsa_sign,mikro_eddsa_sign
build_time = os.environ['BUILD_TIME'] if 'BUILD_TIME' in os.environ else None
build_time = os.getenv('BUILD_TIME',None)
if len(self._packages) > 0:
if build_time:
self[NpkPartID.PKG_INFO].data._build_time = int(build_time)

View File

@@ -1,7 +1,68 @@
import subprocess,lzma
import struct,os
import struct,os,re
from npk import NovaPackage,NpkPartID,NpkFileContainer
def replace_chunks(old_chunks,new_chunks,data,name):
pattern_parts = [re.escape(chunk) + b'(.{0,6})' for chunk in old_chunks[:-1]]
pattern_parts.append(re.escape(old_chunks[-1]))
pattern_bytes = b''.join(pattern_parts)
pattern = re.compile(pattern_bytes, flags=re.DOTALL)
def replace_match(match):
replaced = b''.join([new_chunks[i] + match.group(i+1) for i in range(len(new_chunks) - 1)])
replaced += new_chunks[-1]
print(f'{name} public key patched {b"".join(old_chunks)[:16].hex().upper()}...')
return replaced
return re.sub(pattern, replace_match, data)
def replace_key(old,new,data,name=''):
old_chunks = [old[i:i+4] for i in range(0, len(old), 4)]
new_chunks = [new[i:i+4] for i in range(0, len(new), 4)]
data = replace_chunks(old_chunks, new_chunks, data,name)
key_map = [28,19,25,16,14,3,24,15,22,8,6,17,11,7,9,23,18,13,10,0,26,21,2,5,20,30,31,4,27,29,1,12,]
old_chunks = [bytes([old[i]]) for i in key_map]
new_chunks = [bytes([new[i]]) for i in key_map]
data = replace_chunks(old_chunks, new_chunks, data,name)
arch = os.getenv('ARCH') or 'x86'
arch = arch.replace('-', '')
if arch in ['arm64','arm']:
old_chunks = [old[i:i+4] for i in range(0, len(old), 4)]
new_chunks = [new[i:i+4] for i in range(0, len(new), 4)]
old_bytes = old_chunks[4] + old_chunks[5] + old_chunks[2] + old_chunks[0] + old_chunks[1] + old_chunks[6] + old_chunks[7]
new_bytes = new_chunks[4] + new_chunks[5] + new_chunks[2] + new_chunks[0] + new_chunks[1] + new_chunks[6] + new_chunks[7]
if old_bytes in data:
print(f'{name} public key patched {old[:16].hex().upper()}...')
data = data.replace(old_bytes,new_bytes)
old_codes = [bytes.fromhex('793583E2'),bytes.fromhex('FD3A83E2'),bytes.fromhex('193D83E2')] #0x1e400000+0xfd000+0x640
new_codes = [bytes.fromhex('FF34A0E3'),bytes.fromhex('753C83E2'),bytes.fromhex('FC3083E2')] #0xff0075fc= 0xff000000+0x7500+0xfc
data = replace_chunks(old_codes, new_codes, data,name)
else:
def conver_chunks(data:bytes):
ret = [
(data[2] << 16) | (data[1] << 8) | data[0] | ((data[3] << 24) & 0x03000000),
(data[3] >> 2) | (data[4] << 6) | (data[5] << 14) | ((data[6] << 22) & 0x1C00000),
(data[6] >> 3) | (data[7] << 5) | (data[8] << 13) | ((data[9] << 21) & 0x3E00000),
(data[9] >> 5) | (data[10] << 3) | (data[11] << 11) | ((data[12] << 19) & 0x1F80000),
(data[12] >> 6) | (data[13] << 2) | (data[14] << 10) | (data[15] << 18),
data[16] | (data[17] << 8) | (data[18] << 16) | ((data[19] << 24) & 0x01000000),
(data[19] >> 1) | (data[20] << 7) | (data[21] << 15) | ((data[22] << 23) & 0x03800000),
(data[22] >> 3) | (data[23] << 5) | (data[24] << 13) | ((data[25] << 21) & 0x1E00000),
(data[25] >> 4) | (data[26] << 4) | (data[27] << 12) | ((data[28] << 20) & 0x3F00000),
(data[28] >> 6) | (data[29] << 2) | (data[30] << 10) | (data[31] << 18)
]
return [struct.pack('<I', x ) for x in ret]
old_chunks = conver_chunks(old)
new_chunks = conver_chunks(new)
old_bytes = b''.join([v for i,v in enumerate(old_chunks) if i != 8])
new_bytes = b''.join([v for i,v in enumerate(new_chunks) if i != 8])
if old_bytes in data:
print(f'{name} public key patched {old[:16].hex().upper()}...')
data = data.replace(old_bytes,new_bytes)
old_codes = [bytes.fromhex('713783E2'),bytes.fromhex('223A83E2'),bytes.fromhex('8D3F83E2')] #0x1C40000+0x22000+0x234
new_codes = [bytes.fromhex('973303E3'),bytes.fromhex('DD3883E3'),bytes.fromhex('033483E3')] #0x03DD3397 = 0x3397|0x00DD0000|0x03000000
data = replace_chunks(old_codes, new_codes, data,name)
return data
def patch_bzimage(data:bytes,key_dict:dict):
PE_TEXT_SECTION_OFFSET = 414
HEADER_PAYLOAD_OFFSET = 584
@@ -22,9 +83,7 @@ def patch_bzimage(data:bytes,key_dict:dict):
initramfs = initramfs[:cpio_offset2]
new_initramfs = initramfs
for old_public_key,new_public_key in key_dict.items():
if old_public_key in new_initramfs:
print(f'initramfs public key patched {old_public_key[:16].hex().upper()}...')
new_initramfs = new_initramfs.replace(old_public_key,new_public_key)
new_initramfs = replace_key(old_public_key,new_public_key,new_initramfs,'initramfs')
new_vmlinux = vmlinux.replace(initramfs,new_initramfs)
new_vmlinux_xz = lzma.compress(new_vmlinux,check=lzma.CHECK_CRC32,filters=[
{"id": lzma.FILTER_X86},
@@ -83,9 +142,7 @@ def patch_initrd_xz(initrd_xz:bytes,key_dict:dict,ljust=True):
initrd = lzma.decompress(initrd_xz)
new_initrd = initrd
for old_public_key,new_public_key in key_dict.items():
if old_public_key in new_initrd:
print(f'initrd public key patched {old_public_key[:16].hex().upper()}...')
new_initrd = new_initrd.replace(old_public_key,new_public_key)
new_initrd = replace_key(old_public_key,new_public_key,new_initrd,'initrd')
preset = 6
new_initrd_xz = lzma.compress(new_initrd,check=lzma.CHECK_CRC32,filters=[{"id": lzma.FILTER_LZMA2, "preset": preset }] )
while len(new_initrd_xz) > len(initrd_xz) and preset < 9:
@@ -251,17 +308,31 @@ def patch_kernel(data:bytes,key_dict):
else:
raise Exception('unknown kernel format')
def patch_loader(loader_file):
try:
from package import check_install_package
check_install_package(['pyelftools'])
from loader.patch_loader import patch_loader as do_patch_loader
arch = os.getenv('ARCH') or 'x86'
arch = arch.replace('-', '')
do_patch_loader(loader_file,loader_file,arch)
except ImportError as e:
print(e)
print("loader module import failed. cannot run patch_loader.py")
def patch_squashfs(path,key_dict):
for root, dirs, files in os.walk(path):
for file in files:
file = os.path.join(root,file)
for _file in files:
file = os.path.join(root,_file)
if os.path.isfile(file):
if _file =='loader':
patch_loader(file)
continue
data = open(file,'rb').read()
for old_public_key,new_public_key in key_dict.items():
if old_public_key in data:
print(f'{file} public key patched {old_public_key[:16].hex().upper()}...')
data = data.replace(old_public_key,new_public_key)
open(file,'wb').write(data)
_data = replace_key(old_public_key,new_public_key,data,file)
if _data != data:
open(file,'wb').write(_data)
url_dict = {
os.environ['MIKRO_LICENCE_URL'].encode():os.environ['CUSTOM_LICENCE_URL'].encode(),
os.environ['MIKRO_UPGRADE_URL'].encode():os.environ['CUSTOM_UPGRADE_URL'].encode(),