Compare commits
40 Commits
| Author | SHA1 | Date |
|---|---|---|
|
|
d9bf7c3ccd | |
|
|
ad18fb9854 | |
|
|
bc82203364 | |
|
|
a1fb62ff82 | |
|
|
46e6c8f2db | |
|
|
905d3c98a6 | |
|
|
b08836de50 | |
|
|
cf1f2a8674 | |
|
|
16464646a9 | |
|
|
ba015cf44e | |
|
|
3837635f2c | |
|
|
95c5ca81b2 | |
|
|
bbb7e4cea8 | |
|
|
15eb10ac68 | |
|
|
4c846c712d | |
|
|
4a82fd442d | |
|
|
b3c9ff8419 | |
|
|
fc6fd98a62 | |
|
|
6304328548 | |
|
|
86867fe678 | |
|
|
54349a1c31 | |
|
|
4f18a73239 | |
|
|
67629fb6ef | |
|
|
27a6d256f0 | |
|
|
938dce7333 | |
|
|
99c403ca62 | |
|
|
6ee4101f58 | |
|
|
f94a20d221 | |
|
|
54f810b6b0 | |
|
|
55a3a94065 | |
|
|
8383ecaadf | |
|
|
8deacbc438 | |
|
|
1cfd2b1b9f | |
|
|
766a8ab4ed | |
|
|
b7190f0e1f | |
|
|
857aeb2366 | |
|
|
871670845f | |
|
|
68a68aede9 | |
|
|
4a8f7ac4fb | |
|
|
ee4ce8893c |
|
|
@ -1,19 +1,35 @@
|
|||
name: Bug Report / Сообщение об ошибке
|
||||
description: File a bug report / Сообщить об ошибке в проекте
|
||||
description: File a bug report / Сообщить об ошибке в программе
|
||||
|
||||
body:
|
||||
- type: markdown
|
||||
attributes:
|
||||
value: |
|
||||
Please pay some attention!
|
||||
GoodbyeDPI does not guarantee to work on your ISP on 100% or at all. If GoodbyeDPI can't unblock some or any websites, this is most likely not a software bug, and you should not report it.
|
||||
Please report software bugs, such as: website incompatibility (if the website works without GoodbyeDPI but breaks with GoobyeDPI enabled), antivirus incompatibility, DNS redirection problems, incorrect packet handling, and other software issues.
|
||||
Please make sure to check other opened and closed issues, it could be your question or issue has been already discussed.
|
||||
### USE THIS FORM ONLY FOR BUGS! The webside does not open? That's likely NOT a bug, do not report it here!
|
||||
GoodbyeDPI does not guarantee to work with your ISP for every blocked website or at all. If GoodbyeDPI can't unblock some or any websites, this is most likely not a software bug, and you should not report it here.
|
||||
|
||||
Пожалуйста, прочтите!
|
||||
GoodbyeDPI не гарантирует ни 100% работу с вашим провайдером, ни работу вообще. Если GoodbyeDPI не разблокирует доступ к некоторым или всем веб-сайтам, вероятнее всего, это не программная ошибка, и не стоит о ней сообщать здесь.
|
||||
Сообщайте только об ошибках в программе, таких как: некорректная работа с веб-сайтами (когда веб-сайт работает без GoodbyeDPI, но ломается с GoodbyeDPI), несовместимость с антивирусами, проблемы с перенаправлением DNS, некорректная обработка пакетов, и другие проблемы.
|
||||
Также посмотрите другие открытые и закрытые баги. Возможно, ваш вопрос или проблема уже обсуждались.
|
||||
Please only report software bugs, such as:
|
||||
* program crash
|
||||
* incorrect network packet handling
|
||||
* antivirus incompatibility
|
||||
* DNS redirection problems
|
||||
* other software
|
||||
|
||||
Please make sure to check other opened and closed issues, it could be your bug has been reported already.
|
||||
For questions, or if in doubt, [use NTC.party forum](https://ntc.party/c/community-software/goodbyedpi).
|
||||
|
||||
### ИСПОЛЬЗУЙТЕ ЭТУ ФОРМУ ТОЛЬКО ДЛЯ БАГОВ! Веб-сайт не открывается? Это, скорее всего, не баг, не сообщайте сюда!
|
||||
GoodbyeDPI не гарантирует ни 100% работу с вашим провайдером, ни работу с каждым заблокированным сайтом. Если GoodbyeDPI не разблокирует доступ к некоторым или всем веб-сайтам, вероятнее всего, это не программная ошибка, и не стоит о ней сообщать здесь.
|
||||
|
||||
Пожалуйста, сообщайте только об ошибках в программе, таких как:
|
||||
* падение программы
|
||||
* некорректная обработка сетевых пакетов
|
||||
* несовместимость с антивирусами
|
||||
* проблемы с перенаправлением DNS
|
||||
* другие ошибки в программе
|
||||
|
||||
Также посмотрите другие открытые и закрытые баги. Возможно, ошибка уже обсуждалась или исправлена.
|
||||
Для вопросов, а также в случае сомнений в определении бага, обращайтесь [на форум NTC.party](https://ntc.party/c/community-software/goodbyedpi).
|
||||
- type: input
|
||||
id: os
|
||||
attributes:
|
||||
|
|
@ -35,8 +51,8 @@ body:
|
|||
- type: textarea
|
||||
id: what-happened
|
||||
attributes:
|
||||
label: Describe the issue / Опишите проблему
|
||||
description: A clear and concise description of what the bug is / Подробно опишите, в чём заключается проблема
|
||||
label: Describe the bug / Опишите ошибку программы
|
||||
description: A clear and concise description of what the bug is / Подробно опишите, в чём заключается ошибка
|
||||
placeholder: Attach the screenshots for clarity / При необходимости приложите скриншоты
|
||||
validations:
|
||||
required: true
|
||||
|
|
|
|||
|
|
@ -4,22 +4,24 @@ on:
|
|||
push:
|
||||
paths:
|
||||
- 'src/**'
|
||||
workflow_dispatch:
|
||||
|
||||
env:
|
||||
WINDIVERT_URL: https://www.reqrypt.org/download/WinDivert-1.4.3-A.zip
|
||||
WINDIVERT_NAME: WinDivert-1.4.3-A.zip
|
||||
WINDIVERT_SHA256: 4084bc3931f31546d375ed89e3f842776efa46f321ed0adcd32d3972a7d02566
|
||||
WINDIVERT_URL: https://reqrypt.org/download/WinDivert-2.2.0-D.zip
|
||||
WINDIVERT_NAME: WinDivert-2.2.0-D.zip
|
||||
WINDIVERT_BASENAME: WinDivert-2.2.0-D
|
||||
WINDIVERT_SHA256: 1d461cfdfa7ba88ebcfbb3603b71b703e9f72aba8aeff99a75ce293e6f89d2ba
|
||||
|
||||
jobs:
|
||||
build:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- uses: actions/checkout@v2
|
||||
- uses: actions/checkout@v4
|
||||
|
||||
- name: Declare short commit variable
|
||||
id: vars
|
||||
run: |
|
||||
echo "::set-output name=sha_short::$(git rev-parse --short HEAD)"
|
||||
echo "sha_short=$(git rev-parse --short HEAD)" >> $GITHUB_OUTPUT
|
||||
|
||||
- name: Install MinGW-w64
|
||||
run: >
|
||||
|
|
@ -29,7 +31,7 @@ jobs:
|
|||
|
||||
- name: Download WinDivert from cache
|
||||
id: windivert-cache
|
||||
uses: actions/cache@v2
|
||||
uses: actions/cache@v4
|
||||
with:
|
||||
path: ${{ env. WINDIVERT_NAME }}
|
||||
key: ${{ env. WINDIVERT_SHA256 }}
|
||||
|
|
@ -46,15 +48,15 @@ jobs:
|
|||
- name: Compile x86_64
|
||||
run: >
|
||||
cd src && make clean &&
|
||||
make CPREFIX=x86_64-w64-mingw32- BIT64=1 WINDIVERTHEADERS=../WinDivert-1.4.3-A/include WINDIVERTLIBS=../WinDivert-1.4.3-A/x86_64 -j4
|
||||
|
||||
make CPREFIX=x86_64-w64-mingw32- BIT64=1 WINDIVERTHEADERS=../${{ env.WINDIVERT_BASENAME }}/include WINDIVERTLIBS=../${{ env.WINDIVERT_BASENAME }}/x64 -j4
|
||||
|
||||
- name: Prepare x86_64 directory
|
||||
run: |
|
||||
mkdir goodbyedpi_x86_64_${{ steps.vars.outputs.sha_short }}
|
||||
cp src/goodbyedpi.exe WinDivert-1.4.3-A/x86_64/*.{dll,sys} goodbyedpi_x86_64_${{ steps.vars.outputs.sha_short }}
|
||||
cp src/goodbyedpi.exe ${{ env.WINDIVERT_BASENAME }}/x64/*.{dll,sys} goodbyedpi_x86_64_${{ steps.vars.outputs.sha_short }}
|
||||
|
||||
- name: Upload output file x86_64 (64 bit)
|
||||
uses: actions/upload-artifact@v2
|
||||
- name: Upload output file x86_64
|
||||
uses: actions/upload-artifact@v4
|
||||
with:
|
||||
name: goodbyedpi_x86_64_${{ steps.vars.outputs.sha_short }}
|
||||
path: goodbyedpi_x86_64_${{ steps.vars.outputs.sha_short }}
|
||||
|
|
@ -62,15 +64,15 @@ jobs:
|
|||
- name: Compile i686
|
||||
run: >
|
||||
cd src && make clean &&
|
||||
make CPREFIX=i686-w64-mingw32- WINDIVERTHEADERS=../WinDivert-1.4.3-A/include WINDIVERTLIBS=../WinDivert-1.4.3-A/x86 -j4
|
||||
make CPREFIX=i686-w64-mingw32- WINDIVERTHEADERS=../${{ env.WINDIVERT_BASENAME }}/include WINDIVERTLIBS=../${{ env.WINDIVERT_BASENAME }}/x86 -j4
|
||||
|
||||
- name: Prepare x86 directory
|
||||
run: |
|
||||
mkdir goodbyedpi_x86_${{ steps.vars.outputs.sha_short }}
|
||||
cp src/goodbyedpi.exe WinDivert-1.4.3-A/x86/*.{dll,sys} goodbyedpi_x86_${{ steps.vars.outputs.sha_short }}
|
||||
cp src/goodbyedpi.exe ${{ env.WINDIVERT_BASENAME }}/x86/*.{dll,sys} goodbyedpi_x86_${{ steps.vars.outputs.sha_short }}
|
||||
|
||||
- name: Upload output file x86
|
||||
uses: actions/upload-artifact@v2
|
||||
uses: actions/upload-artifact@v4
|
||||
with:
|
||||
name: goodbyedpi_x86_${{ steps.vars.outputs.sha_short }}
|
||||
path: goodbyedpi_x86_${{ steps.vars.outputs.sha_short }}
|
||||
|
|
|
|||
25
README.md
25
README.md
|
|
@ -43,13 +43,15 @@ Usage: goodbyedpi.exe [OPTION...]
|
|||
supplied text file (HTTP Host/TLS SNI).
|
||||
This option can be supplied multiple times.
|
||||
--allow-no-sni perform circumvention if TLS SNI can't be detected with --blacklist enabled.
|
||||
--frag-by-sni if SNI is detected in TLS packet, fragment the packet right before SNI value.
|
||||
--set-ttl <value> activate Fake Request Mode and send it with supplied TTL value.
|
||||
DANGEROUS! May break websites in unexpected ways. Use with care.
|
||||
DANGEROUS! May break websites in unexpected ways. Use with care (or --blacklist).
|
||||
--auto-ttl [a1-a2-m] activate Fake Request Mode, automatically detect TTL and decrease
|
||||
it based on a distance. If the distance is shorter than a2, TTL is decreased
|
||||
by a2. If it's longer, (a1; a2) scale is used with the distance as a weight.
|
||||
If the resulting TTL is more than m(ax), set it to m.
|
||||
Default (if set): --auto-ttl 1-4-10. Also sets --min-ttl 3.
|
||||
DANGEROUS! May break websites in unexpected ways. Use with care (or --blacklist).
|
||||
--min-ttl <value> minimum TTL distance (128/64 - TTL) for which to send Fake Request
|
||||
in --set-ttl and --auto-ttl modes.
|
||||
--wrong-chksum activate Fake Request Mode and send it with incorrect TCP checksum.
|
||||
|
|
@ -65,6 +67,7 @@ Usage: goodbyedpi.exe [OPTION...]
|
|||
Use this option to reduce CPU usage by skipping huge amount of data
|
||||
(like file transfers) in already established sessions.
|
||||
May skip some huge HTTP requests from being processed.
|
||||
Default (if set): --max-payload 1200.
|
||||
|
||||
|
||||
LEGACY modesets:
|
||||
|
|
@ -74,8 +77,8 @@ LEGACY modesets:
|
|||
-4 -p -r -s (best speed)
|
||||
|
||||
Modern modesets (more stable, more compatible, faster):
|
||||
-5 -f 2 -e 2 --auto-ttl --reverse-frag (this is the default)
|
||||
-6 -f 2 -e 2 --wrong-seq --reverse-frag
|
||||
-5 -f 2 -e 2 --auto-ttl --reverse-frag --max-payload (this is the default)
|
||||
-6 -f 2 -e 2 --wrong-seq --reverse-frag --max-payload
|
||||
```
|
||||
|
||||
To check if your ISP's DPI could be circumvented, first make sure that your provider does not poison DNS answers by enabling "Secure DNS (DNS over HTTPS)" option in your browser.
|
||||
|
|
@ -85,7 +88,7 @@ To check if your ISP's DPI could be circumvented, first make sure that your prov
|
|||
|
||||
Then run the `goodbyedpi.exe` executable without any options. If it works — congratulations! You can use it as-is or configure further, for example by using `--blacklist` option if the list of blocked websites is known and available for your country.
|
||||
|
||||
If your provider intercepts DNS requests, you may want to use `--dns-addr` option to a public DNS resover running on non-standard port (such as Yandex DNS `77.88.8.8:1253`) or configure DNS over HTTPS/TLS using third-party applications.
|
||||
If your provider intercepts DNS requests, you may want to use `--dns-addr` option to a public DNS resolver running on non-standard port (such as Yandex DNS `77.88.8.8:1253`) or configure DNS over HTTPS/TLS using third-party applications.
|
||||
|
||||
Check the .cmd scripts and modify it according to your preference and network conditions.
|
||||
|
||||
|
|
@ -138,11 +141,15 @@ Modify them according to your own needs.
|
|||
|
||||
# Similar projects
|
||||
|
||||
- **[zapret](https://github.com/bol-van/zapret)** by @bol-van (for Linux).
|
||||
- **[Green Tunnel](https://github.com/SadeghHayeri/GreenTunnel)** by @SadeghHayeri (for MacOS, Linux and Windows).
|
||||
- **[DPITunnel](https://github.com/zhenyolka/DPITunnel)** by @zhenyolka (for Android).
|
||||
- **[PowerTunnel](https://github.com/krlvm/PowerTunnel)** by @krlvm (for Windows, MacOS and Linux).
|
||||
- **[PowerTunnel for Android](https://github.com/krlvm/PowerTunnel-Android)** by @krlvm (for Android).
|
||||
- **[zapret](https://github.com/bol-van/zapret)** by @bol-van (for MacOS, Linux and Windows)
|
||||
- **[Green Tunnel](https://github.com/SadeghHayeri/GreenTunnel)** by @SadeghHayeri (for MacOS, Linux and Windows)
|
||||
- **[DPI Tunnel CLI](https://github.com/zhenyolka/DPITunnel-cli)** by @zhenyolka (for Linux and routers)
|
||||
- **[DPI Tunnel for Android](https://github.com/zhenyolka/DPITunnel-android)** by @zhenyolka (for Android)
|
||||
- **[PowerTunnel](https://github.com/krlvm/PowerTunnel)** by @krlvm (for Windows, MacOS and Linux)
|
||||
- **[PowerTunnel for Android](https://github.com/krlvm/PowerTunnel-Android)** by @krlvm (for Android)
|
||||
- **[SpoofDPI](https://github.com/xvzc/SpoofDPI)** by @xvzc (for macOS and Linux)
|
||||
- **[GhosTCP](https://github.com/macronut/ghostcp)** by @macronut (for Windows)
|
||||
- **[ByeDPI](https://github.com/hufrea/byedpi)** for Linux/Windows + **[ByeDPIAndroid](https://github.com/dovecoteescapee/ByeDPIAndroid/)** for Android (no root)
|
||||
|
||||
# Kudos
|
||||
|
||||
|
|
|
|||
|
|
@ -11,7 +11,12 @@ TARGET = goodbyedpi.exe
|
|||
#LIBS = -L$(WINDIVERTLIBS) -Wl,-Bstatic -lssp -Wl,-Bdynamic -lWinDivert -lws2_32
|
||||
LIBS = -L$(WINDIVERTLIBS) -lWinDivert -lws2_32 -l:libssp.a
|
||||
CC = $(CPREFIX)gcc
|
||||
|
||||
CCWINDRES = $(CPREFIX)windres
|
||||
ifeq (, $(shell which $(CPREFIX)windres))
|
||||
CCWINDRES = windres
|
||||
endif
|
||||
|
||||
CFLAGS = -std=c99 -pie -fPIE -pipe -I$(WINDIVERTHEADERS) -L$(WINDIVERTLIBS) \
|
||||
-O2 -D_FORTIFY_SOURCE=2 -fstack-protector \
|
||||
-Wall -Wextra -Wpedantic -Wformat=2 -Wformat-overflow=2 -Wformat-truncation=2 \
|
||||
|
|
|
|||
|
|
@ -70,19 +70,21 @@ static int send_fake_data(const HANDLE w_filter,
|
|||
memcpy(&addr_new, addr, sizeof(WINDIVERT_ADDRESS));
|
||||
memcpy(packet_fake, pkt, packetLen);
|
||||
|
||||
addr_new.PseudoTCPChecksum = 0;
|
||||
addr_new.PseudoIPChecksum = 0;
|
||||
addr_new.TCPChecksum = 0;
|
||||
addr_new.IPChecksum = 0;
|
||||
|
||||
if (!is_ipv6) {
|
||||
// IPv4 TCP Data packet
|
||||
if (!WinDivertHelperParsePacket(packet_fake, packetLen, &ppIpHdr,
|
||||
NULL, NULL, NULL, &ppTcpHdr, NULL, &packet_data, &packet_dataLen))
|
||||
NULL, NULL, NULL, NULL, &ppTcpHdr, NULL, &packet_data, &packet_dataLen,
|
||||
NULL, NULL))
|
||||
return 1;
|
||||
}
|
||||
else {
|
||||
// IPv6 TCP Data packet
|
||||
if (!WinDivertHelperParsePacket(packet_fake, packetLen, NULL,
|
||||
&ppIpV6Hdr, NULL, NULL, &ppTcpHdr, NULL, &packet_data, &packet_dataLen))
|
||||
&ppIpV6Hdr, NULL, NULL, NULL, &ppTcpHdr, NULL, &packet_data, &packet_dataLen,
|
||||
NULL, NULL))
|
||||
return 1;
|
||||
}
|
||||
|
||||
|
|
@ -126,12 +128,12 @@ static int send_fake_data(const HANDLE w_filter,
|
|||
// ...and damage it
|
||||
ppTcpHdr->Checksum = htons(ntohs(ppTcpHdr->Checksum) - 1);
|
||||
}
|
||||
//printf("Pseudo checksum: %d\n", addr_new.PseudoTCPChecksum);
|
||||
//printf("Pseudo checksum: %d\n", addr_new.TCPChecksum);
|
||||
|
||||
WinDivertSend(
|
||||
w_filter, packet_fake,
|
||||
packetLen_new,
|
||||
&addr_new, NULL
|
||||
NULL, &addr_new
|
||||
);
|
||||
debug("Fake packet: OK");
|
||||
|
||||
|
|
|
|||
158
src/goodbyedpi.c
158
src/goodbyedpi.c
|
|
@ -23,7 +23,7 @@
|
|||
// My mingw installation does not load inet_pton definition for some reason
|
||||
WINSOCK_API_LINKAGE INT WSAAPI inet_pton(INT Family, LPCSTR pStringBuf, PVOID pAddr);
|
||||
|
||||
#define GOODBYEDPI_VERSION "v0.2.1"
|
||||
#define GOODBYEDPI_VERSION "v0.2.2"
|
||||
|
||||
#define die() do { sleep(20); exit(EXIT_FAILURE); } while (0)
|
||||
|
||||
|
|
@ -119,8 +119,8 @@ WINSOCK_API_LINKAGE INT WSAAPI inet_pton(INT Family, LPCSTR pStringBuf, PVOID pA
|
|||
} \
|
||||
else if (ttl_min_nhops) { \
|
||||
/* If not Auto TTL mode but --min-ttl is set */ \
|
||||
if (tcp_get_auto_ttl(tcp_conn_info.ttl, 0, 0, ttl_min_nhops, 0)) { \
|
||||
/* Send only if nhops > min_ttl */ \
|
||||
if (!tcp_get_auto_ttl(tcp_conn_info.ttl, 0, 0, ttl_min_nhops, 0)) { \
|
||||
/* Send only if nhops >= min_ttl */ \
|
||||
should_send_fake = 0; \
|
||||
} \
|
||||
} \
|
||||
|
|
@ -162,6 +162,7 @@ static struct option long_options[] = {
|
|||
{"dns-verb", no_argument, 0, 'v' },
|
||||
{"blacklist", required_argument, 0, 'b' },
|
||||
{"allow-no-sni",no_argument, 0, ']' },
|
||||
{"frag-by-sni", no_argument, 0, '>' },
|
||||
{"ip-id", required_argument, 0, 'i' },
|
||||
{"set-ttl", required_argument, 0, '$' },
|
||||
{"min-ttl", required_argument, 0, '[' },
|
||||
|
|
@ -216,7 +217,8 @@ static void add_ip_id_str(int id) {
|
|||
|
||||
static void add_maxpayloadsize_str(unsigned short maxpayload) {
|
||||
char *newstr;
|
||||
const char *maxpayloadsize_str = "and (tcp.PayloadLength ? tcp.PayloadLength < %hu : true)";
|
||||
/* 0x47455420 is "GET ", 0x504F5354 is "POST", big endian. */
|
||||
const char *maxpayloadsize_str = "and (tcp.PayloadLength ? tcp.PayloadLength < %hu or tcp.Payload32[0] == 0x47455420 or tcp.Payload32[0] == 0x504F5354 : true)";
|
||||
char *addfilter = malloc(strlen(maxpayloadsize_str) + 16);
|
||||
|
||||
sprintf(addfilter, maxpayloadsize_str, maxpayload);
|
||||
|
|
@ -309,6 +311,7 @@ static HANDLE init(char *filter, UINT64 flags) {
|
|||
|
||||
static int deinit(HANDLE handle) {
|
||||
if (handle) {
|
||||
WinDivertShutdown(handle, WINDIVERT_SHUTDOWN_BOTH);
|
||||
WinDivertClose(handle);
|
||||
return TRUE;
|
||||
}
|
||||
|
|
@ -415,7 +418,7 @@ static int extract_sni(const char *pktdata, unsigned int pktlen,
|
|||
}
|
||||
/* Validate that hostname has only ascii lowercase characters */
|
||||
for (int i=0; i<hnlen; i++) {
|
||||
if (!( (hnaddr[i] >= '1' && hnaddr[i] <= '9') ||
|
||||
if (!( (hnaddr[i] >= '0' && hnaddr[i] <= '9') ||
|
||||
(hnaddr[i] >= 'a' && hnaddr[i] <= 'z') ||
|
||||
hnaddr[i] == '.' || hnaddr[i] == '-'))
|
||||
{
|
||||
|
|
@ -472,7 +475,7 @@ static void send_native_fragment(HANDLE w_filter, WINDIVERT_ADDRESS addr,
|
|||
PWINDIVERT_TCPHDR ppTcpHdr,
|
||||
unsigned int fragment_size, int step) {
|
||||
char packet_bak[MAX_PACKET_SIZE];
|
||||
memcpy(&packet_bak, packet, packetLen);
|
||||
memcpy(packet_bak, packet, packetLen);
|
||||
UINT orig_packetLen = packetLen;
|
||||
|
||||
if (fragment_size >= packet_dataLen) {
|
||||
|
|
@ -518,8 +521,8 @@ static void send_native_fragment(HANDLE w_filter, WINDIVERT_ADDRESS addr,
|
|||
ppTcpHdr->SeqNum = htonl(ntohl(ppTcpHdr->SeqNum) + fragment_size);
|
||||
}
|
||||
|
||||
addr.PseudoIPChecksum = 0;
|
||||
addr.PseudoTCPChecksum = 0;
|
||||
addr.IPChecksum = 0;
|
||||
addr.TCPChecksum = 0;
|
||||
|
||||
WinDivertHelperCalcChecksums(
|
||||
packet, packetLen, &addr, 0
|
||||
|
|
@ -527,9 +530,9 @@ static void send_native_fragment(HANDLE w_filter, WINDIVERT_ADDRESS addr,
|
|||
WinDivertSend(
|
||||
w_filter, packet,
|
||||
packetLen,
|
||||
&addr, NULL
|
||||
NULL, &addr
|
||||
);
|
||||
memcpy(packet, &packet_bak, orig_packetLen);
|
||||
memcpy(packet, packet_bak, orig_packetLen);
|
||||
//printf("Sent native fragment of %d size (step%d)\n", packetLen, step);
|
||||
}
|
||||
|
||||
|
|
@ -566,6 +569,7 @@ int main(int argc, char *argv[]) {
|
|||
do_dnsv4_redirect = 0, do_dnsv6_redirect = 0,
|
||||
do_dns_verb = 0, do_tcp_verb = 0, do_blacklist = 0,
|
||||
do_allow_no_sni = 0,
|
||||
do_fragment_by_sni = 0,
|
||||
do_fake_packet = 0,
|
||||
do_auto_ttl = 0,
|
||||
do_wrong_chksum = 0,
|
||||
|
|
@ -804,7 +808,11 @@ int main(int argc, char *argv[]) {
|
|||
case ']': // --allow-no-sni
|
||||
do_allow_no_sni = 1;
|
||||
break;
|
||||
case '>': // --frag-by-sni
|
||||
do_fragment_by_sni = 1;
|
||||
break;
|
||||
case '$': // --set-ttl
|
||||
do_auto_ttl = auto_ttl_1 = auto_ttl_2 = auto_ttl_max = 0;
|
||||
do_fake_packet = 1;
|
||||
ttl_of_fake_packet = atoub(optarg, "Set TTL parameter error!");
|
||||
break;
|
||||
|
|
@ -870,7 +878,7 @@ int main(int argc, char *argv[]) {
|
|||
optarg = argv[optind];
|
||||
if (optarg)
|
||||
max_payload_size = atousi(optarg, "Max payload size parameter error!");
|
||||
if (!max_payload_size)
|
||||
else
|
||||
max_payload_size = 1200;
|
||||
break;
|
||||
default:
|
||||
|
|
@ -896,6 +904,7 @@ int main(int argc, char *argv[]) {
|
|||
" supplied text file (HTTP Host/TLS SNI).\n"
|
||||
" This option can be supplied multiple times.\n"
|
||||
" --allow-no-sni perform circumvention if TLS SNI can't be detected with --blacklist enabled.\n"
|
||||
" --frag-by-sni if SNI is detected in TLS packet, fragment the packet right before SNI value.\n"
|
||||
" --set-ttl <value> activate Fake Request Mode and send it with supplied TTL value.\n"
|
||||
" DANGEROUS! May break websites in unexpected ways. Use with care (or --blacklist).\n"
|
||||
" --auto-ttl [a1-a2-m] activate Fake Request Mode, automatically detect TTL and decrease\n"
|
||||
|
|
@ -929,8 +938,8 @@ int main(int argc, char *argv[]) {
|
|||
" -4 -p -r -s (best speed)"
|
||||
"\n"
|
||||
"Modern modesets (more stable, more compatible, faster):\n"
|
||||
" -5 -f 2 -e 2 --auto-ttl --reverse-frag (this is the default)\n"
|
||||
" -6 -f 2 -e 2 --wrong-seq --reverse-frag\n");
|
||||
" -5 -f 2 -e 2 --auto-ttl --reverse-frag --max-payload (this is the default)\n"
|
||||
" -6 -f 2 -e 2 --wrong-seq --reverse-frag --max-payload\n");
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
}
|
||||
|
|
@ -954,6 +963,7 @@ int main(int argc, char *argv[]) {
|
|||
"Fragment HTTP: %u\n" /* 2 */
|
||||
"Fragment persistent HTTP: %u\n" /* 3 */
|
||||
"Fragment HTTPS: %u\n" /* 4 */
|
||||
"Fragment by SNI: %u\n" /* 5 */
|
||||
"Native fragmentation (splitting): %d\n" /* 5 */
|
||||
"Fragments sending in reverse: %d\n" /* 6 */
|
||||
"hoSt: %d\n" /* 7 */
|
||||
|
|
@ -973,23 +983,24 @@ int main(int argc, char *argv[]) {
|
|||
(do_fragment_http ? http_fragment_size : 0), /* 2 */
|
||||
(do_fragment_http_persistent ? http_fragment_size : 0),/* 3 */
|
||||
(do_fragment_https ? https_fragment_size : 0), /* 4 */
|
||||
do_native_frag, /* 5 */
|
||||
do_reverse_frag, /* 6 */
|
||||
do_host, /* 7 */
|
||||
do_host_removespace, /* 8 */
|
||||
do_additional_space, /* 9 */
|
||||
do_host_mixedcase, /* 10 */
|
||||
do_http_allports, /* 11 */
|
||||
do_fragment_http_persistent_nowait, /* 12 */
|
||||
do_dnsv4_redirect, /* 13 */
|
||||
do_dnsv6_redirect, /* 14 */
|
||||
do_allow_no_sni, /* 15 */
|
||||
ttl_of_fake_packet ? "fixed" : (do_auto_ttl ? "auto" : "disabled"), /* 16 */
|
||||
do_fragment_by_sni, /* 5 */
|
||||
do_native_frag, /* 6 */
|
||||
do_reverse_frag, /* 7 */
|
||||
do_host, /* 8 */
|
||||
do_host_removespace, /* 9 */
|
||||
do_additional_space, /* 10 */
|
||||
do_host_mixedcase, /* 11 */
|
||||
do_http_allports, /* 12 */
|
||||
do_fragment_http_persistent_nowait, /* 13 */
|
||||
do_dnsv4_redirect, /* 14 */
|
||||
do_dnsv6_redirect, /* 15 */
|
||||
do_allow_no_sni, /* 16 */
|
||||
do_auto_ttl ? "auto" : (do_fake_packet ? "fixed" : "disabled"), /* 17 */
|
||||
ttl_of_fake_packet, do_auto_ttl ? auto_ttl_1 : 0, do_auto_ttl ? auto_ttl_2 : 0,
|
||||
do_auto_ttl ? auto_ttl_max : 0, ttl_min_nhops,
|
||||
do_wrong_chksum, /* 17 */
|
||||
do_wrong_seq, /* 18 */
|
||||
max_payload_size /* 19 */
|
||||
do_wrong_chksum, /* 18 */
|
||||
do_wrong_seq, /* 19 */
|
||||
max_payload_size /* 20 */
|
||||
);
|
||||
|
||||
if (do_fragment_http && http_fragment_size > 2 && !do_native_frag) {
|
||||
|
|
@ -1001,7 +1012,7 @@ int main(int argc, char *argv[]) {
|
|||
if (do_native_frag && !(do_fragment_http || do_fragment_https)) {
|
||||
puts("\nERROR: Native fragmentation is enabled but fragment sizes are not set.\n"
|
||||
"Fragmentation has no effect.");
|
||||
exit(EXIT_FAILURE);
|
||||
die();
|
||||
}
|
||||
|
||||
if (max_payload_size)
|
||||
|
|
@ -1038,11 +1049,12 @@ int main(int argc, char *argv[]) {
|
|||
signal(SIGINT, sigint_handler);
|
||||
|
||||
while (1) {
|
||||
if (WinDivertRecv(w_filter, packet, sizeof(packet), &addr, &packetLen)) {
|
||||
debug("Got %s packet, len=%d!\n", addr.Direction ? "inbound" : "outbound",
|
||||
if (WinDivertRecv(w_filter, packet, sizeof(packet), &packetLen, &addr)) {
|
||||
debug("Got %s packet, len=%d!\n", addr.Outbound ? "outbound" : "inbound",
|
||||
packetLen);
|
||||
should_reinject = 1;
|
||||
should_recalc_checksum = 0;
|
||||
sni_ok = 0;
|
||||
|
||||
ppIpHdr = (PWINDIVERT_IPHDR)NULL;
|
||||
ppIpV6Hdr = (PWINDIVERT_IPV6HDR)NULL;
|
||||
|
|
@ -1052,35 +1064,35 @@ int main(int argc, char *argv[]) {
|
|||
packet_type = unknown;
|
||||
|
||||
// Parse network packet and set it's type
|
||||
if ((packet_v4 = WinDivertHelperParsePacket(packet, packetLen, &ppIpHdr,
|
||||
NULL, NULL, NULL, &ppTcpHdr, NULL, &packet_data, &packet_dataLen)))
|
||||
if (WinDivertHelperParsePacket(packet, packetLen, &ppIpHdr,
|
||||
&ppIpV6Hdr, NULL, NULL, NULL, &ppTcpHdr, &ppUdpHdr, &packet_data, &packet_dataLen,
|
||||
NULL, NULL))
|
||||
{
|
||||
packet_type = ipv4_tcp_data;
|
||||
}
|
||||
else if ((packet_v6 = WinDivertHelperParsePacket(packet, packetLen, NULL,
|
||||
&ppIpV6Hdr, NULL, NULL, &ppTcpHdr, NULL, &packet_data, &packet_dataLen)))
|
||||
{
|
||||
packet_type = ipv6_tcp_data;
|
||||
}
|
||||
else if ((packet_v4 = WinDivertHelperParsePacket(packet, packetLen, &ppIpHdr,
|
||||
NULL, NULL, NULL, &ppTcpHdr, NULL, NULL, NULL)))
|
||||
{
|
||||
packet_type = ipv4_tcp;
|
||||
}
|
||||
else if ((packet_v6 = WinDivertHelperParsePacket(packet, packetLen, NULL,
|
||||
&ppIpV6Hdr, NULL, NULL, &ppTcpHdr, NULL, NULL, NULL)))
|
||||
{
|
||||
packet_type = ipv6_tcp;
|
||||
}
|
||||
else if ((packet_v4 = WinDivertHelperParsePacket(packet, packetLen, &ppIpHdr,
|
||||
NULL, NULL, NULL, NULL, &ppUdpHdr, &packet_data, &packet_dataLen)))
|
||||
{
|
||||
packet_type = ipv4_udp_data;
|
||||
}
|
||||
else if ((packet_v6 = WinDivertHelperParsePacket(packet, packetLen, NULL,
|
||||
&ppIpV6Hdr, NULL, NULL, NULL, &ppUdpHdr, &packet_data, &packet_dataLen)))
|
||||
{
|
||||
packet_type = ipv6_udp_data;
|
||||
if (ppIpHdr) {
|
||||
packet_v4 = 1;
|
||||
if (ppTcpHdr) {
|
||||
packet_type = ipv4_tcp;
|
||||
if (packet_data) {
|
||||
packet_type = ipv4_tcp_data;
|
||||
}
|
||||
}
|
||||
else if (ppUdpHdr && packet_data) {
|
||||
packet_type = ipv4_udp_data;
|
||||
}
|
||||
}
|
||||
|
||||
else if (ppIpV6Hdr) {
|
||||
packet_v6 = 1;
|
||||
if (ppTcpHdr) {
|
||||
packet_type = ipv6_tcp;
|
||||
if (packet_data) {
|
||||
packet_type = ipv6_tcp_data;
|
||||
}
|
||||
}
|
||||
else if (ppUdpHdr && packet_data) {
|
||||
packet_type = ipv6_udp_data;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
debug("packet_type: %d, packet_v4: %d, packet_v6: %d\n", packet_type, packet_v4, packet_v6);
|
||||
|
|
@ -1090,7 +1102,7 @@ int main(int argc, char *argv[]) {
|
|||
/* Got a TCP packet WITH DATA */
|
||||
|
||||
/* Handle INBOUND packet with data and find HTTP REDIRECT in there */
|
||||
if (addr.Direction == WINDIVERT_DIRECTION_INBOUND && packet_dataLen > 16) {
|
||||
if (!addr.Outbound && packet_dataLen > 16) {
|
||||
/* If INBOUND packet with DATA (tcp.Ack) */
|
||||
|
||||
/* Drop packets from filter with HTTP 30x Redirect */
|
||||
|
|
@ -1114,7 +1126,7 @@ int main(int argc, char *argv[]) {
|
|||
/* Handle OUTBOUND packet on port 443, search for something that resembles
|
||||
* TLS handshake, send fake request.
|
||||
*/
|
||||
else if (addr.Direction == WINDIVERT_DIRECTION_OUTBOUND &&
|
||||
else if (addr.Outbound &&
|
||||
((do_fragment_https ? packet_dataLen == https_fragment_size : 0) ||
|
||||
packet_dataLen > 16) &&
|
||||
ppTcpHdr->DstPort != htons(80) &&
|
||||
|
|
@ -1126,9 +1138,9 @@ int main(int argc, char *argv[]) {
|
|||
* But if the packet is more than 2 bytes, check ClientHello byte.
|
||||
*/
|
||||
if ((packet_dataLen == 2 && memcmp(packet_data, "\x16\x03", 2) == 0) ||
|
||||
(packet_dataLen >= 3 && memcmp(packet_data, "\x16\x03\x01", 3) == 0))
|
||||
(packet_dataLen >= 3 && ( memcmp(packet_data, "\x16\x03\x01", 3) == 0 || memcmp(packet_data, "\x16\x03\x03", 3) == 0 )))
|
||||
{
|
||||
if (do_blacklist) {
|
||||
if (do_blacklist || do_fragment_by_sni) {
|
||||
sni_ok = extract_sni(packet_data, packet_dataLen,
|
||||
&host_addr, &host_len);
|
||||
}
|
||||
|
|
@ -1144,7 +1156,7 @@ int main(int argc, char *argv[]) {
|
|||
char lsni[HOST_MAXLEN + 1] = {0};
|
||||
extract_sni(packet_data, packet_dataLen,
|
||||
&host_addr, &host_len);
|
||||
memcpy(&lsni, host_addr, host_len);
|
||||
memcpy(lsni, host_addr, host_len);
|
||||
printf("Blocked HTTPS website SNI: %s\n", lsni);
|
||||
#endif
|
||||
if (do_fake_packet) {
|
||||
|
|
@ -1158,7 +1170,7 @@ int main(int argc, char *argv[]) {
|
|||
}
|
||||
}
|
||||
/* Handle OUTBOUND packet on port 80, search for Host header */
|
||||
else if (addr.Direction == WINDIVERT_DIRECTION_OUTBOUND &&
|
||||
else if (addr.Outbound &&
|
||||
packet_dataLen > 16 &&
|
||||
(do_http_allports ? 1 : (ppTcpHdr->DstPort == htons(80))) &&
|
||||
find_http_method_end(packet_data,
|
||||
|
|
@ -1179,7 +1191,7 @@ int main(int argc, char *argv[]) {
|
|||
host_len = hdr_value_len;
|
||||
#ifdef DEBUG
|
||||
char lhost[HOST_MAXLEN + 1] = {0};
|
||||
memcpy(&lhost, host_addr, host_len);
|
||||
memcpy(lhost, host_addr, host_len);
|
||||
printf("Blocked HTTP website Host: %s\n", lhost);
|
||||
#endif
|
||||
|
||||
|
|
@ -1281,7 +1293,11 @@ int main(int argc, char *argv[]) {
|
|||
current_fragment_size = http_fragment_size;
|
||||
}
|
||||
else if (do_fragment_https && ppTcpHdr->DstPort != htons(80)) {
|
||||
current_fragment_size = https_fragment_size;
|
||||
if (do_fragment_by_sni && sni_ok) {
|
||||
current_fragment_size = (void*)host_addr - packet_data;
|
||||
} else {
|
||||
current_fragment_size = https_fragment_size;
|
||||
}
|
||||
}
|
||||
|
||||
if (current_fragment_size) {
|
||||
|
|
@ -1302,7 +1318,7 @@ int main(int argc, char *argv[]) {
|
|||
/* Else if we got TCP packet without data */
|
||||
else if (packet_type == ipv4_tcp || packet_type == ipv6_tcp) {
|
||||
/* If we got INBOUND SYN+ACK packet */
|
||||
if (addr.Direction == WINDIVERT_DIRECTION_INBOUND &&
|
||||
if (!addr.Outbound &&
|
||||
ppTcpHdr->Syn == 1 && ppTcpHdr->Ack == 1) {
|
||||
//printf("Changing Window Size!\n");
|
||||
/*
|
||||
|
|
@ -1342,7 +1358,7 @@ int main(int argc, char *argv[]) {
|
|||
else if ((do_dnsv4_redirect && (packet_type == ipv4_udp_data)) ||
|
||||
(do_dnsv6_redirect && (packet_type == ipv6_udp_data)))
|
||||
{
|
||||
if (addr.Direction == WINDIVERT_DIRECTION_INBOUND) {
|
||||
if (!addr.Outbound) {
|
||||
if ((packet_v4 && dns_handle_incoming(&ppIpHdr->DstAddr, ppUdpHdr->DstPort,
|
||||
packet_data, packet_dataLen,
|
||||
&dns_conn_info, 0))
|
||||
|
|
@ -1372,7 +1388,7 @@ int main(int argc, char *argv[]) {
|
|||
}
|
||||
}
|
||||
|
||||
else if (addr.Direction == WINDIVERT_DIRECTION_OUTBOUND) {
|
||||
else if (addr.Outbound) {
|
||||
if ((packet_v4 && dns_handle_outgoing(&ppIpHdr->SrcAddr, ppUdpHdr->SrcPort,
|
||||
&ppIpHdr->DstAddr, ppUdpHdr->DstPort,
|
||||
packet_data, packet_dataLen, 0))
|
||||
|
|
@ -1410,7 +1426,7 @@ int main(int argc, char *argv[]) {
|
|||
if (should_recalc_checksum) {
|
||||
WinDivertHelperCalcChecksums(packet, packetLen, &addr, (UINT64)0LL);
|
||||
}
|
||||
WinDivertSend(w_filter, packet, packetLen, &addr, NULL);
|
||||
WinDivertSend(w_filter, packet, packetLen, NULL, &addr);
|
||||
}
|
||||
}
|
||||
else {
|
||||
|
|
|
|||
|
|
@ -30,7 +30,7 @@ int service_register(int argc, char *argv[])
|
|||
*/
|
||||
if (!service_argc && !service_argv) {
|
||||
service_argc = argc;
|
||||
service_argv = malloc(sizeof(void*) * (size_t)argc);
|
||||
service_argv = calloc((size_t)(argc + 1), sizeof(void*));
|
||||
for (i = 0; i < argc; i++) {
|
||||
service_argv[i] = strdup(argv[i]);
|
||||
}
|
||||
|
|
|
|||
Loading…
Reference in New Issue