p2p学习之网络地址的穿透问题(1)

  • 目录

什么是NAT的方案

p2p中穿越NAT的方案


NAT概述

NAT是一种把私有ip地址转换成公共的ip地址的技术方案,以解决私有网络中的主机然后通过一个公共的ip地址访问互联网的问题。NAT类似于防火墙,路由器等中间设备。NAT虽然节省IP地址等优点,但是它也又有缺点,例如:给网络端到端的实现带来了很多不透明问题,博主曾经尝试利用Qt来做一个qq,但是在即时通讯上停下了,后来我才知道我用的中继穿透NAT.效率最低,不可靠,依赖性强的NAT穿透.

而且由于在互联网上短期无法使用IPV6地址(128进制)完全替代IPV4(32进制),这就造成NAT技术还在互联网存在一段时间。

什么是IP地址

任何一台在线的拥有公共IP地址的主机都可以访问其他拥有公共IP地址的主机,通常IP地址有四部分组成,每部分对应8进制数值

IP地址分类

  1. 固定地址:静态IP地址,长期分配给互联网上主机使用的IP地址
  2. 临时地址:动态IP地址,是指临时互联网服务提供商系统分配出来动态地址
  3. 公共地址:它是用InterNIC(互联网信息中心)负责分配,是指那些在InterNIC上注册的IP地址,它是广域网内的地址
  4. 私有地址:它是指没有在NIC注册的IP地址,它通常由某个组织结构在其私有网络使用进行分配,拥有私有IP地址不能直接访问互联网,它是一种局域网

理论知识

  

1.为什么要有UDP打洞?

可以从图中看出,ClientA访问Server时。先是要通过NAT,经过这一层的转换后,他的内网IP会被换成NAT的公网IP,并且会为ClientA的此次访问事件分配一个临时的端口。

这能解决IP地址日益匮乏的问题。因为NAT的存在,可以是多台Client共用一个公网IP地址。但是同时造成了一个问题。外网访问内网是很麻烦的。因为NA这个时候并没有为ClientA的每个端口提供映射。而是要用时,临时分配一个。那个如果外网的Server想主动发起通信是不可以的。同样的,另一个内网的ClientB想访问ClientA就更难了。

2.UDP打洞

如果ClientA发出连接Server的请求,那么NAT上就会有一个ClientA对应的通信端口的洞。这个时候外网的Server就可以通过这个洞来访问了。因为ClientA请求了Server,代表信任Server。那么Server通过这个洞就能和ClientA进行通信了。

但是要注意一个问题。如果ClientB知道了这个洞大多数情况下,也是不能发送消息给A的。会被NAT抛弃。因为不是可信来源。(要使得ClientB能发送信息给A的前提是。ClientA给ClientB发送一个消息。就像ClientA对B说,我相信你),那么这个时候Clinet'B再给ClientA发送信息,A就能接受到了。

3.打洞过程

(1)ClientA请求Server。

(2)ClientB请求Server。

(3)Server把ClientA的IP和端口信息发给ClientB。

(4)Server把ClientB的IP和端口信息发给ClientA。

(5)ClientA利用信息给ClientB发消息。(A信任B)

(6)ClinetB利用信息给ClientA发消息。(B信任A)

(7)连接已经建立。两者可以直接通信了。

//--------------------------------------------------------------

但是这里一定要注意,能用UDP打洞成功是有要求的,不能是两个NAT设备都是对称类型的。如果一个是对称类型,一个是cone类型的NAT,这种情况下还可以使用预测法。网上可以找到对应的论文,大家可以去看看。我这里的成功是基于两端都是cone NAT类型设备的。

来自 <https://blog.csdn.net/u011580175/article/details/71001796>

 

许多P2P软件比如SKYPE,QQ,电驴之类需要不同内网的两台机子进行通信,而路由器的NAT机制决定了内网访问外网容易,而外网访问内网困难,那如何才能做到这一点呢?有办法------打洞!

 

具体实现方法需要一台服务器,现在假设两台内网PC,A和B想用端口40000通信,网关分别为NATA,NATB.服务器为S,配置如下:

A:              192.168.0.34               40000

NATA:       58.240.157.121           60020

B:              192.168.0.227             40000

NATB:       58.240.157.222           50030

S:              58.240.157.240           40000

 

打洞过程:

1.A访问S,打一个洞,洞的指向为A<->S

2.B访问S,打一个洞,洞的指向为B<->S

3.S访问A,告诉它:B想访问你

4.A访问B,洞的指向为A<->B,这个包B的路由器NATB收到后不会转发给B,而是丢弃,因为它认为这是来历不明的包:(

5.B访问A,洞的指向为B<->A,此时A与B可以进行双向通信,打洞成功

 

打洞的目的是为了告诉NAT,我要访问的IP是我"朋友",你不能阻拦它发过来的信息,比如第4步A通过发送这个包,告诉了NATA:B是我朋友;第5步B发送包给A,告诉了NATB:A是我朋友.最后NATA认识了B,而NATB认识了A,A与B终于实现了双向通信.

 

来自 <https://blog.csdn.net/jdh99/article/details/6667648>

实际操作

  1. 使用winow socket


 

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值