Thursday, October 10, 2013

Creating an FTP Server in C# - with IPv6 Support

Introduction 
First, I want to describe what this article is not. It is not an example of a full featured, scalable, and secure FTP server. It is an introduction into creating an application from a specification, an introduction to socket communication, asynchronous methods, stream encodings, and basic encryption. Please do not use this FTP server in any production environment. It is not secure, and I have done no scalability testing on it. With that out of the way, let's get started.

What is FTP?
According to the specification in IETF RFC 959, the File Transfer Protocol has the following objectives:
  • to promote sharing of files (computer programs and/or data)
  • to encourage indirect or implicit (via programs) use of remote computers
  • to shield a user from variations in file storage systems among hosts, and
  • to transfer data reliably and efficiently.
FTP is a way to transfer files from one computer to another. Typically, a client connects to a server on port 21, sends some login information, and gets access to the server's local filesystem.

Basic steps
We will start by creating a server that can listen for connections from a client. Once we can accept connections, we will learn to pass off those connections to another thread to handle the processing of commands.

How to listen for connections?
The first step in building our FTP server is getting our server to listen for connections from a client. Let's start with the basic FTPServer class:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Net;
using System.Text;
using System.Net.Sockets;
using System.IO;
using System.Threading;

namespace SharpFtpServer
{
    public class FtpServer
    {
        private TcpListener _listener;

        public FtpServer()
        {
        }

        public void Start()
        {
            _listener = new TcpListener(IPAddress.Any, 21);
            _listener.Start();
            _listener.BeginAcceptTcpClient(HandleAcceptTcpClient, _listener);
        }

        public void Stop()
        {
            if (_listener != null)
            {
                _listener.Stop();
            }
        }


Read more: Codeproject
QR: Inline images 1