summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--src/gallium/auxiliary/util/u_format.c28
-rw-r--r--src/gallium/auxiliary/util/u_format.h10
-rw-r--r--src/gallium/auxiliary/util/u_format_parse.py20
-rw-r--r--src/gallium/auxiliary/util/u_format_table.py2
-rw-r--r--src/gallium/tests/unit/u_format_test.c65
5 files changed, 101 insertions, 24 deletions
diff --git a/src/gallium/auxiliary/util/u_format.c b/src/gallium/auxiliary/util/u_format.c
index 862061a8ec2..3a61d54f726 100644
--- a/src/gallium/auxiliary/util/u_format.c
+++ b/src/gallium/auxiliary/util/u_format.c
@@ -149,45 +149,25 @@ util_format_is_pure_uint(enum pipe_format format)
}
/**
- * Returns true if all non-void channels are normalized signed.
+ * Returns true if the format contains normalized signed channels.
*/
boolean
util_format_is_snorm(enum pipe_format format)
{
const struct util_format_description *desc = util_format_description(format);
- int i;
-
- if (desc->is_mixed)
- return FALSE;
-
- i = util_format_get_first_non_void_channel(format);
- if (i == -1)
- return FALSE;
- return desc->channel[i].type == UTIL_FORMAT_TYPE_SIGNED &&
- !desc->channel[i].pure_integer &&
- desc->channel[i].normalized;
+ return desc->is_snorm;
}
/**
- * Returns true if all non-void channels are normalized unsigned.
+ * Returns true if the format contains normalized unsigned channels.
*/
boolean
util_format_is_unorm(enum pipe_format format)
{
const struct util_format_description *desc = util_format_description(format);
- int i;
- if (desc->is_mixed)
- return FALSE;
-
- i = util_format_get_first_non_void_channel(format);
- if (i == -1)
- return FALSE;
-
- return desc->channel[i].type == UTIL_FORMAT_TYPE_UNSIGNED &&
- !desc->channel[i].pure_integer &&
- desc->channel[i].normalized;
+ return desc->is_unorm;
}
boolean
diff --git a/src/gallium/auxiliary/util/u_format.h b/src/gallium/auxiliary/util/u_format.h
index 0c0c505e391..cb1138947aa 100644
--- a/src/gallium/auxiliary/util/u_format.h
+++ b/src/gallium/auxiliary/util/u_format.h
@@ -178,6 +178,16 @@ struct util_format_description
unsigned is_mixed:1;
/**
+ * Whether the format contains UNORM channels
+ */
+ unsigned is_unorm:1;
+
+ /**
+ * Whether the format contains SNORM channels
+ */
+ unsigned is_snorm:1;
+
+ /**
* Input channel description, in the order XYZW.
*
* Only valid for UTIL_FORMAT_LAYOUT_PLAIN formats.
diff --git a/src/gallium/auxiliary/util/u_format_parse.py b/src/gallium/auxiliary/util/u_format_parse.py
index 48cc012cd2a..e8a6c92d119 100644
--- a/src/gallium/auxiliary/util/u_format_parse.py
+++ b/src/gallium/auxiliary/util/u_format_parse.py
@@ -187,6 +187,26 @@ class Format:
return True
return False
+ def is_compressed(self):
+ for channel in self.le_channels:
+ if channel.type != VOID:
+ return False
+ return True
+
+ def is_unorm(self):
+ # Non-compressed formats all have unorm or srgb in their name.
+ for keyword in ['_UNORM', '_SRGB']:
+ if keyword in self.name:
+ return True
+
+ # All the compressed formats in GLES3.2 and GL4.6 ("Table 8.14: Generic
+ # and specific compressed internal formats.") that aren't snorm for
+ # border colors are unorm, other than BPTC_*_FLOAT.
+ return self.is_compressed() and not ('FLOAT' in self.name or self.is_snorm())
+
+ def is_snorm(self):
+ return '_SNORM' in self.name
+
def is_pot(self):
return is_pot(self.block_size())
diff --git a/src/gallium/auxiliary/util/u_format_table.py b/src/gallium/auxiliary/util/u_format_table.py
index 1a966c52bc7..97cd0474382 100644
--- a/src/gallium/auxiliary/util/u_format_table.py
+++ b/src/gallium/auxiliary/util/u_format_table.py
@@ -136,6 +136,8 @@ def write_format_table(formats):
print(" %s,\t/* is_array */" % (bool_map(format.is_array()),))
print(" %s,\t/* is_bitmask */" % (bool_map(format.is_bitmask()),))
print(" %s,\t/* is_mixed */" % (bool_map(format.is_mixed()),))
+ print(" %s,\t/* is_unorm */" % (bool_map(format.is_unorm()),))
+ print(" %s,\t/* is_snorm */" % (bool_map(format.is_snorm()),))
u_format_pack.print_channels(format, do_channel_array)
u_format_pack.print_channels(format, do_swizzle_array)
print(" %s," % (colorspace_map(format.colorspace),))
diff --git a/src/gallium/tests/unit/u_format_test.c b/src/gallium/tests/unit/u_format_test.c
index 437cc94b757..640214dfc50 100644
--- a/src/gallium/tests/unit/u_format_test.c
+++ b/src/gallium/tests/unit/u_format_test.c
@@ -668,6 +668,47 @@ test_format_pack_s_8uint(const struct util_format_description *format_desc,
}
+/* Touch-test that the unorm/snorm flags are set up right by codegen. */
+static boolean
+test_format_norm_flags(const struct util_format_description *format_desc)
+{
+ boolean success = TRUE;
+
+#define FORMAT_CASE(format, unorm, snorm) \
+ case format: \
+ success = (format_desc->is_unorm == unorm && \
+ format_desc->is_snorm == snorm); \
+ break
+
+ switch (format_desc->format) {
+ FORMAT_CASE(PIPE_FORMAT_R8G8B8A8_UNORM, TRUE, FALSE);
+ FORMAT_CASE(PIPE_FORMAT_R8G8B8A8_SRGB, TRUE, FALSE);
+ FORMAT_CASE(PIPE_FORMAT_R8G8B8A8_SNORM, FALSE, TRUE);
+ FORMAT_CASE(PIPE_FORMAT_R32_FLOAT, FALSE, FALSE);
+ FORMAT_CASE(PIPE_FORMAT_X8Z24_UNORM, TRUE, FALSE);
+ FORMAT_CASE(PIPE_FORMAT_S8X24_UINT, FALSE, FALSE);
+ FORMAT_CASE(PIPE_FORMAT_DXT1_RGB, TRUE, FALSE);
+ FORMAT_CASE(PIPE_FORMAT_ETC2_RGB8, TRUE, FALSE);
+ FORMAT_CASE(PIPE_FORMAT_ETC2_R11_SNORM, FALSE, TRUE);
+ FORMAT_CASE(PIPE_FORMAT_ASTC_4x4, TRUE, FALSE);
+ FORMAT_CASE(PIPE_FORMAT_BPTC_RGBA_UNORM, TRUE, FALSE);
+ FORMAT_CASE(PIPE_FORMAT_BPTC_RGB_FLOAT, FALSE, FALSE);
+ default:
+ success = !(format_desc->is_unorm && format_desc->is_snorm);
+ break;
+ }
+#undef FORMAT_CASE
+
+ if (!success) {
+ printf("FAILED: %s (unorm %s, snorm %s)\n",
+ format_desc->short_name,
+ format_desc->is_unorm ? "yes" : "no",
+ format_desc->is_snorm ? "yes" : "no");
+ }
+
+ return success;
+}
+
typedef boolean
(*test_func_t)(const struct util_format_description *format_desc,
const struct util_format_test_case *test);
@@ -698,6 +739,22 @@ test_one_func(const struct util_format_description *format_desc,
return success;
}
+static boolean
+test_format_metadata(const struct util_format_description *format_desc,
+ boolean (*func)(const struct util_format_description *format_desc),
+ const char *suffix)
+{
+ boolean success = TRUE;
+
+ printf("Testing util_format_%s_%s ...\n", format_desc->short_name, suffix);
+ fflush(stdout);
+
+ if (!func(format_desc)) {
+ success = FALSE;
+ }
+
+ return success;
+}
static boolean
test_all(void)
@@ -724,6 +781,11 @@ test_all(void)
} \
}
+# define TEST_FORMAT_METADATA(name) \
+ if (!test_format_metadata(format_desc, &test_format_##name, #name)) { \
+ success = FALSE; \
+ } \
+
TEST_ONE_FUNC(fetch_rgba_float);
TEST_ONE_FUNC(pack_rgba_float);
TEST_ONE_FUNC(unpack_rgba_float);
@@ -737,7 +799,10 @@ test_all(void)
TEST_ONE_FUNC(unpack_s_8uint);
TEST_ONE_FUNC(pack_s_8uint);
+ TEST_FORMAT_METADATA(norm_flags);
+
# undef TEST_ONE_FUNC
+# undef TEST_ONE_FORMAT
}
return success;