Skip to content

Commit

Permalink
Cleaned up memory leaks on the task scheduler.
Browse files Browse the repository at this point in the history
  • Loading branch information
vblanco20-1 committed Jul 30, 2020
1 parent 5852f67 commit 7bf6ba5
Show file tree
Hide file tree
Showing 4 changed files with 136 additions and 129 deletions.
102 changes: 57 additions & 45 deletions Source/ECSTesting/ECS_Base/SystemTasks.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -284,32 +284,20 @@ void ECSSystemScheduler::Run(bool runParallel, ECS_Registry& reg)
while (gameTasks.Dequeue(gametask))
{
// UE_LOG(LogFlying, Warning, TEXT("MTXLOCK:Gametask"));
//endmutex.Lock();

//bool bCanExecute = CanExecute(gametask);


//if (bCanExecute) {
{

// AddPending(gametask, nullptr);


//UE_LOG(LogFlying, Warning, TEXT("MTXUNLOCK:Gametask"));
// endmutex.Unlock();
//UE_LOG(LogFlying, Warning, TEXT("MTXUNLOCK:Gametask"));

//UE_LOG(LogFlying, Warning, TEXT("Executing game task: %s"), *gametask->TaskName);

SCOPE_CYCLE_COUNTER(STAT_TS_GameTask);
gametask->original->function(reg);

AsyncFinished(gametask);
}
//else {
// //back to the queue
// waitingTasks.Add(gametask);
// //UE_LOG(LogFlying, Warning, TEXT("MTXUNLOCK: %s"), "Gametask");
// endmutex.Unlock();
//}
}
}
//UE_LOG(LogFlying, Warning, TEXT("MTXLOCK: SyncLaunch0"));
endmutex.Lock();
Expand All @@ -328,10 +316,10 @@ void ECSSystemScheduler::Run(bool runParallel, ECS_Registry& reg)
sync->original->function(reg);
syncTask = nullptr;
//UE_LOG(LogFlying, Warning, TEXT("MTXUNLOCK: SyncLaunch"));
//endmutex.Unlock();

AsyncFinished(sync);
//UE_LOG(LogFlying, Warning, TEXT("MTXLOCK: SyncLaunch"));
//endmutex.Lock();

sync = nullptr;
if (syncTask != nullptr)
{
Expand All @@ -341,25 +329,20 @@ void ECSSystemScheduler::Run(bool runParallel, ECS_Registry& reg)
else
{
// UE_LOG(LogFlying, Warning, TEXT("MTXLOCK: SyncLaunch2"));
//endmutex.Lock();

}
};
}

//if (pendingTasks.Num() == 0)
//{
//UE_LOG(LogFlying, Warning, TEXT("MTXUNLOCK: FinalSync"));
endmutex.Unlock();
endEvent->Wait(1);
loopcounts++;
if (loopcounts > 100) {
//UE_LOG(LogFlying, Warning, TEXT("Shits busted"));
breakloop = true;
//return;
}
//}

}

//UE_LOG(LogFlying, Warning, TEXT("MTXUNLOCK: FinalSync"));
endmutex.Unlock();
endEvent->Wait(1);
loopcounts++;
if (loopcounts > 100) {
//UE_LOG(LogFlying, Warning, TEXT("Shits busted"));
breakloop = true;

}
}
}
}
Expand All @@ -373,8 +356,6 @@ void ECSSystemScheduler::AsyncFinished(GraphTask* task)

//UE_LOG(LogFlying, Warning, TEXT("MTXLOCK:AsyncFinished0"));
endmutex.Lock();



totalTasks--;
if (task->original)
Expand All @@ -386,10 +367,7 @@ void ECSSystemScheduler::AsyncFinished(GraphTask* task)

endEvent->Trigger();

//trigger execution of next task



//trigger execution of next task
{
//UE_LOG(LogFlying, Warning, TEXT("MTXLOCK: AsyncFinished1"));
endmutex.Lock();
Expand All @@ -401,11 +379,9 @@ void ECSSystemScheduler::AsyncFinished(GraphTask* task)

nxt->predecessorCount--;
if (nxt->predecessorCount == 0) {
// if (CanExecute(nxt)) {

//UE_LOG(LogFlying, Warning, TEXT("ADD WAITING %s"), *nxt->TaskName);
waitingTasks.Add(nxt);
// }

//UE_LOG(LogFlying, Warning, TEXT("ADD WAITING %s"), *nxt->TaskName);
waitingTasks.Add(nxt);
}
}

Expand Down Expand Up @@ -458,7 +434,7 @@ bool ECSSystemScheduler::LaunchTask(GraphTask* task)

return true;
}
else //if (tasktype == ESysTaskType::FreeTask || tasktype == ESysTaskType::GameThread)
else
{
if (!CanExecute(task))
{
Expand Down Expand Up @@ -562,3 +538,39 @@ GraphTask* ECSSystemScheduler::NewGraphTask(SystemTask* originalTask)
return taks;
}

SystemTaskChain* ECSSystemScheduler::NewTaskChain()
{
SystemTaskChain* taks = new SystemTaskChain();

AllocatedChains.Add(taks);

return taks;
}
ECSSystemScheduler::~ECSSystemScheduler() {

Reset();
}

void ECSSystemScheduler::Reset()
{
for (auto t : AllocatedTasks)
{
delete t;
}
for (auto t : AllocatedGraphTasks)
{
delete t;
}
for (auto t : AllocatedChains)
{
delete t;
}

AllocatedTasks.Reset();
AllocatedGraphTasks.Reset();
AllocatedChains.Reset();
systasks.Reset();
waitingTasks.Reset();
pendingTasks.Reset();
}

148 changes: 70 additions & 78 deletions Source/ECSTesting/ECS_Base/SystemTasks.h
Original file line number Diff line number Diff line change
Expand Up @@ -165,27 +165,88 @@ class SystemTaskChain {
};




class ECSSystemScheduler {

struct LaunchedTask {
GraphTask* task;
//SystemTask* task;
TaskDependencies dependencies;
TFuture<void> future;
};

public:

~ECSSystemScheduler();

TArray<SystemTaskChain*> systasks;
ECS_Registry* registry;

void AddTaskgraph(SystemTaskChain* newGraph);

void Run(bool runParallel, ECS_Registry& reg);

void Reset();

void AsyncFinished(GraphTask* task);

bool LaunchTask(GraphTask* task);

void AddPending(GraphTask* task, TFuture<void>* future);
void RemovePending(GraphTask* task);

bool CanExecute(GraphTask* task);

TArray<GraphTask*> waitingTasks;
TArray<TSharedPtr<LaunchedTask>> pendingTasks;

TQueue<GraphTask*> gameTasks;
GraphTask* syncTask;


FCriticalSection mutex;

FCriticalSection endmutex;

TAtomic<int> totalTasks;
//TAtomic<int> tasksUntilSync;
FEvent* endEvent;


SystemTask* NewTask();
GraphTask* NewGraphTask(SystemTask* originalTask);
SystemTaskChain* NewTaskChain();



//pooled allocations for easy cleanup
TArray<SystemTask*> AllocatedTasks;
TArray<GraphTask*> AllocatedGraphTasks;
TArray<SystemTaskChain*> AllocatedChains;
};

class SystemTaskBuilder {
public:
SystemTaskBuilder(FString name, int sortkey, class ECSSystemScheduler* _scheduler, float Priority = 1.f) {
graph = new SystemTaskChain();

graph = _scheduler->NewTaskChain();
graph->name = name;
graph->sortKey = sortkey;
graph->priority = Priority;
scheduler = _scheduler;
};

template< typename C>
void AddTask(const TaskDependencies& deps, C&& c , ESysTaskFlags flags = ESysTaskFlags::ExecuteAsync) {
void AddTask(const TaskDependencies& deps, C&& c, ESysTaskFlags flags = ESysTaskFlags::ExecuteAsync) {
SystemTask* task = scheduler->NewTask();
task->deps = deps;
task->function = std::move(c);
task->type = ESysTaskType::FreeTask;
task->flags = flags;
task->ownerGraph = graph;

if ( !((uint32_t)flags & (uint32_t)ESysTaskFlags::NoECS) )
if (!((uint32_t)flags & (uint32_t)ESysTaskFlags::NoECS))
{
task->deps.AddRead<ECS_Registry>();
}
Expand Down Expand Up @@ -217,7 +278,7 @@ class SystemTaskBuilder {


template<typename C>
void AddSyncTask( C&& c) {
void AddSyncTask(C&& c) {
SystemTask* task = scheduler->NewTask();//new SystemTask();
task->function = std::move(c);
task->type = ESysTaskType::FreeTask;//GameThread;//SyncPoint;
Expand All @@ -228,76 +289,7 @@ class SystemTaskBuilder {
};

SystemTaskChain* FinishGraph() { return graph; };

SystemTaskChain* graph;
ECSSystemScheduler* scheduler{nullptr};
};

class ECSSystemScheduler {

struct LaunchedTask {
GraphTask* task;
//SystemTask* task;
TaskDependencies dependencies;
TFuture<void> future;
};



public:

TArray<SystemTaskChain*> systasks;
ECS_Registry* registry;

void AddTaskgraph(SystemTaskChain* newGraph);

void Run(bool runParallel, ECS_Registry& reg);

#if 0
void AsyncFinished(SystemTask* task);

bool ExecuteTask(SystemTask* task);

void AddPending(SystemTask* task, TFuture<void>* future);
void RemovePending(SystemTask* task);

bool CanExecute(SystemTask* task);
SystemTask* syncTask;
TArray<SystemTask*> waitingTasks;
TArray<TSharedPtr<LaunchedTask>> pendingTasks;

TQueue<SystemTask*> gameTasks;
#else


void AsyncFinished(GraphTask* task);

bool LaunchTask(GraphTask* task);

void AddPending(GraphTask* task, TFuture<void>* future);
void RemovePending(GraphTask* task);

bool CanExecute(GraphTask* task);

TArray<GraphTask*> waitingTasks;
TArray<TSharedPtr<LaunchedTask>> pendingTasks;

TQueue<GraphTask*> gameTasks;
GraphTask* syncTask;
#endif
FCriticalSection mutex;

FCriticalSection endmutex;

TAtomic<int> totalTasks;
//TAtomic<int> tasksUntilSync;
FEvent* endEvent;


SystemTask* NewTask();
GraphTask* NewGraphTask(SystemTask* originalTask);

TArray<SystemTask*> AllocatedTasks;
TArray<GraphTask*> AllocatedGraphTasks;
};

SystemTaskChain* graph;
ECSSystemScheduler* scheduler{ nullptr };
};
11 changes: 6 additions & 5 deletions Source/ECSTesting/ECS_SpaceBattle/Battle_ECSWorld.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
#include "ECS_Core.h"
#include "ECS_BaseSystems.h"
#include "ECS_BattleSystems.h"
#include "SystemTasks.h"



// Sets default values
Expand All @@ -22,6 +22,7 @@ void A_ECSWorldActor::BeginPlay()


ECSWorld = MakeUnique<ECS_World>();
TaskScheduler = MakeUnique<ECSSystemScheduler>();

ECSWorld->CreateAndRegisterSystem<CopyTransformToECSSystem>("CopyTransform");
ECSWorld->CreateAndRegisterSystem<BoidSystem>("Boids");
Expand Down Expand Up @@ -66,13 +67,13 @@ void A_ECSWorldActor::Tick(float DeltaTime)



ECSSystemScheduler* sched = new ECSSystemScheduler();
sched->registry = &ECSWorld->registry;
TaskScheduler->Reset();
TaskScheduler->registry = &ECSWorld->registry;

for(auto sys : ECSWorld->systems){
sys->schedule(sched);
sys->schedule(TaskScheduler.Get());
}

sched->Run(ECSCVars::EnableParallel == 1,ECSWorld->registry);
TaskScheduler->Run(ECSCVars::EnableParallel == 1,ECSWorld->registry);
}

Loading

0 comments on commit 7bf6ba5

Please sign in to comment.