0

学校のプロジェクトとして、ファイル共有アプリケーションを作成しています。必要なすべてのメッセージをサーバーに送信し、すべて問題ありませんが、ファイルをサーバーにアップロードすると、ファイルが本来あるべき状態になることはありません。アプリケーションをデバッグしたところ、Socket が正しいバイト数を返していないことがわかりました。それが正しいかどうかはわかりませんが、間違っていると思います。たとえば、小さな .txt ファイルをアップロードして Notepad++ で開くと、ファイルの末尾に多くの null が表示されます。インターネットで検索したところ、コードプレックスで私が行っているのと同じアプリケーションを見つけましたが、ソケットは正しい量のデータを返しますhttp://srf.codeplex.com/

誰かが私を助けてくれれば幸いです。私の母国語ではないので、英語が下手でしたら申し訳ありません。

最初のメッセージを処理し、クリント接続を受信するサーバー関数:

    public void Brodcast()
    {
        tcpListener.Start();
        while (true)
        {
            try
            {
                ClientSocket = tcpListener.AcceptSocket();
                MessageReceiving();
            }
            catch { }
        }
    }

    public void MessageReceiving()
    {
        if (ClientSocket.Connected)
        {
            OpenPackage.MessageTypeToBytes RSMessage = new OpenPackage.MessageTypeToBytes();
            ClientSocket.Receive(RSMessage.MessageBytes, 512, SocketFlags.None);
            if (RSMessage.TypeOfMessage == MessageType.Login)
                DoLogin();
            else if (RSMessage.TypeOfMessage == MessageType.Download)
                SendFile();
            else if (RSMessage.TypeOfMessage == MessageType.Upload)
                ReceiveFile();
            else if (RSMessage.TypeOfMessage == MessageType.NConta)
                NewAccount();
            else if (RSMessage.TypeOfMessage == MessageType.Search)
                SearchResult();
            else if (RSMessage.TypeOfMessage == MessageType.Apagar)
                DeleteFile();
        }
    }

サーバ:

    public void ReceiveFile()
    {
        try
        {
            byte[] MessageBytes = new byte[512];
            ClientSocket.Receive(MessageBytes, 512, SocketFlags.None);
            string Nickname = Encoding.ASCII.GetString(MessageBytes);
            string[] CNickFich = Nickname.Split('$');
            FileHandler Handler = new FileHandler();
            long DirectorySize = Handler.GetDirectorySize("C:\\" + CNickFich[0]);
            long FileSize = long.Parse(CNickFich[2]);
            bool Subs = false;
            if ((FileSize + DirectorySize) < MaxFolderSize && MaxFileSize > FileSize)
            {
                if (!Directory.Exists("C:\\" + CNickFich[0]))
                    Directory.CreateDirectory("C:\\" + CNickFich[0]);
                if (File.Exists("C:\\" + CNickFich[0] + "\\" + CNickFich[1]))
                {
                    File.Delete("C:\\" + CNickFich[0] + "\\" + CNickFich[1]);
                    Subs = true;
                }
                MessageTypeToBytes MessageInBytes = new MessageTypeToBytes() { TypeOfMessage = MessageType.OK };
                ClientSocket.Send(MessageInBytes.MessageBytes, 512, SocketFlags.None);

                int qtdReceived = 0;
                long CurrentSize = 0;
                byte[] FileBuffer = new byte[BufferSize];
                FileStream FileStr = new FileStream("C:\\" + CNickFich[0] + "\\" + CNickFich[1], FileMode.CreateNew, FileAccess.Write);
                BufferedStream BufferStr = new BufferedStream(FileStr);
                while (CurrentSize < FileSize)
                {
                    qtdReceived = ClientSocket.Receive(FileBuffer, 0, FileBuffer.Length, 0);
                    CurrentSize += qtdReceived;
                    BufferStr.Write(FileBuffer, 0, qtdReceived);
                    BufferStr.Flush();
                }
                BufferStr.Close();
                FileStr.Close();
                SqlDataAdapter data = new SqlDataAdapter("SELECT COD_CONTA FROM CONTAS WHERE NICKNAME='"
                + CNickFich[0] + "'", OConn);
                DataTable dt = new DataTable();
                data.Fill(dt);
                if (NFicheiro(Handler.MD5HashFromFile("C:\\" + CNickFich[0] + "\\" + CNickFich[1]), "C:\\" + CNickFich[0] + "\\" + CNickFich[1], Subs,
                    int.Parse(dt.Rows[0][0].ToString()), CNickFich[3]))
                    MessageInBytes.TypeOfMessage = MessageType.OK;
                else
                    MessageInBytes.TypeOfMessage = MessageType.Erro;
                ClientSocket.Send(MessageInBytes.MessageBytes, 512, SocketFlags.None);
                //NFicheiro(new FileHandler().MD5HashFromFile("C:\\" + CNickFich[0] + "\\" + CNickFich[1]), "C:\\" + CNickFich[0], false, 1, );
            }
            else
            {
                MessageTypeToBytes MessageInBytes = new MessageTypeToBytes() { TypeOfMessage = MessageType.Erro };
                ClientSocket.Send(MessageInBytes.MessageBytes, 512, SocketFlags.None);
            }
        }
        catch
        {
            MessageTypeToBytes MessageInBytes = new MessageTypeToBytes() { TypeOfMessage = MessageType.Erro };
            ClientSocket.Send(MessageInBytes.MessageBytes, 512, SocketFlags.None);
        }
    }

クライアント:

    private void UploadWork_DoWork(object sender, DoWorkEventArgs e)
    {
        FileStream FileStr = null;
        BufferedStream BufferStr = null;
        Stopwatch Counter = new Stopwatch();
        try
        {
            int CurrentProgress = 0;
            Program.CTasks.ClientSocket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
            Program.CTasks.ClientSocket.ReceiveTimeout = 60000;
            Program.CTasks.ClientSocket.SendTimeout = 60000;
            Program.CTasks.ClientSocket.Connect(IPAddress.Parse(Program.CTasks.HostName), Program.CTasks.Port);
            MessageTypeToBytes MessageInBytes = new MessageTypeToBytes() { TypeOfMessage = MessageType.Upload };
            Program.CTasks.ClientSocket.Send(MessageInBytes.MessageBytes, 512, SocketFlags.None);
            FileInfo FileNFO = new FileInfo(Open.FileName);
            byte[] NickPath = new byte[512];
            byte[] UNickPath = Encoding.ASCII.GetBytes(Program.Nickname + "$" + Open.FileName.Substring(Open.FileName.LastIndexOf('\\') + 1) + "$" + FileNFO.Length.ToString() + "$");
            byte[] TagCollectionBytes = Encoding.ASCII.GetBytes(TagCollection + "$");
            UNickPath.CopyTo(NickPath, 0);
            TagCollectionBytes.CopyTo(NickPath, UNickPath.Length);
            Program.CTasks.ClientSocket.Send(NickPath, 512, SocketFlags.None);
            Program.CTasks.ClientSocket.Receive(MessageInBytes.MessageBytes, 512, SocketFlags.None);
            if (MessageInBytes.TypeOfMessage == MessageType.OK)
            {
                long FileSize = FileNFO.Length;
                long CurrentFileSize = 0;
                long qtdRead = 0;
                byte[] FileBytes = new byte[BufferSizer];
                FileStr = new FileStream(Open.FileName, FileMode.Open, FileAccess.Read);
                BufferStr = new BufferedStream(FileStr);
                Counter.Start();
                while ((qtdRead = BufferStr.Read(FileBytes, 0, FileBytes.Length)) > 0)
                {
                    Program.CTasks.ClientSocket.Send(FileBytes, 0, FileBytes.Length, 0);
                    CurrentFileSize += qtdRead;
                    CurrentProgress = (int)((CurrentFileSize * 100) / FileSize);
                    UploadSpeed = ((double)CurrentFileSize / (Counter.Elapsed.TotalMilliseconds / 100));
                    UploadWork.ReportProgress(CurrentProgress);
                }
                FileStr.Close();
                Counter.Stop();
                Program.CTasks.ClientSocket.Receive(MessageInBytes.MessageBytes, 512, SocketFlags.None);
                Program.CTasks.ClientSocket.Close();
            }
        }
        catch
        {
            try
            {
                Counter.Stop();
                FileStr.Close();
                Program.CTasks.ClientSocket.Close();
            }
            catch { }
        }
    }
4

2 に答える 2

2

送信するデータが多すぎます...ファイルの最後では、完全にいっぱいになるため、バイトFileBytesのみを送信する必要があります。qtdRead

交換

Program.CTasks.ClientSocket.Send(FileBytes, 0, FileBytes.Length, 0);

Program.CTasks.ClientSocket.Send(FileBytes, 0, qtdRead, 0);
于 2012-06-08T22:47:59.520 に答える
1

送信時に読み取った長さではなく、バッファの長さを使用しています。

于 2012-06-08T22:47:47.353 に答える