101e04c3fSmrgCOPYRIGHT = """\
201e04c3fSmrg/*
301e04c3fSmrg * Copyright 2017 Google
401e04c3fSmrg *
501e04c3fSmrg * Permission is hereby granted, free of charge, to any person obtaining a
601e04c3fSmrg * copy of this software and associated documentation files (the
701e04c3fSmrg * "Software"), to deal in the Software without restriction, including
801e04c3fSmrg * without limitation the rights to use, copy, modify, merge, publish,
901e04c3fSmrg * distribute, sub license, and/or sell copies of the Software, and to
1001e04c3fSmrg * permit persons to whom the Software is furnished to do so, subject to
1101e04c3fSmrg * the following conditions:
1201e04c3fSmrg *
1301e04c3fSmrg * The above copyright notice and this permission notice (including the
1401e04c3fSmrg * next paragraph) shall be included in all copies or substantial portions
1501e04c3fSmrg * of the Software.
1601e04c3fSmrg *
1701e04c3fSmrg * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
1801e04c3fSmrg * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
1901e04c3fSmrg * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT.
2001e04c3fSmrg * IN NO EVENT SHALL VMWARE AND/OR ITS SUPPLIERS BE LIABLE FOR
2101e04c3fSmrg * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
2201e04c3fSmrg * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
2301e04c3fSmrg * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
2401e04c3fSmrg */
2501e04c3fSmrg"""
2601e04c3fSmrg
2701e04c3fSmrg# stdlib
2801e04c3fSmrgimport argparse
2901e04c3fSmrgfrom sys import stdout
3001e04c3fSmrgfrom mako.template import Template
3101e04c3fSmrg
3201e04c3fSmrg# local
3301e04c3fSmrgimport format_parser
3401e04c3fSmrg
3501e04c3fSmrgdef parse_args():
3601e04c3fSmrg    p = argparse.ArgumentParser()
3701e04c3fSmrg    p.add_argument("csv")
3801e04c3fSmrg    p.add_argument("out")
3901e04c3fSmrg    return p.parse_args()
4001e04c3fSmrg
4101e04c3fSmrgdef get_unorm_to_srgb_map(formats):
4201e04c3fSmrg    names = set(fmt.name for fmt in formats)
4301e04c3fSmrg
4401e04c3fSmrg    for fmt in formats:
4501e04c3fSmrg        if fmt.colorspace != 'srgb':
4601e04c3fSmrg            continue;
4701e04c3fSmrg
4801e04c3fSmrg        replacements = [
4901e04c3fSmrg            ('SRGB', 'RGB'),
5001e04c3fSmrg            ('SRGB', 'UNORM'),
5101e04c3fSmrg            ('SRGB8_ALPHA8', 'RGBA'),
5201e04c3fSmrg            ('SRGB8_ALPHA8', 'RGBA8'),
5301e04c3fSmrg            ('SRGB_ALPHA_UNORM', 'RGBA_UNORM'),
5401e04c3fSmrg        ]
5501e04c3fSmrg        found_unorm_name = False
5601e04c3fSmrg        for rep in replacements:
5701e04c3fSmrg            if fmt.name.find(rep[0]) == -1:
5801e04c3fSmrg                continue
5901e04c3fSmrg
6001e04c3fSmrg            unorm_name = fmt.name.replace(rep[0], rep[1])
6101e04c3fSmrg            if unorm_name in names:
6201e04c3fSmrg                yield unorm_name, fmt.name
6301e04c3fSmrg                found_unorm_name = True
6401e04c3fSmrg                break
6501e04c3fSmrg
6601e04c3fSmrg        # Every sRGB format MUST have a UNORM equivalent
6701e04c3fSmrg        assert found_unorm_name
6801e04c3fSmrg
6901e04c3fSmrgdef get_rgbx_to_rgba_map(formats):
7001e04c3fSmrg    names = set(fmt.name for fmt in formats)
7101e04c3fSmrg
7201e04c3fSmrg    for fmt in formats:
7301e04c3fSmrg        if not fmt.has_channel('r') or not fmt.has_channel('x'):
7401e04c3fSmrg            continue
7501e04c3fSmrg
7601e04c3fSmrg        # The condition above will still let MESA_FORMAT_R9G9B9E5_FLOAT
7701e04c3fSmrg        # through.  We need to ensure it actually has an X in the name.
7801e04c3fSmrg        if not 'X' in fmt.name:
7901e04c3fSmrg            continue
8001e04c3fSmrg
8101e04c3fSmrg        rgbx_name = fmt.name
8201e04c3fSmrg        rgba_name = rgbx_name.replace("X", "A")
8301e04c3fSmrg        if rgba_name not in names:
8401e04c3fSmrg            continue;
8501e04c3fSmrg
8601e04c3fSmrg        yield rgbx_name, rgba_name
8701e04c3fSmrg
887ec681f3Smrgdef get_intensity_to_red_map(formats):
897ec681f3Smrg    names = set(fmt.name for fmt in formats)
907ec681f3Smrg
917ec681f3Smrg    for fmt in formats:
927ec681f3Smrg        if str(fmt.swizzle) != 'xxxx':
937ec681f3Smrg            continue
947ec681f3Smrg
957ec681f3Smrg        i_name = fmt.name
967ec681f3Smrg        r_name = i_name.replace("_I_", "_R_")
977ec681f3Smrg
987ec681f3Smrg        assert r_name in names
997ec681f3Smrg
1007ec681f3Smrg        yield i_name, r_name
1017ec681f3Smrg
10201e04c3fSmrgTEMPLATE = Template(COPYRIGHT + """
10301e04c3fSmrg#include "formats.h"
10401e04c3fSmrg#include "util/macros.h"
10501e04c3fSmrg
10601e04c3fSmrg/**
10701e04c3fSmrg * For an sRGB format, return the corresponding linear color space format.
10801e04c3fSmrg * For non-sRGB formats, return the format as-is.
10901e04c3fSmrg */
11001e04c3fSmrgmesa_format
11101e04c3fSmrg_mesa_get_srgb_format_linear(mesa_format format)
11201e04c3fSmrg{
11301e04c3fSmrg   switch (format) {
11401e04c3fSmrg%for unorm, srgb in unorm_to_srgb_map:
11501e04c3fSmrg   case ${srgb}:
11601e04c3fSmrg      return ${unorm};
11701e04c3fSmrg%endfor
11801e04c3fSmrg   default:
11901e04c3fSmrg      return format;
12001e04c3fSmrg   }
12101e04c3fSmrg}
12201e04c3fSmrg
12301e04c3fSmrg/**
12401e04c3fSmrg * For a linear format, return the corresponding sRGB color space format.
12501e04c3fSmrg * For an sRGB format, return the format as-is.
12601e04c3fSmrg * Assert-fails if the format is not sRGB and does not have an sRGB equivalent.
12701e04c3fSmrg */
12801e04c3fSmrgmesa_format
12901e04c3fSmrg_mesa_get_linear_format_srgb(mesa_format format)
13001e04c3fSmrg{
13101e04c3fSmrg   switch (format) {
13201e04c3fSmrg%for unorm, srgb in unorm_to_srgb_map:
13301e04c3fSmrg   case ${unorm}:
13401e04c3fSmrg      return ${srgb};
13501e04c3fSmrg%endfor
13601e04c3fSmrg%for unorm, srgb in unorm_to_srgb_map:
13701e04c3fSmrg   case ${srgb}:
13801e04c3fSmrg%endfor
13901e04c3fSmrg      return format;
14001e04c3fSmrg   default:
14101e04c3fSmrg      unreachable("Given format does not have an sRGB equivalent");
14201e04c3fSmrg   }
14301e04c3fSmrg}
14401e04c3fSmrg
1457ec681f3Smrg/**
1467ec681f3Smrg * For an intensity format, return the corresponding red format.  For other
1477ec681f3Smrg * formats, return the format as-is.
1487ec681f3Smrg */
1497ec681f3Smrgmesa_format
1507ec681f3Smrg_mesa_get_intensity_format_red(mesa_format format)
1517ec681f3Smrg{
1527ec681f3Smrg   switch (format) {
1537ec681f3Smrg%for i, r in intensity_to_red_map:
1547ec681f3Smrg   case ${i}:
1557ec681f3Smrg      return ${r};
1567ec681f3Smrg%endfor
1577ec681f3Smrg   default:
1587ec681f3Smrg      return format;
1597ec681f3Smrg   }
1607ec681f3Smrg}
1617ec681f3Smrg
16201e04c3fSmrg/**
16301e04c3fSmrg * If the format has an alpha channel, and there exists a non-alpha
16401e04c3fSmrg * variant of the format with an identical bit layout, then return
16501e04c3fSmrg * the non-alpha format. Otherwise return the original format.
16601e04c3fSmrg *
16701e04c3fSmrg * Examples:
16801e04c3fSmrg *    Fallback exists:
16901e04c3fSmrg *       MESA_FORMAT_R8G8B8X8_UNORM -> MESA_FORMAT_R8G8B8A8_UNORM
17001e04c3fSmrg *       MESA_FORMAT_RGBX_UNORM16 -> MESA_FORMAT_RGBA_UNORM16
17101e04c3fSmrg *
17201e04c3fSmrg *    No fallback:
17301e04c3fSmrg *       MESA_FORMAT_R8G8B8A8_UNORM -> MESA_FORMAT_R8G8B8A8_UNORM
17401e04c3fSmrg *       MESA_FORMAT_Z_FLOAT32 -> MESA_FORMAT_Z_FLOAT32
17501e04c3fSmrg */
17601e04c3fSmrgmesa_format
17701e04c3fSmrg_mesa_format_fallback_rgbx_to_rgba(mesa_format format)
17801e04c3fSmrg{
17901e04c3fSmrg   switch (format) {
18001e04c3fSmrg%for rgbx, rgba in rgbx_to_rgba_map:
18101e04c3fSmrg   case ${rgbx}:
18201e04c3fSmrg      return ${rgba};
18301e04c3fSmrg%endfor
18401e04c3fSmrg   default:
18501e04c3fSmrg      return format;
18601e04c3fSmrg   }
18701e04c3fSmrg}
18801e04c3fSmrg""");
18901e04c3fSmrg
19001e04c3fSmrgdef main():
19101e04c3fSmrg    pargs = parse_args()
19201e04c3fSmrg
19301e04c3fSmrg    formats = list(format_parser.parse(pargs.csv))
19401e04c3fSmrg
19501e04c3fSmrg    template_env = {
19601e04c3fSmrg        'unorm_to_srgb_map': list(get_unorm_to_srgb_map(formats)),
19701e04c3fSmrg        'rgbx_to_rgba_map': list(get_rgbx_to_rgba_map(formats)),
1987ec681f3Smrg        'intensity_to_red_map': list(get_intensity_to_red_map(formats)),
19901e04c3fSmrg    }
20001e04c3fSmrg
20101e04c3fSmrg    with open(pargs.out, 'w') as f:
20201e04c3fSmrg        f.write(TEMPLATE.render(**template_env))
20301e04c3fSmrg
20401e04c3fSmrgif __name__ == "__main__":
20501e04c3fSmrg    main()
206