formatting
This commit is contained in:
parent
64dad2457c
commit
2fbaef09ec
@ -135,7 +135,6 @@ AC_Asset *AC_TouchCache(String key, u64 hash, b32 *is_first_touch)
|
|||||||
.hash = hash,
|
.hash = hash,
|
||||||
.key = key_stored
|
.key = key_stored
|
||||||
};
|
};
|
||||||
AddCounter(&asset->counter, 1);
|
|
||||||
if (is_first_touch)
|
if (is_first_touch)
|
||||||
{
|
{
|
||||||
*is_first_touch = 1;
|
*is_first_touch = 1;
|
||||||
@ -165,12 +164,12 @@ void AC_MarkReady(AC_Asset *asset, void *store_data)
|
|||||||
{
|
{
|
||||||
asset->store_data = store_data;
|
asset->store_data = store_data;
|
||||||
asset->status = ASSET_STATUS_READY;
|
asset->status = ASSET_STATUS_READY;
|
||||||
AddCounter(&asset->counter, -1);
|
SetFence(&asset->ready_fence, 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
void AC_YieldOnAssetReady(AC_Asset *asset)
|
void AC_YieldOnAssetReady(AC_Asset *asset)
|
||||||
{
|
{
|
||||||
YieldOnCounter(&asset->counter);
|
YieldOnFence(&asset->ready_fence, 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
////////////////////////////////
|
////////////////////////////////
|
||||||
|
|||||||
@ -17,7 +17,8 @@ Struct(AC_Asset)
|
|||||||
u64 hash;
|
u64 hash;
|
||||||
String key;
|
String key;
|
||||||
|
|
||||||
Counter counter;
|
/* Asset is ready when fence >= 1 */
|
||||||
|
Fence ready_fence;
|
||||||
|
|
||||||
/* Managed via asset_cache_mark_x functions */
|
/* Managed via asset_cache_mark_x functions */
|
||||||
AC_Status status;
|
AC_Status status;
|
||||||
|
|||||||
@ -545,30 +545,37 @@ StaticAssert(alignof(Atomic32Padded) == CachelineSize && sizeof(Atomic32Padded)
|
|||||||
StaticAssert(alignof(Atomic64Padded) == CachelineSize && sizeof(Atomic64Padded) % CachelineSize == 0);
|
StaticAssert(alignof(Atomic64Padded) == CachelineSize && sizeof(Atomic64Padded) % CachelineSize == 0);
|
||||||
|
|
||||||
#if PlatformIsWindows && ArchIsX64
|
#if PlatformIsWindows && ArchIsX64
|
||||||
|
//- Memory barriers
|
||||||
|
# define CompilerMemoryBarrier() _ReadWriteBarrier()
|
||||||
|
# define HardwareMemoryBarrier() MemoryBarrier()
|
||||||
//- 8 bit atomic operations
|
//- 8 bit atomic operations
|
||||||
#define Atomic8Fetch(x) (x)->_v
|
ForceInline i8 Atomic8Fetch (Atomic8 *x) { i8 result = (x)->_v; CompilerMemoryBarrier(); return result; }
|
||||||
#define Atomic8FetchSet(x, e) (i8)_InterlockedExchange8((volatile char *)&(x)->_v, (e))
|
ForceInline void Atomic8Set (Atomic8 *x, i8 e) { CompilerMemoryBarrier(); (x)->_v = e; }
|
||||||
#define Atomic8FetchTestSet(x, c, e) (i8)_InterlockedCompareExchange8((volatile char *)&(x)->_v, (e), (c))
|
ForceInline i8 Atomic8FetchSet (Atomic8 *x, i8 e) { return (i8)_InterlockedExchange8((volatile char *)&(x)->_v, (e)); }
|
||||||
#define Atomic8FetchXor(x, c) (i8)_InterlockedXor8((volatile char *)&(x)->_v, (c))
|
ForceInline i8 Atomic8FetchTestSet (Atomic8 *x, i8 c, i8 e) { return (i8)_InterlockedCompareExchange8((volatile char *)&(x)->_v, (e), (c)); }
|
||||||
#define Atomic8FetchAdd(x, a) (i8)_InterlockedExchangeAdd8((volatile char *)&(x)->_v, (a))
|
ForceInline i8 Atomic8FetchXor (Atomic8 *x, i8 c) { return (i8)_InterlockedXor8((volatile char *)&(x)->_v, (c)); }
|
||||||
|
ForceInline i8 Atomic8FetchAdd (Atomic8 *x, i8 a) { return (i8)_InterlockedExchangeAdd8((volatile char *)&(x)->_v, (a)); }
|
||||||
//- 16 bit atomic operations
|
//- 16 bit atomic operations
|
||||||
#define Atomic16Fetch(x) (x)->_v
|
ForceInline i16 Atomic16Fetch (Atomic16 *x) { i16 result = (x)->_v; CompilerMemoryBarrier(); return result; }
|
||||||
#define Atomic16FetchSet(x, e) (i16)_InterlockedExchange16(&(x)->_v, (e))
|
ForceInline void Atomic16Set (Atomic16 *x, i16 e) { CompilerMemoryBarrier(); (x)->_v = e; }
|
||||||
#define Atomic16FetchTestSet(x, c, e) (i16)_InterlockedCompareExchange16(&(x)->_v, (e), (c))
|
ForceInline i16 Atomic16FetchSet (Atomic16 *x, i16 e) { return (i16)_InterlockedExchange16(&(x)->_v, (e)); }
|
||||||
#define Atomic16FetchXor(x, c) (i16)_InterlockedXor16(&(x)->_v, (c))
|
ForceInline i16 Atomic16FetchTestSet (Atomic16 *x, i16 c, i16 e) { return (i16)_InterlockedCompareExchange16(&(x)->_v, (e), (c)); }
|
||||||
#define Atomic16FetchAdd(x, a) (i16)_InterlockedExchangeAdd16(&(x)->_v, (a))
|
ForceInline i16 Atomic16FetchXor (Atomic16 *x, i16 c) { return (i16)_InterlockedXor16(&(x)->_v, (c)); }
|
||||||
|
ForceInline i16 Atomic16FetchAdd (Atomic16 *x, i16 a) { return (i16)_InterlockedExchangeAdd16(&(x)->_v, (a)); }
|
||||||
//- 32 bit atomic operations
|
//- 32 bit atomic operations
|
||||||
#define Atomic32Fetch(x) (x)->_v
|
ForceInline i32 Atomic32Fetch (Atomic32 *x) { i32 result = (x)->_v; CompilerMemoryBarrier(); return result; }
|
||||||
#define Atomic32FetchSet(x, e) (i32)_InterlockedExchange((volatile long *)&(x)->_v, (e))
|
ForceInline void Atomic32Set (Atomic32 *x, i32 e) { CompilerMemoryBarrier(); (x)->_v = e; }
|
||||||
#define Atomic32FetchTestSet(x, c, e) (i32)_InterlockedCompareExchange((volatile long *)&(x)->_v, (e), (c))
|
ForceInline i32 Atomic32FetchSet (Atomic32 *x, i32 e) { return (i32)_InterlockedExchange((volatile long *)&(x)->_v, (e)); }
|
||||||
#define Atomic32FetchXor(x, c) (i32)_InterlockedXor((volatile long *)&(x)->_v, (c))
|
ForceInline i32 Atomic32FetchTestSet (Atomic32 *x, i32 c, i32 e) { return (i32)_InterlockedCompareExchange((volatile long *)&(x)->_v, (e), (c)); }
|
||||||
#define Atomic32FetchAdd(x, a) (i32)_InterlockedExchangeAdd((volatile long *)&(x)->_v, (a))
|
ForceInline i32 Atomic32FetchXor (Atomic32 *x, i32 c) { return (i32)_InterlockedXor((volatile long *)&(x)->_v, (c)); }
|
||||||
|
ForceInline i32 Atomic32FetchAdd (Atomic32 *x, i32 a) { return (i32)_InterlockedExchangeAdd((volatile long *)&(x)->_v, (a)); }
|
||||||
//- 64 bit atomic operations
|
//- 64 bit atomic operations
|
||||||
#define Atomic64Fetch(x) (x)->_v
|
ForceInline i64 Atomic64Fetch (Atomic64 *x) { i16 result = (x)->_v; CompilerMemoryBarrier(); return result; }
|
||||||
#define Atomic64FetchSet(x, e) (i64)_InterlockedExchange64(&(x)->_v, (e))
|
ForceInline void Atomic64Set (Atomic64 *x, i64 e) { CompilerMemoryBarrier(); (x)->_v = e; }
|
||||||
#define Atomic64FetchTestSet(x, c, e) (i64)_InterlockedCompareExchange64(&(x)->_v, (e), (c))
|
ForceInline i64 Atomic64FetchSet (Atomic64 *x, i64 e) { return (i64)_InterlockedExchange64(&(x)->_v, (e)); }
|
||||||
#define Atomic64FetchXor(x, c) (i64)_InterlockedXor64(&(x)->_v, (c))
|
ForceInline i64 Atomic64FetchTestSet (Atomic64 *x, i64 c, i64 e) { return (i64)_InterlockedCompareExchange64(&(x)->_v, (e), (c)); }
|
||||||
#define Atomic64FetchAdd(x, a) (i64)_InterlockedExchangeAdd64(&(x)->_v, (a))
|
ForceInline i64 Atomic64FetchXor (Atomic64 *x, i64 c) { return (i64)_InterlockedXor64(&(x)->_v, (c)); }
|
||||||
|
ForceInline i64 Atomic64FetchAdd (Atomic64 *x, i64 a) { return (i64)_InterlockedExchangeAdd64(&(x)->_v, (a)); }
|
||||||
#else
|
#else
|
||||||
# error Atomics not implemented
|
# error Atomics not implemented
|
||||||
#endif
|
#endif
|
||||||
@ -712,8 +719,8 @@ Struct(ComputeShader) { Resource resource; };
|
|||||||
# else
|
# else
|
||||||
# error FiberId not implemented
|
# error FiberId not implemented
|
||||||
# endif
|
# endif
|
||||||
# define MaxFibers 1024
|
# define MaxFibers 4096
|
||||||
StaticAssert(MaxFibers < I16Max); /* FiberId type should fit MaxFibers */
|
StaticAssert(MaxFibers < I16Max); /* MaxFibers should fit in FiberId */
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@ -14,7 +14,7 @@ Struct(SharedGstatCtx)
|
|||||||
|
|
||||||
extern SharedGstatCtx _shared_gstat_ctx;
|
extern SharedGstatCtx _shared_gstat_ctx;
|
||||||
|
|
||||||
#define SetGstat(name, value) Atomic64FetchSet(&_shared_gstat_ctx.name.v, (value))
|
#define SetGstat(name, value) Atomic64Set(&_shared_gstat_ctx.name.v, (value))
|
||||||
#define AddGstat(name, value) Atomic64FetchAdd(&_shared_gstat_ctx.name.v, (value))
|
#define AddGstat(name, value) Atomic64FetchAdd(&_shared_gstat_ctx.name.v, (value))
|
||||||
#define GetGstat(name) Atomic64Fetch(&_shared_gstat_ctx.name.v)
|
#define GetGstat(name) Atomic64Fetch(&_shared_gstat_ctx.name.v)
|
||||||
|
|
||||||
|
|||||||
@ -12,24 +12,24 @@ Enum(JobPool)
|
|||||||
{
|
{
|
||||||
JobPool_Inherit = -1,
|
JobPool_Inherit = -1,
|
||||||
|
|
||||||
/* Contains worker threads affinitized over the entire CPU.
|
/* Contains un-affinitized worker threads.
|
||||||
* Meant to take on high-bandwidth temporary work (e.g. loading a level). */
|
* Meant to take on temporary high-throughput work that is allowed to interfere with all other pools (e.g. loading a level). */
|
||||||
JobPool_Hyper = 0, /* High-priority */
|
JobPool_Hyper = 0,
|
||||||
|
|
||||||
/* Contains worker threads affinitized over the entire CPU.
|
/* Contains un-affinitized worker threads.
|
||||||
* Meant to take on blocking work so that affinitized workers workers can continue doing actual work. */
|
* Meant to take on blocking work so that affinitized workers can continue doing actual work. */
|
||||||
JobPool_Blocking = 1, /* Normal priority */
|
JobPool_Blocking = 1,
|
||||||
|
|
||||||
/* Contains worker threads affinitized to cores that don't interfere with workers in specialized pools.
|
/* Contains worker threads affinitized to cores that don't interfere with workers in specialized pools.
|
||||||
* Meant to consume asynchronous work from higher priority pools. */
|
* Meant to consume asynchronous work from higher priority pools. */
|
||||||
JobPool_Background = 2, /* Normal priority */
|
JobPool_Background = 2,
|
||||||
|
|
||||||
/* Contains worker threads affinitized to cores that don't interfere with workers in other specialized pools.
|
/* Contains worker threads affinitized to cores that don't interfere with workers in other specialized pools.
|
||||||
* These pools are meant to only have work pushed onto them from jobs within the same pool (e.g. 100 jobs pushed onto the
|
* These pools are meant to only have work pushed onto them from jobs within the same pool (e.g. 100 jobs pushed onto the
|
||||||
* User pool will not interfere with cores running workers on the Sim pool). */
|
* User pool will not interfere with cores running the Sim pool). */
|
||||||
JobPool_Audio = 3, /* Critical priority */
|
JobPool_Audio = 3,
|
||||||
JobPool_User = 4, /* Above-normal priority */
|
JobPool_User = 4,
|
||||||
JobPool_Sim = 5, /* Above-normal priority */
|
JobPool_Sim = 5,
|
||||||
|
|
||||||
JobPool_Count
|
JobPool_Count
|
||||||
};
|
};
|
||||||
@ -37,26 +37,29 @@ Enum(JobPool)
|
|||||||
////////////////////////////////
|
////////////////////////////////
|
||||||
//~ Job types
|
//~ Job types
|
||||||
|
|
||||||
|
typedef void JobFunc(void *, i32);
|
||||||
|
|
||||||
Struct(JobCounter)
|
Struct(JobCounter)
|
||||||
{
|
{
|
||||||
Fence jobs_completed_fence;
|
|
||||||
Atomic64Padded num_jobs_dispatched;
|
Atomic64Padded num_jobs_dispatched;
|
||||||
|
Fence num_jobs_completed_fence;
|
||||||
};
|
};
|
||||||
|
|
||||||
typedef void JobFunc(void *, i32);
|
|
||||||
|
|
||||||
Struct(Job)
|
Struct(Job)
|
||||||
{
|
{
|
||||||
|
/* Internal */
|
||||||
Job *next;
|
Job *next;
|
||||||
|
Atomic32Padded num_tasks_completed;
|
||||||
|
|
||||||
|
/* Initialized & constant after OpenJob */
|
||||||
Arena *arena;
|
Arena *arena;
|
||||||
JobFunc *func;
|
JobFunc *func;
|
||||||
JobPool pool;
|
JobPool pool;
|
||||||
|
|
||||||
|
/* Configurable between OpenJob & CloseJob */
|
||||||
i32 count;
|
i32 count;
|
||||||
JobCounter *counter;
|
JobCounter *counter;
|
||||||
void *sig;
|
void *sig;
|
||||||
|
|
||||||
Atomic64Padded num_tasks_completed;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
////////////////////////////////
|
////////////////////////////////
|
||||||
@ -112,4 +115,4 @@ do {
|
|||||||
|
|
||||||
Job *OpenJob(JobFunc *func, JobPool pool_kind);
|
Job *OpenJob(JobFunc *func, JobPool pool_kind);
|
||||||
void CloseJob(Job *job);
|
void CloseJob(Job *job);
|
||||||
#define YieldOnJobs(counter) (YieldOnFence(&(counter)->jobs_completed_fence, Atomic64Fetch(&(counter)->num_jobs_dispatched.v)))
|
#define YieldOnJobs(counter) (YieldOnFence(&(counter)->num_jobs_completed_fence, Atomic64Fetch(&(counter)->num_jobs_dispatched.v)))
|
||||||
|
|||||||
@ -56,7 +56,7 @@ Lock LockSpinE(Mutex *m, i32 spin)
|
|||||||
}
|
}
|
||||||
|
|
||||||
#if RtcIsEnabled
|
#if RtcIsEnabled
|
||||||
Atomic32FetchSet(&m->exclusive_fiber_id, FiberId());
|
Atomic32Set(&m->exclusive_fiber_id, FiberId());
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
Lock lock = ZI;
|
Lock lock = ZI;
|
||||||
@ -123,9 +123,9 @@ void Unlock(Lock *l)
|
|||||||
if (l->exclusive)
|
if (l->exclusive)
|
||||||
{
|
{
|
||||||
#if RtcIsEnabled
|
#if RtcIsEnabled
|
||||||
Atomic32FetchSet(&m->exclusive_fiber_id, 0);
|
Atomic32Set(&m->exclusive_fiber_id, 0);
|
||||||
#endif
|
#endif
|
||||||
Atomic32FetchSet(&m->v, 0);
|
Atomic32Set(&m->v, 0);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
@ -165,34 +165,6 @@ void SignalCv(Cv *cv)
|
|||||||
FutexWakeNeq(&cv->wake_gen);
|
FutexWakeNeq(&cv->wake_gen);
|
||||||
}
|
}
|
||||||
|
|
||||||
////////////////////////////////
|
|
||||||
//~ Counter
|
|
||||||
|
|
||||||
i64 ValueFromCounter(Counter *counter)
|
|
||||||
{
|
|
||||||
return Atomic64Fetch(&counter->v);
|
|
||||||
}
|
|
||||||
|
|
||||||
void AddCounter(Counter *counter, i64 x)
|
|
||||||
{
|
|
||||||
i64 old_v = Atomic64FetchAdd(&counter->v, x);
|
|
||||||
i64 new_v = old_v + x;
|
|
||||||
if (old_v > 0 && new_v <= 0)
|
|
||||||
{
|
|
||||||
FutexWakeNeq(&counter->v);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void YieldOnCounter(Counter *counter)
|
|
||||||
{
|
|
||||||
i64 v = Atomic64Fetch(&counter->v);
|
|
||||||
while (v > 0)
|
|
||||||
{
|
|
||||||
FutexYieldNeq(&counter->v, &v, sizeof(v));
|
|
||||||
v = Atomic64Fetch(&counter->v);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
////////////////////////////////
|
////////////////////////////////
|
||||||
//~ Fence
|
//~ Fence
|
||||||
|
|
||||||
@ -201,13 +173,16 @@ i64 FetchFence(Fence *fence)
|
|||||||
return Atomic64Fetch(&fence->v.v);
|
return Atomic64Fetch(&fence->v.v);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void SetFence(Fence *fence, i64 x)
|
||||||
|
{
|
||||||
|
Atomic64Set(&fence->v.v, x);
|
||||||
|
FutexWakeGte(&fence->v.v);
|
||||||
|
}
|
||||||
|
|
||||||
i64 FetchSetFence(Fence *fence, i64 x)
|
i64 FetchSetFence(Fence *fence, i64 x)
|
||||||
{
|
{
|
||||||
i64 fetch = Atomic64FetchSet(&fence->v.v, x);
|
i64 fetch = Atomic64FetchSet(&fence->v.v, x);
|
||||||
if (x > fetch)
|
FutexWakeGte(&fence->v.v);
|
||||||
{
|
|
||||||
FutexWakeGte(&fence->v.v);
|
|
||||||
}
|
|
||||||
return fetch;
|
return fetch;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@ -32,15 +32,6 @@ AlignedStruct(Cv, CachelineSize)
|
|||||||
};
|
};
|
||||||
StaticAssert(alignof(Cv) == CachelineSize && sizeof(Cv) % CachelineSize == 0);
|
StaticAssert(alignof(Cv) == CachelineSize && sizeof(Cv) % CachelineSize == 0);
|
||||||
|
|
||||||
////////////////////////////////
|
|
||||||
//~ Counter types
|
|
||||||
|
|
||||||
AlignedStruct(Counter, CachelineSize)
|
|
||||||
{
|
|
||||||
Atomic64 v;
|
|
||||||
};
|
|
||||||
StaticAssert(alignof(Counter) == CachelineSize && sizeof(Counter) % CachelineSize == 0);
|
|
||||||
|
|
||||||
////////////////////////////////
|
////////////////////////////////
|
||||||
//~ Fence types
|
//~ Fence types
|
||||||
|
|
||||||
@ -75,17 +66,11 @@ void Unlock(Lock *lock);
|
|||||||
void YieldOnCv(Cv *cv, Lock *lock);
|
void YieldOnCv(Cv *cv, Lock *lock);
|
||||||
void SignalCv(Cv *cv);
|
void SignalCv(Cv *cv);
|
||||||
|
|
||||||
////////////////////////////////
|
|
||||||
//~ Counter operations
|
|
||||||
|
|
||||||
i64 ValueFromCounter(Counter *counter);
|
|
||||||
void AddCounter(Counter *counter, i64 x);
|
|
||||||
void YieldOnCounter(Counter *counter);
|
|
||||||
|
|
||||||
////////////////////////////////
|
////////////////////////////////
|
||||||
//~ Fence operations
|
//~ Fence operations
|
||||||
|
|
||||||
i64 FetchFence(Fence *fence);
|
i64 FetchFence(Fence *fence);
|
||||||
|
void SetFence(Fence *fence, i64 x);
|
||||||
i64 FetchSetFence(Fence *fence, i64 x);
|
i64 FetchSetFence(Fence *fence, i64 x);
|
||||||
i64 FetchAddFence(Fence *fence, i64 x);
|
i64 FetchAddFence(Fence *fence, i64 x);
|
||||||
|
|
||||||
|
|||||||
@ -123,7 +123,7 @@ void OnExit(ExitFunc *func)
|
|||||||
void SignalExit(i32 code)
|
void SignalExit(i32 code)
|
||||||
{
|
{
|
||||||
W32_SharedState *g = &W32_shared_state;
|
W32_SharedState *g = &W32_shared_state;
|
||||||
Atomic32FetchSet(&g->exit_code, code);
|
Atomic32Set(&g->exit_code, code);
|
||||||
SetEvent(g->exit_begin_event);
|
SetEvent(g->exit_begin_event);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -241,13 +241,7 @@ i32 W32_Main(void)
|
|||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/* Set up exit events */
|
/* Init time */
|
||||||
g->panic_event = CreateEventW(0, 1, 0, 0);
|
|
||||||
g->startup_end_event = CreateEventW(0, 1, 0, 0);
|
|
||||||
g->exit_begin_event = CreateEventW(0, 1, 0, 0);
|
|
||||||
g->exit_end_event = CreateEventW(0, 1, 0, 0);
|
|
||||||
|
|
||||||
/* Query performance frequency */
|
|
||||||
{
|
{
|
||||||
LARGE_INTEGER qpf;
|
LARGE_INTEGER qpf;
|
||||||
QueryPerformanceFrequency(&qpf);
|
QueryPerformanceFrequency(&qpf);
|
||||||
@ -259,6 +253,12 @@ i32 W32_Main(void)
|
|||||||
g->timer_start_qpc = qpc.QuadPart;
|
g->timer_start_qpc = qpc.QuadPart;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* Set up exit events */
|
||||||
|
g->panic_event = CreateEventW(0, 1, 0, 0);
|
||||||
|
g->startup_end_event = CreateEventW(0, 1, 0, 0);
|
||||||
|
g->exit_begin_event = CreateEventW(0, 1, 0, 0);
|
||||||
|
g->exit_end_event = CreateEventW(0, 1, 0, 0);
|
||||||
|
|
||||||
g->main_thread_id = GetCurrentThreadId();
|
g->main_thread_id = GetCurrentThreadId();
|
||||||
SetThreadDescription(GetCurrentThread(), L"Main thread");
|
SetThreadDescription(GetCurrentThread(), L"Main thread");
|
||||||
|
|
||||||
|
|||||||
@ -187,19 +187,6 @@ void W32_WaitEndThread(W32_Thread *thread)
|
|||||||
Assert(success);
|
Assert(success);
|
||||||
}
|
}
|
||||||
|
|
||||||
////////////////////////////////
|
|
||||||
//~ Pool operations
|
|
||||||
|
|
||||||
W32_JobPool *W32_JobPoolFromKind(JobPool pool_kind)
|
|
||||||
{
|
|
||||||
if (pool_kind == JobPool_Inherit)
|
|
||||||
{
|
|
||||||
W32_Fiber *fiber = W32_FiberFromId(FiberId());
|
|
||||||
pool_kind = fiber->pool;
|
|
||||||
}
|
|
||||||
return &W32_shared_job_state.job_pools[pool_kind];
|
|
||||||
}
|
|
||||||
|
|
||||||
////////////////////////////////
|
////////////////////////////////
|
||||||
//~ Win32 fiber
|
//~ Win32 fiber
|
||||||
|
|
||||||
@ -334,7 +321,7 @@ void W32_FiberEntryPoint(void *win32_fiber_data)
|
|||||||
{
|
{
|
||||||
i16 fiber_id = (i16)(i64)win32_fiber_data;
|
i16 fiber_id = (i16)(i64)win32_fiber_data;
|
||||||
volatile W32_Fiber *fiber = W32_FiberFromId(fiber_id);
|
volatile W32_Fiber *fiber = W32_FiberFromId(fiber_id);
|
||||||
W32_JobPool *pool = W32_JobPoolFromKind(fiber->pool);
|
W32_JobPool *pool = &W32_shared_job_state.job_pools[fiber->pool];
|
||||||
JobPool pool_kind = fiber->pool;
|
JobPool pool_kind = fiber->pool;
|
||||||
char *fiber_name_cstr = fiber->name_cstr;
|
char *fiber_name_cstr = fiber->name_cstr;
|
||||||
for (;;)
|
for (;;)
|
||||||
@ -349,10 +336,10 @@ void W32_FiberEntryPoint(void *win32_fiber_data)
|
|||||||
/* Check if we've completed the last task in the job */
|
/* Check if we've completed the last task in the job */
|
||||||
if (Atomic32FetchAdd(&job->num_tasks_completed.v, 1) + 1 >= job->count)
|
if (Atomic32FetchAdd(&job->num_tasks_completed.v, 1) + 1 >= job->count)
|
||||||
{
|
{
|
||||||
/* Increment fence */
|
/* Increment counter */
|
||||||
if (job->counter)
|
if (job->counter)
|
||||||
{
|
{
|
||||||
FetchAddFence(&job->counter->jobs_completed_fence, 1);
|
FetchAddFence(&job->counter->num_jobs_completed_fence, 1);
|
||||||
}
|
}
|
||||||
/* Free job */
|
/* Free job */
|
||||||
LockTicketMutex(&pool->free_jobs_tm);
|
LockTicketMutex(&pool->free_jobs_tm);
|
||||||
@ -387,7 +374,7 @@ W32_ThreadDef(W32_JobWorkerEntryFunc, worker_ctx_arg)
|
|||||||
{
|
{
|
||||||
W32_WorkerCtx *ctx = worker_ctx_arg;
|
W32_WorkerCtx *ctx = worker_ctx_arg;
|
||||||
JobPool pool_kind = ctx->pool_kind;
|
JobPool pool_kind = ctx->pool_kind;
|
||||||
W32_JobPool *pool = W32_JobPoolFromKind(pool_kind);
|
W32_JobPool *pool = &W32_shared_job_state.job_pools[pool_kind];
|
||||||
i16 worker_fiber_id = FiberId();
|
i16 worker_fiber_id = FiberId();
|
||||||
|
|
||||||
|
|
||||||
@ -514,7 +501,7 @@ void SuspendFiber(void)
|
|||||||
Assert(parent_fiber->id > 0);
|
Assert(parent_fiber->id > 0);
|
||||||
{
|
{
|
||||||
__prof_fiber_leave();
|
__prof_fiber_leave();
|
||||||
Atomic8FetchSet(&fiber->is_suspending, 1);
|
Atomic8Set(&fiber->is_suspending, 1);
|
||||||
W32_SwitchToFiber(parent_fiber);
|
W32_SwitchToFiber(parent_fiber);
|
||||||
__prof_fiber_enter(fiber->name_cstr, PROF_THREAD_GROUP_FIBERS - Mebi(fiber->pool) + Kibi(1) + fiber->id);
|
__prof_fiber_enter(fiber->name_cstr, PROF_THREAD_GROUP_FIBERS - Mebi(fiber->pool) + Kibi(1) + fiber->id);
|
||||||
}
|
}
|
||||||
@ -584,7 +571,12 @@ void ResumeFibers(i16 fiber_ids_count, i16 *fiber_ids)
|
|||||||
|
|
||||||
Job *OpenJob(JobFunc *func, JobPool pool_kind)
|
Job *OpenJob(JobFunc *func, JobPool pool_kind)
|
||||||
{
|
{
|
||||||
W32_JobPool *pool = W32_JobPoolFromKind(pool_kind);
|
if (pool_kind == JobPool_Inherit)
|
||||||
|
{
|
||||||
|
W32_Fiber *fiber = W32_FiberFromId(FiberId());
|
||||||
|
pool_kind = fiber->pool;
|
||||||
|
}
|
||||||
|
W32_JobPool *pool = &W32_shared_job_state.job_pools[pool_kind];
|
||||||
Job *job = 0;
|
Job *job = 0;
|
||||||
{
|
{
|
||||||
Arena *job_arena = 0;
|
Arena *job_arena = 0;
|
||||||
@ -621,7 +613,7 @@ void CloseJob(Job *job)
|
|||||||
{
|
{
|
||||||
TempArena scratch = BeginScratchNoConflict();
|
TempArena scratch = BeginScratchNoConflict();
|
||||||
|
|
||||||
W32_JobPool *pool = W32_JobPoolFromKind(job->pool);
|
W32_JobPool *pool = &W32_shared_job_state.job_pools[job->pool];
|
||||||
u32 num_tasks = job->count;
|
u32 num_tasks = job->count;
|
||||||
|
|
||||||
if (num_tasks > 0)
|
if (num_tasks > 0)
|
||||||
@ -684,7 +676,6 @@ void CloseJob(Job *job)
|
|||||||
{
|
{
|
||||||
LockTicketMutex(&pool->tasks_tm);
|
LockTicketMutex(&pool->tasks_tm);
|
||||||
{
|
{
|
||||||
// QueuePush(pool->first_task, pool->last_task, tasks.first);
|
|
||||||
if (pool->last_task)
|
if (pool->last_task)
|
||||||
{
|
{
|
||||||
pool->last_task->next = tasks.first;
|
pool->last_task->next = tasks.first;
|
||||||
|
|||||||
@ -178,11 +178,6 @@ W32_Thread *W32_StartThread(W32_ThreadFunc *entry_point, void *thread_udata, Str
|
|||||||
b32 W32_TryEndThread(W32_Thread *thread, f32 timeout_seconds);
|
b32 W32_TryEndThread(W32_Thread *thread, f32 timeout_seconds);
|
||||||
void W32_WaitEndThread(W32_Thread *thread);
|
void W32_WaitEndThread(W32_Thread *thread);
|
||||||
|
|
||||||
////////////////////////////////
|
|
||||||
//~ Pool operations
|
|
||||||
|
|
||||||
W32_JobPool *W32_JobPoolFromKind(JobPool pool_kind);
|
|
||||||
|
|
||||||
////////////////////////////////
|
////////////////////////////////
|
||||||
//~ Fiber operations
|
//~ Fiber operations
|
||||||
|
|
||||||
|
|||||||
@ -283,7 +283,7 @@ GPU_Fence GPU_GetGlobalFence(void);
|
|||||||
//~ @hookdecl Resource operations
|
//~ @hookdecl Resource operations
|
||||||
|
|
||||||
GPU_Resource *GPU_AcquireResource(GPU_ResourceDesc desc);
|
GPU_Resource *GPU_AcquireResource(GPU_ResourceDesc desc);
|
||||||
void GPU_ReleaseResource(GPU_Resource *resource, GPU_Fence fence, GPU_ReleaseFlag flags);
|
void GPU_ReleaseResource(GPU_Resource *resource, GPU_ReleaseFlag flags);
|
||||||
|
|
||||||
u32 GPU_GetResourceId(GPU_Resource *resource);
|
u32 GPU_GetResourceId(GPU_Resource *resource);
|
||||||
Vec2I32 GPU_GetTextureSize(GPU_Resource *resource);
|
Vec2I32 GPU_GetTextureSize(GPU_Resource *resource);
|
||||||
|
|||||||
@ -110,7 +110,7 @@ GPU_Resource *GPU_AcquireResource(GPU_ResourceDesc desc)
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
void GPU_ReleaseResource(GPU_Resource *resource, GPU_Fence fence, GPU_ReleaseFlag flags)
|
void GPU_ReleaseResource(GPU_Resource *resource, GPU_ReleaseFlag flags)
|
||||||
{
|
{
|
||||||
/* TODO */
|
/* TODO */
|
||||||
}
|
}
|
||||||
|
|||||||
@ -529,6 +529,7 @@ JobDef(Step, sig, id)
|
|||||||
++i;
|
++i;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
JobCounter counter = ZI;
|
JobCounter counter = ZI;
|
||||||
RunJob(RunCommand,
|
RunJob(RunCommand,
|
||||||
.count = shader_entries_count,
|
.count = shader_entries_count,
|
||||||
@ -1098,7 +1099,7 @@ JobDef(Build, _, __)
|
|||||||
EchoLine(msg);
|
EchoLine(msg);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
EchoLine(StringF(arena, "Runtime: %Fs", FmtFloat(SecondsFromNs(TimeNs()))));
|
||||||
ExitNow(ret);
|
ExitNow(ret);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@ -21,7 +21,7 @@ void P_StartupLog(void)
|
|||||||
ctx->file_valid = 1;
|
ctx->file_valid = 1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Atomic32FetchSet(&ctx->initialized, 1);
|
Atomic32Set(&ctx->initialized, 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
////////////////////////////////
|
////////////////////////////////
|
||||||
|
|||||||
@ -183,9 +183,8 @@ P_W32_Window *P_W32_AcquireWindow(void)
|
|||||||
/* NOTE: This thread must finish building for the window to actually be
|
/* NOTE: This thread must finish building for the window to actually be
|
||||||
* created and receive a HWND, because on Windows a the event proc must run on
|
* created and receive a HWND, because on Windows a the event proc must run on
|
||||||
* the same thread that created the window. */
|
* the same thread that created the window. */
|
||||||
AddCounter(&window->ready_fence, 1);
|
|
||||||
window->window_thread = W32_StartThread(&P_W32_WindowThreadEntryFunc, window, Lit("Window thread"), PROF_THREAD_GROUP_WINDOW);
|
window->window_thread = W32_StartThread(&P_W32_WindowThreadEntryFunc, window, Lit("Window thread"), PROF_THREAD_GROUP_WINDOW);
|
||||||
YieldOnCounter(&window->ready_fence);
|
YieldOnFence(&window->ready_fence, 1);
|
||||||
|
|
||||||
return window;
|
return window;
|
||||||
}
|
}
|
||||||
@ -193,7 +192,7 @@ P_W32_Window *P_W32_AcquireWindow(void)
|
|||||||
void P_W32_ReleaseWindow(P_W32_Window *window)
|
void P_W32_ReleaseWindow(P_W32_Window *window)
|
||||||
{
|
{
|
||||||
/* Stop window threads */
|
/* Stop window threads */
|
||||||
Atomic32FetchSet(&window->shutdown, 1);
|
Atomic32Set(&window->shutdown, 1);
|
||||||
P_W32_SharedState *g = &P_W32_shared_state;
|
P_W32_SharedState *g = &P_W32_shared_state;
|
||||||
P_W32_WakeWindow(window);
|
P_W32_WakeWindow(window);
|
||||||
W32_WaitEndThread(window->window_thread);
|
W32_WaitEndThread(window->window_thread);
|
||||||
@ -400,7 +399,7 @@ W32_ThreadDef(P_W32_WindowThreadEntryFunc, arg)
|
|||||||
window->hwnd = P_W32_InitWindow(window);
|
window->hwnd = P_W32_InitWindow(window);
|
||||||
P_W32_UpdateWindowFromSystem(window);
|
P_W32_UpdateWindowFromSystem(window);
|
||||||
BringWindowToTop(window->hwnd);
|
BringWindowToTop(window->hwnd);
|
||||||
AddCounter(&window->ready_fence, -1);
|
SetFence(&window->ready_fence, 1);
|
||||||
|
|
||||||
while (!Atomic32Fetch(&window->shutdown))
|
while (!Atomic32Fetch(&window->shutdown))
|
||||||
{
|
{
|
||||||
@ -887,14 +886,13 @@ JobDef(P_W32_UpdateTimer, _, __)
|
|||||||
periods[i] = P_W32_DefaultTimerPeriodNs;
|
periods[i] = P_W32_DefaultTimerPeriodNs;
|
||||||
}
|
}
|
||||||
|
|
||||||
Echo(Lit("Starting timer\n"));
|
|
||||||
|
|
||||||
i64 last_cycle_ns = 0;
|
i64 last_cycle_ns = 0;
|
||||||
/* FIXME: shutdown */
|
/* FIXME: shutdown */
|
||||||
for (;;)
|
for (;;)
|
||||||
{
|
{
|
||||||
__profn("Job scheduler cycle");
|
__profn("Job scheduler cycle");
|
||||||
{
|
{
|
||||||
|
/* TODO: Minimum timer frequency in case windows timers ever become ultra precise in the future */
|
||||||
__profn("Job scheduler wait");
|
__profn("Job scheduler wait");
|
||||||
LARGE_INTEGER due = ZI;
|
LARGE_INTEGER due = ZI;
|
||||||
due.QuadPart = -1;
|
due.QuadPart = -1;
|
||||||
@ -922,11 +920,11 @@ JobDef(P_W32_UpdateTimer, _, __)
|
|||||||
periods_sum_ns += (f64)periods[i];
|
periods_sum_ns += (f64)periods[i];
|
||||||
}
|
}
|
||||||
f64 mean_ns = periods_sum_ns / (f64)countof(periods);
|
f64 mean_ns = periods_sum_ns / (f64)countof(periods);
|
||||||
Atomic64FetchSet(&g->average_timer_period_ns.v, RoundF64ToI64(mean_ns));
|
Atomic64Set(&g->average_timer_period_ns.v, RoundF64ToI64(mean_ns));
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Update fence */
|
/* Update fence */
|
||||||
FetchSetFence(&g->timer_fence, now_ns);
|
SetFence(&g->timer_fence, now_ns);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@ -41,7 +41,7 @@ Struct(P_W32_Window)
|
|||||||
u32 flags;
|
u32 flags;
|
||||||
|
|
||||||
HWND hwnd;
|
HWND hwnd;
|
||||||
Counter ready_fence;
|
Fence ready_fence;
|
||||||
|
|
||||||
u16 utf16_high_surrogate_last_input;
|
u16 utf16_high_surrogate_last_input;
|
||||||
|
|
||||||
|
|||||||
@ -23,7 +23,7 @@ ExitFuncDef(PB_WSP_Shutdown)
|
|||||||
{
|
{
|
||||||
__prof;
|
__prof;
|
||||||
PB_WSP_SharedState *g = &PB_WSP_shared_state;
|
PB_WSP_SharedState *g = &PB_WSP_shared_state;
|
||||||
Atomic32FetchSet(&g->shutdown, 1);
|
Atomic32Set(&g->shutdown, 1);
|
||||||
YieldOnJobs(&g->shutdown_job_counter);
|
YieldOnJobs(&g->shutdown_job_counter);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
53
src/pp/pp.c
53
src/pp/pp.c
@ -60,7 +60,7 @@ ExitFuncDef(ShutdownUser)
|
|||||||
{
|
{
|
||||||
__prof;
|
__prof;
|
||||||
SharedUserState *g = &shared_user_state;
|
SharedUserState *g = &shared_user_state;
|
||||||
Atomic32FetchSet(&g->shutdown, 1);
|
Atomic32Set(&g->shutdown, 1);
|
||||||
YieldOnJobs(&g->shutdown_job_counter);
|
YieldOnJobs(&g->shutdown_job_counter);
|
||||||
P_ReleaseWindow(g->window);
|
P_ReleaseWindow(g->window);
|
||||||
}
|
}
|
||||||
@ -2149,12 +2149,13 @@ void UpdateUser(P_Window *window)
|
|||||||
if (g->shade_target && !EqVec2I32(g->render_size, GPU_GetTextureSize(g->shade_target)))
|
if (g->shade_target && !EqVec2I32(g->render_size, GPU_GetTextureSize(g->shade_target)))
|
||||||
{
|
{
|
||||||
__profn("Release render resources");
|
__profn("Release render resources");
|
||||||
GPU_ReleaseResource(g->albedo, g->render_fence, GPU_ReleaseFlag_None);
|
/* FIXME: Yield on render fence */
|
||||||
GPU_ReleaseResource(g->emittance, g->render_fence, GPU_ReleaseFlag_None);
|
GPU_ReleaseResource(g->albedo, GPU_ReleaseFlag_None);
|
||||||
GPU_ReleaseResource(g->emittance_flood_read, g->render_fence, GPU_ReleaseFlag_None);
|
GPU_ReleaseResource(g->emittance, GPU_ReleaseFlag_None);
|
||||||
GPU_ReleaseResource(g->emittance_flood_target, g->render_fence, GPU_ReleaseFlag_None);
|
GPU_ReleaseResource(g->emittance_flood_read, GPU_ReleaseFlag_None);
|
||||||
GPU_ReleaseResource(g->shade_read, g->render_fence, GPU_ReleaseFlag_None);
|
GPU_ReleaseResource(g->emittance_flood_target, GPU_ReleaseFlag_None);
|
||||||
GPU_ReleaseResource(g->shade_target, g->render_fence, GPU_ReleaseFlag_None);
|
GPU_ReleaseResource(g->shade_read, GPU_ReleaseFlag_None);
|
||||||
|
GPU_ReleaseResource(g->shade_target, GPU_ReleaseFlag_None);
|
||||||
g->shade_target = 0;
|
g->shade_target = 0;
|
||||||
}
|
}
|
||||||
if (!g->shade_target)
|
if (!g->shade_target)
|
||||||
@ -2171,7 +2172,8 @@ void UpdateUser(P_Window *window)
|
|||||||
/* Acquire ui buffers */
|
/* Acquire ui buffers */
|
||||||
if (g->ui_target && !EqVec2I32(g->ui_size, GPU_GetTextureSize(g->ui_target)))
|
if (g->ui_target && !EqVec2I32(g->ui_size, GPU_GetTextureSize(g->ui_target)))
|
||||||
{
|
{
|
||||||
GPU_ReleaseResource(g->ui_target, g->render_fence, GPU_ReleaseFlag_None);
|
/* FIXME: Wait on render fence */
|
||||||
|
GPU_ReleaseResource(g->ui_target, GPU_ReleaseFlag_None);
|
||||||
g->ui_target = 0;
|
g->ui_target = 0;
|
||||||
}
|
}
|
||||||
if (!g->ui_target)
|
if (!g->ui_target)
|
||||||
@ -2416,16 +2418,34 @@ void UpdateUser(P_Window *window)
|
|||||||
GPU_RasterizeMode_TriangleList);
|
GPU_RasterizeMode_TriangleList);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
g->render_fence = GPU_EndCommandList(cl);
|
|
||||||
|
/* FIXME: Enable this */
|
||||||
|
#if 0
|
||||||
|
g->most_recent_render_counter = GPU_EndCommandList(cl);
|
||||||
|
|
||||||
/* Release transfer buffers */
|
/* Release transfer buffers */
|
||||||
{
|
{
|
||||||
GPU_ReleaseResource(quad_index_buffer, g->render_fence, GPU_ReleaseFlag_Reuse);
|
{
|
||||||
GPU_ReleaseResource(material_instance_buffer, g->render_fence, GPU_ReleaseFlag_Reuse);
|
/* FIXME: Release resources */
|
||||||
GPU_ReleaseResource(ui_rect_instance_buffer, g->render_fence, GPU_ReleaseFlag_Reuse);
|
GPU_Resource *release_resources[] = {
|
||||||
GPU_ReleaseResource(ui_shape_verts_buffer, g->render_fence, GPU_ReleaseFlag_Reuse);
|
quad_index_buffer,
|
||||||
GPU_ReleaseResource(ui_shape_indices_buffer, g->render_fence, GPU_ReleaseFlag_Reuse);
|
material_instance_buffer,
|
||||||
GPU_ReleaseResource(grids_buffer, g->render_fence, GPU_ReleaseFlag_Reuse);
|
ui_rect_instance_buffer,
|
||||||
|
ui_shape_verts_buffer,
|
||||||
|
ui_shape_indices_buffer,
|
||||||
|
};
|
||||||
|
Job *job = OpenJob(ReleaseRenderResources);
|
||||||
|
{
|
||||||
|
ReleaseRenderResources_Sig *sig = PushStruct(job->arena, ReleaseRenderResources_Sig);
|
||||||
|
job->count = countof(resources);
|
||||||
|
sig->render_counter = g->most_recent_render_counter;
|
||||||
|
sig->resources = PushStructsNoZero(sig->arena, GPU_Resource *, job->count);
|
||||||
|
sig->flags = GPU_ReleaseFlag_Reuse;
|
||||||
|
CopyBytes(sig->resources, resources, sizeof(resources));
|
||||||
|
job->sig = sig;
|
||||||
|
}
|
||||||
|
CloseJob(job);
|
||||||
|
}
|
||||||
ResetArena(g->material_instances_arena);
|
ResetArena(g->material_instances_arena);
|
||||||
ResetArena(g->ui_rect_instances_arena);
|
ResetArena(g->ui_rect_instances_arena);
|
||||||
ResetArena(g->ui_shape_verts_arena);
|
ResetArena(g->ui_shape_verts_arena);
|
||||||
@ -2437,6 +2457,7 @@ void UpdateUser(P_Window *window)
|
|||||||
g->ui_shape_indices_count = 0;
|
g->ui_shape_indices_count = 0;
|
||||||
g->grids_count = 0;
|
g->grids_count = 0;
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
EndScratch(scratch);
|
EndScratch(scratch);
|
||||||
@ -2459,7 +2480,7 @@ JobDef(UpdateUserOrSleep, UNUSED sig, UNUSED id)
|
|||||||
GPU_WaitOnSwapchain(g->swapchain);
|
GPU_WaitOnSwapchain(g->swapchain);
|
||||||
}
|
}
|
||||||
{
|
{
|
||||||
__profn("Frame limiter wait");;
|
__profn("Frame limiter wait");
|
||||||
P_SleepFrame(time_ns, 1000000000 / FPS_LIMIT);
|
P_SleepFrame(time_ns, 1000000000 / FPS_LIMIT);
|
||||||
time_ns = TimeNs();
|
time_ns = TimeNs();
|
||||||
}
|
}
|
||||||
|
|||||||
@ -36,7 +36,7 @@ JobDef(S_LoadTexture, sig, _)
|
|||||||
}
|
}
|
||||||
|
|
||||||
texture->loaded = 1;
|
texture->loaded = 1;
|
||||||
AddCounter(&entry->texture_load_counter, -1);
|
SetFence(&entry->texture_ready_fence, 1);
|
||||||
EndScratch(scratch);
|
EndScratch(scratch);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -224,7 +224,7 @@ JobDef(S_LoadSheet, sig, _)
|
|||||||
}
|
}
|
||||||
|
|
||||||
sheet->loaded = 1;
|
sheet->loaded = 1;
|
||||||
AddCounter(&entry->sheet_load_counter, -1);
|
SetFence(&entry->sheet_ready_fence, 1);
|
||||||
EndScratch(scratch);
|
EndScratch(scratch);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -273,8 +273,6 @@ S_Entry *S_FetchEntry(Resource resource, JobPool pool, S_FetchFlag flags)
|
|||||||
Arena *perm = PermArena();
|
Arena *perm = PermArena();
|
||||||
entry = PushStruct(perm, S_Entry);
|
entry = PushStruct(perm, S_Entry);
|
||||||
entry->resource = resource;
|
entry->resource = resource;
|
||||||
AddCounter(&entry->texture_load_counter, 1);
|
|
||||||
AddCounter(&entry->sheet_load_counter, 1);
|
|
||||||
QueuePushN(bin->first, bin->last, entry, next_in_bin);
|
QueuePushN(bin->first, bin->last, entry, next_in_bin);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -303,7 +301,7 @@ S_Entry *S_FetchEntry(Resource resource, JobPool pool, S_FetchFlag flags)
|
|||||||
S_Texture *S_TextureFromResource(Resource resource)
|
S_Texture *S_TextureFromResource(Resource resource)
|
||||||
{
|
{
|
||||||
S_Entry *entry = S_FetchEntry(resource, JobPool_Inherit, S_FetchFlag_Texture);
|
S_Entry *entry = S_FetchEntry(resource, JobPool_Inherit, S_FetchFlag_Texture);
|
||||||
YieldOnCounter(&entry->texture_load_counter);
|
YieldOnFence(&entry->texture_ready_fence, 1);
|
||||||
return &entry->texture;
|
return &entry->texture;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -311,7 +309,7 @@ S_Texture *S_TextureFromResourceAsync(Resource resource)
|
|||||||
{
|
{
|
||||||
S_Texture *result = &S_NilTexture;
|
S_Texture *result = &S_NilTexture;
|
||||||
S_Entry *entry = S_FetchEntry(resource, JobPool_Inherit, S_FetchFlag_Texture);
|
S_Entry *entry = S_FetchEntry(resource, JobPool_Inherit, S_FetchFlag_Texture);
|
||||||
if (ValueFromCounter(&entry->texture_load_counter) <= 0)
|
if (FetchFence(&entry->texture_ready_fence) >= 1)
|
||||||
{
|
{
|
||||||
result = &entry->texture;
|
result = &entry->texture;
|
||||||
}
|
}
|
||||||
@ -321,7 +319,7 @@ S_Texture *S_TextureFromResourceAsync(Resource resource)
|
|||||||
S_Sheet *S_SheetFromResource(Resource resource)
|
S_Sheet *S_SheetFromResource(Resource resource)
|
||||||
{
|
{
|
||||||
S_Entry *entry = S_FetchEntry(resource, JobPool_Inherit, S_FetchFlag_Sheet);
|
S_Entry *entry = S_FetchEntry(resource, JobPool_Inherit, S_FetchFlag_Sheet);
|
||||||
YieldOnCounter(&entry->sheet_load_counter);
|
YieldOnFence(&entry->sheet_ready_fence, 1);
|
||||||
return &entry->sheet;
|
return &entry->sheet;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -329,7 +327,7 @@ S_Sheet *S_SheetFromResourceAsync(Resource resource)
|
|||||||
{
|
{
|
||||||
S_Sheet *result = &S_NilSheet;
|
S_Sheet *result = &S_NilSheet;
|
||||||
S_Entry *entry = S_FetchEntry(resource, JobPool_Inherit, S_FetchFlag_Sheet);
|
S_Entry *entry = S_FetchEntry(resource, JobPool_Inherit, S_FetchFlag_Sheet);
|
||||||
if (ValueFromCounter(&entry->sheet_load_counter) <= 0)
|
if (FetchFence(&entry->sheet_ready_fence) >= 1)
|
||||||
{
|
{
|
||||||
result = &entry->sheet;
|
result = &entry->sheet;
|
||||||
}
|
}
|
||||||
|
|||||||
@ -109,8 +109,8 @@ Struct(S_Entry)
|
|||||||
Atomic32 sheet_touched;
|
Atomic32 sheet_touched;
|
||||||
|
|
||||||
Resource resource;
|
Resource resource;
|
||||||
Counter texture_load_counter;
|
Fence texture_ready_fence;
|
||||||
Counter sheet_load_counter;
|
Fence sheet_ready_fence;
|
||||||
};
|
};
|
||||||
|
|
||||||
Struct(S_EntryBin)
|
Struct(S_EntryBin)
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user