-
Notifications
You must be signed in to change notification settings - Fork 501
Expand file tree
/
Copy pathhook.js
More file actions
124 lines (115 loc) · 3.91 KB
/
Copy pathhook.js
File metadata and controls
124 lines (115 loc) · 3.91 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
const getMainModule = (version) => {
if (version >= 13331) {
return Process.findModuleByName("flue.dll");
}
return Process.findModuleByName("WeChatAppEx.exe");
};
const patchCDPFilter = (base, config) => {
// xref: SendToClientFilter OR devtools_message_filter_applet_webview.cc
const offset = config.CDPFilterHookOffset;
Interceptor.attach(base.add(offset), {
onEnter(args) {
send(
`[patch] CDP filter on enter, original value of input: ${args[0].readPointer()}`,
);
this.inputValue = args[0];
},
onLeave(retval) {
const inputValue = this.inputValue.readPointer();
if (inputValue.isNull() || inputValue.add(8).isNull()) {
// there's a chance the value could be null
// return here to avoid crash
return;
}
send(
`[patch] CDP filter on leave, patch input, now value: ${inputValue}; ` +
`*(input + 8) = ${inputValue.add(8).readU32()}`,
);
if (inputValue.add(8).readU32() == 6) {
inputValue.add(8).writeU32(0x0);
}
},
});
};
const hookOnLoadScene = (a1, sceneOffsets) => {
const miniappConfigPtr = a1
.add(sceneOffsets[0])
.readPointer()
.add(sceneOffsets[1])
.readPointer();
const miniappScenePtr = miniappConfigPtr
.add(sceneOffsets[2])
.readPointer()
.add(sceneOffsets[3])
.readPointer()
.add(sceneOffsets[4])
.readPointer()
.add(sceneOffsets[5]);
send(`[hook] scene: ${miniappScenePtr.readInt()}`);
// 1000: from issue #83 <-- will crash the process
// 1007: from issue #80
// 1008: from issue #53
// 1027: from issue #78
// 1035: from issue #78
// 1053: from issue #25
// 1074: from issue #32
// 1145: from search
// 1178: from phone (issue #117)
// 1256: from recent
// 1260: from frequently used
// 1302: from services
// 1308: minigame?
const sceneNumberArray = [
1005, 1007, 1008, 1027, 1035, 1053, 1074, 1145, 1178, 1256, 1260, 1302,
1308,
];
if (!sceneNumberArray.includes(miniappScenePtr.readInt())) {
return;
}
send("[hook] hook scene condition -> 1101");
miniappScenePtr.writeInt(1101);
// TODO: customize debugging endpoint
// const websocketServerStringPtr = passArgs.add(8).readPointer().add(520);
// VERBOSE && console.log("[hook] hook websocket server, original: ", websocketServerStringPtr.readUtf8String());
// websocketServerStringPtr.writeUtf8String("ws://127.0.0.1:8189/");
};
const patchOnLoadStart = (base, config) => {
// xref: AppletIndexContainer::OnLoadStart
Interceptor.attach(base.add(config.LoadStartHookOffset), {
onEnter(args) {
send(
`[inteceptor] AppletIndexContainer::OnLoadStart onEnter, ` +
`indexContainer.this: ${this.context.rcx}`,
);
// write dl to 0x1
if ((this.context.rdx & 0xff) !== 1) {
this.context.rdx = (this.context.rdx & ~0xff) | 0x1;
}
// handle onLoad scene
hookOnLoadScene(this.context.rcx, config.SceneOffsets);
},
onLeave(retval) {
// do nothing
},
});
};
const parseConfig = () => {
const rawConfig = `@@CONFIG@@`;
if (rawConfig.includes("@@")) {
// test addresses
return {
Version: 18955,
LoadStartHookOffset: "0x25B52C0",
CDPFilterHookOffset: "0x30248B0",
SceneOffsets: [1408, 1344, 488],
};
}
return JSON.parse(rawConfig);
};
const main = () => {
const config = parseConfig();
const mainModule = getMainModule(config.Version);
patchOnLoadStart(mainModule.base, config);
patchCDPFilter(mainModule.base, config);
};
main();