|
|
@@ -21,6 +21,7 @@ |
|
|
|
|
|
|
|
|
#include "libavutil/bswap.h" |
|
|
#include "libavutil/bswap.h" |
|
|
#include "libavutil/crc.h" |
|
|
#include "libavutil/crc.h" |
|
|
|
|
|
#include "libavutil/opt.h" |
|
|
#include "libavcodec/mpegvideo.h" |
|
|
#include "libavcodec/mpegvideo.h" |
|
|
#include "avformat.h" |
|
|
#include "avformat.h" |
|
|
#include "internal.h" |
|
|
#include "internal.h" |
|
|
@@ -64,8 +65,36 @@ typedef struct MpegTSWrite { |
|
|
int tsid; |
|
|
int tsid; |
|
|
int64_t first_pcr; |
|
|
int64_t first_pcr; |
|
|
int mux_rate; ///< set to 1 when VBR |
|
|
int mux_rate; ///< set to 1 when VBR |
|
|
|
|
|
|
|
|
|
|
|
int transport_stream_id; |
|
|
|
|
|
int original_network_id; |
|
|
|
|
|
int service_id; |
|
|
|
|
|
|
|
|
|
|
|
int pmt_start_pid; |
|
|
|
|
|
int start_pid; |
|
|
} MpegTSWrite; |
|
|
} MpegTSWrite; |
|
|
|
|
|
|
|
|
|
|
|
static const AVOption options[] = { |
|
|
|
|
|
{ "mpegts_transport_stream_id", "Set transport_stream_id field.", |
|
|
|
|
|
offsetof(MpegTSWrite, transport_stream_id), FF_OPT_TYPE_INT, 0x0001, 0x0001, 0xffff, AV_OPT_FLAG_ENCODING_PARAM}, |
|
|
|
|
|
{ "mpegts_original_network_id", "Set original_network_id field.", |
|
|
|
|
|
offsetof(MpegTSWrite, original_network_id), FF_OPT_TYPE_INT, 0x0001, 0x0001, 0xffff, AV_OPT_FLAG_ENCODING_PARAM}, |
|
|
|
|
|
{ "mpegts_service_id", "Set service_id field.", |
|
|
|
|
|
offsetof(MpegTSWrite, service_id), FF_OPT_TYPE_INT, 0x0001, 0x0001, 0xffff, AV_OPT_FLAG_ENCODING_PARAM}, |
|
|
|
|
|
{ "mpegts_pmt_start_pid", "Set the first pid of the PMT.", |
|
|
|
|
|
offsetof(MpegTSWrite, pmt_start_pid), FF_OPT_TYPE_INT, 0x1000, 0x1000, 0x1f00, AV_OPT_FLAG_ENCODING_PARAM}, |
|
|
|
|
|
{ "mpegts_start_pid", "Set the first pid.", |
|
|
|
|
|
offsetof(MpegTSWrite, start_pid), FF_OPT_TYPE_INT, 0x0100, 0x0100, 0x0f00, AV_OPT_FLAG_ENCODING_PARAM}, |
|
|
|
|
|
{ NULL }, |
|
|
|
|
|
}; |
|
|
|
|
|
|
|
|
|
|
|
static const AVClass mpegts_muxer_class = { |
|
|
|
|
|
"MPEGTS muxer", |
|
|
|
|
|
av_default_item_name, |
|
|
|
|
|
options, |
|
|
|
|
|
LIBAVUTIL_VERSION_INT, |
|
|
|
|
|
}; |
|
|
|
|
|
|
|
|
/* NOTE: 4 bytes must be left at the end for the crc32 */ |
|
|
/* NOTE: 4 bytes must be left at the end for the crc32 */ |
|
|
static void mpegts_write_section(MpegTSSection *s, uint8_t *buf, int len) |
|
|
static void mpegts_write_section(MpegTSSection *s, uint8_t *buf, int len) |
|
|
{ |
|
|
{ |
|
|
@@ -152,16 +181,9 @@ static int mpegts_write_section1(MpegTSSection *s, int tid, int id, |
|
|
/*********************************************/ |
|
|
/*********************************************/ |
|
|
/* mpegts writer */ |
|
|
/* mpegts writer */ |
|
|
|
|
|
|
|
|
#define DEFAULT_PMT_START_PID 0x1000 |
|
|
|
|
|
#define DEFAULT_START_PID 0x0100 |
|
|
|
|
|
#define DEFAULT_PROVIDER_NAME "FFmpeg" |
|
|
#define DEFAULT_PROVIDER_NAME "FFmpeg" |
|
|
#define DEFAULT_SERVICE_NAME "Service01" |
|
|
#define DEFAULT_SERVICE_NAME "Service01" |
|
|
|
|
|
|
|
|
/* default network id, transport stream and service identifiers */ |
|
|
|
|
|
#define DEFAULT_ONID 0x0001 |
|
|
|
|
|
#define DEFAULT_TSID 0x0001 |
|
|
|
|
|
#define DEFAULT_SID 0x0001 |
|
|
|
|
|
|
|
|
|
|
|
/* a PES packet header is generated every DEFAULT_PES_HEADER_FREQ packets */ |
|
|
/* a PES packet header is generated every DEFAULT_PES_HEADER_FREQ packets */ |
|
|
#define DEFAULT_PES_HEADER_FREQ 16 |
|
|
#define DEFAULT_PES_HEADER_FREQ 16 |
|
|
#define DEFAULT_PES_PAYLOAD_SIZE ((DEFAULT_PES_HEADER_FREQ - 1) * 184 + 170) |
|
|
#define DEFAULT_PES_PAYLOAD_SIZE ((DEFAULT_PES_HEADER_FREQ - 1) * 184 + 170) |
|
|
@@ -374,7 +396,7 @@ static MpegTSService *mpegts_add_service(MpegTSWrite *ts, |
|
|
service = av_mallocz(sizeof(MpegTSService)); |
|
|
service = av_mallocz(sizeof(MpegTSService)); |
|
|
if (!service) |
|
|
if (!service) |
|
|
return NULL; |
|
|
return NULL; |
|
|
service->pmt.pid = DEFAULT_PMT_START_PID + ts->nb_services - 1; |
|
|
|
|
|
|
|
|
service->pmt.pid = ts->pmt_start_pid + ts->nb_services; |
|
|
service->sid = sid; |
|
|
service->sid = sid; |
|
|
service->provider_name = av_strdup(provider_name); |
|
|
service->provider_name = av_strdup(provider_name); |
|
|
service->name = av_strdup(name); |
|
|
service->name = av_strdup(name); |
|
|
@@ -401,8 +423,8 @@ static int mpegts_write_header(AVFormatContext *s) |
|
|
const char *provider_name; |
|
|
const char *provider_name; |
|
|
int *pids; |
|
|
int *pids; |
|
|
|
|
|
|
|
|
ts->tsid = DEFAULT_TSID; |
|
|
|
|
|
ts->onid = DEFAULT_ONID; |
|
|
|
|
|
|
|
|
ts->tsid = ts->transport_stream_id; |
|
|
|
|
|
ts->onid = ts->original_network_id; |
|
|
/* allocate a single DVB service */ |
|
|
/* allocate a single DVB service */ |
|
|
title = av_metadata_get(s->metadata, "service_name", NULL, 0); |
|
|
title = av_metadata_get(s->metadata, "service_name", NULL, 0); |
|
|
if (!title) |
|
|
if (!title) |
|
|
@@ -410,7 +432,7 @@ static int mpegts_write_header(AVFormatContext *s) |
|
|
service_name = title ? title->value : DEFAULT_SERVICE_NAME; |
|
|
service_name = title ? title->value : DEFAULT_SERVICE_NAME; |
|
|
provider = av_metadata_get(s->metadata, "service_provider", NULL, 0); |
|
|
provider = av_metadata_get(s->metadata, "service_provider", NULL, 0); |
|
|
provider_name = provider ? provider->value : DEFAULT_PROVIDER_NAME; |
|
|
provider_name = provider ? provider->value : DEFAULT_PROVIDER_NAME; |
|
|
service = mpegts_add_service(ts, DEFAULT_SID, provider_name, service_name); |
|
|
|
|
|
|
|
|
service = mpegts_add_service(ts, ts->service_id, provider_name, service_name); |
|
|
service->pmt.write_packet = section_write_packet; |
|
|
service->pmt.write_packet = section_write_packet; |
|
|
service->pmt.opaque = s; |
|
|
service->pmt.opaque = s; |
|
|
service->pmt.cc = 15; |
|
|
service->pmt.cc = 15; |
|
|
@@ -440,7 +462,7 @@ static int mpegts_write_header(AVFormatContext *s) |
|
|
/* MPEG pid values < 16 are reserved. Applications which set st->id in |
|
|
/* MPEG pid values < 16 are reserved. Applications which set st->id in |
|
|
* this range are assigned a calculated pid. */ |
|
|
* this range are assigned a calculated pid. */ |
|
|
if (st->id < 16) { |
|
|
if (st->id < 16) { |
|
|
ts_st->pid = DEFAULT_START_PID + i; |
|
|
|
|
|
|
|
|
ts_st->pid = ts->start_pid + i; |
|
|
} else if (st->id < 0x1FFF) { |
|
|
} else if (st->id < 0x1FFF) { |
|
|
ts_st->pid = st->id; |
|
|
ts_st->pid = st->id; |
|
|
} else { |
|
|
} else { |
|
|
@@ -964,4 +986,5 @@ AVOutputFormat ff_mpegts_muxer = { |
|
|
mpegts_write_header, |
|
|
mpegts_write_header, |
|
|
mpegts_write_packet, |
|
|
mpegts_write_packet, |
|
|
mpegts_write_end, |
|
|
mpegts_write_end, |
|
|
|
|
|
.priv_class = &mpegts_muxer_class, |
|
|
}; |
|
|
}; |