@@ -72,7 +72,7 @@ VideoStore::VideoStore(
7272 next_dts(nullptr ),
7373 audio_next_pts(0 ),
7474 max_stream_index(-1 ),
75- reorder_queue_size(1 ) {
75+ reorder_queue_size(0 ) {
7676 FFMPEGInit ();
7777 swscale.init ();
7878 opkt = av_packet_ptr{av_packet_alloc ()};
@@ -301,19 +301,30 @@ bool VideoStore::open() {
301301 const AVDictionaryEntry *opts_level = av_dict_get (opts, " level" , nullptr , AV_DICT_MATCH_CASE);
302302 if (opts_level) {
303303 video_out_ctx->level = std::stoul (opts_level->value );
304- } else if (!video_out_ctx->level ) {
305- video_out_ctx->level = 32 ;
304+ // } else if (!video_out_ctx->level) {
305+ // video_out_ctx->level = 32;
306306 }
307307 const AVDictionaryEntry *opts_gop_size = av_dict_get (opts, " gop_size" , nullptr , AV_DICT_MATCH_CASE);
308308 if (opts_gop_size) {
309309 video_out_ctx->gop_size = std::stoul (opts_gop_size->value );
310- } else if (!video_out_ctx->gop_size ) {
311- video_out_ctx->gop_size = 12 ;
310+ // } else if (!video_out_ctx->gop_size) {
311+ // video_out_ctx->gop_size = 12;
312312 }
313- zm_dump_codec (video_out_ctx);
314- if (!video_out_ctx->bit_rate ) {
315- video_out_ctx->bit_rate = monitor->get_capture_bitrate ();
313+ // zm_dump_codec(video_out_ctx);
314+ const AVDictionaryEntry *opts_bitrate = av_dict_get (opts, " bitrate" , nullptr , AV_DICT_MATCH_CASE);
315+ if (opts_bitrate) {
316+ video_out_ctx->bit_rate = std::stoul (opts_bitrate->value );
317+ av_dict_set (&opts, " bitrate" , nullptr , AV_DICT_MATCH_CASE);
318+ } else {
319+ opts_bitrate = av_dict_get (opts, " bit_rate" , nullptr , AV_DICT_MATCH_CASE);
320+ if (opts_bitrate) {
321+ video_out_ctx->bit_rate = std::stoul (opts_bitrate->value );
322+ av_dict_set (&opts, " bit_rate" , nullptr , AV_DICT_MATCH_CASE);
323+ }
316324 }
325+ // if (!video_out_ctx->bit_rate) {
326+ // video_out_ctx->bit_rate = monitor->get_capture_bitrate();
327+ // }
317328 zm_dump_codec (video_out_ctx);
318329
319330 // Don't have an input stream, so need to tell it what we are sending it, or are transcoding
@@ -322,8 +333,8 @@ bool VideoStore::open() {
322333 video_out_ctx->codec_type = AVMEDIA_TYPE_VIDEO;
323334
324335 if (video_out_ctx->codec_id == AV_CODEC_ID_H264) {
325- video_out_ctx->bit_rate = 2000000 ;
326- video_out_ctx->max_b_frames = 1 ;
336+ // video_out_ctx->bit_rate = 2000000;
337+ // video_out_ctx->max_b_frames = 1;
327338 } else if (video_out_ctx->codec_id == AV_CODEC_ID_MPEG2VIDEO) {
328339 /* just for testing, we also add B frames */
329340 video_out_ctx->max_b_frames = 2 ;
@@ -345,6 +356,10 @@ bool VideoStore::open() {
345356 av_opt_set (video_out_ctx->priv_data , " enc" , std::to_string (devid).c_str (), 0 );
346357 }
347358#endif
359+ const AVDictionaryEntry *xcoder_params = av_dict_get (opts, " xcoder-params" , nullptr , AV_DICT_MATCH_CASE);
360+ if (xcoder_params) {
361+ av_opt_set (video_out_ctx->priv_data , " xcoder-params" , xcoder_params->value , 0 );
362+ }
348363
349364 if ((ret = avcodec_open2 (video_out_ctx, video_out_codec, &opts)) < 0 ) {
350365 if (wanted_encoder != " " and wanted_encoder != " auto" ) {
@@ -495,6 +510,7 @@ bool VideoStore::open() {
495510 zm_dump_stream_format (oc, 0 , 0 , 1 );
496511 if (audio_out_stream) zm_dump_stream_format (oc, 1 , 0 , 1 );
497512
513+ av_dict_set (&opts, " xcoder-params" , nullptr , AV_DICT_MATCH_CASE);
498514 const AVDictionaryEntry *movflags_entry = av_dict_get (opts, " movflags" , nullptr , AV_DICT_MATCH_CASE);
499515 if (!movflags_entry) {
500516 Debug (1 , " setting movflags to frag_keyframe+empty_moov+faststart" );
@@ -1050,7 +1066,6 @@ int VideoStore::writePacket(const std::shared_ptr<ZMPacket> zm_pkt) {
10501066 Error (" Unknown stream type in packet (%d)" , zm_pkt->codec_type );
10511067 return -1 ;
10521068 }
1053- Debug (1 , " Queue for %d" , stream_index);
10541069 auto &queue = reorder_queues[stream_index];
10551070 Debug (1 , " Queue size for %d is %zu" , stream_index, queue.size ());
10561071
@@ -1154,23 +1169,27 @@ int VideoStore::writeVideoFramePacket(const std::shared_ptr<ZMPacket> zm_packet)
11541169 );
11551170 }
11561171 } else if (zm_packet->ai_frame ) {
1157- Debug (1 , " Using ai_frame" );
1172+ Debug (1 , " Want ai_frame" );
11581173 if (zm_packet->ai_frame ->width == video_out_ctx->width
1159- and
1160- zm_packet->ai_frame ->height == video_out_ctx->height
1161- and
1162- static_cast <AVPixelFormat>(zm_packet->ai_frame ->format ) == chosen_codec_data->sw_pix_fmt
1163- ) {
1164- av_frame_ref (frame.get (), zm_packet->ai_frame .get ());
1165- } else {
1166- frame = av_frame_ptr (zm_packet->get_out_frame (video_out_ctx->width , video_out_ctx->height , chosen_codec_data->sw_pix_fmt ));
1167- if (!frame) {
1168- Error (" Unable to allocate a frame" );
1169- return 0 ;
1170- }
1171- // Have in_frame.... may need to convert it to out_frame
1172- swscale.Convert (zm_packet->ai_frame .get (), frame.get ());
1174+ and
1175+ zm_packet->ai_frame ->height == video_out_ctx->height
1176+ and
1177+ static_cast <AVPixelFormat>(zm_packet->ai_frame ->format ) == chosen_codec_data->sw_pix_fmt
1178+ ) {
1179+ Debug (1 , " Using ai_frame" );
1180+ av_frame_ref (frame.get (), zm_packet->ai_frame .get ());
1181+ } else {
1182+ Debug (1 , " reating ai_frame" );
1183+ frame = av_frame_ptr (zm_packet->get_out_frame (video_out_ctx->width , video_out_ctx->height , chosen_codec_data->sw_pix_fmt ));
1184+ if (!frame) {
1185+ Error (" Unable to allocate a frame" );
1186+ return 0 ;
11731187 }
1188+ av_frame_copy_props (frame.get (), zm_packet->ai_frame .get ());
1189+
1190+ // Have in_frame.... may need to convert it to out_frame
1191+ swscale.Convert (zm_packet->ai_frame .get (), frame.get ());
1192+ }
11741193 } else if (zm_packet->in_frame ) {
11751194 Debug (1 , " Using in_frame" );
11761195 if (zm_packet->in_frame ->width == video_out_ctx->width
@@ -1181,16 +1200,18 @@ int VideoStore::writeVideoFramePacket(const std::shared_ptr<ZMPacket> zm_packet)
11811200 ) {
11821201 av_frame_ref (frame.get (), zm_packet->in_frame .get ());
11831202 } else {
1203+ Debug (1 , " Scaling in_frame" );
11841204 av_frame_ref (frame.get (), zm_packet->get_out_frame (video_out_ctx->width , video_out_ctx->height , chosen_codec_data->sw_pix_fmt ));
11851205 // Have in_frame.... may need to convert it to out_frame
11861206 swscale.Convert (zm_packet->in_frame .get (), frame.get ());
1207+ av_frame_copy_props (frame.get (), zm_packet->in_frame .get ());
11871208 }
11881209 } // end if no in_frame
11891210 } // end if no out_frame
11901211
11911212#if HAVE_LIBAVUTIL_HWCONTEXT_H
11921213 if (video_out_ctx->hw_frames_ctx and (static_cast <AVPixelFormat>(frame->format ) != video_out_ctx->pix_fmt )) {
1193- Debug ( 1 , " Using hwframe" );
1214+ zm_dump_frame (frame. get () , " using hwframe, src is " );
11941215 int ret;
11951216 av_frame_ptr hw_frame = av_frame_ptr{zm_av_frame_alloc ()};
11961217 if (!hw_frame) {
@@ -1208,12 +1229,13 @@ int VideoStore::writeVideoFramePacket(const std::shared_ptr<ZMPacket> zm_packet)
12081229 Error (" Error while transferring frame data to surface: %s." , av_err2str (ret));
12091230 return ret;
12101231 }
1211- ret = av_frame_copy_props (frame .get (), hw_frame .get ());
1232+ ret = av_frame_copy_props ( hw_frame .get (), frame .get ());
12121233 if (ret < 0 ) {
12131234 Error (" Unable to copy props: %s, continuing" , av_make_error_string (ret).c_str ());
12141235 }
12151236
12161237 frame = std::move (hw_frame);
1238+ zm_dump_frame (frame.get (), " using hwframe, dst is" );
12171239 } // end if hwaccel
12181240#endif
12191241 if (!frame) {
@@ -1244,6 +1266,17 @@ int VideoStore::writeVideoFramePacket(const std::shared_ptr<ZMPacket> zm_packet)
12441266 }
12451267 } else {
12461268 if (zm_packet->in_frame ) {
1269+ Debug (2 ,
1270+ " pts for frame(%d) to packet pts (%" PRId64 " ) from (zm_packet->in_frame(%" PRIi64 " - first %" PRId64 " ) @ %d/%d=>%d/%d" ,
1271+ frame_count,
1272+ zm_packet->packet ->pts ,
1273+ zm_packet->in_frame ->pts ,
1274+ video_first_pts,
1275+ video_in_stream->time_base .num ,
1276+ video_in_stream->time_base .den ,
1277+ video_out_ctx->time_base .num ,
1278+ video_out_ctx->time_base .den );
1279+
12471280 if (video_first_pts == AV_NOPTS_VALUE) {
12481281 video_first_pts = zm_packet->in_frame ->pts ;
12491282 Debug (2 , " No video_first_pts, set to (%" PRId64 " )" , video_first_pts);
@@ -1305,7 +1338,7 @@ int VideoStore::writeVideoFramePacket(const std::shared_ptr<ZMPacket> zm_packet)
13051338 if (ret != AVERROR (EAGAIN)) {
13061339 Error (" Could not receive packet (error %d = %s)" , ret, av_make_error_string (ret).c_str ());
13071340 } else {
1308- Debug (1 , " Could not receive packet (error %d = %s)" , ret, av_make_error_string (ret).c_str ());
1341+ Debug (4 , " Could not receive packet (error %d = %s)" , ret, av_make_error_string (ret).c_str ());
13091342 }
13101343 return ret;
13111344 }
@@ -1487,10 +1520,10 @@ int VideoStore::write_packet(AVPacket *pkt, AVStream *stream) {
14871520 if (pkt->dts > pkt->pts ) pkt->pts = pkt->dts ; // Do it here to avoid warning below
14881521 } else if (pkt->dts == last_dts[stream->index ]) {
14891522 // Commonly seen
1490- Debug (1 , " non increasing dts, fixing. our dts %" PRId64 " stream %d last_dts %" PRId64 " stream %d. reorder_queue_size=%zu" ,
1491- pkt->dts , stream->index , last_dts[stream->index ], stream->index , reorder_queue_size);
1523+ Debug (1 , " non increasing dts, fixing. our dts %" PRId64 " stream %d last_dts %" PRId64 " last duration % " PRId64 " stream %d. reorder_queue_size=%zu" ,
1524+ pkt->dts , stream->index , last_dts[stream->index ], last_duration[stream-> index ], stream->index , reorder_queue_size);
14921525 // dts MUST monotonically increase, so add 1 which should be a small enough time difference to not matter.
1493- pkt->dts = last_dts[stream->index ]+last_duration[stream->index ];
1526+ pkt->dts = last_dts[stream->index ]+last_duration[stream->index ]- 1 ;
14941527 if (pkt->dts > pkt->pts ) pkt->pts = pkt->dts ; // Do it here to avoid warning below
14951528 }
14961529 }
0 commit comments