我已经将 VSFTPD 与 pam_mysql 集成,这样我就可以 使用 mysql 数据库中保存的帐户成功登录到 FTP 服务器。
如果用户首次登录服务器,我需要自动为其创建一个目录。我看到有人建议使用 pam_script 或 pam_exec 来实现这一点。
作为测试,我修改了我的/etc/pam.d/vsftpd
配置以包含以下行:
account optional pam_exec.so debug log=/tmp/pam_exec.log /etc/pam-script/test.sh
该脚本只是回应用户:
#!/bin/sh
echo $PAM_USER
我/var/log/auth.log
可以看到该脚本正在被调用:
Jan 16 17:15:44 ip-172-31-8-61 vsftpd: pam_exec(vsftpd:auth): Calling /etc/pam-script/dir.sh ...
但是 FTP 登录没有完成。连接挂起。所有后续连接都失败,我必须重新启动服务才能使其响应。
我已经通过调整 SSHD 登录的 PAM 配置排除了配置/脚本的问题,这似乎运行良好。
我也使用 pam_script 模块对此进行了测试,并在pam_script_auth
调用脚本时得到了类似的结果。
问题似乎是如果 PAM 配置中有其他步骤,VSFTP 就无法完成登录。我尝试了不同的设置(身份验证、帐户)和不同的要求级别(可选、必需),但均未成功。
有人有主意吗?
更新:Ubuntu 12.04。使用经过调整的版本VSFTP 如下所述
答案1
我确认这是 Debian / Ubuntu 和 vsftpd 原生版本的一个错误。任何调用子进程的 PAM 模块都会阻止或挂起 vsftpd(例如 pam_exec、pam_script、涉及系统或 popen 调用的自定义 pam 模块)。
我通过在我的 Debian 上构建 centos 源解决了这个问题:
apt-get install vsftpd
cd /usr/local/src
git clone https://git.centos.org/git/centos-git-common.git
cp ./centos-git-common/*.sh /usr/local/sbin
git clone https://git.centos.org/git/rpms/vsftpd
cd /usr/local/src/vsftpd
git checkout c7
get_sources.sh
cd SOURCES
tar xvzf vsftpd-3.0.2.tar.gz
mv vsftpd-3.0.2/* .
git apply *-3.0.2-*.patch
sed -i -e 's/vsf_findlibs.sh`/vsf_findlibs.sh` -lcap/g' Makefile
sed -i -e 's/undef VSF_BUILD_SSL/define VSF_BUILD_SSL/g' builddefs.h
make
cp vsftpd /usr/sbin
vsftpd 将不再挂起,您将能够从 PAM 模块调用 system() 函数。但由于某种原因,fork 和 exec 仍然无法正常工作。
答案2
我知道这个问题是前一段时间问的,但我在 Debian 上遇到了类似的问题,即在将 pam_exec 添加到链中时挂起 vsftpd 进程。对我来说,问题是添加
session_support=YES
到 vsftpd 配置文件,但也要放
@include common-session
/etc/pam.d/vsftpd
我已注释掉一些有关 vsftpd 虚拟用户的指南。因此,完整的 pam 文件对我来说如下所示:
auth required pam_listfile.so item=user sense=deny file=/etc/ftpusers onerr=succeed
auth required pam_pwdfile.so pwdfile=/etc/ftppasswd
account required pam_permit.so
session optional pam_exec.so type=close_session log=/var/log/session.log /etc/pam_session.sh
@include common-session
(我的用例是在特定 ftp 用户注销后处理上传的文件)
答案3
检查您的 suexec 日志。也许您的目录结构位于 vsftpd 的非标准位置。另外,我认为您的 pam 配置文件中需要更多内容。
以下是我的 pam 配置:
cat /etc/pam.d/vsftpd
#%PAM-1.0
# Auth in MySQL
auth requisite pam_mysql.so user=readonly passwd=readonly host=somehost db=somedb table=accounts usercolumn=username passwdcolumn=pass crypt=3
auth required pam_script.so onerr=success dir=/etc/pam-script
# Account in MySQL
account required pam_mysql.so user=readonly passwd=readonly host=somehost db=somedb table=accounts usercolumn=username passwdcolumn=pass crypt=3
$ cat /etc/pam-script/pam_script_auth
#!/bin/sh
# Purpose: create the users's homedir and default message
#
# The evnironment variable $PAM_USER is passed on from PAM
# layer to this script via pam_script.so
if [ ! -d "/opt/ftp/$PAM_USER" ]; then
/bin/su - ftp -s /bin/sh -c "/usr/bin/env mkdir /opt/ftp/$PAM_USER"
/bin/su - ftp -s /bin/sh -c "/usr/bin/env chmod 751 /opt/ftp/$PAM_USER"
/bin/su - ftp -s /bin/sh -c "/usr/bin/env cat /etc/vsftpd /vsftpd.banner.homedir.txt > /opt/ftp/$PAM_USER/.message"
/bin/su - ftp -s /bin/sh -c "/usr/bin/env cat /etc/vsftpd/vsftpd.banner.homedir.txt > /opt/ftp/$PAM_USER/README.first"
fi
$ cat /etc/vsftpd/vsftpd.int.21.conf
listen=YES
anonymous_enable=NO
local_enable=YES
write_enable=YES
local_umask=022
dirmessage_enable=YES
message_file=.message
xferlog_enable=YES
connect_from_port_20=YES
nopriv_user=ftp
chroot_local_user=YES
secure_chroot_dir=/var/run/vsftpd
pam_service_name=vsftpd
rsa_cert_file=/etc/vsftpd/ssl/
guest_enable=YES
guest_username=ftp
local_root=/opt/ftp/$USER
user_sub_token=$USER
virtual_use_local_privs=YES
user_config_dir=/etc/vsftpd_user_conf
banner_file=/etc/vsftpd/vsftpd.banner.server.txt
pasv_min_port=20005
pasv_max_port=30005
pasv_address=10.10.10.10
## FTPS (21) Config Changes
listen_port=21
ftp_data_port=20
listen_address=10.10.10.123
我已经有一段时间没有看过这个了,所以希望它能有所帮助。