From 0863b886ab7250c129b5ceeabd3f4779f9749a5d Mon Sep 17 00:00:00 2001
From: choogoo <104893934+choogoo@users.noreply.github.com>
Date: Tue, 11 Jul 2023 13:51:58 +0800
Subject: [PATCH 1/6] 3.9.2.23 init (#180)
* 3.9.2.23 initt
* Update init-agent-script.js
* 3.9.2.23 adapter
---
src/agents/agent-script-3.6.0.18.js | 472 ++--
.../agent-script-3.9.2.23-laozhang-raw.js | 801 +++++++
src/agents/agent-script-3.9.2.23-new.js | 1964 +++++++++++++++++
src/init-agent-script.js | 1631 +++++++-------
src/wechat-sidecar.ts | 16 +-
5 files changed, 3791 insertions(+), 1093 deletions(-)
create mode 100644 src/agents/agent-script-3.9.2.23-laozhang-raw.js
create mode 100644 src/agents/agent-script-3.9.2.23-new.js
diff --git a/src/agents/agent-script-3.6.0.18.js b/src/agents/agent-script-3.6.0.18.js
index b0dc6b1..6ae2c78 100644
--- a/src/agents/agent-script-3.6.0.18.js
+++ b/src/agents/agent-script-3.6.0.18.js
@@ -17,8 +17,8 @@
const offset = {
/**---nick call */
- chatroom_member_nick_call_offset_v6:0x3E47B0,//3.6.0.18
- chatroom_member_nick_esi_offset_v6:0x22553D4,
+ chatroom_member_nick_call_offset_v6: 0x3E47B0,//3.6.0.18
+ chatroom_member_nick_esi_offset_v6: 0x22553D4,
/**-- nick call */
node_offset: 0x222f3bc,//0x1db9728 -- 3.3.0.155
handle_offset: 0x4c,
@@ -38,13 +38,13 @@ const offset = {
get_qr_login_data_offset: 0x282160,
get_qr_login_call_offset: 0x286930,
//-------3.6.0.18 send pic
- send_picmsg_call_offset0:0x9A1C0,//assign value to ecx
+ send_picmsg_call_offset0: 0x9A1C0,//assign value to ecx
send_picmsg_call_offset1: 0x4BE160,//0x5ccb50,
- send_picmsg_call_ecx:0x222F0F0,
+ send_picmsg_call_ecx: 0x222F0F0,
//-------3.6.0.18 send pic
/*send_picmsg_call_offset2: 0x6f5c0,
send_picmsg_call_offset3: 0x3e3490,*/
- send_attatch_ecx_offset:0x1D8FA8C,
+ send_attatch_ecx_offset: 0x1D8FA8C,
send_attatch_call_offset0: 0x9A1C0,
send_attatch_call_offset1: 0x701DC0,//0x701CD0,//701CD0
send_attatch_call_offset2: 0x4BA5F0,//4B A5F0
@@ -63,13 +63,13 @@ const offset = {
/*------------------global-------------------------------------------*/
-const availableVersion = 1661337618////3.3.0.115 ==1661141107
+const availableVersion = 1661337618////3.3.0.115 ==1661141107
const moduleBaseAddress = Module.getBaseAddress('WeChatWin.dll')
const moduleLoad = Module.load('WeChatWin.dll')
//1575CF98
-const g_EDIPtr = moduleBaseAddress.add(0x222f38c).readPointer().add(0xD70).readPointer()//
-const g_EDIU32 = moduleBaseAddress.add(0x222f38c).readPointer().add(0xD70).readU32()
+const g_EDIPtr = moduleBaseAddress.add(0x222f38c).readPointer().add(0xD70).readPointer()//
+const g_EDIU32 = moduleBaseAddress.add(0x222f38c).readPointer().add(0xD70).readU32()
let currentVersion = 0
let nodeList = [] //for contact
@@ -88,46 +88,46 @@ let loggedIn = false
let g_initTestAsm = null
let g_BufferEbp2C = null
-let g_initECXU32 = null
-let g_initECXPtr = null
-let g_initEBXPtr = null
-let g_initEBX = null
+let g_initECXU32 = null
+let g_initECXPtr = null
+let g_initEBXPtr = null
+let g_initEBX = null
let g_attatchEBP210Buffer = null
-let g_attatchPathPtr = null
-let g_attatchPath = null
-let g_attatchEBPAc = null
-let g_attatchEBPAcBufPtr = null
+let g_attatchPathPtr = null
+let g_attatchPath = null
+let g_attatchEBPAc = null
+let g_attatchEBPAcBufPtr = null
-let g_attatchContactIdPtr = null
+let g_attatchContactIdPtr = null
//let g_attatchECXBuffer = null
-let g_attatchESIU32 = null
+let g_attatchESIU32 = null
-let g_initECXTempPtr = null
-const initGlobal = ( (contactId,attatchFile)=> {
+let g_initECXTempPtr = null
+const initGlobal = ((contactId, attatchFile) => {
//const base = moduleBaseAddress.add(0x222f38c).readPointer()
//g_EDI = base.add(0xD70).readPointer()//0x438+0x938
- console.log('------------g_attatchEBPAc',g_attatchEBPAc)
- console.log('------------g_EDIU32',g_EDIU32)
+ console.log('------------g_attatchEBPAc', g_attatchEBPAc)
+ console.log('------------g_EDIU32', g_EDIU32)
g_initTestAsm = Memory.alloc(Process.pageSize)
- console.log('------------address',g_initTestAsm)
-
+ console.log('------------address', g_initTestAsm)
+
g_initECXPtr = g_EDIPtr.add(0xB80).readPointer().add(0x1640)
g_initECXTempPtr = g_EDIPtr.add(0xB88).readPointer()
g_initECXU32 = g_initECXPtr.toInt32()
- g_attatchESIU32 = g_EDIU32
+ g_attatchESIU32 = g_EDIU32
+
+ console.log('------------g_initECXU32', g_initECXU32)
+ console.log('------------g_initESIU32', g_attatchESIU32)
- console.log('------------g_initECXU32',g_initECXU32)
- console.log('------------g_initESIU32',g_attatchESIU32)
-
//console.log('==========g_initECXPtr',g_initECXPtr)
//console.log('==========g_EDIU32',g_EDIU32)
-
+
//g_attatchECXBuffer = Memory.alloc(0x1024)
//Memory.copy(g_attatchECXBuffer, g_initECXPtr, 0x1024)
-
+
g_BufferEbp2C = Memory.alloc(0x48)
//g_initEBX = moduleBaseAddress.add(0x2251724).readPointer().readPointer()
@@ -150,7 +150,7 @@ const initGlobal = ( (contactId,attatchFile)=> {
g_attatchEBP210Buffer.add(0x2C).writeU32(moduleBaseAddress.add(0x2ECE87).toInt32())
//console.log('------------g_attatchEBP210Buffer',g_attatchEBP210Buffer)
/*---------------------------------ebp-210----------------*/
-
+
//g_attatchContactIdPtr = Memory.alloc(0x4)
//g_attatchContactIdPtr.writeUtf16String(contactId)
//console.log('------------g_attatchEBP210Buffer',g_attatchEBP210Buffer)
@@ -160,17 +160,17 @@ const initGlobal = ( (contactId,attatchFile)=> {
//g_attatchEBPAc.add(0x4).writePointer(g_attatchEBPAcBufPtr)
//g_attatchEBPAc.add(0x8).writePointer(g_attatchEBPAcBufPtr)
g_attatchEBPAc.add(0x10).writeU32(g_EDIU32)
- console.log('------------g_attatchEBPAc',g_attatchEBPAc)
-
+ console.log('------------g_attatchEBPAc', g_attatchEBPAc)
+
/*g_attatchECXBuffer.add(0x18).writePointer(g_attatchContactIdPtr)
g_attatchECXBuffer.add(0x1C).writeU32(contactId.length*2)
.add(0x04).writeU32(contactId.length*2)*/
-
+
//g_attatchESIU32 = g_EDI.toInt32()
-
+
//console.log('------------g_attatchESIU32',g_attatchESIU32)
//console.log('==========g_attatchECXBuffer',g_attatchECXBuffer)
@@ -188,7 +188,7 @@ const initGlobal = ( (contactId,attatchFile)=> {
cw.putCallAddress(moduleBaseAddress.add(0x131bb0))*/
//cw.putMovRegOffsetPtrU32('ebp', -20, 0)
-
+
/*cw.putPushU32(0)
cw.putMovRegAddress('eax', g_attatchPathPtr)
cw.putPushReg('eax')
@@ -241,24 +241,24 @@ const initGlobal = ( (contactId,attatchFile)=> {
})
-let g_personal_detail_ebx =null
-let g_personal_detail_asm =null
+let g_personal_detail_ebx = null
+let g_personal_detail_asm = null
let g_personal_wxid = null
let g_personal_wxid_ptr = null
-const getOldTest = ( (wxid) => {//personal detail
+const getOldTest = ((wxid) => {//personal detail
g_personal_detail_asm = Memory.alloc(Process.pageSize)
g_personal_detail_ebx = moduleBaseAddress.add(0x222F38C).readPointer().add(0xFB8).toInt32()
-
- g_personal_wxid_ptr=Memory.alloc(wxid.length * 2 + 2)
+
+ g_personal_wxid_ptr = Memory.alloc(wxid.length * 2 + 2)
g_personal_wxid_ptr.writeUtf16String(wxid)
- g_personal_wxid=Memory.alloc(0x14)
+ g_personal_wxid = Memory.alloc(0x14)
g_personal_wxid.writePointer(ptr(g_personal_wxid_ptr)).add(0x04)
- .writeU32(wxid.length*2).add(0x04)
- .writeU32(wxid.length*2).add(0x08)
+ .writeU32(wxid.length * 2).add(0x04)
+ .writeU32(wxid.length * 2).add(0x08)
- console.log('-----------address----------',g_personal_detail_asm)
+ console.log('-----------address----------', g_personal_detail_asm)
Memory.patchCode(g_personal_detail_asm, Process.pageSize, code => {
var cw = new X86Writer(code, { pc: g_personal_detail_asm })
@@ -269,14 +269,14 @@ const getOldTest = ( (wxid) => {//personal detail
//78BA9ACE | E8 2D05D6FF | call wechatwin.7890A000 |
cw.putMovRegU32('ebx', g_personal_detail_ebx)
- cw.putMovRegReg('esi','eax')
+ cw.putMovRegReg('esi', 'eax')
cw.putPushReg('ebx')
- cw.putSubRegImm('esp',0x14)
+ cw.putSubRegImm('esp', 0x14)
cw.putMovRegAddress('eax', g_personal_wxid)
- cw.putMovRegReg('ecx','esp')
+ cw.putMovRegReg('ecx', 'esp')
cw.putPushReg('eax')
cw.putCallAddress(moduleBaseAddress.add(0x701DC0))
- cw.putMovRegReg('ecx','esi')
+ cw.putMovRegReg('ecx', 'esi')
cw.putCallAddress(moduleBaseAddress.add(0x4024A0))
cw.putPopax()
@@ -313,33 +313,33 @@ const getOldTest = ( (wxid) => {//personal detail
* test call
*/
let attatchTestAsm = null
-let attatchTestEbp2C = null
-let attatchGlobalEDI = null
-let attatchGlobalEDIB88 = null
+let attatchTestEbp2C = null
+let attatchGlobalEDI = null
+let attatchGlobalEDIB88 = null
let attatchTestEBX = null
let g_tempEcx = null
let attatchFirstECX = null
//let attatchFirstECX = null
-let gattatchFilePtr=null
+let gattatchFilePtr = null
let gattatchFile = null
-let gattatchReceiveIdPtr=null
-let gattatchReceiveId=null
-let attatchEAX3B0Buf=null
+let gattatchReceiveIdPtr = null
+let gattatchReceiveId = null
+let attatchEAX3B0Buf = null
-let attatchESIbuf = null
-const getWxTest = ( (contactId,filePath)=>{
+let attatchESIbuf = null
+const getWxTest = ((contactId, filePath) => {
//const nativeativeFunction = new NativeFunction(ptr(addr), 'void', [])
//nativeativeFunction()
attatchTestAsm = Memory.alloc(Process.pageSize)
- console.log('----------------address',attatchTestAsm)
+ console.log('----------------address', attatchTestAsm)
attatchTestEbp2C = Memory.alloc(0xC)
attatchGlobalEDI = moduleBaseAddress.add(0x222f38c).readPointer()
- .add(0x938).add(0x438).readPointer()
+ .add(0x938).add(0x438).readPointer()
attatchGlobalEDIB88 = attatchGlobalEDI.add(0xB88).readPointer()
- attatchTestEBX = Memory.alloc(0x4)
+ attatchTestEBX = Memory.alloc(0x4)
attatchTestEBX.writePointer(attatchGlobalEDI)
- console.log('----------------attatchGlobalEDI',attatchGlobalEDI)
- console.log('----------------attatchGlobalEDIB88',attatchGlobalEDIB88)
+ console.log('----------------attatchGlobalEDI', attatchGlobalEDI)
+ console.log('----------------attatchGlobalEDIB88', attatchGlobalEDIB88)
attatchFirstECX = Memory.alloc(0x28)
//const attatchSecondEcx = Memory.alloc(0x14)
@@ -348,13 +348,13 @@ const getWxTest = ( (contactId,filePath)=>{
const contractIdActLength = contactId.length
- gattatchReceiveIdPtr=Memory.alloc(contactId.length * 2 + 2)
+ gattatchReceiveIdPtr = Memory.alloc(contactId.length * 2 + 2)
gattatchReceiveIdPtr.writeUtf16String(contactId)
- gattatchReceiveId=Memory.alloc(0x14)
+ gattatchReceiveId = Memory.alloc(0x14)
gattatchReceiveId.writePointer(ptr(gattatchReceiveIdPtr)).add(0x04)
- .writeU32(contactId.length*2).add(0x04)
- .writeU32(contactId.length*2).add(0x08)
+ .writeU32(contactId.length * 2).add(0x04)
+ .writeU32(contactId.length * 2).add(0x08)
//console.log('----------------attatchGlobalEDIB88',attatchGlobalEDIB88)
//return
/*console.log(hexdump(attatchTestEBX, {
@@ -365,56 +365,56 @@ const getWxTest = ( (contactId,filePath)=>{
}))
return*/
- gattatchFilePtr=Memory.alloc(filePath.length * 2 + 2)
+ gattatchFilePtr = Memory.alloc(filePath.length * 2 + 2)
gattatchFilePtr.writeUtf16String(filePath)
- gattatchFile=Memory.alloc(0x14)
+ gattatchFile = Memory.alloc(0x14)
gattatchFile.writePointer(ptr(gattatchFilePtr)).add(0x04)
- .writeU32(filePath.length*2).add(0x04)
- .writeU32(filePath.length*2).add(0x08)
+ .writeU32(filePath.length * 2).add(0x04)
+ .writeU32(filePath.length * 2).add(0x08)
const attatchLastECX = moduleBaseAddress.add(0x222f170).toInt32()
- attatchEAX3B0Buf = Memory.alloc(0x3B0)
+ attatchEAX3B0Buf = Memory.alloc(0x3B0)
- g_tempEcx = Memory.alloc(0x4)
+ g_tempEcx = Memory.alloc(0x4)
//g_tempEcx1 = Memory.alloc(0x4)
attatchESIbuf = Memory.alloc(0x100)
attatchESIbuf.add(0x0).writeU32(3)
attatchESIbuf.add(0x4).writePointer(gattatchFilePtr)
- attatchESIbuf.add(0x8).writeU32(filePath.length*2)
- attatchESIbuf.add(0xc).writeU32(filePath.length*2)
-
+ attatchESIbuf.add(0x8).writeU32(filePath.length * 2)
+ attatchESIbuf.add(0xc).writeU32(filePath.length * 2)
+
Memory.patchCode(attatchTestAsm, Process.pageSize, code => {
var cw = new X86Writer(code, { pc: attatchTestAsm })
cw.putPushfx()
cw.putPushax()
//cw.putMovRegU32('edi',attatchGlobalEDI)
-
- cw.putMovRegAddress('esi',attatchESIbuf)
-
+
+ cw.putMovRegAddress('esi', attatchESIbuf)
+
cw.putMovRegAddress('ecx', attatchFirstECX.add(0x14))
cw.putMovRegAddress('eax', gattatchFile)
cw.putPushReg('eax')
cw.putCallAddress(moduleBaseAddress.add(0x701DC0))
-
+
cw.putMovRegAddress('ecx', attatchFirstECX)
cw.putMovRegU32('eax', contactIdLength)
cw.putPushReg('eax')
cw.putPushU32(0)
cw.putCallAddress(moduleBaseAddress.add(0x1a11c83))
cw.putAddRegImm('esp', 0x8)
-
- cw.putMovRegReg('edx','eax')
- cw.putMovNearPtrReg(attatchFirstECX,'edx')
+
+ cw.putMovRegReg('edx', 'eax')
+ cw.putMovNearPtrReg(attatchFirstECX, 'edx')
cw.putMovRegU32('edi', contactIdLength)
cw.putPushReg('edi')
cw.putMovRegAddress('eax', gattatchReceiveIdPtr)//ebp-58
cw.putPushReg('eax')
- cw.putMovRegNearPtr('eax',attatchFirstECX)
+ cw.putMovRegNearPtr('eax', attatchFirstECX)
cw.putPushReg('eax')
cw.putCallAddress(moduleBaseAddress.add(0x1a1047a))
cw.putAddRegImm('esp', 0x0c)
@@ -424,7 +424,7 @@ const getWxTest = ( (contactId,filePath)=>{
//cw.putMovRegU32('edx', 0)
//cw.putMovRegRegPtr('eax', 'ecx')
//cw.putMovNearPtrReg(attatchFirstECX.add(0x04),'edi')
- cw.putMovRegU32('edi',contactId.length * 2)
+ cw.putMovRegU32('edi', contactId.length * 2)
cw.putMovRegU32('ecx', attatchLastECX)
cw.putMovRegAddress('eax', attatchEAX3B0Buf)
cw.putPushReg('eax')
@@ -451,8 +451,8 @@ const getTestInfoFunction = ((addr) => {
nativeativeFunction()
//00CFE484
-
-
+
+
/*MemoryAccessMonitor.enable({base:ptr(addr),size:0x01}, {
onAccess(details){
console.log('============')
@@ -492,7 +492,7 @@ const getHeaderNodeAddress = (() => {
// 005
const getChatroomNodeAddress = (() => {
- const baseAddress= moduleBaseAddress.add(0x222f3fc).readPointer()
+ const baseAddress = moduleBaseAddress.add(0x222f3fc).readPointer()
if (baseAddress.isNull()) {
return baseAddress
}
@@ -530,7 +530,7 @@ const getMyselfInfoFunction = (() => {
const getMyselfIdFunction = (() => {
let wx_id = readString(moduleBaseAddress.add(offset.wxid_offset))
-
+
return wx_id
})
@@ -668,9 +668,9 @@ const recurseNew = ((node) => {
//const gender = node.add(0x18C).readU32()
const contactJson = {
- id1:id,
+ id1: id,
id: wxid,
- name:name,
+ name: name,
/*code: wx_code,
name: name,
alias: alias,
@@ -812,7 +812,7 @@ if (!isSupported) {
const getContactNativeFunction = (() => {
const headerNodeAddress = getHeaderNodeAddress()
//console.log('headerNodeAddress',headerNodeAddress)
-
+
if (headerNodeAddress.isNull()) { return '[]' }
const node = headerNodeAddress.add(0x0).readPointer()
@@ -820,7 +820,7 @@ const getContactNativeFunction = (() => {
//console.log(ret)
- console.log('getContactNativeFunction:',ret.length)
+ // console.log('getContactNativeFunction:',ret.length)
/*for (let item of ret){
console.log(JSON.stringify(item))
}*/
@@ -998,7 +998,7 @@ const getQrcodeLoginData = () => {
// 019
const recvMsgNativeCallback = (() => {
-
+
const nativeCallback = new NativeCallback(() => { }, 'void', ['int32', 'pointer', 'pointer', 'pointer', 'pointer', 'int32'])
const nativeativeFunction = new NativeFunction(nativeCallback, 'void', ['int32', 'pointer', 'pointer', 'pointer', 'pointer', 'int32'])
@@ -1006,79 +1006,85 @@ const recvMsgNativeCallback = (() => {
moduleBaseAddress.add(offset.hook_point),
{
onEnter() {
- const addr = this.context.eax//0xc30-0x08
- const msgType = addr.add(0x38).readU32()
- const isMyMsg = addr.add(0x3C).readU32()//add isMyMsg
-
- if (msgType > 0) {
-
- const talkerIdPtr = addr.add(0x48).readPointer()
- //console.log('txt msg',talkerIdPtr.readUtf16String())
- const talkerIdLen = addr.add(0x48 + 0x04).readU32() * 2 + 2
-
- const myTalkerIdPtr = Memory.alloc(talkerIdLen)
- Memory.copy(myTalkerIdPtr, talkerIdPtr, talkerIdLen)
-
-
- let contentPtr = null
- let contentLen = 0
- let myContentPtr = null
- if (msgType == 3) {// pic path
- let thumbPtr = addr.add(0x198).readPointer();
- let hdPtr = addr.add(0x1ac).readPointer();
- let thumbPath = thumbPtr.readUtf16String();
- let hdPath = hdPtr.readUtf16String();
- let picData = [
- thumbPath,// PUPPET.types.Image.Unknown
- thumbPath,// PUPPET.types.Image.Thumbnail
- hdPath,// PUPPET.types.Image.HD
- hdPath// PUPPET.types.Image.Artwork
- ]
- let content = JSON.stringify(picData);
- myContentPtr = Memory.allocUtf16String(content);
- } else {
- contentPtr = addr.add(0x70).readPointer()
- contentLen = addr.add(0x70 + 0x04).readU32() * 2 + 2
- myContentPtr = Memory.alloc(contentLen)
- Memory.copy(myContentPtr, contentPtr, contentLen)
- }
-
- // console.log('----------------------------------------')
- // console.log(msgType)
- // console.log(contentPtr.readUtf16String())
- // console.log('----------------------------------------')
- const groupMsgAddr = addr.add(0x170).readU32() //* 2 + 2
- let myGroupMsgSenderIdPtr = null
- if (groupMsgAddr == 0) {//weChatPublic is zero,type is 49
-
- myGroupMsgSenderIdPtr = Memory.alloc(0x10)
- myGroupMsgSenderIdPtr.writeUtf16String("null")
-
- } else {
-
- const groupMsgSenderIdPtr = addr.add(0x170).readPointer()
- const groupMsgSenderIdLen = addr.add(0x170 + 0x04).readU32() * 2 + 2
- myGroupMsgSenderIdPtr = Memory.alloc(groupMsgSenderIdLen)
- Memory.copy(myGroupMsgSenderIdPtr, groupMsgSenderIdPtr, groupMsgSenderIdLen)
-
- }
-
- const xmlNullPtr = addr.add(0x1ec).readU32()
- let myXmlContentPtr = null
- if (xmlNullPtr == 0) {
-
- myXmlContentPtr = Memory.alloc(0x10)
- myXmlContentPtr.writeUtf16String("null")
-
- } else {
- const xmlContentPtr = addr.add(0x1ec).readPointer()
-
- const xmlContentLen = addr.add(0x1ec + 0x04).readU32() * 2 + 2
- myXmlContentPtr = Memory.alloc(xmlContentLen)
- Memory.copy(myXmlContentPtr, xmlContentPtr, xmlContentLen)
+ let addr
+ let msgType = 0
+ let isMyMsg = 0
+ let curTime = new Date()
+ try {
+ addr = this.context.eax//0xc30-0x08
+ msgType = addr.add(0x38).readU32()
+ isMyMsg = addr.add(0x3C).readU32()//add isMyMsg
+ if (msgType > 0) {
+ const talkerIdPtr = addr.add(0x48).readPointer()
+ //console.log('txt msg',talkerIdPtr.readUtf16String())
+ const talkerIdLen = addr.add(0x48 + 0x04).readU32() * 2 + 2
+
+ const myTalkerIdPtr = Memory.alloc(talkerIdLen)
+ Memory.copy(myTalkerIdPtr, talkerIdPtr, talkerIdLen)
+
+
+ let contentPtr = null
+ let contentLen = 0
+ let myContentPtr = null
+ if (msgType == 3) {// pic path
+ let thumbPtr = addr.add(0x198).readPointer();
+ let hdPtr = addr.add(0x1ac).readPointer();
+ let thumbPath = thumbPtr.readUtf16String();
+ let hdPath = hdPtr.readUtf16String();
+ let picData = [
+ thumbPath,// PUPPET.types.Image.Unknown
+ thumbPath,// PUPPET.types.Image.Thumbnail
+ hdPath,// PUPPET.types.Image.HD
+ hdPath// PUPPET.types.Image.Artwork
+ ]
+ let content = JSON.stringify(picData);
+ myContentPtr = Memory.allocUtf16String(content);
+ } else {
+ contentPtr = addr.add(0x70).readPointer()
+ contentLen = addr.add(0x70 + 0x04).readU32() * 2 + 2
+ myContentPtr = Memory.alloc(contentLen)
+ Memory.copy(myContentPtr, contentPtr, contentLen)
+ }
+
+ // console.log('----------------------------------------')
+ // console.log(msgType)
+ // console.log(contentPtr.readUtf16String())
+ // console.log('----------------------------------------')
+ const groupMsgAddr = addr.add(0x170).readU32() //* 2 + 2
+ let myGroupMsgSenderIdPtr = null
+ if (groupMsgAddr == 0) {//weChatPublic is zero,type is 49
+
+ myGroupMsgSenderIdPtr = Memory.alloc(0x10)
+ myGroupMsgSenderIdPtr.writeUtf16String("null")
+
+ } else {
+
+ const groupMsgSenderIdPtr = addr.add(0x170).readPointer()
+ const groupMsgSenderIdLen = addr.add(0x170 + 0x04).readU32() * 2 + 2
+ myGroupMsgSenderIdPtr = Memory.alloc(groupMsgSenderIdLen)
+ Memory.copy(myGroupMsgSenderIdPtr, groupMsgSenderIdPtr, groupMsgSenderIdLen)
+
+ }
+
+ const xmlNullPtr = addr.add(0x1ec).readU32()
+ let myXmlContentPtr = null
+ if (xmlNullPtr == 0) {
+
+ myXmlContentPtr = Memory.alloc(0x10)
+ myXmlContentPtr.writeUtf16String("null")
+
+ } else {
+ const xmlContentPtr = addr.add(0x1ec).readPointer()
+
+ const xmlContentLen = addr.add(0x1ec + 0x04).readU32() * 2 + 2
+ myXmlContentPtr = Memory.alloc(xmlContentLen)
+ Memory.copy(myXmlContentPtr, xmlContentPtr, xmlContentLen)
+ }
+
+ setImmediate(() => nativeativeFunction(msgType, myTalkerIdPtr, myContentPtr, myGroupMsgSenderIdPtr, myXmlContentPtr, isMyMsg))
}
-
- setImmediate(() => nativeativeFunction(msgType, myTalkerIdPtr, myContentPtr, myGroupMsgSenderIdPtr, myXmlContentPtr, isMyMsg))
+ } catch (err) {
+ console.error(curTime,'recvMsgNativeCallback at onEnter err:', err)
}
}
})
@@ -1182,17 +1188,17 @@ let nickMemberIdStructV6 = null
let memberNickBuffAsmV6 = null
let nickResultEdiV6 = null
-const getChatroomMemberNickInfoV1Function=((memberId, roomId)=>{
+const getChatroomMemberNickInfoV1Function = ((memberId, roomId) => {
nickRoomIdV6 = initidStruct(roomId)
nullEdiWxidStructV6 = initNullIdStruct('')
nickMemberIdStructV6 = initStruct(memberId)
memberNickBuffAsmV6 = Memory.alloc(Process.pageSize)
- console.log('-----',memberNickBuffAsmV6)
+ console.log('-----', memberNickBuffAsmV6)
const tmp = (moduleBaseAddress.add(
offset.chatroom_member_nick_esi_offset_v6
)).readU32()
- console.log('=======tmp',tmp)
+ console.log('=======tmp', tmp)
Memory.patchCode(memberNickBuffAsmV6, Process.pageSize, code => {
var cw = new X86Writer(code, { pc: memberNickBuffAsmV6 })
cw.putPushfx();
@@ -1202,19 +1208,19 @@ const getChatroomMemberNickInfoV1Function=((memberId, roomId)=>{
cw.putMovRegAddress('eax', nickMemberIdStructV6)
cw.putMovRegAddress('ebx', nickRoomIdV6)
-
+
cw.putMovRegAddress('esi', ptr(tmp))
cw.putPushReg('edi')
cw.putPushReg('eax')
cw.putPushReg('ebx')
-
+
cw.putMovRegAddress('ecx', ptr(tmp))
cw.putCallAddress(moduleBaseAddress.add(
offset.chatroom_member_nick_call_offset_v6
))
-
+
//cw.putMovNearPtrReg(nickResultEdiV6, 'edi')
cw.putPopax()
cw.putPopfx()
@@ -1226,7 +1232,7 @@ const getChatroomMemberNickInfoV1Function=((memberId, roomId)=>{
const nativeativeFunction = new NativeFunction(ptr(memberNickBuffAsmV6), 'void', [])
nativeativeFunction()
- console.log('---------nullEdiWxidStructV6',nullEdiWxidStructV6)
+ console.log('---------nullEdiWxidStructV6', nullEdiWxidStructV6)
const nickha = readWideString(nullEdiWxidStructV6)
console.log('-----------------')
@@ -1297,7 +1303,7 @@ const getChatroomMemberNickInfoFunction = ((memberId, roomId) => {
cw.putAddRegImm('esp', 0x04)
//cw.putMovNearPtrReg(nickRetAddr, 'ebx')
//lea eax, buf
-
+
cw.putPopax()
cw.putPopfx()
cw.putRet()
@@ -1324,7 +1330,7 @@ let attatchPathPtr = null
let attatchAsm = null
let attatchBuf = null
-let attatchReceiveIdPtr=null
+let attatchReceiveIdPtr = null
let attatchReceiveId = null
let attatchSendId = null
@@ -1340,15 +1346,15 @@ let attatchEbp210 = null
let attatchEbpAc = null*/
let attatchEbp11E8 = null
-let attatchEbpCC = null
-let attatchEbp368 = null
-let attatchEAX = null
+let attatchEbpCC = null
+let attatchEbp368 = null
+let attatchEAX = null
let sFileName = null
let fileNamePtr = null
let attatchEbp84 = null
-let attatchECX = null
+let attatchECX = null
/**
@@ -1358,37 +1364,37 @@ param {78EDBC86 | 8B80 38040000 | mov eax,dword ptr ds:[eax+438]
*/
// 021
-const sendAttatchMsgNativeFunction = ((contactId, senderId,path,filename,size) => {
+const sendAttatchMsgNativeFunction = ((contactId, senderId, path, filename, size) => {
attatchAsm = Memory.alloc(Process.pageSize)
- console.log('--------------address',attatchAsm)
+ console.log('--------------address', attatchAsm)
- fileNamePtr=Memory.alloc(filename.length * 2 + 2)
+ fileNamePtr = Memory.alloc(filename.length * 2 + 2)
fileNamePtr.writeUtf16String(filename)
- sFileName=Memory.alloc(0x14)
+ sFileName = Memory.alloc(0x14)
sFileName.writePointer(ptr(fileNamePtr)).add(0x04)
- .writeU32(fileNamePtr.length*2).add(0x04)
- .writeU32(fileNamePtr.length*2).add(0x08)
+ .writeU32(fileNamePtr.length * 2).add(0x04)
+ .writeU32(fileNamePtr.length * 2).add(0x08)
//const fileSize = size.toInt32()
- attatchReceiveIdPtr=Memory.alloc(contactId.length * 2 + 2)
+ attatchReceiveIdPtr = Memory.alloc(contactId.length * 2 + 2)
attatchReceiveIdPtr.writeUtf16String(contactId)
- attatchReceiveId=Memory.alloc(0x14)
+ attatchReceiveId = Memory.alloc(0x14)
attatchReceiveId.writePointer(ptr(attatchReceiveIdPtr)).add(0x04)
- .writeU32(contactId.length*2).add(0x04)
- .writeU32(contactId.length*2).add(0x08)
+ .writeU32(contactId.length * 2).add(0x04)
+ .writeU32(contactId.length * 2).add(0x08)
- attatchSendIdPtr=Memory.alloc(senderId.length * 2 + 2)
+ attatchSendIdPtr = Memory.alloc(senderId.length * 2 + 2)
attatchSendIdPtr.writeUtf16String(senderId)
- attatchSendId=Memory.alloc(0x14)
+ attatchSendId = Memory.alloc(0x14)
attatchSendId.writePointer(ptr(attatchSendIdPtr)).add(0x04)
- .writeU32(senderId.length*2).add(0x04)
- .writeU32(senderId.length*2).add(0x08)
+ .writeU32(senderId.length * 2).add(0x04)
+ .writeU32(senderId.length * 2).add(0x08)
attatchPathPtr = Memory.alloc(path.length * 2 + 2)
attatchPathPtr.writeUtf16String(path)
@@ -1399,16 +1405,16 @@ const sendAttatchMsgNativeFunction = ((contactId, senderId,path,filename,size) =
.writeU32(path.length * 2).add(0x04)
attatchEbp11E8 = Memory.alloc(0xBE4)
- attatchEbpCC = Memory.alloc(0x14)
+ attatchEbpCC = Memory.alloc(0x14)
attatchEbp368 = Memory.alloc(0x290)
- attatchEbp84 = Memory.alloc(0x18)
- attatchEAX = Memory.alloc(0x18)
+ attatchEbp84 = Memory.alloc(0x18)
+ attatchEAX = Memory.alloc(0x18)
attatchECX = moduleBaseAddress.add(0x222f178).toInt32()
//console.log('basename',path.basename(path))
//return
-
+
/**
* -------------buffer-------------------------------
*/
@@ -1425,23 +1431,23 @@ const sendAttatchMsgNativeFunction = ((contactId, senderId,path,filename,size) =
cw.putPushU32(moduleBaseAddress.add(0x1E1B3C0).toInt32())
cw.putMovRegAddress('ecx', attatchEbp11E8.add(0x4))//11e4
cw.putCallAddress(moduleBaseAddress.add(0x702410))//write appid
- // cw.putCallAddress(moduleBaseAddress.add(0x702410))//write appid
-
- /**
- * 78482B8D | 6A FF | push FFFFFFFF |
- 78482B8F | 68 B895E979 | push wechatwin.79E995B8 | 79E995B8:L"0"
- 78482B94 | 8D8D 48EEFFFF | lea ecx,dword ptr ss:[ebp-11B8] |
- 78482B9A | E8 71F83600 | call wechatwin.787F2410 | 此处继续写ebp-11b8
- */
+ // cw.putCallAddress(moduleBaseAddress.add(0x702410))//write appid
+
+ /**
+ * 78482B8D | 6A FF | push FFFFFFFF |
+ 78482B8F | 68 B895E979 | push wechatwin.79E995B8 | 79E995B8:L"0"
+ 78482B94 | 8D8D 48EEFFFF | lea ecx,dword ptr ss:[ebp-11B8] |
+ 78482B9A | E8 71F83600 | call wechatwin.787F2410 | 此处继续写ebp-11b8
+ */
cw.putPushU32(-1)
cw.putPushU32(moduleBaseAddress.add(0x1DA95B8).toInt32())
cw.putMovRegAddress('ecx', attatchEbp11E8.add(0x30))//11B8
cw.putCallAddress(moduleBaseAddress.add(0x702410))
- cw.putMovRegU32('eax',0x6)
- cw.putMovNearPtrReg(attatchEbp11E8.add(0x80), 'eax')//1168
- cw.putMovRegU32('eax',size)//file size
- cw.putMovNearPtrReg(attatchEbp11E8.add(0x108), 'eax')//10e0
+ cw.putMovRegU32('eax', 0x6)
+ cw.putMovNearPtrReg(attatchEbp11E8.add(0x80), 'eax')//1168
+ cw.putMovRegU32('eax', size)//file size
+ cw.putMovNearPtrReg(attatchEbp11E8.add(0x108), 'eax')//10e0
cw.putMovRegAddress('eax', sFileName)
@@ -1453,8 +1459,8 @@ const sendAttatchMsgNativeFunction = ((contactId, senderId,path,filename,size) =
cw.putPushReg('eax')
cw.putMovRegAddress('ecx', attatchEbp11E8.add(0x160))//1088=0x11e8-0x160
cw.putCallAddress(moduleBaseAddress.add(0x702980))
-
-
+
+
cw.putMovRegAddress('eax', attatchEbpCC)
cw.putPushReg('eax')
cw.putMovRegAddress('ecx', attatchEbp11E8)
@@ -1475,10 +1481,10 @@ const sendAttatchMsgNativeFunction = ((contactId, senderId,path,filename,size) =
cw.putPushReg('ecx')
cw.putPushReg('eax')
- cw.putMovRegAddress('eax',attatchEbpCC)
+ cw.putMovRegAddress('eax', attatchEbpCC)
cw.putPushReg('eax')
- cw.putMovRegAddress('eax',attatchReceiveId)
+ cw.putMovRegAddress('eax', attatchReceiveId)
cw.putPushReg('eax')
cw.putMovRegAddress('ecx', attatchEbp368)
@@ -1503,7 +1509,7 @@ const sendAttatchMsgNativeFunction = ((contactId, senderId,path,filename,size) =
//cw.putMovNearPtrReg(attatchEbpCC.add(0x64), 'eax')//ebp-68
//cw.putAddRegImm('ecx', 0x8)
//cw.putMovRegAddress('eax', attatchEbp368.add(0x64))//ebp-68
-
+
//cw.putMovRegU32('ecx',attatchECX)
//cw.putPushReg('eax')
//cw.putMovRegAddress('eax', attatchEbpCC.add(0x40))//ebp-8c
@@ -1518,8 +1524,8 @@ const sendAttatchMsgNativeFunction = ((contactId, senderId,path,filename,size) =
//cw.putMovRegAddress('ecx', attatchEbp368)
//cw.putCallAddress(moduleBaseAddress.add(0x63B4F0))
- // 78F33099 | 8D8D 34FFFFFF | lea ecx,dword ptr ss:[ebp-CC] |
-//78F3309F | E8 AC0FD0FF | call wechatwin.78C34050 |
+ // 78F33099 | 8D8D 34FFFFFF | lea ecx,dword ptr ss:[ebp-CC] |
+ //78F3309F | E8 AC0FD0FF | call wechatwin.78C34050 |
//cw.putMovRegAddress('ecx',attatchEbpCC)
//cw.putCallAddress(moduleBaseAddress.add(0x94050))
@@ -1607,7 +1613,7 @@ const sendPicMsgNativeFunction = ((contactId, path) => {
offset.send_picmsg_call_offset0
))
cw.putMovRegReg('edx', 'eax')//缓存
-
+
cw.putSubRegImm('esp', 0x14)
cw.putMovRegAddress('eax', buffwxid)
cw.putMovRegReg('ecx', 'esp')
@@ -1681,7 +1687,7 @@ const sendPicMsgNativeFunction = ((contactId, path) => {
})
- console.log('----------picAsm',picAsm)
+ console.log('----------picAsm', picAsm)
const nativeativeFunction = new NativeFunction(ptr(picAsm), 'void', [])
nativeativeFunction()
@@ -1950,18 +1956,18 @@ const agentReadyCallback = (() => {
})()
// 027
-const SendMiniProgramNativeFunction = ((bg_path_str,send_wxid_str,recv_wxid_str,xmlstr) => {
+const SendMiniProgramNativeFunction = ((bg_path_str, send_wxid_str, recv_wxid_str, xmlstr) => {
console.log("------------------------------------------------------");
- var asmCode=Memory.alloc(Process.pageSize);
+ var asmCode = Memory.alloc(Process.pageSize);
- var ECX_buf=Memory.alloc(0x300);
- var Buf_EAX=Memory.alloc(0x300);
- var buf_1=Memory.alloc(0x300);
- var ptr_to_buf_1=Memory.alloc(0x4).writePointer(buf_1);
- var buf_2=Memory.alloc(0x300);
+ var ECX_buf = Memory.alloc(0x300);
+ var Buf_EAX = Memory.alloc(0x300);
+ var buf_1 = Memory.alloc(0x300);
+ var ptr_to_buf_1 = Memory.alloc(0x4).writePointer(buf_1);
+ var buf_2 = Memory.alloc(0x300);
-// var bg_path_str="C:/aaaa.jpg";
- var bg_path_Ptr=Memory.alloc(bg_path_str.length * 2 + 1)
+ // var bg_path_str="C:/aaaa.jpg";
+ var bg_path_Ptr = Memory.alloc(bg_path_str.length * 2 + 1)
bg_path_Ptr.writeUtf16String(bg_path_str);
var bg_path_Struct = Memory.alloc(0x14) // returns a NativePointer
bg_path_Struct.writePointer(bg_path_Ptr).add(0x04)
@@ -1970,8 +1976,8 @@ const SendMiniProgramNativeFunction = ((bg_path_str,send_wxid_str,recv_wxid_str,
.writeU32(0).add(0x04)
.writeU32(0);
- // var send_wxid_str="wxid_4zr616ir6fi122";
- var send_wxid_Ptr=Memory.alloc(send_wxid_str.length * 2 + 1)
+ // var send_wxid_str="wxid_4zr616ir6fi122";
+ var send_wxid_Ptr = Memory.alloc(send_wxid_str.length * 2 + 1)
send_wxid_Ptr.writeUtf16String(send_wxid_str);
var send_wxid_Struct = Memory.alloc(0x14) // returns a NativePointer
send_wxid_Struct.writePointer(send_wxid_Ptr).add(0x04)
@@ -1980,8 +1986,8 @@ const SendMiniProgramNativeFunction = ((bg_path_str,send_wxid_str,recv_wxid_str,
.writeU32(0).add(0x04)
.writeU32(0);
- // var recv_wxid_str="filehelper";
- var recv_wxid_Ptr=Memory.alloc(recv_wxid_str.length * 2 + 1)
+ // var recv_wxid_str="filehelper";
+ var recv_wxid_Ptr = Memory.alloc(recv_wxid_str.length * 2 + 1)
recv_wxid_Ptr.writeUtf16String(recv_wxid_str);
var recv_wxid_Struct = Memory.alloc(0x14) // returns a NativePointer
recv_wxid_Struct.writePointer(recv_wxid_Ptr).add(0x04)
@@ -1990,9 +1996,9 @@ const SendMiniProgramNativeFunction = ((bg_path_str,send_wxid_str,recv_wxid_str,
.writeU32(0).add(0x04)
.writeU32(0);
- // vvar pXml=initidStruct('wxid_4zr616ir6fi1220腾讯出行服务|加油代驾公交view330https://mp.weixin.qq.com/mp/waerrpage?appid=wx65cc950f42e8fff1&type=upgrade&upgradetype=3#wechat_redirecthttp://mmbiz.qpic.cn/mmbiz_png/NM1fK7leWGPaFnMAe95jbg4sZAI3fkEZWHq69CIk6zA00SGARbmsGTbgLnZUXFoRwjROelKicbSp9K34MaZBuuA/640?wx_fmt=png&wxfrom=200腾讯出行服务|加油代驾公交0gh_ad64296dc8bd@appwx65cc950f42e8fff11http://mmbiz.qpic.cn/mmbiz_png/NM1fK7leWGPaFnMAe95jbg4sZAI3fkEZWHq69CIk6zA00SGARbmsGTbgLnZUXFoRwjROelKicbSp9K34MaZBuuA/640?wx_fmt=png&wxfrom=20002_wx65cc950f42e8fff1_875237370_1644979747_11Window wechat');
+ // vvar pXml=initidStruct('wxid_4zr616ir6fi1220腾讯出行服务|加油代驾公交view330https://mp.weixin.qq.com/mp/waerrpage?appid=wx65cc950f42e8fff1&type=upgrade&upgradetype=3#wechat_redirecthttp://mmbiz.qpic.cn/mmbiz_png/NM1fK7leWGPaFnMAe95jbg4sZAI3fkEZWHq69CIk6zA00SGARbmsGTbgLnZUXFoRwjROelKicbSp9K34MaZBuuA/640?wx_fmt=png&wxfrom=200腾讯出行服务|加油代驾公交0gh_ad64296dc8bd@appwx65cc950f42e8fff11http://mmbiz.qpic.cn/mmbiz_png/NM1fK7leWGPaFnMAe95jbg4sZAI3fkEZWHq69CIk6zA00SGARbmsGTbgLnZUXFoRwjROelKicbSp9K34MaZBuuA/640?wx_fmt=png&wxfrom=20002_wx65cc950f42e8fff1_875237370_1644979747_11Window wechat');
- var pXml=initidStruct(xmlstr)
+ var pXml = initidStruct(xmlstr)
console.log(send_wxid_Struct);
console.log(recv_wxid_Struct);
diff --git a/src/agents/agent-script-3.9.2.23-laozhang-raw.js b/src/agents/agent-script-3.9.2.23-laozhang-raw.js
new file mode 100644
index 0000000..5d9cddc
--- /dev/null
+++ b/src/agents/agent-script-3.9.2.23-laozhang-raw.js
@@ -0,0 +1,801 @@
+/**
+ * WeChat 3.2.1.121
+ * > Special thanks to: @cixingguangming55555 老张学技术
+ *
+ * Credit: https://github.com/cixingguangming55555/wechat-bot
+ * Source: https://pan.baidu.com/s/1OmX2lxNOYHyGsl_3ByhsoA
+ * 《源码3.2.1.121》提取码: 1rfa
+ * WeChat: https://pan.baidu.com/share/init?surl=IHRM2OMvrLyuCz5MRbigGg
+ * 微信:3.2.1.121 提取码: cscn
+ */
+
+//https://blog.csdn.net/iloveitvm/article/details/109119687 frida学习
+
+//const { isNullishCoalesce } = require("typescript")
+
+//3.9.2.23
+
+const offset = {
+
+
+ hook_point: 0xd19a0b, //3.9.2.23
+
+ myselfinfo: {
+ offset: 0x2FFD484, //老版本微信号偏移,后面的地址,都要在这个偏移上增加
+ //wxid_len:0x10,
+ head_img_url: 0x2D8,
+ head_img_url_len: 0x2E8,
+ wx_nick_name: 0x10C,
+ wxcode_new: 0x64, //新版本微信号
+ //wxcode_len:0x74
+ wxid_len_offset: 0x4D4
+ },
+
+ contactInfo: {
+ nodeOffset: 0x2FFDD7C,
+ nodeRootOffset: 0x64
+ },
+ chatroomInfo: {
+ nodeOffset: 0x2FFDDC8,
+ nodeRootOffset: 0x8c8
+ },
+ sendTxtMsg: {
+ callOffset: 0xCE6C80
+ },
+ sendPicMsg: {
+ call1: 0x768140,
+ call2: 0xf59e40,
+ call3: 0xce6640
+ }
+};
+
+
+
+/*------------------global-------------------------------------------*/
+const availableVersion = 1661534743 ////3.9.2.23 ==0x63090217
+
+const moduleBaseAddress = Module.getBaseAddress('WeChatWin.dll')
+const moduleLoad = Module.load('WeChatWin.dll')
+//1575CF98
+
+
+/*---------------base -------------------------*/
+
+let retidPtr=null
+let retidStruct=null
+const initidStruct = ((str) => {
+
+ retidPtr = Memory.alloc(str.length * 2 + 1)
+ retidPtr.writeUtf16String(str)
+
+ retidStruct = Memory.alloc(0x14) // returns a NativePointer
+
+ retidStruct
+ .writePointer(retidPtr).add(0x04)
+ .writeU32(str.length * 2).add(0x04)
+ .writeU32(str.length * 2).add(0x04)
+ .writeU32(0).add(0x04)
+ .writeU32(0)
+
+ return retidStruct
+})
+
+let retPtr = null
+let retStruct = null
+const initStruct = ((str) => {
+
+ retPtr = Memory.alloc(str.length * 2 + 1)
+ retPtr.writeUtf16String(str)
+
+ retStruct = Memory.alloc(0x14) // returns a NativePointer
+
+ retStruct
+ .writePointer(retPtr).add(0x04)
+ .writeU32(str.length * 2).add(0x04)
+ .writeU32(str.length * 2).add(0x04)
+ .writeU32(0).add(0x04)
+ .writeU32(0)
+
+ return retStruct
+})
+
+let msgstrPtr=null
+let msgStruct=null
+const initmsgStruct = ((str) => {
+ msgstrPtr = Memory.alloc(str.length * 2 + 1)
+ msgstrPtr.writeUtf16String(str)
+
+ msgStruct = Memory.alloc(0x14) // returns a NativePointer
+
+ msgStruct
+ .writePointer(msgstrPtr).add(0x04)
+ .writeU32(str.length * 2).add(0x04)
+ .writeU32(str.length * 2).add(0x04)
+ .writeU32(0).add(0x04)
+ .writeU32(0)
+
+ return msgStruct
+})
+
+let atStruct = null
+const initAtMsgStruct = ((wxidStruct) => {
+
+ atStruct = Memory.alloc(0x10)
+
+ atStruct.writePointer(wxidStruct).add(0x04)
+ .writeU32(wxidStruct.toInt32() + 0x14).add(0x04)//0x14 = sizeof(wxid structure)
+ .writeU32(wxidStruct.toInt32() + 0x14).add(0x04)
+ .writeU32(0)
+ return atStruct
+})
+const readStringPtr = (address) => {
+ const addr = ptr(address)
+ const size = addr.add(16).readU32()
+ const capacity = addr.add(20).readU32()
+ addr.ptr = addr
+ addr.size = size
+ addr.capacity = capacity
+ if (capacity > 15 && !addr.readPointer().isNull()) {
+ addr.ptr = addr.readPointer()
+ }
+ addr.ptr._readCString = addr.ptr.readCString
+ addr.ptr._readAnsiString = addr.ptr.readAnsiString
+ addr.ptr._readUtf8String = addr.ptr.readUtf8String
+ addr.readCString = () => {
+ return addr.size ? addr.ptr._readCString(addr.size) : ''
+ }
+ addr.readAnsiString = () => {
+ return addr.size ? addr.ptr._readAnsiString(addr.size) : ''
+ }
+ addr.readUtf8String = () => {
+ return addr.size ? addr.ptr._readUtf8String(addr.size) : ''
+ }
+
+ // console.log('readStringPtr() address:',address,' -> str ptr:', addr.ptr, 'size:', addr.size, 'capacity:', addr.capacity)
+ // console.log('readStringPtr() str:' , addr.readUtf8String())
+ // console.log('readStringPtr() address:', addr,'dump:', addr.readByteArray(24))
+
+ return addr
+}
+
+// std::wstring
+// const wstr = readWStringPtr(ptr).readUtf16String()
+const readWStringPtr = (address) => {
+ const addr = ptr(address)
+ const size = addr.add(4).readU32()
+ const capacity = addr.add(8).readU32()
+ addr.ptr = addr.readPointer()
+ addr.size = size
+ addr.capacity = capacity
+ addr.ptr._readUtf16String = addr.ptr.readUtf16String
+ addr.readUtf16String = () => {
+ return addr.size ? addr.ptr._readUtf16String(addr.size * 2) : ''
+ }
+
+ // console.log('readWStringPtr() address:',address,' -> ptr:', addr.ptr, 'size:', addr.size, 'capacity:', addr.capacity)
+ // console.log('readWStringPtr() str:' , `"${addr.readUtf16String()}"`,'\n',addr.ptr.readByteArray(addr.size*2+2),'\n')
+ // console.log('readWStringPtr() address:', addr,'dump:', addr.readByteArray(16),'\n')
+
+ return addr
+}
+
+const readString = (address) => {
+ return readStringPtr(address).readUtf8String()
+}
+
+const readWideString = (address) => {
+ return readWStringPtr(address).readUtf16String()
+}
+
+
+/*-----------------base-------------------------*/
+
+let currentVersion = 0
+
+let nodeList = [] //for contact
+let contactList = [] //for contact
+
+let chatroomNodeList = [] //for chatroom
+let chatroomMemberList = [] //for chatroom
+let loggedIn = false
+
+
+
+const getWechatVersionFunction = (() => {
+ if (currentVersion) {
+ return currentVersion
+ }
+ const pattern = '55 8B ?? 83 ?? ?? A1 ?? ?? ?? ?? 83 ?? ?? 85 ?? 7F ?? 8D ?? ?? E8 ?? ?? ?? ?? 84 ?? 74 ?? 8B ?? ?? ?? 85 ?? 75 ?? E8 ?? ?? ?? ?? 0F ?? ?? 0D ?? ?? ?? ?? A3 ?? ?? ?? ?? A3 ?? ?? ?? ?? 8B ?? 5D C3'
+ const results = Memory.scanSync(moduleLoad.base, moduleLoad.size, pattern)
+ if (results.length == 0) {
+ return 0
+ }
+ const addr = results[0].address
+ const ret = addr.add(0x07).readPointer()
+ const ver = ret.add(0x0).readU32()
+ currentVersion = ver
+ return ver
+})
+
+// 011
+const getWechatVersionStringFunction = ((ver = getWechatVersionFunction()) => {
+ if (!ver) {
+ return '0.0.0.0'
+ }
+ const vers = []
+ vers.push((ver >> 24) & 255 - 0x60)
+ vers.push((ver >> 16) & 255)
+ vers.push((ver >> 8) & 255)
+ vers.push(ver & 255)
+ return vers.join('.')
+})
+
+const checkSupportedFunction = (() => {
+ const ver = getWechatVersionFunction()
+ return ver == availableVersion
+})
+
+// 019
+const recvMsgNativeCallback = (() => {
+
+
+ const nativeCallback = new NativeCallback(() => {}, 'void', ['int32', 'pointer', 'pointer', 'pointer', 'pointer', 'int32'])
+ const nativeativeFunction = new NativeFunction(nativeCallback, 'void', ['int32', 'pointer', 'pointer', 'pointer', 'pointer', 'int32'])
+
+ Interceptor.attach(
+ moduleBaseAddress.add(offset.hook_point), {
+ onEnter() {
+ const addr = this.context.ecx //0xc30-0x08
+ const msgType = addr.add(0x38).readU32()
+ const isMyMsg = addr.add(0x3C).readU32() //add isMyMsg
+
+ if (msgType > 0) {
+
+ const talkerIdPtr = addr.add(0x48).readPointer()
+ //console.log('txt msg',talkerIdPtr.readUtf16String())
+ const talkerIdLen = addr.add(0x48 + 0x04).readU32() * 2 + 2
+
+ const myTalkerIdPtr = Memory.alloc(talkerIdLen)
+ Memory.copy(myTalkerIdPtr, talkerIdPtr, talkerIdLen)
+
+
+ let contentPtr = null
+ let contentLen = 0
+ let myContentPtr = null
+ if (msgType == 3) { // pic path
+ let thumbPtr = addr.add(0x198).readPointer();
+ let hdPtr = addr.add(0x1ac).readPointer();
+ let thumbPath = thumbPtr.readUtf16String();
+ let hdPath = hdPtr.readUtf16String();
+ let picData = [
+ thumbPath, // PUPPET.types.Image.Unknown
+ thumbPath, // PUPPET.types.Image.Thumbnail
+ hdPath, // PUPPET.types.Image.HD
+ hdPath // PUPPET.types.Image.Artwork
+ ]
+ let content = JSON.stringify(picData);
+ myContentPtr = Memory.allocUtf16String(content);
+ } else {
+ contentPtr = addr.add(0x70).readPointer()
+ contentLen = addr.add(0x70 + 0x04).readU32() * 2 + 2
+ myContentPtr = Memory.alloc(contentLen)
+ Memory.copy(myContentPtr, contentPtr, contentLen)
+ }
+
+ // console.log('----------------------------------------')
+ // console.log(msgType)
+ // console.log(contentPtr.readUtf16String())
+ // console.log('----------------------------------------')
+ const groupMsgAddr = addr.add(0x170).readU32() //* 2 + 2
+ let myGroupMsgSenderIdPtr = null
+ if (groupMsgAddr == 0) { //weChatPublic is zero,type is 49
+
+ myGroupMsgSenderIdPtr = Memory.alloc(0x10)
+ myGroupMsgSenderIdPtr.writeUtf16String("null")
+
+ } else {
+
+ const groupMsgSenderIdPtr = addr.add(0x170).readPointer()
+ const groupMsgSenderIdLen = addr.add(0x170 + 0x04).readU32() * 2 + 2
+ myGroupMsgSenderIdPtr = Memory.alloc(groupMsgSenderIdLen)
+ Memory.copy(myGroupMsgSenderIdPtr, groupMsgSenderIdPtr, groupMsgSenderIdLen)
+
+ }
+
+ const xmlNullPtr = addr.add(0x1f0).readU32() //3.9.2.23
+ let myXmlContentPtr = null
+ if (xmlNullPtr == 0) {
+
+ myXmlContentPtr = Memory.alloc(0x10)
+ myXmlContentPtr.writeUtf16String("null")
+
+ } else {
+ const xmlContentPtr = addr.add(0x1f0).readPointer() //3.9.2.23
+
+ const xmlContentLen = addr.add(0x1f0 + 0x04).readU32() * 2 + 2
+ myXmlContentPtr = Memory.alloc(xmlContentLen)
+ Memory.copy(myXmlContentPtr, xmlContentPtr, xmlContentLen)
+ }
+
+ setImmediate(() => nativeativeFunction(msgType, myTalkerIdPtr, myContentPtr, myGroupMsgSenderIdPtr, myXmlContentPtr, isMyMsg))
+ }
+ }
+ })
+ return nativeCallback
+})()
+
+
+const getBaseNodeAddress = (() => {
+ return moduleBaseAddress.add(offset.contactInfo.nodeOffset).readPointer()
+})
+
+// 004
+const getHeaderNodeAddress = (() => {
+ const baseAddress = getBaseNodeAddress()
+ //console.log('baseAddress',baseAddress)
+ if (baseAddress.isNull()) {
+ return baseAddress
+ }
+
+ //console.log('HeaderNodeAddress',baseAddress.add(offset.handle_offset).readPointer())
+ return baseAddress.add(offset.contactInfo.nodeRootOffset).readPointer()
+})
+
+const getMyselfInfoFunction = (() => {
+
+ let ptr = 0
+ let wx_code = ''
+ let wx_id = ''
+ let wx_name = ''
+ let head_img_url = ''
+
+ const base = moduleBaseAddress.add(offset.myselfinfo.offset)
+ const wxid_len = base.add(offset.myselfinfo.wxid_len_offset).readU32()
+
+ if (wxid_len === 0x13) { // 新版本微信
+ wx_id = base.readPointer().readAnsiString(wxid_len)
+ wx_code = base.add(offset.myselfinfo.wxcode_new).readAnsiString()
+ } else {
+ wx_id = readString(base)
+ wx_code = wx_id
+ }
+
+
+ wx_name = readString(base.add(offset.myselfinfo.wx_nick_name))
+ const img_addr = base.add(offset.myselfinfo.head_img_url).readPointer()
+ const img_len = base.add(offset.myselfinfo.head_img_url_len).readU32()
+
+ head_img_url = img_addr.readAnsiString(img_len)
+
+ const myself = {
+ id: wx_id,
+ code: wx_code,
+ name: wx_name,
+ head_img_url: head_img_url,
+ };
+
+ return JSON.stringify(myself)
+
+})
+
+
+const recurseNew = ((node) => {
+ const headerNodeAddress = getHeaderNodeAddress()
+ if (headerNodeAddress.isNull()) {
+ return
+ }
+
+ if (node.equals(headerNodeAddress)) {
+ return
+ }
+
+ for (const item in nodeList) {
+ if (node.equals(nodeList[item])) {
+ return
+ }
+ }
+
+
+ nodeList.push(node)
+ const id = readString(node.add(0x8))
+ //wxid, format relates to registration method
+ const wxid = readWideString(node.add(0x30))
+ //console.log('-----------',wxid)
+
+
+ //custom id, if not set return null, and use wxid which should be custom id
+ //const wx_code = readWideString(node.add(0x4c)) || readWideString(node.add(0x38))
+
+ //custom Nickname
+ const name = readWideString(node.add(0x8c))
+
+ //alias aka 'remark' in wechat
+ //const alias = readWideString(node.add(0x80))
+
+ //avatarUrl
+ //const avatar = readWideString(node.add(0x138))
+ //const avatar = Memory.readUtf16String(node.add(0x138).readPointer())
+ //contact gender
+ //const gender = node.add(0x18C).readU32()
+
+ const contactJson = {
+ id1: id,
+ id: wxid,
+ name: name,
+ /*code: wx_code,
+ name: name,
+ alias: alias,
+ avatarUrl: avatar,
+ gender: gender,*/
+ }
+
+ contactList.push(contactJson)
+
+ const leftNode = node.add(0x0).readPointer()
+ const centerNode = node.add(0x04).readPointer()
+ //const rightNode = node.add(0x08).readPointer()
+
+ recurseNew(leftNode)
+ recurseNew(centerNode)
+ //recurse(rightNode)
+
+ const allContactJson = contactList
+ return allContactJson
+
+})
+
+
+const getContactNativeFunction = (() => {
+ const headerNodeAddress = getHeaderNodeAddress()
+ //console.log('headerNodeAddress',headerNodeAddress)
+
+ if (headerNodeAddress.isNull()) {
+ return '[]'
+ }
+
+ const node = headerNodeAddress.add(0x0).readPointer()
+ const ret = recurseNew(node)
+
+ //console.log(ret)
+
+ console.log('getContactNativeFunction:', ret.length)
+ /*for (let item of ret){
+ console.log(JSON.stringify(item))
+ }*/
+ //console.log(ret.contact)
+ const cloneRet = JSON.stringify(ret)
+ nodeList.length = 0
+ contactList.length = 0
+
+ return cloneRet
+})
+
+
+const getChatroomNodeAddress = (() => {
+ const baseAddress = moduleBaseAddress.add(offset.chatroomInfo.nodeOffset).readPointer()
+ if (baseAddress.isNull()) {
+ return baseAddress
+ }
+ return baseAddress.add(offset.chatroomInfo.nodeRootOffset).readPointer()
+})
+
+const chatroomRecurse = ((node) => {
+ const chatroomNodeAddress = getChatroomNodeAddress()
+ if (chatroomNodeAddress.isNull()) {
+ return
+ }
+
+ if (node.equals(chatroomNodeAddress)) {
+ return
+ }
+
+ for (const item in chatroomNodeList) {
+ if (node.equals(chatroomNodeList[item])) {
+ return
+ }
+ }
+
+ chatroomNodeList.push(node)
+ const roomid = readWideString(node.add(0x10))
+
+ const len = node.add(0x54).readU32() //
+ //const memberJson={}
+ if (len > 4) { //
+ const memberStr = readString(node.add(0x44))
+ if (memberStr.length > 0) {
+ const memberList = memberStr.split(/[\\^][G]/)
+ const memberJson = {
+ roomid: roomid,
+ roomMember: memberList
+ }
+
+ chatroomMemberList.push(memberJson)
+ }
+
+ }
+
+ const leftNode = node.add(0x0).readPointer()
+ const centerNode = node.add(0x04).readPointer()
+ const rightNode = node.add(0x08).readPointer()
+
+ chatroomRecurse(leftNode)
+ chatroomRecurse(centerNode)
+ chatroomRecurse(rightNode)
+
+ const allChatroomMemberJson = chatroomMemberList
+ return allChatroomMemberJson
+})
+
+const getChatroomMemberInfoFunction = (() => {
+ const chatroomNodeAddress = getChatroomNodeAddress()
+ if (chatroomNodeAddress.isNull()) {
+ return '[]'
+ }
+
+ const node = chatroomNodeAddress.add(0x0).readPointer()
+ const ret = chatroomRecurse(node)
+
+ const cloneRet = JSON.stringify(ret)
+ chatroomNodeList.length = 0 //empty
+ chatroomMemberList.length = 0 //empty
+ return cloneRet
+})
+
+
+
+/**
+ * sendMsgNativeFunction
+ * send text message
+ * @param {string} talkerId = wxid or roomid
+ * @param {string} content
+ */
+const sendMsgNativeFunction = ((talkerId, content) => {
+
+ const txtAsm = Memory.alloc(Process.pageSize)
+ //const buffwxid = Memory.alloc(0x20)
+
+
+ let wxidPtr = Memory.alloc(talkerId.length * 2 + 2)
+ wxidPtr.writeUtf16String(talkerId)
+
+ let picWxid = Memory.alloc(0x0c)
+ picWxid.writePointer(ptr(wxidPtr)).add(0x04)
+ .writeU32(talkerId.length * 2).add(0x04)
+ .writeU32(talkerId.length * 2).add(0x04)
+
+ let contentPtr = Memory.alloc(content.length * 2 + 2)
+ contentPtr.writeUtf16String(content)
+
+ const sizeOfStringStruct = Process.pointerSize * 5
+ let contentStruct = Memory.alloc(sizeOfStringStruct)
+
+ contentStruct
+ .writePointer(contentPtr).add(0x4)
+ .writeU32(content.length).add(0x4)
+ .writeU32(content.length * 2)
+
+
+ const ecxBuffer = Memory.alloc(0x2d8)
+
+ Memory.patchCode(txtAsm, Process.pageSize, code => {
+ var cw = new X86Writer(code, {
+ pc: txtAsm
+ })
+ cw.putPushfx()
+ cw.putPushax()
+
+ cw.putPushU32(0x0)
+ cw.putPushU32(0x0)
+ cw.putPushU32(0x0)
+ cw.putPushU32(0x1)
+ cw.putPushU32(0x0)
+
+ //cw.putMovRegReg
+
+ cw.putMovRegAddress('eax', contentStruct)
+ cw.putPushReg('eax')
+
+ cw.putMovRegAddress('edx', picWxid) //room_id
+
+ cw.putMovRegAddress('ecx', ecxBuffer)
+ cw.putCallAddress(moduleBaseAddress.add(
+ offset.sendTxtMsg.callOffset
+ ))
+
+ cw.putAddRegImm('esp', 0x18)
+ cw.putPopax()
+ cw.putPopfx()
+ cw.putRet()
+ cw.flush()
+
+ })
+
+ console.log('----------txtAsm', txtAsm)
+ const nativeativeFunction = new NativeFunction(ptr(txtAsm), 'void', [])
+ nativeativeFunction()
+
+})
+
+
+let asmAtMsg = null
+let roomid_, msg_, wxid_, atid_
+let ecxBuffer
+const sendAtMsgNativeFunction = ((roomId, text, contactId,nickname) => {
+
+ asmAtMsg = Memory.alloc(Process.pageSize)
+ ecxBuffer = Memory.alloc(0x3b0)
+
+ const atContent = '@'+nickname+' '+text
+
+ roomid_ = initStruct(roomId)
+ wxid_ = initidStruct(contactId)
+ msg_ = initmsgStruct(atContent)
+ atid_ = initAtMsgStruct(wxid_)
+
+ Memory.patchCode(asmAtMsg, Process.pageSize, code => {
+ var cw = new X86Writer(code, {
+ pc: asmAtMsg
+ })
+ cw.putPushfx()
+ cw.putPushax()
+
+ cw.putPushU32(0x0)
+ cw.putPushU32(0x0)
+ cw.putPushU32(0x0)
+ cw.putPushU32(0x1)
+ //cw.putPushU32(0x0)
+ cw.putMovRegAddress('eax', atid_)
+ cw.putPushReg('eax')
+
+ //cw.putMovRegReg
+
+ cw.putMovRegAddress('eax', msg_)
+ cw.putPushReg('eax')
+
+ cw.putMovRegAddress('edx', roomid_) //room_id
+
+ cw.putMovRegAddress('ecx', ecxBuffer)
+ cw.putCallAddress(moduleBaseAddress.add(
+ offset.sendTxtMsg.callOffset
+ ))
+
+ cw.putAddRegImm('esp', 0x18)
+ cw.putPopax()
+ cw.putPopfx()
+ cw.putRet()
+ cw.flush()
+
+ })
+
+ //console.log('----------txtAsm', asmAtMsg)
+ const nativeativeFunction = new NativeFunction(ptr(asmAtMsg), 'void', [])
+ nativeativeFunction()
+
+})
+
+/**
+ *
+ * @param {*} contactId
+ * @param {*} path
+ */
+const sendPicMsgNativeFunction = ((contactId, path) => {
+
+ const picAsm = Memory.alloc(Process.pageSize)
+ const buffwxid = Memory.alloc(0x20)
+ const picbuff = Memory.alloc(0x2D8)
+
+ let pathPtr = Memory.alloc(path.length * 2 + 1)
+ pathPtr.writeUtf16String(path)
+
+ let imagefilepath = Memory.alloc(0x24)
+ imagefilepath.writePointer(pathPtr).add(0x04)
+ .writeU32(path.length * 2).add(0x04)
+ .writeU32(path.length * 2).add(0x04)
+
+ let picWxidPtr = Memory.alloc(contactId.length * 2 + 1)
+ picWxidPtr.writeUtf16String(contactId)
+
+ let picWxid = Memory.alloc(0x0c)
+ picWxid.writePointer(ptr(picWxidPtr)).add(0x04)
+ .writeU32(contactId.length * 2).add(0x04)
+ .writeU32(contactId.length * 2).add(0x04)
+
+
+ //const test_offset1 = 0x701DC0;
+ Memory.patchCode(picAsm, Process.pageSize, code => {
+ var cw = new X86Writer(code, {
+ pc: picAsm
+ })
+ cw.putPushfx();
+ cw.putPushax();
+ cw.putCallAddress(moduleBaseAddress.add(
+ offset.sendPicMsg.call1
+ ))
+ cw.putMovRegReg('edx', 'eax') //缓存
+
+ cw.putSubRegImm('esp', 0x14)
+ cw.putMovRegAddress('eax', buffwxid)
+ cw.putMovRegReg('ecx', 'esp')
+ cw.putMovRegAddress('edi', imagefilepath)
+ cw.putPushReg('eax')
+ cw.putCallAddress(moduleBaseAddress.add(
+ offset.sendPicMsg.call2
+ ))
+
+ cw.putMovRegReg('ecx', 'edx')
+ cw.putMovRegAddress('eax', picWxid) //=lea
+ cw.putMovRegAddress('edi', imagefilepath)
+ cw.putPushReg('edi')
+ cw.putPushReg('eax')
+ cw.putMovRegAddress('eax', picbuff)
+ cw.putPushReg('eax')
+
+ cw.putMovRegAddress('edi', picWxid) //edi
+ cw.putCallAddress(moduleBaseAddress.add(
+ offset.sendPicMsg.call3
+ ))
+
+
+
+ cw.putPopax()
+ cw.putPopfx()
+ cw.putRet()
+ cw.flush()
+
+ })
+
+ //console.log('----------picAsm',picAsm)
+ const nativeativeFunction = new NativeFunction(ptr(picAsm), 'void', [])
+ nativeativeFunction()
+
+})
+
+
+
+
+let memberNickBuffAsm = null
+let nickRoomId = null
+let nickMemberId = null
+let nickBuff = null
+const getChatroomMemberNickInfoFunction = ((memberId, roomId) => {
+
+ nickBuff = Memory.alloc(0x7e4)
+ //const nickRetAddr = Memory.alloc(0x04)
+ memberNickBuffAsm = Memory.alloc(Process.pageSize)
+ //console.log('asm address----------',memberNickBuffAsm)
+ nickRoomId = initidStruct(roomId)
+ //console.log('nick room id',nickRoomId)
+ nickMemberId = initStruct(memberId)
+
+ //console.log('nick nickMemberId id',nickMemberId)
+ //const nickStructPtr = initmsgStruct('')
+
+ Memory.patchCode(memberNickBuffAsm, Process.pageSize, code => {
+ var cw = new X86Writer(code, {
+ pc: memberNickBuffAsm
+ })
+ cw.putPushfx()
+ cw.putPushax()
+ cw.putMovRegAddress('edi', nickRoomId)
+ cw.putMovRegAddress('eax', nickBuff)
+ cw.putMovRegReg('edx', 'edi')
+ cw.putPushReg('eax')
+ cw.putMovRegAddress('ecx', nickMemberId)
+ cw.putCallAddress(moduleBaseAddress.add(0xC06F10))
+ cw.putAddRegImm('esp', 0x04)
+ cw.putPopax()
+ cw.putPopfx()
+ cw.putRet()
+ cw.flush()
+
+ })
+
+ const nativeativeFunction = new NativeFunction(ptr(memberNickBuffAsm), 'void', [])
+ nativeativeFunction()
+
+ const nickname = readWideString(nickBuff)
+ console.log('----nickname', nickname)
+ return readWideString(nickBuff)
+})
+
+
diff --git a/src/agents/agent-script-3.9.2.23-new.js b/src/agents/agent-script-3.9.2.23-new.js
new file mode 100644
index 0000000..f706c38
--- /dev/null
+++ b/src/agents/agent-script-3.9.2.23-new.js
@@ -0,0 +1,1964 @@
+/**
+ * > Special thanks to: @cixingguangming55555 老张学技术
+ *
+ * Credit: https://github.com/cixingguangming55555/wechat-bot
+ */
+
+//https://blog.csdn.net/iloveitvm/article/details/109119687 frida学习
+
+//const { isNullishCoalesce } = require("typescript")
+
+//3.9.2.23
+
+// 偏移地址集合 done
+const offset = {
+ hook_point: 0xd19a0b, //3.9.2.23
+ myselfinfo: {
+ offset: 0x2FFD484, //老版本微信号偏移,后面的地址,都要在这个偏移上增加
+ //wxid_len:0x10,
+ head_img_url: 0x2D8,
+ head_img_url_len: 0x2E8,
+ wx_nick_name: 0x10C,
+ wxcode_new: 0x64, //新版本微信号
+ //wxcode_len:0x74
+ wxid_len_offset: 0x4D4
+ },
+ contactInfo: {
+ nodeOffset: 0x2FFDD7C,
+ nodeRootOffset: 0x64
+ },
+ chatroomInfo: {
+ nodeOffset: 0x2FFDDC8,
+ nodeRootOffset: 0x8c8
+ },
+ sendTxtMsg: {
+ callOffset: 0xCE6C80
+ },
+ sendPicMsg: {
+ call1: 0x768140,
+ call2: 0xf59e40,
+ call3: 0xce6640
+ }
+};
+//3.9.2.23
+
+// 全局配置 done
+/*------------------global-------------------------------------------*/
+const availableVersion = 1661534743 ////3.9.2.23 ==0x63090217
+
+const moduleBaseAddress = Module.getBaseAddress('WeChatWin.dll')
+const moduleLoad = Module.load('WeChatWin.dll')
+//1575CF98
+
+// 全局变量 tbd
+const g_EDIPtr = moduleBaseAddress.add(0x222f38c).readPointer().add(0xD70).readPointer()//
+const g_EDIU32 = moduleBaseAddress.add(0x222f38c).readPointer().add(0xD70).readU32()
+
+/*------------------global-------------------------------------------*/
+
+/*---------------base -------------------------*/
+
+// done
+let retidPtr=null
+let retidStruct=null
+const initidStruct = ((str) => {
+
+ retidPtr = Memory.alloc(str.length * 2 + 1)
+ retidPtr.writeUtf16String(str)
+
+ retidStruct = Memory.alloc(0x14) // returns a NativePointer
+
+ retidStruct
+ .writePointer(retidPtr).add(0x04)
+ .writeU32(str.length * 2).add(0x04)
+ .writeU32(str.length * 2).add(0x04)
+ .writeU32(0).add(0x04)
+ .writeU32(0)
+
+ return retidStruct
+})
+
+// done
+let retPtr = null
+let retStruct = null
+const initStruct = ((str) => {
+
+ retPtr = Memory.alloc(str.length * 2 + 1)
+ retPtr.writeUtf16String(str)
+
+ retStruct = Memory.alloc(0x14) // returns a NativePointer
+
+ retStruct
+ .writePointer(retPtr).add(0x04)
+ .writeU32(str.length * 2).add(0x04)
+ .writeU32(str.length * 2).add(0x04)
+ .writeU32(0).add(0x04)
+ .writeU32(0)
+
+ return retStruct
+})
+
+// done
+let msgstrPtr=null
+let msgStruct=null
+const initmsgStruct = ((str) => {
+ msgstrPtr = Memory.alloc(str.length * 2 + 1)
+ msgstrPtr.writeUtf16String(str)
+
+ msgStruct = Memory.alloc(0x14) // returns a NativePointer
+
+ msgStruct
+ .writePointer(msgstrPtr).add(0x04)
+ .writeU32(str.length * 2).add(0x04)
+ .writeU32(str.length * 2).add(0x04)
+ .writeU32(0).add(0x04)
+ .writeU32(0)
+
+ return msgStruct
+})
+
+// tbd
+let retidNullStruct = null
+let retidNullPtr = null
+const initNullIdStruct = ((str) => {
+
+ retidNullPtr = Memory.alloc(str.length * 2 + 1)
+ retidNullPtr.writeUtf16String(str)
+
+ retidNullStruct = Memory.alloc(0x14) // returns a NativePointer
+
+ retidNullStruct
+ .writePointer(retidNullPtr).add(0x04)
+ .writeU32(str.length * 2).add(0x04)
+ .writeU32(str.length * 2).add(0x04)
+ .writeU32(0).add(0x04)
+ .writeU32(0)
+
+ return retidNullStruct
+})
+
+// done
+/**
+* at msg structure
+*/
+let atStruct = null
+const initAtMsgStruct = ((wxidStruct) => {
+
+ atStruct = Memory.alloc(0x10)
+
+ atStruct.writePointer(wxidStruct).add(0x04)
+ .writeU32(wxidStruct.toInt32() + 0x14).add(0x04)//0x14 = sizeof(wxid structure)
+ .writeU32(wxidStruct.toInt32() + 0x14).add(0x04)
+ .writeU32(0)
+ return atStruct
+})
+
+// done
+// std::string
+// const str = readStringPtr(ptr).readUtf8String()
+const readStringPtr = (address) => {
+ const addr = ptr(address)
+ const size = addr.add(16).readU32()
+ const capacity = addr.add(20).readU32()
+ addr.ptr = addr
+ addr.size = size
+ addr.capacity = capacity
+ if (capacity > 15 && !addr.readPointer().isNull()) {
+ addr.ptr = addr.readPointer()
+ }
+ addr.ptr._readCString = addr.ptr.readCString
+ addr.ptr._readAnsiString = addr.ptr.readAnsiString
+ addr.ptr._readUtf8String = addr.ptr.readUtf8String
+ addr.readCString = () => { return addr.size ? addr.ptr._readCString(addr.size) : '' }
+ addr.readAnsiString = () => { return addr.size ? addr.ptr._readAnsiString(addr.size) : '' }
+ addr.readUtf8String = () => { return addr.size ? addr.ptr._readUtf8String(addr.size) : '' }
+
+ // console.log('readStringPtr() address:',address,' -> str ptr:', addr.ptr, 'size:', addr.size, 'capacity:', addr.capacity)
+ // console.log('readStringPtr() str:' , addr.readUtf8String())
+ // console.log('readStringPtr() address:', addr,'dump:', addr.readByteArray(24))
+
+ return addr
+}
+
+// done
+const readString = (address) => {
+ return readStringPtr(address).readUtf8String()
+}
+
+// done
+const readWideString = (address) => {
+ return readWStringPtr(address).readUtf16String()
+}
+
+/*-----------------base-------------------------*/
+
+let currentVersion = 0
+
+let nodeList = [] //for contact
+let contactList = [] //for contact
+
+let chatroomNodeList = [] //for chatroom
+let chatroomMemberList = []//for chatroom
+let loggedIn = false
+
+//开启日志 3.6.0.18
+// //[0x221c330+wechatwin.dll]+0xf8
+// 20220504
+
+
+let g_initTestAsm = null
+let g_BufferEbp2C = null
+let g_initECXU32 = null
+let g_initECXPtr = null
+let g_initEBXPtr = null
+let g_initEBX = null
+
+let g_attatchEBP210Buffer = null
+let g_attatchPathPtr = null
+let g_attatchPath = null
+let g_attatchEBPAc = null
+let g_attatchEBPAcBufPtr = null
+
+let g_attatchContactIdPtr = null
+//let g_attatchECXBuffer = null
+let g_attatchESIU32 = null
+
+let g_initECXTempPtr = null
+const initGlobal = ((contactId, attatchFile) => {
+
+ //const base = moduleBaseAddress.add(0x222f38c).readPointer()
+ //g_EDI = base.add(0xD70).readPointer()//0x438+0x938
+ console.log('------------g_attatchEBPAc', g_attatchEBPAc)
+ console.log('------------g_EDIU32', g_EDIU32)
+ g_initTestAsm = Memory.alloc(Process.pageSize)
+ console.log('------------address', g_initTestAsm)
+
+ g_initECXPtr = g_EDIPtr.add(0xB80).readPointer().add(0x1640)
+ g_initECXTempPtr = g_EDIPtr.add(0xB88).readPointer()
+ g_initECXU32 = g_initECXPtr.toInt32()
+ g_attatchESIU32 = g_EDIU32
+
+ console.log('------------g_initECXU32', g_initECXU32)
+ console.log('------------g_initESIU32', g_attatchESIU32)
+
+
+ //console.log('==========g_initECXPtr',g_initECXPtr)
+ //console.log('==========g_EDIU32',g_EDIU32)
+
+ //g_attatchECXBuffer = Memory.alloc(0x1024)
+ //Memory.copy(g_attatchECXBuffer, g_initECXPtr, 0x1024)
+
+ g_BufferEbp2C = Memory.alloc(0x48)
+
+ //g_initEBX = moduleBaseAddress.add(0x2251724).readPointer().readPointer()
+ //g_initEBXPtr = Memory.alloc(0x14).writePointer(g_initEBX)
+ //g_initEBXPtr.add(0x08).writePointer(g_BufferEbp2C)
+
+ g_attatchPathPtr = Memory.alloc(attatchFile.length * 2 + 2)
+ g_attatchPathPtr.writeUtf16String(attatchFile)
+
+ g_attatchPath = Memory.alloc(0x28)
+ g_attatchPath.writePointer(g_attatchPathPtr).add(0x04)
+ .writeU32(attatchFile.length * 2).add(0x04)
+ .writeU32(attatchFile.length * 2).add(0x04)
+ /*---------------------------------ebp-210----------------*/
+ g_attatchEBP210Buffer = Memory.alloc(0x48)
+ g_attatchEBP210Buffer.writeU32(0x3)
+ g_attatchEBP210Buffer.add(0x4).writePointer(g_attatchPathPtr)
+ g_attatchEBP210Buffer.add(0x8).writeU32(attatchFile.length * 2)
+ g_attatchEBP210Buffer.add(0xC).writeU32(attatchFile.length * 2)
+ g_attatchEBP210Buffer.add(0x2C).writeU32(moduleBaseAddress.add(0x2ECE87).toInt32())
+ //console.log('------------g_attatchEBP210Buffer',g_attatchEBP210Buffer)
+ /*---------------------------------ebp-210----------------*/
+
+ //g_attatchContactIdPtr = Memory.alloc(0x4)
+ //g_attatchContactIdPtr.writeUtf16String(contactId)
+ //console.log('------------g_attatchEBP210Buffer',g_attatchEBP210Buffer)
+ g_attatchEBPAc = Memory.alloc(0x140)
+ //g_attatchEBPAcBufPtr = Memory.alloc(0x100)
+ //g_attatchEBPAc.writePointer(g_attatchEBP210Buffer)
+ //g_attatchEBPAc.add(0x4).writePointer(g_attatchEBPAcBufPtr)
+ //g_attatchEBPAc.add(0x8).writePointer(g_attatchEBPAcBufPtr)
+ g_attatchEBPAc.add(0x10).writeU32(g_EDIU32)
+ console.log('------------g_attatchEBPAc', g_attatchEBPAc)
+
+ /*g_attatchECXBuffer.add(0x18).writePointer(g_attatchContactIdPtr)
+ g_attatchECXBuffer.add(0x1C).writeU32(contactId.length*2)
+ .add(0x04).writeU32(contactId.length*2)*/
+
+
+
+ //g_attatchESIU32 = g_EDI.toInt32()
+
+
+ //console.log('------------g_attatchESIU32',g_attatchESIU32)
+ //console.log('==========g_attatchECXBuffer',g_attatchECXBuffer)
+
+ Memory.patchCode(g_initTestAsm, Process.pageSize, code => {
+ var cw = new X86Writer(code, { pc: g_initTestAsm })
+ cw.putPushfx()
+ cw.putPushax()
+ //cw.putMovRegAddress('eax', g_attatchEBP210Buffer)
+
+ /*cw.putMovRegAddress('edi',g_EDIPtr)
+ cw.putMovRegReg('esi','edi')
+ cw.putMovRegAddress('eax',g_BufferEbp2C)
+ cw.putMovRegAddress('ecx',g_initECXTempPtr)
+ cw.putPushReg('eax')
+ cw.putCallAddress(moduleBaseAddress.add(0x131bb0))*/
+
+ //cw.putMovRegOffsetPtrU32('ebp', -20, 0)
+
+ /*cw.putPushU32(0)
+ cw.putMovRegAddress('eax', g_attatchPathPtr)
+ cw.putPushReg('eax')
+ cw.putPushU32(3)
+ cw.putMovRegAddress('ecx', g_attatchEBP210Buffer)
+ cw.putCallAddress(moduleBaseAddress.add(0x130220))*/
+
+
+ /*cw.putMovRegAddress('edi', g_attatchEBPAc)//后面要用的的ebp-2c
+ cw.putMovRegAddress('ecx', g_attatchEBP210Buffer)
+ cw.putPushReg('ecx')
+ cw.putMovRegU32('eax',0)
+ cw.putPushReg('eax')//push eax
+ cw.putMovRegReg('ecx', 'edi')
+ cw.putMovRegAddress('esi',g_attatchPathPtr)
+ cw.putCallAddress(moduleBaseAddress.add(0x138880))*/
+
+
+ /*cw.putSubRegImm('esp',0x14)
+ cw.putMovRegU32('ecx',g_initECXU32)
+ cw.putMovRegU32('esi',g_attatchESIU32)
+ cw.putMovRegAddress('eax', g_attatchEBPAc)
+ cw.putPushReg('eax')
+ cw.putCallAddress(moduleBaseAddress.add(0x173620))*/
+ //cw.putCallAddress(moduleBaseAddress.add(0x522590))
+
+ /** g_attatchEBPAc*/
+ //cw.putMovRegNearPtr('eax', g_attatchEBPAc)
+ //cw.putMovNearPtrReg(g_attatchEBPAc.add(0xc), 'eax')
+ /** g_attatchEBPAc*/
+
+
+ //cw.putMovRegAddress('ebx', g_initEBXPtr)
+ //cw.putMovRegU32('edi', g_EDI.toInt32())
+ //cw.putMovRegU32('esi', g_EDI.toInt32())
+ /*cw.putMovRegU32('ecx', g_initECX)
+ cw.putMovRegAddress('eax', g_BufferEbp2C)
+ cw.putPushReg('eax')
+ cw.putCallAddress(moduleBaseAddress.add(0x131BB0))*/
+
+ cw.putPopax()
+ cw.putPopfx()
+ cw.putRet()
+ cw.flush()
+
+ })
+
+ const nativeativeFunction = new NativeFunction(ptr(g_initTestAsm), 'void', [])
+ nativeativeFunction()
+})
+
+
+let g_personal_detail_ebx = null
+let g_personal_detail_asm = null
+let g_personal_wxid = null
+let g_personal_wxid_ptr = null
+const getOldTest = ((wxid) => {//personal detail
+
+ g_personal_detail_asm = Memory.alloc(Process.pageSize)
+ g_personal_detail_ebx = moduleBaseAddress.add(0x222F38C).readPointer().add(0xFB8).toInt32()
+
+ g_personal_wxid_ptr = Memory.alloc(wxid.length * 2 + 2)
+ g_personal_wxid_ptr.writeUtf16String(wxid)
+
+ g_personal_wxid = Memory.alloc(0x14)
+ g_personal_wxid.writePointer(ptr(g_personal_wxid_ptr)).add(0x04)
+ .writeU32(wxid.length * 2).add(0x04)
+ .writeU32(wxid.length * 2).add(0x08)
+
+ console.log('-----------address----------', g_personal_detail_asm)
+
+ Memory.patchCode(g_personal_detail_asm, Process.pageSize, code => {
+ var cw = new X86Writer(code, { pc: g_personal_detail_asm })
+ cw.putPushfx()
+ cw.putPushax()
+
+ cw.putCallAddress(moduleBaseAddress.add(0x9A000))
+
+ //78BA9ACE | E8 2D05D6FF | call wechatwin.7890A000 |
+ cw.putMovRegU32('ebx', g_personal_detail_ebx)
+ cw.putMovRegReg('esi', 'eax')
+ cw.putPushReg('ebx')
+ cw.putSubRegImm('esp', 0x14)
+ cw.putMovRegAddress('eax', g_personal_wxid)
+ cw.putMovRegReg('ecx', 'esp')
+ cw.putPushReg('eax')
+ cw.putCallAddress(moduleBaseAddress.add(0x701DC0))
+ cw.putMovRegReg('ecx', 'esi')
+ cw.putCallAddress(moduleBaseAddress.add(0x4024A0))
+
+ cw.putPopax()
+ cw.putPopfx()
+ cw.putRet()
+ cw.flush()
+
+ })
+
+ const nativeativeFunction = new NativeFunction(ptr(g_personal_detail_asm), 'void', [])
+ nativeativeFunction()
+
+
+})
+
+// const writeLogNativeCallback = (() => {
+// const nativeCallback = new NativeCallback(() => { }, 'void', [])
+// const nativeCallFunction = new NativeFunction(nativeCallback, 'void', [])
+
+// Interceptor.attach(
+// moduleBaseAddress.add(0x7008A4),
+// {
+// onEnter() {
+// const addr = this.context.eax//.sub(0x114)//0xc30-0x08
+// if(addr >0){
+// const log = ptr(addr).readAnsiString()
+// }
+// }
+// })
+// return nativeCallback
+// })()
+
+/**
+ * test call
+ */
+let attatchTestAsm = null
+let attatchTestEbp2C = null
+let attatchGlobalEDI = null
+let attatchGlobalEDIB88 = null
+let attatchTestEBX = null
+let g_tempEcx = null
+let attatchFirstECX = null
+//let attatchFirstECX = null
+let gattatchFilePtr = null
+let gattatchFile = null
+let gattatchReceiveIdPtr = null
+let gattatchReceiveId = null
+let attatchEAX3B0Buf = null
+
+let attatchESIbuf = null
+const getWxTest = ((contactId, filePath) => {
+ //const nativeativeFunction = new NativeFunction(ptr(addr), 'void', [])
+ //nativeativeFunction()
+ attatchTestAsm = Memory.alloc(Process.pageSize)
+ console.log('----------------address', attatchTestAsm)
+ attatchTestEbp2C = Memory.alloc(0xC)
+ attatchGlobalEDI = moduleBaseAddress.add(0x222f38c).readPointer()
+ .add(0x938).add(0x438).readPointer()
+ attatchGlobalEDIB88 = attatchGlobalEDI.add(0xB88).readPointer()
+ attatchTestEBX = Memory.alloc(0x4)
+ attatchTestEBX.writePointer(attatchGlobalEDI)
+ console.log('----------------attatchGlobalEDI', attatchGlobalEDI)
+ console.log('----------------attatchGlobalEDIB88', attatchGlobalEDIB88)
+
+ attatchFirstECX = Memory.alloc(0x28)
+ //const attatchSecondEcx = Memory.alloc(0x14)
+
+ const contactIdLength = contactId.length * 2 + 2//edx
+ const contractIdActLength = contactId.length
+
+
+ gattatchReceiveIdPtr = Memory.alloc(contactId.length * 2 + 2)
+ gattatchReceiveIdPtr.writeUtf16String(contactId)
+
+ gattatchReceiveId = Memory.alloc(0x14)
+ gattatchReceiveId.writePointer(ptr(gattatchReceiveIdPtr)).add(0x04)
+ .writeU32(contactId.length * 2).add(0x04)
+ .writeU32(contactId.length * 2).add(0x08)
+ //console.log('----------------attatchGlobalEDIB88',attatchGlobalEDIB88)
+ //return
+ /*console.log(hexdump(attatchTestEBX, {
+ offset: 0,
+ length: 0x40,
+ header: true,
+ ansi: true
+ }))
+ return*/
+
+ gattatchFilePtr = Memory.alloc(filePath.length * 2 + 2)
+ gattatchFilePtr.writeUtf16String(filePath)
+
+ gattatchFile = Memory.alloc(0x14)
+ gattatchFile.writePointer(ptr(gattatchFilePtr)).add(0x04)
+ .writeU32(filePath.length * 2).add(0x04)
+ .writeU32(filePath.length * 2).add(0x08)
+
+ const attatchLastECX = moduleBaseAddress.add(0x222f170).toInt32()
+
+ attatchEAX3B0Buf = Memory.alloc(0x3B0)
+
+ g_tempEcx = Memory.alloc(0x4)
+ //g_tempEcx1 = Memory.alloc(0x4)
+
+ attatchESIbuf = Memory.alloc(0x100)
+ attatchESIbuf.add(0x0).writeU32(3)
+ attatchESIbuf.add(0x4).writePointer(gattatchFilePtr)
+ attatchESIbuf.add(0x8).writeU32(filePath.length * 2)
+ attatchESIbuf.add(0xc).writeU32(filePath.length * 2)
+
+ Memory.patchCode(attatchTestAsm, Process.pageSize, code => {
+ var cw = new X86Writer(code, { pc: attatchTestAsm })
+ cw.putPushfx()
+ cw.putPushax()
+ //cw.putMovRegU32('edi',attatchGlobalEDI)
+
+
+ cw.putMovRegAddress('esi', attatchESIbuf)
+
+ cw.putMovRegAddress('ecx', attatchFirstECX.add(0x14))
+ cw.putMovRegAddress('eax', gattatchFile)
+ cw.putPushReg('eax')
+ cw.putCallAddress(moduleBaseAddress.add(0x701DC0))
+
+
+ cw.putMovRegAddress('ecx', attatchFirstECX)
+ cw.putMovRegU32('eax', contactIdLength)
+ cw.putPushReg('eax')
+ cw.putPushU32(0)
+ cw.putCallAddress(moduleBaseAddress.add(0x1a11c83))
+ cw.putAddRegImm('esp', 0x8)
+
+ cw.putMovRegReg('edx', 'eax')
+ cw.putMovNearPtrReg(attatchFirstECX, 'edx')
+ cw.putMovRegU32('edi', contactIdLength)
+ cw.putPushReg('edi')
+ cw.putMovRegAddress('eax', gattatchReceiveIdPtr)//ebp-58
+ cw.putPushReg('eax')
+ cw.putMovRegNearPtr('eax', attatchFirstECX)
+ cw.putPushReg('eax')
+ cw.putCallAddress(moduleBaseAddress.add(0x1a1047a))
+ cw.putAddRegImm('esp', 0x0c)
+
+ //cw.putMovRegNearPtr('ecx',attatchFirstECX)
+ //cw.putAddRegImm('esp', 0x0c)
+ //cw.putMovRegU32('edx', 0)
+ //cw.putMovRegRegPtr('eax', 'ecx')
+ //cw.putMovNearPtrReg(attatchFirstECX.add(0x04),'edi')
+ cw.putMovRegU32('edi', contactId.length * 2)
+ cw.putMovRegU32('ecx', attatchLastECX)
+ cw.putMovRegAddress('eax', attatchEAX3B0Buf)
+ cw.putPushReg('eax')
+ cw.putCallAddress(moduleBaseAddress.add(0x392260))
+
+ cw.putMovRegAddress('ecx', attatchEAX3B0Buf)
+ cw.putCallAddress(moduleBaseAddress.add(0x94200))
+
+ cw.putPopax()
+ cw.putPopfx()
+ cw.putRet()
+ cw.flush()
+
+ })
+
+ const nativeativeFunction = new NativeFunction(ptr(attatchTestAsm), 'void', [])
+ nativeativeFunction()
+
+
+})
+// 001
+const getTestInfoFunction = ((addr) => {
+ const nativeativeFunction = new NativeFunction(ptr(addr), 'void', [])
+ nativeativeFunction()
+
+ //00CFE484
+
+
+ /*MemoryAccessMonitor.enable({base:ptr(addr),size:0x01}, {
+ onAccess(details){
+ console.log('============')
+ console.log(details.operation)
+ console.log(details.from)
+ console.log(details.address)
+ console.log('============')
+ }
+ })*/
+
+})
+
+// 002get global data
+
+const isLoggedInFunction = (() => {
+ loggedIn = moduleBaseAddress.add(offset.is_logged_in_offset).readU32()
+ return !!loggedIn
+})
+
+// 007 缺失,请标注已废弃或者其他原因
+const getMyselfIdFunction = (() => {
+
+ let wx_id = readString(moduleBaseAddress.add(offset.wxid_offset))
+
+ return wx_id
+
+})
+
+// std::wstring
+// const wstr = readWStringPtr(ptr).readUtf16String()
+const readWStringPtr = (address) => {
+ const addr = ptr(address)
+ const size = addr.add(4).readU32()
+ const capacity = addr.add(8).readU32()
+ addr.ptr = addr.readPointer()
+ addr.size = size
+ addr.capacity = capacity
+ addr.ptr._readUtf16String = addr.ptr.readUtf16String
+ addr.readUtf16String = () => { return addr.size ? addr.ptr._readUtf16String(addr.size * 2) : '' }
+
+ // console.log('readWStringPtr() address:',address,' -> ptr:', addr.ptr, 'size:', addr.size, 'capacity:', addr.capacity)
+ // console.log('readWStringPtr() str:' , `"${addr.readUtf16String()}"`,'\n',addr.ptr.readByteArray(addr.size*2+2),'\n')
+ // console.log('readWStringPtr() address:', addr,'dump:', addr.readByteArray(16),'\n')
+
+ return addr
+}
+
+//contact
+const recurse = ((node) => {
+ const headerNodeAddress = getHeaderNodeAddress()
+ if (headerNodeAddress.isNull()) { return }
+
+ if (node.equals(headerNodeAddress)) { return }
+
+ for (const item in nodeList) {
+ if (node.equals(nodeList[item])) {
+ return
+ }
+ }
+
+
+ nodeList.push(node)
+ //wxid, format relates to registration method
+ const wxid = readWideString(node.add(0x38))
+
+ //custom id, if not set return null, and use wxid which should be custom id
+ const wx_code = readWideString(node.add(0x4c)) || readWideString(node.add(0x38))
+
+ //custom Nickname
+ const name = readWideString(node.add(0x94))
+
+ //alias aka 'remark' in wechat
+ const alias = readWideString(node.add(0x80))
+
+ //avatarUrl
+ const avatar = readWideString(node.add(0x138))
+ //const avatar = Memory.readUtf16String(node.add(0x138).readPointer())
+ //contact gender
+ const gender = node.add(0x18C).readU32()
+
+ const contactJson = {
+ id: wxid,
+ code: wx_code,
+ name: name,
+ alias: alias,
+ avatarUrl: avatar,
+ gender: gender,
+ }
+
+ contactList.push(contactJson)
+
+ const leftNode = node.add(0x0).readPointer()
+ const centerNode = node.add(0x04).readPointer()
+ const rightNode = node.add(0x08).readPointer()
+
+ recurse(leftNode)
+ recurse(centerNode)
+ recurse(rightNode)
+
+ const allContactJson = contactList
+ return allContactJson
+
+})
+
+// 010 done
+const getWechatVersionFunction = (() => {
+ if (currentVersion) {
+ return currentVersion
+ }
+ const pattern = '55 8B ?? 83 ?? ?? A1 ?? ?? ?? ?? 83 ?? ?? 85 ?? 7F ?? 8D ?? ?? E8 ?? ?? ?? ?? 84 ?? 74 ?? 8B ?? ?? ?? 85 ?? 75 ?? E8 ?? ?? ?? ?? 0F ?? ?? 0D ?? ?? ?? ?? A3 ?? ?? ?? ?? A3 ?? ?? ?? ?? 8B ?? 5D C3'
+ const results = Memory.scanSync(moduleLoad.base, moduleLoad.size, pattern)
+ if (results.length == 0) {
+ return 0
+ }
+ const addr = results[0].address
+ const ret = addr.add(0x07).readPointer()
+ const ver = ret.add(0x0).readU32()
+ currentVersion = ver
+ return ver
+})
+
+// 011 done
+const getWechatVersionStringFunction = ((ver = getWechatVersionFunction()) => {
+ if (!ver) {
+ return '0.0.0.0'
+ }
+ const vers = []
+ vers.push((ver >> 24) & 255 - 0x60)
+ vers.push((ver >> 16) & 255)
+ vers.push((ver >> 8) & 255)
+ vers.push(ver & 255)
+ return vers.join('.')
+})
+
+// 012 done
+const checkSupportedFunction = (() => {
+ const ver = getWechatVersionFunction()
+ return ver == availableVersion
+})
+
+/**
+ * @Hook: recvMsg -> recvMsgNativeCallback
+ */
+
+// 019 done
+const recvMsgNativeCallback = (() => {
+
+
+ const nativeCallback = new NativeCallback(() => {}, 'void', ['int32', 'pointer', 'pointer', 'pointer', 'pointer', 'int32'])
+ const nativeativeFunction = new NativeFunction(nativeCallback, 'void', ['int32', 'pointer', 'pointer', 'pointer', 'pointer', 'int32'])
+
+ Interceptor.attach(
+ moduleBaseAddress.add(offset.hook_point), {
+ onEnter() {
+ const addr = this.context.ecx //0xc30-0x08
+ const msgType = addr.add(0x38).readU32()
+ const isMyMsg = addr.add(0x3C).readU32() //add isMyMsg
+
+ if (msgType > 0) {
+
+ const talkerIdPtr = addr.add(0x48).readPointer()
+ //console.log('txt msg',talkerIdPtr.readUtf16String())
+ const talkerIdLen = addr.add(0x48 + 0x04).readU32() * 2 + 2
+
+ const myTalkerIdPtr = Memory.alloc(talkerIdLen)
+ Memory.copy(myTalkerIdPtr, talkerIdPtr, talkerIdLen)
+
+
+ let contentPtr = null
+ let contentLen = 0
+ let myContentPtr = null
+ if (msgType == 3) { // pic path
+ let thumbPtr = addr.add(0x198).readPointer();
+ let hdPtr = addr.add(0x1ac).readPointer();
+ let thumbPath = thumbPtr.readUtf16String();
+ let hdPath = hdPtr.readUtf16String();
+ let picData = [
+ thumbPath, // PUPPET.types.Image.Unknown
+ thumbPath, // PUPPET.types.Image.Thumbnail
+ hdPath, // PUPPET.types.Image.HD
+ hdPath // PUPPET.types.Image.Artwork
+ ]
+ let content = JSON.stringify(picData);
+ myContentPtr = Memory.allocUtf16String(content);
+ } else {
+ contentPtr = addr.add(0x70).readPointer()
+ contentLen = addr.add(0x70 + 0x04).readU32() * 2 + 2
+ myContentPtr = Memory.alloc(contentLen)
+ Memory.copy(myContentPtr, contentPtr, contentLen)
+ }
+
+ // console.log('----------------------------------------')
+ // console.log(msgType)
+ // console.log(contentPtr.readUtf16String())
+ // console.log('----------------------------------------')
+ const groupMsgAddr = addr.add(0x170).readU32() //* 2 + 2
+ let myGroupMsgSenderIdPtr = null
+ if (groupMsgAddr == 0) { //weChatPublic is zero,type is 49
+
+ myGroupMsgSenderIdPtr = Memory.alloc(0x10)
+ myGroupMsgSenderIdPtr.writeUtf16String("null")
+
+ } else {
+
+ const groupMsgSenderIdPtr = addr.add(0x170).readPointer()
+ const groupMsgSenderIdLen = addr.add(0x170 + 0x04).readU32() * 2 + 2
+ myGroupMsgSenderIdPtr = Memory.alloc(groupMsgSenderIdLen)
+ Memory.copy(myGroupMsgSenderIdPtr, groupMsgSenderIdPtr, groupMsgSenderIdLen)
+
+ }
+
+ const xmlNullPtr = addr.add(0x1f0).readU32() //3.9.2.23
+ let myXmlContentPtr = null
+ if (xmlNullPtr == 0) {
+
+ myXmlContentPtr = Memory.alloc(0x10)
+ myXmlContentPtr.writeUtf16String("null")
+
+ } else {
+ const xmlContentPtr = addr.add(0x1f0).readPointer() //3.9.2.23
+
+ const xmlContentLen = addr.add(0x1f0 + 0x04).readU32() * 2 + 2
+ myXmlContentPtr = Memory.alloc(xmlContentLen)
+ Memory.copy(myXmlContentPtr, xmlContentPtr, xmlContentLen)
+ }
+
+ setImmediate(() => nativeativeFunction(msgType, myTalkerIdPtr, myContentPtr, myGroupMsgSenderIdPtr, myXmlContentPtr, isMyMsg))
+ }
+ }
+ })
+ return nativeCallback
+})()
+
+// 003get myself info done
+const getBaseNodeAddress = (() => {
+ return moduleBaseAddress.add(offset.contactInfo.nodeOffset).readPointer()
+})
+
+// 004 done
+const getHeaderNodeAddress = (() => {
+ const baseAddress = getBaseNodeAddress()
+ //console.log('baseAddress',baseAddress)
+ if (baseAddress.isNull()) {
+ return baseAddress
+ }
+
+ //console.log('HeaderNodeAddress',baseAddress.add(offset.handle_offset).readPointer())
+ return baseAddress.add(offset.contactInfo.nodeRootOffset).readPointer()
+})
+
+// 006 done
+const getMyselfInfoFunction = (() => {
+
+ let ptr = 0
+ let wx_code = ''
+ let wx_id = ''
+ let wx_name = ''
+ let head_img_url = ''
+
+ const base = moduleBaseAddress.add(offset.myselfinfo.offset)
+ const wxid_len = base.add(offset.myselfinfo.wxid_len_offset).readU32()
+
+ if (wxid_len === 0x13) { // 新版本微信
+ wx_id = base.readPointer().readAnsiString(wxid_len)
+ wx_code = base.add(offset.myselfinfo.wxcode_new).readAnsiString()
+ } else {
+ wx_id = readString(base)
+ wx_code = wx_id
+ }
+
+
+ wx_name = readString(base.add(offset.myselfinfo.wx_nick_name))
+ const img_addr = base.add(offset.myselfinfo.head_img_url).readPointer()
+ const img_len = base.add(offset.myselfinfo.head_img_url_len).readU32()
+
+ head_img_url = img_addr.readAnsiString(img_len)
+
+ const myself = {
+ id: wx_id,
+ code: wx_code,
+ name: wx_name,
+ head_img_url: head_img_url,
+ };
+
+ return JSON.stringify(myself)
+
+})
+
+// done
+const recurseNew = ((node) => {
+ const headerNodeAddress = getHeaderNodeAddress()
+ if (headerNodeAddress.isNull()) {
+ return
+ }
+
+ if (node.equals(headerNodeAddress)) {
+ return
+ }
+
+ for (const item in nodeList) {
+ if (node.equals(nodeList[item])) {
+ return
+ }
+ }
+
+
+ nodeList.push(node)
+ const id = readString(node.add(0x8))
+ //wxid, format relates to registration method
+ const wxid = readWideString(node.add(0x30))
+ //console.log('-----------',wxid)
+
+
+ //custom id, if not set return null, and use wxid which should be custom id
+ //const wx_code = readWideString(node.add(0x4c)) || readWideString(node.add(0x38))
+
+ //custom Nickname
+ const name = readWideString(node.add(0x8c))
+
+ //alias aka 'remark' in wechat
+ //const alias = readWideString(node.add(0x80))
+
+ //avatarUrl
+ //const avatar = readWideString(node.add(0x138))
+ //const avatar = Memory.readUtf16String(node.add(0x138).readPointer())
+ //contact gender
+ //const gender = node.add(0x18C).readU32()
+
+ const contactJson = {
+ id1: id,
+ id: wxid,
+ name: name,
+ /*code: wx_code,
+ name: name,
+ alias: alias,
+ avatarUrl: avatar,
+ gender: gender,*/
+ }
+
+ contactList.push(contactJson)
+
+ const leftNode = node.add(0x0).readPointer()
+ const centerNode = node.add(0x04).readPointer()
+ //const rightNode = node.add(0x08).readPointer()
+
+ recurseNew(leftNode)
+ recurseNew(centerNode)
+ //recurse(rightNode)
+
+ const allContactJson = contactList
+ return allContactJson
+
+})
+
+// done ?
+const getContactNativeFunction = (() => {
+ const headerNodeAddress = getHeaderNodeAddress()
+ //console.log('headerNodeAddress',headerNodeAddress)
+
+ if (headerNodeAddress.isNull()) {
+ return '[]'
+ }
+
+ const node = headerNodeAddress.add(0x0).readPointer()
+ const ret = recurseNew(node)
+
+ //console.log(ret)
+
+ console.log('getContactNativeFunction:', ret.length)
+ /*for (let item of ret){
+ console.log(JSON.stringify(item))
+ }*/
+ //console.log(ret.contact)
+ const cloneRet = JSON.stringify(ret)
+ nodeList.length = 0
+ contactList.length = 0
+
+ return cloneRet
+})
+
+// 005 done
+const getChatroomNodeAddress = (() => {
+ const baseAddress = moduleBaseAddress.add(offset.chatroomInfo.nodeOffset).readPointer()
+ if (baseAddress.isNull()) {
+ return baseAddress
+ }
+ return baseAddress.add(offset.chatroomInfo.nodeRootOffset).readPointer()
+})
+
+// 008chatroom member done
+const chatroomRecurse = ((node) => {
+ const chatroomNodeAddress = getChatroomNodeAddress()
+ if (chatroomNodeAddress.isNull()) {
+ return
+ }
+
+ if (node.equals(chatroomNodeAddress)) {
+ return
+ }
+
+ for (const item in chatroomNodeList) {
+ if (node.equals(chatroomNodeList[item])) {
+ return
+ }
+ }
+
+ chatroomNodeList.push(node)
+ const roomid = readWideString(node.add(0x10))
+
+ const len = node.add(0x54).readU32() //
+ //const memberJson={}
+ if (len > 4) { //
+ const memberStr = readString(node.add(0x44))
+ if (memberStr.length > 0) {
+ const memberList = memberStr.split(/[\\^][G]/)
+ const memberJson = {
+ roomid: roomid,
+ roomMember: memberList
+ }
+
+ chatroomMemberList.push(memberJson)
+ }
+
+ }
+
+ const leftNode = node.add(0x0).readPointer()
+ const centerNode = node.add(0x04).readPointer()
+ const rightNode = node.add(0x08).readPointer()
+
+ chatroomRecurse(leftNode)
+ chatroomRecurse(centerNode)
+ chatroomRecurse(rightNode)
+
+ const allChatroomMemberJson = chatroomMemberList
+ return allChatroomMemberJson
+})
+
+// 009 done
+const getChatroomMemberInfoFunction = (() => {
+ const chatroomNodeAddress = getChatroomNodeAddress()
+ if (chatroomNodeAddress.isNull()) {
+ return '[]'
+ }
+
+ const node = chatroomNodeAddress.add(0x0).readPointer()
+ const ret = chatroomRecurse(node)
+
+ const cloneRet = JSON.stringify(ret)
+ chatroomNodeList.length = 0 //empty
+ chatroomMemberList.length = 0 //empty
+ return cloneRet
+})
+
+// 024 done
+/**
+ * sendMsgNativeFunction
+ * send text message
+ * @param {string} talkerId = wxid or roomid
+ * @param {string} content
+ */
+ const sendMsgNativeFunction = ((talkerId, content) => {
+
+ const txtAsm = Memory.alloc(Process.pageSize)
+ //const buffwxid = Memory.alloc(0x20)
+
+
+ let wxidPtr = Memory.alloc(talkerId.length * 2 + 2)
+ wxidPtr.writeUtf16String(talkerId)
+
+ let picWxid = Memory.alloc(0x0c)
+ picWxid.writePointer(ptr(wxidPtr)).add(0x04)
+ .writeU32(talkerId.length * 2).add(0x04)
+ .writeU32(talkerId.length * 2).add(0x04)
+
+ let contentPtr = Memory.alloc(content.length * 2 + 2)
+ contentPtr.writeUtf16String(content)
+
+ const sizeOfStringStruct = Process.pointerSize * 5
+ let contentStruct = Memory.alloc(sizeOfStringStruct)
+
+ contentStruct
+ .writePointer(contentPtr).add(0x4)
+ .writeU32(content.length).add(0x4)
+ .writeU32(content.length * 2)
+
+
+ const ecxBuffer = Memory.alloc(0x2d8)
+
+ Memory.patchCode(txtAsm, Process.pageSize, code => {
+ var cw = new X86Writer(code, {
+ pc: txtAsm
+ })
+ cw.putPushfx()
+ cw.putPushax()
+
+ cw.putPushU32(0x0)
+ cw.putPushU32(0x0)
+ cw.putPushU32(0x0)
+ cw.putPushU32(0x1)
+ cw.putPushU32(0x0)
+
+ //cw.putMovRegReg
+
+ cw.putMovRegAddress('eax', contentStruct)
+ cw.putPushReg('eax')
+
+ cw.putMovRegAddress('edx', picWxid) //room_id
+
+ cw.putMovRegAddress('ecx', ecxBuffer)
+ cw.putCallAddress(moduleBaseAddress.add(
+ offset.sendTxtMsg.callOffset
+ ))
+
+ cw.putAddRegImm('esp', 0x18)
+ cw.putPopax()
+ cw.putPopfx()
+ cw.putRet()
+ cw.flush()
+
+ })
+
+ console.log('----------txtAsm', txtAsm)
+ const nativeativeFunction = new NativeFunction(ptr(txtAsm), 'void', [])
+ nativeativeFunction()
+
+})
+
+// 023 done
+/**
+* send at msg
+*/
+let asmAtMsg = null
+let roomid_, msg_, wxid_, atid_
+let ecxBuffer
+const sendAtMsgNativeFunction = ((roomId, text, contactId,nickname) => {
+
+ asmAtMsg = Memory.alloc(Process.pageSize)
+ ecxBuffer = Memory.alloc(0x3b0)
+
+ const atContent = '@'+nickname+' '+text
+
+ roomid_ = initStruct(roomId)
+ wxid_ = initidStruct(contactId)
+ msg_ = initmsgStruct(atContent)
+ atid_ = initAtMsgStruct(wxid_)
+
+ Memory.patchCode(asmAtMsg, Process.pageSize, code => {
+ var cw = new X86Writer(code, {
+ pc: asmAtMsg
+ })
+ cw.putPushfx()
+ cw.putPushax()
+
+ cw.putPushU32(0x0)
+ cw.putPushU32(0x0)
+ cw.putPushU32(0x0)
+ cw.putPushU32(0x1)
+ //cw.putPushU32(0x0)
+ cw.putMovRegAddress('eax', atid_)
+ cw.putPushReg('eax')
+
+ //cw.putMovRegReg
+
+ cw.putMovRegAddress('eax', msg_)
+ cw.putPushReg('eax')
+
+ cw.putMovRegAddress('edx', roomid_) //room_id
+
+ cw.putMovRegAddress('ecx', ecxBuffer)
+ cw.putCallAddress(moduleBaseAddress.add(
+ offset.sendTxtMsg.callOffset
+ ))
+
+ cw.putAddRegImm('esp', 0x18)
+ cw.putPopax()
+ cw.putPopfx()
+ cw.putRet()
+ cw.flush()
+
+ })
+
+ //console.log('----------txtAsm', asmAtMsg)
+ const nativeativeFunction = new NativeFunction(ptr(asmAtMsg), 'void', [])
+ nativeativeFunction()
+
+})
+
+// 022 done
+/**
+ *
+ * @param {*} contactId
+ * @param {*} path
+ */
+ const sendPicMsgNativeFunction = ((contactId, path) => {
+
+ const picAsm = Memory.alloc(Process.pageSize)
+ const buffwxid = Memory.alloc(0x20)
+ const picbuff = Memory.alloc(0x2D8)
+
+ let pathPtr = Memory.alloc(path.length * 2 + 1)
+ pathPtr.writeUtf16String(path)
+
+ let imagefilepath = Memory.alloc(0x24)
+ imagefilepath.writePointer(pathPtr).add(0x04)
+ .writeU32(path.length * 2).add(0x04)
+ .writeU32(path.length * 2).add(0x04)
+
+ let picWxidPtr = Memory.alloc(contactId.length * 2 + 1)
+ picWxidPtr.writeUtf16String(contactId)
+
+ let picWxid = Memory.alloc(0x0c)
+ picWxid.writePointer(ptr(picWxidPtr)).add(0x04)
+ .writeU32(contactId.length * 2).add(0x04)
+ .writeU32(contactId.length * 2).add(0x04)
+
+
+ //const test_offset1 = 0x701DC0;
+ Memory.patchCode(picAsm, Process.pageSize, code => {
+ var cw = new X86Writer(code, {
+ pc: picAsm
+ })
+ cw.putPushfx();
+ cw.putPushax();
+ cw.putCallAddress(moduleBaseAddress.add(
+ offset.sendPicMsg.call1
+ ))
+ cw.putMovRegReg('edx', 'eax') //缓存
+
+ cw.putSubRegImm('esp', 0x14)
+ cw.putMovRegAddress('eax', buffwxid)
+ cw.putMovRegReg('ecx', 'esp')
+ cw.putMovRegAddress('edi', imagefilepath)
+ cw.putPushReg('eax')
+ cw.putCallAddress(moduleBaseAddress.add(
+ offset.sendPicMsg.call2
+ ))
+
+ cw.putMovRegReg('ecx', 'edx')
+ cw.putMovRegAddress('eax', picWxid) //=lea
+ cw.putMovRegAddress('edi', imagefilepath)
+ cw.putPushReg('edi')
+ cw.putPushReg('eax')
+ cw.putMovRegAddress('eax', picbuff)
+ cw.putPushReg('eax')
+
+ cw.putMovRegAddress('edi', picWxid) //edi
+ cw.putCallAddress(moduleBaseAddress.add(
+ offset.sendPicMsg.call3
+ ))
+
+
+
+ cw.putPopax()
+ cw.putPopfx()
+ cw.putRet()
+ cw.flush()
+
+ })
+
+ //console.log('----------picAsm',picAsm)
+ const nativeativeFunction = new NativeFunction(ptr(picAsm), 'void', [])
+ nativeativeFunction()
+
+})
+
+// 020 done
+let memberNickBuffAsm = null
+let nickRoomId = null
+let nickMemberId = null
+let nickBuff = null
+const getChatroomMemberNickInfoFunction = ((memberId, roomId) => {
+
+ nickBuff = Memory.alloc(0x7e4)
+ //const nickRetAddr = Memory.alloc(0x04)
+ memberNickBuffAsm = Memory.alloc(Process.pageSize)
+ //console.log('asm address----------',memberNickBuffAsm)
+ nickRoomId = initidStruct(roomId)
+ //console.log('nick room id',nickRoomId)
+ nickMemberId = initStruct(memberId)
+
+ //console.log('nick nickMemberId id',nickMemberId)
+ //const nickStructPtr = initmsgStruct('')
+
+ Memory.patchCode(memberNickBuffAsm, Process.pageSize, code => {
+ var cw = new X86Writer(code, {
+ pc: memberNickBuffAsm
+ })
+ cw.putPushfx()
+ cw.putPushax()
+ cw.putMovRegAddress('edi', nickRoomId)
+ cw.putMovRegAddress('eax', nickBuff)
+ cw.putMovRegReg('edx', 'edi')
+ cw.putPushReg('eax')
+ cw.putMovRegAddress('ecx', nickMemberId)
+ cw.putCallAddress(moduleBaseAddress.add(0xC06F10))
+ cw.putAddRegImm('esp', 0x04)
+ cw.putPopax()
+ cw.putPopfx()
+ cw.putRet()
+ cw.flush()
+
+ })
+
+ const nativeativeFunction = new NativeFunction(ptr(memberNickBuffAsm), 'void', [])
+ nativeativeFunction()
+
+ const nickname = readWideString(nickBuff)
+ console.log('----nickname', nickname)
+ return readWideString(nickBuff)
+})
+
+// 013
+const isSupported = checkSupportedFunction()
+
+if (!isSupported) {
+ throw new Error(`Wechat version not supported. \nWechat version: ${getWechatVersionStringFunction()}, supported version: ${getWechatVersionStringFunction(availableVersion)}`)
+}
+
+// 015
+const hookLogoutEventCallback = (() => {
+ const nativeCallback = new NativeCallback(() => { }, 'void', ['int32'])
+ const nativeativeFunction = new NativeFunction(nativeCallback, 'void', ['int32'])
+ Interceptor.attach(moduleBaseAddress.add(offset.hook_on_logout_offset), {
+ onEnter: function (args) {
+ const bySrv = args[0].toInt32()
+ setImmediate(() => nativeativeFunction(bySrv))
+ }
+ })
+ return nativeCallback
+})()
+
+// 016
+const hookLoginEventCallback = (() => {
+ const nativeCallback = new NativeCallback(() => { }, 'void', [])
+ const nativeativeFunction = new NativeFunction(nativeCallback, 'void', [])
+ Interceptor.attach(moduleBaseAddress.add(offset.hook_on_login_offset), {
+ onLeave: function (retval) {
+ isLoggedInFunction()
+ setImmediate(() => nativeativeFunction())
+ return retval
+ }
+ })
+
+ setTimeout(() => {
+ if (isLoggedInFunction()) {
+ setImmediate(() => nativeativeFunction())
+ }
+ }, 500);
+
+ return nativeCallback
+})()
+
+// 017
+const checkQRLoginNativeCallback = (() => {
+
+ const nativeCallback = new NativeCallback(() => { }, 'void', ['int32', 'pointer', 'pointer', 'pointer', 'pointer', 'pointer', 'int32', 'pointer'])
+ const nativeativeFunction = new NativeFunction(nativeCallback, 'void', ['int32', 'pointer', 'pointer', 'pointer', 'pointer', 'pointer', 'int32', 'pointer'])
+ // const json = {
+ // status,
+ // uuid,
+ // wxid,
+ // avatarUrl,
+ // nickname,
+ // phoneType,
+ // phoneClientVer,
+ // pairWaitTip,
+ // }
+
+ const callback = {
+ onLeave: function (retval) {
+ const json = getQrcodeLoginData()
+ if (json.status == 0) {
+ // 当状态为 0 时,即未扫码。而其他状态会触发另一个方法,拥有更多数据。
+ ret(json)
+ }
+ return retval
+ },
+ }
+
+ const ret = (json) => {
+ const arr = [
+ json.status || 0,
+ Memory.allocUtf8String(json.uuid ? `http://weixin.qq.com/x/${json.uuid}` : ''),
+ Memory.allocUtf8String(json.wxid || ''),
+ Memory.allocUtf8String(json.avatarUrl || ''),
+ Memory.allocUtf8String(json.nickname || ''),
+ Memory.allocUtf8String(json.phoneType || ''),
+ json.phoneClientVer || 0,
+ Memory.allocUtf8String(json.pairWaitTip || ''),
+ ]
+ setImmediate(() => nativeativeFunction(...arr))
+ }
+
+ Interceptor.attach(moduleBaseAddress.add(offset.hook_get_login_qr_offset), callback)
+ Interceptor.attach(moduleBaseAddress.add(offset.hook_check_login_qr_offset), callback)
+ Interceptor.attach(moduleBaseAddress.add(offset.hook_save_login_qr_info_offset), {
+ onEnter: function () {
+ const qrNotify = this.context['ebp'].sub(72)
+ const uuid = readString(qrNotify.add(4).readPointer())
+ const wxid = readString(qrNotify.add(8).readPointer())
+ const status = qrNotify.add(16).readUInt()
+ const avatarUrl = readString(qrNotify.add(24).readPointer())
+ const nickname = readString(qrNotify.add(28).readPointer())
+ const pairWaitTip = readString(qrNotify.add(32).readPointer())
+ const phoneClientVer = qrNotify.add(40).readUInt()
+ const phoneType = readString(qrNotify.add(44).readPointer())
+
+ const json = {
+ status,
+ uuid,
+ wxid,
+ avatarUrl,
+ nickname,
+ phoneType,
+ phoneClientVer,
+ pairWaitTip,
+ }
+ ret(json)
+ },
+ onLeave: function (retval) {
+ return retval
+ },
+ })
+
+ if (!isLoggedInFunction()) {
+ setTimeout(() => {
+ const json = getQrcodeLoginData()
+ ret(json)
+ }, 100);
+ }
+
+ return nativeCallback
+})()
+
+// 018
+const getQrcodeLoginData = () => {
+ const getQRCodeLoginMgr = new NativeFunction(moduleBaseAddress.add(offset.get_qr_login_data_offset), 'pointer', [])
+ const qlMgr = getQRCodeLoginMgr()
+
+ const json = {
+ status: 0,
+ uuid: '',
+ wxid: '',
+ avatarUrl: '',
+ }
+
+ if (!qlMgr.isNull()) {
+ json.uuid = readString(qlMgr.add(8))
+ json.status = qlMgr.add(40).readUInt()
+ json.wxid = readString(qlMgr.add(44))
+ json.avatarUrl = readString(qlMgr.add(92))
+ }
+ return json
+}
+
+
+/**
+ * 20220504 writelog
+ * 7A566D72 | FFB5 ECFEFFFF | push dword ptr ss:[ebp-114] | 【3.6.0.18】写日志,这个里面就是日志内容
+ 7A566D78 | FFB5 E8FEFFFF | push dword ptr ss:[ebp-118] |
+ */
+/*const writeLogNativeCallback = (() => {
+ const nativeCallback = new NativeCallback(() => { }, 'void', [])
+ const nativeCallFunction = new NativeFunction(nativeCallback, 'void', [])
+
+ Interceptor.attach(
+ moduleBaseAddress.add(0x1576D7E),
+ {
+ onEnter() {
+ const addr = this.context.ebp.sub(0x114)//0xc30-0x08
+ console.log('-------',addr)
+
+ }
+ })
+ return nativeCallback
+})()*/
+
+let nickRoomIdV6 = null
+let nullEdiWxidStructV6 = null
+let nickMemberIdStructV6 = null
+let memberNickBuffAsmV6 = null
+let nickResultEdiV6 = null
+
+const getChatroomMemberNickInfoV1Function = ((memberId, roomId) => {
+ nickRoomIdV6 = initidStruct(roomId)
+ nullEdiWxidStructV6 = initNullIdStruct('')
+ nickMemberIdStructV6 = initStruct(memberId)
+ memberNickBuffAsmV6 = Memory.alloc(Process.pageSize)
+ console.log('-----', memberNickBuffAsmV6)
+
+ const tmp = (moduleBaseAddress.add(
+ offset.chatroom_member_nick_esi_offset_v6
+ )).readU32()
+ console.log('=======tmp', tmp)
+ Memory.patchCode(memberNickBuffAsmV6, Process.pageSize, code => {
+ var cw = new X86Writer(code, { pc: memberNickBuffAsmV6 })
+ cw.putPushfx();
+ cw.putPushax();
+
+ cw.putMovRegAddress('edi', nullEdiWxidStructV6)
+ cw.putMovRegAddress('eax', nickMemberIdStructV6)
+ cw.putMovRegAddress('ebx', nickRoomIdV6)
+
+
+ cw.putMovRegAddress('esi', ptr(tmp))
+ cw.putPushReg('edi')
+ cw.putPushReg('eax')
+ cw.putPushReg('ebx')
+
+ cw.putMovRegAddress('ecx', ptr(tmp))
+
+ cw.putCallAddress(moduleBaseAddress.add(
+ offset.chatroom_member_nick_call_offset_v6
+ ))
+
+
+ //cw.putMovNearPtrReg(nickResultEdiV6, 'edi')
+ cw.putPopax()
+ cw.putPopfx()
+ cw.putRet()
+ cw.flush()
+
+ })
+
+ const nativeativeFunction = new NativeFunction(ptr(memberNickBuffAsmV6), 'void', [])
+ nativeativeFunction()
+
+ console.log('---------nullEdiWxidStructV6', nullEdiWxidStructV6)
+ const nickha = readWideString(nullEdiWxidStructV6)
+
+ console.log('-----------------')
+ console.log(nickha)
+ console.log('-----------------')
+ return readWideString(nullEdiWxidStructV6)
+})
+
+/**
+* send attatch
+*/
+let attatchWxid = null
+let attatchPath = null
+let attatchPathPtr = null
+let attatchAsm = null
+let attatchBuf = null
+
+let attatchReceiveIdPtr = null
+let attatchReceiveId = null
+
+let attatchSendId = null
+let attatchSendIdPtr = null
+
+/*
+let attatchEbp2C = null
+let attatchEDIPtr = null
+let attatchEDIU32 = null
+let attatchECX = null
+
+let attatchEbp210 = null
+let attatchEbpAc = null*/
+
+let attatchEbp11E8 = null
+let attatchEbpCC = null
+let attatchEbp368 = null
+let attatchEAX = null
+
+let sFileName = null
+let fileNamePtr = null
+
+let attatchEbp84 = null
+let attatchECX = null
+
+
+/**
+ *
+param {78EDBC86 | 8B80 38040000 | mov eax,dword ptr ds:[eax+438] |
+78EDBC8C | 8BB0 800B0000 | mov esi,dword ptr ds:[eax+B80] |} sendWxid
+*/
+
+// 021
+const sendAttatchMsgNativeFunction = ((contactId, senderId, path, filename, size) => {
+
+ attatchAsm = Memory.alloc(Process.pageSize)
+ console.log('--------------address', attatchAsm)
+
+ fileNamePtr = Memory.alloc(filename.length * 2 + 2)
+ fileNamePtr.writeUtf16String(filename)
+
+ sFileName = Memory.alloc(0x14)
+ sFileName.writePointer(ptr(fileNamePtr)).add(0x04)
+ .writeU32(fileNamePtr.length * 2).add(0x04)
+ .writeU32(fileNamePtr.length * 2).add(0x08)
+
+ //const fileSize = size.toInt32()
+
+
+ attatchReceiveIdPtr = Memory.alloc(contactId.length * 2 + 2)
+ attatchReceiveIdPtr.writeUtf16String(contactId)
+
+ attatchReceiveId = Memory.alloc(0x14)
+ attatchReceiveId.writePointer(ptr(attatchReceiveIdPtr)).add(0x04)
+ .writeU32(contactId.length * 2).add(0x04)
+ .writeU32(contactId.length * 2).add(0x08)
+
+ attatchSendIdPtr = Memory.alloc(senderId.length * 2 + 2)
+ attatchSendIdPtr.writeUtf16String(senderId)
+
+ attatchSendId = Memory.alloc(0x14)
+ attatchSendId.writePointer(ptr(attatchSendIdPtr)).add(0x04)
+ .writeU32(senderId.length * 2).add(0x04)
+ .writeU32(senderId.length * 2).add(0x08)
+
+ attatchPathPtr = Memory.alloc(path.length * 2 + 2)
+ attatchPathPtr.writeUtf16String(path)
+
+ attatchPath = Memory.alloc(0x28)
+ attatchPath.writePointer(attatchPathPtr).add(0x04)
+ .writeU32(path.length * 2).add(0x04)
+ .writeU32(path.length * 2).add(0x04)
+
+ attatchEbp11E8 = Memory.alloc(0xBE4)
+ attatchEbpCC = Memory.alloc(0x14)
+ attatchEbp368 = Memory.alloc(0x290)
+ attatchEbp84 = Memory.alloc(0x18)
+ attatchEAX = Memory.alloc(0x18)
+
+ attatchECX = moduleBaseAddress.add(0x222f178).toInt32()
+
+ //console.log('basename',path.basename(path))
+ //return
+
+ /**
+ * -------------buffer-------------------------------
+ */
+
+ Memory.patchCode(attatchAsm, Process.pageSize, code => {
+ var cw = new X86Writer(code, { pc: attatchAsm })
+ cw.putPushfx()
+ cw.putPushax()
+
+ cw.putMovRegAddress('ecx', attatchEbp11E8)
+ cw.putCallAddress(moduleBaseAddress.add(0xE1590))
+
+ cw.putPushU32(-1)
+ cw.putPushU32(moduleBaseAddress.add(0x1E1B3C0).toInt32())
+ cw.putMovRegAddress('ecx', attatchEbp11E8.add(0x4))//11e4
+ cw.putCallAddress(moduleBaseAddress.add(0x702410))//write appid
+ // cw.putCallAddress(moduleBaseAddress.add(0x702410))//write appid
+
+ /**
+ * 78482B8D | 6A FF | push FFFFFFFF |
+ 78482B8F | 68 B895E979 | push wechatwin.79E995B8 | 79E995B8:L"0"
+ 78482B94 | 8D8D 48EEFFFF | lea ecx,dword ptr ss:[ebp-11B8] |
+ 78482B9A | E8 71F83600 | call wechatwin.787F2410 | 此处继续写ebp-11b8
+ */
+ cw.putPushU32(-1)
+ cw.putPushU32(moduleBaseAddress.add(0x1DA95B8).toInt32())
+ cw.putMovRegAddress('ecx', attatchEbp11E8.add(0x30))//11B8
+ cw.putCallAddress(moduleBaseAddress.add(0x702410))
+
+ cw.putMovRegU32('eax', 0x6)
+ cw.putMovNearPtrReg(attatchEbp11E8.add(0x80), 'eax')//1168
+ cw.putMovRegU32('eax', size)//file size
+ cw.putMovNearPtrReg(attatchEbp11E8.add(0x108), 'eax')//10e0
+
+
+ cw.putMovRegAddress('eax', sFileName)
+ cw.putPushReg('eax')
+ cw.putMovRegAddress('ecx', attatchEbp11E8.add(0x44))//11a4=0x11e8-0x160
+ cw.putCallAddress(moduleBaseAddress.add(0x702980))//write filename
+
+ cw.putMovRegAddress('eax', attatchSendId)
+ cw.putPushReg('eax')
+ cw.putMovRegAddress('ecx', attatchEbp11E8.add(0x160))//1088=0x11e8-0x160
+ cw.putCallAddress(moduleBaseAddress.add(0x702980))
+
+
+ cw.putMovRegAddress('eax', attatchEbpCC)
+ cw.putPushReg('eax')
+ cw.putMovRegAddress('ecx', attatchEbp11E8)
+ cw.putCallAddress(moduleBaseAddress.add(0x617C30))
+
+ cw.putMovRegAddress('ecx', attatchEbp368)
+ cw.putCallAddress(moduleBaseAddress.add(0x954F0))
+
+ cw.putPushU32(-1)
+ cw.putPushU32((moduleBaseAddress.add(0x1D8F248)).toInt32())
+ cw.putMovRegAddress('ecx', attatchEbp84)
+ cw.putCallAddress(moduleBaseAddress.add(0x701CD0))
+
+ cw.putMovRegAddress('ecx', attatchPath)
+ cw.putPushU32(0x6)
+ cw.putMovRegAddress('edx', attatchEbp11E8.add(0x160))//1088
+ //cw.putMovRegAddress('eax',attatchEAX)
+ cw.putPushReg('ecx')
+ cw.putPushReg('eax')
+
+ cw.putMovRegAddress('eax', attatchEbpCC)
+ cw.putPushReg('eax')
+
+ cw.putMovRegAddress('eax', attatchReceiveId)
+ cw.putPushReg('eax')
+
+ cw.putMovRegAddress('ecx', attatchEbp368)
+ cw.putCallAddress(moduleBaseAddress.add(0x391F80))
+ cw.putAddRegImm('esp', 0x14)
+
+
+ cw.putPushU32(moduleBaseAddress.add(0x223EC34).toInt32())
+ cw.putPushU32(moduleBaseAddress.add(0x223EC34).toInt32())
+ //cw.putMovRegU32('edx',0xAD0001) 两行代码都可以
+ cw.putAddRegImm('edx', 0x1)
+ cw.putMovRegAddress('ecx', attatchEbp368)
+ cw.putCallAddress(moduleBaseAddress.add(0x392150))
+ cw.putAddRegImm('esp', 0x8)
+
+
+
+ //cw.putMovRegAddress('ecx', attatchEbp368)
+ //cw.putCallAddress(moduleBaseAddress.add(0x63B4F0))
+ // 7B53F178
+ //cw.putMovRegU32('ecx', attatchEbpCC.add(0x3c).toInt32())//ebp-90
+ //cw.putMovNearPtrReg(attatchEbpCC.add(0x64), 'eax')//ebp-68
+ //cw.putAddRegImm('ecx', 0x8)
+ //cw.putMovRegAddress('eax', attatchEbp368.add(0x64))//ebp-68
+
+ //cw.putMovRegU32('ecx',attatchECX)
+ //cw.putPushReg('eax')
+ //cw.putMovRegAddress('eax', attatchEbpCC.add(0x40))//ebp-8c
+ //cw.putPushReg('eax')
+ //cw.putCallAddress(moduleBaseAddress.add(0xC9D30))
+ //cw.putCallAddress(moduleBaseAddress.add(0x522590))
+ //78483063 | E8 28F51800 | call wechatwin.78612590 |
+
+
+ //78483039 | 8D8D 98FCFFFF | lea ecx,dword ptr ss:[ebp-368] |
+ //7848303F | E8 AC842A00 | call wechatwin.7872B4F0 |
+ //cw.putMovRegAddress('ecx', attatchEbp368)
+ //cw.putCallAddress(moduleBaseAddress.add(0x63B4F0))
+
+ // 78F33099 | 8D8D 34FFFFFF | lea ecx,dword ptr ss:[ebp-CC] |
+ //78F3309F | E8 AC0FD0FF | call wechatwin.78C34050 |
+
+ //cw.putMovRegAddress('ecx',attatchEbpCC)
+ //cw.putCallAddress(moduleBaseAddress.add(0x94050))
+
+ /**
+ * 78F3307F | 8B4D AC | mov ecx,dword ptr ss:[ebp-54] |
+ 78F33082 | 8D85 98FCFFFF | lea eax,dword ptr ss:[ebp-368] |
+ 78F33088 | 50 | push eax |
+ 78F33089 | E8 82DACFFF | call wechatwin.78C30B10 |
+
+ cw.putMovRegAddress('ecx', attatchEbp54)
+ cw.putMovRegAddress('eax', attatchEbp368)
+ cw.putPushReg('eax')
+ cw.putCallAddress(moduleBaseAddress.add(0x90B10))*/
+
+ cw.putPopax()
+ cw.putPopfx()
+ cw.putRet()
+ cw.flush()
+
+ })
+
+ const nativeativeFunction = new NativeFunction(ptr(attatchAsm), 'void', [])
+ nativeativeFunction()
+ /*console.log(hexdump(attatchEbp11E8.add(0x80), {
+ offset: 0,
+ length: 0x40,
+ header: true,
+ ansi: true
+ }))*/
+ //console.log('')
+ /*console.log(hexdump(attatchEbpCC.add(0x160), {
+ offset: 0,
+ length: 0x64,
+ header: true,
+ ansi: true
+ }))*/
+ //console.log('-------',attatchEbp1C.readPointer())
+ //console.log('-------',attatchEbp1C.add(0x4).readPointer())
+ //console.log('-------',attatchEbp1C.add(0x8).readPointer())
+})
+/*------------------send pic --------------------------
+let buffwxid = null
+let imagefilepath = null
+let pathPtr = null
+let picWxid = null
+let picWxidPtr = null
+let picAsm = null
+let picbuff = null
+const sendPicMsgNativeFunction = ((contactId, path) => {
+
+ picAsm = Memory.alloc(Process.pageSize)
+ buffwxid = Memory.alloc(0x20)
+ picbuff = Memory.alloc(0x378)
+
+ pathPtr = Memory.alloc(path.length * 2 + 1)
+ pathPtr.writeUtf16String(path)
+
+ imagefilepath = Memory.alloc(0x24)
+ imagefilepath.writePointer(pathPtr).add(0x04)
+ .writeU32(path.length * 2).add(0x04)
+ .writeU32(path.length * 2).add(0x04)
+
+ picWxidPtr = Memory.alloc(contactId.length * 2 + 1)
+ picWxidPtr.writeUtf16String(contactId)
+
+ picWxid = Memory.alloc(0x0c)
+ picWxid.writePointer(ptr(picWxidPtr)).add(0x04)
+ .writeU32(contactId.length * 2).add(0x04)
+ .writeU32(contactId.length * 2).add(0x04)
+
+ Memory.patchCode(picAsm, Process.pageSize, code => {
+ var cw = new X86Writer(code, { pc: picAsm })
+ cw.putPushfx();
+ cw.putPushax();
+
+ cw.putSubRegImm('esp', 0x14)
+ cw.putMovRegAddress('eax', buffwxid)
+
+ cw.putMovRegReg('ecx', 'esp')
+
+ cw.putPushReg('eax')
+ cw.putCallAddress(moduleBaseAddress.add(
+ offset.send_picmsg_call_offset1
+ ))
+
+ cw.putMovRegAddress('ebx', imagefilepath)
+ cw.putPushReg('ebx')
+
+ cw.putMovRegAddress('eax', picWxid)
+ cw.putPushReg('eax')
+
+ cw.putMovRegAddress('eax', picbuff)
+ cw.putPushReg('eax')
+ cw.putCallAddress(moduleBaseAddress.add(
+ offset.send_picmsg_call_offset2
+ ))
+
+ cw.putMovRegReg('ecx', 'eax')
+ cw.putCallAddress(moduleBaseAddress.add(
+ offset.send_picmsg_call_offset3
+ ))
+ cw.putPopax()
+ cw.putPopfx()
+ cw.putRet()
+ cw.flush()
+
+ })
+
+ const nativeativeFunction = new NativeFunction(ptr(picAsm), 'void', [])
+ nativeativeFunction()
+
+})*/
+
+// 025
+const callLoginQrcodeFunction = ((forceRefresh = false) => {
+ const json = getQrcodeLoginData()
+ if (!forceRefresh && json.uuid) {
+ return
+ }
+
+ const callAsm = Memory.alloc(Process.pageSize)
+ const loginWnd = moduleBaseAddress.add(offset.get_login_wnd_offset).readPointer()
+
+ Memory.patchCode(callAsm, Process.pageSize, code => {
+ var cw = new X86Writer(code, { pc: callAsm })
+ cw.putPushfx();
+ cw.putPushax();
+
+ cw.putMovRegAddress('ecx', loginWnd)
+ cw.putCallAddress(moduleBaseAddress.add(offset.get_qr_login_call_offset))
+
+ cw.putPopax()
+ cw.putPopfx()
+ cw.putRet()
+ cw.flush()
+ })
+
+ const nativeativeFunction = new NativeFunction(ptr(callAsm), 'void', [])
+ nativeativeFunction()
+})
+
+
+// 026
+const agentReadyCallback = (() => {
+ const nativeCallback = new NativeCallback(() => { }, 'void', [])
+ const nativeativeFunction = new NativeFunction(nativeCallback, 'void', [])
+
+ setTimeout(() => {
+ nativeativeFunction()
+ }, 500);
+ return nativeCallback
+})()
+
+// 027
+const SendMiniProgramNativeFunction = ((bg_path_str, send_wxid_str, recv_wxid_str, xmlstr) => {
+ console.log("------------------------------------------------------");
+ var asmCode = Memory.alloc(Process.pageSize);
+
+ var ECX_buf = Memory.alloc(0x300);
+ var Buf_EAX = Memory.alloc(0x300);
+ var buf_1 = Memory.alloc(0x300);
+ var ptr_to_buf_1 = Memory.alloc(0x4).writePointer(buf_1);
+ var buf_2 = Memory.alloc(0x300);
+
+ // var bg_path_str="C:/aaaa.jpg";
+ var bg_path_Ptr = Memory.alloc(bg_path_str.length * 2 + 1)
+ bg_path_Ptr.writeUtf16String(bg_path_str);
+ var bg_path_Struct = Memory.alloc(0x14) // returns a NativePointer
+ bg_path_Struct.writePointer(bg_path_Ptr).add(0x04)
+ .writeU32(bg_path_str.length * 2).add(0x04)
+ .writeU32(bg_path_str.length * 2).add(0x04)
+ .writeU32(0).add(0x04)
+ .writeU32(0);
+
+ // var send_wxid_str="wxid_4zr616ir6fi122";
+ var send_wxid_Ptr = Memory.alloc(send_wxid_str.length * 2 + 1)
+ send_wxid_Ptr.writeUtf16String(send_wxid_str);
+ var send_wxid_Struct = Memory.alloc(0x14) // returns a NativePointer
+ send_wxid_Struct.writePointer(send_wxid_Ptr).add(0x04)
+ .writeU32(send_wxid_str.length * 2).add(0x04)
+ .writeU32(send_wxid_str.length * 2).add(0x04)
+ .writeU32(0).add(0x04)
+ .writeU32(0);
+
+ // var recv_wxid_str="filehelper";
+ var recv_wxid_Ptr = Memory.alloc(recv_wxid_str.length * 2 + 1)
+ recv_wxid_Ptr.writeUtf16String(recv_wxid_str);
+ var recv_wxid_Struct = Memory.alloc(0x14) // returns a NativePointer
+ recv_wxid_Struct.writePointer(recv_wxid_Ptr).add(0x04)
+ .writeU32(recv_wxid_str.length * 2).add(0x04)
+ .writeU32(recv_wxid_str.length * 2).add(0x04)
+ .writeU32(0).add(0x04)
+ .writeU32(0);
+
+ // vvar pXml=initidStruct('wxid_4zr616ir6fi1220腾讯出行服务|加油代驾公交view330https://mp.weixin.qq.com/mp/waerrpage?appid=wx65cc950f42e8fff1&type=upgrade&upgradetype=3#wechat_redirecthttp://mmbiz.qpic.cn/mmbiz_png/NM1fK7leWGPaFnMAe95jbg4sZAI3fkEZWHq69CIk6zA00SGARbmsGTbgLnZUXFoRwjROelKicbSp9K34MaZBuuA/640?wx_fmt=png&wxfrom=200腾讯出行服务|加油代驾公交0gh_ad64296dc8bd@appwx65cc950f42e8fff11http://mmbiz.qpic.cn/mmbiz_png/NM1fK7leWGPaFnMAe95jbg4sZAI3fkEZWHq69CIk6zA00SGARbmsGTbgLnZUXFoRwjROelKicbSp9K34MaZBuuA/640?wx_fmt=png&wxfrom=20002_wx65cc950f42e8fff1_875237370_1644979747_11Window wechat');
+
+ var pXml = initidStruct(xmlstr)
+
+ console.log(send_wxid_Struct);
+ console.log(recv_wxid_Struct);
+ console.log(pXml);
+ console.log("okkk");
+
+ console.log("------------------------------------------------------");
+
+ Memory.patchCode(asmCode, Process.pageSize, code => {
+ var cw = new X86Writer(code, { pc: asmCode })
+ cw.putPushfx();
+ cw.putPushax();
+ cw.putMovRegReg('ecx', 'ecx');
+ cw.putMovRegAddress('ecx', ECX_buf);
+ cw.putCallAddress(moduleBaseAddress.add(0x69BB0)); //init ecx
+
+ cw.putPushU32(0x21);
+
+
+ cw.putPushNearPtr(ptr_to_buf_1); //ptr
+ cw.putPushU32(bg_path_Struct.toInt32());
+ cw.putPushU32(pXml.toInt32());
+ cw.putPushU32(recv_wxid_Struct.toInt32());
+
+ cw.putMovRegAddress('edx', send_wxid_Struct);
+ cw.putMovRegAddress('ecx', ECX_buf);
+ cw.putCallAddress(moduleBaseAddress.add(0x2E2420));
+ cw.putAddRegImm('esp', 0x14)
+
+ cw.putPushU32(Buf_EAX.toInt32());
+ cw.putMovRegAddress('ecx', ECX_buf);
+ cw.putCallAddress(moduleBaseAddress.add(0x94C10));
+
+ cw.putPushU32(moduleBaseAddress.add(0x1DCB46C).toInt32());
+ cw.putPushU32(moduleBaseAddress.add(0x1DCB46C).toInt32());
+ cw.putMovRegAddress('ecx', ECX_buf);
+ cw.putCallAddress(moduleBaseAddress.add(0x2E2630));
+ cw.putAddRegImm('esp', 0x8)
+
+ cw.putPopax();
+ cw.putPopfx();
+ cw.putRet();
+ cw.flush();
+ })
+
+ const nativeativeFunction = new NativeFunction(ptr(asmCode), 'void', [])
+ nativeativeFunction()
+
+
+})
\ No newline at end of file
diff --git a/src/init-agent-script.js b/src/init-agent-script.js
index 6ae2c78..f706c38 100644
--- a/src/init-agent-script.js
+++ b/src/init-agent-script.js
@@ -1,75 +1,197 @@
/**
- * WeChat 3.2.1.121
* > Special thanks to: @cixingguangming55555 老张学技术
*
* Credit: https://github.com/cixingguangming55555/wechat-bot
- * Source: https://pan.baidu.com/s/1OmX2lxNOYHyGsl_3ByhsoA
- * 《源码3.2.1.121》提取码: 1rfa
- * WeChat: https://pan.baidu.com/share/init?surl=IHRM2OMvrLyuCz5MRbigGg
- * 微信:3.2.1.121 提取码: cscn
*/
//https://blog.csdn.net/iloveitvm/article/details/109119687 frida学习
//const { isNullishCoalesce } = require("typescript")
-//3.6.0.18
+//3.9.2.23
+// 偏移地址集合 done
const offset = {
- /**---nick call */
- chatroom_member_nick_call_offset_v6: 0x3E47B0,//3.6.0.18
- chatroom_member_nick_esi_offset_v6: 0x22553D4,
- /**-- nick call */
- node_offset: 0x222f3bc,//0x1db9728 -- 3.3.0.155
- handle_offset: 0x4c,
- send_txt_call_offset: 0x4BE7B0,//0x3e3b80
- hook_point: 0x4E94F2,//0x4E9464,//3.3.0.115 = 0x40d3b1
- chatroom_node_offset: 0xad8,
- nickname_offset: 0x222EBB4,
- wxid_offset: 0x222F020,
- head_img_url_offset: 0x222EE94,
- is_logged_in_offset: 0x1DDF9D4,
- hook_on_login_offset: 0x51B790,
- hook_on_logout_offset: 0x51C2C0,
- hook_get_login_qr_offset: 0x4B6020,
- hook_check_login_qr_offset: 0x478B90,
- hook_save_login_qr_info_offset: 0x3DB2E0,
- get_login_wnd_offset: 0x1DB96A4,
- get_qr_login_data_offset: 0x282160,
- get_qr_login_call_offset: 0x286930,
- //-------3.6.0.18 send pic
- send_picmsg_call_offset0: 0x9A1C0,//assign value to ecx
- send_picmsg_call_offset1: 0x4BE160,//0x5ccb50,
- send_picmsg_call_ecx: 0x222F0F0,
- //-------3.6.0.18 send pic
- /*send_picmsg_call_offset2: 0x6f5c0,
- send_picmsg_call_offset3: 0x3e3490,*/
- send_attatch_ecx_offset: 0x1D8FA8C,
- send_attatch_call_offset0: 0x9A1C0,
- send_attatch_call_offset1: 0x701DC0,//0x701CD0,//701CD0
- send_attatch_call_offset2: 0x4BA5F0,//4B A5F0
- send_attatch_call_offset3: 0xC95A0,
- send_attatch_call_offset4: 0x94200,
- send_attatch_call_offset5: 0x3C4950,
- send_attatch_call_offset6: 0x63B4F0,
- send_attatch_call_para1: 0x1D8F248,
- send_attatch_call_para2: 0x19a7350,
- chatroom_member_nick_call_offset1: 0x558cb0,
- chatroom_member_nick_call_offset2: 0x3b0fe0,
- chatroom_member_nick_call_offset3: 0x55f6e0,
- chatroom_member_nick_call_offset4: 0x34cb10,
+ hook_point: 0xd19a0b, //3.9.2.23
+ myselfinfo: {
+ offset: 0x2FFD484, //老版本微信号偏移,后面的地址,都要在这个偏移上增加
+ //wxid_len:0x10,
+ head_img_url: 0x2D8,
+ head_img_url_len: 0x2E8,
+ wx_nick_name: 0x10C,
+ wxcode_new: 0x64, //新版本微信号
+ //wxcode_len:0x74
+ wxid_len_offset: 0x4D4
+ },
+ contactInfo: {
+ nodeOffset: 0x2FFDD7C,
+ nodeRootOffset: 0x64
+ },
+ chatroomInfo: {
+ nodeOffset: 0x2FFDDC8,
+ nodeRootOffset: 0x8c8
+ },
+ sendTxtMsg: {
+ callOffset: 0xCE6C80
+ },
+ sendPicMsg: {
+ call1: 0x768140,
+ call2: 0xf59e40,
+ call3: 0xce6640
+ }
};
-//3.3.0.115
-
+//3.9.2.23
+// 全局配置 done
/*------------------global-------------------------------------------*/
-const availableVersion = 1661337618////3.3.0.115 ==1661141107
+const availableVersion = 1661534743 ////3.9.2.23 ==0x63090217
const moduleBaseAddress = Module.getBaseAddress('WeChatWin.dll')
const moduleLoad = Module.load('WeChatWin.dll')
//1575CF98
+
+// 全局变量 tbd
const g_EDIPtr = moduleBaseAddress.add(0x222f38c).readPointer().add(0xD70).readPointer()//
const g_EDIU32 = moduleBaseAddress.add(0x222f38c).readPointer().add(0xD70).readU32()
+
+/*------------------global-------------------------------------------*/
+
+/*---------------base -------------------------*/
+
+// done
+let retidPtr=null
+let retidStruct=null
+const initidStruct = ((str) => {
+
+ retidPtr = Memory.alloc(str.length * 2 + 1)
+ retidPtr.writeUtf16String(str)
+
+ retidStruct = Memory.alloc(0x14) // returns a NativePointer
+
+ retidStruct
+ .writePointer(retidPtr).add(0x04)
+ .writeU32(str.length * 2).add(0x04)
+ .writeU32(str.length * 2).add(0x04)
+ .writeU32(0).add(0x04)
+ .writeU32(0)
+
+ return retidStruct
+})
+
+// done
+let retPtr = null
+let retStruct = null
+const initStruct = ((str) => {
+
+ retPtr = Memory.alloc(str.length * 2 + 1)
+ retPtr.writeUtf16String(str)
+
+ retStruct = Memory.alloc(0x14) // returns a NativePointer
+
+ retStruct
+ .writePointer(retPtr).add(0x04)
+ .writeU32(str.length * 2).add(0x04)
+ .writeU32(str.length * 2).add(0x04)
+ .writeU32(0).add(0x04)
+ .writeU32(0)
+
+ return retStruct
+})
+
+// done
+let msgstrPtr=null
+let msgStruct=null
+const initmsgStruct = ((str) => {
+ msgstrPtr = Memory.alloc(str.length * 2 + 1)
+ msgstrPtr.writeUtf16String(str)
+
+ msgStruct = Memory.alloc(0x14) // returns a NativePointer
+
+ msgStruct
+ .writePointer(msgstrPtr).add(0x04)
+ .writeU32(str.length * 2).add(0x04)
+ .writeU32(str.length * 2).add(0x04)
+ .writeU32(0).add(0x04)
+ .writeU32(0)
+
+ return msgStruct
+})
+
+// tbd
+let retidNullStruct = null
+let retidNullPtr = null
+const initNullIdStruct = ((str) => {
+
+ retidNullPtr = Memory.alloc(str.length * 2 + 1)
+ retidNullPtr.writeUtf16String(str)
+
+ retidNullStruct = Memory.alloc(0x14) // returns a NativePointer
+
+ retidNullStruct
+ .writePointer(retidNullPtr).add(0x04)
+ .writeU32(str.length * 2).add(0x04)
+ .writeU32(str.length * 2).add(0x04)
+ .writeU32(0).add(0x04)
+ .writeU32(0)
+
+ return retidNullStruct
+})
+
+// done
+/**
+* at msg structure
+*/
+let atStruct = null
+const initAtMsgStruct = ((wxidStruct) => {
+
+ atStruct = Memory.alloc(0x10)
+
+ atStruct.writePointer(wxidStruct).add(0x04)
+ .writeU32(wxidStruct.toInt32() + 0x14).add(0x04)//0x14 = sizeof(wxid structure)
+ .writeU32(wxidStruct.toInt32() + 0x14).add(0x04)
+ .writeU32(0)
+ return atStruct
+})
+
+// done
+// std::string
+// const str = readStringPtr(ptr).readUtf8String()
+const readStringPtr = (address) => {
+ const addr = ptr(address)
+ const size = addr.add(16).readU32()
+ const capacity = addr.add(20).readU32()
+ addr.ptr = addr
+ addr.size = size
+ addr.capacity = capacity
+ if (capacity > 15 && !addr.readPointer().isNull()) {
+ addr.ptr = addr.readPointer()
+ }
+ addr.ptr._readCString = addr.ptr.readCString
+ addr.ptr._readAnsiString = addr.ptr.readAnsiString
+ addr.ptr._readUtf8String = addr.ptr.readUtf8String
+ addr.readCString = () => { return addr.size ? addr.ptr._readCString(addr.size) : '' }
+ addr.readAnsiString = () => { return addr.size ? addr.ptr._readAnsiString(addr.size) : '' }
+ addr.readUtf8String = () => { return addr.size ? addr.ptr._readUtf8String(addr.size) : '' }
+
+ // console.log('readStringPtr() address:',address,' -> str ptr:', addr.ptr, 'size:', addr.size, 'capacity:', addr.capacity)
+ // console.log('readStringPtr() str:' , addr.readUtf8String())
+ // console.log('readStringPtr() address:', addr,'dump:', addr.readByteArray(24))
+
+ return addr
+}
+
+// done
+const readString = (address) => {
+ return readStringPtr(address).readUtf8String()
+}
+
+// done
+const readWideString = (address) => {
+ return readWStringPtr(address).readUtf16String()
+}
+
+/*-----------------base-------------------------*/
+
let currentVersion = 0
let nodeList = [] //for contact
@@ -79,8 +201,6 @@ let chatroomNodeList = [] //for chatroom
let chatroomMemberList = []//for chatroom
let loggedIn = false
-/*------------------global-------------------------------------------*/
-
//开启日志 3.6.0.18
// //[0x221c330+wechatwin.dll]+0xf8
// 20220504
@@ -472,60 +592,6 @@ const isLoggedInFunction = (() => {
return !!loggedIn
})
-// 003get myself info
-
-const getBaseNodeAddress = (() => {
- return moduleBaseAddress.add(offset.node_offset).readPointer()
-})
-
-// 004
-const getHeaderNodeAddress = (() => {
- const baseAddress = getBaseNodeAddress()
- //console.log('baseAddress',baseAddress)
- if (baseAddress.isNull()) {
- return baseAddress
- }
-
- //console.log('HeaderNodeAddress',baseAddress.add(offset.handle_offset).readPointer())
- return baseAddress.add(offset.handle_offset).readPointer()
-})
-
-// 005
-const getChatroomNodeAddress = (() => {
- const baseAddress = moduleBaseAddress.add(0x222f3fc).readPointer()
- if (baseAddress.isNull()) {
- return baseAddress
- }
- return baseAddress.add(offset.chatroom_node_offset).readPointer()
-})
-
-// 006
-const getMyselfInfoFunction = (() => {
-
- let ptr = 0
- let wx_code = ''
- let wx_id = ''
- let wx_name = ''
- let head_img_url = ''
-
- wx_id = readString(moduleBaseAddress.add(offset.wxid_offset))
- wx_code = wx_id
-
- wx_name = readString(moduleBaseAddress.add(offset.nickname_offset))
- head_img_url = readString(moduleBaseAddress.add(offset.head_img_url_offset))
-
-
- const myself = {
- id: wx_id,
- code: wx_code,
- name: wx_name,
- head_img_url: head_img_url,
- };
-
- return JSON.stringify(myself)
-
-})
-
// 007 缺失,请标注已废弃或者其他原因
const getMyselfIdFunction = (() => {
@@ -535,76 +601,6 @@ const getMyselfIdFunction = (() => {
})
-// 008chatroom member
-const chatroomRecurse = ((node) => {
- const chatroomNodeAddress = getChatroomNodeAddress()
- if (chatroomNodeAddress.isNull()) { return }
-
- if (node.equals(chatroomNodeAddress)) { return }
-
- for (const item in chatroomNodeList) {
- if (node.equals(chatroomNodeList[item])) {
- return
- }
- }
-
- chatroomNodeList.push(node)
- const roomid = readWideString(node.add(0x10))
-
- const len = node.add(0x50).readU32() //
- //const memberJson={}
- if (len > 4) {//
- const memberStr = readString(node.add(0x40))
- if (memberStr.length > 0) {
- const memberList = memberStr.split(/[\\^][G]/)
- const memberJson = {
- roomid: roomid,
- roomMember: memberList
- }
-
- chatroomMemberList.push(memberJson)
- }
-
- }
-
- const leftNode = node.add(0x0).readPointer()
- const centerNode = node.add(0x04).readPointer()
- const rightNode = node.add(0x08).readPointer()
-
- chatroomRecurse(leftNode)
- chatroomRecurse(centerNode)
- chatroomRecurse(rightNode)
-
- const allChatroomMemberJson = chatroomMemberList
- return allChatroomMemberJson
-})
-
-// std::string
-// const str = readStringPtr(ptr).readUtf8String()
-const readStringPtr = (address) => {
- const addr = ptr(address)
- const size = addr.add(16).readU32()
- const capacity = addr.add(20).readU32()
- addr.ptr = addr
- addr.size = size
- addr.capacity = capacity
- if (capacity > 15 && !addr.readPointer().isNull()) {
- addr.ptr = addr.readPointer()
- }
- addr.ptr._readCString = addr.ptr.readCString
- addr.ptr._readAnsiString = addr.ptr.readAnsiString
- addr.ptr._readUtf8String = addr.ptr.readUtf8String
- addr.readCString = () => { return addr.size ? addr.ptr._readCString(addr.size) : '' }
- addr.readAnsiString = () => { return addr.size ? addr.ptr._readAnsiString(addr.size) : '' }
- addr.readUtf8String = () => { return addr.size ? addr.ptr._readUtf8String(addr.size) : '' }
-
- // console.log('readStringPtr() address:',address,' -> str ptr:', addr.ptr, 'size:', addr.size, 'capacity:', addr.capacity)
- // console.log('readStringPtr() str:' , addr.readUtf8String())
- // console.log('readStringPtr() address:', addr,'dump:', addr.readByteArray(24))
-
- return addr
-}
-
// std::wstring
// const wstr = readWStringPtr(ptr).readUtf16String()
const readWStringPtr = (address) => {
@@ -624,15 +620,8 @@ const readWStringPtr = (address) => {
return addr
}
-const readString = (address) => {
- return readStringPtr(address).readUtf8String()
-}
-
-const readWideString = (address) => {
- return readWStringPtr(address).readUtf16String()
-}
-
-const recurseNew = ((node) => {
+//contact
+const recurse = ((node) => {
const headerNodeAddress = getHeaderNodeAddress()
if (headerNodeAddress.isNull()) { return }
@@ -646,17 +635,262 @@ const recurseNew = ((node) => {
nodeList.push(node)
- const id = readString(node.add(0x8))
//wxid, format relates to registration method
- const wxid = readWideString(node.add(0x30))
- //console.log('-----------',wxid)
-
+ const wxid = readWideString(node.add(0x38))
//custom id, if not set return null, and use wxid which should be custom id
- //const wx_code = readWideString(node.add(0x4c)) || readWideString(node.add(0x38))
+ const wx_code = readWideString(node.add(0x4c)) || readWideString(node.add(0x38))
//custom Nickname
- const name = readWideString(node.add(0x8c))
+ const name = readWideString(node.add(0x94))
+
+ //alias aka 'remark' in wechat
+ const alias = readWideString(node.add(0x80))
+
+ //avatarUrl
+ const avatar = readWideString(node.add(0x138))
+ //const avatar = Memory.readUtf16String(node.add(0x138).readPointer())
+ //contact gender
+ const gender = node.add(0x18C).readU32()
+
+ const contactJson = {
+ id: wxid,
+ code: wx_code,
+ name: name,
+ alias: alias,
+ avatarUrl: avatar,
+ gender: gender,
+ }
+
+ contactList.push(contactJson)
+
+ const leftNode = node.add(0x0).readPointer()
+ const centerNode = node.add(0x04).readPointer()
+ const rightNode = node.add(0x08).readPointer()
+
+ recurse(leftNode)
+ recurse(centerNode)
+ recurse(rightNode)
+
+ const allContactJson = contactList
+ return allContactJson
+
+})
+
+// 010 done
+const getWechatVersionFunction = (() => {
+ if (currentVersion) {
+ return currentVersion
+ }
+ const pattern = '55 8B ?? 83 ?? ?? A1 ?? ?? ?? ?? 83 ?? ?? 85 ?? 7F ?? 8D ?? ?? E8 ?? ?? ?? ?? 84 ?? 74 ?? 8B ?? ?? ?? 85 ?? 75 ?? E8 ?? ?? ?? ?? 0F ?? ?? 0D ?? ?? ?? ?? A3 ?? ?? ?? ?? A3 ?? ?? ?? ?? 8B ?? 5D C3'
+ const results = Memory.scanSync(moduleLoad.base, moduleLoad.size, pattern)
+ if (results.length == 0) {
+ return 0
+ }
+ const addr = results[0].address
+ const ret = addr.add(0x07).readPointer()
+ const ver = ret.add(0x0).readU32()
+ currentVersion = ver
+ return ver
+})
+
+// 011 done
+const getWechatVersionStringFunction = ((ver = getWechatVersionFunction()) => {
+ if (!ver) {
+ return '0.0.0.0'
+ }
+ const vers = []
+ vers.push((ver >> 24) & 255 - 0x60)
+ vers.push((ver >> 16) & 255)
+ vers.push((ver >> 8) & 255)
+ vers.push(ver & 255)
+ return vers.join('.')
+})
+
+// 012 done
+const checkSupportedFunction = (() => {
+ const ver = getWechatVersionFunction()
+ return ver == availableVersion
+})
+
+/**
+ * @Hook: recvMsg -> recvMsgNativeCallback
+ */
+
+// 019 done
+const recvMsgNativeCallback = (() => {
+
+
+ const nativeCallback = new NativeCallback(() => {}, 'void', ['int32', 'pointer', 'pointer', 'pointer', 'pointer', 'int32'])
+ const nativeativeFunction = new NativeFunction(nativeCallback, 'void', ['int32', 'pointer', 'pointer', 'pointer', 'pointer', 'int32'])
+
+ Interceptor.attach(
+ moduleBaseAddress.add(offset.hook_point), {
+ onEnter() {
+ const addr = this.context.ecx //0xc30-0x08
+ const msgType = addr.add(0x38).readU32()
+ const isMyMsg = addr.add(0x3C).readU32() //add isMyMsg
+
+ if (msgType > 0) {
+
+ const talkerIdPtr = addr.add(0x48).readPointer()
+ //console.log('txt msg',talkerIdPtr.readUtf16String())
+ const talkerIdLen = addr.add(0x48 + 0x04).readU32() * 2 + 2
+
+ const myTalkerIdPtr = Memory.alloc(talkerIdLen)
+ Memory.copy(myTalkerIdPtr, talkerIdPtr, talkerIdLen)
+
+
+ let contentPtr = null
+ let contentLen = 0
+ let myContentPtr = null
+ if (msgType == 3) { // pic path
+ let thumbPtr = addr.add(0x198).readPointer();
+ let hdPtr = addr.add(0x1ac).readPointer();
+ let thumbPath = thumbPtr.readUtf16String();
+ let hdPath = hdPtr.readUtf16String();
+ let picData = [
+ thumbPath, // PUPPET.types.Image.Unknown
+ thumbPath, // PUPPET.types.Image.Thumbnail
+ hdPath, // PUPPET.types.Image.HD
+ hdPath // PUPPET.types.Image.Artwork
+ ]
+ let content = JSON.stringify(picData);
+ myContentPtr = Memory.allocUtf16String(content);
+ } else {
+ contentPtr = addr.add(0x70).readPointer()
+ contentLen = addr.add(0x70 + 0x04).readU32() * 2 + 2
+ myContentPtr = Memory.alloc(contentLen)
+ Memory.copy(myContentPtr, contentPtr, contentLen)
+ }
+
+ // console.log('----------------------------------------')
+ // console.log(msgType)
+ // console.log(contentPtr.readUtf16String())
+ // console.log('----------------------------------------')
+ const groupMsgAddr = addr.add(0x170).readU32() //* 2 + 2
+ let myGroupMsgSenderIdPtr = null
+ if (groupMsgAddr == 0) { //weChatPublic is zero,type is 49
+
+ myGroupMsgSenderIdPtr = Memory.alloc(0x10)
+ myGroupMsgSenderIdPtr.writeUtf16String("null")
+
+ } else {
+
+ const groupMsgSenderIdPtr = addr.add(0x170).readPointer()
+ const groupMsgSenderIdLen = addr.add(0x170 + 0x04).readU32() * 2 + 2
+ myGroupMsgSenderIdPtr = Memory.alloc(groupMsgSenderIdLen)
+ Memory.copy(myGroupMsgSenderIdPtr, groupMsgSenderIdPtr, groupMsgSenderIdLen)
+
+ }
+
+ const xmlNullPtr = addr.add(0x1f0).readU32() //3.9.2.23
+ let myXmlContentPtr = null
+ if (xmlNullPtr == 0) {
+
+ myXmlContentPtr = Memory.alloc(0x10)
+ myXmlContentPtr.writeUtf16String("null")
+
+ } else {
+ const xmlContentPtr = addr.add(0x1f0).readPointer() //3.9.2.23
+
+ const xmlContentLen = addr.add(0x1f0 + 0x04).readU32() * 2 + 2
+ myXmlContentPtr = Memory.alloc(xmlContentLen)
+ Memory.copy(myXmlContentPtr, xmlContentPtr, xmlContentLen)
+ }
+
+ setImmediate(() => nativeativeFunction(msgType, myTalkerIdPtr, myContentPtr, myGroupMsgSenderIdPtr, myXmlContentPtr, isMyMsg))
+ }
+ }
+ })
+ return nativeCallback
+})()
+
+// 003get myself info done
+const getBaseNodeAddress = (() => {
+ return moduleBaseAddress.add(offset.contactInfo.nodeOffset).readPointer()
+})
+
+// 004 done
+const getHeaderNodeAddress = (() => {
+ const baseAddress = getBaseNodeAddress()
+ //console.log('baseAddress',baseAddress)
+ if (baseAddress.isNull()) {
+ return baseAddress
+ }
+
+ //console.log('HeaderNodeAddress',baseAddress.add(offset.handle_offset).readPointer())
+ return baseAddress.add(offset.contactInfo.nodeRootOffset).readPointer()
+})
+
+// 006 done
+const getMyselfInfoFunction = (() => {
+
+ let ptr = 0
+ let wx_code = ''
+ let wx_id = ''
+ let wx_name = ''
+ let head_img_url = ''
+
+ const base = moduleBaseAddress.add(offset.myselfinfo.offset)
+ const wxid_len = base.add(offset.myselfinfo.wxid_len_offset).readU32()
+
+ if (wxid_len === 0x13) { // 新版本微信
+ wx_id = base.readPointer().readAnsiString(wxid_len)
+ wx_code = base.add(offset.myselfinfo.wxcode_new).readAnsiString()
+ } else {
+ wx_id = readString(base)
+ wx_code = wx_id
+ }
+
+
+ wx_name = readString(base.add(offset.myselfinfo.wx_nick_name))
+ const img_addr = base.add(offset.myselfinfo.head_img_url).readPointer()
+ const img_len = base.add(offset.myselfinfo.head_img_url_len).readU32()
+
+ head_img_url = img_addr.readAnsiString(img_len)
+
+ const myself = {
+ id: wx_id,
+ code: wx_code,
+ name: wx_name,
+ head_img_url: head_img_url,
+ };
+
+ return JSON.stringify(myself)
+
+})
+
+// done
+const recurseNew = ((node) => {
+ const headerNodeAddress = getHeaderNodeAddress()
+ if (headerNodeAddress.isNull()) {
+ return
+ }
+
+ if (node.equals(headerNodeAddress)) {
+ return
+ }
+
+ for (const item in nodeList) {
+ if (node.equals(nodeList[item])) {
+ return
+ }
+ }
+
+
+ nodeList.push(node)
+ const id = readString(node.add(0x8))
+ //wxid, format relates to registration method
+ const wxid = readWideString(node.add(0x30))
+ //console.log('-----------',wxid)
+
+
+ //custom id, if not set return null, and use wxid which should be custom id
+ //const wx_code = readWideString(node.add(0x4c)) || readWideString(node.add(0x38))
+
+ //custom Nickname
+ const name = readWideString(node.add(0x8c))
//alias aka 'remark' in wechat
//const alias = readWideString(node.add(0x80))
@@ -693,112 +927,361 @@ const recurseNew = ((node) => {
})
-
-//contact
-const recurse = ((node) => {
+// done ?
+const getContactNativeFunction = (() => {
const headerNodeAddress = getHeaderNodeAddress()
- if (headerNodeAddress.isNull()) { return }
+ //console.log('headerNodeAddress',headerNodeAddress)
- if (node.equals(headerNodeAddress)) { return }
+ if (headerNodeAddress.isNull()) {
+ return '[]'
+ }
- for (const item in nodeList) {
- if (node.equals(nodeList[item])) {
+ const node = headerNodeAddress.add(0x0).readPointer()
+ const ret = recurseNew(node)
+
+ //console.log(ret)
+
+ console.log('getContactNativeFunction:', ret.length)
+ /*for (let item of ret){
+ console.log(JSON.stringify(item))
+ }*/
+ //console.log(ret.contact)
+ const cloneRet = JSON.stringify(ret)
+ nodeList.length = 0
+ contactList.length = 0
+
+ return cloneRet
+})
+
+// 005 done
+const getChatroomNodeAddress = (() => {
+ const baseAddress = moduleBaseAddress.add(offset.chatroomInfo.nodeOffset).readPointer()
+ if (baseAddress.isNull()) {
+ return baseAddress
+ }
+ return baseAddress.add(offset.chatroomInfo.nodeRootOffset).readPointer()
+})
+
+// 008chatroom member done
+const chatroomRecurse = ((node) => {
+ const chatroomNodeAddress = getChatroomNodeAddress()
+ if (chatroomNodeAddress.isNull()) {
+ return
+ }
+
+ if (node.equals(chatroomNodeAddress)) {
+ return
+ }
+
+ for (const item in chatroomNodeList) {
+ if (node.equals(chatroomNodeList[item])) {
return
}
}
+ chatroomNodeList.push(node)
+ const roomid = readWideString(node.add(0x10))
- nodeList.push(node)
- //wxid, format relates to registration method
- const wxid = readWideString(node.add(0x38))
+ const len = node.add(0x54).readU32() //
+ //const memberJson={}
+ if (len > 4) { //
+ const memberStr = readString(node.add(0x44))
+ if (memberStr.length > 0) {
+ const memberList = memberStr.split(/[\\^][G]/)
+ const memberJson = {
+ roomid: roomid,
+ roomMember: memberList
+ }
+
+ chatroomMemberList.push(memberJson)
+ }
+
+ }
+
+ const leftNode = node.add(0x0).readPointer()
+ const centerNode = node.add(0x04).readPointer()
+ const rightNode = node.add(0x08).readPointer()
+
+ chatroomRecurse(leftNode)
+ chatroomRecurse(centerNode)
+ chatroomRecurse(rightNode)
+
+ const allChatroomMemberJson = chatroomMemberList
+ return allChatroomMemberJson
+})
+
+// 009 done
+const getChatroomMemberInfoFunction = (() => {
+ const chatroomNodeAddress = getChatroomNodeAddress()
+ if (chatroomNodeAddress.isNull()) {
+ return '[]'
+ }
+
+ const node = chatroomNodeAddress.add(0x0).readPointer()
+ const ret = chatroomRecurse(node)
+
+ const cloneRet = JSON.stringify(ret)
+ chatroomNodeList.length = 0 //empty
+ chatroomMemberList.length = 0 //empty
+ return cloneRet
+})
+
+// 024 done
+/**
+ * sendMsgNativeFunction
+ * send text message
+ * @param {string} talkerId = wxid or roomid
+ * @param {string} content
+ */
+ const sendMsgNativeFunction = ((talkerId, content) => {
+
+ const txtAsm = Memory.alloc(Process.pageSize)
+ //const buffwxid = Memory.alloc(0x20)
+
+
+ let wxidPtr = Memory.alloc(talkerId.length * 2 + 2)
+ wxidPtr.writeUtf16String(talkerId)
+
+ let picWxid = Memory.alloc(0x0c)
+ picWxid.writePointer(ptr(wxidPtr)).add(0x04)
+ .writeU32(talkerId.length * 2).add(0x04)
+ .writeU32(talkerId.length * 2).add(0x04)
+
+ let contentPtr = Memory.alloc(content.length * 2 + 2)
+ contentPtr.writeUtf16String(content)
+
+ const sizeOfStringStruct = Process.pointerSize * 5
+ let contentStruct = Memory.alloc(sizeOfStringStruct)
+
+ contentStruct
+ .writePointer(contentPtr).add(0x4)
+ .writeU32(content.length).add(0x4)
+ .writeU32(content.length * 2)
+
+
+ const ecxBuffer = Memory.alloc(0x2d8)
+
+ Memory.patchCode(txtAsm, Process.pageSize, code => {
+ var cw = new X86Writer(code, {
+ pc: txtAsm
+ })
+ cw.putPushfx()
+ cw.putPushax()
+
+ cw.putPushU32(0x0)
+ cw.putPushU32(0x0)
+ cw.putPushU32(0x0)
+ cw.putPushU32(0x1)
+ cw.putPushU32(0x0)
+
+ //cw.putMovRegReg
+
+ cw.putMovRegAddress('eax', contentStruct)
+ cw.putPushReg('eax')
+
+ cw.putMovRegAddress('edx', picWxid) //room_id
+
+ cw.putMovRegAddress('ecx', ecxBuffer)
+ cw.putCallAddress(moduleBaseAddress.add(
+ offset.sendTxtMsg.callOffset
+ ))
+
+ cw.putAddRegImm('esp', 0x18)
+ cw.putPopax()
+ cw.putPopfx()
+ cw.putRet()
+ cw.flush()
+
+ })
+
+ console.log('----------txtAsm', txtAsm)
+ const nativeativeFunction = new NativeFunction(ptr(txtAsm), 'void', [])
+ nativeativeFunction()
+
+})
+
+// 023 done
+/**
+* send at msg
+*/
+let asmAtMsg = null
+let roomid_, msg_, wxid_, atid_
+let ecxBuffer
+const sendAtMsgNativeFunction = ((roomId, text, contactId,nickname) => {
+
+ asmAtMsg = Memory.alloc(Process.pageSize)
+ ecxBuffer = Memory.alloc(0x3b0)
+
+ const atContent = '@'+nickname+' '+text
+
+ roomid_ = initStruct(roomId)
+ wxid_ = initidStruct(contactId)
+ msg_ = initmsgStruct(atContent)
+ atid_ = initAtMsgStruct(wxid_)
+
+ Memory.patchCode(asmAtMsg, Process.pageSize, code => {
+ var cw = new X86Writer(code, {
+ pc: asmAtMsg
+ })
+ cw.putPushfx()
+ cw.putPushax()
+
+ cw.putPushU32(0x0)
+ cw.putPushU32(0x0)
+ cw.putPushU32(0x0)
+ cw.putPushU32(0x1)
+ //cw.putPushU32(0x0)
+ cw.putMovRegAddress('eax', atid_)
+ cw.putPushReg('eax')
+
+ //cw.putMovRegReg
+
+ cw.putMovRegAddress('eax', msg_)
+ cw.putPushReg('eax')
+
+ cw.putMovRegAddress('edx', roomid_) //room_id
+
+ cw.putMovRegAddress('ecx', ecxBuffer)
+ cw.putCallAddress(moduleBaseAddress.add(
+ offset.sendTxtMsg.callOffset
+ ))
+
+ cw.putAddRegImm('esp', 0x18)
+ cw.putPopax()
+ cw.putPopfx()
+ cw.putRet()
+ cw.flush()
+
+ })
+
+ //console.log('----------txtAsm', asmAtMsg)
+ const nativeativeFunction = new NativeFunction(ptr(asmAtMsg), 'void', [])
+ nativeativeFunction()
+
+})
+
+// 022 done
+/**
+ *
+ * @param {*} contactId
+ * @param {*} path
+ */
+ const sendPicMsgNativeFunction = ((contactId, path) => {
+
+ const picAsm = Memory.alloc(Process.pageSize)
+ const buffwxid = Memory.alloc(0x20)
+ const picbuff = Memory.alloc(0x2D8)
+
+ let pathPtr = Memory.alloc(path.length * 2 + 1)
+ pathPtr.writeUtf16String(path)
+
+ let imagefilepath = Memory.alloc(0x24)
+ imagefilepath.writePointer(pathPtr).add(0x04)
+ .writeU32(path.length * 2).add(0x04)
+ .writeU32(path.length * 2).add(0x04)
+
+ let picWxidPtr = Memory.alloc(contactId.length * 2 + 1)
+ picWxidPtr.writeUtf16String(contactId)
+
+ let picWxid = Memory.alloc(0x0c)
+ picWxid.writePointer(ptr(picWxidPtr)).add(0x04)
+ .writeU32(contactId.length * 2).add(0x04)
+ .writeU32(contactId.length * 2).add(0x04)
- //custom id, if not set return null, and use wxid which should be custom id
- const wx_code = readWideString(node.add(0x4c)) || readWideString(node.add(0x38))
- //custom Nickname
- const name = readWideString(node.add(0x94))
+ //const test_offset1 = 0x701DC0;
+ Memory.patchCode(picAsm, Process.pageSize, code => {
+ var cw = new X86Writer(code, {
+ pc: picAsm
+ })
+ cw.putPushfx();
+ cw.putPushax();
+ cw.putCallAddress(moduleBaseAddress.add(
+ offset.sendPicMsg.call1
+ ))
+ cw.putMovRegReg('edx', 'eax') //缓存
- //alias aka 'remark' in wechat
- const alias = readWideString(node.add(0x80))
+ cw.putSubRegImm('esp', 0x14)
+ cw.putMovRegAddress('eax', buffwxid)
+ cw.putMovRegReg('ecx', 'esp')
+ cw.putMovRegAddress('edi', imagefilepath)
+ cw.putPushReg('eax')
+ cw.putCallAddress(moduleBaseAddress.add(
+ offset.sendPicMsg.call2
+ ))
- //avatarUrl
- const avatar = readWideString(node.add(0x138))
- //const avatar = Memory.readUtf16String(node.add(0x138).readPointer())
- //contact gender
- const gender = node.add(0x18C).readU32()
+ cw.putMovRegReg('ecx', 'edx')
+ cw.putMovRegAddress('eax', picWxid) //=lea
+ cw.putMovRegAddress('edi', imagefilepath)
+ cw.putPushReg('edi')
+ cw.putPushReg('eax')
+ cw.putMovRegAddress('eax', picbuff)
+ cw.putPushReg('eax')
- const contactJson = {
- id: wxid,
- code: wx_code,
- name: name,
- alias: alias,
- avatarUrl: avatar,
- gender: gender,
- }
+ cw.putMovRegAddress('edi', picWxid) //edi
+ cw.putCallAddress(moduleBaseAddress.add(
+ offset.sendPicMsg.call3
+ ))
- contactList.push(contactJson)
- const leftNode = node.add(0x0).readPointer()
- const centerNode = node.add(0x04).readPointer()
- const rightNode = node.add(0x08).readPointer()
- recurse(leftNode)
- recurse(centerNode)
- recurse(rightNode)
+ cw.putPopax()
+ cw.putPopfx()
+ cw.putRet()
+ cw.flush()
- const allContactJson = contactList
- return allContactJson
+ })
+
+ //console.log('----------picAsm',picAsm)
+ const nativeativeFunction = new NativeFunction(ptr(picAsm), 'void', [])
+ nativeativeFunction()
})
-// 009
-const getChatroomMemberInfoFunction = (() => {
- const chatroomNodeAddress = getChatroomNodeAddress()
- if (chatroomNodeAddress.isNull()) { return '[]' }
+// 020 done
+let memberNickBuffAsm = null
+let nickRoomId = null
+let nickMemberId = null
+let nickBuff = null
+const getChatroomMemberNickInfoFunction = ((memberId, roomId) => {
- const node = chatroomNodeAddress.add(0x0).readPointer()
- const ret = chatroomRecurse(node)
+ nickBuff = Memory.alloc(0x7e4)
+ //const nickRetAddr = Memory.alloc(0x04)
+ memberNickBuffAsm = Memory.alloc(Process.pageSize)
+ //console.log('asm address----------',memberNickBuffAsm)
+ nickRoomId = initidStruct(roomId)
+ //console.log('nick room id',nickRoomId)
+ nickMemberId = initStruct(memberId)
- const cloneRet = JSON.stringify(ret)
- chatroomNodeList.length = 0//empty
- chatroomMemberList.length = 0 //empty
- return cloneRet
-})
+ //console.log('nick nickMemberId id',nickMemberId)
+ //const nickStructPtr = initmsgStruct('')
-// 010
-const getWechatVersionFunction = (() => {
- if (currentVersion) {
- return currentVersion
- }
- const pattern = '55 8B ?? 83 ?? ?? A1 ?? ?? ?? ?? 83 ?? ?? 85 ?? 7F ?? 8D ?? ?? E8 ?? ?? ?? ?? 84 ?? 74 ?? 8B ?? ?? ?? 85 ?? 75 ?? E8 ?? ?? ?? ?? 0F ?? ?? 0D ?? ?? ?? ?? A3 ?? ?? ?? ?? A3 ?? ?? ?? ?? 8B ?? 5D C3'
- const results = Memory.scanSync(moduleLoad.base, moduleLoad.size, pattern)
- if (results.length == 0) {
- return 0
- }
- const addr = results[0].address
- const ret = addr.add(0x07).readPointer()
- const ver = ret.add(0x0).readU32()
- currentVersion = ver
- return ver
-})
+ Memory.patchCode(memberNickBuffAsm, Process.pageSize, code => {
+ var cw = new X86Writer(code, {
+ pc: memberNickBuffAsm
+ })
+ cw.putPushfx()
+ cw.putPushax()
+ cw.putMovRegAddress('edi', nickRoomId)
+ cw.putMovRegAddress('eax', nickBuff)
+ cw.putMovRegReg('edx', 'edi')
+ cw.putPushReg('eax')
+ cw.putMovRegAddress('ecx', nickMemberId)
+ cw.putCallAddress(moduleBaseAddress.add(0xC06F10))
+ cw.putAddRegImm('esp', 0x04)
+ cw.putPopax()
+ cw.putPopfx()
+ cw.putRet()
+ cw.flush()
-// 011
-const getWechatVersionStringFunction = ((ver = getWechatVersionFunction()) => {
- if (!ver) {
- return '0.0.0.0'
- }
- const vers = []
- vers.push((ver >> 24) & 255 - 0x60)
- vers.push((ver >> 16) & 255)
- vers.push((ver >> 8) & 255)
- vers.push(ver & 255)
- return vers.join('.')
-})
+ })
-// 012
-const checkSupportedFunction = (() => {
- const ver = getWechatVersionFunction()
- return ver == availableVersion
+ const nativeativeFunction = new NativeFunction(ptr(memberNickBuffAsm), 'void', [])
+ nativeativeFunction()
+
+ const nickname = readWideString(nickBuff)
+ console.log('----nickname', nickname)
+ return readWideString(nickBuff)
})
// 013
@@ -808,30 +1291,6 @@ if (!isSupported) {
throw new Error(`Wechat version not supported. \nWechat version: ${getWechatVersionStringFunction()}, supported version: ${getWechatVersionStringFunction(availableVersion)}`)
}
-// 014
-const getContactNativeFunction = (() => {
- const headerNodeAddress = getHeaderNodeAddress()
- //console.log('headerNodeAddress',headerNodeAddress)
-
- if (headerNodeAddress.isNull()) { return '[]' }
-
- const node = headerNodeAddress.add(0x0).readPointer()
- const ret = recurseNew(node)
-
- //console.log(ret)
-
- // console.log('getContactNativeFunction:',ret.length)
- /*for (let item of ret){
- console.log(JSON.stringify(item))
- }*/
- //console.log(ret.contact)
- const cloneRet = JSON.stringify(ret)
- nodeList.length = 0
- contactList.length = 0
-
- return cloneRet
-})
-
// 015
const hookLogoutEventCallback = (() => {
const nativeCallback = new NativeCallback(() => { }, 'void', ['int32'])
@@ -973,214 +1432,23 @@ const getQrcodeLoginData = () => {
/**
* 20220504 writelog
* 7A566D72 | FFB5 ECFEFFFF | push dword ptr ss:[ebp-114] | 【3.6.0.18】写日志,这个里面就是日志内容
- 7A566D78 | FFB5 E8FEFFFF | push dword ptr ss:[ebp-118] |
- */
-/*const writeLogNativeCallback = (() => {
- const nativeCallback = new NativeCallback(() => { }, 'void', [])
- const nativeCallFunction = new NativeFunction(nativeCallback, 'void', [])
-
- Interceptor.attach(
- moduleBaseAddress.add(0x1576D7E),
- {
- onEnter() {
- const addr = this.context.ebp.sub(0x114)//0xc30-0x08
- console.log('-------',addr)
-
- }
- })
- return nativeCallback
-})()*/
-
-/**
- * @Hook: recvMsg -> recvMsgNativeCallback
- */
-
-// 019
-const recvMsgNativeCallback = (() => {
-
-
- const nativeCallback = new NativeCallback(() => { }, 'void', ['int32', 'pointer', 'pointer', 'pointer', 'pointer', 'int32'])
- const nativeativeFunction = new NativeFunction(nativeCallback, 'void', ['int32', 'pointer', 'pointer', 'pointer', 'pointer', 'int32'])
-
- Interceptor.attach(
- moduleBaseAddress.add(offset.hook_point),
- {
- onEnter() {
- let addr
- let msgType = 0
- let isMyMsg = 0
- let curTime = new Date()
- try {
- addr = this.context.eax//0xc30-0x08
- msgType = addr.add(0x38).readU32()
- isMyMsg = addr.add(0x3C).readU32()//add isMyMsg
- if (msgType > 0) {
- const talkerIdPtr = addr.add(0x48).readPointer()
- //console.log('txt msg',talkerIdPtr.readUtf16String())
- const talkerIdLen = addr.add(0x48 + 0x04).readU32() * 2 + 2
-
- const myTalkerIdPtr = Memory.alloc(talkerIdLen)
- Memory.copy(myTalkerIdPtr, talkerIdPtr, talkerIdLen)
-
-
- let contentPtr = null
- let contentLen = 0
- let myContentPtr = null
- if (msgType == 3) {// pic path
- let thumbPtr = addr.add(0x198).readPointer();
- let hdPtr = addr.add(0x1ac).readPointer();
- let thumbPath = thumbPtr.readUtf16String();
- let hdPath = hdPtr.readUtf16String();
- let picData = [
- thumbPath,// PUPPET.types.Image.Unknown
- thumbPath,// PUPPET.types.Image.Thumbnail
- hdPath,// PUPPET.types.Image.HD
- hdPath// PUPPET.types.Image.Artwork
- ]
- let content = JSON.stringify(picData);
- myContentPtr = Memory.allocUtf16String(content);
- } else {
- contentPtr = addr.add(0x70).readPointer()
- contentLen = addr.add(0x70 + 0x04).readU32() * 2 + 2
- myContentPtr = Memory.alloc(contentLen)
- Memory.copy(myContentPtr, contentPtr, contentLen)
- }
-
- // console.log('----------------------------------------')
- // console.log(msgType)
- // console.log(contentPtr.readUtf16String())
- // console.log('----------------------------------------')
- const groupMsgAddr = addr.add(0x170).readU32() //* 2 + 2
- let myGroupMsgSenderIdPtr = null
- if (groupMsgAddr == 0) {//weChatPublic is zero,type is 49
-
- myGroupMsgSenderIdPtr = Memory.alloc(0x10)
- myGroupMsgSenderIdPtr.writeUtf16String("null")
-
- } else {
-
- const groupMsgSenderIdPtr = addr.add(0x170).readPointer()
- const groupMsgSenderIdLen = addr.add(0x170 + 0x04).readU32() * 2 + 2
- myGroupMsgSenderIdPtr = Memory.alloc(groupMsgSenderIdLen)
- Memory.copy(myGroupMsgSenderIdPtr, groupMsgSenderIdPtr, groupMsgSenderIdLen)
-
- }
-
- const xmlNullPtr = addr.add(0x1ec).readU32()
- let myXmlContentPtr = null
- if (xmlNullPtr == 0) {
-
- myXmlContentPtr = Memory.alloc(0x10)
- myXmlContentPtr.writeUtf16String("null")
-
- } else {
- const xmlContentPtr = addr.add(0x1ec).readPointer()
-
- const xmlContentLen = addr.add(0x1ec + 0x04).readU32() * 2 + 2
- myXmlContentPtr = Memory.alloc(xmlContentLen)
- Memory.copy(myXmlContentPtr, xmlContentPtr, xmlContentLen)
- }
-
- setImmediate(() => nativeativeFunction(msgType, myTalkerIdPtr, myContentPtr, myGroupMsgSenderIdPtr, myXmlContentPtr, isMyMsg))
- }
- } catch (err) {
- console.error(curTime,'recvMsgNativeCallback at onEnter err:', err)
- }
- }
- })
- return nativeCallback
-})()
-
-
-let msgStruct = null
-let msgstrPtr = null
-const initmsgStruct = ((str) => {
- msgstrPtr = Memory.alloc(str.length * 2 + 1)
- msgstrPtr.writeUtf16String(str)
-
- msgStruct = Memory.alloc(0x14) // returns a NativePointer
-
- msgStruct
- .writePointer(msgstrPtr).add(0x04)
- .writeU32(str.length * 2).add(0x04)
- .writeU32(str.length * 2).add(0x04)
- .writeU32(0).add(0x04)
- .writeU32(0)
-
- return msgStruct
-})
-
-let retidNullStruct = null
-let retidNullPtr = null
-const initNullIdStruct = ((str) => {
-
- retidNullPtr = Memory.alloc(str.length * 2 + 1)
- retidNullPtr.writeUtf16String(str)
-
- retidNullStruct = Memory.alloc(0x14) // returns a NativePointer
-
- retidNullStruct
- .writePointer(retidNullPtr).add(0x04)
- .writeU32(str.length * 2).add(0x04)
- .writeU32(str.length * 2).add(0x04)
- .writeU32(0).add(0x04)
- .writeU32(0)
-
- return retidNullStruct
-})
-
-let retidStruct = null
-let retidPtr = null
-const initidStruct = ((str) => {
-
- retidPtr = Memory.alloc(str.length * 2 + 1)
- retidPtr.writeUtf16String(str)
-
- retidStruct = Memory.alloc(0x14) // returns a NativePointer
-
- retidStruct
- .writePointer(retidPtr).add(0x04)
- .writeU32(str.length * 2).add(0x04)
- .writeU32(str.length * 2).add(0x04)
- .writeU32(0).add(0x04)
- .writeU32(0)
-
- return retidStruct
-})
-
-let retPtr = null
-let retStruct = null
-const initStruct = ((str) => {
-
- retPtr = Memory.alloc(str.length * 2 + 1)
- retPtr.writeUtf16String(str)
-
- retStruct = Memory.alloc(0x14) // returns a NativePointer
-
- retStruct
- .writePointer(retPtr).add(0x04)
- .writeU32(str.length * 2).add(0x04)
- .writeU32(str.length * 2).add(0x04)
- .writeU32(0).add(0x04)
- .writeU32(0)
-
- return retStruct
-})
-
-/**
-* at msg structure
-*/
-let atStruct = null
-const initAtMsgStruct = ((wxidStruct) => {
-
- atStruct = Memory.alloc(0x10)
+ 7A566D78 | FFB5 E8FEFFFF | push dword ptr ss:[ebp-118] |
+ */
+/*const writeLogNativeCallback = (() => {
+ const nativeCallback = new NativeCallback(() => { }, 'void', [])
+ const nativeCallFunction = new NativeFunction(nativeCallback, 'void', [])
- atStruct.writePointer(wxidStruct).add(0x04)
- .writeU32(wxidStruct.toInt32() + 0x14).add(0x04)//0x14 = sizeof(wxid structure)
- .writeU32(wxidStruct.toInt32() + 0x14).add(0x04)
- .writeU32(0)
- return atStruct
-})
+ Interceptor.attach(
+ moduleBaseAddress.add(0x1576D7E),
+ {
+ onEnter() {
+ const addr = this.context.ebp.sub(0x114)//0xc30-0x08
+ console.log('-------',addr)
+
+ }
+ })
+ return nativeCallback
+})()*/
let nickRoomIdV6 = null
let nullEdiWxidStructV6 = null
@@ -1241,86 +1509,6 @@ const getChatroomMemberNickInfoV1Function = ((memberId, roomId) => {
return readWideString(nullEdiWxidStructV6)
})
-//get nick from chatroom
-let nickRoomId = null
-let nickMemberId = null
-let nickStructPtr = null
-let nickBuff = null
-let memberNickBuffAsm = null
-let nickRetAddr = null
-
-// 020
-const getChatroomMemberNickInfoFunction = ((memberId, roomId) => {
-
- nickBuff = Memory.alloc(0x7e4)
- nickRetAddr = Memory.alloc(0x04)
- memberNickBuffAsm = Memory.alloc(Process.pageSize)
- nickRoomId = initidStruct(roomId)
- nickMemberId = initStruct(memberId)
- nickStructPtr = initmsgStruct('')
-
- Memory.patchCode(memberNickBuffAsm, Process.pageSize, code => {
- var cw = new X86Writer(code, { pc: memberNickBuffAsm })
- cw.putPushfx();
- cw.putPushax();
-
- /*cw.putMovRegAddress('ebx', nickStructPtr)
- cw.putMovRegAddress('esi', nickMemberId)
- cw.putMovRegAddress('edi', nickRoomId)
-
- cw.putMovRegAddress('ecx', nickBuff)
- cw.putCallAddress(moduleBaseAddress.add(
- offset.chatroom_member_nick_call_offset1
- ))
-
- cw.putMovRegAddress('eax', nickBuff)
- cw.putPushReg('eax')
- cw.putPushReg('esi')
- cw.putCallAddress(moduleBaseAddress.add(
- offset.chatroom_member_nick_call_offset2
- ))
-
- cw.putMovRegReg('ecx', 'eax')
- cw.putCallAddress(moduleBaseAddress.add(
- offset.chatroom_member_nick_call_offset3
- ))
-
- cw.putPushU32(1)
- cw.putPushReg('ebx')
- cw.putMovRegReg('edx', 'edi')
- cw.putMovRegAddress('ecx', nickBuff)
- cw.putCallAddress(moduleBaseAddress.add(
- offset.chatroom_member_nick_call_offset4
- ))
- cw.putAddRegImm('esp', 0x08)
- cw.putMovNearPtrReg(nickRetAddr, 'ebx')*/
- cw.putMovRegAddress('edi', nickRoomId)
- cw.putMovRegAddress('eax', nickBuff)
- cw.putMovRegReg('edx', 'edi')
- cw.putPushReg('eax')
- cw.putMovRegAddress('ecx', nickMemberId)
- cw.putCallAddress(moduleBaseAddress.add(0x404500))
- cw.putAddRegImm('esp', 0x04)
- //cw.putMovNearPtrReg(nickRetAddr, 'ebx')
- //lea eax, buf
-
- cw.putPopax()
- cw.putPopfx()
- cw.putRet()
- cw.flush()
-
- })
-
- const nativeativeFunction = new NativeFunction(ptr(memberNickBuffAsm), 'void', [])
- nativeativeFunction()
-
- const nickname = readWideString(nickBuff);
- // console.log('--------nickname',nickname)
- return readWideString(nickBuff);
- //return readWideString(nickRetAddr.readPointer())
-
-})
-
/**
* send attatch
*/
@@ -1567,131 +1755,6 @@ const sendAttatchMsgNativeFunction = ((contactId, senderId, path, filename, size
//console.log('-------',attatchEbp1C.add(0x4).readPointer())
//console.log('-------',attatchEbp1C.add(0x8).readPointer())
})
-/*-----------------send pic 3.6.0.18----------------*/
-/*------------------send pic --------------------------*/
-let buffwxid = null
-let imagefilepath = null
-let pathPtr = null
-let picWxid = null
-let picWxidPtr = null
-let picAsm = null
-let picbuff = null
-
-// 022
-const sendPicMsgNativeFunction = ((contactId, path) => {
-
- picAsm = Memory.alloc(Process.pageSize)
- buffwxid = Memory.alloc(0x20)
- picbuff = Memory.alloc(0x3B0)
-
- pathPtr = Memory.alloc(path.length * 2 + 1)
- pathPtr.writeUtf16String(path)
-
- imagefilepath = Memory.alloc(0x24)
- imagefilepath.writePointer(pathPtr).add(0x04)
- .writeU32(path.length * 2).add(0x04)
- .writeU32(path.length * 2).add(0x04)
-
- picWxidPtr = Memory.alloc(contactId.length * 2 + 1)
- picWxidPtr.writeUtf16String(contactId)
-
- picWxid = Memory.alloc(0x0c)
- picWxid.writePointer(ptr(picWxidPtr)).add(0x04)
- .writeU32(contactId.length * 2).add(0x04)
- .writeU32(contactId.length * 2).add(0x04)
-
- /*const ecxValue = (moduleBaseAddress.add(
- offset.send_picmsg_call_offset0
- )).toInt32()
-*/
- const test_offset1 = 0x701DC0;
- Memory.patchCode(picAsm, Process.pageSize, code => {
- var cw = new X86Writer(code, { pc: picAsm })
- cw.putPushfx();
- cw.putPushax();
- cw.putCallAddress(moduleBaseAddress.add(
- offset.send_picmsg_call_offset0
- ))
- cw.putMovRegReg('edx', 'eax')//缓存
-
- cw.putSubRegImm('esp', 0x14)
- cw.putMovRegAddress('eax', buffwxid)
- cw.putMovRegReg('ecx', 'esp')
- cw.putMovRegAddress('edi', imagefilepath)
- cw.putPushReg('eax')
- cw.putCallAddress(moduleBaseAddress.add(
- test_offset1
- ))
-
- cw.putMovRegReg('ecx', 'edx')
- cw.putMovRegAddress('eax', picWxid) //=lea
- cw.putMovRegAddress('edi', imagefilepath)
- cw.putPushReg('edi')
- cw.putPushReg('eax')
- cw.putMovRegAddress('eax', picbuff)
- cw.putPushReg('eax')
-
- cw.putMovRegAddress('edi', picWxid)//edi
- cw.putCallAddress(moduleBaseAddress.add(
- offset.send_picmsg_call_offset1
- ))
-
- /*cw.putCallAddress(moduleBaseAddress.add(
- offset.send_picmsg_call_offset0
- ))
- cw.putMovRegReg('ecx', 'eax')
- cw.putMovRegAddress('eax', picWxid)
- cw.putMovRegAddress('edi', imagefilepath)
- cw.putPushReg('edi')
- cw.putPushReg('eax')
- cw.putMovRegAddress('eax', picbuff)
- cw.putPushReg('eax')
-
- cw.putMovRegAddress('edi', picWxid)//edi
- cw.putCallAddress(moduleBaseAddress.add(
- offset.send_picmsg_call_offset1
- ))-------ok but exception*/
-
- /*3.3.0.115
- cw.putSubRegImm('esp', 0x14)
- cw.putMovRegAddress('eax', buffwxid)
-
- cw.putMovRegReg('ecx', 'esp')
-
- cw.putPushReg('eax')
- cw.putCallAddress(moduleBaseAddress.add(
- offset.send_picmsg_call_offset1
- ))
-
- cw.putMovRegAddress('ebx', imagefilepath)
- cw.putPushReg('ebx')
-
- cw.putMovRegAddress('eax', picWxid)
- cw.putPushReg('eax')
-
- cw.putMovRegAddress('eax', picbuff)
- cw.putPushReg('eax')
- cw.putCallAddress(moduleBaseAddress.add(
- offset.send_picmsg_call_offset2
- ))
-
- cw.putMovRegReg('ecx', 'eax')
- cw.putCallAddress(moduleBaseAddress.add(
- offset.send_picmsg_call_offset3
- ))*/
-
- cw.putPopax()
- cw.putPopfx()
- cw.putRet()
- cw.flush()
-
- })
-
- console.log('----------picAsm', picAsm)
- const nativeativeFunction = new NativeFunction(ptr(picAsm), 'void', [])
- nativeativeFunction()
-
-})
/*------------------send pic --------------------------
let buffwxid = null
let imagefilepath = null
@@ -1764,156 +1827,6 @@ const sendPicMsgNativeFunction = ((contactId, path) => {
nativeativeFunction()
})*/
-/**
-* send at msg
-*/
-let asmAtMsg = null
-let roomid_, msg_, wxid_, atid_
-let ecxBuffer
-
-// 023
-const sendAtMsgNativeFunction = ((roomId, text, contactId) => {
- asmAtMsg = Memory.alloc(Process.pageSize)
- ecxBuffer = Memory.alloc(0x3b0)
-
-
- roomid_ = initStruct(roomId)
- wxid_ = initidStruct(contactId)
- msg_ = initmsgStruct(text)
- atid_ = initAtMsgStruct(wxid_)
-
- Memory.patchCode(asmAtMsg, Process.pageSize, code => {
- var cw = new X86Writer(code, { pc: asmAtMsg })
- //cw.putMovRegAddress('eax',roomid)
-
- cw.putPushfx();
- cw.putPushax();
-
- cw.putPushU32(1) // push
-
- cw.putMovRegAddress('edi', atid_)
- cw.putMovRegAddress('ebx', msg_)//msg_
-
- cw.putPushReg('edi')
- cw.putPushReg('ebx')
-
- //cw.putMovRegRegOffsetPtr('edx', 'ebp', 0x10)//at wxid
- cw.putMovRegAddress('edx', roomid_)//room_id
-
- cw.putMovRegAddress('ecx', ecxBuffer)
-
- cw.putCallAddress(moduleBaseAddress.add(
- offset.send_txt_call_offset
- ))
- cw.putAddRegImm('esp', 0xc)
-
- cw.putPopax()
- cw.putPopfx()
- cw.putRet()
- cw.flush()
- })
-
- const atMsgNativeFunction = new NativeFunction(ptr(asmAtMsg), 'void', [])
- atMsgNativeFunction()
-})
-
-/**
-* @Call: sendMsg -> agentSendMsg
-*/
-
-// 024
-const sendMsgNativeFunction = (() => {
- //const asmBuffer = Memory.alloc(/*0x5a8*/0x5f0) // magic number from wechat-bot (laozhang)
- const asmBuffer = Memory.alloc(0x5f0)
- const asmSendMsg = Memory.alloc(Process.pageSize)
- Memory.patchCode(asmSendMsg, Process.pageSize, code => {
- var cw = new X86Writer(code, { pc: asmSendMsg })
-
- cw.putPushReg('ebp')
- cw.putMovRegReg('ebp', 'esp')
- cw.putPushax()
- cw.putPushfx()
-
- cw.putPushU32(1) // push
- cw.putPushU32(0) // push
-
- cw.putMovRegRegOffsetPtr('ebx', 'ebp', 0xc) // arg 1
- cw.putPushReg('ebx') // push
-
- cw.putMovRegRegOffsetPtr('edx', 'ebp', 0x8) // arg 0
- cw.putMovRegAddress('ecx', asmBuffer)
-
- //0x3b56a0 3.2.1.121
- cw.putCallAddress(moduleBaseAddress.add(
- offset.send_txt_call_offset
- ))
- cw.putAddRegImm('esp', 0xc)
-
- cw.putPopfx()
- cw.putPopax()
- cw.putMovRegRegPtr('esp', 'ebp') // Huan(202107): why use RegRegPtr? (RegRet will fail)
- cw.putPopReg('ebp')
- cw.putRet()
-
- cw.flush()
- })
-
- /*let ins = Instruction.parse(asmSendMsg)
- for (let i=0; i<20; i++) {
- console.log(ins.address, '\t', ins.mnemonic, '\t', ins.opStr)
- ins = Instruction.parse(ins.next)
- }*/
-
- const asmNativeFunction = new NativeFunction(asmSendMsg, 'void', ['pointer', 'pointer'])
-
- const sendMsg = (
- talkerId,
- content,
- ) => {
- const talkerIdPtr = Memory.alloc(talkerId.length * 2 + 1)
- const contentPtr = Memory.alloc(content.length * 2 + 1)
-
- talkerIdPtr.writeUtf16String(talkerId)
- contentPtr.writeUtf16String(content)
-
- const sizeOfStringStruct = Process.pointerSize * 5 // + 0xd
-
- // allocate space for the struct
- const talkerIdStruct = Memory.alloc(sizeOfStringStruct) // returns a NativePointer
- const contentStruct = Memory.alloc(sizeOfStringStruct) // returns a NativePointer
-
- talkerIdStruct
- .writePointer(talkerIdPtr).add(0x4)
- .writeU32(talkerId.length).add(0x4)
- .writeU32(talkerId.length * 2)
-
- contentStruct
- .writePointer(contentPtr).add(0x4)
- .writeU32(content.length).add(0x4)
- .writeU32(content.length * 2)
-
- asmNativeFunction(talkerIdStruct, contentStruct)
- }
-
- /**
- * Best Practices
- * https://frida.re/docs/best-practices/
- *
- * There is however a pitfall: the value returned by Memory.allocUtf8String() must be kept alive
- * – it gets freed as soon as the JavaScript value gets garbage-collected.
- *
- * This means it needs to be kept alive for at least the duration of the function-call,
- * and in some cases even longer; the exact semantics depend on how the API was designed.
- */
- const refHolder = {
- asmBuffer,
- asmSendMsg,
- asmNativeFunction,
- sendMsg,
- }
-
- return (...args) => refHolder.sendMsg(...args)
-})()
// 025
const callLoginQrcodeFunction = ((forceRefresh = false) => {
diff --git a/src/wechat-sidecar.ts b/src/wechat-sidecar.ts
index 8e73d49..4b8ec6c 100644
--- a/src/wechat-sidecar.ts
+++ b/src/wechat-sidecar.ts
@@ -37,6 +37,7 @@ import { codeRoot } from './cjs.js'
const supportedVersions = {
v330115:'3.3.0.115',
v360000:'3.6.0.18',
+ v39223:'3.9.2.23',
}
// let initAgentScript = fs.readFileSync(path.join(
@@ -58,7 +59,7 @@ try {
// await detach(wechatVersion)
- const currentVersion = '3.6.0.18'
+ const currentVersion = '3.9.2.23'
switch (currentVersion) {
case supportedVersions.v330115:
@@ -82,6 +83,19 @@ try {
'init-agent-script.js',
), 'utf-8')
break
+ case supportedVersions.v39223:
+ // initAgentScript = fs.readFileSync(path.join(
+ // codeRoot,
+ // 'src',
+ // 'agents',
+ // 'agent-script-3.6.0.18.js',
+ // ), 'utf-8')
+ initAgentScript = fs.readFileSync(path.join(
+ codeRoot,
+ 'src',
+ 'init-agent-script.js',
+ ), 'utf-8')
+ break
default:
throw new Error(`Wechat version not supported. \nWechat version: ${currentVersion}, supported version: ${JSON.stringify(supportedVersions)}`)
}
From ad0e0e319e31e0f91ed48ac9dd7b95958ac183ef Mon Sep 17 00:00:00 2001
From: choogoo <104893934+choogoo@users.noreply.github.com>
Date: Tue, 11 Jul 2023 21:22:08 +0800
Subject: [PATCH 2/6] 3.9.2.23 init (#182)
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
* 3.9.2.23 initt
* Update init-agent-script.js
* 3.9.2.23 adapter
* 适配3.9.2.23
* Delete agent-script-3.9.2.23-new.js
---
...9.2.23-new.js => agent-script-3.9.2.23.js} | 1845 ++++++++---------
src/init-agent-script.js | 1845 ++++++++---------
2 files changed, 1780 insertions(+), 1910 deletions(-)
rename src/agents/{agent-script-3.9.2.23-new.js => agent-script-3.9.2.23.js} (95%)
diff --git a/src/agents/agent-script-3.9.2.23-new.js b/src/agents/agent-script-3.9.2.23.js
similarity index 95%
rename from src/agents/agent-script-3.9.2.23-new.js
rename to src/agents/agent-script-3.9.2.23.js
index f706c38..9c97f9a 100644
--- a/src/agents/agent-script-3.9.2.23-new.js
+++ b/src/agents/agent-script-3.9.2.23.js
@@ -8,11 +8,14 @@
//const { isNullishCoalesce } = require("typescript")
-//3.9.2.23
+// wechat:3.9.2.23
-// 偏移地址集合 done
+// 028 done
const offset = {
+
+
hook_point: 0xd19a0b, //3.9.2.23
+
myselfinfo: {
offset: 0x2FFD484, //老版本微信号偏移,后面的地址,都要在这个偏移上增加
//wxid_len:0x10,
@@ -23,6 +26,7 @@ const offset = {
//wxcode_len:0x74
wxid_len_offset: 0x4D4
},
+
contactInfo: {
nodeOffset: 0x2FFDD7C,
nodeRootOffset: 0x64
@@ -40,25 +44,20 @@ const offset = {
call3: 0xce6640
}
};
-//3.9.2.23
-// 全局配置 done
+// 029 done
/*------------------global-------------------------------------------*/
const availableVersion = 1661534743 ////3.9.2.23 ==0x63090217
const moduleBaseAddress = Module.getBaseAddress('WeChatWin.dll')
const moduleLoad = Module.load('WeChatWin.dll')
-//1575CF98
-
-// 全局变量 tbd
+// tbd
const g_EDIPtr = moduleBaseAddress.add(0x222f38c).readPointer().add(0xD70).readPointer()//
const g_EDIU32 = moduleBaseAddress.add(0x222f38c).readPointer().add(0xD70).readU32()
-
/*------------------global-------------------------------------------*/
/*---------------base -------------------------*/
-
-// done
+// 030 done
let retidPtr=null
let retidStruct=null
const initidStruct = ((str) => {
@@ -78,7 +77,7 @@ const initidStruct = ((str) => {
return retidStruct
})
-// done
+// 031 done
let retPtr = null
let retStruct = null
const initStruct = ((str) => {
@@ -98,7 +97,7 @@ const initStruct = ((str) => {
return retStruct
})
-// done
+// 032 done
let msgstrPtr=null
let msgStruct=null
const initmsgStruct = ((str) => {
@@ -117,7 +116,23 @@ const initmsgStruct = ((str) => {
return msgStruct
})
-// tbd
+// 034 done
+/**
+* at msg structure
+*/
+let atStruct = null
+const initAtMsgStruct = ((wxidStruct) => {
+
+ atStruct = Memory.alloc(0x10)
+
+ atStruct.writePointer(wxidStruct).add(0x04)
+ .writeU32(wxidStruct.toInt32() + 0x14).add(0x04)//0x14 = sizeof(wxid structure)
+ .writeU32(wxidStruct.toInt32() + 0x14).add(0x04)
+ .writeU32(0)
+ return atStruct
+})
+
+// 033 tbd
let retidNullStruct = null
let retidNullPtr = null
const initNullIdStruct = ((str) => {
@@ -137,25 +152,7 @@ const initNullIdStruct = ((str) => {
return retidNullStruct
})
-// done
-/**
-* at msg structure
-*/
-let atStruct = null
-const initAtMsgStruct = ((wxidStruct) => {
-
- atStruct = Memory.alloc(0x10)
-
- atStruct.writePointer(wxidStruct).add(0x04)
- .writeU32(wxidStruct.toInt32() + 0x14).add(0x04)//0x14 = sizeof(wxid structure)
- .writeU32(wxidStruct.toInt32() + 0x14).add(0x04)
- .writeU32(0)
- return atStruct
-})
-
-// done
-// std::string
-// const str = readStringPtr(ptr).readUtf8String()
+// 035 done
const readStringPtr = (address) => {
const addr = ptr(address)
const size = addr.add(16).readU32()
@@ -169,9 +166,15 @@ const readStringPtr = (address) => {
addr.ptr._readCString = addr.ptr.readCString
addr.ptr._readAnsiString = addr.ptr.readAnsiString
addr.ptr._readUtf8String = addr.ptr.readUtf8String
- addr.readCString = () => { return addr.size ? addr.ptr._readCString(addr.size) : '' }
- addr.readAnsiString = () => { return addr.size ? addr.ptr._readAnsiString(addr.size) : '' }
- addr.readUtf8String = () => { return addr.size ? addr.ptr._readUtf8String(addr.size) : '' }
+ addr.readCString = () => {
+ return addr.size ? addr.ptr._readCString(addr.size) : ''
+ }
+ addr.readAnsiString = () => {
+ return addr.size ? addr.ptr._readAnsiString(addr.size) : ''
+ }
+ addr.readUtf8String = () => {
+ return addr.size ? addr.ptr._readUtf8String(addr.size) : ''
+ }
// console.log('readStringPtr() address:',address,' -> str ptr:', addr.ptr, 'size:', addr.size, 'capacity:', addr.capacity)
// console.log('readStringPtr() str:' , addr.readUtf8String())
@@ -180,913 +183,853 @@ const readStringPtr = (address) => {
return addr
}
-// done
+// 036 done
const readString = (address) => {
return readStringPtr(address).readUtf8String()
}
-// done
+// 037 done
const readWideString = (address) => {
return readWStringPtr(address).readUtf16String()
}
+/*-----------------base-------------------------*/
+
+// 041
+// std::wstring
+// const wstr = readWStringPtr(ptr).readUtf16String()
+const readWStringPtr = (address) => {
+ const addr = ptr(address)
+ const size = addr.add(4).readU32()
+ const capacity = addr.add(8).readU32()
+ addr.ptr = addr.readPointer()
+ addr.size = size
+ addr.capacity = capacity
+ addr.ptr._readUtf16String = addr.ptr.readUtf16String
+ addr.readUtf16String = () => {
+ return addr.size ? addr.ptr._readUtf16String(addr.size * 2) : ''
+ }
+
+ // console.log('readWStringPtr() address:',address,' -> ptr:', addr.ptr, 'size:', addr.size, 'capacity:', addr.capacity)
+ // console.log('readWStringPtr() str:' , `"${addr.readUtf16String()}"`,'\n',addr.ptr.readByteArray(addr.size*2+2),'\n')
+ // console.log('readWStringPtr() address:', addr,'dump:', addr.readByteArray(16),'\n')
+
+ return addr
+}
/*-----------------base-------------------------*/
+// 010 done
let currentVersion = 0
-let nodeList = [] //for contact
+let nodeList = [] //for contact
let contactList = [] //for contact
let chatroomNodeList = [] //for chatroom
-let chatroomMemberList = []//for chatroom
+let chatroomMemberList = [] //for chatroom
let loggedIn = false
-//开启日志 3.6.0.18
-// //[0x221c330+wechatwin.dll]+0xf8
-// 20220504
+const getWechatVersionFunction = (() => {
+ if (currentVersion) {
+ return currentVersion
+ }
+ const pattern = '55 8B ?? 83 ?? ?? A1 ?? ?? ?? ?? 83 ?? ?? 85 ?? 7F ?? 8D ?? ?? E8 ?? ?? ?? ?? 84 ?? 74 ?? 8B ?? ?? ?? 85 ?? 75 ?? E8 ?? ?? ?? ?? 0F ?? ?? 0D ?? ?? ?? ?? A3 ?? ?? ?? ?? A3 ?? ?? ?? ?? 8B ?? 5D C3'
+ const results = Memory.scanSync(moduleLoad.base, moduleLoad.size, pattern)
+ if (results.length == 0) {
+ return 0
+ }
+ const addr = results[0].address
+ const ret = addr.add(0x07).readPointer()
+ const ver = ret.add(0x0).readU32()
+ currentVersion = ver
+ return ver
+})
-let g_initTestAsm = null
-let g_BufferEbp2C = null
-let g_initECXU32 = null
-let g_initECXPtr = null
-let g_initEBXPtr = null
-let g_initEBX = null
+// 011 done
+const getWechatVersionStringFunction = ((ver = getWechatVersionFunction()) => {
+ if (!ver) {
+ return '0.0.0.0'
+ }
+ const vers = []
+ vers.push((ver >> 24) & 255 - 0x60)
+ vers.push((ver >> 16) & 255)
+ vers.push((ver >> 8) & 255)
+ vers.push(ver & 255)
+ return vers.join('.')
+})
-let g_attatchEBP210Buffer = null
-let g_attatchPathPtr = null
-let g_attatchPath = null
-let g_attatchEBPAc = null
-let g_attatchEBPAcBufPtr = null
+// 012 done
+const checkSupportedFunction = (() => {
+ const ver = getWechatVersionFunction()
+ return ver == availableVersion
+})
-let g_attatchContactIdPtr = null
-//let g_attatchECXBuffer = null
-let g_attatchESIU32 = null
+// 019 done
+/**
+ * @Hook: recvMsg -> recvMsgNativeCallback
+ */
+ const recvMsgNativeCallback = (() => {
-let g_initECXTempPtr = null
-const initGlobal = ((contactId, attatchFile) => {
- //const base = moduleBaseAddress.add(0x222f38c).readPointer()
- //g_EDI = base.add(0xD70).readPointer()//0x438+0x938
- console.log('------------g_attatchEBPAc', g_attatchEBPAc)
- console.log('------------g_EDIU32', g_EDIU32)
- g_initTestAsm = Memory.alloc(Process.pageSize)
- console.log('------------address', g_initTestAsm)
+ const nativeCallback = new NativeCallback(() => {}, 'void', ['int32', 'pointer', 'pointer', 'pointer', 'pointer', 'int32'])
+ const nativeativeFunction = new NativeFunction(nativeCallback, 'void', ['int32', 'pointer', 'pointer', 'pointer', 'pointer', 'int32'])
- g_initECXPtr = g_EDIPtr.add(0xB80).readPointer().add(0x1640)
- g_initECXTempPtr = g_EDIPtr.add(0xB88).readPointer()
- g_initECXU32 = g_initECXPtr.toInt32()
- g_attatchESIU32 = g_EDIU32
+ Interceptor.attach(
+ moduleBaseAddress.add(offset.hook_point), {
+ onEnter() {
+ const addr = this.context.ecx //0xc30-0x08
+ const msgType = addr.add(0x38).readU32()
+ const isMyMsg = addr.add(0x3C).readU32() //add isMyMsg
- console.log('------------g_initECXU32', g_initECXU32)
- console.log('------------g_initESIU32', g_attatchESIU32)
+ if (msgType > 0) {
+ const talkerIdPtr = addr.add(0x48).readPointer()
+ //console.log('txt msg',talkerIdPtr.readUtf16String())
+ const talkerIdLen = addr.add(0x48 + 0x04).readU32() * 2 + 2
- //console.log('==========g_initECXPtr',g_initECXPtr)
- //console.log('==========g_EDIU32',g_EDIU32)
+ const myTalkerIdPtr = Memory.alloc(talkerIdLen)
+ Memory.copy(myTalkerIdPtr, talkerIdPtr, talkerIdLen)
- //g_attatchECXBuffer = Memory.alloc(0x1024)
- //Memory.copy(g_attatchECXBuffer, g_initECXPtr, 0x1024)
- g_BufferEbp2C = Memory.alloc(0x48)
+ let contentPtr = null
+ let contentLen = 0
+ let myContentPtr = null
+ if (msgType == 3) { // pic path
+ let thumbPtr = addr.add(0x198).readPointer();
+ let hdPtr = addr.add(0x1ac).readPointer();
+ let thumbPath = thumbPtr.readUtf16String();
+ let hdPath = hdPtr.readUtf16String();
+ let picData = [
+ thumbPath, // PUPPET.types.Image.Unknown
+ thumbPath, // PUPPET.types.Image.Thumbnail
+ hdPath, // PUPPET.types.Image.HD
+ hdPath // PUPPET.types.Image.Artwork
+ ]
+ let content = JSON.stringify(picData);
+ myContentPtr = Memory.allocUtf16String(content);
+ } else {
+ contentPtr = addr.add(0x70).readPointer()
+ contentLen = addr.add(0x70 + 0x04).readU32() * 2 + 2
+ myContentPtr = Memory.alloc(contentLen)
+ Memory.copy(myContentPtr, contentPtr, contentLen)
+ }
- //g_initEBX = moduleBaseAddress.add(0x2251724).readPointer().readPointer()
- //g_initEBXPtr = Memory.alloc(0x14).writePointer(g_initEBX)
- //g_initEBXPtr.add(0x08).writePointer(g_BufferEbp2C)
+ // console.log('----------------------------------------')
+ // console.log(msgType)
+ // console.log(contentPtr.readUtf16String())
+ // console.log('----------------------------------------')
+ const groupMsgAddr = addr.add(0x170).readU32() //* 2 + 2
+ let myGroupMsgSenderIdPtr = null
+ if (groupMsgAddr == 0) { //weChatPublic is zero,type is 49
- g_attatchPathPtr = Memory.alloc(attatchFile.length * 2 + 2)
- g_attatchPathPtr.writeUtf16String(attatchFile)
+ myGroupMsgSenderIdPtr = Memory.alloc(0x10)
+ myGroupMsgSenderIdPtr.writeUtf16String("null")
- g_attatchPath = Memory.alloc(0x28)
- g_attatchPath.writePointer(g_attatchPathPtr).add(0x04)
- .writeU32(attatchFile.length * 2).add(0x04)
- .writeU32(attatchFile.length * 2).add(0x04)
- /*---------------------------------ebp-210----------------*/
- g_attatchEBP210Buffer = Memory.alloc(0x48)
- g_attatchEBP210Buffer.writeU32(0x3)
- g_attatchEBP210Buffer.add(0x4).writePointer(g_attatchPathPtr)
- g_attatchEBP210Buffer.add(0x8).writeU32(attatchFile.length * 2)
- g_attatchEBP210Buffer.add(0xC).writeU32(attatchFile.length * 2)
- g_attatchEBP210Buffer.add(0x2C).writeU32(moduleBaseAddress.add(0x2ECE87).toInt32())
- //console.log('------------g_attatchEBP210Buffer',g_attatchEBP210Buffer)
- /*---------------------------------ebp-210----------------*/
+ } else {
- //g_attatchContactIdPtr = Memory.alloc(0x4)
- //g_attatchContactIdPtr.writeUtf16String(contactId)
- //console.log('------------g_attatchEBP210Buffer',g_attatchEBP210Buffer)
- g_attatchEBPAc = Memory.alloc(0x140)
- //g_attatchEBPAcBufPtr = Memory.alloc(0x100)
- //g_attatchEBPAc.writePointer(g_attatchEBP210Buffer)
- //g_attatchEBPAc.add(0x4).writePointer(g_attatchEBPAcBufPtr)
- //g_attatchEBPAc.add(0x8).writePointer(g_attatchEBPAcBufPtr)
- g_attatchEBPAc.add(0x10).writeU32(g_EDIU32)
- console.log('------------g_attatchEBPAc', g_attatchEBPAc)
+ const groupMsgSenderIdPtr = addr.add(0x170).readPointer()
+ const groupMsgSenderIdLen = addr.add(0x170 + 0x04).readU32() * 2 + 2
+ myGroupMsgSenderIdPtr = Memory.alloc(groupMsgSenderIdLen)
+ Memory.copy(myGroupMsgSenderIdPtr, groupMsgSenderIdPtr, groupMsgSenderIdLen)
- /*g_attatchECXBuffer.add(0x18).writePointer(g_attatchContactIdPtr)
- g_attatchECXBuffer.add(0x1C).writeU32(contactId.length*2)
- .add(0x04).writeU32(contactId.length*2)*/
+ }
+ const xmlNullPtr = addr.add(0x1f0).readU32() //3.9.2.23
+ let myXmlContentPtr = null
+ if (xmlNullPtr == 0) {
+ myXmlContentPtr = Memory.alloc(0x10)
+ myXmlContentPtr.writeUtf16String("null")
- //g_attatchESIU32 = g_EDI.toInt32()
+ } else {
+ const xmlContentPtr = addr.add(0x1f0).readPointer() //3.9.2.23
+ const xmlContentLen = addr.add(0x1f0 + 0x04).readU32() * 2 + 2
+ myXmlContentPtr = Memory.alloc(xmlContentLen)
+ Memory.copy(myXmlContentPtr, xmlContentPtr, xmlContentLen)
+ }
- //console.log('------------g_attatchESIU32',g_attatchESIU32)
- //console.log('==========g_attatchECXBuffer',g_attatchECXBuffer)
+ setImmediate(() => nativeativeFunction(msgType, myTalkerIdPtr, myContentPtr, myGroupMsgSenderIdPtr, myXmlContentPtr, isMyMsg))
+ }
+ }
+ })
+ return nativeCallback
+})()
- Memory.patchCode(g_initTestAsm, Process.pageSize, code => {
- var cw = new X86Writer(code, { pc: g_initTestAsm })
- cw.putPushfx()
- cw.putPushax()
- //cw.putMovRegAddress('eax', g_attatchEBP210Buffer)
+// 003 done
+const getBaseNodeAddress = (() => {
+ return moduleBaseAddress.add(offset.contactInfo.nodeOffset).readPointer()
+})
- /*cw.putMovRegAddress('edi',g_EDIPtr)
- cw.putMovRegReg('esi','edi')
- cw.putMovRegAddress('eax',g_BufferEbp2C)
- cw.putMovRegAddress('ecx',g_initECXTempPtr)
- cw.putPushReg('eax')
- cw.putCallAddress(moduleBaseAddress.add(0x131bb0))*/
+// 004 done
+const getHeaderNodeAddress = (() => {
+ const baseAddress = getBaseNodeAddress()
+ //console.log('baseAddress',baseAddress)
+ if (baseAddress.isNull()) {
+ return baseAddress
+ }
- //cw.putMovRegOffsetPtrU32('ebp', -20, 0)
-
- /*cw.putPushU32(0)
- cw.putMovRegAddress('eax', g_attatchPathPtr)
- cw.putPushReg('eax')
- cw.putPushU32(3)
- cw.putMovRegAddress('ecx', g_attatchEBP210Buffer)
- cw.putCallAddress(moduleBaseAddress.add(0x130220))*/
+ //console.log('HeaderNodeAddress',baseAddress.add(offset.handle_offset).readPointer())
+ return baseAddress.add(offset.contactInfo.nodeRootOffset).readPointer()
+})
+// 006 done
+const getMyselfInfoFunction = (() => {
- /*cw.putMovRegAddress('edi', g_attatchEBPAc)//后面要用的的ebp-2c
- cw.putMovRegAddress('ecx', g_attatchEBP210Buffer)
- cw.putPushReg('ecx')
- cw.putMovRegU32('eax',0)
- cw.putPushReg('eax')//push eax
- cw.putMovRegReg('ecx', 'edi')
- cw.putMovRegAddress('esi',g_attatchPathPtr)
- cw.putCallAddress(moduleBaseAddress.add(0x138880))*/
+ let ptr = 0
+ let wx_code = ''
+ let wx_id = ''
+ let wx_name = ''
+ let head_img_url = ''
+ const base = moduleBaseAddress.add(offset.myselfinfo.offset)
+ const wxid_len = base.add(offset.myselfinfo.wxid_len_offset).readU32()
- /*cw.putSubRegImm('esp',0x14)
- cw.putMovRegU32('ecx',g_initECXU32)
- cw.putMovRegU32('esi',g_attatchESIU32)
- cw.putMovRegAddress('eax', g_attatchEBPAc)
- cw.putPushReg('eax')
- cw.putCallAddress(moduleBaseAddress.add(0x173620))*/
- //cw.putCallAddress(moduleBaseAddress.add(0x522590))
+ if (wxid_len === 0x13) { // 新版本微信
+ wx_id = base.readPointer().readAnsiString(wxid_len)
+ wx_code = base.add(offset.myselfinfo.wxcode_new).readAnsiString()
+ } else {
+ wx_id = readString(base)
+ wx_code = wx_id
+ }
- /** g_attatchEBPAc*/
- //cw.putMovRegNearPtr('eax', g_attatchEBPAc)
- //cw.putMovNearPtrReg(g_attatchEBPAc.add(0xc), 'eax')
- /** g_attatchEBPAc*/
+ wx_name = readString(base.add(offset.myselfinfo.wx_nick_name))
+ const img_addr = base.add(offset.myselfinfo.head_img_url).readPointer()
+ const img_len = base.add(offset.myselfinfo.head_img_url_len).readU32()
- //cw.putMovRegAddress('ebx', g_initEBXPtr)
- //cw.putMovRegU32('edi', g_EDI.toInt32())
- //cw.putMovRegU32('esi', g_EDI.toInt32())
- /*cw.putMovRegU32('ecx', g_initECX)
- cw.putMovRegAddress('eax', g_BufferEbp2C)
- cw.putPushReg('eax')
- cw.putCallAddress(moduleBaseAddress.add(0x131BB0))*/
+ head_img_url = img_addr.readAnsiString(img_len)
- cw.putPopax()
- cw.putPopfx()
- cw.putRet()
- cw.flush()
+ const myself = {
+ id: wx_id,
+ code: wx_code,
+ name: wx_name,
+ head_img_url: head_img_url,
+ };
- })
+ return JSON.stringify(myself)
- const nativeativeFunction = new NativeFunction(ptr(g_initTestAsm), 'void', [])
- nativeativeFunction()
})
+// 043 done
+const recurseNew = ((node) => {
+ const headerNodeAddress = getHeaderNodeAddress()
+ if (headerNodeAddress.isNull()) {
+ return
+ }
-let g_personal_detail_ebx = null
-let g_personal_detail_asm = null
-let g_personal_wxid = null
-let g_personal_wxid_ptr = null
-const getOldTest = ((wxid) => {//personal detail
+ if (node.equals(headerNodeAddress)) {
+ return
+ }
- g_personal_detail_asm = Memory.alloc(Process.pageSize)
- g_personal_detail_ebx = moduleBaseAddress.add(0x222F38C).readPointer().add(0xFB8).toInt32()
+ for (const item in nodeList) {
+ if (node.equals(nodeList[item])) {
+ return
+ }
+ }
- g_personal_wxid_ptr = Memory.alloc(wxid.length * 2 + 2)
- g_personal_wxid_ptr.writeUtf16String(wxid)
- g_personal_wxid = Memory.alloc(0x14)
- g_personal_wxid.writePointer(ptr(g_personal_wxid_ptr)).add(0x04)
- .writeU32(wxid.length * 2).add(0x04)
- .writeU32(wxid.length * 2).add(0x08)
+ nodeList.push(node)
+ const id = readString(node.add(0x8))
+ //wxid, format relates to registration method
+ const wxid = readWideString(node.add(0x30))
+ //console.log('-----------',wxid)
- console.log('-----------address----------', g_personal_detail_asm)
- Memory.patchCode(g_personal_detail_asm, Process.pageSize, code => {
- var cw = new X86Writer(code, { pc: g_personal_detail_asm })
- cw.putPushfx()
- cw.putPushax()
+ //custom id, if not set return null, and use wxid which should be custom id
+ //const wx_code = readWideString(node.add(0x4c)) || readWideString(node.add(0x38))
- cw.putCallAddress(moduleBaseAddress.add(0x9A000))
+ //custom Nickname
+ const name = readWideString(node.add(0x8c))
- //78BA9ACE | E8 2D05D6FF | call wechatwin.7890A000 |
- cw.putMovRegU32('ebx', g_personal_detail_ebx)
- cw.putMovRegReg('esi', 'eax')
- cw.putPushReg('ebx')
- cw.putSubRegImm('esp', 0x14)
- cw.putMovRegAddress('eax', g_personal_wxid)
- cw.putMovRegReg('ecx', 'esp')
- cw.putPushReg('eax')
- cw.putCallAddress(moduleBaseAddress.add(0x701DC0))
- cw.putMovRegReg('ecx', 'esi')
- cw.putCallAddress(moduleBaseAddress.add(0x4024A0))
+ //alias aka 'remark' in wechat
+ //const alias = readWideString(node.add(0x80))
- cw.putPopax()
- cw.putPopfx()
- cw.putRet()
- cw.flush()
+ //avatarUrl
+ //const avatar = readWideString(node.add(0x138))
+ //const avatar = Memory.readUtf16String(node.add(0x138).readPointer())
+ //contact gender
+ //const gender = node.add(0x18C).readU32()
- })
+ const contactJson = {
+ id1: id,
+ id: wxid,
+ name: name,
+ /*code: wx_code,
+ name: name,
+ alias: alias,
+ avatarUrl: avatar,
+ gender: gender,*/
+ }
- const nativeativeFunction = new NativeFunction(ptr(g_personal_detail_asm), 'void', [])
- nativeativeFunction()
+ contactList.push(contactJson)
+ const leftNode = node.add(0x0).readPointer()
+ const centerNode = node.add(0x04).readPointer()
+ //const rightNode = node.add(0x08).readPointer()
-})
+ recurseNew(leftNode)
+ recurseNew(centerNode)
+ //recurse(rightNode)
-// const writeLogNativeCallback = (() => {
-// const nativeCallback = new NativeCallback(() => { }, 'void', [])
-// const nativeCallFunction = new NativeFunction(nativeCallback, 'void', [])
+ const allContactJson = contactList
+ return allContactJson
-// Interceptor.attach(
-// moduleBaseAddress.add(0x7008A4),
-// {
-// onEnter() {
-// const addr = this.context.eax//.sub(0x114)//0xc30-0x08
-// if(addr >0){
-// const log = ptr(addr).readAnsiString()
-// }
-// }
-// })
-// return nativeCallback
-// })()
+})
-/**
- * test call
- */
-let attatchTestAsm = null
-let attatchTestEbp2C = null
-let attatchGlobalEDI = null
-let attatchGlobalEDIB88 = null
-let attatchTestEBX = null
-let g_tempEcx = null
-let attatchFirstECX = null
-//let attatchFirstECX = null
-let gattatchFilePtr = null
-let gattatchFile = null
-let gattatchReceiveIdPtr = null
-let gattatchReceiveId = null
-let attatchEAX3B0Buf = null
+// 044 done
+const getContactNativeFunction = (() => {
+ const headerNodeAddress = getHeaderNodeAddress()
+ //console.log('headerNodeAddress',headerNodeAddress)
-let attatchESIbuf = null
-const getWxTest = ((contactId, filePath) => {
- //const nativeativeFunction = new NativeFunction(ptr(addr), 'void', [])
- //nativeativeFunction()
- attatchTestAsm = Memory.alloc(Process.pageSize)
- console.log('----------------address', attatchTestAsm)
- attatchTestEbp2C = Memory.alloc(0xC)
- attatchGlobalEDI = moduleBaseAddress.add(0x222f38c).readPointer()
- .add(0x938).add(0x438).readPointer()
- attatchGlobalEDIB88 = attatchGlobalEDI.add(0xB88).readPointer()
- attatchTestEBX = Memory.alloc(0x4)
- attatchTestEBX.writePointer(attatchGlobalEDI)
- console.log('----------------attatchGlobalEDI', attatchGlobalEDI)
- console.log('----------------attatchGlobalEDIB88', attatchGlobalEDIB88)
+ if (headerNodeAddress.isNull()) {
+ return '[]'
+ }
- attatchFirstECX = Memory.alloc(0x28)
- //const attatchSecondEcx = Memory.alloc(0x14)
+ const node = headerNodeAddress.add(0x0).readPointer()
+ const ret = recurseNew(node)
- const contactIdLength = contactId.length * 2 + 2//edx
- const contractIdActLength = contactId.length
+ //console.log(ret)
+ console.log('getContactNativeFunction:', ret.length)
+ /*for (let item of ret){
+ console.log(JSON.stringify(item))
+ }*/
+ //console.log(ret.contact)
+ const cloneRet = JSON.stringify(ret)
+ nodeList.length = 0
+ contactList.length = 0
- gattatchReceiveIdPtr = Memory.alloc(contactId.length * 2 + 2)
- gattatchReceiveIdPtr.writeUtf16String(contactId)
+ return cloneRet
+})
- gattatchReceiveId = Memory.alloc(0x14)
- gattatchReceiveId.writePointer(ptr(gattatchReceiveIdPtr)).add(0x04)
- .writeU32(contactId.length * 2).add(0x04)
- .writeU32(contactId.length * 2).add(0x08)
- //console.log('----------------attatchGlobalEDIB88',attatchGlobalEDIB88)
- //return
- /*console.log(hexdump(attatchTestEBX, {
- offset: 0,
- length: 0x40,
- header: true,
- ansi: true
- }))
- return*/
+// 0xx done
+const getChatroomNodeAddress = (() => {
+ const baseAddress = moduleBaseAddress.add(offset.chatroomInfo.nodeOffset).readPointer()
+ if (baseAddress.isNull()) {
+ return baseAddress
+ }
+ return baseAddress.add(offset.chatroomInfo.nodeRootOffset).readPointer()
+})
- gattatchFilePtr = Memory.alloc(filePath.length * 2 + 2)
- gattatchFilePtr.writeUtf16String(filePath)
-
- gattatchFile = Memory.alloc(0x14)
- gattatchFile.writePointer(ptr(gattatchFilePtr)).add(0x04)
- .writeU32(filePath.length * 2).add(0x04)
- .writeU32(filePath.length * 2).add(0x08)
-
- const attatchLastECX = moduleBaseAddress.add(0x222f170).toInt32()
-
- attatchEAX3B0Buf = Memory.alloc(0x3B0)
-
- g_tempEcx = Memory.alloc(0x4)
- //g_tempEcx1 = Memory.alloc(0x4)
-
- attatchESIbuf = Memory.alloc(0x100)
- attatchESIbuf.add(0x0).writeU32(3)
- attatchESIbuf.add(0x4).writePointer(gattatchFilePtr)
- attatchESIbuf.add(0x8).writeU32(filePath.length * 2)
- attatchESIbuf.add(0xc).writeU32(filePath.length * 2)
-
- Memory.patchCode(attatchTestAsm, Process.pageSize, code => {
- var cw = new X86Writer(code, { pc: attatchTestAsm })
- cw.putPushfx()
- cw.putPushax()
- //cw.putMovRegU32('edi',attatchGlobalEDI)
-
-
- cw.putMovRegAddress('esi', attatchESIbuf)
-
- cw.putMovRegAddress('ecx', attatchFirstECX.add(0x14))
- cw.putMovRegAddress('eax', gattatchFile)
- cw.putPushReg('eax')
- cw.putCallAddress(moduleBaseAddress.add(0x701DC0))
-
-
- cw.putMovRegAddress('ecx', attatchFirstECX)
- cw.putMovRegU32('eax', contactIdLength)
- cw.putPushReg('eax')
- cw.putPushU32(0)
- cw.putCallAddress(moduleBaseAddress.add(0x1a11c83))
- cw.putAddRegImm('esp', 0x8)
-
- cw.putMovRegReg('edx', 'eax')
- cw.putMovNearPtrReg(attatchFirstECX, 'edx')
- cw.putMovRegU32('edi', contactIdLength)
- cw.putPushReg('edi')
- cw.putMovRegAddress('eax', gattatchReceiveIdPtr)//ebp-58
- cw.putPushReg('eax')
- cw.putMovRegNearPtr('eax', attatchFirstECX)
- cw.putPushReg('eax')
- cw.putCallAddress(moduleBaseAddress.add(0x1a1047a))
- cw.putAddRegImm('esp', 0x0c)
-
- //cw.putMovRegNearPtr('ecx',attatchFirstECX)
- //cw.putAddRegImm('esp', 0x0c)
- //cw.putMovRegU32('edx', 0)
- //cw.putMovRegRegPtr('eax', 'ecx')
- //cw.putMovNearPtrReg(attatchFirstECX.add(0x04),'edi')
- cw.putMovRegU32('edi', contactId.length * 2)
- cw.putMovRegU32('ecx', attatchLastECX)
- cw.putMovRegAddress('eax', attatchEAX3B0Buf)
- cw.putPushReg('eax')
- cw.putCallAddress(moduleBaseAddress.add(0x392260))
-
- cw.putMovRegAddress('ecx', attatchEAX3B0Buf)
- cw.putCallAddress(moduleBaseAddress.add(0x94200))
-
- cw.putPopax()
- cw.putPopfx()
- cw.putRet()
- cw.flush()
-
- })
-
- const nativeativeFunction = new NativeFunction(ptr(attatchTestAsm), 'void', [])
- nativeativeFunction()
+// 008chatroom member done
+const chatroomRecurse = ((node) => {
+ const chatroomNodeAddress = getChatroomNodeAddress()
+ if (chatroomNodeAddress.isNull()) {
+ return
+ }
+ if (node.equals(chatroomNodeAddress)) {
+ return
+ }
-})
-// 001
-const getTestInfoFunction = ((addr) => {
- const nativeativeFunction = new NativeFunction(ptr(addr), 'void', [])
- nativeativeFunction()
+ for (const item in chatroomNodeList) {
+ if (node.equals(chatroomNodeList[item])) {
+ return
+ }
+ }
- //00CFE484
+ chatroomNodeList.push(node)
+ const roomid = readWideString(node.add(0x10))
+ const len = node.add(0x54).readU32() //
+ //const memberJson={}
+ if (len > 4) { //
+ const memberStr = readString(node.add(0x44))
+ if (memberStr.length > 0) {
+ const memberList = memberStr.split(/[\\^][G]/)
+ const memberJson = {
+ roomid: roomid,
+ roomMember: memberList
+ }
- /*MemoryAccessMonitor.enable({base:ptr(addr),size:0x01}, {
- onAccess(details){
- console.log('============')
- console.log(details.operation)
- console.log(details.from)
- console.log(details.address)
- console.log('============')
+ chatroomMemberList.push(memberJson)
}
- })*/
-})
+ }
-// 002get global data
+ const leftNode = node.add(0x0).readPointer()
+ const centerNode = node.add(0x04).readPointer()
+ const rightNode = node.add(0x08).readPointer()
-const isLoggedInFunction = (() => {
- loggedIn = moduleBaseAddress.add(offset.is_logged_in_offset).readU32()
- return !!loggedIn
-})
+ chatroomRecurse(leftNode)
+ chatroomRecurse(centerNode)
+ chatroomRecurse(rightNode)
-// 007 缺失,请标注已废弃或者其他原因
-const getMyselfIdFunction = (() => {
+ const allChatroomMemberJson = chatroomMemberList
+ return allChatroomMemberJson
+})
- let wx_id = readString(moduleBaseAddress.add(offset.wxid_offset))
+// 009 done
+const getChatroomMemberInfoFunction = (() => {
+ const chatroomNodeAddress = getChatroomNodeAddress()
+ if (chatroomNodeAddress.isNull()) {
+ return '[]'
+ }
- return wx_id
+ const node = chatroomNodeAddress.add(0x0).readPointer()
+ const ret = chatroomRecurse(node)
+ const cloneRet = JSON.stringify(ret)
+ chatroomNodeList.length = 0 //empty
+ chatroomMemberList.length = 0 //empty
+ return cloneRet
})
-// std::wstring
-// const wstr = readWStringPtr(ptr).readUtf16String()
-const readWStringPtr = (address) => {
- const addr = ptr(address)
- const size = addr.add(4).readU32()
- const capacity = addr.add(8).readU32()
- addr.ptr = addr.readPointer()
- addr.size = size
- addr.capacity = capacity
- addr.ptr._readUtf16String = addr.ptr.readUtf16String
- addr.readUtf16String = () => { return addr.size ? addr.ptr._readUtf16String(addr.size * 2) : '' }
-
- // console.log('readWStringPtr() address:',address,' -> ptr:', addr.ptr, 'size:', addr.size, 'capacity:', addr.capacity)
- // console.log('readWStringPtr() str:' , `"${addr.readUtf16String()}"`,'\n',addr.ptr.readByteArray(addr.size*2+2),'\n')
- // console.log('readWStringPtr() address:', addr,'dump:', addr.readByteArray(16),'\n')
+// 024 done
+/**
+ * sendMsgNativeFunction
+ * send text message
+ * @param {string} talkerId = wxid or roomid
+ * @param {string} content
+ */
+ const sendMsgNativeFunction = ((talkerId, content) => {
- return addr
-}
+ const txtAsm = Memory.alloc(Process.pageSize)
+ //const buffwxid = Memory.alloc(0x20)
-//contact
-const recurse = ((node) => {
- const headerNodeAddress = getHeaderNodeAddress()
- if (headerNodeAddress.isNull()) { return }
- if (node.equals(headerNodeAddress)) { return }
+ let wxidPtr = Memory.alloc(talkerId.length * 2 + 2)
+ wxidPtr.writeUtf16String(talkerId)
- for (const item in nodeList) {
- if (node.equals(nodeList[item])) {
- return
- }
- }
+ let picWxid = Memory.alloc(0x0c)
+ picWxid.writePointer(ptr(wxidPtr)).add(0x04)
+ .writeU32(talkerId.length * 2).add(0x04)
+ .writeU32(talkerId.length * 2).add(0x04)
+ let contentPtr = Memory.alloc(content.length * 2 + 2)
+ contentPtr.writeUtf16String(content)
- nodeList.push(node)
- //wxid, format relates to registration method
- const wxid = readWideString(node.add(0x38))
+ const sizeOfStringStruct = Process.pointerSize * 5
+ let contentStruct = Memory.alloc(sizeOfStringStruct)
- //custom id, if not set return null, and use wxid which should be custom id
- const wx_code = readWideString(node.add(0x4c)) || readWideString(node.add(0x38))
+ contentStruct
+ .writePointer(contentPtr).add(0x4)
+ .writeU32(content.length).add(0x4)
+ .writeU32(content.length * 2)
- //custom Nickname
- const name = readWideString(node.add(0x94))
- //alias aka 'remark' in wechat
- const alias = readWideString(node.add(0x80))
+ const ecxBuffer = Memory.alloc(0x2d8)
- //avatarUrl
- const avatar = readWideString(node.add(0x138))
- //const avatar = Memory.readUtf16String(node.add(0x138).readPointer())
- //contact gender
- const gender = node.add(0x18C).readU32()
+ Memory.patchCode(txtAsm, Process.pageSize, code => {
+ var cw = new X86Writer(code, {
+ pc: txtAsm
+ })
+ cw.putPushfx()
+ cw.putPushax()
- const contactJson = {
- id: wxid,
- code: wx_code,
- name: name,
- alias: alias,
- avatarUrl: avatar,
- gender: gender,
- }
+ cw.putPushU32(0x0)
+ cw.putPushU32(0x0)
+ cw.putPushU32(0x0)
+ cw.putPushU32(0x1)
+ cw.putPushU32(0x0)
- contactList.push(contactJson)
+ //cw.putMovRegReg
- const leftNode = node.add(0x0).readPointer()
- const centerNode = node.add(0x04).readPointer()
- const rightNode = node.add(0x08).readPointer()
+ cw.putMovRegAddress('eax', contentStruct)
+ cw.putPushReg('eax')
- recurse(leftNode)
- recurse(centerNode)
- recurse(rightNode)
+ cw.putMovRegAddress('edx', picWxid) //room_id
- const allContactJson = contactList
- return allContactJson
+ cw.putMovRegAddress('ecx', ecxBuffer)
+ cw.putCallAddress(moduleBaseAddress.add(
+ offset.sendTxtMsg.callOffset
+ ))
-})
+ cw.putAddRegImm('esp', 0x18)
+ cw.putPopax()
+ cw.putPopfx()
+ cw.putRet()
+ cw.flush()
-// 010 done
-const getWechatVersionFunction = (() => {
- if (currentVersion) {
- return currentVersion
- }
- const pattern = '55 8B ?? 83 ?? ?? A1 ?? ?? ?? ?? 83 ?? ?? 85 ?? 7F ?? 8D ?? ?? E8 ?? ?? ?? ?? 84 ?? 74 ?? 8B ?? ?? ?? 85 ?? 75 ?? E8 ?? ?? ?? ?? 0F ?? ?? 0D ?? ?? ?? ?? A3 ?? ?? ?? ?? A3 ?? ?? ?? ?? 8B ?? 5D C3'
- const results = Memory.scanSync(moduleLoad.base, moduleLoad.size, pattern)
- if (results.length == 0) {
- return 0
- }
- const addr = results[0].address
- const ret = addr.add(0x07).readPointer()
- const ver = ret.add(0x0).readU32()
- currentVersion = ver
- return ver
-})
+ })
-// 011 done
-const getWechatVersionStringFunction = ((ver = getWechatVersionFunction()) => {
- if (!ver) {
- return '0.0.0.0'
- }
- const vers = []
- vers.push((ver >> 24) & 255 - 0x60)
- vers.push((ver >> 16) & 255)
- vers.push((ver >> 8) & 255)
- vers.push(ver & 255)
- return vers.join('.')
-})
+ console.log('----------txtAsm', txtAsm)
+ const nativeativeFunction = new NativeFunction(ptr(txtAsm), 'void', [])
+ nativeativeFunction()
-// 012 done
-const checkSupportedFunction = (() => {
- const ver = getWechatVersionFunction()
- return ver == availableVersion
})
+// 023 done
/**
- * @Hook: recvMsg -> recvMsgNativeCallback
- */
+* send at msg
+*/
+let asmAtMsg = null
+let roomid_, msg_, wxid_, atid_
+let ecxBuffer
+const sendAtMsgNativeFunction = ((roomId, text, contactId,nickname) => {
-// 019 done
-const recvMsgNativeCallback = (() => {
+ asmAtMsg = Memory.alloc(Process.pageSize)
+ ecxBuffer = Memory.alloc(0x3b0)
+ const atContent = '@'+nickname+' '+text
- const nativeCallback = new NativeCallback(() => {}, 'void', ['int32', 'pointer', 'pointer', 'pointer', 'pointer', 'int32'])
- const nativeativeFunction = new NativeFunction(nativeCallback, 'void', ['int32', 'pointer', 'pointer', 'pointer', 'pointer', 'int32'])
+ roomid_ = initStruct(roomId)
+ wxid_ = initidStruct(contactId)
+ msg_ = initmsgStruct(atContent)
+ atid_ = initAtMsgStruct(wxid_)
- Interceptor.attach(
- moduleBaseAddress.add(offset.hook_point), {
- onEnter() {
- const addr = this.context.ecx //0xc30-0x08
- const msgType = addr.add(0x38).readU32()
- const isMyMsg = addr.add(0x3C).readU32() //add isMyMsg
+ Memory.patchCode(asmAtMsg, Process.pageSize, code => {
+ var cw = new X86Writer(code, {
+ pc: asmAtMsg
+ })
+ cw.putPushfx()
+ cw.putPushax()
- if (msgType > 0) {
+ cw.putPushU32(0x0)
+ cw.putPushU32(0x0)
+ cw.putPushU32(0x0)
+ cw.putPushU32(0x1)
+ //cw.putPushU32(0x0)
+ cw.putMovRegAddress('eax', atid_)
+ cw.putPushReg('eax')
- const talkerIdPtr = addr.add(0x48).readPointer()
- //console.log('txt msg',talkerIdPtr.readUtf16String())
- const talkerIdLen = addr.add(0x48 + 0x04).readU32() * 2 + 2
+ //cw.putMovRegReg
- const myTalkerIdPtr = Memory.alloc(talkerIdLen)
- Memory.copy(myTalkerIdPtr, talkerIdPtr, talkerIdLen)
+ cw.putMovRegAddress('eax', msg_)
+ cw.putPushReg('eax')
+ cw.putMovRegAddress('edx', roomid_) //room_id
- let contentPtr = null
- let contentLen = 0
- let myContentPtr = null
- if (msgType == 3) { // pic path
- let thumbPtr = addr.add(0x198).readPointer();
- let hdPtr = addr.add(0x1ac).readPointer();
- let thumbPath = thumbPtr.readUtf16String();
- let hdPath = hdPtr.readUtf16String();
- let picData = [
- thumbPath, // PUPPET.types.Image.Unknown
- thumbPath, // PUPPET.types.Image.Thumbnail
- hdPath, // PUPPET.types.Image.HD
- hdPath // PUPPET.types.Image.Artwork
- ]
- let content = JSON.stringify(picData);
- myContentPtr = Memory.allocUtf16String(content);
- } else {
- contentPtr = addr.add(0x70).readPointer()
- contentLen = addr.add(0x70 + 0x04).readU32() * 2 + 2
- myContentPtr = Memory.alloc(contentLen)
- Memory.copy(myContentPtr, contentPtr, contentLen)
- }
+ cw.putMovRegAddress('ecx', ecxBuffer)
+ cw.putCallAddress(moduleBaseAddress.add(
+ offset.sendTxtMsg.callOffset
+ ))
- // console.log('----------------------------------------')
- // console.log(msgType)
- // console.log(contentPtr.readUtf16String())
- // console.log('----------------------------------------')
- const groupMsgAddr = addr.add(0x170).readU32() //* 2 + 2
- let myGroupMsgSenderIdPtr = null
- if (groupMsgAddr == 0) { //weChatPublic is zero,type is 49
+ cw.putAddRegImm('esp', 0x18)
+ cw.putPopax()
+ cw.putPopfx()
+ cw.putRet()
+ cw.flush()
- myGroupMsgSenderIdPtr = Memory.alloc(0x10)
- myGroupMsgSenderIdPtr.writeUtf16String("null")
+ })
- } else {
+ //console.log('----------txtAsm', asmAtMsg)
+ const nativeativeFunction = new NativeFunction(ptr(asmAtMsg), 'void', [])
+ nativeativeFunction()
- const groupMsgSenderIdPtr = addr.add(0x170).readPointer()
- const groupMsgSenderIdLen = addr.add(0x170 + 0x04).readU32() * 2 + 2
- myGroupMsgSenderIdPtr = Memory.alloc(groupMsgSenderIdLen)
- Memory.copy(myGroupMsgSenderIdPtr, groupMsgSenderIdPtr, groupMsgSenderIdLen)
+})
- }
+// 022 done
+/**
+ *
+ * @param {*} contactId
+ * @param {*} path
+ */
+ const sendPicMsgNativeFunction = ((contactId, path) => {
- const xmlNullPtr = addr.add(0x1f0).readU32() //3.9.2.23
- let myXmlContentPtr = null
- if (xmlNullPtr == 0) {
+ const picAsm = Memory.alloc(Process.pageSize)
+ const buffwxid = Memory.alloc(0x20)
+ const picbuff = Memory.alloc(0x2D8)
- myXmlContentPtr = Memory.alloc(0x10)
- myXmlContentPtr.writeUtf16String("null")
+ let pathPtr = Memory.alloc(path.length * 2 + 1)
+ pathPtr.writeUtf16String(path)
- } else {
- const xmlContentPtr = addr.add(0x1f0).readPointer() //3.9.2.23
+ let imagefilepath = Memory.alloc(0x24)
+ imagefilepath.writePointer(pathPtr).add(0x04)
+ .writeU32(path.length * 2).add(0x04)
+ .writeU32(path.length * 2).add(0x04)
- const xmlContentLen = addr.add(0x1f0 + 0x04).readU32() * 2 + 2
- myXmlContentPtr = Memory.alloc(xmlContentLen)
- Memory.copy(myXmlContentPtr, xmlContentPtr, xmlContentLen)
- }
+ let picWxidPtr = Memory.alloc(contactId.length * 2 + 1)
+ picWxidPtr.writeUtf16String(contactId)
- setImmediate(() => nativeativeFunction(msgType, myTalkerIdPtr, myContentPtr, myGroupMsgSenderIdPtr, myXmlContentPtr, isMyMsg))
- }
- }
- })
- return nativeCallback
-})()
+ let picWxid = Memory.alloc(0x0c)
+ picWxid.writePointer(ptr(picWxidPtr)).add(0x04)
+ .writeU32(contactId.length * 2).add(0x04)
+ .writeU32(contactId.length * 2).add(0x04)
-// 003get myself info done
-const getBaseNodeAddress = (() => {
- return moduleBaseAddress.add(offset.contactInfo.nodeOffset).readPointer()
-})
-// 004 done
-const getHeaderNodeAddress = (() => {
- const baseAddress = getBaseNodeAddress()
- //console.log('baseAddress',baseAddress)
- if (baseAddress.isNull()) {
- return baseAddress
- }
+ //const test_offset1 = 0x701DC0;
+ Memory.patchCode(picAsm, Process.pageSize, code => {
+ var cw = new X86Writer(code, {
+ pc: picAsm
+ })
+ cw.putPushfx();
+ cw.putPushax();
+ cw.putCallAddress(moduleBaseAddress.add(
+ offset.sendPicMsg.call1
+ ))
+ cw.putMovRegReg('edx', 'eax') //缓存
- //console.log('HeaderNodeAddress',baseAddress.add(offset.handle_offset).readPointer())
- return baseAddress.add(offset.contactInfo.nodeRootOffset).readPointer()
-})
+ cw.putSubRegImm('esp', 0x14)
+ cw.putMovRegAddress('eax', buffwxid)
+ cw.putMovRegReg('ecx', 'esp')
+ cw.putMovRegAddress('edi', imagefilepath)
+ cw.putPushReg('eax')
+ cw.putCallAddress(moduleBaseAddress.add(
+ offset.sendPicMsg.call2
+ ))
-// 006 done
-const getMyselfInfoFunction = (() => {
+ cw.putMovRegReg('ecx', 'edx')
+ cw.putMovRegAddress('eax', picWxid) //=lea
+ cw.putMovRegAddress('edi', imagefilepath)
+ cw.putPushReg('edi')
+ cw.putPushReg('eax')
+ cw.putMovRegAddress('eax', picbuff)
+ cw.putPushReg('eax')
- let ptr = 0
- let wx_code = ''
- let wx_id = ''
- let wx_name = ''
- let head_img_url = ''
+ cw.putMovRegAddress('edi', picWxid) //edi
+ cw.putCallAddress(moduleBaseAddress.add(
+ offset.sendPicMsg.call3
+ ))
- const base = moduleBaseAddress.add(offset.myselfinfo.offset)
- const wxid_len = base.add(offset.myselfinfo.wxid_len_offset).readU32()
- if (wxid_len === 0x13) { // 新版本微信
- wx_id = base.readPointer().readAnsiString(wxid_len)
- wx_code = base.add(offset.myselfinfo.wxcode_new).readAnsiString()
- } else {
- wx_id = readString(base)
- wx_code = wx_id
- }
+ cw.putPopax()
+ cw.putPopfx()
+ cw.putRet()
+ cw.flush()
- wx_name = readString(base.add(offset.myselfinfo.wx_nick_name))
- const img_addr = base.add(offset.myselfinfo.head_img_url).readPointer()
- const img_len = base.add(offset.myselfinfo.head_img_url_len).readU32()
+ })
- head_img_url = img_addr.readAnsiString(img_len)
+ //console.log('----------picAsm',picAsm)
+ const nativeativeFunction = new NativeFunction(ptr(picAsm), 'void', [])
+ nativeativeFunction()
- const myself = {
- id: wx_id,
- code: wx_code,
- name: wx_name,
- head_img_url: head_img_url,
- };
+})
- return JSON.stringify(myself)
+// 020 done
+let memberNickBuffAsm = null
+let nickRoomId = null
+let nickMemberId = null
+let nickBuff = null
+const getChatroomMemberNickInfoFunction = ((memberId, roomId) => {
-})
+ nickBuff = Memory.alloc(0x7e4)
+ //const nickRetAddr = Memory.alloc(0x04)
+ memberNickBuffAsm = Memory.alloc(Process.pageSize)
+ //console.log('asm address----------',memberNickBuffAsm)
+ nickRoomId = initidStruct(roomId)
+ //console.log('nick room id',nickRoomId)
+ nickMemberId = initStruct(memberId)
-// done
-const recurseNew = ((node) => {
- const headerNodeAddress = getHeaderNodeAddress()
- if (headerNodeAddress.isNull()) {
- return
- }
+ //console.log('nick nickMemberId id',nickMemberId)
+ //const nickStructPtr = initmsgStruct('')
- if (node.equals(headerNodeAddress)) {
- return
- }
+ Memory.patchCode(memberNickBuffAsm, Process.pageSize, code => {
+ var cw = new X86Writer(code, {
+ pc: memberNickBuffAsm
+ })
+ cw.putPushfx()
+ cw.putPushax()
+ cw.putMovRegAddress('edi', nickRoomId)
+ cw.putMovRegAddress('eax', nickBuff)
+ cw.putMovRegReg('edx', 'edi')
+ cw.putPushReg('eax')
+ cw.putMovRegAddress('ecx', nickMemberId)
+ cw.putCallAddress(moduleBaseAddress.add(0xC06F10))
+ cw.putAddRegImm('esp', 0x04)
+ cw.putPopax()
+ cw.putPopfx()
+ cw.putRet()
+ cw.flush()
- for (const item in nodeList) {
- if (node.equals(nodeList[item])) {
- return
- }
- }
+ })
+ const nativeativeFunction = new NativeFunction(ptr(memberNickBuffAsm), 'void', [])
+ nativeativeFunction()
- nodeList.push(node)
- const id = readString(node.add(0x8))
- //wxid, format relates to registration method
- const wxid = readWideString(node.add(0x30))
- //console.log('-----------',wxid)
+ const nickname = readWideString(nickBuff)
+ console.log('----nickname', nickname)
+ return readWideString(nickBuff)
+})
+/* 由此之后是3.9.2.23中缺失的未实现方法 */
- //custom id, if not set return null, and use wxid which should be custom id
- //const wx_code = readWideString(node.add(0x4c)) || readWideString(node.add(0x38))
+// 038 初始化全局变量 tbd
+let g_initTestAsm = null
+let g_BufferEbp2C = null
+let g_initECXU32 = null
+let g_initECXPtr = null
+let g_initEBXPtr = null
+let g_initEBX = null
- //custom Nickname
- const name = readWideString(node.add(0x8c))
+let g_attatchEBP210Buffer = null
+let g_attatchPathPtr = null
+let g_attatchPath = null
+let g_attatchEBPAc = null
+let g_attatchEBPAcBufPtr = null
- //alias aka 'remark' in wechat
- //const alias = readWideString(node.add(0x80))
+let g_attatchContactIdPtr = null
+//let g_attatchECXBuffer = null
+let g_attatchESIU32 = null
- //avatarUrl
- //const avatar = readWideString(node.add(0x138))
- //const avatar = Memory.readUtf16String(node.add(0x138).readPointer())
- //contact gender
- //const gender = node.add(0x18C).readU32()
+let g_initECXTempPtr = null
+const initGlobal = ((contactId, attatchFile) => {
- const contactJson = {
- id1: id,
- id: wxid,
- name: name,
- /*code: wx_code,
- name: name,
- alias: alias,
- avatarUrl: avatar,
- gender: gender,*/
- }
+ //const base = moduleBaseAddress.add(0x222f38c).readPointer()
+ //g_EDI = base.add(0xD70).readPointer()//0x438+0x938
+ console.log('------------g_attatchEBPAc', g_attatchEBPAc)
+ console.log('------------g_EDIU32', g_EDIU32)
+ g_initTestAsm = Memory.alloc(Process.pageSize)
+ console.log('------------address', g_initTestAsm)
- contactList.push(contactJson)
+ g_initECXPtr = g_EDIPtr.add(0xB80).readPointer().add(0x1640)
+ g_initECXTempPtr = g_EDIPtr.add(0xB88).readPointer()
+ g_initECXU32 = g_initECXPtr.toInt32()
+ g_attatchESIU32 = g_EDIU32
- const leftNode = node.add(0x0).readPointer()
- const centerNode = node.add(0x04).readPointer()
- //const rightNode = node.add(0x08).readPointer()
+ console.log('------------g_initECXU32', g_initECXU32)
+ console.log('------------g_initESIU32', g_attatchESIU32)
- recurseNew(leftNode)
- recurseNew(centerNode)
- //recurse(rightNode)
- const allContactJson = contactList
- return allContactJson
+ //console.log('==========g_initECXPtr',g_initECXPtr)
+ //console.log('==========g_EDIU32',g_EDIU32)
-})
+ //g_attatchECXBuffer = Memory.alloc(0x1024)
+ //Memory.copy(g_attatchECXBuffer, g_initECXPtr, 0x1024)
-// done ?
-const getContactNativeFunction = (() => {
- const headerNodeAddress = getHeaderNodeAddress()
- //console.log('headerNodeAddress',headerNodeAddress)
+ g_BufferEbp2C = Memory.alloc(0x48)
- if (headerNodeAddress.isNull()) {
- return '[]'
- }
+ //g_initEBX = moduleBaseAddress.add(0x2251724).readPointer().readPointer()
+ //g_initEBXPtr = Memory.alloc(0x14).writePointer(g_initEBX)
+ //g_initEBXPtr.add(0x08).writePointer(g_BufferEbp2C)
- const node = headerNodeAddress.add(0x0).readPointer()
- const ret = recurseNew(node)
+ g_attatchPathPtr = Memory.alloc(attatchFile.length * 2 + 2)
+ g_attatchPathPtr.writeUtf16String(attatchFile)
- //console.log(ret)
+ g_attatchPath = Memory.alloc(0x28)
+ g_attatchPath.writePointer(g_attatchPathPtr).add(0x04)
+ .writeU32(attatchFile.length * 2).add(0x04)
+ .writeU32(attatchFile.length * 2).add(0x04)
+ /*---------------------------------ebp-210----------------*/
+ g_attatchEBP210Buffer = Memory.alloc(0x48)
+ g_attatchEBP210Buffer.writeU32(0x3)
+ g_attatchEBP210Buffer.add(0x4).writePointer(g_attatchPathPtr)
+ g_attatchEBP210Buffer.add(0x8).writeU32(attatchFile.length * 2)
+ g_attatchEBP210Buffer.add(0xC).writeU32(attatchFile.length * 2)
+ g_attatchEBP210Buffer.add(0x2C).writeU32(moduleBaseAddress.add(0x2ECE87).toInt32())
+ //console.log('------------g_attatchEBP210Buffer',g_attatchEBP210Buffer)
+ /*---------------------------------ebp-210----------------*/
- console.log('getContactNativeFunction:', ret.length)
- /*for (let item of ret){
- console.log(JSON.stringify(item))
- }*/
- //console.log(ret.contact)
- const cloneRet = JSON.stringify(ret)
- nodeList.length = 0
- contactList.length = 0
+ //g_attatchContactIdPtr = Memory.alloc(0x4)
+ //g_attatchContactIdPtr.writeUtf16String(contactId)
+ //console.log('------------g_attatchEBP210Buffer',g_attatchEBP210Buffer)
+ g_attatchEBPAc = Memory.alloc(0x140)
+ //g_attatchEBPAcBufPtr = Memory.alloc(0x100)
+ //g_attatchEBPAc.writePointer(g_attatchEBP210Buffer)
+ //g_attatchEBPAc.add(0x4).writePointer(g_attatchEBPAcBufPtr)
+ //g_attatchEBPAc.add(0x8).writePointer(g_attatchEBPAcBufPtr)
+ g_attatchEBPAc.add(0x10).writeU32(g_EDIU32)
+ console.log('------------g_attatchEBPAc', g_attatchEBPAc)
- return cloneRet
-})
+ /*g_attatchECXBuffer.add(0x18).writePointer(g_attatchContactIdPtr)
+ g_attatchECXBuffer.add(0x1C).writeU32(contactId.length*2)
+ .add(0x04).writeU32(contactId.length*2)*/
-// 005 done
-const getChatroomNodeAddress = (() => {
- const baseAddress = moduleBaseAddress.add(offset.chatroomInfo.nodeOffset).readPointer()
- if (baseAddress.isNull()) {
- return baseAddress
- }
- return baseAddress.add(offset.chatroomInfo.nodeRootOffset).readPointer()
-})
-// 008chatroom member done
-const chatroomRecurse = ((node) => {
- const chatroomNodeAddress = getChatroomNodeAddress()
- if (chatroomNodeAddress.isNull()) {
- return
- }
- if (node.equals(chatroomNodeAddress)) {
- return
- }
+ //g_attatchESIU32 = g_EDI.toInt32()
- for (const item in chatroomNodeList) {
- if (node.equals(chatroomNodeList[item])) {
- return
- }
- }
- chatroomNodeList.push(node)
- const roomid = readWideString(node.add(0x10))
+ //console.log('------------g_attatchESIU32',g_attatchESIU32)
+ //console.log('==========g_attatchECXBuffer',g_attatchECXBuffer)
- const len = node.add(0x54).readU32() //
- //const memberJson={}
- if (len > 4) { //
- const memberStr = readString(node.add(0x44))
- if (memberStr.length > 0) {
- const memberList = memberStr.split(/[\\^][G]/)
- const memberJson = {
- roomid: roomid,
- roomMember: memberList
- }
+ Memory.patchCode(g_initTestAsm, Process.pageSize, code => {
+ var cw = new X86Writer(code, { pc: g_initTestAsm })
+ cw.putPushfx()
+ cw.putPushax()
+ //cw.putMovRegAddress('eax', g_attatchEBP210Buffer)
- chatroomMemberList.push(memberJson)
- }
+ /*cw.putMovRegAddress('edi',g_EDIPtr)
+ cw.putMovRegReg('esi','edi')
+ cw.putMovRegAddress('eax',g_BufferEbp2C)
+ cw.putMovRegAddress('ecx',g_initECXTempPtr)
+ cw.putPushReg('eax')
+ cw.putCallAddress(moduleBaseAddress.add(0x131bb0))*/
- }
+ //cw.putMovRegOffsetPtrU32('ebp', -20, 0)
- const leftNode = node.add(0x0).readPointer()
- const centerNode = node.add(0x04).readPointer()
- const rightNode = node.add(0x08).readPointer()
+ /*cw.putPushU32(0)
+ cw.putMovRegAddress('eax', g_attatchPathPtr)
+ cw.putPushReg('eax')
+ cw.putPushU32(3)
+ cw.putMovRegAddress('ecx', g_attatchEBP210Buffer)
+ cw.putCallAddress(moduleBaseAddress.add(0x130220))*/
- chatroomRecurse(leftNode)
- chatroomRecurse(centerNode)
- chatroomRecurse(rightNode)
- const allChatroomMemberJson = chatroomMemberList
- return allChatroomMemberJson
-})
+ /*cw.putMovRegAddress('edi', g_attatchEBPAc)//后面要用的的ebp-2c
+ cw.putMovRegAddress('ecx', g_attatchEBP210Buffer)
+ cw.putPushReg('ecx')
+ cw.putMovRegU32('eax',0)
+ cw.putPushReg('eax')//push eax
+ cw.putMovRegReg('ecx', 'edi')
+ cw.putMovRegAddress('esi',g_attatchPathPtr)
+ cw.putCallAddress(moduleBaseAddress.add(0x138880))*/
-// 009 done
-const getChatroomMemberInfoFunction = (() => {
- const chatroomNodeAddress = getChatroomNodeAddress()
- if (chatroomNodeAddress.isNull()) {
- return '[]'
- }
- const node = chatroomNodeAddress.add(0x0).readPointer()
- const ret = chatroomRecurse(node)
+ /*cw.putSubRegImm('esp',0x14)
+ cw.putMovRegU32('ecx',g_initECXU32)
+ cw.putMovRegU32('esi',g_attatchESIU32)
+ cw.putMovRegAddress('eax', g_attatchEBPAc)
+ cw.putPushReg('eax')
+ cw.putCallAddress(moduleBaseAddress.add(0x173620))*/
+ //cw.putCallAddress(moduleBaseAddress.add(0x522590))
- const cloneRet = JSON.stringify(ret)
- chatroomNodeList.length = 0 //empty
- chatroomMemberList.length = 0 //empty
- return cloneRet
-})
+ /** g_attatchEBPAc*/
+ //cw.putMovRegNearPtr('eax', g_attatchEBPAc)
+ //cw.putMovNearPtrReg(g_attatchEBPAc.add(0xc), 'eax')
+ /** g_attatchEBPAc*/
-// 024 done
-/**
- * sendMsgNativeFunction
- * send text message
- * @param {string} talkerId = wxid or roomid
- * @param {string} content
- */
- const sendMsgNativeFunction = ((talkerId, content) => {
- const txtAsm = Memory.alloc(Process.pageSize)
- //const buffwxid = Memory.alloc(0x20)
+ //cw.putMovRegAddress('ebx', g_initEBXPtr)
+ //cw.putMovRegU32('edi', g_EDI.toInt32())
+ //cw.putMovRegU32('esi', g_EDI.toInt32())
+ /*cw.putMovRegU32('ecx', g_initECX)
+ cw.putMovRegAddress('eax', g_BufferEbp2C)
+ cw.putPushReg('eax')
+ cw.putCallAddress(moduleBaseAddress.add(0x131BB0))*/
+ cw.putPopax()
+ cw.putPopfx()
+ cw.putRet()
+ cw.flush()
- let wxidPtr = Memory.alloc(talkerId.length * 2 + 2)
- wxidPtr.writeUtf16String(talkerId)
+ })
- let picWxid = Memory.alloc(0x0c)
- picWxid.writePointer(ptr(wxidPtr)).add(0x04)
- .writeU32(talkerId.length * 2).add(0x04)
- .writeU32(talkerId.length * 2).add(0x04)
+ const nativeativeFunction = new NativeFunction(ptr(g_initTestAsm), 'void', [])
+ nativeativeFunction()
+})
- let contentPtr = Memory.alloc(content.length * 2 + 2)
- contentPtr.writeUtf16String(content)
+// 039
+let g_personal_detail_ebx = null
+let g_personal_detail_asm = null
+let g_personal_wxid = null
+let g_personal_wxid_ptr = null
+const getOldTest = ((wxid) => {//personal detail
- const sizeOfStringStruct = Process.pointerSize * 5
- let contentStruct = Memory.alloc(sizeOfStringStruct)
+ g_personal_detail_asm = Memory.alloc(Process.pageSize)
+ g_personal_detail_ebx = moduleBaseAddress.add(0x222F38C).readPointer().add(0xFB8).toInt32()
- contentStruct
- .writePointer(contentPtr).add(0x4)
- .writeU32(content.length).add(0x4)
- .writeU32(content.length * 2)
+ g_personal_wxid_ptr = Memory.alloc(wxid.length * 2 + 2)
+ g_personal_wxid_ptr.writeUtf16String(wxid)
+ g_personal_wxid = Memory.alloc(0x14)
+ g_personal_wxid.writePointer(ptr(g_personal_wxid_ptr)).add(0x04)
+ .writeU32(wxid.length * 2).add(0x04)
+ .writeU32(wxid.length * 2).add(0x08)
- const ecxBuffer = Memory.alloc(0x2d8)
+ console.log('-----------address----------', g_personal_detail_asm)
- Memory.patchCode(txtAsm, Process.pageSize, code => {
- var cw = new X86Writer(code, {
- pc: txtAsm
- })
+ Memory.patchCode(g_personal_detail_asm, Process.pageSize, code => {
+ var cw = new X86Writer(code, { pc: g_personal_detail_asm })
cw.putPushfx()
cw.putPushax()
- cw.putPushU32(0x0)
- cw.putPushU32(0x0)
- cw.putPushU32(0x0)
- cw.putPushU32(0x1)
- cw.putPushU32(0x0)
-
- //cw.putMovRegReg
+ cw.putCallAddress(moduleBaseAddress.add(0x9A000))
- cw.putMovRegAddress('eax', contentStruct)
+ //78BA9ACE | E8 2D05D6FF | call wechatwin.7890A000 |
+ cw.putMovRegU32('ebx', g_personal_detail_ebx)
+ cw.putMovRegReg('esi', 'eax')
+ cw.putPushReg('ebx')
+ cw.putSubRegImm('esp', 0x14)
+ cw.putMovRegAddress('eax', g_personal_wxid)
+ cw.putMovRegReg('ecx', 'esp')
cw.putPushReg('eax')
+ cw.putCallAddress(moduleBaseAddress.add(0x701DC0))
+ cw.putMovRegReg('ecx', 'esi')
+ cw.putCallAddress(moduleBaseAddress.add(0x4024A0))
- cw.putMovRegAddress('edx', picWxid) //room_id
-
- cw.putMovRegAddress('ecx', ecxBuffer)
- cw.putCallAddress(moduleBaseAddress.add(
- offset.sendTxtMsg.callOffset
- ))
-
- cw.putAddRegImm('esp', 0x18)
cw.putPopax()
cw.putPopfx()
cw.putRet()
@@ -1094,59 +1037,154 @@ const getChatroomMemberInfoFunction = (() => {
})
- console.log('----------txtAsm', txtAsm)
- const nativeativeFunction = new NativeFunction(ptr(txtAsm), 'void', [])
+ const nativeativeFunction = new NativeFunction(ptr(g_personal_detail_asm), 'void', [])
nativeativeFunction()
+
})
-// 023 done
+// const writeLogNativeCallback = (() => {
+// const nativeCallback = new NativeCallback(() => { }, 'void', [])
+// const nativeCallFunction = new NativeFunction(nativeCallback, 'void', [])
+
+// Interceptor.attach(
+// moduleBaseAddress.add(0x7008A4),
+// {
+// onEnter() {
+// const addr = this.context.eax//.sub(0x114)//0xc30-0x08
+// if(addr >0){
+// const log = ptr(addr).readAnsiString()
+// }
+// }
+// })
+// return nativeCallback
+// })()
+
+// 040
/**
-* send at msg
-*/
-let asmAtMsg = null
-let roomid_, msg_, wxid_, atid_
-let ecxBuffer
-const sendAtMsgNativeFunction = ((roomId, text, contactId,nickname) => {
+ * test call
+ */
+let attatchTestAsm = null
+let attatchTestEbp2C = null
+let attatchGlobalEDI = null
+let attatchGlobalEDIB88 = null
+let attatchTestEBX = null
+let g_tempEcx = null
+let attatchFirstECX = null
+//let attatchFirstECX = null
+let gattatchFilePtr = null
+let gattatchFile = null
+let gattatchReceiveIdPtr = null
+let gattatchReceiveId = null
+let attatchEAX3B0Buf = null
- asmAtMsg = Memory.alloc(Process.pageSize)
- ecxBuffer = Memory.alloc(0x3b0)
+let attatchESIbuf = null
+const getWxTest = ((contactId, filePath) => {
+ //const nativeativeFunction = new NativeFunction(ptr(addr), 'void', [])
+ //nativeativeFunction()
+ attatchTestAsm = Memory.alloc(Process.pageSize)
+ console.log('----------------address', attatchTestAsm)
+ attatchTestEbp2C = Memory.alloc(0xC)
+ attatchGlobalEDI = moduleBaseAddress.add(0x222f38c).readPointer()
+ .add(0x938).add(0x438).readPointer()
+ attatchGlobalEDIB88 = attatchGlobalEDI.add(0xB88).readPointer()
+ attatchTestEBX = Memory.alloc(0x4)
+ attatchTestEBX.writePointer(attatchGlobalEDI)
+ console.log('----------------attatchGlobalEDI', attatchGlobalEDI)
+ console.log('----------------attatchGlobalEDIB88', attatchGlobalEDIB88)
- const atContent = '@'+nickname+' '+text
+ attatchFirstECX = Memory.alloc(0x28)
+ //const attatchSecondEcx = Memory.alloc(0x14)
- roomid_ = initStruct(roomId)
- wxid_ = initidStruct(contactId)
- msg_ = initmsgStruct(atContent)
- atid_ = initAtMsgStruct(wxid_)
+ const contactIdLength = contactId.length * 2 + 2//edx
+ const contractIdActLength = contactId.length
- Memory.patchCode(asmAtMsg, Process.pageSize, code => {
- var cw = new X86Writer(code, {
- pc: asmAtMsg
- })
+
+ gattatchReceiveIdPtr = Memory.alloc(contactId.length * 2 + 2)
+ gattatchReceiveIdPtr.writeUtf16String(contactId)
+
+ gattatchReceiveId = Memory.alloc(0x14)
+ gattatchReceiveId.writePointer(ptr(gattatchReceiveIdPtr)).add(0x04)
+ .writeU32(contactId.length * 2).add(0x04)
+ .writeU32(contactId.length * 2).add(0x08)
+ //console.log('----------------attatchGlobalEDIB88',attatchGlobalEDIB88)
+ //return
+ /*console.log(hexdump(attatchTestEBX, {
+ offset: 0,
+ length: 0x40,
+ header: true,
+ ansi: true
+ }))
+ return*/
+
+ gattatchFilePtr = Memory.alloc(filePath.length * 2 + 2)
+ gattatchFilePtr.writeUtf16String(filePath)
+
+ gattatchFile = Memory.alloc(0x14)
+ gattatchFile.writePointer(ptr(gattatchFilePtr)).add(0x04)
+ .writeU32(filePath.length * 2).add(0x04)
+ .writeU32(filePath.length * 2).add(0x08)
+
+ const attatchLastECX = moduleBaseAddress.add(0x222f170).toInt32()
+
+ attatchEAX3B0Buf = Memory.alloc(0x3B0)
+
+ g_tempEcx = Memory.alloc(0x4)
+ //g_tempEcx1 = Memory.alloc(0x4)
+
+ attatchESIbuf = Memory.alloc(0x100)
+ attatchESIbuf.add(0x0).writeU32(3)
+ attatchESIbuf.add(0x4).writePointer(gattatchFilePtr)
+ attatchESIbuf.add(0x8).writeU32(filePath.length * 2)
+ attatchESIbuf.add(0xc).writeU32(filePath.length * 2)
+
+ Memory.patchCode(attatchTestAsm, Process.pageSize, code => {
+ var cw = new X86Writer(code, { pc: attatchTestAsm })
cw.putPushfx()
cw.putPushax()
+ //cw.putMovRegU32('edi',attatchGlobalEDI)
- cw.putPushU32(0x0)
- cw.putPushU32(0x0)
- cw.putPushU32(0x0)
- cw.putPushU32(0x1)
- //cw.putPushU32(0x0)
- cw.putMovRegAddress('eax', atid_)
+
+ cw.putMovRegAddress('esi', attatchESIbuf)
+
+ cw.putMovRegAddress('ecx', attatchFirstECX.add(0x14))
+ cw.putMovRegAddress('eax', gattatchFile)
cw.putPushReg('eax')
+ cw.putCallAddress(moduleBaseAddress.add(0x701DC0))
- //cw.putMovRegReg
- cw.putMovRegAddress('eax', msg_)
+ cw.putMovRegAddress('ecx', attatchFirstECX)
+ cw.putMovRegU32('eax', contactIdLength)
cw.putPushReg('eax')
+ cw.putPushU32(0)
+ cw.putCallAddress(moduleBaseAddress.add(0x1a11c83))
+ cw.putAddRegImm('esp', 0x8)
- cw.putMovRegAddress('edx', roomid_) //room_id
+ cw.putMovRegReg('edx', 'eax')
+ cw.putMovNearPtrReg(attatchFirstECX, 'edx')
+ cw.putMovRegU32('edi', contactIdLength)
+ cw.putPushReg('edi')
+ cw.putMovRegAddress('eax', gattatchReceiveIdPtr)//ebp-58
+ cw.putPushReg('eax')
+ cw.putMovRegNearPtr('eax', attatchFirstECX)
+ cw.putPushReg('eax')
+ cw.putCallAddress(moduleBaseAddress.add(0x1a1047a))
+ cw.putAddRegImm('esp', 0x0c)
- cw.putMovRegAddress('ecx', ecxBuffer)
- cw.putCallAddress(moduleBaseAddress.add(
- offset.sendTxtMsg.callOffset
- ))
+ //cw.putMovRegNearPtr('ecx',attatchFirstECX)
+ //cw.putAddRegImm('esp', 0x0c)
+ //cw.putMovRegU32('edx', 0)
+ //cw.putMovRegRegPtr('eax', 'ecx')
+ //cw.putMovNearPtrReg(attatchFirstECX.add(0x04),'edi')
+ cw.putMovRegU32('edi', contactId.length * 2)
+ cw.putMovRegU32('ecx', attatchLastECX)
+ cw.putMovRegAddress('eax', attatchEAX3B0Buf)
+ cw.putPushReg('eax')
+ cw.putCallAddress(moduleBaseAddress.add(0x392260))
+
+ cw.putMovRegAddress('ecx', attatchEAX3B0Buf)
+ cw.putCallAddress(moduleBaseAddress.add(0x94200))
- cw.putAddRegImm('esp', 0x18)
cw.putPopax()
cw.putPopfx()
cw.putRet()
@@ -1154,134 +1192,103 @@ const sendAtMsgNativeFunction = ((roomId, text, contactId,nickname) => {
})
- //console.log('----------txtAsm', asmAtMsg)
- const nativeativeFunction = new NativeFunction(ptr(asmAtMsg), 'void', [])
+ const nativeativeFunction = new NativeFunction(ptr(attatchTestAsm), 'void', [])
nativeativeFunction()
+
})
-// 022 done
-/**
- *
- * @param {*} contactId
- * @param {*} path
- */
- const sendPicMsgNativeFunction = ((contactId, path) => {
+// 001
+const getTestInfoFunction = ((addr) => {
+ const nativeativeFunction = new NativeFunction(ptr(addr), 'void', [])
+ nativeativeFunction()
- const picAsm = Memory.alloc(Process.pageSize)
- const buffwxid = Memory.alloc(0x20)
- const picbuff = Memory.alloc(0x2D8)
+ //00CFE484
- let pathPtr = Memory.alloc(path.length * 2 + 1)
- pathPtr.writeUtf16String(path)
- let imagefilepath = Memory.alloc(0x24)
- imagefilepath.writePointer(pathPtr).add(0x04)
- .writeU32(path.length * 2).add(0x04)
- .writeU32(path.length * 2).add(0x04)
+ /*MemoryAccessMonitor.enable({base:ptr(addr),size:0x01}, {
+ onAccess(details){
+ console.log('============')
+ console.log(details.operation)
+ console.log(details.from)
+ console.log(details.address)
+ console.log('============')
+ }
+ })*/
- let picWxidPtr = Memory.alloc(contactId.length * 2 + 1)
- picWxidPtr.writeUtf16String(contactId)
+})
- let picWxid = Memory.alloc(0x0c)
- picWxid.writePointer(ptr(picWxidPtr)).add(0x04)
- .writeU32(contactId.length * 2).add(0x04)
- .writeU32(contactId.length * 2).add(0x04)
+// 002
+const isLoggedInFunction = (() => {
+ loggedIn = moduleBaseAddress.add(offset.is_logged_in_offset).readU32()
+ return !!loggedIn
+})
+// 007 获得当前账号信息
+const getMyselfIdFunction = (() => {
- //const test_offset1 = 0x701DC0;
- Memory.patchCode(picAsm, Process.pageSize, code => {
- var cw = new X86Writer(code, {
- pc: picAsm
- })
- cw.putPushfx();
- cw.putPushax();
- cw.putCallAddress(moduleBaseAddress.add(
- offset.sendPicMsg.call1
- ))
- cw.putMovRegReg('edx', 'eax') //缓存
+ let wx_id = readString(moduleBaseAddress.add(offset.wxid_offset))
- cw.putSubRegImm('esp', 0x14)
- cw.putMovRegAddress('eax', buffwxid)
- cw.putMovRegReg('ecx', 'esp')
- cw.putMovRegAddress('edi', imagefilepath)
- cw.putPushReg('eax')
- cw.putCallAddress(moduleBaseAddress.add(
- offset.sendPicMsg.call2
- ))
+ return wx_id
- cw.putMovRegReg('ecx', 'edx')
- cw.putMovRegAddress('eax', picWxid) //=lea
- cw.putMovRegAddress('edi', imagefilepath)
- cw.putPushReg('edi')
- cw.putPushReg('eax')
- cw.putMovRegAddress('eax', picbuff)
- cw.putPushReg('eax')
+})
- cw.putMovRegAddress('edi', picWxid) //edi
- cw.putCallAddress(moduleBaseAddress.add(
- offset.sendPicMsg.call3
- ))
+//contact
+// 042
+const recurse = ((node) => {
+ const headerNodeAddress = getHeaderNodeAddress()
+ if (headerNodeAddress.isNull()) { return }
+ if (node.equals(headerNodeAddress)) { return }
+ for (const item in nodeList) {
+ if (node.equals(nodeList[item])) {
+ return
+ }
+ }
- cw.putPopax()
- cw.putPopfx()
- cw.putRet()
- cw.flush()
- })
+ nodeList.push(node)
+ //wxid, format relates to registration method
+ const wxid = readWideString(node.add(0x38))
- //console.log('----------picAsm',picAsm)
- const nativeativeFunction = new NativeFunction(ptr(picAsm), 'void', [])
- nativeativeFunction()
+ //custom id, if not set return null, and use wxid which should be custom id
+ const wx_code = readWideString(node.add(0x4c)) || readWideString(node.add(0x38))
-})
+ //custom Nickname
+ const name = readWideString(node.add(0x94))
-// 020 done
-let memberNickBuffAsm = null
-let nickRoomId = null
-let nickMemberId = null
-let nickBuff = null
-const getChatroomMemberNickInfoFunction = ((memberId, roomId) => {
+ //alias aka 'remark' in wechat
+ const alias = readWideString(node.add(0x80))
- nickBuff = Memory.alloc(0x7e4)
- //const nickRetAddr = Memory.alloc(0x04)
- memberNickBuffAsm = Memory.alloc(Process.pageSize)
- //console.log('asm address----------',memberNickBuffAsm)
- nickRoomId = initidStruct(roomId)
- //console.log('nick room id',nickRoomId)
- nickMemberId = initStruct(memberId)
+ //avatarUrl
+ const avatar = readWideString(node.add(0x138))
+ //const avatar = Memory.readUtf16String(node.add(0x138).readPointer())
+ //contact gender
+ const gender = node.add(0x18C).readU32()
- //console.log('nick nickMemberId id',nickMemberId)
- //const nickStructPtr = initmsgStruct('')
+ const contactJson = {
+ id: wxid,
+ code: wx_code,
+ name: name,
+ alias: alias,
+ avatarUrl: avatar,
+ gender: gender,
+ }
- Memory.patchCode(memberNickBuffAsm, Process.pageSize, code => {
- var cw = new X86Writer(code, {
- pc: memberNickBuffAsm
- })
- cw.putPushfx()
- cw.putPushax()
- cw.putMovRegAddress('edi', nickRoomId)
- cw.putMovRegAddress('eax', nickBuff)
- cw.putMovRegReg('edx', 'edi')
- cw.putPushReg('eax')
- cw.putMovRegAddress('ecx', nickMemberId)
- cw.putCallAddress(moduleBaseAddress.add(0xC06F10))
- cw.putAddRegImm('esp', 0x04)
- cw.putPopax()
- cw.putPopfx()
- cw.putRet()
- cw.flush()
+ contactList.push(contactJson)
- })
+ const leftNode = node.add(0x0).readPointer()
+ const centerNode = node.add(0x04).readPointer()
+ const rightNode = node.add(0x08).readPointer()
- const nativeativeFunction = new NativeFunction(ptr(memberNickBuffAsm), 'void', [])
- nativeativeFunction()
+ recurse(leftNode)
+ recurse(centerNode)
+ recurse(rightNode)
+
+ const allContactJson = contactList
+ return allContactJson
- const nickname = readWideString(nickBuff)
- console.log('----nickname', nickname)
- return readWideString(nickBuff)
})
// 013
@@ -1428,13 +1435,13 @@ const getQrcodeLoginData = () => {
return json
}
-
+// 045
/**
* 20220504 writelog
* 7A566D72 | FFB5 ECFEFFFF | push dword ptr ss:[ebp-114] | 【3.6.0.18】写日志,这个里面就是日志内容
7A566D78 | FFB5 E8FEFFFF | push dword ptr ss:[ebp-118] |
*/
-/*const writeLogNativeCallback = (() => {
+const writeLogNativeCallback = (() => {
const nativeCallback = new NativeCallback(() => { }, 'void', [])
const nativeCallFunction = new NativeFunction(nativeCallback, 'void', [])
@@ -1448,8 +1455,9 @@ const getQrcodeLoginData = () => {
}
})
return nativeCallback
-})()*/
+})()
+// 046
let nickRoomIdV6 = null
let nullEdiWxidStructV6 = null
let nickMemberIdStructV6 = null
@@ -1509,6 +1517,7 @@ const getChatroomMemberNickInfoV1Function = ((memberId, roomId) => {
return readWideString(nullEdiWxidStructV6)
})
+// 021
/**
* send attatch
*/
@@ -1550,8 +1559,6 @@ let attatchECX = null
param {78EDBC86 | 8B80 38040000 | mov eax,dword ptr ds:[eax+438] |
78EDBC8C | 8BB0 800B0000 | mov esi,dword ptr ds:[eax+B80] |} sendWxid
*/
-
-// 021
const sendAttatchMsgNativeFunction = ((contactId, senderId, path, filename, size) => {
attatchAsm = Memory.alloc(Process.pageSize)
@@ -1755,78 +1762,6 @@ const sendAttatchMsgNativeFunction = ((contactId, senderId, path, filename, size
//console.log('-------',attatchEbp1C.add(0x4).readPointer())
//console.log('-------',attatchEbp1C.add(0x8).readPointer())
})
-/*------------------send pic --------------------------
-let buffwxid = null
-let imagefilepath = null
-let pathPtr = null
-let picWxid = null
-let picWxidPtr = null
-let picAsm = null
-let picbuff = null
-const sendPicMsgNativeFunction = ((contactId, path) => {
-
- picAsm = Memory.alloc(Process.pageSize)
- buffwxid = Memory.alloc(0x20)
- picbuff = Memory.alloc(0x378)
-
- pathPtr = Memory.alloc(path.length * 2 + 1)
- pathPtr.writeUtf16String(path)
-
- imagefilepath = Memory.alloc(0x24)
- imagefilepath.writePointer(pathPtr).add(0x04)
- .writeU32(path.length * 2).add(0x04)
- .writeU32(path.length * 2).add(0x04)
-
- picWxidPtr = Memory.alloc(contactId.length * 2 + 1)
- picWxidPtr.writeUtf16String(contactId)
-
- picWxid = Memory.alloc(0x0c)
- picWxid.writePointer(ptr(picWxidPtr)).add(0x04)
- .writeU32(contactId.length * 2).add(0x04)
- .writeU32(contactId.length * 2).add(0x04)
-
- Memory.patchCode(picAsm, Process.pageSize, code => {
- var cw = new X86Writer(code, { pc: picAsm })
- cw.putPushfx();
- cw.putPushax();
-
- cw.putSubRegImm('esp', 0x14)
- cw.putMovRegAddress('eax', buffwxid)
-
- cw.putMovRegReg('ecx', 'esp')
-
- cw.putPushReg('eax')
- cw.putCallAddress(moduleBaseAddress.add(
- offset.send_picmsg_call_offset1
- ))
-
- cw.putMovRegAddress('ebx', imagefilepath)
- cw.putPushReg('ebx')
-
- cw.putMovRegAddress('eax', picWxid)
- cw.putPushReg('eax')
-
- cw.putMovRegAddress('eax', picbuff)
- cw.putPushReg('eax')
- cw.putCallAddress(moduleBaseAddress.add(
- offset.send_picmsg_call_offset2
- ))
-
- cw.putMovRegReg('ecx', 'eax')
- cw.putCallAddress(moduleBaseAddress.add(
- offset.send_picmsg_call_offset3
- ))
- cw.putPopax()
- cw.putPopfx()
- cw.putRet()
- cw.flush()
-
- })
-
- const nativeativeFunction = new NativeFunction(ptr(picAsm), 'void', [])
- nativeativeFunction()
-
-})*/
// 025
const callLoginQrcodeFunction = ((forceRefresh = false) => {
diff --git a/src/init-agent-script.js b/src/init-agent-script.js
index f706c38..9c97f9a 100644
--- a/src/init-agent-script.js
+++ b/src/init-agent-script.js
@@ -8,11 +8,14 @@
//const { isNullishCoalesce } = require("typescript")
-//3.9.2.23
+// wechat:3.9.2.23
-// 偏移地址集合 done
+// 028 done
const offset = {
+
+
hook_point: 0xd19a0b, //3.9.2.23
+
myselfinfo: {
offset: 0x2FFD484, //老版本微信号偏移,后面的地址,都要在这个偏移上增加
//wxid_len:0x10,
@@ -23,6 +26,7 @@ const offset = {
//wxcode_len:0x74
wxid_len_offset: 0x4D4
},
+
contactInfo: {
nodeOffset: 0x2FFDD7C,
nodeRootOffset: 0x64
@@ -40,25 +44,20 @@ const offset = {
call3: 0xce6640
}
};
-//3.9.2.23
-// 全局配置 done
+// 029 done
/*------------------global-------------------------------------------*/
const availableVersion = 1661534743 ////3.9.2.23 ==0x63090217
const moduleBaseAddress = Module.getBaseAddress('WeChatWin.dll')
const moduleLoad = Module.load('WeChatWin.dll')
-//1575CF98
-
-// 全局变量 tbd
+// tbd
const g_EDIPtr = moduleBaseAddress.add(0x222f38c).readPointer().add(0xD70).readPointer()//
const g_EDIU32 = moduleBaseAddress.add(0x222f38c).readPointer().add(0xD70).readU32()
-
/*------------------global-------------------------------------------*/
/*---------------base -------------------------*/
-
-// done
+// 030 done
let retidPtr=null
let retidStruct=null
const initidStruct = ((str) => {
@@ -78,7 +77,7 @@ const initidStruct = ((str) => {
return retidStruct
})
-// done
+// 031 done
let retPtr = null
let retStruct = null
const initStruct = ((str) => {
@@ -98,7 +97,7 @@ const initStruct = ((str) => {
return retStruct
})
-// done
+// 032 done
let msgstrPtr=null
let msgStruct=null
const initmsgStruct = ((str) => {
@@ -117,7 +116,23 @@ const initmsgStruct = ((str) => {
return msgStruct
})
-// tbd
+// 034 done
+/**
+* at msg structure
+*/
+let atStruct = null
+const initAtMsgStruct = ((wxidStruct) => {
+
+ atStruct = Memory.alloc(0x10)
+
+ atStruct.writePointer(wxidStruct).add(0x04)
+ .writeU32(wxidStruct.toInt32() + 0x14).add(0x04)//0x14 = sizeof(wxid structure)
+ .writeU32(wxidStruct.toInt32() + 0x14).add(0x04)
+ .writeU32(0)
+ return atStruct
+})
+
+// 033 tbd
let retidNullStruct = null
let retidNullPtr = null
const initNullIdStruct = ((str) => {
@@ -137,25 +152,7 @@ const initNullIdStruct = ((str) => {
return retidNullStruct
})
-// done
-/**
-* at msg structure
-*/
-let atStruct = null
-const initAtMsgStruct = ((wxidStruct) => {
-
- atStruct = Memory.alloc(0x10)
-
- atStruct.writePointer(wxidStruct).add(0x04)
- .writeU32(wxidStruct.toInt32() + 0x14).add(0x04)//0x14 = sizeof(wxid structure)
- .writeU32(wxidStruct.toInt32() + 0x14).add(0x04)
- .writeU32(0)
- return atStruct
-})
-
-// done
-// std::string
-// const str = readStringPtr(ptr).readUtf8String()
+// 035 done
const readStringPtr = (address) => {
const addr = ptr(address)
const size = addr.add(16).readU32()
@@ -169,9 +166,15 @@ const readStringPtr = (address) => {
addr.ptr._readCString = addr.ptr.readCString
addr.ptr._readAnsiString = addr.ptr.readAnsiString
addr.ptr._readUtf8String = addr.ptr.readUtf8String
- addr.readCString = () => { return addr.size ? addr.ptr._readCString(addr.size) : '' }
- addr.readAnsiString = () => { return addr.size ? addr.ptr._readAnsiString(addr.size) : '' }
- addr.readUtf8String = () => { return addr.size ? addr.ptr._readUtf8String(addr.size) : '' }
+ addr.readCString = () => {
+ return addr.size ? addr.ptr._readCString(addr.size) : ''
+ }
+ addr.readAnsiString = () => {
+ return addr.size ? addr.ptr._readAnsiString(addr.size) : ''
+ }
+ addr.readUtf8String = () => {
+ return addr.size ? addr.ptr._readUtf8String(addr.size) : ''
+ }
// console.log('readStringPtr() address:',address,' -> str ptr:', addr.ptr, 'size:', addr.size, 'capacity:', addr.capacity)
// console.log('readStringPtr() str:' , addr.readUtf8String())
@@ -180,913 +183,853 @@ const readStringPtr = (address) => {
return addr
}
-// done
+// 036 done
const readString = (address) => {
return readStringPtr(address).readUtf8String()
}
-// done
+// 037 done
const readWideString = (address) => {
return readWStringPtr(address).readUtf16String()
}
+/*-----------------base-------------------------*/
+
+// 041
+// std::wstring
+// const wstr = readWStringPtr(ptr).readUtf16String()
+const readWStringPtr = (address) => {
+ const addr = ptr(address)
+ const size = addr.add(4).readU32()
+ const capacity = addr.add(8).readU32()
+ addr.ptr = addr.readPointer()
+ addr.size = size
+ addr.capacity = capacity
+ addr.ptr._readUtf16String = addr.ptr.readUtf16String
+ addr.readUtf16String = () => {
+ return addr.size ? addr.ptr._readUtf16String(addr.size * 2) : ''
+ }
+
+ // console.log('readWStringPtr() address:',address,' -> ptr:', addr.ptr, 'size:', addr.size, 'capacity:', addr.capacity)
+ // console.log('readWStringPtr() str:' , `"${addr.readUtf16String()}"`,'\n',addr.ptr.readByteArray(addr.size*2+2),'\n')
+ // console.log('readWStringPtr() address:', addr,'dump:', addr.readByteArray(16),'\n')
+
+ return addr
+}
/*-----------------base-------------------------*/
+// 010 done
let currentVersion = 0
-let nodeList = [] //for contact
+let nodeList = [] //for contact
let contactList = [] //for contact
let chatroomNodeList = [] //for chatroom
-let chatroomMemberList = []//for chatroom
+let chatroomMemberList = [] //for chatroom
let loggedIn = false
-//开启日志 3.6.0.18
-// //[0x221c330+wechatwin.dll]+0xf8
-// 20220504
+const getWechatVersionFunction = (() => {
+ if (currentVersion) {
+ return currentVersion
+ }
+ const pattern = '55 8B ?? 83 ?? ?? A1 ?? ?? ?? ?? 83 ?? ?? 85 ?? 7F ?? 8D ?? ?? E8 ?? ?? ?? ?? 84 ?? 74 ?? 8B ?? ?? ?? 85 ?? 75 ?? E8 ?? ?? ?? ?? 0F ?? ?? 0D ?? ?? ?? ?? A3 ?? ?? ?? ?? A3 ?? ?? ?? ?? 8B ?? 5D C3'
+ const results = Memory.scanSync(moduleLoad.base, moduleLoad.size, pattern)
+ if (results.length == 0) {
+ return 0
+ }
+ const addr = results[0].address
+ const ret = addr.add(0x07).readPointer()
+ const ver = ret.add(0x0).readU32()
+ currentVersion = ver
+ return ver
+})
-let g_initTestAsm = null
-let g_BufferEbp2C = null
-let g_initECXU32 = null
-let g_initECXPtr = null
-let g_initEBXPtr = null
-let g_initEBX = null
+// 011 done
+const getWechatVersionStringFunction = ((ver = getWechatVersionFunction()) => {
+ if (!ver) {
+ return '0.0.0.0'
+ }
+ const vers = []
+ vers.push((ver >> 24) & 255 - 0x60)
+ vers.push((ver >> 16) & 255)
+ vers.push((ver >> 8) & 255)
+ vers.push(ver & 255)
+ return vers.join('.')
+})
-let g_attatchEBP210Buffer = null
-let g_attatchPathPtr = null
-let g_attatchPath = null
-let g_attatchEBPAc = null
-let g_attatchEBPAcBufPtr = null
+// 012 done
+const checkSupportedFunction = (() => {
+ const ver = getWechatVersionFunction()
+ return ver == availableVersion
+})
-let g_attatchContactIdPtr = null
-//let g_attatchECXBuffer = null
-let g_attatchESIU32 = null
+// 019 done
+/**
+ * @Hook: recvMsg -> recvMsgNativeCallback
+ */
+ const recvMsgNativeCallback = (() => {
-let g_initECXTempPtr = null
-const initGlobal = ((contactId, attatchFile) => {
- //const base = moduleBaseAddress.add(0x222f38c).readPointer()
- //g_EDI = base.add(0xD70).readPointer()//0x438+0x938
- console.log('------------g_attatchEBPAc', g_attatchEBPAc)
- console.log('------------g_EDIU32', g_EDIU32)
- g_initTestAsm = Memory.alloc(Process.pageSize)
- console.log('------------address', g_initTestAsm)
+ const nativeCallback = new NativeCallback(() => {}, 'void', ['int32', 'pointer', 'pointer', 'pointer', 'pointer', 'int32'])
+ const nativeativeFunction = new NativeFunction(nativeCallback, 'void', ['int32', 'pointer', 'pointer', 'pointer', 'pointer', 'int32'])
- g_initECXPtr = g_EDIPtr.add(0xB80).readPointer().add(0x1640)
- g_initECXTempPtr = g_EDIPtr.add(0xB88).readPointer()
- g_initECXU32 = g_initECXPtr.toInt32()
- g_attatchESIU32 = g_EDIU32
+ Interceptor.attach(
+ moduleBaseAddress.add(offset.hook_point), {
+ onEnter() {
+ const addr = this.context.ecx //0xc30-0x08
+ const msgType = addr.add(0x38).readU32()
+ const isMyMsg = addr.add(0x3C).readU32() //add isMyMsg
- console.log('------------g_initECXU32', g_initECXU32)
- console.log('------------g_initESIU32', g_attatchESIU32)
+ if (msgType > 0) {
+ const talkerIdPtr = addr.add(0x48).readPointer()
+ //console.log('txt msg',talkerIdPtr.readUtf16String())
+ const talkerIdLen = addr.add(0x48 + 0x04).readU32() * 2 + 2
- //console.log('==========g_initECXPtr',g_initECXPtr)
- //console.log('==========g_EDIU32',g_EDIU32)
+ const myTalkerIdPtr = Memory.alloc(talkerIdLen)
+ Memory.copy(myTalkerIdPtr, talkerIdPtr, talkerIdLen)
- //g_attatchECXBuffer = Memory.alloc(0x1024)
- //Memory.copy(g_attatchECXBuffer, g_initECXPtr, 0x1024)
- g_BufferEbp2C = Memory.alloc(0x48)
+ let contentPtr = null
+ let contentLen = 0
+ let myContentPtr = null
+ if (msgType == 3) { // pic path
+ let thumbPtr = addr.add(0x198).readPointer();
+ let hdPtr = addr.add(0x1ac).readPointer();
+ let thumbPath = thumbPtr.readUtf16String();
+ let hdPath = hdPtr.readUtf16String();
+ let picData = [
+ thumbPath, // PUPPET.types.Image.Unknown
+ thumbPath, // PUPPET.types.Image.Thumbnail
+ hdPath, // PUPPET.types.Image.HD
+ hdPath // PUPPET.types.Image.Artwork
+ ]
+ let content = JSON.stringify(picData);
+ myContentPtr = Memory.allocUtf16String(content);
+ } else {
+ contentPtr = addr.add(0x70).readPointer()
+ contentLen = addr.add(0x70 + 0x04).readU32() * 2 + 2
+ myContentPtr = Memory.alloc(contentLen)
+ Memory.copy(myContentPtr, contentPtr, contentLen)
+ }
- //g_initEBX = moduleBaseAddress.add(0x2251724).readPointer().readPointer()
- //g_initEBXPtr = Memory.alloc(0x14).writePointer(g_initEBX)
- //g_initEBXPtr.add(0x08).writePointer(g_BufferEbp2C)
+ // console.log('----------------------------------------')
+ // console.log(msgType)
+ // console.log(contentPtr.readUtf16String())
+ // console.log('----------------------------------------')
+ const groupMsgAddr = addr.add(0x170).readU32() //* 2 + 2
+ let myGroupMsgSenderIdPtr = null
+ if (groupMsgAddr == 0) { //weChatPublic is zero,type is 49
- g_attatchPathPtr = Memory.alloc(attatchFile.length * 2 + 2)
- g_attatchPathPtr.writeUtf16String(attatchFile)
+ myGroupMsgSenderIdPtr = Memory.alloc(0x10)
+ myGroupMsgSenderIdPtr.writeUtf16String("null")
- g_attatchPath = Memory.alloc(0x28)
- g_attatchPath.writePointer(g_attatchPathPtr).add(0x04)
- .writeU32(attatchFile.length * 2).add(0x04)
- .writeU32(attatchFile.length * 2).add(0x04)
- /*---------------------------------ebp-210----------------*/
- g_attatchEBP210Buffer = Memory.alloc(0x48)
- g_attatchEBP210Buffer.writeU32(0x3)
- g_attatchEBP210Buffer.add(0x4).writePointer(g_attatchPathPtr)
- g_attatchEBP210Buffer.add(0x8).writeU32(attatchFile.length * 2)
- g_attatchEBP210Buffer.add(0xC).writeU32(attatchFile.length * 2)
- g_attatchEBP210Buffer.add(0x2C).writeU32(moduleBaseAddress.add(0x2ECE87).toInt32())
- //console.log('------------g_attatchEBP210Buffer',g_attatchEBP210Buffer)
- /*---------------------------------ebp-210----------------*/
+ } else {
- //g_attatchContactIdPtr = Memory.alloc(0x4)
- //g_attatchContactIdPtr.writeUtf16String(contactId)
- //console.log('------------g_attatchEBP210Buffer',g_attatchEBP210Buffer)
- g_attatchEBPAc = Memory.alloc(0x140)
- //g_attatchEBPAcBufPtr = Memory.alloc(0x100)
- //g_attatchEBPAc.writePointer(g_attatchEBP210Buffer)
- //g_attatchEBPAc.add(0x4).writePointer(g_attatchEBPAcBufPtr)
- //g_attatchEBPAc.add(0x8).writePointer(g_attatchEBPAcBufPtr)
- g_attatchEBPAc.add(0x10).writeU32(g_EDIU32)
- console.log('------------g_attatchEBPAc', g_attatchEBPAc)
+ const groupMsgSenderIdPtr = addr.add(0x170).readPointer()
+ const groupMsgSenderIdLen = addr.add(0x170 + 0x04).readU32() * 2 + 2
+ myGroupMsgSenderIdPtr = Memory.alloc(groupMsgSenderIdLen)
+ Memory.copy(myGroupMsgSenderIdPtr, groupMsgSenderIdPtr, groupMsgSenderIdLen)
- /*g_attatchECXBuffer.add(0x18).writePointer(g_attatchContactIdPtr)
- g_attatchECXBuffer.add(0x1C).writeU32(contactId.length*2)
- .add(0x04).writeU32(contactId.length*2)*/
+ }
+ const xmlNullPtr = addr.add(0x1f0).readU32() //3.9.2.23
+ let myXmlContentPtr = null
+ if (xmlNullPtr == 0) {
+ myXmlContentPtr = Memory.alloc(0x10)
+ myXmlContentPtr.writeUtf16String("null")
- //g_attatchESIU32 = g_EDI.toInt32()
+ } else {
+ const xmlContentPtr = addr.add(0x1f0).readPointer() //3.9.2.23
+ const xmlContentLen = addr.add(0x1f0 + 0x04).readU32() * 2 + 2
+ myXmlContentPtr = Memory.alloc(xmlContentLen)
+ Memory.copy(myXmlContentPtr, xmlContentPtr, xmlContentLen)
+ }
- //console.log('------------g_attatchESIU32',g_attatchESIU32)
- //console.log('==========g_attatchECXBuffer',g_attatchECXBuffer)
+ setImmediate(() => nativeativeFunction(msgType, myTalkerIdPtr, myContentPtr, myGroupMsgSenderIdPtr, myXmlContentPtr, isMyMsg))
+ }
+ }
+ })
+ return nativeCallback
+})()
- Memory.patchCode(g_initTestAsm, Process.pageSize, code => {
- var cw = new X86Writer(code, { pc: g_initTestAsm })
- cw.putPushfx()
- cw.putPushax()
- //cw.putMovRegAddress('eax', g_attatchEBP210Buffer)
+// 003 done
+const getBaseNodeAddress = (() => {
+ return moduleBaseAddress.add(offset.contactInfo.nodeOffset).readPointer()
+})
- /*cw.putMovRegAddress('edi',g_EDIPtr)
- cw.putMovRegReg('esi','edi')
- cw.putMovRegAddress('eax',g_BufferEbp2C)
- cw.putMovRegAddress('ecx',g_initECXTempPtr)
- cw.putPushReg('eax')
- cw.putCallAddress(moduleBaseAddress.add(0x131bb0))*/
+// 004 done
+const getHeaderNodeAddress = (() => {
+ const baseAddress = getBaseNodeAddress()
+ //console.log('baseAddress',baseAddress)
+ if (baseAddress.isNull()) {
+ return baseAddress
+ }
- //cw.putMovRegOffsetPtrU32('ebp', -20, 0)
-
- /*cw.putPushU32(0)
- cw.putMovRegAddress('eax', g_attatchPathPtr)
- cw.putPushReg('eax')
- cw.putPushU32(3)
- cw.putMovRegAddress('ecx', g_attatchEBP210Buffer)
- cw.putCallAddress(moduleBaseAddress.add(0x130220))*/
+ //console.log('HeaderNodeAddress',baseAddress.add(offset.handle_offset).readPointer())
+ return baseAddress.add(offset.contactInfo.nodeRootOffset).readPointer()
+})
+// 006 done
+const getMyselfInfoFunction = (() => {
- /*cw.putMovRegAddress('edi', g_attatchEBPAc)//后面要用的的ebp-2c
- cw.putMovRegAddress('ecx', g_attatchEBP210Buffer)
- cw.putPushReg('ecx')
- cw.putMovRegU32('eax',0)
- cw.putPushReg('eax')//push eax
- cw.putMovRegReg('ecx', 'edi')
- cw.putMovRegAddress('esi',g_attatchPathPtr)
- cw.putCallAddress(moduleBaseAddress.add(0x138880))*/
+ let ptr = 0
+ let wx_code = ''
+ let wx_id = ''
+ let wx_name = ''
+ let head_img_url = ''
+ const base = moduleBaseAddress.add(offset.myselfinfo.offset)
+ const wxid_len = base.add(offset.myselfinfo.wxid_len_offset).readU32()
- /*cw.putSubRegImm('esp',0x14)
- cw.putMovRegU32('ecx',g_initECXU32)
- cw.putMovRegU32('esi',g_attatchESIU32)
- cw.putMovRegAddress('eax', g_attatchEBPAc)
- cw.putPushReg('eax')
- cw.putCallAddress(moduleBaseAddress.add(0x173620))*/
- //cw.putCallAddress(moduleBaseAddress.add(0x522590))
+ if (wxid_len === 0x13) { // 新版本微信
+ wx_id = base.readPointer().readAnsiString(wxid_len)
+ wx_code = base.add(offset.myselfinfo.wxcode_new).readAnsiString()
+ } else {
+ wx_id = readString(base)
+ wx_code = wx_id
+ }
- /** g_attatchEBPAc*/
- //cw.putMovRegNearPtr('eax', g_attatchEBPAc)
- //cw.putMovNearPtrReg(g_attatchEBPAc.add(0xc), 'eax')
- /** g_attatchEBPAc*/
+ wx_name = readString(base.add(offset.myselfinfo.wx_nick_name))
+ const img_addr = base.add(offset.myselfinfo.head_img_url).readPointer()
+ const img_len = base.add(offset.myselfinfo.head_img_url_len).readU32()
- //cw.putMovRegAddress('ebx', g_initEBXPtr)
- //cw.putMovRegU32('edi', g_EDI.toInt32())
- //cw.putMovRegU32('esi', g_EDI.toInt32())
- /*cw.putMovRegU32('ecx', g_initECX)
- cw.putMovRegAddress('eax', g_BufferEbp2C)
- cw.putPushReg('eax')
- cw.putCallAddress(moduleBaseAddress.add(0x131BB0))*/
+ head_img_url = img_addr.readAnsiString(img_len)
- cw.putPopax()
- cw.putPopfx()
- cw.putRet()
- cw.flush()
+ const myself = {
+ id: wx_id,
+ code: wx_code,
+ name: wx_name,
+ head_img_url: head_img_url,
+ };
- })
+ return JSON.stringify(myself)
- const nativeativeFunction = new NativeFunction(ptr(g_initTestAsm), 'void', [])
- nativeativeFunction()
})
+// 043 done
+const recurseNew = ((node) => {
+ const headerNodeAddress = getHeaderNodeAddress()
+ if (headerNodeAddress.isNull()) {
+ return
+ }
-let g_personal_detail_ebx = null
-let g_personal_detail_asm = null
-let g_personal_wxid = null
-let g_personal_wxid_ptr = null
-const getOldTest = ((wxid) => {//personal detail
+ if (node.equals(headerNodeAddress)) {
+ return
+ }
- g_personal_detail_asm = Memory.alloc(Process.pageSize)
- g_personal_detail_ebx = moduleBaseAddress.add(0x222F38C).readPointer().add(0xFB8).toInt32()
+ for (const item in nodeList) {
+ if (node.equals(nodeList[item])) {
+ return
+ }
+ }
- g_personal_wxid_ptr = Memory.alloc(wxid.length * 2 + 2)
- g_personal_wxid_ptr.writeUtf16String(wxid)
- g_personal_wxid = Memory.alloc(0x14)
- g_personal_wxid.writePointer(ptr(g_personal_wxid_ptr)).add(0x04)
- .writeU32(wxid.length * 2).add(0x04)
- .writeU32(wxid.length * 2).add(0x08)
+ nodeList.push(node)
+ const id = readString(node.add(0x8))
+ //wxid, format relates to registration method
+ const wxid = readWideString(node.add(0x30))
+ //console.log('-----------',wxid)
- console.log('-----------address----------', g_personal_detail_asm)
- Memory.patchCode(g_personal_detail_asm, Process.pageSize, code => {
- var cw = new X86Writer(code, { pc: g_personal_detail_asm })
- cw.putPushfx()
- cw.putPushax()
+ //custom id, if not set return null, and use wxid which should be custom id
+ //const wx_code = readWideString(node.add(0x4c)) || readWideString(node.add(0x38))
- cw.putCallAddress(moduleBaseAddress.add(0x9A000))
+ //custom Nickname
+ const name = readWideString(node.add(0x8c))
- //78BA9ACE | E8 2D05D6FF | call wechatwin.7890A000 |
- cw.putMovRegU32('ebx', g_personal_detail_ebx)
- cw.putMovRegReg('esi', 'eax')
- cw.putPushReg('ebx')
- cw.putSubRegImm('esp', 0x14)
- cw.putMovRegAddress('eax', g_personal_wxid)
- cw.putMovRegReg('ecx', 'esp')
- cw.putPushReg('eax')
- cw.putCallAddress(moduleBaseAddress.add(0x701DC0))
- cw.putMovRegReg('ecx', 'esi')
- cw.putCallAddress(moduleBaseAddress.add(0x4024A0))
+ //alias aka 'remark' in wechat
+ //const alias = readWideString(node.add(0x80))
- cw.putPopax()
- cw.putPopfx()
- cw.putRet()
- cw.flush()
+ //avatarUrl
+ //const avatar = readWideString(node.add(0x138))
+ //const avatar = Memory.readUtf16String(node.add(0x138).readPointer())
+ //contact gender
+ //const gender = node.add(0x18C).readU32()
- })
+ const contactJson = {
+ id1: id,
+ id: wxid,
+ name: name,
+ /*code: wx_code,
+ name: name,
+ alias: alias,
+ avatarUrl: avatar,
+ gender: gender,*/
+ }
- const nativeativeFunction = new NativeFunction(ptr(g_personal_detail_asm), 'void', [])
- nativeativeFunction()
+ contactList.push(contactJson)
+ const leftNode = node.add(0x0).readPointer()
+ const centerNode = node.add(0x04).readPointer()
+ //const rightNode = node.add(0x08).readPointer()
-})
+ recurseNew(leftNode)
+ recurseNew(centerNode)
+ //recurse(rightNode)
-// const writeLogNativeCallback = (() => {
-// const nativeCallback = new NativeCallback(() => { }, 'void', [])
-// const nativeCallFunction = new NativeFunction(nativeCallback, 'void', [])
+ const allContactJson = contactList
+ return allContactJson
-// Interceptor.attach(
-// moduleBaseAddress.add(0x7008A4),
-// {
-// onEnter() {
-// const addr = this.context.eax//.sub(0x114)//0xc30-0x08
-// if(addr >0){
-// const log = ptr(addr).readAnsiString()
-// }
-// }
-// })
-// return nativeCallback
-// })()
+})
-/**
- * test call
- */
-let attatchTestAsm = null
-let attatchTestEbp2C = null
-let attatchGlobalEDI = null
-let attatchGlobalEDIB88 = null
-let attatchTestEBX = null
-let g_tempEcx = null
-let attatchFirstECX = null
-//let attatchFirstECX = null
-let gattatchFilePtr = null
-let gattatchFile = null
-let gattatchReceiveIdPtr = null
-let gattatchReceiveId = null
-let attatchEAX3B0Buf = null
+// 044 done
+const getContactNativeFunction = (() => {
+ const headerNodeAddress = getHeaderNodeAddress()
+ //console.log('headerNodeAddress',headerNodeAddress)
-let attatchESIbuf = null
-const getWxTest = ((contactId, filePath) => {
- //const nativeativeFunction = new NativeFunction(ptr(addr), 'void', [])
- //nativeativeFunction()
- attatchTestAsm = Memory.alloc(Process.pageSize)
- console.log('----------------address', attatchTestAsm)
- attatchTestEbp2C = Memory.alloc(0xC)
- attatchGlobalEDI = moduleBaseAddress.add(0x222f38c).readPointer()
- .add(0x938).add(0x438).readPointer()
- attatchGlobalEDIB88 = attatchGlobalEDI.add(0xB88).readPointer()
- attatchTestEBX = Memory.alloc(0x4)
- attatchTestEBX.writePointer(attatchGlobalEDI)
- console.log('----------------attatchGlobalEDI', attatchGlobalEDI)
- console.log('----------------attatchGlobalEDIB88', attatchGlobalEDIB88)
+ if (headerNodeAddress.isNull()) {
+ return '[]'
+ }
- attatchFirstECX = Memory.alloc(0x28)
- //const attatchSecondEcx = Memory.alloc(0x14)
+ const node = headerNodeAddress.add(0x0).readPointer()
+ const ret = recurseNew(node)
- const contactIdLength = contactId.length * 2 + 2//edx
- const contractIdActLength = contactId.length
+ //console.log(ret)
+ console.log('getContactNativeFunction:', ret.length)
+ /*for (let item of ret){
+ console.log(JSON.stringify(item))
+ }*/
+ //console.log(ret.contact)
+ const cloneRet = JSON.stringify(ret)
+ nodeList.length = 0
+ contactList.length = 0
- gattatchReceiveIdPtr = Memory.alloc(contactId.length * 2 + 2)
- gattatchReceiveIdPtr.writeUtf16String(contactId)
+ return cloneRet
+})
- gattatchReceiveId = Memory.alloc(0x14)
- gattatchReceiveId.writePointer(ptr(gattatchReceiveIdPtr)).add(0x04)
- .writeU32(contactId.length * 2).add(0x04)
- .writeU32(contactId.length * 2).add(0x08)
- //console.log('----------------attatchGlobalEDIB88',attatchGlobalEDIB88)
- //return
- /*console.log(hexdump(attatchTestEBX, {
- offset: 0,
- length: 0x40,
- header: true,
- ansi: true
- }))
- return*/
+// 0xx done
+const getChatroomNodeAddress = (() => {
+ const baseAddress = moduleBaseAddress.add(offset.chatroomInfo.nodeOffset).readPointer()
+ if (baseAddress.isNull()) {
+ return baseAddress
+ }
+ return baseAddress.add(offset.chatroomInfo.nodeRootOffset).readPointer()
+})
- gattatchFilePtr = Memory.alloc(filePath.length * 2 + 2)
- gattatchFilePtr.writeUtf16String(filePath)
-
- gattatchFile = Memory.alloc(0x14)
- gattatchFile.writePointer(ptr(gattatchFilePtr)).add(0x04)
- .writeU32(filePath.length * 2).add(0x04)
- .writeU32(filePath.length * 2).add(0x08)
-
- const attatchLastECX = moduleBaseAddress.add(0x222f170).toInt32()
-
- attatchEAX3B0Buf = Memory.alloc(0x3B0)
-
- g_tempEcx = Memory.alloc(0x4)
- //g_tempEcx1 = Memory.alloc(0x4)
-
- attatchESIbuf = Memory.alloc(0x100)
- attatchESIbuf.add(0x0).writeU32(3)
- attatchESIbuf.add(0x4).writePointer(gattatchFilePtr)
- attatchESIbuf.add(0x8).writeU32(filePath.length * 2)
- attatchESIbuf.add(0xc).writeU32(filePath.length * 2)
-
- Memory.patchCode(attatchTestAsm, Process.pageSize, code => {
- var cw = new X86Writer(code, { pc: attatchTestAsm })
- cw.putPushfx()
- cw.putPushax()
- //cw.putMovRegU32('edi',attatchGlobalEDI)
-
-
- cw.putMovRegAddress('esi', attatchESIbuf)
-
- cw.putMovRegAddress('ecx', attatchFirstECX.add(0x14))
- cw.putMovRegAddress('eax', gattatchFile)
- cw.putPushReg('eax')
- cw.putCallAddress(moduleBaseAddress.add(0x701DC0))
-
-
- cw.putMovRegAddress('ecx', attatchFirstECX)
- cw.putMovRegU32('eax', contactIdLength)
- cw.putPushReg('eax')
- cw.putPushU32(0)
- cw.putCallAddress(moduleBaseAddress.add(0x1a11c83))
- cw.putAddRegImm('esp', 0x8)
-
- cw.putMovRegReg('edx', 'eax')
- cw.putMovNearPtrReg(attatchFirstECX, 'edx')
- cw.putMovRegU32('edi', contactIdLength)
- cw.putPushReg('edi')
- cw.putMovRegAddress('eax', gattatchReceiveIdPtr)//ebp-58
- cw.putPushReg('eax')
- cw.putMovRegNearPtr('eax', attatchFirstECX)
- cw.putPushReg('eax')
- cw.putCallAddress(moduleBaseAddress.add(0x1a1047a))
- cw.putAddRegImm('esp', 0x0c)
-
- //cw.putMovRegNearPtr('ecx',attatchFirstECX)
- //cw.putAddRegImm('esp', 0x0c)
- //cw.putMovRegU32('edx', 0)
- //cw.putMovRegRegPtr('eax', 'ecx')
- //cw.putMovNearPtrReg(attatchFirstECX.add(0x04),'edi')
- cw.putMovRegU32('edi', contactId.length * 2)
- cw.putMovRegU32('ecx', attatchLastECX)
- cw.putMovRegAddress('eax', attatchEAX3B0Buf)
- cw.putPushReg('eax')
- cw.putCallAddress(moduleBaseAddress.add(0x392260))
-
- cw.putMovRegAddress('ecx', attatchEAX3B0Buf)
- cw.putCallAddress(moduleBaseAddress.add(0x94200))
-
- cw.putPopax()
- cw.putPopfx()
- cw.putRet()
- cw.flush()
-
- })
-
- const nativeativeFunction = new NativeFunction(ptr(attatchTestAsm), 'void', [])
- nativeativeFunction()
+// 008chatroom member done
+const chatroomRecurse = ((node) => {
+ const chatroomNodeAddress = getChatroomNodeAddress()
+ if (chatroomNodeAddress.isNull()) {
+ return
+ }
+ if (node.equals(chatroomNodeAddress)) {
+ return
+ }
-})
-// 001
-const getTestInfoFunction = ((addr) => {
- const nativeativeFunction = new NativeFunction(ptr(addr), 'void', [])
- nativeativeFunction()
+ for (const item in chatroomNodeList) {
+ if (node.equals(chatroomNodeList[item])) {
+ return
+ }
+ }
- //00CFE484
+ chatroomNodeList.push(node)
+ const roomid = readWideString(node.add(0x10))
+ const len = node.add(0x54).readU32() //
+ //const memberJson={}
+ if (len > 4) { //
+ const memberStr = readString(node.add(0x44))
+ if (memberStr.length > 0) {
+ const memberList = memberStr.split(/[\\^][G]/)
+ const memberJson = {
+ roomid: roomid,
+ roomMember: memberList
+ }
- /*MemoryAccessMonitor.enable({base:ptr(addr),size:0x01}, {
- onAccess(details){
- console.log('============')
- console.log(details.operation)
- console.log(details.from)
- console.log(details.address)
- console.log('============')
+ chatroomMemberList.push(memberJson)
}
- })*/
-})
+ }
-// 002get global data
+ const leftNode = node.add(0x0).readPointer()
+ const centerNode = node.add(0x04).readPointer()
+ const rightNode = node.add(0x08).readPointer()
-const isLoggedInFunction = (() => {
- loggedIn = moduleBaseAddress.add(offset.is_logged_in_offset).readU32()
- return !!loggedIn
-})
+ chatroomRecurse(leftNode)
+ chatroomRecurse(centerNode)
+ chatroomRecurse(rightNode)
-// 007 缺失,请标注已废弃或者其他原因
-const getMyselfIdFunction = (() => {
+ const allChatroomMemberJson = chatroomMemberList
+ return allChatroomMemberJson
+})
- let wx_id = readString(moduleBaseAddress.add(offset.wxid_offset))
+// 009 done
+const getChatroomMemberInfoFunction = (() => {
+ const chatroomNodeAddress = getChatroomNodeAddress()
+ if (chatroomNodeAddress.isNull()) {
+ return '[]'
+ }
- return wx_id
+ const node = chatroomNodeAddress.add(0x0).readPointer()
+ const ret = chatroomRecurse(node)
+ const cloneRet = JSON.stringify(ret)
+ chatroomNodeList.length = 0 //empty
+ chatroomMemberList.length = 0 //empty
+ return cloneRet
})
-// std::wstring
-// const wstr = readWStringPtr(ptr).readUtf16String()
-const readWStringPtr = (address) => {
- const addr = ptr(address)
- const size = addr.add(4).readU32()
- const capacity = addr.add(8).readU32()
- addr.ptr = addr.readPointer()
- addr.size = size
- addr.capacity = capacity
- addr.ptr._readUtf16String = addr.ptr.readUtf16String
- addr.readUtf16String = () => { return addr.size ? addr.ptr._readUtf16String(addr.size * 2) : '' }
-
- // console.log('readWStringPtr() address:',address,' -> ptr:', addr.ptr, 'size:', addr.size, 'capacity:', addr.capacity)
- // console.log('readWStringPtr() str:' , `"${addr.readUtf16String()}"`,'\n',addr.ptr.readByteArray(addr.size*2+2),'\n')
- // console.log('readWStringPtr() address:', addr,'dump:', addr.readByteArray(16),'\n')
+// 024 done
+/**
+ * sendMsgNativeFunction
+ * send text message
+ * @param {string} talkerId = wxid or roomid
+ * @param {string} content
+ */
+ const sendMsgNativeFunction = ((talkerId, content) => {
- return addr
-}
+ const txtAsm = Memory.alloc(Process.pageSize)
+ //const buffwxid = Memory.alloc(0x20)
-//contact
-const recurse = ((node) => {
- const headerNodeAddress = getHeaderNodeAddress()
- if (headerNodeAddress.isNull()) { return }
- if (node.equals(headerNodeAddress)) { return }
+ let wxidPtr = Memory.alloc(talkerId.length * 2 + 2)
+ wxidPtr.writeUtf16String(talkerId)
- for (const item in nodeList) {
- if (node.equals(nodeList[item])) {
- return
- }
- }
+ let picWxid = Memory.alloc(0x0c)
+ picWxid.writePointer(ptr(wxidPtr)).add(0x04)
+ .writeU32(talkerId.length * 2).add(0x04)
+ .writeU32(talkerId.length * 2).add(0x04)
+ let contentPtr = Memory.alloc(content.length * 2 + 2)
+ contentPtr.writeUtf16String(content)
- nodeList.push(node)
- //wxid, format relates to registration method
- const wxid = readWideString(node.add(0x38))
+ const sizeOfStringStruct = Process.pointerSize * 5
+ let contentStruct = Memory.alloc(sizeOfStringStruct)
- //custom id, if not set return null, and use wxid which should be custom id
- const wx_code = readWideString(node.add(0x4c)) || readWideString(node.add(0x38))
+ contentStruct
+ .writePointer(contentPtr).add(0x4)
+ .writeU32(content.length).add(0x4)
+ .writeU32(content.length * 2)
- //custom Nickname
- const name = readWideString(node.add(0x94))
- //alias aka 'remark' in wechat
- const alias = readWideString(node.add(0x80))
+ const ecxBuffer = Memory.alloc(0x2d8)
- //avatarUrl
- const avatar = readWideString(node.add(0x138))
- //const avatar = Memory.readUtf16String(node.add(0x138).readPointer())
- //contact gender
- const gender = node.add(0x18C).readU32()
+ Memory.patchCode(txtAsm, Process.pageSize, code => {
+ var cw = new X86Writer(code, {
+ pc: txtAsm
+ })
+ cw.putPushfx()
+ cw.putPushax()
- const contactJson = {
- id: wxid,
- code: wx_code,
- name: name,
- alias: alias,
- avatarUrl: avatar,
- gender: gender,
- }
+ cw.putPushU32(0x0)
+ cw.putPushU32(0x0)
+ cw.putPushU32(0x0)
+ cw.putPushU32(0x1)
+ cw.putPushU32(0x0)
- contactList.push(contactJson)
+ //cw.putMovRegReg
- const leftNode = node.add(0x0).readPointer()
- const centerNode = node.add(0x04).readPointer()
- const rightNode = node.add(0x08).readPointer()
+ cw.putMovRegAddress('eax', contentStruct)
+ cw.putPushReg('eax')
- recurse(leftNode)
- recurse(centerNode)
- recurse(rightNode)
+ cw.putMovRegAddress('edx', picWxid) //room_id
- const allContactJson = contactList
- return allContactJson
+ cw.putMovRegAddress('ecx', ecxBuffer)
+ cw.putCallAddress(moduleBaseAddress.add(
+ offset.sendTxtMsg.callOffset
+ ))
-})
+ cw.putAddRegImm('esp', 0x18)
+ cw.putPopax()
+ cw.putPopfx()
+ cw.putRet()
+ cw.flush()
-// 010 done
-const getWechatVersionFunction = (() => {
- if (currentVersion) {
- return currentVersion
- }
- const pattern = '55 8B ?? 83 ?? ?? A1 ?? ?? ?? ?? 83 ?? ?? 85 ?? 7F ?? 8D ?? ?? E8 ?? ?? ?? ?? 84 ?? 74 ?? 8B ?? ?? ?? 85 ?? 75 ?? E8 ?? ?? ?? ?? 0F ?? ?? 0D ?? ?? ?? ?? A3 ?? ?? ?? ?? A3 ?? ?? ?? ?? 8B ?? 5D C3'
- const results = Memory.scanSync(moduleLoad.base, moduleLoad.size, pattern)
- if (results.length == 0) {
- return 0
- }
- const addr = results[0].address
- const ret = addr.add(0x07).readPointer()
- const ver = ret.add(0x0).readU32()
- currentVersion = ver
- return ver
-})
+ })
-// 011 done
-const getWechatVersionStringFunction = ((ver = getWechatVersionFunction()) => {
- if (!ver) {
- return '0.0.0.0'
- }
- const vers = []
- vers.push((ver >> 24) & 255 - 0x60)
- vers.push((ver >> 16) & 255)
- vers.push((ver >> 8) & 255)
- vers.push(ver & 255)
- return vers.join('.')
-})
+ console.log('----------txtAsm', txtAsm)
+ const nativeativeFunction = new NativeFunction(ptr(txtAsm), 'void', [])
+ nativeativeFunction()
-// 012 done
-const checkSupportedFunction = (() => {
- const ver = getWechatVersionFunction()
- return ver == availableVersion
})
+// 023 done
/**
- * @Hook: recvMsg -> recvMsgNativeCallback
- */
+* send at msg
+*/
+let asmAtMsg = null
+let roomid_, msg_, wxid_, atid_
+let ecxBuffer
+const sendAtMsgNativeFunction = ((roomId, text, contactId,nickname) => {
-// 019 done
-const recvMsgNativeCallback = (() => {
+ asmAtMsg = Memory.alloc(Process.pageSize)
+ ecxBuffer = Memory.alloc(0x3b0)
+ const atContent = '@'+nickname+' '+text
- const nativeCallback = new NativeCallback(() => {}, 'void', ['int32', 'pointer', 'pointer', 'pointer', 'pointer', 'int32'])
- const nativeativeFunction = new NativeFunction(nativeCallback, 'void', ['int32', 'pointer', 'pointer', 'pointer', 'pointer', 'int32'])
+ roomid_ = initStruct(roomId)
+ wxid_ = initidStruct(contactId)
+ msg_ = initmsgStruct(atContent)
+ atid_ = initAtMsgStruct(wxid_)
- Interceptor.attach(
- moduleBaseAddress.add(offset.hook_point), {
- onEnter() {
- const addr = this.context.ecx //0xc30-0x08
- const msgType = addr.add(0x38).readU32()
- const isMyMsg = addr.add(0x3C).readU32() //add isMyMsg
+ Memory.patchCode(asmAtMsg, Process.pageSize, code => {
+ var cw = new X86Writer(code, {
+ pc: asmAtMsg
+ })
+ cw.putPushfx()
+ cw.putPushax()
- if (msgType > 0) {
+ cw.putPushU32(0x0)
+ cw.putPushU32(0x0)
+ cw.putPushU32(0x0)
+ cw.putPushU32(0x1)
+ //cw.putPushU32(0x0)
+ cw.putMovRegAddress('eax', atid_)
+ cw.putPushReg('eax')
- const talkerIdPtr = addr.add(0x48).readPointer()
- //console.log('txt msg',talkerIdPtr.readUtf16String())
- const talkerIdLen = addr.add(0x48 + 0x04).readU32() * 2 + 2
+ //cw.putMovRegReg
- const myTalkerIdPtr = Memory.alloc(talkerIdLen)
- Memory.copy(myTalkerIdPtr, talkerIdPtr, talkerIdLen)
+ cw.putMovRegAddress('eax', msg_)
+ cw.putPushReg('eax')
+ cw.putMovRegAddress('edx', roomid_) //room_id
- let contentPtr = null
- let contentLen = 0
- let myContentPtr = null
- if (msgType == 3) { // pic path
- let thumbPtr = addr.add(0x198).readPointer();
- let hdPtr = addr.add(0x1ac).readPointer();
- let thumbPath = thumbPtr.readUtf16String();
- let hdPath = hdPtr.readUtf16String();
- let picData = [
- thumbPath, // PUPPET.types.Image.Unknown
- thumbPath, // PUPPET.types.Image.Thumbnail
- hdPath, // PUPPET.types.Image.HD
- hdPath // PUPPET.types.Image.Artwork
- ]
- let content = JSON.stringify(picData);
- myContentPtr = Memory.allocUtf16String(content);
- } else {
- contentPtr = addr.add(0x70).readPointer()
- contentLen = addr.add(0x70 + 0x04).readU32() * 2 + 2
- myContentPtr = Memory.alloc(contentLen)
- Memory.copy(myContentPtr, contentPtr, contentLen)
- }
+ cw.putMovRegAddress('ecx', ecxBuffer)
+ cw.putCallAddress(moduleBaseAddress.add(
+ offset.sendTxtMsg.callOffset
+ ))
- // console.log('----------------------------------------')
- // console.log(msgType)
- // console.log(contentPtr.readUtf16String())
- // console.log('----------------------------------------')
- const groupMsgAddr = addr.add(0x170).readU32() //* 2 + 2
- let myGroupMsgSenderIdPtr = null
- if (groupMsgAddr == 0) { //weChatPublic is zero,type is 49
+ cw.putAddRegImm('esp', 0x18)
+ cw.putPopax()
+ cw.putPopfx()
+ cw.putRet()
+ cw.flush()
- myGroupMsgSenderIdPtr = Memory.alloc(0x10)
- myGroupMsgSenderIdPtr.writeUtf16String("null")
+ })
- } else {
+ //console.log('----------txtAsm', asmAtMsg)
+ const nativeativeFunction = new NativeFunction(ptr(asmAtMsg), 'void', [])
+ nativeativeFunction()
- const groupMsgSenderIdPtr = addr.add(0x170).readPointer()
- const groupMsgSenderIdLen = addr.add(0x170 + 0x04).readU32() * 2 + 2
- myGroupMsgSenderIdPtr = Memory.alloc(groupMsgSenderIdLen)
- Memory.copy(myGroupMsgSenderIdPtr, groupMsgSenderIdPtr, groupMsgSenderIdLen)
+})
- }
+// 022 done
+/**
+ *
+ * @param {*} contactId
+ * @param {*} path
+ */
+ const sendPicMsgNativeFunction = ((contactId, path) => {
- const xmlNullPtr = addr.add(0x1f0).readU32() //3.9.2.23
- let myXmlContentPtr = null
- if (xmlNullPtr == 0) {
+ const picAsm = Memory.alloc(Process.pageSize)
+ const buffwxid = Memory.alloc(0x20)
+ const picbuff = Memory.alloc(0x2D8)
- myXmlContentPtr = Memory.alloc(0x10)
- myXmlContentPtr.writeUtf16String("null")
+ let pathPtr = Memory.alloc(path.length * 2 + 1)
+ pathPtr.writeUtf16String(path)
- } else {
- const xmlContentPtr = addr.add(0x1f0).readPointer() //3.9.2.23
+ let imagefilepath = Memory.alloc(0x24)
+ imagefilepath.writePointer(pathPtr).add(0x04)
+ .writeU32(path.length * 2).add(0x04)
+ .writeU32(path.length * 2).add(0x04)
- const xmlContentLen = addr.add(0x1f0 + 0x04).readU32() * 2 + 2
- myXmlContentPtr = Memory.alloc(xmlContentLen)
- Memory.copy(myXmlContentPtr, xmlContentPtr, xmlContentLen)
- }
+ let picWxidPtr = Memory.alloc(contactId.length * 2 + 1)
+ picWxidPtr.writeUtf16String(contactId)
- setImmediate(() => nativeativeFunction(msgType, myTalkerIdPtr, myContentPtr, myGroupMsgSenderIdPtr, myXmlContentPtr, isMyMsg))
- }
- }
- })
- return nativeCallback
-})()
+ let picWxid = Memory.alloc(0x0c)
+ picWxid.writePointer(ptr(picWxidPtr)).add(0x04)
+ .writeU32(contactId.length * 2).add(0x04)
+ .writeU32(contactId.length * 2).add(0x04)
-// 003get myself info done
-const getBaseNodeAddress = (() => {
- return moduleBaseAddress.add(offset.contactInfo.nodeOffset).readPointer()
-})
-// 004 done
-const getHeaderNodeAddress = (() => {
- const baseAddress = getBaseNodeAddress()
- //console.log('baseAddress',baseAddress)
- if (baseAddress.isNull()) {
- return baseAddress
- }
+ //const test_offset1 = 0x701DC0;
+ Memory.patchCode(picAsm, Process.pageSize, code => {
+ var cw = new X86Writer(code, {
+ pc: picAsm
+ })
+ cw.putPushfx();
+ cw.putPushax();
+ cw.putCallAddress(moduleBaseAddress.add(
+ offset.sendPicMsg.call1
+ ))
+ cw.putMovRegReg('edx', 'eax') //缓存
- //console.log('HeaderNodeAddress',baseAddress.add(offset.handle_offset).readPointer())
- return baseAddress.add(offset.contactInfo.nodeRootOffset).readPointer()
-})
+ cw.putSubRegImm('esp', 0x14)
+ cw.putMovRegAddress('eax', buffwxid)
+ cw.putMovRegReg('ecx', 'esp')
+ cw.putMovRegAddress('edi', imagefilepath)
+ cw.putPushReg('eax')
+ cw.putCallAddress(moduleBaseAddress.add(
+ offset.sendPicMsg.call2
+ ))
-// 006 done
-const getMyselfInfoFunction = (() => {
+ cw.putMovRegReg('ecx', 'edx')
+ cw.putMovRegAddress('eax', picWxid) //=lea
+ cw.putMovRegAddress('edi', imagefilepath)
+ cw.putPushReg('edi')
+ cw.putPushReg('eax')
+ cw.putMovRegAddress('eax', picbuff)
+ cw.putPushReg('eax')
- let ptr = 0
- let wx_code = ''
- let wx_id = ''
- let wx_name = ''
- let head_img_url = ''
+ cw.putMovRegAddress('edi', picWxid) //edi
+ cw.putCallAddress(moduleBaseAddress.add(
+ offset.sendPicMsg.call3
+ ))
- const base = moduleBaseAddress.add(offset.myselfinfo.offset)
- const wxid_len = base.add(offset.myselfinfo.wxid_len_offset).readU32()
- if (wxid_len === 0x13) { // 新版本微信
- wx_id = base.readPointer().readAnsiString(wxid_len)
- wx_code = base.add(offset.myselfinfo.wxcode_new).readAnsiString()
- } else {
- wx_id = readString(base)
- wx_code = wx_id
- }
+ cw.putPopax()
+ cw.putPopfx()
+ cw.putRet()
+ cw.flush()
- wx_name = readString(base.add(offset.myselfinfo.wx_nick_name))
- const img_addr = base.add(offset.myselfinfo.head_img_url).readPointer()
- const img_len = base.add(offset.myselfinfo.head_img_url_len).readU32()
+ })
- head_img_url = img_addr.readAnsiString(img_len)
+ //console.log('----------picAsm',picAsm)
+ const nativeativeFunction = new NativeFunction(ptr(picAsm), 'void', [])
+ nativeativeFunction()
- const myself = {
- id: wx_id,
- code: wx_code,
- name: wx_name,
- head_img_url: head_img_url,
- };
+})
- return JSON.stringify(myself)
+// 020 done
+let memberNickBuffAsm = null
+let nickRoomId = null
+let nickMemberId = null
+let nickBuff = null
+const getChatroomMemberNickInfoFunction = ((memberId, roomId) => {
-})
+ nickBuff = Memory.alloc(0x7e4)
+ //const nickRetAddr = Memory.alloc(0x04)
+ memberNickBuffAsm = Memory.alloc(Process.pageSize)
+ //console.log('asm address----------',memberNickBuffAsm)
+ nickRoomId = initidStruct(roomId)
+ //console.log('nick room id',nickRoomId)
+ nickMemberId = initStruct(memberId)
-// done
-const recurseNew = ((node) => {
- const headerNodeAddress = getHeaderNodeAddress()
- if (headerNodeAddress.isNull()) {
- return
- }
+ //console.log('nick nickMemberId id',nickMemberId)
+ //const nickStructPtr = initmsgStruct('')
- if (node.equals(headerNodeAddress)) {
- return
- }
+ Memory.patchCode(memberNickBuffAsm, Process.pageSize, code => {
+ var cw = new X86Writer(code, {
+ pc: memberNickBuffAsm
+ })
+ cw.putPushfx()
+ cw.putPushax()
+ cw.putMovRegAddress('edi', nickRoomId)
+ cw.putMovRegAddress('eax', nickBuff)
+ cw.putMovRegReg('edx', 'edi')
+ cw.putPushReg('eax')
+ cw.putMovRegAddress('ecx', nickMemberId)
+ cw.putCallAddress(moduleBaseAddress.add(0xC06F10))
+ cw.putAddRegImm('esp', 0x04)
+ cw.putPopax()
+ cw.putPopfx()
+ cw.putRet()
+ cw.flush()
- for (const item in nodeList) {
- if (node.equals(nodeList[item])) {
- return
- }
- }
+ })
+ const nativeativeFunction = new NativeFunction(ptr(memberNickBuffAsm), 'void', [])
+ nativeativeFunction()
- nodeList.push(node)
- const id = readString(node.add(0x8))
- //wxid, format relates to registration method
- const wxid = readWideString(node.add(0x30))
- //console.log('-----------',wxid)
+ const nickname = readWideString(nickBuff)
+ console.log('----nickname', nickname)
+ return readWideString(nickBuff)
+})
+/* 由此之后是3.9.2.23中缺失的未实现方法 */
- //custom id, if not set return null, and use wxid which should be custom id
- //const wx_code = readWideString(node.add(0x4c)) || readWideString(node.add(0x38))
+// 038 初始化全局变量 tbd
+let g_initTestAsm = null
+let g_BufferEbp2C = null
+let g_initECXU32 = null
+let g_initECXPtr = null
+let g_initEBXPtr = null
+let g_initEBX = null
- //custom Nickname
- const name = readWideString(node.add(0x8c))
+let g_attatchEBP210Buffer = null
+let g_attatchPathPtr = null
+let g_attatchPath = null
+let g_attatchEBPAc = null
+let g_attatchEBPAcBufPtr = null
- //alias aka 'remark' in wechat
- //const alias = readWideString(node.add(0x80))
+let g_attatchContactIdPtr = null
+//let g_attatchECXBuffer = null
+let g_attatchESIU32 = null
- //avatarUrl
- //const avatar = readWideString(node.add(0x138))
- //const avatar = Memory.readUtf16String(node.add(0x138).readPointer())
- //contact gender
- //const gender = node.add(0x18C).readU32()
+let g_initECXTempPtr = null
+const initGlobal = ((contactId, attatchFile) => {
- const contactJson = {
- id1: id,
- id: wxid,
- name: name,
- /*code: wx_code,
- name: name,
- alias: alias,
- avatarUrl: avatar,
- gender: gender,*/
- }
+ //const base = moduleBaseAddress.add(0x222f38c).readPointer()
+ //g_EDI = base.add(0xD70).readPointer()//0x438+0x938
+ console.log('------------g_attatchEBPAc', g_attatchEBPAc)
+ console.log('------------g_EDIU32', g_EDIU32)
+ g_initTestAsm = Memory.alloc(Process.pageSize)
+ console.log('------------address', g_initTestAsm)
- contactList.push(contactJson)
+ g_initECXPtr = g_EDIPtr.add(0xB80).readPointer().add(0x1640)
+ g_initECXTempPtr = g_EDIPtr.add(0xB88).readPointer()
+ g_initECXU32 = g_initECXPtr.toInt32()
+ g_attatchESIU32 = g_EDIU32
- const leftNode = node.add(0x0).readPointer()
- const centerNode = node.add(0x04).readPointer()
- //const rightNode = node.add(0x08).readPointer()
+ console.log('------------g_initECXU32', g_initECXU32)
+ console.log('------------g_initESIU32', g_attatchESIU32)
- recurseNew(leftNode)
- recurseNew(centerNode)
- //recurse(rightNode)
- const allContactJson = contactList
- return allContactJson
+ //console.log('==========g_initECXPtr',g_initECXPtr)
+ //console.log('==========g_EDIU32',g_EDIU32)
-})
+ //g_attatchECXBuffer = Memory.alloc(0x1024)
+ //Memory.copy(g_attatchECXBuffer, g_initECXPtr, 0x1024)
-// done ?
-const getContactNativeFunction = (() => {
- const headerNodeAddress = getHeaderNodeAddress()
- //console.log('headerNodeAddress',headerNodeAddress)
+ g_BufferEbp2C = Memory.alloc(0x48)
- if (headerNodeAddress.isNull()) {
- return '[]'
- }
+ //g_initEBX = moduleBaseAddress.add(0x2251724).readPointer().readPointer()
+ //g_initEBXPtr = Memory.alloc(0x14).writePointer(g_initEBX)
+ //g_initEBXPtr.add(0x08).writePointer(g_BufferEbp2C)
- const node = headerNodeAddress.add(0x0).readPointer()
- const ret = recurseNew(node)
+ g_attatchPathPtr = Memory.alloc(attatchFile.length * 2 + 2)
+ g_attatchPathPtr.writeUtf16String(attatchFile)
- //console.log(ret)
+ g_attatchPath = Memory.alloc(0x28)
+ g_attatchPath.writePointer(g_attatchPathPtr).add(0x04)
+ .writeU32(attatchFile.length * 2).add(0x04)
+ .writeU32(attatchFile.length * 2).add(0x04)
+ /*---------------------------------ebp-210----------------*/
+ g_attatchEBP210Buffer = Memory.alloc(0x48)
+ g_attatchEBP210Buffer.writeU32(0x3)
+ g_attatchEBP210Buffer.add(0x4).writePointer(g_attatchPathPtr)
+ g_attatchEBP210Buffer.add(0x8).writeU32(attatchFile.length * 2)
+ g_attatchEBP210Buffer.add(0xC).writeU32(attatchFile.length * 2)
+ g_attatchEBP210Buffer.add(0x2C).writeU32(moduleBaseAddress.add(0x2ECE87).toInt32())
+ //console.log('------------g_attatchEBP210Buffer',g_attatchEBP210Buffer)
+ /*---------------------------------ebp-210----------------*/
- console.log('getContactNativeFunction:', ret.length)
- /*for (let item of ret){
- console.log(JSON.stringify(item))
- }*/
- //console.log(ret.contact)
- const cloneRet = JSON.stringify(ret)
- nodeList.length = 0
- contactList.length = 0
+ //g_attatchContactIdPtr = Memory.alloc(0x4)
+ //g_attatchContactIdPtr.writeUtf16String(contactId)
+ //console.log('------------g_attatchEBP210Buffer',g_attatchEBP210Buffer)
+ g_attatchEBPAc = Memory.alloc(0x140)
+ //g_attatchEBPAcBufPtr = Memory.alloc(0x100)
+ //g_attatchEBPAc.writePointer(g_attatchEBP210Buffer)
+ //g_attatchEBPAc.add(0x4).writePointer(g_attatchEBPAcBufPtr)
+ //g_attatchEBPAc.add(0x8).writePointer(g_attatchEBPAcBufPtr)
+ g_attatchEBPAc.add(0x10).writeU32(g_EDIU32)
+ console.log('------------g_attatchEBPAc', g_attatchEBPAc)
- return cloneRet
-})
+ /*g_attatchECXBuffer.add(0x18).writePointer(g_attatchContactIdPtr)
+ g_attatchECXBuffer.add(0x1C).writeU32(contactId.length*2)
+ .add(0x04).writeU32(contactId.length*2)*/
-// 005 done
-const getChatroomNodeAddress = (() => {
- const baseAddress = moduleBaseAddress.add(offset.chatroomInfo.nodeOffset).readPointer()
- if (baseAddress.isNull()) {
- return baseAddress
- }
- return baseAddress.add(offset.chatroomInfo.nodeRootOffset).readPointer()
-})
-// 008chatroom member done
-const chatroomRecurse = ((node) => {
- const chatroomNodeAddress = getChatroomNodeAddress()
- if (chatroomNodeAddress.isNull()) {
- return
- }
- if (node.equals(chatroomNodeAddress)) {
- return
- }
+ //g_attatchESIU32 = g_EDI.toInt32()
- for (const item in chatroomNodeList) {
- if (node.equals(chatroomNodeList[item])) {
- return
- }
- }
- chatroomNodeList.push(node)
- const roomid = readWideString(node.add(0x10))
+ //console.log('------------g_attatchESIU32',g_attatchESIU32)
+ //console.log('==========g_attatchECXBuffer',g_attatchECXBuffer)
- const len = node.add(0x54).readU32() //
- //const memberJson={}
- if (len > 4) { //
- const memberStr = readString(node.add(0x44))
- if (memberStr.length > 0) {
- const memberList = memberStr.split(/[\\^][G]/)
- const memberJson = {
- roomid: roomid,
- roomMember: memberList
- }
+ Memory.patchCode(g_initTestAsm, Process.pageSize, code => {
+ var cw = new X86Writer(code, { pc: g_initTestAsm })
+ cw.putPushfx()
+ cw.putPushax()
+ //cw.putMovRegAddress('eax', g_attatchEBP210Buffer)
- chatroomMemberList.push(memberJson)
- }
+ /*cw.putMovRegAddress('edi',g_EDIPtr)
+ cw.putMovRegReg('esi','edi')
+ cw.putMovRegAddress('eax',g_BufferEbp2C)
+ cw.putMovRegAddress('ecx',g_initECXTempPtr)
+ cw.putPushReg('eax')
+ cw.putCallAddress(moduleBaseAddress.add(0x131bb0))*/
- }
+ //cw.putMovRegOffsetPtrU32('ebp', -20, 0)
- const leftNode = node.add(0x0).readPointer()
- const centerNode = node.add(0x04).readPointer()
- const rightNode = node.add(0x08).readPointer()
+ /*cw.putPushU32(0)
+ cw.putMovRegAddress('eax', g_attatchPathPtr)
+ cw.putPushReg('eax')
+ cw.putPushU32(3)
+ cw.putMovRegAddress('ecx', g_attatchEBP210Buffer)
+ cw.putCallAddress(moduleBaseAddress.add(0x130220))*/
- chatroomRecurse(leftNode)
- chatroomRecurse(centerNode)
- chatroomRecurse(rightNode)
- const allChatroomMemberJson = chatroomMemberList
- return allChatroomMemberJson
-})
+ /*cw.putMovRegAddress('edi', g_attatchEBPAc)//后面要用的的ebp-2c
+ cw.putMovRegAddress('ecx', g_attatchEBP210Buffer)
+ cw.putPushReg('ecx')
+ cw.putMovRegU32('eax',0)
+ cw.putPushReg('eax')//push eax
+ cw.putMovRegReg('ecx', 'edi')
+ cw.putMovRegAddress('esi',g_attatchPathPtr)
+ cw.putCallAddress(moduleBaseAddress.add(0x138880))*/
-// 009 done
-const getChatroomMemberInfoFunction = (() => {
- const chatroomNodeAddress = getChatroomNodeAddress()
- if (chatroomNodeAddress.isNull()) {
- return '[]'
- }
- const node = chatroomNodeAddress.add(0x0).readPointer()
- const ret = chatroomRecurse(node)
+ /*cw.putSubRegImm('esp',0x14)
+ cw.putMovRegU32('ecx',g_initECXU32)
+ cw.putMovRegU32('esi',g_attatchESIU32)
+ cw.putMovRegAddress('eax', g_attatchEBPAc)
+ cw.putPushReg('eax')
+ cw.putCallAddress(moduleBaseAddress.add(0x173620))*/
+ //cw.putCallAddress(moduleBaseAddress.add(0x522590))
- const cloneRet = JSON.stringify(ret)
- chatroomNodeList.length = 0 //empty
- chatroomMemberList.length = 0 //empty
- return cloneRet
-})
+ /** g_attatchEBPAc*/
+ //cw.putMovRegNearPtr('eax', g_attatchEBPAc)
+ //cw.putMovNearPtrReg(g_attatchEBPAc.add(0xc), 'eax')
+ /** g_attatchEBPAc*/
-// 024 done
-/**
- * sendMsgNativeFunction
- * send text message
- * @param {string} talkerId = wxid or roomid
- * @param {string} content
- */
- const sendMsgNativeFunction = ((talkerId, content) => {
- const txtAsm = Memory.alloc(Process.pageSize)
- //const buffwxid = Memory.alloc(0x20)
+ //cw.putMovRegAddress('ebx', g_initEBXPtr)
+ //cw.putMovRegU32('edi', g_EDI.toInt32())
+ //cw.putMovRegU32('esi', g_EDI.toInt32())
+ /*cw.putMovRegU32('ecx', g_initECX)
+ cw.putMovRegAddress('eax', g_BufferEbp2C)
+ cw.putPushReg('eax')
+ cw.putCallAddress(moduleBaseAddress.add(0x131BB0))*/
+ cw.putPopax()
+ cw.putPopfx()
+ cw.putRet()
+ cw.flush()
- let wxidPtr = Memory.alloc(talkerId.length * 2 + 2)
- wxidPtr.writeUtf16String(talkerId)
+ })
- let picWxid = Memory.alloc(0x0c)
- picWxid.writePointer(ptr(wxidPtr)).add(0x04)
- .writeU32(talkerId.length * 2).add(0x04)
- .writeU32(talkerId.length * 2).add(0x04)
+ const nativeativeFunction = new NativeFunction(ptr(g_initTestAsm), 'void', [])
+ nativeativeFunction()
+})
- let contentPtr = Memory.alloc(content.length * 2 + 2)
- contentPtr.writeUtf16String(content)
+// 039
+let g_personal_detail_ebx = null
+let g_personal_detail_asm = null
+let g_personal_wxid = null
+let g_personal_wxid_ptr = null
+const getOldTest = ((wxid) => {//personal detail
- const sizeOfStringStruct = Process.pointerSize * 5
- let contentStruct = Memory.alloc(sizeOfStringStruct)
+ g_personal_detail_asm = Memory.alloc(Process.pageSize)
+ g_personal_detail_ebx = moduleBaseAddress.add(0x222F38C).readPointer().add(0xFB8).toInt32()
- contentStruct
- .writePointer(contentPtr).add(0x4)
- .writeU32(content.length).add(0x4)
- .writeU32(content.length * 2)
+ g_personal_wxid_ptr = Memory.alloc(wxid.length * 2 + 2)
+ g_personal_wxid_ptr.writeUtf16String(wxid)
+ g_personal_wxid = Memory.alloc(0x14)
+ g_personal_wxid.writePointer(ptr(g_personal_wxid_ptr)).add(0x04)
+ .writeU32(wxid.length * 2).add(0x04)
+ .writeU32(wxid.length * 2).add(0x08)
- const ecxBuffer = Memory.alloc(0x2d8)
+ console.log('-----------address----------', g_personal_detail_asm)
- Memory.patchCode(txtAsm, Process.pageSize, code => {
- var cw = new X86Writer(code, {
- pc: txtAsm
- })
+ Memory.patchCode(g_personal_detail_asm, Process.pageSize, code => {
+ var cw = new X86Writer(code, { pc: g_personal_detail_asm })
cw.putPushfx()
cw.putPushax()
- cw.putPushU32(0x0)
- cw.putPushU32(0x0)
- cw.putPushU32(0x0)
- cw.putPushU32(0x1)
- cw.putPushU32(0x0)
-
- //cw.putMovRegReg
+ cw.putCallAddress(moduleBaseAddress.add(0x9A000))
- cw.putMovRegAddress('eax', contentStruct)
+ //78BA9ACE | E8 2D05D6FF | call wechatwin.7890A000 |
+ cw.putMovRegU32('ebx', g_personal_detail_ebx)
+ cw.putMovRegReg('esi', 'eax')
+ cw.putPushReg('ebx')
+ cw.putSubRegImm('esp', 0x14)
+ cw.putMovRegAddress('eax', g_personal_wxid)
+ cw.putMovRegReg('ecx', 'esp')
cw.putPushReg('eax')
+ cw.putCallAddress(moduleBaseAddress.add(0x701DC0))
+ cw.putMovRegReg('ecx', 'esi')
+ cw.putCallAddress(moduleBaseAddress.add(0x4024A0))
- cw.putMovRegAddress('edx', picWxid) //room_id
-
- cw.putMovRegAddress('ecx', ecxBuffer)
- cw.putCallAddress(moduleBaseAddress.add(
- offset.sendTxtMsg.callOffset
- ))
-
- cw.putAddRegImm('esp', 0x18)
cw.putPopax()
cw.putPopfx()
cw.putRet()
@@ -1094,59 +1037,154 @@ const getChatroomMemberInfoFunction = (() => {
})
- console.log('----------txtAsm', txtAsm)
- const nativeativeFunction = new NativeFunction(ptr(txtAsm), 'void', [])
+ const nativeativeFunction = new NativeFunction(ptr(g_personal_detail_asm), 'void', [])
nativeativeFunction()
+
})
-// 023 done
+// const writeLogNativeCallback = (() => {
+// const nativeCallback = new NativeCallback(() => { }, 'void', [])
+// const nativeCallFunction = new NativeFunction(nativeCallback, 'void', [])
+
+// Interceptor.attach(
+// moduleBaseAddress.add(0x7008A4),
+// {
+// onEnter() {
+// const addr = this.context.eax//.sub(0x114)//0xc30-0x08
+// if(addr >0){
+// const log = ptr(addr).readAnsiString()
+// }
+// }
+// })
+// return nativeCallback
+// })()
+
+// 040
/**
-* send at msg
-*/
-let asmAtMsg = null
-let roomid_, msg_, wxid_, atid_
-let ecxBuffer
-const sendAtMsgNativeFunction = ((roomId, text, contactId,nickname) => {
+ * test call
+ */
+let attatchTestAsm = null
+let attatchTestEbp2C = null
+let attatchGlobalEDI = null
+let attatchGlobalEDIB88 = null
+let attatchTestEBX = null
+let g_tempEcx = null
+let attatchFirstECX = null
+//let attatchFirstECX = null
+let gattatchFilePtr = null
+let gattatchFile = null
+let gattatchReceiveIdPtr = null
+let gattatchReceiveId = null
+let attatchEAX3B0Buf = null
- asmAtMsg = Memory.alloc(Process.pageSize)
- ecxBuffer = Memory.alloc(0x3b0)
+let attatchESIbuf = null
+const getWxTest = ((contactId, filePath) => {
+ //const nativeativeFunction = new NativeFunction(ptr(addr), 'void', [])
+ //nativeativeFunction()
+ attatchTestAsm = Memory.alloc(Process.pageSize)
+ console.log('----------------address', attatchTestAsm)
+ attatchTestEbp2C = Memory.alloc(0xC)
+ attatchGlobalEDI = moduleBaseAddress.add(0x222f38c).readPointer()
+ .add(0x938).add(0x438).readPointer()
+ attatchGlobalEDIB88 = attatchGlobalEDI.add(0xB88).readPointer()
+ attatchTestEBX = Memory.alloc(0x4)
+ attatchTestEBX.writePointer(attatchGlobalEDI)
+ console.log('----------------attatchGlobalEDI', attatchGlobalEDI)
+ console.log('----------------attatchGlobalEDIB88', attatchGlobalEDIB88)
- const atContent = '@'+nickname+' '+text
+ attatchFirstECX = Memory.alloc(0x28)
+ //const attatchSecondEcx = Memory.alloc(0x14)
- roomid_ = initStruct(roomId)
- wxid_ = initidStruct(contactId)
- msg_ = initmsgStruct(atContent)
- atid_ = initAtMsgStruct(wxid_)
+ const contactIdLength = contactId.length * 2 + 2//edx
+ const contractIdActLength = contactId.length
- Memory.patchCode(asmAtMsg, Process.pageSize, code => {
- var cw = new X86Writer(code, {
- pc: asmAtMsg
- })
+
+ gattatchReceiveIdPtr = Memory.alloc(contactId.length * 2 + 2)
+ gattatchReceiveIdPtr.writeUtf16String(contactId)
+
+ gattatchReceiveId = Memory.alloc(0x14)
+ gattatchReceiveId.writePointer(ptr(gattatchReceiveIdPtr)).add(0x04)
+ .writeU32(contactId.length * 2).add(0x04)
+ .writeU32(contactId.length * 2).add(0x08)
+ //console.log('----------------attatchGlobalEDIB88',attatchGlobalEDIB88)
+ //return
+ /*console.log(hexdump(attatchTestEBX, {
+ offset: 0,
+ length: 0x40,
+ header: true,
+ ansi: true
+ }))
+ return*/
+
+ gattatchFilePtr = Memory.alloc(filePath.length * 2 + 2)
+ gattatchFilePtr.writeUtf16String(filePath)
+
+ gattatchFile = Memory.alloc(0x14)
+ gattatchFile.writePointer(ptr(gattatchFilePtr)).add(0x04)
+ .writeU32(filePath.length * 2).add(0x04)
+ .writeU32(filePath.length * 2).add(0x08)
+
+ const attatchLastECX = moduleBaseAddress.add(0x222f170).toInt32()
+
+ attatchEAX3B0Buf = Memory.alloc(0x3B0)
+
+ g_tempEcx = Memory.alloc(0x4)
+ //g_tempEcx1 = Memory.alloc(0x4)
+
+ attatchESIbuf = Memory.alloc(0x100)
+ attatchESIbuf.add(0x0).writeU32(3)
+ attatchESIbuf.add(0x4).writePointer(gattatchFilePtr)
+ attatchESIbuf.add(0x8).writeU32(filePath.length * 2)
+ attatchESIbuf.add(0xc).writeU32(filePath.length * 2)
+
+ Memory.patchCode(attatchTestAsm, Process.pageSize, code => {
+ var cw = new X86Writer(code, { pc: attatchTestAsm })
cw.putPushfx()
cw.putPushax()
+ //cw.putMovRegU32('edi',attatchGlobalEDI)
- cw.putPushU32(0x0)
- cw.putPushU32(0x0)
- cw.putPushU32(0x0)
- cw.putPushU32(0x1)
- //cw.putPushU32(0x0)
- cw.putMovRegAddress('eax', atid_)
+
+ cw.putMovRegAddress('esi', attatchESIbuf)
+
+ cw.putMovRegAddress('ecx', attatchFirstECX.add(0x14))
+ cw.putMovRegAddress('eax', gattatchFile)
cw.putPushReg('eax')
+ cw.putCallAddress(moduleBaseAddress.add(0x701DC0))
- //cw.putMovRegReg
- cw.putMovRegAddress('eax', msg_)
+ cw.putMovRegAddress('ecx', attatchFirstECX)
+ cw.putMovRegU32('eax', contactIdLength)
cw.putPushReg('eax')
+ cw.putPushU32(0)
+ cw.putCallAddress(moduleBaseAddress.add(0x1a11c83))
+ cw.putAddRegImm('esp', 0x8)
- cw.putMovRegAddress('edx', roomid_) //room_id
+ cw.putMovRegReg('edx', 'eax')
+ cw.putMovNearPtrReg(attatchFirstECX, 'edx')
+ cw.putMovRegU32('edi', contactIdLength)
+ cw.putPushReg('edi')
+ cw.putMovRegAddress('eax', gattatchReceiveIdPtr)//ebp-58
+ cw.putPushReg('eax')
+ cw.putMovRegNearPtr('eax', attatchFirstECX)
+ cw.putPushReg('eax')
+ cw.putCallAddress(moduleBaseAddress.add(0x1a1047a))
+ cw.putAddRegImm('esp', 0x0c)
- cw.putMovRegAddress('ecx', ecxBuffer)
- cw.putCallAddress(moduleBaseAddress.add(
- offset.sendTxtMsg.callOffset
- ))
+ //cw.putMovRegNearPtr('ecx',attatchFirstECX)
+ //cw.putAddRegImm('esp', 0x0c)
+ //cw.putMovRegU32('edx', 0)
+ //cw.putMovRegRegPtr('eax', 'ecx')
+ //cw.putMovNearPtrReg(attatchFirstECX.add(0x04),'edi')
+ cw.putMovRegU32('edi', contactId.length * 2)
+ cw.putMovRegU32('ecx', attatchLastECX)
+ cw.putMovRegAddress('eax', attatchEAX3B0Buf)
+ cw.putPushReg('eax')
+ cw.putCallAddress(moduleBaseAddress.add(0x392260))
+
+ cw.putMovRegAddress('ecx', attatchEAX3B0Buf)
+ cw.putCallAddress(moduleBaseAddress.add(0x94200))
- cw.putAddRegImm('esp', 0x18)
cw.putPopax()
cw.putPopfx()
cw.putRet()
@@ -1154,134 +1192,103 @@ const sendAtMsgNativeFunction = ((roomId, text, contactId,nickname) => {
})
- //console.log('----------txtAsm', asmAtMsg)
- const nativeativeFunction = new NativeFunction(ptr(asmAtMsg), 'void', [])
+ const nativeativeFunction = new NativeFunction(ptr(attatchTestAsm), 'void', [])
nativeativeFunction()
+
})
-// 022 done
-/**
- *
- * @param {*} contactId
- * @param {*} path
- */
- const sendPicMsgNativeFunction = ((contactId, path) => {
+// 001
+const getTestInfoFunction = ((addr) => {
+ const nativeativeFunction = new NativeFunction(ptr(addr), 'void', [])
+ nativeativeFunction()
- const picAsm = Memory.alloc(Process.pageSize)
- const buffwxid = Memory.alloc(0x20)
- const picbuff = Memory.alloc(0x2D8)
+ //00CFE484
- let pathPtr = Memory.alloc(path.length * 2 + 1)
- pathPtr.writeUtf16String(path)
- let imagefilepath = Memory.alloc(0x24)
- imagefilepath.writePointer(pathPtr).add(0x04)
- .writeU32(path.length * 2).add(0x04)
- .writeU32(path.length * 2).add(0x04)
+ /*MemoryAccessMonitor.enable({base:ptr(addr),size:0x01}, {
+ onAccess(details){
+ console.log('============')
+ console.log(details.operation)
+ console.log(details.from)
+ console.log(details.address)
+ console.log('============')
+ }
+ })*/
- let picWxidPtr = Memory.alloc(contactId.length * 2 + 1)
- picWxidPtr.writeUtf16String(contactId)
+})
- let picWxid = Memory.alloc(0x0c)
- picWxid.writePointer(ptr(picWxidPtr)).add(0x04)
- .writeU32(contactId.length * 2).add(0x04)
- .writeU32(contactId.length * 2).add(0x04)
+// 002
+const isLoggedInFunction = (() => {
+ loggedIn = moduleBaseAddress.add(offset.is_logged_in_offset).readU32()
+ return !!loggedIn
+})
+// 007 获得当前账号信息
+const getMyselfIdFunction = (() => {
- //const test_offset1 = 0x701DC0;
- Memory.patchCode(picAsm, Process.pageSize, code => {
- var cw = new X86Writer(code, {
- pc: picAsm
- })
- cw.putPushfx();
- cw.putPushax();
- cw.putCallAddress(moduleBaseAddress.add(
- offset.sendPicMsg.call1
- ))
- cw.putMovRegReg('edx', 'eax') //缓存
+ let wx_id = readString(moduleBaseAddress.add(offset.wxid_offset))
- cw.putSubRegImm('esp', 0x14)
- cw.putMovRegAddress('eax', buffwxid)
- cw.putMovRegReg('ecx', 'esp')
- cw.putMovRegAddress('edi', imagefilepath)
- cw.putPushReg('eax')
- cw.putCallAddress(moduleBaseAddress.add(
- offset.sendPicMsg.call2
- ))
+ return wx_id
- cw.putMovRegReg('ecx', 'edx')
- cw.putMovRegAddress('eax', picWxid) //=lea
- cw.putMovRegAddress('edi', imagefilepath)
- cw.putPushReg('edi')
- cw.putPushReg('eax')
- cw.putMovRegAddress('eax', picbuff)
- cw.putPushReg('eax')
+})
- cw.putMovRegAddress('edi', picWxid) //edi
- cw.putCallAddress(moduleBaseAddress.add(
- offset.sendPicMsg.call3
- ))
+//contact
+// 042
+const recurse = ((node) => {
+ const headerNodeAddress = getHeaderNodeAddress()
+ if (headerNodeAddress.isNull()) { return }
+ if (node.equals(headerNodeAddress)) { return }
+ for (const item in nodeList) {
+ if (node.equals(nodeList[item])) {
+ return
+ }
+ }
- cw.putPopax()
- cw.putPopfx()
- cw.putRet()
- cw.flush()
- })
+ nodeList.push(node)
+ //wxid, format relates to registration method
+ const wxid = readWideString(node.add(0x38))
- //console.log('----------picAsm',picAsm)
- const nativeativeFunction = new NativeFunction(ptr(picAsm), 'void', [])
- nativeativeFunction()
+ //custom id, if not set return null, and use wxid which should be custom id
+ const wx_code = readWideString(node.add(0x4c)) || readWideString(node.add(0x38))
-})
+ //custom Nickname
+ const name = readWideString(node.add(0x94))
-// 020 done
-let memberNickBuffAsm = null
-let nickRoomId = null
-let nickMemberId = null
-let nickBuff = null
-const getChatroomMemberNickInfoFunction = ((memberId, roomId) => {
+ //alias aka 'remark' in wechat
+ const alias = readWideString(node.add(0x80))
- nickBuff = Memory.alloc(0x7e4)
- //const nickRetAddr = Memory.alloc(0x04)
- memberNickBuffAsm = Memory.alloc(Process.pageSize)
- //console.log('asm address----------',memberNickBuffAsm)
- nickRoomId = initidStruct(roomId)
- //console.log('nick room id',nickRoomId)
- nickMemberId = initStruct(memberId)
+ //avatarUrl
+ const avatar = readWideString(node.add(0x138))
+ //const avatar = Memory.readUtf16String(node.add(0x138).readPointer())
+ //contact gender
+ const gender = node.add(0x18C).readU32()
- //console.log('nick nickMemberId id',nickMemberId)
- //const nickStructPtr = initmsgStruct('')
+ const contactJson = {
+ id: wxid,
+ code: wx_code,
+ name: name,
+ alias: alias,
+ avatarUrl: avatar,
+ gender: gender,
+ }
- Memory.patchCode(memberNickBuffAsm, Process.pageSize, code => {
- var cw = new X86Writer(code, {
- pc: memberNickBuffAsm
- })
- cw.putPushfx()
- cw.putPushax()
- cw.putMovRegAddress('edi', nickRoomId)
- cw.putMovRegAddress('eax', nickBuff)
- cw.putMovRegReg('edx', 'edi')
- cw.putPushReg('eax')
- cw.putMovRegAddress('ecx', nickMemberId)
- cw.putCallAddress(moduleBaseAddress.add(0xC06F10))
- cw.putAddRegImm('esp', 0x04)
- cw.putPopax()
- cw.putPopfx()
- cw.putRet()
- cw.flush()
+ contactList.push(contactJson)
- })
+ const leftNode = node.add(0x0).readPointer()
+ const centerNode = node.add(0x04).readPointer()
+ const rightNode = node.add(0x08).readPointer()
- const nativeativeFunction = new NativeFunction(ptr(memberNickBuffAsm), 'void', [])
- nativeativeFunction()
+ recurse(leftNode)
+ recurse(centerNode)
+ recurse(rightNode)
+
+ const allContactJson = contactList
+ return allContactJson
- const nickname = readWideString(nickBuff)
- console.log('----nickname', nickname)
- return readWideString(nickBuff)
})
// 013
@@ -1428,13 +1435,13 @@ const getQrcodeLoginData = () => {
return json
}
-
+// 045
/**
* 20220504 writelog
* 7A566D72 | FFB5 ECFEFFFF | push dword ptr ss:[ebp-114] | 【3.6.0.18】写日志,这个里面就是日志内容
7A566D78 | FFB5 E8FEFFFF | push dword ptr ss:[ebp-118] |
*/
-/*const writeLogNativeCallback = (() => {
+const writeLogNativeCallback = (() => {
const nativeCallback = new NativeCallback(() => { }, 'void', [])
const nativeCallFunction = new NativeFunction(nativeCallback, 'void', [])
@@ -1448,8 +1455,9 @@ const getQrcodeLoginData = () => {
}
})
return nativeCallback
-})()*/
+})()
+// 046
let nickRoomIdV6 = null
let nullEdiWxidStructV6 = null
let nickMemberIdStructV6 = null
@@ -1509,6 +1517,7 @@ const getChatroomMemberNickInfoV1Function = ((memberId, roomId) => {
return readWideString(nullEdiWxidStructV6)
})
+// 021
/**
* send attatch
*/
@@ -1550,8 +1559,6 @@ let attatchECX = null
param {78EDBC86 | 8B80 38040000 | mov eax,dword ptr ds:[eax+438] |
78EDBC8C | 8BB0 800B0000 | mov esi,dword ptr ds:[eax+B80] |} sendWxid
*/
-
-// 021
const sendAttatchMsgNativeFunction = ((contactId, senderId, path, filename, size) => {
attatchAsm = Memory.alloc(Process.pageSize)
@@ -1755,78 +1762,6 @@ const sendAttatchMsgNativeFunction = ((contactId, senderId, path, filename, size
//console.log('-------',attatchEbp1C.add(0x4).readPointer())
//console.log('-------',attatchEbp1C.add(0x8).readPointer())
})
-/*------------------send pic --------------------------
-let buffwxid = null
-let imagefilepath = null
-let pathPtr = null
-let picWxid = null
-let picWxidPtr = null
-let picAsm = null
-let picbuff = null
-const sendPicMsgNativeFunction = ((contactId, path) => {
-
- picAsm = Memory.alloc(Process.pageSize)
- buffwxid = Memory.alloc(0x20)
- picbuff = Memory.alloc(0x378)
-
- pathPtr = Memory.alloc(path.length * 2 + 1)
- pathPtr.writeUtf16String(path)
-
- imagefilepath = Memory.alloc(0x24)
- imagefilepath.writePointer(pathPtr).add(0x04)
- .writeU32(path.length * 2).add(0x04)
- .writeU32(path.length * 2).add(0x04)
-
- picWxidPtr = Memory.alloc(contactId.length * 2 + 1)
- picWxidPtr.writeUtf16String(contactId)
-
- picWxid = Memory.alloc(0x0c)
- picWxid.writePointer(ptr(picWxidPtr)).add(0x04)
- .writeU32(contactId.length * 2).add(0x04)
- .writeU32(contactId.length * 2).add(0x04)
-
- Memory.patchCode(picAsm, Process.pageSize, code => {
- var cw = new X86Writer(code, { pc: picAsm })
- cw.putPushfx();
- cw.putPushax();
-
- cw.putSubRegImm('esp', 0x14)
- cw.putMovRegAddress('eax', buffwxid)
-
- cw.putMovRegReg('ecx', 'esp')
-
- cw.putPushReg('eax')
- cw.putCallAddress(moduleBaseAddress.add(
- offset.send_picmsg_call_offset1
- ))
-
- cw.putMovRegAddress('ebx', imagefilepath)
- cw.putPushReg('ebx')
-
- cw.putMovRegAddress('eax', picWxid)
- cw.putPushReg('eax')
-
- cw.putMovRegAddress('eax', picbuff)
- cw.putPushReg('eax')
- cw.putCallAddress(moduleBaseAddress.add(
- offset.send_picmsg_call_offset2
- ))
-
- cw.putMovRegReg('ecx', 'eax')
- cw.putCallAddress(moduleBaseAddress.add(
- offset.send_picmsg_call_offset3
- ))
- cw.putPopax()
- cw.putPopfx()
- cw.putRet()
- cw.flush()
-
- })
-
- const nativeativeFunction = new NativeFunction(ptr(picAsm), 'void', [])
- nativeativeFunction()
-
-})*/
// 025
const callLoginQrcodeFunction = ((forceRefresh = false) => {
From 3faaa0b48b502a1941c32d350e57b6a78f5e82e1 Mon Sep 17 00:00:00 2001
From: choogoo <104893934+choogoo@users.noreply.github.com>
Date: Thu, 21 Sep 2023 14:54:14 +0800
Subject: [PATCH 3/6] =?UTF-8?q?=E9=80=82=E9=85=8D3.9.2.23=20(#185)?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
* 3.9.2.23 initt
* Update init-agent-script.js
* 3.9.2.23 adapter
* 适配3.9.2.23
* Delete agent-script-3.9.2.23-new.js
* 适配3.9.2.23
---------
Co-authored-by: LuChao
---
package.json | 2 +-
src/init-agent-script.js | 1174 ++------------------------------------
src/puppet-xp.ts | 14 +-
src/wechat-sidecar.ts | 66 ++-
4 files changed, 84 insertions(+), 1172 deletions(-)
diff --git a/package.json b/package.json
index 8e9f1dd..ffe22cc 100644
--- a/package.json
+++ b/package.json
@@ -1,6 +1,6 @@
{
"name": "wechaty-puppet-xp",
- "version": "1.12.7",
+ "version": "1.13.0",
"description": "Puppet XP for Wechaty",
"type": "module",
"exports": {
diff --git a/src/init-agent-script.js b/src/init-agent-script.js
index 9c97f9a..802ce45 100644
--- a/src/init-agent-script.js
+++ b/src/init-agent-script.js
@@ -1,16 +1,20 @@
/**
+ * WeChat 3.2.1.121
* > Special thanks to: @cixingguangming55555 老张学技术
*
* Credit: https://github.com/cixingguangming55555/wechat-bot
+ * Source: https://pan.baidu.com/s/1OmX2lxNOYHyGsl_3ByhsoA
+ * 《源码3.2.1.121》提取码: 1rfa
+ * WeChat: https://pan.baidu.com/share/init?surl=IHRM2OMvrLyuCz5MRbigGg
+ * 微信:3.2.1.121 提取码: cscn
*/
//https://blog.csdn.net/iloveitvm/article/details/109119687 frida学习
//const { isNullishCoalesce } = require("typescript")
-// wechat:3.9.2.23
+//3.9.2.23
-// 028 done
const offset = {
@@ -45,19 +49,18 @@ const offset = {
}
};
-// 029 done
+
+
/*------------------global-------------------------------------------*/
const availableVersion = 1661534743 ////3.9.2.23 ==0x63090217
const moduleBaseAddress = Module.getBaseAddress('WeChatWin.dll')
const moduleLoad = Module.load('WeChatWin.dll')
-// tbd
-const g_EDIPtr = moduleBaseAddress.add(0x222f38c).readPointer().add(0xD70).readPointer()//
-const g_EDIU32 = moduleBaseAddress.add(0x222f38c).readPointer().add(0xD70).readU32()
-/*------------------global-------------------------------------------*/
+//1575CF98
+
/*---------------base -------------------------*/
-// 030 done
+
let retidPtr=null
let retidStruct=null
const initidStruct = ((str) => {
@@ -77,7 +80,6 @@ const initidStruct = ((str) => {
return retidStruct
})
-// 031 done
let retPtr = null
let retStruct = null
const initStruct = ((str) => {
@@ -97,7 +99,6 @@ const initStruct = ((str) => {
return retStruct
})
-// 032 done
let msgstrPtr=null
let msgStruct=null
const initmsgStruct = ((str) => {
@@ -116,10 +117,6 @@ const initmsgStruct = ((str) => {
return msgStruct
})
-// 034 done
-/**
-* at msg structure
-*/
let atStruct = null
const initAtMsgStruct = ((wxidStruct) => {
@@ -131,28 +128,6 @@ const initAtMsgStruct = ((wxidStruct) => {
.writeU32(0)
return atStruct
})
-
-// 033 tbd
-let retidNullStruct = null
-let retidNullPtr = null
-const initNullIdStruct = ((str) => {
-
- retidNullPtr = Memory.alloc(str.length * 2 + 1)
- retidNullPtr.writeUtf16String(str)
-
- retidNullStruct = Memory.alloc(0x14) // returns a NativePointer
-
- retidNullStruct
- .writePointer(retidNullPtr).add(0x04)
- .writeU32(str.length * 2).add(0x04)
- .writeU32(str.length * 2).add(0x04)
- .writeU32(0).add(0x04)
- .writeU32(0)
-
- return retidNullStruct
-})
-
-// 035 done
const readStringPtr = (address) => {
const addr = ptr(address)
const size = addr.add(16).readU32()
@@ -183,18 +158,6 @@ const readStringPtr = (address) => {
return addr
}
-// 036 done
-const readString = (address) => {
- return readStringPtr(address).readUtf8String()
-}
-
-// 037 done
-const readWideString = (address) => {
- return readWStringPtr(address).readUtf16String()
-}
-/*-----------------base-------------------------*/
-
-// 041
// std::wstring
// const wstr = readWStringPtr(ptr).readUtf16String()
const readWStringPtr = (address) => {
@@ -216,9 +179,17 @@ const readWStringPtr = (address) => {
return addr
}
+const readString = (address) => {
+ return readStringPtr(address).readUtf8String()
+}
+
+const readWideString = (address) => {
+ return readWStringPtr(address).readUtf16String()
+}
+
+
/*-----------------base-------------------------*/
-// 010 done
let currentVersion = 0
let nodeList = [] //for contact
@@ -229,6 +200,7 @@ let chatroomMemberList = [] //for chatroom
let loggedIn = false
+
const getWechatVersionFunction = (() => {
if (currentVersion) {
return currentVersion
@@ -245,7 +217,7 @@ const getWechatVersionFunction = (() => {
return ver
})
-// 011 done
+// 011
const getWechatVersionStringFunction = ((ver = getWechatVersionFunction()) => {
if (!ver) {
return '0.0.0.0'
@@ -258,17 +230,13 @@ const getWechatVersionStringFunction = ((ver = getWechatVersionFunction()) => {
return vers.join('.')
})
-// 012 done
const checkSupportedFunction = (() => {
const ver = getWechatVersionFunction()
return ver == availableVersion
})
-// 019 done
-/**
- * @Hook: recvMsg -> recvMsgNativeCallback
- */
- const recvMsgNativeCallback = (() => {
+// 019
+const recvMsgNativeCallback = (() => {
const nativeCallback = new NativeCallback(() => {}, 'void', ['int32', 'pointer', 'pointer', 'pointer', 'pointer', 'int32'])
@@ -356,12 +324,12 @@ const checkSupportedFunction = (() => {
return nativeCallback
})()
-// 003 done
+
const getBaseNodeAddress = (() => {
return moduleBaseAddress.add(offset.contactInfo.nodeOffset).readPointer()
})
-// 004 done
+// 004
const getHeaderNodeAddress = (() => {
const baseAddress = getBaseNodeAddress()
//console.log('baseAddress',baseAddress)
@@ -373,7 +341,6 @@ const getHeaderNodeAddress = (() => {
return baseAddress.add(offset.contactInfo.nodeRootOffset).readPointer()
})
-// 006 done
const getMyselfInfoFunction = (() => {
let ptr = 0
@@ -411,7 +378,7 @@ const getMyselfInfoFunction = (() => {
})
-// 043 done
+
const recurseNew = ((node) => {
const headerNodeAddress = getHeaderNodeAddress()
if (headerNodeAddress.isNull()) {
@@ -477,7 +444,7 @@ const recurseNew = ((node) => {
})
-// 044 done
+
const getContactNativeFunction = (() => {
const headerNodeAddress = getHeaderNodeAddress()
//console.log('headerNodeAddress',headerNodeAddress)
@@ -503,7 +470,7 @@ const getContactNativeFunction = (() => {
return cloneRet
})
-// 0xx done
+
const getChatroomNodeAddress = (() => {
const baseAddress = moduleBaseAddress.add(offset.chatroomInfo.nodeOffset).readPointer()
if (baseAddress.isNull()) {
@@ -512,7 +479,6 @@ const getChatroomNodeAddress = (() => {
return baseAddress.add(offset.chatroomInfo.nodeRootOffset).readPointer()
})
-// 008chatroom member done
const chatroomRecurse = ((node) => {
const chatroomNodeAddress = getChatroomNodeAddress()
if (chatroomNodeAddress.isNull()) {
@@ -560,7 +526,6 @@ const chatroomRecurse = ((node) => {
return allChatroomMemberJson
})
-// 009 done
const getChatroomMemberInfoFunction = (() => {
const chatroomNodeAddress = getChatroomNodeAddress()
if (chatroomNodeAddress.isNull()) {
@@ -576,14 +541,15 @@ const getChatroomMemberInfoFunction = (() => {
return cloneRet
})
-// 024 done
+
+
/**
* sendMsgNativeFunction
* send text message
* @param {string} talkerId = wxid or roomid
* @param {string} content
*/
- const sendMsgNativeFunction = ((talkerId, content) => {
+const sendMsgNativeFunction = ((talkerId, content) => {
const txtAsm = Memory.alloc(Process.pageSize)
//const buffwxid = Memory.alloc(0x20)
@@ -650,10 +616,7 @@ const getChatroomMemberInfoFunction = (() => {
})
-// 023 done
-/**
-* send at msg
-*/
+
let asmAtMsg = null
let roomid_, msg_, wxid_, atid_
let ecxBuffer
@@ -710,13 +673,12 @@ const sendAtMsgNativeFunction = ((roomId, text, contactId,nickname) => {
})
-// 022 done
/**
*
* @param {*} contactId
* @param {*} path
*/
- const sendPicMsgNativeFunction = ((contactId, path) => {
+const sendPicMsgNativeFunction = ((contactId, path) => {
const picAsm = Memory.alloc(Process.pageSize)
const buffwxid = Memory.alloc(0x20)
@@ -788,7 +750,9 @@ const sendAtMsgNativeFunction = ((roomId, text, contactId,nickname) => {
})
-// 020 done
+
+
+
let memberNickBuffAsm = null
let nickRoomId = null
let nickMemberId = null
@@ -834,1066 +798,8 @@ const getChatroomMemberNickInfoFunction = ((memberId, roomId) => {
return readWideString(nickBuff)
})
-/* 由此之后是3.9.2.23中缺失的未实现方法 */
-
-// 038 初始化全局变量 tbd
-let g_initTestAsm = null
-let g_BufferEbp2C = null
-let g_initECXU32 = null
-let g_initECXPtr = null
-let g_initEBXPtr = null
-let g_initEBX = null
-
-let g_attatchEBP210Buffer = null
-let g_attatchPathPtr = null
-let g_attatchPath = null
-let g_attatchEBPAc = null
-let g_attatchEBPAcBufPtr = null
-
-let g_attatchContactIdPtr = null
-//let g_attatchECXBuffer = null
-let g_attatchESIU32 = null
-
-let g_initECXTempPtr = null
-const initGlobal = ((contactId, attatchFile) => {
-
- //const base = moduleBaseAddress.add(0x222f38c).readPointer()
- //g_EDI = base.add(0xD70).readPointer()//0x438+0x938
- console.log('------------g_attatchEBPAc', g_attatchEBPAc)
- console.log('------------g_EDIU32', g_EDIU32)
- g_initTestAsm = Memory.alloc(Process.pageSize)
- console.log('------------address', g_initTestAsm)
-
- g_initECXPtr = g_EDIPtr.add(0xB80).readPointer().add(0x1640)
- g_initECXTempPtr = g_EDIPtr.add(0xB88).readPointer()
- g_initECXU32 = g_initECXPtr.toInt32()
- g_attatchESIU32 = g_EDIU32
-
- console.log('------------g_initECXU32', g_initECXU32)
- console.log('------------g_initESIU32', g_attatchESIU32)
-
-
- //console.log('==========g_initECXPtr',g_initECXPtr)
- //console.log('==========g_EDIU32',g_EDIU32)
-
- //g_attatchECXBuffer = Memory.alloc(0x1024)
- //Memory.copy(g_attatchECXBuffer, g_initECXPtr, 0x1024)
-
- g_BufferEbp2C = Memory.alloc(0x48)
-
- //g_initEBX = moduleBaseAddress.add(0x2251724).readPointer().readPointer()
- //g_initEBXPtr = Memory.alloc(0x14).writePointer(g_initEBX)
- //g_initEBXPtr.add(0x08).writePointer(g_BufferEbp2C)
-
- g_attatchPathPtr = Memory.alloc(attatchFile.length * 2 + 2)
- g_attatchPathPtr.writeUtf16String(attatchFile)
-
- g_attatchPath = Memory.alloc(0x28)
- g_attatchPath.writePointer(g_attatchPathPtr).add(0x04)
- .writeU32(attatchFile.length * 2).add(0x04)
- .writeU32(attatchFile.length * 2).add(0x04)
- /*---------------------------------ebp-210----------------*/
- g_attatchEBP210Buffer = Memory.alloc(0x48)
- g_attatchEBP210Buffer.writeU32(0x3)
- g_attatchEBP210Buffer.add(0x4).writePointer(g_attatchPathPtr)
- g_attatchEBP210Buffer.add(0x8).writeU32(attatchFile.length * 2)
- g_attatchEBP210Buffer.add(0xC).writeU32(attatchFile.length * 2)
- g_attatchEBP210Buffer.add(0x2C).writeU32(moduleBaseAddress.add(0x2ECE87).toInt32())
- //console.log('------------g_attatchEBP210Buffer',g_attatchEBP210Buffer)
- /*---------------------------------ebp-210----------------*/
-
- //g_attatchContactIdPtr = Memory.alloc(0x4)
- //g_attatchContactIdPtr.writeUtf16String(contactId)
- //console.log('------------g_attatchEBP210Buffer',g_attatchEBP210Buffer)
- g_attatchEBPAc = Memory.alloc(0x140)
- //g_attatchEBPAcBufPtr = Memory.alloc(0x100)
- //g_attatchEBPAc.writePointer(g_attatchEBP210Buffer)
- //g_attatchEBPAc.add(0x4).writePointer(g_attatchEBPAcBufPtr)
- //g_attatchEBPAc.add(0x8).writePointer(g_attatchEBPAcBufPtr)
- g_attatchEBPAc.add(0x10).writeU32(g_EDIU32)
- console.log('------------g_attatchEBPAc', g_attatchEBPAc)
-
- /*g_attatchECXBuffer.add(0x18).writePointer(g_attatchContactIdPtr)
- g_attatchECXBuffer.add(0x1C).writeU32(contactId.length*2)
- .add(0x04).writeU32(contactId.length*2)*/
-
-
-
- //g_attatchESIU32 = g_EDI.toInt32()
-
-
- //console.log('------------g_attatchESIU32',g_attatchESIU32)
- //console.log('==========g_attatchECXBuffer',g_attatchECXBuffer)
-
- Memory.patchCode(g_initTestAsm, Process.pageSize, code => {
- var cw = new X86Writer(code, { pc: g_initTestAsm })
- cw.putPushfx()
- cw.putPushax()
- //cw.putMovRegAddress('eax', g_attatchEBP210Buffer)
-
- /*cw.putMovRegAddress('edi',g_EDIPtr)
- cw.putMovRegReg('esi','edi')
- cw.putMovRegAddress('eax',g_BufferEbp2C)
- cw.putMovRegAddress('ecx',g_initECXTempPtr)
- cw.putPushReg('eax')
- cw.putCallAddress(moduleBaseAddress.add(0x131bb0))*/
-
- //cw.putMovRegOffsetPtrU32('ebp', -20, 0)
-
- /*cw.putPushU32(0)
- cw.putMovRegAddress('eax', g_attatchPathPtr)
- cw.putPushReg('eax')
- cw.putPushU32(3)
- cw.putMovRegAddress('ecx', g_attatchEBP210Buffer)
- cw.putCallAddress(moduleBaseAddress.add(0x130220))*/
-
-
- /*cw.putMovRegAddress('edi', g_attatchEBPAc)//后面要用的的ebp-2c
- cw.putMovRegAddress('ecx', g_attatchEBP210Buffer)
- cw.putPushReg('ecx')
- cw.putMovRegU32('eax',0)
- cw.putPushReg('eax')//push eax
- cw.putMovRegReg('ecx', 'edi')
- cw.putMovRegAddress('esi',g_attatchPathPtr)
- cw.putCallAddress(moduleBaseAddress.add(0x138880))*/
-
-
- /*cw.putSubRegImm('esp',0x14)
- cw.putMovRegU32('ecx',g_initECXU32)
- cw.putMovRegU32('esi',g_attatchESIU32)
- cw.putMovRegAddress('eax', g_attatchEBPAc)
- cw.putPushReg('eax')
- cw.putCallAddress(moduleBaseAddress.add(0x173620))*/
- //cw.putCallAddress(moduleBaseAddress.add(0x522590))
-
- /** g_attatchEBPAc*/
- //cw.putMovRegNearPtr('eax', g_attatchEBPAc)
- //cw.putMovNearPtrReg(g_attatchEBPAc.add(0xc), 'eax')
- /** g_attatchEBPAc*/
-
-
- //cw.putMovRegAddress('ebx', g_initEBXPtr)
- //cw.putMovRegU32('edi', g_EDI.toInt32())
- //cw.putMovRegU32('esi', g_EDI.toInt32())
- /*cw.putMovRegU32('ecx', g_initECX)
- cw.putMovRegAddress('eax', g_BufferEbp2C)
- cw.putPushReg('eax')
- cw.putCallAddress(moduleBaseAddress.add(0x131BB0))*/
-
- cw.putPopax()
- cw.putPopfx()
- cw.putRet()
- cw.flush()
-
- })
-
- const nativeativeFunction = new NativeFunction(ptr(g_initTestAsm), 'void', [])
- nativeativeFunction()
-})
-
-// 039
-let g_personal_detail_ebx = null
-let g_personal_detail_asm = null
-let g_personal_wxid = null
-let g_personal_wxid_ptr = null
-const getOldTest = ((wxid) => {//personal detail
-
- g_personal_detail_asm = Memory.alloc(Process.pageSize)
- g_personal_detail_ebx = moduleBaseAddress.add(0x222F38C).readPointer().add(0xFB8).toInt32()
-
- g_personal_wxid_ptr = Memory.alloc(wxid.length * 2 + 2)
- g_personal_wxid_ptr.writeUtf16String(wxid)
-
- g_personal_wxid = Memory.alloc(0x14)
- g_personal_wxid.writePointer(ptr(g_personal_wxid_ptr)).add(0x04)
- .writeU32(wxid.length * 2).add(0x04)
- .writeU32(wxid.length * 2).add(0x08)
-
- console.log('-----------address----------', g_personal_detail_asm)
-
- Memory.patchCode(g_personal_detail_asm, Process.pageSize, code => {
- var cw = new X86Writer(code, { pc: g_personal_detail_asm })
- cw.putPushfx()
- cw.putPushax()
-
- cw.putCallAddress(moduleBaseAddress.add(0x9A000))
-
- //78BA9ACE | E8 2D05D6FF | call wechatwin.7890A000 |
- cw.putMovRegU32('ebx', g_personal_detail_ebx)
- cw.putMovRegReg('esi', 'eax')
- cw.putPushReg('ebx')
- cw.putSubRegImm('esp', 0x14)
- cw.putMovRegAddress('eax', g_personal_wxid)
- cw.putMovRegReg('ecx', 'esp')
- cw.putPushReg('eax')
- cw.putCallAddress(moduleBaseAddress.add(0x701DC0))
- cw.putMovRegReg('ecx', 'esi')
- cw.putCallAddress(moduleBaseAddress.add(0x4024A0))
-
- cw.putPopax()
- cw.putPopfx()
- cw.putRet()
- cw.flush()
-
- })
-
- const nativeativeFunction = new NativeFunction(ptr(g_personal_detail_asm), 'void', [])
- nativeativeFunction()
-
-
-})
-
-// const writeLogNativeCallback = (() => {
-// const nativeCallback = new NativeCallback(() => { }, 'void', [])
-// const nativeCallFunction = new NativeFunction(nativeCallback, 'void', [])
-
-// Interceptor.attach(
-// moduleBaseAddress.add(0x7008A4),
-// {
-// onEnter() {
-// const addr = this.context.eax//.sub(0x114)//0xc30-0x08
-// if(addr >0){
-// const log = ptr(addr).readAnsiString()
-// }
-// }
-// })
-// return nativeCallback
-// })()
-
-// 040
-/**
- * test call
- */
-let attatchTestAsm = null
-let attatchTestEbp2C = null
-let attatchGlobalEDI = null
-let attatchGlobalEDIB88 = null
-let attatchTestEBX = null
-let g_tempEcx = null
-let attatchFirstECX = null
-//let attatchFirstECX = null
-let gattatchFilePtr = null
-let gattatchFile = null
-let gattatchReceiveIdPtr = null
-let gattatchReceiveId = null
-let attatchEAX3B0Buf = null
-
-let attatchESIbuf = null
-const getWxTest = ((contactId, filePath) => {
- //const nativeativeFunction = new NativeFunction(ptr(addr), 'void', [])
- //nativeativeFunction()
- attatchTestAsm = Memory.alloc(Process.pageSize)
- console.log('----------------address', attatchTestAsm)
- attatchTestEbp2C = Memory.alloc(0xC)
- attatchGlobalEDI = moduleBaseAddress.add(0x222f38c).readPointer()
- .add(0x938).add(0x438).readPointer()
- attatchGlobalEDIB88 = attatchGlobalEDI.add(0xB88).readPointer()
- attatchTestEBX = Memory.alloc(0x4)
- attatchTestEBX.writePointer(attatchGlobalEDI)
- console.log('----------------attatchGlobalEDI', attatchGlobalEDI)
- console.log('----------------attatchGlobalEDIB88', attatchGlobalEDIB88)
-
- attatchFirstECX = Memory.alloc(0x28)
- //const attatchSecondEcx = Memory.alloc(0x14)
-
- const contactIdLength = contactId.length * 2 + 2//edx
- const contractIdActLength = contactId.length
-
-
- gattatchReceiveIdPtr = Memory.alloc(contactId.length * 2 + 2)
- gattatchReceiveIdPtr.writeUtf16String(contactId)
-
- gattatchReceiveId = Memory.alloc(0x14)
- gattatchReceiveId.writePointer(ptr(gattatchReceiveIdPtr)).add(0x04)
- .writeU32(contactId.length * 2).add(0x04)
- .writeU32(contactId.length * 2).add(0x08)
- //console.log('----------------attatchGlobalEDIB88',attatchGlobalEDIB88)
- //return
- /*console.log(hexdump(attatchTestEBX, {
- offset: 0,
- length: 0x40,
- header: true,
- ansi: true
- }))
- return*/
-
- gattatchFilePtr = Memory.alloc(filePath.length * 2 + 2)
- gattatchFilePtr.writeUtf16String(filePath)
-
- gattatchFile = Memory.alloc(0x14)
- gattatchFile.writePointer(ptr(gattatchFilePtr)).add(0x04)
- .writeU32(filePath.length * 2).add(0x04)
- .writeU32(filePath.length * 2).add(0x08)
-
- const attatchLastECX = moduleBaseAddress.add(0x222f170).toInt32()
-
- attatchEAX3B0Buf = Memory.alloc(0x3B0)
-
- g_tempEcx = Memory.alloc(0x4)
- //g_tempEcx1 = Memory.alloc(0x4)
-
- attatchESIbuf = Memory.alloc(0x100)
- attatchESIbuf.add(0x0).writeU32(3)
- attatchESIbuf.add(0x4).writePointer(gattatchFilePtr)
- attatchESIbuf.add(0x8).writeU32(filePath.length * 2)
- attatchESIbuf.add(0xc).writeU32(filePath.length * 2)
-
- Memory.patchCode(attatchTestAsm, Process.pageSize, code => {
- var cw = new X86Writer(code, { pc: attatchTestAsm })
- cw.putPushfx()
- cw.putPushax()
- //cw.putMovRegU32('edi',attatchGlobalEDI)
-
-
- cw.putMovRegAddress('esi', attatchESIbuf)
-
- cw.putMovRegAddress('ecx', attatchFirstECX.add(0x14))
- cw.putMovRegAddress('eax', gattatchFile)
- cw.putPushReg('eax')
- cw.putCallAddress(moduleBaseAddress.add(0x701DC0))
-
-
- cw.putMovRegAddress('ecx', attatchFirstECX)
- cw.putMovRegU32('eax', contactIdLength)
- cw.putPushReg('eax')
- cw.putPushU32(0)
- cw.putCallAddress(moduleBaseAddress.add(0x1a11c83))
- cw.putAddRegImm('esp', 0x8)
-
- cw.putMovRegReg('edx', 'eax')
- cw.putMovNearPtrReg(attatchFirstECX, 'edx')
- cw.putMovRegU32('edi', contactIdLength)
- cw.putPushReg('edi')
- cw.putMovRegAddress('eax', gattatchReceiveIdPtr)//ebp-58
- cw.putPushReg('eax')
- cw.putMovRegNearPtr('eax', attatchFirstECX)
- cw.putPushReg('eax')
- cw.putCallAddress(moduleBaseAddress.add(0x1a1047a))
- cw.putAddRegImm('esp', 0x0c)
-
- //cw.putMovRegNearPtr('ecx',attatchFirstECX)
- //cw.putAddRegImm('esp', 0x0c)
- //cw.putMovRegU32('edx', 0)
- //cw.putMovRegRegPtr('eax', 'ecx')
- //cw.putMovNearPtrReg(attatchFirstECX.add(0x04),'edi')
- cw.putMovRegU32('edi', contactId.length * 2)
- cw.putMovRegU32('ecx', attatchLastECX)
- cw.putMovRegAddress('eax', attatchEAX3B0Buf)
- cw.putPushReg('eax')
- cw.putCallAddress(moduleBaseAddress.add(0x392260))
-
- cw.putMovRegAddress('ecx', attatchEAX3B0Buf)
- cw.putCallAddress(moduleBaseAddress.add(0x94200))
-
- cw.putPopax()
- cw.putPopfx()
- cw.putRet()
- cw.flush()
-
- })
-
- const nativeativeFunction = new NativeFunction(ptr(attatchTestAsm), 'void', [])
- nativeativeFunction()
-
-
-})
-
-// 001
-const getTestInfoFunction = ((addr) => {
- const nativeativeFunction = new NativeFunction(ptr(addr), 'void', [])
- nativeativeFunction()
-
- //00CFE484
-
-
- /*MemoryAccessMonitor.enable({base:ptr(addr),size:0x01}, {
- onAccess(details){
- console.log('============')
- console.log(details.operation)
- console.log(details.from)
- console.log(details.address)
- console.log('============')
- }
- })*/
-
-})
-
-// 002
const isLoggedInFunction = (() => {
- loggedIn = moduleBaseAddress.add(offset.is_logged_in_offset).readU32()
- return !!loggedIn
-})
-
-// 007 获得当前账号信息
-const getMyselfIdFunction = (() => {
-
- let wx_id = readString(moduleBaseAddress.add(offset.wxid_offset))
-
- return wx_id
-
-})
-
-//contact
-// 042
-const recurse = ((node) => {
- const headerNodeAddress = getHeaderNodeAddress()
- if (headerNodeAddress.isNull()) { return }
-
- if (node.equals(headerNodeAddress)) { return }
-
- for (const item in nodeList) {
- if (node.equals(nodeList[item])) {
- return
- }
- }
-
-
- nodeList.push(node)
- //wxid, format relates to registration method
- const wxid = readWideString(node.add(0x38))
-
- //custom id, if not set return null, and use wxid which should be custom id
- const wx_code = readWideString(node.add(0x4c)) || readWideString(node.add(0x38))
-
- //custom Nickname
- const name = readWideString(node.add(0x94))
-
- //alias aka 'remark' in wechat
- const alias = readWideString(node.add(0x80))
-
- //avatarUrl
- const avatar = readWideString(node.add(0x138))
- //const avatar = Memory.readUtf16String(node.add(0x138).readPointer())
- //contact gender
- const gender = node.add(0x18C).readU32()
-
- const contactJson = {
- id: wxid,
- code: wx_code,
- name: name,
- alias: alias,
- avatarUrl: avatar,
- gender: gender,
- }
-
- contactList.push(contactJson)
-
- const leftNode = node.add(0x0).readPointer()
- const centerNode = node.add(0x04).readPointer()
- const rightNode = node.add(0x08).readPointer()
-
- recurse(leftNode)
- recurse(centerNode)
- recurse(rightNode)
-
- const allContactJson = contactList
- return allContactJson
-
-})
-
-// 013
-const isSupported = checkSupportedFunction()
-
-if (!isSupported) {
- throw new Error(`Wechat version not supported. \nWechat version: ${getWechatVersionStringFunction()}, supported version: ${getWechatVersionStringFunction(availableVersion)}`)
-}
-
-// 015
-const hookLogoutEventCallback = (() => {
- const nativeCallback = new NativeCallback(() => { }, 'void', ['int32'])
- const nativeativeFunction = new NativeFunction(nativeCallback, 'void', ['int32'])
- Interceptor.attach(moduleBaseAddress.add(offset.hook_on_logout_offset), {
- onEnter: function (args) {
- const bySrv = args[0].toInt32()
- setImmediate(() => nativeativeFunction(bySrv))
- }
- })
- return nativeCallback
-})()
-
-// 016
-const hookLoginEventCallback = (() => {
- const nativeCallback = new NativeCallback(() => { }, 'void', [])
- const nativeativeFunction = new NativeFunction(nativeCallback, 'void', [])
- Interceptor.attach(moduleBaseAddress.add(offset.hook_on_login_offset), {
- onLeave: function (retval) {
- isLoggedInFunction()
- setImmediate(() => nativeativeFunction())
- return retval
- }
- })
-
- setTimeout(() => {
- if (isLoggedInFunction()) {
- setImmediate(() => nativeativeFunction())
- }
- }, 500);
-
- return nativeCallback
-})()
-
-// 017
-const checkQRLoginNativeCallback = (() => {
-
- const nativeCallback = new NativeCallback(() => { }, 'void', ['int32', 'pointer', 'pointer', 'pointer', 'pointer', 'pointer', 'int32', 'pointer'])
- const nativeativeFunction = new NativeFunction(nativeCallback, 'void', ['int32', 'pointer', 'pointer', 'pointer', 'pointer', 'pointer', 'int32', 'pointer'])
- // const json = {
- // status,
- // uuid,
- // wxid,
- // avatarUrl,
- // nickname,
- // phoneType,
- // phoneClientVer,
- // pairWaitTip,
- // }
-
- const callback = {
- onLeave: function (retval) {
- const json = getQrcodeLoginData()
- if (json.status == 0) {
- // 当状态为 0 时,即未扫码。而其他状态会触发另一个方法,拥有更多数据。
- ret(json)
- }
- return retval
- },
- }
-
- const ret = (json) => {
- const arr = [
- json.status || 0,
- Memory.allocUtf8String(json.uuid ? `http://weixin.qq.com/x/${json.uuid}` : ''),
- Memory.allocUtf8String(json.wxid || ''),
- Memory.allocUtf8String(json.avatarUrl || ''),
- Memory.allocUtf8String(json.nickname || ''),
- Memory.allocUtf8String(json.phoneType || ''),
- json.phoneClientVer || 0,
- Memory.allocUtf8String(json.pairWaitTip || ''),
- ]
- setImmediate(() => nativeativeFunction(...arr))
- }
-
- Interceptor.attach(moduleBaseAddress.add(offset.hook_get_login_qr_offset), callback)
- Interceptor.attach(moduleBaseAddress.add(offset.hook_check_login_qr_offset), callback)
- Interceptor.attach(moduleBaseAddress.add(offset.hook_save_login_qr_info_offset), {
- onEnter: function () {
- const qrNotify = this.context['ebp'].sub(72)
- const uuid = readString(qrNotify.add(4).readPointer())
- const wxid = readString(qrNotify.add(8).readPointer())
- const status = qrNotify.add(16).readUInt()
- const avatarUrl = readString(qrNotify.add(24).readPointer())
- const nickname = readString(qrNotify.add(28).readPointer())
- const pairWaitTip = readString(qrNotify.add(32).readPointer())
- const phoneClientVer = qrNotify.add(40).readUInt()
- const phoneType = readString(qrNotify.add(44).readPointer())
-
- const json = {
- status,
- uuid,
- wxid,
- avatarUrl,
- nickname,
- phoneType,
- phoneClientVer,
- pairWaitTip,
- }
- ret(json)
- },
- onLeave: function (retval) {
- return retval
- },
- })
-
- if (!isLoggedInFunction()) {
- setTimeout(() => {
- const json = getQrcodeLoginData()
- ret(json)
- }, 100);
- }
-
- return nativeCallback
-})()
-
-// 018
-const getQrcodeLoginData = () => {
- const getQRCodeLoginMgr = new NativeFunction(moduleBaseAddress.add(offset.get_qr_login_data_offset), 'pointer', [])
- const qlMgr = getQRCodeLoginMgr()
-
- const json = {
- status: 0,
- uuid: '',
- wxid: '',
- avatarUrl: '',
- }
-
- if (!qlMgr.isNull()) {
- json.uuid = readString(qlMgr.add(8))
- json.status = qlMgr.add(40).readUInt()
- json.wxid = readString(qlMgr.add(44))
- json.avatarUrl = readString(qlMgr.add(92))
- }
- return json
-}
-
-// 045
-/**
- * 20220504 writelog
- * 7A566D72 | FFB5 ECFEFFFF | push dword ptr ss:[ebp-114] | 【3.6.0.18】写日志,这个里面就是日志内容
- 7A566D78 | FFB5 E8FEFFFF | push dword ptr ss:[ebp-118] |
- */
-const writeLogNativeCallback = (() => {
- const nativeCallback = new NativeCallback(() => { }, 'void', [])
- const nativeCallFunction = new NativeFunction(nativeCallback, 'void', [])
-
- Interceptor.attach(
- moduleBaseAddress.add(0x1576D7E),
- {
- onEnter() {
- const addr = this.context.ebp.sub(0x114)//0xc30-0x08
- console.log('-------',addr)
-
- }
- })
- return nativeCallback
-})()
-
-// 046
-let nickRoomIdV6 = null
-let nullEdiWxidStructV6 = null
-let nickMemberIdStructV6 = null
-let memberNickBuffAsmV6 = null
-let nickResultEdiV6 = null
-
-const getChatroomMemberNickInfoV1Function = ((memberId, roomId) => {
- nickRoomIdV6 = initidStruct(roomId)
- nullEdiWxidStructV6 = initNullIdStruct('')
- nickMemberIdStructV6 = initStruct(memberId)
- memberNickBuffAsmV6 = Memory.alloc(Process.pageSize)
- console.log('-----', memberNickBuffAsmV6)
-
- const tmp = (moduleBaseAddress.add(
- offset.chatroom_member_nick_esi_offset_v6
- )).readU32()
- console.log('=======tmp', tmp)
- Memory.patchCode(memberNickBuffAsmV6, Process.pageSize, code => {
- var cw = new X86Writer(code, { pc: memberNickBuffAsmV6 })
- cw.putPushfx();
- cw.putPushax();
-
- cw.putMovRegAddress('edi', nullEdiWxidStructV6)
- cw.putMovRegAddress('eax', nickMemberIdStructV6)
- cw.putMovRegAddress('ebx', nickRoomIdV6)
-
-
- cw.putMovRegAddress('esi', ptr(tmp))
- cw.putPushReg('edi')
- cw.putPushReg('eax')
- cw.putPushReg('ebx')
-
- cw.putMovRegAddress('ecx', ptr(tmp))
-
- cw.putCallAddress(moduleBaseAddress.add(
- offset.chatroom_member_nick_call_offset_v6
- ))
-
-
- //cw.putMovNearPtrReg(nickResultEdiV6, 'edi')
- cw.putPopax()
- cw.putPopfx()
- cw.putRet()
- cw.flush()
-
- })
-
- const nativeativeFunction = new NativeFunction(ptr(memberNickBuffAsmV6), 'void', [])
- nativeativeFunction()
-
- console.log('---------nullEdiWxidStructV6', nullEdiWxidStructV6)
- const nickha = readWideString(nullEdiWxidStructV6)
-
- console.log('-----------------')
- console.log(nickha)
- console.log('-----------------')
- return readWideString(nullEdiWxidStructV6)
-})
-
-// 021
-/**
-* send attatch
-*/
-let attatchWxid = null
-let attatchPath = null
-let attatchPathPtr = null
-let attatchAsm = null
-let attatchBuf = null
-
-let attatchReceiveIdPtr = null
-let attatchReceiveId = null
-
-let attatchSendId = null
-let attatchSendIdPtr = null
-
-/*
-let attatchEbp2C = null
-let attatchEDIPtr = null
-let attatchEDIU32 = null
-let attatchECX = null
-
-let attatchEbp210 = null
-let attatchEbpAc = null*/
-
-let attatchEbp11E8 = null
-let attatchEbpCC = null
-let attatchEbp368 = null
-let attatchEAX = null
-
-let sFileName = null
-let fileNamePtr = null
-
-let attatchEbp84 = null
-let attatchECX = null
-
-
-/**
- *
-param {78EDBC86 | 8B80 38040000 | mov eax,dword ptr ds:[eax+438] |
-78EDBC8C | 8BB0 800B0000 | mov esi,dword ptr ds:[eax+B80] |} sendWxid
-*/
-const sendAttatchMsgNativeFunction = ((contactId, senderId, path, filename, size) => {
-
- attatchAsm = Memory.alloc(Process.pageSize)
- console.log('--------------address', attatchAsm)
-
- fileNamePtr = Memory.alloc(filename.length * 2 + 2)
- fileNamePtr.writeUtf16String(filename)
-
- sFileName = Memory.alloc(0x14)
- sFileName.writePointer(ptr(fileNamePtr)).add(0x04)
- .writeU32(fileNamePtr.length * 2).add(0x04)
- .writeU32(fileNamePtr.length * 2).add(0x08)
-
- //const fileSize = size.toInt32()
-
-
- attatchReceiveIdPtr = Memory.alloc(contactId.length * 2 + 2)
- attatchReceiveIdPtr.writeUtf16String(contactId)
-
- attatchReceiveId = Memory.alloc(0x14)
- attatchReceiveId.writePointer(ptr(attatchReceiveIdPtr)).add(0x04)
- .writeU32(contactId.length * 2).add(0x04)
- .writeU32(contactId.length * 2).add(0x08)
-
- attatchSendIdPtr = Memory.alloc(senderId.length * 2 + 2)
- attatchSendIdPtr.writeUtf16String(senderId)
-
- attatchSendId = Memory.alloc(0x14)
- attatchSendId.writePointer(ptr(attatchSendIdPtr)).add(0x04)
- .writeU32(senderId.length * 2).add(0x04)
- .writeU32(senderId.length * 2).add(0x08)
-
- attatchPathPtr = Memory.alloc(path.length * 2 + 2)
- attatchPathPtr.writeUtf16String(path)
-
- attatchPath = Memory.alloc(0x28)
- attatchPath.writePointer(attatchPathPtr).add(0x04)
- .writeU32(path.length * 2).add(0x04)
- .writeU32(path.length * 2).add(0x04)
-
- attatchEbp11E8 = Memory.alloc(0xBE4)
- attatchEbpCC = Memory.alloc(0x14)
- attatchEbp368 = Memory.alloc(0x290)
- attatchEbp84 = Memory.alloc(0x18)
- attatchEAX = Memory.alloc(0x18)
-
- attatchECX = moduleBaseAddress.add(0x222f178).toInt32()
-
- //console.log('basename',path.basename(path))
- //return
-
- /**
- * -------------buffer-------------------------------
- */
-
- Memory.patchCode(attatchAsm, Process.pageSize, code => {
- var cw = new X86Writer(code, { pc: attatchAsm })
- cw.putPushfx()
- cw.putPushax()
-
- cw.putMovRegAddress('ecx', attatchEbp11E8)
- cw.putCallAddress(moduleBaseAddress.add(0xE1590))
-
- cw.putPushU32(-1)
- cw.putPushU32(moduleBaseAddress.add(0x1E1B3C0).toInt32())
- cw.putMovRegAddress('ecx', attatchEbp11E8.add(0x4))//11e4
- cw.putCallAddress(moduleBaseAddress.add(0x702410))//write appid
- // cw.putCallAddress(moduleBaseAddress.add(0x702410))//write appid
-
- /**
- * 78482B8D | 6A FF | push FFFFFFFF |
- 78482B8F | 68 B895E979 | push wechatwin.79E995B8 | 79E995B8:L"0"
- 78482B94 | 8D8D 48EEFFFF | lea ecx,dword ptr ss:[ebp-11B8] |
- 78482B9A | E8 71F83600 | call wechatwin.787F2410 | 此处继续写ebp-11b8
- */
- cw.putPushU32(-1)
- cw.putPushU32(moduleBaseAddress.add(0x1DA95B8).toInt32())
- cw.putMovRegAddress('ecx', attatchEbp11E8.add(0x30))//11B8
- cw.putCallAddress(moduleBaseAddress.add(0x702410))
-
- cw.putMovRegU32('eax', 0x6)
- cw.putMovNearPtrReg(attatchEbp11E8.add(0x80), 'eax')//1168
- cw.putMovRegU32('eax', size)//file size
- cw.putMovNearPtrReg(attatchEbp11E8.add(0x108), 'eax')//10e0
-
-
- cw.putMovRegAddress('eax', sFileName)
- cw.putPushReg('eax')
- cw.putMovRegAddress('ecx', attatchEbp11E8.add(0x44))//11a4=0x11e8-0x160
- cw.putCallAddress(moduleBaseAddress.add(0x702980))//write filename
-
- cw.putMovRegAddress('eax', attatchSendId)
- cw.putPushReg('eax')
- cw.putMovRegAddress('ecx', attatchEbp11E8.add(0x160))//1088=0x11e8-0x160
- cw.putCallAddress(moduleBaseAddress.add(0x702980))
-
-
- cw.putMovRegAddress('eax', attatchEbpCC)
- cw.putPushReg('eax')
- cw.putMovRegAddress('ecx', attatchEbp11E8)
- cw.putCallAddress(moduleBaseAddress.add(0x617C30))
-
- cw.putMovRegAddress('ecx', attatchEbp368)
- cw.putCallAddress(moduleBaseAddress.add(0x954F0))
-
- cw.putPushU32(-1)
- cw.putPushU32((moduleBaseAddress.add(0x1D8F248)).toInt32())
- cw.putMovRegAddress('ecx', attatchEbp84)
- cw.putCallAddress(moduleBaseAddress.add(0x701CD0))
-
- cw.putMovRegAddress('ecx', attatchPath)
- cw.putPushU32(0x6)
- cw.putMovRegAddress('edx', attatchEbp11E8.add(0x160))//1088
- //cw.putMovRegAddress('eax',attatchEAX)
- cw.putPushReg('ecx')
- cw.putPushReg('eax')
-
- cw.putMovRegAddress('eax', attatchEbpCC)
- cw.putPushReg('eax')
-
- cw.putMovRegAddress('eax', attatchReceiveId)
- cw.putPushReg('eax')
-
- cw.putMovRegAddress('ecx', attatchEbp368)
- cw.putCallAddress(moduleBaseAddress.add(0x391F80))
- cw.putAddRegImm('esp', 0x14)
-
-
- cw.putPushU32(moduleBaseAddress.add(0x223EC34).toInt32())
- cw.putPushU32(moduleBaseAddress.add(0x223EC34).toInt32())
- //cw.putMovRegU32('edx',0xAD0001) 两行代码都可以
- cw.putAddRegImm('edx', 0x1)
- cw.putMovRegAddress('ecx', attatchEbp368)
- cw.putCallAddress(moduleBaseAddress.add(0x392150))
- cw.putAddRegImm('esp', 0x8)
-
-
-
- //cw.putMovRegAddress('ecx', attatchEbp368)
- //cw.putCallAddress(moduleBaseAddress.add(0x63B4F0))
- // 7B53F178
- //cw.putMovRegU32('ecx', attatchEbpCC.add(0x3c).toInt32())//ebp-90
- //cw.putMovNearPtrReg(attatchEbpCC.add(0x64), 'eax')//ebp-68
- //cw.putAddRegImm('ecx', 0x8)
- //cw.putMovRegAddress('eax', attatchEbp368.add(0x64))//ebp-68
-
- //cw.putMovRegU32('ecx',attatchECX)
- //cw.putPushReg('eax')
- //cw.putMovRegAddress('eax', attatchEbpCC.add(0x40))//ebp-8c
- //cw.putPushReg('eax')
- //cw.putCallAddress(moduleBaseAddress.add(0xC9D30))
- //cw.putCallAddress(moduleBaseAddress.add(0x522590))
- //78483063 | E8 28F51800 | call wechatwin.78612590 |
-
-
- //78483039 | 8D8D 98FCFFFF | lea ecx,dword ptr ss:[ebp-368] |
- //7848303F | E8 AC842A00 | call wechatwin.7872B4F0 |
- //cw.putMovRegAddress('ecx', attatchEbp368)
- //cw.putCallAddress(moduleBaseAddress.add(0x63B4F0))
-
- // 78F33099 | 8D8D 34FFFFFF | lea ecx,dword ptr ss:[ebp-CC] |
- //78F3309F | E8 AC0FD0FF | call wechatwin.78C34050 |
-
- //cw.putMovRegAddress('ecx',attatchEbpCC)
- //cw.putCallAddress(moduleBaseAddress.add(0x94050))
-
- /**
- * 78F3307F | 8B4D AC | mov ecx,dword ptr ss:[ebp-54] |
- 78F33082 | 8D85 98FCFFFF | lea eax,dword ptr ss:[ebp-368] |
- 78F33088 | 50 | push eax |
- 78F33089 | E8 82DACFFF | call wechatwin.78C30B10 |
-
- cw.putMovRegAddress('ecx', attatchEbp54)
- cw.putMovRegAddress('eax', attatchEbp368)
- cw.putPushReg('eax')
- cw.putCallAddress(moduleBaseAddress.add(0x90B10))*/
-
- cw.putPopax()
- cw.putPopfx()
- cw.putRet()
- cw.flush()
-
- })
-
- const nativeativeFunction = new NativeFunction(ptr(attatchAsm), 'void', [])
- nativeativeFunction()
- /*console.log(hexdump(attatchEbp11E8.add(0x80), {
- offset: 0,
- length: 0x40,
- header: true,
- ansi: true
- }))*/
- //console.log('')
- /*console.log(hexdump(attatchEbpCC.add(0x160), {
- offset: 0,
- length: 0x64,
- header: true,
- ansi: true
- }))*/
- //console.log('-------',attatchEbp1C.readPointer())
- //console.log('-------',attatchEbp1C.add(0x4).readPointer())
- //console.log('-------',attatchEbp1C.add(0x8).readPointer())
-})
-
-// 025
-const callLoginQrcodeFunction = ((forceRefresh = false) => {
- const json = getQrcodeLoginData()
- if (!forceRefresh && json.uuid) {
- return
- }
-
- const callAsm = Memory.alloc(Process.pageSize)
- const loginWnd = moduleBaseAddress.add(offset.get_login_wnd_offset).readPointer()
-
- Memory.patchCode(callAsm, Process.pageSize, code => {
- var cw = new X86Writer(code, { pc: callAsm })
- cw.putPushfx();
- cw.putPushax();
-
- cw.putMovRegAddress('ecx', loginWnd)
- cw.putCallAddress(moduleBaseAddress.add(offset.get_qr_login_call_offset))
-
- cw.putPopax()
- cw.putPopfx()
- cw.putRet()
- cw.flush()
- })
-
- const nativeativeFunction = new NativeFunction(ptr(callAsm), 'void', [])
- nativeativeFunction()
-})
-
-
-// 026
-const agentReadyCallback = (() => {
- const nativeCallback = new NativeCallback(() => { }, 'void', [])
- const nativeativeFunction = new NativeFunction(nativeCallback, 'void', [])
-
- setTimeout(() => {
- nativeativeFunction()
- }, 500);
- return nativeCallback
-})()
-
-// 027
-const SendMiniProgramNativeFunction = ((bg_path_str, send_wxid_str, recv_wxid_str, xmlstr) => {
- console.log("------------------------------------------------------");
- var asmCode = Memory.alloc(Process.pageSize);
-
- var ECX_buf = Memory.alloc(0x300);
- var Buf_EAX = Memory.alloc(0x300);
- var buf_1 = Memory.alloc(0x300);
- var ptr_to_buf_1 = Memory.alloc(0x4).writePointer(buf_1);
- var buf_2 = Memory.alloc(0x300);
-
- // var bg_path_str="C:/aaaa.jpg";
- var bg_path_Ptr = Memory.alloc(bg_path_str.length * 2 + 1)
- bg_path_Ptr.writeUtf16String(bg_path_str);
- var bg_path_Struct = Memory.alloc(0x14) // returns a NativePointer
- bg_path_Struct.writePointer(bg_path_Ptr).add(0x04)
- .writeU32(bg_path_str.length * 2).add(0x04)
- .writeU32(bg_path_str.length * 2).add(0x04)
- .writeU32(0).add(0x04)
- .writeU32(0);
-
- // var send_wxid_str="wxid_4zr616ir6fi122";
- var send_wxid_Ptr = Memory.alloc(send_wxid_str.length * 2 + 1)
- send_wxid_Ptr.writeUtf16String(send_wxid_str);
- var send_wxid_Struct = Memory.alloc(0x14) // returns a NativePointer
- send_wxid_Struct.writePointer(send_wxid_Ptr).add(0x04)
- .writeU32(send_wxid_str.length * 2).add(0x04)
- .writeU32(send_wxid_str.length * 2).add(0x04)
- .writeU32(0).add(0x04)
- .writeU32(0);
-
- // var recv_wxid_str="filehelper";
- var recv_wxid_Ptr = Memory.alloc(recv_wxid_str.length * 2 + 1)
- recv_wxid_Ptr.writeUtf16String(recv_wxid_str);
- var recv_wxid_Struct = Memory.alloc(0x14) // returns a NativePointer
- recv_wxid_Struct.writePointer(recv_wxid_Ptr).add(0x04)
- .writeU32(recv_wxid_str.length * 2).add(0x04)
- .writeU32(recv_wxid_str.length * 2).add(0x04)
- .writeU32(0).add(0x04)
- .writeU32(0);
-
- // vvar pXml=initidStruct('wxid_4zr616ir6fi1220腾讯出行服务|加油代驾公交view330https://mp.weixin.qq.com/mp/waerrpage?appid=wx65cc950f42e8fff1&type=upgrade&upgradetype=3#wechat_redirecthttp://mmbiz.qpic.cn/mmbiz_png/NM1fK7leWGPaFnMAe95jbg4sZAI3fkEZWHq69CIk6zA00SGARbmsGTbgLnZUXFoRwjROelKicbSp9K34MaZBuuA/640?wx_fmt=png&wxfrom=200腾讯出行服务|加油代驾公交0gh_ad64296dc8bd@appwx65cc950f42e8fff11http://mmbiz.qpic.cn/mmbiz_png/NM1fK7leWGPaFnMAe95jbg4sZAI3fkEZWHq69CIk6zA00SGARbmsGTbgLnZUXFoRwjROelKicbSp9K34MaZBuuA/640?wx_fmt=png&wxfrom=20002_wx65cc950f42e8fff1_875237370_1644979747_11Window wechat');
-
- var pXml = initidStruct(xmlstr)
-
- console.log(send_wxid_Struct);
- console.log(recv_wxid_Struct);
- console.log(pXml);
- console.log("okkk");
-
- console.log("------------------------------------------------------");
-
- Memory.patchCode(asmCode, Process.pageSize, code => {
- var cw = new X86Writer(code, { pc: asmCode })
- cw.putPushfx();
- cw.putPushax();
- cw.putMovRegReg('ecx', 'ecx');
- cw.putMovRegAddress('ecx', ECX_buf);
- cw.putCallAddress(moduleBaseAddress.add(0x69BB0)); //init ecx
-
- cw.putPushU32(0x21);
-
-
- cw.putPushNearPtr(ptr_to_buf_1); //ptr
- cw.putPushU32(bg_path_Struct.toInt32());
- cw.putPushU32(pXml.toInt32());
- cw.putPushU32(recv_wxid_Struct.toInt32());
-
- cw.putMovRegAddress('edx', send_wxid_Struct);
- cw.putMovRegAddress('ecx', ECX_buf);
- cw.putCallAddress(moduleBaseAddress.add(0x2E2420));
- cw.putAddRegImm('esp', 0x14)
-
- cw.putPushU32(Buf_EAX.toInt32());
- cw.putMovRegAddress('ecx', ECX_buf);
- cw.putCallAddress(moduleBaseAddress.add(0x94C10));
-
- cw.putPushU32(moduleBaseAddress.add(0x1DCB46C).toInt32());
- cw.putPushU32(moduleBaseAddress.add(0x1DCB46C).toInt32());
- cw.putMovRegAddress('ecx', ECX_buf);
- cw.putCallAddress(moduleBaseAddress.add(0x2E2630));
- cw.putAddRegImm('esp', 0x8)
-
- cw.putPopax();
- cw.putPopfx();
- cw.putRet();
- cw.flush();
- })
-
- const nativeativeFunction = new NativeFunction(ptr(asmCode), 'void', [])
- nativeativeFunction()
-
-
+ // loggedIn = moduleBaseAddress.add(offset.is_logged_in_offset).readU32()
+ // return !!loggedIn
+ return true
})
\ No newline at end of file
diff --git a/src/puppet-xp.ts b/src/puppet-xp.ts
index 446ffae..ce4278f 100644
--- a/src/puppet-xp.ts
+++ b/src/puppet-xp.ts
@@ -108,6 +108,7 @@ class PuppetXp extends PUPPET.Puppet {
this.#sidecar = new WeChatSidecar()
await attach(this.sidecar)
+ void this.onLogin()
this.sidecar.on('hook', ({ method, args }) => {
log.verbose('PuppetXp', 'onHook(%s, %s)', method, JSON.stringify(args))
@@ -141,15 +142,16 @@ class PuppetXp extends PUPPET.Puppet {
private async onAgentReady () {
log.verbose('PuppetXp', 'onAgentReady()')
- const isLoggedIn = await this.sidecar.isLoggedIn()
- if (!isLoggedIn) {
- await this.sidecar.callLoginQrcode(false)
- }
+ // const isLoggedIn = await this.sidecar.isLoggedIn()
+ // if (!isLoggedIn) {
+ // await this.sidecar.callLoginQrcode(false)
+ // }
}
private async onLogin () {
const selfInfoRaw = JSON.parse(await this.sidecar.getMyselfInfo())
+ // console.debug('selfInfoRaw:\n\n\n', selfInfoRaw)
const selfInfo: PUPPET.payloads.Contact = {
alias: '',
avatar: selfInfoRaw.head_img_url,
@@ -567,7 +569,7 @@ class PuppetXp extends PUPPET.Puppet {
id: roomId,
memberIdList: roomMember,
ownerId: '',
- topic: topic,
+ topic,
}
this.roomStore[roomId] = room
delete this.contactStore[roomId]
@@ -834,7 +836,7 @@ class PuppetXp extends PUPPET.Puppet {
}
}
- if ([PUPPET.types.Message.Video, PUPPET.types.Message.Audio].includes(message?.type || PUPPET.types.Message.Unknown)) {
+ if ([ PUPPET.types.Message.Video, PUPPET.types.Message.Audio ].includes(message?.type || PUPPET.types.Message.Unknown)) {
this.notSupported('Video/`Audio')
}
return FileBox.fromFile(
diff --git a/src/wechat-sidecar.ts b/src/wechat-sidecar.ts
index 4b8ec6c..ab02a70 100644
--- a/src/wechat-sidecar.ts
+++ b/src/wechat-sidecar.ts
@@ -47,7 +47,11 @@ const supportedVersions = {
// 'agent-script-3.3.0.115.js',
// ), 'utf-8')
-let initAgentScript = ''
+let initAgentScript = fs.readFileSync(path.join(
+ codeRoot,
+ 'src',
+ 'init-agent-script.js',
+), 'utf-8')
try {
// const wechatVersion = new WeChatVersion()
@@ -104,8 +108,8 @@ try {
@Sidecar('WeChat.exe', initAgentScript)
class WeChatSidecar extends SidecarBody {
- @Call(agentTarget('getTestInfoFunction'))
- getTestInfo ():Promise { return Ret() }
+ // @Call(agentTarget('getTestInfoFunction'))
+ // getTestInfo ():Promise { return Ret() }
@Call(agentTarget('getChatroomMemberNickInfoFunction'))
getChatroomMemberNickInfo (
@@ -131,10 +135,10 @@ class WeChatSidecar extends SidecarBody {
@Call(agentTarget('checkSupportedFunction'))
checkSupported ():Promise { return Ret() }
- @Call(agentTarget('callLoginQrcodeFunction'))
- callLoginQrcode (
- forceRefresh: boolean,
- ):Promise { return Ret(forceRefresh) }
+ // @Call(agentTarget('callLoginQrcodeFunction'))
+ // callLoginQrcode (
+ // forceRefresh: boolean,
+ // ):Promise { return Ret(forceRefresh) }
@Call(agentTarget('getContactNativeFunction'))
getContact ():Promise { return Ret() }
@@ -181,30 +185,30 @@ class WeChatSidecar extends SidecarBody {
@ParamType('int32', 'U32') isMyMsg: number, // add isMyMsg type
) { return Ret(msgType, contactId, text, groupMsgSenderId, xmlContent, isMyMsg) }
- @Hook(agentTarget('checkQRLoginNativeCallback'))
- checkQRLogin (
- @ParamType('int32', 'U32') status: number,
- @ParamType('pointer', 'Utf8String') qrcodeUrl: string,
- @ParamType('pointer', 'Utf8String') wxid: string,
- @ParamType('pointer', 'Utf8String') avatarUrl: string,
- @ParamType('pointer', 'Utf8String') nickname: string,
- @ParamType('pointer', 'Utf8String') phoneType: string,
- @ParamType('int32', 'U32') phoneClientVer: number,
- @ParamType('pointer', 'Utf8String') pairWaitTip: string,
- ) { return Ret(status, qrcodeUrl, wxid, avatarUrl, nickname, phoneType, phoneClientVer, pairWaitTip) }
-
- @Hook(agentTarget('hookLogoutEventCallback'))
- logoutEvent (
- @ParamType('int32', 'U32') bySrv: number,
- ) { return Ret(bySrv) }
-
- @Hook(agentTarget('hookLoginEventCallback'))
- loginEvent (
- ) { return Ret() }
-
- @Hook(agentTarget('agentReadyCallback'))
- agentReady (
- ) { return Ret() }
+ // @Hook(agentTarget('checkQRLoginNativeCallback'))
+ // checkQRLogin (
+ // @ParamType('int32', 'U32') status: number,
+ // @ParamType('pointer', 'Utf8String') qrcodeUrl: string,
+ // @ParamType('pointer', 'Utf8String') wxid: string,
+ // @ParamType('pointer', 'Utf8String') avatarUrl: string,
+ // @ParamType('pointer', 'Utf8String') nickname: string,
+ // @ParamType('pointer', 'Utf8String') phoneType: string,
+ // @ParamType('int32', 'U32') phoneClientVer: number,
+ // @ParamType('pointer', 'Utf8String') pairWaitTip: string,
+ // ) { return Ret(status, qrcodeUrl, wxid, avatarUrl, nickname, phoneType, phoneClientVer, pairWaitTip) }
+
+ // @Hook(agentTarget('hookLogoutEventCallback'))
+ // logoutEvent (
+ // @ParamType('int32', 'U32') bySrv: number,
+ // ) { return Ret(bySrv) }
+
+ // @Hook(agentTarget('hookLoginEventCallback'))
+ // loginEvent (
+ // ) { return Ret() }
+
+ // @Hook(agentTarget('agentReadyCallback'))
+ // agentReady (
+ // ) { return Ret() }
}
From 865ef7fb912cf98e2df58a896ebe509a11836277 Mon Sep 17 00:00:00 2001
From: LuChao
Date: Thu, 21 Sep 2023 15:14:07 +0800
Subject: [PATCH 4/6] add 1.3.0 illustrate
---
README.md | 15 ++++++++++++++-
1 file changed, 14 insertions(+), 1 deletion(-)
diff --git a/README.md b/README.md
index 66fdf73..cba69be 100644
--- a/README.md
+++ b/README.md
@@ -81,9 +81,22 @@ Puppet|xp👍|
登录事件|✅
依赖协议|Windows
+## VERSION SUPPORT
+
+puppet-xp|wechat|
+:---|:---|
+>1.11.14|[WeChat-v3.3.0.115](https://github.com/wechaty/wechaty-puppet-xp/releases/download/v0.5/WeChatSetup-v3.3.0.115.exe)|
+1.12.x|[WeChat-v3.6.0.18](https://github.com/tom-snow/wechat-windows-versions/releases/download/v3.6.0.18/WeChatSetup-3.6.0.18.exe)|
+1.3.x|[WeChat-v3.2.2.23](https://github.com/tom-snow/wechat-windows-versions/releases/download/v3.9.2.23/WeChatSetup-3.9.2.23.exe)|
+
## HISTORY
-### main v1.12.0 (November 22, 2022)
+### next v1.13.0 (September 21, 2023)
+
+1. This version start to support WeChat v3.9.2.23,need to update WeChat on your pc to 3.9.2.23
+2. [WeChatSetup-v3.2.2.23.exe](https://github.com/tom-snow/wechat-windows-versions/releases/download/v3.9.2.23/WeChatSetup-3.9.2.23.exe)
+
+### main v1.12.7 (November 22, 2022)
1. This version start to support WeChat v3.6.0.18,need to update WeChat on your pc to 3.6.0.18
2. [WeChatSetup-v3.6.0.18.exe](https://github.com/tom-snow/wechat-windows-versions/releases/download/v3.6.0.18/WeChatSetup-3.6.0.18.exe)
From 7bfb22c01a9bd5172f2a944af073fe6dee39530b Mon Sep 17 00:00:00 2001
From: LuChao
Date: Thu, 21 Sep 2023 15:21:11 +0800
Subject: [PATCH 5/6] Update README.md
---
README.md | 8 ++++----
1 file changed, 4 insertions(+), 4 deletions(-)
diff --git a/README.md b/README.md
index cba69be..1a603cf 100644
--- a/README.md
+++ b/README.md
@@ -84,10 +84,10 @@ Puppet|xp👍|
## VERSION SUPPORT
puppet-xp|wechat|
-:---|:---|
->1.11.14|[WeChat-v3.3.0.115](https://github.com/wechaty/wechaty-puppet-xp/releases/download/v0.5/WeChatSetup-v3.3.0.115.exe)|
-1.12.x|[WeChat-v3.6.0.18](https://github.com/tom-snow/wechat-windows-versions/releases/download/v3.6.0.18/WeChatSetup-3.6.0.18.exe)|
-1.3.x|[WeChat-v3.2.2.23](https://github.com/tom-snow/wechat-windows-versions/releases/download/v3.9.2.23/WeChatSetup-3.9.2.23.exe)|
+|:---|:---|
+|>1.11.14|[WeChat-v3.3.0.115](https://github.com/wechaty/wechaty-puppet-xp/releases/download/v0.5/WeChatSetup-v3.3.0.115.exe)|
+|1.12.x|[WeChat-v3.6.0.18](https://github.com/tom-snow/wechat-windows-versions/releases/download/v3.6.0.18/WeChatSetup-3.6.0.18.exe)|
+|1.3.x|[WeChat-v3.2.2.23](https://github.com/tom-snow/wechat-windows-versions/releases/download/v3.9.2.23/WeChatSetup-3.9.2.23.exe)|
## HISTORY
From e2fe79119b9980c977489f4147d7be513633dcef Mon Sep 17 00:00:00 2001
From: LuChao
Date: Thu, 21 Sep 2023 15:22:03 +0800
Subject: [PATCH 6/6] Update README.md
---
README.md | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/README.md b/README.md
index 1a603cf..00dff81 100644
--- a/README.md
+++ b/README.md
@@ -85,8 +85,8 @@ Puppet|xp👍|
puppet-xp|wechat|
|:---|:---|
-|>1.11.14|[WeChat-v3.3.0.115](https://github.com/wechaty/wechaty-puppet-xp/releases/download/v0.5/WeChatSetup-v3.3.0.115.exe)|
-|1.12.x|[WeChat-v3.6.0.18](https://github.com/tom-snow/wechat-windows-versions/releases/download/v3.6.0.18/WeChatSetup-3.6.0.18.exe)|
+|1.11.14|[WeChat-v3.3.0.115](https://github.com/wechaty/wechaty-puppet-xp/releases/download/v0.5/WeChatSetup-v3.3.0.115.exe)|
+|1.12.7|[WeChat-v3.6.0.18](https://github.com/tom-snow/wechat-windows-versions/releases/download/v3.6.0.18/WeChatSetup-3.6.0.18.exe)|
|1.3.x|[WeChat-v3.2.2.23](https://github.com/tom-snow/wechat-windows-versions/releases/download/v3.9.2.23/WeChatSetup-3.9.2.23.exe)|
## HISTORY