[PATCH i-g-t v5 03/10] tests/imagination: Add DEV_QUERY tests
Robert Mazur <[email protected]> Tue, 28 Jul 2026 09:18:58 +0200
| Newsgroups | org.freedesktop.lists.igt-dev |
|---|---|
| Message-ID | <20260728-test-imagination-add-support-v5-3-33049f0d1937@imgtec.com> |
From: Donald Robson <[email protected]> Add subtests exercising DRM_IOCTL_PVR_DEV_QUERY with invalid type, successful query of all types, and undersized buffer error paths. Signed-off-by: Donald Robson <[email protected]> Signed-off-by: Robert Mazur <[email protected]> --- lib/igt_pvr.c | 31 ++++++++++++ lib/igt_pvr.h | 4 ++ tests/imagination/meson.build | 3 +- tests/imagination/pvr_dev_query.c | 99 +++++++++++++++++++++++++++++++++++++++ 4 files changed, 136 insertions(+), 1 deletion(-) diff --git a/lib/igt_pvr.c b/lib/igt_pvr.c index 048ccab31..2e6c4ade3 100644 --- a/lib/igt_pvr.c +++ b/lib/igt_pvr.c @@ -73,3 +73,34 @@ off_t igt_pvr_ioctl_get_bo_mmap_offset(int fd, uint32_t handle) return (off_t)arg.offset; } + +/** + * igt_pvr_ioctl_dev_query: + * @fd: The file descriptor of the DRM device. + * @type: The type of the device query. + * @size: The size of the query structure. + * @pointer: Pointer to the query structure. + * @expect_err: Expected error code, or 0 if no error is expected. + * + * Function to perform a device query. + * + * Returns: The filled-in query arguments structure. + */ +struct drm_pvr_ioctl_dev_query_args +igt_pvr_ioctl_dev_query(int fd, enum drm_pvr_dev_query type, uint64_t size, + void *pointer, int expect_err) +{ + struct drm_pvr_ioctl_dev_query_args args = { + .type = type, + .size = size, + .pointer = to_user_pointer(pointer), + }; + + if (expect_err) + do_ioctl_err(fd, DRM_IOCTL_PVR_DEV_QUERY, &args, expect_err); + else + do_ioctl(fd, DRM_IOCTL_PVR_DEV_QUERY, &args); + + return args; +} + diff --git a/lib/igt_pvr.h b/lib/igt_pvr.h index e8b2d9026..b25fb1867 100644 --- a/lib/igt_pvr.h +++ b/lib/igt_pvr.h @@ -13,4 +13,8 @@ uint32_t igt_pvr_ioctl_create_bo(int fd, size_t *size); off_t igt_pvr_ioctl_get_bo_mmap_offset(int fd, uint32_t handle); +struct drm_pvr_ioctl_dev_query_args +igt_pvr_ioctl_dev_query(int fd, enum drm_pvr_dev_query type, uint64_t size, + void *pointer, int expect_err); + #endif /* IGT_PVR_H */ diff --git a/tests/imagination/meson.build b/tests/imagination/meson.build index 65b90c39f..62930da2b 100644 --- a/tests/imagination/meson.build +++ b/tests/imagination/meson.build @@ -1,4 +1,5 @@ -pvr_progs = [ 'pvr_gem', +pvr_progs = [ 'pvr_dev_query', + 'pvr_gem', ] pvr_deps = test_deps diff --git a/tests/imagination/pvr_dev_query.c b/tests/imagination/pvr_dev_query.c new file mode 100644 index 000000000..29c7eb550 --- /dev/null +++ b/tests/imagination/pvr_dev_query.c @@ -0,0 +1,99 @@ +// SPDX-License-Identifier: GPL-2.0 or MIT +/* Copyright (c) 2026 Imagination Technologies Ltd. All Rights Reserved */ + +#include <errno.h> +#include <stdint.h> +#include <unistd.h> + +#include "igt.h" +#include "igt_pvr.h" + +#include "pvr_drm.h" + +int igt_main() +{ + const enum drm_pvr_dev_query types[] = { + DRM_PVR_DEV_QUERY_GPU_INFO_GET, + DRM_PVR_DEV_QUERY_RUNTIME_INFO_GET, + DRM_PVR_DEV_QUERY_QUIRKS_GET, + DRM_PVR_DEV_QUERY_ENHANCEMENTS_GET, + DRM_PVR_DEV_QUERY_HEAP_INFO_GET, + DRM_PVR_DEV_QUERY_STATIC_DATA_AREAS_GET, + }; + + const uint64_t sizes[] = { + [DRM_PVR_DEV_QUERY_GPU_INFO_GET] = + sizeof(struct drm_pvr_dev_query_gpu_info), + [DRM_PVR_DEV_QUERY_RUNTIME_INFO_GET] = + sizeof(struct drm_pvr_dev_query_runtime_info), + [DRM_PVR_DEV_QUERY_QUIRKS_GET] = + sizeof(struct drm_pvr_dev_query_quirks), + [DRM_PVR_DEV_QUERY_ENHANCEMENTS_GET] = + sizeof(struct drm_pvr_dev_query_enhancements), + [DRM_PVR_DEV_QUERY_HEAP_INFO_GET] = + sizeof(struct drm_pvr_dev_query_heap_info), + [DRM_PVR_DEV_QUERY_STATIC_DATA_AREAS_GET] = + sizeof(struct drm_pvr_dev_query_static_data_areas), + }; + + struct drm_pvr_dev_query_gpu_info gpu_info = {0}; + struct drm_pvr_dev_query_runtime_info runtime_info = {0}; + struct drm_pvr_dev_query_quirks quirks = {0}; + struct drm_pvr_dev_query_enhancements enhancements = {0}; + struct drm_pvr_dev_query_heap_info heap_info = {0}; + struct drm_pvr_dev_query_static_data_areas static_data_areas = {0}; + + void *const containers[] = { + [DRM_PVR_DEV_QUERY_GPU_INFO_GET] = &gpu_info, + [DRM_PVR_DEV_QUERY_RUNTIME_INFO_GET] = &runtime_info, + [DRM_PVR_DEV_QUERY_QUIRKS_GET] = &quirks, + [DRM_PVR_DEV_QUERY_ENHANCEMENTS_GET] = &enhancements, + [DRM_PVR_DEV_QUERY_HEAP_INFO_GET] = &heap_info, + [DRM_PVR_DEV_QUERY_STATIC_DATA_AREAS_GET] = &static_data_areas, + }; + + int fd; + + static_assert(ARRAY_SIZE(types) == ARRAY_SIZE(sizes)); + static_assert(ARRAY_SIZE(types) == ARRAY_SIZE(containers)); + + igt_fixture() + { + fd = drm_open_driver(DRIVER_POWERVR); + + for (int i = 0; i < ARRAY_SIZE(types); i++) + memset(containers[i], 0, sizes[i]); + } + + igt_describe("Test invalid dev query"); + igt_subtest("dev-query-invalid") { + igt_pvr_ioctl_dev_query(fd, (enum drm_pvr_dev_query)-1, 0, NULL, + EINVAL); + } + + igt_describe("Test valid dev query"); + igt_subtest("dev-query-success-all") { + for (int i = 0; i < ARRAY_SIZE(types); i++) { + struct drm_pvr_ioctl_dev_query_args args = + igt_pvr_ioctl_dev_query(fd, types[i], 0, NULL, 0); + + igt_assert(args.size); + igt_assert(args.size <= sizes[i]); + + igt_pvr_ioctl_dev_query(fd, types[i], args.size, containers[i], 0); + } + } + + igt_describe("Test dev query with too small size"); + igt_subtest("dev-query-fail-too-small") { + for (int i = 0; i < ARRAY_SIZE(types); i++) { + igt_pvr_ioctl_dev_query(fd, types[i], 0, containers[i], EINVAL); + igt_pvr_ioctl_dev_query(fd, types[i], 1, containers[i], EINVAL); + } + } + + igt_fixture() + { + drm_close_driver(fd); + } +} -- 2.43.0