Skip to content

Commit 66aba49

Browse files
author
James Bowley
committed
Add missing codecs to cudacodec which uses Nvidia Video Codec SDK including checks to ensure codec used in input video file is supported on the current device.
Re-enable cudacodec performance test.
1 parent 74ea5de commit 66aba49

File tree

5 files changed

+54
-17
lines changed

5 files changed

+54
-17
lines changed

modules/cudacodec/include/opencv2/cudacodec.hpp

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -250,6 +250,9 @@ enum Codec
250250
JPEG,
251251
H264_SVC,
252252
H264_MVC,
253+
HEVC,
254+
VP8,
255+
VP9,
253256

254257
Uncompressed_YUV420 = (('I'<<24)|('Y'<<16)|('U'<<8)|('V')), //!< Y,U,V (4:2:0)
255258
Uncompressed_YV12 = (('Y'<<24)|('V'<<16)|('1'<<8)|('2')), //!< Y,V,U (4:2:0)
@@ -274,6 +277,7 @@ struct FormatInfo
274277
{
275278
Codec codec;
276279
ChromaFormat chromaFormat;
280+
int nBitDepthMinus8;
277281
int width;
278282
int height;
279283
};

modules/cudacodec/perf/perf_video.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -51,7 +51,7 @@ DEF_PARAM_TEST_1(FileName, string);
5151
//////////////////////////////////////////////////////
5252
// VideoReader
5353

54-
#if defined(HAVE_NVCUVID) && defined(HAVE_VIDEO_INPUT)
54+
#if defined(HAVE_NVCUVID)
5555

5656
PERF_TEST_P(FileName, VideoReader, Values("gpu/video/768x576.avi", "gpu/video/1920x1080.avi"))
5757
{

modules/cudacodec/src/cuvid_video_source.cpp

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -70,6 +70,7 @@ cv::cudacodec::detail::CuvidVideoSource::CuvidVideoSource(const String& fname)
7070

7171
format_.codec = static_cast<Codec>(vidfmt.codec);
7272
format_.chromaFormat = static_cast<ChromaFormat>(vidfmt.chroma_format);
73+
format_.nBitDepthMinus8 = vidfmt.bit_depth_luma_minus8;
7374
format_.width = vidfmt.coded_width;
7475
format_.height = vidfmt.coded_height;
7576
}

modules/cudacodec/src/ffmpeg_video_source.cpp

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -111,6 +111,7 @@ cv::cudacodec::detail::FFmpegVideoSource::FFmpegVideoSource(const String& fname)
111111

112112
format_.codec = static_cast<Codec>(codec);
113113
format_.chromaFormat = static_cast<ChromaFormat>(chroma_format);
114+
format_.nBitDepthMinus8 = -1;
114115
format_.width = width;
115116
format_.height = height;
116117
}

modules/cudacodec/src/video_decoder.cpp

Lines changed: 47 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -57,22 +57,53 @@ void cv::cudacodec::detail::VideoDecoder::create(const FormatInfo& videoFormat)
5757
cudaVideoCreate_PreferCUVID;
5858

5959
// Validate video format. These are the currently supported formats via NVCUVID
60-
CV_Assert(cudaVideoCodec_MPEG1 == _codec ||
61-
cudaVideoCodec_MPEG2 == _codec ||
62-
cudaVideoCodec_MPEG4 == _codec ||
63-
cudaVideoCodec_VC1 == _codec ||
64-
cudaVideoCodec_H264 == _codec ||
65-
cudaVideoCodec_JPEG == _codec ||
66-
cudaVideoCodec_YUV420== _codec ||
67-
cudaVideoCodec_YV12 == _codec ||
68-
cudaVideoCodec_NV12 == _codec ||
69-
cudaVideoCodec_YUYV == _codec ||
70-
cudaVideoCodec_UYVY == _codec );
71-
72-
CV_Assert(cudaVideoChromaFormat_Monochrome == _chromaFormat ||
73-
cudaVideoChromaFormat_420 == _chromaFormat ||
74-
cudaVideoChromaFormat_422 == _chromaFormat ||
75-
cudaVideoChromaFormat_444 == _chromaFormat);
60+
bool codecSupported = cudaVideoCodec_MPEG1 == _codec ||
61+
cudaVideoCodec_MPEG2 == _codec ||
62+
cudaVideoCodec_MPEG4 == _codec ||
63+
cudaVideoCodec_VC1 == _codec ||
64+
cudaVideoCodec_H264 == _codec ||
65+
cudaVideoCodec_JPEG == _codec ||
66+
cudaVideoCodec_H264_SVC == _codec ||
67+
cudaVideoCodec_H264_MVC == _codec ||
68+
cudaVideoCodec_YV12 == _codec ||
69+
cudaVideoCodec_NV12 == _codec ||
70+
cudaVideoCodec_YUYV == _codec ||
71+
cudaVideoCodec_UYVY == _codec;
72+
73+
#if defined (HAVE_CUDA)
74+
#if (CUDART_VERSION >= 6500)
75+
codecSupported |= cudaVideoCodec_HEVC == _codec;
76+
#endif
77+
#if ((CUDART_VERSION == 7500) || (CUDART_VERSION >= 9000))
78+
codecSupported |= cudaVideoCodec_VP8 == _codec ||
79+
cudaVideoCodec_VP9 == _codec ||
80+
cudaVideoCodec_YUV420 == _codec;
81+
#endif
82+
#endif
83+
84+
CV_Assert(codecSupported);
85+
CV_Assert( cudaVideoChromaFormat_Monochrome == _chromaFormat ||
86+
cudaVideoChromaFormat_420 == _chromaFormat ||
87+
cudaVideoChromaFormat_422 == _chromaFormat ||
88+
cudaVideoChromaFormat_444 == _chromaFormat);
89+
90+
#if (CUDART_VERSION >= 9000)
91+
// Check video format is supported by GPU's hardware video decoder
92+
if (videoFormat.nBitDepthMinus8 != -1) { // info not available call to create CuvidVideoSource() failed
93+
CUVIDDECODECAPS decodeCaps = {};
94+
decodeCaps.eCodecType = _codec;
95+
decodeCaps.eChromaFormat = _chromaFormat;
96+
decodeCaps.nBitDepthMinus8 = videoFormat.nBitDepthMinus8;
97+
cuSafeCall(cuvidGetDecoderCaps(&decodeCaps));
98+
if (!decodeCaps.bIsSupported)
99+
CV_Error(Error::StsUnsupportedFormat, "Video source is not supported by hardware video decoder");
100+
101+
CV_Assert(videoFormat.width >= decodeCaps.nMinWidth &&
102+
videoFormat.height >= decodeCaps.nMinHeight &&
103+
videoFormat.width <= decodeCaps.nMaxWidth &&
104+
videoFormat.height <= decodeCaps.nMaxHeight);
105+
}
106+
#endif
76107

77108
// Fill the decoder-create-info struct from the given video-format struct.
78109
std::memset(&createInfo_, 0, sizeof(CUVIDDECODECREATEINFO));

0 commit comments

Comments
 (0)