From a7888c4998d52a6c85a0c5bd80c340a1a6eee867 Mon Sep 17 00:00:00 2001 From: Max Kellermann Date: Tue, 21 Oct 2008 18:12:56 +0200 Subject: ffmpeg: don't pass pointer as hexadecimal string Casting a pointer to some sort of integer and formatting it into a string isn't valid. A pointer derived from this hex string won't work reliably. Since ffmpeg doesn't provide a nice API for passing our pointer, we have to think of a different hack: ffmpeg passes the exact URL pointer to mpdurl_open(), and we can make this string part of a struct. This reduces the problem to casting the string back to the struct. This is still a workaround, but this is "sort of portable", unless the ffmpeg people start messing with the URL pointer (which would be valid according to the API definition). --- src/inputPlugins/ffmpeg_plugin.c | 47 +++++++++++++++++++++++----------------- 1 file changed, 27 insertions(+), 20 deletions(-) (limited to 'src/inputPlugins') diff --git a/src/inputPlugins/ffmpeg_plugin.c b/src/inputPlugins/ffmpeg_plugin.c index 95e15957c..6455cd1ce 100644 --- a/src/inputPlugins/ffmpeg_plugin.c +++ b/src/inputPlugins/ffmpeg_plugin.c @@ -50,26 +50,34 @@ typedef struct { } BasePtrs; typedef struct { + /** hack - see url_to_base() */ + char url[8]; + struct decoder *decoder; InputStream *input; } FopsHelper; -static int mpdurl_open(URLContext *h, const char *filename, int flags) +/** + * Convert a faked mpd:// URL to a FopsHelper structure. This is a + * hack because ffmpeg does not provide a nice API for passing a + * user-defined pointer to mpdurl_open(). + */ +static FopsHelper *url_to_base(const char *url) { - uint32_t ptr; - FopsHelper *base; - if (strlen(filename) == (8+8)) { - errno = 0; - ptr = (uint32_t) strtoll(filename + 6, NULL, 16); - if (errno == 0 && ptr != 0) { - base = (FopsHelper *) ptr; - h->priv_data = base; - h->is_streamed = (base->input->seekable ? 0 : 1); - return 0; - } - } - FATAL("Invalid format %s:%d\n", filename, flags); - return -1; + union { + const char *in; + FopsHelper *out; + } u = { .in = url }; + return u.out; +} + +static int mpdurl_open(URLContext *h, const char *filename, + mpd_unused int flags) +{ + FopsHelper *base = url_to_base(filename); + h->priv_data = base; + h->is_streamed = (base->input->seekable ? 0 : 1); + return 0; } static int mpdurl_read(URLContext *h, unsigned char *buf, int size) @@ -137,8 +145,9 @@ static int ffmpeg_helper(InputStream *input, int (*callback)(BasePtrs *ptrs), AVCodec *aCodec; int ret, audioStream; unsigned i; - FopsHelper fopshelp; - char url[24]; + FopsHelper fopshelp = { + .url = "mpd://X", /* only the mpd:// prefix matters */ + }; fopshelp.input = input; if (ptrs && ptrs->decoder) { @@ -148,9 +157,7 @@ static int ffmpeg_helper(InputStream *input, int (*callback)(BasePtrs *ptrs), } //ffmpeg works with ours "fileops" helper - sprintf(url, "mpd://0x%8x", (unsigned int) &fopshelp); - - if (av_open_input_file(&pFormatCtx, url, NULL, 0, NULL)!=0) { + if (av_open_input_file(&pFormatCtx, fopshelp.url, NULL, 0, NULL)!=0) { ERROR("Open failed!\n"); return -1; } -- cgit v1.2.3