socket程序listen之后,不写accept函数,会是怎样一种情况?

时间:2022-05-30 23:55:21
一般的网络程序,服务器端的socket在收到一个新连接,总是会派生出一个socket与客户端通信。但是如果没有accept,会发生什么情况?
连接会失败吗?
不失败的话,客户端最多能有多少个连接能连上来?

18 个解决方案

#1


服务器不写accept,怎么通信。
服务器通过accept返回的socket,这个socket就是客户端的连接。
在这个socket上send和recv和客户端通信。

服务器不写accept,客户端一个都连接不上。

#2


可以连接上去,个数是监听队列listen里设置的个数,调用了accept,监听队列就能再多监听一个客户端连接了

#3


tcp模式下,没有accept无法连接啊。udp模式下是不需要accept的。

#4



int listen(int sockfd, int backlog);

不用accept 最大的监听个数就是这个backlog了
因为一直没有accept,所以这个里的队列会一直在,不会减少
虽然这个backlog是可以手动设置的,但是linux是最大值128
如果超过这个数目了,就是无效的,最大也就128

#5


同意二楼四楼的

在被动状态的socket有两个队列,一个是正在进行三次握手的socket队列,一个是完成三次握手的socket队列。在握手完成后会从正在握手队列移到握手完成的队列,此时已经建立连接。accept就是从已经完成三次握手的socket队列里面取,不accept客户端能完成的连接就是此队列的大小

#6



       The  behavior  of  the  backlog argument on TCP sockets changed with Linux 2.2.  Now it specifies the queue length for completely established
       sockets waiting to be accepted, instead of the number of incomplete connection requests.  The maximum length  of  the  queue  for  incomplete
       sockets  can  be  set  using /proc/sys/net/ipv4/tcp_max_syn_backlog.  When syncookies are enabled there is no logical maximum length and this setting is ignored.  
backlog指的就是已经完成握手了的队列的大小,不accept能建立连接的大小就是它了。
正在握手的队列大小由/proc/sys/net/ipv4/tcp_max_syn_backlog指定。如果启用了syncookies未完成队列的大小是无限的,syncookies 主要是将在收到客户端SYN包后就分配资源改成在完成握手后再分配这些资源,避免同时收到大量的SYN包的需要分配大量资源而受到攻击。

不知道我的理解正确与否

#7


服务端没accept ,客户端怎么可能连接上

假设服务器listen(s,2)而不accept
那么前2个客户端会阻塞在connect上,得不到返回。(也就是没连上)
第3个开始的客户端connect函数不会阻塞,直接返回SOCKET_ERROR

#8


引用 7 楼 ananluowei 的回复:
服务端没accept ,客户端怎么可能连接上

假设服务器listen(s,2)而不accept
那么前2个客户端会阻塞在connect上,得不到返回。(也就是没连上)
第3个开始的客户端connect函数不会阻塞,直接返回SOCKET_ERROR

说错了,再去试试

#9


引用 8 楼 spirit008 的回复:
Quote: 引用 7 楼 ananluowei 的回复:

服务端没accept ,客户端怎么可能连接上

假设服务器listen(s,2)而不accept
那么前2个客户端会阻塞在connect上,得不到返回。(也就是没连上)
第3个开始的客户端connect函数不会阻塞,直接返回SOCKET_ERROR

说错了,再去试试

试了一下,服务器不accept,客户端还真的能连接上。
你是对的。
话说回来,服务器不accept,得不到client的socket啊,如何与客户端通信?

#10


引用 9 楼 ananluowei 的回复:
Quote: 引用 8 楼 spirit008 的回复:

Quote: 引用 7 楼 ananluowei 的回复:

服务端没accept ,客户端怎么可能连接上

假设服务器listen(s,2)而不accept
那么前2个客户端会阻塞在connect上,得不到返回。(也就是没连上)
第3个开始的客户端connect函数不会阻塞,直接返回SOCKET_ERROR

说错了,再去试试

试了一下,服务器不accept,客户端还真的能连接上。
你是对的。
话说回来,服务器不accept,得不到client的socket啊,如何与客户端通信?

所以,不accpet只是不能继续通讯而已,三次握手是协议栈做的,不是api控制的,否则,你考虑效率要多低,就好像每次这种贴都会争论什么阻塞send什么时候返回,阻塞recv什么时候返回。

#11


引用 10 楼 spirit008 的回复:
所以,不accpet只是不能继续通讯而已,三次握手是协议栈做的,不是api控制的,否则,你考虑效率要多低,就好像每次这种贴都会争论什么阻塞send什么时候返回,阻塞recv什么时候返回。

嗯,明白了,谢谢。

#12


listen()维护两个队列,一个是未完成三次握手的,
一个是已完成三次握手的,
accept()是从已完成三次握手的队列中取出一个而已!

#13


谢谢大伙的热心,这是昨天面试碰到的一个不会答的问题。面试官随即也问到了backlog参数的意义,也不知道!
因为没有这方面的经验-_-! 楼主工作中一直用JAVA写代码-_-!
昨天一回来,赶紧翻unix programming的书,里有一段话:

The backlog argument provides a hint to the system of the number of outstanding connect requests that it should enqueue on behalf of the process. The actual value is determined by the system, but the upper limit is specified as SOMAXCONN in <sys/socket.h>.

On Solaris, the SOMAXCONN value in <sys/socket.h> is ignored. The particular maximum depends on the implementation of each protocol. For TCP, the default is 128.

Once the queue is full, the system will reject additional connect requests, so the backlog value must be chosen based on the expected load of the server and the amount of processing it must do to accept a connect request and start the service.

Once a server has called listen, the socket used can receive connect requests. We use the accept function to retrieve a connect request and convert that into a connection.

这里没有解释说listen之后,维护了2个队列!

第一句话的意思好像是(我也不确定)这个值是未完成(三次握手?)的连接的数量!

引用 6 楼 listenerxu 的回复:
       The  behavior  of  the  backlog argument on TCP sockets changed with Linux 2.2.  Now it specifies the queue length for completely established
       sockets waiting to be accepted, instead of the number of incomplete connection requests.  The maximum length  of  the  queue  for  incomplete
       sockets  can  be  set  using /proc/sys/net/ipv4/tcp_max_syn_backlog.  When syncookies are enabled there is no logical maximum length and this setting is ignored.  
backlog指的就是已经完成握手了的队列的大小,不accept能建立连接的大小就是它了。
正在握手的队列大小由/proc/sys/net/ipv4/tcp_max_syn_backlog指定。如果启用了syncookies未完成队列的大小是无限的,syncookies 主要是将在收到客户端SYN包后就分配资源改成在完成握手后再分配这些资源,避免同时收到大量的SYN包的需要分配大量资源而受到攻击。

不知道我的理解正确与否


所以6楼同学说的:backlog指的就是已经完成握手了的队列的大小
好像是不一样!

6楼同学的这段说明是从哪里摘下来的呢?

#14


引用 13 楼 kittaaron 的回复:
谢谢大伙的热心,这是昨天面试碰到的一个不会答的问题。面试官随即也问到了backlog参数的意义,也不知道!
因为没有这方面的经验-_-! 楼主工作中一直用JAVA写代码-_-!
昨天一回来,赶紧翻unix programming的书,里有一段话:

The backlog argument provides a hint to the system of the number of outstanding connect requests that it should enqueue on behalf of the process. The actual value is determined by the system, but the upper limit is specified as SOMAXCONN in <sys/socket.h>.

On Solaris, the SOMAXCONN value in <sys/socket.h> is ignored. The particular maximum depends on the implementation of each protocol. For TCP, the default is 128.

Once the queue is full, the system will reject additional connect requests, so the backlog value must be chosen based on the expected load of the server and the amount of processing it must do to accept a connect request and start the service.

Once a server has called listen, the socket used can receive connect requests. We use the accept function to retrieve a connect request and convert that into a connection.

这里没有解释说listen之后,维护了2个队列!

第一句话的意思好像是(我也不确定)这个值是未完成(三次握手?)的连接的数量!

Quote: 引用 6 楼 listenerxu 的回复:


       The  behavior  of  the  backlog argument on TCP sockets changed with Linux 2.2.  Now it specifies the queue length for completely established
       sockets waiting to be accepted, instead of the number of incomplete connection requests.  The maximum length  of  the  queue  for  incomplete
       sockets  can  be  set  using /proc/sys/net/ipv4/tcp_max_syn_backlog.  When syncookies are enabled there is no logical maximum length and this setting is ignored.  
backlog指的就是已经完成握手了的队列的大小,不accept能建立连接的大小就是它了。
正在握手的队列大小由/proc/sys/net/ipv4/tcp_max_syn_backlog指定。如果启用了syncookies未完成队列的大小是无限的,syncookies 主要是将在收到客户端SYN包后就分配资源改成在完成握手后再分配这些资源,避免同时收到大量的SYN包的需要分配大量资源而受到攻击。

不知道我的理解正确与否


所以6楼同学说的:backlog指的就是已经完成握手了的队列的大小
好像是不一样!

6楼同学的这段说明是从哪里摘下来的呢?


  The  behavior  of  the  backlog argument on TCP sockets changed with Linux 2.2.  Now it specifies the queue length for completely established sockets waiting to be accepted, instead of the number of incomplete connection requests. 

哪里不对呢?man 手册

#15


引用 12 楼 max_min_ 的回复:
listen()维护两个队列,一个是未完成三次握手的,
一个是已完成三次握手的,
accept()是从已完成三次握手的队列中取出一个而已!


所以就算没有accept(),客户端发起连接请求,握手还是会完成的?这个最大能连接的客户端数量就是已完成三次握手的队列的长度?

#16


回14楼
是因为我在unix环境高级编程上看到这句:The backlog argument provides a hint to the system of the number of outstanding connect requests that it should enqueue on behalf of the process
这个outstanding好像是‘未解决的,未完成的’意思,所以有疑问!

#17


引用 15 楼 kittaaron 的回复:
Quote: 引用 12 楼 max_min_ 的回复:

listen()维护两个队列,一个是未完成三次握手的,
一个是已完成三次握手的,
accept()是从已完成三次握手的队列中取出一个而已!


所以就算没有accept(),客户端发起连接请求,握手还是会完成的?这个最大能连接的客户端数量就是已完成三次握手的队列的长度?

对的! accept只是取已经完成握手的!

#18


int listen(int sockfd, int backlog);
backlog 就是默认最大的等待队列长度

#1


服务器不写accept,怎么通信。
服务器通过accept返回的socket,这个socket就是客户端的连接。
在这个socket上send和recv和客户端通信。

服务器不写accept,客户端一个都连接不上。

#2


可以连接上去,个数是监听队列listen里设置的个数,调用了accept,监听队列就能再多监听一个客户端连接了

#3


tcp模式下,没有accept无法连接啊。udp模式下是不需要accept的。

#4



int listen(int sockfd, int backlog);

不用accept 最大的监听个数就是这个backlog了
因为一直没有accept,所以这个里的队列会一直在,不会减少
虽然这个backlog是可以手动设置的,但是linux是最大值128
如果超过这个数目了,就是无效的,最大也就128

#5


同意二楼四楼的

在被动状态的socket有两个队列,一个是正在进行三次握手的socket队列,一个是完成三次握手的socket队列。在握手完成后会从正在握手队列移到握手完成的队列,此时已经建立连接。accept就是从已经完成三次握手的socket队列里面取,不accept客户端能完成的连接就是此队列的大小

#6



       The  behavior  of  the  backlog argument on TCP sockets changed with Linux 2.2.  Now it specifies the queue length for completely established
       sockets waiting to be accepted, instead of the number of incomplete connection requests.  The maximum length  of  the  queue  for  incomplete
       sockets  can  be  set  using /proc/sys/net/ipv4/tcp_max_syn_backlog.  When syncookies are enabled there is no logical maximum length and this setting is ignored.  
backlog指的就是已经完成握手了的队列的大小,不accept能建立连接的大小就是它了。
正在握手的队列大小由/proc/sys/net/ipv4/tcp_max_syn_backlog指定。如果启用了syncookies未完成队列的大小是无限的,syncookies 主要是将在收到客户端SYN包后就分配资源改成在完成握手后再分配这些资源,避免同时收到大量的SYN包的需要分配大量资源而受到攻击。

不知道我的理解正确与否

#7


服务端没accept ,客户端怎么可能连接上

假设服务器listen(s,2)而不accept
那么前2个客户端会阻塞在connect上,得不到返回。(也就是没连上)
第3个开始的客户端connect函数不会阻塞,直接返回SOCKET_ERROR

#8


引用 7 楼 ananluowei 的回复:
服务端没accept ,客户端怎么可能连接上

假设服务器listen(s,2)而不accept
那么前2个客户端会阻塞在connect上,得不到返回。(也就是没连上)
第3个开始的客户端connect函数不会阻塞,直接返回SOCKET_ERROR

说错了,再去试试

#9


引用 8 楼 spirit008 的回复:
Quote: 引用 7 楼 ananluowei 的回复:

服务端没accept ,客户端怎么可能连接上

假设服务器listen(s,2)而不accept
那么前2个客户端会阻塞在connect上,得不到返回。(也就是没连上)
第3个开始的客户端connect函数不会阻塞,直接返回SOCKET_ERROR

说错了,再去试试

试了一下,服务器不accept,客户端还真的能连接上。
你是对的。
话说回来,服务器不accept,得不到client的socket啊,如何与客户端通信?

#10


引用 9 楼 ananluowei 的回复:
Quote: 引用 8 楼 spirit008 的回复:

Quote: 引用 7 楼 ananluowei 的回复:

服务端没accept ,客户端怎么可能连接上

假设服务器listen(s,2)而不accept
那么前2个客户端会阻塞在connect上,得不到返回。(也就是没连上)
第3个开始的客户端connect函数不会阻塞,直接返回SOCKET_ERROR

说错了,再去试试

试了一下,服务器不accept,客户端还真的能连接上。
你是对的。
话说回来,服务器不accept,得不到client的socket啊,如何与客户端通信?

所以,不accpet只是不能继续通讯而已,三次握手是协议栈做的,不是api控制的,否则,你考虑效率要多低,就好像每次这种贴都会争论什么阻塞send什么时候返回,阻塞recv什么时候返回。

#11


引用 10 楼 spirit008 的回复:
所以,不accpet只是不能继续通讯而已,三次握手是协议栈做的,不是api控制的,否则,你考虑效率要多低,就好像每次这种贴都会争论什么阻塞send什么时候返回,阻塞recv什么时候返回。

嗯,明白了,谢谢。

#12


listen()维护两个队列,一个是未完成三次握手的,
一个是已完成三次握手的,
accept()是从已完成三次握手的队列中取出一个而已!

#13


谢谢大伙的热心,这是昨天面试碰到的一个不会答的问题。面试官随即也问到了backlog参数的意义,也不知道!
因为没有这方面的经验-_-! 楼主工作中一直用JAVA写代码-_-!
昨天一回来,赶紧翻unix programming的书,里有一段话:

The backlog argument provides a hint to the system of the number of outstanding connect requests that it should enqueue on behalf of the process. The actual value is determined by the system, but the upper limit is specified as SOMAXCONN in <sys/socket.h>.

On Solaris, the SOMAXCONN value in <sys/socket.h> is ignored. The particular maximum depends on the implementation of each protocol. For TCP, the default is 128.

Once the queue is full, the system will reject additional connect requests, so the backlog value must be chosen based on the expected load of the server and the amount of processing it must do to accept a connect request and start the service.

Once a server has called listen, the socket used can receive connect requests. We use the accept function to retrieve a connect request and convert that into a connection.

这里没有解释说listen之后,维护了2个队列!

第一句话的意思好像是(我也不确定)这个值是未完成(三次握手?)的连接的数量!

引用 6 楼 listenerxu 的回复:
       The  behavior  of  the  backlog argument on TCP sockets changed with Linux 2.2.  Now it specifies the queue length for completely established
       sockets waiting to be accepted, instead of the number of incomplete connection requests.  The maximum length  of  the  queue  for  incomplete
       sockets  can  be  set  using /proc/sys/net/ipv4/tcp_max_syn_backlog.  When syncookies are enabled there is no logical maximum length and this setting is ignored.  
backlog指的就是已经完成握手了的队列的大小,不accept能建立连接的大小就是它了。
正在握手的队列大小由/proc/sys/net/ipv4/tcp_max_syn_backlog指定。如果启用了syncookies未完成队列的大小是无限的,syncookies 主要是将在收到客户端SYN包后就分配资源改成在完成握手后再分配这些资源,避免同时收到大量的SYN包的需要分配大量资源而受到攻击。

不知道我的理解正确与否


所以6楼同学说的:backlog指的就是已经完成握手了的队列的大小
好像是不一样!

6楼同学的这段说明是从哪里摘下来的呢?

#14


引用 13 楼 kittaaron 的回复:
谢谢大伙的热心,这是昨天面试碰到的一个不会答的问题。面试官随即也问到了backlog参数的意义,也不知道!
因为没有这方面的经验-_-! 楼主工作中一直用JAVA写代码-_-!
昨天一回来,赶紧翻unix programming的书,里有一段话:

The backlog argument provides a hint to the system of the number of outstanding connect requests that it should enqueue on behalf of the process. The actual value is determined by the system, but the upper limit is specified as SOMAXCONN in <sys/socket.h>.

On Solaris, the SOMAXCONN value in <sys/socket.h> is ignored. The particular maximum depends on the implementation of each protocol. For TCP, the default is 128.

Once the queue is full, the system will reject additional connect requests, so the backlog value must be chosen based on the expected load of the server and the amount of processing it must do to accept a connect request and start the service.

Once a server has called listen, the socket used can receive connect requests. We use the accept function to retrieve a connect request and convert that into a connection.

这里没有解释说listen之后,维护了2个队列!

第一句话的意思好像是(我也不确定)这个值是未完成(三次握手?)的连接的数量!

Quote: 引用 6 楼 listenerxu 的回复:


       The  behavior  of  the  backlog argument on TCP sockets changed with Linux 2.2.  Now it specifies the queue length for completely established
       sockets waiting to be accepted, instead of the number of incomplete connection requests.  The maximum length  of  the  queue  for  incomplete
       sockets  can  be  set  using /proc/sys/net/ipv4/tcp_max_syn_backlog.  When syncookies are enabled there is no logical maximum length and this setting is ignored.  
backlog指的就是已经完成握手了的队列的大小,不accept能建立连接的大小就是它了。
正在握手的队列大小由/proc/sys/net/ipv4/tcp_max_syn_backlog指定。如果启用了syncookies未完成队列的大小是无限的,syncookies 主要是将在收到客户端SYN包后就分配资源改成在完成握手后再分配这些资源,避免同时收到大量的SYN包的需要分配大量资源而受到攻击。

不知道我的理解正确与否


所以6楼同学说的:backlog指的就是已经完成握手了的队列的大小
好像是不一样!

6楼同学的这段说明是从哪里摘下来的呢?


  The  behavior  of  the  backlog argument on TCP sockets changed with Linux 2.2.  Now it specifies the queue length for completely established sockets waiting to be accepted, instead of the number of incomplete connection requests. 

哪里不对呢?man 手册

#15


引用 12 楼 max_min_ 的回复:
listen()维护两个队列,一个是未完成三次握手的,
一个是已完成三次握手的,
accept()是从已完成三次握手的队列中取出一个而已!


所以就算没有accept(),客户端发起连接请求,握手还是会完成的?这个最大能连接的客户端数量就是已完成三次握手的队列的长度?

#16


回14楼
是因为我在unix环境高级编程上看到这句:The backlog argument provides a hint to the system of the number of outstanding connect requests that it should enqueue on behalf of the process
这个outstanding好像是‘未解决的,未完成的’意思,所以有疑问!

#17


引用 15 楼 kittaaron 的回复:
Quote: 引用 12 楼 max_min_ 的回复:

listen()维护两个队列,一个是未完成三次握手的,
一个是已完成三次握手的,
accept()是从已完成三次握手的队列中取出一个而已!


所以就算没有accept(),客户端发起连接请求,握手还是会完成的?这个最大能连接的客户端数量就是已完成三次握手的队列的长度?

对的! accept只是取已经完成握手的!

#18


int listen(int sockfd, int backlog);
backlog 就是默认最大的等待队列长度