mpegtsenc: Implement writing of Opus trim_start/trim_end control values
Signed-off-by: Sebastian Dröge <sebastian@centricular.com> Reviewed-by: Kieran Kunhya <kierank@obe.tv> Signed-off-by: Michael Niedermayer <michael@niedermayer.cc>
This commit is contained in:
		
							parent
							
								
									01509cdf92
								
							
						
					
					
						commit
						7d6a4797f1
					
				| @ -230,6 +230,7 @@ typedef struct MpegTSWriteStream { | ||||
| 
 | ||||
|     /* For Opus */ | ||||
|     int opus_queued_samples; | ||||
|     int opus_pending_trim_start; | ||||
| } MpegTSWriteStream; | ||||
| 
 | ||||
| static void mpegts_write_pat(AVFormatContext *s) | ||||
| @ -825,6 +826,9 @@ static int mpegts_write_header(AVFormatContext *s) | ||||
|             if (ret < 0) | ||||
|                 goto fail; | ||||
|         } | ||||
|         if (st->codec->codec_id == AV_CODEC_ID_OPUS) { | ||||
|             ts_st->opus_pending_trim_start = st->codec->initial_padding * 48000 / st->codec->sample_rate; | ||||
|         } | ||||
|     } | ||||
| 
 | ||||
|     av_freep(&pids); | ||||
| @ -1513,17 +1517,38 @@ static int mpegts_write_packet_internal(AVFormatContext *s, AVPacket *pkt) | ||||
| 
 | ||||
|         /* Add Opus control header */ | ||||
|         if ((AV_RB16(pkt->data) >> 5) != 0x3ff) { | ||||
|             uint8_t *side_data; | ||||
|             int side_data_size; | ||||
|             int i, n; | ||||
|             int ctrl_header_size; | ||||
|             int trim_start = 0, trim_end = 0; | ||||
| 
 | ||||
|             opus_samples = opus_get_packet_samples(s, pkt); | ||||
| 
 | ||||
|             data = av_malloc(pkt->size + 2 + pkt->size / 255 + 1); | ||||
|             side_data = av_packet_get_side_data(pkt, | ||||
|                                                 AV_PKT_DATA_SKIP_SAMPLES, | ||||
|                                                 &side_data_size); | ||||
| 
 | ||||
|             if (side_data && side_data_size >= 10) { | ||||
|                 trim_end = AV_RL32(side_data + 4) * 48000 / st->codec->sample_rate; | ||||
|             } | ||||
| 
 | ||||
|             ctrl_header_size = pkt->size + 2 + pkt->size / 255 + 1; | ||||
|             if (ts_st->opus_pending_trim_start) | ||||
|               ctrl_header_size += 2; | ||||
|             if (trim_end) | ||||
|               ctrl_header_size += 2; | ||||
| 
 | ||||
|             data = av_malloc(ctrl_header_size); | ||||
|             if (!data) | ||||
|                 return AVERROR(ENOMEM); | ||||
| 
 | ||||
|             /* TODO: Write trim if needed */ | ||||
|             data[0] = 0x7f; | ||||
|             data[1] = 0xe0; | ||||
|             if (ts_st->opus_pending_trim_start) | ||||
|                 data[1] |= 0x10; | ||||
|             if (trim_end) | ||||
|                 data[1] |= 0x08; | ||||
| 
 | ||||
|             n = pkt->size; | ||||
|             i = 2; | ||||
| @ -1535,9 +1560,21 @@ static int mpegts_write_packet_internal(AVFormatContext *s, AVPacket *pkt) | ||||
| 
 | ||||
|             av_assert0(2 + pkt->size / 255 + 1 == i); | ||||
| 
 | ||||
|             if (ts_st->opus_pending_trim_start) { | ||||
|                 trim_start = FFMIN(ts_st->opus_pending_trim_start, opus_samples); | ||||
|                 AV_WB16(data + i, trim_start); | ||||
|                 i += 2; | ||||
|                 ts_st->opus_pending_trim_start -= trim_start; | ||||
|             } | ||||
|             if (trim_end) { | ||||
|                 trim_end = FFMIN(trim_end, opus_samples - trim_start); | ||||
|                 AV_WB16(data + i, trim_end); | ||||
|                 i += 2; | ||||
|             } | ||||
| 
 | ||||
|             memcpy(data + i, pkt->data, pkt->size); | ||||
|             buf     = data; | ||||
|             size    = pkt->size + 2 + pkt->size / 255 + 1; | ||||
|             size    = ctrl_header_size; | ||||
|         } else { | ||||
|             /* TODO: Can we get TS formatted data here? If so we will
 | ||||
|              * need to count the samples of that too! */ | ||||
|  | ||||
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user