【发布时间】:2015-08-29 07:15:00
【问题描述】:
我试图在使用 Ubuntu 操作系统的笔记本电脑上运行时观察一个简单的 java echo 服务器和客户端程序。为了了解幕后发生的事情,我运行了服务器客户端并使用了这个命令
sudo netstat -pant 10007
Proto Recv-Q Send-Q Local Address Foreign Address State PID/Program name
tcp6 0 0 :::10007 :::* LISTEN 3551/java
tcp6 0 0 127.0.0.1:35459 127.0.0.1:10007 ESTABLISHED 3570/java
tcp6 0 0 127.0.0.1:10007 127.0.0.1:35459 ESTABLISHED 3551/java
因此,我们可以看到被动服务器(环回)处于 LISTEN 状态,并且在接受客户端(127.0.0.1.35459)套接字后,在 ESTABLISHED 中创建与主动服务器(127.0.0.1.10007)的新 TCP 连接状态。 但是,我们知道有几个TCP Socket状态,例如:SYN_SEND,SYN_RECEIVED,ESTABLISHED,LISTEN,FIN_WAIT_1,TIMED_WAIT,CLOSE_WAIT,FIN_WAIT_2,LAST_ACK,CLOSED等。所以,我对其他状态感到困惑,程序是否正在跳过这些套接字状态与否。
我想查看所有 TCP 套接字状态以了解整个套接字状态转换场景。那么我在哪里做错了?我给了错误的命令吗?或缺少任何代码修改?我缺少任何网络工具吗?我的分步过程出了什么问题?
那么,如何演示所有 TCP 套接字状态?
这是服务器代码:
import java.net.*;
import java.io.*;
public class EchoServer
{
public static void main(String[] args) throws IOException
{
ServerSocket serverSocket = null;
try {
serverSocket = new ServerSocket(10007);
}
catch (IOException e)
{
System.err.println("Could not listen on port: 10007.");
System.exit(1);
}
Socket clientSocket = null;
System.out.println ("Waiting for connection.....");
try {
clientSocket = serverSocket.accept();
}
catch (IOException e)
{
System.err.println("Accept failed.");
System.exit(1);
}
System.out.println ("Connection successful");
System.out.println ("Waiting for input.....");
PrintWriter out = new PrintWriter(clientSocket.getOutputStream(),
true);
BufferedReader in = new BufferedReader(
new InputStreamReader( clientSocket.getInputStream()));
String inputLine;
while ((inputLine = in.readLine()) != null)
{
System.out.println ("Server: " + inputLine);
out.println(inputLine);
if (inputLine.equals("Bye."))
break;
}
out.close();
in.close();
clientSocket.close();
serverSocket.close();
}
}
这是客户端代码:
import java.io.*;
import java.net.*;
public class EchoClient {
public static void main(String[] args) throws IOException {
String serverHostname = new String ("127.0.0.1");
if (args.length > 0)
serverHostname = args[0];
System.out.println ("Attemping to connect to host " +
serverHostname + " on port 10007.");
Socket echoSocket = null;
PrintWriter out = null;
BufferedReader in = null;
try {
echoSocket = new Socket(serverHostname, 10007);
out = new PrintWriter(echoSocket.getOutputStream(), true);
in = new BufferedReader(new InputStreamReader(
echoSocket.getInputStream()));
} catch (UnknownHostException e) {
System.err.println("Don't know about host: " + serverHostname);
System.exit(1);
} catch (IOException e) {
System.err.println("Couldn't get I/O for "
+ "the connection to: " + serverHostname);
System.exit(1);
}
BufferedReader stdIn = new BufferedReader(
new InputStreamReader(System.in));
String userInput;
System.out.print ("input: ");
while ((userInput = stdIn.readLine()) != null) {
out.println(userInput);
System.out.println("echo: " + in.readLine());
System.out.print ("input: ");
}
out.close();
in.close();
stdIn.close();
echoSocket.close();
}
}
【问题讨论】:
-
您必须速度很快,或者以非常低的延迟运行链接。如果网络运行正常,SYN-SENT 和 SYN-RECEIVED 将在一秒钟内转换为 ESTABLISHED,这同样适用于几个关闭阶段。
-
您需要使用某种限制工具将网络连接速度降低到 10 字节/秒,然后您会看到所有状态。我怀疑事情发生得太快了,您无法观察所有状态。
-
我无法理解。您能否更具体一点:任何明确的代码或指南或类似链接。
-
你不明白到底是什么?你有两个 cmets,都清楚地表达了。
-
我明白 cmets 说什么,但如何让它变慢?需要哪些命令或代码使其变慢?