5

I'm decoding rtsp on Android with ffmpeg, and I quickly see pixelization when the image updates quickly or with a high resolution:

working decoded frame

non working decoded frame

After googling, I found that it might be correlated to the UDP buffer size. I have then recompiled the ffmpeg library with the following parameters inside ffmpeg/libavformat/udp.c

#define UDP_TX_BUF_SIZE 327680
#define UDP_MAX_PKT_SIZE 655360

It seems to improve but it still starts to fail at some point. Any idea which buffer I should increase and how?

gregoiregentil
  • 1,793
  • 1
  • 26
  • 56
  • It is not solution, but may give some additional information about the problem: https://github.com/ZoneMinder/zoneminder/issues/811 – user1742529 Jun 27 '18 at 09:58
  • you certainly must read this https://stackoverflow.com/q/29075467/1207193 – imbr Feb 18 '21 at 15:39

1 Answers1

1

For my problem (http://libav-users.943685.n4.nabble.com/UDP-Stream-Read-Pixelation-Macroblock-Corruption-td4655270.html), I was trying to capture from a multicast UDP stream that had been set-up by someone else. Because I didn't have the ability to mess with the source, I ended up switching from using libav to using libvlc as a wrapper and it worked perfectly. Here is the summary of what worked for me:

stream.h:

#include <vlc/vlc.h>
#include <vlc/libvlc.h>

struct ctx {
   uchar* frame;
};

stream.cpp:

void* lock(void* data, void** p_pixels){
  struct ctx* ctx = (struct ctx*)data;
  *p_pixels = ctx->frame;
  return NULL;
}

void unlock(void* data, void* id, void* const* p_pixels){
  struct ctx* ctx = (struct ctx*)data;
  uchar* pixels = (uchar*)*p_pixels;
  assert(id == NULL);
}

main.cpp:

struct ctx* context = (struct ctx*)malloc(sizeof(*context));
const char* const vlc_args[] = {"-vvv",
                                 "-q",
                                 "--no-audio"};
libvlc_media_t* media = NULL;
libvlc_media_player_t* media_player = NULL;
libvlc_instance_t* instance = libvlc_new(sizeof(vlc_args) / sizeof(vlc_args[0]), vlc_args);

media = libvlc_media_new_location(instance, "udp://@123.123.123.123:1000");
media_player = libvlc_media_player_new(instance);
libvlc_media_player_set_media(media_player, media);
libvlc_media_release(media);
context->frame = new uchar[height * width * 3];
libvlc_video_set_callbacks(media_player, lock, unlock, NULL, context);
libvlc_video_set_format(media_player, "RV24", VIDEOWIDTH, VIDEOHEIGHT, VIDEOWIDTH * 3);
libvlc_media_player_play(media_player);
Radford Parker
  • 731
  • 4
  • 14
  • 2
    Thank you very much. I mark it as answered though I would have preferred a fix in ffmpeg. – gregoiregentil Jan 30 '13 at 15:50
  • 1
    I remember spending a lot of time looking for a libav/ffmpeg fix similar to what you mentioned and nothing ended up working. If you have the ability to play with the source, I would recommend playing with the packet sizes to see if anything. – Radford Parker Jan 30 '13 at 22:29
  • 1
    you can receive rtsp packets using live555 library then pass it to ffmpeg, it's support for rtsp is much better than ffmpeg – arash kordi Jan 31 '13 at 17:18
  • 1
    It's good feed-back. Thanks. It probably explains why mplayer gives a clear output - I see 555 in the log of mplayer. – gregoiregentil Feb 02 '13 at 06:14
  • But in the end, I have given up on ffmpeg (just too much a pain) and I'm using VLC now. – gregoiregentil Feb 02 '13 at 06:15
  • 1
    Actually, I have just realized that VLC is also using Live555! – gregoiregentil Feb 15 '13 at 00:43
  • Banging my head against this one too. It should be possible through `AVOption`s or `AVDictionary` but nothing has worked for me so far. – Sergio Basurco Mar 16 '15 at 10:18