From 1d352f85279f802ad711971fc8a57722785c2b29 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Kacper=20Michaj=C5=82ow?= Date: Tue, 28 Jan 2025 06:41:44 +0100 Subject: [PATCH] stream_file: allow to open only our fd in case of fuzzing This ensures that we don't open some other fd, for example when loading playlist. Also filters out loading any local files. This also allows to remove custom filtering from fuzzer itself. --- fuzzers/fuzzer_load.c | 7 ++++++- fuzzers/fuzzer_loadfile_direct.c | 20 -------------------- player/loadfile.c | 12 ------------ stream/stream_file.c | 11 +++++++---- 4 files changed, 13 insertions(+), 37 deletions(-) diff --git a/fuzzers/fuzzer_load.c b/fuzzers/fuzzer_load.c index 7621c03211..d522c99a61 100644 --- a/fuzzers/fuzzer_load.c +++ b/fuzzers/fuzzer_load.c @@ -45,6 +45,9 @@ int LLVMFuzzerTestOneInput(const uint8_t *data, size_t size) int fd = memfd_create("fuzz_mpv_load", MFD_CLOEXEC | MFD_ALLOW_SEALING); if (fd == -1) exit(1); + if (dup3(fd, 42, O_CLOEXEC) != 42 || close(fd)) + exit(1); + fd = 42; ssize_t written = 0; while (written < size) { ssize_t result = write(fd, data + written, size - written); @@ -85,7 +88,9 @@ int LLVMFuzzerTestOneInput(const uint8_t *data, size_t size) #endif mpv_terminate_destroy(ctx); - close(fd); + + if (close(fd)) + exit(1); return 0; } diff --git a/fuzzers/fuzzer_loadfile_direct.c b/fuzzers/fuzzer_loadfile_direct.c index 5afcbc314b..f6dd35c341 100644 --- a/fuzzers/fuzzer_loadfile_direct.c +++ b/fuzzers/fuzzer_loadfile_direct.c @@ -38,26 +38,6 @@ int LLVMFuzzerTestOneInput(const uint8_t *data, size_t size) return 0; #endif -#if !defined(MPV_PROTO) || defined(MPV_PROTO_FILE) - const uint8_t *data_check = data; - size_t size_check = size; - size_t prefix_size = sizeof("file://") - 1; - if (str_startswith(data, size - 1, "file://", prefix_size)) { - data_check += prefix_size; - size_check -= prefix_size; - } - // Exclude some common paths that are not useful for testing. - // Exclude - - if (size_check == 2 && !strncmp(data_check, "-", 1)) - return 0; - // Exclude relative paths - if (str_startswith(data_check, size_check - 1, ".", 1)) - return 0; - // Exclude absolute paths - if (str_startswith(data_check, size_check - 1, "/", 1)) - return 0; -#endif - mpv_handle *ctx = mpv_create(); if (!ctx) exit(1); diff --git a/player/loadfile.c b/player/loadfile.c index 253fdf889f..bf707ae56a 100644 --- a/player/loadfile.c +++ b/player/loadfile.c @@ -1182,18 +1182,6 @@ static void start_open(struct MPContext *mpctx, char *url, int url_flags, mpctx->open_for_prefetch = for_prefetch && mpctx->opts->demuxer_thread; mpctx->demuxer_changed = false; -#ifdef FUZZING_BUILD_MODE_UNSAFE_FOR_PRODUCTION - // Don't allow to open local paths or stdin during fuzzing - bstr open_url = bstr0(mpctx->open_url); - if (bstr_startswith0(open_url, "/") || - bstr_startswith0(open_url, ".") || - bstr_equals0(open_url, "-")) - { - cancel_open(mpctx); - return; - } -#endif - if (mp_thread_create(&mpctx->open_thread, open_demux_thread, mpctx)) { cancel_open(mpctx); return; diff --git a/stream/stream_file.c b/stream/stream_file.c index a753384424..d06da98901 100644 --- a/stream/stream_file.c +++ b/stream/stream_file.c @@ -309,10 +309,6 @@ static int open_f(stream_t *stream, const struct stream_open_args *args) MP_ERR(stream, "Invalid FD: %d\n", p->fd); return STREAM_ERROR; } -#endif -#ifdef FUZZING_BUILD_MODE_UNSAFE_FOR_PRODUCTION - if (p->fd == STDIN_FILENO || p->fd == STDOUT_FILENO || p->fd == STDERR_FILENO) - return STREAM_ERROR; #endif if (is_fdclose) p->close = true; @@ -344,6 +340,13 @@ static int open_f(stream_t *stream, const struct stream_open_args *args) p->close = true; } +#ifdef FUZZING_BUILD_MODE_UNSAFE_FOR_PRODUCTION + if (p->fd != 42) { + s_close(stream); + return STREAM_ERROR; + } +#endif + struct stat st; bool is_sock_or_fifo = false; if (fstat(p->fd, &st) == 0) {