diff mbox series

[FFmpeg-devel,2/3] avformat/rtpdec_mpegts: add ff_mpegtsraw_dynamic_handler

Message ID 20201222003600.27621-2-ffmpeg@tmm1.net
State Superseded
Headers show
Series [FFmpeg-devel,1/3] avformat/rtsp: add support for satip://
Related show

Checks

Context Check Description
andriy/x86_make success Make finished
andriy/x86_make_fate success Make fate finished
andriy/PPC64_make success Make finished
andriy/PPC64_make_fate success Make fate finished

Commit Message

Aman Karmani Dec. 22, 2020, 12:35 a.m. UTC
From: Aman Karmani <aman@tmm1.net>

Passthrough handler which can be used to receive MP2T stream
over RTP, and repackage it into a AV_CODEC_ID_MPEG2TS data stream.

Signed-off-by: Aman Karmani <aman@tmm1.net>
---
 libavformat/rtpdec_formats.h |  1 +
 libavformat/rtpdec_mpegts.c  | 55 ++++++++++++++++++++++++++++++++++++
 2 files changed, 56 insertions(+)

Comments

Aman Karmani Dec. 22, 2020, 8:53 a.m. UTC | #1
On Mon, Dec 21, 2020 at 4:36 PM Aman Karmani <ffmpeg@tmm1.net> wrote:

> From: Aman Karmani <aman@tmm1.net>
>
> Passthrough handler which can be used to receive MP2T stream
> over RTP, and repackage it into a AV_CODEC_ID_MPEG2TS data stream.
>
> Signed-off-by: Aman Karmani <aman@tmm1.net>
> ---
>  libavformat/rtpdec_formats.h |  1 +
>  libavformat/rtpdec_mpegts.c  | 55 ++++++++++++++++++++++++++++++++++++
>  2 files changed, 56 insertions(+)
>
> diff --git a/libavformat/rtpdec_formats.h b/libavformat/rtpdec_formats.h
> index dad2b8ac1b..ce349292df 100644
> --- a/libavformat/rtpdec_formats.h
> +++ b/libavformat/rtpdec_formats.h
> @@ -74,6 +74,7 @@ extern const RTPDynamicProtocolHandler
> ff_mpeg_audio_robust_dynamic_handler;
>  extern const RTPDynamicProtocolHandler ff_mpeg_video_dynamic_handler;
>  extern const RTPDynamicProtocolHandler ff_mpeg4_generic_dynamic_handler;
>  extern const RTPDynamicProtocolHandler ff_mpegts_dynamic_handler;
> +extern const RTPDynamicProtocolHandler ff_mpegtsraw_dynamic_handler;
>  extern const RTPDynamicProtocolHandler ff_ms_rtp_asf_pfa_handler;
>  extern const RTPDynamicProtocolHandler ff_ms_rtp_asf_pfv_handler;
>  extern const RTPDynamicProtocolHandler ff_qcelp_dynamic_handler;
> diff --git a/libavformat/rtpdec_mpegts.c b/libavformat/rtpdec_mpegts.c
> index 405271f744..6d5a547030 100644
> --- a/libavformat/rtpdec_mpegts.c
> +++ b/libavformat/rtpdec_mpegts.c
> @@ -20,6 +20,7 @@
>   */
>
>  #include "libavutil/attributes.h"
> +#include "libavformat/internal.h"
>  #include "mpegts.h"
>  #include "rtpdec_formats.h"
>
> @@ -28,6 +29,7 @@ struct PayloadContext {
>      int read_buf_index;
>      int read_buf_size;
>      uint8_t buf[RTP_MAX_PACKET_LENGTH];
> +    AVStream *raw;
>  };
>
>  static void mpegts_close_context(PayloadContext *data)
> @@ -89,6 +91,50 @@ static int mpegts_handle_packet(AVFormatContext *ctx,
> PayloadContext *data,
>      return 0;
>  }
>
> +static av_cold int mpegtsraw_init(AVFormatContext *ctx, int st_index,
> +                                  PayloadContext *data)
> +{
> +    AVStream *st;
> +    st = avformat_new_stream(ctx, NULL);
> +    if (!st)
> +        return AVERROR(ENOMEM);
> +    st->codecpar->codec_type = AVMEDIA_TYPE_DATA;
> +    st->codecpar->codec_id   = AV_CODEC_ID_MPEG2TS;
> +    data->raw = st;
> +    return 0;
> +}
> +
> +static int mpegtsraw_handle_packet(AVFormatContext *ctx, PayloadContext
> *data,
> +                                   AVStream *st, AVPacket *pkt, uint32_t
> *timestamp,
> +                                   const uint8_t *buf, int len, uint16_t
> seq,
> +                                   int flags)
> +{
> +    int ret;
> +
> +    // We don't want to use the RTP timestamps at all. If the mpegts
> demuxer
> +    // doesn't set any pts/dts, the generic rtpdec code shouldn't try to
> +    // fill it in either, since the mpegts and RTP timestamps are in
> totally
> +    // different ranges.
> +    *timestamp = RTP_NOTS_VALUE;
> +
> +    if (!buf || len < 188) {
> +        return AVERROR_INVALIDDATA;
> +    }
> +
> +    if ((ret = av_new_packet(pkt, len)) < 0)
> +        return ret;
> +    memcpy(pkt->data, buf, len);
> +    pkt->stream_index = data->raw->index;
>

I realized this is a lot of unnecessary boilerplate just to copy data into
a packet.

The same thing can be achieved directly in rtsp.c, by creating the DATA
stream there. I've updated my local patchset accordingly and dropped this
patch.


> +    return 0;
> +}
> +
> +static void mpegtsraw_close_context(PayloadContext *data)
> +{
> +    if (!data)
> +        return;
> +    data->raw = NULL;
> +}
> +
>  const RTPDynamicProtocolHandler ff_mpegts_dynamic_handler = {
>      .codec_type        = AVMEDIA_TYPE_DATA,
>      .priv_data_size    = sizeof(PayloadContext),
> @@ -97,3 +143,12 @@ const RTPDynamicProtocolHandler
> ff_mpegts_dynamic_handler = {
>      .close             = mpegts_close_context,
>      .static_payload_id = 33,
>  };
> +
> +const RTPDynamicProtocolHandler ff_mpegtsraw_dynamic_handler = {
> +    .codec_type        = AVMEDIA_TYPE_DATA,
> +    .priv_data_size    = sizeof(PayloadContext),
> +    .parse_packet      = mpegtsraw_handle_packet,
> +    .init              = mpegtsraw_init,
> +    .close             = mpegtsraw_close_context,
> +    .static_payload_id = 33,
> +};
> --
> 2.29.2
>
>
diff mbox series

Patch

diff --git a/libavformat/rtpdec_formats.h b/libavformat/rtpdec_formats.h
index dad2b8ac1b..ce349292df 100644
--- a/libavformat/rtpdec_formats.h
+++ b/libavformat/rtpdec_formats.h
@@ -74,6 +74,7 @@  extern const RTPDynamicProtocolHandler ff_mpeg_audio_robust_dynamic_handler;
 extern const RTPDynamicProtocolHandler ff_mpeg_video_dynamic_handler;
 extern const RTPDynamicProtocolHandler ff_mpeg4_generic_dynamic_handler;
 extern const RTPDynamicProtocolHandler ff_mpegts_dynamic_handler;
+extern const RTPDynamicProtocolHandler ff_mpegtsraw_dynamic_handler;
 extern const RTPDynamicProtocolHandler ff_ms_rtp_asf_pfa_handler;
 extern const RTPDynamicProtocolHandler ff_ms_rtp_asf_pfv_handler;
 extern const RTPDynamicProtocolHandler ff_qcelp_dynamic_handler;
diff --git a/libavformat/rtpdec_mpegts.c b/libavformat/rtpdec_mpegts.c
index 405271f744..6d5a547030 100644
--- a/libavformat/rtpdec_mpegts.c
+++ b/libavformat/rtpdec_mpegts.c
@@ -20,6 +20,7 @@ 
  */
 
 #include "libavutil/attributes.h"
+#include "libavformat/internal.h"
 #include "mpegts.h"
 #include "rtpdec_formats.h"
 
@@ -28,6 +29,7 @@  struct PayloadContext {
     int read_buf_index;
     int read_buf_size;
     uint8_t buf[RTP_MAX_PACKET_LENGTH];
+    AVStream *raw;
 };
 
 static void mpegts_close_context(PayloadContext *data)
@@ -89,6 +91,50 @@  static int mpegts_handle_packet(AVFormatContext *ctx, PayloadContext *data,
     return 0;
 }
 
+static av_cold int mpegtsraw_init(AVFormatContext *ctx, int st_index,
+                                  PayloadContext *data)
+{
+    AVStream *st;
+    st = avformat_new_stream(ctx, NULL);
+    if (!st)
+        return AVERROR(ENOMEM);
+    st->codecpar->codec_type = AVMEDIA_TYPE_DATA;
+    st->codecpar->codec_id   = AV_CODEC_ID_MPEG2TS;
+    data->raw = st;
+    return 0;
+}
+
+static int mpegtsraw_handle_packet(AVFormatContext *ctx, PayloadContext *data,
+                                   AVStream *st, AVPacket *pkt, uint32_t *timestamp,
+                                   const uint8_t *buf, int len, uint16_t seq,
+                                   int flags)
+{
+    int ret;
+
+    // We don't want to use the RTP timestamps at all. If the mpegts demuxer
+    // doesn't set any pts/dts, the generic rtpdec code shouldn't try to
+    // fill it in either, since the mpegts and RTP timestamps are in totally
+    // different ranges.
+    *timestamp = RTP_NOTS_VALUE;
+
+    if (!buf || len < 188) {
+        return AVERROR_INVALIDDATA;
+    }
+
+    if ((ret = av_new_packet(pkt, len)) < 0)
+        return ret;
+    memcpy(pkt->data, buf, len);
+    pkt->stream_index = data->raw->index;
+    return 0;
+}
+
+static void mpegtsraw_close_context(PayloadContext *data)
+{
+    if (!data)
+        return;
+    data->raw = NULL;
+}
+
 const RTPDynamicProtocolHandler ff_mpegts_dynamic_handler = {
     .codec_type        = AVMEDIA_TYPE_DATA,
     .priv_data_size    = sizeof(PayloadContext),
@@ -97,3 +143,12 @@  const RTPDynamicProtocolHandler ff_mpegts_dynamic_handler = {
     .close             = mpegts_close_context,
     .static_payload_id = 33,
 };
+
+const RTPDynamicProtocolHandler ff_mpegtsraw_dynamic_handler = {
+    .codec_type        = AVMEDIA_TYPE_DATA,
+    .priv_data_size    = sizeof(PayloadContext),
+    .parse_packet      = mpegtsraw_handle_packet,
+    .init              = mpegtsraw_init,
+    .close             = mpegtsraw_close_context,
+    .static_payload_id = 33,
+};