第1章.MSNP15概述
MSN是微软推出的一款聊天工具,它的通信协议是微软自己提出的MSNP(即MSN Protocol)。MSNP目前还不是因特网标准协议,但却发展迅速,被广泛地应用到各种聊天工具的开发中。MSNP更新很快,当前的最新版本为MSNP15(即版本15)。MSN8.1所使用的协议就是MSNP15。
MSNP15支持即时消息、文件传输、语音通信、视频通信和远程协助等通信方式。其中文件传输、语音通信和视频通信等是直接的点对点通信,而即时消息等是经过服务器中转通信的。即时消息和文件传输是基于TCP的,而语音通信和视频通信是基于UDP的。
第2章.MSNP15详解
2.1. 几个概念
MSNP15的通信很多是通过服务器中转的,所以它的服务器架构比较复杂。协议的客户端与服务端的交互有两种形式:命令和消息。当客户端发送的命令执行出错时,服务器用错误代码来通知对方。因此,下面将依次讲述服务器、命令、消息和错误。这是协议分析的基础。
2.1.1. 服务器
MSNP15的服务器有三种。
派遣服务器(Dispatch Server, DS)——客户端最先连接的服务器。派遣服务器与客户端连接后,首先根据从客户端处得出的的信息,给客户端分配合适的通知服务器,然后断开与客户端的连接。派遣服务器的端口号是1863。
通知服务器(Notification Server, NS)——客户端需要一直连接的服务器。通知服务器负责大部分非中转的交互,包括登陆,改变状态(隐身、在线等),获取用户列表,修改用户列表,发起聊天等。通知服务器的服务端口号由派遣服务器指定,一般为1863。
接线服务器(Switchboar Server, SB)——客户端间通信所使用的中转服务器。每开一个聊天窗口,客户端就与服务器建立一个TCP会话。文件传输和语音聊天等,为发起点对点的会话,也需要从接线服务器上得到对方的IP地址等信息。接线服务器的服务端口由通知服务器指定,一般为1863。
2.1.2. 命令
命令是服务器与客户交互的一种方式。MSNP15的命令使用纯ASCII码,对非ASCII码使用URL编码。命令的一般格式是:
XXX[<SP>TrID<SP>PARAM1<SP>PARAM2…]<CRLF>
其中,<SP>是空白字符,<CRLF>是回车换行,XXX是一个3字符的命令串,TrID是一个流水号,PARAMx是参数,[ ]内是可选项。最简单的命令没有流水号和参数。为了方便起见,下面讨论时用" "代表<SP>,"\r\n"代表<CRLF>,"\x??"代表一个值为0x??字节。红色表示由客户端发出,蓝色表示由服务器发出。一个比较常见的命令如下。“USR 14 OK bripengandre@hotmail.com 1 0”就是一个比较常见的命令。
2.1.3. 消息
MSN Messenger消息符合MIME 1.0标准,由消息头与消息体组成,通常使用UTF-8编码。一个MSN Messenger消息的例子如下:
MIME-Version: 1.0\r\nContent-Type: text/plain; charset=UTF-8\r\nX-MMS-IM-Format: FN=%E5%AE%8B%E4%BD%93; EF=; CO=0; CS=86; PF=0\r\n\r\nbhw98\xE4\xBD\xA0\xE5\xA5\xBD\xEF\xBC\x81
经简单分析可知,"%E5%AE%8B%E4%BD%93"是"宋体"的UTF-8加URL编码,而"bhw98\xE4\xBD\xA0\xE5\xA5\xBD\xEF\xBC\x81"是"bhw98你好!"的UTF-8编码。
2.1.4. 错误
无论是由于客户端发出的命令无效,参数无效,还是其他什么原因,服务器可以返回一个错误。错误的格式为
XXX[<SP>TrID]<CRLF>
其中,XXX是一个3位数字的串。如“ADD 21 AL non_existent@hotmail.com non_existent@hotmail.com\r\n205 21\r\n”。其中,non_existent@hotmail.com是一个不存在的账号。
2.1.5. 常用命令
为了理解后文中给出的例子,这里给出一些常用命令,如表 1 常用命令所示。需要注意的是,表 1 常用命令中的命令是针对MSNP10的,所以这些命令仅供参考。
命令
|
来源
|
去向
|
说明
|
备注
|
ACK
|
SS
|
Client
|
确认,做出肯定回答。
|
acknowledgement
|
ADD
|
Client
|
NS
|
发出添加新联系人到列表的请求。
|
add user
|
NS
|
Client
|
返回添加新联系人请求的应答。
|
ADG
|
Client
|
NS
|
发出添加新联系人组请求。
|
add group
|
NS
|
Client
|
返回添加新联系人组请求的应答。
|
ANS
|
Client
|
SS
|
接受聊天连接请求。
|
answer
|
BLP
|
Client
|
NS
|
设置对尚未列入明确允许/禁止的联系人列表的保密策略。
|
block list privacy
|
NS
|
Client
|
返回设置保密策略请求的应答。
|
BYE
|
SS
|
Client
|
通知客户端结束会话。
|
bye
|
CAL
|
Client
|
SS
|
发出建立聊天连接的请求。
|
call
|
SS
|
Client
|
返回建立聊天连接请求的应答。
|
CHG
|
Client
|
NS
|
发出改变状态的请求。
|
change state
|
NS
|
Client
|
返回改变状态的应答。
|
CHL
|
NS
|
Client
|
服务器发出验证要求。
|
challenge
|
SS
|
Client
|
CVR
|
Client
|
NS
|
发出客户端的OS、语言、MSN Messenger版本等信息。
|
client version
|
Client
|
SS
|
NS
|
Client
|
返回推荐的MSN Messenger版本、升级软件需要的下载地址等信息。
|
SS
|
Client
|
FLN
|
NS
|
Client
|
通知有联系人列表中的用户下线。
|
off-line
|
GTC
|
Client
|
NS
|
设置当有联系人列表中的用户状态改变时给出的提示。
|
greeting to changes?
|
NS
|
Client
|
返回设置请求的应答。
|
INF
|
Client
|
NS
|
询问服务器所支持的认证方式。
|
information?
|
Client
|
SS
|
NS
|
Client
|
返回服务器所支持的认证方式。
|
SS
|
Client
|
ILN
|
NS
|
Client
|
当客户端登录或添加联系人到列表时,通知列表中的联系人的状态。
|
initial online state
|
IRO
|
SS
|
Client
|
当有新用户加入聊天连接时,通知客户端该连接中的用户名单。
|
initial roster information
|
JOI
|
SS
|
Client
|
通知客户端已经同另外的用户建立了聊天连接。
|
jion
|
LSG
|
Client
|
NS
|
发出获取联系人组列表的请求。
|
list groups
|
NS
|
Client
|
返回获取联系人组列表请求的应答。
|
LST
|
Client
|
NS
|
发出获取联系人列表的请求。
|
list
|
NS
|
Client
|
返回获取联系人列表请求的应答。
|
MSG
|
Client
|
SS
|
发送消息到其他用户(聊天对象)。
|
message
|
NS
|
Client
|
传递服务器(系统) 的消息到客户端。
|
SS
|
Client
|
传递其他用户(聊天对象)的消息到客户端。
|
NAK
|
SS
|
Client
|
做出否定回答。
|
negative acknowledgement
|
NLN
|
NS
|
Client
|
通知客户端联系人上线或改变状态。
|
on-line
|
OUT
|
All
|
All
|
结束客户端-服务器的连接。
|
out
|
PNG
|
Client
|
NS
|
测试TCP连接状态。
|
ping
|
Client
|
SS
|
PRP
|
Client
|
NS
|
发出设置个人电话号码的请求。
|
personal phone number
|
NS
|
Client
|
返回设置请求的应答
|
PNG
|
Client
|
NS
|
测试TCP连接状态。
|
ping
|
Client
|
SS
|
QNG
|
NS
|
Client
|
返回测试TCP连接状态的应答。
|
quiz ping?
|
SS
|
Client
|
QRY
|
Client
|
NS
|
客户端回答服务器的验证要求。
|
quiz reply?
|
Client
|
SS
|
REA
|
Client
|
NS
|
发出修改用户昵称的请求。
|
rename nickname
|
NS
|
Client
|
返回修改用户昵称请求的应答。
|
REG
|
Client
|
NS
|
发出修改联系人组的请求。
|
rename group
|
NS
|
Client
|
返回修改联系人组请求的应答。
|
REM
|
Client
|
NS
|
发出从联系人列表中删除用户的请求。
|
rename user
|
NS
|
Client
|
返回删除用户请求的应答。
|
RMG
|
Client
|
NS
|
发出删除联系人组的请求。
|
remove group
|
NS
|
Client
|
返回删除联系人组请求的应答。
|
RNG
|
NS
|
Client
|
通知客户端有人要建立聊天连接。
|
ring
|
SYN
|
Client
|
NS
|
客户端-服务器同步。
|
synchronization
|
NS
|
Client
|
URL
|
Client
|
NS
|
发出获取MSN服务URL的请求。
|
URL
|
NS
|
Client
|
返回获取URL请求的应答。
|
USR
|
All
|
All
|
声明、传递、鉴别用户身份。
|
user
|
VER
|
Client
|
DS
|
协商MSN Messenger协议版本。
|
version
|
Client
|
NS
|
DS
|
Client
|
NS
|
Client
|
XFR
|
DS
|
Client
|
向客户端分配NS(通知客户端转向连接指定的NS)。
|
transfer
|
Client
|
NS
|
发出分配SS的请求。
|
NS
|
Client
|
返回分配SS请求的应答。
|
表 1 常用命令
(bripengandre) |