mirror of
https://github.com/bol-van/zapret.git
synced 2024-12-02 14:40:52 +03:00
hostspell, openwrt procd, beeline ISP fix
This commit is contained in:
parent
918a088527
commit
3bb71b42a0
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
@ -70,3 +70,10 @@ 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
|
||||
|
@ -4,11 +4,15 @@
|
||||
# CHOOSE ISP HERE. UNCOMMENT ONLY ONE LINE.
|
||||
#ISP=mns
|
||||
#ISP=rt
|
||||
#ISP=beeline
|
||||
ISP=beeline
|
||||
#ISP=domru
|
||||
ISP=tiera
|
||||
#ISP=tiera
|
||||
#ISP=none
|
||||
|
||||
USE_PROCD=1
|
||||
# start betfore firewall - we need ipset populated
|
||||
START=18
|
||||
|
||||
# !!!!! in openwrt you need to add firewall rules manually to /etc/firewall.user
|
||||
|
||||
QNUM=200
|
||||
@ -19,9 +23,6 @@ TPWS=/opt/zapret/tpws/tpws
|
||||
IPSET_CR=/opt/zapret/ipset/create_ipset.sh
|
||||
TPWS_USER=daemon
|
||||
|
||||
# start betfore firewall - we need ipset populated
|
||||
START=18
|
||||
|
||||
|
||||
# must execute /etc/firewall.user on every firewall reload
|
||||
set_firewall_user_reload() {
|
||||
@ -53,7 +54,7 @@ get_daemon() {
|
||||
DAEMON=$NFQWS
|
||||
;;
|
||||
beeline)
|
||||
DAEMON_OPTS="--qnum=$QNUM --hostcase"
|
||||
DAEMON_OPTS="--qnum=$QNUM --hostspell=HOST"
|
||||
DAEMON=$NFQWS
|
||||
;;
|
||||
domru)
|
||||
@ -68,7 +69,7 @@ get_daemon() {
|
||||
}
|
||||
|
||||
|
||||
start() {
|
||||
start_service() {
|
||||
set_firewall_user_reload
|
||||
echo "Creating ipset"
|
||||
($IPSET_CR)
|
||||
@ -76,14 +77,8 @@ start() {
|
||||
get_daemon
|
||||
[ -n "$DAEMON" ] && {
|
||||
echo "Starting $DAEMON"
|
||||
service_start $DAEMON --daemon $DAEMON_OPTS
|
||||
procd_open_instance
|
||||
procd_set_param command $DAEMON $DAEMON_OPTS
|
||||
procd_close_instance
|
||||
}
|
||||
}
|
||||
|
||||
stop() {
|
||||
get_daemon
|
||||
[ -n "$DAEMON" ] && {
|
||||
service_stop $DAEMON
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -45,10 +45,6 @@ pre-start script
|
||||
iptables -t raw -I PREROUTING -p udp --sport 53 -m string --hex-string "|5cfff164|" --algo bm -j DROP --from 40 --to 300
|
||||
iptables -t raw -C PREROUTING -p udp --sport 53 -m string --hex-string "|2a022698a00000000000000000000064|" --algo bm -j DROP --from 40 --to 300 ||
|
||||
iptables -t raw -I PREROUTING -p udp --sport 53 -m string --hex-string "|2a022698a00000000000000000000064|" --algo bm -j DROP --from 40 --to 300
|
||||
iptables -t raw -C PREROUTING -p udp --sport 53 -m string --hex-string "|5cfff16e|" --algo bm -j DROP --from 40 --to 300 ||
|
||||
iptables -t raw -I PREROUTING -p udp --sport 53 -m string --hex-string "|5cfff16e|" --algo bm -j DROP --from 40 --to 300
|
||||
iptables -t raw -C PREROUTING -p udp --sport 53 -m string --hex-string "|2a022698a00000000000000000000110|" --algo bm -j DROP --from 40 --to 300 ||
|
||||
iptables -t raw -I PREROUTING -p udp --sport 53 -m string --hex-string "|2a022698a00000000000000000000110|" --algo bm -j DROP --from 40 --to 300
|
||||
;;
|
||||
tiera)
|
||||
adduser --disabled-login --no-create-home --system --quiet $TPWS_USER
|
||||
@ -73,7 +69,7 @@ script
|
||||
;;
|
||||
beeline)
|
||||
NFEXE=$NFQWS
|
||||
NFARG="--qnum $QNUM --hostcase"
|
||||
NFARG="--qnum $QNUM --hostspell=HOST"
|
||||
;;
|
||||
domru)
|
||||
NFEXE=$TPWS
|
||||
@ -102,8 +98,6 @@ pre-stop script
|
||||
iptables -t nat -D OUTPUT -p tcp --dport 80 -m owner ! --uid-owner $TPWS_USER -m set --match-set zapret dst -j DNAT --to 127.0.0.1:$TPPORT
|
||||
iptables -t raw -D PREROUTING -p udp --sport 53 -m string --hex-string "|5cfff164|" --algo bm -j DROP --from 40 --to 300
|
||||
iptables -t raw -D PREROUTING -p udp --sport 53 -m string --hex-string "|2a022698a00000000000000000000064|" --algo bm -j DROP --from 40 --to 300
|
||||
iptables -t raw -D PREROUTING -p udp --sport 53 -m string --hex-string "|5cfff16e|" --algo bm -j DROP --from 40 --to 300
|
||||
iptables -t raw -D PREROUTING -p udp --sport 53 -m string --hex-string "|2a022698a00000000000000000000110|" --algo bm -j DROP --from 40 --to 300
|
||||
;;
|
||||
tiera)
|
||||
sysctl -w net.ipv4.conf.$SLAVE_ETH.route_localnet=0
|
||||
|
25
nfq/nfqws.c
25
nfq/nfqws.c
@ -248,6 +248,7 @@ struct cbdata_s
|
||||
int wsize;
|
||||
int qnum;
|
||||
bool hostcase;
|
||||
char hostspell[4];
|
||||
};
|
||||
|
||||
// ret: false - not modified, true - modified
|
||||
@ -291,8 +292,8 @@ bool processPacketData(unsigned char *data,int len,const struct cbdata_s *cbdata
|
||||
}
|
||||
if (cbdata->hostcase && (p = find_bin(data,len,"\r\nHost: ",8)))
|
||||
{
|
||||
printf("modifying Host: => host:\n");
|
||||
p[2]='h'; // "Host:" => "host:"
|
||||
printf("modifying Host: => %c%c%c%c:\n",cbdata->hostspell[0],cbdata->hostspell[1],cbdata->hostspell[2],cbdata->hostspell[3]);
|
||||
memcpy(p+2,cbdata->hostspell,4);
|
||||
bRet = true;
|
||||
}
|
||||
if (bRet)
|
||||
@ -349,7 +350,7 @@ bool droproot(uid_t uid, gid_t gid)
|
||||
|
||||
void exithelp()
|
||||
{
|
||||
printf(" --qnum=<nfqueue_number>\n --wsize=<window_size>\t; set window size. 0 = do not modify\n --hostcase\t\t; change Host: => host:\n --daemon\t\t; daemonize\n");
|
||||
printf(" --qnum=<nfqueue_number>\n --wsize=<window_size>\t; set window size. 0 = do not modify\n --hostcase\t\t; change Host: => host:\n --hostspell\t\t; exact spelling of \"Host\" header. must be 4 chars. default is \"host\"\n --daemon\t\t; daemonize\n");
|
||||
exit(1);
|
||||
}
|
||||
|
||||
@ -368,12 +369,15 @@ int main(int argc, char **argv)
|
||||
gid_t gid;
|
||||
|
||||
memset(&cbdata,0,sizeof(cbdata));
|
||||
memcpy(cbdata.hostspell,"host",4); // default hostspell
|
||||
|
||||
const struct option long_options[] = {
|
||||
{"qnum",required_argument,0,0}, // optidx=0
|
||||
{"daemon",no_argument,0,0}, // optidx=1
|
||||
{"wsize",required_argument,0,0}, // optidx=2
|
||||
{"hostcase",no_argument,0,0}, // optidx=3
|
||||
{"user",required_argument,0,0}, // optidx=4
|
||||
{"hostspell",required_argument,0,0}, // optidx=4
|
||||
{"user",required_argument,0,0}, // optidx=5
|
||||
{NULL,0,NULL,0}
|
||||
};
|
||||
if (argc<2) exithelp();
|
||||
@ -397,14 +401,23 @@ int main(int argc, char **argv)
|
||||
cbdata.wsize=atoi(optarg);
|
||||
if (cbdata.wsize<0 || cbdata.wsize>65535)
|
||||
{
|
||||
fprintf(stdout,"bad qnum\n");
|
||||
fprintf(stdout,"bad wsize\n");
|
||||
exit(1);
|
||||
}
|
||||
break;
|
||||
case 3: /* hostcase */
|
||||
cbdata.hostcase = true;
|
||||
break;
|
||||
case 4: /* user */
|
||||
case 4: /* hostspell */
|
||||
if (strlen(optarg)!=4)
|
||||
{
|
||||
fprintf(stdout,"hostspell must be exactly 4 chars long\n");
|
||||
exit(1);
|
||||
}
|
||||
cbdata.hostcase = true;
|
||||
memcpy(cbdata.hostspell,optarg,4);
|
||||
break;
|
||||
case 5: /* user */
|
||||
{
|
||||
struct passwd *pwd = getpwnam(optarg);
|
||||
if (!pwd)
|
||||
|
10
readme.txt
10
readme.txt
@ -1,4 +1,4 @@
|
||||
zapret v.14
|
||||
zapret v.15
|
||||
|
||||
Для чего это надо
|
||||
-----------------
|
||||
@ -99,7 +99,8 @@ nfqws
|
||||
--daemon ; демонизировать прогу
|
||||
--qnum=200 ; номер очереди
|
||||
--wsize=4 ; менять tcp window size на указанный размер
|
||||
--hostcase ; менять регистр заголовка "Host:"
|
||||
--hostcase ; менять регистр заголовка "Host:" по умолчанию на "host:".
|
||||
--hostspell=HoST ; точное написание заголовка Host (можно "HOST" или "HoSt"). автоматом включает --hostcase
|
||||
Параметры манипуляции могут сочетаться в любых комбинациях.
|
||||
|
||||
tpws
|
||||
@ -112,7 +113,8 @@ tpws - это transparent proxy.
|
||||
--user=<username> ; менять uid процесса
|
||||
--split-http-req=method|host ; способ разделения http запросов на сегменты : около метода (GET,POST) или около заголовка Host
|
||||
--split-pos=<offset> ; делить все посылы на сегменты в указанной позиции. Если отсыл длинее 8Kb (размер буфера приема), то будет разделен каждый блок по 8Kb.
|
||||
--hostcase ; замена "Host:" => "host:"
|
||||
--hostcase ; менять регистр заголовка "Host:". по умолчанию на "host:".
|
||||
--hostspell=HoST ; точное написание заголовка Host (можно "HOST" или "HoSt"). автоматом включает --hostcase
|
||||
--hostdot ; добавление точки после имени хоста : "Host: kinozal.tv."
|
||||
--methodspace ; добавить пробел после метода : "GET /" => "GET /"
|
||||
Параметры манипуляции могут сочетаться в любых комбинациях.
|
||||
@ -122,7 +124,7 @@ tpws - это transparent proxy.
|
||||
----------
|
||||
|
||||
mns.ru : нужна замена window size на 4
|
||||
beeline (corbina) : нужна замена регистра "Host:" на протяжении всей http сессии
|
||||
beeline (corbina) : нужна замена регистра "Host:" на протяжении всей http сессии. С некоторых пор "host" не работает, но работают другие регистры букв.
|
||||
dom.ru : нужно проксирование HTTP сессий через tpws с заменой регистра "Host:" и разделение TCP сегментов на хедере "Host:".
|
||||
Ахтунг ! Домру блокирует все поддомены заблоченого домена. IP адреса всевозможных поддоменов узнать невозможно из реестра
|
||||
блокировок, поэтому если вдруг на каком-то сайте вылезает блокировочный баннер, то идите в консоль firefox, вкладка network.
|
||||
|
42
tpws/tpws.c
42
tpws/tpws.c
@ -34,6 +34,7 @@ struct params_s
|
||||
uint16_t port;
|
||||
bool daemon;
|
||||
bool hostcase,hostdot,methodspace;
|
||||
char hostspell[4];
|
||||
enum splithttpreq split_http_req;
|
||||
int split_pos;
|
||||
int maxconn;
|
||||
@ -123,7 +124,7 @@ bool handle_epollin(tproxy_conn_t *conn,int *data_transferred){
|
||||
if (p=find_bin(buf,bs,*item,l))
|
||||
{
|
||||
pos = p-buf;
|
||||
printf("Found http method '%s' at pos %d. Adding extra space.\n",*item,(unsigned int)pos);
|
||||
printf("Found http method '%s' at pos %zd. Adding extra space.\n",*item,pos);
|
||||
p += l-1;
|
||||
pos += l-1;
|
||||
memmove(p+1,p,bs-pos);
|
||||
@ -144,7 +145,7 @@ bool handle_epollin(tproxy_conn_t *conn,int *data_transferred){
|
||||
if (p<(buf+bs))
|
||||
{
|
||||
pos = p-buf;
|
||||
printf("Adding dot to host name at pos %d\n",(unsigned int)pos);
|
||||
printf("Adding dot to host name at pos %zd\n",pos);
|
||||
memmove(p+1,p,bs-pos);
|
||||
*p = '.'; // insert dot
|
||||
bs++; // block will grow by 1 byte
|
||||
@ -193,7 +194,7 @@ bool handle_epollin(tproxy_conn_t *conn,int *data_transferred){
|
||||
if (p=find_bin(buf,bs,*split_item,l))
|
||||
{
|
||||
split_pos = p-buf;
|
||||
printf("Found split item '%s' at pos %d\n",*split_item,(unsigned int)split_pos);
|
||||
printf("Found split item '%s' at pos %zd\n",*split_item,split_pos);
|
||||
split_pos += l-1;
|
||||
break;
|
||||
}
|
||||
@ -203,13 +204,13 @@ bool handle_epollin(tproxy_conn_t *conn,int *data_transferred){
|
||||
{
|
||||
if (phost || (phost=find_bin(buf,bs,"\r\nHost: ",8)))
|
||||
{
|
||||
printf("Changing 'Host:' => 'host:' at pos %d\n",(unsigned int)(phost-buf));
|
||||
phost[2]='h';
|
||||
printf("Changing 'Host:' => '%c%c%c%c:' at pos %zd\n",params.hostspell[0],params.hostspell[1],params.hostspell[2],params.hostspell[3],phost-buf+2);
|
||||
memcpy(phost+2,params.hostspell,4);
|
||||
}
|
||||
}
|
||||
if (split_pos)
|
||||
{
|
||||
printf("Splitting at pos %d\n",(unsigned int)split_pos);
|
||||
printf("Splitting at pos %zd\n",split_pos);
|
||||
wr=send_with_flush(fd_out,buf,split_pos,0);
|
||||
if (wr>=0)
|
||||
wr=send(fd_out,buf+split_pos,bs-split_pos,0);
|
||||
@ -393,7 +394,7 @@ int8_t block_sigpipe(){
|
||||
|
||||
void exithelp()
|
||||
{
|
||||
printf(" --bind-addr=<ipv4_addr>|<ipv6_addr>\n --port=<port>\n --maxconn=<max_connections>\n --split-http-req=method|host\n --split-pos=<numeric_offset>\t; split at specified pos. invalidates split-http-req.\n --hostcase\t\t; change Host: => host:\n --hostdot\t\t; add \".\" after Host: name\n --methodspace\t\t; add extra space after method\n --daemon\t\t; daemonize\n --user=<username>\t; drop root privs\n");
|
||||
printf(" --bind-addr=<ipv4_addr>|<ipv6_addr>\n --port=<port>\n --maxconn=<max_connections>\n --split-http-req=method|host\n --split-pos=<numeric_offset>\t; split at specified pos. invalidates split-http-req.\n --hostcase\t\t; change Host: => host:\n --hostspell\t\t; exact spelling of \"Host\" header. must be 4 chars. default is \"host\"\n --hostdot\t\t; add \".\" after Host: name\n --methodspace\t\t; add extra space after method\n --daemon\t\t; daemonize\n --user=<username>\t; drop root privs\n");
|
||||
exit(1);
|
||||
}
|
||||
|
||||
@ -403,6 +404,7 @@ void parse_params(int argc, char *argv[])
|
||||
int v,i;
|
||||
|
||||
memset(¶ms,0,sizeof(params));
|
||||
memcpy(params.hostspell,"host",4); // default hostspell
|
||||
params.maxconn = DEFAULT_MAX_CONN;
|
||||
|
||||
const struct option long_options[] = {
|
||||
@ -414,10 +416,11 @@ void parse_params(int argc, char *argv[])
|
||||
{"user",required_argument,0,0},// optidx=5
|
||||
{"maxconn",required_argument,0,0},// optidx=6
|
||||
{"hostcase",no_argument,0,0},// optidx=7
|
||||
{"hostdot",no_argument,0,0},// optidx=8
|
||||
{"split-http-req",required_argument,0,0},// optidx=9
|
||||
{"split-pos",required_argument,0,0},// optidx=10
|
||||
{"methodspace",no_argument,0,0},// optidx=11
|
||||
{"hostspell",required_argument,0,0},// optidx=8
|
||||
{"hostdot",no_argument,0,0},// optidx=9
|
||||
{"split-http-req",required_argument,0,0},// optidx=10
|
||||
{"split-pos",required_argument,0,0},// optidx=11
|
||||
{"methodspace",no_argument,0,0},// optidx=12
|
||||
{NULL,0,NULL,0}
|
||||
};
|
||||
while ((v=getopt_long_only(argc,argv,"",long_options,&option_index))!=-1)
|
||||
@ -468,10 +471,19 @@ void parse_params(int argc, char *argv[])
|
||||
case 7: /* hostcase */
|
||||
params.hostcase = true;
|
||||
break;
|
||||
case 8: /* hostdot */
|
||||
case 8: /* hostspell */
|
||||
if (strlen(optarg)!=4)
|
||||
{
|
||||
fprintf(stdout,"hostspell must be exactly 4 chars long\n");
|
||||
exit(1);
|
||||
}
|
||||
params.hostcase = true;
|
||||
memcpy(params.hostspell,optarg,4);
|
||||
break;
|
||||
case 9: /* hostdot */
|
||||
params.hostdot = true;
|
||||
break;
|
||||
case 9: /* split-http-req */
|
||||
case 10: /* split-http-req */
|
||||
if (!strcmp(optarg,"method"))
|
||||
params.split_http_req = split_method;
|
||||
else if (!strcmp(optarg,"host"))
|
||||
@ -482,7 +494,7 @@ void parse_params(int argc, char *argv[])
|
||||
exit(1);
|
||||
}
|
||||
break;
|
||||
case 10: /* split-pos */
|
||||
case 11: /* split-pos */
|
||||
i = atoi(optarg);
|
||||
if (i)
|
||||
params.split_pos = i;
|
||||
@ -492,7 +504,7 @@ void parse_params(int argc, char *argv[])
|
||||
exit(1);
|
||||
}
|
||||
break;
|
||||
case 11: /* methodspace */
|
||||
case 12: /* methodspace */
|
||||
params.methodspace = true;
|
||||
break;
|
||||
}
|
||||
|
@ -1,17 +1,16 @@
|
||||
#define _GNU_SOURCE
|
||||
#include <stdio.h>
|
||||
#include <stdint.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <errno.h>
|
||||
#include <unistd.h>
|
||||
#include <sys/types.h>
|
||||
#include <sys/socket.h>
|
||||
#include <arpa/inet.h>
|
||||
#include <netinet/ip.h>
|
||||
#include <errno.h>
|
||||
#include <string.h>
|
||||
#include <sys/epoll.h>
|
||||
#include <fcntl.h>
|
||||
#include <stdlib.h>
|
||||
#include "linux/netfilter_ipv4.h"
|
||||
#include <linux/netfilter_ipv4.h>
|
||||
#include <ifaddrs.h>
|
||||
|
||||
#include "tpws_conn.h"
|
||||
|
Loading…
Reference in New Issue
Block a user