-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathInvoke-SvcHostInstaller.ps1
More file actions
97 lines (71 loc) · 3.55 KB
/
Copy pathInvoke-SvcHostInstaller.ps1
File metadata and controls
97 lines (71 loc) · 3.55 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
function Install-SvcHostService{
Param(
[Parameter( Position = 0, Mandatory = $true )]
[String]$ServiceName,
[Parameter( Position = 1, Mandatory = $true )]
[String]$DisplayName,
[Parameter( Position = 2, Mandatory = $true )]
[String]$ServiceDll,
[Parameter( Position = 3, Mandatory = $true )]
[String]$ServicePrimaryGroup,
[Parameter( Position = 4, Mandatory = $false )]
[AllowNull()]
[AllowEmptyString()]
[string]$Description = "Example of a Service Loaded via SVCHOST"
)
if(!$PSBoundParameters.ContainsKey('Description')){
Write-Warning "Description is set to the default. This is NOT opsec :eyes:"
}
#Check for older versions of powershell since the "Requires" thing is >=4
$currentPrincipal = New-Object Security.Principal.WindowsPrincipal([Security.Principal.WindowsIdentity]::GetCurrent())
if(!$currentPrincipal.IsInRole([Security.Principal.WindowsBuiltInRole]::Administrator)){
Write-Error -Exception "Not Running as Administrator" -Message "Please run this script as an administrator."
Exit
}
#Checks are below hereeeee
$PossibleGroups = Get-Item "HKLM:\SOFTWARE\Microsoft\Windows NT\CurrentVersion\SVCHOST" | Select-Object -ExpandProperty Property
#First check if the request service group exsists
if(!$PossibleGroups -contains $ServicePrimaryGroup){
Write-Error -Exception "Bad Service Group" -Message "Requested service group not found."
Exit
}
#Check if the service already exsists
$ServiceCheck = Get-Service -ServiceName $ServiceName -ErrorAction "SilentlyContinue"
#get the full path and make sure it exsits
$FullPath = Get-Item $ServiceDll | Select-Object FullName
$Temp = Test-Path $FullPath.FullName
if(!$Temp){
Write-Error -Exception "File Note Found" -Message "The Requested Dll was not found."
Exit
}
$DllName = Get-Item $ServiceDll | Select-Object Name
$FullSystemPath = "C:\Windows\System32\" + $DllName.Name
#Move it to system32 to be nice :)
Copy-Item -Path $FullPath.FullName -Destination $FullSystemPath -Force
$SvcPath = "C:\Windows\System32\svchost.exe -k " + $ServicePrimaryGroup
if($ServiceCheck){
Write-Error -Exception "Bad Service Name" -Message "Requested service name already in use."
Exit
}
#Create the service using New-Service
#many change this later
New-Service -Name $ServiceName -DisplayName $DisplayName -BinaryPathName $SvcPath -StartupType Automatic -Description $Description
$BasePath = "HKLM:\SYSTEM\CurrentControlSet\Services\" + $ServiceName
$RegPath = $BasePath + "\Parameters"
#Create the "Parameters" Key bc by default it is not created with New-Service
New-Item $RegPath
#Create the value ServiceDLL
#MUST BE FULL PATH
New-ItemProperty -Path $RegPath -PropertyType ExpandString -Name ServiceDll -Value $FullSystemPath
#Set the service type to WIN32_SHARED_PROCESS (0x20)
Set-ItemProperty -Path $BasePath -Name Type -Value 0x20
#https://stackoverflow.com/questions/27238523/editing-a-multistring-array-for-a-registry-value-in-powershell
$GroupRegLocation = "SOFTWARE\Microsoft\Windows NT\CurrentVersion\SVCHOST"
$reg = [Microsoft.Win32.RegistryKey]::OpenRemoteBaseKey('LocalMachine', "")
$key = $reg.OpenSubKey($GroupRegLocation, $true)
$arr = $key.GetValue($ServicePrimaryGroup)
$arr += $ServiceName
$key.SetValue($ServicePrimaryGroup, [string[]]$arr, 'MultiString')
Start-Service $ServiceName | Out-Null
Get-Service $ServiceName
}