#!/usr/bin/python3 -i # # Copyright (c) 2013-2019 The Khronos Group Inc. # # Licensed under the Apache License, Version 2.0 (the "License"); # you may not use this file except in compliance with the License. # You may obtain a copy of the License at # # http://www.apache.org/licenses/LICENSE-2.0 # # Unless required by applicable law or agreed to in writing, software # distributed under the License is distributed on an "AS IS" BASIS, # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. # See the License for the specific language governing permissions and # limitations under the License. import re from generator import OutputGenerator, write from jinja_helpers import JinjaTemplate, make_jinja_environment from spec_tools.util import getElemName, getElemType class CStruct: """Represents a OpenXR struct type""" def __init__(self, typeName, structTypeName, members, protect): self.typeName = typeName self.members = members self.structTypeName = structTypeName self.protect = protect class CBitmask: """Represents a OpenXR mask type""" def __init__(self, typeName, maskTuples): self.typeName = typeName self.maskTuples = maskTuples class CEnum: """Represents a OpenXR group enum type""" def __init__(self, typeName, typeNamePrefix, typeNameSuffix, enumTuples): self.typeName = typeName self.typeNamePrefix = typeNamePrefix self.typeNameSuffix = typeNameSuffix self.enumTuples = enumTuples class CReflectionOutputGenerator(OutputGenerator): """Generate specified API interfaces in a specific style, such as a C header""" def __init__(self, *args, **kwargs): super().__init__(*args, **kwargs) self.env = make_jinja_environment(file_with_templates_as_sibs=__file__) self.structs = [] self.enums = [] self.bitmasks = [] def beginFile(self, genOpts): OutputGenerator.beginFile(self, genOpts) self.template = JinjaTemplate(self.env, "template_{}".format(genOpts.filename)) def endFile(self): file_data = '' try: file_data += self.template.render( structs=self.structs, enums=self.enums, bitmasks=self.bitmasks) except TemplateSyntaxError as e: print("{}:{} error: {}".format(e.filename, e.lineno, e.message)) raise e write(file_data, file=self.outFile) # Finish processing in superclass OutputGenerator.endFile(self) def genType(self, typeinfo, name, alias): OutputGenerator.genType(self, typeinfo, name, alias) typeElem = typeinfo.elem category = typeElem.get('category') if category in ('struct', 'union'): # If the type is a struct type, generate it using the # special-purpose generator. self.genStruct(typeinfo, name, alias) def genStruct(self, typeinfo, typeName, alias): OutputGenerator.genStruct(self, typeinfo, typeName, alias) typeElem = typeinfo.elem if alias: return structTypeName = None members = [] for member in typeinfo.getMembers(): memberName = getElemName(member) memberType = getElemType(member) if self.conventions.is_structure_type_member(memberType, memberName): structTypeName = member.get("values") members.append(memberName) self.structs.append(CStruct(typeName, structTypeName, members, typeinfo.elem.get('protect'))) def genGroup(self, groupinfo, groupName, alias=None): OutputGenerator.genGroup(self, groupinfo, groupName, alias) if alias: return if getElemType(groupinfo.elem) == 'bitmask': bitmaskTypeName = getElemName(groupinfo.flagType.elem) bitmaskTuples = [] for elem in groupinfo.elem.findall('enum'): (numVal, strVal) = self.enumToValue(elem, True) bitmaskTuples.append((getElemName(elem), strVal)) self.bitmasks.append(CBitmask(bitmaskTypeName, bitmaskTuples)) else: groupElem = groupinfo.elem expandName = re.sub(r'([0-9a-z_])([A-Z0-9][^A-Z0-9]?)', r'\1_\2', groupName).upper() expandPrefix = expandName expandSuffix = '' expandSuffixMatch = re.search(r'[A-Z][A-Z]+$', groupName) if expandSuffixMatch: expandSuffix = '_' + expandSuffixMatch.group() # Strip off the suffix from the prefix expandPrefix = expandName.rsplit(expandSuffix, 1)[0] enumTuples = [] for elem in groupElem.findall('enum'): (numVal, strVal) = self.enumToValue(elem, True) enumTuples.append((getElemName(elem), strVal)) self.enums.append(CEnum(groupName, expandPrefix, expandSuffix, enumTuples))