1+ $ErrorActionPreference = ' Stop'
2+ Import-Module vm.common - Force - DisableNameChecking
3+
4+ try {
5+ $toolName = ' suricata'
6+ $category = VM- Get-Category ($MyInvocation.MyCommand.Definition )
7+ $toolDir = Join-Path ${Env: ProgramFiles} $toolName
8+ $executablePath = Join-Path $toolDir " $toolName .exe"
9+ $exeUrl = " https://www.openinfosecfoundation.org/download/windows/Suricata-7.0.10-1-64bit.msi"
10+ $sha256 = " b32a6ca8a793a603a23de307c83831c874099f50bbcd2710ee8325d69a49fb44"
11+
12+ $packageArgs = @ {
13+ toolName = $toolName
14+ category = $category
15+ filetype = " MSI"
16+ silentArgs = " /qn /norestart"
17+ executablePath = $executablePath
18+ url = $exeUrl
19+ sha256 = $sha256
20+ consoleApp = $true
21+ }
22+
23+ VM- Install-With - Installer @packageArgs
24+
25+ # Delete default desktop shortcut
26+ $desktopShortcutPath = " ${Env: HomeDrive} \Users\*\Desktop\$toolName *.lnk"
27+ Remove-Item - Path $desktopShortcutPath - ErrorAction SilentlyContinue
28+
29+ # Rules configuration and download
30+ $rulesXmlPath = " $ ( Split-Path - parent $MyInvocation.MyCommand.Definition ) /rules.xml"
31+ $rulesXml = [xml ](Get-Content $rulesXmlPath )
32+ $rulesDir = Join-Path $toolDir " rules" - Resolve
33+ $rules = $rulesXml.rules.rule
34+
35+ # Tempdir for rules been added
36+ # Rules are added to tempdir before been added to default rule folder as other default rules exist in default folder
37+ # Rules filenames are needed for adding to config files
38+ $tempToolDir = Join-Path ${Env: TEMP} " $toolName .vm"
39+ $tempRuleDir = Join-Path $tempToolDir " rules"
40+
41+ foreach ($rule in $rules ) {
42+ VM- Write-Log " INFO" " Attempting to install rule: $ ( $rule.name ) "
43+ $filePath = Join-Path $tempToolDir ([System.IO.Path ]::GetFileName($rule.url ))
44+
45+ # Create rule specific temp folder
46+ $tempRuleSpecificFolder = Join-Path $tempRuleDir $rule.name
47+ New-Item $tempRuleSpecificFolder - ItemType Directory - Force
48+ try {
49+ Invoke-WebRequest - Uri $rule.url - OutFile $filePath - ErrorAction Stop
50+ # If the rule URL is a ZIP archive (collection of multiple rule files)
51+ if ($filePath -like ' *.zip' ) {
52+ VM- Write-Log " INFO" " ZIP file detected."
53+ Get-ChocolateyUnzip - FileFullPath $filePath - Destination $tempRuleSpecificFolder | Out-Null
54+
55+ # If the rule URL is one rules file
56+ } elseif ($filePath -like ' *.rules' ) {
57+ VM- Write-Log " INFO" " Rules file detected. Moving to $tempRuleSpecificFolder ..."
58+ Move-Item - Path $filePath - Destination $tempRuleSpecificFolder
59+
60+ # Any other types of url resource is unsupported
61+ } else {
62+ throw " Unsupported file type: '$filePath '. Only .zip and .rule are allowed."
63+ }
64+ } catch {
65+ VM- Write-Log " WARN" " Failed rule: $filePath . Cause: $ ( $_.Exception.Message ) "
66+ }
67+ }
68+
69+ $allRuleFiles = Get-ChildItem - Path $tempRuleDir - Recurse - File - Filter * .rules
70+
71+ $rulesConfigPath = Join-Path $toolDir " suricata.yaml" - Resolve
72+ $rulesConfigLines = Get-Content - Path $rulesConfigPath
73+
74+ # Index of the location in the yaml where `rule-files:` is specified
75+ # Also collect all rules references in the config file
76+ $ruleFilesIndex = $null
77+ $rulesList = @ ()
78+ for ($i = 0 ; $i -lt $rulesConfigLines.Count ; $i ++ ) {
79+ $line = $rulesConfigLines [$i ].Trim()
80+
81+ # Set ruleFilesIndex when `rule-files:` found
82+ if ($line -match ' ^rule-files:$' ) {
83+ $ruleFilesIndex = $i
84+ continue
85+ }
86+
87+ # Only when `rule-files` found, collect the rules references
88+ if ($null -ne $ruleFilesIndex ){
89+
90+ # Break rules reference search if the line does not start with '- .*'
91+ if ($line -notmatch " - .*" ){
92+ break
93+ }
94+ else {
95+ if ($line -match ' \.rules$' ){
96+ $cleanLine = $line.TrimStart (' - ' )
97+ $rulesList += $cleanLine
98+ }
99+ }
100+ }
101+ }
102+
103+ # The config file must have `rule-files:`, throw an error if not found
104+ if ($null -eq $ruleFilesIndex ) {
105+ throw " Line with 'rule-files:' string not found in the config file."
106+ }
107+
108+ # Move all rule files in temp rule folder to the suricata rule folder
109+ # Add rules to `suricata.yaml`
110+ VM- Write-Log " INFO" " Moving rule-files to $rulesDir ..."
111+ foreach ($ruleFile in $allRuleFiles ){
112+ Move-Item - Path $ruleFile.FullName - Destination $rulesDir - Force
113+ if (-not ($rulesList -contains $ruleFile.Name )){
114+ $newRuleLine = " - $ ( $ruleFile.Name ) "
115+ # Add rule to config file
116+ $rulesConfigLines = $rulesConfigLines [0 .. $ruleFilesIndex ] + $newRuleLine + $rulesConfigLines [($ruleFilesIndex + 1 ).. ($rulesConfigLines.Length - 1 )]
117+ VM- Write-Log " INFO" " [+] Rule-file $ ( $ruleFile.Name ) added to $rulesDir . Added rule-file reference to config file."
118+ }
119+ else {
120+ VM- Write-Log " INFO" " [+] Rule-file $ ( $ruleFile.Name ) added to $rulesDir . Rule-file reference already exist in config file."
121+ }
122+ }
123+
124+ # Save the updated content back to the file
125+ $rulesConfigLines | Set-Content - Path $rulesConfigPath
126+ }
127+ catch {
128+ VM- Write-Log - Exception $_
129+ }
0 commit comments