early-access version 2323

This commit is contained in:
pineappleEA
2021-12-18 08:41:22 +01:00
parent 994096ad3a
commit f244f6654f
31 changed files with 41800 additions and 121887 deletions

View File

@@ -43,7 +43,10 @@ def enquote(s):
"""Return string argument with surrounding quotes,
for serialization into Python code."""
if s:
return "'{}'".format(s)
if isinstance(s, str):
return "'{}'".format(s)
else:
return s
return None
@@ -119,8 +122,11 @@ class GeneratorOptions:
removeExtensions=None,
emitExtensions=None,
emitSpirv=None,
emitFormats=None,
reparentEnums=True,
sortProcedure=regSortFeatures):
sortProcedure=regSortFeatures,
requireCommandAliases=False,
):
"""Constructor.
Arguments:
@@ -152,6 +158,8 @@ class GeneratorOptions:
to None.
- emitSpirv - regex matching names of extensions and capabilities
to actually emit interfaces for.
- emitFormats - regex matching names of formats to actually emit
interfaces for.
- reparentEnums - move <enum> elements which extend an enumerated
type from <feature> or <extension> elements to the target <enums>
element. This is required for almost all purposes, but the
@@ -217,6 +225,10 @@ class GeneratorOptions:
"""regex matching names of extensions and capabilities
to actually emit interfaces for."""
self.emitFormats = self.emptyRegex(emitFormats)
"""regex matching names of formats
to actually emit interfaces for."""
self.reparentEnums = reparentEnums
"""boolean specifying whether to remove <enum> elements from
<feature> or <extension> when extending an <enums> type."""
@@ -230,6 +242,10 @@ class GeneratorOptions:
self.codeGenerator = False
"""True if this generator makes compilable code"""
self.requireCommandAliases = requireCommandAliases
"""True if alias= attributes of <command> tags are transitively
required."""
def emptyRegex(self, pat):
"""Substitute a regular expression which matches no version
or extension names for None or the empty string."""
@@ -257,6 +273,17 @@ class OutputGenerator:
'basetype': 'basetypes',
}
def breakName(self, name, msg):
"""Break into debugger if this is a special name"""
# List of string names to break on
bad = (
)
if name in bad and True:
print('breakName {}: {}'.format(name, msg))
pdb.set_trace()
def __init__(self, errFile=sys.stderr, warnFile=sys.stderr, diagFile=sys.stdout):
"""Constructor
@@ -337,7 +364,7 @@ class OutputGenerator:
# print('About to translate value =', value, 'type =', type(value))
if needsNum:
numVal = int(value, 0)
# If there's a non-integer, numeric 'type' attribute (e.g. 'u' or
# If there is a non-integer, numeric 'type' attribute (e.g. 'u' or
# 'ull'), append it to the string value.
# t = enuminfo.elem.get('type')
# if t is not None and t != '' and t != 'i' and t != 's':
@@ -418,7 +445,7 @@ class OutputGenerator:
+ ') found with different values:' + strVal
+ ' and ' + strVal2)
# Don't add the duplicate to the returned list
# Do not add the duplicate to the returned list
continue
elif numVal in valueMap:
# Duplicate value found (such as an alias); report it, but
@@ -519,7 +546,7 @@ class OutputGenerator:
# Accumulate non-numeric enumerant values separately and append
# them following the numeric values, to allow for aliases.
# NOTE: this doesn't do a topological sort yet, so aliases of
# NOTE: this does not do a topological sort yet, so aliases of
# aliases can still get in the wrong order.
aliasText = ''
@@ -553,7 +580,7 @@ class OutputGenerator:
# Work around this by chasing the aliases to get the actual value.
while numVal is None:
alias = self.registry.tree.find("enums/enum[@name='" + strVal + "']")
(numVal, strVal) = self.enumToValue(alias, True)
(numVal, strVal) = self.enumToValue(alias, True, bitwidth, True)
decl += "static const {} {} = {};\n".format(flagTypeName, name, strVal)
if numVal is not None:
@@ -612,7 +639,7 @@ class OutputGenerator:
# Accumulate non-numeric enumerant values separately and append
# them following the numeric values, to allow for aliases.
# NOTE: this doesn't do a topological sort yet, so aliases of
# NOTE: this does not do a topological sort yet, so aliases of
# aliases can still get in the wrong order.
aliasText = []
@@ -651,7 +678,7 @@ class OutputGenerator:
self.logMsg('error', 'Allowable range for C enum types is [', minValidValue, ',', maxValidValue, '], but', name, 'has a value outside of this (', strVal, ')\n')
exit(1)
# Don't track min/max for non-numbers (numVal is None)
# Do not track min/max for non-numbers (numVal is None)
if isEnum and numVal is not None and elem.get('extends') is None:
if minName is None:
minName = maxName = name
@@ -674,7 +701,7 @@ class OutputGenerator:
" {}_RANGE_SIZE{} = ({} - {} + 1),".format(expandPrefix, expandSuffix, maxName, minName)))
# Generate a range-padding value to ensure the enum is 32 bits, but
# only in code generators, so it doesn't appear in documentation
# only in code generators, so it does not appear in documentation
if (self.genOpts.codeGenerator or
self.conventions.generate_max_enum_in_docs):
body.append(" {}_MAX_ENUM{} = 0x7FFFFFFF".format(
@@ -747,7 +774,7 @@ class OutputGenerator:
def beginFile(self, genOpts):
"""Start a new interface file
- genOpts - GeneratorOptions controlling what's generated and how"""
- genOpts - GeneratorOptions controlling what is generated and how"""
self.genOpts = genOpts
self.should_insert_may_alias_macro = \
self.genOpts.conventions.should_insert_may_alias_macro(self.genOpts)
@@ -778,7 +805,6 @@ class OutputGenerator:
self.warnFile.flush()
if self.diagFile:
self.diagFile.flush()
self.outFile.flush()
if self.outFile != sys.stdout and self.outFile != sys.stderr:
self.outFile.close()
@@ -800,7 +826,7 @@ class OutputGenerator:
- emit - actually write to the header only when True"""
self.emit = emit
self.featureName = interface.get('name')
# If there's an additional 'protect' attribute in the feature, save it
# If there is an additional 'protect' attribute in the feature, save it
self.featureExtraProtect = interface.get('protect')
def endFeature(self):
@@ -812,7 +838,7 @@ class OutputGenerator:
def genRequirements(self, name, mustBeFound = True):
"""Generate text showing what core versions and extensions introduce
an API. This exists in the base Generator class because it's used by
an API. This exists in the base Generator class because it is used by
the shared enumerant-generating interfaces (buildEnumCDecl, etc.).
Here it returns an empty string for most generators, but can be
overridden by e.g. DocGenerator.
@@ -825,7 +851,7 @@ class OutputGenerator:
return ''
def validateFeature(self, featureType, featureName):
"""Validate we're generating something only inside a `<feature>` tag"""
"""Validate we are generating something only inside a `<feature>` tag"""
if self.featureName is None:
raise UserWarning('Attempt to generate', featureType,
featureName, 'when not in feature')
@@ -887,6 +913,14 @@ class OutputGenerator:
Extend to generate as desired in your derived class."""
return
def genFormat(self, format, formatinfo, alias):
"""Generate interface for a format element.
- formatinfo - FormatInfo
Extend to generate as desired in your derived class."""
return
def makeProtoName(self, name, tail):
"""Turn a `<proto>` `<name>` into C-language prototype
and typedef declarations for that name.
@@ -939,6 +973,9 @@ class OutputGenerator:
# Clear prefix for subsequent iterations
prefix = ''
paramdecl = paramdecl + prefix
if aligncol == 0:
# Squeeze out multiple spaces other than the indentation
paramdecl = indent + ' '.join(paramdecl.split())
@@ -1013,7 +1050,7 @@ class OutputGenerator:
return None
def isStructAlwaysValid(self, structname):
"""Try to do check if a structure is always considered valid (i.e. there's no rules to its acceptance)."""
"""Try to do check if a structure is always considered valid (i.e. there is no rules to its acceptance)."""
# A conventions object is required for this call.
if not self.conventions:
raise RuntimeError("To use isStructAlwaysValid, be sure your options include a Conventions object.")
@@ -1109,7 +1146,7 @@ class OutputGenerator:
# Leading text
pdecl += noneStr(proto.text)
tdecl += noneStr(proto.text)
# For each child element, if it's a <name> wrap in appropriate
# For each child element, if it is a <name> wrap in appropriate
# declaration. Otherwise append its contents and tail contents.
for elem in proto:
text = noneStr(elem.text)