1#!/usr/bin/python3 -i 2# 3# Copyright 2020-2023 The Khronos Group Inc. 4# 5# SPDX-License-Identifier: Apache-2.0 6 7# Description: 8# ----------- 9# This script generates a .hpp file that can be included in an application 10# to generate json data that can then be used to generate the pipeline cache. 11 12import os 13import re 14import xml.dom.minidom 15from generator import (GeneratorOptions, OutputGenerator, noneStr, 16 regSortFeatures, write) 17 18copyright = """ 19/* 20** Copyright (c) 2020 The Khronos Group Inc. 21** 22** SPDX-License-Identifier: Apache-2.0 23*/ 24""" 25 26 27predefinedCode = """ 28/********************************************************************************************/ 29/** This code is generated. To make changes, please modify the scripts or the relevant xml **/ 30/********************************************************************************************/ 31 32#pragma once 33 34#include <stdio.h> 35#include <vulkan/vulkan.h> 36 37const char* getJSONOutput(void); 38void resetJSONOutput(void); 39""" 40 41class JSONHeaderGeneratorOptions(GeneratorOptions): 42 """JSONHeaderGeneratorOptions - subclass of GeneratorOptions. 43 44 Adds options used by JSONHeaderOutputGenerator objects during C language header 45 generation.""" 46 47 def __init__(self, 48 prefixText="", 49 genFuncPointers=True, 50 protectFile=True, 51 protectFeature=True, 52 protectProto=None, 53 protectProtoStr=None, 54 apicall='', 55 apientry='', 56 apientryp='', 57 indentFuncProto=True, 58 indentFuncPointer=False, 59 alignFuncParam=0, 60 genEnumBeginEndRange=False, 61 genAliasMacro=False, 62 aliasMacro='', 63 **kwargs 64 ): 65 66 GeneratorOptions.__init__(self, **kwargs) 67 68 69class JSONHeaderOutputGenerator(OutputGenerator): 70 # This is an ordered list of sections in the header file. 71 TYPE_SECTIONS = ['basetype', 'handle', 'enum', 72 'group', 'bitmask', 'struct'] 73 ALL_SECTIONS = TYPE_SECTIONS 74 75 def __init__(self, *args, **kwargs): 76 super().__init__(*args, **kwargs) 77 # Internal state - accumulators for different inner block text 78 self.sections = {section: [] for section in self.ALL_SECTIONS} 79 self.feature_not_empty = False 80 self.may_alias = None 81 self.featureDict = {} 82 self.vkscFeatureList = [] 83 self.baseTypeList = ["int32_t", 84 "uint32_t", 85 "uint8_t", 86 "uint64_t", 87 "float", 88 "int", 89 "double", 90 "int64_t", 91 "uint16_t", 92 "char"] 93 94 95 def createvkscFeatureList(self): 96 for feature in self.registry.reg.findall('feature'): 97 if feature.get('api').find('vulkansc') != -1: 98 # Remove entries that are removed in features in VKSC profile. 99 requiredList = feature.findall("require") 100 101 for requiredItem in requiredList: 102 typeList = requiredItem.findall("type") 103 for typeName in typeList: 104 if typeName.get("name") != "": 105 self.featureDict[typeName.get("name")] = feature.get("name") 106 self.vkscFeatureList.append(typeName.get("name")) 107 108 removeItemList = feature.findall("remove") 109 for removeItem in removeItemList: 110 removeTypes = removeItem.findall("type") 111 for item in removeTypes: 112 if self.vkscFeatureList.count(item.get("name")) > 0: 113 self.vkscFeatureList.remove(item.get("name")) 114 115 allExtensions = self.registry.reg.findall('extensions') 116 for extensions in allExtensions: 117 extensionList = extensions.findall("extension") 118 for extension in extensionList: 119 if extension.get("supported").find("vulkansc") != -1: 120 requiredList = extension.findall("require") 121 for requiredItem in requiredList: 122 typeList = requiredItem.findall("type") 123 for typeName in typeList: 124 self.featureDict[typeName.get("name")] = extension.get("name") 125 self.vkscFeatureList.append(typeName.get("name")) 126 127 def printPrototypes(self): 128 code = "" 129 130 code += "/*************************************** Begin prototypes ***********************************/\n" 131 typesList = self.registry.reg.findall('types') 132 currentExtension = "VK_VERSION_1_0" 133 for types in typesList: 134 typeList = types.findall("type") 135 136 for type in typeList: 137 if type.get("name") != "": 138 cat = type.get("category") 139 name = type.get("name") 140 141 if cat in {"handle", "bitmask", "basetype", "enum", "struct"} and name in self.vkscFeatureList: 142 if name in self.featureDict and currentExtension != self.featureDict[name]: 143 if currentExtension != "VK_VERSION_1_0": 144 code += "#endif\n" 145 currentExtension = self.featureDict[name] 146 if self.featureDict[name] != "VK_VERSION_1_0": 147 code += "#ifdef %s\n" %(currentExtension) 148 code += "void print_%s(const %s* obj, const char* str, int commaNeeded);\n" %(name, name) 149 150 if currentExtension != "VK_VERSION_1_0": 151 code += "#endif\n" 152 code += "/*************************************** End prototypes ***********************************/\n\n" 153 154 return code 155 156 def beginFile(self, genOpts): 157 OutputGenerator.beginFile(self, genOpts) 158 159 self.createvkscFeatureList() 160 161 write(copyright, file=self.outFile) 162 write(predefinedCode, file=self.outFile) 163 164 write(self.printPrototypes(), file=self.outFile) 165 write("void dumpPNextChain(const void* pNext);\n", file=self.outFile) 166 167 def endFile(self): 168 OutputGenerator.endFile(self) 169 170 def beginFeature(self, interface, emit): 171 OutputGenerator.beginFeature(self, interface, emit) 172 self.sections = {section: [] for section in self.ALL_SECTIONS} 173 self.feature_not_empty = False 174 175 def endFeature(self): 176 if self.emit: 177 if self.feature_not_empty: 178 if self.genOpts.conventions.writeFeature(self.featureExtraProtect, self.genOpts.filename): 179 180 for section in self.TYPE_SECTIONS: 181 contents = self.sections[section] 182 if contents: 183 write('\n'.join(contents), file=self.outFile) 184 185 # Finish processing in superclass 186 OutputGenerator.endFeature(self) 187 188 def genType(self, typeinfo, name, alias): 189 OutputGenerator.genType(self, typeinfo, name, alias) 190 191 def genStruct(self, typeinfo, typeName, alias): 192 OutputGenerator.genStruct(self, typeinfo, typeName, alias) 193 194 def genGroup(self, groupinfo, groupName, alias=None): 195 OutputGenerator.genGroup(self, groupinfo, groupName, alias) 196 197