Add support for the rocDecGetDecoderCaps API (#21)
* Add support for the rocDecGetDecoderCaps API * move the RocDecVcnCodecSpec class to a new header file
This commit is contained in:
@@ -145,6 +145,8 @@ typedef enum rocDecodeStatus_enum {
|
||||
//! This structure is used in rocDecGetDecoderCaps API
|
||||
/**************************************************************************************************************/
|
||||
typedef struct _RocdecDecodeCaps {
|
||||
uint8_t deviceid; /**< IN: the device id for which query the decode capability
|
||||
0 for the first device, 1 for the second device on the system, etc.*/
|
||||
rocDecVideoCodec eCodecType; /**< IN: rocDecVideoCodec_XXX */
|
||||
rocDecVideoChromaFormat eChromaFormat; /**< IN: rocDecVideoChromaFormat_XXX */
|
||||
uint32_t nBitDepthMinus8; /**< IN: The Value "BitDepth minus 8" */
|
||||
|
||||
@@ -33,7 +33,6 @@ THE SOFTWARE.
|
||||
#include "../api/rocdecode.h"
|
||||
#include <hip/hip_runtime.h>
|
||||
|
||||
|
||||
class RocDecoder {
|
||||
public:
|
||||
RocDecoder(int device_id = 0);
|
||||
@@ -47,10 +46,9 @@ public:
|
||||
private:
|
||||
rocDecStatus initHIP(int device_id);
|
||||
void initDRMnodes();
|
||||
|
||||
int num_devices_;
|
||||
int device_id_;
|
||||
hipDeviceProp_t hip_dev_prop_;
|
||||
hipStream_t hip_stream_;
|
||||
std::vector<std::string> drm_nodes_;
|
||||
};
|
||||
};
|
||||
@@ -0,0 +1,108 @@
|
||||
/*
|
||||
Copyright (c) 2023 - 2023 Advanced Micro Devices, Inc. All rights reserved.
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in
|
||||
all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
THE SOFTWARE.
|
||||
*/
|
||||
#pragma once
|
||||
|
||||
#include <vector>
|
||||
#include <string>
|
||||
#include <unordered_map>
|
||||
#include <mutex>
|
||||
#include "../commons.h"
|
||||
#include "../../api/rocdecode.h"
|
||||
|
||||
|
||||
// The CodecSpec struct contains information for an individual codec (e.g., rocDecVideoCodec_HEVC)
|
||||
struct CodecSpec {
|
||||
std::vector<rocDecVideoChromaFormat> chroma_format;
|
||||
std::vector<int> bitdepth_minus8;
|
||||
uint16_t output_format_mask;
|
||||
uint32_t max_width;
|
||||
uint32_t max_height;
|
||||
uint16_t min_width;
|
||||
uint16_t min_height;
|
||||
};
|
||||
|
||||
// The VcnCodecsSpec struct contains information for all supported codecs and number of vcn instances per device
|
||||
struct VcnCodecsSpec {
|
||||
std::unordered_map<rocDecVideoCodec, CodecSpec> codecs_spec;
|
||||
uint8_t num_decoders;
|
||||
};
|
||||
|
||||
// The RocDecVcnCodecSpec singleton class for providing access to the the vcn_spec_table
|
||||
class RocDecVcnCodecSpec {
|
||||
public:
|
||||
static RocDecVcnCodecSpec& GetInastance() {
|
||||
static RocDecVcnCodecSpec instance;
|
||||
return instance;
|
||||
}
|
||||
rocDecStatus GetDecoderCaps(std::string gcn_arch_name, RocdecDecodeCaps *pdc) {
|
||||
std::lock_guard<std::mutex> lock(mutex);
|
||||
auto it = vcn_spec_table.find(gcn_arch_name);
|
||||
if (it != vcn_spec_table.end()) {
|
||||
const VcnCodecsSpec& vcn_spec = it->second;
|
||||
auto it1 = vcn_spec.codecs_spec.find(pdc->eCodecType);
|
||||
if (it1 != vcn_spec.codecs_spec.end()) {
|
||||
const CodecSpec& codec_spec = it1->second;
|
||||
auto it_chroma_format = std::find(codec_spec.chroma_format.begin(), codec_spec.chroma_format.end(), pdc->eChromaFormat);
|
||||
auto it_bitdepth_minus8 = std::find(codec_spec.bitdepth_minus8.begin(), codec_spec.bitdepth_minus8.end(), pdc->nBitDepthMinus8);
|
||||
if (it_chroma_format != codec_spec.chroma_format.end() && it_bitdepth_minus8 != codec_spec.bitdepth_minus8.end()) {
|
||||
pdc->bIsSupported = 1;
|
||||
pdc->nNumDecoders = vcn_spec.num_decoders;
|
||||
pdc->nOutputFormatMask = codec_spec.output_format_mask;
|
||||
pdc->nMaxWidth = codec_spec.max_width;
|
||||
pdc->nMaxHeight = codec_spec.max_height;
|
||||
pdc->nMinWidth = codec_spec.min_width;
|
||||
pdc->nMinHeight = codec_spec.min_height;
|
||||
return ROCDEC_SUCCESS;
|
||||
} else {
|
||||
return ROCDEC_NOT_SUPPORTED;
|
||||
}
|
||||
} else {
|
||||
return ROCDEC_NOT_SUPPORTED;
|
||||
}
|
||||
} else {
|
||||
return ROCDEC_DEVICE_INVALID;
|
||||
}
|
||||
}
|
||||
private:
|
||||
std::unordered_map<std::string, VcnCodecsSpec> vcn_spec_table;
|
||||
std::mutex mutex;
|
||||
RocDecVcnCodecSpec() {
|
||||
//vcn lookup table format:
|
||||
//{"gcn_arch_name1",{{{codec1, {{chroma_format1_for_codec1, chroma_format2_for_codec1, ...}, {bit_depth1_minus8_for_codec1, bit_depth2_minus8_for_codec1, ...}, output_format_mask_for_codec1, max_width_for_codec1, max_height_for_codec1, min_width_for_codec1, min_height_for_codec1}},
|
||||
// {codec2, {{chroma_format1_for_codec2, chroma_format2_for_codec2, ...}, {bit_depth1_minus8_for_codec2, bit_depth2_minus8_for_codec2, ...}, output_format_mask_for_codec2, max_width_for_codec2, max_height_for_codec2, min_width_for_codec2, min_height_for_codec2}}}
|
||||
// , vcn_instances_for_gcn_arch_name1}},
|
||||
vcn_spec_table = {
|
||||
{"gfx803",{}},
|
||||
{"gfx900",{}},
|
||||
{"gfx906",{}},
|
||||
{"gfx908",{{{rocDecVideoCodec_HEVC, {{rocDecVideoChromaFormat_420}, {0, 2}, 3, 4096, 2176, 64, 64}}, {rocDecVideoCodec_H264, {{rocDecVideoChromaFormat_420}, {0}, 1, 4096, 2160, 64, 64}}}, 2}},
|
||||
{"gfx90a",{{{rocDecVideoCodec_HEVC, {{rocDecVideoChromaFormat_420}, {0, 2}, 3, 4096, 2176, 64, 64}}, {rocDecVideoCodec_H264, {{rocDecVideoChromaFormat_420}, {0}, 1, 4096, 2160, 64, 64}}}, 2}},
|
||||
{"gfx940",{{{rocDecVideoCodec_HEVC, {{rocDecVideoChromaFormat_420}, {0, 2}, 3, 7680, 4320, 64, 64}}, {rocDecVideoCodec_H264, {{rocDecVideoChromaFormat_420}, {0}, 1, 4096, 2176, 64, 64}}}, 3}},
|
||||
{"gfx941",{{{rocDecVideoCodec_HEVC, {{rocDecVideoChromaFormat_420}, {0, 2}, 3, 7680, 4320, 64, 64}}, {rocDecVideoCodec_H264, {{rocDecVideoChromaFormat_420}, {0}, 1, 4096, 2176, 64, 64}}}, 4}},
|
||||
{"gfx1030",{{{rocDecVideoCodec_HEVC, {{rocDecVideoChromaFormat_420}, {0, 2}, 3, 7680, 4320, 64, 64}}, {rocDecVideoCodec_H264, {{rocDecVideoChromaFormat_420}, {0}, 1, 4096, 2176, 64, 64}}}, 2}},
|
||||
{"gfx1031",{{{rocDecVideoCodec_HEVC, {{rocDecVideoChromaFormat_420}, {0, 2}, 3, 7680, 4320, 64, 64}}, {rocDecVideoCodec_H264, {{rocDecVideoChromaFormat_420}, {0}, 1, 4096, 2176, 64, 64}}}, 2}},
|
||||
{"gfx1032",{{{rocDecVideoCodec_HEVC, {{rocDecVideoChromaFormat_420}, {0, 2}, 3, 7680, 4320, 64, 64}}, {rocDecVideoCodec_H264, {{rocDecVideoChromaFormat_420}, {0}, 1, 4096, 2176, 64, 64}}}, 2}},};
|
||||
}
|
||||
RocDecVcnCodecSpec(const RocDecVcnCodecSpec&) = delete;
|
||||
RocDecVcnCodecSpec& operator = (const RocDecVcnCodecSpec) = delete;
|
||||
~RocDecVcnCodecSpec() = default;
|
||||
};
|
||||
@@ -21,8 +21,10 @@ THE SOFTWARE.
|
||||
*/
|
||||
#include "dec_handle.h"
|
||||
#include "rocdecode.h"
|
||||
#include "roc_decoder_caps.h"
|
||||
#include "../commons.h"
|
||||
|
||||
|
||||
/*****************************************************************************************************/
|
||||
//! \fn rocDecStatus ROCDECAPI rocDecCreateDecoder(rocDecDecoderHandle *phDecoder, RocdecDecoderCreateInfo *pdci)
|
||||
//! Create the decoder object based on pdci. A handle to the created decoder is returned
|
||||
@@ -60,7 +62,33 @@ rocDecDestroyDecoder(rocDecDecoderHandle hDecoder) {
|
||||
/**********************************************************************************************************************/
|
||||
rocDecStatus ROCDECAPI
|
||||
rocDecGetDecoderCaps(RocdecDecodeCaps *pdc) {
|
||||
return ROCDEC_NOT_IMPLEMENTED;
|
||||
if (pdc == nullptr) {
|
||||
return ROCDEC_INVALID_PARAMETER;
|
||||
}
|
||||
hipError_t hip_status = hipSuccess;
|
||||
int num_devices = 0;
|
||||
hipDeviceProp_t hip_dev_prop;
|
||||
hip_status = hipGetDeviceCount(&num_devices);
|
||||
if (hip_status != hipSuccess) {
|
||||
ERR("ERROR: hipGetDeviceCount failed!" + TOSTR(hip_status));
|
||||
return ROCDEC_DEVICE_INVALID;
|
||||
}
|
||||
if (num_devices < 1) {
|
||||
ERR("ERROR: didn't find any GPU!");
|
||||
return ROCDEC_DEVICE_INVALID;
|
||||
}
|
||||
if (pdc->deviceid >= num_devices) {
|
||||
ERR("ERROR: the requested device_id is not found! ");
|
||||
return ROCDEC_DEVICE_INVALID;
|
||||
}
|
||||
hip_status = hipGetDeviceProperties(&hip_dev_prop, pdc->deviceid);
|
||||
if (hip_status != hipSuccess) {
|
||||
ERR("ERROR: hipGetDeviceProperties for device (" +TOSTR(pdc->deviceid) + " ) failed! (" + TOSTR(hip_status) + ")" );
|
||||
return ROCDEC_DEVICE_INVALID;
|
||||
}
|
||||
|
||||
RocDecVcnCodecSpec& vcn_codec_spec = RocDecVcnCodecSpec::GetInastance();
|
||||
return vcn_codec_spec.GetDecoderCaps(hip_dev_prop.gcnArchName, pdc);
|
||||
}
|
||||
|
||||
/*****************************************************************************************************/
|
||||
|
||||
Reference in New Issue
Block a user