PR #25505 opened by Marti2203 URL: https://code.ffmpeg.org/FFmpeg/FFmpeg/pulls/25505 Patch URL: https://code.ffmpeg.org/FFmpeg/FFmpeg/pulls/25505.patch
`http_write_reply()` formats the reply into `char message[BUFFER_SIZE]` (8192 bytes) with `snprintf()` and passes the return value to `ffurl_write()`. When the reply does not fit, that is the length it would have had, so `ffurl_write()` sends bytes from past the end of the stack buffer to the client. The reply includes the user's `-headers` (and `-content_type`), so in listen mode a long `-headers` value is enough: ``` ffmpeg -listen 1 -headers "X-Pad: $(head -c 39000 /dev/zero | tr '\0' b)"$'\r\n' -i http://127.0.0.1:18080/x -f null - ``` A client connecting to it receives a 39100-byte reply, of which only the first 8191 bytes come from `message`; ASan reports: ``` ERROR: AddressSanitizer: stack-buffer-overflow READ of size 39100 thread T0 #0 __interceptor_send #1 tcp_write libavformat/tcp.c:295:11 #2 retry_transfer_wrapper libavformat/avio.c:592:22 #3 ffurl_write2 libavformat/avio.c:649:12 #4 ffurl_write libavformat/url.h:207:12 #5 http_write_reply libavformat/http.c:738:16 #6 handle_http_errors libavformat/http.c:746:5 ``` The patch fails with `AVERROR(EINVAL)` and an error message when the reply does not fit, rather than sending it. With it, the example above sends no reply and the open fails with an error; with short headers the reply is the same 108 bytes as before. This issue was found by an LLM-Enhanced Static Analysis Engine and verified manually. 🤖 Generated with [Claude Code](https://claude.com/claude-code) From 6aa41d0a850b0c79dfd37af9a8c78fdda530708d Mon Sep 17 00:00:00 2001 From: Martin Mirchev <[email protected]> Date: Tue, 27 Oct 2026 10:00:15 +0800 Subject: [PATCH] avformat/http: do not send more than the reply buffer holds http_write_reply() passed the return value of snprintf() to ffurl_write(). When the reply did not fit into message[BUFFER_SIZE], for example with a long -headers value in listen mode, that is the length the reply would have had, so bytes from past the end of the stack buffer were sent to the client. Fail instead. Signed-off-by: Martin Mirchev <[email protected]> --- libavformat/http.c | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/libavformat/http.c b/libavformat/http.c index 2f4f522363a..86fcc7b8879 100644 --- a/libavformat/http.c +++ b/libavformat/http.c @@ -734,6 +734,10 @@ static int http_write_reply(URLContext* h, int status_code) content_type, s->headers ? s->headers : ""); } + if (message_len < 0 || message_len >= sizeof(message)) { + av_log(h, AV_LOG_ERROR, "HTTP reply header too long\n"); + return AVERROR(EINVAL); + } av_log(h, AV_LOG_TRACE, "HTTP reply header: \n%s----\n", message); if ((ret = ffurl_write(s->hd, message, message_len)) < 0) return ret; -- 2.54.0 _______________________________________________ ffmpeg-devel mailing list -- [email protected] To unsubscribe send an email to [email protected]
