screencast: only end the fps measurement when it was started before

Sometimes it can happen that the first frame of the active stream
triggers the renegotiation and destroy the frame without copy and with
that starting the fps_limit counter. This triggers an assert in
fps_limit_measure_end. To avoid it, we only engage the fps_limiter after
a frame was copied successfully.
This commit is contained in:
columbarius 2021-07-06 15:05:12 +02:00
parent 27d1e42ec0
commit 1534a6a17e
2 changed files with 11 additions and 4 deletions

View File

@ -108,6 +108,7 @@ struct xdpw_screencast_instance {
bool with_cursor;
int err;
bool quit;
bool copied;
// fps limit
struct fps_limit_state fps_limit;

View File

@ -34,10 +34,15 @@ void xdpw_wlr_frame_free(struct xdpw_screencast_instance *cast) {
}
if (cast->pwr_stream_state) {
uint64_t delay_ns = fps_limit_measure_end(&cast->fps_limit, cast->framerate);
if (delay_ns > 0) {
xdpw_add_timer(cast->ctx->state, delay_ns,
(xdpw_event_loop_timer_func_t) xdpw_wlr_register_cb, cast);
if (cast->copied) {
uint64_t delay_ns = fps_limit_measure_end(&cast->fps_limit, cast->framerate);
cast->copied = false;
if (delay_ns > 0) {
xdpw_add_timer(cast->ctx->state, delay_ns,
(xdpw_event_loop_timer_func_t) xdpw_wlr_register_cb, cast);
} else {
xdpw_wlr_register_cb(cast);
}
} else {
xdpw_wlr_register_cb(cast);
}
@ -134,6 +139,7 @@ static void wlr_frame_ready(void *data, struct zwlr_screencopy_frame_v1 *frame,
cast->current_frame.tv_sec = ((((uint64_t)tv_sec_hi) << 32) | tv_sec_lo);
cast->current_frame.tv_nsec = tv_nsec;
cast->copied = true;
xdpw_pwr_enqueue_buffer(cast);