Last active
June 16, 2019 14:37
-
-
Save FransBouma/6b41665b14d006be32d081ff69ded3a4 to your computer and use it in GitHub Desktop.
Hitman 2016 Final CT camera table, with smooth movement. For v1.7. By Jim2Point0 and myself.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?xml version="1.0" encoding="utf-8"?> | |
<CheatTable CheatEngineTableVersion="21"> | |
<CheatEntries> | |
<CheatEntry> | |
<ID>11022</ID> | |
<Description>"Camera system. Toggle: INS. Enable first"</Description> | |
<LastState/> | |
<VariableType>Auto Assembler Script</VariableType> | |
<AssemblerScript>//---------------------------------------------------------- | |
// Reworked Hitman 2016 cheat table with free camera / timestop / FoV | |
// Original camera / timestop: Jim2Point0 | |
// Reworked camera / threading code: Otis / Infuse Project | |
// | |
// For Hitman v1.7.0. | |
// | |
// this table contains a thread based camera movement system which moves the camera based on the camera look vector direction | |
// so pressing e.g. 'left' (numpad 4) is moving the camera left, you're no longer moving over the world x/y/z axis which don't align with | |
// the camera direction in most cases. | |
// | |
// I've commented a lot of code in this table. For seasoned assembly programmers these comments might sound like 'water is wet' statements, | |
// but they might help the novice assembly programmer out what's going on (as SIMD programmer isn't straightforward!) :) | |
// The features are enabled / disabled by two child scripts, one for the FoV and one for the camera hook. | |
// This is done so the thread loop can run at almost full speed scanning keys and it's also easier to enable e.g. FoV without the | |
// camera. | |
//---------------------------------------------------------- | |
[ENABLE] | |
globalalloc(OwnCode, 2048) // alloc memory for our code, once. | |
createthread(MainThread) | |
//---------------------------------------------------------- | |
// Code labels | |
label(MainThread) | |
label(MainThread_EndLoop) | |
label(GrabCameraStructAddress) | |
// Data labels | |
label(_disableThread) | |
label(_cameraStruct) | |
label(_cameraEnabled) | |
label(_fovEnabled) | |
label(_altPressed) | |
label(_ctrlPressed) | |
label(_lockCamera) | |
label(MoveCameraSidewaysRight) | |
label(PerformLockCamera) | |
// Symbols. Registering them allows you to use them in the CE UI. | |
registersymbol(_disableThread) | |
registersymbol(_cameraStruct) | |
registersymbol(_cameraEnabled) | |
registersymbol(_fovEnabled) | |
registersymbol(_lockCamera) | |
registersymbol(MainThread) | |
registersymbol(MainThread_EndLoop) | |
registersymbol(GrabCameraStructAddress) | |
registersymbol(MoveCameraSidewaysRight) | |
registersymbol(PerformLockCamera) | |
OwnCode: | |
// Grab camera structure address, which is inside the camera struct we need. | |
// There are more instructions here, as the overwrite is bigger (14 bytes), as it uses a | |
// qword address sourced jump instead of a simple jump because the jump is into global allocated memory! | |
GrabCameraStructAddress: | |
cmp [rbx+38],0 // could also check +20 or +24 for 0 if the above fails | |
jne GrabCameraOriginalCode | |
mov [_cameraStruct], rbx | |
cmp byte [_cameraEnabled], 1 | |
je ExitCameraStructGrab // camera enabled, skip original code. | |
GrabCameraOriginalCode: | |
movss [rbx+00000090],xmm0 // original statement | |
movss xmm0,[rsp+58] // original statement | |
ExitCameraStructGrab: | |
jmp ReturnAfterCameraStructGrab | |
// The lock mouse code. | |
// There are more instructions here, as the overwrite is bigger (14 bytes), as it uses a | |
// qword address sourced jump instead of a simple jump because the jump is into global allocated memory! | |
PerformLockCamera: | |
movaps xmm0,[rax] // original statement | |
cmp byte [_lockCamera], 1 | |
je @f | |
movups [rbx+00000080],xmm0 // original statement, performs write. | |
@@: | |
movss xmm0,[rsp+50] // original statement | |
jmp ReturnAfterPerformLockCamera | |
//--------------------------------------------------------- | |
// Code | |
MainThread: | |
// x64 calls to Win32 functions uses Windows ABI 64 bit calling convention: create 'shadow space on the stack | |
// for the first 4 arguments and 16-byte align the stack, which happens to be 40 bytes. Result is stored in RAX. | |
// So that's the sub rsp/add rsp statements doing around Win32 calls. | |
sub rsp, 28 | |
mov rcx, #25 | |
call kernel32.Sleep // for some reason CE compiles 'Sleep' wrong, but does do it properly when kernel32.Sleep is used. Oh well... | |
add rsp, 28 | |
// check if the thread can die | |
cmp [_disableThread], 1 | |
je MainThread_End // disabled, die | |
// check if the camera struct is already available. If not, loop to the beginning of the thread, | |
// which will be a sleep call. We do this as the thread can be created before the hook is set in the process. | |
cmp qword ptr [_cameraStruct], 0 | |
je MainThread | |
// check if one of the keys is pressed | |
// keys supported: | |
// Camera pos: num8 (forward), num4 (backward), num6 (right), num4 (left), num9 (up), num3 (down). | |
// Enable/disable depends on separate script (see table) | |
// FoV : substract (decrease FoV), add (increase FoV). Enable/disable depends on separate script (see table) | |
// We'll do this one at a time, as it doesn't matter if we e.g. check up+left or first up and then left | |
// Camera position manipulation keys are ignored if camera is disabled | |
// We'll check with GetKeyState, and not GetAsyncKeyState, as GetAsyncKeyState can fail if CE is on a different monitor | |
// than the game. | |
// | |
// FoV keys | |
@@: | |
sub rsp, 28 | |
mov rcx, 6D // numpad substract (VK_SUBSTRACT) | |
call GetKeyState | |
add rsp, 28 | |
test ax, 8000 | |
jz @f | |
// key pressed, do fov decrease | |
call DoFoVDecrease | |
@@: | |
sub rsp, 28 | |
mov rcx, 6B // numpad add (VK_ADD) | |
call GetKeyState | |
add rsp, 28 | |
test ax, 8000 | |
jz @f | |
// key pressed, do fov inccrease | |
call DoFoVIncrease | |
@@: | |
sub rsp, 28 | |
mov rcx, 6A // numpad mul (VK_MULTIPLY) | |
call GetKeyState | |
add rsp, 28 | |
test ax, 8000 | |
jz @f | |
// key pressed, reset fov | |
mov rcx, [_cameraStruct] | |
mov [rcx+17c], (float)0.7 | |
@@: | |
// Free camera movement keys | |
// first check if the free camera is enabled. Enabling is done by a different script. | |
cmp byte [_cameraEnabled], 1 | |
jne MainThread_EndLoop | |
// camera enabled, we can proceed with handling camera movement keys | |
// Check if alt is pressed. If so, we'll speed up the movement. We'll store the bit for later | |
mov rcx, 12 // Alt (VK_MENU) | |
call GetKeyState | |
and eax, 8000 // high bit is either set (key is pressed) or not (key isn't pressed). Rest of bits is garbage, so clear them | |
shr ax, F // so we simply shift right 15 bits, which moves the high bit to the LSB | |
mov [_altPressed], ax | |
// Check if ctrl is pressed. If so, we'll slow down the movement. Same code as Alt. We'll store the bit for later | |
mov rcx, 11 // Ctrl (VK_CONTROL) | |
call GetKeyState | |
and eax, 8000 | |
shr ax, F | |
mov [_ctrlPressed], ax | |
mov rcx, 68 // numpad 8 (VK_NUMPAD8) | |
call GetKeyState | |
test ax, 8000 | |
jz @f | |
// up is pressed, perform camera move forward. | |
call MoveCameraForward | |
@@: | |
mov rcx, 62 // numpad 2 (VK_NUMPAD2) | |
call GetKeyState | |
test ax, 8000 | |
jz @f | |
// down is pressed, perform camera move backwards | |
call MoveCameraBackwards | |
@@: | |
mov rcx, 64 // numpad 4 (VK_NUMPAD4) | |
call GetKeyState | |
test ax, 8000 | |
jz @f | |
// left is pressed, perform camera move sideways | |
call MoveCameraSidewaysLeft | |
@@: | |
mov rcx, 66 // numpad 6 (VK_NUMPAD6) | |
call GetKeyState | |
test ax, 8000 | |
jz @f | |
// right is pressed, perform camera move sideways | |
call MoveCameraSidewaysRight | |
@@: | |
mov rcx, 69 // numpad 9 (VK_NUMPAD9) | |
call GetKeyState | |
test ax, 8000 | |
jz @f | |
// z up is pressed, perform camera move upwards along Z axis | |
xor rbx, rbx // if rbx is set to 0 for this function it will move up, otherwise down | |
call MoveCameraUpDown | |
@@: | |
mov rcx, 63 // numpad 3 (VK_NUMPAD3) | |
call GetKeyState | |
test ax, 8000 | |
jz @f | |
// z down is pressed, perform camera move downwards along Z axis | |
mov rbx, 1 | |
call MoveCameraUpDown | |
@@: | |
MainThread_EndLoop: | |
// check if the thread can die | |
cmp [_disableThread], 1 | |
jne MainThread // not disabled, so loop! | |
MainThread_End: | |
// end | |
mov [_disableThread], 2 | |
ret | |
//------------------------------------------------------------- | |
// camera movement code | |
// We're using a normalized (vector with length 1.0) vector to move the camera. | |
// this vector is at [_cameraStruct]+60, with vX, vY, vZ, W. This is the 3rd row in the camera matrix in general, and also in this case. | |
// The 'W' isn't used, but as the SIMD instructions load 128bits into the registers, they'll load the 4th dword too. | |
// | |
// The vector is the camera look vector so we can use that to manipulate the camera coordinates: | |
// Forward means we're moving in the direction of the vector (X, Y and Z updated) | |
// Left/Right means we're moving in the x/y plane in the direction orthogonal on the look vector (X, Y updated, Z is left alone) | |
// Backwards means we're moving in the opposite direction of the vector (X, Y and Z updated) | |
// The vector uses (-x, -y, z) compared to the world/geometry coordinates. This means that | |
// if the vector is aligned with the x axis looking at the positive x of the world, it's vX component is negative. Same for vY. | |
// If you think 'Why is this bozo doing a sub when he wants to add?!', that's why ;) | |
MoveCameraForward: | |
push rax | |
mov rax, [_cameraStruct] | |
add rax, 90 // load camera X, Y, Z, W into xmm0. X is at [_cameraStruct+90] | |
movups xmm0, [rax] | |
sub rax, 30 // normalized vector is at [_cameraStruct+60]: vX, vY, vZ, vW | |
movups xmm1, [rax] // load normalized vector into xmm1 (vX, vY, vZ, vW) | |
call SizeLookVector // will apply alt/ctrl to vector in xmm1 so it makes movement either faster or slower. | |
subps xmm0, xmm1 // sub the vector from the camera pos, as we're moving in the direction of the vector, but the vector uses -x, -y. If it would have used x, y, we should have used addps | |
mov rax, [_cameraStruct] | |
add rax, 90 | |
movups [rax], xmm0 // move the newly calculated pos back into the camera values. | |
pop rax | |
ret | |
MoveCameraBackwards: | |
push rax | |
mov rax, [_cameraStruct] | |
add rax, 90 // load camera X, Y, Z, W into xmm0. X is at [_cameraStruct+90] | |
movups xmm0, [rax] | |
sub rax, 30 // normalized vector is at [_cameraStruct+60]: vX, vY, vZ, vW | |
movups xmm1, [rax] // load normalized vector into xmm1 (vX, vY, vZ, vW) | |
call SizeLookVector // will apply alt/ctrl to vector in xmm1 so it makes movement either faster or slower. | |
addps xmm0, xmm1 // add the vector from the camera pos, as we're moving in the opposite direction of the vector, but the vector uses -x, -y. If it would have used x, y, we should have used subps | |
mov rax, [_cameraStruct] | |
add rax, 90 | |
movups [rax], xmm0 // move the newly calculated position back into the camera position values. | |
pop rax | |
ret | |
//------------------------------------------------------------ | |
// move left & right will use the x/y portion of the normalized vector and set z to 0. This gives a vector in the x/y plane | |
// which potentially isn't of length 1 so we have to normalize it again. | |
// To refresh your memory concerning xmm regs: [0|1|2|3] are the parts. so vX is placed in the lower element (0), vY in (1) etc. | |
// I use it this way as CE displays xmm registers in that order in the debugger. | |
// so shuffle commands have their bits backwards compared to the order of the xmm elements: 33 22 11 00 | |
// Clear? thought so :) | |
MoveCameraSidewaysLeft: | |
push rax | |
call GetCameraVectorAsXYVector // will load camera vector into xmm1, move it to x/y plane, normalize it | |
// move left means we have to rotate the x/y vector 90 degrees counter-clockwize. This is simple: new vector is (-vY, vX). | |
// first move the elements to the right position | |
shufps xmm1, xmm1, F1 // shuffle using: 11 11 00 01. xmm1 now contains (vY, vX, 0, vW) | |
xorps xmm2, xmm2 // set the value of xmm2 to 0 | |
subss xmm2, xmm1 // substract 1st value of xmm1, which is vY, from 0 | |
movss xmm1, xmm2 // move -vY from xmm2's first element into xmm1. xmm1 now contains (-vY, vX, 0, vW) | |
call SizeLookVector | |
mov rax, [_cameraStruct] | |
add rax, 90 // load camera X, Y, Z, W into xmm0. X is at [_cameraStruct+90] | |
movups xmm0, [rax] | |
subps xmm0, xmm1 // add the vector we calculated to the camera position. But x/y are negative aligned, remember? So we do sub! It should now move left | |
mov rax, [_cameraStruct] | |
add rax, 90 | |
movups [rax], xmm0 // move the newly calculated position back into the camera position values. | |
pop rax | |
ret | |
MoveCameraSidewaysRight: | |
push rax | |
call GetCameraVectorAsXYVector // will load camera vector into xmm1, move it to x/y plane, normalize it | |
// move right means we have to rotate the x/y vector 90 degrees clockwize. This is simple: new vector is (vY, -vX). | |
xorps xmm2, xmm2 // set the value of xmm2 to 0 | |
subss xmm2, xmm1 // substract 1st value of xmm1, which is vX, from 0 | |
movss xmm1, xmm2 // move -vX from xmm2's first element into xmm1. xmm1 now contains (-vX, vY, 0, vW) | |
shufps xmm1, xmm1, F1 // shuffle using: 11 11 00 01. xmm1 now contains (vY, -vX, 0, vW) | |
call SizeLookVector | |
mov rax, [_cameraStruct] | |
add rax, 90 // load camera X, Y, Z, W into xmm0. X is at [_cameraStruct+90] | |
movups xmm0, [rax] | |
subps xmm0, xmm1 // add the vector we calculated to the camera position. But x/y are negative aligned, remember? So we do sub! It should now move right | |
mov rax, [_cameraStruct] | |
add rax, 90 | |
movups [rax], xmm0 // move the newly calculated position back into the camera position values. | |
pop rax | |
ret | |
//------------------------------------------------------------ | |
// Camera up / down movement is done by first creating a vector (0, 0, 1.0) as look vector, size it with the size code, and | |
// simply add it to the camera coords for up and sub it from the camera coords for down. Z is aligned with world coordinates Z. | |
// In: rbx: 0==up, not 0==down | |
MoveCameraUpDown: | |
push rax | |
call GetZVector // xmm1 now contains (0, 0, 1.0, 0) | |
call SizeLookVector // size it based on alt/ctrl keys | |
mov rax, [_cameraStruct] | |
add rax, 90 // load camera X, Y, Z, W into xmm0. X is at [_cameraStruct+90] | |
movups xmm0, [rax] | |
test rbx, rbx // check whether the register is set to 0. If so, we'll move up, otherwise we'll move down | |
je MoveCameraUpDown_Up | |
subps xmm0, xmm1 // sub the vector we calculated from the camera position. Z is aligned with the world axis, so we use sub | |
jmp MoveCameraUpDown_Store | |
MoveCameraUpDown_Up: | |
addps xmm0, xmm1 // add the vector we calculated to the camera position. Z is aligned with the world axis, so we use add (finally, some sanity!) | |
MoveCameraUpDown_Store: | |
mov rax, [_cameraStruct] | |
add rax, 90 | |
movups [rax], xmm0 // move the newly calculated position back into the camera position values. | |
pop rax | |
ret | |
//------------------------------------------------------------ | |
// returns in xmm1 a vector (0, 0, 1.0, 0). | |
// in: nothin' | |
// out: the vector (0, 0, 1.0, 0) | |
// Changes: xmm1 | |
GetZVector: | |
push rax | |
xorps xmm1, xmm1 // set the value of xmm1 to 0 | |
mov rax, (float)1.0 | |
movd xmm1, rax // move 1.0 into xmm1. Which now contains 1.0, 0, 0, 0 | |
shufps xmm1, xmm1, 45 // shuffle xmm1 so the 1.0 is placed at the 3rd element, which is Z. So we'll use: 01 00 01 01 | |
pop rax | |
ret | |
// Loads the camera vector into xmm1, will reset vZ to 0 and will normalize the vector (vX, vY) to length 1.0. | |
// It's a bit dirty, as it will fail with the vector pointing along the Z axis and x/y being 0.0, but the game doesn't allow that | |
// In: nothin' | |
// Out: xmm1: normalized camera vector in x/y plane with vZ set to 0.0. | |
// Changes: xmm2, xmm3 | |
GetCameraVectorAsXYVector: | |
push rax | |
mov rax, [_cameraStruct] | |
add rax, 60 // normalized vector is at [_cameraStruct+60]: vX, vY, vZ, vW | |
movups xmm1, [rax] // load normalized vector into xmm1 (vX, vY, vZ, vW) | |
xorps xmm2, xmm2 // reset xmm2 to 0, all 4 components | |
mov rax, -1 | |
movd xmm2, rax // the 1st element (index 0) contains -1 (ffffffff). | |
shufps xmm2, xmm2, 10 // shuffle using: 00 01 00 00 all 4 elements are now filled with -1 except the 3rd (which contains Z) | |
andps xmm1, xmm2 // this will set the 3rd element (vZ) to 0, keep all other elements. xmm1 now contains (vX, vY, 0, vW) | |
// we now have to normalize the vector in xmm1, as it's not really a length of 1, as x/y are smaller if z isn't 0. This is | |
// done with the formula: vX=vX/length, vY=vY/length. Length = sqrt(x*x+y*y). So first we'll calculate the length. | |
// this is simple, we multiply xmm1 with itself. Of course in another register as we need xmm1 later. | |
movaps xmm2, xmm1 // xmm2 now contains xmm1's values | |
mulps xmm2, xmm2 // multiply xmm2 with itself, which means vX=vX*vX, vY=vY*vY, 0*0, vW=vW*vW (but we don't care about that) | |
movaps xmm3, xmm2 // move the values of xmm2 in xmm3 so we can move vY*vY to the slot 0 to add it to vX*vX | |
shufps xmm3, xmm3, F1 // shuffle using 11 11 00 01 so end result is vY*vY, vX*vX, 0, vW*vW | |
addss xmm2, xmm3 // adds the slot 0 values of xmm3 and xmm2 which means xmm2 now contains vX*vX + vY*vY. | |
sqrtss xmm2, xmm2 // square root the slot 0 value, so it now contains sqrt(vX*vX + vY*vY). | |
shufps xmm2, xmm2, 0 // shuffle the sqrt result to all slots0, 1 and 2 so we can div x and y (and z, but will result in 0) in one go. | |
// so use 00 00 00 00 to avoid div by 0 in the next statement. | |
divps xmm1, xmm2 // div xmm1 with xmm2, which means vX/sqrt(vX*vX+vY*vY), vY/sqrt(vX*vX+vY*vY), 0, vW | |
pop rax | |
ret | |
//------------------------------------------------------------ | |
// Will multiply the camera vector with a scalar to size it up (if alt is pressed) or down (if ctrl is pressed) | |
// If no alt/ctrl is pressed, we size it with the scalar 2.0 to make moving around more pleasant | |
// in : xmm1 (vX, vY, vZ, vW) | |
// changes: xmm7 | |
SizeLookVector: | |
push rbx | |
cmp byte [_altPressed], 1 | |
jne @f | |
// alt pressed. Multiply with 2.0 | |
mov rbx, (float)1.0 | |
jmp SizeLookVector_Calc | |
@@: | |
cmp byte [_ctrlPressed], 1 | |
jne @f | |
// ctrl pressed. Multiply with 0.05 | |
mov rbx, (float)0.01 | |
jmp SizeLookVector_Calc | |
@@: | |
// default scalar sizing | |
mov rbx, (float)0.1 | |
SizeLookVector_Calc: | |
movd xmm7, rbx // load the factor to multiply with into xmm7. This is a scalar, xmm registers contain 4 of them | |
shufps xmm7, xmm7, 0 // so we shuffle the first element to be placed in all 4. | |
mulps xmm1, xmm7 // multiply the vector in xmm1 with the 4 values in xmm7, so vX=vX*xmm7[0], vY=vY*xmm7[1] etc. | |
SizeLookVector_End: | |
pop rbx | |
ret | |
//------------------------------------------------------------ | |
// FoV code | |
DoFoVIncrease: | |
cmp byte [_fovEnabled], 1 | |
je @f | |
// not enabled, nothing to do. | |
ret | |
@@: | |
push rax | |
push rbx | |
mov rax, [_cameraStruct] | |
add rax, 17c // FoV value is at offset 17c. Contains 0.7 for normal fov. | |
movss xmm0, [rax] | |
mov rbx, (float)0.01 // load the register with 0.01 float, and move it using this register into xmm1 | |
movd xmm1, rbx | |
addss xmm0, xmm1 // add the 0.01 to the value. | |
movss [rax], xmm0 // store the new value back into the address. | |
pop rbx | |
pop rax | |
ret | |
DoFoVDecrease: | |
cmp byte [_fovEnabled], 1 | |
je @f | |
// not enabled, nothing to do. | |
ret | |
@@: | |
push rax | |
push rbx | |
mov rax, [_cameraStruct] | |
add rax, 17c // FoV value is at offset 17C | |
movss xmm0, [rax] | |
mov rbx, (float)0.01 // load the register with 0.01 float, and move it using this register into xmm1 | |
movd xmm1, rbx | |
subss xmm0, xmm1 // sub the 0.01 from the value | |
movss [rax], xmm0 // store the new value back into the address. | |
pop rbx | |
pop rax | |
ret | |
//----------------------------------------------------------- | |
// Local data | |
_cameraStruct: | |
dq 0 | |
_disableThread: | |
dd 0 | |
_cameraEnabled: | |
db 0 | |
_fovEnabled: | |
db 0 | |
_lockCamera: | |
db 0 | |
_altPressed: | |
dw 0 | |
_ctrlPressed: | |
dw 0 | |
// overwrite inside the Hitman process the following address with a jmp to our code which grabs the camera struct address | |
// which is in the register rbx. | |
// Remember this is compiled to a long jmp so will take up 14 bytes! | |
//"hitman.exe"+419037A: | |
"hitman.exe"+41C5B9A: | |
jmp GrabCameraStructAddress | |
ReturnAfterCameraStructGrab: | |
// Lock camera overwrite. Remember this is compiled to a long jmp so will take up 14 bytes! | |
//"hitman.exe"+419036A: | |
"hitman.exe"+41C5B8A: | |
jmp PerformLockCamera | |
nop | |
nop | |
ReturnAfterPerformLockCamera: | |
[DISABLE] | |
_cameraStruct: | |
dq 0 | |
_disableThread: | |
dd 1 | |
_cameraEnabled: | |
db 0 | |
_fovEnabled: | |
db 0 | |
_lockMatrix: | |
db 0 | |
_altPressed: | |
dw 0 | |
_ctrlPressed: | |
dw 0 | |
// ALWAYS replace overwritten memory of all subnodes here, as the user can leave them ON and disable this one | |
// which will result in a crash if we don't overwrite them back to normal. | |
// Camera | |
//"hitman.exe"+419037A: | |
"hitman.exe"+41C5B9A: | |
movss [rbx+00000090],xmm0 | |
movss xmm0,[rsp+58] | |
//"hitman.exe"+4190388: | |
"hitman.exe"+41C5BA8: | |
movss [rbx+00000098],xmm0 | |
//"hitman.exe"+4190390: | |
"hitman.exe"+41C5BB0: | |
movss [rbx+00000094],xmm1 | |
// Lock Camera: | |
//"hitman.exe"+419036A: | |
"hitman.exe"+41C5B8A: | |
movaps xmm0,[rax] | |
movups [rbx+00000080],xmm0 | |
movss xmm0,[rsp+50] | |
// Fov | |
//"hitman.exe"+44E4887: | |
//je hitman.CAkRegisteredObj::~CAkRegisteredObj+425C6A | |
//movss xmm0,[hitman.Ordinal277+1303614] | |
"hitman.exe"+44E4887: | |
je hitman.exe+44E48B9 | |
movss xmm0,[hitman.exe+1312714] | |
"hitman.exe"+44E48A9: | |
movss [rcx+0000017C],xmm0 | |
// unregister symbols, as they're no longer needed | |
unregistersymbol(_disableThread) | |
unregistersymbol(_cameraStruct) | |
unregistersymbol(_cameraEnabled) | |
unregistersymbol(_fovEnabled) | |
unregistersymbol(_lockCamera) | |
unregistersymbol(MainThread) | |
unregistersymbol(MainThread_EndLoop) | |
unregistersymbol(GrabCameraStructAddress) | |
unregistersymbol(MoveCameraSidewaysRight) | |
unregistersymbol(PerformLockCamera) | |
</AssemblerScript> | |
<Hotkeys> | |
<Hotkey> | |
<Action>Toggle Activation</Action> | |
<Keys> | |
<Key>45</Key> | |
</Keys> | |
<ID>0</ID> | |
</Hotkey> | |
</Hotkeys> | |
<CheatEntries> | |
<CheatEntry> | |
<ID>11034</ID> | |
<Description>"Lock mouse. Toggle: F5"</Description> | |
<LastState/> | |
<VariableType>Auto Assembler Script</VariableType> | |
<AssemblerScript>[ENABLE] | |
_lockCamera: | |
db 1 // sets flag in main script's thread data | |
[DISABLE] | |
_lockCamera: | |
db 0 // resets flag in main script's thread data | |
</AssemblerScript> | |
<Hotkeys> | |
<Hotkey> | |
<Action>Toggle Activation</Action> | |
<Keys> | |
<Key>116</Key> | |
</Keys> | |
<ID>0</ID> | |
</Hotkey> | |
</Hotkeys> | |
</CheatEntry> | |
<CheatEntry> | |
<ID>11015</ID> | |
<Description>"FOV. Toggle: HOME"</Description> | |
<LastState/> | |
<VariableType>Auto Assembler Script</VariableType> | |
<AssemblerScript>[ENABLE] | |
_fovEnabled: | |
db 1 // sets flag in main script's thread data | |
"hitman.exe"+44E4887: | |
db 90 90 | |
"hitman.exe"+44E48A9: | |
db 90 90 90 90 90 90 90 90 | |
[DISABLE] | |
_fovEnabled: | |
db 0 // resets flag in main script's thread data | |
// original fov write code. | |
"hitman.exe"+44E4887: | |
je hitman.exe+44E48B9 | |
movss xmm0,[hitman.exe+1312714] | |
"hitman.exe"+44E48A9: | |
movss [rcx+0000017C],xmm0 | |
</AssemblerScript> | |
<Hotkeys> | |
<Hotkey> | |
<Action>Toggle Activation</Action> | |
<Keys> | |
<Key>36</Key> | |
</Keys> | |
<ID>0</ID> | |
</Hotkey> | |
</Hotkeys> | |
<CheatEntries> | |
<CheatEntry> | |
<ID>11020</ID> | |
<Description>"Num+/-: change FOV. Num*: reset"</Description> | |
<LastState Value="" RealAddress="00000000"/> | |
<Color>008000</Color> | |
<GroupHeader>1</GroupHeader> | |
</CheatEntry> | |
</CheatEntries> | |
</CheatEntry> | |
<CheatEntry> | |
<ID>11032</ID> | |
<Description>"Free camera. Toggle: END. Num2/8:Y, Num4/6:X, Num3/9:Z"</Description> | |
<LastState/> | |
<VariableType>Auto Assembler Script</VariableType> | |
<AssemblerScript>[ENABLE] | |
_cameraEnabled: | |
db 1 // sets flag in main script's thread data | |
//"hitman.exe"+4190390: | |
"hitman.exe"+41C5BA8: | |
db 90 90 90 90 90 90 90 90 | |
//"hitman.exe"+4190388: | |
"hitman.exe"+41C5BB0: | |
db 90 90 90 90 90 90 90 90 | |
[DISABLE] | |
_cameraEnabled: | |
db 0 // resets flag in main script's thread data | |
// original camera y/z write code. X write code is re-instated through the flag in the main script and when main | |
// script is disabled. | |
//"hitman.exe"+4190388: | |
"hitman.exe"+41C5BA8: | |
movss [rbx+00000098],xmm0 | |
//"hitman.exe"+4190390: | |
"hitman.exe"+41C5BB0: | |
movss [rbx+00000094],xmm1 | |
</AssemblerScript> | |
<Hotkeys> | |
<Hotkey> | |
<Action>Toggle Activation</Action> | |
<Keys> | |
<Key>35</Key> | |
</Keys> | |
<ID>0</ID> | |
</Hotkey> | |
</Hotkeys> | |
<CheatEntries> | |
<CheatEntry> | |
<ID>11033</ID> | |
<Description>"Alt: speed up. Ctrl: Slow down"</Description> | |
<LastState Value="" RealAddress="00000000"/> | |
<Color>008000</Color> | |
<GroupHeader>1</GroupHeader> | |
</CheatEntry> | |
</CheatEntries> | |
</CheatEntry> | |
</CheatEntries> | |
</CheatEntry> | |
<CheatEntry> | |
<ID>11006</ID> | |
<Description>"Game Speed [F3]"</Description> | |
<LastState/> | |
<Color>000000</Color> | |
<VariableType>Auto Assembler Script</VariableType> | |
<AssemblerScript>[ENABLE] | |
aobscanmodule(timeAOB,hitman.exe,F3 0F 59 43 48 F3 0F 59 05) | |
alloc(newmem,2048,"hitman.exe") | |
label(returnhere) | |
label(exit) | |
label(gameSpeed) | |
registersymbol(gameSpeed) | |
registersymbol(timeAOB) | |
newmem: | |
mov [gameSpeed],rbx | |
mulss xmm0,[rbx+48] | |
jmp exit | |
exit: | |
jmp returnhere | |
// | |
/// | |
gameSpeed: | |
dq 0 | |
/// | |
timeAOB: | |
jmp newmem | |
returnhere: | |
[DISABLE] | |
dealloc(newmem) | |
timeAOB: | |
mulss xmm0,[rbx+48] | |
unregistersymbol(gameSpeed) | |
unregistersymbol(timeAOB) | |
</AssemblerScript> | |
<Hotkeys> | |
<Hotkey> | |
<Action>Activate</Action> | |
<Keys> | |
<Key>114</Key> | |
</Keys> | |
<ID>0</ID> | |
</Hotkey> | |
</Hotkeys> | |
<CheatEntries> | |
<CheatEntry> | |
<ID>10297</ID> | |
<Description>"Resume [F4]"</Description> | |
<LastState Value="" RealAddress="00000000"/> | |
<Color>8000FF</Color> | |
<GroupHeader>1</GroupHeader> | |
</CheatEntry> | |
<CheatEntry> | |
<ID>10296</ID> | |
<Description>"Pause [F3]"</Description> | |
<LastState Value="" RealAddress="00000000"/> | |
<Color>8000FF</Color> | |
<GroupHeader>1</GroupHeader> | |
</CheatEntry> | |
<CheatEntry> | |
<ID>11007</ID> | |
<Description>"Game Speed"</Description> | |
<VariableType>Float</VariableType> | |
<Address>gameSpeed</Address> | |
<Offsets> | |
<Offset>48</Offset> | |
</Offsets> | |
<Hotkeys> | |
<Hotkey> | |
<Action>Set Value</Action> | |
<Keys> | |
<Key>114</Key> | |
</Keys> | |
<Value>0.0001</Value> | |
<ID>0</ID> | |
<ActivateSound/> | |
<DeactivateSound/> | |
</Hotkey> | |
<Hotkey> | |
<Action>Set Value</Action> | |
<Keys> | |
<Key>115</Key> | |
</Keys> | |
<Value>1</Value> | |
<ID>1</ID> | |
<ActivateSound/> | |
<DeactivateSound/> | |
</Hotkey> | |
</Hotkeys> | |
</CheatEntry> | |
</CheatEntries> | |
</CheatEntry> | |
<CheatEntry> | |
<ID>11037</ID> | |
<Description>""</Description> | |
<LastState Value="" RealAddress="00000000"/> | |
<GroupHeader>1</GroupHeader> | |
</CheatEntry> | |
<CheatEntry> | |
<ID>11035</ID> | |
<Description>"By -= Jim2Point0 & Otis / Infuse Project =-"</Description> | |
<LastState Value="" RealAddress="00000000"/> | |
<Color>FF8000</Color> | |
<GroupHeader>1</GroupHeader> | |
</CheatEntry> | |
<CheatEntry> | |
<ID>11036</ID> | |
<Description>"https://www.deadendthrills.com/forum/discussion/512/guide-hitman-2016"</Description> | |
<LastState Value="" RealAddress="00000000"/> | |
<Color>FF8000</Color> | |
<GroupHeader>1</GroupHeader> | |
</CheatEntry> | |
<CheatEntry> | |
<ID>11038</ID> | |
<Description>"For game version: 1.7.0"</Description> | |
<LastState Value="" RealAddress="00000000"/> | |
<Color>0000FF</Color> | |
<GroupHeader>1</GroupHeader> | |
</CheatEntry> | |
</CheatEntries> | |
<CheatCodes> | |
<CodeEntry> | |
<Description>Camera Z</Description> | |
<Address>144190388</Address> | |
<ModuleName>hitman.exe</ModuleName> | |
<ModuleNameOffset>4190388</ModuleNameOffset> | |
<Before> | |
<Byte>0F</Byte> | |
<Byte>10</Byte> | |
<Byte>44</Byte> | |
<Byte>24</Byte> | |
<Byte>58</Byte> | |
</Before> | |
<Actual> | |
<Byte>F3</Byte> | |
<Byte>0F</Byte> | |
<Byte>11</Byte> | |
<Byte>83</Byte> | |
<Byte>98</Byte> | |
<Byte>00</Byte> | |
<Byte>00</Byte> | |
<Byte>00</Byte> | |
</Actual> | |
<After> | |
<Byte>F3</Byte> | |
<Byte>0F</Byte> | |
<Byte>11</Byte> | |
<Byte>8B</Byte> | |
<Byte>94</Byte> | |
</After> | |
</CodeEntry> | |
<CodeEntry> | |
<Description>Camera X</Description> | |
<Address>14419037A</Address> | |
<ModuleName>hitman.exe</ModuleName> | |
<ModuleNameOffset>419037A</ModuleNameOffset> | |
<Before> | |
<Byte>0F</Byte> | |
<Byte>10</Byte> | |
<Byte>44</Byte> | |
<Byte>24</Byte> | |
<Byte>50</Byte> | |
</Before> | |
<Actual> | |
<Byte>F3</Byte> | |
<Byte>0F</Byte> | |
<Byte>11</Byte> | |
<Byte>83</Byte> | |
<Byte>90</Byte> | |
<Byte>00</Byte> | |
<Byte>00</Byte> | |
<Byte>00</Byte> | |
</Actual> | |
<After> | |
<Byte>F3</Byte> | |
<Byte>0F</Byte> | |
<Byte>10</Byte> | |
<Byte>44</Byte> | |
<Byte>24</Byte> | |
</After> | |
</CodeEntry> | |
<CodeEntry> | |
<Description>Camera Y</Description> | |
<Address>144190390</Address> | |
<ModuleName>hitman.exe</ModuleName> | |
<ModuleNameOffset>4190390</ModuleNameOffset> | |
<Before> | |
<Byte>83</Byte> | |
<Byte>98</Byte> | |
<Byte>00</Byte> | |
<Byte>00</Byte> | |
<Byte>00</Byte> | |
</Before> | |
<Actual> | |
<Byte>F3</Byte> | |
<Byte>0F</Byte> | |
<Byte>11</Byte> | |
<Byte>8B</Byte> | |
<Byte>94</Byte> | |
<Byte>00</Byte> | |
<Byte>00</Byte> | |
<Byte>00</Byte> | |
</Actual> | |
<After> | |
<Byte>EB</Byte> | |
<Byte>3B</Byte> | |
<Byte>48</Byte> | |
<Byte>8D</Byte> | |
<Byte>4C</Byte> | |
</After> | |
</CodeEntry> | |
<CodeEntry> | |
<Description>FOV 2</Description> | |
<Address>1444AEA69</Address> | |
<ModuleName>hitman.exe</ModuleName> | |
<ModuleNameOffset>44AEA69</ModuleNameOffset> | |
<Before> | |
<Byte>72</Byte> | |
<Byte>03</Byte> | |
<Byte>0F</Byte> | |
<Byte>28</Byte> | |
<Byte>C1</Byte> | |
</Before> | |
<Actual> | |
<Byte>F3</Byte> | |
<Byte>0F</Byte> | |
<Byte>11</Byte> | |
<Byte>81</Byte> | |
<Byte>7C</Byte> | |
<Byte>01</Byte> | |
<Byte>00</Byte> | |
<Byte>00</Byte> | |
</Actual> | |
<After> | |
<Byte>E9</Byte> | |
<Byte>AA</Byte> | |
<Byte>A8</Byte> | |
<Byte>00</Byte> | |
<Byte>00</Byte> | |
</After> | |
</CodeEntry> | |
<CodeEntry> | |
<Description>FOV 1</Description> | |
<Address>1444AEA47</Address> | |
<ModuleName>hitman.exe</ModuleName> | |
<ModuleNameOffset>44AEA47</ModuleNameOffset> | |
<Before> | |
<Byte>89</Byte> | |
<Byte>FC</Byte> | |
<Byte>00</Byte> | |
<Byte>00</Byte> | |
<Byte>00</Byte> | |
</Before> | |
<Actual> | |
<Byte>74</Byte> | |
<Byte>31</Byte> | |
</Actual> | |
<After> | |
<Byte>F3</Byte> | |
<Byte>0F</Byte> | |
<Byte>10</Byte> | |
<Byte>05</Byte> | |
<Byte>C3</Byte> | |
</After> | |
</CodeEntry> | |
<CodeEntry> | |
<Description>Rotation Matrix?</Description> | |
<Address>14419036D</Address> | |
<ModuleName>hitman.exe</ModuleName> | |
<ModuleNameOffset>419036D</ModuleNameOffset> | |
<Before> | |
<Byte>24</Byte> | |
<Byte>54</Byte> | |
<Byte>0F</Byte> | |
<Byte>28</Byte> | |
<Byte>00</Byte> | |
</Before> | |
<Actual> | |
<Byte>0F</Byte> | |
<Byte>11</Byte> | |
<Byte>83</Byte> | |
<Byte>80</Byte> | |
<Byte>00</Byte> | |
<Byte>00</Byte> | |
<Byte>00</Byte> | |
</Actual> | |
<After> | |
<Byte>F3</Byte> | |
<Byte>0F</Byte> | |
<Byte>10</Byte> | |
<Byte>44</Byte> | |
<Byte>24</Byte> | |
</After> | |
</CodeEntry> | |
</CheatCodes> | |
<UserdefinedSymbols> | |
<SymbolEntry> | |
<Name>pHealth</Name> | |
<Address>34760000</Address> | |
</SymbolEntry> | |
<SymbolEntry> | |
<Name>tHealth</Name> | |
<Address>34760010</Address> | |
</SymbolEntry> | |
<SymbolEntry> | |
<Name>pSkillPts</Name> | |
<Address>04E80020</Address> | |
</SymbolEntry> | |
<SymbolEntry> | |
<Name>AOB4_jmp</Name> | |
<Address>00723165</Address> | |
</SymbolEntry> | |
<SymbolEntry> | |
<Name>pWrath</Name> | |
<Address>04100020</Address> | |
</SymbolEntry> | |
<SymbolEntry> | |
<Name>pCurrency</Name> | |
<Address>05010000</Address> | |
</SymbolEntry> | |
<SymbolEntry> | |
<Name>AOB2_jmp</Name> | |
<Address>00726238</Address> | |
</SymbolEntry> | |
<SymbolEntry> | |
<Name>AOB5_jmp</Name> | |
<Address>00811E9C</Address> | |
</SymbolEntry> | |
<SymbolEntry> | |
<Name>AOB3_jmp</Name> | |
<Address>0078347E</Address> | |
</SymbolEntry> | |
<SymbolEntry> | |
<Name>AOB1_jmp</Name> | |
<Address>007248D2</Address> | |
</SymbolEntry> | |
<SymbolEntry> | |
<Name>AOB6_jmp</Name> | |
<Address>00761711</Address> | |
</SymbolEntry> | |
<SymbolEntry> | |
<Name>_fovAddress</Name> | |
<Address>345A00F1</Address> | |
</SymbolEntry> | |
<SymbolEntry> | |
<Name>_cameraX</Name> | |
<Address>32E50308</Address> | |
</SymbolEntry> | |
<SymbolEntry> | |
<Name>_cameraY</Name> | |
<Address>32E5030C</Address> | |
</SymbolEntry> | |
<SymbolEntry> | |
<Name>_cameraZ</Name> | |
<Address>32E50310</Address> | |
</SymbolEntry> | |
<SymbolEntry> | |
<Name>_altPressed</Name> | |
<Address>32E5031A</Address> | |
</SymbolEntry> | |
<SymbolEntry> | |
<Name>coords</Name> | |
<Address>13FFF00DA</Address> | |
</SymbolEntry> | |
<SymbolEntry> | |
<Name>coords2</Name> | |
<Address>0D3B0042</Address> | |
</SymbolEntry> | |
<SymbolEntry> | |
<Name>ammo</Name> | |
<Address>006F5C80</Address> | |
</SymbolEntry> | |
<SymbolEntry> | |
<Name>invis1</Name> | |
<Address>00A0A926</Address> | |
</SymbolEntry> | |
<SymbolEntry> | |
<Name>coords3</Name> | |
<Address>0D3F0029</Address> | |
</SymbolEntry> | |
<SymbolEntry> | |
<Name>OwnCode</Name> | |
<Address>369D0000</Address> | |
</SymbolEntry> | |
<SymbolEntry> | |
<Name>_fovAOB</Name> | |
<Address>1444AEA47</Address> | |
</SymbolEntry> | |
<SymbolEntry> | |
<Name>toggleLock</Name> | |
<Address>13FFD00E3</Address> | |
</SymbolEntry> | |
<SymbolEntry> | |
<Name>currentMode</Name> | |
<Address>13FFD00DF</Address> | |
</SymbolEntry> | |
</UserdefinedSymbols> | |
<Comments>Info about this table: | |
</Comments> | |
</CheatTable> |
Updated camera for v1.7.0
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
v1.02: Fixed: