Files
external_libcamera/utils/codegen/gen-formats.py
Barnabás Pőcze b9fd53fbef treewide: Use argparse.FileType in more places
Convert some scripts to use `argparse.FileType` where the change is relatively
easily doable. This allows better error messages as e.g. missing input files
will be detected during argument parsing. And it also makes writing to stdout
in absence of an explicit argument simpler.

Signed-off-by: Barnabás Pőcze <barnabas.pocze@ideasonboard.com>
Reviewed-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
2025-11-17 09:19:36 +01:00

108 lines
3.1 KiB
Python
Executable File

#!/usr/bin/env python3
# SPDX-License-Identifier: GPL-2.0-or-later
# Copyright (C) 2020, Google Inc.
#
# Author: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
#
# Generate formats definitions from YAML
import argparse
import jinja2
import re
import string
import sys
import yaml
class DRMFourCC(object):
format_regex = re.compile(r"#define (DRM_FORMAT_[A-Z0-9_]+)[ \t]+fourcc_code\(('.', '.', '.', '.')\)")
mod_vendor_regex = re.compile(r"#define DRM_FORMAT_MOD_VENDOR_([A-Z0-9_]+)[ \t]+([0-9a-fA-Fx]+)")
mod_regex = re.compile(r"#define ([A-Za-z0-9_]+)[ \t]+fourcc_mod_code\(([A-Z0-9_]+), ([0-9a-fA-Fx]+)\)")
def __init__(self, file):
self.formats = {}
self.vendors = {}
self.mods = {}
for line in file:
match = DRMFourCC.format_regex.match(line)
if match:
format, fourcc = match.groups()
self.formats[format] = fourcc
continue
match = DRMFourCC.mod_vendor_regex.match(line)
if match:
vendor, value = match.groups()
self.vendors[vendor] = int(value, 0)
continue
match = DRMFourCC.mod_regex.match(line)
if match:
mod, vendor, value = match.groups()
self.mods[mod] = (vendor, int(value, 0))
continue
def fourcc(self, name):
return self.formats[name]
def mod(self, name):
vendor, value = self.mods[name]
return self.vendors[vendor], value
def generate_formats(formats, drm_fourcc):
fmts = []
for format in formats:
name, format = format.popitem()
fourcc = drm_fourcc.fourcc(format['fourcc'])
data = {
'name': name,
'fourcc': fourcc,
'mod': '0, 0',
'big_endian': format.get('big_endian'),
}
mod = format.get('mod')
if mod:
data['mod'] = '%u, %u' % drm_fourcc.mod(mod)
fmts.append(data)
return fmts
def main(argv):
# Parse command line arguments
parser = argparse.ArgumentParser()
parser.add_argument('-o', dest='output', metavar='file', default=sys.stdout,
type=argparse.FileType('w', encoding='utf-8'),
help='Output file name. Defaults to standard output if not specified.')
parser.add_argument('input', type=argparse.FileType('rb'),
help='Input file name.')
parser.add_argument('template', type=argparse.FileType('r', encoding='utf-8'),
help='Template file name.')
parser.add_argument('drm_fourcc', type=argparse.FileType('r', encoding='utf-8'),
help='Path to drm_fourcc.h.')
args = parser.parse_args(argv[1:])
formats = yaml.safe_load(args.input)['formats']
drm_fourcc = DRMFourCC(args.drm_fourcc)
env = jinja2.Environment()
template = env.from_string(args.template.read())
string = template.render({
'formats': generate_formats(formats, drm_fourcc),
})
args.output.write(string)
return 0
if __name__ == '__main__':
sys.exit(main(sys.argv))