command: make loadlist command async and abortable

Don't allow it to freeze everything when loading a playlist from network
(although you definitely shouldn't do that, but whatever).

This also affects the really obscure --ordered-chapters-files option.
The --playlist option on the other hand has no choice but to freeze the
shit, because there's no concept of aborting the player during command
line parsing.
This commit is contained in:
wm4 2018-05-18 22:19:10 +02:00
parent 12d1404b04
commit 76dc5d9aa9
5 changed files with 15 additions and 7 deletions

View File

@ -275,13 +275,14 @@ struct playlist_entry *playlist_entry_from_index(struct playlist *pl, int index)
}
}
struct playlist *playlist_parse_file(const char *file, struct mpv_global *global)
struct playlist *playlist_parse_file(const char *file, struct mp_cancel *cancel,
struct mpv_global *global)
{
struct mp_log *log = mp_log_new(NULL, global->log, "!playlist_parser");
mp_verbose(log, "Parsing playlist file %s...\n", file);
struct demuxer_params p = {.force_format = "playlist"};
struct demuxer *d = demux_open_url(file, &p, NULL, global);
struct demuxer *d = demux_open_url(file, &p, cancel, global);
if (!d) {
talloc_free(log);
return NULL;

View File

@ -101,8 +101,10 @@ int playlist_entry_to_index(struct playlist *pl, struct playlist_entry *e);
int playlist_entry_count(struct playlist *pl);
struct playlist_entry *playlist_entry_from_index(struct playlist *pl, int index);
struct mp_cancel;
struct mpv_global;
struct playlist *playlist_parse_file(const char *file, struct mpv_global *global);
struct playlist *playlist_parse_file(const char *file, struct mp_cancel *cancel,
struct mpv_global *global);
void playlist_entry_unref(struct playlist_entry *e);

View File

@ -264,7 +264,8 @@ static void find_ordered_chapter_sources(struct tl_ctx *ctx)
MP_INFO(ctx, "Loading references from '%s'.\n",
opts->ordered_chapters_files);
struct playlist *pl =
playlist_parse_file(opts->ordered_chapters_files, ctx->global);
playlist_parse_file(opts->ordered_chapters_files,
ctx->tl->cancel, ctx->global);
talloc_steal(tmp, pl);
for (struct playlist_entry *e = pl ? pl->first : NULL; e; e = e->next)
MP_TARRAY_APPEND(tmp, filenames, num_filenames, e->filename);

View File

@ -199,7 +199,7 @@ int m_config_parse_mp_command_line(m_config_t *config, struct playlist *files,
if (bstrcmp0(p.arg, "playlist") == 0) {
// append the playlist to the local args
char *param0 = bstrdup0(NULL, p.param);
struct playlist *pl = playlist_parse_file(param0, global);
struct playlist *pl = playlist_parse_file(param0, NULL, global);
talloc_free(param0);
if (!pl) {
MP_FATAL(config, "Error reading playlist '%.*s'\n",

View File

@ -5387,7 +5387,8 @@ static void cmd_loadlist(void *p)
char *filename = cmd->args[0].v.s;
bool append = cmd->args[1].v.i;
struct playlist *pl = playlist_parse_file(filename, mpctx->global);
struct playlist *pl = playlist_parse_file(filename, cmd->abort->cancel,
mpctx->global);
if (pl) {
prepare_playlist(mpctx, pl);
struct playlist_entry *new = pl->current;
@ -6196,7 +6197,10 @@ const struct mp_cmd_def mp_cmds[] = {
},
{ "loadlist", cmd_loadlist, { OPT_STRING("url", v.s, 0),
OPT_CHOICE("flags", v.i, MP_CMD_OPT_ARG,
({"replace", 0}, {"append", 1})), }},
({"replace", 0}, {"append", 1})), },
.spawn_thread = true,
.can_abort = true,
},
{ "playlist-clear", cmd_playlist_clear },
{ "playlist-remove", cmd_playlist_remove,
{OPT_CHOICE_OR_INT("index", v.i, MP_CMD_OPT_ARG, 0, INT_MAX,