mirror of https://github.com/bol-van/zapret/
31 changed files with 5356 additions and 4789 deletions
@ -0,0 +1,11 @@ |
|||
Standalone version in `zapret-winws` folder !! |
|||
From this folder `winws` can be started only from `cygwin` shell. |
|||
|
|||
`cygwin` refuses to start winws if a copy of `cygwin1.dll` is present ! |
|||
|
|||
How to get Windows 7 and `winws` compatible version of `cygwin`: |
|||
|
|||
```powershell |
|||
curl -O https://www.cygwin.com/setup-x86_64.exe |
|||
setup-x86_64.exe --allow-unsupported-windows --no-verify --site http://ctm.crouchingtigerhiddenfruitbat.org/pub/cygwin/circa/64bit/2024/01/30/231215 |
|||
``` |
|||
@ -1,9 +0,0 @@ |
|||
Standalone version in zapret-winws folder !! |
|||
From this folder winws can be started only from cygwin shell. |
|||
|
|||
Cygwin refuses to start winws if a copy of cygwin1.dll is present ! |
|||
|
|||
How to get win7 and winws compatible version of cygwin : |
|||
|
|||
curl -O https://www.cygwin.com/setup-x86_64.exe |
|||
setup-x86_64.exe --allow-unsupported-windows --no-verify --site http://ctm.crouchingtigerhiddenfruitbat.org/pub/cygwin/circa/64bit/2024/01/30/231215 |
|||
@ -0,0 +1,315 @@ |
|||
# v1 |
|||
|
|||
Initial release |
|||
|
|||
# v2 |
|||
|
|||
* `nfqws`: command line options change. now using standard getopt. |
|||
* `nfqws`: added options for window size changing and `Host:` case change |
|||
* ISP support: tested on mns.ru and beeline (corbina) |
|||
* init scripts: rewritten init scripts for simple choice of ISP |
|||
* create_ipset: now using `ipset restore`, it works much faster |
|||
* `readme`: updated. now using UTF-8 charset. |
|||
|
|||
# v3 |
|||
|
|||
* ``tpws``: |
|||
* added transparent proxy (supports TPROXY and DNAT). |
|||
* can help when ISP tracks whole HTTP session, not only the beginning |
|||
* ipset: |
|||
* added `zapret-hosts-user.txt` which contain user defined host names to be resolved |
|||
* and added to zapret ip list |
|||
* ISP support: dom.ru support via TPROXY/DNAT |
|||
* ISP support: |
|||
* successfully tested sknt.ru on 'domru' configuration |
|||
* other configs will probably also work, but cannot test |
|||
* compile: OpenWrt compile how-to |
|||
|
|||
# v4 |
|||
|
|||
* `tpws`: added ability to insert extra space after HTTP method: `GET /` => `GET /` |
|||
* ISP support: TKT support |
|||
|
|||
# v5 |
|||
|
|||
* `nfqws`: IPv6 support in `nfqws` |
|||
|
|||
# v6 |
|||
|
|||
* `ipset`: added `get_antizapret.sh` |
|||
|
|||
# v7 |
|||
|
|||
* `tpws`: added ability to insert "." after `Host: name` |
|||
|
|||
# v8 |
|||
|
|||
* OpenWrt init: removed `hotplug.d/firewall` because of race conditions. now only use `/etc/firewall.user` |
|||
|
|||
# v9 |
|||
|
|||
* `ipban`: |
|||
* added ipban ipset. place domains banned by ip to `zapret-hosts-user-ipban.txt` |
|||
* these IPs must be soxified for both HTTP and HTTPS |
|||
* ISP support: tiera support |
|||
* ISP support: added DNS filtering to Ubuntu and Debian scripts |
|||
|
|||
# v10 |
|||
|
|||
* `tpws`: added `split-pos` option. split every message at specified position |
|||
|
|||
# v11 |
|||
|
|||
* `ipset`: scripts optimizations |
|||
|
|||
# v12 |
|||
|
|||
* `nfqws`: fix wrong TCP checksum calculation if packet length is odd and platform is big-endian |
|||
|
|||
# v13 |
|||
|
|||
* added binaries |
|||
|
|||
# v14 |
|||
|
|||
* change `get_antizapret` script to work with https://github.com/zapret-info/z-i/raw/master/dump.csv |
|||
* filter out 192.168.*, 127.*, 10.* from blocked ips |
|||
|
|||
# v15 |
|||
|
|||
* added `--hostspell` option to `nfqws` and `tpws` |
|||
* ISP support: beeline now catches "host" but other spellings still work |
|||
* OpenWrt/LEDE: changed init script to work with procd |
|||
* `tpws`, `nfqws`: minor cosmetic fixes |
|||
|
|||
# v16 |
|||
|
|||
* `tpws`: `split-http-req=method`: split inside method name, not after |
|||
* ISP support: mns.ru changed split pos to 3 (got redirect page with HEAD req: `curl -I ej.ru`) |
|||
|
|||
# v17 |
|||
|
|||
* ISP support: athome moved from `nfqws` to `tpws` because of instability and HTTP request hangs |
|||
* `tpws`: added options `unixeol`,`methodeol`,`hosttab` |
|||
|
|||
# v18 |
|||
|
|||
* `tpws`,`nfqws`: added `hostnospace` option |
|||
|
|||
# v19 |
|||
|
|||
* `tpws`: added `hostlist` option |
|||
|
|||
# v20 |
|||
|
|||
* added `ip2net`. `ip2net` groups ips from iplist into subnets and reduces ipset size twice |
|||
|
|||
# v21 |
|||
|
|||
* added `mdig`. `get_reestr.sh` is *real* again |
|||
|
|||
# v22 |
|||
|
|||
* total review of init script logic |
|||
* dropped support of older Debian 7 and Ubuntu 12/14 systems |
|||
* `install_bin.sh`: auto binaries preparation |
|||
* `docs`: `readme` review. some new topics added, others deleted |
|||
* `docs`: VPN setup with policy based routing using WireGuard |
|||
* `docs`: WireGuard modding guide |
|||
|
|||
# v23 |
|||
|
|||
* major init system rewrite |
|||
* OpenWrt: separate firewall include `/etc/firewall.zapret` |
|||
* `install_easy.sh`: easy setup on OpenWrt, Debian, Ubuntu, CentOS, Fedora, openSUSE |
|||
|
|||
# v24 |
|||
|
|||
* separate config from init scripts |
|||
* gzip support in `ipset/*.sh` and `tpws` |
|||
|
|||
# v25 |
|||
|
|||
* init: move to native systemd units |
|||
* use links to units, init scripts and firewall includes, no more copying |
|||
|
|||
# v26 |
|||
|
|||
* IPv6 support |
|||
* `tpws`: advanced bind options |
|||
|
|||
# v27 |
|||
|
|||
* `tpws`: major connection code rewrite. originally it was derived from not top quality example, with many bugs and potential problems. |
|||
* next generation connection code uses nonblocking sockets. now its in EXPERIMENTAL state. |
|||
|
|||
# v28 |
|||
|
|||
* `tpws`: added socks5 support |
|||
* `ipset`: major RKN getlist rewrite. added https://antifilter.network support |
|||
|
|||
# v29 |
|||
|
|||
* `nfqws`: DPI desync attack |
|||
* ip exclude system |
|||
|
|||
# v30 |
|||
|
|||
* `nfqws`: DPI desync attack modes: `fake`, `rst` |
|||
|
|||
# v31 |
|||
|
|||
* `nfqws`: DPI desync attack modes: `disorder`, `disorder2`, `split`, `split2`. |
|||
* `nfqws`: DPI desync fooling mode: `badseq`. multiple modes supported |
|||
|
|||
# v32 |
|||
|
|||
* `tpws`: multiple binds |
|||
* init scripts: run only one instance of `tpws` in any case |
|||
|
|||
# v33 |
|||
|
|||
* OpenWrt: flow offloading support |
|||
* `config`: `MODE` refactoring |
|||
|
|||
# v34 |
|||
|
|||
* `nfqws`: `dpi-desync` 2 mode combos |
|||
* `nfqws`: `dpi-desync` without parameter no more supported. previously it meant `fake` |
|||
* `nfqws`: custom fake HTTP request and TLS ClientHello |
|||
|
|||
# v35 |
|||
|
|||
* limited FreeBSD and OpenBSD support |
|||
|
|||
# v36 |
|||
|
|||
* full FreeBSD and OpenBSD support |
|||
|
|||
# v37 |
|||
|
|||
* limited macOS support |
|||
|
|||
# v38 |
|||
|
|||
* macOS easy install |
|||
|
|||
# v39 |
|||
|
|||
* `nfqws`: `conntrack`, `wssize` |
|||
|
|||
# v40 |
|||
|
|||
* init scripts: `IFACE_LAN`, `IFACE_WAN` now accept multiple interfaces |
|||
* init scripts: OpenWrt uses now `OPENWRT_LAN` parameter to override incoming interfaces for `tpws` |
|||
|
|||
# v41 |
|||
|
|||
* `install_easy`: openrc support |
|||
|
|||
# v42 |
|||
|
|||
* `blockcheck.sh` |
|||
|
|||
# v43 |
|||
|
|||
* `nfqws`: UDP desync with conntrack support (any-protocol only for now) |
|||
|
|||
# v44 |
|||
|
|||
* `nfqws`: `ipfrag` |
|||
|
|||
# v45 |
|||
|
|||
* `nfqws`: `hop-by-hop` - IPv6 desync and fooling |
|||
|
|||
# v46 |
|||
|
|||
* big startup script refactoring to support `nftables` and new OpenWrt snapshot builds with `firewall4` |
|||
|
|||
# v47 |
|||
|
|||
* `nfqws`: QUIC initial decryption |
|||
* `nfqws`: `udplen`, `fakeknown` dpi desync modes |
|||
|
|||
# v48 |
|||
|
|||
* `nfqws`, `tpws`: multiple `--hostlist` and `--hostlist-exclude` support |
|||
* launch system, `ipset`: no more list merging. all lists are passed separately to `nfqws` and `tpws` |
|||
* `nfqws`: `udplen` fooling supports packet shrinking (negative increment value) |
|||
|
|||
# v49 |
|||
|
|||
* QUIC support integrated to the main system and setup |
|||
|
|||
# v50 |
|||
|
|||
* DHT protocol support. |
|||
* DPI desync mode `tamper` for DHT. |
|||
* HEX string support in addition to binary files. |
|||
|
|||
# v51 |
|||
|
|||
* `tpws`: `--tlsrec` attack. |
|||
|
|||
# v52 |
|||
|
|||
* `autohostlist` mode |
|||
|
|||
# v53 |
|||
|
|||
* `nfqws`: TCP session reassemble for TLS ClientHello |
|||
|
|||
# v54 |
|||
|
|||
* `tpws`: out of band send when splitting (`--oob`) |
|||
* `nfqws`: `autottl` |
|||
* `nfqws`: `datanoack` fooling |
|||
* nftables: use POSTNAT path for TCP redirections to allow NAT-breaking strategies. use additional mark bit DESYNC_MARK_POSTNAT. |
|||
|
|||
# v55 |
|||
|
|||
* `tpws`: |
|||
* incompatible `oob` parameter change. it doesn't take oob byte anymore. instead it takes optional protocol filter - HTTP or TLS. |
|||
* the same is done with `disorder`. oob byte can be specified in parameter `--oob-data`. |
|||
* `blockcheck`: quick mode, strategy order optimizations, QUIC protocol support |
|||
* `nfqws`: `syndata` desync mode |
|||
|
|||
# v56 |
|||
|
|||
* `tpws`: `mss` fooling |
|||
* `tpws`: multi thread resolver. eliminates blocks related to hostname resolve. |
|||
|
|||
# v57 |
|||
|
|||
* `tpws`: `--nosplice` option |
|||
* `nfqws`: postnat fixes |
|||
* `nfqws`: `--dpi-desync-start` option |
|||
* `nfqws`: packet delay for kyber TLS and QUIC |
|||
* `nfqws`: `--dpi-desync-retrans` obsolete |
|||
* `nfqws`: `--qnum` is mandatory, no more default queue 0 |
|||
|
|||
# v58 |
|||
|
|||
* `winws` |
|||
|
|||
# v59 |
|||
|
|||
* `tpws`: `--split-tls` |
|||
* `tpws`: `--tlsrec=sniext` |
|||
* `nfqws`: `--dpi-desync-split-http-req`, `--dpi-desync-split-tls`. multi segment TLS support for split. |
|||
* `blockcheck`: `mdig` DNS cache |
|||
|
|||
# v60 |
|||
|
|||
* `blockcheck`: port block test, partial ip block test |
|||
* `nfqws`: `seqovl` `split`/`disorder` modes |
|||
|
|||
# v61 |
|||
|
|||
* C code cleanups |
|||
* `dvtws`: do not use raw sockets. use divert. |
|||
* `nfqws`,`tpws`: detect TLS 1.2 ClientHello from very old libraries with SSL 3.0 version in record layer |
|||
* `nfqws`,``tpws``: debug log to file and syslog |
|||
* ``tpws``: `--connect-bind-addr` option |
|||
* ``tpws``: log local endpoint (including source port number) for remote leg |
|||
@ -1,310 +0,0 @@ |
|||
v1 |
|||
|
|||
Initial release |
|||
|
|||
v2 |
|||
|
|||
nfqws : command line options change. now using standard getopt. |
|||
nfqws : added options for window size changing and "Host:" case change |
|||
ISP support : tested on mns.ru and beeline (corbina) |
|||
init scripts : rewritten init scripts for simple choise of ISP |
|||
create_ipset : now using 'ipset restore', it works much faster |
|||
readme : updated. now using UTF-8 charset. |
|||
|
|||
v3 |
|||
|
|||
tpws : added transparent proxy (supports TPROXY and DNAT). |
|||
can help when ISP tracks whole HTTP session, not only the beginning |
|||
ipset : added zapret-hosts-user.txt which contain user defined host names to be resolved |
|||
and added to zapret ip list |
|||
ISP support : dom.ru support via TPROXY/DNAT |
|||
ISP support : successfully tested sknt.ru on 'domru' configuration |
|||
other configs will probably also work, but cannot test |
|||
compile : openwrt compile howto |
|||
|
|||
v4 |
|||
|
|||
tpws : added ability to insert extra space after http method : "GET /" => "GET /" |
|||
ISP support : TKT support |
|||
|
|||
v5 |
|||
|
|||
nfqws : ipv6 support in nfqws |
|||
|
|||
v6 |
|||
|
|||
ipset : added "get_antizapret.sh" |
|||
|
|||
v7 |
|||
|
|||
tpws : added ability to insert "." after Host: name |
|||
|
|||
v8 |
|||
|
|||
openwrt init : removed hotplug.d/firewall because of race conditions. now only use /etc/firewall.user |
|||
|
|||
v9 |
|||
|
|||
ipban : added ipban ipset. place domains banned by ip to zapret-hosts-user-ipban.txt |
|||
these IPs must be soxified for both http and https |
|||
ISP support : tiera support |
|||
ISP support : added DNS filtering to ubuntu and debian scripts |
|||
|
|||
v10 |
|||
|
|||
tpws : added split-pos option. split every message at specified position |
|||
|
|||
v11 |
|||
|
|||
ipset : scripts optimizations |
|||
|
|||
v12 |
|||
|
|||
nfqws : fix wrong tcp checksum calculation if packet length is odd and platform is big-endian |
|||
|
|||
v13 |
|||
|
|||
added binaries |
|||
|
|||
v14 |
|||
|
|||
change get_antizapret script to work with https://github.com/zapret-info/z-i/raw/master/dump.csv |
|||
filter out 192.168.*, 127.*, 10.* from blocked ips |
|||
|
|||
v15 |
|||
|
|||
added --hostspell option to nfqws and tpws |
|||
ISP support : beeline now catches "host" but other spellings still work |
|||
openwrt/LEDE : changed init script to work with procd |
|||
tpws, nfqws : minor cosmetic fixes |
|||
|
|||
v16 |
|||
|
|||
tpws: split-http-req=method : split inside method name, not after |
|||
ISP support : mns.ru changed split pos to 3 (got redirect page with HEAD req : curl -I ej.ru) |
|||
|
|||
v17 |
|||
|
|||
ISP support : athome moved from nfqws to tpws because of instability and http request hangs |
|||
tpws : added options unixeol,methodeol,hosttab |
|||
|
|||
v18 |
|||
|
|||
tpws,nfqws : added hostnospace option |
|||
|
|||
v19 |
|||
|
|||
tpws : added hostlist option |
|||
|
|||
v20 |
|||
|
|||
added ip2net. ip2net groups ips from iplist into subnets and reduces ipset size twice |
|||
|
|||
v21 |
|||
|
|||
added mdig. get_reestr.sh is *real* again |
|||
|
|||
v22 |
|||
|
|||
total review of init script logic |
|||
dropped support of older debian 7 and ubuntu 12/14 systems |
|||
install_bin.sh : auto binaries preparation |
|||
docs: readme review. some new topics added, others deleted |
|||
docs: VPN setup with policy based routing using wireguard |
|||
docs: wireguard modding guide |
|||
|
|||
v23 |
|||
|
|||
major init system rewrite |
|||
openwrt : separate firewall include /etc/firewall.zapret |
|||
install_easy.sh : easy setup on openwrt, debian, ubuntu, centos, fedora, opensuse |
|||
|
|||
v24 |
|||
|
|||
separate config from init scripts |
|||
gzip support in ipset/*.sh and tpws |
|||
|
|||
v25 |
|||
|
|||
init : move to native systemd units |
|||
use links to units, init scripts and firewall includes, no more copying |
|||
|
|||
v26 |
|||
|
|||
ipv6 support |
|||
tpws : advanced bind options |
|||
|
|||
v27 |
|||
|
|||
tpws : major connection code rewrite. originally it was derived from not top quality example , with many bugs and potential problems. |
|||
next generation connection code uses nonblocking sockets. now its in EXPERIMENTAL state. |
|||
|
|||
v28 |
|||
|
|||
tpws : added socks5 support |
|||
ipset : major RKN getlist rewrite. added antifilter.network support |
|||
|
|||
v29 |
|||
|
|||
nfqws : DPI desync attack |
|||
ip exclude system |
|||
|
|||
v30 |
|||
|
|||
nfqws : DPI desync attack modes : fake,rst |
|||
|
|||
v31 |
|||
|
|||
nfqws : DPI desync attack modes : disorder,disorder2,split,split2. |
|||
nfqws : DPI desync fooling mode : badseq. multiple modes supported |
|||
|
|||
v32 |
|||
|
|||
tpws : multiple binds |
|||
init scripts : run only one instance of tpws in any case |
|||
|
|||
v33 |
|||
|
|||
openwrt : flow offloading support |
|||
config : MODE refactoring |
|||
|
|||
v34 |
|||
|
|||
nfqws : dpi-desync 2 mode combos |
|||
nfqws : dpi-desync without parameter no more supported. previously it meant "fake" |
|||
nfqws : custom fake http request and tls client hello |
|||
|
|||
v35 |
|||
|
|||
limited FreeBSD and OpenBSD support |
|||
|
|||
v36 |
|||
|
|||
full FreeBSD and OpenBSD support |
|||
|
|||
v37 |
|||
|
|||
limited MacOS support |
|||
|
|||
v38 |
|||
|
|||
MacOS easy install |
|||
|
|||
v39 |
|||
|
|||
nfqws: conntrack, wssize |
|||
|
|||
v40 |
|||
|
|||
init scripts : IFACE_LAN, IFACE_WAN now accept multiple interfaces |
|||
init scripts : openwrt uses now OPENWRT_LAN parameter to override incoming interfaces for tpws |
|||
|
|||
v41 |
|||
|
|||
install_easy : openrc support |
|||
|
|||
v42 |
|||
|
|||
blockcheck.sh |
|||
|
|||
v43 |
|||
|
|||
nfqws: UDP desync with conntrack support (any-protocol only for now) |
|||
|
|||
v44 |
|||
|
|||
nfqws: ipfrag |
|||
|
|||
v45 |
|||
|
|||
nfqws: hop-by-hop ipv6 desync and fooling |
|||
|
|||
v46 |
|||
|
|||
big startup script refactoring to support nftables and new openwrt snapshot builds with firewall4 |
|||
|
|||
v47 |
|||
|
|||
nfqws: QUIC initial decryption |
|||
nfqws: udplen, fakeknown dpi desync modes |
|||
|
|||
v48 |
|||
|
|||
nfqws, tpws : multiple --hostlist and --hostlist-exclude support |
|||
launch system, ipset : no more list merging. all lists are passed separately to nfqws and tpws |
|||
nfqws : udplen fooling supports packet shrinking (negative increment value) |
|||
|
|||
v49 |
|||
|
|||
QUIC support integrated to the main system and setup |
|||
|
|||
v50 |
|||
|
|||
DHT protocol support. |
|||
DPI desync mode 'tamper' for DHT. |
|||
HEX string support in addition to binary files. |
|||
|
|||
v51 |
|||
|
|||
tpws --tlsrec attack. |
|||
|
|||
v52 |
|||
|
|||
autohostlist mode |
|||
|
|||
v53 |
|||
|
|||
nfqws: tcp session reassemble for TLS ClientHello |
|||
|
|||
v54 |
|||
|
|||
tpws: out of band send when splitting (--oob) |
|||
nfqws: autottl |
|||
nfqws: datanoack fooling |
|||
nftables: use POSTNAT path for tcp redirections to allow NAT-breaking strategies. use additional mark bit DESYNC_MARK_POSTNAT. |
|||
|
|||
v55 |
|||
|
|||
tpws: incompatible oob parameter change. it doesn't take oob byte anymore. instead it takes optional protocol filter - http or tls. |
|||
the same is done with disorder. oob byte can be specified in parameter --oob-data. |
|||
blockcheck: quick mode, strategy order optimizations, QUIC protocol support |
|||
nfqws: syndata desync mode |
|||
|
|||
v56 |
|||
|
|||
tpws: mss fooling |
|||
tpws: multi thread resolver. eliminates blocks related to hostname resolve. |
|||
|
|||
v57 |
|||
|
|||
tpws: --nosplice option |
|||
nfqws: postnat fixes |
|||
nfqws: --dpi-desync-start option |
|||
nfqws: packet delay for kyber TLS and QUIC |
|||
nfqws: --dpi-desync-retrans obsolete |
|||
nfqws: --qnum is mandatory, no more default queue 0 |
|||
|
|||
v58 |
|||
|
|||
winws |
|||
|
|||
v59 |
|||
|
|||
tpws: --split-tls |
|||
tpws: --tlsrec=sniext |
|||
nfqws: --dpi-desync-split-http-req, --dpi-desync-split-tls. multi segment TLS support for split. |
|||
blockcheck: mdig dns cache |
|||
|
|||
v60 |
|||
|
|||
blockcheck: port block test, partial ip block test |
|||
nfqws: seqovl split/disorder modes |
|||
|
|||
v61 |
|||
|
|||
C code cleanups |
|||
dvtws: do not use raw sockets. use divert. |
|||
nfqws,tpws: detect TLS 1.2 ClientHello from very old libraries with SSL 3.0 version in record layer |
|||
nfqws,tpws: debug log to file and syslog |
|||
tpws: --connect-bind-addr option |
|||
tpws: log local endpoint (including source port number) for remote leg |
|||
@ -0,0 +1,70 @@ |
|||
How to compile native programs for use in OpenWrt |
|||
------------------------------------------------- |
|||
|
|||
1) Fetch correct version of OpenWrt |
|||
|
|||
```sh |
|||
cd ~ |
|||
``` |
|||
|
|||
* the latest: |
|||
|
|||
```sh |
|||
git clone git://git.openwrt.org/openwrt.git |
|||
``` |
|||
|
|||
* exact version for older devices, e.g., 15.05: |
|||
|
|||
```sh |
|||
git clone git://git.openwrt.org/15.05/openwrt.git |
|||
``` |
|||
|
|||
```sh |
|||
cd openwrt |
|||
``` |
|||
|
|||
2) Feed Initialization and Installation |
|||
|
|||
```sh |
|||
./scripts/feeds update -a |
|||
./scripts/feeds install -a |
|||
``` |
|||
|
|||
3) Add `zapret` packages to build root |
|||
|
|||
* Copy package descriptions: copy `compile/openwrt/*` to `~/openwrt` |
|||
* Copy source code of `tpws`: copy `tpws` folder to `~/openwrt/package/zapret/tpws` |
|||
* Copy source code of `nfq`: copy `nfq` folder to `~/openwrt/package/zapret/nfq` |
|||
* Copy source code of `ip2net`: copy `ip2net` folder to `~/openwrt/package/zapret/ip2net` |
|||
|
|||
4) Make a menuconfig |
|||
|
|||
```sh |
|||
make menuconfig |
|||
``` |
|||
|
|||
* Select your target architecture |
|||
* Select packages `Network/Zapret/*` as "M" |
|||
|
|||
5) Compile a toolchain |
|||
|
|||
```sh |
|||
make toolchain/compile |
|||
``` |
|||
|
|||
6) Compile packages |
|||
|
|||
```sh |
|||
make package/tpws/compile |
|||
make package/nfqws/compile |
|||
make package/ip2net/compile |
|||
make package/mdig/compile |
|||
``` |
|||
|
|||
7) Get resulting packages |
|||
|
|||
Take your `tpws*.ipk`, `nfqws*.ipk`, `ip2net*.ipk`, `mdig*.ipk` from there, e.g.: |
|||
|
|||
```sh |
|||
find bin -name tpws*.ipk |
|||
``` |
|||
@ -1,42 +0,0 @@ |
|||
How to compile native programs for use in openwrt |
|||
------------------------------------------------- |
|||
|
|||
1) <fetch correct version of openwrt> |
|||
|
|||
cd ~ |
|||
|
|||
<chaos calmer> |
|||
git clone git://git.openwrt.org/15.05/openwrt.git |
|||
<barrier breaker> |
|||
git clone git://git.openwrt.org/14.07/openwrt.git |
|||
<trunk> |
|||
git clone git://git.openwrt.org/openwrt.git |
|||
|
|||
cd openwrt |
|||
|
|||
2) ./scripts/feeds update -a |
|||
./scripts/feeds install -a |
|||
|
|||
3) #add zapret packages to build root |
|||
#copy package descriptions |
|||
copy compile/openwrt/* to ~/openwrt |
|||
#copy source code of tpws |
|||
copy tpws to ~/openwrt/package/zapret/tpws |
|||
#copy source code of nfq |
|||
copy nfq to ~/openwrt/package/zapret/nfq |
|||
#copy source code of ip2net |
|||
copy ip2net to ~/openwrt/package/zapret/ip2net |
|||
|
|||
4) make menuconfig |
|||
#select your target architecture |
|||
#select packages Network/Zapret/* as "M" |
|||
|
|||
5) make toolchain/compile |
|||
|
|||
6) make package/tpws/compile |
|||
make package/nfqws/compile |
|||
make package/ip2net/compile |
|||
make package/mdig/compile |
|||
|
|||
7) find bin -name tpws*.ipk |
|||
#take your tpws*.ipk , nfqws*.ipk , ip2net*.ipk, mdig*.ipk from there |
|||
@ -0,0 +1,420 @@ |
|||
- [Пример ручной установки на Debian-подобную систему](#пример-ручной-установки-на-debian-подобную-систему) |
|||
- [CentOS 7+, Fedora](#centos-7-fedora) |
|||
- [openSUSE](#opensuse) |
|||
- [Arch Linux](#arch-linux) |
|||
- [Gentoo](#gentoo) |
|||
- [Ручная установка на OpenWrt/LEDE 15.xx-21.xx](#ручная-установка-на-openwrtlede-15xx-21xx) |
|||
|
|||
Пример ручной установки на Debian-подобную систему |
|||
-------------------------------------------------- |
|||
|
|||
На Debian основано большое количество дистрибутивов Linux, включая Ubuntu. |
|||
Здесь рассматриваются прежде всего Debian 8+ и Ubuntu 16+. |
|||
Но с большой вероятностью может сработать и на производных от них. |
|||
Главное условие - наличие `systemd`, `apt` и нескольких стандартных пакетов в репозитории. |
|||
|
|||
Установить пакеты: |
|||
|
|||
```sh |
|||
apt-get update |
|||
apt-get install ipset curl dnsutils git |
|||
``` |
|||
|
|||
Если хотите использовать `nftables`, то нужен пакет `nftables`, а `ipset` не обязателен. |
|||
|
|||
Скопировать директорию `zapret` в `/opt` или скачать через `git`: |
|||
|
|||
```sh |
|||
cd /opt |
|||
git clone --depth 1 https://github.com/bol-van/zapret |
|||
``` |
|||
|
|||
Запустить автоинсталлятор бинарников. Он сам определит рабочую архитектуру и настроит все бинарники. |
|||
|
|||
```sh |
|||
/opt/zapret/install_bin.sh |
|||
``` |
|||
|
|||
**АЛЬТЕРНАТИВА:** `make -C /opt/zapret`. Получите динамические бинарники под вашу ось. |
|||
Для сборки требуются dev пакеты: `zlib1g-dev`, `libcap-dev`, `libnetfilter-queue-dev`. |
|||
|
|||
Создать конфиг по умолчанию: |
|||
|
|||
```sh |
|||
cp /opt/zapret/config.default /opt/zapret/config |
|||
``` |
|||
|
|||
Настроить параметры согласно разделу "Выбор параметров". |
|||
|
|||
Создать user листы по умолчанию: |
|||
|
|||
```sh |
|||
cp /opt/zapret/ipset/zapret-hosts-user-exclude.txt.default /opt/zapret/ipset/zapret-hosts-user-exclude.txt |
|||
echo nonexistent.domain > /opt/zapret/ipset/zapret-hosts-user.txt |
|||
touch /opt/zapret/ipset/zapret-hosts-user-ipban.txt |
|||
``` |
|||
|
|||
Создать ссылку на service unit в `systemd`: |
|||
|
|||
```sh |
|||
ln -fs /opt/zapret/init.d/systemd/zapret.service /lib/systemd/system |
|||
``` |
|||
|
|||
Удалить старые листы, если они были созданы ранее: |
|||
|
|||
```sh |
|||
/opt/zapret/ipset/clear_lists.sh |
|||
``` |
|||
|
|||
По желанию прописать в `/opt/zapret/ipset/zapret-hosts-user.txt` свои домены. |
|||
|
|||
Выполнить скрипт обновления листа: |
|||
|
|||
```sh |
|||
/opt/zapret/ipset/get_config.sh |
|||
``` |
|||
|
|||
Настроить таймер `systemd` для обновления листа: |
|||
|
|||
```sh |
|||
ln -fs /opt/zapret/init.d/systemd/zapret-list-update.service /lib/systemd/system |
|||
ln -fs /opt/zapret/init.d/systemd/zapret-list-update.timer /lib/systemd/system |
|||
``` |
|||
|
|||
Принять изменения в `systemd`: `systemctl daemon-reload` |
|||
|
|||
Включить автозапуск службы: `systemctl enable zapret` |
|||
|
|||
Включить таймер обновления листа: `systemctl enable zapret-list-update.timer` |
|||
|
|||
Запустить службу: `systemctl start zapret` |
|||
|
|||
Шпаргалка по управлению службой и таймером : |
|||
|
|||
- enable auto start: `systemctl enable zapret` |
|||
- disable auto start: `systemctl disable zapret` |
|||
- start: `systemctl start zapret` |
|||
- stop: `systemctl stop zapret` |
|||
- status, output messages: `systemctl status zapret` |
|||
- timer info: `systemctl list-timer` |
|||
- delete service: `systemctl disable zapret; rm /lib/systemd/system/zapret.service` |
|||
- delete timer: `systemctl disable zapret-list-update.timer; rm /lib/systemd/system/zapret-list-update.*` |
|||
|
|||
CentOS 7+, Fedora |
|||
----------------- |
|||
|
|||
CentOS с 7 версии и более-менее новые федоры построены на `systemd`. |
|||
В качестве пакетного менеджера используется `yum`. |
|||
|
|||
Установить пакеты: |
|||
|
|||
```sh |
|||
yum install -y curl ipset dnsutils git |
|||
``` |
|||
|
|||
Далее все аналогично Debian. |
|||
|
|||
openSUSE |
|||
-------- |
|||
|
|||
Новые openSUSE основаны на `systemd` и менеджере пакетов `zypper`. |
|||
|
|||
Установить пакеты: |
|||
|
|||
```sh |
|||
zypper --non-interactive install curl ipset |
|||
``` |
|||
|
|||
Далее все аналогично Debian, кроме расположения `systemd`. |
|||
В openSUSE он находится не в `/lib/systemd`, а в `/usr/lib/systemd`. |
|||
Правильные команды будут: |
|||
|
|||
```sh |
|||
ln -fs /opt/zapret/init.d/systemd/zapret.service /usr/lib/systemd/system |
|||
ln -fs /opt/zapret/init.d/systemd/zapret-list-update.service /usr/lib/systemd/system |
|||
ln -fs /opt/zapret/init.d/systemd/zapret-list-update.timer /usr/lib/systemd/system |
|||
``` |
|||
|
|||
Arch Linux |
|||
---------- |
|||
|
|||
Построен на базе `systemd`. |
|||
|
|||
Установить пакеты: |
|||
|
|||
```sh |
|||
pacman -Syy |
|||
pacman --noconfirm -S ipset curl |
|||
``` |
|||
|
|||
Далее все аналогично Debian. |
|||
|
|||
Gentoo |
|||
------ |
|||
|
|||
Эта система использует OpenRC - улучшенную версию sysvinit. |
|||
Установка пакетов производится командой: `emerge <package_name>` |
|||
Пакеты собираются из исходников. |
|||
|
|||
Требуются все те же `ipset`, `curl`, `git` для скачивания с GitHub. |
|||
`git` и `curl` по умолчанию могут присутствовать, `ipset` отсутствует. |
|||
|
|||
```sh |
|||
emerge ipset |
|||
``` |
|||
|
|||
Настроить параметры согласно разделу "Выбор параметров". |
|||
|
|||
Запустить автоинсталлятор бинарников. Он сам определит рабочую архитектуру и настроит все бинарники: |
|||
|
|||
```sh |
|||
/opt/zapret/install_bin.sh |
|||
``` |
|||
|
|||
**АЛЬТЕРНАТИВА:** `make -C /opt/zapret`. Получите динамические бинарники под вашу ось. |
|||
|
|||
Удалить старые листы, если они были созданы ранее: |
|||
|
|||
```sh |
|||
/opt/zapret/ipset/clear_lists.sh |
|||
``` |
|||
|
|||
По желанию прописать в `/opt/zapret/ipset/zapret-hosts-user.txt` свои домены. |
|||
|
|||
Выполнить скрипт обновления листа: |
|||
|
|||
```sh |
|||
/opt/zapret/ipset/get_config.sh |
|||
``` |
|||
|
|||
Зашедулить обновление листа: |
|||
|
|||
```sh |
|||
crontab -e |
|||
``` |
|||
|
|||
Создать для крона строчку `0 12 */2* * /opt/zapret/ipset/get_config.sh` |
|||
|
|||
Подключить init скрипт: |
|||
|
|||
```sh |
|||
ln -fs /opt/zapret/init.d/openrc/zapret /etc/init.d |
|||
rc-update add zapret |
|||
``` |
|||
|
|||
Запустить службу: |
|||
|
|||
```sh |
|||
rc-service zapret start |
|||
``` |
|||
|
|||
Шпаргалка по управлению службой: |
|||
|
|||
- enable auto start: `rc-update add zapret` |
|||
- disable auto start: `rc-update del zapret` |
|||
- start: `rc-service zapret start` |
|||
- stop: `rc-service zapret stop` |
|||
|
|||
Ручная установка на OpenWrt/LEDE 15.xx-21.xx |
|||
-------------------------------------------- |
|||
|
|||
**ВАЖНО:** Данная инструкция написана для систем, основанных на `iptables`+`firewall3`. |
|||
В новых версиях OpenWrt переходит на `nftables`+`firewall4`, инструкция неприменима. Пользуйтесь `install_easy.sh` |
|||
|
|||
Установить дополнительные пакеты: |
|||
|
|||
```sh |
|||
opkg update |
|||
opkg install iptables-mod-extra iptables-mod-nfqueue iptables-mod-filter iptables-mod-ipopt iptables-mod-conntrack-extra ipset curl |
|||
# (IPv6) opkg install ip6tables-mod-nat |
|||
# (опционально) opkg install gzip |
|||
# (опционально) opkg install coreutils-sort |
|||
``` |
|||
|
|||
**ЭКОНОМИЯ МЕСТА:** |
|||
|
|||
`gzip` от `busybox` в разы медленней полноценного варианта. `gzip` используется скриптами получения листов. |
|||
`sort` от `busybox` медленней полноценного варианта и жрет намного больше памяти. `sort` используется скриптами получения листов. |
|||
`iptables-mod-nfqueue` можно выкинуть, если не будем пользоваться `nfqws`. |
|||
`curl` можно выкинуть, если для получения IP листа будет использоваться только `get_user.sh` |
|||
|
|||
Самая главная трудность - скомпилировать программы на C. Это можно сделать на Linux x64 при помощи SDK, который можно скачать с официального сайта OpenWrt или LEDE. Но процесс кросс-компиляции - это всегда сложности. |
|||
Недостаточно запустить `make` как на традиционной Linux системе. |
|||
Поэтому в `binaries/` имеются готовые статические бинарники для всех самых распространенных архитектур. |
|||
Статическая сборка означает, что бинарник не зависит от типа `libc` (`glibc`, `uclibc` или `musl`) и наличия установленных `*.so`. |
|||
Его можно использовать сразу. Лишь бы подходил тип CPU. У ARM и MIPS есть несколько версий. |
|||
Скорее всего найдется рабочий вариант. Если нет - вам придется собирать самостоятельно. |
|||
Для всех поддерживаемых архитектур бинарники запакованы `upx`. На текущий момент все, кроме `mips64`. |
|||
|
|||
Скопировать директорию `zapret` в `/opt` на роутер. |
|||
|
|||
Если места достаточно, самый простой способ: |
|||
|
|||
```sh |
|||
opkg update |
|||
opkg install git-http |
|||
mkdir /opt |
|||
cd /opt |
|||
git clone --depth 1 https://github.com/bol-van/zapret |
|||
``` |
|||
|
|||
Если места немного: |
|||
|
|||
```sh |
|||
opkg update |
|||
opkg install openssh-sftp-server unzip |
|||
ifconfig br-lan |
|||
``` |
|||
|
|||
Скачать на комп с GitHub zip архив кнопкой "Clone or download" -> Download ZIP |
|||
Скопировать средствами `sftp` zip архив на роутер в `/tmp`. |
|||
|
|||
```sh |
|||
mkdir /opt |
|||
cd /opt |
|||
unzip /tmp/zapret-master.zip |
|||
mv zapret-master zapret |
|||
rm /tmp/zapret-master.zip |
|||
``` |
|||
|
|||
Если места совсем мало: |
|||
На Linux системе скачать и распаковать zapret. Оставить необходимый минимум файлов. |
|||
Запаковать в архив `zapret.tar.gz`. |
|||
|
|||
```sh |
|||
nc -l -p 1111 < zapret.tar.gz |
|||
``` |
|||
|
|||
На роутере: |
|||
|
|||
```sh |
|||
cd /tmp |
|||
nc <linux_system_ip> 1111 >zapret.tar.gz |
|||
``` |
|||
|
|||
Не стоит работать с распакованной версией `zapret` на Windows. Потеряются ссылки и `chmod`. |
|||
|
|||
Запустить автоинсталлятор бинарников. Он сам определит рабочую архитектуру и настроит все бинарники: |
|||
|
|||
```sh |
|||
/opt/zapret/install_bin.sh |
|||
``` |
|||
|
|||
Создать ссылку на скрипт запуска: |
|||
|
|||
```sh |
|||
ln -fs /opt/zapret/init.d/openwrt/zapret /etc/init.d |
|||
``` |
|||
|
|||
Создать ссылку на скрипт события поднятия интерфейса: |
|||
|
|||
```sh |
|||
ln -fs /opt/zapret/init.d/openwrt/90-zapret /etc/hotplug.d/iface |
|||
``` |
|||
|
|||
Создать конфиг по умолчанию: |
|||
|
|||
```sh |
|||
cp /opt/zapret/config.default /opt/zapret/config |
|||
``` |
|||
|
|||
Настроить параметры согласно разделу "Выбор параметров". |
|||
|
|||
Создать user листы по умолчанию: |
|||
|
|||
```sh |
|||
cp /opt/zapret/ipset/zapret-hosts-user-exclude.txt.default /opt/zapret/ipset/zapret-hosts-user-exclude.txt |
|||
echo nonexistent.domain > /opt/zapret/ipset/zapret-hosts-user.txt |
|||
touch /opt/zapret/ipset/zapret-hosts-user-ipban.txt |
|||
``` |
|||
|
|||
Удалить старые листы, если они были созданы ранее: |
|||
|
|||
```sh |
|||
/opt/zapret/ipset/clear_lists.sh |
|||
``` |
|||
|
|||
По желанию прописать в `/opt/zapret/ipset/zapret-hosts-user.txt` свои домены. |
|||
Выполнить скрипт обновления листа: |
|||
|
|||
```sh |
|||
/opt/zapret/ipset/get_config.sh |
|||
``` |
|||
|
|||
Зашедулить обновление листа: |
|||
|
|||
```sh |
|||
crontab -e |
|||
``` |
|||
|
|||
Создать для крона строчку `0 12 */2* * /opt/zapret/ipset/get_config.sh` |
|||
|
|||
Включить автозапуск службы и запустить ее: |
|||
|
|||
```sh |
|||
/etc/init.d/zapret enable |
|||
/etc/init.d/zapret start |
|||
``` |
|||
|
|||
**ПРИМЕЧАНИЕ:** на этапе старта системы интерфейсы еще не подняты. |
|||
В некоторых случаях невозможно правильно сформировать параметры запуска демонов, не зная имя физического интерфейса LAN. |
|||
Скрипт из /etc/hotplug.d/iface перезапустит демоны по событию поднятия LAN. |
|||
|
|||
Создать ссылку на firewall include: |
|||
|
|||
```sh |
|||
ln -fs /opt/zapret/init.d/openwrt/firewall.zapret /etc/firewall.zapret |
|||
``` |
|||
|
|||
Проверить была ли создана ранее запись о firewall include: |
|||
|
|||
```sh |
|||
uci show firewall | grep firewall.zapret |
|||
``` |
|||
|
|||
Если `firewall.zapret` нет, значит добавить: |
|||
|
|||
```sh |
|||
uci add firewall include |
|||
uci set firewall.@include[-1].path="/etc/firewall.zapret" |
|||
uci set firewall.@include[-1].reload="1" |
|||
uci commit firewall |
|||
``` |
|||
|
|||
Проверить, не включен ли flow offload: |
|||
|
|||
```sh |
|||
uci show firewall.@defaults[0] |
|||
``` |
|||
|
|||
Если `flow_offloading=1` или `flow_offloading_hw=1`: |
|||
|
|||
```sh |
|||
uci set firewall.@defaults[0].flow_offloading=0 |
|||
uci set firewall.@defaults[0].flow_offloading_hw=0 |
|||
uci commit firewall |
|||
``` |
|||
|
|||
Перезапустить фаервол: |
|||
|
|||
```sh |
|||
fw3 restart |
|||
``` |
|||
|
|||
Посмотреть через `iptables -nL`, `ip6tables -nL` или через `luci` вкладку "firewall", появились ли нужные правила. |
|||
|
|||
**ЭКОНОМИЯ МЕСТА:** если его мало, то можно оставить в директории `zapret` лишь подкаталоги `ipset/`, `common/`, файл `config/`, `init.d/openwrt/`. |
|||
Далее нужно создать подкаталоги с реально используемыми бинарниками (`ip2net`, `mdig`, `tpws`, `nfq`) и скопировать туда из `binaries/` рабочие executables. |
|||
|
|||
**ЕСЛИ ВСЕ ПЛОХО С МЕСТОМ:** откажитесь от работы со списком РКН. используйте только `get_user.sh`. |
|||
|
|||
**ЕСЛИ СОВСЕМ ВСЕ УЖАСНО С МЕСТОМ:** берете `tpws` и делаете все своими руками. поднятие `iptables`, автостарт бинарника. |
|||
С некоторых версий скрипты запуска zapret без `ipset` не работают (он требуется для IP exclude). |
|||
|
|||
**СОВЕТ:** Покупайте только роутеры с USB. |
|||
В USB можно воткнуть флэшку и вынести на нее корневую файловую систему или использовать ее в качестве оверлея. |
|||
Не надо мучить себя, запихивая незапихиваемое в 8 мб встроенной флэшки. |
|||
Для комфортной работы с zapret нужен роутер с 16 Mb встроенной памяти или USB разъемом и 128+ Mb RAM. |
|||
На 64 Mb без swap будут проблемы с листами РКН. Если у вас только 64 Mb, и вы хотите листы РКН, подключите swap. |
|||
32 Mb для современных версий OpenWrt - конфигурация на грани живучести. Возможны хаотические падения процессов в oom. |
|||
Работа с листами РКН невозможна в принципе. |
|||
@ -1,282 +0,0 @@ |
|||
Пример ручной установки на debian-подобную систему |
|||
-------------------------------------------------- |
|||
|
|||
На debian основано большое количество дистрибутивов linux, включая ubuntu. |
|||
Здесь рассматриваются прежде всего Debian 8+ и Ubuntu 16+. |
|||
Но с большой вероятностью может сработать и на производных от них. |
|||
Главное условие - наличие systemd, apt и нескольких стандартных пакетов в репозитории. |
|||
|
|||
Установить пакеты : |
|||
apt-get update |
|||
apt-get install ipset curl dnsutils git |
|||
|
|||
Если хотите использовать nftables, то нужен пакет nftables, а ipset не обязателен. |
|||
|
|||
Скопировать директорию zapret в /opt или скачать через git : |
|||
cd /opt |
|||
git clone --depth 1 https://github.com/bol-van/zapret |
|||
|
|||
Запустить автоинсталятор бинариков. Он сам определит рабочую архитектуру и настроит все бинарики. |
|||
/opt/zapret/install_bin.sh |
|||
АЛЬТЕРНАТИВА : make -C /opt/zapret. Получите динамические бинарики под вашу ось. |
|||
Для сборки требуются dev пакеты : zlib1g-dev libcap-dev libnetfilter-queue-dev |
|||
|
|||
Создать конфиг по умолчанию : |
|||
cp /opt/zapret/config.default /opt/zapret/config |
|||
|
|||
Настроить параметры согласно разделу "Выбор параметров". |
|||
|
|||
Создать user листы по умолчанию : |
|||
cp /opt/zapret/ipset/zapret-hosts-user-exclude.txt.default /opt/zapret/ipset/zapret-hosts-user-exclude.txt |
|||
echo nonexistent.domain >/opt/zapret/ipset/zapret-hosts-user.txt |
|||
touch /opt/zapret/ipset/zapret-hosts-user-ipban.txt |
|||
|
|||
Создать ссылку на service unit в systemd : |
|||
ln -fs /opt/zapret/init.d/systemd/zapret.service /lib/systemd/system |
|||
|
|||
Удалить старые листы, если они были созданы ранее : |
|||
/opt/zapret/ipset/clear_lists.sh |
|||
По желанию прописать в /opt/zapret/ipset/zapret-hosts-user.txt свои домены. |
|||
Выполнить скрипт обновления листа : |
|||
/opt/zapret/ipset/get_config.sh |
|||
Настроить таймер systemd для обновления листа : |
|||
ln -fs /opt/zapret/init.d/systemd/zapret-list-update.service /lib/systemd/system |
|||
ln -fs /opt/zapret/init.d/systemd/zapret-list-update.timer /lib/systemd/system |
|||
|
|||
Принять изменения в systemd : |
|||
systemctl daemon-reload |
|||
|
|||
Включить автозапуск службы : |
|||
systemctl enable zapret |
|||
|
|||
Включить таймер обновления листа : |
|||
systemctl enable zapret-list-update.timer |
|||
|
|||
Запустить службу : |
|||
systemctl start zapret |
|||
|
|||
Шпаргалка по управлению службой и таймером : |
|||
|
|||
enable auto start : systemctl enable zapret |
|||
disable auto start : systemctl disable zapret |
|||
start : systemctl start zapret |
|||
stop : systemctl stop zapret |
|||
status, output messages : systemctl status zapret |
|||
timer info : systemctl list-timer |
|||
delete service : systemctl disable zapret ; rm /lib/systemd/system/zapret.service |
|||
delete timer : systemctl disable zapret-list-update.timer ; rm /lib/systemd/system/zapret-list-update.* |
|||
|
|||
Centos 7+, Fedora |
|||
----------------- |
|||
|
|||
Centos с 7 версии и более-менее новые федоры построены на systemd. |
|||
В качестве пакетного менеджера используется yum. |
|||
|
|||
Установить пакеты : |
|||
yum install -y curl ipset dnsutils git |
|||
|
|||
Далее все аналогично debian. |
|||
|
|||
OpenSUSE |
|||
-------- |
|||
|
|||
Новые OpenSUSE основаны на systemd и менеджере пакетов zypper. |
|||
|
|||
Установить пакеты : |
|||
zypper --non-interactive install curl ipset |
|||
|
|||
Далее все аналогично debian, кроме расположения systemd. |
|||
В opensuse он находится не в /lib/systemd, а в /usr/lib/systemd. |
|||
Правильные команды будут : |
|||
|
|||
ln -fs /opt/zapret/init.d/systemd/zapret.service /usr/lib/systemd/system |
|||
ln -fs /opt/zapret/init.d/systemd/zapret-list-update.service /usr/lib/systemd/system |
|||
ln -fs /opt/zapret/init.d/systemd/zapret-list-update.timer /usr/lib/systemd/system |
|||
|
|||
Arch linux |
|||
---------- |
|||
|
|||
Построен на базе systemd. |
|||
|
|||
Установить пакеты : |
|||
pacman -Syy |
|||
pacman --noconfirm -S ipset curl |
|||
|
|||
Далее все аналогично debian. |
|||
|
|||
Gentoo |
|||
------ |
|||
|
|||
Эта система использует OpenRC - улучшенную версию sysvinit. |
|||
Установка пакетов производится командой : emerge <package_name> |
|||
Пакеты собираются из исходников. |
|||
|
|||
Требуются все те же ipset, curl, git для скачивания с github. |
|||
git и curl по умолчанию могут присутствовать, ipset отсутствует. |
|||
|
|||
emerge ipset |
|||
|
|||
Настроить параметры согласно разделу "Выбор параметров". |
|||
|
|||
Запустить автоинсталятор бинариков. Он сам определит рабочую архитектуру и настроит все бинарики. |
|||
/opt/zapret/install_bin.sh |
|||
АЛЬТЕРНАТИВА : make -C /opt/zapret. Получите динамические бинарики под вашу ось. |
|||
|
|||
Удалить старые листы, если они были созданы ранее : |
|||
/opt/zapret/ipset/clear_lists.sh |
|||
По желанию прописать в /opt/zapret/ipset/zapret-hosts-user.txt свои домены. |
|||
Выполнить скрипт обновления листа : |
|||
/opt/zapret/ipset/get_config.sh |
|||
Зашедулить обновление листа : |
|||
crontab -e |
|||
Создать строчку "0 12 */2 * * /opt/zapret/ipset/get_config.sh" |
|||
|
|||
Подключить init скрипт : |
|||
|
|||
ln -fs /opt/zapret/init.d/openrc/zapret /etc/init.d |
|||
rc-update add zapret |
|||
|
|||
Запустить службу : |
|||
|
|||
rc-service zapret start |
|||
|
|||
Шпаргалка по управлению службой : |
|||
|
|||
enable auto start : rc-update add zapret |
|||
disable auto start : rc-update del zapret |
|||
start : rc-service zapret start |
|||
stop : rc-service zapret stop |
|||
|
|||
|
|||
|
|||
Ручная установка на openwrt/LEDE 15.xx-21.xx |
|||
-------------------------------------------- |
|||
|
|||
!!! Данная инструкция написана для систем, основанных на iptables+firewall3 |
|||
!!! В новых версиях openwrt переходит на nftables+firewall4, инструкция неприменима. Пользуйтесь install_easy.sh |
|||
|
|||
Установить дополнительные пакеты : |
|||
opkg update |
|||
opkg install iptables-mod-extra iptables-mod-nfqueue iptables-mod-filter iptables-mod-ipopt iptables-mod-conntrack-extra ipset curl |
|||
(ipv6) opkg install ip6tables-mod-nat |
|||
(опционально) opkg install gzip |
|||
(опционально) opkg install coreutils-sort |
|||
|
|||
ЭКОНОМИЯ МЕСТА : |
|||
|
|||
gzip от busybox в разы медленней полноценного варианта. gzip используется скриптами получения листов. |
|||
sort от busybox медленней полноценного варианта и жрет намного больше памяти. sort используется скриптами получения листов. |
|||
iptables-mod-nfqueue можно выкинуть, если не будем пользоваться nfqws |
|||
curl можно выкинуть, если для получения ip листа будет использоваться только get_user.sh |
|||
|
|||
Самая главная трудность - скомпилировать программы на C. Это можно сделать на linux x64 при помощи SDK, который |
|||
можно скачать с официального сайта openwrt или LEDE. Но процесс кросс компиляции - это всегда сложности. |
|||
Недостаточно запустить make как на традиционной linux системе. |
|||
Поэтому в binaries имеются готовые статические бинарики для всех самых распространенных архитектур. |
|||
Статическая сборка означает, что бинарик не зависит от типа libc (glibc, uclibc или musl) и наличия установленных so. |
|||
Его можно использовать сразу. Лишь бы подходил тип CPU. У ARM и MIPS есть несколько версий. |
|||
Скорее всего найдется рабочий вариант. Если нет - вам придется собирать самостоятельно. |
|||
Для всех поддерживаемых архитектур бинарики запакованы upx. На текущий момент все, кроме mips64. |
|||
|
|||
Скопировать директорию "zapret" в /opt на роутер. |
|||
|
|||
Если места достаточно, самый простой способ : |
|||
opkg update |
|||
opkg install git-http |
|||
mkdir /opt |
|||
cd /opt |
|||
git clone --depth 1 https://github.com/bol-van/zapret |
|||
|
|||
Если места немного : |
|||
opkg update |
|||
opkg install openssh-sftp-server unzip |
|||
ifconfig br-lan |
|||
Скачать на комп с github zip архив кнопкой "Clone or download"->Download ZIP |
|||
Скопировать средствами sftp zip архив на роутер в /tmp. |
|||
mkdir /opt |
|||
cd /opt |
|||
unzip /tmp/zapret-master.zip |
|||
mv zapret-master zapret |
|||
rm /tmp/zapret-master.zip |
|||
|
|||
Если места совсем мало : |
|||
На linux системе скачать и распаковать zapret. Оставить необходимый минимум файлов. |
|||
Запаковать в архив zapret.tar.gz. |
|||
nc -l -p 1111 <zapret.tar.gz |
|||
На роутере |
|||
cd /tmp |
|||
nc <linux_system_ip> 1111 >zapret.tar.gz |
|||
|
|||
Не стоит работать с распакованной версией zapret на windows. Потеряются ссылки и chmod. |
|||
|
|||
Запустить автоинсталятор бинариков. Он сам определит рабочую архитектуру и настроит все бинарики. |
|||
/opt/zapret/install_bin.sh |
|||
|
|||
Создать ссылку на скрипт запуска : |
|||
ln -fs /opt/zapret/init.d/openwrt/zapret /etc/init.d |
|||
Создать ссылку на скрипт события поднятия интерфейса : |
|||
ln -fs /opt/zapret/init.d/openwrt/90-zapret /etc/hotplug.d/iface |
|||
|
|||
Создать конфиг по умолчанию : |
|||
cp /opt/zapret/config.default /opt/zapret/config |
|||
|
|||
Настроить параметры согласно разделу "Выбор параметров". |
|||
|
|||
Создать user листы по умолчанию : |
|||
cp /opt/zapret/ipset/zapret-hosts-user-exclude.txt.default /opt/zapret/ipset/zapret-hosts-user-exclude.txt |
|||
echo nonexistent.domain >/opt/zapret/ipset/zapret-hosts-user.txt |
|||
touch /opt/zapret/ipset/zapret-hosts-user-ipban.txt |
|||
|
|||
Удалить старые листы, если они были созданы ранее : |
|||
/opt/zapret/ipset/clear_lists.sh |
|||
По желанию прописать в /opt/zapret/ipset/zapret-hosts-user.txt свои домены. |
|||
Выполнить скрипт обновления листа : |
|||
/opt/zapret/ipset/get_config.sh |
|||
Зашедулить обновление листа : |
|||
crontab -e |
|||
Создать строчку "0 12 */2 * * /opt/zapret/ipset/get_config.sh" |
|||
|
|||
Включить автозапуск службы и запустить ее : |
|||
/etc/init.d/zapret enable |
|||
/etc/init.d/zapret start |
|||
ПРИМЕЧАНИЕ : на этапе старта системы интерфейсы еще не подняты. в некоторых случаях невозможно правильно |
|||
сформировать параметры запуска демонов, не зная имя физического интерфейса LAN. |
|||
Cкрипт из /etc/hotplug.d/iface перезапустит демоны по событию поднятия LAN. |
|||
|
|||
Создать ссылку на firewall include : |
|||
ln -fs /opt/zapret/init.d/openwrt/firewall.zapret /etc/firewall.zapret |
|||
Проверить была ли создана ранее запись о firewall include : |
|||
uci show firewall | grep firewall.zapret |
|||
Если firewall.zapret нет, значит добавить : |
|||
uci add firewall include |
|||
uci set firewall.@include[-1].path="/etc/firewall.zapret" |
|||
uci set firewall.@include[-1].reload="1" |
|||
uci commit firewall |
|||
Проверить не включен ли flow offload : |
|||
uci show firewall.@defaults[0] |
|||
Если flow_offloading=1 или flow_offloading_hw=1 , |
|||
uci set firewall.@defaults[0].flow_offloading=0 |
|||
uci set firewall.@defaults[0].flow_offloading_hw=0 |
|||
uci commit firewall |
|||
Перезапустить фаервол : |
|||
fw3 restart |
|||
|
|||
Посмотреть через iptables -nL, ip6tables -nL или через luci вкладку "firewall" появились ли нужные правила. |
|||
|
|||
ЭКОНОМИЯ МЕСТА : если его мало, то можно оставить в директории zapret лишь подкаталоги |
|||
ipset, common, файл config, init.d/openwrt. |
|||
Далее нужно создать подкаталоги с реально используемыми бинариками (ip2net, mdig, tpws, nfq) |
|||
и скопировать туда из binaries рабочие executables. |
|||
|
|||
ЕСЛИ ВСЕ ПЛОХО С МЕСТОМ : откажитесь от работы со списком РКН. используйте только get_user.sh |
|||
|
|||
ЕСЛИ СОВСЕМ ВСЕ УЖАСНО С МЕСТОМ : берете tpws и делаете все своими руками. поднятие iptables, автостарт бинарика. |
|||
С некоторых версий скрипты запуска zapret без ipset не работают (он требуется для ip exclude) |
|||
|
|||
СОВЕТ : Покупайте только роутеры с USB. В USB можно воткнуть флэшку и вынести на нее корневую файловую систему |
|||
или использовать ее в качестве оверлея. Не надо мучать себя, запихивая незапихиваемое в 8 мб встроенной флэшки. |
|||
Для комфортной работы с zapret нужен роутер с 16 Mb встроенной памяти или USB разъемом и 128+ Mb RAM. |
|||
На 64 Mb без swap будут проблемы с листами РКН. Если у вас только 64 Mb, и вы хотите листы РКН, подключите swap. |
|||
32 Mb для современных версий openwrt - конфигурация на грани живучести. Возможны хаотические падения процессов в oom. |
|||
Работа с листами РКН невозможна в принципе. |
|||
|
|||
@ -1,32 +1,32 @@ |
|||
nftables test cheat sheet |
|||
simplified rules to test nfqws and tpws |
|||
`nftables` test cheat sheet. Simplified rules to test `nfqws` and `tpws`. |
|||
|
|||
For DNAT: |
|||
|
|||
For DNAT : |
|||
|
|||
# run tpws as user "tpws". its required to avoid loops. |
|||
|
|||
```sh |
|||
# run tpws as user "tpws". its required to avoid loops |
|||
nft delete table inet ztest |
|||
nft create table inet ztest |
|||
nft add chain inet ztest pre "{type nat hook prerouting priority dstnat;}" |
|||
nft add rule inet ztest pre tcp dport "{80,443}" redirect to :988 |
|||
nft add chain inet ztest out "{type nat hook output priority -100;}" |
|||
nft add rule inet ztest out tcp dport "{80,443}" skuid != tpws redirect to :988 |
|||
``` |
|||
|
|||
For `dpi-desync` attack: |
|||
|
|||
For dpi desync attack : |
|||
|
|||
```sh |
|||
nft delete table inet ztest |
|||
nft create table inet ztest |
|||
nft add chain inet ztest post "{type filter hook postrouting priority mangle;}" |
|||
nft add rule inet ztest post tcp dport "{80,443}" ct original packets 1-12 queue num 200 bypass |
|||
nft add rule inet ztest post udp dport 443 ct original packets 1-4 queue num 200 bypass |
|||
|
|||
# auto hostlist with avoiding wrong ACK numbers in RST,ACK packets sent by russian DPI |
|||
sysctl net.netfilter.nf_conntrack_tcp_be_liberal=1 |
|||
# auto hostlist with avoiding wrong ACK numbers in RST,ACK packets sent by Russian DPI |
|||
|
|||
sysctl net.netfilter.nf_conntrack_tcp_be_liberal=1 |
|||
nft add chain inet ztest pre "{type filter hook prerouting priority filter;}" |
|||
nft add rule inet ztest pre tcp sport "{80,443}" ct reply packets 1-4 queue num 200 bypass |
|||
``` |
|||
|
|||
|
|||
show rules : nft list table inet ztest |
|||
delete table : nft delete table inet ztest |
|||
* show rules: `nft list table inet ztest`, |
|||
* delete table: `nft delete table inet ztest` |
|||
@ -0,0 +1,142 @@ |
|||
- [Вступление](#вступление) |
|||
- [Минусы](#минусы) |
|||
- [Главная боль №1](#главная-боль-1) |
|||
- [Боль №2](#боль-2) |
|||
- [Боль №3](#боль-3) |
|||
- [Боль №4](#боль-4) |
|||
- [Плюсы](#плюсы) |
|||
- [Плюс №1, главный](#плюс-1-главный) |
|||
- [Плюс №2](#плюс-2) |
|||
- [Плюс №3](#плюс-3) |
|||
- [Плюс №4](#плюс-4) |
|||
- [Плюс №5](#плюс-5) |
|||
- [Выводы](#выводы) |
|||
|
|||
# Вступление |
|||
|
|||
`nftables` - это технология, пришедшая на замену `iptables`. |
|||
В ней собрали все, что относилось к различным `iptables`. А их немало. `iptables`, `ip6tables`, `ebtables`, `arptables`, `ipset`. |
|||
Весь код из разрозненных, но похожих компонент, собрали в одно целое с единым синтаксисом. |
|||
Добавили различные конструкции языка, позволяющие писать правила более лаконично, не повторяя одни и те же команды с небольшими различиями. |
|||
На `nftables` можно сделать почти все, что можно было сделать на `iptables`. Есть то, что можно сделать на `nftables`, но нельзя на `iptables`. |
|||
Есть и наоборот. |
|||
|
|||
# Минусы |
|||
|
|||
К сожалению, не обошлось и без боли. |
|||
|
|||
## Главная боль №1 |
|||
|
|||
Очень серьезная, актуальная для OpenWrt, и решения не видно. |
|||
|
|||
ipset-ы позволяли загонять пересекающиеся интервалы IP адресов или подсетей. |
|||
nftables sets это не позволяют. Любое пересечение вызывает ошибку. |
|||
Есть auto-merge, но это работает только в user mode в процессе `nft`, при условии, что весь блок адресов загоняется одной командой |
|||
и нет пересечений с уже имеющимся контентом в set. |
|||
Это не было бы критической проблемой, поскольку скрипты `zapret` и так загоняют ipset целиком. |
|||
Проблема в катастрофическом расходе памяти при операции загона больших интервальных листов, то есть с подсетями и диапазонами. |
|||
Чтобы загнать 100000 IPv4 записей, едва хватает 300 Mb памяти устройства. |
|||
При успехе операции в ядре список столько не занимает, но суть дела это не меняет. |
|||
Для традиционных Linux систем это не проблема, но почти все роутеры загнутся. |
|||
Приемлемого решения не просматривается. |
|||
Сделать записи непересекающимися в листах - задача непростая. |
|||
Потребуется переписать алгоритм auto-merge из `nft`, но с пониженным расходом памяти. |
|||
Загонять записи по одному отдельными вызовами `nft`, игнорируя ошибки, займет вечность. |
|||
Загонять блоком отдельных команд, игнорируя ошибки, - `nft` такого не умеет. Похоже, при любой ошибке происходит откат всего скрипта. |
|||
К тому же при таком подходе будут неточности в итоговом результате. |
|||
Swap позволяет немного сгладить проблему, но лишь незначительно. |
|||
Скажем, если вдруг list загоняется без ошибок с 300 Mb памяти и с падением на 256 MB, то swap спасает. |
|||
Если памяти становится 200 MB, то swap уже не спасет. |
|||
Все равно вызывается OOM killer, заодно убивая и другие процессы, кроме `nft`, а это уже совсем плохо. Может быть убито что-то важное. |
|||
|
|||
## Боль №2 |
|||
|
|||
Не смертельная, но тоже не айс. |
|||
|
|||
Какие-то нерациональные алгоритмы разбора таблиц в `nft`. |
|||
Например, есть 1 большой set на 100000 элементов и 1 маленький на 2 элемента. |
|||
Чтобы просто пролистать мелкий set или добавить туда еще что-то `nft` будет мусолить несколько секунд. |
|||
Что он делает за это время? Тащит из ядра огромный блоб, в котором все в куче, и разбирает его, чтобы выделить искомую мелочь? |
|||
В какой-то мере удается это сгладить, объединяя несколько команд в единый скрипт. |
|||
|
|||
## Боль №3 |
|||
|
|||
Система `nftables` построена на виртуальной машине. Правила, которые вы пишите, переводятся в псевдокод VM. |
|||
Чтобы потом их показать, `nft` декомпилирует код и переводит в читаемый язык. |
|||
Это довольно сложно, и регулярно случаются баги, связанные с неверным отображением. |
|||
|
|||
Кроме этого, часто встречаются и баги парсера. |
|||
Например, все версии `nft` вплоть до 1.0.1 имеют баг, который не разрешает названия интерфейсов в кавычках в определении flowtable. |
|||
Без кавычек нельзя вставить интерфейсы, имя которых начинается с цифры. |
|||
OpenWrt решает эту проблему отдельным патчем в snapshot версии, но на традиционных системах и в OpenWrt 21.x- его нет. |
|||
Почему бы не наплевать на интерфейсы, начинающиеся с цифры? Потому что для OpenWrt 6to4-6to4, 6in4-he-net - обычное явление. |
|||
На текущий момент этой проблемы в OpenWrt уже нет, если использовать актуальную версию. |
|||
|
|||
Но тем не менее, хоть `nft` и давно перешел отметку 1.0, всякая мелочь, особенно на не совсем стандартных правилах, регулярно всплывает. |
|||
Потому чем новее у вас будет версия `nft`, тем больше там выловлено проблем. |
|||
Здесь обновления важны, чтобы потом не мучиться из-за давно исправленного велосипеда. |
|||
|
|||
## Боль №4 |
|||
|
|||
Невозможно, не копаясь в других таблицах и хуках, ничего не зная об их содержании, предотвратить DROP или REJECT. |
|||
Нельзя написать такое правило, которое что-то важное ACCEPT нет, игнорируя остальные хуки во всех таблицах. |
|||
Если у вас есть какой-то фаервол, и он что-то дропает, то как от этого отказаться, если надо временно что-то принять? |
|||
Это особенность `netfilter`, он так работает, но в `iptables` есть лишь стандартные таблицы с их хуками, куда можно вставить ACCEPT. |
|||
Здесь хуков может быть сколько угодно в каких угодно таблицах. |
|||
Эта проблема частично ломает кайф от независимого управления таблицами. |
|||
|
|||
# Плюсы |
|||
|
|||
## Плюс №1, главный |
|||
|
|||
`iptables` хороши, когда ими пользуется кто-то один. Иначе это проходной двор. |
|||
Когда есть система управления фаерволом, то приходится как-то к ней прикручиваться, чтобы не нарушить ее работу |
|||
и управлять правилами синхронно. Нужно уметь внести и удалить отдельные правила когда это нужно, не трогая все остальное. |
|||
Некоторые системы управления фаерволом вообще не предполагают, чтобы кто-то еще лез в `iptables`, и это очень сильно портит жизнь. |
|||
У `iptables` есть предопределенный набор хуков `netfilter` с фиксированным приоритетом. |
|||
В `nftables` хуков можно создать неограниченное количество с выбранным приоритетом, управляя ими независимо в отдельных таблицах. |
|||
Система управления фаерволом может работать в одной таблице (`fw4` в случае OpenWrt) и не трогать все остальное. |
|||
`zapret` может работать в другой таблице и не трогать систему управления фаерволом. Они друг другу не мешают. |
|||
Это снимает множество боли. |
|||
Но есть и исключение. `nfset`-ы - аналог `ipset`-ов - нельзя использовать из другой таблицы. |
|||
Потому если вам нужен `ipset`, создаваемый `zapret` скриптами, вам понадобится писать правила в той же таблице. |
|||
Но нет никакой необходимости влезать в цепочки `zapret`. |
|||
Создаете свои цепочки и хуки и делаете в них что угодно. |
|||
|
|||
## Плюс №2 |
|||
|
|||
Возможность выбора приоритета хука позволяет легко решить проблему хаотической и принудительной дефрагментацией L3 IPv6, без танцев с загрузкой модулей ядра со специальными параметрами или перекомпиляцией `nftables-nft`. |
|||
Это же позволяет перехватить трафик после SNAT/MASQUERADE, что на `iptables` невозможно. |
|||
Атаки на проходящий трафик, ломающие NAT, крайне затруднены на `iptables`. |
|||
|
|||
## Плюс №3 |
|||
|
|||
Наличие множеств (anonymous/named sets) позволяет не писать кучу однообразных правил там, где в `iptables` их пришлось бы написать. |
|||
|
|||
## Плюс №4 |
|||
|
|||
Если у вас есть `nftables`, то там наверняка есть уже все или почти все. |
|||
Нет кучи разных модулей ядра и .so плагинов для `iptables` user-mode процесса. |
|||
Отдельные модули ядра есть, но их меньше, чем в `iptables`, и OpenWrt их делит на меньшее число пакетов, большинство из которых |
|||
и так ставятся по умолчанию. user-mode процесс `nft` и вовсе неделим. EXE-шник + lib. |
|||
|
|||
## Плюс №5 |
|||
|
|||
Пишут, что `nftables` работают быстрее. Но это не точно и зависит от много чего. |
|||
В целом - чем меньше правил, тем выше скорость. Но в `nftables` правил можно писать меньше, значит скорость тоже может быть выше. |
|||
У разработчиков есть идея перевести backend `nftables` на BPF, а это наверняка будет существенно быстрее. |
|||
|
|||
# Выводы |
|||
|
|||
Без больших листов все почти прекрасно. Но большие ip листы убивают все. Не для домашних это роутеров. |
|||
А ipset-ы к `nftables` не прикрутить. |
|||
Зато есть возможность задействовать более продвинутые атаки, конфликтующие с NAT, которые на `iptables` могут быть невозможны. |
|||
Делать нечего. Openwrt отошел от `iptables`. С этим придется как-то жить. |
|||
Поэтому пришлось сделать для OpenWrt поддержку и `iptables`, и `nftables` (только с версии OpenWrt 21.xx, в более старых будут проблемы). |
|||
`iptables` можно задействовать на любой OpenWrt версии. |
|||
Если используется `fw3`, применяется старый механизм интеграции в `fw3`. |
|||
Если он не используется, то правилами `iptables` управляем как в традиционных Linux системах - то есть с возможностью |
|||
запуска и остановки, а скрипт запуска вносит в том числе и правила `iptables`. |
|||
|
|||
На новых OpenWrt возможно снести `nftables` и `firewall4` и установить `firewall3` и `iptables`. |
|||
Если вам никак без больших IP листов на слабой системе, это может быть единственным спасением. |
|||
@ -1,120 +0,0 @@ |
|||
nftables - это технология, пришедшая на замену iptables. |
|||
В ней собрали все, что относилось к различным iptables. А их немало. iptables, ip6tables, ebtables, arptables, ipset. |
|||
Весь код из разрозненных, но похожих компонент, собрали в одно целое с единым синтаксисом. |
|||
Добавили различные конструкции языка, позволяющие писать правила более лаконично, не повторяя одни и те же команды с небольшими различиями. |
|||
На nftables можно сделать почти все, что можно было сделать на iptables. Есть то, что можно сделать на nftables, но нельзя на iptables. |
|||
Есть и наоборот. |
|||
|
|||
К сожалению, не обошлось и без боли. |
|||
|
|||
Главная боль N1. Очень серьезная, актуальная для openwrt, и решения не видно. |
|||
|
|||
ipset-ы позволяли загонять пересекающиеся интервалы ip адресов или подсетей. |
|||
nftables sets это не позволяют. Любое пересечение вызывает ошибку. |
|||
Есть auto-merge, но это работает только в user mode в процессе nft, при условии, что весь блок адресов загоняется одной командой |
|||
и нет пересечений с уже имеющимся контентом в set. |
|||
Это не было бы критической проблемой, поскольку скрипты zapret и так загоняют ipset целиком. |
|||
Проблема в катастрофическом расходе памяти при операции загона больших интервальных листов, то есть с подсетями и диапазонами. |
|||
Чтобы загнать 100000 ipv4 записей, едва хватает 300 Mb памяти устройства. |
|||
При успехе операции в ядре список столько не занимает, но суть дела это не меняет. |
|||
Для традиционных linux систем это не проблема, но почти все роутеры загнутся. |
|||
Приемлемого решения не просматривается. |
|||
Сделать записи непересекающимися в листах - задача непростая. Потребуется переписать алгоритм auto-merge из nft, |
|||
но с пониженным расходом памяти. |
|||
Загонять записи по одному отдельными вызовами nft, игнорируя ошибки, займет вечность. |
|||
Загонять блоком отдельных команд, игнорируя ошибки, - nft такого не умеет. Похоже, при любой ошибке происходит откат всего скрипта. |
|||
К тому же при таком подходе будут неточности в итоговом результате. |
|||
Swap позволяет немного сгладить проблему, но лишь незначительно. |
|||
Скажем, если вдруг list загоняется без ошибок с 300 Mb памяти и с падением на 256 Mb, то swap спасает. |
|||
Если памяти становится 200 Mb, то swap уже не спасет. Все равно вызывается OOM killer, заодно убивая и другие процессы, кроме nft, |
|||
а это уже совсем плохо. Может быть убито что-то важное. |
|||
|
|||
Боль N2, не смертельная, но тоже не айс. |
|||
|
|||
Какие-то нерациональные алгоритмы разбора таблиц в nft. |
|||
Например, есть 1 большой set на 100000 элементов и 1 маленький на 2 элемента. |
|||
Чтобы просто пролистать мелкий set или добавить туда еще что-то nft будет мусолить несколько секунд. |
|||
Что он делает за это время ? Тащит из ядра огромный блоб, в котором все в куче, и разбирает его, чтобы выделить искомую мелочь ? |
|||
В какой-то мере удается это сгладить, обьединяя несколько команд в единый скрипт. |
|||
|
|||
Боль N3 |
|||
|
|||
Система nftables построена на виртуальной машине. Правила, которые вы пишите, переводятся в псевдокод VM. |
|||
Чтобы потом их показать , nft декомпилирует код и переводит в читаемый язык. |
|||
Это довольно сложно, и регулярно случаются баги, связанные с неверным отображением. |
|||
|
|||
Кроме этого, часто встречаются и баги парсера. |
|||
Например, все версии nft вплоть до 1.0.1 имеют баг, который не разрешает названия интерфейсов в кавычках в |
|||
определении flowtable. Без кавычек нельзя вставить интерфейсы , имя которых начинается с цифры. |
|||
OpenWRT решает эту проблему отдельным патчем в snapshot версии, но на традиционных системах и в openwrt 21.x- его нет. |
|||
Почему бы не наплевать на интерфейсы, начинающиеся с цифры ? Потому что для openwrt 6to4-6to4, 6in4-he-net - обычное явление. |
|||
На текущий момент этой проблемы в openwrt уже нет, если использовать актуальную версию. |
|||
|
|||
Но тем не менее, хоть nft и давно перешел отметку 1.0, всякая мелочь, особенно на не совсем стандартных правилах, |
|||
регулярно всплывает. Потому чем новее у вас будет версия nft, тем больше там выловлено проблем. |
|||
Здесь обновления важны, чтобы потом не мучаться из-за давно исправленного велосипеда. |
|||
|
|||
Боль N4 |
|||
|
|||
Невозможно , не копаясь в других таблицах и хуках, ничего не зная об их содержании, предотвратить DROP или REJECT. |
|||
Нельзя написать такое правило, которое что-то важное ACCEPTнет, игнорируя остальные хуки во всех таблицах. |
|||
Если у вас есть какой-то фаервол, и он что-то дропает, то как от этого отказаться, если надо временно что-то принять ? |
|||
Это особенность netfilter, он так работает, но в iptables есть лишь стандартные таблицы с их хуками, куда можно |
|||
вставить ACCEPT. Здесь хуков может быть сколько угодно в каких угодно таблицах. |
|||
Эта проблема частично ломает кайф от независимого управления таблицами. |
|||
|
|||
|
|||
Плюс N1, главный |
|||
|
|||
iptables хороши, когда ими пользуется кто-то один. Иначе это проходной двор. |
|||
Когда есть система управления фаерволом, то приходится как-то к ней прикручиваться, чтобы не нарушить ее работу |
|||
и управлять правилами синхронно. Нужно уметь внести и удалить отдельные правила когда это нужно, не трогая все остальное. |
|||
Некоторые системы управления фаерволом вообще не предполагают, чтобы кто-то еще лез в iptables, и это очень сильно портит жизнь. |
|||
У iptables есть предопределенный набор хуков netfilter с фиксированным приоритетом. |
|||
В nftables хуков можно создать неограниченное количество с выбранным приоритетом, управляя ими независимо в отдельных таблицах. |
|||
Система управления фаерволом может работать в одной таблице (fw4 в случае openwrt) и не трогать все остальное. |
|||
zapret может работать в другой таблице и не трогать систему управления фаерволом. Они друг другу не мешают. |
|||
Это снимает множество боли. |
|||
Но есть и исключение. nfset-ы - аналог ipset-ов - нельзя использовать из другой таблицы. Потому если вам нужен ipset, |
|||
создаваемый zapret скриптами, вам понадобится писать правила в той же таблице. Но нет никакой необходимости влезать в цепочки zapret. |
|||
Создаете свои цепочки и хуки и делаете в них что угодно. |
|||
|
|||
Плюс N2 |
|||
|
|||
Возможность выбора приоритета хука позволяет легко решить проблему хаотической и принудительной дефрагментацией L3 ipv6, |
|||
без танцев с загрузкой модулей ядра со специальными параметрами или перекомпиляцией nftables-nft. |
|||
Это же позволяет перехватить трафик после SNAT/MASQUERADE, что на iptables невозможно. |
|||
Атаки на проходящий трафик, ломающие NAT, крайне затруднены на iptables. |
|||
|
|||
Плюс N3 |
|||
|
|||
Наличие множеств (anonymous/named sets) позволяет не писать кучу однообразных правил там, где в iptables их пришлось бы написать. |
|||
|
|||
Плюс N4 |
|||
|
|||
Если у вас есть nftables, то там наверняка есть уже все или почти все. |
|||
Нет кучи разных модулей ядра и .so плагинов для iptables user-mode процесса. |
|||
Отдельные модули ядра есть, но их меньше, чем в iptables, и openwrt их делит на меньшее число пакетов, большинство из которых |
|||
и так ставятся по умолчанию. user-mode процесс nft и вовсе неделим. EXE-шник + lib. |
|||
|
|||
Плюс N5 |
|||
|
|||
Пишут, что nftables работают быстрее. Но это не точно и зависит от много чего. |
|||
В целом - чем меньше правил, тем выше скорость. Но в nftables правил можно писать меньше, значит скрость тоже может быть выше. |
|||
У разработчиков есть идея перевести backend nftables на BPF, а это наверняка будет существенно быстрее. |
|||
|
|||
|
|||
Выводы |
|||
|
|||
Без больших листов все почти прекрасно. Но большие ip листы убивают все. Не для домашних это роутеров. |
|||
А ipset-ы к nftables не прикрутить. |
|||
Зато есть возможность задействовать более продвинутые атаки, конфликтующие с NAT, которые на iptables могут быть невозможны. |
|||
Делать нечего. Openwrt отошел от iptables. С этим придется как-то жить. |
|||
Поэтому пришлось сделать для openwrt поддержку и iptables, и nftables (только с версии openwrt 21.xx, в более старых будут проблемы). |
|||
iptables можно задействовать на любой openwrt версии. |
|||
Если используется fw3, применяется старый механизм интеграции в fw3. |
|||
Если он не используется, то правилами iptables управляем как в традиционных linux системах - то есть с возможностью |
|||
запуска и остановки, а скрипт запуска вносит в том числе и правила iptables. |
|||
|
|||
На новых openwrt возможно снести nftables и firewall4 и установить firewall3 и iptables. |
|||
Если вам никак без больших ip листов на слабой системе, это может быть единственным спасением. |
|||
@ -0,0 +1,134 @@ |
|||
Специально для тех, кто хочет побыстрее начать, но не хочет слишком углубляться в простыню `readme.md`. |
|||
|
|||
Предупреждение: не пишите в Issue вопросы типа: "как скопировать файл", "как скачать", "как запустить", ... |
|||
То есть все, что касается базовых навыков обращения с ОС Linux. Эти вопросы буду закрывать сразу. |
|||
Если у вас подобные вопросы возникают, рекомендую не использовать данный софт или искать помощь где-то в другом месте. |
|||
То же самое могу сказать тем, кто хочет нажать 1 кнопку, чтобы все заработало, и совсем не хочет читать и изучать. |
|||
Увы, такое не подвезли и не подвезут. Ищите другие более простые методы обхода. Этот метод не для рядового пользователя. |
|||
|
|||
Обход DPI является хакерской методикой. |
|||
Под этим словом понимается метод, которому сопротивляется окружающая среда, которому автоматически не гарантирована работоспособность в любых условиях и на любых ресурсах, требуется настройка под специфические условия у вашего провайдера. |
|||
Условия могут меняться со временем, и методика может начинать или переставать работать, может потребоваться повторный анализ ситуации. |
|||
Могут обнаруживаться отдельные ресурсы, которые заблокированы иначе, и которые не работают или перестали работать. |
|||
Могут и сломаться отдельные незаблокированные ресурсы. |
|||
Поэтому очень желательно иметь знания в области сетей, чтобы иметь возможность проанализировать техническую ситуацию. |
|||
Не будет лишним иметь обходные каналы проксирования трафика на случай, если обход DPI не помогает. |
|||
|
|||
Будем считать, что у вас есть система на базе традиционного Linux или OpenWrt. |
|||
Если у вас традиционный Linux - задача обойти блокировки только на этой системе, если OpenWrt - обойти блокировки для подключенных устройств. |
|||
Это наиболее распространенный случай. |
|||
|
|||
1) Чтобы процедура установки сработала в штатном режиме на OpenWrt, нужно рассчитывать на свободное место около 1-2 Mb |
|||
для установки самого `zapret` и необходимых дополнительных пакетов. |
|||
Если места мало и нет возможности его увеличить за счет extroot, возможно, придется отказаться от варианта простой установки и прикручивать в ручном режиме без имеющихся скриптов запуска, |
|||
либо попробовать засунуть требуемые `zapret` дополнительные пакеты в сжатый образ squashfs с помощью image builder и перешить этим вариантом роутер. |
|||
См. `docs/manual_setup.md`, `docs/readme.md`. |
|||
|
|||
2) Скачайте `.zip` архив проекта с GitHub в `/tmp`, распакуйте его там, либо клонируйте проект: `git clone --depth 1 https://github.com/bol-van/zapret`. |
|||
|
|||
3) Убедитесь, что у вас отключены все средства обхода блокировок, в том числе и сам `zapret`. |
|||
Гарантированно уберет `zapret` скрипт `uninstall_easy.sh`. |
|||
|
|||
4) Если вы работаете в виртуальной машине, необходимо использовать соединение с сетью в режиме bridge. NAT не подходит. |
|||
|
|||
5) Выполните однократные действия по установке требуемых пакетов в ОС и настройке бинарников правильной архитектуры |
|||
|
|||
```sh |
|||
install_bin.sh |
|||
install_prereq.sh |
|||
``` |
|||
|
|||
Вас могут спросить о типе фаервола (`iptables`/`nftables`) и использовании IPv6. Это нужно для установки |
|||
правильных пакетов в ОС, чтобы не устанавливать лишнее. |
|||
|
|||
6) Запустите `blockcheck.sh`. |
|||
|
|||
`blockcheck.sh` в начале проверяет DNS. Если выводятся сообщения о подмене адресов, то первым делом нужно решить эту проблему, иначе ничего не будет работать. Решение проблемы DNS выходит за рамки проекта. |
|||
Обычно она решается либо заменой DNS серверов от провайдера на публичные (1.1.1.1, 8.8.8.8), либо в случае перехвата провайдером обращений к сторонним серверам - через специальные средства шифрования DNS запросов, такие как DNSCrypt, DoT, DoH. |
|||
|
|||
Еще один эффективный вариант - использовать ресолвер от Yandex 77.88.8.88 на нестандартном порту 1253. |
|||
Многие провайдеры не анализируют обращения к DNS на нестандартных портах. |
|||
|
|||
Проверить работает ли этот вариант можно так : |
|||
|
|||
```sh |
|||
dig -p 53 @77.88.8.88 rutracker.org |
|||
dig -p 1253 @77.88.8.88 rutracker.org |
|||
``` |
|||
|
|||
Если DNS действительно подменяется, и ответ на эти 2 команды разный, значит метод вероятно работает. |
|||
|
|||
В OpenWrt DNS на нестандартном порту можно прописать в `/etc/config/dhcp` таким способом: |
|||
|
|||
``` |
|||
config dnsmasq |
|||
............. |
|||
list server '77.88.8.88#1253' |
|||
``` |
|||
|
|||
Если настройки IP и DNS получаются автоматически от провайдера, в `/etc/config/network` |
|||
найдите секцию интерфейса `wan` и сделайте так: |
|||
|
|||
``` |
|||
config interface 'wan' |
|||
............. |
|||
option peerdns '0' |
|||
``` |
|||
|
|||
```sh |
|||
/etc/init.d/network restart |
|||
/etc/init.d/dnsmasq restart |
|||
``` |
|||
|
|||
Если это не подходит, можно перенаправлять обращения на UDP и TCP порты 53 вашего DNS сервера на 77.88.8.88:1253 средствами `iptables`/`nftables`. В `/etc/resolv.conf` нельзя прописать DNS на нестандартном порту. |
|||
|
|||
7) `blockcheck` позволяет выявить рабочую стратегию обхода блокировок |
|||
По результатам `blockcheck` нужно понять какой вариант будете использовать: `nfqws` или `tpws`. |
|||
И запомнить найденные стратегии. |
|||
|
|||
Следует понимать, что `blockcheck` проверяет доступность только конкретного домена, который вы вводите в начале. |
|||
Вероятно, все остальные домены блокированы подобным образом, но не факт. |
|||
В большинстве случаев можно объединить несколько стратегий в одну универсальную, но для этого необходимо понимать |
|||
"что там за буковки". Если вы в сетях слабо разбираетесь, это не для вас. В противном случае читайте `readme.md`. |
|||
`zapret` не может пробить блокировку по IP адресу. Для проверки нескольких доменов вводите их через пробел. |
|||
|
|||
Сейчас блокираторы ставят на магистральных каналах. В сложных случаях у вас может быть несколько маршрутов с различной длиной по ХОПам, с DPI на разных хопах. |
|||
Приходится преодолевать целый зоопарк DPI, которые еще и включаются в работу хаотичным образом или образом, зависящим от направления (IP сервера). |
|||
`blockcheck` не всегда может выдать вам в итогах оптимальную стратегию, которую надо просто переписать в настройки. |
|||
В некоторых случаях надо реально думать что происходит, анализируя результат на разных стратегиях. |
|||
Если вы применяете большой TTL, чтобы достать до магистрала, то не лишним будет добавить дополнительный ограничитель |
|||
`--dpi-desync-fooling`, чтобы не сломать сайты на более коротких дистанциях. |
|||
`md5sig` наиболее совместим, но работает только на Linux серверах. |
|||
`badseq` может работать только на HTTPS и не работать на HTTP. |
|||
`badsum` и вовсе перестал работать на многих провайдерах с некоторых пор, видимо включили проверку чексумм на DPI. |
|||
Чтобы выяснить какие дополнительные ограничители работают, смотрите результат теста аналогичных стратегий без TTL с каждым из этих ограничителей. |
|||
|
|||
При использовании `autottl` следует протестировать как можно больше разных доменов. |
|||
Эта техника может на одних провайдерах работать стабильно, на других потребуется выяснить при каких параметрах она стабильна, на третьих полный хаос, и проще отказаться. |
|||
|
|||
8) Запустите `install_easy.sh`. |
|||
|
|||
Выберите `nfqws` или `tpws`, затем согласитесь на редактирование параметров. |
|||
Откроется редактор, куда впишите найденные стратегии. |
|||
Для `nfqws` отдельно настраиваются стратегии на HTTP и HTTPS для IPv4 и IPv6. |
|||
То есть по максимуму 4 разных варианта. |
|||
`NFQWS_OPT_DESYNC` - это общая установка, которая применяется, если какой-либо уточняющий параметр не задан |
|||
`NFQWS_OPT_DESYNC_HTTP` и `NFQWS_OPT_DESYNC_HTTPS` заменяют стратегию для HTTP и HTTPS. |
|||
Если у вас включен IPv6, то они так же будут применены и к IPv6. Если для IPv6 нужна другая стратегия, то можно задать уточняющие параметры `NFQWS_OPT_DESYNC_HTTP6` и `NFQWS_OPT_DESYNC_HTTPS6`. |
|||
Если стратегии для IPv4 и IPv6 отличаются лишь TTL, то в целях экономии ресурсов роутера (меньше процессов `nfqws`) следует отказаться от использования специфических для IPv6 установок. Вместо них использовать параметры |
|||
`--dpi-desync-ttl` и `--dpi-desync-ttl6` в общих установках. Таким способом можно заставить один процесс `nfqws` обрабатывать трафик на IPv4 и на IPv6 с разным TTL. |
|||
|
|||
Важным вопросом является вопрос о поддержке HTTP keep alive. |
|||
Отвечайте `N`. Если вдруг на HTTP сайтах будут хаотические сбои типа то загружается, то заглушка или сброс, попробуйте включить поддержку keep alive. |
|||
Но просто "на всякий случай" не включайте - это увеличит нагрузку на роутер. |
|||
|
|||
Если это не помогает, или хаотичное поведение наблюдается и на HTTPS, то еще раз прогоните `blockcheck` с установленным числом попыток проверки не менее 5. |
|||
Возможно, ваш провайдер использует балансировку нагрузки, где на разных путях установлен разный DPI. |
|||
|
|||
9) На все остальные вопросы `install_easy.sh` отвечайте согласно выводимой аннотации. |
|||
|
|||
10) Если ломаются отдельные незаблокированные ресурсы, следует вносить их в исключения, либо пользоваться ограничивающим ipset или хост листом. Читайте основной талмуд `readme.md` ради подробностей. |
|||
|
|||
Это минимальная инструкция, чтобы сориентироваться с чего начать. Однако, это - не панацея. |
|||
В некоторых случаях вы не обойдетесь без знаний и основного "талмуда". |
|||
Подробности и полное техническое описание расписаны в `readme.md`. |
|||
@ -1,137 +0,0 @@ |
|||
Специально для тех, кто хочет побыстрее начать, но не хочет слишком углубляться в простыню readme.txt. |
|||
|
|||
Предупреждение : не пишите в issue вопросы типа "как скопировать файл", "как скачать", "как запустить", ... |
|||
То есть все , что касается базовых навыков обращения с ОС linux. Эти вопросы буду закрывать сразу. |
|||
Если у вас подобные вопросы возникают, рекомендую не использовать данный софт или искать помощь где-то в другом месте. |
|||
То же самое могу сказать тем, кто хочет нажать 1 кнопку, чтобы все заработало, и совсем не хочет читать и изучать. |
|||
Увы, такое не подвезли и не подвезут. Ищите другие более простые методы обхода. Этот метод не для рядового пользователя. |
|||
|
|||
Обход DPI является хакерской методикой. Под этим словом понимается метод, которому сопротивляется окружающая среда, |
|||
которому автоматически не гарантирована работоспособность в любых условиях и на любых ресурсах, |
|||
требуется настройка под специфические условия у вашего провайдера. Условия могут меняться со временем, |
|||
и методика может начинать или переставать работать, может потребоваться повторный анализ ситуации. |
|||
Могут обнаруживаться отдельные ресурсы, которые заблокированы иначе, и которые не работают или перестали работать. |
|||
Могут и сломаться отдельные незаблокированные ресурсы. |
|||
Поэтому очень желательно иметь знания в области сетей, чтобы иметь возможность проанализировать техническую ситуацию. |
|||
Не будет лишним иметь обходные каналы проксирования трафика на случай, если обход DPI не помогает. |
|||
|
|||
Будем считать, что у вас есть система на базе традиционного linux или openwrt. |
|||
Если у вас традиционный linux - задача обойти блокировки только на этой системе, если openwrt - обойти блокировки |
|||
для подключенных устройств. Это наиболее распространенный случай. |
|||
|
|||
1) Чтобы процедура установки сработала в штатном режиме на openwrt, нужно раcсчитывать на свободное место около 1-2 Mb |
|||
для установки самого zapret и необходимых дополнительных пакетов. |
|||
Если места мало и нет возможности его увеличить за счет extroot, возможно придется отказаться от варианта |
|||
простой установки и прикручивать в ручном режиме без имеющихся скриптов запуска, либо попробовать засунуть требуемые |
|||
zapret дополнительные пакеты в сжатый образ squashfs с помощью image builder и перешить этим вариантом роутер. |
|||
См docs/manual_setup.txt , docs/readme.txt . |
|||
|
|||
2) Скачайте zip архив проекта с github в /tmp, распакуйте его там, |
|||
либо клонируйте проект через : git clone --depth 1 https://github.com/bol-van/zapret |
|||
|
|||
3) Убедитесь, что у вас отключены все средства обхода блокировок, в том числе и сам zapret. |
|||
Гарантированно уберет zapret скрипт uninstall_easy.sh. |
|||
|
|||
4) Если вы работаете в виртуальной машине, необходимо использовать соединение с сетью в режиме bridge. nat не подходит |
|||
|
|||
5) Выполните однократные действия по установке требуемых пакетов в ОС и настройке бинариков правильной архитектуры |
|||
|
|||
install_bin.sh |
|||
install_prereq.sh |
|||
|
|||
Вас могут спросить о типе фаервола (iptables/nftables) и использовании ipv6. Это нужно для установки |
|||
правильных пакетов в ОС, чтобы не устанавливать лишнее. |
|||
|
|||
6) Запустите blockcheck.sh. blockcheck.sh в начале проверяет DNS. Если выводятся сообщения о подмене адресов, то |
|||
первым делом нужно решить эту проблему, иначе ничего не будет работать. |
|||
Решение проблемы DNS выходит за рамки проекта. Обычно она решается либо заменой DNS серверов |
|||
от провайдера на публичные (1.1.1.1, 8.8.8.8), либо в случае перехвата провайдером обращений |
|||
к сторонним серверам - через специальные средства шифрования DNS запросов, такие как dnscrypt, DoT, DoH. |
|||
|
|||
Еще один эффективный вариант - использовать ресолвер от yandex 77.88.8.88 на нестандартном порту 1253. |
|||
Многие провайдеры не анализируют обращения к DNS на нестандартных портах. |
|||
|
|||
Проверить работает ли этот вариант можно так : |
|||
|
|||
dig -p 53 @77.88.8.88 rutracker.org |
|||
dig -p 1253 @77.88.8.88 rutracker.org |
|||
|
|||
Если DNS действительно подменяется, и ответ на эти 2 команды разный, значит метод вероятно работает. |
|||
|
|||
В openwrt DNS на нестандартном порту можно прописать в /etc/config/dhcp таким способом : |
|||
|
|||
config dnsmasq |
|||
............. |
|||
list server '77.88.8.88#1253' |
|||
|
|||
Если настройки IP и DNS получаются автоматически от провайдера, в /etc/config/network |
|||
найдите секцию интерфейса 'wan' и сделайте так : |
|||
|
|||
config interface 'wan' |
|||
............. |
|||
option peerdns '0' |
|||
|
|||
/etc/init.d/network restart |
|||
/etc/init.d/dnsmasq restart |
|||
|
|||
Если это не подходит, можно перенаправлять обращения на udp и tcp порты 53 вашего DNS сервера на 77.88.8.88:1253 средствами |
|||
iptables/nftables. В /etc/resolv.conf нельзя прописать DNS на нестандартном порту. |
|||
|
|||
7) blockcheck позволяет выявить рабочую стратегию обхода блокировок |
|||
По результатам blockcheck нужно понять какой вариант будете использовать : nfqws или tpws |
|||
И запомнить найденные стратегии. |
|||
|
|||
Следует понимать, что blockcheck проверяет доступность только конкретного домена, который вы вводите в начале. |
|||
Вероятно, все остальные домены блокированы подобным образом, но не факт. |
|||
В большинстве случаев можно обьединить несколько стратегий в одну универсальную, но для этого необходимо понимать |
|||
"что там за буковки". Если вы в сетях слабо разбираетесь, это не для вас. В противном случае читайте readme.txt. |
|||
zapret не может пробить блокировку по IP адресу |
|||
Для проверки нескольких доменов вводите их через пробел. |
|||
|
|||
Сейчас блокираторы ставят на магистральных каналах. В сложных случаях у вас может быть несколько маршрутов |
|||
с различной длиной по ХОПам, с DPI на разных хопах. Приходится преодолевать целый зоопарк DPI, |
|||
которые еще и включаются в работу хаотичным образом или образом, зависящим от направления (IP сервера). |
|||
blockcheck не всегда может выдать вам в итогах оптимальную стратегию, которую надо просто переписать в настройки. |
|||
В некоторых случаях надо реально думать что происходит, анализируя результат на разных стратегиях. |
|||
Если вы применяете большой TTL, чтобы достать до магистрала, то не лишним будет добавить дополнительный ограничитель |
|||
--dpi-desync-fooling, чтобы не сломать сайты на более коротких дистанциях. |
|||
md5sig наиболее совместим, но работает только на linux серверах. |
|||
badseq может работать только на https и не работать на http. |
|||
badsum и вовсе перестал работать на многих провайдерах с некоторых пор, видимо включили проверку чексумм на DPI. |
|||
Чтобы выяснить какие дополнительные ограничители работают, смотрите результат теста аналогичных стратегий без TTL |
|||
с каждым из этих ограничителей. |
|||
|
|||
При использовании autottl следует протестировать как можно больше разных доменов. Эта техника |
|||
может на одних провайдерах работать стабильно, на других потребуется выяснить при каких параметрах |
|||
она стабильна, на третьих полный хаос, и проще отказаться. |
|||
|
|||
8) Запустите install_easy.sh. |
|||
Выберите nfqws или tpws, затем согласитесь на редактирование параметров. |
|||
Откроется редактор, куда впишите найденные стратегии. |
|||
Для nfqws отдельно настраиваются стратегии на http и https для ipv4 и ipv6. |
|||
То есть по максимуму 4 разных варианта. |
|||
NFQWS_OPT_DESYNC - это общая установка, которая применяется, если какой-либо уточняющий параметр не задан |
|||
NFQWS_OPT_DESYNC_HTTP и NFQWS_OPT_DESYNC_HTTPS заменяют стратегию для http и https. |
|||
Если у вас включен ipv6, то они так же будут применены и к ipv6. Если для ipv6 нужна другая стратегия, |
|||
то можно задать уточняющие параметры NFQWS_OPT_DESYNC_HTTP6 и NFQWS_OPT_DESYNC_HTTPS6. |
|||
Если стратегии для ipv4 и ipv6 отличаются лишь ttl, то в целях экономии ресурсов роутера (меньше процессов nfqws) |
|||
следует отказаться от использования специфических для ipv6 установок. Вместо них использовать параметры |
|||
--dpi-desync-ttl и --dpi-desync-ttl6 в общих установках. Таким способом можно заставить один процесс nfqws |
|||
обрабатывать трафик на ipv4 и на ipv6 с разным ttl. |
|||
|
|||
Важным вопросом является вопрос о поддержке http keep alive. |
|||
Отвечайте N. Если вдруг на http сайтах будут хаотические сбои типа то загружается, то заглушка или сброс, |
|||
попробуйте включить поддержку keep alive. Но просто "на всякий случай" не включайте - это увеличит нагрузку на роутер. |
|||
|
|||
Если это не помогает, или хаотичное поведение наблюдается и на https, то еще раз прогоните blockcheck |
|||
с установленным числом попыток проверки не менее 5. Возможно, ваш провайдер использует балансировку нагрузки, |
|||
где на разных путях установлен разный DPI. |
|||
|
|||
9) На все остальные вопросы install_easy.sh отвечайте согласно выводимой аннонтации. |
|||
|
|||
10) Если ломаются отдельные незаблокированные ресурсы, следует вносить их в исключения, либо пользоваться ограничивающим |
|||
ipset или хост листом. Читайте основной талмуд readme.txt ради подробностей. |
|||
|
|||
Это минимальная инструкция, чтобы соориентироваться с чего начать. Однако, это - не панацея. |
|||
В некоторых случаях вы не обойдетесь без знаний и основного "талмуда". |
|||
Подробности и полное техническое описание расписаны в readme.txt |
|||
@ -0,0 +1,117 @@ |
|||
- [Вступление](#вступление) |
|||
- [Самое простое решение](#самое-простое-решение) |
|||
- [Решение "как положено"](#решение-как-положено) |
|||
|
|||
# Вступление |
|||
|
|||
Специально для тех, кто хочет побыстрее начать, но не хочет слишком углубляться в простыню `readme.md`. |
|||
|
|||
Как обычно, компьютерная грамотность ложится полностью на вас. |
|||
Вы должны уметь работать с консолью Windows и иметь минимальные навыки обращения с командными файлами `.bat`, `.cmd`. |
|||
Если грамотность отсутствует и возникает куча "как" на базовых вещах - проходите мимо или ищите помощь в другом месте. |
|||
|
|||
Обход DPI является хакерской методикой. |
|||
Под этим словом понимается метод, которому сопротивляется окружающая среда, которому автоматически не гарантирована работоспособность в любых условиях и на любых ресурсах, требуется настройка под специфические условия у вашего провайдера. |
|||
Условия могут меняться со временем, и методика может начинать или переставать работать, может потребоваться повторный анализ ситуации. |
|||
Могут обнаруживаться отдельные ресурсы, которые заблокированы иначе, и которые не работают или перестали работать. |
|||
Могут и сломаться отдельные незаблокированные ресурсы. |
|||
Поэтому очень желательно иметь знания в области сетей, чтобы иметь возможность проанализировать техническую ситуацию. |
|||
Не будет лишним иметь обходные каналы проксирования трафика на случай, если обход DPI не помогает. |
|||
|
|||
Будем считать, что у вас есть Windows 7 или выше. Задача - обойти блокировки с самой системы. |
|||
|
|||
Есть решение самое простое, а есть "как положено". |
|||
|
|||
# Самое простое решение |
|||
|
|||
Совсем ничего не могу, все очень сложно, дайте мне таблетку. |
|||
|
|||
Скачайте и распакуйте [архив](https://github.com/bol-van/zapret-win-bundle/archive/refs/heads/master.zip). |
|||
Запустите `zapret-winws/preset_russia.cmd` от имени администратора. |
|||
Возможно, заведется сразу. Этот вариант похож на `2_any_country.cmd` из [GoodbyeDPI](https://github.com/ValdikSS/GoodbyeDPI). |
|||
|
|||
То же самое с ограничителем по автоматически создаваемому хост-листу `preset_russia_autohostlist.cmd`. |
|||
Что такое `autohostlist` - читайте `readme.md`. Проще говоря, мы обходим только то, что долго и упорно не хочет открываться. |
|||
Сначала не будет, но надо пытаться много раз, и тогда сработает, а дальше будет всегда срабатывать. |
|||
Остальное не будет ломаться. Использовать только, если первый вариант тоже работает. |
|||
|
|||
Не помогла таблетка? Это вовсе не значит, что ничего не получится. Но придется делать по-нормальному. |
|||
|
|||
# Решение "как положено" |
|||
|
|||
1) Если у вас Windows 7, обновляйте систему. Годами не обновляемая 7-ка может не запускать драйвер `windivert`. |
|||
Поддержка 32-битных x86 Windows возможна, но в готовом виде отсутствует. |
|||
На Windows 11 ARM64 выполните `arm64/install_arm64.cmd` от имени администратора и перезагрузите компьютер. |
|||
Читайте `docs/windows.md`. |
|||
|
|||
Имейте в виду, что антивирусы могут плохо реагировать на `windivert`. |
|||
`cygwin` имеет внушительный список несовместимостей с антивирусами. Многие антивирусы его ломают. |
|||
Читайте [FAQ](https://www.cygwin.com/faq.html#faq.using.bloda). |
|||
Если это имеет место, используйте исключения. Если это не помогает - отключайте антивирус совсем. |
|||
|
|||
2) Убедитесь, что у вас отключены все средства обхода блокировок, в том числе и сам `zapret`. |
|||
|
|||
3) Если вы работаете в виртуальной машине, необходимо использовать соединение с сетью в режиме bridge. NAT не подходит. |
|||
|
|||
4) Скачайте и распакуйте [архив](https://github.com/bol-van/zapret-win-bundle/archive/refs/heads/master.zip). |
|||
|
|||
5) Запустите `blockcheck\blockcheck.cmd`. |
|||
|
|||
`blockcheck` в начале проверяет DNS. Если выводятся сообщения о подмене адресов, то первым делом нужно решить эту проблему, иначе ничего не будет работать. Решение проблемы DNS выходит за рамки проекта. |
|||
Обычно она решается либо заменой DNS серверов от провайдера на публичные (1.1.1.1, 8.8.8.8), либо в случае перехвата провайдером обращений к сторонним серверам - через специальные средства шифрования DNS запросов, такие как DNSCrypt, DoT, DoH. |
|||
В современных броузерах чаще всего DoH включен по умолчанию, но `curl` будет использовать обычный системный DNS. |
|||
Новые билды Windows 10 и Windows 11 поддерживают системные DoH из коробки. Они не настроены по умолчанию. |
|||
|
|||
[Тут](https://hackware.ru/?p=13707) все разжевано как и где это включается. |
|||
|
|||
6) `blockcheck` позволяет выявить рабочую стратегию обхода блокировок. |
|||
Лог скрипта будет сохранен в `blockcheck\blockcheck.log`. |
|||
Запомните найденные стратегии. |
|||
|
|||
Следует понимать, что `blockcheck` проверяет доступность только конкретного домена, который вы вводите в начале. |
|||
Вероятно, все остальные домены блокированы подобным образом, но не факт. |
|||
В большинстве случаев можно объединить несколько стратегий в одну универсальную, но для этого необходимо понимать "что там за буковки". |
|||
Если вы в сетях слабо разбираетесь, это не для вас. В противном случае читайте `readme.md`. |
|||
`zapret` не может пробить блокировку по IP адресу. Для проверки нескольких доменов вводите их через пробел. |
|||
|
|||
Сейчас блокираторы ставят на магистральных каналах. В сложных случаях у вас может быть несколько маршрутов с различной длиной по ХОПам, с DPI на разных хопах. |
|||
Приходится преодолевать целый зоопарк DPI, которые еще и включаются в работу хаотичным образом или образом, зависящим от направления (IP сервера). |
|||
`blockcheck` не всегда может выдать вам в итогах оптимальную стратегию, которую надо просто переписать в настройки. |
|||
В некоторых случаях надо реально думать что происходит, анализируя результат на разных стратегиях. |
|||
Если вы применяете большой TTL, чтобы достать до магистрала, то не лишним будет добавить дополнительный ограничитель |
|||
`--dpi-desync-fooling`, чтобы не сломать сайты на более коротких дистанциях. |
|||
`md5sig` наиболее совместим, но работает только на Linux серверах. |
|||
`badseq` может работать только на HTTPS и не работать на HTTP. |
|||
Чтобы выяснить какие дополнительные ограничители работают, смотрите результат теста аналогичных стратегий без TTL |
|||
с каждым из этих ограничителей. |
|||
|
|||
При использовании `autottl` следует протестировать как можно больше разных доменов. |
|||
Эта техника может на одних провайдерах работать стабильно, на других потребуется выяснить при каких параметрах она стабильна, на третьих полный хаос, и проще отказаться. |
|||
|
|||
7) Протестируйте найденные стратегии на `winws`. `winws` следует брать из `zapret-winws`. |
|||
Для этого откройте командную строку Windows от имени администратора в директории `zapret-winws`. |
|||
Проще всего это сделать через `_CMD_ADMIN.cmd`. Он сам поднимет права и зайдет в нужную директорию. |
|||
|
|||
8) Обеспечьте удобную загрузку обхода блокировок. |
|||
|
|||
Есть 2 варианта. Ручной запуск через ярлык или автоматический при старте системы, вне контекста текущего пользователя. |
|||
Последний вариант разделяется на запуск через планировщик задач и через службы Windows. |
|||
|
|||
Если хотите ручной запуск, скопируйте `preset_russia.cmd` в `preset_my.cmd` и адаптируйте его под ваши параметра запуска. |
|||
Потом можно создать ярлык на рабочем столе на `preset_my.cmd`. Не забудьте, что требуется запускать от имени администратора. |
|||
|
|||
Но лучше будет сделать неинтерактивный автоматический запуск вместе с системой. |
|||
В `zapret-winws` есть командные файлы `task_*`, предназначенные для управления задачами планировщика. |
|||
Там следует поменять содержимое переменной `WINWS1` на свою стратегию. |
|||
Если вы не можете объединить несколько стратегий для разных протоколов в одну, дублируйте код в каждом из `.cmd` для поддержки нескольких задач: `winws1`, `winws2`, `winws3`. |
|||
После создания задач запустите их. Проверьте, что обход встает после перезагрузки Windows. |
|||
|
|||
Аналогично настраиваются и службы Windows. Смотрите `service_*.cmd`. |
|||
|
|||
9) Если ломаются отдельные незаблокированные ресурсы, используйте хост-листы. |
|||
Где они будут находиться - решайте сами. |
|||
Параметры управления хост-листами точно такие же, как в *nix. |
|||
|
|||
Это минимальная инструкция, чтобы сориентироваться с чего начать. Однако, это - не панацея. |
|||
В некоторых случаях вы не обойдетесь без знаний и основного "талмуда". |
|||
Подробности и полное техническое описание расписаны в `readme.md`. |
|||
@ -1,117 +0,0 @@ |
|||
Специально для тех, кто хочет побыстрее начать, но не хочет слишком углубляться в простыню readme.txt. |
|||
|
|||
Как обычно, компьютерная грамотность ложится полностью на вас. |
|||
Вы должны уметь работать с консолью windows и иметь минимальные навыки обращения с командными файлами bat,cmd. |
|||
Если грамотность отсутствует и возникает куча "как" на базовых вещах - проходите мимо или ищите помощь в другом месте. |
|||
|
|||
Обход DPI является хакерской методикой. Под этим словом понимается метод, которому сопротивляется окружающая среда, |
|||
которому автоматически не гарантирована работоспособность в любых условиях и на любых ресурсах, |
|||
требуется настройка под специфические условия у вашего провайдера. Условия могут меняться со временем, |
|||
и методика может начинать или переставать работать, может потребоваться повторный анализ ситуации. |
|||
Могут обнаруживаться отдельные ресурсы, которые заблокированы иначе, и которые не работают или перестали работать. |
|||
Могут и сломаться отдельные незаблокированные ресурсы. |
|||
Поэтому очень желательно иметь знания в области сетей, чтобы иметь возможность проанализировать техническую ситуацию. |
|||
Не будет лишним иметь обходные каналы проксирования трафика на случай, если обход DPI не помогает. |
|||
|
|||
Будем считать, что у вас есть windows 7 или выше. Задача - обойти блокировки с самой системы. |
|||
|
|||
Есть решение самое простое, а есть "как положено". |
|||
|
|||
САМОЕ ПРОСТОЕ РЕШЕНИЕ |
|||
|
|||
Совсем ничего не могу, все очень сложно, дайте мне таблетку. |
|||
|
|||
Скачайте и распакуйте архив https://github.com/bol-van/zapret-win-bundle/archive/refs/heads/master.zip |
|||
Запустите zapret-winws/preset_russia.cmd от имени администратора. |
|||
Возможно, заведется сразу. Этот вариант похож на "2_any_country.cmd" из GoodbyeDPI. |
|||
|
|||
То же самое с ограничителем по автоматически создаваемому хост-листу preset_russia_autohostlist.cmd. |
|||
Что такое autohostlist - читайте readme.txt. Проще говоря, мы обходим только то, что долго и упорно не хочет открываться. |
|||
Сначала не будет, но надо пытаться много раз, и тогда сработает, а дальше будет всегда срабатывать. |
|||
Остальное не будет ломаться. Использовать только, если первый вариант тоже работает. |
|||
|
|||
Не помогла таблетка ? Это вовсе не значит, что ничего не получится. Но придется делать по-нормальному. |
|||
|
|||
РЕШЕНИЕ "КАК ПОЛОЖЕНО" |
|||
|
|||
1) Если у вас windows 7, обновляйте систему. Годами не обновляемая 7-ка может не запускать драйвер windivert. |
|||
Поддержка 32-битных x86 windows возможна, но в готовом виде отсутствует. |
|||
На windows 11 arm64 выполните arm64/install_arm64.cmd от имени администратора и перезагрузите компьютер. |
|||
Читайте docs/windows.txt |
|||
|
|||
Имейте в виду, что антивирусы могут плохо реагировать на windivert. |
|||
cygwin имеет внушительный список несовместимостей с антивирусами. Многие антивирусы его ломают. |
|||
https://www.cygwin.com/faq.html#faq.using.bloda |
|||
Если это имеет место , используйте исключения. Если это не помогает - отключайте антивирус совсем. |
|||
|
|||
2) Убедитесь, что у вас отключены все средства обхода блокировок, в том числе и сам zapret. |
|||
|
|||
3) Если вы работаете в виртуальной машине, необходимо использовать соединение с сетью в режиме bridge. nat не подходит |
|||
|
|||
4) Скачайте и распакуйте архив https://github.com/bol-van/zapret-win-bundle/archive/refs/heads/master.zip |
|||
|
|||
5) Запустите blockcheck\blockcheck.cmd. blockcheck в начале проверяет DNS. Если выводятся сообщения о подмене адресов, то |
|||
первым делом нужно решить эту проблему, иначе ничего не будет работать. |
|||
Решение проблемы DNS выходит за рамки проекта. Обычно она решается либо заменой DNS серверов |
|||
от провайдера на публичные (1.1.1.1, 8.8.8.8), либо в случае перехвата провайдером обращений |
|||
к сторонним серверам - через специальные средства шифрования DNS запросов, такие как dnscrypt, DoT, DoH. |
|||
В современных броузерах чаще всего DoH включен по умолчанию, но curl будет использовать обычный системный DNS. |
|||
Новые билды win10 и win11 поддерживают системные DoH из коробки. Они не настроены по умолчанию. |
|||
|
|||
Тут все разжевано как и где это включается : https://hackware.ru/?p=13707 |
|||
|
|||
6) blockcheck позволяет выявить рабочую стратегию обхода блокировок. |
|||
Лог скрипта будет сохранен в blockcheck\blockcheck.log. |
|||
Запомните найденные стратегии. |
|||
|
|||
Следует понимать, что blockcheck проверяет доступность только конкретного домена, который вы вводите в начале. |
|||
Вероятно, все остальные домены блокированы подобным образом, но не факт. |
|||
В большинстве случаев можно обьединить несколько стратегий в одну универсальную, но для этого необходимо понимать |
|||
"что там за буковки". Если вы в сетях слабо разбираетесь, это не для вас. В противном случае читайте readme.txt. |
|||
zapret не может пробить блокировку по IP адресу |
|||
Для проверки нескольких доменов вводите их через пробел. |
|||
|
|||
Сейчас блокираторы ставят на магистральных каналах. В сложных случаях у вас может быть несколько маршрутов |
|||
с различной длиной по ХОПам, с DPI на разных хопах. Приходится преодолевать целый зоопарк DPI, |
|||
которые еще и включаются в работу хаотичным образом или образом, зависящим от направления (IP сервера). |
|||
blockcheck не всегда может выдать вам в итогах оптимальную стратегию, которую надо просто переписать в настройки. |
|||
В некоторых случаях надо реально думать что происходит, анализируя результат на разных стратегиях. |
|||
Если вы применяете большой TTL, чтобы достать до магистрала, то не лишним будет добавить дополнительный ограничитель |
|||
--dpi-desync-fooling, чтобы не сломать сайты на более коротких дистанциях. |
|||
md5sig наиболее совместим, но работатет только на linux серверах. |
|||
badseq может работать только на https и не работать на http. |
|||
Чтобы выяснить какие дополнительные ограничители работают, смотрите результат теста аналогичных стратегий без TTL |
|||
с каждым из этих ограничителей. |
|||
|
|||
При использовании autottl следует протестировать как можно больше разных доменов. Эта техника |
|||
может на одних провайдерах работать стабильно, на других потребуется выяснить при каких параметрах |
|||
она стабильна, на третьих полный хаос, и проще отказаться. |
|||
|
|||
7) Протестируйте найденные стратегии на winws. winws следует брать из zapret-winws. |
|||
Для этого откройте командную строку windows от имени администратора в директории zapret-winws. |
|||
Проще всего это сделать через _CMD_ADMIN.cmd. Он сам поднимет права и зайдет в нужную директорию. |
|||
|
|||
8) Обеспечьте удобную загрузку обхода блокировок. |
|||
|
|||
Есть 2 варианта. Ручной запуск через ярлык или автоматический при старте системы, вне контекста текущего пользователя. |
|||
Последний вариант разделяется на запуск через планировщик задач и через службы windows. |
|||
|
|||
Если хотите ручной запуск, скопируйте preset_russia.cmd в preset_my.cmd и адаптируйте его под ваши параметра запуска. |
|||
Потом можно создать ярлык на рабочем столе на preset_my.cmd. Не забудьте, что требуется запускать от имени администратора. |
|||
|
|||
Но лучше будет сделать неинтерактивный автоматический запуск вместе с системой. |
|||
В zapret-winws есть командные файлы task_*, предназначенные для управления задачами планировщика. |
|||
Там следует поменять содержимое переменной WINWS1 на свою стратегию. |
|||
Если вы не можете обьединить несколько стратегий для разных протоколов в одну, дублируйте код в каждом из cmd |
|||
для поддержки нескольких задач : winws1,winws2,winws3. |
|||
После создания задач запустите их. Проверьте, что обход встает после перезагрузки windows. |
|||
|
|||
Аналогично настраиваются и службы windows. Смотрите service_*.cmd |
|||
|
|||
9) Если ломаются отдельные незаблокированные ресурсы, используйте хост-листы. |
|||
Где они будут находиться - решайте сами. |
|||
Параметры управления хост-листами точно такие же, как в *nix. |
|||
|
|||
Это минимальная инструкция, чтобы соориентироваться с чего начать. Однако, это - не панацея. |
|||
В некоторых случаях вы не обойдетесь без знаний и основного "толмуда". |
|||
Подробности и полное техническое описание расписаны в readme.txt |
|||
File diff suppressed because it is too large
File diff suppressed because it is too large
@ -0,0 +1,228 @@ |
|||
- [Введение](#введение) |
|||
- [Прозрачный выборочный заворот TCP соединений на роутере через SOCKS](#прозрачный-выборочный-заворот-tcp-соединений-на-роутере-через-socks) |
|||
- [Сделать так, чтобы все время при загрузке системы на некотором порту возникал SOCKS](#сделать-так-чтобы-все-время-при-загрузке-системы-на-некотором-порту-возникал-socks) |
|||
- [Организовать прозрачную соксификацию](#организовать-прозрачную-соксификацию) |
|||
- [Завертывание соединений через `iptables`](#завертывание-соединений-через-iptables) |
|||
- [Завертывание соединений через `nftables`](#завертывание-соединений-через-nftables) |
|||
- [Проверка](#проверка) |
|||
|
|||
# Введение |
|||
|
|||
Данный мануал пишется не как копипастная инструкция, а как помощь уже соображающему. |
|||
Если вы не знаете основ сетей, Linux, OpenWrt, а пытаетесь что-то скопипастить отсюда без малейшего понимания смысла, то маловероятно, что у вас что-то заработает. Не тратьте свое время напрасно. |
|||
Цель - донести принципы как это настраивается вообще, а не указать какую буковку где вписать. |
|||
|
|||
# Прозрачный выборочный заворот TCP соединений на роутере через SOCKS |
|||
|
|||
Tor поддерживает "из коробки" режим transparent proxy. Это можно использовать в теории, но практически - только на роутерах с 128 мб памяти и выше. И тор еще и тормозной. |
|||
Другой вариант напрашивается, если у вас есть доступ к какой-нибудь unix системе с SSH, где сайты не блокируются. |
|||
Например, у вас есть VPS вне России. Понятийно требуются следующие шаги: |
|||
|
|||
1) Выделять IP, на которые надо проксировать трафик. У нас уже имеется ipset `zapret`, технология создания которого отработана. |
|||
2) Сделать так, чтобы все время при загрузке системы на некотором порту возникал SOCKS. |
|||
3) Установить transparent соксификатор. Redsocks прекрасно подошел на эту роль. |
|||
4) Завернуть через `iptables` или `nftables` трафик с порта назначения 443 и на IP адреса из `ipset`/`nfset` `zapret` на соксификатор. |
|||
|
|||
Тоже самое сделать с `ipset`/`nfset` `ipban` для всех TCP портов. |
|||
Буду рассматривать систему на базе OpenWrt, где уже установлена система обхода DPI `zapret`. |
|||
Если вам не нужны функции обхода DPI, можно выбрать режим `MODE=filter`. |
|||
|
|||
## Сделать так, чтобы все время при загрузке системы на некотором порту возникал SOCKS |
|||
|
|||
Т.к. дефолтный `dropbear` клиент не поддерживает создание SOCKS, то для начала придется заменить `dropbear` SSH client на `OpenSSH`: пакеты `openssh-client` и `openssh-client-utils`. |
|||
Устанавливать их нужно с опцией `opkg --force-overwrite`, поскольку они перепишут SSH клиент от `dropbear`. |
|||
После установки пакетов расслабим неоправданно жестокие права: `chmod 755 /etc/ssh`. |
|||
Следует создать пользователя, под которым будем крутить SSH client. Допустим, это будет 'proxy'. |
|||
Сначала установить пакет `shadow-useradd`, потом: |
|||
|
|||
```sh |
|||
useradd -d /home/proxy proxy |
|||
mkdir -p /home/proxy |
|||
chown proxy:proxy /home/proxy |
|||
``` |
|||
|
|||
OpenSSH ловит разные глюки, если у него нет доступа к `/dev/tty`. |
|||
Добавим в `/etc/rc.local` строчку: `chmod 666 /dev/tty`. |
|||
Сгенерируем для него ключ RSA для доступа к SSH серверу: |
|||
|
|||
```sh |
|||
su proxy |
|||
cd |
|||
mkdir -m 700 .ssh |
|||
cd .ssh |
|||
ssh-keygen |
|||
ls |
|||
exit |
|||
``` |
|||
|
|||
Должны получиться файлы `id_rsa` и `id_rsa.pub`. |
|||
Строчку из `id_rsa.pub` следует добавить на SSH сервер в файл `$HOME/.ssh/authorized_keys`. |
|||
Более подробно о доступе к SSH через авторизацию по ключам [здесь](https://beget.com/ru/articles/ssh_by_key). |
|||
Предположим, ваш SSH сервер - vps.mydomain.com, пользователь называется `proxy`. |
|||
Проверить подключение можно так: `ssh -N -D 1098 -l proxy vps.mydomain.com`. |
|||
Сделайте это под пользователем `proxy`, поскольку при первом подключении SSH спросит о правильности hostkey. |
|||
Соединение может отвалиться в любой момент, поэтому нужно зациклить запуск SSH. |
|||
Для этого лучший вариант - использовать `procd` - упрощенная замена `systemd` на OpenWrt версий BB и выше. |
|||
|
|||
`/etc/init.d/socks_vps`: |
|||
|
|||
```sh |
|||
# !/bin/sh /etc/rc.common |
|||
START=50 |
|||
STOP=50 |
|||
USE_PROCD=1 |
|||
USERNAME=proxy |
|||
COMMAND="ssh -N -D 1098 -l proxy vps.mydomain.com" |
|||
start_service() { |
|||
procd_open_instance |
|||
procd_set_param user $USERNAME |
|||
procd_set_param respawn 10 10 0 |
|||
procd_set_param command $COMMAND |
|||
procd_close_instance |
|||
} |
|||
``` |
|||
|
|||
Этому файлу нужно дать права: `chmod +x /etc/init.d/socks_vps`. |
|||
Запуск: `/etc/init.d/socks_vps start`. |
|||
Останов: `/etc/init.d/socks_vps stop`. |
|||
Включить автозагрузку: `/etc/init.d/socks_vps enable`. |
|||
Проверка: `curl -4 --socks5 127.0.0.1:1098 https://rutracker.org`. |
|||
|
|||
## Организовать прозрачную соксификацию |
|||
|
|||
Установить пакет `redsocks`, прописать конфиг: |
|||
|
|||
`/etc/redsocks.conf`: |
|||
|
|||
``` |
|||
base { |
|||
log_debug = off; |
|||
log_info = on; |
|||
log = "syslog:local7"; |
|||
daemon = on; |
|||
user = nobody; |
|||
group = nogroup; |
|||
redirector = iptables; |
|||
} |
|||
redsocks { |
|||
local_ip = 127.0.0.127; |
|||
local_port = 1099; |
|||
ip = 127.0.0.1; |
|||
port = 1098; |
|||
type = socks5; |
|||
} |
|||
``` |
|||
|
|||
После чего перезапускаем: `/etc/init.d/redsocks restart`. |
|||
Смотрим появился ли листенер: `netstat -tnlp | grep 1099`. |
|||
|
|||
В `zapret` для перенаправления DNAT на интерфейс lo используется 127.0.0.127. |
|||
Ко всем остальным адресам из 127.0.0.0/8 DNAT может быть заблокирован. Читайте `readme.md` про `route_localnet`. |
|||
|
|||
## Завертывание соединений через `iptables` |
|||
|
|||
**ВНИМАНИЕ:** Версии OpenWrt до 21.02 включительно используют `iptables` + `fw3`. |
|||
Более новые перешили на `nftables` по умолчанию. |
|||
В новых OpenWrt можно снести `firewall4` и `nftables`, заменив их на `firewall3` + `iptables`. |
|||
Инструкция относится только к OpenWrt, где используется `iptables`. |
|||
|
|||
Будем завертывать любые TCP соединения на IP из ipset `ipban` и HTTPS на IP из ipset `zapret`, за исключением IP из ipset `nozapret`. |
|||
|
|||
`/etc/firewall.user`: |
|||
|
|||
```sh |
|||
SOXIFIER_PORT=1099 |
|||
|
|||
. /opt/zapret/init.d/openwrt/functions |
|||
|
|||
create_ipset no-update |
|||
|
|||
network_find_wan4_all wan_iface |
|||
for ext_iface in $wan_iface; do |
|||
network_get_device ext_device $ext_iface |
|||
ipt OUTPUT -t nat -o $ext_device -p tcp --dport 443 -m set --match-set zapret dst -m set ! --match-set nozapret dst -j REDIRECT --to-port $SOXIFIER_PORT |
|||
ipt OUTPUT -t nat -o $ext_device -p tcp -m set --match-set ipban dst -m set ! --match-set nozapret dst -j REDIRECT --to-port $SOXIFIER_PORT |
|||
done |
|||
|
|||
prepare_route_localnet |
|||
|
|||
ipt prerouting_lan_rule -t nat -p tcp --dport 443 -m set --match-set zapret dst -m set ! --match-set nozapret -j DNAT --to $TPWS_LOCALHOST4:$SOXIFIER_PORT |
|||
ipt prerouting_lan_rule -t nat -p tcp -m set --match-set ipban dst -m set ! --match-set nozapret -j DNAT --to $TPWS_LOCALHOST4:$SOXIFIER_PORT |
|||
``` |
|||
|
|||
Внести параметр "reload" в указанное место. `/etc/config/firewall`: |
|||
|
|||
``` |
|||
config include |
|||
option path '/etc/firewall.user' |
|||
option reload '1' |
|||
``` |
|||
|
|||
Перезапуск firewall: `/etc/init.d/firewall restart` |
|||
|
|||
## Завертывание соединений через `nftables` |
|||
|
|||
**ВНИМАНИЕ:** Только для версий OpenWrt старше 21.02. |
|||
|
|||
`nftables` не могут использовать ipset. Вместо `ipset` существует аналог - `nfset`. |
|||
`nfset` является частью таблицы nftable и принадлежит только к ней. Адресация `nfset` из другой nftable невозможна. |
|||
Скрипты `ipset/*` в случае `nftables` используют `nfset`-ы в таблице `zapret`. |
|||
Чтобы использовать эти `nfset`-ы в своих правилах, необходимо синхронизироваться с их созданием и вносить свои цепочки в nftable `zapret`. |
|||
Для этого существуют хуки - скрипты, вызываемые из `zapret` на определенных стадиях инициализации фаервола. |
|||
|
|||
Раскомментируйте в `/opt/zapret/config` строчку: |
|||
|
|||
```sh |
|||
INIT_FW_POST_UP_HOOK="/etc/firewall.zapret.hook.post_up" |
|||
``` |
|||
|
|||
Создайте файл `/etc/firewall.zapret.hook.post_up` и присвойте ему `chmod 755`: |
|||
|
|||
```sh |
|||
#!/bin/sh |
|||
|
|||
SOXIFIER_PORT=1099 |
|||
|
|||
. /opt/zapret/init.d/openwrt/functions |
|||
|
|||
cat << EOF | nft -f - 2>/dev/null |
|||
delete chain inet $ZAPRET_NFT_TABLE my_output |
|||
delete chain inet $ZAPRET_NFT_TABLE my_prerouting |
|||
EOF |
|||
|
|||
prepare_route_localnet |
|||
|
|||
cat << EOF | nft -f - |
|||
add chain inet $ZAPRET_NFT_TABLE my_output { type nat hook output priority -102; } |
|||
flush chain inet $ZAPRET_NFT_TABLE my_output |
|||
add rule inet $ZAPRET_NFT_TABLE my_output oifname @wanif meta l4proto tcp ip daddr @ipban ip daddr != @nozapret dnat to $TPWS_LOCALHOST4:$SOXIFIER_PORT |
|||
add rule inet $ZAPRET_NFT_TABLE my_output oifname @wanif tcp dport 443 ip daddr @zapret ip daddr != @nozapret dnat to $TPWS_LOCALHOST4:$SOXIFIER_PORT |
|||
|
|||
add chain inet $ZAPRET_NFT_TABLE my_prerouting { type nat hook prerouting priority -102; } |
|||
flush chain inet $ZAPRET_NFT_TABLE my_prerouting |
|||
add rule inet $ZAPRET_NFT_TABLE my_prerouting iifname @lanif meta l4proto tcp ip daddr @ipban ip daddr != @nozapret dnat to $TPWS_LOCALHOST4:$SOXIFIER_PORT |
|||
add rule inet $ZAPRET_NFT_TABLE my_prerouting iifname @lanif tcp dport 443 ip daddr @zapret ip daddr != @nozapret dnat to $TPWS_LOCALHOST4:$SOXIFIER_PORT |
|||
EOF |
|||
``` |
|||
|
|||
Перезапуск firewall: `/etc/init.d/zapret restart_fw` |
|||
|
|||
## Проверка |
|||
|
|||
Все, теперь можно проверять: |
|||
|
|||
```sh |
|||
/etc/init.d/redsocks stop |
|||
curl -4 https://rutracker.org |
|||
``` |
|||
|
|||
Должно обломаться с надписью "Connection refused". |
|||
Если не обламывается - значит IP адрес rutracker.org не в ipset, либо не сработали правила фаервола. |
|||
Например, из-за не установленных модулей `iptables`. |
|||
|
|||
```sh |
|||
/etc/init.d/redsocks start |
|||
curl -4 https://rutracker.org |
|||
``` |
|||
|
|||
Должно выдать страницу. |
|||
@ -1,196 +0,0 @@ |
|||
Данный мануал пишется не как копипастная инструкция, а как помощь уже соображающему. |
|||
Если вы не знаете основ сетей, linux, openwrt, а пытаетесь что-то скопипастить отсюда без малейшего |
|||
понимания смысла, то маловероятно, что у вас что-то заработает. Не тратье свое время напрасно. |
|||
Цель - донести принципы как это настраивается вообще, а не указать какую буковку где вписать. |
|||
|
|||
|
|||
Прозрачный выборочный заворот tcp соединений на роутере через socks |
|||
|
|||
Tor поддерживает "из коробки" режим transparent proxy. Это можно использовать в теории, но практически - только на роутерах с 128 мб памяти и выше. И тор еще и тормозной. |
|||
Другой вариант напрашивается, если у вас есть доступ к какой-нибудь unix системе с SSH, где сайты не блокируются. Например, у вас есть VPS вне России. |
|||
Понятийно требуются следующие шаги : |
|||
1) Выделять IP, на которые надо проксировать трафик. У нас уже имеется ipset "zapret", технология создания которого отработана. |
|||
2) Сделать так, чтобы все время при загрузке системы на некотором порту возникал socks. |
|||
3) Установить transparent соксификатор. Redsocks прекрасно подошел на эту роль. |
|||
4) Завернуть через iptables или nftables трафик с порта назначения 443 и на ip адреса из ipset/nfset 'zapret' на соксификатор |
|||
Тоже самое сделать с ipset/nfset 'ipban' для всех tcp портов. |
|||
Буду рассматривать систему на базе openwrt, где уже установлена система обхода dpi "zapret". |
|||
Если вам не нужны функции обхода DPI, можно выбрать режим MODE=filter. |
|||
|
|||
|
|||
* Сделать так, чтобы все время при загрузке системы на некотором порту возникал socks |
|||
|
|||
Т.к. дефолтный dropbear клиент не поддерживает создание socks, то для начала придется заменить dropbear ssh client на openssh : пакеты openssh-client и openssh-client-utils. |
|||
Устанавливать их нужно с опцией opkg --force-overwrite, поскольку они перепишут ssh клиент от dropbear. |
|||
После установки пакетов расслабим неоправданно жестокие права : chmod 755 /etc/ssh. |
|||
Следует создать пользователя, под которым будем крутить ssh client. Допустим, это будет 'proxy'. |
|||
Сначала установить пакет shadow-useradd. |
|||
------------------ |
|||
useradd -d /home/proxy proxy |
|||
mkdir -p /home/proxy |
|||
chown proxy:proxy /home/proxy |
|||
------------------ |
|||
Openssh ловит разные глюки, если у него нет доступа к /dev/tty. |
|||
Добавим в /etc/rc.local строчку : "chmod 666 /dev/tty" |
|||
Сгенерируем для него ключ RSA для доступа к ssh серверу. |
|||
------------------ |
|||
su proxy |
|||
cd |
|||
mkdir -m 700 .ssh |
|||
cd .ssh |
|||
ssh-keygen |
|||
ls |
|||
exit |
|||
------------------ |
|||
Должны получиться файлы id_rsa и id_rsa.pub. |
|||
Строчку из id_rsa.pub следует добавить на ssh сервер в файл $HOME/.ssh/authorized_keys. |
|||
Более подробно о доступе к ssh через авторизацию по ключам : https://beget.com/ru/articles/ssh_by_key |
|||
Предположим, ваш ssh сервер - vps.mydomain.com, пользователь называется 'proxy'. |
|||
Проверить подключение можно так : ssh -N -D 1098 -l proxy vps.mydomain.com. |
|||
Сделайте это под пользователем "proxy", поскольку при первом подключении ssh спросит о правильности hostkey. |
|||
Соединение может отвалиться в любой момент, поэтому нужно зациклить запуск ssh. |
|||
Для этого лучший вариант - использовать procd - упрощенная замена systemd на openwrt версий BB и выше. |
|||
--- /etc/init.d/socks_vps --- |
|||
#!/bin/sh /etc/rc.common |
|||
START=50 |
|||
STOP=50 |
|||
USE_PROCD=1 |
|||
USERNAME=proxy |
|||
COMMAND="ssh -N -D 1098 -l proxy vps.mydomain.com" |
|||
start_service() { |
|||
procd_open_instance |
|||
procd_set_param user $USERNAME |
|||
procd_set_param respawn 10 10 0 |
|||
procd_set_param command $COMMAND |
|||
procd_close_instance |
|||
} |
|||
----------------------------- |
|||
Этому файлу нужно дать права : chmod +x /etc/init.d/socks_vps |
|||
Запуск : /etc/init.d/socks_vps start |
|||
Останов : /etc/init.d/socks_vps stop |
|||
Включить автозагрузку : /etc/init.d/socks_vps enable |
|||
Проверка : curl -4 --socks5 127.0.0.1:1098 https://rutracker.org |
|||
|
|||
|
|||
* Организовать прозрачную соксификацию |
|||
|
|||
Установить пакет redsocks. |
|||
Конфиг : |
|||
-- /etc/redsocks.conf : --- |
|||
base { |
|||
log_debug = off; |
|||
log_info = on; |
|||
log = "syslog:local7"; |
|||
daemon = on; |
|||
user = nobody; |
|||
group = nogroup; |
|||
redirector = iptables; |
|||
} |
|||
redsocks { |
|||
local_ip = 127.0.0.127; |
|||
local_port = 1099; |
|||
ip = 127.0.0.1; |
|||
port = 1098; |
|||
type = socks5; |
|||
} |
|||
--------------------------- |
|||
|
|||
После чего перезапускаем : /etc/init.d/redsocks restart |
|||
Смотрим появился ли листенер : netstat -tnlp | grep 1099 |
|||
|
|||
В zapret для перенаправления DNAT на интерфейс lo используется 127.0.0.127. |
|||
Ко всем остальным адресам из 127.0.0.0/8 DNAT может быть заблокирован. Читайте readme.txt про route_localnet. |
|||
|
|||
* Завертывание соединений через iptables |
|||
|
|||
!! Версии OpenWRT до 21.02 включительно используют iptables + fw3. Более новые перешили на nftables по умолчанию. |
|||
!! В новых OpenWRT можно снести firewall4 и nftables, заменив их на firewall3 + iptables |
|||
!! Инструкция относится только к openwrt, где используется iptables. |
|||
|
|||
Будем завертывать любые tcp соединения на ip из ipset "ipban" и https на ip из ipset "zapret", за исключением ip из ipset "nozapret". |
|||
|
|||
--- /etc/firewall.user ----- |
|||
SOXIFIER_PORT=1099 |
|||
|
|||
. /opt/zapret/init.d/openwrt/functions |
|||
|
|||
create_ipset no-update |
|||
|
|||
network_find_wan4_all wan_iface |
|||
for ext_iface in $wan_iface; do |
|||
network_get_device ext_device $ext_iface |
|||
ipt OUTPUT -t nat -o $ext_device -p tcp --dport 443 -m set --match-set zapret dst -m set ! --match-set nozapret dst -j REDIRECT --to-port $SOXIFIER_PORT |
|||
ipt OUTPUT -t nat -o $ext_device -p tcp -m set --match-set ipban dst -m set ! --match-set nozapret dst -j REDIRECT --to-port $SOXIFIER_PORT |
|||
done |
|||
|
|||
prepare_route_localnet |
|||
|
|||
ipt prerouting_lan_rule -t nat -p tcp --dport 443 -m set --match-set zapret dst -m set ! --match-set nozapret -j DNAT --to $TPWS_LOCALHOST4:$SOXIFIER_PORT |
|||
ipt prerouting_lan_rule -t nat -p tcp -m set --match-set ipban dst -m set ! --match-set nozapret -j DNAT --to $TPWS_LOCALHOST4:$SOXIFIER_PORT |
|||
---------------------------- |
|||
|
|||
Внести параметр "reload" в указанное место : |
|||
--- /etc/config/firewall --- |
|||
config include |
|||
option path '/etc/firewall.user' |
|||
option reload '1' |
|||
---------------------------- |
|||
|
|||
Перезапуск firewall : /etc/init.d/firewall restart |
|||
|
|||
|
|||
* Завертывание соединений через nftables |
|||
|
|||
!! Только для версий OpenWRT старше 21.02 |
|||
|
|||
nftables не могут использовать ipset. Вместо ipset существует аналог - nfset. |
|||
nfset является частью таблицы nftable и принадлежит только к ней. Адресация nfset из другой nftable невозможна. |
|||
Скрипты ipset/* в случае nftables используют nfset-ы в таблице zapret. |
|||
Чтобы использовать эти nfset-ы в своих правилах, необходимо синхронизироваться с их созданием и вносить свои цепочки в nftable "zapret". |
|||
Для этого существуют хуки - скрипты, вызываемые из zapret на определенных стадиях инициализации фаервола. |
|||
|
|||
Раскоментируейте в /opt/zapret/config строчку |
|||
INIT_FW_POST_UP_HOOK="/etc/firewall.zapret.hook.post_up" |
|||
|
|||
Создайте файл /etc/firewall.zapret.hook.post_up и присвойте ему chmod 755. |
|||
|
|||
--- /etc/firewall.zapret.hook.post_up --- |
|||
#!/bin/sh |
|||
|
|||
SOXIFIER_PORT=1099 |
|||
|
|||
. /opt/zapret/init.d/openwrt/functions |
|||
|
|||
cat << EOF | nft -f - 2>/dev/null |
|||
delete chain inet $ZAPRET_NFT_TABLE my_output |
|||
delete chain inet $ZAPRET_NFT_TABLE my_prerouting |
|||
EOF |
|||
|
|||
prepare_route_localnet |
|||
|
|||
cat << EOF | nft -f - |
|||
add chain inet $ZAPRET_NFT_TABLE my_output { type nat hook output priority -102; } |
|||
flush chain inet $ZAPRET_NFT_TABLE my_output |
|||
add rule inet $ZAPRET_NFT_TABLE my_output oifname @wanif meta l4proto tcp ip daddr @ipban ip daddr != @nozapret dnat to $TPWS_LOCALHOST4:$SOXIFIER_PORT |
|||
add rule inet $ZAPRET_NFT_TABLE my_output oifname @wanif tcp dport 443 ip daddr @zapret ip daddr != @nozapret dnat to $TPWS_LOCALHOST4:$SOXIFIER_PORT |
|||
|
|||
add chain inet $ZAPRET_NFT_TABLE my_prerouting { type nat hook prerouting priority -102; } |
|||
flush chain inet $ZAPRET_NFT_TABLE my_prerouting |
|||
add rule inet $ZAPRET_NFT_TABLE my_prerouting iifname @lanif meta l4proto tcp ip daddr @ipban ip daddr != @nozapret dnat to $TPWS_LOCALHOST4:$SOXIFIER_PORT |
|||
add rule inet $ZAPRET_NFT_TABLE my_prerouting iifname @lanif tcp dport 443 ip daddr @zapret ip daddr != @nozapret dnat to $TPWS_LOCALHOST4:$SOXIFIER_PORT |
|||
EOF |
|||
---------------------------- |
|||
|
|||
Перезапуск firewall : /etc/init.d/zapret restart_fw |
|||
|
|||
|
|||
* Проверка |
|||
|
|||
Все, теперь можно проверять : |
|||
/etc/init.d/redsocks stop |
|||
curl -4 https://rutracker.org |
|||
# должно обломаться с надписью "Connection refused". если не обламывается - значит ip адрес rutracker.org не в ipset, |
|||
# либо не сработали правила фаервола. например, из-за не установленных модулей ipt |
|||
/etc/init.d/redsocks start |
|||
curl -4 https://rutracker.org |
|||
# должно выдать страницу |
|||
@ -0,0 +1,229 @@ |
|||
- [`tpws`](#tpws) |
|||
- [`winws`](#winws) |
|||
- [Windows 7 и `windivert`](#windows-7-и-windivert) |
|||
- [`blockcheck`](#blockcheck) |
|||
- [Автозапуск `winws`](#автозапуск-winws) |
|||
- [`zapret-win-bundle`](#zapret-win-bundle) |
|||
|
|||
## `tpws` |
|||
|
|||
Запуск `tpws` возможен только в Linux варианте под WSL. |
|||
Нативного варианта под Windows нет, поскольку он использует epoll, которого под Windows не существует. |
|||
|
|||
`tpws` в режиме SOCKS можно запускать под более-менее современными билдами Windows 10 и Windows Server |
|||
с установленным WSL. Совсем не обязательно устанавливать дистрибутив Ubuntu, как вам напишут почти в каждой |
|||
статье про WSL, которую вы найдете в сети. `tpws` - статический бинарник, ему дистрибутив не нужен. |
|||
|
|||
Установить WSL: `dism.exe /online /enable-feature /featurename:Microsoft-Windows-Subsystem-Linux /all` |
|||
|
|||
Скопировать на целевую систему: `binaries/x86_64/tpws_wsl.tgz`. |
|||
|
|||
Выполнить: `wsl --import tpws "%USERPROFILE%\tpws" tpws_wsl.tgz` |
|||
|
|||
Запустить: `wsl -d tpws --exec /tpws --uid=1 --no-resolve --socks --bind-addr=127.0.0.1 --port=1080 <параметры_дурения>` |
|||
|
|||
Прописать SOCKS `127.0.0.1:1080` в броузер или другую программу. |
|||
|
|||
Удаление: `wsl --unregister tpws` |
|||
|
|||
Проверено на Windows 10 build 19041 (20.04). |
|||
|
|||
Не работают функции `--oob` и `--mss` из-за ограничений реализации WSL. |
|||
`--disorder` не работает из-за особенностей TCP/IP стека Windows. |
|||
Может не срабатывать детект RST в `autohostlist`. |
|||
WSL может глючить со `splice`, приводя к зацикливанию процесса. Может потребоваться `--nosplice`. |
|||
Не поддерживается TCP user timeout. |
|||
Чтобы избавиться от сообщений об ошибке, добавляйте `--local-tcp-user-timeout=0 --remote-tcp-user-timeout=0`. |
|||
Эти сообщения только информативные, на работу они не влияют. |
|||
|
|||
## `winws` |
|||
|
|||
Это вариант пакетного фильтра `nfqws` для Windows, построенный на базе `windivert`. |
|||
Все функции работоспособны, однако функционал `ipset` отсутствует. Фильтры по большому количеству IP адресов невозможны. |
|||
Работа с проходящим трафиком, например в случае "расшаривания" соединения, не проверялась и не гарантируется. |
|||
Для работы с `windivert` требуются права администратора. |
|||
Специфические для unix параметры, такие как `--uid`, `--user` и т.д., исключены. Все остальные параметры аналогичны `nfqws` и `dvtws`. |
|||
|
|||
Работа с пакетным фильтром основана на двух действиях. |
|||
|
|||
1) Выделение перенаправляемого трафика в режиме ядра и передача его пакетному фильтру в user mode. |
|||
2) Собственно обработка перенаправленных пакетов в пакетном фильтре. |
|||
|
|||
В Windows отсутствуют встроенные средства для перенаправления трафика, такие как `iptables`, `nftables`, `pf` или `ipfw`. |
|||
Поэтому используется сторонний драйвер ядра `windivert`. Он работает, начиная с Windows 7. На системах с включенным |
|||
Secure Boot могут быть проблемы из-за подписи драйвера. В этом случае отключите Secure Boot или включите режим testsigning. |
|||
На Windows 7 вероятно будут проблемы с загрузкой `windivert`. Читайте ниже соответствующий раздел. |
|||
|
|||
Задача `iptables` в `winws` решается внутренними средствами через фильтры `windivert`. |
|||
У `windivert` существует собственный язык фильтров, похожий на язык фильтров wireshark. |
|||
Документация по фильтрам `windivert` [здесь](https://reqrypt.org/windivert-doc.html#filter_language). |
|||
Чтобы не писать сложные фильтры вручную, предусмотрены различные упрощенные варианты автоматического построения фильтров. |
|||
|
|||
``` |
|||
--wf-iface=<int>[.<int>] ; числовые индексы интерфейса и суб-интерфейса |
|||
--wf-l3=ipv4|ipv6 ; фильтр L3 протоколов. по умолчанию включены IPv4 и IPv6. |
|||
--wf-tcp=[~]port1[-port2] ; фильтр портов для TCP. ~ означает отрицание |
|||
--wf-udp=[~]port1[-port2] ; фильтр портов для UDP. ~ означает отрицание |
|||
--wf-raw=<filter>|@<filename> ; задать напрямую фильтр windivert из параметра или из файла. имени файла предшествует символ @. |
|||
--wf-save=<filename> ; сохранить сконструированный фильтр windivert в файл для последующей правки вручную |
|||
--ssid-filter=ssid1[,ssid2,ssid3,...] ; включать winws только когда подключена любая из указанных Wi-Fi сетей |
|||
--nlm-filter=net1[,net2,net3,...] ; включать winws только когда подключена любая из указанных сетей NLM |
|||
--nlm-list[=all] ; вывести список сетей NLM. по умолчанию только подключенных, all - всех. |
|||
``` |
|||
|
|||
Параметры `--wf-l3`, `--wf-tcp`, `--wf-udp` могут брать несколько значений через запятую. |
|||
|
|||
Номера интерфейсов можно узнать так: `netsh int ip show int`. |
|||
Некоторых типы соединений там не увидеть. В этом случае запускайте `winws` с параметром `--debug` и смотрите `IfIdx` там. |
|||
`SubInterface` используется `windivert`, но практически всегда 0, его можно не указывать. Вероятно он нужен в редких случаях. |
|||
|
|||
Конструктор фильтров автоматически включает входящие TCP пакеты с TCP SYNACK и TCP RST для корректной работы функций |
|||
`autottl` и `autohostlist`. При включении `autohostlist` так же перенаправляются пакеты данных с HTTP redirect с кодами 302 и 307. |
|||
Всегда добавляется фильтр на исключение не-интернет адресов IPv4 и IPv6. |
|||
Для сложных нестандартных сценариев могут потребоваться свои фильтры. Логично будет начать со стандартного шаблона, |
|||
сохраненного через `--wf-save`. Нужно править файл и подсовывать его в параметре `--wf-raw`. Максимальный размер фильтра - 8 Kb. |
|||
|
|||
Можно запускать несколько процессов `winws` с разными стратегиями. Однако, не следует делать пересекающиеся фильтры. |
|||
|
|||
В `--ssid-filter` можно через запятую задать неограниченное количество имен Wi-Fi сетей (SSID). Если задана хотя бы одна сеть, |
|||
то `winws` включается только, если подключен указанный SSID. Если SSID исчезает, `winws` отключается. Если SSID появляется снова, |
|||
`winws` включается. Это нужно, чтобы можно было применять раздельное дурение к каждой отдельной Wi-Fi сети. |
|||
Названия сетей должны быть написаны в том регистре, в котором их видит система. Сравнение идет с учетом регистра! |
|||
При этом нет никаких проверок того, куда реально идет трафик. Если одновременно подключен, допустим, Ethernet, |
|||
и трафик идет туда, то дурение включается и выключается просто по факту наличия Wi-Fi сети, на которую трафик может и не идти. |
|||
И это может сломать дурение на Ethernet. Поэтому полезно так же будет добавить фильтр `--wf-iface` на индекс интерфейса Wi-Fi адаптера, |
|||
чтобы не трогать другой трафик. |
|||
|
|||
`--nlm-filter` аналогичен `--ssid-filter`, но работает с именами или GUIDами сетей Network List Manager (NLM). |
|||
Это те сети, которые вы видите в панели управления в разделе "Центр управления сетями и общим доступом". |
|||
Под сетью подразумевается не конкретный адаптер, а именно сетевое окружение конкретного подключения. |
|||
Обычно проверяется MAC адрес шлюза. К сети можно подключиться через любой адаптер, и она останется той же самой. |
|||
Если подключиться, допустим, к разными роутерам по кабелю, то будут разные сети. |
|||
А если к одному роутеру через 2 разных сетевых карточки на том же компе - будет одна сеть. |
|||
NLM абстрагирует типы сетевых адаптеров. Он работает как с Wi-Fi, так и с Ethernet и любыми другими. |
|||
Поэтому это более универсальный метод, чем SSID фильтр. |
|||
Однако, есть и неприятная сторона. В Windows 7 вы легко могли ткнуть на иконку сети и выбрать тип: private или public. |
|||
Там же вы могли посмотреть список сетей и объединить их. Чтобы, допустим, вы могли подключаться по кабелю и Wi-Fi |
|||
к одному роутеру, и система эти подключения воспринимала как одну сеть. |
|||
В следующих версиях Windows они эти возможности сильно порезали. Похоже нет встроенных средств полноценно управлять |
|||
network locations в Windows 10/11. Кое-что есть в `powershell`. |
|||
Можно поковыряться напрямую в реестре здесь: `HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows NT\CurrentVersion\NetworkList` |
|||
Нужно менять `ProfileGUID` в `Signatures\Unmanaged`. Имена можно поменять в Profiles. |
|||
Есть кое-какие сторонние утилиты. Кое-что находится, позволяющее посмотреть и удалить network profiles, но не объединить. |
|||
Факт, что в ms они это сильно испортили. Движок network list все тот же, и он способен на все то, что было в Windows 7. |
|||
Можно не бороться с этой проблемой, а просто указывать через запятую те названия сетей или GUIDы, которые выбрала система. |
|||
Или если у вас только Wi-Fi, то использовать `--ssid-filter`. Там хотя бы есть гарантия, что SSID соответствуют реальности, |
|||
а система их не назвала как-то по-своему. |
|||
|
|||
Если в путях присутствуют национальные символы, то при вызове `winws` из `cmd` или `bat` кодировку нужно использовать OEM. |
|||
Для русского языка это 866. Пути с пробелами нужно брать в кавычки. |
|||
|
|||
Существует неочевидный момент, касающийся запуска `winws` из `cygwin` шелла. Если в директории, где находится `nfqws`, находится |
|||
копия `cygwin1.dll`, `winws` не запустится. Поэтому в `binaries/win64` существует директория zapret-winws, содержащая полный |
|||
комплект для запуска без `cygwin`. Его вы и берете для повседневного использования. |
|||
Если нужен запуск под `cygwin`, то следует запускать из `binaries/win64`. Это нужно для работы `blockcheck`. |
|||
Из `cygwin` шелла можно посылать `winws` сигналы через `kill` точно так же, как в *nix. |
|||
|
|||
Как получить совместимый с Windows 7 и winws `cygwin`: |
|||
|
|||
```powershell |
|||
curl -O https://www.cygwin.com/setup-x86_64.exe |
|||
setup-x86_64.exe --allow-unsupported-windows --no-verify --site http://ctm.crouchingtigerhiddenfruitbat.org/pub/cygwin/circa/64bit/2024/01/30/231215 |
|||
``` |
|||
|
|||
Следует выбрать установку `curl`. |
|||
|
|||
Для сборки из исходников требуется `gcc-core`, `make`, `zlib-devel`. |
|||
Собирать из директории `nfq` командой `make cygwin`. |
|||
`winws` требует `cygwin1.dll`, `windivert.dll`, `windivert64.sys`. Их можно взять из `binaries/win64/zapret-winws`. |
|||
Версию для 32-битных x86 Windows собрать можно, но такие системы уже уходят в прошлое, поэтому если надо - собирайте сами. |
|||
32-битный `windivert` можно взять с сайта разработчика. Требуется версия 2.2.2. |
|||
|
|||
Для ARM64 Windows нет подписанного драйвера `windivert` и нет `cygwin`. |
|||
Однако, эмуляция x64 Windows 11 позволяет использовать все, кроме `WinDivert64.sys` без изменений. |
|||
Но при этом надо заменить `WinDivert64.sys` на неподписанную ARM64 версию и установить режим testsigning. |
|||
|
|||
## Windows 7 и `windivert` |
|||
|
|||
Требования к подписи драйверов Windows изменились в 2021 году. |
|||
Официальные бесплатные обновления Windows 7 закончились в 2020. |
|||
После этого несколько лет продолжали идти платные обновления по программе ESU. |
|||
Именно в этих ESU обновлениях находится обновление ядра Windows 7, позволяющее загрузить драйвер |
|||
`windivert 2.2.2-A`, который идет в поставке zapret. |
|||
Поэтому варианты следующие: |
|||
|
|||
1) Взять `windivert64.sys` и `windivert.dll` версии 2.2.0-C или 2.2.0-D [отсюда](https://reqrypt.org/download) |
|||
и заменить эти 2 файла. |
|||
В `zapret-win-bundle` есть отдельных 2 места, где находится `winws`: `zapret-winws` и `blockcheck/zapret/nfq`. |
|||
Надо менять в обоих местах. |
|||
Этот вариант проверен и должен работать. Тем не менее патч 10 летней давности, который включает SHA256 |
|||
сигнатуры, все еще необходим. |
|||
|
|||
2) Взломать ESU: [раз](https://hackandpwn.com/windows-7-esu-patching/), [два](http://www.bifido.net/tweaks-and-scripts/8-extended-security-updates-installer.html), и обновить систему |
|||
|
|||
3) Использовать UpdatePack7R2 от [simplix](https://blog.simplix.info). |
|||
Но с этим паком есть проблема. Автор из Украины, он очень обиделся на русских. |
|||
Если в панели управления стоит регион RU или BY, появляется неприятный диалог. |
|||
Чтобы эту проблему обойти, можно поставить временно любой другой регион, потом вернуть. |
|||
Так же нет никаких гарантий, что автор не насовал туда какой-то зловредный код. |
|||
Использовать на свой страх и риск. |
|||
Более безопасный вариант - скачать последнюю нормальную довоенную версию: [22.2.10](https://nnmclub.to/forum/viewtopic.php?t=1530323). |
|||
Ее достаточно, чтобы windivert 2.2.2-A заработал на Windows 7. |
|||
|
|||
## `blockcheck` |
|||
|
|||
`blockcheck.sh` написан на posix shell и требует некоторых стандартных утилит posix. В Windows, естественно, этого нет. |
|||
Потому просто так запустить `blockcheck.sh` невозможно. |
|||
Для этого требуется скачать и установить `cygwin` так, как описано в предыдущем разделе. |
|||
Следует запустить от имени администратора cygwin shell через `cygwin.bat`. |
|||
В нем нужно пройти в директорию с `zapret`. |
|||
Обратные слэши путей Windows нужно удваивать, менять на прямые слэши, либо использовать отображение на unix path. |
|||
|
|||
- Корректный вариант 1: `cd "C:\\Users\\vasya"` |
|||
- Корректный вариант 2: `cd "C:/Users/vasya"` |
|||
- Корректный вариант 3: `cd "/cygdrive/c/Users/vasya"` |
|||
|
|||
Далее все как в *nix: 1 раз `./install_bin.sh`, затем `./blockcheck.sh`. |
|||
WSL использовать нельзя, это не то же самое. |
|||
|
|||
`cygwin` для обычной работы `winws` не нужен. Разве что вы хотите посылать `winws` SIGHUP для перечитки листов без перезапуска. |
|||
|
|||
## Автозапуск `winws` |
|||
|
|||
Для запуска `winws` вместе с Windows есть 2 варианта. Планировщик задач или службы Windows. |
|||
|
|||
Можно создавать задачи и управлять ими через консольную программу `schtasks`. |
|||
В директории `binaries/win64/winws` подготовлены файлы `task_*.cmd`. |
|||
В них реализовано создание, удаление, старт и стоп одной копии процесса `winws` с параметрами из переменной `%WINWS1%`. |
|||
Исправьте параметры на нужную вам стратегию. Если для разных фильтров применяется разная стратегия, размножьте код |
|||
для задач `winws1`, `winws2`, `winws3`,... |
|||
|
|||
Аналогично настраивается вариант запуска через службы Windows. Смотрите `service_*.cmd`. |
|||
Все батники требуется запускать от имени администратора. |
|||
Управлять задачами можно так же из графической программы управления планировщиком `taskschd.msc`. |
|||
|
|||
## `zapret-win-bundle` |
|||
|
|||
Можно не возиться с `cygwin`, а взять [готовый пакет](https://github.com/bol-van/zapret-win-bundle), включающий в себя `cygwin` и `blockcheck`. |
|||
Там сделан максимум удобств для сосредоточения на самом `zapret`, исключая возню с установкой `cygwin`, |
|||
заходами в директории, запусками под администратором и прочими сугубо техническими моментами, в которых могут быть |
|||
ошибки и непонимания, а новичок без базиса знаний может и вовсе запутаться. |
|||
|
|||
- `/zapret-winws` - здесь все, что нужно для запуска `winws` в повседневном рабочем режиме. остальное не нужно. |
|||
- `/zapret-winws/_CMD_ADMIN.cmd` - получить командную строку `cmd` в этой директории от имени администратора для тестирования `winws` с параметрами, вводимыми вручную |
|||
- `/blockcheck/blockcheck.cmd` - достаточно кликнуть по нему, чтобы пошел `blockcheck` с записью лога в `blockcheck/blockcheck.log` |
|||
- `/cygwin/cygwin.cmd` - запуск среды `cygwin bash` под текущим пользователем |
|||
- `/cygwin/cygwin-admin.cmd` - запуск среды `cygwin bash` под администратором |
|||
|
|||
В среде `cygwin` уже настроены alias-ы на `winws`, `blockcheck`, `ip2net`, `mdig`. С путями возиться не нужно! |
|||
Из `cygwin` можно не только тестировать `winws`, но и посылать сигналы. |
|||
Доступны команды `pidof`, `kill`, `killall`, `pgrep`, `pkill`. |
|||
Но важно понимать, что таким образом не выйдет посылать сигналы `winws`, запущенному из `zapret-winws`, |
|||
поскольку там свой `cygwin1.dll`, и они не разделяют общее пространство процессов unix. |
|||
`zapret-winws` - это отдельный комплект для повседневного использования, не требующий что-то еще, но и не связанный со средой `cygwin`. |
|||
|
|||
Среду `cygwin` можно использовать для записи в файл дебаг-лога `winws`. Для этого пользуйтесь командой `tee`: |
|||
`winws --debug --wf-tcp=80,443 | tee winws.log` |
|||
|
|||
`winws.log` будет в `cygwin/home/<имя_пользователя>` |
|||
Если у вас Windows 7, то блокнот не поймет переводы строк в стиле unix. Воспользуйтесь командой: `unix2dos winws.log` |
|||
@ -1,222 +0,0 @@ |
|||
tpws |
|||
---- |
|||
|
|||
Запуск tpws возможен только в Linux варианте под WSL. |
|||
Нативного варианта под Windows нет, поскольку он использует epoll, которого под windows не существует. |
|||
|
|||
tpws в режиме socks можно запускать под более-менее современными билдами windows 10 и windows server |
|||
с установленным WSL. Совсем не обязательно устанавливать дистрибутив убунту, как вам напишут почти в каждой |
|||
статье про WSL, которую вы найдете в сети. tpws - статический бинарик, ему дистрибутив не нужен. |
|||
|
|||
Установить WSL : dism.exe /online /enable-feature /featurename:Microsoft-Windows-Subsystem-Linux /all |
|||
Скопировать на целевую систему binaries/x86_64/tpws_wsl.tgz. |
|||
Выполнить : wsl --import tpws "%USERPROFILE%\tpws" tpws_wsl.tgz |
|||
Запустить : wsl -d tpws --exec /tpws --uid=1 --no-resolve --socks --bind-addr=127.0.0.1 --port=1080 <параметры_дурения> |
|||
Прописать socks 127.0.0.1:1080 в броузер или другую программу. |
|||
|
|||
Удаление : wsl --unregister tpws |
|||
|
|||
Проверено на windows 10 build 19041 (20.04). |
|||
|
|||
Не работают функции --oob и --mss из-за ограничений реализации WSL. |
|||
--disorder не работает из-за особенностей tcp/ip стека windows. |
|||
Может не срабатывать детект RST в autohostlist. |
|||
WSL может глючить со splice, приводя к зацикливанию процесса. Может потребоваться --nosplice. |
|||
Не поддерживается tcp user timeout. |
|||
Чтобы избавиться от исообщений об ошибке добавляйте "--local-tcp-user-timeout=0 --remote-tcp-user-timeout=0". |
|||
Эти сообщения только информативные, на работу они не влияют. |
|||
|
|||
|
|||
winws |
|||
----- |
|||
|
|||
Это вариант пакетного фильтра nfqws для Windows, построенный на базе windivert. |
|||
Все функции работоспособны, однако функционал ipset отсутствует. Фильтры по большому количеству IP адресов невозможны. |
|||
Работа с проходящим трафиком, например в случае "расшаривания" соединения, не проверялась и не гарантируется. |
|||
Для работы с windivert требуются права администратора. |
|||
Специфические для unix параметры, такие как --uid, --user и тд, исключены. Все остальные параметры аналогичны nfqws и dvtws. |
|||
|
|||
Работа с пакетным фильтром основана на двух действиях. |
|||
Первое - выделение перенаправляемого трафика в режиме ядра и передача его пакетному фильтру в user mode. |
|||
Второе - собственно обработка перенаправленных пакетов в пакетном фильтре. |
|||
|
|||
В windows отсутствуют встроенные средства для перенаправления трафика, такие как iptables, nftables, pf или ipfw. |
|||
Поэтому используется сторонний драйвер ядра windivert. Он работает, начиная с windows 7. На системах с включенным |
|||
secure boot могут быть проблемы из-за подписи драйвера. В этом случае отключите secureboot или включите режим testsigning. |
|||
На windows 7 вероятно будут проблемы с загрузкой windivert. Читайте ниже соответствующий раздел. |
|||
|
|||
Задача iptables в winws решается внутренними средствами через фильтры windivert. |
|||
У windivert существует собственный язык фильтров, похожий на язык фильтров wireshark. |
|||
Документация по фильтрам windivert : https://reqrypt.org/windivert-doc.html#filter_language |
|||
Чтобы не писать сложные фильтры вручную, предусмотрены различные упрощенные варианты автоматического построения фильтров. |
|||
|
|||
--wf-iface=<int>[.<int>] ; числовые индексы интерфейса и суб-интерфейса |
|||
--wf-l3=ipv4|ipv6 ; фильтр L3 протоколов. по умолчанию включены ipv4 и ipv6. |
|||
--wf-tcp=[~]port1[-port2] ; фильтр портов для tcp. ~ означает отрицание |
|||
--wf-udp=[~]port1[-port2] ; фильтр портов для udp. ~ означает отрицание |
|||
--wf-raw=<filter>|@<filename> ; задать напрямую фильтр windivert из параметра или из файла. имени файла предшествует символ @. |
|||
--wf-save=<filename> ; сохранить сконструированный фильтр windivert в файл для последующей правки вручную |
|||
--ssid-filter=ssid1[,ssid2,ssid3,...] ; включать winws только когда подключена любая из указанных wifi сетей |
|||
--nlm-filter=net1[,net2,net3,...] ; включать winws только когда подключена любая из указанных сетей NLM |
|||
--nlm-list[=all] ; вывести список сетей NLM. по умолчанию только подключенных, all - всех. |
|||
Параметры --wf-l3, --wf-tcp, --wf-udp могут брать несколько значений через запятую. |
|||
|
|||
Номера интерфейсов можно узнать так : netsh int ip show int. |
|||
Некоторых типы соединений там не увидеть. В этом случае запускайте winws с параметром --debug и смотрите IfIdx там. |
|||
SubInterface используется windivert, но практически всегда 0, его можно не указывать. Вероятно он нужен в редких случаях. |
|||
|
|||
Конструктор фильтров автоматически включает входящие tcp пакеты с tcp synack и tcp rst для корректной работы функций |
|||
autottl и autohostlist. При включении autohostlist так же перенаправляются пакеты данных с http redirect с кодами 302 и 307. |
|||
Всегда добавляется фильтр на исключение не-интернет адресов ipv4 и ipv6. |
|||
Для сложных нестандартных сценариев могут потребоваться свои фильтры. Логично будет начать со стандартного шаблона, |
|||
сохраненного через --wf-save. Нужно править файл и подсовывать его в параметре --wf-raw. Максимальный размер фильтра - 8 Kb. |
|||
|
|||
Можно запускать несколько процессов winws с разными стратегиями. Однако, не следует делать пересекающиеся фильтры. |
|||
|
|||
В --ssid-filter можно через запятую задать неограниченное количество имен wifi сетей (SSID). Если задана хотя бы одна сеть, |
|||
то winws включается только, если подключен указанный SSID. Если SSID исчезает, winws отключается. Если SSID появляется снова, |
|||
winws включается. Это нужно, чтобы можно было применять раздельное дурение к каждой отдельной wifi сети. |
|||
Названия сетей должны быть написаны в том регистре, в котором их видит система. Сравнение идет с учетом регистра ! |
|||
При этом нет никаких проверок куда реально идет трафик. Если одновременно подключен, допустим, ethernet, |
|||
и трафик идет туда, то дурение включается и выключается просто по факту наличия wifi сети, на которую трафик может и не идти. |
|||
И это может сломать дурение на ethernet. Поэтому полезно так же будет добавить фильтр --wf-iface на индекс интерфейса wifi адаптера, |
|||
чтобы не трогать другой трафик. |
|||
|
|||
--nlm-filter аналогичен --ssid-filter, но работает с именами или GUIDами сетей Network List Manager (NLM). |
|||
Это те сети, которые вы видите в панели управления в разделе "Центр управления сетями и общим доступом". |
|||
Под сетью подразумевается не конкретный адаптер, а именно сетевое окружение конкретного подключения. |
|||
Обычно проверяется mac адрес шлюза. К сети можно подключиться через любой адаптер, и она останется той же самой. |
|||
Если подключиться, допустим, к разными роутерам по кабелю, то будут разные сети. |
|||
А если к одному роутеру через 2 разных сетевых карточки на том же компе - будет одна сеть. |
|||
NLM абстрагирует типы сетевых адаптеров. Он работает как с wifi, так и с ethernet и любыми другими. |
|||
Поэтому это более универсальный метод, чем ssid фильтр. |
|||
Однако, есть и неприятная сторона. В windows 7 вы легко могли ткнуть на иконку сети и выбрать тип : private или public. |
|||
Там же вы могли посмотреть список сетей и обьединить их. Чтобы, допустим, вы могли подключаться по кабелю и wifi |
|||
к одному роутеру, и система эти подключения воспринимала как одну сеть. |
|||
В следующих версиях windows они эти возможности сильно порезали. Похоже нет встроенных средств полноценно управлять |
|||
network locations в win10/11. Кое-что есть в powershell. |
|||
Можно поковыряться напрямую в реестре здесь : HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows NT\CurrentVersion\NetworkList |
|||
Нужно менять ProfileGUID в Signatures\Unmanaged. Имена можно поменять в Profiles. |
|||
Есть кое-какие сторонние утилиты. Кое-что находится, позволяющее посмотреть и удалить network profiles, но не обьединить. |
|||
Факт, что в ms они это сильно испортили. Движок network list все тот же, и он способен на все то, что было в win7. |
|||
Можно не бороться с этой проблемой, а просто указывать через запятую те названия сетей или GUIDы, которые выбрала система. |
|||
Или если у вас только wifi, то использовать --ssid-filter. Там хотя бы есть гарантия, что SSID соответствуют реальности, |
|||
а система их не назвала как-то по-своему. |
|||
|
|||
Если в путях присутствуют национальные символы, то при вызове winws из cmd или bat кодировку нужно использовать OEM. |
|||
Для русского языка это 866. Пути с пробелами нужно брать в кавычки. |
|||
|
|||
Существует неочевидный момент, каcаемый запуска winws из cygwin шелла. Если в директории, где находится nfqws, находится |
|||
копия cygwin1.dll, winws не запустится. Поэтому в binaries/win64 существует директория zapret-winws, содержащая полный |
|||
комплект для запуска без cygwin. Его вы и берете для повседневного использования. |
|||
Если нужен запуск под cygwin, то следует запускать из binaries/win64. Это нужно для работы blockcheck. |
|||
Из cygwin шелла можно посылать winws сигналы через kill точно так же, как в *nix. |
|||
|
|||
Как получить совместимый с windows 7 и winws cygwin : |
|||
curl -O https://www.cygwin.com/setup-x86_64.exe |
|||
setup-x86_64.exe --allow-unsupported-windows --no-verify --site http://ctm.crouchingtigerhiddenfruitbat.org/pub/cygwin/circa/64bit/2024/01/30/231215 |
|||
Следует выбрать установку curl. |
|||
|
|||
Для сборки из исходников требуется gcc-core,make,zlib-devel. |
|||
Собирать из директории nfq командой "make cygwin". |
|||
winws требует cygwin1.dll, windivert.dll, windivert64.sys. Их можно взять из binaries/win64/zapret-winws. |
|||
Версию для 32-битных x86 windows собрать можно, но такие системы уже уходят в прошлое, поэтому если надо - собирайте сами. |
|||
32-битный windivert можно взять с сайта разработчика. Требуется версия 2.2.2. |
|||
|
|||
Для arm64 windows нет подписанного драйвера windivert и нет cygwin. |
|||
Однако, эмуляция x64 windows 11 позволяет использовать все, кроме WinDivert64.sys без изменений. |
|||
Но при этом надо заменить WinDivert64.sys на неподписанную arm64 версию и установить режим testsigning. |
|||
|
|||
Windows 7 и windivert |
|||
--------------------- |
|||
|
|||
Требования к подписи драйверов windows изменились в 2021 году. |
|||
Официальные бесплатные обновления windows 7 закончились в 2020. |
|||
После этого несколько лет продолжали идти платные обновления по программе ESU. |
|||
Именно в этих ESU обновлениях находится обновление ядра windows 7, позволяющиее загрузить драйвер |
|||
windivert 2.2.2-A, который идет в поставке zapret. |
|||
Поэтому варианты следующие : |
|||
|
|||
1) Взять windivert64.sys и windivert.dll версии 2.2.0-C или 2.2.0-D отсюда : https://reqrypt.org/download |
|||
и заменить эти 2 файла. |
|||
В zapret-win-bundle есть отдельных 2 места, где находится winws : zapret-winws и blockcheck/zapret/nfq. |
|||
Надо менять в обоих местах. |
|||
Этот вариант проверен и должен работать. Тем не менее патч 10 летней давности, который включает SHA256 |
|||
сигнатуры, все еще необходим. |
|||
|
|||
2) Взломать ESU : |
|||
https://hackandpwn.com/windows-7-esu-patching/ |
|||
http://www.bifido.net/tweaks-and-scripts/8-extended-security-updates-installer.html |
|||
и обновить систему |
|||
|
|||
3) Использовать UpdatePack7R2 от simplix : https://blog.simplix.info |
|||
Но с этим паком есть проблема. Автор из Украины, он очень обиделся на русских. |
|||
Если в панели управления стоит регион RU или BY, появляется неприятный диалог. |
|||
Чтобы эту проблему обойти, можно поставить временно любой другой регион, потом вернуть. |
|||
Так же нет никаких гарантий, что автор не насовал туда какой-то зловредный код. |
|||
Использовать на свой страх и риск. |
|||
Более безопасный вариант - скачать последнюю нормальную довоенную версию : 22.2.10 |
|||
https://nnmclub.to/forum/viewtopic.php?t=1530323 |
|||
Ее достаточно, чтобы windivert 2.2.2-A заработал на windows 7. |
|||
|
|||
blockcheck |
|||
---------- |
|||
|
|||
blockcheck.sh написан на posix shell и требует некоторых стандартных утилит posix. В windows, естественно, этого нет. |
|||
Потому просто так запустить blockcheck.sh невозможно. |
|||
Для этого требуется скачать и установить cygwin так , как описано в предыдущем разделе. |
|||
Следует запустить от имени администратора cygwin shell через cygwin.bat. |
|||
В нем нужно пройти в директорию с zapret. |
|||
Обратные слэши путей windows нужно удваивать, менять на прямые слэши, либо использовать отображение на unix path. |
|||
Корректный вариант 1 : cd "C:\\Users\\vasya" |
|||
Корректный вариант 2 : cd "C:/Users/vasya" |
|||
Корректный вариант 3 : cd "/cygdrive/c/Users/vasya" |
|||
Далее все как в *nix : 1 раз ./install_bin.sh , затем ./blockcheck.sh. |
|||
WSL использовать нельзя, это не то же самое. |
|||
|
|||
cygwin для обычной работы winws не нужен. Разве что вы хотите посылать winws SIGHUP для перечитки листов без перезапуска. |
|||
|
|||
автозапуск winws |
|||
---------------- |
|||
|
|||
Для запуска winws вместе с windows есть 2 варианта. Планировщик задач или службы windows. |
|||
|
|||
Можно создавать задачи и управлять ими через консольную программу schtasks. |
|||
В директории binaries/win64/winws подготовлены файлы task_*.cmd . |
|||
В них реализовано создание, удаление, старт и стоп одной копии процесса winws с параметрами из переменной %WINWS1%. |
|||
Исправьте параметры на нужную вам стратегию. Если для разных фильтров применяется разная стратегия, размножьте код |
|||
для задач winws1,winws2,winws3,... |
|||
|
|||
Аналогично настраивается вариант запуска через службы windows. Смотрите service_*.cmd. |
|||
|
|||
Все батники требуется запускать от имени администратора. |
|||
|
|||
Управлять задачами можно так же из графической программы управления планировщиком taskschd.msc |
|||
|
|||
zapret-win-bundle |
|||
----------------- |
|||
|
|||
Можно не возиться с cygwin, а взять готовый пакет, включающий в себя cygwin и blockcheck : https://github.com/bol-van/zapret-win-bundle |
|||
Там сделан максимум удобств для сосредоточения на самом zapret, исключая возню с установкой cygwin, |
|||
заходами в директории, запусками под администратором и прочими сугубо техническими моментами, в которых могут быть |
|||
ошибки и непонимания, а новичок без базиса знаний может и вовсе запутаться. |
|||
|
|||
/zapret-winws - здесь все, что нужно для запуска winws в повседневном рабочем режиме. остальное не нужно. |
|||
/zapret-winws/_CMD_ADMIN.cmd - получить командную строку cmd в этой директории от имени администратора для тестирования winws |
|||
с параметрами, вводимыми вручную |
|||
/blockcheck/blockcheck.cmd - достаточно кликнуть по нему, чтобы пошел blockcheck с записью лога в blockcheck/blockcheck.log |
|||
/cygwin/cygwin.cmd - запуск среды cygwin bash под текущим пользователем |
|||
/cygwin/cygwin-admin.cmd - запуск среды cygwin bash под администратором |
|||
|
|||
В среде cygwin уже настроены alias-ы на winws,blockcheck,ip2net,mdig. С путями возиться не нужно ! |
|||
Из cygwin можно не только тестировать winws, но и посылать сигналы. |
|||
Доступны команды pidof,kill,killall,pgrep,pkill. |
|||
Но важно понимать, что таким образом не выйдет посылать сигналы winws, запущенному из zapret-winws, |
|||
поскольку там свой cygwin1.dll, и они не разделяют общее пространство процессов unix. |
|||
zapret-winws - это отдельный комплект для повседневного использования, не требующий что-то еще, но и не связанный со средой cygwin. |
|||
|
|||
Среду cygwin можно использовать для записи в файл дебаг-лога winws. Для этого пользуйтесь командой tee. |
|||
winws --debug --wf-tcp=80,443 | tee winws.log |
|||
winws.log будет в cygwin/home/<имя_пользователя> |
|||
Если у вас windows 7, то блокнот не поймет переводы строк в стиле unix. Воспользуйтесь командой |
|||
unix2dos winws.log |
|||
@ -0,0 +1,296 @@ |
|||
# Важное замечание |
|||
|
|||
Эта инструкция написана еще до включения WireGuard в ядро Linux. |
|||
Процесс сборки для in-tree модулей отличается. |
|||
Цель данного чтива - дать идею для программистов как можно исправить исходники WireGuard для преодоления DPI. |
|||
Автор не преследует цели поддерживать готовые патчи для актуальных версий. |
|||
Вместо патчинга гораздо проще использовать навесное решение ipobfs. |
|||
|
|||
# Патчинг |
|||
|
|||
Посвящено возможной блокировке в РФ VPN протоколов через DPI. |
|||
Предпосылками являются последние законодательные акты и во всю сочащиеся "секретные" записки. |
|||
В РФ разрабатываются и готовятся к применению более продвинутые решения по блокировке трафика. |
|||
Вполне вероятно, будут резать стандартные VPN протоколы. Нам надо быть к этому готовыми. |
|||
|
|||
Один из возможных и перспективных путей решения данного вопроса - кастомная модификация исходников VPN с целью незначительного изменения протокола, ломающего стандартные модули обнаружения в DPI. |
|||
Это относительно сложно, доступно только для гиков. |
|||
Никто не будет разрабатывать специальные модули обнаружения в DPI, если только кто-то не сделает простое и удобное решение для всех, и его станут широко применять. |
|||
Но это маловероятно, и даже если и так, то всегда можно модифицировать протокол чуток по другому. |
|||
Делать моды для DPI несравненно дольше и дороже, чем клепать на коленке изменения протокола для WireGuard. |
|||
|
|||
**ЗАМЕЧАНИЕ:** альтернативой модификации конечного софта для VPN является использование "навесных" обфускаторов, см. [одно из решений](https://github.com/bol-van/ipobfs). |
|||
|
|||
Рассмотрю, что нам надо пропатчить в WireGuard. |
|||
Модифицированный WireGuard проверен на виртуалках с десктопным Linux, он работает, сообщения в wireshark действительно не вписываются в стандартный протокол и не опознаются. |
|||
|
|||
WireGuard протокол очень простой. Все сообщения описаны в `messages.h`. Поставим себе целью сделать 2 простые модификации: |
|||
|
|||
1) Добавим в начало всех сообщений немного мусора, чтобы изменить размер сообщений и смещения полей |
|||
2) Изменим коды типов сообщений |
|||
|
|||
Этого может быть вполне достаточно для обмана DPI: |
|||
|
|||
`messages.h`: |
|||
|
|||
```h |
|||
/* |
|||
enum message_type { |
|||
MESSAGE_INVALID = 0, |
|||
MESSAGE_HANDSHAKE_INITIATION = 1, |
|||
MESSAGE_HANDSHAKE_RESPONSE = 2, |
|||
MESSAGE_HANDSHAKE_COOKIE = 3, |
|||
MESSAGE_DATA = 4 |
|||
}; |
|||
*/ |
|||
|
|||
// MOD: message type |
|||
enum message_type { |
|||
MESSAGE_INVALID = 0xE319CCD0, |
|||
MESSAGE_HANDSHAKE_INITIATION = 0x48ADE198, |
|||
MESSAGE_HANDSHAKE_RESPONSE = 0xFCA6A8F3, |
|||
MESSAGE_HANDSHAKE_COOKIE = 0x64A3BB18, |
|||
MESSAGE_DATA = 0x391820AA |
|||
}; |
|||
|
|||
// MOD: generate fast trash without true RNG |
|||
__le32 gen_trash(void); |
|||
|
|||
struct message_header { |
|||
/* The actual layout of this that we want is: |
|||
* u8 type |
|||
* u8 reserved_zero[3] |
|||
* |
|||
* But it turns out that by encoding this as little endian, |
|||
* we achieve the same thing, and it makes checking faster. |
|||
*/ |
|||
|
|||
// MOD: trash field to change message size and add 4 byte offset to all fields |
|||
__le32 trash; |
|||
|
|||
__le32 type; |
|||
}; |
|||
``` |
|||
|
|||
Напишем функцию для генерации `trash`. Функция должна быть быстрая, важно не замедлить скорость. |
|||
Мы не рассчитываем, что нас будут специально ловить, иначе бы пришлось делать полноценный обфускатор. |
|||
Задача лишь сломать стандартный модуль обнаружения протокола WireGuard. Потому истинная рандомность `trash` не важна. |
|||
Но все же немного "трэша" не повредит. Гонки между тредами так же пофигистичны. Это же трэш. |
|||
|
|||
`noise.c`: |
|||
|
|||
```c |
|||
// MOD: trash generator |
|||
__le32 gtrash = 0; |
|||
__le32 gen_trash(void) |
|||
{ |
|||
if (gtrash) |
|||
gtrash = gtrash*1103515243 + 12345; |
|||
else |
|||
// first value is true random |
|||
get_random_bytes_wait(>rash, sizeof(gtrash)); |
|||
return gtrash; |
|||
} |
|||
``` |
|||
|
|||
Теперь осталось найти все места, где создаются сообщения и внести туда заполнение поля `trash`. |
|||
Сообщений всего 4. Их можно найти по присваиванию полю type одного из значений enum message_type. |
|||
|
|||
* 2 места в `noise.c` в функциях `wg_noise_handshake_create_initiation` и `wg_noise_handshake_create_response`, |
|||
* 1 место в `cookie.c` в функции `wg_cookie_message_create`. |
|||
|
|||
Дописываем в конец инициализации структуры сообщения : |
|||
|
|||
```c |
|||
// MOD: randomize trash |
|||
dst->header.trash = gen_trash() |
|||
``` |
|||
|
|||
И в 1 место в `send.c` в функции `encrypt_packet`: |
|||
|
|||
```c |
|||
// MOD: randomize trash |
|||
header->header.trash = gen_trash() |
|||
``` |
|||
|
|||
Вот и весь патчинг. Полный patch (версия `wireguard 0.0.20190123`) лежит в `010-wg-mod.patch`. |
|||
Патчинг кода - самое простое. Для десктопного Linux дальше все просто. |
|||
Пересобираем через `make`, устанавливаем через `make install`, перегружаем модуль `wireguard`, перезапускаем интерфейсы, и все готово. |
|||
|
|||
# Установка и запуск |
|||
|
|||
Настоящий геморрой начнется, когда вы это попытаетесь засунуть на роутер под OpenWrt. |
|||
Одна из больших проблем Linux - отсутствие совместимости драйверов на уровне бинарников. |
|||
Поэтому собирать необходимо в точности под вашу версию ядра и в точности под его `.config`. |
|||
Вам придется либо полностью самостоятельно собирать всю прошивку, либо найти SDK в точности от вашей версии прошивки для вашей архитектуры и собрать модуль с помощью этого SDK. |
|||
Последний вариант более легкий. Для сборки вам понадобится система на Linux x86_64. Ее можно установить в виртуалке. |
|||
Теоретически можно пользоваться WSL из Windows 10, но на практике там очень медленное I/O, по крайней мере на старых версиях Windows 10. Безумно медленное. Будете собирать вечность. |
|||
Может в новых Windows 10 что-то и улучшили, но я бы сразу рассчитывал на полноценный Linux. |
|||
|
|||
Находим [здесь](https://downloads.openwrt.org/) вашу версию. Скачиваем файл `openwrt-sdk-*.tar.xz` или `lede-sdk-*.tar.xz`. |
|||
Например: [https://downloads.openwrt.org/releases/18.06.2/targets/ar71xx/generic/openwrt-sdk-18.06.2-ar71xx-generic_gcc-7.3.0_musl.Linux-x86_64.tar.xz](https://downloads.openwrt.org/releases/18.06.2/targets/ar71xx/generic/openwrt-sdk-18.06.2-ar71xx-generic_gcc-7.3.0_musl.Linux-x86_64.tar.xz). |
|||
Если ваша версия непонятна или стара, то проще будет найти последнюю прошивку и перешить роутер. |
|||
Распаковываем SDK. Следующими командами можно собрать оригинальный вариант WireGuard: |
|||
|
|||
```sh |
|||
scripts/feeds update -a |
|||
scripts/feeds install -a |
|||
make defconfig |
|||
make -j 4 package/wireguard/compile |
|||
``` |
|||
|
|||
Сборка будет довольно долгой. Ведь придется подтащить ядро, собрать его, собрать зависимости. |
|||
`-j 4` означает использовать 4 потока. Впишите вместо 4 количество доступных CPU cores. |
|||
|
|||
Получим следующие файлы: |
|||
|
|||
``` |
|||
openwrt-sdk-18.06.2-ar71xx-generic_gcc-7.3.0_musl.Linux-x86_64/bin/targets/ar71xx/generic/packages/kmod-wireguard_4.9.152+0.0.20190123-1_mips_24kc.ipk |
|||
openwrt-sdk-18.06.2-ar71xx-generic_gcc-7.3.0_musl.Linux-x86_64/bin/packages/mips_24kc/base/wireguard-tools_0.0.20190123-1_mips_24kc.ipk |
|||
``` |
|||
|
|||
Но это будет оригинальный `wireguard`. Нам нужен патченный. |
|||
Установим `quilt` и `mc` для нормального редактора вместо `vim`: |
|||
|
|||
```sh |
|||
sudo apt-get update |
|||
sudo apt-get install quilt mc |
|||
make package/wireguard/clean |
|||
make package/wireguard/prepare V=s QUILT=1 |
|||
``` |
|||
|
|||
Сорцы приготовлены для сборки в: |
|||
|
|||
``` |
|||
openwrt-sdk-18.06.2-ar71xx-generic_gcc-7.3.0_musl.Linux-x86_64/build_dir/target-mips_24kc_musl/linux-ar71xx_generic/WireGuard-0.0.20190123/src |
|||
``` |
|||
|
|||
```sh |
|||
cd build_dir/target-mips_24kc_musl/linux-ar71xx_generic/WireGuard-0.0.20190123/src |
|||
quilt push -a |
|||
quilt new 010-wg-mod.patch |
|||
export EDITOR=mcedit |
|||
``` |
|||
|
|||
Далее будет открываться редактор `mcedit`, в который нужно вносить изменения в каждый файл : |
|||
|
|||
```sh |
|||
quilt edit messages.h |
|||
quilt edit cookie.c |
|||
quilt edit noise.c |
|||
quilt edit send.c |
|||
quilt diff |
|||
quilt refresh |
|||
``` |
|||
|
|||
Получили файл патча в: |
|||
|
|||
``` |
|||
openwrt-sdk-18.06.2-ar71xx-generic_gcc-7.3.0_musl.Linux-x86_64/build_dir/target-mips_24kc_musl/linux-ar71xx_generic/WireGuard-0.0.20190123/patches/010-wg-mod.patch |
|||
``` |
|||
|
|||
Выходим в корень SDK и выполняем: |
|||
|
|||
```sh |
|||
make package/wireguard/compile V=99 |
|||
``` |
|||
|
|||
Если не было ошибок, то получили измененные ipk. |
|||
Патч можно зафиксировать в описании пакета: |
|||
|
|||
```sh |
|||
make package/wireguard/update |
|||
``` |
|||
|
|||
Получим: |
|||
|
|||
``` |
|||
openwrt-sdk-18.06.2-ar71xx-generic_gcc-7.3.0_musl.Linux-x86_64/feeds/base/package/network/services/wireguard/patches/010-wg-mod.patch |
|||
``` |
|||
|
|||
При последующей очистке и пересборке он будет автоматом применяться. |
|||
|
|||
**АЛЬТЕРНАТИВА:** можно не возиться с quilt. Сделайте: |
|||
|
|||
```sh |
|||
make package/wireguard/clean |
|||
make package/wireguard/prepare |
|||
``` |
|||
|
|||
и напрямую модифицируйте или копируйте файлы в: |
|||
|
|||
``` |
|||
openwrt-sdk-18.06.2-ar71xx-generic_gcc-7.3.0_musl.Linux-x86_64/build_dir/target-mips_24kc_musl/linux-ar71xx_generic/WireGuard-0.0.20190123/src |
|||
``` |
|||
|
|||
затем: |
|||
|
|||
```sh |
|||
make package/wireguard/compile |
|||
``` |
|||
|
|||
Если нужно поменять версию WireGuard, то идите в |
|||
|
|||
``` |
|||
openwrt-sdk-18.06.2-ar71xx-generic_gcc-7.3.0_musl.Linux-x86_64/feeds/base/package/network/services/wireguard/Makefile |
|||
``` |
|||
|
|||
поменяйте там версию в `PKG_VERSION` на последнюю [отсюда](https://git.zx2c4.com/WireGuard), скачайте `tar.xz` с этой версией, вычислите его `sha256sum`, впишите в `PKG_HASH`. |
|||
|
|||
1 раз где-нибудь пропатчите файлы последней версии WireGuard в текстовом редакторе, скопируйте в `build_dir`, |
|||
сделайте версию для OpenWrt. эти же файлы скопируйте на ваш сервер с десктопным Linux, сделайте там `make` / `make install` |
|||
|
|||
Но имейте в виду, что `build_dir` - локация для временных файлов. |
|||
`make clean` оттуда все снесет, включая ваши модификации. |
|||
Модифицированные файлы лучше сохранить отдельно, чтобы потом было легко скопировать обратно. |
|||
|
|||
Полученные `.ipk` копируем на роутер в `/tmp`, устанавливаем так: |
|||
|
|||
```sh |
|||
cd /tmp |
|||
rm -r /tmp/opkg-lists |
|||
opkg install *.ipk |
|||
``` |
|||
|
|||
Если требует зависимостей, то: |
|||
|
|||
```sh |
|||
opkg update |
|||
opkg install <зависимости> |
|||
rm -r /tmp/opkg-lists |
|||
opkg install *.ipk |
|||
``` |
|||
|
|||
В `/tmp/opkg-lists` `opkg` хранит кэш списка пакетов. |
|||
Если попытаться установить файл `.ipk`, и такой же пакет найдется в репозитории, opkg будет устанавливать из репозитория. |
|||
А нам это не надо. |
|||
|
|||
```sh |
|||
rmmod wireguard |
|||
kmodloader |
|||
dmesg | tail |
|||
``` |
|||
|
|||
должны увидеть что-то вроде: |
|||
|
|||
``` |
|||
[8985.415490] wireguard: WireGuard 0.0.20190123 loaded. See <www.wireguard.com> for information. |
|||
[8985.424178] wireguard: Copyright (C) 2015-2019 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved. |
|||
``` |
|||
|
|||
значит, модуль загрузился. |
|||
|
|||
Могут понадобиться ключи `opkg` `--force-reinstall`, `--force-depends`. |
|||
`--force-depends` поможет при несоответствии hash версии ядра. То есть версия x.x.x та же самая, но hash конфигурации разный. |
|||
При несоответствии x.x.x вы что-то делаете не так, работать это не будет. |
|||
Например: `4.14.56-1-b1186491495127cc6ff81d29c00a91fc`, `4.14.56-1-3f8a21a63974cfb7ee67e41f2d4b805d` |
|||
Это свидетельствует о несоответствии `.config` ядра при сборке прошивки и в SDK. |
|||
Если несоответствие легкое, то может все прокатить, но при более серьезной разнице в `.config` модуль может не загрузиться или вызвать стабильные или хаотические падения ядра и перезагрузки (включая вариант бесконечной перезагрузки - bootloop). |
|||
Так что перед `--force-depends` убедитесь, что знаете как лечится такая ситуация, и не стоит это делать при отсутствии физического |
|||
доступа к девайсу. |
|||
|
|||
Когда поднимите линк, и вдруг ничего не будет работать, то посмотрите в wireshark UDP пакеты на порт endpoint. |
|||
Они не должны начинаться с 0,1,2,3,4. В первых 4 байтах должен быть рандом, в следующих 4 байтах - значения из измененного enum message_type. |
|||
Если пакет все еще начинается с 0..4, значит, модуль `wireguard` оригинальный, что-то не собралось, не скомпилировалось, не перезапустилось. |
|||
В противном случае должен подняться линк, пинги ходить. Значит вы победили, поздравляю. |
|||
Регулятору будет намного сложнее поймать ваш VPN. |
|||
@ -1,250 +0,0 @@ |
|||
!!! Эта инструкция написана еще до включения wireguard в ядро linux. |
|||
!!! Процесс сборки для in-tree модулей отличается. |
|||
!!! Цель данного чтива - дать идею для программистов как можно исправить исходники wireguard |
|||
!!! для преодоления DPI. Автор не преследует цели поддерживать готовые патчи для актуальных версий. |
|||
!!! Вместо патчинга гораздо проще использовать навесное решение ipobfs. |
|||
|
|||
Посвящено возможной блокировке в РФ VPN протоколов через DPI. |
|||
Предпосылками являются последние законодательные акты и во всю сочащиеся "секретные" записки. |
|||
В РФ разрабатываются и готовятся к применению более продвинутые решения по блокировке трафика. |
|||
Вполне вероятно будут резать стандартные VPN протоколы. Нам надо быть к этому готовыми. |
|||
|
|||
Один из возможных и перспективных путей решения данного вопроса - кустомная модификация |
|||
исходников VPN с целью незначительного изменения протокола, ломающего стандартные модули обнаружения в DPI. |
|||
Это относительно сложно, доступно только для гиков. |
|||
Никто не будет разрабатывать специальные модули обнаружения в DPI, если только кто-то не сделает простое и |
|||
удобное решение для всех, и его станут широко применять. Но это маловероятно, и даже если и так, |
|||
то всегда можно модифицировать протокол чуток по другому. Делать моды для DPI несравненно дольше |
|||
и дороже, чем клепать на коленке изменения протокола для wireguard. |
|||
|
|||
|
|||
ЗАМЕЧЕНИЕ : альтернативой модификации конечного софта для VPN является использование "навесных" |
|||
обфускаторов. см : https://github.com/bol-van/ipobfs |
|||
|
|||
|
|||
Рассмотрю что нам надо пропатчить в wireguard. Модифицированный wireguard проверен на виртуалках |
|||
с десктопным linux, он работает, сообщения в wireshark действительно не вписываются в стандартный |
|||
протокол и не опознаются. |
|||
|
|||
Wireguard протокол очень простой. Все сообщения описаны в messages.h |
|||
Поставим себе целью сделать 2 простые модификации : |
|||
1) Добавим в начало всех сообщений немного мусора, чтобы изменить размер сообщений и смещения полей |
|||
2) Изменим коды типов сообщений |
|||
Этого может быть вполне достаточно для обмана DPI |
|||
|
|||
--messages.h-------------------------- |
|||
/* |
|||
enum message_type { |
|||
MESSAGE_INVALID = 0, |
|||
MESSAGE_HANDSHAKE_INITIATION = 1, |
|||
MESSAGE_HANDSHAKE_RESPONSE = 2, |
|||
MESSAGE_HANDSHAKE_COOKIE = 3, |
|||
MESSAGE_DATA = 4 |
|||
}; |
|||
*/ |
|||
|
|||
// MOD : message type |
|||
enum message_type { |
|||
MESSAGE_INVALID = 0xE319CCD0, |
|||
MESSAGE_HANDSHAKE_INITIATION = 0x48ADE198, |
|||
MESSAGE_HANDSHAKE_RESPONSE = 0xFCA6A8F3, |
|||
MESSAGE_HANDSHAKE_COOKIE = 0x64A3BB18, |
|||
MESSAGE_DATA = 0x391820AA |
|||
}; |
|||
|
|||
// MOD : generate fast trash without true RNG |
|||
__le32 gen_trash(void); |
|||
|
|||
struct message_header { |
|||
/* The actual layout of this that we want is: |
|||
* u8 type |
|||
* u8 reserved_zero[3] |
|||
* |
|||
* But it turns out that by encoding this as little endian, |
|||
* we achieve the same thing, and it makes checking faster. |
|||
*/ |
|||
|
|||
// MOD : trash field to change message size and add 4 byte offset to all fields |
|||
__le32 trash; |
|||
|
|||
__le32 type; |
|||
}; |
|||
-------------------------------------- |
|||
|
|||
Напишем функцию для генерации trash. Функция должна быть быстрая, важно не замедлить скорость. |
|||
Мы не расчитываем, что нас будут специально ловить, иначе бы пришлось делать полноценный обфускатор. |
|||
Задача лишь сломать стандартный модуль обнаружения протокола wireguard. Потому истинная рандомность |
|||
trash не важна. |
|||
Но все же немного "трэша" не повредит. Гонки между тредами так же пофигистичны. Это же трэш. |
|||
|
|||
--noise.c----------------------------- |
|||
// MOD : trash generator |
|||
__le32 gtrash = 0; |
|||
__le32 gen_trash(void) |
|||
{ |
|||
if (gtrash) |
|||
gtrash = gtrash*1103515243 + 12345; |
|||
else |
|||
// first value is true random |
|||
get_random_bytes_wait(>rash, sizeof(gtrash)); |
|||
return gtrash; |
|||
} |
|||
-------------------------------------- |
|||
|
|||
Теперь осталось найти все места, где создаются сообщения и внести туда заполнение поля trash. |
|||
Сообщений всего 4. Их можно найти по присваиванию полю type одного из значений enum message_type. |
|||
|
|||
2 места в noise.c в функциях wg_noise_handshake_create_initiation и wg_noise_handshake_create_response, |
|||
1 место в cookie.c в функции wg_cookie_message_create |
|||
Дописываем в конец инициализации структуры сообщения : |
|||
|
|||
-------------------------------------- |
|||
// MOD : randomize trash |
|||
dst->header.trash = gen_trash(); |
|||
-------------------------------------- |
|||
|
|||
и 1 место в send.c в функции encrypt_packet |
|||
|
|||
-------------------------------------- |
|||
// MOD : randomize trash |
|||
header->header.trash = gen_trash(); |
|||
-------------------------------------- |
|||
|
|||
|
|||
Вот и весь патчинг. Полный patch (версия wireguard 0.0.20190123) лежит в 010-wg-mod.patch. |
|||
Патчинг кода - самое простое. Для десктопного linux дальше все просто. |
|||
Пересобираем через make, устанавливаем через make install, перегружаем |
|||
модуль wireguard, перезапускаем интерфейсы, и все готово. |
|||
|
|||
Настоящий геморой начнется когда вы это попытаетесь засунуть на роутер под openwrt. |
|||
Одна из больших проблем linux - отсутствие совместимости драйверов на уровне бинариков. |
|||
Поэтому собирать необходимо в точности под вашу версию ядра и в точности под его .config. |
|||
Вам придется либо полностью самостоятельно собирать всю прошивку, либо найти SDK в точности |
|||
от вашей версии прошивки для вашей архитектуры и собрать модуль с помощью этого SDK. |
|||
Последний вариант более легкий. |
|||
Для сборки вам понадобится система на linux x86_64. Ее можно установить в виртуалке. |
|||
Теоретически можно пользоваться WSL из win10, но на практике там очень медленное I/O, |
|||
по крайней мере на старых версиях win10. Безумно медленное. Будете собирать вечность. |
|||
Может в новых win10 что-то и улучшили, но я бы сразу расчитывал на полноценный linux. |
|||
|
|||
Находим здесь вашу версию : https://downloads.openwrt.org/ |
|||
Скачиваем файл openwrt-sdk-*.tar.xz или lede-sdk-*.tar.xz |
|||
Например : https://downloads.openwrt.org/releases/18.06.2/targets/ar71xx/generic/openwrt-sdk-18.06.2-ar71xx-generic_gcc-7.3.0_musl.Linux-x86_64.tar.xz |
|||
Если ваша версия непонятна или стара, то проще будет найти последнюю прошивку и перешить роутер. |
|||
Распаковываем SDK. Следующими командами можно собрать оригинальный вариант wireguard : |
|||
|
|||
# scripts/feeds update -a |
|||
# scripts/feeds install -a |
|||
# make defconfig |
|||
# make -j 4 package/wireguard/compile |
|||
|
|||
Сборка будет довольно долгой. Ведь придется подтащить ядро, собрать его, собрать зависимости. |
|||
"-j 4" означает использовать 4 потока. Впишите вместо 4 количество доступных cpu cores. |
|||
|
|||
Получим следующие файлы : |
|||
|
|||
openwrt-sdk-18.06.2-ar71xx-generic_gcc-7.3.0_musl.Linux-x86_64/bin/targets/ar71xx/generic/packages/kmod-wireguard_4.9.152+0.0.20190123-1_mips_24kc.ipk |
|||
openwrt-sdk-18.06.2-ar71xx-generic_gcc-7.3.0_musl.Linux-x86_64/bin/packages/mips_24kc/base/wireguard-tools_0.0.20190123-1_mips_24kc.ipk |
|||
|
|||
Но это будет оригинальный wireguard. Нам нужен патченый. |
|||
Установим quilt и mc для нормального редактора вместо vim : |
|||
|
|||
# sudo apt-get update |
|||
# sudo apt-get install quilt mc |
|||
|
|||
# make package/wireguard/clean |
|||
# make package/wireguard/prepare V=s QUILT=1 |
|||
|
|||
|
|||
Сорцы приготовлены для сборки в : |
|||
openwrt-sdk-18.06.2-ar71xx-generic_gcc-7.3.0_musl.Linux-x86_64/build_dir/target-mips_24kc_musl/linux-ar71xx_generic/WireGuard-0.0.20190123/src |
|||
|
|||
# cd build_dir/target-mips_24kc_musl/linux-ar71xx_generic/WireGuard-0.0.20190123/src |
|||
# quilt push -a |
|||
# quilt new 010-wg-mod.patch |
|||
# export EDITOR=mcedit |
|||
|
|||
Далее будет открываться редактор mcedit, в который нужно вносить изменения в каждый файл : |
|||
|
|||
# quilt edit messages.h |
|||
# quilt edit cookie.c |
|||
# quilt edit noise.c |
|||
# quilt edit send.c |
|||
# quilt diff |
|||
# quilt refresh |
|||
|
|||
Получили файл патча в : |
|||
openwrt-sdk-18.06.2-ar71xx-generic_gcc-7.3.0_musl.Linux-x86_64/build_dir/target-mips_24kc_musl/linux-ar71xx_generic/WireGuard-0.0.20190123/patches/010-wg-mod.patch |
|||
|
|||
Выходим в корень SDK. |
|||
|
|||
# make package/wireguard/compile V=99 |
|||
|
|||
Если не было ошибок, то получили измененные ipk. |
|||
Патч можно зафиксировать в описании пакета : |
|||
|
|||
# make package/wireguard/update |
|||
|
|||
Получим : |
|||
openwrt-sdk-18.06.2-ar71xx-generic_gcc-7.3.0_musl.Linux-x86_64/feeds/base/package/network/services/wireguard/patches/010-wg-mod.patch |
|||
При последующей очистке и пересборке он будет автоматом применяться. |
|||
|
|||
|
|||
АЛЬТЕРНАТИВА : можно не возиться с quilt. |
|||
сделайте |
|||
# make package/wireguard/clean |
|||
# make package/wireguard/prepare |
|||
и напрямую модифицируйте или копируйте файлы в |
|||
openwrt-sdk-18.06.2-ar71xx-generic_gcc-7.3.0_musl.Linux-x86_64/build_dir/target-mips_24kc_musl/linux-ar71xx_generic/WireGuard-0.0.20190123/src |
|||
затем |
|||
# make package/wireguard/compile |
|||
|
|||
Если нужно поменять версию wireguard, то идите в |
|||
openwrt-sdk-18.06.2-ar71xx-generic_gcc-7.3.0_musl.Linux-x86_64/feeds/base/package/network/services/wireguard/Makefile |
|||
поменяйте там версию в PKG_VERSION на последнюю из : https://git.zx2c4.com/WireGuard |
|||
скачайте tar.xz с этой версией , вычислите его sha256sum, впишите в PKG_HASH |
|||
|
|||
1 раз где-нибудь пропатчите файлы последней версии wireguard в текстовом редакторе, скопируйте в build_dir, |
|||
сделайте версию для openwrt. эти же файлы скопируйте на ваш сервер с десктопным linux, сделайте там make / make install |
|||
|
|||
Но имейте в виду, что build_dir - локация для временных файлов. |
|||
make clean оттуда все снесет, включая ваши модификации. Модифицированные файлы лучше сохранить отдельно, |
|||
чтобы потом было легко скопировать обратно. |
|||
|
|||
Полученные ipk копируем на роутер в /tmp, устанавливаем через |
|||
# cd /tmp |
|||
# rm -r /tmp/opkg-lists |
|||
# opkg install *.ipk |
|||
Если требует зависимостей, то |
|||
# opkg update |
|||
# opkg install .... <зависимости> |
|||
# rm -r /tmp/opkg-lists |
|||
# opkg install *.ipk |
|||
|
|||
В /tmp/opkg-lists opkg хранит кэш списка пакетов. Если попытаться установить файл ipk, и такой же пакет |
|||
найдется в репозитории, opkg будет устанавливать из репозитория. А нам это не надо. |
|||
|
|||
# rmmod wireguard |
|||
# kmodloader |
|||
# dmesg | tail |
|||
должны увидеть что-то вроде : |
|||
[8985.415490] wireguard: WireGuard 0.0.20190123 loaded. See www.wireguard.com for information. |
|||
[8985.424178] wireguard: Copyright (C) 2015-2019 Jason A. Donenfeld <[email protected]>. All Rights Reserved. |
|||
значит модуль загрузился |
|||
|
|||
Могут понадобиться ключи opkg --force-reinstall, --force-depends. |
|||
--force-depends поможет при несоответствии hash версии ядра. То есть версия x.x.x та же самая, но hash конфигурации разный. |
|||
При несоответствии x.x.x вы что-то делаете не так, работать это не будет. |
|||
Например : 4.14.56-1-b1186491495127cc6ff81d29c00a91fc, 4.14.56-1-3f8a21a63974cfb7ee67e41f2d4b805d |
|||
Это свидетельствует о несоответствии .config ядра при сборке прошивки и в SDK. |
|||
Если несоответствие легкое, то может все прокатить, но при более серьезной разнице в .config модуль может не загрузиться |
|||
или вызвать стабильные или хаотические падения ядра и перезагрузки (включая вариант беcконечной перезагрузки - bootloop). |
|||
Так что перед --force-depends убедитесь, что знаете как лечится такая ситуация, и не стоит это делать при отсутствии физического |
|||
доступа к девайсу. |
|||
|
|||
Когда поднимите линк, и вдруг ничего не будет работать, то посмотрите в wireshark udp пакеты |
|||
на порт endpoint. Они не должны начинаться с 0,1,2,3,4. В первых 4 байтах должен быть рандом, |
|||
в следующих 4 байтах - значения из измененного enum message_type. Если пакет все еще начинается с 0..4, |
|||
значит модуль wireguard оригинальный, что-то не собралось, не скопировалось, не перезапустилось. |
|||
В противном случае должен подняться линк, пинги ходить. Значит вы победили, поздравляю. |
|||
Регулятору будет намного сложнее поймать ваш VPN. |
|||
@ -0,0 +1,730 @@ |
|||
- [Предисловие](#предисловие) |
|||
- [План действий](#план-действий) |
|||
- [Если нет своего сервера](#если-нет-своего-сервера) |
|||
- [Поднятие сервера](#поднятие-сервера) |
|||
- [Подготовка `zapret`](#подготовка-zapret) |
|||
- [Маркировка трафика `iptables`](#маркировка-трафика-iptables) |
|||
- [Маркировка трафика `nftables`](#маркировка-трафика-nftables) |
|||
- [По поводу двойного NAT](#по-поводу-двойного-nat) |
|||
- [Как мне отправлять на VPN весь трафик с bittorrent?](#как-мне-отправлять-на-vpn-весь-трафик-с-bittorrent) |
|||
- [Автоматизация проброса портов через `miniupnd`](#автоматизация-проброса-портов-через-miniupnd) |
|||
|
|||
# Предисловие |
|||
|
|||
Данный мануал пишется не как копипастная инструкция, а как помощь уже соображающему. |
|||
Если вы не знаете основ сетей, Linux, OpenWrt, а пытаетесь что-то скопипастить отсюда без малейшего понимания смысла, то маловероятно, что у вас что-то заработает. Не тратьте свое время напрасно. |
|||
Цель - донести принципы как это настраивается вообще, а не указать какую буковку где вписать. |
|||
|
|||
# План действий |
|||
|
|||
Есть возможность поднять свой VPN сервер? Не хотим использовать redsocks? |
|||
Хотим завертывать на VPN только часть трафика? |
|||
Например, из ipset zapret только порт TCP:443, из ipban - весь трафик, не только TCP? |
|||
Да, с VPN такое возможно. |
|||
|
|||
Опишу понятийно, как настраивается policy based routing в OpenWrt на примере WireGuard. |
|||
Вместо WireGuard можно использовать OpenVPN или любой другой. Но WireGuard прекрасен сразу несколькими вещами, главная из которых - в разы большая скорость, даже немного превышающая IPsec. |
|||
Ведь OpenVPN основан на tun, а tun - всегда в разы медленнее решения в kernel mode, и если для PC оно может быть не так актуально, для soho роутеров - более чем. |
|||
WireGuard может дать 50 mbps там, где OpenVPN еле тащит 10. |
|||
Но есть и дополнительное требование. WireGuard работает в ядре, значит ядро должно быть под вашим контролем. VPS на базе OpenVZ не подойдет. Нужен Xen, KVM, любой другой вариант, где загружается ваше собственное ядро, а не используется общее, разделяемое на множество VPS. |
|||
|
|||
Понятийно необходимо выполнить следующие шаги : |
|||
|
|||
1) Поднять VPN сервер. |
|||
2) Настроить VPN клиент. |
|||
|
|||
Результат этого шага - получение поднятого интерфейса VPN. |
|||
Будь то WireGuard, OpenVPN или любой другой тип VPN. |
|||
|
|||
3) Создать такую схему маршрутизации, при которой пакеты, помечаемые особым mark, попадают на VPN, а остальные идут обычным способом. |
|||
4) Создать правила, выставляющие mark для всего трафика, который необходимо рулить на VPN. |
|||
|
|||
Критерии могут быть любые, ограниченные лишь возможностями `iptables` и вашим воображением. |
|||
|
|||
Будем считать, что наш VPN сервер находится на IP 91.15.68.202. |
|||
Вешать его будем на UDP порт 12345. На этот же порт будем вешать и клиентов. |
|||
Сервер работает под Debian 9 или выше. Клиент работает под OpenWrt. |
|||
Для VPN отведем подсеть 192.168.254.0/24. |
|||
|
|||
## Если нет своего сервера |
|||
|
|||
Но есть конфиг от VPN провайдера или от друга "Васи", который захотел с вами поделиться. |
|||
Тогда вам не надо настраивать сервер, задача упрощается. Делается невозможным вариант настройки без masquerade (см. ниже). |
|||
Из конфига вытаскиваете приватный ключ своего пира и публичный ключ сервера, IP/host/port сервера, используете их в настройках OpenWrt вместо сгенеренных самостоятельно. |
|||
|
|||
## Поднятие сервера |
|||
|
|||
WireGuard был включен в ядро Linux с версии 5.6. |
|||
Если у вас ядро >=5.6, то достаточно установить пакет `wireguard-tools`. Он содержит user-mode компоненты WireGuard. |
|||
Посмотрите, возможно, в вашем дистрибутиве ядро по умолчанию более старое, но в репозитории имеются бэкпорты новых версий. Лучше будет обновить ядро из репозитория. |
|||
|
|||
В репозитории может быть пакет `wireguard-dkms`. Это автоматизированное средство сборки WireGuard с исходников, в том числе модуль ядра. Можно пользоваться им. |
|||
Иначе вам придется собрать WireGuard самому. Ядро должно быть не ниже 3.10. |
|||
На сервере должны быть установлены заголовки ядра (`linux-headers-...`) и компилятор `gcc`. |
|||
|
|||
```sh |
|||
git clone --depth 1 https://git.zx2c4.com/wireguard-linux-compat |
|||
cd wireguard-linux-compat/src |
|||
make |
|||
strip --strip-debug wireguard.ko |
|||
sudo make install |
|||
``` |
|||
|
|||
WireGuard основан на понятии криптороутинга. Каждый пир (сервер - тоже пир) имеет пару открытый/закрытый ключ. Закрытый ключ остается у пира, открытый прописывается у его партнера. Каждый пир авторизует другого по знанию приватного ключа, соответствующего прописанному у него публичному ключу. |
|||
Протокол построен таким образом, что на все неправильные UDP пакеты не следует ответа. |
|||
Не знаешь приватный ключ? Не смог послать правильный запрос? |
|||
Долбись сколько влезет, я тебе ничего не отвечу. Это защищает от активного пробинга со стороны DPI и просто экономит ресурсы. |
|||
Значит, первым делом нужно создать 2 пары ключей: для сервера и для клиента. |
|||
`wg genkey` генерит приватный ключ, `wg pubkey` получает из него публичный ключ. |
|||
|
|||
```sh |
|||
$ wg genkey |
|||
oAUkmhoREtFQ5D5yZmeHEgYaSWCcLYlKe2jBP7EAGV0= |
|||
$ echo oAUkmhoREtFQ5D5yZmeHEgYaSWCcLYlKe2jBP7EAGV0= | wg pubkey |
|||
bCdDaPYSTBZVO1HTmKD+Tztuf3PbOWGDWfz7Lb1E6C4= |
|||
$ wg genkey |
|||
OKXX0TSlyjJmGt3/yHlHxi0AqjJ0vh+Msne3qEHk0VM= |
|||
$ echo OKXX0TSlyjJmGt3/yHlHxi0AqjJ0vh+Msne3qEHk0VM= | wg pubkey |
|||
EELdA2XzjcKxtriOCPBXMOgxlkgpbRdIyjtc3aIpkxg= |
|||
``` |
|||
|
|||
Пишем конфиг: |
|||
|
|||
`/etc/wireguard/wgvps.conf`: |
|||
|
|||
```conf |
|||
[Interface] |
|||
PrivateKey = OKXX0TSlyjJmGt3/yHlHxi0AqjJ0vh+Msne3qEHk0VM= |
|||
ListenPort = 12345 |
|||
|
|||
[Peer] |
|||
|
|||
# Endpoint = |
|||
PublicKey = bCdDaPYSTBZVO1HTmKD+Tztuf3PbOWGDWfz7Lb1E6C4= |
|||
AllowedIPs = 192.168.254.3 |
|||
PersistentKeepalive=20 |
|||
``` |
|||
|
|||
WireGuard - минималистичный VPN. В нем нет никаких средств для автоконфигурации IP. |
|||
Все придется прописывать руками. |
|||
В `wgvps.conf` должны быть перечислены все пиры с их публичными ключами, а так же прописаны допустимые для них IP адреса. |
|||
Назначим нашему клиенту 192.168.254.3. Сервер будет иметь IP 192.168.254.1. |
|||
Endpoint должен быть прописан хотя бы на одном пире. |
|||
Если endpoint настроен для пира, то WireGuard будет периодически пытаться к нему подключиться. |
|||
В схеме клиент/сервер у сервера можно не прописывать endpoint-ы пиров, что позволит менять IP и быть за NAT. |
|||
Endpoint пира настраивается динамически после успешной фазы проверки ключа. |
|||
|
|||
Включаем маршрутизацию: |
|||
|
|||
```sh |
|||
echo net.ipv4.ip_forward = 1 >>/etc/sysctl.conf |
|||
sysctl -p |
|||
``` |
|||
|
|||
Интерфейс конфигурируется стандартно для дебиан-подобных систем: |
|||
|
|||
`/etc/network/interfaces.d/wgvps`: |
|||
|
|||
``` |
|||
auto wgvps |
|||
iface wgvps inet static |
|||
address 192.168.254.1 |
|||
netmask 255.255.255.0 |
|||
pre-up ip link add $IFACE type wireguard |
|||
pre-up wg setconf $IFACE /etc/wireguard/$IFACE.conf |
|||
post-up iptables -t nat -A POSTROUTING -o eth0 -s 192.168.254.0/24 -j MASQUERADE |
|||
post-up iptables -A FORWARD -o eth0 -p tcp --tcp-flags SYN,RST SYN -j TCPMSS --clamp-mss-to-pmtu |
|||
post-down iptables -D FORWARD -o eth0 -p tcp --tcp-flags SYN,RST SYN -j TCPMSS --clamp-mss-to-pmtu |
|||
post-down iptables -t nat -D POSTROUTING -o eth0 -s 192.168.254.0/24 -j MASQUERADE |
|||
post-down ip link del $IFACE |
|||
``` |
|||
|
|||
Поднятие через `ifup wgvps`, опускание через `ifdown wgvps`. |
|||
При поднятии интерфейса заодно настраивается NAT. `eth0` здесь означает интерфейс VPN сервера с инетовским IP адресом. |
|||
Если у вас какая-то система управления фаерволом, то надо настройку NAT прикручивать туда. |
|||
Пример написан для простейшего случая, когда никаких ограничений нет, таблицы `iptables` пустые. |
|||
Чтобы посмотреть текущие настройки WireGuard, запустите `wg` без параметров. |
|||
|
|||
Поднятие клиента: |
|||
|
|||
```sh |
|||
opkg update |
|||
opkg install wireguard-tools |
|||
``` |
|||
|
|||
Добавляем записи в конфиги: |
|||
|
|||
`/etc/config/network`: |
|||
|
|||
``` |
|||
config interface 'wgvps' |
|||
option proto 'wireguard' |
|||
option auto '1' |
|||
option private_key 'oAUkmhoREtFQ5D5yZmeHEgYaSWCcLYlKe2jBP7EAGV0=' |
|||
option listen_port '12345' |
|||
option metric '9' |
|||
option mtu '1420' |
|||
|
|||
config wireguard_wgvps |
|||
option public_key 'EELdA2XzjcKxtriOCPBXMOgxlkgpbRdIyjtc3aIpkxg=' |
|||
list allowed_ips '0.0.0.0/0' |
|||
option endpoint_host '91.15.68.202' |
|||
option endpoint_port '12345' |
|||
option route_allowed_ips '0' |
|||
option persistent_keepalive '20' |
|||
|
|||
config interface 'wgvps_ip' |
|||
option proto 'static' |
|||
option ifname '@wgvps' |
|||
list ipaddr '192.168.254.3/24' |
|||
|
|||
config route |
|||
option interface 'wgvps' |
|||
option target '0.0.0.0/0' |
|||
option table '100' |
|||
|
|||
config rule |
|||
option mark '0x800/0x800' |
|||
option priority '100' |
|||
option lookup '100' |
|||
``` |
|||
|
|||
`/etc/config/firewall`: |
|||
|
|||
``` |
|||
config zone |
|||
option name 'tunvps' |
|||
option output 'ACCEPT' |
|||
option input 'REJECT' |
|||
option masq '1' |
|||
option mtu_fix '1' |
|||
option forward 'REJECT' |
|||
option network 'wgvps wgvps_ip' |
|||
|
|||
config forwarding |
|||
option dest 'tunvps' |
|||
option src 'lan' |
|||
|
|||
config rule |
|||
option name 'Allow-ICMP-tunvps' |
|||
option src 'tunvps' |
|||
option proto 'icmp' |
|||
option target 'ACCEPT' |
|||
|
|||
config rule |
|||
option target 'ACCEPT' |
|||
option src 'wan' |
|||
option proto 'udp' |
|||
option family 'ipv4' |
|||
option src_port '12345' |
|||
option src_ip '91.15.68.202' |
|||
option name 'WG-VPS' |
|||
``` |
|||
|
|||
Что тут было сделано: |
|||
|
|||
- Настроен интерфейс `wireguard`. Указан собственный приватный ключ. |
|||
- Настроен пир-партнер с указанием его публичного ключа и endpoint (IP:port нашего сервера) |
|||
- Такая настройка заставит периодически долбиться на сервер по указанному IP |
|||
- `route_allowed_ip '0'` запрещает автоматическое создание маршрута |
|||
- `allowed_ips '0.0.0.0/0'` разрешает пакеты с любым адресом источника, ведь мы собираемся подключаться к любым IP в инете |
|||
- `persistent_keepalive '20'` помогает исключить дропание mapping на NAT-е, если мы сидим за ним, да и вообще полезная вещь, чтобы не было подвисших пиров |
|||
- Статическая конфигурация IP интерфейса `wgvps`. |
|||
- Маршрут `default route` на `wgvps` в отдельной таблице маршрутизации с номером 100. Аналог команды `ip route add .. table 100` |
|||
- Правило использовать таблицу 100 при выставлении в mark бита 0x800. Аналог команды `ip rule`. |
|||
- Отдельная зона фаервола для VPN - `tunvps`. В принципе, ее можно не создавать, можете приписать интерфейс к зоне `wan`. |
|||
|
|||
Но в случае с отдельной зоной можно настроить особые правила на подключения с VPN сервера в сторону клиента. |
|||
|
|||
- Разрешение форвардинга между локалкой за роутером и `wgvps`. |
|||
- Разрешение принимать ICMP от VPN сервера, включая пинги. ICMP жизненно важны для правильного функционирования IP сети! |
|||
- И желательно проткнуть дырку в фаерволе, чтобы принимать пакеты WireGuard со стороны инетовского IP VPN сервера. |
|||
|
|||
Конечно, оно скорее всего заработает и так, потому что первый пакет пойдет от клиента к серверу и тем самым создаст запись в conntrack. |
|||
Все дальнейшие пакеты в обе стороны подпадут под состояние ESTABLISHED и будут пропущены. |
|||
Запись будет поддерживаться за счет периодических запросов keep alive. |
|||
Но если вы вдруг уберете keep alive или выставите таймаут, превышающий UDP таймаут в conntrack, то могут начаться ошибки, висы и переподключения. |
|||
Если же в фаерволе проткнута дырка, то пакеты от сервера не будут заблокированы ни при каких обстоятельствах. |
|||
|
|||
Перезапускаем фаерволл, поднимаем интерфейс и проверяем: |
|||
|
|||
```sh |
|||
/etc/init.d/firewall restart |
|||
ifup wgvps |
|||
ifconfig wgvps |
|||
ping 192.168.254.1 |
|||
``` |
|||
|
|||
Если все хорошо, должны ходить пинги. |
|||
С сервера не помешает : |
|||
|
|||
```sh |
|||
ping 192.168.254.3 |
|||
``` |
|||
|
|||
# Подготовка `zapret` |
|||
|
|||
Выполните `install_easy.sh`. Он настроит режим обхода DPI. Если обход DPI не нужен - выберите `MODE=filter`. |
|||
Так же инсталлятор заресолвит домены из `ipset/zapret-hosts-user-ipban.txt` и внесет крон-джоб для периодического обновления IP. |
|||
|
|||
Если вы используете в своих правилах ipset zapret, то он ресолвится и обновляется только, если выбран режим фильтрации обхода DPI по ipset. |
|||
По сути он вам нужен исключительно, если обход DPI не помогает. Например, удается как-то пробить HTTP, но не удается пробить HTTPS. |
|||
И при этом вы хотите, чтобы на VPN направлялись только IP из скачанного IP листа, в добавок к заресолвленному `ipset/zapret-hosts-user.txt`. |
|||
Именно этот случай и рассмотрен в данном примере. Если это не так, то убирайте правила с портом 443 из нижеприведенных правил `iptables`/`nftables`. |
|||
Если не хотите ограничиваться листом, и хотите направлять все на порт 443, то уберите фильтры из правил `iptables`/`nftables`, связанные с `ipset`/`nfset` "zapret". |
|||
|
|||
Фильтрация по именам доменов (`MODE_FILTER=hostlist`) невозможна средствами `iptables`/`nftables`. Она производится исключительно в `tpws` и `nfqws` по результатам анализа протокола прикладного уровня, иногда достаточно сложного, связанного с дешифровкой пакета (QUIC). |
|||
Скачиваются листы с именами доменов, не IP адресами. `ipset/zapret-hosts-user.txt` не ресолвится, а используется как hostlist. |
|||
Потому вам нельзя рассчитывать на ipset zapret. |
|||
Тем не менее, при выборе этого режима фильтрации, либо вовсе при ее отсутствии (`MODE_FILTER=none`), `ipset/zapret-hosts-user-ipban.txt` все равно ресолвится. |
|||
Вы всегда можете рассчитывать на `ipset`/`nfset` "ipban", "nozapret". |
|||
|
|||
"nozapret" - это `ipset`/`nfset`, связанный с системой исключения IP. Сюда загоняется все из `ipset/zapret-hosts-user-exclude.txt` после ресолвинга. |
|||
Его учет крайне желателен, чтобы вдруг из скачанного листа не просочились записи, например, 192.168.0.0/16 и не заставили лезть туда через VPN. |
|||
Хотя скрипты получения листов и пытаются отсечь IP локалок, но так будет намного надежнее. |
|||
|
|||
## Маркировка трафика `iptables` |
|||
|
|||
Завернем на VPN все из ipset zapret на TCP:443 и все из `ipban`. |
|||
OUTPUT относится к исходящим с роутера пакетам, PREROUTING - ко всем остальным. |
|||
Если с самого роутера ничего заруливать не надо, можно опустить часть, отвечающую за OUTPUT. |
|||
|
|||
`/etc/firewall.user`: |
|||
|
|||
```sh |
|||
. /opt/zapret/init.d/openwrt/functions |
|||
|
|||
create_ipset no-update |
|||
|
|||
network_find_wan4_all wan_iface |
|||
for ext_iface in $wan_iface; do |
|||
network_get_device DEVICE $ext_iface |
|||
ipt OUTPUT -t mangle -o $DEVICE -p tcp --dport 443 -m set --match-set zapret dst -m set ! --match-set nozapret dst -j MARK --set-mark 0x800/0x800 |
|||
ipt OUTPUT -t mangle -o $DEVICE -m set --match-set ipban dst -m set ! --match-set nozapret dst -j MARK --set-mark 0x800/0x800 |
|||
done |
|||
|
|||
network_get_device DEVICE lan |
|||
ipt PREROUTING -t mangle -i $DEVICE -p tcp --dport 443 -m set --match-set zapret dst -m set ! --match-set nozapret dst -j MARK --set-mark 0x800/0x800 |
|||
ipt PREROUTING -t mangle -i $DEVICE -m set --match-set ipban dst -m set ! --match-set nozapret dst -j MARK --set-mark 0x800/0x800 |
|||
``` |
|||
|
|||
```sh |
|||
/etc/init.d/firewall restart |
|||
``` |
|||
|
|||
## Маркировка трафика `nftables` |
|||
|
|||
В новых OpenWrt по умолчанию установлен `nftables`, `iptables` отсутствует. |
|||
Есть вариант снести `nftables` + `fw4` и заменить их на `iptables` + `fw3`. |
|||
Веб-интерфейс luci понимает прозрачно и `fw3`, и `fw4`. Однако, при установке `iptables` и `fw3` новые пакеты будут устанавливаться без сжатия squashfs. Убедитесь, что у вас достаточно места. |
|||
Либо сразу настраивайте образ через image builder. |
|||
|
|||
Фаервол `fw4` работает в одноименной nftable - "inet fw4". "inet" означает, что таблица принимает и IPv4, и IPv6. |
|||
Поскольку для маркировки трафика используется `nfset`, принадлежащий таблице zapret, цепочки необходимо помещать в ту же таблицу. |
|||
Для синхронизации лучше всего использовать хук `INIT_FW_POST_UP_HOOK="/etc/firewall.zapret.hook.post_up"` |
|||
Параметр нужно раскомментировать в `/opt/zapret/config`. Далее надо создать указанный файл и дать ему `chmod 755`. |
|||
|
|||
`/etc/firewall.zapret.hook.post_up`: |
|||
|
|||
```sh |
|||
# !/bin/sh |
|||
|
|||
ZAPRET_NFT_TABLE=zapret |
|||
|
|||
cat << EOF | nft -f - 2>/dev/null |
|||
delete chain inet $ZAPRET_NFT_TABLE my_output |
|||
delete chain inet $ZAPRET_NFT_TABLE my_prerouting |
|||
EOF |
|||
|
|||
cat << EOF | nft -f - |
|||
add chain inet $ZAPRET_NFT_TABLE my_output { type route hook output priority mangle; } |
|||
flush chain inet $ZAPRET_NFT_TABLE my_output |
|||
add rule inet $ZAPRET_NFT_TABLE my_output oifname @wanif ip daddr @ipban ip daddr != @nozapret meta mark set mark or 0x800 |
|||
add rule inet $ZAPRET_NFT_TABLE my_output oifname @wanif tcp dport 443 ip daddr @zapret ip daddr != @nozapret meta mark set mark or 0x800 |
|||
add chain inet $ZAPRET_NFT_TABLE my_prerouting { type filter hook prerouting priority mangle; } |
|||
flush chain inet $ZAPRET_NFT_TABLE my_prerouting |
|||
add rule inet $ZAPRET_NFT_TABLE my_prerouting iifname @lanif ip daddr @ipban ip daddr != @nozapret meta mark set mark or 0x800 |
|||
add rule inet $ZAPRET_NFT_TABLE my_prerouting iifname @lanif tcp dport 443 ip daddr @zapret ip daddr != @nozapret meta mark set mark or 0x800 |
|||
EOF |
|||
``` |
|||
|
|||
```sh |
|||
/etc/init.d/zapret restart_fw |
|||
``` |
|||
|
|||
Проверка правил: |
|||
|
|||
```sh |
|||
/etc/init.d/zapret list_table |
|||
# или |
|||
nft -t list table inet zapret |
|||
``` |
|||
|
|||
Должны быть цепочки `my_prerouting` и `my_output`. |
|||
|
|||
Проверка заполнения nfsets: |
|||
|
|||
```sh |
|||
nft list set inet zapret zapret |
|||
nft list set inet zapret ipban |
|||
nft list set inet zapret nozapret |
|||
``` |
|||
|
|||
Проверка заполнения множеств `lanif`, `wanif`, `wanif6`, `link_local`: |
|||
|
|||
```sh |
|||
/etc/init.d/zapret list_ifsets |
|||
``` |
|||
|
|||
Должны присутствовать имена интерфейсов во множествах `lanif`, `wanif`. |
|||
`wanif6` заполняется только при включении IPv6. |
|||
`link_local` нужен только для tpws при включении IPv6. |
|||
|
|||
## По поводу двойного NAT |
|||
|
|||
В описанной конфигурации NAT выполняется дважды: на роутере-клиенте происходит замена адреса источника из LAN на 192.168.254.3 и на сервере замена 192.168.254.3 на внешний адрес сервера в инете. |
|||
Зачем так делать? Исключительно для простоты настройки. Или на случай, если сервер WireGuard не находится под вашим контролем. |
|||
Делать для вас нижеописанные настройки никто не будет с вероятностью, близкой к 100%. |
|||
Если сервер WireGuard - ваш, и вы готовы чуток еще поднапрячься и не хотите двойного NAT, |
|||
то можете вписать в `/etc/config/firewall` `masq '0'`, на сервер дописать маршрут до вашей подсети LAN. |
|||
Чтобы не делать это для каждого клиента, можно отвести под всех клиентов диапазон 192.168.0.0-192.168.127.255 |
|||
и прописать его одним маршрутом: |
|||
|
|||
`/etc/network/interfaces.d/wgvps`: |
|||
|
|||
``` |
|||
post-up ip route add dev $IFACE 192.168.0.0/17 |
|||
post-down ip route del dev $IFACE 192.168.0.0/17 |
|||
``` |
|||
|
|||
Также необходимо указать WireGuard дополнительные разрешенные IP для peer: |
|||
|
|||
`/etc/wireguard/wgvps.conf`: |
|||
|
|||
``` |
|||
[Peer] |
|||
PublicKey = bCdDaPYSTBZVO1HTmKD+Tztuf3PbOWGDWfz7Lb1E6C4= |
|||
AllowedIPs = 192.168.254.3, 192.168.2.0/24 |
|||
``` |
|||
|
|||
Всем клиентам придется назначать различные диапазоны адресов в LAN и индивидуально прописывать `AllowedIPs` |
|||
для каждого peer. |
|||
|
|||
```sh |
|||
ifdown wgvps |
|||
ifup wgvps |
|||
``` |
|||
|
|||
На клиенте разрешим форвард ICMP, чтобы работал пинг и корректно определялось MTU. |
|||
|
|||
`/etc/config/firewall`: |
|||
|
|||
``` |
|||
config rule |
|||
option name 'Allow-ICMP-tunvps' |
|||
option src 'tunvps' |
|||
option dest 'lan' |
|||
option proto 'icmp' |
|||
option target 'ACCEPT' |
|||
``` |
|||
|
|||
Существуют еще два неочевидных нюанса. |
|||
|
|||
Первый из них касается пакетов с самого роутера (цепочка OUTPUT). |
|||
Адрес источника выбирается по особому алгоритму, если программа явно его не задала, еще до этапа `iptables`. |
|||
Он берется с интерфейса, куда бы пошел пакет при нормальном раскладе. |
|||
Обратная маршрутизация с VPN станет невозможной, да и WireGuard такие пакеты порежет, поскольку они не вписываются в `AllowedIPs`. |
|||
Никаким мистическим образом автоматом source address не поменяется. |
|||
В прошлом варианте настройки проблема решалось через маскарад. Сейчас же маскарада нет. |
|||
Потому все же придется его делать в случае, когда пакет изначально направился бы через WAN, |
|||
а мы его завертываем на VPN. Помечаем такие пакеты марком 0x1000. |
|||
Если вам не актуальны исходящие с самого роутера, то можно ничего не менять. |
|||
|
|||
Другой нюанс связан с обработкой проброшенных на VPS портов, соединения по которым приходят как входящие с интерфейса `wgvps`. |
|||
Представьте себе, что вы пробросили порт 2222. Кто-то подключается с адреса 1.2.3.4. Вам приходит пакет SYN 1.2.3.4:51723=>192.168.2.2:2222. |
|||
По правилам маршрутизации он пойдет в локалку. 192.168.2.2 его обработает, ответит пакетом ACK 192.168.2.2:2222=>1.2.3.4:51723. |
|||
Этот пакет придет на роутер. И куда он дальше пойдет? Если он не занесен в ipban, то согласно правилам маршрутизации |
|||
он пойдет по WAN интерфейсу, а не по исходному `wgvps`. |
|||
Чтобы решить эту проблему, необходимо воспользоваться CONNMARK. Существуют 2 отдельных марка: fwmark и connmark. |
|||
connmark относится к соединению, fwmark - к пакету. Трэкингом соединений занимается conntrack. |
|||
Посмотреть его таблицу можно командой `conntrack -L`. Там же найдете connmark: mark=xxxx. |
|||
Как только видим приходящий с `wgvps` пакет с новым соединением, отмечаем его connmark как 0x800/0x800. |
|||
При этом fwmark не меняется, иначе бы пакет тут же бы завернулся обратно на `wgvps` согласно `ip rule`. |
|||
Если к нам приходит пакет с какого-то другого интерфейса, то восстанавливаем его connmark в fwmark по маске 0x800. |
|||
И теперь он подпадает под правило `ip rule`, заворачиваясь на `wgvps`, что и требовалось. |
|||
|
|||
Альтернативное решение - использовать на VPSке для проброса портов не только DNAT, но и SNAT/MASQUERADE. |
|||
Тогда source address будет заменен на 192.168.254.1. Он по таблице маршрутизации пойдет на wgvps. |
|||
Но в этом случае клиентские программы, на которые осуществляется проброс портов, не будут видеть реальный IP подключенца. |
|||
|
|||
`/etc/firewall.user`: |
|||
|
|||
```sh |
|||
. /opt/zapret/init.d/openwrt/functions |
|||
|
|||
create_ipset no-update |
|||
|
|||
network_find_wan4_all wan_iface |
|||
for ext_iface in $wan_iface; do |
|||
network_get_device DEVICE $ext_iface |
|||
ipt OUTPUT -t mangle -o $DEVICE -p tcp --dport 443 -m set --match-set zapret dst -m set ! --match-set nozapret dst -j MARK --set-mark 0x800/0x800 |
|||
ipt OUTPUT -t mangle -o $DEVICE -m set --match-set ipban dst -m set ! --match-set nozapret dst -j MARK --set-mark 0x800/0x800 |
|||
ipt OUTPUT -t mangle -o $DEVICE -j MARK --set-mark 0x1000/0x1000 |
|||
done |
|||
|
|||
network_get_device DEVICE lan |
|||
ipt PREROUTING -t mangle -i $DEVICE -p tcp --dport 443 -m set --match-set zapret dst -m set ! --match-set nozapret dst -j MARK --set-mark 0x800/0x800 |
|||
ipt PREROUTING -t mangle -i $DEVICE -m set --match-set ipban dst -m set ! --match-set nozapret dst -j MARK --set-mark 0x800/0x800 |
|||
|
|||
# do masquerade for OUTPUT to ensure correct outgoing address |
|||
|
|||
ipt postrouting_tunvps_rule -t nat -m mark --mark 0x1000/0x1000 -j MASQUERADE |
|||
|
|||
# incoming from wgvps |
|||
|
|||
network_get_device DEVICE wgvps |
|||
ipt PREROUTING -t mangle ! -i $DEVICE -j CONNMARK --restore-mark --nfmask 0x800 --ctmask 0x800 |
|||
ipt PREROUTING -t mangle -i $DEVICE -m conntrack --ctstate NEW -j CONNMARK --set-mark 0x800/0x800 |
|||
``` |
|||
|
|||
```sh |
|||
/etc/init.d/firewall restart |
|||
``` |
|||
|
|||
Вариант `nftables`: |
|||
|
|||
`/etc/firewall.zapret.hook.post_up`: |
|||
|
|||
```sh |
|||
# !/bin/sh |
|||
|
|||
ZAPRET_NFT_TABLE=zapret |
|||
DEVICE=wgvps |
|||
|
|||
cat << EOF | nft -f - 2>/dev/null |
|||
delete chain inet $ZAPRET_NFT_TABLE my_output |
|||
delete chain inet $ZAPRET_NFT_TABLE my_prerouting |
|||
delete chain inet $ZAPRET_NFT_TABLE my_nat |
|||
EOF |
|||
|
|||
cat << EOF | nft -f - |
|||
add chain inet $ZAPRET_NFT_TABLE my_output { type route hook output priority mangle; } |
|||
flush chain inet $ZAPRET_NFT_TABLE my_output |
|||
add rule inet $ZAPRET_NFT_TABLE my_output oifname @wanif ip daddr @ipban ip daddr != @nozapret meta mark set mark or 0x800 |
|||
add rule inet $ZAPRET_NFT_TABLE my_output oifname @wanif tcp dport 443 ip daddr @zapret ip daddr != @nozapret meta mark set mark or 0x800 |
|||
add rule inet $ZAPRET_NFT_TABLE my_output oifname @wanif meta mark set mark or 0x1000 |
|||
|
|||
add chain inet $ZAPRET_NFT_TABLE my_prerouting { type filter hook prerouting priority mangle; } |
|||
flush chain inet $ZAPRET_NFT_TABLE my_prerouting |
|||
add rule inet $ZAPRET_NFT_TABLE my_prerouting iifname $DEVICE ct state new ct mark set ct mark or 0x800 |
|||
add rule inet $ZAPRET_NFT_TABLE my_prerouting iifname != $DEVICE meta mark set ct mark and 0x800 |
|||
add rule inet $ZAPRET_NFT_TABLE my_prerouting iifname @lanif ip daddr @ipban ip daddr != @nozapret meta mark set mark or 0x800 |
|||
add rule inet $ZAPRET_NFT_TABLE my_prerouting iifname @lanif tcp dport 443 ip daddr @zapret ip daddr != @nozapret meta mark set mark or 0x800 |
|||
|
|||
add chain inet $ZAPRET_NFT_TABLE my_nat { type nat hook postrouting priority 100 ; } |
|||
flush chain inet $ZAPRET_NFT_TABLE my_nat |
|||
add rule inet $ZAPRET_NFT_TABLE my_nat oifname $DEVICE mark and 0x1000 == 0x1000 masquerade |
|||
EOF |
|||
``` |
|||
|
|||
```sh |
|||
/etc/init.d/zapret restart_fw |
|||
``` |
|||
|
|||
К сожалению, здесь возможности `nftables` немного хромают. Полноценного эквивалента `CONNMARK --restore-mark --nfmask` не существует. Оригинал `iptables` предполагал копирование одного бита 0x800 из connmark в mark. |
|||
Лучшее, что можно сделать в `nftables`, это копирование одного бита с занулением всех остальных. |
|||
Сложные выражения типа `meta mark set mark and ~0x800 or (ct mark and 0x800)` nft не понимает. |
|||
Об этом же говорит попытка перевода через `iptables-translate`. |
|||
|
|||
Сейчас уже можно с VPN сервера пингануть IP адрес внутри локалки клиента. Пинги должны ходить. |
|||
|
|||
Отсутствие двойного NAT значительно облегчает проброс портов с внешнего IP VPN сервера в локалку какого-либо клиента. |
|||
Для этого надо выполнить 2 действия: добавить разрешение в фаервол на клиенте и сделать dnat на сервере. |
|||
Пример форварда портов 5001 и 5201 на 192.168.2.2 : |
|||
|
|||
`/etc/config/firewall`: |
|||
|
|||
``` |
|||
config rule |
|||
option target 'ACCEPT' |
|||
option src 'tunvps' |
|||
option dest 'lan' |
|||
option proto 'tcp udp' |
|||
option dest_port '5001 5201' |
|||
option dest_ip '192.168.2.2' |
|||
option name 'IPERF' |
|||
``` |
|||
|
|||
```sh |
|||
/etc/init.d/firewall restart |
|||
/etc/init.d/zapret restart_fw |
|||
``` |
|||
|
|||
`/etc/network/interfaces.d/wgvps`: |
|||
|
|||
``` |
|||
post-up iptables -t nat -A PREROUTING -i eth0 -p tcp -m multiport --dports 5001,5201 -j DNAT --to-destination 192.168.2.2 |
|||
post-up iptables -t nat -A PREROUTING -i eth0 -p udp -m multiport --dports 5001,5201 -j DNAT --to-destination 192.168.2.2 |
|||
post-down iptables -t nat -D PREROUTING -i eth0 -p tcp -m multiport --dports 5001,5201 -j DNAT --to-destination 192.168.2.2 |
|||
post-down iptables -t nat -D PREROUTING -i eth0 -p udp -m multiport --dports 5001,5201 -j DNAT --to-destination 192.168.2.2 |
|||
``` |
|||
|
|||
```sh |
|||
ifdown wgvps |
|||
ifup wgvps |
|||
``` |
|||
|
|||
Пример приведен для `iperf` и `iperf3`, чтобы показать как пробрасывать несколько портов TCP+UDP с минимальным количеством команд. |
|||
Проброс TCP и UDP порта так же необходим для полноценной работы bittorrent клиента, чтобы работали входящие. |
|||
|
|||
# Как мне отправлять на VPN весь трафик с bittorrent? |
|||
|
|||
Можно поступить так: посмотрите порт в настройках torrent клиента, убедитесь, что не поставлено "случайный порт", добавьте на роутер правило маркировки по порту источника. |
|||
Но мне предпочтительно иное решение. На Windows есть замечательная возможность прописать правило установки поля качества обслуживания в заголовках IP пакетов в зависимости от процесса-источника. |
|||
Для Windows 7/2008R2 необходимо будет установить ключик реестра и перезагрузить комп : |
|||
|
|||
```powershell |
|||
reg add HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\services\Tcpip\QoS /v "Do not use NLA" /t REG_SZ /d "1" |
|||
``` |
|||
|
|||
Редактировать политику можно в: `gpedit.msc` -> Computer Configuration -> Windows Settings -> Policy-based QoS |
|||
На Windows 10 ключик реестра больше не работает, правила qos в `gpedit` применяются только для профиля домена. |
|||
Необходимо пользоваться командой `powershell New-NetQosPolicy`. Гуглите хелп по ней. Пример : |
|||
|
|||
```powershell |
|||
powershell New-NetQosPolicy -Name "torrent" -AppPathNameMatchCondition "qbittorrent.exe" -DSCPAction 1 |
|||
``` |
|||
|
|||
Однозначно требуется проверка в WireShark или netmon успешности установки поля `dscp`. Если там по-прежнему 0x00, значит, что-то не сработало. 0x04 означает `DSCP=1` (dscp находится в старших 6 битах). |
|||
|
|||
На роутере в фаервол прописываем правило: |
|||
|
|||
`/etc/config/firewall`: |
|||
|
|||
``` |
|||
config rule |
|||
option target 'MARK' |
|||
option src 'lan' |
|||
option proto 'all' |
|||
option extra '-m dscp --dscp 1' |
|||
option name 'route-dscp-1' |
|||
option set_mark '0x0800/0x0800' |
|||
``` |
|||
|
|||
```sh |
|||
/etc/init.d/firewall restart |
|||
``` |
|||
|
|||
Теперь все с полем dscp "1" идет на VPN. Клиент сам решает какой трафик ему нужно забрасывать |
|||
на VPN, перенастраивать роутер не нужно. |
|||
На Linux клиенте проще всего будет выставлять dscp в `iptables` по номеру порта источника : |
|||
|
|||
`/etc/rc.local`: |
|||
|
|||
```sh |
|||
iptables -A OUTPUT -t mangle -p tcp --sport 23444 -j DSCP --set-dscp 1 |
|||
iptables -A OUTPUT -t mangle -p udp --sport 23444 -j DSCP --set-dscp 1 |
|||
``` |
|||
|
|||
Можно привязываться к pid процесса, но тогда нужно перенастраивать `iptables` при каждом перезапуске |
|||
торрент-клиента, это требует рута, и все становится очень неудобно. |
|||
|
|||
## Автоматизация проброса портов через `miniupnd` |
|||
|
|||
Да, его тоже можно использовать на VPS. Только, как всегда, есть нюансы. |
|||
|
|||
`miniupnpd` поддерживает 3 протокола IGD: UPnP, NAT-PMP и PCP. |
|||
UPnP и PCP работают через мультикаст, который не пройдет через wgvps. |
|||
NAT-PMP работает через посылку специальных сообщений на UDP:5351 на default gateway. |
|||
Обычно их обслуживает `miniupnpd` на роутере. При создании lease `miniupnpd` добавляет |
|||
правила для проброса портов в цепочку `iptables MINIUPNPD`, при потери lease - убирает. |
|||
|
|||
UDP:5351 можно перенаправить на VPN сервер через DNAT, чтобы их обрабатывал `miniupnpd` там. |
|||
Но вы должны иметь однозначный критерий перенаправления. |
|||
Если вы решили завернуть на VPN все, то проблем нет. Пробрасываем UDP:5351 безусловно. |
|||
Если у вас идет перенаправление только с торрент, то необходимо к условию перенаправления добавить условия, выделяющие torrent трафик из прочего. Или по dscp, или по sport. |
|||
Чтобы запросы от остальных программ обрабатывались miniupnpd на роутере. |
|||
Если какая-то программа создаст lease не там, где нужно, то входящий трафик до нее не дойдет. |
|||
|
|||
На роутере стоит запретить протокол UPnP, чтобы торрент клиент не удовлетворился запросом, обслуженным по UPnP на роутере, и пытался использовать NAT-PMP. |
|||
|
|||
`/etc/config/upnp`: |
|||
|
|||
``` |
|||
config upnpd 'config' |
|||
..... |
|||
option enable_upnp '0' |
|||
``` |
|||
|
|||
```sh |
|||
/etc/init.d/miniupnpd restart |
|||
``` |
|||
|
|||
Делаем проброс порта на роутере. |
|||
Для простоты изложения будем считать, что на VPN у нас завернут весь трафик. |
|||
Если это не так, то следует добавить фильтр в "config redirect". |
|||
Заодно выделяем диапазон портов для торрент клиентов. |
|||
Порт в торрент клиенте следует прописать какой-то из этого диапазона. |
|||
|
|||
``` |
|||
config redirect |
|||
option enabled '1' |
|||
option target 'DNAT' |
|||
option src 'lan' |
|||
option dest 'tunvps' |
|||
option proto 'udp' |
|||
option src_dport '5351' |
|||
option dest_ip '192.168.254.1' |
|||
option dest_port '5351' |
|||
option name 'NAT-PMP' |
|||
option reflection '0' |
|||
config rule |
|||
option enabled '1' |
|||
option target 'ACCEPT' |
|||
option src 'tunvps' |
|||
option dest 'lan' |
|||
option name 'tunvps-torrent' |
|||
option dest_port '28000-28009' |
|||
``` |
|||
|
|||
```sh |
|||
/etc/init.d/firewall reload |
|||
``` |
|||
|
|||
На сервере: |
|||
|
|||
```sh |
|||
apt install miniupnpd |
|||
``` |
|||
|
|||
`/etc/miniupnpd/miniupnpd.conf`: |
|||
|
|||
```conf |
|||
enable_natpmp=yes |
|||
enable_upnp=no |
|||
lease_file=/var/log/upnp.leases |
|||
system_uptime=yes |
|||
clean_ruleset_threshold=10 |
|||
clean_ruleset_interval=600 |
|||
force_igd_desc_v1=no |
|||
listening_ip=192.168.254.1/16 |
|||
ext_ifname=eth0 |
|||
``` |
|||
|
|||
```sh |
|||
systemctl restart miniupnpd |
|||
``` |
|||
|
|||
`listening_ip` прописан именно таким образом, чтобы обозначить диапазон разрешенных IP. |
|||
С других IP он не будет обрабатывать запросы на редирект. |
|||
В `ext_ifname` впишите название `inet` интерфейса на сервере. |
|||
|
|||
Запускаем торрент клиент. Попутно смотрим в `tcpdump` весь путь UDP:5351 до сервера и обратно. |
|||
Смотрим `syslog` сервера на ругань от miniupnpd. |
|||
Если все ок, то можем проверить редиректы: `iptables -t nat -nL MINIUPNPD` |
|||
С какого-нибудь другого хоста (не VPN сервер, не ваше подключение) можно попробовать `telnet`-нуться на проброшенный порт. |
|||
Должно установиться соединение. Или качайте торрент и смотрите в пирах флаг "I" (incoming). |
|||
Если "I" есть и по ним идет закачка, значит все в порядке. |
|||
|
|||
**ОСОБЕННОСТЬ НОВЫХ DEBIAN:** по умолчанию используются `iptables-nft`. miniupnpd работает с `iptables-legacy`. |
|||
**ЛЕЧЕНИЕ:** `update-alternatives --set iptables /usr/sbin/iptables-legacy` |
|||
@ -1,645 +0,0 @@ |
|||
Данный мануал пишется не как копипастная инструкция, а как помощь уже соображающему. |
|||
Если вы не знаете основ сетей, linux, openwrt, а пытаетесь что-то скопипастить отсюда без малейшего |
|||
понимания смысла, то маловероятно, что у вас что-то заработает. Не тратье свое время напрасно. |
|||
Цель - донести принципы как это настраивается вообще, а не указать какую буковку где вписать. |
|||
|
|||
|
|||
Есть возможность поднять свой VPN сервер ? Не хотим использовать redsocks ? |
|||
Хотим завертывать на VPN только часть трафика ? |
|||
Например, из ipset zapret только порт tcp:443, из ipban - весь трафик, не только tcp ? |
|||
Да, с VPN такое возможно. |
|||
Опишу понятийно как настраивается policy based routing в openwrt на примере wireguard. |
|||
Вместо wireguard можно использовать openvpn или любой другой. Но wireguard прекрасен сразу несколькими вещами. |
|||
Главная из которых - в разы большая скорость, даже немного превышающая ipsec. |
|||
Ведь openvpn основан на tun, а tun - всегда в разы медленнее решения в kernel mode, |
|||
и если для PC оно может быть не так актуально, для soho роутеров - более чем. |
|||
Wireguard может дать 50 mbps там, где openvpn еле тащит 10. |
|||
Но есть и дополнительное требование. Wireguard работает в ядре, значит ядро должно |
|||
быть под вашим контролем. vps на базе openvz не подойдет. Нужен xen, kvm, |
|||
любой другой вариант, где загружается ваше собственное ядро, а не используется |
|||
общее, разделяемое на множество vps. |
|||
|
|||
Понятийно необходимо выполнить следующие шаги : |
|||
1) Поднять vpn сервер. |
|||
2) Настроить vpn клиент. Результат этого шага - получение поднятого интерфейса vpn. |
|||
Будь то wireguard, openvpn или любой другой тип vpn. |
|||
3) Создать такую схему маршрутизации, при которой пакеты, помечаемые особым mark, |
|||
попадают на vpn, а остальные идут обычным способом. |
|||
4) Создать правила, выставляющие mark для всего трафика, который необходимо рулить на vpn. |
|||
Критерии могут быть любые, ограниченные лишь возможностями iptables и вашим воображением. |
|||
|
|||
Будем считать наш vpn сервер находится на ip 91.15.68.202. |
|||
Вешать его будем на udp порт 12345. На этот же порт будем вешать и клиентов. |
|||
Сервер работает под debian 9 или выше. Клиент работает под openwrt. |
|||
Для vpn отведем подсеть 192.168.254.0/24. |
|||
|
|||
--- Если нет своего сервера --- |
|||
|
|||
Но есть конфиг от VPN провайдера или от друга "Васи", который захотел с вами поделиться. |
|||
Тогда вам не надо настраивать сервер, задача упрощается. Делается невозможным вариант настройки |
|||
без masquerade (см ниже). |
|||
Из конфига вытаскиваете приватный ключ своего пира и публичный ключ сервера, ip/host/port сервера, |
|||
используете их в настройках openwrt вместо сгенеренных самостоятельно. |
|||
|
|||
--- Поднятие сервера --- |
|||
|
|||
Wireguard был включен в ядро linux с версии 5.6. |
|||
Если у вас ядро >=5.6, то достаточно установить пакет wireguard-tools. Он содержит user-mode компоненты wireguard. |
|||
Посмотрите, возможно в вашем дистрибутиве ядро по умолчанию более старое, но в репозитории |
|||
имеются бэкпорты новых версий. Лучше будет обновить ядро из репозитория. |
|||
|
|||
В репозитории может быть пакет wireguard-dkms. Это автоматизированное средство сборки |
|||
wireguard с исходников, в том числе модуль ядра. Можно пользоваться им. |
|||
|
|||
Иначе вам придется собрать wireguard самому. Ядро должно быть не ниже 3.10. |
|||
На сервере должны быть установлены заголовки ядра (linux-headers-...) и компилятор gcc. |
|||
|
|||
# git clone --depth 1 https://git.zx2c4.com/wireguard-linux-compat |
|||
# cd wireguard-linux-compat/src |
|||
# make |
|||
# strip --strip-debug wireguard.ko |
|||
# sudo make install |
|||
|
|||
wireguard основан на понятии криптороутинга. Каждый пир (сервер - тоже пир) |
|||
имеет пару открытый/закрытый ключ. Закрытый ключ остается у пира, |
|||
открытый прописывается у его партнера. Каждый пир авторизует другого |
|||
по знанию приватного ключа, соответствующего прописанному у него публичному ключу. |
|||
Протокол построен таким образом, что на все неправильные udp пакеты не следует ответа. |
|||
Не знаешь приватный ключ ? Не смог послать правильный запрос ? Долбись сколько влезет, |
|||
я тебе ничего не отвечу. Это защищает от активного пробинга со стороны DPI и просто |
|||
экономит ресурсы. |
|||
Значит первым делом нужно создать 2 пары ключей : для сервера и для клиента. |
|||
wg genkey генерит приватный ключ, wg pubkey получает из него публичный ключ. |
|||
|
|||
# wg genkey |
|||
oAUkmhoREtFQ5D5yZmeHEgYaSWCcLYlKe2jBP7EAGV0= |
|||
# echo oAUkmhoREtFQ5D5yZmeHEgYaSWCcLYlKe2jBP7EAGV0= | wg pubkey |
|||
bCdDaPYSTBZVO1HTmKD+Tztuf3PbOWGDWfz7Lb1E6C4= |
|||
# wg genkey |
|||
OKXX0TSlyjJmGt3/yHlHxi0AqjJ0vh+Msne3qEHk0VM= |
|||
# echo OKXX0TSlyjJmGt3/yHlHxi0AqjJ0vh+Msne3qEHk0VM= | wg pubkey |
|||
EELdA2XzjcKxtriOCPBXMOgxlkgpbRdIyjtc3aIpkxg= |
|||
|
|||
Пишем конфиг |
|||
--/etc/wireguard/wgvps.conf------------------- |
|||
[Interface] |
|||
PrivateKey = OKXX0TSlyjJmGt3/yHlHxi0AqjJ0vh+Msne3qEHk0VM= |
|||
ListenPort = 12345 |
|||
|
|||
[Peer] |
|||
#Endpoint = |
|||
PublicKey = bCdDaPYSTBZVO1HTmKD+Tztuf3PbOWGDWfz7Lb1E6C4= |
|||
AllowedIPs = 192.168.254.3 |
|||
PersistentKeepalive=20 |
|||
---------------------------------------------- |
|||
|
|||
Wireguard - минималистичный vpn. В нем нет никаких средств для автоконфигурации ip. |
|||
Все придется прописывать руками. |
|||
В wgvps.conf должны быть перечислены все пиры с их публичными ключами, |
|||
а так же прописаны допустимые для них ip адреса. |
|||
Назначим нашему клиенту 192.168.254.3. Сервер будет иметь ip 192.168.254.1. |
|||
Endpoint должен быть прописан хотя бы на одном пире. |
|||
Если endpoint настроен для пира, то wireguard будет периодически пытаться к нему подключиться. |
|||
В схеме клиент/сервер у сервера можно не прописывать endpoint-ы пиров, что позволит |
|||
менять ip и быть за nat. Endpoint пира настраивается динамически после успешной фазы |
|||
проверки ключа. |
|||
|
|||
Включаем маршрутизцию : |
|||
# echo net.ipv4.ip_forward = 1 >>/etc/sysctl.conf |
|||
# sysctl -p |
|||
|
|||
Интерфейс конфигурится стандартно для дебианоподобных систем : |
|||
|
|||
--/etc/network/interfaces.d/wgvps------------- |
|||
auto wgvps |
|||
iface wgvps inet static |
|||
address 192.168.254.1 |
|||
netmask 255.255.255.0 |
|||
pre-up ip link add $IFACE type wireguard |
|||
pre-up wg setconf $IFACE /etc/wireguard/$IFACE.conf |
|||
post-up iptables -t nat -A POSTROUTING -o eth0 -s 192.168.254.0/24 -j MASQUERADE |
|||
post-up iptables -A FORWARD -o eth0 -p tcp --tcp-flags SYN,RST SYN -j TCPMSS --clamp-mss-to-pmtu |
|||
post-down iptables -D FORWARD -o eth0 -p tcp --tcp-flags SYN,RST SYN -j TCPMSS --clamp-mss-to-pmtu |
|||
post-down iptables -t nat -D POSTROUTING -o eth0 -s 192.168.254.0/24 -j MASQUERADE |
|||
post-down ip link del $IFACE |
|||
---------------------------------------------- |
|||
|
|||
Поднятие через ifup wgvps, опускание через ifdown wgvps. |
|||
При поднятии интерфейса заодно настраивается nat. eth0 здесь означает интерфейс vpn сервера с инетовским ip адресом. |
|||
Если у вас какая-то система управления фаерволом, то надо настройку nat прикручивать туда. |
|||
Пример написан для простейшего случая, когда никаких ограничений нет, таблицы iptables пустые. |
|||
Чтобы посмотреть текущие настройки wireguard, запустите 'wg' без параметров. |
|||
|
|||
|
|||
--- Поднятие клиента --- |
|||
|
|||
# opkg update |
|||
# opkg install wireguard-tools |
|||
|
|||
Добавляем записи в конфиги. |
|||
|
|||
--/etc/config/network-------------------------- |
|||
config interface 'wgvps' |
|||
option proto 'wireguard' |
|||
option auto '1' |
|||
option private_key 'oAUkmhoREtFQ5D5yZmeHEgYaSWCcLYlKe2jBP7EAGV0=' |
|||
option listen_port '12345' |
|||
option metric '9' |
|||
option mtu '1420' |
|||
|
|||
config wireguard_wgvps |
|||
option public_key 'EELdA2XzjcKxtriOCPBXMOgxlkgpbRdIyjtc3aIpkxg=' |
|||
list allowed_ips '0.0.0.0/0' |
|||
option endpoint_host '91.15.68.202' |
|||
option endpoint_port '12345' |
|||
option route_allowed_ips '0' |
|||
option persistent_keepalive '20' |
|||
|
|||
config interface 'wgvps_ip' |
|||
option proto 'static' |
|||
option ifname '@wgvps' |
|||
list ipaddr '192.168.254.3/24' |
|||
|
|||
config route |
|||
option interface 'wgvps' |
|||
option target '0.0.0.0/0' |
|||
option table '100' |
|||
|
|||
config rule |
|||
option mark '0x800/0x800' |
|||
option priority '100' |
|||
option lookup '100' |
|||
------------------------------------------------ |
|||
|
|||
--/etc/config/firewall-------------------------- |
|||
config zone |
|||
option name 'tunvps' |
|||
option output 'ACCEPT' |
|||
option input 'REJECT' |
|||
option masq '1' |
|||
option mtu_fix '1' |
|||
option forward 'REJECT' |
|||
option network 'wgvps wgvps_ip' |
|||
|
|||
config forwarding |
|||
option dest 'tunvps' |
|||
option src 'lan' |
|||
|
|||
config rule |
|||
option name 'Allow-ICMP-tunvps' |
|||
option src 'tunvps' |
|||
option proto 'icmp' |
|||
option target 'ACCEPT' |
|||
|
|||
config rule |
|||
option target 'ACCEPT' |
|||
option src 'wan' |
|||
option proto 'udp' |
|||
option family 'ipv4' |
|||
option src_port '12345' |
|||
option src_ip '91.15.68.202' |
|||
option name 'WG-VPS' |
|||
------------------------------------------------ |
|||
|
|||
Что тут было сделано : |
|||
*) Настроен интерфейс wireguard. Указан собственный приватный ключ. |
|||
*) Настроен пир-партнер с указанием его публичнго ключа и endpoint (ip:port нашего сервера) |
|||
такая настройка заставит периодически долбиться на сервер по указанному ip |
|||
route_allowed_ip '0' запрещает автоматическое создание маршрута |
|||
allowed_ips '0.0.0.0/0' разрешает пакеты с любым адресом источника. |
|||
ведь мы собираемся подключаться к любым ip в инете |
|||
persistent_keepalive '20' помогает исключить дропание mapping на nat-е, если мы сидим за ним, |
|||
да и вообще полезная вещь, чтобы не было подвисших пиров |
|||
*) Статическая конфигурация ip интерфейса wgvps. |
|||
*) Маршрут default route на wgvps в отдельной таблице маршрутизации с номером 100. Аналог команды ip route add .. table 100 |
|||
*) Правило использовать таблицу 100 при выставлении в mark бита 0x800. Аналог команды ip rule. |
|||
*) Отдельная зона фаервола для VPN - 'tunvps'. В принципе ее можно не создавать, можете приписать интерфейс к зоне wan. |
|||
Но в случае с отдельной зоной можно настроить особые правила на подключения с vpn сервера в сторону клиента. |
|||
*) Разрешение форвардинга между локалкой за роутером и wgvps. |
|||
*) Разрешение принимать icmp от vpn сервера, включая пинги. ICMP жизненно важны для правильного функционирования ip сети ! |
|||
*) И желательно проткнуть дырку в фаерволе, чтобы принимать пакеты wireguard со стороны инетовского ip vpn сервера. |
|||
Конечно, оно скорее всего заработает и так, потому что первый пакет пойдет от клиента к серверу и тем самым создаст |
|||
запись в conntrack. Все дальнейшие пакеты в обе стороны подпадут под состояние ESTABLISHED и будут пропущены. |
|||
Запись будет поддерживаться за счет периодических запросов keep alive. Но если вы вдруг уберете keep alive или |
|||
выставите таймаут, превышающий udp таймаут в conntrack, то могут начаться ошибки, висы и переподключения. |
|||
Если же в фаерволе проткнута дырка, то пакеты от сервера не будут заблокированы ни при каких обстоятельствах. |
|||
|
|||
# /etc/init.d/firewall restart |
|||
# ifup wgvps |
|||
# ifconfig wgvps |
|||
# ping 192.168.254.1 |
|||
|
|||
Если все хорошо, должны ходить пинги. |
|||
С сервера не помешает : |
|||
# ping 192.168.254.3 |
|||
|
|||
|
|||
--- Подготовка zapret --- |
|||
|
|||
Выполните install_easy.sh. Он настроит режим обхода DPI. Если обход DPI не нужен - выберите MODE=filter. |
|||
Так же инсталятор заресолвит домены из ipset/zapret-hosts-user-ipban.txt и внесет крон-джоб для периодического обновления ip. |
|||
|
|||
Если вы используете в своих правилах ipset zapret, то он ресолвится и обновляется только, если выбран режим фильтрации обхода DPI по ipset. |
|||
По сути он вам нужен исключительно, если обход DPI не помогает. Например, удается как-то пробить http, но не удается пробить https. |
|||
И при этом вы хотите, чтобы на VPN направлялись только ip из скачанного ip листа, в добавок к заресолвленному ipset/zapret-hosts-user.txt. |
|||
Именно этот случай и рассмотрен в данном примере. Если это не так, то убирайте правила с портом 443 из нижеприведенных правил iptables/nftables. |
|||
Если не хотите ограничиваться листом, и хотите направлять все на порт 443, то уберите фильтры из правил iptables/nftables, |
|||
связанные с ipset/nfset "zapret". |
|||
|
|||
Фильтрация по именам доменов (MODE_FILTER=hostlist) невозможна средствами iptables/nftables. Она производится исключительно в tpws и nfqws |
|||
по результатам анализа протокола прикладного уровня, иногда достаточно сложного, связанного с дешифровкой пакета (QUIC). |
|||
Скачиваются листы с именами доменов, не ip адресами. ipset/zapret-hosts-user.txt не ресолвится, а используется как hostlist. |
|||
Потому вам нельзя расчитывать на ipset zapret. |
|||
Тем не менее при выборе этого режима фильтрации , либо вовсе при ее отсутствии (MODE_FILTER=none), ipset/zapret-hosts-user-ipban.txt |
|||
все равно ресолвится. Вы всегда можете расчитывать на ipset/nfset "ipban", "nozapret". |
|||
|
|||
"nozapret" - это ipset/nfset, связанный с системой исключения ip. Сюда загоняется все из ipset/zapret-hosts-user-exclude.txt после ресолвинга. |
|||
Его учет крайне желателен, чтобы вдруг из скачанного листа не просочились записи, например, 192.168.0.0/16 и не заставили лезть туда через VPN. |
|||
Хотя скрипты получения листов и пытаются отсечь IP локалок, но так будет намного надежнее. |
|||
|
|||
--- Маркировка трафика --- |
|||
|
|||
Завернем на vpn все из ipset zapret на tcp:443 и все из ipban. |
|||
OUTPUT относится к исходящим с роутера пакетам, PREROUTING - ко всем остальным. |
|||
Если с самого роутера ничего заруливать не надо, можно опустить часть, отвечающую за OUTPUT. |
|||
|
|||
--/etc/firewall.user---------------------------- |
|||
. /opt/zapret/init.d/openwrt/functions |
|||
|
|||
create_ipset no-update |
|||
|
|||
network_find_wan4_all wan_iface |
|||
for ext_iface in $wan_iface; do |
|||
network_get_device DEVICE $ext_iface |
|||
ipt OUTPUT -t mangle -o $DEVICE -p tcp --dport 443 -m set --match-set zapret dst -m set ! --match-set nozapret dst -j MARK --set-mark 0x800/0x800 |
|||
ipt OUTPUT -t mangle -o $DEVICE -m set --match-set ipban dst -m set ! --match-set nozapret dst -j MARK --set-mark 0x800/0x800 |
|||
done |
|||
|
|||
network_get_device DEVICE lan |
|||
ipt PREROUTING -t mangle -i $DEVICE -p tcp --dport 443 -m set --match-set zapret dst -m set ! --match-set nozapret dst -j MARK --set-mark 0x800/0x800 |
|||
ipt PREROUTING -t mangle -i $DEVICE -m set --match-set ipban dst -m set ! --match-set nozapret dst -j MARK --set-mark 0x800/0x800 |
|||
------------------------------------------------ |
|||
|
|||
# /etc/init.d/firewall restart |
|||
|
|||
--- Маркировка трафика nftables --- |
|||
|
|||
В новых openwrt по умолчанию установлен nftables, iptables отсутствует. |
|||
Есть вариант снести nftables + fw4 и заменить их на iptables + fw3. |
|||
Веб интерфейс luci понимает прозрачно и fw3, и fw4. Однако, при установке iptables и fw3 новые пакеты |
|||
будут устанавливаться без сжатия squashfs. Убедитесь, что у вас достаточно места. |
|||
Либо сразу настраивайте образ через image builder. |
|||
|
|||
Фаервол fw4 работает в одноименной nftable - "inet fw4". "inet" означает, что таблица принимает и ipv4, и ipv6. |
|||
Поскольку для маркировки трафика используется nfset, принадлежащий таблице zapret, цепочки необходимо помещать в ту же таблицу. |
|||
Для синхронизации лучше всего использовать хук |
|||
INIT_FW_POST_UP_HOOK="/etc/firewall.zapret.hook.post_up" |
|||
Параметр нужно раскоментировать в /opt/zapret/config. Далее надо создать указанный файл и дать ему chmod 755. |
|||
|
|||
--/etc/firewall.zapret.hook.post_up---------------------------- |
|||
#!/bin/sh |
|||
|
|||
ZAPRET_NFT_TABLE=zapret |
|||
|
|||
cat << EOF | nft -f - 2>/dev/null |
|||
delete chain inet $ZAPRET_NFT_TABLE my_output |
|||
delete chain inet $ZAPRET_NFT_TABLE my_prerouting |
|||
EOF |
|||
|
|||
cat << EOF | nft -f - |
|||
add chain inet $ZAPRET_NFT_TABLE my_output { type route hook output priority mangle; } |
|||
flush chain inet $ZAPRET_NFT_TABLE my_output |
|||
add rule inet $ZAPRET_NFT_TABLE my_output oifname @wanif ip daddr @ipban ip daddr != @nozapret meta mark set mark or 0x800 |
|||
add rule inet $ZAPRET_NFT_TABLE my_output oifname @wanif tcp dport 443 ip daddr @zapret ip daddr != @nozapret meta mark set mark or 0x800 |
|||
|
|||
add chain inet $ZAPRET_NFT_TABLE my_prerouting { type filter hook prerouting priority mangle; } |
|||
flush chain inet $ZAPRET_NFT_TABLE my_prerouting |
|||
add rule inet $ZAPRET_NFT_TABLE my_prerouting iifname @lanif ip daddr @ipban ip daddr != @nozapret meta mark set mark or 0x800 |
|||
add rule inet $ZAPRET_NFT_TABLE my_prerouting iifname @lanif tcp dport 443 ip daddr @zapret ip daddr != @nozapret meta mark set mark or 0x800 |
|||
EOF |
|||
------------------------------------------------ |
|||
|
|||
# /etc/init.d/zapret restart_fw |
|||
|
|||
Проверка правил : |
|||
# /etc/init.d/zapret list_table |
|||
или |
|||
# nft -t list table inet zapret |
|||
|
|||
Должны быть цепочки my_prerouting и my_output. |
|||
|
|||
Проверка заполнения nfsets : |
|||
# nft list set inet zapret zapret |
|||
# nft list set inet zapret ipban |
|||
# nft list set inet zapret nozapret |
|||
|
|||
Проверка заполнения множеств lanif, wanif, wanif6, link_local : |
|||
# /etc/init.d/zapret list_ifsets |
|||
|
|||
Должны присутствовать имена интерфейсов во множествах lanif, wanif. |
|||
wanif6 заполняется только при включении ipv6. |
|||
link_local нужен только для tpws при включении ipv6. |
|||
|
|||
--- По поводу двойного NAT --- |
|||
|
|||
В описанной конфигурации nat выполняется дважды : на роутере-клиенте происходит замена адреса источника из LAN |
|||
на 192.168.254.3 и на сервере замена 192.168.254.3 на внешний адрес сервера в инете. |
|||
Зачем так делать ? Исключительно для простоты настройки. Или на случай, если сервер wireguard не находится под вашим контролем. |
|||
Делать для вас нижеописанные настройки никто не будет с вероятностью, близкой к 100%. |
|||
Если сервер wireguard - ваш, и вы готовы чуток еще поднапрячься и не хотите двойного nat, |
|||
то можете вписать в /etc/config/firewall "masq '0'", на сервер дописать маршрут до вашей подсети lan. |
|||
Чтобы не делать это для каждого клиента, можно отвести под всех клиентов диапазон 192.168.0.0-192.168.127.255 |
|||
и прописать его одним маршрутом. |
|||
|
|||
--/etc/network/interfaces.d/wgvps------------- |
|||
post-up ip route add dev $IFACE 192.168.0.0/17 |
|||
post-down ip route del dev $IFACE 192.168.0.0/17 |
|||
---------------------------------------------- |
|||
|
|||
Так же необходимо указать wireguard дополнительные разрешенные ip для peer : |
|||
|
|||
--/etc/wireguard/wgvps.conf------------------- |
|||
[Peer] |
|||
PublicKey = bCdDaPYSTBZVO1HTmKD+Tztuf3PbOWGDWfz7Lb1E6C4= |
|||
AllowedIPs = 192.168.254.3, 192.168.2.0/24 |
|||
---------------------------------------------- |
|||
|
|||
Всем клиентам придется назначать различные диапазоны адресов в lan и индивидуально прописывать AllowedIPs |
|||
для каждого peer. |
|||
|
|||
# ifdown wgvps ; ifup wgvps |
|||
|
|||
На клиенте разрешим форвард icmp, чтобы работал пинг и корректно определялось mtu. |
|||
|
|||
--/etc/config/firewall-------------------------- |
|||
config rule |
|||
option name 'Allow-ICMP-tunvps' |
|||
option src 'tunvps' |
|||
option dest 'lan' |
|||
option proto 'icmp' |
|||
option target 'ACCEPT' |
|||
------------------------------------------------ |
|||
|
|||
Существуют еще два неочевидных нюанса. |
|||
|
|||
Первый из них касается пакетов с самого роутера (цепочка OUTPUT). |
|||
Адрес источника выбирается по особому алгоритму, если программа явно его не задала, еще до этапа iptables. |
|||
Он берется с интерфейса, куда бы пошел пакет при нормальном раскладе. |
|||
Обратная маршрутизация с VPN станет невозможной, да и wireguard такие пакеты порежет, поскольку они не вписываются в AllowedIPs. |
|||
Никаким мистическим образом автоматом source address не поменяется. |
|||
В прошлом варианте настройки проблема решалось через маскарад. Сейчас же маскарада нет. |
|||
Потому все же придется его делать в случае, когда пакет изначально направился бы через wan, |
|||
а мы его завертываем на VPN. Помечаем такие пакеты марком 0x1000. |
|||
Если вам не актуальны исходящие с самого роутера, то можно ничего не менять. |
|||
|
|||
Другой нюанс связан с обработкой проброшенных на vps портов, соединения по которым приходят как входящие с интерфейса wgvps. |
|||
Представьте себе, что вы пробросили порт 2222. Кто-то подключается с адреса 1.2.3.4. Вам приходит пакет SYN 1.2.3.4:51723=>192.168.2.2:2222. |
|||
По правилам маршрутизации он пойдет в локалку. 192.168.2.2 его обработает, ответит пакетом ACK 192.168.2.2:2222=>1.2.3.4:51723. |
|||
Этот пакет придет на роутер. И куда он дальше пойдет ? Если он не занесен в ipban, то согласно правилам машрутизации |
|||
он пойдет по WAN интерфейсу, а не по исходному wgvps. |
|||
Чтобы решить эту проблему, необходимо воспользоваться CONNMARK. Существуют 2 отдельных марка : fwmark и connmark. |
|||
connmark относится к соединению, fwmark - к пакету. Трэкингом соединений занимается conntrack. |
|||
Посмотреть его таблицу можно командой "conntrack -L". Там же найдете connmark : mark=xxxx. |
|||
Как только видим приходящий с wgvps пакет с новым соединением, отмечаем его connmark как 0x800/0x800. |
|||
При этом fwmark не меняется, иначе бы пакет тут же бы завернулся обратно на wgvps согласно ip rule. |
|||
Если к нам приходит пакет с какого-то другого интерфейса, то восстанавливаем его connmark в fwmark по маске 0x800. |
|||
И теперь он подпадает под правило ip rule, заворачиваясь на wgvps, что и требовалось. |
|||
|
|||
Альтернативное решение - использовать на VPSке для проброса портов не только DNAT, но и SNAT/MASQUERADE. Тогда source address |
|||
будет заменен на 192.168.254.1. Он по таблице маршрутизации пойдет на wgvps. Но в этом случае клиентские программы, |
|||
на которые осуществляется проброс портов, не будут видеть реальный IP подключенца. |
|||
|
|||
--/etc/firewall.user---------------------------- |
|||
. /opt/zapret/init.d/openwrt/functions |
|||
|
|||
create_ipset no-update |
|||
|
|||
network_find_wan4_all wan_iface |
|||
for ext_iface in $wan_iface; do |
|||
network_get_device DEVICE $ext_iface |
|||
ipt OUTPUT -t mangle -o $DEVICE -p tcp --dport 443 -m set --match-set zapret dst -m set ! --match-set nozapret dst -j MARK --set-mark 0x800/0x800 |
|||
ipt OUTPUT -t mangle -o $DEVICE -m set --match-set ipban dst -m set ! --match-set nozapret dst -j MARK --set-mark 0x800/0x800 |
|||
ipt OUTPUT -t mangle -o $DEVICE -j MARK --set-mark 0x1000/0x1000 |
|||
done |
|||
|
|||
network_get_device DEVICE lan |
|||
ipt PREROUTING -t mangle -i $DEVICE -p tcp --dport 443 -m set --match-set zapret dst -m set ! --match-set nozapret dst -j MARK --set-mark 0x800/0x800 |
|||
ipt PREROUTING -t mangle -i $DEVICE -m set --match-set ipban dst -m set ! --match-set nozapret dst -j MARK --set-mark 0x800/0x800 |
|||
|
|||
# do masquerade for OUTPUT to ensure correct outgoing address |
|||
ipt postrouting_tunvps_rule -t nat -m mark --mark 0x1000/0x1000 -j MASQUERADE |
|||
|
|||
# incoming from wgvps |
|||
network_get_device DEVICE wgvps |
|||
ipt PREROUTING -t mangle ! -i $DEVICE -j CONNMARK --restore-mark --nfmask 0x800 --ctmask 0x800 |
|||
ipt PREROUTING -t mangle -i $DEVICE -m conntrack --ctstate NEW -j CONNMARK --set-mark 0x800/0x800 |
|||
------------------------------------------------ |
|||
|
|||
# /etc/init.d/firewall restart |
|||
|
|||
Вариант nftables : |
|||
|
|||
--/etc/firewall.zapret.hook.post_up---------------------------- |
|||
#!/bin/sh |
|||
|
|||
ZAPRET_NFT_TABLE=zapret |
|||
DEVICE=wgvps |
|||
|
|||
cat << EOF | nft -f - 2>/dev/null |
|||
delete chain inet $ZAPRET_NFT_TABLE my_output |
|||
delete chain inet $ZAPRET_NFT_TABLE my_prerouting |
|||
delete chain inet $ZAPRET_NFT_TABLE my_nat |
|||
EOF |
|||
|
|||
cat << EOF | nft -f - |
|||
add chain inet $ZAPRET_NFT_TABLE my_output { type route hook output priority mangle; } |
|||
flush chain inet $ZAPRET_NFT_TABLE my_output |
|||
add rule inet $ZAPRET_NFT_TABLE my_output oifname @wanif ip daddr @ipban ip daddr != @nozapret meta mark set mark or 0x800 |
|||
add rule inet $ZAPRET_NFT_TABLE my_output oifname @wanif tcp dport 443 ip daddr @zapret ip daddr != @nozapret meta mark set mark or 0x800 |
|||
add rule inet $ZAPRET_NFT_TABLE my_output oifname @wanif meta mark set mark or 0x1000 |
|||
|
|||
add chain inet $ZAPRET_NFT_TABLE my_prerouting { type filter hook prerouting priority mangle; } |
|||
flush chain inet $ZAPRET_NFT_TABLE my_prerouting |
|||
add rule inet $ZAPRET_NFT_TABLE my_prerouting iifname $DEVICE ct state new ct mark set ct mark or 0x800 |
|||
add rule inet $ZAPRET_NFT_TABLE my_prerouting iifname != $DEVICE meta mark set ct mark and 0x800 |
|||
add rule inet $ZAPRET_NFT_TABLE my_prerouting iifname @lanif ip daddr @ipban ip daddr != @nozapret meta mark set mark or 0x800 |
|||
add rule inet $ZAPRET_NFT_TABLE my_prerouting iifname @lanif tcp dport 443 ip daddr @zapret ip daddr != @nozapret meta mark set mark or 0x800 |
|||
|
|||
add chain inet $ZAPRET_NFT_TABLE my_nat { type nat hook postrouting priority 100 ; } |
|||
flush chain inet $ZAPRET_NFT_TABLE my_nat |
|||
add rule inet $ZAPRET_NFT_TABLE my_nat oifname $DEVICE mark and 0x1000 == 0x1000 masquerade |
|||
EOF |
|||
------------------------------------------------ |
|||
|
|||
# /etc/init.d/zapret restart_fw |
|||
|
|||
К сожалению, здесь возможности nftables немного хромают. Полноценного эквивалента CONNMARK --restore-mark --nfmask |
|||
не существует. Оригинал iptables предполагал копирование одного бита 0x800 из connmark в mark. |
|||
Лучшее, что можно сделать в nftables, это копирование одного бита с занулением всех остальных. |
|||
Сложные выражения типа "meta mark set mark and ~0x800 or (ct mark and 0x800)" nft не понимает. |
|||
Об этом же говорит попытка перевода через iptables-translate. |
|||
|
|||
Сейчас уже можно с vpn сервера пингануть ip адрес внутри локалки клиента. Пинги должны ходить. |
|||
|
|||
Отсутствие двойного NAT значительно облегчает проброс портов с внешнего IP vpn сервера в локалку какого-либо клиента. |
|||
Для этого надо выполнить 2 действия : добавить разрешение в фаервол на клиенте и сделать dnat на сервере. |
|||
Пример форварда портов 5001 и 5201 на 192.168.2.2 : |
|||
|
|||
--/etc/config/firewall-------------------------- |
|||
config rule |
|||
option target 'ACCEPT' |
|||
option src 'tunvps' |
|||
option dest 'lan' |
|||
option proto 'tcp udp' |
|||
option dest_port '5001 5201' |
|||
option dest_ip '192.168.2.2' |
|||
option name 'IPERF' |
|||
------------------------------------------------ |
|||
|
|||
# /etc/init.d/firewall restart |
|||
# /etc/init.d/zapret restart_fw |
|||
|
|||
--/etc/network/interfaces.d/wgvps------------- |
|||
post-up iptables -t nat -A PREROUTING -i eth0 -p tcp -m multiport --dports 5001,5201 -j DNAT --to-destination 192.168.2.2 |
|||
post-up iptables -t nat -A PREROUTING -i eth0 -p udp -m multiport --dports 5001,5201 -j DNAT --to-destination 192.168.2.2 |
|||
post-down iptables -t nat -D PREROUTING -i eth0 -p tcp -m multiport --dports 5001,5201 -j DNAT --to-destination 192.168.2.2 |
|||
post-down iptables -t nat -D PREROUTING -i eth0 -p udp -m multiport --dports 5001,5201 -j DNAT --to-destination 192.168.2.2 |
|||
---------------------------------------------- |
|||
|
|||
# ifdown wgvps ; ifup wgvps |
|||
|
|||
Пример приведен для iperf и iperf3, чтобы показать как пробрасывать несколько портов tcp+udp с минимальным количеством команд. |
|||
Проброс tcp и udp порта так же необходим для полноценной работы bittorrent клиента, чтобы работали входящие. |
|||
|
|||
--- Как мне отправлять на vpn весь трафик с bittorrent ? --- |
|||
|
|||
Можно поступить так : посмотрите порт в настройках torrent клиента, убедитесь, что не поставлено "случайный порт", |
|||
добавьте на роутер правило маркировки по порту источника. |
|||
Но мне предпочтительно иное решение. На windows есть замечательная возможность |
|||
прописать правило установки поля качества обслуживания в заголовках ip пакетов в зависимости от процесса-источника. |
|||
Для windows 7/2008R2 необходимо будет установить ключик реестра и перезагрузить комп : |
|||
# reg add HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\services\Tcpip\QoS /v "Do not use NLA" /t REG_SZ /d "1" |
|||
Редактировать политику можно в : gpedit.msc -> Computer Configuration -> Windows Settings -> Policy-based QoS |
|||
На win 10 ключик реестра больше не работает, правила qos в gpedit применяются только для профиля домена. |
|||
Необходимо пользоваться командой powershell New-NetQosPolicy. Гуглите хелп по ней. Пример : |
|||
# powershell New-NetQosPolicy -Name "torrent" -AppPathNameMatchCondition "qbittorrent.exe" -DSCPAction 1 |
|||
Однозначно требуется проверка в wireshark или netmon успешности установки поля dscp. Если там по-прежнему 0x00, |
|||
значит что-то не сработало. 0x04 означает DSCP=1 (dscp находится в старших 6 битах). |
|||
|
|||
На роутере в фаер прописываем правило : |
|||
|
|||
--/etc/config/firewall-------------------------- |
|||
config rule |
|||
option target 'MARK' |
|||
option src 'lan' |
|||
option proto 'all' |
|||
option extra '-m dscp --dscp 1' |
|||
option name 'route-dscp-1' |
|||
option set_mark '0x0800/0x0800' |
|||
------------------------------------------------ |
|||
|
|||
# /etc/init.d/firewall restart |
|||
|
|||
Теперь все с полем dscp "1" идет на vpn. Клиент сам решает какой трафик ему нужно забрасывать |
|||
на vpn, перенастраивать роутер не нужно. |
|||
На linux клиенте проще всего будет выставлять dscp в iptables по номеру порта источника : |
|||
|
|||
--/etc/rc.local--------------------------------- |
|||
iptables -A OUTPUT -t mangle -p tcp --sport 23444 -j DSCP --set-dscp 1 |
|||
iptables -A OUTPUT -t mangle -p udp --sport 23444 -j DSCP --set-dscp 1 |
|||
------------------------------------------------ |
|||
|
|||
можно привязываться к pid процесса, но тогда нужно перенастраивать iptables при каждом перезапуске |
|||
торент клиента, это требует рута, и все становится очень неудобно. |
|||
|
|||
|
|||
--- Автоматизация проброса портов через miniupnd --- |
|||
|
|||
Да, его тоже можно использовать на vps. Только как всегда есть нюансы. |
|||
|
|||
miniupnpd поддерживает 3 протокола IGD : upnp,nat-pmp и pcp. |
|||
upnp и pcp работают через мультикаст, который не пройдет через wgvps. |
|||
nat-pmp работает через посылку специальных сообщений на udp:5351 на default gateway. |
|||
Обычно их обслуживает miniupnpd на роутере. При создании lease miniupnpd добавляет |
|||
правила для проброса портов в цепочку iptables MINIUPNPD, при потери lease - убирает. |
|||
|
|||
udp:5351 можно перенаправить на vpn сервер через DNAT, чтобы их обрабатывал miniupnpd там. |
|||
Но вы должны иметь однозначный критерий перенаправления. |
|||
Если вы решили завернуть на vpn все, то проблем нет. Пробрасываем udp:5351 безусловно. |
|||
Если у вас идет перенаправление только с торрент, то необходимо к условию перенаправления |
|||
добавить условия, выделяющие torrent трафик из прочего. Или по dscp, или по sport. |
|||
Чтобы запросы от остальных программ обрабатывались miniupnpd на роутере. |
|||
Если какая-то программа создаст lease не там, где нужно, то входящий трафик до нее не дойдет. |
|||
|
|||
На роутере стоит запретить протокол upnp, чтобы торрент клиент не удовлетворился запросом, |
|||
обслуженным по upnp на роутере, и пытался использовать nat-pmp. |
|||
|
|||
--/etc/config/upnp-------------------------- |
|||
config upnpd 'config' |
|||
..... |
|||
option enable_upnp '0' |
|||
------------------------------------------------ |
|||
|
|||
/etc/init.d/miniupnpd restart |
|||
|
|||
Делаем проброс порта на роутере. |
|||
Для простоты изложения будем считать, что на vpn у нас завернут весь трафик. |
|||
Если это не так, то следует добавить фильтр в "config redirect". |
|||
Заодно выделяем диапазон портов для торрент клиентов. |
|||
Порт в торент клиенте следует прописать какой-то из этого диапазона. |
|||
|
|||
------------------------------------------------ |
|||
config redirect |
|||
option enabled '1' |
|||
option target 'DNAT' |
|||
option src 'lan' |
|||
option dest 'tunvps' |
|||
option proto 'udp' |
|||
option src_dport '5351' |
|||
option dest_ip '192.168.254.1' |
|||
option dest_port '5351' |
|||
option name 'NAT-PMP' |
|||
option reflection '0' |
|||
config rule |
|||
option enabled '1' |
|||
option target 'ACCEPT' |
|||
option src 'tunvps' |
|||
option dest 'lan' |
|||
option name 'tunvps-torrent' |
|||
option dest_port '28000-28009' |
|||
------------------------------------------------ |
|||
|
|||
/etc/init.d/firewall reload |
|||
|
|||
|
|||
На сервере : |
|||
|
|||
apt install miniupnpd |
|||
|
|||
--- /etc/miniupnpd/miniupnpd.conf -------- |
|||
enable_natpmp=yes |
|||
enable_upnp=no |
|||
lease_file=/var/log/upnp.leases |
|||
system_uptime=yes |
|||
clean_ruleset_threshold=10 |
|||
clean_ruleset_interval=600 |
|||
force_igd_desc_v1=no |
|||
listening_ip=192.168.254.1/16 |
|||
ext_ifname=eth0 |
|||
------------------------------------------ |
|||
|
|||
systemctl restart miniupnpd |
|||
|
|||
listening_ip прописан именно таким образом, чтобы обозначить диапазон разрешенных IP. |
|||
С других IP он не будет обрабатывать запросы на редирект. |
|||
В ext_ifname впишите название inet интерфейса на сервере. |
|||
|
|||
Запускаем торрент клиент. Попутно смотрим в tcpdump весь путь udp:5351 до сервера и обратно. |
|||
Смотрим syslog сервера на ругань от miniupnpd. |
|||
Если все ок, то можем проверить редиректы : iptables -t nat -nL MINIUPNPD |
|||
С какого-нибудь другого хоста (не vpn сервер, не ваше подключение) можно попробовать telnet-нуться на проброшенный порт. |
|||
Должно установиться соединение. Или качайте торент и смотрите в пирах флаг "I" (incoming). |
|||
Если "I" есть и по ним идет закачка, значит все в порядке. |
|||
|
|||
ОСОБЕННОСТЬ НОВЫХ DEBIAN : по умолчанию используются iptables-nft. miniupnpd работает с iptables-legacy. |
|||
ЛЕЧЕНИЕ : update-alternatives --set iptables /usr/sbin/iptables-legacy |
|||
Loading…
Reference in new issue