PowerShell & Qualys: Get Asset Group Info – Part 2

Today I decided to write another post regarding PowerShell and Qualys Vulnerability Management API.  This post will focus on gathering information about your enrolled Asset Groups.   You can find the complete script on GitHub: https://github.com/MSAdministrator/POSH-Guard/blob/master/Get-QualysAssetGroupInformation

We start of by opening up PowerShell ISE and using our handy “Snippet” shortcut:

PowerShell_ISE_CTRL_+_J

We select the “Cmdlet (Advanced function) – complete” option in the “Snippet” context menu.  Once we have our advanced function template, we then proceed by entering a name for our Qualys Asset Group function.

Since we will be gathering some additional information about our Asset Groups, I am going to name my function:


function Get-QualysAssetGroupInformation

Next, we will start by filling out our “Help” info.  At this point, a lot of people skip this step; I HIGHLY recommend that you do not.  It will help you and anyone else viewing your code, understand what your intention was when writing this function.

Next, we start by looking at our advanced functions template within the body of this function.  The first thing you will see is some default parameters for [CmdletBinding].  With my function, I’m going to weed these parameters down a bit, as they are not really needed.  Your function should look something like this when complete:

function Get-QualysAssetGroupInformation
{
    [CmdletBinding(SupportsShouldProcess=$true, 
                  HelpUri = 'https://raw.githubusercontent.com/MSAdministrator/POSH-Guard/master/Get-QualysAssetGroupInformation',
                  ConfirmImpact='Medium')]
    [Alias()]
    Param
    (
        # Param1 help description
        [parameter(Mandatory=$true,
                   ValueFromPipeline=$true,
                   ValueFromPipelineByPropertyName=$true,
                   HelpMessage="Please provide a credential obejct")]
                   [ValidateNotNullOrEmpty()]
                   [System.Management.Automation.CredentialAttribute()]$credential
        ) 

    Begin
    {
    }
    Process
    {
        
    }
    End
    {
    }
}

After we have the base of this function setup and ready to go, we will start off by adding some code into our Begin block.  Remember, the Begin block will always run once for every call to the function.

	$results = @()
	$assetGroupInfo = @()
        [xml]$assetGroupInfo = Invoke-RestMethod -Uri "https://qualysapi.qualys.com/msp/asset_group_list.php" -Credential $credential

Here I am setting my $assetGroupInfo and a $results variable as empty array’s/hash-table’s. Next, I’m casting my $assetGroupInfo variable as an XML object. This ensures that we receive XML from Invoke-RestMethod Cmdlet.

If we want to make sure that any errors are caught, we should add a Try/Catch block to our Invoke-RestMethod call. Your code should look like this:

 Begin
    {
        $results = @()
        $assetGroupInfo = @()

        Try
        {
            [xml]$assetGroupInfo = Invoke-RestMethod -Uri "https://qualysapi.qualys.com/msp/asset_group_list.php" -Credential $credential
        }
        Catch
        {
            Write-Debug "Error using Invoke-RestMethod: $_"
        }
    }

Now we move to the Process block. This is where we will be parsing our data into our objects. As I mentioned above, we are wanting to gather all our Asset Groups Titles, their assigned IP Addresses, their role, and the users login ID. To do this, we must loop through each item, or branch returned by our query above. Each $item can be considered as an Asset Group. Additionally, we need to loop through each of the users assigned to that Asset Group.

Once we have that data, we want to create a Custom PSObject to hold all of this data. Your code should look like this:

Process
{
	foreach ($item in $assetGroupInfo.SelectNodes("/ASSET_GROUP_LIST/ASSET_GROUP"))
	{
		for ($u=0; $u -lt $($item.ASSIGNED_USERS.ASSIGNED_USER.LOGIN).count;$u++)
		{
			$tempAssetGroupInfo = @()
		                            
                                $props = @{
				userlogin=$($item.ASSIGNED_USERS.ASSIGNED_USER[$u].LOGIN.InnerText)
				userrole=$($item.ASSIGNED_USERS.ASSIGNED_USER[$u].ROLE.InnerText)
                                           assetgrouptitle=$($item.TITLE.InnerText)
                                           ip=$($item.SCANIPS.IP)
                                          }
		
			$tempAssetGroupInfo = New-Object PSObject -Property $props
		        
                                $results += $tempAssetGroupInfo
		}
	}
}

Now, we can either simply put the following line in our End block:

return $results

But, I actually like it to be saved into an XML file. This means that I can use this data with other functions without having to call Qualys again. To be quite frank, as you may know, Qualys is not the fastest website/service out there. Don’t get me wrong, the scanning engines are fast, but their database(s) – not so much.

To return both the object and export the results to an XML, we can just add this one line of code:

Export-Clixml -Path "$env:USERPROFILE\Desktop\QualysData\assetgroupinfo.xml" -InputObject $results

That’s it. We now have a function that can return some details about our Asset Groups within Qualys. Next time, I will focus on creating a function that gathers our enrolled IP Addresses, split’s them into a single list.

Hint: Qualys loves IP ranges (192.168.0.1-192.168.0.123) and their API calls return it the same way. 🙂

Advertisements

PowerShell & Qualys: Authentication – Part 1

I always mean to post more on my blog, but as life gets in the way and work keeps me busy, I always seem to push it to the back-burner. This time, I am hoping to make it stick as a regular routine.

To kick off my new-found motivation to blog more, I am starting a series of posts surrounding PowerShell and Qualys Vulnerability Management API.

To start this off, first I’m going to share some my basic steps with regards to authentication to Qualys VM API v1. This is really basic, but I see a lot of posts around that seem to try to create some “advanced” way of authenticating to Qualys API. You don’t need to do anything fancy.

As with all scripts/modules/etc., I suggest that you get into the habit of using PowerShell ISE and it’s many great keyboard shortcuts to help you get on the right path.

First, open PowerShell ISE and enter the following keyboard shortcut:


CRT + J

Once the “Show Snippets” context menu shows up, select “Advanced Function (Complete)”. I always recommend that you start with a ‘Complete’ Advanced FUnction. This makes your script look much better, and it’s all around a good idea.

Once you have the Snippet loaded, I would begin by coming up with a name; following Microsoft’s approved Verb-Noun naming convention:

Approved Verbs – https://technet.microsoft.com/en-us/library/ms714428(v=vs.85).aspx
Get-Verb Documentation: https://technet.microsoft.com/en-us/library/hh852690.aspx

Next, start adding a “Credential” object parameter to your code. Qualys uses “Basic” authentication, so using Invoke-RestMethod in combination with a “Credential” object is extremely easy.

To capture your credentials into a Credential Object used by Invoke-RestMethod, you simply need the following before you run your function or within your function:


$cred = Get-Credential

Enter your Qualys API username and password.

*NOTE: Do not try to save this credential object to disk or to a file. It’s NOT hard to enter your username and password every time you connect to Qualys API.

Next, you should have the following code in your function:


[xml]$hostinfo = Invoke-RestMethod -Uri "https://qualysapi.qualys.com/msp/get_host_info.php?host_netbios=$netbios&general_info=1"-Credential $credential

I recommend that your $credential object should be passed into your function as a parameter. This will help when you move into more advanced interaction and multiple calls to Qualys VM API.

Now that you have your XML (Type cast) $hostinfo variable, you can then parse the data very, very, very easily.

In my next post I will share with you how to do this to gather some very important data for any Qualys Vulnerability Management Administrator.

If you have any questions, then please leave a comment.


function Test-QualysAuthentication ()
{

[cmdletbinding()]
param (
[parameter(Mandatory=$true,
ValueFromPipelineByPropertyName=$true,
HelpMessage="Please provide a credential obejct")]
[ValidateNotNullOrEmpty()]
[System.Management.Automation.CredentialAttribute()]$credential
)

<# .SYNOPSIS This function tests your Qualys VM API Credentials .PARAMETER Credential Specifices a set of credentials used to query the QualysGuard API .EXAMPLE C:\PS> $cred = Get-Credential
C:\PS> Test-QualysAuthentication -credential $cred

#>

[xml]$hostinfo = Invoke-RestMethod -Uri "https://qualysapi.qualys.com/msp/get_host_info.php?host_netbios=$netbios&general_info=1" -Credential $credential

return $hostinfo
}

PhishReporter: PowerShell Module

If you work in the Info Sec world you know that phishing is a pain in the neck, especially when you’ve been targeted by a large phishing campaign.  I’ve been through these massive phishing attacks, and it is not fun!

One such attack, about a year ago, was especially difficult because the attackers were using very unique tactics and spoofing lots of internal e-mail communications.

Our procedure was to go and find the company that was hosting these phishing URLs and e-mail them to tell them to shut the site down immediately.  Hosting companies like weebly.com, jimdo.com, webs.com, etc. were pretty good at shutting these sites down as soon as they were put online, but this process would take about 5 to 10 minutes and sucked!

Since this last attack, I decided to automate this process.  This new script/tool is a PowerShell Module called PhishReporter.

The PowerShell module can be downloaded on GitHub: https://github.com/MSAdministrator/PhishReporter

This PowerShell Module is designed to send notifications to hosting companies that host phishing URLs by utilizing the major WHOIS/RDAP Abuse Point of Contact (POC) information.

  1. This function takes in a .msg file and strips links from a phishing URL.
  2. After getting the phishig email, it is then converted to it’s IP Address.
  3. Once the IP Address of the hosting website is identified, then we check which WHOIS/RDAP to search.
  4. Each major WHOIS/RDAP is represented: ARIN, APNIC, AFRNIC, LACNIC, & RIPE.
  5. We call the specific WHOIS/RDAP’s API to determine the Abuse POC.
  6. Once we have the POC, we send them an email telling them to shut the website down. This email contains the original email as an attachment, the original phishing link, and e-mail body telling them to remove the website.

This Module came out of necessity. I was sick of trying to contact these individual sites, so I have began automating our response time to these events.

The next steps for this project are to fully integrate into Outlook and automate this even further by enabling a simple text search or based on a selected ‘folder’ event. Please share with the Security community and contribute/improve as you deem fit. I only ask that you share your edits back with this project.

Presentation: Securing Windows with Group Policy

Recently I gave a presentation at MORENet’s 2015 Annual Conference about “Securing Windows with Group Policy”.  This presentation was part of their “Advanced” technology track, and really focused on looking at the current permission levels of your users and deciding if they really need those rights/permissions.

I hope some people find these slides useful or at least a good reference point.  If you have any questions about these slides then please do not hesitate to contact me by leaving a comment below.

Slides can be downloaded here: Securing Windows with Group Policy

NOTE: MORENet’s conference is focused on technology and educational initiatives affecting K-12 & Higher Education within the State of Missouri.

QualysGuard: Decentralized IT & How to organize your Assets

I work for a University with a decentralized IT department: each college, division, department, etc maintains their users.  As a security department who maintains QualysGuard, we were wanting each department to scan their own assets and re-mediate all vulnerabilities found in these scans based on the following policy:

  • Level 4 and Level 5 vulnerabilities must be re-mediated within 15 days
  • Level 3 vulnerabilities must be re-mediated within 30 days
  • Level 2 vulnerabilities must be re-mediated within the next semesters
  • Level 1 vulnerabilities must be re-mediated whenever possible

WIth this policy in mind, we began rolling out our QualysGuard service using the following methods.  We would create Asset Groups for each group of servers that belong to one of the following: a department, college, division, application group, etc.  Each Asset Group would be additionally subdivided into each network core.  For example, if you have a Athletics department, they may have assets in all the different network cores (Faculty/Staff Network, Data Center, DMZ, Residential Network, etc.).  Because each of these departments will have multiple assets in multiple network cores, we relied heavily on our naming conventions.  Our naming convention is the following for Asset Groups: CAMPUS DEPT NETWORK Assets (SCANNER NAME) -> CAMPUS Athletics DC Assets (DC_SCANNER)

When dealing with QualysGuard in a decentralized IT infrastructure, your naming convention will save you!

Once you have a group of Assets in their respective Asset Groups, then we add them to their own Business Unit.  Remember that you must a Unit Manager (at least 1), and you may any number of Scanner and Reader roles.  You can additionally assign a role to specific Asset Groups within the Business Unit (or another Business Unit).

Please see the following graphic, which outlines what was previously stated:

2015-01-11 14_12_21-Business Unit Hierarchy

Remember, when you are rolling out your QualysGuard VM infrastructure you will want to plan (in great detail) your roll-out.  Creating a roll-out plan that relies on system owners to take responsibility for their own systems, instead of System Administrators and/or Security Analyst is the idea goal.  By doing this, it highlights the importance for security in your organization as well as giving everyone insight into the security posture of their organization.  Hopefully they will see QualysGuard as a tool of transparency that helps strengthen your organization vulnerability management life cycle management.