Vsftpd Set Download Only Anonymous Internet Server

by on January 21, 2009 · 3 comments· LAST UPDATED June 19, 2009

in , ,

This example shows how you might set up a large internet facing FTP site for distributing file or software updates. The emphasis will be on security and performance. VSFTPD will make sure only world-readable files and directories are served to the world via anonymous / ftp account. You force to originates FTP port connections from a secure port - so users on the FTP server cannot try and fake file content. You will hide the FTP server user IDs and just display ftp in directory listings. This is also a performance boost. Set a 40000-60000 port range for passive connections. This will help firewall setup.

Defaults

  • The default port - 21 and 20
  • The default directory to upload your files - /var/ftp/pub for anonymous access. By default all users are chrooted to /var/ftp and they are not allowed to change the directory.
  • Anonymous login details - Use anonymous / anonymous or ftp / ftp as username / password combo.

FTP Server Configuration

Edit the vsftpd configuration file, enter:
# vi /etc/vsftpd/vsftpd.conf
Add or correct the following configuration option:
Only allow anonymous access ftp access:

anonymous_enable=YES

Disable local users login to ftp server:

local_enable=NO

Disable upload files and writing permission on the FTP server:

write_enable=NO
anon_upload_enable=NO
anon_mkdir_write_enable=NO
anon_other_write_enable=NO

Only allow file reading permission to the rest of the world:

anon_world_readable_only=YES
connect_from_port_20=YES
hide_ids=YES
pasv_min_port=40000
pasv_max_port=60000

Turn on log features

xferlog_enable=YES
# Do not allow the use of "ls -R" to avoid consume a lot of resources
ls_recurse_enable=NO
ascii_download_enable=NO
async_abor_enable=YES

Set performance option:

# Uses one process per connection to gain performance.
# This is used to supports huge numbers of simultaneously connected users.
one_process_model=YES
# The timeout, in seconds, which is the maximum time a remote client may spend
# between FTP commands.  If the timeout triggers, the remote client is kicked off.
idle_session_timeout=120
# The timeout, in seconds, which is roughly the maximum time we permit data
# transfers to stall for with no progress.  If the timeout triggers, the remote client
# is kicked off.
data_connection_timeout=300
# The timeout, in seconds, for a remote client to establish connection with
# a PASV style data connection.
accept_timeout=60
# The timeout, in seconds, for a remote client to respond to our PORT
# style data connection.
connect_timeout=60
# The maximum data transfer rate permitted, in bytes per second,
# for anonymous clients.
anon_max_rate=50000

Restart the ftp server:
# service vsftpd restart

Sample Iptables Rules to Open Passive FTP Port Ranges

Add the following rules to your firewall shell script:

$IPT -I INPUT -m state --state NEW -j ACCEPT -p tcp -m multiport --ports 40000:60000

If you are using /etc/sysconfig/iptables, add the following lines, ensuring that they appear before the final LOG and DROP lines for the RH-Firewall-1-INPUT:

-A RH-Firewall-1-INPUT -m state --state NEW -j ACCEPT -p tcp -m multiport --ports 40000:60000

Save and close the file. Restart the firewall and vsftpd:
# service vsftpd restart
# service iptables restart

FTP Server Protected by an External *BSD PF Firewall Running NAT

In this case, the firewall must redirect traffic to the VSVTPD FTP server (running on RHEL) in addition to not blocking the required ports. In order to accomplish this, you need to use ftp-proxy.

ftp-proxy can be run in a mode that causes it to forward all FTP connections to a specific FTP server. Basically we'll setup the proxy to listen on port 21 of the firewall and forward all connections to the back-end server.

Edit /etc/rc.conf.local (FreeBSD use should use /etc/rc.conf) and add the following:

ftpproxy_flags="-R 10.1.3.100 -p 21 -b 192.168.1.1"

Where,

  • 10.1.3.100 - the IP address of the actual RHEL VSFTPD FTP server.
  • 21 - the port we want ftp-proxy to listen on
  • 192.168.1.1 - the address on the firewall that we want the proxy to bind to.

Next, pdate your /etc/pf.conf as follows:

ext_ip = "192.168.1.1"
ftp_server_ip = "10.1.3.100"
 
nat-anchor "ftp-proxy/*"
nat on $ext_if inet from $int_if -> ($ext_if)
rdr-anchor "ftp-proxy/*"
 
pass in on $ext_if inet proto tcp to $ext_ip port 21 flags S/SA keep state
pass out on $int_if inet proto tcp to $ftp_ip port 21 user proxy flags S/SA keep state anchor "ftp-proxy/*"

Restart pf firewall:
# pfctl -nf /etc/pf.conf && pfctl -f /etc/pf.conf

TwitterFacebookGoogle+PDF versionFound an error/typo on this page? Help us!

{ 3 comments… read them below or add one }

1 raju July 25, 2012 at 9:14 am

Instead of /var/ftp/pub, I want the user to traverse to another directory.

1. I tried changing ftp user home directory in /etc/passwd
2. Created usergroup ftpusers & gave permissions(chown,chmod) for the directory to be accessible by that group.
Still it doesn’t work..

Is it possible to make it work??

Reply

2 talha jilal February 13, 2014 at 3:57 am

You need change your selinux settings

Reply

3 Stome February 25, 2014 at 3:23 am

Dear Talha jilal,
I have same problem as rajo too. I am a new linux system so what i change in selinux please?
thanks
Stome, Cambodia

Reply

Leave a Comment

Tagged as: , , , , , , , , , , , , , , , , , , , , , , ,

Previous post:

Next post: