vsftpd: update init script to process UCI
authorMohd Husaam Mehdi <husaam.mehdi@iopsys.eu>
Fri, 29 Mar 2024 17:40:07 +0000 (23:10 +0530)
committerFlorian Eckert <Eckert.Florian@googlemail.com>
Wed, 8 Jan 2025 13:40:44 +0000 (14:40 +0100)
* update init script to validate and process UCI
* the option conf_file can be used to pass a conf file
  instead of using UCI

Signed-off-by: Mohd Husaam Mehdi <husaam.mehdi@iopsys.eu>
net/vsftpd/Makefile
net/vsftpd/files/vsftpd.init
net/vsftpd/files/vsftpd.uci [new file with mode: 0644]

index 34f26e3e28627016a96ca559726b156640bf7696..b4ffe3bc01932cc381950c83bc78f794bd5c0eb2 100644 (file)
@@ -9,7 +9,7 @@ include $(TOPDIR)/rules.mk
 
 PKG_NAME:=vsftpd
 PKG_VERSION:=3.0.5
-PKG_RELEASE:=3
+PKG_RELEASE:=4
 
 PKG_SOURCE:=$(PKG_NAME)-$(PKG_VERSION).tar.gz
 PKG_SOURCE_URL:=https://security.appspot.com/downloads/
@@ -92,6 +92,8 @@ define Package/vsftpd/install
        $(INSTALL_CONF) ./files/$(PKG_NAME).conf $(1)/etc/$(PKG_NAME).conf
        $(INSTALL_DIR) $(1)/etc/init.d
        $(INSTALL_BIN) ./files/$(PKG_NAME).init $(1)/etc/init.d/$(PKG_NAME)
+       $(INSTALL_DIR) $(1)/etc/config
+       $(INSTALL_CONF) ./files/$(PKG_NAME).uci $(1)/etc/config/$(PKG_NAME)
        $(INSTALL_DIR) $(1)/etc/vsftpd
 endef
 
index a1673ee43f8e24b80b17b80a7ea5ce6259aa195f..610253d194576de5b60701c36bc894aa78bc741d 100644 (file)
@@ -5,9 +5,149 @@ START=50
 USE_PROCD=1
 BIN=vsftpd
 
+. /lib/functions.sh
+
+PORT=21
+OUTPUT_CONF="/var/etc/vsftpd.conf"
+readonly TEMP_OUTPUT_CONF="/var/etc/vsftpd.conf.tmp"
+
+write_conf() {
+       local key="$1"
+       local value="$2"
+
+       if [ -n "$key" ] && [ -n "$value" ]; then
+               echo "$key=$value" >> "$TEMP_OUTPUT_CONF"
+       fi
+}
+
+write_conf_bool() {
+       local key="$1"
+       local value="$2"
+
+       if  [ "$value" = "1" ]; then
+               write_conf "$key" "YES"
+       else
+               write_conf "$key" "NO"
+       fi
+}
+
+validate_vsftpd_section() {
+       uci_load_validate vsftpd global "$1" "$2" \
+               'listen:bool:1' \
+               'listen_ipv6:bool:0' \
+               'listen_port:port' \
+               'anonymous_enable:bool:0' \
+               'anon_root:directory' \
+               'local_enable:bool:1' \
+               'local_root:directory' \
+               'write_enable:bool:1' \
+               'local_umask:uinteger:022' \
+               'check_shell:bool:0' \
+               'dirmessage_enable:bool:1' \
+               'secure_chroot_dir:directory' \
+               'ftpd_banner:string' \
+               'session_support:bool:0' \
+               'syslog_enable:bool' \
+               'userlist_enable:bool' \
+               'userlist_deny:bool' \
+               'userlist_file:file' \
+               'xferlog_enable:bool' \
+               'xferlog_file:file' \
+               'xferlog_std_format:bool' \
+               'ssl_enable:bool' \
+               'allow_anon_ssl:bool' \
+               'force_local_data_ssl:bool' \
+               'force_local_logins_ssl:bool' \
+               'ssl_tlsv1:bool' \
+               'ssl_sslv2:bool' \
+               'ssl_sslv3:bool' \
+               'rsa_cert_file:file' \
+               'rsa_private_key_file:file'
+}
+
+setup_vsftpd() {
+       local section="$1"
+       local validation_result="$2"
+
+       if [ "$validation_result" != "0" ]; then
+               echo "Validation failed for section: $section"
+               return 1
+       fi
+
+       rm -rf "$TEMP_OUTPUT_CONF"  # Clear temporary file
+       touch "$TEMP_OUTPUT_CONF"
+
+       # always run in foreground
+       write_conf_bool "background" "0"
+
+       [ -n "$listen" ] && write_conf_bool "listen" "$listen"
+       [ -n "$listen_ipv6" ] && write_conf_bool "listen_ipv6" "$listen_ipv6"
+       [ -n "$anonymous_enable" ] && write_conf_bool "anonymous_enable" "$anonymous_enable"
+       [ -n "$local_enable" ] && write_conf_bool "local_enable" "$local_enable"
+       [ -n "$write_enable" ] && write_conf_bool "write_enable" "$write_enable"
+       [ -n "$check_shell" ] && write_conf_bool "check_shell" "$check_shell"
+       [ -n "$dirmessage_enable" ] && write_conf_bool "dirmessage_enable" "$dirmessage_enable"
+       [ -n "$session_support" ] && write_conf_bool "session_support" "$session_support"
+       [ -n "$syslog_enable" ] && write_conf_bool "syslog_enable" "$syslog_enable"
+       [ -n "$userlist_enable" ] && write_conf_bool "userlist_enable" "$userlist_enable"
+       [ -n "$userlist_deny" ] && write_conf_bool "userlist_deny" "$userlist_deny"
+       [ -n "$xferlog_enable" ] && write_conf_bool "xferlog_enable" "$xferlog_enable"
+       [ -n "$xferlog_std_format" ] && write_conf_bool "xferlog_std_format" "$xferlog_std_format"
+       [ -n "$ssl_enable" ] && write_conf_bool "ssl_enable" "$ssl_enable"
+       [ -n "$allow_anon_ssl" ] && write_conf_bool "allow_anon_ssl" "$allow_anon_ssl"
+       [ -n "$force_local_data_ssl" ] && write_conf_bool "force_local_data_ssl" "$force_local_data_ssl"
+       [ -n "$force_local_logins_ssl" ] && write_conf_bool "force_local_logins_ssl" "$force_local_logins_ssl"
+       [ -n "$ssl_tlsv1" ] && write_conf_bool "ssl_tlsv1" "$ssl_tlsv1"
+       [ -n "$ssl_sslv2" ] && write_conf_bool "ssl_sslv2" "$ssl_sslv2"
+       [ -n "$ssl_sslv3" ] && write_conf_bool "ssl_sslv3" "$ssl_sslv3"
+
+       [ -n "$anon_root" ] && write_conf "anon_root" "$anon_root"
+       [ -n "$ftpd_banner" ] && write_conf "ftpd_banner" "$ftpd_banner"
+       [ -n "$listen_port" ] && { write_conf "listen_port" "$listen_port"; PORT="$listen_port"; }
+       [ -n "$local_umask" ] && write_conf "local_umask" "$local_umask"
+       [ -n "$local_root" ] && write_conf "local_root" "$local_root"
+       [ -n "$rsa_cert_file" ] && write_conf "rsa_cert_file" "$rsa_cert_file"
+       [ -n "$rsa_private_key_file" ] && write_conf "rsa_private_key_file" "$rsa_private_key_file"
+       [ -n "$secure_chroot_dir" ] && write_conf "secure_chroot_dir" "$secure_chroot_dir"
+       [ -n "$userlist_file" ] && write_conf "userlist_file" "$userlist_file"
+       [ -n "$xferlog_file" ] && write_conf "xferlog_file" "$xferlog_file"
+
+       # move temporary file to the main configuration file
+       mv "$TEMP_OUTPUT_CONF" "$OUTPUT_CONF"
+}
+
 start_service() {
-       procd_open_instance
-       procd_set_param command $BIN
+       local disabled mdns conf_file
+
+       # Load UCI configuration for vsftpd
+       config_load vsftpd
+
+       # if disabled, just return
+       config_get_bool disabled global disabled 0
+       if [ "${disabled}" -eq 1 ]; then
+               return
+       fi
+
+       config_get_bool conf_file global conf_file ""
+       if [ -n "$conf_file" ]; then 
+               # use user defined conf file instead of UCI
+               OUTPUT_CONF="$conf_file"
+       else
+               # Process the global configuration
+               config_foreach validate_vsftpd_section global setup_vsftpd
+       fi
+
+       procd_open_instance "vsftpd"
+
+       config_get_bool mdns global mdns 0
+       [ "${mdns}" -eq 1 ] && procd_add_mdns "ftp" "tcp" "$PORT" "daemon=$BIN"
+
+       procd_set_param command "$BIN" "$OUTPUT_CONF"
        procd_set_param respawn
        procd_close_instance
 }
+
+service_triggers() {
+       procd_add_reload_trigger "vsftpd"
+       procd_add_validation validate_vsftpd_section
+}
diff --git a/net/vsftpd/files/vsftpd.uci b/net/vsftpd/files/vsftpd.uci
new file mode 100644 (file)
index 0000000..1394742
--- /dev/null
@@ -0,0 +1,6 @@
+config global 'global'
+       option listen '1'
+       option write_enable '1'
+       option anonymous_enable '0'
+       option local_enable '1'
+       option mdns '0'