Probe GPS async route worker
This commit is contained in:
@@ -150,6 +150,12 @@ constexpr uintptr_t kGpsQuerySubmitRva = 0x070A42C;
|
||||
constexpr uintptr_t kGpsQueryDispatchRva = 0x070A570;
|
||||
constexpr uintptr_t kGpsQueryResultFetchRva = 0x07094B8;
|
||||
constexpr uintptr_t kGpsQueryStatusRva = 0x0AA5704;
|
||||
constexpr uintptr_t kGpsDispatchAdvanceRva = 0x08D17D8;
|
||||
constexpr uintptr_t kGpsAsyncWorkerTickRva = 0x0126B28;
|
||||
constexpr uintptr_t kGpsRouteJobStartRva = 0x0818928;
|
||||
constexpr uintptr_t kGpsRouteJobPollRva = 0x0883CD8;
|
||||
constexpr uintptr_t kGpsRouteFinishRva = 0x11F5F60;
|
||||
constexpr uintptr_t kGpsRouteJobBuildRva = 0x0818BA8;
|
||||
constexpr uintptr_t kGpsRouteProducerRva = 0x044CC7C;
|
||||
constexpr uintptr_t kGpsSearchRva = 0x044F054;
|
||||
constexpr uintptr_t kGpsEdgeCostRva = 0x044F838;
|
||||
@@ -213,11 +219,18 @@ uint32_t gGpsQuerySubmitLogCount = 0;
|
||||
uint32_t gGpsQueryDispatchLogCount = 0;
|
||||
uint32_t gGpsQueryResultFetchLogCount = 0;
|
||||
uint32_t gGpsQueryStatusLogCount = 0;
|
||||
uint32_t gGpsDispatchAdvanceLogCount = 0;
|
||||
uint32_t gGpsAsyncWorkerTickLogCount = 0;
|
||||
uint32_t gGpsRouteJobStartLogCount = 0;
|
||||
uint32_t gGpsRouteJobPollLogCount = 0;
|
||||
uint32_t gGpsRouteFinishLogCount = 0;
|
||||
uint32_t gGpsRouteJobBuildLogCount = 0;
|
||||
uint32_t gGpsRouteProducerLogCount = 0;
|
||||
uint32_t gGpsSearchLogCount = 0;
|
||||
uint32_t gGpsEdgeCostLogCount = 0;
|
||||
std::array<uint32_t, 64> gGpsEdgeCostClassLogCounts{};
|
||||
std::mutex gGpsCostLogMutex;
|
||||
std::mutex gGpsAsyncLogMutex;
|
||||
uint64_t gLogStartTick = 0;
|
||||
uint64_t gLogFrequency = 0;
|
||||
void* gMappinSetTrackedTarget = nullptr;
|
||||
@@ -312,6 +325,13 @@ using GpsQuerySubmitFunc = int32_t (*)(void* aManager, void* aQuery);
|
||||
using GpsQueryDispatchFunc = void (*)(void* aRuntimeQuery, void* aTargetPosition, void* aArg3, void* aArg4);
|
||||
using GpsQueryResultFetchFunc = bool (*)(void* aManager, uint32_t aQueryId, void* aOutPath);
|
||||
using GpsQueryStatusFunc = int32_t (*)(void* aManager, uint32_t aQueryId);
|
||||
using GpsDispatchAdvanceFunc = void (*)(void* aRouteSystem, void* aRuntimeQuery, void* aOutTicket,
|
||||
void* aTargetPosition, void* aSourcePosition);
|
||||
using GpsAsyncWorkerTickFunc = void (*)(void* aRouteSystem);
|
||||
using GpsRouteJobStartFunc = bool (*)(void* aRouteSystem, void* aActiveEntry, float aDelta, void* aOutLocal);
|
||||
using GpsRouteJobPollFunc = bool (*)(void* aRouteSystem, void* aActiveEntry);
|
||||
using GpsRouteFinishFunc = void* (*)(void* aResultQueue, void* aOutEntry, void* aActiveEntry, void* aLocalResult);
|
||||
using GpsRouteJobBuildFunc = void* (*)(void* aJob, void* aOut, void* aRequest);
|
||||
using GpsRouteProducerFunc = int32_t (*)(void* aGraph, void* aQuery, void* aOutResult);
|
||||
using GpsSearchFunc = int32_t (*)(void* aGraph, uint64_t aStartHandle, uint64_t aTargetHandle, void* aStartPoint,
|
||||
void* aTargetPoint, void* aCostProvider, void* aOutPath, uint32_t* aOutCount);
|
||||
@@ -370,6 +390,12 @@ GpsQuerySubmitFunc gOriginalGpsQuerySubmit = nullptr;
|
||||
GpsQueryDispatchFunc gOriginalGpsQueryDispatch = nullptr;
|
||||
GpsQueryResultFetchFunc gOriginalGpsQueryResultFetch = nullptr;
|
||||
GpsQueryStatusFunc gOriginalGpsQueryStatus = nullptr;
|
||||
GpsDispatchAdvanceFunc gOriginalGpsDispatchAdvance = nullptr;
|
||||
GpsAsyncWorkerTickFunc gOriginalGpsAsyncWorkerTick = nullptr;
|
||||
GpsRouteJobStartFunc gOriginalGpsRouteJobStart = nullptr;
|
||||
GpsRouteJobPollFunc gOriginalGpsRouteJobPoll = nullptr;
|
||||
GpsRouteFinishFunc gOriginalGpsRouteFinish = nullptr;
|
||||
GpsRouteJobBuildFunc gOriginalGpsRouteJobBuild = nullptr;
|
||||
GpsRouteProducerFunc gOriginalGpsRouteProducer = nullptr;
|
||||
GpsSearchFunc gOriginalGpsSearch = nullptr;
|
||||
GpsEdgeCostFunc gOriginalGpsEdgeCost = nullptr;
|
||||
@@ -1414,6 +1440,138 @@ void AppendGpsResultObjectSummary(std::ostringstream& aLine, const char* aPrefix
|
||||
AppendUint64Field(aLine, (std::string(aPrefix) + "_u50").c_str(), aResultObject, 0x50);
|
||||
}
|
||||
|
||||
uint32_t NextGpsAsyncLogCall(uint32_t& aCounter)
|
||||
{
|
||||
std::lock_guard lock(gGpsAsyncLogMutex);
|
||||
return aCounter++;
|
||||
}
|
||||
|
||||
bool TryReadUint32FieldValue(void* aObject, uintptr_t aOffset, uint32_t& aValue)
|
||||
{
|
||||
return aObject && TryReadMemory(reinterpret_cast<const void*>(reinterpret_cast<uintptr_t>(aObject) + aOffset),
|
||||
aValue);
|
||||
}
|
||||
|
||||
void AppendRouteJobSummary(std::ostringstream& aLine, const char* aPrefix, void* aJob)
|
||||
{
|
||||
const auto prefix = std::string(aPrefix);
|
||||
AppendPointerWithRva(aLine, prefix.c_str(), aJob);
|
||||
if (!aJob)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
AppendUint32Field(aLine, (prefix + "_type10").c_str(), aJob, 0x10);
|
||||
AppendPointerField(aLine, (prefix + "_result18").c_str(), aJob, 0x18);
|
||||
AppendPointerField(aLine, (prefix + "_result30").c_str(), aJob, 0x30);
|
||||
AppendUint32Field(aLine, (prefix + "_u4c").c_str(), aJob, 0x4C);
|
||||
AppendUint32Field(aLine, (prefix + "_count50").c_str(), aJob, 0x50);
|
||||
AppendUint32Field(aLine, (prefix + "_retry54").c_str(), aJob, 0x54);
|
||||
AppendUint32Field(aLine, (prefix + "_flagsc0").c_str(), aJob, 0xC0);
|
||||
AppendUint32Field(aLine, (prefix + "_statec4").c_str(), aJob, 0xC4);
|
||||
AppendPointerField(aLine, (prefix + "_chunkse0").c_str(), aJob, 0xE0);
|
||||
AppendUint32Field(aLine, (prefix + "_chunks_cap_e8").c_str(), aJob, 0xE8);
|
||||
AppendUint32Field(aLine, (prefix + "_chunks_count_ec").c_str(), aJob, 0xEC);
|
||||
AppendPointerField(aLine, (prefix + "_nodesf8").c_str(), aJob, 0xF8);
|
||||
}
|
||||
|
||||
void AppendRouteSystemSummary(std::ostringstream& aLine, const char* aPrefix, void* aRouteSystem)
|
||||
{
|
||||
const auto prefix = std::string(aPrefix);
|
||||
AppendPointerWithRva(aLine, prefix.c_str(), aRouteSystem);
|
||||
if (!aRouteSystem)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
AppendUint32Field(aLine, (prefix + "_queued8fc0").c_str(), aRouteSystem, 0x8FC0);
|
||||
AppendUint32Field(aLine, (prefix + "_active8fd0").c_str(), aRouteSystem, 0x8FD0);
|
||||
AppendPointerField(aLine, (prefix + "_job90d0").c_str(), aRouteSystem, 0x90D0);
|
||||
|
||||
auto* job = ReadPointerField(aRouteSystem, 0x90D0);
|
||||
if (!job)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
AppendRouteJobSummary(aLine, (prefix + "_job").c_str(), job);
|
||||
}
|
||||
|
||||
bool HasPendingRouteWork(void* aRouteSystem)
|
||||
{
|
||||
uint32_t queued = 0;
|
||||
uint32_t active = 0;
|
||||
TryReadUint32FieldValue(aRouteSystem, 0x8FC0, queued);
|
||||
TryReadUint32FieldValue(aRouteSystem, 0x8FD0, active);
|
||||
return queued != 0 || active != 0 || ReadPointerField(aRouteSystem, 0x90D0) != nullptr;
|
||||
}
|
||||
|
||||
void AppendRouteRequestFields(std::ostringstream& aLine, const char* aPrefix, void* aObject, uintptr_t aOffset)
|
||||
{
|
||||
const auto prefix = std::string(aPrefix);
|
||||
auto* base = aObject ? reinterpret_cast<void*>(reinterpret_cast<uintptr_t>(aObject) + aOffset) : nullptr;
|
||||
AppendPointerWithRva(aLine, prefix.c_str(), base);
|
||||
if (!base)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
AppendBytesPointer(aLine, (prefix + "_raw40").c_str(), base, 0x40);
|
||||
AppendVector4Field(aLine, (prefix + "_vec00").c_str(), base, 0x00);
|
||||
AppendVector4Field(aLine, (prefix + "_vec10").c_str(), base, 0x10);
|
||||
AppendUint32Field(aLine, (prefix + "_u00").c_str(), base, 0x00);
|
||||
AppendUint32Field(aLine, (prefix + "_u08").c_str(), base, 0x08);
|
||||
AppendUint32Field(aLine, (prefix + "_u1c").c_str(), base, 0x1C);
|
||||
AppendUint16Field(aLine, (prefix + "_u1e").c_str(), base, 0x1E);
|
||||
AppendUint32Field(aLine, (prefix + "_u20").c_str(), base, 0x20);
|
||||
AppendUint16Field(aLine, (prefix + "_u20w").c_str(), base, 0x20);
|
||||
AppendUint16Field(aLine, (prefix + "_u24").c_str(), base, 0x24);
|
||||
AppendUint16Field(aLine, (prefix + "_u26").c_str(), base, 0x26);
|
||||
AppendUint16Field(aLine, (prefix + "_u28").c_str(), base, 0x28);
|
||||
AppendUint32Field(aLine, (prefix + "_u70").c_str(), base, 0x70);
|
||||
AppendByteField(aLine, (prefix + "_b74").c_str(), base, 0x74);
|
||||
AppendByteField(aLine, (prefix + "_b75").c_str(), base, 0x75);
|
||||
AppendByteField(aLine, (prefix + "_b76").c_str(), base, 0x76);
|
||||
AppendByteField(aLine, (prefix + "_b77").c_str(), base, 0x77);
|
||||
}
|
||||
|
||||
void AppendRouteQueueEntrySummary(std::ostringstream& aLine, const char* aPrefix, void* aEntry)
|
||||
{
|
||||
const auto prefix = std::string(aPrefix);
|
||||
AppendPointerWithRva(aLine, prefix.c_str(), aEntry);
|
||||
if (!aEntry)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
AppendUint32Field(aLine, (prefix + "_id00").c_str(), aEntry, 0x00);
|
||||
AppendRouteRequestFields(aLine, (prefix + "_payload10").c_str(), aEntry, 0x10);
|
||||
AppendPointerField(aLine, (prefix + "_vtable40").c_str(), aEntry, 0x40);
|
||||
AppendPointerField(aLine, (prefix + "_self78").c_str(), aEntry, 0x78);
|
||||
AppendUint32Field(aLine, (prefix + "_u80").c_str(), aEntry, 0x80);
|
||||
AppendByteField(aLine, (prefix + "_b84").c_str(), aEntry, 0x84);
|
||||
AppendByteField(aLine, (prefix + "_b85").c_str(), aEntry, 0x85);
|
||||
AppendByteField(aLine, (prefix + "_b86").c_str(), aEntry, 0x86);
|
||||
AppendByteField(aLine, (prefix + "_b87").c_str(), aEntry, 0x87);
|
||||
}
|
||||
|
||||
void AppendRouteOutputPointerSummary(std::ostringstream& aLine, const char* aPrefix, void* aOut)
|
||||
{
|
||||
const auto prefix = std::string(aPrefix);
|
||||
AppendPointerWithRva(aLine, prefix.c_str(), aOut);
|
||||
if (!aOut)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
auto* value = ReadPointerField(aOut, 0x00);
|
||||
AppendPointerWithRva(aLine, (prefix + "_value").c_str(), value);
|
||||
if (value && IsReadableMemory(value, 0x58))
|
||||
{
|
||||
AppendGpsResultObjectSummary(aLine, (prefix + "_result").c_str(), value);
|
||||
}
|
||||
}
|
||||
|
||||
void TrackGpsQuery(uint32_t aQueryId, void* aManager, uintptr_t aSubmitReturnRva, uint32_t aSubmitCall)
|
||||
{
|
||||
if (aQueryId == UINT32_MAX)
|
||||
@@ -2841,6 +2999,216 @@ int32_t DetourGpsQueryStatus(void* aManager, uint32_t aQueryId)
|
||||
return result;
|
||||
}
|
||||
|
||||
void DetourGpsDispatchAdvance(void* aRouteSystem, void* aRuntimeQuery, void* aOutTicket, void* aTargetPosition,
|
||||
void* aSourcePosition)
|
||||
{
|
||||
constexpr uint32_t kMaxCalls = 128;
|
||||
|
||||
const auto callCount = NextGpsAsyncLogCall(gGpsDispatchAdvanceLogCount);
|
||||
const auto shouldLog = callCount < kMaxCalls;
|
||||
if (shouldLog)
|
||||
{
|
||||
std::ostringstream line;
|
||||
line << "hook GPSDispatchAdvance 0x8d17d8 call=" << callCount;
|
||||
AppendRouteSystemSummary(line, "routeSystem", aRouteSystem);
|
||||
AppendPointerWithRva(line, "runtimeQuery", aRuntimeQuery);
|
||||
AppendPointerWithRva(line, "outTicket", aOutTicket);
|
||||
AppendUint32Field(line, "runtimeQuery_state138", aRuntimeQuery, 0x138);
|
||||
AppendUint32Field(line, "runtimeQuery_bank13c", aRuntimeQuery, 0x13C);
|
||||
AppendVector4Pointer(line, "target", aTargetPosition);
|
||||
AppendVector4Pointer(line, "source", aSourcePosition);
|
||||
AppendReturnRva(line, __builtin_return_address(0));
|
||||
LogRed4ext(line.str());
|
||||
}
|
||||
|
||||
if (gOriginalGpsDispatchAdvance)
|
||||
{
|
||||
gOriginalGpsDispatchAdvance(aRouteSystem, aRuntimeQuery, aOutTicket, aTargetPosition, aSourcePosition);
|
||||
}
|
||||
|
||||
if (shouldLog)
|
||||
{
|
||||
std::ostringstream line;
|
||||
line << "hook GPSDispatchAdvance result call=" << callCount;
|
||||
AppendUint32Field(line, "outTicket_value", aOutTicket, 0x00);
|
||||
AppendRouteSystemSummary(line, "routeSystem", aRouteSystem);
|
||||
LogRed4ext(line.str());
|
||||
}
|
||||
}
|
||||
|
||||
void DetourGpsAsyncWorkerTick(void* aRouteSystem)
|
||||
{
|
||||
constexpr uint32_t kMaxCalls = 192;
|
||||
|
||||
const auto callCount = NextGpsAsyncLogCall(gGpsAsyncWorkerTickLogCount);
|
||||
const auto shouldLogBefore = callCount < 16 || (callCount < kMaxCalls && HasPendingRouteWork(aRouteSystem));
|
||||
if (shouldLogBefore)
|
||||
{
|
||||
std::ostringstream line;
|
||||
line << "hook GPSAsyncWorkerTick 0x126b28 call=" << callCount;
|
||||
AppendRouteSystemSummary(line, "routeSystem", aRouteSystem);
|
||||
AppendReturnRva(line, __builtin_return_address(0));
|
||||
LogRed4ext(line.str());
|
||||
}
|
||||
|
||||
if (gOriginalGpsAsyncWorkerTick)
|
||||
{
|
||||
gOriginalGpsAsyncWorkerTick(aRouteSystem);
|
||||
}
|
||||
|
||||
const auto shouldLogAfter = shouldLogBefore || (callCount < kMaxCalls && HasPendingRouteWork(aRouteSystem));
|
||||
if (shouldLogAfter)
|
||||
{
|
||||
std::ostringstream line;
|
||||
line << "hook GPSAsyncWorkerTick result call=" << callCount;
|
||||
AppendRouteSystemSummary(line, "routeSystem", aRouteSystem);
|
||||
LogRed4ext(line.str());
|
||||
}
|
||||
}
|
||||
|
||||
bool DetourGpsRouteJobStart(void* aRouteSystem, void* aActiveEntry, float aDelta, void* aOutLocal)
|
||||
{
|
||||
constexpr uint32_t kMaxCalls = 128;
|
||||
|
||||
const auto callCount = NextGpsAsyncLogCall(gGpsRouteJobStartLogCount);
|
||||
const auto shouldLog = callCount < kMaxCalls;
|
||||
if (shouldLog)
|
||||
{
|
||||
std::ostringstream line;
|
||||
line << "hook GPSRouteJobStart 0x818928 call=" << callCount << " dt=" << aDelta;
|
||||
AppendRouteSystemSummary(line, "routeSystem", aRouteSystem);
|
||||
AppendRouteQueueEntrySummary(line, "activeEntry", aActiveEntry);
|
||||
AppendRouteOutputPointerSummary(line, "outLocal", aOutLocal);
|
||||
AppendReturnRva(line, __builtin_return_address(0));
|
||||
LogRed4ext(line.str());
|
||||
}
|
||||
|
||||
bool result = false;
|
||||
if (gOriginalGpsRouteJobStart)
|
||||
{
|
||||
result = gOriginalGpsRouteJobStart(aRouteSystem, aActiveEntry, aDelta, aOutLocal);
|
||||
}
|
||||
|
||||
if (shouldLog)
|
||||
{
|
||||
std::ostringstream line;
|
||||
line << "hook GPSRouteJobStart result call=" << callCount << " value=" << static_cast<uint32_t>(result);
|
||||
AppendRouteSystemSummary(line, "routeSystem", aRouteSystem);
|
||||
AppendRouteQueueEntrySummary(line, "activeEntry", aActiveEntry);
|
||||
AppendRouteOutputPointerSummary(line, "outLocal", aOutLocal);
|
||||
LogRed4ext(line.str());
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
bool DetourGpsRouteJobPoll(void* aRouteSystem, void* aActiveEntry)
|
||||
{
|
||||
constexpr uint32_t kMaxCalls = 128;
|
||||
|
||||
const auto callCount = NextGpsAsyncLogCall(gGpsRouteJobPollLogCount);
|
||||
const auto shouldLog = callCount < kMaxCalls;
|
||||
if (shouldLog)
|
||||
{
|
||||
std::ostringstream line;
|
||||
line << "hook GPSRouteJobPoll 0x883cd8 call=" << callCount;
|
||||
AppendRouteSystemSummary(line, "routeSystem", aRouteSystem);
|
||||
AppendRouteQueueEntrySummary(line, "activeEntry", aActiveEntry);
|
||||
AppendReturnRva(line, __builtin_return_address(0));
|
||||
LogRed4ext(line.str());
|
||||
}
|
||||
|
||||
bool result = false;
|
||||
if (gOriginalGpsRouteJobPoll)
|
||||
{
|
||||
result = gOriginalGpsRouteJobPoll(aRouteSystem, aActiveEntry);
|
||||
}
|
||||
|
||||
if (shouldLog || result)
|
||||
{
|
||||
std::ostringstream line;
|
||||
line << "hook GPSRouteJobPoll result call=" << callCount << " value=" << static_cast<uint32_t>(result);
|
||||
AppendRouteSystemSummary(line, "routeSystem", aRouteSystem);
|
||||
AppendRouteQueueEntrySummary(line, "activeEntry", aActiveEntry);
|
||||
LogRed4ext(line.str());
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
void* DetourGpsRouteFinish(void* aResultQueue, void* aOutEntry, void* aActiveEntry, void* aLocalResult)
|
||||
{
|
||||
constexpr uint32_t kMaxCalls = 128;
|
||||
|
||||
const auto callCount = NextGpsAsyncLogCall(gGpsRouteFinishLogCount);
|
||||
const auto shouldLog = callCount < kMaxCalls;
|
||||
if (shouldLog)
|
||||
{
|
||||
std::ostringstream line;
|
||||
line << "hook GPSRouteFinish 0x11f5f60 call=" << callCount;
|
||||
AppendPointerWithRva(line, "resultQueue", aResultQueue);
|
||||
AppendRouteQueueEntrySummary(line, "activeEntry", aActiveEntry);
|
||||
AppendRouteOutputPointerSummary(line, "localResult", aLocalResult);
|
||||
AppendPointerWithRva(line, "outEntry", aOutEntry);
|
||||
AppendReturnRva(line, __builtin_return_address(0));
|
||||
LogRed4ext(line.str());
|
||||
}
|
||||
|
||||
void* result = nullptr;
|
||||
if (gOriginalGpsRouteFinish)
|
||||
{
|
||||
result = gOriginalGpsRouteFinish(aResultQueue, aOutEntry, aActiveEntry, aLocalResult);
|
||||
}
|
||||
|
||||
if (shouldLog)
|
||||
{
|
||||
std::ostringstream line;
|
||||
line << "hook GPSRouteFinish result call=" << callCount;
|
||||
AppendPointerWithRva(line, "value", result);
|
||||
AppendRouteOutputPointerSummary(line, "localResult", aLocalResult);
|
||||
AppendPointerWithRva(line, "outEntry", aOutEntry);
|
||||
LogRed4ext(line.str());
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
void* DetourGpsRouteJobBuild(void* aJob, void* aOut, void* aRequest)
|
||||
{
|
||||
constexpr uint32_t kMaxCalls = 128;
|
||||
|
||||
const auto callCount = NextGpsAsyncLogCall(gGpsRouteJobBuildLogCount);
|
||||
const auto shouldLog = callCount < kMaxCalls;
|
||||
if (shouldLog)
|
||||
{
|
||||
std::ostringstream line;
|
||||
line << "hook GPSRouteJobBuild 0x818ba8 call=" << callCount;
|
||||
AppendRouteJobSummary(line, "job", aJob);
|
||||
AppendRouteOutputPointerSummary(line, "out", aOut);
|
||||
AppendRouteRequestFields(line, "request", aRequest, 0x00);
|
||||
AppendReturnRva(line, __builtin_return_address(0));
|
||||
LogRed4ext(line.str());
|
||||
}
|
||||
|
||||
void* result = nullptr;
|
||||
if (gOriginalGpsRouteJobBuild)
|
||||
{
|
||||
result = gOriginalGpsRouteJobBuild(aJob, aOut, aRequest);
|
||||
}
|
||||
|
||||
if (shouldLog)
|
||||
{
|
||||
std::ostringstream line;
|
||||
line << "hook GPSRouteJobBuild result call=" << callCount;
|
||||
AppendPointerWithRva(line, "value", result);
|
||||
AppendRouteOutputPointerSummary(line, "out", aOut);
|
||||
AppendRouteJobSummary(line, "job", aJob);
|
||||
LogRed4ext(line.str());
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
int32_t DetourGpsRouteProducer(void* aGraph, void* aQuery, void* aOutResult)
|
||||
{
|
||||
constexpr uint32_t kMaxCalls = 512;
|
||||
@@ -3361,6 +3729,24 @@ RED4EXT_C_EXPORT bool RED4EXT_CALL Main(RED4ext::v1::PluginHandle aHandle, RED4e
|
||||
AttachProbeHook("GPSQueryStatus 0xaa5704", kGpsQueryStatusRva,
|
||||
reinterpret_cast<void*>(&DetourGpsQueryStatus),
|
||||
reinterpret_cast<void**>(&gOriginalGpsQueryStatus));
|
||||
AttachProbeHook("GPSDispatchAdvance 0x8d17d8", kGpsDispatchAdvanceRva,
|
||||
reinterpret_cast<void*>(&DetourGpsDispatchAdvance),
|
||||
reinterpret_cast<void**>(&gOriginalGpsDispatchAdvance));
|
||||
AttachProbeHook("GPSAsyncWorkerTick 0x126b28", kGpsAsyncWorkerTickRva,
|
||||
reinterpret_cast<void*>(&DetourGpsAsyncWorkerTick),
|
||||
reinterpret_cast<void**>(&gOriginalGpsAsyncWorkerTick));
|
||||
AttachProbeHook("GPSRouteJobStart 0x818928", kGpsRouteJobStartRva,
|
||||
reinterpret_cast<void*>(&DetourGpsRouteJobStart),
|
||||
reinterpret_cast<void**>(&gOriginalGpsRouteJobStart));
|
||||
AttachProbeHook("GPSRouteJobPoll 0x883cd8", kGpsRouteJobPollRva,
|
||||
reinterpret_cast<void*>(&DetourGpsRouteJobPoll),
|
||||
reinterpret_cast<void**>(&gOriginalGpsRouteJobPoll));
|
||||
AttachProbeHook("GPSRouteFinish 0x11f5f60", kGpsRouteFinishRva,
|
||||
reinterpret_cast<void*>(&DetourGpsRouteFinish),
|
||||
reinterpret_cast<void**>(&gOriginalGpsRouteFinish));
|
||||
AttachProbeHook("GPSRouteJobBuild 0x818ba8", kGpsRouteJobBuildRva,
|
||||
reinterpret_cast<void*>(&DetourGpsRouteJobBuild),
|
||||
reinterpret_cast<void**>(&gOriginalGpsRouteJobBuild));
|
||||
AttachProbeHook("GPSRouteProducer 0x44cc7c", kGpsRouteProducerRva,
|
||||
reinterpret_cast<void*>(&DetourGpsRouteProducer),
|
||||
reinterpret_cast<void**>(&gOriginalGpsRouteProducer));
|
||||
|
||||
Reference in New Issue
Block a user