// // Profiling macros. // #ifndef PROF_ENABLE #define PROF_ENABLE 0 #endif #if PROF_ENABLE > 0 #ifndef PROF_RESET_MINMAX #define PROF_RESET_MINMAX true #endif // Maximum number of profiling to monitor. typedef enum ProfType { PROF_INPUT, PROF_UPDATE, PROF_RENDER, PROF_FLIP, PROF_FILL, PROF_NUM, } ProfType; char *prof_type_str[PROF_NUM] = { "INPUT ", "UPDATE ", "RENDER ", "FLIPBUF", "SCRFILL", }; u32 prof_frame_time = 0; u32 prof_frame_count = 0; u32 prof_frame_avg = -1; u32 prof_frame_time_max = 0; u32 prof_times[PROF_NUM] = {0}; u32 prof_count[PROF_NUM] = {0}; u32 prof_avg[PROF_NUM] = {0}; u32 prof_max[PROF_NUM] = {0}; u32 prof_min[PROF_NUM] = {0}; bool prof_reset_minmax = PROF_RESET_MINMAX; bool prof_show = true; #define PROF_INIT() do { \ for (size_t i = 0; i < PROF_NUM; i++) { \ prof_min[i] = -1; \ } \ } while(0); #define PROF(func, idx) do { \ u32 time_before = profile_measure(); \ (func); \ u32 time_after = profile_measure(); \ u32 time_current = time_after - time_before; \ prof_times[idx] += time_current; \ prof_count[idx]++; \ prof_max[idx] = MAX(time_current, prof_max[idx]);\ prof_min[idx] = MIN(time_current, prof_min[idx]);\ } while(0); #define FRAME_START() do { \ profile_start();\ } while(0) #define FRAME_END() do { \ prof_frame_count++;\ prof_frame_time_max = MAX(prof_frame_time_max, profile_measure());\ prof_frame_time += profile_stop();\ if (prof_show) { \ draw_filled_rect(0, 0, SCREEN_WIDTH - 1, 8 * (PROF_NUM + 1), 0); \ txt_drawf_small("FRAME TIME/FPS: %.9l/%.2l", 0, 0, COL_FG, \ prof_frame_avg, \ (u32)((u64)280896 * 60 / (prof_frame_avg + 1)));\ txt_drawf_small("MAX: %.9l/%l", 8 * 19, 0, COL_FG, \ prof_frame_time_max, 280896);\ for (size_t idx = 0; idx < PROF_NUM; idx++) { \ txt_drawf_small("%s %.9l (%.9l %.9l) %08x:%08x", 0, 8 * (idx + 1), COL_FG, \ prof_type_str[idx], \ prof_avg[idx], \ prof_min[idx], \ prof_max[idx], \ prof_avg[idx], \ prof_max[idx]);\ }; \ } \ if (prof_frame_count >= PROF_ENABLE) { \ for (size_t idx = 0; idx < PROF_NUM; idx++) { \ prof_avg[idx] = prof_times[idx] / prof_frame_count; \ if (prof_reset_minmax) { \ prof_min[idx] = -1; \ prof_max[idx] = 0; \ prof_frame_time_max = 0; \ } \ prof_times[idx] = 0; \ prof_count[idx] = 0; \ }; \ prof_frame_avg = prof_frame_time / prof_frame_count; \ prof_frame_count = 0; \ prof_frame_time = 0; \ } \ } while(0) #define PROF_SHOW() do { \ prof_show ^= 1; \ } while(0) #else // No profiling. #define PROF_INIT() #define PROF(F,VAR) do {F;} while(0) #define FRAME_START() #define FRAME_END() #define PROF_SHOW() #endif