Create Custom Mitigation QID Scripts 

The Custom Mitigation QID Script allows you to execute specific actions to reduce the risk of an active vulnerability identified in your system. This script is used to reduce the risk or impact of a vulnerability, applying temporary measures to minimize the vulnerability's potential impact.

When the script is successfully run, the associated vulnerability is mitigated, meaning the risk has been addressed for now, even though the underlying issue still exists.

You can only create and store Custom Mitigation QID scripts in CAR. These scripts can only be executed through the Patch Management module.

You can create a Custom Mitigation QID script using the following ways:

  • Manually enter a script
  • Upload script from local machine
  • Import from GitHub

To create a Custom Mitigation QID script, follow these steps:

  1. Navigate to Scripts > Scripts > CreateNew Script.

    The Create New Script page is displayed. 

  2. Enter a Name and Description for the script.

    script basic information.

  3. Click Next to view the Script Details page.
  4. Select the Type of Script as Mitigation QID.
  5. Select Platform (Windows or Linux).
  6. Complete the following Mitigation QID Details:
    Fields Description
    QID Number Provide a QID number.
    QID Severity It is a QID Severity. You can select from values 1 (minimum) to 5 (urgent).
    Impact Factor Provide a value to determine the impact of the script on a vulnerability.
    For the mitigation script, the value should be between 1-99

    This indicates that the vulnerability has been mitigated till the provided value.

    Implication The implication indicates whether the impact of the script on a vulnerability is permanent or temporary.

    The Implication value for the mitigation script is Temporary.

    The Implication field is pre-populated depending upon the selected Type of Script.

    CVE IDs Provide CVE IDs that are associated with a specific QID.
    Mitigation Type Provide a text related to the mitigation type.

  7. Select the Scripting Language from the list in which you want to write the script.

    The list of scripting languages for Windows and Linux are different. 

    Platform Supported Scripting Language
    Windows PowerShell-Command, PowerShell-Script, Python, and VBScript
    Linux Lua, Perl, Python, and Shell
  8. Select a script Category from the list.
  9. Specify the Timeout Limit in seconds, minutes, or hours.

    The Timeout Limit lets you define how long a script must be in execution.

    The Timeout Limit for all Windows and Linux assets ranges from one second to 48 hours. The default value is 300 seconds.

    Add script.

  10. In the Scripts section, select Enter Script and manually enter the script by typing or copy-pasting it from another source.

    You also have the following options to provide the Mitigation QID script:

    Example Mitigation ScriptExample Mitigation Script

    param (
        [switch]$verify,
        [switch]$mitigate,
        [switch]$rollback
    )
    $ErrorActionPreference = 'Stop';
    Set-Variable -Name SUCCESS -Value 0 -Option Constant;
    Set-Variable -Name FAILURE -Value 1 -Option Constant;
    Set-Variable -Name UNMITIGATED -Value 201 -Option Constant;
    Set-Variable -Name START_PATH -Value "Registry::HKU\" -Option Constant;
    Set-Variable -Name STOP_PATH -Value "SOFTWARE\Microsoft\Windows\CurrentVersion\" -Option Constant;
    Set-Variable -Name EXPLORER_KEY -Value "Explorer" -Option Constant;
    Set-Variable -Name ADVANCED_KEY -Value "Advanced" -Option Constant;
    Set-Variable -Name ICONS_ONLY_PROP -Value "IconsOnly" -Option Constant;
    Set-Variable -Name MIT -Value 1 -Option Constant;
    Set-Variable -Name ROLL -Value 0 -Option Constant;
    Set-Variable -Name DTYPE -Value "DWORD" -Option Constant;
    Set-Variable -Name DEF -Value "default" -Option Constant;
    Set-Variable -Name ACTION_MIT -Value "ACTION_MIT" -Option Constant;
    Set-Variable -Name ACTION_ROLL -Value "ACTION_ROLL" -Option Constant;
    Set-Variable -Name EXPLORER_PROCESS -Value "explorer" -Option Constant;
    [hashtable]$RetCode = @{
        WrongValue = 99
        NoExplorer = 98
        NoAdvanced = 97
        NoProp = 96
        Ok = 95
        NotOk = 94;
    };
    function Find-RegistryKey() {
        [OutputType([string])]
        param(
            [Parameter(Mandatory = $true)]
            [string]
            $path,
            [Parameter(Mandatory = $true)]
            [string]
            $key
        )
        $item = Get-ChildItem -Path $path -ErrorAction SilentlyContinue | Where-Object { $_.Name -like "*\$key" };
        return $item.Name;
    }
    function Find-RegistryKV() {
        [OutputType([int])]
        param (
            [Parameter(Mandatory = $true)]
            [string]$path,
            [Parameter(Mandatory = $true)]
            [string]$vname,
            [Parameter(Mandatory = $true)]
            $vdata
        )
        $found = Get-ItemProperty -Path $path | Select-Object $vname;
        if ($found.Length -eq 0) {
            return $RetCode.NoProp;
        }
        if ($found.$vname -ne $vdata) {
            return $RetCode.WrongValue;
        }
        return $RetCode.Ok;
    }
    function Test-HKUPath {
        [OutputType([string], [bool])]
        param (
            [Parameter(Mandatory = $true)]
            [string]$base,
            [Parameter(Mandatory = $true)]
            [string]$sid
        )
        $found = Find-RegistryKey -path $base -key $sid;
        $path = Join-Path -Path $base -ChildPath $sid;
        if ($found.Length -eq 0) {
            return ($path, $false);
        }
        return ($path, $true);
    }
    function Verify() {
        [OutputType([hashtable])]
        [hashtable]$statMap = @{};
        $statMap[$DEF] = $RetCode.NotOk;
        $users = Get-WmiObject -Class Win32_UserAccount -Filter "LocalAccount=True" | Where-Object { $_.Status -eq "Ok" }
        foreach($user in $users) {
            $outs = Test-HKUPath -base $START_PATH -sid $user.SID;
            $path = $outs[0];
            if (!$outs[1]) {
                Write-Host "Registry Path: $path not found" -ForegroundColor Yellow;
                continue;
            }
            $path = Join-Path -Path $START_PATH -ChildPath $user.SID;
            $path = Join-Path -Path $path -ChildPath $STOP_PATH;
            $found = Find-RegistryKey -path $path -key $EXPLORER_KEY;
            if ($found.Length -eq 0) {
                $statMap[$path] = $RetCode.NoExplorer;
                continue;
            }
            $path = Join-Path -Path $path -ChildPath $EXPLORER_KEY;
            $found = Find-RegistryKey -path $path -key $ADVANCED_KEY;
            if ($found.Length -eq 0) {
                $statMap[$path] = $RetCode.NoAdvanced;
                continue;
            }
            $path = Join-Path -Path $path -ChildPath $ADVANCED_KEY;
            $status = Find-RegistryKV -path $path -vname $ICONS_ONLY_PROP -vdata $MIT;
            $statMap[$path] = $status;
            if ($status -eq $RetCode.Ok) {
                $statMap[$DEF] = $RetCode.Ok;
            }
        }
        return $statMap;
    }
    function Update-Registry() {
        param (
            [Parameter(Mandatory = $true)]
            [hashtable]
            $statMap,
            [Parameter(Mandatory = $true)]
            [string]
            $action
        )
        foreach($path in $statMap.Keys) {
            if ($path -eq $DEF) {
                continue;
            }
            [int]$code = $statMap[$path];
            switch ($code) {
                $RetCode.NoExplorer {
                    if ($action -eq $ACTION_ROLL) {
                        continue;
                    }
                }
                $RetCode.NoAdvanced {
                    if ($action -eq $ACTION_ROLL) {
                        continue;
                    }
                }
                $RetCode.NoProp {
                    if ($action -eq $ACTION_ROLL) {
                        continue;
                    }
                    New-ItemProperty -Path $path -Name $ICONS_ONLY_PROP -PropertyType $DTYPE -Value $MIT;
                }
                $RetCode.WrongValue {
                    if ($action -eq $ACTION_ROLL) {
                        continue;
                    }
                    Set-ItemProperty -Path $path -Name $ICONS_ONLY_PROP -Value $MIT;
                }
                $RetCode.Ok {
                    if ($action -eq $ACTION_MIT) {
                        continue;
                    }
                    Set-ItemProperty -Path $path -Name $ICONS_ONLY_PROP -Value $ROLL;
                }
            }
        }
        Stop-Process -Name $EXPLORER_PROCESS -Force;
        Start-Process $EXPLORER_PROCESS;
    }
    function Mitigate() {
        [hashtable]$statMap = Verify;
        if ($statMap[$DEF] -eq $RetCode.Ok) {
            Write-Host "Mitigation Exists" -ForegroundColor Cyan;
            return $SUCCESS;
        }
        Update-Registry -statMap $statMap -action $ACTION_MIT;
        Write-Host "Mitigation Done";
        return $SUCCESS;
    }
    function Rollback() {
        [hashtable]$statMap = Verify;
        if ($statMap[$DEF] -eq $RetCode.NotOk) {
            Write-Host "Nothing to Rollback" -ForegroundColor Red;
            return $SUCCESS;
        }
        Update-Registry -statMap $statMap -action $ACTION_ROLL;
        Write-Host "Rollback Done";
        return $SUCCESS;
    }
    function Main() {
        if ($verify) {
            [hashtable]$statMap = Verify;
            if ($statMap[$DEF] -eq $RetCode.Ok) {
                Write-Host "Mitigation Exists" -ForegroundColor Blue;
                # return $SUCCESS;
            }
            Write-Host "Mitigation does NOT exist" -ForegroundColor Red;
            # return $UNMITIGATED;
        }
        if ($mitigate) {
            # return Mitigate;
        }
        if ($rollback) {
            # return Rollback;
        }
        if (-not ($verify -or $mitigate -or $rollback)) {
            Write-Host "Running -mitigate as DEFAULT option" -ForegroundColor Yellow;
            # return Mitigate;
        }
    }
    function Init() {
        try {
            $status = Main;
            exit $status;
        }
        catch {
            Write-Host $_;
            exit $FAILURE;
        }
    }
    Init;
  11. Select the Create Script in the approved state checkbox to create the script in approved state.

    This option is available only for the manager role.

    The user with any other user role must get the script approved by an authorized user.
    For more details, refer to Qualys CAR RBAC

    Approved script.

  12. Click Next to view the Review and Confirm page.
  13. Review the details and click Confirm & Save.

The Mitigation QID script is created and displayed on the Scripts tab.

As CAR is used as a repository for storing the Mitigation QID script, you can only View Details, Edit, Clone, Export Script, and Deprecate.

Edit the Mitigation QID Script

To modify the approved script, follow these steps:

  1. Navigate to the Scripts tab.
  2. To edit a script, select an approved QID script and click Edit on the Quick Actions menu.

    The Basic Information page is displayed.

  3. Modify the details as required and click Next to view the Scripts Details page.

  4. Modify the editable content as required.

  5. Provide the Reason for Edit.

    script edit reason.

  6. Click Next to view the Review and Confirm page.
  7. Review the script and click Update to save the changes to the script.

Related Topics

Cloning Scripts

Exporting Scripts

Deprecating Scripts