From: Louis Chauvet <louis.chauvet@bootlin.com>
To: Haneen Mohammed <hamohammed.sa@gmail.com>,
Simona Vetter <simona@ffwll.ch>,
Melissa Wen <melissa.srw@gmail.com>,
Maarten Lankhorst <maarten.lankhorst@linux.intel.com>,
Maxime Ripard <mripard@kernel.org>,
Thomas Zimmermann <tzimmermann@suse.de>,
David Airlie <airlied@gmail.com>,
jose.exposito89@gmail.com, Jonathan Corbet <corbet@lwn.net>,
Shuah Khan <skhan@linuxfoundation.org>,
Miguel Ojeda <ojeda@kernel.org>,
Nathan Chancellor <nathan@kernel.org>,
Nick Desaulniers <nick.desaulniers+lkml@gmail.com>,
Bill Wendling <morbo@google.com>,
Justin Stitt <justinstitt@google.com>
Cc: victoria@system76.com, sebastian.wick@redhat.com,
victoria@system76.com, airlied@gmail.com,
thomas.petazzoni@bootlin.com, dri-devel@lists.freedesktop.org,
linux-kernel@vger.kernel.org, linux-doc@vger.kernel.org,
Louis Chauvet <louis.chauvet@bootlin.com>,
llvm@lists.linux.dev
Subject: [PATCH v4 22/37] drm/vkms: Introduce configfs for plane format
Date: Wed, 22 Apr 2026 18:48:19 +0200 [thread overview]
Message-ID: <20260422-vkms-all-config-v4-22-dbb52e9aadc3@bootlin.com> (raw)
In-Reply-To: <20260422-vkms-all-config-v4-0-dbb52e9aadc3@bootlin.com>
To allow the userspace to test many hardware configuration, introduce a
new interface to configure the available formats per planes. VKMS supports
multiple formats, so the userspace can choose any combination.
The supported formats are configured by writing the fourcc code in
supported_formats:
# enable AR24 format
echo '+AR24' > /config/vkms/DEVICE_1/planes/PLANE_1/supported_formats
# disable AR24 format
echo '-AR24' > /config/vkms/DEVICE_1/planes/PLANE_1/supported_formats
# enable all format supported by VKMS
echo '+*' > /config/vkms/DEVICE_1/planes/PLANE_1/supported_formats
# disable all formats
echo '-*' > /config/vkms/DEVICE_1/planes/PLANE_1/supported_formats
Signed-off-by: Louis Chauvet <louis.chauvet@bootlin.com>
---
Documentation/ABI/testing/configfs-vkms | 9 ++
Documentation/gpu/vkms.rst | 7 +-
drivers/gpu/drm/vkms/tests/Makefile | 3 +-
drivers/gpu/drm/vkms/tests/vkms_configfs_test.c | 102 +++++++++++++++++++++
drivers/gpu/drm/vkms/vkms_configfs.c | 113 ++++++++++++++++++++++++
drivers/gpu/drm/vkms/vkms_configfs.h | 4 +
6 files changed, 236 insertions(+), 2 deletions(-)
diff --git a/Documentation/ABI/testing/configfs-vkms b/Documentation/ABI/testing/configfs-vkms
index 97681108af1c..dae8b9e9d6bf 100644
--- a/Documentation/ABI/testing/configfs-vkms
+++ b/Documentation/ABI/testing/configfs-vkms
@@ -153,6 +153,15 @@ Description:
Default color range presented to userspace, same
values as supported_color_ranges.
+What: /sys/kernel/config/vkms/<device>/planes/<plane>/supported_formats
+Date: Nov 2025
+Contact: dri-devel@lists.freedesktop.org
+Description:
+ List of supported formats for this plane. To add a new
+ item, write its fourcc code prefixed with '+'. To remove,
+ use '-' prefix. Use '+*' to add all formats, '-*' to
+ remove all.
+
What: /sys/kernel/config/vkms/<device>/planes/<plane>/possible_crtcs
Date: Nov 2025
Contact: dri-devel@lists.freedesktop.org
diff --git a/Documentation/gpu/vkms.rst b/Documentation/gpu/vkms.rst
index 8ba0b0353376..94f7b0d85ca7 100644
--- a/Documentation/gpu/vkms.rst
+++ b/Documentation/gpu/vkms.rst
@@ -87,7 +87,7 @@ Start by creating one or more planes::
sudo mkdir /config/vkms/my-vkms/planes/plane0
-Planes have 8 configurable attributes:
+Planes have 9 configurable attributes:
- type: Plane type: 0 overlay, 1 primary, 2 cursor (same values as those
exposed by the "type" property of a plane)
@@ -109,6 +109,11 @@ Planes have 8 configurable attributes:
must be set too.
- default_color_range: Default color range presented to the userspace, same
values as supported_color_ranges
+- supported_formats: List of supported formats for this plane. To add a new item in the
+ list, write it using a plus and fourcc code: +XR24
+ To remove a format, use a minus and its fourcc: -XR24
+ To add all formats use +*
+ To remove all formats, use -*
Continue by creating one or more CRTCs::
diff --git a/drivers/gpu/drm/vkms/tests/Makefile b/drivers/gpu/drm/vkms/tests/Makefile
index d4d9ba8d4c54..92cfa7262ba4 100644
--- a/drivers/gpu/drm/vkms/tests/Makefile
+++ b/drivers/gpu/drm/vkms/tests/Makefile
@@ -3,6 +3,7 @@
vkms-kunit-tests-y := \
vkms_config_test.o \
vkms_format_test.o \
- vkms_color_test.o
+ vkms_color_test.o \
+ vkms_configfs_test.o \
obj-$(CONFIG_DRM_VKMS_KUNIT_TEST) += vkms-kunit-tests.o
diff --git a/drivers/gpu/drm/vkms/tests/vkms_configfs_test.c b/drivers/gpu/drm/vkms/tests/vkms_configfs_test.c
new file mode 100644
index 000000000000..8d02c2c459d9
--- /dev/null
+++ b/drivers/gpu/drm/vkms/tests/vkms_configfs_test.c
@@ -0,0 +1,102 @@
+// SPDX-License-Identifier: GPL-2.0+
+
+#include "linux/printk.h"
+#include <kunit/test.h>
+
+#include "../vkms_configfs.h"
+
+MODULE_IMPORT_NS("EXPORTED_FOR_KUNIT_TESTING");
+
+/**
+ * struct vkms_configfs_parse_format_case - Store test case for format parsing
+ * @str: Contains the string to parse
+ * @str_len: str len
+ * @expected_len: expected len of the matched format
+ * @expected_offset: expected offset in the string for the parsed format
+ */
+struct vkms_configfs_parse_format_case {
+ const char *str;
+ int str_len;
+ int expected_len;
+ int expected_offset;
+};
+
+struct vkms_configfs_parse_format_case vkms_configfs_parse_format_test_cases[] = {
+ {
+ .str = "+RG24",
+ .str_len = 6,
+ .expected_len = 5,
+ .expected_offset = 0,
+ }, {
+ .str = "-RG24",
+ .str_len = 6,
+ .expected_len = 5,
+ .expected_offset = 0
+ }, {
+ .str = " -RG24",
+ .str_len = 8,
+ .expected_len = 5,
+ .expected_offset = 2
+ }, {
+ .str = "+*",
+ .str_len = 3,
+ .expected_len = 2,
+ .expected_offset = 0
+ }, {
+ .str = "-RG24+RG24",
+ .str_len = 11,
+ .expected_len = 5,
+ .expected_offset = 0
+ }, {
+ .str = "-R1+RG24",
+ .str_len = 9,
+ .expected_len = 3,
+ .expected_offset = 0
+ }, {
+ .str = "\n-R1",
+ .str_len = 5,
+ .expected_len = 3,
+ .expected_offset = 1
+ }, {
+ .str = "-R1111",
+ .str_len = 3,
+ .expected_len = 3,
+ .expected_offset = 0
+ }
+};
+
+static void vkms_configfs_test_parse_format(struct kunit *test)
+{
+ const struct vkms_configfs_parse_format_case *param = test->param_value;
+ char *out;
+ int len = vkms_configfs_parse_next_format(param->str, param->str + param->str_len, &out);
+
+ KUNIT_EXPECT_EQ(test, len, param->expected_len);
+ KUNIT_EXPECT_PTR_EQ(test, out, param->str + param->expected_offset);
+}
+
+static void vkms_configfs_test_parse_format_get_desc(struct vkms_configfs_parse_format_case *t,
+ char *desc)
+{
+ snprintf(desc, KUNIT_PARAM_DESC_SIZE, "%s", t->str);
+}
+
+KUNIT_ARRAY_PARAM(vkms_configfs_test_parse_format, vkms_configfs_parse_format_test_cases,
+ vkms_configfs_test_parse_format_get_desc
+);
+
+static struct kunit_case vkms_configfs_test_cases[] = {
+ KUNIT_CASE_PARAM(vkms_configfs_test_parse_format,
+ vkms_configfs_test_parse_format_gen_params),
+ {}
+};
+
+static struct kunit_suite vkms_configfs_test_suite = {
+ .name = "vkms-configfs",
+ .test_cases = vkms_configfs_test_cases,
+};
+
+kunit_test_suite(vkms_configfs_test_suite);
+
+MODULE_LICENSE("GPL");
+MODULE_DESCRIPTION("Kunit test for vkms configfs utility");
diff --git a/drivers/gpu/drm/vkms/vkms_configfs.c b/drivers/gpu/drm/vkms/vkms_configfs.c
index 855b1d5f5d31..b38d724cfb94 100644
--- a/drivers/gpu/drm/vkms/vkms_configfs.c
+++ b/drivers/gpu/drm/vkms/vkms_configfs.c
@@ -3,6 +3,8 @@
#include <linux/configfs.h>
#include <linux/mutex.h>
#include <linux/slab.h>
+#include <linux/string.h>
+#include <kunit/visibility.h>
#include "vkms_drv.h"
#include "vkms_config.h"
@@ -636,6 +638,115 @@ static ssize_t plane_default_color_encoding_store(struct config_item *item,
return count;
}
+static ssize_t plane_supported_formats_show(struct config_item *item, char *page)
+{
+ struct vkms_configfs_plane *plane;
+
+ plane = plane_item_to_vkms_configfs_plane(item);
+
+ page[0] = '\0';
+
+ scoped_guard(mutex, &plane->dev->lock) {
+ u32 *formats = vkms_config_plane_get_supported_formats(plane->config);
+
+ for (int i = 0;
+ i < vkms_config_plane_get_supported_formats_count(plane->config);
+ i++) {
+ char tmp[6] = { 0 };
+ const ssize_t ret = snprintf(tmp, ARRAY_SIZE(tmp), "%.*s\n",
+ (int)sizeof(*formats),
+ (char *)&formats[i]);
+ if (ret < 0)
+ return ret;
+ /*
+ * Limitation of ConfigFS attributes, an attribute can't be bigger
+ * than PAGE_SIZE. This will crop the result if this plane support
+ * more than ≈1000 formats.
+ */
+ if (ret + strlen(page) > PAGE_SIZE - 1)
+ return -ENOMEM;
+ strncat(page, tmp, ARRAY_SIZE(tmp));
+ }
+ }
+
+ return strlen(page);
+}
+
+/**
+ * vkms_configfs_parse_next_format() - Parse the next format in page,
+ * skipping all non fourcc-related characters
+ * @page: page to search into
+ * @page_end: last character of the page
+ * @out: Output pointer, will point inside page
+ *
+ * Returns: size of the matched format, @out will point to the + or -
+ */
+VISIBLE_IF_KUNIT
+int vkms_configfs_parse_next_format(const char *page, const char *page_end, char **out)
+{
+ int count = page - page_end;
+ char *tmp_plus = strnchr(page, count, '+');
+ char *tmp_minus = strnchr(page, count, '-');
+
+ if (!tmp_plus && !tmp_minus)
+ return 0;
+ if (!tmp_plus)
+ *out = tmp_minus;
+ else if (!tmp_minus)
+ *out = tmp_plus;
+ else
+ *out = min(tmp_plus, tmp_minus);
+
+ char *end = *out + 1;
+
+ while (end < page_end) {
+ if (!isalnum(*end) && *end != '*')
+ break;
+ end++;
+ }
+
+ return end - *out;
+}
+EXPORT_SYMBOL_IF_KUNIT(vkms_configfs_parse_next_format);
+
+static ssize_t plane_supported_formats_store(struct config_item *item,
+ const char *page, size_t count)
+{
+ struct vkms_configfs_plane *plane;
+
+ plane = plane_item_to_vkms_configfs_plane(item);
+ int ret = 0;
+
+ if (count < 2 || count > 5)
+ return -EINVAL;
+
+ if (page[0] != '+' && page[0] != '-')
+ return -EINVAL;
+
+ if (page[1] == '*' && count != 2)
+ return -EINVAL;
+
+ scoped_guard(mutex, &plane->dev->lock) {
+ char fmt[4] = {' ', ' ', ' ', ' '};
+
+ memcpy(fmt, &page[1], min(count - 1, 4));
+
+ if (page[0] == '+' && page[1] == '*')
+ ret = vkms_config_plane_add_all_formats(plane->config);
+ else if (page[0] == '-' && page[1] == '*')
+ vkms_config_plane_remove_all_formats(plane->config);
+ else if (page[0] == '+')
+ ret = vkms_config_plane_add_format(plane->config, *(int *)fmt);
+ else if (page[0] == '-')
+ vkms_config_plane_remove_format(plane->config, *(int *)fmt);
+
+ if (ret)
+ return ret;
+ }
+
+ return count;
+}
+
CONFIGFS_ATTR(plane_, type);
CONFIGFS_ATTR(plane_, name);
CONFIGFS_ATTR(plane_, supported_rotations);
@@ -644,6 +755,7 @@ CONFIGFS_ATTR(plane_, supported_color_ranges);
CONFIGFS_ATTR(plane_, default_color_range);
CONFIGFS_ATTR(plane_, supported_color_encodings);
CONFIGFS_ATTR(plane_, default_color_encoding);
+CONFIGFS_ATTR(plane_, supported_formats);
static struct configfs_attribute *plane_item_attrs[] = {
&plane_attr_type,
@@ -654,6 +766,7 @@ static struct configfs_attribute *plane_item_attrs[] = {
&plane_attr_default_color_range,
&plane_attr_supported_color_encodings,
&plane_attr_default_color_encoding,
+ &plane_attr_supported_formats,
NULL,
};
diff --git a/drivers/gpu/drm/vkms/vkms_configfs.h b/drivers/gpu/drm/vkms/vkms_configfs.h
index e9020b0043db..73be660412ca 100644
--- a/drivers/gpu/drm/vkms/vkms_configfs.h
+++ b/drivers/gpu/drm/vkms/vkms_configfs.h
@@ -5,4 +5,8 @@
int vkms_configfs_register(void);
void vkms_configfs_unregister(void);
+#if IS_ENABLED(CONFIG_KUNIT)
+int vkms_configfs_parse_next_format(const char *page, const char *end_page, char **out);
+#endif
+
#endif /* _VKMS_CONFIGFS_H_ */
--
2.54.0
next prev parent reply other threads:[~2026-04-22 16:49 UTC|newest]
Thread overview: 39+ messages / expand[flat|nested] mbox.gz Atom feed top
2026-04-22 16:47 [PATCH v4 00/37] VKMS: Introduce multiple configFS attributes Louis Chauvet
2026-04-22 16:47 ` [PATCH v4 01/37] drm/drm_mode_config: Add helper to get plane type name Louis Chauvet
2026-04-22 16:47 ` [PATCH v4 02/37] drm/blend: Get a rotation name from it's bitfield Louis Chauvet
2026-04-22 16:52 ` Ville Syrjälä
2026-04-22 16:48 ` [PATCH v4 03/37] drm/drm_color_mgmt: Expose drm_get_color_encoding_name Louis Chauvet
2026-04-22 16:48 ` [PATCH v4 04/37] drm/drm_color_mgmt: Expose drm_get_color_range_name Louis Chauvet
2026-04-22 16:48 ` [PATCH v4 05/37] drm/connector: Export drm_get_colorspace_name Louis Chauvet
2026-04-22 16:48 ` [PATCH v4 06/37] drm/drm_atomic_state_helper: Properly load default value for rotation Louis Chauvet
2026-04-22 16:48 ` [PATCH v4 07/37] Documentation: ABI: vkms: Add current VKMS ABI documentation Louis Chauvet
2026-04-22 16:48 ` [PATCH v4 08/37] drm/vkms: Add error handling in plane config creation Louis Chauvet
2026-04-22 16:48 ` [PATCH v4 09/37] drm/vkms: Simplify plane_release code Louis Chauvet
2026-04-22 16:48 ` [PATCH v4 10/37] drm/vkms: Explicitly display plane type Louis Chauvet
2026-04-22 16:48 ` [PATCH v4 11/37] drm/vkms: Use enabled/disabled instead of 1/0 for debug Louis Chauvet
2026-04-22 16:48 ` [PATCH v4 12/37] drm/vkms: Explicitly display connector status Louis Chauvet
2026-04-22 16:48 ` [PATCH v4 13/37] drm/vkms: Introduce config for plane name Louis Chauvet
2026-04-22 16:48 ` [PATCH v4 14/37] drm/vkms: Introduce configfs " Louis Chauvet
2026-04-22 16:48 ` [PATCH v4 15/37] drm/vkms: Introduce config for plane rotation Louis Chauvet
2026-04-22 16:48 ` [PATCH v4 16/37] drm/vkms: Introduce configfs " Louis Chauvet
2026-04-22 16:48 ` [PATCH v4 17/37] drm/vkms: Introduce config for plane color encoding Louis Chauvet
2026-04-22 16:48 ` [PATCH v4 18/37] drm/vkms: Introduce configfs " Louis Chauvet
2026-04-22 16:48 ` [PATCH v4 19/37] drm/vkms: Introduce config for plane color range Louis Chauvet
2026-04-22 16:48 ` [PATCH v4 20/37] drm/vkms: Introduce configfs " Louis Chauvet
2026-04-22 16:48 ` [PATCH v4 21/37] drm/vkms: Introduce config for plane format Louis Chauvet
2026-04-22 16:48 ` Louis Chauvet [this message]
2026-04-22 16:48 ` [PATCH v4 23/37] drm/vkms: Properly render plane using their zpos Louis Chauvet
2026-04-22 16:48 ` [PATCH v4 24/37] drm/vkms: Introduce config for plane zpos property Louis Chauvet
2026-04-22 16:48 ` [PATCH v4 25/37] drm/vkms: Introduce configfs " Louis Chauvet
2026-04-22 16:48 ` [PATCH v4 26/37] drm/vkms: Introduce config for connector type Louis Chauvet
2026-04-22 16:48 ` [PATCH v4 27/37] drm/vkms: Introduce configfs " Louis Chauvet
2026-04-22 16:48 ` [PATCH v4 28/37] drm/vkms: Rename vkms_connector_init to vkms_connector_init_static Louis Chauvet
2026-04-22 16:48 ` [PATCH v4 29/37] drm/vkms: Introduce config for connector supported colorspace Louis Chauvet
2026-04-22 16:48 ` [PATCH v4 30/37] drm/vkms: Introduce configfs " Louis Chauvet
2026-04-22 16:48 ` [PATCH v4 31/37] drm/vkms: Introduce config for connector EDID Louis Chauvet
2026-04-22 16:48 ` [PATCH v4 32/37] drm/vkms: Introduce configfs " Louis Chauvet
2026-04-22 16:48 ` [PATCH v4 33/37] drm/vkms: Store the enabled/disabled status for connector Louis Chauvet
2026-04-22 16:48 ` [PATCH v4 34/37] drm/vkms: Allow to hot-add connectors Louis Chauvet
2026-04-22 16:48 ` [PATCH v4 35/37] drm/vkms: Introduce configfs for dynamic connector creation Louis Chauvet
2026-04-22 16:48 ` [PATCH v4 36/37] drm/vkms: Add connector parent configuration in vkms_config Louis Chauvet
2026-04-22 16:48 ` [PATCH v4 37/37] drm/vkms: Add ConfigFS interface for connector parent and port_id Louis Chauvet
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20260422-vkms-all-config-v4-22-dbb52e9aadc3@bootlin.com \
--to=louis.chauvet@bootlin.com \
--cc=airlied@gmail.com \
--cc=corbet@lwn.net \
--cc=dri-devel@lists.freedesktop.org \
--cc=hamohammed.sa@gmail.com \
--cc=jose.exposito89@gmail.com \
--cc=justinstitt@google.com \
--cc=linux-doc@vger.kernel.org \
--cc=linux-kernel@vger.kernel.org \
--cc=llvm@lists.linux.dev \
--cc=maarten.lankhorst@linux.intel.com \
--cc=melissa.srw@gmail.com \
--cc=morbo@google.com \
--cc=mripard@kernel.org \
--cc=nathan@kernel.org \
--cc=nick.desaulniers+lkml@gmail.com \
--cc=ojeda@kernel.org \
--cc=sebastian.wick@redhat.com \
--cc=simona@ffwll.ch \
--cc=skhan@linuxfoundation.org \
--cc=thomas.petazzoni@bootlin.com \
--cc=tzimmermann@suse.de \
--cc=victoria@system76.com \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox