[FFmpeg-user] ffmpeg mixing a/v streams from multiple IP but same port for multiple IP camera source

Aswin Thoudam aswinthou at gmail.com
Wed Feb 24 11:10:19 CET 2016


I have used ffmpeg 2.6.3 to record audio and video from multiple IP camera
multicast over respective multicast IP but on same audio and video port on
a PC having RHEL 6.6 OS.

I found that for single camera it is working fine but when 2 or more camera
is used then the video is getting mixed. On further searching I found some
material about some disagreement on the implementation of multicast
receiving between some application developers and kernel developer on who
should own this problem. I don't know if this problem is resolved or not
now or whether this is problem or not in the first place. But I needed to
get it working and found that the socket parameter IP_MULTICAST_ALL can
help in this situation. Also since I am making audio/video recording I
found that sometimes but very rarely ffmpeg is not able to get the video
codec information so it records audio only. So I made it to quit if it
didn't record video. I am uploading/sharing the patch I did for what I
need. Hope it might help any who needs similar behavior. I can't say if
what I did is correct or not but it is working for what I need.

The patch is

diff -crB ffmpeg-2.6.3-orig/libavformat/udp.c ffmpeg-2.5.3/libavformat/udp.c
*** ffmpeg-2.6.3-orig/libavformat/udp.c    2015-03-03 15:54:00.000000000
+0530
--- ffmpeg-2.6.3/libavformat/udp.c    2015-04-08 14:46:30.000000000 +0530
***************
*** 181,186 ****
--- 181,191 ----
              log_net_error(NULL, AV_LOG_ERROR,
"setsockopt(IP_ADD_MEMBERSHIP)");
              return -1;
          }
+         int mc=0;
+          if(setsockopt(sockfd, IPPROTO_IP, IP_MULTICAST_ALL, (const void
*)&mc, sizeof(mc)) < 0)
+           {
+               log_net_error(NULL, AV_LOG_ERROR,
"setsockopt(IP_MULTICAST_ALL)");
+          }
      }
  #endif
  #if HAVE_STRUCT_IPV6_MREQ && defined(IPPROTO_IPV6)
diff -crB ffmpeg-2.6.3-orig/libavformat/utils.c
ffmpeg-2.5.3/libavformat/utils.c
*** ffmpeg-2.6.3-orig/libavformat/utils.c    2015-01-10 09:51:16.000000000
+0530
--- ffmpeg-2.6.3/libavformat/utils.c    2015-04-08 19:29:17.763130726 +0530
***************
*** 3431,3437 ****
      if (ret >= 0 && ic->nb_streams)
          /* We could not have all the codec parameters before EOF. */
          ret = -1;
!     for (i = 0; i < ic->nb_streams; i++) {
          const char *errmsg;
          st = ic->streams[i];
          if (!has_codec_parameters(st, &errmsg)) {
--- 3431,3438 ----
      if (ret >= 0 && ic->nb_streams)
          /* We could not have all the codec parameters before EOF. */
          ret = -1;
!     int breakloop = 0;
!     for (i = 0; i < ic->nb_streams&&breakloop==0; i++) {
          const char *errmsg;
          st = ic->streams[i];
          if (!has_codec_parameters(st, &errmsg)) {
***************
*** 3441,3446 ****
--- 3442,3452 ----
                     "Could not find codec parameters for stream %d (%s):
%s\n"
                     "Consider increasing the value for the
'analyzeduration' and 'probesize' options\n",
                     i, buf, errmsg);
+             if(strstr(buf,"h264"))
+             {
+                 av_log(ic, AV_LOG_WARNING,"Quitting as video stream could
not be decoded\n");
+                 breakloop = 1;
+             }
          } else {
              ret = 0;
          }
***************
*** 3460,3465 ****
--- 3466,3476 ----
      if (ic->pb)
          av_log(ic, AV_LOG_DEBUG, "After avformat_find_stream_info() pos:
%"PRId64" bytes read:%"PRId64" seeks:%d frames:%d\n",
                 avio_tell(ic->pb), ic->pb->bytes_read, ic->pb->seek_count,
count);
+     if(breakloop!=0)
+     {
+         ret = -1;
+         ic->nb_streams=0;
+     }
      return ret;
  }

udp.c is for mixing of stream and utils.c is for making ffmpeg quit


More information about the ffmpeg-user mailing list