[百晓生]-INADDR_ANY

 

 

   [百晓生]-INADDR_ANY

 

    NADDR_ANY就是指定地址为0.0.0.0的地址,这个地址事实上表示不确定地址,或“所有地址”、“任意地址”。 一般来说,在各个系统中均定义成为0值。 一般来说,在各个系统中均定义成为0值。例如MontiVista Linux中在/usr/include/netinet/in.h定义为: 

 /* Address to accept any incoming messages. */

 
  #define INADDR_ANY ((in_addr_t) 0x00000000)
 
  一般情况下,如果你要建立 网络服务器 应用程序 ,则你要通知 服务器操作系统 :请在某地址 xxx.xxx.xxx.xxx上的某端口 yyyy上进行侦听,并且把侦听到的数据包发送给我。这个过程,你是通过bind() 系统调用 完成的。——也就是说,你的程序要绑定 服务器 的某地址,或者说:把服务器的某地址上的某端口占为已用。服务器 操作系统 可以给你这个指定的地址,也可以不给你。
 
  如果你的 服务器 有多个 网卡 (每个网卡上有不同的IP地址),而你的服务(不管是在udp端口上侦听,还是在tcp端口上侦听),出于某种原因:可能是你的 服务器 操作系统可能随时增减IP地址,也有可能是为了省去 确定 服务器上有什么 网络端口 网卡 )的麻烦 —— 可以要在调用 bind() 的时候,告诉操作系统:“我需要在 yyyy 端口上侦听,所以发送到 服务器 的这个端口,不管是哪个网卡/哪个IP地址接收到的数据,都是我处理的。”这时候, 服务器 程序则在0.0.0.0这个地址上进行侦听。例如:
 
  Proto Recv-Q Send-Q Local Address Foreign Address (state)
 
  ……
 
  udp4 0 0 *.7913 *.*
 
  udp4 0 0 *.7911 *.*
 
  tcp4 0 0 *.ftp *.* LISTEN
 
  ……
 
  ……
 
  以上这些是网络侦听的情况,其中Local Address 为 “*.ftp”、“*.7911”等,代表了服务程序绑定了服务器的所有 网卡
 
  好了,你明白了侦听INADDR_ANY是什么意思了,那么,我的 服务器 有N个IP地址,会不会收到重复的数据包收到数据包后,是不是会重复回复 客户端 呢?
 
  答案是:不会收到重复的数据包,也不会重复发送数据。
 
  为什么呢?因为 路由 的关系,从 客户端 来的IP包只可能到达其中一个 网卡 。同时在 服务器 进程发送数据时, 操作系统 根据自身维护着的 路由 表,决定IP数据包应该从哪一个outbound的gateway向目标端发送。根据gateway选择的不同,也就决定了从哪一个 网卡 /哪个IP地址发送。
 
  为什么不会接收到重复的数据包呢?
 
  答:因为 客户端 只向你的 服务器 上的唯一一个IP地址发送数据了。
 
  为什么不会重复发送数据包呢?
 
  答:因为发送数据包的路由( 路径 )是唯一的。如果 服务器 不知道在发送数据的时候应该向哪个地址发送数据,那么数据就会被发送到“ 默认 网关 ”上。
 
  如何选择发送数据的路径呢?
 
  答:依照 路由表 的要求发送。
 
  如果路由表的记录有重复/有冲突呢,这时候如何选择路径呢?
 
  答:路由表记录有优先级别。一般来说,Windows 操作系统 的路由表记录,如果是重复的话,以后来加入的记录为准,而某些操作系统,象linux/FreeBSD是不允许加入重复的路由表记录的;
 
  如果是专用的 路由器 ,有 路由选择 算法,一般来说,到达网络上的某一点的路径是可以有很多条的。 路由选择 算法可以 确定 “最好的一条路径”,这条路径要么是延时最小的,要么是通讯费用最低的,要么是带宽最高的,要么是跳点最小的——究竟是如何选择,就看 路由器 管理员 如何配置了。
 

  对于客户端如果绑定INADDR_ANY,情况类似。对于TCP而言,在connect()系统调用时将其绑定到一具体的IP地址。选择的依据是该地址所在子网到目标地址是可达的(reachable). 这时通过getsockname()系统调用就能得知具体使用哪一个地址。对于UDP而言, 情况比较特殊。即使使用connect()系统调用也不会绑定到一具体地址。这是因为对UDP使用connect()并不会真正向目标地址发送任何建立连接的数据,也不会验证到目标地址的可达性。它只是将目标地址的信息记录在内部的socket数据结构之中,共以后使用。只有当调用sendto()/send()时,由系统内核根据路由表决定由哪一个地址(网卡)发送UDP packet.

 
  P.S.
 
  -----------------------------------------------------------------------------
 
  在IP层中有一个 路由表
 
  在MSDOS窗口可以 运行命令 :netstat -r
 
  来显示路由表。根据 路由表 的条目从指定的 网卡 发送数据。
 
  ARP缓存用:arp -a
 
  来显示。
 

  通常以太网帧的目的MAC地址,是下一跳的MAC地址。

        以上来自百度百科!

 

 

你可能感兴趣的:(百晓生,百晓生,INADDR_ANY,INADDR_ANY,mystery)