make commands actually reply to console

This commit is contained in:
Milxnor
2023-04-03 21:13:34 -04:00
parent fa6fac754a
commit bd4a8da94f
14 changed files with 182 additions and 11 deletions

View File

@@ -0,0 +1,14 @@
#include "EngineTypes.h"
#include "reboot.h"
UStruct* FHitResult::GetStruct()
{
static auto Struct = FindObject<UStruct>("/Script/Engine.HitResult");
return Struct;
}
int FHitResult::GetStructSize()
{
return GetStruct()->GetPropertiesSize();
}

View File

@@ -9,4 +9,10 @@ enum class ESpawnActorCollisionHandlingMethod : uint8
AdjustIfPossibleButAlwaysSpawn, AdjustIfPossibleButAlwaysSpawn,
AdjustIfPossibleButDontSpawnIfColliding, AdjustIfPossibleButDontSpawnIfColliding,
DontSpawnIfColliding DontSpawnIfColliding
};
struct FHitResult
{
static class UStruct* GetStruct();
static int GetStructSize();
}; };

View File

@@ -693,7 +693,7 @@ void AFortGameModeAthena::Athena_HandleStartingNewPlayerHook(AFortGameModeAthena
bool bPrintWarmup = false; bool bPrintWarmup = false;
if (false) if (Engine_Version != 419)
{ {
for (int i = 0; i < SpawnIsland_FloorLoot_Actors.Num(); i++) for (int i = 0; i < SpawnIsland_FloorLoot_Actors.Num(); i++)
{ {

View File

@@ -0,0 +1,76 @@
#include "FortPlayerPawnAthena.h"
#include "FortInventory.h"
#include "FortPlayerControllerAthena.h"
void AFortPlayerPawnAthena::OnCapsuleBeginOverlapHook(UObject* Context, FFrame* Stack, void* Ret)
{
using UPrimitiveComponent = UObject;
auto Pawn = (AFortPlayerPawnAthena*)Context;
UPrimitiveComponent* OverlappedComp;
AActor* OtherActor;
UPrimitiveComponent* OtherComp;
int OtherBodyIndex;
bool bFromSweep;
FHitResult SweepResult = *Alloc<FHitResult>(FHitResult::GetStructSize());
LOG_INFO(LogDev, "OnCapsuleBeginOverlapHook!");
Stack->StepCompiledIn(&OverlappedComp);
Stack->StepCompiledIn(&OtherActor);
Stack->StepCompiledIn(&OtherComp);
Stack->StepCompiledIn(&OtherBodyIndex);
Stack->StepCompiledIn(&bFromSweep);
Stack->StepCompiledIn(&SweepResult);
if (auto Pickup = Cast<AFortPickup>(OtherActor))
{
static auto PawnWhoDroppedPickupOffset = Pickup->GetOffset("PawnWhoDroppedPickup");
if (Pickup->Get<AFortPawn*>(PawnWhoDroppedPickupOffset) != Pawn)
{
auto ItemDefinition = Pickup->GetPrimaryPickupItemEntry()->GetItemDefinition();
auto PlayerController = Cast<AFortPlayerControllerAthena>(Pawn->GetController(), false);
auto& ItemInstances = PlayerController->GetWorldInventory()->GetItemList().GetItemInstances();
bool ItemDefGoingInPrimary = IsPrimaryQuickbar(ItemDefinition);
int PrimarySlotsFilled = 0;
bool bCanStack = false;
bool bFoundStack = false;
for (int i = 0; i < ItemInstances.Num(); i++)
{
auto ItemInstance = ItemInstances.at(i);
auto CurrentItemDefinition = ItemInstance->GetItemEntry()->GetItemDefinition();
if (ItemDefGoingInPrimary && IsPrimaryQuickbar(CurrentItemDefinition))
PrimarySlotsFilled++;
bool bIsInventoryFull = (PrimarySlotsFilled /* - 6 */) >= 5;
if (CurrentItemDefinition == ItemDefinition)
{
bFoundStack = true;
if (ItemInstance->GetItemEntry()->GetCount() < ItemDefinition->GetMaxStackSize())
{
bCanStack = true;
break;
}
}
if (bIsInventoryFull)
return OnCapsuleBeginOverlapOriginal(Context, Stack, Ret);
}
// std::cout << "bCanStack: " << bCanStack << '\n';
// std::cout << "bFoundStack: " << bFoundStack << '\n';
if (!bCanStack ? (!bFoundStack ? true : ItemDefinition->DoesAllowMultipleStacks()) : true)
ServerHandlePickupHook(Pawn, Pickup, 0.4, FVector(), true);
}
}
return OnCapsuleBeginOverlapOriginal(Context, Stack, Ret);
}

View File

@@ -0,0 +1,11 @@
#pragma once
#include "FortPlayerPawn.h"
class AFortPlayerPawnAthena : public AFortPlayerPawn
{
public:
static inline void (*OnCapsuleBeginOverlapOriginal)(UObject* Context, FFrame* Stack, void* Ret);
static void OnCapsuleBeginOverlapHook(UObject* Context, FFrame* Stack, void* Ret);
};

View File

@@ -10,7 +10,7 @@
FNetworkObjectList& UNetDriver::GetNetworkObjectList() FNetworkObjectList& UNetDriver::GetNetworkObjectList()
{ {
return *(*(TSharedPtr<FNetworkObjectList>*)(__int64(this) + 0x490)); return *(*(TSharedPtr<FNetworkObjectList>*)(__int64(this) + Offsets::NetworkObjectList));
} }
void UNetDriver::RemoveNetworkActor(AActor* Actor) void UNetDriver::RemoveNetworkActor(AActor* Actor)

View File

@@ -177,6 +177,7 @@
<ClCompile Include="Controller.cpp" /> <ClCompile Include="Controller.cpp" />
<ClCompile Include="DataTableFunctionLibrary.cpp" /> <ClCompile Include="DataTableFunctionLibrary.cpp" />
<ClCompile Include="dllmain.cpp" /> <ClCompile Include="dllmain.cpp" />
<ClCompile Include="EngineTypes.cpp" />
<ClCompile Include="events.cpp" /> <ClCompile Include="events.cpp" />
<ClCompile Include="FortAthenaCreativePortal.cpp" /> <ClCompile Include="FortAthenaCreativePortal.cpp" />
<ClCompile Include="FortAthenaSupplyDrop.cpp" /> <ClCompile Include="FortAthenaSupplyDrop.cpp" />
@@ -198,6 +199,7 @@
<ClCompile Include="FortPlayerController.cpp" /> <ClCompile Include="FortPlayerController.cpp" />
<ClCompile Include="FortPlayerControllerAthena.cpp" /> <ClCompile Include="FortPlayerControllerAthena.cpp" />
<ClCompile Include="FortPlayerPawn.cpp" /> <ClCompile Include="FortPlayerPawn.cpp" />
<ClCompile Include="FortPlayerPawnAthena.cpp" />
<ClCompile Include="FortPlayerStateAthena.cpp" /> <ClCompile Include="FortPlayerStateAthena.cpp" />
<ClCompile Include="FortPlaysetItemDefinition.cpp" /> <ClCompile Include="FortPlaysetItemDefinition.cpp" />
<ClCompile Include="FortWeapon.cpp" /> <ClCompile Include="FortWeapon.cpp" />
@@ -271,6 +273,7 @@
<ClInclude Include="FortPlayerController.h" /> <ClInclude Include="FortPlayerController.h" />
<ClInclude Include="FortPlayerControllerAthena.h" /> <ClInclude Include="FortPlayerControllerAthena.h" />
<ClInclude Include="FortPlayerPawn.h" /> <ClInclude Include="FortPlayerPawn.h" />
<ClInclude Include="FortPlayerPawnAthena.h" />
<ClInclude Include="FortPlayerState.h" /> <ClInclude Include="FortPlayerState.h" />
<ClInclude Include="FortPlayerStateAthena.h" /> <ClInclude Include="FortPlayerStateAthena.h" />
<ClInclude Include="FortPlaysetItemDefinition.h" /> <ClInclude Include="FortPlaysetItemDefinition.h" />

View File

@@ -173,6 +173,12 @@
<ClCompile Include="NetworkObjectList.cpp"> <ClCompile Include="NetworkObjectList.cpp">
<Filter>Engine\Source\Runtime\Engine\Private</Filter> <Filter>Engine\Source\Runtime\Engine\Private</Filter>
</ClCompile> </ClCompile>
<ClCompile Include="FortPlayerPawnAthena.cpp">
<Filter>FortniteGame\Source\FortniteGame\Private\Pawns</Filter>
</ClCompile>
<ClCompile Include="EngineTypes.cpp">
<Filter>Engine\Source\Runtime\Engine\Private</Filter>
</ClCompile>
</ItemGroup> </ItemGroup>
<ItemGroup> <ItemGroup>
<ClInclude Include="log.h" /> <ClInclude Include="log.h" />
@@ -497,6 +503,9 @@
<ClInclude Include="Level.h"> <ClInclude Include="Level.h">
<Filter>Engine\Source\Runtime\Engine\Classes\Engine</Filter> <Filter>Engine\Source\Runtime\Engine\Classes\Engine</Filter>
</ClInclude> </ClInclude>
<ClInclude Include="FortPlayerPawnAthena.h">
<Filter>FortniteGame\Source\FortniteGame\Public\Pawns</Filter>
</ClInclude>
</ItemGroup> </ItemGroup>
<ItemGroup> <ItemGroup>
<Filter Include="Engine"> <Filter Include="Engine">

View File

@@ -18,16 +18,26 @@ public:
// MORE STUFF HERE // MORE STUFF HERE
void* MostRecentProperty; void* MostRecentProperty; // 48
uint8_t* MostRecentPropertyAddress; uint8_t* MostRecentPropertyAddress; // 56
void*& GetPropertyChainForCompiledIn()
{
static auto PropertyChainForCompiledInOffset = 0x80;
return *(void**)(__int64(this) + PropertyChainForCompiledInOffset);
}
uint8_t*& GetMostRecentPropertyAddress() uint8_t*& GetMostRecentPropertyAddress()
{ {
auto off = (void*)(&((struct FFrame*)NULL)->MostRecentPropertyAddress); auto off = (void*)(&((struct FFrame*)NULL)->MostRecentPropertyAddress);
LOG_INFO(LogDev, "{}", off); LOG_INFO(LogDev, "{}", off);
return MostRecentPropertyAddress; return MostRecentPropertyAddress;
static auto MostRecentPropertyAddressOffset = 56; }
return *(uint8_t**)(__int64(this) + MostRecentPropertyAddressOffset);
void StepExplicitProperty(void* const Result, void* Property)
{
static void (*StepExplicitPropertyOriginal)(__int64 frame, void* const Result, void* Property) = decltype(StepExplicitPropertyOriginal)(Addresses::FrameStepExplicitProperty);
StepExplicitPropertyOriginal(__int64(this), Result, Property);
} }
void Step(UObject* Context, RESULT_DECL) void Step(UObject* Context, RESULT_DECL)
@@ -39,7 +49,7 @@ public:
// (GNatives[B])(Context, *this, RESULT_PARAM); // (GNatives[B])(Context, *this, RESULT_PARAM);
} }
__forceinline void StepCompiledIn(void* Result/*, const FFieldClass* ExpectedPropertyType*/) // https://github.com/EpicGames/UnrealEngine/blob/cdaec5b33ea5d332e51eee4e4866495c90442122/Engine/Source/Runtime/CoreUObject/Public/UObject/Stack.h#L444 __forceinline void StepCompiledIn(void* const Result/*, const FFieldClass* ExpectedPropertyType*/) // https://github.com/EpicGames/UnrealEngine/blob/cdaec5b33ea5d332e51eee4e4866495c90442122/Engine/Source/Runtime/CoreUObject/Public/UObject/Stack.h#L444
{ {
if (Code) if (Code)
{ {
@@ -53,6 +63,10 @@ public:
FProperty* Property = (FProperty*)PropertyChainForCompiledIn; FProperty* Property = (FProperty*)PropertyChainForCompiledIn;
PropertyChainForCompiledIn = Property->Next; PropertyChainForCompiledIn = Property->Next;
StepExplicitProperty(Result, Property); */ StepExplicitProperty(Result, Property); */
auto& Property = GetPropertyChainForCompiledIn();
GetPropertyChainForCompiledIn() = Engine_Version >= 425 ? *(void**)(__int64(Property) + 0x20) : ((UField*)Property)->Next;
StepExplicitProperty(Result, Property);
} }
} }

View File

@@ -239,6 +239,9 @@ void Addresses::FindAll()
LOG_INFO(LogDev, "Finding ActorChannelClose"); LOG_INFO(LogDev, "Finding ActorChannelClose");
Addresses::ActorChannelClose = FindActorChannelClose(); Addresses::ActorChannelClose = FindActorChannelClose();
LOG_INFO(LogDev, "Finding StepExplicitProperty");
Addresses::FrameStepExplicitProperty = FindStepExplicitProperty();
LOG_INFO(LogDev, "Finished finding!"); LOG_INFO(LogDev, "Finished finding!");
} }
@@ -291,6 +294,7 @@ void Addresses::Print()
LOG_INFO(LogDev, "GetMaxTickRate: 0x{:x}", GetMaxTickRate - Base); LOG_INFO(LogDev, "GetMaxTickRate: 0x{:x}", GetMaxTickRate - Base);
LOG_INFO(LogDev, "RemoveFromAlivePlayers: 0x{:x}", RemoveFromAlivePlayers - Base); LOG_INFO(LogDev, "RemoveFromAlivePlayers: 0x{:x}", RemoveFromAlivePlayers - Base);
LOG_INFO(LogDev, "ActorChannelClose: 0x{:x}", ActorChannelClose - Base); LOG_INFO(LogDev, "ActorChannelClose: 0x{:x}", ActorChannelClose - Base);
LOG_INFO(LogDev, "FrameStepExplicitProperty: 0x{:x}", FrameStepExplicitProperty - Base);
} }
void Offsets::FindAll() void Offsets::FindAll()
@@ -332,13 +336,24 @@ void Offsets::FindAll()
Offsets::ServerReplicateActors = 0x67; // checked onb 22.30 Offsets::ServerReplicateActors = 0x67; // checked onb 22.30
if (Engine_Version == 416) // checked on 1.7.2 & 1.8 if (Engine_Version == 416) // checked on 1.7.2 & 1.8
{
Offsets::NetworkObjectList = 0x3F8;
Offsets::ReplicationFrame = 0x288; Offsets::ReplicationFrame = 0x288;
}
if (Fortnite_Version == 2.42) if (Fortnite_Version == 2.42)
{
Offsets::ReplicationFrame = 0x2C8; Offsets::ReplicationFrame = 0x2C8;
}
if (Fortnite_Version == 2.5) if (Fortnite_Version == 2.5)
{
Offsets::NetworkObjectList = 0x4F0;
Offsets::ReplicationFrame = 0x328; Offsets::ReplicationFrame = 0x328;
if (Fortnite_Version == 1.11) }
if (Engine_Version == 419) // checked 2.4.2 & 1.11
{
Offsets::NetworkObjectList = 0x490;
Offsets::ReplicationFrame = 0x2C8; Offsets::ReplicationFrame = 0x2C8;
}
Offsets::IsNetRelevantFor = FindIsNetRelevantForOffset(); Offsets::IsNetRelevantFor = FindIsNetRelevantForOffset();
} }

View File

@@ -53,6 +53,7 @@ namespace Addresses
extern inline uint64 OnRep_ZiplineState = 0; extern inline uint64 OnRep_ZiplineState = 0;
extern inline uint64 RemoveFromAlivePlayers = 0; extern inline uint64 RemoveFromAlivePlayers = 0;
extern inline uint64 ActorChannelClose = 0; extern inline uint64 ActorChannelClose = 0;
extern inline uint64 FrameStepExplicitProperty = 0;
void SetupVersion(); // Finds Engine Version void SetupVersion(); // Finds Engine Version
void FindAll(); void FindAll();
@@ -72,6 +73,7 @@ namespace Offsets
extern inline uint64 ServerReplicateActors = 0; extern inline uint64 ServerReplicateActors = 0;
extern inline uint64 ReplicationFrame = 0; extern inline uint64 ReplicationFrame = 0;
extern inline uint64 IsNetRelevantFor = 0; extern inline uint64 IsNetRelevantFor = 0;
extern inline uint64 NetworkObjectList = 0;
void FindAll(); void FindAll();
void Print(); void Print();

View File

@@ -24,9 +24,18 @@ inline void SendMessageToConsole(AFortPlayerController* PlayerController, const
float MsgLifetime = 1; // unused by ue float MsgLifetime = 1; // unused by ue
FName TypeName = FName(); // auto set to "Event" FName TypeName = FName(); // auto set to "Event"
// PlayerController->ClientMessage(Msg, TypeName, MsgLifetime); static auto ClientMessageFn = FindObject<UFunction>("/Script/Engine.PlayerController.ClientMessage");
auto brah = Msg.ToString(); struct
LOG_INFO(LogDev, "{}", brah); {
FString S; // (Parm, ZeroConstructor, HasGetValueTypeHash, NativeAccessSpecifierPublic)
FName Type; // (Parm, ZeroConstructor, IsPlainOldData, NoDestructor, HasGetValueTypeHash, NativeAccessSpecifierPublic)
float MsgLifeTime; // (Parm, ZeroConstructor, IsPlainOldData, NoDestructor, HasGetValueTypeHash, NativeAccessSpecifierPublic)
} APlayerController_ClientMessage_Params{Msg, TypeName, MsgLifetime};
PlayerController->ProcessEvent(ClientMessageFn, &APlayerController_ClientMessage_Params);
// auto brah = Msg.ToString();
// LOG_INFO(LogDev, "{}", brah);
} }
void ServerCheatHook(AFortPlayerControllerAthena* PlayerController, FString Msg) void ServerCheatHook(AFortPlayerControllerAthena* PlayerController, FString Msg)
@@ -435,6 +444,7 @@ void ServerCheatHook(AFortPlayerControllerAthena* PlayerController, FString Msg)
} }
Pawn->TeleportTo(FVector(X, Y, Z), Pawn->GetActorRotation()); Pawn->TeleportTo(FVector(X, Y, Z), Pawn->GetActorRotation());
SendMessageToConsole(PlayerController, L"Teleported!");
} }
} }
} }

View File

@@ -25,6 +25,7 @@
#include "KismetSystemLibrary.h" #include "KismetSystemLibrary.h"
#include "die.h" #include "die.h"
#include "InventoryManagementLibrary.h" #include "InventoryManagementLibrary.h"
#include "FortPlayerPawnAthena.h"
enum ENetMode enum ENetMode
{ {
@@ -330,6 +331,9 @@ DWORD WINAPI Main(LPVOID)
} }
} }
auto off = (void*)(&((struct FFrame*)NULL)->MostRecentPropertyAddress);
LOG_INFO(LogDev, "{}", off);
LOG_INFO(LogDev, "OnPlayImpactFX: 0x{:x}", OnPlayImpactFXAddr - __int64(GetModuleHandleW(0))); LOG_INFO(LogDev, "OnPlayImpactFX: 0x{:x}", OnPlayImpactFXAddr - __int64(GetModuleHandleW(0)));
Hooking::MinHook::Hook((PVOID)OnPlayImpactFXAddr, AFortWeapon::OnPlayImpactFXHook, (PVOID*)&AFortWeapon::OnPlayImpactFXOriginal); Hooking::MinHook::Hook((PVOID)OnPlayImpactFXAddr, AFortWeapon::OnPlayImpactFXHook, (PVOID*)&AFortWeapon::OnPlayImpactFXOriginal);
@@ -370,6 +374,8 @@ DWORD WINAPI Main(LPVOID)
AFortPawn::NetMulticast_Athena_BatchedDamageCuesHook, (PVOID*)&AFortPawn::NetMulticast_Athena_BatchedDamageCuesOriginal, false, true); AFortPawn::NetMulticast_Athena_BatchedDamageCuesHook, (PVOID*)&AFortPawn::NetMulticast_Athena_BatchedDamageCuesOriginal, false, true);
Hooking::MinHook::Hook(FortPlayerPawnAthenaDefault, FindObject<UFunction>(L"/Script/FortniteGame.FortPlayerPawn.ServerSendZiplineState"), Hooking::MinHook::Hook(FortPlayerPawnAthenaDefault, FindObject<UFunction>(L"/Script/FortniteGame.FortPlayerPawn.ServerSendZiplineState"),
AFortPlayerPawn::ServerSendZiplineStateHook, nullptr, false); AFortPlayerPawn::ServerSendZiplineStateHook, nullptr, false);
/* Hooking::MinHook::Hook(FortPlayerPawnAthenaDefault, FindObject<UFunction>(L"/Script/FortniteGame.FortPlayerPawnAthena.OnCapsuleBeginOverlap") ? FindObject<UFunction>(L"/Script/FortniteGame.FortPlayerPawnAthena.OnCapsuleBeginOverlap") : FindObject<UFunction>(L"/Script/FortniteGame.FortPlayerPawn.OnCapsuleBeginOverlap"),
AFortPlayerPawnAthena::OnCapsuleBeginOverlapHook, (PVOID*)&AFortPlayerPawnAthena::OnCapsuleBeginOverlapOriginal, false, true); */
if (Addresses::FrameStep) // put all non rpc exec hooks in this scope if (Addresses::FrameStep) // put all non rpc exec hooks in this scope
{ {

View File

@@ -363,6 +363,11 @@ static inline uint64 FindGetPlayerViewpoint()
return 0; return 0;
} }
static inline uint64 FindStepExplicitProperty()
{
return Memcury::Scanner::FindPattern("41 8B 40 ? 4D 8B C8").Get();
}
static inline uint64 FindIsNetRelevantForOffset() static inline uint64 FindIsNetRelevantForOffset()
{ {
if (Engine_Version == 416) // checked on 1.7.2 & 1.8 if (Engine_Version == 416) // checked on 1.7.2 & 1.8