radv: Add KHR_display extension to radv [v5]
authorKeith Packard <keithp@keithp.com>
Wed, 7 Feb 2018 18:31:44 +0000 (10:31 -0800)
committerKeith Packard <keithp@keithp.com>
Tue, 19 Jun 2018 21:17:46 +0000 (14:17 -0700)
This adds support for the KHR_display extension to the radv Vulkan
driver. The driver now attempts to open the master DRM node when the
KHR_display extension is requested so that the common winsys code can
perform the necessary operations.

v2:
* Simplify addition of VK_USE_PLATFORM_DISPLAY_KHR to
          vulkan_wsi_args

Suggested-by: Eric Engestrom <eric.engestrom@imgtec.com>
v3:
Adapt to new wsi_device_init API (added display_fd)

v4:
Adopt Jason Ekstrand's coding conventions

Declare variables at first use, eliminate extra whitespace
between types and names. Wrap lines to 80 columns.

Suggested-by: Jason Ekstrand <jason.ekstrand@intel.com>
v5:
Add vkCreateDisplayModeKHR. This doesn't actually create
new modes, it only looks to see if the requested parameters
matches an existing mode and returns that.

Suggested-by: Jason Ekstrand <jason.ekstrand@intel.com>
Signed-off-by: Keith Packard <keithp@keithp.com>
Reviewed-by: Jason Ekstrand <jason@jlekstrand.net>
src/amd/vulkan/Makefile.am
src/amd/vulkan/Makefile.sources
src/amd/vulkan/meson.build
src/amd/vulkan/radv_device.c
src/amd/vulkan/radv_extensions.py
src/amd/vulkan/radv_private.h
src/amd/vulkan/radv_wsi_display.c [new file with mode: 0644]

index 18f263ab44746f6fe095246aa5ab6d51af4c7740..f4f994002757033c99cb8e9fe9214d6c5540c995 100644 (file)
@@ -80,6 +80,14 @@ VULKAN_LIB_DEPS = \
        $(DLOPEN_LIBS) \
        -lm
 
+if HAVE_PLATFORM_DRM
+AM_CPPFLAGS += \
+       -DVK_USE_PLATFORM_DISPLAY_KHR
+
+VULKAN_SOURCES += $(VULKAN_WSI_DISPLAY_FILES)
+
+endif
+
 if HAVE_PLATFORM_X11
 AM_CPPFLAGS += \
        $(XCB_DRI3_CFLAGS) \
index ccb956a23965cb4d5f559a93482c55407ab73f0a..70d56e88cb306fdf547a5555cb68cbd282bbcf87 100644 (file)
@@ -80,6 +80,9 @@ VULKAN_WSI_WAYLAND_FILES := \
 VULKAN_WSI_X11_FILES := \
        radv_wsi_x11.c
 
+VULKAN_WSI_DISPLAY_FILES := \
+       radv_wsi_display.c
+
 VULKAN_GENERATED_FILES := \
        radv_entrypoints.c \
        radv_entrypoints.h \
index b5a99fe91e126bd002b1e2c3582b8f2e22998056..15e69d582dd2468ddd0d92bb780dfba78eecbad6 100644 (file)
@@ -115,6 +115,11 @@ if with_platform_wayland
   libradv_files += files('radv_wsi_wayland.c')
 endif
 
+if with_platform_drm
+  radv_flags += '-DVK_USE_PLATFORM_DISPLAY_KHR'
+  libradv_files += files('radv_wsi_display.c')
+endif
+
 libvulkan_radeon = shared_library(
   'vulkan_radeon',
   [libradv_files, radv_entrypoints, radv_extensions_c, vk_format_table_c],
index 056043a9169755d48f193674e126442e41356a35..ffeb6450b331702d8de6e0159de3738e14b7644a 100644 (file)
@@ -274,6 +274,23 @@ radv_physical_device_init(struct radv_physical_device *device,
                goto fail;
        }
 
+       if (instance->enabled_extensions.KHR_display) {
+               master_fd = open(drm_device->nodes[DRM_NODE_PRIMARY], O_RDWR | O_CLOEXEC);
+               if (master_fd >= 0) {
+                       uint32_t accel_working = 0;
+                       struct drm_amdgpu_info request = {
+                               .return_pointer = (uintptr_t)&accel_working,
+                               .return_size = sizeof(accel_working),
+                               .query = AMDGPU_INFO_ACCEL_WORKING
+                       };
+
+                       if (drmCommandWrite(master_fd, DRM_AMDGPU_INFO, &request, sizeof (struct drm_amdgpu_info)) < 0 || !accel_working) {
+                               close(master_fd);
+                               master_fd = -1;
+                       }
+               }
+       }
+
        device->master_fd = master_fd;
        device->local_fd = fd;
        device->ws->query_info(device->ws, &device->rad_info);
index a5b5a8dc34eba5b76d4569a1654053339e68bea2..6f4fc71bfd8077b3a97f217e1cd5806544f12813 100644 (file)
@@ -86,6 +86,7 @@ EXTENSIONS = [
     Extension('VK_KHR_xcb_surface',                       6, 'VK_USE_PLATFORM_XCB_KHR'),
     Extension('VK_KHR_xlib_surface',                      6, 'VK_USE_PLATFORM_XLIB_KHR'),
     Extension('VK_KHR_multiview',                         1, True),
+    Extension('VK_KHR_display',                          23, 'VK_USE_PLATFORM_DISPLAY_KHR'),
     Extension('VK_EXT_debug_report',                      9, True),
     Extension('VK_EXT_depth_range_unrestricted',          1, True),
     Extension('VK_EXT_descriptor_indexing',               2, True),
@@ -214,7 +215,7 @@ _TEMPLATE_C = Template(COPYRIGHT + """
 #include "vk_util.h"
 
 /* Convert the VK_USE_PLATFORM_* defines to booleans */
-%for platform in ['ANDROID', 'WAYLAND', 'XCB', 'XLIB']:
+%for platform in ['ANDROID', 'WAYLAND', 'XCB', 'XLIB', 'DISPLAY']:
 #ifdef VK_USE_PLATFORM_${platform}_KHR
 #   undef VK_USE_PLATFORM_${platform}_KHR
 #   define VK_USE_PLATFORM_${platform}_KHR true
@@ -233,7 +234,9 @@ _TEMPLATE_C = Template(COPYRIGHT + """
 
 #define RADV_HAS_SURFACE (VK_USE_PLATFORM_WAYLAND_KHR || \\
                          VK_USE_PLATFORM_XCB_KHR || \\
-                         VK_USE_PLATFORM_XLIB_KHR)
+                         VK_USE_PLATFORM_XLIB_KHR || \\
+                         VK_USE_PLATFORM_DISPLAY_KHR)
+
 
 const VkExtensionProperties radv_instance_extensions[RADV_INSTANCE_EXTENSION_COUNT] = {
 %for ext in instance_extensions:
index a76d771e4a577acb7e6d6bcfd241dc3e22c63534..abaf2eb929a58698d1cc2ff1a69ec8e4f4342f8f 100644 (file)
@@ -79,6 +79,7 @@ typedef uint32_t xcb_window_t;
 #include "radv_entrypoints.h"
 
 #include "wsi_common.h"
+#include "wsi_common_display.h"
 
 #define ATI_VENDOR_ID 0x1002
 
diff --git a/src/amd/vulkan/radv_wsi_display.c b/src/amd/vulkan/radv_wsi_display.c
new file mode 100644 (file)
index 0000000..048d992
--- /dev/null
@@ -0,0 +1,155 @@
+/*
+ * Copyright © 2017 Keith Packard
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that copyright
+ * notice and this permission notice appear in supporting documentation, and
+ * that the name of the copyright holders not be used in advertising or
+ * publicity pertaining to distribution of the software without specific,
+ * written prior permission.  The copyright holders make no representations
+ * about the suitability of this software for any purpose.  It is provided "as
+ * is" without express or implied warranty.
+ *
+ * THE COPYRIGHT HOLDERS DISCLAIM ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
+ * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO
+ * EVENT SHALL THE COPYRIGHT HOLDERS BE LIABLE FOR ANY SPECIAL, INDIRECT OR
+ * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
+ * DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
+ * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE
+ * OF THIS SOFTWARE.
+ */
+
+#include <stdbool.h>
+#include <string.h>
+#include <unistd.h>
+#include <fcntl.h>
+#include "radv_private.h"
+#include "radv_cs.h"
+#include "util/disk_cache.h"
+#include "util/strtod.h"
+#include "vk_util.h"
+#include <xf86drm.h>
+#include <xf86drmMode.h>
+#include <amdgpu.h>
+#include <amdgpu_drm.h>
+#include "winsys/amdgpu/radv_amdgpu_winsys_public.h"
+#include "ac_llvm_util.h"
+#include "vk_format.h"
+#include "sid.h"
+#include "util/debug.h"
+#include "wsi_common_display.h"
+
+#define MM_PER_PIXEL     (1.0/96.0 * 25.4)
+
+VkResult
+radv_GetPhysicalDeviceDisplayPropertiesKHR(VkPhysicalDevice physical_device,
+                                           uint32_t *property_count,
+                                           VkDisplayPropertiesKHR *properties)
+{
+       RADV_FROM_HANDLE(radv_physical_device, pdevice, physical_device);
+
+       return wsi_display_get_physical_device_display_properties(
+               physical_device,
+               &pdevice->wsi_device,
+               property_count,
+               properties);
+}
+
+VkResult
+radv_GetPhysicalDeviceDisplayPlanePropertiesKHR(
+       VkPhysicalDevice physical_device,
+       uint32_t *property_count,
+       VkDisplayPlanePropertiesKHR *properties)
+{
+       RADV_FROM_HANDLE(radv_physical_device, pdevice, physical_device);
+
+       return wsi_display_get_physical_device_display_plane_properties(
+               physical_device,
+               &pdevice->wsi_device,
+               property_count,
+               properties);
+}
+
+VkResult
+radv_GetDisplayPlaneSupportedDisplaysKHR(VkPhysicalDevice physical_device,
+                                         uint32_t plane_index,
+                                         uint32_t *display_count,
+                                         VkDisplayKHR *displays)
+{
+       RADV_FROM_HANDLE(radv_physical_device, pdevice, physical_device);
+
+       return wsi_display_get_display_plane_supported_displays(
+               physical_device,
+               &pdevice->wsi_device,
+               plane_index,
+               display_count,
+               displays);
+}
+
+
+VkResult
+radv_GetDisplayModePropertiesKHR(VkPhysicalDevice physical_device,
+                                 VkDisplayKHR display,
+                                 uint32_t *property_count,
+                                 VkDisplayModePropertiesKHR *properties)
+{
+       RADV_FROM_HANDLE(radv_physical_device, pdevice, physical_device);
+
+       return wsi_display_get_display_mode_properties(physical_device,
+                                                      &pdevice->wsi_device,
+                                                      display,
+                                                      property_count,
+                                                      properties);
+}
+
+VkResult
+radv_CreateDisplayModeKHR(VkPhysicalDevice physical_device,
+                          VkDisplayKHR display,
+                          const VkDisplayModeCreateInfoKHR *create_info,
+                          const VkAllocationCallbacks *allocator,
+                          VkDisplayModeKHR *mode)
+{
+       RADV_FROM_HANDLE(radv_physical_device, pdevice, physical_device);
+
+       return wsi_display_create_display_mode(physical_device,
+                                              &pdevice->wsi_device,
+                                              display,
+                                              create_info,
+                                              allocator,
+                                              mode);
+}
+
+VkResult
+radv_GetDisplayPlaneCapabilitiesKHR(VkPhysicalDevice physical_device,
+                                    VkDisplayModeKHR mode_khr,
+                                    uint32_t plane_index,
+                                    VkDisplayPlaneCapabilitiesKHR *capabilities)
+{
+       RADV_FROM_HANDLE(radv_physical_device, pdevice, physical_device);
+
+       return wsi_get_display_plane_capabilities(physical_device,
+                                                 &pdevice->wsi_device,
+                                                 mode_khr,
+                                                 plane_index,
+                                                 capabilities);
+}
+
+VkResult
+radv_CreateDisplayPlaneSurfaceKHR(
+       VkInstance _instance,
+       const VkDisplaySurfaceCreateInfoKHR *create_info,
+       const VkAllocationCallbacks *allocator,
+       VkSurfaceKHR *surface)
+{
+       RADV_FROM_HANDLE(radv_instance, instance, _instance);
+       const VkAllocationCallbacks *alloc;
+
+       if (allocator)
+               alloc = allocator;
+       else
+               alloc = &instance->alloc;
+
+       return wsi_create_display_surface(_instance, alloc,
+                                         create_info, surface);
+}