导航

腾讯QQ空间g_tk算法

Posted on 2011-03-10 12:20  pcajax  阅读(12012)  评论(2编辑  收藏  举报
 在百度搜索g_tk,只得到几个可怜而且不完整的答案,因此,我首次在源始时代公开一下QQ空间的g_tk算法。其实g_tk只是QQ空间对日志进行操作的时候,所采取的一套安全机制,如果g_tk字符串的值不对的话,请求是没有办法提交的,因此,很多刚刚涉及HTTP协议技术的人想对QQ空间这尊大佛动手脚的话,只能望而却步。下面我以VB为例,在这里详解一下g_tk的计算方法。
其实g_tk校验是通过skey值来算出来的,弄过QQ登录的人可能都知道,在登录成功之后,cookies里都会返回skey值,通常是以@开头,并且带有一串看似无规则的大小写字母混合,总共10位。下面我们先来抓包看看,g_tk到底用在了哪里,我们以转载日志为例来抓包,上图:

完整数据包内容如下:
POST /cgi-bin/blognew/blog_quote HTTP/1.1Accept: */*Accept-Language: zh-cnReferer: http://b.qzone.qq.com/proxy.htmlIf-Modified-Since: 0Content-Type: application/x-www-form-urlencodedAccept-Encoding: gzip, deflateUser-Agent: Mozilla/4.0 (compatible; MSIE 8.0; Windows NT 6.1; Trident/4.0; SLCC2; .NET CLR 2.0.50727; .NET CLR 3.5.30729; .NET CLR 3.0.30729; Media Center PC 6.0; .NET4.0C; .NET4.0E; Tablet PC 2.0)Host: b.qzone.qq.comContent-Length: 65Connection: Keep-AliveCache-Control: no-cacheCookie: pt2gguin=o0138001655; ptcz=0b25a27219dd08bcfe38fc85365593dadb1a2a99cac9f1abfd5fb31a7052f89b; pvid=6724688319; flv=10.0; adid=138001655; adSP=GHTsOtSHTIJdDIr9+GXVoaFY59pet/LONpbU1rA0yPY=_837_326830_1290874683_; adVer=3121; ac=1,030,006; ptui_qstatus=2; uin=o0138001655; skey=@sZmfEEBdt; ptisp=ctc; ssid=s8226120880; login_time=B46BD5B3A93F9EC5226847DB4AE9A71589641475FCCEBBC9; __Q_w_s__appDataSeed=1; randomSeed=220115
uin=138001655&fromuin=715746717&blogid=1286714133&g_tk=1423927145
   我们可以看到,数据包主体部分最后一个参数就是g_tk值,一般是一串数字。那这个值到底怎么算出来的呢?
因为我们在网页登录QQ的时候,腾讯都会通过cookies里的skey值来计算,用js来算。既然在运算的时候执行了js脚本,那么我们就可以在抓包中获得。那g_tk是通过什么算法算出来的?其实很简单,当我们得到skey后,循环取单字符的二进制并取左值.累加之后就得到后面的g_tk值了,这听上去很复杂,不过算法不用我们自己写,我们只需要执行在腾讯网页登录的时候所执行的那个js脚本就可以了。当然,js不能直接调用,不过既然我写了这篇文章,就已经是有备而来的,js算法我已经整理并写了一个最简单的,代码如下:
function getGTK(str){
   var hash = 5381;
   for(var i = 0, len = str.length; i < len; ++i)
   {
   hash += (hash << 5) + str.charAt(i).charCodeAt();
   }
   return hash & 0x7fffffff;
}
   那么我们现在还有两个问题没有解决:
1.如何获取登录后的cookies?
2.如何在VB中执行js代码并得到返回值?

上面两个问题其实到了你们手里,我相信也不会是问题了,下面我再通过代码以及讲解,来剖析并解决这两个所谓的问题。对于HTTP数据包POST/GET,相信看这篇文章的人应该都懂得吧,否则你看了也没用,那么我们可以设计一个登录程序,并在登录之后获取cookies中的skey值,并计算出g_tk。下面设计个登录界面:



以下是源码,请移步到原帖地址(带源码下载):
http://www.codeages.com/forum.php?mod=viewthread&tid=43004&extra=page%3D1