Skip to content

Instantly share code, notes, and snippets.

Show Gist options
  • Save cdelashmutt-pivotal/03aca91a9d01e6fc72771d3fa01cf5ea to your computer and use it in GitHub Desktop.
Save cdelashmutt-pivotal/03aca91a9d01e6fc72771d3fa01cf5ea to your computer and use it in GitHub Desktop.
Generate OpenSSH compatible public and private key files in Powershell
<#
.SYNOPSIS
Create an OpenSSH compatible Public and Private Key in pure Powershell
.DESCRIPTION
Many scripts rely on the openssh or openssl tools to be available to generate public and private keys compatible with OpenSSH, but this script relies purely on Powershell (and some .NET classes already included) to generate public and private keys.
.EXAMPLE
PS /git/scripts> ./Create-OpenSSHPubAndPrivateKeys.ps1 -PublicKeyPath my-key.pub -PrivateKeyPath my-key
.LINK
mailto:grog@grogscave.net
#>
[CmdletBinding()]
param (
# The path to use to store the public key file
[Parameter(Mandatory=$true)]
[string]
$PublicKeyFile,
# The path to use to store the private key file
[Parameter(Mandatory=$true)]
[string]
$PrivateKeyFile
)
# SSH key generation significantly cribbed from https://stackoverflow.com/posts/3588388/revisions
# and https://www.thedigitalcatonline.com/blog/2018/04/25/rsa-keys/
function Export-SSHPublicKey([System.Security.Cryptography.RSACryptoServiceProvider] $csp) {
$result = @((Get-LengthAndData ([System.Text.Encoding]::ASCII.GetBytes("ssh-rsa"))))
$rsaParams = $rsa.ExportParameters($false)
$result += Get-LengthAndData $rsaParams.Exponent
$result += Get-LengthAndData $(@(0x0)+$rsaParams.Modulus)
return [System.Convert]::ToBase64String($result)
}
function Get-LengthAndData([byte[]] $data) {
$reverseSize = [System.BitConverter]::GetBytes($data.Length)
[System.Array]::Reverse($reverseSize)
return $reverseSize + $data
}
# Generate RSA Key Pair
Write-Host "Creating a 2048-bit RSA Keypair"
$rsa = New-Object System.Security.Cryptography.RSACryptoServiceProvider -ArgumentList 2048
Write-Host "Saving private and public keys as $PrivateKeyFile and $PublicKeyFile"
#Private Key
"-----BEGIN RSA PRIVATE KEY-----`n" + [System.Convert]::ToBase64String( $rsa.ExportRSAPrivateKey(), [Base64FormattingOptions]::InsertLineBreaks) + "`n-----END RSA PRIVATE KEY-----" | Out-File -Encoding utf8NoBOM $PrivateKeyFile
#Public Key
"ssh-rsa " + (Export-SSHPublicKey $rsa) + " tkg-vms" | Out-File -Encoding utf8NoBOM $PublicKeyFile
@cdelashmutt-pivotal
Copy link
Author

Also, it looks like older versions of Powershell (even up to Powershell 5.1) still use the older .NET Framework 4.8 and lower. You might have better luck on Powershell 6+ if you can use those on whatever machine you are on.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment