parameters: (enum_case, capability_mapping, for_op, for_cap)
return_statement: return '{}{}{}'.format(implies, '\n  ' if implies and avail else '', avail)
docstring: Returns the availability specification string for the given enum case.
  
    Arguments:
      - enum_case: the enum case to generate availability spec for. It may contain
        'version', 'lastVersion', 'extensions', or 'capabilities'.
      - capability_mapping: mapping from duplicated capability symbols to the
        canonicalized symbol chosen for SPIRVBase.td.
      - for_op: bool value indicating whether this is the availability spec for an
        op itself.
      - for_cap: bool value indicating whether this is the availability spec for
        capabilities themselves.
  
    Returns:
      - A `let availability = [...];` string if with availability spec or
        empty string if without availability spec
docstring_summary: Returns the availability specification string for the given enum case.
docstring_tokens: Returns the availability specification string for the given enum case .
function: def get_availability_spec(enum_case, capability_mapping, for_op, for_cap):
    """Returns the availability specification string for the given enum case.
  
    Arguments:
      - enum_case: the enum case to generate availability spec for. It may contain
        'version', 'lastVersion', 'extensions', or 'capabilities'.
      - capability_mapping: mapping from duplicated capability symbols to the
        canonicalized symbol chosen for SPIRVBase.td.
      - for_op: bool value indicating whether this is the availability spec for an
        op itself.
      - for_cap: bool value indicating whether this is the availability spec for
        capabilities themselves.
  
    Returns:
      - A `let availability = [...];` string if with availability spec or
        empty string if without availability spec
    """
    assert not (for_op and for_cap), 'cannot set both for_op and for_cap'
  
    DEFAULT_MIN_VERSION = 'MinVersion<SPV_V_1_0>'
    DEFAULT_MAX_VERSION = 'MaxVersion<SPV_V_1_5>'
    DEFAULT_CAP = 'Capability<[]>'
    DEFAULT_EXT = 'Extension<[]>'
  
    min_version = enum_case.get('version', '')
    if min_version == 'None':
      min_version = ''
    elif min_version:
      min_version = 'MinVersion<SPV_V_{}>'.format(min_version.replace('.', '_'))
    # TODO: delete this once ODS can support dialect-specific content
    # and we can use omission to mean no requirements.
    if for_op and not min_version:
      min_version = DEFAULT_MIN_VERSION
  
    max_version = enum_case.get('lastVersion', '')
    if max_version:
      max_version = 'MaxVersion<SPV_V_{}>'.format(max_version.replace('.', '_'))
    # TODO: delete this once ODS can support dialect-specific content
    # and we can use omission to mean no requirements.
    if for_op and not max_version:
      max_version = DEFAULT_MAX_VERSION
  
    exts = enum_case.get('extensions', [])
    if exts:
      exts = 'Extension<[{}]>'.format(', '.join(sorted(set(exts))))
      # We need to strip the minimal version requirement if this symbol is
      # available via an extension, which means *any* SPIR-V version can support
      # it as long as the extension is provided. The grammar's 'version' field
      # under such case should be interpreted as this symbol is introduced as
      # a core symbol since the given version, rather than a minimal version
      # requirement.
      min_version = DEFAULT_MIN_VERSION if for_op else ''
    # TODO: delete this once ODS can support dialect-specific content
    # and we can use omission to mean no requirements.
    if for_op and not exts:
      exts = DEFAULT_EXT
  
    caps = enum_case.get('capabilities', [])
    implies = ''
    if caps:
      canonicalized_caps = []
      for c in caps:
        if c in capability_mapping:
          canonicalized_caps.append(capability_mapping[c])
        else:
          canonicalized_caps.append(c)
      prefixed_caps = [
          'SPV_C_{}'.format(c) for c in sorted(set(canonicalized_caps))
      ]
      if for_cap:
        # If this is generating the availability for capabilities, we need to
        # put the capability "requirements" in implies field because now
        # the "capabilities" field in the source grammar means so.
        caps = ''
        implies = 'list<I32EnumAttrCase> implies = [{}];'.format(
            ', '.join(prefixed_caps))
      else:
        caps = 'Capability<[{}]>'.format(', '.join(prefixed_caps))
        implies = ''
    # TODO: delete this once ODS can support dialect-specific content
    # and we can use omission to mean no requirements.
    if for_op and not caps:
      caps = DEFAULT_CAP
  
    avail = ''
    # Compose availability spec if any of the requirements is not empty.
    # For ops, because we have a default in SPV_Op class, omit if the spec
    # is the same.
    if (min_version or max_version or caps or exts) and not (
        for_op and min_version == DEFAULT_MIN_VERSION and
        max_version == DEFAULT_MAX_VERSION and caps == DEFAULT_CAP and
        exts == DEFAULT_EXT):
      joined_spec = ',\n    '.join(
          [e for e in [min_version, max_version, exts, caps] if e])
      avail = '{} availability = [\n    {}\n  ];'.format(
          'let' if for_op else 'list<Availability>', joined_spec)
  
    return '{}{}{}'.format(implies, '\n  ' if implies and avail else '', avail)
function_tokens: def get_availability_spec ( enum_case , capability_mapping , for_op , for_cap ) : assert not ( for_op and for_cap ) , 'cannot set both for_op and for_cap' DEFAULT_MIN_VERSION = 'MinVersion<SPV_V_1_0>' DEFAULT_MAX_VERSION = 'MaxVersion<SPV_V_1_5>' DEFAULT_CAP = 'Capability<[]>' DEFAULT_EXT = 'Extension<[]>' min_version = enum_case . get ( 'version' , '' ) if min_version == 'None' : min_version = '' elif min_version : min_version = 'MinVersion<SPV_V_{}>' . format ( min_version . replace ( '.' , '_' ) ) # TODO: delete this once ODS can support dialect-specific content # and we can use omission to mean no requirements. if for_op and not min_version : min_version = DEFAULT_MIN_VERSION max_version = enum_case . get ( 'lastVersion' , '' ) if max_version : max_version = 'MaxVersion<SPV_V_{}>' . format ( max_version . replace ( '.' , '_' ) ) # TODO: delete this once ODS can support dialect-specific content # and we can use omission to mean no requirements. if for_op and not max_version : max_version = DEFAULT_MAX_VERSION exts = enum_case . get ( 'extensions' , [ ] ) if exts : exts = 'Extension<[{}]>' . format ( ', ' . join ( sorted ( set ( exts ) ) ) ) # We need to strip the minimal version requirement if this symbol is # available via an extension, which means *any* SPIR-V version can support # it as long as the extension is provided. The grammar's 'version' field # under such case should be interpreted as this symbol is introduced as # a core symbol since the given version, rather than a minimal version # requirement. min_version = DEFAULT_MIN_VERSION if for_op else '' # TODO: delete this once ODS can support dialect-specific content # and we can use omission to mean no requirements. if for_op and not exts : exts = DEFAULT_EXT caps = enum_case . get ( 'capabilities' , [ ] ) implies = '' if caps : canonicalized_caps = [ ] for c in caps : if c in capability_mapping : canonicalized_caps . append ( capability_mapping [ c ] ) else : canonicalized_caps . append ( c ) prefixed_caps = [ 'SPV_C_{}' . format ( c ) for c in sorted ( set ( canonicalized_caps ) ) ] if for_cap : # If this is generating the availability for capabilities, we need to # put the capability "requirements" in implies field because now # the "capabilities" field in the source grammar means so. caps = '' implies = 'list<I32EnumAttrCase> implies = [{}];' . format ( ', ' . join ( prefixed_caps ) ) else : caps = 'Capability<[{}]>' . format ( ', ' . join ( prefixed_caps ) ) implies = '' # TODO: delete this once ODS can support dialect-specific content # and we can use omission to mean no requirements. if for_op and not caps : caps = DEFAULT_CAP avail = '' # Compose availability spec if any of the requirements is not empty. # For ops, because we have a default in SPV_Op class, omit if the spec # is the same. if ( min_version or max_version or caps or exts ) and not ( for_op and min_version == DEFAULT_MIN_VERSION and max_version == DEFAULT_MAX_VERSION and caps == DEFAULT_CAP and exts == DEFAULT_EXT ) : joined_spec = ',\n    ' . join ( [ e for e in [ min_version , max_version , exts , caps ] if e ] ) avail = '{} availability = [\n    {}\n  ];' . format ( 'let' if for_op else 'list<Availability>' , joined_spec ) return '{}{}{}' . format ( implies , '\n  ' if implies and avail else '' , avail )