Oracle VM VirtualBox - VM escape via VGA device
High8.1CVE-2025-30712 · Published May 15, 2025
### Summary An integer overflow vulnerability exists within the VirtualBox vmsvga3dSurfaceMipBufferSize [[source](https://github.com/mirror/vbox/blob/74117a1cb257c00e2a92cf522e8e930bd1c4d64b/src/VBox/Devices/Graphics/DevVGA-SVGA3d-shared.cpp#L324)] function. This vulnerability allows an attacker to manipulate a malloc call such that 0 bytes are allocated while VirtualBox tracks the size of the buffer as a value greater than 0. An attacker can exploit this condition and achieve linear read/write primitives which can then be escalated to arbitrary read/write access within the host's memory. We provide a proof-of-concept that demonstrates how to exploit this vulnerability to fully escape a virtual machine. ### Severity High - ### Proof of Concept We were able to exploit the [VMSVGAGBO](https://github.com/mirror/vbox/blob/74117a1cb257c00e2a92cf522e8e930bd1c4d64b/src/VBox/Devices/Graphics/DevVGA-SVGA.h#L638) defined inside a [VMSVGAMOB](https://github.com/mirror/vbox/blob/74117a1cb257c00e2a92cf522e8e930bd1c4d64b/src/VBox/Devices/Graphics/DevVGA-SVGA.h#L638) object, which are defined below: ```C++ typedef struct VMSVGAGBO { uint32_t fGboFlags; uint32_t ...
Affected versions
| Package | Affected | Fixed in |
|---|---|---|
| VirtualBox Product | all versions | No fix yet |
Details and references
### Summary An integer overflow vulnerability exists within the VirtualBox vmsvga3dSurfaceMipBufferSize [[source](https://github.com/mirror/vbox/blob/74117a1cb257c00e2a92cf522e8e930bd1c4d64b/src/VBox/Devices/Graphics/DevVGA-SVGA3d-shared.cpp#L324)] function. This vulnerability allows an attacker to manipulate a malloc call such that 0 bytes are allocated while VirtualBox tracks the size of the buffer as a value greater than 0. An attacker can exploit this condition and achieve linear read/write primitives which can then be escalated to arbitrary read/write access within the host's memory. We provide a proof-of-concept that demonstrates how to exploit this vulnerability to fully escape a virtual machine. ### Severity High - ### Proof of Concept We were able to exploit the [VMSVGAGBO](https://github.com/mirror/vbox/blob/74117a1cb257c00e2a92cf522e8e930bd1c4d64b/src/VBox/Devices/Graphics/DevVGA-SVGA.h#L638) defined inside a [VMSVGAMOB](https://github.com/mirror/vbox/blob/74117a1cb257c00e2a92cf522e8e930bd1c4d64b/src/VBox/Devices/Graphics/DevVGA-SVGA.h#L638) object, which are defined below: ```C++ typedef struct VMSVGAGBO { uint32_t fGboFlags; uint32_t cTotalPages; uint32_t cbTotal; uint32_t cDescriptors; PVMSVGAGBODESCRIPTOR paDescriptors; void *pvHost; /* Pointer to cbTotal bytes on the host if VMSVGAGBO_F_HOST_BACKED is set. */ } VMSVGAGBO, *PVMSVGAGBO; typedef struct VMSVGAMOB { AVLU32NODECORE Core; /* Key is the mobid. */ RTLISTNODE nodeLRU; VMSVGAGBO Gbo; } VMSVGAMOB, *PVMSVGAMOB; ``` The algorithm is the following: 1. Trigger the allocation of a `buggy_surface` (surface allocated with size 0) 2. Allocate a `GBO` object with a value in `cbTotal` that could be used to finger print our object (a.k.a an “egg”). After trial an error the value `0x1421337` proved to be reliable enough (~100% success rate) 3. Exploit the out of bounds read and check the bytes just after `buggy_surface` if we can find the egg within a short range (the first `0x5a` bytes), assume that our target GBO object is allocated right after the surface. 4. If not, go back to 1 This algorithm proved to be 100% reliable to get a heap grooming within the first <10 attempts. An arbitrary read can be achieved by corrupting `cbTotal` and `pvHost` using the linear write out of bounds with values of the attacker’s choice, then a guest can issue a [vmsvga3dDXReadbackCOTable](https://github.com/mirror/vbox/blob/74117a1cb257c00e2a92cf522e8e930bd1c4d64b/src/VBox/Devices/Graphics/DevVGA-SVGA3d-dx.cpp#L2358) command, that will end up calling [vmsvgaR3MobBackingStoreWriteToGuest](https://github.com/mirror/vbox/blob/74117a1cb257c00e2a92cf522e8e930bd1c4d64b/src/VBox/Devices/Graphics/DevVGA-SVGA3d-dx.cpp#L2358) which will use both corrupted variables to write cbTotal bytes from pvHost into the guest memory. Similarly, an arbitrary write can be achieved with a [GrowCOTable](https://github.com/mirror/vbox/blob/74117a1cb257c00e2a92cf522e8e930bd1c4d64b/src/VBox/Devices/Graphics/DevVGA-SVGA3d-dx.cpp#L2167) command, which upon calling [vmsvgaR3MobBackingStoreCreate](https://github.com/mirror/vbox/blob/74117a1cb257c00e2a92cf522e8e930bd1c4d64b/src/VBox/Devices/Graphics/DevVGA-SVGA3d-dx.cpp#L2192C14-L2192C43) will eventually result in the device [reading](https://github.com/mirror/vbox/blob/74117a1cb257c00e2a92cf522e8e930bd1c4d64b/src/VBox/Devices/Graphics/DevVGA-SVGA-cmd.cpp#L692) `cbTotal` bytes from guest memory into `pvHost`. #### Arbitrary Heap Allocation Another useful primitive that can be achieved via the `GrowCOTable` is the ability to allocate arbitrary chunks of heap memory, this is done via corrupting the `fGboFlags` field, which will result in the device [allocating](https://github.com/mirror/vbox/blob/74117a1cb257c00e2a92cf522e8e930bd1c4d64b/src/VBox/Devices/Graphics/D
- CVSS 3.1
- CVSS:3.1/AV:L/AC:L/PR:H/UI:N/S:C/C:H/I:H/A:L
- Severity from
- GitHub (reviewed advisory)
More Google advisories
All Google| Date | Advisory | Severity | Fixed in |
|---|---|---|---|
| Jun 232025 | OpenAI Operator - Stealing information in a cross-origin iframe | Medium | No fix yet |
| Jun 202025 | Python - Tarfile Realpath Overflow Vulnerability | Critical | No fix yet |
| Jun 122025 | OpenAI Operator - Locking Operator on FullScreen | Medium | No fix yet |
| May 282025 | OpenAI Operator - Exfiltration of Cross-origin URL | High | No fix yet |
| Apr 222025 | OnlyOffice: Docker Man-in-the-middle attack (MitM) | Low | No fix yet |
| Mar 282025 | W3C - CSS Validator XXE | High | See the advisory |