From 4064a6cd207811434e5400a613b3833fbda6b787 Mon Sep 17 00:00:00 2001 From: Eric Anholt Date: Wed, 1 Jul 2020 13:19:47 -0700 Subject: [PATCH] util: Split the pack/unpack functions out of the format desc. This gives the compiler a chance to GC pack/unpack functions separate from the format descriptions. For drivers that use everything, this is +10-20kb, while for libvulkan_intel it's -1.3MB. Bug: https://bugs.chromium.org/p/chromium/issues/detail?id=1048434 Acked-by: Matt Turner Reviewed-by: Kenneth Graunke Reviewed-by: Jason Ekstrand Part-of: --- .../auxiliary/gallivm/lp_bld_format_aos.c | 12 +- .../auxiliary/translate/translate_generic.c | 14 +- src/gallium/drivers/iris/iris_clear.c | 8 +- src/gallium/drivers/llvmpipe/lp_test_format.c | 4 +- src/gallium/drivers/svga/svga_pipe_clear.c | 6 +- src/gallium/tests/unit/translate_test.c | 16 +- src/util/format/u_format.c | 74 ++++---- src/util/format/u_format.h | 160 ++++++++++-------- src/util/format/u_format_table.py | 72 +++++--- src/util/tests/format/u_format_test.c | 111 +++++++----- 10 files changed, 283 insertions(+), 194 deletions(-) diff --git a/src/gallium/auxiliary/gallivm/lp_bld_format_aos.c b/src/gallium/auxiliary/gallivm/lp_bld_format_aos.c index d48dbfb69b0..4d23047ada2 100644 --- a/src/gallium/auxiliary/gallivm/lp_bld_format_aos.c +++ b/src/gallium/auxiliary/gallivm/lp_bld_format_aos.c @@ -478,6 +478,8 @@ lp_build_fetch_rgba_aos(struct gallivm_state *gallivm, LLVMValueRef j, LLVMValueRef cache) { + const struct util_format_unpack_description *unpack = + util_format_unpack_description(format_desc->format); LLVMBuilderRef builder = gallivm->builder; unsigned num_pixels = type.length / 4; struct lp_build_context bld; @@ -789,7 +791,7 @@ lp_build_fetch_rgba_aos(struct gallivm_state *gallivm, * Fallback to util_format_description::fetch_rgba_8unorm(). */ - if (format_desc->fetch_rgba_8unorm && + if (unpack->fetch_rgba_8unorm && !type.floating && type.width == 8 && !type.sign && type.norm) { /* * Fallback to calling util_format_description::fetch_rgba_8unorm. @@ -839,7 +841,7 @@ lp_build_fetch_rgba_aos(struct gallivm_state *gallivm, gallivm->cache->dont_cache = true; /* make const pointer for the C fetch_rgba_8unorm function */ function = lp_build_const_int_pointer(gallivm, - func_to_pointer((func_pointer) format_desc->fetch_rgba_8unorm)); + func_to_pointer((func_pointer) unpack->fetch_rgba_8unorm)); /* cast the callee pointer to the function's type */ function = LLVMBuildBitCast(builder, function, @@ -895,7 +897,7 @@ lp_build_fetch_rgba_aos(struct gallivm_state *gallivm, * Fallback to util_format_description::fetch_rgba_float(). */ - if (format_desc->fetch_rgba_float) { + if (unpack->fetch_rgba_float) { /* * Fallback to calling util_format_description::fetch_rgba_float. * @@ -922,7 +924,7 @@ lp_build_fetch_rgba_aos(struct gallivm_state *gallivm, } /* - * Declare and bind format_desc->fetch_rgba_float(). + * Declare and bind unpack->fetch_rgba_float(). */ { @@ -942,7 +944,7 @@ lp_build_fetch_rgba_aos(struct gallivm_state *gallivm, if (gallivm->cache) gallivm->cache->dont_cache = true; function = lp_build_const_func_pointer(gallivm, - func_to_pointer((func_pointer) format_desc->fetch_rgba_float), + func_to_pointer((func_pointer) unpack->fetch_rgba_float), ret_type, arg_types, ARRAY_SIZE(arg_types), format_desc->short_name); diff --git a/src/gallium/auxiliary/translate/translate_generic.c b/src/gallium/auxiliary/translate/translate_generic.c index ac3310b4c5e..22d8d90b8a3 100644 --- a/src/gallium/auxiliary/translate/translate_generic.c +++ b/src/gallium/auxiliary/translate/translate_generic.c @@ -799,6 +799,8 @@ translate_generic_create(const struct translate_key *key) for (i = 0; i < key->nr_elements; i++) { const struct util_format_description *format_desc = util_format_description(key->element[i].input_format); + const struct util_format_unpack_description *unpack = + util_format_unpack_description(key->element[i].input_format); assert(format_desc); @@ -814,15 +816,15 @@ translate_generic_create(const struct translate_key *key) } if (format_desc->channel[0].type == UTIL_FORMAT_TYPE_SIGNED) { - assert(format_desc->fetch_rgba_sint); - tg->attrib[i].fetch = (fetch_func)format_desc->fetch_rgba_sint; + assert(unpack->fetch_rgba_sint); + tg->attrib[i].fetch = (fetch_func)unpack->fetch_rgba_sint; } else { - assert(format_desc->fetch_rgba_uint); - tg->attrib[i].fetch = (fetch_func)format_desc->fetch_rgba_uint; + assert(unpack->fetch_rgba_uint); + tg->attrib[i].fetch = (fetch_func)unpack->fetch_rgba_uint; } } else { - assert(format_desc->fetch_rgba_float); - tg->attrib[i].fetch = (fetch_func)format_desc->fetch_rgba_float; + assert(unpack->fetch_rgba_float); + tg->attrib[i].fetch = (fetch_func)unpack->fetch_rgba_float; } tg->attrib[i].buffer = key->element[i].input_buffer; diff --git a/src/gallium/drivers/iris/iris_clear.c b/src/gallium/drivers/iris/iris_clear.c index 2a78155f4e7..3d60c6bfbe3 100644 --- a/src/gallium/drivers/iris/iris_clear.c +++ b/src/gallium/drivers/iris/iris_clear.c @@ -717,16 +717,16 @@ iris_clear_texture(struct pipe_context *ctx, iris_resource_finish_aux_import(ctx->screen, res); if (util_format_is_depth_or_stencil(p_res->format)) { - const struct util_format_description *fmt_desc = - util_format_description(p_res->format); + const struct util_format_unpack_description *unpack = + util_format_unpack_description(p_res->format); float depth = 0.0; uint8_t stencil = 0; - if (fmt_desc->unpack_z_float) + if (unpack->unpack_z_float) util_format_unpack_z_float(p_res->format, &depth, data, 1); - if (fmt_desc->unpack_s_8uint) + if (unpack->unpack_s_8uint) util_format_unpack_s_8uint(p_res->format, &stencil, data, 1); clear_depth_stencil(ice, p_res, level, box, true, true, true, diff --git a/src/gallium/drivers/llvmpipe/lp_test_format.c b/src/gallium/drivers/llvmpipe/lp_test_format.c index a5a1528c667..583e5fc0b4d 100644 --- a/src/gallium/drivers/llvmpipe/lp_test_format.c +++ b/src/gallium/drivers/llvmpipe/lp_test_format.c @@ -367,6 +367,8 @@ test_all(unsigned verbose, FILE *fp) for (use_cache = 0; use_cache < 2; use_cache++) { for (format = 1; format < PIPE_FORMAT_COUNT; ++format) { const struct util_format_description *format_desc; + const struct util_format_unpack_description *unpack = + util_format_unpack_description(format); format_desc = util_format_description(format); if (!format_desc) { @@ -390,7 +392,7 @@ test_all(unsigned verbose, FILE *fp) * precompiled fetch func for any format before we write LLVM code to * fetch from it. */ - if (!format_desc->fetch_rgba_float) + if (!unpack->fetch_rgba_float) continue; /* only test twice with formats which can use cache */ diff --git a/src/gallium/drivers/svga/svga_pipe_clear.c b/src/gallium/drivers/svga/svga_pipe_clear.c index 0661d0a7899..624c2a75931 100644 --- a/src/gallium/drivers/svga/svga_pipe_clear.c +++ b/src/gallium/drivers/svga/svga_pipe_clear.c @@ -290,6 +290,8 @@ svga_clear_texture(struct pipe_context *pipe, union pipe_color_union color; const struct util_format_description *desc = util_format_description(surface->format); + const struct util_format_description *unpack = + util_format_unpack_description(surface->format); if (util_format_is_depth_or_stencil(surface->format)) { float depth; @@ -302,8 +304,8 @@ svga_clear_texture(struct pipe_context *pipe, stencil = 0; } else { - desc->unpack_z_float(&depth, 0, data, 0, 1, 1); - desc->unpack_s_8uint(&stencil, 0, data, 0, 1, 1); + unpack->unpack_z_float(&depth, 0, data, 0, 1, 1); + unpack->unpack_s_8uint(&stencil, 0, data, 0, 1, 1); } if (util_format_has_depth(desc)) { diff --git a/src/gallium/tests/unit/translate_test.c b/src/gallium/tests/unit/translate_test.c index 8e96b7b7b62..49a9c968300 100644 --- a/src/gallium/tests/unit/translate_test.c +++ b/src/gallium/tests/unit/translate_test.c @@ -172,12 +172,14 @@ int main(int argc, char** argv) for (output_format = 1; output_format < PIPE_FORMAT_COUNT; ++output_format) { const struct util_format_description* output_format_desc = util_format_description(output_format); + const struct util_format_pack_description* output_format_pack = util_format_pack_description(output_format); + const struct util_format_unpack_description* output_format_unpack = util_format_unpack_description(output_format); unsigned output_format_size; unsigned output_normalized = 0; if (!output_format_desc - || !output_format_desc->fetch_rgba_float - || !output_format_desc->pack_rgba_float + || !output_format_unpack->fetch_rgba_float + || !output_format_pack->pack_rgba_float || output_format_desc->colorspace != UTIL_FORMAT_COLORSPACE_RGB || output_format_desc->layout != UTIL_FORMAT_LAYOUT_PLAIN || !translate_is_output_format_supported(output_format)) @@ -194,6 +196,8 @@ int main(int argc, char** argv) for (input_format = 1; input_format < PIPE_FORMAT_COUNT; ++input_format) { const struct util_format_description* input_format_desc = util_format_description(input_format); + const struct util_format_pack_description* input_format_pack = util_format_pack_description(input_format); + const struct util_format_unpack_description* input_format_unpack = util_format_unpack_description(input_format); unsigned input_format_size; struct translate* translate[2]; unsigned fail = 0; @@ -202,8 +206,8 @@ int main(int argc, char** argv) boolean input_is_float = FALSE; if (!input_format_desc - || !input_format_desc->fetch_rgba_float - || !input_format_desc->pack_rgba_float + || !input_format_unpack->fetch_rgba_float + || !input_format_pack->pack_rgba_float || input_format_desc->colorspace != UTIL_FORMAT_COLORSPACE_RGB || input_format_desc->layout != UTIL_FORMAT_LAYOUT_PLAIN || !translate_is_output_format_supported(input_format)) @@ -273,8 +277,8 @@ int main(int argc, char** argv) { float a[4]; float b[4]; - input_format_desc->fetch_rgba_float(a, buffer[2] + i * input_format_size, 0, 0); - input_format_desc->fetch_rgba_float(b, buffer[4] + i * input_format_size, 0, 0); + input_format_unpack->fetch_rgba_float(a, buffer[2] + i * input_format_size, 0, 0); + input_format_unpack->fetch_rgba_float(b, buffer[4] + i * input_format_size, 0, 0); for (j = 0; j < count; ++j) { diff --git a/src/util/format/u_format.c b/src/util/format/u_format.c index cd732642154..c9db9a2061c 100644 --- a/src/util/format/u_format.c +++ b/src/util/format/u_format.c @@ -332,6 +332,8 @@ util_format_read_4(enum pipe_format format, unsigned x, unsigned y, unsigned w, unsigned h) { const struct util_format_description *format_desc; + const struct util_format_unpack_description *unpack = + util_format_unpack_description(format); const uint8_t *src_row; format_desc = util_format_description(format); @@ -341,7 +343,7 @@ util_format_read_4(enum pipe_format format, src_row = (const uint8_t *)src + y*src_stride + x*(format_desc->block.bits/8); - format_desc->unpack_rgba(dst, dst_stride, src_row, src_stride, w, h); + unpack->unpack_rgba(dst, dst_stride, src_row, src_stride, w, h); } @@ -352,6 +354,8 @@ util_format_write_4(enum pipe_format format, unsigned x, unsigned y, unsigned w, unsigned h) { const struct util_format_description *format_desc; + const struct util_format_pack_description *pack = + util_format_pack_description(format); uint8_t *dst_row; format_desc = util_format_description(format); @@ -362,11 +366,11 @@ util_format_write_4(enum pipe_format format, dst_row = (uint8_t *)dst + y*dst_stride + x*(format_desc->block.bits/8); if (util_format_is_pure_uint(format)) - format_desc->pack_rgba_uint(dst_row, dst_stride, src, src_stride, w, h); + pack->pack_rgba_uint(dst_row, dst_stride, src, src_stride, w, h); else if (util_format_is_pure_sint(format)) - format_desc->pack_rgba_sint(dst_row, dst_stride, src, src_stride, w, h); + pack->pack_rgba_sint(dst_row, dst_stride, src, src_stride, w, h); else - format_desc->pack_rgba_float(dst_row, dst_stride, src, src_stride, w, h); + pack->pack_rgba_float(dst_row, dst_stride, src, src_stride, w, h); } @@ -374,6 +378,8 @@ void util_format_read_4ub(enum pipe_format format, uint8_t *dst, unsigned dst_stride, const void *src, unsigned src_stride, unsigned x, unsigned y, unsigned w, unsigned h) { const struct util_format_description *format_desc; + const struct util_format_unpack_description *unpack = + util_format_unpack_description(format); const uint8_t *src_row; uint8_t *dst_row; @@ -385,7 +391,7 @@ util_format_read_4ub(enum pipe_format format, uint8_t *dst, unsigned dst_stride, src_row = (const uint8_t *)src + y*src_stride + x*(format_desc->block.bits/8); dst_row = dst; - format_desc->unpack_rgba_8unorm(dst_row, dst_stride, src_row, src_stride, w, h); + unpack->unpack_rgba_8unorm(dst_row, dst_stride, src_row, src_stride, w, h); } @@ -393,6 +399,8 @@ void util_format_write_4ub(enum pipe_format format, const uint8_t *src, unsigned src_stride, void *dst, unsigned dst_stride, unsigned x, unsigned y, unsigned w, unsigned h) { const struct util_format_description *format_desc; + const struct util_format_pack_description *pack = + util_format_pack_description(format); uint8_t *dst_row; const uint8_t *src_row; @@ -404,7 +412,7 @@ util_format_write_4ub(enum pipe_format format, const uint8_t *src, unsigned src_ dst_row = (uint8_t *)dst + y*dst_stride + x*(format_desc->block.bits/8); src_row = src; - format_desc->pack_rgba_8unorm(dst_row, dst_stride, src_row, src_stride, w, h); + pack->pack_rgba_8unorm(dst_row, dst_stride, src_row, src_stride, w, h); } /** @@ -568,6 +576,10 @@ util_format_translate(enum pipe_format dst_format, { const struct util_format_description *dst_format_desc; const struct util_format_description *src_format_desc; + const struct util_format_pack_description *pack = + util_format_pack_description(dst_format); + const struct util_format_unpack_description *unpack = + util_format_unpack_description(src_format); uint8_t *dst_row; const uint8_t *src_row; unsigned x_step, y_step; @@ -622,13 +634,11 @@ util_format_translate(enum pipe_format dst_format, assert(x_step == 1); assert(y_step == 1); - if (src_format_desc->unpack_z_float && - dst_format_desc->pack_z_float) { + if (unpack->unpack_z_float && pack->pack_z_float) { tmp_z = malloc(width * sizeof *tmp_z); } - if (src_format_desc->unpack_s_8uint && - dst_format_desc->pack_s_8uint) { + if (unpack->unpack_s_8uint && pack->pack_s_8uint) { tmp_s = malloc(width * sizeof *tmp_s); } @@ -659,8 +669,8 @@ util_format_translate(enum pipe_format dst_format, unsigned tmp_stride; uint8_t *tmp_row; - if (!src_format_desc->unpack_rgba_8unorm || - !dst_format_desc->pack_rgba_8unorm) { + if (!unpack->unpack_rgba_8unorm || + !pack->pack_rgba_8unorm) { return FALSE; } @@ -670,8 +680,8 @@ util_format_translate(enum pipe_format dst_format, return FALSE; while (height >= y_step) { - src_format_desc->unpack_rgba_8unorm(tmp_row, tmp_stride, src_row, src_stride, width, y_step); - dst_format_desc->pack_rgba_8unorm(dst_row, dst_stride, tmp_row, tmp_stride, width, y_step); + unpack->unpack_rgba_8unorm(tmp_row, tmp_stride, src_row, src_stride, width, y_step); + pack->pack_rgba_8unorm(dst_row, dst_stride, tmp_row, tmp_stride, width, y_step); dst_row += dst_step; src_row += src_step; @@ -679,8 +689,8 @@ util_format_translate(enum pipe_format dst_format, } if (height) { - src_format_desc->unpack_rgba_8unorm(tmp_row, tmp_stride, src_row, src_stride, width, height); - dst_format_desc->pack_rgba_8unorm(dst_row, dst_stride, tmp_row, tmp_stride, width, height); + unpack->unpack_rgba_8unorm(tmp_row, tmp_stride, src_row, src_stride, width, height); + pack->pack_rgba_8unorm(dst_row, dst_stride, tmp_row, tmp_stride, width, height); } free(tmp_row); @@ -701,8 +711,8 @@ util_format_translate(enum pipe_format dst_format, return FALSE; while (height >= y_step) { - src_format_desc->unpack_rgba(tmp_row, tmp_stride, src_row, src_stride, width, y_step); - dst_format_desc->pack_rgba_sint(dst_row, dst_stride, tmp_row, tmp_stride, width, y_step); + unpack->unpack_rgba(tmp_row, tmp_stride, src_row, src_stride, width, y_step); + pack->pack_rgba_sint(dst_row, dst_stride, tmp_row, tmp_stride, width, y_step); dst_row += dst_step; src_row += src_step; @@ -710,8 +720,8 @@ util_format_translate(enum pipe_format dst_format, } if (height) { - src_format_desc->unpack_rgba(tmp_row, tmp_stride, src_row, src_stride, width, height); - dst_format_desc->pack_rgba_sint(dst_row, dst_stride, tmp_row, tmp_stride, width, height); + unpack->unpack_rgba(tmp_row, tmp_stride, src_row, src_stride, width, height); + pack->pack_rgba_sint(dst_row, dst_stride, tmp_row, tmp_stride, width, height); } free(tmp_row); @@ -721,8 +731,8 @@ util_format_translate(enum pipe_format dst_format, unsigned tmp_stride; unsigned int *tmp_row; - if (!src_format_desc->unpack_rgba || - !dst_format_desc->pack_rgba_uint) { + if (!unpack->unpack_rgba || + !pack->pack_rgba_uint) { return FALSE; } @@ -732,8 +742,8 @@ util_format_translate(enum pipe_format dst_format, return FALSE; while (height >= y_step) { - src_format_desc->unpack_rgba(tmp_row, tmp_stride, src_row, src_stride, width, y_step); - dst_format_desc->pack_rgba_uint(dst_row, dst_stride, tmp_row, tmp_stride, width, y_step); + unpack->unpack_rgba(tmp_row, tmp_stride, src_row, src_stride, width, y_step); + pack->pack_rgba_uint(dst_row, dst_stride, tmp_row, tmp_stride, width, y_step); dst_row += dst_step; src_row += src_step; @@ -741,8 +751,8 @@ util_format_translate(enum pipe_format dst_format, } if (height) { - src_format_desc->unpack_rgba(tmp_row, tmp_stride, src_row, src_stride, width, height); - dst_format_desc->pack_rgba_uint(dst_row, dst_stride, tmp_row, tmp_stride, width, height); + unpack->unpack_rgba(tmp_row, tmp_stride, src_row, src_stride, width, height); + pack->pack_rgba_uint(dst_row, dst_stride, tmp_row, tmp_stride, width, height); } free(tmp_row); @@ -751,8 +761,8 @@ util_format_translate(enum pipe_format dst_format, unsigned tmp_stride; float *tmp_row; - if (!src_format_desc->unpack_rgba || - !dst_format_desc->pack_rgba_float) { + if (!unpack->unpack_rgba || + !pack->pack_rgba_float) { return FALSE; } @@ -762,8 +772,8 @@ util_format_translate(enum pipe_format dst_format, return FALSE; while (height >= y_step) { - src_format_desc->unpack_rgba(tmp_row, tmp_stride, src_row, src_stride, width, y_step); - dst_format_desc->pack_rgba_float(dst_row, dst_stride, tmp_row, tmp_stride, width, y_step); + unpack->unpack_rgba(tmp_row, tmp_stride, src_row, src_stride, width, y_step); + pack->pack_rgba_float(dst_row, dst_stride, tmp_row, tmp_stride, width, y_step); dst_row += dst_step; src_row += src_step; @@ -771,8 +781,8 @@ util_format_translate(enum pipe_format dst_format, } if (height) { - src_format_desc->unpack_rgba(tmp_row, tmp_stride, src_row, src_stride, width, height); - dst_format_desc->pack_rgba_float(dst_row, dst_stride, tmp_row, tmp_stride, width, height); + unpack->unpack_rgba(tmp_row, tmp_stride, src_row, src_stride, width, height); + pack->pack_rgba_float(dst_row, dst_stride, tmp_row, tmp_stride, width, height); } free(tmp_row); diff --git a/src/util/format/u_format.h b/src/util/format/u_format.h index 4b182ff558d..91198f65301 100644 --- a/src/util/format/u_format.h +++ b/src/util/format/u_format.h @@ -240,28 +240,87 @@ struct util_format_description * Colorspace transformation. */ enum util_format_colorspace colorspace; +}; +struct util_format_pack_description { /** - * Unpack pixel blocks to R8G8B8A8_UNORM. + * Pack pixel blocks from R8G8B8A8_UNORM. * Note: strides are in bytes. * * Only defined for non-depth-stencil formats. */ void - (*unpack_rgba_8unorm)(uint8_t *dst, unsigned dst_stride, - const uint8_t *src, unsigned src_stride, - unsigned width, unsigned height); + (*pack_rgba_8unorm)(uint8_t *dst, unsigned dst_stride, + const uint8_t *src, unsigned src_stride, + unsigned width, unsigned height); /** - * Pack pixel blocks from R8G8B8A8_UNORM. + * Pack pixel blocks from R32G32B32A32_FLOAT. * Note: strides are in bytes. * * Only defined for non-depth-stencil formats. */ void - (*pack_rgba_8unorm)(uint8_t *dst, unsigned dst_stride, - const uint8_t *src, unsigned src_stride, - unsigned width, unsigned height); + (*pack_rgba_float)(uint8_t *dst, unsigned dst_stride, + const float *src, unsigned src_stride, + unsigned width, unsigned height); + + /** + * Pack pixels from Z32_FLOAT. + * Note: strides are in bytes. + * + * Only defined for depth formats. + */ + void + (*pack_z_32unorm)(uint8_t *dst, unsigned dst_stride, + const uint32_t *src, unsigned src_stride, + unsigned width, unsigned height); + + /** + * Pack pixels from Z32_FLOAT. + * Note: strides are in bytes. + * + * Only defined for depth formats. + */ + void + (*pack_z_float)(uint8_t *dst, unsigned dst_stride, + const float *src, unsigned src_stride, + unsigned width, unsigned height); + + /** + * Pack pixels from S8_UINT. + * Note: strides are in bytes. + * + * Only defined for stencil formats. + */ + void + (*pack_s_8uint)(uint8_t *dst, unsigned dst_stride, + const uint8_t *src, unsigned src_stride, + unsigned width, unsigned height); + + void + (*pack_rgba_uint)(uint8_t *dst, unsigned dst_stride, + const uint32_t *src, unsigned src_stride, + unsigned width, unsigned height); + + void + (*pack_rgba_sint)(uint8_t *dst, unsigned dst_stride, + const int32_t *src, unsigned src_stride, + unsigned width, unsigned height); +}; + + +struct util_format_unpack_description { + /** + * Unpack pixel blocks to R8G8B8A8_UNORM. + * Note: strides are in bytes. + * + * Only defined for non-depth-stencil formats. + */ + void + (*unpack_rgba_8unorm)(uint8_t *dst, unsigned dst_stride, + const uint8_t *src, unsigned src_stride, + unsigned width, unsigned height); /** * Fetch a single pixel (i, j) from a block. @@ -286,17 +345,6 @@ struct util_format_description const uint8_t *src, unsigned src_stride, unsigned width, unsigned height); - /** - * Pack pixel blocks from R32G32B32A32_FLOAT. - * Note: strides are in bytes. - * - * Only defined for non-depth-stencil formats. - */ - void - (*pack_rgba_float)(uint8_t *dst, unsigned dst_stride, - const float *src, unsigned src_stride, - unsigned width, unsigned height); - /** * Fetch a single pixel (i, j) from a block. * @@ -318,17 +366,6 @@ struct util_format_description const uint8_t *src, unsigned src_stride, unsigned width, unsigned height); - /** - * Pack pixels from Z32_FLOAT. - * Note: strides are in bytes. - * - * Only defined for depth formats. - */ - void - (*pack_z_32unorm)(uint8_t *dst, unsigned dst_stride, - const uint32_t *src, unsigned src_stride, - unsigned width, unsigned height); - /** * Unpack pixels to Z32_FLOAT. * Note: strides are in bytes. @@ -340,17 +377,6 @@ struct util_format_description const uint8_t *src, unsigned src_stride, unsigned width, unsigned height); - /** - * Pack pixels from Z32_FLOAT. - * Note: strides are in bytes. - * - * Only defined for depth formats. - */ - void - (*pack_z_float)(uint8_t *dst, unsigned dst_stride, - const float *src, unsigned src_stride, - unsigned width, unsigned height); - /** * Unpack pixels to S8_UINT. * Note: strides are in bytes. @@ -362,27 +388,6 @@ struct util_format_description const uint8_t *src, unsigned src_stride, unsigned width, unsigned height); - /** - * Pack pixels from S8_UINT. - * Note: strides are in bytes. - * - * Only defined for stencil formats. - */ - void - (*pack_s_8uint)(uint8_t *dst, unsigned dst_stride, - const uint8_t *src, unsigned src_stride, - unsigned width, unsigned height); - - void - (*pack_rgba_uint)(uint8_t *dst, unsigned dst_stride, - const uint32_t *src, unsigned src_stride, - unsigned width, unsigned height); - - void - (*pack_rgba_sint)(uint8_t *dst, unsigned dst_stride, - const int32_t *src, unsigned src_stride, - unsigned width, unsigned height); - /** * Fetch a single pixel (i, j) from a block. * @@ -404,10 +409,15 @@ struct util_format_description unsigned i, unsigned j); }; - const struct util_format_description * util_format_description(enum pipe_format format) ATTRIBUTE_CONST; +const struct util_format_pack_description * +util_format_pack_description(enum pipe_format format); + +const struct util_format_unpack_description * +util_format_unpack_description(enum pipe_format format); + /* * Format query functions. @@ -1430,7 +1440,8 @@ static inline void util_format_unpack_z_float(enum pipe_format format, float *dst, const void *src, unsigned w) { - const struct util_format_description *desc = util_format_description(format); + const struct util_format_unpack_description *desc = + util_format_unpack_description(format); desc->unpack_z_float(dst, 0, (const uint8_t *)src, 0, w, 1); } @@ -1439,7 +1450,8 @@ static inline void util_format_unpack_z_32unorm(enum pipe_format format, uint32_t *dst, const void *src, unsigned w) { - const struct util_format_description *desc = util_format_description(format); + const struct util_format_unpack_description *desc = + util_format_unpack_description(format); desc->unpack_z_32unorm(dst, 0, (const uint8_t *)src, 0, w, 1); } @@ -1448,7 +1460,8 @@ static inline void util_format_unpack_s_8uint(enum pipe_format format, uint8_t *dst, const void *src, unsigned w) { - const struct util_format_description *desc = util_format_description(format); + const struct util_format_unpack_description *desc = + util_format_unpack_description(format); desc->unpack_s_8uint(dst, 0, (const uint8_t *)src, 0, w, 1); } @@ -1461,7 +1474,8 @@ static inline void util_format_unpack_rgba(enum pipe_format format, void *dst, const void *src, unsigned w) { - const struct util_format_description *desc = util_format_description(format); + const struct util_format_unpack_description *desc = + util_format_unpack_description(format); desc->unpack_rgba(dst, 0, (const uint8_t *)src, 0, w, 1); } @@ -1470,7 +1484,8 @@ static inline void util_format_pack_z_float(enum pipe_format format, void *dst, const float *src, unsigned w) { - const struct util_format_description *desc = util_format_description(format); + const struct util_format_pack_description *desc = + util_format_pack_description(format); desc->pack_z_float((uint8_t *)dst, 0, src, 0, w, 1); } @@ -1479,7 +1494,8 @@ static inline void util_format_pack_z_32unorm(enum pipe_format format, void *dst, const uint32_t *src, unsigned w) { - const struct util_format_description *desc = util_format_description(format); + const struct util_format_pack_description *desc = + util_format_pack_description(format); desc->pack_z_32unorm((uint8_t *)dst, 0, src, 0, w, 1); } @@ -1488,7 +1504,8 @@ static inline void util_format_pack_s_8uint(enum pipe_format format, void *dst, const uint8_t *src, unsigned w) { - const struct util_format_description *desc = util_format_description(format); + const struct util_format_pack_description *desc = + util_format_pack_description(format); desc->pack_s_8uint((uint8_t *)dst, 0, src, 0, w, 1); } @@ -1502,7 +1519,8 @@ static inline void util_format_pack_rgba(enum pipe_format format, void *dst, const void *src, unsigned w) { - const struct util_format_description *desc = util_format_description(format); + const struct util_format_pack_description *desc = + util_format_pack_description(format); if (util_format_is_pure_uint(format)) desc->pack_rgba_uint((uint8_t *)dst, 0, (const uint32_t *)src, 0, w, 1); diff --git a/src/util/format/u_format_table.py b/src/util/format/u_format_table.py index 8ca8ec33cde..bb89d56a42d 100644 --- a/src/util/format/u_format_table.py +++ b/src/util/format/u_format_table.py @@ -124,6 +124,25 @@ def write_format_table(formats): print(" %s%s\t/* %s */" % (swizzle_map[swizzle], sep, comment)) print(" },") + def generate_table_getter(type): + print("const struct util_format_%sdescription *" % type) + print("util_format_%sdescription(enum pipe_format format)" % type) + print("{") + print(" if (format >= PIPE_FORMAT_COUNT) {") + print(" return NULL;") + print(" }") + print() + print(" switch (format) {") + for format in formats: + print(" case %s:" % format.name) + print(" return &util_format_%s_%sdescription;" % (format.short_name(), type)) + print(" default:") + print(" return NULL;") + print(" }") + print("}") + print() + + for format in formats: sn = format.short_name() @@ -143,6 +162,8 @@ def write_format_table(formats): u_format_pack.print_channels(format, do_channel_array) u_format_pack.print_channels(format, do_swizzle_array) print(" %s," % (colorspace_map(format.colorspace),)) + print("};") + print() # We don't generate code for YUV formats, and many of the new ones lack pack/unpack # functions for softpipe/llvmpipe. @@ -174,55 +195,54 @@ def write_format_table(formats): access = False if format.layout == 'etc' and sn != 'etc1_rgb8': access = False + + print('const struct util_format_pack_description') + print('util_format_%s_pack_description = {' % sn) if format.colorspace != ZS and not format.is_pure_color() and access: - print(" .unpack_rgba_8unorm = &util_format_%s_unpack_rgba_8unorm," % sn) print(" .pack_rgba_8unorm = &util_format_%s_pack_rgba_8unorm," % sn) + print(" .pack_rgba_float = &util_format_%s_pack_rgba_float," % sn) + + if format.has_depth(): + print(" .pack_z_32unorm = &util_format_%s_pack_z_32unorm," % sn) + print(" .pack_z_float = &util_format_%s_pack_z_float," % sn) + + if format.has_stencil(): + print(" .pack_s_8uint = &util_format_%s_pack_s_8uint," % sn) + + if format.is_pure_unsigned() or format.is_pure_signed(): + print(" .pack_rgba_uint = &util_format_%s_pack_unsigned," % sn) + print(" .pack_rgba_sint = &util_format_%s_pack_signed," % sn) + print("};") + print() + + print('const struct util_format_unpack_description') + print('util_format_%s_unpack_description = {' % sn) + if format.colorspace != ZS and not format.is_pure_color() and access: + print(" .unpack_rgba_8unorm = &util_format_%s_unpack_rgba_8unorm," % sn) if format.layout == 's3tc' or format.layout == 'rgtc': print(" .fetch_rgba_8unorm = &util_format_%s_fetch_rgba_8unorm," % sn) print(" .unpack_rgba = &util_format_%s_unpack_rgba_float," % sn) - print(" .pack_rgba_float = &util_format_%s_pack_rgba_float," % sn) print(" .fetch_rgba_float = &util_format_%s_fetch_rgba_float," % sn) if format.has_depth(): print(" .unpack_z_32unorm = &util_format_%s_unpack_z_32unorm," % sn) - print(" .pack_z_32unorm = &util_format_%s_pack_z_32unorm," % sn) print(" .unpack_z_float = &util_format_%s_unpack_z_float," % sn) - print(" .pack_z_float = &util_format_%s_pack_z_float," % sn) if format.has_stencil(): print(" .unpack_s_8uint = &util_format_%s_unpack_s_8uint," % sn) - print(" .pack_s_8uint = &util_format_%s_pack_s_8uint," % sn) if format.is_pure_unsigned(): print(" .unpack_rgba = &util_format_%s_unpack_unsigned," % sn) - print(" .pack_rgba_uint = &util_format_%s_pack_unsigned," % sn) - print(" .pack_rgba_sint = &util_format_%s_pack_signed," % sn) print(" .fetch_rgba_uint = &util_format_%s_fetch_unsigned," % sn) elif format.is_pure_signed(): - print(" .pack_rgba_uint = &util_format_%s_pack_unsigned," % sn) print(" .unpack_rgba = &util_format_%s_unpack_signed," % sn) - print(" .pack_rgba_sint = &util_format_%s_pack_signed," % sn) print(" .fetch_rgba_sint = &util_format_%s_fetch_signed," % sn) print("};") print() - - print("const struct util_format_description *") - print("util_format_description(enum pipe_format format)") - print("{") - print(" if (format >= PIPE_FORMAT_COUNT) {") - print(" return NULL;") - print(" }") - print() - print(" switch (format) {") - for format in formats: - print(" case %s:" % format.name) - print(" return &util_format_%s_description;" % (format.short_name(),)) - print(" default:") - print(" return NULL;") - print(" }") - print("}") - print() + generate_table_getter("") + generate_table_getter("pack_") + generate_table_getter("unpack_") def main(): diff --git a/src/util/tests/format/u_format_test.c b/src/util/tests/format/u_format_test.c index a6f1d608c84..c93199ebd02 100644 --- a/src/util/tests/format/u_format_test.c +++ b/src/util/tests/format/u_format_test.c @@ -204,6 +204,8 @@ static boolean test_format_fetch_rgba_float(const struct util_format_description *format_desc, const struct util_format_test_case *test) { + const struct util_format_unpack_description *unpack = + util_format_unpack_description(format_desc->format); float unpacked[UTIL_FORMAT_MAX_UNPACKED_HEIGHT][UTIL_FORMAT_MAX_UNPACKED_WIDTH][4] = { { { 0 } } }; unsigned i, j, k; boolean success; @@ -211,7 +213,7 @@ test_format_fetch_rgba_float(const struct util_format_description *format_desc, success = TRUE; for (i = 0; i < format_desc->block.height; ++i) { for (j = 0; j < format_desc->block.width; ++j) { - format_desc->fetch_rgba_float(unpacked[i][j], test->packed, j, i); + unpack->fetch_rgba_float(unpacked[i][j], test->packed, j, i); for (k = 0; k < 4; ++k) { if (!compare_float(test->unpacked[i][j][k], unpacked[i][j][k])) { success = FALSE; @@ -238,13 +240,15 @@ static boolean test_format_unpack_rgba(const struct util_format_description *format_desc, const struct util_format_test_case *test) { + const struct util_format_unpack_description *unpack = + util_format_unpack_description(format_desc->format); float unpacked[UTIL_FORMAT_MAX_UNPACKED_HEIGHT][UTIL_FORMAT_MAX_UNPACKED_WIDTH][4] = { { { 0 } } }; unsigned i, j, k; boolean success; - format_desc->unpack_rgba(&unpacked[0][0][0], sizeof unpacked[0], - test->packed, 0, - format_desc->block.width, format_desc->block.height); + unpack->unpack_rgba(&unpacked[0][0][0], sizeof unpacked[0], + test->packed, 0, + format_desc->block.width, format_desc->block.height); success = TRUE; for (i = 0; i < format_desc->block.height; ++i) { @@ -275,6 +279,8 @@ static boolean test_format_pack_rgba_float(const struct util_format_description *format_desc, const struct util_format_test_case *test) { + const struct util_format_pack_description *pack = + util_format_pack_description(format_desc->format); float unpacked[UTIL_FORMAT_MAX_UNPACKED_HEIGHT][UTIL_FORMAT_MAX_UNPACKED_WIDTH][4]; uint8_t packed[UTIL_FORMAT_MAX_PACKED_BYTES]; unsigned i, j, k; @@ -298,7 +304,7 @@ test_format_pack_rgba_float(const struct util_format_description *format_desc, } } - format_desc->pack_rgba_float(packed, 0, + pack->pack_rgba_float(packed, 0, &unpacked[0][0][0], sizeof unpacked[0], format_desc->block.width, format_desc->block.height); @@ -354,6 +360,8 @@ static boolean test_format_unpack_rgba_8unorm(const struct util_format_description *format_desc, const struct util_format_test_case *test) { + const struct util_format_unpack_description *unpack = + util_format_unpack_description(format_desc->format); uint8_t unpacked[UTIL_FORMAT_MAX_UNPACKED_HEIGHT][UTIL_FORMAT_MAX_UNPACKED_WIDTH][4] = { { { 0 } } }; uint8_t expected[UTIL_FORMAT_MAX_UNPACKED_HEIGHT][UTIL_FORMAT_MAX_UNPACKED_WIDTH][4] = { { { 0 } } }; unsigned i, j, k; @@ -362,7 +370,7 @@ test_format_unpack_rgba_8unorm(const struct util_format_description *format_desc if (util_format_is_pure_integer(format_desc->format)) return FALSE; - format_desc->unpack_rgba_8unorm(&unpacked[0][0][0], sizeof unpacked[0], + unpack->unpack_rgba_8unorm(&unpacked[0][0][0], sizeof unpacked[0], test->packed, 0, format_desc->block.width, format_desc->block.height); @@ -396,6 +404,8 @@ static boolean test_format_pack_rgba_8unorm(const struct util_format_description *format_desc, const struct util_format_test_case *test) { + const struct util_format_pack_description *pack = + util_format_pack_description(format_desc->format); uint8_t unpacked[UTIL_FORMAT_MAX_UNPACKED_HEIGHT][UTIL_FORMAT_MAX_UNPACKED_WIDTH][4]; uint8_t packed[UTIL_FORMAT_MAX_PACKED_BYTES]; unsigned i; @@ -419,9 +429,9 @@ test_format_pack_rgba_8unorm(const struct util_format_description *format_desc, memset(packed, 0, sizeof packed); - format_desc->pack_rgba_8unorm(packed, 0, - &unpacked[0][0][0], sizeof unpacked[0], - format_desc->block.width, format_desc->block.height); + pack->pack_rgba_8unorm(packed, 0, + &unpacked[0][0][0], sizeof unpacked[0], + format_desc->block.width, format_desc->block.height); success = TRUE; for (i = 0; i < format_desc->block.bits/8; ++i) @@ -458,13 +468,15 @@ static boolean test_format_unpack_z_float(const struct util_format_description *format_desc, const struct util_format_test_case *test) { + const struct util_format_unpack_description *unpack = + util_format_unpack_description(format_desc->format); float unpacked[UTIL_FORMAT_MAX_UNPACKED_HEIGHT][UTIL_FORMAT_MAX_UNPACKED_WIDTH] = { { 0 } }; unsigned i, j; boolean success; - format_desc->unpack_z_float(&unpacked[0][0], sizeof unpacked[0], - test->packed, 0, - format_desc->block.width, format_desc->block.height); + unpack->unpack_z_float(&unpacked[0][0], sizeof unpacked[0], + test->packed, 0, + format_desc->block.width, format_desc->block.height); success = TRUE; for (i = 0; i < format_desc->block.height; ++i) { @@ -488,6 +500,8 @@ static boolean test_format_pack_z_float(const struct util_format_description *format_desc, const struct util_format_test_case *test) { + const struct util_format_pack_description *pack = + util_format_pack_description(format_desc->format); float unpacked[UTIL_FORMAT_MAX_UNPACKED_HEIGHT][UTIL_FORMAT_MAX_UNPACKED_WIDTH]; uint8_t packed[UTIL_FORMAT_MAX_PACKED_BYTES]; unsigned i, j; @@ -503,9 +517,9 @@ test_format_pack_z_float(const struct util_format_description *format_desc, } } - format_desc->pack_z_float(packed, 0, - &unpacked[0][0], sizeof unpacked[0], - format_desc->block.width, format_desc->block.height); + pack->pack_z_float(packed, 0, + &unpacked[0][0], sizeof unpacked[0], + format_desc->block.width, format_desc->block.height); success = TRUE; for (i = 0; i < format_desc->block.bits/8; ++i) @@ -525,14 +539,16 @@ static boolean test_format_unpack_z_32unorm(const struct util_format_description *format_desc, const struct util_format_test_case *test) { + const struct util_format_unpack_description *unpack = + util_format_unpack_description(format_desc->format); uint32_t unpacked[UTIL_FORMAT_MAX_UNPACKED_HEIGHT][UTIL_FORMAT_MAX_UNPACKED_WIDTH] = { { 0 } }; uint32_t expected[UTIL_FORMAT_MAX_UNPACKED_HEIGHT][UTIL_FORMAT_MAX_UNPACKED_WIDTH] = { { 0 } }; unsigned i, j; boolean success; - format_desc->unpack_z_32unorm(&unpacked[0][0], sizeof unpacked[0], - test->packed, 0, - format_desc->block.width, format_desc->block.height); + unpack->unpack_z_32unorm(&unpacked[0][0], sizeof unpacked[0], + test->packed, 0, + format_desc->block.width, format_desc->block.height); for (i = 0; i < format_desc->block.height; ++i) { for (j = 0; j < format_desc->block.width; ++j) { @@ -562,6 +578,8 @@ static boolean test_format_pack_z_32unorm(const struct util_format_description *format_desc, const struct util_format_test_case *test) { + const struct util_format_pack_description *pack = + util_format_pack_description(format_desc->format); uint32_t unpacked[UTIL_FORMAT_MAX_UNPACKED_HEIGHT][UTIL_FORMAT_MAX_UNPACKED_WIDTH]; uint8_t packed[UTIL_FORMAT_MAX_PACKED_BYTES]; unsigned i, j; @@ -578,9 +596,9 @@ test_format_pack_z_32unorm(const struct util_format_description *format_desc, memset(packed, 0, sizeof packed); - format_desc->pack_z_32unorm(packed, 0, - &unpacked[0][0], sizeof unpacked[0], - format_desc->block.width, format_desc->block.height); + pack->pack_z_32unorm(packed, 0, + &unpacked[0][0], sizeof unpacked[0], + format_desc->block.width, format_desc->block.height); success = TRUE; for (i = 0; i < format_desc->block.bits/8; ++i) @@ -600,14 +618,16 @@ static boolean test_format_unpack_s_8uint(const struct util_format_description *format_desc, const struct util_format_test_case *test) { + const struct util_format_unpack_description *unpack = + util_format_unpack_description(format_desc->format); uint8_t unpacked[UTIL_FORMAT_MAX_UNPACKED_HEIGHT][UTIL_FORMAT_MAX_UNPACKED_WIDTH] = { { 0 } }; uint8_t expected[UTIL_FORMAT_MAX_UNPACKED_HEIGHT][UTIL_FORMAT_MAX_UNPACKED_WIDTH] = { { 0 } }; unsigned i, j; boolean success; - format_desc->unpack_s_8uint(&unpacked[0][0], sizeof unpacked[0], - test->packed, 0, - format_desc->block.width, format_desc->block.height); + unpack->unpack_s_8uint(&unpacked[0][0], sizeof unpacked[0], + test->packed, 0, + format_desc->block.width, format_desc->block.height); for (i = 0; i < format_desc->block.height; ++i) { for (j = 0; j < format_desc->block.width; ++j) { @@ -637,6 +657,8 @@ static boolean test_format_pack_s_8uint(const struct util_format_description *format_desc, const struct util_format_test_case *test) { + const struct util_format_pack_description *pack = + util_format_pack_description(format_desc->format); uint8_t unpacked[UTIL_FORMAT_MAX_UNPACKED_HEIGHT][UTIL_FORMAT_MAX_UNPACKED_WIDTH]; uint8_t packed[UTIL_FORMAT_MAX_PACKED_BYTES]; unsigned i, j; @@ -653,9 +675,9 @@ test_format_pack_s_8uint(const struct util_format_description *format_desc, memset(packed, 0, sizeof packed); - format_desc->pack_s_8uint(packed, 0, - &unpacked[0][0], sizeof unpacked[0], - format_desc->block.width, format_desc->block.height); + pack->pack_s_8uint(packed, 0, + &unpacked[0][0], sizeof unpacked[0], + format_desc->block.width, format_desc->block.height); success = TRUE; for (i = 0; i < format_desc->block.bits/8; ++i) @@ -777,8 +799,15 @@ test_all(void) assert(format_desc->block.height <= UTIL_FORMAT_MAX_UNPACKED_HEIGHT); assert(format_desc->block.width <= UTIL_FORMAT_MAX_UNPACKED_WIDTH); -# define TEST_ONE_FUNC(name) \ - if (format_desc->name) { \ +# define TEST_ONE_PACK_FUNC(name) \ + if (util_format_pack_description(format)->name) { \ + if (!test_one_func(format_desc, &test_format_##name, #name)) { \ + success = FALSE; \ + } \ + } + +# define TEST_ONE_UNPACK_FUNC(name) \ + if (util_format_unpack_description(format)->name) { \ if (!test_one_func(format_desc, &test_format_##name, #name)) { \ success = FALSE; \ } \ @@ -789,18 +818,18 @@ test_all(void) success = FALSE; \ } \ - TEST_ONE_FUNC(fetch_rgba_float); - TEST_ONE_FUNC(pack_rgba_float); - TEST_ONE_FUNC(unpack_rgba); - TEST_ONE_FUNC(pack_rgba_8unorm); - TEST_ONE_FUNC(unpack_rgba_8unorm); - - TEST_ONE_FUNC(unpack_z_32unorm); - TEST_ONE_FUNC(pack_z_32unorm); - TEST_ONE_FUNC(unpack_z_float); - TEST_ONE_FUNC(pack_z_float); - TEST_ONE_FUNC(unpack_s_8uint); - TEST_ONE_FUNC(pack_s_8uint); + TEST_ONE_UNPACK_FUNC(fetch_rgba_float); + TEST_ONE_PACK_FUNC(pack_rgba_float); + TEST_ONE_UNPACK_FUNC(unpack_rgba); + TEST_ONE_PACK_FUNC(pack_rgba_8unorm); + TEST_ONE_UNPACK_FUNC(unpack_rgba_8unorm); + + TEST_ONE_UNPACK_FUNC(unpack_z_32unorm); + TEST_ONE_PACK_FUNC(pack_z_32unorm); + TEST_ONE_UNPACK_FUNC(unpack_z_float); + TEST_ONE_PACK_FUNC(pack_z_float); + TEST_ONE_UNPACK_FUNC(unpack_s_8uint); + TEST_ONE_PACK_FUNC(pack_s_8uint); TEST_FORMAT_METADATA(norm_flags); -- 2.30.2