Frequently, PowerShell functions work with sensitive information, i.e. log-on information including passwords, and store this information in variables. Let’s assume a function like this to play with:
function Connect-Server { param ( [Parameter(Mandatory)] [pscredential] [System.Management.Automation.Credential()] $Credential ) "You entered a credential for {0}." -f $Credential.UserName # now you could do something with $Credential }
When you run this function, you get prompted for a credential and a password. Your information surfaces inside the function as $Credential, and when the function completes, the internal information is removed from memory automatically:
PS> Connect-Server -Credential tobias You entered a credential for Tobias. PS> $Credential PS>
However, any attacker could easily run the function dot-sourced. Now, all internal variables remain in memory after the function completed:
PS> . Connect-Server -Credential tobias You entered a credential for Tobias. PS> $Credential UserName Password -------- -------- Tobias System.Security.SecureString PS> $Credential.GetNetworkCredential().Password test PS>
As you see, the attacker now has access to the credential object and can also extract the original password.
To prevent this, you should manually remove sensitive data from memory again. You can remove variables using Remove-Variable:
function Connect-Server { param ( [Parameter(Mandatory)] [pscredential] [System.Management.Automation.Credential()] $Credential ) "You entered a credential for {0}." -f $Credential.UserName # now you could do something with $Credential, i.e. submit it to # other cmdlets that support the -Credential parameter # i.e. # Get-WmiObject -Class Win32_BIOS -ComputerName SomeComputer -Credential $Credential Remove-Variable -Name Credential }
Now the variable can no longer be retrieved:
PS> Remove-Variable -Name Credential PS> . Connect-Server -Credential tobias You entered a credential for Tobias. PS> $credential PS>