I’ve encountered a recurring problem with my slight ShooterGame alterations; it seems if I call a combination of two functions, I’ll get a UObject limit reached - calling either of the two functions standalone does not trigger the issue.
I’ve verified it applies when the caller is pure C++ or Blueprint scripting, and have removed the BehaviorTree from the equation. I’ve spent the last 48 hours attempting to narrow down the cause, getting to where I am now, and my next step is to compile the engine from source to debug better if nobody has any ideas!
Here’s the log output:
D:\BuildFarm\buildmachine_++depot+UE4-Releases+4.1\Engine\Source\Runtime\CoreUObject\Private\UObject\WeakObjectPtr.cpp(78): Fatal error:
[Index:1115934332] exceeds maximum number of UObjects, [Block:68111] increase MAX_SERIAL_NUMBER_BLOCKS
UE4Editor.exe has triggered a breakpoint.
UE4Editor.exe has triggered a breakpoint.
[2014.05.29-01.39.10:464][648]LogWindows:Error: appError called: [Index:1115934332] exceeds maximum number of UObjects, [Block:68111] increase MAX_SERIAL_NUMBER_BLOCKS
[2014.05.29-01.39.10:476][648]LogWindows:Error: Windows GetLastError: The operation completed successfully. (0)
[2014.05.29-01.39.10:532][648]LogCrashTracker:
[2014.05.29-01.39.10:532][648]LogWindows: === Critical error: ===
[2014.05.29-01.39.10:532][648]LogWindows: [Index:1115934332] exceeds maximum number of UObjects, [Block:68111] increase MAX_SERIAL_NUMBER_BLOCKS
[2014.05.29-01.39.10:641][648]LogExit: Executing StaticShutdownAfterError
[2014.05.29-01.39.10:660][648]LogWindows: FPlatformMisc::RequestExit(1)
The thread 0x1be8 has exited with code 3 (0x3).
...
The two functions in question are FindClosestEnemy, which is modified from ShooterGame to simply return the character instead of updating the blackboard directly:
class AShooterCharacter*
AShooterAIController::FindClosestEnemy()
{
APawn* my_bot = GetPawn();
AShooterCharacter* closest_pawn = NULL;
if ( my_bot == NULL )
{
return NULL;
}
const FVector my_location = my_bot->GetActorLocation();
float closest_dist_sq = MAX_FLT;
for ( FConstPawnIterator iter = GetWorld()->GetPawnIterator(); iter; ++iter )
{
AShooterCharacter* pawn = Cast<AShooterCharacter>(*iter);
if ( pawn && pawn->IsAlive() && pawn->IsEnemyFor(this) )
{
const float dist_sq = (pawn->GetActorLocation() - my_location).SizeSquared();
if ( dist_sq < closest_dist_sq )
{
closest_dist_sq = dist_sq;
closest_pawn = pawn;
}
}
}
return closest_pawn;
}
and the other is the blackboard update function:
void
AShooterAIController::BBUpdateBestEnemy(
class APawn* InPawn
)
{
if ( BlackboardComp )
{
BlackboardComp->SetValueAsObject(BestEnemyKeyID, InPawn);
if ( !InPawn )
{
BlackboardComp->SetValueAsVector(BestEnemyLocationKeyID, FVector::ZeroVector);
return;
}
BlackboardComp->SetValueAsVector(BestEnemyLocationKeyID, InPawn->GetActorLocation());
}
}
I currently have the blueprint calling a LocateBestEnemy
function, which simply calls BBUpdateBestEnemy(FindClosestEnemy())
.
It seems when the input Pawn is NULL, there’s no problem, but when it’s a valid actor, it goes to hell - more annoyingly, stepping through in a debugger doesn’t seem to cause the error to manifest, leading me to think it could be a race condition somewhere, causing memory corruption? The code can work anywhere from 0 seconds all the way up to 60 seconds before it actually bombs out, but seems to be exasperated by moving the player around - I’ve noticed it also frequently occurs right when the bot respawns.
There’s no constant increase of UObjects created before the crash, leading me to believe it’s not a leak anywhere.
Regards