mirror of
https://github.com/springzfx/cgproxy.git
synced 2026-01-07 13:07:56 +08:00
Compare commits
13 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
daa68f20ea | ||
|
|
836a34cdc8 | ||
|
|
3c21882b88 | ||
|
|
71d924a303 | ||
|
|
5d0b137778 | ||
|
|
8a29e88bab | ||
|
|
dd234b08a0 | ||
|
|
168779ea90 | ||
|
|
5b65ac0ffd | ||
|
|
6c77233e1e | ||
|
|
6be14b9935 | ||
|
|
c1cd7e6e07 | ||
|
|
0848d1ddeb |
1
.gitignore
vendored
1
.gitignore
vendored
@@ -1,4 +1,3 @@
|
||||
build
|
||||
.directory
|
||||
.vscode
|
||||
cgproxy2.sh
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
cmake_minimum_required(VERSION 3.10)
|
||||
|
||||
project(cgproxy VERSION 1.0)
|
||||
project(cgproxy VERSION 3.4)
|
||||
add_executable(cgattach cgattach.cpp)
|
||||
|
||||
install(TARGETS cgattach DESTINATION /usr/bin
|
||||
@@ -21,3 +21,28 @@ install(FILES cgproxy.conf
|
||||
DESTINATION /etc/)
|
||||
install(FILES cgroup-tproxy.sh
|
||||
DESTINATION /usr/share/cgproxy/scripts/)
|
||||
|
||||
|
||||
## deb pack
|
||||
set(CPACK_GENERATOR "DEB;RPM")
|
||||
set(CPACK_PACKAGE_NAME "cgproxy")
|
||||
set(CPACK_PACKAGE_DESCRIPTION_SUMMARY "cgproxy will transparent proxy anything running in specific cgroup.It aslo supports global transparent proxy and gateway proxy")
|
||||
|
||||
set(CPACK_DEBIAN_PACKAGE_NAME "cgproxy")
|
||||
set(CPACK_DEBIAN_PACKAGE_ARCHITECTURE "x86_64")
|
||||
set(CPACK_DEBIAN_PACKAGE_DEPENDS "systemd")
|
||||
set(CPACK_DEBIAN_PACKAGE_SECTION "network")
|
||||
set(CPACK_DEBIAN_PACKAGE_PRIORITY "Optional")
|
||||
set(CPACK_DEBIAN_PACKAGE_HOMEPAGE "https://github.com/springzfx/cgproxy")
|
||||
set(CPACK_DEBIAN_PACKAGE_MAINTAINER "springzfx@gmail.com")
|
||||
set(CONTROL_DIR ${CMAKE_SOURCE_DIR}/control)
|
||||
set(CPACK_DEBIAN_PACKAGE_CONTROL_EXTRA "${CONTROL_DIR}/postinst;${CONTROL_DIR}/prerm")
|
||||
|
||||
set(CPACK_RPM_PACKAGE_ARCHITECTURE, "x86_64")
|
||||
set(CPACK_RPM_PACKAGE_REQUIRES "systemd")
|
||||
set(CPACK_RPM_PACKAGE_GROUP "network")
|
||||
set(CPACK_RPM_PACKAGE_URL "https://github.com/springzfx/cgproxy")
|
||||
set(CPACK_RPM_POST_INSTALL_SCRIPT_FILE "${CONTROL_DIR}/postinst")
|
||||
set(CPACK_RPM_PRE_UNINSTALL_SCRIPT_FILE "${CONTROL_DIR}/prerm")
|
||||
|
||||
include(CPack)
|
||||
@@ -11,6 +11,6 @@ else
|
||||
fi
|
||||
|
||||
# test attach success or not
|
||||
[[ -z "$attached" ]] && echo "config error" && exit 1
|
||||
[[ -z "$attached" ]] && echo "attach error" && exit 1
|
||||
|
||||
exec "$@"
|
||||
@@ -9,19 +9,22 @@
|
||||
cgroup_proxy="/proxy.slice"
|
||||
cgroup_noproxy="/noproxy.slice"
|
||||
|
||||
########################################################################
|
||||
## allow as gateway for local network
|
||||
enable_gateway=false
|
||||
|
||||
########################################################################
|
||||
## listening port of another proxy process, for example v2ray
|
||||
port=12345
|
||||
|
||||
## if you set to false, it's traffic won't go through proxy, but still can go direct to internet
|
||||
########################################################################
|
||||
## if you set to false, it's traffic won't go through proxy, but still can go direct to internet
|
||||
enable_tcp=true
|
||||
enable_udp=true
|
||||
enable_ipv4=true
|
||||
enable_ipv6=true
|
||||
enable_dns=true
|
||||
|
||||
|
||||
########################################################################
|
||||
## do not modify this if you don't known what you are doing
|
||||
table=100
|
||||
|
||||
@@ -11,6 +11,6 @@ else
|
||||
fi
|
||||
|
||||
# test attach success or not
|
||||
[[ -z "$attached" ]] && echo "config error" && exit 1
|
||||
[[ -z "$attached" ]] && echo "attach error" && exit 1
|
||||
|
||||
exec "$@"
|
||||
@@ -34,6 +34,9 @@ DOC
|
||||
cgroup_proxy="/proxy.slice"
|
||||
cgroup_noproxy="/noproxy.slice"
|
||||
|
||||
# allow as gateway for local network
|
||||
enable_gateway=false
|
||||
|
||||
## some variables
|
||||
port=12345
|
||||
enable_tcp=true
|
||||
@@ -60,18 +63,29 @@ for i in "$@"
|
||||
do
|
||||
case $i in
|
||||
stop)
|
||||
iptables -t mangle -F
|
||||
iptables -t mangle -D PREROUTING -j TPROXY_PRE
|
||||
iptables -t mangle -D OUTPUT -j TPROXY_OUT
|
||||
iptables -t mangle -F TPROXY_PRE
|
||||
iptables -t mangle -F TPROXY_OUT
|
||||
iptables -t mangle -F TPROXY_ENT
|
||||
iptables -t mangle -X TPROXY_PRE
|
||||
iptables -t mangle -X TPROXY_OUT
|
||||
ip6tables -t mangle -F
|
||||
iptables -t mangle -X TPROXY_ENT
|
||||
ip6tables -t mangle -D PREROUTING -j TPROXY_PRE
|
||||
ip6tables -t mangle -D OUTPUT -j TPROXY_OUT
|
||||
ip6tables -t mangle -F TPROXY_PRE
|
||||
ip6tables -t mangle -F TPROXY_OUT
|
||||
ip6tables -t mangle -F TPROXY_ENT
|
||||
ip6tables -t mangle -X TPROXY_PRE
|
||||
ip6tables -t mangle -X TPROXY_OUT
|
||||
ip6tables -t mangle -X TPROXY_ENT
|
||||
ip rule delete fwmark $mark_proxy lookup $table
|
||||
ip route flush table $table
|
||||
ip -6 rule delete fwmark $mark_proxy lookup $table
|
||||
ip -6 route flush table $table
|
||||
iptables -t nat -A OUTPUT -F
|
||||
ip6tables -t nat -A OUTPUT -F
|
||||
## may not exist, just ignore, and tracking their existence is reliable
|
||||
iptables -t nat -D POSTROUTING -m addrtype ! --src-type LOCAL -j MASQUERADE &> /dev/null
|
||||
ip6tables -t nat -D POSTROUTING -m addrtype ! --src-type LOCAL -j MASQUERADE &> /dev/null
|
||||
exit 0
|
||||
;;
|
||||
--config=*)
|
||||
@@ -94,17 +108,24 @@ test -d $cgroup_mount_point$cgroup_noproxy || mkdir $cgroup_mount_point$cgroup_
|
||||
#ipv4#
|
||||
ip rule add fwmark $mark_proxy table $table
|
||||
ip route add local default dev lo table $table
|
||||
iptables -t mangle -N TPROXY_ENT
|
||||
iptables -t mangle -A TPROXY_ENT -p tcp -j TPROXY --on-ip 127.0.0.1 --on-port $port --tproxy-mark $mark_proxy
|
||||
iptables -t mangle -A TPROXY_ENT -p udp -j TPROXY --on-ip 127.0.0.1 --on-port $port --tproxy-mark $mark_proxy
|
||||
|
||||
iptables -t mangle -N TPROXY_PRE
|
||||
iptables -t mangle -A TPROXY_PRE -p udp -m mark --mark $mark_proxy -j TPROXY --on-ip 127.0.0.1 --on-port $port --tproxy-mark $mark_proxy
|
||||
iptables -t mangle -A TPROXY_PRE -p tcp -m mark --mark $mark_proxy -j TPROXY --on-ip 127.0.0.1 --on-port $port --tproxy-mark $mark_proxy
|
||||
iptables -t mangle -A TPROXY_PRE -m conntrack --ctstate NEW -j CONNMARK --set-mark $make_newin
|
||||
iptables -t mangle -A TPROXY_PRE -m conntrack --ctstate NEW -j CONNMARK --restore-mark
|
||||
iptables -t mangle -A TPROXY_PRE -p udp --dport 53 -j TPROXY_ENT
|
||||
iptables -t mangle -A TPROXY_PRE -p tcp --dport 53 -j TPROXY_ENT
|
||||
iptables -t mangle -A TPROXY_PRE -p icmp -j RETURN
|
||||
iptables -t mangle -A TPROXY_PRE -m addrtype --dst-type LOCAL -j RETURN
|
||||
iptables -t mangle -A TPROXY_PRE -m pkttype --pkt-type broadcast -j RETURN
|
||||
iptables -t mangle -A TPROXY_PRE -m pkttype --pkt-type multicast -j RETURN
|
||||
iptables -t mangle -A TPROXY_PRE -j TPROXY_ENT
|
||||
iptables -t mangle -A PREROUTING -j TPROXY_PRE
|
||||
|
||||
iptables -t mangle -N TPROXY_OUT
|
||||
iptables -t mangle -A TPROXY_OUT -o lo -j RETURN
|
||||
iptables -t mangle -A TPROXY_OUT -p icmp -j RETURN
|
||||
iptables -t mangle -A TPROXY_OUT -m connmark --mark $make_newin -j RETURN # return incoming connection directly, v2ray tproxy not work for this situation, see this: https://github.com/Kr328/ClashForAndroid/issues/146
|
||||
iptables -t mangle -A TPROXY_OUT -m connmark --mark $make_newin -j RETURN
|
||||
iptables -t mangle -A TPROXY_OUT -m mark --mark $mark_noproxy -j RETURN
|
||||
iptables -t mangle -A TPROXY_OUT -m cgroup --path $cgroup_noproxy -j RETURN
|
||||
iptables -t mangle -A TPROXY_OUT -m cgroup --path $cgroup_proxy -j MARK --set-mark $mark_proxy
|
||||
@@ -113,11 +134,18 @@ iptables -t mangle -A OUTPUT -j TPROXY_OUT
|
||||
#ipv6#
|
||||
ip -6 rule add fwmark $mark_proxy table $table
|
||||
ip -6 route add local default dev lo table $table
|
||||
ip6tables -t mangle -N TPROXY_ENT
|
||||
ip6tables -t mangle -A TPROXY_ENT -p tcp -j TPROXY --on-ip ::1 --on-port $port --tproxy-mark $mark_proxy
|
||||
ip6tables -t mangle -A TPROXY_ENT -p udp -j TPROXY --on-ip ::1 --on-port $port --tproxy-mark $mark_proxy
|
||||
|
||||
ip6tables -t mangle -N TPROXY_PRE
|
||||
ip6tables -t mangle -A TPROXY_PRE -p udp -m mark --mark $mark_proxy -j TPROXY --on-ip ::1 --on-port $port --tproxy-mark $mark_proxy
|
||||
ip6tables -t mangle -A TPROXY_PRE -p tcp -m mark --mark $mark_proxy -j TPROXY --on-ip ::1 --on-port $port --tproxy-mark $mark_proxy
|
||||
ip6tables -t mangle -A TPROXY_PRE -m conntrack --ctstate NEW -j CONNMARK --set-mark $make_newin
|
||||
ip6tables -t mangle -A TPROXY_PRE -m conntrack --ctstate NEW -j CONNMARK --restore-mark
|
||||
ip6tables -t mangle -A TPROXY_PRE -p udp --dport 53 -j TPROXY_ENT
|
||||
ip6tables -t mangle -A TPROXY_PRE -p tcp --dport 53 -j TPROXY_ENT
|
||||
ip6tables -t mangle -A TPROXY_PRE -p icmp -j RETURN
|
||||
ip6tables -t mangle -A TPROXY_PRE -m addrtype --dst-type LOCAL -j RETURN
|
||||
ip6tables -t mangle -A TPROXY_PRE -m pkttype --pkt-type broadcast -j RETURN
|
||||
ip6tables -t mangle -A TPROXY_PRE -m pkttype --pkt-type multicast -j RETURN
|
||||
ip6tables -t mangle -A TPROXY_PRE -j TPROXY_ENT
|
||||
ip6tables -t mangle -A PREROUTING -j TPROXY_PRE
|
||||
|
||||
ip6tables -t mangle -N TPROXY_OUT
|
||||
@@ -129,11 +157,6 @@ ip6tables -t mangle -A TPROXY_OUT -m cgroup --path $cgroup_noproxy -j RETURN
|
||||
ip6tables -t mangle -A TPROXY_OUT -m cgroup --path $cgroup_proxy -j MARK --set-mark $mark_proxy
|
||||
ip6tables -t mangle -A OUTPUT -j TPROXY_OUT
|
||||
|
||||
|
||||
## use REDIRECT
|
||||
# iptables -t nat -A OUTPUT -p tcp -m cgroup --path $cgroup_proxy -j DNAT --to-destination 127.0.0.1:12345
|
||||
# ip6tables -t nat -A OUTPUT -p tcp -m cgroup --path $cgroup_proxy -j DNAT --to-destination [::1]:12345
|
||||
|
||||
## allow to disable, order is important
|
||||
$enable_dns || iptables -t mangle -I TPROXY_OUT -p udp --dport 53 -j RETURN
|
||||
$enable_dns || ip6tables -t mangle -I TPROXY_OUT -p udp --dport 53 -j RETURN
|
||||
@@ -144,19 +167,36 @@ $enable_tcp || ip6tables -t mangle -I TPROXY_OUT -p tcp -j RETURN
|
||||
$enable_ipv4 || iptables -t mangle -I TPROXY_OUT -j RETURN
|
||||
$enable_ipv6 || ip6tables -t mangle -I TPROXY_OUT -j RETURN
|
||||
|
||||
if $enable_gateway; then
|
||||
$enable_dns || iptables -t mangle -I TPROXY_PRE -p udp --dport 53 -j RETURN
|
||||
$enable_dns || ip6tables -t mangle -I TPROXY_PRE -p udp --dport 53 -j RETURN
|
||||
$enable_udp || iptables -t mangle -I TPROXY_PRE -p udp -j RETURN
|
||||
$enable_udp || ip6tables -t mangle -I TPROXY_PRE -p udp -j RETURN
|
||||
$enable_tcp || iptables -t mangle -I TPROXY_PRE -p tcp -j RETURN
|
||||
$enable_tcp || ip6tables -t mangle -I TPROXY_PRE -p tcp -j RETURN
|
||||
$enable_ipv4 || iptables -t mangle -I TPROXY_PRE -j RETURN
|
||||
$enable_ipv6 || ip6tables -t mangle -I TPROXY_PRE -j RETURN
|
||||
fi
|
||||
|
||||
## create proxy prefix command for easy use
|
||||
# cat << 'DOC' > /usr/bin/cgproxy
|
||||
# !/usr/bin/bash
|
||||
# systemd-run -q --slice proxy.slice --scope --user $@
|
||||
# DOC
|
||||
# chmod a+x /usr/bin/cgproxy
|
||||
## do not handle local device connection through tproxy if gateway is not enabled
|
||||
$enable_gateway || iptables -t mangle -I TPROXY_PRE -m addrtype ! --src-type LOCAL -m addrtype ! --dst-type LOCAL -j RETURN
|
||||
$enable_gateway || ip6tables -t mangle -I TPROXY_PRE -m addrtype ! --src-type LOCAL -m addrtype ! --dst-type LOCAL -j RETURN
|
||||
|
||||
## make sure following rules are the first in chain TPROXY_PRE to mark new incoming connection or gateway proxy connection
|
||||
## so must put at last to insert first
|
||||
iptables -t mangle -I TPROXY_PRE -m addrtype ! --src-type LOCAL -m conntrack --ctstate NEW -j CONNMARK --set-mark $make_newin
|
||||
ip6tables -t mangle -I TPROXY_PRE -m addrtype ! --src-type LOCAL -m conntrack --ctstate NEW -j CONNMARK --set-mark $make_newin
|
||||
|
||||
## message for user
|
||||
cat << DOC
|
||||
proxied cgroup: $cgroup_proxy
|
||||
DOC
|
||||
|
||||
## tproxy need Root or cap_net_admin capability
|
||||
# setcap cap_net_admin+ep /usr/lib/v2ray/v2ray
|
||||
|
||||
if $enable_gateway; then
|
||||
iptables -t nat -A POSTROUTING -m addrtype ! --src-type LOCAL -j MASQUERADE
|
||||
ip6tables -t nat -A POSTROUTING -m addrtype ! --src-type LOCAL -j MASQUERADE
|
||||
sysctl -w net.ipv4.ip_forward=1
|
||||
sysctl -w net.ipv6.conf.all.forwarding=1
|
||||
echo "gateway enabled"
|
||||
fi
|
||||
|
||||
2
control/postinst
Normal file
2
control/postinst
Normal file
@@ -0,0 +1,2 @@
|
||||
#!/bin/sh
|
||||
systemctl enable --now cgproxy.service
|
||||
2
control/prerm
Normal file
2
control/prerm
Normal file
@@ -0,0 +1,2 @@
|
||||
#!/bin/sh
|
||||
systemctl disable --now cgproxy.service
|
||||
31
readme.md
31
readme.md
@@ -6,16 +6,17 @@
|
||||
|
||||
cgproxy will transparent proxy anything running in specific cgroup. It resembles with *proxychains* and *tsock*, but without their disadvantages, and more powerfull.
|
||||
|
||||
It aslo supports global transparent proxy. See [Global transparent proxy](#global-transparent-proxy)
|
||||
|
||||
It aslo supports global transparent proxy and gateway proxy. See [Global transparent proxy](#global-transparent-proxy) and [Gateway proxy](#gateway-proxy)
|
||||
|
||||
<!--ts-->
|
||||
|
||||
* [Transparent Proxy with cgroup v2](#transparent-proxy-with-cgroup-v2)
|
||||
* [Introduction](#introduction)
|
||||
* [Prerequest](#prerequest)
|
||||
* [How to install](#how-to-install)
|
||||
* [How to use](#how-to-use)
|
||||
* [Global transparent proxy](#global-transparent-proxy)
|
||||
* [Gateway proxy](#gateway-proxy)
|
||||
* [Other useful tools provided in this project](#other-useful-tools-provided-in-this-project)
|
||||
* [NOTES](#notes)
|
||||
* [TIPS](#tips)
|
||||
@@ -29,14 +30,13 @@ It aslo supports global transparent proxy. See [Global transparent proxy](#globa
|
||||
|
||||
- cgroup2
|
||||
|
||||
Both cgroup and cgroup2 are enable in linux by default. So you don't have to do anything about this.
|
||||
Both cgroup and cgroup2 are enabled in linux by default. So you don't have to do anything about this.
|
||||
- `systemd-cgls` to see the cgroup hierarchical tree.
|
||||
- Why cgroup v2? Because simple, elegant and intuitive.
|
||||
|
||||
- TPROXY
|
||||
|
||||
A process listening on port (e.g. 12345) to accept iptables TPROXY, for example v2ray's dokodemo-door in tproxy mode.
|
||||
- Why not REDIRECT? Because REDIRECT only supports tcp and ipv4.
|
||||
|
||||
## How to install
|
||||
|
||||
@@ -67,9 +67,12 @@ It is alreay in [archlinux AUR](https://aur.archlinux.org/packages/cgproxy/).
|
||||
cgproxy curl -vIs https://www.google.com
|
||||
```
|
||||
|
||||
More config in `/etc/cgproxy.conf`:
|
||||
<details>
|
||||
<summary>More config in `/etc/cgproxy.conf` (click to expand)</summary>
|
||||
|
||||
```bash
|
||||
# see how to configure
|
||||
# https://github.com/springzfx/cgproxy
|
||||
########################################################################
|
||||
## cgroup transparent proxy
|
||||
## any process in cgroup_proxy will be proxied, and cgroup_noproxy the opposite
|
||||
@@ -78,19 +81,22 @@ More config in `/etc/cgproxy.conf`:
|
||||
cgroup_proxy="/proxy.slice"
|
||||
cgroup_noproxy="/noproxy.slice"
|
||||
|
||||
########################################################################
|
||||
## allow as gateway for local network
|
||||
enable_gateway=false
|
||||
|
||||
########################################################################
|
||||
## listening port of another proxy process, for example v2ray
|
||||
port=12345
|
||||
|
||||
## if you set to false, it's traffic won't go through proxy, but still can go direct to internet
|
||||
########################################################################
|
||||
## if you set to false, it's traffic won't go through proxy, but still can go direct to internet
|
||||
enable_tcp=true
|
||||
enable_udp=true
|
||||
enable_ipv4=true
|
||||
enable_ipv6=true
|
||||
enable_dns=true
|
||||
|
||||
|
||||
########################################################################
|
||||
## do not modify this if you don't known what you are doing
|
||||
table=100
|
||||
@@ -98,7 +104,7 @@ mark_proxy=0x01
|
||||
mark_noproxy=0xff
|
||||
mark_newin=0x02
|
||||
```
|
||||
|
||||
</details>
|
||||
If you changed config, remember to restart service
|
||||
|
||||
```bash
|
||||
@@ -121,6 +127,11 @@ sudo systemctl restart cgproxy.service
|
||||
|
||||
- Finally, restart service `sudo systemctl restart cgproxy.service`, that's all
|
||||
|
||||
## Gateway proxy
|
||||
|
||||
- set **enable_gateway=true** in `/etc/cgproxy.conf` and restart service
|
||||
- other device set this host as gateway, and set public dns if necessary
|
||||
|
||||
## Other useful tools provided in this project
|
||||
|
||||
- `cgnoproxy` run program wihout proxy, very useful in global transparent proxy
|
||||
@@ -149,10 +160,10 @@ sudo systemctl restart cgproxy.service
|
||||
|
||||
- `cgattach` attach pid to specific cgroup, and has *suid* bit set by default, be careful to use on multi-user server for securiry. To avoid this situation, you can remove the *suid* bit , then it will fallback to use *sudo*, with *visudo* you can restrict permission or set NOPASSWD for youself.
|
||||
|
||||
- v2ray TPROXY need root or special permiassion
|
||||
- v2ray TPROXY need root or special permission
|
||||
|
||||
```bash
|
||||
sudo setcap "cap_net_bind_service=+ep cap_net_admin=+ep" /usr/lib/v2ray/v2ray
|
||||
sudo setcap "cap_net_admin,cap_net_bind_service=ep" /usr/lib/v2ray/v2ray
|
||||
```
|
||||
|
||||
## TIPS
|
||||
|
||||
Reference in New Issue
Block a user