diff --git a/build.c b/build.c index 6b399c99..c0f197bf 100644 --- a/build.c +++ b/build.c @@ -852,7 +852,7 @@ void OnBuild(StringList cli_args) D_GetDirContents(&perm, &src_files, src_dir, 0); D_TagListAppend(&perm, &src_files, D_TagFromPath(&perm, Lit("src/base/base.c"), D_TagKind_File)); D_TagListAppend(&perm, &src_files, D_TagFromPath(&perm, Lit("src/prof/prof.cpp"), D_TagKind_File)); - D_TagListAppend(&perm, &src_files, D_TagFromPath(&perm, Lit("src/sys/sys.c"), D_TagKind_File)); + D_TagListAppend(&perm, &src_files, D_TagFromPath(&perm, Lit("src/platform/platform.c"), D_TagKind_File)); D_TagListAppend(&perm, &src_files, D_TagFromPath(&perm, Lit("src/gp/gp.c"), D_TagKind_File)); D_TagListAppend(&perm, &src_files, D_TagFromPath(&perm, Lit("src/resource/resource.c"), D_TagKind_File)); D_TagListAppend(&perm, &src_files, D_TagFromPath(&perm, Lit("src/watch/watch.c"), D_TagKind_File)); diff --git a/src/app/app.h b/src/app/app.h index 2aac11ed..fda8c809 100644 --- a/src/app/app.h +++ b/src/app/app.h @@ -2,7 +2,7 @@ #define APP_H #include "../base/base.h" -#include "../sys/sys.h" +#include "../platform/platform.h" #include "../ttf/ttf.h" #include "../gp/gp.h" #include "../sim/sim.h" diff --git a/src/app/app_core.c b/src/app/app_core.c index 0d070a7c..27bbaa8a 100644 --- a/src/app/app_core.c +++ b/src/app/app_core.c @@ -12,7 +12,7 @@ INTERNAL String initialize_write_directory(Arena *arena, String write_dir) TempArena scratch = scratch_begin(arena); /* Create write path */ - String base_write_dir = sys_get_write_path(scratch.arena); + String base_write_dir = P_GetWritePath(scratch.arena); String write_path_fmt = base_write_dir.len > 0 ? LIT("%F/%F/") : LIT("%F%F/"); String write_path = string_format( arena, @@ -22,8 +22,8 @@ INTERNAL String initialize_write_directory(Arena *arena, String write_dir) ); /* Create write dir if not present */ - if (!sys_is_dir(write_path)) { - sys_mkdir(write_path); + if (!P_IsDir(write_path)) { + P_MkDir(write_path); /* TODO: handle failure */ } @@ -41,18 +41,18 @@ String app_write_path_cat(Arena *arena, String filename) * Default settings * ========================== */ -INTERNAL struct sys_window_settings default_window_settings(struct sys_window *window) +INTERNAL P_WindowSettings default_window_settings(P_Window *window) { __prof; - V2 monitor_size = sys_window_get_monitor_size(window); + V2 monitor_size = P_GetWindowMonitorSize(window); i32 width = 1280; i32 height = math_round_to_int(width / (f32)(DEFAULT_CAMERA_WIDTH / DEFAULT_CAMERA_HEIGHT)); i32 x = math_round_to_int(monitor_size.x / 2.f - width / 2); i32 y = math_round_to_int(monitor_size.y / 2.f - height / 2); - return (struct sys_window_settings) { + return (P_WindowSettings) { .title = WINDOW_TITLE, .floating_x = x, .floating_y = y, @@ -146,7 +146,7 @@ INTERNAL struct app_arg_list parse_args(Arena *arena, String args_str) * Entry point * ========================== */ -void sys_app_startup(String args_str) +void P_AppStartup(String args_str) { __prof; TempArena scratch = scratch_begin_no_conflict(); @@ -198,7 +198,7 @@ void sys_app_startup(String args_str) String logfile_dir = string_cat(temp.arena, G.write_path, LIT("logs/")); String logfile_path = string_cat(temp.arena, logfile_dir, logfile_name); - sys_mkdir(logfile_dir); + P_MkDir(logfile_dir); log_startup(logfile_path); logf_info("Start of logs"); @@ -214,17 +214,17 @@ void sys_app_startup(String args_str) { TempArena temp = arena_temp_begin(scratch.arena); - struct sys_window_settings window_settings = ZI; + P_WindowSettings window_settings = ZI; String settings_path = app_write_path_cat(temp.arena, settings_file_name); logf_info("Looking for settings file \"%F\"", FMT_STR(settings_path)); - if (sys_is_file(settings_path)) { + if (P_IsFile(settings_path)) { logf_info("Settings file found"); - struct sys_file settings_file = sys_file_open_read(settings_path); - String file_data = sys_file_read_all(temp.arena, settings_file); - sys_file_close(settings_file); + P_File settings_file = P_OpenFileRead(settings_path); + String file_data = P_ReadFile(temp.arena, settings_file); + P_CloseFIle(settings_file); logf_info("Deserializing settings file data: %F", FMT_STR(file_data)); String error = ZI; - struct sys_window_settings *res = settings_deserialize(temp.arena, file_data, &error); + P_WindowSettings *res = settings_deserialize(temp.arena, file_data, &error); if (error.len > 0) { logf_info("Failed to load settings file with error - %F", FMT_STR(error)); String msg = string_format(temp.arena, @@ -237,7 +237,7 @@ void sys_app_startup(String args_str) ), FMT_STR(settings_path), FMT_STR(error)); - sys_panic(msg); + P_Panic(msg); } logf_info("Settings file loaded successfully"); window_settings = *res; @@ -246,7 +246,7 @@ void sys_app_startup(String args_str) window_settings = default_window_settings(window); } string_copy_to_string(STRING_FROM_ARRAY(window_settings.title), LIT(WINDOW_TITLE)); - sys_window_update_settings(window, &window_settings); + P_UpdateWindowSettings(window, &window_settings); arena_temp_end(temp); } @@ -262,11 +262,11 @@ void sys_app_startup(String args_str) AC_StartupReceipt asset_cache_sr = asset_cache_startup(); TTF_StartupReceipt ttf_sr = ttf_startup(); F_StartupReceipt font_sr = font_startup(&asset_cache_sr, &ttf_sr); - struct sprite_startup_receipt sprite_sr = sprite_startup(); + S_StartupReceipt sprite_sr = sprite_startup(); M_StartupReceipt mixer_sr = mixer_startup(); - struct sound_startup_receipt sound_sr = sound_startup(&asset_cache_sr); + SND_StartupReceipt sound_sr = sound_startup(&asset_cache_sr); D_StartupReceipt draw_sr = draw_startup(&font_sr); - struct sim_startup_receipt sim_sr = sim_startup(); + SimStartupReceipt sim_sr = sim_startup(); /* Interface systems */ PB_StartupReceipt playback_sr = playback_startup(&mixer_sr); @@ -283,14 +283,14 @@ void sys_app_startup(String args_str) String window_settings_path = app_write_path_cat(temp.arena, settings_file_name); - struct sys_window_settings settings = sys_window_get_settings(window); + P_WindowSettings settings = P_GetWindowSettings(window); String str = settings_serialize(temp.arena, &settings); logf_info("Serialized window settings: %F", FMT_STR(str)); logf_info("Writing settings file to path \"%F\"", FMT_STR(window_settings_path)); - struct sys_file settings_file = sys_file_open_write(window_settings_path); - sys_file_write(settings_file, str); - sys_file_close(settings_file); + P_File settings_file = P_OpenFileWrite(window_settings_path); + P_WriteFile(settings_file, str); + P_CloseFIle(settings_file); logf_info("Finished writing settings file"); arena_temp_end(temp); @@ -298,7 +298,7 @@ void sys_app_startup(String args_str) #endif #if 0 - sys_window_release(window); + P_ReleaseWindow(window); #endif //logf_info("Program exited normally"); diff --git a/src/asset_cache/asset_cache.h b/src/asset_cache/asset_cache.h index 986277bd..e56202bd 100644 --- a/src/asset_cache/asset_cache.h +++ b/src/asset_cache/asset_cache.h @@ -2,7 +2,7 @@ #define ASSET_CACHE_H #include "../base/base.h" -#include "../sys/sys.h" +#include "../platform/platform.h" #include "asset_cache_core.h" diff --git a/src/asset_cache/asset_cache_core.c b/src/asset_cache/asset_cache_core.c index 7f0523cc..66ebcfc7 100644 --- a/src/asset_cache/asset_cache_core.c +++ b/src/asset_cache/asset_cache_core.c @@ -6,18 +6,18 @@ #define ASSET_LOOKUP_TABLE_CAPACITY (MAX_ASSETS * 4) GLOBAL struct { - struct snc_mutex lookup_mutex; + P_Mutex lookup_mutex; AC_Asset lookup[ASSET_LOOKUP_TABLE_CAPACITY]; u64 num_assets; - struct snc_mutex store_mutex; + P_Mutex store_mutex; Arena *store_arena; #if RTC /* Array of len `num_assets` pointing into populated entries of `lookup`. */ AC_Asset *dbg_table[ASSET_LOOKUP_TABLE_CAPACITY]; u64 dbg_table_count; - struct snc_mutex dbg_table_mutex; + P_Mutex dbg_table_mutex; #endif } G = ZI, DEBUG_ALIAS(G, G_asset_cache); @@ -40,7 +40,7 @@ AC_StartupReceipt asset_cache_startup(void) INTERNAL void refresh_dbg_table(void) { #if RTC - struct snc_lock lock = snc_lock_e(&G.dbg_table_mutex); + P_Lock lock = snc_lock_e(&G.dbg_table_mutex); MEMZERO_ARRAY(G.dbg_table); G.dbg_table_count = 0; for (u64 i = 0; i < countof(G.lookup); ++i) { @@ -55,7 +55,7 @@ INTERNAL void refresh_dbg_table(void) /* Returns first matching slot or first empty slot if not found. * Check returned slot->hash != 0 for presence. */ -INTERNAL AC_Asset *asset_cache_get_slot_locked(struct snc_lock *lock, String key, u64 hash) +INTERNAL AC_Asset *asset_cache_get_slot_locked(P_Lock *lock, String key, u64 hash) { snc_assert_locked_e_or_s(lock, &G.lookup_mutex); (UNUSED)lock; @@ -101,7 +101,7 @@ AC_Asset *asset_cache_touch(String key, u64 hash, b32 *is_first_touch) /* Lookup */ { - struct snc_lock lock = snc_lock_s(&G.lookup_mutex); + P_Lock lock = snc_lock_s(&G.lookup_mutex); asset = asset_cache_get_slot_locked(&lock, key, hash); snc_unlock(&lock); } @@ -112,14 +112,14 @@ AC_Asset *asset_cache_touch(String key, u64 hash, b32 *is_first_touch) *is_first_touch = 0; } } else { - struct snc_lock lock = snc_lock_e(&G.lookup_mutex); + P_Lock lock = snc_lock_e(&G.lookup_mutex); /* Re-check asset presence in case it was inserted since lock */ asset = asset_cache_get_slot_locked(&lock, key, hash); if (!asset->hash) { if (G.num_assets >= MAX_ASSETS) { - sys_panic(LIT("Max assets reached")); + P_Panic(LIT("Max assets reached")); } String key_stored = ZI; { @@ -196,7 +196,7 @@ void *asset_cache_get_store_data(AC_Asset *asset) /* Asset store should be opened to allocate memory to the store arena */ AC_Store asset_cache_store_open(void) { - struct snc_lock lock = snc_lock_e(&G.store_mutex); + P_Lock lock = snc_lock_e(&G.store_mutex); AC_Store store = { .lock = lock, .arena = G.store_arena diff --git a/src/asset_cache/asset_cache_core.h b/src/asset_cache/asset_cache_core.h index a00b4ffc..b94a9217 100644 --- a/src/asset_cache/asset_cache_core.h +++ b/src/asset_cache/asset_cache_core.h @@ -13,7 +13,7 @@ struct AC_Asset { u64 hash; String key; - struct snc_counter counter; + P_Counter counter; /* Managed via asset_cache_mark_x functions */ AC_Status status; @@ -27,7 +27,7 @@ struct AC_Store { Arena *arena; /* Internal */ - struct snc_lock lock; + P_Lock lock; }; typedef struct AC_StartupReceipt AC_StartupReceipt; diff --git a/src/base/base_arena.c b/src/base/base_arena.c index a193473b..27dd3c89 100644 --- a/src/base/base_arena.c +++ b/src/base/base_arena.c @@ -16,7 +16,7 @@ Arena *arena_alloc(u64 reserve) if (!base) { /* Hard fail on memory reserve failure for now */ /* FIXME: Enable this */ - //sys_panic(LIT("Failed to reserve memory")); + //P_Panic(LIT("Failed to reserve memory")); (*(volatile int *)0) = 0; } u64 reserved = reserve; @@ -27,7 +27,7 @@ Arena *arena_alloc(u64 reserve) if (!base) { /* Hard fail on commit failure */ /* FIXME: Enable this */ - //sys_panic(LIT("Failed to commit initial memory block: System may be out of memory")); + //P_Panic(LIT("Failed to commit initial memory block: System may be out of memory")); (*(volatile int *)0) = 0; } @@ -83,14 +83,14 @@ void *arena_push_bytes_no_zero(Arena *arena, u64 size, u64 align) if (new_capacity > arena->reserved) { /* Hard fail if we overflow reserved memory for now */ /* FIXME: Enable this */ - //sys_panic(LIT("Failed to commit new memory block: Overflow of reserved memory")); + //P_Panic(LIT("Failed to commit new memory block: Overflow of reserved memory")); (*(volatile int *)0) = 0; } void *commit_address = base + arena->committed; if (!memory_commit(commit_address, commit_bytes)) { /* Hard fail on memory allocation failure for now */ /* FIXME: Enable this */ - //sys_panic(LIT("Failed to commit new memory block: System may be out of memory")); + //P_Panic(LIT("Failed to commit new memory block: System may be out of memory")); (*(volatile int *)0) = 0; } arena->committed += commit_bytes; diff --git a/src/base/base_incbin.c b/src/base/base_incbin.c index 3049cc84..acc4875b 100644 --- a/src/base/base_incbin.c +++ b/src/base/base_incbin.c @@ -54,7 +54,7 @@ String _incbin_get(_IncbinRcResource *inc) EnumResourceNamesW(0, RT_RCDATA, &enum_func, (LONG_PTR)¶ms); if (!params.found) { /* FIXME: enable this */ - //sys_panic(string_format(scratch.arena, + //P_Panic(string_format(scratch.arena, // LIT("INCBIN include not found in RC file: \"%F\""), // FMT_STR(inc->rc_name))); (*(volatile int *)0) = 0; diff --git a/src/font/font_core.c b/src/font/font_core.c index af875bf2..3440196c 100644 --- a/src/font/font_core.c +++ b/src/font/font_core.c @@ -15,7 +15,7 @@ struct font_task_params { struct font_task_params_store { struct font_task_params *head_free; Arena *arena; - struct snc_mutex mutex; + P_Mutex mutex; }; /* ========================== * @@ -48,7 +48,7 @@ INTERNAL struct font_task_params *font_task_params_alloc(void) { struct font_task_params *p = 0; { - struct snc_lock lock = snc_lock_e(&G.params.mutex); + P_Lock lock = snc_lock_e(&G.params.mutex); if (G.params.head_free) { p = G.params.head_free; G.params.head_free = p->next_free; @@ -62,7 +62,7 @@ INTERNAL struct font_task_params *font_task_params_alloc(void) INTERNAL void font_task_params_release(struct font_task_params *p) { - struct snc_lock lock = snc_lock_e(&G.params.mutex); + P_Lock lock = snc_lock_e(&G.params.mutex); p->next_free = G.params.head_free; G.params.head_free = p; snc_unlock(&lock); @@ -72,7 +72,7 @@ INTERNAL void font_task_params_release(struct font_task_params *p) * Load * ========================== */ -INTERNAL SYS_JOB_DEF(font_load_asset_job, job) +INTERNAL P_JobDef(font_load_asset_job, job) { __prof; TempArena scratch = scratch_begin_no_conflict(); @@ -83,7 +83,7 @@ INTERNAL SYS_JOB_DEF(font_load_asset_job, job) AC_Asset *asset = params->asset; logf_info("Loading font \"%F\" (point size %F)", FMT_STR(path), FMT_FLOAT((f64)point_size)); - i64 start_ns = sys_time_ns(); + i64 start_ns = P_TimeNs(); ASSERT(string_ends_with(path, LIT(".ttf"))); ASSERT(countof(g_font_codes) < LOOKUP_TABLE_SIZE); @@ -92,7 +92,7 @@ INTERNAL SYS_JOB_DEF(font_load_asset_job, job) R_Resource res = resource_open(path); if (!resource_exists(&res)) { /* FIME: Load baked font instead of panicking */ - sys_panic(string_format(scratch.arena, + P_Panic(string_format(scratch.arena, LIT("Font \"%F\" not found"), FMT_STR(path))); } @@ -121,7 +121,7 @@ INTERNAL SYS_JOB_DEF(font_load_asset_job, job) /* FIXME: Load baked font instead of panicking */ if (font->glyphs_count <= 0) { - sys_panic(string_format(scratch.arena, + P_Panic(string_format(scratch.arena, LIT("Parsed 0 glyphs from font \"%F\"!"), FMT_STR(path))); } @@ -138,7 +138,7 @@ INTERNAL SYS_JOB_DEF(font_load_asset_job, job) font_task_params_release(params); - logf_success("Loaded font \"%F\" (point size %F) in %F seconds", FMT_STR(path), FMT_FLOAT((f64)point_size), FMT_FLOAT(SECONDS_FROM_NS(sys_time_ns() - start_ns))); + logf_success("Loaded font \"%F\" (point size %F) in %F seconds", FMT_STR(path), FMT_FLOAT((f64)point_size), FMT_FLOAT(SECONDS_FROM_NS(P_TimeNs() - start_ns))); asset_cache_mark_ready(asset, font); scratch_end(scratch); @@ -163,7 +163,7 @@ AC_Asset *font_load_asset(String path, f32 point_size, b32 wait) /* Assemble task params */ struct font_task_params *params = font_task_params_alloc(); if (path.len > (sizeof(params->path_cstr) - 1)) { - sys_panic(string_format(scratch.arena, + P_Panic(string_format(scratch.arena, LIT("Font path \"%F\" too long!"), FMT_STR(path))); } @@ -174,7 +174,7 @@ AC_Asset *font_load_asset(String path, f32 point_size, b32 wait) /* Push task */ asset_cache_mark_loading(asset); - sys_run(1, font_load_asset_job, params, SYS_POOL_BACKGROUND, SYS_PRIORITY_LOW, 0); + P_Run(1, font_load_asset_job, params, P_Pool_Background, P_Priority_Low, 0); if (wait) { asset_cache_wait(asset); } diff --git a/src/gp/gp.h b/src/gp/gp.h index 5efd4495..334f0a71 100644 --- a/src/gp/gp.h +++ b/src/gp/gp.h @@ -2,7 +2,7 @@ #define GP_H #include "../base/base.h" -#include "../sys/sys.h" +#include "../platform/platform.h" #include "../tar/tar.h" #include "../ase/ase.h" #include "../dxc/dxc.h" diff --git a/src/gp/gp_core.h b/src/gp/gp_core.h index bebbf55e..0cc7f222 100644 --- a/src/gp/gp_core.h +++ b/src/gp/gp_core.h @@ -1,6 +1,3 @@ -struct sys_window; -struct snc_counter; - typedef struct G_Indices G_Indices; struct G_Indices { u32 count; @@ -138,7 +135,7 @@ G_MemoryInfo gp_query_memory_info(void); typedef struct G_Swapchain G_Swapchain; -G_Swapchain *gp_swapchain_alloc(struct sys_window *window, V2i32 resolution); +G_Swapchain *gp_swapchain_alloc(P_Window *window, V2i32 resolution); void gp_swapchain_release(G_Swapchain *gp_swapchain); diff --git a/src/gp/gp_core_dx12.c b/src/gp/gp_core_dx12.c index 8e82ebd7..5ba3992f 100644 --- a/src/gp/gp_core_dx12.c +++ b/src/gp/gp_core_dx12.c @@ -124,7 +124,7 @@ struct command_queue { ID3D12CommandQueue *cq; Arena *arena; - struct snc_mutex submit_fence_mutex; + P_Mutex submit_fence_mutex; u64 submit_fence_target; ID3D12Fence *submit_fence; @@ -138,7 +138,7 @@ struct command_queue { struct command_list_pool { struct command_queue *cq; Arena *arena; - struct snc_mutex mutex; + P_Mutex mutex; struct command_list *first_submitted_command_list; struct command_list *last_submitted_command_list; }; @@ -148,7 +148,7 @@ struct command_list { struct command_list_pool *pool; struct ID3D12CommandAllocator *ca; struct ID3D12GraphicsCommandList *cl; - struct snc_lock global_record_lock; + P_Lock global_record_lock; struct pipeline *cur_pipeline; @@ -238,7 +238,7 @@ struct swapchain { struct cpu_descriptor_heap { enum D3D12_DESCRIPTOR_HEAP_TYPE type; Arena *arena; - struct snc_mutex mutex; + P_Mutex mutex; u32 descriptor_size; u32 num_descriptors_reserved; @@ -265,7 +265,7 @@ struct fenced_release_data { * Internal procs * ========================== */ -INTERNAL SYS_EXIT_FUNC(gp_shutdown); +INTERNAL P_ExitFuncDef(gp_shutdown); INTERNAL void dx12_init_device(void); @@ -279,7 +279,7 @@ INTERNAL struct cpu_descriptor_heap *cpu_descriptor_heap_alloc(enum D3D12_DESCRI INTERNAL void command_queue_release(struct command_queue *cq); -INTERNAL SYS_JOB_DEF(dx12_evictor_job, _); +INTERNAL P_JobDef(dx12_evictor_job, _); INTERNAL void fenced_release(void *data, enum fenced_release_kind kind); @@ -288,13 +288,13 @@ INTERNAL struct dx12_resource *dx12_resource_alloc(D3D12_HEAP_PROPERTIES heap_pr INTERNAL struct descriptor *descriptor_alloc(struct cpu_descriptor_heap *dh); struct command_queue_alloc_job_sig { struct command_queue_desc *descs_in; struct command_queue **cqs_out; }; -INTERNAL SYS_JOB_DEF(command_queue_alloc_job, job); +INTERNAL P_JobDef(command_queue_alloc_job, job); struct pipeline_alloc_job_sig { struct pipeline_desc *descs_in; struct pipeline **pipelines_out; }; -INTERNAL SYS_JOB_DEF(pipeline_alloc_job, job); +INTERNAL P_JobDef(pipeline_alloc_job, job); struct dx12_upload_job_sig { struct dx12_resource *resource; void *data; }; -INTERNAL SYS_JOB_DEF(dx12_upload_job, job); +INTERNAL P_JobDef(dx12_upload_job, job); #if RESOURCE_RELOADING INTERNAL WATCH_CALLBACK_FUNC_DEF(pipeline_watch_callback, name); @@ -308,23 +308,23 @@ GLOBAL struct { Atomic32 initialized; /* Descriptor heaps pool */ - struct snc_mutex command_descriptor_heaps_mutex; + P_Mutex command_descriptor_heaps_mutex; Arena *command_descriptor_heaps_arena; struct command_descriptor_heap *first_submitted_command_descriptor_heap; struct command_descriptor_heap *last_submitted_command_descriptor_heap; /* Command buffers pool */ - struct snc_mutex command_buffers_mutex; + P_Mutex command_buffers_mutex; Arena *command_buffers_arena; Dict *command_buffers_dict; /* Resources pool */ - struct snc_mutex resources_mutex; + P_Mutex resources_mutex; Arena *resources_arena; struct dx12_resource *first_free_resource; /* Swapchains pool */ - struct snc_mutex swapchains_mutex; + P_Mutex swapchains_mutex; Arena *swapchains_arena; struct swapchain *first_free_swapchain; @@ -332,7 +332,7 @@ GLOBAL struct { struct tar_archive dxc_archive; /* Pipeline cache */ - struct snc_mutex pipelines_mutex; + P_Mutex pipelines_mutex; Arena *pipelines_arena; struct pipeline *first_free_pipeline; Dict *pipeline_descs; @@ -341,7 +341,7 @@ GLOBAL struct { struct pipeline_scope *first_free_pipeline_scope; /* Fenced release queue */ - struct snc_mutex fenced_releases_mutex; + P_Mutex fenced_releases_mutex; Arena *fenced_releases_arena; u64 fenced_release_targets[DX12_NUM_QUEUES]; @@ -363,14 +363,14 @@ GLOBAL struct { struct cpu_descriptor_heap *rtv_heap; /* Command queues */ - struct snc_mutex global_command_list_record_mutex; - struct snc_mutex global_submit_mutex; + P_Mutex global_command_list_record_mutex; + P_Mutex global_submit_mutex; struct command_queue *command_queues[DX12_NUM_QUEUES]; /* Evictor job */ - struct snc_counter evictor_job_counter; - struct snc_cv evictor_wake_cv; - struct snc_mutex evictor_wake_mutex; + P_Counter evictor_job_counter; + P_Cv evictor_wake_cv; + P_Mutex evictor_wake_mutex; i64 evictor_wake_gen; b32 evictor_shutdown; } G = ZI, DEBUG_ALIAS(G, G_gp_dx12); @@ -383,7 +383,7 @@ void gp_startup(void) { __prof; if (atomic32_fetch_test_set(&G.initialized, 0, 1) != 0) { - sys_panic(LIT("GP layer already initialized")); + P_Panic(LIT("GP layer already initialized")); } /* Initialize command descriptor heaps pool */ @@ -411,7 +411,7 @@ void gp_startup(void) /* Initialize embedded shader archive */ String embedded_data = inc_dxc_tar(); if (embedded_data.len <= 0) { - sys_panic(LIT("No embedded shaders found")); + P_Panic(LIT("No embedded shaders found")); } G.dxc_archive = tar_parse(G.pipelines_arena, embedded_data, LIT("")); @@ -426,13 +426,13 @@ void gp_startup(void) #if RESOURCE_RELOADING watch_register_callback(pipeline_watch_callback); #endif - sys_on_exit(gp_shutdown); + P_OnExit(gp_shutdown); /* Start evictor job */ - sys_run(1, dx12_evictor_job, 0, SYS_POOL_BACKGROUND, SYS_PRIORITY_LOW, &G.evictor_job_counter); + P_Run(1, dx12_evictor_job, 0, P_Pool_Background, P_Priority_Low, &G.evictor_job_counter); } -INTERNAL SYS_EXIT_FUNC(gp_shutdown) +INTERNAL P_ExitFuncDef(gp_shutdown) { __prof; #if 0 @@ -448,7 +448,7 @@ INTERNAL SYS_EXIT_FUNC(gp_shutdown) #endif { - struct snc_lock lock = snc_lock_e(&G.evictor_wake_mutex); + P_Lock lock = snc_lock_e(&G.evictor_wake_mutex); G.evictor_shutdown = 1; snc_cv_signal(&G.evictor_wake_cv, I32_MAX); snc_unlock(&lock); @@ -464,7 +464,7 @@ INTERNAL void dx12_init_error(String error) { TempArena scratch = scratch_begin_no_conflict(); String msg = string_format(scratch.arena, LIT("Failed to initialize DirectX 12.\n\n%F"), FMT_STR(error)); - sys_panic(msg); + P_Panic(msg); scratch_end(scratch); } @@ -658,8 +658,8 @@ INTERNAL void dx12_init_objects(void) sig.descs_in = params; sig.cqs_out = G.command_queues; { - struct snc_counter counter = ZI; - sys_run(DX12_NUM_QUEUES, command_queue_alloc_job, &sig, SYS_POOL_INHERIT, SYS_PRIORITY_INHERIT, &counter); + P_Counter counter = ZI; + P_Run(DX12_NUM_QUEUES, command_queue_alloc_job, &sig, P_Pool_Inherit, P_Priority_Inherit, &counter); snc_counter_wait(&counter); } #if PROFILING @@ -752,8 +752,8 @@ INTERNAL void dx12_init_pipelines(void) struct pipeline_alloc_job_sig sig = ZI; sig.descs_in = descs; sig.pipelines_out = pipelines; - struct snc_counter counter = ZI; - sys_run(num_pipelines, pipeline_alloc_job, &sig, SYS_POOL_INHERIT, SYS_PRIORITY_INHERIT, &counter); + P_Counter counter = ZI; + P_Run(num_pipelines, pipeline_alloc_job, &sig, P_Pool_Inherit, P_Priority_Inherit, &counter); snc_counter_wait(&counter); } for (u32 i = 0; i < num_pipelines; ++i) { @@ -768,7 +768,7 @@ INTERNAL void dx12_init_pipelines(void) String error = pipeline->error.len > 0 ? pipeline->error : LIT("Unknown error"); String msg = string_format(scratch.arena, LIT("Error initializing pipeline \"%F\":\n\n%F"), FMT_STR(pipeline->name), FMT_STR(error)); log_error(msg); - sys_message_box(SYS_MESSAGE_BOX_KIND_WARNING, msg); + P_MessageBox(P_MessageBoxKind_Warning, msg); } } pipeline_register(num_pipelines, pipelines); @@ -793,7 +793,7 @@ INTERNAL void dx12_init_noise(void) if (resource_exists(&noise_res)) { String data = resource_get_data(&noise_res); if (data.len != expected_size) { - sys_panic(string_format(scratch.arena, + P_Panic(string_format(scratch.arena, LIT("Noise texture has unexpected size for a %Fx%Fx%F texture (expected %F, got %F)"), FMT_UINT(K_BLUE_NOISE_TEX_WIDTH), FMT_UINT(K_BLUE_NOISE_TEX_HEIGHT), FMT_UINT(K_BLUE_NOISE_TEX_DEPTH), FMT_UINT(expected_size), FMT_UINT(data.len))); @@ -824,16 +824,16 @@ INTERNAL void dx12_init_noise(void) /* Upload texture */ { - struct snc_counter counter = ZI; + P_Counter counter = ZI; struct dx12_upload_job_sig sig = ZI; sig.resource = r; sig.data = data.text; - sys_run(1, dx12_upload_job, &sig, SYS_POOL_INHERIT, SYS_PRIORITY_INHERIT, &counter); + P_Run(1, dx12_upload_job, &sig, P_Pool_Inherit, P_Priority_Inherit, &counter); snc_counter_wait(&counter); } } } else { - sys_panic(string_format(scratch.arena, LIT("Noise resource \"%F\" not found"), FMT_STR(noise_res_name))); + P_Panic(string_format(scratch.arena, LIT("Noise resource \"%F\" not found"), FMT_STR(noise_res_name))); } resource_close(&noise_res); } @@ -867,7 +867,7 @@ struct shader_compile_job_sig { struct shader_compile_result *results; }; -INTERNAL SYS_JOB_DEF(shader_compile_job, job) +INTERNAL P_JobDef(shader_compile_job, job) { __prof; struct shader_compile_job_sig *sig = job.sig; @@ -877,7 +877,7 @@ INTERNAL SYS_JOB_DEF(shader_compile_job, job) TempArena scratch = scratch_begin(arena); { - i64 start_ns = sys_time_ns(); + i64 start_ns = P_TimeNs(); DXC_Result dxc_result = ZI; { __profn("Compile shader"); @@ -904,7 +904,7 @@ INTERNAL SYS_JOB_DEF(shader_compile_job, job) result->success = dxc_result.success; result->dxc = dxc_result.dxc; result->errors = dxc_result.errors; - result->elapsed_ns = sys_time_ns() - start_ns; + result->elapsed_ns = P_TimeNs() - start_ns; } scratch_end(scratch); @@ -916,7 +916,7 @@ INTERNAL SYS_JOB_DEF(shader_compile_job, job) * Pipeline * ========================== */ -INTERNAL SYS_JOB_DEF(pipeline_alloc_job, job) +INTERNAL P_JobDef(pipeline_alloc_job, job) { __prof; struct pipeline_alloc_job_sig *sig = job.sig; @@ -925,7 +925,7 @@ INTERNAL SYS_JOB_DEF(pipeline_alloc_job, job) struct pipeline *pipeline = 0; { - struct snc_lock lock = snc_lock_e(&G.pipelines_mutex); + P_Lock lock = snc_lock_e(&G.pipelines_mutex); if (G.first_free_pipeline) { pipeline = G.first_free_pipeline; G.first_free_pipeline = pipeline->next; @@ -942,7 +942,7 @@ INTERNAL SYS_JOB_DEF(pipeline_alloc_job, job) TempArena scratch = scratch_begin_no_conflict(); { - i64 start_ns = sys_time_ns(); + i64 start_ns = P_TimeNs(); String pipeline_name = pipeline->name; logf_info("Loading pipeline \"%F\"", FMT_STR(pipeline_name)); b32 success = 1; @@ -1165,7 +1165,7 @@ INTERNAL SYS_JOB_DEF(pipeline_alloc_job, job) pipeline->pso = pso; pipeline->rootsig = rootsig; - pipeline->compilation_time_ns = sys_time_ns() - start_ns; + pipeline->compilation_time_ns = P_TimeNs() - start_ns; pipeline->success = success; pipeline->is_gfx = cs_dxc.len == 0; pipeline->error = error_str; @@ -1192,7 +1192,7 @@ INTERNAL void pipeline_release_now(struct pipeline *pipeline) if (pipeline->pso) { ID3D12PipelineState_Release(pipeline->pso); } - struct snc_lock lock = snc_lock_e(&G.pipelines_mutex); + P_Lock lock = snc_lock_e(&G.pipelines_mutex); { pipeline->next = G.first_free_pipeline; G.first_free_pipeline = pipeline; @@ -1209,7 +1209,7 @@ INTERNAL struct pipeline_scope *pipeline_scope_begin(void) __prof; struct pipeline_scope *scope = 0; { - struct snc_lock lock = snc_lock_e(&G.pipelines_mutex); + P_Lock lock = snc_lock_e(&G.pipelines_mutex); if (G.first_free_pipeline_scope) { scope = G.first_free_pipeline_scope; G.first_free_pipeline_scope = scope->next_free; @@ -1232,7 +1232,7 @@ INTERNAL struct pipeline_scope *pipeline_scope_begin(void) INTERNAL void pipeline_scope_end(struct pipeline_scope *scope) { __prof; - struct snc_lock lock = snc_lock_e(&G.pipelines_mutex); + P_Lock lock = snc_lock_e(&G.pipelines_mutex); { for (DictEntry *entry = scope->refs->first; entry; entry = entry->next) { struct pipeline *pipeline = (struct pipeline *)entry->value; @@ -1258,7 +1258,7 @@ INTERNAL struct pipeline *pipeline_from_name(struct pipeline_scope *scope, Strin res = tmp; } else { { - struct snc_lock lock = snc_lock_e(&G.pipelines_mutex); + P_Lock lock = snc_lock_e(&G.pipelines_mutex); tmp = (struct pipeline *)dict_get(G.top_successful_pipelines, hash); if (tmp) { ++tmp->refcount; @@ -1277,7 +1277,7 @@ INTERNAL struct pipeline *pipeline_from_name(struct pipeline_scope *scope, Strin INTERNAL void pipeline_register(u64 num_pipelines, struct pipeline **pipelines) { __prof; - struct snc_lock lock = snc_lock_e(&G.pipelines_mutex); + P_Lock lock = snc_lock_e(&G.pipelines_mutex); { for (u64 i = 0; i < num_pipelines; ++i) { struct pipeline *pipeline = pipelines[i]; @@ -1328,8 +1328,8 @@ INTERNAL WATCH_CALLBACK_FUNC_DEF(pipeline_watch_callback, name) if (is_rs || is_cs) { logf_debug("Change detected in shader source file \"%F\", recompiling...", FMT_STR(name)); success = 1; - struct sys_file file = sys_file_open_read_wait(name); - String data = sys_file_read_all(scratch.arena, file); + P_File file = P_OpenFileReadWait(name); + String data = P_ReadFile(scratch.arena, file); { friendly_name = name; StringArray split = string_split(scratch.arena, friendly_name, LIT("src/")); @@ -1371,12 +1371,12 @@ INTERNAL WATCH_CALLBACK_FUNC_DEF(pipeline_watch_callback, name) sig.descs[0].target = LIT("cs_6_6"); } { - struct snc_counter counter = ZI; - sys_run(num_shaders, shader_compile_job, &sig, SYS_POOL_INHERIT, SYS_PRIORITY_INHERIT, &counter); + P_Counter counter = ZI; + P_Run(num_shaders, shader_compile_job, &sig, P_Pool_Inherit, P_Priority_Inherit, &counter); snc_counter_wait(&counter); } } - sys_file_close(file); + P_CloseFIle(file); } @@ -1423,12 +1423,12 @@ INTERNAL WATCH_CALLBACK_FUNC_DEF(pipeline_watch_callback, name) struct pipeline_alloc_job_sig sig = ZI; sig.descs_in = pipeline_descs; sig.pipelines_out = pipelines; - struct snc_counter counter = ZI; - sys_run(num_pipelines, pipeline_alloc_job, &sig, SYS_POOL_INHERIT, SYS_PRIORITY_INHERIT, &counter); + P_Counter counter = ZI; + P_Run(num_pipelines, pipeline_alloc_job, &sig, P_Pool_Inherit, P_Priority_Inherit, &counter); snc_counter_wait(&counter); } { - struct snc_lock lock = snc_lock_s(&G.pipelines_mutex); + P_Lock lock = snc_lock_s(&G.pipelines_mutex); for (u32 i = 0; i < num_pipelines; ++i) { struct pipeline *pipeline = pipelines[i]; if (pipeline->success) { @@ -1448,7 +1448,7 @@ INTERNAL WATCH_CALLBACK_FUNC_DEF(pipeline_watch_callback, name) /* If no previously successful pipeline exists, then show a message box rather than logging since logs may not be visible to user */ String error = pipeline->error.len > 0 ? pipeline->error : LIT("Unknown error"); String msg = string_format(scratch.arena, LIT("Error compiling pipeline \"%F\":\n\n%F"), FMT_STR(pipeline->name), FMT_STR(error)); - sys_message_box(SYS_MESSAGE_BOX_KIND_WARNING, msg); + P_MessageBox(P_MessageBoxKind_Warning, msg); } } @@ -1474,7 +1474,7 @@ INTERNAL struct descriptor *descriptor_alloc(struct cpu_descriptor_heap *dh) u32 index = 0; D3D12_CPU_DESCRIPTOR_HANDLE handle = ZI; { - struct snc_lock lock = snc_lock_e(&dh->mutex); + P_Lock lock = snc_lock_e(&dh->mutex); if (dh->first_free_descriptor) { d = dh->first_free_descriptor; dh->first_free_descriptor = d->next_free; @@ -1482,7 +1482,7 @@ INTERNAL struct descriptor *descriptor_alloc(struct cpu_descriptor_heap *dh) index = d->index; } else { if (dh->num_descriptors_reserved >= dh->num_descriptors_capacity) { - sys_panic(LIT("Max descriptors reached in heap")); + P_Panic(LIT("Max descriptors reached in heap")); } d = arena_push_no_zero(dh->arena, struct descriptor); index = dh->num_descriptors_reserved++; @@ -1500,7 +1500,7 @@ INTERNAL struct descriptor *descriptor_alloc(struct cpu_descriptor_heap *dh) INTERNAL void descriptor_release(struct descriptor *descriptor) { struct cpu_descriptor_heap *dh = descriptor->heap; - struct snc_lock lock = snc_lock_e(&dh->mutex); + P_Lock lock = snc_lock_e(&dh->mutex); { descriptor->next_free = dh->first_free_descriptor; dh->first_free_descriptor = descriptor; @@ -1529,7 +1529,7 @@ INTERNAL struct cpu_descriptor_heap *cpu_descriptor_heap_alloc(enum D3D12_DESCRI descriptor_size = G.desc_sizes[type]; } if (num_descriptors == 0 || descriptor_size == 0) { - sys_panic(LIT("Unsupported CPU descriptor type")); + P_Panic(LIT("Unsupported CPU descriptor type")); } dh->num_descriptors_capacity = num_descriptors; dh->descriptor_size = descriptor_size; @@ -1539,7 +1539,7 @@ INTERNAL struct cpu_descriptor_heap *cpu_descriptor_heap_alloc(enum D3D12_DESCRI desc.NumDescriptors = num_descriptors; HRESULT hr = ID3D12Device_CreateDescriptorHeap(G.device, &desc, &IID_ID3D12DescriptorHeap, (void **)&dh->heap); if (FAILED(hr)) { - sys_panic(LIT("Failed to create CPU descriptor heap")); + P_Panic(LIT("Failed to create CPU descriptor heap")); } ID3D12DescriptorHeap_GetCPUDescriptorHandleForHeapStart(dh->heap, &dh->handle); @@ -1569,7 +1569,7 @@ INTERNAL void fenced_release(void *data, enum fenced_release_kind kind) /* Read current fence target values from command queues */ for (u32 i = 0; i < countof(G.command_queues); ++i) { struct command_queue *cq = G.command_queues[i]; - struct snc_lock lock = snc_lock_s(&cq->submit_fence_mutex); + P_Lock lock = snc_lock_s(&cq->submit_fence_mutex); { fr_targets[i] = cq->submit_fence_target; } @@ -1578,7 +1578,7 @@ INTERNAL void fenced_release(void *data, enum fenced_release_kind kind) /* Push data to release queue */ { - struct snc_lock lock = snc_lock_e(&G.fenced_releases_mutex); + P_Lock lock = snc_lock_e(&G.fenced_releases_mutex); { *arena_push(G.fenced_releases_arena, struct fenced_release_data) = fr; MEMCPY(G.fenced_release_targets, fr_targets, sizeof(fr_targets)); @@ -1588,7 +1588,7 @@ INTERNAL void fenced_release(void *data, enum fenced_release_kind kind) /* Wake evictor */ { - struct snc_lock lock = snc_lock_e(&G.evictor_wake_mutex); + P_Lock lock = snc_lock_e(&G.evictor_wake_mutex); { ++G.evictor_wake_gen; snc_cv_signal(&G.evictor_wake_cv, I32_MAX); @@ -1606,7 +1606,7 @@ INTERNAL struct dx12_resource *dx12_resource_alloc(D3D12_HEAP_PROPERTIES heap_pr __prof; struct dx12_resource *r = 0; { - struct snc_lock lock = snc_lock_e(&G.resources_mutex); + P_Lock lock = snc_lock_e(&G.resources_mutex); if (G.first_free_resource) { r = G.first_free_resource; G.first_free_resource = r->next_free; @@ -1622,7 +1622,7 @@ INTERNAL struct dx12_resource *dx12_resource_alloc(D3D12_HEAP_PROPERTIES heap_pr HRESULT hr = ID3D12Device_CreateCommittedResource(G.device, &heap_props, heap_flags, &desc, initial_state, clear_value_ptr, &IID_ID3D12Resource, (void **)&r->resource); if (FAILED(hr)) { /* TODO: Don't panic */ - sys_panic(LIT("Failed to create resource")); + P_Panic(LIT("Failed to create resource")); } r->state = initial_state; @@ -1657,7 +1657,7 @@ INTERNAL void dx12_resource_release_now(struct dx12_resource *t) ID3D12Resource_Release(t->resource); /* Add to free list */ - struct snc_lock lock = snc_lock_e(&G.resources_mutex); + P_Lock lock = snc_lock_e(&G.resources_mutex); t->next_free = G.first_free_resource; G.first_free_resource = t; snc_unlock(&lock); @@ -1729,7 +1729,7 @@ INTERNAL void dx12_resource_barriers(ID3D12GraphicsCommandList *cl, i32 num_desc INTERNAL struct command_list_pool *command_list_pool_alloc(struct command_queue *cq); -INTERNAL SYS_JOB_DEF(command_queue_alloc_job, job) +INTERNAL P_JobDef(command_queue_alloc_job, job) { __prof; struct command_queue_alloc_job_sig *sig = job.sig; @@ -1749,12 +1749,12 @@ INTERNAL SYS_JOB_DEF(command_queue_alloc_job, job) dx12_desc.Priority = desc->priority; HRESULT hr = ID3D12Device_CreateCommandQueue(G.device, &dx12_desc, &IID_ID3D12CommandQueue, (void **)&cq->cq); if (FAILED(hr)) { - sys_panic(LIT("Failed to create command queue")); + P_Panic(LIT("Failed to create command queue")); } hr = ID3D12Device_CreateFence(G.device, 0, 0, &IID_ID3D12Fence, (void **)&cq->submit_fence); if (FAILED(hr)) { - sys_panic(LIT("Failed to create command queue fence")); + P_Panic(LIT("Failed to create command queue fence")); } cq->cl_pool = command_list_pool_alloc(cq); @@ -1797,7 +1797,7 @@ INTERNAL struct command_list *command_list_open(struct command_list_pool *pool) struct ID3D12GraphicsCommandList *old_cl = 0; struct ID3D12CommandAllocator *old_ca = 0; { - struct snc_lock lock = snc_lock_e(&pool->mutex); + P_Lock lock = snc_lock_e(&pool->mutex); /* Find first command list ready for reuse */ for (struct command_list *tmp = pool->first_submitted_command_list; tmp; tmp = tmp->next_submitted) { if (completed_fence_value >= tmp->submitted_fence_target) { @@ -1838,29 +1838,29 @@ INTERNAL struct command_list *command_list_open(struct command_list_pool *pool) } else { hr = ID3D12Device_CreateCommandAllocator(G.device, cq->desc.type, &IID_ID3D12CommandAllocator, (void **)&cl->ca); if (FAILED(hr)) { - sys_panic(LIT("Failed to create command allocator")); + P_Panic(LIT("Failed to create command allocator")); } hr = ID3D12Device_CreateCommandList(G.device, 0, cq->desc.type, cl->ca, 0, &IID_ID3D12GraphicsCommandList, (void **)&cl->cl); if (FAILED(hr)) { - sys_panic(LIT("Failed to create command list")); + P_Panic(LIT("Failed to create command list")); } hr = ID3D12GraphicsCommandList_Close(cl->cl); if (FAILED(hr)) { - sys_panic(LIT("Failed to close command list during initialization")); + P_Panic(LIT("Failed to close command list during initialization")); } } /* Reset */ hr = ID3D12CommandAllocator_Reset(cl->ca); if (FAILED(hr)) { - sys_panic(LIT("Failed to reset command allocator")); + P_Panic(LIT("Failed to reset command allocator")); } hr = ID3D12GraphicsCommandList_Reset(cl->cl, cl->ca, 0); if (FAILED(hr)) { - sys_panic(LIT("Failed to reset command list")); + P_Panic(LIT("Failed to reset command list")); } return cl; @@ -1879,7 +1879,7 @@ INTERNAL u64 command_list_close(struct command_list *cl) HRESULT hr = ID3D12GraphicsCommandList_Close(cl->cl); if (FAILED(hr)) { /* TODO: Don't panic */ - sys_panic(LIT("Failed to close command list before execution")); + P_Panic(LIT("Failed to close command list before execution")); } } @@ -1887,8 +1887,8 @@ INTERNAL u64 command_list_close(struct command_list *cl) u64 submit_fence_target = 0; { __profn("Execute"); - struct snc_lock submit_lock = snc_lock_s(&G.global_submit_mutex); - struct snc_lock fence_lock = snc_lock_e(&cq->submit_fence_mutex); + P_Lock submit_lock = snc_lock_s(&G.global_submit_mutex); + P_Lock fence_lock = snc_lock_e(&cq->submit_fence_mutex); { submit_fence_target = ++cq->submit_fence_target; ID3D12CommandQueue_ExecuteCommandLists(cq->cq, 1, (ID3D12CommandList **)&cl->cl); @@ -1900,7 +1900,7 @@ INTERNAL u64 command_list_close(struct command_list *cl) /* Add descriptor heaps to submitted list */ { - struct snc_lock lock = snc_lock_e(&G.command_descriptor_heaps_mutex); + P_Lock lock = snc_lock_e(&G.command_descriptor_heaps_mutex); for (struct command_descriptor_heap *cdh = cl->first_command_descriptor_heap; cdh; cdh = cdh->next_in_command_list) { cdh->submitted_cq = cq; cdh->submitted_fence_target = submit_fence_target; @@ -1916,7 +1916,7 @@ INTERNAL u64 command_list_close(struct command_list *cl) /* Add command buffers to submitted list */ { - struct snc_lock lock = snc_lock_e(&G.command_buffers_mutex); + P_Lock lock = snc_lock_e(&G.command_buffers_mutex); for (struct command_buffer *cb = cl->first_command_buffer; cb; cb = cb->next_in_command_list) { struct command_buffer_group *group = cb->group; cb->submitted_cq = cq; @@ -1935,7 +1935,7 @@ INTERNAL u64 command_list_close(struct command_list *cl) snc_unlock(&cl->global_record_lock); cl->submitted_fence_target = submit_fence_target; { - struct snc_lock lock = snc_lock_e(&pool->mutex); + P_Lock lock = snc_lock_e(&pool->mutex); if (pool->last_submitted_command_list) { pool->last_submitted_command_list->next_submitted = cl; } else { @@ -1963,7 +1963,7 @@ INTERNAL struct command_descriptor_heap *command_list_push_descriptor_heap(struc D3D12_CPU_DESCRIPTOR_HANDLE old_start_cpu_handle = ZI; D3D12_GPU_DESCRIPTOR_HANDLE old_start_gpu_handle = ZI; { - struct snc_lock lock = snc_lock_e(&G.command_descriptor_heaps_mutex); + P_Lock lock = snc_lock_e(&G.command_descriptor_heaps_mutex); /* Find first heap ready for reuse */ for (struct command_descriptor_heap *tmp = G.first_submitted_command_descriptor_heap; tmp; tmp = tmp->next_submitted) { /* TODO: Cache completed fence values */ @@ -2009,7 +2009,7 @@ INTERNAL struct command_descriptor_heap *command_list_push_descriptor_heap(struc desc.Flags = D3D12_DESCRIPTOR_HEAP_FLAG_SHADER_VISIBLE; HRESULT hr = ID3D12Device_CreateDescriptorHeap(G.device, &desc, &IID_ID3D12DescriptorHeap, (void **)&cdh->heap); if (FAILED(hr)) { - sys_panic(LIT("Failed to create GPU descriptor heap")); + P_Panic(LIT("Failed to create GPU descriptor heap")); } ID3D12DescriptorHeap_GetCPUDescriptorHandleForHeapStart(cdh->heap, &cdh->start_cpu_handle); ID3D12DescriptorHeap_GetGPUDescriptorHandleForHeapStart(cdh->heap, &cdh->start_gpu_handle); @@ -2017,7 +2017,7 @@ INTERNAL struct command_descriptor_heap *command_list_push_descriptor_heap(struc /* Copy CPU heap */ { - struct snc_lock lock = snc_lock_s(&dh_cpu->mutex); + P_Lock lock = snc_lock_s(&dh_cpu->mutex); ID3D12Device_CopyDescriptorsSimple(G.device, dh_cpu->num_descriptors_reserved, cdh->start_cpu_handle, dh_cpu->handle, D3D12_DESCRIPTOR_HEAP_TYPE_CBV_SRV_UAV); snc_unlock(&lock); } @@ -2071,7 +2071,7 @@ INTERNAL struct command_buffer *_command_list_push_buffer(struct command_list *c struct command_buffer *cb = 0; struct dx12_resource *r = 0; { - struct snc_lock lock = snc_lock_e(&G.command_buffers_mutex); + P_Lock lock = snc_lock_e(&G.command_buffers_mutex); { u64 group_hash = command_buffer_hash_from_size(size); @@ -2163,7 +2163,7 @@ INTERNAL struct command_buffer *_command_list_push_buffer(struct command_list *c HRESULT hr = ID3D12Resource_Map(cb->resource->resource, 0, &read_range, &dst); if (FAILED(hr) || !dst) { /* TODO: Don't panic */ - sys_panic(LIT("Failed to map command buffer resource")); + P_Panic(LIT("Failed to map command buffer resource")); } MEMCPY(dst, data, data_len); ID3D12Resource_Unmap(cb->resource->resource, 0, 0); @@ -2185,7 +2185,7 @@ struct dx12_wait_fence_job_sig { u64 target; }; -INTERNAL SYS_JOB_DEF(dx12_wait_fence_job, job) +INTERNAL P_JobDef(dx12_wait_fence_job, job) { __prof; struct dx12_wait_fence_job_sig *sig = job.sig; @@ -2208,7 +2208,7 @@ G_Resource *gp_texture_alloc(G_TextureFormat format, u32 flags, V2i32 size, void { __prof; if (size.x <= 0 || size.y <= 0) { - sys_panic(LIT("Tried to create texture with dimension <= 0")); + P_Panic(LIT("Tried to create texture with dimension <= 0")); } LOCAL_PERSIST const DXGI_FORMAT formats[] = { [GP_TEXTURE_FORMAT_R8_UNORM] = DXGI_FORMAT_R8_UNORM, @@ -2222,7 +2222,7 @@ G_Resource *gp_texture_alloc(G_TextureFormat format, u32 flags, V2i32 size, void dxgi_format = formats[format]; } if (format == 0) { - sys_panic(LIT("Tried to create texture with unknown format")); + P_Panic(LIT("Tried to create texture with unknown format")); } D3D12_HEAP_PROPERTIES heap_props = { .Type = D3D12_HEAP_TYPE_DEFAULT }; @@ -2260,11 +2260,11 @@ G_Resource *gp_texture_alloc(G_TextureFormat format, u32 flags, V2i32 size, void /* Upload texture */ if (initial_data) { /* TODO: Make wait optional */ - struct snc_counter counter = ZI; + P_Counter counter = ZI; struct dx12_upload_job_sig sig = ZI; sig.resource = r; sig.data = initial_data; - sys_run(1, dx12_upload_job, &sig, SYS_POOL_INHERIT, SYS_PRIORITY_INHERIT, &counter); + P_Run(1, dx12_upload_job, &sig, P_Pool_Inherit, P_Priority_Inherit, &counter); snc_counter_wait(&counter); } @@ -2281,7 +2281,7 @@ V2i32 gp_texture_get_size(G_Resource *resource) * Upload * ========================== */ -INTERNAL SYS_JOB_DEF(dx12_upload_job, job) +INTERNAL P_JobDef(dx12_upload_job, job) { struct dx12_upload_job_sig *sig = job.sig; struct dx12_resource *r = sig->resource; @@ -2335,7 +2335,7 @@ INTERNAL SYS_JOB_DEF(dx12_upload_job, job) HRESULT hr = ID3D12Resource_Map(upload->resource, 0, &read_range, &mapped); if (FAILED(hr) || !mapped) { /* TODO: Don't panic */ - sys_panic(LIT("Failed to map texture upload resource")); + P_Panic(LIT("Failed to map texture upload resource")); } u8 *dst = (u8 *)mapped + placed_footprint.Offset; u8 *src = data; @@ -2375,8 +2375,8 @@ INTERNAL SYS_JOB_DEF(dx12_upload_job, job) struct dx12_wait_fence_job_sig wait_sig = ZI; wait_sig.fence = cq->submit_fence; wait_sig.target = fence_target; - struct snc_counter counter = ZI; - sys_run(1, dx12_wait_fence_job, &wait_sig, SYS_POOL_FLOATING, SYS_PRIORITY_LOW, &counter); + P_Counter counter = ZI; + P_Run(1, dx12_wait_fence_job, &wait_sig, P_Pool_Floating, P_Priority_Low, &counter); snc_counter_wait(&counter); } @@ -3189,7 +3189,7 @@ INTERNAL void swapchain_init_resources(struct swapchain *swapchain) HRESULT hr = IDXGISwapChain3_GetBuffer(swapchain->swapchain, i, &IID_ID3D12Resource, (void **)&resource); if (FAILED(hr)) { /* TODO: Don't panic */ - sys_panic(LIT("Failed to get swapchain buffer")); + P_Panic(LIT("Failed to get swapchain buffer")); } struct swapchain_buffer *sb = &swapchain->buffers[i]; MEMZERO_STRUCT(sb); @@ -3201,15 +3201,15 @@ INTERNAL void swapchain_init_resources(struct swapchain *swapchain) } } -G_Swapchain *gp_swapchain_alloc(struct sys_window *window, V2i32 resolution) +G_Swapchain *gp_swapchain_alloc(P_Window *window, V2i32 resolution) { HRESULT hr = 0; - HWND hwnd = (HWND)sys_window_get_internal_handle(window); + HWND hwnd = (HWND)P_GetInternalWindowHandle(window); struct command_queue *cq = G.command_queues[DX12_QUEUE_DIRECT]; struct swapchain *swapchain = 0; { - struct snc_lock lock = snc_lock_e(&G.swapchains_mutex); + P_Lock lock = snc_lock_e(&G.swapchains_mutex); if (G.first_free_swapchain) { swapchain = G.first_free_swapchain; G.first_free_swapchain = swapchain->next_free; @@ -3236,14 +3236,14 @@ G_Swapchain *gp_swapchain_alloc(struct sys_window *window, V2i32 resolution) desc.SwapEffect = DXGI_SWAP_EFFECT_FLIP_DISCARD; hr = IDXGIFactory2_CreateSwapChainForHwnd(G.factory, (IUnknown *)cq->cq, hwnd, &desc, 0, 0, &swapchain1); if (FAILED(hr)) { - sys_panic(LIT("Failed to create IDXGISwapChain1")); + P_Panic(LIT("Failed to create IDXGISwapChain1")); } } /* Upgrade to swapchain3 */ hr = IDXGISwapChain1_QueryInterface(swapchain1, &IID_IDXGISwapChain3, (void **)&swapchain->swapchain); if (FAILED(hr)) { - sys_panic(LIT("Failed to create IDXGISwapChain3")); + P_Panic(LIT("Failed to create IDXGISwapChain3")); } /* Create waitable object */ @@ -3293,9 +3293,9 @@ INTERNAL struct swapchain_buffer *update_swapchain(struct swapchain *swapchain, struct command_queue *cq = G.command_queues[DX12_QUEUE_DIRECT]; /* Lock direct queue submissions (in case any write to backbuffer) */ /* TODO: Less overkill approach - Only flush present_blit since we know it's the only operation targeting backbuffer */ - struct snc_lock lock = snc_lock_e(&cq->submit_fence_mutex); + P_Lock lock = snc_lock_e(&cq->submit_fence_mutex); //DEBUGBREAKABLE; - //struct snc_lock lock = snc_lock_e(&G.global_command_list_record_mutex); + //P_Lock lock = snc_lock_e(&G.global_command_list_record_mutex); { /* Flush direct queue */ //ID3D12CommandQueue_Signal(cq->cq, cq->submit_fence, ++cq->submit_fence_target); @@ -3317,7 +3317,7 @@ INTERNAL struct swapchain_buffer *update_swapchain(struct swapchain *swapchain, hr = IDXGISwapChain_ResizeBuffers(swapchain->swapchain, 0, resolution.x, resolution.y, DXGI_FORMAT_UNKNOWN, DX12_SWAPCHAIN_FLAGS); if (FAILED(hr)) { /* TODO: Don't panic */ - sys_panic(LIT("Failed to resize swapchain")); + P_Panic(LIT("Failed to resize swapchain")); } } snc_unlock(&lock); @@ -3464,7 +3464,7 @@ void gp_present(G_Swapchain *gp_swapchain, V2i32 backbuffer_resolution, G_Resour __profn("Mark queue frames"); /* Lock because frame marks shouldn't occur while command lists are recording */ - struct snc_lock lock = snc_lock_e(&G.global_command_list_record_mutex); + P_Lock lock = snc_lock_e(&G.global_command_list_record_mutex); for (u32 i = 0; i < countof(G.command_queues); ++i) { { struct command_queue *cq = G.command_queues[i]; @@ -3487,7 +3487,7 @@ void gp_present(G_Swapchain *gp_swapchain, V2i32 backbuffer_resolution, G_Resour * Evictor thread * ========================== */ -INTERNAL SYS_JOB_DEF(dx12_evictor_job, _) +INTERNAL P_JobDef(dx12_evictor_job, _) { (UNUSED)_; @@ -3505,7 +3505,7 @@ INTERNAL SYS_JOB_DEF(dx12_evictor_job, _) struct fenced_release_data *fenced_releases = 0; { __profn("Copy queued releases"); - struct snc_lock lock = snc_lock_e(&G.fenced_releases_mutex); + P_Lock lock = snc_lock_e(&G.fenced_releases_mutex); num_fenced_releases = G.fenced_releases_arena->pos / sizeof(struct fenced_release_data); fenced_releases = arena_push_array_no_zero(scratch.arena, struct fenced_release_data, num_fenced_releases); MEMCPY(fenced_releases, arena_base(G.fenced_releases_arena), G.fenced_releases_arena->pos); @@ -3528,8 +3528,8 @@ INTERNAL SYS_JOB_DEF(dx12_evictor_job, _) sig.fence = cq->submit_fence; sig.target = targets[i]; { - struct snc_counter counter = ZI; - sys_run(1, dx12_wait_fence_job, &sig, SYS_POOL_FLOATING, SYS_PRIORITY_LOW, &counter); + P_Counter counter = ZI; + P_Run(1, dx12_wait_fence_job, &sig, P_Pool_Floating, P_Priority_Low, &counter); snc_counter_wait(&counter); } } @@ -3563,7 +3563,7 @@ INTERNAL SYS_JOB_DEF(dx12_evictor_job, _) } scratch_end(scratch); } - struct snc_lock lock = snc_lock_e(&G.evictor_wake_mutex); + P_Lock lock = snc_lock_e(&G.evictor_wake_mutex); { while (!G.evictor_shutdown && G.evictor_wake_gen == 0) { snc_cv_wait(&G.evictor_wake_cv, &lock); diff --git a/src/mixer/mixer.h b/src/mixer/mixer.h index ce2ff76a..3d50fe05 100644 --- a/src/mixer/mixer.h +++ b/src/mixer/mixer.h @@ -2,7 +2,7 @@ #define MIXER_H #include "../base/base.h" -#include "../sys/sys.h" +#include "../platform/platform.h" #include "../sound/sound.h" #include "mixer_core.h" diff --git a/src/mixer/mixer_core.c b/src/mixer/mixer_core.c index 310b0da6..1e2bd34a 100644 --- a/src/mixer/mixer_core.c +++ b/src/mixer/mixer_core.c @@ -26,7 +26,7 @@ struct mix { M_TrackDesc desc; struct effect_data effect_data; - struct sound *source; + SND_Sound *source; u64 source_pos; }; @@ -34,7 +34,7 @@ struct track { u64 gen; /* Controlled via interface */ - struct sound *sound; + SND_Sound *sound; M_TrackDesc desc; /* Internal */ @@ -45,7 +45,7 @@ struct track { }; GLOBAL struct { - struct snc_mutex mutex; + P_Mutex mutex; /* Listener */ V2 listener_pos; @@ -94,7 +94,7 @@ INTERNAL struct track *track_from_handle(M_Handle handle) } } -INTERNAL struct track *track_alloc_locked(struct snc_lock *lock, struct sound *sound) +INTERNAL struct track *track_alloc_locked(P_Lock *lock, SND_Sound *sound) { snc_assert_locked_e(lock, &G.mutex); (UNUSED)lock; @@ -133,7 +133,7 @@ INTERNAL struct track *track_alloc_locked(struct snc_lock *lock, struct sound *s return track; } -INTERNAL void track_release_locked(struct snc_lock *lock, struct track *track) +INTERNAL void track_release_locked(P_Lock *lock, struct track *track) { snc_assert_locked_e(lock, &G.mutex); (UNUSED)lock; @@ -172,16 +172,16 @@ INTERNAL void track_release_locked(struct snc_lock *lock, struct track *track) /* TODO: Rework interface to take "mixer_cmd"s instead of * directly modifying tracks. */ -M_Handle mixer_play(struct sound *sound) +M_Handle mixer_play(SND_Sound *sound) { return mixer_play_ex(sound, MIXER_DESC()); } -M_Handle mixer_play_ex(struct sound *sound, M_TrackDesc desc) +M_Handle mixer_play_ex(SND_Sound *sound, M_TrackDesc desc) { struct track *track; { - struct snc_lock lock = snc_lock_e(&G.mutex); + P_Lock lock = snc_lock_e(&G.mutex); { track = track_alloc_locked(&lock, sound); track->desc = desc; @@ -199,7 +199,7 @@ M_TrackDesc mixer_track_get(M_Handle handle) struct track *track = track_from_handle(handle); if (track) { /* TODO: Only lock mutex on track itself or something */ - struct snc_lock lock = snc_lock_e(&G.mutex); + P_Lock lock = snc_lock_e(&G.mutex); { /* Confirm handle is still valid now that we're locked */ track = track_from_handle(handle); @@ -219,7 +219,7 @@ void mixer_track_set(M_Handle handle, M_TrackDesc desc) struct track *track = track_from_handle(handle); if (track) { /* TODO: Only lock mutex on track itself or something */ - struct snc_lock lock = snc_lock_e(&G.mutex); + P_Lock lock = snc_lock_e(&G.mutex); { /* Confirm handle is still valid now that we're locked */ track = track_from_handle(handle); @@ -233,7 +233,7 @@ void mixer_track_set(M_Handle handle, M_TrackDesc desc) void mixer_set_listener(V2 pos, V2 dir) { - struct snc_lock lock = snc_lock_e(&G.mutex); + P_Lock lock = snc_lock_e(&G.mutex); { G.listener_pos = pos; G.listener_dir = v2_norm(dir); @@ -245,7 +245,7 @@ void mixer_set_listener(V2 pos, V2 dir) * Update * ========================== */ -INTERNAL i16 sample_sound(struct sound *sound, u64 sample_pos, b32 wrap) +INTERNAL i16 sample_sound(SND_Sound *sound, u64 sample_pos, b32 wrap) { if (wrap) { return sound->pcm.samples[sample_pos % sound->pcm.count]; @@ -274,7 +274,7 @@ M_PcmF32 mixer_update(Arena *arena, u64 frame_count) struct mix **mixes = 0; u64 mixes_count = 0; { - struct snc_lock lock = snc_lock_e(&G.mutex); + P_Lock lock = snc_lock_e(&G.mutex); /* Read listener info */ listener_pos = G.listener_pos; @@ -301,7 +301,7 @@ M_PcmF32 mixer_update(Arena *arena, u64 frame_count) continue; } - struct sound *source = mix->source; + SND_Sound *source = mix->source; M_TrackDesc desc = mix->desc; struct effect_data *effect_data = &mix->effect_data; b32 source_is_stereo = source->flags & SOUND_FLAG_STEREO; @@ -462,7 +462,7 @@ M_PcmF32 mixer_update(Arena *arena, u64 frame_count) { __profn("Update track effect data"); - struct snc_lock lock = snc_lock_e(&G.mutex); + P_Lock lock = snc_lock_e(&G.mutex); for (u64 i = 0; i < mixes_count; ++i) { struct mix *mix = mixes[i]; struct track *track = track_from_handle(mix->track_handle); diff --git a/src/mixer/mixer_core.h b/src/mixer/mixer_core.h index 0d724a11..68be8eeb 100644 --- a/src/mixer/mixer_core.h +++ b/src/mixer/mixer_core.h @@ -1,5 +1,3 @@ -struct sound; - #define MIXER_FLAG_NONE 0x0 #define MIXER_FLAG_SPATIALIZE 0x1 @@ -44,8 +42,8 @@ struct M_StartupReceipt { i32 _; }; M_StartupReceipt mixer_startup(void); /* Interface */ -M_Handle mixer_play(struct sound *sound); -M_Handle mixer_play_ex(struct sound *sound, M_TrackDesc desc); +M_Handle mixer_play(SND_Sound *sound); +M_Handle mixer_play_ex(SND_Sound *sound, M_TrackDesc desc); M_TrackDesc mixer_track_get(M_Handle handle); void mixer_track_set(M_Handle handle, M_TrackDesc desc); void mixer_set_listener(V2 pos, V2 dir); diff --git a/src/net/net.h b/src/net/net.h index 443142b0..420d8830 100644 --- a/src/net/net.h +++ b/src/net/net.h @@ -2,7 +2,7 @@ #define NET_H #include "../base/base.h" -#include "../sys/sys.h" +#include "../platform/platform.h" #include "net_core.h" diff --git a/src/net/net_core.c b/src/net/net_core.c index 418787c4..8643b813 100644 --- a/src/net/net_core.c +++ b/src/net/net_core.c @@ -34,7 +34,7 @@ struct host_channel { struct host_channel *next_free; - struct sys_address address; + P_Address address; u64 address_hash; struct host_channel *next_address_hash; struct host_channel *prev_address_hash; @@ -76,7 +76,7 @@ struct host_channel_list { struct host_rcv_packet { struct sock *sock; - struct sys_address address; + P_Address address; String data; struct host_rcv_packet *next; }; @@ -159,14 +159,14 @@ N_Host *host_alloc(u16 listen_port) host->num_msg_assembler_lookup_bins = N_NumMsgAssemblerLookupBins; host->msg_assembler_lookup_bins = arena_push_array(host->arena, struct host_msg_assembler_lookup_bin, host->num_msg_assembler_lookup_bins); - host->sock = sys_sock_alloc(listen_port, MEBI(2), MEBI(2)); + host->sock = P_AllocSock(listen_port, MEBI(2), MEBI(2)); return host; } void host_release(N_Host *host) { - sys_sock_release(host->sock); + P_ReleaseSock(host->sock); buddy_ctx_release(host->buddy); arena_release(host->rcv_buffer_write->arena); @@ -180,17 +180,17 @@ void host_release(N_Host *host) * Channel * ========================== */ -INTERNAL u64 hash_from_address(struct sys_address address) +INTERNAL u64 hash_from_address(P_Address address) { return hash_fnv64(HASH_FNV64_BASIS, STRING_FROM_STRUCT(&address)); } -INTERNAL struct host_channel *host_channel_from_address(N_Host *host, struct sys_address address) +INTERNAL struct host_channel *host_channel_from_address(N_Host *host, P_Address address) { u64 hash = hash_from_address(address); N_ChannelLookupBin *bin = &host->channel_lookup_bins[hash % host->num_channel_lookup_bins]; for (struct host_channel *channel = bin->first; channel; channel = channel->next_address_hash) { - if (channel->address_hash == hash && sys_address_eq(channel->address, address)) { + if (channel->address_hash == hash && P_AddressIsEqual(channel->address, address)) { return channel; } } @@ -238,7 +238,7 @@ INTERNAL struct host_channel_list host_channels_from_id(Arena *arena, N_Host *ho return res; } -INTERNAL struct host_channel *host_channel_alloc(N_Host *host, struct sys_address address) +INTERNAL struct host_channel *host_channel_alloc(N_Host *host, P_Address address) { N_ChannelId id = ZI; struct host_channel *channel; @@ -546,7 +546,7 @@ INTERNAL N_Cmd *host_cmd_alloc_and_append(N_Host *host) return cmd; } -void host_queue_connect_to_address(N_Host *host, struct sys_address connect_address) +void host_queue_connect_to_address(N_Host *host, P_Address connect_address) { struct host_channel *channel = host_channel_from_address(host, connect_address); if (!channel->valid) { @@ -602,7 +602,7 @@ N_EventList host_update_begin(Arena *arena, N_Host *host) TempArena scratch = scratch_begin(arena); N_EventList events = ZI; - i64 now_ns = sys_time_ns(); + i64 now_ns = P_TimeNs(); { __profn("Read packets"); @@ -611,10 +611,10 @@ N_EventList host_update_begin(Arena *arena, N_Host *host) struct host_rcv_packet *last_packet = 0; { __profn("Read socket"); - struct sys_sock *sock = host->sock; - struct sys_sock_read_result res = ZI; - while ((res = sys_sock_read(scratch.arena, sock)).valid) { - struct sys_address address = res.address; + P_Sock *sock = host->sock; + P_SockReadResult res = ZI; + while ((res = P_ReadSock(scratch.arena, sock)).valid) { + P_Address address = res.address; String data = res.data; if (data.len > 0) { struct host_rcv_packet *packet = arena_push(scratch.arena, struct host_rcv_packet); @@ -635,7 +635,7 @@ N_EventList host_update_begin(Arena *arena, N_Host *host) __profn("Process host packets"); for (struct host_rcv_packet *packet = first_packet; packet; packet = packet->next) { //struct sock *sock = packet->sock; - struct sys_address address = packet->address; + P_Address address = packet->address; Bitbuff bb = bitbuff_from_string(packet->data); BitbuffReader br = br_from_bitbuff(&bb); u32 magic = br_read_ubits(&br, 32); /* TODO: implicitly encode magic into crc32 */ @@ -672,7 +672,7 @@ N_EventList host_update_begin(Arena *arena, N_Host *host) { /* A foreign host is trying to connect to us */ if (!channel->valid) { - logf_info("Host received conection attempt from %F", FMT_STR(sys_string_from_address(scratch.arena, address))); + logf_info("Host received conection attempt from %F", FMT_STR(P_StringFromAddress(scratch.arena, address))); /* TODO: Verify that some per-host uuid isn't present in a rolling window to prevent reconnects right after a disconnect? */ channel = host_channel_alloc(host, address); } @@ -685,7 +685,7 @@ N_EventList host_update_begin(Arena *arena, N_Host *host) { /* We successfully connected to a foreign host and they are ready to receive messages */ if (channel->valid && !channel->connected) { - logf_info("Host received connection from %F", FMT_STR(sys_string_from_address(scratch.arena, address))); + logf_info("Host received connection from %F", FMT_STR(P_StringFromAddress(scratch.arena, address))); N_Event *event = push_event(arena, &events); event->kind = HOST_EVENT_KIND_CHANNEL_OPENED; event->channel_id = channel->id; @@ -697,7 +697,7 @@ N_EventList host_update_begin(Arena *arena, N_Host *host) { /* A foreign host disconnected from us */ if (channel->valid) { - logf_info("Host received disconnection from %F", FMT_STR(sys_string_from_address(scratch.arena, address))); + logf_info("Host received disconnection from %F", FMT_STR(P_StringFromAddress(scratch.arena, address))); N_Event *event = push_event(arena, &events); event->kind = HOST_EVENT_KIND_CHANNEL_CLOSED; event->channel_id = channel->id; @@ -981,19 +981,19 @@ void host_update_end(N_Host *host) { __profn("Send host packets"); for (u64 i = 0; i < host->num_channels_reserved; ++i) { - struct sys_sock *sock = host->sock; + P_Sock *sock = host->sock; struct host_channel *channel = &host->channels[i]; u64 total_sent = 0; if (channel->valid) { - struct sys_address address = channel->address; + P_Address address = channel->address; /* Send reliable packets to channel */ for (N_SndPacket *packet = channel->first_reliable_packet; packet; packet = packet->next) { - sys_sock_write(sock, address, STRING(packet->data_len, packet->data)); + P_WriteSock(sock, address, STRING(packet->data_len, packet->data)); total_sent += packet->data_len; } /* Send unreliable packets to channel */ for (N_SndPacket *packet = channel->first_unreliable_packet; packet; packet = packet->next) { - sys_sock_write(sock, address, STRING(packet->data_len, packet->data)); + P_WriteSock(sock, address, STRING(packet->data_len, packet->data)); total_sent += packet->data_len; } /* Release unreliable packets */ diff --git a/src/net/net_core.h b/src/net/net_core.h index 4331eae1..0c59a6d4 100644 --- a/src/net/net_core.h +++ b/src/net/net_core.h @@ -94,7 +94,7 @@ typedef struct N_Host N_Host; struct N_Host { Arena *arena; - struct sys_sock *sock; + P_Sock *sock; BuddyCtx *buddy; /* For storing msg assembler data */ @@ -118,7 +118,7 @@ struct N_Host { u64 num_msg_assembler_lookup_bins; /* Double buffer for incoming data */ - struct snc_mutex rcv_buffer_write_mutex; + P_Mutex rcv_buffer_write_mutex; N_RcvBuffer *rcv_buffer_read; N_RcvBuffer *rcv_buffer_write; @@ -146,7 +146,7 @@ void host_release(N_Host *host); * Queue * ========================== */ -void host_queue_connect_to_address(N_Host *host, struct sys_address connect_address); +void host_queue_connect_to_address(N_Host *host, P_Address connect_address); void host_queue_disconnect(N_Host *host, N_ChannelId channel_id); diff --git a/src/platform/platform.c b/src/platform/platform.c new file mode 100644 index 00000000..0c713800 --- /dev/null +++ b/src/platform/platform.c @@ -0,0 +1,11 @@ +#include "platform.h" + +#include "platform_snc.c" +#include "platform_sleep.c" +#include "platform_log.c" + +#if PLATFORM_WINDOWS +# include "platform_win32.c" +#else +# error Platform core not implemented +#endif diff --git a/src/platform/platform.h b/src/platform/platform.h new file mode 100644 index 00000000..0e8d0c2c --- /dev/null +++ b/src/platform/platform.h @@ -0,0 +1,15 @@ +#ifndef PLATFORM_H +#define PLATFORM_H + +#include "../base/base.h" + +#include "platform_snc.h" +#include "platform_sleep.h" +#include "platform_core.h" +#include "platform_log.h" + +#if PLATFORM_WINDOWS +# include "platform_win32.h" +#endif + +#endif diff --git a/src/platform/platform_core.h b/src/platform/platform_core.h new file mode 100644 index 00000000..abf593b6 --- /dev/null +++ b/src/platform/platform_core.h @@ -0,0 +1,482 @@ +/* ========================== * + * Wait + * ========================== */ + + /* Futex-like wait & wake */ + +void P_Wait(volatile void *addr, void *cmp, u32 size, i64 timeout_ns); + +void P_Wake(void *addr, i32 count); + +/* ========================== * + * Job + * ========================== */ + + /* Work pools contain their own worker threads with their own thread priority/affinity based on the intended context of the pool. */ +typedef enum P_Pool { + P_Pool_Inherit = -1, + + /* The floating pool contains a large number of lower priority threads that have affinity over the entire CPU. + * Other pools should push jobs that only block and do no work here so that they can yield on the blocking job rather than blocking themselves. */ + P_Pool_Floating = 0, + + P_Pool_Background = 1, + P_Pool_Audio = 2, + P_Pool_User = 3, + P_Pool_Sim = 4, + + P_Pool_Count +} P_Pool; + +/* Job execution order within a pool is based on priority. */ +typedef enum P_Priority { + P_Priority_Inherit = -1, + P_Priority_High = 0, + P_Priority_Normal = 1, + P_Priority_Low = 2, + + P_Priority_Count +} P_Priority; + +typedef struct P_JobData P_JobData; +struct P_JobData { + i32 id; + void *sig; +}; + +#define P_JobDef(job_name, arg_name) void job_name(P_JobData arg_name) +typedef P_JobDef(P_JobFunc, job_data); + +void P_Run(i32 count, P_JobFunc *func, void *sig, P_Pool pool_kind, P_Priority priority, P_Counter *counter); + +/* ========================== * + * Time + * ========================== */ + +typedef struct P_DateTime P_DateTime; +struct P_DateTime { + u32 year; + u32 month; + u32 day_of_week; + u32 day; + u32 hour; + u32 minute; + u32 second; + u32 milliseconds; +}; + +P_DateTime P_LocalTime(void); + +i64 P_TimeNs(void); + +/* ========================== * + * File system + * + * NOTE: File paths use forward slash '/' as delimiter + * ========================== */ + +typedef struct P_File P_File; +struct P_File { + u64 handle; + b32 valid; +}; + +typedef struct P_FileTime P_FileTime; +struct P_FileTime { + P_DateTime created; + P_DateTime accessed; + P_DateTime modified; +}; + +String P_GetWritePath(Arena *arena); + +b32 P_IsFile(String path); + +b32 P_IsDir(String path); + +void P_MkDir(String path); + +P_File P_OpenFileRead(String path); + +P_File P_OpenFileReadWait(String path); /* Waits until file is not being used by another program */ + +P_File P_OpenFileWrite(String path); + +P_File P_OpenFileAppend(String path); + +void P_CloseFIle(P_File file); + +String P_ReadFile(Arena *arena, P_File file); + +void P_WriteFile(P_File file, String data); + +u64 P_GetFileSize(P_File file); + +P_FileTime P_GetFileTime(P_File file); + +/* ========================== * + * File map + * ========================== */ + +typedef struct P_FileMap P_FileMap; +struct P_FileMap { + String mapped_memory; + u64 handle; + b32 valid; +}; + +P_FileMap P_OpenFileMap(P_File file); + +void P_CloseFileMap(P_FileMap map); + +String P_GetFileMapData(P_FileMap map); + +/* ========================== * + * Watch + * ========================== */ + +typedef enum P_WatchInfoKind { + P_WatchInfoKind_Unknown, + P_WatchInfoKind_Added, + P_WatchInfoKind_Removed, + P_WatchInfoKind_Modified, + P_WatchInfoKind_RenamedOld, + P_WatchInfoKind_RenamedNew +} P_WatchInfoKind; + +typedef struct P_WatchInfo P_WatchInfo; +struct P_WatchInfo { + P_WatchInfoKind kind; + String name; + P_WatchInfo *next; + P_WatchInfo *prev; +}; + +typedef struct P_WatchInfoList P_WatchInfoList; +struct P_WatchInfoList { + P_WatchInfo *first; + P_WatchInfo *last; + u64 count; +}; + +typedef struct P_Watch P_Watch; + +P_Watch *P_AllocWatch(String path); + +void P_ReleaseWatch(P_Watch *dw); + +P_WatchInfoList P_ReadWatchWait(Arena *arena, P_Watch *dw); + +void P_WakeWatch(P_Watch *dw); + +/* ========================== * + * Window + * ========================== */ + +typedef struct P_Window P_Window; + +typedef enum P_Btn { + P_Btn_None, + + P_Btn_M1, + P_Btn_M2, + P_Btn_M3, + P_Btn_M4, + P_Btn_M5, + + P_Btn_MWheelUp, + P_Btn_MWheelDown, + + P_Btn_ESC, + P_Btn_F1, + P_Btn_F2, + P_Btn_F3, + P_Btn_F4, + P_Btn_F5, + P_Btn_F6, + P_Btn_F7, + P_Btn_F8, + P_Btn_F9, + P_Btn_F10, + P_Btn_F11, + P_Btn_F12, + P_Btn_F13, + P_Btn_F14, + P_Btn_F15, + P_Btn_F16, + P_Btn_F17, + P_Btn_F18, + P_Btn_F19, + P_Btn_F20, + P_Btn_F21, + P_Btn_F22, + P_Btn_F23, + P_Btn_F24, + P_Btn_GraveAccent, + P_Btn_0, + P_Btn_1, + P_Btn_2, + P_Btn_3, + P_Btn_4, + P_Btn_5, + P_Btn_6, + P_Btn_7, + P_Btn_8, + P_Btn_9, + P_Btn_Minus, + P_Btn_Equal, + P_Btn_Backspace, + P_Btn_Delete, + P_Btn_Tab, + P_Btn_A, + P_Btn_B, + P_Btn_C, + P_Btn_D, + P_Btn_E, + P_Btn_F, + P_Btn_G, + P_Btn_H, + P_Btn_I, + P_Btn_J, + P_Btn_K, + P_Btn_L, + P_Btn_M, + P_Btn_N, + P_Btn_O, + P_Btn_P, + P_Btn_Q, + P_Btn_R, + P_Btn_S, + P_Btn_T, + P_Btn_U, + P_Btn_V, + P_Btn_W, + P_Btn_X, + P_Btn_Y, + P_Btn_Z, + P_Btn_Space, + P_Btn_Enter, + P_Btn_Ctrl, + P_Btn_Shift, + P_Btn_Alt, + P_Btn_Up, + P_Btn_Left, + P_Btn_Down, + P_Btn_Right, + P_Btn_PageUp, + P_Btn_PageDown, + P_Btn_Home, + P_Btn_End, + P_Btn_ForwardSlash, + P_Btn_Period, + P_Btn_Comma, + P_Btn_Quote, + P_Btn_LeftBracket, + P_Btn_RightBracket, + P_Btn_Insert, + P_Btn_Semicolon, + + P_Btn_Count +} P_Btn; + +typedef enum P_WindowEventKind { + P_WindowEventKind_None, + + P_WindowEventKind_ButtonDown, + P_WindowEventKind_ButtonUp, + P_WindowEventKind_CursorMove, + P_WindowEventKind_MouseMove, + P_WindowEventKind_Text, + P_WindowEventKind_Quit, + + P_WindowEventKind_Count +} P_WindowEventKind; + +typedef struct P_WindowEvent P_WindowEvent; +struct P_WindowEvent { + P_WindowEventKind kind; + + /* P_WindowEventKind_BUTTON_DOWN */ + /* P_WindowEventKind_BUTTON_UP */ + P_Btn button; + b32 is_repeat; + + /* P_WindowEventKind_TEXT */ + u32 text_codepoint; + + /* P_WindowEventKind_CURSOR_MOVE */ + V2 cursor_position; + + /* P_WindowEventKind_MOUSE_MOVE */ + V2 mouse_delta; +}; + +typedef struct P_WindowEventArray P_WindowEventArray; +struct P_WindowEventArray { + u64 count; + P_WindowEvent *events; +}; + +/* NOTE: + * A window object can only be interacted with by the thread that created it. + * This restriction is in place because of how Win32 works, IE you cannot + * create a Win32 window in one thread and process its messages on another. */ + +typedef enum P_WindowSettingsFlag { + P_WindowSettingsFlag_None = 0x00, + P_WindowSettingsFlag_Fullscreen = 0x01, + + /* NOTE: Both maximized and minimized can be true at the same time. This + * means that the window was minimized from a maximized state, and will + * restore to being maximized once it's un-minimized. */ + P_WindowSettingsFlag_Maximized = 0x02, + P_WindowSettingsFlag_Minimized = 0x04 +} P_WindowSettingsFlag; + +typedef enum P_WindowFlag { + P_WindowFlag_None = 0x00, + P_WindowFlag_Showing = 0x02 +} P_WindowFlag; + +/* P_UpdateWindowSettings should be used when altering settings values */ +typedef struct P_WindowSettings P_WindowSettings; +struct P_WindowSettings { + char title[256]; + u32 flags; + + /* NOTE: Below fields are NOT representative of actual window dimensions. + * These values represent the window dimensions when the window is not + * maximized, minimized, or fullscreen. AKA 'floating'. Use + * `P_GetWindowSize` for rendering instead. */ + i32 floating_x; + i32 floating_y; + i32 floating_width; + i32 floating_height; +}; + +P_Window *P_AllocWindow(void); + +void P_ReleaseWindow(P_Window *window); + +P_WindowEventArray P_PopWindowEvents(Arena *arena, P_Window *window); + +void P_UpdateWindowSettings(P_Window *window, P_WindowSettings *settings); + +P_WindowSettings P_GetWindowSettings(P_Window *window); + +void P_ShowWindow(P_Window *window); + +V2 P_GetWindowSize(P_Window *window); + +V2 P_GetWindowMonitorSize(P_Window *window); + +/* Returns a platform specific representation of the window. E.g. `hwnd` on win32. */ +u64 P_GetInternalWindowHandle(P_Window *window); + +void P_SetWindowCursorPos(P_Window *window, V2 pos); + +void P_ShowWindowCursor(P_Window *window); + +void P_HideWindowCursor(P_Window *window); + +void P_EnableWindoweCursorClip(P_Window *window, Rect bounds); + +void P_DisableWindoweCursorClip(P_Window *window); + +void P_ToggleWindowTopmost(P_Window *window); + +/* ========================== * + * Address + * ========================== */ + +typedef enum P_AddressFamily { + P_AddressFamily_Ipv4, + P_AddressFamily_Ipv6 +} P_AddressFamily; + +typedef struct P_Address P_Address; +struct P_Address { + b32 valid; + P_AddressFamily family; + /* NOTE: ipnb & portnb are stored in network byte order */ + u8 ipnb[16]; + u16 portnb; +}; + +P_Address P_AddressFromString(String str); + +P_Address P_AddressFromIpPortCstr(char *ip_cstr, char *port_cstr); + +P_Address P_AddressFromPort(u16 port); + +String P_StringFromAddress(Arena *arena, P_Address address); + +b32 P_AddressIsEqual(P_Address a, P_Address b); + +/* ========================== * + * Sock + * ========================== */ + +typedef struct P_SockReadResult P_SockReadResult; +struct P_SockReadResult { + b32 valid; /* Since data.len = 0 can be valid */ + P_Address address; + String data; +}; + +typedef struct P_Sock P_Sock; + +P_Sock *P_AllocSock(u16 listen_port, u64 sndbuf_size, u64 rcvbuf_size); + +void P_ReleaseSock(P_Sock *sock); + +P_SockReadResult P_ReadSock(Arena *arena, P_Sock *sock); + +void P_WriteSock(P_Sock *sock, P_Address address, String data); + +/* ========================== * + * Util + * ========================== */ + +typedef enum P_MessageBoxKind { + P_MessageBoxKind_Ok, + P_MessageBoxKind_Warning, + P_MessageBoxKind_Error, + P_MessageBoxKind_Fatal +} P_MessageBoxKind; + +void P_MessageBox(P_MessageBoxKind kind, String message); + +void P_SetClipboardText(String str); + +String P_GetClipboardText(Arena *arena); + +u32 P_GetLogicalProcessorCount(void); + +u32 P_GetThreadId(void); + +i64 P_GetCurrentSchedulerPeriodNs(void); + +/* ========================== * + * Exit + * ========================== */ + + +#define P_ExitFuncDef(name) void name(void) +typedef P_ExitFuncDef(P_ExitFunc); + +/* Registers a function to be called during graceful shutdown (in reverse order) */ +void P_OnExit(P_ExitFunc *func); + +/* Signals the program to shut down gracefully and run exit callbacks */ +void P_Exit(void); + +/* Forcefully exits the program and displays `msg` to the user */ +void P_Panic(String msg); + +/* ========================== * + * App entry point + * ========================== */ + + /* Must be defined by app */ +void P_AppStartup(String args_str); diff --git a/src/sys/sys_log.c b/src/platform/platform_log.c similarity index 86% rename from src/sys/sys_log.c rename to src/platform/platform_log.c index 6efe5c3a..2400753d 100644 --- a/src/sys/sys_log.c +++ b/src/platform/platform_log.c @@ -11,17 +11,17 @@ struct log_event_callback { struct shared_log_ctx { Atomic32 initialized; - struct snc_mutex callbacks_mutex; + P_Mutex callbacks_mutex; Arena *callbacks_arena; struct log_event_callback *first_callback; struct log_event_callback *last_callback; - struct sys_file file; + P_File file; b32 file_valid; }; GLOBAL struct shared_log_ctx g_shared_log_ctx = ZI; -GLOBAL READONLY struct log_level_settings g_log_settings[LOG_LEVEL_COUNT] = { +GLOBAL READONLY P_LogLevelSettings g_log_settings[LOG_LEVEL_COUNT] = { [LOG_LEVEL_CRITICAL] = { LIT_NOCAST("CRITICAL"), COLOR_PURPLE @@ -64,10 +64,10 @@ void log_startup(String logfile_path) ctx->callbacks_arena = arena_alloc(MEBI(8)); if (logfile_path.len > 0) { /* Create / wipe log file */ - sys_file_close(sys_file_open_write(logfile_path)); + P_CloseFIle(P_OpenFileWrite(logfile_path)); /* Keep log file open for appending */ - if (sys_is_file(logfile_path)) { - ctx->file = sys_file_open_append(logfile_path); + if (P_IsFile(logfile_path)) { + ctx->file = P_OpenFileAppend(logfile_path); ctx->file_valid = 1; } } @@ -82,7 +82,7 @@ void log_register_callback(log_event_callback_func *func, i32 level) { struct shared_log_ctx *ctx = &g_shared_log_ctx; if (!atomic32_fetch(&ctx->initialized)) { return; } - struct snc_lock lock = snc_lock_e(&ctx->callbacks_mutex); + P_Lock lock = snc_lock_e(&ctx->callbacks_mutex); { struct log_event_callback *callback = arena_push(ctx->callbacks_arena, struct log_event_callback); callback->func = func; @@ -110,7 +110,7 @@ INTERNAL void append_to_logfile(String msg) if (ctx->file_valid) { TempArena scratch = scratch_begin_no_conflict(); String msg_line = string_cat(scratch.arena, msg, LIT("\n")); - sys_file_write(ctx->file, msg_line); + P_WriteFile(ctx->file, msg_line); scratch_end(scratch); } } @@ -123,9 +123,9 @@ void _log_panic(String msg) if (!atomic32_fetch(&ctx->initialized)) { return; } if (ctx->file_valid) { - sys_file_write(ctx->file, LIT("******** PANICKING ********\n")); - sys_file_write(ctx->file, msg); - sys_file_write(ctx->file, LIT("\n***************************\n")); + P_WriteFile(ctx->file, LIT("******** PANICKING ********\n")); + P_WriteFile(ctx->file, msg); + P_WriteFile(ctx->file, LIT("\n***************************\n")); } } @@ -140,17 +140,17 @@ void _log(i32 level, String msg) if (!atomic32_fetch(&ctx->initialized)) { return; } if (level < 0 || level >= LOG_LEVEL_COUNT) { - sys_panic(LIT("Invalid log level")); + P_Panic(LIT("Invalid log level")); } TempArena scratch = scratch_begin_no_conflict(); - struct sys_datetime datetime = sys_local_time(); - i64 time_ns = sys_time_ns(); + P_DateTime datetime = P_LocalTime(); + i64 time_ns = P_TimeNs(); - u32 tid = sys_current_thread_id(); + u32 tid = P_GetThreadId(); - struct log_level_settings settings = g_log_settings[level]; + P_LogLevelSettings settings = g_log_settings[level]; String shorthand = settings.shorthand; #if LOG_INCLUDE_SOURCE_LOCATION @@ -204,7 +204,7 @@ void _log(i32 level, String msg) /* Run callbacks */ - struct log_event event = ZI; + P_LogEvent event = ZI; event.level = level; event.msg = msg; event.datetime = datetime; @@ -214,7 +214,7 @@ void _log(i32 level, String msg) event.line = line; #endif { - struct snc_lock lock = snc_lock_s(&ctx->callbacks_mutex); + P_Lock lock = snc_lock_s(&ctx->callbacks_mutex); for (struct log_event_callback *callback = ctx->first_callback; callback; callback = callback->next) { if (level <= callback->level) { __profn("Run log callback"); diff --git a/src/sys/sys_log.h b/src/platform/platform_log.h similarity index 96% rename from src/sys/sys_log.h rename to src/platform/platform_log.h index 156ab04d..c2fdb23a 100644 --- a/src/sys/sys_log.h +++ b/src/platform/platform_log.h @@ -27,17 +27,19 @@ * Callback interface * ========================== */ -struct log_level_settings { +typedef struct P_LogLevelSettings P_LogLevelSettings; +struct P_LogLevelSettings { String shorthand; u32 color; }; -struct log_event { +typedef struct P_LogEvent P_LogEvent; +struct P_LogEvent { /* Msg lifetime is only as long as callback duration */ String msg; i32 level; - struct sys_datetime datetime; + P_DateTime datetime; i64 time_ns; /* These will be zeroed if LOG_INCLUDE_SOURCE_LOCATION is disabled */ @@ -45,7 +47,7 @@ struct log_event { i32 line; }; -#define LOG_EVENT_CALLBACK_FUNC_DEF(name, log_event_arg) void name(struct log_event log_event_arg) +#define LOG_EVENT_CALLBACK_FUNC_DEF(name, log_event_arg) void name(P_LogEvent log_event_arg) typedef LOG_EVENT_CALLBACK_FUNC_DEF(log_event_callback_func, log_event); void log_register_callback(log_event_callback_func *func, i32 level); diff --git a/src/sys/sys_sleep.c b/src/platform/platform_sleep.c similarity index 76% rename from src/sys/sys_sleep.c rename to src/platform/platform_sleep.c index c4613ac7..3e80e7ac 100644 --- a/src/sys/sys_sleep.c +++ b/src/platform/platform_sleep.c @@ -2,18 +2,18 @@ void sys_sleep_precise(i64 sleep_time_ns) { __prof; - i64 big_sleep = sys_current_scheduler_period_ns(); + i64 big_sleep = P_GetCurrentSchedulerPeriodNs(); i64 tolerance = (f64)big_sleep * 0.5; //i64 tolerance = 1000000000; - i64 now_ns = sys_time_ns(); + i64 now_ns = P_TimeNs(); i64 target_ns = now_ns + sleep_time_ns; /* Sleep */ while (now_ns < target_ns - big_sleep - tolerance) { __profn("Sleep part"); - sys_wait(0, 0, 0, big_sleep); - now_ns = sys_time_ns(); + P_Wait(0, 0, 0, big_sleep); + now_ns = P_TimeNs(); } /* Spin */ @@ -21,7 +21,7 @@ void sys_sleep_precise(i64 sleep_time_ns) __profn("Sleep spin"); while (now_ns < target_ns) { ix_pause(); - now_ns = sys_time_ns(); + now_ns = P_TimeNs(); } } } @@ -29,7 +29,7 @@ void sys_sleep_precise(i64 sleep_time_ns) void sys_sleep_frame(i64 last_frame_time_ns, i64 target_dt_ns) { if (last_frame_time_ns != 0 && target_dt_ns > 0) { - i64 now_ns = sys_time_ns(); + i64 now_ns = P_TimeNs(); i64 last_frame_dt_ns = now_ns - last_frame_time_ns; i64 sleep_time_ns = target_dt_ns - last_frame_dt_ns; if (sleep_time_ns > 0) { diff --git a/src/sys/sys_sleep.h b/src/platform/platform_sleep.h similarity index 100% rename from src/sys/sys_sleep.h rename to src/platform/platform_sleep.h diff --git a/src/sys/sys_snc.c b/src/platform/platform_snc.c similarity index 76% rename from src/sys/sys_snc.c rename to src/platform/platform_snc.c index f1611ec4..93744741 100644 --- a/src/sys/sys_snc.c +++ b/src/platform/platform_snc.c @@ -4,7 +4,7 @@ * Mutex * ========================== */ -struct snc_lock snc_lock_spin_e(struct snc_mutex *m, i32 spin) +P_Lock snc_lock_spin_e(P_Mutex *m, i32 spin) { b32 locked = 0; i32 spin_cnt = 0; @@ -39,7 +39,7 @@ struct snc_lock snc_lock_spin_e(struct snc_mutex *m, i32 spin) if (spin_cnt < spin) { ix_pause(); } else { - sys_wait(&m->v, &v, 4, I64_MAX); + P_Wait(&m->v, &v, 4, I64_MAX); spin_cnt = 0; } } @@ -49,13 +49,13 @@ struct snc_lock snc_lock_spin_e(struct snc_mutex *m, i32 spin) atomic32_fetch_set(&m->exclusive_fiber_id, FiberId()); #endif - struct snc_lock lock = ZI; + P_Lock lock = ZI; lock.exclusive = 1; lock.mutex = m; return lock; } -struct snc_lock snc_lock_spin_s(struct snc_mutex *m, i32 spin) +P_Lock snc_lock_spin_s(P_Mutex *m, i32 spin) { b32 locked = 0; i32 spin_cnt = 0; @@ -76,29 +76,29 @@ struct snc_lock snc_lock_spin_s(struct snc_mutex *m, i32 spin) if (spin_cnt < spin) { ix_pause(); } else { - sys_wait(&m->v, &v, 4, I64_MAX); + P_Wait(&m->v, &v, 4, I64_MAX); spin_cnt = 0; } } } - struct snc_lock lock = ZI; + P_Lock lock = ZI; lock.mutex = m; return lock; } -struct snc_lock snc_lock_e(struct snc_mutex *m) +P_Lock snc_lock_e(P_Mutex *m) { return snc_lock_spin_e(m, DEFAULT_MUTEX_SPIN); } -struct snc_lock snc_lock_s(struct snc_mutex *m) +P_Lock snc_lock_s(P_Mutex *m) { return snc_lock_spin_s(m, DEFAULT_MUTEX_SPIN); } -void snc_unlock(struct snc_lock *l) +void snc_unlock(P_Lock *l) { - struct snc_mutex *m = l->mutex; + P_Mutex *m = l->mutex; if (l->exclusive) { #if RTC atomic32_fetch_set(&m->exclusive_fiber_id, 0); @@ -107,7 +107,7 @@ void snc_unlock(struct snc_lock *l) } else { atomic32_fetch_add(&m->v, -1); } - sys_wake(&m->v, I32_MAX); + P_Wake(&m->v, I32_MAX); MEMZERO_STRUCT(l); } @@ -115,20 +115,20 @@ void snc_unlock(struct snc_lock *l) * Condition variable * ========================== */ -void snc_cv_wait(struct snc_cv *cv, struct snc_lock *l) +void snc_cv_wait(P_Cv *cv, P_Lock *l) { snc_cv_wait_time(cv, l, I64_MAX); } -void snc_cv_wait_time(struct snc_cv *cv, struct snc_lock *l, i64 timeout_ns) +void snc_cv_wait_time(P_Cv *cv, P_Lock *l, i64 timeout_ns) { u64 old_wake_gen = atomic64_fetch(&cv->wake_gen); - struct snc_mutex *mutex = l->mutex; + P_Mutex *mutex = l->mutex; b32 exclusive = l->exclusive; { snc_unlock(l); { - sys_wait(&cv->wake_gen, &old_wake_gen, sizeof(old_wake_gen), timeout_ns); + P_Wait(&cv->wake_gen, &old_wake_gen, sizeof(old_wake_gen), timeout_ns); } if (exclusive) { *l = snc_lock_e(mutex); @@ -138,30 +138,30 @@ void snc_cv_wait_time(struct snc_cv *cv, struct snc_lock *l, i64 timeout_ns) } } -void snc_cv_signal(struct snc_cv *cv, i32 count) +void snc_cv_signal(P_Cv *cv, i32 count) { atomic64_fetch_add(&cv->wake_gen, 1); - sys_wake(&cv->wake_gen, count); + P_Wake(&cv->wake_gen, count); } /* ========================== * * Counter * ========================== */ -void snc_counter_add(struct snc_counter *counter, i64 x) +void snc_counter_add(P_Counter *counter, i64 x) { i64 old_v = atomic64_fetch_add(&counter->v, x); i64 new_v = old_v + x; if (old_v > 0 && new_v <= 0) { - sys_wake(&counter->v, I32_MAX); + P_Wake(&counter->v, I32_MAX); } } -void snc_counter_wait(struct snc_counter *counter) +void snc_counter_wait(P_Counter *counter) { i64 v = atomic64_fetch(&counter->v); while (v > 0) { - sys_wait(&counter->v, &v, sizeof(v), I64_MAX); + P_Wait(&counter->v, &v, sizeof(v), I64_MAX); v = atomic64_fetch(&counter->v); } } diff --git a/src/platform/platform_snc.h b/src/platform/platform_snc.h new file mode 100644 index 00000000..aa7b5394 --- /dev/null +++ b/src/platform/platform_snc.h @@ -0,0 +1,72 @@ +/* ========================== * + * Mutex + * ========================== */ + +typedef struct P_Mutex P_Mutex; +struct alignas(64) P_Mutex { + /* Bit 31 = Exclusive lock is held + * Bit 30 = Exclusive lock is pending + * Bit 0-30 = Shared locks count + */ + Atomic32 v; + +#if RTC + Atomic32 exclusive_fiber_id; + u8 _pad[56]; +#else + u8 _pad[60]; +#endif +}; +STATIC_ASSERT(sizeof(P_Mutex) == 64); /* Padding validation */ +STATIC_ASSERT(alignof(P_Mutex) == 64); /* Prevent false sharing */ + +typedef struct P_Lock P_Lock; +struct P_Lock { + P_Mutex *mutex; + b32 exclusive; +}; + +P_Lock snc_lock_spin_e(P_Mutex *m, i32 spin); +P_Lock snc_lock_spin_s(P_Mutex *m, i32 spin); +P_Lock snc_lock_e(P_Mutex *m); +P_Lock snc_lock_s(P_Mutex *m); +void snc_unlock(P_Lock *lock); + +#if RTC +# define snc_assert_locked_e(l, m) ASSERT((l)->mutex == (m) && (l)->exclusive == 1) +# define snc_assert_locked_e_or_s(l, m) ASSERT((l)->mutex == (m)) +#else +# define snc_assert_locked_e(l, m) (UNUSED)l +# define snc_assert_locked_e_or_s(l, m) (UNUSED)l +#endif + +/* ========================== * + * Condition variable + * ========================== */ + +typedef struct P_Cv P_Cv; +struct alignas(64) P_Cv { + Atomic64 wake_gen; + u8 _pad[56]; +}; +STATIC_ASSERT(sizeof(P_Cv) == 64); /* Padding validation */ +STATIC_ASSERT(alignof(P_Cv) == 64); /* Prevent false sharing */ + +void snc_cv_wait(P_Cv *cv, P_Lock *lock); +void snc_cv_wait_time(P_Cv *cv, P_Lock *l, i64 timeout_ns); +void snc_cv_signal(P_Cv *cv, i32 count); + +/* ========================== * + * Counter + * ========================== */ + +typedef struct P_Counter P_Counter; +struct alignas(64) P_Counter { + Atomic64 v; + u8 _pad[56]; +}; +STATIC_ASSERT(sizeof(P_Counter) == 64); /* Padding validation */ +STATIC_ASSERT(alignof(P_Counter) == 64); /* Prevent false sharing */ + +void snc_counter_add(P_Counter *counter, i64 x); +void snc_counter_wait(P_Counter *counter); diff --git a/src/sys/sys_core_win32.c b/src/platform/platform_win32.c similarity index 63% rename from src/sys/sys_core_win32.c rename to src/platform/platform_win32.c index ae9c2bde..8f5d7d14 100644 --- a/src/sys/sys_core_win32.c +++ b/src/platform/platform_win32.c @@ -1,19 +1,3 @@ -#pragma warning(push, 0) -# define UNICODE -# define WIN32_LEAN_AND_MEAN -# include -# include -# include -# include -# include -# include -# include -# include -# include -# include -# include -#pragma warning(pop) - #pragma comment(lib, "kernel32") #pragma comment(lib, "user32") #pragma comment(lib, "shell32") @@ -25,333 +9,13 @@ #pragma comment(lib, "avrt") #pragma comment(lib, "ws2_32.lib") -#define SYS_WINDOW_EVENT_LISTENERS_MAX 512 -#define WINDOW_CLASS_NAME L"power_play_window_class" - -#define THREAD_STACK_SIZE KIBI(64) -#define FIBER_STACK_SIZE MEBI(4) - -#define THREAD_DEF(name, arg_name) void name(void *arg_name) -typedef THREAD_DEF(thread_func, data); - -/* Assume scheduler cycle is 20hz at start to be conservative */ -#define DEFAULT_SCHEDULER_CYCLE_PERIOD_NS 50000000 -#define NUM_ROLLING_SCHEDULER_PERIODS 1000 - -#define FIBER_NAME_PREFIX_CSTR "Fiber [" -#define FIBER_NAME_SUFFIX_CSTR "]" -#define FIBER_NAME_MAX_SIZE 64 - -#define NUM_WAIT_ADDR_BINS 16384 -#define NUM_WAIT_TIME_BINS 1024 - -#define MAX_EXIT_FUNCS 1024 - -/* Arbitrary threshold for determining when to fall back from a looped WakeByAddressSingle to WakeByAddressAll */ -#define WAKE_ALL_THRESHOLD 16 - -struct ticket_mutex { - Atomic64Padded ticket; - Atomic64Padded serving; -}; - -struct thread { - thread_func *entry_point; - void *thread_data; - char thread_name_cstr[256]; - wchar_t thread_name_wstr[256]; - i32 profiler_group; - - struct thread *next; - struct thread *prev; - - HANDLE handle; -}; - -enum win32_window_cursor_set_flag { - WIN32_WINDOW_CURSOR_SET_FLAG_NONE = 0x0, - WIN32_WINDOW_CURSOR_SET_FLAG_POSITION = 0x1, - WIN32_WINDOW_CURSOR_SET_FLAG_HIDE = 0x2, - WIN32_WINDOW_CURSOR_SET_FLAG_SHOW = 0x4, - WIN32_WINDOW_CURSOR_SET_FLAG_ENABLE_CLIP = 0X8, - WIN32_WINDOW_CURSOR_SET_FLAG_DISABLE_CLIP = 0X10 -}; - -struct win32_window { - u32 flags; - - HWND hwnd; - struct snc_counter ready_fence; - - u16 utf16_high_surrogate_last_input; - - struct snc_mutex settings_mutex; - struct sys_window_settings settings; - - i32 monitor_width; - i32 monitor_height; - /* NOTE: width & height are unaffected by window minimization (they retain - * their pre-minimized values) */ - i32 x, y, width, height; - - /* FIXME: Use a cmd buffer for updating cursor (and maybe also settings). - * Current setup means cursor_set calls can be applied out of order */ - u32 cursor_set_flags; - V2 cursor_set_position; - Rect cursor_clip_bounds; - - Atomic32 topmost_toggles; - b32 is_topmost; - - struct snc_mutex event_arena_swp_mutex; - i32 current_event_arena_index; - Arena *event_arenas[2]; - - struct thread *window_thread; - - Atomic32 shutdown; - struct win32_window *next_free; -}; - -struct win32_address { - i32 size; - i32 family; - union { - struct sockaddr_storage sas; - struct sockaddr sa; - struct sockaddr_in sin; - struct sockaddr_in6 sin6; - }; -}; - -struct win32_sock { - SOCKET sock; - struct win32_sock *next_free; -}; - -struct alignas(64) wait_list { - u64 value; - i16 first_waiter; - i16 last_waiter; - i32 num_waiters; - struct wait_list *next_in_bin; - struct wait_list *prev_in_bin; -}; -STATIC_ASSERT(alignof(struct wait_list) == 64); /* Avoid false sharing */ - -struct alignas(64) wait_bin { - struct wait_list *first_wait_list; - struct wait_list *last_wait_list; - struct wait_list *first_free_wait_list; - struct ticket_mutex lock; -}; -STATIC_ASSERT(alignof(struct wait_bin) == 64); /* Avoid false sharing */ - -enum yield_kind { - YIELD_KIND_NONE, - YIELD_KIND_DONE, - YIELD_KIND_WAIT, - - NUM_YIELD_KINDS -}; - -struct yield_param { - enum yield_kind kind; - union { - struct { - volatile void *addr; - void *cmp; - u32 size; - i64 timeout_ns; - } wait; - }; -}; - -struct alignas(64) fiber { - /* ---------------------------------------------------- */ - void *addr; /* 08 bytes */ - /* ---------------------------------------------------- */ - char *name_cstr; /* 08 bytes */ - /* ---------------------------------------------------- */ - Atomic32 wake_lock; /* 04 bytes (4 byte alignment) */ - i16 id; /* 02 bytes */ - i16 parent_id; /* 02 bytes */ - /* ---------------------------------------------------- */ - u64 wait_addr; /* 08 bytes */ - /* ---------------------------------------------------- */ - u64 wait_time; /* 08 bytes */ - /* ---------------------------------------------------- */ - i16 next_addr_waiter; /* 02 bytes */ - i16 prev_addr_waiter; /* 02 bytes */ - i16 next_time_waiter; /* 02 bytes */ - i16 prev_time_waiter; /* 02 bytes */ - /* ---------------------------------------------------- */ - u8 _pad1[8]; /* 08 bytes (padding) */ - /* ---------------------------------------------------- */ - u8 _pad2[8]; /* 08 bytes (padding) */ - /* ---------------------------------------------------- */ - /* -------------------- Cache line -------------------- */ - /* ---------------------------------------------------- */ - sys_job_func *job_func; /* 08 bytes */ - /* ---------------------------------------------------- */ - void *job_sig; /* 08 bytes */ - /* ---------------------------------------------------- */ - i32 job_id; /* 04 bytes */ - i16 job_pool; /* 02 bytes */ - i16 job_priority; /* 02 bytes */ - /* ---------------------------------------------------- */ - struct snc_counter *job_counter; /* 08 bytes */ - /* ---------------------------------------------------- */ - struct yield_param *yield_param; /* 08 bytes */ - /* ---------------------------------------------------- */ - u8 _pad3[24]; /* 24 bytes (padding) */ - -}; -STATIC_ASSERT(sizeof(struct fiber) == 128); /* Padding validation (increase if necessary) */ -STATIC_ASSERT(alignof(struct fiber) == 64); /* Avoid false sharing */ -STATIC_ASSERT(offsetof(struct fiber, wake_lock) % 4 == 0); /* Atomic must be aligned */ - -struct alignas(64) worker_ctx { - enum sys_pool pool_kind; - i32 id; -}; - -struct job_info { - i32 num_dispatched; - - i32 count; - sys_job_func *func; - void *sig; - struct snc_counter *counter; - - i16 fiber_id; /* If the job is being resumed from a yield */ - - struct job_info *next; -}; - -struct alignas(64) job_queue { - struct ticket_mutex lock; - Arena *arena; - - struct job_info *first; - struct job_info *last; - - struct job_info *first_free; -}; - -struct alignas(64) job_pool { - /* Jobs */ - struct job_queue job_queues[NUM_SYS_PRIORITIES]; - - struct ticket_mutex free_fibers_lock; - i16 first_free_fiber_id; - - /* Workers */ - Atomic32Padded workers_shutdown; - Atomic64Padded num_jobs_in_queue; - struct ticket_mutex workers_wake_lock; - - i32 num_worker_threads; - i32 thread_priority; - u64 thread_affinity_mask; - b32 thread_is_audio; - Arena *worker_threads_arena; - struct thread **worker_threads; - struct worker_ctx *worker_contexts; -}; - -/* ========================== * - * Global state - * ========================== */ - -GLOBAL struct { - SYSTEM_INFO info; - i64 timer_start_qpc; - i64 ns_per_qpc; - u32 main_thread_id; - Atomic32 shutdown; - - wchar_t cmdline_args_wstr[8192]; - - /* Application control flow */ - Atomic32 panicking; - wchar_t panic_wstr[4096]; - HANDLE panic_event; - HANDLE startup_end_event; - HANDLE exit_begin_event; - HANDLE exit_end_event; - - /* Key lookup table */ - enum sys_btn vk_btn_table[256]; - - /* Threads pool */ - struct snc_mutex threads_mutex; - Arena *threads_arena; - struct thread *first_thread; - struct thread *last_thread; - struct thread *first_free_thread; - - /* Watches pool */ - struct snc_mutex watches_mutex; - Arena *watches_arena; - struct win32_watch *watches_first_free; - - /* Windows pool */ - WNDCLASSEXW window_class; - struct snc_mutex windows_mutex; - Arena *windows_arena; - struct win32_window *first_free_window; - - /* Sockets pool */ - WSADATA wsa_data; - Arena *socks_arena; - struct snc_mutex socks_mutex; - struct win32_sock *first_free_sock; - - - - /* Exit funcs */ - Atomic32 num_exit_funcs; - sys_exit_func *exit_funcs[MAX_EXIT_FUNCS]; - - /* Scheduler */ - Atomic64Padded current_scheduler_cycle; - Atomic64Padded current_scheduler_cycle_period_ns; - - /* Fibers */ - struct ticket_mutex fibers_lock; - i16 num_fibers; - Arena *fiber_names_arena; - struct fiber fibers[MAX_FIBERS]; - - /* Wait lists */ - Atomic64Padded waiter_wake_gen; - struct ticket_mutex wait_lists_arena_lock; - Arena *wait_lists_arena; - - /* Wait tables */ - struct wait_bin wait_addr_bins[NUM_WAIT_ADDR_BINS]; - struct wait_bin wait_time_bins[NUM_WAIT_TIME_BINS]; - - /* Job pools */ - struct job_pool job_pools[NUM_SYS_POOLS]; -} G = ZI, DEBUG_ALIAS(G, G_sys_win32); - - - - -INTERNAL struct fiber *fiber_alloc(struct job_pool *pool); -INTERNAL struct fiber *fiber_from_id(i16 id); -INTERNAL void job_fiber_yield(struct fiber *fiber, struct fiber *parent_fiber); - - - +P_W32_Ctx P_W32_g_shared_ctx = ZI; /* ========================== * * Ticket mutex * ========================== */ -INTERNAL void tm_lock(struct ticket_mutex *tm) +void P_W32_LockTicketMutex(P_W32_TicketMutex *tm) { i64 ticket = atomic64_fetch_add(&tm->ticket.v, 1); while (atomic64_fetch(&tm->serving.v) != ticket) { @@ -359,20 +23,20 @@ INTERNAL void tm_lock(struct ticket_mutex *tm) } } -INTERNAL void tm_unlock(struct ticket_mutex *tm) +void P_W32_UnlockTicketMutex(P_W32_TicketMutex *tm) { atomic64_fetch_add(&tm->serving.v, 1); } /* ========================== * - * Thread + * Win32 thread * ========================== */ -INTERNAL DWORD WINAPI win32_thread_proc(LPVOID vt) +DWORD WINAPI P_W32_Win32ThreadProc(LPVOID vt) { - fiber_alloc(0); + P_W32_AllocFiber(0); - struct thread *t = (struct thread *)vt; + P_W32_Thread *t = (P_W32_Thread *)vt; __profthread(t->thread_name_cstr, t->profiler_group); /* Initialize COM */ @@ -383,7 +47,7 @@ INTERNAL DWORD WINAPI win32_thread_proc(LPVOID vt) SetThreadDescription(GetCurrentThread(), t->thread_name_wstr); } - logf_info("New thread \"%F\" created with ID %F", FMT_STR(string_from_cstr_no_limit(t->thread_name_cstr)), FMT_UINT(sys_current_thread_id())); + logf_info("New thread \"%F\" created with ID %F", FMT_STR(string_from_cstr_no_limit(t->thread_name_cstr)), FMT_UINT(P_GetThreadId())); /* Enter thread entry point */ t->entry_point(t->thread_data); @@ -394,32 +58,33 @@ INTERNAL DWORD WINAPI win32_thread_proc(LPVOID vt) return 0; } -INTERNAL struct thread *thread_alloc(thread_func *entry_point, void *thread_data, String thread_name, i32 profiler_group) +P_W32_Thread *P_W32_AllocThread(P_W32_ThreadFunc *entry_point, void *thread_data, String thread_name, i32 profiler_group) { __prof; TempArena scratch = scratch_begin_no_conflict(); + P_W32_Ctx *g = &P_W32_g_shared_ctx; ASSERT(entry_point != 0); logf_info("Creating thread \"%F\"", FMT_STR(thread_name)); /* Allocate thread object */ - struct thread *t = 0; + P_W32_Thread *t = 0; { - struct snc_lock lock = snc_lock_e(&G.threads_mutex); - if (G.first_free_thread) { - t = G.first_free_thread; - G.first_free_thread = t->next; + P_Lock lock = snc_lock_e(&g->threads_mutex); + if (g->first_free_thread) { + t = g->first_free_thread; + g->first_free_thread = t->next; } else { - t = arena_push_no_zero(G.threads_arena, struct thread); + t = arena_push_no_zero(g->threads_arena, P_W32_Thread); } MEMZERO_STRUCT(t); - if (G.last_thread) { - G.last_thread->next = t; - t->prev = G.last_thread; + if (g->last_thread) { + g->last_thread->next = t; + t->prev = g->last_thread; } else { - G.first_thread = t; + g->first_thread = t; } - G.last_thread = t; + g->last_thread = t; snc_unlock(&lock); } @@ -443,27 +108,28 @@ INTERNAL struct thread *thread_alloc(thread_func *entry_point, void *thread_data t->handle = CreateThread( 0, - THREAD_STACK_SIZE, - win32_thread_proc, + P_W32_ThreadStackSize, + P_W32_Win32ThreadProc, t, 0, 0 ); if (!t->handle) { - sys_panic(LIT("Failed to create thread")); + P_Panic(LIT("Failed to create thread")); } scratch_end(scratch); - return (struct thread *)t; + return (P_W32_Thread *)t; } /* Returns 0 if the thread could not release in specified timeout (e.g. because it is still running) */ -INTERNAL b32 thread_try_release(struct thread *thread, f32 timeout_seconds) +b32 P_W32_TryReleaseThread(P_W32_Thread *thread, f32 timeout_seconds) { __prof; + P_W32_Ctx *g = &P_W32_g_shared_ctx; b32 success = 0; - struct thread *t = (struct thread *)thread; + P_W32_Thread *t = (P_W32_Thread *)thread; HANDLE handle = t->handle; if (handle) { /* Wait for thread to stop */ @@ -474,22 +140,22 @@ INTERNAL b32 thread_try_release(struct thread *thread, f32 timeout_seconds) success = 1; CloseHandle(handle); { - struct snc_lock lock = snc_lock_e(&G.threads_mutex); + P_Lock lock = snc_lock_e(&g->threads_mutex); { - struct thread *prev = t->prev; - struct thread *next = t->next; + P_W32_Thread *prev = t->prev; + P_W32_Thread *next = t->next; if (prev) { prev->next = next; } else { - G.first_thread = next; + g->first_thread = next; } if (next) { next->prev = prev; } else { - G.last_thread = prev; + g->last_thread = prev; } - t->next = G.first_free_thread; - G.first_free_thread = t; + t->next = g->first_free_thread; + g->first_free_thread = t; } snc_unlock(&lock); } @@ -498,77 +164,48 @@ INTERNAL b32 thread_try_release(struct thread *thread, f32 timeout_seconds) return success; } -INTERNAL void thread_wait_release(struct thread *thread) +void P_W32_WaitReleaseThread(P_W32_Thread *thread) { __prof; - b32 success = thread_try_release(thread, F32_INFINITY); + b32 success = P_W32_TryReleaseThread(thread, F32_INFINITY); ASSERT(success); (UNUSED)success; } /* ========================== * - * Wait / wake + * Win32 Wait / wake * ========================== */ -void sys_wait(volatile void *addr, void *cmp, u32 size, i64 timeout_ns) -{ - struct fiber *fiber = fiber_from_id(FiberId()); - i16 parent_id = fiber->parent_id; - if (parent_id != 0) { - *fiber->yield_param = (struct yield_param) { - .kind = YIELD_KIND_WAIT, - .wait = { - .addr = addr, - .cmp = cmp, - .size = size, - .timeout_ns = timeout_ns - } - }; - job_fiber_yield(fiber, fiber_from_id(parent_id)); - } else { - i32 timeout_ms = 0; - if (timeout_ns > 10000000000000000ll) { - timeout_ms = INFINITE; - } else if (timeout_ns != 0) { - timeout_ms = timeout_ns / 1000000; - timeout_ms += (timeout_ms == 0) * math_fsign(timeout_ns); - } - if (addr == 0) { - Sleep(timeout_ms); - } else { - WaitOnAddress(addr, cmp, size, timeout_ms); - } - } -} - /* REQUIRED: Caller must have acquired `wake_lock` for each fiber in array */ -INTERNAL void wake_fibers_locked(i32 num_fibers, struct fiber **fibers) +void P_W32_WakeLockedFibers(i32 num_fibers, P_W32_Fiber **fibers) { + P_W32_Ctx *g = &P_W32_g_shared_ctx; + /* Update wait lists */ for (i32 i = 0; i < num_fibers; ++i) { - struct fiber *fiber = fibers[i]; + P_W32_Fiber *fiber = fibers[i]; u64 wait_addr = fiber->wait_addr; u64 wait_time = fiber->wait_time; /* Lock & search wait bins */ /* TODO: Cache these in parameters since caller has one of them already calculated */ - struct wait_bin *wait_addr_bin = 0; - struct wait_bin *wait_time_bin = 0; - struct wait_list *wait_addr_list = 0; - struct wait_list *wait_time_list = 0; + P_W32_WaitBin *wait_addr_bin = 0; + P_W32_WaitBin *wait_time_bin = 0; + P_W32_WaitList *wait_addr_list = 0; + P_W32_WaitList *wait_time_list = 0; if (wait_addr != 0) { - wait_addr_bin = &G.wait_addr_bins[wait_addr % NUM_WAIT_ADDR_BINS]; - tm_lock(&wait_addr_bin->lock); - for (struct wait_list *tmp = wait_addr_bin->first_wait_list; tmp && !wait_addr_list; tmp = tmp->next_in_bin) { + wait_addr_bin = &g->wait_addr_bins[wait_addr % P_W32_NumWaitAddrBins]; + P_W32_LockTicketMutex(&wait_addr_bin->lock); + for (P_W32_WaitList *tmp = wait_addr_bin->first_wait_list; tmp && !wait_addr_list; tmp = tmp->next_in_bin) { if (tmp->value == (u64)wait_addr) { wait_addr_list = tmp; } } } if (wait_time != 0) { - wait_time_bin = &G.wait_time_bins[wait_time % NUM_WAIT_TIME_BINS]; - tm_lock(&wait_time_bin->lock); - for (struct wait_list *tmp = wait_time_bin->first_wait_list; tmp && !wait_time_list; tmp = tmp->next_in_bin) { + wait_time_bin = &g->wait_time_bins[wait_time % P_W32_NumWaitTimeBins]; + P_W32_LockTicketMutex(&wait_time_bin->lock); + for (P_W32_WaitList *tmp = wait_time_bin->first_wait_list; tmp && !wait_time_list; tmp = tmp->next_in_bin) { if (tmp->value == (u64)wait_time) { wait_time_list = tmp; } @@ -579,8 +216,8 @@ INTERNAL void wake_fibers_locked(i32 num_fibers, struct fiber **fibers) if (wait_addr_list) { if (--wait_addr_list->num_waiters == 0) { /* Free addr list */ - struct wait_list *prev = wait_addr_list->prev_in_bin; - struct wait_list *next = wait_addr_list->next_in_bin; + P_W32_WaitList *prev = wait_addr_list->prev_in_bin; + P_W32_WaitList *next = wait_addr_list->next_in_bin; if (prev) { prev->next_in_bin = next; } else { @@ -597,12 +234,12 @@ INTERNAL void wake_fibers_locked(i32 num_fibers, struct fiber **fibers) i16 prev_id = fiber->prev_addr_waiter; i16 next_id = fiber->next_addr_waiter; if (prev_id) { - fiber_from_id(prev_id)->next_addr_waiter = next_id; + P_W32_FiberFromId(prev_id)->next_addr_waiter = next_id; } else { wait_addr_list->first_waiter = next_id; } if (next_id) { - fiber_from_id(next_id)->prev_addr_waiter = prev_id; + P_W32_FiberFromId(next_id)->prev_addr_waiter = prev_id; } else { wait_addr_list->last_waiter = prev_id; } @@ -615,8 +252,8 @@ INTERNAL void wake_fibers_locked(i32 num_fibers, struct fiber **fibers) if (wait_time_list) { if (--wait_time_list->num_waiters == 0) { /* Free time list */ - struct wait_list *prev = wait_time_list->prev_in_bin; - struct wait_list *next = wait_time_list->next_in_bin; + P_W32_WaitList *prev = wait_time_list->prev_in_bin; + P_W32_WaitList *next = wait_time_list->next_in_bin; if (prev) { prev->next_in_bin = next; } else { @@ -633,12 +270,12 @@ INTERNAL void wake_fibers_locked(i32 num_fibers, struct fiber **fibers) i16 prev_id = fiber->prev_time_waiter; i16 next_id = fiber->next_time_waiter; if (prev_id) { - fiber_from_id(prev_id)->next_time_waiter = next_id; + P_W32_FiberFromId(prev_id)->next_time_waiter = next_id; } else { wait_time_list->first_waiter = next_id; } if (next_id) { - fiber_from_id(next_id)->prev_time_waiter = prev_id; + P_W32_FiberFromId(next_id)->prev_time_waiter = prev_id; } else { wait_time_list->last_waiter = prev_id; } @@ -651,27 +288,27 @@ INTERNAL void wake_fibers_locked(i32 num_fibers, struct fiber **fibers) atomic32_fetch_set(&fiber->wake_lock, 0); } /* Unlock wait bins */ - if (wait_time_bin != 0) tm_unlock(&wait_time_bin->lock); - if (wait_addr_bin != 0) tm_unlock(&wait_addr_bin->lock); + if (wait_time_bin != 0) P_W32_UnlockTicketMutex(&wait_time_bin->lock); + if (wait_addr_bin != 0) P_W32_UnlockTicketMutex(&wait_addr_bin->lock); } /* Resume jobs */ /* TODO: Batch submit waiters based on queue kind rather than one at a time */ - i32 job_counts_per_pool[NUM_SYS_POOLS] = ZI; + i32 job_counts_per_pool[P_Pool_Count] = ZI; for (i32 i = 0; i < num_fibers; ++i) { - struct fiber *fiber = fibers[i]; - enum sys_pool pool_kind = fiber->job_pool; + P_W32_Fiber *fiber = fibers[i]; + P_Pool pool_kind = fiber->job_pool; ++job_counts_per_pool[pool_kind]; - struct job_pool *pool = &G.job_pools[pool_kind]; - struct job_queue *queue = &pool->job_queues[fiber->job_priority]; - tm_lock(&queue->lock); + P_W32_JobPool *pool = &g->job_pools[pool_kind]; + P_W32_JobQueue *queue = &pool->job_queues[fiber->job_priority]; + P_W32_LockTicketMutex(&queue->lock); { - struct job_info *info = 0; + P_W32_JobInfo *info = 0; if (queue->first_free) { info = queue->first_free; queue->first_free = info->next; } else { - info = arena_push_no_zero(queue->arena, struct job_info); + info = arena_push_no_zero(queue->arena, P_W32_JobInfo); } MEMZERO_STRUCT(info); info->count = 1; @@ -687,19 +324,19 @@ INTERNAL void wake_fibers_locked(i32 num_fibers, struct fiber **fibers) } queue->first = info; } - tm_unlock(&queue->lock); + P_W32_UnlockTicketMutex(&queue->lock); } /* Wake workers */ if (num_fibers > 0) { - for (enum sys_pool pool_kind = 0; pool_kind < (i32)countof(job_counts_per_pool); ++pool_kind) { + for (P_Pool pool_kind = 0; pool_kind < (i32)countof(job_counts_per_pool); ++pool_kind) { i32 job_count = job_counts_per_pool[pool_kind]; if (job_count > 0) { - struct job_pool *pool = &G.job_pools[pool_kind]; - tm_lock(&pool->workers_wake_lock); + P_W32_JobPool *pool = &g->job_pools[pool_kind]; + P_W32_LockTicketMutex(&pool->workers_wake_lock); { atomic64_fetch_add(&pool->num_jobs_in_queue.v, job_count); - if (job_count >= WAKE_ALL_THRESHOLD) { + if (job_count >= P_W32_WakeAllThreshold) { WakeByAddressAll(&pool->num_jobs_in_queue); } else { for (i32 i = 0; i < job_count; ++i) { @@ -707,28 +344,29 @@ INTERNAL void wake_fibers_locked(i32 num_fibers, struct fiber **fibers) } } } - tm_unlock(&pool->workers_wake_lock); + P_W32_UnlockTicketMutex(&pool->workers_wake_lock); } } } } -INTERNAL void wake_address(void *addr, i32 count) +void P_W32_WakeByAddress(void *addr, i32 count) { TempArena scratch = scratch_begin_no_conflict(); + P_W32_Ctx *g = &P_W32_g_shared_ctx; - u64 wait_addr_bin_index = (u64)addr % NUM_WAIT_ADDR_BINS; - struct wait_bin *wait_addr_bin = &G.wait_addr_bins[wait_addr_bin_index]; - struct wait_list *wait_addr_list = 0; + u64 wait_addr_bin_index = (u64)addr % P_W32_NumWaitAddrBins; + P_W32_WaitBin *wait_addr_bin = &g->wait_addr_bins[wait_addr_bin_index]; + P_W32_WaitList *wait_addr_list = 0; /* Get list of waiting fibers */ i32 num_fibers = 0; - struct fiber **fibers = 0; + P_W32_Fiber **fibers = 0; { - tm_lock(&wait_addr_bin->lock); + P_W32_LockTicketMutex(&wait_addr_bin->lock); { /* Search for wait addr list */ - for (struct wait_list *tmp = wait_addr_bin->first_wait_list; tmp && !wait_addr_list; tmp = tmp->next_in_bin) { + for (P_W32_WaitList *tmp = wait_addr_bin->first_wait_list; tmp && !wait_addr_list; tmp = tmp->next_in_bin) { if (tmp->value == (u64)addr) { wait_addr_list = tmp; } @@ -736,8 +374,8 @@ INTERNAL void wake_address(void *addr, i32 count) /* Lock fibers & build array */ if (wait_addr_list) { - fibers = arena_push_array_no_zero(scratch.arena, struct fiber *, wait_addr_list->num_waiters); - for (struct fiber *fiber = fiber_from_id(wait_addr_list->first_waiter); fiber && num_fibers < count; fiber = fiber_from_id(fiber->next_addr_waiter)) { + fibers = arena_push_array_no_zero(scratch.arena, P_W32_Fiber *, wait_addr_list->num_waiters); + for (P_W32_Fiber *fiber = P_W32_FiberFromId(wait_addr_list->first_waiter); fiber && num_fibers < count; fiber = P_W32_FiberFromId(fiber->next_addr_waiter)) { if (atomic32_fetch_test_set(&fiber->wake_lock, 0, 1) == 0) { fibers[num_fibers] = fiber; ++num_fibers; @@ -745,15 +383,15 @@ INTERNAL void wake_address(void *addr, i32 count) } } } - tm_unlock(&wait_addr_bin->lock); + P_W32_UnlockTicketMutex(&wait_addr_bin->lock); } if (num_fibers > 0) { - wake_fibers_locked(num_fibers, fibers); + P_W32_WakeLockedFibers(num_fibers, fibers); } /* Wake win32 blocking thread waiters */ - if (count >= WAKE_ALL_THRESHOLD) { + if (count >= P_W32_WakeAllThreshold) { WakeByAddressAll(addr); } else { for (i32 i = 0; i < count; ++i) { @@ -764,22 +402,23 @@ INTERNAL void wake_address(void *addr, i32 count) scratch_end(scratch); } -INTERNAL void wake_time(u64 time) +void P_W32_WakeByTime(u64 time) { TempArena scratch = scratch_begin_no_conflict(); + P_W32_Ctx *g = &P_W32_g_shared_ctx; - u64 wait_time_bin_index = (u64)time % NUM_WAIT_TIME_BINS; - struct wait_bin *wait_time_bin = &G.wait_time_bins[wait_time_bin_index]; - struct wait_list *wait_time_list = 0; + u64 wait_time_bin_index = (u64)time % P_W32_NumWaitTimeBins; + P_W32_WaitBin *wait_time_bin = &g->wait_time_bins[wait_time_bin_index]; + P_W32_WaitList *wait_time_list = 0; /* Build list of waiters to resume */ i32 num_fibers = 0; - struct fiber **fibers = 0; + P_W32_Fiber **fibers = 0; { - tm_lock(&wait_time_bin->lock); + P_W32_LockTicketMutex(&wait_time_bin->lock); { /* Search for wait time list */ - for (struct wait_list *tmp = wait_time_bin->first_wait_list; tmp && !wait_time_list; tmp = tmp->next_in_bin) { + for (P_W32_WaitList *tmp = wait_time_bin->first_wait_list; tmp && !wait_time_list; tmp = tmp->next_in_bin) { if (tmp->value == (u64)time) { wait_time_list = tmp; } @@ -787,8 +426,8 @@ INTERNAL void wake_time(u64 time) if (wait_time_list) { /* Set waiter wake status & build fibers list */ - fibers = arena_push_array_no_zero(scratch.arena, struct fiber *, wait_time_list->num_waiters); - for (struct fiber *fiber = fiber_from_id(wait_time_list->first_waiter); fiber; fiber = fiber_from_id(fiber->next_time_waiter)) { + fibers = arena_push_array_no_zero(scratch.arena, P_W32_Fiber *, wait_time_list->num_waiters); + for (P_W32_Fiber *fiber = P_W32_FiberFromId(wait_time_list->first_waiter); fiber; fiber = P_W32_FiberFromId(fiber->next_time_waiter)) { if (atomic32_fetch_test_set(&fiber->wake_lock, 0, 1) == 0) { fibers[num_fibers] = fiber; ++num_fibers; @@ -797,54 +436,48 @@ INTERNAL void wake_time(u64 time) } } } - tm_unlock(&wait_time_bin->lock); + P_W32_UnlockTicketMutex(&wait_time_bin->lock); } - wake_fibers_locked(num_fibers, fibers); + P_W32_WakeLockedFibers(num_fibers, fibers); scratch_end(scratch); } -void sys_wake(void *addr, i32 count) -{ - wake_address(addr, count); -} - /* ========================== * * Fibers * ========================== */ -INTERNAL void job_fiber_entry(void *id_ptr); - /* If `pool` is 0, then the currently running thread will be converted into a fiber */ -INTERNAL struct fiber *fiber_alloc(struct job_pool *pool) +P_W32_Fiber *P_W32_AllocFiber(P_W32_JobPool *pool) { + P_W32_Ctx *g = &P_W32_g_shared_ctx; i16 fiber_id = 0; - struct fiber *fiber = 0; + P_W32_Fiber *fiber = 0; char *new_name_cstr = 0; { if (pool != 0) { - tm_lock(&pool->free_fibers_lock); + P_W32_LockTicketMutex(&pool->free_fibers_lock); if (pool->first_free_fiber_id) { fiber_id = pool->first_free_fiber_id; - fiber = &G.fibers[fiber_id]; + fiber = &g->fibers[fiber_id]; pool->first_free_fiber_id = fiber->parent_id; } - tm_unlock(&pool->free_fibers_lock); + P_W32_UnlockTicketMutex(&pool->free_fibers_lock); } if (!fiber_id) { - tm_lock(&G.fibers_lock); + P_W32_LockTicketMutex(&g->fibers_lock); { { - fiber_id = G.num_fibers++; + fiber_id = g->num_fibers++; if (fiber_id >= MAX_FIBERS) { - sys_panic(LIT("Max fibers reached")); + P_Panic(LIT("Max fibers reached")); } - fiber = &G.fibers[fiber_id]; - new_name_cstr = arena_push_array(G.fiber_names_arena, char, FIBER_NAME_MAX_SIZE); + fiber = &g->fibers[fiber_id]; + new_name_cstr = arena_push_array(g->fiber_names_arena, char, P_W32_FiberNameMaxSize); } } - tm_unlock(&G.fibers_lock); + P_W32_UnlockTicketMutex(&g->fibers_lock); } } @@ -874,20 +507,20 @@ INTERNAL struct fiber *fiber_alloc(struct job_pool *pool) /* Concat fiber name */ i32 name_size = 1; - ASSERT(sizeof(sizeof(FIBER_NAME_PREFIX_CSTR)) <= FIBER_NAME_MAX_SIZE); - MEMCPY(new_name_cstr, FIBER_NAME_PREFIX_CSTR, sizeof(FIBER_NAME_PREFIX_CSTR)); - name_size += sizeof(FIBER_NAME_PREFIX_CSTR) - 2; + ASSERT(sizeof(sizeof(P_W32_FiberNamePrefixCstr)) <= P_W32_FiberNameMaxSize); + MEMCPY(new_name_cstr, P_W32_FiberNamePrefixCstr, sizeof(P_W32_FiberNamePrefixCstr)); + name_size += sizeof(P_W32_FiberNamePrefixCstr) - 2; MEMCPY(new_name_cstr + name_size, id_chars, id_chars_len); name_size += id_chars_len; - MEMCPY(new_name_cstr + name_size, FIBER_NAME_SUFFIX_CSTR, sizeof(FIBER_NAME_SUFFIX_CSTR)); - name_size += sizeof(FIBER_NAME_SUFFIX_CSTR) - 2; + MEMCPY(new_name_cstr + name_size, P_W32_FiberNameSuffixCstr, sizeof(P_W32_FiberNameSuffixCstr)); + name_size += sizeof(P_W32_FiberNameSuffixCstr) - 2; fiber->name_cstr = new_name_cstr; /* Init win32 fiber */ if (pool != 0) { __profn("CreateFiber"); - fiber->addr = CreateFiber(FIBER_STACK_SIZE, job_fiber_entry, (void *)(i64)fiber_id); + fiber->addr = CreateFiber(P_W32_FiberStackSize, P_W32_FiberEntryPoint, (void *)(i64)fiber_id); } else { /* Fiber is not a part of a job pool, convert thread to fiber */ __profn("ConvertThreadToFiber"); @@ -911,38 +544,35 @@ INTERNAL struct fiber *fiber_alloc(struct job_pool *pool) return fiber; } -INTERNAL void fiber_release(struct job_pool *pool, struct fiber *fiber) +void P_W32_ReleaseFiber(P_W32_JobPool *pool, P_W32_Fiber *fiber) { - tm_lock(&pool->free_fibers_lock); + P_W32_LockTicketMutex(&pool->free_fibers_lock); { i16 fiber_id = fiber->id; fiber->parent_id = pool->first_free_fiber_id; pool->first_free_fiber_id = fiber_id; } - tm_unlock(&pool->free_fibers_lock); + P_W32_UnlockTicketMutex(&pool->free_fibers_lock); } -INTERNAL FORCE_INLINE struct fiber *fiber_from_id(i16 id) +FORCE_INLINE P_W32_Fiber *P_W32_FiberFromId(i16 id) { + P_W32_Ctx *g = &P_W32_g_shared_ctx; if (id <= 0) { return 0; } else { - return &G.fibers[id]; + return &g->fibers[id]; } } -INTERNAL FORCE_NO_INLINE void fiber_resume(struct fiber *fiber) +FORCE_NO_INLINE void P_W32_FiberResume(P_W32_Fiber *fiber) { MemoryBarrier(); SwitchToFiber(fiber->addr); MemoryBarrier(); } -/* ========================== * - * Job - * ========================== */ - -INTERNAL void job_fiber_yield(struct fiber *fiber, struct fiber *parent_fiber) +void P_W32_YieldFiber(P_W32_Fiber *fiber, P_W32_Fiber *parent_fiber) { (UNUSED)fiber; ASSERT(fiber->id == FiberId()); @@ -950,22 +580,22 @@ INTERNAL void job_fiber_yield(struct fiber *fiber, struct fiber *parent_fiber) ASSERT(parent_fiber->id > 0); { __prof_fiber_leave(); - fiber_resume(parent_fiber); + P_W32_FiberResume(parent_fiber); __prof_fiber_enter(fiber->name_cstr, PROF_THREAD_GROUP_FIBERS - MEBI(fiber->job_pool) + KIBI(1) + fiber->id); } } -INTERNAL void job_fiber_entry(void *id_ptr) +void P_W32_FiberEntryPoint(void *id_ptr) { i16 id = (i32)(i64)id_ptr; - volatile struct fiber *fiber = fiber_from_id(id); + volatile P_W32_Fiber *fiber = P_W32_FiberFromId(id); __prof_fiber_enter(fiber->name_cstr, PROF_THREAD_GROUP_FIBERS - MEBI(fiber->job_pool) + KIBI(1) + fiber->id); for (;;) { /* Run job */ { - struct yield_param *yield_param = fiber->yield_param; - yield_param->kind = YIELD_KIND_NONE; - struct sys_job_data data = ZI; + P_W32_YieldParam *yield_param = fiber->yield_param; + yield_param->kind = P_W32_YieldKind_None; + P_JobData data = ZI; data.id = fiber->job_id; data.sig = fiber->job_sig; { @@ -977,69 +607,14 @@ INTERNAL void job_fiber_entry(void *id_ptr) /* Job completed, yield */ { /* Decrement job counter */ - struct snc_counter *job_counter = fiber->job_counter; + P_Counter *job_counter = fiber->job_counter; if (job_counter) { snc_counter_add(job_counter, -1); } /* Yield to worker */ - fiber->yield_param->kind = YIELD_KIND_DONE; - struct fiber *parent_fiber = fiber_from_id(fiber->parent_id); - job_fiber_yield((struct fiber *)fiber, parent_fiber); - } - } -} - -void sys_run(i32 count, sys_job_func *func, void *sig, enum sys_pool pool_kind, enum sys_priority priority, struct snc_counter *counter) -{ - __prof; - if (count > 0) { - if (counter) { - snc_counter_add(counter, count); - } - struct fiber *fiber = fiber_from_id(FiberId()); - priority = clamp_i32(priority, fiber->job_priority, NUM_SYS_PRIORITIES - 1); /* A job cannot create a job with a higher priority than itself */ - if (pool_kind == SYS_POOL_INHERIT) { - pool_kind = fiber->job_pool; - } - struct job_pool *pool = &G.job_pools[pool_kind]; - struct job_queue *queue = &pool->job_queues[priority]; - tm_lock(&queue->lock); - { - struct job_info *info = 0; - if (queue->first_free) { - info = queue->first_free; - queue->first_free = info->next; - } else { - info = arena_push_no_zero(queue->arena, struct job_info); - } - MEMZERO_STRUCT(info); - info->count = count; - info->func = func; - info->sig = sig; - info->counter = counter; - if (queue->last) { - queue->last->next = info; - } else { - queue->first = info; - } - queue->last = info; - } - tm_unlock(&queue->lock); - - /* Wake workers */ - { - tm_lock(&pool->workers_wake_lock); - { - atomic64_fetch_add(&pool->num_jobs_in_queue.v, count); - if (count >= WAKE_ALL_THRESHOLD) { - WakeByAddressAll(&pool->num_jobs_in_queue); - } else { - for (i32 i = 0; i < count; ++i) { - WakeByAddressSingle(&pool->num_jobs_in_queue); - } - } - } - tm_unlock(&pool->workers_wake_lock); + fiber->yield_param->kind = P_W32_YieldKind_Done; + P_W32_Fiber *parent_fiber = P_W32_FiberFromId(fiber->parent_id); + P_W32_YieldFiber((P_W32_Fiber *)fiber, parent_fiber); } } } @@ -1048,11 +623,12 @@ void sys_run(i32 count, sys_job_func *func, void *sig, enum sys_pool pool_kind, * Job worker thread * ========================== */ -INTERNAL THREAD_DEF(job_worker_entry, worker_ctx_arg) +P_W32_ThreadDef(P_W32_JobWorkerEntryFunc, worker_ctx_arg) { - struct worker_ctx *ctx = worker_ctx_arg; - enum sys_pool pool_kind = ctx->pool_kind; - struct job_pool *pool = &G.job_pools[pool_kind]; + P_W32_Ctx *g = &P_W32_g_shared_ctx; + P_W32_WorkerCtx *ctx = worker_ctx_arg; + P_Pool pool_kind = ctx->pool_kind; + P_W32_JobPool *pool = &g->job_pools[pool_kind]; (UNUSED)ctx; { @@ -1100,26 +676,26 @@ INTERNAL THREAD_DEF(job_worker_entry, worker_ctx_arg) i32 worker_fiber_id = FiberId(); - struct fiber *job_fiber = 0; + P_W32_Fiber *job_fiber = 0; b32 shutdown = 0; while (!shutdown) { /* Pull job from queue */ - enum sys_priority job_priority = 0; + P_Priority job_priority = 0; i16 job_fiber_id = 0; i32 job_id = 0; - sys_job_func *job_func = 0; + P_JobFunc *job_func = 0; void *job_sig = 0; - struct snc_counter *job_counter = 0; + P_Counter *job_counter = 0; { //__profnc("Pull job", RGB32_F(0.75, 0.75, 0)); - for (enum sys_priority priority = 0; priority < (i32)countof(pool->job_queues) && !job_func; ++priority) { - struct job_queue *queue = &pool->job_queues[priority]; + for (P_Priority priority = 0; priority < (i32)countof(pool->job_queues) && !job_func; ++priority) { + P_W32_JobQueue *queue = &pool->job_queues[priority]; if (queue) { - tm_lock(&queue->lock); + P_W32_LockTicketMutex(&queue->lock); { - struct job_info *info = queue->first; + P_W32_JobInfo *info = queue->first; while (info && !job_func) { - struct job_info *next = info->next; + P_W32_JobInfo *next = info->next; b32 dequeue = 0; if (info->fiber_id <= 0) { job_id = info->num_dispatched++; @@ -1157,7 +733,7 @@ INTERNAL THREAD_DEF(job_worker_entry, worker_ctx_arg) info = next; } } - tm_unlock(&queue->lock); + P_W32_UnlockTicketMutex(&queue->lock); } } } @@ -1165,21 +741,21 @@ INTERNAL THREAD_DEF(job_worker_entry, worker_ctx_arg) /* Use resumed fiber if present */ if (job_fiber_id > 0) { if (job_fiber) { - fiber_release(pool, job_fiber); + P_W32_ReleaseFiber(pool, job_fiber); } - job_fiber = fiber_from_id(job_fiber_id); + job_fiber = P_W32_FiberFromId(job_fiber_id); } /* Run fiber */ if (job_func) { if (!job_fiber) { - job_fiber = fiber_alloc(pool); + job_fiber = P_W32_AllocFiber(pool); } job_fiber_id = job_fiber->id; { __profnc("Run fiber", RGB32_F(1, 1, 1)); __profvalue(job_fiber->id); - struct yield_param yield = ZI; + P_W32_YieldParam yield = ZI; job_fiber->parent_id = worker_fiber_id; job_fiber->job_func = job_func; job_fiber->job_sig = job_sig; @@ -1190,17 +766,17 @@ INTERNAL THREAD_DEF(job_worker_entry, worker_ctx_arg) job_fiber->yield_param = &yield; b32 done = 0; while (!done) { - fiber_resume(job_fiber); + P_W32_FiberResume(job_fiber); switch (yield.kind) { default: { /* Invalid yield kind */ TempArena scratch = scratch_begin_no_conflict(); - sys_panic(string_format(scratch.arena, LIT("Invalid fiber yield kind \"%F\""), FMT_SINT(yield.kind))); + P_Panic(string_format(scratch.arena, LIT("Invalid fiber yield kind \"%F\""), FMT_SINT(yield.kind))); scratch_end(scratch); } break; - case YIELD_KIND_WAIT: + case P_W32_YieldKind_Wait: { __profn("Process fiber wait"); volatile void *wait_addr = yield.wait.addr; @@ -1209,19 +785,19 @@ INTERNAL THREAD_DEF(job_worker_entry, worker_ctx_arg) i64 wait_timeout_ns = yield.wait.timeout_ns; i64 wait_time = 0; if (wait_timeout_ns > 0 && wait_timeout_ns < I64_MAX) { - u64 current_scheduler_cycle = atomic64_fetch(&G.current_scheduler_cycle.v); - i64 current_scheduler_cycle_period_ns = atomic64_fetch(&G.current_scheduler_cycle_period_ns.v); + u64 current_scheduler_cycle = atomic64_fetch(&g->current_scheduler_cycle.v); + i64 current_scheduler_cycle_period_ns = atomic64_fetch(&g->current_scheduler_cycle_period_ns.v); wait_time = current_scheduler_cycle + max_i64((i64)((f64)wait_timeout_ns / (f64)current_scheduler_cycle_period_ns), 1); } - u64 wait_addr_bin_index = (u64)wait_addr % NUM_WAIT_ADDR_BINS; - u64 wait_time_bin_index = (u64)wait_time % NUM_WAIT_TIME_BINS; - struct wait_bin *wait_addr_bin = &G.wait_addr_bins[wait_addr_bin_index]; - struct wait_bin *wait_time_bin = &G.wait_time_bins[wait_time_bin_index]; + u64 wait_addr_bin_index = (u64)wait_addr % P_W32_NumWaitAddrBins; + u64 wait_time_bin_index = (u64)wait_time % P_W32_NumWaitTimeBins; + P_W32_WaitBin *wait_addr_bin = &g->wait_addr_bins[wait_addr_bin_index]; + P_W32_WaitBin *wait_time_bin = &g->wait_time_bins[wait_time_bin_index]; - if (wait_addr != 0) tm_lock(&wait_addr_bin->lock); + if (wait_addr != 0) P_W32_LockTicketMutex(&wait_addr_bin->lock); { - if (wait_time != 0) tm_lock(&wait_time_bin->lock); + if (wait_time != 0) P_W32_LockTicketMutex(&wait_time_bin->lock); { b32 cancel_wait = wait_addr == 0 && wait_time == 0; if (wait_addr != 0) { @@ -1234,13 +810,13 @@ INTERNAL THREAD_DEF(job_worker_entry, worker_ctx_arg) } } if (wait_time != 0 && !cancel_wait) { - cancel_wait = wait_time <= atomic64_fetch(&G.current_scheduler_cycle.v); + cancel_wait = wait_time <= atomic64_fetch(&g->current_scheduler_cycle.v); } if (!cancel_wait) { if (wait_addr != 0) { /* Search for wait addr list in bin */ - struct wait_list *wait_addr_list = 0; - for (struct wait_list *tmp = wait_addr_bin->first_wait_list; tmp && !wait_addr_list; tmp = tmp->next_in_bin) { + P_W32_WaitList *wait_addr_list = 0; + for (P_W32_WaitList *tmp = wait_addr_bin->first_wait_list; tmp && !wait_addr_list; tmp = tmp->next_in_bin) { if (tmp->value == (u64)wait_addr) { wait_addr_list = tmp; } @@ -1251,11 +827,11 @@ INTERNAL THREAD_DEF(job_worker_entry, worker_ctx_arg) wait_addr_list = wait_addr_bin->first_free_wait_list; wait_addr_bin->first_free_wait_list = wait_addr_list->next_in_bin; } else { - tm_lock(&G.wait_lists_arena_lock); + P_W32_LockTicketMutex(&g->wait_lists_arena_lock); { - wait_addr_list = arena_push_no_zero(G.wait_lists_arena, struct wait_list); + wait_addr_list = arena_push_no_zero(g->wait_lists_arena, P_W32_WaitList); } - tm_unlock(&G.wait_lists_arena_lock); + P_W32_UnlockTicketMutex(&g->wait_lists_arena_lock); } MEMZERO_STRUCT(wait_addr_list); wait_addr_list->value = (u64)wait_addr; @@ -1270,7 +846,7 @@ INTERNAL THREAD_DEF(job_worker_entry, worker_ctx_arg) /* Insert fiber into wait addr list */ job_fiber->wait_addr = (u64)wait_addr; if (wait_addr_list->last_waiter) { - fiber_from_id(wait_addr_list->last_waiter)->next_addr_waiter = job_fiber_id; + P_W32_FiberFromId(wait_addr_list->last_waiter)->next_addr_waiter = job_fiber_id; job_fiber->prev_addr_waiter = wait_addr_list->last_waiter; } else { wait_addr_list->first_waiter = job_fiber_id; @@ -1280,8 +856,8 @@ INTERNAL THREAD_DEF(job_worker_entry, worker_ctx_arg) } if (wait_time != 0) { /* Search for wait time list in bin */ - struct wait_list *wait_time_list = 0; - for (struct wait_list *tmp = wait_time_bin->first_wait_list; tmp && !wait_time_list; tmp = tmp->next_in_bin) { + P_W32_WaitList *wait_time_list = 0; + for (P_W32_WaitList *tmp = wait_time_bin->first_wait_list; tmp && !wait_time_list; tmp = tmp->next_in_bin) { if (tmp->value == (u64)wait_time) { wait_time_list = tmp; } @@ -1292,11 +868,11 @@ INTERNAL THREAD_DEF(job_worker_entry, worker_ctx_arg) wait_time_list = wait_time_bin->first_free_wait_list; wait_time_bin->first_free_wait_list = wait_time_list->next_in_bin; } else { - tm_lock(&G.wait_lists_arena_lock); + P_W32_LockTicketMutex(&g->wait_lists_arena_lock); { - wait_time_list = arena_push_no_zero(G.wait_lists_arena, struct wait_list); + wait_time_list = arena_push_no_zero(g->wait_lists_arena, P_W32_WaitList); } - tm_unlock(&G.wait_lists_arena_lock); + P_W32_UnlockTicketMutex(&g->wait_lists_arena_lock); } MEMZERO_STRUCT(wait_time_list); wait_time_list->value = wait_time; @@ -1311,7 +887,7 @@ INTERNAL THREAD_DEF(job_worker_entry, worker_ctx_arg) /* Insert fiber into wait time list */ job_fiber->wait_time = wait_time; if (wait_time_list->last_waiter) { - fiber_from_id(wait_time_list->last_waiter)->next_time_waiter = job_fiber_id; + P_W32_FiberFromId(wait_time_list->last_waiter)->next_time_waiter = job_fiber_id; job_fiber->prev_time_waiter = wait_time_list->last_waiter; } else { wait_time_list->first_waiter = job_fiber_id; @@ -1325,12 +901,12 @@ INTERNAL THREAD_DEF(job_worker_entry, worker_ctx_arg) done = 1; } } - if (wait_time != 0) tm_unlock(&wait_time_bin->lock); + if (wait_time != 0) P_W32_UnlockTicketMutex(&wait_time_bin->lock); } - if (wait_addr != 0) tm_unlock(&wait_addr_bin->lock); + if (wait_addr != 0) P_W32_UnlockTicketMutex(&wait_addr_bin->lock); } break; - case YIELD_KIND_DONE: + case P_W32_YieldKind_Done: { done = 1; } break; @@ -1344,27 +920,27 @@ INTERNAL THREAD_DEF(job_worker_entry, worker_ctx_arg) shutdown = atomic32_fetch(&pool->workers_shutdown.v); if (num_jobs_in_queue <= 0 && !shutdown) { //__profnc("Wait for job", RGB32_F(0.75, 0.75, 0)); - tm_lock(&pool->workers_wake_lock); + P_W32_LockTicketMutex(&pool->workers_wake_lock); { num_jobs_in_queue = atomic64_fetch(&pool->num_jobs_in_queue.v); shutdown = atomic32_fetch(&pool->workers_shutdown.v); while (num_jobs_in_queue <= 0 && !shutdown) { { - tm_unlock(&pool->workers_wake_lock); + P_W32_UnlockTicketMutex(&pool->workers_wake_lock); WaitOnAddress(&pool->num_jobs_in_queue, &num_jobs_in_queue, sizeof(num_jobs_in_queue), INFINITE); - tm_lock(&pool->workers_wake_lock); + P_W32_LockTicketMutex(&pool->workers_wake_lock); } shutdown = atomic32_fetch(&pool->workers_shutdown.v); num_jobs_in_queue = atomic64_fetch(&pool->num_jobs_in_queue.v); } } - tm_unlock(&pool->workers_wake_lock); + P_W32_UnlockTicketMutex(&pool->workers_wake_lock); } } /* Worker shutdown */ if (job_fiber) { - fiber_release(pool, job_fiber); + P_W32_ReleaseFiber(pool, job_fiber); } } @@ -1372,8 +948,10 @@ INTERNAL THREAD_DEF(job_worker_entry, worker_ctx_arg) * Job scheduler thread * ========================== */ -INTERNAL THREAD_DEF(job_scheduler_entry, _) +P_W32_ThreadDef(P_W32_JobSchedulerEntryFunc, _) { + struct P_W32_Ctx *g = &P_W32_g_shared_ctx; + (UNUSED)_; { i32 priority = THREAD_PRIORITY_TIME_CRITICAL; @@ -1385,18 +963,18 @@ INTERNAL THREAD_DEF(job_scheduler_entry, _) /* Create high resolution timer */ HANDLE timer = CreateWaitableTimerExW(0, 0, CREATE_WAITABLE_TIMER_HIGH_RESOLUTION, TIMER_ALL_ACCESS); if (!timer) { - sys_panic(LIT("Failed to create high resolution timer")); + P_Panic(LIT("Failed to create high resolution timer")); } /* Create rolling buffer of scheduler cycles initialized to default value */ i32 periods_index = 0; - i64 periods[NUM_ROLLING_SCHEDULER_PERIODS] = ZI; + i64 periods[P_W32_NumRollingSchedulerPeriods] = ZI; for (i32 i = 0; i < (i32)countof(periods); ++i) { - periods[i] = DEFAULT_SCHEDULER_CYCLE_PERIOD_NS; + periods[i] = P_W32_DefaultSchedulerPeriodNs; } i64 last_cycle_ns = 0; - while (!atomic32_fetch(&G.shutdown)) { + while (!atomic32_fetch(&g->shutdown)) { __profn("Job scheduler cycle"); { __profn("Job scheduler wait"); @@ -1411,8 +989,8 @@ INTERNAL THREAD_DEF(job_scheduler_entry, _) } /* Calculate mean period */ - i64 now_ns = sys_time_ns(); - i64 period_ns = last_cycle_ns == 0 ? DEFAULT_SCHEDULER_CYCLE_PERIOD_NS : now_ns - last_cycle_ns; + i64 now_ns = P_TimeNs(); + i64 period_ns = last_cycle_ns == 0 ? P_W32_DefaultSchedulerPeriodNs : now_ns - last_cycle_ns; last_cycle_ns = now_ns; /* Calculate mean period */ @@ -1426,13 +1004,113 @@ INTERNAL THREAD_DEF(job_scheduler_entry, _) periods_sum_ns += (f64)periods[i]; } f64 mean_ns = periods_sum_ns / (f64)countof(periods); - atomic64_fetch_set(&G.current_scheduler_cycle_period_ns.v, math_round_to_int64(mean_ns)); + atomic64_fetch_set(&g->current_scheduler_cycle_period_ns.v, math_round_to_int64(mean_ns)); } { __profn("Job scheduler run"); - i64 current_cycle = atomic64_fetch_add(&G.current_scheduler_cycle.v, 1) + 1; - wake_time((u64)current_cycle); + i64 current_cycle = atomic64_fetch_add(&g->current_scheduler_cycle.v, 1) + 1; + P_W32_WakeByTime((u64)current_cycle); + } + } +} + +/* ========================== * + * Wait / wake + * ========================== */ + +void P_Wait(volatile void *addr, void *cmp, u32 size, i64 timeout_ns) +{ + P_W32_Fiber *fiber = P_W32_FiberFromId(FiberId()); + i16 parent_id = fiber->parent_id; + if (parent_id != 0) { + *fiber->yield_param = (P_W32_YieldParam) { + .kind = P_W32_YieldKind_Wait, + .wait = { + .addr = addr, + .cmp = cmp, + .size = size, + .timeout_ns = timeout_ns + } + }; + P_W32_YieldFiber(fiber, P_W32_FiberFromId(parent_id)); + } else { + i32 timeout_ms = 0; + if (timeout_ns > 10000000000000000ll) { + timeout_ms = INFINITE; + } else if (timeout_ns != 0) { + timeout_ms = timeout_ns / 1000000; + timeout_ms += (timeout_ms == 0) * math_fsign(timeout_ns); + } + if (addr == 0) { + Sleep(timeout_ms); + } else { + WaitOnAddress(addr, cmp, size, timeout_ms); + } + } +} + +void P_Wake(void *addr, i32 count) +{ + P_W32_WakeByAddress(addr, count); +} + +/* ========================== * + * Job + * ========================== */ + +void P_Run(i32 count, P_JobFunc *func, void *sig, P_Pool pool_kind, P_Priority priority, P_Counter *counter) +{ + __prof; + struct P_W32_Ctx *g = &P_W32_g_shared_ctx; + if (count > 0) { + if (counter) { + snc_counter_add(counter, count); + } + P_W32_Fiber *fiber = P_W32_FiberFromId(FiberId()); + priority = clamp_i32(priority, fiber->job_priority, P_Priority_Count - 1); /* A job cannot create a job with a higher priority than itself */ + if (pool_kind == P_Pool_Inherit) { + pool_kind = fiber->job_pool; + } + P_W32_JobPool *pool = &g->job_pools[pool_kind]; + P_W32_JobQueue *queue = &pool->job_queues[priority]; + P_W32_LockTicketMutex(&queue->lock); + { + P_W32_JobInfo *info = 0; + if (queue->first_free) { + info = queue->first_free; + queue->first_free = info->next; + } else { + info = arena_push_no_zero(queue->arena, P_W32_JobInfo); + } + MEMZERO_STRUCT(info); + info->count = count; + info->func = func; + info->sig = sig; + info->counter = counter; + if (queue->last) { + queue->last->next = info; + } else { + queue->first = info; + } + queue->last = info; + } + P_W32_UnlockTicketMutex(&queue->lock); + + /* Wake workers */ + { + P_W32_LockTicketMutex(&pool->workers_wake_lock); + { + atomic64_fetch_add(&pool->num_jobs_in_queue.v, count); + if (count >= P_W32_WakeAllThreshold) { + WakeByAddressAll(&pool->num_jobs_in_queue); + } else { + for (i32 i = 0; i < count; ++i) { + WakeByAddressSingle(&pool->num_jobs_in_queue); + } + } + } + P_W32_UnlockTicketMutex(&pool->workers_wake_lock); } } } @@ -1441,41 +1119,42 @@ INTERNAL THREAD_DEF(job_scheduler_entry, _) * Time * ========================== */ -INTERNAL struct sys_datetime win32_time_to_sys_time(SYSTEMTIME st) +P_DateTime P_W32_DateTimeFromWin32SystemTime(SYSTEMTIME st) { - return (struct sys_datetime) - { + return (P_DateTime) { .year = st.wYear, - .month = st.wMonth, - .day_of_week = st.wDayOfWeek, - .day = st.wDay, - .hour = st.wHour, - .minute = st.wMinute, - .second = st.wSecond, - .milliseconds = st.wMilliseconds + .month = st.wMonth, + .day_of_week = st.wDayOfWeek, + .day = st.wDay, + .hour = st.wHour, + .minute = st.wMinute, + .second = st.wSecond, + .milliseconds = st.wMilliseconds }; } -struct sys_datetime sys_local_time(void) +P_DateTime P_LocalTime(void) { SYSTEMTIME lt; GetLocalTime(<); - return win32_time_to_sys_time(lt); + return P_W32_DateTimeFromWin32SystemTime(lt); } -i64 sys_time_ns(void) +i64 P_TimeNs(void) { + struct P_W32_Ctx *g = &P_W32_g_shared_ctx; LARGE_INTEGER qpc; QueryPerformanceCounter(&qpc); - i64 res = (qpc.QuadPart - G.timer_start_qpc) * G.ns_per_qpc; + i64 res = (qpc.QuadPart - g->timer_start_qpc) * g->ns_per_qpc; return res; } + /* ========================== * * File system * ========================== */ -INTERNAL String string_from_win32_path(Arena *arena, wchar_t *src) +String P_W32_StringFromWin32Path(Arena *arena, wchar_t *src) { String res = { .len = 0, @@ -1501,7 +1180,7 @@ INTERNAL String string_from_win32_path(Arena *arena, wchar_t *src) return res; } -String sys_get_write_path(Arena *arena) +String P_GetWritePath(Arena *arena) { u16 *p = 0; /* TODO: cache this? */ @@ -1513,13 +1192,13 @@ String sys_get_write_path(Arena *arena) ); String path = ZI; if (res == S_OK) { - path = string_from_win32_path(arena, p); + path = P_W32_StringFromWin32Path(arena, p); } CoTaskMemFree(p); return path; } -b32 sys_is_file(String path) +b32 P_IsFile(String path) { __prof; TempArena scratch = scratch_begin_no_conflict(); @@ -1529,7 +1208,7 @@ b32 sys_is_file(String path) return attributes != INVALID_FILE_ATTRIBUTES && !(attributes & FILE_ATTRIBUTE_DIRECTORY); } -b32 sys_is_dir(String path) +b32 P_IsDir(String path) { TempArena scratch = scratch_begin_no_conflict(); wchar_t *path_wstr = wstr_from_string(scratch.arena, path); @@ -1538,7 +1217,7 @@ b32 sys_is_dir(String path) return attributes != INVALID_FILE_ATTRIBUTES && (attributes & FILE_ATTRIBUTE_DIRECTORY); } -void sys_mkdir(String path) +void P_MkDir(String path) { __prof; TempArena scratch = scratch_begin_no_conflict(); @@ -1570,19 +1249,19 @@ void sys_mkdir(String path) } if (err.len > 0) { String msg = string_format(scratch.arena, - LIT("Failed to create directory \"%F\": %F"), - FMT_STR(path), - FMT_STR(err)); - sys_panic(msg); + LIT("Failed to create directory \"%F\": %F"), + FMT_STR(path), + FMT_STR(err)); + P_Panic(msg); } scratch_end(scratch); } -struct sys_file sys_file_open_read(String path) +P_File P_OpenFileRead(String path) { __prof; TempArena scratch = scratch_begin_no_conflict(); - struct sys_file file = ZI; + P_File file = ZI; wchar_t *path_wstr = wstr_from_string(scratch.arena, path); HANDLE handle = CreateFileW( @@ -1601,11 +1280,11 @@ struct sys_file sys_file_open_read(String path) return file; } -struct sys_file sys_file_open_read_wait(String path) +P_File P_OpenFileReadWait(String path) { __prof; TempArena scratch = scratch_begin_no_conflict(); - struct sys_file file = ZI; + P_File file = ZI; wchar_t *path_wstr = wstr_from_string(scratch.arena, path); i32 delay_ms = 1; @@ -1628,11 +1307,11 @@ struct sys_file sys_file_open_read_wait(String path) return file; } -struct sys_file sys_file_open_write(String path) +P_File P_OpenFileWrite(String path) { __prof; TempArena scratch = scratch_begin_no_conflict(); - struct sys_file file = ZI; + P_File file = ZI; wchar_t *path_wstr = wstr_from_string(scratch.arena, path); HANDLE handle = CreateFileW( @@ -1651,11 +1330,11 @@ struct sys_file sys_file_open_write(String path) return file; } -struct sys_file sys_file_open_append(String path) +P_File P_OpenFileAppend(String path) { __prof; TempArena scratch = scratch_begin_no_conflict(); - struct sys_file file = ZI; + P_File file = ZI; wchar_t *path_wstr = wstr_from_string(scratch.arena, path); HANDLE handle = CreateFileW( @@ -1674,7 +1353,7 @@ struct sys_file sys_file_open_append(String path) return file; } -void sys_file_close(struct sys_file file) +void P_CloseFIle(P_File file) { __prof; if (file.handle) { @@ -1682,7 +1361,7 @@ void sys_file_close(struct sys_file file) } } -String sys_file_read_all(Arena *arena, struct sys_file file) +String P_ReadFile(Arena *arena, P_File file) { __prof; i64 size = 0; @@ -1710,16 +1389,16 @@ String sys_file_read_all(Arena *arena, struct sys_file file) return s; } -void sys_file_write(struct sys_file file, String data) +void P_WriteFile(P_File file, String data) { __prof; /* TODO: Check what the real data limit is and chunk sequentially based on * that (rather than failing) */ if (data.len >= 0x7FFF) { TempArena scratch = scratch_begin_no_conflict(); - sys_panic(string_format(scratch.arena, - LIT("Tried to write too many bytes to disk (%F)"), - FMT_UINT(data.len))); + P_Panic(string_format(scratch.arena, + LIT("Tried to write too many bytes to disk (%F)"), + FMT_UINT(data.len))); scratch_end(scratch); } @@ -1733,14 +1412,14 @@ void sys_file_write(struct sys_file file, String data) ); } -u64 sys_file_get_size(struct sys_file file) +u64 P_GetFileSize(P_File file) { LARGE_INTEGER li_file_size; GetFileSizeEx((HANDLE)file.handle, &li_file_size); return (u64)(li_file_size.QuadPart > 0 ? li_file_size.QuadPart : 0); } -struct sys_file_time sys_file_get_time(struct sys_file file) +P_FileTime P_GetFileTime(P_File file) { __prof; @@ -1763,14 +1442,14 @@ struct sys_file_time sys_file_get_time(struct sys_file file) FileTimeToSystemTime(&ft_accessed, &st_accessed); FileTimeToSystemTime(&ft_modified, &st_modified); - return (struct sys_file_time) + return (P_FileTime) { - .created = win32_time_to_sys_time(st_created), - .accessed = win32_time_to_sys_time(st_accessed), - .modified = win32_time_to_sys_time(st_modified) + .created = P_W32_DateTimeFromWin32SystemTime(st_created), + .accessed = P_W32_DateTimeFromWin32SystemTime(st_accessed), + .modified = P_W32_DateTimeFromWin32SystemTime(st_modified) }; } else { - return (struct sys_file_time) { 0 }; + return (P_FileTime) { 0 }; } } @@ -1778,12 +1457,12 @@ struct sys_file_time sys_file_get_time(struct sys_file file) * File map * ========================== */ -struct sys_file_map sys_file_map_open_read(struct sys_file file) +P_FileMap P_OpenFileMap(P_File file) { __prof; - struct sys_file_map map = ZI; + P_FileMap map = ZI; - u64 size = sys_file_get_size(file); + u64 size = P_GetFileSize(file); u8 *base_ptr = 0; HANDLE map_handle = 0; @@ -1822,7 +1501,7 @@ struct sys_file_map sys_file_map_open_read(struct sys_file file) return map; } -void sys_file_map_close(struct sys_file_map map) +void P_CloseFileMap(P_FileMap map) { if (map.mapped_memory.text) { UnmapViewOfFile(map.mapped_memory.text); @@ -1832,89 +1511,30 @@ void sys_file_map_close(struct sys_file_map map) } } -String sys_file_map_data(struct sys_file_map map) +String P_GetFileMapData(P_FileMap map) { return map.mapped_memory; } -/* ========================== * - * File iter - * ========================== */ - -struct win32_file_filter { - HANDLE find_handle; - wchar_t *filter_wstr; -}; - -struct sys_file_filter sys_file_filter_begin(Arena *arena, String pattern) -{ - struct sys_file_filter filter = ZI; - struct win32_file_filter *filter_internal = arena_push(arena, struct win32_file_filter); - filter_internal->filter_wstr = wstr_from_string(arena, pattern); - filter.handle = (u64)filter_internal; - return filter; -} - -b32 sys_file_filter_next(Arena *arena, struct sys_file_filter *filter) -{ - struct win32_file_filter *filter_internal = (struct win32_file_filter *)filter->handle; - - WIN32_FIND_DATAW find_file_data = ZI; - b32 found = 0; - - if (filter_internal->find_handle) { - found = FindNextFileW(filter_internal->find_handle, &find_file_data); - } else { - filter_internal->find_handle = FindFirstFileExW(filter_internal->filter_wstr, FindExInfoStandard, &find_file_data, FindExSearchNameMatch, 0, FIND_FIRST_EX_CASE_SENSITIVE | FIND_FIRST_EX_LARGE_FETCH); - found = filter_internal->find_handle != INVALID_HANDLE_VALUE; - } - - if (found) { - String file_name = string_from_wstr_no_limit(arena, find_file_data.cFileName); - if (string_eq(file_name, LIT(".")) || string_eq(file_name, LIT(".."))) { - /* Skip initial '.' and '..' matches */ - found = sys_file_filter_next(arena, filter); - } else { - filter->info.is_dir = find_file_data.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY; - filter->info.filename = string_copy(arena, file_name); - } - } - - return found; -} - -void sys_file_filter_end(struct sys_file_filter *filter) -{ - struct win32_file_filter *filter_internal = (struct win32_file_filter *)filter->handle; - if (filter_internal->find_handle) { - FindClose(filter_internal->find_handle); - } -} /* ========================== * * Watch * ========================== */ -struct win32_watch { - HANDLE dir_handle; - HANDLE wake_handle; - struct win32_watch *next_free; - u8 results_buff[KIBI(64)]; -}; - -struct sys_watch *sys_watch_alloc(String dir_path) +P_Watch *P_AllocWatch(String dir_path) { TempArena scratch = scratch_begin_no_conflict(); + struct P_W32_Ctx *g = &P_W32_g_shared_ctx; - struct win32_watch *w32_watch = 0; + P_W32_Watch *w32_watch = 0; { - struct snc_lock lock = snc_lock_e(&G.watches_mutex); + P_Lock lock = snc_lock_e(&g->watches_mutex); { - if (G.watches_first_free) { - w32_watch = G.watches_first_free; - G.watches_first_free = w32_watch->next_free; + if (g->watches_first_free) { + w32_watch = g->watches_first_free; + g->watches_first_free = w32_watch->next_free; } else { - w32_watch = arena_push_no_zero(G.watches_arena, struct win32_watch); + w32_watch = arena_push_no_zero(g->watches_arena, P_W32_Watch); } } snc_unlock(&lock); @@ -1935,28 +1555,29 @@ struct sys_watch *sys_watch_alloc(String dir_path) w32_watch->wake_handle = CreateEventW(0, 0, 0, 0); scratch_end(scratch); - return (struct sys_watch *)w32_watch; + return (P_Watch *)w32_watch; } -void sys_watch_release(struct sys_watch *dw) +void P_ReleaseWatch(P_Watch *dw) { - struct win32_watch *w32_watch = (struct win32_watch *)dw; + P_W32_Watch *w32_watch = (P_W32_Watch *)dw; + struct P_W32_Ctx *g = &P_W32_g_shared_ctx; CloseHandle(w32_watch->dir_handle); CloseHandle(w32_watch->wake_handle); - struct snc_lock lock = snc_lock_e(&G.watches_mutex); + P_Lock lock = snc_lock_e(&g->watches_mutex); { - w32_watch->next_free = G.watches_first_free; - G.watches_first_free = w32_watch; + w32_watch->next_free = g->watches_first_free; + g->watches_first_free = w32_watch; } snc_unlock(&lock); } -struct sys_watch_info_list sys_watch_read_wait(Arena *arena, struct sys_watch *dw) +P_WatchInfoList P_ReadWatchWait(Arena *arena, P_Watch *dw) { __prof; - struct win32_watch *w32_watch = (struct win32_watch *)dw; - struct sys_watch_info_list list = ZI; + P_W32_Watch *w32_watch = (P_W32_Watch *)dw; + P_WatchInfoList list = ZI; DWORD filter = FILE_NOTIFY_CHANGE_FILE_NAME | FILE_NOTIFY_CHANGE_DIR_NAME | @@ -1991,7 +1612,7 @@ struct sys_watch_info_list sys_watch_read_wait(Arena *arena, struct sys_watch *d while (!done) { FILE_NOTIFY_INFORMATION *res = (FILE_NOTIFY_INFORMATION *)(w32_watch->results_buff + offset); - struct sys_watch_info *info = arena_push(arena, struct sys_watch_info); + P_WatchInfo *info = arena_push(arena, P_WatchInfo); if (list.last) { list.last->next = info; info->prev = list.last; @@ -2015,32 +1636,32 @@ struct sys_watch_info_list sys_watch_read_wait(Arena *arena, struct sys_watch *d switch (res->Action) { case FILE_ACTION_ADDED: { - info->kind = SYS_WATCH_INFO_KIND_ADDED; + info->kind = P_WatchInfoKind_Added; } break; case FILE_ACTION_REMOVED: { - info->kind = SYS_WATCH_INFO_KIND_REMOVED; + info->kind = P_WatchInfoKind_Removed; } break; case FILE_ACTION_MODIFIED: { - info->kind = SYS_WATCH_INFO_KIND_MODIFIED; + info->kind = P_WatchInfoKind_Modified; } break; case FILE_ACTION_RENAMED_OLD_NAME: { - info->kind = SYS_WATCH_INFO_KIND_REMOVED; + info->kind = P_WatchInfoKind_RenamedOld; } break; case FILE_ACTION_RENAMED_NEW_NAME: { - info->kind = SYS_WATCH_INFO_KIND_RENAMED_OLD; + info->kind = P_WatchInfoKind_RenamedNew; } break; default: { - info->kind = SYS_WATCH_INFO_KIND_RENAMED_NEW; + info->kind = P_WatchInfoKind_Unknown; } break; } @@ -2061,9 +1682,9 @@ struct sys_watch_info_list sys_watch_read_wait(Arena *arena, struct sys_watch *d return list; } -void sys_watch_wake(struct sys_watch *dw) +void P_WakeWatch(P_Watch *dw) { - struct win32_watch *w32_watch = (struct win32_watch *)dw; + P_W32_Watch *w32_watch = (P_W32_Watch *)dw; SetEvent(w32_watch->wake_handle); } @@ -2071,21 +1692,20 @@ void sys_watch_wake(struct sys_watch *dw) * Window * ========================== */ -INTERNAL void win32_update_window_from_system(struct win32_window *window); -INTERNAL void win32_window_wake(struct win32_window *window); - -INTERNAL void win32_window_process_event(struct win32_window *window, struct sys_window_event event) +void P_W32_ProcessWindowEvent(P_W32_Window *window, P_WindowEvent event) { __prof; - struct snc_lock lock = snc_lock_e(&window->event_arena_swp_mutex); + P_Lock lock = snc_lock_e(&window->event_arena_swp_mutex); { - *arena_push(window->event_arenas[window->current_event_arena_index], struct sys_window_event) = event; + *arena_push(window->event_arenas[window->current_event_arena_index], P_WindowEvent) = event; } snc_unlock(&lock); } -INTERNAL HWND win32_window_init(struct win32_window *window) +HWND P_W32_InitWindow(P_W32_Window *window) { + struct P_W32_Ctx *g = &P_W32_g_shared_ctx; + /* * From martins (https://gist.github.com/mmozeiko/5e727f845db182d468a34d524508ad5f#file-win32_d3d11-c-L66-L70): * WS_EX_NOREDIRECTIONBITMAP flag here is needed to fix ugly bug with Windows 10 @@ -2098,7 +1718,7 @@ INTERNAL HWND win32_window_init(struct win32_window *window) /* TODO: Check for hwnd success */ HWND hwnd = CreateWindowExW( exstyle, - G.window_class.lpszClassName, + g->window_class.lpszClassName, L"", WS_OVERLAPPEDWINDOW, CW_USEDEFAULT, @@ -2107,7 +1727,7 @@ INTERNAL HWND win32_window_init(struct win32_window *window) CW_USEDEFAULT, 0, 0, - G.window_class.hInstance, + g->window_class.hInstance, 0 ); @@ -2121,13 +1741,13 @@ INTERNAL HWND win32_window_init(struct win32_window *window) return hwnd; } -INTERNAL THREAD_DEF(window_thread, arg) +P_W32_ThreadDef(P_W32_WindowThreadEntryFunc, arg) { - struct win32_window *window = (struct win32_window *)arg; + P_W32_Window *window = (P_W32_Window *)arg; /* Win32 limitation: Window must be initialized on same thread that processes events */ - window->hwnd = win32_window_init(window); - win32_update_window_from_system(window); + window->hwnd = P_W32_InitWindow(window); + P_W32_UpdateWindowFromSystem(window); BringWindowToTop(window->hwnd); snc_counter_add(&window->ready_fence, -1); @@ -2149,16 +1769,17 @@ INTERNAL THREAD_DEF(window_thread, arg) DestroyWindow(window->hwnd); } -INTERNAL struct win32_window *win32_window_alloc(void) +P_W32_Window *P_W32_AllocWindow(void) { - struct win32_window *window = 0; + P_W32_Ctx *g = &P_W32_g_shared_ctx; + P_W32_Window *window = 0; { - struct snc_lock lock = snc_lock_e(&G.windows_mutex); - if (G.first_free_window) { - window = G.first_free_window; - G.first_free_window = window->next_free; + P_Lock lock = snc_lock_e(&g->windows_mutex); + if (g->first_free_window) { + window = g->first_free_window; + g->first_free_window = window->next_free; } else { - window = arena_push_no_zero(G.windows_arena, struct win32_window); + window = arena_push_no_zero(g->windows_arena, P_W32_Window); } snc_unlock(&lock); } @@ -2172,49 +1793,50 @@ INTERNAL struct win32_window *win32_window_alloc(void) * created and receive a HWND, because on Windows a the event proc must run on * the same thread that created the window. */ snc_counter_add(&window->ready_fence, 1); - window->window_thread = thread_alloc(&window_thread, window, LIT("Window thread"), PROF_THREAD_GROUP_WINDOW); + window->window_thread = P_W32_AllocThread(&P_W32_WindowThreadEntryFunc, window, LIT("Window thread"), PROF_THREAD_GROUP_WINDOW); snc_counter_wait(&window->ready_fence); return window; } -INTERNAL void win32_window_release(struct win32_window *window) +void P_W32_ReleaseWindow(P_W32_Window *window) { /* Stop window threads */ atomic32_fetch_set(&window->shutdown, 1); - win32_window_wake(window); - thread_wait_release(window->window_thread); + P_W32_Ctx *g = &P_W32_g_shared_ctx; + P_W32_WakeWindow(window); + P_W32_WaitReleaseThread(window->window_thread); - struct snc_lock lock = snc_lock_e(&G.windows_mutex); + P_Lock lock = snc_lock_e(&g->windows_mutex); { - window->next_free = G.first_free_window; - G.first_free_window = window; + window->next_free = g->first_free_window; + g->first_free_window = window; } snc_unlock(&lock); } -struct sys_window_event_array sys_window_pop_events(Arena *arena, struct sys_window *sys_window) +P_WindowEventArray P_PopWindowEvents(Arena *arena, P_Window *p_window) { __prof; - struct win32_window *window = (struct win32_window *)sys_window; + P_W32_Window *window = (P_W32_Window *)p_window; i32 event_arena_index = 0; { /* Swap event buffers */ - struct snc_lock lock = snc_lock_e(&window->event_arena_swp_mutex); + P_Lock lock = snc_lock_e(&window->event_arena_swp_mutex); event_arena_index = window->current_event_arena_index; window->current_event_arena_index = 1 - window->current_event_arena_index; snc_unlock(&lock); } Arena *events_arena = window->event_arenas[event_arena_index]; - struct sys_window_event_array events = ZI; - events.count = events_arena->pos / sizeof(struct sys_window_event); - events.events = arena_push_array_no_zero(arena, struct sys_window_event, events.count); + P_WindowEventArray events = ZI; + events.count = events_arena->pos / sizeof(P_WindowEvent); + events.events = arena_push_array_no_zero(arena, P_WindowEvent, events.count); MEMCPY(events.events, arena_base(events_arena), events_arena->pos); arena_reset(events_arena); return events; } -INTERNAL void win32_update_window_from_system(struct win32_window *window) +void P_W32_UpdateWindowFromSystem(P_W32_Window *window) { HWND hwnd = window->hwnd; @@ -2235,19 +1857,19 @@ INTERNAL void win32_update_window_from_system(struct win32_window *window) window->monitor_height = monitor_rect.bottom - monitor_rect.top; /* Minimized / maximized */ - if (window->flags & SYS_WINDOW_FLAG_SHOWING) { + if (window->flags & P_WindowFlag_Showing) { WINDOWPLACEMENT placement = { .length = sizeof(placement) }; GetWindowPlacement(hwnd, &placement); if (placement.showCmd == SW_SHOWMINIMIZED) { - window->settings.flags |= SYS_WINDOW_SETTINGS_FLAG_MINIMIZED; + window->settings.flags |= P_WindowSettingsFlag_Minimized; } else { - window->settings.flags &= ~SYS_WINDOW_SETTINGS_FLAG_MINIMIZED; + window->settings.flags &= ~P_WindowSettingsFlag_Minimized; } if (placement.showCmd == SW_SHOWMAXIMIZED - || ((window->settings.flags & SYS_WINDOW_SETTINGS_FLAG_MINIMIZED) && ((placement.flags & WPF_RESTORETOMAXIMIZED) != 0))) { - window->settings.flags |= SYS_WINDOW_SETTINGS_FLAG_MAXIMIZED; + || ((window->settings.flags & P_WindowSettingsFlag_Minimized) && ((placement.flags & WPF_RESTORETOMAXIMIZED) != 0))) { + window->settings.flags |= P_WindowSettingsFlag_Maximized; } else { - window->settings.flags &= ~SYS_WINDOW_SETTINGS_FLAG_MAXIMIZED; + window->settings.flags &= ~P_WindowSettingsFlag_Maximized; } } @@ -2256,12 +1878,12 @@ INTERNAL void win32_update_window_from_system(struct win32_window *window) i32 y = client_rect.top; i32 width = client_rect.right - client_rect.left; i32 height = client_rect.bottom - client_rect.top; - if (!(window->settings.flags & SYS_WINDOW_SETTINGS_FLAG_MINIMIZED)) { + if (!(window->settings.flags & P_WindowSettingsFlag_Minimized)) { window->x = x; window->y = y; window->width = width; window->height = height; - if (!(window->settings.flags & (SYS_WINDOW_SETTINGS_FLAG_MAXIMIZED | SYS_WINDOW_SETTINGS_FLAG_FULLSCREEN))) { + if (!(window->settings.flags & (P_WindowSettingsFlag_Maximized | P_WindowSettingsFlag_Fullscreen))) { /* Treat a window resize in non maximized/fullscreen mode as a * settings change. * @@ -2275,27 +1897,27 @@ INTERNAL void win32_update_window_from_system(struct win32_window *window) } } -INTERNAL void win32_update_window_from_settings(struct win32_window *window, struct sys_window_settings *settings) +void P_W32_UpdateWindowFromSettings(P_W32_Window *window, P_WindowSettings *settings) { HWND hwnd = window->hwnd; - struct sys_window_settings old_settings = window->settings; + P_WindowSettings old_settings = window->settings; window->settings = *settings; i32 show_cmd = SW_HIDE; - if (window->flags & SYS_WINDOW_FLAG_SHOWING) { + if (window->flags & P_WindowFlag_Showing) { show_cmd = SW_NORMAL; - if (settings->flags & SYS_WINDOW_SETTINGS_FLAG_MAXIMIZED) { + if (settings->flags & P_WindowSettingsFlag_Maximized) { show_cmd = SW_SHOWMAXIMIZED; - } else if (settings->flags & SYS_WINDOW_SETTINGS_FLAG_MINIMIZED) { + } else if (settings->flags & P_WindowSettingsFlag_Minimized) { show_cmd = SW_MINIMIZE; } } RECT rect = ZI; - b32 old_fullscreen = old_settings.flags & SYS_WINDOW_SETTINGS_FLAG_FULLSCREEN; - b32 fullscreen = settings->flags & SYS_WINDOW_SETTINGS_FLAG_FULLSCREEN; + b32 old_fullscreen = old_settings.flags & P_WindowSettingsFlag_Fullscreen; + b32 fullscreen = settings->flags & P_WindowSettingsFlag_Fullscreen; if (fullscreen) { if (!old_fullscreen) { @@ -2337,16 +1959,17 @@ INTERNAL void win32_update_window_from_settings(struct win32_window *window, str } } -INTERNAL void win32_window_wake(struct win32_window *window) +void P_W32_WakeWindow(P_W32_Window *window) { /* Post a blank message to the window's thread message queue to wake it. */ PostMessageW(window->hwnd, 0, 0, 0); } -INTERNAL LRESULT CALLBACK win32_window_proc(HWND hwnd, UINT msg, WPARAM wparam, LPARAM lparam) +LRESULT CALLBACK P_W32_Win32WindowProc(HWND hwnd, UINT msg, WPARAM wparam, LPARAM lparam) { __prof; - struct win32_window *window = (struct win32_window *)GetWindowLongPtrW(hwnd, GWLP_USERDATA); + P_W32_Ctx *g = &P_W32_g_shared_ctx; + P_W32_Window *window = (P_W32_Window *)GetWindowLongPtrW(hwnd, GWLP_USERDATA); if (!window) { return DefWindowProcW(hwnd, msg, wparam, lparam); @@ -2357,17 +1980,17 @@ INTERNAL LRESULT CALLBACK win32_window_proc(HWND hwnd, UINT msg, WPARAM wparam, u32 cursor_flags = window->cursor_set_flags; /* Hide cursor */ - if (cursor_flags & WIN32_WINDOW_CURSOR_SET_FLAG_HIDE) { + if (cursor_flags & P_W32_CursorFlag_Hide) { while (ShowCursor(0) >= 0); } /* Show cursor */ - if (cursor_flags & WIN32_WINDOW_CURSOR_SET_FLAG_SHOW) { + if (cursor_flags & P_W32_CursorFlag_Show) { while (ShowCursor(1) < 0); } /* Update position */ - if (cursor_flags & WIN32_WINDOW_CURSOR_SET_FLAG_POSITION) { + if (cursor_flags & P_W32_CursorFlag_Position) { V2 window_space_pos = window->cursor_set_position; POINT p = { window_space_pos.x, window_space_pos.y }; ClientToScreen(window->hwnd, &p); @@ -2375,12 +1998,12 @@ INTERNAL LRESULT CALLBACK win32_window_proc(HWND hwnd, UINT msg, WPARAM wparam, } /* Stop clipping cursor */ - if (cursor_flags & WIN32_WINDOW_CURSOR_SET_FLAG_DISABLE_CLIP) { + if (cursor_flags & P_W32_CursorFlag_DisableClip) { ClipCursor(0); } /* Clip cursor in window window */ - if (cursor_flags & WIN32_WINDOW_CURSOR_SET_FLAG_ENABLE_CLIP) { + if (cursor_flags & P_W32_CursorFlag_EnableClip) { i32 left = window->x + math_round_to_int(window->cursor_clip_bounds.x); i32 right = left + math_round_to_int(window->cursor_clip_bounds.width); i32 top = window->y + math_round_to_int(window->cursor_clip_bounds.y); @@ -2417,11 +2040,13 @@ INTERNAL LRESULT CALLBACK win32_window_proc(HWND hwnd, UINT msg, WPARAM wparam, switch (msg) { case WM_QUIT: case WM_CLOSE: - case WM_DESTROY: { - win32_window_process_event(window, (struct sys_window_event) { .kind = SYS_EVENT_KIND_QUIT }); + case WM_DESTROY: + { + P_W32_ProcessWindowEvent(window, (P_WindowEvent) { .kind = P_WindowEventKind_Quit }); } break; - case WM_PAINT: { + case WM_PAINT: + { result = DefWindowProcW(hwnd, msg, wparam, lparam); } break; @@ -2429,49 +2054,54 @@ INTERNAL LRESULT CALLBACK win32_window_proc(HWND hwnd, UINT msg, WPARAM wparam, case WM_MOVE: case WM_MOVING: case WM_SIZE: - case WM_SIZING: { - win32_update_window_from_system(window); + case WM_SIZING: + { + P_W32_UpdateWindowFromSystem(window); result = DefWindowProcW(hwnd, msg, wparam, lparam); } break; /* Keyboard buttons */ case WM_SYSKEYUP: - case WM_SYSKEYDOWN: { + case WM_SYSKEYDOWN: + { if (LOWORD(wparam) != VK_MENU) { result = DefWindowProcW(hwnd, msg, wparam, lparam); } } FALLTHROUGH; case WM_KEYUP: - case WM_KEYDOWN: { + case WM_KEYDOWN: + { WORD vk_code = LOWORD(wparam); b32 is_repeat = 0; - enum sys_window_event_kind event_kind = SYS_EVENT_KIND_NONE; + P_WindowEventKind event_kind = P_WindowEventKind_None; if (msg == WM_KEYDOWN || msg == WM_SYSKEYDOWN) { - event_kind = SYS_EVENT_KIND_BUTTON_DOWN; + event_kind = P_WindowEventKind_ButtonDown; is_repeat = (lparam & 0x40000000) != 0; } else if (msg == WM_KEYUP || msg == WM_SYSKEYUP) { - event_kind = SYS_EVENT_KIND_BUTTON_UP; + event_kind = P_WindowEventKind_ButtonUp; } - enum sys_btn button = SYS_BTN_NONE; - if (vk_code < countof(G.vk_btn_table)) { - button = G.vk_btn_table[vk_code]; + P_Btn button = P_Btn_None; + if (vk_code < countof(g->vk_btn_table)) { + button = g->vk_btn_table[vk_code]; } - win32_window_process_event( + P_W32_ProcessWindowEvent( window, - (struct sys_window_event) { - .kind = event_kind, + (P_WindowEvent) + { + .kind = event_kind, .button = button, .is_repeat = is_repeat - } + } ); } break; /* Text */ case WM_SYSCHAR: - case WM_CHAR: { + case WM_CHAR: + { u16 utf16_char = (u32)wparam; /* Decode */ @@ -2498,12 +2128,13 @@ INTERNAL LRESULT CALLBACK win32_window_proc(HWND hwnd, UINT msg, WPARAM wparam, if (codepoint == '\r') { codepoint = '\n'; /* Just treat all \r as newline */ } - if((codepoint >= 32 && codepoint != 127) || codepoint == '\t' || codepoint == '\n') { - win32_window_process_event( + if ((codepoint >= 32 && codepoint != 127) || codepoint == '\t' || codepoint == '\n') { + P_W32_ProcessWindowEvent( window, - (struct sys_window_event) { - .kind = SYS_EVENT_KIND_TEXT, - .text_codepoint = codepoint + (P_WindowEvent) + { + .kind = P_WindowEventKind_Text, + .text_codepoint = codepoint } ); } @@ -2516,73 +2147,81 @@ INTERNAL LRESULT CALLBACK win32_window_proc(HWND hwnd, UINT msg, WPARAM wparam, case WM_LBUTTONUP: case WM_MBUTTONUP: case WM_RBUTTONUP: - case WM_XBUTTONUP: { + case WM_XBUTTONUP: + { ReleaseCapture(); is_release = 1; } FALLTHROUGH; case WM_LBUTTONDOWN: case WM_MBUTTONDOWN: case WM_RBUTTONDOWN: - case WM_XBUTTONDOWN: { - if(!is_release) { + case WM_XBUTTONDOWN: + { + if (!is_release) { SetCapture(hwnd); } - enum sys_window_event_kind event_kind = is_release ? SYS_EVENT_KIND_BUTTON_UP : SYS_EVENT_KIND_BUTTON_DOWN; - enum sys_btn button = 0; + P_WindowEventKind event_kind = is_release ? P_WindowEventKind_ButtonUp : P_WindowEventKind_ButtonDown; + P_Btn button = 0; - switch(msg) { - case WM_LBUTTONUP: case WM_LBUTTONDOWN: button = SYS_BTN_M1; break; - case WM_RBUTTONUP: case WM_RBUTTONDOWN: button = SYS_BTN_M2; break; - case WM_MBUTTONUP: case WM_MBUTTONDOWN: button = SYS_BTN_M3; break; - case WM_XBUTTONUP: case WM_XBUTTONDOWN: { + switch (msg) { + case WM_LBUTTONUP: case WM_LBUTTONDOWN: button = P_Btn_M1; break; + case WM_RBUTTONUP: case WM_RBUTTONDOWN: button = P_Btn_M2; break; + case WM_MBUTTONUP: case WM_MBUTTONDOWN: button = P_Btn_M3; break; + case WM_XBUTTONUP: case WM_XBUTTONDOWN: + { u32 wparam_xbutton = GET_XBUTTON_WPARAM(wparam); if (wparam_xbutton == XBUTTON1) { - button = SYS_BTN_M4; + button = P_Btn_M4; } else if (wparam_xbutton == XBUTTON2) { - button = SYS_BTN_M5; + button = P_Btn_M5; } } break; } if (button) { - win32_window_process_event( + P_W32_ProcessWindowEvent( window, - (struct sys_window_event) { - .kind = event_kind, + (P_WindowEvent) + { + .kind = event_kind, .button = button - } + } ); } } break; /* Mouse wheel */ - case WM_MOUSEWHEEL: { + case WM_MOUSEWHEEL: + { int delta = GET_WHEEL_DELTA_WPARAM(wparam); i32 dir = delta >= 0 ? 1 : -1; - enum sys_btn button = dir >= 0 ? SYS_BTN_MWHEELUP : SYS_BTN_MWHEELDOWN; + P_Btn button = dir >= 0 ? P_Btn_MWheelUp : P_Btn_MWheelDown; for (i32 i = 0; i < (dir * delta); i += WHEEL_DELTA) { /* Send a button down & button up event simultaneously */ - win32_window_process_event(window, (struct sys_window_event) { .kind = SYS_EVENT_KIND_BUTTON_DOWN, .button = button }); - win32_window_process_event(window, (struct sys_window_event) { .kind = SYS_EVENT_KIND_BUTTON_UP, .button = button }); + P_W32_ProcessWindowEvent(window, (P_WindowEvent) { .kind = P_WindowEventKind_ButtonDown, .button = button }); + P_W32_ProcessWindowEvent(window, (P_WindowEvent) { .kind = P_WindowEventKind_ButtonUp, .button = button }); } } break; /* Mouse move */ - case WM_MOUSEMOVE: { + case WM_MOUSEMOVE: + { i32 x = GET_X_LPARAM(lparam); i32 y = GET_Y_LPARAM(lparam); - win32_window_process_event( + P_W32_ProcessWindowEvent( window, - (struct sys_window_event) { - .kind = SYS_EVENT_KIND_CURSOR_MOVE, + (P_WindowEvent) + { + .kind = P_WindowEventKind_CursorMove, .cursor_position = V2FromXY(x, y) - } + } ); } break; /* Raw mouse move */ - case WM_INPUT: { + case WM_INPUT: + { TempArena scratch = scratch_begin_no_conflict(); /* Read raw input buffer */ @@ -2600,12 +2239,13 @@ INTERNAL LRESULT CALLBACK win32_window_proc(HWND hwnd, UINT msg, WPARAM wparam, i32 x = raw.data.mouse.lLastX; i32 y = raw.data.mouse.lLastY; V2 delta = V2FromXY(x, y); - win32_window_process_event( + P_W32_ProcessWindowEvent( window, - (struct sys_window_event) { - .kind = SYS_EVENT_KIND_MOUSE_MOVE, + (P_WindowEvent) + { + .kind = P_WindowEventKind_MouseMove, .mouse_delta = delta - } + } ); } @@ -2613,14 +2253,16 @@ INTERNAL LRESULT CALLBACK win32_window_proc(HWND hwnd, UINT msg, WPARAM wparam, } break; /* Minmax info */ - case WM_GETMINMAXINFO: { + case WM_GETMINMAXINFO: + { /* Set minimum window size */ LPMINMAXINFO mmi = (LPMINMAXINFO)lparam; mmi->ptMinTrackSize.x = 100; mmi->ptMinTrackSize.y = 100; } break; - default: { + default: + { result = DefWindowProcW(hwnd, msg, wparam, lparam); } break; } @@ -2628,127 +2270,127 @@ INTERNAL LRESULT CALLBACK win32_window_proc(HWND hwnd, UINT msg, WPARAM wparam, return result; } -struct sys_window *sys_window_alloc(void) +P_Window *P_AllocWindow(void) { __prof; - return (struct sys_window *)win32_window_alloc(); + return (P_Window *)P_W32_AllocWindow(); } -void sys_window_release(struct sys_window *sys_window) +void P_ReleaseWindow(P_Window *p_window) { __prof; - struct win32_window *window = (struct win32_window *)sys_window; - win32_window_release(window); + P_W32_Window *window = (P_W32_Window *)p_window; + P_W32_ReleaseWindow(window); } -void sys_window_update_settings(struct sys_window *sys_window, struct sys_window_settings *settings) +void P_UpdateWindowSettings(P_Window *p_window, P_WindowSettings *settings) { __prof; - struct win32_window *window = (struct win32_window *)sys_window; - struct snc_lock lock = snc_lock_e(&window->settings_mutex); + P_W32_Window *window = (P_W32_Window *)p_window; + P_Lock lock = snc_lock_e(&window->settings_mutex); { - win32_update_window_from_settings(window, settings); + P_W32_UpdateWindowFromSettings(window, settings); } snc_unlock(&lock); } /* FIXME: Lock settings mutex for these functions */ -struct sys_window_settings sys_window_get_settings(struct sys_window *sys_window) +P_WindowSettings P_GetWindowSettings(P_Window *p_window) { - struct win32_window *window = (struct win32_window *)sys_window; + P_W32_Window *window = (P_W32_Window *)p_window; return window->settings; } -void sys_window_show(struct sys_window *sys_window) +void P_ShowWindow(P_Window *p_window) { - struct win32_window *window = (struct win32_window *)sys_window; + P_W32_Window *window = (P_W32_Window *)p_window; HWND hwnd = window->hwnd; - struct snc_lock lock = snc_lock_e(&window->settings_mutex); + P_Lock lock = snc_lock_e(&window->settings_mutex); { i32 show_cmd = SW_NORMAL; - struct sys_window_settings *settings = &window->settings; - if (settings->flags & SYS_WINDOW_SETTINGS_FLAG_MAXIMIZED) { + P_WindowSettings *settings = &window->settings; + if (settings->flags & P_WindowSettingsFlag_Maximized) { show_cmd = SW_SHOWMAXIMIZED; - } else if (settings->flags & SYS_WINDOW_SETTINGS_FLAG_MINIMIZED) { + } else if (settings->flags & P_WindowSettingsFlag_Minimized) { show_cmd = SW_MINIMIZE; } - window->flags |= SYS_WINDOW_FLAG_SHOWING; + window->flags |= P_WindowFlag_Showing; ShowWindow(hwnd, show_cmd); BringWindowToTop(hwnd); } snc_unlock(&lock); } -V2 sys_window_get_size(struct sys_window *sys_window) +V2 P_GetWindowSize(P_Window *p_window) { - struct win32_window *window = (struct win32_window *)sys_window; + P_W32_Window *window = (P_W32_Window *)p_window; return V2FromXY((f32)window->width, (f32)window->height); } -V2 sys_window_get_monitor_size(struct sys_window *sys_window) +V2 P_GetWindowMonitorSize(P_Window *p_window) { - struct win32_window *window = (struct win32_window *)sys_window; + P_W32_Window *window = (P_W32_Window *)p_window; return V2FromXY((f32)window->monitor_width, (f32)window->monitor_height); } -u64 sys_window_get_internal_handle(struct sys_window *sys_window) +u64 P_GetInternalWindowHandle(P_Window *p_window) { - struct win32_window *window = (struct win32_window *)sys_window; + P_W32_Window *window = (P_W32_Window *)p_window; return (u64)window->hwnd; } -void sys_window_cursor_set_pos(struct sys_window *sys_window, V2 pos) +void P_SetWindowCursorPos(P_Window *p_window, V2 pos) { - struct win32_window *window = (struct win32_window *)sys_window; + P_W32_Window *window = (P_W32_Window *)p_window; window->cursor_set_position = pos; - window->cursor_set_flags |= WIN32_WINDOW_CURSOR_SET_FLAG_POSITION; - win32_window_wake(window); + window->cursor_set_flags |= P_W32_CursorFlag_Position; + P_W32_WakeWindow(window); } -void sys_window_cursor_show(struct sys_window *sys_window) +void P_ShowWindowCursor(P_Window *p_window) { - struct win32_window *window = (struct win32_window *)sys_window; - window->cursor_set_flags |= WIN32_WINDOW_CURSOR_SET_FLAG_SHOW; - win32_window_wake(window); + P_W32_Window *window = (P_W32_Window *)p_window; + window->cursor_set_flags |= P_W32_CursorFlag_Show; + P_W32_WakeWindow(window); } -void sys_window_cursor_hide(struct sys_window *sys_window) +void P_HideWindowCursor(P_Window *p_window) { - struct win32_window *window = (struct win32_window *)sys_window; - window->cursor_set_flags |= WIN32_WINDOW_CURSOR_SET_FLAG_HIDE; - win32_window_wake(window); + P_W32_Window *window = (P_W32_Window *)p_window; + window->cursor_set_flags |= P_W32_CursorFlag_Hide; + P_W32_WakeWindow(window); } -void sys_window_cursor_enable_clip(struct sys_window *sys_window, Rect bounds) +void P_EnableWindoweCursorClip(P_Window *p_window, Rect bounds) { - struct win32_window *window = (struct win32_window *)sys_window; + P_W32_Window *window = (P_W32_Window *)p_window; window->cursor_clip_bounds = bounds; - window->cursor_set_flags |= WIN32_WINDOW_CURSOR_SET_FLAG_ENABLE_CLIP; - win32_window_wake(window); + window->cursor_set_flags |= P_W32_CursorFlag_EnableClip; + P_W32_WakeWindow(window); } -void sys_window_cursor_disable_clip(struct sys_window *sys_window) +void P_DisableWindoweCursorClip(P_Window *p_window) { - struct win32_window *window = (struct win32_window *)sys_window; - window->cursor_set_flags |= WIN32_WINDOW_CURSOR_SET_FLAG_DISABLE_CLIP; - win32_window_wake(window); + P_W32_Window *window = (P_W32_Window *)p_window; + window->cursor_set_flags |= P_W32_CursorFlag_DisableClip; + P_W32_WakeWindow(window); } -void sys_window_toggle_topmost(struct sys_window *sys_window) +void P_ToggleWindowTopmost(P_Window *p_window) { - struct win32_window *window = (struct win32_window *)sys_window; + P_W32_Window *window = (P_W32_Window *)p_window; atomic32_fetch_add(&window->topmost_toggles, 1); - win32_window_wake(window); + P_W32_WakeWindow(window); } /* ========================== * * Address * ========================== */ -INTERNAL struct sys_address sys_address_from_ip_port_cstr(char *ip_cstr, char *port_cstr) +P_Address P_AddressFromIpPortCstr(char *ip_cstr, char *port_cstr) { - struct sys_address res = ZI; + P_Address res = ZI; struct addrinfo hints = ZI; hints.ai_family = AF_UNSPEC; @@ -2762,7 +2404,7 @@ INTERNAL struct sys_address sys_address_from_ip_port_cstr(char *ip_cstr, char *p if (ai_res->ai_family == AF_INET) { struct sockaddr_in *sockaddr = (struct sockaddr_in *)ai_res->ai_addr; res.valid = 1; - res.family = SYS_ADDRESS_FAMILY_IPV4; + res.family = P_AddressFamily_Ipv4; res.portnb = sockaddr->sin_port; STATIC_ASSERT(sizeof(sockaddr->sin_addr) == 4); MEMCPY(res.ipnb, (void *)&sockaddr->sin_addr, 4); @@ -2772,7 +2414,7 @@ INTERNAL struct sys_address sys_address_from_ip_port_cstr(char *ip_cstr, char *p #if 0 struct sockaddr_in6 *sockaddr = (struct sockaddr_in6 *)ai_res->ai_addr; res.valid = 1; - res.family = SYS_ADDRESS_FAMILY_IPV6; + res.family = P_AddressFamily_Ipv6; res.portnb = sockaddr->sin6_port; STATIC_ASSERT(sizeof(sockaddr->sin6_addr) == 16); MEMCPY(res.ipnb, (void *)&sockaddr->sin6_addr, 16); @@ -2787,7 +2429,7 @@ INTERNAL struct sys_address sys_address_from_ip_port_cstr(char *ip_cstr, char *p return res; } -struct sys_address sys_address_from_string(String str) +P_Address P_AddressFromString(String str) { /* Parse string into ip & port */ u8 ip_buff[1024]; @@ -2855,11 +2497,11 @@ struct sys_address sys_address_from_string(String str) } } - struct sys_address res = sys_address_from_ip_port_cstr(ip_cstr, port_cstr); + P_Address res = P_AddressFromIpPortCstr(ip_cstr, port_cstr); return res; } -struct sys_address sys_address_from_port(u16 port) +P_Address P_AddressFromPort(u16 port) { u8 port_buff[128]; char *port_cstr = 0; @@ -2882,16 +2524,16 @@ struct sys_address sys_address_from_port(u16 port) } } - struct sys_address res = sys_address_from_ip_port_cstr(0, port_cstr); + P_Address res = P_AddressFromIpPortCstr(0, port_cstr); return res; } -String sys_string_from_address(Arena *arena, struct sys_address address) +String P_StringFromAddress(Arena *arena, P_Address address) { String res = ZI; - if (address.family == SYS_ADDRESS_FAMILY_IPV6) { + if (address.family == P_AddressFamily_Ipv6) { /* TODO */ } else { u8 ip[4]; @@ -2905,15 +2547,15 @@ String sys_string_from_address(Arena *arena, struct sys_address address) return res; } -b32 sys_address_eq(struct sys_address a, struct sys_address b) +b32 P_AddressIsEqual(P_Address a, P_Address b) { return MEMEQ_STRUCT(&a, &b); } -INTERNAL struct win32_address win32_address_from_sys_address(struct sys_address addr) +P_W32_Address P_W32_Win32AddressFromPlatformAddress(P_Address addr) { - struct win32_address res = ZI; - if (addr.family == SYS_ADDRESS_FAMILY_IPV4) { + P_W32_Address res = ZI; + if (addr.family == P_AddressFamily_Ipv4) { res.family = AF_INET; res.size = sizeof(struct sockaddr_in); res.sin.sin_port = addr.portnb; @@ -2929,9 +2571,8 @@ INTERNAL struct win32_address win32_address_from_sys_address(struct sys_address return res; } -#if 0 /* If supplied address has ip INADDR_ANY (0), convert ip to localhost */ -INTERNAL struct win32_address win32_address_convert_any_to_localhost(struct win32_address addr) +P_W32_Address P_W32_ConvertAnyaddrToLocalhost(P_W32_Address addr) { if (addr.family == AF_INET) { u8 *bytes = (u8 *)&addr.sin.sin_addr; @@ -2961,18 +2602,17 @@ INTERNAL struct win32_address win32_address_convert_any_to_localhost(struct win3 } return addr; } -#endif -INTERNAL struct sys_address sys_address_from_win32_address(struct win32_address ws_addr) +P_Address P_W32_PlatformAddressFromWin32Address(P_W32_Address ws_addr) { - struct sys_address res = ZI; + P_Address res = ZI; if (ws_addr.family == AF_INET) { - res.family = SYS_ADDRESS_FAMILY_IPV4; + res.family = P_AddressFamily_Ipv4; res.portnb = ws_addr.sin.sin_port; MEMCPY(res.ipnb, &ws_addr.sin.sin_addr, 4); res.valid = 1; } else if (ws_addr.family == AF_INET6) { - res.family = SYS_ADDRESS_FAMILY_IPV6; + res.family = P_AddressFamily_Ipv6; res.portnb = ws_addr.sin6.sin6_port; MEMCPY(res.ipnb, &ws_addr.sin6.sin6_addr.s6_addr, 16); res.valid = 1; @@ -2985,23 +2625,24 @@ INTERNAL struct sys_address sys_address_from_win32_address(struct win32_address * Sock * ========================== */ -struct sys_sock *sys_sock_alloc(u16 listen_port, u64 sndbuf_size, u64 rcvbuf_size) +P_Sock *P_AllocSock(u16 listen_port, u64 sndbuf_size, u64 rcvbuf_size) { - struct win32_sock *ws = 0; + P_W32_Ctx *g = &P_W32_g_shared_ctx; + P_W32_Sock *ws = 0; { - struct snc_lock lock = snc_lock_e(&G.socks_mutex); - if (G.first_free_sock) { - ws = G.first_free_sock; - G.first_free_sock = ws->next_free; + P_Lock lock = snc_lock_e(&g->socks_mutex); + if (g->first_free_sock) { + ws = g->first_free_sock; + g->first_free_sock = ws->next_free; } else { - ws = arena_push_no_zero(G.socks_arena, struct win32_sock); + ws = arena_push_no_zero(g->socks_arena, P_W32_Sock); } snc_unlock(&lock); } MEMZERO_STRUCT(ws); - struct sys_address addr = sys_address_from_port(listen_port); - struct win32_address bind_address = win32_address_from_sys_address(addr); + P_Address addr = P_AddressFromPort(listen_port); + P_W32_Address bind_address = P_W32_Win32AddressFromPlatformAddress(addr); ws->sock = socket(bind_address.family, SOCK_DGRAM, IPPROTO_UDP); { i32 sb = sndbuf_size; @@ -3013,39 +2654,40 @@ struct sys_sock *sys_sock_alloc(u16 listen_port, u64 sndbuf_size, u64 rcvbuf_siz } bind(ws->sock, &bind_address.sa, bind_address.size); - return (struct sys_sock *)ws; + return (P_Sock *)ws; } -void sys_sock_release(struct sys_sock *sock) +void P_ReleaseSock(P_Sock *sock) { - struct win32_sock *ws = (struct win32_sock *)sock; + P_W32_Ctx *g = &P_W32_g_shared_ctx; + P_W32_Sock *ws = (P_W32_Sock *)sock; closesocket(ws->sock); - struct snc_lock lock = snc_lock_e(&G.socks_mutex); + P_Lock lock = snc_lock_e(&g->socks_mutex); { - ws->next_free = G.first_free_sock; - G.first_free_sock = ws; + ws->next_free = g->first_free_sock; + g->first_free_sock = ws; } snc_unlock(&lock); } -struct sys_sock_read_result sys_sock_read(Arena *arena, struct sys_sock *sock) +P_SockReadResult P_ReadSock(Arena *arena, P_Sock *sock) { - struct win32_sock *ws = (struct win32_sock *)sock; + P_W32_Sock *ws = (P_W32_Sock *)sock; u64 read_buff_size = KIBI(64); String read_buff = ZI; read_buff.len = read_buff_size; read_buff.text = arena_push_array_no_zero(arena, u8, read_buff_size); - struct sys_sock_read_result res = ZI; + P_SockReadResult res = ZI; - struct win32_address ws_addr = ZI; + P_W32_Address ws_addr = ZI; ws_addr.size = sizeof(ws_addr.sas); i32 size = recvfrom(ws->sock, (char *)read_buff.text, read_buff.len, 0, &ws_addr.sa, &ws_addr.size); ws_addr.family = ws_addr.sin.sin_family; - res.address = sys_address_from_win32_address(ws_addr); + res.address = P_W32_PlatformAddressFromWin32Address(ws_addr); if (size >= 0) { gstat_add(GSTAT_SOCK_BYTES_RECEIVED, size); res.data.text = read_buff.text; @@ -3066,10 +2708,10 @@ struct sys_sock_read_result sys_sock_read(Arena *arena, struct sys_sock *sock) return res; } -void sys_sock_write(struct sys_sock *sock, struct sys_address address, String data) +void P_WriteSock(P_Sock *sock, P_Address address, String data) { - struct win32_sock *ws = (struct win32_sock *)sock; - struct win32_address ws_addr = win32_address_from_sys_address(address); + P_W32_Sock *ws = (P_W32_Sock *)sock; + P_W32_Address ws_addr = P_W32_Win32AddressFromPlatformAddress(address); i32 size = sendto(ws->sock, (char *)data.text, data.len, 0, &ws_addr.sa, ws_addr.size); if (size > 0) { gstat_add(GSTAT_SOCK_BYTES_SENT, size); @@ -3087,7 +2729,7 @@ void sys_sock_write(struct sys_sock *sock, struct sys_address address, String da * Util * ========================== */ -void sys_message_box(enum sys_message_box_kind kind, String message) +void P_MessageBox(P_MessageBoxKind kind, String message) { TempArena scratch = scratch_begin_no_conflict(); @@ -3096,24 +2738,24 @@ void sys_message_box(enum sys_message_box_kind kind, String message) UINT mbox_type = MB_SETFOREGROUND; switch (kind) { - case SYS_MESSAGE_BOX_KIND_OK: + case P_MessageBoxKind_Ok: { mbox_type |= MB_ICONINFORMATION; } break; - case SYS_MESSAGE_BOX_KIND_WARNING: + case P_MessageBoxKind_Warning: { title = L"Warning"; mbox_type |= MB_ICONWARNING; } break; - case SYS_MESSAGE_BOX_KIND_ERROR: + case P_MessageBoxKind_Error: { title = L"Error"; mbox_type |= MB_ICONERROR; } break; - case SYS_MESSAGE_BOX_KIND_FATAL: + case P_MessageBoxKind_Fatal: { title = L"Fatal error"; mbox_type |= MB_ICONSTOP; @@ -3126,7 +2768,7 @@ void sys_message_box(enum sys_message_box_kind kind, String message) scratch_end(scratch); } -void sys_set_clipboard_text(String str) +void P_SetClipboardText(String str) { if (OpenClipboard(0)) { TempArena scratch = scratch_begin_no_conflict(); @@ -3146,7 +2788,7 @@ void sys_set_clipboard_text(String str) } } -String sys_get_clipboard_text(Arena *arena) +String P_GetClipboardText(Arena *arena) { String res = ZI; if (IsClipboardFormatAvailable(CF_UNICODETEXT) && OpenClipboard(0)) { @@ -3161,49 +2803,53 @@ String sys_get_clipboard_text(Arena *arena) return res; } -u32 sys_num_logical_processors(void) +u32 P_GetLogicalProcessorCount(void) { return GetActiveProcessorCount(ALL_PROCESSOR_GROUPS); } -u32 sys_current_thread_id(void) +u32 P_GetThreadId(void) { return GetCurrentThreadId(); } -i64 sys_current_scheduler_period_ns(void) +i64 P_GetCurrentSchedulerPeriodNs(void) { - return atomic64_fetch(&G.current_scheduler_cycle_period_ns.v); + P_W32_Ctx *g = &P_W32_g_shared_ctx; + return atomic64_fetch(&g->current_scheduler_cycle_period_ns.v); } /* ========================== * * Exit * ========================== */ -void sys_on_exit(sys_exit_func *func) +void P_OnExit(P_ExitFunc *func) { - i32 index = atomic32_fetch_add(&G.num_exit_funcs, 1); - if (index >= MAX_EXIT_FUNCS) { - sys_panic(LIT("Maximum on exit functions registered")); + P_W32_Ctx *g = &P_W32_g_shared_ctx; + i32 index = atomic32_fetch_add(&g->num_exit_funcs, 1); + if (index >= P_W32_MaxOnExitFuncs) { + P_Panic(LIT("Maximum on exit functions registered")); } - G.exit_funcs[index] = func; + g->exit_funcs[index] = func; } -void sys_exit(void) +void P_Exit(void) { - SetEvent(G.exit_begin_event); + P_W32_Ctx *g = &P_W32_g_shared_ctx; + SetEvent(g->exit_begin_event); } -void sys_panic(String msg) +void P_Panic(String msg) { - if (atomic32_fetch_test_set(&G.panicking, 0, 1) == 0) { + P_W32_Ctx *g = &P_W32_g_shared_ctx; + if (atomic32_fetch_test_set(&g->panicking, 0, 1) == 0) { log_panic(msg); - wchar_t *wstr = G.panic_wstr; + wchar_t *wstr = g->panic_wstr; u64 wstr_len = 0; wchar_t prefix[] = L"A fatal error has occured and the application needs to exit:\n\n"; - MEMCPY(wstr, prefix, min_u64(countof(G.panic_wstr), (countof(prefix) << 1))); + MEMCPY(wstr, prefix, min_u64(countof(g->panic_wstr), (countof(prefix) << 1))); wstr_len += countof(prefix) - 1; /* Perform manual string encode to avoid any implicit memory @@ -3215,7 +2861,7 @@ void sys_panic(String msg) Utf8DecodeResult decoded = uni_decode_utf8(str8_remaining); Utf16EncodeResult encoded = uni_encode_utf16(decoded.codepoint); u64 wstr_new_len = wstr_len + encoded.count16; - if (wstr_new_len < (countof(G.panic_wstr) - 1)) { + if (wstr_new_len < (countof(g->panic_wstr) - 1)) { u16 *dest = wstr + wstr_len; MEMCPY(dest, encoded.chars16, (encoded.count16 << 1)); wstr_len = wstr_new_len; @@ -3232,10 +2878,10 @@ void sys_panic(String msg) ASSERT(0); #endif - SetEvent(G.panic_event); + SetEvent(g->panic_event); /* Wait for process termination */ - if (GetCurrentThreadId() != G.main_thread_id) { + if (GetCurrentThreadId() != g->main_thread_id) { Sleep(INFINITE); } } @@ -3245,72 +2891,75 @@ void sys_panic(String msg) * Entry point * ========================== */ -INTERNAL void win32_init_vk_btn_table(void) +void P_W32_InitBtnTable(void) { - MEMZERO_ARRAY(G.vk_btn_table); + P_W32_Ctx *g = &P_W32_g_shared_ctx; + MEMZERO_ARRAY(g->vk_btn_table); - for (u32 i = 'A', j = SYS_BTN_A; i <= 'Z'; ++i, ++j) { - G.vk_btn_table[i] = (enum sys_btn)j; + for (u32 i = 'A', j = P_Btn_A; i <= 'Z'; ++i, ++j) { + g->vk_btn_table[i] = (P_Btn)j; } - for (u32 i = '0', j = SYS_BTN_0; i <= '9'; ++i, ++j) { - G.vk_btn_table[i] = (enum sys_btn)j; + for (u32 i = '0', j = P_Btn_0; i <= '9'; ++i, ++j) { + g->vk_btn_table[i] = (P_Btn)j; } - for (u32 i = VK_F1, j = SYS_BTN_F1; i <= VK_F24; ++i, ++j) { - G.vk_btn_table[i] = (enum sys_btn)j; + for (u32 i = VK_F1, j = P_Btn_F1; i <= VK_F24; ++i, ++j) { + g->vk_btn_table[i] = (P_Btn)j; } - G.vk_btn_table[VK_ESCAPE] = SYS_BTN_ESC; - G.vk_btn_table[VK_OEM_3] = SYS_BTN_GRAVE_ACCENT; - G.vk_btn_table[VK_OEM_MINUS] = SYS_BTN_MINUS; - G.vk_btn_table[VK_OEM_PLUS] = SYS_BTN_EQUAL; - G.vk_btn_table[VK_BACK] = SYS_BTN_BACKSPACE; - G.vk_btn_table[VK_TAB] = SYS_BTN_TAB; - G.vk_btn_table[VK_SPACE] = SYS_BTN_SPACE; - G.vk_btn_table[VK_RETURN] = SYS_BTN_ENTER; - G.vk_btn_table[VK_CONTROL] = SYS_BTN_CTRL; - G.vk_btn_table[VK_SHIFT] = SYS_BTN_SHIFT; - G.vk_btn_table[VK_MENU] = SYS_BTN_ALT; - G.vk_btn_table[VK_UP] = SYS_BTN_UP; - G.vk_btn_table[VK_LEFT] = SYS_BTN_LEFT; - G.vk_btn_table[VK_DOWN] = SYS_BTN_DOWN; - G.vk_btn_table[VK_RIGHT] = SYS_BTN_RIGHT; - G.vk_btn_table[VK_DELETE] = SYS_BTN_DELETE; - G.vk_btn_table[VK_PRIOR] = SYS_BTN_PAGE_UP; - G.vk_btn_table[VK_NEXT] = SYS_BTN_PAGE_DOWN; - G.vk_btn_table[VK_HOME] = SYS_BTN_HOME; - G.vk_btn_table[VK_END] = SYS_BTN_END; - G.vk_btn_table[VK_OEM_2] = SYS_BTN_FORWARD_SLASH; - G.vk_btn_table[VK_OEM_PERIOD] = SYS_BTN_PERIOD; - G.vk_btn_table[VK_OEM_COMMA] = SYS_BTN_COMMA; - G.vk_btn_table[VK_OEM_7] = SYS_BTN_QUOTE; - G.vk_btn_table[VK_OEM_4] = SYS_BTN_LEFT_BRACKET; - G.vk_btn_table[VK_OEM_6] = SYS_BTN_RIGHT_BRACKET; - G.vk_btn_table[VK_INSERT] = SYS_BTN_INSERT; - G.vk_btn_table[VK_OEM_1] = SYS_BTN_SEMICOLON; + g->vk_btn_table[VK_ESCAPE] = P_Btn_ESC; + g->vk_btn_table[VK_OEM_3] = P_Btn_GraveAccent; + g->vk_btn_table[VK_OEM_MINUS] = P_Btn_Minus; + g->vk_btn_table[VK_OEM_PLUS] = P_Btn_Equal; + g->vk_btn_table[VK_BACK] = P_Btn_Backspace; + g->vk_btn_table[VK_TAB] = P_Btn_Tab; + g->vk_btn_table[VK_SPACE] = P_Btn_Space; + g->vk_btn_table[VK_RETURN] = P_Btn_Enter; + g->vk_btn_table[VK_CONTROL] = P_Btn_Ctrl; + g->vk_btn_table[VK_SHIFT] = P_Btn_Shift; + g->vk_btn_table[VK_MENU] = P_Btn_Alt; + g->vk_btn_table[VK_UP] = P_Btn_Up; + g->vk_btn_table[VK_LEFT] = P_Btn_Left; + g->vk_btn_table[VK_DOWN] = P_Btn_Down; + g->vk_btn_table[VK_RIGHT] = P_Btn_Right; + g->vk_btn_table[VK_DELETE] = P_Btn_Delete; + g->vk_btn_table[VK_PRIOR] = P_Btn_PageUp; + g->vk_btn_table[VK_NEXT] = P_Btn_PageDown; + g->vk_btn_table[VK_HOME] = P_Btn_Home; + g->vk_btn_table[VK_END] = P_Btn_End; + g->vk_btn_table[VK_OEM_2] = P_Btn_ForwardSlash; + g->vk_btn_table[VK_OEM_PERIOD] = P_Btn_Period; + g->vk_btn_table[VK_OEM_COMMA] = P_Btn_Comma; + g->vk_btn_table[VK_OEM_7] = P_Btn_Quote; + g->vk_btn_table[VK_OEM_4] = P_Btn_LeftBracket; + g->vk_btn_table[VK_OEM_6] = P_Btn_RightBracket; + g->vk_btn_table[VK_INSERT] = P_Btn_Insert; + g->vk_btn_table[VK_OEM_1] = P_Btn_Semicolon; } -INTERNAL SYS_JOB_DEF(sys_app_startup_job, _) +P_JobDef(P_W32_AppStartupJob, _) { (UNUSED)_; + P_W32_Ctx *g = &P_W32_g_shared_ctx; TempArena scratch = scratch_begin_no_conflict(); { - String cmdline_args = string_from_wstr(scratch.arena, G.cmdline_args_wstr, countof(G.cmdline_args_wstr)); - sys_app_startup(cmdline_args); - SetEvent(G.startup_end_event); + String cmdline_args = string_from_wstr(scratch.arena, g->cmdline_args_wstr, countof(g->cmdline_args_wstr)); + P_AppStartup(cmdline_args); + SetEvent(g->startup_end_event); } scratch_end(scratch); } -INTERNAL SYS_JOB_DEF(sys_app_shutdown_job, _) +P_JobDef(P_W32_AppShutdownJob, _) { __prof; + P_W32_Ctx *g = &P_W32_g_shared_ctx; (UNUSED)_; - i32 num_funcs = atomic32_fetch(&G.num_exit_funcs); + i32 num_funcs = atomic32_fetch(&g->num_exit_funcs); for (i32 i = num_funcs - 1; i >= 0; --i) { - sys_exit_func *func = G.exit_funcs[i]; + P_ExitFunc *func = g->exit_funcs[i]; func(); } - SetEvent(G.exit_end_event); + SetEvent(g->exit_end_event); } int CALLBACK wWinMain(_In_ HINSTANCE instance, _In_opt_ HINSTANCE prev_instance, _In_ LPWSTR cmdline_wstr, _In_ int show_code) @@ -3321,7 +2970,7 @@ int CALLBACK wWinMain(_In_ HINSTANCE instance, _In_opt_ HINSTANCE prev_instance, (UNUSED)show_code; __profthread("Main thread", PROF_THREAD_GROUP_MAIN); - + P_W32_Ctx *g = &P_W32_g_shared_ctx; #if PROFILING /* Start profiler */ @@ -3388,67 +3037,67 @@ int CALLBACK wWinMain(_In_ HINSTANCE instance, _In_opt_ HINSTANCE prev_instance, #endif /* 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->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); /* Init timer */ { LARGE_INTEGER qpf; QueryPerformanceFrequency(&qpf); - G.ns_per_qpc = 1000000000 / qpf.QuadPart; + g->ns_per_qpc = 1000000000 / qpf.QuadPart; } { LARGE_INTEGER qpc; QueryPerformanceCounter(&qpc); - G.timer_start_qpc = qpc.QuadPart; + g->timer_start_qpc = qpc.QuadPart; } /* Init fibers */ - G.num_fibers = 1; /* Fiber at index 0 always nil */ - G.fiber_names_arena = arena_alloc(GIBI(64)); + g->num_fibers = 1; /* Fiber at index 0 always nil */ + g->fiber_names_arena = arena_alloc(GIBI(64)); /* Init wait lists */ - G.wait_lists_arena = arena_alloc(GIBI(64)); + g->wait_lists_arena = arena_alloc(GIBI(64)); /* Convert main thread to fiber */ - fiber_alloc(0); + P_W32_AllocFiber(0); /* Init job pools */ - for (enum sys_pool pool_kind = 0; pool_kind < (i32)countof(G.job_pools); ++pool_kind) { - struct job_pool *pool = &G.job_pools[pool_kind]; + for (P_Pool pool_kind = 0; pool_kind < (i32)countof(g->job_pools); ++pool_kind) { + P_W32_JobPool *pool = &g->job_pools[pool_kind]; /* Init queues */ - for (enum sys_priority priority = 0; priority < (i32)countof(pool->job_queues); ++priority) { - struct job_queue *queue = &pool->job_queues[priority]; + for (P_Priority priority = 0; priority < (i32)countof(pool->job_queues); ++priority) { + P_W32_JobQueue *queue = &pool->job_queues[priority]; queue->arena = arena_alloc(GIBI(64)); } } - u64 cmdline_len = wstr_len(cmdline_wstr, countof(G.cmdline_args_wstr) - 1); - MEMCPY(G.cmdline_args_wstr, cmdline_wstr, cmdline_len * sizeof(*cmdline_wstr)); - G.cmdline_args_wstr[cmdline_len] = 0; + u64 cmdline_len = wstr_len(cmdline_wstr, countof(g->cmdline_args_wstr) - 1); + MEMCPY(g->cmdline_args_wstr, cmdline_wstr, cmdline_len * sizeof(*cmdline_wstr)); + g->cmdline_args_wstr[cmdline_len] = 0; - G.main_thread_id = GetCurrentThreadId(); + g->main_thread_id = GetCurrentThreadId(); SetThreadDescription(GetCurrentThread(), L"Main thread"); /* Query system info */ - GetSystemInfo(&G.info); + GetSystemInfo(&g->info); /* Initialize vk table */ - win32_init_vk_btn_table(); + P_W32_InitBtnTable(); /* Create window class */ { /* Register the window class */ - WNDCLASSEXW *wc = &G.window_class; + WNDCLASSEXW *wc = &g->window_class; wc->cbSize = sizeof(WNDCLASSEX); - wc->lpszClassName = WINDOW_CLASS_NAME; + wc->lpszClassName = P_W32_WindowClassName; wc->hCursor = LoadCursor(0, IDC_ARROW); wc->style = CS_HREDRAW | CS_VREDRAW | CS_OWNDC; //wc->hbrBackground = (HBRUSH)GetStockObject(BLACK_BRUSH); - wc->lpfnWndProc = win32_window_proc; + wc->lpfnWndProc = P_W32_Win32WindowProc; wc->hInstance = instance; /* Use first icon resource as window icon (same as explorer) */ @@ -3457,12 +3106,12 @@ int CALLBACK wWinMain(_In_ HINSTANCE instance, _In_opt_ HINSTANCE prev_instance, ExtractIconExW(path, 0, &wc->hIcon, &wc->hIconSm, 1); if (!RegisterClassExW(wc)) { - sys_panic(LIT("Failed to register window class")); + P_Panic(LIT("Failed to register window class")); } } /* Register raw input */ - if (!atomic32_fetch(&G.panicking)) { + if (!atomic32_fetch(&g->panicking)) { RAWINPUTDEVICE rid = (RAWINPUTDEVICE) { .usUsagePage = 0x01, /* HID_USAGE_PAGE_GENERIC */ .usUsage = 0x02, /* HID_USAGE_GENERIC_MOUSE */ @@ -3475,34 +3124,34 @@ int CALLBACK wWinMain(_In_ HINSTANCE instance, _In_opt_ HINSTANCE prev_instance, } /* Init threads pool */ - G.threads_arena = arena_alloc(GIBI(64)); + g->threads_arena = arena_alloc(GIBI(64)); /* Init watches pool */ - G.watches_arena = arena_alloc(GIBI(64)); + g->watches_arena = arena_alloc(GIBI(64)); /* Init windows pool */ - G.windows_arena = arena_alloc(GIBI(64)); + g->windows_arena = arena_alloc(GIBI(64)); /* Init winsock */ - WSAStartup(MAKEWORD(2, 2), &G.wsa_data); - G.socks_arena = arena_alloc(GIBI(64)); + WSAStartup(MAKEWORD(2, 2), &g->wsa_data); + g->socks_arena = arena_alloc(GIBI(64)); /* Start job scheduler */ - atomic64_fetch_set(&G.current_scheduler_cycle_period_ns.v, DEFAULT_SCHEDULER_CYCLE_PERIOD_NS); - struct thread *scheduler_thread = thread_alloc(job_scheduler_entry, 0, LIT("Scheduler thread"), PROF_THREAD_GROUP_SCHEDULER); + atomic64_fetch_set(&g->current_scheduler_cycle_period_ns.v, P_W32_DefaultSchedulerPeriodNs); + P_W32_Thread *scheduler_thread = P_W32_AllocThread(P_W32_JobSchedulerEntryFunc, 0, LIT("Scheduler thread"), PROF_THREAD_GROUP_SCHEDULER); /* Start job workers */ /* TODO: Heuristic worker counts & affinities */ { __profn("Start job workers"); - for (enum sys_pool pool_kind = 0; pool_kind < (i32)countof(G.job_pools); ++pool_kind) { - struct job_pool *pool = &G.job_pools[pool_kind]; + for (P_Pool pool_kind = 0; pool_kind < (i32)countof(g->job_pools); ++pool_kind) { + P_W32_JobPool *pool = &g->job_pools[pool_kind]; String name_fmt = ZI; i32 prof_group = PROF_THREAD_GROUP_FIBERS - MEBI(pool_kind); switch (pool_kind) { default: ASSERT(0); break; - case SYS_POOL_SIM: + case P_Pool_Sim: { name_fmt = LIT("Sim worker #%F"); pool->num_worker_threads = 4; @@ -3510,7 +3159,7 @@ int CALLBACK wWinMain(_In_ HINSTANCE instance, _In_opt_ HINSTANCE prev_instance, pool->thread_priority = THREAD_PRIORITY_TIME_CRITICAL; } break; - case SYS_POOL_USER: + case P_Pool_User: { name_fmt = LIT("User worker #%F"); pool->num_worker_threads = 4; @@ -3518,7 +3167,7 @@ int CALLBACK wWinMain(_In_ HINSTANCE instance, _In_opt_ HINSTANCE prev_instance, pool->thread_priority = THREAD_PRIORITY_TIME_CRITICAL; } break; - case SYS_POOL_AUDIO: + case P_Pool_Audio: { name_fmt = LIT("Audio worker #%F"); pool->num_worker_threads = 2; @@ -3527,14 +3176,14 @@ int CALLBACK wWinMain(_In_ HINSTANCE instance, _In_opt_ HINSTANCE prev_instance, pool->thread_is_audio = 1; } break; - case SYS_POOL_BACKGROUND: + case P_Pool_Background: { name_fmt = LIT("Background worker #%F"); pool->num_worker_threads = 2; pool->thread_affinity_mask = 0x0000000000000C00ull; } break; - case SYS_POOL_FLOATING: + case P_Pool_Floating: { name_fmt = LIT("Floating worker #%F"); pool->num_worker_threads = 8; @@ -3542,14 +3191,14 @@ int CALLBACK wWinMain(_In_ HINSTANCE instance, _In_opt_ HINSTANCE prev_instance, } break; } pool->worker_threads_arena = arena_alloc(GIBI(64)); - pool->worker_threads = arena_push_array(pool->worker_threads_arena, struct thread *, pool->num_worker_threads); - pool->worker_contexts = arena_push_array(pool->worker_threads_arena, struct worker_ctx, pool->num_worker_threads); + pool->worker_threads = arena_push_array(pool->worker_threads_arena, P_W32_Thread *, pool->num_worker_threads); + pool->worker_contexts = arena_push_array(pool->worker_threads_arena, P_W32_WorkerCtx, pool->num_worker_threads); for (i32 i = 0; i < pool->num_worker_threads; ++i) { - struct worker_ctx *ctx = &pool->worker_contexts[i]; + P_W32_WorkerCtx *ctx = &pool->worker_contexts[i]; ctx->pool_kind = pool_kind; ctx->id = i; String name = string_format(pool->worker_threads_arena, name_fmt, FMT_SINT(i)); - pool->worker_threads[i] = thread_alloc(job_worker_entry, ctx, name, prof_group + i); + pool->worker_threads[i] = P_W32_AllocThread(P_W32_JobWorkerEntryFunc, ctx, name, prof_group + i); } } } @@ -3557,25 +3206,25 @@ int CALLBACK wWinMain(_In_ HINSTANCE instance, _In_opt_ HINSTANCE prev_instance, /* ================================================== * * App startup */ - /* Run app start job */ - if (!atomic32_fetch(&G.panicking)) { - sys_run(1, sys_app_startup_job, 0, SYS_POOL_FLOATING, SYS_PRIORITY_HIGH, 0); + /* Run app start job */ + if (!atomic32_fetch(&g->panicking)) { + P_Run(1, P_W32_AppStartupJob, 0, P_Pool_Floating, P_Priority_High, 0); } /* Wait for startup end or panic */ - if (!atomic32_fetch(&G.panicking)) { + if (!atomic32_fetch(&g->panicking)) { HANDLE handles[] = { - G.startup_end_event, - G.panic_event + g->startup_end_event, + g->panic_event }; WaitForMultipleObjects(countof(handles), handles, 0, INFINITE); } /* Wait for exit start or panic */ - if (!atomic32_fetch(&G.panicking)) { + if (!atomic32_fetch(&g->panicking)) { HANDLE handles[] = { - G.exit_begin_event, - G.panic_event + g->exit_begin_event, + g->panic_event }; WaitForMultipleObjects(countof(handles), handles, 0, INFINITE); } @@ -3584,65 +3233,65 @@ int CALLBACK wWinMain(_In_ HINSTANCE instance, _In_opt_ HINSTANCE prev_instance, * App shutdown */ /* Run exit callbacks job */ - if (!atomic32_fetch(&G.panicking)) { - sys_run(1, sys_app_shutdown_job, 0, SYS_POOL_FLOATING, SYS_PRIORITY_HIGH, 0); + if (!atomic32_fetch(&g->panicking)) { + P_Run(1, P_W32_AppShutdownJob, 0, P_Pool_Floating, P_Priority_High, 0); } /* Wait for exit end or panic */ - if (!atomic32_fetch(&G.panicking)) { + if (!atomic32_fetch(&g->panicking)) { HANDLE handles[] = { - G.exit_end_event, - G.panic_event + g->exit_end_event, + g->panic_event }; WaitForMultipleObjects(countof(handles), handles, 0, INFINITE); } /* Signal shutdown */ - if (!atomic32_fetch(&G.panicking)) { - atomic32_fetch_set(&G.shutdown, 1); - for (enum sys_pool pool_kind = 0; pool_kind < (i32)countof(G.job_pools); ++pool_kind) { - struct job_pool *pool = &G.job_pools[pool_kind]; - tm_lock(&pool->workers_wake_lock); + if (!atomic32_fetch(&g->panicking)) { + atomic32_fetch_set(&g->shutdown, 1); + for (P_Pool pool_kind = 0; pool_kind < (i32)countof(g->job_pools); ++pool_kind) { + P_W32_JobPool *pool = &g->job_pools[pool_kind]; + P_W32_LockTicketMutex(&pool->workers_wake_lock); { atomic32_fetch_set(&pool->workers_shutdown.v, 1); atomic64_fetch_set(&pool->num_jobs_in_queue.v, -100000); WakeByAddressAll(&pool->num_jobs_in_queue); } - tm_unlock(&pool->workers_wake_lock); + P_W32_UnlockTicketMutex(&pool->workers_wake_lock); } } /* Wait on worker threads */ - if (!atomic32_fetch(&G.panicking)) { - for (enum sys_pool pool_kind = 0; pool_kind < (i32)countof(G.job_pools); ++pool_kind) { - struct job_pool *pool = &G.job_pools[pool_kind]; + if (!atomic32_fetch(&g->panicking)) { + for (P_Pool pool_kind = 0; pool_kind < (i32)countof(g->job_pools); ++pool_kind) { + P_W32_JobPool *pool = &g->job_pools[pool_kind]; for (i32 i = 0; i < pool->num_worker_threads; ++i) { - struct thread *worker_thread = pool->worker_threads[i]; - thread_wait_release(worker_thread); + P_W32_Thread *worker_thread = pool->worker_threads[i]; + P_W32_WaitReleaseThread(worker_thread); } } } /* Wait on scheduler thread */ - if (!atomic32_fetch(&G.panicking)) { - thread_wait_release(scheduler_thread); + if (!atomic32_fetch(&g->panicking)) { + P_W32_WaitReleaseThread(scheduler_thread); } /* Find any dangling threads that haven't exited gracefully by now */ - if (!atomic32_fetch(&G.panicking)) { - struct snc_lock lock = snc_lock_s(&G.threads_mutex); - if (G.first_thread) { + if (!atomic32_fetch(&g->panicking)) { + P_Lock lock = snc_lock_s(&g->threads_mutex); + if (g->first_thread) { TempArena scratch = scratch_begin_no_conflict(); u64 num_dangling_threads = 0; String threads_msg = ZI; threads_msg.text = arena_push_dry(scratch.arena, u8); - for (struct thread *t = G.first_thread; t; t = t->next) { + for (P_W32_Thread *t = g->first_thread; t; t = t->next) { String name = string_from_cstr(t->thread_name_cstr, countof(t->thread_name_cstr)); threads_msg.len += string_format(scratch.arena, LIT(" \"%F\"\n"), FMT_STR(name)).len; ++num_dangling_threads; } threads_msg = string_format(scratch.arena, LIT("%F dangling thread(s):\n%F"), FMT_UINT(num_dangling_threads), FMT_STR(threads_msg)); - sys_panic(threads_msg); + P_Panic(threads_msg); scratch_end(scratch); } snc_unlock(&lock); @@ -3650,9 +3299,9 @@ int CALLBACK wWinMain(_In_ HINSTANCE instance, _In_opt_ HINSTANCE prev_instance, /* Exit */ i32 exit_code = 0; - if (atomic32_fetch(&G.panicking)) { - WaitForSingleObject(G.panic_event, INFINITE); - MessageBoxExW(0, G.panic_wstr, L"Fatal error", MB_ICONSTOP | MB_SETFOREGROUND | MB_TOPMOST, 0); + if (atomic32_fetch(&g->panicking)) { + WaitForSingleObject(g->panic_event, INFINITE); + MessageBoxExW(0, g->panic_wstr, L"Fatal error", MB_ICONSTOP | MB_SETFOREGROUND | MB_TOPMOST, 0); exit_code = 1; } return exit_code; @@ -3668,7 +3317,7 @@ int CALLBACK wWinMain(_In_ HINSTANCE instance, _In_opt_ HINSTANCE prev_instance, #pragma clang diagnostic ignored "-Wmissing-variable-declarations" #pragma clang diagnostic ignored "-Wmissing-prototypes" -/* Enable floating point */ + /* Enable floating point */ __attribute((used)) int _fltused; diff --git a/src/platform/platform_win32.h b/src/platform/platform_win32.h new file mode 100644 index 00000000..809c3eaf --- /dev/null +++ b/src/platform/platform_win32.h @@ -0,0 +1,469 @@ +#pragma warning(push, 0) +# define UNICODE +# define WIN32_LEAN_AND_MEAN +# include +# include +# include +# include +# include +# include +# include +# include +# include +# include +# include +#pragma warning(pop) + +#define P_W32_WindowClassName L"power_play_window_class" + +#define P_W32_ThreadStackSize KIBI(64) +#define P_W32_FiberStackSize MEBI(4) + +#define P_W32_ThreadDef(name, arg_name) void name(void *arg_name) +typedef P_W32_ThreadDef(P_W32_ThreadFunc, data); + +/* Assume scheduler cycle is 20hz at start to be conservative */ +#define P_W32_DefaultSchedulerPeriodNs 50000000 +#define P_W32_NumRollingSchedulerPeriods 1000 + +#define P_W32_FiberNamePrefixCstr "Fiber [" +#define P_W32_FiberNameSuffixCstr "]" +#define P_W32_FiberNameMaxSize 64 + +#define P_W32_NumWaitAddrBins 16384 +#define P_W32_NumWaitTimeBins 1024 + +#define P_W32_MaxOnExitFuncs 1024 + +/* Arbitrary threshold for determining when to fall back from a looped WakeByAddressSingle to WakeByAddressAll */ +#define P_W32_WakeAllThreshold 16 + +/* ========================== * + * Ticket mutex + * ========================== */ + +typedef struct P_W32_TicketMutex P_W32_TicketMutex; +struct P_W32_TicketMutex { + Atomic64Padded ticket; + Atomic64Padded serving; +}; + +void P_W32_LockTicketMutex(P_W32_TicketMutex *tm); + +void P_W32_UnlockTicketMutex(P_W32_TicketMutex *tm); + +/* ========================== * + * Thread + * ========================== */ + +typedef struct P_W32_Thread P_W32_Thread; +struct P_W32_Thread { + P_W32_ThreadFunc *entry_point; + void *thread_data; + char thread_name_cstr[256]; + wchar_t thread_name_wstr[256]; + i32 profiler_group; + + P_W32_Thread *next; + P_W32_Thread *prev; + + HANDLE handle; +}; + +DWORD WINAPI P_W32_Win32ThreadProc(LPVOID vt); + +P_W32_Thread *P_W32_AllocThread(P_W32_ThreadFunc *entry_point, void *thread_data, String thread_name, i32 profiler_group); + +b32 P_W32_TryReleaseThread(P_W32_Thread *thread, f32 timeout_seconds); + +void P_W32_WaitReleaseThread(P_W32_Thread *thread); + +/* ========================== * + * Wait list + * ========================== */ + +typedef struct P_W32_JobPool P_W32_JobPool; + +typedef struct P_W32_WaitList P_W32_WaitList; +struct alignas(64) P_W32_WaitList { + u64 value; + i16 first_waiter; + i16 last_waiter; + i32 num_waiters; + P_W32_WaitList *next_in_bin; + P_W32_WaitList *prev_in_bin; +}; +STATIC_ASSERT(alignof(P_W32_WaitList) == 64); /* Avoid false sharing */ + +typedef struct P_W32_WaitBin P_W32_WaitBin; +struct alignas(64) P_W32_WaitBin { + P_W32_WaitList *first_wait_list; + P_W32_WaitList *last_wait_list; + P_W32_WaitList *first_free_wait_list; + P_W32_TicketMutex lock; +}; +STATIC_ASSERT(alignof(P_W32_WaitBin) == 64); /* Avoid false sharing */ + +typedef struct P_W32_Fiber P_W32_Fiber; +void P_W32_WakeLockedFibers(i32 num_fibers, P_W32_Fiber **fibers); + +void P_W32_WakeByAddress(void *addr, i32 count); + +void P_W32_WakeByTime(u64 time); + +/* ========================== * + * Fiber + * ========================== */ + +typedef enum P_W32_YieldKind { + P_W32_YieldKind_None, + P_W32_YieldKind_Done, + P_W32_YieldKind_Wait, + + P_W32_YieldKind_Count +} P_W32_YieldKind; + +typedef struct P_W32_YieldParam P_W32_YieldParam; +struct P_W32_YieldParam { + P_W32_YieldKind kind; + union { + struct { + volatile void *addr; + void *cmp; + u32 size; + i64 timeout_ns; + } wait; + }; +}; + +typedef struct P_W32_Fiber P_W32_Fiber; +struct alignas(64) P_W32_Fiber { + /* ---------------------------------------------------- */ + void *addr; /* 08 bytes */ + /* ---------------------------------------------------- */ + char *name_cstr; /* 08 bytes */ + /* ---------------------------------------------------- */ + Atomic32 wake_lock; /* 04 bytes (4 byte alignment) */ + i16 id; /* 02 bytes */ + i16 parent_id; /* 02 bytes */ + /* ---------------------------------------------------- */ + u64 wait_addr; /* 08 bytes */ + /* ---------------------------------------------------- */ + u64 wait_time; /* 08 bytes */ + /* ---------------------------------------------------- */ + i16 next_addr_waiter; /* 02 bytes */ + i16 prev_addr_waiter; /* 02 bytes */ + i16 next_time_waiter; /* 02 bytes */ + i16 prev_time_waiter; /* 02 bytes */ + /* ---------------------------------------------------- */ + u8 _pad1[8]; /* 08 bytes (padding) */ + /* ---------------------------------------------------- */ + u8 _pad2[8]; /* 08 bytes (padding) */ + /* ---------------------------------------------------- */ + /* -------------------- Cache line -------------------- */ + /* ---------------------------------------------------- */ + P_JobFunc *job_func; /* 08 bytes */ + /* ---------------------------------------------------- */ + void *job_sig; /* 08 bytes */ + /* ---------------------------------------------------- */ + i32 job_id; /* 04 bytes */ + i16 job_pool; /* 02 bytes */ + i16 job_priority; /* 02 bytes */ + /* ---------------------------------------------------- */ + P_Counter *job_counter; /* 08 bytes */ + /* ---------------------------------------------------- */ + P_W32_YieldParam *yield_param; /* 08 bytes */ + /* ---------------------------------------------------- */ + u8 _pad3[24]; /* 24 bytes (padding) */ + +}; +STATIC_ASSERT(sizeof(P_W32_Fiber) == 128); /* Padding validation (increase if necessary) */ +STATIC_ASSERT(alignof(P_W32_Fiber) == 64); /* Avoid false sharing */ +STATIC_ASSERT(offsetof(P_W32_Fiber, wake_lock) % 4 == 0); /* Atomic must be aligned */ + +P_W32_Fiber *P_W32_AllocFiber(P_W32_JobPool *pool); + +void P_W32_ReleaseFiber(P_W32_JobPool *pool, P_W32_Fiber *fiber); + +FORCE_INLINE P_W32_Fiber *P_W32_FiberFromId(i16 id); + +FORCE_NO_INLINE void P_W32_FiberResume(P_W32_Fiber *fiber); + +void P_W32_YieldFiber(P_W32_Fiber *fiber, P_W32_Fiber *parent_fiber); + +void P_W32_FiberEntryPoint(void *id_ptr); + +/* ========================== * + * Job queue + * ========================== */ + +typedef struct P_W32_WorkerCtx P_W32_WorkerCtx; +struct alignas(64) P_W32_WorkerCtx { + P_Pool pool_kind; + i32 id; +}; + +typedef struct P_W32_JobInfo P_W32_JobInfo; +struct P_W32_JobInfo { + i32 num_dispatched; + + i32 count; + P_JobFunc *func; + void *sig; + P_Counter *counter; + + i16 fiber_id; /* If the job is being resumed from a yield */ + + P_W32_JobInfo *next; +}; + +typedef struct P_W32_JobQueue P_W32_JobQueue; +struct alignas(64) P_W32_JobQueue { + P_W32_TicketMutex lock; + Arena *arena; + + P_W32_JobInfo *first; + P_W32_JobInfo *last; + + P_W32_JobInfo *first_free; +}; + +typedef struct P_W32_JobPool P_W32_JobPool; +struct alignas(64) P_W32_JobPool { + /* Jobs */ + P_W32_JobQueue job_queues[P_Priority_Count]; + + P_W32_TicketMutex free_fibers_lock; + i16 first_free_fiber_id; + + /* Workers */ + Atomic32Padded workers_shutdown; + Atomic64Padded num_jobs_in_queue; + P_W32_TicketMutex workers_wake_lock; + + i32 num_worker_threads; + i32 thread_priority; + u64 thread_affinity_mask; + b32 thread_is_audio; + Arena *worker_threads_arena; + P_W32_Thread **worker_threads; + P_W32_WorkerCtx *worker_contexts; +}; + +P_W32_ThreadDef(P_W32_JobWorkerEntryFunc, worker_ctx_arg); + +P_W32_ThreadDef(P_W32_JobSchedulerEntryFunc, _); + +/* ========================== * + * Time + * ========================== */ + +P_DateTime P_W32_DateTimeFromWin32SystemTime(SYSTEMTIME st); + +/* ========================== * + * File system + * ========================== */ + +String P_W32_StringFromWin32Path(Arena *arena, wchar_t *src); + +/* ========================== * + * Window + * ========================== */ + +typedef enum P_W32_CursorFlag { + P_W32_CursorFlag_None = (0 << 0), + P_W32_CursorFlag_Position = (1 << 0), + P_W32_CursorFlag_Hide = (1 << 1), + P_W32_CursorFlag_Show = (1 << 2), + P_W32_CursorFlag_EnableClip = (1 << 3), + P_W32_CursorFlag_DisableClip = (1 << 4) +} P_W32_CursorFlag; + +typedef struct P_W32_Window P_W32_Window; +struct P_W32_Window { + u32 flags; + + HWND hwnd; + P_Counter ready_fence; + + u16 utf16_high_surrogate_last_input; + + P_Mutex settings_mutex; + P_WindowSettings settings; + + i32 monitor_width; + i32 monitor_height; + /* NOTE: width & height are unaffected by window minimization (they retain + * their pre-minimized values) */ + i32 x, y, width, height; + + /* FIXME: Use a cmd buffer for updating cursor (and maybe also settings). + * Current setup means cursor_set calls can be applied out of order */ + u32 cursor_set_flags; + V2 cursor_set_position; + Rect cursor_clip_bounds; + + Atomic32 topmost_toggles; + b32 is_topmost; + + P_Mutex event_arena_swp_mutex; + i32 current_event_arena_index; + Arena *event_arenas[2]; + + P_W32_Thread *window_thread; + + Atomic32 shutdown; + P_W32_Window *next_free; +}; + +void P_W32_ProcessWindowEvent(P_W32_Window *window, P_WindowEvent event); + +HWND P_W32_InitWindow(P_W32_Window *window); + +P_W32_ThreadDef(P_W32_WindowThreadEntryFunc, arg); + +P_W32_Window *P_W32_AllocWindow(void); + +void P_W32_ReleaseWindow(P_W32_Window *window); + +void P_W32_UpdateWindowFromSystem(P_W32_Window *window); + +void P_W32_UpdateWindowFromSettings(P_W32_Window *window, P_WindowSettings *settings); + +void P_W32_WakeWindow(P_W32_Window *window); + +LRESULT CALLBACK P_W32_Win32WindowProc(HWND hwnd, UINT msg, WPARAM wparam, LPARAM lparam); + +/* ========================== * + * Watch + * ========================== */ + +typedef struct P_W32_Watch P_W32_Watch; +struct P_W32_Watch { + HANDLE dir_handle; + HANDLE wake_handle; + P_W32_Watch *next_free; + u8 results_buff[KIBI(64)]; +}; + +/* ========================== * + * Address + * ========================== */ + +typedef struct P_W32_Address P_W32_Address; +struct P_W32_Address { + i32 size; + i32 family; + union { + struct sockaddr_storage sas; + struct sockaddr sa; + struct sockaddr_in sin; + struct sockaddr_in6 sin6; + }; +}; + +P_W32_Address P_W32_Win32AddressFromPlatformAddress(P_Address addr); + +/* If supplied address has ip INADDR_ANY (0), convert ip to localhost */ +P_W32_Address P_W32_ConvertAnyaddrToLocalhost(P_W32_Address addr); + +P_Address P_W32_PlatformAddressFromWin32Address(P_W32_Address ws_addr); + +/* ========================== * + * Sock + * ========================== */ + +typedef struct P_W32_Sock P_W32_Sock; +struct P_W32_Sock { + SOCKET sock; + P_W32_Sock *next_free; +}; + +/* ========================== * + * Entry + * ========================== */ + + +void P_W32_InitBtnTable(void); + +P_JobDef(P_W32_AppStartupJob, _); + +P_JobDef(P_W32_AppShutdownJob, _); + +/* ========================== * + * Global state + * ========================== */ + +typedef struct P_W32_Ctx P_W32_Ctx; +struct P_W32_Ctx { + SYSTEM_INFO info; + i64 timer_start_qpc; + i64 ns_per_qpc; + u32 main_thread_id; + Atomic32 shutdown; + + wchar_t cmdline_args_wstr[8192]; + + /* Application control flow */ + Atomic32 panicking; + wchar_t panic_wstr[4096]; + HANDLE panic_event; + HANDLE startup_end_event; + HANDLE exit_begin_event; + HANDLE exit_end_event; + + /* Key lookup table */ + P_Btn vk_btn_table[256]; + + /* Threads pool */ + P_Mutex threads_mutex; + Arena *threads_arena; + P_W32_Thread *first_thread; + P_W32_Thread *last_thread; + P_W32_Thread *first_free_thread; + + /* Watches pool */ + P_Mutex watches_mutex; + Arena *watches_arena; + P_W32_Watch *watches_first_free; + + /* Windows pool */ + WNDCLASSEXW window_class; + P_Mutex windows_mutex; + Arena *windows_arena; + P_W32_Window *first_free_window; + + /* Sockets pool */ + WSADATA wsa_data; + Arena *socks_arena; + P_Mutex socks_mutex; + P_W32_Sock *first_free_sock; + + /* Exit funcs */ + Atomic32 num_exit_funcs; + P_ExitFunc *exit_funcs[P_W32_MaxOnExitFuncs]; + + /* Scheduler */ + Atomic64Padded current_scheduler_cycle; + Atomic64Padded current_scheduler_cycle_period_ns; + + /* Fibers */ + P_W32_TicketMutex fibers_lock; + i16 num_fibers; + Arena *fiber_names_arena; + P_W32_Fiber fibers[MAX_FIBERS]; + + /* Wait lists */ + Atomic64Padded waiter_wake_gen; + P_W32_TicketMutex wait_lists_arena_lock; + Arena *wait_lists_arena; + + /* Wait tables */ + P_W32_WaitBin wait_addr_bins[P_W32_NumWaitAddrBins]; + P_W32_WaitBin wait_time_bins[P_W32_NumWaitTimeBins]; + + /* Job pools */ + P_W32_JobPool job_pools[P_Pool_Count]; +}; + +extern P_W32_Ctx P_W32_g_shared_ctx; diff --git a/src/playback/playback.h b/src/playback/playback.h index c3a7c2b0..9ed64c6f 100644 --- a/src/playback/playback.h +++ b/src/playback/playback.h @@ -2,7 +2,7 @@ #define PLAYBACK_H #include "../base/base.h" -#include "../sys/sys.h" +#include "../platform/platform.h" #include "../mixer/mixer.h" #include "playback_core.h" diff --git a/src/playback/playback_core_win32.c b/src/playback/playback_core_win32.c index 59484f70..23d3659f 100644 --- a/src/playback/playback_core_win32.c +++ b/src/playback/playback_core_win32.c @@ -8,10 +8,6 @@ #define COBJMACROS #define WIN32_LEAN_AND_MEAN #define UNICODE -#define WINVER 0x0A00 -#define _WIN32_WINNT 0x0A00 -#define NTDDI_WIN11_DT 0x0C0A0000 -#define NTDDI_VERSION 0x0A000000 #include #include #include @@ -39,7 +35,7 @@ GLOBAL struct { IAudioRenderClient *playback; WAVEFORMATEX *buffer_format; u32 buffer_frames; - struct snc_counter playback_job_counter; + P_Counter playback_job_counter; } G = ZI, DEBUG_ALIAS(G, G_playback_wasapi); /* ========================== * @@ -47,8 +43,8 @@ GLOBAL struct { * ========================== */ INTERNAL void wasapi_initialize(void); -INTERNAL SYS_EXIT_FUNC(playback_shutdown); -INTERNAL SYS_JOB_DEF(playback_job, _); +INTERNAL P_ExitFuncDef(playback_shutdown); +INTERNAL P_JobDef(playback_job, _); PB_StartupReceipt playback_startup(M_StartupReceipt *mixer_sr) { @@ -56,13 +52,13 @@ PB_StartupReceipt playback_startup(M_StartupReceipt *mixer_sr) (UNUSED)mixer_sr; wasapi_initialize(); /* Start playback job */ - sys_run(1, playback_job, 0, SYS_POOL_AUDIO, SYS_PRIORITY_HIGH, &G.playback_job_counter); - sys_on_exit(&playback_shutdown); + P_Run(1, playback_job, 0, P_Pool_Audio, P_Priority_High, &G.playback_job_counter); + P_OnExit(&playback_shutdown); return (PB_StartupReceipt) { 0 }; } -INTERNAL SYS_EXIT_FUNC(playback_shutdown) +INTERNAL P_ExitFuncDef(playback_shutdown) { __prof; atomic32_fetch_set(&G.shutdown, 1); @@ -219,7 +215,7 @@ INTERNAL void wasapi_update_end(struct wasapi_buffer *wspbuf, M_PcmF32 src) * Playback thread entry * ========================== */ -INTERNAL SYS_JOB_DEF(playback_job, _) +INTERNAL P_JobDef(playback_job, _) { __prof; (UNUSED)_; diff --git a/src/resource/resource.h b/src/resource/resource.h index cfa0df62..31faea71 100644 --- a/src/resource/resource.h +++ b/src/resource/resource.h @@ -2,7 +2,7 @@ #define RESOURCE_H #include "../base/base.h" -#include "../sys/sys.h" +#include "../platform/platform.h" #include "../tar/tar.h" #if RESOURCES_EMBEDDED diff --git a/src/resource/resource_core.c b/src/resource/resource_core.c index 843e919c..d7c3460b 100644 --- a/src/resource/resource_core.c +++ b/src/resource/resource_core.c @@ -24,13 +24,13 @@ R_StartupReceipt resource_startup(void) #if RESOURCES_EMBEDDED String embedded_data = inc_res_tar(); if (embedded_data.len <= 0) { - sys_panic(LIT("No embedded resources found")); + P_Panic(LIT("No embedded resources found")); } G.archive = tar_parse(G.arena, embedded_data, LIT("")); #else /* Ensure we have the right working directory */ - if (!sys_is_dir(LIT("res"))) { - sys_panic(LIT("Resource directory \"res\" not found. Make sure the executable is being launched from the correct working directory.")); + if (!P_IsDir(LIT("res"))) { + P_Panic(LIT("Resource directory \"res\" not found. Make sure the executable is being launched from the correct working directory.")); } #endif @@ -67,18 +67,18 @@ R_Resource resource_open(String name) path = STRING(path_text_len, path_text); } - struct sys_file file = sys_file_open_read_wait(path); - struct sys_file_map file_map = ZI; + P_File file = P_OpenFileReadWait(path); + P_FileMap file_map = ZI; String data = ZI; if (file.valid) { - file_map = sys_file_map_open_read(file); + file_map = P_OpenFileMap(file); if (file_map.valid) { - data = sys_file_map_data(file_map); + data = P_GetFileMapData(file_map); } else { - sys_file_map_close(file_map); + P_CloseFileMap(file_map); } } else { - sys_file_close(file); + P_CloseFIle(file); } res._exists = file.valid && file_map.valid; @@ -97,7 +97,7 @@ R_Resource resource_open(String name) #if !RESOURCES_EMBEDDED void resource_close(R_Resource *res_ptr) { - sys_file_map_close(res_ptr->_file_map); - sys_file_close(res_ptr->_file); + P_CloseFileMap(res_ptr->_file_map); + P_CloseFIle(res_ptr->_file); } #endif diff --git a/src/resource/resource_core.h b/src/resource/resource_core.h index ac97ae16..53f55fd9 100644 --- a/src/resource/resource_core.h +++ b/src/resource/resource_core.h @@ -10,8 +10,8 @@ struct R_Resource { #if RESOURCES_EMBEDDED String _name; #else - struct sys_file _file; - struct sys_file_map _file_map; + P_File _file; + P_FileMap _file_map; u8 _name_text[RESOURCE_NAME_LEN_MAX]; u8 _name_len; #endif diff --git a/src/settings/settings.h b/src/settings/settings.h index 8ed9a898..7c066ef6 100644 --- a/src/settings/settings.h +++ b/src/settings/settings.h @@ -2,7 +2,7 @@ #define SETTINGS_H #include "../base/base.h" -#include "../sys/sys.h" +#include "../platform/platform.h" #include "../json/json.h" #include "settings_core.h" diff --git a/src/settings/settings_core.c b/src/settings/settings_core.c index 76b0ed6e..b339f9e2 100644 --- a/src/settings/settings_core.c +++ b/src/settings/settings_core.c @@ -1,10 +1,10 @@ -String settings_serialize(Arena *arena, const struct sys_window_settings *settings) +String settings_serialize(Arena *arena, const P_WindowSettings *settings) { __prof; - String minimized = settings->flags & SYS_WINDOW_SETTINGS_FLAG_MINIMIZED ? LIT("true") : LIT("false"); - String maximized = settings->flags & SYS_WINDOW_SETTINGS_FLAG_MAXIMIZED ? LIT("true") : LIT("false"); - String fullscreen = settings->flags & SYS_WINDOW_SETTINGS_FLAG_FULLSCREEN ? LIT("true") : LIT("false"); + String minimized = settings->flags & P_WindowSettingsFlag_Minimized ? LIT("true") : LIT("false"); + String maximized = settings->flags & P_WindowSettingsFlag_Maximized ? LIT("true") : LIT("false"); + String fullscreen = settings->flags & P_WindowSettingsFlag_Fullscreen ? LIT("true") : LIT("false"); i32 x = settings->floating_x; i32 y = settings->floating_y; i32 width = settings->floating_width; @@ -37,7 +37,7 @@ String settings_serialize(Arena *arena, const struct sys_window_settings *settin return formatted; } -struct sys_window_settings *settings_deserialize(Arena *arena, String src, String *error_out) +P_WindowSettings *settings_deserialize(Arena *arena, String src, String *error_out) { __prof; TempArena scratch = scratch_begin(arena); @@ -45,7 +45,7 @@ struct sys_window_settings *settings_deserialize(Arena *arena, String src, Strin String error = ZI; JSON_Error json_error = ZI; - struct sys_window_settings *settings = arena_push(arena, struct sys_window_settings); + P_WindowSettings *settings = arena_push(arena, P_WindowSettings); JSON_Result parse_res = json_from_string(scratch.arena, src); if (parse_res.errors.count > 0) { @@ -80,7 +80,7 @@ struct sys_window_settings *settings_deserialize(Arena *arena, String src, Strin goto abort; } if (child->value.boolean) { - settings->flags |= SYS_WINDOW_SETTINGS_FLAG_MAXIMIZED; + settings->flags |= P_WindowSettingsFlag_Maximized; } found_maximized = 1; } else if (string_eq(key, LIT("fullscreen"))) { @@ -89,7 +89,7 @@ struct sys_window_settings *settings_deserialize(Arena *arena, String src, Strin goto abort; } if (child->value.boolean) { - settings->flags |= SYS_WINDOW_SETTINGS_FLAG_FULLSCREEN; + settings->flags |= P_WindowSettingsFlag_Fullscreen; } found_fullscreen = 1; } else if (string_eq(key, LIT("x"))) { diff --git a/src/settings/settings_core.h b/src/settings/settings_core.h index 014a7489..749b5318 100644 --- a/src/settings/settings_core.h +++ b/src/settings/settings_core.h @@ -1,3 +1,3 @@ -String settings_serialize(Arena *arena, const struct sys_window_settings *settings); +String settings_serialize(Arena *arena, const P_WindowSettings *settings); -struct sys_window_settings *settings_deserialize(Arena *arena, String src, String *error_out); +P_WindowSettings *settings_deserialize(Arena *arena, String src, String *error_out); diff --git a/src/sim/sim_core.c b/src/sim/sim_core.c index 3c71bace..a7c05b97 100644 --- a/src/sim/sim_core.c +++ b/src/sim/sim_core.c @@ -34,40 +34,40 @@ GLOBAL struct { Arena *nil_arena; - struct sim_client_store *nil_client_store; - struct sim_client *nil_client; - struct sim_snapshot *nil_snapshot; + ClientStore *nil_client_store; + Client *nil_client; + Snapshot *nil_snapshot; struct sim_ent *nil_ent; } G = ZI, DEBUG_ALIAS(G, G_sim); /* Accessed via `sim_client_store_nil()` */ -READONLY struct sim_client_store **_g_sim_client_store_nil = &G.nil_client_store; +READONLY ClientStore **_g_sim_client_store_nil = &G.nil_client_store; /* Accessed via `sim_client_nil()` */ -READONLY struct sim_client **_g_sim_client_nil = &G.nil_client; +READONLY Client **_g_sim_client_nil = &G.nil_client; /* Accessed via `sim_snapshot_nil()` */ -READONLY struct sim_snapshot **_g_sim_snapshot_nil = &G.nil_snapshot; +READONLY Snapshot **_g_sim_snapshot_nil = &G.nil_snapshot; /* Accessed via `sim_ent_nil()` */ READONLY struct sim_ent **_g_sim_ent_nil = &G.nil_ent; -struct sim_startup_receipt sim_startup(void) +SimStartupReceipt sim_startup(void) { __prof; G.nil_arena = arena_alloc(GIBI(1)); /* Nil client store */ - G.nil_client_store = arena_push(G.nil_arena, struct sim_client_store); + G.nil_client_store = arena_push(G.nil_arena, ClientStore); G.nil_client_store->valid = 0; /* Nil client */ - G.nil_client = arena_push(G.nil_arena, struct sim_client); + G.nil_client = arena_push(G.nil_arena, Client); G.nil_client->valid = 0; G.nil_client->store = sim_client_store_nil(); /* Nil snapshot */ - G.nil_snapshot = arena_push(G.nil_arena, struct sim_snapshot); + G.nil_snapshot = arena_push(G.nil_arena, Snapshot); G.nil_snapshot->valid = 0; G.nil_snapshot->client = sim_client_nil(); @@ -87,35 +87,35 @@ struct sim_startup_receipt sim_startup(void) /* Lock nil arena */ arena_set_readonly(G.nil_arena); - return (struct sim_startup_receipt) { 0 }; + return (SimStartupReceipt) { 0 }; } /* ========================== * * Client store alloc * ========================== */ -struct sim_client_store *sim_client_store_alloc(void) +ClientStore *sim_client_store_alloc(void) { __prof; - struct sim_client_store *store; + ClientStore *store; { Arena *arena = arena_alloc(GIBI(64)); - store = arena_push(arena, struct sim_client_store); + store = arena_push(arena, ClientStore); store->arena = arena; } store->valid = 1; store->num_client_lookup_bins = CLIENT_LOOKUP_BINS; - store->client_lookup_bins = arena_push_array(store->arena, struct sim_client_lookup_bin, store->num_client_lookup_bins); + store->client_lookup_bins = arena_push_array(store->arena, ClientLookupBin, store->num_client_lookup_bins); store->clients_arena = arena_alloc(GIBI(64)); - store->clients = arena_push_dry(store->clients_arena, struct sim_client); + store->clients = arena_push_dry(store->clients_arena, Client); return store; } -void sim_client_store_release(struct sim_client_store *store) +void sim_client_store_release(ClientStore *store) { __prof; for (u64 i = 0; i < store->num_clients_reserved; ++i) { - struct sim_client *client = &store->clients[i]; + Client *client = &store->clients[i]; if (client->valid) { sim_client_release(client); } @@ -128,17 +128,17 @@ void sim_client_store_release(struct sim_client_store *store) * Client alloc * ========================== */ -struct sim_client *sim_client_alloc(struct sim_client_store *store) +Client *sim_client_alloc(ClientStore *store) { - struct sim_client_handle handle = ZI; - struct sim_client *client = sim_client_from_handle(store, store->first_free_client); + ClientHandle handle = ZI; + Client *client = sim_client_from_handle(store, store->first_free_client); if (client->valid) { store->first_free_client = client->next_free; handle = client->handle; ++handle.gen; } else { - client = arena_push_no_zero(store->clients_arena, struct sim_client); + client = arena_push_no_zero(store->clients_arena, Client); handle.gen = 1; handle.idx = store->num_clients_reserved; ++store->num_clients_reserved; @@ -151,19 +151,19 @@ struct sim_client *sim_client_alloc(struct sim_client_store *store) client->snapshots_arena = arena_alloc(GIBI(8)); client->num_snapshot_lookup_bins = TICK_LOOKUP_BINS; - client->snapshot_lookup_bins = arena_push_array(client->snapshots_arena, struct sim_snapshot_lookup_bin, client->num_snapshot_lookup_bins); + client->snapshot_lookup_bins = arena_push_array(client->snapshots_arena, SnapshotLookupBin, client->num_snapshot_lookup_bins); return client; } -void sim_client_release(struct sim_client *client) +void sim_client_release(Client *client) { /* Release internal snapshot memory */ for (u64 i = 0; i < client->num_snapshot_lookup_bins; ++i) { - struct sim_snapshot_lookup_bin *bin = &client->snapshot_lookup_bins[i]; - struct sim_snapshot *ss = bin->first; + SnapshotLookupBin *bin = &client->snapshot_lookup_bins[i]; + Snapshot *ss = bin->first; while (ss) { - struct sim_snapshot *next = ss->next_in_bin; + Snapshot *next = ss->next_in_bin; arena_release(ss->ents_arena); arena_release(ss->arena); ss = next; @@ -174,7 +174,7 @@ void sim_client_release(struct sim_client *client) sim_client_set_channel_id(client, HOST_CHANNEL_ID_NIL); /* Release client */ - struct sim_client_store *store = client->store; + ClientStore *store = client->store; client->valid = 0; client->next_free = store->first_free_client; store->first_free_client = client->handle; @@ -192,17 +192,17 @@ INTERNAL u64 hash_from_channel_id(N_ChannelId channel_id) return hash_fnv64(HASH_FNV64_BASIS, STRING_FROM_STRUCT(&channel_id)); } -void sim_client_set_channel_id(struct sim_client *client, N_ChannelId channel_id) +void sim_client_set_channel_id(Client *client, N_ChannelId channel_id) { - struct sim_client_store *store = client->store; + ClientStore *store = client->store; N_ChannelId old_channel_id = client->channel_id; /* Remove old channel id from channel lookup */ if (!host_channel_id_is_nil(old_channel_id)) { u64 bin_index = client->channel_hash % store->num_client_lookup_bins; - struct sim_client_lookup_bin *bin = &store->client_lookup_bins[bin_index]; - struct sim_client *prev = sim_client_from_handle(store, client->prev_in_bin); - struct sim_client *next = sim_client_from_handle(store, client->next_in_bin); + ClientLookupBin *bin = &store->client_lookup_bins[bin_index]; + Client *prev = sim_client_from_handle(store, client->prev_in_bin); + Client *next = sim_client_from_handle(store, client->next_in_bin); if (prev->valid) { prev->next_in_bin = next->handle; } else { @@ -222,9 +222,9 @@ void sim_client_set_channel_id(struct sim_client *client, N_ChannelId channel_id client->channel_hash = channel_hash; if (!host_channel_id_is_nil(channel_id)) { u64 bin_index = channel_hash % store->num_client_lookup_bins; - struct sim_client_lookup_bin *bin = &store->client_lookup_bins[bin_index]; + ClientLookupBin *bin = &store->client_lookup_bins[bin_index]; { - struct sim_client *prev_in_bin = sim_client_from_handle(store, bin->last); + Client *prev_in_bin = sim_client_from_handle(store, bin->last); if (prev_in_bin->valid) { prev_in_bin->next_in_bin = client->handle; client->prev_in_bin = prev_in_bin->handle; @@ -236,13 +236,13 @@ void sim_client_set_channel_id(struct sim_client *client, N_ChannelId channel_id } } -struct sim_client *sim_client_from_channel_id(struct sim_client_store *store, N_ChannelId channel_id) +Client *sim_client_from_channel_id(ClientStore *store, N_ChannelId channel_id) { - struct sim_client *res = sim_client_nil(); + Client *res = sim_client_nil(); u64 channel_hash = hash_from_channel_id(channel_id); u64 bin_index = channel_hash % store->num_client_lookup_bins; - struct sim_client_lookup_bin *bin = &store->client_lookup_bins[bin_index]; - for (struct sim_client *client = sim_client_from_handle(store, bin->first); client->valid; client = sim_client_from_handle(store, client->next_in_bin)) { + ClientLookupBin *bin = &store->client_lookup_bins[bin_index]; + for (Client *client = sim_client_from_handle(store, bin->first); client->valid; client = sim_client_from_handle(store, client->next_in_bin)) { if (client->channel_hash == channel_hash) { res = client; break; @@ -251,10 +251,10 @@ struct sim_client *sim_client_from_channel_id(struct sim_client_store *store, N_ return res; } -struct sim_client *sim_client_from_handle(struct sim_client_store *store, struct sim_client_handle handle) +Client *sim_client_from_handle(ClientStore *store, ClientHandle handle) { if (handle.gen != 0 && handle.idx < store->num_clients_reserved) { - struct sim_client *client = &store->clients[handle.idx]; + Client *client = &store->clients[handle.idx]; if (client->handle.gen == handle.gen) { return client; } @@ -267,13 +267,13 @@ struct sim_client *sim_client_from_handle(struct sim_client_store *store, struct * ========================== */ /* Produces a new snapshot at `tick` with data copied from `src` snapshot. */ -struct sim_snapshot *sim_snapshot_alloc(struct sim_client *client, struct sim_snapshot *src, u64 tick) +Snapshot *sim_snapshot_alloc(Client *client, Snapshot *src, u64 tick) { if (tick == 0) { return sim_snapshot_nil(); } - struct sim_snapshot *ss; + Snapshot *ss; { Arena *arena = ZI; Arena *ents_arena = 0; @@ -291,7 +291,7 @@ struct sim_snapshot *sim_snapshot_alloc(struct sim_client *client, struct sim_sn } } arena_reset(arena); - ss = arena_push(arena, struct sim_snapshot); + ss = arena_push(arena, Snapshot); ss->arena = arena; ss->ents_arena = ents_arena; @@ -360,7 +360,7 @@ struct sim_snapshot *sim_snapshot_alloc(struct sim_client *client, struct sim_sn /* Release duplicate tick if it exists */ { - struct sim_snapshot *existing = sim_snapshot_from_tick(client, tick); + Snapshot *existing = sim_snapshot_from_tick(client, tick); if (existing->valid) { sim_snapshot_release(existing); } @@ -368,7 +368,7 @@ struct sim_snapshot *sim_snapshot_alloc(struct sim_client *client, struct sim_sn /* Linear search to insert snapshot in tick order */ { - struct sim_snapshot *prev = sim_snapshot_from_tick(client, client->last_tick); + Snapshot *prev = sim_snapshot_from_tick(client, client->last_tick); while (prev->valid) { if (prev->tick < tick) { break; @@ -376,7 +376,7 @@ struct sim_snapshot *sim_snapshot_alloc(struct sim_client *client, struct sim_sn prev = sim_snapshot_from_tick(client, prev->prev_tick); } if (prev->valid) { - struct sim_snapshot *next = sim_snapshot_from_tick(client, prev->next_tick); + Snapshot *next = sim_snapshot_from_tick(client, prev->next_tick); if (next->valid) { next->prev_tick = tick; } else { @@ -386,7 +386,7 @@ struct sim_snapshot *sim_snapshot_alloc(struct sim_client *client, struct sim_sn ss->prev_tick = prev->tick; prev->next_tick = ss->tick; } else { - struct sim_snapshot *first = sim_snapshot_from_tick(client, client->first_tick); + Snapshot *first = sim_snapshot_from_tick(client, client->first_tick); if (first->valid) { ss->next_tick = first->tick; first->prev_tick = tick; @@ -401,7 +401,7 @@ struct sim_snapshot *sim_snapshot_alloc(struct sim_client *client, struct sim_sn /* Insert into lookup */ { u64 bin_index = tick % client->num_snapshot_lookup_bins; - struct sim_snapshot_lookup_bin *bin = &client->snapshot_lookup_bins[bin_index]; + SnapshotLookupBin *bin = &client->snapshot_lookup_bins[bin_index]; if (bin->last) { bin->last->next_in_bin = ss; ss->prev_in_bin = bin->last; @@ -414,16 +414,16 @@ struct sim_snapshot *sim_snapshot_alloc(struct sim_client *client, struct sim_sn return ss; } -void sim_snapshot_release(struct sim_snapshot *ss) +void sim_snapshot_release(Snapshot *ss) { - struct sim_client *client = ss->client; + Client *client = ss->client; /* Remove from lookup */ { u64 bin_index = ss->tick % client->num_snapshot_lookup_bins; - struct sim_snapshot_lookup_bin *bin = &client->snapshot_lookup_bins[bin_index]; - struct sim_snapshot *prev = ss->prev_in_bin; - struct sim_snapshot *next = ss->next_in_bin; + SnapshotLookupBin *bin = &client->snapshot_lookup_bins[bin_index]; + Snapshot *prev = ss->prev_in_bin; + Snapshot *next = ss->next_in_bin; if (prev) { prev->next_in_bin = next; } else { @@ -438,8 +438,8 @@ void sim_snapshot_release(struct sim_snapshot *ss) /* Remove from snapshot list */ { - struct sim_snapshot *prev = sim_snapshot_from_tick(client, ss->prev_tick); - struct sim_snapshot *next = sim_snapshot_from_tick(client, ss->next_tick); + Snapshot *prev = sim_snapshot_from_tick(client, ss->prev_tick); + Snapshot *next = sim_snapshot_from_tick(client, ss->next_tick); if (prev->valid) { prev->next_tick = next->tick; } else { @@ -459,7 +459,7 @@ void sim_snapshot_release(struct sim_snapshot *ss) } /* Release all snapshots for client with tick in range [start, end] */ -void sim_snapshot_release_ticks_in_range(struct sim_client *client, u64 start, u64 end) +void sim_snapshot_release_ticks_in_range(Client *client, u64 start, u64 end) { if (start > end) { u64 swp = start; @@ -467,7 +467,7 @@ void sim_snapshot_release_ticks_in_range(struct sim_client *client, u64 start, u end = swp; } - struct sim_snapshot *ss = sim_snapshot_from_tick(client, client->first_tick); + Snapshot *ss = sim_snapshot_from_tick(client, client->first_tick); while (ss->valid) { u64 tick = ss->tick; u64 next_tick = ss->next_tick; @@ -486,13 +486,13 @@ void sim_snapshot_release_ticks_in_range(struct sim_client *client, u64 start, u * Snapshot lookup * ========================== */ -struct sim_snapshot *sim_snapshot_from_tick(struct sim_client *client, u64 tick) +Snapshot *sim_snapshot_from_tick(Client *client, u64 tick) { - struct sim_snapshot *ss = sim_snapshot_nil(); + Snapshot *ss = sim_snapshot_nil(); if (tick > 0) { u64 bin_index = tick % client->num_snapshot_lookup_bins; - struct sim_snapshot_lookup_bin *bin = &client->snapshot_lookup_bins[bin_index]; - for (struct sim_snapshot *search = bin->first; search; search = search->next_in_bin) { + SnapshotLookupBin *bin = &client->snapshot_lookup_bins[bin_index]; + for (Snapshot *search = bin->first; search; search = search->next_in_bin) { if (search->tick == tick) { ss = search; break; @@ -503,9 +503,9 @@ struct sim_snapshot *sim_snapshot_from_tick(struct sim_client *client, u64 tick) } /* Returns the snapshot at nearest valid tick <= supplied tick */ -struct sim_snapshot *sim_snapshot_from_closest_tick_lte(struct sim_client *client, u64 tick) +Snapshot *sim_snapshot_from_closest_tick_lte(Client *client, u64 tick) { - struct sim_snapshot *ss = sim_snapshot_from_tick(client, tick); + Snapshot *ss = sim_snapshot_from_tick(client, tick); if (!ss->valid) { /* Degenerate to linear search */ ss = sim_snapshot_from_tick(client, client->last_tick); @@ -520,9 +520,9 @@ struct sim_snapshot *sim_snapshot_from_closest_tick_lte(struct sim_client *clien } /* Returns the snapshot at nearest valid tick >= supplied tick */ -struct sim_snapshot *sim_snapshot_from_closest_tick_gte(struct sim_client *client, u64 tick) +Snapshot *sim_snapshot_from_closest_tick_gte(Client *client, u64 tick) { - struct sim_snapshot *ss = sim_snapshot_from_tick(client, tick); + Snapshot *ss = sim_snapshot_from_tick(client, tick); if (!ss->valid) { /* Degenerate to linear search */ ss = sim_snapshot_from_tick(client, client->first_tick); @@ -589,11 +589,11 @@ V2i32 sim_tile_chunk_index_from_world_tile_index(V2i32 world_tile_index) return res; } -void sim_snapshot_set_tile(struct sim_snapshot *ss, V2i32 world_tile_index, enum sim_tile_kind tile_kind) +void sim_snapshot_set_tile(Snapshot *ss, V2i32 world_tile_index, TileKind tile_kind) { V2i32 chunk_index = sim_tile_chunk_index_from_world_tile_index(world_tile_index); - struct sim_ent_id chunk_id = sim_ent_tile_chunk_id_from_tile_chunk_index(chunk_index); + EntId chunk_id = sim_ent_tile_chunk_id_from_tile_chunk_index(chunk_index); struct sim_ent *chunk_ent = sim_ent_from_id(ss, chunk_id); if (!chunk_ent->valid) { struct sim_ent *root = sim_ent_from_id(ss, SIM_ENT_ROOT_ID); @@ -610,14 +610,14 @@ void sim_snapshot_set_tile(struct sim_snapshot *ss, V2i32 world_tile_index, enum * Snapshot lerp * ========================== */ -struct sim_snapshot *sim_snapshot_alloc_from_lerp(struct sim_client *client, struct sim_snapshot *ss0, struct sim_snapshot *ss1, f64 blend) +Snapshot *sim_snapshot_alloc_from_lerp(Client *client, Snapshot *ss0, Snapshot *ss1, f64 blend) { __prof; /* New snapshot will be allocated with same tick as ss0 or ss1, so the result should go into a different client */ ASSERT(ss0->client != client && ss1->client != client); - struct sim_snapshot *ss; + Snapshot *ss; b32 should_blend = 1; if (ss0->continuity_gen == ss1->continuity_gen && 0 < blend && blend < 1) { ss = sim_snapshot_alloc(client, ss0, ss0->tick); @@ -661,7 +661,7 @@ struct sim_snapshot *sim_snapshot_alloc_from_lerp(struct sim_client *client, str * ========================== */ /* Syncs entity data between snapshots */ -void sim_snapshot_sync_ents(struct sim_snapshot *local_ss, struct sim_snapshot *remote_ss, struct sim_ent_id remote_player, u32 sync_flags) +void sim_snapshot_sync_ents(Snapshot *local_ss, Snapshot *remote_ss, EntId remote_player, u32 sync_flags) { __prof; @@ -720,7 +720,7 @@ void sim_snapshot_sync_ents(struct sim_snapshot *local_ss, struct sim_snapshot * * Snapshot encode * ========================== */ -void sim_snapshot_encode(BitbuffWriter *bw, struct sim_client *receiver, struct sim_snapshot *ss0, struct sim_snapshot *ss1) +void sim_snapshot_encode(BitbuffWriter *bw, Client *receiver, Snapshot *ss0, Snapshot *ss1) { __prof; @@ -789,7 +789,7 @@ void sim_snapshot_encode(BitbuffWriter *bw, struct sim_client *receiver, struct * Snapshot decode * ========================== */ -void sim_snapshot_decode(BitbuffReader *br, struct sim_snapshot *ss) +void sim_snapshot_decode(BitbuffReader *br, Snapshot *ss) { __prof; @@ -801,7 +801,7 @@ void sim_snapshot_decode(BitbuffReader *br, struct sim_snapshot *ss) ss->continuity_gen = br_read_uv(br); ss->phys_iteration = br_read_uv(br); - ss->local_player = (struct sim_ent_id) { .uid = br_read_uid(br) }; + ss->local_player = (EntId) { .uid = br_read_uid(br) }; /* Id bins */ /* TODO: Don't decode these, determine them implicitly from decoded ents */ @@ -869,7 +869,7 @@ void sim_snapshot_decode(BitbuffReader *br, struct sim_snapshot *ss) * Snapshot encode * ========================== */ -void sim_snapshot_encode(BitbuffWriter *bw, struct sim_client *receiver, struct sim_snapshot *ss0, struct sim_snapshot *ss1) +void sim_snapshot_encode(BitbuffWriter *bw, Client *receiver, Snapshot *ss0, Snapshot *ss1) { __prof; @@ -936,7 +936,7 @@ struct sim_ent_decode_queue { struct sim_ent_decode_node *last; }; -void sim_snapshot_decode(BitbuffReader *br, struct sim_snapshot *ss) +void sim_snapshot_decode(BitbuffReader *br, Snapshot *ss) { __prof; TempArena scratch = scratch_begin_no_conflict(); @@ -947,7 +947,7 @@ void sim_snapshot_decode(BitbuffReader *br, struct sim_snapshot *ss) ss->continuity_gen = br_read_uv(br); ss->phys_iteration = br_read_uv(br); - ss->local_player = (struct sim_ent_id) { .uid = br_read_uid(br) }; + ss->local_player = (EntId) { .uid = br_read_uid(br) }; #if 1 @@ -978,7 +978,7 @@ void sim_snapshot_decode(BitbuffReader *br, struct sim_snapshot *ss) b32 released = 0; u32 alloc_parent_index = ZI; - struct sim_ent_id alloc_ent_id = ZI; + EntId alloc_ent_id = ZI; if (allocation_changed) { released = br_read_bit(br); if (released) { diff --git a/src/sim/sim_core.h b/src/sim/sim_core.h index 804bfa81..ddc306bc 100644 --- a/src/sim/sim_core.h +++ b/src/sim/sim_core.h @@ -1,4 +1,4 @@ -#define SIM_CLIENT_NIL_HANDLE ((struct sim_client_handle) { .gen = 0, .idx = 0 }) +#define SIM_CLIENT_NIL_HANDLE ((ClientHandle) { .gen = 0, .idx = 0 }) /* Absolute layers */ #define SIM_LAYER_FLOOR_DECALS (-300) @@ -11,11 +11,13 @@ #define SIM_LAYER_RELATIVE_DEFAULT (0) #define SIM_LAYER_RELATIVE_WEAPON (1) -struct sim_ent_id { +typedef struct EntId EntId; +struct EntId { UID uid; }; -struct sim_client_handle { +typedef struct ClientHandle ClientHandle; +struct ClientHandle { u32 idx; u32 gen; }; @@ -24,58 +26,63 @@ struct sim_client_handle { * Startup * ========================== */ -struct sim_startup_receipt { i32 _; }; -struct sim_startup_receipt sim_startup(void); +typedef struct SimStartupReceipt SimStartupReceipt; +struct SimStartupReceipt { i32 _; }; +SimStartupReceipt sim_startup(void); /* ========================== * * Client store * ========================== */ -struct sim_client_lookup_bin { - struct sim_client_handle first; - struct sim_client_handle last; +typedef struct ClientLookupBin ClientLookupBin; +struct ClientLookupBin { + ClientHandle first; + ClientHandle last; }; -struct sim_client_store { +typedef struct Client Client; +typedef struct ClientStore ClientStore; +struct ClientStore { b32 valid; Arena *arena; /* Client lookup */ - struct sim_client_lookup_bin *client_lookup_bins; + ClientLookupBin *client_lookup_bins; u64 num_client_lookup_bins; /* Clients */ Arena *clients_arena; - struct sim_client *clients; - struct sim_client_handle first_free_client; + Client *clients; + ClientHandle first_free_client; u64 num_clients_allocated; u64 num_clients_reserved; }; -INLINE struct sim_client_store *sim_client_store_nil(void) +INLINE ClientStore *sim_client_store_nil(void) { - extern READONLY struct sim_client_store **_g_sim_client_store_nil; + extern READONLY ClientStore **_g_sim_client_store_nil; return *_g_sim_client_store_nil; } -struct sim_client_store *sim_client_store_alloc(void); -void sim_client_store_release(struct sim_client_store *store); +ClientStore *sim_client_store_alloc(void); +void sim_client_store_release(ClientStore *store); /* ========================== * * Client * ========================== */ -struct sim_snapshot; - -struct sim_snapshot_lookup_bin { - struct sim_snapshot *first; - struct sim_snapshot *last; +typedef struct Snapshot Snapshot; +typedef struct SnapshotLookupBin SnapshotLookupBin; +struct SnapshotLookupBin { + Snapshot *first; + Snapshot *last; }; -struct sim_client { +typedef struct Client Client; +struct Client { b32 valid; - struct sim_client_handle handle; - struct sim_client_store *store; + ClientHandle handle; + ClientStore *store; Arena *snapshots_arena; @@ -85,12 +92,12 @@ struct sim_client { N_ChannelId channel_id; u64 channel_hash; - struct sim_client_handle next_free; - struct sim_client_handle next_in_bin; - struct sim_client_handle prev_in_bin; + ClientHandle next_free; + ClientHandle next_in_bin; + ClientHandle prev_in_bin; /* The client's player entity id in the master sim (if relevant) */ - struct sim_ent_id player_id; + EntId player_id; /* This is the highest confirmed tick of ours that we know this client has received */ u64 ack; @@ -107,40 +114,40 @@ struct sim_client { u64 first_tick; u64 last_tick; u64 num_ticks; - struct sim_snapshot *first_free_snapshot; + Snapshot *first_free_snapshot; /* Tick -> snapshot lookup */ u64 num_snapshot_lookup_bins; - struct sim_snapshot_lookup_bin *snapshot_lookup_bins; + SnapshotLookupBin *snapshot_lookup_bins; }; -INLINE struct sim_client *sim_client_nil(void) +INLINE Client *sim_client_nil(void) { - extern READONLY struct sim_client **_g_sim_client_nil; + extern READONLY Client **_g_sim_client_nil; return *_g_sim_client_nil; } -INLINE b32 sim_client_handle_eq(struct sim_client_handle a, struct sim_client_handle b) +INLINE b32 sim_client_handle_eq(ClientHandle a, ClientHandle b) { return a.gen == b.gen && a.idx == b.idx; } -struct sim_client *sim_client_alloc(struct sim_client_store *store); -void sim_client_release(struct sim_client *client); +Client *sim_client_alloc(ClientStore *store); +void sim_client_release(Client *client); -struct sim_client *sim_client_from_channel_id(struct sim_client_store *store, N_ChannelId channel_id); -void sim_client_set_channel_id(struct sim_client *client, N_ChannelId channel_id); -struct sim_client *sim_client_from_handle(struct sim_client_store *store, struct sim_client_handle handle); +Client *sim_client_from_channel_id(ClientStore *store, N_ChannelId channel_id); +void sim_client_set_channel_id(Client *client, N_ChannelId channel_id); +Client *sim_client_from_handle(ClientStore *store, ClientHandle handle); /* ========================== * * Snapshot * ========================== */ -enum sim_sync_flag { +typedef enum SyncFlag { SIM_SYNC_FLAG_NOSYNC_PREDICTABLES = 1 << 0 -}; +} SyncFlag; -enum sim_control_flag { +typedef enum ControlFlag { SIM_CONTROL_FLAG_FIRE = 1 << 0, SIM_CONTROL_FLAG_FIRE_ALT = 1 << 1, @@ -156,39 +163,42 @@ enum sim_control_flag { SIM_CONTROL_FLAG_TILE_TEST = 1 << 10, SIM_CONTROL_FLAG_EXPLODE_TEST = 1 << 11, SIM_CONTROL_FLAG_TELEPORT_TEST = 1 << 12, -}; +} ControlFlag; -struct sim_control { +typedef struct ControlData ControlData; +struct ControlData { V2 move; /* Movement direction vector (speed of 0 -> 1) */ V2 focus; /* Focus direction vector (where does the controller want to look) */ V2 dbg_cursor; /* Where is the user's cursor in the world (used for things like editing the world) */ u32 flags; }; -enum sim_cmd_kind { +typedef enum CmdKind { SIM_CMD_KIND_INVALID, SIM_CMD_KIND_CONTROL, SIM_CMD_KIND_CHAT -}; +} CmdKind; -enum sim_tile_kind { + +typedef enum TileKind { SIM_TILE_KIND_NONE, SIM_TILE_KIND_WALL, NUM_SIM_TILE_KINDS -}; +} TileKind; STATIC_ASSERT(NUM_SIM_TILE_KINDS < 256); /* Tile kind must fit in 8 bits */ struct sim_ent_bin; -struct sim_snapshot { +typedef struct Snapshot Snapshot; +struct Snapshot { b32 valid; u64 tick; - struct sim_client *client; - struct sim_snapshot *next_free; - struct sim_snapshot *next_in_bin; - struct sim_snapshot *prev_in_bin; + Client *client; + Snapshot *next_free; + Snapshot *next_in_bin; + Snapshot *prev_in_bin; u64 prev_tick; u64 next_tick; @@ -205,7 +215,7 @@ struct sim_snapshot { u64 phys_iteration; /* The id of the receiver's player in the snapshot */ - struct sim_ent_id local_player; + EntId local_player; /* Id lookup */ struct sim_ent_bin *id_bins; @@ -219,21 +229,21 @@ struct sim_snapshot { u32 num_ents_reserved; }; -INLINE struct sim_snapshot *sim_snapshot_nil(void) +INLINE Snapshot *sim_snapshot_nil(void) { - extern READONLY struct sim_snapshot **_g_sim_snapshot_nil; + extern READONLY Snapshot **_g_sim_snapshot_nil; return *_g_sim_snapshot_nil; } /* Alloc */ -struct sim_snapshot *sim_snapshot_alloc(struct sim_client *client, struct sim_snapshot *src, u64 tick); -void sim_snapshot_release(struct sim_snapshot *sim_snapshot); -void sim_snapshot_release_ticks_in_range(struct sim_client *client, u64 start, u64 end); +Snapshot *sim_snapshot_alloc(Client *client, Snapshot *src, u64 tick); +void sim_snapshot_release(Snapshot *sim_snapshot); +void sim_snapshot_release_ticks_in_range(Client *client, u64 start, u64 end); /* Lookup */ -struct sim_snapshot *sim_snapshot_from_tick(struct sim_client *client, u64 tick); -struct sim_snapshot *sim_snapshot_from_closest_tick_lte(struct sim_client *client, u64 tick); -struct sim_snapshot *sim_snapshot_from_closest_tick_gte(struct sim_client *client, u64 tick); +Snapshot *sim_snapshot_from_tick(Client *client, u64 tick); +Snapshot *sim_snapshot_from_closest_tick_lte(Client *client, u64 tick); +Snapshot *sim_snapshot_from_closest_tick_gte(Client *client, u64 tick); /* Tile */ V2i32 sim_world_tile_index_from_pos(V2 pos); @@ -241,14 +251,14 @@ V2 sim_pos_from_world_tile_index(V2i32 world_tile_index); V2i32 sim_local_tile_index_from_world_tile_index(V2i32 world_tile_index); V2i32 sim_world_tile_index_from_local_tile_index(V2i32 tile_chunk_index, V2i32 local_tile_index); V2i32 sim_tile_chunk_index_from_world_tile_index(V2i32 world_tile_index); -void sim_snapshot_set_tile(struct sim_snapshot *ss, V2i32 world_tile_index, enum sim_tile_kind tile_kind); +void sim_snapshot_set_tile(Snapshot *ss, V2i32 world_tile_index, TileKind tile_kind); /* Lerp */ -struct sim_snapshot *sim_snapshot_alloc_from_lerp(struct sim_client *client, struct sim_snapshot *ss0, struct sim_snapshot *ss1, f64 blend); +Snapshot *sim_snapshot_alloc_from_lerp(Client *client, Snapshot *ss0, Snapshot *ss1, f64 blend); /* Sync */ -void sim_snapshot_sync_ents(struct sim_snapshot *local_ss, struct sim_snapshot *remote_ss, struct sim_ent_id remote_player, u32 sync_flags); +void sim_snapshot_sync_ents(Snapshot *local_ss, Snapshot *remote_ss, EntId remote_player, u32 sync_flags); /* Encode / decode */ -void sim_snapshot_encode(BitbuffWriter *bw, struct sim_client *receiver, struct sim_snapshot *ss0, struct sim_snapshot *ss1); -void sim_snapshot_decode(BitbuffReader *br, struct sim_snapshot *ss); +void sim_snapshot_encode(BitbuffWriter *bw, Client *receiver, Snapshot *ss0, Snapshot *ss1); +void sim_snapshot_decode(BitbuffReader *br, Snapshot *ss); diff --git a/src/sim/sim_ent.c b/src/sim/sim_ent.c index 3ee218eb..52a6182c 100644 --- a/src/sim/sim_ent.c +++ b/src/sim/sim_ent.c @@ -3,12 +3,12 @@ #define SIM_ENT_COLLISION_DEBUG_BASIS_UID (MakeUID(0x302c01182013bb02, 0x570bd270399d11a5)) #define SIM_ENT_TILE_CHUNK_BASIS_UID (MakeUID(0x3ce42de071dd226b, 0x9b566f7df30c813a)) -INTERNAL u32 index_from_ent(struct sim_snapshot *ss, struct sim_ent *ent) +INTERNAL u32 index_from_ent(Snapshot *ss, struct sim_ent *ent) { return ent - ss->ents; } -INTERNAL struct sim_ent *ent_from_index(struct sim_snapshot *ss, u32 index) +INTERNAL struct sim_ent *ent_from_index(Snapshot *ss, u32 index) { if (index > 0 && index < ss->num_ents_reserved) { return &ss->ents[index]; @@ -21,7 +21,7 @@ INTERNAL struct sim_ent *ent_from_index(struct sim_snapshot *ss, u32 index) * Ent allocation * ========================== */ -struct sim_ent *sim_ent_alloc_raw(struct sim_snapshot *ss, struct sim_ent *parent, struct sim_ent_id id) +struct sim_ent *sim_ent_alloc_raw(Snapshot *ss, struct sim_ent *parent, EntId id) { ASSERT(parent->valid); ASSERT(ss->valid); @@ -52,15 +52,15 @@ struct sim_ent *sim_ent_alloc_raw(struct sim_snapshot *ss, struct sim_ent *paren /* Allocates a new entity that will not sync */ struct sim_ent *sim_ent_alloc_local(struct sim_ent *parent) { - struct sim_snapshot *ss = parent->ss; + Snapshot *ss = parent->ss; struct sim_ent *e = sim_ent_alloc_raw(ss, parent, sim_ent_random_id()); e->owner = ss->local_player; return e; } -struct sim_ent *sim_ent_alloc_local_with_id(struct sim_ent *parent, struct sim_ent_id id) +struct sim_ent *sim_ent_alloc_local_with_id(struct sim_ent *parent, EntId id) { - struct sim_snapshot *ss = parent->ss; + Snapshot *ss = parent->ss; struct sim_ent *e = sim_ent_alloc_raw(ss, parent, id); e->owner = ss->local_player; return e; @@ -69,16 +69,16 @@ struct sim_ent *sim_ent_alloc_local_with_id(struct sim_ent *parent, struct sim_e /* Allocates a new entity to be synced to clients */ struct sim_ent *sim_ent_alloc_sync_src(struct sim_ent *parent) { - struct sim_snapshot *ss = parent->ss; + Snapshot *ss = parent->ss; struct sim_ent *e = sim_ent_alloc_raw(ss, parent, sim_ent_random_id()); sim_ent_enable_prop(e, SEPROP_SYNC_SRC); e->owner = ss->local_player; return e; } -struct sim_ent *sim_ent_alloc_sync_src_with_id(struct sim_ent *parent, struct sim_ent_id id) +struct sim_ent *sim_ent_alloc_sync_src_with_id(struct sim_ent *parent, EntId id) { - struct sim_snapshot *ss = parent->ss; + Snapshot *ss = parent->ss; struct sim_ent *e = sim_ent_alloc_raw(ss, parent, id); sim_ent_enable_prop(e, SEPROP_SYNC_SRC); e->owner = ss->local_player; @@ -86,9 +86,9 @@ struct sim_ent *sim_ent_alloc_sync_src_with_id(struct sim_ent *parent, struct si } /* Allocates a new entity that will sync with incoming net src ents containing id, and coming from the specified owner */ -struct sim_ent *sim_ent_alloc_sync_dst(struct sim_ent *parent, struct sim_ent_id ent_id, struct sim_ent_id owner_id) +struct sim_ent *sim_ent_alloc_sync_dst(struct sim_ent *parent, EntId ent_id, EntId owner_id) { - struct sim_snapshot *ss = parent->ss; + Snapshot *ss = parent->ss; struct sim_ent *e = sim_ent_alloc_raw(ss, parent, ent_id); sim_ent_enable_prop(e, SEPROP_SYNC_DST); e->owner = owner_id; @@ -97,7 +97,7 @@ struct sim_ent *sim_ent_alloc_sync_dst(struct sim_ent *parent, struct sim_ent_id void sim_ent_release_raw(struct sim_ent *ent) { - struct sim_snapshot *ss = ent->ss; + Snapshot *ss = ent->ss; /* Release children */ struct sim_ent *child = sim_ent_from_id(ss, ent->first); while (child->valid) { @@ -118,7 +118,7 @@ void sim_ent_release_raw(struct sim_ent *ent) void sim_ent_release(struct sim_ent *ent) { - struct sim_snapshot *ss = ent->ss; + Snapshot *ss = ent->ss; struct sim_ent *parent = sim_ent_from_id(ss, ent->parent); if (parent->valid) { sim_ent_unlink_from_parent(ent); @@ -126,7 +126,7 @@ void sim_ent_release(struct sim_ent *ent) sim_ent_release_raw(ent); } -void sim_ent_release_all_with_prop(struct sim_snapshot *ss, enum sim_ent_prop prop) +void sim_ent_release_all_with_prop(Snapshot *ss, enum sim_ent_prop prop) { TempArena scratch = scratch_begin_no_conflict(); @@ -168,16 +168,16 @@ void sim_ent_activate(struct sim_ent *ent, u64 current_tick) * Ent id * ========================== */ -INTERNAL struct sim_ent_bin *bin_from_id(struct sim_snapshot *ss, struct sim_ent_id id) +INTERNAL struct sim_ent_bin *bin_from_id(Snapshot *ss, EntId id) { return &ss->id_bins[id.uid.lo % ss->num_id_bins]; } /* NOTE: This should only really happen during ent allocation (it doesn't make sense for an allocated ent's id to change) */ -void sim_ent_set_id(struct sim_ent *ent, struct sim_ent_id id) +void sim_ent_set_id(struct sim_ent *ent, EntId id) { - struct sim_snapshot *ss = ent->ss; - struct sim_ent_id old_id = ent->id; + Snapshot *ss = ent->ss; + EntId old_id = ent->id; if (!sim_ent_id_eq(old_id, id)) { /* Release old from lookup */ if (!sim_ent_id_is_nil(old_id)) { @@ -244,7 +244,7 @@ void sim_ent_set_id(struct sim_ent *ent, struct sim_ent_id id) } -struct sim_ent *sim_ent_from_id(struct sim_snapshot *ss, struct sim_ent_id id) +struct sim_ent *sim_ent_from_id(Snapshot *ss, EntId id) { struct sim_ent *res = sim_ent_nil(); if (!sim_ent_id_is_nil(id) && ss->valid) { @@ -259,17 +259,17 @@ struct sim_ent *sim_ent_from_id(struct sim_snapshot *ss, struct sim_ent_id id) return res; } -struct sim_ent_id sim_ent_random_id(void) +EntId sim_ent_random_id(void) { - struct sim_ent_id res = ZI; + EntId res = ZI; res.uid = uid_true_rand(); return res; } /* Returns the deterministic id of the contact constraint ent id that should be produced from e0 & e1 colliding */ -struct sim_ent_id sim_ent_contact_constraint_id_from_contacting_ids(struct sim_ent_id player_id, struct sim_ent_id id0, struct sim_ent_id id1) +EntId sim_ent_contact_constraint_id_from_contacting_ids(EntId player_id, EntId id0, EntId id1) { - struct sim_ent_id res = ZI; + EntId res = ZI; res.uid = SIM_ENT_CONTACT_BASIS_UID; res.uid = uid_combine(res.uid, player_id.uid); res.uid = uid_combine(res.uid, id0.uid); @@ -278,9 +278,9 @@ struct sim_ent_id sim_ent_contact_constraint_id_from_contacting_ids(struct sim_e } /* Returns the deterministic id of the debug contact constraint ent id that should be produced from e0 & e1 colliding */ -struct sim_ent_id sim_ent_collision_debug_id_from_ids(struct sim_ent_id player_id, struct sim_ent_id id0, struct sim_ent_id id1) +EntId sim_ent_collision_debug_id_from_ids(EntId player_id, EntId id0, EntId id1) { - struct sim_ent_id res = ZI; + EntId res = ZI; res.uid = SIM_ENT_COLLISION_DEBUG_BASIS_UID; res.uid = uid_combine(res.uid, player_id.uid); res.uid = uid_combine(res.uid, id0.uid); @@ -289,9 +289,9 @@ struct sim_ent_id sim_ent_collision_debug_id_from_ids(struct sim_ent_id player_i } /* Returns the deterministic id of the tile chunk that should be produced at chunk pos */ -struct sim_ent_id sim_ent_tile_chunk_id_from_tile_chunk_index(V2i32 chunk_index) +EntId sim_ent_tile_chunk_id_from_tile_chunk_index(V2i32 chunk_index) { - struct sim_ent_id res = ZI; + EntId res = ZI; res.uid = SIM_ENT_TILE_CHUNK_BASIS_UID; res.uid = uid_combine(res.uid, MakeUID(rand_u64_from_seed(chunk_index.x), rand_u64_from_seed(chunk_index.y))); return res; @@ -301,7 +301,7 @@ struct sim_ent_id sim_ent_tile_chunk_id_from_tile_chunk_index(V2i32 chunk_index) * Ent query * ========================== */ -struct sim_ent *sim_ent_find_first_match_one(struct sim_snapshot *ss, enum sim_ent_prop prop) +struct sim_ent *sim_ent_find_first_match_one(Snapshot *ss, enum sim_ent_prop prop) { u64 count = ss->num_ents_reserved; struct sim_ent *entities = ss->ents; @@ -314,7 +314,7 @@ struct sim_ent *sim_ent_find_first_match_one(struct sim_snapshot *ss, enum sim_e return sim_ent_nil(); } -struct sim_ent *sim_ent_find_first_match_all(struct sim_snapshot *ss, struct sim_ent_prop_array props) +struct sim_ent *sim_ent_find_first_match_all(Snapshot *ss, struct sim_ent_prop_array props) { u64 count = ss->num_ents_reserved; struct sim_ent *entities = ss->ents; @@ -342,7 +342,7 @@ struct sim_ent *sim_ent_find_first_match_all(struct sim_snapshot *ss, struct sim void sim_ent_link_parent(struct sim_ent *ent, struct sim_ent *parent) { - struct sim_snapshot *ss = ent->ss; + Snapshot *ss = ent->ss; struct sim_ent *old_parent = sim_ent_from_id(ss, ent->parent); if (old_parent->valid) { @@ -350,8 +350,8 @@ void sim_ent_link_parent(struct sim_ent *ent, struct sim_ent *parent) sim_ent_unlink_from_parent(ent); } - struct sim_ent_id ent_id = ent->id; - struct sim_ent_id last_child_id = parent->last; + EntId ent_id = ent->id; + EntId last_child_id = parent->last; struct sim_ent *last_child = sim_ent_from_id(ss, last_child_id); if (last_child->valid) { ent->prev = last_child_id; @@ -374,9 +374,9 @@ void sim_ent_link_parent(struct sim_ent *ent, struct sim_ent *parent) /* NOTE: Entity will be dangling after calling this, should re-link to root ent. */ void sim_ent_unlink_from_parent(struct sim_ent *ent) { - struct sim_snapshot *ss = ent->ss; + Snapshot *ss = ent->ss; - struct sim_ent_id parent_id = ent->parent; + EntId parent_id = ent->parent; struct sim_ent *parent = sim_ent_from_id(ss, parent_id); struct sim_ent *prev = sim_ent_from_id(ss, ent->prev); struct sim_ent *next = sim_ent_from_id(ss, ent->next); @@ -400,7 +400,7 @@ void sim_ent_unlink_from_parent(struct sim_ent *ent) * Ent xform * ========================== */ -INTERNAL void sim_ent_mark_child_xforms_dirty(struct sim_snapshot *ss, struct sim_ent *ent) +INTERNAL void sim_ent_mark_child_xforms_dirty(Snapshot *ss, struct sim_ent *ent) { for (struct sim_ent *child = sim_ent_from_id(ss, ent->first); child->valid; child = sim_ent_from_id(ss, child->next)) { if (child->_is_xform_dirty) { @@ -412,7 +412,7 @@ INTERNAL void sim_ent_mark_child_xforms_dirty(struct sim_snapshot *ss, struct si } } -INTERNAL Xform sim_ent_get_xform_internal(struct sim_snapshot *ss, struct sim_ent *ent) +INTERNAL Xform sim_ent_get_xform_internal(Snapshot *ss, struct sim_ent *ent) { Xform xf; if (ent->_is_xform_dirty) { @@ -440,7 +440,7 @@ Xform sim_ent_get_xform(struct sim_ent *ent) if (ent->is_top) { xf = ent->_local_xform; } else { - struct sim_snapshot *ss = ent->ss; + Snapshot *ss = ent->ss; struct sim_ent *parent = sim_ent_from_id(ss, ent->parent); xf = sim_ent_get_xform_internal(ss, parent); xf = xform_mul(xf, ent->_local_xform); @@ -463,7 +463,7 @@ Xform sim_ent_get_local_xform(struct sim_ent *ent) void sim_ent_set_xform(struct sim_ent *ent, Xform xf) { if (!xform_eq(xf, ent->_xform)) { - struct sim_snapshot *ss = ent->ss; + Snapshot *ss = ent->ss; /* Update local xform */ if (ent->is_top) { ent->_local_xform = xf; @@ -559,23 +559,23 @@ void sim_ent_apply_torque(struct sim_ent *ent, f32 torque) * Tile * ========================== */ -struct sim_ent *sim_tile_chunk_from_chunk_index(struct sim_snapshot *ss, V2i32 chunk_index) +struct sim_ent *sim_tile_chunk_from_chunk_index(Snapshot *ss, V2i32 chunk_index) { - struct sim_ent_id chunk_id = sim_ent_tile_chunk_id_from_tile_chunk_index(chunk_index); + EntId chunk_id = sim_ent_tile_chunk_id_from_tile_chunk_index(chunk_index); struct sim_ent *chunk_ent = sim_ent_from_id(ss, chunk_id); return chunk_ent; } -struct sim_ent *sim_tile_chunk_from_world_tile_index(struct sim_snapshot *ss, V2i32 world_tile_index) +struct sim_ent *sim_tile_chunk_from_world_tile_index(Snapshot *ss, V2i32 world_tile_index) { V2i32 chunk_index = sim_tile_chunk_index_from_world_tile_index(world_tile_index); struct sim_ent *chunk_ent = sim_tile_chunk_from_chunk_index(ss, chunk_index); return chunk_ent; } -enum sim_tile_kind sim_get_chunk_tile(struct sim_ent *chunk_ent, V2i32 local_tile_index) +TileKind sim_get_chunk_tile(struct sim_ent *chunk_ent, V2i32 local_tile_index) { - enum sim_tile_kind res = chunk_ent->tile_chunk_tiles[local_tile_index.x + (local_tile_index.y * SIM_TILES_PER_CHUNK_SQRT)]; + TileKind res = chunk_ent->tile_chunk_tiles[local_tile_index.x + (local_tile_index.y * SIM_TILES_PER_CHUNK_SQRT)]; return res; } @@ -624,14 +624,14 @@ void sim_ent_lerp(struct sim_ent *e, struct sim_ent *e0, struct sim_ent *e1, f64 * ========================== */ /* Walks a local & remote ent tree and allocates any missing net dst ents from remote src ents */ -void sim_ent_sync_alloc_tree(struct sim_ent *local_parent, struct sim_ent *remote, struct sim_ent_id remote_player) +void sim_ent_sync_alloc_tree(struct sim_ent *local_parent, struct sim_ent *remote, EntId remote_player) { __prof; if (sim_ent_has_prop(remote, SEPROP_SYNC_SRC)) { - struct sim_snapshot *local_ss = local_parent->ss; - struct sim_snapshot *remote_ss = remote->ss; + Snapshot *local_ss = local_parent->ss; + Snapshot *remote_ss = remote->ss; - struct sim_ent_id id = remote->id; + EntId id = remote->id; struct sim_ent *local_ent = sim_ent_from_id(local_ss, id); if (!local_ent->valid) { local_ent = sim_ent_alloc_sync_dst(local_parent, id, remote_player); @@ -689,7 +689,7 @@ void sim_ent_sync(struct sim_ent *local, struct sim_ent *remote) void sim_ent_encode(BitbuffWriter *bw, struct sim_ent *e0, struct sim_ent *e1) { - struct sim_snapshot *ss = e1->ss; + Snapshot *ss = e1->ss; /* FIXME: Things like xforms need to be retreived manually rather than memcopied. */ /* TODO: Granular delta encoding */ @@ -716,7 +716,7 @@ void sim_ent_encode(BitbuffWriter *bw, struct sim_ent *e0, struct sim_ent *e1) void sim_ent_decode(BitbuffReader *br, struct sim_ent *e) { - struct sim_snapshot *old_ss = e->ss; + Snapshot *old_ss = e->ss; { u64 pos = 0; while (pos < sizeof(*e)) { @@ -741,7 +741,7 @@ void sim_ent_decode(BitbuffReader *br, struct sim_ent *e) void sim_ent_encode(BitbuffWriter *bw, struct sim_ent *e0, struct sim_ent *e1) { - struct sim_snapshot *ss = e1->ss; + Snapshot *ss = e1->ss; /* FIXME: Things like xforms need to be retreived manually rather than memcopied. @@ -789,8 +789,8 @@ void sim_ent_decode(BitbuffReader *br, struct sim_ent *e) } decoded.ss = e->ss; - struct sim_ent_id old_id = e->id; - struct sim_ent_id new_id = decoded.id; + EntId old_id = e->id; + EntId new_id = decoded.id; MEMCPY_STRUCT(e, &decoded); e->id = old_id; if (!sim_ent_id_eq(old_id, new_id)) { diff --git a/src/sim/sim_ent.h b/src/sim/sim_ent.h index c60e6d38..5b6e5fc4 100644 --- a/src/sim/sim_ent.h +++ b/src/sim/sim_ent.h @@ -1,5 +1,5 @@ -#define SIM_ENT_NIL_ID ((struct sim_ent_id) { MakeUID(0, 0) }) -#define SIM_ENT_ROOT_ID ((struct sim_ent_id) { MakeUID(0xaaaaaaaaaaaaaaaa, 0xaaaaaaaaaaaaaaaa) }) +#define SIM_ENT_NIL_ID ((EntId) { MakeUID(0, 0) }) +#define SIM_ENT_ROOT_ID ((EntId) { MakeUID(0xaaaaaaaaaaaaaaaa, 0xaaaaaaaaaaaaaaaa) }) enum sim_ent_prop { SEPROP_ACTIVE, @@ -61,13 +61,13 @@ enum sim_ent_prop { }; struct sim_ent { - struct sim_snapshot *ss; + Snapshot *ss; /* ====================================================================== */ /* Metadata */ b32 valid; /* Is this ent allocated in memory that can be written to (can always be read) */ - struct sim_ent_id id; + EntId id; u64 props[(SEPROP_COUNT + 63) / 64]; u64 continuity_gen; @@ -78,14 +78,14 @@ struct sim_ent { b32 is_top; /* The id of the top level parent of the ent tree (if ent is top then this point to itself) */ - struct sim_ent_id top; + EntId top; /* Tree */ - struct sim_ent_id parent; - struct sim_ent_id next; - struct sim_ent_id prev; - struct sim_ent_id first; - struct sim_ent_id last; + EntId parent; + EntId next; + EntId prev; + EntId first; + EntId last; /* Lists keyed by index in snapshot ent array */ u32 next_in_id_bin; @@ -99,10 +99,10 @@ struct sim_ent { /* SEPROP_SYNC_DST */ /* Id of the player that owns simulation for this entity */ - struct sim_ent_id owner; + EntId owner; /* Id of the player that should predict simulation of this this entity locally */ - struct sim_ent_id predictor; + EntId predictor; /* ====================================================================== */ /* Position */ @@ -129,14 +129,14 @@ struct sim_ent { /* SEPROP_CMD */ - enum sim_cmd_kind cmd_kind; - struct sim_ent_id cmd_player; + CmdKind cmd_kind; + EntId cmd_player; /* FIXME: Lerp */ /* Control cmd */ - struct sim_control cmd_control; - struct sim_ent_id cmd_control_hovered_ent; + ControlData cmd_control; + EntId cmd_control_hovered_ent; /* Chat cmd */ //String cmd_chat_msg; @@ -146,7 +146,7 @@ struct sim_ent { /* SEPROP_CHAT */ - struct sim_ent_id chat_player; + EntId chat_player; //String chat_msg; @@ -166,16 +166,16 @@ struct sim_ent { /* FIXME: Lerp */ - struct sim_client_handle player_client_handle; /* The client handle on the master sim's machine */ + ClientHandle player_client_handle; /* The client handle on the master sim's machine */ - struct sim_control player_control; + ControlData player_control; V2 player_cursor_pos; - struct sim_ent_id player_hovered_ent; - struct sim_ent_id player_control_ent; - struct sim_ent_id player_camera_ent; + EntId player_hovered_ent; + EntId player_control_ent; + EntId player_camera_ent; - struct sim_ent_id player_dbg_drag_joint_ent; + EntId player_dbg_drag_joint_ent; b32 player_dbg_drag_start; b32 player_dbg_drag_stop; @@ -190,42 +190,42 @@ struct sim_ent { CLD_Shape local_collider; #if COLLIDER_DEBUG - struct phys_collision_debug collision_debug_data; + CollisionDebugData collision_debug_data; #endif - struct space_entry_handle space_handle; + SpaceEntryHandle space_handle; /* ====================================================================== */ /* Constraints / joints */ /* SEPROP_CONSTRAINT_CONTACT */ - struct phys_contact_constraint contact_constraint_data; + ContactConstraint contact_constraint_data; /* SEPROP_MOTOR_JOINT */ - struct phys_motor_joint motor_joint_data; + MotorJoint motor_joint_data; /* SEPROP_MOUSE_JOINT */ - struct phys_mouse_joint mouse_joint_data; + MouseJoint mouse_joint_data; /* SEPROP_WELD_JOINT */ - struct phys_weld_joint weld_joint_data; + WeldJoint weld_joint_data; /* ====================================================================== */ /* Control */ /* SEPROP_CONTROLLED */ - struct sim_ent_id controlling_player; + EntId controlling_player; f32 control_force; /* How much force is applied to achieve desired control movement */ f32 control_force_max_speed; /* Maximum linear velocity achieved by force (m/s) */ f32 control_torque; /* How much torque is applied when turning towards desired focus */ - struct sim_control control; + ControlData control; - struct sim_ent_id move_joint; - struct sim_ent_id aim_joint; + EntId move_joint; + EntId aim_joint; /* ====================================================================== */ /* Physics */ @@ -239,7 +239,7 @@ struct sim_ent { f32 mass_unscaled; /* Mass of ent in kg before any transformations */ f32 inertia_unscaled; /* Inertia of ent in kg*m^2 before any transformations */ - struct sim_ent_id ground_friction_joint; + EntId ground_friction_joint; f32 linear_ground_friction; f32 angular_ground_friction; @@ -256,7 +256,7 @@ struct sim_ent { /* ====================================================================== */ /* Sprite */ - struct sprite_tag sprite; + S_Tag sprite; String sprite_span_name; u32 sprite_tint; V3 sprite_emittance; @@ -282,22 +282,22 @@ struct sim_ent { /* ====================================================================== */ /* Equip */ - struct sim_ent_id equipped; + EntId equipped; /* ====================================================================== */ /* Chucker */ /* SEPROP_WEAPON_CHUCKER */ - struct sim_ent_id chucker_zone; - struct sim_ent_id chucker_joint; + EntId chucker_zone; + EntId chucker_joint; /* ====================================================================== */ /* Chucker zone */ /* SEPROP_CHUCKER_ZONE */ - struct sim_ent_id chucker_zone_ent; + EntId chucker_zone_ent; u64 chucker_zone_ent_tick; /* ====================================================================== */ @@ -319,14 +319,14 @@ struct sim_ent { i64 triggered_count; /* Other triggers to activate when this entity has been triggered */ - //struct sim_ent_id trigger_out_left; - //struct sim_ent_id trigger_out_right; + //EntId trigger_out_left; + //EntId trigger_out_right; /* ====================================================================== */ /* Bullet */ - struct sim_ent_id bullet_src; - struct sim_ent_id bullet_tracer; + EntId bullet_src; + EntId bullet_tracer; V2 bullet_src_pos; V2 bullet_src_dir; f32 bullet_launch_velocity; @@ -380,7 +380,7 @@ struct sim_ent { /* Camera */ /* SEPROP_CAMERA */ - struct sim_ent_id camera_follow; + EntId camera_follow; Xform camera_quad_xform; f32 camera_lerp; /* Rate at which camera xform approaches target xform */ @@ -420,12 +420,12 @@ INLINE struct sim_ent *sim_ent_nil(void) * Id helpers * ========================== */ -INLINE b32 sim_ent_id_eq(struct sim_ent_id a, struct sim_ent_id b) +INLINE b32 sim_ent_id_eq(EntId a, EntId b) { return uid_eq(a.uid, b.uid); } -INLINE b32 sim_ent_id_is_nil(struct sim_ent_id id) +INLINE b32 sim_ent_id_is_nil(EntId id) { return uid_eq(id.uid, SIM_ENT_NIL_ID.uid); } @@ -476,7 +476,7 @@ INLINE b32 sim_ent_should_simulate(struct sim_ent *ent) if (sim_ent_is_valid_and_active(ent)) { res = 1; if (sim_ent_has_prop(ent, SEPROP_SYNC_DST)) { - struct sim_ent_id local_player = ent->ss->local_player; + EntId local_player = ent->ss->local_player; res = sim_ent_id_eq(local_player, ent->owner) || sim_ent_id_eq(local_player, ent->predictor); } } @@ -488,31 +488,31 @@ INLINE b32 sim_ent_should_simulate(struct sim_ent *ent) * ========================== */ /* Alloc */ -struct sim_ent *sim_ent_alloc_raw(struct sim_snapshot *ss, struct sim_ent *parent, struct sim_ent_id id); +struct sim_ent *sim_ent_alloc_raw(Snapshot *ss, struct sim_ent *parent, EntId id); struct sim_ent *sim_ent_alloc_local(struct sim_ent *parent); -struct sim_ent *sim_ent_alloc_local_with_id(struct sim_ent *parent, struct sim_ent_id id); +struct sim_ent *sim_ent_alloc_local_with_id(struct sim_ent *parent, EntId id); struct sim_ent *sim_ent_alloc_sync_src(struct sim_ent *parent); -struct sim_ent *sim_ent_alloc_sync_src_with_id(struct sim_ent *parent, struct sim_ent_id id); -struct sim_ent *sim_ent_alloc_sync_dst(struct sim_ent *parent, struct sim_ent_id ent_id, struct sim_ent_id owner_id); +struct sim_ent *sim_ent_alloc_sync_src_with_id(struct sim_ent *parent, EntId id); +struct sim_ent *sim_ent_alloc_sync_dst(struct sim_ent *parent, EntId ent_id, EntId owner_id); void sim_ent_release_raw(struct sim_ent *ent); void sim_ent_release(struct sim_ent *ent); -void sim_ent_release_all_with_prop(struct sim_snapshot *ss, enum sim_ent_prop prop); +void sim_ent_release_all_with_prop(Snapshot *ss, enum sim_ent_prop prop); /* Activate */ void sim_ent_activate(struct sim_ent *ent, u64 current_tick); /* Id */ -void sim_ent_set_id(struct sim_ent *ent, struct sim_ent_id id); -struct sim_ent *sim_ent_from_id(struct sim_snapshot *ss, struct sim_ent_id id); -struct sim_ent_id sim_ent_random_id(void); -struct sim_ent_id sim_ent_contact_constraint_id_from_contacting_ids(struct sim_ent_id player_id, struct sim_ent_id id0, struct sim_ent_id id1); -struct sim_ent_id sim_ent_collision_debug_id_from_ids(struct sim_ent_id player_id, struct sim_ent_id id0, struct sim_ent_id id1); -struct sim_ent_id sim_ent_tile_chunk_id_from_tile_chunk_index(V2i32 chunk_start); +void sim_ent_set_id(struct sim_ent *ent, EntId id); +struct sim_ent *sim_ent_from_id(Snapshot *ss, EntId id); +EntId sim_ent_random_id(void); +EntId sim_ent_contact_constraint_id_from_contacting_ids(EntId player_id, EntId id0, EntId id1); +EntId sim_ent_collision_debug_id_from_ids(EntId player_id, EntId id0, EntId id1); +EntId sim_ent_tile_chunk_id_from_tile_chunk_index(V2i32 chunk_start); /* Query */ -struct sim_ent *sim_ent_find_first_match_one(struct sim_snapshot *ss, enum sim_ent_prop prop); -struct sim_ent *sim_ent_find_first_match_all(struct sim_snapshot *ss, struct sim_ent_prop_array props); +struct sim_ent *sim_ent_find_first_match_one(Snapshot *ss, enum sim_ent_prop prop); +struct sim_ent *sim_ent_find_first_match_all(Snapshot *ss, struct sim_ent_prop_array props); /* Tree */ void sim_ent_link_parent(struct sim_ent *parent, struct sim_ent *child); @@ -534,15 +534,15 @@ void sim_ent_apply_angular_impulse(struct sim_ent *ent, f32 impulse); void sim_ent_apply_torque(struct sim_ent *ent, f32 torque); /* Tile */ -struct sim_ent *sim_tile_chunk_from_chunk_index(struct sim_snapshot *ss, V2i32 chunk_index); -struct sim_ent *sim_tile_chunk_from_world_tile_index(struct sim_snapshot *ss, V2i32 world_tile_index); -enum sim_tile_kind sim_get_chunk_tile(struct sim_ent *chunk_ent, V2i32 local_tile_index); +struct sim_ent *sim_tile_chunk_from_chunk_index(Snapshot *ss, V2i32 chunk_index); +struct sim_ent *sim_tile_chunk_from_world_tile_index(Snapshot *ss, V2i32 world_tile_index); +TileKind sim_get_chunk_tile(struct sim_ent *chunk_ent, V2i32 local_tile_index); /* Lerp */ void sim_ent_lerp(struct sim_ent *e, struct sim_ent *e0, struct sim_ent *e1, f64 blend); /* Sync */ -void sim_ent_sync_alloc_tree(struct sim_ent *local_parent, struct sim_ent *remote, struct sim_ent_id remote_player); +void sim_ent_sync_alloc_tree(struct sim_ent *local_parent, struct sim_ent *remote, EntId remote_player); void sim_ent_sync(struct sim_ent *local, struct sim_ent *remote); /* Encode / decode */ diff --git a/src/sim/sim_phys.c b/src/sim/sim_phys.c index abd1d965..8a194447 100644 --- a/src/sim/sim_phys.c +++ b/src/sim/sim_phys.c @@ -14,13 +14,13 @@ INTERNAL b32 can_contact(struct sim_ent *e0, struct sim_ent *e1) return res; } -void phys_create_and_update_contacts(struct phys_step_ctx *ctx, f32 elapsed_dt, u64 phys_iteration) +void phys_create_and_update_contacts(PhysStepCtx *ctx, f32 elapsed_dt, u64 phys_iteration) { __prof; - struct sim_step_ctx *sim_step_ctx = ctx->sim_step_ctx; - struct sim_snapshot *ss = sim_step_ctx->world; - struct space *space = sim_step_ctx->accel->space; - struct sim_ent_id local_player = ss->local_player; + SimStepCtx *sim_step_ctx = ctx->sim_step_ctx; + Snapshot *ss = sim_step_ctx->world; + Space *space = sim_step_ctx->accel->space; + EntId local_player = ss->local_player; phys_collision_callback_func *collision_callback = ctx->collision_callback; struct sim_ent *root = sim_ent_from_id(ss, SIM_ENT_ROOT_ID); @@ -36,8 +36,8 @@ void phys_create_and_update_contacts(struct phys_step_ctx *ctx, f32 elapsed_dt, CLD_Shape check0_collider = check0->local_collider; Aabb aabb = collider_aabb_from_collider(&check0_collider, check0_xf); - struct space_iter iter = space_iter_begin_aabb(space, aabb); - struct space_entry *space_entry; + SpaceIter iter = space_iter_begin_aabb(space, aabb); + SpaceEntry *space_entry; while ((space_entry = space_iter_next(&iter)) != 0) { struct sim_ent *check1 = sim_ent_from_id(ss, space_entry->ent); if (!sim_ent_is_valid_and_active(check1)) continue; @@ -68,7 +68,7 @@ void phys_create_and_update_contacts(struct phys_step_ctx *ctx, f32 elapsed_dt, e1_collider = check0_collider; } - struct sim_ent_id constraint_id = sim_ent_contact_constraint_id_from_contacting_ids(local_player, e0->id, e1->id); + EntId constraint_id = sim_ent_contact_constraint_id_from_contacting_ids(local_player, e0->id, e1->id); struct sim_ent *constraint_ent = sim_ent_from_id(ss, constraint_id); if (constraint_ent->valid) { @@ -87,7 +87,7 @@ void phys_create_and_update_contacts(struct phys_step_ctx *ctx, f32 elapsed_dt, STATIC_ASSERT(countof(constraint_ent->contact_constraint_data.points) == 2); STATIC_ASSERT(countof(collider_res.points) == 2); - struct phys_contact_constraint *constraint = 0; + ContactConstraint *constraint = 0; if (collider_res.num_points > 0) { b32 is_start = 0; if (!constraint_ent->valid) { @@ -111,7 +111,7 @@ void phys_create_and_update_contacts(struct phys_step_ctx *ctx, f32 elapsed_dt, /* Delete old contacts that are no longer present */ for (u32 i = 0; i < constraint->num_points; ++i) { - struct phys_contact_point *old = &constraint->points[i]; + ContactPoint *old = &constraint->points[i]; u32 id = old->id; b32 found = 0; for (u32 j = 0; j < collider_res.num_points; ++j) { @@ -133,10 +133,10 @@ void phys_create_and_update_contacts(struct phys_step_ctx *ctx, f32 elapsed_dt, V2 point = res_point->point; f32 sep = res_point->separation; u32 id = res_point->id; - struct phys_contact_point *contact = 0; + ContactPoint *contact = 0; /* Match */ for (u32 j = 0; j < constraint->num_points; ++j) { - struct phys_contact_point *t = &constraint->points[j]; + ContactPoint *t = &constraint->points[j]; if (t->id == id) { contact = t; break; @@ -178,7 +178,7 @@ void phys_create_and_update_contacts(struct phys_step_ctx *ctx, f32 elapsed_dt, /* Run collision callback */ if (collision_callback) { - struct phys_collision_data data = ZI; + CollisionData data = ZI; data.e0 = e0->id; data.e1 = e1->id; data.normal = collider_res.normal; @@ -208,7 +208,7 @@ void phys_create_and_update_contacts(struct phys_step_ctx *ctx, f32 elapsed_dt, data.vrel = vrel; /* Collision data from e1's perspective */ - struct phys_collision_data data_inverted = data; + CollisionData data_inverted = data; data_inverted.e0 = data.e1; data_inverted.e1 = data.e0; data_inverted.normal = v2_neg(data.normal); @@ -228,7 +228,7 @@ void phys_create_and_update_contacts(struct phys_step_ctx *ctx, f32 elapsed_dt, /* TODO: Remove this (debugging) */ #if COLLIDER_DEBUG && COLLIDER_DEBUG_DETAILED { - struct sim_ent_id dbg_ent_id = sim_ent_collision_debug_id_from_ids(local_player, e0->id, e1->id); + EntId dbg_ent_id = sim_ent_collision_debug_id_from_ids(local_player, e0->id, e1->id); struct sim_ent *dbg_ent = sim_ent_from_id(ss, dbg_ent_id); if (!dbg_ent->valid) { /* FIXME: Entity never released */ @@ -236,7 +236,7 @@ void phys_create_and_update_contacts(struct phys_step_ctx *ctx, f32 elapsed_dt, sim_ent_enable_prop(dbg_ent, SEPROP_COLLISION_DEBUG); } - struct phys_collision_debug *dbg = &dbg_ent->collision_debug_data; + CollisionDebugData *dbg = &dbg_ent->collision_debug_data; dbg->e0 = e0->id; dbg->e1 = e1->id; @@ -265,17 +265,17 @@ void phys_create_and_update_contacts(struct phys_step_ctx *ctx, f32 elapsed_dt, } } -void phys_prepare_contacts(struct phys_step_ctx *ctx, u64 phys_iteration) +void phys_prepare_contacts(PhysStepCtx *ctx, u64 phys_iteration) { __prof; - struct sim_snapshot *ss = ctx->sim_step_ctx->world; + Snapshot *ss = ctx->sim_step_ctx->world; for (u64 sim_ent_index = 0; sim_ent_index < ss->num_ents_reserved; ++sim_ent_index) { struct sim_ent *constraint_ent = &ss->ents[sim_ent_index]; if (!sim_ent_should_simulate(constraint_ent)) continue; if (!sim_ent_has_prop(constraint_ent, SEPROP_CONTACT_CONSTRAINT)) continue; - struct phys_contact_constraint *constraint = &constraint_ent->contact_constraint_data; + ContactConstraint *constraint = &constraint_ent->contact_constraint_data; u32 num_points = constraint->num_points; struct sim_ent *e0 = sim_ent_from_id(ss, constraint->e0); @@ -318,7 +318,7 @@ void phys_prepare_contacts(struct phys_step_ctx *ctx, u64 phys_iteration) /* Update / insert returned contacts */ for (u32 i = 0; i < num_points; ++i) { - struct phys_contact_point *contact = &constraint->points[i]; + ContactPoint *contact = &constraint->points[i]; V2 vcp0 = contact->vcp0; V2 vcp1 = contact->vcp1; @@ -359,7 +359,7 @@ void phys_prepare_contacts(struct phys_step_ctx *ctx, u64 phys_iteration) if (!sim_ent_should_simulate(dbg_ent)) continue; if (!sim_ent_has_prop(dbg_ent, SEPROP_COLLISION_DEBUG)) continue; - struct phys_collision_debug *dbg = &dbg_ent->collision_debug_data; + CollisionDebugData *dbg = &dbg_ent->collision_debug_data; struct sim_ent *e0 = sim_ent_from_id(ss, dbg->e0); struct sim_ent *e1 = sim_ent_from_id(ss, dbg->e1); @@ -375,16 +375,16 @@ void phys_prepare_contacts(struct phys_step_ctx *ctx, u64 phys_iteration) #endif } -void phys_warm_start_contacts(struct phys_step_ctx *ctx) +void phys_warm_start_contacts(PhysStepCtx *ctx) { __prof; - struct sim_snapshot *ss = ctx->sim_step_ctx->world; + Snapshot *ss = ctx->sim_step_ctx->world; for (u64 sim_ent_index = 0; sim_ent_index < ss->num_ents_reserved; ++sim_ent_index) { struct sim_ent *constraint_ent = &ss->ents[sim_ent_index]; if (!sim_ent_should_simulate(constraint_ent)) continue; if (!sim_ent_has_prop(constraint_ent, SEPROP_CONTACT_CONSTRAINT)) continue; - struct phys_contact_constraint *constraint = &constraint_ent->contact_constraint_data; + ContactConstraint *constraint = &constraint_ent->contact_constraint_data; u32 num_points = constraint->num_points; struct sim_ent *e0 = sim_ent_from_id(ss, constraint->e0); @@ -406,7 +406,7 @@ void phys_warm_start_contacts(struct phys_step_ctx *ctx) V2 tangent = v2_perp(normal); f32 inv_num_points = 1.f / num_points; for (u32 i = 0; i < num_points; ++i) { - struct phys_contact_point *point = &constraint->points[i]; + ContactPoint *point = &constraint->points[i]; V2 vcp0 = point->vcp0; V2 vcp1 = point->vcp1; @@ -427,16 +427,16 @@ void phys_warm_start_contacts(struct phys_step_ctx *ctx) } } -void phys_solve_contacts(struct phys_step_ctx *ctx, f32 dt, b32 apply_bias) +void phys_solve_contacts(PhysStepCtx *ctx, f32 dt, b32 apply_bias) { __prof; - struct sim_snapshot *ss = ctx->sim_step_ctx->world; + Snapshot *ss = ctx->sim_step_ctx->world; for (u64 sim_ent_index = 0; sim_ent_index < ss->num_ents_reserved; ++sim_ent_index) { struct sim_ent *constraint_ent = &ss->ents[sim_ent_index]; if (!sim_ent_should_simulate(constraint_ent)) continue; if (!sim_ent_has_prop(constraint_ent, SEPROP_CONTACT_CONSTRAINT)) continue; - struct phys_contact_constraint *constraint = &constraint_ent->contact_constraint_data; + ContactConstraint *constraint = &constraint_ent->contact_constraint_data; struct sim_ent *e0 = sim_ent_from_id(ss, constraint->e0); struct sim_ent *e1 = sim_ent_from_id(ss, constraint->e1); @@ -459,7 +459,7 @@ void phys_solve_contacts(struct phys_step_ctx *ctx, f32 dt, b32 apply_bias) /* Normal impulse */ V2 normal = constraint->normal; for (u32 point_index = 0; point_index < num_points; ++point_index) { - struct phys_contact_point *point = &constraint->points[point_index]; + ContactPoint *point = &constraint->points[point_index]; V2 vcp0 = point->vcp0; V2 vcp1 = point->vcp1; V2 p0 = v2_add(e0_xf.og, vcp0); @@ -509,7 +509,7 @@ void phys_solve_contacts(struct phys_step_ctx *ctx, f32 dt, b32 apply_bias) /* Tangent impulse */ V2 tangent = v2_perp(normal); for (u32 point_index = 0; point_index < num_points; ++point_index) { - struct phys_contact_point *point = &constraint->points[point_index]; + ContactPoint *point = &constraint->points[point_index]; V2 vcp0 = point->vcp0; V2 vcp1 = point->vcp1; @@ -548,15 +548,15 @@ void phys_solve_contacts(struct phys_step_ctx *ctx, f32 dt, b32 apply_bias) * Motor joint * ========================== */ -struct phys_motor_joint_def phys_motor_joint_def_init(void) +MotorJointDesc phys_motor_joint_def_init(void) { - struct phys_motor_joint_def def = ZI; + MotorJointDesc def = ZI; return def; } -struct phys_motor_joint phys_motor_joint_from_def(struct phys_motor_joint_def def) +MotorJoint phys_motor_joint_from_def(MotorJointDesc def) { - struct phys_motor_joint res = ZI; + MotorJoint res = ZI; res.e0 = def.e0; res.e1 = def.e1; res.correction_rate = clamp_f32(def.correction_rate, 0, 1); @@ -565,16 +565,16 @@ struct phys_motor_joint phys_motor_joint_from_def(struct phys_motor_joint_def de return res; } -void phys_prepare_motor_joints(struct phys_step_ctx *ctx) +void phys_prepare_motor_joints(PhysStepCtx *ctx) { __prof; - struct sim_snapshot *ss = ctx->sim_step_ctx->world; + Snapshot *ss = ctx->sim_step_ctx->world; for (u64 sim_ent_index = 0; sim_ent_index < ss->num_ents_reserved; ++sim_ent_index) { struct sim_ent *joint_ent = &ss->ents[sim_ent_index]; if (!sim_ent_should_simulate(joint_ent)) continue; if (!sim_ent_has_prop(joint_ent, SEPROP_MOTOR_JOINT)) continue; - struct phys_motor_joint *joint = &joint_ent->motor_joint_data; + MotorJoint *joint = &joint_ent->motor_joint_data; struct sim_ent *e0 = sim_ent_from_id(ss, joint->e0); struct sim_ent *e1 = sim_ent_from_id(ss, joint->e1); @@ -629,16 +629,16 @@ void phys_prepare_motor_joints(struct phys_step_ctx *ctx) } } -void phys_warm_start_motor_joints(struct phys_step_ctx *ctx) +void phys_warm_start_motor_joints(PhysStepCtx *ctx) { __prof; - struct sim_snapshot *ss = ctx->sim_step_ctx->world; + Snapshot *ss = ctx->sim_step_ctx->world; for (u64 sim_ent_index = 0; sim_ent_index < ss->num_ents_reserved; ++sim_ent_index) { struct sim_ent *joint_ent = &ss->ents[sim_ent_index]; if (!sim_ent_should_simulate(joint_ent)) continue; if (!sim_ent_has_prop(joint_ent, SEPROP_MOTOR_JOINT)) continue; - struct phys_motor_joint *joint = &joint_ent->motor_joint_data; + MotorJoint *joint = &joint_ent->motor_joint_data; struct sim_ent *e0 = sim_ent_from_id(ss, joint->e0); struct sim_ent *e1 = sim_ent_from_id(ss, joint->e1); @@ -661,16 +661,16 @@ void phys_warm_start_motor_joints(struct phys_step_ctx *ctx) } } -void phys_solve_motor_joints(struct phys_step_ctx *ctx, f32 dt) +void phys_solve_motor_joints(PhysStepCtx *ctx, f32 dt) { __prof; - struct sim_snapshot *ss = ctx->sim_step_ctx->world; + Snapshot *ss = ctx->sim_step_ctx->world; for (u64 sim_ent_index = 0; sim_ent_index < ss->num_ents_reserved; ++sim_ent_index) { struct sim_ent *joint_ent = &ss->ents[sim_ent_index]; if (!sim_ent_should_simulate(joint_ent)) continue; if (!sim_ent_has_prop(joint_ent, SEPROP_MOTOR_JOINT)) continue; - struct phys_motor_joint *joint = &joint_ent->motor_joint_data; + MotorJoint *joint = &joint_ent->motor_joint_data; struct sim_ent *e0 = sim_ent_from_id(ss, joint->e0); struct sim_ent *e1 = sim_ent_from_id(ss, joint->e1); @@ -742,9 +742,9 @@ void phys_solve_motor_joints(struct phys_step_ctx *ctx, f32 dt) * Mouse joint * ========================== */ -struct phys_mouse_joint_def phys_mouse_joint_def_init(void) +MouseJointDesc phys_mouse_joint_def_init(void) { - struct phys_mouse_joint_def def = ZI; + MouseJointDesc def = ZI; def.linear_spring_hz = 5.0f; def.linear_spring_damp = 0.7f; def.angular_spring_hz = 5.0f; @@ -753,9 +753,9 @@ struct phys_mouse_joint_def phys_mouse_joint_def_init(void) return def; } -struct phys_mouse_joint phys_mouse_joint_from_def(struct phys_mouse_joint_def def) +MouseJoint phys_mouse_joint_from_def(MouseJointDesc def) { - struct phys_mouse_joint res = ZI; + MouseJoint res = ZI; res.target = def.target; res.point_local_start = def.point_local_start; res.point_end = def.point_end; @@ -767,16 +767,16 @@ struct phys_mouse_joint phys_mouse_joint_from_def(struct phys_mouse_joint_def de return res; } -void phys_prepare_mouse_joints(struct phys_step_ctx *ctx) +void phys_prepare_mouse_joints(PhysStepCtx *ctx) { __prof; - struct sim_snapshot *ss = ctx->sim_step_ctx->world; + Snapshot *ss = ctx->sim_step_ctx->world; for (u64 sim_ent_index = 0; sim_ent_index < ss->num_ents_reserved; ++sim_ent_index) { struct sim_ent *joint_ent = &ss->ents[sim_ent_index]; if (!sim_ent_should_simulate(joint_ent)) continue; if (!sim_ent_has_prop(joint_ent, SEPROP_MOUSE_JOINT)) continue; - struct phys_mouse_joint *joint = &joint_ent->mouse_joint_data; + MouseJoint *joint = &joint_ent->mouse_joint_data; struct sim_ent *ent = sim_ent_from_id(ss, joint->target); if (sim_ent_should_simulate(ent)) { Xform xf = sim_ent_get_xform(ent); @@ -814,16 +814,16 @@ void phys_prepare_mouse_joints(struct phys_step_ctx *ctx) } } -void phys_warm_start_mouse_joints(struct phys_step_ctx *ctx) +void phys_warm_start_mouse_joints(PhysStepCtx *ctx) { __prof; - struct sim_snapshot *ss = ctx->sim_step_ctx->world; + Snapshot *ss = ctx->sim_step_ctx->world; for (u64 sim_ent_index = 0; sim_ent_index < ss->num_ents_reserved; ++sim_ent_index) { struct sim_ent *joint_ent = &ss->ents[sim_ent_index]; if (!sim_ent_should_simulate(joint_ent)) continue; if (!sim_ent_has_prop(joint_ent, SEPROP_MOUSE_JOINT)) continue; - struct phys_mouse_joint *joint = &joint_ent->mouse_joint_data; + MouseJoint *joint = &joint_ent->mouse_joint_data; struct sim_ent *ent = sim_ent_from_id(ss, joint->target); if (sim_ent_should_simulate(ent)) { f32 inv_m = joint->inv_m; @@ -836,16 +836,16 @@ void phys_warm_start_mouse_joints(struct phys_step_ctx *ctx) } } -void phys_solve_mouse_joints(struct phys_step_ctx *ctx, f32 dt) +void phys_solve_mouse_joints(PhysStepCtx *ctx, f32 dt) { __prof; - struct sim_snapshot *ss = ctx->sim_step_ctx->world; + Snapshot *ss = ctx->sim_step_ctx->world; for (u64 sim_ent_index = 0; sim_ent_index < ss->num_ents_reserved; ++sim_ent_index) { struct sim_ent *joint_ent = &ss->ents[sim_ent_index]; if (!sim_ent_should_simulate(joint_ent)) continue; if (!sim_ent_has_prop(joint_ent, SEPROP_MOUSE_JOINT)) continue; - struct phys_mouse_joint *joint = &joint_ent->mouse_joint_data; + MouseJoint *joint = &joint_ent->mouse_joint_data; struct sim_ent *ent = sim_ent_from_id(ss, joint->target); if (sim_ent_should_simulate(ent)) { V2 v = ent->linear_velocity; @@ -909,9 +909,9 @@ void phys_solve_mouse_joints(struct phys_step_ctx *ctx, f32 dt) * Weld joint * ========================== */ -struct phys_weld_joint_def phys_weld_joint_def_init(void) +WeldJointDesc phys_weld_joint_def_init(void) { - struct phys_weld_joint_def def = ZI; + WeldJointDesc def = ZI; def.linear_spring_hz = 50; def.linear_spring_damp = 0; def.angular_spring_hz = 50; @@ -919,9 +919,9 @@ struct phys_weld_joint_def phys_weld_joint_def_init(void) return def; } -struct phys_weld_joint phys_weld_joint_from_def(struct phys_weld_joint_def def) +WeldJoint phys_weld_joint_from_def(WeldJointDesc def) { - struct phys_weld_joint res = ZI; + WeldJoint res = ZI; res.e0 = def.e0; res.e1 = def.e1; res.linear_spring_hz = def.linear_spring_hz; @@ -932,10 +932,10 @@ struct phys_weld_joint phys_weld_joint_from_def(struct phys_weld_joint_def def) return res; } -void phys_prepare_weld_joints(struct phys_step_ctx *ctx) +void phys_prepare_weld_joints(PhysStepCtx *ctx) { __prof; - struct sim_snapshot *ss = ctx->sim_step_ctx->world; + Snapshot *ss = ctx->sim_step_ctx->world; for (u64 sim_ent_index = 0; sim_ent_index < ss->num_ents_reserved; ++sim_ent_index) { struct sim_ent *joint_ent = &ss->ents[sim_ent_index]; if (!sim_ent_should_simulate(joint_ent)) continue; @@ -943,7 +943,7 @@ void phys_prepare_weld_joints(struct phys_step_ctx *ctx) /* TODO: Lookup and disable collision for any contacts between e0 & e1? */ - struct phys_weld_joint *joint = &joint_ent->weld_joint_data; + WeldJoint *joint = &joint_ent->weld_joint_data; struct sim_ent *e0 = sim_ent_from_id(ss, joint->e0); struct sim_ent *e1 = sim_ent_from_id(ss, joint->e1); if (sim_ent_should_simulate(e0) && sim_ent_should_simulate(e1)) { @@ -981,16 +981,16 @@ void phys_prepare_weld_joints(struct phys_step_ctx *ctx) } } -void phys_warm_start_weld_joints(struct phys_step_ctx *ctx) +void phys_warm_start_weld_joints(PhysStepCtx *ctx) { __prof; - struct sim_snapshot *ss = ctx->sim_step_ctx->world; + Snapshot *ss = ctx->sim_step_ctx->world; for (u64 sim_ent_index = 0; sim_ent_index < ss->num_ents_reserved; ++sim_ent_index) { struct sim_ent *joint_ent = &ss->ents[sim_ent_index]; if (!sim_ent_should_simulate(joint_ent)) continue; if (!sim_ent_has_prop(joint_ent, SEPROP_WELD_JOINT)) continue; - struct phys_weld_joint *joint = &joint_ent->weld_joint_data; + WeldJoint *joint = &joint_ent->weld_joint_data; #if 0 struct sim_ent *e0 = sim_ent_from_id(ss, joint->e0); @@ -1018,16 +1018,16 @@ void phys_warm_start_weld_joints(struct phys_step_ctx *ctx) } } -void phys_solve_weld_joints(struct phys_step_ctx *ctx, f32 dt) +void phys_solve_weld_joints(PhysStepCtx *ctx, f32 dt) { __prof; - struct sim_snapshot *ss = ctx->sim_step_ctx->world; + Snapshot *ss = ctx->sim_step_ctx->world; for (u64 sim_ent_index = 0; sim_ent_index < ss->num_ents_reserved; ++sim_ent_index) { struct sim_ent *joint_ent = &ss->ents[sim_ent_index]; if (!sim_ent_should_simulate(joint_ent)) continue; if (!sim_ent_has_prop(joint_ent, SEPROP_WELD_JOINT)) continue; - struct phys_weld_joint *joint = &joint_ent->weld_joint_data; + WeldJoint *joint = &joint_ent->weld_joint_data; struct sim_ent *e0 = sim_ent_from_id(ss, joint->e0); struct sim_ent *e1 = sim_ent_from_id(ss, joint->e1); if (sim_ent_should_simulate(e0) && sim_ent_should_simulate(e1)) { @@ -1098,10 +1098,10 @@ INTERNAL Xform get_derived_xform(struct sim_ent *ent, f32 dt) return xf; } -void phys_integrate_forces(struct phys_step_ctx *ctx, f32 dt) +void phys_integrate_forces(PhysStepCtx *ctx, f32 dt) { __prof; - struct sim_snapshot *ss = ctx->sim_step_ctx->world; + Snapshot *ss = ctx->sim_step_ctx->world; for (u64 sim_ent_index = 0; sim_ent_index < ss->num_ents_reserved; ++sim_ent_index) { struct sim_ent *ent = &ss->ents[sim_ent_index]; if (!sim_ent_should_simulate(ent)) continue; @@ -1140,10 +1140,10 @@ void phys_integrate_forces(struct phys_step_ctx *ctx, f32 dt) } } -void phys_integrate_velocities(struct phys_step_ctx *ctx, f32 dt) +void phys_integrate_velocities(PhysStepCtx *ctx, f32 dt) { __prof; - struct sim_snapshot *ss = ctx->sim_step_ctx->world; + Snapshot *ss = ctx->sim_step_ctx->world; for (u64 sim_ent_index = 0; sim_ent_index < ss->num_ents_reserved; ++sim_ent_index) { struct sim_ent *ent = &ss->ents[sim_ent_index]; if (!sim_ent_should_simulate(ent)) continue; @@ -1158,11 +1158,11 @@ void phys_integrate_velocities(struct phys_step_ctx *ctx, f32 dt) * Earliest time of impact * ========================== */ -f32 phys_determine_earliest_toi(struct phys_step_ctx *ctx, f32 step_dt, f32 tolerance, u32 max_iterations) +f32 phys_determine_earliest_toi(PhysStepCtx *ctx, f32 step_dt, f32 tolerance, u32 max_iterations) { __prof; - struct sim_snapshot *ss = ctx->sim_step_ctx->world; - struct space *space = ctx->sim_step_ctx->accel->space; + Snapshot *ss = ctx->sim_step_ctx->world; + Space *space = ctx->sim_step_ctx->accel->space; f32 smallest_t = 1; for (u64 e0_index = 0; e0_index < ss->num_ents_reserved; ++e0_index) { @@ -1181,8 +1181,8 @@ f32 phys_determine_earliest_toi(struct phys_step_ctx *ctx, f32 step_dt, f32 tole Aabb aabb_t1 = collider_aabb_from_collider(&e0_collider, e0_xf_t1); Aabb combined_aabb = collider_aabb_from_combined_aabb(aabb_t0, aabb_t1); - struct space_iter iter = space_iter_begin_aabb(space, combined_aabb); - struct space_entry *entry; + SpaceIter iter = space_iter_begin_aabb(space, combined_aabb); + SpaceEntry *entry; while ((entry = space_iter_next(&iter)) != 0) { struct sim_ent *e1 = sim_ent_from_id(ss, entry->ent); if (!sim_ent_should_simulate(e1)) continue; @@ -1209,17 +1209,17 @@ f32 phys_determine_earliest_toi(struct phys_step_ctx *ctx, f32 step_dt, f32 tole * Space * ========================== */ -void phys_update_aabbs(struct phys_step_ctx *ctx) +void phys_update_aabbs(PhysStepCtx *ctx) { __prof; - struct sim_snapshot *ss = ctx->sim_step_ctx->world; - struct space *space = ctx->sim_step_ctx->accel->space; + Snapshot *ss = ctx->sim_step_ctx->world; + Space *space = ctx->sim_step_ctx->accel->space; for (u64 sim_ent_index = 0; sim_ent_index < ss->num_ents_reserved; ++sim_ent_index) { struct sim_ent *ent = &ss->ents[sim_ent_index]; if (!sim_ent_is_valid_and_active(ent)) continue; if (ent->local_collider.count > 0) { Xform xf = sim_ent_get_xform(ent); - struct space_entry *space_entry = space_entry_from_handle(space, ent->space_handle); + SpaceEntry *space_entry = space_entry_from_handle(space, ent->space_handle); if (!space_entry->valid) { space_entry = space_entry_alloc(space, ent->id); ent->space_handle = space_entry->handle; @@ -1235,11 +1235,11 @@ void phys_update_aabbs(struct phys_step_ctx *ctx) * ========================== */ /* Returns phys iteration to be fed into next step. Supplied iteration must be > 0. */ -void phys_step(struct phys_step_ctx *ctx, f32 timestep) +void phys_step(PhysStepCtx *ctx, f32 timestep) { __prof; phys_integrate_forces(ctx, timestep); - struct sim_snapshot *ss = ctx->sim_step_ctx->world; + Snapshot *ss = ctx->sim_step_ctx->world; u64 phys_iteration = ss->phys_iteration; phys_update_aabbs(ctx); diff --git a/src/sim/sim_phys.h b/src/sim/sim_phys.h index 19016627..509856a7 100644 --- a/src/sim/sim_phys.h +++ b/src/sim/sim_phys.h @@ -1,11 +1,7 @@ -struct space; -struct sim_ent_lookup; -struct sim_step_ctx; - -struct phys_contact_constraint; -struct phys_collision_data { - struct sim_ent_id e0; - struct sim_ent_id e1; +typedef struct CollisionData CollisionData; +struct CollisionData { + EntId e0; + EntId e1; V2 point; V2 normal; /* Normal of the collision from e0 to e1 */ V2 vrel; /* Relative velocity at point of collision */ @@ -14,12 +10,14 @@ struct phys_collision_data { }; /* Callback can return 1 to prevent the physics system from resolving */ -#define PHYS_COLLISION_CALLBACK_FUNC_DEF(name, arg_collision_data, arg_sim_step_ctx) b32 name(struct phys_collision_data *arg_collision_data, struct sim_step_ctx *arg_sim_step_ctx) +typedef struct SimStepCtx SimStepCtx; +#define PHYS_COLLISION_CALLBACK_FUNC_DEF(name, arg_collision_data, arg_sim_step_ctx) b32 name(CollisionData *arg_collision_data, SimStepCtx *arg_sim_step_ctx) typedef PHYS_COLLISION_CALLBACK_FUNC_DEF(phys_collision_callback_func, collision_data, ctx); /* Structure containing data used for a single physics step */ -struct phys_step_ctx { - struct sim_step_ctx *sim_step_ctx; +typedef struct PhysStepCtx PhysStepCtx; +struct PhysStepCtx { + SimStepCtx *sim_step_ctx; phys_collision_callback_func *collision_callback; }; @@ -27,7 +25,8 @@ struct phys_step_ctx { * Contact * ========================== */ -struct phys_contact_point { +typedef struct ContactPoint ContactPoint; +struct ContactPoint { /* Contact point relative to the center of each entity. * * NOTE: We use fixed (non-rotated) points relative to the entities @@ -52,12 +51,13 @@ struct phys_contact_point { #endif }; -struct phys_contact_constraint { +typedef struct ContactConstraint ContactConstraint; +struct ContactConstraint { u64 last_phys_iteration; /* To avoid checking collisions for the same constraint twice in one tick */ b32 skip_solve; b32 wrong_dir; - struct sim_ent_id e0; - struct sim_ent_id e1; + EntId e0; + EntId e1; f32 inv_m0; f32 inv_m1; f32 inv_i0; @@ -65,7 +65,7 @@ struct phys_contact_constraint { V2 normal; /* Normal vector of collision from e0 -> e1 */ u64 last_iteration; - struct phys_contact_point points[2]; + ContactPoint points[2]; u32 num_points; f32 friction; @@ -73,12 +73,13 @@ struct phys_contact_constraint { f32 pushout_velocity; }; -struct phys_collision_debug { - struct sim_ent_id e0; - struct sim_ent_id e1; +typedef struct CollisionDebugData CollisionDebugData; +struct CollisionDebugData { + EntId e0; + EntId e1; CLD_CollisionResult res; - struct phys_contact_point points[2]; + ContactPoint points[2]; u32 num_points; V2 closest0; @@ -88,26 +89,28 @@ struct phys_collision_debug { Xform xf1; }; -void phys_create_and_update_contacts(struct phys_step_ctx *ctx, f32 elapsed_dt, u64 phys_iteration); -void phys_prepare_contacts(struct phys_step_ctx *ctx, u64 phys_iteration); -void phys_warm_start_contacts(struct phys_step_ctx *ctx); -void phys_solve_contacts(struct phys_step_ctx *ctx, f32 dt, b32 apply_bias); +void phys_create_and_update_contacts(PhysStepCtx *ctx, f32 elapsed_dt, u64 phys_iteration); +void phys_prepare_contacts(PhysStepCtx *ctx, u64 phys_iteration); +void phys_warm_start_contacts(PhysStepCtx *ctx); +void phys_solve_contacts(PhysStepCtx *ctx, f32 dt, b32 apply_bias); /* ========================== * * Motor joint * ========================== */ -struct phys_motor_joint_def { - struct sim_ent_id e0; - struct sim_ent_id e1; +typedef struct MotorJointDesc MotorJointDesc; +struct MotorJointDesc { + EntId e0; + EntId e1; f32 correction_rate; f32 max_force; f32 max_torque; }; -struct phys_motor_joint { - struct sim_ent_id e0; - struct sim_ent_id e1; +typedef struct MotorJoint MotorJoint; +struct MotorJoint { + EntId e0; + EntId e1; f32 correction_rate; f32 max_force; f32 max_torque; @@ -127,18 +130,19 @@ struct phys_motor_joint { f32 angular_mass; }; -struct phys_motor_joint_def phys_motor_joint_def_init(void); -struct phys_motor_joint phys_motor_joint_from_def(struct phys_motor_joint_def def); -void phys_prepare_motor_joints(struct phys_step_ctx *ctx); -void phys_warm_start_motor_joints(struct phys_step_ctx *ctx); -void phys_solve_motor_joints(struct phys_step_ctx *ctx, f32 dt); +MotorJointDesc phys_motor_joint_def_init(void); +MotorJoint phys_motor_joint_from_def(MotorJointDesc def); +void phys_prepare_motor_joints(PhysStepCtx *ctx); +void phys_warm_start_motor_joints(PhysStepCtx *ctx); +void phys_solve_motor_joints(PhysStepCtx *ctx, f32 dt); /* ========================== * * Mouse joint * ========================== */ -struct phys_mouse_joint_def { - struct sim_ent_id target; +typedef struct MouseJointDesc MouseJointDesc; +struct MouseJointDesc { + EntId target; V2 point_local_start; V2 point_end; f32 linear_spring_hz; @@ -148,8 +152,9 @@ struct phys_mouse_joint_def { f32 max_force; }; -struct phys_mouse_joint { - struct sim_ent_id target; +typedef struct MouseJoint MouseJoint; +struct MouseJoint { + EntId target; V2 point_local_start; V2 point_end; f32 linear_spring_hz; @@ -167,19 +172,20 @@ struct phys_mouse_joint { Xform linear_mass_xf; }; -struct phys_mouse_joint_def phys_mouse_joint_def_init(void); -struct phys_mouse_joint phys_mouse_joint_from_def(struct phys_mouse_joint_def def); -void phys_prepare_mouse_joints(struct phys_step_ctx *ctx); -void phys_warm_start_mouse_joints(struct phys_step_ctx *ctx); -void phys_solve_mouse_joints(struct phys_step_ctx *ctx, f32 dt); +MouseJointDesc phys_mouse_joint_def_init(void); +MouseJoint phys_mouse_joint_from_def(MouseJointDesc def); +void phys_prepare_mouse_joints(PhysStepCtx *ctx); +void phys_warm_start_mouse_joints(PhysStepCtx *ctx); +void phys_solve_mouse_joints(PhysStepCtx *ctx, f32 dt); /* ========================== * * Weld joint * ========================== */ -struct phys_weld_joint_def { - struct sim_ent_id e0; - struct sim_ent_id e1; +typedef struct WeldJointDesc WeldJointDesc; +struct WeldJointDesc { + EntId e0; + EntId e1; /* The xform that transforms a point in e0's space into the desired e1 space * (IE `xf` * V2FromXY(0, 0) should evaluate to the local point that e1's origin will lie) */ @@ -191,9 +197,10 @@ struct phys_weld_joint_def { f32 angular_spring_damp; }; -struct phys_weld_joint { - struct sim_ent_id e0; - struct sim_ent_id e1; +typedef struct WeldJoint WeldJoint; +struct WeldJoint { + EntId e0; + EntId e1; Xform xf0_to_xf1; f32 linear_spring_hz; @@ -212,33 +219,33 @@ struct phys_weld_joint { f32 angular_impulse1; }; -struct phys_weld_joint_def phys_weld_joint_def_init(void); -struct phys_weld_joint phys_weld_joint_from_def(struct phys_weld_joint_def def); -void phys_prepare_weld_joints(struct phys_step_ctx *ctx); -void phys_warm_start_weld_joints(struct phys_step_ctx *ctx); -void phys_solve_weld_joints(struct phys_step_ctx *ctx, f32 dt); +WeldJointDesc phys_weld_joint_def_init(void); +WeldJoint phys_weld_joint_from_def(WeldJointDesc def); +void phys_prepare_weld_joints(PhysStepCtx *ctx); +void phys_warm_start_weld_joints(PhysStepCtx *ctx); +void phys_solve_weld_joints(PhysStepCtx *ctx, f32 dt); /* ========================== * * Integration * ========================== */ -void phys_integrate_forces(struct phys_step_ctx *ctx, f32 dt); -void phys_integrate_velocities(struct phys_step_ctx *ctx, f32 dt); +void phys_integrate_forces(PhysStepCtx *ctx, f32 dt); +void phys_integrate_velocities(PhysStepCtx *ctx, f32 dt); /* ========================== * * Earliest time of impact * ========================== */ -f32 phys_determine_earliest_toi(struct phys_step_ctx *ctx, f32 step_dt, f32 tolerance, u32 max_iterations); +f32 phys_determine_earliest_toi(PhysStepCtx *ctx, f32 step_dt, f32 tolerance, u32 max_iterations); /* ========================== * * Space * ========================== */ -void phys_update_aabbs(struct phys_step_ctx *ctx); +void phys_update_aabbs(PhysStepCtx *ctx); /* ========================== * * Step * ========================== */ -void phys_step(struct phys_step_ctx *ctx, f32 timestep); +void phys_step(PhysStepCtx *ctx, f32 timestep); diff --git a/src/sim/sim_space.c b/src/sim/sim_space.c index e68c3812..593d59ed 100644 --- a/src/sim/sim_space.c +++ b/src/sim/sim_space.c @@ -1,12 +1,12 @@ /* FIXME: Default space entry & cell pointers to nil */ /* Offset in bytes from start of space struct to start of entry array (assume adjacently allocated) */ -#define SPACE_ENTRIES_OFFSET (sizeof(struct space) + (sizeof(struct space) % alignof(struct space_entry))) +#define SPACE_ENTRIES_OFFSET (sizeof(Space) + (sizeof(Space) % alignof(SpaceEntry))) /* Accessed via sim_ent_nil() */ -READONLY struct space_entry _g_space_entry_nil = { .valid = 0 }; -READONLY struct space_cell _g_space_cell_nil = { .valid = 0 }; -READONLY struct space _g_space_nil = { .valid = 0 }; +READONLY SpaceEntry _g_space_entry_nil = { .valid = 0 }; +READONLY SpaceCell _g_space_cell_nil = { .valid = 0 }; +READONLY Space _g_space_nil = { .valid = 0 }; /* ========================== * * Space alloc @@ -15,50 +15,50 @@ READONLY struct space _g_space_nil = { .valid = 0 }; /* NOTE: * The number of bins determines how often tiles will collide in the spatial hash. * For example, at `num_bins_sqrt` = 256 (65536 bins), tiles <1, 1>, <1, 257>, and <257, 257> will collide. */ -struct space *space_alloc(f32 cell_size, u32 num_bins_sqrt) +Space *space_alloc(f32 cell_size, u32 num_bins_sqrt) { - struct space *space; + Space *space; { Arena *arena = arena_alloc(GIBI(64)); - space = arena_push(arena, struct space); + space = arena_push(arena, Space); space->entry_arena = arena; } space->valid = 1; - space->entries = arena_push_dry(space->entry_arena, struct space_entry); + space->entries = arena_push_dry(space->entry_arena, SpaceEntry); space->cell_arena = arena_alloc(GIBI(64)); space->cell_size = cell_size; space->num_bins = num_bins_sqrt * num_bins_sqrt; space->num_bins_sqrt = num_bins_sqrt; - space->bins = arena_push_array(space->cell_arena, struct space_cell_bin, space->num_bins); + space->bins = arena_push_array(space->cell_arena, SpaceCellBin, space->num_bins); return space; } -void space_release(struct space *space) +void space_release(Space *space) { arena_release(space->cell_arena); arena_release(space->entry_arena); } -void space_reset(struct space *space) +void space_reset(Space *space) { arena_pop_to(space->entry_arena, (u64)space->entries - (u64)arena_base(space->entry_arena)); arena_reset(space->cell_arena); - space->bins = arena_push_array(space->cell_arena, struct space_cell_bin, space->num_bins); + space->bins = arena_push_array(space->cell_arena, SpaceCellBin, space->num_bins); space->num_entries_reserved = 0; space->first_free_cell = 0; space->first_free_cell_node = 0; space->first_free_entry = 0; } -struct space *space_from_entry(struct space_entry *entry) +Space *space_from_entry(SpaceEntry *entry) { if (entry->valid) { u64 first_entry_addr = (u64)(entry - entry->handle.idx); - struct space *space = (struct space *)(first_entry_addr - SPACE_ENTRIES_OFFSET); - ASSERT(space->entries == (struct space_entry *)first_entry_addr); + Space *space = (Space *)(first_entry_addr - SPACE_ENTRIES_OFFSET); + ASSERT(space->entries == (SpaceEntry *)first_entry_addr); return space; } else { return space_nil(); @@ -78,7 +78,7 @@ INTERNAL V2i32 world_to_cell_coords(f32 cell_size, V2 world_pos) return V2i32FromXY((i32)x, (i32)y); } -INTERNAL i32 cell_coords_to_bin_index(struct space *space, V2i32 cell_pos) +INTERNAL i32 cell_coords_to_bin_index(Space *space, V2i32 cell_pos) { i32 num_bins_sqrt = space->num_bins_sqrt; @@ -100,12 +100,12 @@ INTERNAL i32 cell_coords_to_bin_index(struct space *space, V2i32 cell_pos) return bin_index; } -struct space_cell *space_get_cell(struct space *space, V2i32 cell_pos) +SpaceCell *space_get_cell(Space *space, V2i32 cell_pos) { i32 bin_index = cell_coords_to_bin_index(space, cell_pos); - struct space_cell_bin *bin = &space->bins[bin_index]; - struct space_cell *res = space_cell_nil(); - for (struct space_cell *n = bin->first_cell; n; n = n->next_in_bin) { + SpaceCellBin *bin = &space->bins[bin_index]; + SpaceCell *res = space_cell_nil(); + for (SpaceCell *n = bin->first_cell; n; n = n->next_in_bin) { if (v2i32_eq(n->pos, cell_pos)) { res = n; break; @@ -114,15 +114,15 @@ struct space_cell *space_get_cell(struct space *space, V2i32 cell_pos) return res; } -INTERNAL void space_cell_node_alloc(V2i32 cell_pos, struct space_entry *entry) +INTERNAL void space_cell_node_alloc(V2i32 cell_pos, SpaceEntry *entry) { - struct space *space = space_from_entry(entry); + Space *space = space_from_entry(entry); i32 bin_index = cell_coords_to_bin_index(space, cell_pos); - struct space_cell_bin *bin = &space->bins[bin_index]; + SpaceCellBin *bin = &space->bins[bin_index]; /* Find existing cell */ - struct space_cell *cell = 0; - for (struct space_cell *n = bin->first_cell; n; n = n->next_in_bin) { + SpaceCell *cell = 0; + for (SpaceCell *n = bin->first_cell; n; n = n->next_in_bin) { if (v2i32_eq(n->pos, cell_pos)) { cell = n; break; @@ -135,7 +135,7 @@ INTERNAL void space_cell_node_alloc(V2i32 cell_pos, struct space_entry *entry) cell = space->first_free_cell; space->first_free_cell = cell->next_free; } else { - cell = arena_push_no_zero(space->cell_arena, struct space_cell); + cell = arena_push_no_zero(space->cell_arena, SpaceCell); } MEMZERO_STRUCT(cell); if (bin->last_cell) { @@ -151,13 +151,13 @@ INTERNAL void space_cell_node_alloc(V2i32 cell_pos, struct space_entry *entry) } /* Allocate node */ - struct space_cell_node *node; + SpaceCellNode *node; { if (space->first_free_cell_node) { node = space->first_free_cell_node; space->first_free_cell_node = node->next_free; } else { - node = arena_push_no_zero(space->cell_arena, struct space_cell_node); + node = arena_push_no_zero(space->cell_arena, SpaceCellNode); } MEMZERO_STRUCT(node); } @@ -183,17 +183,17 @@ INTERNAL void space_cell_node_alloc(V2i32 cell_pos, struct space_entry *entry) entry->last_node = node; } -INTERNAL void space_cell_node_release(struct space_cell_node *n) +INTERNAL void space_cell_node_release(SpaceCellNode *n) { - struct space_cell *cell = n->cell; - struct space_entry *entry = n->entry; - struct space *space = space_from_entry(entry); - struct space_cell_bin *bin = cell->bin; + SpaceCell *cell = n->cell; + SpaceEntry *entry = n->entry; + Space *space = space_from_entry(entry); + SpaceCellBin *bin = cell->bin; /* Remove from entry list */ { - struct space_cell_node *prev = n->prev_in_entry; - struct space_cell_node *next = n->next_in_entry; + SpaceCellNode *prev = n->prev_in_entry; + SpaceCellNode *next = n->next_in_entry; if (prev) { prev->next_in_entry = next; } else { @@ -208,8 +208,8 @@ INTERNAL void space_cell_node_release(struct space_cell_node *n) /* Remove from cell list */ { - struct space_cell_node *prev = n->prev_in_cell; - struct space_cell_node *next = n->next_in_cell; + SpaceCellNode *prev = n->prev_in_cell; + SpaceCellNode *next = n->next_in_cell; if (prev) { prev->next_in_cell = next; } else { @@ -225,8 +225,8 @@ INTERNAL void space_cell_node_release(struct space_cell_node *n) /* If cell is now empty, release it */ if (!cell->first_node && !cell->last_node) { /* Remove from bin */ - struct space_cell *prev = cell->prev_in_bin; - struct space_cell *next = cell->next_in_bin; + SpaceCell *prev = cell->prev_in_bin; + SpaceCell *next = cell->next_in_bin; if (prev) { prev->next_in_bin = next; } else { @@ -253,12 +253,12 @@ INTERNAL void space_cell_node_release(struct space_cell_node *n) * Entry * ========================== */ -struct space_entry *space_entry_from_handle(struct space *space, struct space_entry_handle handle) +SpaceEntry *space_entry_from_handle(Space *space, SpaceEntryHandle handle) { - struct space_entry *entry = space_entry_nil(); + SpaceEntry *entry = space_entry_nil(); if (handle.gen > 0 && handle.idx < space->num_entries_reserved) { - struct space_entry *tmp = &space->entries[handle.idx]; + SpaceEntry *tmp = &space->entries[handle.idx]; if (tmp->handle.gen == handle.gen) { entry = tmp; } @@ -267,16 +267,16 @@ struct space_entry *space_entry_from_handle(struct space *space, struct space_en return entry; } -struct space_entry *space_entry_alloc(struct space *space, struct sim_ent_id ent) +SpaceEntry *space_entry_alloc(Space *space, EntId ent) { - struct space_entry *entry = 0; - struct space_entry_handle handle = ZI; + SpaceEntry *entry = 0; + SpaceEntryHandle handle = ZI; if (space->first_free_entry) { entry = space->first_free_entry; space->first_free_entry = entry->next_free; handle = entry->handle; } else { - entry = arena_push_no_zero(space->entry_arena, struct space_entry); + entry = arena_push_no_zero(space->entry_arena, SpaceEntry); handle.idx = space->num_entries_reserved; handle.gen = 1; ++space->num_entries_reserved; @@ -288,27 +288,27 @@ struct space_entry *space_entry_alloc(struct space *space, struct sim_ent_id ent return entry; } -void space_entry_release(struct space_entry *entry) +void space_entry_release(SpaceEntry *entry) { /* Release nodes */ - struct space_cell_node *n = entry->first_node; + SpaceCellNode *n = entry->first_node; while (n) { - struct space_cell_node *next = n->next_in_entry; + SpaceCellNode *next = n->next_in_entry; /* TODO: More efficient batch release that doesn't care about maintaining entry list */ space_cell_node_release(n); n = next; } - struct space *space = space_from_entry(entry); + Space *space = space_from_entry(entry); entry->next_free = space->first_free_entry; entry->valid = 0; ++entry->handle.gen; space->first_free_entry = entry; } -void space_entry_update_aabb(struct space_entry *entry, Aabb new_aabb) +void space_entry_update_aabb(SpaceEntry *entry, Aabb new_aabb) { - struct space *space = space_from_entry(entry); + Space *space = space_from_entry(entry); f32 cell_size = space->cell_size; V2i32 old_cell_p0 = V2i32FromXY(0, 0); @@ -323,13 +323,13 @@ void space_entry_update_aabb(struct space_entry *entry, Aabb new_aabb) V2i32 new_cell_p1 = world_to_cell_coords(cell_size, new_aabb.p1); /* Release outdated nodes */ - struct space_cell_node *n = entry->first_node; + SpaceCellNode *n = entry->first_node; while (n) { - struct space_cell *cell = n->cell; + SpaceCell *cell = n->cell; V2i32 cell_pos = cell->pos; if (cell_pos.x < new_cell_p0.x || cell_pos.x > new_cell_p1.x || cell_pos.y < new_cell_p0.y || cell_pos.y > new_cell_p1.y) { /* Cell is outside of new AABB */ - struct space_cell_node *next = n->next_in_entry; + SpaceCellNode *next = n->next_in_entry; space_cell_node_release(n); n = next; } else { @@ -354,9 +354,9 @@ void space_entry_update_aabb(struct space_entry *entry, Aabb new_aabb) * Iter * ========================== */ -struct space_iter space_iter_begin_aabb(struct space *space, Aabb aabb) +SpaceIter space_iter_begin_aabb(Space *space, Aabb aabb) { - struct space_iter iter = ZI; + SpaceIter iter = ZI; f32 cell_size = space->cell_size; iter.space = space; @@ -377,16 +377,16 @@ struct space_iter space_iter_begin_aabb(struct space *space, Aabb aabb) return iter; } -struct space_entry *space_iter_next(struct space_iter *iter) +SpaceEntry *space_iter_next(SpaceIter *iter) { - struct space *space = iter->space; + Space *space = iter->space; Aabb iter_aabb = iter->aabb; V2i32 cell_start = iter->cell_start; V2i32 cell_end = iter->cell_end; V2i32 cell_cur = iter->cell_cur; i32 span = cell_end.x - cell_start.x; - struct space_cell_node *next_node = 0; + SpaceCellNode *next_node = 0; if (cell_cur.x >= cell_start.x && cell_cur.x <= cell_end.x && cell_cur.y >= cell_start.y && cell_cur.y <= cell_end.y) { /* Started */ ASSERT(iter->prev != 0); @@ -398,7 +398,7 @@ struct space_entry *space_iter_next(struct space_iter *iter) for (;;) { if (next_node) { - struct space_entry *entry = next_node->entry; + SpaceEntry *entry = next_node->entry; Aabb entry_aabb = entry->aabb; if (collider_test_aabb(entry_aabb, iter_aabb)) { break; @@ -414,7 +414,7 @@ struct space_entry *space_iter_next(struct space_iter *iter) cell_cur.y += nexty; cell_cur.x += (cell_cur.x == 0); cell_cur.y += (cell_cur.y == 0); - struct space_cell *cell = space_get_cell(space, cell_cur); + SpaceCell *cell = space_get_cell(space, cell_cur); next_node = cell->first_node; } else { /* Reached end of iter */ diff --git a/src/sim/sim_space.h b/src/sim/sim_space.h index 956a5781..3b8c5ba4 100644 --- a/src/sim/sim_space.h +++ b/src/sim/sim_space.h @@ -1,104 +1,112 @@ -struct space_cell_bin; - -struct space_entry_handle { +typedef struct SpaceEntryHandle SpaceEntryHandle; +struct SpaceEntryHandle { u64 idx; u64 gen; }; -struct space_entry { +typedef struct SpaceCellNode SpaceCellNode; +typedef struct SpaceEntry SpaceEntry; +struct SpaceEntry { b32 valid; - struct space_entry_handle handle; + SpaceEntryHandle handle; - struct space_cell_node *first_node; - struct space_cell_node *last_node; + SpaceCellNode *first_node; + SpaceCellNode *last_node; Aabb aabb; - struct sim_ent_id ent; + EntId ent; - struct space_entry *next_free; + SpaceEntry *next_free; }; /* Links a cell to a entry. * Acts as both a node in the list of entries contained by the cell, and a node in the list of cells containing the entry. */ -struct space_cell_node { - struct space_entry *entry; - struct space_cell *cell; +typedef struct SpaceCell SpaceCell; +typedef struct SpaceCellNode SpaceCellNode; +struct SpaceCellNode { + SpaceEntry *entry; + SpaceCell *cell; /* For list of all entries contained by cell */ - struct space_cell_node *prev_in_cell; - struct space_cell_node *next_in_cell; + SpaceCellNode *prev_in_cell; + SpaceCellNode *next_in_cell; /* For list of all cells containing entry */ - struct space_cell_node *prev_in_entry; - struct space_cell_node *next_in_entry; + SpaceCellNode *prev_in_entry; + SpaceCellNode *next_in_entry; - struct space_cell_node *next_free; + SpaceCellNode *next_free; }; -struct space_cell { +typedef struct SpaceCellBin SpaceCellBin; +typedef struct SpaceCell SpaceCell; +struct SpaceCell { b32 valid; V2i32 pos; - struct space_cell_node *first_node; - struct space_cell_node *last_node; + SpaceCellNode *first_node; + SpaceCellNode *last_node; - struct space_cell_bin *bin; - struct space_cell *prev_in_bin; - struct space_cell *next_in_bin; + SpaceCellBin *bin; + SpaceCell *prev_in_bin; + SpaceCell *next_in_bin; - struct space_cell *next_free; + SpaceCell *next_free; }; -struct space_cell_bin { - struct space_cell *first_cell; - struct space_cell *last_cell; +typedef struct SpaceCellBin SpaceCellBin; +struct SpaceCellBin { + SpaceCell *first_cell; + SpaceCell *last_cell; }; -struct space { +typedef struct Space Space; +struct Space { b32 valid; f32 cell_size; Arena *cell_arena; - struct space_cell_bin *bins; + SpaceCellBin *bins; i32 num_bins; i32 num_bins_sqrt; - struct space_cell *first_free_cell; - struct space_cell_node *first_free_cell_node; + SpaceCell *first_free_cell; + SpaceCellNode *first_free_cell_node; Arena *entry_arena; u64 num_entries_reserved; - struct space_entry *entries; - struct space_entry *first_free_entry; + SpaceEntry *entries; + SpaceEntry *first_free_entry; }; -struct space_iter { +typedef struct SpaceIter SpaceIter; +struct SpaceIter { Aabb aabb; - struct space *space; + Space *space; V2i32 cell_start; V2i32 cell_end; V2i32 cell_cur; - struct space_cell_node *prev; + SpaceCellNode *prev; }; /* ========================== * * Nil * ========================== */ -INLINE struct space_entry *space_entry_nil(void) +INLINE SpaceEntry *space_entry_nil(void) { - extern READONLY struct space_entry _g_space_entry_nil; + extern READONLY SpaceEntry _g_space_entry_nil; return &_g_space_entry_nil; } -INLINE struct space_cell *space_cell_nil(void) +INLINE SpaceCell *space_cell_nil(void) { - extern READONLY struct space_cell _g_space_cell_nil; + extern READONLY SpaceCell _g_space_cell_nil; return &_g_space_cell_nil; } -INLINE struct space *space_nil(void) +INLINE Space *space_nil(void) { - extern READONLY struct space _g_space_nil; + extern READONLY Space _g_space_nil; return &_g_space_nil; } @@ -106,31 +114,31 @@ INLINE struct space *space_nil(void) * Space * ========================== */ -struct space *space_alloc(f32 cell_size, u32 num_bins_sqrt); -void space_release(struct space *space); -void space_reset(struct space *space); +Space *space_alloc(f32 cell_size, u32 num_bins_sqrt); +void space_release(Space *space); +void space_reset(Space *space); -struct space *space_from_entry(struct space_entry *entry); +Space *space_from_entry(SpaceEntry *entry); /* ========================== * * Cell * ========================== */ -struct space_cell *space_get_cell(struct space *space, V2i32 cell_pos); +SpaceCell *space_get_cell(Space *space, V2i32 cell_pos); /* ========================== * * Entry * ========================== */ -struct space_entry *space_entry_from_handle(struct space *space, struct space_entry_handle handle); -struct space_entry *space_entry_alloc(struct space *space, struct sim_ent_id entity); -void space_entry_release(struct space_entry *entry); -void space_entry_update_aabb(struct space_entry *entry, Aabb new_aabb); +SpaceEntry *space_entry_from_handle(Space *space, SpaceEntryHandle handle); +SpaceEntry *space_entry_alloc(Space *space, EntId entity); +void space_entry_release(SpaceEntry *entry); +void space_entry_update_aabb(SpaceEntry *entry, Aabb new_aabb); /* ========================== * * Iter * ========================== */ -struct space_iter space_iter_begin_aabb(struct space *space, Aabb aabb); -struct space_entry *space_iter_next(struct space_iter *iter); +SpaceIter space_iter_begin_aabb(Space *space, Aabb aabb); +SpaceEntry *space_iter_next(SpaceIter *iter); #define space_iter_end(i) diff --git a/src/sim/sim_step.c b/src/sim/sim_step.c index 2b81d880..3abd2b11 100644 --- a/src/sim/sim_step.c +++ b/src/sim/sim_step.c @@ -2,19 +2,19 @@ * Sim accel * ========================== */ -struct sim_accel sim_accel_alloc(void) +SimAccel sim_accel_alloc(void) { - struct sim_accel accel = ZI; + SimAccel accel = ZI; accel.space = space_alloc(SPACE_CELL_SIZE, SPACE_CELL_BINS_SQRT); return accel; } -void sim_accel_release(struct sim_accel *accel) +void sim_accel_release(SimAccel *accel) { space_release(accel->space); } -void sim_accel_reset(struct sim_snapshot *ss, struct sim_accel *accel) +void sim_accel_reset(Snapshot *ss, SimAccel *accel) { space_reset(accel->space); @@ -358,7 +358,7 @@ INTERNAL void test_spawn_entities4(struct sim_ent *parent, V2 pos) e->sprite_tint = RGB32_F(1, 1, 1); } -INTERNAL void test_spawn_tile(struct sim_snapshot *world, V2 world_pos) +INTERNAL void test_spawn_tile(Snapshot *world, V2 world_pos) { #if 0 struct sim_ent *e = sim_ent_alloc_sync_src(parent); @@ -382,8 +382,8 @@ INTERNAL void test_spawn_tile(struct sim_snapshot *world, V2 world_pos) e->sprite_tint = COLOR_RED; { - struct sprite_scope *scope = sprite_scope_begin(); - struct sprite_sheet *sheet = sprite_sheet_from_tag_await(scope, e->sprite); + S_Scope *scope = sprite_scope_begin(); + S_Sheet *sheet = sprite_sheet_from_tag_await(scope, e->sprite); e->sprite_local_xform = XFORM_TRS(.s = v2_div(sheet->frame_size, PIXELS_PER_UNIT)); sprite_scope_end(scope); } @@ -431,7 +431,7 @@ INTERNAL SORT_COMPARE_FUNC_DEF(tile_chunk_sort_y, arg_a, arg_b, udata) return res; } -INTERNAL void test_generate_walls(struct sim_snapshot *world) +INTERNAL void test_generate_walls(Snapshot *world) { __prof; TempArena scratch = scratch_begin_no_conflict(); @@ -495,12 +495,12 @@ INTERNAL void test_generate_walls(struct sim_snapshot *world) i32 wall_dir = -1; for (i32 tile_x = 0; tile_x < x_iterations; ++tile_x) { i32 desired_wall_dir = -1; - enum sim_tile_kind tile = SIM_TILE_KIND_NONE; + TileKind tile = SIM_TILE_KIND_NONE; if (tile_x < SIM_TILES_PER_CHUNK_SQRT && tile_y < SIM_TILES_PER_CHUNK_SQRT) { tile = sim_get_chunk_tile(chunk, V2i32FromXY(tile_x, tile_y)); } if (tile_x < SIM_TILES_PER_CHUNK_SQRT) { - enum sim_tile_kind top_tile = SIM_TILE_KIND_NONE; + TileKind top_tile = SIM_TILE_KIND_NONE; if (tile_y == 0) { if (top_chunk->valid) { V2i32 top_tile_local_index = V2i32FromXY(tile_x, SIM_TILES_PER_CHUNK_SQRT - 1); @@ -584,13 +584,13 @@ INTERNAL void test_generate_walls(struct sim_snapshot *world) i32 wall_dir = -1; for (i32 tile_y = 0; tile_y < y_iterations; ++tile_y) { i32 desired_wall_dir = -1; - enum sim_tile_kind tile = SIM_TILE_KIND_NONE; + TileKind tile = SIM_TILE_KIND_NONE; if (tile_x < SIM_TILES_PER_CHUNK_SQRT && tile_y < SIM_TILES_PER_CHUNK_SQRT) { tile = sim_get_chunk_tile(chunk, V2i32FromXY(tile_x, tile_y)); } if (tile_y < SIM_TILES_PER_CHUNK_SQRT) { - enum sim_tile_kind left_tile = SIM_TILE_KIND_NONE; + TileKind left_tile = SIM_TILE_KIND_NONE; if (tile_x == 0) { if (left_chunk->valid) { V2i32 left_tile_local_index = V2i32FromXY(SIM_TILES_PER_CHUNK_SQRT - 1, tile_y); @@ -695,9 +695,9 @@ INTERNAL void test_generate_walls(struct sim_snapshot *world) -INTERNAL void test_clear_level(struct sim_step_ctx *ctx) +INTERNAL void test_clear_level(SimStepCtx *ctx) { - struct sim_snapshot *world = ctx->world; + Snapshot *world = ctx->world; for (u64 j = 0; j < world->num_ents_reserved; ++j) { struct sim_ent *ent = &world->ents[j]; if (ent->valid) { @@ -712,7 +712,7 @@ INTERNAL void test_clear_level(struct sim_step_ctx *ctx) INTERNAL PHYS_COLLISION_CALLBACK_FUNC_DEF(on_collision, data, step_ctx) { - struct sim_snapshot *world = step_ctx->world; + Snapshot *world = step_ctx->world; struct sim_ent *e0 = sim_ent_from_id(world, data->e0); struct sim_ent *e1 = sim_ent_from_id(world, data->e1); struct sim_ent *root = sim_ent_from_id(world, SIM_ENT_ROOT_ID); @@ -836,19 +836,19 @@ INTERNAL PHYS_COLLISION_CALLBACK_FUNC_DEF(on_collision, data, step_ctx) * Update * ========================== */ -void sim_step(struct sim_step_ctx *ctx) +void sim_step(SimStepCtx *ctx) { __prof; TempArena scratch = scratch_begin_no_conflict(); b32 is_master = ctx->is_master; - struct sim_snapshot *world = ctx->world; + Snapshot *world = ctx->world; - struct sim_client_store *client_store = world->client->store; - struct sim_client *world_client = world->client; - struct sim_client *user_input_client = ctx->user_input_client; - struct sim_client *publish_client = ctx->publish_client; - struct sim_client *master_client = ctx->master_client; + ClientStore *client_store = world->client->store; + Client *world_client = world->client; + Client *user_input_client = ctx->user_input_client; + Client *publish_client = ctx->publish_client; + Client *master_client = ctx->master_client; i64 sim_dt_ns = ctx->sim_dt_ns; @@ -860,7 +860,7 @@ void sim_step(struct sim_step_ctx *ctx) world->sim_time_ns += world->sim_dt_ns; f32 sim_dt = SECONDS_FROM_NS(world->sim_dt_ns); - struct sprite_scope *sprite_frame_scope = sprite_scope_begin(); + S_Scope *sprite_frame_scope = sprite_scope_begin(); struct sim_ent *root = sim_ent_from_id(world, SIM_ENT_ROOT_ID); root->owner = world->client->player_id; @@ -872,7 +872,7 @@ void sim_step(struct sim_step_ctx *ctx) { /* FIXME: Ensure only cmds are synced to master player */ for (u64 client_index = 0; client_index < client_store->num_clients_reserved; ++client_index) { - struct sim_client *client = &client_store->clients[client_index]; + Client *client = &client_store->clients[client_index]; if (client->valid && client != master_client && client != world_client && client != publish_client) { struct sim_ent *player = sim_ent_from_id(world, client->player_id); @@ -904,7 +904,7 @@ void sim_step(struct sim_step_ctx *ctx) /* Sync ents from client */ if (player->valid) { - struct sim_snapshot *src_ss = sim_snapshot_from_tick(client, world->tick); + Snapshot *src_ss = sim_snapshot_from_tick(client, world->tick); if (src_ss->valid) { sim_snapshot_sync_ents(world, src_ss, player->id, 0); } @@ -983,7 +983,7 @@ void sim_step(struct sim_step_ctx *ctx) continue; } - enum sim_cmd_kind kind = cmd_ent->cmd_kind; + CmdKind kind = cmd_ent->cmd_kind; switch (kind) { case SIM_CMD_KIND_CONTROL: { @@ -991,8 +991,8 @@ void sim_step(struct sim_step_ctx *ctx) persist_cmd = 1; /* Process control cmd for player */ - struct sim_control old_control = player->player_control; - struct sim_control *control = &player->player_control; + ControlData old_control = player->player_control; + ControlData *control = &player->player_control; *control = cmd_ent->cmd_control; { u32 flags = control->flags; @@ -1170,11 +1170,11 @@ void sim_step(struct sim_step_ctx *ctx) if (!sim_ent_should_simulate(ent)) continue; if (sprite_tag_is_nil(ent->sprite)) continue; - struct sprite_sheet *sheet = sprite_sheet_from_tag_await(sprite_frame_scope, ent->sprite); + S_Sheet *sheet = sprite_sheet_from_tag_await(sprite_frame_scope, ent->sprite); /* Update animation */ { - struct sprite_sheet_span span = sprite_sheet_get_span(sheet, ent->sprite_span_name); + S_SheetSpan span = sprite_sheet_get_span(sheet, ent->sprite_span_name); if (ent->animation_last_frame_change_time_ns == 0) { ent->animation_last_frame_change_time_ns = SECONDS_FROM_NS(world->sim_time_ns); } @@ -1186,7 +1186,7 @@ void sim_step(struct sim_step_ctx *ctx) } if (span.end > span.start) { - struct sprite_sheet_frame frame = sprite_sheet_get_frame(sheet, frame_index); + S_SheetFrame frame = sprite_sheet_get_frame(sheet, frame_index); while (time_in_frame > frame.duration) { time_in_frame -= frame.duration; ++frame_index; @@ -1205,7 +1205,7 @@ void sim_step(struct sim_step_ctx *ctx) #if 0 /* Update sprite local xform */ { - struct sprite_sheet_slice slice = sprite_sheet_get_slice(sheet, LIT("pivot"), ent->animation_frame); + S_SheetSlice slice = sprite_sheet_get_slice(sheet, LIT("pivot"), ent->animation_frame); V2 sprite_size = v2_div(sheet->frame_size, (f32)PIXELS_PER_UNIT); V2 dir = v2_mul_v2(sprite_size, slice.dir); @@ -1223,7 +1223,7 @@ void sim_step(struct sim_step_ctx *ctx) if (ent->sprite_collider_slice.len > 0) { Xform cxf = ent->sprite_local_xform; - struct sprite_sheet_slice slice = sprite_sheet_get_slice(sheet, ent->sprite_collider_slice, ent->animation_frame); + S_SheetSlice slice = sprite_sheet_get_slice(sheet, ent->sprite_collider_slice, ent->animation_frame); ent->local_collider = collider_from_quad(xform_mul_quad(cxf, quad_from_rect(slice.rect))); } @@ -1273,12 +1273,12 @@ void sim_step(struct sim_step_ctx *ctx) if (!sim_ent_has_prop(ent, SEPROP_ATTACHED)) continue; struct sim_ent *parent = sim_ent_from_id(world, ent->parent); - struct sprite_tag parent_sprite = parent->sprite; - struct sprite_sheet *parent_sheet = sprite_sheet_from_tag_await(sprite_frame_scope, parent_sprite); + S_Tag parent_sprite = parent->sprite; + S_Sheet *parent_sheet = sprite_sheet_from_tag_await(sprite_frame_scope, parent_sprite); Xform parent_sprite_xf = parent->sprite_local_xform; - struct sprite_sheet_slice attach_slice = sprite_sheet_get_slice(parent_sheet, ent->attach_slice, parent->animation_frame); + S_SheetSlice attach_slice = sprite_sheet_get_slice(parent_sheet, ent->attach_slice, parent->animation_frame); V2 attach_pos = xform_mul_v2(parent_sprite_xf, attach_slice.center); V2 attach_dir = xform_basis_mul_v2(parent_sprite_xf, attach_slice.dir); @@ -1297,7 +1297,7 @@ void sim_step(struct sim_step_ctx *ctx) if (!sim_ent_should_simulate(ent)) continue; if (sim_ent_has_prop(ent, SEPROP_CONTROLLED)) { - struct sim_control *control = &ent->control; + ControlData *control = &ent->control; u32 flags = control->flags; if (flags & SIM_CONTROL_FLAG_FIRE) { struct sim_ent *equipped = sim_ent_from_id(world, ent->equipped); @@ -1350,11 +1350,11 @@ void sim_step(struct sim_step_ctx *ctx) /* Fire smg */ if (sim_ent_has_prop(ent, SEPROP_WEAPON_SMG)) { if (primary_triggered) { - struct sprite_tag sprite = ent->sprite; + S_Tag sprite = ent->sprite; u32 animation_frame = ent->animation_frame; - struct sprite_sheet *sheet = sprite_sheet_from_tag_await(sprite_frame_scope, sprite); + S_Sheet *sheet = sprite_sheet_from_tag_await(sprite_frame_scope, sprite); Xform sprite_local_xform = ent->sprite_local_xform; - struct sprite_sheet_slice out_slice = sprite_sheet_get_slice(sheet, LIT("out"), animation_frame); + S_SheetSlice out_slice = sprite_sheet_get_slice(sheet, LIT("out"), animation_frame); V2 rel_pos = xform_mul_v2(sprite_local_xform, out_slice.center); V2 rel_dir = xform_basis_mul_v2(sprite_local_xform, out_slice.dir); @@ -1397,11 +1397,11 @@ void sim_step(struct sim_step_ctx *ctx) /* Fire launcher */ if (sim_ent_has_prop(ent, SEPROP_WEAPON_LAUNCHER)) { if (primary_triggered) { - struct sprite_tag sprite = ent->sprite; + S_Tag sprite = ent->sprite; u32 animation_frame = ent->animation_frame; - struct sprite_sheet *sheet = sprite_sheet_from_tag_await(sprite_frame_scope, sprite); + S_Sheet *sheet = sprite_sheet_from_tag_await(sprite_frame_scope, sprite); Xform sprite_local_xform = ent->sprite_local_xform; - struct sprite_sheet_slice out_slice = sprite_sheet_get_slice(sheet, LIT("out"), animation_frame); + S_SheetSlice out_slice = sprite_sheet_get_slice(sheet, LIT("out"), animation_frame); V2 rel_pos = xform_mul_v2(sprite_local_xform, out_slice.center); V2 rel_dir = xform_basis_mul_v2(sprite_local_xform, out_slice.dir); @@ -1458,7 +1458,7 @@ void sim_step(struct sim_step_ctx *ctx) Xform xf0_to_xf1 = xform_mul(xform_invert(xf0), xf1); sim_ent_enable_prop(joint_ent, SEPROP_WELD_JOINT); - struct phys_weld_joint_def def = phys_weld_joint_def_init(); + WeldJointDesc def = phys_weld_joint_def_init(); def.e0 = ent->id; def.e1 = target->id; def.xf = xf0_to_xf1; @@ -1498,7 +1498,7 @@ void sim_step(struct sim_step_ctx *ctx) ent->move_joint = joint_ent->id; sim_ent_enable_prop(joint_ent, SEPROP_MOTOR_JOINT); - struct phys_motor_joint_def def = phys_motor_joint_def_init(); + MotorJointDesc def = phys_motor_joint_def_init(); def.e0 = joint_ent->id; /* Re-using joint entity as e0 */ def.e1 = ent->id; def.correction_rate = 0; @@ -1539,7 +1539,7 @@ void sim_step(struct sim_step_ctx *ctx) sim_ent_enable_prop(joint_ent, SEPROP_ACTIVE); ent->aim_joint = joint_ent->id; - struct phys_motor_joint_def def = phys_motor_joint_def_init(); + MotorJointDesc def = phys_motor_joint_def_init(); def.e0 = joint_ent->id; /* Re-using joint entity as e0 */ def.e1 = ent->id; def.max_force = 0; @@ -1561,8 +1561,8 @@ void sim_step(struct sim_step_ctx *ctx) V2 sprite_hold_pos; V2 sprite_hold_dir; { - struct sprite_sheet *sheet = sprite_sheet_from_tag_await(sprite_frame_scope, ent->sprite); - struct sprite_sheet_slice slice = sprite_sheet_get_slice(sheet, LIT("attach.wep"), ent->animation_frame); + S_Sheet *sheet = sprite_sheet_from_tag_await(sprite_frame_scope, ent->sprite); + S_SheetSlice slice = sprite_sheet_get_slice(sheet, LIT("attach.wep"), ent->animation_frame); sprite_hold_pos = slice.center; sprite_hold_dir = slice.dir; } @@ -1624,7 +1624,7 @@ void sim_step(struct sim_step_ctx *ctx) struct sim_ent *joint_ent = sim_ent_from_id(world, ent->ground_friction_joint); - struct phys_motor_joint_def def = phys_motor_joint_def_init(); + MotorJointDesc def = phys_motor_joint_def_init(); def.e0 = root->id; def.e1 = ent->id; def.correction_rate = 0; @@ -1678,7 +1678,7 @@ void sim_step(struct sim_step_ctx *ctx) } Xform xf = sim_ent_get_xform(target_ent); - struct phys_mouse_joint_def def = phys_mouse_joint_def_init(); + MouseJointDesc def = phys_mouse_joint_def_init(); def.target = target_ent->id; if (sim_ent_id_eq(joint_ent->mouse_joint_data.target, target_ent->id)) { def.point_local_start = joint_ent->mouse_joint_data.point_local_start; @@ -1703,7 +1703,7 @@ void sim_step(struct sim_step_ctx *ctx) * ========================== */ { - struct phys_step_ctx phys = ZI; + PhysStepCtx phys = ZI; phys.sim_step_ctx = ctx; phys.collision_callback = on_collision; phys_step(&phys, sim_dt); @@ -1916,8 +1916,8 @@ void sim_step(struct sim_step_ctx *ctx) * ========================== */ if (publish_client->valid && world->tick > publish_client->last_tick) { - struct sim_snapshot *prev_pub_world = sim_snapshot_from_tick(publish_client, publish_client->last_tick); - struct sim_snapshot *pub_world = sim_snapshot_alloc(publish_client, prev_pub_world, world->tick); + Snapshot *prev_pub_world = sim_snapshot_from_tick(publish_client, publish_client->last_tick); + Snapshot *pub_world = sim_snapshot_alloc(publish_client, prev_pub_world, world->tick); /* Sync */ sim_snapshot_sync_ents(pub_world, world, world_client->player_id, 0); diff --git a/src/sim/sim_step.h b/src/sim/sim_step.h index ae3ee92b..a4d0aca4 100644 --- a/src/sim/sim_step.h +++ b/src/sim/sim_step.h @@ -1,7 +1,3 @@ -struct space; -struct sim_snapshot; -struct sim_snapshot_list; - /* ========================== * * Sim accel * ========================== */ @@ -9,29 +5,31 @@ struct sim_snapshot_list; /* Structure used to accelerate up entity lookup (rebuilt every step) */ /* TODO: Remove this and do something better. Just a hack to de-couple old sim ctx from step. */ -struct sim_accel { - struct space *space; +typedef struct SimAccel SimAccel; +struct SimAccel { + Space *space; }; -struct sim_accel sim_accel_alloc(void); -void sim_accel_release(struct sim_accel *accel); -void sim_accel_reset(struct sim_snapshot *ss, struct sim_accel *accel); +SimAccel sim_accel_alloc(void); +void sim_accel_release(SimAccel *accel); +void sim_accel_reset(Snapshot *ss, SimAccel *accel); /* ========================== * * Sim step * ========================== */ -struct sim_step_ctx { +typedef struct SimStepCtx SimStepCtx; +struct SimStepCtx { b32 is_master; - struct sim_accel *accel; + SimAccel *accel; RandState rand; /* TODO: Replace with per-sim rand for deterministic rng */ - struct sim_snapshot *world; /* The world to simulate */ + Snapshot *world; /* The world to simulate */ i64 sim_dt_ns; /* How much sim time should progress */ - struct sim_client *user_input_client; /* The client that contains input from the user thread */ - struct sim_client *master_client; /* The master client to read snapshots from (nil if world is master) */ - struct sim_client *publish_client; /* The publish client to write syncable state to (nil if skipping publish) */ + Client *user_input_client; /* The client that contains input from the user thread */ + Client *master_client; /* The master client to read snapshots from (nil if world is master) */ + Client *publish_client; /* The publish client to write syncable state to (nil if skipping publish) */ }; -void sim_step(struct sim_step_ctx *ctx); +void sim_step(SimStepCtx *ctx); diff --git a/src/sound/sound.h b/src/sound/sound.h index ef384e10..38ce369e 100644 --- a/src/sound/sound.h +++ b/src/sound/sound.h @@ -2,7 +2,7 @@ #define SOUND_H #include "../base/base.h" -#include "../sys/sys.h" +#include "../platform/platform.h" #include "../mp3/mp3.h" #include "../resource/resource.h" #include "../asset_cache/asset_cache.h" diff --git a/src/sound/sound_core.c b/src/sound/sound_core.c index 6ac432f2..9008b3b1 100644 --- a/src/sound/sound_core.c +++ b/src/sound/sound_core.c @@ -12,7 +12,7 @@ struct sound_task_params { struct sound_task_params_store { struct sound_task_params *head_free; Arena *arena; - struct snc_mutex mutex; + P_Mutex mutex; }; /* ========================== * @@ -27,12 +27,12 @@ GLOBAL struct { * Startup * ========================== */ -struct sound_startup_receipt sound_startup(AC_StartupReceipt *asset_cache_sr) +SND_StartupReceipt sound_startup(AC_StartupReceipt *asset_cache_sr) { __prof; (UNUSED)asset_cache_sr; G.params.arena = arena_alloc(GIBI(64)); - return (struct sound_startup_receipt) { 0 }; + return (SND_StartupReceipt) { 0 }; } /* ========================== * @@ -43,7 +43,7 @@ INTERNAL struct sound_task_params *sound_task_params_alloc(void) { struct sound_task_params *p = 0; { - struct snc_lock lock = snc_lock_e(&G.params.mutex); + P_Lock lock = snc_lock_e(&G.params.mutex); if (G.params.head_free) { p = G.params.head_free; G.params.head_free = p->next_free; @@ -57,7 +57,7 @@ INTERNAL struct sound_task_params *sound_task_params_alloc(void) INTERNAL void sound_task_params_release(struct sound_task_params *p) { - struct snc_lock lock = snc_lock_e(&G.params.mutex); + P_Lock lock = snc_lock_e(&G.params.mutex); p->next_free = G.params.head_free; G.params.head_free = p; snc_unlock(&lock); @@ -67,7 +67,7 @@ INTERNAL void sound_task_params_release(struct sound_task_params *p) * Load * ========================== */ -INTERNAL SYS_JOB_DEF(sound_load_asset_job, job) +INTERNAL P_JobDef(sound_load_asset_job, job) { __prof; struct sound_task_params *params = job.sig; @@ -77,7 +77,7 @@ INTERNAL SYS_JOB_DEF(sound_load_asset_job, job) u32 flags = params->flags; logf_info("Loading sound \"%F\"", FMT_STR(path)); - i64 start_ns = sys_time_ns(); + i64 start_ns = P_TimeNs(); String error_msg = LIT("Unknown error"); @@ -104,11 +104,11 @@ INTERNAL SYS_JOB_DEF(sound_load_asset_job, job) if (decoded.success) { /* Store */ - struct sound *sound = 0; + SND_Sound *sound = 0; i16 *samples = 0; { AC_Store store = asset_cache_store_open(); - sound = arena_push_no_zero(store.arena, struct sound); + sound = arena_push_no_zero(store.arena, SND_Sound); samples = arena_push_array_no_zero(store.arena, i16, decoded.pcm.count); asset_cache_store_close(&store); } @@ -120,19 +120,19 @@ INTERNAL SYS_JOB_DEF(sound_load_asset_job, job) sound->pcm.samples = samples; MEMCPY(sound->pcm.samples, decoded.pcm.samples, decoded.pcm.count * sizeof(*decoded.pcm.samples)); - logf_success("Loaded sound \"%F\" in %F seconds", FMT_STR(path), FMT_FLOAT(SECONDS_FROM_NS(sys_time_ns() - start_ns))); + logf_success("Loaded sound \"%F\" in %F seconds", FMT_STR(path), FMT_FLOAT(SECONDS_FROM_NS(P_TimeNs() - start_ns))); asset_cache_mark_ready(asset, sound); } else { logf_error("Error loading sound \"%F\": %F", FMT_STR(path), FMT_STR(error_msg)); /* Store */ - struct sound *sound = 0; + SND_Sound *sound = 0; { AC_Store store = asset_cache_store_open(); - sound = arena_push_no_zero(store.arena, struct sound); + sound = arena_push_no_zero(store.arena, SND_Sound); asset_cache_store_close(&store); } - *sound = (struct sound) { 0 }; + *sound = (SND_Sound) { 0 }; asset_cache_mark_ready(asset, sound); } @@ -159,7 +159,7 @@ AC_Asset *sound_load_asset(String path, u32 flags, b32 wait) /* Assemble task params */ struct sound_task_params *params = sound_task_params_alloc(); if (path.len > (sizeof(params->path_cstr) - 1)) { - sys_panic(string_format(scratch.arena, + P_Panic(string_format(scratch.arena, LIT("Sound path \"%F\" too long!"), FMT_STR(path))); } @@ -170,7 +170,7 @@ AC_Asset *sound_load_asset(String path, u32 flags, b32 wait) /* Push task */ asset_cache_mark_loading(asset); - sys_run(1, sound_load_asset_job, params, SYS_POOL_BACKGROUND, SYS_PRIORITY_LOW, &asset->counter); + P_Run(1, sound_load_asset_job, params, P_Pool_Background, P_Priority_Low, &asset->counter); if (wait) { asset_cache_wait(asset); } @@ -180,20 +180,20 @@ AC_Asset *sound_load_asset(String path, u32 flags, b32 wait) return asset; } -struct sound *sound_load_async(String path, u32 flags) +SND_Sound *sound_load_async(String path, u32 flags) { __prof; AC_Asset *asset = sound_load_asset(path, flags, 0); - struct sound *sound = (struct sound *)asset_cache_get_store_data(asset); + SND_Sound *sound = (SND_Sound *)asset_cache_get_store_data(asset); return sound; } -struct sound *sound_load(String path, u32 flags) +SND_Sound *sound_load(String path, u32 flags) { __prof; AC_Asset *asset = sound_load_asset(path, flags, 1); asset_cache_wait(asset); - struct sound *sound = (struct sound *)asset_cache_get_store_data(asset); + SND_Sound *sound = (SND_Sound *)asset_cache_get_store_data(asset); return sound; } diff --git a/src/sound/sound_core.h b/src/sound/sound_core.h index 09a93944..0717fe27 100644 --- a/src/sound/sound_core.h +++ b/src/sound/sound_core.h @@ -1,14 +1,16 @@ #define SOUND_FLAG_NONE 0x0 #define SOUND_FLAG_STEREO 0x1 -struct sound { +typedef struct SND_Sound SND_Sound; +struct SND_Sound { u32 flags; PcmData pcm; }; -struct sound_startup_receipt { i32 _; }; -struct sound_startup_receipt sound_startup(AC_StartupReceipt *asset_cache_sr); +typedef struct SND_StartupReceipt SND_StartupReceipt; +struct SND_StartupReceipt { i32 _; }; +SND_StartupReceipt sound_startup(AC_StartupReceipt *asset_cache_sr); AC_Asset *sound_load_asset(String path, u32 flags, b32 wait); -struct sound *sound_load_async(String path, u32 flags); -struct sound *sound_load(String path, u32 flags); +SND_Sound *sound_load_async(String path, u32 flags); +SND_Sound *sound_load(String path, u32 flags); diff --git a/src/sprite/sprite.h b/src/sprite/sprite.h index 5c93ec56..47e498df 100644 --- a/src/sprite/sprite.h +++ b/src/sprite/sprite.h @@ -2,7 +2,7 @@ #define SPRITE_H #include "../base/base.h" -#include "../sys/sys.h" +#include "../platform/platform.h" #include "../gp/gp.h" #include "../ase/ase.h" #include "../resource/resource.h" diff --git a/src/sprite/sprite_core.c b/src/sprite/sprite_core.c index 877a7df8..f1ba712d 100644 --- a/src/sprite/sprite_core.c +++ b/src/sprite/sprite_core.c @@ -60,8 +60,8 @@ struct cache_entry { i64 load_time_ns; u64 memory_usage; Arena *arena; - struct sprite_texture *texture; - struct sprite_sheet *sheet; + S_Texture *texture; + S_Sheet *sheet; /* Hash list */ struct cache_entry *next_in_bin; @@ -76,7 +76,7 @@ struct cache_entry { }; struct cache_bin { - struct snc_mutex mutex; + P_Mutex mutex; struct cache_entry *first; struct cache_entry *last; }; @@ -85,7 +85,7 @@ struct cache { Atomic64Padded memory_usage; Arena *arena; struct cache_bin *bins; - struct snc_mutex entry_pool_mutex; + P_Mutex entry_pool_mutex; struct cache_entry *entry_pool_first_free; }; @@ -106,9 +106,9 @@ struct sprite_scope_cache_ref { struct load_cmd { struct load_cmd *next_free; - struct sprite_scope *scope; + S_Scope *scope; struct cache_ref ref; - struct sprite_tag tag; + S_Tag tag; u8 tag_path_buff[512]; }; @@ -118,30 +118,30 @@ struct load_cmd { GLOBAL struct { Arena *perm_arena; - struct sprite_texture *nil_texture; - struct sprite_texture *loading_texture; - struct sprite_sheet *nil_sheet; - struct sprite_sheet *loading_sheet; + S_Texture *nil_texture; + S_Texture *loading_texture; + S_Sheet *nil_sheet; + S_Sheet *loading_sheet; /* Cache */ struct cache cache; /* Load cmds */ - struct snc_mutex load_cmds_mutex; + P_Mutex load_cmds_mutex; Arena *load_cmds_arena; struct load_cmd *first_free_load_cmd; /* Scopes */ - struct snc_mutex scopes_mutex; + P_Mutex scopes_mutex; Arena *scopes_arena; - struct sprite_scope *first_free_scope; + S_Scope *first_free_scope; /* Evictor */ Atomic32Padded evictor_cycle; - struct snc_counter shutdown_counter; + P_Counter shutdown_counter; b32 evictor_scheduler_shutdown; - struct snc_mutex evictor_scheduler_mutex; - struct snc_cv evictor_scheduler_shutdown_cv; + P_Mutex evictor_scheduler_mutex; + P_Cv evictor_scheduler_shutdown_cv; } G = ZI, DEBUG_ALIAS(G, G_sprite); /* ========================== * @@ -186,24 +186,24 @@ INTERNAL ImageDataRgba generate_purple_black_image(Arena *arena, u32 width, u32 * Startup * ========================== */ -INTERNAL SYS_EXIT_FUNC(sprite_shutdown); -INTERNAL SYS_JOB_DEF(sprite_load_job, arg); -INTERNAL SYS_JOB_DEF(sprite_evictor_job, _); +INTERNAL P_ExitFuncDef(sprite_shutdown); +INTERNAL P_JobDef(sprite_load_job, arg); +INTERNAL P_JobDef(sprite_evictor_job, _); #if RESOURCE_RELOADING INTERNAL WATCH_CALLBACK_FUNC_DEF(sprite_watch_callback, info); #endif -struct sprite_startup_receipt sprite_startup(void) +S_StartupReceipt sprite_startup(void) { __prof; G.perm_arena = arena_alloc(MEBI(1)); { /* Init loading texture */ - G.loading_texture = arena_push(G.perm_arena, struct sprite_texture); + G.loading_texture = arena_push(G.perm_arena, S_Texture); /* Init nil texture */ - G.nil_texture = arena_push(G.perm_arena, struct sprite_texture); + G.nil_texture = arena_push(G.perm_arena, S_Texture); G.nil_texture->loaded = 1; { TempArena scratch = scratch_begin_no_conflict(); @@ -213,12 +213,12 @@ struct sprite_startup_receipt sprite_startup(void) } /* Init loading sheet */ - G.loading_sheet = arena_push(G.perm_arena, struct sprite_sheet); + G.loading_sheet = arena_push(G.perm_arena, S_Sheet); G.loading_sheet->image_size = V2FromXY(PIXELS_PER_UNIT, PIXELS_PER_UNIT); G.loading_sheet->frame_size = V2FromXY(PIXELS_PER_UNIT, PIXELS_PER_UNIT); /* Init nil sheet */ - G.nil_sheet = arena_push(G.perm_arena, struct sprite_sheet); + G.nil_sheet = arena_push(G.perm_arena, S_Sheet); G.nil_sheet->image_size = V2FromXY(PIXELS_PER_UNIT, PIXELS_PER_UNIT); G.nil_sheet->frame_size = V2FromXY(PIXELS_PER_UNIT, PIXELS_PER_UNIT); G.nil_sheet->loaded = 1; @@ -232,20 +232,20 @@ struct sprite_startup_receipt sprite_startup(void) G.scopes_arena = arena_alloc(GIBI(64)); - sys_run(1, sprite_evictor_job, 0, SYS_POOL_BACKGROUND, SYS_PRIORITY_LOW, &G.shutdown_counter); + P_Run(1, sprite_evictor_job, 0, P_Pool_Background, P_Priority_Low, &G.shutdown_counter); - sys_on_exit(&sprite_shutdown); + P_OnExit(&sprite_shutdown); watch_register_callback(&sprite_watch_callback); - return (struct sprite_startup_receipt) { 0 }; + return (S_StartupReceipt) { 0 }; } -INTERNAL SYS_EXIT_FUNC(sprite_shutdown) +INTERNAL P_ExitFuncDef(sprite_shutdown) { __prof; /* Signal evictor shutdown */ { - struct snc_lock lock = snc_lock_e(&G.evictor_scheduler_mutex); + P_Lock lock = snc_lock_e(&G.evictor_scheduler_mutex); G.evictor_scheduler_shutdown = 1; snc_cv_signal(&G.evictor_scheduler_shutdown_cv, I32_MAX); snc_unlock(&lock); @@ -258,20 +258,20 @@ INTERNAL SYS_EXIT_FUNC(sprite_shutdown) * Tag * ========================== */ -struct sprite_tag sprite_tag_from_path(String path) +S_Tag sprite_tag_from_path(String path) { - struct sprite_tag res = ZI; + S_Tag res = ZI; res.hash = hash_fnv64(HASH_FNV64_BASIS, path); res.path = path; return res; } -b32 sprite_tag_is_nil(struct sprite_tag tag) +b32 sprite_tag_is_nil(S_Tag tag) { return tag.hash == 0; } -b32 sprite_tag_eq(struct sprite_tag t1, struct sprite_tag t2) +b32 sprite_tag_eq(S_Tag t1, S_Tag t2) { return t1.hash == t2.hash; } @@ -285,12 +285,12 @@ INTERNAL struct cache_entry_hash cache_entry_hash_from_tag_hash(u64 tag_hash, en * Load * ========================== */ -INTERNAL struct sprite_scope_cache_ref *scope_ensure_ref_from_ref(struct sprite_scope *scope, struct cache_ref ref); -INTERNAL void push_load_job(struct cache_ref ref, struct sprite_tag tag) +INTERNAL struct sprite_scope_cache_ref *scope_ensure_ref_from_ref(S_Scope *scope, struct cache_ref ref); +INTERNAL void push_load_job(struct cache_ref ref, S_Tag tag) { struct load_cmd *cmd = 0; { - struct snc_lock lock = snc_lock_e(&G.load_cmds_mutex); + P_Lock lock = snc_lock_e(&G.load_cmds_mutex); if (G.first_free_load_cmd) { cmd = G.first_free_load_cmd; G.first_free_load_cmd = cmd->next_free; @@ -312,10 +312,10 @@ INTERNAL void push_load_job(struct cache_ref ref, struct sprite_tag tag) } /* Push work */ - sys_run(1, sprite_load_job, cmd, SYS_POOL_BACKGROUND, SYS_PRIORITY_INHERIT, 0); + P_Run(1, sprite_load_job, cmd, P_Pool_Background, P_Priority_Inherit, 0); } -INTERNAL void cache_entry_load_texture(struct cache_ref ref, struct sprite_tag tag) +INTERNAL void cache_entry_load_texture(struct cache_ref ref, S_Tag tag) { __prof; TempArena scratch = scratch_begin_no_conflict(); @@ -326,7 +326,7 @@ INTERNAL void cache_entry_load_texture(struct cache_ref ref, struct sprite_tag t logf_info("Loading sprite texture [%F] \"%F\"", FMT_HEX(e->hash.v), FMT_STR(path)); b32 success = 0; - i64 start_ns = sys_time_ns(); + i64 start_ns = P_TimeNs(); ASSERT(string_ends_with(path, LIT(".ase"))); ASSERT(e->kind == CACHE_ENTRY_KIND_TEXTURE); @@ -350,7 +350,7 @@ INTERNAL void cache_entry_load_texture(struct cache_ref ref, struct sprite_tag t if (decoded.success) { /* Initialize */ - e->texture = arena_push(e->arena, struct sprite_texture); + e->texture = arena_push(e->arena, S_Texture); e->texture->width = decoded.image.width; e->texture->height = decoded.image.height; e->texture->valid = 1; @@ -369,7 +369,7 @@ INTERNAL void cache_entry_load_texture(struct cache_ref ref, struct sprite_tag t logf_success("Loaded sprite texture [%F] \"%F\" in %F seconds (cache size: %F bytes).", FMT_HEX(e->hash.v), FMT_STR(path), - FMT_FLOAT(SECONDS_FROM_NS(sys_time_ns() - start_ns)), + FMT_FLOAT(SECONDS_FROM_NS(P_TimeNs() - start_ns)), FMT_UINT(e->memory_usage)); } @@ -377,14 +377,14 @@ INTERNAL void cache_entry_load_texture(struct cache_ref ref, struct sprite_tag t #if RESOURCE_RELOADING struct cache_bin *bin = &G.cache.bins[e->hash.v % CACHE_BINS_COUNT]; - struct snc_lock bin_lock = snc_lock_e(&bin->mutex); + P_Lock bin_lock = snc_lock_e(&bin->mutex); { for (struct cache_entry *old_entry = bin->first; old_entry; old_entry = old_entry->next_in_bin) { if (old_entry != e && old_entry->hash.v == e->hash.v) { atomic32_fetch_set(&old_entry->out_of_date, 1); } } - e->load_time_ns = sys_time_ns(); + e->load_time_ns = P_TimeNs(); } snc_unlock(&bin_lock); #endif @@ -392,10 +392,10 @@ INTERNAL void cache_entry_load_texture(struct cache_ref ref, struct sprite_tag t scratch_end(scratch); } -INTERNAL struct sprite_sheet init_sheet_from_ase_result(Arena *arena, Ase_DecodedSheet ase) +INTERNAL S_Sheet init_sheet_from_ase_result(Arena *arena, Ase_DecodedSheet ase) { __prof; - struct sprite_sheet sheet = ZI; + S_Sheet sheet = ZI; ASSERT(ase.num_frames >= 1); @@ -407,7 +407,7 @@ INTERNAL struct sprite_sheet init_sheet_from_ase_result(Arena *arena, Ase_Decode __profn("Init frames"); sheet.image_size = ase.image_size; sheet.frame_size = ase.frame_size; - sheet.frames = arena_push_array(arena, struct sprite_sheet_frame, ase.num_frames); + sheet.frames = arena_push_array(arena, S_SheetFrame, ase.num_frames); sheet.frames_count = ase.num_frames; for (Ase_Frame *ase_frame = ase.frame_head; ase_frame; ase_frame = ase_frame->next) { u32 index = ase_frame->index; @@ -415,7 +415,7 @@ INTERNAL struct sprite_sheet init_sheet_from_ase_result(Arena *arena, Ase_Decode V2 clip_p1 = { (f32)ase_frame->x1 / (f32)ase.image_size.x, (f32)ase_frame->y1 / (f32)ase.image_size.y }; V2 clip_p2 = { (f32)ase_frame->x2 / (f32)ase.image_size.x, (f32)ase_frame->y2 / (f32)ase.image_size.y }; - sheet.frames[index] = (struct sprite_sheet_frame) { + sheet.frames[index] = (S_SheetFrame) { .index = index, .duration = ase_frame->duration, .clip = (ClipRect) { clip_p1, clip_p2 } @@ -427,12 +427,12 @@ INTERNAL struct sprite_sheet init_sheet_from_ase_result(Arena *arena, Ase_Decode sheet.spans_count = ase.num_spans; if (ase.num_spans > 0) { __profn("Init spans"); - sheet.spans = arena_push_array(arena, struct sprite_sheet_span, sheet.spans_count); + sheet.spans = arena_push_array(arena, S_SheetSpan, sheet.spans_count); sheet.spans_dict = dict_init(arena, (u64)(ase.num_spans * SHEET_SPAN_LOOKUP_TABLE_BIN_RATIO)); u64 index = 0; for (Ase_Span *ase_span = ase.span_head; ase_span; ase_span = ase_span->next) { String name = string_copy(arena, ase_span->name); - struct sprite_sheet_span *span = &sheet.spans[index]; + S_SheetSpan *span = &sheet.spans[index]; span->name = name; span->start = ase_span->start; span->end = ase_span->end; @@ -461,7 +461,7 @@ INTERNAL struct sprite_sheet init_sheet_from_ase_result(Arena *arena, Ase_Decode struct temp_ase_slice_key_node *temp_ase_slice_key_head; struct temp_slice_group_node *next; - struct sprite_sheet_slice_group *final_slice_group; + S_SheetSliceGroup *final_slice_group; }; /* Group slices by name and find out counts per frame */ @@ -496,16 +496,16 @@ INTERNAL struct sprite_sheet init_sheet_from_ase_result(Arena *arena, Ase_Decode /* Allocate slice groups & fill originals in 2d array */ sheet.slice_groups_count = num_temp_slice_group_nodes; - sheet.slice_groups = arena_push_array(arena, struct sprite_sheet_slice_group, sheet.slice_groups_count); + sheet.slice_groups = arena_push_array(arena, S_SheetSliceGroup, sheet.slice_groups_count); sheet.slice_groups_dict = dict_init(arena, (u64)(num_temp_slice_group_nodes * SHEET_SLICE_LOOKUP_TABLE_BIN_RATIO)); u64 index = 0; for (struct temp_slice_group_node *temp_slice_group_node = temp_slice_group_head; temp_slice_group_node; temp_slice_group_node = temp_slice_group_node->next) { - struct sprite_sheet_slice_group *slice_group = &sheet.slice_groups[index]; + S_SheetSliceGroup *slice_group = &sheet.slice_groups[index]; slice_group->name = string_copy(arena, temp_slice_group_node->name); slice_group->per_frame_count = temp_slice_group_node->per_frame_count; - slice_group->frame_slices = arena_push_array(arena, struct sprite_sheet_slice, ase.num_frames * slice_group->per_frame_count); + slice_group->frame_slices = arena_push_array(arena, S_SheetSlice, ase.num_frames * slice_group->per_frame_count); u64 index_in_frame = 0; for (struct temp_ase_slice_key_node *node = temp_slice_group_node->temp_ase_slice_key_head; node; node = node->next) { @@ -514,7 +514,7 @@ INTERNAL struct sprite_sheet init_sheet_from_ase_result(Arena *arena, Ase_Decode for (Ase_Slice *ase_slice = key->slice_head; ase_slice; ase_slice = ase_slice->next) { u32 start = ase_slice->start; - struct sprite_sheet_slice *slice = &slice_group->frame_slices[(start * slice_group->per_frame_count) + index_in_frame]; + S_SheetSlice *slice = &slice_group->frame_slices[(start * slice_group->per_frame_count) + index_in_frame]; slice->original = 1; f32 x1_px = ase_slice->x1; @@ -566,7 +566,7 @@ INTERNAL struct sprite_sheet init_sheet_from_ase_result(Arena *arena, Ase_Decode /* Propagate original slices into next frames (and first slices into previous frames) */ for (struct temp_slice_group_node *temp_slice_group_node = temp_slice_group_head; temp_slice_group_node; temp_slice_group_node = temp_slice_group_node->next) { - struct sprite_sheet_slice_group *slice_group = temp_slice_group_node->final_slice_group; + S_SheetSliceGroup *slice_group = temp_slice_group_node->final_slice_group; for (struct temp_ase_slice_key_node *node = temp_slice_group_node->temp_ase_slice_key_head; node; node = node->next) { Ase_SliceKey *key = node->key; @@ -574,12 +574,12 @@ INTERNAL struct sprite_sheet init_sheet_from_ase_result(Arena *arena, Ase_Decode for (Ase_Slice *ase_slice = key->slice_head; ase_slice; ase_slice = ase_slice->next) { u32 start = ase_slice->start; - struct sprite_sheet_slice *slice = &slice_group->frame_slices[(start * slice_group->per_frame_count) + index_in_frame]; + S_SheetSlice *slice = &slice_group->frame_slices[(start * slice_group->per_frame_count) + index_in_frame]; /* Propagate earliest slice to all previous frames */ if (start == node->earliest_frame && start > 0) { for (u32 i = start; i-- > 0;) { - struct sprite_sheet_slice *target = &slice_group->frame_slices[(i * slice_group->per_frame_count) + index_in_frame]; + S_SheetSlice *target = &slice_group->frame_slices[(i * slice_group->per_frame_count) + index_in_frame]; *target = *slice; target->original = 0; } @@ -587,7 +587,7 @@ INTERNAL struct sprite_sheet init_sheet_from_ase_result(Arena *arena, Ase_Decode /* Propagate slice to forward frames until original is found */ for (u32 i = start + 1; i < ase.num_frames; ++i) { - struct sprite_sheet_slice *target = &slice_group->frame_slices[(i * slice_group->per_frame_count) + index_in_frame]; + S_SheetSlice *target = &slice_group->frame_slices[(i * slice_group->per_frame_count) + index_in_frame]; if (target->original) { break; } else { @@ -603,25 +603,25 @@ INTERNAL struct sprite_sheet init_sheet_from_ase_result(Arena *arena, Ase_Decode for (struct temp_slice_group_node *temp_slice_group_node = temp_slice_group_head; temp_slice_group_node; temp_slice_group_node = temp_slice_group_node->next) { String ray_suffix = LIT(".ray"); - struct sprite_sheet_slice_group *ray_slice_group = temp_slice_group_node->final_slice_group; + S_SheetSliceGroup *ray_slice_group = temp_slice_group_node->final_slice_group; String ray_slice_name = ray_slice_group->name; if (string_ends_with(ray_slice_name, ray_suffix)) { String point_slice_name = ray_slice_name; point_slice_name.len -= ray_suffix.len; u64 hash = hash_fnv64(HASH_FNV64_BASIS, point_slice_name); - struct sprite_sheet_slice_group *point_slice_group = (struct sprite_sheet_slice_group *)dict_get(sheet.slice_groups_dict, hash); + S_SheetSliceGroup *point_slice_group = (S_SheetSliceGroup *)dict_get(sheet.slice_groups_dict, hash); if (point_slice_group) { u32 point_slices_per_frame = point_slice_group->per_frame_count; for (u32 i = 0; i < ase.num_frames; ++i) { /* Use ray slice in ray group */ - struct sprite_sheet_slice *ray_slice = &ray_slice_group->frame_slices[i * point_slices_per_frame]; + S_SheetSlice *ray_slice = &ray_slice_group->frame_slices[i * point_slices_per_frame]; V2 ray_end = ray_slice->center_px; V2 ray_end_norm = ray_slice->center; /* Apply to each point slice in point group */ for (u32 j = 0; j < point_slices_per_frame; ++j) { - struct sprite_sheet_slice *point_slice = &point_slice_group->frame_slices[(i * point_slices_per_frame) + j]; + S_SheetSlice *point_slice = &point_slice_group->frame_slices[(i * point_slices_per_frame) + j]; point_slice->dir_px = v2_sub(ray_end, point_slice->center_px); point_slice->dir = v2_sub(ray_end_norm, point_slice->center); point_slice->has_ray = 1; @@ -638,7 +638,7 @@ INTERNAL struct sprite_sheet init_sheet_from_ase_result(Arena *arena, Ase_Decode return sheet; } -INTERNAL void cache_entry_load_sheet(struct cache_ref ref, struct sprite_tag tag) +INTERNAL void cache_entry_load_sheet(struct cache_ref ref, S_Tag tag) { __prof; TempArena scratch = scratch_begin_no_conflict(); @@ -649,7 +649,7 @@ INTERNAL void cache_entry_load_sheet(struct cache_ref ref, struct sprite_tag tag logf_info("Loading sprite sheet [%F] \"%F\"", FMT_HEX(e->hash.v), FMT_STR(path)); b32 success = 0; - i64 start_ns = sys_time_ns(); + i64 start_ns = P_TimeNs(); ASSERT(e->kind == CACHE_ENTRY_KIND_SHEET); @@ -674,7 +674,7 @@ INTERNAL void cache_entry_load_sheet(struct cache_ref ref, struct sprite_tag tag resource_close(&sheet_rs); /* Initialize */ - e->sheet = arena_push_no_zero(e->arena, struct sprite_sheet); + e->sheet = arena_push_no_zero(e->arena, S_Sheet); *e->sheet = init_sheet_from_ase_result(e->arena, decoded); e->sheet->loaded = 1; e->sheet->valid = 1; @@ -690,7 +690,7 @@ INTERNAL void cache_entry_load_sheet(struct cache_ref ref, struct sprite_tag tag logf_success("Loaded sprite sheet [%F] \"%F\" in %F seconds (cache size: %F bytes).", FMT_HEX(e->hash.v), FMT_STR(path), - FMT_FLOAT(SECONDS_FROM_NS(sys_time_ns() - start_ns)), + FMT_FLOAT(SECONDS_FROM_NS(P_TimeNs() - start_ns)), FMT_UINT(e->memory_usage)); } @@ -698,14 +698,14 @@ INTERNAL void cache_entry_load_sheet(struct cache_ref ref, struct sprite_tag tag #if RESOURCE_RELOADING struct cache_bin *bin = &G.cache.bins[e->hash.v % CACHE_BINS_COUNT]; - struct snc_lock bin_lock = snc_lock_e(&bin->mutex); + P_Lock bin_lock = snc_lock_e(&bin->mutex); { for (struct cache_entry *old_entry = bin->first; old_entry; old_entry = old_entry->next_in_bin) { if (old_entry != e && old_entry->hash.v == e->hash.v) { atomic32_fetch_set(&old_entry->out_of_date, 1); } } - e->load_time_ns = sys_time_ns(); + e->load_time_ns = P_TimeNs(); } snc_unlock(&bin_lock); #endif @@ -735,7 +735,7 @@ INTERNAL void refcount_add(struct cache_entry *e, i32 amount) } } -INTERNAL struct sprite_scope_cache_ref *scope_ensure_ref_unsafe(struct sprite_scope *scope, struct cache_entry *e) +INTERNAL struct sprite_scope_cache_ref *scope_ensure_ref_unsafe(S_Scope *scope, struct cache_entry *e) { u64 bin_index = e->hash.v % CACHE_BINS_COUNT; @@ -751,7 +751,7 @@ INTERNAL struct sprite_scope_cache_ref *scope_ensure_ref_unsafe(struct sprite_sc if (*slot == 0) { if (scope->num_references >= MAX_SCOPE_REFERENCES) { - sys_panic(LIT("Max sprite scope references reached")); + P_Panic(LIT("Max sprite scope references reached")); } /* Increment refcount */ @@ -768,27 +768,27 @@ INTERNAL struct sprite_scope_cache_ref *scope_ensure_ref_unsafe(struct sprite_sc return *slot; } -INTERNAL struct sprite_scope_cache_ref *scope_ensure_ref_from_entry(struct sprite_scope *scope, struct cache_entry *e, struct snc_lock *bin_lock) +INTERNAL struct sprite_scope_cache_ref *scope_ensure_ref_from_entry(S_Scope *scope, struct cache_entry *e, P_Lock *bin_lock) { /* Guaranteed safe if caller has lock on entry's bin, since entry may not have an existing reference and could otherwise be evicted while ensuring this reference */ snc_assert_locked_e_or_s(bin_lock, &G.cache.bins[e->hash.v % CACHE_BINS_COUNT].mutex); return scope_ensure_ref_unsafe(scope, e); } -INTERNAL struct sprite_scope_cache_ref *scope_ensure_ref_from_ref(struct sprite_scope *scope, struct cache_ref ref) +INTERNAL struct sprite_scope_cache_ref *scope_ensure_ref_from_ref(S_Scope *scope, struct cache_ref ref) { /* Safe since caller has ref */ return scope_ensure_ref_unsafe(scope, ref.e); } -struct sprite_scope *sprite_scope_begin(void) +S_Scope *sprite_scope_begin(void) { /* Alloc scope */ - struct sprite_scope *res = 0; + S_Scope *res = 0; struct sprite_scope_cache_ref **bins = 0; struct sprite_scope_cache_ref *pool = 0; { - struct snc_lock lock = snc_lock_e(&G.scopes_mutex); + P_Lock lock = snc_lock_e(&G.scopes_mutex); { if (G.first_free_scope) { res = G.first_free_scope; @@ -796,7 +796,7 @@ struct sprite_scope *sprite_scope_begin(void) bins = res->ref_node_bins; pool = res->ref_node_pool; } else { - res = arena_push_no_zero(G.scopes_arena, struct sprite_scope); + res = arena_push_no_zero(G.scopes_arena, S_Scope); bins = arena_push_array_no_zero(G.scopes_arena, struct sprite_scope_cache_ref *, CACHE_BINS_COUNT); pool = arena_push_array_no_zero(G.scopes_arena, struct sprite_scope_cache_ref, MAX_SCOPE_REFERENCES); } @@ -810,7 +810,7 @@ struct sprite_scope *sprite_scope_begin(void) return res; } -void sprite_scope_end(struct sprite_scope *scope) +void sprite_scope_end(S_Scope *scope) { /* Dereference entries */ u64 num_references = scope->num_references; @@ -820,7 +820,7 @@ void sprite_scope_end(struct sprite_scope *scope) } /* Release scope */ - struct snc_lock lock = snc_lock_e(&G.scopes_mutex); + P_Lock lock = snc_lock_e(&G.scopes_mutex); { scope->next_free = G.first_free_scope; G.first_free_scope = scope; @@ -832,7 +832,7 @@ void sprite_scope_end(struct sprite_scope *scope) * Cache interface * ========================== */ -INTERNAL struct sprite_scope_cache_ref *cache_lookup(struct sprite_scope *scope, struct cache_entry_hash hash, struct snc_lock *bin_lock) +INTERNAL struct sprite_scope_cache_ref *cache_lookup(S_Scope *scope, struct cache_entry_hash hash, P_Lock *bin_lock) { struct sprite_scope_cache_ref *scope_ref = 0; @@ -869,7 +869,7 @@ INTERNAL struct sprite_scope_cache_ref *cache_lookup(struct sprite_scope *scope, return scope_ref; } -INTERNAL struct sprite_scope_cache_ref *cache_entry_from_tag(struct sprite_scope *scope, struct sprite_tag tag, enum cache_entry_kind kind, b32 force_new) +INTERNAL struct sprite_scope_cache_ref *cache_entry_from_tag(S_Scope *scope, S_Tag tag, enum cache_entry_kind kind, b32 force_new) { struct cache_entry_hash hash = cache_entry_hash_from_tag_hash(tag.hash, kind); u64 bin_index = hash.v % CACHE_BINS_COUNT; @@ -892,7 +892,7 @@ INTERNAL struct sprite_scope_cache_ref *cache_entry_from_tag(struct sprite_scope /* Search in cache */ if (!force_new) { - struct snc_lock bin_lock = snc_lock_s(&bin->mutex); + P_Lock bin_lock = snc_lock_s(&bin->mutex); { scope_ref = cache_lookup(scope, hash, &bin_lock); } @@ -901,7 +901,7 @@ INTERNAL struct sprite_scope_cache_ref *cache_entry_from_tag(struct sprite_scope /* If not in cache, allocate new entry */ if (!scope_ref) { - struct snc_lock bin_lock = snc_lock_e(&bin->mutex); + P_Lock bin_lock = snc_lock_e(&bin->mutex); { /* Search cache one more time in case an entry was allocated between locks */ if (!force_new) { @@ -912,7 +912,7 @@ INTERNAL struct sprite_scope_cache_ref *cache_entry_from_tag(struct sprite_scope /* Cache entry still absent, allocate new entry */ struct cache_entry *entry = 0; { - struct snc_lock pool_lock = snc_lock_e(&G.cache.entry_pool_mutex); + P_Lock pool_lock = snc_lock_e(&G.cache.entry_pool_mutex); if (G.cache.entry_pool_first_free) { entry = G.cache.entry_pool_first_free; G.cache.entry_pool_first_free = entry->next_free; @@ -948,14 +948,14 @@ INTERNAL struct sprite_scope_cache_ref *cache_entry_from_tag(struct sprite_scope return scope_ref; } -INTERNAL void *data_from_tag_internal(struct sprite_scope *scope, struct sprite_tag tag, enum cache_entry_kind kind, b32 await) +INTERNAL void *data_from_tag_internal(S_Scope *scope, S_Tag tag, enum cache_entry_kind kind, b32 await) { /* TODO: Replace switch statements */ void *res = 0; switch (kind) { case CACHE_ENTRY_KIND_TEXTURE: { res = G.loading_texture; } break; case CACHE_ENTRY_KIND_SHEET: { res = G.loading_sheet; } break; - default: { sys_panic(LIT("Unknown sprite cache entry kind")); } break; + default: { P_Panic(LIT("Unknown sprite cache entry kind")); } break; } struct sprite_scope_cache_ref *scope_ref = cache_entry_from_tag(scope, tag, kind, 0); @@ -966,7 +966,7 @@ INTERNAL void *data_from_tag_internal(struct sprite_scope *scope, struct sprite_ switch (kind) { case CACHE_ENTRY_KIND_TEXTURE: { res = ref.e->texture; } break; case CACHE_ENTRY_KIND_SHEET: { res = ref.e->sheet; } break; - default: { sys_panic(LIT("Unknown sprite cache entry kind")); } break; + default: { P_Panic(LIT("Unknown sprite cache entry kind")); } break; } } else if (state == CACHE_ENTRY_STATE_NONE) { /* If entry is new, load texture */ @@ -982,7 +982,7 @@ INTERNAL void *data_from_tag_internal(struct sprite_scope *scope, struct sprite_ cache_entry_load_sheet(ref, tag); res = ref.e->sheet; } break; - default: { sys_panic(LIT("Unknown sprite cache entry kind")); } break; + default: { P_Panic(LIT("Unknown sprite cache entry kind")); } break; } } else { /* Allocate cmd */ @@ -1005,18 +1005,18 @@ INTERNAL void *data_from_tag_internal(struct sprite_scope *scope, struct sprite_ * Texture * ========================== */ -struct sprite_texture *sprite_texture_from_tag_await(struct sprite_scope *scope, struct sprite_tag tag) +S_Texture *sprite_texture_from_tag_await(S_Scope *scope, S_Tag tag) { - return (struct sprite_texture *)data_from_tag_internal(scope, tag, CACHE_ENTRY_KIND_TEXTURE, 1); + return (S_Texture *)data_from_tag_internal(scope, tag, CACHE_ENTRY_KIND_TEXTURE, 1); } -struct sprite_texture *sprite_texture_from_tag_async(struct sprite_scope *scope, struct sprite_tag tag) +S_Texture *sprite_texture_from_tag_async(S_Scope *scope, S_Tag tag) { - return (struct sprite_texture *)data_from_tag_internal(scope, tag, CACHE_ENTRY_KIND_TEXTURE, 0); + return (S_Texture *)data_from_tag_internal(scope, tag, CACHE_ENTRY_KIND_TEXTURE, 0); } -void sprite_texture_from_tag_prefetch(struct sprite_scope *scope, struct sprite_tag tag) +void sprite_texture_from_tag_prefetch(S_Scope *scope, S_Tag tag) { data_from_tag_internal(scope, tag, CACHE_ENTRY_KIND_TEXTURE, 0); } @@ -1025,40 +1025,40 @@ void sprite_texture_from_tag_prefetch(struct sprite_scope *scope, struct sprite_ * Sheet * ========================== */ -struct sprite_sheet *sprite_sheet_from_tag_await(struct sprite_scope *scope, struct sprite_tag tag) +S_Sheet *sprite_sheet_from_tag_await(S_Scope *scope, S_Tag tag) { - return (struct sprite_sheet *)data_from_tag_internal(scope, tag, CACHE_ENTRY_KIND_SHEET, 1); + return (S_Sheet *)data_from_tag_internal(scope, tag, CACHE_ENTRY_KIND_SHEET, 1); } -struct sprite_sheet *sprite_sheet_from_tag_async(struct sprite_scope *scope, struct sprite_tag tag) +S_Sheet *sprite_sheet_from_tag_async(S_Scope *scope, S_Tag tag) { - return (struct sprite_sheet *)data_from_tag_internal(scope, tag, CACHE_ENTRY_KIND_SHEET, 0); + return (S_Sheet *)data_from_tag_internal(scope, tag, CACHE_ENTRY_KIND_SHEET, 0); } -void sprite_sheet_from_tag_prefetch(struct sprite_scope *scope, struct sprite_tag tag) +void sprite_sheet_from_tag_prefetch(S_Scope *scope, S_Tag tag) { data_from_tag_internal(scope, tag, CACHE_ENTRY_KIND_SHEET, 0); } -struct sprite_sheet_frame sprite_sheet_get_frame(struct sprite_sheet *sheet, u32 index) +S_SheetFrame sprite_sheet_get_frame(S_Sheet *sheet, u32 index) { if (index < sheet->frames_count ) { return sheet->frames[index]; } - struct sprite_sheet_frame res = ZI; + S_SheetFrame res = ZI; res.index = 0; res.duration = 0.1; res.clip = CLIP_ALL; return res; } -struct sprite_sheet_span sprite_sheet_get_span(struct sprite_sheet *sheet, String name) +S_SheetSpan sprite_sheet_get_span(S_Sheet *sheet, String name) { - struct sprite_sheet_span res = ZI; + S_SheetSpan res = ZI; if (sheet->spans_count > 0) { u64 hash = hash_fnv64(HASH_FNV64_BASIS, name); - struct sprite_sheet_span *entry = (struct sprite_sheet_span *)dict_get(sheet->spans_dict, hash); + S_SheetSpan *entry = (S_SheetSpan *)dict_get(sheet->spans_dict, hash); if (entry) { res = *entry; } @@ -1066,18 +1066,18 @@ struct sprite_sheet_span sprite_sheet_get_span(struct sprite_sheet *sheet, Strin return res; } -struct sprite_sheet_slice sprite_sheet_get_slice(struct sprite_sheet *sheet, String name, u32 frame_index) +S_SheetSlice sprite_sheet_get_slice(S_Sheet *sheet, String name, u32 frame_index) { if (sheet->slice_groups_count > 0) { u64 hash = hash_fnv64(HASH_FNV64_BASIS, name); - struct sprite_sheet_slice_group *group = (struct sprite_sheet_slice_group *)dict_get(sheet->slice_groups_dict, hash); + S_SheetSliceGroup *group = (S_SheetSliceGroup *)dict_get(sheet->slice_groups_dict, hash); if (group) { return group->frame_slices[frame_index * group->per_frame_count]; } } /* Return 'pivot' by default */ - struct sprite_sheet_slice res = ZI; + S_SheetSlice res = ZI; if (string_eq(name, LIT("pivot"))) { /* 'pivot' slice does not exist, return center */ res.center = V2FromXY(0, 0); @@ -1091,12 +1091,12 @@ struct sprite_sheet_slice sprite_sheet_get_slice(struct sprite_sheet *sheet, Str return res; } -struct sprite_sheet_slice_array sprite_sheet_get_slices(struct sprite_sheet *sheet, String name, u32 frame_index) +S_SheetSliceArray sprite_sheet_get_slices(S_Sheet *sheet, String name, u32 frame_index) { - struct sprite_sheet_slice_array res = ZI; + S_SheetSliceArray res = ZI; if (sheet->slice_groups_count > 0) { u64 hash = hash_fnv64(HASH_FNV64_BASIS, name); - struct sprite_sheet_slice_group *group = (struct sprite_sheet_slice_group *)dict_get(sheet->slice_groups_dict, hash); + S_SheetSliceGroup *group = (S_SheetSliceGroup *)dict_get(sheet->slice_groups_dict, hash); if (group) { res.count = group->per_frame_count; res.slices = &group->frame_slices[frame_index * group->per_frame_count]; @@ -1109,7 +1109,7 @@ struct sprite_sheet_slice_array sprite_sheet_get_slices(struct sprite_sheet *she * Load job * ========================== */ -INTERNAL SYS_JOB_DEF(sprite_load_job, job) +INTERNAL P_JobDef(sprite_load_job, job) { __prof; struct load_cmd *cmd = job.sig; @@ -1122,11 +1122,11 @@ INTERNAL SYS_JOB_DEF(sprite_load_job, job) case CACHE_ENTRY_KIND_SHEET: { cache_entry_load_sheet(ref, cmd->tag); } break; - default: { sys_panic(LIT("Unknown sprite cache node kind")); } break; + default: { P_Panic(LIT("Unknown sprite cache node kind")); } break; } /* Free cmd */ - struct snc_lock lock = snc_lock_e(&G.load_cmds_mutex); + P_Lock lock = snc_lock_e(&G.load_cmds_mutex); { sprite_scope_end(cmd->scope); cmd->next_free = G.first_free_load_cmd; @@ -1141,12 +1141,12 @@ INTERNAL SYS_JOB_DEF(sprite_load_job, job) #if RESOURCE_RELOADING -INTERNAL void reload_if_exists(struct sprite_scope *scope, struct sprite_tag tag, enum cache_entry_kind kind) +INTERNAL void reload_if_exists(S_Scope *scope, S_Tag tag, enum cache_entry_kind kind) { struct cache_entry_hash hash = cache_entry_hash_from_tag_hash(tag.hash, kind); struct cache_bin *bin = &G.cache.bins[hash.v % CACHE_BINS_COUNT]; struct sprite_scope_cache_ref *existing_ref = 0; - struct snc_lock bin_lock = snc_lock_s(&bin->mutex); + P_Lock bin_lock = snc_lock_s(&bin->mutex); { existing_ref = cache_lookup(scope, hash, &bin_lock); } @@ -1161,14 +1161,14 @@ INTERNAL void reload_if_exists(struct sprite_scope *scope, struct sprite_tag tag INTERNAL WATCH_CALLBACK_FUNC_DEF(sprite_watch_callback, name) { - struct sprite_scope *scope = sprite_scope_begin(); + S_Scope *scope = sprite_scope_begin(); if (string_starts_with(name, LIT("res/"))) { name.len -= LIT("res/").len; name.text += LIT("res/").len; } - struct sprite_tag tag = sprite_tag_from_path(name); + S_Tag tag = sprite_tag_from_path(name); for (enum cache_entry_kind kind = 0; kind < NUM_CACHE_ENTRY_KINDS; ++kind) { reload_if_exists(scope, tag, kind); } @@ -1210,7 +1210,7 @@ INTERNAL SORT_COMPARE_FUNC_DEF(evict_sort, arg_a, arg_b, udata) * - The cache is over its memory budget and the node's last reference is longer ago than the grace period * - Resource reloading is enabled and the node is out of date due to a change to its original resource file */ -INTERNAL SYS_JOB_DEF(sprite_evictor_job, _) +INTERNAL P_JobDef(sprite_evictor_job, _) { (UNUSED)_; b32 shutdown = 0; @@ -1229,7 +1229,7 @@ INTERNAL SYS_JOB_DEF(sprite_evictor_job, _) __profn("Evictor scan"); for (u64 i = 0; i < CACHE_BINS_COUNT; ++i) { struct cache_bin *bin = &G.cache.bins[i]; - struct snc_lock bin_lock = snc_lock_s(&bin->mutex); + P_Lock bin_lock = snc_lock_s(&bin->mutex); { struct cache_entry *n = bin->first; while (n) { @@ -1282,7 +1282,7 @@ INTERNAL SYS_JOB_DEF(sprite_evictor_job, _) struct cache_entry *entry = en->cache_entry; i32 last_ref_cycle = en->last_ref_cycle; b32 cache_over_budget_target = atomic64_fetch(&G.cache.memory_usage.v) > (i64)CACHE_MEMORY_BUDGET_TARGET; - struct snc_lock bin_lock = snc_lock_e(&bin->mutex); + P_Lock bin_lock = snc_lock_e(&bin->mutex); { u64 refcount_uncast = atomic64_fetch(&entry->refcount_struct.v); struct cache_refcount refcount = *(struct cache_refcount *)&refcount_uncast; @@ -1333,7 +1333,7 @@ INTERNAL SYS_JOB_DEF(sprite_evictor_job, _) /* Add evicted nodes to free list */ { __profn("Evictor free list append"); - struct snc_lock pool_lock = snc_lock_e(&G.cache.entry_pool_mutex); + P_Lock pool_lock = snc_lock_e(&G.cache.entry_pool_mutex); for (struct evict_node *en = first_evicted; en; en = en->next_evicted) { struct cache_entry *n = en->cache_entry; n->next_free = G.cache.entry_pool_first_free; @@ -1349,7 +1349,7 @@ INTERNAL SYS_JOB_DEF(sprite_evictor_job, _) /* Evictor sleep */ { - struct snc_lock lock = snc_lock_e(&G.evictor_scheduler_mutex); + P_Lock lock = snc_lock_e(&G.evictor_scheduler_mutex); { if (!G.evictor_scheduler_shutdown) { snc_cv_wait_time(&G.evictor_scheduler_shutdown_cv, &lock, EVICTOR_CYCLE_INTERVAL_NS); diff --git a/src/sprite/sprite_core.h b/src/sprite/sprite_core.h index b8343b2e..fab92afb 100644 --- a/src/sprite/sprite_core.h +++ b/src/sprite/sprite_core.h @@ -1,47 +1,48 @@ -struct sprite_sheet_span; -struct sprite_sheet_slice_group; - /* ========================== * * Startup * ========================== */ -struct sprite_startup_receipt { i32 _; }; -struct sprite_startup_receipt sprite_startup(void); +typedef struct S_StartupReceipt S_StartupReceipt; +struct S_StartupReceipt { i32 _; }; +S_StartupReceipt sprite_startup(void); /* ========================== * * Tag * ========================== */ -struct sprite_tag { +typedef struct S_Tag S_Tag; +struct S_Tag { u64 hash; String path; }; -INLINE struct sprite_tag sprite_tag_nil(void) { return (struct sprite_tag) { 0 }; } +INLINE S_Tag sprite_tag_nil(void) { return (S_Tag) { 0 }; } -struct sprite_tag sprite_tag_from_path(String path); -b32 sprite_tag_is_nil(struct sprite_tag tag); -b32 sprite_tag_eq(struct sprite_tag t1, struct sprite_tag t2); +S_Tag sprite_tag_from_path(String path); +b32 sprite_tag_is_nil(S_Tag tag); +b32 sprite_tag_eq(S_Tag t1, S_Tag t2); /* ========================== * * Scope * ========================== */ -struct sprite_scope { +typedef struct S_Scope S_Scope; +struct S_Scope { struct sprite_scope_cache_ref **ref_node_bins; struct sprite_scope_cache_ref *ref_node_pool; u64 num_references; - struct sprite_scope *next_free; + S_Scope *next_free; }; -struct sprite_scope *sprite_scope_begin(void); -void sprite_scope_end(struct sprite_scope *scope); +S_Scope *sprite_scope_begin(void); +void sprite_scope_end(S_Scope *scope); /* ========================== * * Texture load * ========================== */ -struct sprite_texture { +typedef struct S_Texture S_Texture; +struct S_Texture { b32 loaded; b32 valid; G_Resource *gp_texture; @@ -49,53 +50,60 @@ struct sprite_texture { u32 height; }; -struct sprite_texture *sprite_texture_from_tag_await(struct sprite_scope *scope, struct sprite_tag tag); -struct sprite_texture *sprite_texture_from_tag_async(struct sprite_scope *scope, struct sprite_tag tag); -void sprite_texture_from_tag_prefetch(struct sprite_scope *scope, struct sprite_tag tag); +S_Texture *sprite_texture_from_tag_await(S_Scope *scope, S_Tag tag); +S_Texture *sprite_texture_from_tag_async(S_Scope *scope, S_Tag tag); +void sprite_texture_from_tag_prefetch(S_Scope *scope, S_Tag tag); /* ========================== * * Sheet load * ========================== */ -struct sprite_sheet { +typedef struct S_SheetSliceGroup S_SheetSliceGroup; +typedef struct S_SheetSpan S_SheetSpan; +typedef struct S_SheetFrame S_SheetFrame; +typedef struct S_Sheet S_Sheet; +struct S_Sheet { b32 loaded; b32 valid; V2 image_size; V2 frame_size; u32 frames_count; - struct sprite_sheet_frame *frames; + S_SheetFrame *frames; u32 spans_count; - struct sprite_sheet_span *spans; + S_SheetSpan *spans; Dict *spans_dict; u32 slice_groups_count; - struct sprite_sheet_slice_group *slice_groups; + S_SheetSliceGroup *slice_groups; Dict *slice_groups_dict; }; -struct sprite_sheet *sprite_sheet_from_tag_await(struct sprite_scope *scope, struct sprite_tag tag); -struct sprite_sheet *sprite_sheet_from_tag_async(struct sprite_scope *scope, struct sprite_tag tag); -void sprite_sheet_from_tag_prefetch(struct sprite_scope *scope, struct sprite_tag tag); +S_Sheet *sprite_sheet_from_tag_await(S_Scope *scope, S_Tag tag); +S_Sheet *sprite_sheet_from_tag_async(S_Scope *scope, S_Tag tag); +void sprite_sheet_from_tag_prefetch(S_Scope *scope, S_Tag tag); /* ========================== * * Sheet query * ========================== */ -struct sprite_sheet_frame { +typedef struct S_SheetFrame S_SheetFrame; +struct S_SheetFrame { u32 index; f64 duration; ClipRect clip; }; -struct sprite_sheet_span { +typedef struct S_SheetSpan S_SheetSpan; +struct S_SheetSpan { String name; u32 start; u32 end; }; -struct sprite_sheet_slice { +typedef struct S_SheetSlice S_SheetSlice; +struct S_SheetSlice { /* If 1, this slice was not copied over from another frame in the sprite sheet */ b32 original; @@ -113,26 +121,28 @@ struct sprite_sheet_slice { V2 dir_px; }; -struct sprite_sheet_slice_array { +typedef struct S_SheetSliceArray S_SheetSliceArray; +struct S_SheetSliceArray { u64 count; - struct sprite_sheet_slice *slices; + S_SheetSlice *slices; }; -struct sprite_sheet_slice_group { +typedef struct S_SheetSliceGroup S_SheetSliceGroup; +struct S_SheetSliceGroup { String name; u64 per_frame_count; /* 2d array of slices with length (num frames) * (num slices per frame). * Index with [(frame index * num slices per frame) + slice index in frame] */ - struct sprite_sheet_slice *frame_slices; + S_SheetSlice *frame_slices; }; -struct sprite_sheet_frame sprite_sheet_get_frame(struct sprite_sheet *sheet, u32 index); +S_SheetFrame sprite_sheet_get_frame(S_Sheet *sheet, u32 index); -struct sprite_sheet_span sprite_sheet_get_span(struct sprite_sheet *sheet, String name); +S_SheetSpan sprite_sheet_get_span(S_Sheet *sheet, String name); /* Returns first slice with name in frame */ -struct sprite_sheet_slice sprite_sheet_get_slice(struct sprite_sheet *sheet, String name, u32 frame_index); +S_SheetSlice sprite_sheet_get_slice(S_Sheet *sheet, String name, u32 frame_index); /* Returns all slices with name in frame */ -struct sprite_sheet_slice_array sprite_sheet_get_slices(struct sprite_sheet *sheet, String name, u32 frame_index); +S_SheetSliceArray sprite_sheet_get_slices(S_Sheet *sheet, String name, u32 frame_index); diff --git a/src/sys/sys.c b/src/sys/sys.c deleted file mode 100644 index 7a91b6cf..00000000 --- a/src/sys/sys.c +++ /dev/null @@ -1,6 +0,0 @@ -#include "sys.h" - -#include "sys_snc.c" -#include "sys_sleep.c" -#include "sys_core.c" -#include "sys_log.c" diff --git a/src/sys/sys.h b/src/sys/sys.h deleted file mode 100644 index 5fd71073..00000000 --- a/src/sys/sys.h +++ /dev/null @@ -1,11 +0,0 @@ -#ifndef SYS_H -#define SYS_H - -#include "../base/base.h" - -#include "sys_snc.h" -#include "sys_sleep.h" -#include "sys_core.h" -#include "sys_log.h" - -#endif diff --git a/src/sys/sys_core.c b/src/sys/sys_core.c deleted file mode 100644 index c6f6fd5a..00000000 --- a/src/sys/sys_core.c +++ /dev/null @@ -1,5 +0,0 @@ -#if PLATFORM_WINDOWS -# include "sys_core_win32.c" -#else -# error System core layer not implemented -#endif diff --git a/src/sys/sys_core.h b/src/sys/sys_core.h deleted file mode 100644 index 061bacd0..00000000 --- a/src/sys/sys_core.h +++ /dev/null @@ -1,482 +0,0 @@ -/* ========================== * - * Wait - * ========================== */ - - /* Futex-like wait & wake */ -void sys_wait(volatile void *addr, void *cmp, u32 size, i64 timeout_ns); -void sys_wake(void *addr, i32 count); - -/* ========================== * - * Job - * ========================== */ - - /* Work pools contain their own worker threads with their own thread priority/affinity based on the intended context of the pool. */ -enum sys_pool { - SYS_POOL_INHERIT = -1, - - /* The floating pool contains a large number of lower priority threads that have affinity over the entire CPU. - * Other pools should push jobs that only block and do no work here so that they can yield on the blocking job rather than blocking themselves. */ - SYS_POOL_FLOATING = 0, - - SYS_POOL_BACKGROUND = 1, - SYS_POOL_AUDIO = 2, - SYS_POOL_USER = 3, - SYS_POOL_SIM = 4, - - NUM_SYS_POOLS -}; - -/* Job execution order within a pool is based on priority. */ -enum sys_priority { - SYS_PRIORITY_INHERIT = -1, - SYS_PRIORITY_HIGH = 0, - SYS_PRIORITY_NORMAL = 1, - SYS_PRIORITY_LOW = 2, - - NUM_SYS_PRIORITIES -}; - -struct sys_job_data { - i32 id; - void *sig; -}; - -#define SYS_JOB_DEF(job_name, arg_name) void job_name(struct sys_job_data arg_name) -typedef SYS_JOB_DEF(sys_job_func, job_data); - -void sys_run(i32 count, sys_job_func *func, void *sig, enum sys_pool pool_kind, enum sys_priority priority, struct snc_counter *counter); - -/* ========================== * - * Time - * ========================== */ - -struct sys_datetime { - u32 year; - u32 month; - u32 day_of_week; - u32 day; - u32 hour; - u32 minute; - u32 second; - u32 milliseconds; -}; - -struct sys_datetime sys_local_time(void); - -i64 sys_time_ns(void); - -/* ========================== * - * File system - * - * NOTE: File paths use forward slash '/' as delimiter - * ========================== */ - -struct sys_file { - u64 handle; - b32 valid; -}; - -struct sys_file_time { - struct sys_datetime created; - struct sys_datetime accessed; - struct sys_datetime modified; -}; - -String sys_get_write_path(Arena *arena); - -b32 sys_is_file(String path); - -b32 sys_is_dir(String path); - -void sys_mkdir(String path); - -struct sys_file sys_file_open_read(String path); - -struct sys_file sys_file_open_read_wait(String path); /* Waits until file is not being used by another program */ - -struct sys_file sys_file_open_write(String path); - -struct sys_file sys_file_open_append(String path); - -void sys_file_close(struct sys_file file); - -String sys_file_read_all(Arena *arena, struct sys_file file); - -void sys_file_write(struct sys_file file, String data); - -u64 sys_file_get_size(struct sys_file file); - -struct sys_file_time sys_file_get_time(struct sys_file file); - -/* ========================== * - * File map - * ========================== */ - -struct sys_file_map { - String mapped_memory; - u64 handle; - b32 valid; -}; - -struct sys_file_map sys_file_map_open_read(struct sys_file file); - -void sys_file_map_close(struct sys_file_map map); - -String sys_file_map_data(struct sys_file_map map); - -/* ========================== * - * Dir iter - * ========================== */ - -struct sys_file_filter_result { - String filename; - b32 is_dir; -}; - -struct sys_file_filter { - struct sys_file_filter_result info; - u64 handle; -}; - -/* Iterate all files in a directory */ -struct sys_file_filter sys_file_filter_begin(Arena *arena, String pattern); - -b32 sys_file_filter_next(Arena *arena, struct sys_file_filter *iter); - -void sys_file_filter_end(struct sys_file_filter *iter); - -/* ========================== * - * Watch - * ========================== */ - -enum sys_watch_info_kind { - SYS_WATCH_INFO_KIND_UNKNOWN, - SYS_WATCH_INFO_KIND_ADDED, - SYS_WATCH_INFO_KIND_REMOVED, - SYS_WATCH_INFO_KIND_MODIFIED, - SYS_WATCH_INFO_KIND_RENAMED_OLD, - SYS_WATCH_INFO_KIND_RENAMED_NEW - -}; - -struct sys_watch_info { - enum sys_watch_info_kind kind; - String name; - struct sys_watch_info *next; - struct sys_watch_info *prev; -}; - -struct sys_watch_info_list { - struct sys_watch_info *first; - struct sys_watch_info *last; - u64 count; -}; - -struct sys_watch *sys_watch_alloc(String path); - -void sys_watch_release(struct sys_watch *dw); - -struct sys_watch_info_list sys_watch_read_wait(Arena *arena, struct sys_watch *dw); - -void sys_watch_wake(struct sys_watch *dw); - -/* ========================== * - * Window - * ========================== */ - -enum sys_btn { - SYS_BTN_NONE, - - SYS_BTN_M1, - SYS_BTN_M2, - SYS_BTN_M3, - SYS_BTN_M4, - SYS_BTN_M5, - - SYS_BTN_MWHEELUP, - SYS_BTN_MWHEELDOWN, - - SYS_BTN_ESC, - SYS_BTN_F1, - SYS_BTN_F2, - SYS_BTN_F3, - SYS_BTN_F4, - SYS_BTN_F5, - SYS_BTN_F6, - SYS_BTN_F7, - SYS_BTN_F8, - SYS_BTN_F9, - SYS_BTN_F10, - SYS_BTN_F11, - SYS_BTN_F12, - SYS_BTN_F13, - SYS_BTN_F14, - SYS_BTN_F15, - SYS_BTN_F16, - SYS_BTN_F17, - SYS_BTN_F18, - SYS_BTN_F19, - SYS_BTN_F20, - SYS_BTN_F21, - SYS_BTN_F22, - SYS_BTN_F23, - SYS_BTN_F24, - SYS_BTN_GRAVE_ACCENT, - SYS_BTN_0, - SYS_BTN_1, - SYS_BTN_2, - SYS_BTN_3, - SYS_BTN_4, - SYS_BTN_5, - SYS_BTN_6, - SYS_BTN_7, - SYS_BTN_8, - SYS_BTN_9, - SYS_BTN_MINUS, - SYS_BTN_EQUAL, - SYS_BTN_BACKSPACE, - SYS_BTN_DELETE, - SYS_BTN_TAB, - SYS_BTN_A, - SYS_BTN_B, - SYS_BTN_C, - SYS_BTN_D, - SYS_BTN_E, - SYS_BTN_F, - SYS_BTN_G, - SYS_BTN_H, - SYS_BTN_I, - SYS_BTN_J, - SYS_BTN_K, - SYS_BTN_L, - SYS_BTN_M, - SYS_BTN_N, - SYS_BTN_O, - SYS_BTN_P, - SYS_BTN_Q, - SYS_BTN_R, - SYS_BTN_S, - SYS_BTN_T, - SYS_BTN_U, - SYS_BTN_V, - SYS_BTN_W, - SYS_BTN_X, - SYS_BTN_Y, - SYS_BTN_Z, - SYS_BTN_SPACE, - SYS_BTN_ENTER, - SYS_BTN_CTRL, - SYS_BTN_SHIFT, - SYS_BTN_ALT, - SYS_BTN_UP, - SYS_BTN_LEFT, - SYS_BTN_DOWN, - SYS_BTN_RIGHT, - SYS_BTN_PAGE_UP, - SYS_BTN_PAGE_DOWN, - SYS_BTN_HOME, - SYS_BTN_END, - SYS_BTN_FORWARD_SLASH, - SYS_BTN_PERIOD, - SYS_BTN_COMMA, - SYS_BTN_QUOTE, - SYS_BTN_LEFT_BRACKET, - SYS_BTN_RIGHT_BRACKET, - SYS_BTN_INSERT, - SYS_BTN_SEMICOLON, - - SYS_BTN_COUNT -}; - -enum sys_window_event_kind { - SYS_EVENT_KIND_NONE, - - SYS_EVENT_KIND_BUTTON_DOWN, - SYS_EVENT_KIND_BUTTON_UP, - SYS_EVENT_KIND_CURSOR_MOVE, - SYS_EVENT_KIND_MOUSE_MOVE, - SYS_EVENT_KIND_TEXT, - SYS_EVENT_KIND_QUIT, - - SYS_EVENT_KIND_COUNT -}; - -struct sys_window_event { - enum sys_window_event_kind kind; - - /* SYS_EVENT_KIND_BUTTON_DOWN */ - /* SYS_EVENT_KIND_BUTTON_UP */ - enum sys_btn button; - b32 is_repeat; - - /* SYS_EVENT_KIND_TEXT */ - u32 text_codepoint; - - /* SYS_EVENT_KIND_CURSOR_MOVE */ - V2 cursor_position; - - /* SYS_EVENT_KIND_MOUSE_MOVE */ - V2 mouse_delta; -}; - -struct sys_window_event_array { - u64 count; - struct sys_window_event *events; -}; - -/* NOTE: - * A window object can only be interacted with by the thread that created it. - * This restriction is in place because of how Win32 works, IE you cannot - * create a Win32 window in one thread and process its messages on another. */ - -enum sys_window_settings_flags { - SYS_WINDOW_SETTINGS_FLAG_NONE = 0x00, - SYS_WINDOW_SETTINGS_FLAG_FULLSCREEN = 0x01, - - /* NOTE: Both maximized and minimized can be true at the same time. This - * means that the window was minimized from a maximized state, and will - * restore to being maximized once it's un-minimized. */ - SYS_WINDOW_SETTINGS_FLAG_MAXIMIZED = 0x02, - SYS_WINDOW_SETTINGS_FLAG_MINIMIZED = 0x04 -}; - -enum sys_window_flags { - SYS_WINDOW_FLAG_NONE = 0x00, - SYS_WINDOW_FLAG_SHOWING = 0x02 -}; - -/* sys_window_update_settings should be used when altering settings values */ -struct sys_window_settings { - char title[256]; - u32 flags; - - /* NOTE: Below fields are NOT representative of actual window dimensions. - * These values represent the window dimensions when the window is not - * maximized, minimized, or fullscreen. AKA 'floating'. Use - * `sys_window_get_size` for rendering instead. */ - i32 floating_x; - i32 floating_y; - i32 floating_width; - i32 floating_height; -}; - -struct sys_window *sys_window_alloc(void); - -void sys_window_release(struct sys_window *sys_window); - -struct sys_window_event_array sys_window_pop_events(Arena *arena, struct sys_window *sys_window); - -void sys_window_update_settings(struct sys_window *sys_window, struct sys_window_settings *settings); - -struct sys_window_settings sys_window_get_settings(struct sys_window *sys_window); - -void sys_window_show(struct sys_window *sys_window); - -V2 sys_window_get_size(struct sys_window *sys_window); - -V2 sys_window_get_monitor_size(struct sys_window *sys_window); - -/* Returns a platform specific representation of the window. E.g. `hwnd` on win32. */ -u64 sys_window_get_internal_handle(struct sys_window *sys_window); - -void sys_window_cursor_set_pos(struct sys_window *sys_window, V2 pos); - -void sys_window_cursor_show(struct sys_window *sys_window); - -void sys_window_cursor_hide(struct sys_window *sys_window); - -void sys_window_cursor_enable_clip(struct sys_window *sys_window, Rect bounds); - -void sys_window_cursor_disable_clip(struct sys_window *sys_window); - -void sys_window_toggle_topmost(struct sys_window *sys_window); - -/* ========================== * - * Address - * ========================== */ - -enum sys_address_family { - SYS_ADDRESS_FAMILY_IPV4, - SYS_ADDRESS_FAMILY_IPV6 -}; - -struct sys_address { - b32 valid; - enum sys_address_family family; - /* NOTE: ipnb & portnb are stored in network byte order */ - u8 ipnb[16]; - u16 portnb; -}; - -struct sys_address sys_address_from_string(String str); - -struct sys_address sys_address_from_port(u16 port); - -String sys_string_from_address(Arena *arena, struct sys_address address); - -b32 sys_address_eq(struct sys_address a, struct sys_address b); - -/* ========================== * - * Sock - * ========================== */ - -struct sys_sock_read_result { - b32 valid; /* Since data.len = 0 can be valid */ - struct sys_address address; - String data; -}; - -struct sys_sock *sys_sock_alloc(u16 listen_port, u64 sndbuf_size, u64 rcvbuf_size); - -void sys_sock_release(struct sys_sock *sock); - -struct sys_sock_read_result sys_sock_read(Arena *arena, struct sys_sock *sock); - -void sys_sock_write(struct sys_sock *sock, struct sys_address address, String data); - -/* ========================== * - * Util - * ========================== */ - -enum sys_message_box_kind { - SYS_MESSAGE_BOX_KIND_OK, - SYS_MESSAGE_BOX_KIND_WARNING, - SYS_MESSAGE_BOX_KIND_ERROR, - SYS_MESSAGE_BOX_KIND_FATAL -}; - -void sys_message_box(enum sys_message_box_kind kind, String message); - -void sys_set_clipboard_text(String str); - -String sys_get_clipboard_text(Arena *arena); - -u32 sys_num_logical_processors(void); - -u32 sys_current_thread_id(void); - -i64 sys_current_scheduler_period_ns(void); - -/* ========================== * - * Exit - * ========================== */ - - -#define SYS_EXIT_FUNC(name) void name(void) -typedef SYS_EXIT_FUNC(sys_exit_func); - -/* Registers a function to be called during graceful shutdown (in reverse order) */ -void sys_on_exit(sys_exit_func *func); - -/* Signals the program to shut down gracefully and run exit callbacks */ -void sys_exit(void); - -/* Forcefully exits the program and displays `msg` to the user */ -void sys_panic(String msg); - -/* ========================== * - * App entry point - * ========================== */ - - /* Must be defined by app */ -void sys_app_startup(String args_str); diff --git a/src/sys/sys_snc.h b/src/sys/sys_snc.h deleted file mode 100644 index 8d4c2b8e..00000000 --- a/src/sys/sys_snc.h +++ /dev/null @@ -1,68 +0,0 @@ -/* ========================== * - * Mutex - * ========================== */ - -struct snc_lock { - struct snc_mutex *mutex; - b32 exclusive; -}; - -struct alignas(64) snc_mutex { - /* Bit 31 = Exclusive lock is held - * Bit 30 = Exclusive lock is pending - * Bit 0-30 = Shared locks count - */ - Atomic32 v; - -#if RTC - Atomic32 exclusive_fiber_id; - u8 _pad[56]; -#else - u8 _pad[60]; -#endif -}; -STATIC_ASSERT(sizeof(struct snc_mutex) == 64); /* Padding validation */ -STATIC_ASSERT(alignof(struct snc_mutex) == 64); /* Prevent false sharing */ - -struct snc_lock snc_lock_spin_e(struct snc_mutex *m, i32 spin); -struct snc_lock snc_lock_spin_s(struct snc_mutex *m, i32 spin); -struct snc_lock snc_lock_e(struct snc_mutex *m); -struct snc_lock snc_lock_s(struct snc_mutex *m); -void snc_unlock(struct snc_lock *lock); - -#if RTC -# define snc_assert_locked_e(l, m) ASSERT((l)->mutex == (m) && (l)->exclusive == 1) -# define snc_assert_locked_e_or_s(l, m) ASSERT((l)->mutex == (m)) -#else -# define snc_assert_locked_e(l, m) (UNUSED)l -# define snc_assert_locked_e_or_s(l, m) (UNUSED)l -#endif - -/* ========================== * - * Condition variable - * ========================== */ - -struct alignas(64) snc_cv { - Atomic64 wake_gen; - u8 _pad[56]; -}; -STATIC_ASSERT(sizeof(struct snc_cv) == 64); /* Padding validation */ -STATIC_ASSERT(alignof(struct snc_cv) == 64); /* Prevent false sharing */ - -void snc_cv_wait(struct snc_cv *cv, struct snc_lock *lock); -void snc_cv_wait_time(struct snc_cv *cv, struct snc_lock *l, i64 timeout_ns); -void snc_cv_signal(struct snc_cv *cv, i32 count); - -/* ========================== * - * Counter - * ========================== */ - -struct alignas(64) snc_counter { - Atomic64 v; - u8 _pad[56]; -}; -STATIC_ASSERT(sizeof(struct snc_counter) == 64); /* Padding validation */ -STATIC_ASSERT(alignof(struct snc_counter) == 64); /* Prevent false sharing */ - -void snc_counter_add(struct snc_counter *counter, i64 x); -void snc_counter_wait(struct snc_counter *counter); diff --git a/src/tar/tar.h b/src/tar/tar.h index 8d5ff52c..b89c5923 100644 --- a/src/tar/tar.h +++ b/src/tar/tar.h @@ -2,7 +2,7 @@ #define TAR_H #include "../base/base.h" -#include "../sys/sys.h" +#include "../platform/platform.h" #include "tar_core.h" diff --git a/src/ttf/ttf_core_dwrite.cpp b/src/ttf/ttf_core_dwrite.cpp index 96757cc7..4f1ba9fd 100644 --- a/src/ttf/ttf_core_dwrite.cpp +++ b/src/ttf/ttf_core_dwrite.cpp @@ -59,7 +59,7 @@ TTF_StartupReceipt ttf_startup(void) #endif if (error != S_OK) { /* FIXME: Enable this */ - //sys_panic(LIT("Error creating DWrite factory")); + //P_Panic(LIT("Error creating DWrite factory")); (*(volatile int *)0) = 0; } diff --git a/src/user/user_core.c b/src/user/user_core.c index 71d05cf4..105f25fa 100644 --- a/src/user/user_core.c +++ b/src/user/user_core.c @@ -16,7 +16,7 @@ struct console_log { String msg; i32 level; i32 color_index; - struct sys_datetime datetime; + P_DateTime datetime; i64 time_ns; Rect bounds; struct console_log *prev; @@ -25,8 +25,8 @@ struct console_log { GLOBAL struct { Atomic32 shutdown; - struct snc_counter shutdown_job_counters; - struct sys_window *window; + P_Counter shutdown_job_counters; + P_Window *window; G_Swapchain *swapchain; struct sim_ctx *local_sim_ctx; @@ -34,10 +34,10 @@ GLOBAL struct { Arena *arena; String connect_address_str; - struct sim_client_store *user_client_store; - struct sim_client *user_unblended_client; /* Contains snapshots received from local sim */ - struct sim_client *user_blended_client; /* Contains single snapshot from result of blending local sim snapshots */ - struct sim_snapshot *ss_blended; /* Points to blended snapshot contained in blended client */ + ClientStore *user_client_store; + Client *user_unblended_client; /* Contains snapshots received from local sim */ + Client *user_blended_client; /* Contains single snapshot from result of blending local sim snapshots */ + Snapshot *ss_blended; /* Points to blended snapshot contained in blended client */ /* Usage stats */ i64 last_second_reset_ns; @@ -50,14 +50,14 @@ GLOBAL struct { struct bind_state bind_states[USER_BIND_KIND_COUNT]; /* Debug camera */ - struct sim_ent_id debug_following; + EntId debug_following; b32 debug_camera; b32 debug_camera_panning; V2 debug_camera_pan_start; b32 debug_draw; /* Debug console */ - struct snc_mutex console_logs_mutex; + P_Mutex console_logs_mutex; Arena *console_logs_arena; struct console_log *first_console_log; struct console_log *last_console_log; @@ -66,13 +66,13 @@ GLOBAL struct { b32 debug_console; /* Window -> user */ - struct snc_mutex sys_window_events_mutex; + P_Mutex sys_window_events_mutex; Arena *sys_window_events_arena; /* User -> local sim */ - struct snc_mutex user_sim_cmd_mutex; - struct sim_control user_sim_cmd_control; - struct sim_ent_id user_hovered_ent; + P_Mutex user_sim_cmd_mutex; + ControlData user_sim_cmd_control; + EntId user_hovered_ent; u64 last_user_sim_cmd_gen; u64 user_sim_cmd_gen; @@ -80,9 +80,9 @@ GLOBAL struct { Atomic32 user_paused_steps; /* Local sim -> user */ - struct snc_mutex local_to_user_client_mutex; - struct sim_client_store *local_to_user_client_store; - struct sim_client *local_to_user_client; + P_Mutex local_to_user_client_mutex; + ClientStore *local_to_user_client_store; + Client *local_to_user_client; i64 local_to_user_client_publish_dt_ns; i64 local_to_user_client_publish_time_ns; @@ -125,47 +125,47 @@ GLOBAL struct { /* TODO: Remove this */ -GLOBAL READONLY enum user_bind_kind g_binds[SYS_BTN_COUNT] = { - [SYS_BTN_W] = USER_BIND_KIND_MOVE_UP, - [SYS_BTN_S] = USER_BIND_KIND_MOVE_DOWN, - [SYS_BTN_A] = USER_BIND_KIND_MOVE_LEFT, - [SYS_BTN_D] = USER_BIND_KIND_MOVE_RIGHT, - //[SYS_BTN_ALT] = USER_BIND_KIND_WALK, - [SYS_BTN_M1] = USER_BIND_KIND_FIRE, - [SYS_BTN_M2] = USER_BIND_KIND_FIRE_ALT, +GLOBAL READONLY enum user_bind_kind g_binds[P_Btn_Count] = { + [P_Btn_W] = USER_BIND_KIND_MOVE_UP, + [P_Btn_S] = USER_BIND_KIND_MOVE_DOWN, + [P_Btn_A] = USER_BIND_KIND_MOVE_LEFT, + [P_Btn_D] = USER_BIND_KIND_MOVE_RIGHT, + //[P_Btn_Alt] = USER_BIND_KIND_WALK, + [P_Btn_M1] = USER_BIND_KIND_FIRE, + [P_Btn_M2] = USER_BIND_KIND_FIRE_ALT, /* Testing */ - [SYS_BTN_Z] = USER_BIND_KIND_TILE_TEST, + [P_Btn_Z] = USER_BIND_KIND_TILE_TEST, - [SYS_BTN_M5] = USER_BIND_KIND_DEBUG_DRAG, - [SYS_BTN_M4] = USER_BIND_KIND_DEBUG_DELETE, - [SYS_BTN_F] = USER_BIND_KIND_DEBUG_EXPLODE, - [SYS_BTN_T] = USER_BIND_KIND_DEBUG_TELEPORT, - [SYS_BTN_C] = USER_BIND_KIND_DEBUG_CLEAR, - [SYS_BTN_1] = USER_BIND_KIND_DEBUG_SPAWN1, - [SYS_BTN_2] = USER_BIND_KIND_DEBUG_SPAWN2, - [SYS_BTN_3] = USER_BIND_KIND_DEBUG_SPAWN3, - [SYS_BTN_4] = USER_BIND_KIND_DEBUG_SPAWN4, - [SYS_BTN_G] = USER_BIND_KIND_DEBUG_WALLS, - [SYS_BTN_N] = USER_BIND_KIND_DEBUG_STEP, - [SYS_BTN_Q] = USER_BIND_KIND_DEBUG_FOLLOW, - [SYS_BTN_F1] = USER_BIND_KIND_DEBUG_PAUSE, - [SYS_BTN_F2] = USER_BIND_KIND_DEBUG_CAMERA, - [SYS_BTN_F3] = USER_BIND_KIND_DEBUG_DRAW, - [SYS_BTN_F4] = USER_BIND_KIND_DEBUG_TOGGLE_TOPMOST, - [SYS_BTN_GRAVE_ACCENT] = USER_BIND_KIND_DEBUG_CONSOLE, - [SYS_BTN_ALT] = USER_BIND_KIND_FULLSCREEN_MOD, - [SYS_BTN_ENTER] = USER_BIND_KIND_FULLSCREEN, - [SYS_BTN_MWHEELUP] = USER_BIND_KIND_ZOOM_IN, - [SYS_BTN_MWHEELDOWN] = USER_BIND_KIND_ZOOM_OUT, - [SYS_BTN_M3] = USER_BIND_KIND_PAN, + [P_Btn_M5] = USER_BIND_KIND_DEBUG_DRAG, + [P_Btn_M4] = USER_BIND_KIND_DEBUG_DELETE, + [P_Btn_F] = USER_BIND_KIND_DEBUG_EXPLODE, + [P_Btn_T] = USER_BIND_KIND_DEBUG_TELEPORT, + [P_Btn_C] = USER_BIND_KIND_DEBUG_CLEAR, + [P_Btn_1] = USER_BIND_KIND_DEBUG_SPAWN1, + [P_Btn_2] = USER_BIND_KIND_DEBUG_SPAWN2, + [P_Btn_3] = USER_BIND_KIND_DEBUG_SPAWN3, + [P_Btn_4] = USER_BIND_KIND_DEBUG_SPAWN4, + [P_Btn_G] = USER_BIND_KIND_DEBUG_WALLS, + [P_Btn_N] = USER_BIND_KIND_DEBUG_STEP, + [P_Btn_Q] = USER_BIND_KIND_DEBUG_FOLLOW, + [P_Btn_F1] = USER_BIND_KIND_DEBUG_PAUSE, + [P_Btn_F2] = USER_BIND_KIND_DEBUG_CAMERA, + [P_Btn_F3] = USER_BIND_KIND_DEBUG_DRAW, + [P_Btn_F4] = USER_BIND_KIND_DEBUG_TOGGLE_TOPMOST, + [P_Btn_GraveAccent] = USER_BIND_KIND_DEBUG_CONSOLE, + [P_Btn_Alt] = USER_BIND_KIND_FULLSCREEN_MOD, + [P_Btn_Enter] = USER_BIND_KIND_FULLSCREEN, + [P_Btn_MWheelUp] = USER_BIND_KIND_ZOOM_IN, + [P_Btn_MWheelDown] = USER_BIND_KIND_ZOOM_OUT, + [P_Btn_M3] = USER_BIND_KIND_PAN, #if RTC /* Debug */ - [SYS_BTN_FORWARD_SLASH] = USER_BIND_KIND_RESET_DEBUG_STEPS, - [SYS_BTN_COMMA] = USER_BIND_KIND_DECR_DEBUG_STEPS, - [SYS_BTN_PERIOD] = USER_BIND_KIND_INCR_DEBUG_STEPS + [P_Btn_ForwardSlash] = USER_BIND_KIND_RESET_DEBUG_STEPS, + [P_Btn_Comma] = USER_BIND_KIND_DECR_DEBUG_STEPS, + [P_Btn_Period] = USER_BIND_KIND_INCR_DEBUG_STEPS #endif }; @@ -173,19 +173,19 @@ GLOBAL READONLY enum user_bind_kind g_binds[SYS_BTN_COUNT] = { * Startup * ========================== */ -INTERNAL SYS_EXIT_FUNC(user_shutdown); +INTERNAL P_ExitFuncDef(user_shutdown); INTERNAL LOG_EVENT_CALLBACK_FUNC_DEF(debug_console_log_callback, log); -INTERNAL SYS_JOB_DEF(user_update_job, _); -INTERNAL SYS_JOB_DEF(local_sim_job , _); +INTERNAL P_JobDef(user_update_job, _); +INTERNAL P_JobDef(local_sim_job , _); struct user_startup_receipt user_startup(F_StartupReceipt *font_sr, - struct sprite_startup_receipt *sprite_sr, + S_StartupReceipt *sprite_sr, D_StartupReceipt *draw_sr, AC_StartupReceipt *asset_cache_sr, - struct sound_startup_receipt *sound_sr, + SND_StartupReceipt *sound_sr, M_StartupReceipt *mixer_sr, N_StartupReceipt *host_sr, - struct sim_startup_receipt *sim_sr, + SimStartupReceipt *sim_sr, String connect_address_str) { __prof; @@ -201,7 +201,7 @@ struct user_startup_receipt user_startup(F_StartupReceipt *font_sr, gstat_set(GSTAT_DEBUG_STEPS, U64_MAX); G.arena = arena_alloc(GIBI(64)); - G.real_time_ns = sys_time_ns(); + G.real_time_ns = P_TimeNs(); /* TODO: Remove this */ G.connect_address_str = string_copy(G.arena, connect_address_str); @@ -228,24 +228,24 @@ struct user_startup_receipt user_startup(F_StartupReceipt *font_sr, //log_register_callback(debug_console_log_callback, LOG_LEVEL_SUCCESS); log_register_callback(debug_console_log_callback, LOG_LEVEL_DEBUG); - G.window = sys_window_alloc(); + G.window = P_AllocWindow(); G.swapchain = gp_swapchain_alloc(G.window, V2i32FromXY(100, 100)); - sys_window_show(G.window); + P_ShowWindow(G.window); /* Start jobs */ - sys_run(1, user_update_job, 0, SYS_POOL_USER, SYS_PRIORITY_HIGH, &G.shutdown_job_counters); - sys_run(1, local_sim_job, 0, SYS_POOL_SIM, SYS_PRIORITY_HIGH, &G.shutdown_job_counters); - sys_on_exit(&user_shutdown); + P_Run(1, user_update_job, 0, P_Pool_User, P_Priority_High, &G.shutdown_job_counters); + P_Run(1, local_sim_job, 0, P_Pool_Sim, P_Priority_High, &G.shutdown_job_counters); + P_OnExit(&user_shutdown); return (struct user_startup_receipt) { 0 }; } -INTERNAL SYS_EXIT_FUNC(user_shutdown) +INTERNAL P_ExitFuncDef(user_shutdown) { __prof; atomic32_fetch_set(&G.shutdown, 1); snc_counter_wait(&G.shutdown_job_counters); - sys_window_release(G.window); + P_ReleaseWindow(G.window); } /* ========================== * @@ -296,7 +296,7 @@ INTERNAL void debug_draw_movement(struct sim_ent *ent) INTERNAL String get_ent_debug_text(Arena *arena, struct sim_ent *ent) { TempArena scratch = scratch_begin(arena); - struct sim_snapshot *ss = ent->ss; + Snapshot *ss = ent->ss; const u8 hex[] = "0123456789abcdef"; @@ -388,7 +388,7 @@ INTERNAL String get_ent_debug_text(Arena *arena, struct sim_ent *ent) INTERNAL LOG_EVENT_CALLBACK_FUNC_DEF(debug_console_log_callback, log) { __prof; - struct snc_lock lock = snc_lock_e(&G.console_logs_mutex); + P_Lock lock = snc_lock_e(&G.console_logs_mutex); { struct console_log *clog = arena_push(G.console_logs_arena, struct console_log); clog->level = log.level; @@ -446,10 +446,10 @@ INTERNAL void draw_debug_console(i32 level, b32 minimized) } G.console_logs_height = 0; - i64 now_ns = sys_time_ns(); + i64 now_ns = P_TimeNs(); F_Font *font = font_load_async(LIT("font/fixedsys.ttf"), 12.0f); if (font) { - struct snc_lock lock = snc_lock_e(&G.console_logs_mutex); + P_Lock lock = snc_lock_e(&G.console_logs_mutex); { for (struct console_log *log = G.last_console_log; log; log = log->prev) { f32 opacity = 0.75; @@ -466,7 +466,7 @@ INTERNAL void draw_debug_console(i32 level, b32 minimized) /* Draw text */ String text = log->msg; if (!minimized) { - struct sys_datetime datetime = log->datetime; + P_DateTime datetime = log->datetime; text = string_format( scratch.arena, LIT("[%F:%F:%F.%F] %F"), @@ -548,7 +548,7 @@ INTERNAL SORT_COMPARE_FUNC_DEF(ent_draw_order_cmp, arg_a, arg_b, udata) * Update * ========================== */ -INTERNAL void user_update(struct sys_window *window) +INTERNAL void user_update(P_Window *window) { __prof; @@ -558,11 +558,11 @@ INTERNAL void user_update(struct sys_window *window) * Begin frame * ========================== */ - G.real_dt_ns = sys_time_ns() - G.real_time_ns; + G.real_dt_ns = P_TimeNs() - G.real_time_ns; G.real_time_ns += G.real_dt_ns; - G.screen_size = sys_window_get_size(window); + G.screen_size = P_GetWindowSize(window); - struct sprite_scope *sprite_frame_scope = sprite_scope_begin(); + S_Scope *sprite_frame_scope = sprite_scope_begin(); /* ========================== * * Pull latest local sim snapshot @@ -570,11 +570,11 @@ INTERNAL void user_update(struct sys_window *window) { __profn("Pull snapshot"); - struct snc_lock lock = snc_lock_e(&G.local_to_user_client_mutex); + P_Lock lock = snc_lock_e(&G.local_to_user_client_mutex); u64 old_last_tick = G.user_unblended_client->last_tick; u64 last_tick = G.local_to_user_client->last_tick; if (last_tick > old_last_tick) { - struct sim_snapshot *src = sim_snapshot_from_tick(G.local_to_user_client, last_tick); + Snapshot *src = sim_snapshot_from_tick(G.local_to_user_client, last_tick); sim_snapshot_alloc(G.user_unblended_client, src, src->tick); G.last_local_to_user_snapshot_published_at_ns = G.local_to_user_client_publish_time_ns; G.average_local_to_user_snapshot_publish_dt_ns -= G.average_local_to_user_snapshot_publish_dt_ns / 50; @@ -597,7 +597,7 @@ INTERNAL void user_update(struct sys_window *window) } /* Predict local sim time based on average snapshot publish dt. */ - struct sim_snapshot *newest_snapshot = sim_snapshot_from_tick(G.user_unblended_client, G.user_unblended_client->last_tick); + Snapshot *newest_snapshot = sim_snapshot_from_tick(G.user_unblended_client, G.user_unblended_client->last_tick); G.local_sim_last_known_time_ns = newest_snapshot->sim_time_ns; G.local_sim_last_known_tick = newest_snapshot->tick; if (atomic32_fetch(&G.user_paused)) { @@ -621,10 +621,10 @@ INTERNAL void user_update(struct sys_window *window) } /* Get two snapshots nearest to render time */ - struct sim_snapshot *left_snapshot = sim_snapshot_nil(); - struct sim_snapshot *right_snapshot = newest_snapshot; + Snapshot *left_snapshot = sim_snapshot_nil(); + Snapshot *right_snapshot = newest_snapshot; { - struct sim_snapshot *ss = sim_snapshot_from_tick(G.user_unblended_client, G.user_unblended_client->first_tick); + Snapshot *ss = sim_snapshot_from_tick(G.user_unblended_client, G.user_unblended_client->first_tick); while (ss->valid) { u64 next_tick = ss->next_tick; i64 ss_time_ns = ss->sim_time_ns; @@ -678,7 +678,7 @@ INTERNAL void user_update(struct sys_window *window) { __profn("Process sys events"); - struct sys_window_event_array events = sys_window_pop_events(scratch.arena, window); + P_WindowEventArray events = P_PopWindowEvents(scratch.arena, window); /* Reset bind pressed / released states */ for (u32 i = 0; i < countof(G.bind_states); ++i) { @@ -688,32 +688,32 @@ INTERNAL void user_update(struct sys_window *window) } for (u64 ent_index = 0; ent_index < events.count; ++ent_index) { - struct sys_window_event *event = &events.events[ent_index]; - if (event->kind == SYS_EVENT_KIND_QUIT) { - sys_exit(); + P_WindowEvent *event = &events.events[ent_index]; + if (event->kind == P_WindowEventKind_Quit) { + P_Exit(); } - if (event->kind == SYS_EVENT_KIND_BUTTON_UP) { + if (event->kind == P_WindowEventKind_ButtonUp) { /* Escape quit */ - if (event->button == SYS_BTN_ESC) { - sys_exit(); + if (event->button == P_Btn_ESC) { + P_Exit(); } } /* Update mouse pos */ - if (event->kind == SYS_EVENT_KIND_CURSOR_MOVE) { + if (event->kind == P_WindowEventKind_CursorMove) { G.screen_cursor = event->cursor_position; } /* Update bind states */ - if ((event->kind == SYS_EVENT_KIND_BUTTON_DOWN || event->kind == SYS_EVENT_KIND_BUTTON_UP)) { - enum sys_btn button = event->button; - button = button >= SYS_BTN_COUNT ? SYS_BTN_NONE : button; + if ((event->kind == P_WindowEventKind_ButtonDown|| event->kind == P_WindowEventKind_ButtonUp)) { + P_Btn button = event->button; + button = button >= P_Btn_Count ? P_Btn_None : button; enum user_bind_kind bind = g_binds[button]; if (bind) { - b32 pressed = event->kind == SYS_EVENT_KIND_BUTTON_DOWN; + b32 pressed = event->kind == P_WindowEventKind_ButtonDown; #if 0 - b32 out_of_bounds = button >= SYS_BTN_M1 && button <= SYS_BTN_M5 && + b32 out_of_bounds = button >= P_Btn_M1 && button <= P_Btn_M5 && (G.ui_cursor.x < 0 || G.ui_cursor.y < 0 || G.ui_cursor.x > G.ui_size.x || @@ -782,9 +782,9 @@ INTERNAL void user_update(struct sys_window *window) /* Test fullscreen */ { if (G.bind_states[USER_BIND_KIND_FULLSCREEN].num_presses && G.bind_states[USER_BIND_KIND_FULLSCREEN_MOD].is_held) { - struct sys_window_settings settings = sys_window_get_settings(window); - settings.flags ^= SYS_WINDOW_SETTINGS_FLAG_FULLSCREEN; - sys_window_update_settings(window, &settings); + P_WindowSettings settings = P_GetWindowSettings(window); + settings.flags ^= P_WindowSettingsFlag_Fullscreen; + P_UpdateWindowSettings(window, &settings); } } @@ -793,7 +793,7 @@ INTERNAL void user_update(struct sys_window *window) } if (G.bind_states[USER_BIND_KIND_DEBUG_TOGGLE_TOPMOST].num_presses > 0) { - sys_window_toggle_topmost(window); + P_ToggleWindowTopmost(window); logf_success("Toggle topmost"); } @@ -1166,7 +1166,7 @@ INTERNAL void user_update(struct sys_window *window) if (!sim_ent_is_valid_and_active(ent)) continue; //if (sprite_tag_is_nil(ent->sprite)) continue; - struct sprite_tag sprite = ent->sprite; + S_Tag sprite = ent->sprite; struct sim_ent *parent = sim_ent_from_id(G.ss_blended, ent->parent); @@ -1223,15 +1223,15 @@ INTERNAL void user_update(struct sys_window *window) /* Draw sprite */ if (!sprite_tag_is_nil(sprite)) { - struct sprite_sheet *sheet = sprite_sheet_from_tag_async(sprite_frame_scope, sprite); - struct sprite_texture *texture = sprite_texture_from_tag_async(sprite_frame_scope, sprite); + S_Sheet *sheet = sprite_sheet_from_tag_async(sprite_frame_scope, sprite); + S_Texture *texture = sprite_texture_from_tag_async(sprite_frame_scope, sprite); /* TODO: Fade in placeholder if texture isn't loaded */ if (sheet->loaded && texture->loaded) { b32 is_light = sim_ent_has_prop(ent, SEPROP_LIGHT_TEST); V3 emittance = ent->sprite_emittance; u32 tint = ent->sprite_tint; - struct sprite_sheet_frame frame = sprite_sheet_get_frame(sheet, ent->animation_frame); + S_SheetFrame frame = sprite_sheet_get_frame(sheet, ent->animation_frame); D_MaterialParams params = DRAW_MATERIAL_PARAMS(.xf = sprite_xform, .texture = texture->gp_texture, .tint = tint, .clip = frame.clip, .is_light = is_light, .light_emittance = emittance); draw_material(G.render_sig, params); } @@ -1241,14 +1241,14 @@ INTERNAL void user_update(struct sys_window *window) /* TODO: Something better */ if (sim_ent_has_prop(ent, SEPROP_TILE_CHUNK)) { V2i32 chunk_index = ent->tile_chunk_index; - struct sprite_tag tile_sprite = sprite_tag_from_path(LIT("sprite/tile.ase")); - struct sprite_texture *tile_texture = sprite_texture_from_tag_async(sprite_frame_scope, tile_sprite); + S_Tag tile_sprite = sprite_tag_from_path(LIT("sprite/tile.ase")); + S_Texture *tile_texture = sprite_texture_from_tag_async(sprite_frame_scope, tile_sprite); if (tile_texture->loaded) { f32 tile_size = 1.f / SIM_TILES_PER_UNIT_SQRT; for (i32 tile_y = 0; tile_y < SIM_TILES_PER_CHUNK_SQRT; ++tile_y) { for (i32 tile_x = 0; tile_x < SIM_TILES_PER_CHUNK_SQRT; ++tile_x) { V2i32 local_tile_index = V2i32FromXY(tile_x, tile_y); - enum sim_tile_kind tile = ent->tile_chunk_tiles[local_tile_index.x + (local_tile_index.y * SIM_TILES_PER_CHUNK_SQRT)]; + TileKind tile = ent->tile_chunk_tiles[local_tile_index.x + (local_tile_index.y * SIM_TILES_PER_CHUNK_SQRT)]; //if (tile > -1) { if (tile == SIM_TILE_KIND_WALL) { V2i32 world_tile_index = sim_world_tile_index_from_local_tile_index(chunk_index, local_tile_index); @@ -1289,8 +1289,8 @@ INTERNAL void user_update(struct sys_window *window) /* Draw focus arrow */ if (ent == local_control || sim_ent_id_eq(ent->id, G.debug_following)) { - struct sprite_sheet *sheet = sprite_sheet_from_tag_async(sprite_frame_scope, ent->sprite); - struct sprite_sheet_slice slice = sprite_sheet_get_slice(sheet, LIT("attach.wep"), ent->animation_frame); + S_Sheet *sheet = sprite_sheet_from_tag_async(sprite_frame_scope, ent->sprite); + S_SheetSlice slice = sprite_sheet_get_slice(sheet, LIT("attach.wep"), ent->animation_frame); V2 start = xform_mul_v2(sprite_xform, slice.center); start = xform_mul_v2(G.world_to_ui_xf, start); V2 end = v2_add(xf.og, ent->control.focus); @@ -1301,18 +1301,18 @@ INTERNAL void user_update(struct sys_window *window) #if 0 /* Draw slices */ if (!sprite_tag_is_nil(ent->sprite)) { - struct sprite_sheet *sheet = sprite_sheet_from_tag_async(sprite_frame_scope, sprite); + S_Sheet *sheet = sprite_sheet_from_tag_async(sprite_frame_scope, sprite); u32 quad_color = RGBA32_F(1, 0, 0.5, 1); u32 point_color = RGBA32_F(1, 0, 0, 1); u32 ray_color = RGBA32_F(1, 0, 0.5, 1); for (u64 i = 0; i < sheet->slice_groups_count; ++i) { - struct sprite_sheet_slice_group *group = &sheet->slice_groups[i]; + S_SheetSliceGroup *group = &sheet->slice_groups[i]; if (string_ends_with(group->name, LIT(".ray"))) continue; for (u32 j = 0; j < group->per_frame_count; ++j) { - struct sprite_sheet_slice slice = group->frame_slices[(ent->animation_frame * group->per_frame_count) + j]; + S_SheetSlice slice = group->frame_slices[(ent->animation_frame * group->per_frame_count) + j]; V2 center = xform_mul_v2(sprite_xform, slice.center); center = xform_mul_v2(G.world_to_ui_xf, center); @@ -1404,7 +1404,7 @@ INTERNAL void user_update(struct sys_window *window) /* Draw contact constraint */ if (sim_ent_has_prop(ent, SEPROP_CONTACT_CONSTRAINT)) { - struct phys_contact_constraint *data = &ent->contact_constraint_data; + ContactConstraint *data = &ent->contact_constraint_data; struct sim_ent *e0 = sim_ent_from_id(G.ss_blended, data->e0); struct sim_ent *e1 = sim_ent_from_id(G.ss_blended, data->e1); (UNUSED)e0; @@ -1416,7 +1416,7 @@ INTERNAL void user_update(struct sys_window *window) f32 radius = 5; for (u32 i = 0; i < data->num_points; ++i) { u32 color = (data->skip_solve || data->wrong_dir) ? ALPHA32_F(COLOR_YELLOW, 0.3) : RGBA32_F(0.8, 0.2, 0.2, 1); - struct phys_contact_point point = data->points[i]; + ContactPoint point = data->points[i]; V2 dbg_pt = point.dbg_pt; /* Draw point */ @@ -1473,7 +1473,7 @@ INTERNAL void user_update(struct sys_window *window) /* Draw collision debug */ #if COLLIDER_DEBUG if (sim_ent_has_prop(ent, SEPROP_COLLISION_DEBUG)) { - struct phys_collision_debug *data = &ent->collision_debug_data; + CollisionDebugData *data = &ent->collision_debug_data; CLD_CollisionResult collider_res = data->res; struct sim_ent *e0 = sim_ent_from_id(G.ss_blended, data->e0); struct sim_ent *e1 = sim_ent_from_id(G.ss_blended, data->e1); @@ -1693,8 +1693,8 @@ INTERNAL void user_update(struct sys_window *window) if (!G.debug_camera) { __profn("Draw crosshair"); V2 crosshair_pos = G.ui_cursor; - struct sprite_tag crosshair = sprite_tag_from_path(LIT("sprite/crosshair.ase")); - struct sprite_texture *t = sprite_texture_from_tag_async(sprite_frame_scope, crosshair); + S_Tag crosshair = sprite_tag_from_path(LIT("sprite/crosshair.ase")); + S_Texture *t = sprite_texture_from_tag_async(sprite_frame_scope, crosshair); V2 size = V2FromXY(t->width, t->height); Xform xf = XFORM_TRS(.t = crosshair_pos, .s = size); draw_ui_rect(G.render_sig, DRAW_UI_RECT_PARAMS(.xf = xf, .texture = t->gp_texture)); @@ -1705,17 +1705,17 @@ INTERNAL void user_update(struct sys_window *window) { __profn("Update window cursor"); if (G.debug_camera) { - sys_window_cursor_disable_clip(G.window); - sys_window_cursor_show(G.window); + P_DisableWindoweCursorClip(G.window); + P_ShowWindowCursor(G.window); } else { - struct sprite_texture *t = sprite_texture_from_tag_async(sprite_frame_scope, sprite_tag_from_path(LIT("sprite/crosshair.ase"))); + S_Texture *t = sprite_texture_from_tag_async(sprite_frame_scope, sprite_tag_from_path(LIT("sprite/crosshair.ase"))); V2 size = V2FromXY(t->width, t->height); Rect cursor_clip = RECT_FROM_V2(G.ui_screen_offset, G.ui_size); cursor_clip.pos = v2_add(cursor_clip.pos, v2_mul(size, 0.5f)); cursor_clip.pos = v2_add(cursor_clip.pos, V2FromXY(1, 1)); cursor_clip.size = v2_sub(cursor_clip.size, size); - sys_window_cursor_hide(G.window); - sys_window_cursor_enable_clip(G.window, cursor_clip); + P_HideWindowCursor(G.window); + P_EnableWindoweCursorClip(G.window, cursor_clip); } } #endif @@ -1780,7 +1780,7 @@ INTERNAL void user_update(struct sys_window *window) /* Queue player control cmd */ { - struct sim_control control = ZI; + ControlData control = ZI; control.move = input_move_dir; control.focus = input_aim_dir; control.dbg_cursor = G.world_cursor; @@ -1848,7 +1848,7 @@ INTERNAL void user_update(struct sys_window *window) /* Set user sim control */ { - struct snc_lock lock = snc_lock_e(&G.user_sim_cmd_mutex); + P_Lock lock = snc_lock_e(&G.user_sim_cmd_mutex); /* Reset flags */ if (G.user_sim_cmd_gen != G.last_user_sim_cmd_gen) { @@ -1882,7 +1882,7 @@ INTERNAL void user_update(struct sys_window *window) { /* Update network usage stats */ - i64 stat_now_ns = sys_time_ns(); + i64 stat_now_ns = P_TimeNs(); G.net_bytes_read.last_second_end = gstat_get(GSTAT_SOCK_BYTES_RECEIVED); G.net_bytes_sent.last_second_end = gstat_get(GSTAT_SOCK_BYTES_SENT); if (stat_now_ns - G.last_second_reset_ns > NS_FROM_SECONDS(1)) { @@ -2081,12 +2081,12 @@ INTERNAL void user_update(struct sys_window *window) scratch_end(scratch); } -INTERNAL SYS_JOB_DEF(user_update_job, _) +INTERNAL P_JobDef(user_update_job, _) { (UNUSED)_; - i64 time_ns = sys_time_ns(); + i64 time_ns = P_TimeNs(); while (!atomic32_fetch(&G.shutdown)) { - struct sys_window *window = G.window; + P_Window *window = G.window; { __profn("User sleep"); { @@ -2096,7 +2096,7 @@ INTERNAL SYS_JOB_DEF(user_update_job, _) { __profn("Frame limiter wait"); sys_sleep_frame(time_ns, 1000000000 / FPS_LIMIT); - time_ns = sys_time_ns(); + time_ns = P_TimeNs(); } } user_update(window); @@ -2117,10 +2117,10 @@ INTERNAL SYS_JOB_DEF(user_update_job, _) -INTERNAL void generate_user_input_cmds(struct sim_client *user_input_client, u64 tick) +INTERNAL void generate_user_input_cmds(Client *user_input_client, u64 tick) { - struct sim_snapshot *prev_user_input_ss = sim_snapshot_from_tick(user_input_client, user_input_client->last_tick); - struct sim_snapshot *user_input_ss = sim_snapshot_alloc(user_input_client, prev_user_input_ss, tick); + Snapshot *prev_user_input_ss = sim_snapshot_from_tick(user_input_client, user_input_client->last_tick); + Snapshot *user_input_ss = sim_snapshot_alloc(user_input_client, prev_user_input_ss, tick); struct sim_ent *user_input_root = sim_ent_from_id(user_input_ss, SIM_ENT_ROOT_ID); /* Find / create local control cmd ent */ struct sim_ent *control_cmd = sim_ent_find_first_match_one(user_input_ss, SEPROP_CMD); @@ -2132,7 +2132,7 @@ INTERNAL void generate_user_input_cmds(struct sim_client *user_input_client, u64 sim_ent_activate(control_cmd, user_input_ss->tick); } { - struct snc_lock lock = snc_lock_e(&G.user_sim_cmd_mutex); + P_Lock lock = snc_lock_e(&G.user_sim_cmd_mutex); /* Update control cmd */ { control_cmd->cmd_control = G.user_sim_cmd_control; @@ -2166,7 +2166,7 @@ INTERNAL void generate_user_input_cmds(struct sim_client *user_input_client, u64 struct sim_ss_decode_node { - struct sim_client *client; + Client *client; u64 tick; u64 base_tick; String tmp_encoded; @@ -2179,7 +2179,7 @@ struct sim_decode_queue { }; -INTERNAL SYS_JOB_DEF(local_sim_job, _) +INTERNAL P_JobDef(local_sim_job, _) { (UNUSED)_; @@ -2196,7 +2196,7 @@ INTERNAL SYS_JOB_DEF(local_sim_job, _) N_Host *host; if (G.connect_address_str.len > 0) { host = host_alloc(0); - struct sys_address addr = sys_address_from_string(G.connect_address_str); + P_Address addr = P_AddressFromString(G.connect_address_str); host_queue_connect_to_address(host, addr); } else { host = host_alloc(12345); @@ -2205,15 +2205,15 @@ INTERNAL SYS_JOB_DEF(local_sim_job, _) Bitbuff msg_writer_bb = bitbuff_alloc(GIBI(64)); Bitbuff snapshot_writer_bb = bitbuff_alloc(GIBI(64)); - struct sim_accel accel = sim_accel_alloc(); + SimAccel accel = sim_accel_alloc(); - struct sim_client_store *store = sim_client_store_alloc(); - struct sim_client *user_input_client = sim_client_alloc(store); /* Stores snapshots containing commands to be published to local client */ - struct sim_client *local_client = sim_client_alloc(store); /* Stores snapshots produced locally */ - struct sim_client *publish_client = sim_client_alloc(store); /* Stores versions of local snapshots that will be published to remote sims */ + ClientStore *store = sim_client_store_alloc(); + Client *user_input_client = sim_client_alloc(store); /* Stores snapshots containing commands to be published to local client */ + Client *local_client = sim_client_alloc(store); /* Stores snapshots produced locally */ + Client *publish_client = sim_client_alloc(store); /* Stores versions of local snapshots that will be published to remote sims */ - struct sim_client *master_client = sim_client_nil(); /* Stores snapshots received from master */ - struct sim_client *master_blended_client = sim_client_nil(); /* Stores interpolated master snapshots */ + Client *master_client = sim_client_nil(); /* Stores snapshots received from master */ + Client *master_blended_client = sim_client_nil(); /* Stores interpolated master snapshots */ b32 initialized_from_master = 0; @@ -2265,7 +2265,7 @@ INTERNAL SYS_JOB_DEF(local_sim_job, _) { __profn("Sim update"); - real_dt_ns = sys_time_ns() - real_time_ns; + real_dt_ns = P_TimeNs() - real_time_ns; real_time_ns += real_dt_ns; N_EventList host_events = host_update_begin(scratch.arena, host); @@ -2275,7 +2275,7 @@ INTERNAL SYS_JOB_DEF(local_sim_job, _) { for (N_Event *event = host_events.first; event; event = event->next) { N_ChannelId channel_id = event->channel_id; - struct sim_client *client = sim_client_from_channel_id(store, channel_id); + Client *client = sim_client_from_channel_id(store, channel_id); switch (event->kind) { case HOST_EVENT_KIND_CHANNEL_OPENED: { @@ -2330,7 +2330,7 @@ INTERNAL SYS_JOB_DEF(local_sim_job, _) tmp_encoded.text = br_read_bytes_raw(&decoder_br, tmp_encoded.len); if (!tmp_encoded.text) tmp_encoded.len = 0; - struct sim_snapshot *base_ss = sim_snapshot_from_tick(client, base_tick); + Snapshot *base_ss = sim_snapshot_from_tick(client, base_tick); if (base_ss->tick == base_tick) { if (is_master) { /* Queue incoming slave client snapshot for decoding */ @@ -2392,16 +2392,16 @@ INTERNAL SYS_JOB_DEF(local_sim_job, _) /* Decode incoming snapshots */ for (struct sim_ss_decode_node *n = queue.first; n; n = n->next) { - struct sim_client *client = n->client; + Client *client = n->client; u64 base_tick = n->base_tick; u64 tick = n->tick; - struct sim_snapshot *base_ss = sim_snapshot_from_tick(client, base_tick); + Snapshot *base_ss = sim_snapshot_from_tick(client, base_tick); if (base_ss->tick == base_tick) { Bitbuff bb = bitbuff_from_string(n->tmp_encoded); BitbuffReader br = br_from_bitbuff(&bb); /* Alloc & decode snapshot */ - struct sim_snapshot *ss = sim_snapshot_alloc(client, base_ss, tick); + Snapshot *ss = sim_snapshot_alloc(client, base_ss, tick); sim_snapshot_decode(&br, ss); /* Assume all incoming ents want to be sync srcs */ @@ -2440,7 +2440,7 @@ INTERNAL SYS_JOB_DEF(local_sim_job, _) /* Update networked clients */ u64 oldest_client_ack = 0; for (u64 i = 0; i < store->num_clients_reserved; ++i) { - struct sim_client *client = &store->clients[i]; + Client *client = &store->clients[i]; if (client->valid && client != local_client && client != publish_client && client != user_input_client && client != master_client) { client->last_rtt_ns = host_get_channel_last_rtt_ns(host, client->channel_id); /* Release unneeded received snapshots */ @@ -2493,14 +2493,14 @@ INTERNAL SYS_JOB_DEF(local_sim_job, _) /* Step master */ u64 prev_tick = local_client->last_tick; u64 next_tick = prev_tick + 1; - struct sim_step_ctx ctx = ZI; + SimStepCtx ctx = ZI; ctx.is_master = is_master; ctx.sim_dt_ns = step_dt_ns; ctx.accel = &accel; ctx.user_input_client = user_input_client; ctx.master_client = master_client; ctx.publish_client = publish_client; - struct sim_snapshot *prev_world = sim_snapshot_from_tick(local_client, prev_tick); + Snapshot *prev_world = sim_snapshot_from_tick(local_client, prev_tick); ctx.world = sim_snapshot_alloc(local_client, prev_world, next_tick); generate_user_input_cmds(user_input_client, next_tick); sim_step(&ctx); @@ -2511,7 +2511,7 @@ INTERNAL SYS_JOB_DEF(local_sim_job, _) b32 master_ss_is_blended = 0; - struct sim_snapshot *master_ss = sim_snapshot_nil(); + Snapshot *master_ss = sim_snapshot_nil(); { /* How along are we between master sim ticks (0 = start of tick, 1 = end of tick) */ f64 tick_progress = 0; @@ -2521,7 +2521,7 @@ INTERNAL SYS_JOB_DEF(local_sim_job, _) } /* Predict master sim time based on average snapshot publish dt. */ - struct sim_snapshot *newest_snapshot = sim_snapshot_from_tick(master_client, master_client->last_tick); + Snapshot *newest_snapshot = sim_snapshot_from_tick(master_client, master_client->last_tick); i64 master_sim_predicted_time_ns = newest_snapshot->sim_time_ns + (newest_snapshot->sim_dt_ns * tick_progress); /* Determine blend time */ @@ -2539,10 +2539,10 @@ INTERNAL SYS_JOB_DEF(local_sim_job, _) /* Get snapshot nearest to master blend time */ /* TODO: Blend */ - struct sim_snapshot *left_snapshot = sim_snapshot_nil(); - struct sim_snapshot *right_snapshot = newest_snapshot; + Snapshot *left_snapshot = sim_snapshot_nil(); + Snapshot *right_snapshot = newest_snapshot; { - struct sim_snapshot *ss = sim_snapshot_from_tick(master_client, master_client->first_tick); + Snapshot *ss = sim_snapshot_from_tick(master_client, master_client->first_tick); while (ss->valid) { u64 next_tick = ss->next_tick; i64 ss_time_ns = ss->sim_time_ns; @@ -2665,7 +2665,7 @@ INTERNAL SYS_JOB_DEF(local_sim_job, _) } /* Sync master with local base tick */ - struct sim_snapshot *base_ss = sim_snapshot_from_tick(local_client, step_base_tick); + Snapshot *base_ss = sim_snapshot_from_tick(local_client, step_base_tick); if (mispredicted_tick) { if (base_ss->valid) { sim_snapshot_sync_ents(base_ss, master_ss, master_player->id, 0); @@ -2680,7 +2680,7 @@ INTERNAL SYS_JOB_DEF(local_sim_job, _) /* Step */ generate_user_input_cmds(user_input_client, step_end_tick); { - struct sim_step_ctx ctx = ZI; + SimStepCtx ctx = ZI; ctx.is_master = is_master; ctx.sim_dt_ns = step_dt_ns; ctx.accel = &accel; @@ -2689,7 +2689,7 @@ INTERNAL SYS_JOB_DEF(local_sim_job, _) ctx.publish_client = publish_client; u64 step_tick = step_base_tick + 1; - struct sim_snapshot *prev_ss = base_ss; + Snapshot *prev_ss = base_ss; while (step_tick <= step_end_tick) { ctx.world = sim_snapshot_alloc(local_client, prev_ss, step_tick); if (!mispredicted_tick && step_tick == step_end_tick) { @@ -2705,15 +2705,15 @@ INTERNAL SYS_JOB_DEF(local_sim_job, _) /* Publish snapshot to remote clients */ for (u64 i = 0; i < store->num_clients_reserved; ++i) { - struct sim_client *client = &store->clients[i]; + Client *client = &store->clients[i]; if (client->valid && client != user_input_client && client != local_client && client != publish_client) { BitbuffWriter msg_bw = bw_from_bitbuff(&msg_writer_bb); bw_write_uv(&msg_bw, client->highest_received_tick); /* ack */ bw_write_uv(&msg_bw, client->ack); /* double ack */ - struct sim_snapshot *base_ss = sim_snapshot_from_tick(publish_client, client->ack); - struct sim_snapshot *publish_ss; + Snapshot *base_ss = sim_snapshot_from_tick(publish_client, client->ack); + Snapshot *publish_ss; if (client == master_client) { /* If sending to master, start sending all snapshots since last ack */ publish_ss = sim_snapshot_from_closest_tick_gte(publish_client, base_ss->tick + 1); @@ -2747,12 +2747,12 @@ INTERNAL SYS_JOB_DEF(local_sim_job, _) /* Copy local snapshot to user client */ { - struct sim_snapshot *local_ss = sim_snapshot_from_tick(local_client, local_client->last_tick); + Snapshot *local_ss = sim_snapshot_from_tick(local_client, local_client->last_tick); if (local_ss->valid) { /* TODO: Double buffer */ - struct snc_lock lock = snc_lock_e(&G.local_to_user_client_mutex); + P_Lock lock = snc_lock_e(&G.local_to_user_client_mutex); sim_snapshot_alloc(G.local_to_user_client, local_ss, local_ss->tick); - i64 publish_ns = sys_time_ns(); + i64 publish_ns = P_TimeNs(); if (last_publish_to_user_ns == 0) { last_publish_to_user_ns = publish_ns - G.average_local_to_user_snapshot_publish_dt_ns; } diff --git a/src/user/user_core.h b/src/user/user_core.h index 7a731ee9..d2a4aad3 100644 --- a/src/user/user_core.h +++ b/src/user/user_core.h @@ -1,7 +1,3 @@ -struct sprite_startup_receipt; -struct sound_startup_receipt; -struct sim_startup_receipt; - enum user_bind_kind { USER_BIND_KIND_NONE, @@ -53,11 +49,11 @@ enum user_bind_kind { struct user_startup_receipt { i32 _; }; struct user_startup_receipt user_startup(F_StartupReceipt *font_sr, - struct sprite_startup_receipt *sprite_sr, + S_StartupReceipt *sprite_sr, D_StartupReceipt *draw_sr, AC_StartupReceipt *asset_cache_sr, - struct sound_startup_receipt *sound_sr, + SND_StartupReceipt *sound_sr, M_StartupReceipt *mixer_sr, N_StartupReceipt *host_sr, - struct sim_startup_receipt *sim_sr, + SimStartupReceipt *sim_sr, String connect_address_str); diff --git a/src/watch/watch.h b/src/watch/watch.h index 885ffb44..c18151e7 100644 --- a/src/watch/watch.h +++ b/src/watch/watch.h @@ -2,7 +2,7 @@ #define WATCH_H #include "../base/base.h" -#include "../sys/sys.h" +#include "../platform/platform.h" #include "watch_core.h" diff --git a/src/watch/watch_core.c b/src/watch/watch_core.c index 3530bc8d..cea2447c 100644 --- a/src/watch/watch_core.c +++ b/src/watch/watch_core.c @@ -6,17 +6,17 @@ struct watch_event { }; GLOBAL struct { - struct sys_watch *watch; + P_Watch *watch; Atomic32 watch_shutdown; - struct snc_counter watch_jobs_counter; + P_Counter watch_jobs_counter; - struct snc_mutex watch_dispatcher_mutex; + P_Mutex watch_dispatcher_mutex; Arena *watch_events_arena; struct watch_event *first_watch_event; struct watch_event *last_watch_event; - struct snc_cv watch_dispatcher_cv; + P_Cv watch_dispatcher_cv; - struct snc_mutex watch_callbacks_mutex; + P_Mutex watch_callbacks_mutex; watch_callback *watch_callbacks[64]; u64 num_watch_callbacks; } G = ZI, DEBUG_ALIAS(G, G_watch); @@ -25,34 +25,34 @@ GLOBAL struct { * Startup * ========================== */ -INTERNAL SYS_JOB_DEF(watch_monitor_job, _); -INTERNAL SYS_JOB_DEF(watch_dispatcher_job, _); -INTERNAL SYS_EXIT_FUNC(watch_shutdown); +INTERNAL P_JobDef(watch_monitor_job, _); +INTERNAL P_JobDef(watch_dispatcher_job, _); +INTERNAL P_ExitFuncDef(watch_shutdown); void watch_startup(void) { - G.watch = sys_watch_alloc(LIT("./")); + G.watch = P_AllocWatch(LIT("./")); G.watch_events_arena = arena_alloc(GIBI(64)); - sys_run(1, watch_monitor_job, 0, SYS_POOL_FLOATING, SYS_PRIORITY_LOW, &G.watch_jobs_counter); - sys_run(1, watch_dispatcher_job, 0, SYS_POOL_BACKGROUND, SYS_PRIORITY_LOW, &G.watch_jobs_counter); - sys_on_exit(&watch_shutdown); + P_Run(1, watch_monitor_job, 0, P_Pool_Floating, P_Priority_Low, &G.watch_jobs_counter); + P_Run(1, watch_dispatcher_job, 0, P_Pool_Background, P_Priority_Low, &G.watch_jobs_counter); + P_OnExit(&watch_shutdown); } /* ========================== * * Watch * ========================== */ -INTERNAL SYS_EXIT_FUNC(watch_shutdown) +INTERNAL P_ExitFuncDef(watch_shutdown) { __prof; atomic32_fetch_set(&G.watch_shutdown, 1); { - struct snc_lock lock = snc_lock_e(&G.watch_dispatcher_mutex); + P_Lock lock = snc_lock_e(&G.watch_dispatcher_mutex); snc_cv_signal(&G.watch_dispatcher_cv, I32_MAX); - sys_watch_wake(G.watch); + P_WakeWatch(G.watch); snc_unlock(&lock); } snc_counter_wait(&G.watch_jobs_counter); @@ -60,18 +60,18 @@ INTERNAL SYS_EXIT_FUNC(watch_shutdown) void watch_register_callback(watch_callback *callback) { - struct snc_lock lock = snc_lock_e(&G.watch_callbacks_mutex); + P_Lock lock = snc_lock_e(&G.watch_callbacks_mutex); { if (G.num_watch_callbacks < countof(G.watch_callbacks)) { G.watch_callbacks[G.num_watch_callbacks++] = callback; } else { - sys_panic(LIT("Max resource watch callbacks reached")); + P_Panic(LIT("Max resource watch callbacks reached")); } } snc_unlock(&lock); } -INTERNAL SYS_JOB_DEF(watch_monitor_job, _) +INTERNAL P_JobDef(watch_monitor_job, _) { (UNUSED)_; TempArena scratch = scratch_begin_no_conflict(); @@ -83,11 +83,11 @@ INTERNAL SYS_JOB_DEF(watch_monitor_job, _) while (!atomic32_fetch(&G.watch_shutdown)) { TempArena temp = arena_temp_begin(scratch.arena); - struct sys_watch_info_list info_list = sys_watch_read_wait(temp.arena, G.watch); + P_WatchInfoList info_list = P_ReadWatchWait(temp.arena, G.watch); if (info_list.first && !atomic32_fetch(&G.watch_shutdown)) { - struct snc_lock lock = snc_lock_e(&G.watch_dispatcher_mutex); + P_Lock lock = snc_lock_e(&G.watch_dispatcher_mutex); { - for (struct sys_watch_info *info = info_list.first; info; info = info->next) { + for (P_WatchInfo *info = info_list.first; info; info = info->next) { String name_src = info->name; b32 ignore = 0; for (u32 i = 0; i < countof(ignored); ++i) { @@ -129,7 +129,7 @@ struct watch_callback_job_sig { watch_callback **callbacks; }; -INTERNAL SYS_JOB_DEF(watch_callback_job, job) +INTERNAL P_JobDef(watch_callback_job, job) { __prof; struct watch_callback_job_sig *sig = job.sig; @@ -138,7 +138,7 @@ INTERNAL SYS_JOB_DEF(watch_callback_job, job) callback(name); } -INTERNAL SYS_JOB_DEF(watch_dispatcher_job, _) +INTERNAL P_JobDef(watch_dispatcher_job, _) { (UNUSED)_; @@ -152,12 +152,12 @@ INTERNAL SYS_JOB_DEF(watch_dispatcher_job, _) /* Delay so that duplicate events pile up */ { __profn("Delay"); - sys_wait(0, 0, 0, NS_FROM_SECONDS(WATCH_DISPATCHER_DELAY_SECONDS)); + P_Wait(0, 0, 0, NS_FROM_SECONDS(WATCH_DISPATCHER_DELAY_SECONDS)); } /* Pull watch events from queue */ { - struct snc_lock lock = snc_lock_e(&G.watch_dispatcher_mutex); + P_Lock lock = snc_lock_e(&G.watch_dispatcher_mutex); for (struct watch_event *src_event = G.first_watch_event; src_event; src_event = src_event->next) { struct watch_event *e = arena_push(scratch.arena, struct watch_event); e->name = string_copy(scratch.arena, src_event->name); @@ -177,7 +177,7 @@ INTERNAL SYS_JOB_DEF(watch_dispatcher_job, _) /* Build callbacks array */ u64 num_callbacks = 0; watch_callback **callbacks = 0; - struct snc_lock callbacks_lock = snc_lock_s(&G.watch_callbacks_mutex); + P_Lock callbacks_lock = snc_lock_s(&G.watch_callbacks_mutex); { num_callbacks = G.num_watch_callbacks; callbacks = arena_push_array_no_zero(scratch.arena, watch_callback *, num_callbacks); @@ -204,8 +204,8 @@ INTERNAL SYS_JOB_DEF(watch_dispatcher_job, _) struct watch_callback_job_sig sig = ZI; sig.name = e->name; sig.callbacks = callbacks; - struct snc_counter counter = ZI; - sys_run(num_callbacks, watch_callback_job, &sig, SYS_POOL_BACKGROUND, SYS_PRIORITY_LOW, &counter); + P_Counter counter = ZI; + P_Run(num_callbacks, watch_callback_job, &sig, P_Pool_Background, P_Priority_Low, &counter); snc_counter_wait(&counter); } } @@ -215,7 +215,7 @@ INTERNAL SYS_JOB_DEF(watch_dispatcher_job, _) } /* Wait for event */ - struct snc_lock lock = snc_lock_s(&G.watch_dispatcher_mutex); + P_Lock lock = snc_lock_s(&G.watch_dispatcher_mutex); { shutdown = atomic32_fetch(&G.watch_shutdown); while (!shutdown && !G.first_watch_event) {