web-dev-qa-db-ja.com

.EXEをBase64にエンコード/デコードする

Base-64文字列にエンコードしたい.NET exeファイルがあり、後でPowershellを使用してBase64文字列から.exeファイルにデコードします。

私がこれまでに持っているもの。exeファイルを生成しますただし、このファイルはWindowsで実行可能なアプリケーションとして認識されず、常に渡されるファイルとは異なる長さですエンコードスクリプト。

ここで間違ったエンコーディングを使用している可能性がありますが、よくわかりません。

スクリプトのエンコード:

Function Get-FileName($initialDirectory)
{   
 [System.Reflection.Assembly]::LoadWithPartialName("System.windows.forms") | Out-Null
$OpenFileDialog = New-Object System.Windows.Forms.OpenFileDialog
$OpenFileDialog.initialDirectory = $initialDirectory
$OpenFileDialog.filter = "All files (*.*)| *.*"
$OpenFileDialog.ShowDialog() | Out-Null
$FileName = $OpenFileDialog.filename
$FileName

} #end function Get-FileName

$FileName = Get-FileName

$Data = get-content $FileName
$Bytes = [System.Text.Encoding]::Unicode.GetBytes($Data)
$EncodedData = [Convert]::ToBase64String($Bytes)

デコードスクリプト:

$Data = get-content $FileName
$Bytes = [System.Text.Encoding]::UTF8.GetBytes($Data)
$EncodedData = [System.Text.Encoding]::Unicode.GetString([System.Convert]::FromBase64String($Bytes))

$EncodedData | Out-File ( $FileName )
17
schizoid04

問題の原因は次のとおりです。

  1. Get-Contentなし-rawはファイルを行の配列に分割し、コードを破壊します
  2. Text.Encodingは、バイナリコードをテキストとして解釈し、コードを破壊します。
  3. Out-Fileはバイナリデータではなくテキストデータ用です

正しいアプローチはIO.Fileを使用することです ReadAllBytes

$base64string = [Convert]::ToBase64String([IO.File]::ReadAllBytes($FileName))

および WriteAllBytes デコードする場合:

[IO.File]::WriteAllBytes($FileName, [Convert]::FromBase64String($base64string))
34
wOxxOm

同様のタスクを実行したい人のために代替手段を追加するために、Windowsにはcertutil.exe(証明書を操作するツール)。ファイルをbase64でエンコードおよびデコードできます。

certutil -encode test.exe test.txt
certutil -decode test.txt test.exe
17
Swonkie