1 unstable release
0.4.0 | Feb 28, 2022 |
---|---|
0.3.1 |
|
0.3.0 |
|
0.2.0 |
|
0.1.0 |
|
#120 in #udp
38KB
332 lines
udppp
High performence UDP proxy with Proxy Protocol and mmproxy support.
Features
- Async
- Support Proxy Protocol V2
- SOCKET preserve client IP addresses in L7 proxies(mmproxy)
- Single executable
Build & Run
$> cargo build --release
Installation
$> cargo install udppp
Usage
Usage: udppp -m MODE [-b BIND_ADDR] -l LOCAL_PORT -h REMOTE_ADDR -r REMOTE_PORT -p
Options:
-m, --mode MODE 1 : reverse proxy mode , 2 : mmproxy mode
-l, --local-port LOCAL_PORT
The local port to which udppp should bind to
-r, --remote-port REMOTE_PORT
The remote port to which UDP packets should be
forwarded
-h, --host REMOTE_ADDR
The remote address to which packets will be forwarded
-b, --bind BIND_ADDR
The address on which to listen for incoming requests
-p, --proxyprotocol
enable proxy-protocol
-s, --slient disable print log
mmproxy
The idea comes from a creative paper, thanks to the author.
mmproxy - Creative Linux routing to preserve client IP addresses in L7 proxies
However, cloudflare has not officially implemented mmproxy that supports udp. This project makes up for this shortcoming.
Run Proxy (proxy server)
Suppose the udp reverse proxy service port is 8000 , upstream server is 192.168.0.2:8001
./udppp -m 1 -b 0.0.0.0 -l 8000 -h 192.168.0.2 -r 8001 -p
Routing setup (upstream server)
Route all traffic originating from loopback back to loopback
ip rule add from 127.0.0.1/8 iif lo table 123
ip route add local 0.0.0.0/0 dev lo table 123
Normally, response packets coming from the application are routed to the Internet - via a default gateway. We do this by totally abusing the AnyIP trick and assigning 0.0.0.0/0 to "local" - meaning that entire internet shall be treated as belonging to our machine.
Run mmproxy (upstream server)
Suppose the port of the application server is 127.0.0.1:8001
./udppp -m 2 -b 0.0.0.0 -l 8001 -h 127.0.0.1 -r 8002 -p
Benchmark
load test tool : https://github.com/b23r0/udppp/tree/main/test/udpbench
Send a udp packet of 4 bytes and get the same return packet once, loop 1000 times. In the actual test of nginx, when the single test exceeds 1000 times, the client will not receive the return packet.
Test Envoriment
Envoriment | Value |
---|---|
OS | Ubuntu20.04 |
CPU | Intel Xeon(Cascade Lake) Platinum 8269 |
CPU Cores | 4 |
Memory | 8G |
Network | LAN (0.2 Gbps) |
Test Count | 1k |
Test Result
Project | Language | Base | Take Time |
---|---|---|---|
udppp | Rust | Tokio | 56 ms |
nginx | C | Multi-Thread | 54 ms |
go-proxy | Golang | Goroutine | 65 ms |
Take Time
is take the average of 10 times.
(Test Date : 28 Feb 2022)
Dependencies
~7–14MB
~166K SLoC