From 992792fb1f35546b9d66c3f69aa3d0f5adb94ef6 Mon Sep 17 00:00:00 2001 From: dec05eba Date: Sat, 7 Sep 2024 14:09:04 +0200 Subject: Move amix to separate thread --- src/main.cpp | 57 +++++++++++++++++++++++++++++++-------------------------- 1 file changed, 31 insertions(+), 26 deletions(-) diff --git a/src/main.cpp b/src/main.cpp index db44530..c6e9909 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -3266,12 +3266,39 @@ int main(int argc, char **argv) { } } + std::thread amix_thread; + if(uses_amix) { + amix_thread = std::thread([&]() { + AVFrame *aframe = av_frame_alloc(); + while(running) { + std::lock_guard lock(audio_filter_mutex); + for(AudioTrack &audio_track : audio_tracks) { + if(!audio_track.sink) + continue; + + int err = 0; + while ((err = av_buffersink_get_frame(audio_track.sink, aframe)) >= 0) { + aframe->pts = audio_track.pts; + err = avcodec_send_frame(audio_track.codec_context, aframe); + if(err >= 0){ + // TODO: Move to separate thread because this could write to network (for example when livestreaming) + receive_frames(audio_track.codec_context, audio_track.stream_index, audio_track.stream, aframe->pts, av_format_context, record_start_time, frame_data_queue, replay_buffer_size_secs, frames_erased, write_output_mutex, paused_time_offset); + } else { + fprintf(stderr, "Failed to encode audio!\n"); + } + av_frame_unref(aframe); + audio_track.pts += audio_track.codec_context->frame_size; + } + } + } + av_frame_free(&aframe); + }); + } + // Set update_fps to 24 to test if duplicate/delayed frames cause video/audio desync or too fast/slow video. const double update_fps = fps + 190; bool should_stop_error = false; - AVFrame *aframe = av_frame_alloc(); - int64_t video_pts_counter = 0; int64_t video_prev_pts = 0; @@ -3287,29 +3314,6 @@ int main(int argc, char **argv) { break; } - // TODO: Move to another thread, since this shouldn't be locked to video encoding fps - { - std::lock_guard lock(audio_filter_mutex); - for(AudioTrack &audio_track : audio_tracks) { - if(!audio_track.sink) - continue; - - int err = 0; - while ((err = av_buffersink_get_frame(audio_track.sink, aframe)) >= 0) { - aframe->pts = audio_track.pts; - err = avcodec_send_frame(audio_track.codec_context, aframe); - if(err >= 0){ - // TODO: Move to separate thread because this could write to network (for example when livestreaming) - receive_frames(audio_track.codec_context, audio_track.stream_index, audio_track.stream, aframe->pts, av_format_context, record_start_time, frame_data_queue, replay_buffer_size_secs, frames_erased, write_output_mutex, paused_time_offset); - } else { - fprintf(stderr, "Failed to encode audio!\n"); - } - av_frame_unref(aframe); - audio_track.pts += audio_track.codec_context->frame_size; - } - } - } - const bool damaged = !capture->is_damaged || capture->is_damaged(capture); if(damaged) { ++damage_fps_counter; @@ -3431,7 +3435,8 @@ int main(int argc, char **argv) { } } - av_frame_free(&aframe); + if(amix_thread.joinable()) + amix_thread.join(); if (replay_buffer_size_secs == -1 && av_write_trailer(av_format_context) != 0) { fprintf(stderr, "Failed to write trailer\n"); -- cgit v1.2.3