
VirtualBox 7.2.20 - Élevé - Local - Débordement de tas - HGCM SSM cParms wrap
abraxaslabs.tech · github.com/abraxas · @abraxas_null · [email protected] · vbox-hgcm-ssm-cparms
Classe : Débordement de tas Portée : Locale (hôte)
Oracle VM VirtualBox OSS 7.2.20 (f2792cf44) - Oracle
Le HGCM en direct refuse toujours cParms > 32. Le chargement d'un état sauvegardé, non. vmmdevR3HgcmLoadState lit cParms depuis le .sav sans plafond VMMDEV_MAX_HGCM_PARMS, puis dimensionne la commande avec uint32_t cbCmd. À cParms = 0x4000000, ce produit déborde et vaut sizeof(VBOXHGCMCMD) (~120). Le premier stockage de enmType est déjà une écriture de 4 octets au-delà du bloc.
Un utilisateur hôte qui restaure un état sauvegardé hostile provoque un débordement du tas du processus VM. Un invité ne peut pas l'implanter via Save.
| ID | pas encore de CVE |
| Classe | Débordement de tas (écriture hors limites dans le processus VM ; pas une évasion vers le noyau hôte) |
| Portée | Locale (hôte) (UI:R restauration d'état sauvegardé / de snapshot) |
| CWE | CWE-190, CWE-787 |
| CVSS | Élevé : 7.8 CVSS:3.1/AV:L/AC:L/PR:N/UI:R/S:U/C:H/I:H/A:H |
| Produit | VirtualBox OSS |
| Affecté | 7.2.20 (f2792cf44f663989818507e36d3db5f978523c5e) |
| Auth | l'utilisateur hôte restaure une VM sauvegardée, un snapshot ou un .sav |
| Licence | GNU Affero GPL v3.0 |
| Labo | 127.0.0.1 uniquement. Harnais source. Aucun démarrage de VirtualBox, aucune analyse de .sav. |
Remettre à l'opérateur un dossier de VM dont l'état sauvegardé contient un appel CALL VMMDev HGCM en attente. Il clique sur Start sur une VM sauvegardée, restaure un snapshot ou adopte le .sav. La restauration de la console traverse SSMR3 jusqu'à vmmdevR3LoadExec puis vmmdevR3HgcmLoadState. C'est le UI:R. Le résidu est le parseur, pas un hypercall invité.
VMMDev est activé par défaut. Pas de 3D. Pas de Guest Additions. Pas de VRDP. Pas de PUEL.
| Étape | Où | Ce qu'elle permet |
|---|---|---|
| Restauration | UI hôte / VBoxManage startvm sur une VM sauvegardée | L'utilisateur hôte ouvre le .sav hostile. C'est le seul clic requis. |
| Unité SSM | VMMDev vmmdevR3HgcmLoadState (VMMDevHGCM.cpp:2043-2091) | SSMGetU32 dans cParms sans plafond VMMDEV_MAX_HGCM_PARMS (32). |
| Débordement d'allocation | vmmdevR3HgcmCmdAlloc (VMMDevHGCM.cpp:376-381) | uint32_t cbCmd = sizeof(VBOXHGCMCMD) + cParms * (40+24). cParms = 0x4000000 déborde et vaut ~120. RTMemAllocZ de cette taille réussit face au budget du tas. |
| Premier stockage | boucle de chargement paGuestParms[i].enmType (VMMDevHGCM.cpp:2085-2091) | paGuestParms vaut pCmd + sizeof(VBOXHGCMCMD), ce qui correspond déjà à la fin de l'allocation après le débordement. Le premier dword de type est une écriture hors limites de 4 octets. Le flux n'a besoin que de l'en-tête CALL plus un type de paramètre. Il n'a pas besoin de 67 millions d'enregistrements. |
| Type | Provenance | Ce que l'attaquant obtient |
|---|---|---|
| Recon | aucune | Les octets de débordement sont choisis par le sav. Ce n'est pas une fuite. Le contenu du tas n'est pas renvoyé au fichier. |
| Intégrité | prouvé en laboratoire | cParms=0x4000000 fait déborder uint32_t cbCmd à 120. Un seul stockage enmType avec i=0 écrase un canary 0xA5. canary0=56424f58 est le préfixe VBOX de VBOX-HGCM-SSM-CPARMS-WITNESS. Le contrôle cParms=2 laisse le canary intact. |
| Intégrité | déduit | D'autres enregistrements de paramètres contrôlés par le sav (type dword plus champs 32/64 bits ou descripteurs de pointeur) écrivent linéairement au-delà de l'allocation RTMemAllocZ d'environ 120 octets dans VirtualBoxVM / VBoxHeadless. C'est une primitive d'écriture dans le processus de la VM, de la même classe que la memcorr de migration de QEMU. Ce pack ne démontre pas le contrôle du pointeur d'instruction. |
| Disponibilité | déduit | Crash de VBoxVM si l'écrasement n'est pas transformé en écriture contrôlée. Le harnais est un écrasement de canary, pas un crash du processus VirtualBox. |
vmmdevR3HgcmCallAlloc actif rejette toujours cParms > 32 (VMMDevHGCM.cpp:921-926). Un guest ne peut pas implanter le contournement via un Save légitime.VMMDEV_MAX_HGCM_PARMS 32, VMMDEV_MAX_HGCM_DATA_SIZE 128MiB).offValue / cbValue à la complétion est une seconde écriture dans le tas hôte uniquement si les clients HGCM restaurent dans le même sav. Ce n'est pas ce laboratoire.Le host-user / host-kernel complet nécessite encore un reliquat de durcissement. Combiner cet écrasement avec le contournement IDispatch public est écarté.
J'ai épinglé VirtualBox/virtualbox tag v7.2.20 peel f2792cf44. Le HGCM actif a été la première lecture car CVE-2013-5892 était de cette classe : contournement de taille d'argument dans VBOXHGCMCMD. Le chemin actif a toujours la limite :
ASSERT_GUEST_STMT_RETURN( cParms <= (cbHGCMCall - sizeof(VMMDevHGCMCall)) / cbHGCMParmStruct
&& cParms <= VMMDEV_MAX_HGCM_PARMS,
LogRelMax(50, ("VMMDev: request packet with invalid number of HGCM parameters: ...")),
VERR_INVALID_PARAMETER);
Le chargement ne le fait pas. vmmdevR3HgcmLoadState prend cParms depuis le sav et appelle le même allocateur :
const uint32_t cbCmd = sizeof(VBOXHGCMCMD) + cParms * (sizeof(VBOXHGCMGUESTPARM) + sizeof(VBOXHGCMSVCPARM))
+ (enmCmdType == VBOXHGCMCMDTYPE_CONNECT ? sizeof(HGCMServiceLocation) : 0);
Les commentaires AssertCompile sur ce pin placent CMD à 120, guestparm à 40, svcparm à 24. cParms = 0x4000000 fait que le produit 64 bits vaut 0x100000000 + 120. Le stockage dans uint32_t conserve 120. Ensuite :
for (i = 0; i < cParms; ++i)
{
VBOXHGCMGUESTPARM * const pGuestParm = &pCmd->u.call.paGuestParms[i];
rc = pHlp->pfnSSMGetU32(pSSM, &u32);
pGuestParm->enmType = (HGCMFunctionParameterType)u32;
paGuestParms se trouve à pCmd + sizeof(VBOXHGCMCMD). Après le wrap, c'est la fin de l'allocation. Le premier store est déjà OOB.
Fausses pistes déjà consignées : traiter le HGCM live comme le résidu (il plafonne toujours à 32) ; parcourir 67 millions de stores dans le harness (le premier dword est la preuve) ; prétendre qu'un guest peut implanter cela via Save ; gonfler le heap smash du processus VM en évasion vers le noyau hôte ; chaîner un IDispatch public.
Mise en scène : un reverse shell, un parseur .sav, le démarrage de VirtualBox. L'oracle est le wrap plus un smash de canary de VBOX-HGCM-SSM-CPARMS-WITNESS.
cd lab
./run.sh