Click here to Skip to main content
15,886,799 members
Please Sign up or sign in to vote.
0.00/5 (No votes)
Hi,

I have a tcp sender that send large file over tcp.
I have a receiver that receive the files and save them to disk.
It work great for one file, for multiple files it does not work!
I am googleing a few days, went over almost all articles and did not find a solution.
I would VERY appreciate if someone can help me and make my code run as I need!!!
thanks in advanced!


In the sender , I have a fileSystemWatcher, that watch a folder, and when a file created it takes the file and send it over tcp, by the sender.

Here is the sender code:

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

namespace Sender
{
    /// <summary>
    /// SocketSender is used to asynchronously listen the client and send file to the client.
    /// </summary>
    public   class SocketSender
    { 
        
        #region Memebers
    
        private  IPEndPoint targetEndPoint = null;
        private bool _isConnected;
        Socket clientSock = null;
        private ManualResetEvent PauseIfDisconnected;

        #endregion


        public SocketSender(IPEndPoint ipEndPoint)
        {
            targetEndPoint= ipEndPoint;
            clientSock = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
            _isConnected = false;
            PauseIfDisconnected = new ManualResetEvent(_isConnected);
        }


        public void Connect()
        {
            try
            {
                while (true)
                {
                    if (!_isConnected)
                    {
                        try
                        {
                            // Connect
                            clientSock = null;
                           clientSock = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);

                            clientSock.Connect(targetEndPoint); //target machine's ip address and the port number

                            PauseIfDisconnected.Set();
                            _isConnected = true;
                        }
                        catch (Exception ex)
                        {
                            Console.WriteLine("======= ERROR Connect function =====");
                            Console.WriteLine(ex.ToString());
                        }
                    }
                    else
                    {
                        if (!clientSock.Connected)
                        {
                            PauseIfDisconnected.Reset();
                            _isConnected = false;
                            clientSock.Close();
                        }
                    }
                }
            }
            catch (Exception ex)
            {
                Console.WriteLine("======= ERROR Connect function =====");
                Console.WriteLine(ex.ToString());
            }
        }
       
 

        /// <summary>
        /// Send file information to client
        /// </summary>
        public void Send(string fileToSend)
        {
            if (targetEndPoint == null)
                return;

            Socket clientSock = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);


            // Turn xml to bytes array
            byte[] fileName = Encoding.UTF8.GetBytes(Path.GetFileName(fileToSend)); //file name

           //This line - read bytes cause after the first time- an exception of :the file is being used by another process. but if I debug it- it works and doesn't fail (why?)
            byte[] fileData = File.ReadAllBytes(fileToSend); //file


            byte[] fileNameLen = BitConverter.GetBytes(fileName.Length); //lenght of file name
          var  clientData = new byte[4 + fileName.Length + fileData.Length];

            fileNameLen.CopyTo(clientData, 0);
            fileName.CopyTo(clientData, 4);
            fileData.CopyTo(clientData, 4 + fileName.Length);


            try
            {
                clientSock.Connect(targetEndPoint);
                clientSock.Send(clientData);
                clientSock.Close();
            }
            catch (Exception ex)
            {
                Console.WriteLine("======= ERROR Send function =====");
                Console.WriteLine(ex.ToString());

           
            }
           
        }
    }
}


Her is the receive code (a different project):

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

namespace Receiver
{

    /// <summary>
    /// AsynchronousClient is used to asynchronously receive the file from server.
    /// </summary>
    public   class AsynchronousClient
    {

        #region Members

          Thread t1;
          int flag = 0;
         IPEndPoint ipEnd = null;
         string folderSavePath;
         public static ManualResetEvent allDone = new ManualResetEvent(false);

        #endregion

         public AsynchronousClient(IPEndPoint ipEndPoint, string fSavePath)
         {
             ipEnd = ipEndPoint;
             folderSavePath = fSavePath;

             t1 = new Thread(new ThreadStart(StartListening));
             t1.Start();
         }


        /// <summary>
        /// Start connect to the server.
        /// </summary>
        public   void StartListening()
        {
            if (ipEnd == null)
                return;

  
            Socket listener = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
            try
            {
                listener.Bind(ipEnd);
                listener.Listen(100);
                while (true)
                {
                    allDone.Reset();
                    listener.BeginAccept(new AsyncCallback(AcceptCallback), listener);
                    allDone.WaitOne();

                }
            }
            catch (Exception ex)
            {

            }

        }

        public   void AcceptCallback(IAsyncResult ar)
        {

            allDone.Set();


            Socket listener = (Socket)ar.AsyncState;
            Socket handler = listener.EndAccept(ar);


            StateObject state = new StateObject();
            state.WorkSocket = handler;

            // Begin to receive the file from the server.
            handler.BeginReceive(state.Buffer, 0, StateObject.BufferSize, 0, new AsyncCallback(ReadCallback), state);
            flag = 0;
        }

        string fileSavePath = string.Empty;

        /// <summary>
        /// Receive the file send by the server.
        /// </summary>
        public   void ReadCallback(IAsyncResult ar)
        {
           
            int fileNameLen = 1;
            String content = String.Empty;
            StateObject state = (StateObject)ar.AsyncState;
            Socket handler = state.WorkSocket;
            int bytesRead = handler.EndReceive(ar);
           

            try
            {
                if (bytesRead > 0)
                {

                    if (flag == 0)
                    {

                        //create the folder for saving if needed

                        if (!Directory.Exists(folderSavePath))
                        {
                            Directory.CreateDirectory(folderSavePath);
                        }

                        // Get the filename length from the server.
                        fileNameLen = BitConverter.ToInt32(state.Buffer, 0);
                        string fileName = Encoding.UTF8.GetString(state.Buffer, 4, fileNameLen);

                        fileSavePath = folderSavePath + "\\" + fileName;
                        flag++;
                    }
                    if (flag >= 1)
                    {
                        using (BinaryWriter writer = new BinaryWriter(File.Open(fileSavePath, FileMode.Append, FileAccess.Write, FileShare.ReadWrite)))
                        {
                            if (flag == 1)
                            {
                                writer.Write(state.Buffer, 4 + fileNameLen, bytesRead - (4 + fileNameLen));
                                flag++;
                            }
                            else
                                writer.Write(state.Buffer, 0, bytesRead);

                            writer.Flush();
                            writer.Close();
                        }

                            handler.BeginReceive(state.Buffer, 0, StateObject.BufferSize, 0,
                            new AsyncCallback(ReadCallback), state);
                        
                    }

                }
                else
                {
                    handler.Close();
                }
            }
            catch(Exception ex)
            {

            }

        }

      
    }

    }


What I have tried:

I tried to develope a tcp sender that send multiple large files over TCP,
and a receiver, that listen and get the files from TCP and save them to disk.
Posted
Updated 15-Aug-18 6:05am
Comments
Mehdi Gholam 8-Jun-16 4:08am    
Try sending in blocks.
Richard MacCutchan 8-Jun-16 4:15am    
You have not explained what happens when you try sending more than one file.
Member 10844632 8-Jun-16 5:01am    
Something in the receiver does not work as needed. It just throw out of range excption, it seems that it proceed the files together and not one AFTER one or all in PERELAL
Richard MacCutchan 8-Jun-16 5:33am    
Something in the receiver does not work as needed
Then you need to use your debugger to find out what it is; we cannot guess and we cannot see your screen to know what is happening.
Member 10844632 8-Jun-16 6:46am    
I meant 'something' - that I do not know what to change in order to run it as needed with multiple files.
The receiver throw out of range exception on recive call back when I send a few files one after one

1 solution

Just take a short look at your code:
C#
the file is being used by another process

It means your file is being read, and you want to read it again at the same time.

Read once, split it in many blocks, and send this block.
 
Share this answer
 

This content, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)



CodeProject, 20 Bay Street, 11th Floor Toronto, Ontario, Canada M5J 2N8 +1 (416) 849-8900