有一个称为socket();
的系统调用,它在监听服务器上创建一个套接字。
我想了解的是服务器创建 IP+端口组合。
假设 telnet 使用端口 23。
现在,当客户端机器进行连接时,服务器正在监听的端口然后那里的连接不在端口 23 上,实际上它在不同的端口上。我的困惑是
在服务器端也会发生同样的事情。
例如,我写了一个服务器来监听端口 23,然后将在服务器端与不同的客户端完成连接,它们是如何区分的,因为它们都在同一个端口上。那么你怎么能在同一个服务器上建立这么多连接端口。如果有人使用
telnet (23) 或 ftp (21) 或 ssh (22) 那么许多人仍然可以登录到服务器上的同一服务端口,即不同用户的多个 ssh 连接,其中 ssh 仅在端口 22 监听。那又怎样套接字究竟是做什么的,或者套接字是如何创建的?
更新
我明白了所解释的内容。取决于发起连接的客户端计算机的 IP + 端口组合,服务器端可以处理其余的事情,我认为此信息可能由套接字文件描述符使用。我看到的是 connect()
系统调用,我们使用如下
connect(sockfd,(struct sockaddr *)&client_address,size_t);
我们确实在客户端传递 struct sockaddr *
,它具有唯一的 IP + 端口组合我认为当服务器接受它时,事情就会继续。
我想进一步了解的是服务器端的参数
accept(server_sockfd,(struct sockaddr *)&client_address,(size_t *)sizeof (struct sockaddr ));
它是否获得了从客户端使用 connect() 传递过来的相同的 client_address 系统调用?如果是,则同一服务器监听多个客户端的socket_descriptors是不同的。我想知道的是,当它接受来自客户端的请求时,服务器端的数据结构是如何维护的。
最佳答案
标识连接的唯一组合是:
- 源地址和端口
- 目的地址和端口
在您的示例中,许多连接的目标地址和端口都是相同的,但每个连接都来自源地址和端口的唯一组合。
这是一个简介tcpdump
我通过 FTP(端口 21)从桌面连接到服务器的 session :
22:55:50.160704 IP 172.17.42.19.64619 > 172.17.42.1.21: S 2284409007:2284409007(0) win 8192 <mss 1460,nop,nop,sackOK>
22:55:50.160735 IP 172.17.42.1.21 > 172.17.42.19.64619: S 1222495721:1222495721(0) ack 2284409008 win 65535 <mss 1460,sackOK,eol>
22:55:50.160827 IP 172.17.42.19.64619 > 172.17.42.1.21: . ack 1 win 8192
22:55:50.162991 IP 172.17.42.1.21 > 172.17.42.19.64619: P 1:61(60) ack 1 win 65535
22:55:50.369860 IP 172.17.42.19.64619 > 172.17.42.1.21: . ack 61 win 8132
22:55:56.288779 IP 172.17.42.19.64620 > 172.17.42.1.21: S 3841819536:3841819536(0) win 8192 <mss 1460,nop,nop,sackOK>
22:55:56.288811 IP 172.17.42.1.21 > 172.17.42.19.64620: S 454286057:454286057(0) ack 3841819537 win 65535 <mss 1460,sackOK,eol>
22:55:56.288923 IP 172.17.42.19.64620 > 172.17.42.1.21: . ack 1 win 8192
22:55:56.290224 IP 172.17.42.1.21 > 172.17.42.19.64620: P 1:61(60) ack 1 win 65535
22:55:56.488239 IP 172.17.42.19.64620 > 172.17.42.1.21: . ack 61 win 8132
22:56:03.301421 IP 172.17.42.19.64619 > 172.17.42.1.21: P 1:12(11) ack 61 win 8132
22:56:03.306994 IP 172.17.42.1.21 > 172.17.42.19.64619: P 61:94(33) ack 12 win 65535
22:56:03.510663 IP 172.17.42.19.64619 > 172.17.42.1.21: . ack 94 win 8099
22:56:06.525348 IP 172.17.42.19.64620 > 172.17.42.1.21: P 1:12(11) ack 61 win 8132
22:56:06.526332 IP 172.17.42.1.21 > 172.17.42.19.64620: P 61:94(33) ack 12 win 65535
22:56:06.726857 IP 172.17.42.19.64620 > 172.17.42.1.21: . ack 94 win 8099
可以看到初始连接是172.17.42.19.64619 <-> 172.17.42.1.21
.端口 64619 是 Windows 7 框在建立传出连接时碰巧选择为源端口的端口。 S
的两行是 SYN
数据包来回建立连接。然后我启动下一个连接,Windows 只使用下一个可用端口 64620。连接 172.17.42.19.64620 <-> 172.17.42.1.21
形成我在顶部列出的项目的新的唯一元组。只有客户端的端口不同,但这就足够了。每个到达服务器21端口的数据包都可以通过源端口来区分。从服务器上的 21 端口到达客户端的每个数据包 都可以通过目标端口来区分。
关于c - 与C网络编程中的套接字相关的问题,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/6516994/