X-Git-Url: https://git.sesse.net/?a=blobdiff_plain;f=x264_speed_control.cpp;h=47086829dbf0a239a85a96bf4adeede319fab752;hb=892760d7067fd93ae7a86340ee131e201932ff0c;hp=3ed3ece8e5b95ed0a69d8788511d489eb39217eb;hpb=16c0e5da7fa7b4eeea79470c24697a1ba193f071;p=nageru diff --git a/x264_speed_control.cpp b/x264_speed_control.cpp index 3ed3ece..4708682 100644 --- a/x264_speed_control.cpp +++ b/x264_speed_control.cpp @@ -1,18 +1,26 @@ #include "x264_speed_control.h" -#include "flags.h" - -#include - +#include +#include +#include +#include #include +#include +#include +#include +#include + +#include "flags.h" using namespace std; +using namespace std::chrono; X264SpeedControl::X264SpeedControl(x264_t *x264, float f_speed, int i_buffer_size, float f_buffer_init) - : x264(x264), f_speed(f_speed) + : dyn(load_x264_for_bit_depth(global_flags.x264_bit_depth)), + x264(x264), f_speed(f_speed) { x264_param_t param; - x264_encoder_parameters(x264, ¶m); + dyn.x264_encoder_parameters(x264, ¶m); float fps = (float)param.i_fps_num / param.i_fps_den; uspf = 1e6 / fps; @@ -20,12 +28,14 @@ X264SpeedControl::X264SpeedControl(x264_t *x264, float f_speed, int i_buffer_siz buffer_fill = buffer_size * f_buffer_init; buffer_fill = max(buffer_fill, uspf); buffer_fill = min(buffer_fill, buffer_size); - timestamp = mdate(); + timestamp = steady_clock::now(); preset = -1; cplx_num = 3e3; //FIXME estimate initial complexity cplx_den = .1; stat.min_buffer = buffer_size; stat.max_buffer = 0; + stat.avg_preset = 0.0; + stat.den = 0; } X264SpeedControl::~X264SpeedControl() @@ -35,6 +45,9 @@ X264SpeedControl::~X264SpeedControl() (float)stat.min_buffer / buffer_size, (float)stat.max_buffer / buffer_size ); // x264_log( x264, X264_LOG_INFO, "speedcontrol: avg cplx=%.5f\n", cplx_num / cplx_den ); + if (dyn.handle) { + dlclose(dyn.handle); + } } typedef struct @@ -162,40 +175,45 @@ void X264SpeedControl::before_frame(float new_buffer_fill, int new_buffer_size, } buffer_fill = buffer_size * new_buffer_fill; - int64_t t, delta_t; + steady_clock::time_point t; // update buffer state after encoding and outputting the previous frame(s) if (first) { - t = timestamp = mdate(); + t = timestamp = steady_clock::now(); first = false; } else { - t = mdate(); + t = steady_clock::now(); } - delta_t = t - timestamp; + auto delta_t = t - timestamp; timestamp = t; // update the time predictor - int cpu_time = cpu_time_last_frame; - cplx_num *= cplx_decay; - cplx_den *= cplx_decay; - cplx_num += cpu_time / presets[preset].time; - ++cplx_den; - - stat.avg_preset += preset; - ++stat.den; + if (preset >= 0) { + int cpu_time = duration_cast(cpu_time_last_frame).count(); + cplx_num *= cplx_decay; + cplx_den *= cplx_decay; + cplx_num += cpu_time / presets[preset].time; + ++cplx_den; + + stat.avg_preset += preset; + ++stat.den; + } stat.min_buffer = min(buffer_fill, stat.min_buffer); stat.max_buffer = max(buffer_fill, stat.max_buffer); if (buffer_fill >= buffer_size) { // oops, cpu was idle // not really an error, but we'll warn for debugging purposes - static int64_t idle_t = 0, print_interval = 0; + static int64_t idle_t = 0; + static steady_clock::time_point print_interval; + static bool first = false; idle_t += buffer_fill - buffer_size; - if (t - print_interval > 1e6) { + if (first || duration(t - print_interval).count() > 0.1) { //fprintf(stderr, "speedcontrol idle (%.6f sec)\n", idle_t/1e6); print_interval = t; idle_t = 0; + first = false; } buffer_fill = buffer_size; } else if (buffer_fill <= 0) { // oops, we're late @@ -243,8 +261,8 @@ void X264SpeedControl::before_frame(float new_buffer_fill, int new_buffer_size, if (global_flags.x264_speedcontrol_verbose) { static float cpu, wall, tgt, den; const float decay = 1-1/100.; - cpu = cpu*decay + cpu_time_last_frame; - wall = wall*decay + delta_t; + cpu = cpu*decay + duration_cast(cpu_time_last_frame).count(); + wall = wall*decay + duration_cast(delta_t).count(); tgt = tgt*decay + target; den = den*decay + 1; fprintf(stderr, "speed: %.2f+%.2f %d[%.5f] (t/c/w: %6.0f/%6.0f/%6.0f = %.4f) fps=%.2f\r", @@ -257,7 +275,7 @@ void X264SpeedControl::before_frame(float new_buffer_fill, int new_buffer_size, void X264SpeedControl::after_frame() { - cpu_time_last_frame = mdate() - timestamp; + cpu_time_last_frame = steady_clock::now() - timestamp; } void X264SpeedControl::set_buffer_size(int new_buffer_size) @@ -289,7 +307,7 @@ void X264SpeedControl::apply_preset(int new_preset) const sc_preset_t *s = &presets[new_preset]; x264_param_t p; - x264_encoder_parameters(x264, &p); + dyn.x264_encoder_parameters(x264, &p); p.i_frame_reference = s->refs; p.i_bframe_adaptive = s->badapt; @@ -301,13 +319,9 @@ void X264SpeedControl::apply_preset(int new_preset) p.analyse.b_mixed_references = s->mix; p.analyse.i_direct_mv_pred = s->direct; p.analyse.i_me_range = s->merange; - x264_encoder_reconfig(x264, &p); + if (override_func) { + override_func(&p); + } + dyn.x264_encoder_reconfig(x264, &p); preset = new_preset; } - -int64_t X264SpeedControl::mdate() -{ - timespec now; - clock_gettime(CLOCK_MONOTONIC, &now); - return now.tv_sec * 1000000 + now.tv_nsec / 1000; -}