HitchTimeQuotaMS
HitchTimeQuotaMS
#Overview
name: HitchTimeQuotaMS
The value of this variable can be defined or overridden in .ini config files. 3
.ini config files referencing this setting variable.
It is referenced in 9
C++ source files.
#Summary
#Usage in the C++ source code
The purpose of HitchTimeQuotaMS is to detect frame hitches in Unreal Engine’s networking system, specifically for preventing false positives in DDoS (Distributed Denial of Service) and RPC (Remote Procedure Call) DoS detection.
This setting variable is primarily used in the networking subsystem of Unreal Engine, particularly in the DDoS detection and RPC DoS detection modules. It’s referenced in the Engine and Net/Core modules.
The value of this variable is typically set through configuration files. It’s loaded from the game’s configuration (GEngineIni) in the FDDoSDetection::InitConfig function and from a configuration object in the FRPCDoSDetection::InitConfig function.
HitchTimeQuotaMS interacts with several other variables, including:
- HitchSuspendDetectionTimeMS
- HitchFrameTolerance
- HitchFrameCount
Developers must be aware that this variable is crucial for balancing between detecting actual DoS attacks and preventing false positives due to normal network or performance issues. Setting it too low might lead to false positives, while setting it too high might allow actual attacks to go undetected.
Best practices when using this variable include:
- Carefully tuning the value based on your game’s performance characteristics and network environment.
- Monitoring its effectiveness in conjunction with other DoS detection metrics.
- Considering the target platforms and their typical performance characteristics when setting this value.
- Regularly reviewing and adjusting this value as part of your game’s network security strategy.
#Setting Variables
#References In INI files
Location: <Workspace>/Engine/Config/BaseEngine.ini:1650, section: [DDoSDetection]
- INI Section:
DDoSDetection
- Raw value:
500
- Is Array:
False
Location: <Workspace>/Engine/Config/BaseEngine.ini:1700, section: [GameNetDriver RPCDoSDetection]
- INI Section:
GameNetDriver RPCDoSDetection
- Raw value:
1000
- Is Array:
False
Location: <Workspace>/Engine/Config/BaseEngine.ini:1717, section: [BeaconNetDriver RPCDoSDetection]
- INI Section:
BeaconNetDriver RPCDoSDetection
- Raw value:
1000
- Is Array:
False
#References in C++ code
#Callsites
This variable is referenced in the following C++ source code:
#Loc: <Workspace>/Engine/Source/Runtime/Engine/Private/Net/RPCDoSDetection.cpp:373
Scope (from outer to inner):
file
function void FRPCDoSDetection::InitConfig
Source code excerpt:
bRPCDoSDetection = CurConfigObj->bRPCDoSDetection;
bRPCDoSAnalytics = CurConfigObj->bRPCDoSAnalytics;
HitchTimeQuotaMS = CurConfigObj->HitchTimeQuotaMS;
HitchSuspendDetectionTimeMS = CurConfigObj->HitchSuspendDetectionTimeMS;
if (NextTimeQuotaCheck == 0.0 && CurConfigObj->InitialConnectToleranceMS > 0)
{
NextTimeQuotaCheck = FPlatformTime::Seconds() + (CurConfigObj->InitialConnectToleranceMS / 1000.0);
}
#Loc: <Workspace>/Engine/Source/Runtime/Engine/Private/Net/RPCDoSDetection.cpp:764
Scope (from outer to inner):
file
function void FRPCDoSDetection::PreTickDispatch
Source code excerpt:
NextTimeQuotaCheck = FMath::Max(TimeSeconds + TimeQuotaCheckInterval, NextTimeQuotaCheck);
if (HitchTimeQuotaMS > 0 && ReceivedPacketEndTime != 0.0)
{
// Timing is approximate to reduce timestamp retrieval, and packets aren't received each frame
if (LastPreTickDispatchTime > ReceivedPacketEndTime)
{
ReceivedPacketEndTime = LastPreTickDispatchTime;
}
#Loc: <Workspace>/Engine/Source/Runtime/Engine/Private/Net/RPCDoSDetection.cpp:774
Scope (from outer to inner):
file
function void FRPCDoSDetection::PreTickDispatch
Source code excerpt:
double EstHitchTimeMS = (TimeSeconds - ReceivedPacketEndTime) * 1000.0;
if ((int32)EstHitchTimeMS >= HitchTimeQuotaMS)
{
bHitchSuspendDetection = true;
HitchSuspendDetectionStartTime = TimeSeconds;
}
else if (bHitchSuspendDetection && (int32)((TimeSeconds - HitchSuspendDetectionStartTime) * 1000.0) > HitchSuspendDetectionTimeMS)
{
#Loc: <Workspace>/Engine/Source/Runtime/Engine/Private/Net/RPCDoSDetectionConfig.h:66
Scope (from outer to inner):
file
class class URPCDoSDetectionConfig : public UObject
Source code excerpt:
/** The amount of time since the previous frame, for detecting hitches, to prevent false positives from built-up packets */
UPROPERTY(config)
int32 HitchTimeQuotaMS;
/** The amount of time to suspend RPC DoS Detection, once a hitch is encountered, prevent false positives from built-up packets */
UPROPERTY(config)
int32 HitchSuspendDetectionTimeMS;
/** Names of the different RPC DoS detection states, for escalating severity, depending on the amount of RPC spam */
#Loc: <Workspace>/Engine/Source/Runtime/Engine/Public/Net/RPCDoSDetection.h:1131
Scope (from outer to inner):
file
class class FRPCDoSDetection : protected FRPCDoSState
Source code excerpt:
/** The amount of time since the previous frame, for detecting hitches, to prevent false positives from built-up packets */
int32 HitchTimeQuotaMS = 0;
/** The amount of time to suspend RPC DoS Detection, once a hitch is encountered, to prevent false positives from built-up packets */
int32 HitchSuspendDetectionTimeMS = 0;
/** List of RPC's which should never be blocked */
TArray<FName> RPCBlockAllowList;
#Loc: <Workspace>/Engine/Source/Runtime/Net/Core/Private/Net/Core/Misc/DDoSDetection.cpp:75
Scope (from outer to inner):
file
function FDDoSDetection::FDDoSDetection
Source code excerpt:
, DDoSLogSpamLimit(0)
, LogHitCounter(0)
, HitchTimeQuotaMS(-1)
, HitchFrameTolerance(-1)
, HitchFrameCount(0)
, LastPerSecQuotaBegin(0.0)
, CounterPerSecHistory()
, LastCounterPerSecHistoryIdx(0)
, StartFrameRecvTimestamp(0.0)
#Loc: <Workspace>/Engine/Source/Runtime/Net/Core/Private/Net/Core/Misc/DDoSDetection.cpp:105
Scope (from outer to inner):
file
function void FDDoSDetection::InitConfig
Source code excerpt:
GConfig->GetBool(DDoSSection, TEXT("bDDoSAnalytics"), bDDoSAnalytics, GEngineIni);
GConfig->GetInt(DDoSSection, TEXT("DDoSLogSpamLimit"), DDoSLogSpamLimit, GEngineIni);
GConfig->GetInt(DDoSSection, TEXT("HitchTimeQuotaMS"), HitchTimeQuotaMS, GEngineIni);
GConfig->GetInt(DDoSSection, TEXT("HitchFrameTolerance"), HitchFrameTolerance32, GEngineIni);
HitchFrameTolerance = IntCastChecked<int8>(HitchFrameTolerance32);
DDoSLogSpamLimit = DDoSLogSpamLimit > 0 ? DDoSLogSpamLimit : 64;
DetectionSeverity.Empty();
#Loc: <Workspace>/Engine/Source/Runtime/Net/Core/Private/Net/Core/Misc/DDoSDetection.cpp:266
Scope (from outer to inner):
file
function void FDDoSDetection::PreFrameReceive
Source code excerpt:
bMetEscalationConditionsThisFrame = false;
if (HitchTimeQuotaMS > 0 && EndFrameRecvTimestamp != 0.0)
{
const double HitchTimeMS = (StartFrameRecvTimestamp - EndFrameRecvTimestamp) * 1000.0;
if ((((int32)HitchTimeMS) - HitchTimeQuotaMS) > 0)
{
HitchFrameCount++;
UE_LOG(LogNetCore, Verbose, TEXT("Detected '%i' successive hitches outside NetDriver Tick. Last Hitch: %fms (Max: %ims)"),
HitchFrameCount, HitchTimeMS, HitchTimeQuotaMS);
}
else
{
HitchFrameCount = 0;
}
}
#Loc: <Workspace>/Engine/Source/Runtime/Net/Core/Public/Net/Core/Misc/DDoSDetection.h:330
Scope (from outer to inner):
file
class class FDDoSDetection : protected FDDoSPacketCounters, protected FDDoSState
Source code excerpt:
/** The amount of time since the previous frame, for detecting frame hitches, to prevent DDoS detection false positives */
int32 HitchTimeQuotaMS;
/** The number of frames spent hitching, before disabling false positive detection, and treating packet buildup as potential DDoS */
int8 HitchFrameTolerance;
/** The number of consecutive frames spent hitching */
int32 HitchFrameCount;