Skip to content

Commit

Permalink
vkd3d: Add workaround to explicitly clear memory on 6.10+ amdgpu.
Browse files Browse the repository at this point in the history
It seems like there is a bug with the new zerovram code in kernel.
Manifests as test failures in specific circumstances.

Signed-off-by: Hans-Kristian Arntzen <[email protected]>
  • Loading branch information
HansKristian-Work committed Dec 4, 2024
1 parent f97a7f6 commit 5645ca1
Show file tree
Hide file tree
Showing 3 changed files with 34 additions and 0 deletions.
28 changes: 28 additions & 0 deletions libs/vkd3d/device.c
Original file line number Diff line number Diff line change
Expand Up @@ -2998,6 +2998,32 @@ static HRESULT vkd3d_select_queues(const struct d3d12_device *device,
return S_OK;
}

static void d3d12_device_init_workarounds(struct d3d12_device *device)
{
uint32_t major, minor, patch;

if (vkd3d_config_flags & VKD3D_CONFIG_FLAG_SKIP_DRIVER_WORKAROUNDS)
return;

if (device->device_info.properties2.properties.vendorID != 0x1002)
return;

if (vkd3d_get_linux_kernel_version(&major, &minor, &patch))
{
/* 6.10 amdgpu kernel changes the clear vram code to do background clears instead
* of on-demand clearing. This seems to have bugs, and we have been able to observe
* non-zeroed VRAM coming from the affected kernels.
* This workaround needs to be in place until we have confirmed a fix in upstream kernel. */
INFO("Detected Linux kernel version %u.%u.%u\n", major, minor, patch);

if (major > 6 || (major == 6 && minor >= 10))
{
INFO("AMDGPU broken kernel detected. Enabling manual memory clearing path.\n");
device->workarounds.amdgpu_broken_clearvram = true;
}
}
}

static HRESULT vkd3d_create_vk_device(struct d3d12_device *device,
const struct vkd3d_device_create_info *create_info)
{
Expand Down Expand Up @@ -3136,6 +3162,8 @@ static HRESULT vkd3d_create_vk_device(struct d3d12_device *device,
device->vk_info.extension_count = device_info.enabledExtensionCount;
device->vk_info.extension_names = extensions;

d3d12_device_init_workarounds(device);

TRACE("Created Vulkan device %p.\n", vk_device);

return hr;
Expand Down
1 change: 1 addition & 0 deletions libs/vkd3d/memory.c
Original file line number Diff line number Diff line change
Expand Up @@ -1892,6 +1892,7 @@ HRESULT vkd3d_allocate_memory(struct d3d12_device *device, struct vkd3d_memory_a
* RADV definitely does this, and it seems like NV also does it.
* TODO: an extension for this would be nice. */
implementation_implicitly_clears =
!device->workarounds.amdgpu_broken_clearvram &&
vkd3d_driver_implicitly_clears(device->device_info.vulkan_1_2_properties.driverID) &&
!suballocate;

Expand Down
5 changes: 5 additions & 0 deletions libs/vkd3d/vkd3d_private.h
Original file line number Diff line number Diff line change
Expand Up @@ -4980,6 +4980,11 @@ struct d3d12_device

struct vkd3d_device_swapchain_info swapchain_info;
struct vkd3d_device_frame_markers frame_markers;

struct
{
bool amdgpu_broken_clearvram;
} workarounds;
};

HRESULT d3d12_device_create(struct vkd3d_instance *instance,
Expand Down

0 comments on commit 5645ca1

Please sign in to comment.