mirror of
https://github.com/obsproject/obs-studio.git
synced 2024-09-19 20:32:15 +02:00
libobs: Fix potential crash on output stop
In certain circumstances where the output was stopping, and where data took a long enough time to send (such as when using an encoding preset that causes high CPU usage), the output would sometimes still send data even after it was stopped, typically causing the output to crash.
This commit is contained in:
parent
8e1549820b
commit
244280335b
@ -395,6 +395,7 @@ struct obs_output {
|
||||
int total_frames;
|
||||
|
||||
bool active;
|
||||
volatile bool stopped;
|
||||
video_t *video;
|
||||
audio_t *audio;
|
||||
obs_encoder_t *video_encoder;
|
||||
|
@ -159,6 +159,8 @@ bool obs_output_start(obs_output_t *output)
|
||||
if (!output)
|
||||
return false;
|
||||
|
||||
output->stopped = false;
|
||||
|
||||
success = output->info.start(output->context.data);
|
||||
|
||||
if (success && output->video) {
|
||||
@ -207,6 +209,8 @@ static void log_frame_info(struct obs_output *output)
|
||||
void obs_output_stop(obs_output_t *output)
|
||||
{
|
||||
if (output) {
|
||||
output->stopped = true;
|
||||
|
||||
os_event_signal(output->reconnect_stop_event);
|
||||
if (output->reconnect_thread_active)
|
||||
pthread_join(output->reconnect_thread, NULL);
|
||||
@ -617,7 +621,8 @@ static inline void send_interleaved(struct obs_output *output)
|
||||
output->total_frames++;
|
||||
|
||||
da_erase(output->interleaved_packets, 0);
|
||||
output->info.encoded_packet(output->context.data, &out);
|
||||
if (!output->stopped)
|
||||
output->info.encoded_packet(output->context.data, &out);
|
||||
obs_free_encoder_packet(&out);
|
||||
}
|
||||
|
||||
@ -787,7 +792,8 @@ static void interleave_packets(void *data, struct encoder_packet *packet)
|
||||
static void default_encoded_callback(void *param, struct encoder_packet *packet)
|
||||
{
|
||||
struct obs_output *output = param;
|
||||
output->info.encoded_packet(output->context.data, packet);
|
||||
if (!output->stopped)
|
||||
output->info.encoded_packet(output->context.data, packet);
|
||||
|
||||
if (packet->type == OBS_ENCODER_VIDEO)
|
||||
output->total_frames++;
|
||||
@ -796,10 +802,18 @@ static void default_encoded_callback(void *param, struct encoder_packet *packet)
|
||||
static void default_raw_video_callback(void *param, struct video_data *frame)
|
||||
{
|
||||
struct obs_output *output = param;
|
||||
output->info.raw_video(output->context.data, frame);
|
||||
if (!output->stopped)
|
||||
output->info.raw_video(output->context.data, frame);
|
||||
output->total_frames++;
|
||||
}
|
||||
|
||||
static void default_raw_audio_callback(void *param, struct audio_data *frames)
|
||||
{
|
||||
struct obs_output *output = param;
|
||||
if (!output->stopped)
|
||||
output->info.raw_audio(output->context.data, frames);
|
||||
}
|
||||
|
||||
static void hook_data_capture(struct obs_output *output, bool encoded,
|
||||
bool has_video, bool has_audio)
|
||||
{
|
||||
@ -831,8 +845,7 @@ static void hook_data_capture(struct obs_output *output, bool encoded,
|
||||
if (has_audio)
|
||||
audio_output_connect(output->audio,
|
||||
get_audio_conversion(output),
|
||||
output->info.raw_audio,
|
||||
output->context.data);
|
||||
default_raw_audio_callback, output);
|
||||
}
|
||||
}
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user