Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- using System;
- using System.Collections.Generic;
- using System.Diagnostics;
- using System.IO;
- using System.Linq;
- using System.Net;
- using System.Net.Sockets;
- using System.Threading;
- // THE EXCEPTION HAPPENS AT UPLOADFILE METHOD (I call it from outside)
- namespace FtpProtocol_test
- {
- class FtpService
- {
- // Fields //
- private readonly TcpClient client = new TcpClient();
- private readonly IPEndPoint _ipEndPoint;
- private NetworkStream stream;
- // Properties //
- public int Port { get { return _ipEndPoint.Port; } }
- public IPAddress IpAddress { get { return _ipEndPoint.Address; } }
- // Constructors //
- public FtpService(IPEndPoint ipEndpont, bool connectNow)
- {
- _ipEndPoint = ipEndpont;
- if (connectNow)
- Connect();
- }
- public FtpService(string ip, int port, bool connectNow)
- : this(new IPEndPoint(IPAddress.Parse(ip), port), connectNow)
- { }
- public FtpService(bool connectNow)
- : this(new IPEndPoint(IPAddress.Loopback, 21), connectNow)
- { }
- // Methods //
- /// <summary>
- /// Method to connect to the FTP server.
- /// </summary>
- /// <returns>Returns a boolean value whether the connection succeeded.</returns>
- public bool Connect()
- {
- try
- {
- client.Connect(_ipEndPoint);
- stream = client.GetStream();
- }
- catch (Exception ex)
- {
- Trace.WriteLine(ex.Message);
- return false;
- }
- return true;
- }
- private void Send(byte[] buffer, bool doFlush = false)
- {
- stream.Write(buffer, 0, buffer.Length);
- if (doFlush) stream.Flush();
- }
- private void Read(byte[] buffer)
- {
- while (!stream.DataAvailable) { Thread.Sleep(1); }
- stream.Read(buffer, 0, buffer.Length);
- }
- /// <summary>
- /// Synchoronous method to download a file from an FTP server.
- /// </summary>
- /// <param name="filenamewithExtension">Name of the file with the extension located on the FTP server.</param>
- /// <returns>Returns the file in binary format.</returns>
- public byte[] DownloadFile(string filenamewithExtension)
- {
- // Verify filename, whether it exists or not
- var bytes = filenamewithExtension.GetBytes();
- Send(Values.FilenameDownload);
- Send(bytes);
- Send(Values.Endvalue, true);
- // Check results
- bytes = new byte[2];
- Read(bytes);
- if (bytes.MembersEquals(Values.Missing))
- {
- Trace.WriteLine("There is no such file found on the server!");
- return null;
- }
- // Start downloading
- List<byte> list = new List<byte>();
- bool succeeded = false;
- bytes = new byte[1024];
- while (true)
- {
- Send(Values.Download);
- Read(bytes);
- if (bytes.MembersEquals(Values.Success, 2))
- {
- succeeded = true;
- break;
- }
- if (bytes.MembersEquals(Values.Denied, 2) || bytes.MembersEquals(Values.NoFilename, 2))
- {
- break;
- }
- list.AddRange(bytes);
- }
- return succeeded ? list.ToArray() : null;
- }
- /// <summary>
- /// Synchronous method to download a file from the FTP server.
- /// </summary>
- /// <param name="filepath">Path of the file on the disk.</param>
- /// <returns>Returns a boolean value whether the upload has succeeded or not.</returns>
- public bool UploadFile(string filepath)
- {
- // Set filename and size
- var filecontent = Path.GetFileName(filepath).GetBytes();
- Send(Values.FilenameAndSizeUpload);
- Send(filecontent);
- //Send("|".GetBytes());
- filecontent = File.ReadAllBytes(filepath);
- //Send(BitConverter.GetBytes(filecontent.Sum(b => b)));
- Send(Values.Endvalue, true);
- // Check results
- var temp = new byte[2];
- Read(temp);
- if (temp.MembersEquals(Values.Exist))
- {
- Trace.WriteLine("This file already exists on the server!");
- return false;
- }
- // Start uploading
- int chunkIndex = 0;
- const int chunkSize = 1;
- int hash;
- while (filecontent.Length > chunkSize)
- {
- Send(Values.Upload);
- temp = GetSubArray(filecontent, chunkIndex, chunkSize);
- Send(temp);
- Send(Values.Endvalue, true);
- hash = temp.GetHashCode();
- temp = new byte[chunkSize];
- Read(temp);
- if (!BitConverter.GetBytes(hash).MembersEquals(temp, GetActualArrayLength(temp)))
- {
- Trace.WriteLine("Hash failed!");
- return false;
- // Szar megoldás, tudom, hogy újra kellene küldenem, és a szerveroldalon erre figyelni, külön packet, etc....
- }
- chunkIndex += chunkSize;
- }
- if (filecontent.Length == chunkIndex) return true;
- Send(Values.Upload);
- temp = GetSubArray(filecontent, chunkIndex, filecontent.Length - chunkIndex);
- Send(temp);
- Send(Values.Endvalue, true);
- hash = temp.GetHashCode();
- temp = new byte[1024];
- Read(temp);
- if (!BitConverter.GetBytes(hash).MembersEquals(temp, GetActualArrayLength(temp)))
- {
- Trace.WriteLine("Hash failed!");
- return false;
- }
- return true;
- }
- private static int GetActualArrayLength(byte[] array)
- {
- for (int i = 0; i < array.Length; i++)
- {
- if (array[i] == '\0') return i;
- }
- return array.Length;
- }
- private static byte[] GetSubArray(byte[] array, int index, int length)
- {
- var result = new byte[length];
- Array.Copy(array, index, result, 0, length);
- return result;
- }
- }
- }
Advertisement
Add Comment
Please, Sign In to add comment