CVE-2024-21979
An arbitrary write vulnerability exists in the Shader Functionality of AMD Radeon DirectX 11 Driver atidxx64.dll 31.0.21018.6011. A specially crafted executable/shader file can lead to an out-of-bounds write. An attacker can provide a specially crafted shader file to trigger this vulnerability.
The versions below were either tested or verified to be vulnerable by Talos or confirmed to be vulnerable by the vendor.
AMD Radeon DirectX 11 Driver atidxx64.dll 31.0.21018.6011
Radeon DirectX 11 Driver atidxx64.dll - https://amd.com
5.3 - CVSS:3.1/AV:L/AC:L/PR:L/UI:N/S:U/C:L/I:L/A:L
CWE-787 - Out-of-bounds Write
AMD Graphics drivers are software for AMD Graphics GPUs installed on a PC, used to communicate between the operating system and the GPU device. This software is required in most cases for the hardware device to function properly.
This vulnerability could be triggered from guest machines running virtualization environments (ie. VMware, qemu, VirtualBox, etc.) in order to perform guest-to-host escape (demonstrated before in TALOS-2018-0533, TALOS-2018-0568, etc.). Theoretically this vulnerability could also be triggered from a web browser (using webGL and webassembly). We have already demonstrated in previously reported bugs that such vulnerabilities could be triggered from HYPER-V guest using the RemoteFX feature, leading to executing the vulnerable code on the HYPER-V host (inside of the rdvgm.exe process). While the RemoteFX was recently deprecated by Microsoft, some older machines may still use this software.
This vulnerability can be triggered by supplying a malformed shader. This leads to a memory corruption problem in AMD driver.
Example of shader instruction triggering the bug:
store_uav_typed u[r+4503625397176231].xyzw, r0.yyyy
Vulnerable code:
00007FF9CD210C73 | 48:8B71 30 | mov rsi,qword ptr ds:[rcx+30] |
00007FF9CD210C77 | 48:8B69 08 | mov rbp,qword ptr ds:[rcx+8] |
00007FF9CD210C7B | 48:3BFE | cmp rdi,rsi |
00007FF9CD210C7E | 4C:8B71 10 | mov r14,qword ptr ds:[rcx+10] |
00007FF9CD210C82 | 48:0F43F7 | cmovae rsi,rdi |
00007FF9CD210C86 | 48:83C6 10 | add rsi,10 |
00007FF9CD210C8A | 48:8B8D D0010000 | mov rcx,qword ptr ss:[rbp+1D0] |
00007FF9CD210C91 | 8BD6 | mov edx,esi | truncating memory size to 32bit number!!!!
00007FF9CD210C93 | FF95 C8010000 | call qword ptr ss:[rbp+1C8] | RtlAllocateHeap()
00007FF9CD210C99 | 48:85C0 | test rax,rax |
00007FF9CD210C9C | 74 56 | je atidxx64.7FF9CD210CF4 |
00007FF9CD210C9E | 4C:8BC6 | mov r8,rsi | using 64bit number as size parameter (overflow)
00007FF9CD210CA1 | 48:8943 10 | mov qword ptr ds:[rbx+10],rax |
00007FF9CD210CA5 | 33D2 | xor edx,edx |
00007FF9CD210CA7 | 48:8BC8 | mov rcx,rax |
00007FF9CD210CAA | E8 C1925F00 | call atidxx64.7FF9CD809F70 | memset causing memory corruption
Where the size value is computed from the shader bytecode (in other words, an attacker can directly influence the size parameter from the RtlAllocateHeap and memset function).
0:000> !analyze -v
*******************************************************************************
* *
* Exception Analysis *
* *
*******************************************************************************
KEY_VALUES_STRING: 1
Key : AV.Fault
Value: Write
Key : Analysis.CPU.mSec
Value: 4906
Key : Analysis.Elapsed.mSec
Value: 10843
Key : Analysis.IO.Other.Mb
Value: 9
Key : Analysis.IO.Read.Mb
Value: 0
Key : Analysis.IO.Write.Mb
Value: 16
Key : Analysis.Init.CPU.mSec
Value: 483
Key : Analysis.Init.Elapsed.mSec
Value: 12460
Key : Analysis.Memory.CommitPeak.Mb
Value: 88
Key : Failure.Bucket
Value: INVALID_POINTER_WRITE_STRING_DEREFERENCE_c0000005_atidxx64.dll!Unknown
Key : Failure.Hash
Value: {fd0d2c7b-9b3d-0989-7368-90e576a2b965}
Key : Timeline.OS.Boot.DeltaSec
Value: 69308
Key : Timeline.Process.Start.DeltaSec
Value: 12
Key : WER.OS.Branch
Value: vb_release
Key : WER.OS.Version
Value: 10.0.19041.1
NTGLOBALFLAG: 70
APPLICATION_VERIFIER_FLAGS: 0
EXCEPTION_RECORD: (.exr -1)
ExceptionAddress: 00007ff9cd809f59 (atidxx64!AmdLiquidVrD3D11WrapDeviceContext+0x000000000007ff49)
ExceptionCode: c0000005 (Access violation)
ExceptionFlags: 00000000
NumberParameters: 2
Parameter[0]: 0000000000000001
Parameter[1]: 0000019b3d79b000
Attempt to write to address 0000019b3d79b000
FAULTING_THREAD: 00003340
PROCESS_NAME: POC_EXEC11.exe
WRITE_ADDRESS: 0000019b3d79b000
ERROR_CODE: (NTSTATUS) 0xc0000005 - The instruction at 0x%p referenced memory at 0x%p. The memory could not be %s.
EXCEPTION_CODE_STR: c0000005
EXCEPTION_PARAMETER1: 0000000000000001
EXCEPTION_PARAMETER2: 0000019b3d79b000
STACK_TEXT:
00000037`430f92e0 00007ff9`cd210caf : 0000019a`00000000 0000019a`7c48f8c0 0000019a`7c0f80a0 00007ff9`cd110000 : atidxx64!AmdLiquidVrD3D11WrapDeviceContext+0x7ff49
00000037`430f92f0 00007ff9`cd11a824 : 0000019a`7c0f9e80 00000000`00000030 00000000`7c0fa1b8 0000019a`7c0f9ef8 : atidxx64!AmdDxGsaFreeCompiledShader+0x46215f
00000037`430f9320 00007ff9`cd11a790 : 0000019a`7c0f9ef8 00000037`430f93c8 0000019a`7c0f9e80 00000000`00000000 : atidxx64!AmdDxGsaFreeCompiledShader+0x36bcd4
00000037`430f9380 00007ff9`cd114758 : 0000019a`7c0f9ef8 0000019a`7c0f9e80 00000000`00000000 0000019a`7c0e29d0 : atidxx64!AmdDxGsaFreeCompiledShader+0x36bc40
00000037`430f93c0 00007ff9`cd51bfeb : 0000019a`7c0f9e80 0000019a`7c01c4b0 0000019a`7c01c4b0 00000000`00000000 : atidxx64!AmdDxGsaFreeCompiledShader+0x365c08
00000037`430f93f0 00007ff9`cd51f851 : 0000019a`7c0e29d0 0000019a`00000000 0000019a`7c0f9d98 00000000`00000000 : atidxx64!AmdDxGsaFreeCompiledShader+0x76d49b
00000037`430f9460 00007ff9`cd51f25d : 0000019a`7c46f900 0000019a`7c46f928 0000019a`7c46fa28 00000000`00000000 : atidxx64!AmdDxGsaFreeCompiledShader+0x770d01
00000037`430f94e0 00007ff9`ccf04540 : 0000019a`7c01c4b0 0000019a`7c46f928 0000019a`7c0e4478 0000019a`7c0f5ad8 : atidxx64!AmdDxGsaFreeCompiledShader+0x77070d
00000037`430f9510 00007ff9`ccf02bdc : 0000019a`7c16e400 0000019a`7c46f928 00000000`00000000 00000000`00000000 : atidxx64!AmdDxGsaFreeCompiledShader+0x1559f0
00000037`430f9570 00007ff9`ccee88c6 : 0000019a`7c01c4b0 0000019a`7c170fe8 0000019a`7c16c828 0000019a`7c46f928 : atidxx64!AmdDxGsaFreeCompiledShader+0x15408c
00000037`430f97b0 00007ff9`ccebd58d : 0000019a`7c01c4b0 0000019a`7c16c828 00000037`430fa130 0000019a`7c01c4b0 : atidxx64!AmdDxGsaFreeCompiledShader+0x139d76
00000037`430f9810 00007ff9`ccdce024 : 0000019a`7c16c828 00000037`430fa130 0000019a`7c16c828 00000037`430fa130 : atidxx64!AmdDxGsaFreeCompiledShader+0x10ea3d
00000037`430f9eb0 00007ff9`cd6c447a : 00000000`00000000 00000037`430f9fe0 00000037`430fa130 0000019a`7bf929b0 : atidxx64!AmdDxGsaFreeCompiledShader+0x1f4d4
00000037`430f9ee0 00007ff9`cd6a1feb : 0000019a`00000000 0000019a`7c16c5e0 00000037`430fa130 00000000`00000000 : atidxx64!AmdDxGsaFreeCompiledShader+0x91592a
00000037`430fa040 00007ff9`cd6c401f : 00000000`00000000 0000019a`7c16c5e0 0000019a`7bf83910 00000000`00000000 : atidxx64!AmdDxGsaFreeCompiledShader+0x8f349b
00000037`430fa0a0 00007ff9`cd6a1d70 : 0000019a`7c16c5e0 0000019a`7bf83910 0000019a`7c16b9c0 00000000`00000000 : atidxx64!AmdDxGsaFreeCompiledShader+0x9154cf
00000037`430fa100 00007ff9`cd6d0cc3 : 0000019a`7c16c5e0 00000000`00000000 00000000`00000000 00000037`430fdfe0 : atidxx64!AmdDxGsaFreeCompiledShader+0x8f3220
00000037`430fdf90 00007ff9`cd6a1a7f : 00000000`00000005 0000019a`7c16b9c0 0000019a`7bfdbff0 0000019a`7bf929b0 : atidxx64!AmdDxGsaFreeCompiledShader+0x922173
00000037`430fdfc0 00007ff9`ccdc9552 : 00000000`00000000 00000000`00000000 00000000`00000000 00000037`430fe170 : atidxx64!AmdDxGsaFreeCompiledShader+0x8f2f2f
00000037`430fe020 00007ff9`ccdc929d : 0000019a`7bfae760 00000000`00000000 0000019a`7bfae798 0000019a`7c163730 : atidxx64!AmdDxGsaFreeCompiledShader+0x1aa02
00000037`430fe060 00007ff9`ccd4a73b : 00000037`00000001 00000000`00000000 00000000`00000000 0000019a`00000000 : atidxx64!AmdDxGsaFreeCompiledShader+0x1a74d
00000037`430fe0e0 00007ff9`cd68f247 : 00000000`00000000 0000019a`75e730d0 0000019a`75e89740 00000037`430fe390 : atidxx64!XdxQueryTlsLookupTable+0x91ab
00000037`430fe120 00007ff9`ccd5f38d : 0000019a`77c2d748 0000019a`75e89740 0000019a`75e92320 00007ff9`d6f656ca : atidxx64!AmdDxGsaFreeCompiledShader+0x8e06f7
00000037`430fe150 00007ff9`d6f5e3d1 : 00000037`430fe5e0 0000019a`77c2d748 00000000`00000000 00000000`45434649 : atidxx64!XdxQueryTlsLookupTable+0x1ddfd
00000037`430fe280 00007ff9`d6f5ddeb : 0000019a`7bd54840 00000000`00000000 0000019a`77c2d738 0000019a`77c2d618 : d3d11!CComputeShader::CLS::FinalConstruct+0x125
00000037`430fe400 00007ff9`d6f5dd27 : 00000037`430feac0 00007ff9`d713a360 0000019a`77c2d600 00000000`00001660 : d3d11!CLayeredObjectWithCLS<CComputeShader>::FinalConstruct+0xa3
00000037`430fe490 00007ff9`d6f7dbc9 : 0000019a`77c2d648 00000037`430feac0 00000037`430feaf0 00007ff9`d713a360 : d3d11!CLayeredObjectWithCLS<CComputeShader>::CreateInstance+0x137
00000037`430fe4f0 00007ff9`d6f8382d : 00000000`00000000 00000000`00000030 00000000`00000000 00000000`00000000 : d3d11!CDevice::CreateLayeredChild+0x10e9
00000037`430fe930 00007ff9`d6f83fdc : 0000019a`77c2d600 00007ff7`8d9a9850 00007ff9`d7138538 00000000`00000030 : d3d11!NDXGI::CDevice::CreateLayeredChild+0x6d
00000037`430fea80 00007ff9`d6f5e046 : 0000019a`7bd4b6a0 00000000`00000018 00000000`00000001 00000000`00000000 : d3d11!NOutermost::CDevice::CreateLayeredChild+0x1bc
00000037`430fec70 00007ff7`8d92271f : 00000000`80070057 0000019a`7bd545e0 0000019a`7bd4bee8 00000000`00000001 : d3d11!CDevice::CreateComputeShader+0x1a6
00000037`430fedc0 00007ff7`8d9242a7 : 0000019a`75e04f90 00000000`00007bac 0000019a`7bd4bee8 0000019a`7bd5c18c : POC_EXEC11+0x271f
00000037`430fee30 00007ff7`8d92c880 : 00000000`00000000 0000019a`75e55f14 0000019a`75e31620 0000019a`00007bac : POC_EXEC11+0x42a7
00000037`430ff260 00007ff7`8d92a8cc : 00000000`00000000 00000000`00000000 00000000`00000001 00007ff9`00000000 : POC_EXEC11+0xc880
00000037`430ff360 00007ff7`8d92a26c : 00000000`00000000 004e0045`0056005f 00000000`00000000 0059004c`004e004f : POC_EXEC11+0xa8cc
00000037`430ff580 00007ff7`8d92324a : 0000019a`75e31620 00000000`00000000 0000019a`75e31620 0000019a`75e0af20 : POC_EXEC11+0xa26c
00000037`430ff770 00007ff7`8d94f5aa : 00000000`0000000a 00000000`00000000 00000000`00000000 00000000`00000000 : POC_EXEC11+0x324a
00000037`430ff7c0 00007ff9`dcb07344 : 00000000`00000000 00000000`00000000 00000000`00000000 00000000`00000000 : POC_EXEC11+0x2f5aa
00000037`430ff800 00007ff9`dd0826b1 : 00000000`00000000 00000000`00000000 00000000`00000000 00000000`00000000 : KERNEL32!BaseThreadInitThunk+0x14
00000037`430ff830 00000000`00000000 : 00000000`00000000 00000000`00000000 00000000`00000000 00000000`00000000 : ntdll!RtlUserThreadStart+0x21
STACK_COMMAND: ~0s ; .cxr ; kb
SYMBOL_NAME: atidxx64+7ff49
MODULE_NAME: atidxx64
IMAGE_NAME: atidxx64.dll
FAILURE_BUCKET_ID: INVALID_POINTER_WRITE_STRING_DEREFERENCE_c0000005_atidxx64.dll!Unknown
OS_VERSION: 10.0.19041.1
BUILDLAB_STR: vb_release
OSPLATFORM_TYPE: x64
OSNAME: Windows 10
IMAGE_VERSION: 31.0.21018.6011
FAILURE_ID_HASH: {fd0d2c7b-9b3d-0989-7368-90e576a2b965}
Followup: MachineOwner
---------
The vendor has released an advisory at: https://www.amd.com/en/resources/product-security/bulletin/amd-sb-6012.html
2023-11-29 - Vendor Disclosure
2024-04-09 - Vendor Patch Release
2024-04-10 - Public Release
Discovered by Piotr Bania of Cisco Talos.