#!/bin/sh /etc/rc.common
# Copyright (C) 2020 Lienol <lawlienol@gmail.com>

START=99

CONFIG=socat
CONFIG_PATH=/var/etc/$CONFIG

add_rule() {
	accept_port=$(cat /var/etc/$CONFIG.port | tr "\n" " ")
	if [ "$accept_port" ]; then
		uci -q delete firewall.socat
		uci set firewall.socat=rule
		uci set firewall.socat.name="socat"
		uci set firewall.socat.target="ACCEPT"
		uci set firewall.socat.src="wan"
		uci set firewall.socat.dest_port="$accept_port"
		uci set firewall.socat.enabled="1"
		uci commit firewall
		/etc/init.d/firewall reload >/dev/null 2>&1
	else
		del_rule
	fi
}

del_rule() {
	uci -q delete firewall.socat
	uci commit firewall
	/etc/init.d/firewall reload >/dev/null 2>&1
}

run_service() {
	config_get enable $1 enable
	[ "$enable" = "0" ] && return 0
	config_get remarks $1 remarks
	config_get protocol $1 protocol
	config_get family $1 family
	config_get proto $1 proto
	config_get listen_port $1 listen_port
	config_get reuseaddr $1 reuseaddr
	config_get dest_proto $1 dest_proto
	config_get dest_ip $1 dest_ip
	config_get dest_port $1 dest_port
	config_get firewall_accept $1 firewall_accept
	ln -s /usr/bin/socat ${CONFIG_PATH}/$1
	
	if [ "$reuseaddr" == "1" ]; then
		reuseaddr=",reuseaddr"
	else
		reuseaddr=""
	fi
	
	if [ "$family" == "6" ]; then
		ipv6only_params=",ipv6-v6only"
	else
		ipv6only_params=""
	fi
	
	# 端口转发
	if [ "$protocol" == "port_forwards" ]; then
		listen=${proto}${family}
		[ "$family" == "" ] && listen=${proto}6
		${CONFIG_PATH}/$1 ${listen}-listen:${listen_port}${ipv6only_params}${reuseaddr},fork ${dest_proto}:${dest_ip}:${dest_port} >/dev/null 2>&1 &
	fi
	
	[ "$firewall_accept" == "1" ] && {
		echo $listen_port >> /var/etc/$CONFIG.port
	}
}

stop_service() {
	busybox ps -w | grep "$CONFIG_PATH/" | grep -v "grep" | awk '{print $1}' | xargs kill -9 >/dev/null 2>&1 &
	del_rule
	rm -rf $CONFIG_PATH /var/etc/$CONFIG.port
}

start() {
	[ -f "/etc/config/socat" ] && [ $(grep -c global /etc/config/socat) -eq 0 ] && {
		uci add socat global
		uci rename socat.@global[0]='global'
		uci set socat.global.enable="$(grep -q "enable '1'" /etc/config/socat && echo '1' || echo '0')"
		uci commit socat
	}
	enable=$(uci -q get $CONFIG.@global[0].enable)
	if [ "$enable" = "0" ];then
		stop_service
	else
		mkdir -p $CONFIG_PATH
		rm -f /var/etc/$CONFIG.port
		config_load $CONFIG
		config_foreach run_service "config"
		add_rule
	fi
}

stop() {
	stop_service
}

reload_service() {
	stop
	sleep 1
	start
}
