vulkan: Pull the device lost framework from ANV
It's a bit on the over-complicated side but the objective is to make the debug log messages show up in the same thread as the first VK_ERROR_DEVICE_LOST so we don't massively confuse the app. It's unknown if this is actually ever a problem but, with submit happening off on its own thread, logging errors from threads the client doesn't know about doesn't seem like a massively great plan. Reviewed-by: Lionel Landwerlin <lionel.g.landwerlin@intel.com> Acked-by: Bas Nieuwenhuizen <bas@basnieuwenhuizen.nl> Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/13427>
This commit is contained in:
parent
e6b4678fdb
commit
dd89ef96d7
|
@ -189,6 +189,10 @@ Core Mesa environment variables
|
|||
overrides the WSI present mode clients specify in
|
||||
``VkSwapchainCreateInfoKHR::presentMode``. Values can be ``fifo``,
|
||||
``relaxed``, ``mailbox`` or ``immediate``.
|
||||
:envvar:`MESA_VK_ABORT_ON_DEVICE_LOSS`
|
||||
causes the Vulkan driver to call abort() immediately after detecting a
|
||||
lost device. This is extremely useful when testing as it prevents the
|
||||
test suite from continuing on with a lost device.
|
||||
:envvar:`MESA_LOADER_DRIVER_OVERRIDE`
|
||||
chooses a different driver binary such as ``etnaviv`` or ``zink``.
|
||||
|
||||
|
|
|
@ -29,6 +29,7 @@
|
|||
#include "vk_physical_device.h"
|
||||
#include "vk_queue.h"
|
||||
#include "vk_util.h"
|
||||
#include "util/debug.h"
|
||||
#include "util/hash_table.h"
|
||||
#include "util/ralloc.h"
|
||||
|
||||
|
@ -117,6 +118,45 @@ vk_device_finish(UNUSED struct vk_device *device)
|
|||
vk_object_base_finish(&device->base);
|
||||
}
|
||||
|
||||
void
|
||||
_vk_device_report_lost(struct vk_device *device)
|
||||
{
|
||||
assert(p_atomic_read(&device->_lost.lost) > 0);
|
||||
|
||||
device->_lost.reported = true;
|
||||
|
||||
vk_foreach_queue(queue, device) {
|
||||
if (queue->_lost.lost) {
|
||||
__vk_errorf(queue, VK_ERROR_DEVICE_LOST,
|
||||
queue->_lost.error_file, queue->_lost.error_line,
|
||||
"%s", queue->_lost.error_msg);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
VkResult
|
||||
_vk_device_set_lost(struct vk_device *device,
|
||||
const char *file, int line,
|
||||
const char *msg, ...)
|
||||
{
|
||||
/* This flushes out any per-queue device lost messages */
|
||||
if (vk_device_is_lost(device))
|
||||
return VK_ERROR_DEVICE_LOST;
|
||||
|
||||
p_atomic_inc(&device->_lost.lost);
|
||||
device->_lost.reported = true;
|
||||
|
||||
va_list ap;
|
||||
va_start(ap, msg);
|
||||
__vk_errorv(device, VK_ERROR_DEVICE_LOST, file, line, msg, ap);
|
||||
va_end(ap);
|
||||
|
||||
if (env_var_as_boolean("MESA_VK_ABORT_ON_DEVICE_LOSS", false))
|
||||
abort();
|
||||
|
||||
return VK_ERROR_DEVICE_LOST;
|
||||
}
|
||||
|
||||
PFN_vkVoidFunction
|
||||
vk_device_get_proc_addr(const struct vk_device *device,
|
||||
const char *name)
|
||||
|
|
|
@ -28,6 +28,7 @@
|
|||
#include "vk_object.h"
|
||||
|
||||
#include "util/list.h"
|
||||
#include "util/u_atomic.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
|
@ -47,6 +48,11 @@ struct vk_device {
|
|||
|
||||
struct list_head queues;
|
||||
|
||||
struct {
|
||||
int lost;
|
||||
bool reported;
|
||||
} _lost;
|
||||
|
||||
#ifdef ANDROID
|
||||
mtx_t swapchain_private_mtx;
|
||||
struct hash_table *swapchain_private;
|
||||
|
@ -66,6 +72,31 @@ vk_device_init(struct vk_device *device,
|
|||
void
|
||||
vk_device_finish(struct vk_device *device);
|
||||
|
||||
VkResult PRINTFLIKE(4, 5)
|
||||
_vk_device_set_lost(struct vk_device *device,
|
||||
const char *file, int line,
|
||||
const char *msg, ...);
|
||||
|
||||
#define vk_device_set_lost(device, ...) \
|
||||
_vk_device_set_lost(device, __FILE__, __LINE__, __VA_ARGS__)
|
||||
|
||||
void _vk_device_report_lost(struct vk_device *device);
|
||||
|
||||
static inline bool
|
||||
vk_device_is_lost_no_report(struct vk_device *device)
|
||||
{
|
||||
return p_atomic_read(&device->_lost.lost) > 0;
|
||||
}
|
||||
|
||||
static inline bool
|
||||
vk_device_is_lost(struct vk_device *device)
|
||||
{
|
||||
int lost = vk_device_is_lost_no_report(device);
|
||||
if (unlikely(lost && !device->_lost.reported))
|
||||
_vk_device_report_lost(device);
|
||||
return lost;
|
||||
}
|
||||
|
||||
PFN_vkVoidFunction
|
||||
vk_device_get_proc_addr(const struct vk_device *device,
|
||||
const char *name);
|
||||
|
|
|
@ -23,6 +23,8 @@
|
|||
|
||||
#include "vk_queue.h"
|
||||
|
||||
#include "util/debug.h"
|
||||
|
||||
#include "vk_device.h"
|
||||
|
||||
VkResult
|
||||
|
@ -54,3 +56,30 @@ vk_queue_finish(struct vk_queue *queue)
|
|||
list_del(&queue->link);
|
||||
vk_object_base_finish(&queue->base);
|
||||
}
|
||||
|
||||
VkResult
|
||||
_vk_queue_set_lost(struct vk_queue *queue,
|
||||
const char *file, int line,
|
||||
const char *msg, ...)
|
||||
{
|
||||
if (queue->_lost.lost)
|
||||
return VK_ERROR_DEVICE_LOST;
|
||||
|
||||
queue->_lost.lost = true;
|
||||
queue->_lost.error_file = file;
|
||||
queue->_lost.error_line = line;
|
||||
|
||||
va_list ap;
|
||||
va_start(ap, msg);
|
||||
vsnprintf(queue->_lost.error_msg, sizeof(queue->_lost.error_msg), msg, ap);
|
||||
va_end(ap);
|
||||
|
||||
p_atomic_inc(&queue->base.device->_lost.lost);
|
||||
|
||||
if (env_var_as_boolean("MESA_VK_ABORT_ON_DEVICE_LOSS", false)) {
|
||||
_vk_device_report_lost(queue->base.device);
|
||||
abort();
|
||||
}
|
||||
|
||||
return VK_ERROR_DEVICE_LOST;
|
||||
}
|
||||
|
|
|
@ -48,6 +48,14 @@ struct vk_queue {
|
|||
/* Which queue this is within the queue family */
|
||||
uint32_t index_in_family;
|
||||
|
||||
struct {
|
||||
/* Only set once atomically by the queue */
|
||||
int lost;
|
||||
int error_line;
|
||||
const char *error_file;
|
||||
char error_msg[80];
|
||||
} _lost;
|
||||
|
||||
/**
|
||||
* VK_EXT_debug_utils
|
||||
*
|
||||
|
@ -99,6 +107,20 @@ vk_queue_init(struct vk_queue *queue, struct vk_device *device,
|
|||
void
|
||||
vk_queue_finish(struct vk_queue *queue);
|
||||
|
||||
VkResult PRINTFLIKE(4, 5)
|
||||
_vk_queue_set_lost(struct vk_queue *queue,
|
||||
const char *file, int line,
|
||||
const char *msg, ...);
|
||||
|
||||
#define vk_queue_set_lost(queue, ...) \
|
||||
_vk_queue_set_lost(queue, __FILE__, __LINE__, __VA_ARGS__)
|
||||
|
||||
static inline bool
|
||||
vk_queue_is_lost(struct vk_queue *queue)
|
||||
{
|
||||
return queue->_lost.lost;
|
||||
}
|
||||
|
||||
#define vk_foreach_queue(queue, device) \
|
||||
list_for_each_entry(struct vk_queue, queue, &(device)->queues, link)
|
||||
|
||||
|
|
Loading…
Reference in New Issue