mirror of
https://github.com/kkroening/ffmpeg-python.git
synced 2025-08-07 18:39:47 +08:00
Build: Include coders specific to hwaccell APIs
This commit is contained in:
parent
ca427cb904
commit
130457ffe1
@ -40,6 +40,8 @@ CODEC_DESCRIPTION_RE = re.compile(
|
||||
CODEC_CODERS_RE = re.compile(
|
||||
r' \((?P<type>(de|en)coders): (?P<coders>[^)]+) \)')
|
||||
|
||||
HWACCEL_SYNONYMS = dict(cuvid=['nvenc', 'nvdec', 'cuda'])
|
||||
|
||||
FILTER_RE = re.compile(
|
||||
r'^ (?P<timeline>[T.])(?P<slice>[S.])(?P<command>[C.]) '
|
||||
r'(?P<name>[^ ]+) +(?P<io>[^ ]+) +(?P<description>.+)$',
|
||||
@ -248,22 +250,53 @@ def get_hw_devices(cmd='ffmpeg'):
|
||||
|
||||
def get_hwaccels(cmd='ffmpeg'):
|
||||
"""
|
||||
Extract the hwaccels of the ffmpeg build.
|
||||
Extract the hwaccels of the ffmpeg build, including specific codecs.
|
||||
|
||||
Return all the hardware acceleration APIs supported by this build
|
||||
including all the codecs that are specific to the API.
|
||||
"""
|
||||
data = dict(codecs=get_codecs(cmd=cmd), hwaccels=[])
|
||||
|
||||
stdout = _run([cmd, '-hwaccels'])
|
||||
return stdout.split('\n')[1:-2]
|
||||
hwaccel_names = stdout.split('\n')[1:-2]
|
||||
|
||||
for hwaccel_name in hwaccel_names:
|
||||
hwaccel = dict(name=hwaccel_name)
|
||||
data['hwaccels'].append(hwaccel)
|
||||
hwaccel['codecs'] = hwaccel_codecs = {}
|
||||
for codec_name, codec in data['codecs'].items():
|
||||
hwaccel_codec = {}
|
||||
for coders_key in ('decoders', 'encoders'):
|
||||
matching_coders = []
|
||||
for coder in codec.get(coders_key, []):
|
||||
for synonym in (
|
||||
[hwaccel_name] +
|
||||
HWACCEL_SYNONYMS.get(hwaccel_name, [])):
|
||||
if (
|
||||
coder == synonym or
|
||||
'_' + synonym in coder or
|
||||
synonym + '_' in coder):
|
||||
matching_coders.append(coder)
|
||||
break
|
||||
if matching_coders:
|
||||
hwaccel_codec[coders_key] = matching_coders
|
||||
if hwaccel_codec:
|
||||
hwaccel_codecs[codec_name] = hwaccel_codec
|
||||
|
||||
return data
|
||||
|
||||
|
||||
def get_build_data(cmd='ffmpeg'):
|
||||
"""
|
||||
Extract details about the ffmpeg build.
|
||||
"""
|
||||
hwaccels_data = get_hwaccels(cmd=cmd)
|
||||
return dict(
|
||||
version=get_version(cmd=cmd),
|
||||
formats=get_formats(cmd=cmd),
|
||||
demuxers=get_demuxers(cmd=cmd),
|
||||
muxers=get_muxers(cmd=cmd),
|
||||
codecs=get_codecs(cmd=cmd),
|
||||
codecs=hwaccels_data['codecs'],
|
||||
bsfs=get_bsfs(cmd=cmd),
|
||||
protocols=get_protocols(cmd=cmd),
|
||||
filters=get_filters(cmd=cmd),
|
||||
@ -273,7 +306,7 @@ def get_build_data(cmd='ffmpeg'):
|
||||
colors=get_colors(cmd=cmd),
|
||||
devices=get_devices(cmd=cmd),
|
||||
hw_devices=get_hw_devices(cmd=cmd),
|
||||
hwaccels=get_hwaccels(cmd=cmd))
|
||||
hwaccels=hwaccels_data['hwaccels'])
|
||||
|
||||
__all__ = [
|
||||
'get_build_data',
|
||||
|
@ -43,10 +43,6 @@ HWACCELS_BY_PERFORMANCE = [
|
||||
'qsv', 'd3d11va', 'dxva2', 'vaapi', 'drm']
|
||||
# Loaded from JSON
|
||||
DATA = None
|
||||
# Some accelerated codecs use a different prefix than the base codec
|
||||
CODEC_SYNONYMS = {
|
||||
'mpeg1video': 'mpeg1',
|
||||
'mpeg2video': 'mpeg2'}
|
||||
|
||||
|
||||
def detect_gpu():
|
||||
@ -67,14 +63,15 @@ def detect_hwaccels(hwaccels=None, cmd='ffmpeg'):
|
||||
Extract details about the ffmpeg build.
|
||||
"""
|
||||
# Filter against what's available in the ffmpeg build
|
||||
build_hwaccels = ffmpeg.get_hwaccels(cmd=cmd)
|
||||
hwaccels_data = ffmpeg.get_hwaccels(cmd=cmd)
|
||||
if hwaccels is None:
|
||||
# Consider all the available hwaccels
|
||||
hwaccels = build_hwaccels
|
||||
hwaccels = hwaccels_data['hwaccels']
|
||||
else:
|
||||
# Support passing in a restricted set of hwaccels
|
||||
hwaccels = [
|
||||
hwaccel for hwaccel in hwaccels if hwaccel in build_hwaccels]
|
||||
hwaccel for hwaccel in hwaccels_data['hwaccels']
|
||||
if hwaccel['name'] in hwaccels]
|
||||
|
||||
# Filter against which APIs are available on this OS+GPU
|
||||
data = _get_data()
|
||||
@ -82,16 +79,18 @@ def detect_hwaccels(hwaccels=None, cmd='ffmpeg'):
|
||||
gpu = detect_gpu()
|
||||
api_avail = data['hwaccels']['api_avail'][plat_sys][
|
||||
gpu['vendor'].replace(' Corporation', '')]
|
||||
hwaccels = [hwaccel for hwaccel in hwaccels if hwaccel in api_avail]
|
||||
hwaccels = [
|
||||
hwaccel for hwaccel in hwaccels if hwaccel['name'] in api_avail]
|
||||
|
||||
hwaccels.sort(key=lambda hwaccel: (
|
||||
# Sort unranked hwaccels last, but in the order given by ffmpeg
|
||||
hwaccel not in HWACCELS_BY_PERFORMANCE,
|
||||
hwaccel['name'] in HWACCELS_BY_PERFORMANCE and 1 or 0,
|
||||
(
|
||||
# Sort ranked hwaccels per the constant
|
||||
hwaccel in HWACCELS_BY_PERFORMANCE and
|
||||
HWACCELS_BY_PERFORMANCE.index(hwaccel))))
|
||||
return hwaccels
|
||||
hwaccel['name'] in HWACCELS_BY_PERFORMANCE and
|
||||
HWACCELS_BY_PERFORMANCE.index(hwaccel['name']))))
|
||||
hwaccels_data['hwaccels'] = hwaccels
|
||||
return hwaccels_data
|
||||
|
||||
|
||||
def detect_coder(
|
||||
|
@ -727,7 +727,16 @@ def test__build_data():
|
||||
|
||||
assert isinstance(data['version'], str)
|
||||
|
||||
for fields_key in {'formats', 'demuxers', 'muxers', 'codecs', 'filters'}:
|
||||
assert isinstance(data['codecs'], dict)
|
||||
for codec, coders in data['codecs'].items():
|
||||
assert isinstance(codec, str)
|
||||
assert isinstance(coders, dict)
|
||||
assert isinstance(data['hwaccels'], list)
|
||||
for hwaccel in data['hwaccels']:
|
||||
assert isinstance(hwaccel, dict)
|
||||
assert 'name' in hwaccel
|
||||
|
||||
for fields_key in {'formats', 'demuxers', 'muxers', 'filters'}:
|
||||
assert isinstance(data[fields_key], dict)
|
||||
|
||||
list_keys = {'bsfs'}
|
||||
@ -741,10 +750,13 @@ def test__build_data():
|
||||
|
||||
|
||||
def test__detect():
|
||||
for hwaccels in [
|
||||
for hwaccels_data in [
|
||||
ffmpeg.detect_hwaccels(),
|
||||
ffmpeg.detect_hwaccels(['foohwaccel'])]:
|
||||
assert isinstance(hwaccels, list)
|
||||
assert isinstance(hwaccels_data['hwaccels'], list)
|
||||
for hwaccel in hwaccels_data['hwaccels']:
|
||||
assert isinstance(hwaccel, dict)
|
||||
assert 'name' in hwaccel
|
||||
|
||||
for codecs in [
|
||||
ffmpeg.detect_codecs('h264', 'h264'),
|
||||
|
Loading…
x
Reference in New Issue
Block a user