深入解析iodine项目的DNS隧道协议v00000500
iodine Official git repo for iodine dns tunnel 项目地址: https://gitcode.com/gh_mirrors/io/iodine
协议概述
iodine是一个通过DNS协议建立隧道的工具,它巧妙地将网络数据封装在DNS查询和响应中,实现网络通信。本文将详细解析iodine项目中版本号为00000500的协议规范,帮助读者理解其工作原理。
协议版本协商
在连接建立阶段,客户端和服务器首先进行协议版本协商:
-
客户端发送:
- 首字节为'v'或'V'
- 后续内容使用Base32编码:
- 4字节大端序协议版本号
- 2字节缓存未命中计数器(CMC)
-
服务器响应:
- 4字符响应码:
- VACK:版本匹配,后跟登录挑战
- VNAK:版本不匹配,后跟服务器协议版本
- VFUL:服务器无空闲槽位,后跟最大用户数
- 4字节值:根据响应码不同,含义不同
- 1字节用户ID(仅VACK时有效)
- 4字符响应码:
登录认证流程
认证过程确保只有授权用户能建立连接:
-
客户端发送:
- 首字节为'l'或'L'
- Base32编码内容:
- 1字节用户ID
- 16字节MD5哈希值(密码前32字节与8次重复的登录挑战异或后计算)
- CMC
-
服务器响应:
- LNAK:认证失败
- x.x.x.x-y.y.y.y-mtu-netmask:认证成功,包含服务器IP、客户端IP、MTU和网络掩码位数
数据编码与传输
iodine协议设计了高效的数据封装方式:
上行数据头格式(客户端→服务器)
3210 432 10 43 210 4321 0
+----+---+--+--+---+----+-+
|UUUU|SSS|FF|FF|DDD|GGGG|L|
+----+---+--+--+---+----+-+
下行数据头格式(服务器→客户端)
7 654 3210 765 4321 0
+-+---+----+---+----+-+
|C|SSS|FFFF|DDD|GGGG|L|
+-+---+----+---+----+-+
字段说明:
- UUUU:用户ID
- L:数据包最后一个分片标志
- SS/SSS:上行数据包序列号
- FFFF:上行数据分片号
- DDD:下行数据包序列号
- GGGG:下行数据分片号
- C:下行数据压缩标志
数据包结构
上行数据包:
- 1字节ASCII十六进制编码的用户字节
- 3字节Base32编码的头部
- 使用选定编解码器编码的负载数据
下行数据包:
- 2字节头部
- 可能被压缩的负载数据
高级功能
编解码器切换
客户端可以请求切换编解码器:
- 发送首字节's'或'S'
- Base32编码的5位用户ID
- Base32编码的5位值(5或6),表示每个编码字节的原始位数
服务器响应编解码器名称或BADCODEC(拒绝切换)
分片大小探测与设置
探测:
- 客户端发送首字节'r'或'R'
- 3个Base32字符编码的15位信息:
- 4位用户ID
- 11位分片大小
- 跟随一个长随机查询
设置:
- 客户端发送首字节'n'或'N'
- Base32编码内容:
- 1字节用户ID
- 2字节新的下行分片大小
- CMC
服务器返回新的分片大小或BADFRAG(拒绝设置)
心跳机制
客户端发送Ping包:
- 首字节'p'或'P'
- Base32编码内容:
- 1字节(4位用户ID)
- 1字节(3位下行序列号+4位下行分片号)
- CMC
服务器响应DNS NULL类型响应:
- 无数据发送:数据长度为0字节
- 有数据发送:发送下行数据包,前缀为2字节头部
协议设计特点
- 高效性:通过精心设计的头部结构,最大化利用DNS数据包空间
- 灵活性:支持动态编解码器切换和分片大小调整
- 可靠性:包含序列号和分片号确保数据有序传输
- 安全性:使用挑战-响应机制进行认证
理解这些协议细节有助于开发者更好地使用iodine工具,或在类似项目中实现DNS隧道功能。协议中的许多设计考虑,如分片机制和编解码器切换,都是针对DNS协议特性所做的优化,值得网络协议开发者借鉴。
iodine Official git repo for iodine dns tunnel 项目地址: https://gitcode.com/gh_mirrors/io/iodine
创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考