diff options
author | Mitya Selivanov <automainint@guattari.tech> | 2025-04-07 02:37:35 +0200 |
---|---|---|
committer | Mitya Selivanov <automainint@guattari.tech> | 2025-04-07 02:37:35 +0200 |
commit | 0150f3e65a00894e5ed2d4fe304311e47c835424 (patch) | |
tree | 6b3477f905fcdbcae15ef18802e9c3ed5554e407 | |
parent | 1b72dceae8427a7e43bef44c7dbb47f53c0cb865 (diff) | |
download | reduced_system_layer-0150f3e65a00894e5ed2d4fe304311e47c835424.zip |
Simple profiling
-rwxr-xr-x | reduced_system_layer.c | 170 |
1 files changed, 166 insertions, 4 deletions
diff --git a/reduced_system_layer.c b/reduced_system_layer.c index 6473039..acd8cc6 100755 --- a/reduced_system_layer.c +++ b/reduced_system_layer.c @@ -53,7 +53,6 @@ #/ + [x] Requests cache #/ + [x] Global anti-aliasing #/ + [x] Fill triangles -#/ - Profiling #/ - Examples #/ - Conway's Game of Life #/ - Julia Set @@ -139,6 +138,7 @@ #/ - Testing #/ - Stackless coroutines #/ - Allocator +#/ - Profiling #/ - Graphics #/ - Font #/ - Adaptive resolution @@ -716,6 +716,11 @@ i64 network_send(u16 slot, Network_Address address, i64 size, u8 *data, u16 *loc void dynamic_library_open (u16 slot, c8 *name); void *dynamic_library_get_proc_address(u16 slot, c8 *proc); +// Profiling +void PROFILER_init(u32 slot, c8 *name); +void PROFILER_begin(u32 slot); +void PROFILER_end(u32 slot); + // NOTE: This will shutdown main window, networking, audio, // and close all opened dynamic libraries. // If g_platform.graceful_shutdown is 0, this does nothing. @@ -748,6 +753,13 @@ extern Platform g_platform; #ifndef REDUCED_SYSTEM_LAYER_IMPL_GUARD_ #define REDUCED_SYSTEM_LAYER_IMPL_GUARD_ +enum { + PROFILE_DOWNSCALE, + PROFILE_RESIZE, + PROFILE_WAITING, + PROFILE_FRAME, +}; + // ---------------------------------------------------------------- static void mem_set_(void *dst, u8 x, i64 size) { @@ -1253,8 +1265,11 @@ static i64 _frame_duration [NUM_FRAMES_AVERAGED] = {0}; void run_main_window_event_loop(void) { init_main_window(); #if !defined(__wasm__) - while (!g_platform.done) + while (!g_platform.done) { + PROFILER_begin(PROFILE_FRAME); update_and_render_frame(); + PROFILER_end(PROFILE_FRAME); + } shutdown_all_systems(); #endif } @@ -1461,6 +1476,117 @@ void resize_dynamic_array_capacity(i64 *num, i64 *capacity, void **data, i64 ele // ================================================================ // +// Profiling +// +// ================================================================ + +typedef struct { + c8 *name; + i64 count; + i64 time_sec; + i64 time_nsec; + i64 begin_sec; + i64 begin_nsec; +} Profiler_Slot_; + +i64 _profiler_num_slots = 0; +Profiler_Slot_ *_profiler_slots = NULL; + +void PROFILER_init(u32 slot, c8 *name) { + if ((i64) (u64) slot >= _profiler_num_slots) + resize_dynamic_array_exact(&_profiler_num_slots, (void **) &_profiler_slots, sizeof *_profiler_slots, (i64) (u64) slot + 1); + + if ((i64) (u64) slot >= _profiler_num_slots) { + LOG_ERROR("Invalid slot: %d", (i32) slot); + return; + } + + mem_set_(_profiler_slots + slot, 0, sizeof *_profiler_slots); + _profiler_slots[slot].name = name; +} + +void PROFILER_begin(u32 slot) { + if ((i64) (u64) slot >= _profiler_num_slots) { + LOG_ERROR("Invalid slot: %d", (i32) slot); + return; + } + + if (_profiler_slots[slot].count < 0) { + LOG_ERROR("Sanity"); + return; + } + + ++_profiler_slots[slot].count; + if (_profiler_slots[slot].count != 1) + return; + + current_utc_time_in_sec_and_nsec( + &_profiler_slots[slot].begin_sec, + &_profiler_slots[slot].begin_nsec + ); +} + +static void normalize_time_(i64 *sec, i64 *nsec) { + if (sec == NULL || nsec == NULL) { + LOG_ERROR("Sanity"); + return; + } + + if (*nsec < 0) { + *sec -= 1; + *nsec += 1000000000; + } + + if (*nsec >= 1000000000) { + *sec += *nsec / 1000000000; + *nsec = *nsec % 1000000000; + } +} + +void PROFILER_end(u32 slot) { + if ((i64) (u64) slot >= _profiler_num_slots) { + LOG_ERROR("Invalid slot: %d", (i32) slot); + return; + } + + if (_profiler_slots[slot].count <= 0) { + LOG_ERROR("Sanity"); + return; + } + + --_profiler_slots[slot].count; + if (_profiler_slots[slot].count != 0) + return; + + i64 sec, nsec; + current_utc_time_in_sec_and_nsec(&sec, &nsec); + + sec -= _profiler_slots[slot].begin_sec; + nsec -= _profiler_slots[slot].begin_nsec; + + normalize_time_(&sec, &nsec); + + for (i64 i = 0; i < _profiler_num_slots; ++i) { + if (_profiler_slots[i].count == 0) + continue; + + _profiler_slots[i].time_sec -= sec; + _profiler_slots[i].time_nsec -= nsec; + + normalize_time_(&_profiler_slots[i].time_sec, &_profiler_slots[i].time_nsec); + } + + _profiler_slots[slot].begin_sec = 0; + _profiler_slots[slot].begin_nsec = 0; + + _profiler_slots[slot].time_sec += sec; + _profiler_slots[slot].time_nsec += nsec; + + normalize_time_(&_profiler_slots[slot].time_sec, &_profiler_slots[slot].time_nsec); +} + +// ================================================================ +// // Platform // // ================================================================ @@ -1643,6 +1769,8 @@ static void convert_pixels_for_window_(void) { return; } + PROFILER_begin(PROFILE_DOWNSCALE); + f32 k = 1.f / (aa_scale * aa_scale); vec4_f32 *s = g_platform.pixels; u32 *d = _internal_pixels; @@ -1671,6 +1799,8 @@ static void convert_pixels_for_window_(void) { for (; d < d_end; ++d, ++im) *d = rgb_u32_from_f32_((vec3_f32) { .x = im->x * k, .y = im->y * k, .z = im->z * k, }) | 0xff000000; } + + PROFILER_end(PROFILE_DOWNSCALE); } // Resize internal pixel buffer in-place. @@ -1692,6 +1822,8 @@ static void convert_pixels_for_window_(void) { return; } + PROFILER_begin(PROFILE_RESIZE); + f64 di = ((f64) src_width) / dst_width; f64 dj = ((f64) src_height) / dst_height; @@ -1720,6 +1852,8 @@ static void convert_pixels_for_window_(void) { *d = s[(i64) ii]; } } + + PROFILER_end(PROFILE_RESIZE); } } @@ -1781,9 +1915,14 @@ void dynamic_library_open(u16 slot, c8 *name) { return; } - if (slot >= _dynamic_libraries.num_slots) + if ((i64) (u64) slot >= _dynamic_libraries.num_slots) resize_dynamic_array_exact(&_dynamic_libraries.num_slots, (void **) &_dynamic_libraries.slots, sizeof *_dynamic_libraries.slots, (i64) slot + 1); + if ((i64) (u64) slot >= _dynamic_libraries.num_slots) { + LOG_ERROR("Invalid slot: %d", (i32) slot); + return; + } + if (_dynamic_libraries.slots[slot].handle != NULL) { dlclose(_dynamic_libraries.slots[slot].handle); _dynamic_libraries.slots[slot].handle = NULL; @@ -1801,7 +1940,7 @@ void dynamic_library_open(u16 slot, c8 *name) { } void *dynamic_library_get_proc_address(u16 slot, c8 *proc) { - if (slot >= _dynamic_libraries.num_slots) { + if ((i64) (u64) slot >= _dynamic_libraries.num_slots) { LOG_ERROR("Invalid slot: %d", (i32) slot); return NULL; } @@ -1948,6 +2087,11 @@ static void network_cleanup_(void) { b8 network_open(u16 slot, Network_Address address, u16 *local_port) { network_init_(slot); + if ((i64) (u64) slot >= _num_sockets) { + LOG_ERROR("Invalid slot: %d", (i32) slot); + return 0; + } + b8 change_address = !_sockets[slot].ready || _sockets[slot].address.protocol != address.protocol @@ -2940,6 +3084,11 @@ void put_image_to_main_window_(void) { } void init_main_window(void) { + PROFILER_init(PROFILE_DOWNSCALE, "Downscale anti-aliasing"); + PROFILER_init(PROFILE_RESIZE, "Resize in-place"); + PROFILER_init(PROFILE_WAITING, "Waiting for events"); + PROFILER_init(PROFILE_FRAME, "Update frame"); + for (i64 i = 0; i < NUM_FRAMES_AVERAGED; ++i) _frame_duration[i] = (MIN_FRAME_DURATION + MAX_FRAME_DURATION) / 2; @@ -3165,6 +3314,16 @@ void init_main_window(void) { } void shutdown_all_systems(void) { + if (_profiler_num_slots > 0) { + printf("\nPROFILER REPORT\n\n"); + for (i64 i = 0; i < _profiler_num_slots; ++i) { + if (_profiler_slots[i].name == NULL) + continue; + printf("%-31s %lld.%09lld\n", _profiler_slots[i].name, _profiler_slots[i].time_sec, _profiler_slots[i].time_nsec); + } + printf("\n"); + } + g_platform.done = 1; if (!g_platform.graceful_shutdown) @@ -3725,6 +3884,8 @@ i32 handle_main_window_events(void) { } i32 wait_main_window_events(void) { + PROFILER_begin(PROFILE_WAITING); + i32 num_events = 0; for (;;) { @@ -3734,6 +3895,7 @@ i32 wait_main_window_events(void) { usleep(0); } + PROFILER_end(PROFILE_WAITING); return num_events; } |