TCP客户端连接 [英] TCP Client Connection

查看:139
本文介绍了TCP客户端连接的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有我对整个公司的分布式我的应用程序,通过我们的Windows 2003服务器将数据发送到我编写的应用程序(运行IIS 6.0)。小短信打通,但包含更多的数据(约20 KB)较大的邮件没有得到通过。

I have an application that I have written for my application distributed throughout the company to send data to me through our Windows 2003 server (running IIS 6.0). Small text messages get through, but larger messages containing more data (about 20 KB) are not getting through.

我设置字节的缓冲区,以TCP客户端的缓冲区大小。我注意到这是在服务器上接收到的我的数据;但是,它只能通过接受常规循环一次,我的大文件总是缓冲区大小正好的大小或8 KB我们的服务器上。换句话说,我的代码只能使它通过一个循环的服务器关闭套接字连接之前。

I set the byte buffer to the TCP Client’s buffer size. I noticed that my data was being received on the server; however, it only looped through the receive routine once, and my large files were always exactly the size of the buffer size, or 8 KB on our server. In other words, my code only makes it through one loop before the server closes the socket connection.

思考则可能是填充整个缓冲区的问题,我试图限制我的读/写仅有1 KB但这只会导致我们的服务器关闭套接字关闭连接之前收到1 KB后。

Thinking there might be an issue with filling the whole buffer, I tried limiting my read/writes to just 1 KB but this only resulted in our server closing the socket after receiving 1 KB before closing the connection.

我发送服务器的错误消息回客户端这样我就可以查看。我从客户端收到的特定错误消息是:

I send the server’s error message back to the client so I can view it. The specific error message that I receive from the client is:

无法将数据写入传输
连接:已建立

"Unable to write data to the transport connection: An established connection was aborted by the software in your host machine."

我更新我的服务器应用程序,以便底层TCP套接字将使用保持有效指示这一行:

I updated my server application so that the underlying TCP Socket would use "keep alives" with this line:

client.Client.SetSocketOption(SocketOptionLevel.Tcp, SocketOptionName.KeepAlive, true);

现在,每当我试图发送一个消息,客户端会收到错误:

Now, whenever I attempt sending a message, the client receives the error:

无法将数据写入传输
连接:一个现有的连接
远程主机强行关闭

"Unable to write data to the transport connection: An existing connection was forcibly closed by the remote host."

我们的网络管理员已经告诉我,他没有一个防火墙或阻止我们内部的服务器上的任意端口。

Our Network Administrator has told me that he does not have a firewall or any ports blocked on our internal server.

谷歌搜索中的错误,我发现帖子暗示人们尝试远程登录到服务器。我用自己的方向远程登录到服务器,但我不知道做出回应的内容:

Googling the errors, I found posts suggesting people try to telnet into the server. I used their directions to telnet into the server, but I am not sure what to make of the response:

C:>远程登录欢迎微软
Telnet客户端

C:> telnet Welcome to Microsoft Telnet Client

转义字符是'CTRL +]

Escape Character is ‘CTRL+]’

微软的Telnet>打开cpapp 500
连接到cpapp ...

Microsoft Telnet> open cpapp 500 Connecting To cpapp…

这是我得到的。我从来没有得到一个错误,而微软的Telnet屏幕最终将改变为按任意键继续...... - 我想它超时了,但我的代码以某种方式能够连接

This is all I get. I never get an error, and Microsoft’s Telnet screen will eventually change to "Press any key to continue…" – I guess it times out, but my code is somehow able to connect.

我曾尝试其他港口代码和通过Telnet包括25,80,和8080的Telnet踢出端口25,但我的应用程序似乎读的第一回路不管什么端口我告诉它运行。

I have tried other ports in code and through Telnet including 25, 80, and 8080. Telnet kicks out port 25, but my application seems to read the first loop no matter what port I tell it to run.

下面是我的代码是在客户机上运行:

Here is my code that runs on the clients:

int sendUsingTcp(string location) {
  string result = string.Empty;
  try {
    using (FileStream fs = new FileStream(location, FileMode.Open, FileAccess.Read)) {
      using (TcpClient client = new TcpClient(GetHostIP, CpAppDatabase.ServerPortNumber)) {
        byte[] riteBuf = new byte[client.SendBufferSize];
        byte[] readBuf = new byte[client.ReceiveBufferSize];
        using (NetworkStream ns = client.GetStream()) {
          if ((ns.CanRead == true) && (ns.CanWrite == true)) {
            int len;
            string AOK = string.Empty;
            do {
              len = fs.Read(riteBuf, 0, riteBuf.Length);
              ns.Write(riteBuf, 0, len);
              int nsRsvp = ns.Read(readBuf, 0, readBuf.Length);
              AOK = Encoding.ASCII.GetString(readBuf, 0, nsRsvp);
            } while ((len == riteBuf.Length) && (-1 < AOK.IndexOf("AOK")));
            result = AOK;
            return 1;
          }
          return 0;
        }
      }
    }
  } catch (Exception err) {
    Logger.LogError("Send()", err);
    MessageBox.Show(err.Message, "Message Failed", MessageBoxButtons.OK, MessageBoxIcon.Hand, 0);
    return -1;
  }
}

下面是我的代码在服务器上运行:

Here is my code that runs on the server:

SvrForm.Server = new TcpListener(IPAddress.Any, CpAppDatabase.ServerPortNumber);

void Worker_Engine(object sender, DoWorkEventArgs e) {
  BackgroundWorker worker = sender as BackgroundWorker;
  string path = Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.ApplicationData), Application.CompanyName);
  if (Directory.Exists(path) == false) Directory.CreateDirectory(path);
  Thread.Sleep(0);
  string eMsg = string.Empty;
  try {
    SvrForm.Server.Start();
    do {
      using (TcpClient client = SvrForm.Server.AcceptTcpClient()) { // waits until data is avaiable
        if (worker.CancellationPending == true) return;
        client.Client.SetSocketOption(SocketOptionLevel.Tcp, SocketOptionName.KeepAlive, true);
        string location = Path.Combine(path, string.Format("Acp{0:yyyyMMddHHmmssff}.bin", DateTime.Now));
        byte[] buf = new byte[client.ReceiveBufferSize];
        try {
          using (NetworkStream ns = client.GetStream()) {
            if ((ns.CanRead == true) && (ns.CanWrite == true)) {
              try {
                int len;
                byte[] AOK = Encoding.ASCII.GetBytes("AOK");
                using (FileStream fs = new FileStream(location, FileMode.Create, FileAccess.Write)) {
                  do {
                    len = ns.Read(buf, 0, client.ReceiveBufferSize);
                    fs.Write(buf, 0, len);
                    ns.Write(AOK, 0, AOK.Length);
                  } while ((0 < len) && (ns.DataAvailable == true));
                }
                byte[] okBuf = Encoding.ASCII.GetBytes("Message Received on Server");
                ns.Write(okBuf, 0, okBuf.Length);
              } catch (Exception err) {
                Global.LogError("ServerForm.cs - Worker_Engine(DoWorkEvent)", err);
                byte[] errBuf = Encoding.ASCII.GetBytes(err.Message);
                ns.Write(errBuf, 0, errBuf.Length);
              }
            }
          }
        }
        worker.ReportProgress(1, location);
      }
    } while (worker.CancellationPending == false);
  } catch (SocketException) {
    // See MSDN: Windows Sockets V2 API Error Code Documentation for detailed description of error code
    e.Cancel = true;
  } catch (Exception err) {
    eMsg = "Worker General Error:\r\n" + err.Message;
    e.Cancel = true;
    e.Result = err;
  } finally {
    SvrForm.Server.Stop();
  }
}



为什么我的应用程序继续从TCP读客户?难道我忘了设定的东西,告诉插槽,直至我完成继续开放?服务器代码永远不会看到一个异常,因为TCP客户端从来没有停止过,所以我知道有没有错误。

Why doesn’t my application continue reading from the TCP Client? Have I neglected to set something that tells the Socket to stay open until I have finished? The server code never sees an exception because the TCP Client is never stopped, so I know there is no error.

我们的网络管理员还没有收到他的副学士学位还,所以如果它原来是与服务器的一个问题,请你如何解决这个问题,因为我们可能不明白你在说什么的描述中详细说明。

Our Network Administrator has not received his Associates Degree yet, so if it turns out to be an issue with the Server, kindly be detailed in your description of how to resolve this, because we might not understand what you’re saying.

我这是这么长时间道歉,但我想确保你的乡亲那里知道我在做什么 - 甚至可能从闪耀我的技术的一些信息

I apologize for this being so long, but I want to make sure you folks out there know what I'm doing - and maybe even gleam some information from my technique!

感谢您的帮助!
〜乔

Thanks for helping! ~Joe

推荐答案

您应该先于发送的内容与内容的长度。你的循环假设所有的数据的循环执行之前,当在现实中作为数据发送你​​的循环正在执行的发送。会有时间当没有数据等待在电线上,所以循环终止;同时,内容仍然被通过线路发送。这就是为什么你的循环只运行一次。

You should precede the sent content with the length of that content. Your loop assumes that all of the data is sent before the loop executes, when in reality your loop is executing as the data is sent. There will be times when there is no data waiting on the wire, so the loop terminates; meanwhile, content is still being sent across the wire. That's why your loop is only running once.

这篇关于TCP客户端连接的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆