Handle SDL_PushEvent() errors

Pushing an event to the main thread may fail. If this happens, log an
error, and try to recover when possible.
This commit is contained in:
Romain Vimont 2021-10-30 20:21:00 +02:00
parent 4c4381de4c
commit dae091e3ab
3 changed files with 30 additions and 4 deletions

View file

@ -62,7 +62,10 @@ BOOL WINAPI windows_ctrl_handler(DWORD ctrl_type) {
if (ctrl_type == CTRL_C_EVENT) {
SDL_Event event;
event.type = SDL_QUIT;
SDL_PushEvent(&event);
int ret = SDL_PushEvent(&event);
if (ret < 0) {
LOGW("Could not post SDL_QUIT event: %s", SDL_GetError());
}
return TRUE;
}
return FALSE;
@ -250,7 +253,11 @@ stream_on_eos(struct stream *stream, void *userdata) {
SDL_Event stop_event;
stop_event.type = EVENT_STREAM_STOPPED;
SDL_PushEvent(&stop_event);
int ret = SDL_PushEvent(&stop_event);
if (ret < 0) {
LOGE("Could not post stream stopped event: %s", SDL_GetError());
// XXX What could we do?
}
}
bool

View file

@ -282,17 +282,33 @@ sc_video_buffer_on_new_frame(struct sc_video_buffer *vb, bool previous_skipped,
(void) vb;
struct screen *screen = userdata;
// event_failed implies previous_skipped (the previous frame may not have
// been consumed if the event was not sent)
assert(!screen->event_failed || previous_skipped);
bool need_new_event;
if (previous_skipped) {
fps_counter_add_skipped_frame(&screen->fps_counter);
// The EVENT_NEW_FRAME triggered for the previous frame will consume
// this new frame instead
// this new frame instead, unless the previous event failed
need_new_event = screen->event_failed;
} else {
need_new_event = true;
}
if (need_new_event) {
static SDL_Event new_frame_event = {
.type = EVENT_NEW_FRAME,
};
// Post the event on the UI thread
SDL_PushEvent(&new_frame_event);
int ret = SDL_PushEvent(&new_frame_event);
if (ret < 0) {
LOGW("Could not post new frame event: %s", SDL_GetError());
screen->event_failed = true;
} else {
screen->event_failed = false;
}
}
}
@ -302,6 +318,7 @@ screen_init(struct screen *screen, const struct screen_params *params) {
screen->has_frame = false;
screen->fullscreen = false;
screen->maximized = false;
screen->event_failed = false;
static const struct sc_video_buffer_callbacks cbs = {
.on_new_frame = sc_video_buffer_on_new_frame,

View file

@ -44,6 +44,8 @@ struct screen {
bool maximized;
bool mipmaps;
bool event_failed; // in case SDL_PushEvent() returned an error
AVFrame *frame;
};