This commit is contained in:
SkyperTHC 2023-11-07 08:17:51 +00:00
parent 214304494c
commit 41bbf128b6
No known key found for this signature in database
GPG Key ID: A9BD386DF9113CD6
19 changed files with 245 additions and 84 deletions

@ -1,5 +1,8 @@
0.5.0 - 2023-10-00 0.5.0 - 2023-11-00
* Access to /dev/kvm (for token users). * Configurable access to /dev/kvm
* Reverse Port via curl sf/port
* Token via curl sf/set -dtoken=<NAME>
* per LG traffic shaping
0.4.9p3 - 2023-09-20 0.4.9p3 - 2023-09-20
* Helix (hx) * Helix (hx)

@ -73,7 +73,25 @@ http {
rewrite /net /net/; rewrite /net /net/;
rewrite /wg /wg/; rewrite /wg /wg/;
rewrite /dmesg /dmesg/; rewrite /dmesg /dmesg/;
rewrite /port /port/;
rewrite /set /set/;
location ~* ^/set/.* {
fastcgi_param REMOTE_ADDR $remote_addr;
fastcgi_param REQUEST_URI $request_uri;
fastcgi_param REQUEST_BODY $request_body;
fastcgi_param FCGI_CMD set;
fastcgi_param SCRIPT_FILENAME /cgi-bin/rpc;
fastcgi_pass unix:/dev/shm/sf/master/fcgiwrap.socket;
}
location ~* ^/port/.* {
fastcgi_param REMOTE_ADDR $remote_addr;
fastcgi_param REQUEST_URI $request_uri;
fastcgi_param REQUEST_BODY $request_body;
fastcgi_param FCGI_CMD port;
fastcgi_param SCRIPT_FILENAME /cgi-bin/rpc;
fastcgi_pass unix:/dev/shm/sf/master/fcgiwrap.socket;
}
location ~* ^/net/.* { location ~* ^/net/.* {
fastcgi_param REMOTE_ADDR $remote_addr; fastcgi_param REMOTE_ADDR $remote_addr;
fastcgi_param REQUEST_URI $request_uri; fastcgi_param REQUEST_URI $request_uri;

@ -13,20 +13,25 @@
#SF_USER_MEMORY_LIMIT=256m #SF_USER_MEMORY_LIMIT=256m
#SF_USER_MEMORY_AND_SWAP_LIMIT= # Not set=no swap. Example =4g #SF_USER_MEMORY_AND_SWAP_LIMIT= # Not set=no swap. Example =4g
#SF_USER_PIDS_LIMIT=128 #SF_USER_PIDS_LIMIT=128
#SF_USER_CPU_SHARE=8 # 2..1024. docker's default is 1024. 2048 gives 2x and 512 half. #SF_USER_CPU_SHARE=8 # 2..1024. docker's default is 1024. 2048 gives 2x and 512 half.
#SF_USER_OOM_SCORE=500 #SF_USER_OOM_SCORE=500
#SF_USER_NICE_SCORE=10 #-20 (most often scheduled) to 19 (least often scheduled) #SF_USER_NICE_SCORE=10 #-20 (most often scheduled) to 19 (least often scheduled)
#SF_ULIMIT_NOFILE="1024:8192" #SF_ULIMIT_NOFILE="8192" # Number of open files 16384:65536" _per_ container
#SF_USER_BLKIO_WEIGHT=100 # Reduced to 10 during DoS #SF_USER_BLKIO_WEIGHT=100 # Reduced to 10 during DoS
#SF_MAX_STRAIN=100 #SF_MAX_STRAIN=100
#SF_SHM_SIZE= # Hard limit is USER_MEMORY_LIMIT #SF_SHM_SIZE= # Hard limit is USER_MEMORY_LIMIT
#SF_CPUS= # automatic between 1..4 depending on host's cpu count #SF_CPUS= # automatic between 1..4 depending on host's cpu count
#SF_TOKEN_PROHIBITED= # Prohibit the use of TOKENS
#SF_USER_SYN_BURST=8196 # Can send 8k tcp sync packets #SF_USER_SYN_BURST=8196 # Can send 8k tcp sync packets
#SF_USER_SYN_LIMIT=1 # Thereafter refill with 1 syn/second, 0=unlimited #SF_USER_SYN_LIMIT=1 # Thereafter refill with 1 syn/second, 0=unlimited
#SF_USER_UL_RATE= # Limit LG egress speed (10Mbit, 20Mbit, ...)
#SF_SYN_BURST=10000 # Global limit. (0-10000) #SF_SYN_BURST=10000 # Global limit. (0-10000)
#SF_SYN_LIMIT=200 # Global Limit. 0=unlimited #SF_SYN_LIMIT=200 # Global Limit. 0=unlimited
#SF_RPORT=1 # Enable reverse ports for users.
#SF_RPORT_ON_LOGIN= # Auto-assign a reverse port on log in. Implies SF_RPORT=1.
## Per user limit of root filesystem / ## Per user limit of root filesystem /
#SF_USER_ROOT_FS_SIZE= # e.g. 16MB, 2GB, 0=unlimited. Not set=read-only #SF_USER_ROOT_FS_SIZE= # e.g. 16MB, 2GB, 0=unlimited. Not set=read-only
#SF_USER_ROOT_FS_INODE=65536 # Inode Limit. Only enforced if FS_SIZE > 0 #SF_USER_ROOT_FS_INODE=65536 # Inode Limit. Only enforced if FS_SIZE > 0
@ -38,6 +43,7 @@
#SF_USER_DEV_KVM= # =1 to allow access to /dev/kvm (Warning: User can DoS PHY) #SF_USER_DEV_KVM= # =1 to allow access to /dev/kvm (Warning: User can DoS PHY)
#SF_ALLOW_SRC_TOR= # =1 to allow connections from TOR #SF_ALLOW_SRC_TOR= # =1 to allow connections from TOR
#SF_USER_IMMUNE= # =1 to not ban user by lgban
# Limit to 8 concurrently running servers per IP # Limit to 8 concurrently running servers per IP
#SF_LIMIT_SERVER_BY_IP=8 #SF_LIMIT_SERVER_BY_IP=8

@ -15,10 +15,11 @@ while [[ $i -gt 0 ]]; do
rsync -ral "${h}":/sf/config/db/banned "${h}":/sf/config/db/token "${h}":/sf/config/db/limits . rsync -ral "${h}":/sf/config/db/banned "${h}":/sf/config/db/token "${h}":/sf/config/db/limits .
done done
echo "====================================================" echo "==[DOWN done. Press Enter to start UP]=================================================="
read
i=0 i=0
for h in "${HOSTS[@]}"; do for h in "${HOSTS[@]}"; do
echo "#$i Syncing ${h} UP" echo "#$i Syncing ${h} UP"
rsync -ral banned token limits "${h}":'/sf/config/db' rsync -ral banned token limits "${h}":'/sf/config/db'
((i++)) ((i++))
done done

@ -44,6 +44,7 @@ services:
- "${SF_BASEDIR:-.}/config/etc/sf:/config/etc/sf:ro" - "${SF_BASEDIR:-.}/config/etc/sf:/config/etc/sf:ro"
- "${SF_BASEDIR:-.}/data:/encfs/raw" - "${SF_BASEDIR:-.}/data:/encfs/raw"
- "${SF_SHMDIR:-/dev/shm/sf}/encfs-sec:/encfs/sec:shared" - "${SF_SHMDIR:-/dev/shm/sf}/encfs-sec:/encfs/sec:shared"
- "${SF_SHMDIR:-/dev/shm/sf}/run:/sf/run:ro"
- "${SF_SHMDIR:-/dev/shm/sf}/run/encfsd/user:/sf/run/encfsd/user" - "${SF_SHMDIR:-/dev/shm/sf}/run/encfsd/user:/sf/run/encfsd/user"
- "${SF_BASEDIR:-.}/sfbin:/sf/bin:ro" - "${SF_BASEDIR:-.}/sfbin:/sf/bin:ro"
- "${SF_OVERLAYDIR:-/var/lib/docker/overlay2}:/var/lib/docker/overlay2:ro" - "${SF_OVERLAYDIR:-/var/lib/docker/overlay2}:/var/lib/docker/overlay2:ro"
@ -253,7 +254,7 @@ services:
- "${SF_SHMDIR:-/dev/shm/sf}/config-for-guest:/config/guest" # vpn_status to guest - "${SF_SHMDIR:-/dev/shm/sf}/config-for-guest:/config/guest" # vpn_status to guest
- "${SF_SHMDIR:-/dev/shm/sf}/run/redis/sock:/redis-sock" - "${SF_SHMDIR:-/dev/shm/sf}/run/redis/sock:/redis-sock"
- "${SF_BASEDIR:-.}/sfbin:/sf/bin:ro" - "${SF_BASEDIR:-.}/sfbin:/sf/bin:ro"
# entrypoint: sleep infinity # FIXME-2022 # entrypoint: sleep infinity # FIXME-TESTING
mullvad: mullvad:
@ -421,6 +422,7 @@ services:
- SF_NORDVPN_IP=${SF_NORDVPN_IP:?} - SF_NORDVPN_IP=${SF_NORDVPN_IP:?}
- SF_CRYPTOSTORM_IP=${SF_CRYPTOSTORM_IP:?} - SF_CRYPTOSTORM_IP=${SF_CRYPTOSTORM_IP:?}
- SF_MULLVAD_IP=${SF_MULLVAD_IP:?} - SF_MULLVAD_IP=${SF_MULLVAD_IP:?}
- SF_GUEST_MTU=${SF_GUEST_MTU:-1420}
volumes: volumes:
- "${SF_SHMDIR:-/dev/shm/sf}/run/vpn:/sf/run/vpn" - "${SF_SHMDIR:-/dev/shm/sf}/run/vpn:/sf/run/vpn"
- "${SF_BASEDIR:-.}/config/etc/sf:/config/host/etc/sf:ro" - "${SF_BASEDIR:-.}/config/etc/sf:/config/host/etc/sf:ro"
@ -458,6 +460,7 @@ services:
- SF_MULLVAD_ROUTE=${SF_MULLVAD_ROUTE:?} - SF_MULLVAD_ROUTE=${SF_MULLVAD_ROUTE:?}
- SF_DNS=${SF_NET_VPN_DNS_IP} - SF_DNS=${SF_NET_VPN_DNS_IP}
- SF_NET_LG_ROUTER_IP=${SF_NET_LG_ROUTER_IP:?} - SF_NET_LG_ROUTER_IP=${SF_NET_LG_ROUTER_IP:?}
- SF_HOST_MTU=${SF_HOST_MTU:-1500}
volumes: volumes:
- "${SF_SHMDIR:-/dev/shm/sf}:/dev/shm/sf" - "${SF_SHMDIR:-/dev/shm/sf}:/dev/shm/sf"
- "${SF_BASEDIR:-.}/config/db:/config/db" - "${SF_BASEDIR:-.}/config/db:/config/db"
@ -638,7 +641,7 @@ services:
- SF_DIRECT - SF_DIRECT
- SF_DEBUG - SF_DEBUG
- SF_BACKING_FS - SF_BACKING_FS
# - SF_DEBUG_SSHD=1 # FIXME-2022 sshd debug # - SF_DEBUG_SSHD=1 # FIXME-TESTING sshd debug
volumes: volumes:
- "${SF_BASEDIR:-.}/config:/config/host" - "${SF_BASEDIR:-.}/config:/config/host"
- "${SF_BASEDIR:-.}/data/share:/sf/share:ro" - "${SF_BASEDIR:-.}/data/share:/sf/share:ro"
@ -650,8 +653,8 @@ services:
- "/var/run/docker.sock:/var/run/docker.sock" - "/var/run/docker.sock:/var/run/docker.sock"
- "/var/lib/lxcfs:/var/lib/lxcfs:ro" - "/var/lib/lxcfs:/var/lib/lxcfs:ro"
- "${SF_SHMDIR:-/dev/shm/sf}/run/redis/sock:/redis-sock" - "${SF_SHMDIR:-/dev/shm/sf}/run/redis/sock:/redis-sock"
# - /research/segfault/host/fs-root/bin/segfaultsh:/bin/segfaultsh:ro # FIXME-2022 # - /research/segfault/host/fs-root/bin/segfaultsh:/bin/segfaultsh:ro # FIXME-TESTING
# - /research/segfault/host:/host:ro # FIXME-2022 sshd debug # - /research/segfault/host:/host:ro # FIXME-TESTING sshd debug
nginx: nginx:
image: nginx image: nginx
@ -671,9 +674,17 @@ services:
- "${SF_BASEDIR:-.}/config/etc/nginx/nginx.conf:/etc/nginx/nginx.conf:ro" - "${SF_BASEDIR:-.}/config/etc/nginx/nginx.conf:/etc/nginx/nginx.conf:ro"
networks: networks:
# Force docker0
default:
driver: bridge
driver_opts:
com.docker.network.driver.mtu: ${SF_HOST_MTU:-1500}
vpn-net: vpn-net:
name: sf-vpn name: sf-vpn
driver: bridge driver: bridge
driver_opts:
com.docker.network.driver.mtu: ${SF_HOST_MTU:-1500}
ipam: ipam:
config: config:
- subnet: ${SF_NET_VPN:?} - subnet: ${SF_NET_VPN:?}
@ -684,6 +695,8 @@ networks:
# expects all host traffic to arrive at SF_NET_DIRECT_ROUTE_IP. # expects all host traffic to arrive at SF_NET_DIRECT_ROUTE_IP.
name: A-sf-direct name: A-sf-direct
driver: bridge driver: bridge
driver_opts:
com.docker.network.driver.mtu: ${SF_HOST_MTU:-1500}
ipam: ipam:
config: config:
- subnet: ${SF_NET_DIRECT:?} - subnet: ${SF_NET_DIRECT:?}
@ -692,6 +705,8 @@ networks:
# sf-host and gsnc # sf-host and gsnc
name: sf-access name: sf-access
driver: bridge driver: bridge
driver_opts:
com.docker.network.driver.mtu: ${SF_HOST_MTU:-1500}
ipam: ipam:
config: config:
- subnet: ${SF_NET_ACCESS:?} - subnet: ${SF_NET_ACCESS:?}
@ -699,6 +714,8 @@ networks:
dmz-net: dmz-net:
name: sf-dmz name: sf-dmz
driver: bridge driver: bridge
driver_opts:
com.docker.network.driver.mtu: ${SF_HOST_MTU:-1500}
ipam: ipam:
config: config:
- subnet: ${SF_NET_DMZ:?} - subnet: ${SF_NET_DMZ:?}
@ -706,6 +723,8 @@ networks:
dns-doh-net: dns-doh-net:
name: sf-dns-doh name: sf-dns-doh
driver: bridge driver: bridge
driver_opts:
com.docker.network.driver.mtu: ${SF_HOST_MTU:-1500}
ipam: ipam:
config: config:
- subnet: ${SF_NET_DOH:?} - subnet: ${SF_NET_DOH:?}
@ -715,7 +734,7 @@ networks:
name: sf-guest name: sf-guest
driver: bridge driver: bridge
driver_opts: driver_opts:
com.docker.network.driver.mtu: 1420 com.docker.network.driver.mtu: ${SF_GUEST_MTU:-1420}
# Can not use 'internal'. This will only remvoe the host's bridge # Can not use 'internal'. This will only remvoe the host's bridge
# but this also means we can not route via 10.11.0.* even if we can # but this also means we can not route via 10.11.0.* even if we can
# ping the router. # ping the router.

@ -31,6 +31,7 @@ stop_lg()
rm -f "/sf/run/pids/lg-${lid}.pid" rm -f "/sf/run/pids/lg-${lid}.pid"
rm -f "/sf/run/ips/lg-${lid}.ip" rm -f "/sf/run/ips/lg-${lid}.ip"
rm -rf "/config/self-for-guest/lg-${lid}" rm -rf "/config/self-for-guest/lg-${lid}"
rm -rf "/sf/run/users/lg-${lid}"
# Tear down container # Tear down container
[[ -n $is_container ]] && docker stop "lg-$lid" &>/dev/nuill [[ -n $is_container ]] && docker stop "lg-$lid" &>/dev/nuill

@ -124,7 +124,6 @@ encfs_mount_server()
load_limits() load_limits()
{ {
local lid local lid
local token
lid="$1" lid="$1"
unset SF_USER_FS_SIZE unset SF_USER_FS_SIZE
@ -132,16 +131,7 @@ load_limits()
unset SF_USER_ROOT_FS_SIZE unset SF_USER_ROOT_FS_SIZE
unset SF_USER_ROOT_FS_INODE unset SF_USER_ROOT_FS_INODE
# First source global source "/sf/run/users/lg-${lid}/limits.txt"
[[ -f "/config/etc/sf/sf.conf" ]] && eval "$(grep ^SF_ "/config/etc/sf/sf.conf")"
# Then Token
[[ -f "/config/db/user/lg-${lid}/token" ]] && {
token=$(<"/config/db/user/lg-${lid}/token")
source "/config/db/token/token-${token,,}.conf" 2>/dev/null
}
# Then source user specific limits
[[ -f "/config/db/user/lg-${lid}/limits.conf" ]] && eval "$(grep ^SF_ "/config/db/user/lg-${lid}/limits.conf")"
} }
dir2prjid() dir2prjid()

@ -49,6 +49,7 @@ RUN /pkg-install.sh BASE apt-get install -y --no-install-recommends \
jq \ jq \
less \ less \
openssh-sftp-server \ openssh-sftp-server \
pipx \
python3-pip \ python3-pip \
screen \ screen \
sharutils \ sharutils \
@ -227,7 +228,6 @@ RUN /pkg-install.sh LARGE apt-get install -y --no-install-recommends \
p7zip-full \ p7zip-full \
peass \ peass \
pip \ pip \
pipx \
proxychains \ proxychains \
python2-minimal \ python2-minimal \
python-is-python3 \ python-is-python3 \

@ -253,6 +253,9 @@ lsg() {
ls -Alh --color=always | grep -i -E "$*" ls -Alh --color=always | grep -i -E "$*"
} }
noansi() { sed -e 's/\x1b\[[0-9;]*m//g'; }
alias nocol=noansi
[[ -f /usr/bin/fdfind ]] && alias fd=fdfind [[ -f /usr/bin/fdfind ]] && alias fd=fdfind
[[ -z $LANG ]] && export LANG=en_US.UTF-8 [[ -z $LANG ]] && export LANG=en_US.UTF-8

@ -18,13 +18,22 @@ function cnf_preexec() {
cmd="$1" cmd="$1"
# Remove any variable like in `FOO=blah duf` # Remove any variable like in `FOO=blah duf`
# Test: X="FOO BAR" Y="hello world" Z=mememe whoami
while :; do while :; do
cmd="${cmd#"${cmd%%[^[:space:]]*}"}" # remove leading whitespace characters cmd="${cmd#"${cmd%%[^[:space:]]*}"}" # remove leading whitespace characters
[[ $cmd != *" "* ]] && break [[ $cmd != *" "* ]] && break
# Check if first string before " " is a variable (contains '=') # Check if first string before \s is a variable (contains '=')
[[ ${cmd%% *} != *"="* ]] && break [[ ${cmd%% *} != *"="* ]] && break
# HERE: It's a variable. Remove it for 'cmd'
cmd=${cmd#* } # HERE: It's a variable. X=foo, X="foo" or X="foo bar". Remove it for 'cmd'
[[ ${cmd%% *} != *"=\""* ]] && {
# HERE: variable without quotes
cmd=${cmd#* }
continue;
}
# HERE: X="foo" or X="foo bar"
cmd=${cmd#*=\"}
cmd=${cmd#*\" }
done done
typeset -g cnf_command="${cmd%% *}" typeset -g cnf_command="${cmd%% *}"
@ -32,7 +41,7 @@ function cnf_preexec() {
# HERE: command not found # HERE: command not found
[ -n "$cnf_once" ] && return [ -n "$cnf_once" ] && return
typeset -g cnf_once="1" typeset -g cnf_once="1"
echo -en "\e[0;31m" echo -en "💥 \e[0;31m"
} }
function cnf_precmd() { function cnf_precmd() {
@ -42,7 +51,7 @@ function cnf_precmd() {
echo -en "\e[0m" echo -en "\e[0m"
(($cnf_ret)) && [ -n "$cnf_command" ] && { (($cnf_ret)) && [ -n "$cnf_command" ] && {
whence -- "${cnf_command}" >& /dev/null || whence -- "${cnf_command}" >& /dev/null ||
echo -e "\e[0;34m[\e[0;33mSF\e[0;34m]\e[0m ¯\_(⊙︿⊙)_/¯ Like us to install \e[0;36m${cnf_command}\e[0m?\n\e[0;34m[\e[0;33mSF\e[0;34m] \e[1;37mTell us at https://t.me/thcorg\e[0m" echo -e "\e[0;34m[\e[0;33mSF\e[0;34m]\e[0m ¯\_(⊙︿⊙)_/¯ Like us to install \e[0;36m${cnf_command}\e[0m?\n\e[0;34m[\e[0;33mSF\e[0;34m] \e[1;37mTell us at https://t.me/thcorg\e[0m 🌈😘"
unset cnf_command unset cnf_command
} }
} }

@ -81,7 +81,8 @@ loc="${loc:0:15}"
IPPORT="${CDY}$(</config/self/reverse_ip):$(</config/self/reverse_port)" IPPORT="${CDY}$(</config/self/reverse_ip):$(</config/self/reverse_port)"
[[ -f /config/self/reverse_geoip ]] && IPPORT+=" ${CF}($(<config/self/reverse_geoip))" [[ -f /config/self/reverse_geoip ]] && IPPORT+=" ${CF}($(<config/self/reverse_geoip))"
} }
[[ -z $IPPORT ]] && IPPORT="${CDR}N/A${CN}" token_str="${CDC}${CF}Type ${CN}${CDC}curl sf/port${CN}"
[[ -z $IPPORT ]] && IPPORT="${CDC}Type ${CC}curl sf/port${CDC} for reverse port."
### Always show when a Token is being used but obfuscate unless server creation ### Always show when a Token is being used but obfuscate unless server creation
### or info is typed. ### or info is typed.

@ -84,6 +84,7 @@ xmkdir()
xln() xln()
{ {
[[ -L "$2" ]] && return
[[ -e "$2" ]] && return [[ -e "$2" ]] && return
ln -s "$1" "$2" ln -s "$1" "$2"
} }

@ -102,6 +102,7 @@ mk_userdir()
mk_userdir "${SF_RUN_DIR}/pids" mk_userdir "${SF_RUN_DIR}/pids"
mk_userdir "${SF_RUN_DIR}/ips" mk_userdir "${SF_RUN_DIR}/ips"
mk_userdir "${SF_RUN_DIR}/users"
[[ ! -d "${SF_RUN_DIR}/logs" ]] && mkdir -p "${SF_RUN_DIR}/logs" [[ ! -d "${SF_RUN_DIR}/logs" ]] && mkdir -p "${SF_RUN_DIR}/logs"
chown 1000 "${SF_RUN_DIR}/logs" chown 1000 "${SF_RUN_DIR}/logs"

@ -56,7 +56,7 @@ _log()
# Replace ' with '"'"' # Replace ' with '"'"'
str="${*//\'/\'\"\'\"\'}" str="${*//\'/\'\"\'\"\'}"
# NOTE: segfault.log must be owned 1000:1000 # NOTE: segfault.log must be owned 1000:1000
bash -c "{ echo -en '[$(date '+%F %T' -u)]${p:- }'; echo -e '[${CDM}${LID}${CN}] $str';} 2>/dev/null >>'/sf/run/logs/segfault.log'" bash -c "{ echo -en '[$(date '+%F %T' -u)]${p:- }'; echo -e '[${CDM}${LID}${CN}] $str';} 2>/dev/null >>'${SF_RUN_DIR}/logs/segfault.log'"
} }
LOG(){ _log "" "$@"; } LOG(){ _log "" "$@"; }
@ -197,6 +197,12 @@ exec_errnull()
fi fi
} }
logpipe() {
[[ ! -e "${SF_RUN_DIR}/logpipe/logPipe.sock" ]] && return
echo "$*" | exec_devnull unix-socket-client
}
# Overcoming a restricted shell. Write $1 to file in $2 # Overcoming a restricted shell. Write $1 to file in $2
# tofile "foobar \$HOME \"|';id;" world.txt # tofile "foobar \$HOME \"|';id;" world.txt
tofile() tofile()
@ -319,7 +325,7 @@ init_vars()
init_defaults init_defaults
init_emu init_emu
[[ -f "/sf/run/logs/segfault.log" ]] && IS_LOGGING=1 [[ -f "${SF_RUN_DIR}/logs/segfault.log" ]] && IS_LOGGING=1
NOW="$(date +%s)" NOW="$(date +%s)"
[[ -z $YOUR_IP ]] && { [[ -z $YOUR_IP ]] && {
@ -341,11 +347,13 @@ init_vars()
SF_USER_DB_DIR="${db_dir}/user/lg-${LID}" SF_USER_DB_DIR="${db_dir}/user/lg-${LID}"
SF_BLACKLIST_DIR="${db_dir}/banned" SF_BLACKLIST_DIR="${db_dir}/banned"
SF_TOKEN_DIR="${db_dir}/token" SF_TOKEN_DIR="${db_dir}/token"
SF_LIMITS_DIR="${db_dir}/limits"
HNLID_DIR="${db_dir}/hn" HNLID_DIR="${db_dir}/hn"
SF_RUN_DIR="/sf/run/" SF_RUN_DIR="/sf/run"
LG_PID_DIR="${SF_RUN_DIR}/pids" LG_PID_DIR="${SF_RUN_DIR}/pids"
LG_PID_FILE="${LG_PID_DIR}/pid-${LID}.$$" LG_PID_FILE="${LG_PID_DIR}/pid-${LID}.$$"
LG_RUN_DIR="${SF_RUN_DIR}/users/lg-${LID}"
TS_LOGOUT_FILE="${SF_USER_DB_DIR}/ts_logout" TS_LOGOUT_FILE="${SF_USER_DB_DIR}/ts_logout"
TS_LOGIN_FILE="${SF_USER_DB_DIR}/ts_login" TS_LOGIN_FILE="${SF_USER_DB_DIR}/ts_login"
TS_RUN_FILE="${SF_USER_DB_DIR}/ts_run" TS_RUN_FILE="${SF_USER_DB_DIR}/ts_run"
@ -365,6 +373,7 @@ init_vars()
fi fi
fi fi
xmkdir "${LG_RUN_DIR}"
# Check if we are still in sshd's Network Namespace # Check if we are still in sshd's Network Namespace
IS_SSHD_NS_NET=1 IS_SSHD_NS_NET=1
[[ ${SF_NS_NET:?} != "$(readlink /proc/self/ns/net)" ]] && unset IS_SSHD_NS_NET # Already inside LG's Network Namespace [[ ${SF_NS_NET:?} != "$(readlink /proc/self/ns/net)" ]] && unset IS_SSHD_NS_NET # Already inside LG's Network Namespace
@ -374,21 +383,6 @@ init_vars()
trap cb_sighup SIGPIPE trap cb_sighup SIGPIPE
} }
mk_portforward()
{
local ipport
ipport=$(echo -e "DEL portd:response-${LID}\"\n\
RPUSH portd:blcmd \"getport ${LID}\"\n\
BLPOP portd:response-${LID} 5" | redr) || return
# DEBUGF "ipport='$ipport'"
ipport="${ipport##*$'\n'}"
[[ ! "${ipport##*:}" -gt 0 ]] && { DEBUGF "Failed to get Reverse Port Forward (ipport='$ipport')"; return; }
# The PortD add's a /sf/run/self/reverse_forward.
DEBUGF "Reverse Port Forward: $ipport"
}
# Called when a new server is created. # Called when a new server is created.
print_disclaimer() print_disclaimer()
{ {
@ -514,7 +508,7 @@ sshd_to_ns()
# Load PID of container's init process (uid=1000) # Load PID of container's init process (uid=1000)
[[ -z $LG_PID ]] && { [[ -z $LG_PID ]] && {
LG_PID=$(<"/sf/run/pids/lg-${LID}.pid") LG_PID=$(<"${LG_PID_DIR}/lg-${LID}.pid")
[[ -z $LG_PID ]] && ERREXIT 222 "Init PID not found." [[ -z $LG_PID ]] && ERREXIT 222 "Init PID not found."
} }
ln -sf "/proc/${LG_PID}/ns/net" "/dev/shm/ns-net-${PPID}" ln -sf "/proc/${LG_PID}/ns/net" "/dev/shm/ns-net-${PPID}"
@ -532,12 +526,16 @@ spawn_shell_exit()
sem_release sem_release
# Add a log entry into elastisearch using logpipe
logpipe "Type:Login|LID:${LID}|Hostname:${SF_HOSTNAME}||C_ISO:${YOUR_COUNTRY_ISO}|CONTINENT=${YOUR_CONTINENT_CODE}|"
# Update current IP: # Update current IP:
tofile "${YOUR_IP_DISPLAY:?}" "/config/self-for-guest/lg-${LID}/ip" tofile "${YOUR_IP_DISPLAY:?}" "/config/self-for-guest/lg-${LID}/ip"
tofile "${YOUR_IP:?}" "/sf/run/ips/lg-${LID}.ip" tofile "${YOUR_IP:?}" "${SF_RUN_DIR}/ips/lg-${LID}.ip"
[[ -n $YOUR_GEOIP ]] && tofile "${YOUR_GEOIP}" "/config/self-for-guest/lg-${LID}/geoip" [[ -n $YOUR_GEOIP ]] && tofile "${YOUR_GEOIP}" "/config/self-for-guest/lg-${LID}/geoip"
# Request a reverse Port Forward # Request a reverse Port Forward
[[ ! -f "/config/self-for-guest/lg-${LID}/reverse_ip" ]] && mk_portforward "${LID}" [[ -n $SF_RPORT_ON_LOGIN ]] && [[ -n $SF_RPORT ]] && [[ ! -f "/config/self-for-guest/lg-${LID}/reverse_ip" ]] && exec_devnull docker exec --user 0:0 "lg-${LID}" curl -s sf/port
# Warn user if this is the last server by IP (after semaphore has been released) # Warn user if this is the last server by IP (after semaphore has been released)
[[ -n $IS_SHOW_LAST_SERVER ]] && show_last_server "$IS_SHOW_LAST_SERVER" [[ -n $IS_SHOW_LAST_SERVER ]] && show_last_server "$IS_SHOW_LAST_SERVER"
@ -606,13 +604,22 @@ BLPOP \"encfs-$$-${LID}-X\" 10" | red) || return 255
return 0 return 0
} }
load_limits_fn() {
local fn=$1
[[ ! -f "$fn" ]] && return
eval "$(<"${fn}")"
}
load_limits() load_limits()
{ {
# Set the default values. # Set the default values.
# No default for ROOT_FS limit. Should be set in sf.conf or if not set # No default for ROOT_FS limit. Should be set in sf.conf or if not set
# then root is mounted read-only # then root is mounted read-only
#SF_USER_ROOT_FS_SIZE=2GB # SF_USER_ROOT_FS_SIZE=8g
SF_USER_ROOT_FS_INODE=65536 # SF_USER_ROOT_FS_INODE=65536
# SF_USER_FS_SIZE=16g
# SF_USER_FS_INODE=65536
SF_USER_MEMORY_LIMIT=256m SF_USER_MEMORY_LIMIT=256m
SF_USER_PIDS_LIMIT=128 SF_USER_PIDS_LIMIT=128
SF_USER_CPU_SHARE=8 SF_USER_CPU_SHARE=8
@ -620,11 +627,12 @@ load_limits()
SF_USER_NICE_SCORE=10 SF_USER_NICE_SCORE=10
SF_LIMIT_SERVER_BY_IP=8 SF_LIMIT_SERVER_BY_IP=8
SF_USER_BLKIO_WEIGHT=100 SF_USER_BLKIO_WEIGHT=100
SF_ULIMIT_NOFILE="1024:8192" SF_ULIMIT_NOFILE="8192"
SF_USER_SYN_BURST=8196 SF_USER_SYN_BURST=8196
SF_USER_SYN_LIMIT=1 SF_USER_SYN_LIMIT=1
SF_USER_DL_BURST=8gb SF_USER_DL_BURST=8gb
SF_USER_UL_BURST=8gb SF_USER_UL_BURST=8gb
SF_RPORT=1
# No new shells until load goes below STRAIN*NPROC. # No new shells until load goes below STRAIN*NPROC.
# Should be larger than ContainerGuard's strain when CG starts killing # Should be larger than ContainerGuard's strain when CG starts killing
@ -634,7 +642,13 @@ load_limits()
# dd bs=1M count=10024 if=/dev/zero of=/dump.dat oflag=direct status=progress # dd bs=1M count=10024 if=/dev/zero of=/dump.dat oflag=direct status=progress
# Source system wide limits # Source system wide limits
[[ -f "${SF_ETCSF_DIR}/sf.conf" ]] && eval "$(<"${SF_ETCSF_DIR}/sf.conf")" load_limits_fn "${SF_ETCSF_DIR}/sf.conf"
# Source continent specific limits
load_limits_fn "${SF_LIMITS_DIR}/limits-continent-${YOUR_CONTINENT_CODE}.conf"
# Source country specific limits
load_limits_fn "${SF_LIMITS_DIR}/limits-country-${YOUR_COUNTRY_ISO}.conf"
# Then source token specific limits (and write TOKEN information) # Then source token specific limits (and write TOKEN information)
if [[ -z $SF_TOKEN ]]; then if [[ -z $SF_TOKEN ]]; then
@ -666,10 +680,17 @@ load_limits()
} }
# Then source user specific limits # Then source user specific limits
[[ -f "${SF_USER_DB_DIR}/limits.conf" ]] && eval "$(<"${SF_USER_DB_DIR}/limits.conf")" load_limits_fn "${SF_USER_DB_DIR}/limits.conf"
# Then source IP specific limits # Then source IP specific limits
[[ -f "${SF_ETCSF_DIR}/sf-${YOUR_IP}.conf" ]] && eval "$(<"${SF_ETCSF_DIR}/sf-${YOUR_IP}.conf")" load_limits_fn "${SF_ETCSF_DIR}/sf-${YOUR_IP}.conf"
# Add SF docker args to LG container.
# DISABLED: otherwise, an attacker with write access to token/limits (e.g. through a web user-management interface) could own the PHY.
# [[ ${#SF_USER_DOCKER_ARGS[@]} -gt 0 ]] && DOCKER_ARGS+=("${SF_USER_DOCKER_ARGS[@]}")
# User gets a reverse port on login
[[ -n $SF_RPORT_ON_LOGIN ]] && SF_RPORT=1
# Set swap limit if not set in sf.conf # Set swap limit if not set in sf.conf
[[ -z $SF_USER_MEMORY_AND_SWAP_LIMIT ]] && SF_USER_MEMORY_AND_SWAP_LIMIT="$SF_USER_MEMORY_LIMIT" [[ -z $SF_USER_MEMORY_AND_SWAP_LIMIT ]] && SF_USER_MEMORY_AND_SWAP_LIMIT="$SF_USER_MEMORY_LIMIT"
@ -692,7 +713,7 @@ load_limits()
DOCKER_ARGS+=("--oom-score-adj=${SF_USER_OOM_SCORE}") DOCKER_ARGS+=("--oom-score-adj=${SF_USER_OOM_SCORE}")
DOCKER_ARGS+=("--blkio-weight=${SF_USER_BLKIO_WEIGHT}") DOCKER_ARGS+=("--blkio-weight=${SF_USER_BLKIO_WEIGHT}")
[[ -n $SF_USER_DEV_KVM ]] && DOCKER_ARGS+=("--device=/dev/kvm") [[ -n $SF_USER_DEV_KVM ]] && [[ -e /dev/kvm ]] && DOCKER_ARGS+=("--device=/dev/kvm")
if [[ -z $SF_USER_ROOT_FS_SIZE ]]; then if [[ -z $SF_USER_ROOT_FS_SIZE ]]; then
DOCKER_ARGS+=("--read-only") DOCKER_ARGS+=("--read-only")
@ -708,6 +729,8 @@ load_limits()
} }
fi fi
write_lg_limits
# NOTE: This is no longer used because /dev/shm is now mounted as tmpfs to make UML work # NOTE: This is no longer used because /dev/shm is now mounted as tmpfs to make UML work
# [[ -n $SF_SHM_SIZE ]] && DOCKER_ARGS+=("--shm-size=$SF_SHM_SIZE") # [[ -n $SF_SHM_SIZE ]] && DOCKER_ARGS+=("--shm-size=$SF_SHM_SIZE")
@ -716,11 +739,15 @@ load_limits()
setup_fs_limit || ERREXIT 202 "Can't configure XFS limit" setup_fs_limit || ERREXIT 202 "Can't configure XFS limit"
} }
# Publish user limits to self/limits # Publish user limits to self/limits, human readable.
write_guest_limits() write_guest_limits()
{ {
local is_token local is_token
local is_ro local is_ro
local tx;
tx="${SF_USER_UL_RATE}"
[[ -z $SF_USER_UL_RATE ]] && tx="${SF_MAXOUT}"
is_token="no" is_token="no"
[[ -n $SF_TOKEN ]] && is_token="yes" [[ -n $SF_TOKEN ]] && is_token="yes"
@ -737,7 +764,7 @@ SHM_SIZE=${SF_SHM_SIZE}
PIDS=${SF_USER_PIDS_LIMIT} PIDS=${SF_USER_PIDS_LIMIT}
MEMORY=${SF_USER_MEMORY_LIMIT} MEMORY=${SF_USER_MEMORY_LIMIT}
NOFILE=${SF_ULIMIT_NOFILE} NOFILE=${SF_ULIMIT_NOFILE}
TX=${SF_MAXOUT} TX=${tx:-unlimited}
RX=${SF_MAXIN:-unlimited} RX=${SF_MAXIN:-unlimited}
SYN_BURST=${SF_USER_SYN_BURST} SYN_BURST=${SF_USER_SYN_BURST}
SYN_RATE=${SF_USER_SYN_LIMIT}/sec SYN_RATE=${SF_USER_SYN_LIMIT}/sec
@ -745,6 +772,18 @@ SERVERS=${SF_LIMIT_SERVER_BY_IP}
GREETINGS='${SF_SYSCOP_MSG}'" "/config/self-for-guest/lg-${LID}/limits" GREETINGS='${SF_SYSCOP_MSG}'" "/config/self-for-guest/lg-${LID}/limits"
} }
# Write limits to file that can be loaded by other processes (like rpc and encfsd)
write_lg_limits() {
tofile "\
SF_USER_ROOT_FS_SIZE=\"$SF_USER_ROOT_FS_SIZE\"
SF_USER_ROOT_FS_INODE=\"$SF_USER_ROOT_FS_INODE\"
SF_USER_FS_SIZE=\"$SF_USER_FS_SIZE\"
SF_USER_FS_INODE=\"$SF_USER_FS_INODE\"
SF_USER_UL_RATE=\"$SF_USER_UL_RATE\"
SF_RPORT=\"$SF_RPORT\"
SF_USER_IMMUNE=\"$SF_USER_IMMUNE\"" "${LG_RUN_DIR}/limits.txt"
}
check_banned() check_banned()
{ {
local blfn local blfn
@ -975,6 +1014,9 @@ check_limit_server_by_ip()
mk_geoip() mk_geoip()
{ {
local ip local ip
local country
local country_iso
local continent_code
ip="${1}" ip="${1}"
[[ ! -f /sf/share/GeoLite2-City.mmdb ]] && return [[ ! -f /sf/share/GeoLite2-City.mmdb ]] && return
[[ -z ${ip} ]] && return [[ -z ${ip} ]] && return
@ -984,6 +1026,16 @@ mk_geoip()
res=$(mmdbinspect --db /sf/share/GeoLite2-City.mmdb "${ip}") res=$(mmdbinspect --db /sf/share/GeoLite2-City.mmdb "${ip}")
[[ -z $SF_HIDEIP ]] && city=$(echo "$res" | jq -r '.[0].Records[0].Record.city.names.en | select(. != null)') [[ -z $SF_HIDEIP ]] && city=$(echo "$res" | jq -r '.[0].Records[0].Record.city.names.en | select(. != null)')
country=$(echo "$res" | jq -r '.[0].Records[0].Record.country.names.en | select(. != null)') country=$(echo "$res" | jq -r '.[0].Records[0].Record.country.names.en | select(. != null)')
country_iso=$(echo "$res" | jq -r '.[0].Records[0].Record.country.iso_code | select(. != null)')
continent_code=$(echo "$res" | jq -r '.[0].Records[0].Record.country.iso_code | select(. != null)')
country_iso="${country_iso,,}"
country_iso="${country_iso//[^a-z]}"
YOUR_COUNTRY_ISO="${country_iso:0:2}"
continent_code="${continent_code,,}"
continent_code="${continent_code//[^a-z]}"
YOUR_CONTINENT_CODE="${continent_code:0:6}"
unset YOUR_GEOIP unset YOUR_GEOIP
if [[ -n $city ]] && [[ -n $country ]]; then if [[ -n $city ]] && [[ -n $country ]]; then
@ -1091,9 +1143,6 @@ export LID
[[ -z $SF_SEED ]] && ERREXIT 244 "SF_SEED= is not set." [[ -z $SF_SEED ]] && ERREXIT 244 "SF_SEED= is not set."
# Show system messages
sysmsg "/config/host/etc/loginmsg-all.sh"
# Call init_vars() after LID is set # Call init_vars() after LID is set
init_vars init_vars
# Load CPU/PID/OOM limits (systemwide or user specific) # Load CPU/PID/OOM limits (systemwide or user specific)
@ -1102,6 +1151,10 @@ load_limits
check_banned check_banned
mk_hostname mk_hostname
# Show system messages
sysmsg "/config/host/etc/loginmsg-all.sh"
HNLID_FILE="${HNLID_DIR}/hn2lid-${SF_HOSTNAME}" HNLID_FILE="${HNLID_DIR}/hn2lid-${SF_HOSTNAME}"
LG_SEM="sema:lg-$(( (SF_NUM + SF_RAND_OFS) % SF_HM_SIZE_LG ))" LG_SEM="sema:lg-$(( (SF_NUM + SF_RAND_OFS) % SF_HM_SIZE_LG ))"
@ -1153,6 +1206,8 @@ else
tofile "$SF_HOSTNAME" "${SF_USER_DB_DIR}/hostname" tofile "$SF_HOSTNAME" "${SF_USER_DB_DIR}/hostname"
[[ -d "${HNLID_DIR}" ]] || exec_devnull mkdir "${HNLID_DIR}" [[ -d "${HNLID_DIR}" ]] || exec_devnull mkdir "${HNLID_DIR}"
tofile "$LID" "${HNLID_FILE}" || ERREXIT 231 "tofile: Failed to create hnlid_file" tofile "$LID" "${HNLID_FILE}" || ERREXIT 231 "tofile: Failed to create hnlid_file"
# Add a log entry into elastisearch using logpipe
logpipe "Type:Create|LID:${LID}|Hostname:${SF_HOSTNAME}|C_ISO:${YOUR_COUNTRY_ISO}|CONTINENT=${YOUR_CONTINENT_CODE}|"
fi fi
DEBUGF "LID=${LID} SF_HOSTNAME=${SF_HOSTNAME}" DEBUGF "LID=${LID} SF_HOSTNAME=${SF_HOSTNAME}"
@ -1295,7 +1350,7 @@ CID=${arr[0]}
LG_PID=${arr[1]} LG_PID=${arr[1]}
C_IP=${arr[2]} C_IP=${arr[2]}
[[ -z $C_IP ]] && ERREXIT 249 "Could not get container's IP address." [[ -z $C_IP ]] && ERREXIT 249 "Could not get container's IP address."
tofile "${LG_PID:?}" "/sf/run/pids/lg-${LID}.pid" tofile "${LG_PID:?}" "${LG_PID_DIR}/lg-${LID}.pid"
# Set up Root FS / inode limits and move encfsd to lg's cgroup # Set up Root FS / inode limits and move encfsd to lg's cgroup
setup_encfsd || STOPEXIT "${LID}" 244 "Could not set FS quota." setup_encfsd || STOPEXIT "${LID}" 244 "Could not set FS quota."
@ -1308,7 +1363,7 @@ res=$(red SET "ip:${C_IP}" "${LID} ${CID} ${LG_PID}") || STOPEXIT "$LID" 252 "Fa
exec_devnull docker exec sf-router /user-limit.sh "${YOUR_IP_HASH}" "${YOUR_IP}" "${C_IP}" "$SF_USER_SYN_LIMIT" "$SF_USER_SYN_BURST" "$SF_USER_DL_RATE" "$SF_USER_DL_BURST" "$SF_USER_UL_RATE" "$SF_USER_UL_BURST" || STOPEXIT "${LID}" 251 "Faild to set syn-limit..."; exec_devnull docker exec sf-router /user-limit.sh "${YOUR_IP_HASH}" "${YOUR_IP}" "${C_IP}" "$SF_USER_SYN_LIMIT" "$SF_USER_SYN_BURST" "$SF_USER_DL_RATE" "$SF_USER_DL_BURST" "$SF_USER_UL_RATE" "$SF_USER_UL_BURST" || STOPEXIT "${LID}" 251 "Faild to set syn-limit...";
# Ready container # Ready container
exec_devnull docker exec sf-master /ready-lg.sh "${LID}" "${C_IP}" "${LG_PID}" || STOPEXIT "${LID}" 246 "Failed-#3 to ready guest container..." exec_devnull docker exec sf-master /ready-lg.sh "${LID}" "${C_IP}" "${LG_PID}" "${SF_USER_DL_RATE}" "${SF_USER_UL_RATE}" || STOPEXIT "${LID}" 246 "Failed-#3 to ready guest container..."
# Setup container (within container's namespace) # Setup container (within container's namespace)
unset WGNAME_UP unset WGNAME_UP
@ -1319,9 +1374,6 @@ tofile "${C_IP:?}" "/config/self-for-guest/lg-${LID}/c_ip"
echo_pty -e "....[${CG}OK${CN}]" echo_pty -e "....[${CG}OK${CN}]"
# Add a log entry into elastisearch using logpipe
echo "Type:Login|LID:${LID}|Hostname:${SF_HOSTNAME}|" | unix-socket-client &> /dev/null
# Spawn shell # Spawn shell
spawn_shell_exit "$@" spawn_shell_exit "$@"
# NOT REACHED # NOT REACHED

@ -63,6 +63,7 @@ GetFormVars()
[[ ${key} == "privatekey" ]] && key="private" [[ ${key} == "privatekey" ]] && key="private"
[[ ${key} == "private" ]] && R_WG_PRIVATE="${val//[^[:alnum:]+\/]}=" [[ ${key} == "private" ]] && R_WG_PRIVATE="${val//[^[:alnum:]+\/]}="
[[ ${key} == "name" ]] && { val="${val//[^[:alnum:]]}"; R_WT_NAME="${val:0:13}"; } [[ ${key} == "name" ]] && { val="${val//[^[:alnum:]]}"; R_WT_NAME="${val:0:13}"; }
[[ ${key} == "token" ]] && { val="${val//[^a-zA-Z0-9@]}"; val="${val##*@}"; TOKEN_NAME="${val:0:64}"; }
### wgOUT ### wgOUT
[[ ${key} == "psk" ]] && R_OUT_PSK="${val//[^[:alnum:]+\/]}=" [[ ${key} == "psk" ]] && R_OUT_PSK="${val//[^[:alnum:]+\/]}="
[[ ${key} == "public" ]] && key="peer" # Alias [[ ${key} == "public" ]] && key="peer" # Alias
@ -612,15 +613,22 @@ CheckGoodKey()
BAIL "${R}ERROR${N}: Bad Key for ${opt}=" BAIL "${R}ERROR${N}: Bad Key for ${opt}="
} }
wg_net_init() # Load LG specific configuration (by source IP)
{ load_lg() {
local arr local arr;
local IFS
# Retrieve (LID CID PID) # Retrieve (LID CID PID)
arr=($(redr GET "ip:${REMOTE_ADDR}")) || BAIL "Bad Value" "Bad Value: " "ret=$?, ${#arr[@]}" arr=($(redr GET "ip:${REMOTE_ADDR}")) || BAIL "Bad Value" "Bad Value: " "ret=$?, ${#arr[@]}"
[[ ${#arr[@]} -ne 3 ]] && BAIL "Value != 3" "Value != 3: " "${#arr[@]}" [[ ${#arr[@]} -ne 3 ]] && BAIL "Value != 3" "Value != 3: " "${#arr[@]}"
LID="${arr[0]}" LID="${arr[0]}"
# CID="${arr[1]}"
PID="${arr[2]}"
}
wg_net_init()
{
local IFS
load_lg
LID_WGDIR="/config/db/user/lg-${LID}/wg" LID_WGDIR="/config/db/user/lg-${LID}/wg"
[[ ! -d "${LID_WGDIR}" ]] && mkdir "${LID_WGDIR}" [[ ! -d "${LID_WGDIR}" ]] && mkdir "${LID_WGDIR}"
LID_PROMPT_FN="/dev/shm/sf/self-for-guest/lg-${LID}/prompt" LID_PROMPT_FN="/dev/shm/sf/self-for-guest/lg-${LID}/prompt"
@ -631,14 +639,8 @@ wg_net_init()
USER_DB_WGNAME_UP_FN="/config/db/user/lg-${LID}/wg/name_up" USER_DB_WGNAME_UP_FN="/config/db/user/lg-${LID}/wg/name_up"
# USER_DB_WGCLIENT_FN="/config/db/user/lg-${LID}/wg/client" # USER_DB_WGCLIENT_FN="/config/db/user/lg-${LID}/wg/client"
# CID="${arr[1]}"
PID="${arr[2]}"
# Split into arguments # Split into arguments
IFS=/ read -r -a ARGS <<< "${REQUEST_URI:1}" # Ignore first '/'. Split into arguements. IFS=/ read -r -a ARGS <<< "${REQUEST_URI:1}" # Ignore first '/'. Split into arguements.
# Load CLIENT config
# source "${USER_DB_WGCLIENT_FN}" 2>/dev/null
} }
ERR_wg_help_exit() ERR_wg_help_exit()
@ -649,13 +651,50 @@ ERR_wg_help_exit()
exit exit
} }
cmd_port() {
local ipport
load_lg
source "/dev/shm/sf/run/users/lg-${LID}/limits.txt"
[[ -z $SF_RPORT ]] && BAIL "💥 ${CR}ERROR${CN}: ${CDM}Please contact a SysCop to enable this feature for you.${CN}"
red RPUSH portd:cmd "remport ${lid}" >/dev/null
sleep 1 # Stop DoS attack: flood-requesting reverse ports
ipport=$(echo -e "DEL portd:response-${LID}\"\n\
RPUSH portd:blcmd \"getport ${LID}\"\n\
BLPOP portd:response-${LID} 5" | redr) || return
# DEBUGF "ipport='$ipport'"
ipport="${ipport##*$'\n'}"
[[ ! "${ipport##*:}" -gt 0 ]] && { DEBUGF "Failed to get Reverse Port Forward (ipport='$ipport')"; return; }
# The PortD add's a /sf/run/self/reverse_forward.
echo -en "\
${CDM}Tip${CN}: ${CDC}${CF}Type ${CDC}cat /config/self/reverse_*${CN}.
${CDG}👾 New reverse Port is ${CDY}${ipport}${CN}"
# portd.sh automaticaly adds this to /config/self/reverse_*
exit
}
cmd_token() {
local token_fn="/config/db/token/token-${TOKEN_NAME,,}.conf"
load_lg
source "/dev/shm/sf/run/users/lg-${LID}/limits.txt"
[[ -n $SF_TOKEN_PROHIBITED ]] && BAIL "💥 ${CR}ERROR${CN}: ${CDM}Please contact a SysCop to enable this feature for you.${CN}"
[[ ! -f "${token_fn}" ]] && { sleep 1; BAIL "💥 ${CR}ERROR${CN}: ${CDM}Token '${TOKEN_NAME}' does not exist.${CN}"; }
echo "${TOKEN_NAME}" >"/config/db/user/lg-${LID}/token"
exit
}
# CLIENT # CLIENT
cmd_wg_up() cmd_wg_up()
{ {
local epip local epip
local args local args
local err local err
local epport
[[ ${R_OUT_ENDPOINT} != *:* ]] && R_OUT_ENDPOINT+=":51820" [[ ${R_OUT_ENDPOINT} != *:* ]] && R_OUT_ENDPOINT+=":51820"
epip="${R_OUT_ENDPOINT%%:*}" epip="${R_OUT_ENDPOINT%%:*}"
@ -684,7 +723,7 @@ cmd_wg_up()
echo "$R_WG_PRIVATE" >"/dev/shm/private.$$" echo "$R_WG_PRIVATE" >"/dev/shm/private.$$"
err=$(nsenter.u1000 --setuid 0 --setgid 0 -t "${PID}" -n wg set "$WG_DEV" private-key "/dev/shm/private.$$" peer "$R_OUT_PEER" "${args[@]}" endpoint "${R_OUT_ENDPOINT}" persistent-keepalive 25 allowed-ips 0.0.0.0/0,::/0 2>&1) || BAIL "${R}ERROR${N}: Failed: wg set (${err:0:128})" err=$(nsenter.u1000 --setuid 0 --setgid 0 -t "${PID}" -n wg set "$WG_DEV" private-key "/dev/shm/private.$$" peer "$R_OUT_PEER" "${args[@]}" endpoint "${R_OUT_ENDPOINT}" persistent-keepalive 25 allowed-ips 0.0.0.0/0,::/0 2>&1) || BAIL "${R}ERROR${N}: Failed: wg set (${err:0:128})"
rm -f "/dev/shm/private.$$" "/dev/shm/psk.$$" rm -f "/dev/shm/private.$$" "/dev/shm/psk.$$"
nsenter.u1000 --setuid 0 --setgid 0 -t "${PID}" -n ip link set mtu $((1500 - 80 - 80)) up dev "${WG_DEV}" nsenter.u1000 --setuid 0 --setgid 0 -t "${PID}" -n ip link set mtu $((SF_HOST_MTU - 80 - 80)) up dev "${WG_DEV}"
# Route to WG endpoint: # Route to WG endpoint:
nsenter.u1000 --setuid 0 --setgid 0 -t "${PID}" -n ip route add "${epip}" via "${SF_NET_LG_ROUTER_IP}" 2>/dev/null nsenter.u1000 --setuid 0 --setgid 0 -t "${PID}" -n ip route add "${epip}" via "${SF_NET_LG_ROUTER_IP}" 2>/dev/null
@ -767,6 +806,12 @@ GetFormVars
exit exit
} }
[[ "${FCGI_CMD}" == "port" ]] && cmd_port
[[ "${FCGI_CMD}" == "set" ]] && {
[[ -n $TOKEN_NAME ]] && cmd_token
BAIL "💥 ${CR}ERROR${CN}: ${CDM}Setting not found.${CN}"
}
[[ -n $SF_DEBUG ]] && [[ "${FCGI_CMD}" == "env" ]] && { env; exit; } [[ -n $SF_DEBUG ]] && [[ "${FCGI_CMD}" == "env" ]] && { env; exit; }
wg_net_init wg_net_init
@ -883,7 +928,7 @@ wg_net_init
# Configure interface after moving # Configure interface after moving
nsenter.u1000 --setuid 0 --setgid 0 -t "${PID}" -n ip -4 address add "${WG_IP}" dev "${WG_DEV}" nsenter.u1000 --setuid 0 --setgid 0 -t "${PID}" -n ip -4 address add "${WG_IP}" dev "${WG_DEV}"
err=$(nsenter.u1000 --setuid 0 --setgid 0 -t "${PID}" -n ip -6 address add "${WG_IP6}" dev "${WG_DEV}" 2>&1) || echo >&2 "${CR}ERROR${CN}: ip -6: $err" err=$(nsenter.u1000 --setuid 0 --setgid 0 -t "${PID}" -n ip -6 address add "${WG_IP6}" dev "${WG_DEV}" 2>&1) || echo >&2 "${CR}ERROR${CN}: ip -6: $err"
nsenter.u1000 --setuid 0 --setgid 0 -t "${PID}" -n ip link set mtu 1420 up dev "${WG_DEV}" nsenter.u1000 --setuid 0 --setgid 0 -t "${PID}" -n ip link set mtu $((SF_HOST_MTU - 80)) up dev "${WG_DEV}"
set_route set_route

@ -14,6 +14,8 @@ source /dev/shm/config-lg.txt || exit 255
LID="$1" LID="$1"
C_IP="$2" C_IP="$2"
LG_PID="$3" LG_PID="$3"
USER_DL_RATE="$4"
USER_UL_RATE="$5"
LID_PROMPT_FN="/dev/shm/sf/self-for-guest/lg-${LID}/prompt" LID_PROMPT_FN="/dev/shm/sf/self-for-guest/lg-${LID}/prompt"
# Create 'empty' for ZSH's prompt to show WG EXIT # Create 'empty' for ZSH's prompt to show WG EXIT
@ -30,7 +32,12 @@ nsenter.u1000 -t "${LG_PID:?}" --setuid 0 --setgid 0 -n arp -s "${SF_RPC_IP}"
# 255.0.0.1 always points to guest's localhost: user can now set up a ssh -D1080 and connect with browser to # 255.0.0.1 always points to guest's localhost: user can now set up a ssh -D1080 and connect with browser to
# 255.0.0.1 and reach guest's 127.0.0.1. # 255.0.0.1 and reach guest's 127.0.0.1.
# iptables is u+s and does not need --setuid
nsenter.u1000 -t "${LG_PID}" -n iptables -t nat -A OUTPUT -p tcp --dst 255.0.0.1 -j DNAT --to-destination 127.0.0.1 nsenter.u1000 -t "${LG_PID}" -n iptables -t nat -A OUTPUT -p tcp --dst 255.0.0.1 -j DNAT --to-destination 127.0.0.1
# Set egress limits per LG
[[ -n $USER_UL_RATE ]] && nsenter.u1000 -t "${LG_PID:?}" --setuid 0 --setgid 0 -n tc qdisc add dev eth0 root cake bandwidth "${USER_UL_RATE}" dsthost
set +e set +e
exit 0 exit 0

@ -29,6 +29,7 @@ SF_BASEDIR=${HOME}/segfault
## Example: Germany:::<BLAHQCY26Tnz7KzDo9JPvBrzEzV+Z7RG1Hx/rXGgmH4=:::none:::10.65.13.37 ## Example: Germany:::<BLAHQCY26Tnz7KzDo9JPvBrzEzV+Z7RG1Hx/rXGgmH4=:::none:::10.65.13.37
#SF_MULLVAD_CONFIG= #SF_MULLVAD_CONFIG=
#SF_HOST_MTU=1500
SF_TOR_IP=172.20.0.111 SF_TOR_IP=172.20.0.111
SF_NORDVPN_IP=172.20.0.254 SF_NORDVPN_IP=172.20.0.254
SF_CRYPTOSTORM_IP=172.20.0.253 SF_CRYPTOSTORM_IP=172.20.0.253

@ -246,9 +246,10 @@ ipt_set()
# #
# The only way around this is to advertise a smaller MSS for TCP and hope for the best # The only way around this is to advertise a smaller MSS for TCP and hope for the best
# for all other protocols. Ultimately we need bad routers on the Internet to disappear. # for all other protocols. Ultimately we need bad routers on the Internet to disappear.
iptables -A FORWARD -i "${DEV_LG}" -o "${DEV_GW}" -p tcp --tcp-flags SYN,RST SYN -j TCPMSS --set-mss 1380 # 1500 - 80 - 40
iptables -A FORWARD -i "${DEV_LG}" -o "${DEV_GW}" -p tcp --tcp-flags SYN,RST SYN -j TCPMSS --set-mss $((SF_GUEST_MTU - 40))
# Mode when TOR goes via VPN (rarely used) # Mode when TOR goes via VPN (rarely used)
iptables -A FORWARD -i "${DEV_GW}" -o "${DEV_GW}" -s "${TOR_IP}" -p tcp --tcp-flags SYN,RST SYN -j TCPMSS --set-mss 1380 iptables -A FORWARD -i "${DEV_GW}" -o "${DEV_GW}" -s "${TOR_IP}" -p tcp --tcp-flags SYN,RST SYN -j TCPMSS --set-mss $((SF_GUEST_MTU - 40))
# -----BEGIN DIRECT SSH----- # -----BEGIN DIRECT SSH-----
# Note: The IP addresses are FLIPPED because we use DNAT/SNAT/MASQ in PREROUTING # Note: The IP addresses are FLIPPED because we use DNAT/SNAT/MASQ in PREROUTING

@ -154,6 +154,8 @@ warn_outdated()
load_env load_env
[[ -z $SF_DATADIR ]] && SF_DATADIR="${SF_BASEDIR}/data" [[ -z $SF_DATADIR ]] && SF_DATADIR="${SF_BASEDIR}/data"
[[ -z $SF_SHMDIR ]] && SF_SHMDIR="/dev/shm/sf" [[ -z $SF_SHMDIR ]] && SF_SHMDIR="/dev/shm/sf"
[[ -z $SF_HOST_MTU ]] && SF_HOST_MTU=1500
export SF_GUEST_MTU=$((SF_HOST_MTU - 80))
[[ ! -d "${SF_DATADIR}/user" ]] && mkdir -p "${SF_DATADIR}/user" [[ ! -d "${SF_DATADIR}/user" ]] && mkdir -p "${SF_DATADIR}/user"
[[ ! -d "${SF_DATADIR}/share" ]] && mkdir -p "${SF_DATADIR}/share" [[ ! -d "${SF_DATADIR}/share" ]] && mkdir -p "${SF_DATADIR}/share"