实现PROXY穿越(12):NTLM type1 Message

  当发送一个HTTP的请求,收到服务器返回407的时候,我们检查Proxy-Authenticate字段。这个字段可能出现多次,常见的出现三次,参数分别为Negotiate, Kerberos、NTLM。Negotiate是一个ssp(Security Support Provider),它会根据用户的环境选择其它合适的具体SSP:NTLM或者kerberos。 NTLM 是一个比较老的SSP,但支持广泛,Kerberos是新的比较好的SSP,但不支持NT4.0以及之前版本。用户一般不直接调用NTLM或者 Kerberos,而是调用Negotiate。Negotiate的策略是,如果用户系统不支持Kerberos,或者没有提供支持Kerberos的 信息,则Negotiate会默认返回NTLM给客户端。
  我们还需要检查Connect字段,如果给出Close,客户端应该关闭原来的TCP连接,在新的TCP连接中给出下一个消息。假设我们选择了NTLM作为认证的算法,客户端收到407后,将第一个HTTP请求增加认证内容重新发送一次,即将NTLM type1 Message,并经过base64的扰码放置在Proxy-Authorization: Negotiate %s中。下面讨论NTLM type1 Message的构造。如果希望详细资料,推荐 http://davenport.sourceforge.net/ntlm.html 。对于开发而言,还是本着实用主义,不求甚解,只求怎用。NTLM还是比较麻烦,即使你确实使用NTLM算法,还需要和服务器通过NTLM flag来确定具体使用NTLMv1还是v2还是v2 session等等。这么多不确定性,完全符合IT人力求的简单复杂化,清楚的也给你弄迷糊的一贯原则。
  client发送携带type1 message的请求给服务器,服务器再次返回407,携带type2 Message,中间含有挑战值,client根据挑战值计算response,封装在type3 message中,再次向服务器发送请求,如果认证通过,服务器,返回200 OK。

  NTLM type1消息有三个输入:

  • 客户端所在的DOMAIN
  • 主机的名字HOSTNAME,注意这个不是登陆PROXY的用户帐号,而是你的机器workstation在网络中的名字。
  • OS操作系统的版本,可选,不填最省事。

这里给出一个数据结构。

 0-7字节: char protocol[8]
表明属于NTLMSSP协议,依次位'N', 'T', 'L', 'M', 'S', 'S', 'P', '/0'
 8-11字节:int type
其中第8字节NTLM的类型即type1,填入0x01,后三个字节为0,4字节依次为0x01 00 00 00。由于我们的操作系统是little_endian,本应是0x00 00 00 01表示1,由于高位在前面,故顺序反过来。通过ethreal工具抓包的时候,可以看得非常清楚。
 12-15字节:unsigned int flags
 NTLM的flags,是个很麻烦的东西。
  • 0x00000001 Negotiate Unicode :允许unicode的方式,在先前的算法分析中,需要使用到unicode,这年头哪能不支持,话说回来,如果不支持,还不晓得之前的算法计算需要怎么样的改动,所以位置1。
  • 0x00000002 Negotiate OEM :到网上共产主义科普了一下『OEM是Original Equipment Manufacture(原始设备制造商)的缩写,它是指一种"代工生产"方式,其含义是生产者不直接生产产品,而是利用自己掌握的"关键的核心技术",负责设计和开发、控制销售"渠道",具体的加工任务交给别的企业去做的方式。这种方式是在电子产业大量发展起来以后才在世界范围内逐步生成的一种普遍现象,微软、IBM等国际上的主要大企业均采用这种方式。』。不清楚此项对算法的计算有什么影响,从实际的效果看,是否置位没有关系。
  • 0x00000004 Request Target,要求server在Type2 Message中给出target信息。从NTLM的三种计算方式中,我们知道在NTLMv2的时候需要使用target,因此如果我们希望使用NTLM v1或者NTLM v2 session的方式,此位置0,如果使用NTLM v2方式,此位置1。
  • 0x00000008 Unknown,置0
  • 0x00000010 Negotiate Sign,携带电子戳用于保证消息的完整性。不知道如何搞电子戳,我们目标先保证proxy的穿越,置0
  • 0x00000020 Negotiate Seal,在服务器和客户端之间的认证进行加密,置0
  • 0x00000040 Negotiate Datagram Style 表明对datagram进行认证,这个不太清楚具体如何进行,选择置0
  • 0x00000080 Negotiate Lan Manager Key,LM key将被用于数字签名和Sealing,只有在0x00000100或者0x00000200置位的时候才有效,故我们悬着置0
  • 0x00000100 Negotiate Netware 不曾使用,置0
  • 0x00000200 Negotiate NTLM,表明使用NTLM方式,当然置1
  • 0x00000400 unknown,置0
  • 0x00000800 Negotiate Anonymous,用于type3 Message,表明建立一个anonymous context
  • 0x00001000 Negotiate Domain Supplied,表明在type1 message中包含主机的domain信息,置1
  • 0x00002000 Negotiate Workstation Supplied,表明在type message中给出主机(workstation)的名字,置1
  • 0x00004000 Negotiate Local Call,表面客户端和服务器在同一台主机,这样可以使用内部的认证来取代对挑战值进行响应的方式,置0
  • 0x00008000 Negotiate Always Sign,表面客户端和服务器之间的通信,使用哑元签发,不懂,是否如果没有数字签名都应该置1,从网络抓包看,直接置1
  • 0x00010000 Target Type Domain,由服务器给出的Type2 Message中使用,表明给出的target是一个域
  • 0x00020000 Target Type Server,由服务器给出的Type2 Message中使用,表明给出的target是一个服务器
  • 0x00040000 Target Type Share,不详细,由Type2 MEssage使用,通常置0
  • 0x00080000 Negotiate NTLM2 Key,如果希望使用NTLM v2 session的方式,置1,否则置0
  • 0x00100000 Request Init Response,无用,置0
  • 0x00200000 Request Accept Response,无用,置0
  • 0x00400000 Request Non-NT Session Key,无用,置0
  • 0x00800000 Negotiate Target Info,对于Type2 Message消息,如果携带target信息,置1,否则置0
  • 0x01000000 unknown,置0
  • 0x02000000 unknown,在Ethereal中,也没有给出相关的解析,但是在MSN和firefox的抓包中,这一位置1,如果我们使用NLTMv2或者v2 session的方式,我们置1,否则置0
  • 0x04000000 unknown,置0
  • 0x08000000 unknown,置0
  • 0x10000000 unknown,置0
  • 0x20000000 Negotiate 128,支持128比特的加密,不明白具体指什么。
  • 0x40000000 Negotiate Key Exchange,表面客户端在type3 message中在session key中给出一个加密的master key
  • 0x80000000 Negotiate 56,支持56比特的加密,不明白具体置什么。
 16-19字节:
short domain_len;
short domain_allocation_len;
无论是domain的长度,还是domain分配的长度,都是一样的,如果域名为“DOMAIN”,就为0x07000700。
 20-23字节:int domain_offset
放置domain位置的偏移量,即开始存放domain信息的位置
 24-27字节
short hostname_len;
short hostname_allocation_len;
无论是hostname的长度,还是分配的长度,都是一样的,名字为“WORKSTATION”,就为0x0b000b00。
 28-31字节:int hostname_offset
放置hostname得偏移量,如果没有可选8字节os_version信息,从32字节开始给出hostname得信息,即为0x20000000,如果含有则从40字节开始,为0x28000000。
 32字节开始:内容存放
  • 8字节的os_version信息
  • 存放hostname
  • 存放domain
需要注意的是,计算机得主机名和域名是指主机所在的workstation的名字,和登陆帐号域名不一样,这点需要特别主义。对于windows机器来讲,可以从系统中获取,这两个信息使用大写的方式表达。不提供的话,长度给出0就可以了。


对于NTLM v1,type1 message中flags我们给出0xb201,在NTLM v2,给出0x0280b205,在NTLM session中给出0x0288b201,如果在Type2消息中协商成功,那么在type3消息中的flags是同样的值。

 

相关链接:我的网络通信相关文章

NTLM的实现:

  • 实现PROXY穿越(16):NTLM的PROXY穿越
  • 实现PROXY穿越(15):NTLM Session Security
  • 实现PROXY穿越(14):NTLM type3 Message
  • 实现PROXY穿越(13):NTLM type2 Message
  • 实现PROXY穿越(12):NTLM type1 Message
  • 实现PROXY穿越(11):NTLMv2 session response
  • 实现PROXY穿越(10):NTLMv2 response
  • 实现PROXY穿越(9):NTLMv1 response
  • 实现PROXY穿越(8):NT-Hash的实现
  • 实现PROXY穿越(7):MD4和MD5
  • 实现PROXY穿越(6):LM-Hash的实现
  • 实现PROXY穿越(5):DES算法之三
  • 实现PROXY穿越(4):DES算法之二
  • 实现PROXY穿越(3):DES算法之一
  • 实现PROXY穿越(2):Base64算法
  • 实现PROXY穿越(1):流程和NTLM算法

你可能感兴趣的:(算法,加密,session,服务器,domain,Allocation)