diff --git a/doc/muxers.texi b/doc/muxers.texi
index 1af603b..575841c 100644
--- a/doc/muxers.texi
+++ b/doc/muxers.texi
@@ -1924,7 +1924,8 @@ is less than 100 ms is used for VBR streams.
 Maximum time in seconds between PAT/PMT tables. Default is @code{0.1}.
 
 @item sdt_period @var{duration}
-Maximum time in seconds between SDT tables. Default is @code{0.5}.
+Maximum time in seconds between SDT tables. Default is @code{0.5}. Regardless
+of this setting no SDT is written in m2ts mode.
 
 @item nit_period @var{duration}
 Maximum time in seconds between NIT tables. Default is @code{0.5}.
diff --git a/libavformat/mpegtsenc.c b/libavformat/mpegtsenc.c
index ead2ca2..f4c9e1f 100644
--- a/libavformat/mpegtsenc.c
+++ b/libavformat/mpegtsenc.c
@@ -29,6 +29,7 @@
 
 #include "libavcodec/ac3_parser_internal.h"
 #include "libavcodec/startcode.h"
+#include "libavcodec/put_bits.h"
 
 #include "avformat.h"
 #include "avio_internal.h"
@@ -36,6 +37,9 @@
 #include "mpegts.h"
 
 #define PCR_TIME_BASE 27000000
+#define M2TS_DEFAULT_MUXRATE 54000000
+#define M2TS_DEFAULT_UHD_MUXRATE 128000000
+#define M2TS_PCR_RETRANS_TIME 50
 
 /* write DVB SI sections */
 
@@ -76,6 +80,7 @@ typedef struct MpegTSWrite {
     const AVClass *av_class;
     MpegTSSection pat; /* MPEG-2 PAT table */
     MpegTSSection sdt; /* MPEG-2 SDT table context */
+    MpegTSSection sit; /* MPEG-2 SIT table context */
     MpegTSSection nit; /* MPEG-2 NIT table context */
     MpegTSService **services;
     AVPacket *pkt;
@@ -102,6 +107,8 @@ typedef struct MpegTSWrite {
     int m2ts_audio_pid;
     int m2ts_pgssub_pid;
     int m2ts_textsub_pid;
+    int64_t m2ts_pcr_period;
+    int64_t m2ts_last_pcr;
 
     int pcr_period_ms;
 #define MPEGTS_FLAG_REEMIT_PAT_PMT  0x01
@@ -119,6 +126,7 @@ typedef struct MpegTSWrite {
     int64_t last_pat_ts;
     int64_t last_sdt_ts;
     int64_t last_nit_ts;
+    int64_t nb_packets;
 
     uint8_t provider_name[256];
 
@@ -203,8 +211,9 @@ static int mpegts_write_section1(MpegTSSection *s, int tid, int id,
 {
     uint8_t section[1024], *q;
     unsigned int tot_len;
-    /* reserved_future_use field must be set to 1 for SDT and NIT */
-    unsigned int flags = (tid == SDT_TID || tid == NIT_TID) ? 0xf000 : 0xb000;
+    /* reserved_future_use field must be set to 1 for SDT, SIT and NIT */
+    unsigned int flags = (tid == SDT_TID || tid == NIT_TID || tid == SIT_TID) ? 0xf000 : 0xb000;
+
 
     tot_len = 3 + 5 + len + 4;
     /* check if not too big */
@@ -232,6 +241,7 @@ static int mpegts_write_section1(MpegTSSection *s, int tid, int id,
 
 /* we retransmit the SI info at this rate */
 #define SDT_RETRANS_TIME 500
+#define SIT_RETRANS_TIME 500
 #define PAT_RETRANS_TIME 100
 #define PCR_RETRANS_TIME 20
 #define NIT_RETRANS_TIME 500
@@ -272,6 +282,10 @@ static void mpegts_write_pat(AVFormatContext *s)
         put16(&q, 0x0000);
         put16(&q, NIT_PID);
     }
+    if (ts->m2ts_mode) {
+        put16(&q, 0);
+        put16(&q, 0xe000 | SIT_PID);
+    }
     for (i = 0; i < ts->nb_services; i++) {
         service = ts->services[i];
         put16(&q, service->sid);
@@ -829,6 +843,44 @@ static int mpegts_write_pmt(AVFormatContext *s, MpegTSService *service)
     return 0;
 }
 
+static void mpegts_write_sit(AVFormatContext *s)
+{
+    MpegTSWrite *ts = s->priv_data;
+    uint8_t data[SECTION_LENGTH];
+    PutBitContext bs;
+
+    init_put_bits(&bs, data, sizeof(data));
+
+    put_bits(&bs,  4, 0x0f);    // DVB_reserved_for_future_use
+
+    if (ts->m2ts_mode) {
+        put_bits(&bs, 12, 0x0a);      // transmission_info_loop_length
+        put_bits(&bs,  8, 0x63);      // descriptor_tag - partial_transport_stream_descriptor
+        put_bits(&bs,  8, 0x08);      // descriptor_length
+        put_bits(&bs,  2, 0x03);      // DVB_reserved_future_use
+        put_bits(&bs, 22, ts->mux_rate / 400); // peak_rate
+        put_bits(&bs,  2, 0x03);      // DVB_reserved_future_use
+        put_bits(&bs, 22, 0x3fffff);  // minimum_overall_smoothing_rate
+        put_bits(&bs,  2, 0x03);      // DVB_reserved_future_use
+        put_bits(&bs, 14, 0x3fff);    // maximum_overall_smoothing_buffer
+    } else {
+        put_bits(&bs, 12, 0);         // transmission_info_loop_length
+    }
+
+    for (int i = 0; i < ts->nb_services; i++) {
+        put_bits(&bs, 16, ts->services[i]->sid & 0xffff); // service_id (equivalent to program_number)
+        put_bits(&bs,  1, 1);          // DVB_reserved_future_use
+        put_bits(&bs,  3, 0);          // running_status
+        put_bits(&bs, 12, 0);          // service_loop_length
+    }
+
+    flush_put_bits(&bs);
+
+    mpegts_write_section1(&ts->sit, SIT_TID, 0xffff, ts->tables_version, 0, 0,
+                          data, put_bits_count(&bs) >> 3);
+}
+
+
 static void mpegts_write_sdt(AVFormatContext *s)
 {
     MpegTSWrite *ts = s->priv_data;
@@ -946,7 +998,7 @@ invalid:
 
 static int64_t get_pcr(const MpegTSWrite *ts)
 {
-    return av_rescale(ts->total_size + 11, 8 * PCR_TIME_BASE, ts->mux_rate) +
+    return av_rescale(ts->nb_packets * TS_PACKET_SIZE + 11, 8 * PCR_TIME_BASE, ts->mux_rate) +
            ts->first_pcr;
 }
 
@@ -962,6 +1014,7 @@ static void write_packet(AVFormatContext *s, const uint8_t *packet)
     }
     avio_write(s->pb, packet, TS_PACKET_SIZE);
     ts->total_size += TS_PACKET_SIZE;
+    ts->nb_packets++;
 }
 
 static void section_write_packet(MpegTSSection *s, const uint8_t *packet)
@@ -994,7 +1047,7 @@ static MpegTSService *mpegts_add_service(AVFormatContext *s, int sid,
         return NULL;
     service->pmt.pid       = ts->pmt_start_pid + ts->nb_services;
     service->sid           = sid;
-    service->pcr_pid       = 0x1fff;
+    service->pcr_pid       = ts->m2ts_mode ? M2TS_PCR_PID : 0x1fff;
     if (encode_str8(service->provider_name, provider_name) < 0 ||
         encode_str8(service->name, service_name) < 0) {
         av_log(s, AV_LOG_ERROR, "Too long service or provider name\n");
@@ -1102,6 +1155,17 @@ static int mpegts_init(AVFormatContext *s)
             av_log(s, AV_LOG_ERROR, "Only one program is allowed in m2ts mode!\n");
             return AVERROR(EINVAL);
         }
+        if (ts->mux_rate <= 1) {
+            ts->mux_rate = M2TS_DEFAULT_MUXRATE;
+            for (i = 0; i < s->nb_streams; i++) {
+                AVCodecParameters *codecpar = s->streams[i]->codecpar;
+                if (codecpar->codec_type == AVMEDIA_TYPE_VIDEO && codecpar->height > 1080)
+                    ts->mux_rate = M2TS_DEFAULT_UHD_MUXRATE;
+            }
+            av_log(s, AV_LOG_INFO, "Muxrate is not set for m2ts mode, using %d bps\n", ts->mux_rate);
+        }
+        // this is used for sit period in m2ts mode
+        ts->sdt_period_us = SIT_RETRANS_TIME * 1000LL;
     }
 
     if (s->max_delay < 0) /* Not set by the caller */
@@ -1136,6 +1200,12 @@ static int mpegts_init(AVFormatContext *s)
     ts->sdt.write_packet = section_write_packet;
     ts->sdt.opaque       = s;
 
+    ts->sit.pid          = SIT_PID;
+    ts->sit.cc           = 15;
+    ts->sit.discontinuity= ts->flags & MPEGTS_FLAG_DISCONT;
+    ts->sit.write_packet = section_write_packet;
+    ts->sit.opaque       = s;
+
     ts->nit.pid          = NIT_PID;
     ts->nit.cc           = 15;
     ts->nit.discontinuity= ts->flags & MPEGTS_FLAG_DISCONT;
@@ -1257,7 +1327,11 @@ static int mpegts_init(AVFormatContext *s)
     if (ts->copyts < 1)
         ts->first_pcr = av_rescale(s->max_delay, PCR_TIME_BASE, AV_TIME_BASE);
 
-    select_pcr_streams(s);
+    ts->m2ts_pcr_period = av_rescale(ts->pcr_period_ms == -1 ? M2TS_PCR_RETRANS_TIME : ts->pcr_period_ms, PCR_TIME_BASE, 1000);
+    ts->m2ts_last_pcr   = ts->first_pcr - ts->m2ts_pcr_period;
+
+    if (!ts->m2ts_mode)
+        select_pcr_streams(s);
 
     ts->last_pat_ts = AV_NOPTS_VALUE;
     ts->last_sdt_ts = AV_NOPTS_VALUE;
@@ -1301,7 +1375,10 @@ static void retransmit_si_info(AVFormatContext *s, int force_pat, int force_sdt,
     ) {
         if (pcr != AV_NOPTS_VALUE)
             ts->last_sdt_ts = FFMAX(pcr, ts->last_sdt_ts);
-        mpegts_write_sdt(s);
+        if (!ts->m2ts_mode)
+            mpegts_write_sdt(s);
+        else
+            mpegts_write_sit(s);
     }
     if ((pcr != AV_NOPTS_VALUE && ts->last_pat_ts == AV_NOPTS_VALUE) ||
         (pcr != AV_NOPTS_VALUE && pcr - ts->last_pat_ts >= ts->pat_period) ||
@@ -1338,11 +1415,17 @@ static int write_pcr_bits(uint8_t *buf, int64_t pcr)
 }
 
 /* Write a single null transport stream packet */
-static void mpegts_insert_null_packet(AVFormatContext *s)
+static void mpegts_insert_null_packet(AVFormatContext *s, int force)
 {
+    MpegTSWrite *ts = s->priv_data;
     uint8_t *q;
     uint8_t buf[TS_PACKET_SIZE];
 
+    if (ts->m2ts_mode && !force) {
+        ts->nb_packets++;
+        return;
+    }
+
     q    = buf;
     *q++ = 0x47;
     *q++ = 0x00 | 0x1f;
@@ -1353,24 +1436,23 @@ static void mpegts_insert_null_packet(AVFormatContext *s)
 }
 
 /* Write a single transport stream packet with a PCR and no payload */
-static void mpegts_insert_pcr_only(AVFormatContext *s, AVStream *st)
+static void mpegts_insert_pcr_only(AVFormatContext *s, int pid, int cc, int *discontinuity)
 {
     MpegTSWrite *ts = s->priv_data;
-    MpegTSWriteStream *ts_st = st->priv_data;
     uint8_t *q;
     uint8_t buf[TS_PACKET_SIZE];
 
     q    = buf;
     *q++ = 0x47;
-    *q++ = ts_st->pid >> 8;
-    *q++ = ts_st->pid;
-    *q++ = 0x20 | ts_st->cc;   /* Adaptation only */
+    *q++ = pid >> 8;
+    *q++ = pid;
+    *q++ = 0x20 | cc;   /* Adaptation only */
     /* Continuity Count field does not increment (see 13818-1 section 2.4.3.3) */
     *q++ = TS_PACKET_SIZE - 5; /* Adaptation Field Length */
     *q++ = 0x10;               /* Adaptation flags: PCR present */
-    if (ts_st->discontinuity) {
+    if (discontinuity && *discontinuity) {
         q[-1] |= 0x80;
-        ts_st->discontinuity = 0;
+        *discontinuity = 0;
     }
 
     /* PCR coded into 6 bytes */
@@ -1381,6 +1463,12 @@ static void mpegts_insert_pcr_only(AVFormatContext *s, AVStream *st)
     write_packet(s, buf);
 }
 
+static void mpegts_insert_pcr_only_for_stream(AVFormatContext *s, AVStream *st)
+{
+    MpegTSWriteStream *ts_st = st->priv_data;
+    mpegts_insert_pcr_only(s, ts_st->pid, ts_st->cc, &ts_st->discontinuity);
+}
+
 static void write_pts(uint8_t *q, int fourbits, int64_t pts)
 {
     int val;
@@ -1510,6 +1598,11 @@ static void mpegts_write_pes(AVFormatContext *s, AVStream *st,
             pcr = get_pcr(ts);
             if (pcr >= ts->next_pcr) {
                 int64_t next_pcr = INT64_MAX;
+                if (ts->m2ts_mode) {
+                    mpegts_insert_pcr_only(s, M2TS_PCR_PID, 0, NULL);
+                    ts->m2ts_last_pcr = FFMAX(pcr - ts->m2ts_pcr_period, ts->m2ts_last_pcr + ts->m2ts_pcr_period);
+                    next_pcr = FFMIN(next_pcr, ts->m2ts_last_pcr + ts->m2ts_pcr_period);
+                } else {
                 for (int i = 0; i < s->nb_streams; i++) {
                     /* Make the current stream the last, because for that we
                      * can insert the pcr into the payload later */
@@ -1520,7 +1613,7 @@ static void mpegts_write_pes(AVFormatContext *s, AVStream *st,
                         if (pcr - ts_st2->last_pcr >= ts_st2->pcr_period) {
                             ts_st2->last_pcr = FFMAX(pcr - ts_st2->pcr_period, ts_st2->last_pcr + ts_st2->pcr_period);
                             if (st2 != st) {
-                                mpegts_insert_pcr_only(s, st2);
+                                mpegts_insert_pcr_only_for_stream(s, st2);
                                 pcr = get_pcr(ts);
                             } else {
                                 write_pcr = 1;
@@ -1529,14 +1622,15 @@ static void mpegts_write_pes(AVFormatContext *s, AVStream *st,
                         next_pcr = FFMIN(next_pcr, ts_st2->last_pcr + ts_st2->pcr_period);
                     }
                 }
+                }
                 ts->next_pcr = next_pcr;
             }
             if (dts != AV_NOPTS_VALUE && (dts - pcr / 300) > delay) {
                 /* pcr insert gets priority over null packet insert */
                 if (write_pcr)
-                    mpegts_insert_pcr_only(s, st);
+                    mpegts_insert_pcr_only_for_stream(s, st);
                 else
-                    mpegts_insert_null_packet(s);
+                    mpegts_insert_null_packet(s, 0);
                 /* recalculate write_pcr and possibly retransmit si_info */
                 continue;
             }
@@ -2162,7 +2256,7 @@ static void mpegts_write_flush(AVFormatContext *s)
     if (ts->m2ts_mode) {
         int packets = (avio_tell(s->pb) / (TS_PACKET_SIZE + 4)) % 32;
         while (packets++ < 32)
-            mpegts_insert_null_packet(s);
+            mpegts_insert_null_packet(s, 1);
     }
 }
 
@@ -2281,7 +2375,7 @@ static const AVOption options[] = {
     { "nit", "Enable NIT transmission",
       0, AV_OPT_TYPE_CONST, { .i64 = MPEGTS_FLAG_NIT}, 0, INT_MAX, ENC, "mpegts_flags" },
     { "mpegts_copyts", "don't offset dts/pts", OFFSET(copyts), AV_OPT_TYPE_BOOL, { .i64 = -1 }, -1, 1, ENC },
-    { "tables_version", "set PAT, PMT, SDT and NIT version", OFFSET(tables_version), AV_OPT_TYPE_INT, { .i64 = 0 }, 0, 31, ENC },
+    { "tables_version", "set PAT, PMT, SDT, SIT and NIT version", OFFSET(tables_version), AV_OPT_TYPE_INT, { .i64 = 0 }, 0, 31, ENC },
     { "omit_video_pes_length", "Omit the PES packet length for video packets",
       OFFSET(omit_video_pes_length), AV_OPT_TYPE_BOOL, { .i64 = 1 }, 0, 1, ENC },
     { "pcr_period", "PCR retransmission time in milliseconds",
